NASM 无效的地址行为?
NASM invalid address behaviour?
我有一个名为 a
的数组和一个名为 n 的常量,我试图将其作为二维数组进行寻址,并使用以下行:mov al, [a+ebx*n+esi]
问题在于,如果 n
是偶数 (n equ 4
),它可以完美运行,但如果 n
是奇数 (n equ 3
),编译器会给出 "error: invalid effective address"。我能理解它在两种情况下是否有效,但我不明白为什么它们的工作方式不同。
编译器:NASM
链接器:GCC(Windows 的 minGW)
IDE:SASM
程序:
%include "io.inc"
section .data
a db 1, 2, 3, 4
db 5, 6, 7, 9
db 9, 10, 11, 12
db 13, 14, 15, 16
n equ 4
section .text
global CMAIN
CMAIN:
mov ebp, esp; for correct debugging
; write your code here
;
; get upper limit
xor eax, eax
mov edi, n
;
; get last column
mov esi, n-1
xor ebx, ebx
xor edx, edx ; count in DL
xor ecx, ecx ; sum in CX
mov dh, 3
cycle:
xor ah, ah
mov al, [a+ebx*n+esi]
div dh
cmp ah, 0
jne afteradd
add cl, [a+ebx*n+esi]
add dl, 1
afteradd:
add ebx, 1
cmp ebx, edi
jl cycle
solve:
mov ax, cx
div dl ; среднее арифметическое будет в AL
aftercycle:
xor eax, eax
ret
地址的偏移部分以base + index*scale + displacement
的形式给出。偏移量的 scale
部分仅允许某些值。它们是 1
(默认值)、2
、4
和 8
。
这在 Intel's Software Developers Manual 第 1 卷(名为 指定偏移量 的部分)中进行了描述:
The offset part of a memory address can be specified directly as a static value (called a displacement) or through
an address computation made up of one or more of the following components:
• Displacement — An 8-, 16-, or 32-bit value.
• Base — The value in a general-purpose register.
• Index — The value in a general-purpose register.
• Scale factor — A value of 2, 4, or 8 that is multiplied by the index value.
(以上引述适用于 32 位模式,但比例因子的相同限制适用于 64 位模式)
我有一个名为 a
的数组和一个名为 n 的常量,我试图将其作为二维数组进行寻址,并使用以下行:mov al, [a+ebx*n+esi]
问题在于,如果 n
是偶数 (n equ 4
),它可以完美运行,但如果 n
是奇数 (n equ 3
),编译器会给出 "error: invalid effective address"。我能理解它在两种情况下是否有效,但我不明白为什么它们的工作方式不同。
编译器:NASM
链接器:GCC(Windows 的 minGW)
IDE:SASM
程序:
%include "io.inc"
section .data
a db 1, 2, 3, 4
db 5, 6, 7, 9
db 9, 10, 11, 12
db 13, 14, 15, 16
n equ 4
section .text
global CMAIN
CMAIN:
mov ebp, esp; for correct debugging
; write your code here
;
; get upper limit
xor eax, eax
mov edi, n
;
; get last column
mov esi, n-1
xor ebx, ebx
xor edx, edx ; count in DL
xor ecx, ecx ; sum in CX
mov dh, 3
cycle:
xor ah, ah
mov al, [a+ebx*n+esi]
div dh
cmp ah, 0
jne afteradd
add cl, [a+ebx*n+esi]
add dl, 1
afteradd:
add ebx, 1
cmp ebx, edi
jl cycle
solve:
mov ax, cx
div dl ; среднее арифметическое будет в AL
aftercycle:
xor eax, eax
ret
地址的偏移部分以base + index*scale + displacement
的形式给出。偏移量的 scale
部分仅允许某些值。它们是 1
(默认值)、2
、4
和 8
。
这在 Intel's Software Developers Manual 第 1 卷(名为 指定偏移量 的部分)中进行了描述:
The offset part of a memory address can be specified directly as a static value (called a displacement) or through an address computation made up of one or more of the following components:
• Displacement — An 8-, 16-, or 32-bit value.
• Base — The value in a general-purpose register.
• Index — The value in a general-purpose register.
• Scale factor — A value of 2, 4, or 8 that is multiplied by the index value.
(以上引述适用于 32 位模式,但比例因子的相同限制适用于 64 位模式)