五子棋 v2.5b3 简单算法分析

今天女儿要玩五子棋,从网上随便找了个,也不知道是哪年的了(后来看了下是1999年的,晕),挺老。以为是免费的,结果女儿玩了两局跳出提示框,呵呵,太不给我面子。网上搜索,却没发现注册码。很久不碰软件了,今天看来只有自己动手了。

软件简介:
五子棋2.5版,这是华东计算机研究所蒋祥刚先生的作品,支持人机对战、双人对战及网络对战等多种模式,网络对战中还可以三个人同时玩“三足鼎立”,当然它的棋力也甚为可观,介面自不必说了,它甚至还有多语种支撑功能,最大限度地满足了各个层面用户的需求。

注册名:LeExOyO
注册码:72:1:2
试验码:654321

主文件Five.exe,无壳,delphi编程。用DeDe很快找到断点:

0045EC0C /. 55 push ebp //下断
0045EC0D |. 8BEC mov ebp, esp
0045EC0F |. 6A 00 push 0
0045EC11 |. 53 push ebx
0045EC12 |. 33C0 xor eax, eax

。。。。。。。。。。。。。。。

0045EC76 |. E8 31FDFFFF call 0045E9AC      //关键call
0045EC7B |. 803D 60FA4600>cmp byte ptr [46FA60], 0
0045EC82 |. 75 0C jnz short 0045EC90
0045EC84 |. B8 04ED4500 mov eax, 0045ED04
0045EC89 |. E8 82CAFEFF call 0044B710
0045EC8E |. EB 14 jmp short 0045ECA4
0045EC90 |> B8 30ED4500 mov eax, 0045ED30
0045EC95 |. E8 76CAFEFF call 0044B710
0045EC9A |. A1 5CFA4600 mov eax, [46FA5C]
0045EC9F |. E8 804EFEFF call 00443B24
0045ECA4 |> 33C0 xor eax, eax
0045ECA6 |. 5A pop edx
0045ECA7 |. 59 pop ecx

************************进入后****************

0045E9AC /$ 55 push ebp
0045E9AD |. 8BEC mov ebp, esp
0045E9AF |. 81C4 CCFDFFFF add esp, -234
0045E9B5 |. 53 push ebx
0045E9B6 |. 56 push esi
0045E9B7 |. 57 push edi

。。。。。。。。。。。。。。。。

0045EA5C |. 80BD 36FFFFFF>cmp byte ptr [ebp-CA], 6      //注册码为6位
0045EA63 |. 74 0C je short 0045EA71
0045EA65 |> \C605 60FA4600>mov byte ptr [46FA60], 0
0045EA6C |. E9 99000000 jmp 0045EB0A
0045EA71 |> 8BF0 mov esi, eax
0045EA73 |. 81E6 FF000000 and esi, 0FF
0045EA79 |. 85F6 test esi, esi
0045EA7B |. 7C 22 jl short 0045EA9F
0045EA7D |. 46 inc esi
0045EA7E |. 8D4D 9B lea ecx, [ebp-65] ;      //[ebp-65]="LeExOyO"
0045EA81 |. 8D9D D1FEFFFF lea ebx, [ebp-12F]
0045EA87 |> 33C0 /xor eax, eax
0045EA89 |. 8A01 |mov al, [ecx]             //依次取注册名各字符转成16进制送到al
0045EA8B |. BF 0A000000 |mov edi, 0A
0045EA90 |. 33D2 |xor edx, edx
0045EA92 |. F7F7 |div edi               //除以0xA取余
0045EA94 |. 80C2 30 |add dl, 30
0045EA97 |. 42 |inc edx                 //加1
0045EA98 |. 8813 |mov [ebx], dl
0045EA9A |. 43 |inc ebx
0045EA9B |. 41 |inc ecx
0045EA9C |. 4E |dec esi
0045EA9D |.^ 75 E8 \jnz short 0045EA87 ;       //循环算出注册码,并依次放入[ebx]内
0045EA9F |> 8A45 9B mov al, [ebp-65]
0045EAA2 |. 3C 06 cmp al, 6
0045EAA4 |. 73 31 jnb short 0045EAD7
0045EAA6 |. 33C9 xor ecx, ecx
0045EAA8 |. 8AC8 mov cl, al
0045EAAA |. 41 inc ecx
0045EAAB |. 83F9 06 cmp ecx, 6
0045EAAE |. 7F 27 jg short 0045EAD7
0045EAB0 |. 8D9C0D D0FEFF>lea ebx, [ebp+ecx-130]
0045EAB7 |> 33C0 /xor eax, eax
0045EAB9 |. 8A03 |mov al, [ebx]
0045EABB |. 83C0 02 |add eax, 2
0045EABE |. 83E8 30 |sub eax, 30
0045EAC1 |. BE 0A000000 |mov esi, 0A
0045EAC6 |. 33D2 |xor edx, edx
0045EAC8 |. F7F6 |div esi
0045EACA |. 80C2 30 |add dl, 30
0045EACD |. 8853 01 |mov [ebx+1], dl
0045EAD0 |. 41 |inc ecx
0045EAD1 |. 43 |inc ebx
0045EAD2 |. 83F9 07 |cmp ecx, 7
0045EAD5 |.^ 75 E0 \jnz short 0045EAB7
0045EAD7 |> C685 D8FEFFFF>mov byte ptr [ebp-128], 0
0045EADE |. C605 60FA4600>mov byte ptr [46FA60], 1
0045EAE5 |. B9 06000000 mov ecx, 6
0045EAEA |. 8D85 D2FEFFFF lea eax, [ebp-12E] ;     //[ebp-12E]="72:1:2"
0045EAF0 |. 8D95 37FFFFFF lea edx, [ebp-C9] ;       //[ebp-c9]=654321
0045EAF6 |> 8A18 /mov bl, [eax]
0045EAF8 |. 3A1A |cmp bl, [edx] ;           //逐位比较
0045EAFA |. 74 09 |je short 0045EB05
0045EAFC |. C605 60FA4600>|mov byte ptr [46FA60], 0
0045EB03 |. EB 05 |jmp short 0045EB0A
0045EB05 |> 42 |inc edx
0045EB06 |. 40 |inc eax
0045EB07 |. 49 |dec ecx
0045EB08 |.^ 75 EC \jnz short 0045EAF6
0045EB0A |> 33C0 xor eax, eax
0045EB0C |. 5A pop edx
0045EB0D |. 59 pop ecx
0045EB0E |. 59 pop ecx
0045EB0F |. 64:8910 mov fs:[eax], edx
0045EB12 |. 68 2AEB4500 push 0045EB2A
0045EB17 |> 8D85 CCFDFFFF lea eax, [ebp-234]
0045EB1D |. E8 B64DFAFF call 004038D8
0045EB22 \. C3 retn

算法比较简单:将注册名各字符的16进制除以0xA后的余数加上0x1,得到的值转为10进制取前面6位得到注册码。小于6位的注册名没有仔细看。

注册码明码保存在当前系统的windows目录下的Five99.ini中。
[Register]
Name=LeExOyO
RegNo=72:1:2

                          李逍遥[LeExOyO]
                           2006.08.04

  • 标 题: 答复
  • 作 者:KAN
  • 时 间:2006-08-20 01:05

现在的软件(不说了),没这样的好事了,我这两天分析了两个,靠
破解不难,你要跟他的算法,那个苦啊,一层又一层,几百行的计算
代码,其中又有十个八个大循环,要完全分析出来,没一两天所有
空余时间,怕是没结果了,不感碰啊

顺便答一下 二楼的朋友

0045EA89 |. 8A01 |mov al, [ecx]             //依次取注册名各字符转成16进制送到al

ds:[ecx] 每次提取了用户名的字符,那是一个循环,一个循环取出一个入 AL ,然后开始计算