首页
社区
课程
招聘
[原创]一个简单的cm的注册分析及编写注册机
发表于: 2009-6-13 10:49 6089

[原创]一个简单的cm的注册分析及编写注册机

2009-6-13 10:49
6089

标 题: 一个简单的cm的注册分析及编写注册机
作 者: keheng
时 间: 2009年06月13日 10:46:50
链 接: http://bbs.pediy.com/showthread.php?t=91441
          http://www.bt518.cn/Blog/article.asp?id=39

【文章标题】: 一个简单的cm的注册分析及编写注册机
【文章作者】: keheng
【作者邮箱】: keheng@163com
【软件名称】: d2k2_crackme01.exe
【下载地址】: 忘记在哪下载的了。
【使用工具】: ollydbg,peid
【作者声明】: 写的第一个cm注册机,还忘记大侠指教一下。
--------------------------------------------------------------------------------

  第一次写破文和注册机,实话说,感触很多,尤其是写注册机的时候觉得很多的命令不知道用什么来表示,作为一个菜鸟,要学的东西太多

了。一个简单的cm,花了好几天的才时间才写出了注册机,不过这已经是一个好的开始,能走出第一步就行,希望很多像我一样的菜鸟能从这

篇破文中得到学习。谢谢红尘岁月大侠的指点。

--------------------------------------------------------------------------------
【详细过程】

        同样,老方法开始,先用peid查壳,我用的是peid0.96,据说是非官方版,查无壳
od载入程序停在这里:
00401000 >/$  6A 00         push    0                                ; /pModule = NULL
00401002  |.  E8 35040000   call    <jmp.&KERNEL32.GetModuleHandleA> ; \GetModuleHandleA
00401007  |.  A3 30314000   mov     dword ptr [403130], eax
0040100C  |.  6A 0A         push    0A
0040100E  |.  6A 00         push    0
00401010  |.  6A 00         push    0
00401012  |.  FF35 30314000 push    dword ptr [403130]
00401018  |.  E8 07000000   call    00401024
0040101D  |.  6A 00         push    0                                ; /ExitCode = 0

同样是老方法,查找字符串,

Ultra String Reference, 条目 18
Address=004013A8
Disassembly=push    004030C2
Text String=good cracker

到这里后双击来到

004013A8  |.  68 C2304000   push    004030C2                         ; |good cracker

向上找到

00401248  |.  6A 28         push    28                               ; /Count = 28 (40.)
0040124A  |.  68 8C314000   push    0040318C                         ; |Buffer = d2k2_cra.0040318C
0040124F  |.  6A 02         push    2                                ; |ControlID = 2
00401251  |.  FF75 08       push    dword ptr [ebp+8]                ; |hWnd
00401254  |.  E8 8F010000   call    <jmp.&USER32.GetDlgItemTextA>    ; \GetDlgItemTextA
00401259  |.  84C0          test    al, al                           ;  ZF=0   //0x8&0x8=0x8
0040125B  |.  0F84 06010000 je      00401367                         ;  不跳    //ZF=0;只有相等时,才跳
00401261  |.  3C 20         cmp     al, 20                           ;  AL是否为空
00401263  |.  0F8F 13010000 jg      0040137C                         ;  不跳    //ZF=1;当比较结果是大于时,才跳
00401269  |.  3C 05         cmp     al, 5                            ;  ZF=0   //AL=0x8
0040126B  |.  0F8C 20010000 jl      00401391                         ;  不跳    //ZF=0,当比较结果是小于时,才跳
00401271  |.  8D1D 8C314000 lea     ebx, dword ptr [40318C]

在00401248处F2下断,然后F9运行程序停在断点。

00401248  |.  6A 28         push    28                               ; /Count = 28 (40.)
0040124A  |.  68 8C314000   push    0040318C                         ; |Buffer = d2k2_cra.0040318C
0040124F  |.  6A 02         push    2                                ; |ControlID = 2
00401251  |.  FF75 08       push    dword ptr [ebp+8]                ; |hWnd
00401254  |.  E8 8F010000   call    <jmp.&USER32.GetDlgItemTextA>    ; \GetDlgItemTextA
00401259  |.  84C0          test    al, al                           ;  ZF=0   //0x8&0x8=0x8
0040125B  |.  0F84 06010000 je      00401367                         ;  判断用户名是否为空
00401261  |.  3C 20         cmp     al, 20                           ;  判断用户名是否大于20位
00401263  |.  0F8F 13010000 jg      0040137C                         ;  不跳    //ZF=1;当比较结果是大于时,才跳
00401269  |.  3C 05         cmp     al, 5                            ;  判断用户名是否小于5位
0040126B  |.  0F8C 20010000 jl      00401391                         ;  不跳    //ZF=0,当比较结果是小于时,才跳
00401271  |.  8D1D 8C314000 lea     ebx, dword ptr [40318C]          ;  获取用户名
00401277  |.  33C9          xor     ecx, ecx                         ;  ECX清零,存放注册值
00401279  |.  B0 05         mov     al, 5                            ;  AL=0x5    计数器
0040127B  |.  33D2          xor     edx, edx                         ;  EDX=0,CF=0   //自身xor运算结果为0,CF=0
0040127D  |>  8A0C1A        mov     cl, byte ptr [edx+ebx]           ;  取用户名的第一个字母开始计算
00401280  |.  80F1 29       xor     cl, 29                           ;  CL=0x53  与29异或
00401283  |.  02C8          add     cl, al                           ;  CL=0x54   //CL=0x53+0x1
00401285  |.  80F9 41       cmp     cl, 41                           ;  CL与'A'比较    小于A则跳
00401288  |.  7C 1C         jl      short 004012A6                   ;  不跳    //ZF=0,当比较结果是小于时,才跳
0040128A  |.  80F9 5A       cmp     cl, 5A                           ;  CL与'Z'比较    大于Z则跳
0040128D  |.  7F 17         jg      short 004012A6                   ;  不跳    //ZF=1;当比较结果是大于时,才跳
0040128F  |>  888A 3C314000 mov     byte ptr [edx+40313C], cl        ;  保存算出的值
00401295  |.  C682 3D314000>mov     byte ptr [edx+40313D], 0
0040129C  |.  FEC2          inc     dl                               ;  DL=(0x4)++
0040129E  |.  FEC8          dec     al                               ;  AL=(0x1)--   //减1
004012A0  |.  3C 00         cmp     al, 0                            ;  ZF=1   //AL=0x0
004012A2  |.  74 08         je      short 004012AC                   ;  跳到004012AC  //ZF=1,结果相等
004012A4  |.^ EB D7         jmp     short 0040127D                   ;  跳转到0040127D
004012A6  |>  B1 52         mov     cl, 52                           ;  CL=0x52
004012A8  |.  02C8          add     cl, al                           ;  CL=0x54   //CL=0x52+0x2
004012AA  |.^ EB E3         jmp     short 0040128F                   ;  跳转到0040128F
004012AC  |>  33D2          xor     edx, edx                         ;  EDX=0,CF=0   //自身xor运算结果为0,CF=0
004012AE  |.  B8 05000000   mov     eax, 5                           ;  EAX=0x5
004012B3  |>  8A0C1A        mov     cl, byte ptr [edx+ebx]
004012B6  |.  80F1 27       xor     cl, 27                           ;  CL=0x49   //CL=0x6E^0x27
004012B9  |.  02C8          add     cl, al                           ;  CL=0x44   //CL=0x42+0x2
004012BB  |.  80C1 01       add     cl, 1                            ;  CL=0x45   //CL=0x44+0x1
004012BE  |.  80F9 41       cmp     cl, 41                           ;  CL与'A'比较    //CL=0x45;ZF=0
004012C1  |.  7C 1C         jl      short 004012DF                   ;  不跳    //ZF=0,当比较结果是小于时,才跳
004012C3  |.  80F9 5A       cmp     cl, 5A                           ;  CL与'Z'比较    //CL=0x45;ZF=0
004012C6  |.  7F 17         jg      short 004012DF                   ;  不跳    //ZF=1;当比较结果是大于时,才跳
004012C8  |>  888A 41314000 mov     byte ptr [edx+403141], cl
004012CE  |.  C682 42314000>mov     byte ptr [edx+403142], 0
004012D5  |.  FEC2          inc     dl                               ;  DL=(0x4)++
004012D7  |.  FEC8          dec     al                               ;  AL=(0x1)--   //减1
004012D9  |.  3C 00         cmp     al, 0                            ;  ZF=1   //AL=0x0
004012DB  |.  74 08         je      short 004012E5                   ;  不跳    //ZF=0;只有相等时,才跳
004012DD  |.^ EB D4         jmp     short 004012B3                   ;  跳转到004012B3
004012DF  |>  B1 4D         mov     cl, 4D                           ;  CL=0x4D
004012E1  |.  02C8          add     cl, al                           ;  CL=0x52   //CL=0x4D+0x5
004012E3  |.^ EB E3         jmp     short 004012C8                   ;  跳转到004012C8
004012E5  |>  33C0          xor     eax, eax
004012E7  |.  6A 28         push    28                               ; /Count = 28 (40.)
004012E9  |.  68 B4314000   push    004031B4                         ; |Buffer = d2k2_cra.004031B4
004012EE  |.  6A 04         push    4                                ; |ControlID = 4
004012F0  |.  FF75 08       push    dword ptr [ebp+8]                ; |hWnd
004012F3  |.  E8 F0000000   call    <jmp.&USER32.GetDlgItemTextA>    ; \GetDlgItemTextA
004012F8  |.  66:85C0       test    ax, ax                           ;  ZF=0   //0x9&0x9=0x9
004012FB  |.  74 55         je      short 00401352                   ;  不跳    //ZF=0;只有相等时,才跳
004012FD  |.  66:83F8 0A    cmp     ax, 0A                           ;  ZF=0   //AX=0x9
00401301  |.  7F 4F         jg      short 00401352                   ;  不跳    //ZF=1;当比较结果是大于时,才跳
00401303  |.  7C 4D         jl      short 00401352                   ;  跳到00401352  //ZF=0,SF!=OF
00401305  |.  33C0          xor     eax, eax
00401307  |.  33DB          xor     ebx, ebx
00401309  |.  33C9          xor     ecx, ecx
0040130B  |.  33D2          xor     edx, edx
0040130D  |.  8D05 B4314000 lea     eax, dword ptr [4031B4]          ;  获取假码
00401313  |>  8A1C01        mov     bl, byte ptr [ecx+eax]           ;  获取真码的第一个位
00401316  |.  8A91 3C314000 mov     dl, byte ptr [ecx+40313C]        ;  获取假码的第一位
0040131C  |.  80FB 00       cmp     bl, 0
0040131F  |.  0F84 81000000 je      004013A6
00401325  |.  80C2 05       add     dl, 5                            ;  dl=dl+5
00401328  |.  80FA 5A       cmp     dl, 5A                           ;  是否大于Z
0040132B  |.  7F 14         jg      short 00401341
0040132D  |>  80F2 0C       xor     dl, 0C                           ;  异或比较
00401330  |.  80FA 41       cmp     dl, 41                           ;  是否小于A
00401333  |.  7C 11         jl      short 00401346
00401335  |.  80FA 5A       cmp     dl, 5A
00401338  |.  7F 12         jg      short 0040134C
0040133A  |>  41            inc     ecx
0040133B  |.  38DA          cmp     dl, bl                           ;  比较真假
0040133D  |.^ 74 D4         je      short 00401313
0040133F  |.  EB 11         jmp     short 00401352
00401341  |>  80EA 0D       sub     dl, 0D
00401344  |.^ EB E7         jmp     short 0040132D
00401346  |>  B2 4B         mov     dl, 4B
00401348  |.  02D1          add     dl, cl
0040134A  |.^ EB EE         jmp     short 0040133A
0040134C  |>  B2 4B         mov     dl, 4B
0040134E  |.  2AD1          sub     dl, cl
00401350  |.^ EB E8         jmp     short 0040133A
00401352  |>  6A 00         push    0                                ; /0x0进栈
00401354  |.  68 49304000   push    00403049                         ; |dont give up...
00401359  |.  68 59304000   push    00403059                         ; |wrong code!try again!
0040135E  |.  6A 00         push    0                                ; |hOwner = NULL
00401360  |.  E8 A1000000   call    <jmp.&USER32.MessageBoxA>        ; \MessageBoxA
00401365  |.  EB 52         jmp     short 004013B9
00401367  |>  6A 00         push    0                                ; /Style = MB_OK|MB_APPLMODAL
00401369  |.  68 6F304000   push    0040306F                         ; |sorry...
0040136E  |.  68 97304000   push    00403097                         ; |enter name!
00401373  |.  6A 00         push    0                                ; |hOwner = NULL
00401375  |.  E8 8C000000   call    <jmp.&USER32.MessageBoxA>        ; \MessageBoxA
0040137A  |.  EB 3D         jmp     short 004013B9
0040137C  |>  6A 00         push    0                                ; /Style = MB_OK|MB_APPLMODAL
0040137E  |.  68 6F304000   push    0040306F                         ; |sorry...
00401383  |.  68 A3304000   push    004030A3                         ; |name can be max 32 chars long!
00401388  |.  6A 00         push    0                                ; |hOwner = NULL
0040138A  |.  E8 77000000   call    <jmp.&USER32.MessageBoxA>        ; \MessageBoxA
0040138F  |.  EB 28         jmp     short 004013B9
00401391  |>  6A 00         push    0                                ; /Style = MB_OK|MB_APPLMODAL
00401393  |.  68 6F304000   push    0040306F                         ; |sorry...
00401398  |.  68 78304000   push    00403078                         ; |name must be min 5 chars long!
0040139D  |.  6A 00         push    0                                ; |hOwner = NULL
0040139F  |.  E8 62000000   call    <jmp.&USER32.MessageBoxA>        ; \MessageBoxA
004013A4  |.  EB 13         jmp     short 004013B9
004013A6  |>  6A 00         push    0                                ; /Style = MB_OK|MB_APPLMODAL
004013A8  |.  68 C2304000   push    004030C2                         ; |good cracker
004013AD  |.  68 CF304000   push    004030CF                         ; |serial is correct! now write a keygen + tut and send it to: diablo2oo2@gmx.net !
004013B2  |.  6A 00         push    0                                ; |hOwner = NULL
004013B4  |.  E8 4D000000   call    <jmp.&USER32.MessageBoxA>        ; \MessageBoxA
004013B9  |>  EB 15         jmp     short 004013D0
004013BB  |>  FF75 14       push    dword ptr [ebp+14]               ; /lParam
004013BE  |.  FF75 10       push    dword ptr [ebp+10]               ; |wParam
004013C1  |.  FF75 0C       push    dword ptr [ebp+C]                ; |Message
004013C4  |.  FF75 08       push    dword ptr [ebp+8]                ; |hWnd
004013C7  |.  E8 10000000   call    <jmp.&USER32.DefWindowProcA>     ; \DefWindowProcA

--------------------------------------------------------------------------------
【算法总结】
        较简单,还需要深入学习
【注册机算法】

代码:
      分析上面代码写出注册机

ebx = Text1.Text
ecx = 0
al = &H5
edx = 0
For i = 1 To 5
    cl = Asc(Mid(ebx, i, 1))
    cl = cl Xor &H29
    cl = cl + al
    If cl < &H41 Or cl > &H5A Then
        cl = &H52
        cl = cl + al
    End If
    CodeStr1 = CodeStr1 & Chr(cl)
    Code1 = Code1 & al
    dl = dl + 1
    al = al - 1
    'MsgBox CodeStr1
Next
edx = 0
eax = &H5
al = &H5
For i = 1 To 5
    cl = Asc(Mid(ebx, i, 1))
    cl = cl Xor &H27
    cl = cl + al
    cl = cl + 1
    If cl < &H41 Or cl > &H5A Then
        cl = &H4D
        cl = cl + al
    End If
    CodeStr2 = CodeStr2 & Chr(cl)
    Code2 = Code2 & al
    dl = dl + 1
    al = al - 1
Next
Text2.Text = CodeStr1 & CodeStr2
Code = Code1 & Code2
eax = 0
ebx = 0
ecx = 0
edx = 0
eax = Text2.Text
cl = 0
For i = 1 To 10
    dl = Asc(Mid(Text2.Text, i, 1))
    dl = dl + &H5
    If dl > &H5A Then
        dl = dl - &HD
    End If
    dl = dl Xor &HC
    If dl < &H41 Then
        dl = &H4B
        dl = dl + cl
    End If
    If dl > &H5A Then
        dl = &H4B
        dl = dl - cl
    End If
    cl = cl + 1
    AA = AA & Chr(dl)
Next
Text3.Text = AA

写的不好,大侠指点一下。。。

  

  注册机和原始cm见附件。。。
--------------------------------------------------------------------------------
【经验总结】
        需要有汇编基础,最少也要懂最基础的几个汇编命令,然后在写注册机的时候知道汇编与各种语言的转换函数
        1、chr()   返回与指定字符代码相关联的字符。可将数字转换为字母
        2、hex()   函数返回表示十六进制数字值的字符串
        3、asc()   返回与字符串的第一个字母对应的 ANSI 字符代码。
        4、汇编里面的16进制数在VB里面用&H表示,比如:mav al,5a   这里的5a在VB里面要写成&H5A
        5、还有一个要感谢红尘岁月帮我解答的test al,al   判断al是否等于零
--------------------------------------------------------------------------------
【版权声明】: 本文原创于看雪技术论坛, 转载请注明作者并保持文章的完整, 谢谢!

                                                       2009年06月13日 10:46:50


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

上传的附件:
收藏
免费 7
支持
分享
最新回复 (2)
雪    币: 369
活跃值: (10)
能力值: ( LV7,RANK:100 )
在线值:
发帖
回帖
粉丝
2
写的不错,vb来的,学习下
2009-6-13 15:42
0
雪    币: 452
活跃值: (10)
能力值: ( LV6,RANK:90 )
在线值:
发帖
回帖
粉丝
3

汇编里面的16进制数在VB里面用&H表示
test al,al 判断al是否等于零


呵呵,经验总结很棒呀!
2009-6-27 20:10
0
游客
登录 | 注册 方可回帖
返回
//