From 2f5305c2597b4c7733331a149c9d44dba005d138 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Joan=20Lled=C3=B3?= Date: Sun, 14 Jul 2019 12:30:40 +0200 Subject: [PATCH] Unix port: improve support for the Hurd Signed-off-by: Simon Goldschmidt --- contrib/ports/unix/check/CMakeLists.txt | 10 ++++---- contrib/ports/unix/port/sys_arch.c | 32 +++++++++++++++++++++---- 2 files changed, 33 insertions(+), 9 deletions(-) diff --git a/contrib/ports/unix/check/CMakeLists.txt b/contrib/ports/unix/check/CMakeLists.txt index 68833163..9cf8d05a 100644 --- a/contrib/ports/unix/check/CMakeLists.txt +++ b/contrib/ports/unix/check/CMakeLists.txt @@ -4,12 +4,14 @@ set (CMAKE_CONFIGURATION_TYPES "Debug;Release") project(lwipunittests C) -if (NOT CMAKE_SYSTEM_NAME STREQUAL "Linux" AND NOT CMAKE_SYSTEM_NAME STREQUAL "Darwin") - message(FATAL_ERROR "Unit test are currently only working on Linux or Darwin") +if (NOT CMAKE_SYSTEM_NAME STREQUAL "Linux" AND NOT CMAKE_SYSTEM_NAME STREQUAL "Darwin" AND NOT CMAKE_SYSTEM_NAME STREQUAL "GNU") + message(FATAL_ERROR "Unit test are currently only working on Linux, Darwin or Hurd") endif() set(LWIP_DIR ${CMAKE_CURRENT_SOURCE_DIR}/../../../..) -set(LWIP_USE_SANITIZERS true) +if (NOT CMAKE_SYSTEM_NAME STREQUAL "GNU") + set(LWIP_USE_SANITIZERS true) +endif() include(${LWIP_DIR}/contrib/ports/CMakeCommon.cmake) if(CMAKE_C_COMPILER_ID STREQUAL "Clang") @@ -45,7 +47,7 @@ if (NOT CMAKE_SYSTEM_NAME STREQUAL "Darwin") target_link_libraries(lwip_unittests ${LIBSUBUNIT}) endif() -if (CMAKE_SYSTEM_NAME STREQUAL "Linux") +if (CMAKE_SYSTEM_NAME STREQUAL "Linux" OR CMAKE_SYSTEM_NAME STREQUAL "GNU") find_library(LIBUTIL util) find_library(LIBPTHREAD pthread) find_library(LIBRT rt) diff --git a/contrib/ports/unix/port/sys_arch.c b/contrib/ports/unix/port/sys_arch.c index a56d7de1..b083ccbf 100644 --- a/contrib/ports/unix/port/sys_arch.c +++ b/contrib/ports/unix/port/sys_arch.c @@ -68,6 +68,9 @@ #include "lwip/stats.h" #include "lwip/tcpip.h" +/* Return code for an interrupted timed wait */ +#define SYS_ARCH_INTR 0xfffffffeUL + u32_t lwip_port_rand(void) { @@ -489,14 +492,20 @@ cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex, u32_t timeout) struct timespec rtime1, rtime2, ts; int ret; -#ifdef __GNU__ +#ifdef LWIP_UNIX_HURD #define pthread_cond_wait pthread_hurd_cond_wait_np #define pthread_cond_timedwait pthread_hurd_cond_timedwait_np #endif if (timeout == 0) { - pthread_cond_wait(cond, mutex); - return 0; + ret = pthread_cond_wait(cond, mutex); + return +#ifdef LWIP_UNIX_HURD + /* On the Hurd, ret == 1 means the RPC has been cancelled. + * The thread is awakened (not terminated) and execution must continue */ + ret == 1 ? SYS_ARCH_INTR : +#endif + (u32_t)ret; } /* Get a timestamp and add the timeout value. */ @@ -517,6 +526,12 @@ cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex, u32_t timeout) #endif if (ret == ETIMEDOUT) { return SYS_ARCH_TIMEOUT; +#ifdef LWIP_UNIX_HURD + /* On the Hurd, ret == 1 means the RPC has been cancelled. + * The thread is awakened (not terminated) and execution must continue */ + } else if (ret == EINTR) { + return SYS_ARCH_INTR; +#endif } /* Calculate for how long we waited for the cond. */ @@ -546,11 +561,18 @@ sys_arch_sem_wait(struct sys_sem **s, u32_t timeout) if (time_needed == SYS_ARCH_TIMEOUT) { pthread_mutex_unlock(&(sem->mutex)); return SYS_ARCH_TIMEOUT; +#ifdef LWIP_UNIX_HURD + } else if(time_needed == SYS_ARCH_INTR) { + pthread_mutex_unlock(&(sem->mutex)); + return 0; +#endif } /* pthread_mutex_unlock(&(sem->mutex)); return time_needed; */ - } else { - cond_wait(&(sem->cond), &(sem->mutex), 0); + } else if(cond_wait(&(sem->cond), &(sem->mutex), 0)) { + /* Some error happened or the thread has been awakened but not by lwip */ + pthread_mutex_unlock(&(sem->mutex)); + return 0; } } sem->c--;