Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Add on_exit support on SIMIX/MSG, calling functions when the process is dying (stopped)
authorSamuel Lepetit <samuel.lepetit@inria.fr>
Wed, 20 Jun 2012 15:50:32 +0000 (17:50 +0200)
committerSamuel Lepetit <samuel.lepetit@inria.fr>
Wed, 20 Jun 2012 15:50:38 +0000 (17:50 +0200)
include/msg/msg.h
src/msg/msg_process.c
src/simix/smx_context_base.c
src/simix/smx_process.c
src/simix/smx_process_private.h

index 0e4838d..80fae8f 100644 (file)
@@ -138,6 +138,7 @@ XBT_PUBLIC(const char *) MSG_process_get_property_value(m_process_t
 XBT_PUBLIC(MSG_error_t) MSG_process_suspend(m_process_t process);
 XBT_PUBLIC(MSG_error_t) MSG_process_resume(m_process_t process);
 XBT_PUBLIC(int) MSG_process_is_suspended(m_process_t process);
+XBT_PUBLIC(void) MSG_process_on_exit_add(int_f_pvoid_t fun, void *data);
 
 /************************** Task handling ************************************/
 XBT_PUBLIC(m_task_t) MSG_task_create(const char *name,
index 2ce1d5d..2834674 100644 (file)
@@ -488,3 +488,12 @@ int MSG_process_is_suspended(m_process_t process)
 smx_context_t MSG_process_get_smx_ctx(m_process_t process) {
   return SIMIX_process_get_context(process);
 }
+/**
+ * \ingroup m_process_management
+ * \brief Add a function to the list of "on_exit" functions for the current process.
+ * The on_exit functions are the functions executed when your process is killed.
+ * You should use them to free the data used by your process.
+ */
+void MSG_process_on_exit_add(int_f_pvoid_t fun, void *data) {
+  SIMIX_process_on_exit_add(fun,data);
+}
index 56efcf1..c162275 100644 (file)
@@ -83,6 +83,7 @@ void smx_ctx_base_free(smx_context_t context)
 
 void smx_ctx_base_stop(smx_context_t context)
 {
+  SIMIX_process_on_exit(context->data);
   if (context->cleanup_func)
     context->cleanup_func(context->data);
   context->iwannadie = 0;
index 009e927..b47fe45 100644 (file)
@@ -219,6 +219,9 @@ void SIMIX_process_create(smx_process_t *process,
 
     XBT_DEBUG("Start context '%s'", (*process)->name);
 
+    /* Build the dynars for the on_exit functions */
+    (*process)->on_exit_fun = xbt_dynar_new(sizeof(int_f_pvoid_t),NULL);
+    (*process)->on_exit_args = xbt_dynar_new(sizeof(void*),NULL);
     /* Now insert it in the global process list and in the process to run list */
     xbt_swag_insert(*process, simix_global->process_list);
     XBT_DEBUG("Inserting %s(%s) in the to_run list", (*process)->name, host->name);
@@ -711,3 +714,20 @@ xbt_dynar_t SIMIX_processes_as_dynar(void) {
   }
   return res;
 }
+void SIMIX_process_on_exit(smx_process_t process) {
+  int length = xbt_dynar_length(process->on_exit_fun);
+  int cpt;
+  int_f_pvoid_t fun;
+  void *data;
+  for (cpt = 0; cpt < length; cpt++) {
+    fun = xbt_dynar_get_as(process->on_exit_fun,cpt,int_f_pvoid_t);
+    data = xbt_dynar_get_as(process->on_exit_args,cpt,void*);
+    (fun)(data);
+  }
+}
+void SIMIX_process_on_exit_add(int_f_pvoid_t fun, void *data) {
+  smx_process_t process = SIMIX_process_self();
+  xbt_assert(process, "current process not found: are you in maestro context ?");
+  xbt_dynar_push_as(process->on_exit_fun,int_f_pvoid_t,fun);
+  xbt_dynar_push_as(process->on_exit_args,void*,data);
+}
index e19d835..73fc714 100644 (file)
 #include "simgrid/simix.h"
 #include "smx_smurf_private.h"
 
+typedef struct s_smx_process_exit_fun {
+  int_f_pvoid_t fun;
+  void *arg;
+} s_smx_process_exit_fun_t, *smx_process_exit_fun_t;
+
 /** @brief Process datatype */
 typedef struct s_smx_process {
   s_xbt_swag_hookup_t process_hookup;
@@ -20,7 +25,7 @@ typedef struct s_smx_process {
   unsigned long pid;
   char *name;                   /**< @brief process name if any */
   smx_host_t smx_host;          /* the host on which the process is running */
-  smx_context_t context;        /* the context (either uctx or thread) that executes the user function */
+  smx_context_t context;        /* the context (uctx/raw/thread) that executes the user function */
   xbt_running_ctx_t *running_ctx;
   unsigned doexception:1;
   unsigned blocked:1;
@@ -31,7 +36,8 @@ typedef struct s_smx_process {
   xbt_dict_t properties;
   s_smx_simcall_t simcall;
   void *data;                   /* kept for compatibility, it should be replaced with moddata */
-
+  xbt_dynar_t on_exit_fun;     /* list of functions executed when the process dies */
+  xbt_dynar_t on_exit_args;    /* arguments (void*) of the functions executed when the process dies */
 } s_smx_process_t;
 
 typedef struct s_smx_process_arg {
@@ -86,4 +92,6 @@ void SIMIX_process_sleep_suspend(smx_action_t action);
 void SIMIX_process_sleep_resume(smx_action_t action);
 void SIMIX_process_sleep_destroy(smx_action_t action);
 
+void SIMIX_process_on_exit(smx_process_t process);
+void SIMIX_process_on_exit_add(int_f_pvoid_t fun, void *data);
 #endif