From 2b5b5c22f290e2fe2c87187fc43efdc93b847d68 Mon Sep 17 00:00:00 2001 From: Syping Date: Thu, 16 Jul 2020 20:38:56 +0200 Subject: [PATCH] Clean termination on *nix systems --- SMSubProcess.cpp | 19 +++++++++++++++++-- SMSubProcess.h | 1 + main.cpp | 33 +++++++++++++++++++++++++++++++++ 3 files changed, 51 insertions(+), 2 deletions(-) diff --git a/SMSubProcess.cpp b/SMSubProcess.cpp index 766665b..587908f 100644 --- a/SMSubProcess.cpp +++ b/SMSubProcess.cpp @@ -67,16 +67,31 @@ void SMSubProcess::processError(QProcess::ProcessError error) } } +void SMSubProcess::aboutToQuit() +{ + // Main process terminated + if (process.state() == QProcess::Running) { + process.terminate(); + if (!process.waitForFinished(60000)) { + QTextStream(stderr) << "Failed to terminate process!" << endl; + } + } +} + void SMSubProcess::killProcess() { // Kill process as requested - process.kill(); + if (process.state() == QProcess::Running) { + process.kill(); + } } void SMSubProcess::stopProcess() { // Terminate process as requested - process.terminate(); + if (process.state() == QProcess::Running) { + process.terminate(); + } } void SMSubProcess::writeInput(const QByteArray &input) diff --git a/SMSubProcess.h b/SMSubProcess.h index 83289f5..fa98e06 100644 --- a/SMSubProcess.h +++ b/SMSubProcess.h @@ -33,6 +33,7 @@ private: QProcess process; public slots: + void aboutToQuit(); void killProcess(); void stopProcess(); void writeInput(const QByteArray &input); diff --git a/main.cpp b/main.cpp index 5ccb185..85646e1 100644 --- a/main.cpp +++ b/main.cpp @@ -30,12 +30,44 @@ #include "SMSubServer.h" #include "smsub.h" +#ifdef Q_OS_UNIX +#include +#include "signal.h" +#include "unistd.h" +#endif + +#ifdef Q_OS_UNIX +void catchUnixSignals(std::initializer_list quitSignals) { + auto handler = [](int sig) -> void { + QTextStream(stderr) << "Received Unix signal: " << sig << endl; + QCoreApplication::quit(); + }; + + sigset_t blocking_mask; + sigemptyset(&blocking_mask); + for (auto sig : quitSignals) + sigaddset(&blocking_mask, sig); + + struct sigaction sa; + sa.sa_handler = handler; + sa.sa_mask = blocking_mask; + sa.sa_flags = 0; + + for (auto sig : quitSignals) + sigaction(sig, &sa, nullptr); +} +#endif + int main(int argc, char *argv[]) { QCoreApplication a(argc, argv); a.setApplicationName("Server Manager Subprocess"); a.setApplicationVersion("0.1"); +#ifdef Q_OS_UNIX + catchUnixSignals({SIGQUIT, SIGINT, SIGTERM, SIGHUP}); +#endif + QCommandLineParser commandLineParser; commandLineParser.addHelpOption(); commandLineParser.addVersionOption(); @@ -148,6 +180,7 @@ int main(int argc, char *argv[]) QObject::connect(&subServer, SIGNAL(inputWritten(QByteArray)), &subProcess, SLOT(writeInput(QByteArray))); QObject::connect(&subServer, SIGNAL(killRequested()), &subProcess, SLOT(killProcess())); QObject::connect(&subServer, SIGNAL(stopRequested()), &subProcess, SLOT(stopProcess())); + QObject::connect(&a, SIGNAL(aboutToQuit()), &subProcess, SLOT(aboutToQuit())); subProcess.start();