下面写了一个是注册表编辑器DLL注入代码,读取的是右边SysListView 控件的例子
有什么不懂得可以提问,有时间一定解答
DLL 代码 对话框的资源,自己添加!
xx.h
// The following ifdef block is the standard way of creating macros which make exporting // from a DLL simpler. All files within this DLL are compiled with the DYNAMIC_DLL_EXPORTS // symbol defined on the command line. this symbol should not be defined on any project // that uses this DLL. This way any other project whose source files include this file see // DYNAMIC_DLL_API functions as being imported from a DLL, whereas this DLL sees symbols // defined with this macro as being exported. #ifdef DYNAMIC_DLL_EXPORTS #define DYNAMIC_DLL_API __declspec(dllexport) #else #define DYNAMIC_DLL_API __declspec(dllimport) #endif // This class is exported from the dynamic_DLL.dll class DYNAMIC_DLL_API Cdynamic_DLL { public: Cdynamic_DLL(void); // TODO: add your methods here. }; extern DYNAMIC_DLL_API int ndynamic_DLL; DYNAMIC_DLL_API int fndynamic_DLL(void); extern "C" DYNAMIC_DLL_API BOOL SetDIPSHook(DWORD dwThreadId);
xx.cpp
// dynamic_DLL.cpp : Defines the entry point for the DLL application. // #include "stdafx.h" #include "dynamic_DLL.h" #include <stdio.h> #include <winbase.h> #include <Windows.h> #include <WindowsX.h> #include <assert.h> #include "resource.h" #include <atldef.h> #include <CommCtrl.h> #ifdef _MANAGED #pragma managed(push, off) #endif #pragma data_seg("Shared") HHOOK g_hHook = NULL; DWORD g_dwThreadIdDIPS = 0; #pragma data_seg() // Instruct the linker to make the Shared section // readable, writable, and shared. #pragma comment(linker, "/section:Shared,rws") HINSTANCE g_hInstDll = NULL; BOOL APIENTRY DllMain( HMODULE hModule, DWORD ul_reason_for_call, LPVOID lpReserved ) { switch (ul_reason_for_call) { case DLL_PROCESS_ATTACH: g_hInstDll = hModule; printf("process_attach\n"); break; case DLL_THREAD_ATTACH: printf("thread_attach\n"); break; case DLL_THREAD_DETACH: printf("thread_detach\n"); break; case DLL_PROCESS_DETACH: printf("process_detach\n"); break; } return TRUE; } #ifdef _MANAGED #pragma managed(pop) #endif // This is an example of an exported variable DYNAMIC_DLL_API int ndynamic_DLL=0; // This is an example of an exported function. DYNAMIC_DLL_API int fndynamic_DLL(void) { return 42; } // This is the constructor of a class that has been exported. // see dynamic_DLL.h for the class definition Cdynamic_DLL::Cdynamic_DLL() { return; } int MyAdd(int a,int b) { return a + b; } int MyTest() { return 10; } BOOL CALLBACK Dlg_Proc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) { HWND hsysList =NULL; TCHAR buf[256]={0}; HTREEITEM itemChild,Itemtwo,ItemThree; HTREEITEM itemRoot; TVITEMEX iteminfo; TCHAR temBuf[512]; DWORD dwLen = 0; BOOL brs; switch(message) { case WM_APP: hsysList = (HWND)wParam; { DWORD dwMax = ListView_GetItemCount(hsysList); for (DWORD i=0; i < dwMax; ++i) { TCHAR Name[256] = {0}; ListView_GetItemText(hsysList,i,0,Name,256); OutputDebugString(Name); } } // itemRoot = TreeView_GetRoot(hwnd); // brs = TreeView_Expand(hwnd, itemRoot,TVM_EXPAND); // itemChild = TreeView_GetChild(hwnd,itemRoot); // Itemtwo = TreeView_GetNextSibling(hwnd, itemChild); // iteminfo.hItem = itemChild; // iteminfo.mask = TVIF_TEXT; // iteminfo.pszText = temBuf; // iteminfo.cchTextMax = 512; // // TreeView_GetItem(hwnd,&iteminfo); // // iteminfo.hItem = Itemtwo; // // TreeView_GetItem(hwnd,&iteminfo); return (TRUE); case WM_INITDIALOG: { // MessageBox(NULL,L"1",L"1",MB_OK); ShowWindow(hDlg,SW_SHOWNORMAL); } return (TRUE); case WM_CLOSE: { DestroyWindow(hDlg); } return (TRUE); case WM_COMMAND: switch (LOWORD(wParam)) { case IDCANCEL: { SendMessage(hDlg, WM_CLOSE, 0, 0); } return (TRUE); case IDOK: { } return (TRUE); } return (FALSE); } return (FALSE); } LRESULT WINAPI GetMsgProc(int nCode, WPARAM wParam, LPARAM lParam) { static BOOL bFirstTime = TRUE; if (bFirstTime) { // The DLL just got injected. bFirstTime = FALSE; // Uncomment the line below to invoke the debugger // on the process that just got the injected DLL. // ForceDebugBreak(); // Create the DIPS Server window to handle the client request. CreateDialog(g_hInstDll, MAKEINTRESOURCE(IDD_DIALOG1), NULL, Dlg_Proc); // Tell the DIPS application that the server is up // and ready to handle requests. PostThreadMessage(g_dwThreadIdDIPS, WM_NULL, 0, 0); } return(CallNextHookEx(g_hHook, nCode, wParam, lParam)); } DYNAMIC_DLL_API BOOL SetDIPSHook(DWORD dwThreadId) { BOOL bOk = FALSE; if (dwThreadId != 0) { // Make sure that the hook is not already installed. assert(g_hHook == NULL); // Save our thread ID in a shared variable so that our GetMsgProc // function can post a message back to the thread when the server // window has been created. g_dwThreadIdDIPS = GetCurrentThreadId(); // Install the hook on the specified thread g_hHook = SetWindowsHookEx(WH_GETMESSAGE, GetMsgProc, g_hInstDll, dwThreadId); bOk = (g_hHook != NULL); if (bOk) { // The hook was installed successfully; force a benign message to // the thread's queue so that the hook function gets called. bOk = PostThreadMessage(dwThreadId, WM_NULL, 0, 0); } } else { // Make sure that a hook has been installed. assert(g_hHook != NULL); bOk = UnhookWindowsHookEx(g_hHook); g_hHook = NULL; } return(bOk); }
main.cpp
#include <stdio.h> #include <windows.h> #include <process.h> #include "dynamic_DLL.h" #include <assert.h> int main(int argc, char* argv[]) { HWND hRegEdit_RegEdit = FindWindow(L"RegEdit_RegEdit",L"注册表编辑器"); HWND hSysTreeView = GetDlgItem(hRegEdit_RegEdit,01); HWND hSysList = GetDlgItem(hRegEdit_RegEdit,02); BOOL b = SetDIPSHook(GetWindowThreadProcessId(hRegEdit_RegEdit,NULL)); MSG msg; GetMessage(&msg,NULL,0,0); HWND hWndDIPS = FindWindow(NULL, TEXT("myTest")); SendMessage(hWndDIPS, WM_APP, (WPARAM)hSysList, 0); SendMessage(hWndDIPS, WM_CLOSE,0,0); assert(!IsWindow(hWndDIPS)); SetDIPSHook(0); getchar(); return 0; }
下面的代码是在远端进程,创建一个线程,然后加载需要的DLL
/****************************************************************************** Module: InjLib.cpp Notices: Copyright (c) 2008 Jeffrey Richter & Christophe Nasarre ******************************************************************************/ #include "..\CommonFiles\CmnHdr.h" /* See Appendix A. */ #include <windowsx.h> #include <stdio.h> #include <tchar.h> #include <malloc.h> // For alloca #include <TlHelp32.h> #include "Resource.h" #include <StrSafe.h> /////////////////////////////////////////////////////////////////////////////// #ifdef UNICODE #define InjectLib InjectLibW #define EjectLib EjectLibW #else #define InjectLib InjectLibA #define EjectLib EjectLibA #endif // !UNICODE /////////////////////////////////////////////////////////////////////////////// BOOL WINAPI InjectLibW(DWORD dwProcessId, PCWSTR pszLibFile) { BOOL bOk = FALSE; // Assume that the function fails HANDLE hProcess = NULL, hThread = NULL; PWSTR pszLibFileRemote = NULL; __try { // Get a handle for the target process. hProcess = OpenProcess( PROCESS_QUERY_INFORMATION | // Required by Alpha PROCESS_CREATE_THREAD | // For CreateRemoteThread PROCESS_VM_OPERATION | // For VirtualAllocEx/VirtualFreeEx PROCESS_VM_WRITE, // For WriteProcessMemory FALSE, dwProcessId); if (hProcess == NULL) __leave; // Calculate the number of bytes needed for the DLL's pathname int cch = 1 + lstrlenW(pszLibFile); int cb = cch * sizeof(wchar_t); // Allocate space in the remote process for the pathname pszLibFileRemote = (PWSTR) VirtualAllocEx(hProcess, NULL, cb, MEM_COMMIT, PAGE_READWRITE); if (pszLibFileRemote == NULL) __leave; // Copy the DLL's pathname to the remote process' address space if (!WriteProcessMemory(hProcess, pszLibFileRemote, (PVOID) pszLibFile, cb, NULL)) __leave; // Get the real address of LoadLibraryW in Kernel32.dll PTHREAD_START_ROUTINE pfnThreadRtn = (PTHREAD_START_ROUTINE) GetProcAddress(GetModuleHandle(TEXT("Kernel32")), "LoadLibraryW"); if (pfnThreadRtn == NULL) __leave; // Create a remote thread that calls LoadLibraryW(DLLPathname) hThread = CreateRemoteThread(hProcess, NULL, 0, pfnThreadRtn, pszLibFileRemote, 0, NULL); if (hThread == NULL) __leave; // Wait for the remote thread to terminate WaitForSingleObject(hThread, INFINITE); bOk = TRUE; // Everything executed successfully } __finally { // Now, we can clean everything up // Free the remote memory that contained the DLL's pathname if (pszLibFileRemote != NULL) VirtualFreeEx(hProcess, pszLibFileRemote, 0, MEM_RELEASE); if (hThread != NULL) CloseHandle(hThread); if (hProcess != NULL) CloseHandle(hProcess); } return(bOk); } /////////////////////////////////////////////////////////////////////////////// BOOL WINAPI InjectLibA(DWORD dwProcessId, PCSTR pszLibFile) { // Allocate a (stack) buffer for the Unicode version of the pathname SIZE_T cchSize = lstrlenA(pszLibFile) + 1; PWSTR pszLibFileW = (PWSTR) _alloca(cchSize * sizeof(wchar_t)); // Convert the ANSI pathname to its Unicode equivalent StringCchPrintfW(pszLibFileW, cchSize, L"%S", pszLibFile); // Call the Unicode version of the function to actually do the work. return(InjectLibW(dwProcessId, pszLibFileW)); } /////////////////////////////////////////////////////////////////////////////// BOOL WINAPI EjectLibW(DWORD dwProcessId, PCWSTR pszLibFile) { BOOL bOk = FALSE; // Assume that the function fails HANDLE hthSnapshot = NULL; HANDLE hProcess = NULL, hThread = NULL; __try { // Grab a new snapshot of the process hthSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, dwProcessId); if (hthSnapshot == INVALID_HANDLE_VALUE) __leave; // Get the HMODULE of the desired library MODULEENTRY32W me = { sizeof(me) }; BOOL bFound = FALSE; BOOL bMoreMods = Module32FirstW(hthSnapshot, &me); for (; bMoreMods; bMoreMods = Module32NextW(hthSnapshot, &me)) { bFound = (_wcsicmp(me.szModule, pszLibFile) == 0) || (_wcsicmp(me.szExePath, pszLibFile) == 0); if (bFound) break; } if (!bFound) __leave; // Get a handle for the target process. hProcess = OpenProcess( PROCESS_QUERY_INFORMATION | PROCESS_CREATE_THREAD | PROCESS_VM_OPERATION, // For CreateRemoteThread FALSE, dwProcessId); if (hProcess == NULL) __leave; // Get the real address of FreeLibrary in Kernel32.dll PTHREAD_START_ROUTINE pfnThreadRtn = (PTHREAD_START_ROUTINE) GetProcAddress(GetModuleHandle(TEXT("Kernel32")), "FreeLibrary"); if (pfnThreadRtn == NULL) __leave; // Create a remote thread that calls FreeLibrary() hThread = CreateRemoteThread(hProcess, NULL, 0, pfnThreadRtn, me.modBaseAddr, 0, NULL); if (hThread == NULL) __leave; // Wait for the remote thread to terminate WaitForSingleObject(hThread, INFINITE); bOk = TRUE; // Everything executed successfully } __finally { // Now we can clean everything up if (hthSnapshot != NULL) CloseHandle(hthSnapshot); if (hThread != NULL) CloseHandle(hThread); if (hProcess != NULL) CloseHandle(hProcess); } return(bOk); } /////////////////////////////////////////////////////////////////////////////// BOOL WINAPI EjectLibA(DWORD dwProcessId, PCSTR pszLibFile) { // Allocate a (stack) buffer for the Unicode version of the pathname SIZE_T cchSize = lstrlenA(pszLibFile) + 1; PWSTR pszLibFileW = (PWSTR) _alloca(cchSize * sizeof(wchar_t)); // Convert the ANSI pathname to its Unicode equivalent StringCchPrintfW(pszLibFileW, cchSize, L"%S", pszLibFile); // Call the Unicode version of the function to actually do the work. return(EjectLibW(dwProcessId, pszLibFileW)); } /////////////////////////////////////////////////////////////////////////////// BOOL Dlg_OnInitDialog(HWND hWnd, HWND hWndFocus, LPARAM lParam) { chSETDLGICONS(hWnd, IDI_INJLIB); return(TRUE); } /////////////////////////////////////////////////////////////////////////////// void Dlg_OnCommand(HWND hWnd, int id, HWND hWndCtl, UINT codeNotify) { switch (id) { case IDCANCEL: EndDialog(hWnd, id); break; case IDC_INJECT: DWORD dwProcessId = GetDlgItemInt(hWnd, IDC_PROCESSID, NULL, FALSE); if (dwProcessId == 0) { // A process ID of 0 causes everything to take place in the // local process; this makes things easier for debugging. dwProcessId = GetCurrentProcessId(); } TCHAR szLibFile[MAX_PATH]; GetModuleFileName(NULL, szLibFile, _countof(szLibFile)); PTSTR pFilename = _tcsrchr(szLibFile, TEXT('\\')) + 1; _tcscpy_s(pFilename, _countof(szLibFile) - (pFilename - szLibFile), TEXT("22-ImgWalk.DLL")); if (InjectLib(dwProcessId, szLibFile)) { chVERIFY(EjectLib(dwProcessId, szLibFile)); chMB("DLL Injection/Ejection successful."); } else { chMB("DLL Injection/Ejection failed."); } break; } } /////////////////////////////////////////////////////////////////////////////// INT_PTR WINAPI Dlg_Proc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { switch (uMsg) { chHANDLE_DLGMSG(hWnd, WM_INITDIALOG, Dlg_OnInitDialog); chHANDLE_DLGMSG(hWnd, WM_COMMAND, Dlg_OnCommand); } return(FALSE); } /////////////////////////////////////////////////////////////////////////////// int WINAPI _tWinMain(HINSTANCE hInstExe, HINSTANCE, PTSTR pszCmdLine, int) { DialogBox(hInstExe, MAKEINTRESOURCE(IDD_INJLIB), NULL, Dlg_Proc); return(0); } //////////////////////////////// End of File //////////////////////////////////
/****************************************************************************** Module: ImgWalk.cpp Notices: Copyright (c) 2008 Jeffrey Richter & Christophe Nasarre ******************************************************************************/ #include "..\CommonFiles\CmnHdr.h" /* See Appendix A. */ #include <tchar.h> /////////////////////////////////////////////////////////////////////////////// BOOL WINAPI DllMain(HINSTANCE hInstDll, DWORD fdwReason, PVOID fImpLoad) { if (fdwReason == DLL_PROCESS_ATTACH) { char szBuf[MAX_PATH * 100] = { 0 }; PBYTE pb = NULL; MEMORY_BASIC_INFORMATION mbi; while (VirtualQuery(pb, &mbi, sizeof(mbi)) == sizeof(mbi)) { int nLen; char szModName[MAX_PATH]; if (mbi.State == MEM_FREE) mbi.AllocationBase = mbi.BaseAddress; if ((mbi.AllocationBase == hInstDll) || (mbi.AllocationBase != mbi.BaseAddress) || (mbi.AllocationBase == NULL)) { // Do not add the module name to the list // if any of the following is true: // 1. If this region contains this DLL // 2. If this block is NOT the beginning of a region // 3. If the address is NULL nLen = 0; } else { nLen = GetModuleFileNameA((HINSTANCE) mbi.AllocationBase, szModName, _countof(szModName)); } if (nLen > 0) { wsprintfA(strchr(szBuf, 0), "\n%p-%s", mbi.AllocationBase, szModName); } pb += mbi.RegionSize; } // NOTE: Normally, you should not display a message box in DllMain // due to the loader lock described in Chapter 20. However, to keep // this sample application simple, I am violating this rule. chMB(&szBuf[1]); } return(TRUE); } //////////////////////////////// End of File //////////////////////////////////