VMware Workstation PVSCSI LFH Escape (VMware-vmx on Windows 11)
Tip
Učite i vežbajte AWS Hacking:
HackTricks Training AWS Red Team Expert (ARTE)
Učite i vežbajte GCP Hacking:HackTricks Training GCP Red Team Expert (GRTE)
Učite i vežbajte Azure Hacking:
HackTricks Training Azure Red Team Expert (AzRTE)
Podržite HackTricks
- Proverite planove pretplate!
- Pridružite se 💬 Discord grupi ili telegram grupi ili pratite nas na Twitteru 🐦 @hacktricks_live.
- Podelite hakerske trikove slanjem PR-ova na HackTricks i HackTricks Cloud github repozitorijume.
Anatomija buga: fixed-size realloc + rasuta OOB pisanja
PVSCSI_FillSGIkopira guest scatter/gather unose u internu strukturu. Počinje sa statičkim baferom od 512 unosa (0x2000). Iznad 512 unosa vrši realloc na 0x4000 bajtova i, zbog funkcionalnog buga, reallocira pri svakoj iteraciji.- Veličina realokacije se nikad ne povećava: 0x4000 / 0x10-bajtni unosi = 1024 korisna unosa. Kada guest dostavi >1024 unosa, svaki novi unos se upisuje 16 bajtova posle tek alociranog 0x4000 chunk-a, korumpirajući susedni chunk header ili objekat.
- Sadržaj overflow-a: VMware čuva
{u64 addr; u64 len}; guest daje{u64 addr; u32 len; u32 flags}. 32-bitlense zero-extenduje, tako da je poslednji dword svakog 16-bajtnog OOB elementa uvek 0x00000000.
LFH ograničenja i determinističko “Ping-Pong” raspoređivanje
- 0x4000 alokacije završavaju u Windows 11 LFH (16 chunks/bucket, 0x10-bajtna metadata sa keyed checksum-om). Bilo koji chunk čiji header checksum bude pogođen kasnije će prekinuti proces, zato korumpirani header-i ne smeju biti ponovo korišćeni.
- LFH vraća nasumični slobodan chunk, ali preferira bucket koji sadrži najnovije oslobođeni chunk. Ograničite slobodna mesta na samo dva:
- Alocirajte sve slobodne 0x4000 chunke da poravnate allocator; naprskajte (spray) 32 SVGA shaders da popunite B1 i B2 buckets.
- Oslobodite B1 osim jednog fiksiranog shader-a (Hole0) tako da B1 ostane aktivan; alocirajte 15 URBs u B1.
- Oslobodite jedan shader u B2 (PONG), zatim odmah oslobodite Hole0. LFH će naizmenično dodeljivati alokacije između dva dostupna slota PING (B1) i PONG (B2).
- Iteracija 1025 korumpira header posle PONG (nikad više nije diran); iteracija 1026 pogađa prvih 16 bajtova URB-a posle PING (sigurni bypass metapodataka). Povratite PING/PONG sa placeholder shader-ima da zadržite stabilan i ponovljiv raspored.
Reap Oracle: označavanje kontinualnih rupa
- UHCI URB-ovi žive u FIFO redu i oslobađaju se kad su potpuno reaped. Ograničeno 16-bajtno prepisivanje uvek postavlja
actual_lenna nulu, dajući marker. - Reap-ujte URB-ove redom; kad se vidi
actual_lenpostavljen na nulu, odmah popunite oslobođeni slot prepoznatljivim shader-om. Iteriranjem mapirate Hole0–Hole3 kao četiri susedna chunka u poznatom redu za kasnije primitive zavisne od susedstva.
Pretvaranje ograničenih upisa u arbitrarni overwrite (zloupotreba coalescing-a)
PVSCSI koalescira susedne unose koristeći AddrA + LenA == AddrB i kompaktira kasnije unose prema gore.
- Two-pass overflow: Pokrenite od PING (neparni indeksi) i izađite ranije da preskočite coalescing; pokrenite ponovo od PONG (parni indeksi) da popunite praznine i nastavite upis u sprayan shader koji sadrži lažne S/G unose.
- Vacuum + payload: Postavite unose
[1023..2047]na{addr=0,len=0}tako da ih coalescing svede u jedan, kreirajući logičku rupu. Payload unosi postavljeni kasnije (u shader-u) se pomere gore u raniju memoriju, završavajući unutar victim URB-a. - Adjacency-check bypass: Postavljanjem
LenA=0uslov postajeAddrA==AddrB. Sastavite parove
{addr = X, len = 0}
{addr = X, len = Y}
tako da ih coalescing spoji u {addr=X,len=Y}. Nula-veličinski elementi na parnim indeksima dolaze iz ograničenog overflow-a; neparni indeksi žive u shader-u. Rezultat: arbitrary 16-byte patterns uprkos prisilnom nul dword-u.
Hybrid URB infoleak via coalescing side-effects
- Rasporedite susedne chunke:
[Hole0 (free/PING), URB1 (target), URB2 (valid, actual_len=0), URB3 (leak target)]. - Popunite URB1 kontinualnim lažnim unosima (veličine
0xFFFFFFFF), dodirujući URB2 minimalno. Coalescing ih spoji u jedan unos; zbir0xFFFFFFFF * 0x401postavlja gornji dword na offset-uactual_lenURB1 na 0x400. - Kompakcija kopira sledeće podatke prema gore, povlačeći URB2’s header u URB1. URB1 sada ima validan header (pipe/list pointers),
actual_len=0x400, i data pointer koji već pokazuje na kraj URB2-ovog bafera. - Reap-ovanje URB1 kopira 0x400 bajtova počevši malo pre URB3, što daje OOB read URB3-ovog header-a/self-referenci, i otkriva apsolutne heap adrese i ruši ASLR za naknadne falsifikovane strukture.
Post-leak primitive (bez ponovnog okidanja buga)
- Forge-ujte URB strukturu unutar shader-a koji zauzima Hole0, zatim iskoristite coalescing “move up” da zamenite URB1 falsifikovanim podacima.
- Učinite URB persistentnim: postavite
URB1.next = Hole0i uvećajterefcount; reaping URB1 stavlja Hole0-backed fake URB na FIFO vrh. Buduće primitive su samo realokacije Hole0 sa novim lažnim URB-ovima. - Arbitrary read: lažni URB sa izabranim
data_ptriactual_len, zatim reap da kopira host memoriju u gena. - Arbitrary write (32-bit): lažni URB čiji
pipepokazuje na kontrolisanu memoriju i zloupotrebite UHCI TDBuffer writeback da sačuvate izabrani dword na arbitrarnoj adresi. - Arbitrary call: prepišite USB pipe callback; host će ga pozvati sa kontrolisanim podacima na
RCX+0x90. RešiteWinExecdinamički (guest-side read of Kernel32) i pivotirajte kroz CFG-valid gadget inside vmware-vmx koji učitava argumente izRCX+0x100pre prosleđivanja kaWinExec("calc.exe").
LFH timing side-channel za određivanje početnog bucket offset-a
- Deterministički Ping-Pong zahteva poznavanje LFH free-chunk offset-a (koji od 16 slotova će biti pogođen prvi). Koristite VMware backdoor instrukciju (
inl %%dx, %%eax) sa sinhronim VMware Tools komandamavmx.capability.unified_loopi 0x4000-byte string, što forsira dve 0x4000 alokacije po pozivu. - Merite vreme 8 poziva (16 alokacija) preko
gettimeofday; jedan poziv pokazuje konzistentan skok kada LFH kreira novi bucket. Ponavljajte sa jednim dodatnim alociranjem: ako skok ostane na istom indeksu offset je neparan, ako se pomeri onda je paran; u suprotnom restartujte zbog buke. - Upozorenje:
unified_loopčuva jedinstvene stringove u nerefearabilnoj listi, što izaziva O(n) lookup overhead i rastuću buku, pa se side-channel mora brzo konvergirati.
References
Tip
Učite i vežbajte AWS Hacking:
HackTricks Training AWS Red Team Expert (ARTE)
Učite i vežbajte GCP Hacking:HackTricks Training GCP Red Team Expert (GRTE)
Učite i vežbajte Azure Hacking:
HackTricks Training Azure Red Team Expert (AzRTE)
Podržite HackTricks
- Proverite planove pretplate!
- Pridružite se 💬 Discord grupi ili telegram grupi ili pratite nas na Twitteru 🐦 @hacktricks_live.
- Podelite hakerske trikove slanjem PR-ova na HackTricks i HackTricks Cloud github repozitorijume.


