老文章档案 · 2003 年

B-Puzzle拼图游戏算法分析(2)

破解教程 · 算法分析 · 2003-08-13 · 作者:人气: · 出处:赢政天下整理收藏)

B-Puzzle拼图游戏算法分析(2)

进入关键CALL,我们来到:

:004027C4 55 push ebp

:004027C5 8BEC mov ebp, esp

:004027C7 83C4F8 add esp, FFFFFFF8

:004027CA 53 push ebx

:004027CB 56 push esi

:004027CC 57 push edi

:004027CD FF7508 push [ebp+08]

:004027D0 E83F190500 call 00454114

:004027D5 59 pop ecx

:004027D6 83F808 cmp eax, 00000008

:004027D9 7710 ja 004027EB

* Possible StringData Ref from Data Obj ->" "

|

:004027DB 68E7254600 push 004625E7

:004027E0 FF7508 push [ebp+08]

:004027E3 E820180500 call 00454008

:004027E8 83C408 add esp, 00000008

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

|:004027D9(C)

|

:004027EB 33FF xor edi, edi

:004027ED 33F6 xor esi, esi

:004027EF 8B450C mov eax, dword ptr [ebp+0C]

:004027F2 8D1C38 lea ebx, dword ptr [eax+edi]

:004027F5 8B4508 mov eax, dword ptr [ebp+08]

:004027F8 8BD0 mov edx, eax

:004027FA 8955F8 mov dword ptr [ebp-08], edx==》用户名移到ebp-08

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

|:00402854(C)

SN1算法开始的地方:

也许你要问如何判断算法的开始,其实我的判断的依据就是:

1.它的注册码是动态的,也就是根据用户名的不同而变的。

2.所以,跟踪算法的时候,时刻注意各个寄存器中是否出现了你的用户名的16进制,和循环

3.看看在算法CALL中,哪里是出现真SN,它们进行反推,向上走。

4.一般,算法都会出现在关键CALL的最后。

:004027FD FF3590234600 push dword ptr [00462390]

:00402803 E80C190500 call 00454114

:00402808 59 pop ecx

:00402809 50 push eax

:0040280A 8BC6 mov eax, esi

:0040280C 5A pop edx

:0040280D 8BCA mov ecx, edx

:0040280F 33D2 xor edx, edx

:00402811 F7F1 div ecx

:00402813 A190234600 mov eax, dword ptr [00462390]==》00462390值移到EAX,00462390为"PUZZLEVERO"

:00402818 8A0410 mov al, byte ptr [eax+edx]==》取EAX第一位到AL

:0040281B 8B55F8 mov edx, dword ptr [ebp-08]==》取用户名第一位移到EDX

:0040281E 3202 xor al, byte ptr [edx]==》AL与EAX的值取异或,结果在AL

:00402820 0FBEC0 movsx eax, al==》16位寄存器扩展,目的是为了与32位寄存器间数据传送,异或后的值传入EDX

:00402823 6A0A push 0000000A

:00402825 8D55FC lea edx, dword ptr [ebp-04]==》EDX的值送入ebp-04

:00402828 52 push edx

:00402829 50 push eax

:0040282A E8F1940500 call 0045BD20==》寻其对应的DEC(十进制值)数值

:0040282F 83C40C add esp, 0000000C

:00402832 807DFD00 cmp byte ptr [ebp-03], 00==》比较ebp-03的值是否为零

:00402836 7504 jne 0040283C==》不等就跳

:00402838 B131 mov cl, 31

:0040283A EB03 jmp 0040283F

(说明:我第一次得到的ESP-04的值是40,那么ESP-03=ESP-04+01的值就是0,明白了吗?)

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

|:00402836(C)

|

:0040283C 8A4DFD mov cl, byte ptr [ebp-03]==》把ebp-03的值移到CL中

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

|:0040283A(U)

|

:0040283F 880B mov byte ptr [ebx], cl再由CL传入EBX

:00402841 43 inc ebx==》EBX加一

:00402842 8A45FC mov al, byte ptr [ebp-04]==》算好的值(40)的第一位又送到AL

:00402845 47 inc edi

:00402846 47 inc edi==》EDI连续加1,2次

:00402847 8803 mov byte ptr [ebx], al==》AL的值再送入加一后的EBX容器,那么她的值就,以我为例变为04

所以,00402832~00402847的作用就是把用户名第一位与定值“PUZZLEVERO"的第一位"P"取异或后的值,取前两位,并且进行位置互换。

:00402849 43 inc ebx==》EBX又加一

:0040284A 83C602 add esi, 00000002

:0040284D 8345F802 add dword ptr [ebp-08], 00000002==》EBP-08地址加2,即:用户名跳过一位,比如,我的用户名xx-fish第一次经过这一步之后变成-fish,明白吗?

:00402851 83FE08 cmp esi, 00000008==》比较ESI是否为8,来判断是否循环,也就是说这SN1的计算只有4次循环。

:00402854 7CA7 jl 004027FD==》小于则转移,继续循环。

:00402856 8B550C mov edx, dword ptr [ebp+0C]

:00402859 C6043A00 mov byte ptr [edx+edi], 00

:0040285D FF750C push [ebp+0C]

:00402860 E887920500 call 0045BAEC==》获取SN1的值到EAX是十六进制哦

:00402865 59 pop ecx

:00402866 8BF8 mov edi, eax==》sn1移到EDI,下面SN2的计算会用到

:00402868 33DB xor ebx, ebx==》清零

:0040286A 8B4508 mov eax, dword ptr [ebp+08]

:0040286D 8BF0 mov esi, eax ==》用户名转到esi寄存器

:0040286F EB09 jmp 0040287A

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

==》SN2算法真正的开始了

|:00402885(C)

|

:00402871 0FBE06 movsx eax, byte ptr [esi]==》ESI是你的用户名,依次取你的用户名

:00402874 F7EB imul ebx==》EAX与EBX相乘,(EBX起始值为0,是技术器)

:00402876 03F8 add edi, eax==》EAX与EDI固定值相加,存取EDI

:00402878 43 inc ebx==》计数器EBX加一

:00402879 46 inc esi==》ESI加一,取用于取用户名第二位

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

|:0040286F(U)

|

:0040287A FF7508 push [ebp+08]

:0040287D E892180500 call 00454114==》EAX赋值F(循环次数)

:00402882 59 pop ecx

:00402883 3BD8 cmp ebx, eax==》比较循环是否该结束

:00402885 7CEA jl 00402871==》不等就跳

:00402887 6A0A push 0000000A

:00402889 FF750C push [ebp+0C] 循环结束后,EDI的值,就是注册码的16

:0040288C 57 push edi 进制。

:0040288D E8B2AB0500 call 0045D444

:00402892 83C40C add esp, 0000000C

:00402895 8B450C mov eax, dword ptr [ebp+0C]

:00402898 5F pop edi

:00402899 5E pop esi

:0040289A 5B pop ebx

:0040289B 59 pop ecx

:0040289C 59 pop ecx

:0040289D 5D pop ebp

:0040289E C3 ret

注册码算法总结:

算法分两段:

1.SN1的计算是,用户名的1,3,5,7位与“PUZZLEVERO"的1,3,5,7位取异或。结果取前两位,并且位置互换。用户名位数不够用空格20代替。这个值作为下一段SN2的计算的基数。

2.用户名的第一位与计数器EBX(其实值为0)相乘,再与SN1相加,作为新的基数,如此循环16次,用户名位数不够用空格代替。

以我的用户名xx-fish为例(&符号后面代表的是所表示的进制):

sn1

1.x xor P=40&D 取前两位40再变成04

3.- xor Z=119&D 取前两位11再变成11

5.i xor L=37&D取前两位37再变成73

7.h xor V=62&D取前两位62再变成26

所以SN1就是04117326,再转换成16进制就是3ED34E&H

sn2

x imul 0=0,0 ADD SN1=3ED34E&H

x imul 1=78&H,78&H ADD 3ED34E&H=3ED3C6&H

- IMUL 2=5A&H,5A&H ADD 3ED3C6&H=3ED420&H

f IMUL 3=132&H,132&H ADD 3ED420&H=3ED552&H

i IMUL 4=1A4&H,1A4&H ADD 3ED552&H=3ED6F6&H

s IMUL 5=23f&H,23F&H ADD 3ED6F6&H=3ED935&H

h IMUL 6=270&H,270&H ADD 3ED935&H=3EDBA5&H

空格 IMUL 7=E0&H,E0H ADD 3EDBA5&H=3EDC85&H

空格 IMUL 8=100&H,100H ADD 3EDC85&H=3EDD85&H

(出处:赢政天下整理收藏)

相关文章:

·语音界面2.0算法分析及注册机源码!

·侠客系统修改器1.21破解手记--算法分析

·中文拨号上网计时计费器 V4.12注册算法分析

·ClockWise 3.22e注册码算法分析

·CoolClock V1.02注册算法分析

·Directory Scanner v1.5 注册算法分析

·Disk Chief 1.2 简单注册算法分析

·EffeTech HTTP Sniffer 3.2注册算法分析

·eLib2.01算法分析

·EZ MP3 Recorder 1.15 注册算法分析

相关软件:

→ 特别推荐

→ 热点TOP10

我为人人《《==》》人人为我

关于我们 |

帮助(?)

| 广告服务 |

版权声明 |

商业合作 |

发展历程 |

加盟我们 |

联系我们

Copyright © 1999-2003

winzheng.com All Rights Reserved.

繁体版:由华琦数码技术提供

Powered

by:MeSky.Net

2003-2004 年,宽带刚刚普及,下载站的文章区是许多人学电脑的第一课堂。
🕰 → 🤖 从那时到现在

当年一篇教程能让一台电脑焕然一新;今天的效率工具换成了 AI。 想知道当下最可靠的 AI 模型怎么选?看 赢政指数——我们用了 28 年的选软件严谨,现在用来评测大模型。

档案性质声明:本页为赢政天下(1998-2011)老文章的历史档案复原, 内容反映当年发表时的原貌——包括当年的技术表述、软件版本与观点,部分方法在今天已不适用或不合规,仅作互联网历史记录与研究用途, 不提供任何形式的下载。原始数据经由公共网络存档(Internet Archive)复原。发现问题请联系我们
← 返回老文章档案 · 软件史档案馆 · 赢政天下站史