数学建模社区-数学中国
标题:
用OllyDbg脱ASPR 1.3x的壳
[打印本页]
作者:
韩冰
时间:
2004-10-6 10:49
标题:
用OllyDbg脱ASPR 1.3x的壳
作者:LaBBa
: b! B$ w, {* t1 X) p
翻译:gmh001
0 k) p1 K! ^9 O" G' y
软件: System Cleaner 4.89 Build 110
( s4 u( I2 S* C" f; r X
Url : http://www.allerasoft.com/products/systemcleaner/
F/ B3 a1 M1 M4 V. @& _
* _$ |% g3 g1 g6 c. E
前言
! @, k3 d; G+ Z, b" f0 ~0 V
==================
9 ]% ^$ W- i5 x2 z8 W( f+ Q$ q
OK,贴上来!!这是我第三次写这篇破解文章,第一次正在写的时候机死机了,第二次停电了。
) z' d; v3 ~! M+ W5 b" g: g o6 D1 L
(呵呵,运气有点背啊…)
$ }& L/ N2 S$ b! m. `( J
现在…
5 ^$ F- Z' @ k0 D
: U; e) B* \% T! p( ?
这篇文章讲述如何真正快速简单的脱掉ASPR 1.3x的壳,并且找出被抽掉的字节…
" d) C% F4 l9 o- {3 ?* S3 b1 V# X
并且不使用SoftIce、IceDump和 /tracex!用什么?使用OllyDbg !
4 O0 V4 M" E x6 [: K; x
3 [. D4 ~5 B) ?+ ], Q* L% I
所需工具
' J% o) D; }3 |
================
5 a! a8 i: _" d& ^0 o5 v7 R
1. OllyDbg 1.09b2 or newer
1 u* V! ^' w+ s m/ {$ T
2. ProcDump(G-rom)/Pe-edit(y0da)
0 _8 K7 M- `7 P
3. imprec 1.3 (MackT/UCF)(protools.cjb.net)
$ q# d; ]$ \; Z! k* D8 w% B. u
4. HVIEW / Hex Editor
0 u+ M3 D& D3 n- ~ n
' B7 l7 K5 V5 R/ T& U% {+ n
脱壳步骤
/ W1 n- y' H% U0 U* w7 k9 A
=======================
9 i# T- F# _) L1 ]. D
1. 找到 OEP+从内存中抓取程序
3 w: U" b2 K3 @
2. 找到抽掉的字节
9 C, L& M$ K w) l/ |* m
3. 重建IAT
! F; n! f! i5 B/ Z" } e- o1 d- c$ `
4. 修正OEP
& Z* K- x, z+ i0 ^% {& m6 I, Y2 n
5. 结束
# `0 e% W6 \& d2 H7 Z
: V# m0 I8 L$ |4 H1 Y9 {3 s! C# |$ F$ F
* S9 z. q V& u/ {) w! I
====================================
* T2 k. W2 I# q5 v! z3 ~8 J
第一步—找到 OEP+从内存中抓取程序
5 x+ T) b+ h- R# f; C3 v
====================================
4 b/ ?/ n' W- R
: U1 h" w# ?, j5 l: D
1. 运行Olly并载入应用程序(如果有提示就按 YES!)
3 c+ D0 X& q" r- G: s! }+ J
2. 现在按F9就会在这儿中断:
" ?) g9 f" X- ~$ N5 J4 a& x+ f
) J" l5 q; n% D2 G$ O: |
017E3414 3100 XOR DWORD PTR DS:[EAX],EAX 〈-我们在这儿中断!
' ^8 n3 T% A& x/ z5 H( F5 E
017E3416 EB 01 JMP SHORT 017E3419
1 f" V. ~ n: @4 a4 x3 J
017E3418 68 648F0500 PUSH 58F64
2 {( U/ F3 L4 }4 T: R D7 R1 ]
: z' U3 n3 Y( r; M; @$ z0 Q
为什么Olly会中断?我们不用设断点吗?!
# h( p4 K& ^* {6 \5 @3 U
呵呵,Olly在每次进入一个新模块时都会中断…我们将继续使用它!!
. |& t1 t! E" d2 k; q" a k
7 c( a5 {0 ?% X# D2 |8 r: O; g
3. 按Shift+F9,这样Olly会继续运行直到遇到一个新模块。
d0 A5 ^% a& I$ N$ I
4. 按Shift+F926次后我们将到达这里:
: ^) O a- `# `8 Q5 E( h* M
. W, Y! x( d0 z/ n M7 K" d
017E2D7A 3100 XOR DWORD PTR DS:[EAX],EAX〈-我们停在这里
% n8 N C* E9 o ?1 \) e4 ?; \
017E2D7C 64:8F05 00000000 POP DWORD PTR FS:[0] 〈在这里设断点
) ~5 P" l) L0 N& M7 S
017E2D83 58 POP EAX
- r% a0 K; k; Z& x; M. ~0 \
017E2D84 833D 806D7E01 00 CMP DWORD PTR DS:[17E6D80],0
0 |- ]2 K4 t# |( P6 ~% ^, J
017E2D8B 74 14 JE SHORT 017E2DA1
2 _# a" i% Z6 @
017E2D8D 6A 0C PUSH 0C
/ g: Z! {4 v7 G8 W, g2 {# X- G
017E2D8F B9 806D7E01 MOV ECX,17E6D80
* y. J: q [& `6 \7 ?( U: l |
017E2D94 8D45 F8 LEA EAX,DWORD PTR SS:[EBP-8]
6 ]% l0 \5 I: l; n+ R
017E2D97 BA 04000000 MOV EDX,4
! R" d! P2 {4 J0 s% I! A" T+ i
017E2D9C E8 EFE0FFFF CALL 017E0E90
0 G. ?3 | [7 I! E, g* l' [' C2 ]
017E2DA1 FF75 FC PUSH DWORD PTR SS:[EBP-4]
) S9 d/ _3 Z2 w! w. y9 L! ^
017E2DA4 FF75 F8 PUSH DWORD PTR SS:[EBP-8]
0 a/ d) w* B+ _
017E2DA7 8B45 F4 MOV EAX,DWORD PTR SS:[EBP-C]
8 M. Q( E9 i, u* o, k6 m# U) i
017E2DAA 8338 00 CMP DWORD PTR DS:[EAX],0
1 f0 x: D+ K1 M6 j3 }
017E2DAD 74 02 JE SHORT 017E2DB1
- S8 Y4 }. q2 D2 v! l$ k, L
017E2DAF FF30 PUSH DWORD PTR DS:[EAX]
% a: T l! p4 c; w5 i; z
017E2DB1 FF75 F0 PUSH DWORD PTR SS:[EBP-10]
V! l5 L+ r! e
017E2DB4 FF75 EC PUSH DWORD PTR SS:[EBP-14]
4 b1 B, |/ O& i; y1 R8 v+ {
017E2DB7 C3 RETN
3 `9 K h3 |1 w( l7 d# @: {
+ n; l& S" w6 g( ^5 i; O: G
如果我们再按一次Shift+F9,软件就运行了…千万别这么做!!
, T1 i4 t3 B# p7 D: e! O- H+ i
$ |9 W1 U) u0 N" N7 J+ A
5. 现在我们向下移光标,到这里:
4 L" x* F( X2 z/ q
# i$ V5 g2 ^1 x( ^
017E2D7C 64:8F05 00000000 POP DWORD PTR FS:[0]
8 }1 Q7 w$ J* H
# z; @* M/ d) a3 ^9 \: ?4 H
按 F2(设断点)。
! }: y6 G. i/ |3 w: j- v# D4 A
再按Shift+F9,Olly就会在断点中断。
3 k6 F- `& Q7 Q9 H: W
7 [+ h9 c. c7 Z) D/ d( o
6. 现在按F8单步追踪,执行RETN将会到达这里:
' w2 D; _, x- O: O" L; y; a
* w; P Q; q! X( T4 Z1 Y
017F4EC8 E9 080A0000 JMP 017F58D5 〈-在这里
" {/ i+ |( G# S9 s! N( l* ^# C
- J6 ~" @' i$ Y9 L
按F8执行这个跳转…
. k, P' F7 ~# g( O8 B
现在我们来到这里:
0 V1 _/ G- G% `6 s, H+ X
017F58D5 D3DE RCR ESI,CL 〈-停在这里
% O$ z( z- C4 c( F! v; u6 K
017F58D7 B9 7D966271 MOV ECX,7162967D
) c9 s- w' A0 z! z( a
017F58DC 81C1 38F10A23 ADD ECX,230AF138
7 G) w; R, Z+ T o% W5 e7 m+ ^
017F58E2 D3EE SHR ESI,CL
) h" M2 K* `' I/ i& @- v" k4 X; K
017F58E4 BA 9ECC7376 MOV EDX,7673CC9E
: |/ M2 a# E5 M# @9 W
017F58E9 81EA C56EFFD4 SUB EDX,D4FF6EC5
6 N! N) s9 O& h' m: |- e% Q
017F58EF 81F2 B7104902 XOR EDX,24910B7
( r. r5 C( T# I$ i( w
017F58F5 C1CA 94 ROR EDX,94
W3 ]0 K7 U: [" `8 B5 I/ X! s' V$ P
017F58F8 8BF2 MOV ESI,EDX
* T" Z* }1 ~- S: D; }* \
017F58FA 81EE 87D851D2 SUB ESI,D251D887
c% t. B* x+ F7 g R6 f1 l
017F5900 C1CE B0 ROR ESI,0B0
, Q* G% h. {# W+ a* g3 T
017F5903 8BC6 MOV EAX,ESI
: U2 O# Y* Q/ a. L: P9 o+ r
017F5905 C1C8 28 ROR EAX,28
* E4 r- {0 T9 c9 A, v7 X: w( |4 {8 S1 s, o
017F5908 53 PUSH EBX
4 I+ }& P+ a' A, y, \& G- w' w
017F5909 5E POP ESI
2 R8 ^$ _: W, R' E$ s# d5 [
017F590A 81C5 974FAF73 ADD EBP,73AF4F97
7 f7 m5 b- G8 |$ M* m$ Y
017F5910 BA 048A9178 MOV EDX,78918A04
9 n/ z, }! a% N: C G5 d/ z
017F5915 F7D2 NOT EDX
6 m' P- r2 k; ~* a
017F5917 F7D2 NOT EDX
- U) }% A$ [! [$ ~* ?+ {7 r7 n
017F5919 81C2 FC756E87 ADD EDX,876E75FC
- b- ~' Z/ F. _3 W+ h9 |) L
017F591F 8BDA MOV EBX,EDX
, Y" k3 V0 M1 I; p
017F5921 41 INC ECX-------------------------
g8 W1 x3 S0 @6 J
017F5922 8BD9 MOV EBX,ECX |
5 U6 Z5 d+ n n L* Y# \
017F5924 D1C3 ROL EBX,1 | a Realy Long
3 y, U6 z1 Q% y/ [( C
017F5926 81F3 A38FD7AC XOR EBX,ACD78FA3 | Loop
, d+ \( b* a' D
017F592C 3BD8 CMP EBX,EAX |
1 \3 Z4 W( K# F9 I+ U/ x, P# t
017F592E ^0F85 EDFFFFFF JNZ 017F5921--------------------
! l( o' R& i1 E/ y4 _0 Y
017F5934 8BC1 MOV EAX,ECX 〈〈-在这里设断点!!
/ V& w5 y+ R/ Z5 X/ U1 P
. h& |% H( v8 e# `7 L! I' {4 v' G Y
好了,我们可以不用通过按 F8 来追踪整个循环!!我们在下面的指令上设一个断点:
8 D, l& f0 S5 r7 ?
* z* g1 u! a3 w0 Y
017F5934 8BC1 MOV EAX,ECX
" v: y- G- B1 U# [, Q/ T
+ ~8 _2 `8 G% ?" y6 |! ~# Q
设置断点后(F2),按F9(运行),将会在断点上停下来。
: K2 ]" T* U6 o* G# e( K, W
! g" N6 d- W/ {( E/ W8 [
7. 为什么??总是用F8 / F7追踪??!!
% ]4 P- Z# }7 q- z, a! {0 g
好吧…不!!
* g3 D$ v6 n! H$ H
Olly里有一个很好的功能:调用命令行。
, X" g \: q0 I4 ^/ x( r" d" J
从菜单里选择:Plugins->Command line->Command line
. A! e" b8 v; U+ u" O1 \% c& d
3 V! v# n; Q) y- x P( E" o+ u% D2 Q0 q
现在我们将写一个条件追踪命令!
1 Q; P) O$ d" g* M$ |& h1 d
YES ! Olly有一个追踪命令!它调用-TC-条件追踪
" q0 @( k" m2 H1 i7 R& q
它将会在条件表达式为真时中断!
- F1 u9 y# T" [5 H; W
8 S9 K% P# L/ t' P# m
这样…在文本框里写入:TC EIP<900000
+ b' R4 ` G% J: h
按Enter键。
( Q# J3 R; v# G
在窗口的右下会出现:“正在追踪”
3 b( m1 n4 ~; A$ d
0 ^% b6 `3 t. ]& W1 h9 T& j+ C
我的机子慢,花了大约8分钟(350MHz)
* L9 K+ s6 |8 N& W) N
在另一台较快的机子上花了2分钟多一点(900MHz Celeron)
6 l H! r% K1 ~+ R, y& Z
( ~, ]4 n/ P4 Z7 H
8. 追踪完成后中断在这里:
. K, } t' B$ Y+ m; q
4 c( J& n+ Y5 c; r
0057EA5B E8 DB E8
J' C+ x# B7 B& _ O
0057EA5C 00 DB 00
3 u/ o! y N9 b
0057EA5D 8A DB 8A
& M- M- i. ^' ]3 x
0057EA5E E8 DB E8
( e& L/ }, L& f: e P9 _) k
0057EA5F FF DB FF
! U+ e- f( w! @" ^/ m, G
$ d1 y/ _5 I0 c+ |- W3 V* U
嘿!! i Dont See Shit !!这是为什么?!
- `% r* ^0 y& O) Q5 f2 X/ {
噢,Olly没有分析这段代码,实际上我们并没有真提停在OEP上!
+ r: N0 |- {5 @' `9 a( P+ @
OEP=57EA5B
% M" r+ J9 Q, X: j. o9 F1 f
+ `6 s) }$ K, E3 c" e
9. 重点!! 在OEP处看盾EAX值(CPU窗口的右上面)
- A3 l% S t5 Y# m- S7 D) ^
EAX=57E318
& i' r3 ]0 G! G2 |: ]( g9 o
记住它,以后会用到它的。
( t. P0 {4 M o7 W5 L- b8 Q
/ H3 U) Y ^' }) k' ]1 |
10. 打开 ProcDump/Pe-Edit,完全抓取进程。
/ M$ x" W% C) O
% h+ d7 K3 h9 n6 ?8 c' Z$ B
===================================
- y5 U( t/ N7 h( f$ O: X
第三步-找出抽掉的字节=
- {# ^8 }) p4 K' Y& L
===================================
3 E% Q, P( u# b" v j1 w
1 s! {3 W) _0 F8 f" L2 M, P
找出抽掉的字节有三种方法:
5 R9 | Z8 T9 T, E( }8 n0 ?
0 S4 x Q' m& B$ c. J; g
1. ASPR会执行抽掉的字节,象下面这样跳转到OEP:
( x) ?& Z' u1 z$ C8 x
0 v. l+ q) W/ \9 A2 ~1 D
Stolen_Bytes_1
! [. o0 J X3 L j6 l: ~) Q
Stolen_Bytes_2
I# } o' P' d. `+ F3 x4 P
Stolen_Bytes_3
, _; e6 Y1 ^; Y. T
.....
, S! B u; v, x
.....
7 c' W3 a8 w0 Y% _; q
PUSH_THE_ADDRESS_OF_OEP
1 q; x o. q7 I. w! Z
RET_TO_OEP
+ R9 @& a: i f; P! C j
5 y) N0 \9 i# r' t1 b; x$ p4 c0 _
2. ASPR首先保存抽掉的字节,然后从OEP处还原,再象下面这样跳转到OEP:
3 U3 O/ J' Y( _( \' {1 Y
' U" S! T2 }4 k4 v. ]4 \
Stolen_Bytes_1
/ u: l( v3 w) `( p
Stolen_Bytes_2
8 l' P5 `" A4 Z( \
Stolen_Bytes_3
2 B% y- @* y+ Z
PUSH EBX
! v3 Y$ r& T0 H" J% k, T. v. R3 \
PUSH ESI
+ E2 q6 E/ @; C) Q
PUSH EDI
' V" ]9 r- G2 a
......
/ v; E) t0 b7 E" k
......
* |4 f$ q. ^1 {7 d* y
......
! i# j* U, W/ X* i- A. x1 W
REPZ STOSB 〈-还原字节
4 L, Y! d" {+ ?. g) L }
POPFD
% M3 ?7 o( V+ s
POPAD
! E3 y' n# o7 }
JMP_TO_OEP
) H/ v5 ?8 M& x6 L
" B/ n# |2 X% d0 M) j1 [. m
3. 没有抽掉的字节时,只执行PopAD指令和跳转到OEP。
7 P9 J# {; J) ~2 I
6 ?8 k7 x+ H: _% s: z* D2 k
那么我们怎么处理它呢?
6 H" ]7 p' r* X2 O/ ~8 |% c
看看ASPR在跳转到OEP前的最后几步是什么。这需要查看跟踪日记。
( J! u9 a/ d- a2 k* C
太好了!Olly可以使用"Run Trace"功能来得到一个 跟踪日记。
: o9 g1 Q+ a, Y7 _8 a; y
这样…选择菜单: View->Run trace
' n5 H# k, a# w) ~% h2 A
现在我们看见一个新窗口…跳转到最后一行的前一行,你会看到CPU窗口也变为同样的地址,象下面这样:
' O9 \2 Q$ v% f1 C& [
5 |9 N- ?" W& Z1 [3 |
017F5779 F3:AA REP STOS BYTE PTR ES:[EDI]
5 L7 ~- n9 ?) G7 A4 H0 H! x& ^% }
017F577B 9D POPFD
6 }/ O7 L R/ H) `" o
017F577C 61 POPAD
# F% c2 `7 N% Z2 |8 K4 E: A$ H" ]
017F577D -E9 D992D8FE JMP SYSTEMCL.0057EA5B 〈-OEP的地址
; U( s" ?& q) S
. f& t/ ~5 J% p0 l
我们用第二种方法对付它!!
S: a: B" h' }0 o' F8 D
0 Q2 J% \5 t% t$ w9 Z4 N
上面的内容我是在 winXP下发现的,不是 win98::
8 D( C' l' B' n% X2 E
在CPU窗口里按 Ctrl+S(搜索命令的次序)
; q/ O7 Q" s0 E- j; e1 e
写入下面的:
, l- a d; J' U! h" U
$ g* G9 C0 d: B4 w/ l
PUSH EBX
8 u x3 [; s! g
PUSH ESI
! G7 a# ^& M$ X/ v) u) {* F; M- l1 Y, l
PUSH EDI
) s2 {. C3 Y1 I+ X
) I' S$ i5 u3 i n" q. `% i
你会发现:
9 c) K! q# t' A9 [1 h
7 F# m& K: T8 N* p# Y
01029227 0055 8B ADD BYTE PTR SS:[EBP-75],DL
5 v3 ]3 u' b0 h& Y( {
0102922A EC IN AL,DX ; I/O命令
8 x* Z+ S! ]1 M9 q
0102922B 83EC 54 SUB ESP,54
( j$ }% W# t& F6 ? H
0102922E 53 PUSH EBX
" v% P) U! V# i: I s9 A5 D8 t! m
0102922F 56 PUSH ESI
% T* ~+ ?7 b( x% A3 P$ ]
01029230 57 PUSH EDI
+ a) ~6 C5 O8 V6 h
01029231 6A 11 PUSH 11
0 c1 m6 M* e1 Y' Y8 n1 Z
4 A. A- O/ J( @5 S) l/ {( W
忽略 "00",你会找到抽掉的字节:55,8b,ec,83,ec,54
( o& |- j4 \: N! K' [
记下它们,以后会有用的…
# L% c. O. o# N8 h, h3 \; @4 A
0 F. `& z3 a. d$ r, J
关闭OLLY…
3 y: X7 G1 Z7 w4 c' u
目前是不需要它啦…
2 B* m) W3 c) T, S0 c2 o% v# B
4 p) @2 T, [8 e4 O+ ~2 k! X" n8 ?6 H
( S: Y0 i' N8 a1 j
=============================
$ N$ V3 l3 Z( u: H1 v" m
第三步-重建IAT=
8 ~# g1 u% I' X) h' w( Q
=============================
/ @% i0 ]" w2 V5 s
) l2 m9 B& E' g0 i$ K
1. 首先运行软件,等候它被载入。
0 g( A9 N, Y3 s
2. 运行Imprec,从列表中选择进程。
! V8 R, f$ V- Z! E) N
3. 按"IAT AutoSearch"
5 Q; c; X5 h. k( E, M6 x- G- }
4. 把大小从"BC"修改为1000(BC太小了!!)
7 s3 B H; s' _ i$ S
5. 按"Get Imports"
) }8 J, W) c |3 q1 ^6 S
6. 按"Show Invalid"
) A9 s8 M6 R6 {% ?7 ?; _
7. 在显示无效的项目上右击鼠标,选择"Trace level 1"
+ N8 i. F* d) J( h
8. 再次按"Show Invalid"…现在我们应该得到下面的东西:
0 e% h; L' `# E4 J h2 n8 O2 s
( D4 S. P4 C9 G0 p( v5 G2 @: o( Z3 S# n
(从保存的树中剪切)
( t% n1 l9 l0 }* r' f9 f
FThunk: 0019E258 NbFunc: 00000400
0 p: {; R) g) p+ d) ]
1 0019E258 kernel32.dll 00D6 DeleteCriticalSection
4 L; H: @$ A, Z; k
1 0019E25C kernel32.dll 0228 LeaveCriticalSection
, x0 l# _* l9 G- }
................
) C( H, N5 k5 p7 Q' P& f
省略-省略
?/ J$ O" G) M- o0 J" M7 i) c
................
- i+ }3 K3 p% l; A
1 0019E2A4 kernel32.dll 01D1 GetThreadLocale
( m$ D- l1 ^4 i3 p
1 0019E2A8 kernel32.dll 01B9 GetStartupInfoA
* W; P9 n0 v0 |& a, R9 I5 s7 x8 {
0 0019E2AC ? 0000 017E0F2C <-- good
1 K) k( F4 c8 M* Y% t. D
0 0019E2B0 ? 0000 017E139C <-- good
" {+ G; @4 T. E5 g. d
1 0019E2B4 kernel32.dll 018B GetModuleFileNameA
, E' n# J2 [4 z: @1 R+ E
1 0019E2B8 kernel32.dll 0183 GetLocaleInfoA
5 b1 x/ I; W( _3 x& N" }: ]
1 0019E2BC kernel32.dll 0181 GetLastError
( N( J) {- A& I6 O7 [
1 0019E2C0 kernel32.dll 0158 GetCurrentDirectoryA
: c! Z8 ?' {4 ]1 `0 j
0 0019E2C4 ? 0000 017E1408 <-- good
$ x3 R4 y3 F$ N0 U# D
1 0019E2C8 kernel32.dll 0133 FreeLibrary
) m" k5 P& J9 {. N) D0 H2 i
1 0019E2CC kernel32.dll 011C FindFirstFileA
4 m" C# i( _/ l" _) w
..................
6 t+ U& q4 o/ p+ H5 k/ W
省略-省略
" F! z7 e* D+ k8 l0 K
..................
- ?+ j: E4 V9 r. }
1 0019E314 kernel32.dll 00A0 CloseHandle
* a0 I m6 K1 l. S, k5 v- ~# d7 x: U
0 0019E318 ? 0000 0255A00E <-- BAD
/ Q: d4 c5 Y2 N) U! L6 X P+ V
1 0019E31C user32.dll 0112 GetKeyboardType
8 X+ a% |+ w [0 m
1 0019E320 user32.dll 019F LoadStringA
+ q( M9 ?) l: t5 p
1 0019E324 user32.dll 01AD MessageBoxA
9 Y/ s9 K4 U' g$ }
1 0019E328 user32.dll 0026 CharNextA
M# }% e, @ @) s, M- J
0 0019E32C ? 0000 70F7D832 <-- BAD
+ C# x! s+ V- c
1 0019E330 advapi32.dll 00F7 RegQueryvalueExA
9 R. J4 M. ?' |& X
1 0019E334 advapi32.dll 00EF RegOpenKeyExA
- h! n5 m9 K8 m) h
1 0019E338 advapi32.dll 00D8 RegCloseKey
; Z3 D' Q1 S' k9 H4 ^3 T8 s
0 0019E33C ? 0000 F37514C2 <-- BAD
+ [! ]- g" m" w0 t
1 0019E340 oleaut32.dll 0006 SysFreeString
1 s- n3 P1 H5 h$ n" Y+ Y
1 0019E344 oleaut32.dll 0005 SysReAllocStringLen
# k6 l) I! C( k6 N. o/ g
1 0019E348 oleaut32.dll 0004 SysAllocStringLen
* c" e) E2 |% H0 h5 S8 Z& z- _ d0 |
0 0019E34C ? 0000 4007F56E <-- BAD
/ ^5 u# W# v, O* o( @3 q9 C
1 0019E350 kernel32.dll 0307 TlsSetvalue
" l5 b' b' N+ p0 G8 A, Q
1 0019E354 kernel32.dll 0306 TlsGetvalue
3 e: P5 I* m6 Y+ h5 ?; |/ P( P6 Z2 J
1 0019E358 kernel32.dll 01E6 GlobalAlloc
, h9 G# X$ |: Q; H6 `4 Z
0 0019E35C ? 0000 017E139C <-- good
6 }: o; W# [( s( M% W
0 0019E360 ? 0000 BF57C0D8 <-- BAD
- |/ r1 o$ n- M
.......................
6 {, d# H5 S4 N8 n) A4 v+ o
省略-省略
. ^) C C$ U- i+ c
.......................
) r# h- B5 F: T. @! b6 M
2 x/ n$ @' q0 `( a8 `% @
好了,我们继续重复这样做…
1 M0 N. I; m' v9 s( O) ^
我们需要手工选择所有坏地址(不在压缩代码内),然后在它们上面右击鼠标,从菜单里选择 "Cut Thunk(s)"。
4 G! @# ^7 B# N9 b
观察窗口在最下…那儿有好的Thunk(s)…
7 Z% ^9 n. L/ J G
5 Q- n! Z& e) h# \1 |* q# P
现在我们需要修正这些好字节…你可能从fraviamb.cjb.net下载过一些插件
) k8 i' W! o7 D6 n+ e* V1 a
或者看我其他关于如何重建的文章(New2Cracking.cjb.net或者Fraviamb.cjb.net)
; s8 d! \9 E1 B; y( ^
这是我修正的:
6 G* p1 r0 t* T! W. [
+ @4 l( Q) a% h- S2 P
0019E2AC-> 017E0F2C ->GetProcAddress
$ X# F1 z/ M* ?( Q" N |: m" m) y
0019E2B0-> 017E139C ->GetModuleHandleA
3 s. [$ Y; i) G! U
0019E2C4-> 017E1408 ->GetCommandLineA
8 X9 ]9 a& V9 m6 }0 F
0019E35C-> 017E139C ->GetModuleHandleA
: u, ?7 k) v+ I5 j' l; @
0019E428-> 017E1420 ->LockResource
. I% g: [' e3 F; T
0019E47C-> 017E13C4 ->GetVersion
$ `# S; U/ r' y( T! w* B. S9 b
0019E4AC-> 017E0F2C ->GetProcAddress
8 g# x' g5 I6 ?4 _6 M; T
0019E4B8-> 017E139C ->GetModuleHandleA
; p( f2 n8 k$ G! D& U& L5 S2 u
0019E4FC-> 017E13F8 ->GetCurrentProcessId
: J1 h2 t* B- q
0019E500-> 017E13F0 ->GetCurrentProcess
: C) d, E' p6 [% O
0019E50C-> 017E1430 ->FreeResource
# i4 `) H& j+ W Z0 r# r P
$ f/ j5 K- K! i& @! L6 \
9. 按"Fix Dump",选择我们抓取的文件…
/ d) k! ~; M+ O0 _! {5 W* x
imprec将会以在文件名前加"_"的方式保存抓取的文件。
; N! l- w& K: W2 J) k
% b. M! Y% v% r2 R# e
=========================
5 ], @# t- i9 F" q
第四步-修正OEP=
/ A: V; E7 V" S0 m% g" u
=========================
$ l+ s+ y# @5 s1 @% m; {9 }
& z" ~/ S6 M/ k: R5 J
1.打开HVIEW /Hex编辑器,跳转到OEP的偏移地址:57ea5b处,
* `( }% w4 e N! b3 ~* g
向后移6字节到57ea55处,用"00"替换写入 stolen bytes. 保存为新文件。
5 `) Q, j- c4 P* v: D6 K
( z+ X$ q- M6 k) ]7 D5 x
2. 打开ProcDump/Pe-Edit ,点击“Pe-Edit”按纽载入重建的新文件,修改入口点为:57ea55 (因为抽掉的字节)
' j! c; I$ ^+ F* H8 s
+ k0 F/ z- D% O& G
3. 如果你现在试图运行程序,它会死掉的!!
. {2 R# p- m- f7 c) R: v# B8 d
( P/ V: `0 r# q- ^
4. 打开Olly并载入我们的修正文件。
0 l: Q% N0 v$ C8 N4 y! T5 c
& P' J8 i; H+ D0 @- o
5. 停在OEP: 57ea55处,EAX寄存器的值是什么?还记得我告诉过你在抓取之前保存的EAX的值吗?它是EAX=57E318,两个值的差别意味着有两
+ F8 ~: r; X, N7 z7 [9 g+ x% `
) O. B. a8 C% w- U- y) o" x
个以上的命令: that is stolen:
9 F+ ]+ k& n' h
, z" m. J1 l+ a
MOV EAX, 0157E318
% \( a) x1 J( l% k2 v0 G
* [: F- r# G- m8 n
这条指令占用5个字节(你可自己在 HVIEW里试一下)
+ z v$ F) y0 H, \; q1 P
B818E35700 MOV EAX, 0157E318
$ u3 u& ?1 }; i3 m7 v
这意味着有6+5=11(十进制)个抽掉的字节
+ _4 s. t1 [, c i$ i$ N, ~
那么,真正的OEP是:
# _3 V5 y3 b( }. u$ q) t
11=B(hex)
6 W6 S7 i0 y1 ^; B" W
OLD_OEP-STOLEN_BYTES=57EA5B-B=57EA50
- H7 h6 Z% A& Z' ^* {0 s& c
OEP = 57EA50
/ Z7 I* Z: E3 v9 j
用HVIEW/Hex打开,跳转到新的OEP,写入:
: V- T* _! [. z' N7 T& O7 u
% j( I% F/ X# `& y$ l
55,8B,EC,83,EC,54,B8,18,E3,57,00
6 N9 e: M7 p& s& Y: ]
9 T$ l2 S! n# d; y6 r6 H$ X6 U% x
用ProcDump\Pe-Edit修改入口点为:57EA50
9 `5 A/ T, H- o7 i
哈哈,这下程序能运行了!!!
' C* Z, t! q0 R
收工!!!
7 \' Z* V' c& i" d
8 y+ i& B0 \. `5 Y l V
翻译后记:俺一直用Softice,没用过OllyDbg,所以有些内容不知道是否准确,再者水平有限,如有错误,请各位大虾指点!!
1 Q2 S. r; T& {( m
/ ], G0 O$ e/ u8 o9 t
_) a6 t7 w: q7 I& X
欢迎光临 数学建模社区-数学中国 (http://www.madio.net/)
Powered by Discuz! X2.5