• 标 题:屏幕录像专家 V3.0 算法分析 (13千字)
  • 作 者:PaulYoung[CCG]
  • 时 间:2003-4-8 21:20:22
  • 链 接:http://bbs.pediy.com

屏幕录像专家 V3.0 算法分析

作者:PaulYoung[CCG]
软件下载:http://www.tlxsoft.com/
破解工具:SoftICE
破解时间:2003-4-8
***********************************************************************************************

  你一定可以来到这里……  ^_^

:0041B862 8D45F8                  lea eax, dword ptr [ebp-08]
:0041B865 E8B68FFEFF              call 00404820
:0041B86A 50                      push eax
:0041B86B 8D9580FBFFFF            lea edx, dword ptr [ebp+FFFFFB80]
:0041B871 52                      push edx
:0041B872 E84D0C0700              call 0048C4C4
:0041B877 83C408                  add esp, 00000008
:0041B87A FF4DBC                  dec [ebp-44]
:0041B87D 8D45F8                  lea eax, dword ptr [ebp-08]
:0041B880 BA02000000              mov edx, 00000002
:0041B885 E886C00700              call 00497910
:0041B88A 8D8D80FBFFFF            lea ecx, dword ptr [ebp+FFFFFB80]
:0041B890 51                      push ecx
:0041B891 E85E0C0700              call 0048C4F4
:0041B896 59                      pop ecx
:0041B897 89458C                  mov dword ptr [ebp-74], eax
:0041B89A C745889CFFFFFF          mov [ebp-78], FFFFFF9C          //[ebp-78]=0xFFFFFF9C
:0041B8A1 33C0                    xor eax, eax
:0041B8A3 894590                  mov dword ptr [ebp-70], eax
:0041B8A6 8B5590                  mov edx, dword ptr [ebp-70]
:0041B8A9 3B558C                  cmp edx, dword ptr [ebp-74]
:0041B8AC 7D20                    jge 0041B8CE

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0041B8CC(C)
|
:0041B8AE 8B4D90                  mov ecx, dword ptr [ebp-70]
:0041B8B1 8A840D80FBFFFF          mov al, byte ptr [ebp+ecx-00000480]
:0041B8B8 884597                  mov byte ptr [ebp-69], al
:0041B8BB 33D2                    xor edx, edx
:0041B8BD 8A5597                  mov dl, byte ptr [ebp-69]
:0041B8C0 015588                  add dword ptr [ebp-78], edx      //0xFFFFFF9C 与用户名每个字符累加求和
:0041B8C3 FF4590                  inc [ebp-70]
:0041B8C6 8B4D90                  mov ecx, dword ptr [ebp-70]
:0041B8C9 3B4D8C                  cmp ecx, dword ptr [ebp-74]
:0041B8CC 7CE0                    jl 0041B8AE

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0041B8AC(C)
|
:0041B8CE 8B4588                  mov eax, dword ptr [ebp-78]
:0041B8D1 898578F7FFFF            mov dword ptr [ebp+FFFFF778], eax
:0041B8D7 33D2                    xor edx, edx
:0041B8D9 89957CF7FFFF            mov dword ptr [ebp+FFFFF77C], edx
:0041B8DF DFAD78F7FFFF            fild qword ptr [ebp+FFFFF778]      //累加和结果送 st(0)
:0041B8E5 DB2D5CBD4100            fld tbyte ptr [0041BD5C]  //st(1)=0.6480041472265422897
:0041B8EB DEC9                    fmulp st(1), st(0)                  //st(1)=st(0)*st(1)
:0041B8ED D80568BD4100            fadd dword ptr [0041BD68]  //加上1233.99999999999999957
:0041B8F3 E8F84F0700              call 004908F0                      //取结果的整数
:0041B8F8 894588                  mov dword ptr [ebp-78], eax
:0041B8FB 8B5588                  mov edx, dword ptr [ebp-78]
:0041B8FE 899578F7FFFF            mov dword ptr [ebp+FFFFF778], edx
:0041B904 33C9                    xor ecx, ecx
:0041B906 898D7CF7FFFF            mov dword ptr [ebp+FFFFF77C], ecx
:0041B90C DFAD78F7FFFF            fild qword ptr [ebp+FFFFF778]
:0041B912 DC0D6CBD4100            fmul qword ptr [0041BD6C]
//上面的整数*3121.14159259999996697388632872504
:0041B918 E8D34F0700              call 004908F0                        //取结果的整数
:0041B91D 894588                  mov dword ptr [ebp-78], eax          //保存到[ebp-78]
:0041B920 66C745B02C00            mov [ebp-50], 002C
:0041B926 8D45F4                  lea eax, dword ptr [ebp-0C]
:0041B929 E8065EFEFF              call 00401734
:0041B92E 8BD0                    mov edx, eax
:0041B930 FF45BC                  inc [ebp-44]
:0041B933 8B4D9C                  mov ecx, dword ptr [ebp-64]
:0041B936 8B81E4020000            mov eax, dword ptr [ecx+000002E4]
:0041B93C E84B150400              call 0045CE8C
:0041B941 8D45F4                  lea eax, dword ptr [ebp-0C]
:0041B944 E8D78EFEFF              call 00404820
:0041B949 50                      push eax
:0041B94A 8D9580FBFFFF            lea edx, dword ptr [ebp+FFFFFB80]
:0041B950 52                      push edx
:0041B951 E86E0B0700              call 0048C4C4
:0041B956 83C408                  add esp, 00000008
:0041B959 FF4DBC                  dec [ebp-44]
:0041B95C 8D45F4                  lea eax, dword ptr [ebp-0C]
:0041B95F BA02000000              mov edx, 00000002
:0041B964 E8A7BF0700              call 00497910
:0041B969 8D8D80FBFFFF            lea ecx, dword ptr [ebp+FFFFFB80]
:0041B96F 51                      push ecx
:0041B970 E87F0B0700              call 0048C4F4
:0041B975 59                      pop ecx
:0041B976 89458C                  mov dword ptr [ebp-74], eax
:0041B979 33C0                    xor eax, eax
:0041B97B 894590                  mov dword ptr [ebp-70], eax        //[ebp-70]=eax=0
:0041B97E 8B5590                  mov edx, dword ptr [ebp-70]
:0041B981 3B558C                  cmp edx, dword ptr [ebp-74]
:0041B984 7D46                    jge 0041B9CC

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0041B9CA(C)
|
:0041B986 8B4590                  mov eax, dword ptr [ebp-70]          //[ebp-70]依次等于 0,1,2,3...
:0041B989 B903000000              mov ecx, 00000003
:0041B98E 99                      cdq
:0041B98F F7F9                    idiv ecx                            //[ebp-70]/3,商送 al
:0041B991 8B5590                  mov edx, dword ptr [ebp-70]
:0041B994 8A8C1580FBFFFF          mov cl, byte ptr [ebp+edx-00000480]  //依次取注册码各个字符
:0041B99B 80C1EC                  add cl, EC                          //字符+0xFFFFFFEC
:0041B99E 8B5590                  mov edx, dword ptr [ebp-70]          //[ebp-70]=edx
:0041B9A1 81E201000080            and edx, 80000001  //取奇数位字符则edx=0,取偶数位字符则edx=1
:0041B9A7 7905                    jns 0041B9AE
:0041B9A9 4A                      dec edx
:0041B9AA 83CAFE                  or edx, FFFFFFFE
:0041B9AD 42                      inc edx

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0041B9A7(C)
|
:0041B9AE 03D2                    add edx, edx
:0041B9B0 8D1492                  lea edx, dword ptr [edx+4*edx] //奇数位字符则dl=0,偶数位字符则 dl=0xA
:0041B9B3 2ACA                    sub cl, dl  //cl=cl-dl(即计算奇数位字符时-0,计算偶数位字符时-0xA)
:0041B9B5 02C1                    add al, cl  //al=al+cl(al 就是[ebp-70]/3的商)
:0041B9B7 8B4D90                  mov ecx, dword ptr [ebp-70]
:0041B9BA 88840D80FBFFFF          mov byte ptr [ebp+ecx-00000480], al
:0041B9C1 FF4590                  inc [ebp-70]                      //[ebp-70]递增1
:0041B9C4 8B4590                  mov eax, dword ptr [ebp-70]
:0041B9C7 3B458C                  cmp eax, dword ptr [ebp-74]
:0041B9CA 7CBA                    jl 0041B986        //循环并分别用注册码各个字符计算出一串数值

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:0041B984(C)
|
:0041B9CC 8D8580FBFFFF            lea eax, dword ptr [ebp+FFFFFB80]
:0041B9D2 50                      push eax
:0041B9D3 8D9580F7FFFF            lea edx, dword ptr [ebp+FFFFF780]
:0041B9D9 52                      push edx
:0041B9DA E8E50A0700              call 0048C4C4
:0041B9DF 83C408                  add esp, 00000008
:0041B9E2 66C745B03800            mov [ebp-50], 0038
:0041B9E8 8D9580F7FFFF            lea edx, dword ptr [ebp+FFFFF780]
:0041B9EE 8D45F0                  lea eax, dword ptr [ebp-10]
:0041B9F1 E8B2BD0700              call 004977A8
:0041B9F6 8BD0                    mov edx, eax
:0041B9F8 FF45BC                  inc [ebp-44]
:0041B9FB 8D45FC                  lea eax, dword ptr [ebp-04]
:0041B9FE E83DBF0700              call 00497940
:0041BA03 FF4DBC                  dec [ebp-44]
:0041BA06 8D45F0                  lea eax, dword ptr [ebp-10]
:0041BA09 BA02000000              mov edx, 00000002
:0041BA0E E8FDBE0700              call 00497910
:0041BA13 8D45FC                  lea eax, dword ptr [ebp-04]
:0041BA16 E8F5C00700              call 00497B10  //验证注册码的“合法性”并计算出一个值送 eax ,跟入……

  从0041BA16 → 00497B38 → 00482057,来到……

:0048903C 53                      push ebx
:0048903D 56                      push esi
:0048903E 57                      push edi
:0048903F 89C6                    mov esi, eax
:00489041 50                      push eax
:00489042 85C0                    test eax, eax
:00489044 7473                    je 004890B9
:00489046 31C0                    xor eax, eax
:00489048 31DB                    xor ebx, ebx
:0048904A BFCCCCCC0C              mov edi, 0CCCCCCC

下面是逐个验证注册码各个字符计算出的数值的“合法性”,实际上间接验证了输入注册码的“合法性”。

* Referenced by a (U)nconditional or (C)onditional Jump at Address:
|:00489055(C)
|
:0048904F 8A1E                    mov bl, byte ptr [esi]
:00489051 46                      inc esi
:00489052 80FB20                  cmp bl, 20
:00489055 74F8                    je 0048904F
:00489057 B500                    mov ch, 00
:00489059 80FB2D                  cmp bl, 2D
:0048905C 7469                    je 004890C7
:0048905E 80FB2B                  cmp bl, 2B
:00489061 7466                    je 004890C9
:00489063 80FB24                  cmp bl, 24
:00489066 7466                    je 004890CE
:00489068 80FB78                  cmp bl, 78
:0048906B 7461                    je 004890CE
:0048906D 80FB58                  cmp bl, 58
:00489070 745C                    je 004890CE
:00489072 80FB30                  cmp bl, 30
:00489075 7513                    jne 0048908A
:00489077 8A1E                    mov bl, byte ptr [esi]
:00489079 46                      inc esi
:0048907A 80FB78                  cmp bl, 78
:0048907D 744F                    je 004890CE
:0048907F 80FB58                  cmp bl, 58
:00489082 744A                    je 004890CE
:00489084 84DB                    test bl, bl
:00489086 7420                    je 004890A8
:00489088 EB04                    jmp 0048908E

* Referenced by a (U)nconditional or (C)onditional Jump at Addresses:
|:00489075(C), :004890CC(U)
|
:0048908A 84DB                    test bl, bl
:0048908C 7434                    je 004890C2

* Referenced by a (U)nconditional or (C)onditional Jump at Addresses:
|:00489088(U), :004890A6(C)
|
:0048908E 80EB30                  sub bl, 30
:00489091 80FB09                  cmp bl, 09    //关键,从中我们可以推算出各位注册码的取值范围
:00489094 772C                    ja 004890C2    //跳???不要!!!
:00489096 39F8                    cmp eax, edi
:00489098 7728                    ja 004890C2
:0048909A 8D0480                  lea eax, dword ptr [eax+4*eax]
:0048909D 01C0                    add eax, eax
:0048909F 01D8                    add eax, ebx  //每次 "bl-30" 的值组成串再转换成数值
:004890A1 8A1E                    mov bl, byte ptr [esi]
:004890A3 46                      inc esi
:004890A4 84DB                    test bl, bl
:004890A6 75E6                    jne 0048908E

  计算完毕,回到……

:0041BA1B B97C000000              mov ecx, 0000007C
:0041BA20 99                      cdq
:0041BA21 F7F9                    idiv ecx
:0041BA23 83C064                  add eax, 00000064
:0041BA26 894584                  mov dword ptr [ebp-7C], eax
:0041BA29 8B4584                  mov eax, dword ptr [ebp-7C]  //eax=eax/0x7C+0x64
:0041BA2C 2B4588                  sub eax, dword ptr [ebp-78]  //eax-用户名计算出的值
:0041BA2F 83F864                  cmp eax, 00000064       //等于 0x64 则注册成功
:0041BA32 0F85BC020000            jne 0041BCF4



****************************

  实例分析:
  以用户名 PaulYoung 为例,

用户名计算:
0xFFFFFF9C+0x50+0x61+0x75+0x6C+0x59+0x6F0x75+0x6E+0x67=0x340=832
832*0.6480041472265422897+1233.99999999999999957结果的整数为1773
1773*3121.14159259999996697388632872504结果的整数为0x547058

注册码计算:
假设某位注册码字符为 S ,则
奇数位计算:S+0xFFFFFFEC+(x/3 的商)  (x 依次等于0,1,2,3...)
偶数位计算:S+0xFFFFFFEC-0xA+(x/3 的商)

而从
:0048908E 80EB30                  sub bl, 30
:00489091 80FB09                  cmp bl, 09
:00489094 772C                    ja 004890C2

我们可以看到,奇数位及偶数位注册码取值范围分别是:
奇数位范围:0x30≤S+0xFFFFFFEC+(x/3)≤0x39
偶数位范围:0x30≤S+0xFFFFFFEC-0xA+(x/3)≤0x39
由此我们可以推算出注册码的“合法”取值范围,分别是:
第一位:D,E,F,G,H,I,J,K,L,M
第二位:N,O,P,Q,R,S,T,U,V,W
第三位:D,E,F,G,H,I,J,K,L,M
第四位:M,N,O,P,Q,R,S,T,U,V
第五位:C,D,E,F,G,H,I,J,K,L
第六位:M,N,O,P,Q,R,S,T,U,V
第七位:B,C,D,E,F,G,H,I,J,K
第八位:L,M,N,O,P,Q,R,S,T,U
第九位:B,C,D,E,F,G,H,I,J,K
...

注册码计算出的值假设为 N ,(N/0x7C的商)+0x64-用户名计算出的值=0x64 ,满足条件则注册成功。
用 PaulYoung 计算出的值为 0x547058,则用 0x547058*0x7C 可以算出N=686189216 (DEC)
而686189216中每位数字实际是0048908E中算出的 bl 的值。
因此,我们可以逆推出注册码各个字符,如第一位注册码(假设为S),即
S+0xFFFFFFEC+0/3-0x30=6 ,则 S=0x4A='J'

也可这样理解,如第一位注册码:
0,1,2,3,4,5,6,7,8,9 对应
D,E,F,G,H,I,J,K,L,M

是6则取对应的J,其它同理……

依此类推,算出一个可用的注册码
Name:PaulYoung
Code:JVJNKVDMH

Name:CCG
Code:INGVCOBNF

  另外,N/0x7C 只用到它的商,不同的 N 值都可以算出同样的商,因此,同一用户名其实可以有很多个可用的注册码。
____________________________________________________________________________________________

  很久很久没玩破解了,基于个性的懒惰,分析可能并不全面,如有发现,请跟帖批评指正。希望我粗糙的文笔及蹩脚的表达能力不会令大家望而生厌……  :-)

PaulYoung
属于中国破解组织CCG(CHiNA CrACKiNG GrOUp)