文章目录
数据搬移指令
@ 1.1 数据处理指令:数学运算、逻辑运算
@ 数据搬移指令
@ MOV R1, #1 @ 往R1寄存器存值1
@ R1 = 1 @ 第二种写法
@ MOV R2, R1 @ 可以将R1寄存器的值搬移给R2寄存器
@ R2 = R1 @ 第二种写法
@ MVN R0, #0xFF
@ R0 = ~0xFF 先位取反,再搬移
验证PC寄存器
PC寄存器会自动取下一条指令的地址。且自增4;
PC指向谁就要执行哪条指令;可以看到0地址是第一条指令的地址,因此会跳转执行第一条指令
若指定PC寄存器的地址,会强制将地址的最后两位设为0;
验证ARM指令大小都是32位(4字节)
每条指令存储的都是4个字节
立即数
由于整个指令占32位,如果单单MOV后面的一个数就占32位了,加上MOV这个指令后肯定超过32位了。
立即数
:能够放在指令后面的数
注意:尽管0xFFFFFFFF不是立即数,要看调试信息反汇编的内容
@ 编译器替换
@ MOV R0, #0xFFFFFFFF 编译器会替换成MVN 0x00000000
@ 立即数
@ 立即数的本质就是包含在指令当中的数,属于指令的一部分
@ 立即数的优点:取指的时候就可以将其读取到CPU,不用单独去内存读取,速度快
@ 立即数的缺点:不能是任意的32位的数字,有局限性
@ MOV R0, #0x12345678 不是立即数
@ MOV R0, #0x12 是立即数
数据运算指令基本格式
@ 数据运算指令基本格式
@ 《操作码》《目标寄存器》《第一操作寄存器》《第二操作数》
@ 操作码 指示执行哪种运算
@ 目标寄存器: 存储运算结果
@ 第一操作寄存器:第一个参与运算的数据(只能是寄存器)
@ 第二操作数: 第二个参与运算的数据(可以是寄存器或立即数)
加法
@ 加法指令
@ MOV R2, #5
@ MOV R3, #3
@ ADD R1, R2, R3
@ R1 = R2 + R3
@ ADD R1, R2, #5 也可以写成寄存器和数相加
@ R1 = R2 + 5
减法
@ 减法指令
@ SUB R1, R2, R3
@ R1 = R2 - R3
@ SUB R1, R2, #3
@ R1 = R2 - 3
逆向减法指令
逆向减法
:由于减法指令的减数必须是第一寄存器,所以如果要用一个数作为减数的话减法就不行了,因此引入了逆向减法。
@ 逆向减法指令
@ RSB R1, R2, #3
@ R1 = 3 - R2
乘法
@ 乘法指令
@ MUL R1, R2, R3
@ R1 = R2 * R3
@ 乘法指令只能是两个寄存器相乘
除法
ARM处理器指令中没有除法指令
按位与
@ 按位与指令
@ AND R1, R2, R3
@ R1 = R2 & R3
按位或
@ 按位或指令
@ ORR R1, R2, R3
@ R1 = R2 | R3
按位异或
@ 按位异或指令
@ EOR R1, R2, R3
@ R1 = R2 ^ R3
左移
@ 左移指令
@ LSL R1, R2, R3
@ R1 = (R2 << R3)
右移
@ 右移指令
@ LSR R1, R2, R3
@ R1 = (R2 >> R3)
位清零
@ 位清零指令
@ MOV R2, #0xFF
@ BIC R1, R2, #0x0F
@ 第二操作数中的哪一位为1,就将第一操作寄存器的中哪一位清零,然后将结果写入目标寄存器
@ 比如0x0F最后4位为1,就将R2最后4位清零,把结果给R1,R2不变
数据运算指令的格式扩展
@ 格式扩展
@ MOV R2, #3
@ MOV R1, R2, LSL #1
@ R1 = (R2 << 1)
验证CPSR寄存器
@ 数据运算指令对条件位(N、Z、C、V)的影响
@ 默认情况下数据运算不会对条件位产生影响,在指令后加后缀”S“才可以影响
MOV R1, #3
SUBS R2, R1, #3
ADDS R2, R1, #2
32位寄存器怎么运算64位的数
32位处理器:单次运算能力为32位的处理器
通过将64位的低、高位分别存在2个寄存器中,低位和低位运算,高位和高位运算,最后把结果也按低、高位分别存放在2个寄存器中
但如果低位相加要进位到高位,此时应按下列写法,ADC表示带进位的加法
@ 带进位的加法指令
@ 两个64位的数据做加法运算
@ 第一个数的低32位放在R1
@ 第一个数的高32位放在R2
@ 第二个数的低32位放在R3
@ 第二个数的高32位放在R4
@ 运算结果的低32位放在R5
@ 运算结果的高32位放在R6
@ 第一个数
@ 0x00000001 FFFFFFFF
@ 第二个数
@ 0x00000002 00000005
@ MOV R1, #0xFFFFFFFF
@ MOV R2, #0x00000001
@ MOV R3, #0x00000005
@ MOV R4, #0x00000002
@ ADDS R5, R1, R3
@ ADC R6, R2, R4
@ 本质:R6 = R2 + R4 + 'C'(C位)
@ 带借位的减法指令
@ 第一个数
@ 0x00000002 00000001
@ 第二个数
@ 0x00000001 00000005
@ MOV R1, #0x00000001
@ MOV R2, #0x00000002
@ MOV R3, #0x00000005
@ MOV R4, #0x00000001
@ SUBS R5, R1, R3
@ SBC R6, R2, R4
@ 本质:R6 = R2 - R4 - '!C'(Bit[28]中减法借位自动置0,因此要取反变成1才能正确被减)
编程实现用32位ARM处理器实现两个128位数据相加
.text
.global _start
_start:
@ 第一个数
MOV R1, #0x00000001
MOV R2, #0x00000001
MOV R3, #0x00000001
MOV R4, #0x00000001
@ 第二个数
MOV R5, #0x00000001
MOV R6, #0x00000001
MOV R7, #0x00000001
MOV R8, #0x00000001
@ 相加
ADD R9, R1, R5
ADD R10, R2, R6
ADD R11, R3, R7
ADD R12, R4, R8
.end
要学会用汇编的思想写C语言
a = a / 2;
//最好写成
a >>= 1;
//尽量少用float