Hack The Planet

๋ฐ˜๊ฐ‘์Šต๋‹ˆ๋‹ค, cyalume์˜ ๋ธ”๋กœ๊ทธ์ž…๋‹ˆ๋‹ค.

reverse engineering

[๋ฆฌ๋ฒ„์‹ฑ ํ•ต์‹ฌ์›๋ฆฌ] DLL injection ์˜ˆ์ œ ์ฝ”๋“œ ํ•ด์„ค

cyalume 2021. 7. 11. 01:27

Windows ๋ฉ”์‹œ์ง€ ํ›„ํ‚น

Hookmain.cpp

//HookMain.cpp 
#include "stdio.h" 
#include "conio.h" 
#include "windows.h" 

#define DEF_DLL_NAME "KeyHook.dll" 
#define DEF_HOOKSTART "HookStart" 
#define DEF_HOOKSTOP "HookStop" 

typedef void(*PFN_HOOKSTART)(); 
typedef void(*PFN_HOOKSTOP)(); 

void main() { 
	HMODULE hDll = NULL; 
    
    PFN_HOOKSTART HookStart = NULL; 
    PFN_HOOKSTOP HookStop = NULL; 
    char ch = 0; 
    
    hDll = LoadLibraryA(DEF_DLL_NAME); 
    
    HookStart = (PFN_HOOKSTART)GetProcAddress(hDll, DEF_HOOKSTART); 
    HookStop = (PFN_HOOKSTOP)GetProcAddress(hDll, DEF_HOOKSTOP); 
    
    HookStart(); 
    
    printf("press 'q' to quit!\n"); 
    
    while(_getch() != 'q'); 
    HookStop(); 
    
    FreeLibrary(hDll); 
}



01) Preprocessor - ์ „์ฒ˜๋ฆฌ

#include "stdio.h" 
#include "conio.h" 
#include "windows.h" 

#define DEF_DLL_NAME "KeyHook.dll" 
#define DEF_HOOKSTART "HookStart" 
#define DEF_HOOKSTOP "HookStop"

[#include "HeaderName"]
HookMain.cpp์—์„œ ์‚ฌ์šฉ๋˜๋Š” ํ•จ์ˆ˜๋“ค๊ณผ ๊ทธ ํ•จ์ˆ˜๊ฐ€ ์ •์˜๋œ ํ—ค๋”ํŒŒ์ผ์ž…๋‹ˆ๋‹ค.
stdio.h: printf()
conio.h: _getch()
windows.h: LoadLibraryA(), GetProcAddress(), FreeLibrary()

#define DEF_DLL_NAME "KeyHook.dll" 
#define DEF_HOOKSTART "HookStart" 
#define DEF_HOOKSTOP "HookStop"

[#define identifier token-string]
#define ์ง€์‹œ๋ฌธ์„ ํ†ตํ•ด ์ปดํŒŒ์ผ๋Ÿฌ๋Š” ๋ชจ๋“  identifier๋ฅผ token-string์œผ๋กœ ๋Œ€์ฒดํ•ฉ๋‹ˆ๋‹ค.
์œ„์˜ ์ฝ”๋“œ์ฒ˜๋Ÿผ, #define DEF_DLL_NAME "KeyHook.dll" ์ด๋ผ๋Š” ์ „์ฒ˜๋ฆฌ ์ง€์‹œ๋ฌธ์„ ์˜ˆ๋กœ ๋“ค์–ด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.
์ปดํŒŒ์ผ ํ›„ ์ฝ”๋“œ ๋‚ด ๋ชจ๋“  DEF_DLL_NAME์€ "KeyHook.dll" ์ด๋ผ๋Š” ๋ฌธ์ž์—ด๋กœ ๋Œ€์ฒด๋˜์–ด ๋‚˜์˜ค๊ธฐ ๋•Œ๋ฌธ์—, hDll = LoadLibraryA(DEF_DLL_NAME); ์ด๋ผ๋Š” ๊ตฌ๋ฌธ์€ ํ›„์— hDll = LoadLibraryA("KeyHook.dll"); ๋กœ ๋ฐ”๋€Œ๊ฒŒ ๋˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

[ํ•œ์ค„์š”์•ฝ]
#include "ํ—ค๋”ํŒŒ์ผ" => ํ—ค๋”ํŒŒ์ผ ๋งํฌ
#define A B => ์ฝ”๋“œ ๋‚ด ๋ชจ๋“  A๋Š” ์ปดํŒŒ์ผ ์‹œ B๋กœ ๋ฐ”๋€œ

02) typedef - ํ˜•์‹ ์ •์˜

typedef void(*PFN_HOOKSTART)(); 
typedef void(*PFN_HOOKSTOP)();

[typedef type-specifier identifier;]
typedef๋Š” ๊ธฐ์กด ํ˜•์‹์˜ ๋™์˜์–ด๋‚˜ ๋‹ค๋ฅธ ๋ฐฉ์‹์œผ๋กœ ์ง€์ •ํ•  ์ˆ˜ ์žˆ๋Š” ํ˜•์‹์˜ ์ด๋ฆ„์„ ๋งŒ๋“ญ๋‹ˆ๋‹ค.
๋ง์ด ์ข€ ์–ด๋ ค์šด๋ฐ, type-specifier์—๊ฒŒ identifier๋ผ๋Š” ๋ณ„์นญ์„ ๋ถ™์—ฌ์ฃผ๋Š” ๊ฒ๋‹ˆ๋‹ค.

//        ↓ ๋ฐ˜ํ™˜๊ฐ’ ์ž๋ฃŒํ˜• 
 typedef void (*PFN_HOOKSTART)(); // PFN_HOOKSTART๋ฅผ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ ๋ณ„์นญ์œผ๋กœ ์ •์˜ 
//              ↑ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ ๋ณ„์นญ

์œ„ ์ฝ”๋“œ์—์„œ๋Š” ๋ฐ˜ํ™˜๊ฐ’ ์ž๋ฃŒํ˜•์ด void์ธ (๋ฐ˜ํ™˜ ์ž๋ฃŒํ˜•์ด ์—†๋Š”) ํ•จ์ˆ˜ ํฌ์ธํ„ฐ์—๊ฒŒ PFN_HOOKSTART๋ผ๋Š” ๋ณ„์นญ์„ ๋ถ™์—ฌ์คฌ์Šต๋‹ˆ๋‹ค. ์ด๋Ÿฌํ•œ ๋ฐฉ์‹์€ void (*PFN_HOOKSTART)();๋ผ ์ผ์ผ์ด ์ž๋ฃŒํ˜•์„ ๋ช…์‹œํ•ด์•ผ ํ•˜๋Š” full pointer type ์˜ ์‚ฌ์šฉ์„ ์ค„์ด๊ธฐ ์œ„ํ•ด ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค. ์งฑ์งฑ.

[ํ•œ์ค„์š”์•ฝ]
typedef ์ž๋ฃŒํ˜• (*๋ณ„์นญ)(์ธ์ž ํƒ€์ž…, ์ธ์ž ํƒ€์ž…...); => ํ•จ์ˆ˜ ๋ณ„์นญ์œผ๋กœ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ ์„ ์–ธ ๊ฐ€๋Šฅ(ํŽธํ•จ)

03-0) main - ๋ณ€์ˆ˜ ์ •์˜

HMODULE hDll = NULL; 

PFN_HOOKSTART HookStart = NULL; 
PFN_HOOKSTOP HookStop = NULL; 
char ch = 0;

HMODULE: dll์˜ ์ธ์Šคํ„ด์Šค ํ•ธ๋“ค์ž…๋‹ˆ๋‹ค. dll ํŒŒ์ผ ์ด๋ฏธ์ง€๊ฐ€ ๋งคํ•‘๋œ ๊ฐ€์ƒ ๋ฉ”๋ชจ๋ฆฌ ์ฃผ์†Ÿ๊ฐ’์ž…๋‹ˆ๋‹ค.
(์ถœ์ฒ˜: ์ˆ˜๊นŒ๋ฝ์˜ ํ”„๋กœ๊ทธ๋ž˜๋ฐ ์ด์•ผ๊ธฐ)
์ด ํƒ€์ž…์˜ ๋ณ€์ˆ˜๋Š” ํ›„์— GetProcAddress()์˜ ์ฒซ๋ฒˆ์งธ ์ธ์ž๋กœ ๋“ค์–ด๊ฐ‘๋‹ˆ๋‹ค.
PFN_HOOKSTART์™€ PFN_HOOKSTOP ์ž๋ฃŒํ˜•์˜ ๋ณ€์ˆ˜๊ฐ€ ๊ฐ๊ฐ ์„ ์–ธ๋œ ๊ฒƒ์„ ๋ณผ ์ˆ˜ ์žˆ๋Š”๋ฐ, ์•ž์˜ typedef ๊ตฌ๋ฌธ์œผ๋กœ ๋ฏธ๋ฃจ์–ด๋ณด์•„ ์ด๋Š” ๊ทธ๋ƒฅ voidํ˜• ํ•จ์ˆ˜ ํฌ์ธํ„ฐ๋ฅผ ์„ ์–ธํ–ˆ๋‹ค๊ณ  ๋ณด์•„๋„ ๋ฌด๊ด€ํ•ฉ๋‹ˆ๋‹ค.

๊ฐ ๋ณ€์ˆ˜์˜ ์“ฐ์ž„์— ๋Œ€ํ•ด ์ •๋ฆฌํ•˜์ž๋ฉด..

hDll: LoadLibraryA()๋ฅผ ํ†ตํ•ด "KeyHook.dll"์˜ ํ•ธ๋“ค ๊ฐ’์„ ๊ฐ–๊ฒŒ ๋จ, GetProcAddress() ์˜ ์ฒซ ์ธ์ž๋กœ ์“ฐ์ž„
HookStart: KeyHook.dll ๋‚ด์˜ HookStart() ํ•จ์ˆ˜๋ฅผ ๊ฐ€๋ฆฌํ‚ค๋Š” ํ•จ์ˆ˜ ํฌ์ธํ„ฐ
HookStop: KeyHook.dll ๋‚ด์˜ HookStop() ํ•จ์ˆ˜๋ฅผ ๊ฐ€๋ฆฌํ‚ค๋Š” ํ•จ์ˆ˜ ํฌ์ธํ„ฐ
ch: ??

03-1) main - LoadLibraryA()

hDll = LoadLibraryA(DEF_DLL_NAME);

DEF_DLL_NAME (์ปดํŒŒ์ผ์„ ๊ฑฐ์น˜๋ฉฐ "KeyHook.dll"๋กœ ๋ณ€๊ฒฝ) ์ด๋ผ๋Š” DLL์„ ๋กœ๋“œํ•˜๊ณ , hDll์— "KeyHook.dll"์— ๋Œ€ํ•œ ํ•ธ๋“ค ๊ฐ’์„ ์ค๋‹ˆ๋‹ค.

03-2) main - GetProcAddress

HookStart = (PFN_HOOKSTART)GetProcAddress(hDll, DEF_HOOKSTART); 
HookStop = (PFN_HOOKSTOP)GetProcAddress(hDll, DEF_HOOKSTOP);

๋จผ์ € GetProcAddress๋ผ๋Š” ํ•จ์ˆ˜๋ฅผ ์‚ดํŽด๋ณด๋„๋ก ํ•ฉ์‹œ๋‹ค. (msdn์€ ์—ฌ๊ธฐ)

FARPROC GetProcAddress(HMODULE hModule, LPCSTR lpProcName);

์›ํ˜•์€ ์ด๋ ‡๊ฒŒ ์ƒ๊ฒผ์Šต๋‹ˆ๋‹ค.
์ฒซ ์ธ์ž hModule์—๋Š” LoadLibraryA()์˜ ๋ฐ˜ํ™˜ ๊ฐ’์„ ๋„ฃ์–ด์ฃผ๋ฉด ๋ฉ๋‹ˆ๋‹ค.
๋‘ ๋ฒˆ์งธ ์ธ์ž lpProcName๋Š” ์ฐพ์„ ํ•จ์ˆ˜ ์ด๋ฆ„ ์ •๋„๋กœ ์ƒ๊ฐํ•ฉ์‹œ๋‹ค.
์ด ํ•จ์ˆ˜๋Š” export ํ•จ์ˆ˜ ์ฃผ์†Œ๋ฅผ ์–ป๊ธฐ ์œ„ํ•ด ์‚ฌ์šฉ๋ฉ๋‹ˆ๋‹ค.

GetProcAddress()๋กœ ํ•จ์ˆ˜ ์ฃผ์†Œ๋ฅผ ์–ป์–ด์˜ค๊ธฐ ์œ„ํ•ด์„œ๋Š” ์ ์ ˆํ•œ ํ˜• ๋ณ€ํ™˜์„ ๊ฑฐ์ณ์•ผ ํ•ฉ๋‹ˆ๋‹ค.
์œ„์—์„œ๋Š” PFN_HOOKSTART/PFN_HOOKSTOP ํƒ€์ž…์œผ๋กœ ํ˜•ํƒœ๋ฅผ ๋ณ€ํ™˜ํ•ฉ๋‹ˆ๋‹ค.
(์ด๋Š” ์•„๊นŒ typedef์—์„œ ๋ช…์‹œ๋˜์—ˆ๋“ฏ voidํ˜• ํ•จ์ˆ˜ํฌ์ธํ„ฐ๋กœ ์ƒ๊ฐํ•˜์…”๋„ ๋ฌด๊ด€ํ•ฉ๋‹ˆ๋‹ค.)

dll์„ ๋กœ๋“œํ•˜๊ณ , ๋กœ๋“œ๋œ dll ๋‚ด์—์„œ ์‚ฌ์šฉํ•  ํ•จ์ˆ˜์˜ ์ฃผ์†Œ๋ฅผ ๊ตฌํ–ˆ์œผ๋‹ˆ ์ด์ œ ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•  ์ผ๋งŒ ๋‚จ์•˜์Šต๋‹ˆ๋‹ค.

03-2) main - export ํ•จ์ˆ˜ ์‚ฌ์šฉ

HookStart(); 
printf("press 'q' to quit!\n"); 

while(_getch() != 'q'); 
HookStop(); 

FreeLibrary(hDll);

PFN_HOOKSTART ํ˜•์˜ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ HookStart()๋Š” ์œ„์˜ ๊ณผ์ •์„ ๊ฑฐ์ณ ๊ตฌํ•œ KeyHook.dll์˜ HookStart ํ•จ์ˆ˜๋ฅผ ๊ฐ€๋ฆฌํ‚ต๋‹ˆ๋‹ค.
HookStart()๋ฅผ ํ˜ธ์ถœํ•ด ํ›„ํ‚น์„ ์‹œ์ž‘ํ•ฉ๋‹ˆ๋‹ค.

while(_getch() != 'q'); ๋ถ€๋ถ„์„ ๋ด…์‹œ๋‹ค.
๊ฐ„๋‹จํ•˜๊ฒŒ, q๋ฅผ ์ž…๋ ฅํ•˜์ง€ ์•Š์œผ๋ฉด HookStart() ํ•จ์ˆ˜๊ฐ€ ๋๋‚˜์ง€ ์•Š๋Š”๋‹ค๋Š” ์˜๋ฏธ์ž…๋‹ˆ๋‹ค.
('q'๋ฅผ ์ž…๋ ฅํ•˜๋ฉด while๋ฌธ ์•„๋ž˜์˜ HookStop() ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•ฉ๋‹ˆ๋‹ค.)

๋งˆ์ฐฌ๊ฐ€์ง€๋กœ KeyHook.dll ๋‚ด HookStop() ํ•จ์ˆ˜์˜ ์ฃผ์†Œ๋ฅผ ๋‹ด๊ณ  ์žˆ๋Š” PFN_HOOKSTOP ํ˜•์˜ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ HookStop()์„ ํ˜ธ์ถœํ•ฉ๋‹ˆ๋‹ค. (์ด ํ•จ์ˆ˜๋Š” ํ›„ํ‚น์„ ์ค‘๋‹จํ•˜๋Š” ์—ญํ• ์„ ํ•ฉ๋‹ˆ๋‹ค.)
ํ›„ํ‚น์„ ์ข…๋ฃŒํ•œ ํ›„, ๋กœ๋“œํ•œ KeyHook.dll์„ ์–ธ๋กœ๋“œ ํ•˜๊ธฐ ์œ„ํ•ด FreeLibrary() ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค.
FreeLibrary()์˜ ์ธ์ž๋กœ๋Š” ์–ธ๋กœ๋“œ ํ•  dll์˜ ํ•ธ๋“ค ๊ฐ’์„ ๋„˜๊ฒจ์ฃผ๋ฉด ๋ฉ๋‹ˆ๋‹ค.
(LoadLibrary() ํ˜ธ์ถœ๋กœ ์–ป์€ ๋ฐ˜ํ™˜ ๊ฐ’์„ FreeLibrary() ์ธ์ž๋กœ ๋„ฃ์–ด์ฃผ๋ฉด ํ•ด์ œํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.)

๋‹ค์Œ์œผ๋กœ๋Š” KeyHook.dll (KeyHook.cpp) ์˜ ์ฝ”๋“œ๋ฅผ ์‚ดํŽด๋ณด๋„๋ก ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.
์ฒ˜์Œ์—๋Š” ๋‹ค์†Œ ๋ณต์žกํ•˜๋‹ค๊ณ  ๋Š๋‚„ ์ˆ˜ ์žˆ์œผ๋‚˜, ์ฐจ๊ทผ์ฐจ๊ทผ ํ•ด์„ํ•ด๋ณธ๋‹ค๋ฉด ์ „ํ˜€ ์–ด๋ ต์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

KeyHook.cpp (KeyHook.dll)

//KeyHook.cpp 
#include "stdio.h" 
#include "windows.h" 
#define DEF_PROCESS_NAME "notepad.exe" 

HINSTANCE g_hInstance = NULL; 
HHOOK g_hHook = NULL; 
HWND g_hWnd = NULL; 

BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD dwReason, LPVOID lpvReserved) {
	switch( dwReason) {
    	case DLL_PROCESS_ATTACH: 
        	g_hInstance = hinstDLL; 
            break; 
        
        case DLL_PROCESS_DETACH: 
        	break; 
    } 
    
    return TRUE; 
} 

LRESULT CALLBACK KeyboardProc(int nCode, WPARAM wParam, LPARAM lParam) { 
	char szPath[MAX_PATH] = {0, }; 
    char *p = NULL; 
    
    if( nCode >= 0 ) { //bit 31: 0 = key press, 1 = key release 
    	if( !(lParam & 0x80000000) ) { 
        	GetModuleFileNameA(NULL, szPath, MAX_PATH); 
            p = strrchr(szPath, '\\'); 
            if( !_stricmp(p+1, DEF_PROCESS_NAME)) { 
            	return 1; 
            } 
        } 
    } 
    
    return CallNextHookEx(g_hHook, nCode, wParam, lParam); 
} 

#ifdef __cplusplus 
extern "C" { 
#endif
    __declspec(dllexport) void HookStart() {
    	g_hHook = SetWindowsHookEx(WH_KEYBOARD, KeyboardProc, g_hInstance, 0); 
    } 
    __declspec(dllexport) void HookStop() { 
    	if(g_hHook) { 
        	UnhookWindowsHookEx(g_hHook); 
            g_hHook = NULL; 
        } 
    } 
#ifdef __cplusplus 
} 
#endif

dll์ด ๋กœ๋“œ๋˜๋ฉด ๊ฐ€์žฅ ๋จผ์ € DllMain()์ด ํ˜ธ์ถœ๋˜๋ฏ€๋กœ dll injection์ด ๊ฐ€๋Šฅํ•ด์ง‘๋‹ˆ๋‹ค.

01) Preprocessor - ์ „์ฒ˜๋ฆฌ

#include "stdio.h" 
#include "windows.h" 

#define DEF_PROCESS_NAME "notepad.exe"

[#include "HeaderName"]
stdio.h ์™€ windows.h ํ—ค๋”ํŒŒ์ผ์„ ํฌํ•จํ•ด์ค๋‹ˆ๋‹ค.

[#define identifier token-string]
์ปดํŒŒ์ผ์„ ๊ฑฐ์น˜๋ฉฐ ์ฝ”๋“œ ๋‚ด ๋ชจ๋“  DEF_PROCESS_NAME์€ "notepad.exe"๋กœ ๋ณ€๊ฒฝ๋ฉ๋‹ˆ๋‹ค.

02) ๋ณ€์ˆ˜ ์ •์˜

HINSTANCE g_hInstance = NULL; 
HHOOK g_hHook = NULL; 
HWND g_hWnd = NULL;

์ƒ์†Œํ•œ ์ž๋ฃŒํ˜•์ด ๊ฝค๋‚˜ ๋ณด์ž…๋‹ˆ๋‹ค.
HINSTANCE(Handle Instance): ํ”„๋กœ๊ทธ๋žจ์˜ ์ธ์Šคํ„ด์Šค ์‹๋ณ„์ž(ํ•ธ๋“ค)
HHOOK: Hook ํ•ธ๋“ค, ์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด Hook Chain์˜ ์ฒซ ํ›… ํ•ธ๋“ค์—๊ฒŒ ์ด๋ฒคํŠธ๋ฅผ ์ „๋‹ฌํ•˜๊ณ , ๊ฐ ํ›…์€ ๋‹ค์Œ ํ›…์„ ํ˜ธ์ถœํ•˜์—ฌ Chain์— ์žˆ๋Š” ๋ชจ๋“  ํ›… ํ”„๋กœ์‹œ์ €๋ฅผ ํ˜ธ์ถœํ•จ
HWND: (Handle Windows): ์œˆ๋„์šฐ์˜ ํ•ธ๋“ค ๋ฒˆํ˜ธ, HINSTANCE๋Š” ์ธ์Šคํ„ด์Šค(์‹คํ–‰์ค‘์ธ ์ฐฝ)์˜ ํ•ธ๋“ค์„ ๊ฐ–์ง€๋งŒ HWND๋Š” ์œˆ๋„์šฐ ์ž์ฒด์˜ ํ•ธ๋“ค์„ ๊ฐ–๋Š”๋‹ค๋Š” ์ฐจ์ด๊ฐ€ ์žˆ์Œ

๋ณ€์ˆ˜์˜ ์“ฐ์ž„์„ ์ถ”๋ ค๋ณธ๋‹ค๋ฉด
g_hInstance: ํ›… ํ”„๋กœ์‹œ์ €๊ฐ€ ์†ํ•ด ์žˆ๋Š” dll ํ•ธ๋“ค์„ ๊ฐ–๊ฒŒ ๋˜๋ฉฐ, ํ›„์— SetWindowsHookEx()์˜ ์„ธ ๋ฒˆ์งธ ์ธ์ž๋กœ ์ „๋‹ฌ๋จ
g_hHook: SetWindowsHookEx() ํ•จ์ˆ˜์˜ ๋ฆฌํ„ด ๊ฐ’(์ฒ˜๋ฆฌ ์ค‘์ธ ํ›… ํ•ธ๋“ค)์„ ๊ฐ–๊ณ  CallNextHookEx()์˜ ์ฒซ ๋ฒˆ์งธ ์ธ์ž๋กœ ์ „๋‹ฌ๋จ
g_hWnd: ??

03) DllMain()

BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD dwReason, LPVOID lpvReserved) { switch( dwReason) { case DLL_PROCESS_ATTACH: g_hInstance = hinstDLL; break; case DLL_PROCESS_DETACH: break; } return TRUE; }

DllMain ํ•จ์ˆ˜์˜ ์ธ์ž๋ถ€ํ„ฐ ์‚ดํŽด๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

hinstDLL: dll์ด ๊ฐ€์ƒ ๋ฉ”๋ชจ๋ฆฌ ์ฃผ์†Œ์— ๋งคํ•‘๋˜์—ˆ์„ ๋•Œ์˜ ํ•ธ๋“ค(dll์˜ ์ธ์Šคํ„ด์Šค ํ•ธ๋“ค)
dwReason: dll์ด ํ˜ธ์ถœ๋œ ์ด์œ (ํƒ€์ด๋ฐ)
ex) DLL_PROCESS_ATTACH: dll์ด ํ”„๋กœ์„ธ์Šค์˜ ์ฃผ์†Œ ๊ณต๊ฐ„์— ๋งคํ•‘๋˜์—ˆ์„ ๋•Œ
DLL_PROCESS_DETACH: dll์ด ํ”„๋กœ์„ธ์Šค์˜ ์ฃผ์†Œ ๊ณต๊ฐ„์—์„œ ํ•ด์ œ๋˜์—ˆ์„ ๋•Œ
์ด ์™ธ์—๋„ DLL_THREAD_ATTACH, DLL_THREAD_DETACH๊ฐ€ ์žˆ์Œ
lpvReserved: ํ•จ์ˆ˜๊ฐ€ ์–ด๋Š dll์— ์†ํ•ด์žˆ๋Š”์ง€ ๋ฐํžˆ์ง€ ์•Š๊ณ  ์‚ฌ์šฉํ•  ์‹œ TRUE, ๋ฐํžˆ๊ณ  ์‚ฌ์šฉํ•  ์‹œ FALSE

DllMain ํ•จ์ˆ˜์˜ ์ฝ”๋“œ๋ฅผ ๊ฐ„๋žตํ•˜๊ฒŒ ์„ค๋ช…ํ•˜์ž๋ฉด
dll์ด ํ”„๋กœ์„ธ์Šค์˜ ์ฃผ์†Œ ๊ณต๊ฐ„์— ๋งคํ•‘๋˜์—ˆ์„ ๋•Œ๋Š” g_hInstance์—๊ฒŒ dll์˜ ์ธ์Šคํ„ด์Šค ํ•ธ๋“ค์„ ๋„˜๊ฒจ์ฃผ๊ณ , dll์ด ํ”„๋กœ์„ธ์Šค์˜ ์ฃผ์†Œ ๊ณต๊ฐ„์—์„œ ํ•ด์ œ๋˜์—ˆ์„ ๋•Œ๋Š” ๊ทธ๋ƒฅ switch๋ฌธ์„ ๋น ์ ธ๋‚˜์™€ TRUE ๊ฐ’์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

03) LRESULT CALLBACK KeyboardProc()

LRESULT CALLBACK KeyboardProc(int nCode, WPARAM wParam, LPARAM lParam) { char szPath[MAX_PATH] = {0, }; char *p = NULL; if( nCode >= 0 ) { //bit 31: 0 = key press, 1 = key release if( !(lParam & 0x80000000) ) { GetModuleFileNameA(NULL, szPath, MAX_PATH); p = strrchr(szPath, '\\'); if( !_stricmp(p+1, DEF_PROCESS_NAME)) { return 1; } } } return CallNextHookEx(g_hHook, nCode, wParam, lParam); }

ํ‚ค๋ณด๋“œ ์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜์˜€์„ ๋•Œ ์ฒ˜๋ฆฌ ๋ฐฉ์‹์„ ๊ฒฐ์ •ํ•˜๋Š” ํ•จ์ˆ˜์ž…๋‹ˆ๋‹ค.
CALLBACK์ด๋ผ๋Š” ์ด๋ฆ„์œผ๋กœ ๋ฏธ๋ฃจ์–ด๋ณด์•„, ๋‹ค๋ฅธ ํ•จ์ˆ˜์˜ ์ธ์ž๋กœ ๋“ค์–ด๊ฐ„๋‹ค๋Š” ๊ฑธ ์•Œ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

nCode: ํ›… ํ”„๋กœ์‹œ์ €๊ฐ€ ๋ฉ”์‹œ์ง€๋ฅผ ์ฒ˜๋ฆฌํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ๊ฒฐ์ •ํ•˜๋Š” ๋ฐ ์‚ฌ์šฉํ•˜๋Š” ์ฝ”๋“œ, ์ด ๊ฐ’์ด 0๋ณด๋‹ค ์ž‘์œผ๋ฉด CallNextHookEx()๋กœ ๋‹ค์Œ ํ›…์— ๋ฉ”์‹œ์ง€๋ฅผ ์ „๋‹ฌํ•จ
wParam: ์ด ์ฝ”๋“œ์—์„œ๋Š” virtual-key code๋กœ ์‚ฌ์šฉ๋จ
lParam: ์ถ”๊ฐ€ ์ •๋ณด, ์—ฌ๊ธฐ์„œ๋Š” ํ‚ค press ์—ฌ๋ถ€๋ฅผ ํŒ๋‹จํ•˜๊ธฐ ์œ„ํ•ด ์‚ฌ์šฉ๋จ

szPath: ํ˜„์žฌ ์‹คํ–‰์ค‘์ธ ํŒŒ์ผ์˜ ๊ฒฝ๋กœ๋ฅผ ๋‹ด์Œ
p: strrchr()์˜ ๋ฆฌํ„ด ๊ฐ’, szPath์˜ ๋ชจ๋“ˆ ์ด๋ฆ„์—์„œ '\\'์˜ ๋’ท ๋ถ€๋ถ„๋งŒ์„ ๋‹ด์Œ

์ฝ”๋“œ๋ฅผ ๊ฐ„๋‹จํ•˜๊ฒŒ ํ•ด์„คํ•˜์ž๋ฉด...
nCode๊ฐ€ 0๋ณด๋‹ค ์ž‘์œผ๋ฉด CallNextHookEx()๋กœ ๋ฉ”์‹œ์ง€๋ฅผ ํ›… ์ฒด์ธ์˜ ๋‹ค์Œ ํ›…์œผ๋กœ ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค.
nCode๊ฐ€ 0๋ณด๋‹ค ํฌ๊ฑฐ๋‚˜ ๊ฐ™๋‹ค๋ฉด, ๊ทธ๋ฆฌ๊ณ  ํ‚ค๊ฐ€ ๋ˆŒ๋ ค ์žˆ์„ ๋•Œ (lParam์˜ 31๋ฒˆ์งธ ๋น„ํŠธ์— ์ด์— ๊ด€ํ•œ ์ •๋ณด๊ฐ€ ์žˆ๋Š”๋ฐ, ์ด๋ฅผ 0x80000000์™€ AND ์—ฐ์‚ฐ์„ ๊ฑฐ์ณ ์•Œ์•„๋‚ผ ์ˆ˜ ์žˆ์Œ, 0 = pressed, 1 = released) GetModuleFileNameA()๋กœ szPath ๋ณ€์ˆ˜์— ํŒŒ์ผ์˜ ๊ฒฝ๋กœ๋ฅผ ๋‹ด์•„์ค๋‹ˆ๋‹ค. ํ›„์— strrchr ํ•จ์ˆ˜๋ฅผ ํ†ตํ•ด ํฌ์ธํ„ฐ p์— '\ํŒŒ์ผ์ด๋ฆ„'์ด๋ผ๋Š” ๋ฌธ์ž์—ด์ด ๋“ค์–ด๊ฐ‘๋‹ˆ๋‹ค. ์•„๋ž˜๋Š” ๊ฒฝ๋กœ ์ฒ˜๋ฆฌ ๊ณผ์ •์˜ ์ดํ•ด๋ฅผ ๋•๊ธฐ ์œ„ํ•œ ์˜ˆ์ œ์ž…๋‹ˆ๋‹ค.

๋ณด์‹œ๋‹ค์‹œํ”ผ, strrchr ํ•จ์ˆ˜๋กœ ๊ฒฝ๋กœ๋ฅผ ๊ฐ€๊ณตํ–ˆ์Œ์—๋„ ํŒŒ์ผ ์ด๋ฆ„ ์•ž์— \์ด ๋ถ™์–ด ๋‚˜์˜ค๋Š” ๊ฑธ ํ™•์ธํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
๋ญ ๊ทธ๋ž˜์„œ, ๋‹ค์Œ ์ค„์— p+1์˜ ํฌ์ธํ„ฐ ์—ฐ์‚ฐ์„ ํ†ตํ•ด \ ๋ฌธ์ž๋ฅผ ์ œ๊ฑฐํ•œ ์ˆœ์ˆ˜ ํŒŒ์ผ ์ด๋ฆ„๋งŒ ๋‚จ๊ฒผ๋Š”๋ฐ.. ์ด๊ฒŒ DEF_PROCESS_NAME("notepad.exe")์™€ ๊ฐ™๋‹ค๋ฉด 1์„ ๋ฆฌํ„ดํ•ฉ๋‹ˆ๋‹ค. if๋ฌธ์˜ ์กฐ๊ฑด์— ํ•˜๋‚˜๋ผ๋„ ๋ถ€ํ•ฉํ•˜์ง€ ์•Š๋Š”๋‹ค๋ฉด, CallNextHookEx()๋กœ ๋ฉ”์‹œ์ง€๋ฅผ ๋‹ค์Œ ํ›…์—๊ฒŒ ๋„˜๊น๋‹ˆ๋‹ค.

04) HookStart(), HookStop()

#ifdef __cplusplus extern "C" { #endif __declspec(dllexport) void HookStart() { g_hHook = SetWindowsHookEx(WH_KEYBOARD, KeyboardProc, g_hInstance, 0); } __declspec(dllexport) void HookStop() { if(g_hHook) { UnhookWindowsHookEx(g_hHook); g_hHook = NULL; } } #ifdef __cplusplus } #endif

#ifdef __cplusplus
extern "C" {
#endif
.
.
.
#ifdef __cplusplus
}
#endif

์œ„ ์ฝ”๋“œ๋Š” C++ ์ปดํŒŒ์ผ๋Ÿฌ์—๊ฒŒ ์ด๋Ÿฌํ•œ ํ˜•์‹ ์‚ฌ์ด์˜ ๊ตฌ๋ฌธ์„ C ๋ฌธ๋ฒ•์„ ์ ์šฉํ•ด ์ปดํŒŒ์ผ ํ•˜๋ผ๊ณ  ์•Œ๋ ค์ฃผ๋Š” ์—ญํ• ์„ ํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ž˜์„œ ์ด๊ฒŒ ์™œ ํ•„์š”ํ•œ๊ฐ€? C++์˜ ์ถ”์ƒํ™” ๊ฐœ๋… ๋•Œ๋ฌธ์— ๊ทธ๋ ‡๋‹ค๊ณ  ํ•ฉ๋‹ˆ๋‹ค.
KeyHook.cpp์€ C++๋กœ ์ž‘์„ฑ๋œ ๊ฒƒ์ด์ง€๋งŒ ์ด ๋ถ€๋ถ„๋งŒ์€ C์˜ ๋ฌธ๋ฒ•์„ ์ ์šฉํ•ด ์ปดํŒŒ์ผ ๋ฉ๋‹ˆ๋‹ค.

HookStart()๋ถ€ํ„ฐ ๋ด…์‹œ๋‹ค.
__declspec์€ ํ•จ์ˆ˜์— ๋Œ€ํ•œ ์ •๋ณด๋ฅผ ๋‚˜ํƒ€๋‚ด๋Š” ์„ ์–ธ๋ฌธ์ž…๋‹ˆ๋‹ค.
__declspec(dllexport)๋Š” ์ •์˜๋œ ํ•จ์ˆ˜๊ฐ€ dll์—์„œ export ๋˜๋Š” ํ•จ์ˆ˜๋ผ๋Š” ๋œป์ž…๋‹ˆ๋‹ค.
๊ธฐ์–ตํ•˜์‹ค์ง€๋Š” ๋ชจ๋ฅด๊ฒ ์ง€๋งŒ ์•ž์„œ HHOOK ํƒ€์ž…์˜ g_hHook ๋ณ€์ˆ˜๋Š” SetWindowsHookEx()์˜ ๋ฆฌํ„ด ๊ฐ’(ํ›… ํ•ธ๋“ค)์„ ๊ฐ–๋Š”๋‹ค๊ณ  ๋ง์”€๋“œ๋ ธ์Šต๋‹ˆ๋‹ค. ์•”ํŠผ ๊ทธ๋ž˜์„œ g_hHook์€ ํ›… ํ•ธ๋“ค์„ ๊ฐ–๊ฒŒ ๋ฉ๋‹ˆ๋‹ค.

HHOOK SetWindowsHookExA( int idHook, HOOKPROC lpfn, HINSTANCE hmod, DWORD dwThreadId );

์›ํ˜•์€ ์ด๋ ‡๊ฒŒ ์ƒ๊ฒผ์Šต๋‹ˆ๋‹ค.
idHook: ํ›„ํ‚นํ•  ํƒ€์ž…, ์œ„ ์ฝ”๋“œ์„  WH_KEYBOARD๋ฅผ idHook์œผ๋กœ ์ฃผ์—ˆ์œผ๋ฏ€๋กœ ํ‚ค๋ณด๋“œ๋ฅผ ํ›„ํ‚นํ•  ๊ฒƒ์ž„
lpfn: ํ›… ํ”„๋กœ์‹œ์ €์˜ ํ•จ์ˆ˜ ํฌ์ธํ„ฐ. ์•„๊นŒ ์‚ดํŽด๋ณธ KeyboardProc์„ lpfn์œผ๋กœ ๋„˜๊ฒจ์„œ ์”€
hmod: lpfn์˜ ํ›„ํ‚น ํ•จ์ˆ˜๊ฐ€ ๋“ค์–ด์žˆ๋Š” ๋ชจ๋“ˆ์˜ ์ฃผ์†Œ. ์ธ์ž๋กœ g_hInstance๊ฐ€ ๋„˜์–ด๊ฐ€๋Š”๋ฐ, ์ด g_hInstance๋Š” DllMain()์ด DLL_PROCESS_ATTACH๋กœ ์‹คํ–‰๋˜์—ˆ์„ ๋•Œ hinstDLL ๊ฐ’์„ ๊ฐ€์ง
dwThreadId: ํ›„ํ‚นํ•  ๋Œ€์ƒ์˜ ์Šค๋ ˆ๋“œ id, ์ด ๊ฐ’์ด 0์ด๋ผ๋ฉด ๋ฐ์Šคํฌํƒ‘์˜ ๋ชจ๋“  ์Šค๋ ˆ๋“œ๋ฅผ ํฌํ•จํ•˜๋Š” ์ „์—ญ ํ›„ํ‚น์ด ์ด๋ฃจ์–ด์ง„๋‹ค.

์ด๋ ‡๊ฒŒ ํ•ด์„œ notepad.exe์˜ ๋ฉ”์‹œ์ง€ ํ›„ํ‚น์ด ์ด๋ฃจ์–ด์ง‘๋‹ˆ๋‹ค.
๊ธ€์€ ์ถ”ํ›„์— ๋” ์ •๋ฆฌํ•ด๋ณด๋„๋ก ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.