summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/Makefile1
-rw-r--r--src/rharchive.c16
-rw-r--r--src/sig_handler.c111
-rw-r--r--src/sig_handler.h37
4 files changed, 156 insertions, 9 deletions
diff --git a/src/Makefile b/src/Makefile
index 79c2a82..ba2f19a 100644
--- a/src/Makefile
+++ b/src/Makefile
@@ -32,6 +32,7 @@ endif
EXECUTABLE := rharchive
C_OBJS := log.o \
+ sig_handler.o \
options.o \
slist.o \
string_list.o \
diff --git a/src/rharchive.c b/src/rharchive.c
index 6ab1538..dc3c552 100644
--- a/src/rharchive.c
+++ b/src/rharchive.c
@@ -48,7 +48,7 @@ static gboolean bus_call(GstBus *bus, GstMessage *msg, gpointer data)
switch (GST_MESSAGE_TYPE(msg)) {
case GST_MESSAGE_EOS: {
log_printf(NOTICE, "End of stream");
- g_main_loop_quit (loop);
+ g_main_loop_quit(loop);
break;
}
case GST_MESSAGE_ERROR: {
@@ -77,7 +77,7 @@ int main_loop(options_t* opt)
GstElement *pipeline, *source, *encoder, *muxer, *sink;
GstBus *bus;
- loop = g_main_loop_new (NULL, FALSE);
+ loop = g_main_loop_new(NULL, FALSE);
pipeline = gst_pipeline_new("rharchive");
source = gst_element_factory_make("audiotestsrc", "raw-source");
@@ -101,7 +101,9 @@ int main_loop(options_t* opt)
log_printf(INFO, "Set State: Playing");
gst_element_set_state(pipeline, GST_STATE_PLAYING);
- g_main_loop_run (loop);
+ signal_start(loop);
+ g_main_loop_run(loop);
+ signal_stop();
log_printf(INFO, "Stopping pipeline");
gst_element_set_state (pipeline, GST_STATE_NULL);
@@ -199,6 +201,7 @@ int main(int argc, char* argv[])
fclose(pid_file);
}
+ signal_init();
gst_init(NULL, NULL);
const gchar *nano_str;
guint major, minor, micro, nano;
@@ -215,12 +218,7 @@ int main(int argc, char* argv[])
options_clear(&opt);
- if(!ret)
- log_printf(NOTICE, "normal shutdown");
- else if(ret < 0)
- log_printf(NOTICE, "shutdown after error");
- else
- log_printf(NOTICE, "shutdown after signal");
+ log_printf(NOTICE, "rharchive shutdown");
gst_deinit();
log_close();
diff --git a/src/sig_handler.c b/src/sig_handler.c
new file mode 100644
index 0000000..e2afb17
--- /dev/null
+++ b/src/sig_handler.c
@@ -0,0 +1,111 @@
+/*
+ * rharchive
+ *
+ * rharchive is a simple tcp connection proxy which combines the
+ * features of rinetd and 6tunnel. rharchive supports IPv4 and
+ * IPv6 and also supports connections from IPv6 to IPv4
+ * endpoints and vice versa.
+ *
+ *
+ * Copyright (C) 2010-2011 Christian Pointner <equinox@helsinki.at>
+ *
+ * This file is part of rharchive.
+ *
+ * rharchive is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * any later version.
+ *
+ * rharchive is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with rharchive. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "datatypes.h"
+
+#include "log.h"
+
+#include "sig_handler.h"
+
+#include <glib.h>
+#include <errno.h>
+
+static GThread *signal_thread;
+
+void signal_init()
+{
+ sigset_t signal_set;
+
+ sigemptyset(&signal_set);
+ sigaddset(&signal_set, SIGINT);
+ sigaddset(&signal_set, SIGQUIT);
+ sigaddset(&signal_set, SIGHUP);
+ sigaddset(&signal_set, SIGTERM);
+ sigaddset(&signal_set, SIGUSR1);
+ sigaddset(&signal_set, SIGUSR2);
+
+ pthread_sigmask(SIG_BLOCK, &signal_set, NULL);
+}
+
+static gpointer signal_thread_func(gpointer data)
+{
+ GMainLoop *loop = (GMainLoop *)data;
+
+ struct timespec timeout;
+ sigset_t signal_set;
+ int sig_num;
+ for(;;) {
+ sigemptyset(&signal_set);
+ sigaddset(&signal_set, SIGINT);
+ sigaddset(&signal_set, SIGQUIT);
+ sigaddset(&signal_set, SIGHUP);
+ sigaddset(&signal_set, SIGTERM);
+ sigaddset(&signal_set, SIGUSR1);
+ sigaddset(&signal_set, SIGUSR2);
+ timeout.tv_sec = 1;
+ timeout.tv_nsec = 0;
+ sig_num = sigtimedwait(&signal_set, NULL, &timeout);
+ if(sig_num == -1) {
+ if(errno != EINTR && errno != EAGAIN) {
+ log_printf(ERROR, "sigwait failed with error: %d, signal handling will be disabled", errno);
+ break;
+ }
+ } else {
+ switch(sig_num) {
+ case SIGTERM:
+ case SIGINT:
+ case SIGQUIT: {
+ log_printf(NOTICE, "signal %d received, exiting", sig_num);
+ g_main_loop_quit(loop);
+ break;
+ }
+ default: {
+ log_printf(NOTICE, "signal %d received, ignoring", sig_num);
+ break;
+ }
+ }
+ }
+ }
+
+ return NULL;
+}
+
+int signal_start(GMainLoop *loop)
+{
+ g_assert(!signal_thread);
+
+ signal_thread = g_thread_create_full(signal_thread_func, loop, 8192,TRUE, TRUE, G_THREAD_PRIORITY_HIGH, NULL);
+ if(!signal_thread)
+ return -1;
+
+ return 0;
+}
+
+void signal_stop()
+{
+ // nothing yet..
+}
diff --git a/src/sig_handler.h b/src/sig_handler.h
new file mode 100644
index 0000000..dee9589
--- /dev/null
+++ b/src/sig_handler.h
@@ -0,0 +1,37 @@
+/*
+ * rharchive
+ *
+ * rharchive is a simple tcp connection proxy which combines the
+ * features of rinetd and 6tunnel. rharchive supports IPv4 and
+ * IPv6 and also supports connections from IPv6 to IPv4
+ * endpoints and vice versa.
+ *
+ *
+ * Copyright (C) 2010-2011 Christian Pointner <equinox@helsinki.at>
+ *
+ * This file is part of rharchive.
+ *
+ * rharchive is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * any later version.
+ *
+ * rharchive is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with rharchive. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef RHARCHIVE_sig_handler_h_INCLUDED
+#define RHARCHIVE_sig_handler_h_INCLUDED
+
+#include <glib.h>
+
+void signal_init();
+int signal_start(GMainLoop *loop);
+void signal_stop();
+
+#endif