[C++Windows] Problème de création de DLL de Hook, handle & co

Problème de création de DLL de Hook, handle & co [C++Windows] - C++ - Programmation

Marsh Posté le 10-01-2003 à 21:12:04    

Bon voila je dois créer une DLL pour gérer les hook (capture d'événements) de manière a écouter tous les évenement système et à les envoyer à une application future. Pour l instant c'est une appli de test toute simple.
 
Mon problème est le suivant. Lors de l'initialisation de la DLL, je dois récupérer son handle pour le refiler à l'application pour qu'ils puissent communiquer (normal). Et comme handle je me tape 1 en retour... et apres lors de l execution de l appli qui load la dll "EAccessViolation" comme par hazard.
 
 
 
Le code de la DLL, tout se compile bien
 

Code :
  1. #include <vcl.h>
  2. #include <windows.h>
  3. #pragma hdrstop
  4. #pragma argsused
  5. // Définition de la structure de la zone mémoire partagée
  6. typedef struct _TDonnees
  7. {
  8.      HHOOK MouseHookHandle; // Handle du hook de la souris  
  9.      HHOOK KeybdHookHandle; // Handle du hook du clavier
  10.      HWND hDestWindow; // Handle de la fenêtre à laquelle le hook du clavier doit les données
  11.      // Mettez ici toutes les données que vous voulez partager
  12. } TDonnees;
  13. // Déclaration des variables globales de la DLL
  14. HANDLE MemPartagee; // Handle de la zone de mémoire partagée
  15. TDonnees * VueDonnees; // Pointeur vers la zone de mémoire
  16. HINSTANCE HInst; // Handle d'intance de la DLL
  17. // Déclaration des fonctions de la DLL
  18. void InitHook(HWND hDest);
  19. void EndHook();
  20. LRESULT CALLBACK MouseProc(int nCode,WPARAM wParam,LPARAM lParam);
  21. LRESULT CALLBACK KeybdProc(int nCode,WPARAM wParam,LPARAM lParam);
  22. // fonction d'initialisation de la DLL
  23. int WINAPI DllEntryPoint(HINSTANCE hinst, unsigned long reason, void* lpReserved)
  24. {
  25.      HInst = hinst;
  26.      switch (reason)
  27.      {
  28.           case DLL_PROCESS_ATTACH : // à la création de l'instance de la DLL
  29.                // Attachement d'une zone de mémoire partagée (notez le cast)
  30.                MemPartagee = CreateFileMapping((HANDLE)0xFFFFFFFF, // On map un espace mémoire
  31.                                         NULL, // Pas d'informations de sécurité
  32.                                         PAGE_READWRITE, // Partage en lecture/écriture
  33.                                         0, // Taille de la zone réservée sur 64 bits (32 bits de poid fort)
  34.                                         sizeof(TDonnees), // 32 bits de poids faible
  35.                                         "RMS" ); // Nom de la zone réservée
  36.                // Création d'une vue pour pouvoir accéder à la zone de mémoire partagée (notez le cast)
  37.                VueDonnees = (TDonnees *)(MapViewOfFile((HANDLE)MemPartagee, // Zone sur laquelle créer la vue
  38.                                         FILE_MAP_WRITE, // Mode d'accès en lecture/écriture
  39.                                         0, 0, // Offset de début de la vue sur 64 bits
  40.                                         0)); // Taille de la vue (0 = tout)
  41.                                         break;
  42.           case DLL_PROCESS_DETACH : // au détachement de la DLL
  43.                // Destruction de la vue sur la zone de mémoire partagée
  44.                UnmapViewOfFile((LPVOID)VueDonnees);
  45.                // Détachement de la zone de mémoire partagée
  46.                CloseHandle(MemPartagee);
  47.                break;
  48.           default :
  49.                // DLL_THREAD_ATTACH, DLL_THREAD_DETACH
  50.                break;
  51.      }
  52.      return 1;
  53. }
  54. void _export InitHook(HWND hDest) // _export est spécifique à BCB  
  55. {
  56.      // Installation du hook sur la souris
  57.      VueDonnees->MouseHookHandle = SetWindowsHookEx(WH_MOUSE, // Créer un hook sur la souris
  58.                                              (HOOKPROC)MouseProc, // Utiliser la fonction MouseProc
  59.                                              HInst, // Dans la DLL d'instance HInst
  60.                                              0); // Pour tous les threads
  61.      // Installation du hook pour le clavier
  62.      VueDonnees->KeybdHookHandle = SetWindowsHookEx(WH_KEYBOARD, // Créer un hook sur le clavier
  63.                                              (HOOKPROC)KeybdProc, // Utiliser la fonction KeybdProc
  64.                                              HInst, // Dans la DLL d'instance HInst
  65.                                              0); // Pour tous les threads
  66.      // Partage de la fenêtre destinatrice des données du clavier
  67.      VueDonnees->hDestWindow = hDest;
  68. }
  69. void _export EndHook()
  70. {
  71.      // Supression des hooks
  72.      UnhookWindowsHookEx(VueDonnees->MouseHookHandle);
  73.      UnhookWindowsHookEx(VueDonnees->KeybdHookHandle);
  74. }
  75. #define WMAP_MOUSEMOVE WM_APP + 1
  76. LRESULT CALLBACK _export MouseProc(int nCode,WPARAM wParam,LPARAM lParam)
  77. {
  78.      // On envoie un message WMAP_MOUSEMOVE à chaque fois que
  79.  // l'utilisateur déplace la souris
  80.      if (wParam == WM_MOUSEMOVE)
  81.   PostMessage(VueDonnees->hDestWindow, WMAP_MOUSEMOVE, 0, 0);
  82.  return CallNextHookEx(VueDonnees->MouseHookHandle,nCode,wParam,lParam);
  83. }
  84. #define WMAP_KEYBOARDPRESS WM_APP + 2
  85. LRESULT CALLBACK _export KeybdProc(int nCode,WPARAM wParam,LPARAM lParam)
  86. {
  87.      // On envoie un message WMAP_KEYBOARDPRESS à chaque fois que
  88.  // l'utilisateur presse la touche CONTROL
  89.      if (wParam == VK_CONTROL)
  90.           PostMessage(VueDonnees->hDestWindow, WMAP_KEYBOARDPRESS, 0, 0);
  91.      return CallNextHookEx(VueDonnees->KeybdHookHandle,nCode,wParam,lParam);
  92. }


 
 
 
La ptite appli qui utilise la DLL
 

Code :
  1. #include <vcl.h>
  2. #pragma hdrstop
  3. #include "testHook.h"
  4. //---------------------------------------------------------------------------
  5. #pragma package(smart_init)
  6. #pragma resource "*.dfm"
  7. TForm1 *Form1;
  8. //---------------------------------------------------------------------------
  9. __fastcall TForm1::TForm1(TComponent* Owner)
  10.           : TForm(Owner)
  11. {
  12.      bHook = false; // Les hooks ne sont pas initialisés
  13.      hinstDLL = LoadLibrary("hooksClSo.dll" ); // Chargement de la librairie hinstDLL = 1 a ce moment et je crois que c'est pas cool
  14.      if (!hinstDLL) // Erreur lors du chargement de la librairie ?
  15.           Application->MessageBox("Impossible de charger la librairie.","gloups",MB_OK);
  16.      else
  17.  {
  18.           // On récupère les adresses des fonctions
  19.           InitHooks = (TInitFunc)GetProcAddress(hinstDLL, "_InitHook" );
  20.           EndHooks = (TEndFunc)GetProcAddress(hinstDLL, "_EndHook" );
  21.           bHook = true;
  22.           InitHooks(Application->Handle); // On initialise les hooks
  23.      }
  24. }
  25. void __fastcall TForm1::FormClose(TObject *Sender, TCloseAction &Action)
  26. {
  27.      if (bHook) // Si les hooks sont actifs, on les supprime avant de quitter
  28.           EndHooks();
  29.      Action = caFree;
  30. }
  31. void __fastcall TForm1::DeplSouris(TWMNoParams &p)
  32. {
  33. TPoint pt ;
  34.      GetCursorPos ( & pt) ;
  35.      EditX->Text = IntToStr(pt.x);
  36. EditY->Text = IntToStr(pt.y);
  37. }
  38. void __fastcall TForm1::PressionControl(TWMNoParams &p)
  39. {
  40. chkCtrl->Checked = true;
  41. }
  42. void __fastcall TForm1::CheckBox1Click(TObject *Sender)
  43. {
  44. if (!hinstDLL) // La librairie n'est pas chargée, inutile de continuer
  45.           Close();
  46.      else if (CheckBox1->Checked) // Activer les hooks
  47.      {
  48.           InitHooks(Application->Handle); // On initialise les hooks
  49.      }
  50.      else // Désactiver les hooks
  51.           EndHooks(); // On supprime les hooks
  52. }


 
 
voila le topo je sais pas pourquoi hinst = 1, enfin je suis vraiment pas fort en prog alors c'est ptet normal mais ca m etonnerait. De toute facon le EAccessViolation est un mystere ensuite !


Message édité par Masure le 10-01-2003 à 21:13:54
Reply

Marsh Posté le 10-01-2003 à 21:12:04   

Reply

Marsh Posté le 10-01-2003 à 23:50:39    

:bounce:

Reply

Marsh Posté le 11-01-2003 à 00:27:50    

rien à voir: c'est quoi un handle?

Reply

Marsh Posté le 11-01-2003 à 00:45:11    

masure a dit a écrit :

Et comme handle je me tape 1 en retour...



 
Il est sûr que 1 n'est sûrement pas une valeur valide pour le handle de la dll (enfin, il est censé être valide mais c'est tout de même une valeur hautement improbable).
 

masure a dit a écrit :

... et apres lors de l execution de l appli qui load la dll "EAccessViolation" comme par hazard.



 
Ca se produit quand cette erreur ? Lors du chargement des fonctions (GetProcAddress) ou lors de l'utilisation de ces fonctions ?
 
Une chose que tu peux peut être essayer est de ne rien faire dans ton DllEntryPoint (en fournissant une fonction Init et Cleanup par exemple). En effet, le platform SDK indique sur cette page que des erreurs de violations d'accès peuvent se produire dans le cas d'appel à certaines fonctions.


---------------
each day I don't die is cheating
Reply

Marsh Posté le 11-01-2003 à 12:15:47    

Merci pour tes conseils, mais j'avoue que des deux qui travaillons la-dessus je ne suis pas le plus doué :(. J'essaye de bricoloer mais j'avoue que c'est sans succes.
 
Pour les âmes charitables, je met à disposition les projets c++ builder correspondant :
 
http://aragorn.dunadan.free.fr/hardware/testHook.zip
 
http://aragorn.dunadan.free.fr/hardware/hooksClSo.zip
 
Je sais que c'est abusé mais je suis pas vraiment fort pour la prog windows. Merci

Reply

Marsh Posté le 11-01-2003 à 12:20:17    

gatorette a écrit :


 
Il est sûr que 1 n'est sûrement pas une valeur valide pour le handle de la dll (enfin, il est censé être valide mais c'est tout de même une valeur hautement improbable).
 
 
 
Ca se produit quand cette erreur ? Lors du chargement des fonctions (GetProcAddress) ou lors de l'utilisation de ces fonctions ?
 
Une chose que tu peux peut être essayer est de ne rien faire dans ton DllEntryPoint (en fournissant une fonction Init et Cleanup par exemple). En effet, le platform SDK indique sur cette page que des erreurs de violations d'accès peuvent se produire dans le cas d'appel à certaines fonctions.


 
Je suis pas sur paske la j'ai pas pu installé C++ Builder encore, on etait chez mon collègue mais il me semble bie nque c'etait sur le getProcAdress en effet !

Reply

Marsh Posté le 11-01-2003 à 12:25:14    

masure a écrit :

Merci pour tes conseils, mais j'avoue que des deux qui travaillons la-dessus je ne suis pas le plus doué :(. J'essaye de bricoloer mais j'avoue que c'est sans succes.
 
Pour les âmes charitables, je met à disposition les projets c++ builder correspondant :
 
http://aragorn.dunadan.free.fr/hardware/testHook.zip
 
http://aragorn.dunadan.free.fr/hardware/hooksClSo.zip
 
Je sais que c'est abusé mais je suis pas vraiment fort pour la prog windows. Merci  


 
bon je peux pas tester ton prog ici, mais déjà y a un truc qui me gene c'est ta variable hinstDLL. LoadLibrary retourne un HMODULE et non pas un HINSTANCE.

Reply

Marsh Posté le 11-01-2003 à 12:28:10    

"The HINSTANCE of a DLL is the same as the HMODULE of the DLL, so hinstDLL can be used in calls to functions that require a module handle."
 
Ca vient de la MSDN donc je pense que ya pas de probleme


Message édité par Masure le 11-01-2003 à 13:01:06
Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed