gnunet-svn
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[gnunet] branch master updated: - fixed bug with broadcast test. - added


From: gnunet
Subject: [gnunet] branch master updated: - fixed bug with broadcast test. - added configurable port for router in netjail_start.sh. - added key for configuring broadcast in topo.sh. - port for communicators can variable. - added variable additional_connects in GNUNET_TESTING_NetjailTopology. - additional connects can be configured in topology file. - added distance vector test with circle topology. - Reassambly for fragmentation is now stored at VirtualLink, not at Neighbour. - DV forwarding distingush between control flow and pa [...]
Date: Fri, 21 Jan 2022 15:44:50 +0100

This is an automated email from the git hooks/post-receive script.

t3sserakt pushed a commit to branch master
in repository gnunet.

The following commit(s) were added to refs/heads/master by this push:
     new fc99f5407 - fixed bug with broadcast test. - added configurable port 
for router in netjail_start.sh. - added key for configuring broadcast in 
topo.sh. - port for communicators can variable. - added variable 
additional_connects in GNUNET_TESTING_NetjailTopology. - additional connects 
can be configured in topology file. - added distance vector test with circle 
topology. - Reassambly for fragmentation is now stored at VirtualLink, not at 
Neighbour. - DV forwarding distingush between [...]
fc99f5407 is described below

commit fc99f54070e04c043c14f2244f85833ecf6b00c4
Author: t3sserakt <t3ss@posteo.de>
AuthorDate: Fri Jan 21 15:31:44 2022 +0100

    - fixed bug with broadcast test.
    - added configurable port for router in netjail_start.sh.
    - added key for configuring broadcast in topo.sh.
    - port for communicators can variable.
    - added variable additional_connects in GNUNET_TESTING_NetjailTopology.
    - additional connects can be configured in topology file.
    - added distance vector test with circle topology.
    - Reassambly for fragmentation is now stored at VirtualLink, not at 
Neighbour.
    - DV forwarding distingush between control flow and payload.
    - handling fragment box switch to be based on VirtualLink.
    - reliability box will not be handled like a fragment.
    - propagating next retransmission attempt variable of fragment to the root 
message.
    - check for fragmentation when adding reliability box.
    - several smaller bug fixes.
---
 contrib/netjail/netjail_start.sh                   |   9 +-
 contrib/netjail/topo.sh                            |   4 +
 po/POTFILES.in                                     |   1 -
 src/include/gnunet_testing_netjail_lib.h           |   5 +
 src/testing/testing.c                              |  24 +-
 .../testing_api_cmd_netjail_start_testsystem.c     |   6 +-
 src/transport/Makefile.am                          |   4 +-
 src/transport/gnunet-service-tng.c                 | 645 ++++++++++++---------
 .../test_transport_distance_vector_topo.conf       |   8 +
 src/transport/test_transport_hmac_calculation.c    | 250 --------
 .../test_transport_plugin_cmd_simple_send_dv.c     | 109 +++-
 .../test_transport_simple_send_dv_circle.sh        |  12 +
 src/transport/transport-testing-cmds.h             |   5 +-
 src/transport/transport_api_cmd_connecting_peers.c |  39 +-
 src/transport/transport_api_cmd_start_peer.c       |   4 +-
 15 files changed, 559 insertions(+), 566 deletions(-)

diff --git a/contrib/netjail/netjail_start.sh b/contrib/netjail/netjail_start.sh
index 997ad0a95..f7c417c27 100755
--- a/contrib/netjail/netjail_start.sh
+++ b/contrib/netjail/netjail_start.sh
@@ -11,6 +11,8 @@ filename=$1
 PREFIX=$2
 readfile=$3
 
+BROADCAST=0
+
 if [ $readfile -eq 0 ]
 then
     read_topology_string "$filename"
@@ -25,6 +27,11 @@ LOCAL_GROUP="192.168.15"
 GLOBAL_GROUP="92.68.150"
 KNOWN_GROUP="92.68.151"
 
+if [ $BROADCAST -eq 0  ]; then
+   PORT="60002"
+else
+    PORT="2086"
+fi
 
 echo "Start [local: $LOCAL_GROUP.0/24, global: $GLOBAL_GROUP.0/16]"
 
@@ -75,7 +82,7 @@ for N in $(seq $GLOBAL_N); do
     fi
     if [ "1" == "${R_UDP[$N]}" ]
     then
-        ip netns exec ${ROUTERS[$N]} iptables -t nat -A PREROUTING -p udp -d 
$GLOBAL_GROUP.$N --dport 60002 -j DNAT --to $LOCAL_GROUP.1
+        ip netns exec ${ROUTERS[$N]} iptables -t nat -A PREROUTING -p udp -d 
$GLOBAL_GROUP.$N --dport $PORT -j DNAT --to $LOCAL_GROUP.1
         ip netns exec ${ROUTERS[$N]} iptables -A FORWARD -d $LOCAL_GROUP.1  -m 
state --state NEW,RELATED,ESTABLISHED -j ACCEPT
     fi
 done
diff --git a/contrib/netjail/topo.sh b/contrib/netjail/topo.sh
index 9af017ff0..d7586d425 100755
--- a/contrib/netjail/topo.sh
+++ b/contrib/netjail/topo.sh
@@ -76,6 +76,10 @@ parse_line(){
     then
        PLUGIN=$(cut -d : -f 2 <<< $line)
        echo $PLUGIN
+    elif [ "$key" = "B" ]
+    then
+       BROADCAST=$(cut -d : -f 2 <<< $line)
+       echo $BROADCAST
     elif [ "$key" = "K" ]
     then
        echo know node
diff --git a/po/POTFILES.in b/po/POTFILES.in
index 94b64e5b3..ffa06a484 100644
--- a/po/POTFILES.in
+++ b/po/POTFILES.in
@@ -314,7 +314,6 @@ src/reclaim/plugin_rest_reclaim.c
 src/reclaim/reclaim_api.c
 src/reclaim/reclaim_attribute.c
 src/reclaim/reclaim_credential.c
-src/reclaim/test.c
 src/regex/gnunet-daemon-regexprofiler.c
 src/regex/gnunet-regex-profiler.c
 src/regex/gnunet-regex-simulation-profiler.c
diff --git a/src/include/gnunet_testing_netjail_lib.h 
b/src/include/gnunet_testing_netjail_lib.h
index 69d6e7a7d..4b5d7cfa1 100644
--- a/src/include/gnunet_testing_netjail_lib.h
+++ b/src/include/gnunet_testing_netjail_lib.h
@@ -232,6 +232,11 @@ struct GNUNET_TESTING_NetjailTopology
    * Hash map containing the global known nodes which are not natted.
    */
   struct GNUNET_CONTAINER_MultiShortmap *map_globals;
+
+  /**
+   * Additional connects we do expect, beside the connects which are 
configured in the topology.
+   */
+  unsigned int additional_connects;
 };
 
 /**
diff --git a/src/testing/testing.c b/src/testing/testing.c
index fd0701d7d..6480d32f9 100644
--- a/src/testing/testing.c
+++ b/src/testing/testing.c
@@ -38,11 +38,11 @@
 
 #define LOG(kind, ...) GNUNET_log_from (kind, "testing-api", __VA_ARGS__)
 
-#define CONNECT_ADDRESS_TEMPLATE "%s-192.168.15.%u:60002"
+#define CONNECT_ADDRESS_TEMPLATE "%s-192.168.15.%u"
 
-#define ROUTER_CONNECT_ADDRESS_TEMPLATE "%s-92.68.150.%u:60002"
+#define ROUTER_CONNECT_ADDRESS_TEMPLATE "%s-92.68.150.%u"
 
-#define KNOWN_CONNECT_ADDRESS_TEMPLATE "%s-92.68.151.%u:60002"
+#define KNOWN_CONNECT_ADDRESS_TEMPLATE "%s-92.68.151.%u"
 
 #define PREFIX_TCP "tcp"
 
@@ -2298,6 +2298,7 @@ GNUNET_TESTING_get_address (struct 
GNUNET_TESTING_NodeConnection *connection,
   struct GNUNET_TESTING_NetjailNode *node;
   char *addr;
   char *template;
+  unsigned int node_n;
 
   LOG (GNUNET_ERROR_TYPE_DEBUG,
        "node_n: %u\n",
@@ -2307,14 +2308,17 @@ GNUNET_TESTING_get_address (struct 
GNUNET_TESTING_NodeConnection *connection,
   if (connection->namespace_n == node->namespace_n)
   {
     template = CONNECT_ADDRESS_TEMPLATE;
+    node_n = connection->node_n;
   }
   else if (0 == connection->namespace_n)
   {
     template = KNOWN_CONNECT_ADDRESS_TEMPLATE;
+    node_n = connection->node_n;
   }
   else if (1 == connection->node_n)
   {
     template = ROUTER_CONNECT_ADDRESS_TEMPLATE;
+    node_n = connection->namespace_n;
   }
   else
   {
@@ -2327,14 +2331,14 @@ GNUNET_TESTING_get_address (struct 
GNUNET_TESTING_NodeConnection *connection,
     GNUNET_asprintf (&addr,
                      template,
                      prefix,
-                     connection->node_n);
+                     node_n);
   }
   else if (0 == strcmp (PREFIX_UDP, prefix))
   {
     GNUNET_asprintf (&addr,
                      template,
                      prefix,
-                     connection->node_n);
+                     node_n);
   }
   else
   {
@@ -2439,6 +2443,16 @@ GNUNET_TESTING_get_topo_from_string (char *data)
            out);
       topo->nodes_x = out;
     }
+    else if (0 == strcmp (key, "AC"))
+    {
+      LOG (GNUNET_ERROR_TYPE_DEBUG,
+           "Get first Value for AC.\n");
+      out = get_first_value (token);
+      LOG (GNUNET_ERROR_TYPE_DEBUG,
+           "AC: %u\n",
+           out);
+      topo->additional_connects = out;
+    }
     else if (0 == strcmp (key, "T"))
     {
       LOG (GNUNET_ERROR_TYPE_DEBUG,
diff --git a/src/testing/testing_api_cmd_netjail_start_testsystem.c 
b/src/testing/testing_api_cmd_netjail_start_testsystem.c
index 9f39fbfda..0624a7f46 100644
--- a/src/testing/testing_api_cmd_netjail_start_testsystem.c
+++ b/src/testing/testing_api_cmd_netjail_start_testsystem.c
@@ -499,11 +499,11 @@ helper_mst (void *cls, const struct GNUNET_MessageHeader 
*message)
 static void
 exp_cb (void *cls)
 {
-  struct TestingSystemCount *tbc = cls;
+  struct NetJailState *ns = cls;
 
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Called exp_cb.\n");
-  GNUNET_SCHEDULER_cancel (tbc->ns->timeout_task);
-  GNUNET_TESTING_async_fail (&(tbc->ns->ac));
+  GNUNET_SCHEDULER_cancel (ns->timeout_task);
+  GNUNET_TESTING_async_fail (&(ns->ac));
 }
 
 
diff --git a/src/transport/Makefile.am b/src/transport/Makefile.am
index ed5a2ef54..6e8ceb638 100644
--- a/src/transport/Makefile.am
+++ b/src/transport/Makefile.am
@@ -779,7 +779,9 @@ check_SCRIPTS= \
   test_transport_simple_send_string.sh \
   test_transport_simple_send.sh \
   test_transport_simple_send_broadcast.sh \
-  test_transport_udp_backchannel.sh 
+  test_transport_udp_backchannel.sh \
+  test_transport_simple_send_dv_circle.sh 
+  # test_transport_simple_send_dv_inverse.sh
 
 test_transport_start_with_config_SOURCES = \
  test_transport_start_with_config.c
diff --git a/src/transport/gnunet-service-tng.c 
b/src/transport/gnunet-service-tng.c
index e41a1b000..56a854a70 100644
--- a/src/transport/gnunet-service-tng.c
+++ b/src/transport/gnunet-service-tng.c
@@ -741,6 +741,11 @@ struct TransportDVBoxMessage
    */
   struct GNUNET_MessageHeader header;
 
+  /**
+   * Flag if the payload is a control message. In NBO.
+   */
+  unsigned int without_fc;
+
   /**
    * Number of total hops this messages travelled. In NBO.
    * @e origin sets this to zero, to be incremented at
@@ -1197,6 +1202,65 @@ struct CoreSentContext
 };
 
 
+/**
+ * Information we keep for a message that we are reassembling.
+ */
+struct ReassemblyContext
+{
+  /**
+   * Original message ID for of the message that all the fragments
+   * belong to.
+   */
+  struct MessageUUIDP msg_uuid;
+
+  /**
+   * Which neighbour is this context for?
+   */
+  struct VirtualLink *virtual_link;
+
+  /**
+   * Entry in the reassembly heap (sorted by expiration).
+   */
+  struct GNUNET_CONTAINER_HeapNode *hn;
+
+  /**
+   * Bitfield with @e msg_size bits representing the positions
+   * where we have received fragments.  When we receive a fragment,
+   * we check the bits in @e bitfield before incrementing @e msg_missing.
+   *
+   * Allocated after the reassembled message.
+   */
+  uint8_t *bitfield;
+
+  /**
+   * At what time will we give up reassembly of this message?
+   */
+  struct GNUNET_TIME_Absolute reassembly_timeout;
+
+  /**
+   * Time we received the last fragment.  @e avg_ack_delay must be
+   * incremented by now - @e last_frag multiplied by @e num_acks.
+   */
+  struct GNUNET_TIME_Absolute last_frag;
+
+  /**
+   * How big is the message we are reassembling in total?
+   */
+  uint16_t msg_size;
+
+  /**
+   * How many bytes of the message are still missing?  Defragmentation
+   * is complete when @e msg_missing == 0.
+   */
+  uint16_t msg_missing;
+
+  /* Followed by @e msg_size bytes of the (partially) defragmented original
+   * message */
+
+  /* Followed by @e bitfield data */
+};
+
+
 /**
  * A virtual link is another reachable peer that is known to CORE.  It
  * can be either a `struct Neighbour` with at least one confirmed
@@ -1212,6 +1276,25 @@ struct VirtualLink
    */
   struct GNUNET_PeerIdentity target;
 
+  /**
+   * Map with `struct ReassemblyContext` structs for fragments under
+   * reassembly. May be NULL if we currently have no fragments from
+   * this @e pid (lazy initialization).
+   */
+  struct GNUNET_CONTAINER_MultiHashMap32 *reassembly_map;
+
+  /**
+   * Heap with `struct ReassemblyContext` structs for fragments under
+   * reassembly. May be NULL if we currently have no fragments from
+   * this @e pid (lazy initialization).
+   */
+  struct GNUNET_CONTAINER_Heap *reassembly_heap;
+
+  /**
+   * Task to free old entries from the @e reassembly_heap and @e 
reassembly_map.
+   */
+  struct GNUNET_SCHEDULER_Task *reassembly_timeout_task;
+
   /**
    * Communicators blocked for receiving on @e target as we are waiting
    * on the @e core_recv_window to increase.
@@ -1819,63 +1902,7 @@ struct Queue
 };
 
 
-/**
- * Information we keep for a message that we are reassembling.
- */
-struct ReassemblyContext
-{
-  /**
-   * Original message ID for of the message that all the fragments
-   * belong to.
-   */
-  struct MessageUUIDP msg_uuid;
 
-  /**
-   * Which neighbour is this context for?
-   */
-  struct Neighbour *neighbour;
-
-  /**
-   * Entry in the reassembly heap (sorted by expiration).
-   */
-  struct GNUNET_CONTAINER_HeapNode *hn;
-
-  /**
-   * Bitfield with @e msg_size bits representing the positions
-   * where we have received fragments.  When we receive a fragment,
-   * we check the bits in @e bitfield before incrementing @e msg_missing.
-   *
-   * Allocated after the reassembled message.
-   */
-  uint8_t *bitfield;
-
-  /**
-   * At what time will we give up reassembly of this message?
-   */
-  struct GNUNET_TIME_Absolute reassembly_timeout;
-
-  /**
-   * Time we received the last fragment.  @e avg_ack_delay must be
-   * incremented by now - @e last_frag multiplied by @e num_acks.
-   */
-  struct GNUNET_TIME_Absolute last_frag;
-
-  /**
-   * How big is the message we are reassembling in total?
-   */
-  uint16_t msg_size;
-
-  /**
-   * How many bytes of the message are still missing?  Defragmentation
-   * is complete when @e msg_missing == 0.
-   */
-  uint16_t msg_missing;
-
-  /* Followed by @e msg_size bytes of the (partially) defragmented original
-   * message */
-
-  /* Followed by @e bitfield data */
-};
 
 
 /**
@@ -1888,25 +1915,6 @@ struct Neighbour
    */
   struct GNUNET_PeerIdentity pid;
 
-  /**
-   * Map with `struct ReassemblyContext` structs for fragments under
-   * reassembly. May be NULL if we currently have no fragments from
-   * this @e pid (lazy initialization).
-   */
-  struct GNUNET_CONTAINER_MultiHashMap32 *reassembly_map;
-
-  /**
-   * Heap with `struct ReassemblyContext` structs for fragments under
-   * reassembly. May be NULL if we currently have no fragments from
-   * this @e pid (lazy initialization).
-   */
-  struct GNUNET_CONTAINER_Heap *reassembly_heap;
-
-  /**
-   * Task to free old entries from the @e reassembly_heap and @e 
reassembly_map.
-   */
-  struct GNUNET_SCHEDULER_Task *reassembly_timeout_task;
-
   /**
    * Head of MDLL of DV hops that have this neighbour as next hop. Must be
    * purged if this neighbour goes down.
@@ -2940,6 +2948,75 @@ free_pending_message (struct PendingMessage *pm)
 }
 
 
+/**
+ * Free @a rc
+ *
+ * @param rc data structure to free
+ */
+static void
+free_reassembly_context (struct ReassemblyContext *rc)
+{
+  struct VirtualLink *vl = rc->virtual_link;
+
+  GNUNET_assert (rc == GNUNET_CONTAINER_heap_remove_node (rc->hn));
+  GNUNET_assert (GNUNET_OK ==
+                 GNUNET_CONTAINER_multihashmap32_remove (vl->reassembly_map,
+                                                         rc->msg_uuid.uuid,
+                                                         rc));
+  GNUNET_free (rc);
+}
+
+
+/**
+ * Task run to clean up reassembly context of a neighbour that have expired.
+ *
+ * @param cls a `struct Neighbour`
+ */
+static void
+reassembly_cleanup_task (void *cls)
+{
+  struct VirtualLink *vl = cls;
+  struct ReassemblyContext *rc;
+
+  vl->reassembly_timeout_task = NULL;
+  while (NULL != (rc = GNUNET_CONTAINER_heap_peek (vl->reassembly_heap)))
+  {
+    if (0 == GNUNET_TIME_absolute_get_remaining (rc->reassembly_timeout)
+        .rel_value_us)
+    {
+      free_reassembly_context (rc);
+      continue;
+    }
+    GNUNET_assert (NULL == vl->reassembly_timeout_task);
+    vl->reassembly_timeout_task =
+      GNUNET_SCHEDULER_add_at (rc->reassembly_timeout,
+                               &reassembly_cleanup_task,
+                               vl);
+    return;
+  }
+}
+
+
+/**
+ * function called to #free_reassembly_context().
+ *
+ * @param cls NULL
+ * @param key unused
+ * @param value a `struct ReassemblyContext` to free
+ * @return #GNUNET_OK (continue iteration)
+ */
+static int
+free_reassembly_cb (void *cls, uint32_t key, void *value)
+{
+  struct ReassemblyContext *rc = value;
+
+  (void) cls;
+  (void) key;
+  free_reassembly_context (rc);
+  return GNUNET_OK;
+}
+
+
 /**
  * Free virtual link.
  *
@@ -2951,6 +3028,21 @@ free_virtual_link (struct VirtualLink *vl)
   struct PendingMessage *pm;
   struct CoreSentContext *csc;
 
+  if (NULL != vl->reassembly_map)
+  {
+    GNUNET_CONTAINER_multihashmap32_iterate (vl->reassembly_map,
+                                             &free_reassembly_cb,
+                                             NULL);
+    GNUNET_CONTAINER_multihashmap32_destroy (vl->reassembly_map);
+    vl->reassembly_map = NULL;
+    GNUNET_CONTAINER_heap_destroy (vl->reassembly_heap);
+    vl->reassembly_heap = NULL;
+  }
+  if (NULL != vl->reassembly_timeout_task)
+  {
+    GNUNET_SCHEDULER_cancel (vl->reassembly_timeout_task);
+    vl->reassembly_timeout_task = NULL;
+  }
   while (NULL != (pm = vl->pending_msg_head))
     free_pending_message (pm);
   GNUNET_assert (GNUNET_YES ==
@@ -3267,75 +3359,6 @@ client_connect_cb (void *cls,
 }
 
 
-/**
- * Free @a rc
- *
- * @param rc data structure to free
- */
-static void
-free_reassembly_context (struct ReassemblyContext *rc)
-{
-  struct Neighbour *n = rc->neighbour;
-
-  GNUNET_assert (rc == GNUNET_CONTAINER_heap_remove_node (rc->hn));
-  GNUNET_assert (GNUNET_OK ==
-                 GNUNET_CONTAINER_multihashmap32_remove (n->reassembly_map,
-                                                         rc->msg_uuid.uuid,
-                                                         rc));
-  GNUNET_free (rc);
-}
-
-
-/**
- * Task run to clean up reassembly context of a neighbour that have expired.
- *
- * @param cls a `struct Neighbour`
- */
-static void
-reassembly_cleanup_task (void *cls)
-{
-  struct Neighbour *n = cls;
-  struct ReassemblyContext *rc;
-
-  n->reassembly_timeout_task = NULL;
-  while (NULL != (rc = GNUNET_CONTAINER_heap_peek (n->reassembly_heap)))
-  {
-    if (0 == GNUNET_TIME_absolute_get_remaining (rc->reassembly_timeout)
-        .rel_value_us)
-    {
-      free_reassembly_context (rc);
-      continue;
-    }
-    GNUNET_assert (NULL == n->reassembly_timeout_task);
-    n->reassembly_timeout_task =
-      GNUNET_SCHEDULER_add_at (rc->reassembly_timeout,
-                               &reassembly_cleanup_task,
-                               n);
-    return;
-  }
-}
-
-
-/**
- * function called to #free_reassembly_context().
- *
- * @param cls NULL
- * @param key unused
- * @param value a `struct ReassemblyContext` to free
- * @return #GNUNET_OK (continue iteration)
- */
-static int
-free_reassembly_cb (void *cls, uint32_t key, void *value)
-{
-  struct ReassemblyContext *rc = value;
-
-  (void) cls;
-  (void) key;
-  free_reassembly_context (rc);
-  return GNUNET_OK;
-}
-
-
 /**
  * Release memory used by @a neighbour.
  *
@@ -3354,16 +3377,6 @@ free_neighbour (struct Neighbour *neighbour)
                                                        neighbour));
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Freeing neighbour\n");
-  if (NULL != neighbour->reassembly_map)
-  {
-    GNUNET_CONTAINER_multihashmap32_iterate (neighbour->reassembly_map,
-                                             &free_reassembly_cb,
-                                             NULL);
-    GNUNET_CONTAINER_multihashmap32_destroy (neighbour->reassembly_map);
-    neighbour->reassembly_map = NULL;
-    GNUNET_CONTAINER_heap_destroy (neighbour->reassembly_heap);
-    neighbour->reassembly_heap = NULL;
-  }
   while (NULL != (dvh = neighbour->dv_head))
   {
     struct DistanceVector *dv = dvh->dv;
@@ -3372,11 +3385,6 @@ free_neighbour (struct Neighbour *neighbour)
     if (NULL == dv->dv_head)
       free_dv_route (dv);
   }
-  if (NULL != neighbour->reassembly_timeout_task)
-  {
-    GNUNET_SCHEDULER_cancel (neighbour->reassembly_timeout_task);
-    neighbour->reassembly_timeout_task = NULL;
-  }
   if (NULL != neighbour->get)
   {
     GNUNET_PEERSTORE_iterate_cancel (neighbour->get);
@@ -4232,9 +4240,10 @@ update_ephemeral (struct DistanceVector *dv)
   GNUNET_CRYPTO_ecdhe_key_create (&dv->private_key);
   GNUNET_CRYPTO_ecdhe_key_get_public (&dv->private_key, &dv->ephemeral_key);
   ec.purpose.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_TRANSPORT_EPHEMERAL);
-  ec.purpose.size = htonl (sizeof(ec));
   ec.target = dv->target;
   ec.ephemeral_key = dv->ephemeral_key;
+  ec.sender_monotonic_time = GNUNET_TIME_absolute_hton (dv->monotime);
+  ec.purpose.size = htonl (sizeof(ec));
   GNUNET_CRYPTO_eddsa_sign (GST_my_private_key,
                             &ec,
                             &dv->sender_sig);
@@ -4455,7 +4464,8 @@ dv_setup_key_state_from_km (const struct GNUNET_HashCode 
*km,
                                     km,
                                     sizeof(*km),
                                     iv,
-                                    sizeof(*iv)));
+                                    sizeof(*iv),
+                                    NULL));
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Deriving backchannel key based on KM %s and IV %s\n",
               GNUNET_h2s (km),
@@ -4616,6 +4626,7 @@ typedef void (*DVMessageHandler) (void *cls,
  * @param use function to call with the encapsulated message
  * @param use_cls closure for @a use
  * @param options whether path must be confirmed or not, to be passed to @a use
+ * @param shall this TransportDVBoxMessage be forwarded without flow control.
  * @return expected RTT for transmission, #GNUNET_TIME_UNIT_FOREVER_REL if 
sending failed
  */
 static struct GNUNET_TIME_Relative
@@ -4625,7 +4636,8 @@ encapsulate_for_dv (struct DistanceVector *dv,
                     const struct GNUNET_MessageHeader *hdr,
                     DVMessageHandler use,
                     void *use_cls,
-                    enum RouteMessageOptions options)
+                    enum RouteMessageOptions options,
+                    enum GNUNET_GenericReturnValue without_fc)
 {
   struct TransportDVBoxMessage box_hdr;
   struct TransportDVBoxPayloadP payload_hdr;
@@ -4633,28 +4645,31 @@ encapsulate_for_dv (struct DistanceVector *dv,
   char enc[sizeof(struct TransportDVBoxPayloadP) + enc_body_size] GNUNET_ALIGN;
   struct TransportDVBoxPayloadP *enc_payload_hdr =
     (struct TransportDVBoxPayloadP *) enc;
-  struct DVKeyState key;
+  struct DVKeyState *key;
   struct GNUNET_TIME_Relative rtt;
 
+  key = GNUNET_new (struct DVKeyState);
   /* Encrypt payload */
   box_hdr.header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_DV_BOX);
   box_hdr.total_hops = htons (0);
+  box_hdr.without_fc = htons (without_fc);
   update_ephemeral (dv);
   box_hdr.ephemeral_key = dv->ephemeral_key;
   payload_hdr.sender_sig = dv->sender_sig;
+
   GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_NONCE,
                               &box_hdr.iv,
                               sizeof(box_hdr.iv));
-  dh_key_derive_eph_pid (&dv->private_key, &dv->target, &box_hdr.iv, &key);
+  dh_key_derive_eph_pid (&dv->private_key, &dv->target, &box_hdr.iv, key);
   payload_hdr.sender = GST_my_identity;
   payload_hdr.monotonic_time = GNUNET_TIME_absolute_hton (dv->monotime);
-  dv_encrypt (&key, &payload_hdr, enc_payload_hdr, sizeof(payload_hdr));
-  dv_encrypt (&key,
+  dv_encrypt (key, &payload_hdr, enc_payload_hdr, sizeof(payload_hdr));
+  dv_encrypt (key,
               hdr,
               &enc[sizeof(struct TransportDVBoxPayloadP)],
               enc_body_size);
-  dv_hmac (&key, &box_hdr.hmac, enc, sizeof(enc));
-  dv_key_clean (&key);
+  dv_hmac (key, &box_hdr.hmac, enc, sizeof(enc));
+  dv_key_clean (key);
   rtt = GNUNET_TIME_UNIT_FOREVER_REL;
   /* For each selected path, take the pre-computed header and body
      and add the path in the middle of the message; then send it. */
@@ -4681,7 +4696,7 @@ encapsulate_for_dv (struct DistanceVector *dv,
       char *path;
 
       path = GNUNET_strdup (GNUNET_i2s (&GST_my_identity));
-      for (unsigned int j = 0; j <= num_hops; j++)
+      for (unsigned int j = 0; j < num_hops; j++)
       {
         char *tmp;
 
@@ -4694,7 +4709,7 @@ encapsulate_for_dv (struct DistanceVector *dv,
                   ntohs (hdr->type),
                   GNUNET_i2s (&dv->target),
                   i + 1,
-                  num_dvhs + 1,
+                  num_dvhs,
                   path);
       GNUNET_free (path);
     }
@@ -4704,6 +4719,7 @@ encapsulate_for_dv (struct DistanceVector *dv,
          dvh->next_hop,
          (const struct GNUNET_MessageHeader *) buf,
          options);
+    GNUNET_free (key);
   }
   return rtt;
 }
@@ -4828,13 +4844,16 @@ route_control_message_without_fc (struct VirtualLink 
*vl,
                   "Failed to route message, could not determine DV path\n");
       return rtt1;
     }
+    GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                "encapsulate_for_dv 1\n");
     rtt2 = encapsulate_for_dv (dv,
                                res,
                                hops,
                                hdr,
                                &send_dv_to_neighbour,
                                NULL,
-                               options & (~RMO_REDUNDANT));
+                               options & (~RMO_REDUNDANT),
+                               GNUNET_YES);
   }
   return GNUNET_TIME_relative_min (rtt1, rtt2);
 }
@@ -4955,7 +4974,8 @@ check_vl_transmission (struct VirtualLink *vl)
         vl->outbound_fc_window_size)
     {
       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-                  "Stalled transmission on VL %s due to flow control: %llu < 
%llu\n",
+                  "Stalled message %lu transmission on VL %s due to flow 
control: %llu < %llu\n",
+                  pm->logging_uuid,
                   GNUNET_i2s (&vl->target),
                   (unsigned long long) vl->outbound_fc_window_size,
                   (unsigned long long) (pm->bytes_msg
@@ -4964,6 +4984,14 @@ check_vl_transmission (struct VirtualLink *vl)
       return;     /* We have a message, but flow control says "nope" */
     }
     elig = GNUNET_YES;
+    GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                "Eligible message %lu of size %llu to %s: %llu/%llu\n",
+                pm->logging_uuid,
+                pm->bytes_msg,
+                GNUNET_i2s (&vl->target),
+                (unsigned long long) vl->outbound_fc_window_size,
+                (unsigned long long) (pm->bytes_msg
+                                      + vl->outbound_fc_window_size_used));
     break;
   }
   if (GNUNET_NO == elig)
@@ -5482,7 +5510,7 @@ handle_raw_message (void *cls, const struct 
GNUNET_MessageHeader *mh)
     vl->incoming_fc_window_size_used += size;
     /* TODO-M1 */
     GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-                "Dropped message of type %u with %u bytes to CORE: no CORE 
client connected!",
+                "Dropped message of type %u with %u bytes to CORE: no CORE 
client connected!\n",
                 (unsigned int) ntohs (mh->type),
                 (unsigned int) ntohs (mh->size));
     finish_cmc_handling (cmc);
@@ -5567,7 +5595,7 @@ transmit_cummulative_ack_cb (void *cls)
   struct VirtualLink *vl;
   struct AcknowledgementCummulator *ac = cls;
   char buf[sizeof(struct TransportReliabilityAckMessage)
-           + ac->ack_counter + ac->num_acks
+           + ac->num_acks
            * sizeof(struct TransportCummulativeAckPayloadP)] GNUNET_ALIGN;
   struct TransportReliabilityAckMessage *ack =
     (struct TransportReliabilityAckMessage *) buf;
@@ -5576,16 +5604,16 @@ transmit_cummulative_ack_cb (void *cls)
   ac->task = NULL;
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Sending ACK with %u components to %s\n",
-              ac->ack_counter,
+              ac->num_acks,
               GNUNET_i2s (&ac->target));
-  GNUNET_assert (0 <= ac->ack_counter);
+  GNUNET_assert (0 < ac->num_acks);
   ack->header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_RELIABILITY_ACK);
   ack->header.size =
     htons (sizeof(*ack)
-           + ac->ack_counter * sizeof(struct TransportCummulativeAckPayloadP));
+           + ac->num_acks * sizeof(struct TransportCummulativeAckPayloadP));
   ack->ack_counter = htonl (ac->ack_counter += ac->num_acks);
   ap = (struct TransportCummulativeAckPayloadP *) &ack[1];
-  for (unsigned int i = 0; i < ac->ack_counter; i++)
+  for (unsigned int i = 0; i < ac->num_acks; i++)
   {
     ap[i].ack_uuid = ac->ack_uuids[i].ack_uuid;
     ap[i].ack_delay = GNUNET_TIME_relative_hton (
@@ -5657,7 +5685,6 @@ cummulative_ack (const struct GNUNET_PeerIdentity *pid,
     if (MAX_CUMMULATIVE_ACKS == ac->num_acks)
     {
       /* must run immediately, ack buffer full! */
-      GNUNET_SCHEDULER_cancel (ac->task);
       transmit_cummulative_ack_cb (ac);
     }
     GNUNET_SCHEDULER_cancel (ac->task);
@@ -5727,7 +5754,7 @@ static void
 handle_fragment_box (void *cls, const struct TransportFragmentBoxMessage *fb)
 {
   struct CommunicatorMessageContext *cmc = cls;
-  struct Neighbour *n;
+  struct VirtualLink *vl;
   struct ReassemblyContext *rc;
   const struct GNUNET_MessageHeader *msg;
   uint16_t msize;
@@ -5737,30 +5764,33 @@ handle_fragment_box (void *cls, const struct 
TransportFragmentBoxMessage *fb)
   struct GNUNET_TIME_Relative cdelay;
   struct FindByMessageUuidContext fc;
 
-  n = lookup_neighbour (&cmc->im.sender);
-  if (NULL == n)
+  vl = lookup_virtual_link (&cmc->im.sender);
+  if (NULL == vl)
   {
     struct GNUNET_SERVICE_Client *client = cmc->tc->client;
 
+    GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                "No virtual link for %s to handle fragment\n",
+                GNUNET_i2s (&cmc->im.sender));
     GNUNET_break (0);
     finish_cmc_handling (cmc);
     GNUNET_SERVICE_client_drop (client);
     return;
   }
-  if (NULL == n->reassembly_map)
+  if (NULL == vl->reassembly_map)
   {
-    n->reassembly_map = GNUNET_CONTAINER_multihashmap32_create (8);
-    n->reassembly_heap =
+    vl->reassembly_map = GNUNET_CONTAINER_multihashmap32_create (8);
+    vl->reassembly_heap =
       GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN);
-    n->reassembly_timeout_task =
+    vl->reassembly_timeout_task =
       GNUNET_SCHEDULER_add_delayed (REASSEMBLY_EXPIRATION,
                                     &reassembly_cleanup_task,
-                                    n);
+                                    vl);
   }
   msize = ntohs (fb->msg_size);
   fc.message_uuid = fb->msg_uuid;
   fc.rc = NULL;
-  (void) GNUNET_CONTAINER_multihashmap32_get_multiple (n->reassembly_map,
+  (void) GNUNET_CONTAINER_multihashmap32_get_multiple (vl->reassembly_map,
                                                        fb->msg_uuid.uuid,
                                                        &find_by_message_uuid,
                                                        &fc);
@@ -5769,17 +5799,17 @@ handle_fragment_box (void *cls, const struct 
TransportFragmentBoxMessage *fb)
     rc = GNUNET_malloc (sizeof(*rc) + msize    /* reassembly payload buffer */
                         + (msize + 7) / 8 * sizeof(uint8_t) /* bitfield */);
     rc->msg_uuid = fb->msg_uuid;
-    rc->neighbour = n;
+    rc->virtual_link = vl;
     rc->msg_size = msize;
     rc->reassembly_timeout =
       GNUNET_TIME_relative_to_absolute (REASSEMBLY_EXPIRATION);
     rc->last_frag = GNUNET_TIME_absolute_get ();
-    rc->hn = GNUNET_CONTAINER_heap_insert (n->reassembly_heap,
+    rc->hn = GNUNET_CONTAINER_heap_insert (vl->reassembly_heap,
                                            rc,
                                            
rc->reassembly_timeout.abs_value_us);
     GNUNET_assert (GNUNET_OK ==
                    GNUNET_CONTAINER_multihashmap32_put (
-                     n->reassembly_map,
+                     vl->reassembly_map,
                      rc->msg_uuid.uuid,
                      rc,
                      GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE));
@@ -6452,12 +6482,12 @@ learn_dv_path (const struct GNUNET_PeerIdentity *path,
   for (struct DistanceVectorHop *pos = dv->dv_head; NULL != pos;
        pos = pos->next_dv)
   {
-    if (pos->distance < path_len - 2)
+    if (pos->distance < path_len - 3)
       shorter_distance++;
-    /* Note that the distances in 'pos' excludes us (path[0]) and
-       the next_hop (path[1]), so we need to subtract two
+    /* Note that the distances in 'pos' excludes us (path[0]),
+       the next_hop (path[1]) and the target so we need to subtract three
        and check next_hop explicitly */
-    if ((pos->distance == path_len - 2) && (pos->next_hop == next_hop))
+    if ((pos->distance == path_len - 3) && (pos->next_hop == next_hop))
     {
       int match = GNUNET_YES;
 
@@ -6521,16 +6551,16 @@ learn_dv_path (const struct GNUNET_PeerIdentity *path,
               "Discovered new DV path to %s\n",
               GNUNET_i2s (&dv->target));
   hop = GNUNET_malloc (sizeof(struct DistanceVectorHop)
-                       + sizeof(struct GNUNET_PeerIdentity) * (path_len - 2));
+                       + sizeof(struct GNUNET_PeerIdentity) * (path_len - 3));
   hop->next_hop = next_hop;
   hop->dv = dv;
   hop->path = (const struct GNUNET_PeerIdentity *) &hop[1];
   memcpy (&hop[1],
           &path[2],
-          sizeof(struct GNUNET_PeerIdentity) * (path_len - 2));
+          sizeof(struct GNUNET_PeerIdentity) * (path_len - 3));
   hop->timeout = GNUNET_TIME_relative_to_absolute (DV_PATH_VALIDITY_TIMEOUT);
   hop->path_valid_until = path_valid_until;
-  hop->distance = path_len - 2;
+  hop->distance = path_len - 3;
   hop->pd.aged_rtt = network_latency;
   GNUNET_CONTAINER_MDLL_insert (dv, dv->dv_head, dv->dv_tail, hop);
   GNUNET_CONTAINER_MDLL_insert (neighbour,
@@ -6630,6 +6660,7 @@ forward_dv_learn (const struct GNUNET_PeerIdentity 
*next_hop,
   fwd->init_sig = msg->init_sig;
   fwd->initiator = msg->initiator;
   fwd->challenge = msg->challenge;
+  fwd->monotonic_time = msg->monotonic_time;
   dhops = (struct DVPathEntryP *) &fwd[1];
   GNUNET_memcpy (dhops, hops, sizeof(struct DVPathEntryP) * nhops);
   dhops[nhops].hop = GST_my_identity;
@@ -6795,6 +6826,9 @@ dv_neighbour_transmission (void *cls,
 {
   struct NeighbourSelectionContext *nsc = cls;
 
+  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+              "transmission %s\n",
+              GNUNET_i2s (pid));
   (void) value;
   if (0 == GNUNET_memcmp (pid, &nsc->dvl->initiator))
     return GNUNET_YES; /* skip initiator */
@@ -7012,7 +7046,7 @@ handle_dv_learn (void *cls, const struct 
TransportDVLearnMessage *dvl)
                                                       &dvl->init_sig))
     {
       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-                  "DV learn signature from %s invalid",
+                  "DV learn signature from %s invalid\n",
                   GNUNET_i2s (&dvl->initiator));
       GNUNET_break_op (0);
       return;
@@ -7141,7 +7175,7 @@ handle_dv_learn (void *cls, const struct 
TransportDVLearnMessage *dvl)
                   GNUNET_i2s (&path[i]),
                   GNUNET_STRINGS_relative_time_to_string (ilat, GNUNET_YES));
       learn_dv_path (path,
-                     i,
+                     i + 1,
                      ilat,
                      GNUNET_TIME_relative_to_absolute (
                        ADDRESS_VALIDATION_LIFETIME));
@@ -7177,10 +7211,10 @@ handle_dv_learn (void *cls, const struct 
TransportDVLearnMessage *dvl)
 
       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
                   "Learned inverse path with %u hops to %s\n",
-                  i + 1,
+                  i + 2,
                   GNUNET_i2s (&path[i + 2]));
       iret = learn_dv_path (path,
-                            i + 2,
+                            i + 3,
                             GNUNET_TIME_UNIT_FOREVER_REL,
                             GNUNET_TIME_UNIT_ZERO_ABS);
       if (GNUNET_SYSERR == iret)
@@ -7218,13 +7252,10 @@ handle_dv_learn (void *cls, const struct 
TransportDVLearnMessage *dvl)
     return;
   }
 
-  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "8 handle dv learn message from %s\n",
-              GNUNET_i2s (&dvl->initiator));
   /* Forward to initiator, if path non-trivial and possible */
   bi_history = (bi_history << 1) | (bi_hop ? 1 : 0);
   did_initiator = GNUNET_NO;
-  if ((1 < nhops) &&
+  if ((1 <= nhops) &&
       (GNUNET_YES ==
        GNUNET_CONTAINER_multipeermap_contains (neighbours, &dvl->initiator)))
   {
@@ -7327,7 +7358,7 @@ check_dv_box (void *cls, const struct 
TransportDVBoxMessage *dvb)
  */
 static void
 forward_dv_box (struct Neighbour *next_hop,
-                const struct TransportDVBoxMessage *hdr,
+                struct TransportDVBoxMessage *hdr,
                 uint16_t total_hops,
                 uint16_t num_hops,
                 const struct GNUNET_PeerIdentity *hops,
@@ -7336,37 +7367,57 @@ forward_dv_box (struct Neighbour *next_hop,
 {
   struct VirtualLink *vl = next_hop->vl;
   struct PendingMessage *pm;
-  size_t msg_size;
+  size_t msg_size = sizeof(struct TransportDVBoxMessage)
+                    + num_hops * sizeof(struct GNUNET_PeerIdentity)
+                    + enc_payload_size;
   char *buf;
+  char msg_buf[msg_size] GNUNET_ALIGN;
   struct GNUNET_PeerIdentity *dhops;
 
-  GNUNET_assert (NULL != vl);
-  msg_size = sizeof(struct TransportDVBoxMessage)
-             + num_hops * sizeof(struct GNUNET_PeerIdentity) + 
enc_payload_size;
-  pm = GNUNET_malloc (sizeof(struct PendingMessage) + msg_size);
-  pm->pmt = PMT_DV_BOX;
-  pm->vl = vl;
-  pm->timeout = GNUNET_TIME_relative_to_absolute (DV_FORWARD_TIMEOUT);
-  pm->logging_uuid = logging_uuid_gen++;
-  pm->prefs = GNUNET_MQ_PRIO_BACKGROUND;
-  pm->bytes_msg = msg_size;
-  buf = (char *) &pm[1];
-  memcpy (buf, hdr, sizeof(*hdr));
-  dhops =
-    (struct GNUNET_PeerIdentity *) &buf[sizeof(struct TransportDVBoxMessage)];
+  GNUNET_assert (GNUNET_YES == ntohs (hdr->without_fc) || NULL != vl);
+
+  hdr->num_hops = htons (num_hops);
+  hdr->total_hops = htons (total_hops);
+  memcpy (msg_buf, hdr, sizeof(*hdr));
+  dhops = (struct GNUNET_PeerIdentity *) &msg_buf[sizeof(struct
+                                                         
TransportDVBoxMessage)];
   memcpy (dhops, hops, num_hops * sizeof(struct GNUNET_PeerIdentity));
   memcpy (&dhops[num_hops], enc_payload, enc_payload_size);
-  GNUNET_CONTAINER_MDLL_insert (vl,
-                                vl->pending_msg_head,
-                                vl->pending_msg_tail,
-                                pm);
-  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "Created pending message %llu for DV Box with next hop %s 
(%u/%u)\n",
-              pm->logging_uuid,
-              GNUNET_i2s (&next_hop->pid),
-              (unsigned int) num_hops,
-              (unsigned int) total_hops);
-  check_vl_transmission (vl);
+
+  if (GNUNET_YES == ntohs (hdr->without_fc))
+  {
+    GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                "Forwarding control message in DV Box to next hop %s (%u/%u) 
\n",
+                GNUNET_i2s (&next_hop->pid),
+                (unsigned int) num_hops,
+                (unsigned int) total_hops);
+    route_via_neighbour (next_hop, (const struct
+                                    GNUNET_MessageHeader *) msg_buf,
+                         RMO_ANYTHING_GOES);
+  }
+  else
+  {
+    pm = GNUNET_malloc (sizeof(struct PendingMessage) + msg_size);
+    pm->pmt = PMT_DV_BOX;
+    pm->vl = vl;
+    pm->timeout = GNUNET_TIME_relative_to_absolute (DV_FORWARD_TIMEOUT);
+    pm->logging_uuid = logging_uuid_gen++;
+    pm->prefs = GNUNET_MQ_PRIO_BACKGROUND;
+    pm->bytes_msg = msg_size;
+    buf = (char *) &pm[1];
+    memcpy (buf, msg_buf, msg_size);
+    GNUNET_CONTAINER_MDLL_insert (vl,
+                                  vl->pending_msg_head,
+                                  vl->pending_msg_tail,
+                                  pm);
+    GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                "Created pending message %llu for DV Box with next hop %s 
(%u/%u)\n",
+                pm->logging_uuid,
+                GNUNET_i2s (&next_hop->pid),
+                (unsigned int) num_hops,
+                (unsigned int) total_hops);
+    check_vl_transmission (vl);
+  }
 }
 
 
@@ -7579,11 +7630,14 @@ handle_dv_box (void *cls, const struct 
TransportDVBoxMessage *dvb)
   const char *enc_payload = (const char *) &hops[num_hops];
   uint16_t enc_payload_size =
     size - (num_hops * sizeof(struct GNUNET_PeerIdentity));
-  struct DVKeyState key;
+  char enc[enc_payload_size];
+  struct DVKeyState *key;
   struct GNUNET_HashCode hmac;
   const char *hdr;
   size_t hdr_len;
 
+  key = GNUNET_new (struct DVKeyState);
+
   if (GNUNET_EXTRA_LOGGING > 0)
   {
     char *path;
@@ -7624,8 +7678,9 @@ handle_dv_box (void *cls, const struct 
TransportDVBoxMessage *dvb)
                   "Skipping %u/%u hops ahead while routing DV Box\n",
                   i,
                   num_hops);
+
       forward_dv_box (n,
-                      dvb,
+                      (struct TransportDVBoxMessage *) dvb,
                       ntohs (dvb->total_hops) + 1,
                       num_hops - i - 1,    /* number of hops left */
                       &hops[i + 1],    /* remaining hops */
@@ -7657,10 +7712,13 @@ handle_dv_box (void *cls, const struct 
TransportDVBoxMessage *dvb)
                             GNUNET_NO);
   cmc->total_hops = ntohs (dvb->total_hops);
 
-  dh_key_derive_eph_pub (&dvb->ephemeral_key, &dvb->iv, &key);
+  dh_key_derive_eph_pub (&dvb->ephemeral_key, &dvb->iv, key);
   hdr = (const char *) &dvb[1];
-  hdr_len = ntohs (dvb->header.size) - sizeof(*dvb);
-  dv_hmac (&key, &hmac, hdr, hdr_len);
+  hdr_len = ntohs (dvb->header.size) - sizeof(*dvb) - sizeof(struct
+                                                             
GNUNET_PeerIdentity)
+            * ntohs (dvb->total_hops);
+
+  dv_hmac (key, &hmac, hdr, hdr_len);
   if (0 != GNUNET_memcmp (&hmac, &dvb->hmac))
   {
     /* HMAC mismatch, discard! */
@@ -7679,9 +7737,9 @@ handle_dv_box (void *cls, const struct 
TransportDVBoxMessage *dvb)
 
     GNUNET_assert (hdr_len >=
                    sizeof(ppay) + sizeof(struct GNUNET_MessageHeader));
-    dv_decrypt (&key, &ppay, hdr, sizeof(ppay));
-    dv_decrypt (&key, &body, &hdr[sizeof(ppay)], hdr_len - sizeof(ppay));
-    dv_key_clean (&key);
+    dv_decrypt (key, &ppay, hdr, sizeof(ppay));
+    dv_decrypt (key, &body, &hdr[sizeof(ppay)], hdr_len - sizeof(ppay));
+    dv_key_clean (key);
     if (ntohs (mh->size) != sizeof(body))
     {
       GNUNET_break_op (0);
@@ -7727,9 +7785,10 @@ handle_dv_box (void *cls, const struct 
TransportDVBoxMessage *dvb)
       struct EphemeralConfirmationPS ec;
 
       ec.purpose.purpose = htonl 
(GNUNET_SIGNATURE_PURPOSE_TRANSPORT_EPHEMERAL);
-      ec.purpose.size = htonl (sizeof(ec));
       ec.target = GST_my_identity;
       ec.ephemeral_key = dvb->ephemeral_key;
+      ec.purpose.size =  htonl (sizeof(ec));
+      ec.sender_monotonic_time = ppay.monotonic_time;
       if (
         GNUNET_OK !=
         GNUNET_CRYPTO_eddsa_verify (
@@ -8656,6 +8715,12 @@ fragment_message (struct Queue *queue,
   mtu = (UINT16_MAX == queue->mtu)
         ? UINT16_MAX - sizeof(struct GNUNET_TRANSPORT_SendMessageTo)
         : queue->mtu;
+  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+              "Fragmenting message <%llu> with size %u to %s for MTU %u\n",
+              pm->logging_uuid,
+              pm->bytes_msg,
+              GNUNET_i2s (&pm->vl->target),
+              (unsigned int) mtu);
   set_pending_message_uuid (pm);
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Fragmenting message %llu <%llu> with size %u to %s for MTU 
%u\n",
@@ -8789,7 +8854,8 @@ reliability_box_message (struct Queue *queue,
   bpm->logging_uuid = logging_uuid_gen++;
   bpm->vl = pm->vl;
   bpm->frag_parent = pm;
-  GNUNET_CONTAINER_MDLL_insert (frag, pm->head_frag, pm->tail_frag, bpm);
+  // Why was this needed?
+  // GNUNET_CONTAINER_MDLL_insert (frag, pm->head_frag, pm->tail_frag, bpm);
   bpm->timeout = pm->timeout;
   bpm->pmt = PMT_RELIABILITY_BOX;
   bpm->bytes_msg = pm->bytes_msg + sizeof(rbox);
@@ -8807,6 +8873,30 @@ reliability_box_message (struct Queue *queue,
 }
 
 
+static void
+reorder_root_pm (struct PendingMessage *pm,
+                 struct GNUNET_TIME_Absolute next_attempt)
+{
+  struct VirtualLink *vl = pm->vl;
+  struct PendingMessage *pos;
+
+  /* re-insert sort in neighbour list */
+  GNUNET_CONTAINER_MDLL_remove (vl,
+                                vl->pending_msg_head,
+                                vl->pending_msg_tail,
+                                pm);
+  pos = vl->pending_msg_tail;
+  while ((NULL != pos) &&
+         (next_attempt.abs_value_us > pos->next_attempt.abs_value_us))
+    pos = pos->prev_vl;
+  GNUNET_CONTAINER_MDLL_insert_after (vl,
+                                      vl->pending_msg_head,
+                                      vl->pending_msg_tail,
+                                      pos,
+                                      pm);
+}
+
+
 /**
  * Change the value of the `next_attempt` field of @a pm
  * to @a next_attempt and re-order @a pm in the transmission
@@ -8829,22 +8919,11 @@ update_pm_next_attempt (struct PendingMessage *pm,
 
   if (NULL == pm->frag_parent)
   {
-    struct PendingMessage *pos;
-
-    /* re-insert sort in neighbour list */
-    GNUNET_CONTAINER_MDLL_remove (vl,
-                                  vl->pending_msg_head,
-                                  vl->pending_msg_tail,
-                                  pm);
-    pos = vl->pending_msg_tail;
-    while ((NULL != pos) &&
-           (next_attempt.abs_value_us > pos->next_attempt.abs_value_us))
-      pos = pos->prev_vl;
-    GNUNET_CONTAINER_MDLL_insert_after (vl,
-                                        vl->pending_msg_head,
-                                        vl->pending_msg_tail,
-                                        pos,
-                                        pm);
+    reorder_root_pm (pm, next_attempt);
+  }
+  else if ((PMT_RELIABILITY_BOX == pm->pmt)||(PMT_DV_BOX == pm->pmt))
+  {
+    reorder_root_pm (pm->frag_parent, next_attempt);
   }
   else
   {
@@ -8862,6 +8941,15 @@ update_pm_next_attempt (struct PendingMessage *pm,
                                         fp->tail_frag,
                                         pos,
                                         pm);
+    if (NULL == pos)
+    {
+      pos = fp;
+      // Get the root pm
+      while (NULL != pos->frag_parent)
+        pos = pos->frag_parent;
+      pos->next_attempt = next_attempt;
+      reorder_root_pm (pos, next_attempt);
+    }
   }
 }
 
@@ -8965,8 +9053,18 @@ select_best_pending_from_link (struct 
PendingMessageScoreContext *sc,
         (0 == (pos->prefs & GNUNET_MQ_PREF_UNRELIABLE)) &&
         (GNUNET_TRANSPORT_CC_RELIABLE != queue->tc->details.communicator.cc))
     {
-      relb = GNUNET_YES;
       real_overhead += sizeof(struct TransportReliabilityBoxMessage);
+
+      if ((0 != queue->mtu) && (pos->bytes_msg + real_overhead > queue->mtu))
+      {
+        frag = GNUNET_YES;
+        real_overhead = overhead + sizeof(struct TransportFragmentBoxMessage);
+      }
+      else
+      {
+        relb = GNUNET_YES;
+      }
+
     }
 
     /* Finally, compare to existing 'best' in sc to see if this 'pos' pending
@@ -8980,7 +9078,8 @@ select_best_pending_from_link (struct 
PendingMessageScoreContext *sc,
          given message fits _this_ queue, and do not consider how well other
          queues might suit the message. Taking other queues into consideration
          may further improve the result, but could also be expensive
-         in terms of CPU time.  */long long sc_score = sc->frag * 40 + 
sc->relb * 20 + sc->real_overhead;
+         in terms of CPU time.  */
+      long long sc_score = sc->frag * 40 + sc->relb * 20 + sc->real_overhead;
       long long pm_score = frag * 40 + relb * 20 + real_overhead;
       long long time_delta =
         (sc->best->next_attempt.abs_value_us - pos->next_attempt.abs_value_us)
@@ -8994,12 +9093,10 @@ select_best_pending_from_link (struct 
PendingMessageScoreContext *sc,
         time_delta *= 10;     /* increase weight (always, both are low 
latency) */
       else if ((0 != (pos->prefs & GNUNET_MQ_PREF_LOW_LATENCY)) &&
                (time_delta > 0))
-        time_delta *=
-          10;     /* increase weight, favors 'pos', which is low latency */
+        time_delta *= 10;     /* increase weight, favors 'pos', which is low 
latency */
       else if ((0 != (sc->best->prefs & GNUNET_MQ_PREF_LOW_LATENCY)) &&
                (time_delta < 0))
-        time_delta *=
-          10;     /* increase weight, favors 'sc->best', which is low latency 
*/
+        time_delta *= 10;     /* increase weight, favors 'sc->best', which is 
low latency */
       if (0 != queue->mtu)
       {
         /* Grant bonus if we are below MTU, larger bonus the closer we will
@@ -9016,6 +9113,7 @@ select_best_pending_from_link (struct 
PendingMessageScoreContext *sc,
     sc->dvh = dvh;
     sc->frag = frag;
     sc->relb = relb;
+    sc->real_overhead = real_overhead;
   }
 }
 
@@ -9027,7 +9125,7 @@ select_best_pending_from_link (struct 
PendingMessageScoreContext *sc,
  *
  * @param cls a `struct PendingMessageScoreContext`
  * @param next_hop next hop of the DV path
- * @param hdr encapsulated message, technically a `struct 
TransportDFBoxMessage`
+ * @param hdr encapsulated message, technically a `struct 
TransportDVBoxMessage`
  * @param options options of the original message
  */
 static void
@@ -9045,6 +9143,11 @@ extract_box_cb (void *cls,
   bpm = GNUNET_malloc (sizeof(struct PendingMessage) + bsize);
   bpm->logging_uuid = logging_uuid_gen++;
   bpm->pmt = PMT_DV_BOX;
+  bpm->vl = pm->vl;
+  bpm->timeout = pm->timeout;
+  bpm->bytes_msg = bsize;
+  bpm->frag_parent = pm;
+  set_pending_message_uuid (bpm);
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Creating DV Box %llu for original message %llu (next hop is 
%s)\n",
               bpm->logging_uuid,
@@ -9132,13 +9235,16 @@ transmit_on_queue (void *cls)
       free_pending_message (sc.best->bpm);
       sc.best->bpm = NULL;
     }
+    GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                "encapsulate_for_dv 2\n");
     encapsulate_for_dv (sc.dvh->dv,
                         1,
                         &sc.dvh,
                         (const struct GNUNET_MessageHeader *) &sc.best[1],
                         &extract_box_cb,
                         &sc,
-                        RMO_NONE);
+                        RMO_NONE,
+                        GNUNET_NO);
     GNUNET_assert (NULL != sc.best->bpm);
     pm = sc.best->bpm;
   }
@@ -9227,6 +9333,11 @@ transmit_on_queue (void *cls)
        OPTIMIZE: Note that in the future this heuristic should likely
        be improved further (measure RTT stability, consider message
        urgency and size when delaying ACKs, etc.) */
+    GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                "Waiting %s for ACK\n",
+                GNUNET_STRINGS_relative_time_to_string (
+                  GNUNET_TIME_relative_multiply (
+                    queue->pd.aged_rtt, 4), GNUNET_NO));
     update_pm_next_attempt (pm,
                             GNUNET_TIME_relative_to_absolute (
                               GNUNET_TIME_relative_multiply 
(queue->pd.aged_rtt,
diff --git a/src/transport/test_transport_distance_vector_topo.conf 
b/src/transport/test_transport_distance_vector_topo.conf
new file mode 100644
index 000000000..ead3e0a0a
--- /dev/null
+++ b/src/transport/test_transport_distance_vector_topo.conf
@@ -0,0 +1,8 @@
+M:2
+N:2
+X:0
+T:libgnunet_test_transport_plugin_cmd_simple_send_dv
+R:1|{tcp_port:1}|{udp_port:0}
+R:2|{tcp_port:1}|{udp_port:0}
+P:1:1|{connect:{P:2:1:tcp}}
+P:2:1|{connect:{P:1:1:tcp}}
diff --git a/src/transport/test_transport_hmac_calculation.c 
b/src/transport/test_transport_hmac_calculation.c
deleted file mode 100644
index 59f7e3d90..000000000
--- a/src/transport/test_transport_hmac_calculation.c
+++ /dev/null
@@ -1,250 +0,0 @@
-/*
-     This file is part of GNUnet.
-     Copyright (C) 2002-2015 GNUnet e.V.
-
-     GNUnet is free software: you can redistribute it and/or modify it
-     under the terms of the GNU Affero General Public License as published
-     by the Free Software Foundation, either version 3 of the License,
-     or (at your option) any later version.
-
-     GNUnet is distributed in the hope that it will be useful, but
-     WITHOUT ANY WARRANTY; without even the implied warranty of
-     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-     Affero General Public License for more details.
-
-     You should have received a copy of the GNU Affero General Public License
-     along with this program.  If not, see <http://www.gnu.org/licenses/>.
-
-     SPDX-License-Identifier: AGPL3.0-or-later
-
- */
-/**
- * @file util/test_crypto_ecdh_eddsa.c
- * @brief testcase for ECC DH key exchange with EdDSA private keys.
- * @author Christian Grothoff
- * @author Bart Polot
- */
-#include "platform.h"
-#include "gnunet_util_lib.h"
-#include <gcrypt.h>
-
-
-/**
- * Structure of the key material used to encrypt backchannel messages.
- */
-struct DVKeyState
-{
-  /**
-   * State of our block cipher.
-   */
-  gcry_cipher_hd_t cipher;
-
-  /**
-   * Actual key material.
-   */
-  struct
-  {
-    /**
-     * Key used for HMAC calculations (via #GNUNET_CRYPTO_hmac()).
-     */
-    struct GNUNET_CRYPTO_AuthKey hmac_key;
-
-    /**
-     * Symmetric key to use for encryption.
-     */
-    char aes_key[256 / 8];
-
-    /**
-     * Counter value to use during setup.
-     */
-    char aes_ctr[128 / 8];
-  } material;
-};
-
-
-/**
- * Given the key material in @a km and the initialization vector
- * @a iv, setup the key material for the backchannel in @a key.
- *
- * @param km raw master secret
- * @param iv initialization vector
- * @param key[out] symmetric cipher and HMAC state to generate
- */
-static void
-dv_setup_key_state_from_km (const struct GNUNET_HashCode *km,
-                            const struct GNUNET_ShortHashCode *iv,
-                            struct DVKeyState *key)
-{
-  char *key_string;
-
-
-  /* must match #dh_key_derive_eph_pub */
-  GNUNET_assert (GNUNET_YES ==
-                 GNUNET_CRYPTO_kdf (&key->material,
-                                    sizeof(key->material),
-                                    "transport-backchannel-key",
-                                    strlen ("transport-backchannel-key"),
-                                    &km,
-                                    sizeof(km),
-                                    iv,
-                                    sizeof(*iv),
-                                    NULL));
-  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "Deriving backchannel key based on KM %s and IV %s\n",
-              GNUNET_h2s (km),
-              GNUNET_sh2s (iv));
-  GNUNET_assert (0 == gcry_cipher_open (&key->cipher,
-                                        GCRY_CIPHER_AES256 /* low level: go 
for speed */,
-                                        GCRY_CIPHER_MODE_CTR,
-                                        0 /* flags */));
-  GNUNET_assert (0 == gcry_cipher_setkey (key->cipher,
-                                          &key->material.aes_key,
-                                          sizeof(key->material.aes_key)));
-  gcry_cipher_setctr (key->cipher,
-                      &key->material.aes_ctr,
-                      sizeof(key->material.aes_ctr));
-  GNUNET_free (key_string);
-}
-
-
-/**
- * Do HMAC calculation for backchannel messages over @a data using key
- * material from @a key.
- *
- * @param key key material (from DH)
- * @param hmac[out] set to the HMAC
- * @param data data to perform HMAC calculation over
- * @param data_size number of bytes in @a data
- */
-static void
-dv_hmac (const struct DVKeyState *key,
-         struct GNUNET_HashCode *hmac,
-         const void *data,
-         size_t data_size)
-{
-  GNUNET_CRYPTO_hmac (&key->material.hmac_key, data, data_size, hmac);
-}
-
-
-/**
- * Clean up key material in @a key.
- *
- * @param key key material to clean up (memory must not be free'd!)
- */
-static void
-dv_key_clean (struct DVKeyState *key)
-{
-  gcry_cipher_close (key->cipher);
-  GNUNET_CRYPTO_zero_keys (&key->material, sizeof(key->material));
-}
-
-
-static int
-test_ecdh ()
-{
-  struct GNUNET_CRYPTO_EddsaPrivateKey priv_dsa;
-  struct GNUNET_CRYPTO_EcdhePrivateKey priv_ecdh;
-  struct GNUNET_CRYPTO_EddsaPublicKey id1;
-  struct GNUNET_CRYPTO_EcdhePublicKey id2;
-  struct GNUNET_HashCode dh[2];
-  struct DVKeyState *key[2];
-  struct GNUNET_ShortHashCode iv;
-  struct GNUNET_HashCode hmac[2];
-  char *enc = "test";
-  char *key_string_1;
-  char *key_string_2;
-
-
-  key[0] = GNUNET_new (struct DVKeyState);
-  key[1] = GNUNET_new (struct DVKeyState);
-  GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_NONCE,
-                              &iv,
-                              sizeof(iv));
-
-  /* Generate keys */
-  GNUNET_CRYPTO_eddsa_key_create (&priv_dsa);
-  GNUNET_CRYPTO_eddsa_key_get_public (&priv_dsa,
-                                      &id1);
-
-  GNUNET_CRYPTO_ecdhe_key_create (&priv_ecdh);
-  /* Extract public keys */
-  GNUNET_CRYPTO_ecdhe_key_get_public (&priv_ecdh,
-                                      &id2);
-  /* Do ECDH */
-  GNUNET_assert (GNUNET_OK == GNUNET_CRYPTO_eddsa_ecdh (&priv_dsa,
-                                                        &id2,
-                                                        &dh[0]));
-  GNUNET_assert (GNUNET_OK == GNUNET_CRYPTO_ecdh_eddsa (&priv_ecdh,
-                                                        &id1,
-                                                        &dh[1]));
-  /* Check that both DH results are equal. */
-  GNUNET_assert (0 == GNUNET_memcmp (&dh[0],
-                                     &dh[1]));
-
-  dv_setup_key_state_from_km (&dh[0],
-                              (const struct GNUNET_ShortHashCode *) &iv,
-                              key[0]);
-  dv_hmac ((const struct DVKeyState * ) key[0],
-           &hmac[0], enc,
-           sizeof(enc));
-
-  dv_setup_key_state_from_km (&dh[1],
-                              (const struct GNUNET_ShortHashCode *) &iv,
-                              key[1]);
-  dv_hmac ((const struct DVKeyState *) key[1],
-           &hmac[1],
-           enc,
-           sizeof(enc));
-
-  key_string_1 = GNUNET_STRINGS_data_to_string_alloc 
(&key[0]->material.hmac_key,
-                                                      sizeof (struct
-                                                            
GNUNET_CRYPTO_AuthKey));
-  key_string_2 = GNUNET_STRINGS_data_to_string_alloc 
(&key[1]->material.hmac_key,
-                                                      sizeof (struct 
GNUNET_CRYPTO_AuthKey));
-
-  if (0 != GNUNET_memcmp (key[0], key[1]) || 0 != GNUNET_memcmp (&hmac[0], 
&hmac[1]))
-  {
-  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "first key  %s\n",
-              key_string_1);
-  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "second key %s\n",
-              key_string_2);
-  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "first hmac  %s\n",
-              GNUNET_h2s (&hmac[0]));
-  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "second hmac %s\n",
-              GNUNET_h2s (&hmac[1]));
-  }
-  dv_key_clean (key[0]);
-  dv_key_clean (key[1]);
-  GNUNET_free (key_string_1);
-  GNUNET_free (key_string_2);
-
-  return 0;
-}
-
-
-int
-main (int argc, char *argv[])
-{
-  if (! gcry_check_version ("1.6.0"))
-  {
-    fprintf (stderr,
-             _ (
-               "libgcrypt has not the expected version (version %s is 
required).\n"),
-             "1.6.0");
-    return 0;
-  }
-  if (getenv ("GNUNET_GCRYPT_DEBUG"))
-    gcry_control (GCRYCTL_SET_DEBUG_FLAGS, 1u, 0);
-  GNUNET_log_setup ("test-transport-hmac-calculation", "DEBUG", NULL);
-  if (0 != test_ecdh ())
-    return 1;
-  
-  return 0;
-}
-
-
-/* end of test_crypto_ecdh_eddsa.c */
diff --git a/src/transport/test_transport_plugin_cmd_simple_send_dv.c 
b/src/transport/test_transport_plugin_cmd_simple_send_dv.c
index e73e5a0b2..167120e2b 100644
--- a/src/transport/test_transport_plugin_cmd_simple_send_dv.c
+++ b/src/transport/test_transport_plugin_cmd_simple_send_dv.c
@@ -64,6 +64,12 @@ struct TestState
    * The complete topology information.
    */
   struct GNUNET_TESTING_NetjailTopology *topology;
+
+  /**
+   * The number of messages received.
+   */
+  unsigned int number_received;
+
 };
 
 static struct GNUNET_TESTING_Command block_send;
@@ -74,6 +80,8 @@ static struct GNUNET_TESTING_Command connect_peers;
 
 static struct GNUNET_TESTING_Command local_prepared;
 
+static struct GNUNET_TESTING_Command start_peer;
+
 /**
  * Function called to check a message of type 
GNUNET_TRANSPORT_TESTING_SIMPLE_MTYPE being
  * received.
@@ -83,6 +91,7 @@ static int
 check_test (void *cls,
             const struct GNUNET_TRANSPORT_TESTING_TestMessage *message)
 {
+  GNUNET_assert (NULL != cls);
   return GNUNET_OK;
 }
 
@@ -96,17 +105,52 @@ static void
 handle_test (void *cls,
              const struct GNUNET_TRANSPORT_TESTING_TestMessage *message)
 {
-  const struct GNUNET_TESTING_AsyncContext *ac;
+  struct TestState *ts = cls;
+  const struct GNUNET_TESTING_AsyncContext *ac_block;
+  const struct GNUNET_TESTING_AsyncContext *ac_start;
+  const struct GNUNET_TESTING_Command *cmd;
+  const struct GNUNET_CONTAINER_MultiShortmap *connected_peers_map;
+  unsigned int connected;
+  struct BlockState *bs;
+
+
 
+  GNUNET_TRANSPORT_get_trait_connected_peers_map (&start_peer,
+                                                  &connected_peers_map);
+
+  connected = GNUNET_CONTAINER_multishortmap_size (
+    connected_peers_map);
+
+  ts->number_received++;
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-              "Received test message\n");
+              "Received %u test message(s) from %u connected peer(s)\n",
+              ts->number_received,
+              connected);
+
   GNUNET_TESTING_get_trait_async_context (&block_receive,
-                                          &ac);
-  GNUNET_assert  (NULL != ac);
-  if (NULL == ac->cont)
-    GNUNET_TESTING_async_fail ((struct GNUNET_TESTING_AsyncContext *) ac);
-  else
-    GNUNET_TESTING_async_finish ((struct GNUNET_TESTING_AsyncContext *) ac);
+                                          &ac_block);
+
+  if ( connected == ts->number_received)
+  {
+    if (NULL != ac_block->is)
+    {
+      GNUNET_assert  (NULL != ac_block);
+      if (NULL == ac_block->cont)
+        GNUNET_TESTING_async_fail ((struct
+                                    GNUNET_TESTING_AsyncContext *) ac_block);
+      else
+        GNUNET_TESTING_async_finish ((struct
+                                      GNUNET_TESTING_AsyncContext *) ac_block);
+    }
+    else
+    {
+      GNUNET_TESTING_get_trait_block_state (
+        &block_receive,
+        (const struct BlockState  **) &bs);
+      bs->asynchronous_finish = GNUNET_YES;
+    }
+
+  }
 }
 
 
@@ -232,8 +276,17 @@ start_testcase (TESTING_CMD_HELPER_write_cb write_message, 
char *router_ip,
   unsigned int num;
   struct TestState *ts = GNUNET_new (struct TestState);
   struct GNUNET_TESTING_NetjailTopology *topology;
+  struct GNUNET_MQ_MessageHandler handlers[] = {
+    GNUNET_MQ_hd_var_size (test,
+                           GNUNET_TRANSPORT_TESTING_SIMPLE_MTYPE,
+                           struct GNUNET_TRANSPORT_TESTING_TestMessage,
+                           ts),
+    GNUNET_MQ_handler_end ()
+  };
 
-
+  LOG (GNUNET_ERROR_TYPE_DEBUG,
+       "number_received %u\n",
+       ts->number_received);
 
   if (GNUNET_YES == *read_file)
   {
@@ -258,12 +311,13 @@ start_testcase (TESTING_CMD_HELPER_write_cb 
write_message, char *router_ip,
   block_send = GNUNET_TESTING_cmd_block_until_external_trigger ("block");
   block_receive = GNUNET_TESTING_cmd_block_until_external_trigger (
     "block-receive");
-  connect_peers = GNUNET_TRANSPORT_cmd_connect_peers ("connect-peers",
-                                                      "start-peer",
-                                                      "system-create",
-                                                      num,
-                                                      topology,
-                                                      8);
+  connect_peers = GNUNET_TRANSPORT_cmd_connect_peers (
+    "connect-peers",
+    "start-peer",
+    "system-create",
+    num,
+    topology,
+    topology->additional_connects);
   local_prepared = GNUNET_TESTING_cmd_local_test_prepared (
     "local-test-prepared",
     write_message);
@@ -286,25 +340,18 @@ start_testcase (TESTING_CMD_HELPER_write_cb 
write_message, char *router_ip,
                    m,
                    n);
 
-  struct GNUNET_MQ_MessageHandler handlers[] = {
-    GNUNET_MQ_hd_var_size (test,
-                           GNUNET_TRANSPORT_TESTING_SIMPLE_MTYPE,
-                           struct GNUNET_TRANSPORT_TESTING_TestMessage,
-                           ts),
-    GNUNET_MQ_handler_end ()
-  };
-
+  start_peer = GNUNET_TRANSPORT_cmd_start_peer ("start-peer",
+                                                "system-create",
+                                                num,
+                                                node_ip,
+                                                handlers,
+                                                ts->cfgname,
+                                                notify_connect,
+                                                GNUNET_YES);
   struct GNUNET_TESTING_Command commands[] = {
     GNUNET_TESTING_cmd_system_create ("system-create",
                                       ts->testdir),
-    GNUNET_TRANSPORT_cmd_start_peer ("start-peer",
-                                     "system-create",
-                                     num,
-                                     node_ip,
-                                     handlers,
-                                     ts->cfgname,
-                                     notify_connect,
-                                     GNUNET_YES),
+    start_peer,
     GNUNET_TESTING_cmd_send_peer_ready ("send-peer-ready",
                                         write_message),
     block_send,
diff --git a/src/transport/test_transport_simple_send_dv_circle.sh 
b/src/transport/test_transport_simple_send_dv_circle.sh
new file mode 100755
index 000000000..de16df356
--- /dev/null
+++ b/src/transport/test_transport_simple_send_dv_circle.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+if ! [ -d "/run/netns" ]; then
+    echo You have to create the directory /run/netns.
+fi
+if  [ "$(cat /proc/sys/kernel/unprivileged_userns_clone)" == 1 ]; then
+    # exec unshare -r -nmU bash -c "mount -t tmpfs --make-rshared tmpfs 
/run/netns; valgrind --leak-check=full --track-origins=yes --trace-children=yes 
--trace-children-skip=/usr/bin/awk,/usr/bin/cut,/usr/bin/seq,/sbin/ip/sed/bash  
./test_transport_start_with_config test_transport_distance_vector_topo.conf"
+    exec unshare -r -nmU bash -c "mount -t tmpfs --make-rshared tmpfs 
/run/netns; ./test_transport_start_with_config 
test_transport_distance_vector_circle_topo.conf"
+    #./test_transport_start_with_config 
test_transport_distance_vector_circle_topo.conf
+else
+    echo -e "Error during test setup: The kernel parameter 
kernel.unprivileged_userns_clone has to be set to 1! One has to execute\n\n 
sysctl kernel.unprivileged_userns_clone=1\n"
+    exit 78
+fi
diff --git a/src/transport/transport-testing-cmds.h 
b/src/transport/transport-testing-cmds.h
index af6f47962..5a3fb22d6 100644
--- a/src/transport/transport-testing-cmds.h
+++ b/src/transport/transport-testing-cmds.h
@@ -187,7 +187,7 @@ struct StartPeerState
   /**
    * Flag indicating, if udp broadcast should be switched on.
    */
-  unsigned int broadcast;
+  enum GNUNET_GenericReturnValue broadcast;
 };
 
 
@@ -337,7 +337,8 @@ GNUNET_TRANSPORT_cmd_backchannel_check (const char *label,
   op (hello, const char) \
   op (application_handle, const struct GNUNET_TRANSPORT_ApplicationHandle) \
   op (connect_peer_state, const struct ConnectPeersState) \
-  op (state, const struct StartPeerState)
+  op (state, const struct StartPeerState) \
+  op (broadcast, const enum GNUNET_GenericReturnValue)
 
 GNUNET_TRANSPORT_SIMPLE_TRAITS (GNUNET_TRANSPORT_MAKE_DECL_SIMPLE_TRAIT)
 
diff --git a/src/transport/transport_api_cmd_connecting_peers.c 
b/src/transport/transport_api_cmd_connecting_peers.c
index fc925675d..296a98147 100644
--- a/src/transport/transport_api_cmd_connecting_peers.c
+++ b/src/transport/transport_api_cmd_connecting_peers.c
@@ -54,17 +54,25 @@ connect_peers_run (void *cls,
   const struct GNUNET_TRANSPORT_ApplicationHandle *ah;
   struct GNUNET_PeerIdentity *peer;
   char *addr;
+  char *addr_and_port;
   enum GNUNET_NetworkType nt = 0;
   uint32_t num;
   struct GNUNET_TESTING_NodeConnection *pos_connection;
   struct GNUNET_TESTING_AddressPrefix *pos_prefix;
   unsigned int con_num = 0;
+  const enum GNUNET_GenericReturnValue *broadcast;
+  const enum GNUNET_GenericReturnValue *broadcast_pointer;
+  char *port;
 
   cps->is = is;
   peer1_cmd = GNUNET_TESTING_interpreter_lookup_command (is,
                                                          
cps->start_peer_label);
   GNUNET_TRANSPORT_get_trait_application_handle (peer1_cmd,
                                                  &ah);
+  GNUNET_TRANSPORT_get_trait_broadcast (peer1_cmd,
+                                        &broadcast);
+
+  // broadcast = *broadcast_pointer;
 
   system_cmd = GNUNET_TESTING_interpreter_lookup_command (is,
                                                           cps->create_label);
@@ -93,19 +101,38 @@ connect_peers_run (void *cls,
                                          pos_prefix->address_prefix);
       if (NULL != addr)
       {
+        if (0 == GNUNET_memcmp (pos_prefix->address_prefix, "udp"))
+          GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                      "validating memcmp\n");
+        if (GNUNET_YES == *broadcast)
+          GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+                      "validating broadcast\n");
+        if ((0 == GNUNET_memcmp (pos_prefix->address_prefix, "udp")) &&
+            (GNUNET_YES == *broadcast) )
+          GNUNET_asprintf (&addr_and_port,
+                           "%s:2086",
+                           addr);
+        else
+          GNUNET_asprintf (&addr_and_port,
+                           "%s:60002",
+                           addr);
         peer = GNUNET_TESTING_get_pub_key (num, tl_system);
         GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
-                    "validating peer number %u with identity %s\n",
+                    "validating peer number %u with identity %s and address %s 
%u %s\n",
                     num,
-                    GNUNET_i2s (peer));
+                    GNUNET_i2s (peer),
+                    addr_and_port,
+                    *broadcast,
+                    pos_prefix->address_prefix);
         GNUNET_TRANSPORT_application_validate ((struct
                                                 
GNUNET_TRANSPORT_ApplicationHandle
                                                 *) ah,
                                                peer,
                                                nt,
-                                               addr);
+                                               addr_and_port);
         GNUNET_free (peer);
         GNUNET_free (addr);
+        GNUNET_free (addr_and_port);
       }
     }
   }
@@ -146,6 +173,12 @@ notify_connect (struct GNUNET_TESTING_Interpreter *is,
   if (cps->con_num == con_num)
     cps->additional_connects_notified++;
 
+  GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+              "con_num: %u add: %u num_notified: %u add_notified: %u\n",
+              cps->con_num,
+              cps->additional_connects,
+              cps->con_num_notified,
+              cps->additional_connects_notified);
   if (cps->con_num + cps->additional_connects == cps->con_num_notified
       + cps->additional_connects_notified)
   {
diff --git a/src/transport/transport_api_cmd_start_peer.c 
b/src/transport/transport_api_cmd_start_peer.c
index be2ea25b4..e305e24e1 100644
--- a/src/transport/transport_api_cmd_start_peer.c
+++ b/src/transport/transport_api_cmd_start_peer.c
@@ -124,7 +124,7 @@ notify_connect (void *cls,
   struct GNUNET_HashCode hc;
   struct GNUNET_CRYPTO_EddsaPublicKey public_key = peer->public_key;
 
-  void *ret = NULL;
+  void *ret = sps->handlers;
 
   LOG (GNUNET_ERROR_TYPE_DEBUG,
        "This Peer %s \n",
@@ -150,7 +150,6 @@ notify_connect (void *cls,
   sps->notify_connect (sps->ac.is,
                        peer);
 
-  // TODO what does the handler function need?
   return ret;
 }
 
@@ -418,6 +417,7 @@ start_peer_traits (void *cls,
     GNUNET_TRANSPORT_make_trait_hello ((const void *) hello),
     GNUNET_TRANSPORT_make_trait_hello_size ((const void *) hello_size),
     GNUNET_TRANSPORT_make_trait_state ((const void *) sps),
+    GNUNET_TRANSPORT_make_trait_broadcast ((const void *) &sps->broadcast),
     GNUNET_TESTING_trait_end ()
   };
 

-- 
To stop receiving notification emails like this one, please contact
gnunet@gnunet.org.



reply via email to

[Prev in Thread] Current Thread [Next in Thread]