dll注入,除了常見的遠執行緒注入,掛鉤和修改登錄檔以外還可以通過修改pe檔案頭來達到注入目的,廢話少說先上菜。
pe檔案經常會呼叫外部dll檔案,而需要呼叫的dll檔案都會在pe檔案說明,通過 nt頭->可選頭->匯入表 可以找到匯入表,而匯入表就是對需要匯入的每個dll的說明,它實際上是乙個20個位元組組成的iid結構體陣列,每個結構體就是乙個dll資訊說明,我們只需要向pe檔案中準確新增這樣的乙個iid結構體,並且修改好相應指標就能利用作業系統載入pe檔案的時候自動載入dll檔案了。
以下通過乙個例項說明,例子**於《逆向工程核心原理》25章,其中包括乙個test.exe檔案和乙個myhack3.dll檔案,目的是要通過手動修改test.exe檔案的內容來注入myhack3.dll檔案。
(1)首先用peview檢視test.exe檔案已包含的dll檔案,並分析iid的插入方法
從上圖發現test.exe已經載入了4個dll檔案每個dll檔案都是乙個iid結構體,佔20個位元組,而且最後乙個結構體為空,即全0結構。
《windows pe權威指南》113頁上面提到最後乙個結構體實際不必要為全空,只要其中的name[1]是0就能滿足結束條件我們要插入乙個iid結構在現有結構體陣列的最後面(實際不一定非要插在這裡),就要檢視此處是否有可利用空間(可利用空間的意思就是一定要被載入到記憶體,且不影響到其他資料完整性還要有可寫入許可權,為什麼要有可寫入許可權,是因為系統載入時需要用int的指標寫入iat),於是我們需要檢視上圖中的76cc-772f這段內容,看它尾部是否有可利用空間iid結構說明:
struct iamge_import_descriptor
dword timedatestamp; //乙個32位的時間標誌
dword forwarderchain;//這是乙個被轉向api的索引,一般為0
dword name;//dll名字,是個以00結尾的ascii字元的rva位址
dword firstthunk; // 指向輸入表的rva
} ;
我們發現772f後面有資料f6 87…,因此不能把iid插入到這裡,需要另尋它處,於是我們在來檢視.rdata節區後面的空間,看是否有剩餘空間(由於檔案對齊的原因一般都有剩餘空間,但其實我們還可以加入乙個新節來存放iid,不過相對麻煩一點)
從上圖發現該節去尾部還有大段空白,於是我們可以吧iid結構體陣列移動到這裡,並新增上自己的iid,然後吧相關標頭檔案指標修改指向這裡,但是這裡還需要注意乙個問題:此處是否是上文提到過的可利用區域,即是否會被載入到記憶體以及是否有可寫許可權?
我們檢視該節頭部發現載入到記憶體的檔案部分應該是長度是2c56 而實際存在與磁碟的內容為2e00比記憶體中的內容要大,那麼磁碟檔案中多出的2e00-2c56去**了?(實際上這是磁碟檔案對了保證檔案對齊而填充的0,如上上個圖所示),所以我們在這裡新增其它資料不會影響到pe檔案的其它資料,同時還要修改上圖中的記憶體許可權標記新增rdata節區可讀屬性0x80000000
可寫屬性的巨集是(image_scn_mem_write)自此,我們已經找到了iid結構所在位址76cc-772f和要把它複製到的地方7e60-7fff,還有需要新增的許可權0x80000000,下面開始修改。
(2)移動iid陣列,並在尾部新增乙個iid結構,新增可寫許可權
先複製76cc-772f到7e60-7fff這片區域
移動的具體位址可在這片區域隨意選擇,這裡選擇了7e80,其次是新增自己iid結構,這裡自己新增的iid結構位址為7ed0,它實際上是覆蓋了之前原有iid結構陣列的最後乙個全0結構,至於新增的內容
struct iamge_import_descriptor
dword timedatestamp; //乙個32位的時間標誌 =0
dword forwarderchain;//被轉向api的索引 =0
dword name;//dll名字 =8d10
dword firstthunk; // 指向輸入表的rva iat=8d20
} ;
而上述位址都是rva,要把它們轉變為raw(檔案偏移),如下表所示
上圖來自書中,而填好位址之後還得在相應的位址填上實際的內容
圖中的8d00、8d10、8d20、8d30都是之rva轉化為raw之後分別是 7f00、7f10、 7f20、 7f30,位址轉換可一手動計算也可以利用peview等工具計算,移動iid陣列和新增iid都已完成,現在要新增可寫許可權即與之前的40000040 or一下,於是
80000000 or 40000040=c0000040
(3)修改可選頭(image_optional_header)頭部指標,刪除繫結匯入表
繫結匯入表:image_directory_entry_bound_import用於加快修正匯入表,不是必要pe檔案必要內容,當我們自己新增了dll又不修改它的話就會出錯,為了省去麻煩這裡就直接刪除它可選頭(image_optional_header)中有個指標指向了iid結構陣列的起始位置,我們移動了iid結構,所以要修改此處
rva 84cc改為我們修改的位址rva 8c80也就是raw 7e80,檔案大小0x64改為0x78也就是增加0x78-0x64=0x14=20個位元組,
自此,大功告成,只差驗證!!!我的天,寫了半天、、、
(4)驗收
從圖中可以看出myhack3.dll已經載入成功,任務copy!沒有表情,暈死|||
修改PE檔案頭刪除ASLR
windows核心6.0版本之後增設了alsr address space layout randomization 機制,使得每次pe檔案記載到虛擬記憶體的起始位址不一樣,而且棧和堆起始位址也不一樣.熟知pe檔案頭格式的逆向玩家,可以通過修改乙個標誌位來達到刪除編譯好的可執行檔案的aslr功能.p...
PE檔案本地DLL注入實現
之前寫過乙個利用遠端執行緒注入dll的工具,大致過程如下 1.使用openprocesstoken lookupprivilegevalue adjusttokenprivileges函式修改當前程序的的訪問令牌,獲得除錯許可權。2.openprocess開啟目標程序,用virtualallocex...
PE檔案頭結構
typedef struct image file header image file header,pimage file header 1.machine 每個cpu都有唯一的machine碼,用來指定檔案的執行平台 define image file machine unknown 0 def...