summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/win32service.h11
-rw-r--r--src/inspircd.cpp2
-rw-r--r--win/configureVC80.vcproj45
-rw-r--r--win/inspircdVC80.vcproj4
-rw-r--r--win/inspircd_win32wrapper.h2
-rw-r--r--win/win32service.cpp56
6 files changed, 83 insertions, 37 deletions
diff --git a/include/win32service.h b/include/win32service.h
new file mode 100644
index 000000000..93c9c8e09
--- /dev/null
+++ b/include/win32service.h
@@ -0,0 +1,11 @@
+#ifndef _WIN32SERVICE_H_
+#define _WIN32SERVICE_H_
+
+/* Hook for win32service.cpp to exit properly with the service specific error code */
+#define exit(a) newexit(a)
+void newexit(int status);
+
+/* Marks the service as running, not called until the config is parsed */
+void SetServiceRunning();
+
+#endif \ No newline at end of file
diff --git a/src/inspircd.cpp b/src/inspircd.cpp
index 0efbd293a..dab49ddf0 100644
--- a/src/inspircd.cpp
+++ b/src/inspircd.cpp
@@ -719,6 +719,8 @@ InspIRCd::InspIRCd(int argc, char** argv)
WindowsForkKillOwner(this);
FreeConsole();
}
+ /* Set win32 service as running, if we are running as a service */
+ SetServiceRunning();
#endif
Logs->Log("STARTUP", DEFAULT, "Startup complete as '%s'[%s], %d max open sockets", Config->ServerName,Config->GetSID().c_str(), SE->GetMaxFds());
diff --git a/win/configureVC80.vcproj b/win/configureVC80.vcproj
index 547091660..f9f23ed54 100644
--- a/win/configureVC80.vcproj
+++ b/win/configureVC80.vcproj
@@ -98,9 +98,9 @@
/>
</Configuration>
<Configuration
- Name="Debug|x64"
+ Name="Release|Win32"
OutputDirectory="."
- IntermediateDirectory="x64Debug_Configure"
+ IntermediateDirectory="Release"
ConfigurationType="1"
InheritedPropertySheets="$(VCInstallDir)VCProjectDefaults\UpgradeFromVC71.vsprops"
CharacterSet="2"
@@ -119,18 +119,18 @@
/>
<Tool
Name="VCMIDLTool"
- TargetEnvironment="3"
/>
<Tool
Name="VCCLCompilerTool"
+ AdditionalOptions="/I:&quot;include&quot;"
Optimization="0"
- PreprocessorDefinitions="WIN32;_DEBUG;_WINDOWS;WIN64"
+ WholeProgramOptimization="true"
+ PreprocessorDefinitions="WIN32;NDEBUG;_WINDOWS"
MinimalRebuild="true"
- BasicRuntimeChecks="3"
- RuntimeLibrary="1"
+ RuntimeLibrary="2"
UsePrecompiledHeader="0"
WarningLevel="3"
- Detect64BitPortabilityProblems="true"
+ Detect64BitPortabilityProblems="false"
DebugInformationFormat="3"
/>
<Tool
@@ -144,12 +144,15 @@
/>
<Tool
Name="VCLinkerTool"
+ AdditionalDependencies="kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib"
OutputFile="$(OutDir)/configure.exe"
- LinkIncremental="2"
+ LinkIncremental="1"
GenerateDebugInformation="true"
- ProgramDatabaseFile="$(OutDir)/configure.pdb"
SubSystem="2"
- TargetMachine="17"
+ OptimizeReferences="2"
+ EnableCOMDATFolding="2"
+ LinkTimeCodeGeneration="1"
+ TargetMachine="1"
/>
<Tool
Name="VCALinkTool"
@@ -177,9 +180,9 @@
/>
</Configuration>
<Configuration
- Name="Release|Win32"
+ Name="Debug|x64"
OutputDirectory="."
- IntermediateDirectory="Release"
+ IntermediateDirectory="x64Debug_Configure"
ConfigurationType="1"
InheritedPropertySheets="$(VCInstallDir)VCProjectDefaults\UpgradeFromVC71.vsprops"
CharacterSet="2"
@@ -198,17 +201,18 @@
/>
<Tool
Name="VCMIDLTool"
+ TargetEnvironment="3"
/>
<Tool
Name="VCCLCompilerTool"
Optimization="0"
- WholeProgramOptimization="true"
- PreprocessorDefinitions="WIN32;NDEBUG;_WINDOWS"
+ PreprocessorDefinitions="WIN32;_DEBUG;_WINDOWS;WIN64"
MinimalRebuild="true"
- RuntimeLibrary="2"
+ BasicRuntimeChecks="3"
+ RuntimeLibrary="1"
UsePrecompiledHeader="0"
WarningLevel="3"
- Detect64BitPortabilityProblems="false"
+ Detect64BitPortabilityProblems="true"
DebugInformationFormat="3"
/>
<Tool
@@ -222,15 +226,12 @@
/>
<Tool
Name="VCLinkerTool"
- AdditionalDependencies="kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib"
OutputFile="$(OutDir)/configure.exe"
- LinkIncremental="1"
+ LinkIncremental="2"
GenerateDebugInformation="true"
+ ProgramDatabaseFile="$(OutDir)/configure.pdb"
SubSystem="2"
- OptimizeReferences="2"
- EnableCOMDATFolding="2"
- LinkTimeCodeGeneration="1"
- TargetMachine="1"
+ TargetMachine="17"
/>
<Tool
Name="VCALinkTool"
diff --git a/win/inspircdVC80.vcproj b/win/inspircdVC80.vcproj
index 263c597ff..aee4dcbde 100644
--- a/win/inspircdVC80.vcproj
+++ b/win/inspircdVC80.vcproj
@@ -730,6 +730,10 @@
>
</File>
<File
+ RelativePath="..\include\win32service.h"
+ >
+ </File>
+ <File
RelativePath="..\include\xline.h"
>
</File>
diff --git a/win/inspircd_win32wrapper.h b/win/inspircd_win32wrapper.h
index 94f799c18..89309fbc9 100644
--- a/win/inspircd_win32wrapper.h
+++ b/win/inspircd_win32wrapper.h
@@ -18,6 +18,8 @@
#ifndef INSPIRCD_WIN32WRAPPER_H
#define INSPIRCD_WIN32WRAPPER_H
+#include "win32service.h"
+
/* Define the WINDOWS macro. This means we're building on windows to the rest of the server.
I think this is more reasonable than using WIN32, especially if we're gonna be doing 64-bit compiles */
#define WINDOWS 1
diff --git a/win/win32service.cpp b/win/win32service.cpp
index 0fb94f3e4..5923c1458 100644
--- a/win/win32service.cpp
+++ b/win/win32service.cpp
@@ -40,6 +40,16 @@ struct Commandline
/* A function pointer for dynamic linking tricks */
SETSERVDESC ChangeServiceConf;
+bool IsAService();
+{
+ USEROBJECTFLAGS uoflags;
+ HWINSTA winstation = GetProcessWindowStation();
+ if (GetUserObjectInformation(winstation, UOI_FLAGS, &uoflags, sizeof(uoflags), NULL))
+ return ((uoflags.dwFlags & WSF_VISIBLE) == 0);
+ else
+ return false;
+}
+
/* Kills the service by setting an event which the other thread picks up and exits */
void KillService()
{
@@ -61,6 +71,22 @@ DWORD WINAPI WorkerThread(LPDWORD param)
return 0;
}
+/* This is called when all startup is done */
+void SetServiceRunning()
+{
+ if (!IsAService())
+ return;
+
+ serviceCurrentStatus = SERVICE_RUNNING;
+ success = UpdateSCMStatus(SERVICE_RUNNING, NO_ERROR, 0, 0, 0);
+ if (!success)
+ {
+ terminateService(6, GetLastError());
+ return;
+ }
+}
+
+
/** Starts the worker thread above */
void StartServiceThread()
{
@@ -110,10 +136,22 @@ BOOL UpdateSCMStatus (DWORD dwCurrentState, DWORD dwWin32ExitCode, DWORD dwServi
/** This function is called by us when the service is being shut down or when it can't be started */
void terminateService (int code, int wincode)
{
- UpdateSCMStatus(SERVICE_STOPPED,wincode?wincode:ERROR_SERVICE_SPECIFIC_ERROR,(wincode)?0:code,0,0);
+ UpdateSCMStatus(SERVICE_STOPPED, wincode ? wincode : ERROR_SERVICE_SPECIFIC_ERROR, wincode ? 0 : code, 0, 0);
return;
}
+/* In windows we hook this to exit() */
+void newexit(int status)
+{
+ if (!IsAService())
+ exit(status);
+
+ /* Are we running as a service? If so, trigger the service specific exit code */
+ terminateService(status, 0);
+ KillService();
+ exit(status);
+}
+
/** This callback is called by windows when the state of the service has been changed */
VOID ServiceCtrlHandler (DWORD controlCode)
{
@@ -171,13 +209,6 @@ VOID ServiceMain(DWORD argc, LPTSTR *argv)
}
StartServiceThread();
- serviceCurrentStatus = SERVICE_RUNNING;
- success = UpdateSCMStatus(SERVICE_RUNNING, NO_ERROR, 0, 0, 0);
- if (!success)
- {
- terminateService(6, GetLastError());
- return;
- }
WaitForSingleObject (killServiceEvent, INFINITE);
}
@@ -323,13 +354,8 @@ int main(int argc, char** argv)
/* Check if the process is running interactively. InspIRCd does not run interactively
* as a service so if this is true, we just run the non-service inspircd.
*/
- USEROBJECTFLAGS uoflags;
- HWINSTA winstation = GetProcessWindowStation();
- if (GetUserObjectInformation(winstation, UOI_FLAGS, &uoflags, sizeof(uoflags), NULL))
- {
- if (uoflags.dwFlags == WSF_VISIBLE)
- return smain(argc, argv);
- }
+ if (!IsAService())
+ return smain(argv, argc);
/* If we get here, we know the service is installed so we can start it */