カスペルスキークラックミーのハッキング:防衛メカニズムの調査(パート1)

最近、Kaspersky Labが開催したZeroNight2015リバースエンジニアリングコンテストは終了しました。 私の意見では、コンテストの組織は不十分でしたが、記事はそれについてではありません。 「スマートフォン」と呼ばれるコンペティションで興味深いタスクが発表されました。この分析では、このシリーズの記事が取り上げられます。 この記事では、問題の状態の説明と保護メカニズムの検索に専念します。 2番目の記事では、Xコードの実装によるハッキングされたプログラムの速度の最適化について説明します。 3番目の記事では、単体テストを使用して埋め込みコードのエラーを見つけるプロセスについて説明します。



問題の説明から始めましょう。 次の割り当ての説明と.exeプログラムファイルをダウンロードする機能は、コンテストのWebサイトで提供されます。







プログラムを開始すると、メールとシリアル番号の入力を求めるウィンドウが表示されます。







タスクは、自分のメールアドレスのシリアル番号を見つけることです。 問題を解決した後、サイトのフォームを使用して確認のためにシリアル番号が送信されます。このフォームには、評価に表示される独自の電子メールとニックネームが以前に示されています。







crackmeにランダムなシリアル番号を入力した後、プログラムは私のコンピューターが遅すぎることを警告し、チェックの結果を待つ前に老化する時間があります。 警告メッセージが閉じられた後、プログラムは絶望的にフリーズし、プロセッサの1つのコアを最大限にロードします。







シリアル番号をチェックした結果を待つことは失敗する運命にあり、プログラムを強制的に終了するだけです。 これは、部分的にこのタスクの一意性です。 このコンテストの他のタスクでは、検証の結果がすぐに表示されます。 たとえば、「クレジットカード」タスクでは、次のように表示されます。







ハッキングされたプログラムの内部に入り込んで、正確に何が起こっているのか、なぜハングしたのか、そして私たちに期待するシリアル番号を把握する時が来ました。 これらの目的のために、IDA Pro対話型逆アセンブラーを使用します。デモ版は、 hex-rays Webサイトからダウンロードできます。



保護メカニズムの検索を開始するには、「この操作ではコンピューターが非常に遅い!」というメッセージを表示してウィンドウを呼び出す関数の呼び出しを相互参照します。 結果を取得すると、灰色のひげになります... ;-) "、" "チェック"ボタンをクリックするとすぐに表示されます。 これを行うには、[インポート]タブを開き、USER32ライブラリからMessageBoxW関数を見つけます。







これをダブルクリックして、インポートテーブルで関数を定義します。 次に、相互参照のリストを開きます(ホットキー<x>)。







リストの最後の3つの要素が最初の要素を複製するため、リストから最初の3つの相互参照をチェックするだけで十分です。 最初の2つの呼び出しは、見出し「Internal Error:」でmessageBoxを呼び出すコードのセクションにつながります。 明らかに、これはいくつかの内部エラーに関するメッセージの出力であり、そこには行かないほうがよいでしょう。



.text:004010A4
.text:00401090 push ebp .text:00401091 mov ebp, esp .text:00401093 mov eax, [ebp+8] .text:00401096 test eax, eax .text:00401098 jz short loc_4010AA .text:0040109A push 10h .text:0040109C push offset aInternalError ; "Internal Error:" .text:004010A1 push eax .text:004010A2 push 0 .text:004010A4 call ds:MessageBoxW
      
      







sub_4010B0 + 14
 .text:004010B0 push ebp .text:004010B1 mov ebp, esp .text:004010B3 mov eax, [ebp+lpText] .text:004010B6 test eax, eax .text:004010B8 jz short loc_4010CA .text:004010BA push 10h ; uType .text:004010BC push offset aInternalError ; "Internal Error:" .text:004010C1 push eax ; lpText .text:004010C2 push 0 ; hWnd .text:004010C4 call ds:MessageBoxW
      
      







3番目の相互参照は、ヘッダーパラメーター「警告」と「コンピューターが非常に遅い....」というメッセージを含む目的の関数呼び出しにつながります。



 .text:00404E98 push ebx .text:00404E99 push offset Caption ; "Warning!" .text:00404E9E push offset Text ; "Your computer is extremely slow for thi"... .text:00404EA3 push ebx ; hWnd .text:00404EA4 call ds:MessageBoxW
      
      





これは、警告メッセージボックスが呼び出される場所です。 呼び出しは、sub_404E50関数から行われます。



sub_404E50
 .text:00404E50 .text:00404E50 sub_404E50 proc near ; CODE XREF: sub_401340+1C5 .text:00404E50 .text:00404E50 var_104 = dword ptr -104h .text:00404E50 var_100 = byte ptr -100h .text:00404E50 var_A8 = dword ptr -0A8h .text:00404E50 var_A4 = byte ptr -0A4h .text:00404E50 var_58 = byte ptr -58h .text:00404E50 var_57 = byte ptr -57h .text:00404E50 var_24 = byte ptr -24h .text:00404E50 var_23 = dword ptr -23h .text:00404E50 var_1F = dword ptr -1Fh .text:00404E50 var_1B = dword ptr -1Bh .text:00404E50 var_17 = word ptr -17h .text:00404E50 var_15 = byte ptr -15h .text:00404E50 var_14 = byte ptr -14h .text:00404E50 var_13 = dword ptr -13h .text:00404E50 var_F = dword ptr -0Fh .text:00404E50 var_B = dword ptr -0Bh .text:00404E50 var_7 = word ptr -7 .text:00404E50 var_5 = byte ptr -5 .text:00404E50 var_4 = dword ptr -4 .text:00404E50 arg_0 = dword ptr 8 .text:00404E50 arg_4 = dword ptr 0Ch .text:00404E50 arg_8 = dword ptr 10h .text:00404E50 arg_C = dword ptr 14h .text:00404E50 .text:00404E50 push ebp .text:00404E51 mov ebp, esp .text:00404E53 sub esp, 104h .text:00404E59 mov eax, ___security_cookie .text:00404E5E xor eax, ebp .text:00404E60 mov [ebp+var_4], eax .text:00404E63 mov eax, [ebp+arg_8] .text:00404E66 push ebx .text:00404E67 push esi .text:00404E68 mov esi, [ebp+arg_0] .text:00404E6B xor ebx, ebx .text:00404E6D push edi .text:00404E6E mov [ebp+var_104], eax .text:00404E74 cmp esi, ebx .text:00404E76 jz loc_404FBE .text:00404E7C mov edi, [ebp+arg_4] .text:00404E7F cmp edi, ebx .text:00404E81 jz loc_404FBE .text:00404E87 cmp eax, ebx .text:00404E89 jz loc_404FBE .text:00404E8F cmp [ebp+arg_C], ebx .text:00404E92 jz loc_404FBE .text:00404E98 push ebx ; uType .text:00404E99 push offset Caption ; "Warning!" .text:00404E9E push offset Text ; "Your computer is extremely slow for thi"... .text:00404EA3 push ebx ; hWnd .text:00404EA4 call ds:MessageBoxW .text:00404EAA push 4Ch ; size_t .text:00404EAC lea eax, [ebp+var_A4] .text:00404EB2 push ebx ; int .text:00404EB3 push eax ; void * .text:00404EB4 mov [ebp+var_A8], ebx .text:00404EBA call _memset .text:00404EBF push 31h ; size_t .text:00404EC1 lea ecx, [ebp+var_57] .text:00404EC4 push ebx ; int .text:00404EC5 push ecx ; void * .text:00404EC6 mov [ebp+var_58], bl .text:00404EC9 call _memset .text:00404ECE lea edx, [ebp+var_A8] .text:00404ED4 push edx .text:00404ED5 call sub_4047C0 .text:00404EDA xor eax, eax .text:00404EDC mov [ebp+var_13], eax .text:00404EDF mov [ebp+var_F], eax .text:00404EE2 mov [ebp+var_B], eax .text:00404EE5 mov [ebp+var_7], ax .text:00404EE9 mov [ebp+var_5], al .text:00404EEC mov [ebp+var_23], eax .text:00404EEF mov [ebp+var_1F], eax .text:00404EF2 mov [ebp+var_1B], eax .text:00404EF5 mov [ebp+var_17], ax .text:00404EF9 mov [ebp+var_15], al .text:00404EFC lea eax, [ebp+var_100] .text:00404F02 push eax .text:00404F03 mov [ebp+var_14], bl .text:00404F06 mov [ebp+var_24], bl .text:00404F09 call sub_401C90 .text:00404F0E push 40h .text:00404F10 lea ecx, [ebp+var_A8] .text:00404F16 push ecx .text:00404F17 lea edx, [ebp+var_100] .text:00404F1D push edx .text:00404F1E call sub_402410 .text:00404F23 lea eax, [ebp+var_14] .text:00404F26 push eax .text:00404F27 lea ecx, [ebp+var_100] .text:00404F2D push ecx .text:00404F2E call sub_402540 .text:00404F33 lea edx, [ebp+var_100] .text:00404F39 push edx .text:00404F3A call sub_401C90 .text:00404F3F push edi .text:00404F40 lea eax, [ebp+var_100] .text:00404F46 push esi .text:00404F47 push eax .text:00404F48 call sub_402410 .text:00404F4D add esp, 44h .text:00404F50 lea ecx, [ebp+var_24] .text:00404F53 push ecx .text:00404F54 lea edx, [ebp+var_100] .text:00404F5A push edx .text:00404F5B call sub_402540 .text:00404F60 add esp, 8 .text:00404F63 xor esi, esi .text:00404F65 lea edi, [ebp+var_58] .text:00404F68 jmp short loc_404F70 .text:00404F68 ; --------------------------------------------------------------------------- .text:00404F6A align 10h .text:00404F70 .text:00404F70 loc_404F70: ; CODE XREF: sub_404E50+118 .text:00404F70 ; sub_404E50+143 .text:00404F70 mov al, [ebp+esi+var_24] .text:00404F74 xor [ebp+esi+var_14], al .text:00404F78 movzx ecx, [ebp+esi+var_14] .text:00404F7D push ecx .text:00404F7E push offset a02x ; "%02X" .text:00404F83 push edi ; char * .text:00404F84 call _sprintf .text:00404F89 inc esi .text:00404F8A add esp, 0Ch .text:00404F8D add edi, 2 .text:00404F90 cmp esi, 10h .text:00404F93 jl short loc_404F70 .text:00404F95 mov eax, [ebp+var_104] .text:00404F9B lea edx, [ebp+var_58] .text:00404F9E push edx ; char * .text:00404F9F push eax ; char * .text:00404FA0 call __stricmp .text:00404FA5 add esp, 8 .text:00404FA8 pop edi .text:00404FA9 test eax, eax .text:00404FAB pop esi .text:00404FAC setz al .text:00404FAF pop ebx .text:00404FB0 mov ecx, [ebp+var_4] .text:00404FB3 xor ecx, ebp .text:00404FB5 call @__security_check_cookie@4 ; __security_check_cookie(x) .text:00404FBA mov esp, ebp .text:00404FBC pop ebp .text:00404FBD retn .text:00404FBE ; --------------------------------------------------------------------------- .text:00404FBE .text:00404FBE loc_404FBE: ; CODE XREF: sub_404E50+26 .text:00404FBE ; sub_404E50+31 ... .text:00404FBE mov ecx, [ebp+var_4] .text:00404FC1 pop edi .text:00404FC2 pop esi .text:00404FC3 xor ecx, ebp .text:00404FC5 xor al, al .text:00404FC7 pop ebx .text:00404FC8 call @__security_check_cookie@4 ; __security_check_cookie(x) .text:00404FCD mov esp, ebp .text:00404FCF pop ebp .text:00404FD0 retn .text:00404FD0 sub_404E50 endp .text:00404FD0
      
      







機能の割り当てをすぐに理解することは困難です。 これまでのところ、関数が4つの引数を取ることは明らかです。 最初に、引数がゼロと等しくないかどうかがチェックされます。 それらの少なくとも1つがゼロに等しい場合、制御はloc_404FBEブランチに転送され、alレジスタに値0を返すことで関数の実行を終了します。



sub_404E50関数を呼び出すコードを見てみましょう。 これを行うには、相互参照sub_401340 + 1C5に従います。



sub_401340
 .text:00401340 .text:00401340 sub_401340 proc near ; CODE XREF: DialogFunc+11E .text:00401340 .text:00401340 var_10 = dword ptr -10h .text:00401340 var_C = dword ptr -0Ch .text:00401340 var_4 = dword ptr -4 .text:00401340 .text:00401340 push ebp .text:00401341 mov ebp, esp .text:00401343 push 0FFFFFFFFh .text:00401345 push offset sub_410040 .text:0040134A mov eax, large fs:0 .text:00401350 push eax .text:00401351 push ecx .text:00401352 push ebx .text:00401353 push esi .text:00401354 push edi .text:00401355 mov eax, ___security_cookie .text:0040135A xor eax, ebp .text:0040135C push eax .text:0040135D lea eax, [ebp+var_C] .text:00401360 mov large fs:0, eax .text:00401366 mov [ebp+var_10], esp .text:00401369 mov esi, ecx .text:0040136B mov eax, [esi+54h] .text:0040136E xor edi, edi .text:00401370 push eax .text:00401371 mov [ebp+var_4], edi .text:00401374 call sub_4077E5 .text:00401379 mov eax, [esi+4Ch] .text:0040137C push eax .text:0040137D mov [esi+54h], edi .text:00401380 call sub_4077E5 .text:00401385 mov eax, [esi+50h] .text:00401388 push eax .text:00401389 mov [esi+4Ch], edi .text:0040138C call sub_4077E5 .text:00401391 mov eax, [esi+48h] .text:00401394 push eax .text:00401395 mov [esi+50h], edi .text:00401398 call sub_4077E5 .text:0040139D mov eax, [esi+18h] .text:004013A0 add esp, 10h .text:004013A3 push eax ; hWnd .text:004013A4 mov [esi+48h], edi .text:004013A7 call ds:GetWindowTextLengthW .text:004013AD mov edi, eax .text:004013AF xor ecx, ecx .text:004013B1 lea ebx, [edi+1] .text:004013B4 mov eax, ebx .text:004013B6 mov edx, 2 .text:004013BB mul edx .text:004013BD seto cl .text:004013C0 neg ecx .text:004013C2 or ecx, eax .text:004013C4 push ecx .text:004013C5 call unknown_libname_2 ; Microsoft VisualC 2-11/net runtime .text:004013CA mov [esi+48h], eax .text:004013CD xor ecx, ecx .text:004013CF mov [eax+edi*2], cx .text:004013D3 mov edx, [esi+48h] .text:004013D6 add esp, 4 .text:004013D9 xor eax, eax .text:004013DB mov [edx], ax .text:004013DE mov ecx, [esi+48h] .text:004013E1 mov edx, [esi+18h] .text:004013E4 push ebx ; nMaxCount .text:004013E5 push ecx ; lpString .text:004013E6 push edx ; hWnd .text:004013E7 call ds:GetWindowTextW .text:004013ED mov eax, [esi+1Ch] .text:004013F0 push eax ; hWnd .text:004013F1 call ds:GetWindowTextLengthW .text:004013F7 mov ebx, eax .text:004013F9 xor ecx, ecx .text:004013FB lea eax, [ebx+1] .text:004013FE mov edx, 2 .text:00401403 mul edx .text:00401405 seto cl .text:00401408 neg ecx .text:0040140A or ecx, eax .text:0040140C push ecx .text:0040140D call unknown_libname_2 ; Microsoft VisualC 2-11/net runtime .text:00401412 mov [esi+50h], eax .text:00401415 xor ecx, ecx .text:00401417 mov [eax+ebx*2], cx .text:0040141B mov edx, [esi+50h] .text:0040141E xor eax, eax .text:00401420 mov [edx], ax .text:00401423 mov ecx, [esi+50h] .text:00401426 mov edx, [esi+1Ch] .text:00401429 add esp, 4 .text:0040142C lea eax, [ebx+1] .text:0040142F push eax ; nMaxCount .text:00401430 push ecx ; lpString .text:00401431 push edx ; hWnd .text:00401432 call ds:GetWindowTextW .text:00401438 mov eax, [esi+50h] .text:0040143B mov ecx, [esi+48h] .text:0040143E push 0 .text:00401440 push 0 .text:00401442 push ebx .text:00401443 push eax .text:00401444 push edi .text:00401445 push ecx .text:00401446 push 7Fh .text:00401448 push esi .text:00401449 call sub_4012F0 .text:0040144E add esp, 20h .text:00401451 test eax, eax .text:00401453 jnz short loc_4014A7 .text:00401455 mov edx, [esi+38h] .text:00401458 push edx ; lParam .text:00401459 push eax ; wParam .text:0040145A mov eax, [esi+28h] .text:0040145D push 172h ; Msg .text:00401462 push eax ; hWnd .text:00401463 call ds:SendMessageW .text:00401469 mov ecx, [esi+2Ch] .text:0040146C push offset String ; "Serial is invalid" .text:00401471 push ecx ; hWnd .text:00401472 call ds:SetWindowTextW .text:00401478 mov edx, [esi+28h] .text:0040147B mov edi, ds:ShowWindow .text:00401481 push 5 ; nCmdShow .text:00401483 push edx ; hWnd .text:00401484 call edi ; ShowWindow .text:00401486 mov eax, [esi+2Ch] .text:00401489 push 5 ; nCmdShow .text:0040148B push eax ; hWnd .text:0040148C call edi ; ShowWindow .text:0040148E mov dword ptr [esi+58h], 0 .text:00401495 mov ecx, [ebp+var_C] .text:00401498 mov large fs:0, ecx .text:0040149F pop ecx .text:004014A0 pop edi .text:004014A1 pop esi .text:004014A2 pop ebx .text:004014A3 mov esp, ebp .text:004014A5 pop ebp .text:004014A6 retn .text:004014A7 ; --------------------------------------------------------------------------- .text:004014A7 .text:004014A7 loc_4014A7: ; CODE XREF: sub_401340+113 .text:004014A7 lea eax, [edi+1] .text:004014AA push eax .text:004014AB call unknown_libname_2 ; Microsoft VisualC 2-11/net runtime .text:004014B0 mov [esi+4Ch], eax .text:004014B3 mov byte ptr [eax+edi], 0 .text:004014B7 mov ecx, [esi+4Ch] .text:004014BA add esp, 4 .text:004014BD mov byte ptr [ecx], 0 .text:004014C0 mov edx, [esi+48h] .text:004014C3 lea eax, [edi+1] .text:004014C6 push eax ; size_t .text:004014C7 mov eax, [esi+4Ch] .text:004014CA push edx ; wchar_t * .text:004014CB push eax ; char * .text:004014CC call _wcstombs .text:004014D1 lea eax, [ebx+1] .text:004014D4 push eax .text:004014D5 call unknown_libname_2 ; Microsoft VisualC 2-11/net runtime .text:004014DA mov [esi+54h], eax .text:004014DD mov byte ptr [eax+ebx], 0 .text:004014E1 mov ecx, [esi+54h] .text:004014E4 add esp, 10h .text:004014E7 mov byte ptr [ecx], 0 .text:004014EA mov edx, [esi+50h] .text:004014ED lea eax, [ebx+1] .text:004014F0 push eax ; size_t .text:004014F1 mov eax, [esi+54h] .text:004014F4 push edx ; wchar_t * .text:004014F5 push eax ; char * .text:004014F6 call _wcstombs .text:004014FB mov ecx, [esi+54h] .text:004014FE mov edx, [esi+4Ch] .text:00401501 push ebx .text:00401502 push ecx .text:00401503 push edi .text:00401504 push edx .text:00401505 call sub_404E50 .text:0040150A mov bl, al .text:0040150C add esp, 1Ch .text:0040150F test bl, bl .text:00401511 jz short loc_40151D .text:00401513 mov eax, [esi+34h] .text:00401516 mov edi, offset aSerialIsValid ; "Serial is valid" .text:0040151B jmp short loc_401525 .text:0040151D ; --------------------------------------------------------------------------- .text:0040151D .text:0040151D loc_40151D: ; CODE XREF: sub_401340+1D1 .text:0040151D mov eax, [esi+38h] .text:00401520 mov edi, offset String ; "Serial is invalid" .text:00401525 .text:00401525 loc_401525: ; CODE XREF: sub_401340+1DB .text:00401525 push eax ; lParam .text:00401526 mov eax, [esi+28h] .text:00401529 push 0 ; wParam .text:0040152B push 172h ; Msg .text:00401530 push eax ; hWnd .text:00401531 call ds:SendMessageW .text:00401537 mov ecx, [esi+2Ch] .text:0040153A push edi ; lpString .text:0040153B push ecx ; hWnd .text:0040153C call ds:SetWindowTextW .text:00401542 mov edx, [esi+28h] .text:00401545 mov edi, ds:ShowWindow .text:0040154B push 5 ; nCmdShow .text:0040154D push edx ; hWnd .text:0040154E call edi ; ShowWindow .text:00401550 mov eax, [esi+2Ch] .text:00401553 push 5 ; nCmdShow .text:00401555 push eax ; hWnd .text:00401556 call edi ; ShowWindow .text:00401558 movzx ecx, bl .text:0040155B mov [esi+58h], ecx .text:0040155E mov ecx, [ebp+var_C] .text:00401561 mov large fs:0, ecx .text:00401568 pop ecx .text:00401569 pop edi .text:0040156A pop esi .text:0040156B pop ebx .text:0040156C mov esp, ebp .text:0040156E pop ebp .text:0040156F retn .text:0040156F sub_401340 endp .text:0040156F
      
      







明確にするために、スペースバーを押してグラフビュー表示モードに移動します。



シリアル番号の確認に関してユーザーから返されるメッセージは、sub_404E50から返される値に依存することが明らかになりました。 関数が0を返す場合、「シリアルが無効です」というメッセージが表示されます。それ以外の場合、「シリアルが有効です」というメッセージが表示されます。 ただし、この場合、プログラムはメッセージを表示しません。 どこかに早くフリーズします。

アドレス.text:00401340で関数の先頭にブレークポイント(<F2>)を設定し、デバッグ(<F9>)を実行し、トレース(<F8>)を使用して、プログラムの実行を終了する関数を見つけます。 この関数は予想通りsub_404E50です。 これを確実にするために、行.text:00401505を呼び出す関数にブレークポイントを設定することでデバッグを再開できますが、関数を入力する代わりに、次のコマンドに移動します(次のコマンドにカーソルを置き、<ctrl + N>を押します)。 その後、プログラムの実行を続行し、シリアル番号が正しいというメッセージを確認します。



これは、レジスタahにsub_404E50関数呼び出しの前にゼロ以外の値があったために発生します。そうでない場合、間違ったシリアル番号に関するメッセージが表示されます。

これで十分な場合、16進エディターで「call sub_404E50」命令をいくつかの「nop」命令に変更できます。プログラムは任意のシリアル番号を有効と見なしますが、タスクは電子メールのシリアル番号を生成することです。 したがって、分析を続けます。

最初に、sub_404E50関数に渡される引数を扱いましょう。 命令の最初のブロック.text:00401340-00401453では、GetWindowTextW関数が異なるhWndパラメーターで2回呼び出されます。 デバッガーを使用すると、最初の呼び出しで電子メールフィールドのUnicode文字列を受信し、アドレス[esi + 48h]に保存することがわかります。これは、おそらくecxポインターによって渡されるオブジェクトのフィールドです。

 .text:004013DE mov ecx, [esi+48h] .text:004013E1 mov edx, [esi+18h] .text:004013E4 push ebx ; nMaxCount .text:004013E5 push ecx ; lpString .text:004013E6 push edx ; hWnd .text:004013E7 call ds:GetWindowTextW
      
      





同様に、2番目の呼び出しはシリアル番号文字列を[esi + 50h]に保存します。

 .text:00401423 mov ecx, [esi+50h] .text:00401426 mov edx, [esi+1Ch] .text:00401429 add esp, 4 .text:0040142C lea eax, [ebx+1] .text:0040142F push eax ; nMaxCount .text:00401430 push ecx ; lpString .text:00401431 push edx ; hWnd .text:00401432 call ds:GetWindowTextW
      
      





実験的に、シリアル番号または電子メールにキリル文字などの拡張ユニコード文字が含まれている場合、.text:00401455ブランチの制御が転送されることがわかります。

拡張Unicode文字が見つからない場合、文字列はwcstombs関数を使用してwchar_t *からchar *に変換されます。 変換された電子メールおよびシリアル回線は、それぞれアドレス[esi + 4Ch]および[esi + 54h]にあります。 同時に、電子メール文字列の長さはediレジスタに保存され、シリアル番号はebxレジスタに保存されます。

 .text:004014C0 mov edx, [esi+48h] .text:004014C3 lea eax, [edi+1] .text:004014C6 push eax ; size_t .text:004014C7 mov eax, [esi+4Ch] .text:004014CA push edx ; wchar_t * .text:004014CB push eax ; char * .text:004014CC call _wcstombs
      
      





 .text:004014EA mov edx, [esi+50h] .text:004014ED lea eax, [ebx+1] .text:004014F0 push eax ; size_t .text:004014F1 mov eax, [esi+54h] .text:004014F4 push edx ; wchar_t * .text:004014F5 push eax ; char * .text:004014F6 call _wcstombs .text:004014FB mov ecx, [esi+54h] .text:004014FE mov edx, [esi+4Ch] .text:00401501 push ebx .text:00401502 push ecx .text:00401503 push edi .text:00401504 push edx .text:00401505 call sub_404E50
      
      





したがって、関数sub_404E50はシリアル番号を確認するように設計されており、その署名は次のようになります。



  bool sub_404E50(char * email_str, size_t email_size, char *serial_str, size_t serial_size);
      
      





次に、この関数がどのように機能するかを理解します。 まず、どの場所でハングするかを判断します。そのために、ブレークポイントを内部に設定してトレースします。 トレースにより、sub_4047C0関数呼び出しのアドレス.text:00404ED5でハングが発生することが示されました。 sub_4047C0関数は、ローカルのvar_A8変数へのポインターという1つの引数を取ります。 関数sub_4047C0の内容は恐ろしく、その分析は次の記事で検討しますが、好奇心for盛な人のために、そのコードとグラフィック表現を紹介します。



sub_4047C0




 .text:004047C0 .text:004047C0 sub_4047C0 proc near ; CODE XREF: sub_404E50+85 .text:004047C0 .text:004047C0 var_EC = dword ptr -0ECh .text:004047C0 var_E8 = dword ptr -0E8h .text:004047C0 var_E4 = dword ptr -0E4h .text:004047C0 var_E0 = dword ptr -0E0h .text:004047C0 var_D8 = dword ptr -0D8h .text:004047C0 var_D4 = dword ptr -0D4h .text:004047C0 var_D0 = dword ptr -0D0h .text:004047C0 var_CC = dword ptr -0CCh .text:004047C0 var_C8 = dword ptr -0C8h .text:004047C0 var_C4 = dword ptr -0C4h .text:004047C0 var_BC = dword ptr -0BCh .text:004047C0 var_B8 = dword ptr -0B8h .text:004047C0 var_B4 = dword ptr -0B4h .text:004047C0 var_B0 = dword ptr -0B0h .text:004047C0 var_AC = dword ptr -0ACh .text:004047C0 var_A8 = dword ptr -0A8h .text:004047C0 var_A4 = dword ptr -0A4h .text:004047C0 var_A0 = dword ptr -0A0h .text:004047C0 var_98 = dword ptr -98h .text:004047C0 var_94 = dword ptr -94h .text:004047C0 var_90 = dword ptr -90h .text:004047C0 var_80 = dword ptr -80h .text:004047C0 var_7C = dword ptr -7Ch .text:004047C0 var_75 = byte ptr -75h .text:004047C0 var_74 = byte ptr -74h .text:004047C0 var_73 = byte ptr -73h .text:004047C0 var_10 = dword ptr -10h .text:004047C0 var_C = dword ptr -0Ch .text:004047C0 var_4 = dword ptr -4 .text:004047C0 arg_0 = dword ptr 8 .text:004047C0 .text:004047C0 push ebp .text:004047C1 mov ebp, esp .text:004047C3 push 0FFFFFFFFh .text:004047C5 push offset sub_41065C .text:004047CA mov eax, large fs:0 .text:004047D0 push eax .text:004047D1 sub esp, 0E0h .text:004047D7 mov eax, ___security_cookie .text:004047DC xor eax, ebp .text:004047DE mov [ebp+var_10], eax .text:004047E1 push ebx .text:004047E2 push esi .text:004047E3 push edi .text:004047E4 push eax .text:004047E5 lea eax, [ebp+var_C] .text:004047E8 mov large fs:0, eax .text:004047EE mov eax, [ebp+arg_0] .text:004047F1 push 1Ch ; size_t .text:004047F3 mov [ebp+var_D8], eax .text:004047F9 call ??2@YAPAXI@Z ; operator new(uint) .text:004047FE mov esi, eax .text:00404800 add esp, 4 .text:00404803 mov [ebp+var_B4], esi .text:00404809 xor edi, edi .text:0040480B mov [ebp+var_4], edi .text:0040480E cmp esi, edi .text:00404810 jz short loc_40488D .text:00404812 mov dword ptr [esi], offset off_4117D4 .text:00404818 push 30h ; size_t .text:0040481A mov [esi+0Ch], edi .text:0040481D call ??2@YAPAXI@Z ; operator new(uint) .text:00404822 add esp, 4 .text:00404825 cmp eax, edi .text:00404827 jz short loc_40485A .text:00404829 mov [esi+8], eax .text:0040482C mov [eax], eax .text:0040482E mov eax, [esi+8] .text:00404831 mov [eax+4], eax .text:00404834 mov eax, [esi+8] .text:00404837 mov [eax+8], eax .text:0040483A mov ecx, [esi+8] .text:0040483D mov byte ptr [ecx+2Ch], 1 .text:00404841 mov edx, [esi+8] .text:00404844 mov byte ptr [edx+2Dh], 1 .text:00404848 mov dword ptr [esi+14h], 200h .text:0040484F mov [esi+18h], edi .text:00404852 mov [ebp+var_98], esi .text:00404858 jmp short loc_404893 .text:0040485A ; --------------------------------------------------------------------------- .text:0040485A .text:0040485A loc_40485A: ; CODE XREF: sub_4047C0+67 .text:0040485A lea eax, [ebp+var_94] .text:00404860 push eax .text:00404861 lea ecx, [ebp+var_A4] .text:00404867 mov [ebp+var_94], edi .text:0040486D call ??0exception@std@@QAE@ABQBD@Z ; std::exception::exception(char const * const &) .text:00404872 push offset unk_413D14 .text:00404877 lea ecx, [ebp+var_A4] .text:0040487D push ecx .text:0040487E mov [ebp+var_A4], offset off_4116C0 .text:00404888 call __CxxThrowException@8 ; _CxxThrowException(x,x) .text:0040488D ; --------------------------------------------------------------------------- .text:0040488D .text:0040488D loc_40488D: ; CODE XREF: sub_4047C0+50 .text:0040488D mov [ebp+var_98], edi .text:00404893 .text:00404893 loc_404893: ; CODE XREF: sub_4047C0+98 .text:00404893 mov [ebp+var_A8], edi .text:00404899 mov [ebp+var_A4], edi .text:0040489F mov [ebp+var_A0], edi .text:004048A5 mov [ebp+var_4], 1 .text:004048AC mov [ebp+var_CC], edi .text:004048B2 mov [ebp+var_C8], edi .text:004048B8 mov [ebp+var_C4], edi .text:004048BE push 18h ; size_t .text:004048C0 mov byte ptr [ebp+var_4], 2 .text:004048C4 call ??2@YAPAXI@Z ; operator new(uint) .text:004048C9 add esp, 4 .text:004048CC mov [ebp+var_94], eax .text:004048D2 mov byte ptr [ebp+var_4], 3 .text:004048D6 cmp eax, edi .text:004048D8 jz short loc_4048EB .text:004048DA push 60h .text:004048DC mov ecx, eax .text:004048DE call sub_4033D0 .text:004048E3 mov [ebp+var_B8], eax .text:004048E9 jmp short loc_4048F1 .text:004048EB ; --------------------------------------------------------------------------- .text:004048EB .text:004048EB loc_4048EB: ; CODE XREF: sub_4047C0+118 .text:004048EB mov [ebp+var_B8], edi .text:004048F1 .text:004048F1 loc_4048F1: ; CODE XREF: sub_4047C0+129 .text:004048F1 push 18h ; size_t .text:004048F3 mov byte ptr [ebp+var_4], 2 .text:004048F7 call ??2@YAPAXI@Z ; operator new(uint) .text:004048FC add esp, 4 .text:004048FF mov [ebp+var_94], eax .text:00404905 mov byte ptr [ebp+var_4], 4 .text:00404909 cmp eax, edi .text:0040490B jz short loc_404921 .text:0040490D push 200h .text:00404912 mov ecx, eax .text:00404914 call sub_4033D0 .text:00404919 mov [ebp+var_AC], eax .text:0040491F jmp short loc_404927 .text:00404921 ; --------------------------------------------------------------------------- .text:00404921 .text:00404921 loc_404921: ; CODE XREF: sub_4047C0+14B .text:00404921 mov [ebp+var_AC], edi .text:00404927 .text:00404927 loc_404927: ; CODE XREF: sub_4047C0+15F .text:00404927 mov ebx, [ebp+var_C8] .text:0040492D mov [ebp+var_BC], edi .text:00404933 mov edi, [ebp+var_98] .text:00404939 mov byte ptr [ebp+var_4], 2 .text:0040493D .text:0040493D loc_40493D: ; CODE XREF: sub_4047C0+4B9 .text:0040493D mov eax, [ebp+var_BC] .text:00404943 inc eax .text:00404944 mov [ebp+var_94], eax .text:0040494A test eax, eax .text:0040494C jle loc_404B8A .text:00404952 mov ecx, [ebp+var_A4] .text:00404958 sub ecx, [ebp+var_A8] .text:0040495E mov ebx, [ebp+var_AC] .text:00404964 mov eax, 92492493h .text:00404969 imul ecx .text:0040496B add edx, ecx .text:0040496D sar edx, 4 .text:00404970 mov eax, edx .text:00404972 shr eax, 1Fh .text:00404975 add eax, edx .text:00404977 mov edx, [ebp+var_94] .text:0040497D mov [ebp+var_D4], eax .text:00404983 mov [ebp+var_B4], edx .text:00404989 lea esp, [esp+0] .text:00404990 .text:00404990 loc_404990: ; CODE XREF: sub_4047C0+3BE .text:00404990 push 63h ; size_t .text:00404992 lea eax, [ebp+var_73] .text:00404995 push 0 ; int .text:00404997 push eax ; void * .text:00404998 mov [ebp+var_74], 0 .text:0040499C call _memset .text:004049A1 add esp, 0Ch .text:004049A4 xor esi, esi .text:004049A6 call _rand .text:004049AB cdq .text:004049AC mov ecx, 28h .text:004049B1 idiv ecx .text:004049B3 add edx, 14h .text:004049B6 test edx, edx .text:004049B8 jle short loc_4049E9 .text:004049BA lea ebx, [ebx+0] .text:004049C0 .text:004049C0 loc_4049C0: ; CODE XREF: sub_4047C0+227 .text:004049C0 call _rand .text:004049C5 cdq .text:004049C6 mov ecx, 60h .text:004049CB idiv ecx .text:004049CD inc esi .text:004049CE add dl, 20h .text:004049D1 mov [ebp+esi+var_75], dl .text:004049D5 call _rand .text:004049DA cdq .text:004049DB mov ecx, 28h .text:004049E0 idiv ecx .text:004049E2 add edx, 14h .text:004049E5 cmp esi, edx .text:004049E7 jl short loc_4049C0 .text:004049E9 .text:004049E9 loc_4049E9: ; CODE XREF: sub_4047C0+1F8 .text:004049E9 lea eax, [ebp+var_74] .text:004049EC mov [ebp+var_7C], 0Fh .text:004049F3 mov [ebp+var_80], 0 .text:004049FA mov byte ptr [ebp+var_90], 0 .text:00404A01 lea edx, [eax+1] .text:00404A04 .text:00404A04 loc_404A04: ; CODE XREF: sub_4047C0+249 .text:00404A04 mov cl, [eax] .text:00404A06 inc eax .text:00404A07 test cl, cl .text:00404A09 jnz short loc_404A04 .text:00404A0B sub eax, edx .text:00404A0D push eax ; size_t .text:00404A0E lea edx, [ebp+var_74] .text:00404A11 push edx ; void * .text:00404A12 lea ecx, [ebp+var_90] .text:00404A18 call sub_405BB0 .text:00404A1D mov eax, [edi] .text:00404A1F mov edx, [eax+4] .text:00404A22 lea ecx, [ebp+var_90] .text:00404A28 push ecx .text:00404A29 mov ecx, edi .text:00404A2B mov byte ptr [ebp+var_4], 5 .text:00404A2F call edx .text:00404A31 cmp [ebp+var_7C], 10h .text:00404A35 mov byte ptr [ebp+var_4], 2 .text:00404A39 jb short loc_404A4A .text:00404A3B mov eax, [ebp+var_90] .text:00404A41 push eax ; void * .text:00404A42 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404A47 add esp, 4 .text:00404A4A .text:00404A4A loc_404A4A: ; CODE XREF: sub_4047C0+279 .text:00404A4A cmp [ebp+var_D4], 0 .text:00404A51 jbe loc_404B10 .text:00404A57 mov ecx, [ebp+var_D4] .text:00404A5D mov esi, [ebp+var_A8] .text:00404A63 mov [ebp+var_D0], ecx .text:00404A69 lea esp, [esp+0] .text:00404A70 .text:00404A70 loc_404A70: ; CODE XREF: sub_4047C0+34A .text:00404A70 cmp [ebp+var_BC], 3 .text:00404A77 jl short loc_404A8A .text:00404A79 mov ecx, [ebp+var_B8] .text:00404A7F mov edx, [ecx] .text:00404A81 mov eax, [edx+8] .text:00404A84 call eax .text:00404A86 test al, al .text:00404A88 jz short loc_404B01 .text:00404A8A .text:00404A8A loc_404A8A: ; CODE XREF: sub_4047C0+2B7 .text:00404A8A lea eax, [ebp+var_74] .text:00404A8D mov [ebp+var_7C], 0Fh .text:00404A94 mov [ebp+var_80], 0 .text:00404A9B mov byte ptr [ebp+var_90], 0 .text:00404AA2 lea edx, [eax+1] .text:00404AA5 .text:00404AA5 loc_404AA5: ; CODE XREF: sub_4047C0+2EA .text:00404AA5 mov cl, [eax] .text:00404AA7 inc eax .text:00404AA8 test cl, cl .text:00404AAA jnz short loc_404AA5 .text:00404AAC sub eax, edx .text:00404AAE push eax ; size_t .text:00404AAF lea ecx, [ebp+var_74] .text:00404AB2 push ecx ; void * .text:00404AB3 lea ecx, [ebp+var_90] .text:00404AB9 call sub_405BB0 .text:00404ABE mov edx, [ebx] .text:00404AC0 mov edx, [edx+4] .text:00404AC3 sub esp, 14h .text:00404AC6 mov eax, esp .text:00404AC8 mov [ebp+var_B0], esp .text:00404ACE push eax .text:00404ACF mov ecx, ebx .text:00404AD1 mov byte ptr [ebp+var_4], 6 .text:00404AD5 call edx .text:00404AD7 mov eax, [edi] .text:00404AD9 mov edx, [eax+8] .text:00404ADC lea ecx, [ebp+var_90] .text:00404AE2 push ecx .text:00404AE3 push esi .text:00404AE4 mov ecx, edi .text:00404AE6 call edx .text:00404AE8 cmp [ebp+var_7C], 10h .text:00404AEC mov byte ptr [ebp+var_4], 2 .text:00404AF0 jb short loc_404B01 .text:00404AF2 mov eax, [ebp+var_90] .text:00404AF8 push eax ; void * .text:00404AF9 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404AFE add esp, 4 .text:00404B01 .text:00404B01 loc_404B01: ; CODE XREF: sub_4047C0+2C8 .text:00404B01 ; sub_4047C0+330 .text:00404B01 add esi, 1Ch .text:00404B04 dec [ebp+var_D0] .text:00404B0A jnz loc_404A70 .text:00404B10 .text:00404B10 loc_404B10: ; CODE XREF: sub_4047C0+291 .text:00404B10 lea eax, [ebp+var_74] .text:00404B13 mov [ebp+var_7C], 0Fh .text:00404B1A mov [ebp+var_80], 0 .text:00404B21 mov byte ptr [ebp+var_90], 0 .text:00404B28 lea edx, [eax+1] .text:00404B2B jmp short loc_404B30 .text:00404B2B ; --------------------------------------------------------------------------- .text:00404B2D align 10h .text:00404B30 .text:00404B30 loc_404B30: ; CODE XREF: sub_4047C0+36B .text:00404B30 ; sub_4047C0+375 .text:00404B30 mov cl, [eax] .text:00404B32 inc eax .text:00404B33 test cl, cl .text:00404B35 jnz short loc_404B30 .text:00404B37 sub eax, edx .text:00404B39 push eax ; size_t .text:00404B3A lea ecx, [ebp+var_74] .text:00404B3D push ecx ; void * .text:00404B3E lea ecx, [ebp+var_90] .text:00404B44 call sub_405BB0 .text:00404B49 lea edx, [ebp+var_90] .text:00404B4F push edx .text:00404B50 lea ecx, [ebp+var_CC] .text:00404B56 mov byte ptr [ebp+var_4], 7 .text:00404B5A call sub_4072B0 .text:00404B5F cmp [ebp+var_7C], 10h .text:00404B63 mov byte ptr [ebp+var_4], 2 .text:00404B67 jb short loc_404B78 .text:00404B69 mov eax, [ebp+var_90] .text:00404B6F push eax ; void * .text:00404B70 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404B75 add esp, 4 .text:00404B78 .text:00404B78 loc_404B78: ; CODE XREF: sub_4047C0+3A7 .text:00404B78 dec [ebp+var_B4] .text:00404B7E jnz loc_404990 .text:00404B84 mov ebx, [ebp+var_C8] .text:00404B8A .text:00404B8A loc_404B8A: ; CODE XREF: sub_4047C0+18C .text:00404B8A mov ecx, [ebp+var_A4] .text:00404B90 cmp [ebp+var_A8], ecx .text:00404B96 jz short loc_404BF9 .text:00404B98 mov edx, [ebp+var_B0] .text:00404B9E mov eax, [ebp+var_A8] .text:00404BA4 push edx .text:00404BA5 push eax ; void * .text:00404BA6 mov eax, ecx .text:00404BA8 push eax ; int .text:00404BA9 push eax ; int .text:00404BAA call sub_406140 .text:00404BAF mov edi, eax .text:00404BB1 add esp, 10h .text:00404BB4 mov esi, edi .text:00404BB6 cmp edi, [ebp+var_A4] .text:00404BBC jz short loc_404BED .text:00404BBE mov edi, edi .text:00404BC0 .text:00404BC0 loc_404BC0: ; CODE XREF: sub_4047C0+42B .text:00404BC0 cmp dword ptr [esi+14h], 10h .text:00404BC4 jb short loc_404BD1 .text:00404BC6 mov eax, [esi] .text:00404BC8 push eax ; void * .text:00404BC9 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404BCE add esp, 4 .text:00404BD1 .text:00404BD1 loc_404BD1: ; CODE XREF: sub_4047C0+404 .text:00404BD1 mov dword ptr [esi+14h], 0Fh .text:00404BD8 mov dword ptr [esi+10h], 0 .text:00404BDF mov byte ptr [esi], 0 .text:00404BE2 add esi, 1Ch .text:00404BE5 cmp esi, [ebp+var_A4] .text:00404BEB jnz short loc_404BC0 .text:00404BED .text:00404BED loc_404BED: ; CODE XREF: sub_4047C0+3FC .text:00404BED mov [ebp+var_A4], edi .text:00404BF3 mov edi, [ebp+var_98] .text:00404BF9 .text:00404BF9 loc_404BF9: ; CODE XREF: sub_4047C0+3D6 .text:00404BF9 lea ecx, [ebp+var_CC] .text:00404BFF push ecx .text:00404C00 lea ecx, [ebp+var_A8] .text:00404C06 call sub_406F10 .text:00404C0B cmp [ebp+var_CC], ebx .text:00404C11 jz short loc_404C6A .text:00404C13 mov edx, [ebp+var_B0] .text:00404C19 mov eax, [ebp+var_CC] .text:00404C1F push edx .text:00404C20 push eax ; void * .text:00404C21 push ebx ; int .text:00404C22 push ebx ; int .text:00404C23 call sub_406140 .text:00404C28 mov edi, eax .text:00404C2A add esp, 10h .text:00404C2D mov esi, edi .text:00404C2F cmp edi, ebx .text:00404C31 jz short loc_404C5C .text:00404C33 .text:00404C33 loc_404C33: ; CODE XREF: sub_4047C0+49A .text:00404C33 cmp dword ptr [esi+14h], 10h .text:00404C37 jb short loc_404C44 .text:00404C39 mov eax, [esi] .text:00404C3B push eax ; void * .text:00404C3C call ??3@YAXPAX@Z ; operator delete(void *) .text:00404C41 add esp, 4 .text:00404C44 .text:00404C44 loc_404C44: ; CODE XREF: sub_4047C0+477 .text:00404C44 mov dword ptr [esi+14h], 0Fh .text:00404C4B mov dword ptr [esi+10h], 0 .text:00404C52 mov byte ptr [esi], 0 .text:00404C55 add esi, 1Ch .text:00404C58 cmp esi, ebx .text:00404C5A jnz short loc_404C33 .text:00404C5C .text:00404C5C loc_404C5C: ; CODE XREF: sub_4047C0+471 .text:00404C5C mov ebx, edi .text:00404C5E mov edi, [ebp+var_98] .text:00404C64 mov [ebp+var_C8], ebx .text:00404C6A .text:00404C6A loc_404C6A: ; CODE XREF: sub_4047C0+451 .text:00404C6A mov eax, [ebp+var_94] .text:00404C70 mov [ebp+var_BC], eax .text:00404C76 cmp eax, 32h .text:00404C79 jl loc_40493D .text:00404C7F mov edi, [ebp+var_A4] .text:00404C85 cmp [ebp+var_A8], edi .text:00404C8B jz short loc_404CE7 .text:00404C8D mov ecx, [ebp+var_B0] .text:00404C93 mov edx, [ebp+var_A8] .text:00404C99 push ecx .text:00404C9A push edx ; void * .text:00404C9B push edi ; int .text:00404C9C push edi ; int .text:00404C9D call sub_406140 .text:00404CA2 mov ebx, eax .text:00404CA4 add esp, 10h .text:00404CA7 mov esi, ebx .text:00404CA9 cmp ebx, edi .text:00404CAB jz short loc_404CD9 .text:00404CAD lea ecx, [ecx+0] .text:00404CB0 .text:00404CB0 loc_404CB0: ; CODE XREF: sub_4047C0+517 .text:00404CB0 cmp dword ptr [esi+14h], 10h .text:00404CB4 jb short loc_404CC1 .text:00404CB6 mov eax, [esi] .text:00404CB8 push eax ; void * .text:00404CB9 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404CBE add esp, 4 .text:00404CC1 .text:00404CC1 loc_404CC1: ; CODE XREF: sub_4047C0+4F4 .text:00404CC1 mov dword ptr [esi+14h], 0Fh .text:00404CC8 mov dword ptr [esi+10h], 0 .text:00404CCF mov byte ptr [esi], 0 .text:00404CD2 add esi, 1Ch .text:00404CD5 cmp esi, edi .text:00404CD7 jnz short loc_404CB0 .text:00404CD9 .text:00404CD9 loc_404CD9: ; CODE XREF: sub_4047C0+4EB .text:00404CD9 mov edi, ebx .text:00404CDB mov ebx, [ebp+var_C8] .text:00404CE1 mov [ebp+var_A4], edi .text:00404CE7 .text:00404CE7 loc_404CE7: ; CODE XREF: sub_4047C0+4CB .text:00404CE7 mov esi, [ebp+var_98] .text:00404CED mov eax, [esi] .text:00404CEF mov edx, [eax+10h] .text:00404CF2 lea ecx, [ebp+var_EC] .text:00404CF8 push ecx .text:00404CF9 mov ecx, esi .text:00404CFB call edx .text:00404CFD mov eax, [ebp+var_D8] .text:00404D03 push eax .text:00404D04 lea ecx, [ebp+var_EC] .text:00404D0A mov byte ptr [ebp+var_4], 8 .text:00404D0E call sub_402920 .text:00404D13 mov ecx, [ebp+var_B8] .text:00404D19 test ecx, ecx .text:00404D1B jz short loc_404D25 .text:00404D1D mov edx, [ecx] .text:00404D1F mov eax, [edx] .text:00404D21 push 1 .text:00404D23 call eax .text:00404D25 .text:00404D25 loc_404D25: ; CODE XREF: sub_4047C0+55B .text:00404D25 mov ecx, [ebp+var_AC] .text:00404D2B test ecx, ecx .text:00404D2D jz short loc_404D37 .text:00404D2F mov edx, [ecx] .text:00404D31 mov eax, [edx] .text:00404D33 push 1 .text:00404D35 call eax .text:00404D37 .text:00404D37 loc_404D37: ; CODE XREF: sub_4047C0+56D .text:00404D37 mov edx, [esi] .text:00404D39 mov eax, [edx] .text:00404D3B push 1 .text:00404D3D mov ecx, esi .text:00404D3F call eax .text:00404D41 mov eax, [ebp+var_E8] .text:00404D47 mov ecx, [ebp+var_E4] .text:00404D4D mov [ebp+var_EC], offset off_41171C .text:00404D57 cmp eax, ecx .text:00404D59 jz short loc_404D75 .text:00404D5B push 0 ; size_t .text:00404D5D push ecx ; void * .text:00404D5E push eax ; void * .text:00404D5F mov esi, eax .text:00404D61 call _memcpy_0 .text:00404D66 mov eax, [ebp+var_E8] .text:00404D6C add esp, 0Ch .text:00404D6F mov [ebp+var_E4], esi .text:00404D75 .text:00404D75 loc_404D75: ; CODE XREF: sub_4047C0+599 .text:00404D75 xor esi, esi .text:00404D77 cmp eax, esi .text:00404D79 jz short loc_404D84 .text:00404D7B push eax ; void * .text:00404D7C call ??3@YAXPAX@Z ; operator delete(void *) .text:00404D81 add esp, 4 .text:00404D84 .text:00404D84 loc_404D84: ; CODE XREF: sub_4047C0+5B9 .text:00404D84 mov [ebp+var_E8], esi .text:00404D8A mov [ebp+var_E4], esi .text:00404D90 mov [ebp+var_E0], esi .text:00404D96 cmp [ebp+var_CC], esi .text:00404D9C jz short loc_404DE2 .text:00404D9E mov esi, [ebp+var_CC] .text:00404DA4 cmp esi, ebx .text:00404DA6 jz short loc_404DD1 .text:00404DA8 .text:00404DA8 loc_404DA8: ; CODE XREF: sub_4047C0+60F .text:00404DA8 cmp dword ptr [esi+14h], 10h .text:00404DAC jb short loc_404DB9 .text:00404DAE mov ecx, [esi] .text:00404DB0 push ecx ; void * .text:00404DB1 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404DB6 add esp, 4 .text:00404DB9 .text:00404DB9 loc_404DB9: ; CODE XREF: sub_4047C0+5EC .text:00404DB9 mov dword ptr [esi+14h], 0Fh .text:00404DC0 mov dword ptr [esi+10h], 0 .text:00404DC7 mov byte ptr [esi], 0 .text:00404DCA add esi, 1Ch .text:00404DCD cmp esi, ebx .text:00404DCF jnz short loc_404DA8 .text:00404DD1 .text:00404DD1 loc_404DD1: ; CODE XREF: sub_4047C0+5E6 .text:00404DD1 mov edx, [ebp+var_CC] .text:00404DD7 push edx ; void * .text:00404DD8 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404DDD add esp, 4 .text:00404DE0 xor esi, esi .text:00404DE2 .text:00404DE2 loc_404DE2: ; CODE XREF: sub_4047C0+5DC .text:00404DE2 cmp [ebp+var_A8], esi .text:00404DE8 jz short loc_404E34 .text:00404DEA mov esi, [ebp+var_A8] .text:00404DF0 cmp esi, edi .text:00404DF2 jz short loc_404E25 .text:00404DF4 mov ebx, 0Fh .text:00404DF9 lea esp, [esp+0] .text:00404E00 .text:00404E00 loc_404E00: ; CODE XREF: sub_4047C0+663 .text:00404E00 cmp dword ptr [esi+14h], 10h .text:00404E04 jb short loc_404E11 .text:00404E06 mov eax, [esi] .text:00404E08 push eax ; void * .text:00404E09 call ??3@YAXPAX@Z ; operator delete(void *) .text:00404E0E add esp, 4 .text:00404E11 .text:00404E11 loc_404E11: ; CODE XREF: sub_4047C0+644 .text:00404E11 mov [esi+14h], ebx .text:00404E14 mov dword ptr [esi+10h], 0 .text:00404E1B mov byte ptr [esi], 0 .text:00404E1E add esi, 1Ch .text:00404E21 cmp esi, edi .text:00404E23 jnz short loc_404E00 .text:00404E25 .text:00404E25 loc_404E25: ; CODE XREF: sub_4047C0+632 .text:00404E25 mov ecx, [ebp+var_A8] .text:00404E2B push ecx ; void * .text:00404E2C call ??3@YAXPAX@Z ; operator delete(void *) .text:00404E31 add esp, 4 .text:00404E34 .text:00404E34 loc_404E34: ; CODE XREF: sub_4047C0+628 .text:00404E34 mov ecx, [ebp+var_C] .text:00404E37 mov large fs:0, ecx .text:00404E3E pop ecx .text:00404E3F pop edi .text:00404E40 pop esi .text:00404E41 pop ebx .text:00404E42 mov ecx, [ebp+var_10] .text:00404E45 xor ecx, ebp .text:00404E47 call @__security_check_cookie@4 ; __security_check_cookie(x) .text:00404E4C mov esp, ebp .text:00404E4E pop ebp .text:00404E4F retn .text:00404E4F sub_4047C0 endp .text:00404E4F
      
      







それまでの間、残りの関数sub_404E50を処理します。sub_401C90関数呼び出しは、var_100変数の最初の18バイトを一定の値で初期化します。



 .text:00404EFC lea eax, [ebp+var_100] .text:00404F02 push eax ... .text:00404F09 call sub_401C90
      
      





sub_401C90
 .text:00401C90 sub_401C90 proc near ; CODE XREF: sub_404E50+B9 .text:00401C90 ; sub_404E50+EA .text:00401C90 .text:00401C90 arg_0 = dword ptr 8 .text:00401C90 .text:00401C90 push ebp .text:00401C91 mov ebp, esp .text:00401C93 mov eax, [ebp+arg_0] .text:00401C96 mov dword ptr [eax+4], 0 .text:00401C9D mov dword ptr [eax], 0 .text:00401CA3 mov dword ptr [eax+8], 67452301h .text:00401CAA mov dword ptr [eax+0Ch], 0EFCDAB89h .text:00401CB1 mov dword ptr [eax+10h], 98BADCFEh .text:00401CB8 mov dword ptr [eax+14h], 10325476h .text:00401CBF pop ebp .text:00401CC0 retn .text:00401CC0 sub_401C90 endp
      
      







sub_402410およびsub_402540関数の呼び出しの結果、64ビット長のvar_A8文字列から128ビットのハッシュが生成され、var_14変数に書き込まれます。



 .text:00404F0E push 40h .text:00404F10 lea ecx, [ebp+var_A8] .text:00404F16 push ecx .text:00404F17 lea edx, [ebp+var_100] .text:00404F1D push edx .text:00404F1E call sub_402410 .text:00404F23 lea eax, [ebp+var_14] .text:00404F26 push eax .text:00404F27 lea ecx, [ebp+var_100] .text:00404F2D push ecx .text:00404F2E call sub_402540
      
      





sub_402410
 .text:00402410 sub_402410 proc near ; CODE XREF: sub_402540+42 .text:00402410 ; sub_404E50+CE ... .text:00402410 .text:00402410 var_44 = dword ptr -44h .text:00402410 var_40 = dword ptr -40h .text:00402410 var_3C = dword ptr -3Ch .text:00402410 var_38 = dword ptr -38h .text:00402410 var_4 = dword ptr -4 .text:00402410 arg_0 = dword ptr 8 .text:00402410 arg_4 = dword ptr 0Ch .text:00402410 arg_8 = dword ptr 10h .text:00402410 .text:00402410 push ebp .text:00402411 mov ebp, esp .text:00402413 sub esp, 44h .text:00402416 mov eax, ___security_cookie .text:0040241B xor eax, ebp .text:0040241D mov [ebp+var_4], eax .text:00402420 push esi .text:00402421 mov esi, [ebp+arg_0] .text:00402424 mov ecx, [esi] .text:00402426 push edi .text:00402427 mov edi, [ebp+arg_8] .text:0040242A mov eax, ecx .text:0040242C shr eax, 3 .text:0040242F lea edx, [ecx+edi*8] .text:00402432 and eax, 3Fh .text:00402435 cmp edx, ecx .text:00402437 jnb short loc_40243C .text:00402439 inc dword ptr [esi+4] .text:0040243C .text:0040243C loc_40243C: ; CODE XREF: sub_402410+27 .text:0040243C mov ecx, edi .text:0040243E shr ecx, 1Dh .text:00402441 add [esi+4], ecx .text:00402444 mov [esi], edx .text:00402446 test edi, edi .text:00402448 jz loc_402524 .text:0040244E push ebx .text:0040244F nop .text:00402450 .text:00402450 loc_402450: ; CODE XREF: sub_402410+10D .text:00402450 mov ecx, [ebp+arg_4] .text:00402453 mov dl, [ecx] .text:00402455 mov [esi+eax+18h], dl .text:00402459 inc eax .text:0040245A inc ecx .text:0040245B dec edi .text:0040245C mov [ebp+arg_4], ecx .text:0040245F cmp eax, 40h .text:00402462 jnz loc_40251B .text:00402468 xor ecx, ecx .text:0040246A lea eax, [esi+1Ah] .text:0040246D lea ecx, [ecx+0] .text:00402470 .text:00402470 loc_402470: ; CODE XREF: sub_402410+F4 .text:00402470 movzx edx, byte ptr [eax+1] .text:00402474 movzx ebx, byte ptr [eax] .text:00402477 shl edx, 8 .text:0040247A or edx, ebx .text:0040247C movzx ebx, byte ptr [eax-1] .text:00402480 shl edx, 8 .text:00402483 or edx, ebx .text:00402485 movzx ebx, byte ptr [eax-2] .text:00402489 shl edx, 8 .text:0040248C or edx, ebx .text:0040248E movzx ebx, byte ptr [eax+4] .text:00402492 mov [ebp+ecx*4+var_44], edx .text:00402496 movzx edx, byte ptr [eax+5] .text:0040249A shl edx, 8 .text:0040249D or edx, ebx .text:0040249F movzx ebx, byte ptr [eax+3] .text:004024A3 shl edx, 8 .text:004024A6 or edx, ebx .text:004024A8 movzx ebx, byte ptr [eax+2] .text:004024AC shl edx, 8 .text:004024AF or edx, ebx .text:004024B1 movzx ebx, byte ptr [eax+8] .text:004024B5 mov [ebp+ecx*4+var_40], edx .text:004024B9 movzx edx, byte ptr [eax+9] .text:004024BD shl edx, 8 .text:004024C0 or edx, ebx .text:004024C2 movzx ebx, byte ptr [eax+7] .text:004024C6 shl edx, 8 .text:004024C9 or edx, ebx .text:004024CB movzx ebx, byte ptr [eax+6] .text:004024CF shl edx, 8 .text:004024D2 or edx, ebx .text:004024D4 movzx ebx, byte ptr [eax+0Ch] .text:004024D8 mov [ebp+ecx*4+var_3C], edx .text:004024DC movzx edx, byte ptr [eax+0Dh] .text:004024E0 shl edx, 8 .text:004024E3 or edx, ebx .text:004024E5 movzx ebx, byte ptr [eax+0Bh] .text:004024E9 shl edx, 8 .text:004024EC or edx, ebx .text:004024EE movzx ebx, byte ptr [eax+0Ah] .text:004024F2 shl edx, 8 .text:004024F5 or edx, ebx .text:004024F7 mov [ebp+ecx*4+var_38], edx .text:004024FB add ecx, 4 .text:004024FE add eax, 10h .text:00402501 cmp ecx, 10h .text:00402504 jb loc_402470 .text:0040250A lea eax, [esi+8] .text:0040250D push eax .text:0040250E lea eax, [ebp+var_44] .text:00402511 call sub_401CD0 .text:00402516 add esp, 4 .text:00402519 xor eax, eax .text:0040251B .text:0040251B loc_40251B: ; CODE XREF: sub_402410+52 .text:0040251B test edi, edi .text:0040251D jnz loc_402450 .text:00402523 pop ebx .text:00402524 .text:00402524 loc_402524: ; CODE XREF: sub_402410+38 .text:00402524 mov ecx, [ebp+var_4] .text:00402527 pop edi .text:00402528 xor ecx, ebp .text:0040252A pop esi .text:0040252B call @__security_check_cookie@4 ; __security_check_cookie(x) .text:00402530 mov esp, ebp .text:00402532 pop ebp .text:00402533 retn .text:00402533 sub_402410 endp
      
      







sub_402540
 .text:00402540 sub_402540 proc near ; CODE XREF: sub_404E50+DE .text:00402540 ; sub_404E50+10B .text:00402540 .text:00402540 var_44 = dword ptr -44h .text:00402540 var_40 = dword ptr -40h .text:00402540 var_C = dword ptr -0Ch .text:00402540 var_8 = dword ptr -8 .text:00402540 var_4 = dword ptr -4 .text:00402540 arg_0 = dword ptr 8 .text:00402540 arg_4 = dword ptr 0Ch .text:00402540 .text:00402540 push ebp .text:00402541 mov ebp, esp .text:00402543 sub esp, 44h .text:00402546 mov eax, ___security_cookie .text:0040254B xor eax, ebp .text:0040254D mov [ebp+var_4], eax .text:00402550 push ebx .text:00402551 push esi .text:00402552 mov esi, [ebp+arg_0] .text:00402555 mov eax, [esi] .text:00402557 mov ecx, [esi+4] .text:0040255A mov [ebp+var_C], eax .text:0040255D shr eax, 3 .text:00402560 and eax, 3Fh .text:00402563 push edi .text:00402564 mov edi, [ebp+arg_4] .text:00402567 mov [ebp+var_8], ecx .text:0040256A mov ecx, 38h .text:0040256F cmp eax, 38h .text:00402572 jl short loc_402579 .text:00402574 mov ecx, 78h .text:00402579 .text:00402579 loc_402579: ; CODE XREF: sub_402540+32 .text:00402579 sub ecx, eax .text:0040257B push ecx .text:0040257C push offset unk_411588 .text:00402581 push esi .text:00402582 call sub_402410 .text:00402587 add esp, 0Ch .text:0040258A xor ecx, ecx .text:0040258C lea eax, [esi+1Ah] .text:0040258F nop .text:00402590 .text:00402590 loc_402590: ; CODE XREF: sub_402540+9E .text:00402590 movzx edx, byte ptr [eax+1] .text:00402594 movzx ebx, byte ptr [eax] .text:00402597 shl edx, 8 .text:0040259A or edx, ebx .text:0040259C movzx ebx, byte ptr [eax-1] .text:004025A0 shl edx, 8 .text:004025A3 or edx, ebx .text:004025A5 movzx ebx, byte ptr [eax-2] .text:004025A9 shl edx, 8 .text:004025AC or edx, ebx .text:004025AE movzx ebx, byte ptr [eax+4] .text:004025B2 mov [ebp+ecx*4+var_44], edx .text:004025B6 movzx edx, byte ptr [eax+5] .text:004025BA shl edx, 8 .text:004025BD or edx, ebx .text:004025BF movzx ebx, byte ptr [eax+3] .text:004025C3 shl edx, 8 .text:004025C6 or edx, ebx .text:004025C8 movzx ebx, byte ptr [eax+2] .text:004025CC shl edx, 8 .text:004025CF or edx, ebx .text:004025D1 mov [ebp+ecx*4+var_40], edx .text:004025D5 add ecx, 2 .text:004025D8 add eax, 8 .text:004025DB cmp ecx, 0Eh .text:004025DE jb short loc_402590 .text:004025E0 lea ebx, [esi+8] .text:004025E3 push ebx .text:004025E4 lea eax, [ebp+var_44] .text:004025E7 call sub_401CD0 .text:004025EC movzx eax, byte ptr [ebx] .text:004025EF mov [edi], al .text:004025F1 movzx ecx, byte ptr [esi+9] .text:004025F5 mov [edi+1], cl .text:004025F8 movzx edx, byte ptr [esi+0Ah] .text:004025FC mov [edi+2], dl .text:004025FF movzx eax, byte ptr [esi+0Bh] .text:00402603 mov [edi+3], al .text:00402606 movzx ecx, byte ptr [esi+0Ch] .text:0040260A mov [edi+4], cl .text:0040260D movzx edx, byte ptr [esi+0Dh] .text:00402611 mov [edi+5], dl .text:00402614 movzx eax, byte ptr [esi+0Eh] .text:00402618 mov [edi+6], al .text:0040261B movzx ecx, byte ptr [esi+0Fh] .text:0040261F mov [edi+7], cl .text:00402622 movzx edx, byte ptr [esi+10h] .text:00402626 mov [edi+8], dl .text:00402629 movzx eax, byte ptr [esi+11h] .text:0040262D mov [edi+9], al .text:00402630 movzx ecx, byte ptr [esi+12h] .text:00402634 mov [edi+0Ah], cl .text:00402637 movzx edx, byte ptr [esi+13h] .text:0040263B mov [edi+0Bh], dl .text:0040263E movzx eax, byte ptr [esi+14h] .text:00402642 mov [edi+0Ch], al .text:00402645 movzx ecx, byte ptr [esi+15h] .text:00402649 mov [edi+0Dh], cl .text:0040264C movzx edx, byte ptr [esi+16h] .text:00402650 mov ecx, [ebp+var_4] .text:00402653 mov [edi+0Eh], dl .text:00402656 movzx eax, byte ptr [esi+17h] .text:0040265A add esp, 4 .text:0040265D mov [edi+0Fh], al .text:00402660 pop edi .text:00402661 pop esi .text:00402662 xor ecx, ebp .text:00402664 pop ebx .text:00402665 call @__security_check_cookie@4 ; __security_check_cookie(x) .text:0040266A mov esp, ebp .text:0040266C pop ebp .text:0040266D retn .text:0040266D sub_402540 endp
      
      







同様に、電子メールを含む文字列からハッシュが生成され、var_24変数に書き込まれます。



 .text:01324F3F push edi .text:01324F40 lea eax, [ebp+var_100] .text:01324F46 push esi .text:01324F47 push eax .text:01324F48 call sub_1322410 .text:01324F4D add esp, 44h .text:01324F50 lea ecx, [ebp+var_24] .text:01324F53 push ecx .text:01324F54 lea edx, [ebp+var_100] .text:01324F5A push edx .text:01324F5B call sub_1322540
      
      





その後、var_24行とvar_14行がビットごとに加算され、テキスト形式で提供されます。結果の文字列はvar_58変数に書き込まれ、最終段階でユーザーが入力したシリアル番号の文字列と比較されます。このリンクはvar_104変数に格納されます。文字列var_58とvar_104が一致する場合(大文字と小文字を区別しない)、関数sub_404E50は1を返します。それ以外の場合は0を返します。







したがって、最終段階でvar_58変数に書き込まれる有効なシリアル番号を見つけるには、 var_A8。sub_4047C0ホバー関数によって生成されます。 var_A8行が既知になったら、.text:00404EDA-00404F95操作ブロックを実行し、var_58変数からシリアル番号行を読み取るだけで十分です。



デバッグモードで残りのコードが正しく機能することを確認するために、sub_4047C0関数呼び出しをスキップして、入力されたシリアル番号と実際のシリアル番号が比較される.text:00404FA0の場所に移動します。すべてのコードが正しく実行され、結果のシリアル番号は「D1985BE6F7AEDF39E4BB93A02C854B99」に等しくなります。







プログラムはsub_4047C0関数をスキップするときにこのシリアル番号を受け入れますが、この結果を送信しようとすると予想どおり失敗します。











まとめると。このcrackmeの保護メカニズムの検索には、それほど時間はかかりません。シリアル番号をチェックする機能は、クロスリンクをクリックしてメッセージボックスを呼び出すだけで確認できます。デバッグ対策やプログラムの分解との干渉は検出されませんでした。この問題を解決する主な障害は、シリアル番号を生成するために使用される中間行を初期化するsub_4047C0関数が、初期化を実行せずにハングアップするという事実です。次のステップは、sub_4047C0関数を調査し、そのパフォーマンスを最適化することです。このために、無効な関数への呼び出しが置き換えられるリンクとともに、Xコード挿入が使用されます。



All Articles