[JSC] Add global priority queue inliner
Component: JSC DFG JIT | bdb7246
Source/JavaScriptCore/dfg/DFGByteCodeParser.cpp
Source/JavaScriptCore/runtime/OptionsList.h
DFG is JSC's optimizing JIT tier; during bytecode parsing it decides which function calls to inline directly into the caller's IR rather than emitting a call. Previously that decision was greedy — made as each call site was encountered during a single parse pass, so earlier call sites could exhaust the inlining budget regardless of profitability.
The new InliningPlan performs a pre-pass survey of profiled call sites, prices and ranks them by a computed score, and builds a tree of admitted candidates the parser consults via planPermitsInlining(). It functions purely as a veto: it can decline a call site the survey's admitted list excludes, but the existing cost checks and per-site heuristics in handleCallVariant still run afterward, and InlineAttribute::Always callees bypass the plan entirely. A site the survey never predicted — one that turns out to be an intrinsic, a DOM call, or a varargs frame — falls back to the old heuristics unchanged. Gated behind useGlobalInliningPlanner, defaulting false, with the budget kept high enough that observable behavior is unchanged.
Significance
Once enabled and tuned, this changes which functions get inlined across the codebase — and therefore the shape of the machine code security researchers reason about when studying JIT behavior. For now it is opt-in infrastructure: roughly 260 lines of new subsystem sitting directly in the DFG bytecode-parsing path, historically one of JSC's bug-rich areas.
Audit directions
The forward-facing pattern is an in-code comment asserting that a divergence "costs decision quality and never correctness" — a claim that holds only while the veto-only property is preserved. Narrow: check whether that invariant survives once the option is enabled, i.e. whether any path lets the plan admit a site the per-site heuristics would have declined rather than only declining one they would have admitted; the match tell is any consumer of site->admitted that skips a subsequent cost check rather than adding to it. Wider: the new data structures carry their own memory-safety questions — Site* parent/child pointers into a SegmentedVector<Site, 16> (does reallocation invalidate them?) and a calleeIdentity pointer compared for identity but never dereferenced (what guarantees the address is not reused by a freed-and-reallocated object?). The same interior-pointer-into-growable-container shape is worth grepping for across the DFG's other side tables. Widest: a survey pass and a parse pass computing the same predicate through different code is the divergence class from the PNG decoder fix above, transplanted into a JIT — any two implementations of "should this be inlined" will drift, and the survey's model of a call site is necessarily coarser than the parser's.