Don't leak the http handlers.
git-svn-id: https://www.unprompted.com/svn/projects/tildefriends/trunk@4801 ed5197a5-7fde-0310-b194-c3ffbd925b24
This commit is contained in:
parent
55fb5dce1a
commit
14a4117aff
@ -68,6 +68,7 @@ typedef struct _tf_http_handler_t
|
|||||||
{
|
{
|
||||||
const char* pattern;
|
const char* pattern;
|
||||||
tf_http_callback_t* callback;
|
tf_http_callback_t* callback;
|
||||||
|
tf_http_cleanup_t* cleanup;
|
||||||
void* user_data;
|
void* user_data;
|
||||||
} tf_http_handler_t;
|
} tf_http_handler_t;
|
||||||
|
|
||||||
@ -656,13 +657,14 @@ int tf_http_listen(tf_http_t* http, int port, tf_tls_context_t* tls)
|
|||||||
return assigned_port;
|
return assigned_port;
|
||||||
}
|
}
|
||||||
|
|
||||||
void tf_http_add_handler(tf_http_t* http, const char* pattern, tf_http_callback_t* callback, void* user_data)
|
void tf_http_add_handler(tf_http_t* http, const char* pattern, tf_http_callback_t* callback, tf_http_cleanup_t* cleanup, void* user_data)
|
||||||
{
|
{
|
||||||
http->handlers = tf_realloc(http->handlers, sizeof(tf_http_handler_t) * (http->handlers_count + 1));
|
http->handlers = tf_realloc(http->handlers, sizeof(tf_http_handler_t) * (http->handlers_count + 1));
|
||||||
http->handlers[http->handlers_count++] = (tf_http_handler_t)
|
http->handlers[http->handlers_count++] = (tf_http_handler_t)
|
||||||
{
|
{
|
||||||
.pattern = tf_strdup(pattern),
|
.pattern = tf_strdup(pattern),
|
||||||
.callback = callback,
|
.callback = callback,
|
||||||
|
.cleanup = cleanup,
|
||||||
.user_data = user_data,
|
.user_data = user_data,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@ -691,6 +693,10 @@ void tf_http_destroy(tf_http_t* http)
|
|||||||
tf_free((void*)http->handlers[i].pattern);
|
tf_free((void*)http->handlers[i].pattern);
|
||||||
http->handlers[i].pattern = NULL;
|
http->handlers[i].pattern = NULL;
|
||||||
}
|
}
|
||||||
|
if (http->handlers[i].cleanup)
|
||||||
|
{
|
||||||
|
http->handlers[i].cleanup(http->handlers[i].user_data);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
tf_free(http->handlers);
|
tf_free(http->handlers);
|
||||||
http->handlers_count = 0;
|
http->handlers_count = 0;
|
||||||
|
@ -38,7 +38,7 @@ typedef void (tf_http_cleanup_t)(void* user_data);
|
|||||||
tf_http_t* tf_http_create(uv_loop_t* loop);
|
tf_http_t* tf_http_create(uv_loop_t* loop);
|
||||||
void tf_http_set_trace(tf_http_t* http, tf_trace_t* trace);
|
void tf_http_set_trace(tf_http_t* http, tf_trace_t* trace);
|
||||||
int tf_http_listen(tf_http_t* http, int port, tf_tls_context_t* tls);
|
int tf_http_listen(tf_http_t* http, int port, tf_tls_context_t* tls);
|
||||||
void tf_http_add_handler(tf_http_t* http, const char* pattern, tf_http_callback_t* callback, void* user_data);
|
void tf_http_add_handler(tf_http_t* http, const char* pattern, tf_http_callback_t* callback, tf_http_cleanup_t* cleanup, void* user_data);
|
||||||
void tf_http_respond(tf_http_request_t* request, int status, const char** headers, int headers_count, const void* body, size_t content_length);
|
void tf_http_respond(tf_http_request_t* request, int status, const char** headers, int headers_count, const void* body, size_t content_length);
|
||||||
size_t tf_http_get_body(const tf_http_request_t* request, const void** out_data);
|
size_t tf_http_get_body(const tf_http_request_t* request, const void** out_data);
|
||||||
void tf_http_destroy(tf_http_t* http);
|
void tf_http_destroy(tf_http_t* http);
|
||||||
|
@ -334,6 +334,13 @@ static JSValue _httpd_websocket_upgrade(JSContext* context, JSValueConst this_va
|
|||||||
return JS_UNDEFINED;
|
return JS_UNDEFINED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void _httpd_cleanup_callback(void* user_data)
|
||||||
|
{
|
||||||
|
http_handler_data_t* data = user_data;
|
||||||
|
JS_FreeValue(data->context, data->callback);
|
||||||
|
tf_free(data);
|
||||||
|
}
|
||||||
|
|
||||||
static JSValue _httpd_endpoint_all(JSContext* context, JSValueConst this_val, int argc, JSValueConst* argv)
|
static JSValue _httpd_endpoint_all(JSContext* context, JSValueConst this_val, int argc, JSValueConst* argv)
|
||||||
{
|
{
|
||||||
tf_http_t* http = JS_GetOpaque(this_val, _httpd_class_id);
|
tf_http_t* http = JS_GetOpaque(this_val, _httpd_class_id);
|
||||||
@ -341,7 +348,7 @@ static JSValue _httpd_endpoint_all(JSContext* context, JSValueConst this_val, in
|
|||||||
http_handler_data_t* data = tf_malloc(sizeof(http_handler_data_t));
|
http_handler_data_t* data = tf_malloc(sizeof(http_handler_data_t));
|
||||||
*data = (http_handler_data_t) { .context = context, .callback = JS_DupValue(context, argv[1]) };
|
*data = (http_handler_data_t) { .context = context, .callback = JS_DupValue(context, argv[1]) };
|
||||||
/* TODO: This leaks the callback. */
|
/* TODO: This leaks the callback. */
|
||||||
tf_http_add_handler(http, pattern, _httpd_callback, data);
|
tf_http_add_handler(http, pattern, _httpd_callback, _httpd_cleanup_callback, data);
|
||||||
JS_FreeCString(context, pattern);
|
JS_FreeCString(context, pattern);
|
||||||
return JS_UNDEFINED;
|
return JS_UNDEFINED;
|
||||||
}
|
}
|
||||||
@ -527,11 +534,11 @@ void tf_httpd_register(JSContext* context)
|
|||||||
tf_http_set_trace(http, tf_task_get_trace(task));
|
tf_http_set_trace(http, tf_task_get_trace(task));
|
||||||
JS_SetOpaque(httpd, http);
|
JS_SetOpaque(httpd, http);
|
||||||
|
|
||||||
tf_http_add_handler(http, "/debug", _httpd_endpoint_debug, task);
|
tf_http_add_handler(http, "/debug", _httpd_endpoint_debug, NULL, task);
|
||||||
tf_http_add_handler(http, "/disconnections", _httpd_endpoint_disconnections, task);
|
tf_http_add_handler(http, "/disconnections", _httpd_endpoint_disconnections, NULL, task);
|
||||||
tf_http_add_handler(http, "/hitches", _httpd_endpoint_hitches, task);
|
tf_http_add_handler(http, "/hitches", _httpd_endpoint_hitches, NULL, task);
|
||||||
tf_http_add_handler(http, "/mem", _httpd_endpoint_mem, task);
|
tf_http_add_handler(http, "/mem", _httpd_endpoint_mem, NULL, task);
|
||||||
tf_http_add_handler(http, "/trace", _httpd_endpoint_trace, task);
|
tf_http_add_handler(http, "/trace", _httpd_endpoint_trace, NULL, task);
|
||||||
|
|
||||||
JS_SetPropertyStr(context, httpd, "handlers", JS_NewObject(context));
|
JS_SetPropertyStr(context, httpd, "handlers", JS_NewObject(context));
|
||||||
JS_SetPropertyStr(context, httpd, "all", JS_NewCFunction(context, _httpd_endpoint_all, "all", 2));
|
JS_SetPropertyStr(context, httpd, "all", JS_NewCFunction(context, _httpd_endpoint_all, "all", 2));
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
#include "socket.js.h"
|
#include "socket.js.h"
|
||||||
|
|
||||||
|
#include "log.h"
|
||||||
#include "mem.h"
|
#include "mem.h"
|
||||||
#include "task.h"
|
#include "task.h"
|
||||||
#include "tls.h"
|
#include "tls.h"
|
||||||
|
@ -1838,6 +1838,15 @@ void tf_task_destroy(tf_task_t* task)
|
|||||||
{
|
{
|
||||||
tf_ssb_destroy(task->_ssb);
|
tf_ssb_destroy(task->_ssb);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* This ensures the HTTP handlers get cleaned up. */
|
||||||
|
if (task->_trusted)
|
||||||
|
{
|
||||||
|
JSValue global = JS_GetGlobalObject(task->_context);
|
||||||
|
JS_SetPropertyStr(task->_context, global, "httpd", JS_UNDEFINED);
|
||||||
|
JS_FreeValue(task->_context, global);
|
||||||
|
}
|
||||||
|
|
||||||
JS_FreeContext(task->_context);
|
JS_FreeContext(task->_context);
|
||||||
JS_FreeRuntime(task->_runtime);
|
JS_FreeRuntime(task->_runtime);
|
||||||
|
|
||||||
|
@ -737,8 +737,8 @@ static void _test_http(const tf_test_options_t* options)
|
|||||||
uv_loop_t loop = { 0 };
|
uv_loop_t loop = { 0 };
|
||||||
uv_loop_init(&loop);
|
uv_loop_init(&loop);
|
||||||
tf_http_t* http = tf_http_create(&loop);
|
tf_http_t* http = tf_http_create(&loop);
|
||||||
tf_http_add_handler(http, "/hello", _test_http_handler, NULL);
|
tf_http_add_handler(http, "/hello", _test_http_handler, NULL, NULL);
|
||||||
tf_http_add_handler(http, "/post", _test_http_handler_post, NULL);
|
tf_http_add_handler(http, "/post", _test_http_handler_post, NULL, NULL);
|
||||||
tf_http_listen(http, 23456, NULL);
|
tf_http_listen(http, 23456, NULL);
|
||||||
|
|
||||||
test_http_t test = { .loop = &loop };
|
test_http_t test = { .loop = &loop };
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
#include "tlscontext.js.h"
|
#include "tlscontext.js.h"
|
||||||
|
|
||||||
|
#include "log.h"
|
||||||
#include "mem.h"
|
#include "mem.h"
|
||||||
#include "task.h"
|
#include "task.h"
|
||||||
#include "tls.h"
|
#include "tls.h"
|
||||||
|
Loading…
Reference in New Issue
Block a user