]> git.meshlink.io Git - meshlink/commitdiff
Use atomic operations to check whether to write to the signal pipe.
authorGuus Sliepen <guus@meshlink.io>
Thu, 11 Jun 2020 19:52:00 +0000 (21:52 +0200)
committerGuus Sliepen <guus@meshlink.io>
Thu, 11 Jun 2020 20:22:58 +0000 (22:22 +0200)
We need to do an atomic test-and-set operation to check whether we can
avoid writing to the signal pipe. Use C11 atomics to do this in a portable
way (hopefully).

configure.ac
src/event.c
src/event.h
src/have.h

index cfef2a11362b7b411ad9face45cb0a1f477969d4..f0617f3206de57c1f8ccb6de7e785a2f8207990c 100644 (file)
@@ -54,6 +54,8 @@ if test -d /sw/lib ; then
   LIBS="$LIBS -L/sw/lib"
 fi
 
   LIBS="$LIBS -L/sw/lib"
 fi
 
+AX_CHECK_COMPILE_FLAG([-std=c11], [CPPFLAGS="-std=c11"])
+
 dnl Compiler hardening flags
 dnl No -fstack-protector-all because it doesn't work on all platforms or architectures.
 
 dnl Compiler hardening flags
 dnl No -fstack-protector-all because it doesn't work on all platforms or architectures.
 
index 5e9763e2702835672c760d93115787308726dab6..43e4e0401d941601b0ffc3818720655a0edc505c 100644 (file)
@@ -199,7 +199,7 @@ static void signalio_handler(event_loop_t *loop, void *data, int flags) {
        });
 
        if(sig) {
        });
 
        if(sig) {
-               sig->set = false;
+               atomic_flag_clear(&sig->set);
                sig->cb(loop, sig->data);
        }
 }
                sig->cb(loop, sig->data);
        }
 }
@@ -224,12 +224,11 @@ static void pipe_exit(event_loop_t *loop) {
 }
 
 void signal_trigger(event_loop_t *loop, signal_t *sig) {
 }
 
 void signal_trigger(event_loop_t *loop, signal_t *sig) {
-       if(sig->set) {
+       if(atomic_flag_test_and_set(&sig->set)) {
                return;
        }
 
        uint8_t signum = sig->signum;
                return;
        }
 
        uint8_t signum = sig->signum;
-       sig->set = true;
        write(loop->pipefd[1], &signum, 1);
        return;
 }
        write(loop->pipefd[1], &signum, 1);
        return;
 }
@@ -240,9 +239,10 @@ void signal_add(event_loop_t *loop, signal_t *sig, signal_cb_t cb, void *data, u
        sig->cb = cb;
        sig->data = data;
        sig->signum = signum;
        sig->cb = cb;
        sig->data = data;
        sig->signum = signum;
-       sig->set = false;
        sig->node.data = sig;
 
        sig->node.data = sig;
 
+       atomic_flag_clear(&sig->set);
+
        if(loop->pipefd[0] == -1) {
                pipe_init(loop);
        }
        if(loop->pipefd[0] == -1) {
                pipe_init(loop);
        }
index a87685da1c361152343d185e3bf566bde1e3dc30..ce6701ac441491cce83fe2f67717fb8d9c8097a7 100644 (file)
@@ -52,7 +52,7 @@ typedef struct timeout_t {
 typedef struct signal_t {
        struct splay_node_t node;
        int signum;
 typedef struct signal_t {
        struct splay_node_t node;
        int signum;
-       bool set;
+       volatile atomic_flag set;
        signal_cb_t cb;
        void *data;
 } signal_t;
        signal_cb_t cb;
        void *data;
 } signal_t;
index f64e15d09d9e57dd4e6f8bd3f500f755f4ef7d01..c0686a54ec6fdd26be2e2d312a4d09be34fd0f27 100644 (file)
@@ -32,6 +32,7 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <stdarg.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <stdarg.h>
+#include <stdatomic.h>
 #include <stdbool.h>
 #include <stdint.h>
 #include <inttypes.h>
 #include <stdbool.h>
 #include <stdint.h>
 #include <inttypes.h>