假设要自己编程来加载Windows下后缀为.sys的驱动程序;首先要使用 OpenSCManager 函数打开Windows服务控制管理器;
下面先来调用此函数看一下会不会打开成功;代码如下;
#include <windows.h>
#include <winsvc.h>
#include <conio.h>
#include <stdio.h>
#define DRIVER_NAME "HelloDriver"
#define DRIVER_PATH "..//MyDriver//HelloDriver.sys"
int APIENTRY WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR lpCmdLine,
int nCmdShow)
{
/* TODO: Place code here.*/
PVOID lpMsgBuf;
char szBuffer[100];
char szDriverImagePath[256];
//得到完整的驱动路径
//GetFullPathName(lpszDriverPath, 256, szDriverImagePath, NULL);
BOOL bRet = FALSE;
SC_HANDLE hServiceMgr=NULL;//SCM管理器的句柄
SC_HANDLE hServiceDDK=NULL;//NT驱动程序的服务句柄
//打开服务控制管理器
//hServiceMgr = OpenSCManager( NULL, NULL, SC_MANAGER_ALL_ACCESS );
hServiceMgr = OpenSCManager( NULL, "abc", SC_MANAGER_ALL_ACCESS);
if( hServiceMgr == NULL )
{
//OpenSCManager失败
if (FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS,
NULL,
GetLastError(), // 错误代码
MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
(LPTSTR)&lpMsgBuf,
0,
NULL))
{
MessageBox(NULL, (LPCTSTR)lpMsgBuf, TEXT("打开服务控制管理器失败"), MB_OK);
}
}
else
{
wsprintf(szBuffer, "0x%08x",hServiceMgr);
MessageBox(NULL,szBuffer,TEXT("开服务控制管理器,句柄:"),0);
}
LocalFree(lpMsgBuf);
return 0;
}
打开成功,则显示打开的句柄;打开失败,显示格式化错误消息;使用Dev C++;
打开成功如下;
OpenSCManager 函数描述如下;
SC_HANDLE WINAPI OpenSCManager(
_In_opt_ LPCTSTR lpMachineName,
_In_opt_ LPCTSTR lpDatabaseName,
_In_ DWORD dwDesiredAccess
);
函数作用:以一定的权限,在指定的计算机打开指定的SCM数据库;
参数:
1. lpMachineName:目标计算机名,NULL表示本地计算机
2. lpDatabaseName:服务管理程序系统组件数据库,可以设为SERVICES_ACTIVE_DATABASE,如果为NULL,表示默认打开SERVICES_ACTIVE_DATABASE数据库
3. dwDesiredAccess:对SCM的权限,可以是以下:
Access right Description
SC_MANAGER_ALL_ACCESS (0xF003F) Includes STANDARD_RIGHTS_REQUIRED, in addition to all access rights in this table.
SC_MANAGER_CREATE_SERVICE (0x0002) Required to call the CreateService function to create a service object and add it to the database.
SC_MANAGER_CONNECT (0x0001) Required to connect to the service control manager.
SC_MANAGER_ENUMERATE_SERVICE (0x0004) SC_MANAGER_LOCK (0x0008) Required to call the LockServiceDatabase function to acquire a lock on the database.
SC_MANAGER_MODIFY_BOOT_CONFIG (0x0020) Required to call the NotifyBootConfigStatus function.
SC_MANAGER_QUERY_LOCK_STATUS (0x0010) Required to call the QueryServiceLockStatus function to retrieve the lock status information for the database.
第二个参数是数据库名;如果随便给个"abc",则打开失败如下;