分类: 嵌入式
2011-05-09 17:07:35
从学习arm汇编开始就一直以为arm的指令b是一个绝对跳转指令,最近在学习u-boot,看到一处使用b的例子,觉得这个指令并不是直接跳转那么回事。
写了个测试的例子:
head.s
====================
.global _start
.text
_start:
b reset
b aa
b bb
b 0x30
reset:
.space 8,0xab
aa: .word 0xdeadbeef
.space 8,0xab
bb: .word 0xdeadbeef
.word 0xdeadbeef
.end
====================执行命令:arm-none-eabi-gcc -mcpu=arm7tdmi -c head.s -o head.o&&arm-none-eabi-gcc -Ttext 0x0 -mcpu=arm7tdmi -nostartfiles head.o -o head.elf&&arm-none-eabi-objdump -d head.elf 后的输出结果如下(反汇编):
==================
Disassembly of section .text:
00000000 <_start>:
0: ea000002 b 104: ea000003 b 18 8: ea000005 b 24 c: ea000004 b 24 00000010
:
10: abababab .word 0xabababab
14: abababab .word 0xabababab00000018
:
18: deadbeef .word 0xdeadbeef
1c: abababab .word 0xabababab
20: abababab .word 0xabababab00000024
:
24: deadbeef .word 0xdeadbeef
28: deadbeef .word 0xdeadbeef==================
从上面的例子可以看到:
b reset==>ea000002
b aa==>ea000003
b bb==>ea000005
b 0x30==>ea000004
从上面可以发现规律:指令所要跳转到的标号地址=执行这条指令时PC的值(这条指令的地址值+8,预取指的原因)+机器码中的立即数*4
比如,
=0+8+2*4=0x10 =4+8+3*4=0x18 也就是标号处是当前指令的地址向后数(机器码中的立即数+2)个指令,也就是它跳转时是相对PC当前值的。
至于直接跳转到数字值(上面的b 0x30)怎么生成的地址,还没搞清楚。。。
至少,从这个例子可以看出,b指令也是相对跳转指令,它所要跳到的标号跟当前指令的地址有关。
(这个是自己的理解,欢迎大牛批评指正!)