RISC-V32I指令集
1.RV指令集分类
指令集分为基础指令集和扩展指令集;又根据处理器位数不同,分为32位、64位以及128位,其中32位指令集(RV32I)为了进一步支持嵌入式又制定嵌入式指令集(RV32E),将32个32位的通用寄存器砍掉一半,即只有16个32位的通用寄存器,其他保持不变;
指令集类型 | 指令集名称 | 指令集描述 |
---|---|---|
I | 基本整数集 | 包含整数的基本计算、Load/Store和控制流,所有的硬件实现都必须 包含这一部分。 |
C | 压缩指令扩展 | 将某些指令进行压缩,提高代码密度。 |
M | 整数乘除法扩展 | 增加了整数寄存器中的乘除法指令。 |
A | 原子操作扩展 | 增加对储存器的原子读、写、修改和处理器间的同步。 |
F | 单精度浮点扩展 | 增加了浮点寄存器、计算指令、L/S指令。 |
D | 双精度扩展 | 扩展双精度浮点寄存器,双精度计算指令、L/S指令 |
2.RV寄存器
RV32I型具有32个32-bit的通用寄存器,具体定义和功能如下:
3.RV32I指令类型
4.RV32I指令介绍
-- 符号扩展:--
(1)U-TYPE
-
LUI: 将20位立即数放32位的高位,低12位置0,将结果载入目标寄存器。
汇编写法:
lui rd, imm
-
AUIPC: 将20位立即数放32位的高位,低12位置0,加上PC的结果载入目标寄存器。
汇编写法:
auipc rd, imm
(2)J-TYPE
J型也只有两条指令,同U型一样,操作码不一致;
-
Jal:将其携带的20位立即数做符号扩展,并左移一位,产生32bit的有符号数,然后与PC值相加产生指令存储器的目标地址,跳转至PC±1MB的地址范围;同时将紧随其后的指令的地址存入目标寄存器。
问题:为什么左移一位?
-
jalr指令:将其携带的12位立即数与源寄存器1值相加,并将结果的末尾清零,作为跳转的地址;与jal指令一样,将其后的指令地址存入目标寄存器中;
-
汇编写法:
jalr rd, offset(rs1)
-
(3)B-TYPE
-
-
beq:源寄存器1、2值相等,跳转至目标地址;而目标地址由立即数符号扩展,并左移1位与PC值相加产生;
-
汇编写法:
beq rs1, rs2, imm
-
bne:源寄存器1、2值不相等,跳转至目标地址;而目标地址由立即数符号扩展,并左移1位与PC值相加产生;
-
汇编写法:
bne rs1, rs2, imm
-
blt:源寄存器1小于源寄存器2值,跳转至目标地址;而目标地址由立即数符号扩展,并左移1位与PC值相加产生;
-
汇编写法:
blt rs1, rs2, imm
-
bge:源寄存器1不小于源寄存器2值,跳转至目标地址;而目标地址由立即数符号扩展,并左移1位与PC值相加产生;
-
汇编写法:
bge rs1, rs2, imm
-
bltu:源寄存器1小于源寄存器2值,跳转至目标地址;而目标地址由立即数符号扩展,并左移1位与PC值相加产生;
-
汇编写法:
bltu rs1, rs2, imm
-
bgeu:源寄存器1不小于源寄存器2值,跳转至目标地址;而目标地址由立即数符号扩展,并左移1位与PC值相加产生;
-
汇编写法:
bgeu rs1, rs2, imm
(3)I-TYPE
I型主要分成两类功能:操作数据存储器、立即数运算;还有其他但这里先不讨论;先介绍操作数据存储器指令,即Load指令;
-
lb:立即数符号扩展后,与源寄存器1相加,作为读取数据的地址,读出该地址的1字节数据,经符号扩展写入到目标寄存器中;
-
汇编写法:
lb rd, offset(rs1)
-
lh:立即数符号扩展后,与源寄存器1相加,作为读取数据的地址,读出该地址的2字节数据,经符号扩展写入到目标寄存器中;
-
汇编写法:
lh rd, offset(rs1)
-
lw:立即数(12位)符号扩展后,与源寄存器1相加,作为读取数据的地址,读出该地址的4字节数据,经符号扩展写入到目标寄存器中;
-
汇编写法:
lw rd, offset(rs1)
-
lbu:立即数(12位)符号扩展后,与源寄存器1相加,作为读取数据的地址,读出该地址的1字节数据,经0扩展写入到目标寄存器中;
-
汇编写法:
lbu rd, offset(rs1)
-
lhu:立即数(12位)符号扩展后,与源寄存器1相加,作为读取数据的地址,读出该地址的2字节数据,经0扩展写入到目标寄存器中;
-
汇编写法:
lhu rd, offset(rs1)
接下来介绍立即数运算指令:
-
addi:立即数(12位)做符号扩展,与源寄存器1相加(忽略溢出),将结果存入目标寄存器;
-
汇编写法:
addi rd, rs1, imm
-
slti:立即数(12位)做符号扩展,与源寄存器1做比较:条件成立目标寄存器置1,否则置0;
-
汇编写法:
slti rd, rs1, imm
-
sltiu:立即数(12位)做符号扩展,与源寄存器1做比较:条件成立目标寄存器置1,否则置0;
-
汇编写法:
sltiu rd, rs1, imm
-
xori:立即数做符号扩展,与源寄存器1相异或,将结果存入目标寄存器;
-
汇编写法:
xori rd, rs1, imm
-
ori:立即数做符号扩展,与源寄存器1相或,将结果存入目标寄存器;
-
汇编写法:
ori rd, rs1, imm
-
ani:立即数做符号扩展,与源寄存器相与,将结果存入目标寄存器;
-
汇编写法:
ani rd, rs1, imm
-
slli:将源寄存器1值左移shamt位,空位填0,结果写入目标寄存器;shamt[5]为0有效;
-
汇编写法:
slli rd, rs1, shamt
-
srli :将源寄存器1值右移shamt位,空位填0,结果写入目标寄存器;shamt[5]为0有效;
-
汇编写法:
srli rd, rs1, shamt
-
srai:将源寄存器1值循环右移shamt位,结果写入目标寄存器;shamt[5]为0有效;
-
汇编写法:
srai rd, rs1, shamt
(5)S-TYPE
-
sb:立即数符号扩展后,与源寄存器1相加作为数据存储器的地址,将源寄存器2的最低字节存入;
-
汇编写法:
sb rs2, offset(rs1)
-
sh:立即数符号扩展后,与源寄存器1相加作为数据存储器的地址,将源寄存器2的最低2个字节存入;
-
汇编写法:
sh rs2, offset(rs1)
-
sw:立即数符号扩展后,与源寄存器1相加作为数据存储器的地址,将源寄存器2的整字存入;
-
汇编写法:
sw rs2, offset(rs1)
(6)R-TYPE
-
add:源寄存器1、2相加(忽略溢出),结果将被写入目标寄存器中;
-
汇编写法:
add rd, rs1, rs2
-
sub:源寄存器1 - 源寄存器2(忽略溢出),结果将被写入目标寄存器中;
-
汇编写法:
sub rd, rs1, rs2
-
sll:源寄存器1值左移源寄存器2[4:0]位,空位补0,结果写入目标寄存器;
-
汇编写法:
sll rd, rs1, rs2
-
slt:有符号比较源寄存器1、2值,源寄存器1小,目标寄存器写1,否则写0;
-
汇编写法:
slt rd, rs1, rs2
-
sltu:无符号比较源寄存器1、2值,源寄存器1小,目标寄存器写1,否则写0;
-
汇编写法:
sltu rd, rs1, rs2
-
xor:源寄存器1、2按位异或,结果写入目标寄存器;
-
汇编写法:
xor rd, rs1, rs2
-
srl:源寄存器1值右移源寄存器2[4:0]位,空位补0,结果写入目标寄存器;
-
汇编写法:
srl rd, rs1, rs2
-
sra:源寄存器1值循环右移源寄存器2[4:0]位,结果写入目标寄存器;
-
汇编写法:
sra rd, rs1, rs2
-
or:源寄存器1、2按位或,结果写入目标寄存器;
-
汇编写法:
or rd, rs1, rs2
-
and:源寄存器1、2按位与,结果写入目标寄存器;
-
汇编写法:
and rd, rs1, rs2