- add rekey state
authorBart Polot <bart@net.in.tum.de>
Tue, 17 Jun 2014 12:13:33 +0000 (12:13 +0000)
committerBart Polot <bart@net.in.tum.de>
Tue, 17 Jun 2014 12:13:33 +0000 (12:13 +0000)
src/cadet/gnunet-service-cadet_tunnel.c
src/cadet/gnunet-service-cadet_tunnel.h

index 227c29fd6c488706e69de2620cb2d91170c3e5ce..6bceb5dff4927f1bc0edd182f8cbbf8abf605e9e 100644 (file)
@@ -400,7 +400,9 @@ is_ready (struct CadetTunnel *t)
   int ready;
 
   GCT_debug (t, GNUNET_ERROR_TYPE_DEBUG);
-  ready = CADET_TUNNEL3_READY == t->cstate && CADET_TUNNEL3_KEY_OK == t->estate;
+  ready = CADET_TUNNEL3_READY == t->cstate
+          && (CADET_TUNNEL3_KEY_OK == t->estate
+              || CADET_TUNNEL3_KEY_REKEY == t->estate);
   ready = ready || GCT_is_loopback (t);
   return ready;
 }
@@ -1294,6 +1296,22 @@ rekey_tunnel (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
     LOG (GNUNET_ERROR_TYPE_DEBUG, "  new challenge for %s: %u\n",
          GCT_2s (t), t->kx_ctx->challenge);
   }
+  else
+  {
+    struct GNUNET_TIME_Relative duration;
+
+    duration = GNUNET_TIME_absolute_get_duration (t->kx_ctx->rekey_start_time);
+    LOG (GNUNET_ERROR_TYPE_DEBUG, " kx started %s ago\n",
+         GNUNET_STRINGS_relative_time_to_string (duration, GNUNET_YES));
+
+    // FIXME make duration of old keys configurable
+    if (duration.rel_value_us > GNUNET_TIME_UNIT_MINUTES.rel_value_us)
+    {
+      memset (&t->kx_ctx->d_key_old, 0, sizeof (t->kx_ctx->d_key_old));
+      memset (&t->kx_ctx->e_key_old, 0, sizeof (t->kx_ctx->e_key_old));
+      t->estate = CADET_TUNNEL3_KEY_PING;
+    }
+  }
 
   send_ephemeral (t);
 
@@ -1304,10 +1322,12 @@ rekey_tunnel (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
       break;
     case CADET_TUNNEL3_KEY_SENT:
       break;
-    case CADET_TUNNEL3_KEY_PING:
     case CADET_TUNNEL3_KEY_OK:
+      t->estate = CADET_TUNNEL3_KEY_REKEY;
+      /* fall-thru */
+    case CADET_TUNNEL3_KEY_PING:
+    case CADET_TUNNEL3_KEY_REKEY:
       send_ping (t);
-      t->estate = CADET_TUNNEL3_KEY_PING;
       break;
     default:
       LOG (GNUNET_ERROR_TYPE_DEBUG, "Unexpected state %u\n", t->estate);
@@ -1709,6 +1729,10 @@ handle_ephemeral (struct CadetTunnel *t,
   {
     t->peers_ephemeral_key = msg->ephemeral_key;
     create_keys (t);
+    if (CADET_TUNNEL3_KEY_OK == t->estate)
+    {
+      t->estate = CADET_TUNNEL3_KEY_REKEY;
+    }
   }
   if (CADET_TUNNEL3_KEY_SENT == t->estate)
   {
index 721167a76d95c2827436da4dd17058c256d7cc6f..84323d895f325f8acdfd1e189dd03ee2b5fa5bef 100644 (file)
@@ -90,7 +90,8 @@ enum CadetTunnelEState
   /**
    * New ephemeral key and ping sent, waiting for pong.
    * This means that we DO have the peer's ephemeral key, otherwise the
-   * state would be KEY_SENT.
+   * state would be KEY_SENT. We DO NOT have a valid session key (either no
+   * previous key or previous key expired).
    */
   CADET_TUNNEL3_KEY_PING,
 
@@ -98,6 +99,13 @@ enum CadetTunnelEState
    * Handshake completed: session key available.
    */
   CADET_TUNNEL3_KEY_OK,
+
+  /**
+   * New ephemeral key and ping sent, waiting for pong. Opposite to KEY_PING,
+   * we still have a valid session key and therefore we *can* still send
+   * traffic on the tunnel.
+   */
+  CADET_TUNNEL3_KEY_REKEY,
 };
 
 /**