Fetching latest headlines…
Porting Test Drive II from SNES to PC, Part 10: Closing the 1014..1021 ownership block
NORTH AMERICA
πŸ‡ΊπŸ‡Έ United Statesβ€’March 22, 2026

Porting Test Drive II from SNES to PC, Part 10: Closing the 1014..1021 ownership block

1 views0 likes0 comments
Originally published byDev.to

Porting Test Drive II from SNES to PC, Part 10: Closing the 1014..1021 ownership block

The previous checkpoint closed the direct bridge-extracted 1006..1013 block with live ownership evidence.

That left the next step unchanged:

push the same proof surface one block later and see whether the late 01:9FE5 path is still stable when the window reaches frame 1021.

This checkpoint does that.

Why 1021 mattered

1021 is the end of the next direct bridge-extracted block:

  • 1014..1021

By this point the repo already had a strong bridge-visible story for the block, but that is still weaker than a producer-trace-backed contract.

The questions were:

  • does the block still close under the same callback family?
  • do the producer domains stay the same again?
  • does the write pattern change even if the visible overlay stops growing?

Those are the questions worth answering if the goal is to replace sampled attract slices with native state playback instead of just collecting screenshots.

The checkpoint

The workflow stayed intentionally small:

  1. extract frame 1021
  2. build a design pack
  3. run a bounded write-point probe across 1014..1021
  4. merge that probe into a visual contract

The exact commands were:

MESEN_RELEASE_DIR=/home/nivando-soares/Mesen2/bin/linux-x64/Release \
make -C tools mesen-design-pack MESEN_FRAME=1021

MESEN_RELEASE_DIR=/home/nivando-soares/Mesen2/bin/linux-x64/Release \
MESEN_TIMEOUT_SECONDS=150 \
TD2_BOOT_PROBE_OUTPUT_PREFIX=tools/out/visual_contract_probe_1021_live/td2_boot_probe \
TD2_BOOT_PROBE_TOTAL_FRAMES=1022 \
TD2_BOOT_PROBE_TRACE_START_FRAME=1014 \
TD2_BOOT_PROBE_TRACE_END_FRAME=1021 \
TD2_BOOT_PROBE_TRACE_WRITE_POINTS='objsel=00:2101,oamaddl=00:2102,oamaddh=00:2103,oamdata=00:2104,vmaddl=00:2116,vmaddh=00:2117,vmdatal=00:2118,vmdatah=00:2119,cgadd=00:2121,cgdata=00:2122' \
TD2_BOOT_PROBE_WRITE_POINT_MAX_HITS=8192 \
./validation/run_mesen_probe_boot.sh

python3 tools/build_mesen_visual_contract.py \
  tools/out/design_frame1021 \
  tools/out/visual_contract_frame1021_live_probe.json \
  --probe-json tools/out/visual_contract_probe_1021_live/td2_boot_probe.json

The promoted artifacts are now committed:

  • tools/out/visual_contract_probe_1021_live/td2_boot_probe.json
  • tools/out/visual_contract_frame1021_live_probe.json

What the trace showed

The probe recorded:

  • 5400 write hits
  • 0 drops
  • exact trace window 1014..1021

The callback family still does not move:

  • active main callback: 01:9FE5
  • active IRQ callback: 00:835F

The producer domains also still stay in the same two places:

  • OAM: 4368 writes across 1014..1021
  • VRAM: 1032 writes at 1014, 1015, 1017, and 1019

That is the useful nuance of this checkpoint.

At 1013, bounded VRAM traffic had already stopped short of the block end. By 1021, that pattern gets even sparser while OAM stays flat.

So the better reading is now:

  • callback ownership stays flat
  • OAM ownership stays flat
  • bounded VRAM activity thins out inside the block instead of staying continuous

That is exactly the kind of result that is easy to miss if you only compare final images.

What changed visually

The fresh design pack for 1021 reports:

  • 61 visible sprites

That matches the previous end-of-block proof at 1013, which also had:

  • 61 visible sprites

So the visible overlay does not keep expanding here.

That matters because it separates two different readings:

  • the block is still active under the same owner
  • but the visible-sprite count has flattened while bounded VRAM traffic keeps thinning

That is a better behavioral description than β€œthe screen still looks like the same scene.”

Validation

The extracted frame was compared against a fresh local screenshot-backed capture for 1021:

python3 tools/compare_frames.py \
  tools/out/intro_loop_frame_01021_frame.png \
  tools/out/mesen_frame1021/main_visible.ppm \
  --diff-out tools/out/mesen_frame1021_vs_intro1021_diff.ppm

That landed at:

  • 3557 mismatched pixels (6.202916%)

This is still not a screenshot-exact checkpoint.

The bounded renderer-side validation stayed on the stable Python mode7-ppu surface:

python3 tools/render_mesen_snes_bg.py \
  tools/out/mesen_frame1021/vram.bin \
  tools/out/mesen_frame1021/cgram.bin \
  tools/out/mesen_frame1021/ppu_state.json \
  tools/out/mesen_frame1021_mode7ppu.ppm \
  --oam tools/out/mesen_frame1021/oam.bin \
  --obj-renderer mode7-ppu \
  --json-out tools/out/mesen_frame1021_mode7ppu.json

python3 tools/compare_frames.py \
  tools/out/mesen_frame1021/main_visible.ppm \
  tools/out/mesen_frame1021_mode7ppu.ppm \
  --diff-out tools/out/mesen_frame1021_mode7ppu_vs_mesen1021_diff.ppm

That compare landed at:

  • 10 mismatched pixels (0.017439%)

So the renderer side is still on the same practical bridge-visible surface already expected for this later attract family.

Why this checkpoint is useful

After 998, 1005, and 1013, the repo could already say that the late direct bridge-extracted blocks were staying inside one ownership family.

After 1021, it can say something stronger:

  • the third consecutive direct block is also closed by live ownership evidence
  • OAM still stays flat
  • visible sprites no longer increase
  • bounded VRAM activity becomes sparse instead of continuous

That is a clearer statement about the actual behavior of the scene.

The late ownership chain is now closed at:

  • 998
  • 1005
  • 1013
  • 1021

That makes the next move obvious.

What comes next

The next step is to extend the same proof surface to frame 1029 and close the next direct bridge-extracted 1022..1029 block.

The headline for this checkpoint is simple:

the 1014..1021 block is now closed by live ownership evidence, and the useful new fact is that visible sprites flatten while bounded VRAM traffic becomes sparse inside the block.

Comments (0)

Sign in to join the discussion

Be the first to comment!