接着上一篇,同样是Dll 注入,只是实现方法不同,现在讲的是 通过远程 线程实现 的,应该说比Windows挂钩较难些, 但这种方法也比上一种比较强大些。最终目标都是将我们写的Dll映射到目标进程地址空间中。好实现控制他人 。同样,也是用汇编语言实现的,很多人都清楚汇编在CSDN是严重受歧视的, 用过汇编的人都知道他的好,没有学过的人永远都只会跟着别人说:汇编是老古董,太低级......................之类的........。 就是这样子的 ,这样跟风不好 .
好了下面讲下实现的的思路:
0.用OpenProcess 获得目标进程的句柄 hProcess
1.通过VirtualAllocEx 在目标进程中分配一块内存块 lpDllName,用于存放Dll的路径的名称 szDllName
3.用WriteProcessMemory向刚刚在目标进程获得的lpDllName中写入szDllName(含路径).
4.用GetModelHandle获得Kernel32的实例句柄hInstance
5.用GetProcAddress获得Loadlibrary函数的地址lpLoadlibrary
6.用CreateRemoteThread创建远程线程,线程函数指定为 lpLoadlibrary ,参数指定为 lpDllName
7.接下来就是在Dll的入口函数中写你要对目标进程做的事情,随便你怎么写都好
好了,下面直接上代码 ,这篇稍微有些注释,只是不多,还是那句话,有问题的找我好了================================ zhong_sf@sina.com
这是用于执行上面那些步骤的代码:
.386p
.model flat,stdcall
option casemap:none
DLG_MAIN equ 101
IDC_PID equ 1000
IDC_INJECT equ 1001
ICO_MAIN equ 1002
include windows.inc
include user32.inc
include kernel32.inc
includelib user32.lib
includelib kernel32.lib
.data
hInstance dword ?
hWndMain dword ?
hProcess dword ?
hRemoteThread dword ?
lpDllName dword ?
lpLoadLibrary dword ?
lpFreeLibrary dword ?
.const
szDllName byte "G:\masm32\Source\Remote Inject\rjdll.dll",0
szKernel byte "Kernel32",0
szLoadLibrary byte "LoadLibraryA",0
szFreeLibrary byte "FreeLibrary",0
szWndTitle byte "Remote Inject",0
szErr byte "Error!",0
szErr2 byte "请输入正确的进程ID!",0
szErr3 byte "远程内存提交失败!",0
szErr4 byte "远程内存写入失败!",0
szErr5 byte "读取库函数地址失败!",0
szErr6 byte "远程线程创建失败!",0
.code
_DlgProc proc ,hWnd ,uMsg ,wParam ,lParam
local dwPid:dword
local bflag:byte
local dwWriten:dword
local dwThreadId:dword
mov eax ,uMsg
.IF eax == WM_INITDIALOG
mov eax ,hWnd
mov hWndMain ,eax
invoke LoadIcon ,hInstance ,ICO_MAIN
invoke SendMessage ,hWnd ,WM_SETICON ,ICON_BIG ,eax
.ELSEIF eax == WM_COMMAND
mov eax ,wParam
.if ax == IDC_INJECT
invoke GetDlgItemInt ,hWnd ,IDC_PID ,addr bflag ,TRUE
.if bflag == TRUE
mov dwPid ,eax
.else
Err: invoke MessageBox ,hWnd ,addr szErr2 ,addr szWndTitle ,MB_OK
ret
.endif
;open process
invoke OpenProcess ,PROCESS_CREATE_THREAD or PROCESS_VM_OPERATION or \
PROCESS_VM_WRITE , FALSE ,dwPid
.if eax == NULL
jmp Err
.else
mov hProcess ,eax
.endif
;alloc Remote memory
invoke VirtualAllocEx ,hProcess ,NULL ,MAX_PATH ,MEM_COMMIT ,PAGE_READWRITE
.if eax == NULL
invoke MessageBox ,hWndMain ,addr szErr3 ,addr szWndTitle ,MB_OK
ret
.else
mov lpDllName ,eax
;Write Name to Memory
invoke WriteProcessMemory ,hProcess ,lpDllName ,addr szDllName ,\
sizeof szDllName , addr dwWriten
.if eax == NULL
invoke MessageBox ,hWnd ,addr szErr4 ,addr szWndTitle ,MB_OK
ret
.endif
.endif
;get Function address
invoke GetModuleHandle ,addr szKernel
invoke GetProcAddress ,eax ,addr szLoadLibrary
.if eax == NULL
Err2: invoke MessageBox ,hWnd ,addr szErr5 ,addr szWndTitle ,MB_OK
ret
.else
mov lpLoadLibrary ,eax
.endif
;Create Remote Thread
invoke CreateRemoteThread ,hProcess ,NULL ,0 , lpLoadLibrary ,lpDllName ,\
0 ,addr dwThreadId
.if eax == NULL
invoke MessageBox ,hWnd ,addr szErr6 ,addr szWndTitle ,MB_OK
ret
.else
mov hRemoteThread ,eax
.endif
;Create Remote Thread to Free the Remote Process Memory
;get FreeLibrary address
invoke GetModuleHandle ,addr szKernel
invoke GetProcAddress , eax ,addr szFreeLibrary
.if eax == NULL
jmp Err2
.else
mov lpFreeLibrary ,eax
.endif
;Create thread
invoke CreateRemoteThread , hProcess ,NULL ,0 ,lpFreeLibrary ,lpDllName ,\
0 , addr dwThreadId
ret
.endif
.ELSEIF eax ==WM_CLOSE
invoke EndDialog ,hWnd ,TRUE
.ELSE
mov eax ,FALSE
ret
.ENDIF
mov eax ,TRUE
ret
_DlgProc endp
start:
invoke GetModuleHandle ,NULL
mov hInstance ,eax
invoke DialogBoxParam ,hInstance , DLG_MAIN ,NULL ,offset _DlgProc ,NULL
invoke ExitProcess ,NULL
end start
下面是Dll中的代码,很简单,同上篇一样,也是替换它的窗口过程,仅拦截WM_COMMAND ,:
.386p
.model flat ,stdcall
option casemap:none
include windows.inc
include user32.inc
include kernel32.inc
includelib user32.lib
includelib kernel32.lib
.data?
hWndMain dword ?
hInstance dword ?
lpOldWndProc dword ?
.const
szWndTitle byte "PEid v0.94",0 //若要注入控制其他程序,得将这换成 那程序窗口的标题 。
szInfo byte "Dll注入成功!",0
szInfo2 byte "注入Dll已使该功能失效!",0
szErr1 byte "Cannot Find the window",0
.code
_NewWndProc proc ,hWnd ,uMsg ,wParam ,lParam
mov eax ,uMsg
.if eax == WM_COMMAND
invoke MessageBox ,hWndMain ,addr szInfo2 ,addr szInfo ,MB_OK
.else
invoke CallWindowProc ,lpOldWndProc ,hWnd ,uMsg ,wParam ,lParam
.endif
ret
_NewWndProc endp
DllEntry proc ,_hInstance ,_dwReason ,_dwReserved
push _hInstance
pop hInstance
.if _dwReason == DLL_PROCESS_ATTACH
invoke MessageBox ,NULL, addr szInfo ,addr szInfo ,MB_OK
invoke FindWindow ,NULL , addr szWndTitle
.if eax
mov hWndMain ,eax
.ELSE
invoke MessageBox ,NULL ,addr szErr1 ,addr szErr1 ,MB_OK
.ENDIF
invoke GetWindowLong ,hWndMain ,GWL_WNDPROC
mov lpOldWndProc ,eax
invoke SetWindowLong ,hWndMain ,GWL_WNDPROC ,offset _NewWndProc
.ENDIF
ret
DllEntry endp
end DllEntry
下面上个效果图吧: