← Back to Feed CACHED · 2026-10-07 20:54:09 · CACHE_KEY CVE-2026-32475
CVE-2026-32475 · CWE-434 · Disclosed 2026-08-19

Elementor Pro Forms Unauthenticated Arbitrary File Upload to RCE via Array Validation Bypass

ASSESSED — NOISGATE
Vendor
—
—
—
Reassessed
—
—
—
Verdict: —
Do you agree?
01 · The Real Story

The bouncer checks the first ID, sees it's blank, and walks away — letting everyone behind that person into the club unchecked

CVE-2026-32475 is an unauthenticated arbitrary file upload flaw in Elementor Pro ≤ 4.2.1, the most popular WordPress page builder with 10 million+ active installations powering roughly a third of all WordPress sites. The bug lives in the Forms module's File Upload field handler (modules/forms/fields/upload.php). Two code loops — validation() and process_field() — process the same uploaded files but disagree on what to do with an empty entry. The validator hits an empty first file part (UPLOAD_ERR_NO_FILE) and executes return, killing the entire check. The processor hits the same empty entry and executes continue, skipping only that entry and happily moving the attacker's PHP payload — submitted as the second file part — into /wp-content/uploads/elementor/forms/ with a .php extension. No login, no nonce, no user interaction. The file is callable via direct HTTP GET and gives the attacker a web shell.

The vendor's CRITICAL / 9.0 rating is honest and, if anything, slightly conservative. The CVSS vector encodes AC:H because the attacker must race uniqid() to recover the dropped filename, but multiple public PoCs (Boreas37, 4minx, absholi7ly on GitHub) solve this trivially with concurrent thread pools, and Wordfence confirmed 190,000+ real-world exploitation attempts within the first five days of disclosure. Patchstack scored it 9.0; Wordfence scored it 9.8. In practice, the attack complexity is closer to Low for any attacker using automated tooling. The only real prerequisite — a published form with a non-required File Upload field — is a bread-and-butter Elementor Pro feature present on a large fraction of installations. This is a legitimate CRITICAL that we nudge to 9.2 to reflect the weaponized, actively-exploited reality.

"Unauthenticated RCE in Elementor Pro is actively exploited; patch or disable file upload fields now."
02 · The Attack Path

5 steps from start to impact.

STEP 01

Identify vulnerable Elementor Pro form

The attacker crawls the target WordPress site looking for pages containing Elementor Pro forms with a File Upload field. These are identifiable via the elementor-widget-form CSS class and upload field type in the rendered HTML. Automated scanners like WPScan or custom nuclei templates can fingerprint Elementor Pro versions from asset URLs (/wp-content/plugins/elementor-pro/assets/). This step is entirely passive and unauthenticated.
Conditions required:
  • Target runs Elementor Pro ≤ 4.2.1
  • At least one published page contains an Elementor Pro form with a File Upload field
  • File Upload field is not set as required (default state)
Where this breaks in practice:
  • Not all Elementor Pro sites have forms with file upload fields — this narrows the target population
  • Sites behind WAFs with WordPress-specific rulesets (Cloudflare, Sucuri, Wordfence) may block reconnaissance
Detection/coverage: WPScan, nuclei Elementor Pro version detection templates, Wordfence vulnerability scanner
STEP 02

Craft desynchronized multipart upload

The attacker constructs a multipart POST request to /wp-admin/admin-ajax.php with action=elementor_pro_forms_send_form. The file field is submitted as an array: index [0] is an empty file entry (blank filename, triggering UPLOAD_ERR_NO_FILE), and index [1] is the PHP web shell payload with a .php extension. The empty first entry causes validation() to return early, bypassing the extension blocklist entirely. The PoC tools (Boreas37's stdlib Python, 4minx's exploit) automate this construction. No authentication or CSRF token is required.
Conditions required:
  • Form's POST endpoint is reachable
  • No WAF rule blocks the crafted multipart structure
Where this breaks in practice:
  • Managed WordPress hosts (WP Engine, Kinsta, Pantheon) often disable PHP execution in /uploads/ directories, which blocks step 4 even if the file lands
  • Some WAFs specifically block .php in upload filenames at the network layer
Detection/coverage: Wordfence firewall rule (deployed Aug 19), ModSecurity CRS rule 933110, Cloudflare WAF managed ruleset for WordPress
STEP 03

PHP file written to public uploads directory

The process_field() loop encounters the empty first entry, executes continue, then moves the PHP payload to /wp-content/uploads/elementor/forms/<uniqid>.php. The filename is generated by PHP's uniqid() — a 13-character hex string derived from server microsecond time. The file is world-readable via direct HTTP request. At this point the attacker has achieved arbitrary file write but not yet code execution.
Conditions required:
  • Web server process has write permission to uploads directory (standard WordPress)
  • No filesystem-level restriction prevents .php file creation in uploads
Where this breaks in practice:
  • Hosts with open_basedir or AppArmor/SELinux profiles may restrict writes
  • Some security plugins (iThemes, Wordfence) monitor uploads directory for new PHP files and alert or quarantine
Detection/coverage: File integrity monitoring (OSSEC, Wazuh, Wordfence file scanner), inotifywait on uploads directory
STEP 04

Recover dropped filename via uniqid sweep

The attacker must determine the uniqid()-based filename to request the shell. Public PoCs use concurrent thread pools (default 24 workers) to probe filenames across the microsecond window surrounding the upload timestamp. Boreas37's PoC sweeps the predictable namespace with configurable --probe-seconds and --step-us parameters. In testing, filename recovery succeeds reliably within seconds. Exit code 0 confirms recovery; exit code 2 means file was written but filename not yet found.
Conditions required:
  • Attacker can make HTTP GET requests to the uploads directory
  • Directory listing is not required — direct filename probing suffices
Where this breaks in practice:
  • Rate limiting on the target may slow the brute-force sweep
  • CDN caching layers may obscure direct file access
Detection/coverage: Anomalous burst of 404s against /wp-content/uploads/elementor/forms/ in access logs
STEP 05

Execute web shell for full server compromise

Once the filename is recovered, the attacker sends a GET request to the dropped PHP file with commands in a header (e.g., X-CMD). The web shell executes as the web server user (www-data, apache, nginx), giving the attacker command execution on the underlying server. From here, standard post-exploitation follows: reading wp-config.php for database credentials, dumping the database, pivoting to other services on the host or network, installing persistent backdoors, or injecting malicious JavaScript into served pages for supply-chain attacks against site visitors.
Conditions required:
  • PHP execution is enabled in the uploads directory
  • Web shell file has not been quarantined by a security plugin
Where this breaks in practice:
  • Hardened hosts with php_flag engine off in uploads .htaccess block execution entirely
  • Container-based WordPress deployments may limit lateral movement
Detection/coverage: EDR/HIDS detecting process spawning from PHP, web server access logs showing GET to .php in uploads path, Wordfence real-time firewall
03 · Compensating Control

1
CRITICAL 9.2→IGNORE 0.0
SEVERITY REDUCED
Upgrade Elementor Pro to 4.2.2 immediately — The definitive fix. Version 4.2.2 corrects the return/continue desynchronization in validation() and process_field(). Per the noisgate mitigation SLA for CRITICAL, deploy within 3 days. Test in staging first if you have a change-management process, but do not let process delay this beyond the 3-day window given active exploitation.
2
CRITICAL 9.2→MEDIUM 5.3
SEVERITY REDUCED
Disable PHP execution in the Elementor uploads directory — Add php_flag engine off to /wp-content/uploads/elementor/forms/.htaccess (Apache) or equivalent location block denying .php execution (Nginx). This breaks step 5 of the attack path — even if the PHP file lands on disk, it cannot execute. Deploy within hours as an interim control while patching is staged. This does NOT prevent the file write, so you still have an arbitrary file upload — but it eliminates the RCE impact.
3
CRITICAL 9.2→IGNORE 0.0
SEVERITY REDUCED
Remove or disable File Upload fields from all published Elementor forms — If no form on the site includes a File Upload field, the attack path is broken at step 1 — there is no entry point. Edit each Elementor form and either remove the Upload widget or set it to Required (which changes the validation behavior). This is a zero-cost change if file uploads are not business-critical.
4
CRITICAL 9.2→HIGH 7.5
SEVERITY REDUCED
Deploy WAF rules blocking PHP uploads to admin-ajax.php — Wordfence, Cloudflare, Sucuri, and ModSecurity CRS all have rules targeting this specific attack pattern (multipart POST to admin-ajax.php with .php filenames). Enable managed WordPress WAF rulesets. This blocks step 2 at the network layer. Not a substitute for patching — determined attackers may find bypasses — but effective against automated scanning.
5
CRITICAL 9.2→CRITICAL 9.2
Scan uploads directory for existing webshells — Search /wp-content/uploads/elementor/forms/ for any .php files — there should be none in normal operation. Run find /path/to/wp-content/uploads/elementor/forms/ -name '*.php' and investigate any results. Given exploitation began August 19, any unpatched site may already be compromised.
What doesn't work
  • WordPress user role restrictions / capability checks — the vulnerability is unauthenticated, so WordPress's permission model is never consulted. Restricting user roles does nothing.
  • Limiting 'Allowed File Types' in the Elementor form settings — the validation bypass skips the extension check entirely, so this setting is never evaluated during the attack.
  • Setting the File Upload field max file size to a small value — the validation function exits before reaching the size check, so this control is bypassed along with the extension check.
  • Disabling XML-RPC or REST API — the attack goes through admin-ajax.php, not XML-RPC or the REST API. Disabling those endpoints does not affect this attack vector.
  • CAPTCHA on the form — Elementor's CAPTCHA validation runs in a separate handler; the file upload validation bypass occurs regardless of CAPTCHA status.
04 · Intelligence Metadata

The supporting signals.

In-the-Wild ExploitationConfirmed active. Wordfence blocked 190,000+ exploitation attempts between August 19–23, 2026. BleepingComputer, The Hacker News, and SCWorld independently confirmed campaigns deploying PHP web shells. Attackers are targeting sites opportunistically at scale.
Proof-of-Concept AvailabilityMultiple public PoCs. GitHub repos: Boreas37/CVE-2026-32475-PoC (stdlib Python, concurrent uniqid sweep), 4minx/CVE-2026-32475, absholi7ly/Elementor-Pro-Unauthenticated-Arbitrary-File-Upload-to-RCE, 0xBlackash/CVE-2026-32475. Exploit is fully weaponized with automated form recon, upload, filename recovery, and shell execution.
EPSS Score0.01995 (top ~2% probability of exploitation in 30 days). Given confirmed active exploitation, EPSS is lagging reality — treat this as actively exploited regardless of the percentile.
KEV StatusNot listed as of 2026-10-08. Expect CISA addition given confirmed exploitation — KEV listing often lags active campaigns by weeks for non-federal-agency software.
CVSS VectorCVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:C/C:H/I:H/A:H = 9.0. AV:N (network-reachable), PR:N (no auth), UI:N (no user interaction), S:C (scope change — web shell escapes the WordPress application boundary to the OS). AC:H reflects the uniqid() race, but automated tooling makes this effectively AC:L in practice.
Affected VersionsElementor Pro ≤ 4.2.1 — all prior versions of the Pro plugin with the Forms module are affected. The free Elementor plugin is not affected (no Forms module).
Fixed VersionElementor Pro 4.2.2 (released August 19, 2026). No distro backports apply — this is a commercial WordPress plugin updated via its own license-based updater or WordPress dashboard.
Installed Base / ExposureElementor Pro has 10 million+ active installations powering 22 million+ sites. Elementor (free+Pro combined) runs on ~32.67% of WordPress sites (HTTP Archive, April 2026). WordPress itself powers ~43% of all websites globally. The intersection — Elementor Pro sites with vulnerable forms — is a subset, but the absolute numbers are massive.
Disclosure & ResearcherDiscovered by Tin Pham (TF1T) via Patchstack. Reported July 16, 2026; vendor patched July 17; patch validated August 3; public disclosure August 19, 2026.
Scanning / DetectionWordfence released a firewall rule on August 19. Patchstack virtual patch available. Nuclei templates exist for version detection. No specific GreyNoise or Shodan tag identified, but mass scanning is confirmed by the 190K+ blocked attempts.

Sources.

  1. Patchstack Advisory — Critical Unauthenticated File Upload to RCE in Elementor Pro
  2. The Hacker News — Elementor Pro Flaw Could Let Unauthenticated Attackers Upload PHP
  3. BleepingComputer — Critical Elementor Pro Flaw Exploited to Take Over WordPress Sites
  4. Boreas37 PoC — CVE-2026-32475 Stdlib Python Exploit
  5. SecurityOnline — CVE-2026-32475: Elementor Pro RCE Exploited in the Wild
  6. Wordfence / Really Simple Security — Elementor Pro ≤ 4.2.1 Upload Field Array Validation Bypass
  7. DEV Community — Active Exploitation Analysis of PHP Web Shell via Array Validation Bypass
  8. Colorlib — Elementor Statistics 2026: Market Share, Usage & Trends
05 · The Call

Final Verdict
= UNCHANGED to CRITICAL (9.2/10)

Why this verdict

  • Active exploitation confirmed: 190,000+ attack attempts blocked by Wordfence in the first 5 days post-disclosure. This is not theoretical — attackers are scanning and exploiting at scale right now.
  • Weaponized PoCs eliminate AC:H friction: The CVSS vector encodes AC:H for the uniqid() filename race, but at least four public GitHub repos provide fully automated exploits with concurrent thread pools that reliably recover filenames in seconds. In practice, attack complexity is Low.
  • Unauthenticated, zero-interaction, network-reachable: The full chain — form discovery through web shell execution — requires no credentials, no CSRF tokens, no user interaction. Any internet-facing WordPress site with a vulnerable Elementor Pro form is a target.
  • Massive installed base: 10M+ active Elementor Pro installations. Even if only 10–20% have forms with file upload fields, that's 1–2 million directly vulnerable targets. The absolute exposure surface is enormous.
  • Role multiplier: WordPress with Elementor Pro is canonically an internet-facing web application tier. In the typical role, compromise yields: (1) full server-level RCE as the web server user, (2) database credential theft via wp-config.php, (3) customer PII / payment data exfiltration, (4) supply-chain risk via JavaScript injection into pages served to visitors. In the high-value role — e-commerce sites, customer portals with PII, corporate sites serving software downloads — the blast radius extends to mass data egress and supply-chain compromise affecting downstream visitors. Given that Elementor Pro's core use case is building production customer-facing sites, a significant fraction (well above 1%) of the installed base occupies this high-value web-application role. The chain succeeds fully in these roles. Verdict floor: HIGH, and the active exploitation + unauthenticated RCE + massive exposure pushes above the floor to CRITICAL.
  • Scope change (S:C) is real: The web shell escapes the WordPress application sandbox to the underlying OS, enabling lateral movement to co-hosted sites, databases, and internal network segments depending on hosting architecture.

Why not higher?

The score is already near the ceiling at 9.2. A 10.0 would require AC:L in the formal vector and trivial, reliable exploitation with no prerequisites. The uniqid() race and the requirement for a specific form configuration (file upload field present and non-required) prevent a perfect 10, even though automated tooling largely negates the race condition.

Why not lower?

Downgrading below CRITICAL would require evidence that the prerequisite form configuration is rare or that PHP execution in uploads is commonly disabled. Neither holds: file upload fields are a standard Elementor Pro Forms feature, the 'Required' toggle defaults to off, and most WordPress hosting environments allow PHP execution in uploads by default. The confirmed active exploitation at scale (190K+ attempts) eliminates any theoretical doubt about exploitability. Managed hosts that disable PHP in uploads are a minority of the installed base.

06 · Verification

Crowdsourced verification payload.

Run this script on each WordPress host as a user with read access to the WordPress installation directory (typically www-data or root). Invoke with: sudo bash check_cve_2026_32475.sh /var/www/html where the argument is the WordPress root directory. No network access or external dependencies required.

noisgate-verify.sh
BASHREAD-ONLYSAFE
#!/usr/bin/env bash
# CVE-2026-32475 Checker — Elementor Pro Unauthenticated File Upload to RCE
# Usage: bash check_cve_2026_32475.sh /path/to/wordpress
# Exit codes: 0=VULNERABLE, 1=PATCHED, 2=UNKNOWN

set -euo pipefail

WP_ROOT="${1:-}"
if [ -z "$WP_ROOT" ] || [ ! -d "$WP_ROOT" ]; then
  echo "UNKNOWN — Usage: $0 /path/to/wordpress-root"
  exit 2
fi

PLUGIN_DIR="$WP_ROOT/wp-content/plugins/elementor-pro"

# Check if Elementor Pro is installed
if [ ! -d "$PLUGIN_DIR" ]; then
  echo "UNKNOWN — Elementor Pro plugin not found at $PLUGIN_DIR"
  exit 2
fi

# Extract version from elementor-pro.php header
MAIN_FILE="$PLUGIN_DIR/elementor-pro.php"
if [ ! -f "$MAIN_FILE" ]; then
  echo "UNKNOWN — Main plugin file not found: $MAIN_FILE"
  exit 2
fi

VERSION=$(grep -i 'Version:' "$MAIN_FILE" | head -1 | sed 's/.*Version:[[:space:]]*//' | tr -d '[:space:]')
if [ -z "$VERSION" ]; then
  echo "UNKNOWN — Could not parse version from $MAIN_FILE"
  exit 2
fi

echo "Elementor Pro version detected: $VERSION"

# Compare versions — 4.2.2 is the fix
# Using sort -V for version comparison
FIXED_VERSION="4.2.2"
LOWER=$(printf '%s\n%s' "$VERSION" "$FIXED_VERSION" | sort -V | head -1)

if [ "$VERSION" = "$FIXED_VERSION" ] || [ "$LOWER" = "$FIXED_VERSION" ]; then
  echo "PATCHED — Elementor Pro $VERSION >= $FIXED_VERSION (CVE-2026-32475 fix)"
  # Also check for existing webshells
  UPLOAD_DIR="$WP_ROOT/wp-content/uploads/elementor/forms"
  if [ -d "$UPLOAD_DIR" ]; then
    PHP_FILES=$(find "$UPLOAD_DIR" -name '*.php' -o -name '*.phtml' -o -name '*.pht' 2>/dev/null | head -20)
    if [ -n "$PHP_FILES" ]; then
      echo "WARNING — Suspicious PHP files found in uploads (possible prior compromise):"
      echo "$PHP_FILES"
    fi
  fi
  exit 1
else
  echo "VULNERABLE — Elementor Pro $VERSION < $FIXED_VERSION"
  echo "CVE-2026-32475: Unauthenticated arbitrary file upload to RCE"
  echo "Action: Upgrade to Elementor Pro >= $FIXED_VERSION immediately"
  # Check for existing webshells
  UPLOAD_DIR="$WP_ROOT/wp-content/uploads/elementor/forms"
  if [ -d "$UPLOAD_DIR" ]; then
    PHP_FILES=$(find "$UPLOAD_DIR" -name '*.php' -o -name '*.phtml' -o -name '*.pht' 2>/dev/null | head -20)
    if [ -n "$PHP_FILES" ]; then
      echo "CRITICAL — Suspicious PHP files found in uploads directory (POSSIBLE ACTIVE COMPROMISE):"
      echo "$PHP_FILES"
      echo "Investigate immediately for webshells."
    fi
  fi
  # Check if PHP execution is disabled in uploads
  HTACCESS="$WP_ROOT/wp-content/uploads/elementor/forms/.htaccess"
  if [ -f "$HTACCESS" ] && grep -qi 'engine off\|deny from all\|RemoveHandler' "$HTACCESS"; then
    echo "NOTE — .htaccess in uploads may disable PHP execution (partial mitigation)"
  else
    echo "NOTE — No PHP execution restriction detected in uploads directory"
  fi
  exit 0
fi