2011-11-22 25 views
6

我正在学习有关汇编语言的分割。根据我学习的书,idiv操作的结果放在eax中,其余部分放在edx中。如何在程序集中实现mod运算符

本书中的练习是在组装中实现number = result % divisor

我会认为这将等于一个正常的除法操作,除了edx将是结果。

但是这并没有奏效,edx返回了看似垃圾。

为什么?你如何在程序集中实现上述伪代码?

+4

我会编写一个小小的C函数,并查看生成的程序集(例如'gcc -O -fverbose-asm -S tiny.c') –

+2

您的问题与http://stackoverflow.com/questions类似/ 8021772/assembly-language-how-to-do-modulo/8022107显示你的实际代码,如果你有特定的问题(很可能你没有清除rdx的上部分:rax,edx:eax或dx:斧头)。 – user786653

+0

很难猜测没有看到代码,但一个常见的滑动是在idiv之前忘记edx。 –

回答

15

整数模可以通过两种方式实现:

首先使用DIVIDIV,那里的其余部分将投入EDX,但你需要零EDX第一,还是要引用英特尔:

操作数大小----------- |股息|除数|商数|剩余部分

四字/双字| EDX:EAX | r/m32 | EAX | EDX。

如:

eax = eax % 9 

当无符号变为:

XOR EDX,EDX ;clear the destinations for outputs. this stops the garbage remainder  
MOV ECX,9 
DIV ECX 
MOV EAX,EDX 

签署时,它是:

MOV ECX,9 
CDQ ;this will clear EDX due to the sign extension 
IDIV ECX 
MOV EAX,EDX 

第二种方法是,当你取模使用用于优化两次幂,在这种情况下,你AND由o小于2的幂,例如:eax = eax % 8变为AND EAX,7

+0

由于idiv是签名版本,你不应该CDQ到edx吗? – harold

+0

我试图删除我的问题,但您已经回答。我只想说明,在添加代码示例后,它可能会发生一些变化。 –

+0

@harold:你好,忘记了,好抓:) – Necrolis