diff --git a/context/gauges-hud.md b/context/gauges-hud.md index 3ecb848..aaba082 100644 --- a/context/gauges-hud.md +++ b/context/gauges-hud.md @@ -699,6 +699,47 @@ a batch of gauges per gauge turn (a visit is only a rate-mask check unless due). within ~1s, bg cost 2-4 ms/frame. Diagnostics: `BT_PERF=1` → `[perf] … bgTasks/gaugeTurns/ sweeps/active` 1 Hz (APPMGR.cpp); `[score] panel DRAW` edge log (btl4gau3.cpp, BT_SCORE_LOG). +## The COOLANT-LEAK ALARM audio chain — fully built; the shared-Stop is AUTHENTIC (#99, 2026-08-01) [T1 disasm-verified] + +The audible leak warning is **implemented and works end to end**; an earlier note +claiming it was "genuinely unbuilt" was wrong (asserted without checking). + +**The chain**, traced live (all probes under `BT_ATTRBIND_LOG`): +`HeatSink::coolantActive` (published as the `ReportLeak` attribute) changes 0->1 +-> `AttributeWatcherOf::Execute` sees it (`[watchpoll] CHANGE`) +-> `AudioMatchOf::SendNotificationOfChange` fires (`[matchfire] val=1 -> ctl 1`) +-> `AudioControlSequence::ReceiveControl(StartAudioControlID)` -> `StartSequence` +-> an `AudioIdleWatcher` ticks it each frame (`IdleAudioControlID` -> `RunSequence`) +-> `[seqsend]` emits the authored pattern: two chirps then an ~8s sustained tone, looped. + +**The authored wiring (BTL4.RES): 19 subsystems, ONE shared alarm sequence.** +`Condenser1-6, GeneratorA-D, Myomers, PPC_1/2, ERMLaser_1-3, SRM6_1/2, Avionics` +each bind TWO `AudioLogicalTrigger`s to their own `ReportLeak` — match 1 -> ctl 1 +(Start), match 0 -> ctl 2 (Stop) — and every one of them drives the SAME sequence. + +**Consequence, and it is AUTHENTIC:** any single subsystem clearing its leak sends +an unconditional Stop, silencing the alarm even while others still leak; the +still-leaking ones never re-assert because their flag has not *changed*. Reported +from the field as a bug ("was sounding, resolved a leak, but there was another"). +**Do NOT 'fix' it** — verified in the arcade image, not merely inferred from the +engine source lineage: + +| what | where | +|---|---| +| same MUNGA sources compiled in | `d: esla_bt\munga\AUDSEQ.CPP` / `AUDWTHR.CPP` strings present | +| object factory | `@00466184` `case 0x4b` -> alloc **0x5C** -> ctor `@0043ccec` | +| vtable | `0x4ead48` | +| `ReceiveControl` | `@0043d3a4` — switch on control IDs **1 / 2 / 9 / 12** = Start / Stop / Idle / Tempo (exactly our enum) | +| Stop case | `@0043d3ca` -> unconditional `call StopSequence @0043d2d4` | +| `StopSequence` | tests only its OWN `isRunning` (`+0x28`), then the Chase loop — **no refcount, no awareness of other leak sources** | + +So the arcade had the identical structure. Silence in 4.11.674 was a different +cause: the OpenAL source pool was exhausted in every player session (see the audio +pooling fix) — an alarm that cannot acquire a source is silent. + +⚠ The bench cannot confirm audibility: it runs with no audio device (`live=0 +pooled=0`), so the control chain is verified but final playback is not. + ## Key Relationships - Full history: `docs/GAUGE_COMPOSITE.md`; reticle recovery: `phases/phase-02-dpl2d-reticle.md`. - Uses: [[attribute-pointer]] + [[reconstruction-gotchas]]; reads [[subsystems]] state.