菜鸟脱arm的Debug-Blocker+CopyMem-II+Memory-Patching+Better/Slower Compression
 

破文作者:四库全书
发表时间:2006-3-19 09:14
链接地址:http://www.unpack.cn/viewthread.php?tid=3544

用armgfindprotected工具检测内容如下:

!- Protected Armadillo

<Protection Options> Debug-Blocker CopyMem-II Enable Memory-Patching Protections

<Backup Key Options> Fixed Backup Keys

<Compression Options> Better/Slower Compression !- Child detach Child process ID: 00000D20 Entry point: 00736363 Original bytes: 558B

虽然有Enable Memory-Patching Protections,但是如果使用修改版的od,直接把它当做CopyMem-II来脱就行!这个没有code,只有iat,所以简单些

od载入,忽略所有异常,隐藏od

00736363 >/$ 55 PUSH EBP 00736364 |. 8BEC MOV EBP,ESP 00736366 |. 6A FF PUSH -1 00736368 |. 68 200B7600 PUSH fotobatc.00760B20 0073636D |. 68 A0607300 PUSH fotobatc.007360A0 ; SE 处理程序安装 00736372 |. 64:A1 0000000>MOV EAX,DWORD PTR FS:[0] 00736378 |. 50 PUSH EAX 00736379 |. 64:8925 00000>MOV DWORD PTR FS:[0],ESP 00736380 |. 83EC 58 SUB ESP,58 00736383 |. 53 PUSH EBX

(1)查找OEP 在命令行中先下bp WaitForDebugEvent断点,这个函数有两个参数,其中一个指向接收调试事件信息DEBUG_ENENT的指针,Shift+F9运行

7C849128 > 8BFF MOV EDI,EDI 来到这里,注意此时的堆栈处

7C84912A 55 PUSH EBP 7C84912B 8BEC MOV EBP,ESP 7C84912D 83EC 68 SUB ESP,68 7C849130 56 PUSH ESI 堆栈处如下:

0012BCB8 007264DF /CALL 到 WaitForDebugEvent 来自 fotobatc.007264D9 0012BCBC 0012CD90 |pDebugEvent = 0012CD90 ;这个就是指针了,在数据窗口跟随,按F2键取消断点 0012BCC0 000003E8 \Timeout = 1000. ms

继续在命令行下bp WriteProcessMemory断点,Shift+F9运行

7C80226F > 8BFF MOV EDI,EDI 来到这里,看看堆栈处 7C802271 55 PUSH EBP 7C802272 8BEC MOV EBP,ESP 7C802274 51 PUSH ECX 7C802275 51 PUSH ECX 7C802276 8B45 0C MOV EAX,DWORD PTR SS:[EBP+C] 7C802279 53 PUSH EBX 7C80227A 8B5D 14 MOV EBX,DWORD PTR SS:[EBP+14] 堆栈处如下: 0012BB58 0072A477 /CALL 到 WriteProcessMemory 来自 fotobatc.0072A471 0012BB5C 0000004C |hProcess = 0000004C (window) 0012BB60 006A9000 |Address = 6A9000 ;这里是欲写入区域的基地址 0012BB64 003EE6C8 |Buffer = 003EE6C8 0012BB68 00001000 |BytesToWrite = 1000 (4096.) 0012BB6C 0012BC74 \pBytesWritten = 0012BC74

现在我们看数据窗口

0012CD9C 80000001 0012CDA0 00000000 0012CDA4 00000000 0012CDA8 006A9E80 fotobatc.006A9E80 0012CDAC 00000002 0012CDB0 00000000 0012CDB4 006A9E80 fotobatc.006A9E80 0012CDB8 006A9E80 fotobatc.006A9E80 0012CDBC 00000001

看到OEP了吧。OEP=006a9e80

(2)dump 重新在OD中载入程序,重新下bp WaitForDebugEvent,Shift+F9运行,取消断点Alt+F9返回

007264DF . 85C0 TEST EAX,EAX 返回到这里 007264E1 . 0F84 2B270000 JE fotobatc.00728C12 007264E7 . 8B85 FCFDFFFF MOV EAX,DWORD PTR SS:[EBP-204] 007264ED . 25 FF000000 AND EAX,0FF 007264F2 . 85C0 TEST EAX,EAX 007264F4 . 74 13 JE SHORT fotobatc.00726509 007264F6 . 8B0D 441F7600 MOV ECX,DWORD PTR DS:[761F44] 007264FC . 8379 20 00 CMP DWORD PTR DS:[ECX+20],0 00726500 . 74 07 JE SHORT fotobatc.00726509

按CTRL+F键,输入按CTRL+F键,输入or eax,0fffffff8按查找。按查找。

00726A63 > \83BD CCF5FFFF>CMP DWORD PTR SS:[EBP-A34],0 ;找到这里,设置断点运行到这里 00726A6A . 0F8C A8020000 JL fotobatc.00726D18 注意这里 00726A70 . 8B8D CCF5FFFF MOV ECX,DWORD PTR SS:[EBP-A34] 注意这里 00726A76 . 3B0D 481F7600 CMP ECX,DWORD PTR DS:[761F48] 注意这里 00726A7C . 0F8D 96020000 JGE fotobatc.00726D18 00726A82 . 8B95 40F6FFFF MOV EDX,DWORD PTR SS:[EBP-9C0] 00726A88 . 81E2 FF000000 AND EDX,0FF 00726A8E . 85D2 TEST EDX,EDX 00726A90 . 0F84 AD000000 JE fotobatc.00726B43 00726A96 . 6A 00 PUSH 0 00726A98 . 8BB5 CCF5FFFF MOV ESI,DWORD PTR SS:[EBP-A34] 00726A9E . C1E6 04 SHL ESI,4 00726AA1 . 8B85 CCF5FFFF MOV EAX,DWORD PTR SS:[EBP-A34] 00726AA7 . 25 07000080 AND EAX,80000007 00726AAC . 79 05 JNS SHORT fotobatc.00726AB3 00726AAE . 48 DEC EAX 00726AAF . 83C8 F8 OR EAX,FFFFFFF8 ;找到这里。来到这里,向上翻 00726AB2 . 40 INC EAX 00726AB3 > 33C9 XOR ECX,ECX

在726A63处下断点,F9运行到726A63 处,取消断点,得到[0012CD7c]=000002a8,把0012cd7c的数据改为0,

代码窗口向下翻

00726B1D . 8B15 2C1F7600 MOV EDX,DWORD PTR DS:[761F2C] 00726B23 . 8D04B2 LEA EAX,DWORD PTR DS:[EDX+ESI*4] 00726B26 . 50 PUSH EAX 00726B27 . 8B8D CCF5FFFF MOV ECX,DWORD PTR SS:[EBP-A34] 00726B2D . 51 PUSH ECX 00726B2E . E8 2F210000 CALL fotobatc.00728C62 00726B33 . 83C4 0C ADD ESP,0C 00726B36 . 25 FF000000 AND EAX,0FF 从这里开始修改 00726B3B . 85C0 TEST EAX,EAX 00726B3D . 0F84 D5010000 JE fotobatc.00726D18 00726B43 > 837D D8 00 CMP DWORD PTR SS:[EBP-28],0 00726B47 . 75 27 JNZ SHORT fotobatc.00726B70

找到 00726B36 . 25 FF000000 AND EAX,0FF 00726B3B . 85C0 TEST EAX,EAX 00726B3D . 0F84 D5010000 JE fotobatc.00726D18

改为 00726B36 FF05 7CCD1200 INC DWORD PTR DS:[12CD7C] 00726B3C C705 4C1F7600>MOV DWORD PTR DS:[761F4C],1 00726B46 ^ E9 18FFFFFF JMP fotobatc.00726A63

接着在00726A63下一行处可看到 00726A6A . /0F8C A8020000 JL fotobatc.00726D18

跟随到00726D18处下断点,Shift+F9运行,取消断点, 这时所有代码都强制解压完成,运行LordPE,选择第二个进程完整脱壳,修改脱壳后的dumped的OEP为2a9e80,保存进入下一步。

重新把原程序载入OD,下断bp DebugActiveProcess,Shift+F9运行,注意堆栈处

0012BCBC 0072633A /CALL 到 DebugActiveProcess 来自 fotobatc.00726334 0012BCC0 000007F0 \ProcessId = 7F0 这个是子进程ID,你的不一定相同

另开一个OD,在附加处选择7f0这个进程,Alt+F9返回

00736363 >- EB FE JMP SHORT fotobatc.<模块入口点> 停在这里,修改为55 8B 00736365 EC IN AL,DX ; I/O 命令 00736366 6A FF PUSH -1 00736368 68 200B7600 PUSH fotobatc.00760B20 0073636D 68 A0607300 PUSH fotobatc.007360A0 ; SE 处理程序安装

然后运行双进程转单进程脚本。完毕后,下断BP GetModuleHandleA+5,Shift+F9,注意观察堆栈!

00126880 /0012CCE0 00126884 |01083637 返回到 01083637 来自 kernel32.GetModuleHandleA 00126888 |01097474 ASCII "kernel32.dll" 0012688C |01098744 ASCII "VirtualAlloc" 00126890 |00000001

00126880 /0012CCE0 00126884 |01083654 返回到 01083654 来自 kernel32.GetModuleHandleA 00126888 |01097474 ASCII "kernel32.dll" 0012688C |01098738 ASCII "VirtualFree"

001265F0 /00126884 001265F4 |0106ABB9 返回到 0106ABB9 来自 kernel32.GetModuleHandleA 001265F8 |00126738 ASCII "kernel32.dll" 001265FC |00000000

不断Shft+F9直到经过VirtualAlloc、VirtualFree再次在堆栈中看见kernel32.dll,是返回的时机了,取消断点,ALT+F9返回

0106ABB9 8B0D E4C90901 MOV ECX,DWORD PTR DS:[109C9E4] 0106ABBF 89040E MOV DWORD PTR DS:[ESI+ECX],EAX 0106ABC2 A1 E4C90901 MOV EAX,DWORD PTR DS:[109C9E4] 0106ABC7 391C06 CMP DWORD PTR DS:[ESI+EAX],EBX 0106ABCA 75 16 JNZ SHORT 0106ABE2 0106ABCC 8D85 B4FEFFFF LEA EAX,DWORD PTR SS:[EBP-14C] 0106ABD2 50 PUSH EAX 0106ABD3 FF15 E0200901 CALL DWORD PTR DS:[10920E0] ; kernel32.LoadLibraryA 0106ABD9 8B0D E4C90901 MOV ECX,DWORD PTR DS:[109C9E4] 0106ABDF 89040E MOV DWORD PTR DS:[ESI+ECX],EAX 0106ABE2 A1 E4C90901 MOV EAX,DWORD PTR DS:[109C9E4] 0106ABE7 391C06 CMP DWORD PTR DS:[ESI+EAX],EBX 0106ABEA 0F84 32010000 JE 0106AD22 修改为jmp 0106AD22 0106ABF0 33C9 XOR ECX,ECX 0106ABF2 8B07 MOV EAX,DWORD PTR DS:[EDI]

按一次F9直接运行 打开ImportREC选择7f0这个进程 OEP=2a9e80 RAV=2E7280 大小=930 直接点击获取输入表,CUT掉无效的指针修复dumped即可以了.

这里说说rva的找法 od载入dump.exe 006A9E80 dumped.<> 55 push ebp 006A9E81 8BEC mov ebp,esp 006A9E83 B9 13000000 mov ecx,13 006A9E88 6A 00 push 0 006A9E8A 6A 00 push 0 006A9E8C 49 dec ecx 006A9E8D ^ 75 F9 jnz short dumped.006A9E88 006A9E8F 53 push ebx 006A9E90 56 push esi 006A9E91 57 push edi 006A9E92 B8 90986A00 mov eax,dumped.006A9890 006A9E97 E8 B0CFD5FF call dumped.00406E4C 这里f7 006A9E9C 33C0 xor eax,eax

到这里 00406E4C 53 push ebx 00406E4D 8BD8 mov ebx,eax 00406E4F 33C0 xor eax,eax 00406E51 A3 ACB06A00 mov dword ptr ds:[6AB0AC],eax 00406E56 6A 00 push 0 00406E58 E8 2BFFFFFF call dumped.00406D88 这里f7 00406E5D A3 68A66C00 mov dword ptr ds:[6CA668],eax

到这里 00406D88 - FF25 78736E00 jmp dword ptr ds:[6E7378] 00406D8E 8BC0 mov eax,eax 00406D90 - FF25 74736E00 jmp dword ptr ds:[6E7374] ; kernel32.LocalAlloc 00406D96 8BC0 mov eax,eax 00406D98 - FF25 70736E00 jmp dword ptr ds:[6E7370] ; kernel32.TlsGetValue 00406D9E 8BC0 mov eax,eax 00406DA0 - FF25 6C736E00 jmp dword ptr ds:[6E736C] ; kernel32.TlsSetValue

在数据窗口,ctrl+G,输入006e7378

上下查找 006E727C 00000000 006E7280 7C96AE65 ntdll.RtlDeleteCriticalSection 这里开始的 006E7284 7C95F2FC ntdll.RtlLeaveCriticalSection 006E7288 7C95F337 ntdll.RtlEnterCriticalSection 006E728C 7C8284E0 kernel32.InitializeCriticalSection

006E7BA8 0105BF23 006E7BAC 77BDA69A GDI32.CreateDIBSection 006E7BB0 0105BF23 这里结束的

大小=006E7BB0-006E7280=930

运行,ok

下面简单说说注册

脱壳后,程序仍然要求注册!od,载入,f9运行,到程序帮助菜单下,输入注册码,比如注册码为aabbccddeeffgg,点确定,没反映,不要紧,回到od下,alt+m,右键,搜索,asscii,输入aabbccddeeffgg,找到了吧,ctrl+L,观察下面的字符串,重新填入注册就是.

上一篇   下一篇