zapline 发表于 2009-2-4 01:08

一个简单CrackMe的分析

crackme.de上的新CM,很简单
只要求输入注册码
通过下GetDlgItemTextA断点,找到关键部分0040034E|.6A 10         push 10                                  ; /Count = 10 (16.)
00400350|.68 60024000   push crcme.00400260                      ; |Buffer = crcme.00400260
00400355|.6A 65         push 65                                  ; |ControlID = 65 (101.)
00400357|.FF75 08       push                            ; |hWnd
0040035A|.E8 93000000   call <jmp.&USER32.GetDlgItemTextA>       ; \GetDlgItemTextA获取注册码,返回长度在EAX
注册码保存在:地址=00400260, (ASCII "pponmlkj")0040035F|.83F8 08       cmp eax,8
00400362|.75 34         jnz short crcme.00400398长度不为8则跳至00400398提示失败00400364|.8BC8          mov ecx,eax
00400366|.8D35 60024000 lea esi,dword ptr ds:长度放至ECX,做计数器,ESI指向注册码0040036C|>AC            /lods byte ptr ds:与00400381处命令照应,依次取注册码字符ASCII值存于EAX0040036D|.3C 61         |cmp al,61
0040036F|.7C 27         |jl short crcme.00400398
00400371|.3C 7A         |cmp al,7A
00400373|.7F 23         |jg short crcme.00400398字符ASCII值应在十六进制61和7A之间,即为小写字母00400375|.99            |cdqEDX清零(详细解释见附)00400376|.8BD9          |mov ebx,ecx
00400378|.F7F3          |div ebx
0040037A|.85D2          |test edx,edx
0040037C|.75 1A         |jnz short crcme.00400398
0040037E|.49            |dec ecxEDX = EAX值(字符ASCII值) / ECX
ECX递减,依次为8,7,6,5,4,3,2,1
EDX不为零(即字符ASCII值不能整除当前ECX)则跳至00400398提示出错0040037F|.85C9          |test ecx,ecx
00400381|.^ 75 E9         \jnz short crcme.0040036CECX是否为0(即字符串是否取完),没取玩则跳至0040036C继续
取完且上面的判断全部通过则继续向下00400383|.6A 00         push 0                                 ; /Style = MB_OK|MB_APPLMODAL
00400385|.68 7C024000   push crcme.0040027C                      ; |Title = "CRACKED!"
0040038A|.68 85024000   push crcme.00400285                      ; |Text = "MAKE A KEYGEN!"
0040038F|.6A 00         push 0                                 ; |hOwner = NULL
00400391|.E8 68000000   call <jmp.&USER32.MessageBoxA>         ; \MessageBoxA
00400396|.EB 34         jmp short crcme.004003CC提示成功00400398|>6A 00         push 0                                 ; /Style = MB_OK|MB_APPLMODAL
0040039A|.68 74024000   push crcme.00400274                      ; |Title = "NoOo..."
0040039F|.68 74024000   push crcme.00400274                      ; |Text = "NoOo..."
004003A4|.6A 00         push 0                                 ; |hOwner = NULL
004003A6|.E8 53000000   call <jmp.&USER32.MessageBoxA>         ; \MessageBoxA提示失败

附:CDQ 大多出现在除法运算之前,作用只是把EDX的所有位都设成EAX最高位的值. 也就是说,当EAX <80000000, EDX 00000000; 当EAX >= 80000000, EDX 则为FFFFFFFF).

总结:
注册码为八位
依次要能被8,7,6,5,4,3,2,1整除

“a”ASCII为十六进制61,即十进制97
所以 “hbfddcba”为一组可用注册码

附件:


讲的特别详细了
再讲讲KEYGEN的编写
注册码为八位
第一位可以为“h”“ p”“ x” 即13*8 14*8 15*8
第二位可以为14*7 15*7 16*7 17*7
第三位可以为17-20的数 *6
第四位可以为20-24    *5
第三位可以为25-20    *4
第三位可以为33-40    *3
第三位可以为49-61    *2
第三位可以为97-122    *1
.子程序 _按钮1_被单击
.局部变量 sjs, 整数型
.局部变量 pass, 文本型

pass = “”
编辑框1.内容 = “”
sjs = 取随机数 (13, 15)
pass = pass + 字符 (到字节 (sjs × 8))
sjs = 取随机数 (14, 17)
pass = pass + 字符 (到字节 (sjs × 7))
sjs = 取随机数 (17, 20)
pass = pass + 字符 (到字节 (sjs × 6))
sjs = 取随机数 (20, 24)
pass = pass + 字符 (到字节 (sjs × 5))
sjs = 取随机数 (25, 30)
pass = pass + 字符 (到字节 (sjs × 4))
sjs = 取随机数 (33, 40)
pass = pass + 字符 (到字节 (sjs × 3))
sjs = 取随机数 (49, 61)
pass = pass + 字符 (到字节 (sjs × 2))
sjs = 取随机数 (97, 122)
pass = pass + 字符 (到字节 (sjs × 1))
编辑框1.内容 = pass以下为计算出的几组注册码:
xwrdxoze
ppxipofx
pbldhlhx
pplilxbq
xplnxllo
xwrspctp

[ 本帖最后由 zapline 于 2009-2-4 13:48 编辑 ]

johway 发表于 2009-2-4 01:14

写东西就是这个??
=======================哇日


我也与沙发有缘?双

老万 发表于 2009-3-4 19:34

学习一下,谢谢楼主。

wz2796 发表于 2009-3-20 23:03

:lol学习一下,谢谢楼主。

myshell 发表于 2009-3-20 23:12

算法分析对菜鸟真的很难。

yncxhcd 发表于 2009-3-22 12:30

我支持你下 下载收藏

诸葛 发表于 2009-4-7 18:26

哎 都是高人啊

老海 发表于 2009-4-8 06:38

谢谢楼主,分析的很祥细。
页: [1]
查看完整版本: 一个简单CrackMe的分析