aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPau Espin Pedrol <pespin@sysmocom.de>2019-03-29 19:20:06 +0100
committerPau Espin Pedrol <pespin@sysmocom.de>2019-03-29 19:20:08 +0100
commit21032b75c00710ab30a0a74a4006608a58295d99 (patch)
tree51a75dc753487f5b880df32f370d5dd0f724fe39
parentd01c7b98b63dfda1e72e289eccd7a384c658069f (diff)
osmo-trx: Use signalfd to serialize signals in main thread ctx
This should avoid prolematic scenarios where different signal handlers are running on different thread in parallel. Furthermore, we make sure those signals are always run by main loop thread. Change-Id: I9b9d9793be9af11dbe433e0ce09b7ac57a3bdfb5
-rw-r--r--Transceiver52M/osmo-trx.cpp51
1 files changed, 46 insertions, 5 deletions
diff --git a/Transceiver52M/osmo-trx.cpp b/Transceiver52M/osmo-trx.cpp
index 0141810..88b9de0 100644
--- a/Transceiver52M/osmo-trx.cpp
+++ b/Transceiver52M/osmo-trx.cpp
@@ -34,6 +34,7 @@
#include <string>
#include <sstream>
#include <iostream>
+#include <sys/signalfd.h>
#include <GSMCommon.h>
#include <Logger.h>
@@ -66,6 +67,7 @@ extern "C" {
static char* config_file = (char*)DEFAULT_CONFIG_FILE;
+struct osmo_fd signal_ofd;
volatile bool gshutdown = false;
static void *tall_trx_ctx;
@@ -185,20 +187,57 @@ static void sig_handler(int signo)
case SIGUSR2:
talloc_report_full(tall_trx_ctx, stderr);
break;
+ case SIGHUP:
+ log_targets_reopen();
default:
break;
}
+
+}
+
+static int signalfd_callback(struct osmo_fd *ofd, unsigned int what)
+{
+ struct signalfd_siginfo fdsi;
+ ssize_t s;
+
+ s = read(ofd->fd, &fdsi, sizeof(struct signalfd_siginfo));
+ if (s < 0) {
+ LOG(FATAL) << "Failed to read from signalfd ("<< ofd->fd << "): " << errno;
+ gshutdown = true;
+ return 0;
+ }
+ sig_handler(fdsi.ssi_signo);
+ return 0;
}
static void setup_signal_handlers()
{
- /* Handle keyboard interrupt SIGINT */
- signal(SIGINT, &sig_handler);
- signal(SIGTERM, &sig_handler);
+ sigset_t set;
+ int sfd;
+
signal(SIGABRT, &sig_handler);
- signal(SIGUSR1, &sig_handler);
- signal(SIGUSR2, &sig_handler);
osmo_init_ignore_signals();
+
+ /* Other threads created by this thread (main) will inherit a copy of the
+ signal mask. */
+ sigemptyset(&set);
+ sigaddset(&set, SIGINT);
+ sigaddset(&set, SIGTERM);
+ sigaddset(&set, SIGUSR1);
+ sigaddset(&set, SIGUSR2);
+ sigaddset(&set, SIGHUP);
+ if (pthread_sigmask(SIG_BLOCK, &set, NULL)) {
+ fprintf(stderr, "pthread_sigmask() failed.\n");
+ exit(EXIT_FAILURE);
+ }
+
+ if ((sfd = signalfd(-1, &set, 0)) == -1) {
+ fprintf(stderr, "signalfd() failed (%d).\n", errno);
+ exit(EXIT_FAILURE);
+ }
+
+ osmo_fd_setup(&signal_ofd, sfd, OSMO_FD_READ, signalfd_callback, NULL, 0);
+ osmo_fd_register(&signal_ofd);
}
static void print_help()
@@ -594,5 +633,7 @@ int main(int argc, char *argv[])
trx_stop();
+ osmo_fd_unregister(&signal_ofd);
+ osmo_fd_close(&signal_ofd);
return 0;
}