飘云 发表于 2010-5-1 20:28:23

老板来啦--信任危机 V4.32算法深度分析 ASM注册函数

【破文标题】老板来啦--信任危机 V4.32算法深度分析+ASM注册函数
【破文作者】飘云/P.Y.G
【官方主页】https://www.chinapyg.com
【作者博客】http://blog.piaoyunsoft.com
【破解平台】WinXp SP3
【破解工具】PEiD0.94、OD
【作者邮箱】[email protected]
【软件名称】老板来啦--信任危机 V4.32
【软件大小】673 K
【原版下载】http://www.skycn.com/soft/20362.html
【破解过程】

这是个2004年的老软件~~ 拿来做教程吧,有点代表性~~~ASM代码的几个函数值得收藏~~ 哈~

FSG1.3壳,脱壳过程--略

OD载入脱壳后的程序

搜索 "SOFTWARE\Microsoft\Sbackup5"

找到如下代码:00477D0A   .BA C0884700    mov   edx, 004788C0                  ;ASCII "SOFTWARE\Microsoft\Sbackup5"
00477D0F   .A1 804E4800    mov   eax, dword ptr
00477D14   .E8 E383FEFF    call    004600FC
00477D19   .8D4D F4      lea   ecx, dword ptr
00477D1C   .BA E4884700    mov   edx, 004788E4                  ;ASCII "sysback"
00477D21   .A1 804E4800    mov   eax, dword ptr
00477D26   .E8 B985FEFF    call    004602E4
.
.
.
.
.
.
.
004780CF   .E8 E4D7FFFF    call    004758B8
004780D4   .8B55 98      mov   edx, dword ptr           ;机器码
004780D7   .8B45 F4      mov   eax, dword ptr
004780DA   .E8 61C7F8FF    call    00404840
004780DF   .0F85 87000000jnz   0047816C
004780E5   .8D45 94      lea   eax, dword ptr
004780E8   .50             push    eax
004780E9   .8D55 90      lea   edx, dword ptr
004780EC   .8B45 F4      mov   eax, dword ptr
004780EF   .E8 9CDAFFFF    call    00475B90                         ;算法CALL,F7跟进
004780F4   .8B45 90      mov   eax, dword ptr
004780F7   .B9 0A000000    mov   ecx, 0A                        ;参数:10
004780FC   .33D2         xor   edx, edx
004780FE   .E8 51C8F8FF    call    00404954                         ;截取前10位注册码,所以算法CALL里面的最后连接**部分是没用的
00478103   .8B55 94      mov   edx, dword ptr           ;真码
00478106   .8B45 F0      mov   eax, dword ptr           ;假码
00478109   .E8 32C7F8FF    call    00404840                         ;比较
0047810E   .75 5C          jnz   short 0047816C                   ;关键跳转


{----------------------算法CALL:--------------------------}
00475B90/$55            push    ebp
00475B91|.8BEC          mov   ebp, esp
00475B93|.33C9          xor   ecx, ecx
00475B95|.51            push    ecx
00475B96|.51            push    ecx
00475B97|.51            push    ecx
00475B98|.51            push    ecx
00475B99|.51            push    ecx
00475B9A|.51            push    ecx
00475B9B|.51            push    ecx
00475B9C|.51            push    ecx
00475B9D|.53            push    ebx
00475B9E|.56            push    esi
00475B9F|.8BF2          mov   esi, edx
00475BA1|.8945 FC       mov   dword ptr , eax
00475BA4|.8B45 FC       mov   eax, dword ptr
00475BA7|.E8 38EDF8FF   call    004048E4
00475BAC|.33C0          xor   eax, eax
00475BAE|.55            push    ebp
00475BAF|.68 8B5D4700   push    00475D8B
00475BB4|.64:FF30       push    dword ptr fs:
00475BB7|.64:8920       mov   dword ptr fs:, esp
00475BBA|.8D45 F8       lea   eax, dword ptr
00475BBD|.E8 82E8F8FF   call    00404444
00475BC2|.8B45 FC       mov   eax, dword ptr           ;机器码
00475BC5|.E8 4E2EF9FF   call    00408A18                        ;机器码转换成16进制
00475BCA|.B9 1F000000   mov   ecx, 1F                         ;ecx = 0x1F
00475BCF|.99            cdq
00475BD0|.F7F9          idiv    ecx                           ;eax / ecx
00475BD2|.05 750E0000   add   eax, 0E75                     ;eax = 上面的结果 + 0x0E75
00475BD7|.B9 03000000   mov   ecx, 3                        ;ecx = 3
00475BDC|.99            cdq
00475BDD|.F7F9          idiv    ecx                           ;eax = eax / 3
00475BDF|.83C0 65       add   eax, 65                         ;结果+0x65保存到eax
00475BE2|.8D55 EC       lea   edx, dword ptr
00475BE5|.E8 CA2DF9FF   call    004089B4                        ;转换成10进制字符串 设为 X1
00475BEA|.8B55 EC       mov   edx, dword ptr
00475BED|.8D45 FC       lea   eax, dword ptr
00475BF0|.E8 E7E8F8FF   call    004044DC
00475BF5|.8D45 F4       lea   eax, dword ptr
00475BF8|.8B55 FC       mov   edx, dword ptr           ;X1
00475BFB|.8A12          mov   dl, byte ptr             ;第一位ASCII设为 ASCII_X1_1
00475BFD|.E8 22EAF8FF   call    00404624                        ;保存起来,下面要用到
00475C02|.8B45 FC       mov   eax, dword ptr
00475C05|.E8 F2EAF8FF   call    004046FC                        ;X1长度
00475C0A|.8B55 FC       mov   edx, dword ptr
00475C0D|.8A5402 FF   mov   dl, byte ptr       ;最后一位ASCII 设为 ASCII_X1_N
00475C11|.8D45 F0       lea   eax, dword ptr
00475C14|.E8 0BEAF8FF   call    00404624                        ;保存起来,下面要用到
00475C19|.8B45 FC       mov   eax, dword ptr
00475C1C|.E8 DBEAF8FF   call    004046FC
00475C21|.83F8 08       cmp   eax, 8
00475C24|.7E 18         jle   short 00475C3E                  ;长度是否小于8位,小于则跳
00475C26|.8D45 FC       lea   eax, dword ptr
00475C29|.50            push    eax
00475C2A|.B9 08000000   mov   ecx, 8
00475C2F|.33D2          xor   edx, edx
00475C31|.8B45 FC       mov   eax, dword ptr
00475C34|.E8 1BEDF8FF   call    00404954
00475C39|.E9 AE000000   jmp   00475CEC
00475C3E|>8B45 FC       mov   eax, dword ptr
00475C41|.E8 B6EAF8FF   call    004046FC
00475C46|.83F8 07       cmp   eax, 7                        ;Switch (cases 0..7)
00475C49|.0F87 9D000000 ja      00475CEC
00475C4F|.FF2485 565C47>jmp   dword ptr       ;下面是根据长度来拼接字符串~~ 最终为8位~ 设为X2
00475C56|.DF5C4700      dd      dumped_.00475CDF                ;分支表 被用于 00475C4F
00475C5A|.D05C4700      dd      dumped_.00475CD0
00475C5E|.C15C4700      dd      dumped_.00475CC1
00475C62|.B25C4700      dd      dumped_.00475CB2
00475C66|.A35C4700      dd      dumped_.00475CA3
00475C6A|.945C4700      dd      dumped_.00475C94
00475C6E|.855C4700      dd      dumped_.00475C85
00475C72|.765C4700      dd      dumped_.00475C76
00475C76|>8D45 FC       lea   eax, dword ptr           ;Case 7 of switch 00475C46
00475C79|.BA A05D4700   mov   edx, 00475DA0                   ;ASCII "2"
00475C7E|.E8 81EAF8FF   call    00404704
00475C83|.EB 67         jmp   short 00475CEC
00475C85|>8D45 FC       lea   eax, dword ptr           ;Case 6 of switch 00475C46
00475C88|.BA AC5D4700   mov   edx, 00475DAC                   ;ASCII "25"
00475C8D|.E8 72EAF8FF   call    00404704
00475C92|.EB 58         jmp   short 00475CEC
00475C94|>8D45 FC       lea   eax, dword ptr           ;Case 5 of switch 00475C46
00475C97|.BA B85D4700   mov   edx, 00475DB8                   ;ASCII "232"
00475C9C|.E8 63EAF8FF   call    00404704
00475CA1|.EB 49         jmp   short 00475CEC
00475CA3|>8D45 FC       lea   eax, dword ptr           ;Case 4 of switch 00475C46
00475CA6|.BA C45D4700   mov   edx, 00475DC4                   ;ASCII "4675"
00475CAB|.E8 54EAF8FF   call    00404704
00475CB0|.EB 3A         jmp   short 00475CEC
00475CB2|>8D45 FC       lea   eax, dword ptr           ;Case 3 of switch 00475C46
00475CB5|.BA D45D4700   mov   edx, 00475DD4                   ;ASCII "83855"
00475CBA|.E8 45EAF8FF   call    00404704
00475CBF|.EB 2B         jmp   short 00475CEC
00475CC1|>8D45 FC       lea   eax, dword ptr           ;Case 2 of switch 00475C46
00475CC4|.BA E45D4700   mov   edx, 00475DE4                   ;ASCII "334342"
00475CC9|.E8 36EAF8FF   call    00404704
00475CCE|.EB 1C         jmp   short 00475CEC
00475CD0|>8D45 FC       lea   eax, dword ptr           ;Case 1 of switch 00475C46
00475CD3|.BA F45D4700   mov   edx, 00475DF4                   ;ASCII "3447584"
00475CD8|.E8 27EAF8FF   call    00404704
00475CDD|.EB 0D         jmp   short 00475CEC
00475CDF|>8D45 FC       lea   eax, dword ptr           ;Case 0 of switch 00475C46
00475CE2|.BA 045E4700   mov   edx, 00475E04                   ;ASCII "47568328"
00475CE7|.E8 18EAF8FF   call    00404704
00475CEC|>BB 01000000   mov   ebx, 1                        ;Default case of switch 00475C46
00475CF1|>8D45 E4       /lea   eax, dword ptr
00475CF4      8B55 FC       mov   edx, dword ptr           ;(ASCII "42074232")
00475CF7|.8A541A FF   |mov   dl, byte ptr        ;第i位
00475CFB|.E8 24E9F8FF   |call    00404624
00475D00|.8B45 E4       |mov   eax, dword ptr
00475D03|.8D55 E8       |lea   edx, dword ptr
00475D06|.E8 45FCFFFF   |call    00475950                     ;对X2进行查表~~F7进入,看下

{
==========================================
00475AA0   dd      FFFFFFFF
00475AA4   dd      00000001
00475AA8   ascii   "1",0
00475AAA   db      00
00475AAB   db      00
00475AAC   dd      FFFFFFFF
00475AB0   dd      00000001
00475AB4   ascii   "I",0
00475AB6   db      00
00475AB7   db      00
00475AB8   dd      FFFFFFFF
00475ABC   dd      00000001
00475AC0   ascii   "2",0
00475AC2   db      00
00475AC3   db      00
00475AC4   dd      FFFFFFFF
00475AC8   dd      00000001
00475ACC   ascii   "M",0
00475ACE   db      00
00475ACF   db      00
00475AD0   dd      FFFFFFFF
00475AD4   dd      00000001
00475AD8   ascii   "3",0
00475ADA   db      00
00475ADB   db      00
00475ADC   dd      FFFFFFFF
00475AE0   dd      00000001
00475AE4   ascii   "J",0
00475AE6   db      00
00475AE7   db      00
00475AE8   dd      FFFFFFFF
00475AEC   dd      00000001
00475AF0   ascii   "4",0
00475AF2   db      00
00475AF3   db      00
00475AF4   dd      FFFFFFFF
00475AF8   dd      00000001
00475AFC   ascii   "S",0
00475AFE   db      00
00475AFF   db      00
00475B00   dd      FFFFFFFF
00475B04   dd      00000001
00475B08   ascii   "5",0
00475B0A   db      00
00475B0B   db      00
00475B0C   dd      FFFFFFFF
00475B10   dd      00000001
00475B14   ascii   "Z",0
00475B16   db      00
00475B17   db      00
00475B18   dd      FFFFFFFF
00475B1C   dd      00000001
00475B20   ascii   "6",0
00475B22   db      00
00475B23   db      00
00475B24   dd      FFFFFFFF
00475B28   dd      00000001
00475B2C   ascii   "T",0
00475B2E   db      00
00475B2F   db      00
00475B30   dd      FFFFFFFF
00475B34   dd      00000001
00475B38   ascii   "7",0
00475B3A   db      00
00475B3B   db      00
00475B3C   dd      FFFFFFFF
00475B40   dd      00000001
00475B44   ascii   "X",0
00475B46   db      00
00475B47   db      00
00475B48   dd      FFFFFFFF
00475B4C   dd      00000001
00475B50   ascii   "8",0
00475B52   db      00
00475B53   db      00
00475B54   dd      FFFFFFFF
00475B58   dd      00000001
00475B5C   ascii   "K",0
00475B5E   db      00
00475B5F   db      00
00475B60   dd      FFFFFFFF
00475B64   dd      00000001
00475B68   ascii   "9",0
00475B6A   db      00
00475B6B   db      00
00475B6C   dd      FFFFFFFF
00475B70   dd      00000001
00475B74   ascii   "L",0
00475B76   db      00
00475B77   db      00
00475B78   dd      FFFFFFFF
00475B7C   dd      00000001
00475B80   ascii   "0",0
00475B82   db      00
00475B83   db      00
00475B84   dd      FFFFFFFF
00475B88   dd      00000001
00475B8C   ascii   "B",0
==========================================
整理之后得到:
0123456789
BIMJSZTXKL
==========================================
}

00475D0B|.8B55 E8       |mov   edx, dword ptr
00475D0E|.8D45 F8       |lea   eax, dword ptr
00475D11|.E8 EEE9F8FF   |call    00404704
00475D16|.43            |inc   ebx
00475D17|.83FB 09       |cmp   ebx, 9
00475D1A|.^ 75 D5         \jnz   short 00475CF1               ;循环完成的结果设为X3
00475D1C|.8D55 F8       lea   edx, dword ptr
00475D1F|.B9 03000000   mov   ecx, 3
00475D24|.8B45 F4       mov   eax, dword ptr           ;参数A = ASCII_X1_1
00475D27|.E8 B0ECF8FF   call    004049DC                        ;在X3第3位插入参数A 设为X4
00475D2C|.8D55 F8       lea   edx, dword ptr
00475D2F|.B9 07000000   mov   ecx, 7
00475D34      8B45 F0       mov   eax, dword ptr          ;参数B = ASCII_X1_N
00475D37|.E8 A0ECF8FF   call    004049DC                        ;在X4第7位插入参数B 设为SN
00475D3C|.FF75 F8       push    dword ptr                ;这里出来之后就是10位注册码了~
00475D3F|.B8 E8030000   mov   eax, 3E8
00475D44|.E8 23D2F8FF   call    00402F6C                        ;下面几个CALL计算和连接**字符串,因为考虑 ASCII_X1_1 和 ASCII_X1_N 为空的情况~~ 导致

注册码为8位~~
00475D49|.8D55 E0       lea   edx, dword ptr          ;我仔细分析了下,不会出现为空的情况,所以下面的连接部分忽略不计~
00475D4C|.E8 632CF9FF   call    004089B4
00475D51|.FF75 E0       push    dword ptr
00475D54|.68 185E4700   push    00475E18                        ;ASCII "**"
00475D59|.8D45 F8       lea   eax, dword ptr
00475D5C|.BA 03000000   mov   edx, 3
00475D61|.E8 56EAF8FF   call    004047BC
00475D66|.8BC6          mov   eax, esi
00475D68|.8B55 F8       mov   edx, dword ptr
00475D6B|.E8 28E7F8FF   call    00404498
00475D70|.33C0          xor   eax, eax
00475D72|.5A            pop   edx
00475D73|.59            pop   ecx
00475D74|.59            pop   ecx
00475D75|.64:8910       mov   dword ptr fs:, edx
00475D78|.68 925D4700   push    00475D92
00475D7D|>8D45 E0       lea   eax, dword ptr
00475D80|.BA 08000000   mov   edx, 8
00475D85|.E8 DEE6F8FF   call    00404468
00475D8A\.C3            retn
00475D8B   .^ E9 58E0F8FF   jmp   00403DE8
00475D90   .^ EB EB         jmp   short 00475D7D
00475D92   .5E            pop   esi
00475D93   .5B            pop   ebx
00475D94   .8BE5          mov   esp, ebp
00475D96   .5D            pop   ebp
00475D97   .C3            retn【算法总结】
1.eax = 16进制(机器码) / 0x1F
2.eax = eax + 0x0E75
3.eax = eax / 3
4.eax = eax + 0x65
5.X1 = 10进制(eax)
6.ASCII_X1_1 = X1
7.ASCII_X1_N = X1
8.Len(X1)=8位则用原来的数据 Len(X1)<8 则补充长度为8位~
分别为:
====================
7位: + "2"
6位: + "25"
5位: + "232"
4位: + "4675"
3位: + "83855"
2位: + "334342"
1位: + "3447584"
0位: + "47568328"
====================

补充之后的数据为X2
9.对X2逐位查表:
0123456789
BIMJSZTXKL
10.在X3第3位插入参数ASCII_X1_1(字符)
11.在X4第7位插入参数ASCII_X1_N((字符)
12.截取步骤11的前10位即为注册码

【注册函数】
;字符串操作宏
T MACRO text
      local @lbl
      .const
                @lbl db text,0
      .code
      exitm   <offset @lbl>
ENDM

.data
;密码表
szConstTable                db                'BIMJSZTXKL',0
szFormatOct                        db                '%d',0

.code

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;函数功能:将字符串转换成数值
;Code By PiaoYun/P.Y.G
;http://blog.piaoyunsoft.com
;说明:仅做转换用,没有判断传入字符串的合法性~~如 "1111" --> 1111
;
;函数参数:
;lpszStr:指针,传入字符串的地址
;返回值:16进制数值
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
_ProcStrToDword proc lpszStr:dword
      mov         esi,lpszStr
      xoreax, eax
      xorebx, ebx
      
@@:
      movbl, byte ptr [esi]
      test bl, bl
      je         @F
      subbl, 30h
      leaeax, dword ptr [eax+eax*4]
      addeax, eax
      addeax, ebx
      incesi
      jmp         @B
@@:
      ret
_ProcStrToDword endp


;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;函数功能:在字符串中指定位置插入字符
;Code By PiaoYun/P.Y.G
;http://blog.piaoyunsoft.com
;函数参数:
;lpszStr:指针,待插入字符的字符串地址
;lpChar: 指针,要插入的字符地址
;wPos:  插入的位置
;返回值:没有
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
_InsertCharproclpszStr:DWORD,lpChar:DWORD,wPos:DWORD
local@szInStr:BYTE
movedi,lpszStr
movesi,lpChar
movedx,wPos
decedx
movecx,edx
addedx,edi
addedi,ecx
invokelstrcpy, addr @szInStr,edx
movbl,BYTE ptr [esi]
movBYTE ptr [edi],bl
movBYTE ptr [edi+1],0
invokelstrcat,edi,addr @szInStr
ret
_InsertCharendp

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;函数功能:注册算法总户数
;Code By PiaoYun/P.Y.G
;http://blog.piaoyunsoft.com
;函数参数:
;lpID:      指针,传入机器码地址
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
KeyGen      proc      uses ecx edx lpID:DWORD

      LOCAL      @szKey:byte
      
      invoke      RtlZeroMemory,addr @szKey,sizeof @szKey      

      xor                ecx,ecx
      xor                edx,edx
      
      ;机器码转换成数值
      invoke      _ProcStrToDword,lpID
      
      mov   ecx, 1Fh
      cdq
      idiv    ecx
      add   eax, 0E75h
      mov   ecx, 3h
      cdq
      idiv    ecx
      add   eax, 65h

      ;上面累加结果转成字符串
      invoke wsprintf,addr @szKey,addr szFormatOct,eax
      ;获取字符串长度
      invoke lstrlen,addr @szKey
      
      ;第一位字符
      mov                dl,byte ptr [@szKey]
      mov                [@szKey+100],dl
      
      ;最后一位字符
      mov                dl,byte ptr [@szKey + eax -1]
      mov                [@szKey+101],dl
      
      .if eax <= 8
                .if      eax == 6
                        invoke      lstrcat,addr @szKey,T("2")      
                        .elseif      eax == 6
                              invoke      lstrcat,addr @szKey,T("25")      
                        .elseif      eax == 5
                              invoke      lstrcat,addr @szKey,T("232")      
                        .elseif      eax == 4
                              invoke      lstrcat,addr @szKey,T("4675")      
                        .elseif      eax == 3
                              invoke      lstrcat,addr @szKey,T("83855")      
                        .elseif      eax == 2
                              invoke      lstrcat,addr @szKey,T("334342")      
                        .elseif      eax == 1
                              invoke      lstrcat,addr @szKey,T("3447584")      
                        .elseif      eax == 0
                              invoke      lstrcat,addr @szKey,T("47568328")      
                .endif
      ;如果大于8位,则截断后面的
      .elseif      
                mov      byte ptr[@szKey + 8],0
      .endif
      
      
                xor                ebx,ebx
      @@:
                movzx   edx,byte ptr [@szKey+ebx]
                sub          edx,30h
                movzx      edx,byte ptr edx]
                mov                byte ptr[@szKey + ebx],dl
                inc                ebx
                cmp                ebx,8
                jnz                @B
               
      invoke_InsertChar,addr @szKey,addr [@szKey+100],3
      invoke_InsertChar,addr @szKey,addr [@szKey+101],7
      

      ;取前十位作为注册码(这句可省略)
      ;mov      byte ptr[@szKey + 10],0
      
      ;插入分隔符
      invoke_InsertChar,addr @szKey,T("-"),6
      
      lea                eax,@szKey
      ret

KeyGen endp
【版权声明】 本文纯属技术交流, 原创于PYG官方论坛, 转载请注明作者并保持文章的完整, 谢谢!

月之精灵 发表于 2010-5-1 22:04:44

第一个来学习

sjh717142 发表于 2010-5-2 00:04:31

刚用了LZ的PYG.dll
Thanks

GGLHY 发表于 2010-5-2 10:14:40

前来学习!
膜拜下!

老万 发表于 2010-5-2 22:05:12

学习了,谢谢飘云老大

gerald2008 发表于 2010-5-11 08:48:22

学习了,谢谢!

kelvar 发表于 2010-5-19 20:01:43

多谢分享。发现PYG用FireFox登录的时候回复总是有验证码,并且怎么输入都不对。郁闷
页: [1]
查看完整版本: 老板来啦--信任危机 V4.32算法深度分析 ASM注册函数