日期:2014-05-16  浏览次数:20575 次

OllyDBG 入门系列(四)-内存断点

【原创】OllyDBG 入门系列(四)-内存断点
<!-- PHPForce - Joey修改性别 --><!-- /PHPForce - Joey修改性别 -->CCDebuger 当前离线

<!-- / icon and title --><!-- message --><!--Joey 修改防止撑破表格 -->
标 题: 【原创】OllyDBG 入门系列(四)-内存断点
作 者: CCDebuger
时 间: 2006-02-15,23:22:00
链 接: http://bbs.pediy.com/showthread.php?t=21378

<!-- google_ad_section_start -->OllyDBG?入门系列(四)-内存断点

作者:CCDebuger

还记得上一篇《OllyDBG?入门系列(三)-函数参考》中的内容吗?在那篇文章中我们分析后发现一个?ESI?寄存器值不知是从什么地方产生的,要弄清这个问题必须要找到生成这个?ESI?值的计算部分。今天我们的任务就是使用?OllyDBG?的内存断点功能找到这个地方,搞清楚这个值是如何算出来的。这次分析的目标程序还是上一篇的那个?crackme,附件我就不再上传了,用上篇中的附件就可以了。下面我们开始:
还记得我们上篇中所说的关键代码的地方吗?温习一下:

00401323?|.?E8?4C010000?????????CALL?<JMP.&USER32.GetWindowTextA>???????????;?GetWindowTextA
00401328?|.?E8?A5000000?????????CALL?CrackHea.004013D2??????????????????????;?关键,要按F7键跟进去
0040132D?|.?3BC6????????????????CMP?EAX,ESI?????????????????????????????????;?比较
0040132F?|.?75?42???????????????JNZ?SHORT?CrackHea.00401373?????????????????;?不等则完蛋

我们重新用?OllyDBG?载入目标程序,F9运行来到上面代码所在的地方(你上次设的断点应该没删吧?),我们向上看看能不能找到那个?ESI?寄存器中最近是在哪里赋的值。哈哈,原来就在附近啊:
/UpLoads/images/sjkjc/20140516060350286293.gif?
我们现在知道?ESI?寄存器的值是从内存地址?40339C?中送过来的,那内存地址?40339C?中的数据是什么时候产生的呢?大家注意,我这里信息窗口中显示的是?DS:[0040339C]=9FCF87AA,你那可能是?DS:[0040339C]=XXXXXXXX,这里的?XXXXXXXX?表示的是其它的值,就是说与我这里显示的?9FCF87AA?不一样。我们按上图的操作在数据窗口中看一下:
/UpLoads/images/sjkjc/20140516060350218093.gif?
从上图我们可以看出内存地址?40339C?处的值已经有了,说明早就算过了。现在怎么办呢?我们考虑一下,看情况程序是把这个值算出来以后写在这个内存地址,那我们要是能让?OllyDBG?在程序开始往这个内存地址写东西的时候中断下来,不就有可能知道目标程序是怎么算出这个值的吗?说干就干,我们在?OllyDBG?的菜单上点?调试->重新开始,或者按?CTR+F2?组合键(还可以点击工具栏上的那个有两个实心左箭头的图标)来重新载入程序。这时会跳出一个“进程仍处于激活状态”的对话框(我们可以在在调试选项的安全标签下把“终止活动进程时警告”这条前面的勾去掉,这样下次就不会出现这个对话框了),问我们是否要终止进程。这里我们选“是”,程序被重新载入,我们停在下面这一句上:

00401000?>/$?6A?00??????????????PUSH?0??????????????????????????????????????;?pModule?=?NULL

现在我们就要来设内存断点了。在?OllyDBG?中一般我们用到的内存断点有内存访问和内存写入断点。内存访问断点就是指程序访问内存中我们指定的内存地址时中断,内存写入断点就是指程序往我们指定的内存地址中写东西时中断。更多关于断点的知识大家可以参考?论坛精华7->基础知识->断点技巧->断点原理?这篇?Lenus?兄弟写的《如何对抗硬件断点之一?---?调试寄存器》文章,也可以看这个帖:http://bbs.pediy.com/showthread.php?threadid=10829。根据当前我们调试的具体程序的情况,我们选用内存写入断点。还记得前面我叫大家记住的那个?40339C?内存地址吗?现在我们要用上了。我们先在?OllyDBG?的数据窗口中左键点击一下,再右击,会弹出一个如下图所示的菜单。我们选择其中的转到->表达式(也可以左键点击数据窗口后按?CTR+G?组合键)。如下图:
/UpLoads/images/sjkjc/20140516060350963001.gif?
现在将会出现这样一个对话框:
?
我们在上面那个编辑框中输入我们想查看内容的内存地址?40339C,然后点确定按钮,数据窗口中显示如下:
/UpLoads/images/sjkjc/20140516060351785385.gif?
我们可以看到,40339C?地址开始处的这段内存里面还没有内容。我们现在在?40339C?地址处后面的?HEX?数据或?ASCII?栏中按住左键往后拖放,选择一段。内存断点的特性就是不管你选几个字节,OllyDBG?都会分配?4096?字节的内存区。这里我就选从?40339C?地址处开始的四个字节,主要是为了让大家提前了解一下硬件断点的设法,因为硬件断点最多只能选?4?个字节。选中部分会显示为灰色。选好以后松开鼠标左键,在我们选中的灰色部分上右击:
/UpLoads/images/sjkjc/20140516060351205187.gif?
经过上面的操作,我们的内存断点就设好了(这里还有个要注意的地方:内存断点只在当前调试的进程中有效,就是说你如果重新载入程序的话内存断点就自动删除了。且内存断点每一时刻只能有一个。就是说你不能像按?F2?键那样同时设置多个断点)。现在按?F9?键让程序运行,呵,OllyDBG?中断了!

7C932F39?8808???????????????????MOV?BYTE?PTR?DS:[EAX],CL????????????????????;?这就是我们第一次断下来的地方
7C932F3B?40?????????????????????INC?EAX
7C932F3C?4F?????????????????????DEC?EDI
7C932F3D?4E??????