• 标 题:PEbundle V2.3脱壳 - 某算法注册机
  • 作 者:David
  • 时 间:2004年3月22日 12:16
  • 链 接:http://bbs.pediy.com

【脱文标题】 PEbundle V2.3脱壳 - 某算法注册机

【脱文作者】 weiyi75[Dfcg] 

【作者邮箱】 weiyi75@sohu.com

【作者主页】 Dfcg官方大本营 --- www.chinadfcg.com
 
【使用工具】 Fi,Ollydbg,Loadpe,Imprec1.42

【脱壳平台】 Win2K

【软件名称】 keygen

【软件简介】 PEbundle v2.3 加壳的一个某算法注册机

【软件大小】 164KB  

【下载地址】 本地下载

【加壳方式】 PEbundle v2.3

【保护方式】 压缩壳,IAT简单加密
 
【脱壳声明】 我是一只小菜鸟,偶得一点心得,愿与大家分享: 
  

-------------------------------------------------------------------------------- 

【脱壳内容】 

看过 PEbundle V2.3脱壳——唐诗三百首 V1.2 脱文,大家对PEbundle V2.3有些概念吧,特点是循环多。

既然有了前面的经验,就没必要慢慢跟踪了,首先找Oep。

OD设置忽略全部异常设置,载入程序,无须隐藏OD,因为PEbundle是个压缩壳。

00439000 >  9C              pushfd  //入口点
00439001    60              pushad
00439002    E8 02000000     call keygen.00439009
00439007    33C0            xor eaxeax
00439009    8BC4            mov eaxesp
0043900B    83C0 04         add eax, 4
0043900E    93              xchg eaxebx
0043900F    8BE3            mov espebx
00439011    8B5B FC         mov ebxdword ptr ds:[ebx-4]
00439014    81EB 07304000   sub ebx, keygen.00403007                 ; ASCII "D$"
0043901A    87DD            xchg ebpebx
0043901C    80BD DD3B4000 0>cmp byte ptr ss:[ebp+403BDD], 0
00439023    74 21           je short keygen.00439046
00439025    8D85 D6384000   lea eaxdword ptr ss:[ebp+4038D6]
0043902B    50              push eax
0043902C    FF95 B2384000   call dword ptr ss:[ebp+4038B2]
00439032    8D8D 2C3A4000   lea ecxdword ptr ss:[ebp+403A2C]
00439038    51              push ecx
00439039    50              push eax
0043903A    FF95 A2384000   call dword ptr ss:[ebp+4038A2]
....................................................................................

找Oep试试我的二次软硬断点结合法,这个方法只能找Oep,IAT无法避免加密。

命令行 d 12ffc0

0012FFC0  F8 FF 12 00 F5 87 E6 77 A8 16 55 00 56 00 00 00  ?.鯂鎤?U.V...  //已经有数据了,没关系,还是下个硬件写入dword断点
0012FFD0  00 F0 FD 7F 00 02 00 00 C8 FF 12 00 00 02 00 00  .瘕...?....
0012FFE0  FF FF FF FF B4 F0 E7 77 C8 8E E6 77 00 00 00 00  答鐆葞鎤....
0012FFF0  00 00 00 00 00 00 00 00 00 90 43 00 00 00 00     .........怌.....

F9运行

硬件断点1

00439376    C3              retn
00439377    C8 000000       enter 0, 0
0043937B    57              push edi
0043937C    56              push esi
0043937D    8B75 08         mov esidword ptr ss:[ebp+8]
00439380    8B7D 0C         mov edidword ptr ss:[ebp+C]
00439383    8A06            mov albyte ptr ds:[esi]
00439385    3C 61           cmp al, 61
00439387    72 06           jb short keygen.0043938F
00439389    3C 7A           cmp al, 7A
0043938B    77 02           ja short keygen.0043938F
0043938D    04 E0           add al, 0E0
0043938F    8A27            mov ahbyte ptr ds:[edi]
00439391    80FC 61         cmp ah, 61
00439394    72 08           jb short keygen.0043939E
00439396    80FC 7A         cmp ah, 7A
00439399    77 03           ja short keygen.0043939E
0043939B    80C4 E0         add ah, 0E0
0043939E    46              inc esi
0043939F    47              inc edi
004393A0    837D 10 01      cmp dword ptr ss:[ebp+10], 1
004393A4    75 01           jnz short keygen.004393A7
...........................................................................

然后Alt+M 打开内存镜像窗口。

内存镜像,项目 12
 地址=00401000      //Code 段下内存访问断点,F9运行
 大小=0000D000 (53248.)
 Owner=keygen   00400000
 区段=.text
 包含=code
 类型=Imag 01001002
 访问=R
 初始访问=RWE
 
内存断点

0040D1EF  /.  55            push ebp        //OEP 入口,LoadPe脱壳
0040D1F0  |.  8BEC          mov ebpesp
0040D1F2  |.  6A FF         push -1
0040D1F4  |.  68 10FD4000   push keygen.0040FD10
0040D1F9  |.  68 4ED34000   push keygen.0040D34E                     ;  jmp to MSVCRT._except_handler3; SE handler 

installation
0040D1FE  |.  64:A1 0000000>mov eaxdword ptr fs:[0]
0040D204  |.  50            push eax
0040D205  |.  64:8925 00000>mov dword ptr fs:[0], esp
0040D20C  |.  83EC 68       sub esp, 68
0040D20F  |.  53            push ebx
0040D210  |.  56            push esi
0040D211  |.  57            push edi
0040D212  |.  8965 E8       mov dword ptr ss:[ebp-18], esp
0040D215  |.  33DB          xor ebxebx
0040D217  |.  895D FC       mov dword ptr ss:[ebp-4], ebx
0040D21A  |.  6A 02         push 2
0040D21C  |.  FF15 54E44000 call dword ptr ds:[40E454]               ;  MSVCRT.__set_app_type
0040D222  |.  59            pop ecx
0040D223  |.  830D 70234100>or dword ptr ds:[412370], FFFFFFFF
0040D22A  |.  830D 74234100>or dword ptr ds:[412374], FFFFFFFF
0040D231  |.  FF15 50E44000 call dword ptr ds:[40E450]               ;  MSVCRT.__p__fmode
0040D237  |.  8B0D 64234100 mov ecxdword ptr ds:[412364]
0040D23D  |.  8908          mov dword ptr ds:[eax], ecx
0040D23F  |.  FF15 4CE44000 call dword ptr ds:[40E44C]               ;  MSVCRT.__p__commode
.........................................................................................

脱壳后发现程序不能运行,这时需要用Imprec修复引入函数表(Import Table)

Imprec选择进程,在Oep处填71B80,点IT自动搜索,然后点获输入信息,看到输入表有无效的,点显示无效按钮,提示有1个未修复的指针,这是垃

圾指针吗?直接Cut程序是无法运行的,删除这个指针程序可以运行,感觉不爽。为这个问题特地请教Jwh51。

不同的DLL之间一定要有个空间进行区别,所以很多壳就在这个空间内插入垃圾了,而同一个DLL之内是没有空余空间的.所以也无法插入垃圾了。

一般情况下,垃圾总是位于两个DLL之间,而这个指针位于Kernel32.dll之间, 所以这个指针不是垃圾指针,为什么这个指针删除仍然可以运行?这是因为在程序里API是按顺序排列的,排上去不并不一定马上就要用到。当然

,可能程序里没用到这个指针,就不会出错了。

那我们找找它是Kernel32.dll的哪个Api函数。

图中我们看到,40e078处的指针无法识别,这个用功能强大的OD下断点,基本上都能从堆栈获寄存器里找到加密指针。

还是命令行 d 40e078,然后对40e078下硬件写入dword断点,当加密指针时Od立刻会通知我们。

F9运行中断两次,第二次到这里中断。

硬件中断

00439BD4  ^E9 67FFFFFF     jmp keygen.00439B40
00439BD9    F8              clc
00439BDA    C3              retn
00439BDB    F9              stc
00439BDC    C3              retn
00439BDD    0000            add byte ptr ds:[eax], al
00439BDF    0000            add byte ptr ds:[eax], al
00439BE1    0000            add byte ptr ds:[eax], al
00439BE3    0000            add byte ptr ds:[eax], al
00439BE5    0000            add byte ptr ds:[eax], al
00439BE7    0000            add byte ptr ds:[eax], al
00439BE9    0000            add byte ptr ds:[eax], al
00439BEB    0000            add byte ptr ds:[eax], al
00439BED    0000            add byte ptr ds:[eax], al
00439BEF    0000            add byte ptr ds:[eax], al
..........................................................................................


0012FF80   00036000
0012FF84   00439B87  keygen.00439B87
0012FF88   004394AA  keygen.004394AA
0012FF8C   77E705CF  KERNEL32.LoadLibraryA  //堆栈滚动条往上一点看到 KERNEL32.LoadLibraryA
0012FF90   00400000  keygen.00400000
0012FF94   00410A30  keygen.00410A30
0012FF98   00439ABC  返回到 keygen.00439ABC 来自 keygen.00439AC9
0012FF9C   004392C1  返回到 keygen.004392C1 来自 keygen.00439AAD
0012FFA0   005516A8

ECX 00410A30 keygen.00410A30
EDX 00400000 keygen.00400000
EBX 004110B8 ASCII "LoadLibraryA"  //寄存器EBX中存放的加密指针
ESP 0012FF98
EBP 00036000
ESI 00410914 keygen.00410914
EDI 0040E07C keygen.0040E07C
EIP 00439BD4 keygen.00439BD4
C 1  ES 0023 32bit 0(FFFFFFFF)
P 1  CS 001B 32bit 0(FFFFFFFF)
A 0  SS 0023 32bit 0(FFFFFFFF)
Z 0  DS 0023 32bit 0(FFFFFFFF)
S 1  FS 0038 32bit 7FFDE000(FFF)
T 0  GS 0000 NULL
D 0
O 0  LastErr ERROR_SUCCESS (00000000)
EFL 00000287 (NO,B,NE,BE,S,PE,L,LE)
ST0 empty 0.0
ST1 empty 0.0
ST2 empty 0.0
ST3 empty 0.0
ST4 empty 0.0
ST5 empty 0.0
ST6 empty 0.0
ST7 empty -UNORM E330 00000020 00000000
               3 2 1 0      E S P U O Z D I
FST 0000  Cond 0 0 0 0  Err 0 0 0 0 0 0 0 0  (GT)
FCW 027F  Prec NEAR,53  Mask    1 1 1 1 1 1
..............................................................................

于是在Rva 0000E078 处填入 KERNEL32.LoadLibraryA

指针全部修复,修复程序,正常运行。



【脱壳总结】PEbundle V2.3手动脱壳一般用二次软硬断点结合法找OEP,IAT一般没有加密,加密指针也很容易用硬件访问断点找到答案。



--------------------------------------------------------------------------------  
  
 

【版权声明】 本文纯属技术交流, 转载请注明作者并保持文章的完整,感谢Jwh51兄的耐心指点!