Bring-up software reads a peripheral before its clock is enabled, or a linker script places a table one bank too high, and the fabric answers with a code. If the team cannot read that code, the debug starts with a guess instead of a location: DECERR means nobody claimed the address, SLVERR means somebody refused it, and PSLVERR means the refusal happened on the APB side. On NanoSoC each code points at a different block, so the response is the first half of the diagnosis.
DECERR, binary 2'b11 on the AXI response signals, means decode error: no slave was selected and the interconnect default slave answered, with its first beat one clock after the address handshake. It arrives from holes H1, H2 and H4, where no first-level select fires. SLVERR, 2'b10, means slave error: a slave was selected but refused the access. On NanoSoC it arrives from four places: the secure-fault responder refusing a non-secure access to secure-only SRAM1 at the first level, the per-slot secure check refusing a non-secure access to the reset-controller slot behind the bridge, hole H3 inside the APB window, and unmapped register offsets inside any slot. PSLVERR is the APB form of the same refusal, raised by the slot decoder's default slave or by a block like the DMA for an unmapped offset, and the bridge converts it into AXI SLVERR; software on the AXI side always sees SLVERR, while the distinction matters to whoever debugs the bridge.
Address | First level | Second level | Response seen by software |
|---|---|---|---|
0x0000_0000 (ROM) | Selects ROM | n/a | Data, cacheable in the I-cache. |
0x0000_4000 (H1) | No select, interconnect default | n/a | DECERR. |
0x2000_0004 (SRAM0) | Selects SRAM0 | n/a | Data. |
0x2001_0000 secure (SRAM1) | Selects SRAM1 | n/a | Data, never cached. |
0x2001_0000 non-secure | sel_fault: secure-fault responder | n/a | SLVERR, no data. |
0x4000_0004 (DMA STATUS) | Selects APB, slot 0 | Mapped offset | Data. |
0x4000_0014 (DMA gap) | Selects APB, slot 0 | Unmapped offset | SLVERR via PSLVERR. |
0x4000_0104 (alias image) | Selects APB, slot 0 | Mapped offset in the second image | Data: the alias answers normally. |
0x4000_7000 (H3) | Selects APB, slot 7 | Slot default slave | SLVERR via PSLVERR. |
0x4000_6000 non-secure (RSTPWR) | Selects APB, slot 6 | Secure-only slot refuses | SLVERR via PSLVERR. |
0x5000_0000 (H4) | No select, interconnect default | n/a | DECERR. |
Two rows deserve a second look. The alias read at 0x4000_0104 returns data, not an error: the responder cannot tell which image was intended, which is why aliases are a policy problem rather than a hardware error. And the two secure refusals return SLVERR rather than DECERR on purpose. The reason is semantic: DECERR means no slave decoded the address, SLVERR means a slave or its filter refused it, so DECERR for SRAM1 would misreport an existing region as absent and send debugging to the wrong decode level. Mapped and forbidden therefore means SLVERR on NanoSoC, answered by the fault responder at the interconnect or by PSLVERR behind the bridge, with no data in either case. Hiding existence from a prober is a separate security-policy decision some designs make on top of this; it is not what the codes themselves mean.
Never probe. Mapped regions are accessed through the generated headers, and anything else is a bug in the image, not a discovery method. A DECERR on an instruction fetch means the linker script is wrong; halt and fix the image. A DECERR or SLVERR on data means the driver used a stale base or hit a secure region from the wrong state; log the faulting address and trap. The boot ROM follows the same discipline: it touches only mapped addresses, so any error response during boot points at the hardware or the map, never at a probing strategy.
The response table above, or its equivalent, is in the integration specification with the responder named per row.
The fault handler logs the faulting address and the response code, so field returns carry the diagnosis.
No production software reads an address to learn whether it exists; existence comes from the map version.
In the test environment, with a timeout on every access, run the sweep from the holes lesson: one access per row of the table, confirming each answer. Pay special attention to the two secure rows, tested from both security states, and to the boundary rows 0x0000_3FFF versus 0x0000_4000 and 0x4000_6FFF versus 0x4000_7000. If a row answers differently, read the next lesson before touching anything: the responder is either the default slave, which has its own design rules, or a decoder bug, which has its own method.
First level selects APB since addr[31:16] is 0x4000. Second level finds slot 7 unmapped, so the APB default slave raises PSLVERR and the bridge presents SLVERR. Reserved slot, correct error, software must not be there.