📄 ntservice.cpp
字号:
}
if( bRet ) {
// installation succeeded. Now register the message file
RegisterApplicationLog(
szPath, // the path to the application itself
EVENTLOG_ERROR_TYPE | EVENTLOG_WARNING_TYPE | EVENTLOG_INFORMATION_TYPE // supported types
);
AddToMessageLog(TEXT("Service installed"),EVENTLOG_INFORMATION_TYPE);
}
} //!! TCW MOD
return bRet;
}
BOOL CNTService :: RemoveService() {
BOOL bRet = FALSE;
SetupConsole(); //!! TCW MOD - have to show the console here for the
// diagnostic or error reason: orignal class assumed
// that we were using _main for entry (a console app).
// This particular usage is a Windows app (no console),
// so we need to create it. Using SetupConsole with _main
// is ok - does nothing, since you only get one console.
if( OsIsWin95() ) { //!! TCW MOD - code added to install as Win95 service
HKEY hKey = 0;
LONG lRet = ERROR_SUCCESS;
if( ::RegCreateKey(HKEY_LOCAL_MACHINE, gszWin95ServKey , &hKey) == ERROR_SUCCESS ) {
lRet = ::RegDeleteValue(hKey, m_lpServiceName);
::RegCloseKey(hKey);
bRet=TRUE;
}
} else {
// Real NT services go here.
SC_HANDLE schSCManager = OpenSCManager(
0, // machine (NULL == local)
0, // database (NULL == default)
SC_MANAGER_ALL_ACCESS // access required
);
if( schSCManager ) {
SC_HANDLE schService = OpenService(
schSCManager,
m_lpServiceName,
SERVICE_ALL_ACCESS
);
if( schService ) {
// try to stop the service
if( ControlService(schService, SERVICE_CONTROL_STOP, &m_ssStatus) ) {
_tprintf(TEXT("Stopping %s."), m_lpDisplayName);
Sleep(1000);
while( QueryServiceStatus(schService, &m_ssStatus) ) {
if( m_ssStatus.dwCurrentState == SERVICE_STOP_PENDING ) {
_tprintf(TEXT("."));
Sleep( 1000 );
} else
break;
}
if( m_ssStatus.dwCurrentState == SERVICE_STOPPED )
_tprintf(TEXT("\n%s stopped.\n"), m_lpDisplayName);
else
_tprintf(TEXT("\n%s failed to stop.\n"), m_lpDisplayName);
}
// now remove the service
if( DeleteService(schService) ) {
_tprintf(TEXT("%s removed.\n"), m_lpDisplayName);
bRet = TRUE;
} else {
TCHAR szErr[256];
_tprintf(TEXT("DeleteService failed - %s\n"), GetLastErrorText(szErr,256));
}
CloseServiceHandle(schService);
} else {
TCHAR szErr[256];
_tprintf(TEXT("OpenService failed - %s\n"), GetLastErrorText(szErr,256));
}
CloseServiceHandle(schSCManager);
} else {
TCHAR szErr[256];
_tprintf(TEXT("OpenSCManager failed - %s\n"), GetLastErrorText(szErr,256));
}
if( bRet )
DeregisterApplicationLog();
}
return bRet;
}
BOOL CNTService :: EndService() {
BOOL bRet = FALSE;
SC_HANDLE schSCManager = ::OpenSCManager(
0, // machine (NULL == local)
0, // database (NULL == default)
SC_MANAGER_ALL_ACCESS // access required
);
if( schSCManager ) {
SC_HANDLE schService = ::OpenService(
schSCManager,
m_lpServiceName,
SERVICE_ALL_ACCESS
);
if( schService ) {
// try to stop the service
if( ::ControlService(schService, SERVICE_CONTROL_STOP, &m_ssStatus) ) {
_tprintf(TEXT("Stopping %s."), m_lpDisplayName);
::Sleep(1000);
while( ::QueryServiceStatus(schService, &m_ssStatus) ) {
if( m_ssStatus.dwCurrentState == SERVICE_STOP_PENDING ) {
_tprintf(TEXT("."));
::Sleep( 1000 );
} else
break;
}
if( m_ssStatus.dwCurrentState == SERVICE_STOPPED )
bRet = TRUE, _tprintf(TEXT("\n%s stopped.\n"), m_lpDisplayName);
else
_tprintf(TEXT("\n%s failed to stop.\n"), m_lpDisplayName);
}
::CloseServiceHandle(schService);
} else {
TCHAR szErr[256];
_tprintf(TEXT("OpenService failed - %s\n"), GetLastErrorText(szErr,256));
}
::CloseServiceHandle(schSCManager);
} else {
TCHAR szErr[256];
_tprintf(TEXT("OpenSCManager failed - %s\n"), GetLastErrorText(szErr,256));
}
return bRet;
}
BOOL CNTService :: StartupService() {
BOOL bRet = FALSE;
SC_HANDLE schSCManager = ::OpenSCManager(
0, // machine (NULL == local)
0, // database (NULL == default)
SC_MANAGER_ALL_ACCESS // access required
);
if( schSCManager ) {
SC_HANDLE schService = ::OpenService(
schSCManager,
m_lpServiceName,
SERVICE_ALL_ACCESS
);
if( schService ) {
// try to start the service
_tprintf(TEXT("Starting up %s."), m_lpDisplayName);
if( ::StartService(schService, 0, 0) ) {
Sleep(1000);
while( ::QueryServiceStatus(schService, &m_ssStatus) ) {
if( m_ssStatus.dwCurrentState == SERVICE_START_PENDING ) {
_tprintf(TEXT("."));
Sleep( 1000 );
} else
break;
}
if( m_ssStatus.dwCurrentState == SERVICE_RUNNING )
bRet = TRUE, _tprintf(TEXT("\n%s started.\n"), m_lpDisplayName);
else
_tprintf(TEXT("\n%s failed to start.\n"), m_lpDisplayName);
} else {
// StartService failed
TCHAR szErr[256];
_tprintf(TEXT("\n%s failed to start: %s\n"), m_lpDisplayName, GetLastErrorText(szErr,256));
}
::CloseServiceHandle(schService);
} else {
TCHAR szErr[256];
_tprintf(TEXT("OpenService failed - %s\n"), GetLastErrorText(szErr,256));
}
::CloseServiceHandle(schSCManager);
} else {
TCHAR szErr[256];
_tprintf(TEXT("OpenSCManager failed - %s\n"), GetLastErrorText(szErr,256));
}
return bRet;
}
////////////////////////////////////////////////////////////////////////////
//!! TCW MOD - faceless window procedure for usage within Win95 (mostly),
// but can be invoked under NT by using -f
LRESULT CALLBACK _FacelessWndProc_( HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) {
if (uMsg==WM_QUERYENDSESSION || uMsg==WM_ENDSESSION || uMsg==WM_QUIT) {
if (lParam==NULL || uMsg==WM_QUIT) {
DestroyWindow(hwnd); // kill me
if (AfxGetService()!=NULL)
AfxGetService()->Stop(); // stop me.
return TRUE;
}
}
return DefWindowProc(hwnd,uMsg,wParam,lParam);
}
////////////////////////////////////////////////////////////////////////////
BOOL CNTService :: DebugService(int argc, char ** argv, BOOL faceless) {
DWORD dwArgc;
LPTSTR *lpszArgv;
#ifdef UNICODE
lpszArgv = CommandLineToArgvW(GetCommandLineW(), &(dwArgc) );
#else
dwArgc = (DWORD) argc;
lpszArgv = argv;
#endif
if( !faceless ) { //!! TCW MOD - no faceless, so give it a face.
SetupConsole(); //!! TCW MOD - make the console for debugging
_tprintf(TEXT("Debugging %s.\n"), m_lpDisplayName);
SetConsoleCtrlHandler(ControlHandler, TRUE);
}
//!! TCW MOD START - if Win95, register server
typedef DWORD (WINAPI *fp_RegServProc)(DWORD dwProcessId,DWORD dwType);
fp_RegServProc fncptr=NULL;
if( faceless /*&& OsIsWin95()*/ ) {
WNDCLASS wndclass;
memset(&wndclass,0,sizeof(WNDCLASS));
wndclass.lpfnWndProc = _FacelessWndProc_;
wndclass.hInstance = HINSTANCE(::GetModuleHandle(0));
wndclass.lpszClassName = TEXT("RRL__FacelessWndProc_");
ATOM atom = ::RegisterClass(&wndclass);
HWND hwnd = ::CreateWindow(wndclass.lpszClassName,TEXT(""),0,0,0,0,0,0,0,wndclass.hInstance,0);
HMODULE hModule = ::GetModuleHandle(TEXT("kernel32.dll"));
// punch F1 on "RegisterServiceProcess" for what it does and when to use it.
fncptr=(fp_RegServProc)::GetProcAddress(hModule, "RegisterServiceProcess");
if (fncptr!=NULL)
(*fncptr)(0, RSP_SIMPLE_SERVICE);
}
//!! TCW MOD END - if Win95, register server
Run(dwArgc, lpszArgv);
#ifdef UNICODE
::GlobalFree(HGLOBAL)lpszArgv);
#endif
if (fncptr!=NULL) //!! TCW MOD - if it's there, remove it: our run is over
(*fncptr)(0, RSP_UNREGISTER_SERVICE);
return TRUE;
}
void CNTService :: Pause() {
}
void CNTService :: Continue() {
}
void CNTService :: Shutdown() {
}
/////////////////////////////////////////////////////////////////////////////
// class CNTService -- default handlers
char CNTService::m_szParam[32]; //wjh
void WINAPI CNTService :: ServiceMain(DWORD dwArgc, LPTSTR *lpszArgv) {
_ASSERTE( gpTheService != 0 );
if(dwArgc>=2) strncpy(m_szParam,lpszArgv[1],sizeof(m_szParam));
// register our service control handler:
gpTheService->m_sshStatusHandle = RegisterServiceCtrlHandler(
gpTheService->m_lpServiceName,
CNTService::ServiceCtrl
);
if( gpTheService->m_sshStatusHandle )
// report the status to the service control manager.
if( gpTheService->ReportStatus(SERVICE_START_PENDING) ){
gpTheService->Run( dwArgc, lpszArgv );}
// try to report the stopped status to the service control manager.
if( gpTheService->m_sshStatusHandle )
gpTheService->ReportStatus(SERVICE_STOPPED);
}
void WINAPI CNTService :: ServiceCtrl(DWORD dwCtrlCode) {
_ASSERTE( gpTheService != 0 );
// Handle the requested control code.
switch( dwCtrlCode ) {
case SERVICE_CONTROL_STOP:
// Stop the service.
gpTheService->m_ssStatus.dwCurrentState = SERVICE_STOP_PENDING;
gpTheService->Stop();
break;
case SERVICE_CONTROL_PAUSE:
gpTheService->m_ssStatus.dwCurrentState = SERVICE_PAUSE_PENDING;
gpTheService->Pause();
break;
case SERVICE_CONTROL_CONTINUE:
gpTheService->m_ssStatus.dwCurrentState = SERVICE_CONTINUE_PENDING;
gpTheService->Continue();
break;
case SERVICE_CONTROL_SHUTDOWN:
gpTheService->Shutdown();
break;
case SERVICE_CONTROL_INTERROGATE:
// Update the service status.
gpTheService->ReportStatus(gpTheService->m_ssStatus.dwCurrentState);
break;
default:
// invalid control code
break;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -