龍文輸入通演算法分析 (27千字)

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

軟體名稱:龍文輸入通  註冊版 Ver3.36  Build 2003年9月30日
型別:共享軟體
下載地址:www.inputsoft.com
簡介:龍文通用輸入法平臺是一個綜合性的、能夠滿足使用者多種輸入要求的軟體,它集中了眾多輸入法的優點和功能,使用者即可以掛接任意的形碼方案作為形碼輸入法,如五筆輸入,也可以用作拼音輸入法,拼音輸入支援字、詞、句間的無縫轉換,系統會根據使用者輸入的拼音由一定的演算法自動選出最可能的漢字,免去使用者逐字逐詞進行選擇的麻煩,提高了拼音輸入的效率。
限制:時間限制,到期後會有功能限制
工具;TRW2000娃娃修改版,OllyDbg 1.09c,W32Dasm,呵呵 還有windows記事本
宣告:初學Crack,只是感興趣,沒有其它目的。失誤之處敬請諸位大俠賜教!

*********************************************************
由於是輸入法,不可能用OllyDbg直接開啟跟蹤,想attach,居然在OllyDbg的程式視窗裡找不到該輸入法(高手一定在笑了‘SB啊,要是在程式裡看到輸入法就怪了’)。於是我就用了TRW2000,可在裡面d來d去的就是看不出什麼名堂(因為我是菜鳥嘛,俗話說的好“天下菜鳥是一家……”),還是回到了OllyDbg,畢竟OllyDbg是廣大菜鳥的最愛嘛。我先隨便開啟一個記事本,選輸入法為龍文輸入平臺,再在輸入法條上開啟註冊視窗,在OllyDbg的程式視窗裡赫然有了“龍文輸入平臺 系統設定與管理”的字樣,不過該程式是WINDOWS的NOTEPAD.EXE。沒關係用OllyDbg attach該程式後選擇名為lwsrf的可執行模組(該模組指向WINDOWS\SYSTEM或WINNT\SYSTEM32下的lwsrf.ime檔案,該檔案應該是Dll型別,是該輸入法安裝後留在系統目錄裡的,用W32Dasm開啟後會得到不少有用的提示),就會看到和TRW2000裡一模一樣的東西了。

*********************************************************
破解過程:
該軟體在保護上做了不少手腳,不光有較大的跳躍和垃圾似的計算,連在註冊視窗裡給出的一長串機器碼都是經過變化的假機器碼,難怪作者提示說獲取註冊碼時可以用複製-貼上的方法傳送機器碼。害的我走了不少彎路浪費不少時間,不過這樣的東西更值得一破!
軟體給出的我的機器碼:A177-8C79-9A8A-8084-3084-C631-A173-8339-9A8A-8084
試煉碼:A123-4B56-7C8D-9087-4567-1234 (根據試驗,註冊碼必須是6部分29位)

用OllyDbg在GetWindowTextA下斷
100278B0   FF15 24B30410    CALL DWORD PTR DS:[<&USER32.GetWindowTextA>]     斷在這
100278B6   8D7C24 18        LEA EDI,DWORD PTR SS:[ESP+18]
100278BA   83C9 FF          OR ECX,FFFFFFFF
100278BD   33C0             XOR EAX,EAX
100278BF   8D9424 40010000  LEA EDX,DWORD PTR SS:[ESP+140]
100278C6   F2:AE            REPNE SCAS BYTE PTR ES:[EDI]
100278C8   F7D1             NOT ECX
100278CA   2BF9             SUB EDI,ECX
100278CC   6A 00            PUSH 0
100278CE   8BC1             MOV EAX,ECX
100278D0   8BF7             MOV ESI,EDI
100278D2   8BFA             MOV EDI,EDX
100278D4   6A 00            PUSH 0
100278D6   C1E9 02          SHR ECX,2
100278D9   F3:A5            REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]
100278DB   8BC8             MOV ECX,EAX
100278DD   6A 01            PUSH 1
100278DF   83E1 03          AND ECX,3
100278E2   F3:A4            REP MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI]
100278E4   8D4C24 24        LEA ECX,DWORD PTR SS:[ESP+24]
100278E8   51               PUSH ECX
100278E9   E8 62F1FFFF      CALL LWSRF.10026A50                              很重要的CALL,跟入
100278EE   83C4 10          ADD ESP,10
100278F1   A3 2EB30510      MOV DWORD PTR DS:[1005B32E],EAX                  這EAX=0和下面對應
100278F6   85C0             TEST EAX,EAX
100278F8   75 2E            JNZ SHORT LWSRF.10027928
100278FA   8D5424 18        LEA EDX,DWORD PTR SS:[ESP+18]
100278FE   6A 23            PUSH 23
10027900   52               PUSH EDX
10027901   68 C2040000      PUSH 4C2
10027906   53               PUSH EBX
10027907   FFD5             CALL EBP
10027909   50               PUSH EAX
1002790A   FF15 24B30410    CALL DWORD PTR DS:[<&USER32.GetWindowTextA>]
10027910   6A 01            PUSH 1
10027912   6A 00            PUSH 0
10027914   8D4424 20        LEA EAX,DWORD PTR SS:[ESP+20]
10027918   6A 01            PUSH 1
1002791A   50               PUSH EAX
1002791B   E8 30F1FFFF      CALL LWSRF.10026A50
10027920   83C4 10          ADD ESP,10
10027923   A3 2EB30510      MOV DWORD PTR DS:[1005B32E],EAX                  這EAX=0和下面對應
10027928   8DBC24 40010000  LEA EDI,DWORD PTR SS:[ESP+140]
1002792F   83C9 FF          OR ECX,FFFFFFFF
10027932   33C0             XOR EAX,EAX
10027934   8D5424 18        LEA EDX,DWORD PTR SS:[ESP+18]
10027938   F2:AE            REPNE SCAS BYTE PTR ES:[EDI]
1002793A   F7D1             NOT ECX
1002793C   2BF9             SUB EDI,ECX
1002793E   8B1D 34B30410    MOV EBX,DWORD PTR DS:[<&USER32.LoadStringA>]
10027944   8BC1             MOV EAX,ECX
10027946   8BF7             MOV ESI,EDI
10027948   8BFA             MOV EDI,EDX
1002794A   8B15 F4830510    MOV EDX,DWORD PTR DS:[100583F4]                  LWSRF.10000000
10027950   C1E9 02          SHR ECX,2
10027953   F3:A5            REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]
10027955   8BC8             MOV ECX,EAX
10027957   6A 0A            PUSH 0A
10027959   83E1 03          AND ECX,3
1002795C   F3:A4            REP MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI]
1002795E   8D4C24 74        LEA ECX,DWORD PTR SS:[ESP+74]
10027962   51               PUSH ECX
10027963   68 06060000      PUSH 606
10027968   52               PUSH EDX
10027969   FFD3             CALL EBX
1002796B   BF 00A00510      MOV EDI,LWSRF.1005A000
10027970   83C9 FF          OR ECX,FFFFFFFF
10027973   33C0             XOR EAX,EAX
10027975   8D9424 40010000  LEA EDX,DWORD PTR SS:[ESP+140]
1002797C   F2:AE            REPNE SCAS BYTE PTR ES:[EDI]
1002797E   F7D1             NOT ECX
10027980   2BF9             SUB EDI,ECX
10027982   68 18270510      PUSH LWSRF.10052718
10027987   8BC1             MOV EAX,ECX
10027989   8BF7             MOV ESI,EDI
1002798B   8BFA             MOV EDI,EDX
1002798D   8D9424 44010000  LEA EDX,DWORD PTR SS:[ESP+144]
10027994   C1E9 02          SHR ECX,2
10027997   F3:A5            REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]
10027999   8BC8             MOV ECX,EAX
1002799B   33C0             XOR EAX,EAX
1002799D   83E1 03          AND ECX,3
100279A0   F3:A4            REP MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI]
100279A2   8D7C24 74        LEA EDI,DWORD PTR SS:[ESP+74]
100279A6   83C9 FF          OR ECX,FFFFFFFF
100279A9   F2:AE            REPNE SCAS BYTE PTR ES:[EDI]
100279AB   F7D1             NOT ECX
100279AD   2BF9             SUB EDI,ECX
100279AF   8BF7             MOV ESI,EDI
100279B1   8BE9             MOV EBP,ECX
100279B3   8BFA             MOV EDI,EDX
100279B5   83C9 FF          OR ECX,FFFFFFFF
100279B8   F2:AE            REPNE SCAS BYTE PTR ES:[EDI]
100279BA   8BCD             MOV ECX,EBP
100279BC   4F               DEC EDI
100279BD   C1E9 02          SHR ECX,2
100279C0   F3:A5            REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]
100279C2   8BCD             MOV ECX,EBP
100279C4   8D8424 44010000  LEA EAX,DWORD PTR SS:[ESP+144]
100279CB   83E1 03          AND ECX,3
100279CE   50               PUSH EAX
100279CF   F3:A4            REP MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI]
100279D1   E8 1FC60100      CALL LWSRF.10043FF5
100279D6   8BF0             MOV ESI,EAX
100279D8   83C4 08          ADD ESP,8
100279DB   85F6             TEST ESI,ESI
100279DD   74 14            JE SHORT LWSRF.100279F3
100279DF   8D4C24 18        LEA ECX,DWORD PTR SS:[ESP+18]
100279E3   56               PUSH ESI
100279E4   51               PUSH ECX
100279E5   E8 12CB0100      CALL LWSRF.100444FC
100279EA   56               PUSH ESI
100279EB   E8 75C50100      CALL LWSRF.10043F65
100279F0   83C4 0C          ADD ESP,0C
100279F3   A1 F4830510      MOV EAX,DWORD PTR DS:[100583F4]
100279F8   8D9424 2C010000  LEA EDX,DWORD PTR SS:[ESP+12C]
100279FF   6A 14            PUSH 14
10027A01   52               PUSH EDX
10027A02   68 06060000      PUSH 606
10027A07   50               PUSH EAX
10027A08   FFD3             CALL EBX
10027A0A   8D4C24 10        LEA ECX,DWORD PTR SS:[ESP+10]
10027A0E   51               PUSH ECX
10027A0F   68 02000080      PUSH 80000002
10027A14   E8 27C3FEFF      CALL LWSRF.10013D40
10027A19   83C4 08          ADD ESP,8
10027A1C   85C0             TEST EAX,EAX
10027A1E   74 15            JE SHORT LWSRF.10027A35
10027A20   8D5424 10        LEA EDX,DWORD PTR SS:[ESP+10]
10027A24   52               PUSH EDX
10027A25   68 C8E40410      PUSH LWSRF.1004E4C8                              ASCII "Software\Microsoft\Windows\CurrentVersion"
10027A2A   68 02000080      PUSH 80000002
10027A2F   FF15 08B00410    CALL DWORD PTR DS:[<&ADVAPI32.RegCreateKeyA>]
10027A35   8B4C24 10        MOV ECX,DWORD PTR SS:[ESP+10]
10027A39   8D4424 14        LEA EAX,DWORD PTR SS:[ESP+14]
10027A3D   6A 00            PUSH 0
10027A3F   50               PUSH EAX
10027A40   6A 00            PUSH 0
10027A42   68 3F000F00      PUSH 0F003F
10027A47   6A 00            PUSH 0
10027A49   6A 00            PUSH 0
10027A4B   6A 00            PUSH 0
10027A4D   68 60DA0510      PUSH LWSRF.1005DA60
10027A52   51               PUSH ECX
10027A53   FF15 0CB00410    CALL DWORD PTR DS:[<&ADVAPI32.RegCreateKeyExA>]
10027A59   8D7C24 18        LEA EDI,DWORD PTR SS:[ESP+18]
10027A5D   83C9 FF          OR ECX,FFFFFFFF
10027A60   33C0             XOR EAX,EAX
10027A62   8D5424 18        LEA EDX,DWORD PTR SS:[ESP+18]
10027A66   F2:AE            REPNE SCAS BYTE PTR ES:[EDI]
10027A68   F7D1             NOT ECX
10027A6A   51               PUSH ECX
10027A6B   8B4C24 18        MOV ECX,DWORD PTR SS:[ESP+18]
10027A6F   52               PUSH EDX
10027A70   6A 03            PUSH 3
10027A72   50               PUSH EAX
10027A73   8D8424 3C010000  LEA EAX,DWORD PTR SS:[ESP+13C]
10027A7A   50               PUSH EAX
10027A7B   51               PUSH ECX
10027A7C   FF15 14B00410    CALL DWORD PTR DS:[<&ADVAPI32.RegSetValueExA>]
10027A82   8B35 18B00410    MOV ESI,DWORD PTR DS:[<&ADVAPI32.RegCloseKey>]
10027A88   8B5424 14        MOV EDX,DWORD PTR SS:[ESP+14]
10027A8C   52               PUSH EDX
10027A8D   FFD6             CALL ESI
10027A8F   8B4424 10        MOV EAX,DWORD PTR SS:[ESP+10]
10027A93   50               PUSH EAX
10027A94   FFD6             CALL ESI
10027A96   8B15 F4830510    MOV EDX,DWORD PTR DS:[100583F4]                  LWSRF.10000000
10027A9C   8D8C24 40010000  LEA ECX,DWORD PTR SS:[ESP+140]
10027AA3   68 C8000000      PUSH 0C8
10027AA8   51               PUSH ECX
10027AA9   68 03060000      PUSH 603
10027AAE   52               PUSH EDX
10027AAF   FFD3             CALL EBX
10027AB1   8B0D F4830510    MOV ECX,DWORD PTR DS:[100583F4]                  LWSRF.10000000
10027AB7   8D4424 70        LEA EAX,DWORD PTR SS:[ESP+70]
10027ABB   6A 78            PUSH 78
10027ABD   50               PUSH EAX
10027ABE   68 04060000      PUSH 604
10027AC3   51               PUSH ECX
10027AC4   FFD3             CALL EBX
10027AC6   A1 F4830510      MOV EAX,DWORD PTR DS:[100583F4]
10027ACB   8D9424 E8000000  LEA EDX,DWORD PTR SS:[ESP+E8]
10027AD2   6A 14            PUSH 14
10027AD4   52               PUSH EDX
10027AD5   68 05060000      PUSH 605
10027ADA   50               PUSH EAX
10027ADB   FFD3             CALL EBX
10027ADD   A1 2EB30510      MOV EAX,DWORD PTR DS:[1005B32E]                  就是這讓EAX=0
10027AE2   6A 00            PUSH 0
10027AE4   85C0             TEST EAX,EAX                                    以EAX為標誌
10027AE6   74 27            JE SHORT LWSRF.10027B0F                         如果是0就彈出錯誤提示
10027AE8   8D8C24 EC000000  LEA ECX,DWORD PTR SS:[ESP+EC]
10027AEF   8D5424 74        LEA EDX,DWORD PTR SS:[ESP+74]
10027AF3   51               PUSH ECX
10027AF4   52               PUSH EDX
10027AF5   6A 00            PUSH 0
10027AF7   FF15 50B30410    CALL DWORD PTR DS:[<&USER32.MessageBoxA>]        註冊成功提示
10027AFD   5F               POP EDI
10027AFE   5E               POP ESI
10027AFF   5D               POP EBP
10027B00   B8 01000000      MOV EAX,1
10027B05   5B               POP EBX
10027B06   81C4 D8020000    ADD ESP,2D8
10027B0C   C2 1000          RETN 10
10027B0F   8D8424 EC000000  LEA EAX,DWORD PTR SS:[ESP+EC]
10027B16   8D8C24 44010000  LEA ECX,DWORD PTR SS:[ESP+144]
10027B1D   50               PUSH EAX
10027B1E   51               PUSH ECX
10027B1F   6A 00            PUSH 0
10027B21   FF15 50B30410    CALL DWORD PTR DS:[<&USER32.MessageBoxA>]        ;註冊失敗提示
10027B27   5F               POP EDI
10027B28   5E               POP ESI
10027B29   5D               POP EBP
10027B2A   B8 01000000      MOV EAX,1
10027B2F   5B               POP EBX
10027B30   81C4 D8020000    ADD ESP,2D8
10027B36   C2 1000          RETN 10


由100278E9處的CALL LWSRF.10026A50 進入到此:
10026A50   83EC 6C          SUB ESP,6C
10026A53   8B0D F4830510    MOV ECX,DWORD PTR DS:[100583F4]                  LWSRF.10000000
10026A59   8D4424 34        LEA EAX,DWORD PTR SS:[ESP+34]
10026A5D   53               PUSH EBX
10026A5E   55               PUSH EBP
10026A5F   56               PUSH ESI
10026A60   57               PUSH EDI
10026A61   6A 0A            PUSH 0A
10026A63   50               PUSH EAX
10026A64   68 0B060000      PUSH 60B
10026A69   51               PUSH ECX
10026A6A   FF15 34B30410    CALL DWORD PTR DS:[<&USER32.LoadStringA>]
10026A70   8BB424 84000000  MOV ESI,DWORD PTR SS:[ESP+84]
10026A77   33DB             XOR EBX,EBX
10026A79   3BF3             CMP ESI,EBX
10026A7B   74 09            JE SHORT LWSRF.10026A86
10026A7D   8B15 684D0510    MOV EDX,DWORD PTR DS:[10054D68]
10026A83   895A 18          MOV DWORD PTR DS:[EDX+18],EBX
10026A86   53               PUSH EBX
10026A87   68 00040000      PUSH 400
10026A8C   6A 01            PUSH 1
10026A8E   FF15 C4B10410    CALL DWORD PTR DS:[<&KERNEL32.HeapCreate>]
10026A94   6A 64            PUSH 64
10026A96   6A 08            PUSH 8
10026A98   50               PUSH EAX
10026A99   894424 20        MOV DWORD PTR SS:[ESP+20],EAX
10026A9D   FF15 DCB10410    CALL DWORD PTR DS:[<&KERNEL32.HeapAlloc>]
10026AA3   8BE8             MOV EBP,EAX
10026AA5   33C0             XOR EAX,EAX
10026AA7   898424 8C000000  MOV DWORD PTR SS:[ESP+8C],EAX
10026AAE   8B0D 684D0510    MOV ECX,DWORD PTR DS:[10054D68]                第1次註冊碼檢驗錯誤後就會跳到這裡,而後進行一些看上去眼花繚亂的計算,但命運終歸是死亡
10026AB4   8D0440           LEA EAX,DWORD PTR DS:[EAX+EAX*2]
10026AB7   C1E0 02          SHL EAX,2
10026ABA   894424 24        MOV DWORD PTR SS:[ESP+24],EAX
10026ABE   8D5408 20        LEA EDX,DWORD PTR DS:[EAX+ECX+20]
10026AC2   8BC5             MOV EAX,EBP
10026AC4   8B0A             MOV ECX,DWORD PTR DS:[EDX]                       ECX=73865E8C
10026AC6   8908             MOV DWORD PTR DS:[EAX],ECX                       EAX->[0148F00C]=73865E8C
10026AC8   8B4A 04          MOV ECX,DWORD PTR DS:[EDX+4]                     ECX=7F7B6575
10026ACB   8948 04          MOV DWORD PTR DS:[EAX+4],ECX                     [0148F010]=7F7B6575
10026ACE   B9 06000000      MOV ECX,6
10026AD3   8B52 08          MOV EDX,DWORD PTR DS:[EDX+8]                     EDX=C9CECF7B
10026AD6   8950 08          MOV DWORD PTR DS:[EAX+8],EDX                     [0148F014]=C9CECF7B
10026AD9   895C24 10        MOV DWORD PTR SS:[ESP+10],EBX
10026ADD   66:8B10          MOV DX,WORD PTR DS:[EAX]              \          
10026AE0   83C0 02          ADD EAX,2                             |
10026AE3   66:F7D2          NOT DX                                |          
10026AE6   66:8950 FE       MOV WORD PTR DS:[EAX-2],DX            |
10026AEA   49               DEC ECX                               |         這個迴圈得到真正得機器碼:A173-8C79-9A8A-8084-3084-3631
10026AEB  ^75 F0            JNZ SHORT LWSRF.10026ADD              /
10026AED   3BF3             CMP ESI,EBX
10026AEF   0F84 E5000000    JE LWSRF.10026BDA
10026AF5   33C0             XOR EAX,EAX
10026AF7   899C24 84000000  MOV DWORD PTR SS:[ESP+84],EBX
10026AFE   66:8B45 00       MOV AX,WORD PTR SS:[EBP]
10026B02   C1E0 05          SHL EAX,5                                        EAX=A173 SHL 5=00142E60
                           .
                           .
                           .
                           .
                           .
                           .
10026E86   0F85 61010000    JNZ LWSRF.10026FED                              上面省略的一段都是一堆垃圾,把個機器碼變來變去的,耍花招呢,不用怕,就在下面又還機器碼真實面目
10026E8C   8B0D 684D0510    MOV ECX,DWORD PTR DS:[10054D68]                  ECX=83B8B000下面這段又重新得到機器碼,並進行計算
10026E92   884424 2C        MOV BYTE PTR SS:[ESP+2C],AL
10026E96   8B4424 24        MOV EAX,DWORD PTR SS:[ESP+24]
10026E9A   8D4C08 20        LEA ECX,DWORD PTR DS:[EAX+ECX+20]                ECX=83B8B020
10026E9E   8BC5             MOV EAX,EBP
10026EA0   8B31             MOV ESI,DWORD PTR DS:[ECX]                       ESI=73865E8C
10026EA2   8930             MOV DWORD PTR DS:[EAX],ESI
10026EA4   8B71 04          MOV ESI,DWORD PTR DS:[ECX+4]                     ESI=7F7B6575
10026EA7   8970 04          MOV DWORD PTR DS:[EAX+4],ESI
10026EAA   8B49 08          MOV ECX,DWORD PTR DS:[ECX+8]                     ECX=C9CECF7B
10026EAD   8948 08          MOV DWORD PTR DS:[EAX+8],ECX
10026EB0   33C9             XOR ECX,ECX
10026EB2  >66:8B444D 00     MOV AX,WORD PTR SS:[EBP+ECX*2]         \          
10026EB7   66:F7D0          NOT AX                                 |         
10026EBA   66:89444D 00     MOV WORD PTR SS:[EBP+ECX*2],AX         |
10026EBF   25 FFFF0000      AND EAX,0FFFF                          |
10026EC4   03D8             ADD EBX,EAX                            |
10026EC6   83F9 03          CMP ECX,3                              |                                   
10026EC9   75 03            JNZ SHORT LWSRF.10026ECE               |
10026ECB   8D1C43           LEA EBX,DWORD PTR DS:[EBX+EAX*2]       |
10026ECE   41               INC ECX                                |          這個迴圈把真機器碼的6個部分
10026ECF   83F9 06          CMP ECX,6                              |          按①+②+③+④+④*2+⑤+⑥的式子計算得3B0B7
10026ED2  ^7C DE            JL SHORT LWSRF.10026EB2                /
10026ED4   33F6             XOR ESI,ESI
10026ED6   8BFA             MOV EDI,EDX
10026ED8   89AC24 84000000  MOV DWORD PTR SS:[ESP+84],EBP                  
10026EDF   83FE 06          CMP ESI,6                                \     
10026EE2   0F8D 49010000    JGE LWSRF.10027031                       |
10026EE8   85F6             TEST ESI,ESI                             |
10026EEA   7D 27            JGE SHORT LWSRF.10026F13                 |
10026EEC   8B8424 84000000  MOV EAX,DWORD PTR SS:[ESP+84]            |
10026EF3   33D2             XOR EDX,EDX                              |
10026EF5   8BC8             MOV ECX,EAX                              |
10026EF7   66:8B10          MOV DX,WORD PTR DS:[EAX]                 |
10026EFA   83C1 02          ADD ECX,2
10026EFD   0FAFD6           IMUL EDX,ESI
10026F00   D1E2             SHL EDX,1                                |
10026F02   46               INC ESI
10026F03   895424 10        MOV DWORD PTR SS:[ESP+10],EDX            |
10026F07   898C24 84000000  MOV DWORD PTR SS:[ESP+84],ECX
10026F0E   83C7 05          ADD EDI,5
10026F11  ^EB CC            JMP SHORT LWSRF.10026EDF                 |
10026F13   8B0F             MOV ECX,DWORD PTR DS:[EDI]                      
10026F15   8D5424 10        LEA EDX,DWORD PTR SS:[ESP+10]            |
10026F19   52               PUSH EDX
10026F1A   8D4424 2C        LEA EAX,DWORD PTR SS:[ESP+2C]            |      
10026F1E   68 98E60410      PUSH LWSRF.1004E698                              ASCII "%lx"
10026F23   50               PUSH EAX
10026F24   C64424 38 00     MOV BYTE PTR SS:[ESP+38],0
10026F29   894C24 34        MOV DWORD PTR SS:[ESP+34],ECX            |
10026F2D   E8 2AD20100      CALL LWSRF.1004415C
10026F32   83C4 0C          ADD ESP,0C                               |
10026F35   83FE 05          CMP ESI,5
10026F38   7D 1D            JGE SHORT LWSRF.10026F57
10026F3A   8B4424 10        MOV EAX,DWORD PTR SS:[ESP+10]            |
10026F3E   8B8C24 84000000  MOV ECX,DWORD PTR SS:[ESP+84]
10026F45   03D8             ADD EBX,EAX                              |       EBX=3B0B7+A123=451DA+4B56=49D30+7C8D=519BD+9087=5AA44+4567=5EFAB
10026F47   83C1 02          ADD ECX,2                                |       EBX=7FFF8+A123=8A11B+4B56=8EC71+7C8D=968FE+9087=9F985+4567=A3EEC
10026F4A   46               INC ESI                                  |
10026F4B   898C24 84000000  MOV DWORD PTR SS:[ESP+84],ECX            |
10026F52   83C7 05          ADD EDI,5                                |       這個迴圈是把上面得到的3B0B7依次加上假碼的每一部分
10026F55  ^EB 88            JMP SHORT LWSRF.10026EDF                 /       結果放在EBX中
10026F57   8B4424 10        MOV EAX,DWORD PTR SS:[ESP+10]                    把假碼的最後一部分放入EAX
10026F5B   81E3 FFFF0000    AND EBX,0FFFF                                    取結果的後兩位元組EBX=EFAB
10026F61   25 FFFF0000      AND EAX,0FFFF                                    與假碼的最後一部分比較
10026F66   3BC3             CMP EAX,EBX                                     在這裡用記憶體序號產生器中斷,取得暫存器EBX的值,就應該是真碼的最後一部分
10026F68   894424 10        MOV DWORD PTR SS:[ESP+10],EAX
10026F6C   75 1A            JNZ SHORT LWSRF.10026F88                        相等就不跳,跳就完蛋!
10026F6E   8B8C24 84000000  MOV ECX,DWORD PTR SS:[ESP+84]                   可見我的正確註冊碼的最後一部分應該等於EFAB,即A123-4B56-7C8D-9087-4567-EFAB
10026F75   46               INC ESI
10026F76   83C1 02          ADD ECX,2
10026F79   83C7 05          ADD EDI,5
10026F7C   898C24 84000000  MOV DWORD PTR SS:[ESP+84],ECX
10026F83  ^E9 57FFFFFF      JMP LWSRF.10026EDF
10026F88   8B8424 8C000000  MOV EAX,DWORD PTR SS:[ESP+8C]
10026F8F   85C0             TEST EAX,EAX
10026F91   75 7C            JNZ SHORT LWSRF.1002700F
10026F93   C78424 8C000000 >MOV DWORD PTR SS:[ESP+8C],1
10026F9E   83CE FF          OR ESI,FFFFFFFF
10026FA1   8B8424 8C000000  MOV EAX,DWORD PTR SS:[ESP+8C]
10026FA8   33DB             XOR EBX,EBX
10026FAA  ^E9 FFFAFFFF      JMP LWSRF.10026AAE                                如果上面跳了的話,這裡就再跳到最前面算出一些很奇怪的值來,反正是死路一條
10026FAF   8D7C24 58        LEA EDI,DWORD PTR SS:[ESP+58]
10026FB3   83C9 FF          OR ECX,FFFFFFFF
10026FB6   33C0             XOR EAX,EAX
10026FB8   F2:AE            REPNE SCAS BYTE PTR ES:[EDI]
10026FBA   F7D1             NOT ECX
10026FBC   2BF9             SUB EDI,ECX
10026FBE   8B4424 14        MOV EAX,DWORD PTR SS:[ESP+14]
10026FC2   8BD1             MOV EDX,ECX
10026FC4   8BF7             MOV ESI,EDI
10026FC6   8BBC24 80000000  MOV EDI,DWORD PTR SS:[ESP+80]
10026FCD   50               PUSH EAX
10026FCE   C1E9 02          SHR ECX,2
10026FD1   F3:A5            REP MOVS DWORD PTR ES:[EDI],DWORD PTR DS:[ESI]
10026FD3   8BCA             MOV ECX,EDX
10026FD5   83E1 03          AND ECX,3
10026FD8   F3:A4            REP MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI]
10026FDA   FF15 C8B10410    CALL DWORD PTR DS:[<&KERNEL32.HeapDestroy>]
10026FE0   5F               POP EDI
10026FE1   5E               POP ESI
10026FE2   5D               POP EBP
10026FE3   B8 01000000      MOV EAX,1
10026FE8   5B               POP EBX
10026FE9   83C4 6C          ADD ESP,6C
10026FEC   C3               RETN
10026FED   8B4C24 14        MOV ECX,DWORD PTR SS:[ESP+14]
10026FF1   51               PUSH ECX
10026FF2   FF15 C8B10410    CALL DWORD PTR DS:[<&KERNEL32.HeapDestroy>]
10026FF8   8B15 684D0510    MOV EDX,DWORD PTR DS:[10054D68]
10026FFE   5F               POP EDI
10026FFF   5E               POP ESI
10027000   5D               POP EBP
10027001   C742 18 00000000 MOV DWORD PTR DS:[EDX+18],0
10027008   33C0             XOR EAX,EAX
1002700A   5B               POP EBX
1002700B   83C4 6C          ADD ESP,6C
1002700E   C3               RETN
1002700F   8B4424 14        MOV EAX,DWORD PTR SS:[ESP+14]
10027013   50               PUSH EAX
10027014   FF15 C8B10410    CALL DWORD PTR DS:[<&KERNEL32.HeapDestroy>]
1002701A   8B0D 684D0510    MOV ECX,DWORD PTR DS:[10054D68]
10027020   5F               POP EDI
10027021   5E               POP ESI
10027022   5D               POP EBP
10027023   C741 18 00000000 MOV DWORD PTR DS:[ECX+18],0
1002702A   33C0             XOR EAX,EAX
1002702C   5B               POP EBX
1002702D   83C4 6C          ADD ESP,6C
10027030   C3               RETN
10027031   8B15 684D0510    MOV EDX,DWORD PTR DS:[10054D68]
10027037   8B4C24 14        MOV ECX,DWORD PTR SS:[ESP+14]
1002703B   51               PUSH ECX
1002703C   C742 18 01000000 MOV DWORD PTR DS:[EDX+18],1
10027043   A1 684D0510      MOV EAX,DWORD PTR DS:[10054D68]
10027048   66:C740 50 BC00  MOV WORD PTR DS:[EAX+50],0BC
1002704E   FF15 C8B10410    CALL DWORD PTR DS:[<&KERNEL32.HeapDestroy>]
10027054   5F               POP EDI
10027055   5E               POP ESI
10027056   5D               POP EBP
10027057   B8 01000000      MOV EAX,1
1002705C   5B               POP EBX
1002705D   83C4 6C          ADD ESP,6C
10027060   C3               RETN
***********************************************************************
演算法總結:
    軟體的演算法本身沒什麼新意,但加了不少沒用的東西掩人耳目,基本演算法為:真機器碼的6個部分(不包含'-')按①+②+③+④+④*2+⑤+⑥求和(是直接作為16進位制相加),再用這個和依次累加註冊碼的前5部分(不包含'-'),設累加結果為SUM(也是直接作為16進位制相加),最後檢驗註冊碼最後一部分即第6部分是否等於SUM,等於就成功,不等於就跳死。
假機器碼的由來:
    軟體在啟動註冊視窗時得到真機器碼,把它的前4部分接到它自己的屁股後面去,再經過下面的變換得到假的也就是顯示在註冊視窗上的機器碼
10027429   F3:A4            REP MOVS BYTE PTR ES:[EDI],BYTE PTR DS:[ESI>
1002742B   8A8424 8F000000  MOV AL,BYTE PTR SS:[ESP+8F]
10027432   8A4C24 71        MOV CL,BYTE PTR SS:[ESP+71]
10027436   8A9424 89000000  MOV DL,BYTE PTR SS:[ESP+89]
1002743D   884424 71        MOV BYTE PTR SS:[ESP+71],AL
10027441   8A8424 94000000  MOV AL,BYTE PTR SS:[ESP+94]
10027448   888C24 8F000000  MOV BYTE PTR SS:[ESP+8F],CL
1002744F   8A8C24 86000000  MOV CL,BYTE PTR SS:[ESP+86]
10027456   888424 89000000  MOV BYTE PTR SS:[ESP+89],AL
1002745D   8A8424 9F000000  MOV AL,BYTE PTR SS:[ESP+9F]
10027464   889424 94000000  MOV BYTE PTR SS:[ESP+94],DL
1002746B   8A9424 95000000  MOV DL,BYTE PTR SS:[ESP+95]
10027472   888424 86000000  MOV BYTE PTR SS:[ESP+86],AL
10027479   8A4424 73        MOV AL,BYTE PTR SS:[ESP+73]
1002747D   888C24 9F000000  MOV BYTE PTR SS:[ESP+9F],CL
10027484   888424 95000000  MOV BYTE PTR SS:[ESP+95],AL
1002748B   8D4424 70        LEA EAX,DWORD PTR SS:[ESP+70]
如:我的真機器碼是A173-8C79-9A8A-8084-3084-3631,把前4部分接到後面得:A173-8C79-9A8A-8084-3084-3631-A173-8C79-9A8A-8084,經變換後得到的假機器碼為A177-8C79-9A8A-8084-3084-C631-A173-8339-9A8A-8084
我大致看了一下好象是做了下面的對掉:
                  第2位<---->第32位
                  第4位<---->第38位
                 第23位<---->第48位
                 第26位<---->第37位
我數的不是太仔細,有興趣的可以自己看看,不對的地方還請指正 :P
    註冊碼不管對錯都以二進位制儲存在登錄檔“HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\龍文輸入法”的“註冊碼”主鍵下
軟體還在“HKEY_LOCAL_MACHINE\SOFTWARE\Zlocksoft\Zlock20020630”下寫了“Name”“Serial”和“Version”3個主鍵,我沒看懂什麼意思,可能是用來判斷是否過期的吧,哪位知道請告訴我哦
**********************************************************
記憶體序號產生器:with keymake1.73

           程式名:  NOTEPAD.EXE
           中斷地址:10026F66
           中斷次數:1   
           第1位元組: 3B
           指令長度:2位元組

           暫存器方式
           EBX   十六進位制

使用方法:把序號產生器放在WINDOWS或WINNT目錄下,執行後在出現的記事本上選出龍文輸入平臺輸入法,開啟它的註冊視窗,填好註冊碼(必須是29位6部分,以'-'分隔,每部分4位),點註冊,斷下後在序號產生器上看到的數可能是重複的兩部分,如EFABEFAB,取其中的一部分(4位,不足4位在前面加0),就是你註冊碼的最後一部分,如果不是重複的兩部分,就取其前4位,也應該是你註冊碼的最後一部分。為什麼可能重複也可能不重複我也說不清楚,在OllyDbg跟蹤時明明看到斷後EBX只有兩個低位位元組,可用記憶體序號產生器斷後看到的就不只兩位,還請哪位大哥指教 :)

呵,終於寫完了,可以睡覺了。我的上一篇破文居然引的軟體作者跑到論壇上來和我理論,希望這篇不要再引的作者來,不然我可睡不好覺哦 ^_^

              
                                                                   thl0057 
                                                               2003/10/25 凌晨 於 HD

相關文章