如何仅使用 3 条指令和一个 8 位寄存器(8086 指令集)编写循环 256 次的代码?
How can I write a code that loops 256 times using only 3 instructions and one 8-bit register (8086 instruction set)?
这是我的一位教授之前提出的问题,我假设 8 位寄存器是 CL 或 CH。我通过简单地将 01H 移动到 CH 寄存器来让它工作,但我想知道是否有任何其他方法可以做到这一点,因为我在 运行 代码时技术上使用整个 16 位 CX 寄存器。
我的参考代码:
MOV CH,01H
L1:INC AX ;to keep count
LOOP L1
没错,您的代码使用了 16 位 CX。更糟糕的是,这取决于 CL 在该代码段执行之前为零!从零开始的 8 位循环计数器将在 256 次递减(或递增)后返回到零。
mov al, 0 ; uint8_t i = 0. xor ax,ax is the same code size but zeros AH
loop: ; do {
dec al
jnz loop ; }while(--i != 0)
问题中没有任何内容表示循环内需要任何工作;这只是一个空的延迟循环。
效率说明:dec ax
比dec al
小,loop rel8
比dec
/jnz
还要紧凑。因此,如果您针对真正的 8086 或 8088 进行优化,您会希望循环体更小,因为它比循环前的代码运行的次数更多。当然,如果你真的只想延迟,这会延迟更长的时间,因为 code-fetch 需要更多的内存访问。 mov ax, 256
(3 字节)与 xor ax,ax
(2 字节)或 mov al, 0
(2 字节)相比,总体代码大小是相同的。
这对任何 8 位寄存器都是一样的; AL 对于这些指令中的任何一条都不是特殊的,因此您通常希望将它免费用于可以从其特殊编码中受益的东西,例如 cmp al, imm8
2 字节而不是通常的 3.
这是我的一位教授之前提出的问题,我假设 8 位寄存器是 CL 或 CH。我通过简单地将 01H 移动到 CH 寄存器来让它工作,但我想知道是否有任何其他方法可以做到这一点,因为我在 运行 代码时技术上使用整个 16 位 CX 寄存器。
我的参考代码:
MOV CH,01H
L1:INC AX ;to keep count
LOOP L1
没错,您的代码使用了 16 位 CX。更糟糕的是,这取决于 CL 在该代码段执行之前为零!从零开始的 8 位循环计数器将在 256 次递减(或递增)后返回到零。
mov al, 0 ; uint8_t i = 0. xor ax,ax is the same code size but zeros AH
loop: ; do {
dec al
jnz loop ; }while(--i != 0)
问题中没有任何内容表示循环内需要任何工作;这只是一个空的延迟循环。
效率说明:dec ax
比dec al
小,loop rel8
比dec
/jnz
还要紧凑。因此,如果您针对真正的 8086 或 8088 进行优化,您会希望循环体更小,因为它比循环前的代码运行的次数更多。当然,如果你真的只想延迟,这会延迟更长的时间,因为 code-fetch 需要更多的内存访问。 mov ax, 256
(3 字节)与 xor ax,ax
(2 字节)或 mov al, 0
(2 字节)相比,总体代码大小是相同的。
这对任何 8 位寄存器都是一样的; AL 对于这些指令中的任何一条都不是特殊的,因此您通常希望将它免费用于可以从其特殊编码中受益的东西,例如 cmp al, imm8
2 字节而不是通常的 3.