在很多人眼裡,hook都是高階程式設計師才會使用的技術。一年前,我也是。每每看到別人使用了hook技術就很嫉妒。是的,說嫉妒一點都不誇張。
剛開始,不知道hook到底是什麼技術。或者說,hook到底是做什麼的。hook的英文是鉤子,但是,說實話,我的中文意識中,怎麼也不能將鉤子和hook劃等同符號。
乙個鉤子,它在等待我們去往上面掛上我們想要的東西。這點,從最終結果看。確實和這個技術很符合。可問題是,那些鉤子在什麼地方?我們家門口倒是有幾個掛衣服的鉤子,可是我要掛其他物件的鉤子在**呢?
最常聽說的就是api hook了。有句話說得很有道理,hook api是乙個永恆的話題。網路上,不知有多少人在追捧這個技術。畢竟,喜歡探險是我們的本能。深入別人的系統,獲取別人的資訊,修改別人的行為,一直都是我們夢寐以求的。
api hook又分為13種,具體參考msdn。這些當中很多在你對系統核心很感興趣的時候,非常有用。不過我們經常說的鉤子,都是滑鼠鉤子、鍵盤鉤子、訊息鉤子。
如果我們只滿足於這些鉤子,那麼鉤子也不會發展得這麼興旺了。事實上,除了微軟提供的鉤子函式外,通過鉤子的實現原理,我們還可以實現其他類似的鉤子。
我對鉤子的深入了解和大多數人可能相反,這得感謝我的超同事。我深入了解鉤子的時候,是從delphi的**鉤子開始的。
delphi的vcl中有些函式實現可能比較低效,但是又沒有提供修改的機會。怎麼辦呢?大家知道,函式在記憶體中的表現,就是一段**,其中不連續部分,使用跳轉指令(這點很重要)完成。就是說,我們的**有這個特性:
**片段(a+b) =**片段a + jump +**片段b
正是因為這個特性,我們可以通過一些新增乙個跳轉,讓原想呼叫「**片段(a+b)」的**,實際呼叫「**片段a + jump + **片段c」。這個特性先簡單的說明,以後會詳細描述。
話說回來,我們解決低效的方法,就是找乙個高效的**,hook原有的低效**。【我這裡希望大家接受我的乙個建議,不要關注hook細節,如果技術可行,我們就簡單說明為hook。就像這裡我這麼描述一樣】
慢慢的,發現有時候vcl的類庫有一些bug。發現也可以使用類似方法實現。當然了,這裡需要注意類方法和普通方法的引數差異(多乙個sender引數)。
有乙個典型的例子,就是在delphi中,tobject提供了從物件到介面的轉換服務(as操作符),但是並沒有提供介面到實現物件的轉換服務,即由乙個介面指標,得到實現此介面的物件的服務。
如果我們知道實現此介面的類,我們可以通過獲取物件指標和介面指標的偏移,來獲得類例項指標。(偏移請參考tobject的initinstance函式)
但如果我們從高一點的角度來看,假設我們認為tobject必須有這個服務,那麼tobject的設計就是有缺陷的。如果我們修復這個錯誤呢?那麼,這個設計不就符合我們的要求了嘛?
下面是我的超同志曾經提出的一種改寫方式:
請注意和原有**差異:
type
tgetinte***cefunc = function(self: tobject; const iid: tguid; out obj): boolean;
const
iid_queryobject: tguid = '';
varoldgetinte***ce: tgetinte***cefunc;
function getinte***ce(self: tobject; const iid: tguid; out obj): boolean;
varinte***ceentry: pinte***ceentry;
begin
if isequalguid(iid_queryobject, iid) then
begin
pointer(obj) := self;
result := true;
endelse begin
result := oldgetinte***ce(self, iid, obj); // oldgetinte***ce是在hook的時候,記錄
// 的原有函式的位址。
end;
end;
方法是通過對介面中queryinte***ce的基礎方法getinte***ce進行改寫,如果傳入的iid等於iid_queryobject的話,就返回物件指標。最後就是針對vcl,hook上面這個方法。
細心的你可能發現,上面列舉的例子,我刻意地沒有去描述hook的原理,而重點在說hook的應用,或者說,是在使用hook技術來解決問題。
事實上,我更想說的是,我們使用hook這種思想來解決問題。s每每想起hook的巧妙解決方式,我都非常振奮。也這是因為這些振奮,才使我想寫一系列關於hook思想的文章。希望大家都能使用hook思想去思考問題,而不是只是關注於hook技術本身。
現在正在流行的aop(面向方面程式設計)思想,也是基於hook技術發展起來的。但是,aop一直強調aop不只是hook!實際上,aop更注重基於hook的切片思想。這正和我的想法一致。
我的最終目標不是把大家引向aop,而是讓大家逐步了解到基於hook的一些原則和實踐。中間有些章節載自別人的文章,只是希望能夠比較詳細的描述hook思想。
HOOK啟思錄 前言 HOOK是一種思想
在很多人眼裡,hook都是高階程式設計師才會使用的技術。一年前,我也是。每每看到別人使用了hook技術就很嫉妒。是的,說嫉妒一點都不誇張。剛開始,不知道hook到底是什麼技術。或者說,hook到底是做什麼的。hook的英文是鉤子,但是,說實話,我的中文意識中,怎麼也不能將鉤子和hook劃等同符號。乙...
HOOK啟思錄 第三章 HOOK的應用模式
觀察模式 在hook很多應用中,有一類應用最為常用,那就是觀察模式。對於資訊獲取的要求,在很多時候都是非常的重要的功能。在很多時候,我們都需要根據一定量的資訊去判斷如何決策。正如打仗一樣,沒有一定量的有意義的資料,就是摸黑,只能死路一條。像windows提供的setwindowhook就是典型地為這...
HOOK啟思錄 第三章 HOOK的應用模式
2006年11月27日 23 18 00 觀察模式 在hook很多應用中,有一類應用最為常用,那就是觀察模式。對於資訊獲取的要求,在很多時候都是非常的重要的功能。在很多時候,我們都需要根據一定量的資訊去判斷如何決策。正如打仗一樣,沒有一定量的有意義的資料,就是摸黑,只能死路一條。像windows提供...