金盾2018SS加密視訊機器碼替換工具的分析過程三
前面講了
金盾2018SS加密視訊機器碼替換工具的分析過程二 |
現在接著分析生成的DLL檔案在做些什麼。首先,我們到系統目錄下,把生成的2個檔案複製出來。
使用OD載入JDPlayer.exe後,直接F9執行.使用OD帶的外掛StrongOD把生成的DLL注入,看有什麼變化。
在模組視窗可以看該DLL已經注入,注入後,我們支看下DLL裡有哪些字元值得我們參考的。
字串可以看到很多有用的資訊,我們把這些關鍵地方都下一個斷點,重新載入播放器注入,看它會斷在哪個地方。
100111F0 /$ 55 push ebp 100111F1 |. 8BEC mov ebp,esp 100111F3 |. 8B45 0C mov eax,[arg.2] 100111F6 |. 48 dec eax 100111F7 |. 75 1D jnz Xsunflove.10011216 100111F9 |. 68 F8010210 push sunflove.100201F8 ; /sunflover.dll 載入!\r\n 100111FE |. FF15 74D00110 call dword ptr ds:[<&KERNEL32.OutputDebu>; \OutputDebugStringA 10011204 |. 68 A0110110 push sunflove.100111A0 10011209 |. 68 2CAA0410 push sunflove.1004AA2C ; , 1001120E |. E8 CDF3FFFF call sunflove.100105E0 ; 斷在該CALL內 10011213 |. 83C4 08 add esp,0x8 10011216 |> B8 01000000 mov eax,0x1 1001121B |. 5D pop ebp 1001121C \. C2 0C00 retn 0xC
斷在載入DLL處,繼續F8往下走,我們發現它對 CreateWindowExA函式進行了記憶體屬性更改,並直接HOOK了該函式
10010662 |. FF15 50D00110 call dword ptr ds:[<&KERNEL32.GetCurrent>; [GetCurrentProcess 10010668 |. 33C9 xor ecx,ecx 1001066A |. 894D F4 mov [local.3],ecx 1001066D |. 894D F8 mov [local.2],ecx 10010670 |. 8D4D F4 lea ecx,[local.3] 10010673 |. 51 push ecx ; /pOldProtect 10010674 |. 6A 40 push 0x40 ; |NewProtect = PAGE_EXECUTE_READWRITE 10010676 |. 57 push edi ; |Size 10010677 |. 53 push ebx ; |Address 10010678 |. 50 push eax ; |hProcess 10010679 |. 8945 FC mov [local.1],eax ; | 1001067C |. FF15 4CD00110 call dword ptr ds:[<&KERNEL32.VirtualPro>; \VirtualProtectEx 10010682 |. 85C0 test eax,eax 10010684 |. 0F84 E1000000 je sunflove.1001076B 1001068A |. 8B45 FC mov eax,[local.1] 1001068D |. 8D55 F8 lea edx,[local.2] 10010690 |. 52 push edx ; /pOldProtect 10010691 |. 6A 40 push 0x40 ; |NewProtect = PAGE_EXECUTE_READWRITE 10010693 |. 6A 6C push 0x6C ; |Size = 6C (108.) 10010695 |. 56 push esi ; |Address 10010696 |. 50 push eax ; |hProcess 10010697 |. FF15 4CD00110 call dword ptr ds:[<&KERNEL32.VirtualPro>; \VirtualProtectEx
HOOK:
10010717 |. E8 04F9FFFF call sunflove.10010020 ;修改函式頭5位元組 10010706 |. 50 push eax ; /RegionSize 10010707 |. 8D46 0C lea eax,dword ptr ds:[esi+0xC] ; | 1001070A |. 50 push eax ; |RegionBase 1001070B |. 51 push ecx ; |hProcess 1001070C |. FF15 48D00110 call dword ptr ds:[<&KERNEL32.FlushInstr>; \FlushInstructionCache 重新整理 10010712 |. 8D4E 0C lea ecx,dword ptr ds:[esi+0xC] 10010715 |> 8BC3 mov eax,ebx 10010717 |. E8 04F9FFFF call sunflove.10010020 1001071C |. 8B55 0C mov edx,[arg.2] 1001071F |. 57 push edi ; /RegionSize 10010720 |. 8D46 2C lea eax,dword ptr ds:[esi+0x2C] ; | 10010723 |. 50 push eax ; |RegionBase 10010724 |. 8B45 FC mov eax,[local.1] ; | 10010727 |. 50 push eax ; |hProcess 10010728 |. 897E 04 mov dword ptr ds:[esi+0x4],edi ; | 1001072B |. 891E mov dword ptr ds:[esi],ebx ; | 1001072D |. 8956 08 mov dword ptr ds:[esi+0x8],edx ; | 10010730 |. FF15 48D00110 call dword ptr ds:[<&KERNEL32.FlushInstr>; \FlushInstructionCache
往下走,就完了。這個CALL就是載入DLL後,對CreateWindowExA進行了HOOK。現在我們進入HOOK的函式,看它會做些什麼
[color=#ff0000]75AAD23E >- E9 5D3F569A jmp sunflove.100111A0[/color]
關鍵位置:100111A0
100111A0 . 55 push ebp 100111A1 . 8BEC mov ebp,esp 100111A3 . 56 push esi 100111A4 . 8B35 74D00110 mov esi,dword ptr ds:[<&KERNEL32.OutputD>; kernel32.OutputDebugStringA 100111AA . 68 E0010210 push sunflove.100201E0 ; /HookCreateWindowExA\r\n 100111AF . FFD6 call esi ; \OutputDebugStringA 100111B1 . A1 38990410 mov eax,dword ptr ds:[0x10049938] 100111B6 . 8338 00 cmp dword ptr ds:[eax],0x0 100111B9 . 74 27 je Xsunflove.100111E2 100111BB . 68 2CAA0410 push sunflove.1004AA2C ; , 100111C0 . E8 DBF5FFFF call sunflove.100107A0 100111C5 . 83C4 04 add esp,0x4 100111C8 . 68 C4010210 push sunflove.100201C4 ; Unhook CreateWindowExA!\r\n 100111CD . FFD6 call esi 100111CF . 68 B8010210 push sunflove.100201B8 ; 正正補丁!\r\n 100111D4 . FFD6 call esi 100111D6 . E8 C5FDFFFF call sunflove.10010FA0 100111DB . 68 AC010210 push sunflove.100201AC ; 補丁完成!\r\n 100111E0 . FFD6 call esi 100111E2 > 5E pop esi 100111E3 . 5D pop ebp 100111E4 .- FF25 2CAA0410 jmp dword ptr ds:[0x1004AA2C]
只有在建立新視窗的時候它才會呼叫該函式,執行這裡面的程式碼。到此,我們F9讓程式執行起來。用播放器新增視訊檔案,會彈出新對話方塊,看它會不會呼叫該函式執行HOOK程式碼。
<ignore_js_op>
並未呼叫該函式,看來注入時機太晚了。要在建立主視窗時就要注入了。
通過前面的分析,我們知道DLL在注入時就會對 視窗函式進行HOOK,並未對播放器操作所以就不會檢測和報錯,那麼我們直接OD載入播放器後,把DLL注入進行,F9執行。此時就看到DLL直接對視窗函式進行了HOOK,並在建立視窗時,執行了HOOK的程式碼。來到了地址:100111A0 裡
100111A0 . 55 push ebp 100111A1 . 8BEC mov ebp,esp 100111A3 . 56 push esi 100111A4 . 8B35 74D00110 mov esi,dword ptr ds:[<&KERNEL32.OutputD>; kernel32.OutputDebugStringA 100111AA . 68 E0010210 push sunflove.100201E0 ; /HookCreateWindowExA\r\n 100111AF . FFD6 call esi ; \OutputDebugStringA 100111B1 . A1 38990410 mov eax,dword ptr ds:[0x10049938] 100111B6 . 8338 00 cmp dword ptr ds:[eax],0x0 100111B9 . 74 27 je Xsunflove.100111E2 100111BB . 68 2CAA0410 push sunflove.1004AA2C ; , 100111C0 . E8 DBF5FFFF call sunflove.100107A0 100111C5 . 83C4 04 add esp,0x4 100111C8 . 68 C4010210 push sunflove.100201C4 ; Unhook CreateWindowExA!\r\n 100111CD . FFD6 call esi 100111CF . 68 B8010210 push sunflove.100201B8 ; 正正補丁!\r\n 100111D4 . FFD6 call esi 100111D6 . E8 C5FDFFFF call sunflove.10010FA0 100111DB . 68 AC010210 push sunflove.100201AC ; 補丁完成!\r\n 100111E0 . FFD6 call esi 100111E2 > 5E pop esi 100111E3 . 5D pop ebp 100111E4 .- FF25 2CAA0410 jmp dword ptr ds:[0x1004AA2C]
看到上面功能就是輸出除錯語句,中間有一個關鍵的CALL:
100111D6 . E8 C5FDFFFF call sunflove.10010FA0 進入看到是原先找字串時下過的斷
10010FA0 /$ 55 push ebp 10010FA1 |. 8BEC mov ebp,esp 10010FA3 |. 83EC 38 sub esp,0x38 10010FA6 |. 6A 00 push 0x0 ; /pModule = NULL 10010FA8 |. FF15 58D00110 call dword ptr ds:[<&KERNEL32.GetModuleH>; \GetModuleHandleA 10010FAE |. 50 push eax 10010FAF |. E8 4CFFFFFF call sunflove.10010F00 10010FB4 |. 83C4 04 add esp,0x4 10010FB7 |. FF15 44D00110 call dword ptr ds:[<&KERNEL32.GetCurrent>; [GetCurrentProcessId 10010FBD |. 85C0 test eax,eax 10010FBF |. 79 07 jns Xsunflove.10010FC8 10010FC1 |. 83C8 FF or eax,0xFFFFFFFF 10010FC4 |. 8BE5 mov esp,ebp 10010FC6 |. 5D pop ebp 10010FC7 |. C3 retn
往下看,這是一個關鍵的CALL,F9執行斷下後,F8往下走。
[color=#0000ff]10010FD1 |. 8B1D 38990410 mov ebx,dword ptr ds:[0x10049938] ; JDPlayer.0040B50B[/color] 10010FD7 |. 8B35 78D00110 mov esi,dword ptr ds:[<&KERNEL32.VirtualPro>; kernel32.VirtualProtect 10010FDD |. 83C4 04 add esp,0x4 10010FE0 |. 8D45 FC lea eax,[local.1] 10010FE3 |. 50 push eax ; /pOldProtect 10010FE4 |. 6A 40 push 0x40 ; |NewProtect = PAGE_EXECUTE_READWRITE 10010FE6 |. 6A 06 push 0x6 ; |Size = 6 10010FE8 |. 53 push ebx ; |Address => JDPlayer.0040B50B 10010FE9 |. FFD6 call esi ; \VirtualProtect
程式碼中對播放器一個地址:0040B50B 進行了屬性更改,F8往下走看到關鍵地方:
1001102F |. 68 94010210 push sunflove.10020194 ; /patch 10011034 |. 68 84010210 push sunflove.10020184 ; |/sunflover.dll 10011039 |. C745 C8 609C8>mov [local.14],0xFA839C60 ; || 10011040 |. C745 CC 00741>mov [local.13],0x83177400 ; || 10011047 |. C745 D0 7AFC0>mov [local.12],0x750EFC7A ; || 1001104E |. C745 D4 11807>mov [local.11],0x127A8011 ; || 10011055 |. C745 D8 2D750>mov [local.10],0x520B752D ; || 1001105C |. C645 DC B8 mov byte ptr ss:[ebp-0x24],0xB8 ; || 10011060 |. C745 E1 FFD08>mov dword ptr ss:[ebp-0x1F],0xC483D0FF ; || 10011067 |. C745 E5 049D6>mov dword ptr ss:[ebp-0x1B],0x8B619D04 ; || 1001106E |. C745 E9 44240>mov dword ptr ss:[ebp-0x17],0x85042444 ; || 10011075 |. 66:C745 ED FF>mov word ptr ss:[ebp-0x13],0x68FF ; || 1001107B |. C645 F3 C3 mov byte ptr ss:[ebp-0xD],0xC3 ; || 1001107F |. FF15 58D00110 call dword ptr ds:[<&KERNEL32.GetModuleHand>; |\GetModuleHandleA 10011085 |. 50 push eax ; |hModule 10011086 |. FF15 54D00110 call dword ptr ds:[<&KERNEL32.GetProcAddres>; \GetProcAddress 1001108C |. 8D53 06 lea edx,dword ptr ds:[ebx+0x6] 1001108F |. 8945 DD mov dword ptr ss:[ebp-0x23],eax 10011092 |. 8955 EF mov dword ptr ss:[ebp-0x11],edx 10011095 |. B9 0B000000 mov ecx,0xB 1001109A |. 8D75 C8 lea esi,[local.14] 1001109D |. 68 70010210 push sunflove.10020170 ; /inject complete!\r\n 100110A2 |. F3:A5 rep movs dword ptr es:[edi],dword ptr ds:[e>; | 100110A4 |. FF15 74D00110 call dword ptr ds:[<&KERNEL32.OutputDebugSt>; \OutputDebugStringA
從彙編程式碼來看,它對一個地址(新申請的一空間)進行了填充,並載入DLL呼叫了本身內的函式:patch(這是一個匯出函式,使用工具可以看到DLL確實匯出了該函式)
現在我們直接來到播放器位置:0040B50B
0040B50B 68 00003800 push 0x380000 0040B510 C3 retn
上面彙編程式碼中,進行屬性更改後,也對該地址進行了HOOK,當執行到該地址就進入到0x380000 ,我們看下該地址有什麼內容
00380000 60 pushad 00380001 9C pushfd 00380002 83FA 00 cmp edx,0x0 00380005 74 17 je X0038001E 00380007 837A FC 0E cmp dword ptr ds:[edx-0x4],0xE 0038000B 75 11 jnz X0038001E 0038000D 807A 12 2D cmp byte ptr ds:[edx+0x12],0x2D 00380011 75 0B jnz X0038001E 00380013 52 push edx 00380014 B8 C0100110 mov eax,sunflove.patch 00380019 FFD0 call eax 0038001B 83C4 04 add esp,0x4 0038001E 9D popfd 0038001F 61 popad 00380020 8B4424 04 mov eax,dword ptr ss:[esp+0x4] 00380024 85FF test edi,edi 00380026 68 11B54000 push 0x40B511 0038002B C3 retn
程式碼是不是很熟悉?對,就是前面它填充的資料。 這裡有一個地方就是上面獲取的一個匯出函式地址:
00380014 B8 C0100110 [color=#ff0000]mov eax,0x100110C0;patch[/color] 00380019 FFD0 call eax
說了那麼多,我們直接跟一下,在上面關鍵位置下斷,F9執行後,新增視訊,看是否會斷在此處。
一直斷在了00380000 60 pushad
我們直接取消斷點,讓播放器載入起來後,選中加密視訊後,在下斷。斷下後,該處在一直做判斷。先判斷EDX是否為0,是0返回執行到播放器自身處理,還有比較EDX-4,EDX+0X12的內空是否為0XE,0X2D,檢測這個主要是當EDX的值是機器碼內容時,就檢測它的位數和第5位是不是-,我們的機器碼是:1111-2222-3333.通過這些判斷後,確定是機器碼後,執行HOOK的程式碼,進入到0x100110C0 對EDX的值進行替換。
替換的關鍵處:
10012674 > \8B448E E4 mov eax,dword ptr ds:[esi+ecx*4-0x1C] 10012678 . 89448F E4 mov dword ptr ds:[edi+ecx*4-0x1C],eax 1001267C > 8B448E E8 mov eax,dword ptr ds:[esi+ecx*4-0x18] 10012680 . 89448F E8 mov dword ptr ds:[edi+ecx*4-0x18],eax 10012684 > 8B448E EC mov eax,dword ptr ds:[esi+ecx*4-0x14] 10012688 . 89448F EC mov dword ptr ds:[edi+ecx*4-0x14],eax 1001268C > 8B448E F0 mov eax,dword ptr ds:[esi+ecx*4-0x10] 10012690 . 89448F F0 mov dword ptr ds:[edi+ecx*4-0x10],eax 10012694 > 8B448E F4 mov eax,dword ptr ds:[esi+ecx*4-0xC] 10012698 . 89448F F4 mov dword ptr ds:[edi+ecx*4-0xC],eax 1001269C > 8B448E F8 mov eax,dword ptr ds:[esi+ecx*4-0x8] 100126A0 . 89448F F8 mov dword ptr ds:[edi+ecx*4-0x8],eax 100126A4 > 8B448E FC mov eax,dword ptr ds:[esi+ecx*4-0x4] 100126A8 . 89448F FC mov dword ptr ds:[edi+ecx*4-0x4],eax 100126AC . 8D048D 000000>lea eax,dword ptr ds:[ecx*4] 100126B3 . 03F0 add esi,eax 100126B5 . 03F8 add edi,eax 100126B7 > FF2495 C02601>jmp dword ptr ds:[edx*4+0x100126C0]
替換完後,在執行HOOK前的程式碼回到播放器空間中
00380020 8B4424 04 mov eax,dword ptr ss:[esp+0x4] 00380024 85FF test edi,edi 00380026 68 11B54000 push 0x40B511 0038002B C3 retn
到此該DLL替換機器碼的功能就分析完了。
執行播放器後,機器碼也成功替換,輸入密碼就能直接播放樣本視訊。
總結:
1、DLL啟動直接對函式:CreateWindowExA 進行了HOOK,當播放器執行到該函式後,對播放器地址:0040B50B 進行了HOOK
2、HOOK的關鍵函式功能是:先判斷EDX是否為0,是0返回執行到播放器自身處理,還有比較EDX-4,EDX+0X12的內空是否為0XE,0X2D,檢測這個主要是當EDX的值是機器碼內容時,就檢測它的位數是否為:0XE和第5位是不是-,我們的機器碼是:1111-2222-3333.通過這些判斷確定是機器碼後,執行HOOK的程式碼,進入到0x100110C0 對EDX的值進行替換。
3、分析發現機器碼資訊有CPU,硬碟,網絡卡,當機器碼加密都選中了,該DLL才能使用。還有2種可能,單獨選一種硬體或選2種硬體生成的機器碼時該DLL就無效了;不過分析這方法後,我們對替換的程式碼手動修改下就能實現另外的2種機器碼的替換了。
4、作者把執行的每一步都做了除錯輸出,可以很方便看到執行到哪步。大家可以用工具檢視到。
5、該套工具的功能就都分析完了,能力有限,菜鳥水平,不足的地方還請見諒。
金盾2018SS加密視訊機器碼替換工具的分析過程三
http://www.it0365.com/thread-25-1-1.html
(出處: IT資源社群)