implement proper SEND_MSG wrapping for control messages
authorChristian Grothoff <christian@grothoff.org>
Wed, 17 Apr 2019 10:50:33 +0000 (12:50 +0200)
committerChristian Grothoff <christian@grothoff.org>
Wed, 17 Apr 2019 10:50:33 +0000 (12:50 +0200)
src/transport/gnunet-service-tng.c

index 41aed96303c7bb26e14e37708898059430a9109c..29bf3bf95a815c9b0e9e294d07a6fa5672adb8ef 100644 (file)
@@ -33,8 +33,6 @@
  *       transport-to-transport traffic)
  *
  * Implement next:
- * - FIXMEs: missing communicator-protocol wrappers around messages
- *           passed in MQ transmission requests on queues (see FIXME in code)
  * - route_message() implementation, including using DV data structures
  *   (but not when routing certain message types, like DV learn,
  *    MUST pay attention to content here -- or pass extra flags?)
@@ -1460,7 +1458,12 @@ enum PendingMessageType
   /**
    * Any type of acknowledgement.
    */
-  PMT_ACKNOWLEDGEMENT = 3
+  PMT_ACKNOWLEDGEMENT = 3,
+
+  /**
+   * Control traffic generated by the TRANSPORT service itself.
+   */
+  PMT_CONTROL = 4
 
 };
 
@@ -5670,6 +5673,55 @@ reliability_box_message (struct PendingMessage *pm)
 }
 
 
+/**
+ * Send the control message @a payload on @a queue.
+ *
+ * @param queue the queue to use for transmission
+ * @param pm pending message to update once transmission is done, may be NULL!
+ * @param payload the payload to send (encapsulated in a
+ *        #GNUNET_MESSAGE_TYPE_TRANSPORT_SEND_MSG).
+ * @param payload_size number of bytes in @a payload
+ */
+static void
+queue_send_msg (struct Queue *queue,
+                struct PendingMessage *pm,
+                const void *payload,
+                size_t payload_size)
+{
+  struct Neighbour *n = queue->neighbour;
+  struct GNUNET_TRANSPORT_SendMessageTo *smt;
+  struct GNUNET_MQ_Envelope *env;
+
+  env = GNUNET_MQ_msg_extra (smt,
+                             payload_size,
+                             GNUNET_MESSAGE_TYPE_TRANSPORT_SEND_MSG);
+  smt->qid = queue->qid;
+  smt->mid = queue->mid_gen;
+  smt->receiver = n->pid;
+  memcpy (&smt[1],
+          payload,
+          payload_size);
+  {
+    /* Pass the env to the communicator of queue for transmission. */
+    struct QueueEntry *qe;
+
+    qe = GNUNET_new (struct QueueEntry);
+    qe->mid = queue->mid_gen++;
+    qe->queue = queue;
+    // qe->pm = pm; // FIXME: not so easy, reference management on 'free(s)'!
+    // (also, note that pm may be NULL!)
+    GNUNET_CONTAINER_DLL_insert (queue->queue_head,
+                                 queue->queue_tail,
+                                 qe);
+    GNUNET_assert (CT_COMMUNICATOR == queue->tc->type);
+    queue->queue_length++;
+    queue->tc->details.communicator.total_queue_length++;
+    GNUNET_MQ_send (queue->tc->mq,
+                    env);
+  }
+}
+
+
 /**
  * We believe we are ready to transmit a message on a queue. Double-checks
  * with the queue's "tracker_out" and then gives the message to the
@@ -5686,8 +5738,6 @@ transmit_on_queue (void *cls)
   struct PendingMessage *pm;
   struct PendingMessage *s;
   uint32_t overhead;
-  struct GNUNET_TRANSPORT_SendMessageTo *smt;
-  struct GNUNET_MQ_Envelope *env;
 
   queue->transmit_task = NULL;
   if (NULL == (pm = n->pending_msg_head))
@@ -5728,33 +5778,10 @@ transmit_on_queue (void *cls)
   }
 
   /* Pass 's' for transission to the communicator */
-  env = GNUNET_MQ_msg_extra (smt,
-                             s->bytes_msg,
-                             GNUNET_MESSAGE_TYPE_TRANSPORT_SEND_MSG);
-  smt->qid = queue->qid;
-  smt->mid = queue->mid_gen;
-  smt->receiver = n->pid;
-  memcpy (&smt[1],
-          &s[1],
-          s->bytes_msg);
-  {
-    /* Pass the env to the communicator of queue for transmission. */
-    struct QueueEntry *qe;
-
-    qe = GNUNET_new (struct QueueEntry);
-    qe->mid = queue->mid_gen++;
-    qe->queue = queue;
-    // qe->pm = s; // FIXME: not so easy, reference management on 'free(s)'!
-    GNUNET_CONTAINER_DLL_insert (queue->queue_head,
-                                 queue->queue_tail,
-                                 qe);
-    GNUNET_assert (CT_COMMUNICATOR == queue->tc->type);
-    queue->queue_length++;
-    queue->tc->details.communicator.total_queue_length++;
-    GNUNET_MQ_send (queue->tc->mq,
-                    env);
-  }
-
+  queue_send_msg (queue,
+                  s,
+                  &s[1],
+                  s->bytes_msg);
   // FIXME: do something similar to the logic below
   // in defragmentation / reliability ACK handling!
 
@@ -6217,19 +6244,18 @@ static void
 validation_transmit_on_queue (struct Queue *q,
                               struct ValidationState *vs)
 {
-  struct GNUNET_MQ_Envelope *env;
-  struct TransportValidationChallenge *tvc;
+  struct TransportValidationChallenge tvc;
 
   vs->last_challenge_use = GNUNET_TIME_absolute_get ();
-  env = GNUNET_MQ_msg (tvc,
-                       GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_CHALLENGE);
-  tvc->reserved = htonl (0);
-  tvc->challenge = vs->challenge;
-  tvc->sender_time = GNUNET_TIME_absolute_hton (vs->last_challenge_use);
-  // FIXME: not so easy, need to BOX this message
-  // in a transmission request! (mistake also done elsewhere!)
-  GNUNET_MQ_send (q->tc->mq,
-                  env);
+  tvc.header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_CHALLENGE);
+  tvc.header.size = htons (sizeof (tvc));
+  tvc.reserved = htonl (0);
+  tvc.challenge = vs->challenge;
+  tvc.sender_time = GNUNET_TIME_absolute_hton (vs->last_challenge_use);
+  queue_send_msg (q,
+                  NULL,
+                  &tvc,
+                  sizeof (tvc));
 }
 
 
@@ -6379,8 +6405,7 @@ start_dv_learn (void *cls)
 {
   struct LearnLaunchEntry *lle;
   struct QueueQualityContext qqc;
-  struct GNUNET_MQ_Envelope *env;
-  struct TransportDVLearn *dvl;
+  struct TransportDVLearn dvl;
 
   (void) cls;
   dvlearn_task = NULL;
@@ -6433,11 +6458,11 @@ start_dv_learn (void *cls)
                                                     &lle->challenge,
                                                     lle,
                                                     GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY));
-  env = GNUNET_MQ_msg (dvl,
-                       GNUNET_MESSAGE_TYPE_TRANSPORT_DV_LEARN);
-  dvl->num_hops = htons (0);
-  dvl->bidirectional = htons (0);
-  dvl->non_network_delay = GNUNET_TIME_relative_hton (GNUNET_TIME_UNIT_ZERO);
+  dvl.header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_DV_LEARN);
+  dvl.header.size = htons (sizeof (dvl));
+  dvl.num_hops = htons (0);
+  dvl.bidirectional = htons (0);
+  dvl.non_network_delay = GNUNET_TIME_relative_hton (GNUNET_TIME_UNIT_ZERO);
   {
     struct DvInitPS dvip = {
       .purpose.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_TRANSPORT_DV_INITIATOR),
@@ -6448,10 +6473,10 @@ start_dv_learn (void *cls)
     GNUNET_assert (GNUNET_OK ==
                    GNUNET_CRYPTO_eddsa_sign (GST_my_private_key,
                                              &dvip.purpose,
-                                             &dvl->init_sig));
+                                             &dvl.init_sig));
   }
-  dvl->initiator = GST_my_identity;
-  dvl->challenge = lle->challenge;
+  dvl.initiator = GST_my_identity;
+  dvl.challenge = lle->challenge;
 
   qqc.quality_count = 0;
   qqc.k = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK,
@@ -6465,11 +6490,11 @@ start_dv_learn (void *cls)
 
   /* Do this as close to transmission time as possible! */
   lle->launch_time = GNUNET_TIME_absolute_get ();
-  // FIXME: not so easy, need to BOX this message
-  // in a transmission request! (mistake also done elsewhere!)
-  GNUNET_MQ_send (qqc.q->tc->mq,
-                  env);
 
+  queue_send_msg (qqc.q,
+                  NULL,
+                  &dvl,
+                  sizeof (dvl));
   /* reschedule this job, randomizing the time it runs (but no
      actual backoff!) */
   dvlearn_task