首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> VC >> 關於VC++

獲取他進程視窗程序:遠程線程注入 + 機器碼構造技術深度解析

     編輯:關於VC++

GetWindowLong(hWnd, GWL_WNDPROC) 只能獲取「同進程」視窗的視窗程序。跨進程調用會直接返回 0。本文詳述一種不依賴全域 Hook、輕量級的方案:在目標進程建立遠程線程,執行機器碼級別的 GetWindowLong + PostThreadMessage 回報結果。

為什麼不直接用 GetWindowLong?

系統內部會檢查調用進程 ID 與視窗所屬進程 ID 是否一致,不一致則返回 0。Spy++ 使用全域 Hook (WH_GETMESSAGE) 讓 DLL 注入所有進程繞過此限制,但為單一查詢裝載 Hook 過於沉重。

遠程線程注入核心步驟

  1. 取得目標進程資訊:GetWindowThreadProcessId(hWndTarget, &dwProcessId)。
  2. 開啟進程權限:OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId),失敗時需 AdjustTokenPrivileges 提權。
  3. 判斷 Unicode/ANSI:IsWindowUnicode(hWndTarget) 決定呼叫 GetWindowLongW 仍是 GetWindowLongA。
  4. 目標進程配置記憶體:VirtualAllocEx(hProcess, NULL, 34, MEM_COMMIT, PAGE_EXECUTE_READWRITE),預留 34 位元組 (指令碼 + ret)。
  5. 構造機器碼指令碼 (本地組裝後寫入):
    // 假設 hWndTarget=0x12345678, dwThreadId=0x5678, 自訂訊息 WM_MYMSG=0x1234
    // GetWindowLongA(hWndTarget, GWL_WNDPROC)  ; GWL_WNDPROC = -4 = 0xFC
    6A FC                push 0xFC
    68 78 56 34 12       push 0x12345678
    E8 xx xx xx xx       call GetWindowLongA   ; 相對偏移
    
    50                   push eax              ; lParam = 返回的 WNDPROC
    68 78 56 34 12       push 0x12345678       ; wParam = hWndTarget
    68 34 12 00 00       push 0x1234           ; Msg
    68 78 56 00 00       push 0x5678           ; dwThreadId
    E8 xx xx xx xx       call PostThreadMessageA
    C3                   ret
  6. 寫入記憶體並建立線程:WriteProcessMemory 寫入指令碼 → CreateRemoteThread(hProcess, NULL, 0, pRemoteCode, NULL, 0, NULL)。
  7. 本地訊息迴圈等待回報:
    MSG msg;
    while (GetMessage(&msg, NULL, 0, 0)) {
        if (msg.message == WM_MYMSG) {
            WNDPROC proc = (WNDPROC)msg.lParam; // 取得目標視窗程序
            break;
        }
    }
  8. 清理資源:關閉線程/進程句柄,VirtualFreeEx 釋放遠程記憶體。

關鍵技術細節

  • CALL 指令相對偏移計算:E8 [目標地址 - (當前指址+5)],需在本地精確計算遠程函數地址 (GetProcAddress 取本地 kernel32/user32 地址,假設系統 DLL 基址相同,或需額外解析)。
  • 參數壓棧順序:__stdcall 為右至左 (最後參數先 push)。
  • GWL_WNDPROC 值:-4 (0xFFFFFFFC),32 位元下 push 0xFC 即可 (符號擴展)。

優缺點評估

優點缺點
無需全域 Hook,輕量、針對性強需高權限 (OpenProcess)、依賴機器碼構造,維護難度高
適用單次查詢場景64 位元進程無法從 32 位元注入 (需同位元編譯)、ASLR 可能導致系統 DLL 基址不同

完整可編譯範例碼請參考原文配套源碼。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved