diff --git a/DAPNETGateway.cpp b/DAPNETGateway.cpp index a66b521..71e8ee1 100644 --- a/DAPNETGateway.cpp +++ b/DAPNETGateway.cpp @@ -1,5 +1,5 @@ /* -* Copyright (C) 2018,2020 by Jonathan Naylor G4KLX +* Copyright (C) 2018,2020,2024 by Jonathan Naylor G4KLX * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -43,6 +43,17 @@ const char* DEFAULT_INI_FILE = "DAPNETGateway.ini"; const char* DEFAULT_INI_FILE = "/etc/DAPNETGateway.ini"; #endif +static bool m_killed = false; +static int m_signal = 0; + +#if !defined(_WIN32) && !defined(_WIN64) +static void sigHandler(int signum) +{ + m_killed = true; + m_signal = signum; +} +#endif + #include #include @@ -93,11 +104,40 @@ int main(int argc, char** argv) } } - CDAPNETGateway* gateway = new CDAPNETGateway(std::string(iniFile)); +#if !defined(_WIN32) && !defined(_WIN64) + ::signal(SIGINT, sigHandler); + ::signal(SIGTERM, sigHandler); + ::signal(SIGHUP, sigHandler); +#endif - int ret = gateway->run(); + int ret = 0; - delete gateway; + do { + m_signal = 0; + m_killed = false; + + CDAPNETGateway* gateway = new CDAPNETGateway(std::string(iniFile)); + ret = gateway->run(); + + delete gateway; + + switch (m_signal) { + case 2: + ::LogInfo("DAPNETGateway-%s exited on receipt of SIGINT", VERSION); + break; + case 15: + ::LogInfo("DAPNETGateway-%s exited on receipt of SIGTERM", VERSION); + break; + case 1: + ::LogInfo("DAPNETGateway-%s is restarting on receipt of SIGHUP", VERSION); + break; + default: + ::LogInfo("DAPNETGateway-%s exited on receipt of an unknown signal", VERSION); + break; + } + } while (m_signal == 1); + + ::LogFinalise(); return ret; } @@ -146,7 +186,7 @@ int CDAPNETGateway::run() pid_t pid = ::fork(); if (pid == -1) { ::fprintf(stderr, "Couldn't fork() , exiting\n"); - return -1; + return 1; } else if (pid != 0) { exit(EXIT_SUCCESS); } @@ -154,13 +194,13 @@ int CDAPNETGateway::run() // Create new session and process group if (::setsid() == -1) { ::fprintf(stderr, "Couldn't setsid(), exiting\n"); - return -1; + return 1; } // Set the working directory to the root directory if (::chdir("/") == -1) { ::fprintf(stderr, "Couldn't cd /, exiting\n"); - return -1; + return 1; } // If we are currently root... @@ -168,7 +208,7 @@ int CDAPNETGateway::run() struct passwd* user = ::getpwnam("mmdvm"); if (user == NULL) { ::fprintf(stderr, "Could not get the mmdvm user, exiting\n"); - return -1; + return 1; } uid_t mmdvm_uid = user->pw_uid; @@ -177,18 +217,18 @@ int CDAPNETGateway::run() // Set user and group ID's to mmdvm:mmdvm if (setgid(mmdvm_gid) != 0) { ::fprintf(stderr, "Could not set mmdvm GID, exiting\n"); - return -1; + return 1; } if (setuid(mmdvm_uid) != 0) { ::fprintf(stderr, "Could not set mmdvm UID, exiting\n"); - return -1; + return 1; } // Double check it worked (AKA Paranoia) if (setuid(0) != -1) { ::fprintf(stderr, "It's possible to regain root - something is wrong!, exiting\n"); - return -1; + return 1; } } } @@ -223,8 +263,6 @@ int CDAPNETGateway::run() ret = m_pocsagNetwork->open(); if (!ret) { ::LogError("Cannot open the repeater network port"); - ::LogFinalise(); - return 1; } @@ -235,8 +273,6 @@ int CDAPNETGateway::run() if (dapnetAuthKey.length() == 0 || dapnetAuthKey == "TOPSECRET") { ::LogError("AuthKey not set or invalid"); - ::LogFinalise(); - return 1; } @@ -248,7 +284,6 @@ int CDAPNETGateway::run() delete m_dapnetNetwork; ::LogError("Cannot open the DAPNET network port"); - ::LogFinalise(); return 1; } @@ -263,7 +298,6 @@ int CDAPNETGateway::run() delete m_dapnetNetwork; ::LogError("Cannot login to the DAPNET network"); - ::LogFinalise(); return 1; } @@ -285,7 +319,7 @@ int CDAPNETGateway::run() regexWhitelist = m_regexWhitelist->get(); - for (;;) { + while (!m_killed) { unsigned char buffer[200U]; if (m_pocsagNetwork->read(buffer) > 0U) { @@ -400,8 +434,6 @@ int CDAPNETGateway::run() m_dapnetNetwork->close(); delete m_dapnetNetwork; - ::LogFinalise(); - return 0; }