RISC-V常见指令详解-计组
注意:由于I型指令中仅有rs1,没有rs2,所以该类型指令的第二个操作数一定是立即数,第一个操作数一定是用寄存器地址表示。把寄存器rs1的值存入地址为寄存器rs2的值加offset的主存中,其中offset = imm,imm是12位补码。从地址为寄存器rs1的值加offset的主存中读一个双字,注意算式 (rs1+offset) 的寻址单位是。其中offset = imm,imm是12位补码。注
常见指令类型
R型指令
一、指令格式
funct7(7 bit) | rs2(5 bit) | rs1(5 bit) | funct3(3 bit) | rd(5 bit) | opcode(7 bit) |
---|
其中:
- rs1(5 bit):存储第一个操作数所在的寄存器号
- rs2(5 bit):存储第二个操作数所在的寄存器号
- rd(5 bit): 存储结果数所在的寄存器号
二、示例
Example One:
add x7, x8, x9
funct7(7 bit) | rs2(5 bit) | rs1(5 bit) | funct3(3 bit) | rd(5 bit) | opcode(7 bit) |
---|---|---|---|---|---|
******* | 01001(9) | 01000(8) | *** | 00111(7) | ******* |
I型指令
一、指令格式
imm(12 bit) | rs1(5 bit) | funct3(3 bit) | rd(5 bit) | opcode(7 bit) |
---|
其中:
- rs1(5 bit):存储第一个操作数所在的寄存器号
- imm(12 bit):是一个12位的立即数字段,用于提供操作数的立即数值。这个立即数可以被有符号扩展到32位,并与寄存器rs1的内容进行运算。
- rd(5 bit): 存储结果数所在的寄存器号
注意:由于I型指令中仅有rs1,没有rs2,所以该类型指令的第二个操作数一定是立即数,第一个操作数一定是用寄存器地址表示
二、示例
Example One:
addi x7, x8, 20
imm(12 bit) | rs1(5 bit) | funct3(3 bit) | rd(5 bit) | opcode(7 bit) |
---|---|---|---|---|
10100(20) | 01000(8) | *** | 00111(7) | ******* |
Example Two:
ld x7, 30(x8)
imm(12 bit) | rs1(5 bit) | funct3(3 bit) | rd(5 bit) | opcode(7 bit) |
---|---|---|---|---|
0000 0001 1110(30) | 01000(8) | *** | 00111(7) | ******* |
S型指令
一、指令格式
imm[11:5](7 bit) | rs2(5 bit) | rs1(5 bit) | funct3(3 bit) | imm[4:0](5 bit) | opcode(7 bit) |
---|
其中:
- rs1(5 bit):存储基址寄存器号
- rs2(5 bit):存储将要被保存在内存中的数据的寄存器号
- imm(12 bit):存储偏移量
二、示例
Example One:
sd x10, 16(x5)
imm[11:5](7 bit) | rs2(5 bit) | rs1(5 bit) | funct3(3 bit) | imm[4:0](5 bit) | opcode(7 bit) |
---|---|---|---|---|---|
0000 000 | 01010(10) | 00101(5) | *** | 1 0000 | ******* |
SB型指令
一、指令格式
imm[12] | imm[10:5] | rs2 | rs1 | funct3 | imm[4:1] | imm[11] | opcode |
---|
其中:
- immediate(12 bit):表示分支目标相对于当前指令地址的偏移量。
- rs1(5 bit):存储用于比较的数值的寄存器号
- rs2(5 bit):存储用于比较的数值的寄存器号
二、示例
Example One:
bne x9, x10, 100
imm[12] | imm[10:5] | rs2 | rs1 | funct3 | imm[4:1] | imm[11] | opcode |
---|---|---|---|---|---|---|---|
0 | 001 100 | 01010(10) | 01001(9) | *** | 0 010 | 0 | ******* |
U型指令
一、指令格式
imm[31:12] | rd(5 bit) | opcode(7 bit) |
---|
其中:
- imm[31:12]:20 位的立即数字段,表示要加载到目标寄存器的高位立即数。
- rd:目标寄存器,用于存储加载的立即数。
- U型指令中常见的仅有lui指令和auipc指令
二、示例
lui x1, 0x00001
imm[31:12] | rd(5 bit) | opcode(7 bit) |
---|---|---|
0000 0000 0000 0000 0001 | 00001 | ******* |
UJ型指令
一、指令格式
offset(20 bit) | rd | opcode |
---|---|---|
offset[20] offset[10:1] offset[11] offset[19:12] | rd | 110111 |
注意仅有jal指令属于UJ型指令,且UJ型跳转指令的立即数同样需要进行一位移位操作,以半字为单位进行指令寻址
二、示例
Example One:
jal x1, 20
opcode | rd | offset(20 bit) |
---|---|---|
110111 | 0 0001 | 0000 0000 0000 0001 0100(20) |
常见指令释义
- add(R-type)
add rd, rs1, rs2
reg[rd] = reg[rs1] + reg[rs2]
2. ld(I-type)
ld rd, offset(rs1)
reg[rd] = mem[reg[rs1] + offset]
从地址为寄存器rs1的值加offset的主存中读一个双字,注意算式 (rs1+offset) 的寻址单位是字节。其中offset = imm,imm是12位补码。
3. sd(S-type)
sd rs1, offset(rs2)
mem[reg[rs2] + offset] = reg[rs1]
把寄存器rs1的值存入地址为寄存器rs2的值加offset的主存中,其中offset = imm,imm是12位补码。
4. beq(SB-type)
beq rs1, rs2, offset
if (reg[rs1] == reg[rs2])
PC = PC + offset*2;
else
PC = PC + 4;
注意offset是13位有符号数,用补码形式存储
5. jal(J-type)
jal rd offset
reg[rd] = PC + 4;
PC = PC + offset*2;
注意offset是20位有符号数,用补码形式存储
6. jalr(I-type)
jalr rd, rs1, offset
int temp = (reg[rs1] + offset) & ~1;
reg[rd] = PC + 4;
PC = temp;
寄存器 rs1 和符号扩展的立即偏移量之和将作为跳转指令的地址
注意因为jalr是I型指令,所以不会将立即数偏移量左移一位。
而寄存器rd中将会保存当前PC地址加4(当前指令的下一条指令的地址)
其中offset是12位有符号数
更多推荐
所有评论(0)