# 1. R-Type integer register-register instruction

Related reference articles:

# RISC-V teaching plan

The above RISC-V instruction set explanation (3) I-Type shift instruction and U-type instruction have introduced the integer register-immediate instruction, and this article begins to explain the integer register-register instruction.

RV32I defines several arithmetic R-type operations. All operations read the rs1 and rs2 registers as source operands and write the result to register rd, note that R-type instructions have no immediate data, only registers rs1, rs2 and rd.

The funct7 and funct3 fields select the operation type, as shown in Figure 1.

R-type has a total of 10 instructions, the opcode name is OP, and the value is 011_0011 (all R-type instructions have the same opcode).

Figure 1 Integer register-register instruction machine coding format[1]

## 1.1. ADD

The ADD instruction is similar to the RISC-V instruction set explanation (2) The operation principle of the ADDI instruction mentioned in the I-Type integer register-immediate instruction is similar. The only difference is that the position of the 12-bit immediate value is split into 7-bit funct7 and 5 bits of rs2.

The ADD instruction format is **ADD rd, rs1, rs2. **x[rd] = x[rs1] + x[rs2]

As shown in Figure 2, the funct7 of the ADD instruction is 000_0000, and the funct3 is 000 . This instruction is to write the result of rs1 + rs2 into rd. Note: Instead of adding bits 15-19 and 20-24 of the machine code position, the values of the registers corresponding to the index numbers are added.

Similar to ADDI, the overflow part is ignored (overflow processing can be implemented by software, here is how to handle it), and only the low XLEN bit is written to rd.

An example of addition overflow is adding two 8-bit signed binary numbers, 0100_0000(64) + 0111_0000(112) = 1011_0000(-80), the result is obviously wrong.

Command example:

**ADD x14, x12, x13**

Add the numbers in the x12 and x13 registers and place the result in the x14 register.

OP-IMM is 011_0011

funct3 is 000

funct7 is 7’b000_0000

rs2 is 5’b0_1101

rs1 is 5’b0_1100

rd is 5’b0_1110

So the machine code corresponding to **ADD x14, x12, x13** is 0000000_01101_01100_000_01110_0110011, and the corresponding hexadecimal is 32’h00d6_0733

Figure 2 ADD machine encoding format [2]

## 1.2. SLT

Also, SLT is similar to SLTI, the SLT instruction format is SLT rd, rs1, rs2 . x[rd] = x[rs1] < x[rs2]

As shown in Figure 3, the funct7 of the SLT instruction is 000_0000 , and the funct3 is 010 . rs1 and rs2 are compared as **signed numbers , if rs1 < rs2, rd is set to 1, otherwise it is set to 0.**

Command example:

**SLT x14, x12, x13**

Compare the numbers in the x12 and x13 registers as **signed numbers** . If the number in the x12 register is less than the number in the x13 register, the number in the x14 register is set to 1, otherwise it is set to 0.

Figure 3 SLT machine encoding format [2]

## 1.3. SLTU

The instruction format of SLTU is SLTU rd, rs1, rs2 . x[rd] = x[rs1] < x[rs2]

As shown in Figure 4, the funct7 of the SLTU instruction is 000_0000 , and the funct3 is 011 . **Unsigned compares** rs1 and rs2, if rs1 < rs2, rd is set to 1, otherwise it is set to 0.

Note that in SLTU rd, x0, rs2, if rs2 is not equal to 0, then rd is set to 1, otherwise, rd is set to 0. The corresponding pseudo-instruction is **SNEZ rd, rs2**

Command example:

**SLTU x14, x12, x13**

Compare the numbers in the x12 and x13 registers as **unsigned numbers** . If the number in the x12 register is less than the number in the x13 register, the x14 register is set to 1, otherwise it is set to 0.

Figure 4 SLTU machine encoding format [2]

## 1.4. AND

The instruction format of AND is AND rd, rs1, rs2 . x[rd] = x[rs1] & x[rs2]

As shown in Figure 5, the funct7 of the AND instruction instruction is 000_0000 , and the funct3 is 111 . This instruction writes the result of rs1 & rs2 into rd, and “&” means that rs1 and rs2 are ANDed bit by bit.

Command example:

**AND x14, x12, x13**

Write the result of the bitwise AND of the numbers in the x12 and x13 registers to the x14 register.

Figure 5 AND machine encoding format [2]

## 1.5. OR

The instruction format of OR is OR rd, rs1, rs2 . x[rd] = x[rs1] | x[rs2]

As shown in Figure 6, the funct7 of the OR instruction is 000_0000 , and the funct3 is 110 . This instruction writes the result of rs1 | rs2 into rd, and “|” means the bitwise OR of rs1 and rs2.

Command example:

**OR x14, x12, x13**

Writes the result of the bitwise OR of the numbers in the x12 and x13 registers to the x14 register.

Figure 6 OR machine encoding format [2]

## 1.6. XOR

The instruction format of XOR is XOR rd, rs1, rs2 . x[rd] = x[rs1] ^ x[rs2]

As shown in Figure 7, the funct7 of the XOR instruction is 000_0000 , and the funct3 is 100 . This instruction writes the result of the bitwise XOR of rs1 to rs2 into rd.

Command example:

**XOR x14, x12, x13**

Write the result of the bitwise XOR of the numbers in the x12 and x13 registers into the x14 register.

Figure 7 XOR machine encoding format [2]

## 1.7. SLL

The instruction format of SLL (shift left logical, logical left shift) is SLL rd, rs1, rs2 . x[rd] = x[rs1] ≪ x[rs2]

As shown in Figure 8, the funct7 of the SLL instruction is 000_0000 , and the funct3 is 001 . This instruction shifts rs1 to the left by rs2 (the value in this register), fills the vacant position with 0, and writes the result to the rd register. The lower 5 bits in the rs2 register are the effective shift bits (up to 2^5 – 1 = 31 bits), and the upper bits are ignored.

Command example:

**SLL x14, x12, x13**

Shift x12 to the left. The number of bits shifted to the left is determined by the lower 5 bits of the number stored in the x13 register (the upper bits are ignored), the vacated position is filled with 0, and the result is written into the x14 register.

Figure 8 SLL machine encoding format [2]

## 1.8. SRL

The instruction format of SRL (shift right logical, logical right shift) is SRL rd, rs1, rs2 . x[rd] = x[rs1] ≫ x[rs2]

As shown in Figure 9, the funct7 of the SRL instruction is 000_0000 and the funct3 is 101 . This instruction shifts rs1 to the right by rs2 (the value in this register), fills the vacant position with 0, and writes the result to the rd register. The lower 5 bits in the rs2 register are the effective shift bits (up to 2^5 – 1 = 31 bits), and the upper bits are ignored.

Command example:

**SRL x14, x12, x13**

Shift x12 to the right, and the number of bits shifted to the right is determined by the lower 5 bits of the number stored in the x13 register (the upper bits are ignored), fill the vacant position with 0, and write the result to the x14 register.

Figure 9 SRL machine encoding format [2]

## 1.9. SRA

The instruction format of SRA (shift right arithmetic, arithmetic right shift) is SRA rd, rs1, rs2 . x[rd] = x[rs1] ≫ x[rs2]

As shown in Figure 10, the funct7 of the SRA instruction is 010_0000 and the funct3 is 101 . This instruction shifts rs1 to the right by rs2 (the value in this register) bits, and the vacated position is filled with the **highest bit (rs1[31])** in the value of the rs1 register, and the result is written to the rd register. The lower 5 bits in the rs2 register are the effective shift bits (up to 2^5 – 1 = 31 bits), and the upper bits are ignored.

Command example:

**SRA x14, x12, x13**

Shift x12 to the right, the number of bits shifted to the right is determined by the lower 5 bits of the number stored in the x13 register (the higher bits are ignored), and the vacated position is filled **with the highest bit (sign bit) of the number stored in the rs1 register** , and the result is written. into the x14 register.

Figure 10 SRA machine encoding format [2]

**Note: In the above three move instructions, the value of the rs1 register is only copied, and the original value remains unchanged.**

## 1.10. SUB

The instruction format of SUB is SUB rd, rs1, rs2 . x[rd] = x[rs1] − x[rs2]

As shown in Figure 11, the funct7 of the SUB instruction is 010_0000 , and the funct3 is 000 . This instruction subtracts the value in the rs2 register from the value in the rs1 register and ignores arithmetic overflows.

Command example:

**SUB x14, x12, x13**

Subtract the number stored in the x12 register from the number stored in the x13 register, and write the result to the x14 register (ignoring arithmetic overflow).

Figure 11 SUB machine encoding format [2]

# 2. Article reference

[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.