DLL的11种注入方法 (6)

淡若清风 分享 2020-06-21 下载文档

DLL时你必须知道原有DLL中的函数都有哪些,以免导至其它进程调用DLL时找不到相应的API函数

,特别是在替换系统DLL文件时更要小心。

第六种方法:

无DLL注入

在第三中方法中,我们启动远程线程时,线程函数是我们从Kernel32.dll中取得的

LoadLibrary函数的地址为线程函数的地址,其实我们可以直接将线程函数体和函数参数写入目标

进程的地址空间,然后创建远程线程。

使用这个方法时,需要注意以下几个问题:

(1) 远程线程函数体不得使用kernel32.dll,user32.dll以外的函数。因为这个两个模块在

各个进程的相对地址是一样的,如果一定要使用其它函数,则必须将函数体写入目标进程空间。

(2) 不能使用任何字符串常量,因为字符串常量是存放在PE文件里.data这个段里面的,函数

里保存的只是相对地址。

(3) 去掉编译器的/GZ编译选项,这个选项是用来Enable Stack Frame Run-Time Error

Checking。当这个选项打开时,编译器会在每个函数中加入一些代码,用来检验ESP在函数体中是

否被改变,但是这些检验函数的地址在不同PE文件中有可能是不一样的。 (4) 不得使用增量链接(incremental linking)。增量链接是编译器为了减少链接时间做的

处理,把函数体用一个JMP指令代替,这样就可以随意改变函数的内容,而不用修改CALL指令。

(5) 不要在函数体内使用超过4kb的局部变量。局部变量是存放在栈中的,例如下面这个函数

void Dummy(void) { BYTE var[256]; var[0] = 0; var[1] = 1; var[255] = 255;

}

在分配局部变量空间时是这样的 :00401000 push ebp

:00401001 mov ebp, esp

:00401003 sub esp, 00000100 ; change ESP as storage for ; local variables is needed :00401006 mov byte ptr [esp], 00 ; var[0] = 0; :0040100A mov byte ptr [esp+01], 01 ; var[1] = 1;

:0040100F mov byte ptr [esp+FF], FF ; var[255] = 255; :00401017 mov esp, ebp ; restore stack pointer :00401019 pop ebp :0040101A ret

但是当局部变量的大小超过4kb时,栈指针并不直接改版,而是调用另一个函数来分配内存,这个

函数有可能在不同进程中的地址不一样。

(6) 函数体内switch语句中的case不要超过3个,否则编译器会在PE文件中使用跳转表,而这

个跳转表有可能在目标进程中并不存在。 下面是一个无DLL注入的例子: //参数结构 ;

typedef struct _RemotePara{ PVOID dwMessageBox; wchar_t strMessageBox[12]; }RemotePara; // 远程线程执行体

DWORD __stdcall ThreadProc(RemotePara *Para) {

typedef int (/*__stdcall*/ *PMessageBox) ( HWND , LPCTSTR , LPCTSTR , UINT ); PMessageBox MessageBoxFunc = (PMessageBox)Para->dwMessageBox;

MessageBoxFunc(NULL, Para->strMessageBox, Para->strMessageBox, MB_OK); return 0 ; }

DWORD THREADSIZE=1024; DWORD pID = 4688; DWORD byte_write;

HANDLE hRemoteProcess,hThread;

RemotePara myRemotePara,*pRemotePara; void *pRemoteThread; HINSTANCE hUser32 ;

hRemoteProcess = OpenProcess(PROCESS_ALL_ACCESS,FALSE,pID); if(!hRemoteProcess)return 0;

// 在远程进程地址空间分配虚拟内存

pRemoteThread = VirtualAllocEx(hRemoteProcess, 0, THREADSIZE, MEM_COMMIT |

MEM_RESERVE,PAGE_EXECUTE_READWRITE); if(!pRemoteThread)return 0;

// 将线程执行体ThreadProc写入远程进程

if(!WriteProcessMemory(hRemoteProcess, pRemoteThread, &ThreadProc, THREADSIZE,0))

return 0;

ZeroMemory(&myRemotePara,sizeof(RemotePara)); hUser32 = LoadLibrary(L\

myRemotePara.dwMessageBox = (PVOID)GetProcAddress(hUser32, \ wcscat(myRemotePara.strMessageBox,L\复制MessageBox函数的参数 //写进目标进程

pRemotePara =(RemotePara *)VirtualAllocEx (hRemoteProcess ,0,sizeof

(RemotePara),MEM_COMMIT,PAGE_READWRITE); if(!pRemotePara)return 0;

if(!WriteProcessMemory (hRemoteProcess ,pRemotePara,&myRemotePara,sizeof

myRemotePara,0))return 0; // 启动线程

hThread = CreateRemoteThread(hRemoteProcess ,0,0,(LPTHREAD_START_ROUTINE)

pRemoteThread ,pRemotePara,0,&byte_write); FreeLibrary(hUser32);

CloseHandle(hRemoteProcess);

第七种方法:

利用DLL劫持内存补丁技术注入

当一个可执行文件运行时,Windows加载器将可执行模块映射到进程的地址空间中,加载器分

析可执行模块的输入表,并设法找出任何需要的DLL,并将它们映射到进程的地址空间中。

由于输入表中只包含DLL名而没有它的路径名,因此加载程序必须在磁盘上搜索DLL文件。首先会

尝试从当前程序所在的目录加载DLL,如果没找到,则在Windows系统目录查找,最后是在环境变

量中列出的各个目录下查找。利用这个特点,先伪造一个系统同名的DLL,提供同样的输出表,每

个输出函数转向真正的系统DLL。程序调用系统DLL时会先调用当前目录下伪造的DLL,完成相关功

能后,再跳到系统DLL同名函数里执行。这个过程用个形象的词来描述就是系统DLL被劫持

(hijack)了。

示例DELPHI源码: Library USP10; uses

Windows, SysUtils, Classes;

{$R *.res}

ID:THandle;

ModHandle: Cardinal; POldLpkPresent: Pointer;

POldScriptApplyDigitSubstitution: Pointer; POldScriptApplyLogicalWidth: Pointer; POldScriptBreak: Pointer; POldScriptCPtoX: Pointer;

POldScriptCacheGetHeight: Pointer; POldScriptFreeCache: Pointer; POldScriptGetCMap: Pointer;

POldScriptGetFontProperties: Pointer; POldScriptGetGlyphABCWidth: Pointer; POldScriptGetLogicalWidths: Pointer; POldScriptGetProperties: Pointer; POldScriptIsComplex: Pointer; POldScriptItemize: Pointer; POldScriptJustify: Pointer; POldScriptLayout: Pointer; POldScriptPlace: Pointer;

POldScriptRecordDigitSubstitution: Pointer; POldScriptShape: Pointer;

POldScriptStringAnalyse: Pointer; POldScriptStringCPtoX: Pointer; POldScriptStringFree: Pointer;

POldScriptStringGetLogicalWidths: Pointer; POldScriptStringGetOrder: Pointer; POldScriptStringOut: Pointer; POldScriptStringValidate: Pointer; POldScriptStringXtoCP: Pointer; POldScriptString_pLogAttr: Pointer; POldScriptString_pSize: Pointer;

POldScriptString_pcOutChars: Pointer; POldScriptTextOut: Pointer; POldScriptXtoCP: Pointer; POldUspAllocCache: Pointer; POldUspAllocTemp: Pointer; POldUspFreeMem: Pointer;

procedure LpkPresent; asm jmp POldLpkPresent end;

procedure ScriptApplyDigitSubstitution; asm jmp POldScriptApplyDigitSubstitution end; procedure ScriptApplyLogicalWidth; asm jmp POldScriptApplyLogicalWidth end; procedure ScriptBreak; asm jmp POldScriptBreak end; procedure ScriptCPtoX; asm jmp POldScriptCPtoX end;

procedure ScriptCacheGetHeight; asm jmp POldScriptCacheGetHeight end; procedure ScriptFreeCache; asm jmp POldScriptFreeCache end; procedure ScriptGetCMap; asm jmp POldScriptGetCMap end;

procedure ScriptGetFontProperties; asm jmp POldScriptGetFontProperties end;

procedure ScriptGetGlyphABCWidth; asm jmp POldScriptGetGlyphABCWidth end; procedure ScriptGetLogicalWidths; asm jmp POldScriptGetLogicalWidths end; procedure ScriptGetProperties; asm jmp POldScriptGetProperties end; procedure ScriptIsComplex; asm jmp POldScriptIsComplex end; procedure ScriptItemize; asm jmp POldScriptItemize end; procedure ScriptJustify; asm jmp POldScriptJustify end; procedure ScriptLayout; asm jmp POldScriptLayout end; procedure ScriptPlace; asm jmp POldScriptPlace end;

procedure ScriptRecordDigitSubstitution; asm jmp POldScriptRecordDigitSubstitution end;

procedure ScriptShape; asm jmp POldScriptShape end;

procedure ScriptStringAnalyse; asm jmp POldScriptStringAnalyse end; procedure ScriptStringCPtoX; asm jmp POldScriptStringCPtoX end; procedure ScriptStringFree; asm jmp POldScriptStringFree end;

procedure ScriptStringGetLogicalWidths; asm jmp POldScriptStringGetLogicalWidths end; procedure ScriptStringGetOrder; asm jmp POldScriptStringGetOrder end; procedure ScriptStringOut; asm jmp POldScriptStringOut end;

procedure ScriptStringValidate; asm jmp POldScriptStringValidate end; procedure ScriptStringXtoCP; asm jmp POldScriptStringXtoCP end;

procedure ScriptString_pLogAttr; asm jmp POldScriptString_pLogAttr end;


DLL的11种注入方法 (6).doc 将本文的Word文档下载到电脑

下一篇:以青春梦想为主题的晚会串词

相关推荐
相关阅读
本类排行
× 游客快捷下载通道(下载后可以自由复制和排版)

下载本文档需要支付 7 元

支付方式:

开通VIP包月会员 特价:29元/月

注:下载文档有可能“只有目录或者内容不全”等情况,请下载之前注意辨别,如果您已付费且无法下载或内容有问题,请联系我们协助你处理。
微信:xxxxxx QQ:xxxxxx