Files
xenia-rs/audit-runs/audit-060-fnptr-array-bootstrap/canary-summary.md
MechaCat02 ef93a4fa14 handoff: VSync/event-wedge fixes + iterate 2.A–2.BC research notes
Source changes (dormant parity infra, retained from iterate 2.AI/2.AO):
- xenia-kernel/exports.rs: nt_create_event manual_reset polarity +
  related event wiring
- xenia-gpu/mmio_region.rs: D1MODE_VBLANK_VLINE_STATUS hardcode parity

Also lands the audit-runs/ analysis notes (.md/.txt/.json digests) for the
iterate 2.x VSync/0x10e8/0x1004 wedge investigation. Raw trace dumps
(.jsonl/.gz/.csv/.stdout) and agent worktrees (.claude/) are gitignored as
regenerable local artifacts — see memory + HANDOFF for the running findings.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-05 07:19:08 +02:00

5.0 KiB
Raw Blame History

AUDIT-060 PROBE C-WIN — canary side, fnptr-array bootstrap

Date: 2026-05-12 Engine: xenia-canary Windows Debug under Wine 9.0 (6de80dffe clean + AUDIT-030 patch re-applied/reverted) ISO: Project Sylpheed - Arc of Deception (USA/EU) Output dir: xenia-rs/audit-runs/audit-060-fnptr-array-bootstrap/ Discipline: READ-ONLY wrt logic; audit-030 patch reverted clean at exit.

Phase 1: sanity check — PASS

PC 0x825070F0, 90s wallclock → 1 fire, lr=0x824F7B24 — bit-identical to AUDIT-058 Linux Debug canary. Windows Debug canary under Wine reaches the same activation phase. New oracle validated for future audits.

Phase 2: sub_821B6DF4 entry — 0× fires

  • 120s → 0 fires (canary-sub821B6DF4-120s.log)
  • 240s → 0 fires (canary-sub821B6DF4-240s.log)

Does not fire in canary either at the runtimes probed. Cross-reference with PROBE-O (ours-summary.md) — which dis-asmed sub_821B6DF4 and found subi r31, r12, 112; mflr r12; ... prolog + MSVC FuncInfo magic 0x19930522 at .rdata:0x820C1994 referencing it — confirms sub_821B6DF4 is a C++ EH catch-handler thunk, not a normal call target. AUDIT-058's "static caller ladder" was reading EH handler-array linkage as if it were a call ladder.

Phase 3: sub_8245FEB8 entry — 2× fires, single caller PC

  • 120s → 2 fires, both lr=0x8246020C (canary-sub8245FEB8.log)
    • Fire 1: r3=BC365C40 r4=00000004 r5=701CF340 r6=0 r31=701CF2E0
    • Fire 2: r3=BC365C40 r4=00000001 r5=705AFB00 r6=0 r31=705AFAA0
  • Same r3, different r4 (4 then 1) — installing two different slot indices into same dispatch object.

Phase 4: LR resolution + caller chain

LR 0x8246020C → containing fn sub_824601A0 (824601A0..82460254).

Linear caller chain in DB:

sub_8245FEB8  (vptr installer)
  ← sub_824601A0  (1 static caller)
    ← sub_82460118  (1 static caller)
      ← sub_82452AB8  (6 static callers — branches; AUDIT-050 direct target of sub_82452DC0)
        ← sub_82452DC0  (work-submitter; AUDIT-050-054 root)

Verified: sub_82452DC0 → sub_82452AB8 is one of the 9 edges AUDIT-050 enumerated as direct targets of the work-submitter.

Phase 5: cross-reference

sub_8245FEB8 has 2 static callers:

  • sub_824601A0 (1 site, PC=0x82460208) — the one canary fires via in this run
  • sub_8245FB68 (2 sites, PCs 0x8245FD00 + 0x8245FD28) — internal lib path

The PROBE-O parallel track (xenia-rs side) found sub_8245FEB8 actually fires 5× in ours, called from multiple paths including sub_824601A0+0x68 (PC=0x82460208) — i.e. the exact same call site canary uses. AUDIT-059's "vptr installer dead in ours" was FALSIFIED at runtime by PROBE-O.

Combined verdict (this run + PROBE-O)

  1. AUDIT-058's caller ladder is an EH unwind path, not a normal activation chain. sub_821B6DF4 is a C++ catch-handler. The 6-level ladder up from sub_825070F0 is throw-side EH metadata, fires iff a specific exception type-id is thrown. Doesn't fire in canary at 240s and doesn't fire in ours at 500M instr — neither engine throws this exception in our window.

  2. AUDIT-059's "vptr installer dead in ours" is false (PROBE-O measured 5× fires). The dispatch-table-installer infrastructure (sub_8245FEB8) is ALIVE in both engines. The γ-wedge bug is NOT a missing vptr-install — it's downstream.

  3. Convergence on AUDIT-050-054 territory: the bootstrap path for the two AUDIT-059 signalers AND the AUDIT-058 sub_825070F0 chain all funnel through sub_82452DC0 (work-submitter). This is the SAME gate AUDIT-051's +0x78 beq cr6 predicate identifies. AUDIT-060 collapses the gamma investigation into AUDIT-051's struct-population bug — there is ONE root cause, not multiple parallel "dead clusters".

  4. New Windows Debug canary oracle is operational. Wine + audit-030 patch reproduces Linux Debug canary results bit-identically (verified at PC 0x825070F0). Can be used for future probes including potentially deeper traces.

Files

  • canary-sanity-825070F0.log — Phase 1 (1 fire)
  • canary-sub821B6DF4-120s.log — Phase 2 first run (0 fires)
  • canary-sub821B6DF4-240s.log — Phase 2 extended (0 fires)
  • canary-sub8245FEB8.log — Phase 3 (2 fires lr=0x8246020C)
  • p2-stdout.log, p2b-stdout.log, p3-stdout.log — wine stdout
  • ours-summary.md — PROBE-O parallel track (xenia-rs side)
  • canary-summary.md — this file

Recommendation for AUDIT-061

Echoing PROBE-O's recommendation:

  • Drop the "find fnptr-array activator" framing — sub_821B6DF4 is an EH catch handler.
  • Drop "vptr installer dead" framing — measured 5× live in ours.
  • Re-focus on AUDIT-051's struct-population bug at sub_82452DC0+0x78 (the [r3+0]/[r3+4] predicate gate from 80-byte stack-local at r31+96). With Windows Debug canary oracle online, mid-fn PC probes inside sub_82452DC0 become feasible at scale.
  • Optional: investigate _CxxThrowException-equivalent fire-counts canary vs ours — if canary throws an exception ours doesn't (or vice versa) at boot, that would explain the AUDIT-058 ladder differential.