1
0
Fork 0
mirror of https://github.com/warmcat/libwebsockets.git synced 2025-03-30 00:00:16 +01:00

windows: pthreads

Add support for external pthreads lib on windows and some docs about how to do.

It can build with LWS_WITH_THREADPOOL and LWS_WITH_MINIMAL_EXAMPLES including the
pthreads-dependent ones without warnings or errors on windows platform as well with this.

pthreads_t can be anything, including a struct - not a pointer-to-a-struct
but the struct itself.  These can't be cast to a void * for printing as they can
on linux, where the base type is a pointer.

Let's fix all the usage of those to determine their own thread index in terms
of the meaning to the program rather than as a tid.
This commit is contained in:
Andy Green 2020-04-07 14:05:21 +01:00
parent 954fcf2bc3
commit d3308df40f
31 changed files with 274 additions and 72 deletions

View file

@ -497,7 +497,6 @@ endif()
if (WIN32) if (WIN32)
set(LWS_MAX_SMP 1) set(LWS_MAX_SMP 1)
set(LWS_WITH_THREADPOOL 0)
endif() endif()
if (LWS_WITHOUT_SERVER) if (LWS_WITHOUT_SERVER)
@ -592,6 +591,10 @@ set(LWS_GLIB_INCLUDE_DIRS CACHE PATH "Path to the glib include directory")
set(LWS_GLIB_LIBRARIES CACHE PATH "Path to the glib library") set(LWS_GLIB_LIBRARIES CACHE PATH "Path to the glib library")
set(LWS_LIBMOUNT_INCLUDE_DIRS CACHE PATH "Path to the libmount include directory") set(LWS_LIBMOUNT_INCLUDE_DIRS CACHE PATH "Path to the libmount include directory")
set(LWS_LIBMOUNT_LIBRARIES CACHE PATH "Path to the libmount library") set(LWS_LIBMOUNT_LIBRARIES CACHE PATH "Path to the libmount library")
# on unix, these are in the toolchain. On win32 you have to put them somewhere
# yourself and point to them here
set(LWS_EXT_PTHREAD_INCLUDE_DIR CACHE PATH "Path to an external pthreads include directory")
set(LWS_EXT_PTHREAD_LIBRARIES CACHE PATH "Path to an external pthreads library")
if (NOT LWS_WITH_SSL) if (NOT LWS_WITH_SSL)
@ -911,6 +914,14 @@ if (NOT LWS_HAVE_GETIFADDRS)
set(LWS_BUILTIN_GETIFADDRS 1) set(LWS_BUILTIN_GETIFADDRS 1)
endif() endif()
if (LWS_EXT_PTHREAD_INCLUDE_DIR)
set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES};${LWS_EXT_PTHREAD_INCLUDE_DIR})
include_directories(${LWS_EXT_PTHREAD_INCLUDE_DIR})
list(APPEND LIB_LIST ${LWS_EXT_PTHREAD_LIBRARIES})
set(CMAKE_REQUIRED_FLAGS ${CMAKE_REQUIRED_FLAGS} " -DHAVE_STRUCT_TIMESPEC=1")
endif()
CHECK_INCLUDE_FILE(dlfcn.h LWS_HAVE_DLFCN_H) CHECK_INCLUDE_FILE(dlfcn.h LWS_HAVE_DLFCN_H)
CHECK_INCLUDE_FILE(fcntl.h LWS_HAVE_FCNTL_H) CHECK_INCLUDE_FILE(fcntl.h LWS_HAVE_FCNTL_H)
CHECK_INCLUDE_FILE(in6addr.h LWS_HAVE_IN6ADDR_H) CHECK_INCLUDE_FILE(in6addr.h LWS_HAVE_IN6ADDR_H)
@ -1015,9 +1026,9 @@ CHECK_C_SOURCE_COMPILES("#include <stdint.h>
if (LWS_HAVE_PTHREAD_H) if (LWS_HAVE_PTHREAD_H)
if ((CMAKE_C_COMPILER_ID MATCHES "Clang") OR (CMAKE_CXX_COMPILER_ID MATCHES "Clang")) if ((CMAKE_C_COMPILER_ID MATCHES "Clang") OR (CMAKE_CXX_COMPILER_ID MATCHES "Clang"))
set(CMAKE_REQUIRED_FLAGS "-pthread -Wno-error=unused-command-line-argument") set(CMAKE_REQUIRED_FLAGS ${CMAKE_REQUIRED_FLAGS} "-pthread -Wno-error=unused-command-line-argument")
else() else()
set(CMAKE_REQUIRED_FLAGS "-pthread") set(CMAKE_REQUIRED_FLAGS ${CMAKE_REQUIRED_FLAGS} "-pthread")
endif() endif()
CHECK_C_SOURCE_COMPILES("#define _GNU_SOURCE CHECK_C_SOURCE_COMPILES("#define _GNU_SOURCE
@ -1103,8 +1114,6 @@ if (LWS_WITH_FSMOUNT AND ${CMAKE_SYSTEM_NAME} STREQUAL "Linux")
list(APPEND SOURCES lib/misc/fsmount.c) list(APPEND SOURCES lib/misc/fsmount.c)
endif() endif()
if (LWS_WITH_FILE_OPS) if (LWS_WITH_FILE_OPS)
list(APPEND SOURCES lib/core/vfs.c) list(APPEND SOURCES lib/core/vfs.c)
endif() endif()
@ -1250,7 +1259,7 @@ if (LWS_ROLE_MQTT AND LWS_WITH_CLIENT)
) )
endif() endif()
if (LWS_WITH_THREADPOOL AND UNIX AND LWS_HAVE_PTHREAD_H) if (LWS_WITH_THREADPOOL AND LWS_HAVE_PTHREAD_H)
list(APPEND SOURCES lib/misc/threadpool/threadpool.c) list(APPEND SOURCES lib/misc/threadpool/threadpool.c)
endif() endif()
@ -1796,6 +1805,7 @@ source_group("Resources" FILES ${RESOURCES})
# #
set(LWS_LIBRARIES) set(LWS_LIBRARIES)
if (LWS_WITH_STATIC) if (LWS_WITH_STATIC)
if (LWS_STATIC_PIC) if (LWS_STATIC_PIC)
set(CMAKE_POSITION_INDEPENDENT_CODE ON) set(CMAKE_POSITION_INDEPENDENT_CODE ON)
@ -1896,6 +1906,9 @@ set(LIB_LIST)
# #
# Find libraries. # Find libraries.
# #
if (LWS_EXT_PTHREAD_INCLUDE_DIR)
list(APPEND LIB_LIST ${LWS_EXT_PTHREAD_LIBRARIES})
endif()
# #
# ZLIB (needed for deflate extension and if LWS_WITH_HTTP_STREAM_COMPRESSION) # ZLIB (needed for deflate extension and if LWS_WITH_HTTP_STREAM_COMPRESSION)
@ -1977,7 +1990,7 @@ if (LWS_WITH_SSL)
include_directories("${inc}" "${inc}/wolfssl") include_directories("${inc}" "${inc}/wolfssl")
endforeach() endforeach()
endif() endif()
set(CMAKE_REQUIRED_INCLUDES ${OPENSSL_INCLUDE_DIRS}) set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES} ${OPENSSL_INCLUDE_DIRS})
set(VARIA wolfSSL_) set(VARIA wolfSSL_)
list(APPEND LIB_LIST "${WOLFSSL_LIBRARIES}") list(APPEND LIB_LIST "${WOLFSSL_LIBRARIES}")
@ -2020,7 +2033,7 @@ if (LWS_WITH_SSL)
if (NOT LWS_WITH_MBEDTLS) if (NOT LWS_WITH_MBEDTLS)
# older (0.98) Openssl lacks this # older (0.98) Openssl lacks this
set(CMAKE_REQUIRED_INCLUDES ${OPENSSL_INCLUDE_DIRS}) set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES} ${OPENSSL_INCLUDE_DIRS})
check_include_file(openssl/ecdh.h LWS_HAVE_OPENSSL_ECDH_H) check_include_file(openssl/ecdh.h LWS_HAVE_OPENSSL_ECDH_H)
if (LWS_SSL_SERVER_WITH_ECDH_CERT AND NOT LWS_HAVE_OPENSSL_ECDH_H) if (LWS_SSL_SERVER_WITH_ECDH_CERT AND NOT LWS_HAVE_OPENSSL_ECDH_H)
@ -2181,7 +2194,7 @@ foreach (lib ${LWS_LIBRARIES})
endforeach() endforeach()
set (temp ${CMAKE_REQUIRED_LIBRARIES}) set (temp ${CMAKE_REQUIRED_LIBRARIES})
set(CMAKE_REQUIRED_LIBRARIES ${LIB_LIST}) set(CMAKE_REQUIRED_LIBRARIES ${LIB_LIST} ${CMAKE_REQUIRED_LIBRARIES})
if (LWS_WITH_ZLIB) if (LWS_WITH_ZLIB)
if (LWS_WITH_BUNDLED_ZLIB) if (LWS_WITH_BUNDLED_ZLIB)

View file

@ -73,3 +73,22 @@ there.
``` ```
After that you can run the test apps OK. After that you can run the test apps OK.
## pthreads
It's amazing but after all these years windows doesn't offer pthreads compatibility
itself. Just like the many other missing POSIX bits like fork().
I downloaded the latest (2012) zip release of pthreads-win32 from here
ftp://sourceware.org/pub/pthreads-win32
Then I created a dir "C:\Program Files (x86)\pthreads", and copied the `dll`,
`include` and `lib` subdirs from the `prebuilt` folder in the zip there.
The cmake incantation to build against pthreads set up like that is
```
$ cmake .. -DLWS_EXT_PTHREAD_INCLUDE_DIR="C:\Program Files (x86)\pthreads\include" -DLWS_EXT_PTHREAD_LIBRARIES="C:\Program Files (x86)\pthreads\lib\x64\libpthreadGC2.a" -DLWS_WITH_MINIMAL_EXAMPLES=1
```

View file

@ -18,6 +18,8 @@
#cmakedefine LWS_LIBRARY_VERSION_NUMBER #cmakedefine LWS_LIBRARY_VERSION_NUMBER
#cmakedefine LWS_EXT_PTHREAD_LIBRARIES
#cmakedefine LWS_AVOID_SIGPIPE_IGN #cmakedefine LWS_AVOID_SIGPIPE_IGN
#cmakedefine LWS_BUILD_HASH "${LWS_BUILD_HASH}" #cmakedefine LWS_BUILD_HASH "${LWS_BUILD_HASH}"
#cmakedefine LWS_BUILTIN_GETIFADDRS #cmakedefine LWS_BUILTIN_GETIFADDRS

View file

@ -26,6 +26,12 @@
#define _GNU_SOURCE #define _GNU_SOURCE
#endif #endif
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#include "private-lib-core.h" #include "private-lib-core.h"
@ -131,10 +137,10 @@ __lws_threadpool_task_dump(struct lws_threadpool_task *task, char *buf, int len)
} }
if (task->acc_running) if (task->acc_running)
runms = task->acc_running; runms = (int)task->acc_running;
if (task->acc_syncing) if (task->acc_syncing)
syncms = task->acc_syncing; syncms = (int)task->acc_syncing;
if (!task->done) { if (!task->done) {
buf += lws_snprintf(buf, end - buf, buf += lws_snprintf(buf, end - buf,

View file

@ -16,6 +16,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -88,9 +94,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -15,6 +15,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
static struct lws_context *context; static struct lws_context *context;
@ -119,10 +125,7 @@ attach_callback(struct lws_context *context, int tsi, void *opaque)
/* /*
* Even though it was asked for from a different thread, we are called * Even though it was asked for from a different thread, we are called
* back by lws from the lws event loop thread context * back by lws from the lws event loop thread context
*/ *
lwsl_user("%s: called from tid %p\n", __func__, (void *)pthread_self());
/*
* We can set up our operations on the lws event loop and return so * We can set up our operations on the lws event loop and return so
* they can happen asynchronously * they can happen asynchronously
*/ */
@ -218,7 +221,6 @@ int main(int argc, const char **argv)
logs = atoi(p); logs = atoi(p);
lws_set_log_level(logs, NULL); lws_set_log_level(logs, NULL);
lwsl_user("%s: main thread tid %p\n", __func__, (void *)pthread_self());
lwsl_user("LWS minimal http client attach\n"); lwsl_user("LWS minimal http client attach\n");
pthread_mutex_init(&lock, NULL); pthread_mutex_init(&lock, NULL);

View file

@ -15,6 +15,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -85,9 +91,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared pthread) add_dependencies(${SAMP} websockets_shared ${PTHREAD_LIB})
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -18,6 +18,13 @@
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#define COUNT_THREADS 8 #define COUNT_THREADS 8

View file

@ -15,6 +15,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -85,9 +91,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared pthread) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -21,6 +21,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#define COUNT_THREADS 8 #define COUNT_THREADS 8

View file

@ -15,6 +15,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -85,9 +91,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -19,6 +19,12 @@
#include <string.h> #include <string.h>
#include <stdlib.h> #include <stdlib.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#include <time.h> #include <time.h>
@ -86,7 +92,11 @@ thread_spam(void *d)
{ {
struct vhd *vhd = (struct vhd *)d; struct vhd *vhd = (struct vhd *)d;
struct msg amsg; struct msg amsg;
int len = 128, index = 1, n; int len = 128, index = 1, n, whoami = 0;
for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++)
if (pthread_equal(pthread_self(), vhd->pthread_spam[n]))
whoami = n + 1;
do { do {
/* don't generate output if nobody connected */ /* don't generate output if nobody connected */
@ -108,10 +118,9 @@ thread_spam(void *d)
goto wait_unlock; goto wait_unlock;
} }
n = lws_snprintf((char *)amsg.payload, len, n = lws_snprintf((char *)amsg.payload, len,
"%s: tid: %p, msg: %d", __func__, "%s: tid: %d, msg: %d", __func__, whoami, index++);
(void *)pthread_self(), index++);
amsg.len = n; amsg.len = n;
n = lws_ring_insert(vhd->ring, &amsg, 1); n = (int)lws_ring_insert(vhd->ring, &amsg, 1);
if (n != 1) { if (n != 1) {
__minimal_destroy_message(&amsg); __minimal_destroy_message(&amsg);
lwsl_user("dropping!\n"); lwsl_user("dropping!\n");
@ -131,7 +140,7 @@ wait:
} while (!vhd->finished); } while (!vhd->finished);
lwsl_notice("thread_spam %p exiting\n", (void *)pthread_self()); lwsl_notice("thread_spam %d exiting\n", whoami);
pthread_exit(NULL); pthread_exit(NULL);
@ -186,7 +195,6 @@ callback_sse(struct lws *wsi, enum lws_callback_reasons reason, void *user,
init_fail: init_fail:
vhd->finished = 1; vhd->finished = 1;
for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++) for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++)
if (vhd->pthread_spam[n])
pthread_join(vhd->pthread_spam[n], &retval); pthread_join(vhd->pthread_spam[n], &retval);
if (vhd->ring) if (vhd->ring)

View file

@ -14,6 +14,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -84,9 +90,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -19,6 +19,12 @@
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#include <time.h> #include <time.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
/* /*

View file

@ -11,6 +11,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#include <assert.h> #include <assert.h>

View file

@ -11,6 +11,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#include <assert.h> #include <assert.h>

View file

@ -15,8 +15,15 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
# If we are being built as part of lws, confirm current build config supports # If we are being built as part of lws, confirm current build config supports
# reqconfig, else skip building ourselves. # reqconfig, else skip building ourselves.
# #
@ -84,9 +91,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared pthread) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -14,6 +14,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
static struct lws_context *context; static struct lws_context *context;

View file

@ -15,8 +15,15 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
# If we are being built as part of lws, confirm current build config supports # If we are being built as part of lws, confirm current build config supports
# reqconfig, else skip building ourselves. # reqconfig, else skip building ourselves.
# #
@ -84,9 +91,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared pthread) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -13,6 +13,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
enum { enum {

View file

@ -15,8 +15,15 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
# If we are being built as part of lws, confirm current build config supports # If we are being built as part of lws, confirm current build config supports
# reqconfig, else skip building ourselves. # reqconfig, else skip building ourselves.
# #
@ -84,9 +91,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared pthread) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -21,6 +21,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
static int interrupted; static int interrupted;
@ -70,7 +76,11 @@ thread_spam(void *d)
struct per_vhost_data__minimal *vhd = struct per_vhost_data__minimal *vhd =
(struct per_vhost_data__minimal *)d; (struct per_vhost_data__minimal *)d;
struct msg amsg; struct msg amsg;
int len = 128, index = 1, n; int len = 128, index = 1, n, whoami = 0;
for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++)
if (pthread_equal(pthread_self(), vhd->pthread_spam[n]))
whoami = n + 1;
do { do {
/* don't generate output if client not connected */ /* don't generate output if client not connected */
@ -92,10 +102,9 @@ thread_spam(void *d)
goto wait_unlock; goto wait_unlock;
} }
n = lws_snprintf((char *)amsg.payload + LWS_PRE, len, n = lws_snprintf((char *)amsg.payload + LWS_PRE, len,
"tid: %p, msg: %d", "tid: %d, msg: %d", whoami, index++);
(void *)pthread_self(), index++);
amsg.len = n; amsg.len = n;
n = lws_ring_insert(vhd->ring, &amsg, 1); n = (int)lws_ring_insert(vhd->ring, &amsg, 1);
if (n != 1) { if (n != 1) {
__minimal_destroy_message(&amsg); __minimal_destroy_message(&amsg);
lwsl_user("dropping!\n"); lwsl_user("dropping!\n");
@ -114,7 +123,7 @@ wait:
} while (!vhd->finished); } while (!vhd->finished);
lwsl_notice("thread_spam %p exiting\n", (void *)pthread_self()); lwsl_notice("thread_spam %d exiting\n", whoami);
pthread_exit(NULL); pthread_exit(NULL);
@ -188,7 +197,6 @@ callback_minimal_broker(struct lws *wsi, enum lws_callback_reasons reason,
init_fail: init_fail:
vhd->finished = 1; vhd->finished = 1;
for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++) for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++)
if (vhd->pthread_spam[n])
pthread_join(vhd->pthread_spam[n], &retval); pthread_join(vhd->pthread_spam[n], &retval);
if (vhd->ring) if (vhd->ring)

View file

@ -15,6 +15,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -86,9 +92,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -21,6 +21,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#define LWS_PLUGIN_STATIC #define LWS_PLUGIN_STATIC
@ -125,5 +131,7 @@ int main(int argc, const char **argv)
lws_context_destroy(context); lws_context_destroy(context);
lwsl_user("%s: exiting cleanly...\n", __func__);
return 0; return 0;
} }

View file

@ -43,6 +43,10 @@ struct task_data {
uint64_t pos, end; uint64_t pos, end;
}; };
#if defined(WIN32)
static void usleep(unsigned long l) { Sleep(l / 1000); }
#endif
/* /*
* Create the private data for the task * Create the private data for the task
* *
@ -254,6 +258,8 @@ callback_minimal(struct lws *wsi, enum lws_callback_reasons reason,
*/ */
task = lws_threadpool_get_task_wsi(wsi); task = lws_threadpool_get_task_wsi(wsi);
if (!task)
break;
n = lws_threadpool_task_status(task, &_user); n = lws_threadpool_task_status(task, &_user);
lwsl_debug("%s: LWS_CALLBACK_SERVER_WRITEABLE: status %d\n", lwsl_debug("%s: LWS_CALLBACK_SERVER_WRITEABLE: status %d\n",
__func__, n); __func__, n);
@ -277,7 +283,7 @@ callback_minimal(struct lws *wsi, enum lws_callback_reasons reason,
lws_set_timeout(wsi, PENDING_TIMEOUT_THREADPOOL_TASK, 5); lws_set_timeout(wsi, PENDING_TIMEOUT_THREADPOOL_TASK, 5);
n = strlen(priv->result + LWS_PRE); n = (int)strlen(priv->result + LWS_PRE);
m = lws_write(wsi, (unsigned char *)priv->result + LWS_PRE, m = lws_write(wsi, (unsigned char *)priv->result + LWS_PRE,
n, LWS_WRITE_TEXT); n, LWS_WRITE_TEXT);
if (m < n) { if (m < n) {

View file

@ -15,6 +15,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -85,9 +91,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -21,6 +21,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#define LWS_PLUGIN_STATIC #define LWS_PLUGIN_STATIC

View file

@ -83,7 +83,11 @@ thread_spam(void *d)
struct per_vhost_data__minimal *vhd = struct per_vhost_data__minimal *vhd =
(struct per_vhost_data__minimal *)d; (struct per_vhost_data__minimal *)d;
struct msg amsg; struct msg amsg;
int len = 128, index = 1, n; int len = 128, index = 1, n, whoami = 0;
for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++)
if (pthread_equal(pthread_self(), vhd->pthread_spam[n]))
whoami = n + 1;
do { do {
/* don't generate output if nobody connected */ /* don't generate output if nobody connected */
@ -105,10 +109,10 @@ thread_spam(void *d)
goto wait_unlock; goto wait_unlock;
} }
n = lws_snprintf((char *)amsg.payload + LWS_PRE, len, n = lws_snprintf((char *)amsg.payload + LWS_PRE, len,
"%s: spam tid: %p, msg: %d", vhd->config, "%s: spam tid: %d, msg: %d", vhd->config,
(void *)pthread_self(), index++); whoami, index++);
amsg.len = n; amsg.len = n;
n = lws_ring_insert(vhd->ring, &amsg, 1); n = (int)lws_ring_insert(vhd->ring, &amsg, 1);
if (n != 1) { if (n != 1) {
__minimal_destroy_message(&amsg); __minimal_destroy_message(&amsg);
lwsl_user("dropping!\n"); lwsl_user("dropping!\n");
@ -127,7 +131,7 @@ wait:
} while (!vhd->finished); } while (!vhd->finished);
lwsl_notice("thread_spam %p exiting\n", (void *)pthread_self()); lwsl_notice("thread_spam %d exiting\n", whoami);
pthread_exit(NULL); pthread_exit(NULL);
@ -199,7 +203,6 @@ callback_minimal(struct lws *wsi, enum lws_callback_reasons reason,
init_fail: init_fail:
vhd->finished = 1; vhd->finished = 1;
for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++) for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++)
if (vhd->pthread_spam[n])
pthread_join(vhd->pthread_spam[n], &retval); pthread_join(vhd->pthread_spam[n], &retval);
if (vhd->ring) if (vhd->ring)
@ -231,7 +234,7 @@ init_fail:
} }
n = lws_snprintf(temp + LWS_PRE, sizeof(temp) - LWS_PRE, n = lws_snprintf(temp + LWS_PRE, sizeof(temp) - LWS_PRE,
"svc tid:%p, %s", (void *)pthread_self(), "svc, %s",
(char *)pmsg->payload + LWS_PRE); (char *)pmsg->payload + LWS_PRE);
/* notice we allowed for LWS_PRE in the payload already */ /* notice we allowed for LWS_PRE in the payload already */
@ -265,8 +268,7 @@ init_fail:
break; break;
case LWS_CALLBACK_EVENT_WAIT_CANCELLED: case LWS_CALLBACK_EVENT_WAIT_CANCELLED:
lwsl_notice("LWS_CALLBACK_EVENT_WAIT_CANCELLED in svc tid %p\n", lwsl_notice("LWS_CALLBACK_EVENT_WAIT_CANCELLED in svc\n");
(void *)pthread_self());
if (!vhd) if (!vhd)
break; break;
/* /*

View file

@ -15,6 +15,12 @@ MACRO(require_pthreads result)
else() else()
message(FATAL_ERROR "threading support requires pthreads") message(FATAL_ERROR "threading support requires pthreads")
endif() endif()
else()
if (WIN32)
set(PTHREAD_LIB ${LWS_EXT_PTHREAD_LIBRARIES})
else()
set(PTHREAD_LIB pthread)
endif()
endif() endif()
ENDMACRO() ENDMACRO()
@ -88,9 +94,9 @@ if (requirements)
add_executable(${SAMP} ${SRCS}) add_executable(${SAMP} ${SRCS})
if (websockets_shared) if (websockets_shared)
target_link_libraries(${SAMP} websockets_shared pthread) target_link_libraries(${SAMP} websockets_shared ${PTHREAD_LIB})
add_dependencies(${SAMP} websockets_shared) add_dependencies(${SAMP} websockets_shared)
else() else()
target_link_libraries(${SAMP} websockets pthread) target_link_libraries(${SAMP} websockets ${PTHREAD_LIB})
endif() endif()
endif() endif()

View file

@ -21,6 +21,12 @@
#include <libwebsockets.h> #include <libwebsockets.h>
#include <string.h> #include <string.h>
#include <signal.h> #include <signal.h>
#if defined(WIN32)
#define HAVE_STRUCT_TIMESPEC
#if defined(pid_t)
#undef pid_t
#endif
#endif
#include <pthread.h> #include <pthread.h>
#define LWS_PLUGIN_STATIC #define LWS_PLUGIN_STATIC

View file

@ -83,7 +83,11 @@ thread_spam(void *d)
struct per_vhost_data__minimal *vhd = struct per_vhost_data__minimal *vhd =
(struct per_vhost_data__minimal *)d; (struct per_vhost_data__minimal *)d;
struct msg amsg; struct msg amsg;
int len = 128, index = 1, n; int len = 128, index = 1, n, whoami = 0;
for (n = 0; n < (int)LWS_ARRAY_SIZE(vhd->pthread_spam); n++)
if (pthread_equal(pthread_self(), vhd->pthread_spam[n]))
whoami = n + 1;
do { do {
/* don't generate output if nobody connected */ /* don't generate output if nobody connected */
@ -105,8 +109,8 @@ thread_spam(void *d)
goto wait_unlock; goto wait_unlock;
} }
n = lws_snprintf((char *)amsg.payload + LWS_PRE, len, n = lws_snprintf((char *)amsg.payload + LWS_PRE, len,
"%s: tid: %p, msg: %d", vhd->config, "%s: tid: %d, msg: %d", vhd->config,
(void *)pthread_self(), index++); whoami, index++);
amsg.len = n; amsg.len = n;
n = lws_ring_insert(vhd->ring, &amsg, 1); n = lws_ring_insert(vhd->ring, &amsg, 1);
if (n != 1) { if (n != 1) {
@ -127,7 +131,7 @@ wait:
} while (!vhd->finished); } while (!vhd->finished);
lwsl_notice("thread_spam %p exiting\n", (void *)pthread_self()); lwsl_notice("thread_spam %d exiting\n", whoami);
pthread_exit(NULL); pthread_exit(NULL);