工具OD,以下是分析代码时的部分笔记,写的有点乱,有误之处还请指点

壳用到的SEH异常有 1,int3
                  2,int1
                  3,push pushfd
                    or dowrd ptr [esp],100
                    popfd //设置单步异常
F7,F8碰到第二,三种时,最好在SEH回调涵数中设断,再F9运行 

设置OD中断在系统事件

参考文章:simonzh2000 大侠的<<ExeCryptor 2.2.X 的 Anti Ollydbg 小结>>
1,OEP处的CC检测
在TLS callback 008Ac981 //TLS 回调涵数 F2调断
中断后的第一处SEH
seh回调涵数中修改eip的值 008A9499       C701 FCA68A00       mov dword ptr ds:[ecx],zhengtu.008AA6FC
得到预先保存的校验值     008AA6E7       8B00                mov eax,dword ptr ds:[eax]
进行比较,相等跳          008A5056       29D0                sub eax,edx
                         008A5058       0F84 D9340000       je zhengtu.008A8537

2,反dump 
得到peb   008A4EFB     64:8B05 >mov eax,dword ptr fs:[30]
得到peb.c 008A5DF6       81C0 30B5AB18       add eax,18ABB530
          008A5DFC       81C0 DC4A54E7       add eax,E7544ADC
          008A5E02       8B00                mov eax,dword ptr ds:[eax]

seh 修改eip 8AC2B0
得到模块信息 008AC526     8B00     mov eax,dword ptr ds:[eax]
修改镜像大小 008A5AB1     C702 001>mov dword ptr ds:[edx],1000

3,
修改的eip    008A86CC
seh中修改eip 008A73D5     C701 81A>mov dword ptr ds:[ecx],zhengtu.008AA781
seh中修改eip 008A5B0A     C701 C07>mov dword ptr ds:[ecx],zhengtu.008A70C0
seh中修改eip 008AB71F     C701 227>mov dword ptr ds:[ecx],zhengtu.008A7E22

得到PEB      008A4A50     64:8B05 >mov eax,dword ptr fs:[30]
             008AC621        03C7                add eax,edi//eax=eax+2
得到PEB.2    008A7AD3     8B00     mov eax,dword ptr ds:[eax]

比较PEB.2的值008A4C3F     08C0     or al,al
       008A4C41     0F84 E06>je zhengtu.008AB827

4,
得到PEB      008AA7E6     64:8B05 >mov eax,dword ptr fs:[30]
seh中修改eip 008A8F7A     C701 AF6>mov dword ptr ds:[ecx],zhengtu.008A69AF
得到PEB.68   008A69B9     81C0 1D0>add eax,FC450C1D
             008A69BF     81C0 4BF>add eax,3BAF44B//eax=PEB+68
             008A5E51     8B00     mov eax,dword ptr ds:[eax]//eax=PEB.68=70 OD调试时
seh中修改eip  008AA23E     C701 9BB>mov dword ptr ds:[ecx],zhengtu.008ABF9B
seh中修改eip  008A8BEC     C701 34908A00       mov dword ptr ds:[ecx],zhengtu.008A9034
seh中修改eip   008A83EF        C701 A37F8A00       mov dword ptr ds:[ecx],zhengtu.008A7FA3

比较测试值是否为70
             008A7631     68 5C49F>push A3F0495C
             008A7636     5F       pop edi
             008A7637     81C7 19E>add edi,C226E919
             008A763D     81CF E8F>or edi,6578F7E8
             008A7643     81F7 8DF>xor edi,677FF78D//edi=0x70
             008A7649     9D       popfd
             008A764A     85C7     test edi,eax//


修改的eip    8A9034
seh中修改eip 008A83EF     C701 A37>mov dword ptr ds:[ecx],zhengtu.008A7FA3

测试比较的结果008A53C8    /0F84 4E4>je zhengtu.008A9F1C

Test PEB.68,2
             008AA760     81F7 FC7>xor edi,BFFB77FC
             008AA766     85C7     test edi,eax//和2做test运算
             008AA768     873424   xchg dword ptr ss:[esp],esi
             008AA76B     8BFE     mov edi,esi
             008AA76D     5E       pop esi
             008AA76E     0F84 631>je zhengtu.008AC3D7


最开始的反调试就到这结束,接着就是解压代码,获得几个外壳需要的API地址
再接着就是重定位call 和 jmp 处的地址
//还原e8  和 e9 后的地址值 也就是call 和jmp bswap
0075455D        FC                  cld
0075455E        AC                  lods byte ptr ds:[esi]
0075455F        D0E8                shr al,1
00754561        80F8 74             cmp al,74
00754564        75 0E               jnz short zhengtu.00754574
00754566        8B06                mov eax,dword ptr ds:[esi]
00754568        0FC8                bswap eax
0075456A        01C8                add eax,ecx
0075456C        8906                mov dword ptr ds:[esi],eax
0075456E        83C6 04             add esi,4
00754571        83E9 04             sub ecx,4
00754574        49                  dec ecx
00754575      ^ 7F E7               jg short zhengtu.0075455E
00754577        59                  pop ecx
00754578        5E                  pop esi
00754579        C3                  retn

SEH反跟踪修改eip的指令  008A5CDB        C701 B45C8A00       mov dword ptr ds:[ecx],zhengtu.008A5CB4



//获得部分外壳需要的API
008AC77F      /0F84 E0000000       je zhengtu.008AC865
008AC785      |F7C3 00000080       test ebx,80000000
008AC78B      |0F85 04000000       jnz zhengtu.008AC795
008AC791      |8D5C13 02           lea ebx,dword ptr ds:[ebx+edx+2]
008AC795      |81E3 FFFFFF7F       and ebx,7FFFFFFF
008AC79B      |53                  push ebx
008AC79C      |FF75 F8             push dword ptr ss:[ebp-8]
008AC79F      |FF15 BC407500       call dword ptr ds:[<&kernel32.GetProcA>; kernel32.GetProcAddress
008AC7A5      |09C0                or eax,eax
008AC7A7      |0F84 0B000000       je zhengtu.008AC7B8
008AC7AD      |8907                mov dword ptr ds:[edi],eax
008AC7AF      |8345 F4 04          add dword ptr ss:[ebp-C],4
008AC7B3     ^|E9 A6FFFFFF         jmp zhengtu.008AC75E
008AC7B8      |53                  push ebx

seh修改eip  008A94C4       C701 B9C08A00       mov dword ptr ds:[ecx],zhengtu.008AC0B9
seh修改eip  008A4CDB       C701 19A48A00       mov dword ptr ds:[ecx],zhengtu.008AA419

.....
CheckRemoteDebuggerPresent 检测是否被调试
007230CF        50                  push eax//当前进程ID
007230D0        FF55 F4             call dword ptr ss:[ebp-C]//CheckRemoteDebuggerPresent
007230D3        85C0                test eax,eax//测试返回值

......

之后就创建的16个子线程,很惭愧,由于功力不够,没有把子线程分析出来
......

在代码段 查找FF 15 就能知道,输入表的地址是61d000段

以下是壳解密API地址的代码部分分析

0072A862      8955 F8          mov dword ptr ss:[ebp-8],edx           ; ebp.8=edx=API加密值
0072A865      8945 FC          mov dword ptr ss:[ebp-4],eax           ; ebp.4=eax=hMoudle
0072A868      33C0             xor eax,eax
0072A86A      8945 F4          mov dword ptr ss:[ebp-C],eax           ; ebp.c=0=计数用...
0072A86D      837D FC 00       cmp dword ptr ss:[ebp-4],0
0072A871    ^ 0F84 9694FEFF    je zhengtu.00713D0D                    ; if hMoudle == NULL 跳

00752B0A      871424           xchg dword ptr ss:[esp],edx
00752B0D      5A               pop edx                                ; add esp,4
00752B0E      8945 F4          mov dword ptr ss:[ebp-C],eax           ; ebp.c=eax=0
00752B11      837D FC 00       cmp dword ptr ss:[ebp-4],0
00752B15    ^ 0F84 F211FCFF    je zhengtu.00713D0D                    ; 比较模块句柄是否为0
00752B1B      8B45 FC          mov eax,dword ptr ss:[ebp-4]
00752B1E      83C0 3C          add eax,3C                             ; 得到模块的pe的RVA
00752B21    ^ E9 AF5CFDFF      jmp zhengtu.007287D5
007287D5      8B00             mov eax,dword ptr ds:[eax]             ; eax=RVA  PE结构
007287D7      0345 FC          add eax,dword ptr ss:[ebp-4]           ; RVA+hModule=PE结构VA
007287DA      83C0 18          add eax,18                             ; +18=可选头
007287DD    ^ E9 E6CAFEFF      jmp zhengtu.007152C8
00731165      8945 F0          mov dword ptr ss:[ebp-10],eax          ; ebp.10=PE.可选头
00731168    ^ E9 97B5FFFF      jmp zhengtu.0072C704

0073421C      8B45 F0          mov eax,dword ptr ss:[ebp-10]
0073421F      8B40 60          mov eax,dword ptr ds:[eax+60]          ; eax=数据目录表
00734222      0345 FC          add eax,dword ptr ss:[ebp-4]           ; +基址
00734225      8945 EC          mov dword ptr ss:[ebp-14],eax          ; ebp.14=eax=IET 输出表
00734228      8B45 EC          mov eax,dword ptr ss:[ebp-14]
0073422B      8B40 18          mov eax,dword ptr ds:[eax+18]          ; eax=IET.NumberOfFunctions 涵数个数
0073422E      48               dec eax                                ; 个数-1
0073422F      E9 F6570000      jmp zhengtu.00739A2A
00739A2A      85C0             test eax,eax                           ; 如果输出涵数个数小于=0,跳
00739A2C    ^ 0F8C DBA2FDFF    jl zhengtu.00713D0D
00739A32      40               inc eax                                ; 项++
00739A33      8945 DC          mov dword ptr ss:[ebp-24],eax          ; ebp.24=导出涵数个数
00739A36      C745 E8 00000000 mov dword ptr ss:[ebp-18],0
00739A3D      8B45 EC          mov eax,dword ptr ss:[ebp-14]          ; eax=ebp.14=IET
00739A40      8B40 20          mov eax,dword ptr ds:[eax+20]          ; eax=IET.Base=基址
00739A43    ^ E9 805EFDFF      jmp zhengtu.0070F8C8
0070F8C8      0345 FC          add eax,dword ptr ss:[ebp-4]           ; eax+hModule=导出涵数数组
0070F8CB      33D2             xor edx,edx
0070F8CD      52               push edx                               ; push 0
0070F8CE      50               push eax                               ; push 导出涵数数组
0070F8CF      E9 D6C50000      jmp zhengtu.0071BEAA
0071BEAA      8B45 E8          mov eax,dword ptr ss:[ebp-18]          ; eax已处理涵数计数
00712610      C1E0 02          shl eax,2                              ; 序号*4
00712613      99               cdq
00752682      8B00             mov eax,dword ptr ds:[eax]             ; 取导出涵数项的RVA
0071B87F      0345 FC          add eax,dword ptr ss:[ebp-4]           ; RVA+hModule

00730F50      FF45 F4          inc dword ptr ss:[ebp-C]               ; 涵数名数组++

007311AD     /0F85 1E7F0100    jnz zhengtu.007490D1                   ; != NULL 跳
007311B3     |8B45 FC          mov eax,dword ptr ss:[ebp-4]           ; 得出涵数名长度
007311B6     |8945 F4          mov dword ptr ss:[ebp-C],eax
007311B9     |C165 F8 08       shl dword ptr ss:[ebp-8],8             ; 涵数名长度左移8位???
00708209      0FB600           movzx eax,byte ptr ds:[eax]            ; eax=取涵数名的字节值
0070820C      0145 F8          add dword ptr ss:[ebp-8],eax           ; 长度左移8位后+涵数名字节
0070820F      8B45 F8          mov eax,dword ptr ss:[ebp-8]
00708212      C1E0 0A          shl eax,0A                             ; 再左移A位

即出循环
00712CE2      8B45 F8          mov eax,dword ptr ss:[ebp-8]           ; 取涵数名运算后的值
0074505D      C1E0 03          shl eax,3                              ; 运算后的值左移3位
007236AA      C1E8 0B          shr eax,0B                             ; 左移B位
007236AD      3145 F8          xor dword ptr ss:[ebp-8],eax           ; 异域
007236B0      8B45 F8          mov eax,dword ptr ss:[ebp-8]
007236B3      C1E0 0F          shl eax,0F                             ; 左移F位
007236B6    ^ E9 2520FFFF      jmp zhengtu.007156E0
007156E0      0145 F8          add dword ptr ss:[ebp-8],eax
007156E3      68 B6947100      push zhengtu.007194B6
007194B6      8B45 F8          mov eax,dword ptr ss:[ebp-8]           ; eax=涵数名的运算值 ----涵数返回
007194B9      8BE5             mov esp,ebp
007194BB      5D               pop ebp
007194BC      C3               retn

0071B882      E8 D4E80000      call <zhengtu.Get涵数校验值>//以上为该涵数的运算
0071B887      3B45 F8          cmp eax,dword ptr ss:[ebp-8]           ; 比较还回的值校验值,是否是需要寻找的API
0071B88A    ^ 0F85 9499FFFF    jnz zhengtu.00715224                   ; 不相等继续
0071B890      E9 9AE30100      jmp zhengtu.00739C2F                   ; 相等,跳-----------------------------------在此外下断,就能得到API的真实地址


以下是修复IAT的代码
随便找一块空白区域
写上
//修复输入表写上去的代码
00753F26          55               push ebp
00753F27          BE 68D06100      mov esi,zhengtu.0061D000            ; //未处理IAT首地址
00753F2C          AD               lods dword ptr ds:[esi]
00753F2D          3D 00000010      cmp eax,10000000
00753F32        ^ 77 F8            ja short zhengtu.00753F2C
00753F34          85C0             test eax,eax
00753F36        ^ 74 F4            je short zhengtu.00753F2C
00753F38          8935 40387500    mov dword ptr ds:[753840],esi       ; //保存IAT地址
00753F3E          BB 4B3F7500      mov ebx,zhengtu.00753F4B            ; //保存还回的地址
00753F43          891D 44387500    mov dword ptr ds:[753844],ebx
00753F49          FFD0             call eax
00753F4B          8B35 40387500    mov esi,dword ptr ds:[753840]       ; //还原IAT地址
00753F51          8946 FC          mov dword ptr ds:[esi-4],eax        ; //保存值
00753F54          81FE 20D36100    cmp esi,zhengtu.0061D320            ; //比较输入表是否被处理完毕
00753F5A        - 77 FE            ja short zhengtu.00753F5A           ; //大于进入死循环
00753F5C        ^ EB CE            jmp short zhengtu.00753F2C          ; //跳回接着处理

然后在壳解密出API真实地址处写上以下代码:
0070A27E          8B1D 44387500    mov ebx,dword ptr ds:[753844]       ; 返回自已写的代码处,继续处理下一个API
0070A284          53               push ebx
0070A285          C3               retn


到此,代码已解开,IAT也修复了,但OEP被抽取的代码,盼望大侠指点