- test for external iterator
[oweals/gnunet.git] / src / util / mq.c
index d0253c40f073ebe0f597fe72b0b3aac7f0c7854c..c215de187f1a88049abd57f58991c9a7e32d4291 100644 (file)
@@ -167,10 +167,12 @@ struct ClientConnectionState
 };
 
 
-
-
 /**
- * Call the right callback for a message.
+ * Call the message message handler that was registered
+ * for the type of the given message in the given message queue.
+ *
+ * This function is indended to be used for the implementation
+ * of message queues.
  *
  * @param mq message queue with the handlers
  * @param mh message to dispatch
@@ -199,9 +201,14 @@ GNUNET_MQ_inject_message (struct GNUNET_MQ_Handle *mq, const struct GNUNET_Messa
 
 
 /**
- * Call the right callback for an error condition.
+ * Call the error handler of a message queue with the given
+ * error code.  If there is no error handler, log a warning.
+ *
+ * This function is intended to be used by the implementation
+ * of message queues.
  *
  * @param mq message queue
+ * @param error the error type
  */
 void
 GNUNET_MQ_inject_error (struct GNUNET_MQ_Handle *mq,
@@ -230,7 +237,7 @@ GNUNET_MQ_discard (struct GNUNET_MQ_Envelope *mqm)
  * May only be called once per message.
  * 
  * @param mq message queue
- * @param ev the message to send.
+ * @param ev the envelope with the message to send.
  */
 void
 GNUNET_MQ_send (struct GNUNET_MQ_Handle *mq, struct GNUNET_MQ_Envelope *ev)
@@ -288,10 +295,11 @@ GNUNET_MQ_impl_send_continue (struct GNUNET_MQ_Handle *mq)
  *
  * @param send function the implements sending messages
  * @param destroy function that implements destroying the queue
- * @param destroy function that implements canceling a message
- * @param state for the queue, passed to 'send' and 'destroy'
+ * @param cancel function that implements canceling a message
+ * @param impl_state for the queue, passed to 'send' and 'destroy'
  * @param handlers array of message handlers
  * @param error_handler handler for read and write errors
+ * @param cls closure for message handlers and error handler
  * @return a new message queue
  */
 struct GNUNET_MQ_Handle *
@@ -391,6 +399,15 @@ GNUNET_MQ_msg_ (struct GNUNET_MessageHeader **mhp, uint16_t size, uint16_t type)
 }
 
 
+/**
+ * Implementation of the GNUNET_MQ_msg_nested_mh macro.
+ *
+ * @param mhp pointer to the message header pointer that will be changed to allocate at
+ *        the newly allocated space for the message.
+ * @param base_size size of the data before the nested message
+ * @param type type of the message in the envelope
+ * @param nested_mh the message to append to the message after base_size
+ */
 struct GNUNET_MQ_Envelope *
 GNUNET_MQ_msg_nested_mh_ (struct GNUNET_MessageHeader **mhp, uint16_t base_size, uint16_t type,
                           const struct GNUNET_MessageHeader *nested_mh)
@@ -595,6 +612,7 @@ connection_client_send_impl (struct GNUNET_MQ_Handle *mq,
 struct GNUNET_MQ_Handle *
 GNUNET_MQ_queue_for_connection_client (struct GNUNET_CLIENT_Connection *connection,
                                        const struct GNUNET_MQ_MessageHandler *handlers,
+                                       GNUNET_MQ_ErrorHandler error_handler,
                                        void *cls)
 {
   struct GNUNET_MQ_Handle *mq;
@@ -604,6 +622,7 @@ GNUNET_MQ_queue_for_connection_client (struct GNUNET_CLIENT_Connection *connecti
 
   mq = GNUNET_new (struct GNUNET_MQ_Handle);
   mq->handlers = handlers;
+  mq->error_handler = error_handler;
   mq->handlers_cls = cls;
   state = GNUNET_new (struct ClientConnectionState);
   state->connection = connection;
@@ -633,7 +652,6 @@ GNUNET_MQ_replace_handlers (struct GNUNET_MQ_Handle *mq,
  * Associate the assoc_data in mq with a unique request id.
  *
  * @param mq message queue, id will be unique for the queue
- * @param mqm message to associate
  * @param assoc_data to associate
  */
 uint32_t
@@ -672,8 +690,7 @@ GNUNET_MQ_assoc_remove (struct GNUNET_MQ_Handle *mq, uint32_t request_id)
   if (NULL == mq->assoc_map)
     return NULL;
   val = GNUNET_CONTAINER_multihashmap32_get (mq->assoc_map, request_id);
-  GNUNET_assert (NULL != val);
-  GNUNET_CONTAINER_multihashmap32_remove (mq->assoc_map, request_id, val);
+  GNUNET_CONTAINER_multihashmap32_remove_all (mq->assoc_map, request_id);
   return val;
 }
 
@@ -691,18 +708,35 @@ GNUNET_MQ_notify_sent (struct GNUNET_MQ_Envelope *mqm,
 void
 GNUNET_MQ_destroy (struct GNUNET_MQ_Handle *mq)
 {
-  /* FIXME: destroy all pending messages in the queue */
-
   if (NULL != mq->destroy_impl)
   {
     mq->destroy_impl (mq, mq->impl_state);
   }
 
+  while (NULL != mq->envelope_head)
+  {
+    struct GNUNET_MQ_Envelope *ev;
+    ev = mq->envelope_head;
+    GNUNET_CONTAINER_DLL_remove (mq->envelope_head, mq->envelope_tail, ev);
+    GNUNET_MQ_discard (ev);
+  }
+
+  if (NULL != mq->current_envelope)
+  {
+    GNUNET_MQ_discard (mq->current_envelope);
+    mq->current_envelope = NULL;
+  }
+
+  if (NULL != mq->assoc_map)
+  {
+    GNUNET_CONTAINER_multihashmap32_destroy (mq->assoc_map);
+    mq->assoc_map = NULL;
+  }
+
   GNUNET_free (mq);
 }
 
 
-
 struct GNUNET_MessageHeader *
 GNUNET_MQ_extract_nested_mh_ (const struct GNUNET_MessageHeader *mh, uint16_t base_size)
 {