Inject-APC (Ring3)

  1 // APCInject.cpp : 定义控制台应用程序的入口点。
  2 //
  3 
  4 #include "stdafx.h"
  5 #include "APCInject.h"
  6 
  7 #include <windows.h>
  8 #include <TlHelp32.h>
  9 
 10 #include <iostream>
 11 #include <string>
 12  
 13 
 14 
 15 #define _WIN32_WINNT 0x0400
 16 
 17 #define DEF_BUF_SIZE 1024
 18 
 19 
 20 #ifdef _DEBUG
 21 #define new DEBUG_NEW
 22 #endif
 23 
 24 
 25 // 唯一的应用程序对象
 26 
 27 CWinApp theApp;
 28 
 29 using namespace std;
 30 
 31 
 32 typedef long(__fastcall *pfnRtlAdjustPrivilege64)(ULONG, ULONG, ULONG, PVOID);
 33 pfnRtlAdjustPrivilege64 RtlAdjustPrivilege;
 34 BOOL InjectModuleToProcessById(DWORD dwProcessId);
 35 // 用于存储注入模块DLL的路径全名
 36 char szDllPath[DEF_BUF_SIZE] = { 0 };
 37 int main()
 38 {
 39     int nRetCode = 0;
 40     // 取得当前工作目录路径
 41     GetCurrentDirectoryA(DEF_BUF_SIZE, szDllPath);
 42 
 43     // 生成注入模块DLL的路径全名
 44     strcat(szDllPath, "\MessageBox32.dll");
 45 
 46     DWORD dwProcessId = 0;
 47     // 接收用户输入的目标进程ID
 48     while (cout << "请输入目标进程ID:" && cin >> dwProcessId && dwProcessId > 0)
 49     {
 50         BOOL bRet = InjectModuleToProcessById(dwProcessId);
 51         cout << (bRet ? "注入成功!" : "注入失败!") << endl;
 52     }
 53     
 54     return nRetCode;
 55 }
 56 
 57 
 58 
 59 // 使用APC机制向指定ID的进程注入模块
 60 BOOL InjectModuleToProcessById(DWORD dwProcessId)
 61 {
 62     DWORD    dwRet = 0;
 63     BOOL    bStatus = FALSE;
 64     LPVOID    lpData = NULL;
 65     UINT    uLen = strlen(szDllPath) + 1;
 66     LPTHREAD_START_ROUTINE FuncAddress = NULL;
 67     DWORD dwRetVal = 0;
 68 #ifdef _WIN64   // x64 OpenProcess提权操作
 69     //RtlAdjustPrivilege = (pfnRtlAdjustPrivilege64)GetProcAddress((HMODULE)(FuncAddress(L"ntdll.dll")), "RtlAdjustPrivilege");
 70 
 71     //if (RtlAdjustPrivilege == NULL)
 72     //{
 73     //    return FALSE;
 74     //}
 75     ///*
 76     //.常量 SE_BACKUP_PRIVILEGE, "17", 公开
 77     //.常量 SE_RESTORE_PRIVILEGE, "18", 公开
 78     //.常量 SE_SHUTDOWN_PRIVILEGE, "19", 公开
 79     //.常量 SE_DEBUG_PRIVILEGE, "20", 公开
 80     //*/
 81     //RtlAdjustPrivilege(20, 1, 0, &dwRetVal);  //19
 82 #endif
 83                                               // 打开目标进程
 84     HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, dwProcessId);
 85     if (hProcess)
 86     {
 87         // 分配空间
 88         lpData = VirtualAllocEx(hProcess, NULL, uLen, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
 89         if (lpData)
 90         {
 91             // 写入需要注入的模块路径全名
 92             bStatus = WriteProcessMemory(hProcess, lpData, szDllPath, uLen, NULL);
 93         }
 94         CloseHandle(hProcess);
 95     }
 96 
 97     if (bStatus == FALSE)
 98         return FALSE;
 99 
100     // 创建线程快照
101     THREADENTRY32 te32 = { sizeof(THREADENTRY32) };
102     HANDLE hThreadSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0);
103     if (hThreadSnap == INVALID_HANDLE_VALUE)
104         return FALSE;
105 
106     bStatus = FALSE;
107     // 枚举所线程
108     if (Thread32First(hThreadSnap, &te32))
109     {
110         do {
111             // 判断是否目标进程中的线程
112             if (te32.th32OwnerProcessID == dwProcessId)
113             {
114                 // 打开线程
115                 HANDLE hThread = OpenThread(THREAD_ALL_ACCESS, FALSE, te32.th32ThreadID);
116                 if (hThread)
117                 {
118                     // 向指定线程添加APC
119                     DWORD dwRet = QueueUserAPC((PAPCFUNC)LoadLibraryA, hThread, (ULONG_PTR)lpData);
120                     if (dwRet > 0)
121                         bStatus = TRUE;
122                     CloseHandle(hThread);
123                 }
124             }
125 
126         } while (Thread32Next(hThreadSnap, &te32));
127     }
128 
129     CloseHandle(hThreadSnap);
130     return bStatus;
131 }
原文地址:https://www.cnblogs.com/shercy/p/6550080.html