Accueil > > > SERVICE WINDOWS DANS UNE DLL LANCÉ PAR SVCHOST.EXE
SERVICE WINDOWS DANS UNE DLL LANCÉ PAR SVCHOST.EXE
Information sur la source
Description
Ce code source montre comment implémenter un service Windows dans une DLL afin qu'il soit exécuté par un processus hôte svchost.exe. Au démarrage de Windows, le système examine une clé de la base de registres pour grouper des services dans diférentes instances de svchost.exe. Notre service fera partie du groupe netsvcs. Ce dernier présente l'avantage de s'exécuter en LocalSystem. Notre DLL exporte trois fonctions : ServiceMain(), obligatoire, InstallService() et RemoveService(). Les deux dernières servent à installer/désinstaller le service grâce à l'utilisation de RunDll32 en ligne de commandes. A noter que l'invite de commandes doit être lancé en mode administrateur. On peut mettre le fichier RacppService.dll dans le dossier System32 puis, pour installer le service, taper la ligne suivante: rundll32 racppservice.dll InstallService Pour supprimer le service on tape: rundll32 racppservice.dll RemoveService Si on choisit un autre emplacement que System32, il faudra taper le chemin complet de la dll. L'installation ou la suppression de notre service nécessite un redémarrage de Windows. Tous les détails de l'installation et de la configuration de notre service figurent dans le code de la fonction InstallService(). Notre service utilise un timer pour écrire, toutes les minutes, dans un fichier log c:\racppservice.log, la date et l'heure du déclenchement du timer. Ceci est juste pour montrer le bon fonctionnement du service. Pour tous les détails, regarder le code source. Le code est réalisé en c sous Visual C/C++ 2005 mais il est facilement adaptable pour les autres outils. Pour préserver la clarté du code, la gestion des erreurs est minimale. Le service a tété testé sans aucun problème sous Windows XP, Vista et 7. La dll RacppService.dll est fournie dans le zip si vous vouler tester. Voilà, j'espère n'avoir rien oublié. Tous les commentaires ou remarques sont les bienvenus.
Source
- #define _WIN32_WINNT 0x0500 // Pour Windows 2000 et supérieur
- #include <windows.h>
-
- // Déclarations globales:
- HINSTANCE hDll;
- SERVICE_STATUS_HANDLE hServiceStatusHandle;
- SERVICE_STATUS ServiceStatus;
- HANDLE hEvent,hFile;
- char buff[MAX_PATH];
-
- // Fonction d'installation du service:
- int WINAPI InstallService()
- {
- HKEY hkService,hkSvchost;
- SC_HANDLE schScm ,schService;
- char* pData;
- DWORD dwError=0, dwLen,dwSize = 0;
- // Ouvrir le gestionnaire de services:
- schScm = OpenSCManager(0, 0, SC_MANAGER_ALL_ACCESS);
- if(schScm)
- {
- // Créer notre service:
- schService = CreateService(schScm, "RacppService", 0, SERVICE_ALL_ACCESS, SERVICE_WIN32_SHARE_PROCESS, SERVICE_AUTO_START, SERVICE_ERROR_NORMAL, "%SystemRoot%\\System32\\svchost.exe -k netsvcs", 0, 0, 0, 0, 0);
- if(schService)
- {
- // Ajouter une description à notre service:
- SERVICE_DESCRIPTION sd;
- sd.lpDescription = "Service dans une DLL lancé par svchost.exe";
- ChangeServiceConfig2(schService, SERVICE_CONFIG_DESCRIPTION, &sd);
- // Ajouter la sous-clé Parameters à la clé de notre service:
- RegCreateKeyEx(HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Services\\RacppService\\Parameters", 0, 0, REG_OPTION_NON_VOLATILE,KEY_ALL_ACCESS, 0, &hkService, 0);
- // Récupérer le chemin complet de notre Dll:
- GetModuleFileName(hDll, buff, sizeof(buff));
- // Affecter le chemin de la Dll à la sous-clé Parameters sous le nom ServiceDll:
- RegSetValueEx(hkService, "ServiceDll", 0, REG_EXPAND_SZ, (BYTE*)buff, lstrlen(buff)+1);
- // Fermer la clé de notre service:
- RegCloseKey(hkService);
- // Ouvrir la clé indiquant la liste des groupes d'instances de svchost.exe:
- RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Svchost", 0, KEY_ALL_ACCESS, &hkSvchost);
- // Obtenir la longueur du contenu du groupe netsvcs:
- RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, 0, &dwSize);
- // Fixer le nom de notre service pour la liste des services du groupe netsvcs:
- lstrcpy(buff,"RacppService");
- dwLen=lstrlen(buff);
- // Allouer la mémoire nécessaire pour la nouvelle liste des noms de services du groupe netsvcs:
- pData=HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,dwSize + dwLen + 1);
- if(pData)
- {
- char *pNames;
- // Récupérer la liste des noms de services du groupe netsvcs:
- RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, (BYTE*)pData, &dwSize);
- // Vérifier si le nom existe
- for (pNames = pData; *pNames; pNames=strchr(pNames,0)+1) if(!lstrcmpi(pNames, buff)) break;
- // L'ajouter s'il n'existe pas:
- if (*pNames == 0)
- {
- memcpy(pData + dwSize - 1, buff, dwLen + 1);
- RegSetValueEx(hkSvchost, "netsvcs", 0, REG_MULTI_SZ, (BYTE*)pData, dwSize + dwLen + 1);
- }
- else dwError=ERROR_ALREADY_EXISTS;
- // Libérer la mémoire allouée:
- HeapFree(GetProcessHeap(),0,pData);
- }
- else dwError=ERROR_NOT_ENOUGH_MEMORY;
- // Fermer la clé svchost:
- RegCloseKey(hkSvchost);
- // Fermer le handle de notre service:
- CloseServiceHandle(schService);
- }
- // Fermer le handle du gestionnaire de services:
- CloseServiceHandle(schScm);
- }
- // Retourner dwError si non nul, sinon GetLastError():
- return dwError? dwError : GetLastError();
- }
-
- // Fonction de désinstallation du service:
- DWORD WINAPI RemoveService()
- {
- HKEY hkSvchost;
- SC_HANDLE schScm ,schService;
- char* pData;
- DWORD dwError=0,dwSize = 0;
- // Ouvrir le gestionnaire de services:
- schScm = OpenSCManager(0, 0, SC_MANAGER_ALL_ACCESS);
- if(schScm)
- {
- // Ouvrir notre service:
- schService=OpenService(schScm,"RacppService",SERVICE_ALL_ACCESS);
- if(schService)
- {
- // Supprimer le service:
- if(DeleteService(schService))
- {
- // Ouvrir la clé indiquant la liste des groupes d'instances de svchost.exe:
- RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Svchost", 0, KEY_ALL_ACCESS, &hkSvchost);
- // Obtenir la longueur du contenu du groupe netsvcs:
- RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, 0, &dwSize);
- // Fixer le nom de notre service pour la liste des services du groupe netsvcs:
- lstrcpy(buff,"RacppService");
- // Allouer la mémoire nécessaire pour tous les noms de services du groupe netsvcs:
- pData=HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,dwSize);
- if(pData)
- {
- char *pNames;
- // Récupérer la liste des noms de services du groupe netsvcs:
- RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, (BYTE*)pData, &dwSize);
- // Vérifier si le nom existe:
- for (pNames = pData; *pNames; pNames=strchr(pNames,0)+1) if(!lstrcmpi(pNames,buff)) break;
- // Le supprimer s'il existe:
- if (*pNames)
- {
- char* pNext;
- pNext=strchr(pNames,0)+1;
- memcpy(pNames,pNext,dwSize-(pNext-pData));
- RegSetValueEx(hkSvchost, "netsvcs", 0, REG_MULTI_SZ, (BYTE*)pData, dwSize -(lstrlen(buff)+1));
- }
- else dwError=ERROR_NO_SUCH_MEMBER;
- // Libérer la mémoire allouée:
- HeapFree(GetProcessHeap(),0,pData);
- }
- else dwError=ERROR_NOT_ENOUGH_MEMORY;
- // Fermer la clé svchost:
- RegCloseKey(hkSvchost);
- }
- // Fermer le handle de notre service:
- CloseServiceHandle(schService);
- }
- // Fermer le handle du gestionnaire de services:
- CloseServiceHandle(schScm);
- }
- // Retourner dwError si non nul, sinon GetLastError():
- return dwError? dwError : GetLastError();
- }
-
- // Fonction HandlerEx communiquant avec le gestionnaire de services:
- DWORD WINAPI HandlerEx(DWORD dwControl, DWORD dwEventType, LPVOID lpEventData, LPVOID lpContext)
- {
- switch(dwControl)
- {
- case SERVICE_CONTROL_STOP:
- case SERVICE_CONTROL_SHUTDOWN:
- // Mettre le service à l'état "En cours d'arrêt":
- ServiceStatus.dwWaitHint = 1000;
- ServiceStatus.dwCurrentState = SERVICE_STOP_PENDING;
- SetServiceStatus(hServiceStatusHandle, &ServiceStatus );
- // Mettre l'Event à l'état signalé:
- SetEvent(hEvent);
- return NO_ERROR;
- default:
- ServiceStatus.dwWaitHint = 0;
- break;
- }
- SetServiceStatus(hServiceStatusHandle, &ServiceStatus);// Obligatoire selon MSDN
- return NO_ERROR;
- }
-
- // Fonction Callback appelée toutes les minutes notre timer:
- VOID CALLBACK TimerProc( LPVOID lpParameter,BOOLEAN TimerOrWaitFired)
- {
- SYSTEMTIME st;
- DWORD dwLen;
- // Se positionner à la fin du fichier log:
- SetFilePointer(hFile,0,0,FILE_END);
- // Former la ligne à écrire dans le fichier log:
- lstrcpy(buff,"Le timer de RacppService a été déclenché le ");
- GetLocalTime(&st);
- GetDateFormat(0,0,&st,"dd/MM/yyyy",buff+lstrlen(buff),12);
- lstrcat(buff," à ");
- GetTimeFormat(0,0,&st,"HH:mm:ss",buff+lstrlen(buff),12);
- lstrcat(buff,"\r\n");
- // Ecrire la ligne formée dans le fichier log:
- WriteFile(hFile,buff,lstrlen(buff),&dwLen,0);
- return;
- }
-
- // ServiceMain
- VOID WINAPI ServiceMain(DWORD dwArgc, LPTSTR *lpszArgv)
- {
- hServiceStatusHandle = RegisterServiceCtrlHandlerEx("RacppService", HandlerEx, NULL);
- if (hServiceStatusHandle)
- {
- // Initialiser notre structure SERVICE_STATUS:
- ServiceStatus.dwServiceType = SERVICE_WIN32;
- ServiceStatus.dwControlsAccepted = 0;
- ServiceStatus.dwWin32ExitCode = 0;
- ServiceStatus.dwServiceSpecificExitCode = 0;
- ServiceStatus.dwCheckPoint = 0;
- // Mettre le service dans l'état "En cours de démarrage":
- ServiceStatus.dwWaitHint = 1000;
- ServiceStatus.dwCurrentState = SERVICE_START_PENDING;
- SetServiceStatus(hServiceStatusHandle, &ServiceStatus);
- // Créer un Event avec "non signalé" comme état initial:
- hEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
- if (hEvent)
- {
- // Ouvrir notre fichier log ou le créer si inexistant:
- hFile=CreateFile("C:\\racppservice.log", GENERIC_WRITE, FILE_SHARE_READ, 0, OPEN_ALWAYS, 0, 0);
- if(hFile!=INVALID_HANDLE_VALUE)
- {
- // Créer et lancer notre timer:
- HANDLE hTimerQueue,hTimer;
- hTimerQueue=CreateTimerQueue();
- CreateTimerQueueTimer(&hTimer,hTimerQueue,TimerProc,0,0,60000,WT_EXECUTEINTIMERTHREAD);
- // Mettre le service dans l'état "Démarré":
- ServiceStatus.dwWaitHint = 0;
- ServiceStatus.dwCurrentState = SERVICE_RUNNING;
- ServiceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN ;
- SetServiceStatus(hServiceStatusHandle, &ServiceStatus);
- // Attendre que l'Event soit à l'état signalé:
- WaitForSingleObject(hEvent, INFINITE);
- // Détruire notre timer:
- DeleteTimerQueueTimer(hTimerQueue,hTimer,0);
- DeleteTimerQueueEx(hTimerQueue,0);
- // Fermer le handle de notre fichier log:
- CloseHandle(hFile);
- }
- // Fermer le handle de l'Event:
- CloseHandle(hEvent);
- }
- // Mettre le service dans l'état "Arrêté":
- ServiceStatus.dwWaitHint = 0;
- ServiceStatus.dwCurrentState = SERVICE_STOPPED;
- SetServiceStatus(hServiceStatusHandle, &ServiceStatus);
- }
- return;
- }
-
- // DllMain
- BOOL APIENTRY DllMain(HINSTANCE hInst, DWORD dwReason, LPVOID lpReserved)
- {
- // Obtenir le HINSTANCE de notre dll:
- hDll=hInst;
- return TRUE;
- }
#define _WIN32_WINNT 0x0500 // Pour Windows 2000 et supérieur
#include <windows.h>
// Déclarations globales:
HINSTANCE hDll;
SERVICE_STATUS_HANDLE hServiceStatusHandle;
SERVICE_STATUS ServiceStatus;
HANDLE hEvent,hFile;
char buff[MAX_PATH];
// Fonction d'installation du service:
int WINAPI InstallService()
{
HKEY hkService,hkSvchost;
SC_HANDLE schScm ,schService;
char* pData;
DWORD dwError=0, dwLen,dwSize = 0;
// Ouvrir le gestionnaire de services:
schScm = OpenSCManager(0, 0, SC_MANAGER_ALL_ACCESS);
if(schScm)
{
// Créer notre service:
schService = CreateService(schScm, "RacppService", 0, SERVICE_ALL_ACCESS, SERVICE_WIN32_SHARE_PROCESS, SERVICE_AUTO_START, SERVICE_ERROR_NORMAL, "%SystemRoot%\\System32\\svchost.exe -k netsvcs", 0, 0, 0, 0, 0);
if(schService)
{
// Ajouter une description à notre service:
SERVICE_DESCRIPTION sd;
sd.lpDescription = "Service dans une DLL lancé par svchost.exe";
ChangeServiceConfig2(schService, SERVICE_CONFIG_DESCRIPTION, &sd);
// Ajouter la sous-clé Parameters à la clé de notre service:
RegCreateKeyEx(HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Services\\RacppService\\Parameters", 0, 0, REG_OPTION_NON_VOLATILE,KEY_ALL_ACCESS, 0, &hkService, 0);
// Récupérer le chemin complet de notre Dll:
GetModuleFileName(hDll, buff, sizeof(buff));
// Affecter le chemin de la Dll à la sous-clé Parameters sous le nom ServiceDll:
RegSetValueEx(hkService, "ServiceDll", 0, REG_EXPAND_SZ, (BYTE*)buff, lstrlen(buff)+1);
// Fermer la clé de notre service:
RegCloseKey(hkService);
// Ouvrir la clé indiquant la liste des groupes d'instances de svchost.exe:
RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Svchost", 0, KEY_ALL_ACCESS, &hkSvchost);
// Obtenir la longueur du contenu du groupe netsvcs:
RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, 0, &dwSize);
// Fixer le nom de notre service pour la liste des services du groupe netsvcs:
lstrcpy(buff,"RacppService");
dwLen=lstrlen(buff);
// Allouer la mémoire nécessaire pour la nouvelle liste des noms de services du groupe netsvcs:
pData=HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,dwSize + dwLen + 1);
if(pData)
{
char *pNames;
// Récupérer la liste des noms de services du groupe netsvcs:
RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, (BYTE*)pData, &dwSize);
// Vérifier si le nom existe
for (pNames = pData; *pNames; pNames=strchr(pNames,0)+1) if(!lstrcmpi(pNames, buff)) break;
// L'ajouter s'il n'existe pas:
if (*pNames == 0)
{
memcpy(pData + dwSize - 1, buff, dwLen + 1);
RegSetValueEx(hkSvchost, "netsvcs", 0, REG_MULTI_SZ, (BYTE*)pData, dwSize + dwLen + 1);
}
else dwError=ERROR_ALREADY_EXISTS;
// Libérer la mémoire allouée:
HeapFree(GetProcessHeap(),0,pData);
}
else dwError=ERROR_NOT_ENOUGH_MEMORY;
// Fermer la clé svchost:
RegCloseKey(hkSvchost);
// Fermer le handle de notre service:
CloseServiceHandle(schService);
}
// Fermer le handle du gestionnaire de services:
CloseServiceHandle(schScm);
}
// Retourner dwError si non nul, sinon GetLastError():
return dwError? dwError : GetLastError();
}
// Fonction de désinstallation du service:
DWORD WINAPI RemoveService()
{
HKEY hkSvchost;
SC_HANDLE schScm ,schService;
char* pData;
DWORD dwError=0,dwSize = 0;
// Ouvrir le gestionnaire de services:
schScm = OpenSCManager(0, 0, SC_MANAGER_ALL_ACCESS);
if(schScm)
{
// Ouvrir notre service:
schService=OpenService(schScm,"RacppService",SERVICE_ALL_ACCESS);
if(schService)
{
// Supprimer le service:
if(DeleteService(schService))
{
// Ouvrir la clé indiquant la liste des groupes d'instances de svchost.exe:
RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Svchost", 0, KEY_ALL_ACCESS, &hkSvchost);
// Obtenir la longueur du contenu du groupe netsvcs:
RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, 0, &dwSize);
// Fixer le nom de notre service pour la liste des services du groupe netsvcs:
lstrcpy(buff,"RacppService");
// Allouer la mémoire nécessaire pour tous les noms de services du groupe netsvcs:
pData=HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,dwSize);
if(pData)
{
char *pNames;
// Récupérer la liste des noms de services du groupe netsvcs:
RegQueryValueEx(hkSvchost, "netsvcs", 0, 0, (BYTE*)pData, &dwSize);
// Vérifier si le nom existe:
for (pNames = pData; *pNames; pNames=strchr(pNames,0)+1) if(!lstrcmpi(pNames,buff)) break;
// Le supprimer s'il existe:
if (*pNames)
{
char* pNext;
pNext=strchr(pNames,0)+1;
memcpy(pNames,pNext,dwSize-(pNext-pData));
RegSetValueEx(hkSvchost, "netsvcs", 0, REG_MULTI_SZ, (BYTE*)pData, dwSize -(lstrlen(buff)+1));
}
else dwError=ERROR_NO_SUCH_MEMBER;
// Libérer la mémoire allouée:
HeapFree(GetProcessHeap(),0,pData);
}
else dwError=ERROR_NOT_ENOUGH_MEMORY;
// Fermer la clé svchost:
RegCloseKey(hkSvchost);
}
// Fermer le handle de notre service:
CloseServiceHandle(schService);
}
// Fermer le handle du gestionnaire de services:
CloseServiceHandle(schScm);
}
// Retourner dwError si non nul, sinon GetLastError():
return dwError? dwError : GetLastError();
}
// Fonction HandlerEx communiquant avec le gestionnaire de services:
DWORD WINAPI HandlerEx(DWORD dwControl, DWORD dwEventType, LPVOID lpEventData, LPVOID lpContext)
{
switch(dwControl)
{
case SERVICE_CONTROL_STOP:
case SERVICE_CONTROL_SHUTDOWN:
// Mettre le service à l'état "En cours d'arrêt":
ServiceStatus.dwWaitHint = 1000;
ServiceStatus.dwCurrentState = SERVICE_STOP_PENDING;
SetServiceStatus(hServiceStatusHandle, &ServiceStatus );
// Mettre l'Event à l'état signalé:
SetEvent(hEvent);
return NO_ERROR;
default:
ServiceStatus.dwWaitHint = 0;
break;
}
SetServiceStatus(hServiceStatusHandle, &ServiceStatus);// Obligatoire selon MSDN
return NO_ERROR;
}
// Fonction Callback appelée toutes les minutes notre timer:
VOID CALLBACK TimerProc( LPVOID lpParameter,BOOLEAN TimerOrWaitFired)
{
SYSTEMTIME st;
DWORD dwLen;
// Se positionner à la fin du fichier log:
SetFilePointer(hFile,0,0,FILE_END);
// Former la ligne à écrire dans le fichier log:
lstrcpy(buff,"Le timer de RacppService a été déclenché le ");
GetLocalTime(&st);
GetDateFormat(0,0,&st,"dd/MM/yyyy",buff+lstrlen(buff),12);
lstrcat(buff," à ");
GetTimeFormat(0,0,&st,"HH:mm:ss",buff+lstrlen(buff),12);
lstrcat(buff,"\r\n");
// Ecrire la ligne formée dans le fichier log:
WriteFile(hFile,buff,lstrlen(buff),&dwLen,0);
return;
}
// ServiceMain
VOID WINAPI ServiceMain(DWORD dwArgc, LPTSTR *lpszArgv)
{
hServiceStatusHandle = RegisterServiceCtrlHandlerEx("RacppService", HandlerEx, NULL);
if (hServiceStatusHandle)
{
// Initialiser notre structure SERVICE_STATUS:
ServiceStatus.dwServiceType = SERVICE_WIN32;
ServiceStatus.dwControlsAccepted = 0;
ServiceStatus.dwWin32ExitCode = 0;
ServiceStatus.dwServiceSpecificExitCode = 0;
ServiceStatus.dwCheckPoint = 0;
// Mettre le service dans l'état "En cours de démarrage":
ServiceStatus.dwWaitHint = 1000;
ServiceStatus.dwCurrentState = SERVICE_START_PENDING;
SetServiceStatus(hServiceStatusHandle, &ServiceStatus);
// Créer un Event avec "non signalé" comme état initial:
hEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
if (hEvent)
{
// Ouvrir notre fichier log ou le créer si inexistant:
hFile=CreateFile("C:\\racppservice.log", GENERIC_WRITE, FILE_SHARE_READ, 0, OPEN_ALWAYS, 0, 0);
if(hFile!=INVALID_HANDLE_VALUE)
{
// Créer et lancer notre timer:
HANDLE hTimerQueue,hTimer;
hTimerQueue=CreateTimerQueue();
CreateTimerQueueTimer(&hTimer,hTimerQueue,TimerProc,0,0,60000,WT_EXECUTEINTIMERTHREAD);
// Mettre le service dans l'état "Démarré":
ServiceStatus.dwWaitHint = 0;
ServiceStatus.dwCurrentState = SERVICE_RUNNING;
ServiceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN ;
SetServiceStatus(hServiceStatusHandle, &ServiceStatus);
// Attendre que l'Event soit à l'état signalé:
WaitForSingleObject(hEvent, INFINITE);
// Détruire notre timer:
DeleteTimerQueueTimer(hTimerQueue,hTimer,0);
DeleteTimerQueueEx(hTimerQueue,0);
// Fermer le handle de notre fichier log:
CloseHandle(hFile);
}
// Fermer le handle de l'Event:
CloseHandle(hEvent);
}
// Mettre le service dans l'état "Arrêté":
ServiceStatus.dwWaitHint = 0;
ServiceStatus.dwCurrentState = SERVICE_STOPPED;
SetServiceStatus(hServiceStatusHandle, &ServiceStatus);
}
return;
}
// DllMain
BOOL APIENTRY DllMain(HINSTANCE hInst, DWORD dwReason, LPVOID lpReserved)
{
// Obtenir le HINSTANCE de notre dll:
hDll=hInst;
return TRUE;
}
Sources du même auteur
Sources de la même categorie
Commentaires et avis
Discussions en rapport avec ce code source dans le forum
Problème de hook clavier [ par Oeil_de_taupe ]
Bonjour tout le monde, Je suis en train de créer un programme me permettant d'utiliser qu'un seul clavier sur deux ordinateurs (grâce à une connectio
je veut créer une dll non managé en c++ qui utilise un service web [ par vboussema ]
salutj'ai une dll qui dois contenir une methode qui retourne un boolean cette dll est ecrite en c++ non managé pour qu'un autre programme (exe )va uti
DLL appel Web service [ par pcorbella ]
Hello Everybody, J'ai une appli en smalltalk VSE 3.2 sous windows ... autant dire que c'est pas tout jeune qui sais activer des dll. Est il possible
espionner une dll [ par 01Dawi ]
Bon je sais ca va faire bondir beaucoup d'entre vous mais on sait jamais.Est ce que quelqu'un sait si ya moyen d'espionner (à l'aide d'une applic
comment faire une src [ par zackman ]
Voila, en premier tps je me presente, zackman, je suis joueur de sof2 sur un server de aimbots, je vous expliques pas c'est pas la peine je pense ;).D
Appel Dll Visual Basic en C++ [ par Cako19 ]
Bonjour, Comment fait-on pour appeler les fonctions d'une dll Visual Basic en C ++?Si qqun le sait, je suis preneuse !Merci d'avance,Cako19
Aide en "api hooking" URGENT !!! [ par Kangourou_Nomade ]
Pour faire un logiciel api hooking, sachant la difficulté du truc je voulais savoir si quelqu'un pouvait me filer une dll avec les fonctions appr
Comment utiliser SetPixel dans ma DLL ? [ par YoYoDev21 ]
Bonjour,Je développe une DLL en C afin d'accélérer certain traitement fait dans un programme VB6.Entre autre, je voudrais que la DLL re
intercepter les messages d'un programme avec une dll [ par cyber_al ]
bonjours a tous voila voila !je souhaiterait "hooker" un programme qui utilise les fonctions MDI ,en fait le but est de filtrer les messages de ce pro
DLL faite en C++ avec VB [ par Sniper_Vgaerr ]
Je fais un programme de cryptage avec clé privée et publique et je prefere l'interface de VB que celle du C, mais comme le C va plus vite je
|
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
|