| Autor |
Beitrag |
Andreas Pfau
      
Beiträge: 997
|
Verfasst: Di 04.02.03 21:03
Hallo,
ich habe einen Tastatur-Hook geschreiben. Ich will, dass er auch dann arbeitet, wenn die Anwendung, die ihn installiert, beendet wird. Wenn das nicht geht, müsste ich eine Eigenständige Anwendung schreiben. Daher meine Fragen:
- Wie lasse ich einen Hook laufen, wenn die App beendet wird oder
- Wie kann ich mit einem Programm kommunizierren, dass kein Fenster hat, also ohne Messages?
|
|
Luckie
Ehemaliges Mitglied
Erhaltene Danke: 1
|
Verfasst: Di 04.02.03 21:19
Versuch es mit einem Service, den kann nur der Admin beenden. Zur Kommunikation kannst du MMF nehmen.
Ist aber sehr unschön, was du da machst. Ist übrigens strafbar, wenn du die nutzer des Computers nicht daraufhinweist, das iher Eingaben alle mit protokolliert werden.
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Di 04.02.03 22:05
1) Danke für den Tipp. Aber was ist "MMF"? Na ja, wie auch immer, mir ist auch was eingefallen. Ich nehme einfach ein Event, um eine externe Server-App zu beenden. Ist einfacher. Trotzdem danke für den Tipp!
2) Was denkst du von mir? Klar, naheliegend. Aber ich kläre dich mal aucf: Der Hook soll "X" in "Y" umwandeln, und umgekehrt. Also ein Wrapper für Anwendungen, die auf dei englische Tastatur ausgelegt sind, z.B. Midi-Keyboards, (Windows-)Spiele etc. Der funktioniert schon, aber mich nervt's, dass die App immer sichtbar sein muss, um zu wrappen. Am besten wäre es natürlich, dass der wrapper nur dann arbeitet, wenn eine bestimmte Anwendung läuft (also eine, die gewrappt werden muss). Das will ich mit FindWindow() und GetForegroundWindow() machen. Müsste klappen. Aber wenn ich das mache, ist doch klar, dass der wrapper unsichbar arbeitet, ich kein nerviges Taskbar- oder Trayicon haben will, gell?
Wie auch immer. Was meinst du zu Events? Müsste doch gehen, oder? Oder ist MMF besser, was auch immer das ist?
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Di 04.02.03 22:50
Jawoll, der Karren sitzt im Dreck!
Warum funktioniert der Hook nihct, wenn ich ihn aus einer Anwendung ohne Fenster aufrufe? Ich habe nur 'ne DPR, beim Start wird der Hook installiert, dann warte ich auf ein event, deinstallieren, DLL freigeben, DPR zu Ende. Warum tut's nicht?
|
|
Luckie
Ehemaliges Mitglied
Erhaltene Danke: 1
|
Verfasst: Di 04.02.03 23:20
Das Fenster ist doch nur ein Werkzeug, um die Hook-DLL zu registrieren. Wenn du den Nagel in die Wand geschlagen hast kannst du doch auch den Hammer wegschmeißen und trotzdem am Nagel noch ein Bild aufhängen.
MMF = Memory Mapped Files. Sende doch von der DLL aus eine Nachricht an die Anwendung in der der Buchstabe ersetzt werden soll. Zum schicken barauchst du doch keine Nachrichten Schleife.
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Mi 05.02.03 18:09
Also... den Hammer wegschmeißen... heißt das jetzt, dass ich ein Fensterhandle brauche? Aber wozu, das muss ich doch nirgends übergeben, oder? Ganz allgemein: Wie kann ich ohne Fenster einen Hoomk installieren und deinstallieren? Aber das mit dem Hammer wegschmeißen gefällt mir gar nicht! Dazu muss ich doch die DLL-Instanz freigeben, und dann ist der Hook futsch! Die App muss laufen. Aber eben ohne Fenster!
OK, was MMF heißt wissen wir jetzt. Kannst du mir dan mal 'ne Adresse posten, wo ich codes oder tuts finde? Also rein vom Namen her nehme ich an, das ist 'ne Art Heap, den ich wie 'nen Stream zum Lesen oder schreiben nehmen kann. Oder?
Na ja, und das mit den Nachrichten senden... Nichts anderes mache ich! Aber ohne Hook erfahre ich ja nicht, wann ich 'nen Keystroke senden muss. Daher der Hook.
Außerdem: ein bisserl Definitionssache: 'ne Nachrichtenschleife ist doch ne Schleife, in der ich bei jedem Durchlauf Messages abhole und verarbeite. Aber hier liegt keine Schleife vor, sondern 'ne Prozedur, die Windows für mich aufruft (Sorry, ich will dich nicht kritisieren  ).
|
|
Luckie
Ehemaliges Mitglied
Erhaltene Danke: 1
|
Verfasst: Mi 05.02.03 20:10
Wenn die App was auswerrten soll, was die Hook-DLL liefert, dann muß sie logischerweise weiterlaufen. Aber es schreibt dir ja keiner vor, dass du das fenster auch anzeigen mußt oder?
|
|
DaFox
      
Beiträge: 189
|
Verfasst: Mi 05.02.03 20:26
Jetzt mal 'ne andere Frage: Für was braucht man 'ne "App", wenn nur ein paar Tasten vertauscht werden sollen? Das kannst Du auch in der Hook-Proc machen. Das befreit Dich aber nicht vor der Verwendung eines MMF, da Du ja in jedem Prozess den nächsten Hook in der Schlange aufrufen musst...
Markus
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Mi 05.02.03 21:04
Ne, ne, ihr versteht mich falsch...
Ich hab 'ne EXE und 'ne DLL. In der DLL ist ein Hook implementiert, der die Tasten wrappt. Wenn ich den Hook in 'ner EXE implementiere, ist er ja nicht global. Aber ich kann ja wohl schlecht 'nen Hook ohne App installieren, gell, @DaFox? Außerdem soll man ja auch ein Config-Fenster haben, z.B. Autorun. OK, fassen wir zusammen, ich brauche eine App.
Dann... Danke, @Luckie, ich habe deinen Rat befolgt und den Hammer weggeworfen... äh... das Fenster mit TForm.Hide() versteckt.
Na ja, dann bin aich auf ein weitere Prob gestoßen... Der Hook arbeitet nur lokal... Tastendrücke außerhalb meiner App werden nicht gewrappt... aber das ist ja grad der Witz, meine App ist ja deutsch... Gibt es villeicht irgend eine Methode, eine Hook von Lokal auf Global zu ändern?
LBNL... @Luckie, erklär mir doch bitte mal genau, was ein MMF ist. Ich habe es jetzt mal so implementiert: Beim Programmstrt wir mittels Mutex ermittelt, ob die App läuft. Wenn nicht, wird eine Nachricht mir RegisterWindowMessage() gesendet, die von der laufenden instanz empfangen wird, welche sich darauf hin maximiert. Genial, gell?[/code]
|
|
DaFox
      
Beiträge: 189
|
Verfasst: Mi 05.02.03 21:34
Hm, dass Du einen "Loader" für Deine DLL brauchst ist logisch.
Dass der globale Hook in einer DLL ist  logisch.
Dass der Hook nur lokal arbeitet, wenn Du noch nie was von MMF gehört hast, könnte  logisch sein
Denn bedenke: Ein globaler Hook läuft im Speicherkontext jedes Prozesses. Du lädst den Hook. Ergo: Die DLL, der Hook, wurde im Kontext Deines Prozesses gestartet und er läuft. Was passiert, wenn Du Informationen brauchst, die aus einem anderen Programm kommen? Du bekommst die Daten nicht weil Du nicht auf Sie zugreifen darfst und Du kannst nicht den nächsten Hook in der Hookchain aufrufen, weil die Variable in Deiner DLL (hHook) nur in der DLL initialisiert ist, der in Deinem Prozess läuft.
Du musst Dich um MMFs kümmern.
Zur "App": Du brauchst ja nur den Loader bzw. ein Konfigurationsmenu. Dadurch kannst Du auf das Programm (EXE) verzichten, während Du nur die Tasten vertauschen willst. Pack 'ne Endlosschleife in Deine DLL, in der Du per TranslateMessage(), DispatchMessage(), GetMessage() auf Nachrichten wartest.
Gruß,
Markus
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Mi 05.02.03 21:56
Also, ich Schätze deine Hilfe sehr  , aber...
1) Was ist MMF? Ich brauche harte Fakten, keine "Du brauchst MMF". Was ist das, wie geht das, wo bleibt mein Code?
2) Komisch, in meiner alten version (die noch im Systray läuft) klappt es, sogar Global. Da ich nix von MMF weiß, habe ich das auch nicht in der alten DLL verwendet, aber es tut, global, uneingeschränkt, aber wieso jetzt nicht mehr?
3) OK, gehen wir mal davon aus, einer von euch beiden verrät mir jetzt mal mehr über MMF *kein sarkasmus*... wie kann ich dann den Hook in jedem Prozess installieren? Also, so wie ich das verstanden habe, werden hook von Windows in die MessageQueue reingeschaltet, wozu soll ich mich dann in jeden Prozess einklinken?
4) | Zitat: | | Pack 'ne Endlosschleife in Deine DLL |
OK. Wie ich das verstehe, willst du, dass die App nach der installation des Hooks destroyt wird. Dann wird die DLL freigegeben. Dann wird der Hook freigegeben. Also muss ich sie laufen lassen. Also kann ich doch gleich mit eben dieser App den Hook installieren/deinstallieren. Warum Messages von 'ner peeken, wenn ich denn hook auch so kontrollieren kann? Und Wer empfängt eigentlich Messages, wo doch 'ne DLL kein Fensterhandle hat? Geht das? Ich meine, besteht die Möglichkeit, pseudohandles zu erstellen?
Sorry, dass ich mit meinen Fragen so stresse. Aber es ist doch schon komisch, dass das mit dem Hook auf einmal nicht mehr klappt...
Mal ganz nebenbei... Hooks sind die einzige Möglichkeit, Tastendrücke global abzufangen, oder?
|
|
DaFox
      
Beiträge: 189
|
Verfasst: Mi 05.02.03 22:22
| Andreas Pfau hat folgendes geschrieben: |
1) Was ist MMF? Ich brauche harte Fakten, keine "Du brauchst MMF". Was ist das, wie geht das...
|
Such mal in Deinen schlauen Büchern oder im Internet nach
OpenFileMapping() und MapViewOfFile().
| Andreas Pfau hat folgendes geschrieben: |
...wo bleibt mein Code?
|
Kein Kommentar.
| Andreas Pfau hat folgendes geschrieben: |
2) Komisch, in meiner alten version (die noch im Systray läuft) klappt es, sogar Global. Da ich nix von MMF weiß, habe ich das auch nicht in der alten DLL verwendet, aber es tut, global, uneingeschränkt, aber wieso jetzt nicht mehr?
|
Ohne Code, kann ich das nicht sagen.
| Andreas Pfau hat folgendes geschrieben: |
... wie kann ich dann den Hook in jedem Prozess installieren? Also, so wie ich das verstanden habe, werden hook von Windows in die MessageQueue reingeschaltet, wozu soll ich mich dann in jeden Prozess einklinken?
|
Wieso musst Du uns das fragen?
| Das PSDK hat folgendes geschrieben: |
dwThreadId
Specifies the identifier of the thread with which the hook procedure is to be associated. If this parameter is zero, the hook procedure is associated with all existing threads.
|
| Andreas Pfau hat folgendes geschrieben: |
Also, so wie ich das verstanden habe, werden hook von Windows in die MessageQueue reingeschaltet, wozu soll ich mich dann in jeden Prozess einklinken?
|
Vielleicht weil der Endanwender nicht nur bei der Benutzung von Deinem Programm auf die Tasten klimmpert?
Markus
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Do 06.02.03 17:41
alos, erstmal vielen Dank für das über MMF  . Ich schaue gleich mal in der SDK nach.
| Zitat: | | Vielleicht weil der Endanwender nicht nur bei der Benutzung von Deinem Programm auf die Tasten klimmpert |
Du verstehst mich falsch: Wenn du 'nen hook codest, dann fragst du doch auch nicht die MessageQueue jedes Progs ab. Du lässt dich einfach benachrischtigen, wenn eine Message an ein X-Beliebiges Fenster kommt. Gell? Also, was ich sagen will, ich weise Windows an, das für jeden Prozess zu machen, und fertig. Ich habe verstanden mit dem dwThreadId = 0 lege ich das fest. OK.
Also, Fazit: Vielen Dank für eure Hilfe die ganze Zeit über  . Ich gehe mal davon auc, dass das globale an irgend einem klitzekleinen Fehler im code kliegt, das versuche ich zu beheben. Das mit MMF probiere ich aus.
|
|
DaFox
      
Beiträge: 189
|
Verfasst: Do 06.02.03 18:37
| Andreas Pfau hat folgendes geschrieben: |
Du verstehst mich falsch
|
Kann schon sein, aber irgendwie werde ich das Gefühl nicht los, dass Du die Idee hinter Hooks nicht verstehst.
| Andreas Pfau hat folgendes geschrieben: |
Wenn du 'nen hook codest, dann fragst du doch auch nicht die MessageQueue jedes Progs ab.
|
Richtig, weil Du (Dein Hook) die Message bekommt, bevor sie in den MessageQueue kommt.
| Andreas Pfau hat folgendes geschrieben: |
Du lässt dich einfach benachrischtigen, wenn eine Message an ein X-Beliebiges Fenster kommt. Gell?
|
Nö! Wenn Dein Hook der 1. in der Hookchain ist, wird er von Windows aufgerufen. Bist Du nicht der 1. in der Hookchain, dann wirst Du von dem Hook vor Deinem in der Hookchain aufgerufen (deshalb auch CallNextHookEx()). So wird das fortgesetzt bis zum Ende der Schleife. Diese Hookchain gibt es nicht einmal im ganzen System, sondern für jede Art (WH_GETMESSAGE,...) und jedes Programm.
Gruß,
Markus
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Do 06.02.03 20:47
Dann muss ich mich wohl bei euch entschuldigen... Sorry! Ich habe das ganze halt nicht so recht verstanden... OK.
Also, fassen wir das zusammen, nur damit ich's richtig verstehe: Falls da ein Hook vor mir ist, bekomme ich gar nix ab, sofern der 1. Hook das nicht will. Da wäre ich also Machtlos. Dann könnte es ja praktisch sein, dass irgendwo ein anderer Hook operiert. Kannd as sein? Wenn mein Fenster 'nen Keystroke bekommte, registreiert der Hook das ja. Aber warum? Woher kennt der Hook mein Fensterhandle? Egal. Also, ich tüftle jetzt halt mal ein bisschen rum, in der Hoffnung, es zum laufen zu biringen, sonst lasse ich's eben beim TrayIcon, denn diese Wrapper-Version funzt ja.
PS: Ich schreibt immer "Andreas Pfau hat folgendes geschrieben:". Wie macht man das? Ich meine, ich kopiere halt euren Text unten aus der Übersicht und mache ein "quote" draus. Aber wie setze ich den Text darüber?
|
|
Luckie
Ehemaliges Mitglied
Erhaltene Danke: 1
|
Verfasst: Do 06.02.03 20:53
Schon rechts im Kopf jden Beitrages den Knopf "Zitat" gefunden? 
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Do 06.02.03 21:02
Äh... na ja... du weißt ja: der geistige Horizont ist der Abstand zwischen Kopf und Brett... Danke!
Un noch was: es klappt! Es klappt! Ja, es klappt! Es muss mir schon peinlich sein.. ich habe einfach nur die Parameter von KeyboardProc falsch bearbeitet... sorry, dass ich euch damit so gestresst habe  .
Also, jetzt läuft mein Wrapper, und das unsichtbar (na ja, noch nicht ganz, das muss ich noch code, aber das Prinzip läuft). Danke für eure Mühe! 
|
|
DaFox
      
Beiträge: 189
|
Verfasst: Do 06.02.03 21:19
| Andreas Pfau hat folgendes geschrieben: |
Dann muss ich mich wohl bei euch entschuldigen... Sorry! Ich habe das ganze halt nicht so recht verstanden... OK.
|
Kein Problem, dafür sind wir ja da und eine Community.
| Andreas Pfau hat folgendes geschrieben: |
Also, fassen wir das zusammen, nur damit ich's richtig verstehe: Falls da ein Hook vor mir ist, bekomme ich gar nix ab, sofern der 1. Hook das nicht will. Da wäre ich also Machtlos. Dann könnte es ja praktisch sein, dass irgendwo ein anderer Hook operiert. Kannd as sein?
|
Klar, aber das wäre ja auch die Message, die das Zielfensterhandle bekommen würde.
| Andreas Pfau hat folgendes geschrieben: |
Wenn mein Fenster 'nen Keystroke bekommte, registreiert der Hook das ja. Aber warum? Woher kennt der Hook mein Fensterhandle?
|
Nein, deshalb gibt's ja die dwThreadId. Ist diese 0, so ist es ein sogenannter Systemhook, also systemweit. Ansonsten gibst Du ja als Parameter die ThreadId des Zielfensters an.
| Andreas Pfau hat folgendes geschrieben: |
Ja, es klappt!
|
Sehr schön, Glückwunsch!
| Andreas Pfau hat folgendes geschrieben: |
Danke für eure Mühe!´
|
Keine Ursache.
Gruß,
Markus
|
|
Andreas Pfau 
      
Beiträge: 997
|
Verfasst: Do 06.02.03 22:49
Ja, dafür liebe ich Foren (auche wenndas ein Board ist, obwohl es sich Forum nennt...). Also, obwohl ich die ganze Zeit über eigneltich kein Problem, sondern eher einen Denkfehler hatte, hab ich doch viel gelernt. Letzendlich muss ich sagen, Hooks sind doch etwas mehr als ich dachte. Wenigstens habe ich jetzt meine Wrapper gecodet. Ja, dann...
|
|
DaFox
      
Beiträge: 189
|
Verfasst: Fr 07.02.03 00:12
Hm, und ich dachte immer:
Forum [deutsch] = (Message-) Board [englisch]
Wo liegt da der Unterschied?
Gruß,
Markus
|
|
|