获取标签地址到ARM上的寄存器?

sup*_*ggs 3 arm

如何编写一条将标签所引用的地址放入寄存器的指令?

art*_*ise 5

有四种方法,其中三种方法记录在Sourceware的Gnu Assembler手册中。我想标签是这样的,

 target:
     .long 0xfeadbeef
Run Code Online (Sandbox Code Playgroud)
  1. adr r0,target
  2. adrl r0,target
  3. ldr r0,=target
  4. sub r0,pc,#(.+8-target)

前两个非常相似并生成sub r0,pc,#offset。的3 放长在一个文字池和负载这通过ldr r0,[pc,#offset2]或者它可以使用一个mov,如果汇编程序找到它可以(通常是对齐的标签,如在为0x8000)。最后一个版本是手动计算它。

adr和之间的区别adrl来自立即操作数。它们是8 旋转的2的倍数。因此,如果地址很远,则可能需要执行两条指令,这通常会比通过数据高速缓存内存获得完整32位的第三种 ldr变体更快。

另请参阅:汇编程序中的重定位


Thumb2添加了movw和的组合movt。例如,

label:
 ; data
...
movw    r0, :lower16:label - .
movt    r0, :upper16:label - . 
Run Code Online (Sandbox Code Playgroud)

这会将偏移量放入r0。它对PC相对而言没有用,但对绝对值或常数直接加载有用。

请参阅:有关常数的ARM博客