Turn a byte address into a register index, and reject every address that is not exactly one of the four registers.
Hardware context: Memory-mapped control/status register bank. Convert an aligned bus address into the correct control-register index.
A timer test reported a DUT bug, but the DUT was right. The testbench model computed the register index by subtracting the base and shifting, so it rounded the misaligned address 0x40001001 down to register 0 and predicted a normal write.
This peripheral has four 32-bit registers at 0x40001000, 0x40001004, 0x40001008 and 0x4000100C. Write register_index(address), which returns 0, 1, 2 or 3 for those four addresses and -1 for every other address.
The whole 32-bit address counts. 0x40001003 is inside the block but is not the start of a register, so it returns -1. So does 0x50001004, which has the right low bits in the wrong page, and 0x40001010, the first byte past the block.
Signals in the timeline
| Signal | Width | Role |
|---|---|---|
address | 32 | input of each check |
Full specification
function automatic int register_index(input logic [31:0] address);
| address | returns |
|---|---|
| 0x40001000 | 0 |
| 0x40001004 | 1 |
| 0x40001008 | 2 |
| 0x4000100C | 3 |
| anything else | -1 |
Addresses are known 32-bit byte addresses. A register address is in the range [0x40001000, 0x40001010) and is a multiple of 4.
Examples
Example 1
The third register- Input
address = 0x40001008
- Output
index = 2
0x40001008 is inside the block and a multiple of 4: (0x8) / 4 = 2.
Example 2
Inside the block, but not a register- Input
address = 0x40001003
- Output
index = -1
The low two bits are 11, so this is not the start of a register. Rounding down to 0 would be wrong.
Example 3
The first byte past the block- Input
address = 0x40001010
- Output
index = -1
The block ends just before 0x40001010, so there is no register 4.
Constraints and contract
- address is a known 32-bit unsigned value.
- Return -1 for every address that is not one of the four register addresses.
- Keep the function name and signature.
Hints
Hint 1
Write the rule as two checks: is the address inside the block, and is it a multiple of 4? Only then compute an index.
Hint 2
Which bits of the address show that it is not a multiple of 4? What happens to them if you shift first?
Hint 3
Compare the full 32-bit address against both ends of the block, using a half-open range, before you subtract the base.
What this judge verifies: Your decoder is called on every byte address around the block, on the same offsets in other pages and on single-bit address flips. Passing shows only the four register addresses decode.
185 checks on Icarus Verilog · browser. Run the examples first, then check the full regression. The suite is local and inspectable. A passing result establishes the tested cases, not a proof for all possible inputs.
See all 6 steps and the final capstone