菜鸟的hook法

in 时光记忆 with 1 comment

在论坛闲逛的时候发现了这个,就转载过来,最近再写一个小程序,累点,就没更新,先转篇...

//内核中根据模块名得到模块基地址和模块大小.

//MyGetModuleInfo:根据模块名得到模块的基地址和大小.
#define BASEADDRLEN 10;
...... ULONG
MyGetModuleInfo(
IN  char * ModuleName,
OUT ULONG *pModuleSize
)

{
PSYSTEM_MODULE_INFORMATION    pSysModule;
ULONG            uReturn;
ULONG            uCount;
PCHAR            pBuffer = NULL;
PCHAR            pName    = NULL;
NTSTATUS        status;
UINT            ui;
CHAR            szBuffer[BASEADDRLEN];
ULONG          BaseAddress;
//说来说去就是这个函数的使用.
status = ZwQuerySystemInformation( SystemModuleInformation, szBuffer, BASEADDRLEN, &uReturn );
pBuffer = ( PCHAR )ExAllocatePool( NonPagedPool, uReturn ); if ( pBuffer )
{
status = ZwQuerySystemInformation( SystemModuleInformation, pBuffer, uReturn, &uReturn );
if( status == STATUS_SUCCESS )
{
uCount = ( ULONG )*( ( ULONG * )pBuffer );
pSysModule = ( PSYSTEM_MODULE_INFORMATION )( pBuffer + sizeof( ULONG ) );
for ( ui = 0; ui < uCount; ui++ )
{
pName = strrchr( pSysModule->ImageName, '' );
if ( !pName )
{
pName = pSysModule->ImageName;
}
else {
pName++;
}
if( !_stricmp( pName, ModuleName ) )
{
(*pModuleSize) = pSysModule->Size;
BaseAddress = pSysModule->Base;
ExFreePool( pBuffer );
return BaseAddress;
}
pSysModule ++;
}
}
ExFreePool( pBuffer );
}
return NULL; } //然后可以看看导入表有没有我们想要hook的函数,用这个函数看看.
//如果有,就可以再干点别的.
PIMAGE_IMPORT_DESCRIPTOR
FindTheImportDescriptor(
ULONG BaseAddr,
char *file)

{
PIMAGE_DOS_HEADER pimDH = (PIMAGE_DOS_HEADER)BaseAddr;
PIMAGE_NT_HEADERS pimNH = (PIMAGE_NT_HEADERS)((char*)BaseAddr+pimDH->e_lfanew);
//PIMAGE_IMPORT_DESCRIPTOR.
PIMAGE_IMPORT_DESCRIPTOR pimID = (PIMAGE_IMPORT_DESCRIPTOR)(BaseAddr+pimNH->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress);
char * pName = NULL;
int    ulval=0;
if(pimID == NULL)
return 0;
while(pimID->Name)
{
//DLL文件的名称(0结尾的ASCII码字符串)的32位VA
pName = (char*)(BaseAddr + pimID->Name);
ulval=0;
for(int i=0;pName[i];i++)
{
ulval = pName[i]-file[i];
if(ulval!=0) break;
}
//ulval;
if(ulval==0) break;//如果找到
pimID++;
}
if(pimID->Name)
return pimID; //返回的是结构IMAGE_IMPORT_DESCRIPTOR指针.
else
return 0;
}
//然后可以去hook想要hook的函数. VOID
MyHookFunction(
ULONG BaseAddr,    //模块基地址.
char * DllName,    //要hook的函数位于什么模块,这里是这个模块名.
char * FuncName,  //要hook的函数名.
PVOID  FuncHook,  //新函数地址.
ULONG * lpFunc)    //保存原函数地址.

{
//找到用到DllName的 IMAGE_IMPORT_DESCRIPTOR
PIMAGE_IMPORT_DESCRIPTOR pimID = FindTheImportDescriptor(BaseAddr,DllName);
if(pimID==NULL)  return;
PIMAGE_THUNK_DATA pITD = (PIMAGE_THUNK_DATA)((char *) BaseAddr + pimID->OriginalFirstThunk);
PIMAGE_THUNK_DATA pITD2 = (PIMAGE_THUNK_DATA)((char *) BaseAddr + pimID->FirstThunk);
PIMAGE_IMPORT_BY_NAME pIIBN = NULL;
int    ulval=0;
ULONG  cr0value = 0;
if(0 == pITD->AddressOfData) return TRUE; do
{
if(pITD->AddressOfData < 0x80000000)
{
pIIBN = (PIMAGE_IMPORT_BY_NAME)(pITD->AddressOfData +  BaseAddr);
if(pIIBN->Name[0]=='')
continue;

ulval=0;
for(int i=0;pIIBN->Name[i];i++)
{
ulval = FuncName[i] - pIIBN->Name[i];
if(ulval!=0) break;
}
//ulval;
if(ulval==0) //如果找到
{
CloseWriteProtect(&cr0value);//修改Cr0值来关闭写保护
lpFunc = pITD2->Function;    //保存
pITD2->Function = FuncHook;  //hook
SetCr0(cr0value);            //还原Cr0值
break;
}
}
pITD ++;
pITD2 ++;
}while(pITD!=NULL);
return TRUE;
}

Comments are closed.
  1. 好看的