From a6874a46c6be6920dba866b1705446b30fb7725b Mon Sep 17 00:00:00 2001 From: David Cermak Date: Thu, 21 Apr 2022 09:12:42 +0200 Subject: [PATCH] contrib/ports: Add semaphore per thread option for unix --- .../ports/unix/port/include/arch/sys_arch.h | 9 +++ contrib/ports/unix/port/sys_arch.c | 69 +++++++++++++++++++ 2 files changed, 78 insertions(+) diff --git a/contrib/ports/unix/port/include/arch/sys_arch.h b/contrib/ports/unix/port/include/arch/sys_arch.h index 422104a2..567e1256 100644 --- a/contrib/ports/unix/port/include/arch/sys_arch.h +++ b/contrib/ports/unix/port/include/arch/sys_arch.h @@ -59,6 +59,15 @@ typedef struct sys_mbox * sys_mbox_t; struct sys_thread; typedef struct sys_thread * sys_thread_t; +#if LWIP_NETCONN_SEM_PER_THREAD +sys_sem_t* sys_arch_netconn_sem_get(void); +void sys_arch_netconn_sem_alloc(void); +void sys_arch_netconn_sem_free(void); +#define LWIP_NETCONN_THREAD_SEM_GET() sys_arch_netconn_sem_get() +#define LWIP_NETCONN_THREAD_SEM_ALLOC() sys_arch_netconn_sem_alloc() +#define LWIP_NETCONN_THREAD_SEM_FREE() sys_arch_netconn_sem_free() +#endif /* #if LWIP_NETCONN_SEM_PER_THREAD */ + #define LWIP_EXAMPLE_APP_ABORT() lwip_unix_keypressed() int lwip_unix_keypressed(void); diff --git a/contrib/ports/unix/port/sys_arch.c b/contrib/ports/unix/port/sys_arch.c index 9f7c8d3a..10c22023 100644 --- a/contrib/ports/unix/port/sys_arch.c +++ b/contrib/ports/unix/port/sys_arch.c @@ -68,6 +68,11 @@ #include "lwip/stats.h" #include "lwip/tcpip.h" +#if LWIP_NETCONN_SEM_PER_THREAD +/* pthread key to *our* thread local storage entry */ +static pthread_key_t sys_thread_sem_key; +#endif + /* Return code for an interrupted timed wait */ #define SYS_ARCH_INTR 0xfffffffeUL @@ -664,6 +669,67 @@ sys_mutex_free(struct sys_mutex **mutex) #endif /* !NO_SYS */ +#if LWIP_NETCONN_SEM_PER_THREAD +/*-----------------------------------------------------------------------------------*/ +/* Semaphore per thread located TLS */ + +static void +sys_thread_sem_free(void* data) +{ + sys_sem_t *sem = (sys_sem_t*)(data); + + if (sem) { + sys_sem_free(sem); + free(sem); + } +} + +static sys_sem_t* +sys_thread_sem_alloc(void) +{ + sys_sem_t *sem; + err_t err; + int ret; + + sem = (sys_sem_t*)malloc(sizeof(sys_sem_t*)); + LWIP_ASSERT("failed to allocate memory for TLS semaphore", sem != NULL); + err = sys_sem_new(sem, 0); + LWIP_ASSERT("failed to initialise TLS semaphore", err == ERR_OK); + ret = pthread_setspecific(sys_thread_sem_key, sem); + LWIP_ASSERT("failed to initialise TLS semaphore storage", ret == 0); + return sem; +} + +sys_sem_t* +sys_arch_netconn_sem_get(void) +{ + sys_sem_t* sem = (sys_sem_t*)pthread_getspecific(sys_thread_sem_key); + if (!sem) { + sem = sys_thread_sem_alloc(); + } + LWIP_DEBUGF(SYS_DEBUG, ("sys_thread_sem_get s=%p\n", (void*)sem)); + return sem; +} + +void +sys_arch_netconn_sem_alloc(void) +{ + sys_sem_t* sem = sys_thread_sem_alloc(); + LWIP_DEBUGF(SYS_DEBUG, ("sys_thread_sem created s=%p\n", (void*)sem)); +} + +void +sys_arch_netconn_sem_free(void) +{ + int ret; + + sys_sem_t *sem = (sys_sem_t *)pthread_getspecific(sys_thread_sem_key); + sys_thread_sem_free(sem); + ret = pthread_setspecific(sys_thread_sem_key, NULL); + LWIP_ASSERT("failed to de-init TLS semaphore storage", ret == 0); +} +#endif /* LWIP_NETCONN_SEM_PER_THREAD */ + /*-----------------------------------------------------------------------------------*/ /* Time */ u32_t @@ -695,6 +761,9 @@ sys_jiffies(void) void sys_init(void) { +#if LWIP_NETCONN_SEM_PER_THREAD + pthread_key_create(&sys_thread_sem_key, sys_thread_sem_free); +#endif } /*-----------------------------------------------------------------------------------*/