re: confirm, move and back -- every cue the five screens need is now

located, and two of them reproduce

Continuing Q8 rather than opening anything new. The gap that mattered was
the confirm cue: a menu needs a sound on A, and I had only cursor and
cancel.

The fix was where I was counting from. The first run started counting
streams at the main menu, so the confirm cue had already fired during
boot and showed up as "played before any input". Counting from the TITLE
instead attributes it cleanly: the A that advances title -> main menu
fires the 12288-byte wave at 0x5d6c0, together with the two stereo BGM
stems, which is the menu's music starting.

So move (0x1ec0, 0.533 s), confirm (0x5d6c0, 1.016 s) and back (0x0ec0,
0.344 s) are all located and decodable. Move and back came back with
IDENTICAL head bytes and sizes on a second independent boot, so the
dedup-keyed method is stable and those two are now n=2 rather than n=1.

Two honest limits recorded rather than smoothed over. The A press both
confirms and opens a screen, so its wave could be the cue the vocabulary
calls DECIDE or the one it calls SUB_WIN_OPN -- the port gets the sound
the game plays, not a name. And left/right fired no new stream, which
excludes a DISTINCT invalid cue but cannot exclude them quietly replaying
one of the three already heard, because the probe dedups on head bytes.
This commit is contained in:
Sylpheed RE agent
2026-08-28 19:38:09 +00:00
parent b1b2576769
commit 2b0e66b6ca
3 changed files with 60 additions and 6 deletions

View File

@@ -170,10 +170,18 @@ authored version can be deleted.
executable — those extensions are the authoring tool's). But Canary's executable — those extensions are the authoring tool's). But Canary's
`--xma_param_probe=true` logs every stream's head bytes, and searching them in `--xma_param_probe=true` logs every stream's head bytes, and searching them in
`Static.slb` locates the wave exactly: `Static.slb` locates the wave exactly:
**d-pad move → `0x1ec0`, 4 packets / 8 192 B, mono 48 kHz; Ⓑ back`0x0ec0`, **d-pad move → `0x1ec0` (4 pkts / 8 192 B, 0.533 s); Ⓐ confirm`0x5d6c0`
2 packets / 4 096 B.** Each matched at one offset only, and they are contiguous (6 pkts / 12 288 B, 1.016 s); Ⓑ back → `0x0ec0` (2 pkts / 4 096 B, 0.344 s)** —
every cue the five screens need. Move and back reproduce with identical head
bytes across **two independent boots**. Each matched at one offset only, and
the first two are contiguous
(`0x0ec0 + 4096 = 0x1ec0`) — the bank is a packed run of whole 2 048-byte (`0x0ec0 + 4096 = 0x1ec0`) — the bank is a packed run of whole 2 048-byte
packets with no delimiters, which is why nothing could be scanned for. packets with no delimiters, which is why nothing could be scanned for.
**⬅ and ➡ play nothing distinct** — no new stream on either, so leave them
silent (the probe dedups, so this excludes a *distinct* invalid cue, not a
quiet replay of an already-heard one).
🟡 The Ⓐ press both confirms and opens a screen, so whether its wave is the cue
named `SE_UI_DECIDE` or `SE_UI_SUB_WIN_OPN` is not separated.
⚠️ The order is **not** cue-id order, so the index must be observed per cue, not ⚠️ The order is **not** cue-id order, so the index must be observed per cue, not
counted. ✅ **The slices decode**: 0.533 s, 0.344 s and 1.016 s of mono 48 kHz counted. ✅ **The slices decode**: 0.533 s, 0.344 s and 1.016 s of mono 48 kHz
audio with the attack-and-decay shape of UI blips, via audio with the attack-and-decay shape of UI blips, via
@@ -258,7 +266,8 @@ here until 2026-08-28 and is now settled.)
| | what | why it is stuck | | | what | why it is stuck |
|---|---|---| |---|---|---|
| 🟡 | **cue NAME → event binding** (Q8) | the event→**wave** binding is now measured; that the cursor's wave is the cue *named* `SE_UI_CURSOR` is still read off the authors' identifiers | | 🟡 | **cue NAME → event binding** (Q8) | event→**wave** is measured for move/confirm/back; that the cursor's wave is the cue *named* `SE_UI_CURSOR` is still read off the authors' identifiers |
| ❔ | **the other ~319 SE cues** (Q8) | located one at a time by triggering them; only the three the menu needs have been done |
| 🟡 | **the paint-order tie-break** (Q3) | eight candidates refuted; costs one element's blend on one screen | | 🟡 | **the paint-order tie-break** (Q3) | eight candidates refuted; costs one element's blend on one screen |
| 🟡 | **GamePart ids behind the buttons** (Q4) | the *screens* are measured; the ids are a name match onto the executable's class names | | 🟡 | **GamePart ids behind the buttons** (Q4) | the *screens* are measured; the ids are a name match onto the executable's class names |
| ❔ | **the boot transitions in code** (Q6) | bounded as code-not-data, not proven. `sub_821C6458` — the substantial function in `GamePart_Title`'s neighbourhood — has **not been read** | | ❔ | **the boot transitions in code** (Q6) | bounded as code-not-data, not proven. `sub_821C6458` — the substantial function in `GamePart_Title`'s neighbourhood — has **not been read** |

View File

@@ -8,7 +8,7 @@ event packets bytes channels/rate offset in Static.slb
------------------------- ------- ------ -------------- -------------------- ------------------------- ------- ------ -------------- --------------------
d-pad move (cursor) 4 8192 mono 48000 Hz 0x1ec0 d-pad move (cursor) 4 8192 mono 48000 Hz 0x1ec0
B / back (cancel) 2 4096 mono 48000 Hz 0x0ec0 B / back (cancel) 2 4096 mono 48000 Hz 0x0ec0
(played before any input) 6 12288 mono 48000 Hz 0x5d6c0 A / confirm (title->menu) 6 12288 mono 48000 Hz 0x5d6c0
Each head matched at exactly ONE offset. The first two are contiguous: Each head matched at exactly ONE offset. The first two are contiguous:
0x0ec0 + 4096 = 0x1ec0. 0x0ec0 + 4096 = 0x1ec0.
@@ -29,3 +29,11 @@ DECODED 2026-08-28 with tools/re-capture/slb_extract_wave.py + ffmpeg's xma1:
CONTROL: the same synthesized RIFF wrapper applied to BGM_001.slb's first wave CONTROL: the same synthesized RIFF wrapper applied to BGM_001.slb's first wave
(offset 14336, stereo) decodes to 173.808875 s -- identical to the duration (offset 14336, stereo) decodes to 173.808875 s -- identical to the duration
obtained from that bank's own on-disc RIFF header. The wrapper is correct. obtained from that bank's own on-disc RIFF header. The wrapper is correct.
SECOND RUN 2026-08-28 -- independent boot, same probe:
* d-pad move and B reproduced with IDENTICAL head bytes and sizes (2 of 2 runs).
* The 12288-byte wave fires on the A that advances title -> main menu, together
with the two stereo BGM stems (the menu's music starting). Counting from the
title rather than the menu is what attributed it.
* Left and Right fired NO new stream -- no distinct invalid cue. (Dedup caveat:
a press replaying an already-heard wave would also log nothing.)

View File

@@ -159,7 +159,7 @@ bytes**. Searching those bytes in `Static.slb` finds the wave.
|---|---|---|---|---| |---|---|---|---|---|
| **d-pad move** (cursor) | 4 | 8 192 | mono 48 kHz | **`0x1ec0`** | | **d-pad move** (cursor) | 4 | 8 192 | mono 48 kHz | **`0x1ec0`** |
| **Ⓑ back** (cancel) | 2 | 4 096 | mono 48 kHz | **`0x0ec0`** | | **Ⓑ back** (cancel) | 2 | 4 096 | mono 48 kHz | **`0x0ec0`** |
| played before any input | 6 | 12 288 | mono 48 kHz | `0x5d6c0` | | **Ⓐ confirm** (title → main menu) | 6 | 12 288 | mono 48 kHz | **`0x5d6c0`** |
Each head matched at **exactly one** offset. Reference data in Each head matched at **exactly one** offset. Reference data in
[`data/se-cue-runtime-offsets.txt`](data/se-cue-runtime-offsets.txt). [`data/se-cue-runtime-offsets.txt`](data/se-cue-runtime-offsets.txt).
@@ -198,7 +198,7 @@ slb_extract_wave.py Static.slb 0x1ec0 4 # -> Static_0x1ec0.riff -> 0.533 s
|---|---|---|---|---|---|---| |---|---|---|---|---|---|---|
| d-pad move | `0x1ec0` | 4 | **0.533 s** | 2 085 | 29 813 | sharp attack, monotonic decay | | d-pad move | `0x1ec0` | 4 | **0.533 s** | 2 085 | 29 813 | sharp attack, monotonic decay |
| Ⓑ back | `0x0ec0` | 2 | **0.344 s** | 2 985 | 16 973 | attack, peak in frame 2 | | Ⓑ back | `0x0ec0` | 2 | **0.344 s** | 2 985 | 16 973 | attack, peak in frame 2 |
| pre-input cue | `0x5d6c0` | 6 | **1.016 s** | 4 327 | 32 767 | peaks in frame 3, long decay | | **Ⓐ confirm** | `0x5d6c0` | 6 | **1.016 s** | 4 327 | 32 767 | peaks in frame 3, long decay |
All three are mono 48 kHz, audible from sample 0, and have the percussive All three are mono 48 kHz, audible from sample 0, and have the percussive
attack-and-decay shape of UI blips — not silence, not noise. attack-and-decay shape of UI blips — not silence, not noise.
@@ -216,3 +216,40 @@ The bitrates are consistent too: 8 192 B / 0.533 s ≈ 15.4 kB/s, 4 096 / 0.344
it from the disc, and the corpus keeps measurements and tooling rather than it from the disc, and the corpus keeps measurements and tooling rather than
extracted game audio. The offsets, packet counts and this tool are the extracted game audio. The offsets, packet counts and this tool are the
deliverable. deliverable.
## The three cues the milestone needs are bound — 2026-08-28, second run
A second, independent boot repeated the probe and pinned the one that was still
unattributed.
| event | wave | packets / bytes | runs agreeing |
|---|---|---|---|
| **d-pad move** | `Static.slb+0x1ec0` | 4 / 8 192 | **2 of 2** — identical head bytes |
| **Ⓑ back** | `Static.slb+0x0ec0` | 2 / 4 096 | **2 of 2** — identical head bytes |
| **Ⓐ confirm** | `Static.slb+0x5d6c0` | 6 / 12 288 | newly bound this run |
The `0x5d6c0` wave was previously logged as "played before any input", because
the first run only started counting at the main menu. Counting from the **title**
instead shows it appears exactly on the Ⓐ that advances title → main menu, along
with the two stereo BGM stems (the menu's music starting).
So move / confirm / back — everything the five-screen milestone needs — are
located and decodable.
🟡 **What that Ⓐ measurement does not separate.** The same press both *confirms*
and *opens a screen*, so this wave could be the cue the vocabulary calls
`SE_UI_DECIDE` or the one it calls `SE_UI_SUB_WIN_OPN`. The port needs *a* sound
on confirm and this is the one the game plays there; which name it carries is not
established.
## ❔ ⬅ and ➡ play nothing distinct
[`menu-navigation-semantics.md`](menu-navigation-semantics.md) measured that
left/right do not move the cursor. They also **fire no new XMA stream** — so
there is no distinct "invalid" cue on the main menu, and `SE_UI_IMPOSI` was not
observed. The port should leave left/right silent.
⚠️ **Reach of that negative:** the probe dedups on head bytes, so a press that
replayed an *already-heard* wave would log nothing. At that point in the run the
cursor, confirm and BGM waves had all been heard. So this excludes a **distinct**
invalid cue; it cannot exclude left/right quietly replaying one of those three.