diff --git a/Makefile b/Makefile index 93c76448..54c4af55 100644 --- a/Makefile +++ b/Makefile @@ -383,7 +383,7 @@ OBJLIST = \ ${OBJDIR}win32_pthread_key_delete${OBJEXT} \ ${OBJDIR}win32_pthread_mutex_destroy${OBJEXT} \ ${OBJDIR}win32_pthread_mutex_init${OBJEXT} \ - ${OBJDIR}win32_pthread_mutex_lock${OBJEXT} \ + ${OBJDIR}httplib_pthread_mutex_lock${OBJEXT} \ ${OBJDIR}httplib_pthread_mutex_trylock${OBJEXT} \ ${OBJDIR}httplib_pthread_mutex_unlock${OBJEXT} \ ${OBJDIR}httplib_pthread_self${OBJEXT} \ @@ -1446,8 +1446,7 @@ ${OBJDIR}win32_pthread_mutex_init${OBJEXT} : ${SRCDIR}win32_pthread_mutex_ini ${SRCDIR}httplib_main.h \ ${INCDIR}libhttp.h -${OBJDIR}win32_pthread_mutex_lock${OBJEXT} : ${SRCDIR}win32_pthread_mutex_lock.c \ - ${SRCDIR}httplib_pthread.h \ +${OBJDIR}httplib_pthread_mutex_lock${OBJEXT} : ${SRCDIR}httplib_pthread_mutex_lock.c \ ${SRCDIR}httplib_main.h \ ${INCDIR}libhttp.h diff --git a/doc/api/httplib_pthread_mutex_lock.md b/doc/api/httplib_pthread_mutex_lock.md new file mode 100644 index 00000000..71f5036d --- /dev/null +++ b/doc/api/httplib_pthread_mutex_lock.md @@ -0,0 +1,26 @@ +# LibHTTP API Reference + +### `httplib_pthread_mutex_lock( mutex );` + +### Parameters + +| Parameter | Type | Description | +| :--- | :--- | :--- | +|**`mutex`**|`pthread_mutex_t`|The key to the mutex to lock| + +### Return Value + +| Type | Description | +| :--- | :--- | +|`int`|Integer value with the result of the function| + +### Description + +The platform independent function `httplib_pthread_mutex_lock()` is used to lock a mutex. The function returns **0** if this is succesful, or an error code if it fails. If a mutex is locked by another thread, the function will not return but wait until the other thread releases the mutex and the mutex be successfully locked. On systems which support it, this function is implemented as a direct call to `pthread_mutex_lock()`. On other systems own code is used to emulate the same functionality. + +### See Also + +* [`httplib_pthread_mutex_destroy();`](httplib_pthread_mutex_destroy.md) +* [`httplib_pthread_mutex_init();`](httplib_pthread_mutex_init.md) +* [`httplib_pthread_mutex_trylock();`](httplib_pthread_mutex_trylock.md) +* [`httplib_pthread_mutex_unlock();`](httplib_pthread_mutex_unlock.md) diff --git a/doc/api/httplib_pthread_mutex_trylock.md b/doc/api/httplib_pthread_mutex_trylock.md index f6bb3561..ba6bdefa 100644 --- a/doc/api/httplib_pthread_mutex_trylock.md +++ b/doc/api/httplib_pthread_mutex_trylock.md @@ -24,6 +24,3 @@ The platform independent function `httplib_pthread_mutex_trylock()` is used to t * [`httplib_pthread_mutex_init();`](httplib_pthread_mutex_init.md) * [`httplib_pthread_mutex_lock();`](httplib_pthread_mutex_lock.md) * [`httplib_pthread_mutex_unlock();`](httplib_pthread_mutex_unlock.md) - -* [`httplib_pthread_getspecific();`](httplib_pthread_getspecific.md) -* [`httplib_pthread_self();`](httplib_pthread_self.md) diff --git a/doc/api/httplib_pthread_mutex_unlock.md b/doc/api/httplib_pthread_mutex_unlock.md index 431ac62f..6fd57940 100644 --- a/doc/api/httplib_pthread_mutex_unlock.md +++ b/doc/api/httplib_pthread_mutex_unlock.md @@ -24,6 +24,3 @@ The platform independent function `httplib_pthread_mutex_unlock()` is used to re * [`httplib_pthread_mutex_init();`](httplib_pthread_mutex_init.md) * [`httplib_pthread_mutex_lock();`](httplib_pthread_mutex_lock.md) * [`httplib_pthread_mutex_trylock();`](httplib_pthread_mutex_trylock.md) - -* [`httplib_pthread_getspecific();`](httplib_pthread_getspecific.md) -* [`httplib_pthread_self();`](httplib_pthread_self.md) diff --git a/include/libhttp.h b/include/libhttp.h index bf7120f4..220de4ad 100644 --- a/include/libhttp.h +++ b/include/libhttp.h @@ -985,6 +985,7 @@ LIBHTTP_API int httplib_kill( pid_t pid, int sig_num ); LIBHTTP_API int httplib_mkdir( const char *path, int mode ); LIBHTTP_API DIR * httplib_opendir( const char *name ); LIBHTTP_API int httplib_poll( struct pollfd *pfd, unsigned int nfds, int timeout ); +LIBHTTP_API int httplib_pthread_mutex_lock( pthread_mutex_t *mutex ); LIBHTTP_API int httplib_pthread_mutex_trylock( pthread_mutex_t *mutex ); LIBHTTP_API int httplib_pthread_mutex_unlock( pthread_mutex_t *mutex ); LIBHTTP_API pthread_t httplib_pthread_self( void ); diff --git a/src/httplib_consume_socket.c b/src/httplib_consume_socket.c index c6fd59e3..90475e49 100644 --- a/src/httplib_consume_socket.c +++ b/src/httplib_consume_socket.c @@ -54,9 +54,9 @@ int XX_httplib_consume_socket( struct httplib_context *ctx, struct socket *sp, i #define QUEUE_SIZE(ctx) ((int)(ARRAY_SIZE(ctx->queue))) - (void)thread_index; + UNUSED_PARAMETER(thread_index); - pthread_mutex_lock(&ctx->thread_mutex); + httplib_pthread_mutex_lock( & ctx->thread_mutex ); /* If the queue is empty, wait. We're idle at this point. */ while (ctx->sq_head == ctx->sq_tail && ctx->stop_flag == 0) { diff --git a/src/httplib_event_queue.c b/src/httplib_event_queue.c index b8d7980c..f91e0c3f 100644 --- a/src/httplib_event_queue.c +++ b/src/httplib_event_queue.c @@ -121,7 +121,7 @@ void *event_create(void) { int event_wait(void *eventhdl) { struct posix_event *ev = (struct posix_event *)eventhdl; - pthread_mutex_lock(&(ev->mutex)); + httplib_pthread_mutex_lock( & ev->mutex ); pthread_cond_wait(&(ev->cond), &(ev->mutex)); httplib_pthread_mutex_unlock( & ev->mutex ); return 1; @@ -132,7 +132,7 @@ int event_wait(void *eventhdl) { int event_signal(void *eventhdl) { struct posix_event *ev = (struct posix_event *)eventhdl; - pthread_mutex_lock(&(ev->mutex)); + httplib_pthread_mutex_lock( & ev->mutex ); pthread_cond_signal(&(ev->cond)); httplib_pthread_mutex_unlock( & ev->mutex ); return 1; diff --git a/src/httplib_lock_unlock_connection.c b/src/httplib_lock_unlock_connection.c index e4acfc35..c1d81e8e 100644 --- a/src/httplib_lock_unlock_connection.c +++ b/src/httplib_lock_unlock_connection.c @@ -36,7 +36,7 @@ void httplib_lock_connection( struct httplib_connection *conn ) { - if ( conn != NULL ) pthread_mutex_lock( & conn->mutex ); + if ( conn != NULL ) httplib_pthread_mutex_lock( & conn->mutex ); } /* httplib_lock_connection */ diff --git a/src/httplib_lock_unlock_context.c b/src/httplib_lock_unlock_context.c index b9c87ce5..7d973e8e 100644 --- a/src/httplib_lock_unlock_context.c +++ b/src/httplib_lock_unlock_context.c @@ -36,7 +36,7 @@ void httplib_lock_context( struct httplib_context *ctx ) { - if ( ctx != NULL ) pthread_mutex_lock( & ctx->nonce_mutex ); + if ( ctx != NULL ) httplib_pthread_mutex_lock( & ctx->nonce_mutex ); } /* httplib_lock_context */ diff --git a/src/httplib_master_thread.c b/src/httplib_master_thread.c index e5de57af..c8be75c1 100644 --- a/src/httplib_master_thread.c +++ b/src/httplib_master_thread.c @@ -129,7 +129,7 @@ static void master_thread_run(void *thread_func_param) { XX_httplib_close_all_listening_sockets(ctx); /* Wakeup workers that are waiting for connections to handle. */ - pthread_mutex_lock(&ctx->thread_mutex); + httplib_pthread_mutex_lock( & ctx->thread_mutex ); #if defined(ALTERNATIVE_QUEUE) for (i = 0; i < ctx->cfg_worker_threads; i++) { event_signal(ctx->client_wait_events[i]); diff --git a/src/httplib_produce_socket.c b/src/httplib_produce_socket.c index 013ff0dc..21b3e893 100644 --- a/src/httplib_produce_socket.c +++ b/src/httplib_produce_socket.c @@ -62,13 +62,14 @@ void XX_httplib_produce_socket( struct httplib_context *ctx, const struct socket void XX_httplib_produce_socket(struct httplib_context *ctx, const struct socket *sp) { #define QUEUE_SIZE(ctx) ((int)(ARRAY_SIZE(ctx->queue))) - if (!ctx) return; - pthread_mutex_lock(&ctx->thread_mutex); + + if ( ctx == NULL ) return; + + httplib_pthread_mutex_lock( & ctx->thread_mutex ); /* If the queue is full, wait */ - while (ctx->stop_flag == 0 - && ctx->sq_head - ctx->sq_tail >= QUEUE_SIZE(ctx)) { - (void)pthread_cond_wait(&ctx->sq_empty, &ctx->thread_mutex); + while (ctx->stop_flag == 0 && ctx->sq_head - ctx->sq_tail >= QUEUE_SIZE(ctx)) { + pthread_cond_wait(&ctx->sq_empty, &ctx->thread_mutex); } if (ctx->sq_head - ctx->sq_tail < QUEUE_SIZE(ctx)) { diff --git a/src/httplib_pthread.h b/src/httplib_pthread.h index 6af50924..902c6e99 100644 --- a/src/httplib_pthread.h +++ b/src/httplib_pthread.h @@ -42,7 +42,6 @@ int pthread_key_delete( pthread_key_t key ); int pthread_mutex_destroy( pthread_mutex_t *mutex ); int pthread_mutex_init( pthread_mutex_t *mutex, void *unused ); -int pthread_mutex_lock( pthread_mutex_t *mutex ); void * pthread_getspecific( pthread_key_t key ); diff --git a/src/win32_pthread_mutex_lock.c b/src/httplib_pthread_mutex_lock.c similarity index 60% rename from src/win32_pthread_mutex_lock.c rename to src/httplib_pthread_mutex_lock.c index 7dceb85a..01f4143d 100644 --- a/src/win32_pthread_mutex_lock.c +++ b/src/httplib_pthread_mutex_lock.c @@ -22,18 +22,34 @@ * THE SOFTWARE. * * ============ - * Release: 1.8 + * Release: 2.0 */ #include "httplib_main.h" -#include "httplib_pthread.h" + +/* + * int httplib_pthread_mutex_lock( pthread_mutex_t *mutex ); + * + * The platform independent function httplib_pthread_mutex_lock() starts a + * blocking call to lock a mutex. If the mutex is locked by another thread, the + * function will wait until the mutex has been released. Success is indicated + * with the return value 0, while another value indicates an error. + * + * On systems wshich support it, this function is implemented with a direct + * call to pthread_mutex_lock(). On other systems own code is used to emulate + * the same behaviour. + */ + +int httplib_pthread_mutex_lock( pthread_mutex_t *mutex ) { #if defined(_WIN32) -int pthread_mutex_lock( pthread_mutex_t *mutex ) { + return ( WaitForSingleObject( *mutex, INFINITE ) == WAIT_OBJECT_0 ) ? 0 : -1; - return (WaitForSingleObject(*mutex, INFINITE) == WAIT_OBJECT_0) ? 0 : -1; +#else /* _WIN32 */ -} /* pthread_mutex_lock */ + return pthread_mutex_lock( mutex ); -#endif /* _WIN32 */ +#endif /* _WIN32 */ + +} /* httplib_pthread_mutex_lock */ diff --git a/src/httplib_send_authorization_request.c b/src/httplib_send_authorization_request.c index 37966ba4..8eaa46c0 100644 --- a/src/httplib_send_authorization_request.c +++ b/src/httplib_send_authorization_request.c @@ -40,7 +40,7 @@ void XX_httplib_send_authorization_request( struct httplib_connection *conn ) { uint64_t nonce = (uint64_t)(conn->ctx->start_time); - pthread_mutex_lock(&conn->ctx->nonce_mutex); + httplib_pthread_mutex_lock( & conn->ctx->nonce_mutex ); nonce += conn->ctx->nonce_count; ++conn->ctx->nonce_count; httplib_pthread_mutex_unlock( & conn->ctx->nonce_mutex ); diff --git a/src/httplib_ssl_locking_callback.c b/src/httplib_ssl_locking_callback.c index a135dce2..0dcf34ff 100644 --- a/src/httplib_ssl_locking_callback.c +++ b/src/httplib_ssl_locking_callback.c @@ -45,7 +45,7 @@ void XX_httplib_ssl_locking_callback( int mode, int mutex_num, const char *file, UNUSED_PARAMETER(line); UNUSED_PARAMETER(file); - if ( mode & 1 ) pthread_mutex_lock( & XX_httplib_ssl_mutexes[mutex_num] ); + if ( mode & 1 ) httplib_pthread_mutex_lock( & XX_httplib_ssl_mutexes[mutex_num] ); else httplib_pthread_mutex_unlock( & XX_httplib_ssl_mutexes[mutex_num] ); } /* XX_httplib_ssl_locking_callback */ diff --git a/src/httplib_timer.c b/src/httplib_timer.c index fc89dacb..95211403 100644 --- a/src/httplib_timer.c +++ b/src/httplib_timer.c @@ -77,7 +77,7 @@ static int timer_add( struct httplib_context *ctx, double next_time, double peri if ( is_relative ) next_time += dt; else if ( next_time < dt ) next_time = dt; - pthread_mutex_lock(&ctx->timers->mutex); + httplib_pthread_mutex_lock( & ctx->timers->mutex ); if (ctx->timers->timer_count == MAX_TIMERS) { error = 1; } else { @@ -129,7 +129,7 @@ static void timer_thread_run( void *thread_func_param ) { clock_gettime(CLOCK_MONOTONIC, &now); d = (double)now.tv_sec + (double)now.tv_nsec * 1.0E-9; while (ctx->stop_flag == 0) { - pthread_mutex_lock(&ctx->timers->mutex); + httplib_pthread_mutex_lock( & ctx->timers->mutex ); if (ctx->timers->timer_count > 0 && d >= ctx->timers->timers[0].time) { t = ctx->timers->timers[0]; for (u = 1; u < ctx->timers->timer_count; u++) {