Accueil > > > SOUS-CLASSEMENT DE FENÊTRE D'UN AUTRE PROCESS PAR INJECTION DLL
SOUS-CLASSEMENT DE FENÊTRE D'UN AUTRE PROCESS PAR INJECTION DLL
Information sur la source
Description
Voici un code source montrant comment sous-classer une fenêtre appartenant à un autre process. La technique de l'injection de code par dll est utilisée. Le but de ce sous-classement est de pouvoir intercepter les messages destinés à n'importe quelle fenêtre cible afin de les traiter de manière personnalisée. L'injecteur est sous forme de boite de dialogue disposant d'un combobox qui contiendra les noms de toutes les fenêtres visibles à l'écran. Le bouton "Injecter" permet d'injecter et exécuter le code de notre dll dans le process de la fenêtre choisie. Le HWND de cette dernière est transmis via le presse-papier au DllMain de notre dll en utilisant un format privé. Un bouton "Actualiser" permet de rafraichir le contenu du combobox. La dll contient deux fonctions: Le DllMain et notre procédure de sous-classement. Dans le DllMain, l'adresse de la procédure originale de la fenêtre à sous-classer est sauvegardée dans une propriété assignée pour l'occasion à cette fenêtre grâce à SetProp(). GetProp() permet de retrouver cette adresse originale dans la procédure de sous-classement afin d'y aiguiller les messages qu'on ne désire pas traiter. Ainsi, chaque fenêtre retrouve sa propre procédure originale si le message qui lui parvient n'est pas capturé par notre procédure de sous-classement. Dans cet exemple, le message WM_SYSCOMMAND dont wParam vaut SC_CLOSE est intercepté pour afficher un petit message prouvant que le sous-classement est effectif chaque fois qu'on décide de fermer la fenêtre sous-classée. Libre à vous de modifier le code pour traiter les messages que vous voulez. Ce code source se compose de deux projets: celui de l'injecteur et celui de la dll. Cette dernière est incluse en ressource binaire de l'exécutable injecteur qui l'extrait dans son dossier s'il ne la trouve pas. Les deux petits projets ont été faits sous Visual C/C++ 2005 et sont facilement adaptables. Celui de la dll est en pur C. Il est à noter que par souci de clarté du code source, généralement les valeurs de retour des fonctions ne sont pas traitées. Pour tester l'injecteur, renommez-le en Injecteur.exe. Des tests ont été faits sans aucun problème sur Windows XP, Vista et 7. Voilà, j'espère n'avoir rien oublié. Toutes les remarques, questions et commentaires sont les bienvenus.
Source
- //********************** Code de l'injecteur **********************
- #include <windows.h>
-
- DWORD Inject(HWND hwndclipboard, HWND hwndcible)
- {
- char dllpath[MAX_PATH];
- // Obtenir le chemin complet de notre exécutable:
- GetModuleFileName(0,dllpath,MAX_PATH);
- // Remplacer le nom de l'exécutable par le nom de la dll:
- lstrcpy(strrchr(dllpath,'\\')+1,"wndprocdll.dll");
- // Vérifier l'existence de la dll dans le dossier de l'exe:
- DWORD attrib=GetFileAttributes(dllpath);
- // Extraire la dll depuis les ressouces de l'exe si elle n'existe pas:
- if(attrib==INVALID_FILE_ATTRIBUTES)
- {
- // Trouver la ressource:
- HRSRC hbinresource=FindResource(0,"IDB_DLL","BINARY");
- // Déterminer sa taille:
- DWORD dwtaille=SizeofResource(0,hbinresource);
- // Charger la ressource en mémoire:
- HGLOBAL hResource=LoadResource(0,hbinresource);
- // Obtenir un pointeur sur cette zone mémoire:
- char* pbuf=(char*)LockResource(hResource);
- // Créer le fichier destination:
- HANDLE hFichier=CreateFile(dllpath,GENERIC_WRITE,0,0,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,0);
- // S'assurer que le fichier a bien été créé:
- if(hFichier!=INVALID_HANDLE_VALUE)
- {
- // Copier la ressource dans le fichier:
- DWORD dwecrits;
- WriteFile(hFichier,pbuf,dwtaille,&dwecrits,0);
- // Fermer le fichier:
- CloseHandle(hFichier);
- }
- // Libérer la ressource:
- UnlockResource(hResource);
- FreeResource (hResource);
- }
- // Obtenir l'identificateur du process auquel appartient la fenêtre:
- DWORD dwpid;
- DWORD threadid=GetWindowThreadProcessId(hwndcible,&dwpid);
- // Ouvrir ce process:
- HANDLE hProcess=OpenProcess( PROCESS_ALL_ACCESS, 0,dwpid);
- // Obtenir la longueur du chemin complet de notre dll:
- DWORD dwpathlen=lstrlen(dllpath);
- // Allouer de la mémoire dans ce process pour y stocker le chemin de notre dll:
- char* pmem=(char*)VirtualAllocEx(hProcess,0,dwpathlen+1,MEM_COMMIT,PAGE_READWRITE);
- // Copier le chemin de notre dll vers la mémoire allouée dans le process cible:
- BOOL bret=WriteProcessMemory(hProcess,(LPVOID) pmem,(LPVOID) dllpath, dwpathlen+1, NULL);
- // Obtenir le HMODULE de kernel32.dll:
- HMODULE hkernel32=GetModuleHandle("Kernel32");
- // Obtenir l'adresse de la fonction LoadLibraryA de kernel32.dll:
- PTHREAD_START_ROUTINE pfnThreadRtn=(PTHREAD_START_ROUTINE)GetProcAddress(hkernel32, "LoadLibraryA");
- // Ouvrir le presse-papier:
- OpenClipboard(hwndclipboard);
- // Mettre le HWND de la fenêtre cible dans le presse-papier:
- SetClipboardData(CF_PRIVATEFIRST ,hwndcible);// Format privé
- // Fermer le presse-papier:
- CloseClipboard();
- // Créer et lancer un thread distant dans le process cible:
- HANDLE hThread= CreateRemoteThread(hProcess, NULL, 0,pfnThreadRtn, pmem, 0, NULL);
- // Attendre que le thread soit terminé:
- WaitForSingleObject(hThread, INFINITE);
- // Libérer la mémoire allouée précédemment:
- VirtualFreeEx(hProcess, pmem, 0, MEM_RELEASE);
- // Fermer les handles:
- CloseHandle(hThread);
- CloseHandle(hProcess);
- return 0;
- }
-
- // Procédure d'énumération des fenêtres et de remplissage du combobox:
- BOOL CALLBACK EnumWindowsProc(HWND hwnd,LPARAM lParam)
- {
- static char buffer[MAX_PATH];
- // S'assurer que la fenêtre est visible:
- if(IsWindowVisible(hwnd))
- {
- // Récupérer le HWND de notre combobox depuis lParam:
- HWND hCombo=(HWND)lParam;
- // S'assurer que la fenêtre a un titre et qu'il ne s'agit pas de celle de notre injecteur:
- if(GetWindowTextLength(hwnd) && hwnd!=GetParent(hCombo))
- {
- // Obtenir le nom de la classe de fenêtre:
- GetClassName(hwnd,buffer,MAX_PATH);
- // S'assurer que le nom de classe est différent de "progman":
- if(lstrcmpi(buffer,"progman"))
- {
- // Obtenir le texte du titre de la fenêtre:
- GetWindowText(hwnd,buffer,MAX_PATH);
- // Ajouter ce texte comme élément au combobox:
- SendMessage(hCombo,CB_INSERTSTRING,0,(LPARAM)buffer);
- // Mettre le HWND de la fenêtre comme valeur associée à l'élément:
- SendMessage(hCombo,CB_SETITEMDATA,0,(LPARAM)hwnd);
- }
- }
- }
- return TRUE;
- }
-
- // Procédure de notre boite de dialogue:
- BOOL CALLBACK DlgProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
- {
- static HWND hCombo,hFermer,hInjecter,hActualiser;
- switch(message)
- {
-
- case WM_INITDIALOG:
- {
- // Définir le titre de notre boite de dialogue:
- SetWindowText(hwnd,"Injecteur");
- // Créer les contrôles:
- CreateWindowEx(0,"static","Liste des fenêtres :",WS_CHILD | WS_VISIBLE,20,10,360,20,hwnd,0,0,0);
- hCombo=CreateWindowEx(0,"combobox",0,WS_CHILD | WS_VISIBLE | CBS_DROPDOWNLIST | WS_VSCROLL,20,28,360,150,hwnd,0,0,0);
- hActualiser=CreateWindowEx(0,"button","Actualiser",WS_CHILD | WS_VISIBLE ,20,170,80,20,hwnd,0,0,0);
- hInjecter=CreateWindowEx(0,"button","Injecter",WS_CHILD | WS_VISIBLE | WS_DISABLED ,160,170,80,20,hwnd,0,0,0);
- hFermer=CreateWindowEx(0,"button","Fermer",WS_CHILD | WS_VISIBLE ,300,170,80,20,hwnd,0,0,0);
- // Enumérer les fenêtres en remplissant le combobox:
- EnumWindows(EnumWindowsProc,(LPARAM)hCombo);
- // Obtenir la police par défaut des boites de dialogue:
- HFONT hguifont=(HFONT)GetStockObject(DEFAULT_GUI_FONT);
- // Appliquer cette police à nos contrôles:
- HWND child=0;
- while(child=FindWindowEx(hwnd,child,0,0))SendMessage(child,WM_SETFONT,(WPARAM)hguifont,0);
- }
- break;
-
- case WM_COMMAND:
- // Dégriser le bouton "Injecter" si un élément du combobox a été sélectionné:
- if(HIWORD(wParam)==CBN_SELENDOK) EnableWindow(hInjecter,1);
- // Clic sur "Injecter":
- if((HWND)lParam==hInjecter)
- {
- // Obtenir l'index de la séléction courante du combobox:
- int cursel=(int)SendMessage(hCombo,CB_GETCURSEL,0,0);
- // Récupérer le HWND associé comme valeur à l'élément sélectionné:
- HWND hwndcible=(HWND)SendMessage(hCombo,CB_GETITEMDATA,cursel,0);
- // S'assurer que la fenêtre n'a pas déjà été sous-classée:
- if(GetProp(hwndcible,"PROP_WNDPROC"))
- {
- MessageBox(hwnd,"La fenêtre choisie a déjà été sous-classée.","Injecteur",0);
- return 0;
- }
- // Lancer la fonction d'injection si la fenêtre est valide:
- if(IsWindow(hwndcible))Inject(hwnd,hwndcible);
- // Sinon afficher un message indiquant que le HWND n'est pas valide:
- else MessageBox(hwnd,"Le HWND de la fenêtre choisie n'est plus valide.","Injecteur",0);
- return 0;
- }
- // Clic sur "Actualier":
- if((HWND)lParam==hActualiser)
- {
- // Vider le combobox:
- SendMessage(hCombo,CB_RESETCONTENT,0,0);
- // Griser le bouton "Injecter":
- EnableWindow(hInjecter,0);
- // Enumérer les fenêtres en remplissant le combobox:
- EnumWindows(EnumWindowsProc,(LPARAM)hCombo);
- return 0;
- }
- // Fermer la boite de dialogue si clic sur "Fermer":
- if((HWND)lParam==hFermer)SendMessage(hwnd,WM_CLOSE,0,0);
- break;
-
- case WM_CLOSE:
- // Détruire la boite de dialogue:
- EndDialog(hwnd,0);
- break;
- default:
- break;
- }
- return 0;
- }
- int APIENTRY WinMain (HINSTANCE hinst, HINSTANCE hprev, LPSTR szcmd, int ishow)
- {
- // Allouer de la mémoire pour notre DIALOG TEMPLATE:
- LPDLGTEMPLATE lpdt=(LPDLGTEMPLATE)GlobalAlloc(GPTR,512);
- // Définir les dimensions de notre boite dedialogue:
- lpdt->cx=200; lpdt->cy=100;
- // Définir les styles de notre boite de dialogue:
- lpdt->style=DS_CENTER | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX;
- // Lancer notre boite de dialogue:
- DialogBoxIndirectParam(GetModuleHandle(0),lpdt,0,(DLGPROC)DlgProc,0);
- // Libérer la mémoire allouée pour notre DIALOG TEMPLATE:
- GlobalFree(lpdt);
- return 0;
- }
- //***********************************************************************
-
-
- //*********************** Code de la DLL ********************************
- #include <windows.h>
-
- // Notre procédure de sous-classement:
- LRESULT CALLBACK MyWndProc(HWND hwnd,UINT message, WPARAM wParam, LPARAM lParam)
- {
- WNDPROC OldWndProc;
- // Récupérer l'adresse de la procédure originale depuis la propriété "PROP_WNDPROC" assignée à la fenêtre:
- OldWndProc=(WNDPROC)GetProp(hwnd,"PROP_WNDPROC");
- switch(message)
- {
- case WM_SYSCOMMAND:
- if(wParam==SC_CLOSE)
- {
- // Afficher le message prouvant le sous-classement de la fenêtre:
- MessageBox(hwnd,"Ce message prouve que la fenêtre a bien été sous-classée.","Sous-Classement par injection de code.",0);
- }
- break;
- case WM_NCDESTROY:
- // Retirer la propriété "PROP_WNDPROC" préalablement assignée à la fenêtre sous-classée:
- RemoveProp(hwnd,"PROP_WNDPROC");
- break;
- default:
- break;
- }
- // Appeler la procédure originale:
- return CallWindowProc(OldWndProc,hwnd,message,wParam, lParam);
- }
-
- // La fonction d'entrée DllMain:
- int APIENTRY DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
- {
- if (dwReason == DLL_PROCESS_ATTACH)
- {
- HWND hwnd;
- // Ouvrir le presse-papier:
- OpenClipboard(0);
- // récupérer le HWND de la fenêtre cible transmis par le programme injetceur:
- hwnd=(HWND)GetClipboardData(CF_PRIVATEFIRST);
- // Fermer le presse-papier:
- CloseClipboard();
- // S'assurer que le HWND est valide et que la propriété "PROP_WNDPROC" ne lui est pas assignée:
- if(IsWindow(hwnd) && !GetProp(hwnd,"PROP_WNDPROC"))
- {
- WNDPROC OldWndProc;
- // Récupérer l'adresse de la procédure originale de la fenêtre cible:
- OldWndProc=(WNDPROC)GetWindowLong(hwnd,GWL_WNDPROC);
- //Sauvegarder cette adresse dans la propriété "PROP_WNDPROC" à assigner à la fenêtre:
- SetProp(hwnd,"PROP_WNDPROC",(HANDLE)OldWndProc);
- // Remplacer la procédure originale par la notre:
- SetWindowLong(hwnd, GWLP_WNDPROC, (LONG)MyWndProc);
- }
- }
- return 1;
- }
- //**********************************************************************
//********************** Code de l'injecteur **********************
#include <windows.h>
DWORD Inject(HWND hwndclipboard, HWND hwndcible)
{
char dllpath[MAX_PATH];
// Obtenir le chemin complet de notre exécutable:
GetModuleFileName(0,dllpath,MAX_PATH);
// Remplacer le nom de l'exécutable par le nom de la dll:
lstrcpy(strrchr(dllpath,'\\')+1,"wndprocdll.dll");
// Vérifier l'existence de la dll dans le dossier de l'exe:
DWORD attrib=GetFileAttributes(dllpath);
// Extraire la dll depuis les ressouces de l'exe si elle n'existe pas:
if(attrib==INVALID_FILE_ATTRIBUTES)
{
// Trouver la ressource:
HRSRC hbinresource=FindResource(0,"IDB_DLL","BINARY");
// Déterminer sa taille:
DWORD dwtaille=SizeofResource(0,hbinresource);
// Charger la ressource en mémoire:
HGLOBAL hResource=LoadResource(0,hbinresource);
// Obtenir un pointeur sur cette zone mémoire:
char* pbuf=(char*)LockResource(hResource);
// Créer le fichier destination:
HANDLE hFichier=CreateFile(dllpath,GENERIC_WRITE,0,0,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,0);
// S'assurer que le fichier a bien été créé:
if(hFichier!=INVALID_HANDLE_VALUE)
{
// Copier la ressource dans le fichier:
DWORD dwecrits;
WriteFile(hFichier,pbuf,dwtaille,&dwecrits,0);
// Fermer le fichier:
CloseHandle(hFichier);
}
// Libérer la ressource:
UnlockResource(hResource);
FreeResource (hResource);
}
// Obtenir l'identificateur du process auquel appartient la fenêtre:
DWORD dwpid;
DWORD threadid=GetWindowThreadProcessId(hwndcible,&dwpid);
// Ouvrir ce process:
HANDLE hProcess=OpenProcess( PROCESS_ALL_ACCESS, 0,dwpid);
// Obtenir la longueur du chemin complet de notre dll:
DWORD dwpathlen=lstrlen(dllpath);
// Allouer de la mémoire dans ce process pour y stocker le chemin de notre dll:
char* pmem=(char*)VirtualAllocEx(hProcess,0,dwpathlen+1,MEM_COMMIT,PAGE_READWRITE);
// Copier le chemin de notre dll vers la mémoire allouée dans le process cible:
BOOL bret=WriteProcessMemory(hProcess,(LPVOID) pmem,(LPVOID) dllpath, dwpathlen+1, NULL);
// Obtenir le HMODULE de kernel32.dll:
HMODULE hkernel32=GetModuleHandle("Kernel32");
// Obtenir l'adresse de la fonction LoadLibraryA de kernel32.dll:
PTHREAD_START_ROUTINE pfnThreadRtn=(PTHREAD_START_ROUTINE)GetProcAddress(hkernel32, "LoadLibraryA");
// Ouvrir le presse-papier:
OpenClipboard(hwndclipboard);
// Mettre le HWND de la fenêtre cible dans le presse-papier:
SetClipboardData(CF_PRIVATEFIRST ,hwndcible);// Format privé
// Fermer le presse-papier:
CloseClipboard();
// Créer et lancer un thread distant dans le process cible:
HANDLE hThread= CreateRemoteThread(hProcess, NULL, 0,pfnThreadRtn, pmem, 0, NULL);
// Attendre que le thread soit terminé:
WaitForSingleObject(hThread, INFINITE);
// Libérer la mémoire allouée précédemment:
VirtualFreeEx(hProcess, pmem, 0, MEM_RELEASE);
// Fermer les handles:
CloseHandle(hThread);
CloseHandle(hProcess);
return 0;
}
// Procédure d'énumération des fenêtres et de remplissage du combobox:
BOOL CALLBACK EnumWindowsProc(HWND hwnd,LPARAM lParam)
{
static char buffer[MAX_PATH];
// S'assurer que la fenêtre est visible:
if(IsWindowVisible(hwnd))
{
// Récupérer le HWND de notre combobox depuis lParam:
HWND hCombo=(HWND)lParam;
// S'assurer que la fenêtre a un titre et qu'il ne s'agit pas de celle de notre injecteur:
if(GetWindowTextLength(hwnd) && hwnd!=GetParent(hCombo))
{
// Obtenir le nom de la classe de fenêtre:
GetClassName(hwnd,buffer,MAX_PATH);
// S'assurer que le nom de classe est différent de "progman":
if(lstrcmpi(buffer,"progman"))
{
// Obtenir le texte du titre de la fenêtre:
GetWindowText(hwnd,buffer,MAX_PATH);
// Ajouter ce texte comme élément au combobox:
SendMessage(hCombo,CB_INSERTSTRING,0,(LPARAM)buffer);
// Mettre le HWND de la fenêtre comme valeur associée à l'élément:
SendMessage(hCombo,CB_SETITEMDATA,0,(LPARAM)hwnd);
}
}
}
return TRUE;
}
// Procédure de notre boite de dialogue:
BOOL CALLBACK DlgProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
static HWND hCombo,hFermer,hInjecter,hActualiser;
switch(message)
{
case WM_INITDIALOG:
{
// Définir le titre de notre boite de dialogue:
SetWindowText(hwnd,"Injecteur");
// Créer les contrôles:
CreateWindowEx(0,"static","Liste des fenêtres :",WS_CHILD | WS_VISIBLE,20,10,360,20,hwnd,0,0,0);
hCombo=CreateWindowEx(0,"combobox",0,WS_CHILD | WS_VISIBLE | CBS_DROPDOWNLIST | WS_VSCROLL,20,28,360,150,hwnd,0,0,0);
hActualiser=CreateWindowEx(0,"button","Actualiser",WS_CHILD | WS_VISIBLE ,20,170,80,20,hwnd,0,0,0);
hInjecter=CreateWindowEx(0,"button","Injecter",WS_CHILD | WS_VISIBLE | WS_DISABLED ,160,170,80,20,hwnd,0,0,0);
hFermer=CreateWindowEx(0,"button","Fermer",WS_CHILD | WS_VISIBLE ,300,170,80,20,hwnd,0,0,0);
// Enumérer les fenêtres en remplissant le combobox:
EnumWindows(EnumWindowsProc,(LPARAM)hCombo);
// Obtenir la police par défaut des boites de dialogue:
HFONT hguifont=(HFONT)GetStockObject(DEFAULT_GUI_FONT);
// Appliquer cette police à nos contrôles:
HWND child=0;
while(child=FindWindowEx(hwnd,child,0,0))SendMessage(child,WM_SETFONT,(WPARAM)hguifont,0);
}
break;
case WM_COMMAND:
// Dégriser le bouton "Injecter" si un élément du combobox a été sélectionné:
if(HIWORD(wParam)==CBN_SELENDOK) EnableWindow(hInjecter,1);
// Clic sur "Injecter":
if((HWND)lParam==hInjecter)
{
// Obtenir l'index de la séléction courante du combobox:
int cursel=(int)SendMessage(hCombo,CB_GETCURSEL,0,0);
// Récupérer le HWND associé comme valeur à l'élément sélectionné:
HWND hwndcible=(HWND)SendMessage(hCombo,CB_GETITEMDATA,cursel,0);
// S'assurer que la fenêtre n'a pas déjà été sous-classée:
if(GetProp(hwndcible,"PROP_WNDPROC"))
{
MessageBox(hwnd,"La fenêtre choisie a déjà été sous-classée.","Injecteur",0);
return 0;
}
// Lancer la fonction d'injection si la fenêtre est valide:
if(IsWindow(hwndcible))Inject(hwnd,hwndcible);
// Sinon afficher un message indiquant que le HWND n'est pas valide:
else MessageBox(hwnd,"Le HWND de la fenêtre choisie n'est plus valide.","Injecteur",0);
return 0;
}
// Clic sur "Actualier":
if((HWND)lParam==hActualiser)
{
// Vider le combobox:
SendMessage(hCombo,CB_RESETCONTENT,0,0);
// Griser le bouton "Injecter":
EnableWindow(hInjecter,0);
// Enumérer les fenêtres en remplissant le combobox:
EnumWindows(EnumWindowsProc,(LPARAM)hCombo);
return 0;
}
// Fermer la boite de dialogue si clic sur "Fermer":
if((HWND)lParam==hFermer)SendMessage(hwnd,WM_CLOSE,0,0);
break;
case WM_CLOSE:
// Détruire la boite de dialogue:
EndDialog(hwnd,0);
break;
default:
break;
}
return 0;
}
int APIENTRY WinMain (HINSTANCE hinst, HINSTANCE hprev, LPSTR szcmd, int ishow)
{
// Allouer de la mémoire pour notre DIALOG TEMPLATE:
LPDLGTEMPLATE lpdt=(LPDLGTEMPLATE)GlobalAlloc(GPTR,512);
// Définir les dimensions de notre boite dedialogue:
lpdt->cx=200; lpdt->cy=100;
// Définir les styles de notre boite de dialogue:
lpdt->style=DS_CENTER | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX;
// Lancer notre boite de dialogue:
DialogBoxIndirectParam(GetModuleHandle(0),lpdt,0,(DLGPROC)DlgProc,0);
// Libérer la mémoire allouée pour notre DIALOG TEMPLATE:
GlobalFree(lpdt);
return 0;
}
//***********************************************************************
//*********************** Code de la DLL ********************************
#include <windows.h>
// Notre procédure de sous-classement:
LRESULT CALLBACK MyWndProc(HWND hwnd,UINT message, WPARAM wParam, LPARAM lParam)
{
WNDPROC OldWndProc;
// Récupérer l'adresse de la procédure originale depuis la propriété "PROP_WNDPROC" assignée à la fenêtre:
OldWndProc=(WNDPROC)GetProp(hwnd,"PROP_WNDPROC");
switch(message)
{
case WM_SYSCOMMAND:
if(wParam==SC_CLOSE)
{
// Afficher le message prouvant le sous-classement de la fenêtre:
MessageBox(hwnd,"Ce message prouve que la fenêtre a bien été sous-classée.","Sous-Classement par injection de code.",0);
}
break;
case WM_NCDESTROY:
// Retirer la propriété "PROP_WNDPROC" préalablement assignée à la fenêtre sous-classée:
RemoveProp(hwnd,"PROP_WNDPROC");
break;
default:
break;
}
// Appeler la procédure originale:
return CallWindowProc(OldWndProc,hwnd,message,wParam, lParam);
}
// La fonction d'entrée DllMain:
int APIENTRY DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
{
if (dwReason == DLL_PROCESS_ATTACH)
{
HWND hwnd;
// Ouvrir le presse-papier:
OpenClipboard(0);
// récupérer le HWND de la fenêtre cible transmis par le programme injetceur:
hwnd=(HWND)GetClipboardData(CF_PRIVATEFIRST);
// Fermer le presse-papier:
CloseClipboard();
// S'assurer que le HWND est valide et que la propriété "PROP_WNDPROC" ne lui est pas assignée:
if(IsWindow(hwnd) && !GetProp(hwnd,"PROP_WNDPROC"))
{
WNDPROC OldWndProc;
// Récupérer l'adresse de la procédure originale de la fenêtre cible:
OldWndProc=(WNDPROC)GetWindowLong(hwnd,GWL_WNDPROC);
//Sauvegarder cette adresse dans la propriété "PROP_WNDPROC" à assigner à la fenêtre:
SetProp(hwnd,"PROP_WNDPROC",(HANDLE)OldWndProc);
// Remplacer la procédure originale par la notre:
SetWindowLong(hwnd, GWLP_WNDPROC, (LONG)MyWndProc);
}
}
return 1;
}
//**********************************************************************
Conclusion
Téléchargez le zip pour voir les deux projets.
Fichier Zip
Sources du même auteur
Sources de la même categorie
Commentaires et avis
Discussions en rapport avec ce code source dans le forum
Mettre une fenêtre graphique dans une dll [ par Arnaud ]
Comment mettre une fenêtre graphique dans une dll (plus précisément dans la dll pour visual basic)MerciDjsteyhttp://www.codejeuxvideo.com
SendMessage vers une fenêtre minimisée [ par Keenes ]
Bonjour,Le sujet du message n'étant pas très explicite, voici de quoi il s'agit :Je cherche à réaliser une logiciel de capture d'écran, comme il en ex
tutos injection de DLL ? [ par XenonGP ]
Bonjour tout le monde, j'aimerais avoir quelques liens vers des tutos sur l'injection de DLL(en anglais ou en français). Ce qui m'intéresse,
Injection dll et systray ? [ par mayti ]
Hello, Voilà j'injecte une dll dans un exe et je voudrais afficher une bulle dans le systray (balloon tip) mais en utilisant l'icon de cet exe.
Dialog dans DLL ? [ par Zootella ]
Hello all J'esseye d'utiliser dans mon programme une fenêtre dialog qui se trouve dans une dll, mais la fonction qui traite les message de la fe
detection d'un messageBox et fermeture automatique [ par elroulianito ]
J'aimerai utiliser une fonction issue d'une dll. Le problème est qu'à l'execution de celle-ci une fenêtre de type messagebox apparait m
Injection de Richter ? [ par albert0 ]
Bonjour, Voila, j'ai lut le chapitre 22 du bouc. de Richter, qui parle des Injections (methode avec CreateRemoteThread) Comme d'hab, j'aime bien tes
Injection et DirectX [ par wxccxw ]
Salut, voila j'ai une scene directX genre jeu, qui utilise des models.... et j'aimerai Injecter dedans un Dll qui change l'opaciter des models.quel st
[Aide]Anti DLL Injection and API Hooking [ par belette321 ]
Bon voilla je tente presentement de creer un DLL qui lors qu'il est inclue a un programme, block les tentative de "DLL Injection" et de "API Hook", Un
Problème injection DLL. [ par Latino888 ]
Bien le bonjour, je vous écrit aujourd'hui pour un problème d'injection DLL, en effet je shouterais tester la sécurité d'un de mes serveurs sur BF2, e
|
Derniers Blogs
IMAGINE CUP 2012, MAKE A SIGN EN FINALEIMAGINE CUP 2012, MAKE A SIGN EN FINALE par junarnoalg
Voilà qui est fait, la nouvelle est officielle ! L'équipe belge "Make a Sign" va au pays des kangourous défendre son projet dans la catégorie Software Design. http://www.imaginecup.com/CompetitionsContent/Competition/WorldwideFinalists.aspx V...
Cliquez pour lire la suite de l'article par junarnoalg KINECT 1.5 IS OUT !KINECT 1.5 IS OUT ! par Vko
La version 1.5 du Kinect For Microsoft vient tout juste de sortir ! Plein de nouveautés: Tracking de squelette en Near Mode Détection en position assise Détection faciale avec un SDK dédié Documentation et des guideline (enfin) Un out...
Cliquez pour lire la suite de l'article par Vko LES ACTUALITéS DE LA SEMAINE SUR C2I.FR (14 MAI - 20 MAI) LES ACTUALITéS DE LA SEMAINE SUR C2I.FR (14 MAI - 20 MAI) par richardc
Mise à jour des Web API du 14 Mai
Réservez dès maintenant votre journée du 20 juin pour le Windows Azure Dev Camp 2012 à Paris
Mise à jour de Team Foundation Service
MechCommander 2 sur Windows 8
Entity Framework 5 Release Candidate e...
Cliquez pour lire la suite de l'article par richardc REACTIVE EXTENSIONS : CONSOMMER DES SERVICES AVEC RX PARTIE 3, LES PIèGES à éVITERREACTIVE EXTENSIONS : CONSOMMER DES SERVICES AVEC RX PARTIE 3, LES PIèGES à éVITER par Groc
Une mauvaise utilisation de rx lors de l'écriture d'une couche d'accès à des services peut conduire à des cas embarassants avec des erreurs mal gérées, des appels qui ne partent lorsqu'ils le devraient, et même des résultats incorrects . le tout nuis...
Cliquez pour lire la suite de l'article par Groc SHAREPOINT BLOG SITE, PROBLèME D'ARCHIVESSHAREPOINT BLOG SITE, PROBLèME D'ARCHIVES par junarnoalg
Dernièrement, nous avons migré le site
myTIC
vers un nouveau serveur SharePoint 2010. Dans les contenus que nous vouloins récupérer, nous avions un certain nombre de blogs.
Nous avons utilisé les commandes Power...
Cliquez pour lire la suite de l'article par junarnoalg
Forum
RE : SAC A DOS RE : SAC A DOS par hadjkaddour
Cliquez pour lire la suite par hadjkaddour
Logiciels
sDEVIS-FACTURES vlPRO (8.1.0.3)SDEVIS-FACTURES VLPRO (8.1.0.3)sDEVIS-FACTURES vlPRO a été mis au point pour les particuliers, créateurs, entrepreneurs, artisa... Cliquez pour télécharger sDEVIS-FACTURES vlPRO 974 Application Server (12.2.4.6)974 APPLICATION SERVER (12.2.4.6)Développez de puissantes applications dans un environnement de 'cloud computing', clusterisé, séc... Cliquez pour télécharger 974 Application Server vPicture (1.4.2.1)VPICTURE (1.4.2.1)Avec vPicture, hébergez vos images facilement et rapidement.
vPicture est un utilitaire simple, ... Cliquez pour télécharger vPicture Easy-Planning (2.2.1.6)EASY-PLANNING (2.2.1.6)Easy-Planning permet de créer des plannings sous la représentation de diagrammes et est adapté au... Cliquez pour télécharger Easy-Planning COM-BACKUP (2.0)COM-BACKUP (2.0)
COM-BACKUP est un logiciel de sauvegarde qui permet de planifier les sauvegardes de vos dossiers ...
Cliquez pour télécharger COM-BACKUP
|