loop 指令的功能是重复执行一段相同的代码,处理器在执行它的时候会顺序做两件事:
- 将寄存器 CX 的内容减一;
- 如果 CX 的内容不为零,转移到指定的位置处执行,否则顺序执行后面的指令。
和 jmp near start 一样,loop digit 后跟的操作数也是一个相对的偏移量,是在编译阶段,编译器用标号 digit 所在位置的汇编地址减去 loop 指令的汇编地址,再减去 loop 指令的长度( 2 )来得到的。
;计算各个数位
mov bx,ax
mov cx,5 ;设置循环次数
mov si,10 ;除数
digit:
xor dx,dx
div si
mov [bx],dl ;保存数位
inc bx
loop digit
图为 lst 文件的内容。
上面 loop 指令的操作数0xF7,编译阶段是这么算出来的。0x43 - 0x4A - 0x2 = -9,而-9 截取一个字节的话,就是 F7.
现在的问题是 cpu 是如何使用 loop 指令的操作数的?我是这么猜的:
- 取出 loop 指令自己所在地址的低 8bit 4A ,然后
0x4A + F7 + 2 = 0x143 - 然后对 0x143 截取低 8bit ,为 0x43
- 然后把自己的地址
0x0000_004A的低 8bit 替换为算出来的0x43,得到 要跳转的地址0x0000_0043
不知道对不对?