我试了调用了几次都出错。。 [StructLayout(LayoutKind.Sequential)]
public struct QUERY_SERVICE_CONFIG
{
public int dwServiceType;
public int dwStartType;
public int dwErrorControl;
public string lpBinaryPathName;
public string lpLoadOrderGroup;
public int dwTagId;
public string lpDependencies;
public string lpServiceStartName;
public string lpDisplayName; } [StructLayout(LayoutKind.Sequential)]
public struct SERVICE_DESCRIPTION
{
public string lpDescription;
} //连接服务控制管理器
[DllImport("Advapi32.dll")]
public extern static int OpenSCManager(string lpMachineName, string lpDatabaseName, int dwDesiredAccess);
//打开服务
[DllImport("Advapi32.dll")]
public extern static int OpenService(int hSCManager, string lpServiceName, int dwDesiredAccess);
//获取服务配置
[DllImport("Advapi32.dll")]
public extern static bool QueryServiceConfig(int hService, out QUERY_SERVICE_CONFIG QueryServiceConfig, int cbBufSize, out int pcbBytesNeeded);
//获取服务描述
[DllImport("Advapi32.dll")]
public extern static bool QueryServiceConfig2(int hService, int dwInfoLevel, out SERVICE_DESCRIPTION ServiceDescription, int cbBufSize, out int pcbBytesNeeded);
//获取错误代码
[DllImport("Kernel32.dll")]
public extern static int GetLastError(); public QUERY_SERVICE_CONFIG qsc = new QUERY_SERVICE_CONFIG();
public SERVICE_DESCRIPTION sd = new SERVICE_DESCRIPTION();
public void GetLocalServiceAttribute(String serviceName)
{
int hSCManager = OpenSCManager(null, null, 0xF003F);////SC_MANAGER_ALL_ACCESS (0xF003F)
if (hSCManager != 0)
{
int hService = OpenService(hSCManager, serviceName, 0xF01FF);////SERVICE_ALL_ACCESS (0xF01FF)
if (hService != 0)
{
int dwError = 0, cbBufSize = 0, dwBytesNeeded = 0; if (!QueryServiceConfig(hService, out qsc, 0, out dwBytesNeeded))//
{
dwError = GetLastError();
if (dwError == 122)
{
cbBufSize = dwBytesNeeded;
}
else
{
//MessageBox.Show("Query Service: " + serviceName + "'s Config Failed!");
}
}
if (!QueryServiceConfig(hService, out qsc, cbBufSize, out dwBytesNeeded))//这里出错显示 尝试读取或写入受保护的内存。这通常指示其他内存已损坏。
{
// MessageBox.Show("Query Service: " + serviceName + "'s Config Failed!");
} if (!QueryServiceConfig2(hService, 1, out sd, 0, out dwBytesNeeded))
{
//第二个参数:dwInfoLevel:1==SERVICE_CONFIG_DESCRIPTION
dwError = GetLastError();
if (dwError == 122)
{
cbBufSize = dwBytesNeeded;
if (!QueryServiceConfig2(hService, 1, out sd, cbBufSize, out dwBytesNeeded))))//这里出错显示 尝试读取或写入受保护的内存。这通常指示其他内存已损坏。 {
//MessageBox.Show("Query Service: " + serviceName + "'s Description Failed!");
}
}
else
{
// MessageBox.Show("Query Service: " + serviceName + "'s Description Failed!");
}
}
}
else
{
// MessageBox.Show("OpenService " + serviceName + " Failed!");
}
}
else
{
// MessageBox.Show("OpenSCManager Failed!");
}
}
public struct QUERY_SERVICE_CONFIG
{
public int dwServiceType;
public int dwStartType;
public int dwErrorControl;
public string lpBinaryPathName;
public string lpLoadOrderGroup;
public int dwTagId;
public string lpDependencies;
public string lpServiceStartName;
public string lpDisplayName; } [StructLayout(LayoutKind.Sequential)]
public struct SERVICE_DESCRIPTION
{
public string lpDescription;
} //连接服务控制管理器
[DllImport("Advapi32.dll")]
public extern static int OpenSCManager(string lpMachineName, string lpDatabaseName, int dwDesiredAccess);
//打开服务
[DllImport("Advapi32.dll")]
public extern static int OpenService(int hSCManager, string lpServiceName, int dwDesiredAccess);
//获取服务配置
[DllImport("Advapi32.dll")]
public extern static bool QueryServiceConfig(int hService, out QUERY_SERVICE_CONFIG QueryServiceConfig, int cbBufSize, out int pcbBytesNeeded);
//获取服务描述
[DllImport("Advapi32.dll")]
public extern static bool QueryServiceConfig2(int hService, int dwInfoLevel, out SERVICE_DESCRIPTION ServiceDescription, int cbBufSize, out int pcbBytesNeeded);
//获取错误代码
[DllImport("Kernel32.dll")]
public extern static int GetLastError(); public QUERY_SERVICE_CONFIG qsc = new QUERY_SERVICE_CONFIG();
public SERVICE_DESCRIPTION sd = new SERVICE_DESCRIPTION();
public void GetLocalServiceAttribute(String serviceName)
{
int hSCManager = OpenSCManager(null, null, 0xF003F);////SC_MANAGER_ALL_ACCESS (0xF003F)
if (hSCManager != 0)
{
int hService = OpenService(hSCManager, serviceName, 0xF01FF);////SERVICE_ALL_ACCESS (0xF01FF)
if (hService != 0)
{
int dwError = 0, cbBufSize = 0, dwBytesNeeded = 0; if (!QueryServiceConfig(hService, out qsc, 0, out dwBytesNeeded))//
{
dwError = GetLastError();
if (dwError == 122)
{
cbBufSize = dwBytesNeeded;
}
else
{
//MessageBox.Show("Query Service: " + serviceName + "'s Config Failed!");
}
}
if (!QueryServiceConfig(hService, out qsc, cbBufSize, out dwBytesNeeded))//这里出错显示 尝试读取或写入受保护的内存。这通常指示其他内存已损坏。
{
// MessageBox.Show("Query Service: " + serviceName + "'s Config Failed!");
} if (!QueryServiceConfig2(hService, 1, out sd, 0, out dwBytesNeeded))
{
//第二个参数:dwInfoLevel:1==SERVICE_CONFIG_DESCRIPTION
dwError = GetLastError();
if (dwError == 122)
{
cbBufSize = dwBytesNeeded;
if (!QueryServiceConfig2(hService, 1, out sd, cbBufSize, out dwBytesNeeded))))//这里出错显示 尝试读取或写入受保护的内存。这通常指示其他内存已损坏。 {
//MessageBox.Show("Query Service: " + serviceName + "'s Description Failed!");
}
}
else
{
// MessageBox.Show("Query Service: " + serviceName + "'s Description Failed!");
}
}
}
else
{
// MessageBox.Show("OpenService " + serviceName + " Failed!");
}
}
else
{
// MessageBox.Show("OpenSCManager Failed!");
}
}
OpenSCManager(null, null, 0xF003F);////这里的对的。。
OpenService(hSCManager, serviceName,0xF01FF);//这里改成0x00001还是不行。。于是我用c++写了个dll。调用成功获得服务的描述和服务文件的路径。
CReadService.hstruct CServerRead
{
char * DisplayName;
int ServiceType;
char * ServicePath;
char * ServiceMs;
};
typedef void(_stdcall *CallBackService)(CServerRead);
void _stdcall OutService(char * ServiceName,CallBackService mae);CReadService.cppvoid _stdcall OutService(char * ServiceName,CallBackService callmae)
{
CServerRead mae;
SC_HANDLE scm; if((scm=::OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS))==NULL)
{
//return false;
}
SC_HANDLE service=NULL;
service=OpenService(scm,ServiceName,SERVICE_QUERY_CONFIG); LPQUERY_SERVICE_CONFIG ServicesInfo;
LPSERVICE_DESCRIPTION lpsd; DWORD nResumeHandle=0;
DWORD cbBufSize, dwError;
//QueryServiceConfig( service, NULL, 0, &nResumeHandle); if( !QueryServiceConfigA( service, NULL, 0, &nResumeHandle)) //The QueryServiceConfig2 function retrieves the optional configuration parameters of the specified service
{
dwError = GetLastError();
if( ERROR_INSUFFICIENT_BUFFER == dwError )
{
cbBufSize = nResumeHandle;
ServicesInfo = (LPQUERY_SERVICE_CONFIG) LocalAlloc(LMEM_FIXED, cbBufSize);
}
else
{
//return false;
}
}
//EnumDependentServices();
//GetServiceDisplayName();
//http://www.hackline.net/a/school/ymbc/C/2010/0729/5062.html
if(!::QueryServiceConfigA(service,ServicesInfo,cbBufSize,&nResumeHandle))
{
//return false;
} if( !QueryServiceConfig2A( service, SERVICE_CONFIG_DESCRIPTION,NULL, 0, &nResumeHandle)) //The QueryServiceConfig2 function retrieves the optional configuration parameters of the specified service
{
dwError = GetLastError();
if( ERROR_INSUFFICIENT_BUFFER == dwError )
{
cbBufSize = nResumeHandle;
lpsd = (LPSERVICE_DESCRIPTION) LocalAlloc(LMEM_FIXED, cbBufSize);
}
else
{
//return false;
}
}
if (! QueryServiceConfig2A(service, SERVICE_CONFIG_DESCRIPTION,(LPBYTE) lpsd, cbBufSize, &nResumeHandle))
{
//return false;
} mae.DisplayName=ServicesInfo->lpDisplayName;
mae.ServicePath=ServicesInfo->lpBinaryPathName;
mae.ServiceType=ServicesInfo->dwServiceType;
mae.ServiceMs=lpsd->lpDescription; callmae(mae); LocalFree(ServicesInfo);
LocalFree(lpsd); CloseServiceHandle(service);
CloseServiceHandle(scm);
//return true;
}还是希望找到c#直接调用的方法。哪位高手请指点下。。
1楼:错误是:其他信息: 尝试读取或写入受保护的内存。这通常指示其他内存已损坏。
http://pinvoke.net/default.aspx/advapi32/OpenService.html
http://pinvoke.net/default.aspx/advapi32/QueryServiceConfig.html
http://pinvoke.net/default.aspx/advapi32/QueryServiceConfig2.html