gnunetutil: add 2d and 3d allocation including tests
[oweals/gnunet.git] / src / include / gnunet_mq_lib.h
index 0bc8307f78145a6f5fbd24717ab3278b2631e209..86144abcaa07b1701b7bae362048b71235118c55 100644 (file)
 
 
 /**
- * Implementation of the GNUNET_MQ_extract_nexted_mh macro.
+ * Implementation of the #GNUNET_MQ_extract_nexted_mh macro.
  *
  * @param mh message header to extract nested message header from
  * @param base_size size of the message before the nested message's header appears
@@ -117,6 +117,12 @@ GNUNET_MQ_extract_nested_mh_ (const struct GNUNET_MessageHeader *mh,
                               uint16_t base_size);
 
 
+/**
+ * Opaque handle to an envelope.
+ */
+struct GNUNET_MQ_Envelope;
+
+
 /**
  * Implementation of the #GNUNET_MQ_msg_nested_mh macro.
  *
@@ -138,11 +144,6 @@ GNUNET_MQ_msg_nested_mh_ (struct GNUNET_MessageHeader **mhp,
  */
 struct GNUNET_MQ_Handle;
 
-/**
- * Opaque handle to an envelope.
- */
-struct GNUNET_MQ_Envelope;
-
 
 /**
  * Error codes for the queue.
@@ -304,7 +305,7 @@ struct GNUNET_MQ_MessageHandler
 /**
  * End-marker for the handlers array
  */
-#define GNUNET_MQ_handler_end() {NULL, NULL, NULL, 0, 0}
+#define GNUNET_MQ_handler_end() { NULL, NULL, NULL, 0, 0 }
 
 
 /**
@@ -322,27 +323,26 @@ struct GNUNET_MQ_MessageHandler
  *                      const struct GNUNET_MessageTest *msg)
  * { ... }
  *
- * GNUNET_MQ_hd_fixed_size(test_message,
- *                         GNUNET_MESSAGE_TYPE_TEST,
- *                         struct GNUNET_MessageTest);
  * struct GNUNET_MQ_MessageHandler handlers[] = {
- *   make_test_message_handler (),
+ *   GNUNET_MQ_hd_fixed_size(test_message,
+ *                           GNUNET_MESSAGE_TYPE_TEST,
+ *                           struct GNUNET_MessageTest,
+ *                           "context"),
  *   GNUNET_MQ_handler_end()
  * };
  *
  * @param name unique basename for the functions
  * @param code message type constant
  * @param str type of the message (a struct)
+ * @param ctx context for the callbacks
  */
-#define GNUNET_MQ_hd_fixed_size(name,code,str)   \
-  struct GNUNET_MQ_MessageHandler                           \
-  make_##name##_handler (void *cls) {                        \
-    void (*cb)(void *cls, const str *msg) = &handle_##name;  \
-    struct GNUNET_MQ_MessageHandler mh = {                  \
-      NULL, (GNUNET_MQ_MessageCallback) cb,                  \
-      cls, code, sizeof (str) };                             \
-    return mh;                                               \
-  }
+#define GNUNET_MQ_hd_fixed_size(name,code,str,ctx)           \
+  ({                                                         \
+    void (*_cb)(void *cls, const str *msg) = &handle_##name; \
+    ((struct GNUNET_MQ_MessageHandler) {                     \
+      NULL, (GNUNET_MQ_MessageCallback) _cb,                 \
+      (ctx), (code), sizeof (str) });                        \
+  })
 
 
 /**
@@ -355,9 +355,6 @@ struct GNUNET_MQ_MessageHandler
  * The macro is to be used as follows:
  * <code>
  * struct GNUNET_MessageTest { ... }; // can be variable size
- * GNUNET_MQ_hd_var_size(test_message,
- *                       GNUNET_MESSAGE_TYPE_TEST,
- *                       struct GNUNET_MessageTest);
  * static int
  * check_test (void *cls,
  *             const struct GNUNET_MessageTest *msg)
@@ -376,25 +373,27 @@ struct GNUNET_MQ_MessageHandler
  * }
  *
  * struct GNUNET_MQ_MessageHandler handlers[] = {
- *   make_test_message_handler ("context"),
+ *   GNUNET_MQ_hd_var_size(test_message,
+ *                         GNUNET_MESSAGE_TYPE_TEST,
+ *                         struct GNUNET_MessageTest,
+ *                         "context"),
  *   GNUNET_MQ_handler_end()
  * };
  *
  * @param name unique basename for the functions
  * @param code message type constant
  * @param str type of the message (a struct)
+ * @param ctx context for the callbacks
  */
-#define GNUNET_MQ_hd_var_size(name,code,str)               \
-  struct GNUNET_MQ_MessageHandler                         \
-  make_##name##_handler (void *ctx) {                     \
-    int (*mv)(void *cls, const str *msg) = &check_##name;  \
-    void (*cb)(void *cls, const str *msg) = &handle_##name;\
-    struct GNUNET_MQ_MessageHandler mh =                   \
-      { (GNUNET_MQ_MessageValidationCallback) mv,          \
-       (GNUNET_MQ_MessageCallback) cb,                    \
-       ctx, code, sizeof (str) };                         \
-    return mh;                                             \
-  }
+#define GNUNET_MQ_hd_var_size(name,code,str,ctx)             \
+  ({                                                         \
+    int (*_mv)(void *cls, const str *msg) = &check_##name;   \
+    void (*_cb)(void *cls, const str *msg) = &handle_##name; \
+    ((struct GNUNET_MQ_MessageHandler)                       \
+      { (GNUNET_MQ_MessageValidationCallback) _mv,           \
+        (GNUNET_MQ_MessageCallback) _cb,                     \
+        (ctx), (code), sizeof (str) });                      \
+  })
 
 
 /**
@@ -411,6 +410,16 @@ GNUNET_MQ_msg_ (struct GNUNET_MessageHeader **mhp,
                 uint16_t type);
 
 
+/**
+ * Create a new envelope by copying an existing message.
+ *
+ * @param hdr header of the message to copy
+ * @return envelope containing @a hdr
+ */
+struct GNUNET_MQ_Envelope *
+GNUNET_MQ_msg_copy (const struct GNUNET_MessageHeader *hdr);
+
+
 /**
  * Discard the message queue message, free all
  * allocated resources. Must be called in the event
@@ -423,7 +432,78 @@ GNUNET_MQ_discard (struct GNUNET_MQ_Envelope *mqm);
 
 
 /**
- * Send a message with the give message queue.
+ * Function to obtain the current envelope
+ * from within #GNUNET_MQ_SendImpl implementations.
+ *
+ * @param mq message queue to interrogate
+ * @return the current envelope
+ */
+struct GNUNET_MQ_Envelope *
+GNUNET_MQ_get_current_envelope (struct GNUNET_MQ_Handle *mq);
+
+
+/**
+ * Function to obtain the last envelope in the queue.
+ *
+ * @param mq message queue to interrogate
+ * @return the last envelope in the queue
+ */
+struct GNUNET_MQ_Envelope *
+GNUNET_MQ_get_last_envelope (struct GNUNET_MQ_Handle *mq);
+
+
+/**
+ * Set application-specific options for this envelope.
+ * Overrides the options set for the queue with
+ * #GNUNET_MQ_set_options() for this message only.
+ *
+ * @param env message to set options for
+ * @param flags flags to use (meaning is queue-specific)
+ * @param extra additional buffer for further data (also queue-specific)
+ */
+void
+GNUNET_MQ_env_set_options (struct GNUNET_MQ_Envelope *env,
+                          uint64_t flags,
+                          const void *extra);
+
+
+/**
+ * Get application-specific options for this envelope.
+ *
+ * @param env message to set options for
+ * @param[out] flags set to flags to use (meaning is queue-specific)
+ * @return extra additional buffer for further data (also queue-specific)
+ */
+const void *
+GNUNET_MQ_env_get_options (struct GNUNET_MQ_Envelope *env,
+                          uint64_t *flags);
+
+
+/**
+ * Set application-specific options for this queue.
+ *
+ * @param mq message queue to set options for
+ * @param flags flags to use (meaning is queue-specific)
+ * @param extra additional buffer for further data (also queue-specific)
+ */
+void
+GNUNET_MQ_set_options (struct GNUNET_MQ_Handle *mq,
+                      uint64_t flags,
+                      const void *extra);
+
+
+/**
+ * Obtain the current length of the message queue.
+ *
+ * @param mq queue to inspect
+ * @return number of queued, non-transmitted messages
+ */
+unsigned int
+GNUNET_MQ_get_length (struct GNUNET_MQ_Handle *mq);
+
+
+/**
+ * Send a message with the given message queue.
  * May only be called once per message.
  *
  * @param mq message queue
@@ -434,6 +514,18 @@ GNUNET_MQ_send (struct GNUNET_MQ_Handle *mq,
                struct GNUNET_MQ_Envelope *ev);
 
 
+/**
+ * Send a copy of a message with the given message queue.
+ * Can be called repeatedly on the same envelope.
+ *
+ * @param mq message queue
+ * @param ev the envelope with the message to send.
+ */
+void
+GNUNET_MQ_send_copy (struct GNUNET_MQ_Handle *mq,
+                     const struct GNUNET_MQ_Envelope *ev);
+
+
 /**
  * Cancel sending the message. Message must have been sent with
  * #GNUNET_MQ_send before.  May not be called after the notify sent
@@ -502,6 +594,18 @@ GNUNET_MQ_queue_for_callbacks (GNUNET_MQ_SendImpl send,
                                void *cls);
 
 
+/**
+ * Change the closure argument in all of the `handlers` of the
+ * @a mq.
+ *
+ * @param mq to modify
+ * @param handlers_cls new closure to use
+ */
+void
+GNUNET_MQ_set_handlers_closure (struct GNUNET_MQ_Handle *mq,
+                                void *handlers_cls);
+
+
 /**
  * Call a callback once the envelope has been sent, that is,
  * sending it can not be canceled anymore.