Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Factorize a lot of code in context factories through a proper object implementation
authormquinson <mquinson@48e7efb5-ca39-0410-a469-dd3cf9ba447f>
Tue, 23 Mar 2010 12:26:32 +0000 (12:26 +0000)
committermquinson <mquinson@48e7efb5-ca39-0410-a469-dd3cf9ba447f>
Tue, 23 Mar 2010 12:26:32 +0000 (12:26 +0000)
git-svn-id: svn+ssh://scm.gforge.inria.fr/svn/simgrid/simgrid/trunk@7311 48e7efb5-ca39-0410-a469-dd3cf9ba447f

src/Makefile.am
src/simix/private.h
src/simix/smx_context_java.c
src/simix/smx_context_lua.c
src/simix/smx_context_private.h
src/simix/smx_context_ruby.c
src/simix/smx_context_sysv.c
src/simix/smx_context_thread.c

index 8306675..72c04a9 100644 (file)
@@ -212,7 +212,8 @@ SIMIX_SRC= \
   simix/smx_context.c \
   simix/smx_action.c \
   simix/smx_synchro.c \
-  simix/smx_network.c
+  simix/smx_network.c \
+  simix/smx_context_base.c
   
 if CONTEXT_THREADS
   SURF_SRC += xbt/xbt_os_thread.c simix/smx_context_thread.c
index bca6453..8fb2bc4 100644 (file)
@@ -223,6 +223,17 @@ typedef struct s_smx_context {
   void_f_pvoid_t cleanup_func;
   void *cleanup_arg;
 } s_smx_ctx_base_t;
+/* methods of this class */
+void smx_ctx_base_factory_init(smx_context_factory_t * factory);
+int smx_ctx_base_factory_finalize(smx_context_factory_t * factory);
+
+smx_context_t
+smx_ctx_base_factory_create_context_sized(size_t size,
+    xbt_main_func_t code, int argc, char** argv,
+    void_f_pvoid_t cleanup_func, void* cleanup_arg);
+void smx_ctx_base_free(smx_context_t context);
+void smx_ctx_base_stop(smx_context_t context);
+
 
 /* *********************** */
 /* factory type definition */
index 5a59f78..ef79b31 100644 (file)
@@ -16,8 +16,6 @@ static smx_context_t
 smx_ctx_java_factory_create_context(xbt_main_func_t code, int argc, char** argv, 
                                     void_f_pvoid_t cleanup_func, void* cleanup_arg);
 
-static int smx_ctx_java_factory_finalize(smx_context_factory_t * factory);
-
 static void smx_ctx_java_free(smx_context_t context);
 static void smx_ctx_java_start(smx_context_t context);
 static void smx_ctx_java_stop(smx_context_t context);
@@ -27,10 +25,10 @@ static void smx_ctx_java_resume(smx_context_t new_context);
 void SIMIX_ctx_java_factory_init(smx_context_factory_t * factory)
 {
   /* instantiate the context factory */
-  *factory = xbt_new0(s_smx_context_factory_t, 1);
+  smx_ctx_base_factory_init(factory);
 
   (*factory)->create_context = smx_ctx_java_factory_create_context;
-  (*factory)->finalize = smx_ctx_java_factory_finalize;
+  /* Leave default behavior of (*factory)->finalize */
   (*factory)->free = smx_ctx_java_free;
   (*factory)->stop = smx_ctx_java_stop;
   (*factory)->suspend = smx_ctx_java_suspend;
@@ -39,13 +37,6 @@ void SIMIX_ctx_java_factory_init(smx_context_factory_t * factory)
   (*factory)->name = "ctx_java_factory";
 }
 
-static int smx_ctx_java_factory_finalize(smx_context_factory_t * factory)
-{
-  free(*factory);
-  *factory = NULL;
-  return 0;
-}
-
 static smx_context_t
 smx_ctx_java_factory_create_context(xbt_main_func_t code, int argc, char** argv, 
                                     void_f_pvoid_t cleanup_func, void* cleanup_arg)
@@ -80,10 +71,9 @@ static void smx_ctx_java_free(smx_context_t context)
       if (jprocess_is_alive(jprocess, get_current_thread_env()))
         jprocess_join(jprocess, get_current_thread_env());
     }
-
-    free(context);
-    context = NULL;
   }
+
+  smx_ctx_base_free(context);
 } 
 
 static void smx_ctx_java_stop(smx_context_t context)
index 5c3c3e9..e194ffb 100644 (file)
@@ -64,7 +64,7 @@ void SIMIX_ctx_lua_factory_set_state(void* state) {
 }
 void SIMIX_ctx_lua_factory_init(smx_context_factory_t *factory) {
 
-  *factory = xbt_new0(s_smx_context_factory_t, 1);
+  smx_ctx_base_factory_init(factory);
 
   (*factory)->create_context = smx_ctx_lua_create_context;
   (*factory)->finalize = smx_ctx_lua_factory_finalize;
@@ -80,9 +80,7 @@ void SIMIX_ctx_lua_factory_init(smx_context_factory_t *factory) {
 static int smx_ctx_lua_factory_finalize(smx_context_factory_t * factory) {
   lua_close(lua_state);
 
-  free(*factory);
-  *factory = NULL;
-  return 0;
+  return smx_ctx_base_factory_finalize(factory);
 }
 
 static smx_context_t 
@@ -126,29 +124,16 @@ smx_ctx_lua_create_context(xbt_main_func_t code, int argc, char** argv,
   return (smx_context_t)context;
 }
 
-static void smx_ctx_lua_free(smx_context_t pcontext)
-{
-  int i;
-  smx_ctx_lua_t context = (smx_ctx_lua_t)pcontext;
+static void smx_ctx_lua_free(smx_context_t context) {
 
   if (context){
     DEBUG1("smx_ctx_lua_free_context(%p)",context);
 
-    /* free argv */
-    if (context->super.argv) {
-      for (i = 0; i < context->super.argc; i++)
-        if (context->super.argv[i])
-          free(context->super.argv[i]);
-
-      free(context->super.argv);
-    }
-
     /* let the lua garbage collector reclaim the thread used for the coroutine */
-    luaL_unref(lua_state,LUA_REGISTRYINDEX,context->ref );
-
-    free(context);
-    context = NULL;
+    luaL_unref(lua_state,LUA_REGISTRYINDEX,((smx_ctx_lua_t)context)->ref );
   }
+
+  smx_ctx_base_free(context);
 }
 
 static void smx_ctx_lua_stop(smx_context_t pcontext) {
index 7ee1ce0..bc4b45e 100644 (file)
@@ -71,7 +71,6 @@ typedef struct s_smx_context_factory {
   smx_pfn_context_factory_create_context_t create_context;
   smx_pfn_context_factory_finalize_t finalize;
   smx_pfn_context_free_t free;
-  smx_pfn_context_kill_t kill;
   smx_pfn_context_schedule_t schedule;
   smx_pfn_context_yield_t yield;
   smx_pfn_context_stop_t stop;
index 3427d87..2da3977 100644 (file)
@@ -19,7 +19,6 @@ static smx_context_t
 smx_ctx_ruby_create_context(xbt_main_func_t code,int argc,char** argv,
     void_f_pvoid_t cleanup_func,void *cleanup_arg);
 
-static int smx_ctx_ruby_factory_finalize(smx_context_factory_t *factory);
 static void smx_ctx_ruby_free(smx_context_t context);
 static void smx_ctx_ruby_stop(smx_context_t context);
 static void smx_ctx_ruby_suspend(smx_context_t context);
@@ -28,10 +27,10 @@ static void smx_ctx_ruby_wrapper(void);
 
 
 void SIMIX_ctx_ruby_factory_init(smx_context_factory_t *factory) {
-  *factory = xbt_new0(s_smx_context_factory_t,1);
+  smx_ctx_base_factory_init(factory);
 
   (*factory)->create_context = smx_ctx_ruby_create_context;
-  (*factory)->finalize = smx_ctx_ruby_factory_finalize;
+  /* Do not overload that method (*factory)->finalize */
   (*factory)->free = smx_ctx_ruby_free;
   (*factory)->stop = smx_ctx_ruby_stop;
   (*factory)->suspend = smx_ctx_ruby_suspend;
@@ -41,48 +40,28 @@ void SIMIX_ctx_ruby_factory_init(smx_context_factory_t *factory) {
   ruby_init_loadpath();
 }
 
-static int smx_ctx_ruby_factory_finalize(smx_context_factory_t *factory) {
-  free(*factory);
-  *factory = NULL;
-  return 0;
-}
-
 static smx_context_t 
 smx_ctx_ruby_create_context(xbt_main_func_t code,int argc,char** argv,
     void_f_pvoid_t cleanup_func,void* cleanup_arg) {
 
-  smx_ctx_ruby_t context = xbt_new0(s_smx_ctx_ruby_t,1);
+  smx_ctx_ruby_t context = (smx_ctx_ruby_t)smx_ctx_base_factory_create_context_sized
+      (sizeof(s_smx_ctx_ruby_t), code,argc,argv,cleanup_func,cleanup_arg);
 
   /* if the user provided a function for the process , then use it
      Otherwise it's the context for maestro */
   if (code) {
-    context->super.cleanup_func = cleanup_func;
-    context->super.cleanup_arg = cleanup_arg;
     context->process = (VALUE)code;
-    context->super.argc=argc;
-    context->super.argv=argv;
 
     DEBUG1("smx_ctx_ruby_create_context(%s)...Done",argv[0]);
   }
   return (smx_context_t) context;
 }
 
-// FIXME 
 static void smx_ctx_ruby_free(smx_context_t context) {
-  int i;
- if (context) {
+ if (context)
     DEBUG1("smx_ctx_ruby_free_context(%p)",context);
-    /* free argv */
-    if (context->argv) {
-      for (i = 0; i < context->argc; i++)
-        if (context->argv[i])
-          free(context->argv[i]);
 
-      free(context->argv);
-    }
-    free (context);
-    context = NULL;
-  }
+ smx_ctx_base_free(context);
 }
 
 static void smx_ctx_ruby_stop(smx_context_t context) {
index 242a962..afa5403 100644 (file)
@@ -34,8 +34,6 @@ static smx_context_t
 smx_ctx_sysv_factory_create_context(xbt_main_func_t code, int argc, char** argv, 
     void_f_pvoid_t cleanup_func, void* cleanup_arg);
 
-static int smx_ctx_sysv_factory_finalize(smx_context_factory_t *factory);
-
 static void smx_ctx_sysv_free(smx_context_t context);
 static void smx_ctx_sysv_stop(smx_context_t context);
 static void smx_ctx_sysv_suspend(smx_context_t context);
@@ -43,12 +41,12 @@ static void smx_ctx_sysv_resume(smx_context_t new_context);
 
 static void smx_ctx_sysv_wrapper(void);
 
-void SIMIX_ctx_sysv_factory_init(smx_context_factory_t *factory)
-{
-  *factory = xbt_new0(s_smx_context_factory_t, 1);
+void SIMIX_ctx_sysv_factory_init(smx_context_factory_t *factory) {
+
+  smx_ctx_base_factory_init(factory);
 
   (*factory)->create_context = smx_ctx_sysv_factory_create_context;
-  (*factory)->finalize = smx_ctx_sysv_factory_finalize;
+  /* Do not overload that method (*factory)->finalize */
   (*factory)->free = smx_ctx_sysv_free;
   (*factory)->stop = smx_ctx_sysv_stop;
   (*factory)->suspend = smx_ctx_sysv_suspend;
@@ -56,23 +54,16 @@ void SIMIX_ctx_sysv_factory_init(smx_context_factory_t *factory)
   (*factory)->name = "smx_sysv_context_factory";
 }
 
-static int smx_ctx_sysv_factory_finalize(smx_context_factory_t * factory)
-{
-  free(*factory);
-  *factory = NULL;
-  return 0;
-}
-
 static smx_context_t 
 smx_ctx_sysv_factory_create_context(xbt_main_func_t code, int argc, char** argv, 
     void_f_pvoid_t cleanup_func, void* cleanup_arg)
 {
-  smx_ctx_sysv_t context = xbt_new0(s_smx_ctx_sysv_t, 1);
+  smx_ctx_sysv_t context = (smx_ctx_sysv_t)smx_ctx_base_factory_create_context_sized
+      (sizeof(s_smx_ctx_sysv_t), code,argc,argv,cleanup_func,cleanup_arg);
 
   /* If the user provided a function for the process then use it
      otherwise is the context for maestro */
   if(code){
-    context->super.code = code;
 
     xbt_assert2(getcontext(&(context->uc)) == 0,
         "Error in context saving: %d (%s)", errno, strerror(errno));
@@ -92,49 +83,28 @@ smx_ctx_sysv_factory_create_context(xbt_main_func_t code, int argc, char** argv,
             context->uc.uc_stack.ss_size);
 #endif /* HAVE_VALGRIND_VALGRIND_H */
 
-    context->super.argc = argc;
-    context->super.argv = argv;
-    context->super.cleanup_func = cleanup_func;
-    context->super.cleanup_arg = cleanup_arg;
-
     makecontext(&((smx_ctx_sysv_t)context)->uc, smx_ctx_sysv_wrapper, 0);
   }
 
   return (smx_context_t)context;
 }
 
-static void smx_ctx_sysv_free(smx_context_t pcontext)
-{
-  int i;
-  smx_ctx_sysv_t context = (smx_ctx_sysv_t)pcontext;   
+static void smx_ctx_sysv_free(smx_context_t context) {
+
   if (context){
 
 #ifdef HAVE_VALGRIND_VALGRIND_H
     VALGRIND_STACK_DEREGISTER(((smx_ctx_sysv_t) context)->valgrind_stack_id);
 #endif /* HAVE_VALGRIND_VALGRIND_H */
 
-    /* free argv */
-    if (context->super.argv) {
-      for (i = 0; i < context->super.argc; i++)
-        if (context->super.argv[i])
-          free(context->super.argv[i]);
-
-      free(context->super.argv);
-    }
-
-    /* destroy the context */
-    free(context);
   }
+  smx_ctx_base_free(context);
 }
 
-static void smx_ctx_sysv_stop(smx_context_t pcontext)
-{
-  smx_ctx_sysv_t context = (smx_ctx_sysv_t)pcontext;
-
-  if (context->super.cleanup_func)
-    (*context->super.cleanup_func) (context->super.cleanup_arg);
+static void smx_ctx_sysv_stop(smx_context_t context) {
+  smx_ctx_base_stop(context);
 
-  smx_ctx_sysv_suspend(pcontext);
+  smx_ctx_sysv_suspend(context);
 }
 
 static void smx_ctx_sysv_wrapper()
@@ -155,20 +125,18 @@ static void smx_ctx_sysv_wrapper()
 }
 
 static void smx_ctx_sysv_suspend(smx_context_t context) {
-  int rv;
   ucontext_t maestro_ctx = ((smx_ctx_sysv_t)simix_global->maestro_process->context)->uc;
 
-  rv = swapcontext(&((smx_ctx_sysv_t) context)->uc, &maestro_ctx);
+  int rv = swapcontext(&((smx_ctx_sysv_t) context)->uc, &maestro_ctx);
 
   xbt_assert0((rv == 0), "Context swapping failure");
 }
 
 static void 
 smx_ctx_sysv_resume(smx_context_t new_context) {
-  int rv;
   smx_ctx_sysv_t maestro = (smx_ctx_sysv_t)simix_global->maestro_process->context;
 
-  rv = swapcontext(&(maestro->uc), &((smx_ctx_sysv_t)new_context)->uc);
+  int rv = swapcontext(&(maestro->uc), &((smx_ctx_sysv_t)new_context)->uc);
 
   xbt_assert0((rv == 0), "Context swapping failure");
 }
index 63f2556..53f343d 100644 (file)
@@ -18,7 +18,7 @@
 XBT_LOG_EXTERNAL_DEFAULT_CATEGORY(simix_context);
 
 typedef struct s_smx_ctx_thread {
-  SMX_CTX_BASE_T;
+  s_smx_ctx_base_t super;       /* Fields of super implementation */
   xbt_os_thread_t thread;       /* a plain dumb thread (portable to posix or windows) */
   xbt_os_sem_t begin;           /* this semaphore is used to schedule/yield the process  */
   xbt_os_sem_t end;             /* this semaphore is used to schedule/unschedule the process   */
@@ -28,7 +28,6 @@ static smx_context_t
 smx_ctx_thread_factory_create_context(xbt_main_func_t code, int argc, char** argv, 
                                       void_f_pvoid_t cleanup_func, void* cleanup_arg);
 
-static int smx_ctx_thread_factory_finalize(smx_context_factory_t * factory);
 static void smx_ctx_thread_free(smx_context_t context);
 static void smx_ctx_thread_stop(smx_context_t context);
 static void smx_ctx_thread_suspend(smx_context_t context);
@@ -36,12 +35,12 @@ static void smx_ctx_thread_resume(smx_context_t new_context);
 
 static void *smx_ctx_thread_wrapper(void *param);
 
-void SIMIX_ctx_thread_factory_init(smx_context_factory_t * factory)
-{
-  *factory = xbt_new0(s_smx_context_factory_t, 1);
+void SIMIX_ctx_thread_factory_init(smx_context_factory_t * factory) {
+
+  smx_ctx_base_factory_init(factory);
 
   (*factory)->create_context = smx_ctx_thread_factory_create_context;
-  (*factory)->finalize = smx_ctx_thread_factory_finalize;
+  /* Do not overload that method (*factory)->finalize */
   (*factory)->free = smx_ctx_thread_free;
   (*factory)->stop = smx_ctx_thread_stop;
   (*factory)->suspend = smx_ctx_thread_suspend;
@@ -49,27 +48,16 @@ void SIMIX_ctx_thread_factory_init(smx_context_factory_t * factory)
   (*factory)->name = "ctx_thread_factory";
 }
 
-static int smx_ctx_thread_factory_finalize(smx_context_factory_t * factory)
-{
-  free(*factory);
-  *factory = NULL;
-  return 0;
-}
-
 static smx_context_t 
 smx_ctx_thread_factory_create_context(xbt_main_func_t code, int argc, char** argv, 
                                       void_f_pvoid_t cleanup_func, void* cleanup_arg)
 {
-  smx_ctx_thread_t context = xbt_new0(s_smx_ctx_thread_t, 1);
+  smx_ctx_thread_t context = (smx_ctx_thread_t)smx_ctx_base_factory_create_context_sized
+      (sizeof(s_smx_ctx_thread_t), code,argc,argv,cleanup_func,cleanup_arg);
 
   /* If the user provided a function for the process then use it
      otherwise is the context for maestro */
   if(code){
-    context->code = code;
-    context->argc = argc;
-    context->argv = argv;
-    context->cleanup_func = cleanup_func;
-    context->cleanup_arg = cleanup_arg;
     context->begin = xbt_os_sem_init(0);
     context->end = xbt_os_sem_init(0);
 
@@ -102,17 +90,7 @@ static void smx_ctx_thread_free(smx_context_t pcontext)
     xbt_os_sem_destroy(context->end);
   }
   
-  /* free argv */
-  if (context->argv) {
-    for (i = 0; i < context->argc; i++)
-      if (context->argv[i])
-        free(context->argv[i]);
-
-    free(context->argv);
-  }
-    
-  /* finally destroy the context */
-  free(context);
+  smx_ctx_base_free(pcontext);
 }
 
 static void smx_ctx_thread_stop(smx_context_t pcontext)
@@ -121,8 +99,7 @@ static void smx_ctx_thread_stop(smx_context_t pcontext)
   smx_ctx_thread_t context = (smx_ctx_thread_t)pcontext;
   
   /* please no debug here: our procdata was already free'd */
-  if (context->cleanup_func)
-    (*context->cleanup_func) (context->cleanup_arg);
+  smx_ctx_base_stop(pcontext);
 
   /* signal to the maestro that it has finished */
   xbt_os_sem_release(((smx_ctx_thread_t) context)->end);
@@ -140,7 +117,7 @@ static void *smx_ctx_thread_wrapper(void *param)
   xbt_os_sem_release(context->end);
   xbt_os_sem_acquire(context->begin);
 
-  (context->code) (context->argc, context->argv);
+  (context->super.code) (context->super.argc, context->super.argv);
 
   smx_ctx_thread_stop((smx_context_t)context);
   return NULL;