首页
社区
课程
招聘
[原创]KCR CM2的简单分析
发表于: 2009-1-2 15:29 5511

[原创]KCR CM2的简单分析

2009-1-2 15:29
5511
【文章标题】: KCR CM2的简单分析
【文章作者】: samisgod
【下载地址】: http://bbs.pediy.com/showthread.php?t=79864
【编写语言】: VC6
【使用工具】: OD
【操作平台】: Windows XP x64 SP3
【作者声明】: 只是感兴趣,没有其他目的。失误之处敬请诸位大侠赐教!

[更新下]

今天没事干来到CM版转转,无意间看到这个CM,还没人分析,遂自己下下来看看...

这个CM算法的2个关键点并不难定位GetWindowText直接可到了

下面进行简单分析

打开后的第一个框内数值这里将其称为MCode

第一部分:

00401EC0   .  53            push    ebx
00401EC1   .  56            push    esi
00401EC2   .  57            push    edi
00401EC3   .  8BF1          mov     esi, ecx
00401EC5   .  6A 01         push    1
00401EC7   .  E8 1A030000   call    <CWnd::UpdateData(int)>             ;  jmp 到 MFC42.#6334
00401ECC   .  8B46 60       mov     eax, dword ptr [esi+60]
00401ECF   .  8D5E 64       lea     ebx, dword ptr [esi+64]
00401ED2   .  53            push    ebx
00401ED3   .  68 E9030000   push    3E9
00401ED8   .  8B78 F8       mov     edi, dword ptr [eax-8]
00401EDB   .  8BCE          mov     ecx, esi
00401EDD   .  E8 D4020000   call    <CWnd::GetDlgItem(int)>             ;  jmp 到 MFC42.#3092
00401EE2   .  8BC8          mov     ecx, eax
00401EE4   .  E8 F1020000   call    <CWnd::GetWindowTextA(CString &)>   ;  jmp 到 MFC42.#3874
00401EE9   .  33C0          xor     eax, eax
00401EEB   .  85FF          test    edi, edi
00401EED   .  7E 12         jle     short <loc_401F01>
00401EEF > >  8B4E 60       mov     ecx, dword ptr [esi+60]             ;  SN
00401EF2   .  40            inc     eax
00401EF3   .  3BC7          cmp     eax, edi
00401EF5   .  8A5408 FF     mov     dl, byte ptr [eax+ecx-1]
00401EF9   .  8890 7B414000 mov     byte ptr [eax+40417B], dl
00401EFF   .^ 7C EE         jl      short <loc_401EEF>
00401F01 > >  83FF 0A       cmp     edi, 0A                             ;  loc_401F01
00401F04   .  7C 45         jl      short <loc_401F4B>
00401F06   .  8B0D 9C414000 mov     ecx, dword ptr [40419C]
00401F0C   .  8B15 A0414000 mov     edx, dword ptr [4041A0]
00401F12   .  33C0          xor     eax, eax                            ;  eax初始化
00401F14 > >  8B3B          mov     edi, dword ptr [ebx]                ;  loc_401F14
00401F16   .  40            inc     eax
00401F17   .  83F8 0A       cmp     eax, 0A                             ;  10?
00401F1A   .  0FBE7C07 FF   movsx   edi, byte ptr [edi+eax-1]           ;  逐位取前10位
00401F1F   .  8D4C39 D0     lea     ecx, dword ptr [ecx+edi-30]         ;  ecx=ecx+edi-0x30
00401F23   .  890D 9C414000 mov     dword ptr [40419C], ecx             ;  (前10位ASC-0x30累加)放入40419C
00401F29   .  8B7E 60       mov     edi, dword ptr [esi+60]             ;  SN
00401F2C   .  0FBE7C38 FF   movsx   edi, byte ptr [eax+edi-1]           ;  逐位取SN
00401F31   .  8D543A D0     lea     edx, dword ptr [edx+edi-30]         ;  ASC - 0x30累加
00401F35   .  8915 A0414000 mov     dword ptr [4041A0], edx             ;  存入4041A0
00401F3B   .^ 7C D7         jl      short <loc_401F14>
00401F3D   .  8BCE          mov     ecx, esi
00401F3F   .  C605 60414000>mov     byte ptr [404160], 1
00401F46   .  E8 87010000   call    <CDialog::OnCancel(void)>           ;  jmp 到 MFC42.#4376
00401F4B > >  5F            pop     edi                                 ;  loc_401F4B
00401F4C   .  5E            pop     esi
00401F4D   .  5B            pop     ebx
00401F4E   .  C3            retn



这一部分有3个全局变量用在算法部分
40419C   
4041A0   
作用上面已经说明
404160
注册码达10位后会置1
用来简单看了下会用作流程判断,为1时会开启注册流程2

下面开始第2部分
这里说明下,为了方便,我们的注册码直接填写一个简单分析后获取并经过简单修改的值 -_-bb
00A0000000033333333399
另外,为了分析方便,我的MCode被我锁定为324207125552-2111
00401600  |.  83EC 10       sub     esp, 10
00401603  |.  53            push    ebx
00401604  |.  55            push    ebp
00401605  |.  8BE9          mov     ebp, ecx
00401607  |.  57            push    edi
00401608  |.  C64424 0F 00  mov     byte ptr [esp+F], 0
0040160D  |.  C64424 10 00  mov     byte ptr [esp+10], 0
00401612  |.  8D7D 60       lea     edi, [arg.23]
00401615  |.  66:C74424 11 >mov     word ptr [esp+11], 0
0040161C  |.  57            push    edi
0040161D  |.  68 E8030000   push    3E8
00401622  |.  E8 8F0B0000   call    <CWnd::GetDlgItem(int)>             ;  jmp 到 MFC42.#3092
00401627  |.  8BC8          mov     ecx, eax
00401629  |.  E8 AC0B0000   call    <CWnd::GetWindowTextA(CString &)>   ;  jmp 到 MFC42.#3874
0040162E  |.  8B07          mov     eax, dword ptr [edi]
00401630  |.  8378 F8 16    cmp     dword ptr [eax-8], 16               ;  注册码不到22位就挂
00401634  |.  74 07         je      short <loc_40163D>
00401636  |.  6A 00         push    0
00401638  |.  E9 25010000   jmp     <loc_401762>
0040163D >|>  56            push    esi                                 ;  loc_40163D
0040163E  |.  FF15 84314000 call    dword ptr [<&MSVCRT.clock>]         ;  msvcrt.clock
00401644  |.  8D75 64       lea     esi, [arg.24]
00401647  |.  8BCD          mov     ecx, ebp
00401649  |.  56            push    esi
0040164A  |.  68 E9030000   push    3E9
0040164F  |.  894424 24     mov     dword ptr [esp+24], eax
00401653  |.  E8 5E0B0000   call    <CWnd::GetDlgItem(int)>             ;  jmp 到 MFC42.#3092
00401658  |.  8BC8          mov     ecx, eax
0040165A      E8 7B0B0000   call    <CWnd::GetWindowTextA(CString &)>   ;  324207125552-2111
0040165F  |.  8B06          mov     eax, dword ptr [esi]                ;  MCode
00401661  |.  8A48 0F       mov     cl, byte ptr [eax+F]                ;  16位(1)
00401664  |.  884C24 14     mov     byte ptr [esp+14], cl
00401668  |.  8A50 10       mov     dl, byte ptr [eax+10]               ;  17位(1)
0040166B  |.  8D4424 14     lea     eax, dword ptr [esp+14]
0040166F  |.  885424 15     mov     byte ptr [esp+15], dl               ;  末2位转数字
00401673  |.  50            push    eax                                 ; /s
00401674  |.  C64424 1A 00  mov     byte ptr [esp+1A], 0                ; |
00401679  |.  FF15 E4314000 call    dword ptr [<&MSVCRT.atoi>]          ; \atoi
0040167F  |.  8BD8          mov     ebx, eax                            ;  11 -> B 放 ebx
00401681  |.  8B06          mov     eax, dword ptr [esi]                ;  MCode
00401683  |.  8A48 0D       mov     cl, byte ptr [eax+D]                ;  14位(2)
00401686  |.  884C24 18     mov     byte ptr [esp+18], cl
0040168A  |.  8A50 0E       mov     dl, byte ptr [eax+E]                ;  15位(1)
0040168D  |.  8D4424 18     lea     eax, dword ptr [esp+18]
00401691  |.  885424 19     mov     byte ptr [esp+19], dl               ;  14.15位连接转数字
00401695  |.  50            push    eax                                 ; /s
00401696  |.  C64424 1E 00  mov     byte ptr [esp+1E], 0                ; |
0040169B  |.  FF15 E4314000 call    dword ptr [<&MSVCRT.atoi>]          ; \atoi
004016A1  |.  8B0E          mov     ecx, dword ptr [esi]                ;  21 -> 0x15
004016A3  |.  894424 20     mov     dword ptr [esp+20], eax             ;  eax(15)保存
004016A7  |.  8B07          mov     eax, dword ptr [edi]                ;  SN
004016A9  |.  0FBE1419      movsx   edx, byte ptr [ecx+ebx]             ;  MCode取ebx+1(B->12)位 (2->ASC=0x32)
004016AD  |.  0FBE4C02 D0   movsx   ecx, byte ptr [edx+eax-30]          ;  SN取上面计算出的0x32+1-0x30位 (3) = 0
004016B2  |.  51            push    ecx                                 ; /c
004016B3  |.  FF15 D0314000 call    dword ptr [<&MSVCRT.isupper>]       ; \isupper
004016B9  |.  83C4 0C       add     esp, 0C                             ;  判断是否大写,是则返回非0值
004016BC  |.  85C0          test    eax, eax
004016BE  |.  74 20         je      short <off_4036E0>                  ;  0则跳
004016C0  |.  8B16          mov     edx, dword ptr [esi]                ;  MCode
004016C2  |.  8B0F          mov     ecx, dword ptr [edi]                ;  SN
004016C4  |.  0FBE041A      movsx   eax, byte ptr [edx+ebx]             ;  MCode取第ebx+1(C->12)位 = 2 -> ASC=0x32
004016C8  |.  8B5424 18     mov     edx, dword ptr [esp+18]             ;  上面计算出的15
004016CC  |.  8A5C08 D0     mov     bl, byte ptr [eax+ecx-30]           ;  SN取eax(0x32)-0x30+1位 (A -> 0x41)
004016D0  |.  8A1495 204040>mov     dl, byte ptr [edx*4+404020]         ;  查表取值 edx=0x15 时得值1,直接Ctrl+G到404020可看到
004016D7  |.  80C2 41       add     dl, 41                              ;  1+0x41  = 0x42
004016DA  |.  3ADA          cmp     bl, dl
004016DC  |.  B3 01         mov     bl, 1                               ;  成功标识1
004016DE  |.  74 04         je      short <loc_4016E4>                  ;  根据0x42,修改第3位为B,并需要恢复全局变量值
004016E0 >|>  8A5C24 13     mov     bl, byte ptr [esp+13]               ;  off_4036E0
004016E4 >|>  8B0D A0414000 mov     ecx, dword ptr [4041A0]             ;  loc_4016E4
004016EA  |.  33C0          xor     eax, eax                            ;  初始化eax
004016EC >|>  8B17          /mov     edx, dword ptr [edi]               ;  loc_4016EC
004016EE  |.  40            |inc     eax                                ;  eax++
004016EF  |.  83F8 0B       |cmp     eax, 0B                            ;  11?
004016F2  |.  0FBE5410 0A   |movsx   edx, byte ptr [eax+edx+A]          ;  SN取eax+0xA+1位(61)  -> SN从12位开始向后取值
004016F7  |.  8D4C11 D0     |lea     ecx, dword ptr [ecx+edx-30]
004016FB  |.  890D A0414000 |mov     dword ptr [4041A0], ecx
00401701  |.^ 7C E9         \jl      short <loc_4016EC>                 ;  [4041A0] + 12位向后各位与0x30的差  -> 第一个终值
00401703  |.  8B06          mov     eax, dword ptr [esi]                ;  MCode
00401705  |.  8B15 9C414000 mov     edx, dword ptr [40419C]             ;  1F
0040170B  |.  0FBE48 0A     movsx   ecx, byte ptr [eax+A]               ;  MCode取11位 (5)
0040170F  |.  8D440A 2A     lea     eax, dword ptr [edx+ecx+2A]         ;  0x1F+11位ASC+0x2A=7E
00401713  |.  A3 9C414000   mov     dword ptr [40419C], eax             ;  7E
00401718  |.  8B0E          mov     ecx, dword ptr [esi]                ;  MCode
0040171A  |.  99            cdq
0040171B  |.  0FBE49 0B     movsx   ecx, byte ptr [ecx+B]               ;  MCode取12位 (2 -> ASC = 32)
0040171F  |.  83E9 30       sub     ecx, 30                             ;  -0x30 = 2
00401722  |.  F7F9          idiv    ecx                                 ;  7E/2
00401724  |.  8BF0          mov     esi, eax                            ;  3F  ->  第二个终值
00401726  |.  FF15 84314000 call    dword ptr [<&MSVCRT.clock>]         ;  msvcrt.clock
0040172C  |.  8B0D A0414000 mov     ecx, dword ptr [4041A0]
00401732  |.  3BCE          cmp     ecx, esi                            ;  终值1,2比较
00401734  |.  5E            pop     esi
00401735  |.  75 3B         jnz     short <loc_401772>
00401737  |.  80FB 01       cmp     bl, 1
0040173A  |.  75 36         jnz     short <loc_401772>
0040173C  |.  8B7C24 18     mov     edi, dword ptr [esp+18]
00401740  |.  6A 01         push    1
00401742  |.  2BC7          sub     eax, edi
00401744  |.  8BC8          mov     ecx, eax
00401746  |.  B8 D34D6210   mov     eax, 10624DD3
0040174B  |.  F7E9          imul    ecx
0040174D      C1FA 06       sar     edx, 6
00401750      8BC2          mov     eax, edx
00401752      C1E8 1F       shr     eax, 1F
00401755      03D0          add     edx, eax
00401757      F7DA          neg     edx
00401759      1BD2          sbb     edx, edx
0040175B      42            inc     edx
0040175C  |.  8915 78414000 mov     dword ptr [404178], edx
00401762 >|>  6A 01         push    1                                   ;  loc_401762
00401764  |.  8BCD          mov     ecx, ebp
00401766  |.  E8 4B0A0000   call    <CWnd::GetDlgItem(int)>             ;  jmp 到 MFC42.#3092
0040176B  |.  8BC8          mov     ecx, eax
0040176D  |.  E8 380A0000   call    <CWnd::EnableWindow(int)>           ;  jmp 到 MFC42.#2642
00401772 >|>  5F            pop     edi                                 ;  loc_401772
00401773  |.  5D            pop     ebp
00401774  |.  5B            pop     ebx
00401775  |.  83C4 10       add     esp, 10
00401778  \.  C3            retn




附,由于MCode不固定,这里可以将程序补丁使其产生固定值,另一方面,那两个全局变量在经过注册流程后会发生改变
这里我们同样将其手动初始化
我的方法很简陋,大家可自行解决
0040165A     /E9 6F0F0000   jmp     004025CE                            

004025CE      E8 07FCFFFF   call    <CWnd::GetWindowTextA(CString &)>   ;  jmp 到 MFC42.#3874
004025D3      C701 33323432 mov     dword ptr [ecx], 32343233
004025D9      C741 04 30373>mov     dword ptr [ecx+4], 32313730
004025E0      C741 08 35353>mov     dword ptr [ecx+8], 32353535
004025E7      C741 0C 2D323>mov     dword ptr [ecx+C], 3131322D
004025EE      C741 10 31000>mov     dword ptr [ecx+10], 31
004025F5      C705 9C414000>mov     dword ptr [40419C], 1F
004025FF      C705 A0414000>mov     dword ptr [4041A0], 12
00402609    ^ E9 51F0FFFF   jmp     0040165F


要得到一个注册码
1. 0x3F-0x12= 0x2D
2. 使11位向后各位-0x30值累加得0x2D
这里的33333333399即符合条件
拼合前值得到
00B0000000033333333399

问题
最后,我们尝试填写注册码进去,发现在OD中,程序成功走到了注册流程最后
mov     dword ptr [404178], edx
这里404178为成功标示,并于
0040176B  |.  8BC8          mov     ecx, eax
0040176D  |.  E8 380A0000   call    <CWnd::EnableWindow(int)>           ;  jmp 到 MFC42.#2642
这里激活了OK按钮,但是程序却不能最终激活

这里看下发现某Clock函数在检测执行时间...
这里下断EnableWindow,很快来到
004017A0      6A 00         push    0
004017A2   .  6A 01         push    1
004017A4   .  E8 0D0A0000   call    <CWnd::GetDlgItem(int)>             ;  jmp 到 MFC42.#3092
004017A9   .  8BC8          mov     ecx, eax
004017AB   .  E8 FA090000   call    <CWnd::EnableWindow(int)>           ;  jmp 到 MFC42.#2642
004017B0   .  C3            retn

直接在函数头C3
至此,OK激活完成,功能正常

如果你把断点全部取消也可解决此问题

这里提示下
程序在接受注册码10位后才会激活流程2,直接复制入注册码的话会需要再复制一遍
也可复制前21位再手动输入1位即可

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

收藏
免费 0
支持
分享
最新回复 (4)
雪    币: 2110
活跃值: (21)
能力值: (RANK:260 )
在线值:
发帖
回帖
粉丝
2
请看:

keygen.zip

请大家试验后提供反馈,有没有不成功的,若有不成功的,请将机器码和生成的注册码贴上来,谢谢
上传的附件:
2009-1-3 01:42
0
雪    币: 239
活跃值: (10)
能力值: ( LV9,RANK:170 )
在线值:
发帖
回帖
粉丝
3
老大能说下我哪里出错了吗
2009-1-6 00:34
0
雪    币: 200
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
kcr
4
楼上两位前辈强大,把我写的CrackMe分析出来了。
2009-1-6 10:30
0
雪    币: 239
活跃值: (10)
能力值: ( LV9,RANK:170 )
在线值:
发帖
回帖
粉丝
5
原来不能直接复制完,还有个时间检测,,,,
2009-1-6 10:37
0
游客
登录 | 注册 方可回帖
返回
//