Skip to content

Registers

The register file

  • There are 32 integer registers (x0x31).
    • Unlike ARM, which has 16 registers.
  • This means that each register needs a 5-bit identifier.
    • This is 4-bit for ARM.

Register file with rs1, rs2 and rd address inputs, WD write data, WE write enable, CLK, and RD1/RD2 read data outputs

The register file: three 5-bit address ports, one 32-bit write port, two 32-bit read ports.
  • There are also 32 floating-point extension registers if supporting floating point; as well as control and status registers (most not accessible in user mode).

Calling convention (ABI)

The description below is the typical use (part of the calling convention / ABI) for each register.

Register ABI Name Description Saver
x0 zero Zero constant
x1 ra Return address Caller
x2 sp Stack pointer Callee
x3 gp Global pointer
x4 tp Thread pointer
x5x7 t0t2 Temporaries Caller
x8 s0 / fp Saved / frame pointer Callee
x9 s1 Saved register Callee
x10x11 a0a1 Fn args/return values Caller
x12x17 a2a7 Fn args Caller
x18x27 s2s11 Saved registers Callee
x28x31 t3t6 Temporaries Caller

x0 and the PC

  • Register x0 is hardwired to 0. Writes to x0 are ignored.
    • Allows for easy comparison with 0.
    • The equivalent of MOV is implemented using addition with x0, etc.
  • PC is not a register readable/writable explicitly by any instruction, i.e. it is not a visible register.
    • Unlike ARM, where PC can be specified as an operand (R15).
  • Reading from PC can be done indirectly through auipc, jal, and branch instructions, which use PC itself as an operand.
    • And not PC+8 like in ARMv3 or PC+4 like in ARMv7M / Thumb2.
  • Writing PC is done only by branch/jump instructions.

Register reads and writes

One write port, two read ports

These two constraints shape a surprising amount of the rest of the ISA.

  • No instruction updates more than one visible register, and the register updated is explicitly specified in the rd field.
    • This is unlike ARM, where some instructions such as BL update a visible register (R14/LR) implicitly, i.e. without 14 explicitly specified in the instruction.
    • This ensures that the register file needs only one write port.
    • This has some implications such as not having pre/post-indexed addressing, multiply/division not giving 64-bit results, etc. (discussed later).
  • No instruction reads more than two registers. The register file needs only 2 read ports.
    • This implies that instructions such as MLA (multiply and accumulate) are not possible.

Flag registers

  • There is no flag register(s) — flags are generated and used in the same instruction and not memorized for future use.1
  • It was designed this way to minimize interaction between instructions.
  • Only branch instructions are conditional, based on the result of a comparison done by the instruction itself — CMP + BEQ of ARM is replaced by beq.
  • This also means the branch target computation cannot be done in the ALU, as the ALU does the comparison.

  1. If the result of a comparison is needed for future use other than branching, an instruction such as slt is used. It writes the result to a general-purpose register rather than to a dedicated flag register/flip-flop.