RISC-V 常用汇编指令

RISCV 常用汇编指令


相关寄存器

寄存器 ABI 名 用途 Saver
x0 zero 读取时总为 0, 写入时不起任何效果 -
x1 ra 存放函数返回地址 (return address) Caller
x2 sp 存放栈指针 (stack pointer) Callee
x3 gp global pointer -
x4 tp thread point -
x5 - x7 t0 - t2 临时 (temporaries) 寄存器,Callee 可能会使用这些寄存器,所以 Callee 不保证这些寄存器中的值在函数调用过程中保持不变,这意味着对于 Caller 来说,如果需要的话,Caller 需要自己在调用 Callee 之前保存临时寄存器中的值。 Caller
x28 - x31 t3 - t6 临时寄存器,同上 Caller
x8 - x9 s0/fp - s1 保存 (saved) 寄存器,Callee 需要保证这些寄存器的值在函数返回后仍然维持函数调用之前的原值,所以一旦 Callee 在自己的函数中会用到这些寄存器则需要在栈中备份并在退出函数时进行恢复。 Callee
x18 - x27 s2 - s11 保存寄存器,同上 Callee
x10 - x11 a0 - a1 参数 (argument) 寄存器,用于在函数调用过程中保存第一个和第二个参数,以及在函数返回时传递返回值。 Caller
x12 - x17 a2 - a7 参数 (argument) 寄存器,如果函数调用时需要传递更多的参数,则可以用这些寄存器,但注意用于传递参数的寄存器最多只有 8 个 (a0 ~ a7) ,如果还有更多的参数则要利用栈。 Caller

Caller :调用者,Callee : 被调用函数【这里可以视为在 Caller (函数)中调用 Callee (函数)】
Caller 维护的寄存器,在运行被调函数前不会被保存,函数返回时这些寄存器可能会被改变,所以在调用前由 Caller 保存维护。
Callee 维护的寄存器,在运行被调函数前会被保存,函数返回后这些寄存器与运行被调函数前相同。


算术运算指令

指令 语法 描述 例子
add add rd,rs1,rs2 (rs1 + rs2) 的值保存到 rd add x5,x6,x7
sub sub rd,rs1,rs2 (rs1 - rs2)的值保存到 rd sub x5,x6,x7
lui lui rd,imm rd = (imm << 12) (20位的立即数左移12位) lui x5,0x12345
auipc auipc rd,imm(20bit) rd = (imm << 12) + pc (相对 pc 的偏移值) auipc x5,0x1234
伪指令 语法 等价语句 描述 例子
neg neg rd,rs sub rd,x0,rs rd = ~rs (取反) neg x5,x6
mv mov rd,rs addi rd,rs,0 rd = rs mov x5,x6
nop nop addi x0,x0,0 空指令 nop
li li rd,imm rd = imm (32bit) 直接加载32位立即数 li x5,0x12345678
la la rd,addr rd = addr 加载地址到寄存器 la x5,0x12345

逻辑运算指令

指令 语法 描述 例子
and and rd,rs1,rs2 rd = (rs1 & rs2) and x5,x6,x7
or or rd,rs1,rs2 rd = (rs1 | rs2) or x5,x6,x7
xor xor rd,rs1,rs2 rd = (rs ^ rs2) xor x5,x6,x7
andi andi rd,rs,imm rd = (rs & imm) andi x5,x6,10
ori ori rd,rs,imm rd = (rs | imm) ori x5,x6,20
xori xori rd,rs,imm rd = (rs ^ imm) xori x5,x6,10
伪指令 语法 等价语句 描述 例子
not not rd,rs xori rd,rs,-1 按位取反 not x5,x6

移位运算指令

逻辑移位 补零

指令 语法 描述 例子
sll sll rd,rs1,rs2 (rs1 << rs2) sll x5,x6,x7
srl srl rd,rs1,rs2 (rs1 >> rs2) srl x5,x6,x7
slli sll rd,rs1,imm (rs1 << imm) slli x5,x6,10
srli srl rd,rs1,imm rd = (rs1 >> imm) srli x5,x6,20

算术移位(只有右移,补符号位)

指令 语法 描述 例子
sra sra rd,rs1,rs2 rd = (rs1 << rs2) sra x5,x6,x7
srai srai rd,rs1,imm rd = (rs1 >> imm) srl x5,x6,20

内存读写指令

imm 为12bit有符号整数

读指令

指令 语法 描述 例子
lb lb rd,imm(rs) 从内存 imm+rs 处读取8bit数据(符号拓展)到 rd 中(符号拓展) lb x5,40(x6)
lbu lbu rd,imm(rs) 从内存 imm+rs 处读取8bit无符号整数(0扩展)到 rd 中(0扩展) lbu x5,40(x6)
lh lh rd,imm(rs) 从内存 imm+rs 处读取16bit数据(符号拓展)到 rd 中(符号拓展) lh x5,40(x6)
lhu lhu rd,imm(rs) 从内存 imm+rs 处读取16bit无符号整数(0扩展)到 rd 中(0扩展) lhu x5,40(x6)
lw lw rd,imm(rs) 从内存 imm+rs 处读取32bit数据到 rd 中 lw x5,40(x6)

写指令

指令 语法 描述 例子
sb sb rs2,imm(rs1) 将rs2中的8bit数据写入内存 imm+rs1 处 sb x5,40(x6)
sh sh rs2,imm(rs1) 将rs2中的16bit数据写入内存 imm+rs1 处 sb x5,40(x6)
sw sw rs2,imm(rs1) 将rs2中的32bit数据写入内存 imm+rs1 处 sb x5,40(x6)

条件分支指令

指令 语法 描述 例子
beq beq rs1,rs2,imm 如果rs1 == rs2,跳转到 imm 地址处 beq x5,x6,100
bne bne rs1,rs2,imm 如果rs1 != rs2,跳转到 imm 地址处 bne x5,x6,100
blt blt rs1,rs2,imm 如果rs1 < rs2(有符号方式),跳转 blt x5,x6,100
bltu bltu rs1,rs2,imm 如果rs1 < rs2(无符号方式),跳转 bltu x5,x6,100
bge blt rs1,rs2,imm 如果rs1 >= rs2(有符号方式),跳转 bge x5,x6,100
bgeu bltu rs1,rs2,imm 如果rs1 >= rs2(无符号方式),跳转 bgeu x5,x6,100

跳转的目标地址计算方法(对齐):(imm<<1)+pc 具体编程时由标号给出

伪指令 语法 等价语句 例子
ble ble rs1,rs2,offset 如果 rs1 <= rs2,跳转到 offset 地址处 ble x5,x6,100
bleu bleu rs1,rs2,offset 如果 rs1 <= rs2(无符号),跳转到 offset 地址处 bequ x5,x6,100
bgt bgt rs1,rs2,offset 如果 rs1 >= rs2,跳转到 offset 地址处 bgt x5,x6,100
bgtu bgtu rs1,rs2,offset 如果 rs1 >= rs2(无符号),跳转到 offset 地址处 bgtu x5,x6,100
beqz beqz rs1,offset 如果 rs1 == 0,跳转到 offset 地址处 beqz x5,x6,100
bnez bnez rs1,offset 如果 rs1 != 0,跳转到 offset 地址处 bnez x5,x6,100
bltz bltz rs1,offset 如果 rs1 < 0,跳转到 offset 地址处 bltz x5,x6,100
blez blez rs1,offset 如果 rs1 <= 0,跳转到 offset 地址处 blez x5,x6,100
bgtz bgtz rs1,offset 如果 rs1 > 0,跳转到 offset 地址处 bgtz x5,x6,100
bgez bgez rs1,offset 如果 rs1 >= 0,跳转到 offset 地址处 bgez x5,x6,100

无条件跳转指令

指令 语法 描述 例子
jal jal rd,label 指令的下一条指令地址存入rd,跳转到label (20bit) jal x1,label
jalr jalr rd,imm(rs) 12bit的imm符号拓展,(rs+imm)低位置0存到rd,跳转 jarl x1,0(x5)
伪指令 语法 等价语句 描述
j j offset jal x0,offset [不会保存跳转前的地址] j label
jr jr rs jalr x0,0(rs) [不会保存跳转前的地址] jr x5

函数调用

伪指令 语法 等价语句 描述 例子
jal jal offset jal x1,offset 保存返回地址到x1,跳转到 offset jal label
jalr jalr rs jalr x1,0(rs) 保存返回地址到x1,跳转到rs寄存器保存的地址 jalr label
call call offset auipc x1,offset[31:12]+offset[11];jalr x1,ofsset[11:0] (x1) call fun
ret ret jalr x0,0(x1) 返回 ret

参考

  • 循序渐进,学习开发一个RISC-V上的操作系统
  • mit 6.S081

你可能感兴趣的:(笔记,risc-v)