mirror of
https://git.rwth-aachen.de/acs/public/villas/node/
synced 2025-03-09 00:00:00 +01:00
web: fix lws_callback_on_writable() on macOS caused by multithreading issues
This commit is contained in:
parent
84aff14eed
commit
88b1ec7850
4 changed files with 35 additions and 5 deletions
|
@ -26,6 +26,7 @@
|
|||
#include <pthread.h>
|
||||
|
||||
#include <villas/common.h>
|
||||
#include <villas/queue.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
@ -42,6 +43,8 @@ struct web {
|
|||
struct lws_context *context; /**< The libwebsockets server context. */
|
||||
struct lws_vhost *vhost; /**< The libwebsockets vhost. */
|
||||
|
||||
struct queue writables; /**< Queue of WSIs for which we will call lws_callback_on_writable() */
|
||||
|
||||
int port; /**< Port of the build in HTTP / WebSocket server. */
|
||||
char *htdocs; /**< The root directory for files served via HTTP. */
|
||||
char *ssl_cert; /**< Path to the SSL certitifcate for HTTPS / WSS. */
|
||||
|
@ -65,6 +68,8 @@ int web_stop(struct web *w);
|
|||
/** Parse HTTPd and WebSocket related options */
|
||||
int web_parse(struct web *w, json_t *cfg);
|
||||
|
||||
void web_callback_on_writable(struct lws *wsi);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -326,7 +326,7 @@ int api_stop(struct api *a)
|
|||
|
||||
s->state = API_SESSION_STATE_SHUTDOWN;
|
||||
|
||||
lws_callback_on_writable(s->wsi);
|
||||
web_callback_on_writable(s->wsi);
|
||||
}
|
||||
|
||||
for (int i = 0; i < 10 && list_length(&a->sessions) > 0; i++) {
|
||||
|
@ -373,7 +373,7 @@ static void * api_worker(void *ctx)
|
|||
|
||||
queue_push(&s->response.queue, resp);
|
||||
|
||||
lws_callback_on_writable(s->wsi);
|
||||
web_callback_on_writable(s->wsi);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
|
|
|
@ -164,7 +164,7 @@ static int websocket_connection_write(struct websocket_connection *c, struct sam
|
|||
|
||||
/* Client connections which are currently conecting don't have an associate c->wsi yet */
|
||||
if (c->wsi)
|
||||
lws_callback_on_writable(c->wsi);
|
||||
web_callback_on_writable(c->wsi);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
29
lib/web.c
29
lib/web.c
|
@ -165,19 +165,34 @@ static void logger(int level, const char *msg) {
|
|||
}
|
||||
}
|
||||
|
||||
void web_callback_on_writable(struct lws *wsi)
|
||||
{
|
||||
struct lws_context *ctx = lws_get_context(wsi);
|
||||
struct web *w = lws_context_user(ctx);
|
||||
|
||||
queue_push(&w->writables, (void *) wsi);
|
||||
}
|
||||
|
||||
static void * web_worker(void *ctx)
|
||||
{
|
||||
struct lws *wsi;
|
||||
struct web *w = ctx;
|
||||
|
||||
for (;;)
|
||||
for (;;) {
|
||||
lws_service(w->context, 100);
|
||||
|
||||
while (queue_available(&w->writables)) {
|
||||
queue_pull(&w->writables, (void **) &wsi);
|
||||
lws_callback_on_writable(wsi);
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int web_init(struct web *w, struct api *a)
|
||||
{
|
||||
int lvl = LLL_ERR | LLL_WARN | LLL_NOTICE;
|
||||
int ret, lvl = LLL_ERR | LLL_WARN | LLL_NOTICE;
|
||||
|
||||
if (global_log->level >=10 && global_log->facilities & LOG_WEB)
|
||||
lvl |= (1 << LLL_COUNT) - 1;
|
||||
|
@ -190,6 +205,10 @@ int web_init(struct web *w, struct api *a)
|
|||
w->port = getuid() > 0 ? 8080 : 80; /**< @todo Use libcap to check if user can bind to ports < 1024 */
|
||||
w->htdocs = strdup(WEB_PATH);
|
||||
|
||||
ret = queue_init(&w->writables, 128, &memory_heap);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
w->state = STATE_INITIALIZED;
|
||||
|
||||
return 0;
|
||||
|
@ -312,6 +331,8 @@ int web_stop(struct web *w)
|
|||
|
||||
int web_destroy(struct web *w)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if (w->state == STATE_DESTROYED)
|
||||
return 0;
|
||||
|
||||
|
@ -328,6 +349,10 @@ int web_destroy(struct web *w)
|
|||
if (w->htdocs)
|
||||
free(w->htdocs);
|
||||
|
||||
ret = queue_destroy(&w->writables);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
w->state = STATE_DESTROYED;
|
||||
|
||||
return 0;
|
||||
|
|
Loading…
Add table
Reference in a new issue