From 3feb4f103160403164263e76779a8e3f0c2d77d7 Mon Sep 17 00:00:00 2001 From: Sebastian Reimers Date: Fri, 13 May 2022 14:27:29 +0200 Subject: [PATCH] main: use C11 thread mutex --- src/main/init.c | 4 +- src/main/main.c | 134 +++++++++++++++--------------------------------- 2 files changed, 43 insertions(+), 95 deletions(-) diff --git a/src/main/init.c b/src/main/init.c index 4c3492f11..cb47905d8 100644 --- a/src/main/init.c +++ b/src/main/init.c @@ -31,7 +31,9 @@ int libre_init(void) if (err) goto out; - out: + err = re_thread_init(); + +out: if (err) { net_sock_close(); #ifdef USE_OPENSSL diff --git a/src/main/main.c b/src/main/main.c index 104051f18..537f80571 100644 --- a/src/main/main.c +++ b/src/main/main.c @@ -2,7 +2,9 @@ * @file main.c Main polling routine * * Copyright (C) 2010 Creytiv.com + * Copyright (C) 2020-2022 Sebastian Reimers */ +#include #ifdef HAVE_SYS_TIME_H #include #endif @@ -42,12 +44,8 @@ #include #include #include +#include #include "main.h" -#ifdef HAVE_PTHREAD -#define __USE_GNU 1 -#include -#include -#endif #define DEBUG_MODULE "main" @@ -97,52 +95,17 @@ struct re { struct kevent *evlist; int kqfd; #endif - -#ifdef HAVE_PTHREAD - pthread_mutex_t mutex; /**< Mutex for thread synchronization */ - pthread_mutex_t *mutexp; /**< Pointer to active mutex */ -#endif -}; - -static struct re global_re = { - NULL, - 0, - 0, - METHOD_NULL, - false, - false, - 0, - LIST_INIT, -#ifdef HAVE_POLL - NULL, -#endif -#ifdef HAVE_EPOLL - NULL, - -1, -#endif -#ifdef HAVE_KQUEUE - NULL, - -1, -#endif -#ifdef HAVE_PTHREAD -#if MAIN_DEBUG && defined (PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP) - PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP, -#else - PTHREAD_MUTEX_INITIALIZER, -#endif - &global_re.mutex, -#endif + mtx_t mutex; /**< Pointer to active mutex */ + mtx_t *mutexp; /**< Pointer to active mutex */ }; - -#ifdef HAVE_PTHREAD - static void poll_close(struct re *re); -static pthread_once_t pt_once = PTHREAD_ONCE_INIT; -static pthread_key_t pt_key; +static tss_t key; +static once_flag flag = ONCE_FLAG_INIT; +/** fallback destructor if thread gets destroyed before re_thread_close() */ static void thread_destructor(void *arg) { poll_close(arg); @@ -152,22 +115,13 @@ static void thread_destructor(void *arg) static void re_once(void) { - pthread_key_create(&pt_key, thread_destructor); + tss_create(&key, thread_destructor); } static struct re *re_get(void) { - struct re *re; - - pthread_once(&pt_once, re_once); - - re = pthread_getspecific(pt_key); - if (!re) { - re = &global_re; - } - - return re; + return tss_get(key); } @@ -175,10 +129,9 @@ static inline void re_lock(struct re *re) { int err; - err = pthread_mutex_lock(re->mutexp); - if (err) { + err = mtx_lock(re->mutexp); + if (err) DEBUG_WARNING("re_lock: %m\n", err); - } } @@ -186,24 +139,11 @@ static inline void re_unlock(struct re *re) { int err; - err = pthread_mutex_unlock(re->mutexp); - if (err) { + err = mtx_unlock(re->mutexp); + if (err) DEBUG_WARNING("re_unlock: %m\n", err); - } -} - - -#else - -static struct re *re_get(void) -{ - return &global_re; } -#define re_lock(x) /**< Stub */ -#define re_unlock(x) /**< Stub */ - -#endif #ifdef WIN32 /** @@ -1152,26 +1092,34 @@ int poll_method_set(enum poll_method method) */ int re_thread_init(void) { -#ifdef HAVE_PTHREAD struct re *re; + int err; - pthread_once(&pt_once, re_once); + call_once(&flag, re_once); + + re = re_get(); - re = pthread_getspecific(pt_key); if (re) { DEBUG_WARNING("thread_init: already added for thread %d\n", - pthread_self()); + thrd_current()); return EALREADY; } - re = malloc(sizeof(*re)); + re = malloc(sizeof(struct re)); if (!re) return ENOMEM; memset(re, 0, sizeof(*re)); - pthread_mutex_init(&re->mutex, NULL); + + err = mtx_init(&re->mutex, mtx_plain); + if (err) { + DEBUG_WARNING("re_init: mtx_init error\n"); + goto out; + } re->mutexp = &re->mutex; + list_init(&re->tmrl); + #ifdef HAVE_EPOLL re->epfd = -1; #endif @@ -1180,11 +1128,15 @@ int re_thread_init(void) re->kqfd = -1; #endif - pthread_setspecific(pt_key, re); - return 0; -#else - return ENOSYS; -#endif + err = tss_set(key, re); + if (err) + DEBUG_WARNING("re_init: tss_set error\n"); + +out: + if (err) + mem_deref(re); + + return err; } @@ -1193,18 +1145,16 @@ int re_thread_init(void) */ void re_thread_close(void) { -#ifdef HAVE_PTHREAD struct re *re; - pthread_once(&pt_once, re_once); + call_once(&flag, re_once); - re = pthread_getspecific(pt_key); + re = re_get(); if (re) { poll_close(re); free(re); - pthread_setspecific(pt_key, NULL); + tss_set(key, NULL); } -#endif } @@ -1237,13 +1187,9 @@ void re_thread_leave(void) */ void re_set_mutex(void *mutexp) { -#ifdef HAVE_PTHREAD struct re *re = re_get(); re->mutexp = mutexp ? mutexp : &re->mutex; -#else - (void)mutexp; -#endif }