
CVE-2026-2766, ma con wasm
Stato: PoC di crash validato con dirottamento del flusso di controllo dimostrato
(crash pc = poison della cella liberata 0xcdcdcdcdcdcdcdcd sotto la debug
shell — il motore salta a un puntatore letto dall'ICScript liberato).
Lavoro rimanente: controllare i byte reclamati. Vedi
research/README.md.
Una catena della famiglia WasmBlazeFox su un bug del 2026: CVE-2026-2766, "JIT miscompilation / use-after-free nel JavaScript Engine: componente JIT", corretto in Firefox 148 (MFSA 2026-13). L'endgame è lo stesso di CVE-2024-29943-but-with-wasm: trasformare la primitiva in controllo di un code pointer, e puntarlo verso una pagina JIT WASM piena di costanti shellcode.
Dai commenti del regression test di Mozilla stesso (bug 2013583, test atterrato in
hg 457b68097f81) e dall'SMDOC ICScript Lifetimes in js/src/jit/JitScript.h:
removeInlinedChild → l'ICScript del figlio viene rimosso da
inlinedChildren_ ma è ancora referenziato dal vettore inlinedScripts_
dell'InliningRoot — e, fatalmente, dallo stub obsoleto
CallInlinedFunction ancora presente nella catena IC del chiamante.gczeal(14, 1), cioè ZealCompactValue ad ogni
allocazione) sposta/evacua l'ICScript orfano mentre la catena di stub obsoleta
mantiene il vecchio indirizzo.0xe5, dando un crash molto leggibile.Build vulnerabile: mozilla-central rev b3663be61a1a (nightly del 2026-01-15;
la correzione è atterrata tra il 2026-01-15 e il 2026-02-09 — la nightly del 09-Feb
sopravvive). Shell: jsshell Taskcluster linux64-fuzzing-asan-opt per quella
rev (necessaria per gczeal; le shell release-opt ne sono prive).
./js --ion-warmup-threshold=100000 poc.js
== ERROR: AddressSanitizer: SEGV on unknown address 0xe5e5e5e5e5e5e5e5
The signal is caused by a READ memory access.
#0-#3 <unknown module> <- baseline JIT code
#4 EnterJit / MaybeEnterJit <- js/src/jit/Jit.cpp
#10 js::jit::DoCallFallback <- BaselineIC.cpp (the stale IC chain)
rdi = 0xe5e5e5e5e5e5e5e5 <- the freed ICScript
La dereferenziazione avviene nel codice JIT baseline che percorre la catena di stub obsoleta: il controllo della cella reclamata = controllo dei campi ICEntry/stub di cui il baseline si fida, incluso il puntatore al codice dello stub verso cui salta.
orphaned ICScript (this PoC)
-> compacting GC moves it; stale chain keeps old address
-> reclaim the old cell with controlled bytes (size-class spray)
-> baseline reads fake ICEntry -> fake ICStub -> fake code_ pointer
-> jump into the WASM JIT page shellcode (f64.const immediates,
FuncExport entry-offset overwrite — see the 2024-29943 repo)
Vedi research/README.md per il log completo di
weaponization. Riepilogo dello stato attuale:
TrailingArray) —
reclamabile tramite spray in linea di principio con buffer di classi di dimensione.new Ctor(flag), senza alcun punto di callback JS tra di esse; gli spray
ingenui o mancano la finestra (reclaim1/2) o sconvolgono lo stato IC
con una tempesta di GC zeal (reclaim3). La catena obsoleta sopravvive a un singolo
gc() semplice (purge_check).Lo stadio WASM in sé è già costruito e dimostrato in CVE-2024-29943-but-with-wasm; solo gli offset dell'object-model devono essere ri-derivati per questa build dell'era FF149.
poc.js — il regression test di Mozilla (bug 2013583), verificato per mandare in crash la
jsshell ASAN del 2026-01-15 come mostrato sopra.457b68097f81