在8086上归零%EAX寄存器

时间:2013-11-25 18:10:16

标签: assembly x86 x86-16

我在DEC PDP-8小型机的每个程序开始时发出的第一条指令是CLA CLL来清除累加器和链接(溢出)位。

这个简单的指令似乎并不存在于8086系列处理器中,而且我已经在最快捷的方式上看到了很多关于各种技术网站的讨论,比如对它自己进行异或。

这是否已由处理器逻辑处理? 所以在程序开始之前保证为0?

4 个答案:

答案 0 :(得分:1)

对于8086,清除AX寄存器(不是EAX)的最快和最短的方法是发出一些执行操作的ALU指令。那就是:

xor ax,ax  ; opcode: 29 C0

或者

sub ax,ax  ; opcode: 31 C0

最短,因为常规mov ax,0需要3个字节:B8 00 00,多一个字节。 最快,因为xorsub使用3个时钟周期。 mov使用4个周期。

另一方面,xorsub将改变标志,而mov则不会。有时你不介意在需要清除寄存器时更改标志,有时你不会想要改变标志。关于代码清晰度,xor / sub“技巧”是众所周知的,并且编译器确实使用它来快速注册清除,因此任何汇编程序员都会意识到你想要做的事情。

答案 1 :(得分:0)

xormov执行不同的操作。 xor将设置条件位,而mov则不会。 如果您的目标是将注册表设置为特定值,mov会清楚地将该注册表传达给您的软件读者。

优化汇编程序有时可以安全地将mov reg, 0转换为xor reg, regsub reg, reg

sub reg, regxor reg, reg并不一定会在所有时间内同样快速地执行。减法需要携带和排他或不。承载通常以极其有效的方式实施,并且所花费的额外时间难以测量,因此出于实际目的,人们倾向于将它们称为具有同样快速执行。

答案 2 :(得分:0)

程序启动时处理器寄存器中的内容是无关紧要的(x86堆栈指针除外)。如果您不喜欢寄存器中的垃圾,只需将它们设置为您喜欢的值即可。

在您的代码开头,这可能会花费您10条指令。在实践中,您不需要初始化您没有立即使用的寄存器,因此它只有1或2条指令。更重要的是,大多数装配程序比这大得多,所以没有人关心。

如果您坚持,可以通过将寄存器归零(xor reg,reg / sub reg,reg / mov reg,0)来初始化寄存器。

值得知道处理器可以利用某些指令。在现代英特尔芯片(不一定是x86)上,“xor reg,reg”打破了对“reg”的管道依赖性,实现了更快的代码,所以你应该坚持使用这些指令。

答案 3 :(得分:0)

如果我们首先使用同一寄存器的16位部分并且想要在以下指令中将访问权限更改为32位,则还建议对32位寄存器使用“xor reg,reg”。
例如:

LOCATION DW 3

xor eax, eax
mov ax, [LOCATION] ; first a 16 bit access to the lower part of EAX
shl eax, 2         ; following by a 32 bit access

xor-instruction可以更快地执行代码。我认为movzx指令的执行速度会慢一些。

德克