.ascii和.string汇编程序指令之间的区别是什么?

Aad*_*hah 8 x86 assembly gcc directive gnu-assembler

我知道该.ascii指令不会在字符串的末尾添加空字符.该.asciz指令用于此目的.但是,我不知道该.string指令是否在字符串的末尾放置一个空字符.如果确实如此,那么指令.asciz.string指令之间的区别是什么?对我来说,同时具有.ascii.string似乎是多余的.

cal*_*hiz 6

根据binutils 文档

.ascii "string" (这里是为了完整性)

.ascii 需要零个或多个以逗号分隔的字符串文字。它将每个字符串(没有自动尾随零字节)组装成连续的地址。

.asciz "string"

.asciz 就像 .ascii,但每个字符串后跟一个零字节。'.asciz' 中的“z”代表“零”。

.string "str", .string8 "str", .string16 "str", .string32 "str", .string64 "str"

将 str 中的字符复制到目标文件中。您可以指定多个要复制的字符串,用逗号分隔。除非对特定机器另有规定,否则汇编器用 0 字节标记每个字符串的结尾。

...

变体 string16、string32 和 string64 与字符串伪操作码的不同之处在于,str 中的每个 8 位字符都被复制并分别扩展为 16、32 或 64 位。扩展的字符以目标字节序存储。

它们都支持转义序列并接受多个参数。至于之间的区别.string.asciz

  • 在某些体系结构中,.string不会添加空字节,当.asciz总是会。要测试您自己的系统,您可以这样做:
    • echo '.string ""' | gcc -c -o stdout.o -xassembler -; objdump -sj .text stdout.o.
    • 如果第一个字节是 00,则插入了空字符。
  • .string 也有将字符扩展到特定宽度(16、32 或 64)的后缀,但默认情况下它是 8。

正如问题的评论中所述,在大多数情况下,除了语义之外没有其他区别,但从技术上讲,这两个伪操作是不同的。

附录:

事实证明,文档确实提到了两种行为不同的架构:

  • HPPA (HP Precision Architecture) - 不加 0,但有一个特殊的.stringz指令。
  • TI-C54X(德州仪器的某些 DSP 芯片) - 每个字的高 8 位(2 字节)填充零。有一个相关的.pstring指令来打包字符并用零填充未使用的空间。

gas/config文件夹中挖掘源代码,我们可以确认这一点并找到更多:

  • IA64(英特尔架构) -.string.stringz行为很像HPPA。

  • @Herdsman 它位于源代码文件夹中。https://ftp.gnu.org/gnu/binutils/ (2认同)