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>
81 lines
3.4 KiB
Diff
81 lines
3.4 KiB
Diff
Phase C+8 — KeResetEvent canary-parity return value (sibling of C+7)
|
|
====================================================================
|
|
|
|
Scope: `crates/xenia-kernel/src/exports.rs`
|
|
LOC: ~12 body + ~80 test = ~92 net
|
|
|
|
Body change — `ke_reset_event` (~4160-4181):
|
|
--------------------------------------------
|
|
|
|
-fn ke_reset_event(ctx: &mut PpcContext, mem: &GuestMemory, state: &mut KernelState) {
|
|
- let h = ctx.gpr[3] as u32;
|
|
- ensure_dispatcher_object(state, mem, h);
|
|
- let previous = match state.objects.get_mut(&h) {
|
|
- Some(KernelObject::Event { signaled, .. }) => {
|
|
- let prev = *signaled;
|
|
- *signaled = false;
|
|
- prev as u32
|
|
- }
|
|
- _ => 0,
|
|
- };
|
|
- ctx.gpr[3] = previous as u64;
|
|
-}
|
|
+fn ke_reset_event(ctx: &mut PpcContext, mem: &GuestMemory, state: &mut KernelState) {
|
|
+ // r3 = PKEVENT on Ke* (guest pointer). See `ensure_dispatcher_object`
|
|
+ // for the lazy-shadow step.
|
|
+ let h = ctx.gpr[3] as u32;
|
|
+ ensure_dispatcher_object(state, mem, h);
|
|
+ // Canary parity (xevent.cc:72-75): `XEvent::Reset` returns constant `1`
|
|
+ // on success — exact sibling of `XEvent::Set`. The NT contract claims
|
|
+ // the prior signaled state, but canary hardcodes `1` and the game
|
|
+ // observes that value via Phase A oracle at idx=102164. Sibling fix
|
|
+ // of Phase C+7 KeSetEvent (xevent.cc:60-64). The `assert_always;
|
|
+ // return 0` arm is preserved (no shadow -> 0).
|
|
+ let (previous, found) = match state.objects.get_mut(&h) {
|
|
+ Some(KernelObject::Event { signaled, .. }) => {
|
|
+ let prev = *signaled;
|
|
+ *signaled = false;
|
|
+ (prev as u32, true)
|
|
+ }
|
|
+ _ => (0u32, false),
|
|
+ };
|
|
+ state.audit_signal(h, ctx.lr as u32, "KeResetEvent", previous as u64);
|
|
+ ctx.gpr[3] = if found { 1 } else { 0 };
|
|
+}
|
|
|
|
Existing test (~5631-5647) comment-only update:
|
|
-----------------------------------------------
|
|
|
|
- assert_eq!(ctx.gpr[3], 1, "previous state must be reported");
|
|
+ assert_eq!(ctx.gpr[3], 1, "canary parity: KeResetEvent returns constant 1 on hit");
|
|
(plus updated doc explaining canary parity)
|
|
|
|
New tests added at module end (mirror of C+7's KeSetEvent block):
|
|
-----------------------------------------------------------------
|
|
|
|
// Phase C+8 -- KeResetEvent canary-parity return value (sibling of C+7)
|
|
1. ke_reset_event_returns_constant_one_on_unsignaled_manual_reset
|
|
(this is THE Phase A oracle case -- prior state 0, canary returns 1)
|
|
2. ke_reset_event_returns_constant_one_on_signaled_auto_reset
|
|
(distinguish from prior-state-return bug: prior 1 == constant 1)
|
|
3. ke_reset_event_returns_zero_on_missing_object
|
|
(canary's `assert_always; return 0` arm -- invalid handle)
|
|
4. nt_clear_event_resets_shadow_and_returns_status_success
|
|
(already canary-parity; symmetry coverage)
|
|
|
|
`nt_clear_event` body: no change. Canary `NtClearEvent_entry` calls
|
|
`xeNtClearEvent` which uses `XEvent::Clear` (void return); already
|
|
returning STATUS_SUCCESS in ours.
|
|
|
|
Cascade outcome:
|
|
----------------
|
|
- A=verify canary's return: DONE, `1` confirmed from xevent.cc:72-75
|
|
- B=land fix: DONE
|
|
- C=main chain advances past 102164: DONE -- 102164 -> 102197 (+33)
|
|
- D=clean re-validation: DONE
|
|
- E=no escalation: DONE (12-LOC body change, additive tests only)
|
|
|
|
Next target: XamContentCreateEnumerator at tid=6->1 idx=102197
|
|
canary return_value=1317 (0x525 = X_ERROR_NO_CONTENT)
|
|
ours return_value=0 (likely STATUS_SUCCESS or missing impl)
|