libmicrohttpd

HTTP/1.x server C library (MHD 1.x, stable)
Log | Files | Refs | Submodules | README | LICENSE

commit 280232dc1e9a6e26b13530c5e576880151935b19
parent 631a581657a7f2896f8b5ab7f1ea92c6997fc6c4
Author: Evgeny Grin (Karlson2k) <k2k@narod.ru>
Date:   Fri, 11 Nov 2016 13:18:18 +0300

Added support for faster setting thread names by pthread_attr_setname_np() where available.

Diffstat:
MChangeLog | 5+++++
Mconfigure.ac | 66++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++----
Msrc/include/microhttpd.h | 2+-
Msrc/microhttpd/mhd_threads.c | 41+++++++++++++++++++++++++++++++++++++++++
Msrc/microhttpd/mhd_threads.h | 3++-
5 files changed, 111 insertions(+), 6 deletions(-)

diff --git a/ChangeLog b/ChangeLog @@ -1,3 +1,8 @@ +Thu Nov 11 20:49:23 MSK 2016 + Added support for various forms of + pthread_attr_setname_np() so thread names will be set + more efficiently on certain platforms (Solaris, NetBSD etc.) -EG + Thu Nov 10 21:50:35 MSK 2016 Added rejection in MHD_start_daemon() of invalid combinations of daemon flags. diff --git a/configure.ac b/configure.ac @@ -352,16 +352,72 @@ if test "x$enable_thread_names" != "xno" && test "x$USE_THREADS" = "xposix"; the CFLAGS="$CFLAGS $PTHREAD_CFLAGS" AC_CHECK_HEADERS([pthread_np.h],[],[],[AC_INCLUDES_DEFAULT]) + # Try to find how to set thread name by thread attributes. + # If pthread_attr_setname_np(3) is not declared, it's not possible to detect + # form of pthread_attr_setname_np(3) due to C "feature" "implicit declaration". + AC_CHECK_DECL([[pthread_attr_setname_np]],[],[],[[ +#include <pthread.h> +#ifdef HAVE_PTHREAD_NP_H +#include <pthread_np.h> +#endif +]]) + + AS_IF([[test "x$ac_cv_have_decl_pthread_attr_setname_np" = "xyes"]], + [AC_MSG_CHECKING([[for pthread_attr_setname_np(3) in NetBSD or OSF1 form]]) + AC_LINK_IFELSE( + [AC_LANG_PROGRAM([[ +#include <pthread.h> +#ifdef HAVE_PTHREAD_NP_H +#include <pthread_np.h> +#endif +]], [[ + pthread_attr_t thr_attr; + pthread_attr_init(&thr_attr); + pthread_attr_setname_np(&thr_attr, "name", 0); + pthread_attr_destroy(&thr_attr); + ]])], + [AC_DEFINE([[HAVE_PTHREAD_ATTR_SETNAME_NP_NETBSD]], [[1]], [Define if you have NetBSD form (or OSF1 form) of pthread_attr_setname_np(3) function.]) + HAVE_THREAD_NAME_FUNC="yes" + AC_MSG_RESULT([[yes]])], + [AC_MSG_RESULT([[no]])] + ) + ]) + + AS_IF([[test "x$HAVE_THREAD_NAME_FUNC" != "xyes" && test "x$ac_cv_have_decl_pthread_attr_setname_np" = "xyes"]], + [AC_MSG_CHECKING([[for pthread_attr_setname_np(3) in IBM i form]]) + AC_LINK_IFELSE( + [AC_LANG_PROGRAM([[ +#include <pthread.h> +#ifdef HAVE_PTHREAD_NP_H +#include <pthread_np.h> +#endif +]], [[ + pthread_attr_t thr_attr; + pthread_attr_init(&thr_attr); + pthread_attr_setname_np(&thr_attr, "name"); + pthread_attr_destroy(&thr_attr); + ]])], + [AC_DEFINE([[HAVE_PTHREAD_ATTR_SETNAME_NP_IBMI]], [[1]], [Define if you have IBM i form of pthread_attr_setname_np(3) function.]) + HAVE_THREAD_NAME_FUNC="yes" + AC_MSG_RESULT([[yes]])], + [AC_MSG_RESULT([[no]])] + ) + ]) + + # Try to find how to set thread name for started thread - less convinent + # than setting name by attributes. # If pthread_setname_np(3) is not declared, it's not possible to detect # form of pthread_setname_np(3) due to C "feature" "implicit declaration". - AC_CHECK_DECL([[pthread_setname_np]],[],[],[[ + AS_IF([[test "x$HAVE_THREAD_NAME_FUNC" != "xyes"]], + [AC_CHECK_DECL([[pthread_setname_np]],[],[],[[ #include <pthread.h> #ifdef HAVE_PTHREAD_NP_H #include <pthread_np.h> #endif -]]) + ]]) + ]) - AS_IF([[test "x$ac_cv_have_decl_pthread_setname_np" = "xyes"]], + AS_IF([[test "x$HAVE_THREAD_NAME_FUNC" != "xyes" && test "x$ac_cv_have_decl_pthread_setname_np" = "xyes"]], [AC_MSG_CHECKING([[for pthread_setname_np(3) in NetBSD or OSF1 form]]) AC_LINK_IFELSE( [AC_LANG_PROGRAM([[ @@ -451,7 +507,9 @@ choke me #endif /* Keep in sync with mhd_threads.h */ -#if defined(MHD_USE_POSIX_THREADS) && (defined(HAVE_PTHREAD_SETNAME_NP_GNU) || defined(HAVE_PTHREAD_SET_NAME_NP_FREEBSD) || defined(HAVE_PTHREAD_SETNAME_NP_DARWIN) || defined(HAVE_PTHREAD_SETNAME_NP_NETBSD) ) +#if defined(MHD_USE_POSIX_THREADS) && (defined(HAVE_PTHREAD_ATTR_SETNAME_NP_NETBSD) || defined(HAVE_PTHREAD_ATTR_SETNAME_NP_IBMI) || \ + defined(HAVE_PTHREAD_SETNAME_NP_GNU) || defined(HAVE_PTHREAD_SET_NAME_NP_FREEBSD) || defined(HAVE_PTHREAD_SETNAME_NP_DARWIN) || \ + defined(HAVE_PTHREAD_SETNAME_NP_NETBSD) ) int a = 1; #elif defined(MHD_USE_W32_THREADS) && defined(_MSC_FULL_VER) int b = 2; diff --git a/src/include/microhttpd.h b/src/include/microhttpd.h @@ -126,7 +126,7 @@ typedef intptr_t ssize_t; * Current version of the library. * 0x01093001 = 1.9.30-1. */ -#define MHD_VERSION 0x00095208 +#define MHD_VERSION 0x00095209 /** * MHD-internal return code for "YES". diff --git a/src/microhttpd/mhd_threads.c b/src/microhttpd/mhd_threads.c @@ -54,6 +54,10 @@ typedef DWORD MHD_thread_ID_; #else /* MHD_USE_THREAD_NAME_ */ #if defined(MHD_USE_POSIX_THREADS) +#if defined(HAVE_PTHREAD_ATTR_SETNAME_NP_NETBSD) || defined(HAVE_PTHREAD_ATTR_SETNAME_NP_IBMI) +# define MHD_USE_THREAD_ATTR_SETNAME 1 +#endif /* HAVE_PTHREAD_ATTR_SETNAME_NP_NETBSD || HAVE_PTHREAD_ATTR_SETNAME_NP_IBMI */ + #if defined(HAVE_PTHREAD_SETNAME_NP_GNU) || defined(HAVE_PTHREAD_SET_NAME_NP_FREEBSD) \ || defined(HAVE_PTHREAD_SETNAME_NP_NETBSD) @@ -237,6 +241,7 @@ MHD_create_thread_ (MHD_thread_handle_ *thread, #ifdef MHD_USE_THREAD_NAME_ +#ifndef MHD_USE_THREAD_ATTR_SETNAME struct MHD_named_helper_param_ { /** @@ -275,6 +280,7 @@ named_thread_starter (void *data) return thr_func(arg); } +#endif /* ! MHD_USE_THREAD_ATTR_SETNAME */ /** @@ -294,6 +300,40 @@ MHD_create_named_thread_ (MHD_thread_handle_ *thread, MHD_THREAD_START_ROUTINE_ start_routine, void *arg) { +#if defined(MHD_USE_THREAD_ATTR_SETNAME) + int res; + pthread_attr_t attr; + + res = pthread_attr_init (&attr); + if (0 == res) + { +#if defined(HAVE_PTHREAD_ATTR_SETNAME_NP_NETBSD) + /* NetBSD use 3 arguments: second argument is string in printf-like format, + * third argument is single argument for printf; + * OSF1 use 3 arguments too, but last one always must be zero (NULL). + * MHD doesn't use '%' in thread names, so both form are used in same way. + */ + res = pthread_attr_setname_np (&attr, thread_name, 0); +#elif defined(HAVE_PTHREAD_ATTR_SETNAME_NP_IBMI) + res = pthread_attr_setname_np (&attr, thread_name); +#else +#error No pthread_attr_setname_np() function. +#endif + if (res == 0 && 0 != stack_size) + res = pthread_attr_setstacksize (&attr, + stack_size); + if (0 == res) + res = pthread_create (thread, + &attr, + start_routine, + arg); + pthread_attr_destroy (&attr); + } + if (0 != res) + errno = res; + + return !res; +#else /* ! MHD_USE_THREAD_ATTR_SETNAME */ struct MHD_named_helper_param_ *param; if (NULL == thread_name) @@ -323,6 +363,7 @@ MHD_create_named_thread_ (MHD_thread_handle_ *thread, } return !0; +#endif /* ! MHD_USE_THREAD_ATTR_SETNAME */ } #endif /* MHD_USE_THREAD_NAME_ */ diff --git a/src/microhttpd/mhd_threads.h b/src/microhttpd/mhd_threads.h @@ -59,7 +59,8 @@ #ifndef MHD_NO_THREAD_NAMES # if defined(MHD_USE_POSIX_THREADS) # if defined(HAVE_PTHREAD_SETNAME_NP_GNU) || defined(HAVE_PTHREAD_SET_NAME_NP_FREEBSD) || \ - defined(HAVE_PTHREAD_SETNAME_NP_DARWIN) || defined(HAVE_PTHREAD_SETNAME_NP_NETBSD) + defined(HAVE_PTHREAD_SETNAME_NP_DARWIN) || defined(HAVE_PTHREAD_SETNAME_NP_NETBSD) || \ + defined(HAVE_PTHREAD_ATTR_SETNAME_NP_NETBSD) || defined(HAVE_PTHREAD_ATTR_SETNAME_NP_IBMI) # define MHD_USE_THREAD_NAME_ # endif /* HAVE_PTHREAD_SETNAME_NP */ # elif defined(MHD_USE_W32_THREADS)