天天看點

Windows鈎子—我的需求

我一直在利用工作時間寫文章,這并不能說明我不愛工作一心做自己的事,而是因為我做事非常迅速,往往将分内的工作完成以後沒有事幹,可是上司就不願意了,他們不可能讓我閑着,然而我又十分不情願接受新的任務而沒有得到任務額外的報酬,于是我就寫一些linux方面的文章,上司當然不願意了,他們看到我在寫文章總會過來說我幾句。他們怎麼能看到我在寫文章呢?很簡單,隻要我一寫,他們當然能看到我寫的内容,于是他們就過來了,告訴我還有别的任務要做,我讨厭這種方式,于是我想通過我的老本行避開這樣的騷擾。我一向對linux感興趣,但是這并不能說我對别的就沒有興趣,我對windows也是十分了解的,隻不過我不喜歡它罷了,說實話我一開始的第一份工作就是做windows驅動的,呵呵。我對windows還是有自己的了解的,特别是windows鈎子方面的内容。

既然我不想讓上司看到我在做什麼,那麼我就有必要寫一個程式來實作這一個需求,誰讓咱是幹這的呢!于是我想寫一個程式,要點就是我輸入編輯器比如“記事本”的内容不回顯,但是我輸入的内容卻已經儲存在了另外的一個位置。這個很簡單,利用windows鈎子就可以做到,但是必須了解windows的消息機制,這個對于我來說已經不再話下了,我對windows鈎子還是十分了解的,于是我就寫了一個程式,該程式運作以後無論我往編輯器寫什麼内容都不會被回顯,但是我寫的内容卻已經儲存在了檔案裡面,呵呵,道高一尺魔高一丈,我就是這樣避開上司的監視的。

啥也不說了,先看我的程式的核心内容,其實就是寫了一個全局鈎子,該鈎子鈎住了所有的windows消息,然後用我自己的方式處理了以後再發送,鈎子的具體定義如下:

HHOOK hHook = NULL; //鈎子句柄

LRESULT CALLBACK HookProc(int nCode, WPARAM wParam, LPARAM lParam)

{

PMSG pmsg = (PMSG)lParam;

if(nCode != HC_ACTION)

return 0;

if(pmsg->message==WM_IME_COMPOSITION)

HIMC handle;

DWORD size;

HWND hWnd = pmsg->hwnd;

if(pmsg->lParam & GCS_RESULTSTR)

char buff[128];

handle = ImmGetContext(hWnd); //這些API都是MS提供了輸入法API,學習它們是沒有意義的,用着了查就得了。

size = ImmGetCompositionString(handle, GCS_RESULTSTR,NULL, 0);

size += sizeof(WCHAR);

memset(buff, 0, sizeof(buff));

ImmGetCompositionString(handle, GCS_RESULTSTR, buff, size); //得到輸入的中文字元串

fp = fopen( "c://dd.txt","a+");

fwrite( lpstr,strlen(buff),1,fp ); //将中文輸入法的輸入漢字寫入檔案

fclose(fp);

pmsg->lParam = 0; //重置消息,這樣的話消息就被更改了,于是編輯器上就顯示不出你輸入的中文字元串了。

pmsg->wParam = 0

ImmReleaseContext(hWnd, handle);

}

void hook()

hHook = SetWindowsHookEx(WH_GETMESSAGE,(HOOKPROC)HookProc,/*this dll*/,0);

再寫一個應用程式加載這個鈎子,大功就告成了,就是這麼簡單,鈎子函數的具體内容注釋都有,如果不了解加之誰想用的話,直接複制就可以,呵呵。加載這個鈎子以後,我寫的任何内容都會被儲存在c:/dd.txt檔案裡面,如此一來,上司就不會看到我寫的是什麼了,猛吧?其實windows挺好的,無論你有什麼需求,它都會滿足你的。

說到這裡我不得不發一番感慨了,windows竟然提供了這麼多政策性的API,在unix/linux中這是絕對不可能的。你可以看看MS的MSDN幾乎什麼都有的,你隻要需要一個功能,它都會滿足你的,這看起來十分不錯,但是很藝術嗎?不!我現在有點喝多了,有點語無倫次,但是,我還是十分欣賞unix的那種方式:政策由使用者自己實作,而十分反 ”感windows的方式:為使用者提供政策性的API。 像“ 輸入法”這一類的API簡直太“政策“化了,真的不明白為何windows的設計者要為使用者提供如此的API。

不過還好,我既然用windows的API解決了我的一個實際問題,那麼我就沒有什麼好說的了。感謝我現在用windows系統,感謝我們都用windows系統。

其實對于這個鈎子我還有一些要說的,這不關windows和unix/linux的比較,而是僅僅對于windows鈎子說的,如果你截獲WH_KEYBOARD鈎子的話,你在鈎子函數裡面的到的僅僅是一個鍵盤消息的副本,而不是鍵盤消息的真實值,但是WH_GETMESSAGE不一樣,他所得到的就是消息的指針,你更改的指針就是實際消息。這樣的話,你所得到的 lParam其實就是消息的指針值,這樣的話,你就可以更改消息了,具體的流程如何還請參見windows的消息流程啦。

 本文轉自 dog250 51CTO部落格,原文連結:http://blog.51cto.com/dog250/1273456

繼續閱讀