- fix #3091
authorBart Polot <bart@net.in.tum.de>
Thu, 7 Nov 2013 16:24:46 +0000 (16:24 +0000)
committerBart Polot <bart@net.in.tum.de>
Thu, 7 Nov 2013 16:24:46 +0000 (16:24 +0000)
src/mesh/gnunet-service-mesh-enc.c
src/mesh/gnunet-service-mesh_channel.c
src/mesh/gnunet-service-mesh_channel.h
src/mesh/gnunet-service-mesh_local.c
src/mesh/gnunet-service-mesh_local.h
src/mesh/gnunet-service-mesh_tunnel.c
src/mesh/mesh_api_enc.c
src/mesh/mesh_protocol_enc.h

index 3d1238a3653dfaa3c8c24eef1459ff0cd41ba491..f5e365e1cec9e8b336727540995902990a65460a 100644 (file)
 #include "gnunet-service-mesh_peer.h"
 
 
-/******************************************************************************/
-/************************      DATA STRUCTURES     ****************************/
-/******************************************************************************/
-
-
-
-/******************************************************************************/
-/************************      DEBUG FUNCTIONS     ****************************/
-/******************************************************************************/
-
-
 /******************************************************************************/
 /***********************      GLOBAL VARIABLES     ****************************/
 /******************************************************************************/
@@ -96,33 +85,10 @@ struct GNUNET_PeerIdentity my_full_id;
 static struct GNUNET_CRYPTO_EddsaPrivateKey *my_private_key;
 
 
-/******************************************************************************/
-/***********************         DECLARATIONS        **************************/
-/******************************************************************************/
-
-
-/******************************************************************************/
-/******************      GENERAL HELPER FUNCTIONS      ************************/
-/******************************************************************************/
-
-
-
-/******************************************************************************/
-/****************      MESH NETWORK HANDLER HELPERS     ***********************/
-/******************************************************************************/
-
-
-
-/******************************************************************************/
-/********************      MESH NETWORK HANDLERS     **************************/
-/******************************************************************************/
-
-
 /******************************************************************************/
 /************************      MAIN FUNCTIONS      ****************************/
 /******************************************************************************/
 
-
 /**
  * Task run during shutdown.
  *
index 4b5baa528d777313eaa62a089fe81d60dee85194..e7fc0323b9a1ed3e5956c154ee3c5b2151ce2902 100644 (file)
@@ -481,6 +481,23 @@ send_client_ack (struct MeshChannel *ch, int fwd)
 }
 
 
+/**
+ * Notify the root that the destination rejected the channel.
+ *
+ * @param ch Rejected channel.
+ */
+static void
+send_client_nack (struct MeshChannel *ch)
+{
+  if (NULL == ch->root)
+  {
+    GNUNET_break (0);
+    return;
+  }
+  GML_send_nack (ch->root, ch->lid_root);
+}
+
+
 /**
  * Destroy all reliable messages queued for a channel,
  * during a channel destruction.
@@ -714,6 +731,27 @@ channel_send_ack (struct MeshChannel *ch, int fwd)
 }
 
 
+/**
+ * Notify that a channel create didn't succeed.
+ *
+ * @param ch The channel to reject.
+ */
+static void
+channel_send_nack (struct MeshChannel *ch)
+{
+  struct GNUNET_MESH_ChannelManage msg;
+
+  msg.header.size = htons (sizeof (msg));
+  msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_CHANNEL_NACK);
+  LOG (GNUNET_ERROR_TYPE_DEBUG,
+       "  sending channel NACK for channel %s\n",
+       GMCH_2s (ch));
+
+  msg.chid = htonl (ch->gid);
+  GMCH_send_prebuilt_message (&msg.header, ch, GNUNET_NO);
+}
+
+
 /**
  * Channel was ACK'd by remote peer, mark as ready and cancel retransmission.
  *
@@ -941,6 +979,10 @@ handle_loopback (struct MeshChannel *ch,
                        fwd);
       break;
 
+    case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_NACK:
+      GMCH_handle_nack (ch);
+      break;
+
     case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_DESTROY:
       GMCH_handle_destroy (ch,
                            (struct GNUNET_MESH_ChannelManage *) msgh,
@@ -1692,7 +1734,15 @@ GMCH_handle_create (struct MeshTunnel3 *t,
   {
     /* TODO send reject */
     LOG (GNUNET_ERROR_TYPE_DEBUG, "  no client has port registered\n");
-    channel_destroy (ch);
+    if (is_loopback (ch))
+    {
+      channel_send_nack (ch);
+    }
+    else
+    {
+      channel_send_nack (ch);
+      channel_destroy (ch);
+    }
     return NULL;
   }
   else
@@ -1713,6 +1763,21 @@ GMCH_handle_create (struct MeshTunnel3 *t,
 }
 
 
+/**
+ * Handler for channel NACK messages.
+ *
+ * NACK messages always go dest -> root, no need for 'fwd' or 'msg' parameter.
+ *
+ * @param ch Channel.
+ */
+void
+GMCH_handle_nack (struct MeshChannel *ch)
+{
+  send_client_nack (ch);
+  channel_destroy (ch);
+}
+
+
 /**
  * Handler for channel ack messages.
  *
index 66fe333408e3efd7eb556b5ebc9451d76ee02edb..e718b315c2f3c8223bf2d8004b80e5580e7a1b56 100644 (file)
@@ -277,6 +277,16 @@ struct MeshChannel *
 GMCH_handle_create (struct MeshTunnel3 *t,
                     const struct GNUNET_MESH_ChannelCreate *msg);
 
+/**
+ * Handler for channel NACK messages.
+ *
+ * NACK messages always go dest -> root, no need for 'fwd' or 'msg' parameter.
+ *
+ * @param ch Channel.
+ */
+void
+GMCH_handle_nack (struct MeshChannel *ch);
+
 /**
  * Handler for channel ack messages.
  *
index 78a63956f65ae961504869c9ae0da941534ff42f..9430fbefac211797677618fe17fc581b80f3d92b 100644 (file)
@@ -946,6 +946,32 @@ GML_send_ack (struct MeshClient *c, MESH_ChannelNumber id)
 }
 
 
+/**
+ * Build a local channel NACK message and send it to a local client.
+ *
+ * @param c Client to whom send the NACK.
+ * @param id Channel ID to use
+ */
+void
+GML_send_nack (struct MeshClient *c, MESH_ChannelNumber id)
+{
+  struct GNUNET_MESH_LocalAck msg;
+
+  LOG (GNUNET_ERROR_TYPE_DEBUG,
+              "send local nack on %X towards %p\n",
+              id, c);
+
+  msg.header.size = htons (sizeof (msg));
+  msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_NACK);
+  msg.channel_id = htonl (id);
+  GNUNET_SERVER_notification_context_unicast (nc,
+                                              c->handle,
+                                              &msg.header,
+                                              GNUNET_NO);
+
+}
+
+
 /**
  * Notify the client that a new incoming channel was created.
  *
index 0c07fedfef20b485a6acbb66b4fb9fea5aa603cf..a78ef7af2f1234d76d1c93a67737250c35f8c7e0 100644 (file)
@@ -159,6 +159,15 @@ GML_client_delete_channel (struct MeshClient *c,
 void
 GML_send_ack (struct MeshClient *c, MESH_ChannelNumber id);
 
+/**
+ * Build a local channel NACK message and send it to a local client.
+ *
+ * @param c Client to whom send the NACK.
+ * @param id Channel ID to use
+ */
+void
+GML_send_nack (struct MeshClient *c, MESH_ChannelNumber id);
+
 /**
  * Notify the appropriate client that a new incoming channel was created.
  *
index 977908f35fc8ca4c3c0494ba6edf49808c400bcc..07c907c6cf88d299762dea70f9165e824db28044 100644 (file)
@@ -838,7 +838,7 @@ rekey (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
  */
-void
+static void
 handle_data (struct MeshTunnel3 *t,
              const struct GNUNET_MESH_Data *msg,
              int fwd)
@@ -888,7 +888,7 @@ handle_data (struct MeshTunnel3 *t,
  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
  */
-void
+static void
 handle_data_ack (struct MeshTunnel3 *t,
                  const struct GNUNET_MESH_DataACK *msg,
                  int fwd)
@@ -925,7 +925,7 @@ handle_data_ack (struct MeshTunnel3 *t,
  * @param t Tunnel on which the data came.
  * @param msg Data message.
  */
-void
+static void
 handle_ch_create (struct MeshTunnel3 *t,
                   const struct GNUNET_MESH_ChannelCreate *msg)
 {
@@ -955,6 +955,43 @@ handle_ch_create (struct MeshTunnel3 *t,
 }
 
 
+
+/**
+ * Handle channel NACK.
+ *
+ * @param t Tunnel on which the data came.
+ * @param msg Data message.
+ */
+static void
+handle_ch_nack (struct MeshTunnel3 *t,
+                const struct GNUNET_MESH_ChannelManage *msg)
+{
+  struct MeshChannel *ch;
+  size_t size;
+
+  /* Check size */
+  size = ntohs (msg->header.size);
+  if (size != sizeof (struct GNUNET_MESH_ChannelManage))
+  {
+    GNUNET_break (0);
+    return;
+  }
+
+  /* Check channel */
+  ch = GMT_get_channel (t, ntohl (msg->chid));
+  if (NULL != ch && ! GMT_is_loopback (t))
+  {
+    GNUNET_STATISTICS_update (stats, "# channel NACK on unknown channel",
+                              1, GNUNET_NO);
+    LOG (GNUNET_ERROR_TYPE_DEBUG, "WARNING channel %u unknown\n",
+         ntohl (msg->chid));
+    return;
+  }
+
+  GMCH_handle_nack (ch);
+}
+
+
 /**
  * Handle a CHANNEL ACK (SYNACK/ACK).
  *
@@ -965,7 +1002,7 @@ handle_ch_create (struct MeshTunnel3 *t,
  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
  */
-void
+static void
 handle_ch_ack (struct MeshTunnel3 *t,
                const struct GNUNET_MESH_ChannelManage *msg,
                int fwd)
@@ -1007,7 +1044,7 @@ handle_ch_ack (struct MeshTunnel3 *t,
  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
  */
-void
+static void
 handle_ch_destroy (struct MeshTunnel3 *t,
                    const struct GNUNET_MESH_ChannelManage *msg,
                    int fwd)
@@ -1169,6 +1206,11 @@ handle_decrypted (struct MeshTunnel3 *t,
                         (struct GNUNET_MESH_ChannelCreate *) msgh);
       break;
 
+    case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_NACK:
+      handle_ch_nack (t,
+                      (struct GNUNET_MESH_ChannelManage *) msgh);
+      break;
+
     case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_ACK:
       handle_ch_ack (t,
                      (struct GNUNET_MESH_ChannelManage *) msgh,
index 8f4d42fd38e2f1a40027935c64cfba28152fbe2b..e1eb697404d499789f01a24e0af06a7cef6eb34d 100644 (file)
@@ -486,7 +486,7 @@ destroy_channel (struct GNUNET_MESH_Channel *ch, int call_cleaner)
       continue;
     /* Clients should have aborted their requests already.
      * Management traffic should be ok, as clients can't cancel that */
-    GNUNET_break (GNUNET_NO == th_is_payload(th));
+    GNUNET_break (GNUNET_NO == th_is_payload (th));
     GNUNET_CONTAINER_DLL_remove (h->th_head, h->th_tail, th);
 
     /* clean up request */
@@ -966,37 +966,37 @@ process_ack (struct GNUNET_MESH_Handle *h,
  * @param h Mesh handle.
  * @param message Message itself.
  */
-static void
-process_get_channels (struct GNUNET_MESH_Handle *h,
-                     const struct GNUNET_MessageHeader *message)
-{
-  struct GNUNET_MESH_LocalMonitor *msg;
-
-  GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Get Channels messasge received\n");
-
-  if (NULL == h->channels_cb)
-  {
-    GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "  ignored\n");
-    return;
-  }
-
-  msg = (struct GNUNET_MESH_LocalMonitor *) message;
-  if (ntohs (message->size) !=
-      (sizeof (struct GNUNET_MESH_LocalMonitor) +
-       sizeof (struct GNUNET_PeerIdentity)))
-  {
-    GNUNET_break_op (0);
-    GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
-                "Get channels message: size %hu - expected %u\n",
-                ntohs (message->size),
-                sizeof (struct GNUNET_MESH_LocalMonitor));
-    return;
-  }
-  h->channels_cb (h->channels_cls,
-                  ntohl (msg->channel_id),
-                  &msg->owner,
-                  &msg->destination);
-}
+// static void
+// process_get_channels (struct GNUNET_MESH_Handle *h,
+//                      const struct GNUNET_MessageHeader *message)
+// {
+//   struct GNUNET_MESH_LocalMonitor *msg;
+// 
+//   GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Get Channels messasge received\n");
+// 
+//   if (NULL == h->channels_cb)
+//   {
+//     GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "  ignored\n");
+//     return;
+//   }
+// 
+//   msg = (struct GNUNET_MESH_LocalMonitor *) message;
+//   if (ntohs (message->size) !=
+//       (sizeof (struct GNUNET_MESH_LocalMonitor) +
+//        sizeof (struct GNUNET_PeerIdentity)))
+//   {
+//     GNUNET_break_op (0);
+//     GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+//                 "Get channels message: size %hu - expected %u\n",
+//                 ntohs (message->size),
+//                 sizeof (struct GNUNET_MESH_LocalMonitor));
+//     return;
+//   }
+//   h->channels_cb (h->channels_cls,
+//                   ntohl (msg->channel_id),
+//                   &msg->owner,
+//                   &msg->destination);
+// }
 
 
 
@@ -1006,43 +1006,43 @@ process_get_channels (struct GNUNET_MESH_Handle *h,
  * @param h Mesh handle.
  * @param message Message itself.
  */
-static void
-process_show_channel (struct GNUNET_MESH_Handle *h,
-                     const struct GNUNET_MessageHeader *message)
-{
-  struct GNUNET_MESH_LocalMonitor *msg;
-  size_t esize;
-
-  GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Show Channel messasge received\n");
-
-  if (NULL == h->channel_cb)
-  {
-    GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "  ignored\n");
-    return;
-  }
-
-  /* Verify message sanity */
-  msg = (struct GNUNET_MESH_LocalMonitor *) message;
-  esize = sizeof (struct GNUNET_MESH_LocalMonitor);
-  if (ntohs (message->size) != esize)
-  {
-    GNUNET_break_op (0);
-    GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
-                "Show channel message: size %hu - expected %u\n",
-                ntohs (message->size),
-                esize);
-
-    h->channel_cb (h->channel_cls, NULL, NULL);
-    h->channel_cb = NULL;
-    h->channel_cls = NULL;
-
-    return;
-  }
-
-  h->channel_cb (h->channel_cls,
-                 &msg->destination,
-                 &msg->owner);
-}
+// static void
+// process_show_channel (struct GNUNET_MESH_Handle *h,
+//                      const struct GNUNET_MessageHeader *message)
+// {
+//   struct GNUNET_MESH_LocalMonitor *msg;
+//   size_t esize;
+// 
+//   GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Show Channel messasge received\n");
+// 
+//   if (NULL == h->channel_cb)
+//   {
+//     GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "  ignored\n");
+//     return;
+//   }
+// 
+//   /* Verify message sanity */
+//   msg = (struct GNUNET_MESH_LocalMonitor *) message;
+//   esize = sizeof (struct GNUNET_MESH_LocalMonitor);
+//   if (ntohs (message->size) != esize)
+//   {
+//     GNUNET_break_op (0);
+//     GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+//                 "Show channel message: size %hu - expected %u\n",
+//                 ntohs (message->size),
+//                 esize);
+// 
+//     h->channel_cb (h->channel_cls, NULL, NULL);
+//     h->channel_cb = NULL;
+//     h->channel_cls = NULL;
+// 
+//     return;
+//   }
+// 
+//   h->channel_cb (h->channel_cls,
+//                  &msg->destination,
+//                  &msg->owner);
+// }
 
 
 /**
@@ -1076,21 +1076,21 @@ msg_received (void *cls, const struct GNUNET_MessageHeader *msg)
     break;
     /* Notify of a channel disconnection */
   case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_DESTROY:
+  case GNUNET_MESSAGE_TYPE_MESH_LOCAL_NACK:
     process_channel_destroy (h, (struct GNUNET_MESH_ChannelMessage *) msg);
     break;
-    /* Notify of a new data packet in the channel */
   case GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA:
     process_incoming_data (h, msg);
     break;
   case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK:
     process_ack (h, msg);
     break;
-  case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_CHANNELS:
-    process_get_channels (h, msg);
-    break;
-  case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_CHANNEL:
-    process_show_channel (h, msg);
-    break;
+//   case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_CHANNELS: DEPRECATED
+//     process_get_channels (h, msg);
+//     break;
+//   case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_CHANNEL: DEPRECATED
+//     process_show_channel (h, msg);
+//     break;
   default:
     /* We shouldn't get any other packages, log and ignore */
     LOG (GNUNET_ERROR_TYPE_WARNING,
index 2f834642ca42cee4da898283626901b034b89713..aa26a6237418a1d9f4f0901c50a14f7875ef39ee 100644 (file)
@@ -287,7 +287,7 @@ struct GNUNET_MESH_ChannelCreate
 struct GNUNET_MESH_ChannelManage
 {
   /**
-   * Type: GNUNET_MESSAGE_TYPE_MESH_CHANNEL_{ACK|DESTROY}
+   * Type: GNUNET_MESSAGE_TYPE_MESH_CHANNEL_{ACK|NACK|DESTROY}
    */
   struct GNUNET_MessageHeader header;