【问题标题】:Assembly commands LEA/LDS/LES [duplicate]装配命令 LEA/LDS/LES [重复]
【发布时间】:2013-12-06 22:01:19
【问题描述】:

以下命令有什么区别:LEALDSLES?我搜索了答案,但我不是很清楚。据我了解block1 应该等同于block2

.data
  str1 db 'My first string. $'
  str2 db 'My second string. $'
  ptr_str1 dd str1 
  ptr_str2 dd str2
.code
  _block1:
  mov AX, @data
  mov DS, AX
  mov ES, AX
  lea SI, str1
  lea DI, str2

  _block2:
  lds SI, ptr_str1
  les DI, ptr_str2

...但是当我使用以下宏打印str1str1 时,第二个块不会返回预期的结果。

print MACRO param
    lea DX, param
    mov AH, 9
    int 21h
ENDM

【问题讨论】:

标签: assembly x86 command


【解决方案1】:

lea 表示加载有效地址。所以lea SI, str1si 设置为str1 的偏移量。 lea 和其他指令使用的正确内存寻址语法取决于使用的汇编程序,有些汇编程序需要lea si,[str1]

ldsles 做的事情与lea 完全不同。 lds 表示使用 DS 加载指针,同样les 表示使用 ES 加载指针。在实践中,lds SI, ptr_str1 根据存储在内存地址ds:ptr_str1 中的值设置dssi(在某些汇编程序中语法为[ds:ptr_str1])。

那么,这些指令在您的代码中的作用:

  1. lea SI, str1 设置si 指向str1 的地址。这似乎完全没问题。

  2. lds SI, ptr_str1si 设置为'My'(十六进制为0x794d),还将ds 设置为' f'(十六进制为0x6620)。请注意,x86 是一种小端架构。 ds 是使用ldsles 读取指针值的默认段。所以不是将字符串地址加载到ds:si,而是将字符串的前4个字节用作加载到ds:si的地址。我想这不是你想做的。

  3. les DI, ptr_str2 根据存储在 0x6620:ptr_str2 中的值设置 dids 是大多数 x86 指令的默认段,当前 ds 的值是 0x6620)并且还设置 @987654355 @ 根据 0x6620:ptr_str2+2 中存储的值。可能这不是你想做的。

【讨论】:

  • 我个人从不写lea si,str1(或类似的,用于movpush等)但总是lea si,[str1](如果不清楚,可能与dword ptr和朋友一起写) ) 或mov si,offset str,也就是说,我总是添加方括号或offset 运算符,以消除歧义。这是因为当您两者都不做时,汇编程序彼此不同:一些添加括号,一些添加offset(尤其是对mov 和朋友的刺激)。但是很好的解释,+1。
  • @mirabilos dword ptr 和朋友与lea 无关并且不影响编码,因为只有内存地址对lea 很重要。不同 x86/x86-64 汇编器的内存寻址语法的差异非常烦人,因为完全相同的语法在不同的 x86/x86-64 汇编器中可能具有不同的含义,因此如果使用不同的汇编器进行汇编可能会导致错误。 stackoverflow.com/questions/14984788/…
  • 我知道 lea 也是如此,但是,一口气教好风格可能并非不重要。
猜你喜欢
  • 1970-01-01
  • 2011-05-30
  • 2012-08-14
  • 1970-01-01
  • 1970-01-01
  • 2021-03-30
  • 2012-02-27
  • 2011-11-12
  • 1970-01-01
相关资源
最近更新 更多