# Fuse / debug-unlock reachability, round 1: method established, result under-powered Following `LEAD-SYSDRV-FUSE-DEBUG-DMA-SURFACE.md`, which found `fuse_program_bits`, `debug_unlock_apply` and friends in our own symbol map with **no mention anywhere in the project**. The question is how they are dispatched and whether anything host- or TA-reachable gets to them. ## Static pointer-table scan — useless, and its control said so Scanned the SYS_DRV image for each target address as a 32-bit word (with and without the Thumb bit), expecting dispatch tables. **Method control: 0 of 40 randomly sampled known functions appear as a 32-bit word anywhere in the image.** So SYS_DRV does not hold absolute pointer tables in the static image — dispatch is via `tbb`/`tbh` switch tables, the same shape already documented for HDCP. The scan could not have found anything, and the control is what established that rather than the empty result. ## Dynamic sweep — controls good, coverage bad Swept 4352 opcodes (0x0000-0x00FF and 0x1000-0x1FFF) through the real entry `sub_E087E4` in `sysdrv_env`, with execution hooks on 19 fuse/debug/flash functions. Controls all fire, so the path and the hooks work: | control | hits | | --- | --- | | entry `sub_E087E4` | 4352 | | high dispatcher `sub_E105A8` | 4096 | | allowlist `sub_E0AB44` | 4443 | | crypto dispatcher `sub_E1DC30` | 256 | Targets: **none of the 19 reached.** ## Why that negative does not mean "unreachable" Two of the 19 are `spirom_write_checked` and `rom_parse_directory` — known, real SYS_DRV functionality that this project has studied in depth. They were not reached either. Total coverage was **666 SYS_DRV blocks**, and it stopped growing after the first ~2000 opcodes. So the sweep dispatches every opcode but the handlers bail early — almost certainly on argument validation or uninitialised state, exactly the class of gap that blocked RAS at `0xE575B8`. The experiment cannot distinguish "not reachable" from "my requests are too poorly formed to get past the front door", and the flash controls prove it is the latter. **This result bounds nothing about the fuse/debug surface.** It establishes the method and shows the current request construction is too weak. ## What round 2 needs Per-opcode valid arguments, not one generic request. The tree already knows how to do this for a few opcodes (`sysdrv_bridge.py` drives 0x0001/0x0002/0x000d/ 0x1077 with RAS-supplied arguments and gets three to succeed). The useful target is coverage: drive handlers deep enough that `spirom_write_checked` becomes reachable, and only then is a negative on `fuse_program_bits` meaningful. An alternative that avoids the argument problem entirely: run the sweep inside `full_system.py`, where SYS_DRV has real state and real callers, and hook the targets there over a long boot. That measures what actually executes rather than what a synthetic request can reach. ## Artifacts `psp_out/fuse_reach.py`. --- # Round 2: measure what actually executes in a real boot Hooking the targets inside `full_system.py`, where SYS_DRV has real state and real callers, instead of trying to synthesise valid requests. ## First reading was wrong The entry-point hook reported `fuse_program_bits` executing once, which looked like a headline result. It is not. The call context showed `LR = 0xE0BE7D` — pointing *into the function itself*, not at a caller — and **zero blocks executed inside its 464-byte body**, with the next block being `0x8`, an exception vector. An entry address being touched is not the function running. Re-measured at **body level**: count blocks executed *within* each function's range across a whole boot, with two known functions as controls. | function | hits | distinct blocks | | | --- | --- | --- | --- | | `heap2_zero_block` | 156 | 4 | **CONTROL — measurement works** | | `bn_from_bytes_be` | 0 | 0 | control, crypto-only path | | **`dma_transfer`** | **17** | **16** | **genuinely executes** | | `fuse_program_bits` | 2 | 1 | one block only — prologue/guard, not its logic | | `spirom_read_checked` | 1 | 1 | one block only | | `fuse_write_field` | 0 | 0 | | | `debug_unlock_apply` | 0 | 0 | | | `secure_boot_state` | 0 | 0 | | | `fuse_read_flag` / `fuse_read_config` / `fuse_read_pair` | 0 | 0 | | | `rom_parse_directory` / `spirom_read_header` | 0 | 0 | | ## What this establishes * **`dma_transfer` is live.** 16 distinct blocks across a normal boot — a PSP DMA engine that actually runs and that the emulator does not model. That is the most substantive item here and it was not previously known to execute. * **The fuse-write and debug-unlock paths do not execute during a normal boot.** `fuse_program_bits` reaching exactly one block twice is a guard or prologue returning immediately, not its logic; `fuse_write_field`, `debug_unlock_apply` and `secure_boot_state` are never entered at all. ## What it does not establish Not executing during boot says nothing about whether they can be *driven* by a host or TA request. Round 1 showed the synthetic-request sweep is too weak to test that, and round 2 measures a different thing: normal-path execution. The reachability question stays open. The honest summary of both rounds: the dispatch mechanism is `tbb`/`tbh` switch tables (no pointer tables to scan), these functions are not on the boot path except `dma_transfer`, and testing request-driven reachability still needs per-opcode valid arguments with `spirom_write_checked` as the coverage gate.