种好心田自有收!

寻找真正的入口(OEP)--广义ESP定律

上一篇 / 下一篇  2008-03-07 17:15:51 / 个人分类:实训项目

寻找真正的入口(OEP)--广义ESP定律
MG u Phk2t8C0
t;GU7vv+O{vHQY0作者:Lenus个人博客---梅州教育城域网JB8[3?J]tY
FROM: poptown.gamewan.com/bbs
{?*Hv%SvL?x0E-MAIL:Lenus_M@163.com
4qgi0k1X0
Q:_Qd x\01.前言
%b7[:[-k5FE0  
(uo4l!G?0  在论坛上看到很多朋友,不知道什么是ESP定律,ESP的适用范围是什么,ESP定律的原理是什么,如何使用ESP定律?看到了我在个人博客---梅州教育城域网m4?hq3W&U^|,[
个人博客---梅州教育城域网)}p eiG
http://poptown.gamewan.com/dispbbs.asp?boardID=5&ID=54&page=1个人博客---梅州教育城域网G(c AtQe(v+G"y{
个人博客---梅州教育城域网:?*P"Dpt
调查结果发现,大家对ESP定律很感兴趣,当然因为实在是太好用了,现在我就来告诉大家什么是ESP定律,它的原理是什么!!个人博客---梅州教育城域网]#n^%Bm:YX@

9X5Z7np%g!nai6Y0BTW:在看完了手动脱壳入门十八篇了以后,再看这篇文章也许会对你更有帮助!个人博客---梅州教育城域网M$MXNr7x+V k

)c.L Fw6`}L.E0在下面地址下载:
8W)e4Hkc Cy{0
c1N `5u cU/bu2y0http://soft.winzheng.com/SoftView/SoftView_23125.htm
ogeLQY1z0个人博客---梅州教育城域网Ua:X'W3m^n'W
2.准备知识
u3B0U*N;y-Uy0
bZ$Jh)tU$BJ0  在我们开始讨论ESP定律之前,我先给你讲解一下一些简单的汇编知识。个人博客---梅州教育城域网 BX \*{L%r X_
  1.call
[ cxF'e0  这个命令是访问子程序的一个汇编基本指令。也许你说,这个我早就知道了!别急请继续看完。
0`/TMu{"K M2c}}U0  call真正的意义是什么呢?我们可以这样来理解:1.向堆栈中压入下一行程序的地址;2.JMP到call的子程序地址处。例如:个人博客---梅州教育城域网v9]h'd!cYM _ Px

;Ui#{g^|_g000401029    .  E8 DA240A00    call 004A3508个人博客---梅州教育城域网2[!k$gX6M
0040102E    .  5A             pop edx个人博客---梅州教育城域网inlK%\
在执行了00401029以后,程序会将0040102E压入堆栈,然后JMP到004A3508地址处!个人博客---梅州教育城域网$V:f&M1R6g$sR
   个人博客---梅州教育城域网p6kEWd*O I'qZ
  2.RET个人博客---梅州教育城域网E^IS+C8d v+iUvS
  与call对应的就是RET了。对于RET我们可以这样来理解:1.将当前的ESP中指向的地址出栈;2.JMP到这个地址。个人博客---梅州教育城域网xl k~ R_'{/i~
  
"@.`(}1D"s:lF7u0  这个就完成了一次调用子程序的过程。在这里关键的地方是:如果我们要返回父程序,则当我们在堆栈中进行堆栈的操作的时候,一定要保证在RET这条指令之前,ESP指向的是我们压入栈中的地址。这也就是著名的“堆栈平衡”原理!
$H.xYSRe0
"~3[7H!T%},g!h"kG B03.狭义ESP定律
U;q]*Mk.V[~/j;u([0  个人博客---梅州教育城域网Zl5ZA\(`?@!zu
  ESP定律的原理就是“堆栈平衡”原理。个人博客---梅州教育城域网p~)U0f.z$r'Ou y
  个人博客---梅州教育城域网R/v^M1R6\xMN
  让我们来到程序的入口处看看吧!个人博客---梅州教育城域网Z#^6i k+m
  个人博客---梅州教育城域网7p(Z7A)Y9WIUB rh
  1.这个是加了UPX壳的入口时各个寄存器的值!个人博客---梅州教育城域网+q8_"P"\ N
EAX 00000000
_"@#a'n } yd(r0ECX 0012FFB0
-]%s c,[}e0EDX 7FFE0304
oO+P9[1]W*f%R0EBX 7FFDF000
-~G] U5Z ^D0ESP 0012FFC4个人博客---梅州教育城域网N!K'L f(a%Gi5R [R
EBP 0012FFF0个人博客---梅州教育城域网;Y2}:o'HecC7J
ESI 77F51778 ntdll.77F51778
ps5QJ.a$H P0EDI 77F517E6 ntdll.77F517E6
5c C?"F"~:RX q(L F0EIP 0040EC90 note-upx.<ModuleEntryPoint>个人博客---梅州教育城域网6n3E E\6@ t c
C 0  ES 0023 32bit 0(FFFFFFFF)
6~kvm8O+u~u/XI g0P 1  CS 001B 32bit 0(FFFFFFFF)
M4LEbDGJR!X0A 0  SS 0023 32bit 0(FFFFFFFF)
/UVh1sp0Z 0  DS 0023 32bit 0(FFFFFFFF)
yS6]KY+N.Ue0S 1  FS 0038 32bit 7FFDE000(FFF)个人博客---梅州教育城域网1p3p}PRzd2nK
T 0  GS 0000 NULL个人博客---梅州教育城域网0_B/M\hap4X
D 0个人博客---梅州教育城域网CI:us;@+p*E
O 0  LastErr ERROR_MOD_NOT_FOUND (0000007E)个人博客---梅州教育城域网0TYjJ9ui

;@Vz6~GG/g1?7}$H q W0  2.这个是UPX壳JMP到OEP后的寄存器的值!
/uk;LMC8P9lS)P0EAX 00000000
E|}S8KHHFt%W6h0ECX 0012FFB0
kn"M.? Tw D\}0EDX 7FFE0304
;AmRX0j;t0EBX 7FFDF000个人博客---梅州教育城域网3J(z xKbSN7l)G4X
ESP 0012FFC4
7qm `@0vc/X0EBP 0012FFF0
'A^(RP&Z]9Ds*`0ESI 77F51778 ntdll.77F51778个人博客---梅州教育城域网Uz-e2cr)[7l8j!?4]
EDI 77F517E6 ntdll.77F517E6个人博客---梅州教育城域网5d wT bGMf
EIP 004010CC note-upx.004010CC个人博客---梅州教育城域网 W`W6|`|n
C 0  ES 0023 32bit 0(FFFFFFFF)个人博客---梅州教育城域网!I(r,X?&b,YU*S8c
P 1  CS 001B 32bit 0(FFFFFFFF)个人博客---梅州教育城域网-UF I!W/Z:NP-GL
A 0  SS 0023 32bit 0(FFFFFFFF)个人博客---梅州教育城域网R5TI f-B"]$y1PE!f8o
Z 1  DS 0023 32bit 0(FFFFFFFF)
*l+V^i"},d!M0S 0  FS 0038 32bit 7FFDE000(FFF)个人博客---梅州教育城域网A0W%q { M%H}
T 0  GS 0000 NULL个人博客---梅州教育城域网 s0PnLl3D3q/U&p
D 0
g-Oo.~ GK9Z:Eg0O 0  LastErr ERROR_MOD_NOT_FOUND (0000007E)
%P]"XJ8G m-p0
u)`S"DpvsO%@b0呵呵~是不是除了EIP不同以外,其他都一模一样啊!
]:Qi"h_v&?FO0个人博客---梅州教育城域网}7i`my(nnz
为什么会这样呢?
fs-[eN9T }0我们来看看UPX的壳的第一行:个人博客---梅州教育城域网9zr^d]
个人博客---梅州教育城域网HJJ,R+d
0040EC90 n>  60               pushad      //****注意这里*****个人博客---梅州教育城域网k%nNE`
0040EC91     BE 15B04000      mov esi,note-upx.0040B015个人博客---梅州教育城域网e4f,f%]+O unrG.X
  
(N{4y.iy0PUSHAD就是把所有寄存器压栈!我们在到壳的最后看看:个人博客---梅州教育城域网?L%f'vpX_u"i

8e5c#_O.C7E op-l00040EE0F     61               popad      //****注意这里*****
5G-~JYe9O5L00040EE10   - E9 B722FFFF      jmp note-upx.004010CC   //JMP到OEP
e_ y4t"l I [0个人博客---梅州教育城域网*C o/nE8l&N2C
POP就是将所有寄存器出栈!个人博客---梅州教育城域网/G-L!S/B(Q8CXq
个人博客---梅州教育城域网f#]H }f
个人博客---梅州教育城域网up5U*W2I~v[ s
而当我们PUSHAD的时候,ESP将寄存器压入了0012FFC0--0012FFA4的堆栈中!如下:个人博客---梅州教育城域网yQC8u:f8}e N

5D0IO&@S,q9a#Y ~-t5u00012FFA4   77F517E6  返回到 ntdll.77F517E6 来自 ntdll.77F78C4E           //EDI 个人博客---梅州教育城域网'G7`i A6k$u
0012FFA8   77F51778  返回到 ntdll.77F51778 来自 ntdll.77F517B5          //ESI
L7e? `R(ZNY00012FFAC   0012FFF0                                                    //EBP
d#H[?gie;J00012FFB0   0012FFC4                                                   //ESP个人博客---梅州教育城域网?PUR5A
0012FFB4   7FFDF000                                                  //EBX个人博客---梅州教育城域网.qY&K ?l"N1Pww [
0012FFB8   7FFE0304                                                 //EDX
t D+J5R7Juw9z h00012FFBC   0012FFB0                                                //ECX个人博客---梅州教育城域网X:|m&X0L\
0012FFC0   00000000                                               //EAX个人博客---梅州教育城域网9m K%~"v[uy h'Kk
个人博客---梅州教育城域网3RR z&A8K8Q3R
所以这个时候,在教程上面就告诉我们对ESP的0012FFA4下硬件访问断点。也就是说当程序要访问这些堆栈,从而恢复原来寄存器的值,准备跳向苦苦寻觅的OEP的时候,OD帮助我们中断下来。个人博客---梅州教育城域网4ymA&x;Tp3Qs(x

e`6O3Mz1A[0于是我们停在0040EE10这一行!
;D/E2E)g6Sfg{0  
9xOEg+h6p~7}0g0总结:我们可以把壳假设为一个子程序,当壳把代码解压前和解压后,他必须要做的是遵循堆栈平衡的原理,让ESP执行到OEP的时候,使ESP=0012FFC4。
F"YTSj-o(j0
2al*N^"k9a&h6D04.广义ESP定律
Ei2Q'jx|`0
RK1f6ipRV0  很多人看完了教程就会问:ESP定律是不是就是0012FFA4,ESP定律的适用范围是不是只能是压缩壳!个人博客---梅州教育城域网/Vh*Ozhf6Jb)_
  个人博客---梅州教育城域网;S0h%W/k5SIX
  我的回答是:NO!
$y_"R,J1b/D$js-tc0
8o8Hx'zqMsg.WG6G0  看完了上面你就知道你如果用0012FFA8也是可以的,ESP定律不仅用于压缩壳他也可以用于加密壳!!!个人博客---梅州教育城域网 qJPOM} ~T4j
个人博客---梅州教育城域网 Ky^5h;TPRp7Po
  首先,告诉你一条经验也是事实---当PE文件运行开始的时候,也就是进入壳的第一行代码的时候。寄存器的值总是上面的那些值,不信你自己去试试!而当到达OEP后,绝大多的程序都第一句都是压栈!(除了BC编写的程序,BC一般是在下面几句压栈)
zA e,B2`O0个人博客---梅州教育城域网 jj_-hmn6Og U2A
  现在,根据上面的ESP原理,我们知道多数壳在运行到OEP的时候ESP=0012FFC4。这就是说程序的第一句是对0012FFC0进行写入操作!个人博客---梅州教育城域网*oA*VxY`J1Z3Se p
  个人博客---梅州教育城域网~!^ {s6oav/R]V
  最后我们得到了广义的ESP定律,对只要在0012FFC0下,硬件写入断点,我们就能停在OEP的第二句处!!个人博客---梅州教育城域网2gp;]%Be+h)I8H

)P`7N$gDTQ.o0下面我们来举个例子,就脱壳进阶第一篇吧!
[5uq C+X0
d#u ^R,yl0  载入OD后,来到这里:个人博客---梅州教育城域网'E4A~ {#~~+_;H

.d8xA0aOL00040D042 N>  B8 00D04000      mov eax,Notepad.0040D000 //停在这里个人博客---梅州教育城域网5@uz8H~&E$e'l-m\
0040D047     68 4C584000      push Notepad.0040584C
&P+X#c M EO.^&r*SY00040D04C     64:FF35 00000000 push dword ptr fs:[0]    //第一次硬件中断,F9个人博客---梅州教育城域网WZ5OlY^ p(EE
0040D053     64:8925 00000000 mov dword ptr fs:[0],esp个人博客---梅州教育城域网P?O e(eh
0040D05A     66:9C            pushfw
.z;[$R8Z0e MZ9_.ds{'j00040D05C     60               pushad
NB1M0RD-~4zg6{00040D05D     50               push eax
baXPa5oh0
)p9w$rb,|v$t0直接对0012FFC0下硬件写入断点,F9运行。(注意硬件中断)
7A C A^EK0
"TS2Ndwbp0在0040D04C第一次硬件中断,F9继续!
/Y ad2X(L0
#bpdqe r00040D135     A4               movs byte ptr es:[edi],byte ptr ds:[esi] //访问异常,不管他 shift+F9继续个人博客---梅州教育城域网I:FO@Zd `
0040D136     33C9             xor ecx,ecx个人博客---梅州教育城域网+bEMTK9Z
0040D138     83FB 00          cmp ebx,0
F:zYQ8Z6H9L ^00040D13B   ^ 7E A4            jle short Notepad.0040D0E1
tD5W3s(E7NKuR5o0个人博客---梅州教育城域网$|k:yE4H(d Xm/i
第二次硬件中断。个人博客---梅州教育城域网 ?M mh$cC'e9w(|D

.?vI7qG#{/AZ0004058B5       64             db 64                                 //断在这里个人博客---梅州教育城域网 o0de3PPL]8c9L
004058B6       89             db 89
0h%KVE(|5] Hc{0004058B7       1D             db 1D
kg:s J1g2|6M0004058B8       00             db 00个人博客---梅州教育城域网j*m S.c$fN
004058B9       00             db 00
J&twD/Q?8i0个人博客---梅州教育城域网Nw;qbhO*f(\u UvV
这里也不是,F9继续!
/tG `D} p0个人博客---梅州教育城域网;{V s)],a
004010CC   /.  55             push ebp个人博客---梅州教育城域网'LUQ7v d ED)I2f
004010CD   |.  8BEC           mov ebp,esp  //断在这里,哈哈,到了!(如果发现有花指令,用ctrl+A分析一下就能显示出来)个人博客---梅州教育城域网0p_sE}$pVXB;X
004010CF   |.  83EC 44        sub esp,44个人博客---梅州教育城域网4A3rgl'~9Sd"YC
004010D2   |.  56             push esi
0L5S y)D4MR3V0
D.Tn;Z\6Kc0   快吧!还不过瘾,在来一个例子。
0H IQ C7N(b0个人博客---梅州教育城域网x8be2\;J&j
   脱壳进阶第二篇个人博客---梅州教育城域网S&b6UrM:kEv{8vd|
个人博客---梅州教育城域网/a6T;DF:D
   如果按上面的方法断不下来,程序直接运行了!没什么,我们在用另一种方法!个人博客---梅州教育城域网HV2Wg,h O
  
&k/A"V[EkpB(w0   载入后停在这里,用插件把OD隐藏!
-f:~:iH4H0X!Eb0个人博客---梅州教育城域网(~,m_s:\p:v*J
0040DBD6 N>^\E9 25E4FFFF      jmp Note_tEl.0040C000                  //停在这里个人博客---梅州教育城域网Wtx eo5i/m
0040DBDB     0000             add byte ptr ds:[eax],al
Y!H"q$P UnT00040DBDD     0038             add byte ptr ds:[eax],bh
]p-Uv1g00040DBDF     A4               movs byte ptr es:[edi],byte ptr ds:[esi]个人博客---梅州教育城域网1D7Ii5K^!W1E&vQ
0040DBE0     54               push esp个人博客---梅州教育城域网2T+To._?-`\P{
个人博客---梅州教育城域网5^(N]CN
   F9运行,然后用SHIFT+F9跳过异常来到这里:
;Rd9SL Y8@*eu0
!R&H*aiL-D`"v00040D817   ^\73 DC            jnb short Note_tEl.0040D7F5       //到这里个人博客---梅州教育城域网:` NHp.BQ7i$J*W
0040D819     CD20 64678F06    vxdcall 68F6764个人博客---梅州教育城域网#aiix9Q:J"N
0040D81F     0000             add byte ptr ds:[eax],al个人博客---梅州教育城域网\P.~&R([4}d
0040D821     58               pop eax个人博客---梅州教育城域网Aos8|ptV
个人博客---梅州教育城域网/k/m!p Ok9?.^
   在这里对0012FFC0下硬件写入断点!(命令行里键入HW 12FFC0)SHIFT+F9跳过异常,就来到OEP的第二行处:(用CTRL+A分析一下)个人博客---梅州教育城域网P6Wu'@}W P
个人博客---梅州教育城域网`o D Fe Yz Z
004010CC   /.  55             push ebp个人博客---梅州教育城域网Z#Y*B$Ouh+I
004010CD   |.  8BEC           mov ebp,esp                       //断在这里个人博客---梅州教育城域网L1g d)SW.^
004010CF   |.  83EC 44        sub esp,44
ET o9Q~z*D&u0004010D2   |.  56             push esi
hXvE%Q&h0004010D3   |.  FF15 E4634000  call dword ptr ds:[4063E4]个人博客---梅州教育城域网+D)_`I,YT`
004010D9   |.  8BF0           mov esi,eax个人博客---梅州教育城域网*b PZ8k$x%Mj"H0~'?yg
004010DB   |.  8A00           mov al,byte ptr ds:[eax]
9h(w,k^A zY0004010DD   |.  3C 22          cmp al,22
jRA*i+u/H3yW O u3U0个人博客---梅州教育城域网h4YE |_-G&IA
   就这样我们轻松搞定了两个加密壳的找OEP问题!
IQb/HY0^D?OV0个人博客---梅州教育城域网 xO!a!s,iB`A
5.总结个人博客---梅州教育城域网tm] kG4spv q)v

&C j!Y M l3V ~ jA0  现在我们可以轻松的回答一些问题了。个人博客---梅州教育城域网#\1Hz1nx-F
  个人博客---梅州教育城域网%rD5S#U3po
  1.ESP定律的原理是什么?个人博客---梅州教育城域网["O/S.w FFc
个人博客---梅州教育城域网%nRMo~8S[ }2up
  堆栈平衡原理。
A mBx8X0  
7].I._ ]e/B$I0  2.ESP定律的适用范围是什么?
eU.S9c;`1Uh if@#g%KN0个人博客---梅州教育城域网*Z%c#Hj G2~/C
  几乎全部的压缩壳,部分加密壳。只要是在JMP到OEP后,ESP=0012FFC4的壳,理论上我们都可以使用。但是在何时下断点避开校验,何时下断OD才能断下来,这还需要多多总结和多多积累。欢迎你将你的经验和我们分享。个人博客---梅州教育城域网.xR{/J+zd*s6E
个人博客---梅州教育城域网q*U"Yz3lDq2V
  3.是不是只能下断12FFA4的访问断点?个人博客---梅州教育城域网^ d L$K\"N

_;n+f r rR5\1cC+Go/S9e0  当然不是,那只是ESP定律的一个体现,我们运用的是ESP定律的原理,而不应该是他的具体数值,不能说12FFA4,或者12FFC0就是ESP定律,他们只是ESP定律的一个应用罢了!个人博客---梅州教育城域网U H9V5O5@Bh~z%ebh
个人博客---梅州教育城域网e3RfhC@
  4.对于STOLEN CODE我们怎么办?
y6n"Fv B$CQ/CUE0个人博客---梅州教育城域网| fN|&lE
  哈哈,这正是寻找STOLEN CODE最好的办法!当我们断下时,正好断在了壳处理STOLEN CODE的地方,在F8一会就到OEP了!个人博客---梅州教育城域网&a8f"LcMm)w
个人博客---梅州教育城域网}$]'E)fL ["CQ5o|
6.后话个人博客---梅州教育城域网 C)LT:S!Z&g~;r9f
  
@A f2L HB4H\ P)@f0  个人博客---梅州教育城域网&Sh-P"F:I!z
  以上的方法原理都是我自己总结,自己的经验,如果有什么不对的地方,有什么没解释清楚的地方。还请海涵!但是如果觉得我很厉害,那就大可不必,因为ESP定律也是别人教我的,不是我第一个提出来的!我只是个比你们早飞一点的菜鸟罢了^-^个人博客---梅州教育城域网 h*rvB J dp
个人博客---梅州教育城域网"WA/f[n,F
  看了上面的文字希望能对你在寻找OEP的时候有帮助,但是别忘了一句话:菜鸟认为找OEP很难,高手认为修复才是最难! 好了,下一篇应该写IAT的修复原理了!让我们共同努力吧!
L#b6d H/^8M U0

TAG:

 

评分:0

我来说两句

显示全部

:loveliness: :handshake :victory: :funk: :time: :kiss: :call: :hug: :lol :'( :Q :L ;P :$ :P :o :@ :D :( :)

Open Toolbar