pub struct RuntimeRoots<'a> { /* private fields */ }Expand description
Everything the runtime owns that names a GcRef — five arms that keep one
alive, and one that only has to keep one valid.
Sealed: the only constructor is RuntimeRoots::from_context, so a
collection cannot be run against a hand-picked subset. The six arms are
every documented owner of a reference:
| arm | strength | owner |
|---|---|---|
shadow | strong | ctx.shadow — the generated shadow stack, scanned [base, top) (ADR-019, ADR-101) |
input | strong | ctx.input_source — the read-in buffer |
parse_partial | strong | ParseDetail.fail.partial — the best partial parse |
snapshot | strong | the runtime-owned CrashSnapshot’s copied locals |
native | strong | NativeRootStore — what Rust helpers hold, scanned [0, len) (ADR-114) |
debug | weak | ctx.debug_frames + ctx.debug_values — the crash debugger’s live frames and the value slots they name (ADR-104, ADR-106) |
abi::maybe_collect builds one of these and passes it whole, so a
host-driven allocation and one taken inside the parser interpreter collect
against the same arms generated code does.
§Why the sixth arm is weak
The debug slots are the over-approximate set: ADR-044 split them from the
root set precisely so that making the root set exact would not make the
debugger render <uninit> for a local the user can still see in their
source. RootSlots::dead nulls a shadow slot at its local’s last use; the
debug slot keeps the value, because a value that has been produced stays
renderable.
Pushing debug in RootSet::push_roots would undo exactly that split. It
is one line, it makes every dead local reachable again, and
a_dead_local_stops_being_reachable_from_its_frame is the end-to-end gate
that fails when someone writes it — deliberately, and it must keep failing.
The arm’s whole content is therefore in WeakSet::clear_reclaimed: the
collector decides what dies without consulting the debugger, and then tells
the debugger what died.
Implementations§
Source§impl<'a> RuntimeRoots<'a>
impl<'a> RuntimeRoots<'a>
Sourcepub unsafe fn from_context(ctx: *mut RuntimeContext) -> RuntimeRoots<'a>
pub unsafe fn from_context(ctx: *mut RuntimeContext) -> RuntimeRoots<'a>
Read every root arm out of ctx.
§Safety
ctx must be null, or point at a live RuntimeContext whose non-null
shadow / parse_detail / crash_snapshot / native_roots /
debug_frames / debug_values pointers reference live values for 'a.
A non-null context’s input_source must be a valid GcRef
(RuntimeContext::placeholder documents the same requirement).
Trait Implementations§
Source§impl RootSet for RuntimeRoots<'_>
impl RootSet for RuntimeRoots<'_>
Source§fn push_roots(&self, out: &mut Vec<GcRef>)
fn push_roots(&self, out: &mut Vec<GcRef>)
out, in any order.Source§impl WeakSet for RuntimeRoots<'_>
impl WeakSet for RuntimeRoots<'_>
Source§fn clear_reclaimed(&self) -> usize
fn clear_reclaimed(&self) -> usize
Null every debug value slot whose object the sweep just reclaimed.
The whole of the weak arm. Called by Heap::collect_inner between the
sweep and the return to the allocator — see
WeakSet for why nowhere else will do.