Automated Threat Modeling

MW WP Form CVE-2026-5436: Brief Summary of an Unauthenticated Arbitrary File Move Vulnerability Affecting 200,000 WordPress Sites

A brief summary of CVE-2026-5436, a high-severity arbitrary file move vulnerability in the MW WP Form WordPress plugin (versions 5.1.1 and earlier) that lets unauthenticated attackers relocate critical files like wp-config.php. Covers patch details, detection strategies, and vendor security history.

CVE Analysis

10 min read

ZeroPath CVE Analysis
ZeroPath CVE Analysis

2026-04-08

MW WP Form CVE-2026-5436: Brief Summary of an Unauthenticated Arbitrary File Move Vulnerability Affecting 200,000 WordPress Sites
Experimental AI-Generated Content

This CVE analysis is an experimental publication that is completely AI-generated. The content may contain errors or inaccuracies and is subject to change as more information becomes available. We are continuously refining our process.

If you have feedback, questions, or notice any errors, please reach out to us.

[email protected]

Introduction

An unauthenticated path traversal flaw in the MW WP Form WordPress plugin lets attackers move arbitrary files on the server into the public uploads directory, including critical configuration files like wp-config.php. With roughly 200,000 active installations exposed and no authentication required, this vulnerability is a significant risk to the WordPress ecosystem.

MW WP Form is a popular contact form builder plugin for WordPress, developed by web soudan and inc2734. It is widely used across Japanese and international WordPress deployments and supports form creation with file uploads and database storage of inquiry data. Its large install base and deep integration with WordPress file handling make vulnerabilities in this plugin especially damaging.

Technical Information

Root Cause: path_join() and Unsanitized Upload Field Keys

The vulnerability (classified as CWE-22, Path Traversal) comes from a misunderstanding of how WordPress's path_join() function behaves. When path_join() receives an absolute path as its second argument, it returns that absolute path unchanged and discards the first argument (the intended base directory) entirely. The MW WP Form plugin relied on path_join() to keep file operations inside a designated upload directory, but never validated that the input to path_join() was a relative path.

The generate_user_file_dirpath() function in classes/models/class.directory.php accepts a $name parameter (the upload field key) and passes it directly to path_join() alongside the intended user directory. If $name is an absolute path like /var/www/html/wordpress/wp-config.php, the function returns that absolute path verbatim.

Attack Flow

The attack moves through the plugin's data model and file handling pipeline in four steps:

  1. Injection via POST parameter. The attacker submits a crafted POST request to a form that uses MW WP Form. The mwf_upload_files[] parameter contains an absolute filesystem path (e.g., /var/www/html/wordpress/wp-config.php) as a key value. No authentication is required.
  2. Data model ingestion. The plugin's Data model loads the submitted parameters via the _set_request_valiables() function. The attacker-controlled key enters the plugin's internal data structures without sanitization.
  3. Key iteration and path resolution. During form processing, regenerate_upload_file_keys() in class.data.php iterates over the upload file keys and calls generate_user_filepath() with the attacker-supplied key as the $name argument. The key survives validation because the targeted file exists at the specified absolute path.
  4. File relocation. The _get_attachments() method re-reads the surviving keys and passes the resolved absolute file path to move_temp_file_to_upload_dir(). This function calls PHP's rename(), which physically moves the targeted file from its original location into the WordPress uploads folder.

Why the Previous Fix (5.1.1) Was Insufficient

This vulnerability bypasses the fix that version 5.1.1 introduced for the related CVE-2026-4347. That earlier patch hardened the generate_user_filepath() function, but the attacker-controlled upload field key still flowed unchecked into generate_user_file_dirpath(). The regenerate_upload_file_keys() function in class.data.php iterated over these keys without proper sanitization, so an attacker could bypass the 5.1.1 path traversal mitigations through this alternative code path.

Exploitation Preconditions

Two conditions must be met for successful exploitation:

  1. A file upload field must be actively present on the targeted form.
  2. The "Saving inquiry data in database" option must be enabled for that form.

If either condition is absent, the vulnerable code path is not reachable.

Patch Information

A public patch is available in MW WP Form version 5.1.2, released on April 8, 2026. The fix was merged via Pull Request #32 from the security/fix-file-upload-path-validation branch, authored by Kazuto Takeshita, in commit f872ab18ca670f5867b2241745daa30cd0fab861. The commit touches seven files with 203 additions and 20 deletions, and the security-critical logic is concentrated in classes/models/class.directory.php.

Defense in Depth: Three New Validation Methods

The 5.1.2 patch introduces three new protected static methods in class.directory.php:

  • _is_valid_path_segment($value) is a strict gatekeeper. It rejects any path component that is empty, contains null bytes (\0), equals . or .., is an absolute path, or does not match its own wp_basename() (meaning it contains directory separators). The patch applies this check to both the $name and $filename parameters before either can influence any file system path.
  • _is_within_expected_dir_candidate($form_id, $path) independently reconstructs what the legitimate user temp directory should be, then verifies that the candidate path either matches it exactly or begins with it (plus a trailing slash). This containment check is what defeats the path_join() absolute path bypass.
  • _get_expected_user_dir($form_id, $base_dir) independently computes the expected user directory from the CSRF token (validated against /^[a-z0-9]+$/) and the form ID (validated against /^\d+$/), and returns false if any component is malformed.

Patched generate_user_file_dirpath()

The patch adds this validation logic to the previously unprotected function:

public static function generate_user_file_dirpath( $form_id, $name ) { if ( ! static::_is_valid_path_segment( $name ) ) { throw new \RuntimeException( '[MW WP Form] Invalid file reference requested.' ); } $user_dir = static::generate_user_dirpath( $form_id ); $user_file_dir = path_join( $user_dir, $name ); if ( ! static::_is_within_expected_dir_candidate( $form_id, $user_file_dir ) ) { throw new \RuntimeException( '[MW WP Form] Invalid file reference requested.' ); } return $user_file_dir; }

Patched generate_user_filepath()

The patch replaced the old inline check (wp_basename($normalized_filename) !== $normalized_filename || strstr($normalized_filename, "\0")) with the segment validator up front and the containment check after the path is assembled:

if ( ! static::_is_valid_path_segment( $filename ) ) { throw new \RuntimeException( '[MW WP Form] Invalid file reference requested.' ); } // ... path assembled ... if ( ! static::_is_within_expected_dir_candidate( $form_id, $filepath ) ) { throw new \RuntimeException( '[MW WP Form] Invalid file reference requested.' ); }

generate_user_dirpath() also gained a numeric-only form ID check:

if ( ! preg_match( '/^\d+$/', (string) $form_id ) ) { throw new \RuntimeException( '[MW WP Form] Invalid form ID.' ); }

Caller-Side Error Handling

Both regenerate_upload_file_keys() in class.data.php and _get_attachments() in class.main.php were updated to wrap calls to generate_user_filepath() in try/catch blocks. When the code catches a RuntimeException (a sign of a path traversal attempt), it logs the error, removes the offending upload key from the list, clears its value, and continues processing the remaining legitimate keys. A single malicious entry therefore does not crash the entire form submission.

The commit also includes unit tests in test-directory.php and test-data.php covering absolute paths, nested paths, directory traversal sequences like ../../../wordpress, and Windows-style absolute paths.

Detection Methods

Web Server Access Log Analysis

The most direct detection method targets the attack's entry point, the mwf_upload_files[] POST parameter. Defenders should review web server access logs (Apache, Nginx, or a reverse proxy) for POST requests to any MW WP Form endpoint where the request body includes mwf_upload_files keys containing absolute filesystem paths or path traversal sequences (e.g., ../). Because the vulnerability requires no authentication, any external IP making such requests is suspect. Web Application Firewalls (WAFs) can be configured to inspect POST body parameters for the mwf_upload_files key combined with values that begin with / or contain traversal patterns like ...

PHP Error Log Monitoring (Post-Patch)

If you have already applied the patch (version 5.1.2), the fix itself gives you a built-in detection mechanism. Whenever it detects an invalid path segment, the patched code calls error_log() with the message from a RuntimeException. Exploitation attempts against a patched instance will produce entries in the PHP error log containing the string [MW WP Form] Invalid file reference requested. Multiple occurrences from the same source IP should be treated as high-confidence indicators of targeted attack activity.

File System Integrity Monitoring

The exploit uses PHP's rename(), so the targeted file is moved into the WordPress uploads directory rather than copied. A successful exploitation therefore produces two simultaneous filesystem anomalies: (1) a critical file such as wp-config.php disappears from its expected location, and (2) that same file appears unexpectedly inside the wp-content/uploads/ directory tree. File Integrity Monitoring (FIM) tools such as OSSEC, Wazuh, or Tripwire should be configured to alert on any deletion or modification of wp-config.php and other sensitive WordPress core files. Monitoring the uploads directory for non-media files (e.g., .php, .conf, .ini files) can also catch post-exploitation artifacts.

Behavioral and Host-Based Indicators

A successful exploitation will almost certainly cause an immediate, observable side effect. If wp-config.php is moved, the WordPress site will display Error establishing a database connection because the application can no longer locate its configuration. If this error suddenly appears on a previously working site running MW WP Form, investigate it for this CVE. Uptime monitoring and synthetic health checks on WordPress instances running MW WP Form can act as a fast-response detection layer.

Vulnerability Scanning and Version Detection

Standard vulnerability scanners (Nessus, Qualys, OpenVAS) and WordPress-specific tools like WPScan or Wordfence can identify vulnerable installations by checking the MW WP Form plugin version. Any installation running version 5.1.1 or earlier is affected.

Note on Public Signatures

As of publication, no vendor-agnostic IDS/IPS rules (Snort, Suricata), Sigma rules, or YARA rules explicitly targeting CVE-2026-5436 have been identified in public repositories. For now, the most actionable approaches are the detection strategies above, particularly log monitoring for the mwf_upload_files[] parameter with path-like values, PHP error log alerting, and FIM on critical WordPress files.

Affected Systems and Versions

All versions of the MW WP Form plugin for WordPress up to and including version 5.1.1 are affected. The vulnerability is only exploitable on installations where both of the following conditions are true:

  1. A file upload field is present on at least one active form.
  2. The "Saving inquiry data in database" option is enabled for that form.

The fix is available in version 5.1.2 and later.

Vendor Security History

The MW WP Form plugin has a documented pattern of severe file handling vulnerabilities across consecutive releases, all exploitable without authentication:

Plugin Version RangeVulnerability TypeCVE
Versions 5.0.1 and earlierUnauthenticated Arbitrary File UploadRelated prior CVE
Versions 5.1.0 and earlierUnauthenticated Arbitrary File Move via move_temp_file_to_upload_dirRelated prior CVE
Versions 5.1.1 and earlierUnauthenticated Arbitrary File Move and Read via regenerate_upload_file_keysCVE-2026-5436

These file manipulation flaws keep recurring, and all of them center on insufficient input validation in file system operations. That pattern suggests systemic architectural weaknesses in the plugin's file handling code. Organizations using this plugin should scrutinize future updates closely and consider strict WAF rules for all form submissions as an additional layer of defense.

References

Detect & fix
what others miss

Works with
  • GitHub
  • GitLab
  • Bitbucket
  • Azure DevOps Services
  • Gerrit
  • CVS
  • Jira
  • Linear
  • Slack
  • Security Compass
Explore integrations
Security magnifying glass visualization