第10章 CALL 和 RET 指令


    call和ret指令都是转移指令,它们都 修改IP,或同时修改CS和IP

10.1 ret 和 retf

ret指令用栈中数据, 修改IP的内容,从而实现近转移;执行下面两步操作:
(1) (IP)=((ss)*16+(sp))
(2) (sp)=(sp)+2
retf指令用栈中数据, 修改CS和IP的内容,从而实现远转移;执行下面4步操作:
(1) (IP)=((ss)*16+(sp))
(2) (sp)=(sp)+2
(3) (CS)=((ss)*16+(sp))
(4) (sp)=(sp)+2



10.2 call 指令

CPU执行call指令时,进行两步操作:
(1) 将当前的IP或CS和IP压入栈中
(2) 转移

    call指令不能实现短转移,除此之外,call指令实现转移的方法和jmp指令的原理相同。




10.3 依据位移进行转移的 call 指令

“call 标号”,执行时进行如下操作:
(1) (sp)=(sp)-2 ((ss)*16+(sp))=(IP)
(2) (IP)=(IP)+16位位移

    16位位移 = 标号处的地址 - call指令后第一个字节的地址;
    16位位移的范围为:-32768~32767
    16位位移由编译程序在编译时算出


    用汇编语法来解释此种格式的call指令,相当于“push IP ;jmp near ptr 标号”


10.4 转移的目的地址在指令中的 call 指令

“call far ptr 标号”,执行时进行如下操作:
(1) (sp)=(sp)-2 ((ss)*16+(sp))=(CS) (sp)=(sp)-2 ((ss)*16+(sp))=(IP)
(2) (CS)=标号所在段的段地址 (IP)=标号在段中的偏移地址

    用汇编语法解释此种格式的call指令,相当于“push CS;push IP;jmp far ptr 标号”


10.5 转移地址在寄存器中的 call 指令

“call reg(16位)”,执行时进行如下操作:
(1) (sp)=(sp)-2 ((ss)*16+(sp))=(IP)
(2) (IP)=(16位reg)

    用汇编语法解释此种格式的命令,相当于“push IP; jmp 16位reg”


10.6 转移地址在内存中的 call 指令

“call word ptr 内存单元地址”,用汇编语法来解释此种格式的 call 指令,相当于:
push IP
jmp word ptr 内存单元地址
“call dword ptr 内存单元地址”,用汇编语法来解释此种格式的 call 指令,相当于:
push CS
push IP
jmp dword ptr 内存单元地址

    这一节的监测点10.5中问题一,如果你通过debug单步跟踪是得不到正确结果的,关键步骤就是“call word ptr ds:[0eh]”如果你单步执行,中断时,必然将eflags cs ip都要入栈保存,哪怕你没通过push指令进行入栈操作,这就破坏了栈数据导致程序不能按照原代码执行,得不到结果。直接执行或者通过debug的g命令,运行到最后再查看ax中数据,就会得到正确结果ax=3


10.7 call 和 ret 的配合使用

    写一个具有一定功能的程序段,称其为子程序,在需要时,用call指令转去执行。可是执行完子程序后,如何让CPU接着call指令向下执行? call指令转去执行子程序之前,call指令后面的指令地址将存储在栈中,所以可在子程序的后面使用ret指令,用栈中的数据设置IP的值,从而转到call指令后面的代码处继续执行。
    我们可以利用call和ret来实现子程序的机制。


    学到后面发现jmp和call两个指令我还是有点模糊,特别是jmp指令,我总容易忽略它。这里补充点东西强化以下对这两个指令的理解。

jmp call ret
转移指令 转移指令 转移指令
可以只修改IP或同时修改CS、IP 可以只修改IP或同时修改CS、IP 可以只修改IP或同时修改CS、IP
分为段内转移(只修改IP)和段间转移(同时修改CS和IP) 分为段内转移(只修改IP)和段间转移(同时修改CS和IP) ret只修改IP,retf同时修改CS、IP
针对修改IP范围的不同,段内转移分为:短转移(8位)和近转移(16位) 段内转移只有近转移一种(16位) 与call类似,不会依据修改IP的范围再区分
转移之后无需返回
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值