Menu Close

Unconditional Jumps and Conditional Branches

1. Control transfer instruction

 

Related reference articles:

RISC-V teaching plan

 

There are two main types of control transfer instructions in RV32I: unconditional jumps and conditional jumps.

 

2. Unconditional jump

Unconditional jump instructions use PC-relative addressing. Unconditional jump mainly includes two instructions: JAL and JALR.

 

2.1 JAL

JAL instructions are in J-type format (JAL is the only J-type instruction in RV32I).

The instruction format of JAL is JAL rd, offset . x[rd] = pc+4; pc += sext(offset)

Its machine code format is shown in Figure 1. Its opcode is 110_1111. This instruction stores the address of the next instruction (PC + 4) in the rd register and then sets PC to the current value plus the sign-extended offset.

JAL machine codeFigure 1 JAL machine encoding format [1]

Note that the offset is sign extended. It can be seen that the offset is 2-byte aligned (offset [20:1]), although all instruction addresses in RV32I are 4-byte aligned, but JAL may also be used for compatibility with the C extended instruction set (details See RISC-V Introduction (4) RISC-V instruction set coding structure for its description), so the default offset bit 0 is 0 (ie, 2-byte alignment).

Therefore, the address to which the JAL jumps has a range of +/- 1MB. (2^21 = 2MB = +/- 1MB).

The standard software calling convention (calling convention) uses x1 register as return address register (rd), also can use x5 as alternate link register (link register). Because the offset in the JAL instruction is an offset relative to the PC, an accurate address difference is required when writing, and an assembly instruction is added/deleted arbitrarily, the offset in the JAL may need to be modified again, which gives the JAL instruction The use of JAL brings a lot of burden, so generally when using JAL instructions, use JAL rd, label instead of JAL rd, offset.

In JAL rd, the label in the label is a label, which is used to mark the location of a certain program, and provides a jump entry for jumping and branching statements in the program (the example of label usage can be clicked here ). The compiler will automatically calculate the label and the offset of the current instruction.

Example:

JAL x1, main 

Pseudo instruction: JAL main, corresponding real instruction: JAL x1, main

Pseudo instruction: J main, corresponding real instruction: JAL x0, main

Jump to the main function and store the next instruction in the x1 register

Notice:

  1. The x5 register was chosen as the alternate link register for two reasons:
    1. is used as a temporary variable in the standard calling convention
    2. It is only 1 bit different from the regular linker x1 0_0001 –> 0_0101
  2. When the JAL instruction omits rd, the default rd is x1.
  3. rd in pseudo-instruction J is x0.

JAL machine code

Figure 1 JAL machine encoding format [1]

 

2.2 JALR

The indirect jump instruction JALR uses the I-type encoding type. The instruction format is JALR rd, offset(rs1) .

t = pc + 4; pc = (x[rs1]+sext(offset)) & ~1 ; x[rd]=t is equivalent to:

t = pc + 4; pc = (x[rs1]+sext(offset)) & 0xffff_fffe ; x[rd]=t // RV32I

Its machine code is shown in Figure 2, its opcode is 110_0111 , and funct3 is 000 .

This instruction sets PC to the value in the rs1 register plus a sign-extended offset, sets the least significant bit of the calculated address to 0, and writes the original PC + 4 value to the rd register. If the destination register is not required, rd can be set to x0.

JALR’s offset is also sign-extended, and the address range of the JALR offset is +/- 2KB of the address stored in the rs1 register (2^12 = 4096 = 4 KB = +/- 2KB). The JALR instruction is defined so that two instruction sequences can jump anywhere within the 32-bit absolute address range (because the jump range of the JAL instruction is not large enough).

Example:

JALR x13, 0(x1)

Jump to the address stored in the x1 register and store the next instruction in the x13 register.

Examples of other pseudo-instructions:

JR x1 => JALR x0, x1, 0

RET => JALR x0, x1, 0

JALR x13 => JALR x1, x13, 0

Generally speaking, the combination of LUI and JALR can jump to the 32-bit absolute address range, and the combination of AUIPC and JALR can jump to the 32-bit address range relative to the PC.

JALR machine code

Figure 2 JALR machine encoding format [1]

 

3. Conditional branch jump

All branch instructions are in B-type encoding format, and the machine code is shown in Figure 3. A 12-bit immediate encodes a signed offset (offset[12:1]) in multiples of 2 bytes.

Although all instruction addresses in RV32I are 4-byte aligned, JAL may also be used to be compatible with the C extended instruction set, so the default offset bit 0 is 0 (ie, 2-byte alignment).

The target address consists of the address of the branch instruction plus a sign-extended offset in the range 2^13 = 8192 = 8 KB = +/- 4 KB.

Similar to JAL, the common usage of the Branch instruction can also replace the offset with a label, such as BEQ rs1, rs2, label .

branch machine code

Figure 3 branch instruction machine encoding format [1]

 

3.1 BEQ

BEQ (branch if equal, branch when equal), its instruction format is BEQ rs1, rs2, offset . if (rs1 == rs2) pc += sext(offset)

As shown in Figure 4, its opcode is 110_0011 and funct3 is 000 . This instruction is to judge whether the values ​​in the rs1 register and the rs2 register are equal. If they are equal, set the value of the PC to the current value plus the offset offset of the sign bit extension.

Example:

BEQ x12, x13, LOOP

Compare the values ​​in the x12 and x13 registers for equality , and if so , jump to LOOP(label).

BEQ machine code

Figure 4 BEQ machine encoding format [2]

 

3.2 BNE

BNE (branch if not equal, branch if not equal), its instruction format is BNE rs1, rs2, offset . if (rs1 ≠ rs2) pc += sext(offset)

As shown in Figure 5, its opcode is 110_0011 and funct3 is 001 . This instruction is to judge whether the values ​​in the rs1 register and the rs2 register are not equal. If they are not equal, set the value of the PC to the current value plus the offset offset of the sign bit extension.

Example:

BNE x12, x13, LOOP

Compare the values ​​in the x12 and x13 registers for equality, if not , jump to LOOP(label).

BNE machine code

Figure 5 BNE machine encoding format [2]

 

3.3 BLT

BLT (branch if less than, branch when less than), its instruction format is BLT rs1, rs2, offset . if (rs1 <s rs2) pc += sext(offset)

As shown in Figure 6, its opcode is 110_0011 and funct3 is 100. This instruction is to judge whether the value of the rs1 register is less than the value in the rs2 register (all regarded as a signed number), and if so, set the value of the PC to the current value plus the offset of the sign bit extension.

Example:

BLT x12, x13, LOOP

Signed compares the values ​​in the x12 and x13 registers, if the value in the x12 register is less than x13, jump to LOOP(label).

BLT machine code

Figure 6 BLT machine encoding format [2]

 

3.4 BLTU

BLTU (branch if less than, unsigned, branch if unsigned less than), its instruction format is BLTU rs1, rs2, offset . if (rs1 <u rs2) pc += sext(offset)

As shown in Figure 7, its opcode is 110_0011 and funct3 is 110. This instruction is to judge whether the value of the rs1 register is less than the value in the rs2 register (all regarded as unsigned numbers), if so, set the value of the PC to the current value plus the offset of the sign bit extension.

Example:

BLTU x12, x13, LOOP

Unsigned compares the values ​​in the x12 and x13 registers, if the value in the x12 register is less than x13, jump to LOOP(label).

BLTU machine code

Figure 7 BLTU machine encoding format [2]

 

3.5 BGE

BGE (branch if greater than or equal, branch if greater than or equal), its instruction format is BGE rs1, rs2, offset . if (rs1 ≥s rs2) pc += sext(offset)

As shown in Figure 8, its opcode is 110_0011 and funct3 is 101 . This instruction is to judge whether the value of the rs1 register is greater than or equal to the value in the rs2 register (all regarded as signed numbers), if so, set the value of the PC to the current value plus the offset of the sign bit extension.

Example:

BGE x12, x13, LOOP

Signed compares the values ​​in the x12 and x13 registers, if the value in the x12 register is greater than or equal to x13, jump to LOOP (label).

BGE machine code

Figure 8 BGE machine encoding format [2]

 

3.6 BGEU

BGEU (branch if greater than or equal, unsigned, branch if greater than or equal), its instruction format is BGEU rs1, rs2, offset . if (rs1 ≥u rs2) pc += sext(offset)

As shown in Figure 9, its opcode is 110_0011 and funct3 is 111. This instruction is to judge whether the value of the rs1 register is greater than or equal to the value in the rs2 register (all regarded as unsigned numbers), if so, set the value of the PC to the current value plus the offset of the sign bit extension.

Example:

BGEU x12, x13, LOOP

Unsigned compares the values ​​in the x12 and x13 registers, if the value in the x12 register is greater than or equal to x13, jump to LOOP (label).

BGEU machine code

Figure 9 BGEU machine encoding format [2]

 

4. Article references

[1] Riscv.org , 2021. [Online]. Available: https://riscv.org/wp-content/uploads/2019/12/riscv-spec-20191213.pdf. [Accessed: 22- Feb- 2021] .

[2] D. Patterson and A. Waterman,  The RISC-V reader. Berkeley: Strawberry Canyon LLC, 2018.

Posted in FPGA, RISC-V, RISC-V Textbook, Textbook and Training Project

Related Articles

Leave a Reply

Your email address will not be published.

Leave the field below empty!