This Week in WebKit — February 28 – March 06, 2026
Featured
drawIndexed validates that vertex indices stay inside the bound vertex buffer, and Buffer::needsIndexValidation caches the largest index seen so far to amortize the check. The uint32 branch was correct. The uint16 branch had its operands reversed — m_maxUshortIndex > maxUshortIndex — so the cache only updated and reported 'needs validation' when the new max was smaller; in the dangerous direction it silently said 'already covered.' Issue a small drawIndexed first, then one whose uint16 indices land outside the vertex buffer; the GPU reads past the bound region.
Highlight::clearFromSetLike walked m_highlightRanges and called repaintRange on each entry, but under WebKit's synchronous layout model repaintRange can re-enter through style and layout into code that adds or removes ranges. The iterator over a vector being mutated mid-loop is a familiar shape — UAF on the backing store, with an ASAN signature reaching all the way back to Document::commonTeardown. The fix drains the vector into a stack-local via std::exchange before iteration starts, so any re-entrant mutation lands on the now-empty member.
WebKit's .serialization.in DSL exposes [Validator='...'] expressions that read like comparisons but compile to native C++ arithmetic, with all the wrap-around hazards. ShareableBitmap's bytesPerRow validator computed m_size->width() * *bytesPerPixel and asserted bytesPerRow >= product — but a sufficiently large width wraps the product to a value any normal-looking bytesPerRow satisfies. A compromised WebContent process can then ship a deliberately inconsistent bitmap across IPC, and a privileged receiver uses the attacker-supplied bytesPerRow to compute offsets into shared memory.
When a JavaScript function declares more parameters than the caller supplied, JSC pads the call frame with undefined slots — arity fixup — and the overflow guard is supposed to refuse fixups that push past the soft stack limit. The LLInt computed the projected new stack pointer from cfr (the frame top) instead of sp (already below all callee locals and slow-path scratch space), overestimating remaining capacity by exactly numCalleeLocals + maxFrameExtentForSlowPathCallInRegisters. Construct a function with both many declared parameters and many locals via new Function(...); the JIT correctly throws RangeError, the LLInt writes past the limit.
ValueRepReductionPhase rewrites DFG/FTL nodes whose JSValue results are only ever consumed as doubles, narrowing the node's result type to NodeResultDouble. For MultiGetByOffset, that narrowing has to walk the case vector and convert any embedded Constant cases — including the absent-property case where the constant is undefined. The phase forgot. The raw JSValue bit pattern of undefined is then materialized as a 'double,' a deterministic non-Number value the rest of the FTL pipeline trusts as IEEE 754 — exactly the primitive that steers downstream bounds and range speculation guards.
Wasm's function-references proposal introduces nonnullable reference types like (ref func) and (ref T), and the Wasm-side compilers (BBQ, OMG) lean on the type system to elide null checks on operations against them. JSC's JS-to-Wasm marshalling never enforced the promise. A JS host function declared to return (ref func) could return null and the value sailed through the boundary across four parallel paths — three C++ slow paths and the JIT-compiled wasmToJS stub. Whatever runs next on the Wasm side does so under an invariant that no longer holds.
Security fixes
-
DFG proto-fold type confusion via TOCTOU race in GetByStatus condition validation
High JSC DFG JIT
-
DFG RegExp constructor miscompilation via missing newTarget propagation
Medium JSC DFG JIT
-
GameControllerGamepad UAF from raw this capture in framework-retained blocks
Medium WebCore Gamepad
-
SubtleCrypto RSA import OOB read from missing ASN.1 bounds check
Medium WebCore SubtleCrypto
Notable development
-
Cloned SymbolTable cache per JSGlobalObject fixes DFG constant-folding of mutable variables
bug
-
CSS revert-rule keyword implementation
feature
-
DFG/FTL PerformPromiseThen node for species-check-free Promise.then()
optimization
-
Site Isolation: UIProcess routing for same-site child frame back/forward navigations
hardening
-
GPU texture atlas pipeline for Skia painting on GTK/WPE
optimization