标题:
请帮忙看看以下代码哪里出了问题:
[打印本页]
作者:
武骧金星
时间:
2010-3-6 06:07
标题:
请帮忙看看以下代码哪里出了问题:
004CE7B6 8B4D FC MOV ECX,DWORD PTR SS:[EBP-4]
004CE7B9 8A51 01 MOV DL,BYTE PTR DS:[ECX+1]
004CE7BC 8BCA MOV ECX,EDX
004CE7BE 6BC9 24 IMUL ECX,ECX,24
004CE7C1 81C1 502C4B00 ADD ECX,Ekd5.004B2C50
004CE7C7 E8 A40EF9FF CALL Ekd5.0045F670
这段代码在CALL 45F670时会出现以下的问题:(以下是单步步过的结果)
0045F670 /$ 55 PUSH EBP
0045F671 |. 8BEC MOV EBP,ESP
0045F673 |. 51 PUSH ECX
0045F674 |. 894D FC MOV DWORD PTR SS:[EBP-4],ECX
0045F677 |. 8B45 FC MOV EAX,DWORD PTR SS:[EBP-4]
0045F67A |. 8B00 MOV EAX,DWORD PTR DS:[EAX]
//访问违规: 读取[0A94AE14]
0045F67C |. 8BE5 MOV ESP,EBP
0045F67E |. 5D POP EBP
0045F67F \. C3 RETN
请问这可能是由于什么原因?谢谢。
[
本帖最后由 武骧金星 于 2010-3-6 06:22 编辑
]
作者:
godtype
时间:
2010-3-6 07:59
在004CE7B9这里加一个断点(F2),看一下从[EBP-4]输出到ECX的值是多少。
作者:
武骧金星
时间:
2010-3-6 12:34
……真奇怪,这时ECX的值是004927F0,应该是没问题的……
可是接下去几步后ECX就变成那个违规调用的内存位置了……
[
本帖最后由 武骧金星 于 2010-3-6 13:02 编辑
]
作者:
武骧金星
时间:
2010-3-6 13:12
经过仔细研究发现:原来代码应该改成这个样子:
004CE7B6 8B4D FC MOV ECX,DWORD PTR SS:[EBP-4]
004CE7B9 8A51 01 MOV DL,BYTE PTR DS:[ECX+1]
004CE7BC 8BCA MOV ECX,EDX
在这里插一条: AND ECX, 0FF
004CE7BE 6BC9 24 IMUL ECX,ECX,24
004CE7C1 81C1 502C4B00 ADD ECX,Ekd5.004B2C50
这样就行了……
不过,能不能在技术上解释一下这里出问题的原因呢?谢谢。
作者:
godtype
时间:
2010-3-6 15:36
嗯,我开头也没有注意看。
因为 MOV DL,BYTE PTR DS:[ECX+1] 是单字节,而 MOV ECX,EDX 是四字节,所以要进行零扩展。
也可以改成以下几种方式:
1、在MOV DL,BYTE PTR DS:[ECX+1]的前面加一条XOR EDX,EDX
2、将MOV DL,BYTE PTR DS:[ECX+1]改成MOVZX EDX,BYTE PTR DS:[ECX+1]
以上两种都可以省去AND ECX,0FF
3、
MOV EDX,DWORD PTR SS:[EBP-4]
MOVZX ECX,BYTE PTR DS:[EDX+1]
这样还可以省多一条MOV ECX,EDX
4、将
AND ECX, 0FF
IMUL ECX,ECX,24
ADD ECX,Ekd5.004B2C50
写成一个自定义函数,直接CALL就是了,这样以后在其他地方修改也更方便一些。
欢迎光临 轩辕春秋文化论坛 (http://www.xycq.org.cn/forum/)
Powered by Discuz! 5.0.0