首页
社区
课程
招聘
[原创]菜鸟的第一篇破文
2006-5-2 18:08 11329

[原创]菜鸟的第一篇破文

2006-5-2 18:08
11329
【破文标题】HAGGAR的KeyMe no.4分析
【破文作者】foria
【破解工具】OD peid
【破解平台】WINXP
【下载地址】www.crackmes.de(由于没有上传权限,在首页上找找吧,很容易的)
【破解声明】初学Crack,只是感兴趣,没有其他目的。失误之处敬请诸位大侠赐教!

根据creakme的作者的声明,这个crack Me的加密方式跟很多游戏差不多,我们下面就来研究一下这个crack me。

第一步还是拿peid看一下,看是那什么语言写的,Nothing found *,先不管它,运行一下再说。
程序非常简单,就一个输入cd-key的地方,然后就是next和cancel。

好了,现在拿OD载入。Ctrl+N,看一下有什么好用的api可以设断的,GetDlgItemTextA,MessageBoxA,在这几个api上设好断点。
按F9运行,随便输入假的序列号。程序断在了下面的位置。

00401123   .  E8 72090000   call    <jmp.&user32.GetDlgItemTextA>    ; \GetDlgItemTextA
00401128   .  83F8 04       cmp     eax, 4                           ;  如果输入的不是4个字符
0040112B   .  74 09         je      short 00401136                   ;  跳走则注册失败

F9,继续运行
004012E1   ?  58            pop     eax
004012E2   ?  6A 30         push    30
004012E4   ?  68 00304000   push    00403000                         ;  ASCII "Information"
004012E9  />  68 0C304000   push    0040300C                         ; |Text = "The entered CD key appears to be invalid. Setup cannot continue without valid key. Please try again."
004012EE  |.  6A 00         push    0                                ; |hOwner = NULL
004012F0  |.  E8 B1070000   call    <jmp.&user32.MessageBoxA>        ; \MessageBoxA
004012F5  |.  C3            retn

由于代码中夹杂了一些花指令,程序断下来后,用Ctrl+方向箭头上下调整一下,就看到了上面的结果,这里是错误的提示信息,将鼠标滚轮向上翻滚,可以看到还有一个MessageBox:

0040125E   .  E8 93000000   call    004012F6                         ;  关键的call
00401263   .  83F8 00       cmp     eax, 0                           ;  呵呵,这里就是比较了。。。
00401266   .  74 19         je      short 00401281                   ;  跳走就完蛋
00401268   .  6A 40         push    40
0040126A   .  68 00304000   push    00403000                         ;  ASCII "Information"
0040126F   .  68 71304000   push    00403071                         ;  ASCII "The entered key appears to be valid. You will be never asked for that key by our company. Please, do not give that key to anybody. Thank you."
00401274   >  6A 00         push    0                                ; |hOwner = NULL
00401276   .  E8 2B080000   call    <jmp.&user32.MessageBoxA>        ; \MessageBoxA

如果是爆破的话,将上面的je改为jne就够了,但是作者是要我们做出注册机,所以上面的call用F7跟进去。

004012F6  |$  50            push    eax
004012F7  |.  E8 03000000   call    004012FF                         ;  call的地址很近,很有可能是替代jmp的,F7跟进去
004012FC  \.^ EB EB         jmp     short 004012E9
004012FE      02            db      02
004012FF   $^ EB FC         jmp     short 004012FD
00401301   .  3E:8B0424     mov     eax, ds:[esp]
00401305   .  83C0 09       add     eax, 9
00401308   >  EB 02         jmp     short 0040130C
0040130A   .  EB 06         jmp     short 00401312
0040130C   >  FFE0          jmp     eax
0040130E   .  58            pop     eax
0040130F   .  83C0 19       add     eax, 19
00401312   >^ EB F4         jmp     short 00401308

这里上面是一段花指令(整个程序用得非常多),作用是来替代jmp的,不要被call所迷惑了,用F7一直按下去,就可以到达这一段代码的出口。
0040131C   ?  33F6          xor     esi, esi
0040131E   ?  B9 74314000   mov     ecx, 00403174
00401323      8B            db      8B
00401324      C6            db      C6

到这里之后,拿OD的花指令去除插件用一下,就可以看到代码了,后面遇到类似的情况也同样处理。下面一段代码的跟踪的过程就不细说了(这一段代码没什么用)。跟踪到这里:

0040153F      8A81 14374000 mov     al, [ecx+403714]                 ;  复制注册码
00401545      8881 34374000 mov     [ecx+403734], al                 ;  从内存403714的复制到
0040154B      41            inc     ecx     
0040154C      83F9 14       cmp     ecx, 14                          ;  逐位复制,总共14次
0040154F    ^ 72 EE         jb      short 0040153F

00401571      8D05 14374000 lea     eax, [403714]                    ;  eax指向刚才复制的注册码的位置
00401577      33D2          xor     edx, edx                         ;  置换,关键位置
00401579      33DB          xor     ebx, ebx
0040157B      B9 02000000   mov     ecx, 2
00401580      8A1408        mov     dl, [eax+ecx]
00401583      8A58 0D       mov     bl, [eax+D]                      ;  eax[2]与eax[D]置换
00401586      881C08        mov     [eax+ecx], bl
00401589      8A58 0E       mov     bl, [eax+E]
0040158C      8850 0D       mov     [eax+D], dl
0040158F      BA 04000000   mov     edx, 4
00401594      03C8          add     ecx, eax
00401596      8D0C10        lea     ecx, [eax+edx]
00401599      8A11          mov     dl, [ecx]
0040159B      8819          mov     [ecx], bl
0040159D      8A58 0F       mov     bl, [eax+F]
004015A0      8850 0E       mov     [eax+E], dl                      ;  4与e置换
004015A3      B9 05000000   mov     ecx, 5
004015A8      8A1408        mov     dl, [eax+ecx]
004015AB      881C08        mov     [eax+ecx], bl
004015AE      8A58 10       mov     bl, [eax+10]
004015B1      8850 0F       mov     [eax+F], dl                      ;  5与f置换,下面的类似,省略
004015B4      BA 07000000   mov     edx, 7
004015B9      03C8          add     ecx, eax
004015BB      8D0C10        lea     ecx, [eax+edx]
004015BE      8A11          mov     dl, [ecx]
004015C0      8819          mov     [ecx], bl
004015C2      8A58 11       mov     bl, [eax+11]
004015C5      8850 10       mov     [eax+10], dl
004015C8      B9 0C000000   mov     ecx, 0C
004015CD      8A1408        mov     dl, [eax+ecx]
004015D0      881C08        mov     [eax+ecx], bl
004015D3      8A58 12       mov     bl, [eax+12]
004015D6      03C8          add     ecx, eax
004015D8      8850 11       mov     [eax+11], dl
004015DB      BA 01000000   mov     edx, 1
004015E0      8D0C10        lea     ecx, [eax+edx]                   ;  最后的置换表:
004015E3      8A11          mov     dl, [ecx]                        ;  2<->D
004015E5      8819          mov     [ecx], bl                        ;  4<->E
004015E7      8A58 13       mov     bl, [eax+13]                     ;  5<->F
004015EA      8850 12       mov     [eax+12], dl                     ;  7<->G
004015ED      B9 03000000   mov     ecx, 3                           ;  C<->H
004015F2      8A1408        mov     dl, [eax+ecx]                    ;  1<->I
004015F5      03C8          add     ecx, eax                         ;  3<->J
004015F7      8819          mov     [ecx], bl
004015F9      8850 13       mov     [eax+13], dl                     ;  置换完毕
004015FC      C640 14 00    mov     byte ptr [eax+14], 0             ;  尾部加零

如果你输入的注册码是0123-4567-89AB-CDEF-GHIJ,置换后就是0IDJ-EF6G-89AB-H245-7C13。

00401688      8D05 55374000 lea     eax, [403755]                    ;  计算magic number
0040168E      3E:8B0C24     mov     ecx, ds:[esp]
00401692      8AD1          mov     dl, cl
00401694      80E2 1F       and     dl, 1F
00401697      8850 06       mov     [eax+6], dl
0040169A      8BD1          mov     edx, ecx
0040169C      C1EA 05       shr     edx, 5
0040169F      80E2 1F       and     dl, 1F
004016A2      8850 05       mov     [eax+5], dl
004016A5      8BD1          mov     edx, ecx
004016A7      C1EA 0A       shr     edx, 0A
004016AA      80E2 1F       and     dl, 1F
004016AD      8850 04       mov     [eax+4], dl
004016B0      8BD1          mov     edx, ecx
004016B2      C1EA 0F       shr     edx, 0F
004016B5      80E2 1F       and     dl, 1F
004016B8      8850 03       mov     [eax+3], dl
......
计算一个magic number,放在内存403755的位置,用OD察看一下,9HYJ4LB,好奇怪的一个数字...
0040176B      8A81 55374000 mov     al, [ecx+403755]                 ;  将magic number复制到注册码的尾部
00401771      8881 21374000 mov     [ecx+403721], al
00401777      41            inc     ecx
00401778      83F9 07       cmp     ecx, 7
0040177B    ^ 72 EE         jb      short 0040176B

继续跟踪:
0040185B      8D05 55374000 lea     eax, [403755]                    ;  再次计算magic number
00401861      8AD1          mov     dl, cl
00401863      80E2 03       and     dl, 3
00401866      C0E2 03       shl     dl, 3
00401869      8850 06       mov     [eax+6], dl
0040186C      C1E9 02       shr     ecx, 2
0040186F      8AD1          mov     dl, cl
00401871      80E2 1F       and     dl, 1F
00401874      8850 05       mov     [eax+5], dl
00401877      8BD1          mov     edx, ecx
00401879      C1EA 05       shr     edx, 5
0040187C      80E2 1F       and     dl, 1F
0040187F      8850 04       mov     [eax+4], dl

00401937     /EB 0D         jmp     short 00401946
00401939     |8A81 55374000 mov     al, [ecx+403755]
0040193F     |8881 21374000 mov     [ecx+403721], al
00401945     |41            inc     ecx
00401946     \83F9 07       cmp     ecx, 7
00401949    ^ 72 EE         jb      short 00401939

同样是计算magic number和复制,跟到了这里,我们会发现前面相同功能的一段代码没有什么用,第二次的结果完全把第一次的结果覆盖了。
现在的magic number是222227J,注册码则变为了0IDJ-EF6G-89AB-H222-227J。

0040196B      8D05 14374000 lea     eax, [403714]
00401971      33D2          xor     edx, edx
00401973      33DB          xor     ebx, ebx
00401975      B9 02000000   mov     ecx, 2                           ;  第二次置换
.......
004019F3      8850 13       mov     [eax+13], dl                     ;  置换表与第一次完全一样
004019F6      C640 14 00    mov     byte ptr [eax+14], 0             ;  第二次置换完毕
经过第二轮置换后,注册码现在变为了072J-2262-89AB-2DEF-GHIJ。

00401A1E      33C9          xor     ecx, ecx
00401A20      EB 14         jmp     short 00401A36
00401A22      8A99 14374000 mov     bl, [ecx+403714]                 ;  置换过的注册码
00401A28      8AB9 34374000 mov     bh, [ecx+403734]                 ; 原始的注册码
00401A2E      38FB          cmp     bl, bh                           ;  逐位比较
00401A30      74 03         je      short 00401A35     
00401A32      33C0          xor     eax, eax                         ;  eax清零
00401A34      C3            retn     ;  到这就注册失败
00401A35      41            inc     ecx
00401A36      83F9 14       cmp     ecx, 14                          ;  比较14次
00401A39    ^ 72 E7         jb      short 00401A22
00401A3B      50            push    eax                              ;  到这就成功了

这一段就是最后的比较部分了,push后面还有一段代码,作用是置eax为1,返回,注册成功。

现在我们对程序的注册方式就了解了,cdkey的认证采用自校验的方式,先将用户的注册码做一次置换,将尾部七个字符修改为magic number,再做一次相同的置换,再将现在变换过的注册码与最原始的相比,相同则注册成功。

变换过的注册码在1,2,3,4,5,7,C这几个位置变为了magic number,而别的位置都不变。

最后的注册算法如下:
072J-2202-0000-2000-0000,将0的位置替换为任意的字符(例如R72J-22M2-B3RB-2222-227J),就可以得到任意的注册码了(因为0所在的位置在变换后是不变的,而非0的地方正是magic number所在的地方)。到了这里注册机就很容易写出了。

等等,还没完,我们上面分析中还少了一点,其实注册码中是不能含有某些字符的,看下面:

0040136A      C705 74364000>mov     dword ptr [403674], 1010101      ; 将掩码写入内存,后面要用
00401374      C705 78364000>mov     dword ptr [403678], 1010101     
0040137E      C705 7C364000>mov     dword ptr [40367C], 1010101
00401388      C705 80364000>mov     dword ptr [403680], 1010101
00401392      C705 84364000>mov     dword ptr [403684], 1010101
0040139C      C705 88364000>mov     dword ptr [403688], 1010100
004013A6      C705 8C364000>mov     dword ptr [40368C], 1000001
004013B0      C705 90364000>mov     dword ptr [403690], 1010101
004013BA      C705 94364000>mov     dword ptr [403694], 1000101
004013C4      C705 98364000>mov     dword ptr [403698], 1010101

这里是前面一段比较注册码的地方,主要是看注册码是否合理,外层循环采用查表的的方法,确定是哪一个字符,
内层在跟掩码比较,如果恰好遇到掩码是0的话,程序就跳走了,注册失败。

我们来计算一下那几个字符被掩掉了:
004030FF  30 31 32 33 34 35 36 37 38 39 41 42 43 44 45 46  0123456789ABCDEF
0040310F  47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56  GHIJKLMNOPQRSTUV
0040311F  57 5A 59 58 00 36 34 33 38 32 39 35 37 4A 4B 4C  WZYX.64382957JKL
这就是程序中用到的表。
00403674  01 01 01 01 01 01 01 01 01 01 01 01 01 01 01 01  
00403684  01 01 01 01 00 01 01 01 01 00 00 01 01 01 01 01  ...
00403694  01 01 00 01 01 01 01 01 00 00 00 00 00 00 00 00  .........
这是掩码。
掩码为零的地方恰好是K,P,Q,Y这几个字符,所以在制作注册机的时候要把这几个字符过滤掉。

004014F5     /EB 18         jmp     short 0040150F
004014F7     |3A81 FF304000 cmp     al, [ecx+4030FF]
004014FD     |75 0F         jnz     short 0040150E
004014FF     |80B9 74364000>cmp     byte ptr [ecx+403674], 1         ;  内层循环跟掩码比较
00401506     |74 06         je      short 0040150E                   ;  相等则注册失败
00401508     |83C4 04       add     esp, 4
0040150B     |33C0          xor     eax, eax
0040150D     |C3            retn
0040150E     |41            inc     ecx
0040150F     \83F9 24       cmp     ecx, 24
00401512    ^ 72 E3         jb      short 004014F7                   ;  外层循环先确定是哪一个字母

总结一下,注册码由数字和大写字母组成,但是大写字母不包括K、P、Q、Y四个字母。072J-2202-0000-2000-0000,将0的位置替换为任意的字符,就可以得到任意的注册码了。

[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

收藏
点赞7
打赏
分享
最新回复 (24)
雪    币: 214
活跃值: (55)
能力值: ( LV6,RANK:90 )
在线值:
发帖
回帖
粉丝
我从零KS 2 2006-5-2 18:35
2
0
希望能把算法总结一下。
雪    币: 443
活跃值: (200)
能力值: ( LV9,RANK:1140 )
在线值:
发帖
回帖
粉丝
冷血书生 28 2006-5-3 00:46
3
0
最初由 foria 发布
【破文标题】HAGGAR的KeyMe no.4分析
【破文作者】foria
【破解工具】OD peid
【破解平台】WINXP
【下载地址】www.crackmes.de(由于没有上传权限,在首页上找找吧,很容易的)
........


帮你上传过来~

上传的附件:
雪    币: 177
活跃值: (40)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
foria 1 2006-5-3 15:29
4
0
注册机传上来
上传的附件:
雪    币: 204
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
jazzljt 2006-5-4 02:05
5
0
从0做起,一步一步学
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
huanjian 2006-5-4 02:51
6
0
呵呵  我也学习了
雪    币: 207
活跃值: (10)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
houhq 1 2006-5-5 11:58
7
0
花指令花晕了,慢慢看
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
小呵呵 2006-5-5 12:24
8
0
好好学习一下
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
yhongjiang 2006-5-7 02:48
9
0
我也要学,第一次学这种东西一定很刺激
雪    币: 221
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
寒冷的风 2006-5-10 21:20
10
0
GetDlgItemTextA,MessageBoxA,在这几个api上设好断点。
按F9运行,随便输入假的序列号。程序断在了下面的位置。

但是到不了你说的那里,到了7710B013那里
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
ytian 2006-5-19 16:46
11
0
简单易懂,好!
雪    币: 332
活跃值: (25)
能力值: ( LV12,RANK:460 )
在线值:
发帖
回帖
粉丝
火影 11 2006-5-19 19:42
12
0
顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶顶
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
ikohl 2006-5-21 14:02
13
0
还是比较难的,花指令太花了
雪    币: 241
活跃值: (160)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
xiluoyou 2006-5-21 23:48
14
0
忘了Ctrl+N这个快捷键,好多时候都很郁闷
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
reboot 2006-7-6 15:12
15
0
对我这种新手很有用,谢谢
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
golden 2006-7-6 15:50
16
0
第一次学这种东西一定很刺激
雪    币: 201
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
yczzz 2006-7-7 09:13
17
0
写得还不错呀!希望以后多交流!
雪    币: 237
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
dongfeng 2006-7-7 10:04
18
0
除了学习还是学习
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
golden 2006-7-7 12:44
19
0
还是看不懂,能不能再简单点的
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
dujing 2006-7-7 13:56
20
0
谢谢,一定会努力学的
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
zhtzzyzy 2006-7-7 15:55
21
0
我也是菜鸟,学习了。
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
jsjyjstz 2006-7-21 19:53
22
0
学习中,不错的文章
雪    币: 338
活跃值: (10)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
bfqyygy 1 2006-7-22 18:36
23
0
新手练习的好
雪    币: 1301
活跃值: (25)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
dgrzh 1 2006-7-23 10:45
24
0
对我们这些新手来说是很好的学习资料。
雪    币: 338
活跃值: (10)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
bfqyygy 1 2006-7-24 17:17
25
0
不太懂的说!
游客
登录 | 注册 方可回帖
返回