WinNT&Win2K下實現程式的完全隱藏(轉)
WinNT&Win2K下實現程式的完全隱藏(轉)[@more@] 關於程式的隱藏,98下的例子數不勝數。WinNT/Win2K下的隱藏方法,西祠的高手shotgun在去年的6月就已經在網上釋出出例項《揭開木馬的神秘面紗》 ,我也多次拜讀他的文章,對他的計算機水平及熱心幫助朋友的作風十分敬佩。這裡也可算是對shotgun的文章的補充與深入介紹吧,好了,閒話少說。 在WinNT下"真正隱藏程式"這一說法,可以講是根本不可能實現,只要我們的程式是以程式核心的形式執行,都是不可能逃離CTRL+ALT+DEL的法眼。那麼奇怪了,這豈不是與我們的標題《WinNT & Win2K下實現程式的完全隱藏》相矛盾嗎?是的,實際上應該是:以非程式方式執行目的碼,而逃避程式檢視器的檢查,從而達到"程式隱藏"的目的。 我們這裡用的,是在宿主程式中,以執行緒的方式執行我們的程式碼。實現起來非常簡單。 首先,我們先建立一個不執行任何語句的執行緒 DWORD stdcall ThreadProc(LPVOID *lpVoid){ return 0; } 然後,將執行緒程式碼拷備至宿主程式所能夠執行的任何地方(即頁面屬性為PAGGE_EXECUTE_READWRITE),如:共享記憶體影射區、宿主程式內。這裡我們選擇宿主程式,拷備的時侯,我們需要先在宿主程式中使用VirtualAllocEx函式申請一段記憶體,然後再使用WriteP rocessMemory將執行緒體寫入宿主程式中。 以上工作完成後,我們便可CreateRemoteThread函式啟用其執行。下面給出一個完整的例子 //遠端執行緒執行體 DWORD __stdcall ThreadProc (void *lpPara){ return 0; } int main(int argc, char* argv[]){ const DWORD THREADSIZE=1024*4;//暫定執行緒體大小為4K,實際上沒這麼大,稍後我將會介紹 DWORD byte_write; //獲得指定程式ID控制程式碼,並設其許可權為PROCESS_ALL_ACCESS,992是宿程式的ID號,獲取ID號的方法這裡我就不多講了 HANDLE hWnd = :penProcess (PROCESS_ALL_ACCESS,FALSE,992); if(!hWnd)return 0; void *pRemoteThread =::VirtualAllocEx(hWnd,0,THREADSIZE,MEM_COMMIT| MEM_RESERVE,PAGE_EXECUTE_READWRITE);//申請 if(!pRemoteThread)return 0; if(!::WriteProcessMemory(hWnd,pRemoteThread,&ThreadProc,THREADSIZE,0))//寫入程式 return 0; //啟動執行緒 HANDLE hThread = ::CreateRemoteThread (hWnd ,0,0,(DWORD (__stdcall *)(void*))pRemoteThread ,NULL,0,&byte_write); if(!hThread){ //還有記憶體分配未釋放 return 0; } return 0; } 到這裡,對於隱藏的方法就算告一段落,相信看過的朋友對這個思路有個非常明確的概念了吧。 在理解隱藏的方法後,我們著重開始寫執行緒的執行部分了。如下: DWORD __stdcall ThreadProc(void *lpPara){ MessageBox(NULL,"hello","hello",0); return 0; } 編譯執行後,你會發現出現一個非法操作錯誤,為什麼呢?在我們以段頁式記憶體管理的win2K作業系統中,編譯時會把所有的常量編譯在PE檔案的.data節中,而程式碼段則在.text中,所以,我們拷備到宿主程式中的程式碼是在.text中的程式碼,MessageBox(NULL,(char *)指標,p,0);所指向的地址是本程式的記憶體虛擬地址。而在宿主程式中是無法訪問的。解決的方法很簡單,按舊照搬的將"hello"也拷備到目標程式中,然後再引用。同理,MessageBox函式地址編譯時,也是儲存在.Import中,寫過Win2k病毒的朋友都知道,所有常量與函式入口地址都需在程式碼段定義與得出,我們這裡也與他有點類似。言歸正傳,同樣情況我們也把函式的入口地址一起寫入目標程式中。//先定義引數結構typedef struct _RemotePara{//引數結構 char pMessageBox[12]; DWORD dwMessageBox; }RemotePara; //付值 RemotePara myRemotePara; ::ZeroMemory(&myRemotePara,sizeof(RemotePara)); HINSTANCE hUser32 = ::LoadLibrary ("user32.dll"); myRemotePara.dwMessageBox =(DWORD) ::GetProcAddress (hUser32 , "MessageBoxA"); strcat(myRemotePara.pMessageBox,"hello"); //寫進目標程式 RemotePara *pRemotePara =(RemotePara *) ::VirtualAllocEx (hWnd ,0,sizeof(RemotePara),MEM_COMMIT,PAGE_READWRITE);//注意申請空間時的頁面保護屬性 if(!pRemotePara)return 0; if(!::WriteProcessMemory (hWnd ,pRemotePara,&myRemotePara,sizeof myRemotePara,0))return 0; //啟動進將引數傳遞進入 HANDLE hThread = ::CreateRemoteThread (hWnd ,0,0,(DWORD (__stdcall *)(void *))pRemoteThread ,pRemotePara,0,&byte_write); if(!hThread){ return 0; }好了,就這麼簡單,下在給出一個彈出一個MessageBox的例項:// RemoteThread.cpp: Defines the entry point for the console application. // #include "stdafx.h" typedef struct _RemotePara{//引數結構 char pMessageBox[12]; DWORD dwMessageBox; }RemotePara; //遠端執行緒 DWORD __stdcall ThreadProc (RemotePara *lpPara){ typedef int (__stdcall *MMessageBoxA)(HWND,LPCTSTR,LPCTSTR,DWORD);//定義MessageBox函式 MMessageBoxA myMessageBoxA; myMessageBoxA =(MMessageBoxA) lpPara->dwMessageBox ;//得到函式入口地址 myMessageBoxA(NULL,lpPara->pMessageBox ,lpPara->pMessageBox,0);//call return 0; } void EnableDebugPriv();//提升應用級除錯許可權 int main(int argc, char* argv[]){ const DWORD THREADSIZE=1024*4; DWORD byte_write; EnableDebugPriv();//提升許可權 HANDLE hWnd = :penProcess (PROCESS_ALL_ACCESS,FALSE,992); if(!hWnd)return 0; void *pRemoteThread =::VirtualAllocEx(hWnd,0,THREADSIZE,MEM_COMMIT| MEM_RESERVE,PAGE_EXECUTE_READWRITE); if(!pRemoteThread)return 0; if(!::WriteProcessMemory(hWnd,pRemoteThread,&ThreadProc,THREADSIZE,0)) return 0; //再付值 RemotePara myRemotePara; ::ZeroMemory(&myRemotePara,sizeof(RemotePara)); HINSTANCE hUser32 = ::LoadLibrary ("user32.dll"); myRemotePara.dwMessageBox =(DWORD) ::GetProcAddress (hUser32 , "MessageBoxA"); strcat(myRemotePara.pMessageBox,"hello"); //寫進目標程式 RemotePara *pRemotePara =(RemotePara *) ::VirtualAllocEx (hWnd ,0,sizeof(RemotePara),MEM_COMMIT,PAGE_READWRITE);//注意申請空間時的頁面屬性 if(!pRemotePara)return 0; if(!::WriteProcessMemory (hWnd ,pRemotePara,&myRemotePara,sizeof myRemote Para,0))return 0; //啟動執行緒 HANDLE hThread = ::CreateRemoteThread (hWnd ,0,0,(DWORD (__stdcall *)(voi d *))pRemoteThread ,pRemotePara,0,&byte_write); if(!hThread){ return 0; } return 0; } //提升許可權 void EnableDebugPriv( void ) { HANDLE hToken; LUID sedebugnameValue; TOKEN_PRIVILEGES tkp; if ( ! OpenProcessToken( GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken ) ) return; if ( ! LookupPrivilegeValue( NULL, SE_DEBUG_NAME, &sedebugnameValue ) ){ CloseHandle( hToken ); return; } tkp.PrivilegeCount = 1; tkp.Privileges[0].Luid = sedebugnameValue; tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED; if ( ! AdjustTokenPrivileges( hToken, FALSE, &tkp, sizeof tkp, NULL, NULL ) ) CloseHandle( hToken ); } 好了,程式編譯執行後會在程式號為992的程式中建立一執行緒,彈出hello對話方塊。是不是非常簡單呢! 這裡有幾個地方需要注意的: 1、遠端執行緒在宿主程式中申請空間時,空間大小的確定了是我一直無法解決的問題。我曾使用兩個貼近一起的執行緒,以執行緒間的距離大小,並加上引數大小,作為申請空間時,仍然會出現非法操作,如下: static void StartThread (LPVOID *lpPara){ return ; } static void EndThread(LPVOID *lpPara){ return; } 然後使用DWORD dwLenght = (DWORD)((char *)&StartThread - (char *)&EndThread); //得到StartThread執行緒程式碼長度,dwLenght += sizeof(ThreadPara); 仍會出現非法操作讓我很迷惑。在win2k中,執行緒的預設堆疊的頁大小是4KB,這裡我在為執行緒申請記憶體時,申請的大小暫時使用一個常數,始終為4KB的倍數,選取時儘量取大,線上程可成功執行後,再一點點改小。辦法是笨了點,如這裡的朋友有更好的方法,請不吝賜教。 2、什麼時侯,什麼引數是需要從外部傳遞進來的呢?我這裡並沒有一個十分有力的答案,我的理解是:PE檔案中除了.text節以外的所有節,均需使用外部引數傳遞到執行緒中使用,如:.rsrc、.data、rdata等其他的15個節。在我們實際編寫的過程中,初學者並不知道我們的程式碼會編譯在什麼地方,這個時侯,我們可以在執行的時侯ALT + 8(VC中快捷鍵)反編譯過來,一般有lea eax p、push offset p等取地址語句,這個時侯,我們大都需要以
·上一篇:·下一篇:
最新更新 | ||
······························ |
| ||
| | | | | | | | ||
| ||
Copyright © 2004 - 2007 All Rights Reserved
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/10763080/viewspace-970212/,如需轉載,請註明出處,否則將追究法律責任。
下一篇:
介紹一套給網管使用的安全檢查工具(轉)
請登入後發表評論
登入
全部評論
|
相關文章
- “黑屏”隱藏實現 (轉)
- 讓VisualBasic實現隱藏Mouse (轉)
- 在VC中實現程式在啟動時隱藏 (轉)
- VB中實現窗體自動隱藏 (轉)
- CSS實現隱藏超出的內容CSS
- 用CSS樣式實現顯示隱藏層 (轉)CSS
- js實現的控制table指定行的隱藏和現實程式碼例項JS
- 點選實現隱藏元素本身程式碼例項
- Mac下顯示和隱藏隱藏檔案的命令Mac
- C++“隱藏實現,開放介面”的實現方案C++
- css實現隱藏滾動條CSS
- 隱藏uitabbar的程式碼UItabBar
- jQuery 實現顯示與隱藏效果jQuery
- 實現android按下Enter鍵便隱藏輸入鍵盤Android
- 點選按鈕實現隱藏和顯示的切換程式碼
- 編寫驅動攔截NT的API實現隱藏檔案目錄 (轉)API
- jQuery實現的點選元素隱藏和顯示jQuery
- javascript實現的點選當前元素隱藏效果JavaScript
- css實現文字超出li寬度的部分隱藏CSS
- GRUB選單隱藏的解除(轉)
- 刪除WinXP隱藏的元件(轉)元件
- Delphi程式設計:完全控制桌面的實現 (轉)程式設計
- 點選按鈕實現隱藏一個元素程式碼例項
- 小程式tabBar跳轉頁面並隱藏tabBartabBar
- 揭開NTFS下真正的隱藏檔案--'流'的奧秘 (轉)
- 微信隱藏程式碼整理
- 點選按鈕實現div的顯示和隱藏
- 點選元素實現當前元素隱藏效果
- 網頁中隱藏幀的妙用 (轉)網頁
- MAC如何顯示隱藏檔案和隱藏隱藏檔案的命令Mac
- 隱藏nginx版本號資訊(轉)Nginx
- chrome,firfox,IE實現隱藏滾動條但是可以正常滾動(瀏覽器自帶隱藏屬性實現)Chrome瀏覽器
- vue中點選空白處隱藏div的實現(用指令優雅的實現)Vue
- jQuery實現的元素延遲指定時間之後隱藏jQuery
- Linux環境下實現NTFS分割槽完全讀寫的方法(轉)Linux
- js下拉框實現div顯示和隱藏JS
- 直播系統程式碼,輸入時實現密碼顯示與隱藏密碼
- 隱藏資料夾怎麼取消隱藏 關閉隱藏檔案的辦法