feat(causal): offcpu column + closed-books eff in the attrib probe

The probe now prints eff+offcpu next to eff — attributed plus the
counted runnable off-CPU gaps over ground-truth in-site time — the
per-window check that the located mechanism accounts for the whole
residual (~1.00 = books closed, no remaining silent loss). Audit line
gains the offcpu column, same delta-terms convention as the lib
renderer. Header doc rewritten from hypothesis to resolution.
This commit is contained in:
Claude (sandbox)
2026-07-13 12:46:58 +00:00
parent 0ee3fe7330
commit 527f045e17
+22 -11
View File
@@ -1,12 +1,15 @@
//! Attribution-efficiency probe (RFC 007 follow-up). //! Attribution-efficiency probe (RFC 007 follow-up).
//! //!
//! Hypothesis: the ~4pt impact shortfall on the 24-core validation //! Original hypothesis: the ~4pt impact shortfall on the 24-core
//! (+29.3/+83.5 vs theoretical +33/+100) is a constant attribution //! validation (+29.3/+83.5 vs theoretical +33/+100) is a constant
//! efficiency eff ≈ 0.91 — only ~91% of true in-target-site time is ever //! attribution efficiency eff ≈ 0.91 from site-exit tail truncation.
//! sampled, because samples are taken only when `maybe_preempt`'s cold //! The guard-drop flush closed that leak, yet eff held at ~0.93 —
//! block fires while in-site: the tail between the last in-site check and //! RESOLVED (2026-07-13 sweep): the residual is runnable off-CPU time
//! `SiteGuard` drop (and any in-site time truncated by a deschedule) is //! inside the site (~4.9 slice-expiry yields/entry x ~5.6µs runqueue
//! discarded. //! wait), wall time the ground truth below counts but on-CPU
//! attribution correctly skips. The offcpu audit bucket now counts it;
//! `eff+offcpu` printed per window should sit at ~1.00 — the
//! closed-books check.
//! //!
//! Measurement: same pipeline as `causal_pipeline`, but the `reserve` //! Measurement: same pipeline as `causal_pipeline`, but the `reserve`
//! actor also measures its raw in-site time directly (rdtsc at guard //! actor also measures its raw in-site time directly (rdtsc at guard
@@ -19,8 +22,9 @@
//! //!
//! tail_us/entry = (Δin_site Δglobal_delay/(pct/100)) / Δentries //! tail_us/entry = (Δin_site Δglobal_delay/(pct/100)) / Δentries
//! //!
//! A constant eff across 25/50% with tail/entry in the tens of µs (about //! A constant eff across 25/50% with tail/entry in the tens of µs
//! half the causal-check cadence) confirms site-exit tail truncation. //! localizes a per-entry mechanism; `eff+offcpu` ≈ 1.00 confirms the
//! runnable-gap account and rules out any remaining silent loss.
//! //!
//! Run: cargo run --release --example causal_attrib_probe --features smarm-causal //! Run: cargo run --release --example causal_attrib_probe --features smarm-causal
@@ -147,6 +151,11 @@ fn main() {
let attributed = injected as f64 / (pct as f64 / 100.0); let attributed = injected as f64 / (pct as f64 / 100.0);
let eff = attributed / in_site as f64; let eff = attributed / in_site as f64;
// Books-closure check: add back the runnable off-CPU gaps the
// audit counted (delta terms -> raw via /pct) — should be ~1.00.
let eff_closed = (injected as f64 + audit.offcpu_in_site_cycles as f64)
/ (pct as f64 / 100.0)
/ in_site as f64;
let missing = in_site as f64 - attributed; let missing = in_site as f64 - attributed;
let tail_us = if entries > 0 { let tail_us = if entries > 0 {
missing / entries as f64 / hz * 1e6 missing / entries as f64 / hz * 1e6
@@ -154,7 +163,7 @@ fn main() {
f64::NAN f64::NAN
}; };
println!( println!(
"pct {pct:>2}% in_site {:>8.1}ms attributed {:>8.1}ms eff {eff:.3} entries {entries} missing/entry {tail_us:.1}µs", "pct {pct:>2}% in_site {:>8.1}ms attributed {:>8.1}ms eff {eff:.3} eff+offcpu {eff_closed:.3} entries {entries} missing/entry {tail_us:.1}µs",
in_site as f64 / hz * 1e3, in_site as f64 / hz * 1e3,
attributed / hz * 1e3, attributed / hz * 1e3,
); );
@@ -163,13 +172,15 @@ fn main() {
// missing attribution above. // missing attribution above.
let ms = |c: u64| c as f64 / hz * 1e3; let ms = |c: u64| c as f64 / hz * 1e3;
println!( println!(
" audit: absorbed {:>7.1}ms forgiven {:>6.1}ms drop park {:>5.2}ms/{:<5} yield {:>5.2}ms/{:<5} discard >max {:>5.2}ms/{:<3} unarmed {}", " audit: absorbed {:>7.1}ms forgiven {:>6.1}ms drop park {:>5.2}ms/{:<5} yield {:>5.2}ms/{:<5} offcpu {:>6.2}ms/{:<5} discard >max {:>5.2}ms/{:<3} unarmed {}",
ms(audit.spin_absorbed_cycles), ms(audit.spin_absorbed_cycles),
ms(audit.park_forgiven_cycles), ms(audit.park_forgiven_cycles),
ms(audit.drop_park_cycles), ms(audit.drop_park_cycles),
audit.drop_park_n, audit.drop_park_n,
ms(audit.drop_yield_cycles), ms(audit.drop_yield_cycles),
audit.drop_yield_n, audit.drop_yield_n,
ms(audit.offcpu_in_site_cycles),
audit.offcpu_in_site_n,
ms(audit.discard_overmax_cycles), ms(audit.discard_overmax_cycles),
audit.discard_overmax_n, audit.discard_overmax_n,
audit.discard_unarmed_n audit.discard_unarmed_n