Revival 的算法跟踪, yqmjch兄弟的一个题目
软件名称: revive3.1
软件大小: 1079 KB
软件语言: 国外软件
软件类别: 国外软件 / 共享版 /
应用平台: Win9x/NT/2000/XP
破解工具: olldbg-cn v1.09
【作者声明】:初学Crack,只是感兴趣,没有其它目的。可能我的描述有不到之处,请大家指正
程序是vc++编的,没有壳.在0lldbg中下getwindowtexta中断就能到核心.前面部分就不写了.
加载后用户名和单位名软件填好了,就填试验码 789456123012 .运行中断后不久就到:
****************************************************************
004032A0 SUB ESP, 24
004032A3 PUSH EBX
004032A4 PUSH ESI
004032A5 MOV ESI, DWORD PTR SS:[ESP+30] ; ESI<== 0093292C,(ASCII "789456123012")
004032A9 PUSH EDI
004032AA MOVSX EAX, BYTE PTR DS:[ESI] ; EAX <==DS:[0093292C]=37 ('7')
004032AD PUSH EAX
004032AE CALL Revival.0041F880 ; 这个CALL把hex值-20
004032B3 ADD ESP, 4
004032B6 CMP EAX, 52 ; 比较第一位是不是52+20=72 ('r')
004032B9 JNZ Revival.0040340F ; 注册码的第二个条件:注册码的第一位是('r'), 把第一位改为r再试
004032BF MOVSX EAX, BYTE PTR DS:[ESI+1] ; EAX <== DS:[0093292D] = 61 ('a')
004032C3 PUSH EAX
004032C4 CALL Revival.0041F880 ; 这个CALL把hex值-20
004032C9 ADD ESP, 4
004032CC CMP EAX, 56 ; 注册码的第3个条件:注册码的第一位是56+20=76 ('v'), 把第2位改为v再试
004032CF JNZ Revival.0040340F
----------------------
CALL Revival.0041F880
|
|
0041F880 CMP DWORD PTR DS:[45DC20], 0
0041F887 PUSH ESI
0041F888 PUSH EDI
0041F889 JNZ SHORT Revival.0041F89F
0041F88B MOV EAX, DWORD PTR SS:[ESP+C] ; 这一段是比较注册码第一位的取值范围hex=61-7A (小写字母)
0041F88F CMP EAX, 61 ; 注册码的第一个条件(把试验码改为asdfghjklzxcvbnm后继续)
0041F892 JL SHORT Revival.0041F8EB
0041F894 CMP EAX, 7A
0041F897 JG SHORT Revival.0041F8EB
0041F899 SUB EAX, 20 ; EAX =61-20=41
0041F89C POP EDI
0041F89D POP ESI ; ESI <== 0093266C,(ASCII"asdfghjklzxcvbnm")
0041F89E RETN
*********************************************
下面继续分析:
004032D5 CMP BYTE PTR DS:[ESI+7], 2D ; 注册码的第4个条件:注册码的第8位2d ('-a'), 把第8位改为-再试
004032D9 JNZ Revival.0040340F
004032DF PUSH ESI ; /ESI = 0093266C,(ASCII "rvasdfg-jklzxcv")
004032E0 CALL DWORD PTR DS:[<&kernel32.lstr>; \lstrlenA
004032E6 CMP EAX, 0F ; EAX = 0F (注册码的长度=15位),条件5
004032E9 JNZ Revival.0040340F
004032EF MOV EDI, 2 ; EDI=2 (下面从第三位计算起)
004032F4 /MOVSX EAX, BYTE PTR DS:[ESI+EDI] ; EAX <== DS:[0093266E]=61 ('a')
004032F8 |PUSH EAX
004032F9 |CALL Revival.0041F810 ; 比较条件CALL
004032FE |ADD ESP, 4
00403301 |TEST EAX, EAX
00403303 |JE Revival.004033F4
00403309 |INC EDI
0040330A |CMP EDI, 7
0040330D \JL SHORT Revival.004032F4
0040330F MOV EDI, 8
00403314 /MOVSX EAX, BYTE PTR DS:[ESI+EDI]
00403318 |PUSH EAX
00403319 |CALL Revival.0041F810
0040331E |ADD ESP, 4
00403321 |TEST EAX, EAX
00403323 |JE Revival.004033FD
00403329 |INC EDI
0040332A |CMP EDI, 0F
0040332D \JL SHORT Revival.00403314
-----------------------------------------------------
CALL Revival.0041F810
|
|
0041F810 CMP DWORD PTR DS:[45D9DC], 1
0041F817 JLE SHORT Revival.0041F829 ;这里一定跳
0041F819 MOV ECX, DWORD PTR SS:[ESP+4] |
0041F81D PUSH 4 |
0041F81F PUSH ECX |
0041F820 CALL Revival.00423610 |
0041F825 ADD ESP, 8 \|/
0041F828 RETN .
0041F829 MOV EDX, DWORD PTR DS:[45D7D0] ; Revival.0045D7DA (寻址的基址)
0041F82F XOR EAX, EAX
0041F831 MOV ECX, DWORD PTR SS:[ESP+4] ; ECX <== SS:[0012F500]=61 ('a')
0041F835 MOV AX, WORD PTR DS:[EDX+ECX*2] ; 用ECX的值做指针,来寻址.计算方法=基址+各位hex*2
0041F839 AND EAX, 4 ; EAX =EAX AND 4 寻址得到的值再计算
0041F83C RETN ; 条件6--EAX AND 4 不等于0 ,就正确.
++++++++++++++++++++++++++++++++++++++++++++++++++++++
这是内存中数组的值:
0045D7DA ==> 20 00 20 00 20 00 .. . . .
0045D7E0 20 00 20 00 20 00 20 00 . . . .
0045D7E8 20 00 20 00 28 00 28 00 . .(.(.
0045D7F0 28 00 28 00 28 00 20 00 (.(.(. .
0045D7F8 20 00 20 00 20 00 20 00 . . . .
0045D800 20 00 20 00 20 00 20 00 . . . .
0045D808 20 00 20 00 20 00 20 00 . . . .
0045D810 20 00 20 00 20 00 20 00 . . . .
0045D818 20 00 48 00 10 00 10 00 .H...
0045D820 10 00 10 00 10 00 10 00 ....
0045D828 10 00 10 00 10 00 10 00 ....
0045D830 10 00 10 00 10 00 10 00 ....
0045D838 10 00 84 00 84 00 84 00 .??? ;经过分析发现内存中的值只有84 AND 4 不等于0
0045D840 84 00 84 00 84 00 84 00 ???? //84的偏移量=45D83A-45D7DA=60H++2 ==>6AH
0045D848 84 00 84 00 84 00 10 00 ???. //那么第三位值应该=60/2=30 ('0')++ ==>39 ('9')
0045D850 10 00 10 00 10 00 10 00 .... ;上面的计算告诉我们从第三位开始取值的范围(0-9)
0045D858 10 00 10 00 81 00 81 00 ..?? //把试验码改为:rv01234-5678901 后继续
0045D860 81 00 81 00 81 00 81 00 ????
0045D868 01 00 01 00 01 00 01 00 ....
0045D870 01 00 01 00 01 00 01 00 ....
0045D878 01 00 01 00 01 00 01 00 ....
0045D880 01 00 01 00 01 00 01 00 ....
0045D888 01 00 01 00 01 00 01 00 ....
0045D890 10 00 10 00 10 00 10 00 ....
0045D898 10 00 10 00 82 00 82 00 ..??
0045D8A0 82 00 82 00 82 00 82 00 ????
0045D8A8 02 00 02 00 02 00 02 00 ....
0045D8B0 02 00 02 00 02 00 02 00 ....
0045D8B8 02 00 02 00 02 00 02 00 ....
0045D8C0 02 00 02 00 02 00 02 00 ....
0045D8C8 02 00 02 00 02 00 02 00 ....
0045D8D0 10 00 10 00 10 00 10 00 ....
=======================================================================================
下面继续我们的
0040332F MOV AX, WORD PTR DS:[ESI+2] ; AX <==DS:[ESI+2](取二位)=DS:[0093266E]=3130 ('01')
00403333 MOV WORD PTR SS:[ESP+10], AX ; AX ==>SS:[0012F514]
00403338 LEA EAX, DWORD PTR SS:[ESP+10]
0040333C MOV BYTE PTR SS:[ESP+12], 0
00403341 PUSH EAX ; EAX =0012F514,(ASCII "01") 第三 四位
00403342 CALL Revival.0041F800 *********第一次调用
------------------------
CALL Revival.0041F800
|
|
0041F800 MOV EAX, DWORD PTR SS:[ESP+4]
0041F804 PUSH EAX ; EAX =0012F514,(ASCII "01") 第三 四位
0041F805 CALL Revival.0041F750 ; 计算的CALL
0041F80A ADD ESP, 4
0041F80D RETN
-----------------------
CALL Revival.0041F750
|
|
0041F750 PUSH EBX
0041F751 PUSH ESI
0041F752 MOV ESI, DWORD PTR SS:[ESP+C] ; ESI =0012F514,(ASCII "01") 第三 四位
0041F756 PUSH EDI
0041F757 PUSH EBP
0041F758 MOV EDI, 1 ; EDI=1
0041F75D /CMP DWORD PTR DS:[45D9DC], EDI
0041F763 |JLE SHORT Revival.0041F776
0041F765 |PUSH 8
0041F767 |XOR EAX, EAX
0041F769 |MOV AL, BYTE PTR DS:[ESI]
0041F76B |PUSH EAX
0041F76C |CALL Revival.00423610
0041F771 |ADD ESP, 8
0041F774 |JMP SHORT Revival.0041F789
0041F776 |XOR EDX, EDX
0041F778 |MOV ECX, DWORD PTR DS:[45D7D0] ; ECX <== DS:[0045D7D0] (参数的基地址)
0041F77E |MOV DL, BYTE PTR DS:[ESI] ; DL <== DS:[0012F514]=30 ('0')
0041F780 |XOR EAX, EAX
0041F782 |MOV AX, WORD PTR DS:[ECX+EDX*2] ; 用DL值做寻值的指针,偏移量=DL*2
0041F786 |AND EAX, 8 ; 计算方法
0041F789 |TEST EAX, EAX ; 注册码的判断条件,即DL*2偏移处的值AND 8 不能等于0
0041F78B |JE SHORT Revival.0041F790 ; 条件不成立就跳
0041F78D |INC ESI
0041F78E \JMP SHORT Revival.0041F75D
++++++++++++++++++++++++++++++++++++++++++++++++++++++
这是内存中数组的值:
0045D7D0 DA D7 45 00 DA D7 45 00 谧E.谧E.
0045D7D8 00 00 20 00 20 00 20 00 .. . . .
0045D7E0 20 00 20 00 20 00 20 00 . . . .
0045D7E8 20 00 20 00 28 00 28 00 . .(.(.
0045D7F0 28 00 28 00 28 00 20 00 (.(.(. .
0045D7F8 20 00 20 00 20 00 20 00 . . . .
0045D800 20 00 20 00 20 00 20 00 . . . .
0045D808 20 00 20 00 20 00 20 00 . . . .
0045D810 20 00 20 00 20 00 20 00 . . . .
0045D818 20 00 48 00 10 00 10 00 .H...
0045D820 10 00 10 00 10 00 10 00 ....
0045D828 10 00 10 00 10 00 10 00 ....
0045D830 10 00 10 00 10 00 10 00 ....
0045D838 10 00 84 00 84 00 84 00 .??? ;由于偏移量最小是从45D83A开始的.
0045D840 84 00 84 00 84 00 84 00 ???? ;分析下面的各个值没有符合条件的.
0045D848 84 00 84 00 84 00 10 00 ???.
0045D850 10 00 10 00 10 00 10 00 ....
0045D858 10 00 10 00 81 00 81 00 ..??
0045D860 81 00 81 00 81 00 81 00 ????
0045D868 01 00 01 00 01 00 01 00 ....
0045D870 01 00 01 00 01 00 01 00 ....
0045D878 01 00 01 00 01 00 01 00 ....
0045D880 01 00 01 00 01 00 01 00 ....
0045D888 01 00 01 00 01 00 01 00 ....
0045D890 10 00 10 00 10 00 10 00 ....
0045D898 10 00 10 00 82 00 82 00 ..??
0045D8A0 82 00 82 00 82 00 82 00 ????
0045D8A8 02 00 02 00 02 00 02 00 ....
0045D8B0 02 00 02 00 02 00 02 00 ....
0045D8B8 02 00 02 00 02 00 02 00 ....
0045D8C0 02 00 02 00 02 00 02 00 ....
0045D8C8 02 00 02 00 02 00 02 00 ....
0045D8D0 10 00 10 00 10 00 10 00 ....
0045D8D8 20 00 00 00 00 00 00 00 .......
--------------
这一段只是为下面服务的
==============================================
继续:
-----
|
|
0041F790 XOR EBX, EBX
0041F792 MOV BL, BYTE PTR DS:[ESI] ; BL <== DS:[0012F514]=30 ('0') || =33 ||=37
0041F794 INC ESI ; ESI ++
0041F795 MOV EDI, EBX ; EDI <== 30
0041F797 CMP EBX, 2D
0041F79A JE SHORT Revival.0041F7A1
0041F79C CMP EBX, 2B
0041F79F JNZ SHORT Revival.0041F7A6
0041F7A1 XOR EBX, EBX
0041F7A3 MOV BL, BYTE PTR DS:[ESI]
0041F7A5 INC ESI
0041F7A6 XOR EBP, EBP
0041F7A8 /CMP DWORD PTR DS:[45D9DC], 1 ; DS:[45D9DC]=01
0041F7AF |JLE SHORT Revival.0041F7BE
0041F7B1 |PUSH 4
0041F7B3 |PUSH EBX
0041F7B4 |CALL Revival.00423610
0041F7B9 |ADD ESP, 8
0041F7BC |JMP SHORT Revival.0041F7CD
0041F7BE |MOV ECX, DWORD PTR DS:[45D7D0] ; 如果上面的条件都不成立,就跳到这里 ECX <== DS:[00457D0] (基地址)
0041F7C4 |XOR EAX, EAX
0041F7C6 |MOV AX, WORD PTR DS:[ECX+EBX*2] ; EBX =30 还是用第三位的hex值来做指针寻址
0041F7CA |AND EAX, 4 ; 计算方法
0041F7CD |TEST EAX, EAX ; 注册码的判断条件,即DL*2偏移处的值AND 4 不能等于0
0041F7CF |JE SHORT Revival.0041F7E1
0041F7D1 |LEA EAX, DWORD PTR SS:[EBP+EBP*4] ; EBP=0 ,第二次它就是把试验码*5==>EAX中,这个值有用
0041F7D5 |INC ESI ; //EAX =0 ;EAX =HEX*5
0041F7D6 |LEA EBP, DWORD PTR DS:[EBX+EAX*2->; EBP <== 01 |<==03 这个计算是把十六进制转化为ASCII值,因为EAX=0||第二次计算的时候
0041F7DA |XOR EBX, EBX ; //就是把后一位的hex+前一位值*A-30
0041F7DC |MOV BL, BYTE PTR DS:[ESI-1] ; BL <== DS:[0012F515]=31 ('1')
0041F7DF \JMP SHORT Revival.0041F7A8
0041F7E1 MOV EAX, EBP ; EAX <==EBP (经过上面计算的值) ||(78901) =13435|||(56)=38
0041F7E3 CMP EDI, 2D
0041F7E6 JNZ SHORT Revival.0041F7EF
0041F7E8 NEG EAX
0041F7EA POP EBP
0041F7EB POP EDI
0041F7EC POP ESI
0041F7ED POP EBX
0041F7EE RETN
-----------------
这一段要分析一下: 下面要的四个关键值的计算
1.第一次用试验码的第三位,第四位进行如下计算:后一位值+前一位值*A 例如:(01)==>1+0*A=01
2.第二次用试验码的第六位,第七位进行相同计算:后一位值+前一位值*A 例如:(34)==>4+3*A=22
3.第三次用试验码的最后五位进行如下计算:前一位值*A+后一位值 ,然后把前面的值*A+后一位的值
例如(78901)==>1+(0+(9+(8+7*a)*a)*a)*a=13435
4.第四次用试验码的第九位,第十位进行如下计算:前一位值*A+后一位值 例如:(56)==>6+5*A=38
======================================================================================
00403347 MOV CX, WORD PTR DS:[ESI+5] ; CX = 3433 ("34")
0040334B ADD ESP, 4
0040334E MOV WORD PTR SS:[ESP+10], CX ; CX ==>SS:[0012F514]
00403353 SUB AL, 13 ; AL =01 SUB 13=EE |这里把第一组值-13
00403355 LEA ECX, DWORD PTR SS:[ESP+10] ; ECX <==0012F514, (ASCII "34")
00403359 MOV BYTE PTR SS:[ESP+C], AL ; AL =EE ==>SS:[0012F510] |第一组的值保存在这里
0040335D MOV BYTE PTR SS:[ESP+12], 0
00403362 PUSH ECX
00403363 CALL Revival.0041F800 *********第二次调用
00403368 LEA EDX, DWORD PTR SS:[ESP+14] ; EDX <== 0012F514,(ASCII "34")
0040336C ADD ESP, 4
0040336F LEA EBX, DWORD PTR DS:[EAX-25] ; EBX <== EAX(上面CALL计算的值)-25=FFFFFFFD |第二组计算的值-25
00403372 LEA ECX, DWORD PTR DS:[ESI+A] ; ECX <== DS:[ESI+A]=00932676,(ASCII "78901"). 试验码的后五位
00403375 PUSH EDX ; EDX =34
00403376 MOV EAX, DWORD PTR DS:[ECX] ; EAX <== DS:[00932676]=30393837
00403378 MOV DWORD PTR DS:[EDX], EAX ; DS:[0012F514] <== 03393837
0040337A MOV CL, BYTE PTR DS:[ECX+4] ; CL <== DS:[ECX+4]=31 ('1') 试验码的最后一位
0040337D MOV BYTE PTR DS:[EDX+4], CL ; 第五位也转移过来
00403380 MOV BYTE PTR SS:[ESP+19], 0
00403385 CALL Revival.0041F800 *********第三次调用
0040338A ADD ESP, 4
0040338D MOV EDI, EAX ; EDI <==13435 (后五位经过上面计算的值)
0040338F XOR DI, 5468 ; DI=3435 XOR 5468=605D (只取这个值的后四位计算)
00403394 MOV AX, WORD PTR DS:[ESI+8] ; AX <== DS:[00932674]=3635 ("56") ,试验码的第九第十位
00403398 MOV WORD PTR SS:[ESP+10], AX
0040339D LEA EAX, DWORD PTR SS:[ESP+10] ; EAX <== SS:[ESP+10]=0012F514,(ASCII "56901")
004033A1 MOV BYTE PTR SS:[ESP+12], 0
004033A6 MOVZX EDI, DI ; EDI<==605D
004033A9 PUSH EAX
004033AA CALL Revival.0041F800 *********第四次调用
004033AF MOV BYTE PTR SS:[ESP+14], AL ; SS:[0012F514]=38 ,第四次的值
004033B3 ADD ESP, 4
004033B6 XOR EAX, EAX
004033B8 MOV ECX, 64 ; ECX =64 <--参数
004033BD MOV AL, BL ; AL =FD ,第二次的值
004033BF MOV EBX, 0A ; EBX <=0A <--参数
004033C4 LEA EAX, DWORD PTR DS:[EAX+EDI+3] ; EAX <==FD+6150D+3 ,第三次的值
004033C8 CDQ
004033C9 IDIV ECX ; ECX = 64 IDIV EAX = 615D ==>EAX =F9 EDX=19
004033CB MOV CL, DL ; CL <== 19
004033CD XOR EAX, EAX
004033CF MOV AL, BYTE PTR SS:[ESP+C] ; AL <== SS:[0012F510]=EE ,第一次的值
004033D3 LEA EAX, DWORD PTR DS:[EAX+EDI+3] ; EAX =EE+605D+3= 614E
004033D7 CDQ
004033D8 IDIV EBX ; EAX =614E IDIV EBX=A ==>EAX=9BB EDX=000
004033DA SUB DL, BYTE PTR DS:[ESI+4] ; DL =DL-32 ('2') ,试验码的第五位
004033DD CMP DL, 0D0 ; DL =CE
004033E0 JNZ SHORT Revival.00403406 ; 注册码的正确条件7
004033E2 CMP CL, BYTE PTR SS:[ESP+10] ; CL = 19 SS:[ESP+10] =SS:[0012F514]=38
004033E6 JNZ SHORT Revival.00403406 ; 注册码的正确条件8
004033E8 MOV EAX, 1
004033ED POP EDI
004033EE POP ESI
004033EF POP EBX
004033F0 ADD ESP, 24
004033F3 RETN
#####################################################################################
以上算法分析已经完成,下面来总结注册码的计算方法: 注册码的长度=15位
1.首先看注册码的前二位比较容易固定值rv
2.注册码的第八位是 2D('-')
3.注册码的其他几位必须是数字
4.其他几位正确的条件:设第一次计算的值为M ,第二次的值为N ,第三次值的后四位为J ,第四次计算的值为K
1).(M+(J XOR 5468)+3) MOD A + D0 = 注册码的第五位
2).(N+(J XOR 5468)+3) MOD 64 = k
5.假如我们知道M N J K
这样注册码的这几位可以知道假设了: rv01?34-??78901
6.为了使上式成立,我们做如下分析:
从 K 分析: 设K=19 ,第九位为T1 ,第十位为T2
则:T2=19-T1*A >=0 ; T1 的取值范围只能是 2 那么 T2 =19-2*A=5
这样把注册码设成:rv01???-2578901
现在来分析一下它对第一个条件能不能成立:
1).(M+(J XOR 5468)+3) MOD A = 注册码的第五位
上式改为注册码的第五位=6145 MOD A =0
把注册码改为:rv01034-2578901
几点说明:
1.这个软件的注册码如果不进行假设的话,可能很难知道结果.
2.SUB DL, BYTE PTR DS:[ESI+4] ; DL =DL-32 ('2') ,试验码的第五位
(M+(J XOR 5468)+3) MOD A = 注册码的第五位,这个我是怎么知道的
原来 MOD A 得到的值是<A -30以上的值是负数,我无法用计算器计算,只好用sice的计算功能才
知道0-30=D0 ,因此上面式子就是:
SUB DL, BYTE PTR DS:[ESI+4]
CMP DL, 0D0
JNZ SHORT Revival.00403406 <== 不能跳
成立的描述.
3.以上算法得到的注册码,能注册成功,但是重新启动时不能通过,请老师们斧正
fxyang
2003.3.1
相关视频
相关阅读 Windows错误代码大全 Windows错误代码查询激活windows有什么用Mac QQ和Windows QQ聊天记录怎么合并 Mac QQ和Windows QQ聊天记录Windows 10自动更新怎么关闭 如何关闭Windows 10自动更新windows 10 rs4快速预览版17017下载错误问题Win10秋季创意者更新16291更新了什么 win10 16291更新内容windows10秋季创意者更新时间 windows10秋季创意者更新内容kb3150513补丁更新了什么 Windows 10补丁kb3150513是什么
热门文章 去除winrar注册框方法
最新文章
比特币病毒怎么破解 比去除winrar注册框方法
华为无线路由器HG522-C破解教程(附超级密码JEB格式文件京东电子书下载和阅读限制破解教UltraISO注册码全集(最新)通过Access破解MSSQL获得数据
人气排行 华为无线路由器HG522-C破解教程(附超级密码JEB格式文件京东电子书下载和阅读限制破解教UltraISO注册码全集(最新)qq相册密码破解方法去除winrar注册框方法(适应任何版本)怎么用手机破解收费游戏华为无线猫HG522破解如何给软件脱壳基础教程
查看所有0条评论>>