SysSync Version 1.02簡單演算法分析+VB序號產生器原始碼 (8千字)

看雪資料發表於2015-11-15

軟體名稱:SysSync Version 1.02
軟體介紹:Browse to two separate locations and then synchronise in either direction. List files to be excluded from the synchronisation. Synchronise complete folder hierarchies. Save profiles of each synchronisation set up to quickly re run. 
下載地址:http://www.mike.franklin.btinternet.co.uk/downloads/syssync.zip

破解人:BurSH (於2003.7.10)
所屬組織:FCG-CCG-BCG-OCN-DFCG
破解工具:Trw2000 1.23

/--------------------\
| 尋找正確的註冊碼:  |
\--------------------/

任意輸入使用者名稱和註冊碼,Ctrl+N撥出Trw2000,下斷點Bpx GetWindowTextA,F5,回到軟體註冊介面點確定,Trw2000彈出後輸入Pmodule回到軟體領空,F12按33下(因為按34下的話軟體就彈出註冊失敗的對話方塊),再按一下F10,看到如下程式碼:

016F:00417383 8B442428         MOV      EAX,[ESP+28]      //將使用者名稱放入EAX
016F:00417387 3BC6             CMP      EAX,ESI           //此時ESI=0
016F:00417389 7505             JNZ      00417390          //是否輸入使用者名稱?
016F:0041738B B8B4474500       MOV      EAX,004547B4      //再次將使用者名稱放入EAX-_-
016F:00417390 8D542454         LEA      EDX,[ESP+54]      //[ESP+54]指向正確註冊碼將要放的地方
☆這裡說明一下,軟體的註冊演算法有個缺陷--不能使用一個字母的使用者名稱.因為如果只有一位使用者名稱,[ESP+54]指向的地址的數值就會參加計算,而軟體啟動時對註冊碼的校驗[ESP+54]指向的數值會與現在的不同,造成了在軟體註冊介面彈出註冊成功的對話方塊,啟動時卻提示軟體還未註冊.☆
016F:00417394 52               PUSH     EDX
016F:00417395 50               PUSH     EAX
016F:00417396 E87548FFFF       CALL     0040BC10          //演算法Call,F8跟進!
016F:0041739B 8D7C245C         LEA      EDI,[ESP+5C]
016F:0041739F 83C9FF           OR       ECX,BYTE -01
016F:004173A2 33C0             XOR      EAX,EAX
016F:004173A4 83C408           ADD      ESP,BYTE +08
016F:004173A7 F2AE             REPNE SCASB 
016F:004173A9 F7D1             NOT      ECX
016F:004173AB 49               DEC      ECX
016F:004173AC 8D442454         LEA      EAX,[ESP+54]     //將正確註冊放入EAX
016F:004173B0 51               PUSH     ECX
016F:004173B1 8B4C2440         MOV      ECX,[ESP+40]     //將你輸入的註冊嗎的位數放入ECX
016F:004173B5 50               PUSH     EAX
016F:004173B6 51               PUSH     ECX
016F:004173B7 56               PUSH     ESI
016F:004173B8 8D4C2444         LEA      ECX,[ESP+44]
016F:004173BC E86F41FFFF       CALL     0040B530         //裡面比較註冊碼正確與否
016F:004173C1 3BC6             CMP      EAX,ESI          //正確的話EAX置零
016F:004173C3 7511             JNZ      004173D6         //比較成功就往下走彈出成功的對話方塊!       
016F:004173C5 56               PUSH     ESI
016F:004173C6 6A40             PUSH     BYTE +40
016F:004173C8 C6856C01000001   MOV      BYTE [EBP+016C],01
016F:004173CF 6840454600       PUSH     DWORD 00464540   //一些提示註冊成功的話入棧^0^!
016F:004173D4 EB0E             JMP      SHORT 004173E4
016F:004173D6 56               PUSH     ESI
016F:004173D7 56               PUSH     ESI
016F:004173D8 C6856C01000000   MOV      BYTE [EBP+016C],00
016F:004173DF 68A8444600       PUSH     DWORD 004644A8   //一些提示註冊失敗的話入棧:(
016F:004173E4 E8163C0300       CALL     0044AFFF         //這裡彈出對話方塊
016F:004173E9 6A01             PUSH     BYTE +01
016F:004173EB 8D4C2438         LEA      ECX,[ESP+38]

/----------------------------------------\
| 跟進40BC10的演算法Call,我們看到如下程式碼:  |
\----------------------------------------/

016F:0040BC10 53               PUSH     EBX
016F:0040BC11 55               PUSH     EBP
016F:0040BC12 8B6C240C         MOV      EBP,[ESP+0C]    //將使用者名稱放入EBP
016F:0040BC16 56               PUSH     ESI
016F:0040BC17 8B742414         MOV      ESI,[ESP+14]    
016F:0040BC1B 57               PUSH     EDI             
016F:0040BC1C 8BD6             MOV      EDX,ESI
016F:0040BC1E 33C0             XOR      EAX,EAX
016F:0040BC20 8BFD             MOV      EDI,EBP
016F:0040BC22 2BD5             SUB      EDX,EBP
016F:0040BC24 8A0F             MOV      CL,[EDI]        //取一位使用者名稱
016F:0040BC26 84C9             TEST     CL,CL           //把所有使用者名稱都取完了?
016F:0040BC28 7410             JZ       0040BC3A        //是則跳走
016F:0040BC2A 8A5C2801         MOV      BL,[EAX+EBP+01] //取下一位位使用者名稱 
016F:0040BC2E 02D9             ADD      BL,CL           //將第兩位使用者名稱相加
016F:0040BC30 40               INC      EAX             //計數器EAX加一
016F:0040BC31 881C3A           MOV      [EDX+EDI],BL    //依次將結果放入[EDX+EDI] (其實就是放在ESI,看上面40BC1C-40BC22就知道了,注意EDI是計數器)
016F:0040BC34 47               INC      EDI             //計數器EDI加一 
016F:0040BC35 83F80A           CMP      EAX,BYTE +0A    
016F:0040BC38 7CEA             JL       0040BC24        //只計算十位使用者名稱
016F:0040BC3A 83F80A           CMP      EAX,BYTE +0A    //如果這裡是從40BC28跳來的,則會跳去40BC52進行後面幾位的計算
016F:0040BC3D 7D13             JNL      0040BC52        //若EAX>=A,則跳
016F:0040BC3F 8BCE             MOV      ECX,ESI         //ECX=ESI(上面計算的結果的地址放在這裡)
016F:0040BC41 8A5101           MOV      DL,[ECX+01]     //上面計算的一位結果依次放入DL
016F:0040BC44 8A19             MOV      BL,[ECX]        //後一位放入BL
016F:0040BC46 02D3             ADD      DL,BL           //DL=DL+BL
016F:0040BC48 881430           MOV      [EAX+ESI],DL    //逐個把計算結果放到前次計算結果的後面
016F:0040BC4B 40               INC      EAX             //計數器EAX加一
016F:0040BC4C 41               INC      ECX             //指標ECX加一
016F:0040BC4D 83F80A           CMP      EAX,BYTE +0A    //計算完十位了沒有?
016F:0040BC50 7CEF             JL       0040BC41        //是就繼續往下走
016F:0040BC52 33C9             XOR      ECX,ECX         //ECX清零
016F:0040BC54 BF05000000       MOV      EDI,05          //EDI=5
016F:0040BC59 33C0             XOR      EAX,EAX         //EAX清零
016F:0040BC5B 33D2             XOR      EDX,EDX         //EDX清零
016F:0040BC5D 8A0437           MOV      AL,[EDI+ESI]    //依次取出後五位的計算結果
016F:0040BC60 8A1431           MOV      DL,[ECX+ESI]    //依次取出前五位的計算結果
016F:0040BC63 03C2             ADD      EAX,EDX         //相加
016F:0040BC65 BB1A000000       MOV      EBX,1A          //EBX=1A
016F:0040BC6A 99               CDQ     
016F:0040BC6B F7FB             IDIV     EBX             //EAX=EAX\EDI,EDX=EAX/EDI的餘數
016F:0040BC6D 8D4701           LEA      EAX,[EDI+01]    //EAX=EDI+1
016F:0040BC70 BF0A000000       MOV      EDI,0A          //EDI=A
016F:0040BC75 80C261           ADD      DL,61           //EAX/1A的餘數加61(結果就是26個小寫字母的ASCII碼)
016F:0040BC78 881431           MOV      [ECX+ESI],DL    //依次將結果放回去
016F:0040BC7B 41               INC      ECX             //計數器ECX+1
016F:0040BC7C 99               CDQ     
016F:0040BC7D F7FF             IDIV     EDI             //EAX=EAX\EDI,EDX=EAX/EDI的餘數
016F:0040BC7F 83F90A           CMP      ECX,BYTE +0A    //計算完了嗎?
016F:0040BC82 8BFA             MOV      EDI,EDX         //EDI=EDX
016F:0040BC84 7CD3             JL       0040BC59        //十位註冊碼還沒計算完就再跳回去
016F:0040BC86 C6043100         MOV      BYTE [ECX+ESI],00  
016F:0040BC8A 5F               POP      EDI             //最終計算得的十位註冊碼就放在ESI!
016F:0040BC8B 5E               POP      ESI
016F:0040BC8C 5D               POP      EBP
016F:0040BC8D 5B               POP      EBX
016F:0040BC8E C3               RET     

/==================================\
| 附上支援中文使用者名稱的VB序號產生器原始碼 |
\==================================/

'我VB菜,程式碼寫得羅嗦,隨便大家笑去吧^_^!
Private Sub cmdCalc_Click()
On Error Resume Next

Dim i As Long, j As Long
Dim sn(9) As Long
Dim AscArray() As Byte

txtSerial.Text = ""

   If txtUserName.Text = "" Then
      txtSerial.Text = "請輸入使用者名稱"
      Exit Sub
   End If

AscArray = StrConv(txtUserName.Text, vbFromUnicode)
   
   If UBound(AscArray) = 0 Then
      txtSerial.Text = "使用者名稱必須大於一位"
      Exit Sub
   End If
   
For i = 0 To UBound(AscArray)
    sn(i) = AscArray(i)
Next i

If UBound(AscArray) < 9 Then
    
    For i = 0 To UBound(AscArray)
    sn(i) = (sn(i) + sn(i + 1)) Mod 256
    Next i
   
    For j = 0 To 9 - i
    sn(i) = (sn(j) + sn(j + 1)) Mod 256
    i = i + 1
    Next j

Else
    
    For i = 0 To UBound(AscArray)
    sn(i) = sn(i) + sn(i + 1)
    Next i

End If

j = 5
For i = 0 To 9
    sn(i) = ((((sn(i) + sn(j)) Mod 26) Mod 256) + 97) Mod 256
    j = (j + 1) Mod 10
Next i

For i = 0 To 9
txtSerial.Text = txtSerial.Text & Trim(Chr(sn(i)))
Next i
    
End Sub

相關文章