使用“.intel_syntax noprefix”如何获得标签的内存地址?

问题描述:

我正在学习如何建立组装和连接的实模式程序:使用“.intel_syntax noprefix”如何获得标签的内存地址?

  • GCC汇编版本2.25
  • Binutils的版本2.25
  • GCC 5.2.0版本

我使用英特尔语法不带前缀.intel_syntax noprefix

我想将一个字符串的地址加载到SI注册。我知道,如何引用NASM中的内存位置,但是当我在GNU汇编程序代码中执行相同操作时,它只将字符串的WORD移动到寄存器中,而不是标签的地址。

我的代码是:

.code16 
.intel_syntax noprefix 

mov cx, 11 
mov si, name 
mov di, 0x7E00 
push di 
rep cmpsb 
pop di 
je LOAD 

当我用GCC编译它,我可以在处理器确实调试器看到:

mov si, WORD ptr ds:0x7d2d 

,但我想要的字符串的地址迁入寄存器,而不是它指向的数据。

我也试图把方括号的名字是这样的:

.code16 
.intel_syntax noprefix 

mov cx, 11 
mov si, [name] 
mov di, 0x7E00 
push di 
rep cmpsb 
pop di 
je LOAD 

它不会有所作为。

NASM我知道,这汇编代码的工作原理:

mov si, name 

NASM将生成的name地址移动到寄存器SI指令。

我的问题:有没有办法强制GCC使用带有无前缀的英特尔语法将符号的地址加载到寄存器中?

+0

事实后,我发现一个相关的问题,与[*答案](http://*.com/questions/16121173/why-does-switching-from-att-to-intel-syntax-make-this -tutorial-segfault-using-g)是相似的。根据不同的观点,这个问题可能被认为是重复的。 –

如果使用GNU汇编代码(通过GCC)与指令:

.intel_syntax noprefix 

那么语法似乎有点不寻常,并在规范的来源无据可查。此代码:

mov si, name 

在存储位置移动16位WORD指向标签nameSI。以下说明做同样的事情,虽然我更喜欢方括号[],因为代码的意图是清晰的:

mov si, name    
mov si, [name] 
mov si, word ptr [name] # This is the same as two above in long form 
          #  The use of "word ptr" here is similar to MASM 

要获得name的地址,并把它放入你需要使用offset这样的寄存器:

mov si, offset name 

如果有人有,实际上描述了可与使用的语法规范源请在评论中告诉我。我知道blogs about the syntax,连同一些轻蔑,但没有官方。

+1

我还没有见过任何使用'.intel_syntax'源文件的开源项目。项目通常选择AT&T语法,或使用NASM或YASM。不过,我想不出/为什么GNU'.intel_syntax'不太好的具体原因。例如我不认为你在AT&T语法中可以做任何你不能在'intel_syntax'中做的任何事情,或者额外的含糊之处。 (我的缺点是,它就像MASM语法,而我更喜欢NASM语法,所有有效地址都需要'[]')。 –

+0

@PeterCordes:我同意,并且这种语法不是我经常看到的 - 我知道一些含糊之处,但这绝对是我缺乏第一手经验的一个领域。如果我使用GAS,我通常会采用AT&T语法,如果我需要Intel,我会使用NASM,YASM等。如果你没有其他选择,并且不能用于AT&T语法,那么我想这可能会成为一个用例。想象一下当我找不到完整语法的canon源时我的失望。阅读binutils源代码太像工作了;-) –

+1

是的,我预计它也会在某个地方正式记录。尽管如此,我并不完全感到震惊。对我来说,它是反汇编/编译器输出的主要格式,不能写入。 –