Imported Upstream version 0.3.3
[anytun.git] / src / win32 / winService.cpp
index 1b7c9f8..8c17420 100644 (file)
 #include "../anytunError.h"\r
 #include "../threadUtils.hpp"\r
 \r
-WinService* WinService::inst = NULL;\r
-Mutex WinService::instMutex;\r
-WinService& gWinService = WinService::instance();\r
-\r
-WinService& WinService::instance()\r
-{\r
-       Lock lock(instMutex);\r
-       static instanceCleaner c;\r
-       if(!inst)\r
-               inst = new WinService();\r
-       \r
-       return *inst;\r
-}\r
-\r
-WinService::~WinService()\r
-{\r
-  if(started_)\r
-    CloseHandle(stop_event_);\r
-}\r
-\r
 void WinService::install()\r
 {\r
   SC_HANDLE schSCManager;\r
@@ -125,75 +105,54 @@ void WinService::start()
     AnytunError::throwErr() << "Error on StartServiceCtrlDispatcher: " << AnytunErrno(GetLastError());\r
 }\r
 \r
-void WinService::waitForStop()\r
-{\r
-  if(!started_)\r
-    AnytunError::throwErr() << "Service not started correctly";\r
-  \r
-  reportStatus(SERVICE_RUNNING, NO_ERROR);\r
-  WaitForSingleObject(stop_event_, INFINITE);\r
-  reportStatus(SERVICE_STOP_PENDING, NO_ERROR);\r
-  cLog.msg(Log::PRIO_NOTICE) << "WinService received stop signal, exitting";\r
-}\r
-\r
-void WinService::stop()\r
-{\r
-  if(!started_)\r
-    AnytunError::throwErr() << "Service not started correctly";\r
-\r
-  reportStatus(SERVICE_STOPPED, NO_ERROR);\r
-}\r
-\r
-int real_main(int argc, char* argv[]);\r
+int real_main(int argc, char* argv[], WinService& service);\r
 \r
 VOID WINAPI WinService::main(DWORD dwArgc, LPTSTR *lpszArgv)\r
 {\r
-  if(gWinService.started_) {\r
-    cLog.msg(Log::PRIO_ERROR) << "Service is already running";\r
-    return;\r
-  }\r
+  WinService service;\r
 \r
-  gWinService.status_handle_ = RegisterServiceCtrlHandlerA(SVC_NAME, WinService::ctrlHandler);\r
-  if(!gWinService.status_handle_) { \r
+  service.status_handle_ = RegisterServiceCtrlHandlerA(SVC_NAME, WinService::ctrlHandler);\r
+  if(!service.status_handle_) { \r
     cLog.msg(Log::PRIO_ERROR) << "Error on RegisterServiceCtrlHandler: " << AnytunErrno(GetLastError());\r
     return;\r
   }\r
-  gWinService.status_.dwServiceType = SERVICE_WIN32_OWN_PROCESS; \r
-  gWinService.status_.dwServiceSpecificExitCode = 0;    \r
-  gWinService.reportStatus(SERVICE_START_PENDING, NO_ERROR);\r
-  gWinService.started_ = true;\r
+  service.status_.dwServiceType = SERVICE_WIN32_OWN_PROCESS; \r
+  service.status_.dwServiceSpecificExitCode = 0;    \r
+  service.reportStatus(SERVICE_START_PENDING, NO_ERROR);\r
   \r
-  gWinService.stop_event_ = CreateEvent(NULL, true, false, NULL);\r
-  if(!gWinService.stop_event_) {\r
-    cLog.msg(Log::PRIO_ERROR) << "WinService Error on CreateEvent: " << AnytunErrno(GetLastError());\r
-    gWinService.reportStatus(SERVICE_STOPPED, -1);\r
-    return;\r
-  }\r
-\r
-  real_main(dwArgc, lpszArgv);\r
+  real_main(dwArgc, lpszArgv, service);\r
+  \r
+  service.reportStatus(SERVICE_STOPPED, NO_ERROR);\r
 }\r
 \r
 VOID WINAPI WinService::ctrlHandler(DWORD dwCtrl)\r
 {\r
-  switch(dwCtrl) {\r
+  gSignalController.inject(dwCtrl);\r
+}\r
+\r
+int WinService::handleCtrlSignal(int sig, const std::string& msg)\r
+{\r
+  switch(sig) {\r
     case SERVICE_CONTROL_STOP: {\r
-      gWinService.reportStatus(SERVICE_STOP_PENDING, NO_ERROR);\r
-      SetEvent(gWinService.stop_event_);\r
-      return;\r
+      reportStatus(SERVICE_STOP_PENDING, NO_ERROR);\r
+      cLog.msg(Log::PRIO_NOTICE) << "received service stop signal, exitting";\r
+      return 1;\r
     }\r
     case SERVICE_CONTROL_INTERROGATE: break;\r
     default: break;\r
   }\r
-  gWinService.reportStatus(gWinService.status_.dwCurrentState, NO_ERROR);\r
+  reportStatus(status_.dwCurrentState, NO_ERROR);\r
+\r
+  return 0;\r
 }\r
 \r
-void WinService::reportStatus(DWORD dwCurrentState, DWORD dwWin32ExitCode, DWORD dwWaitHint)\r
+void WinService::reportStatus(DWORD dwCurrentState, DWORD dwWin32ExitCode)\r
 {\r
   static DWORD dwCheckPoint = 1;\r
 \r
   status_.dwCurrentState = dwCurrentState;\r
   status_.dwWin32ExitCode = dwWin32ExitCode;\r
-  status_.dwWaitHint = dwWaitHint;\r
+  status_.dwWaitHint = 0;\r
 \r
   if((dwCurrentState == SERVICE_START_PENDING) ||\r
      (dwCurrentState == SERVICE_STOP_PENDING))\r
@@ -210,4 +169,29 @@ void WinService::reportStatus(DWORD dwCurrentState, DWORD dwWin32ExitCode, DWORD
   SetServiceStatus(status_handle_, &status_);\r
 }\r
 \r
+void WinService::initPrivs(std::string const& username, std::string const& groupname)\r
+{\r
+// nothing here\r
+}\r
+\r
+void WinService::dropPrivs()\r
+{\r
+// nothing here\r
+}\r
+\r
+void WinService::chroot(std::string const& dir)\r
+{\r
+// nothing here\r
+}\r
+\r
+void WinService::daemonize()\r
+{\r
+// nothing here\r
+}\r
+\r
+bool WinService::isDaemonized()\r
+{\r
+  return true;\r
+}\r
+\r
 #endif\r