如何在汇编语言的定义双字中存储 4 个字符?
How to store 4 characters in a define doubleword in assembly language?
我目前正在使用 MASM 在 DOSBox 上进行汇编编程(16 位)。
var1 dd 'abcd'
对于上述代码,MASM 正在生成错误:
A2010: syntax error
语法有什么问题?我只是将 4 个字符存储在一个双字中。
我正在做 16 位汇编,这是一个问题吗?我可以只使用 db
和 dw
因为其他变量大于 16 位吗?
var1 db 'abcd'
(不是dd
)将你想要的4个字节按源顺序放入内存。
what is the purpose of having variables other than db?
编写初始化程序方便,dd 1234h
比db 34h, 12h, 0, 0
更方便,但assemble将相同的数据写入输出文件。此外,当您使用符号时,MASM 将它们视为暗示 operand-size 的方式。
更高版本的 MASM 确实接受 dd 'abcd'
,但它们以字节顺序翻转它。 (而不是像 NASM 那样按源顺序将字节组装到内存中。)参见 .
NASM 将接受 mov eax, 'abcd'
或 dd 'abcd'
就好了: multi-character 文字只是整数文字的另一种形式,第一个字节在内存中最先(最少显着),因为 x86 是小端。即在 NASM 中,multi-character 整数文字的内存顺序与其源顺序相匹配。
但 MASM 在与 dd
或 dw
一起使用时会反转它们,因此第一个字符成为整数的 最 有效字节,并且内存顺序是源顺序的倒序。即使在支持语法的 MASM 版本中避免它也是一个好主意,并使用十六进制 ASCII 代码加注释。
在 MASM 中,var1 dd
与 db
还设置了默认的 operand-size 用于访问数据,如果您将其声明为变量而不是标签。
使用 var1 db ...
意味着任何时候您想要使用 mov eax, [var1]
访问所有 4 个字节时都必须使用显式 dword ptr
。没有 dword ptr [var1]
,MASM 会抱怨 operand-size 不匹配。
但是如果你将它声明为一个简单的标签,而不是绑定到任何 assemble 字节到内存中的 db 或 dd 指令,我认为你可以自由地使用它的任何大小。
(更新:显然带有 :
的标签是 MASM 代码段之外的错误。我不确定是否有办法只声明一个不是 MASM 的数据标签“变量”。请参阅评论中的讨论。)
;; I'm not sure this is correct, I'm making this up from memory
;; and I've never actually used MASM. I know the syntax from SO answers.
.data
label1: ; "Just" a label, no data
db 'abcd'
; little-endian 'abcd'
var2 dd 64636261h ; no : so the symbol becomes a variable with a size from the dd
.code
func:
mov eax, [label1] ; legal I think
mov al, [label1] ; also legal
mov eax, dword ptr [label1] ; always works
movzx eax, byte ptr [label1+2] ; zero extend the 'c' into EAX
inc [label1] ; ERROR: ambiguous operand-size
mov eax, [var1] ; fine, both operands are dwords
mov al, [var1] ; ERROR: operand-size mismatch
mov al, byte ptr [var1] ; load the low byte of the dword
inc [var1] ; legal: the "variable" implies dword operand size
inc dword ptr [var1] ; same as above
and byte ptr [var1], ~20h ; upper-case just the first character, 'abcd' into 'Abcd'
请注意,mov eax, var1
等同于 MASM 语法中的 mov eax, [var1]
,但我更喜欢使用 []
.
显式显示内存引用
我目前正在使用 MASM 在 DOSBox 上进行汇编编程(16 位)。
var1 dd 'abcd'
对于上述代码,MASM 正在生成错误:
A2010: syntax error
语法有什么问题?我只是将 4 个字符存储在一个双字中。
我正在做 16 位汇编,这是一个问题吗?我可以只使用 db
和 dw
因为其他变量大于 16 位吗?
var1 db 'abcd'
(不是dd
)将你想要的4个字节按源顺序放入内存。
what is the purpose of having variables other than db?
编写初始化程序方便,dd 1234h
比db 34h, 12h, 0, 0
更方便,但assemble将相同的数据写入输出文件。此外,当您使用符号时,MASM 将它们视为暗示 operand-size 的方式。
更高版本的 MASM 确实接受 dd 'abcd'
,但它们以字节顺序翻转它。 (而不是像 NASM 那样按源顺序将字节组装到内存中。)参见
NASM 将接受 mov eax, 'abcd'
或 dd 'abcd'
就好了: multi-character 文字只是整数文字的另一种形式,第一个字节在内存中最先(最少显着),因为 x86 是小端。即在 NASM 中,multi-character 整数文字的内存顺序与其源顺序相匹配。
但 MASM 在与 dd
或 dw
一起使用时会反转它们,因此第一个字符成为整数的 最 有效字节,并且内存顺序是源顺序的倒序。即使在支持语法的 MASM 版本中避免它也是一个好主意,并使用十六进制 ASCII 代码加注释。
在 MASM 中,var1 dd
与 db
还设置了默认的 operand-size 用于访问数据,如果您将其声明为变量而不是标签。
使用 var1 db ...
意味着任何时候您想要使用 mov eax, [var1]
访问所有 4 个字节时都必须使用显式 dword ptr
。没有 dword ptr [var1]
,MASM 会抱怨 operand-size 不匹配。
但是如果你将它声明为一个简单的标签,而不是绑定到任何 assemble 字节到内存中的 db 或 dd 指令,我认为你可以自由地使用它的任何大小。
(更新:显然带有 :
的标签是 MASM 代码段之外的错误。我不确定是否有办法只声明一个不是 MASM 的数据标签“变量”。请参阅评论中的讨论。)
;; I'm not sure this is correct, I'm making this up from memory
;; and I've never actually used MASM. I know the syntax from SO answers.
.data
label1: ; "Just" a label, no data
db 'abcd'
; little-endian 'abcd'
var2 dd 64636261h ; no : so the symbol becomes a variable with a size from the dd
.code
func:
mov eax, [label1] ; legal I think
mov al, [label1] ; also legal
mov eax, dword ptr [label1] ; always works
movzx eax, byte ptr [label1+2] ; zero extend the 'c' into EAX
inc [label1] ; ERROR: ambiguous operand-size
mov eax, [var1] ; fine, both operands are dwords
mov al, [var1] ; ERROR: operand-size mismatch
mov al, byte ptr [var1] ; load the low byte of the dword
inc [var1] ; legal: the "variable" implies dword operand size
inc dword ptr [var1] ; same as above
and byte ptr [var1], ~20h ; upper-case just the first character, 'abcd' into 'Abcd'
请注意,mov eax, var1
等同于 MASM 语法中的 mov eax, [var1]
,但我更喜欢使用 []
.