200 lines
18 KiB
Markdown
200 lines
18 KiB
Markdown
# Next Analysis Targets
|
|
|
|
## Priority 0: Native playable acceptance and calibration
|
|
|
|
The QEMU/HVF Cocoa game path, loopback `spike3-playfield/v1` bridge, safe
|
|
pause/restart synchronization, VPX 10.8.1 controller-plugin rebase, generated
|
|
manifest mapping, dual-mode VPX table, private controller profile, and native
|
|
two-window launcher are implemented; see `native-playable-table.md`. The
|
|
standalone table remains available.
|
|
|
|
The current native stop point is not yet validation-only. Resolve these two
|
|
blocking integration defects first:
|
|
|
|
- Replace the undefined VPX `Service1Key` through `Service4Key` variables with
|
|
the pinned host's supported `VPXActionKey(25)` through `VPXActionKey(28)`
|
|
expressions and exercise every mapped input in native VPX.
|
|
- Implement power-distribution command `0x15` for active-low Action, Start, and
|
|
cabinet-door inputs; correct the CPU-SPI `0-SW-23` raw-byte alignment; then
|
|
identify and complete the genuine factory/pre-play setup flow.
|
|
|
|
After those blockers, continue acceptance and calibration:
|
|
|
|
- Complete and preserve a normal three-ball game plus a multiball sequence
|
|
through the genuine game rules, without dashboard ball-motion shortcuts.
|
|
- Run the configurable native shot suite across shooter lane, both orbits,
|
|
every ramp, both outlanes/returns, pops, QEMU-authoritative slings, captive
|
|
ball, Town VUK, Poké Ball hold, gates/posts, and Meowth movement; tune only
|
|
the transitions that fail.
|
|
- Record input-to-visible-flipper and bridge-output-to-mechanism p95/p99 from
|
|
live native traces, plus rendered fps/1% low under simultaneous QEMU load.
|
|
- Preserve a full 60-minute inventory soak and explicit QEMU, bridge, and VPX
|
|
restart logs before declaring the long-run acceptance row complete.
|
|
- Replace `photo_estimate`, `comparable_part`, and `playability_tuned` ramp Z,
|
|
coil, restitution, and friction values when direct measurements or
|
|
slow-motion reference footage become available.
|
|
- Test QEMU D-Bus shared-memory scanout only after the two-window release is
|
|
stable. Retain Cocoa rather than adopting a VNC/browser capture fallback if
|
|
page-flip, 60 fps, or one-frame latency gates fail.
|
|
|
|
The current derived-data inventory and confidence boundaries are summarized in `analysis-evidence-map.md`. This page tracks only the work that remains or still needs stronger validation.
|
|
|
|
## Priority 1: Main Game Binary
|
|
|
|
Status: first-pass static strings, dependency review, targeted Ghidra decompilation, topper serial-key recovery, a MicroPython emulator artifact, and a Docker/QEMU emulation scaffold are complete; see `main-game-behavior.md`, `topper-serial-key-emulator.md`, and `docker-qemu-emulation.md`.
|
|
|
|
Target:
|
|
|
|
- `/games/pokemon_pro/game`
|
|
|
|
Why:
|
|
|
|
- It is the real machine application started by `game_monitor`.
|
|
- It interprets hardware state, controls gameplay, and likely talks to SPIKE node hardware.
|
|
- Exit codes are meaningful and documented in `game_monitor`.
|
|
|
|
Suggested first passes:
|
|
|
|
- Extract strings with offsets. Done: `analysis/static-triage/game.strings`.
|
|
- Identify linked libraries with an AArch64-aware ELF parser. Done with `objdump -p`; see `analysis/static-triage/game.objdump-p.txt`.
|
|
- Load into Ghidra/IDA/rizin as AArch64 PIE. Done for targeted paths.
|
|
- Search for paths from the init scripts: `/connectivity`, `/data`, `/games`, `/dev`, `UPDATE_REQUESTED`, `UPDATE_COMPLETED`, and node firmware filenames.
|
|
- Search for exit-code constants matching the monitor script: `0` through `6`, plus signal paths.
|
|
|
|
Follow-up passes:
|
|
|
|
- Exercise the new process-level lane documented in `process-level-emulation.md`. Static validation resolves all 51 target runtime libraries and matching `GLIBC_2.39`/`GLIBCXX_3.4.32` nodes; launcher/unit/syntax checks and the Apple Silicon ARM64 container build pass without executing the target. The initial `prepare` run exposed a nested `/games/spike3` alias bug which is now fixed and regression-tested; the post-fix run was blocked by the local Codex Docker approval/usage gate. The next acceptance sequence is `prepare`, `boot-display`, `spike-menu`, then `game`: execute the Mesa FBO smoke test, verify changing noVNC frames on port 6081, nonzero WAV capture, five-minute attract stability, one synthetic-ball Start/flipper/drain cycle from the dashboard, a qemu-user smoke run, and live GDB attachment. Record each failure from the timestamped `emulation/work/runs/` bundle rather than treating source completion as playability.
|
|
- Continue from `emulation/`: QEMU now boots the generated rootfs, exposes noVNC/dashboard, uses cached rootfs preparation, loads `virtio_gpu`, creates `/dev/dri/card0` plus `/dev/dri/renderD128`, and reaches `boot-display`, `spike-menu`, and `/games/game`. The generated rootfs includes a display probe, `fbdev` fallback interposer, Mesa surfaceless/pbuffer support, synthetic GLES/GBM/EGLImage fallbacks, GPIO sysfs stubs, framebuffer diagnostic renderer, and null ALSA default. Verified captures include nonblank `emulation/work/boot-display-fbo-wrap.ppm`, `emulation/work/spike-menu-gpio-wrap.ppm`, `emulation/work/game-gl-limits.ppm`, `emulation/work/game-fbdev-real-egl.png`, and the earlier diagnostic screen in `emulation/work/game-diagnostic.png`. The prior black-screen, missing-ALSA-default, boot-display framebuffer retry, SPIKE-menu GPIO 25 spam, Mesa loader dependency, and zero-varying shader blockers are cleared. The Docker/VNC softpipe path still encounters the target-created EGLImage/FBO issue and fallback color bands. The native macOS HVF/Cocoa path now has a verified complete 1920x1080 game-frame capture with the opt-in Debian Mesa 22.3.6 llvmpipe stack, although it uses about 5.3 host CPU cores and logs rejected page flips. Other current blockers are TAS/MAX amp register verify reads and bridge/netbridge startup failures (`OpenOCD init failed`, `netbridge image CRC mismatch`, `failed to init bridge thread`). The next display pass should measure llvmpipe frame pacing against softpipe and then investigate an Apple-GPU-backed VirtIO/translation path separately from the working CPU-rendered baseline.
|
|
- Validate `analysis/topper-emulator/topper_emulator.py` on live hardware or a nodebus capture.
|
|
- Recover the exact Magikarp topper `IDENTITY_BOARD_PART_ID` expected by command `0xfe`.
|
|
- Confirm physical UART pins, baud, voltage level, and any netbridge timing/break behavior required for a MicroPython node.
|
|
|
|
## Priority 2: `image.bin` / Radium Runtime Image
|
|
|
|
Status: first-pass static comparison, whole-rootfs audio search, targeted Ghidra xrefs for the sound path, main-game section 8 PCM table reversal, full main-game section 5 sound command-stream scan, generic section 5 opcode stream decode with payload-field summaries, native opcode length/handler table dumps, section 3 bitmap-record preview extraction, SPIKE menu section 8 PCM parse, SPIKE menu section 5 command-stream scan, Godot `.gdc` string decoding, full main-game WAV export, 54 SPIKE menu WAV exports, 25 Ghidra-confirmed native sound-name aliases, catalog-order offset candidate audit and preview page, 1,137 aligned Pokedex voice aliases, 1,705 draft ASR transcript labels, 169 low-confidence ASR review candidates, complete best-available named alias export, game-asset spoiler/unreleased-feature inventory, and wiki preview pages are complete; see `package-image-firmware.md`, `audio-asset-search.md`, `radium-image-format.md`, `sound-export.md`, `sound-catalog-offset-candidates.md`, `sound-pokedex-voice.md`, `sound-spike-menu.md`, `sound-native-names.md`, `sound-native-sound-test.md`, `sound-asr-draft-labels.md`, `sound-asr-review-candidates.md`, `sound-best-named-export.md`, `asset-previews.md`, `radium-section3-bitmaps.md`, and `game-asset-spoilers-unreleased.md`.
|
|
|
|
Targets:
|
|
|
|
- `/games/pokemon_pro/image.bin`
|
|
- `/games/pokemon_pro/spike3/spike_menu/image.bin`
|
|
|
|
Why:
|
|
|
|
- `image.bin` is larger than the executable and is probably a resource pack, filesystem image, or application asset bundle used by the game.
|
|
- The SPIKE menu explicitly copies its `image.bin` to tmpfs because updates may overwrite it while mmap-ed.
|
|
- `main.pck` has already been extracted into workspace-local `assets/`; see `godot-and-radium-assets.md`.
|
|
|
|
Suggested first passes:
|
|
|
|
- Run `file`, `binwalk`, entropy analysis, and magic-number scans. `file`, `binwalk`, header dump, and first strings completed.
|
|
- Search for embedded filenames, JSON, SQLite, compression headers, and Godot pack headers. First strings show Stern EULA text; no standard archive signature found by `binwalk`.
|
|
- Compare structure between game `image.bin` and spike-menu `image.bin`. First 0xb0-byte header shape and early EULA structure are similar, with different size/table values.
|
|
- Reverse the Radium/cereal mmap image table used by `/games/pokemon_pro/game` strings such as `Flash memory init mmap failed`, `/lcd/demand_loaded`, and `/lcd/auto_loaded`.
|
|
- Map the remaining Radium sound object IDs and section 8 chunk indices to higher-level script/gameplay names and call sites. Section 8 is decoded as headerless 16-bit PCM chunks, the parser resolves section 5 opcode `0x0b` command-stream references for all chunks, and all chunks are exported as WAVs. A native Godot bridge table confirms names for 25 IDs; Ghidra xrefs to its registration helper are exhausted at those 25 direct calls. Catalog-order comparison now identifies two native anchor offsets, `+69` for EOB Pokedex FX and `+78` for attack-type FX, and writes 199 neighboring unpromoted candidate labels plus one sound-test-candidate disagreement to `analysis/radium-image/catalog_offset_candidate_labels.tsv`. Of those candidates, 196 non-conflicting rows are now used as explicitly marked `catalog_offset_candidate` best-name aliases for sounds that previously had only structural object references. The Pokedex voice stream now maps objects `409` through `1545` to 1,137 semantic Pokemon voice labels. The current ASR pass adds 1,705 draft content labels for bounded voice-like clips, including 220 catalog-matched `SE_PK_VO_*` inferred names across 90 catalog constants, plus 34 low-confidence ASR review aliases for rows that would otherwise remain structural. ASR labels and catalog-offset candidates still need native/script confirmation.
|
|
- Maintain `analysis/all-sound-best-name-manifest.tsv` as the complete named-export surface. It currently has 2,545 rows: 25 confirmed native names, 1,137 Pokedex voice alignments, 220 catalog-matched ASR aliases, 583 raw ASR draft aliases after stronger-name priority, 196 explicitly marked catalog-offset candidate aliases, 34 low-confidence ASR review aliases, 1 main-image duplicate hash match inheriting a confirmed native name, 295 main structural object fallbacks, 4 SPIKE menu exact-payload matches inheriting stronger main-image names, and 50 SPIKE menu structural fallbacks. The remaining 345 structural rows are also grouped for review in `sound-unresolved-review.md` by bank and duration/channel bucket. Four sound-test-adjacent native label rows are retained for audit, but are not promoted as confirmed best-name labels because their numeric field conflicts with ASR/Pokedex cross-checks.
|
|
- Continue section 3 image-record recovery. Ghidra xrefs identify section 3 as a 1,477-entry qword pointer table; the current static exporter renders 1,449 raw indexed bitmap records and leaves 28 compact payload records undecoded in `analysis/radium-image/section3_bitmap_manifest.tsv`. Next steps are recovering the compact subtype, confirming palette/alpha semantics, and correlating section 3 records with section 4 or runtime display callers.
|
|
- Recover SPIKE menu object metadata and higher-level menu names in `/games/pokemon_pro/spike3/spike_menu/game`. The current menu export resolves all 54 section 8 PCM chunks through 300 section 5 opcode `0x0b` references, but only to local object IDs.
|
|
- Continue decoding compiled GDScript bytecode beyond string recovery if broader script call-site reconstruction is needed. Current static `.gdc` string decoding recovers the 760-name sound catalog and 12 direct Pokedex EOB scene references, but not a general name-to-Radium-object map.
|
|
- Assign semantics to the non-sound section 5 opcodes now summarized in `analysis/radium-image/command_opcode_payload_summary.tsv`, `analysis/radium-spike-menu-image/command_opcode_payload_summary.tsv`, `analysis/radium-image/opcode_handler_table.tsv`, and `analysis/radium-spike-menu-image/opcode_handler_table.tsv`. The current generic decode confirms clean `0x00`-terminated streams, observed opcodes, fixed payload sizes, common payload values, native handler-address table entries, and that opcode `0x0b` is the sound-reference command, but most non-`0x0b` opcode names still need confirmation from runtime consumers.
|
|
- Validate the unreleased/deep-feature candidates from `game-asset-spoilers-unreleased.md`: Team Rocket Multiball 3, Pikachu vs. Lucario / Story Wizard 2, Pikachu vs. Magikarp, Eevee Evolution Combos, and Cave/Mountain Top backgrounds. The current evidence is static strings, extracted assets, and candidate sound labels; reachability still needs code-path or runtime confirmation.
|
|
|
|
## Priority 3: `conagent`
|
|
|
|
Status: first-pass reverse engineering complete in `conagent-re.md`; non-compilable C-like flow export is in `conagent-pseudocode.c`; host-side backend/machine emulator added under `analysis/conagent-machine-emulator/` and documented in `conagent-machine-emulator.md`.
|
|
|
|
Target:
|
|
|
|
- `/games/pokemon_pro/conagent`
|
|
|
|
Why:
|
|
|
|
- It is separately supervised and restarted forever.
|
|
- Name and `/connectivity` paths suggest Stern Insider Connected or connectivity agent behavior.
|
|
|
|
Suggested first passes:
|
|
|
|
- Strings and URL/domain extraction.
|
|
- Network syscall/import review.
|
|
- Trace references to `/connectivity/cache`, `/connectivity/files`, `/connectivity/update`, and hostname handling.
|
|
|
|
Follow-up passes:
|
|
|
|
- Force Ghidra function creation for the stripped text region and rerun decompilation.
|
|
- Audit `ifup`/`ifdown` command construction and interface-name validation.
|
|
- Audit direct Game-to-Server endpoint validation.
|
|
- Audit file-transfer local path validation and update handoff.
|
|
- Recover enough of the `/usr/local/spike/agent.uds` framed protocol to add a local game-process emulator mode.
|
|
|
|
## Priority 4: Netbridge Debug Path
|
|
|
|
Status: first-pass strings, ELF program-header review, targeted Ghidra decompilation, host protocol recovery, a Python host-side emulator scaffold, Docker/QEMU optional serial wiring, and a Pico SDK firmware recreation are complete; see `package-image-firmware.md`, `netbridge-re.md`, and `docker-qemu-emulation.md`.
|
|
|
|
Targets:
|
|
|
|
- `/games/pokemon_pro/spike3/netbridge/netbridge.elf`
|
|
- `/games/pokemon_pro/spike3/netbridge/spike3-swd.cfg`
|
|
- `/games/pokemon_pro/spike3/netbridge/rp2040.cfg`
|
|
|
|
Why:
|
|
|
|
- `netbridge.elf` is not stripped and has debug info.
|
|
- OpenOCD config maps SWD onto Raspberry Pi GPIOs 10 and 11.
|
|
- This may be the clearest path to understanding lower-level board communication and programming/debug pathways.
|
|
|
|
Findings:
|
|
|
|
- `netbridge.elf` is a 32-bit ARM static executable with code mapped at `0x10000000` and RAM at `0x20000000`/`0x20040000`.
|
|
- Strings include `uart_node.c`, `NODEBUS_Poll`, `NODEUART_Write`, `UART_NodeRxIrq`, and `WS2812_NodeSetLED`.
|
|
- Ghidra decompilation identifies the Pi-facing host UART as 2,000,000 baud STX/ETX/ESC framed messages on RP2040 GPIO 16/17, with `0x30` returning firmware CRC `0x357f5327` and `0x41` carrying direct nodebus requests.
|
|
- `analysis/netbridge-emulator/netbridge_emu.py` implements the recovered host frame codec, core bridge commands, CRC response, PTY serving mode, and a stub node at address `0x0a`.
|
|
- `analysis/netbridge-pico-firmware/` implements the same recovered protocol as a Pico SDK firmware recreation with a portable host-core test.
|
|
- Docker/QEMU now has an optional `SPIKE3_NETBRIDGE_EMU=1` path that starts the Python emulator on `emulation/work/netbridge.sock`, attaches it as a second PL011 serial, maps guest `/dev/ttyAMA5` to the real serial, and lets the preload shim pass that path through.
|
|
|
|
Follow-up passes:
|
|
|
|
- Run the full Docker path with `SPIKE3_NETBRIDGE_EMU=1` and verify whether the game bridge thread accepts the emulated `/dev/ttyAMA5` device.
|
|
- Decide whether the OpenOCD programming path should be allowed, replaced with a success stub, or bypassed once CRC command `0x30` is reachable.
|
|
- Build a Pico UF2 after configuring `PICO_SDK_PATH`, then bench-test it against a host serial harness before connecting it to target hardware.
|
|
- Validate nodebus timing, break behavior, voltage level, and connector routing on live hardware or a logic-analyzer capture.
|
|
- Expand the node model beyond the Magikarp/topper-oriented commands once the game requests additional playfield nodes.
|
|
|
|
## Priority 5: Node Firmware
|
|
|
|
Status: first-pass Intel HEX range parsing complete for top-level node firmware; see `package-image-firmware.md`.
|
|
|
|
Targets:
|
|
|
|
- All `*-LPC*.hex` files under `/games/pokemon_pro`.
|
|
- `/games/pokemon_pro/spike3/powerdist/powerdist_ext.hex`.
|
|
|
|
Why:
|
|
|
|
- These likely define behavior for distributed playfield nodes: coils, LEDs, LCD, magnet sensors, HDMI, TMC drivers, power distribution.
|
|
- Firmware names expose node families and MCU types.
|
|
|
|
Suggested first passes:
|
|
|
|
- Parse Intel HEX metadata and address ranges. Done for 17 top-level HEX files in `analysis/static-triage/node-firmware-ranges.md`.
|
|
- Group by MCU family. Initial grouping by filename identifies LPC1112, LPC1113, LPC1124, LPC1313, and LPC812 families.
|
|
- Disassemble with the correct Cortex-M profile per chip.
|
|
- Correlate firmware names with harnesses, playfield devices, and game binary strings.
|
|
|
|
## Priority 6: Update Format
|
|
|
|
Status: first-pass `.sidx` strings/header review complete; see `package-image-firmware.md`.
|
|
|
|
Targets:
|
|
|
|
- `/games/spk/index/pokemon_pro-0_83_0.sidx`
|
|
- Any available `.spk` update packages outside this rootfs.
|
|
|
|
Why:
|
|
|
|
- `/etc/init.d/update` and `update_monitor` make `.spk` the software update format.
|
|
- The index file may describe package contents, hashes, versions, or install paths.
|
|
|
|
Suggested first passes:
|
|
|
|
- Inspect `.sidx` with `file`, strings, hexdump, and structured parsers. Done with `file`, `xxd`, and `strings`; 686 package paths were identified.
|
|
- Compare with any `.spk` available from machine update media or connectivity cache.
|