• 标 题:Registry Crawler 4.0注册码算法分析 - OCG (20千字)
  • 作 者:alphakk
  • 时 间:2002-4-7 0:56:16
  • 链 接:http://bbs.pediy.com

=====Open Cracking Group======


=Registry Crawler 4.0注册码算法分析


=        CrAcKeD BY alphakk/OCG
=====================
=====================================
=软件简介:                               =
=  Registry Crawler 是强大的用户和开发者快速定位并配置注册表的工具软  =
=件。一个强大的搜索引擎允许你基于搜索标准查找注册信息。允许你单击超链 =
=接显示条目。支持书签功能,可在注册表中的任何键中添加书签并直接从系统 =
=托盘读取。此特征允许你访问你经常存取的注册键而无需手工打开 REGEDIT。 =
=每天需要操作注册表的用户会发现 Registry Crawler 是一个节约时间的工具。=
=====================================
=========================================================
破解工具:SOFTICE,W32DASM
分析:
本软件采用用户名,注册码的验证方式,不注册的话会有30天的试用期,过期会提示用户注册,还未注册的话,将不能继续使用。
此软件无功能限制。
在注册窗口中输入以下信息:
用户名:alphakk/OCG
注册码:98765432
用GETWINDOWTEXT作断点,点击“解锁”,被SOFTICE中断,接着按F11跳出GETWINDOWTEXT函数,来到:

* Reference To: USER32.GetWindowTextA, Ord:015Eh
                                |
:0042DA07 FF1550844400            Call dword ptr [00448450]
:0042DA0D EB12                    jmp 0042DA21  <<-------按F11后来到的地方

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0042D9FA(C)
|
:0042DA0F FF742408                push [esp+08]
:0042DA13 8B10                    mov edx, dword ptr [eax]
:0042DA15 8BC8                    mov ecx, eax
:0042DA17 FF742408                push [esp+08]
:0042DA1B FF9284000000            call dword ptr [edx+00000084]

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0042DA0D(U)
|
:0042DA21 C20800                  ret 0008
======================F10单步跟踪过上面后,来到:
* Possible Reference to Dialog: 
                                |
:0040AFDC 6810E54500              push 0045E510  
:0040AFE1 8D8EBC030000            lea ecx, dword ptr [esi+000003BC]
:0040AFE7 E8092A0200              call 0042D9F5
:0040AFEC 68FF000000              push 000000FF

* Possible Reference to Dialog: 
                                |
:0040AFF1 6810E64500              push 0045E610  <<-----输入的注册码入栈
:0040AFF6 8D8E80030000            lea ecx, dword ptr [esi+00000380]
:0040AFFC E8F4290200              call 0042D9F5

* Possible Reference to Dialog: 
                                |
:0040B001 6810E54500              push 0045E510   <<------用户名入栈
:0040B006 8D4C240C                lea ecx, dword ptr [esp+0C]
:0040B00A E8F6330200              call 0042E405
:0040B00F 8B00                    mov eax, dword ptr [eax] <<------用户名首地址->EAX

* Possible Reference to Dialog: 
                                |
:0040B011 68848C4500              push 00458C84  <<------“TRIAL USER”入栈
:0040B016 50                      push eax  <<------用户名入栈
:0040B017 E8BFE60000              call 004196DB  <<------比较函数,不同则EAX=1
:0040B01C 83C408                  add esp, 00000008
:0040B01F 8D4C2408                lea ecx, dword ptr [esp+08]
:0040B023 85C0                    test eax, eax
:0040B025 0F94C3                  sete bl    <<------BL置0
:0040B028 E86A330200              call 0042E397
:0040B02D 84DB                    test bl, bl
:0040B02F 740F                    je 0040B040   <<------跳
:0040B031 6A01                    push 00000001
:0040B033 8BCE                    mov ecx, esi
:0040B035 E8DB3F0200              call 0042F015
:0040B03A 5E                      pop esi
:0040B03B 5B                      pop ebx
:0040B03C 83C408                  add esp, 00000008
:0040B03F C3                      ret

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0040B02F(C)
|
:0040B040 E8ABFCFFFF              call 0040ACF0  <<-----注意这个CALL,此处先用F10带过
:0040B045 85C0                    test eax, eax
:0040B047 0F849D000000            je 0040B0EA  <<-------上面的CALL用F10过的话,这里就会跳

* Possible StringData Ref from Data Obj ->"Software\4Developers\RCrawler"
                                |
:0040B04D 8B15F88A4500            mov edx, dword ptr [00458AF8]
:0040B053 8D44240C                lea eax, dword ptr [esp+0C]
:0040B057 8D4C2408                lea ecx, dword ptr [esp+08]
:0040B05B 33DB                    xor ebx, ebx
:0040B05D 50                      push eax
:0040B05E 51                      push ecx
:0040B05F 53                      push ebx
:0040B060 683F000F00              push 000F003F
:0040B065 53                      push ebx
:0040B066 53                      push ebx
:0040B067 53                      push ebx
:0040B068 52                      push edx
:0040B069 6802000080              push 80000002
:0040B06E 895C2430                mov dword ptr [esp+30], ebx
:0040B072 895C242C                mov dword ptr [esp+2C], ebx

* Reference To: ADVAPI32.RegCreateKeyExA, Ord:015Fh
                                |
:0040B076 FF1534804400            Call dword ptr [00448034]
:0040B07C 3BC3                    cmp eax, ebx
:0040B07E 7531                    jne 0040B0B1

* Possible StringData Ref from Data Obj ->"4D"
                                |
:0040B080 A1048B4500              mov eax, dword ptr [00458B04]
:0040B085 8B4C2408                mov ecx, dword ptr [esp+08]
:0040B089 57                      push edi
:0040B08A 6800020000              push 00000200
:0040B08F 6810E54500              push 0045E510
:0040B094 6A03                    push 00000003
:0040B096 53                      push ebx
:0040B097 50                      push eax
:0040B098 51                      push ecx

* Reference To: ADVAPI32.RegSetvalueExA, Ord:0186h
                                |
:0040B099 FF1524804400            Call dword ptr [00448024]
:0040B09F 8B54240C                mov edx, dword ptr [esp+0C]
:0040B0A3 8BF8                    mov edi, eax
:0040B0A5 52                      push edx

* Reference To: ADVAPI32.RegCloseKey, Ord:015Bh
                                |
:0040B0A6 FF1520804400            Call dword ptr [00448020]
:0040B0AC 3BFB                    cmp edi, ebx
:0040B0AE 5F                      pop edi
:0040B0AF 7419                    je 0040B0CA

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0040B07E(C)
|
:0040B0B1 53                      push ebx
:0040B0B2 53                      push ebx

* Possible StringData Ref from Data Obj ->"无法记录注册信息.

请联系 crawler@4dev.com"
                                |
:0040B0B3 68A88F4500              push 00458FA8
:0040B0B8 E866B50200              call 00436623
:0040B0BD 8BCE                    mov ecx, esi
:0040B0BF E8DE400200              call 0042F1A2
:0040B0C4 5E                      pop esi
:0040B0C5 5B                      pop ebx
:0040B0C6 83C408                  add esp, 00000008
:0040B0C9 C3                      ret



* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0040B0AF(C)
|
:0040B0CA 6A40                    push 00000040

* Possible Reference to Dialog: 
                                |
:0040B0CC 68988F4500              push 00458F98

* Possible StringData Ref from Data Obj ->"欢迎使用 Registry Crawle 的完整版本. "
                                      ->"感谢你注册软件.

请重新启动程序,以解除所有未注"
                                      ->"册版本的功能限制."
                                |
:0040B0D1 68FC8E4500              push 00458EFC
:0040B0D6 8BCE                    mov ecx, esi
:0040B0D8 E80F110200              call 0042C1EC
:0040B0DD 8BCE                    mov ecx, esi
:0040B0DF E8BE400200              call 0042F1A2
:0040B0E4 5E                      pop esi
:0040B0E5 5B                      pop ebx
:0040B0E6 83C408                  add esp, 00000008
:0040B0E9 C3                      ret

======看看0040B047处的跳转是到哪儿了:
* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0040B047(C)
|
:0040B0EA 8BCE                    mov ecx, esi
:0040B0EC E80FFAFFFF              call 0040AB00 <<-------注意这个CALL,F10带过的话,EAX=0
:0040B0F1 85C0                    test eax, eax
:0040B0F3 7419                    je 0040B10E  <<------跳
:0040B0F5 6A40                    push 00000040

* Possible Reference to Dialog: 
                                |
:0040B0F7 68E88E4500              push 00458EE8

* Possible StringData Ref from Data Obj ->"你输入的注册信息仅能用于 Registry "
                                      ->"Crawler 3.x 版本.

要注册 4.0 "
                                      ->"以上版本,你需要新的注册信息.请与我们联系,将你?
                                      ->"淖⒉崧肷兜?Registry Crawler "
                                      ->"4.0 (E-mail sales@4dev.com). 注意在 "
                                      ->"E-mail 中你必须提供旧版本的注册码.

谢谢,
4Dev"
                                      ->"elopers Team."
                                |
:0040B0FC 68AC8D4500              push 00458DAC
:0040B101 8BCE                    mov ecx, esi
:0040B103 E8E4100200              call 0042C1EC
:0040B108 5E                      pop esi
:0040B109 5B                      pop ebx
:0040B10A 83C408                  add esp, 00000008
:0040B10D C3                      ret

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0040B0F3(C)
|
:0040B10E 6A30                    push 00000030

* Possible Reference to Dialog: 
                                |
:0040B110 68A08D4500              push 00458DA0

* Possible StringData Ref from Data Obj ->"你输入的注册信息是无效的.
请重新输入你从 "
                                      ->"4Developers LLC 得到的用户 ID "
                                      ->"及相应的注册码.

如果你尚未注册,你可以点击下面"
                                      ->"的 '马上定购' 软件.如果你需要帮助,请发 "
                                      ->"E-mail 到: crawler@4dev.com"
                                |
:0040B115 68908C4500              push 00458C90
:0040B11A 8BCE                    mov ecx, esi
:0040B11C E8CB100200              call 0042C1EC
:0040B121 5E                      pop esi
:0040B122 5B                      pop ebx
:0040B123 83C408                  add esp, 00000008
:0040B126 C3                      ret
===================================================
由上面这段代码不难看出,Regstry Crawler 的注册码运算有两处:0040B040处的CALL,0040B0EC处的CALL,其中前者为4.0版的注册码运算,而后者为3.x版注册码的运算,3.x版的注册码运算与4.0版的有点像。注册码验证流程为:先将用户名用4.0版的注册码算法进行运算,并与用户输入的注册码进行比较,不同的话,再将用户名用3.x版的注册码算法进行运算,并与用户输入的注册码进行比较,如果相同,则提示用户更新注册码,如果不同,则跳出注册失败对话框。本文只是对4.0版的注册码运算进行分析,不讨论3.x版的算法,因此不进入第二个CALL。
===================================================
初步分析完成,进入第二次分析:
来到 0040B040处,按F8进入CALL,此时来到:

* Referenced by a CALL at Addresses:
|:0040AAF3  , :0040B040 
|
:0040ACF0 83EC24                  sub esp, 00000024
:0040ACF3 83C9FF                  or ecx, FFFFFFFF
:0040ACF6 33C0                    xor eax, eax
:0040ACF8 55                      push ebp
:0040ACF9 57                      push edi

* Possible Reference to Dialog: 
                                |
:0040ACFA BF10E54500              mov edi, 0045E510 <<------0045E510为用户名首地址 \
:0040ACFF F2                      repnz                                              \
:0040AD00 AE                      scasb                                        测试用户名长度->ECX
:0040AD01 F7D1                    not ecx                                            /
:0040AD03 49                      dec ecx                                            /
:0040AD04 8BE9                    mov ebp, ecx
:0040AD06 83FD08                  cmp ebp, 00000008
:0040AD09 7D06                    jge 0040AD11   <--------大于或等于8则跳,如果不跳,则不进行4.0版的注册码算法(此例中的用户名符合条件)
:0040AD0B 5F                      pop edi
:0040AD0C 5D                      pop ebp
:0040AD0D 83C424                  add esp, 00000024
:0040AD10 C3                      ret


==================下面开始注册码算法======================
* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0040AD09(C)
|
:0040AD11 53                      push ebx
:0040AD12 56                      push esi
:0040AD13 6810E54500              push 0045E510   <<-------用户名入栈
:0040AD18 E845D00100              call 00427D62     <<-------将用户名中所有的大写字母转成小写字母
:0040AD1D B907000000              mov ecx, 00000007
:0040AD22 33C0                    xor eax, eax
:0040AD24 8D7C2419                lea edi, dword ptr [esp+19]
:0040AD28 C644241800              mov [esp+18], 00
:0040AD2D F3                      repz
:0040AD2E AB                      stosd
:0040AD2F 66AB                    stosw
:0040AD31 83C404                  add esp, 00000004
:0040AD34 AA                      stosb
:0040AD35 8D442414                lea eax, dword ptr [esp+14]

* Possible Reference to Dialog: 
                                |
:0040AD39 68E48B4500              push 00458BE4  <<---------“8267-”入栈
:0040AD3E 50                      push eax

* Reference To: KERNEL32.lstrcpyA, Ord:0302h
                                |
:0040AD3F FF155C834400            Call dword ptr [0044835C]  <<-------“8267-”首地址->EAX
:0040AD45 33DB                    xor ebx, ebx  <<-------EBX清零,准备计数

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0040ADFA(C)
|

* Possible StringData Ref from Data Obj ->"0123456789"
                                |
:0040AD47 8B35FC8A4500            mov esi, dword ptr [00458AFC]   <<--------字符串“0123456789”的首地址->ESI
:0040AD4D 83C9FF                  or ecx, FFFFFFFF
:0040AD50 8BFE                    mov edi, esi  \
:0040AD52 33C0                    xor eax, eax    \
:0040AD54 F2                      repnz            \
:0040AD55 AE                      scasb          测试“0123456789”的长度->ECX
:0040AD56 F7D1                    not ecx        /
:0040AD58 49                      dec ecx        /
:0040AD59 8BC3                    mov eax, ebx
:0040AD5B 33D2                    xor edx, edx
:0040AD5D 8BFE                    mov edi, esi
:0040AD5F F7F1                    div ecx    <<--------此处运算后,EDX存放余数
:0040AD61 8BC3                    mov eax, ebx
:0040AD63 6A01                    push 00000001
:0040AD65 0FBE0C32                movsx ecx, byte ptr [edx+esi]  <<-------字符串“0123456789”的每个字符按顺序依次送入ECX,每次循环送入一个
:0040AD69 33D2                    xor edx, edx
:0040AD6B F7F5                    div ebp     <<=======EBP存放用户名长度,始终不变
:0040AD6D 0FBE8210E54500          movsx eax, byte ptr [edx+0045E510]  <<---------用户名的第个字符按顺序依次送入EAX,每次循环送入一个,如果用户名长度小于循环次数,则遍历完一次用户名后,重新从用户名的第一位开始
:0040AD74 8BD0                    mov edx, eax
:0040AD76 C1E205                  shl edx, 05
:0040AD79 03D0                    add edx, eax
:0040AD7B 8D0450                  lea eax, dword ptr [eax+2*edx]
:0040AD7E 03C8                    add ecx, eax
:0040AD80 8BC3                    mov eax, ebx
:0040AD82 0FAFC3                  imul eax, ebx
:0040AD85 0FAFC3                  imul eax, ebx

:0040AD8B 8D1480                  lea edx, dword ptr [eax+4*eax]
:0040AD8E 8D0450                  lea eax, dword ptr [eax+2*edx]
:0040AD91 03C8                    add ecx, eax
:0040AD93 33C0                    xor eax, eax
:0040AD95 8BD1                    mov edx, ecx
:0040AD97 83C9FF                  or ecx, FFFFFFFF  \
:0040AD9A F2                      repnz                \
:0040AD9B AE                      scasb            测试“0123456789”的长度->ECX
:0040AD9C F7D1                    not ecx              /
:0040AD9E 8BC2                    mov eax, edx        /
:0040ADA0 49                      dec ecx            /
:0040ADA1 33D2                    xor edx, edx
:0040ADA3 F7F1                    div ecx    <<------运算的余数->EDX
:0040ADA5 8D442418                lea eax, dword ptr [esp+18]
:0040ADA9 03D6                    add edx, esi  <<-------ESI为“0123456789”的首地址
:0040ADAB 52                      push edx
:0040ADAC 50                      push eax
:0040ADAD E82EEB0000              call 004198E0
:0040ADB2 83C40C                  add esp, 0000000C
:0040ADB5 85DB                    test ebx, ebx
:0040ADB7 743D                    je 0040ADF6  <<------------仅第一次循环时(EBX=0)跳 \
:0040ADB9 8BC3                    mov eax, ebx                                              \
:0040ADBB 33D2                    xor edx, edx                                              \
:0040ADBD B903000000              mov ecx, 00000003                                          此处控制注册码的形式
:0040ADC2 F7F1                    div ecx                                                  /
:0040ADC4 85D2                    test edx, edx                                            /
:0040ADC6 752E                    jne 0040ADF6   <<---------余数不为0则跳              /

* Possible Reference to Dialog: 
                                |
:0040ADC8 BFEC8B4500              mov edi, 00458BEC
:0040ADCD 83C9FF                  or ecx, FFFFFFFF
:0040ADD0 33C0                    xor eax, eax
:0040ADD2 8D542414                lea edx, dword ptr [esp+14]
:0040ADD6 F2                      repnz
:0040ADD7 AE                      scasb
:0040ADD8 F7D1                    not ecx
:0040ADDA 2BF9                    sub edi, ecx
:0040ADDC 8BF7                    mov esi, edi
:0040ADDE 8BFA                    mov edi, edx
:0040ADE0 8BD1                    mov edx, ecx
:0040ADE2 83C9FF                  or ecx, FFFFFFFF
:0040ADE5 F2                      repnz
:0040ADE6 AE                      scasb
:0040ADE7 8BCA                    mov ecx, edx
:0040ADE9 4F                      dec edi
:0040ADEA C1E902                  shr ecx, 02
:0040ADED F3                      repz
:0040ADEE A5                      movsd
:0040ADEF 8BCA                    mov ecx, edx
:0040ADF1 83E103                  and ecx, 00000003
:0040ADF4 F3                      repz
:0040ADF5 A4                      movsb

* Referenced by a (U)nconditional or (C)onditional Jump at Addresses:
|:0040ADB7(C), :0040ADC6(C)
|
:0040ADF6 43                      inc ebx
:0040ADF7 83FB09                  cmp ebx, 00000009
:0040ADFA 0F8247FFFFFF            jb 0040AD47
:0040AE00 8D442414                lea eax, dword ptr [esp+14]
:0040AE04 6810E64500              push 0045E610
:0040AE09 50                      push eax
:0040AE0A E801570100              call 00420510
:0040AE0F 83C408                  add esp, 00000008
:0040AE12 F7D8                    neg eax
:0040AE14 5E                      pop esi
:0040AE15 5B                      pop ebx
:0040AE16 1BC0                    sbb eax, eax
:0040AE18 5F                      pop edi
:0040AE19 40                      inc eax
:0040AE1A 5D                      pop ebp
:0040AE1B 83C424                  add esp, 00000024
:0040AE1E C3                      ret
=====================================================
算法思想:
  将用户名与固定字符串“0123456789”进行运算,以运算结果的EDX(余数)中的值为偏移量,取得此偏移量所指向的“0123456789”中的值并输出,共循环9次。注册码形式为:8267-XXXX-XXX-XX
本例中:
  用户名:alphakk/OCG
  注册码:8267-7626-579-75
=====================================================
=====Open Cracking Group======


=Registry Crawler 4.0注册码算法分析
=          (附:注册机)

=        CrAcKeD BY alphakk/OCG
=====================
注册机在:http://www.newclw.com/lllufh/cgi-bin/leoboard.cgi