首页 > 代码库 > Signature Scanning(中文暂时译为"特征码扫描")是在C++(起码我是用C++^^)开发中很好的一种方式

Signature Scanning(中文暂时译为"特征码扫描")是在C++(起码我是用C++^^)开发中很好的一种方式

1.介绍

    本文主要简单介绍在没有代码的情况下,如何从一个动态链接库中获取某个函数的址.主要实现方式为Signature Scanning(特征码扫描)

2.什么是Signature Scanning(特征码扫描)

    我就简单解释一下,其实就是从一个二进制文件的开始位置扫描,一直到文件的末尾的这样一项工作,当扫到某一段与我们所需要的符合时,

那么就说明查找到目标的地址.(感觉说得不够好,这里大家自己补补吧^^.https://wiki.alliedmods.net/Signature_Scanning#What_is_Sigscanning.3F,

当然有C++底的,应该可以通过我下面的代码就能理解了哈^^)

3.准备工作

1).通过逆向工具,这里我推荐IDA哈,如果你有其它工具能得到特征码,那也行.至于IDA自己想办法哈,这里我就不提供了

2).查看此文章以了解如何获取特征码.

3).所需要的二进制文件,与特征码

4.正式开始

    1.获取某二进制文件的基地址与大小,可能通过以下函数获得

 1 DWORD MH_GetModuleBase(HMODULE hModule) //获取二进制文件的基地址 2 {  3     MEMORY_BASIC_INFORMATION mem; 4  5     if (!VirtualQuery(hModule, &mem, sizeof(MEMORY_BASIC_INFORMATION)))  6         return 0; 7  8     return (DWORD)mem.AllocationBase;  9 }10 11 DWORD MH_GetModuleSize(HMODULE hModule) //获取二进制文件的大小12 { 13     return ((IMAGE_NT_HEADERS *)((DWORD)hModule + ((IMAGE_DOS_HEADER *)hModule)->e_lfanew))->OptionalHeader.SizeOfImage; 14 }

 

    2.然后就能过以下函数在加载该进制文件后进行扫描

 1 void *MH_SearchPattern(void *pStartSearch, DWORD dwSearchLen, char *pPattern, DWORD dwPatternLen)  2 {  3     DWORD dwStartAddr = (DWORD)pStartSearch;  4     DWORD dwEndAddr = dwStartAddr + dwSearchLen - dwPatternLen; 5  6     while (dwStartAddr < dwEndAddr) //这里从文件的开始位置扫描,如果没有找到指定特征码的位置的话,就会跳出循环并结束扫描工作;否则会返回所查到的址 7     {  8         bool found = true; 9 10         for (DWORD i = 0; i < dwPatternLen; i++) 11         { 12             char code = *(char *)(dwStartAddr + i);13             //0x2A为跳转码的转换,比如当某一部分为 E8 AB CD 2E 76     call sub_xxxxxxxx时,14             //那么此时除了E8之外,其它的应该更换为2A15             if (pPattern[i] != 0x2A && pPattern[i] != code) 16             { 17                 found = false; 18                 break; 19             } 20         }21 22         if (found) 23             return (void *)dwStartAddr;24 25         dwStartAddr++; 26     }27 28     return 0; 29 }

 

    如果扫描成功,会返回该特征码存在的地址否则返回空

5.这样做有什么用?

    对于函数挂勾有非常大的作用,可能通过Inline Hook直接勾函数,接下来要干什么就自己做吧^^,欢迎吐

补充大概用法:
 1 #define SIG_FUNC "\x55\x8B\xEC\x53\x56\x8B\xF1\x57\x8B\x4E\x2A\xE8\x2A\x2A\x2A\x2A\x56\xB9\x2A\x2A\x2A\x2A\xE8\x2A\x2A\x2A\x2A\x6A" 2  3  4 void *g_pOrigin = NULL; 5 HMODULE g_hModule = NULL; 6 DWORD g_dwBase, g_dwSize; 7  8 g_hModule = LoadLibrary("my.dll"); 9 g_dwBase = MH_GetModuleBase(g_hModule);10 g_dwSize = MH_GetModuleSize(g_hModule);11 g_pOrigin = MH_SearchPattern(g_dwBase, g_dwSize, SIG_FUNC, sizeof(SIG_FUNC) - 1);12 13 正常情况下,g_pOrigin返回就是特征所指向的函数地址了^^

 

Signature Scanning(中文暂时译为"特征码扫描")是在C++(起码我是用C++^^)开发中很好的一种方式