Put the container on the chip, and find the held bus costs 463 times the seam
ROADMAP P6c, FINDINGS 68. 78,125 B of a DLXP2's audio out of channel 3, sample-exact, while the video channel fetches records off the same disc. The two pieces 67.6 said were missing: the lump buffer (pg_afill/pg_afetch, three slots and the minimum is unmeasured) and 67.2's remainder accumulator (pg_apay). The capture prices what the accumulator avoided at 1.26 s of lip-sync over the game, against 67.2's predicted 1.25. The finding is the third piece, which nothing had named: the MSM6258 has no starvation state, so the gap between a channel counting out and the next arm is a held nibble pair driving the predictor. Stealing, the seam is 0.51 ms over ten seconds because dma.i's new DM_HOOK services the chip from inside the transfer wait -- 250,000 of 250,240 looks. Held, the 68000 is halted and gets 369: every one of the ten lump boundaries has a seam, worst 72.8 ms, 2.31% of the audio. Identical bytes, different sound. 64.3 reaching the audio. Two bugs, and no counter in the player could see either. Clearing DM_BARV does not unchain a channel -- OCR bits 3-2 are what it obeys -- and the symptom is POLL TIMEOUT on the lump and every record after it. And the refill ran one lump ahead of its ring and overwrote the buffer the channel was reading: 11 of 11 armed, 11 fetched, no starve, and the sound wrong from 0.2 s in. Which is why the gate is a WAV: verify_packed_audio.py walks the stream one delivered byte at a time, because MAME's okim6258 resets the nibble select on every write and a byte is two nibbles only 99.994% of the time. check.sh ALL GREEN before (tmp/check_s36_start.log) and after (tmp/check_s36_end.log), with the new stage. Claude-Session: https://claude.ai/code/session_01194oWYW8DQXK1SZ2DnChW6
This commit is contained in:
+22
-5
@@ -100,18 +100,35 @@ def delta(nibble, step, variant):
|
||||
return -d if nibble & 8 else d
|
||||
|
||||
|
||||
def decode(nibbles, variant="shift", init=0, bits=12):
|
||||
"""Nibbles -> signed samples. State is (signal, step index); the step index
|
||||
is 0 at the start of a stream and `init` is where the accumulator starts."""
|
||||
def decode_state(nibbles, variant="shift", state=None, init=0, bits=12):
|
||||
"""The recursion, with its STATE in and out. (samples, (signal, idx)).
|
||||
|
||||
`decode` is this with the state thrown away, and it is written this way
|
||||
round rather than duplicated because a stream that STOPS and RESUMES is not
|
||||
a hypothetical here: an MSM6258 fed by a DMA channel goes on decoding
|
||||
whatever byte its data register still holds when the channel counts out
|
||||
(MAME okim6258 sound_stream_update reads m_data_in unconditionally while
|
||||
PLAYING), so the samples between one lump and the next are the recursion
|
||||
continuing over a repeated byte. tools/bench/verify_packed_audio.py has to
|
||||
carry that state across the seam to check the lump on the far side of it,
|
||||
and a second copy of the loop is a second place the clamp can drift.
|
||||
"""
|
||||
lo, hi = clamp_bounds(bits)
|
||||
signal, idx, out = init, 0, []
|
||||
signal, idx = state if state is not None else (init, 0)
|
||||
out = []
|
||||
for n in nibbles:
|
||||
signal += delta(n, STEP[idx], variant)
|
||||
signal = lo if signal < lo else (hi if signal > hi else signal)
|
||||
idx += INDEX_ADJUST[n & 7]
|
||||
idx = 0 if idx < 0 else (48 if idx > 48 else idx)
|
||||
out.append(signal)
|
||||
return out
|
||||
return out, (signal, idx)
|
||||
|
||||
|
||||
def decode(nibbles, variant="shift", init=0, bits=12):
|
||||
"""Nibbles -> signed samples. State is (signal, step index); the step index
|
||||
is 0 at the start of a stream and `init` is where the accumulator starts."""
|
||||
return decode_state(nibbles, variant, None, init, bits)[0]
|
||||
|
||||
|
||||
def encode(samples, variant="shift", init=0, bits=12):
|
||||
|
||||
Reference in New Issue
Block a user