Shutting down a server thats running as a background service

Hello Community (and hopeful developers too)

In short, same Problem as described here: forums. funcom. com /t/problem-on-shutdown-the-server-when-the-server-is-installed-as-an-windows-service/10047

my server is installed as a windows service using a third party service manager ( nssm in this case)
as in the post referenced above the server process is just being killed instead performing a controlled shutdown despite getting the correct stop signal.

First question: is there a debug setting that will log what exact signal (SIGINT / SIGTERM etc.) has been recieved by the process to trigger the shutdown/kill?

Second question: is there or will there be a ingame-console function to trigger a controlled shutdown just like when pressing Ctrl + C in the cmd window?
[EDIT]sub question: also available via rcon?

Third question:
will there be a version of the ConanSandboxServer.exe that is able to be handled by the windows service control itself?

I am aware of the existence of the dedicated server launcher but i prefer my machine just running the server-service without having the need for a logged on user and/or another piece of software

For completeness:
The steam workshop mod “pippi server and user management” (880454836) does offer a ingame chat command and a command that can be run through an rcon connection to shut down the server, however they only work when there is at least one player logged on, they dont work on empty servers.

So the main Problem persists: how do i shut down my background service server when no user is able to log on due to version mismatches (either game or mods)

A possible solution would be some kind of minimal game client thats just creating a logged in player instnce on the server to enable the rcon commands to be used through that.

I believe the only way at the moment to get the server to cleanly close is to send it a WM_QUIT or WM_CLOSE message.

In the Dedicated Server Launcher tool, I actually use this code:

void DedicatedServerLauncher::ShutdownGameServer()
{
  DW_Print(INFOL_IMPORTANT, e_DedicatedServerLauncher, "Shutting down the game server");

  // http://stanislavs.org/stopping-command-line-applications-programatically-with-ctrl-c-events-from-net/
  HWND handle = dw::win32::FindProcessMainWindow(m_ServerProcessId);
  if (handle)
  {
    PostMessage(handle, WM_CLOSE, 0, 0);
    m_ServerShuttingDown = true;
  }
}

not sure if that will help you, but that’s all I have at the moment :slight_smile:

2 Likes

OK, thanks for the info.
nssm first sends a Ctrl + C which i believe is translated into SIGINT and then after a user set timeout it moves on to send WM_QUIT.
I’ll try disabling the initial Ctrl-C and have nssm sending WM-Quit directly and see if that changes anything…

EDIT: nope, didn’t, its still killing all handles immediately after doing “nssm stop ceds”

I did some digging and found this on a blog posts comment, it looks promising but i havent been writing programs in ages and have no idea to implement this into a helper program that finds my dedicated server process and performs this operation.

the idea is to start another console application, attach it to the target process, disable the listening for ctrl+c on that new application and then generate that very signal which should result in initiating the graceful shutdown of the target application.

  private static void StopProgramByAttachingToItsConsoleAndIssuingCtrlCEvent(Process process, int waitForExitTimeout = 2000)
        {
            if (!AttachConsole((uint) process.Id))
            {
                return;
            }

            // Disable Ctrl-C handling for our program
            SetConsoleCtrlHandler(null, true);

            // Sent Ctrl-C to the attached console
            GenerateConsoleCtrlEvent(CtrlTypes.CTRL_C_EVENT, 0);

            // Wait for the graceful end of the process.
            // If the process will not exit in time specified by 'waitForExitTimeout', the process will be killed
            using (new Timer((dummy => {if (!process.HasExited) process.Kill(); }), null, waitForExitTimeout, Timeout.Infinite))
            {
                // Must wait here. If we don't wait and re-enable Ctrl-C handling below too fast, we might terminate ourselves.
                process.WaitForExit();    
            }

            FreeConsole();

            // Re-enable Ctrl-C handling or any subsequently started programs will inherit the disabled state.
            SetConsoleCtrlHandler(null, false);
        }
reference: stanislavs. org / stopping-command-line-applications-programatically-with-ctrl-c-events-from-net/#comment-2880

when i’m using the pippi command via rcon it takes around 4 minutes for the graceful shutdown from issuing the command to last instance of sandboxserver.exe disappearing from the process list (getting marked as exited)

1 Like

Interesting.

Have to see if that would work from a Win32 GUI C++ application, could be an alternate way to stop the program I guess.

The core problem seems to be that background services do not have windows and therefore WM_QUIT wont work since its a window manager command.