Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions changelog.d/7977-lint-red-gcheader-cast.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
### Fixed

- **`lint` was red on `main`**, so every merge was bypassing a required context. `scripts/addr_class_inventory.py` flagged one violation — `crates/perry-runtime/src/object/tests.rs:646` `[gcheader-cast]`, a bare `(obj as *const u8).sub(GC_HEADER_SIZE) as *const GcHeader` added by #7928's inline-slot-floor probe.

Replaced with the approved accessor `addr_class::try_read_gc_header`, which takes the object address and performs the header arithmetic behind its plausibility and slab checks. The audit passes again (1056 files, 546 ratcheted sites), with no new allowlist entry — the ratchet's whole point is that a fix deletes the violation rather than exempting it.

Worth stating plainly because it is the shape CLAUDE.md warns about: a **required** context that is red trains everyone to bypass it, and a genuinely new violation would then land invisibly behind the old one.
10 changes: 8 additions & 2 deletions crates/perry-runtime/src/object/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -643,8 +643,14 @@ fn two_field_literal_footprint_is_exactly_accounted() {
let obj = js_object_alloc_with_shape(0x7916_0001, 2, keys.as_ptr(), keys.len() as u32);
assert!(!obj.is_null());
let recorded = unsafe {
let gc = (obj as *const u8).sub(crate::gc::GC_HEADER_SIZE) as *const crate::gc::GcHeader;
(*gc).size as usize
// #7928 added this probe with a bare `as *const GcHeader`, which the
// addr-class ratchet rejects (and which turned required `lint` red on
// `main`). `try_read_gc_header` is the approved accessor: it takes the
// OBJECT address and does the header arithmetic itself, behind the
// plausibility and slab checks.
crate::value::addr_class::try_read_gc_header(obj as usize)
.expect("a freshly allocated object must carry a readable GcHeader")
.size as usize
};
let expected = crate::gc::GC_HEADER_SIZE
+ std::mem::size_of::<ObjectHeader>()
Expand Down
Loading