Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Fix remaining memory leaks in MSG
authorChristophe Thiéry <christopho128@gmail.com>
Fri, 14 Oct 2011 15:04:28 +0000 (17:04 +0200)
committerChristophe Thiéry <christopho128@gmail.com>
Fri, 14 Oct 2011 15:04:28 +0000 (17:04 +0200)
src/msg/gos.c
src/msg/task.c
src/simix/smx_network.c

index 4a09c65..cb6c929 100644 (file)
@@ -437,8 +437,8 @@ XBT_INLINE msg_comm_t MSG_task_isend_with_matching(m_task_t task, const char *al
  * \brief Sends a task on a mailbox.
  *
  * This is a non blocking detached send function.
  * \brief Sends a task on a mailbox.
  *
  * This is a non blocking detached send function.
- * Think of it as a best effort send. The communication
- * object will be destroyed by the receiver (if any).
+ * Think of it as a best effort send. The task should
+ * be destroyed by the receiver.
  *
  * \param task a #m_task_t to send on another location.
  * \param alias name of the mailbox to sent the task to
  *
  * \param task a #m_task_t to send on another location.
  * \param alias name of the mailbox to sent the task to
@@ -623,9 +623,7 @@ void MSG_comm_destroy(msg_comm_t comm)
     (*comm->task_received)->simdata->isused = 0;
   }
 
     (*comm->task_received)->simdata->isused = 0;
   }
 
-  /* FIXME auto-destroy comms from SIMIX to avoid this request */
-  /*SIMIX_req_comm_destroy(comm->s_comm);*/
-  free(comm);
+  xbt_free(comm);
 }
 
 /** \ingroup msg_gos_functions
 }
 
 /** \ingroup msg_gos_functions
index 2a9a5c0..b0df136 100644 (file)
@@ -159,25 +159,22 @@ MSG_error_t MSG_task_destroy(m_task_t task)
   smx_action_t action = NULL;
   xbt_assert((task != NULL), "Invalid parameter");
 
   smx_action_t action = NULL;
   xbt_assert((task != NULL), "Invalid parameter");
 
-  /* why? if somebody is using, then you can't free! ok... but will return MSG_OK? when this task will be destroyed? isn't the user code wrong? */
-  if (task->simdata->isused > 0) {
-    XBT_DEBUG("Cannot destroy task %p since somebody is using it", task);
-    return MSG_OK;
+  if (task->simdata->isused) {
+    /* the task is still being used, it may be an unfinished dsend */
+    MSG_task_cancel(task);
   }
 #ifdef HAVE_TRACING
   TRACE_msg_task_destroy(task);
 #endif
 
   }
 #ifdef HAVE_TRACING
   TRACE_msg_task_destroy(task);
 #endif
 
-  if (task->name)
-    free(task->name);
+  xbt_free(task->name);
 
   action = task->simdata->compute;
   if (action)
     SIMIX_req_host_execution_destroy(action);
 
   /* parallel tasks only */
 
   action = task->simdata->compute;
   if (action)
     SIMIX_req_host_execution_destroy(action);
 
   /* parallel tasks only */
-  if (task->simdata->host_list)
-    xbt_free(task->simdata->host_list);
+  xbt_free(task->simdata->host_list);
 
   /* free main structures */
   xbt_free(task->simdata);
 
   /* free main structures */
   xbt_free(task->simdata);
@@ -201,6 +198,7 @@ MSG_error_t MSG_task_cancel(m_task_t task)
   }
   else if (task->simdata->comm) {
     SIMIX_req_comm_cancel(task->simdata->comm);
   }
   else if (task->simdata->comm) {
     SIMIX_req_comm_cancel(task->simdata->comm);
+    task->simdata->isused = 0;
   }
   else {
     static int warned = 0;
   }
   else {
     static int warned = 0;
index 3c4440e..68d36ae 100644 (file)
@@ -18,6 +18,7 @@ unsigned long int smx_total_comms = 0;
 static void SIMIX_waitany_req_remove_from_actions(smx_req_t req);
 static void SIMIX_comm_copy_data(smx_action_t comm);
 static smx_action_t SIMIX_comm_new(e_smx_comm_type_t type);
 static void SIMIX_waitany_req_remove_from_actions(smx_req_t req);
 static void SIMIX_comm_copy_data(smx_action_t comm);
 static smx_action_t SIMIX_comm_new(e_smx_comm_type_t type);
+static void SIMIX_comm_remove_from_processes(smx_action_t action);
 static XBT_INLINE void SIMIX_rdv_push(smx_rdv_t rdv, smx_action_t comm);
 static XBT_INLINE void SIMIX_rdv_remove(smx_rdv_t rdv, smx_action_t comm);
 static smx_action_t SIMIX_rdv_get_request(smx_rdv_t rdv, e_smx_comm_type_t type,
 static XBT_INLINE void SIMIX_rdv_push(smx_rdv_t rdv, smx_action_t comm);
 static XBT_INLINE void SIMIX_rdv_remove(smx_rdv_t rdv, smx_action_t comm);
 static smx_action_t SIMIX_rdv_get_request(smx_rdv_t rdv, e_smx_comm_type_t type,
@@ -551,6 +552,8 @@ void SIMIX_comm_finish(smx_action_t action)
   unsigned int destroy_count = 0;
   smx_req_t req;
 
   unsigned int destroy_count = 0;
   smx_req_t req;
 
+  SIMIX_comm_remove_from_processes(action);
+
   while ((req = xbt_fifo_shift(action->request_list))) {
 
     /* If a waitany request is waiting for this action to finish, then remove
   while ((req = xbt_fifo_shift(action->request_list))) {
 
     /* If a waitany request is waiting for this action to finish, then remove
@@ -678,33 +681,46 @@ void SIMIX_post_comm(smx_action_t action)
   XBT_DEBUG("SIMIX_post_comm: comm %p, state %d, src_proc %p, dst_proc %p, detached: %d",
       action, action->state, action->comm.src_proc, action->comm.dst_proc, action->comm.detached);
 
   XBT_DEBUG("SIMIX_post_comm: comm %p, state %d, src_proc %p, dst_proc %p, detached: %d",
       action, action->state, action->comm.src_proc, action->comm.dst_proc, action->comm.detached);
 
-  /* remove the action from pending communications of both processes (if they still exist) */
+  /* destroy the surf actions associated with the Simix communication */
+  SIMIX_comm_destroy_internal_actions(action);
+
+  /* if there are requests associated with the action, then answer them */
+  if (xbt_fifo_size(action->request_list)) {
+    SIMIX_comm_finish(action);
+  }
+  else {
+    SIMIX_comm_remove_from_processes(action);
+  }
+}
+
+/**
+ * \brief Removes a communication action from the list of pending communications
+ * of both processes (if they still exist)
+ * \param action a communication action
+ */
+static void SIMIX_comm_remove_from_processes(smx_action_t action) {
+
   if (action->comm.src_proc) {
     xbt_fifo_remove(action->comm.src_proc->comms, action);
   }
   if (action->comm.dst_proc) {
     xbt_fifo_remove(action->comm.dst_proc->comms, action);
   }
   if (action->comm.src_proc) {
     xbt_fifo_remove(action->comm.src_proc->comms, action);
   }
   if (action->comm.dst_proc) {
     xbt_fifo_remove(action->comm.dst_proc->comms, action);
   }
-
-  /* destroy the surf actions associated with the Simix communication */
-  SIMIX_comm_destroy_internal_actions(action);
-
-  /* if there are requests associated with the action, then answer them */
-  if (xbt_fifo_size(action->request_list))
-    SIMIX_comm_finish(action);
 }
 
 void SIMIX_comm_cancel(smx_action_t action)
 {
 }
 
 void SIMIX_comm_cancel(smx_action_t action)
 {
-  /* If the action is a waiting state means that it is still in a rdv */
+  /* if the action is a waiting state means that it is still in a rdv */
   /* so remove from it and delete it */
   if (action->state == SIMIX_WAITING) {
     SIMIX_rdv_remove(action->comm.rdv, action);
     action->state = SIMIX_FAILED;
   /* so remove from it and delete it */
   if (action->state == SIMIX_WAITING) {
     SIMIX_rdv_remove(action->comm.rdv, action);
     action->state = SIMIX_FAILED;
-  } else {
-    /* When running the MC there are no surf actions */
-    if(!MC_IS_ENABLED)
-      surf_workstation_model->action_cancel(action->comm.surf_comm);
+  }
+  else if (!MC_IS_ENABLED
+      && (action->state == SIMIX_READY || action->state == SIMIX_RUNNING)) {
+
+    /* when running the MC there are no surf actions */
+    surf_workstation_model->action_cancel(action->comm.surf_comm);
   }
 }
 
   }
 }