亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

C++封裝IATHOOK類實(shí)例

 更新時(shí)間:2014年10月17日 10:29:23   投稿:shichen2014  
這篇文章主要介紹了C++封裝IATHOOK類的實(shí)現(xiàn)方法,對(duì)IAT的HOOK實(shí)例進(jìn)行了封裝,非常具有實(shí)用價(jià)值,需要的朋友可以參考下

本文實(shí)例講述了C++封裝IATHOOK類的實(shí)現(xiàn)方法。分享給大家供大家參考。具體方法如下:

1. 定義成類的靜態(tài)成員,從而實(shí)現(xiàn)自動(dòng)調(diào)用

復(fù)制代碼 代碼如下:
static CAPIHOOK sm_LoadLibraryA; 
static CAPIHOOK sm_LoadLibraryW; 
static CAPIHOOK sm_LoadLibraryExA; 
static CAPIHOOK sm_LoadLibraryExW; 
static CAPIHOOK sm_GetProcAddress;

2. ReplaceIATEntryInAllMods中遍歷模塊的框架

復(fù)制代碼 代碼如下:
void CAPIHOOK::ReplaceIATEntryInAllMods(LPCTSTR pszExportMod, PROC pfnCurrent, PROC pfnNewFunc, BOOL bExcludeAPIHookMod) 

    //取得當(dāng)前模塊句柄 
    HMODULE hModThis = NULL; 
    if (bExcludeAPIHookMod) 
    { 
        MEMORY_BASIC_INFORMATION mbi; 
        if (0 != ::VirtualQuery(ReplaceIATEntryInAllMods, &mbi, sizeof(MEMORY_BASIC_INFORMATION))) //ReplaceIATEntryInAllMods必須為類的static函數(shù) 
        { 
            hModThis = (HMODULE)mbi.AllocationBase; 
        } 
    } 
    //取得本進(jìn)程的模塊列表 
    HANDLE hModuleSnap = INVALID_HANDLE_VALUE;  
    MODULEENTRY32 me32; 
    hModuleSnap = ::CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, GetCurrentProcessId()); 
    if (INVALID_HANDLE_VALUE == hModuleSnap) 
    { 
        return; 
    } 
    me32.dwSize = sizeof( MODULEENTRY32 );  
    if( !Module32First( hModuleSnap, &me32 ) )  
    {  
        return; 
    } 
    do  
    { //對(duì)每一個(gè)模塊 
        if (me32.hModule != hModThis) 
        { 
            ReplaceIATEntryInOneMod(pszExportMod, pfnCurrent, pfnNewFunc, me32.hModule); 
        } 
    } while( Module32Next( hModuleSnap, &me32 ) );  
 
 
    ::CloseHandle(hModuleSnap); //配對(duì)寫 
 
}

3. 遍歷鏈表摘除自己的框架

復(fù)制代碼 代碼如下:
CAPIHOOK::~CAPIHOOK(void) 

    //取消對(duì)函數(shù)的HOOK 
    ReplaceIATEntryInAllMods(m_pszModName, m_pfnHook, m_pfnOrig, TRUE); 
 
    //把自己從鏈表中刪除 
    CAPIHOOK* p = sm_pHeader; 
    if (p == this) 
    { 
        sm_pHeader = this->m_pNext; 
    } 
    else 
    { 
        while(p != NULL) 
        { 
            if (p->m_pNext == this) 
            { 
                p->m_pNext = this->m_pNext; 
                break; 
            } 
            p = p->m_pNext; 
        } 
    } 
}

4. 在cpp中靜態(tài)變量寫好后,再編譯,不然容易出現(xiàn)LINK錯(cuò)誤

復(fù)制代碼 代碼如下:
CAPIHOOK *CAPIHOOK::sm_pHeader = NULL;

源碼:

.cpp源文件如下:

復(fù)制代碼 代碼如下:
#include "APIHOOK.h" 
#include <Tlhelp32.h> 
 
CAPIHOOK *CAPIHOOK::sm_pHeader = NULL; 
CAPIHOOK CAPIHOOK::sm_LoadLibraryA("kernel32.dll", "LoadLibraryA", (PROC)CAPIHOOK::LoadLibraryA, TRUE); 
CAPIHOOK CAPIHOOK::sm_LoadLibraryW("kernel32.dll", "LoadLibraryW", (PROC)CAPIHOOK::LoadLibraryW, TRUE); 
CAPIHOOK CAPIHOOK::sm_LoadLibraryExA("kernel32.dll", "LoadLibraryExA", (PROC)CAPIHOOK::LoadLibraryExA, TRUE); 
CAPIHOOK CAPIHOOK::sm_LoadLibraryExW("kernel32.dll", "LoadLibraryExW", (PROC)CAPIHOOK::LoadLibraryExW, TRUE); 
CAPIHOOK CAPIHOOK::sm_GetProcAddress("kernel32.dll", "GetProcAddress", (PROC)CAPIHOOK::GetProcess, TRUE); 
CAPIHOOK::CAPIHOOK(LPTSTR lpszModName, LPSTR pszFuncName, PROC pfnHook, BOOL bExcludeAPIHookMod) 

    //初始化變量 
    m_pszModName = lpszModName; 
    m_pszFuncName = pszFuncName; 
    m_pfnOrig = ::GetProcAddress(::GetModuleHandleA(lpszModName), pszFuncName); 
    m_pfnHook = pfnHook; 
 
    //將此對(duì)象加入鏈表中 
    m_pNext = sm_pHeader; 
    sm_pHeader = this; 
 
    //在當(dāng)前已加載的模塊中HOOK這個(gè)函數(shù) 
    ReplaceIATEntryInAllMods(lpszModName, m_pfnOrig, m_pfnHook, bExcludeAPIHookMod); 

 
CAPIHOOK::~CAPIHOOK(void) 

    //取消對(duì)函數(shù)的HOOK 
    ReplaceIATEntryInAllMods(m_pszModName, m_pfnHook, m_pfnOrig, TRUE); 
 
    //把自己從鏈表中刪除 
    CAPIHOOK* p = sm_pHeader; 
    if (p == this) 
    { 
        sm_pHeader = this->m_pNext; 
    } 
    else 
    { 
        while(p != NULL) 
        { 
            if (p->m_pNext == this) 
            { 
                p->m_pNext = this->m_pNext; 
                break; 
            } 
            p = p->m_pNext; 
        } 
    } 

//防止程序運(yùn)行期間動(dòng)態(tài)加載模塊 
void CAPIHOOK::HookNewlyLoadedModule(HMODULE hModule, DWORD dwFlags) 

    if (hModule!=NULL && (dwFlags&LOAD_LIBRARY_AS_DATAFILE)==0) 
    { 
        CAPIHOOK* p = sm_pHeader;  //循環(huán)遍歷鏈表,對(duì)每個(gè)CAPIHOOK進(jìn)入HOOK 
        if (p != NULL)   
        { 
            ReplaceIATEntryInOneMod(p->m_pszModName, p->m_pfnOrig, p->m_pfnHook, hModule); 
            p = p->m_pNext; 
        } 
    } 

//防止程序運(yùn)行期間動(dòng)態(tài)調(diào)用API函數(shù) 
FARPROC WINAPI CAPIHOOK::GetProcess(HMODULE hModule, PCSTR pszProcName) 

    //得到函數(shù)的真實(shí)地址 
    FARPROC pfn = ::GetProcAddress(hModule, pszProcName); 
    //遍歷列表 看是不是要HOOK的函數(shù) 
    CAPIHOOK* p = sm_pHeader; 
    while(p != NULL) 
    { 
        if (p->m_pfnOrig == pfn) //是要HOOK的函數(shù) 
        { 
            pfn = p->m_pfnHook; //HOOK掉 
            break; 
        } 
        p = p->m_pNext; 
    } 
    return pfn; 

 
void CAPIHOOK::ReplaceIATEntryInOneMod(LPCTSTR pszExportMod, PROC pfnCurrent, PROC pfnNewFunc, HMODULE hModCaller) 

    IMAGE_DOS_HEADER* pDosHeader = (IMAGE_DOS_HEADER*)hModCaller; 
    IMAGE_OPTIONAL_HEADER* pOpNtHeader = (IMAGE_OPTIONAL_HEADER*)((BYTE*)hModCaller + pDosHeader->e_lfanew + 24); //這里加24 
    IMAGE_IMPORT_DESCRIPTOR* pImportDesc = (IMAGE_IMPORT_DESCRIPTOR*)((BYTE*)hModCaller + pOpNtHeader->DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress); 
 
    BOOL bFindDll = FALSE; 
    while (pImportDesc->FirstThunk) 
    { 
        char* pszDllName = (char*)((BYTE*)hModCaller + pImportDesc->Name); 
 
        if (stricmp(pszDllName, pszExportMod) == 0)//如果找到pszExportMod模塊,相當(dāng)于hook messageboxa時(shí)的“user32.dll” 
        { 
            bFindDll = TRUE; 
            break; 
        } 
        pImportDesc++;   
    } 
 
    if (bFindDll) 
    { 
        DWORD n = 0; 
        //一個(gè)IMAGE_THUNK_DATA就是一個(gè)導(dǎo)入函數(shù) 
        IMAGE_THUNK_DATA* pThunk = (IMAGE_THUNK_DATA*)((BYTE*)hModCaller + pImportDesc->OriginalFirstThunk); 
        while (pThunk->u1.Function) 
        { 
            //取得函數(shù)名稱 
            char* pszFuncName = (char*)((BYTE*)hModCaller+pThunk->u1.AddressOfData+2); //函數(shù)名前面有兩個(gè).. 
            //printf("function name:%-25s,  ", pszFuncName); 
            //取得函數(shù)地址 
            PDWORD lpAddr = (DWORD*)((BYTE*)hModCaller + pImportDesc->FirstThunk) + n; //從第一個(gè)函數(shù)的地址,以后每次+4字節(jié) 
            //printf("addrss:%X\n", lpAddr); 
            //在這里是比較的函數(shù)地址 
            if (*lpAddr == (DWORD)pfnCurrent)  //找到iat中的函數(shù)地址 
            {                                
                DWORD* lpNewProc = (DWORD*)pfnNewFunc; 
                MEMORY_BASIC_INFORMATION mbi; 
                DWORD dwOldProtect; 
                //修改內(nèi)存頁(yè)的保護(hù)屬性 
                ::VirtualQuery(lpAddr, &mbi, sizeof(MEMORY_BASIC_INFORMATION)); 
                ::VirtualProtect(lpAddr, sizeof(DWORD), PAGE_READWRITE, &dwOldProtect); 
                ::WriteProcessMemory(GetCurrentProcess(), lpAddr, &lpNewProc, sizeof(DWORD), NULL); 
                ::VirtualProtect(lpAddr, sizeof(DWORD), dwOldProtect, NULL); 
                return; 
            }            
            n++; //每次增加一個(gè)DWORD 
        }    
    } 

 
void CAPIHOOK::ReplaceIATEntryInAllMods(LPCTSTR pszExportMod, PROC pfnCurrent, PROC pfnNewFunc, BOOL bExcludeAPIHookMod) 

    //取得當(dāng)前模塊句柄 
    HMODULE hModThis = NULL; 
    if (bExcludeAPIHookMod) 
    { 
        MEMORY_BASIC_INFORMATION mbi; 
        if (0 != ::VirtualQuery(ReplaceIATEntryInAllMods, &mbi, sizeof(MEMORY_BASIC_INFORMATION))) //ReplaceIATEntryInAllMods必須為類的static函數(shù) 
        { 
            hModThis = (HMODULE)mbi.AllocationBase; 
        } 
    } 
    //取得本進(jìn)程的模塊列表 
    HANDLE hModuleSnap = INVALID_HANDLE_VALUE;  
    MODULEENTRY32 me32; 
    hModuleSnap = ::CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, GetCurrentProcessId()); 
    if (INVALID_HANDLE_VALUE == hModuleSnap) 
    { 
        return; 
    } 
    me32.dwSize = sizeof( MODULEENTRY32 );  
    if( !Module32First( hModuleSnap, &me32 ) )  
    {  
        return; 
    } 
    do  
    { //對(duì)每一個(gè)模塊 
        if (me32.hModule != hModThis) 
        { 
            ReplaceIATEntryInOneMod(pszExportMod, pfnCurrent, pfnNewFunc, me32.hModule); 
        } 
    } while( Module32Next( hModuleSnap, &me32 ) );  
 
    ::CloseHandle(hModuleSnap); //配對(duì)寫 

 
//防止自動(dòng)加載 
HMODULE WINAPI CAPIHOOK::LoadLibraryA(LPCTSTR lpFileName) 

    HMODULE hModule = LoadLibraryA(lpFileName); 
    HookNewlyLoadedModule(hModule, 0); //這個(gè)函數(shù)中憶檢測(cè)hModule 了 
    return hModule; 

HMODULE WINAPI CAPIHOOK::LoadLibraryW(LPCTSTR lpFileName) 

    HMODULE hModule = LoadLibraryW(lpFileName); 
    HookNewlyLoadedModule(hModule, 0); //這個(gè)函數(shù)中憶檢測(cè)hModule 了 
    return hModule; 

HMODULE WINAPI CAPIHOOK::LoadLibraryExA(LPCTSTR lpFileName, HANDLE hFile,  DWORD dwFlags) 

    HMODULE hModule = LoadLibraryExA(lpFileName, hFile, dwFlags); 
    HookNewlyLoadedModule(hModule, dwFlags); //這個(gè)函數(shù)中憶檢測(cè)hModule 了 
    return hModule; 

HMODULE WINAPI CAPIHOOK::LoadLibraryExW(LPCTSTR lpFileName, HANDLE hFile,  DWORD dwFlags) 

    HMODULE hModule = LoadLibraryExW(lpFileName, hFile, dwFlags); 
    HookNewlyLoadedModule(hModule, dwFlags); //這個(gè)函數(shù)中憶檢測(cè)hModule 了 
    return hModule; 
}

.h頭文件如下:

復(fù)制代碼 代碼如下:
#pragma once 
#include <Windows.h> 
 
class CAPIHOOK 

public: 
    CAPIHOOK(LPTSTR lpszModName, LPSTR pszFuncName, PROC pfnHook, BOOL bExcludeAPIHookMod = TRUE); 
    ~CAPIHOOK(void); 
 
private: 
    static void ReplaceIATEntryInOneMod(LPCTSTR pszExportMod, PROC pfnCurrent, PROC pfnNewFunc, HMODULE hModCaller); 
    static void ReplaceIATEntryInAllMods(LPCTSTR pszExportMod, PROC pfnCurrent, PROC pfnNewFunc, BOOL bExcludeAPIHookMod); 
    //防止程序運(yùn)行期間動(dòng)態(tài)加載模塊, 當(dāng)一個(gè)新DLL被加載時(shí)調(diào)用 
    static void HookNewlyLoadedModule(HMODULE hModule,  DWORD dwFlags); 
 
    //跟蹤當(dāng)前進(jìn)程加載新的DLL 
    static HMODULE WINAPI LoadLibraryA(LPCTSTR lpFileName); 
    static HMODULE WINAPI LoadLibraryW(LPCTSTR lpFileName); 
    static HMODULE WINAPI LoadLibraryExA(LPCTSTR lpFileName, HANDLE hFile,  DWORD dwFlags); 
    static HMODULE WINAPI LoadLibraryExW(LPCTSTR lpFileName, HANDLE hFile,  DWORD dwFlags); 
    //防止程序運(yùn)行期間動(dòng)態(tài)調(diào)用API函數(shù) 對(duì)于請(qǐng)求已HOOK的API函數(shù),返回用戶自定義的函數(shù)地址 
    static FARPROC WINAPI GetProcess(HMODULE hModule, PCSTR pszProcName);
 
private: //定義成靜態(tài)的,會(huì)自動(dòng)調(diào)用,從而實(shí)現(xiàn)自動(dòng)HOOK 
    static CAPIHOOK sm_LoadLibraryA; 
    static CAPIHOOK sm_LoadLibraryW; 
    static CAPIHOOK sm_LoadLibraryExA; 
    static CAPIHOOK sm_LoadLibraryExW; 
    static CAPIHOOK sm_GetProcAddress; 
 
private: 
    static CAPIHOOK* sm_pHeader; //鉤子鏈表 
    CAPIHOOK* m_pNext; 
 
    //要鉤子的函數(shù) 
    PROC m_pfnOrig; 
    PROC m_pfnHook; 
 
    //要鉤子的函數(shù)所在的dll 
    LPSTR m_pszModName; 
    //要鉤子的函數(shù)名稱 
    LPSTR m_pszFuncName; 
};

希望本文所述對(duì)大家的C++程序設(shè)計(jì)有所幫助。

相關(guān)文章

  • C++實(shí)現(xiàn)單鏈表刪除倒數(shù)第k個(gè)節(jié)點(diǎn)的方法

    C++實(shí)現(xiàn)單鏈表刪除倒數(shù)第k個(gè)節(jié)點(diǎn)的方法

    這篇文章主要介紹了C++實(shí)現(xiàn)單鏈表刪除倒數(shù)第k個(gè)節(jié)點(diǎn)的方法,結(jié)合實(shí)例形式分析了C++單鏈表的定義、遍歷及刪除相關(guān)操作技巧,需要的朋友可以參考下
    2017-05-05
  • 矩陣的行主序與列主序的分析

    矩陣的行主序與列主序的分析

    這篇文章主要介紹了矩陣的行主序與列主序的分析的相關(guān)資料,需要的朋友可以參考下
    2017-07-07
  • 詳解C/C++實(shí)現(xiàn)各種字符轉(zhuǎn)換方法合集

    詳解C/C++實(shí)現(xiàn)各種字符轉(zhuǎn)換方法合集

    這篇文章主要為大家詳細(xì)介紹了C/C++中實(shí)現(xiàn)各種字符轉(zhuǎn)換的方法,文中的示例代碼講解詳細(xì),對(duì)我們學(xué)習(xí)C++具有一定借鑒價(jià)值,需要的可以參考一下
    2022-09-09
  • 字符串的模式匹配詳解--BF算法與KMP算法

    字符串的模式匹配詳解--BF算法與KMP算法

    這篇文章記錄一下串里面的模式匹配,模式匹配,顧名思義就是給定一個(gè)被匹配的字符串,然后用一個(gè)字符串模式(模型)去匹配上面說(shuō)的字符串,看后者是否在前者里面出現(xiàn)。常用的有2種算法可以實(shí)現(xiàn),下面我們來(lái)具體探討下
    2014-08-08
  • opencv3/C++基于顏色的目標(biāo)跟蹤方式

    opencv3/C++基于顏色的目標(biāo)跟蹤方式

    今天小編就為大家分享一篇opencv3/C++基于顏色的目標(biāo)跟蹤方式,具有很好的參考價(jià)值,希望對(duì)的有所幫助。一起跟隨小編過(guò)來(lái)看看吧
    2019-12-12
  • C語(yǔ)言關(guān)鍵字總結(jié)解析

    C語(yǔ)言關(guān)鍵字總結(jié)解析

    這篇文章主要介紹了C語(yǔ)言關(guān)鍵字總結(jié)解析,本篇文章通過(guò)簡(jiǎn)要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是本文的詳細(xì)內(nèi)容,需要的朋友可以參考下
    2021-07-07
  • 解析c語(yǔ)言中"函數(shù)調(diào)用中缺少哨兵"的情況分析

    解析c語(yǔ)言中"函數(shù)調(diào)用中缺少哨兵"的情況分析

    本篇文章是對(duì)c語(yǔ)言中"函數(shù)調(diào)用中缺少哨兵"的情況進(jìn)行了詳細(xì)的分析介紹,需要的朋友參考下
    2013-05-05
  • 基于C語(yǔ)言中野指針的深入解析

    基于C語(yǔ)言中野指針的深入解析

    “野指針”不是NULL指針,是指向“垃圾”內(nèi)存的指針。人們一般不會(huì)錯(cuò)用NULL指針,因?yàn)橛胕f語(yǔ)句很容易判斷。但是“野指針”是很危險(xiǎn)的,if語(yǔ)句對(duì)它不起作用
    2013-07-07
  • Pthread并發(fā)編程之線程基本元素和狀態(tài)的剖析

    Pthread并發(fā)編程之線程基本元素和狀態(tài)的剖析

    本篇文章主要給大家介紹pthread并發(fā)編程當(dāng)中關(guān)于線程的基礎(chǔ)概念,并且深入剖析進(jìn)程的相關(guān)屬性和設(shè)置,以及線程在內(nèi)存當(dāng)中的布局形式,幫助大家深刻理解線程
    2022-11-11
  • C++ 虛函數(shù)專題

    C++ 虛函數(shù)專題

    這篇文章主要介紹了C++中虛函數(shù)的知識(shí)點(diǎn),文中配合代碼講解非常細(xì)致,供大家參考和學(xué)習(xí),感興趣的朋友可以了解下
    2020-06-06

最新評(píng)論