欢迎来到 嗅灵易学

零基础也能上手的脚本技术课,一对一答疑带你入门

Universe 1.63注册码生成分析及注册机原码(中) (7千字)

Universe 1.63注册码生成分析及注册机原码(中) (7千字)

Universe 1.63注册码生成分析及注册机原码(中)

我们追进算注册码的CALL,看到下面的程序段:
0177:00416844  PUSH    EBP
0177:00416845  MOV      EBP,ESP
0177:00416847  PUSH    BYTE -01
0177:00416849  PUSH    DWORD 004754B9
0177:0041684E  MOV      EAX,`DOSMGR_BackFill_Allowed`
0177:00416854  PUSH    EAX
0177:00416855  MOV      `DOSMGR_BackFill_Allowed`,ESP
0177:0041685C  SUB      ESP,BYTE +2C
0177:0041685F  PUSH    DWORD 0048DCCC
0177:00416864  LEA      EAX,[EBP-30]
0177:00416867  PUSH    EAX
0177:00416868  CALL    00416CC2
0177:0041686D  ADD      ESP,BYTE +08
0177:00416870  MOV      [EBP-34],EAX
0177:00416873  MOV      ECX,[EBP-34]
0177:00416876  MOV      [EBP-38],ECX
0177:00416879  MOV      DWORD [EBP-04],00
0177:00416880  MOV      EDX,[EBP-38]
0177:00416883  PUSH    EDX
0177:00416884  MOV      EAX,[EBP+08]
0177:00416887  PUSH    EAX
0177:00416888  CALL    00417020
0177:0041688D  MOV      [EBP-2C],AL
0177:00416890  MOV      DWORD [EBP-04],FFFFFFFF
0177:00416897  LEA      ECX,[EBP-30]
0177:0041689A  CALL    00455C64
0177:0041689F  MOV      ECX,[EBP-2C]
0177:004168A2  AND      ECX,FF
0177:004168A8  TEST    ECX,ECX
0177:004168AA  JZ      004168B3
0177:004168AC  XOR      EAX,EAX
0177:004168AE  JMP      00416997
0177:004168B3  CALL    0042A6D0
0177:004168B8  MOV      [EBP-24],EAX
0177:004168BB  MOV      DWORD [EBP-10],00
0177:004168C2  MOV      DWORD [EBP-20],01
0177:004168C9  MOV      DWORD [EBP-1C],00
0177:004168D0  JMP      SHORT 004168DB
以上是一些无太多关系的操作,主要是姓名和注册码的存取和转换,下面来到重点了:
0177:004168D2  MOV      EDX,[EBP-1C]
0177:004168D5  ADD      EDX,BYTE +01
0177:004168D8  MOV      [EBP-1C],EDX
0177:004168DB  MOV      ECX,[EBP+08]
0177:004168DE  CALL    00403460      <=====计算姓名的位数
0177:004168E3  CMP      [EBP-1C],EAX  <=====EBP-1C是指针,用于取字符
0177:004168E6  JNL      00416937
0177:004168E8  MOV      EAX,[EBP-1C]  <=====指针送入EAX
0177:004168EB  PUSH    EAX
0177:004168EC  MOV      ECX,[EBP+08]  <=====这里D *ECX 可以看到用户名"Maomao[CCG]"
0177:004168EF  CALL    00417000      <=====取指针所指字符到AL
0177:004168F4  MOVSX    ECX,AL        <=====送入ECX
0177:004168F7  MOV      [EBP-28],ECX  <=====临时寄存这个字符(下面还要用到)
0177:004168FA  MOV      EDX,[EBP-10]  <=====取累加器中的数据(EBP-10为累加器)
0177:004168FD  ADD      EDX,[EBP-28]  <=====相加
0177:00416900  MOV      [EBP-10],EDX  <=====结果送入累加器,下一次再使用
0177:00416903  MOV      EAX,[EBP-1C]  <=====取指针到EAX
0177:00416906  AND      EAX,80000001  <=====与0x80000001 AND
                                        (当指针为奇数时结果为0,偶数数结果为1)
0177:0041690B  JNS      00416912
0177:0041690D  DEC      EAX
0177:0041690E  OR      EAX,BYTE -02
0177:00416911  INC      EAX
0177:00416912  TEST    EAX,EAX        <=====判断奇偶
0177:00416914  JZ      0041691F
0177:00416916  MOV      DWORD [EBP-20],FFFFFFFF <=====偶位时送符号位-1
0177:0041691D  JMP      SHORT 00416926
0177:0041691F  MOV      DWORD [EBP-20],01      <=====奇位时送符号位1
0177:00416926  MOV      ECX,[EBP-20]            <=====取符号位
0177:00416929  IMUL    ECX,[EBP-28]            <=====取临时寄存的字符与符号相乘(偶数位结果为负)
0177:0041692D  MOV      EDX,[EBP-10]            <=====取累加器中的值
0177:00416930  ADD      EDX,ECX                <=====再相加(如果是偶数位就是相减了)
0177:00416932  MOV      [EBP-10],EDX            <=====送入累加器
0177:00416935  JMP      SHORT 004168D2          <=====取下一字符
    上面这段程序完成奇位字符相加两次,偶位字符一加一减(等于不运算)。结果为所有奇位字符和的二倍。
紧接着:
0177:00416937  MOV      EAX,[EBP-10]      <=====取累加器中的值
0177:0041693A  MOV      [EBP-18],EAX      <=====送入[EBP-18]
0177:0041693D  MOV      ECX,[EBP-10]      <=====取累加器中的值到ECX
0177:00416940  IMUL    ECX,[EBP-10]      <=====相乘(相当于求平方)
0177:00416944  MOV      [EBP-10],ECX      <=====结果送入累加器
0177:00416947  MOV      EDX,[EBP-10]      <=====取累加器中的值
0177:0041694A  ADD      EDX,[EBP-18]      <=====与刚才保存的[EBP-18]相加
0177:0041694D  MOV      [EBP-10],EDX      <=====结果送入累加器
0177:00416950  MOV      EAX,[EBP-10]      <=====累加器送入EAX
0177:00416953  PUSH    EAX
0177:00416954  CALL    0042A6C0          <=====保存中间值到[0048E7E8],此call略
0177:00416959  ADD      ESP,BYTE +04     
  以上程序完成求形如(X*X+X)的结果,其中X为第一段累加运算的结果。接下来:
0177:0041695C  MOV      DWORD [EBP-1C],00 <=====指针清0
0177:00416963  JMP      SHORT 0041696E
0177:00416965  MOV      ECX,[EBP-1C]
0177:00416968  ADD      ECX,BYTE +01      <=====指针加1
0177:0041696B  MOV      [EBP-1C],ECX
0177:0041696E  MOV      EDX,[EBP-1C]     
0177:00416971  CMP      EDX,[00497808]  <=====[00497808]为循环计数器,值为3
0177:00416977  JNL      00416980     <=====大于或等于时结束运算 
0177:00416979  CALL    0042A6E0     <=====运算的call 
0177:0041697E  JMP      SHORT 00416965
0177:00416980  CALL    0042A6E0     <=====再运算一次 
0177:00416985  MOV      [EBP-14],EAX      <=====保存结果
0177:00416988  MOV      EAX,[EBP-24]
0177:0041698B  PUSH    EAX
0177:0041698C  CALL    0042A6C0
0177:00416991  ADD      ESP,BYTE +04
0177:00416994  MOV      EAX,[EBP-14]   <=====取回结果
0177:00416997  MOV      ECX,[EBP-0C]
0177:0041699A  MOV      `DOSMGR_BackFill_Allowed`,ECX
0177:004169A1  MOV      ESP,EBP
0177:004169A3  POP      EBP
0177:004169A4  RET   
  以上这段完成四次循环运算,结果保存在EAX中。看来还要跟进0177:00416980的CALL 0042A6E0。
跟进后,是这样的程序段:
0177:0042A6E0  MOV      EAX,[0048E7E8]  <=====取加保存的中间结果
0177:0042A6E5  PUSH    DWORD 78B30C40  <=====放一个辅助运算数0x78B30C40
0177:0042A6EA  CDQ   
0177:0042A6EB  PUSH    BYTE +00
0177:0042A6ED  PUSH    DWORD 25A2A40D  <=====放另一个辅助运算数0x25A2A40D
0177:0042A6F2  PUSH    EDX       
0177:0042A6F3  PUSH    EAX
0177:0042A6F4  CALL    00441870     <=====第一次运算  
0177:0042A6F9  ADD      EAX,BYTE +01   <=====运算结果加1
0177:0042A6FC  ADC      EDX,BYTE +00
0177:0042A6FF  PUSH    EDX
0177:0042A700  PUSH    EAX
0177:0042A701  CALL    0042A760        <=====第二次运算
0177:0042A706  ADD      ESP,BYTE +0C
0177:0042A709  MOV      [0048E7E8],EAX  <=====保存中间结果,下次使用
0177:0042A70E  RET   
第一次运算的call:
0177:00441870  MOV      EAX,[ESP+08]
0177:00441874  MOV      ECX,[ESP+10]
0177:00441878  OR      ECX,EAX
0177:0044187A  MOV      ECX,[ESP+0C]  <=====取辅助运算数0x25A2A40D
0177:0044187E  JNZ      00441889
0177:00441880  MOV      EAX,[ESP+04]  <=====取累算的结果
0177:00441884  MUL      ECX       <=====两数相乘送入ECX
0177:00441886  RET      10
第二次运算的call:
0177:0042A760  PUSH    EBP
0177:0042A761  MOV      EBP,ESP
0177:0042A763  PUSH    EBX
0177:0042A764  MOV      EAX,[EBP+08] <=====取累算的结果
0177:0042A767  MOV      EDX,[EBP+0C]
0177:0042A76A  MOV      EBX,[EBP+10] <=====取辅助运算数0x78B30C40
0177:0042A76D  DIV      EBX      <=====相除(商到EAX,余数到EDX)
0177:0042A76F  MOV      EAX,EDX    <=====只取余数
0177:0042A771  POP      EBX
0177:0042A772  POP      EBP
0177:0042A773  RET   
  这段程序主要完成形如 [(X*0x25A2A40D)+1]  mod  0x78B30C40 的功能,并且要重复运算4次!
OK,可以整理一下了:
    注册算码程序首先取用户名的奇位字符的2倍累加,对结果再进行形如(X*X+X)的运算,然后循环四次,循环中进行形如 [(X*0x25A2A40D)+1]  mod  0x78B30C40 的运算,结果为正确的注册码。
  到这里就结束了吗?没有,还有注册机的制作,请看下篇:C++Builder的注册机原码
(中篇完~~~)

注意:上传附件及图片大小不得大于30M。

⚠️ 版权声明:
本博客所有内容(含教程、源码、工具)仅供个人技术学习与研究交流使用,严禁商用、倒卖、二次分发及非法用途
未经作者书面授权,任何组织或个人不得转载、复制或用于其他平台,违者将追究相关责任。

0 0 0 举报
复制成功