Skip to content

Don't use _Thread_local in run-test262.c #667

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Nov 9, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@ jobs:
make cxxtest

- name: test
if: ${{ matrix.config.configType != 'examples' && matrix.config.configType != 'tcc' }}
if: ${{ matrix.config.configType != 'examples' }}
run: |
make test

Expand Down
9 changes: 1 addition & 8 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -289,14 +289,7 @@ endif()
# Test262 runner
#

if(EMSCRIPTEN
OR CMAKE_C_COMPILER_ID STREQUAL "TinyCC"
OR (CMAKE_C_COMPILER_ID STREQUAL "GNU" AND CMAKE_C_COMPILER_VERSION VERSION_LESS 5))
# Empty. run-test262 uses pthreads, sorry Windows users.
# tcc and gcc 4.8 don't understand _Thread_local, whereas I
# don't understand why people still use 4.8 in this day and age
# but hey, here we are.
else()
if(NOT EMSCRIPTEN)
add_executable(run-test262
run-test262.c
)
Expand Down
71 changes: 44 additions & 27 deletions quickjs-libc.c
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,16 @@ static BOOL my_isdigit(int c)
return (c >= '0' && c <= '9');
}

static JSThreadState *js_get_thread_state(JSRuntime *rt)
{
return (JSThreadState *)js_std_cmd(/*GetOpaque*/0, rt);
}

static void js_set_thread_state(JSRuntime *rt, JSThreadState *ts)
{
js_std_cmd(/*SetOpaque*/1, rt, ts);
}
Comment on lines +184 to +192
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The other approach is a mutex-protected list or hash table but this seemed all around easier.


static JSValue js_printf_internal(JSContext *ctx,
int argc, JSValue *argv, FILE *fp)
{
Expand Down Expand Up @@ -831,7 +841,7 @@ static JSValue js_evalScript(JSContext *ctx, JSValue this_val,
int argc, JSValue *argv)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
const char *str = NULL;
size_t len;
JSValue ret, obj;
Expand Down Expand Up @@ -905,7 +915,7 @@ static BOOL is_stdio(FILE *f)

static void js_std_file_finalizer(JSRuntime *rt, JSValue val)
{
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSSTDFile *s = JS_GetOpaque(val, ts->std_file_class_id);
if (s) {
if (s->f && !is_stdio(s->f)) {
Expand Down Expand Up @@ -939,7 +949,7 @@ static JSValue js_std_strerror(JSContext *ctx, JSValue this_val,
static JSValue js_new_std_file(JSContext *ctx, FILE *f, BOOL is_popen)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSSTDFile *s;
JSValue obj;
obj = JS_NewObjectClass(ctx, ts->std_file_class_id);
Expand Down Expand Up @@ -1099,7 +1109,7 @@ static JSValue js_std_printf(JSContext *ctx, JSValue this_val,
static FILE *js_std_file_get(JSContext *ctx, JSValue obj)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSSTDFile *s = JS_GetOpaque2(ctx, obj, ts->std_file_class_id);
if (!s)
return NULL;
Expand Down Expand Up @@ -1140,7 +1150,7 @@ static JSValue js_std_file_close(JSContext *ctx, JSValue this_val,
int argc, JSValue *argv)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSSTDFile *s = JS_GetOpaque2(ctx, this_val, ts->std_file_class_id);
int err;
if (!s)
Expand Down Expand Up @@ -1657,7 +1667,7 @@ static int js_std_init(JSContext *ctx, JSModuleDef *m)
{
JSValue proto;
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);

/* FILE class */
/* the class ID is created once */
Expand Down Expand Up @@ -1945,7 +1955,7 @@ static JSValue js_os_rename(JSContext *ctx, JSValue this_val,

static BOOL is_main_thread(JSRuntime *rt)
{
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
return !ts->recv_pipe;
}

Expand Down Expand Up @@ -1976,7 +1986,7 @@ static JSValue js_os_setReadHandler(JSContext *ctx, JSValue this_val,
int argc, JSValue *argv, int magic)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSOSRWHandler *rh;
int fd;
JSValue func;
Expand Down Expand Up @@ -2046,7 +2056,7 @@ static JSValue js_os_signal(JSContext *ctx, JSValue this_val,
int argc, JSValue *argv)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSOSSignalHandler *sh;
uint32_t sig_num;
JSValue func;
Expand Down Expand Up @@ -2128,7 +2138,7 @@ static JSValue js_os_setTimeout(JSContext *ctx, JSValue this_val,
int argc, JSValue *argv, int magic)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
int64_t delay;
JSValue func;
JSOSTimer *th;
Expand Down Expand Up @@ -2171,7 +2181,7 @@ static JSValue js_os_clearTimeout(JSContext *ctx, JSValue this_val,
int argc, JSValue *argv)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSOSTimer *th;
int64_t timer_id;

Expand All @@ -2189,7 +2199,7 @@ static JSValue js_os_sleepAsync(JSContext *ctx, JSValueConst this_val,
int argc, JSValueConst *argv)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
int64_t delay;
JSOSTimer *th;
JSValue promise, resolving_funcs[2];
Expand Down Expand Up @@ -2228,7 +2238,7 @@ static int call_handler(JSContext *ctx, JSValue func)
r = 0;
if (JS_IsException(ret)) {
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
ts->exc = JS_GetException(ctx);
r = -1;
}
Expand Down Expand Up @@ -2278,7 +2288,7 @@ static int js_os_run_timers(JSRuntime *rt, JSContext *ctx, JSThreadState *ts, in
static int js_os_poll(JSContext *ctx)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
int min_delay, console_fd;
JSOSRWHandler *rh;
struct list_head *el;
Expand Down Expand Up @@ -2407,7 +2417,7 @@ static int handle_posted_message(JSRuntime *rt, JSContext *ctx,
static int js_os_poll(JSContext *ctx)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
int ret, fd_max, min_delay;
fd_set rfds, wfds;
JSOSRWHandler *rh;
Expand Down Expand Up @@ -3415,7 +3425,7 @@ static void js_free_port(JSRuntime *rt, JSWorkerMessageHandler *port)

static void js_worker_finalizer(JSRuntime *rt, JSValue val)
{
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSWorkerData *worker = JS_GetOpaque(val, ts->worker_class_id);
if (worker) {
js_free_message_pipe(worker->recv_pipe);
Expand Down Expand Up @@ -3448,7 +3458,7 @@ static void *worker_func(void *opaque)
JS_SetModuleLoaderFunc(rt, NULL, js_module_loader, NULL);

/* set the pipe to communicate with the parent */
ts = JS_GetRuntimeOpaque(rt);
ts = js_get_thread_state(rt);
ts->recv_pipe = args->recv_pipe;
ts->send_pipe = args->send_pipe;

Expand Down Expand Up @@ -3485,7 +3495,7 @@ static JSValue js_worker_ctor_internal(JSContext *ctx, JSValue new_target,
JSWorkerMessagePipe *send_pipe)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSValue obj = JS_UNDEFINED, proto;
JSWorkerData *s;

Expand Down Expand Up @@ -3602,7 +3612,7 @@ static JSValue js_worker_postMessage(JSContext *ctx, JSValue this_val,
int argc, JSValue *argv)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSWorkerData *worker = JS_GetOpaque2(ctx, this_val, ts->worker_class_id);
JSWorkerMessagePipe *ps;
size_t data_len, i;
Expand Down Expand Up @@ -3681,7 +3691,7 @@ static JSValue js_worker_set_onmessage(JSContext *ctx, JSValue this_val,
JSValue func)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSWorkerData *worker = JS_GetOpaque2(ctx, this_val, ts->worker_class_id);
JSWorkerMessageHandler *port;

Expand Down Expand Up @@ -3715,7 +3725,7 @@ static JSValue js_worker_set_onmessage(JSContext *ctx, JSValue this_val,
static JSValue js_worker_get_onmessage(JSContext *ctx, JSValue this_val)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSWorkerData *worker = JS_GetOpaque2(ctx, this_val, ts->worker_class_id);
JSWorkerMessageHandler *port;
if (!worker)
Expand Down Expand Up @@ -3862,7 +3872,7 @@ static const JSCFunctionListEntry js_os_funcs[] = {
static int js_os_init(JSContext *ctx, JSModuleDef *m)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);

ts->can_js_os_poll = TRUE;

Expand Down Expand Up @@ -3989,6 +3999,13 @@ void js_std_add_helpers(JSContext *ctx, int argc, char **argv)
JS_FreeValue(ctx, global_obj);
}

static void js_std_finalize(JSRuntime *rt, void *arg)
{
JSThreadState *ts = arg;
js_set_thread_state(rt, NULL);
js_free_rt(rt, ts);
}

void js_std_init_handlers(JSRuntime *rt)
{
JSThreadState *ts;
Expand All @@ -4006,8 +4023,8 @@ void js_std_init_handlers(JSRuntime *rt)
ts->next_timer_id = 1;
ts->exc = JS_UNDEFINED;

JS_SetRuntimeOpaque(rt, ts);
JS_AddRuntimeFinalizer(rt, js_free_rt, ts);
js_set_thread_state(rt, ts);
JS_AddRuntimeFinalizer(rt, js_std_finalize, ts);

#ifdef USE_WORKER
/* set the SharedArrayBuffer memory handlers */
Expand All @@ -4024,7 +4041,7 @@ void js_std_init_handlers(JSRuntime *rt)

void js_std_free_handlers(JSRuntime *rt)
{
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
struct list_head *el, *el1;

list_for_each_safe(el, el1, &ts->os_rw_handlers) {
Expand Down Expand Up @@ -4101,7 +4118,7 @@ void js_std_promise_rejection_tracker(JSContext *ctx, JSValue promise,
JSValue js_std_loop(JSContext *ctx)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSContext *ctx1;
int err;

Expand Down Expand Up @@ -4131,7 +4148,7 @@ JSValue js_std_loop(JSContext *ctx)
JSValue js_std_await(JSContext *ctx, JSValue obj)
{
JSRuntime *rt = JS_GetRuntime(ctx);
JSThreadState *ts = JS_GetRuntimeOpaque(rt);
JSThreadState *ts = js_get_thread_state(rt);
JSValue ret;
int state;

Expand Down
25 changes: 25 additions & 0 deletions quickjs.c
Original file line number Diff line number Diff line change
Expand Up @@ -298,6 +298,7 @@ struct JSRuntime {
JSShape **shape_hash;
bf_context_t bf_ctx;
void *user_opaque;
void *libc_opaque;
JSRuntimeFinalizerState *finalizers;
};

Expand Down Expand Up @@ -55424,6 +55425,30 @@ BOOL JS_DetectModule(const char *input, size_t input_len)
return is_module;
}

uintptr_t js_std_cmd(int cmd, ...) {
JSRuntime *rt;
uintptr_t rv;
va_list ap;

rv = 0;
va_start(ap, cmd);
switch (cmd) {
case 0: // GetOpaque
rt = va_arg(ap, JSRuntime *);
rv = (uintptr_t)rt->libc_opaque;
break;
case 1: // SetOpaque
rt = va_arg(ap, JSRuntime *);
rt->libc_opaque = va_arg(ap, void *);
break;
default:
rv = -1;
}
va_end(ap);

return rv;
}

#undef malloc
#undef free
#undef realloc
3 changes: 3 additions & 0 deletions quickjs.h
Original file line number Diff line number Diff line change
Expand Up @@ -1031,6 +1031,9 @@ JS_EXTERN int JS_SetModuleExportList(JSContext *ctx, JSModuleDef *m,

JS_EXTERN const char* JS_GetVersion(void);

/* Integration point for quickjs-libc.c, not for public use. */
JS_EXTERN uintptr_t js_std_cmd(int cmd, ...);

#undef JS_EXTERN
#undef js_force_inline
#undef __js_printf_like
Expand Down
Loading
Loading