ARM程序集中的立即值是否需要哈希值?

时间:2014-02-08 23:02:33

标签: gcc assembly arm gas

我一直在努力阅读gcc生成的一些不同的手臂汇编代码,我发现了一些我在规范中找不到的东西。

movw    r0, #39784
movt    r0, 1

显然第一个是将值39784移动到底部16位或r0,但是'1'的movt的操作数是奇数,因为它之前没有哈希值,而且我认为立即值需要哈希。在某些情况下它是否可选?还是我错过了一些神奇的东西?

2 个答案:

答案 0 :(得分:3)

GNU汇编程序在ARM汇编代码的立即操作数之前不需要octothorpe。您的印象不正确。

答案 1 :(得分:2)

ARMv7的GNU gas行为取决于.syntax

文档说https://sourceware.org/binutils/docs-2.26/as/ARM_002dInstruction_002dSet.html#ARM_002dInstruction_002dSet

  

ARM和THUMB指令支持两种略有不同的语法。默认值划分后使用旧样式,其中ARM和THUMB指令具有自己的单独语法。可以通过.syntax指令选择新的统一语法,它具有以下主要功能:

     
      
  • 立即操作数不需要#前缀。
  •   

https://sourceware.org/binutils/docs-2.26/as/ARM_002dChars.html#ARM_002dChars说:

  

'#'或'$'均可用于指示立即数。

对于ARMv8,#始终是可选的

https://sourceware.org/binutils/docs-2.26/as/AArch64_002dChars.html#AArch64_002dChars文档:

  

'#'可以选择用来表示立即操作数。

测试

Ubuntu 16.04,Binutils 2.26.1。

v7.S:

   /* These fail */
   mov r0, 1
   mov r0, 0x1

   /* These work */
   mov r0, #1
   mov r0, #0x1
   mov r0, $1
   mov r0, $0x1
.syntax unified
   mov r0, 1
   mov r0, #1
   mov r0, 0x1
   mov r0, #0x1
   mov r0, $1
   mov r0, $0x1

v8.S:

   mov x0, 1
   mov x0, #1
   mov x0, 0x1
   mov x0, #0x1

组装:

arm-linux-gnueabi-as v7.S
aarch64-linux-gnu-as v8.S

结果:v8成功,v7在divided行上失败,而没有#

v7.S:1: Error: immediate expression requires a # prefix -- `mov r0,1'
v7.S:2: Error: immediate expression requires a # prefix -- `mov r0,0x1'

待办事项

嗯,但是有些v7指令的#实际上是可选的,例如movwmovt没有错误:

   movw r0, 1
   movt r0, 0x1

但是存在以下错误:

   movw r0, $1
   movt r0, $0x1

个人推荐

在v7代码中使用.syntax unified,切勿在v7或v8的任何文字上使用#

统一语法更新,更好,而#$符号只是更多的代码噪音。

Linux内核同意我的观点:https://github.com/torvalds/linux/blob/v4.19/arch/arm/include/asm/unified.h#L23