检测点10.4
本帖最后由 丶Haw 于 2012-8-1 00:02 编辑检测点10.4下面的程序执行后,ax中的数值为多少?内存地址 机器码 汇编指令 执行后情况1000:0 b8 06 00 mov ax,6 ax=6,ip指向1000:31000:3 ff d0 call ax pop ip,ip指向1000:6 这里的IP为什么是6?为什么不是下面说的先将该指令后的第一个字节偏移地址ip入栈1000:5 40 inc ax1000:6 58 mov bp,sp bp=sp=fffehSP的值是从哪里来的? add ax, ax==6+5=0bh 为什么 ds:(fffeh)的值是5?用debug进行跟踪确认,“call ax(16位reg)”是先将该指令后的第一个字节偏移地址ip入栈,再转到偏移地址为ax(16位reg)处执行指令。 刚才看到一帖子,call ax的解如下,我觉得不对,call ax ;将下一条指令的IP=0005压入栈,此时栈顶应该是sp=FFFE , 因为AX=0006,然后跳转(位移)到1000:0006,
这里跳到1000:0006 是因为 ax=0006? 如果ax=ffff,那不是直接跳到1000:ffff? ip不是call ax(16位reg)”是先将该指令后的第一个字节偏移地址ip入栈?
call 16位 reg相当于
push ip (这步是把该指令后的第一个字节偏移地址ip入栈,你说的没错,比如这题就是把call后面的指令的第一个字节偏移0005h入栈,这里题目没设栈段你就想它把ip存到了一个系统给的小房子里,但是这个小房子的地址我们没必要知道,以后pop一下就出来了)
jump 16位reg (已经把ip的值保存下来了,就可以跳转到reg寄存器存储的地方去执行命令了,比如这题reg寄存器是ax,里面存的值是0006h,以后要回来ret一下就好了。)
你的第一个疑问:
1000:3 ff d0 call ax pop ip,ip指向1000:6 这里的IP为什么是6?为什么不是下面说的先将该指令后的第一个字节偏移地址ip入栈
解释是:call是有两个步骤的,先保存,再跳转,先把ip=0005h,保存入栈。然后再跳转到,ax寄存器里面值,就是把ip修改为ax里面的值,如果ax=0ffffh,那么call完后,系统确实要跳到ip=ffffh处执行命令哦给你看我刚刚的debug图只不过你call完后你能不能回来呢?呵呵。也就是说你不知道ip=ffffh后指令是啥了。
你的第二个疑问:
1000:6 58 mov bp,sp bp=sp=fffeh SP的值是从哪里来的?
你的这个疑问明显是对栈不了解啊。因为刚刚不是call了吗?call的第一步就是把call指令后的第一个字节偏移地址ip入栈啊。入栈肯定要知道栈顶在哪儿,也就是sp呢?sp开始系统默认是0000h,入栈也是两步哦。sp先减2(0-2=0fffeh),然后把ip的值存入ss:sp 指向的内存单元,ss:sp此时指向新栈顶。也就是说此时ss:0fffeh里面保存的值是ip(刚刚说的ip=0005h)。这步执行完了,就是bp=sp=0fffeh。这段看不懂的话,去看书P60。
你的第三个疑问:
add ax, ax==6+5=0bh 为什么 dsfffeh)的值是5
注意一下,bp默认的寄存器是ss哦,不是ds,是栈段寄存器。刚刚上面解释了,ss:0fffeh里面保存的值是ip,这个ip是call指令后的第一个字节的ip=0005h。
{:5_96:}解释的不好。
lukelqz 发表于 2012-7-31 23:43 static/image/common/back.gif
call 16位 reg相当于
push ip (这步是把该指令后的第一个字节偏移地址ip入栈,你说的没错,比如这题就是 ...
非常感谢 ,解释得很好,很强大! 丶Haw 发表于 2012-8-1 12:55 static/image/common/back.gif
非常感谢 ,解释得很好,很强大!
{:5_102:}不谢。互助哈 1000:3 ff d0 call ax pop ip,ip指向1000:6
你 看答案了吧,答案都有写错了,是PUSH ip,push的时候sp由0000指向fffeh,然后把现在ip内的值,即下一行代码0005存入1000:fffe中,存入后就直接跳到ax的偏移中去,即下一行代码"mov bp,sp"
而sp由于push了一下,所以变为-2,即补码为fffe,下一行意思是把1000:fffe内的值,即之前push的ip值与0005相加,即为000bh 学到了
页:
[1]