首页
社区
课程
招聘
[旧帖] [原创]求邀请,一个带保护的delphi程序之逆向小结,并请高手指点 0.00雪花
发表于: 2012-4-9 14:23 1404

[旧帖] [原创]求邀请,一个带保护的delphi程序之逆向小结,并请高手指点 0.00雪花

2012-4-9 14:23
1404
1.  序言

Delphi菜鸟,从未用过Delphi。前一段时间随机拿来研究的,再过点时间恐怕就会忘了,所以写下来,请大牛指点。

没用PEID查壳,直接拖IDA里去了,结果有如下段:
CODE   00401000 0049D000 R . X . L para 0001 public CODE 32 0000 0000 0001 FFFFFFFF FFFFFFFF
DATA   0049D000 004A0000 R W . . L para 0002 public DATA 32 0000 0000 0001 FFFFFFFF FFFFFFFF
BSS    004A0000 004A1000 R W . . L para 0003 public      32 0000 0000 0001 FFFFFFFF FFFFFFFF
.idata 004A1000 004A4000 R W . . L para 0004 public DATA 32 0000 0000 0001 FFFFFFFF FFFFFFFF
.tls   004A4000 004A5000 R W . . L para 0005 public      32 0000 0000 0001 FFFFFFFF FFFFFFFF
.rdata 004A5000 004A6000 R . . . L para 0006 public DATA 32 0000 0000 0001 FFFFFFFF FFFFFFFF
.jwx0  004A6000 004B1000 R W . . L para 0007 public DATA 32 0000 0000 0001 FFFFFFFF FFFFFFFF
.jwx1  0054F000 005CE000 R W X . L para 0008 public CODE 32 0000 0000 0001 FFFFFFFF FFFFFFFF

比较奇怪的是jwx0和jwx1,一个数据段,一个代码段,名字以前没见过,感觉是作者自己写的。起初怀疑这两个段是什么壳用的,但鉴于已有CODE段了(放眼望去,基本是DELPHI的库函数等),因此个人觉得是作者自创的什么保护机制了。

2.查看关键算法(大牛跳过)

算法什么的查找还算简单,用DeDe查看下事件按钮,一般都是ButtonClick之类的,下个断点再跟下,想看的算法就出来了。

3.  算法逆向(大牛可忽略,不过最后有个小问题)

算法的逆向稍有些特殊,《加密与解密(三)》中p76说道,delphi采用__fastcall规范传递参数时,最左边的三个不大于4个字节(DWORD)的参数分别放在eac,edx,ecx寄存器,寄存器用完之后,多余的参数按照从左至右的PASCAL方式来压栈。

因此在这个地方多加注意,算法的逆向也只是时间问题了。但本人实践发现,F5显示的参数顺序有时候是有问题的,特别是在对函数的多层封装中。因此,完全依赖工具也会走弯路的。不知其他朋友是否发现这个问题?

4.保护机制的分析(大牛请看)

用ollydbg跟了下,看到jwx1中最主要的是一个jmp 到CODE中的一个地址0x0049A105去,而这个地址的引用居然出现了106次之多。为了近距离观察这个loc_开头的地址,在该位置创建了函数,变为sub函数,使用F5观察下内容(需要Alt+K调整栈偏移成正的)如下:

void __usercall sub_49A105(unsigned __int8 _CF<cf>, char _ZF<zf>, char _SF<sf>, unsigned __int8 _OF<of>, int a5<eax>, int a6<edx>, int a7, int a8, int a9, int a10, double a11)
{
  __int16 v12; // dx@22
  int v17; // kr08_4@29
  char v18; // al@32
  int v19; // eax@32
  int v21; // esi@1
  char v22; // zf@1
  DWORD v23; // eax@1
  int v24; // edx@1
  DWORD v25; // ebx@1
  signed int v26; // ecx@1
  int v27; // edi@1
  signed int v28; // eax@5
  signed int v29; // ecx@5
  int v30; // edi@9
  char v31; // bl@9
  int v32; // esi@9
  char v33; // dl@10
  unsigned __int8 v34; // dl@10
  int v39; // eax@10
  char v40; // al@13
  __int16 v41; // dx@41
  signed int v42; // ett@41
  char v45; // al@48
  unsigned int v46; // [sp-7Ah] [bp-92h]@1
  int v47; // [sp-76h] [bp-8Eh]@14
  int v48; // [sp-72h] [bp-8Ah]@1
  int v49; // [sp-6Eh] [bp-86h]@1
  int v50; // [sp-52h] [bp-6Ah]@1
  signed __int32 v51; // [sp-32h] [bp-4Ah]@19
  char v52; // [sp-2Eh] [bp-46h]@20
  __int16 v53; // [sp-2Ch] [bp-44h]@21
  char v54; // [sp-2Ah] [bp-42h]@21
  int v55; // [sp-26h] [bp-3Eh]@27
  __int16 v56; // [sp-22h] [bp-3Ah]@27
  int v57; // [sp-20h] [bp-38h]@28
  __int16 v58; // [sp-1Ch] [bp-34h]@28
  unsigned int v59; // [sp-1Ah] [bp-32h]@29
  int v60; // [sp-16h] [bp-2Eh]@29
  __int16 v61; // [sp-Ch] [bp-24h]@18
  char v62[6]; // [sp+12h] [bp-6h]@15
  void *v63; // [sp+18h] [bp+0h]@18

  v49 = a6;
  v48 = a5;
  __asm { pushf }
  v46 = 0;
  v21 = v50;
  v23 = GetCurrentThreadId();
  v25 = v23;
  v26 = 256;
  v27 = v24;
  do
  {
    if ( !v26 )
      break;
    v22 = *(_DWORD *)v27 == v23;
    v27 += 4;
    --v26;
  }
  while ( !v22 );
  if ( !v22 )
  {
    v28 = v26;
    v29 = 256;
    v27 = v24;
    do
    {
      if ( !v29 )
        break;
      _ZF = *(_DWORD *)v27 == v28;
      v27 += 4;
      --v29;
    }
    while ( !_ZF );
    *(_DWORD *)(v27 - 4) = v25;
  }
  v30 = v24 + 16 * (v27 - v24) + 960;
  v31 = v21;
  v32 = v46 + v21;
  while ( 1 )
  {
    v33 = __ROL__(v31 + *(_BYTE *)v32 + 1, 7);
    v34 = __ROL__(v33 + 1, 1);
    ++v34;
    ++v32;
    _CF = __CFADD__(v34, v31);
    _OF = __OFADD__(v34, v31);
    _ZF = v34 + v31 == 0;
    _SF = (char)(v34 + v31) < 0;
    v31 += v34;
    v39 = v34;
    switch ( v34 )
    {
      case 0u:
        __asm { fistp   dword ptr [esp+0] }
        break;
      case 1u:
        __asm { mov     eax, cr6 }
        *(_DWORD *)&v62[2] = _EAX;
        break;
      case 2u:
        _EDX = *(_DWORD *)&v54;
        __asm { mov     dr7, edx }
        break;
      case 3u:
      case 0xBu:
        _CF = __CFADD__((_WORD)v63, v61);
        _OF = __OFADD__((_WORD)v63, v61);
        _ZF = (_WORD)v63 + v61 == 0;
        _SF = (signed __int16)((_WORD)v63 + v61) < 0;
        v61 += (signed __int16)v63;
        __asm { pushfw }
        break;
      case 5u:
        __asm { f2xm1 }
        break;
      case 6u:
        LOWORD(v42) = HIWORD(v46);
        HIWORD(v42) = v46;
        v41 = v42 % (signed __int16)v47;
        LOWORD(v47) = v42 / (signed __int16)v47;
        HIWORD(v46) = v41;
        break;
      case 7u:
        __asm { fld1 }
        break;
      case 8u:
        *(_WORD *)&v62[4] = **(_WORD **)&v62[2];
        break;
      case 9u:
        HIWORD(v46) += v46;
        break;
      case 0xAu:
        __asm { fstp    tbyte ptr [esp] }
        break;
      case 0xCu:
      case 0x1Au:
        *(_DWORD *)&v62[2] = **(_DWORD **)&v62[2];
        break;
      case 0xDu:
        _CF = BYTE2(v39) != 0;
        _OF = BYTE2(v39) != 0;
        UNDEF(_ZF);
        UNDEF(_SF);
        HIWORD(v46) = (char)v46 * SBYTE2(v46);
        __asm { pushfw }
        break;
      case 0xEu:
        *(_BYTE *)v51 = v52;
        break;
      case 0xFu:
        _EAX = v46;
        __asm { mov     cr6, eax }
        break;
      case 0x10u:
      case 0x27u:
        v51 = __readfsdword(v51);
        break;
      case 0x11u:
      case 0x22u:
      case 4u:
        continue;
      case 0x12u:
      case 0x13u:
        __asm { fsubr   dword ptr [esp+0] }
        break;
      case 0x14u:
        *(_WORD *)v55 = v56;
        break;
      case 0x15u:
        __asm { fldlg2 }
        break;
      case 0x16u:
        __asm { ftst }
        break;
      case 0x17u:
        *MK_FP(__GS__, v57) = v58;
        break;
      case 0x18u:
        v45 = *(_BYTE *)v32++;
        v31 += ~(~(v31 + v45 - 82) - 62);
        break;
      case 0x19u:
        __asm { fcos }
        break;
      case 0x1Bu:
        v46 = *(_DWORD *)v46;
        break;
      case 0x1Cu:
        __asm { fldpi }
        break;
      case 0x1Du:
        _CF = (unsigned __int8)(v59 * (unsigned __int64)(unsigned int)v60 >> 32) != 0;
        _OF = (unsigned __int8)(v59 * (unsigned __int64)(unsigned int)v60 >> 32) != 0;
        UNDEF(_ZF);
        UNDEF(_SF);
        v17 = v59 * v60;
        v59 = v59 * (unsigned __int64)(unsigned int)v60 >> 32;
        v60 = v17;
        __asm { pushfw }
        break;
      case 0x1Eu:
        __ES__ = (unsigned __int16)v46;
        break;
      case 0x1Fu:
        __asm { fst     qword ptr [esp+0] }
        break;
      case 0x20u:
        _CF = __CFSHL__(v53, v54);
        UNDEF(_OF);
        _ZF = v53 << v54 == 0;
        _SF = (signed __int16)(v53 << v54) < 0;
        *(_WORD *)&v54 = v53 << v54;
        __asm { pushfw }
        break;
      case 0x21u:
        v18 = *(_BYTE *)v32++;
        v19 = (unsigned __int8)-(char)(((unsigned __int8)(v31 + v18 - 112) ^ 0xC8) - 90);
        v31 += v19;
        HIWORD(v57) = *(_BYTE *)(v30 + 4 * v19);
        break;
      case 0x23u:
        *(int *)((char *)&v47 + 2) = *(_QWORD *)&v46 >> v48;
        __asm { pushfw }
        break;
      case 0x24u:
        *(unsigned int *)((char *)&v46 + 2) = v46 >> v47;
        break;
      case 0x25u:
        _ECX = *(_DWORD *)&v52;
        __asm { mov     dr4, ecx }
        break;
      case 0x26u:
        v40 = *(_BYTE *)v32++;
        v31 += ~(~(v31 + v40 - 82) - 62);
        break;
      case 0x28u:
        v12 = (unsigned int)(v53 * *(signed __int16 *)&v54) >> 16;
        _CF = (unsigned __int8)((unsigned int)(v53 * *(signed __int16 *)&v54) >> 16) != 0;
        _OF = (unsigned __int8)((unsigned int)(v53 * *(signed __int16 *)&v54) >> 16) != 0;
        UNDEF(_ZF);
        UNDEF(_SF);
        *(_WORD *)&v54 *= v53;
        v53 = v12;
        __asm { pushfw }
        break;
      case 0x29u:
        _CF = BYTE2(v39) != 0;
        _OF = BYTE2(v39) != 0;
        UNDEF(_ZF);
        UNDEF(_SF);
        HIWORD(v46) = (unsigned __int8)v46 * BYTE2(v46);
        __asm { pushfw }
        break;
      case 0x2Au:
        __asm { fnclex }
        break;
      case 0x2Bu:
        __asm { fcomp   dword ptr [esp+0] }
        break;
      case 0x2Cu:
        __asm { fnstsw  ax }
        LOWORD(v57) = _AX;
        break;
      case 0x2Du:
        v47 += v46;
        break;
      case 0x2Eu:
        HIWORD(v46) = *(_WORD *)v46;
        break;
    }
  }
}

对应的代码(部分,由于实在太长没补全):
CODE:0049A105       sub_49A105      proc near               ; CODE XREF: .jwx1:005BE04Cj
CODE:0049A105                                               ; .jwx1:005BE072j ...
CODE:0049A105
CODE:0049A105       var_92          = byte ptr -92h
CODE:0049A105       var_86          = dword ptr -86h
CODE:0049A105       var_82          = dword ptr -82h
CODE:0049A105       anonymous_0     = byte ptr -46h
CODE:0049A105       anonymous_1     = word ptr -42h
CODE:0049A105       var_16          = dword ptr -16h
CODE:0049A105       var_12          = dword ptr -12h
CODE:0049A105       var_6           = byte ptr -6
CODE:0049A105       arg_4           = dword ptr  8
CODE:0049A105       arg_10          = qword ptr  14h
CODE:0049A105
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499C9D SIZE 00000009 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499CAD SIZE 00000009 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499D0C SIZE 00000013 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499D2C SIZE 0000000D BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499D73 SIZE 00000013 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499D8F SIZE 00000010 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499DC8 SIZE 00000012 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499DE5 SIZE 00000009 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499E38 SIZE 00000008 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499E5F SIZE 00000011 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499E85 SIZE 00000009 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499EAF SIZE 0000000A BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499ED8 SIZE 0000000D BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499F3B SIZE 00000007 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:00499FC5 SIZE 00000007 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A0B6 SIZE 0000001C BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A0EB SIZE 00000008 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A0FC SIZE 00000009 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A297 SIZE 00000007 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A7CA SIZE 0000000F BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A848 SIZE 00000016 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A8D1 SIZE 00000009 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A910 SIZE 00000012 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A936 SIZE 00000007 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A9B2 SIZE 00000006 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A9C0 SIZE 00000011 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049A9F5 SIZE 0000000F BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049AA7C SIZE 0000000B BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049AA99 SIZE 0000000B BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049AACC SIZE 00000016 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049AAEB SIZE 00000007 BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049AB03 SIZE 0000000F BYTES
CODE:0049A105       ; FUNCTION CHUNK AT CODE:0049AB2E SIZE 0000000A BYTES
CODE:0049A105       ; FUNCTION CHUNK AT .jwx1:005C237A SIZE 0000000A BYTES
CODE:0049A105
CODE:0049A105 0 05C                 push    ecx
CODE:0049A106 0 06E                 push    ebx
CODE:0049A107 0 072                 push    edi
CODE:0049A108 0 076                 push    esp
CODE:0049A109 0 07A                 push    ebp
CODE:0049A10A 0 07E                 push    esi
CODE:0049A10B 0 082                 push    edx
CODE:0049A10C 0 086                 push    eax
CODE:0049A10D 0 08A                 pushf
CODE:0049A10E 0 08E                 push    0
CODE:0049A113 0 092                 mov     esi, [esp+28h]
CODE:0049A117 0 092                 cld
CODE:0049A118 0 092                 mov     edx, offset unk_4A6000
CODE:0049A11D 0 092                 call    ds:__imp_GetCurrentThreadId
CODE:0049A123 0 092                 mov     ebx, eax
CODE:0049A125 0 092                 mov     ecx, 100h
CODE:0049A12A 0 092                 mov     edi, edx
CODE:0049A12C 0 092                 repne scasd
CODE:0049A12E 0 092                 jz      short loc_49A13D
CODE:0049A130 0 092                 mov     eax, 100h
CODE:0049A135 0 092                 xchg    eax, ecx
CODE:0049A136 0 092                 mov     edi, edx
CODE:0049A138 0 092                 repne scasd
CODE:0049A13A 0 092                 mov     [edi-4], ebx
CODE:0049A13D
CODE:0049A13D       loc_49A13D:                             ; CODE XREF: sub_49A105+29j
CODE:0049A13D 0 092                 mov     ebp, edi
CODE:0049A13F 0 092                 sub     edi, edx
CODE:0049A141 0 092                 shl     edi, 1
CODE:0049A143 0 092                 lea     edi, [edx+edi*8+3C0h]
CODE:0049A14A
CODE:0049A14A       loc_49A14A:                             ; CODE XREF: CODE:00499CD9j
CODE:0049A14A 0 092                 mov     ebx, esi
CODE:0049A14C 0 092                 add     esi, [esp]
CODE:0049A14F
CODE:0049A14F       loc_49A14F:                             ; CODE XREF: CODE:00499C8Fj
CODE:0049A14F                                               ; CODE:00499C98j ...
CODE:0049A14F 0 092                 mov     dl, [esi]
CODE:0049A151 0 092                 add     dl, bl
CODE:0049A153 0 092                 inc     dl
CODE:0049A155 0 092                 rol     dl, 7
CODE:0049A158 0 092                 inc     dl
CODE:0049A15A 0 092                 rol     dl, 1
CODE:0049A15C 0 092                 inc     dl
CODE:0049A15E 0 092                 add     esi, 1
CODE:0049A161 0 092                 add     bl, dl
CODE:0049A163 0 092                 movzx   eax, dl
CODE:0049A166 0 092                 jmp     off_49A2B6[eax*4]
CODE:0049A16D
CODE:0049A16D       loc_49A16D:                             ; DATA XREF: CODE:0049A2C6o
CODE:0049A16D 0 092                 push    esp
CODE:0049A16E 0 096                 jmp     loc_49A14F
CODE:0049A16E       ; ---------------------------------------------------------------------------
CODE:0049A173 0 096                 db 97h
CODE:0049A174 0 096                 dd 1F76h
CODE:0049A178 0 096 a_4d_2d_2d_2d_2 db '%.4d-%.2d-%.2d %.2d:%.2d:%.2d',0
CODE:0049A196 0 096                 align 4
CODE:0049A198 0 096                 push    0E9F1D453h
CODE:0049A19D 0 09A                 jmp     loc_5C237A      ; 查看痕迹11  time related
CODE:0049A1A2       ; ---------------------------------------------------------------------------
CODE:0049A1A2 0 09A                 pop     ecx
CODE:0049A1A3 0 096                 pop     small word ptr es:[ecx]
CODE:0049A1A7 0 094                 jmp     loc_49A14F
CODE:0049A1AC       ; ---------------------------------------------------------------------------
CODE:0049A1AC
CODE:0049A1AC       loc_49A1AC:                             ; CODE XREF: sub_49A105+61j
CODE:0049A1AC                                               ; DATA XREF: CODE:0049A36Eo
CODE:0049A1AC 0 092                 pop     edx
CODE:0049A1AD 0 08E                 push    small word ptr es:[edx]
CODE:0049A1B1 0 090                 jmp     loc_49A14F
CODE:0049A1B6       ; ---------------------------------------------------------------------------
CODE:0049A1B6 0 090                 pop     ecx
CODE:0049A1B7 0 08C                 push    dword ptr gs:[ecx]
CODE:0049A1BA 0 090                 jmp     loc_49A14F
CODE:0049A1BF       ; ---------------------------------------------------------------------------
CODE:0049A1BF 0 090                 pop     ecx
CODE:0049A1C0 0 08C                 pop     ax
CODE:0049A1C2 0 08A                 mov     ss:[ecx], al
CODE:0049A1C5 0 08A                 jmp     loc_49A14F
CODE:0049A1C5       ; ---------------------------------------------------------------------------
CODE:0049A1CA 0 08A                 db 0DFh
CODE:0049A1CB       ; ---------------------------------------------------------------------------
CODE:0049A1CB 0 08A                 sub     al, 24h
CODE:0049A1CD 0 08A                 jmp     loc_49A14F
CODE:0049A1CD       ; ---------------------------------------------------------------------------
CODE:0049A1D2 0 08A                 db 59h
CODE:0049A1D3       ; ---------------------------------------------------------------------------
CODE:0049A1D3 0 08A                 push    small word ptr cs:[ecx]
CODE:0049A1D7 0 08C                 jmp     loc_49A14F
CODE:0049A1DC       ; ---------------------------------------------------------------------------
CODE:0049A1DC 0 08C                 pop     cx
CODE:0049A1DE 0 08A                 jmp     loc_49A14F
CODE:0049A1E3       ; ---------------------------------------------------------------------------
CODE:0049A1E3 0 08A                 pop     eax
CODE:0049A1E4 0 086                 pop     dword ptr ss:[eax]
CODE:0049A1E7 0 082                 jmp     loc_49A14F
CODE:0049A1EC       ; ---------------------------------------------------------------------------
CODE:0049A1EC                       db      66h
CODE:0049A1EC 0 082                 push    ds
CODE:0049A1EE 0 084                 jmp     loc_49A14F
CODE:0049A1F3       ; ---------------------------------------------------------------------------
CODE:0049A1F3 0 084                 mov     edx, cr1
CODE:0049A1F6 0 084                 push    edx
CODE:0049A1F7 0 088                 jmp     loc_49A14F
CODE:0049A1FC       ; ---------------------------------------------------------------------------
CODE:0049A1FC 0 088                 pop     dx
CODE:0049A1FE 0 086                 pop     ax
CODE:0049A200 0 084                 pop     cx
CODE:0049A202 0 082                 div     cx
CODE:0049A205 0 082                 push    ax
CODE:0049A207 0 084                 push    dx
CODE:0049A209 0 086                 jmp     loc_49A14F
CODE:0049A20E       ; ---------------------------------------------------------------------------
CODE:0049A20E 0 086                 pop     ecx
CODE:0049A20F 0 082                 not     ecx
CODE:0049A211 0 082                 not     [esp+82h+var_82]
CODE:0049A214 0 082                 and     [esp+82h+var_82], ecx
CODE:0049A217 0 082                 pushfw
CODE:0049A219 0 084                 jmp     loc_49A14F
CODE:0049A21E       ; ---------------------------------------------------------------------------
CODE:0049A21E
CODE:0049A21E       loc_49A21E:                             ; CODE XREF: sub_49A105+61j
CODE:0049A21E                                               ; DATA XREF: CODE:0049A34Eo
CODE:0049A21E 0 092                 lodsb
CODE:0049A21F 0 092                 add     al, bl
CODE:0049A221 0 092                 sub     al, 52h
CODE:0049A223 0 092                 not     al
CODE:0049A225 0 092                 sub     al, 3Eh
CODE:0049A227 0 092                 not     al
CODE:0049A229 0 092                 add     bl, al
CODE:0049A22B 0 092                 push    ax
CODE:0049A22D 0 094                 jmp     loc_49A14F
CODE:0049A232       ; ---------------------------------------------------------------------------
CODE:0049A232
CODE:0049A232       loc_49A232:                             ; CODE XREF: sub_49A105+61j
CODE:0049A232                                               ; DATA XREF: CODE:0049A36Ao
CODE:0049A232 0 092                 pop     ecx
CODE:0049A233 0 08E                 add     dword ptr [esp+8Eh+var_92+4], ecx
CODE:0049A236 0 08E                 jmp     loc_49A14F
CODE:0049A23B       ; ---------------------------------------------------------------------------
CODE:0049A23B 0 08E                 pop     edx
CODE:0049A23C 0 08A                 mov     dr5, edx
CODE:0049A23F 0 08A                 jmp     loc_49A14F
CODE:0049A244       ; ---------------------------------------------------------------------------
CODE:0049A244 0 08A                 pop     eax
CODE:0049A245 0 086                 mov     dr3, eax
CODE:0049A248 0 086                 jmp     loc_49A14F
CODE:0049A24D       ; ---------------------------------------------------------------------------
CODE:0049A24D 0 086                 fadd    [esp+86h+var_86]
CODE:0049A250 0 086                 jmp     loc_49A14F
CODE:0049A255       ; ---------------------------------------------------------------------------
CODE:0049A255 0 086                 pop     eax
CODE:0049A256 0 082                 push    small word ptr gs:[eax]
CODE:0049A25A 0 084                 jmp     loc_49A14F
CODE:0049A25F       ; ---------------------------------------------------------------------------
CODE:0049A25F 0 084                 mov     dx, fs
CODE:0049A262 0 084                 push    dx
CODE:0049A264 0 086                 jmp     loc_49A14F
CODE:0049A269       ; ---------------------------------------------------------------------------
CODE:0049A269 0 086                 fprem
CODE:0049A26B 0 086                 jmp     loc_49A14F
CODE:0049A270       ; ---------------------------------------------------------------------------
CODE:0049A270 0 086                 fst     [esp+86h+var_86]
CODE:0049A273 0 086                 jmp     loc_49A14F
CODE:0049A278       ; ---------------------------------------------------------------------------
CODE:0049A278 0 086                 fldln2
CODE:0049A27A 1 086                 jmp     loc_49A14F
CODE:0049A27F       ; ---------------------------------------------------------------------------
CODE:0049A27F 1 086                 fprem1
CODE:0049A281 1 086                 jmp     loc_49A14F
CODE:0049A286       ; ---------------------------------------------------------------------------
CODE:0049A286 1 086                 pop     eax
CODE:0049A287 1 082                 mov     cr2, eax
CODE:0049A28A 1 082                 jmp     loc_49A14F
CODE:0049A28A       sub_49A105      endp ; sp-analysis failed
CODE:0049A28A
CODE:0049A28F       ; ---------------------------------------------------------------------------
CODE:0049A28F                       fisub   word ptr [esp]
CODE:0049A292                       jmp     loc_49A14F
CODE:0049A297       ; ---------------------------------------------------------------------------
CODE:0049A297       ; START OF FUNCTION CHUNK FOR sub_49A105
CODE:0049A297
CODE:0049A297       loc_49A297:                             ; CODE XREF: sub_49A105+61j
CODE:0049A297                                               ; DATA XREF: CODE:0049A35Eo
CODE:0049A297 0 0CA                 fnclex
CODE:0049A299 0 0CA                 jmp     loc_49A14F
CODE:0049A299       ; END OF FUNCTION CHUNK FOR sub_49A105
CODE:0049A29E       ; ---------------------------------------------------------------------------
CODE:0049A29E                       pop     ecx
CODE:0049A29F                       pop     dword ptr fs:[ecx]
CODE:0049A2A2                       jmp     loc_49A14F
CODE:0049A2A7       ; ---------------------------------------------------------------------------
CODE:0049A2A7                       push    ebx
CODE:0049A2A7       ; ---------------------------------------------------------------------------
CODE:0049A2A8                       db 0Fh
CODE:0049A2A9                       db 0ACh ; 
CODE:0049A2AA                       db  8Bh ; 
CODE:0049A2AB                       db 0C0h ;
下面还有很多类似的,省略了。

在调试中,每次程序运行某个新功能(如点击一个按钮),都会执行该段代码。个人感觉,是传说中的一种保护机制+花指令,不知道大牛能否指点下。

比如,DeDe中显示的某个按钮对应的RVA地址是0049A2AC,内容如下:
loc_49A2AC:                             ; DATA XREF: CODE:00499B64o
CODE:0049A2AC                       push    7BA49400h
CODE:0049A2B1                       jmp     loc_5BE122      ;

loc_5BE122:                             ; CODE XREF: CODE:0049A2B1j
.jwx1:005BE122                                               ; .jwx1:005BF33Dj
.jwx1:005BE122                       push    offset dword_4AE970
.jwx1:005BE127                       jmp     sub_49A105

基本每个按钮都类似,两次jmp跳转后到了sub_49A105,然后该函数内部经历颠来倒去的执行后,再要执行一段pushf起始、popf+retn结束的代码,才执行程序真正的算法的代码。比如ollydbg中Ctrl+F9,到达0x005becd5(此时ollydbg的反汇编已经出错,或者一旦移动指令的滚动条,就出错了,保护起作用了?)

.jwx1:005BECD5                     pushf                   ; function:view
.jwx1:005BECD6                     neg     eax
.jwx1:005BECD8                     lea     eax, [eax+69FB4EBDh]
.jwx1:005BECDE                     inc     edx
.jwx1:005BECDF                     neg     edi
.jwx1:005BECE1                     neg     esi
.jwx1:005BECE3                     xor     ecx, 9EDF567h
.jwx1:005BECE9                     neg     edx
.jwx1:005BECEB                     not     eax
.jwx1:005BECED                     ror     edi, 16h
.jwx1:005BECF0                     not     ebx
.jwx1:005BECF2                     not     ecx
.jwx1:005BECF4                     rol     ebx, 2
.jwx1:005BECF7                     xor     eax, 0F9728541h
.jwx1:005BECFC                     dec     ecx
.jwx1:005BECFD                     not     ecx
.jwx1:005BECFF                     add     ebx, 434F8044h
.jwx1:005BED05                     neg     ecx
.jwx1:005BED07                     rol     edx, 16h
.jwx1:005BED0A                     not     edx
.jwx1:005BED0C                     xor     esi, 6E86D853h
.jwx1:005BED12                     bswap   ebx
.jwx1:005BED14                     sub     ecx, 54CCA5EFh
.jwx1:005BED1A                     rol     ebx, 1Eh
.jwx1:005BED1D                     sub     edx, 36E0F994h
.jwx1:005BED23                     xor     edx, 61305FE6h
.jwx1:005BED29                     lea     edi, [edi+695E8B0Eh]
.jwx1:005BED2F                     lea     ebx, [ebx+55BB756h]
.jwx1:005BED35                     neg     ebp
.jwx1:005BED37                     xor     ebp, 0F0A55AF4h
.jwx1:005BED3D                     inc     esi
.jwx1:005BED3E                     neg     ebp
.jwx1:005BED40                     not     esi
.jwx1:005BED42                     dec     ebp
.jwx1:005BED43                     rol     ebp, 17h
.jwx1:005BED46                     bswap   ebp
.jwx1:005BED48                     neg     esi
.jwx1:005BED4A                     ror     edi, 8
.jwx1:005BED4D                     xor     dword ptr [esp], 8D5h
.jwx1:005BED54                     rol     esi, 11h
.jwx1:005BED57                     popf
.jwx1:005BED58                     retn
.jwx1:005BED58     ; ---------------------------------------------------------------------------

上述这段代码执行后,程序执行正常的程序部分(位于CODE节中)

pushf和popf之间的代码是无效代码么?
如果创建函数,F5结果如下:

int __usercall sub_5BECD5<eax>(char _CF<cf>, char _ZF<zf>, char _SF<sf>, char _OF<of>, int a5<eax>)
{
  int result; // eax@1

  __asm { pushf }
  result = ~(1778077373 - a5) ^ 0xF9728541;
  __asm { popf }
  return result;
}
这样看来还是有些用的。。。

执行完该正常部分函数后,又回到如下代码:
.jwx1:005BE31D                     push    5557A4h
.jwx1:005BE322                     jmp     sub_49A105

可见最后又回到了sub_49A105。sub_49A105这个位置的代码几乎就是中枢神经的位置了。有点像派遣函数的作用。似乎所有的程序正常功能的使用必须通过sub_49A105才能执行。

此外,sub_49A105的F5经常出现问题,可能是对应的汇编代码实在比较特殊吧(好多花指令的手法么?)。

基本的保护机制已经分析完毕,看看高手知道或者用过这种保护方式的,指点下吧,比如代码怎么写的。

[培训]《安卓高级研修班(网课)》月薪三万计划,掌握调试、分析还原ollvm、vmp的方法,定制art虚拟机自动化脱壳的方法

收藏
免费 0
支持
分享
最新回复 (4)
雪    币: 144
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
没人看么。。。伤心了
2012-4-10 08:51
0
雪    币: 32
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
我看了,不过不懂啊
顶一下,让懂的同学看到
2012-4-10 09:20
0
雪    币: 144
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
4
看雪不给力厄


在别的论坛,有人说可能是VMP的壳,我想了下是有可能的:
1。保护了某个特定的一些函数
2。VMP中的区段的名字依稀记得是可以自定义的
3。sub_49A105可能就是VMP虚拟机的核心代码部分

此外,《加密解密三》中提到,
push bytecode
jmp VStartVM
这个形式与上文中的是吻合的。

最后,PEID复查下,看不出是VMP的,但我觉得应该是正常情况了 。


仅猜测,不知道熟悉VMP壳的大牛是否可以确认下
上传的附件:
2012-4-12 08:56
0
雪    币: 208
活跃值: (40)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
5
是早期比较老的TMD,那个GetCurrentThreadId后来的版本已经不用了。
应该是只用了VM的功能,没有做anti,估计OEP没有变化,这样查壳的话,还是显示原始的编译器。
2012-4-12 14:33
0
游客
登录 | 注册 方可回帖
返回
//