zoukankan      html  css  js  c++  java
  • 穷举法破解 zebrone1.1

    系统 : Windows xp

    程序 : zebrone1.1

    程序下载地址 :http://pan.baidu.com/s/1boqVcU7

    要求 : 编写注册机

    使用工具 :OD

    可在看雪论坛中查找关于此程序的讨论:传送门

    用OD载入程序,查找字串发现成功提示“congratulations, you have cracked the zebra crackme ver 1.1”,双击定位该字串:

    004012AA  |> 6A 0A         push    0A                               ; /Count = A (10.); Case 1 of switch 0040128D
    004012AC  |.  8D45 EC       lea     eax, dword ptr [ebp-14]          ; |
    004012AF  |.  50            push    eax                              ; |Buffer
    004012B0  |.  6A 65         push    65                               ; |ControlID = 65 (101.)
    004012B2  |.  FF75 08       push    dword ptr [ebp+8]                ; |hWnd
    004012B5  |.  E8 F2010000   call    <jmp.&USER32.GetDlgItemTextA>    ; GetDlgItemTextA
    004012BA  |.  6A 0A         push    0A                               ; /Count = A (10.)
    004012BC  |.  8D45 F6       lea     eax, dword ptr [ebp-A]           ; |
    004012BF  |.  50            push    eax                              ; |Buffer
    004012C0  |.  6A 66         push    66                               ; |ControlID = 66 (102.)
    004012C2  |.  FF75 08       push    dword ptr [ebp+8]                ; |hWnd
    004012C5  |.  E8 E2010000   call    <jmp.&USER32.GetDlgItemTextA>    ; GetDlgItemTextA
    004012CA  |.  8D45 F6       lea     eax, dword ptr [ebp-A]           ;  取序列号
    004012CD  |.  50            push    eax                              ;  序列号入栈
    004012CE  |.  8D45 EC       lea     eax, dword ptr [ebp-14]          ;  取用户名
    004012D1  |.  50            push    eax                              ;  用户名入栈
    004012D2  |.  E8 73000000   call    0040134A
    004012D7  |.  83C4 08       add     esp, 8                           ;  平衡堆栈
    004012DA  |.  09C0          or      eax, eax                         ;  eax 为 0?
    004012DC  |.  74 16         je      short 004012F4                   ;  为0 则错误。
    004012DE  |.  6A 00         push    0                                ; /Style = MB_OK|MB_APPLMODAL
    004012E0  |.  68 26324000   push    00403226                         ; |great !!!
    004012E5  |.  68 30324000   push    00403230                         ; |congratulations, you have cracked the zebra crackme ver 1.1
    004012EA  |.  FF75 08       push    dword ptr [ebp+8]                ; |hOwner
    004012ED  |.  E8 C6010000   call    <jmp.&USER32.MessageBoxA>        ; MessageBoxA
    004012F2  |.  EB 14         jmp     short 00401308
    004012F4  |>  6A 00         push    0                                ; /Style = MB_OK|MB_APPLMODAL
    004012F6  |.  68 F8314000   push    004031F8                         ; |hmmmm :p
    004012FB  |.  68 01324000   push    00403201                         ; |Text = "Sorry... The Serial isn't correct :?
    00401300  |.  FF75 08       push    dword ptr [ebp+8]                ; |hOwner
    00401303  |.  E8 B0010000   call    <jmp.&USER32.MessageBoxA>        ; MessageBoxA

    跟入关键call:

    0040134A  /$  55            push    ebp
    0040134B  |.  89E5          mov     ebp, esp
    0040134D  |.  83EC 68       sub     esp, 68                          ;  ↓将用户名字串转化为浮点数
    00401350  |.  FF75 08       push    dword ptr [ebp+8]                ; /s
    00401353  |.  E8 78010000   call    <jmp.&CRTDLL.atof>               ; atof
    00401358  |.  DD55 E8       fst     qword ptr [ebp-18]               ;  保存转化结果
    0040135B  |.  83EC 08       sub     esp, 8                           ;  开辟内存
    0040135E  |.  DD1C24        fstp    qword ptr [esp]                  ;  保存转化结果并弹栈
    00401361  |.  E8 82010000   call    <jmp.&CRTDLL.floor>              ;  向下取整
    00401366  |.  DD5D F8       fstp    qword ptr [ebp-8]                ;  ↓将序列号转化为浮点数
    00401369  |.  FF75 0C       push    dword ptr [ebp+C]                ; /s
    0040136C  |.  E8 5F010000   call    <jmp.&CRTDLL.atof>               ; atof
    00401371  |.  DD55 D8       fst     qword ptr [ebp-28]               ;  保存转化后的序列号
    00401374  |.  83EC 08       sub     esp, 8                           ;  平衡堆栈
    00401377  |.  DD1C24        fstp    qword ptr [esp]                  ;  将结果入栈
    0040137A  |.  E8 69010000   call    <jmp.&CRTDLL.floor>              ;  向下取整
    0040137F  |.  83C4 18       add     esp, 18                          ;  平衡堆栈
    00401382  |.  DD55 F0       fst     qword ptr [ebp-10]               ;  保存取整结果
    00401385  |.  DC4D F8       fmul    qword ptr [ebp-8]                ;  乘以用户名
    00401388  |.  D9EE          fldz                                     ;  载入0
    0040138A  |.  DED9          fcompp                                   ;  比较st(0)st(1),并弹出寄存器堆栈
    0040138C  |.  DFE0          fstsw   ax                               ;  把该状态寄存器的值传送给通用寄存器AX
    0040138E  |.  9E            sahf                                     ;  标志传送指令
    0040138F  |.  75 07         jnz     short 00401398                   ;  st0和st1相等?
    00401391  |.  31C0          xor     eax, eax                         ;  清空eax
    00401393  |.  E9 96000000   jmp     0040142E                         ;  函数结束
    00401398  |>  DD45 F8       fld     qword ptr [ebp-8]                ;  用户名浮点数入栈
    0040139B  |.  DC5D F0       fcomp   qword ptr [ebp-10]               ;  与序列号浮点数比较
    0040139E  |.  DFE0          fstsw   ax
    004013A0  |.  9E            sahf
    004013A1  |.  75 07         jnz     short 004013AA                   ;  用户名浮点数与序列号浮点数相等则函数结束
    004013A3  |.  31C0          xor     eax, eax                         ;  清空eax
    004013A5  |.  E9 84000000   jmp     0040142E                         ;  函数结束
    004013AA  |>  DD45 F8       fld     qword ptr [ebp-8]                ;  用户名浮点数入栈
    004013AD  |.  DD5D C8       fstp    qword ptr [ebp-38]               ;  保存用户名浮点数
    004013B0  |.  D9E8          fld1                                     ;  1入栈
    004013B2  |.  DD55 C0       fst     qword ptr [ebp-40]               ;  保存1
    004013B5  |.  DC5D C8       fcomp   qword ptr [ebp-38]               ;  1 > 用户名浮点数?
    004013B8  |.  DFE0          fstsw   ax
    004013BA  |.  9E            sahf
    004013BB  |.  77 2D         ja      short 004013EA                   ;  是则错误
    004013BD  |.  DF2D 38304000 fild    qword ptr [403038]               ;  载入10的10次方
    004013C3  |.  DD55 B8       fst     qword ptr [ebp-48]               ;  保存
    004013C6  |.  DC5D C8       fcomp   qword ptr [ebp-38]               ;  10的10次方 < 用户名浮点数?
    004013C9  |.  DFE0          fstsw   ax
    004013CB  |.  9E            sahf
    004013CC  |.  72 1C         jb      short 004013EA                   ;  是则错误
    004013CE  |.  DD45 F0       fld     qword ptr [ebp-10]               ;  序列号浮点数入栈
    004013D1  |.  DD5D B0       fstp    qword ptr [ebp-50]               ;  保存
    004013D4  |.  DD45 C0       fld     qword ptr [ebp-40]               ;  用户名浮点数入栈
    004013D7  |.  DC5D B0       fcomp   qword ptr [ebp-50]               ;  用户名浮点数 > 序列号浮点数?
    004013DA  |.  DFE0          fstsw   ax
    004013DC  |.  9E            sahf
    004013DD  |.  77 0B         ja      short 004013EA                   ;  是则错误
    004013DF  |.  DD45 B8       fld     qword ptr [ebp-48]               ;  载入10的10次方
    004013E2  |.  DC5D B0       fcomp   qword ptr [ebp-50]               ;  10的10次方 >= 序列号浮点数?
    004013E5  |.  DFE0          fstsw   ax
    004013E7  |.  9E            sahf
    004013E8  |.  73 04         jnb     short 004013EE                   ;  是则继续流程
    004013EA  |>  31C0          xor     eax, eax                         ;  清空eax
    004013EC  |.  EB 40         jmp     short 0040142E                   ;  函数结束
    004013EE  |>  DD45 F8       fld     qword ptr [ebp-8]                ;  用户名浮点数入栈
    004013F1  |.  D9FE          fsin                                     ;  计算栈顶的正弦函数
    004013F3  |.  DD5D A8       fstp    qword ptr [ebp-58]               ;  保存结果
    004013F6  |.  DD45 F0       fld     qword ptr [ebp-10]               ;  序列号浮点数入栈
    004013F9  |.  D9FE          fsin                                     ;  计算栈顶的正弦函数
    004013FB  |.  DD5D A0       fstp    qword ptr [ebp-60]               ;  保存结果
    004013FE  |.  DD45 A8       fld     qword ptr [ebp-58]               ;  用户名正弦值入栈
    00401401  |.  DC4D A0       fmul    qword ptr [ebp-60]               ;  乘以 序列号正弦值
    00401404  |.  DF2D 30304000 fild    qword ptr [403030]               ;  10的16次方入栈
    0040140A  |.  DEC9          fmulp   st(1), st                        ;  再相乘
    0040140C  |.  83EC 08       sub     esp, 8                           ;  开辟8个字节的空间
    0040140F  |.  DD1C24        fstp    qword ptr [esp]                  ;  保存结果
    00401412  |.  E8 D1000000   call    <jmp.&CRTDLL.floor>              ;  向下取整
    00401417  |.  83C4 08       add     esp, 8
    0040141A  |.  DD5D 98       fstp    qword ptr [ebp-68]               ;  保存
    0040141D  |.  D9EE          fldz                                     ;  载入0
    0040141F  |.  DC5D 98       fcomp   qword ptr [ebp-68]               ;  结果是否为0?
    00401422  |.  DFE0          fstsw   ax
    00401424  |.  9E            sahf                                     ;  (initial cpu selection)
    00401425  |.  75 05         jnz     short 0040142C                   ;  不为0则失败
    00401427  |.  31C0          xor     eax, eax
    00401429  |.  40            inc     eax
    0040142A  |.  EB 02         jmp     short 0040142E
    0040142C  |>  31C0          xor     eax, eax
    0040142E  |>  C9            leave
    0040142F  .  C3            retn

    这里的Sin指令是按弧度制算的,所以想用180的倍数充当乘数是不行的,我们只能遍历[1,10^10],找出其中正弦值为正数且正弦值小于10^-8的实数。这样的两个实数相乘再乘以10的16次方的乘积就满足了条件。{ x | 0 < x < 1 }

    动手编写程序,验证我们的猜想:

    =========================十年后============================》

    好吧。。。肯定是哪儿出问题了,经过Debug之后源程序如下:

    #include <iostream>
    #include <math.h>
    #include <iomanip>                                                // 精度控制头文件 
    
    using namespace std;
    
    inline double Sin( double Var )                                    //内联Sin指令
    {
        __asm{
            fld Var
            fsin
            fstp Var
        }
    
        return Var;
    }
    
    int main( void )
    {
        double i,j,res;
        const double min = 1e-8;
    
        cout << "Valid number:" << endl;
    
        for ( i = 1 ; i <= 1e+10 ; i++ ){
            res = Sin( i );                                                //接受正弦值。
            
            bool Flag = false;
            __asm{
                    push eax
    
                    fld res                                                //载入正弦值
                    fldz                                                //载入0
                    fcompp                                                 //0 < 正弦值?
                    fstsw ax
                    sahf
                    jnb s                                                //不小于则跳转
                    fld res                                                //载入正弦值
                    fcomp min                                            //正弦值 < min?
                    fstsw ax
                    sahf
                    jnb s                                                //不小于则跳转
                    mov Flag,1
    
                s:    pop eax
            }
    
            if ( Flag )    
                cout << setprecision(10) << i <<endl;
        }
            
    
        cout << "Done." << endl;
    
        return 0;
    }

    运行效果:

    但经过测试发现,算出的数中 大于 10的9次方的数的Sin值与zebrone1.1的Sin值有偏差,所以有效的数值有:

    245850922
    411557987
    657408909
    823115974

    随便取出两个按照 升序填入:

    就注册成功了:

  • 相关阅读:
    【转】linux shell I/O重定向小结
    vnc 最近打开
    [转]设置修改CentOS系统时区/时间
    【转】动态链接库、静态库区别与VS2005项目相关设置
    更改默认shell
    19个PHP模板引擎
    const char*, char const*, char*const的区别
    按任意键继续
    [转]CentOS设置服务开机自动启动
    centos 修改eth2为eth0
  • 原文地址:https://www.cnblogs.com/ZRBYYXDM/p/5222765.html
Copyright © 2011-2022 走看看