CE和OD配合找大闹天宫游戏基址

2023-10-21 10:40:19 浏览数 (1)

使用CE的传统方法找基址一般是先搜到内存地址以后,然后再查看是什么代码访问或者改写了该地址,再根据这行代码中的地址和偏移量一步步查找,例如我分析大闹天宫时,代表锁鱼类型的内存地址是:0x9BAFB28,然后查看改写这个地址的代码是:

00C9B75C  |.  8B4C90 58     mov ecx,dword ptr ds:[eax edx*4 0x58]    ; 

再往前找:

00C9B755  |.  8B43 7C       mov eax,dword ptr ds:[ebx 0x7C]          ; 

然后再按照这种方法找就找不出什么准确的内容了。 使用CE找基址这时候陷入困境。实在没办法,用OD找找看,先附加游戏进程,然后定位到上面的代码,如图:

大闹天宫找基址

可以看出,这个基址的关键是EBX(099F4B00),附近没有改写EBX的代码。然后按CTRL F9运行到返回,然后找到这个代码块的call地址,再进入这个call看看开头,发现给EBX赋值的是:mov ebx,dword ptr ss:[ebp 0x8],ebp 0x8也就是这个call的第一个参数,再返回调用这个call的指令处查看:

大闹天宫找基址

发现这个参数是EBP传入的,也就是要找的基址EBX等于此处的EBP,而EBP一般只在子程序的开头赋值,所以再CTRL F9运行到返回,然后F7单步补进一下,停留在下图这个地方:

大闹天宫找基址

发现上面的call是call eax,call地址不是一个确定的数字,不能直接进入。在此处下断,然后F7进入,看到下面代码:

大闹天宫找基址

,发现EBP的值来自ECX,然后返回刚才的call eax处再看,发现:

00C87400  |.  8B08          mov ecx,dword ptr ds:[eax]

ECX的值是来自[eax],再记录一下关系,免得一会步数太多,记不清了。此时要找的基址=[EAX]

这个EAX是怎么来的呢,在他上面最近的一个call处下断分析:

大闹天宫找基址

很明显,eax的值来自这个call,进入看一下:

大闹天宫找基址

因为函数返回值总是用eax来返回,这个eax应该在该子程序最下面,所以从下往上找,依次找到:

00C84089  |.  8BC6          mov eax,esi

00C84076  |> 8D77 FC       lea esi,dword ptr ds:[edi-0x4]

00C8403F  |.  8B7E 10       mov edi,dword ptr ds:[esi 0x10]

注意这是从下到上的顺序,分析得到:EAX=ESI=[EDI-4]=[[ESI 0X10]-4],找到这里,感觉差不多了,因为不像刚才那样都是call之间直接传值的样子,先用CE搜一下这个ESI的值:708cf8,如果CE还是找不到基址再回OD继续找。

大闹天宫找基址

在CE中搜到3个地址,有一个地址是绿的(绿色是静态地址,一般就是基址),查看一下这个静态地址,是:dntg2.exe 87F18,说明基址找到了。最终这个ebx=[[[[dntg2.exe 87F18] 0x10]]-4]

进而找到锁鱼类型的基址:

大闹天宫找基址

分析:为什么有时候用CE不能直接找到基址?感觉是因为CE只能查找全部通过[寄存器 偏移]这种形式访问的基址,如果在基址传递过程中有其他的形式,用CE就不好找了。就像这个例子,[[[dntg2.exe 87F18] 0x10]]-4这个值先是给了EAX,然后通过[eax]给ebp,再调用call又给ebx,这些都是直接在寄存器之间互相传值,所以CE的“查看什么指令访问了内存地址”就没有用了,因为寄存器之间传递值不会访问内存。这时候就只能用OD下断分析这些值具体的来源了。当然,CE也有简单的下断、运行到返回、步进、步过等功能,就是功能相对很简单,不如OD强大。

以上分析过程是我个人长时间琢磨出来的,自己记录一下,以后遇到类似问题可以座位参考。网上有其他刚入门的小白也可以参考一下。本人也是小白,深知没有师傅的情况下研究这些问题有多么困难,希望有志同道合的朋友来一起交流。

0 人点赞