From a88c481b02a7a350f056ef0d809fd63da476fa4f Mon Sep 17 00:00:00 2001 From: Matthew Flatt Date: Thu, 19 Nov 2009 16:12:04 +0000 Subject: [PATCH] fix check for on-demand JITting svn: r16892 --- src/mzscheme/src/future.c | 32 ++++++++++++++++++++------------ src/mzscheme/src/future.h | 2 +- src/mzscheme/src/jit.c | 3 ++- src/mzscheme/src/thread.c | 4 ++++ 4 files changed, 27 insertions(+), 14 deletions(-) diff --git a/src/mzscheme/src/future.c b/src/mzscheme/src/future.c index 409388e431..8799435239 100644 --- a/src/mzscheme/src/future.c +++ b/src/mzscheme/src/future.c @@ -50,7 +50,7 @@ void scheme_init_futures(Scheme_Env *env) extern void *on_demand_jit_code; -#define THREAD_POOL_SIZE 1 +#define THREAD_POOL_SIZE 7 #define INITIAL_C_STACK_SIZE 500000 static pthread_t g_pool_threads[THREAD_POOL_SIZE]; static int *g_fuel_pointers[THREAD_POOL_SIZE]; @@ -103,7 +103,7 @@ THREAD_LOCAL_DECL(static future_t *current_ft); #ifndef UNIT_TEST static void *worker_thread_future_loop(void *arg); static void invoke_rtcall(future_t *future); -static future_t *enqueue_future(void); +static future_t *enqueue_future(future_t *ft);; static future_t *get_pending_future(void); static future_t *get_my_future(void); static future_t *get_last_future(void); @@ -455,8 +455,9 @@ Scheme_Object *future(int argc, Scheme_Object *argv[]) ncd = nc->code; //Create the future descriptor and add to the queue as 'pending' - pthread_mutex_lock(&g_future_queue_mutex); - ft = enqueue_future(); + ft = MALLOC_ONE_TAGGED(future_t); + ft->so.type = scheme_future_type; + futureid = ++g_next_futureid; ft->id = futureid; ft->orig_lambda = lambda; @@ -479,8 +480,6 @@ Scheme_Object *future(int argc, Scheme_Object *argv[]) ft->runstack_size = init_runstack_size; } - //pthread_mutex_unlock(&g_future_queue_mutex); - //JIT compile the code if not already jitted //Temporarily repoint MZ_RUNSTACK //to the worker thread's runstack - @@ -491,9 +490,10 @@ Scheme_Object *future(int argc, Scheme_Object *argv[]) scheme_on_demand_generate_lambda(nc, 0, NULL); } - //pthread_mutex_lock(&g_future_queue_mutex); ft->code = (void*)ncd->code; + pthread_mutex_lock(&g_future_queue_mutex); + enqueue_future(ft); //Signal that a future is pending pthread_cond_signal(&g_future_pending_cv); pthread_mutex_unlock(&g_future_queue_mutex); @@ -683,6 +683,8 @@ void *worker_thread_future_loop(void *arg) //Work is available for this thread ft->status = RUNNING; + pthread_mutex_unlock(&g_future_queue_mutex); + ft->threadid = pthread_self(); //Decrement the number of available pool threads @@ -697,7 +699,6 @@ void *worker_thread_future_loop(void *arg) scheme_jit_fill_threadlocal_table(); jitcode = (Scheme_Object* (*)(Scheme_Object*, int, Scheme_Object**))(ft->code); - pthread_mutex_unlock(&g_future_queue_mutex); current_ft = ft; @@ -738,6 +739,15 @@ void *worker_thread_future_loop(void *arg) END_XFORM_SKIP; } +void scheme_check_future_work() +/* Called in the runtime thread by the scheduler */ +{ + /* Check for work that future threads need from the runtime thread + and that can be done in any Scheme thread (e.g., get a new page + for allocation). */ + +} + //Returns 0 if the call isn't actually executed by this function, //i.e. if we are already running on the runtime thread. Otherwise returns @@ -1146,13 +1156,11 @@ void invoke_rtcall(future_t *future) /* Helpers for manipulating the futures queue */ /**********************************************************************/ -future_t *enqueue_future(void) +future_t *enqueue_future(future_t *ft) /* Called in runtime thread */ { - future_t *last, *ft; + future_t *last; last = get_last_future(); - ft = MALLOC_ONE_TAGGED(future_t); - ft->so.type = scheme_future_type; if (NULL == last) { g_future_queue = ft; diff --git a/src/mzscheme/src/future.h b/src/mzscheme/src/future.h index c25bff1617..e9848b5b42 100644 --- a/src/mzscheme/src/future.h +++ b/src/mzscheme/src/future.h @@ -242,7 +242,7 @@ extern int rtcall_int_pobj_obj( void scheme_future_block_until_gc(); void scheme_future_continue_after_gc(); - +void scheme_check_future_work(); #ifdef UNIT_TEST //These forwarding decls only need to be here to make diff --git a/src/mzscheme/src/jit.c b/src/mzscheme/src/jit.c index 70925c3cd6..dbf8846dc6 100644 --- a/src/mzscheme/src/jit.c +++ b/src/mzscheme/src/jit.c @@ -9511,7 +9511,8 @@ static void on_demand_with_args(Scheme_Object **in_argv) argc = in_argv[1]; argv = (Scheme_Object **)in_argv[2]; - scheme_on_demand_generate_lambda((Scheme_Native_Closure *)c, SCHEME_INT_VAL(argc), argv); + if (((Scheme_Native_Closure *)c)->code->code == on_demand_jit_code) + scheme_on_demand_generate_lambda((Scheme_Native_Closure *)c, SCHEME_INT_VAL(argc), argv); } static void on_demand() diff --git a/src/mzscheme/src/thread.c b/src/mzscheme/src/thread.c index 3651d687e6..96e72532a9 100644 --- a/src/mzscheme/src/thread.c +++ b/src/mzscheme/src/thread.c @@ -4107,6 +4107,10 @@ void scheme_thread_block(float sleep_time) /* Check scheduled_kills early and often. */ check_scheduled_kills(); +#ifdef FUTURES_ENABLED + scheme_check_future_work(); +#endif + if (!do_atomic && (sleep_end >= 0.0)) { find_next_thread(&next); } else