StartService 失败,错误代码 1053
我正在尝试在远程计算机上启动一个进程。我正在使用 OpenSCManager()、CreateService()、QueryServiceStatusEx() 和 StartService() API。我能够成功地将我的进程安装为服务,但是当我尝试启动它时,StartService 返回错误代码 1053(“服务没有及时响应启动或控制请求。”)。谁能帮我解决这个问题?
提前致谢!
kampi
更新:这是到目前为止我的代码(几乎来自 msdn,但我编辑了一些)
#include <windows.h>
VOID SvcInstall();
VOID __stdcall DoStartSvc();
#pragma comment(lib, "Advapi32.lib")
SC_HANDLE schSCManager;
SC_HANDLE schService;
int _tmain(int argc, _TCHAR* argv[])
{
SvcInstall();
DoStartSvc();
return 0;
}
VOID SvcInstall()
{
SC_HANDLE schSCManager;
SC_HANDLE schService;
TCHAR szPath[MAX_PATH];
if( !GetModuleFileName( NULL, szPath, MAX_PATH ) )
{
printf("Cannot install service (%d)\n", GetLastError());
return;
}
// Get a handle to the SCM database.
schSCManager = OpenSCManager(
_T("\\\\kampimachine"), // remote computer
NULL, // ServicesActive database
SC_MANAGER_ALL_ACCESS); // full access rights
if (NULL == schSCManager)
{
printf("OpenSCManager failed (%d)\n", GetLastError());
return;
}
// Create the service
schService = CreateService(
schSCManager, // SCM database
_T("kampi"), // name of service
_T("kampi"), // service name to display
SERVICE_ALL_ACCESS, // desired access
SERVICE_WIN32_OWN_PROCESS, // service type
SERVICE_DEMAND_START, // start type
SERVICE_ERROR_NORMAL, // error control type
_T("%SystemRoot%\\system32\\notepad.exe"),// path to service's binary
NULL, // no load ordering group
NULL, // no tag identifier
NULL, // no dependencies
_T("domain\\user"), // LocalSystem account
_T("password")); // no password
if (schService == NULL)
{
printf("CreateService failed (%d)\n", GetLastError());
CloseServiceHandle(schSCManager);
return;
}
else printf("Service installed successfully\n");
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
}
VOID __stdcall DoStartSvc()
{
SERVICE_STATUS_PROCESS ssStatus;
DWORD dwOldCheckPoint;
DWORD dwStartTickCount;
DWORD dwWaitTime;
DWORD dwBytesNeeded;
// Get a handle to the SCM database.
schSCManager = OpenSCManager(
_T("\\\\kampimachine"), // remote computer
NULL, // servicesActive database
SC_MANAGER_ALL_ACCESS); // full access rights
if (NULL == schSCManager)
{
printf("OpenSCManager failed (%d)\n", GetLastError());
return;
}
// Get a handle to the service.
schService = OpenService(
schSCManager, // SCM database
_T("kampi"), // name of service
SERVICE_ALL_ACCESS); // full access
if (schService == NULL)
{
printf("OpenService failed (%d)\n", GetLastError());
CloseServiceHandle(schSCManager);
return;
}
// Check the status in case the service is not stopped.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // information level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // size needed if buffer is too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
// Check if the service is already running. It would be possible
// to stop the service here, but for simplicity this example just returns.
if(ssStatus.dwCurrentState != SERVICE_STOPPED && ssStatus.dwCurrentState != SERVICE_STOP_PENDING)
{
printf("Cannot start the service because it is already running\n");
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
// Save the tick count and initial checkpoint.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
// Wait for the service to stop before attempting to start it.
while (ssStatus.dwCurrentState == SERVICE_STOP_PENDING)
{
// Do not wait longer than the wait hint. A good interval is
// one-tenth of the wait hint but not less than 1 second
// and not more than 10 seconds.
dwWaitTime = ssStatus.dwWaitHint / 10;
if( dwWaitTime < 1000 )
dwWaitTime = 1000;
else if ( dwWaitTime > 10000 )
dwWaitTime = 10000;
Sleep( dwWaitTime );
// Check the status until the service is no longer stop pending.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // information level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // size needed if buffer is too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
if ( ssStatus.dwCheckPoint > dwOldCheckPoint )
{
// Continue to wait and check.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
}
else
{
if(GetTickCount()-dwStartTickCount > ssStatus.dwWaitHint)
{
printf("Timeout waiting for service to stop\n");
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
}
}
// Attempt to start the service.
if (!StartService(
schService, // handle to service
0, // number of arguments
NULL) ) // no arguments
{
printf("StartService failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
else printf("Service start pending...\n");
// Check the status until the service is no longer start pending.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // info level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // if buffer too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
// Save the tick count and initial checkpoint.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
while (ssStatus.dwCurrentState == SERVICE_START_PENDING)
{
// Do not wait longer than the wait hint. A good interval is
// one-tenth the wait hint, but no less than 1 second and no
// more than 10 seconds.
dwWaitTime = ssStatus.dwWaitHint / 10;
if( dwWaitTime < 1000 )
dwWaitTime = 1000;
else if ( dwWaitTime > 10000 )
dwWaitTime = 10000;
Sleep( dwWaitTime );
// Check the status again.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // info level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // if buffer too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
break;
}
if ( ssStatus.dwCheckPoint > dwOldCheckPoint )
{
// Continue to wait and check.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
}
else
{
if(GetTickCount()-dwStartTickCount > ssStatus.dwWaitHint)
{
// No progress made within the wait hint.
break;
}
}
}
// Determine whether the service is running.
if (ssStatus.dwCurrentState == SERVICE_RUNNING)
{
printf("Service started successfully.\n");
}
else
{
printf("Service not started. \n");
printf(" Current State: %d\n", ssStatus.dwCurrentState);
printf(" Exit Code: %d\n", ssStatus.dwWin32ExitCode);
printf(" Check Point: %d\n", ssStatus.dwCheckPoint);
printf(" Wait Hint: %d\n", ssStatus.dwWaitHint);
}
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
}
I'm trying to start a process on a remote machine. I'm using OpenSCManager(), CreateService(), QueryServiceStatusEx() and StartService() API-s. I'm able to successfully install my process as a serice, but when i'm trying to start it, StartService returns with errorocode 1053 ("The service didn't respond to the start or control request in a timely fashion."). Can anyone help me to solve this problem?
Thanks in advance!
kampi
Update: Here's my code so far(almost from msdn, but i have edited a bit)
#include <windows.h>
VOID SvcInstall();
VOID __stdcall DoStartSvc();
#pragma comment(lib, "Advapi32.lib")
SC_HANDLE schSCManager;
SC_HANDLE schService;
int _tmain(int argc, _TCHAR* argv[])
{
SvcInstall();
DoStartSvc();
return 0;
}
VOID SvcInstall()
{
SC_HANDLE schSCManager;
SC_HANDLE schService;
TCHAR szPath[MAX_PATH];
if( !GetModuleFileName( NULL, szPath, MAX_PATH ) )
{
printf("Cannot install service (%d)\n", GetLastError());
return;
}
// Get a handle to the SCM database.
schSCManager = OpenSCManager(
_T("\\\\kampimachine"), // remote computer
NULL, // ServicesActive database
SC_MANAGER_ALL_ACCESS); // full access rights
if (NULL == schSCManager)
{
printf("OpenSCManager failed (%d)\n", GetLastError());
return;
}
// Create the service
schService = CreateService(
schSCManager, // SCM database
_T("kampi"), // name of service
_T("kampi"), // service name to display
SERVICE_ALL_ACCESS, // desired access
SERVICE_WIN32_OWN_PROCESS, // service type
SERVICE_DEMAND_START, // start type
SERVICE_ERROR_NORMAL, // error control type
_T("%SystemRoot%\\system32\\notepad.exe"),// path to service's binary
NULL, // no load ordering group
NULL, // no tag identifier
NULL, // no dependencies
_T("domain\\user"), // LocalSystem account
_T("password")); // no password
if (schService == NULL)
{
printf("CreateService failed (%d)\n", GetLastError());
CloseServiceHandle(schSCManager);
return;
}
else printf("Service installed successfully\n");
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
}
VOID __stdcall DoStartSvc()
{
SERVICE_STATUS_PROCESS ssStatus;
DWORD dwOldCheckPoint;
DWORD dwStartTickCount;
DWORD dwWaitTime;
DWORD dwBytesNeeded;
// Get a handle to the SCM database.
schSCManager = OpenSCManager(
_T("\\\\kampimachine"), // remote computer
NULL, // servicesActive database
SC_MANAGER_ALL_ACCESS); // full access rights
if (NULL == schSCManager)
{
printf("OpenSCManager failed (%d)\n", GetLastError());
return;
}
// Get a handle to the service.
schService = OpenService(
schSCManager, // SCM database
_T("kampi"), // name of service
SERVICE_ALL_ACCESS); // full access
if (schService == NULL)
{
printf("OpenService failed (%d)\n", GetLastError());
CloseServiceHandle(schSCManager);
return;
}
// Check the status in case the service is not stopped.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // information level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // size needed if buffer is too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
// Check if the service is already running. It would be possible
// to stop the service here, but for simplicity this example just returns.
if(ssStatus.dwCurrentState != SERVICE_STOPPED && ssStatus.dwCurrentState != SERVICE_STOP_PENDING)
{
printf("Cannot start the service because it is already running\n");
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
// Save the tick count and initial checkpoint.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
// Wait for the service to stop before attempting to start it.
while (ssStatus.dwCurrentState == SERVICE_STOP_PENDING)
{
// Do not wait longer than the wait hint. A good interval is
// one-tenth of the wait hint but not less than 1 second
// and not more than 10 seconds.
dwWaitTime = ssStatus.dwWaitHint / 10;
if( dwWaitTime < 1000 )
dwWaitTime = 1000;
else if ( dwWaitTime > 10000 )
dwWaitTime = 10000;
Sleep( dwWaitTime );
// Check the status until the service is no longer stop pending.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // information level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // size needed if buffer is too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
if ( ssStatus.dwCheckPoint > dwOldCheckPoint )
{
// Continue to wait and check.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
}
else
{
if(GetTickCount()-dwStartTickCount > ssStatus.dwWaitHint)
{
printf("Timeout waiting for service to stop\n");
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
}
}
// Attempt to start the service.
if (!StartService(
schService, // handle to service
0, // number of arguments
NULL) ) // no arguments
{
printf("StartService failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
else printf("Service start pending...\n");
// Check the status until the service is no longer start pending.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // info level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // if buffer too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
return;
}
// Save the tick count and initial checkpoint.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
while (ssStatus.dwCurrentState == SERVICE_START_PENDING)
{
// Do not wait longer than the wait hint. A good interval is
// one-tenth the wait hint, but no less than 1 second and no
// more than 10 seconds.
dwWaitTime = ssStatus.dwWaitHint / 10;
if( dwWaitTime < 1000 )
dwWaitTime = 1000;
else if ( dwWaitTime > 10000 )
dwWaitTime = 10000;
Sleep( dwWaitTime );
// Check the status again.
if (!QueryServiceStatusEx(
schService, // handle to service
SC_STATUS_PROCESS_INFO, // info level
(LPBYTE) &ssStatus, // address of structure
sizeof(SERVICE_STATUS_PROCESS), // size of structure
&dwBytesNeeded ) ) // if buffer too small
{
printf("QueryServiceStatusEx failed (%d)\n", GetLastError());
break;
}
if ( ssStatus.dwCheckPoint > dwOldCheckPoint )
{
// Continue to wait and check.
dwStartTickCount = GetTickCount();
dwOldCheckPoint = ssStatus.dwCheckPoint;
}
else
{
if(GetTickCount()-dwStartTickCount > ssStatus.dwWaitHint)
{
// No progress made within the wait hint.
break;
}
}
}
// Determine whether the service is running.
if (ssStatus.dwCurrentState == SERVICE_RUNNING)
{
printf("Service started successfully.\n");
}
else
{
printf("Service not started. \n");
printf(" Current State: %d\n", ssStatus.dwCurrentState);
printf(" Exit Code: %d\n", ssStatus.dwWin32ExitCode);
printf(" Check Point: %d\n", ssStatus.dwCheckPoint);
printf(" Wait Hint: %d\n", ssStatus.dwWaitHint);
}
CloseServiceHandle(schService);
CloseServiceHandle(schSCManager);
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
我认为您在这里缺少一个关键组件:启动服务控制调度程序。如文档 您必须启动服务控制调度程序才能使 Windows 的服务控制管理器 (SCM) 向您的服务发送命令(例如
SERVICE_CONTROL_STOP
)调度程序的完成方式如下:
SERVICE_TABLE_ENTRY
(背景是每个服务都是通过SCM启动的,等待服务启动其Service Control Dispatcher 为了接收其命令...
我看到另一个问题您的代码:您正在尝试在每次启动服务时安装它!您最好检查适当的命令行参数以确定是否要安装或启动该服务!
I think you are missing a key component here: starting Service Control Dispatcher. As stated in the documentation you have to start the service control dispatcher in order to enable Windows' Service Control Manager (SCM) to send commands to your service (like
SERVICE_CONTROL_STOP
for example)Starting the dispatcher is done as follows:
SERVICE_TABLE_ENTRY
(look at MSDN library) containing your services' name as well as its Service Main Function (wich is different from your ordinary main method!)The background is that every service is being started via SCM, that waits for the service to start its Service Control Dispatcher in order to receive its commands...
I see another problem in your code: you're trying to install your service everytime it's being started! You'd better check for appropriate command line arguments to determine if the service is either going to be installed or started!
您的服务很可能立即关闭或崩溃。我建议向您的服务添加一些日志信息,以便发现它退出的原因。
There is a good chance that your service is either shutting down immediately or crashing. I would recommend adding some logging information to your service in order to discover why it is exiting.
实际上你想做的是模拟远程电脑。如果电脑使用的是Windows XP,那么您需要除管理员之外的权限才能创建服务。要调整权限,请参阅远程电脑中的本地系统策略。顺便问一下,你可以从你的电脑上打开远程电脑中的 ADMIN$ 共享吗?如果不是,那么这就是问题所在。
如需进一步参考,请检查 sysinternals 中的 psexec。
没有 BSOD、没有 Rootkit、没有乐趣 -- Biswanath Chowdhury(Win32 内核开发人员)
Actually what u r tryin to do is Impersonating the remote pc. If the pc is using Windows XP, then you need priviledges other than Administrator to create services. To adjust priviledges, see the Local system policy in the remote pc. By the way, can u just open the ADMIN$ share in the remote pc from yours? if not, then this is the problem.
for further reference check psexec in sysinternals.
NO BSOD, No Rootkit ,No Fun -- Biswanath Chowdhury (Win32 Kernel Developer)