During my recent review of computer architecture, the jalr (Jump and Link Register) instruction in the RISC-V instruction set stood out due to its unique role in dynamic control flow. Unlike direct jumps, jalr enables indirect jumping, which is crucial for function returns, switch statements, and dynamic method dispatch.
1. The Instruction Format
The jalr instruction operates under the I-type format. Its syntax is typically written as:
jalr rd, offset(rs1)
Here, rs1 is the base register containing the target address, offset is a 12-bit signed immediate value, and rd is the destination register where the return address will be saved.
2. Hardware Implementation & Datapath
At the microarchitectural level, executing jalr involves several coordinated steps within the CPU datapath:
- Address Calculation: The ALU adds the value inside
rs1and the sign-extended 12-bitoffset. The least significant bit (LSB) of the result is set to 0 to ensure instruction alignment. - Link Operation: The address of the next sequential instruction (
PC + 4) is written into the destination registerrd. If no return address is needed (e.g., a simple indirect jump), the zero registerx0is used asrd. - PC Update: The calculated target address is finally fed into the Program Counter (PC) multiplexer to update the PC for the next clock cycle.
3. A Classic Use Case: Function Return
The most ubiquitous use of jalr is returning from a subroutine. In RISC-V assembly, the pseudo-instruction ret is actually translated to:
jalr x0, 0(x1)
This tells the processor to jump to the address stored in the return address register (x1 or ra) with an offset of 0, and discard the new link address by saving it to the hardwired zero register x0.
Understanding the hardware logic behind jalr not only clarified the mechanics of the instruction set but also highlighted the elegant simplicity of the RISC-V design philosophy.