-
Код Dll практически полностью взят из faq по hook'ам.
library keyhook; uses SysUtils, windows, Classes; {$R *.res} const MMFName: PChar = 'KeyMMF'; // имя объекта файлового отображения type PGlobalDLLData = ^TGlobalDLLData; TGlobalDLLData = packed record SysHook: HWND; // дескриптор установленной ловушки MyAppWnd: HWND; // дескриптор нашего приложения end; var GlobalData: PGlobalDLLData; MMFHandle: THandle; hookmessage:dword; function globalkeyhook(code: integer; wParam: word; lParam: longword): longword; stdcall; begin if code<0 then begin //if code is <0 your keyboard hook should always run CallNextHookEx instantly and result:=CallNextHookEx(0,code,wParam,lparam); //then return the value from it. Exit; end; if (wParam=$45) and ((lparam and $80000000)=0) then if ((getkeystate(VK_control) and $80) >0) and ((getkeystate(VK_menu) and $80) =0) and ((getkeystate(VK_shift) and $80) =0) then begin
postmessage(GlobalData^.MyAppWnd,hookmessage,0,1); CallNextHookEx(0,code,wParam,lparam); result:=1; exit; end; CallNextHookEx(0,code,wParam,lparam); result:=0; exit; end;
procedure sethookhandle(hMainProg: HWND; switch : Boolean) export; stdcall; begin if switch=true then begin {Устанавливаю HOOK, если он не установлен (switch=true). } GlobalData^.SysHook := SetWindowsHookEx(WH_KEYBOARD, @globalkeyhook, HInstance, 0); GlobalData^.MyAppWnd:= hMainProg; if GlobalData^.SysHook <> 0 then MessageBox(0, 'KEYBOARD HOOK установлен !', 'Message from keyhook.dll', 0) else MessageBox(0, 'HOOK установить не удалось !', 'Message from keyhook.dll', 0);
end else begin
{Удаляю функцию-фильтр, если она установлена (т.е. switch=false). } if UnhookWindowsHookEx(GlobalData^.SysHook) then MessageBox(0, 'HOOK снят !', 'Message from keyhook.dll', 0) else MessageBox(0, 'HOOK снять не удалось !', 'Message from keyhook.dll', 0);
end; end;
procedure OpenGlobalData(); begin {регестрируем свой тип сообщения в системе} hookmessage:=registerwindowmessage('wm_hookmessage');
{получаем объект файлового отображения} MMFHandle:= CreateFileMapping(INVALID_HANDLE_VALUE, nil, PAGE_READWRITE, 0, SizeOf(TGlobalDLLData), MMFName);
if MMFHandle = 0 then begin MessageBox(0, 'Can''t create FileMapping', 'Message from keyhook.dll', 0); Exit; end;
{отображаем глобальные данные на АП вызывающего процесса и получаем указатель на начало выделенного пространства} GlobalData:= MapViewOfFile(MMFHandle, FILE_MAP_ALL_ACCESS, 0, 0, SizeOf(TGlobalDLLData)); if GlobalData = nil then begin CloseHandle(MMFHandle); MessageBox(0, 'Can''t make MapViewOfFile', 'Message from keyhook.dll', 0); Exit; end;
end;
procedure CloseGlobalData(); begin UnmapViewOfFile(GlobalData); CloseHandle(MMFHandle); end;
procedure DLLEntryPoint(dwReason: DWord); stdcall; begin case dwReason of DLL_PROCESS_ATTACH: OpenGlobalData; DLL_PROCESS_DETACH: CloseGlobalData; end; end;
exports sethookhandle;
begin //hookmessage:=registerwindowmessage('wm_hookmessage'); {назначим поцедуру переменной DLLProc} DLLProc:= @DLLEntryPoint; {вызываем назначенную процедуру для отражения факта присоединения данной библиотеки к процессу} DLLEntryPoint(DLL_PROCESS_ATTACH);
end.
Бибилиотека загружается и работает несколько минут. После этого выдает ошибку доступа к памяти и виснет программа из которой запускаю dll и окна в которых нажимались клавиши(все процессы к которым подгружалась библиотека)
-
Попробовал на xp запускать. Работает нормально, но при некоторых манипуляций с окном выдает ошибку, и при закрытии всегда выдает ошибку. Возможно не может обработать какие-то сообщения системы.
-
Это плохой пример (подозреваю что от Миши Фленова), возьми другой...
-
> function globalkeyhook(code: integer; wParam: word; lParam: > longword): longword; stdcall;
когда вы уже поумнеете ?
-
|