- UID
- 2198
注册时间2005-6-29
阅读权限255
最后登录1970-1-1
副坛主
该用户从未签到
|
PEiD测壳:UPX 0.89.6 - 1.02 / 1.05 - 1.24 (Delphi) stub -> Markus & Laszlo [Overlay]
注意这里,壳的尾部多了一个[Overlay]。意思就是说程序有尾部数据,脱壳后需要把附加数据补到程序尾部才能运行。
关于尾部数据的处理,我们可以使用很多工具进行修复:
1.在使用使用PEiD测壳的同时,使用其插件“ExtOverlay Plugin”取出尾部数据,我们将得到一个后缀名为“.OVR”的文件,再使用MergeOverlay将PEid插件分离出的.OVR文件增添到我们Dump下来的文件中。
可以到这里下载:MergeOverlay
2.使用WinHex手动添加尾部数据。飘云以前制作过使用WinHex手动修复的视频教程。大家可以到该帖中下载:
提醒大家的是我们使用的WinHex一定要使用安装版,使用绿色版(就是不经过安装直接解压)可能导致以下过程无法正常实现:在Dump下来的文件尾部“0000”代码上右键“编辑-减切版数据-写入-文件另存为”。
WinHex 13.2 SR-11 汉化版(推荐):http://www.newhua.com/soft/1509.htm
WinHex 13.8 SR-4 英文原版:http://www.newhua.com/soft/1510.htm
3.使用“Overlay最终版”这个工具,无须分离尾部数据文件,直接从原文件中提取并添加到我们Dump下的文件中,一步搞定。
Overlay 最终版2下载:http://www.cqsn.net/soft/download/Overlay.rar
更多关于Overlay的资料,大家可以参看看雪论坛Lenus的这篇文章:浅谈脱壳中的附加数据问题(overlay)
由于第一次调试这个软件的时候,只注意了下壳是UPX,没有看到[Overlay],导致在脱壳文件的修复上绕了大弯。这里就和大家简单的说一下这其中所走的弯路。权当是一篇去NAP思路和问题处理思路。
UPX的壳,使用ESP定律简单脱之,LoadPE Dump文件,ImportREC(简称IR)修复。修复后的文件名:dumped_.exe
PEiD再查壳:Borland Delphi 6.0 - 7.0
运行修复后的文件,弹出一个NAP窗口。一般文件缺失尾部数据都是弹出一个“Error”的警告窗口。而该软件弹出的文字提示,伪装的更象是一个NAG。于是我的思路肯定是先搞定该Nag再说。
我们OD载入脱壳后的程序,使用插件搜索软件的ASCII,找到关键字符:
0049A983 FF57 0C call dword ptr ds:[edi+C] ; 我们在这里下断点
0049A986 8B7D FC mov edi,dword ptr ss:[ebp-4] ; 这里是从文件尾部数据中取出最后一个字的数值在下一行代码进行比较,来判断文件是否有尾部数据,即是否被脱壳。
0049A989 81FF 97130000 cmp edi,1397 ; 我们注意这里的“1397”这个数值
0049A98F 74 40 je short dumped_.0049A9D1 ; 我们注意这个跳转,如果跳走,则不弹出NAG(将je修改为jmp)
0049A991 6A 00 push 0
0049A993 8D4D E8 lea ecx,dword ptr ss:[ebp-18]
0049A996 33D2 xor edx,edx
0049A998 8BC7 mov eax,edi
0049A99A E8 91E0F6FF call dumped_.00408A30
0049A99F 8B4D E8 mov ecx,dword ptr ss:[ebp-18]
0049A9A2 8D45 EC lea eax,dword ptr ss:[ebp-14]
0049A9A5 BA 90AA4900 mov edx,dumped_.0049AA90 ; 双击来到这里,显然从这以下将弹出Nap窗口
0049A9AA E8 D59AF6FF call dumped_.00404484
0049A9AF 8B45 EC mov eax,dword ptr ss:[ebp-14]
0049A9B2 66:8B0D E4AA4900 mov cx,word ptr ds:[49AAE4]
0049A9B9 B2 01 mov dl,1
0049A9BB E8 8483F9FF call dumped_.00432D44
0049A9C0 A1 AC024A00 mov eax,dword ptr ds:[4A02AC]
0049A9C5 8B00 mov eax,dword ptr ds:[eax]
0049A9C7 E8 C4D5FDFF call dumped_.00477F90
0049A9CC E9 8C000000 jmp dumped_.0049AA5D
0049A9D1 8BC3 mov eax,ebx ; 上方的跳转来到这里
0049A9D3 8B10 mov edx,dword ptr ds:[eax]
0049A9D5 FF12 call dword ptr ds:[edx]
0049A9D7 8BF8 mov edi,eax
0049A9D9 2B7D F0 sub edi,dword ptr ss:[ebp-10]
0049A9DC 89BE 44030000 mov dword ptr ds:[esi+344],ed>
0049A9E2 33C9 xor ecx,ecx
0049A9E4 8BD7 mov edx,edi
0049A9E6 8BC3 mov eax,ebx
0049A9E8 8B38 mov edi,dword ptr ds:[eax]
0049A9EA FF57 14 call dword ptr ds:[edi+14]
0049A9ED 8BD3 mov edx,ebx
0049A9EF 8BC6 mov eax,esi
0049A9F1 E8 6E030000 call dumped_.0049AD64 ; OD载入原程序,跟进该CALL发现这里进行了很多数据的传递
0049A9F6 8BD3 mov edx,ebx
0049A9F8 8BC6 mov eax,esi
0049A9FA E8 31F4FFFF call dumped_.00499E30 ; 程序运行到这里,弹出第二个NAG。OD载入原程序到该CALL时,在这里并不弹出窗口
由于去掉NAG后,又出现一NAG。只好用另一个OD载入原程序,看看两个CALL中到底是进行了什么操作,导致Dunp的程序弹出NAG。
OD进入原程序后,跟进该行0049A9F1,发现其中进行了很多文字数据的传递,而我们Dump的文件中该Call却没有什么数据的传递。
0049A9F1 E8 6E030000 call dumped_.0049AD64 ; OD载入原程序,跟进该CALL发现这里进行了很多数据的传递
接着跟进下一个CALL,发现
0049A9FA E8 31F4FFFF call dumped_.00499E30 ; 程序运行到这里,弹出第二个NAG。OD载入原程序到该CALL时,在这里并不弹出窗口
我们跟进该CALL:
00499E30 55 push ebp
00499E31 8BEC mov ebp,esp
……
……
00499E95 8B80 48030000 mov eax,dword ptr ds:[eax+348>
00499E9B E8 58E2FFFF call dumped_.004980F8 ; 跟进该CALL看看
00499EA0 84C0 test al,al ; 这里有标志位AL的比较,所以上方的CALL是设置标志位的关键
00499EA2 75 45 jnz short dumped_.00499EE9 ; 这里是第二个NAG的关键跳转 (跳走则躲过第二个NAG 这里我们修改上方关键CALL中的标志位设置 修改方法见下文)
00499EA4 8B4D FC mov ecx,dword ptr ss:[ebp-4]
……
……
跟进00499E9B,修改此代码:
00498150 0F94C0 sete al ; 将其修改为setne al (标志位暴破的修改方式之一,我们在暴破一章有详细讲解)
但是我们修改之后,程序虽然没有第二个NAG出现,但是程序出现异常,无法继续运行。
分析:我们在使用OD调试原程序时,跟入这两处0049A9F1、0049A9FA时发现,这两个CALL不仅有数据的处理,还有MD的验证。这就使我有点晕了,莫非软件和天网一样,还对原文件进行MD5的验证?使用Crypt Tool工具查看一下软件使用的算法,发现确实有MD存在。如果真的有MD的验证,那么修复起来可就不容易了。
后来在几位朋友的提示下,才恍然大悟。原来是尾部数据的缘故。汗死我,软件的作者太高明了,用几个NAG让大家来忽视对尾部数据的处理。
修复一下尾部数据,OK,现在程序可以运行了。我们来思考下,软件是怎样发现程序缺少了尾部数据的?
还记得第一个NAG出现时上方的代码吗?
0049A989 81FF 97130000 cmp edi,1397 ; 我们注意这里的“1397”这个数值
我们现在用WinHEX来打开修复好的文件,查看文件的尾部,就会发现文件的最后一个字是“1397”。呵呵,相信这下大家明白了软件是怎么弹出第一个NAP了。
OK,下一部呢,我们就是下断破解这个软件了,这个软件的在注册部分使用了N多的指针,导致想使用API函数下断点并不容易,这里我们使用OD的插件“万能断点”来下断。
我们OD载入程序,运行到注册对话框,输入假码:chinapyg ,然后下万能断点。
下断后,点确定,程序被OD断了下来。OD断在了系统领空,我们在寄存器窗口ESI寄存器中看到了我们输入的假码。
77D3353D F3:A5 rep movs dword ptr es:[edi], dword ptr [esi] ;OD断在了这里。我们F8单步向下
77D3353F 8BC8 mov ecx, eax
77D33541 83E1 03 and ecx, 3
77D33544 F3:A4 rep movs byte ptr es:[edi], byte ptr [esi]
77D33546 E8 E3FBFFFF call 77D3312E
77D3354B 5F pop edi
77D3354C 5E pop esi
77D3354D 8BC3 mov eax, ebx
77D3354F 5B pop ebx
77D33550 5D pop ebp
77D33551 C2 1000 retn 10
我们一路F8单步,几次返回后来到程序领空;
0045C6DC 8943 0C mov [ebx+C], eax
0045C6DF 8B03 mov eax, [ebx]
0045C6E1 83F8 0C cmp eax, 0C
……
到了程序领空就好办事了,我们继续F8单步跟踪,直到来到这里;
00498779 |. 8B45 FC mov eax, [ebp-4] ; F8直到程序运行到这里 我们可以看到EAX寄存器中我们输入的假码
0049877C |. 50 push eax
0049877D |. 8D55 F8 lea edx, [ebp-8]
00498780 |. 8BC3 mov eax, ebx
00498782 |. 8B08 mov ecx, [eax]
00498784 |. FF91 F8000000 call [ecx+F8] ; 该CALL取出我们的机器码 接下来呢就要进入算法了哦
0049878A |. 8B45 F8 mov eax, [ebp-8] ; 这里看到我们软件的机器码
0049878D |. 8B8B 20030000 mov ecx, [ebx+320] ; 取出一固定值fanren529送ECX中 肯定是参与算法运算的
00498793 |. 5A pop edx
00498794 |. E8 B7ECFFFF call 00497450 ; 上方取出了几个固定值 接下来就要计算了 通过看寄存器窗口 我们也能感觉到这里就是算法CALL 我们跟进算法CALL
00498799 |. 8BD8 mov ebx, eax
0049879B |. 33C0 xor eax, eax
0049879D |. 5A pop edx
0049879E |. 59 pop ecx
0049879F |. 59 pop ecx
004987A0 |. 64:8910 mov fs:[eax], edx
004987A3 |. 68 BD874900 push 004987BD
004987A8 |> 8D45 F8 lea eax, [ebp-8]
004987AB |. BA 02000000 mov edx, 2
004987B0 |. E8 E7B9F6FF call 0040419C
004987B5 \. C3 retn
跟进算法CALL:
00497459 |. 53 push ebx
0049745A |. 56 push esi
0049745B |. 57 push edi
0049745C |. 33DB xor ebx, ebx
0049745E |. 895D FC mov [ebp-4], ebx
00497461 |. 8BF9 mov edi, ecx
00497463 |. 8BF2 mov esi, edx
00497465 |. 8BD8 mov ebx, eax
00497467 |. 33C0 xor eax, eax
00497469 |. 55 push ebp
0049746A |. 68 B7744900 push 004974B7
0049746F |. 64:FF30 push dword ptr fs:[eax]
00497472 |. 64:8920 mov fs:[eax], esp
00497475 |. 8D8D FCFEFFFF lea ecx, [ebp-104]
0049747B |. 8BD7 mov edx, edi
0049747D |. 8BC3 mov eax, ebx
0049747F |. E8 64FEFFFF call 004972E8 ; 这里跟进 是关键算法II 由于软件是明码 不再继续分析算法部分
00497484 |. 8D95 FCFEFFFF lea edx, [ebp-104] ; OK 我们在这里看到数据窗口已经出现了软件正确的注册码
0049748A |. 8D45 FC lea eax, [ebp-4] ; 真码进EDX中
0049748D |. E8 4ACFF6FF call 004043DC
00497492 |. 8B45 FC mov eax, [ebp-4]
00497495 |. 8BD6 mov edx, esi ; 真码进EXA中
00497497 |. E8 E8D0F6FF call 00404584 ; 假码进EDX中 该CALL比较注册码正确与否
0049749C 0F94C0 sete al ; 设置标志位 暴破的关键点 修改为setne al
0049749F |. 8BD8 mov ebx, eax ; 经过sete设置标志位后,EAX数值为1 这里我们注意EAX数值的移动
004974A1 |. 33C0 xor eax, eax ; EAX数值移动到EBX中 这里清空EBX
004974A3 |. 5A pop edx
004974A4 |. 59 pop ecx
004974A5 |. 59 pop ecx
004974A6 |. 64:8910 mov fs:[eax], edx
004974A9 |. 68 BE744900 push 004974BE
004974AE |> 8D45 FC lea eax, [ebp-4]
004974B1 |. E8 C2CCF6FF call 00404178
004974B6 \. C3 retn
004974B7 .- E9 C0C6F6FF jmp 00403B7C
004974BC .^ EB F0 jmp short 004974AE
004974BE . 8BC3 mov eax, ebx ; 这里又将EBX保存的标志位数值回送到EAX中
004974C0 . 5F pop edi ; 游戏外挂.004997A4
004974C1 . 5E pop esi
004974C2 . 5B pop ebx
004974C3 . 8BE5 mov esp, ebp
004974C5 . 5D pop ebp
004974C6 . C3 retn
0049882E |. 8B15 ACFF4900 mov edx, [49FFAC] ; 算法Call出来 返回到这里
00498834 |. 8802 mov [edx], al ; 这里比较标志位AL
00498836 |. A1 ACFF4900 mov eax, [49FFAC]
0049883B |. 8038 00 cmp byte ptr [eax], 0 ; 暴破这里也可以 将0修改为1,因为刚才sete设置AL标志位后 使eax数值为1
0049883E |. 75 19 jnz short 00498859 ; 该跳转应该就是关键跳 不等则跳走,若不跳提示注册失败 暴破这里也可以jnz修改为nz
00498840 |. 6A 00 push 0
00498842 |. A1 00044A00 mov eax, [4A0400]
00498847 |. 8B00 mov eax, [eax]
00498849 |. 66:8B0D C0884900 mov cx, [4988C0]
00498850 |. B2 01 mov dl, 1
00498852 |. E8 EDA4F9FF call 00432D44 ; 这里提示软件注册码错误
00498857 |. EB 3E jmp short 00498897
软件注册信息保存到这里:
HKEY_USERS\S-1-5-21-746137067-484061587-682003330-500\Software\eBook Edit Pro\Login\97E55762
破解总结:
总体上来说,该软件的加密体系还是很不错的,至少在04年的时候,我们还没有如此多优秀的工具辅助下,破解这个软件还是需要一定时间的。从暴破角度上将,该软件的暴破还没那么简单,修改修改的地方还有很多,上方给出的几个暴破点只限于注册时可以使注册成功而已,如果大家对暴破和算法感兴趣,可继续研究下。如果软件设置算法部分时,设计成非明码比较的软件,势必增加解密难度。
从上文分析的几处出现真码的地方,都可以做内存注册机,如00497497 |. E8 E8D0F6FF call 00404584 ; 假码进EDX中 该CALL比较注册码正确与否 |
|