![]() |
Message wird nicht gesendet bei globalem Hook
Liste der Anhänge anzeigen (Anzahl: 1)
Hallo !!
Ich habe mich heute mit Hooks beschäftigt und bin auf dieses ![]() Das ist natürlich sehr seltsam. Zum schicken der Nachricht verwende ich SendMessage. Der Fehler liegt auch bei dieser Funktion, denn die Hook-Prozedur wird auch ausgeführt, wenn mein Fenster im Hintergrund ist. Hier mal ein bisschen Code, vielleicht hilft er euch ja weiter.
Delphi-Quellcode:
Habt ihr Ideen, wieso er die Message nicht mehr schickt ??
// aus der DLL
const WM_MOUSEHOOKMSG = WM_USER + 1; var GlobalHooksFormHandle: HWND = 0; MouseHookHandle: HHOOK = 0; function MouseHookProc(nCode: Integer; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall; var LMouseHookStruct: TMouseHookStruct; LMousePositionX: Integer; LMousePositionY: Integer; begin if nCode = HC_ACTION then begin LMouseHookStruct := PMouseHookStruct(lParam)^; LMousePositionX := LMouseHookStruct.pt.X; LMousePositionY := LMouseHookStruct.pt.Y; if GlobalHooksFormHandle <> 0 then SendMessage(GlobalHooksFormHandle, WM_MOUSEHOOKMSG, LMousePositionX, LMousePositionY); end; Result := CallNextHookEx(MouseHookHandle, nCode, wParam, lParam); end; function InstallHooks(AGlobalHooksFormHandle: HWND): Boolean; stdcall; var LMouseHookProc: TFNHookProc; begin GlobalHooksFormHandle := AGlobalHooksFormHandle; LMouseHookProc := MouseHookProc; MouseHookHandle := SetWindowsHookEx(WH_MOUSE, LMouseHookProc, HInstance, 0); Result := MouseHookHandle <> 0; end; Falls euch der Code nicht reicht, ich hab mal die ganze Projektgruppe angehängt. Vielen Dank schon mal im Voraus, Oliver :hi: |
Re: Message wird nicht gesendet bei globalem Hook
du könntest versuchen, als Nachricht eine mit RegisterWindowMessage erzeugte Nachricht zu benutzen. WM_USER+x wird nur empfohlen, wenn du in deinen threads rumfunkst und nicht zwischen prozessen.
Außerdem solltest du GlobalHooksFormHandle mal protokollieren(in eine datei schreiben z.B.), es könnte sein, dass die nicht immer den richtigen Wert hat. am besten per Broadcast suchen (und dann auf jeden fall mit RegisterWindowMessage). Broadcasts kommen übrigens nur bei top-level windows an, also im Application.OnMessage! |
Re: Message wird nicht gesendet bei globalem Hook
Genau aus dem Grund nimmt der Author mmf's.
Wenn du einen Hook "installierst" wird die DLL in die verschiedensten Prozesse geladen. Beim laden der DLL in den verschiedenen Prozessen ruft jedoch niemand deine Methode InstallHooks auf. Die Methode InstallHooks wird einzig in der DLL-Instanz geladen welche du in deinem Programm lädst. Wenn deine DLL als in der Explorer.exe geladen wird, wird dort sozusagen nur ein LoadLibrary gemacht und ein lokaler Hook auf deine DLL-Procedure. Es wird bei einem SetWindowsHook-Aufruf also nix anderes gemacht als - Lade in so ziemlich jedem Prozess die DLL "DeineDLL.DLL" und schleife alle Nachrichten durch die Funktion MouseHookProc der DLL. Es wird also darin nirgends deine Variable GlobalHooksFormHandle gesetzt, das geschieht einzug und allein in der DLL instanz die du in deinem Programm lädst. Dir scheint also das Verständnis zu fählen was genau bei einem hook-setzen passiert. Dein Code kommt ungefähr dem gleich: Du hast einen Notizblock und schreibst eine Telefonnummer drauf. Dann sagst du all deinen Freunden Sie sollen sich auch einen Notizblock vom Stabel nehmen und alles was passiert sollen sie telefonisch an die auf dem Block vermerkte Nummer übermitteln. Das Problem: Die telefonnummer steht nur auf deinem Block. |
Re: Message wird nicht gesendet bei globalem Hook
jop, das liegt daran, dass die DLLs nicht den selben speicher benutzen. Ein Feature, das Delphi einfach fehlt. (Liegt das nicht am MemoryManager? Kann das nicht z.B. FastMM?)
|
Re: Message wird nicht gesendet bei globalem Hook
@DGL-Luke: Nein, das ist kein Problem vom Delphimemorymanager. Wie bereits geschrieben wird die DLL bei einem Aufruf von SetWindowsHookEx in jedem Prozess neu geladen, so als würde in dem Prozess jemand einen lokalen Hook mit SetWindowsHookEx starten. Ein globaler Hook ist sozusagen ein Rundruf das so ziemlich jeder einen Lokalen Hook auf die Adresse-X in der DLL-X setzen soll. Dabei laden dann die Prozesse die DLL und setzen eben einen lokalen Hook auf die Funktion.
Einziges was es in Delphi nicht gibt (was in C++ wohl einfacher gelöst ist) das es da gemeinsam genutzen Speicher ohne den Umweg über mmf's gibt. Das ganze ist aber auch logisch, denn wenn die Messages von anderen Prozessen an die Hook-Procedure des geinen Prozesses übergeben werden würden wären die Adressen welche sich teilweise in WParam und LParam befinden völlig nutzlos da die Adressen nur im anderen Prozess gültig sind (also in dem Prozess wo sie her kommen). |
Re: Message wird nicht gesendet bei globalem Hook
Okay, danke :)
Jetzt weiß ich wo mein Problem liegt, und werde einen anderen Weg nehmen. mfg Oliver |
Re: Message wird nicht gesendet bei globalem Hook
Zitat:
|
Re: Message wird nicht gesendet bei globalem Hook
aber eben auch nur wenn die Variable in C++ so speziell deklariert wäre das sie im gemeinsam genutzten speicher liegt. Und dementsprechend kann man das in Delphi durch mmf's auch erreichen.
ich habs bei meinen Programmen wenn ich sowas braucht bisher immer im Hauptprogramm ein mmf angelegt und das Handle rein geschrieben. Die DLL's haben dann beim laden (also zwischen begin und end) das mmf geöffnet und das handle gelesen und dann auch mit sendmessage kommuniziert. |
Re: Message wird nicht gesendet bei globalem Hook
Ich hab's jetzt so gemacht, dass im Ladeabschnitt der DLL per FindWindow mein Handle gesucht wird.
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 04:48 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz