How it works · write-up
Final shop and campaign restart
The earlier full campaigns stopped too early. $1178C is the final-message
selection byte, written before ShopScreen_InitAndOpen begins. It is not an
end-of-recording signal, and stays nonzero after Level 1 reloads. This correction
does not change any combat, navigation, collection or purchase tactic.
Original game logic
ReVa /mydumpat0 contains the shared shop code used by all levels:
$7D56clears the byte for ordinary shops;$7D6Csets it for the Level 5 ending.$10520,ShopScreen_InitAndOpen, checks it at$10652and$10670. The ending skips Sell/Buy and shows the three messages beginning at$10864,$1087Fand$108A6.$10798..$107C6prints those messages, separated by calls to$10912.$10912,ShopPanel_IdleWaitWhileDrawing, waits a counter, not a fire edge. The third message asks whether the game was good enough for the viewer.$107C6..$10842closes the shop and finishes the timed ending.$7E78..$7EAAadvances the level, wraps 6 to 1, increments the campaign-loop counter at$E18, and loads the next arena.- The subsequent GET READY interstitial waits for fire using instruction
$0011. This is the fire acknowledgement observed in the recording; no purchase or menu movement is required in the final shop itself.
The C session formerly gave the completion byte priority over every lifecycle branch, permanently suppressing that fire acknowledgement and subsequent play. It now acknowledges captured fire prompts first, remains passive during the timed final shop, and resumes normal gameplay once the player returns to Level 1. No ABI fields or per-frame host control calls were added.
The native validator latches the Level 5 ending, records shop-entry and restart milestones, and stops only at playable Level 1 outside the shop/fire prompt. Timed ending text uses a bounded ending wait rather than the ordinary idle-menu stall threshold. Explicit shorter probe flags retain their existing behavior.
Visible resident-C continuation
Source checkpoint:
E:/xenon_runs/ffmpeg-full-hd-highfps-20261005-r581-1.validation/checkpoints/f49973-periodic.sav
Both Release Hatari and the Python replay DLL were rebuilt through
xenon_tools/hatari_dev.ps1. The following run used resident C control, a visible
Sprite Stream window, normal speed, HD sprites, HIGH FPS, 1280x800 sprite recording,
QSV H.264/AAC MP4, and checkpoint requests every 150 frames:
python xenon_tools\validate_campaign.py native-run ffmpeg-final-shop-20261005-r582 --output-root E:/xenon_runs --resume E:/xenon_runs/ffmpeg-full-hd-highfps-20261005-r581-1.validation/checkpoints/f49973-periodic.sav --build-type Release --build-directory out/build/codex-validate --port 6945 --memory-trace off --record-format mp4 --record-encoder qsv --record-quality 18 --ffmpeg-path C:/Users/matej/AppData/Local/Microsoft/WinGet/Links/ffmpeg.exe --sprite-scale 4 --hd-sprites --high-fps --checkpoint-interval 150
Artifacts are in
ffmpeg-final-shop-20261005-r582.validation:
Canonical recordingOriginal MP4HD/high-FPS sprite MP4Run result,video audit,shop audit
| Event | Canonical frame |
|---|---|
| Loaded checkpoint | 49973 |
| First captured frame | 49975 |
| Final shop selected/opened | 49983 |
| Shop finished; Level 1 loading began | 51040 |
| GET READY waiting for fire | 51327 |
C pilot emitted Fire (0x80) |
51328 |
| Fire wait cleared | 51329 |
| Playable Level 1 returned | 51352 |
| Last recorded frame | 51358 |
There are 1384 continuous canonical records, zero shield damage, zero lost lives, zero stalls and no cleanup errors. Both shop messages and the final Level 1 playfield were inspected in the two videos. The final shop makes no transactions: cash remains 6400 and equipment remains unchanged throughout it. Hatari is left visible and paused after recording, with manual input released to the user.
Both MP4s fully decode with H.264 video and nonsilent mono AAC at 44100 Hz. The sprite video has 2657 continuous VBL-indexed frames, 1280x800, 44.256 seconds; the original has 2661 frames, 640x400, 44.322 seconds. Each audio track matches its own video duration (original drift 19 microseconds). Their different capture boundaries mean the decoded audio hashes are not identical.
An existing renderer limitation is visible after the shop closes: Sprite Stream temporarily retains the shop backdrop during part of the Level 1 loading screen, where the original recording displays loading text. The shop dialogue and the returned gameplay are recorded in both; use the original video for the complete authentic intervening loading screen. No renderer changes were made in this fix.
Validation: python -m unittest test_native_campaign test_native_session from
xenon_tools passes all 26 tests. Tests cover early ending selection, an active
shop, loading without a player, fire waits, the sticky flag in Level 1, bounded
ending stalls and resuming C gameplay. Re-observing the finalized capture with
the current monitor confirms completion at 51352 with no incidents.
This is a continuation from the latest checkpoint, not a new uninterrupted campaign. Earlier campaign survival and gameplay comparisons remain useful; their endpoint should be described as spaceship defeat/final-shop entry.