- initiate retransmit timer only after message has been sent
[oweals/gnunet.git] / src / mesh / gnunet-service-mesh_channel.c
1 /*
2      This file is part of GNUnet.
3      (C) 2013 Christian Grothoff (and other contributing authors)
4
5      GNUnet is free software; you can redistribute it and/or modify
6      it under the terms of the GNU General Public License as published
7      by the Free Software Foundation; either version 3, or (at your
8      option) any later version.
9
10      GNUnet is distributed in the hope that it will be useful, but
11      WITHOUT ANY WARRANTY; without even the implied warranty of
12      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13      General Public License for more details.
14
15      You should have received a copy of the GNU General Public License
16      along with GNUnet; see the file COPYING.  If not, write to the
17      Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18      Boston, MA 02111-1307, USA.
19 */
20
21
22 #include "platform.h"
23 #include "gnunet_util_lib.h"
24
25 #include "gnunet_statistics_service.h"
26
27 #include "mesh.h"
28 #include "mesh_protocol.h"
29
30 #include "gnunet-service-mesh_channel.h"
31 #include "gnunet-service-mesh_local.h"
32 #include "gnunet-service-mesh_tunnel.h"
33 #include "gnunet-service-mesh_peer.h"
34
35 #define LOG(level, ...) GNUNET_log_from(level,"mesh-chn",__VA_ARGS__)
36
37 #define MESH_RETRANSMIT_TIME    GNUNET_TIME_UNIT_SECONDS
38 #define MESH_RETRANSMIT_MARGIN  4
39
40
41 /**
42  * All the states a connection can be in.
43  */
44 enum MeshChannelState
45 {
46   /**
47    * Uninitialized status, should never appear in operation.
48    */
49   MESH_CHANNEL_NEW,
50
51   /**
52    * Connection create message sent, waiting for ACK.
53    */
54   MESH_CHANNEL_SENT,
55
56   /**
57    * Connection confirmed, ready to carry traffic.
58    */
59   MESH_CHANNEL_READY,
60 };
61
62
63
64 /**
65  * Info needed to retry a message in case it gets lost.
66  */
67 struct MeshReliableMessage
68 {
69     /**
70      * Double linked list, FIFO style
71      */
72   struct MeshReliableMessage    *next;
73   struct MeshReliableMessage    *prev;
74
75     /**
76      * Type of message (payload, channel management).
77      */
78   int16_t type;
79
80     /**
81      * Tunnel Reliability queue this message is in.
82      */
83   struct MeshChannelReliability  *rel;
84
85     /**
86      * ID of the message (ACK needed to free)
87      */
88   uint32_t                      mid;
89
90   /**
91    * Tunnel Queue.
92    */
93   struct MeshTunnel3Queue *q;
94
95     /**
96      * When was this message issued (to calculate ACK delay)
97      */
98   struct GNUNET_TIME_Absolute   timestamp;
99
100   /* struct GNUNET_MESH_Data with payload */
101 };
102
103
104 /**
105  * Info about the traffic state for a client in a channel.
106  */
107 struct MeshChannelReliability
108 {
109     /**
110      * Channel this is about.
111      */
112   struct MeshChannel *ch;
113
114     /**
115      * DLL of messages sent and not yet ACK'd.
116      */
117   struct MeshReliableMessage        *head_sent;
118   struct MeshReliableMessage        *tail_sent;
119
120     /**
121      * DLL of messages received out of order.
122      */
123   struct MeshReliableMessage        *head_recv;
124   struct MeshReliableMessage        *tail_recv;
125
126     /**
127      * Messages received.
128      */
129   unsigned int                      n_recv;
130
131     /**
132      * Next MID to use for outgoing traffic.
133      */
134   uint32_t                          mid_send;
135
136     /**
137      * Next MID expected for incoming traffic.
138      */
139   uint32_t                          mid_recv;
140
141     /**
142      * Can we send data to the client?
143      */
144   int                               client_ready;
145
146   /**
147    * Can the client send data to us?
148    */
149   int                               client_allowed;
150
151     /**
152      * Task to resend/poll in case no ACK is received.
153      */
154   GNUNET_SCHEDULER_TaskIdentifier   retry_task;
155
156     /**
157      * Counter for exponential backoff.
158      */
159   struct GNUNET_TIME_Relative       retry_timer;
160
161     /**
162      * How long does it usually take to get an ACK.
163      */
164   struct GNUNET_TIME_Relative       expected_delay;
165 };
166
167
168 /**
169  * Struct containing all information regarding a channel to a remote client.
170  */
171 struct MeshChannel
172 {
173     /**
174      * Tunnel this channel is in.
175      */
176   struct MeshTunnel3 *t;
177
178     /**
179      * Destination port of the channel.
180      */
181   uint32_t port;
182
183     /**
184      * Global channel number ( < GNUNET_MESH_LOCAL_CHANNEL_ID_CLI)
185      */
186   MESH_ChannelNumber gid;
187
188     /**
189      * Local tunnel number for root (owner) client.
190      * ( >= GNUNET_MESH_LOCAL_CHANNEL_ID_CLI or 0 )
191      */
192   MESH_ChannelNumber lid_root;
193
194     /**
195      * Local tunnel number for local destination clients (incoming number)
196      * ( >= GNUNET_MESH_LOCAL_CHANNEL_ID_SERV or 0).
197      */
198   MESH_ChannelNumber lid_dest;
199
200     /**
201      * Channel state.
202      */
203   enum MeshChannelState state;
204
205     /**
206      * Is the tunnel bufferless (minimum latency)?
207      */
208   int nobuffer;
209
210     /**
211      * Is the tunnel reliable?
212      */
213   int reliable;
214
215     /**
216      * Last time the channel was used
217      */
218   struct GNUNET_TIME_Absolute timestamp;
219
220     /**
221      * Client owner of the tunnel, if any
222      */
223   struct MeshClient *root;
224
225     /**
226      * Client destination of the tunnel, if any.
227      */
228   struct MeshClient *dest;
229
230     /**
231      * Flag to signal the destruction of the channel.
232      * If this is set GNUNET_YES the channel will be destroyed
233      * when the queue is empty.
234      */
235   int destroy;
236
237     /**
238      * Total messages pending for this channel, payload or not.
239      */
240   unsigned int pending_messages;
241
242     /**
243      * Reliability data.
244      * Only present (non-NULL) at the owner of a tunnel.
245      */
246   struct MeshChannelReliability *root_rel;
247
248     /**
249      * Reliability data.
250      * Only present (non-NULL) at the destination of a tunnel.
251      */
252   struct MeshChannelReliability *dest_rel;
253
254 };
255
256
257 /******************************************************************************/
258 /*******************************   GLOBALS  ***********************************/
259 /******************************************************************************/
260
261 /**
262  * Global handle to the statistics service.
263  */
264 extern struct GNUNET_STATISTICS_Handle *stats;
265
266 /**
267  * Local peer own ID (memory efficient handle).
268  */
269 extern GNUNET_PEER_Id myid;
270
271
272 /******************************************************************************/
273 /********************************   STATIC  ***********************************/
274 /******************************************************************************/
275
276 /**
277  * Destroy a reliable message after it has been acknowledged, either by
278  * direct mid ACK or bitfield. Updates the appropriate data structures and
279  * timers and frees all memory.
280  *
281  * @param copy Message that is no longer needed: remote peer got it.
282  * @param update_time Is the timing information relevant?
283  *                    If this message is ACK in a batch the timing information
284  *                    is skewed by the retransmission, count only for the
285  *                    retransmitted message.
286  */
287 static void
288 rel_message_free (struct MeshReliableMessage *copy, int update_time);
289
290 /**
291  * We have received a message out of order, or the client is not ready.
292  * Buffer it until we receive an ACK from the client or the missing
293  * message from the channel.
294  *
295  * @param msg Message to buffer (MUST be of type MESH_DATA).
296  * @param rel Reliability data to the corresponding direction.
297  */
298 static void
299 add_buffered_data (const struct GNUNET_MESH_Data *msg,
300                    struct MeshChannelReliability *rel)
301 {
302   struct MeshReliableMessage *copy;
303   struct MeshReliableMessage *prev;
304   uint32_t mid;
305   uint16_t size;
306
307   size = ntohs (msg->header.size);
308   mid = ntohl (msg->mid);
309
310   LOG (GNUNET_ERROR_TYPE_DEBUG, "add_buffered_data %u\n", mid);
311
312   copy = GNUNET_malloc (sizeof (*copy) + size);
313   copy->mid = mid;
314   copy->rel = rel;
315   copy->type = GNUNET_MESSAGE_TYPE_MESH_DATA;
316   memcpy (&copy[1], msg, size);
317
318   rel->n_recv++;
319
320   // FIXME do something better than O(n), although n < 64...
321   // FIXME start from the end (most messages are the latest ones)
322   for (prev = rel->head_recv; NULL != prev; prev = prev->next)
323   {
324     LOG (GNUNET_ERROR_TYPE_DEBUG, " prev %u\n", prev->mid);
325     if (GMC_is_pid_bigger (prev->mid, mid))
326     {
327       LOG (GNUNET_ERROR_TYPE_DEBUG, " bingo!\n");
328       GNUNET_CONTAINER_DLL_insert_before (rel->head_recv, rel->tail_recv,
329                                           prev, copy);
330       return;
331     }
332   }
333     LOG (GNUNET_ERROR_TYPE_DEBUG, " insert at tail!\n");
334     GNUNET_CONTAINER_DLL_insert_tail (rel->head_recv, rel->tail_recv, copy);
335     LOG (GNUNET_ERROR_TYPE_DEBUG, "add_buffered_data END\n");
336 }
337
338 /**
339  * Add a destination client to a channel, initializing all data structures
340  * in the channel and the client.
341  *
342  * @param ch Channel to which add the destination.
343  * @param c Client which to add to the channel.
344  */
345 static void
346 add_destination (struct MeshChannel *ch, struct MeshClient *c)
347 {
348   if (NULL != ch->dest)
349   {
350     GNUNET_break (0);
351     return;
352   }
353
354   /* Assign local id as destination */
355   ch->lid_dest = GML_get_next_chid (c);
356
357   /* Store in client's hashmap */
358   GML_channel_add (c, ch->lid_dest, ch);
359
360   GNUNET_break (NULL == ch->dest_rel);
361   ch->dest_rel = GNUNET_new (struct MeshChannelReliability);
362   ch->dest_rel->ch = ch;
363   ch->dest_rel->expected_delay = MESH_RETRANSMIT_TIME;
364
365   ch->dest = c;
366 }
367
368
369 /**
370  * Send data to a client.
371  *
372  * If the client is ready, send directly, otherwise buffer while listening
373  * for a local ACK.
374  *
375  * @param ch Channel
376  * @param msg Message.
377  * @param fwd Is this a fwd (root->dest) message?
378  */
379 static void
380 send_client_data (struct MeshChannel *ch,
381                   const struct GNUNET_MESH_Data *msg,
382                   int fwd)
383 {
384   if (fwd)
385   {
386     if (ch->dest_rel->client_ready)
387       GML_send_data (ch->dest, msg, ch->lid_dest);
388     else
389       add_buffered_data (msg, ch->dest_rel);
390   }
391   else
392   {
393     if (ch->root_rel->client_ready)
394       GML_send_data (ch->root, msg, ch->lid_root);
395     else
396       add_buffered_data (msg, ch->root_rel);
397   }
398 }
399
400
401 /**
402  * Send a buffered message to the client, for in order delivery or
403  * as result of client ACK.
404  *
405  * @param ch Channel on which to empty the message buffer.
406  * @param c Client to send to.
407  * @param fwd Is this to send FWD data?.
408  */
409 static void
410 send_client_buffered_data (struct MeshChannel *ch,
411                            struct MeshClient *c,
412                            int fwd)
413 {
414   struct MeshReliableMessage *copy;
415   struct MeshChannelReliability *rel;
416
417   LOG (GNUNET_ERROR_TYPE_DEBUG, "send_buffered_data\n");
418   rel = fwd ? ch->dest_rel : ch->root_rel;
419   if (GNUNET_NO == rel->client_ready)
420   {
421     LOG (GNUNET_ERROR_TYPE_DEBUG, "client not ready\n");
422     return;
423   }
424
425   copy = rel->head_recv;
426   /* We never buffer channel management messages */
427   if (NULL != copy)
428   {
429     if (copy->mid == rel->mid_recv || GNUNET_NO == ch->reliable)
430     {
431       struct GNUNET_MESH_Data *msg = (struct GNUNET_MESH_Data *) &copy[1];
432
433       LOG (GNUNET_ERROR_TYPE_DEBUG,
434            " have %u! now expecting %u\n",
435            copy->mid, rel->mid_recv + 1);
436       send_client_data (ch, msg, fwd);
437       rel->n_recv--;
438       rel->mid_recv++;
439       GNUNET_CONTAINER_DLL_remove (rel->head_recv, rel->tail_recv, copy);
440       GNUNET_free (copy);
441     }
442     else
443     {
444       LOG (GNUNET_ERROR_TYPE_DEBUG,
445            " reliable && don't have %u, next is %u\n",
446            rel->mid_recv,
447            copy->mid);
448       return;
449     }
450   }
451   LOG (GNUNET_ERROR_TYPE_DEBUG, "send_buffered_data END\n");
452 }
453
454
455 /**
456  * Allow a client to send more data.
457  *
458  * In case the client was already allowed to send data, do nothing.
459  *
460  * @param ch Channel.
461  * @param fwd Is this a FWD ACK? (FWD ACKs are sent to root)
462  */
463 static void
464 send_client_ack (struct MeshChannel *ch, int fwd)
465 {
466   struct MeshChannelReliability *rel = fwd ? ch->root_rel : ch->dest_rel;
467
468   LOG (GNUNET_ERROR_TYPE_DEBUG,
469        "  sending %s ack to client on channel %s\n",
470        fwd ? "FWD" : "BCK", GMCH_2s (ch));
471
472   if (NULL == rel)
473   {
474     GNUNET_break (0);
475     return;
476   }
477
478   if (GNUNET_YES == rel->client_allowed)
479   {
480     LOG (GNUNET_ERROR_TYPE_DEBUG, "  already allowed\n");
481     return;
482   }
483   rel->client_allowed = GNUNET_YES;
484
485   GML_send_ack (fwd ? ch->root : ch->dest, fwd ? ch->lid_root : ch->lid_dest);
486 }
487
488
489 /**
490  * Notify the root that the destination rejected the channel.
491  *
492  * @param ch Rejected channel.
493  */
494 static void
495 send_client_nack (struct MeshChannel *ch)
496 {
497   if (NULL == ch->root)
498   {
499     GNUNET_break (0);
500     return;
501   }
502   GML_send_nack (ch->root, ch->lid_root);
503 }
504
505
506 /**
507  * Destroy all reliable messages queued for a channel,
508  * during a channel destruction.
509  * Frees the reliability structure itself.
510  *
511  * @param rel Reliability data for a channel.
512  */
513 static void
514 channel_rel_free_all (struct MeshChannelReliability *rel)
515 {
516   struct MeshReliableMessage *copy;
517   struct MeshReliableMessage *next;
518
519   if (NULL == rel)
520     return;
521
522   for (copy = rel->head_recv; NULL != copy; copy = next)
523   {
524     next = copy->next;
525     GNUNET_CONTAINER_DLL_remove (rel->head_recv, rel->tail_recv, copy);
526     GNUNET_free (copy);
527   }
528   for (copy = rel->head_sent; NULL != copy; copy = next)
529   {
530     next = copy->next;
531     GNUNET_CONTAINER_DLL_remove (rel->head_sent, rel->tail_sent, copy);
532     GNUNET_free (copy);
533   }
534   if (GNUNET_SCHEDULER_NO_TASK != rel->retry_task)
535     GNUNET_SCHEDULER_cancel (rel->retry_task);
536   GNUNET_free (rel);
537 }
538
539
540 /**
541  * Mark future messages as ACK'd.
542  *
543  * @param rel Reliability data.
544  * @param msg DataACK message with a bitfield of future ACK'd messages.
545  */
546 static void
547 channel_rel_free_sent (struct MeshChannelReliability *rel,
548                        const struct GNUNET_MESH_DataACK *msg)
549 {
550   struct MeshReliableMessage *copy;
551   struct MeshReliableMessage *next;
552   uint64_t bitfield;
553   uint64_t mask;
554   uint32_t mid;
555   uint32_t target;
556   unsigned int i;
557
558   bitfield = msg->futures;
559   mid = ntohl (msg->mid);
560   LOG (GNUNET_ERROR_TYPE_DEBUG,
561               "!!! free_sent_reliable %u %llX\n",
562               mid, bitfield);
563   LOG (GNUNET_ERROR_TYPE_DEBUG,
564               " rel %p, head %p\n",
565               rel, rel->head_sent);
566   for (i = 0, copy = rel->head_sent;
567        i < 64 && NULL != copy && 0 != bitfield;
568        i++)
569   {
570     LOG (GNUNET_ERROR_TYPE_DEBUG,
571                 " trying bit %u (mid %u)\n",
572                 i, mid + i + 1);
573     mask = 0x1LL << i;
574     if (0 == (bitfield & mask))
575      continue;
576
577     LOG (GNUNET_ERROR_TYPE_DEBUG, " set!\n");
578     /* Bit was set, clear the bit from the bitfield */
579     bitfield &= ~mask;
580
581     /* The i-th bit was set. Do we have that copy? */
582     /* Skip copies with mid < target */
583     target = mid + i + 1;
584     LOG (GNUNET_ERROR_TYPE_DEBUG, " target %u\n", target);
585     while (NULL != copy && GMC_is_pid_bigger (target, copy->mid))
586      copy = copy->next;
587
588     /* Did we run out of copies? (previously freed, it's ok) */
589     if (NULL == copy)
590     {
591      LOG (GNUNET_ERROR_TYPE_DEBUG, "run out of copies...\n");
592      return;
593     }
594
595     /* Did we overshoot the target? (previously freed, it's ok) */
596     if (GMC_is_pid_bigger (copy->mid, target))
597     {
598      LOG (GNUNET_ERROR_TYPE_DEBUG, " next copy %u\n", copy->mid);
599      continue;
600     }
601
602     /* Now copy->mid == target, free it */
603     next = copy->next;
604     rel_message_free (copy, GNUNET_YES);
605     copy = next;
606   }
607   LOG (GNUNET_ERROR_TYPE_DEBUG, "free_sent_reliable END\n");
608 }
609
610
611 /**
612  * We haven't received an ACK after a certain time: restransmit the message.
613  *
614  * @param cls Closure (MeshReliableMessage with the message to restransmit)
615  * @param tc TaskContext.
616  */
617 static void
618 channel_retransmit_message (void *cls,
619                             const struct GNUNET_SCHEDULER_TaskContext *tc)
620 {
621   struct MeshChannelReliability *rel = cls;
622   struct MeshReliableMessage *copy;
623   struct MeshChannel *ch;
624   struct GNUNET_MESH_Data *payload;
625   int fwd;
626
627   rel->retry_task = GNUNET_SCHEDULER_NO_TASK;
628   if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN))
629     return;
630
631   ch = rel->ch;
632   copy = rel->head_sent;
633   if (NULL == copy)
634   {
635     GNUNET_break (0);
636     return;
637   }
638
639   /* Search the message to be retransmitted in the outgoing queue.
640    * Check only the queue for the connection that is going to be used,
641    * if the message is stuck in some other connection's queue we shouldn't
642    * act upon it:
643    * - cancelling it and sending the new one doesn't guarantee it's delivery,
644    *   the old connection could be temporary stalled or the queue happened to
645    *   be long at time of insertion.
646    * - not sending the new one could cause terrible delays the old connection
647    *   is stalled.
648    */
649 //   FIXME access to queue elements is limited
650   payload = (struct GNUNET_MESH_Data *) &copy[1];
651   fwd = (rel == ch->root_rel);
652 //   c = GMT_get_connection (ch->t, fwd);
653 //   hop = connection_get_hop (c, fwd);
654 //   for (q = hop->queue_head; NULL != q; q = q->next)
655 //   {
656 //     if (ntohs (payload->header.type) == q->type && ch == q->ch)
657 //     {
658 //       struct GNUNET_MESH_Data *queued_data = q->cls;
659 // 
660 //       if (queued_data->mid == payload->mid)
661 //         break;
662 //     }
663 //   }
664
665   /* Message not found in the queue that we are going to use. */
666 //   if (NULL == q)
667 //   {
668     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! RETRANSMIT %u\n", copy->mid);
669
670     GMCH_send_prebuilt_message (&payload->header, ch, fwd);
671     GNUNET_STATISTICS_update (stats, "# data retransmitted", 1, GNUNET_NO);
672 //   }
673 //   else
674 //   {
675 //     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! ALREADY IN QUEUE %u\n", copy->mid);
676 //   }
677
678   copy->timestamp = GNUNET_TIME_absolute_get();
679   rel->retry_timer = GNUNET_TIME_STD_BACKOFF (rel->retry_timer);
680   rel->retry_task = GNUNET_SCHEDULER_add_delayed (rel->retry_timer,
681                                                   &channel_retransmit_message,
682                                                   cls);
683 }
684
685
686 /**
687  * Destroy a reliable message after it has been acknowledged, either by
688  * direct mid ACK or bitfield. Updates the appropriate data structures and
689  * timers and frees all memory.
690  *
691  * @param copy Message that is no longer needed: remote peer got it.
692  * @param update_time Is the timing information relevant?
693  *                    If this message is ACK in a batch the timing information
694  *                    is skewed by the retransmission, count only for the
695  *                    retransmitted message.
696  */
697 static void
698 rel_message_free (struct MeshReliableMessage *copy, int update_time)
699 {
700   struct MeshChannelReliability *rel;
701   struct GNUNET_TIME_Relative time;
702
703   rel = copy->rel;
704   LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! Freeing %u\n", copy->mid);
705   if (update_time)
706   {
707     time = GNUNET_TIME_absolute_get_duration (copy->timestamp);
708     rel->expected_delay.rel_value_us *= 7;
709     rel->expected_delay.rel_value_us += time.rel_value_us;
710     rel->expected_delay.rel_value_us /= 8;
711     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!!  took %s\n",
712                 GNUNET_STRINGS_relative_time_to_string (time, GNUNET_NO));
713     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!!  new expected delay %s\n",
714                 GNUNET_STRINGS_relative_time_to_string (rel->expected_delay,
715                                                         GNUNET_NO));
716     rel->retry_timer = rel->expected_delay;
717   }
718   else
719   {
720     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! batch free, ignoring timing\n");
721   }
722   GNUNET_CONTAINER_DLL_remove (rel->head_sent, rel->tail_sent, copy);
723   GNUNET_free (copy);
724 }
725
726
727 /**
728  * Confirm we got a channel create.
729  *
730  * @param ch The channel to confirm.
731  * @param fwd Should we send a FWD ACK? (going dest->root)
732  */
733 static void
734 channel_send_ack (struct MeshChannel *ch, int fwd)
735 {
736   struct GNUNET_MESH_ChannelManage msg;
737
738   msg.header.size = htons (sizeof (msg));
739   msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_CHANNEL_ACK);
740   LOG (GNUNET_ERROR_TYPE_DEBUG,
741               "  sending channel %s ack for channel %s\n",
742               fwd ? "FWD" : "BCK", GMCH_2s (ch));
743
744   msg.chid = htonl (ch->gid);
745   GMCH_send_prebuilt_message (&msg.header, ch, !fwd);
746 }
747
748
749 /**
750  * Notify that a channel create didn't succeed.
751  *
752  * @param ch The channel to reject.
753  */
754 static void
755 channel_send_nack (struct MeshChannel *ch)
756 {
757   struct GNUNET_MESH_ChannelManage msg;
758
759   msg.header.size = htons (sizeof (msg));
760   msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_CHANNEL_NACK);
761   LOG (GNUNET_ERROR_TYPE_DEBUG,
762        "  sending channel NACK for channel %s\n",
763        GMCH_2s (ch));
764
765   msg.chid = htonl (ch->gid);
766   GMCH_send_prebuilt_message (&msg.header, ch, GNUNET_NO);
767 }
768
769
770 /**
771  * Channel was ACK'd by remote peer, mark as ready and cancel retransmission.
772  *
773  * @param ch Channel to mark as ready.
774  * @param fwd Was the ACK message a FWD ACK? (dest->root, SYNACK)
775  */
776 static void
777 channel_confirm (struct MeshChannel *ch, int fwd)
778 {
779   struct MeshChannelReliability *rel;
780   struct MeshReliableMessage *copy;
781   struct MeshReliableMessage *next;
782
783   LOG (GNUNET_ERROR_TYPE_DEBUG,
784               "  channel confirm %s %s:%X\n",
785               fwd ? "FWD" : "BCK", GMT_2s (ch->t), ch->gid);
786   ch->state = MESH_CHANNEL_READY;
787
788   rel = fwd ? ch->root_rel : ch->dest_rel;
789   rel->client_ready = GNUNET_YES;
790   for (copy = rel->head_sent; NULL != copy; copy = next)
791   {
792     struct GNUNET_MessageHeader *msg;
793
794     next = copy->next;
795     msg = (struct GNUNET_MessageHeader *) &copy[1];
796     if (ntohs (msg->type) == GNUNET_MESSAGE_TYPE_MESH_CHANNEL_CREATE)
797     {
798       rel_message_free (copy, GNUNET_YES);
799       /* TODO return? */
800     }
801   }
802   send_client_ack (ch, fwd);
803
804   /* In case of a FWD ACK (SYNACK) send a BCK ACK (ACK). */
805   if (fwd)
806     channel_send_ack (ch, !fwd);
807 }
808
809 static void
810 message_sent (void *cls,
811               struct MeshTunnel3 *t,
812               struct MeshTunnel3Queue *q,
813               uint16_t type, size_t size)
814 {
815   struct MeshReliableMessage *copy = cls;
816   struct MeshChannelReliability *rel = copy->rel;
817
818   copy->timestamp = GNUNET_TIME_absolute_get ();
819   if (GNUNET_SCHEDULER_NO_TASK == rel->retry_task)
820   {
821     rel->retry_timer =
822         GNUNET_TIME_relative_multiply (rel->expected_delay,
823                                        MESH_RETRANSMIT_MARGIN);
824     rel->retry_task =
825         GNUNET_SCHEDULER_add_delayed (rel->retry_timer,
826                                       &channel_retransmit_message,
827                                       rel);
828   }
829 }
830
831
832 /**
833  * Save a copy to retransmit in case it gets lost.
834  *
835  * Initializes all needed callbacks and timers.
836  *
837  * @param ch Channel this message goes on.
838  * @param msg Message to copy.
839  * @param fwd Is this fwd traffic?
840  */
841 static struct MeshReliableMessage *
842 channel_save_copy (struct MeshChannel *ch,
843                    const struct GNUNET_MessageHeader *msg,
844                    int fwd)
845 {
846   struct MeshChannelReliability *rel;
847   struct MeshReliableMessage *copy;
848   uint32_t mid;
849   uint16_t type;
850   uint16_t size;
851
852   rel = fwd ? ch->root_rel : ch->dest_rel;
853   mid = rel->mid_send - 1;
854   type = ntohs (msg->type);
855   size = ntohs (msg->size);
856
857   LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! SAVE %u %s\n",
858        mid, GNUNET_MESH_DEBUG_M2S (type));
859   copy = GNUNET_malloc (sizeof (struct MeshReliableMessage) + size);
860   copy->mid = mid;
861   copy->rel = rel;
862   copy->type = type;
863   memcpy (&copy[1], msg, size);
864   GNUNET_CONTAINER_DLL_insert_tail (rel->head_sent, rel->tail_sent, copy);
865
866   return copy;
867 }
868
869
870 /**
871  * Destroy a channel and free all resources.
872  *
873  * @param ch Channel to destroy.
874  */
875 static void
876 channel_destroy (struct MeshChannel *ch)
877 {
878   struct MeshClient *c;
879
880   if (NULL == ch)
881     return;
882
883   LOG (GNUNET_ERROR_TYPE_DEBUG, "destroying channel %s:%u\n",
884               GMT_2s (ch->t), ch->gid);
885   GMCH_debug (ch);
886
887   c = ch->root;
888   if (NULL != c)
889   {
890     GML_channel_remove (c, ch->lid_root, ch);
891   }
892
893   c = ch->dest;
894   if (NULL != c)
895   {
896     GML_channel_remove (c, ch->lid_dest, ch);
897   }
898
899   channel_rel_free_all (ch->root_rel);
900   channel_rel_free_all (ch->dest_rel);
901
902   GMT_remove_channel (ch->t, ch);
903   GNUNET_STATISTICS_update (stats, "# channels", -1, GNUNET_NO);
904
905   GNUNET_free (ch);
906 }
907
908
909 /**
910  * Create a new channel.
911  *
912  * @param t Tunnel this channel is in.
913  * @param owner Client that owns the channel, NULL for foreign channels.
914  * @param lid_root Local ID for root client.
915  *
916  * @return A new initialized channel. NULL on error.
917  */
918 static struct MeshChannel *
919 channel_new (struct MeshTunnel3 *t,
920              struct MeshClient *owner,
921              MESH_ChannelNumber lid_root)
922 {
923   struct MeshChannel *ch;
924
925   ch = GNUNET_new (struct MeshChannel);
926   ch->root = owner;
927   ch->lid_root = lid_root;
928   ch->t = t;
929
930   GNUNET_STATISTICS_update (stats, "# channels", 1, GNUNET_NO);
931
932   if (NULL != owner)
933   {
934     ch->gid = GMT_get_next_chid (t);
935     GML_channel_add (owner, lid_root, ch);
936   }
937   GMT_add_channel (t, ch);
938
939   return ch;
940 }
941
942
943 /**
944  * Set options in a channel, extracted from a bit flag field
945  *
946  * @param ch Channel to set options to.
947  * @param options Bit array in host byte order.
948  */
949 static void
950 channel_set_options (struct MeshChannel *ch, uint32_t options)
951 {
952   ch->nobuffer = (options & GNUNET_MESH_OPTION_NOBUFFER) != 0 ?
953                  GNUNET_YES : GNUNET_NO;
954   ch->reliable = (options & GNUNET_MESH_OPTION_RELIABLE) != 0 ?
955                  GNUNET_YES : GNUNET_NO;
956 }
957
958 static int
959 is_loopback (const struct MeshChannel *ch)
960 {
961   if (NULL != ch->t)
962     return GMT_is_loopback (ch->t);
963
964   return (NULL != ch->root && NULL != ch->dest);
965 }
966
967
968 /**
969  * Handle a loopback message: call the appropriate handler for the message type.
970  *
971  * @param ch Channel this message is on.
972  * @param msgh Message header.
973  * @param fwd Is this FWD traffic?
974  */
975 void
976 handle_loopback (struct MeshChannel *ch,
977                  const struct GNUNET_MessageHeader *msgh,
978                  int fwd)
979 {
980   uint16_t type;
981
982   type = ntohs (msgh->type);
983   LOG (GNUNET_ERROR_TYPE_DEBUG,
984        "Loopback %s %s message!\n",
985        fwd ? "FWD" : "BCK", GNUNET_MESH_DEBUG_M2S (type));
986
987   switch (type)
988   {
989     case GNUNET_MESSAGE_TYPE_MESH_DATA:
990       /* Don't send hop ACK, wait for client to ACK */
991       GMCH_handle_data (ch, (struct GNUNET_MESH_Data *) msgh, fwd);
992       break;
993
994     case GNUNET_MESSAGE_TYPE_MESH_DATA_ACK:
995       GMCH_handle_data_ack (ch, (struct GNUNET_MESH_DataACK *) msgh, fwd);
996       break;
997
998     case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_CREATE:
999       GMCH_handle_create (ch->t,
1000                           (struct GNUNET_MESH_ChannelCreate *) msgh);
1001       break;
1002
1003     case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_ACK:
1004       GMCH_handle_ack (ch,
1005                        (struct GNUNET_MESH_ChannelManage *) msgh,
1006                        fwd);
1007       break;
1008
1009     case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_NACK:
1010       GMCH_handle_nack (ch);
1011       break;
1012
1013     case GNUNET_MESSAGE_TYPE_MESH_CHANNEL_DESTROY:
1014       GMCH_handle_destroy (ch,
1015                            (struct GNUNET_MESH_ChannelManage *) msgh,
1016                            fwd);
1017       break;
1018
1019     default:
1020       GNUNET_break_op (0);
1021       LOG (GNUNET_ERROR_TYPE_DEBUG,
1022            "end-to-end message not known (%u)\n",
1023            ntohs (msgh->type));
1024   }
1025 }
1026
1027
1028
1029 /******************************************************************************/
1030 /********************************    API    ***********************************/
1031 /******************************************************************************/
1032
1033
1034 /**
1035  * Get channel ID.
1036  *
1037  * @param ch Channel.
1038  *
1039  * @return ID
1040  */
1041 MESH_ChannelNumber
1042 GMCH_get_id (const struct MeshChannel *ch)
1043 {
1044   return ch->gid;
1045 }
1046
1047
1048 /**
1049  * Get the channel tunnel.
1050  *
1051  * @param ch Channel to get the tunnel from.
1052  *
1053  * @return tunnel of the channel.
1054  */
1055 struct MeshTunnel3 *
1056 GMCH_get_tunnel (const struct MeshChannel *ch)
1057 {
1058   return ch->t;
1059 }
1060
1061
1062 /**
1063  * Get free buffer space towards the client on a specific channel.
1064  *
1065  * @param ch Channel.
1066  * @param fwd Is query about FWD traffic?
1067  *
1068  * @return Free buffer space [0 - 64]
1069  */
1070 unsigned int
1071 GMCH_get_buffer (struct MeshChannel *ch, int fwd)
1072 {
1073   struct MeshChannelReliability *rel;
1074
1075   rel = fwd ? ch->dest_rel : ch->root_rel;
1076
1077   /* If rel is NULL it means that the end is not yet created,
1078    * most probably is a loopback channel at the point of sending
1079    * the ChannelCreate to itself.
1080    */
1081   if (NULL == rel)
1082     return 64;
1083
1084   return (64 - rel->n_recv);
1085 }
1086
1087
1088 /**
1089  * Get flow control status of end point: is client allow to send?
1090  *
1091  * @param ch Channel.
1092  * @param fwd Is query about FWD traffic? (Request root status).
1093  *
1094  * @return #GNUNET_YES if client is allowed to send us data.
1095  */
1096 int
1097 GMCH_get_allowed (struct MeshChannel *ch, int fwd)
1098 {
1099   struct MeshChannelReliability *rel;
1100
1101   rel = fwd ? ch->root_rel : ch->dest_rel;
1102
1103   return rel->client_allowed;
1104 }
1105
1106
1107 /**
1108  * Is the root client for this channel on this peer?
1109  *
1110  * @param ch Channel.
1111  * @param fwd Is this for fwd traffic?
1112  *
1113  * @return #GNUNET_YES in case it is.
1114  */
1115 int
1116 GMCH_is_origin (struct MeshChannel *ch, int fwd)
1117 {
1118   struct MeshClient *c;
1119
1120   c = fwd ? ch->root : ch->dest;
1121   return NULL != c;
1122 }
1123
1124
1125 /**
1126  * Is the destination client for this channel on this peer?
1127  *
1128  * @param ch Channel.
1129  * @param fwd Is this for fwd traffic?
1130  *
1131  * @return #GNUNET_YES in case it is.
1132  */
1133 int
1134 GMCH_is_terminal (struct MeshChannel *ch, int fwd)
1135 {
1136   struct MeshClient *c;
1137
1138   c = fwd ? ch->dest : ch->root;
1139   return NULL != c;
1140 }
1141
1142
1143 /**
1144  * Notify the destination client that a new incoming channel was created.
1145  *
1146  * @param ch Channel that was created.
1147  */
1148 void
1149 GMCH_send_create (struct MeshChannel *ch)
1150 {
1151   uint32_t opt;
1152
1153   if (NULL == ch->dest)
1154     return;
1155
1156   opt = 0;
1157   opt |= GNUNET_YES == ch->reliable ? GNUNET_MESH_OPTION_RELIABLE : 0;
1158   opt |= GNUNET_YES == ch->nobuffer ? GNUNET_MESH_OPTION_NOBUFFER : 0;
1159   GML_send_channel_create (ch->dest, ch->lid_dest, ch->port, opt,
1160                            GMT_get_destination (ch->t));
1161
1162 }
1163
1164 /**
1165  * Notify a client that the channel is no longer valid.
1166  *
1167  * @param ch Channel that is destroyed.
1168  */
1169 void
1170 GMCH_send_destroy (struct MeshChannel *ch)
1171 {
1172   struct GNUNET_MESH_ChannelManage msg;
1173
1174   msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_CHANNEL_DESTROY);
1175   msg.header.size = htons (sizeof (msg));
1176   msg.chid = htonl (ch->gid);
1177
1178   /* If root is not NULL, notify.
1179    * If it's NULL, check lid_root. When a local destroy comes in, root 
1180    * is set to NULL but lid_root is left untouched. In this case, do nothing,
1181    * the client is the one who reuqested the channel to be destroyed.
1182    */
1183   if (NULL != ch->root)
1184     GML_send_channel_destroy (ch->root, ch->lid_root);
1185   else if (0 == ch->lid_root)
1186     GMCH_send_prebuilt_message (&msg.header, ch, GNUNET_NO);
1187
1188   if (NULL != ch->dest)
1189     GML_send_channel_destroy (ch->dest, ch->lid_dest);
1190   else if (0 == ch->lid_dest)
1191     GMCH_send_prebuilt_message (&msg.header, ch, GNUNET_YES);
1192 }
1193
1194
1195 /**
1196  * Send an end-to-end ACK message for the most recent in-sequence payload.
1197  *
1198  * If channel is not reliable, do nothing.
1199  *
1200  * @param ch Channel this is about.
1201  * @param fwd Is for FWD traffic? (ACK dest->owner)
1202  */
1203 void
1204 GMCH_send_data_ack (struct MeshChannel *ch, int fwd)
1205 {
1206   struct GNUNET_MESH_DataACK msg;
1207   struct MeshChannelReliability *rel;
1208   struct MeshReliableMessage *copy;
1209   unsigned int delta;
1210   uint64_t mask;
1211   uint32_t ack;
1212
1213   if (GNUNET_NO == ch->reliable)
1214   {
1215     return;
1216   }
1217   rel = fwd ? ch->dest_rel : ch->root_rel;
1218   ack = rel->mid_recv - 1;
1219   LOG (GNUNET_ERROR_TYPE_DEBUG,
1220               " !! Send DATA_ACK for %u\n",
1221               ack);
1222
1223   msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_DATA_ACK);
1224   msg.header.size = htons (sizeof (msg));
1225   msg.chid = htonl (ch->gid);
1226   msg.futures = 0;
1227   for (copy = rel->head_recv; NULL != copy; copy = copy->next)
1228   {
1229     if (copy->type != GNUNET_MESSAGE_TYPE_MESH_DATA)
1230     {
1231       LOG (GNUNET_ERROR_TYPE_DEBUG,
1232            "!!  Type %s, expected DATA\n",
1233            GNUNET_MESH_DEBUG_M2S (copy->type));
1234       continue;
1235     }
1236     if (copy->mid == ack + 1)
1237     {
1238       ack++;
1239       continue;
1240     }
1241     delta = copy->mid - (ack + 1);
1242     if (63 < delta)
1243       break;
1244     mask = 0x1LL << delta;
1245     msg.futures |= mask;
1246     LOG (GNUNET_ERROR_TYPE_DEBUG,
1247          " !! setting bit for %u (delta %u) (%llX) -> %llX\n",
1248          copy->mid, delta, mask, msg.futures);
1249   }
1250   msg.mid = htonl (ack);
1251   LOG (GNUNET_ERROR_TYPE_DEBUG,
1252        "!!! ACK for %u, futures %llX\n",
1253        ack, msg.futures);
1254
1255   GMCH_send_prebuilt_message (&msg.header, ch, !fwd);
1256   LOG (GNUNET_ERROR_TYPE_DEBUG, "send_data_ack END\n");
1257 }
1258
1259
1260 /**
1261  * Allow a client to send us more data, in case it was choked.
1262  *
1263  * @param ch Channel.
1264  * @param fwd Is this about FWD traffic? (Root client).
1265  */
1266 void
1267 GMCH_allow_client (struct MeshChannel *ch, int fwd)
1268 {
1269   struct MeshChannelReliability *rel;
1270   unsigned int buffer;
1271
1272   LOG (GNUNET_ERROR_TYPE_DEBUG, "GMCH allow\n");
1273
1274   if (MESH_CHANNEL_READY != ch->state)
1275   {
1276     LOG (GNUNET_ERROR_TYPE_DEBUG, " channel not ready yet!\n");
1277     return;
1278   }
1279
1280   if (GNUNET_YES == ch->reliable)
1281   {
1282     rel = fwd ? ch->root_rel : ch->dest_rel;
1283     if (NULL == rel)
1284     {
1285       GNUNET_break (0);
1286       return;
1287     }
1288     if (NULL != rel->head_sent && 64 <= rel->mid_send - rel->head_sent->mid)
1289     {
1290       LOG (GNUNET_ERROR_TYPE_DEBUG, " too big MID gap! Wait for ACK.\n");
1291       return;
1292     }
1293   }
1294
1295   if (is_loopback (ch))
1296     buffer = GMCH_get_buffer (ch, fwd);
1297   else
1298     buffer = GMT_get_connections_buffer (ch->t);
1299
1300   if (0 == buffer)
1301   {
1302     LOG (GNUNET_ERROR_TYPE_DEBUG, " no buffer space.\n");
1303     return;
1304   }
1305
1306   LOG (GNUNET_ERROR_TYPE_DEBUG, " buffer space %u, allowing\n", buffer);
1307   send_client_ack (ch, fwd);
1308 }
1309
1310
1311 /**
1312  * Log channel info.
1313  *
1314  * @param ch Channel.
1315  */
1316 void
1317 GMCH_debug (struct MeshChannel *ch)
1318 {
1319   if (NULL == ch)
1320   {
1321     LOG (GNUNET_ERROR_TYPE_DEBUG, "*** DEBUG NULL CHANNEL ***\n");
1322     return;
1323   }
1324   LOG (GNUNET_ERROR_TYPE_DEBUG, "Channel %s:%X (%p)\n",
1325               GMT_2s (ch->t), ch->gid, ch);
1326   LOG (GNUNET_ERROR_TYPE_DEBUG, "  root %p/%p\n",
1327               ch->root, ch->root_rel);
1328   if (NULL != ch->root)
1329   {
1330     LOG (GNUNET_ERROR_TYPE_DEBUG, "  cli %s\n", GML_2s (ch->root));
1331     LOG (GNUNET_ERROR_TYPE_DEBUG, "  ready %s\n",
1332                 ch->root_rel->client_ready ? "YES" : "NO");
1333     LOG (GNUNET_ERROR_TYPE_DEBUG, "  id %X\n", ch->lid_root);
1334   }
1335   LOG (GNUNET_ERROR_TYPE_DEBUG, "  dest %p/%p\n",
1336               ch->dest, ch->dest_rel);
1337   if (NULL != ch->dest)
1338   {
1339     LOG (GNUNET_ERROR_TYPE_DEBUG, "  cli %s\n", GML_2s (ch->dest));
1340     LOG (GNUNET_ERROR_TYPE_DEBUG, "  ready %s\n",
1341                 ch->dest_rel->client_ready ? "YES" : "NO");
1342     LOG (GNUNET_ERROR_TYPE_DEBUG, "  id %X\n", ch->lid_dest);
1343   }
1344 }
1345
1346
1347 /**
1348  * Handle an ACK given by a client.
1349  *
1350  * Mark client as ready and send him any buffered data we could have for him.
1351  *
1352  * @param ch Channel.
1353  * @param fwd Is this a "FWD ACK"? (FWD ACKs are sent by dest and go BCK)
1354  */
1355 void
1356 GMCH_handle_local_ack (struct MeshChannel *ch, int fwd)
1357 {
1358   struct MeshChannelReliability *rel;
1359   struct MeshClient *c;
1360
1361   rel = fwd ? ch->dest_rel : ch->root_rel;
1362   c   = fwd ? ch->dest     : ch->root;
1363
1364   rel->client_ready = GNUNET_YES;
1365   send_client_buffered_data (ch, c, fwd);
1366   if (is_loopback (ch))
1367   {
1368     unsigned int buffer;
1369
1370     buffer = GMCH_get_buffer (ch, fwd);
1371     if (0 < buffer)
1372       GMCH_allow_client (ch, fwd);
1373
1374     return;
1375   }
1376   GMT_send_connection_acks (ch->t);
1377 }
1378
1379
1380 /**
1381  * Handle data given by a client.
1382  *
1383  * Check whether the client is allowed to send in this tunnel, save if channel
1384  * is reliable and send an ACK to the client if there is still buffer space
1385  * in the tunnel.
1386  *
1387  * @param ch Channel.
1388  * @param c Client which sent the data.
1389  * @param message Message.
1390  * @param fwd Is this a FWD data?
1391  *
1392  * @return GNUNET_OK if everything goes well, GNUNET_SYSERR in case of en error.
1393  */
1394 int
1395 GMCH_handle_local_data (struct MeshChannel *ch,
1396                         struct MeshClient *c,
1397                         struct GNUNET_MessageHeader *message,
1398                         int fwd)
1399 {
1400   struct MeshChannelReliability *rel;
1401   struct GNUNET_MESH_Data *payload;
1402   size_t size = ntohs (message->size);
1403   uint16_t p2p_size = sizeof(struct GNUNET_MESH_Data) + size;
1404   unsigned char cbuf[p2p_size];
1405
1406   /* Is the client in the channel? */
1407   if ( !( (fwd &&
1408            ch->root == c)
1409          ||
1410           (!fwd &&
1411            ch->dest == c) ) )
1412   {
1413     GNUNET_break_op (0);
1414     return GNUNET_SYSERR;
1415   }
1416
1417   rel = fwd ? ch->root_rel : ch->dest_rel;
1418
1419   if (GNUNET_NO == rel->client_allowed)
1420   {
1421     GNUNET_break_op (0);
1422     return GNUNET_SYSERR;
1423   }
1424
1425   rel->client_allowed = GNUNET_NO;
1426
1427   /* Ok, everything is correct, send the message. */
1428   payload = (struct GNUNET_MESH_Data *) cbuf;
1429   payload->mid = htonl (rel->mid_send);
1430   rel->mid_send++;
1431   memcpy (&payload[1], message, size);
1432   payload->header.size = htons (p2p_size);
1433   payload->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_DATA);
1434   payload->chid = htonl (ch->gid);
1435   LOG (GNUNET_ERROR_TYPE_DEBUG, "  sending on channel...\n");
1436   GMCH_send_prebuilt_message (&payload->header, ch, fwd);
1437
1438   if (is_loopback (ch))
1439   {
1440     if (GMCH_get_buffer (ch, fwd) > 0)
1441       send_client_ack (ch, fwd);
1442
1443     return GNUNET_OK;
1444   }
1445
1446   if (GMT_get_connections_buffer (ch->t) > 0)
1447   {
1448     send_client_ack (ch, fwd);
1449   }
1450
1451   return GNUNET_OK;
1452 }
1453
1454
1455 /**
1456  * Handle a channel destroy requested by a client.
1457  *
1458  * Destroy the channel and the tunnel in case this was the last channel.
1459  *
1460  * @param ch Channel.
1461  * @param c Client that requested the destruction (to avoid notifying him).
1462  */
1463 void
1464 GMCH_handle_local_destroy (struct MeshChannel *ch,
1465                            struct MeshClient *c)
1466 {
1467   struct MeshTunnel3 *t;
1468
1469   /* Cleanup after the tunnel */
1470   if (c == ch->dest)
1471   {
1472     LOG (GNUNET_ERROR_TYPE_DEBUG, " Client %s is destination.\n", GML_2s (c));
1473     GML_client_delete_channel (c, ch, ch->lid_dest);
1474     ch->dest = NULL;
1475   }
1476   if (c == ch->root)
1477   {
1478     LOG (GNUNET_ERROR_TYPE_DEBUG, " Client %s is owner.\n", GML_2s (c));
1479     GML_client_delete_channel (c, ch, ch->lid_root);
1480     ch->root = NULL;
1481   }
1482
1483   t = ch->t;
1484   GMCH_send_destroy (ch);
1485   channel_destroy (ch);
1486   GMT_destroy_if_empty (t);
1487 }
1488
1489
1490 /**
1491  * Handle a channel create requested by a client.
1492  *
1493  * Create the channel and the tunnel in case this was the first0 channel.
1494  *
1495  * @param c Client that requested the creation (will be the root).
1496  * @param msg Create Channel message.
1497  *
1498  * @return GNUNET_OK if everything went fine, GNUNET_SYSERR otherwise.
1499  */
1500 int
1501 GMCH_handle_local_create (struct MeshClient *c,
1502                           struct GNUNET_MESH_ChannelMessage *msg)
1503 {
1504   struct MeshChannel *ch;
1505   struct MeshTunnel3 *t;
1506   struct MeshPeer *peer;
1507   MESH_ChannelNumber chid;
1508
1509   LOG (GNUNET_ERROR_TYPE_DEBUG, "  towards %s:%u\n",
1510               GNUNET_i2s (&msg->peer), ntohl (msg->port));
1511   chid = ntohl (msg->channel_id);
1512
1513   /* Sanity check for duplicate channel IDs */
1514   if (NULL != GML_channel_get (c, chid))
1515   {
1516     GNUNET_break (0);
1517     return GNUNET_SYSERR;
1518   }
1519
1520   peer = GMP_get (&msg->peer);
1521   GMP_add_tunnel (peer);
1522   t = GMP_get_tunnel (peer);
1523
1524   if (GMP_get_short_id (peer) == myid)
1525   {
1526     GMT_change_state (t, MESH_TUNNEL3_READY);
1527   }
1528   else
1529   {
1530     GMP_connect (peer);
1531   }
1532
1533   /* Create channel */
1534   ch = channel_new (t, c, chid);
1535   if (NULL == ch)
1536   {
1537     GNUNET_break (0);
1538     return GNUNET_SYSERR;
1539   }
1540   ch->port = ntohl (msg->port);
1541   channel_set_options (ch, ntohl (msg->opt));
1542
1543   /* In unreliable channels, we'll use the DLL to buffer BCK data */
1544   ch->root_rel = GNUNET_new (struct MeshChannelReliability);
1545   ch->root_rel->ch = ch;
1546   ch->root_rel->expected_delay = MESH_RETRANSMIT_TIME;
1547
1548   LOG (GNUNET_ERROR_TYPE_DEBUG, "CREATED CHANNEL %s\n", GMCH_2s (ch));
1549
1550   /* Send create channel */
1551   {
1552     struct GNUNET_MESH_ChannelCreate msgcc;
1553
1554     msgcc.header.size = htons (sizeof (msgcc));
1555     msgcc.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_CHANNEL_CREATE);
1556     msgcc.chid = htonl (ch->gid);
1557     msgcc.port = msg->port;
1558     msgcc.opt = msg->opt;
1559
1560     GMT_send_prebuilt_message (&msgcc.header, t, ch, GNUNET_YES, NULL, NULL);
1561   }
1562   return GNUNET_OK;
1563 }
1564
1565
1566 /**
1567  * Handler for mesh network payload traffic.
1568  *
1569  * @param ch Channel for the message.
1570  * @param msg Unencryted data message.
1571  * @param fwd Is this message fwd? This only is meaningful in loopback channels.
1572  *            #GNUNET_YES if message is FWD on the respective channel (loopback)
1573  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
1574  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
1575  */
1576 void
1577 GMCH_handle_data (struct MeshChannel *ch,
1578                   const struct GNUNET_MESH_Data *msg,
1579                   int fwd)
1580 {
1581   struct MeshChannelReliability *rel;
1582   struct MeshClient *c;
1583   uint32_t mid;
1584
1585   /* If this is a remote (non-loopback) channel, find 'fwd'. */
1586   if (GNUNET_SYSERR == fwd)
1587   {
1588     if (is_loopback (ch))
1589     {
1590       /* It is a loopback channel after all... */
1591       GNUNET_break (0);
1592       return;
1593     }
1594     fwd = (NULL != ch->dest) ? GNUNET_YES : GNUNET_NO;
1595   }
1596
1597   /*  Initialize FWD/BCK data */
1598   c   = fwd ? ch->dest     : ch->root;
1599   rel = fwd ? ch->dest_rel : ch->root_rel;
1600
1601   if (NULL == c)
1602   {
1603     GNUNET_break (0);
1604     return;
1605   }
1606
1607   GNUNET_STATISTICS_update (stats, "# data received", 1, GNUNET_NO);
1608
1609   mid = ntohl (msg->mid);
1610   LOG (GNUNET_ERROR_TYPE_DEBUG, "!! got mid %u\n", mid);
1611
1612   if (GNUNET_NO == ch->reliable ||
1613       ( !GMC_is_pid_bigger (rel->mid_recv, mid) &&
1614         GMC_is_pid_bigger (rel->mid_recv + 64, mid) ) )
1615   {
1616     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! RECV %u\n", mid);
1617     if (GNUNET_YES == ch->reliable)
1618     {
1619       /* Is this the exact next expected messasge? */
1620       if (mid == rel->mid_recv)
1621       {
1622         LOG (GNUNET_ERROR_TYPE_DEBUG, "as expected\n");
1623         rel->mid_recv++;
1624         send_client_data (ch, msg, fwd);
1625       }
1626       else
1627       {
1628         LOG (GNUNET_ERROR_TYPE_DEBUG, "save for later\n");
1629         add_buffered_data (msg, rel);
1630       }
1631     }
1632     else
1633     {
1634       /* Tunnel is unreliable: send to clients directly */
1635       /* FIXME: accept Out Of Order traffic */
1636       rel->mid_recv = mid + 1;
1637       send_client_data (ch, msg, fwd);
1638     }
1639   }
1640   else
1641   {
1642     GNUNET_break_op (0);
1643     LOG (GNUNET_ERROR_TYPE_DEBUG,
1644                 " MID %u not expected (%u - %u), dropping!\n",
1645                 mid, rel->mid_recv, rel->mid_recv + 63);
1646   }
1647
1648   GMCH_send_data_ack (ch, fwd);
1649 }
1650
1651
1652 /**
1653  * Handler for mesh network traffic end-to-end ACKs.
1654  *
1655  * @param ch Channel on which we got this message.
1656  * @param msg Data message.
1657  * @param fwd Is this message fwd? This only is meaningful in loopback channels.
1658  *            #GNUNET_YES if message is FWD on the respective channel (loopback)
1659  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
1660  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
1661  */
1662 void
1663 GMCH_handle_data_ack (struct MeshChannel *ch,
1664                       const struct GNUNET_MESH_DataACK *msg,
1665                       int fwd)
1666 {
1667   struct MeshChannelReliability *rel;
1668   struct MeshReliableMessage *copy;
1669   struct MeshReliableMessage *next;
1670   uint32_t ack;
1671   int work;
1672
1673   /* If this is a remote (non-loopback) channel, find 'fwd'. */
1674   if (GNUNET_SYSERR == fwd)
1675   {
1676     if (is_loopback (ch))
1677     {
1678       /* It is a loopback channel after all... */
1679       GNUNET_break (0);
1680       return;
1681     }
1682     /* Inverted: if message came 'FWD' is a 'BCK ACK'. */
1683     fwd = (NULL != ch->dest) ? GNUNET_NO : GNUNET_YES;
1684   }
1685
1686   ack = ntohl (msg->mid);
1687   LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! %s ACK %u\n",
1688        (GNUNET_YES == fwd) ? "FWD" : "BCK", ack);
1689
1690   if (GNUNET_YES == fwd)
1691   {
1692     rel = ch->root_rel;
1693   }
1694   else
1695   {
1696     rel = ch->dest_rel;
1697   }
1698   if (NULL == rel)
1699   {
1700     GNUNET_break_op (0);
1701     return;
1702   }
1703
1704   /* Free ACK'd copies: no need to retransmit those anymore */
1705   for (work = GNUNET_NO, copy = rel->head_sent; copy != NULL; copy = next)
1706   {
1707     if (GMC_is_pid_bigger (copy->mid, ack))
1708     {
1709       LOG (GNUNET_ERROR_TYPE_DEBUG, "!!!  head %u, out!\n", copy->mid);
1710       channel_rel_free_sent (rel, msg);
1711       break;
1712     }
1713     work = GNUNET_YES;
1714     LOG (GNUNET_ERROR_TYPE_DEBUG, " !!  id %u\n", copy->mid);
1715     next = copy->next;
1716     rel_message_free (copy, GNUNET_YES);
1717   }
1718
1719   /* ACK client if needed */
1720   GMCH_allow_client (ch, fwd);
1721
1722   /* If some message was free'd, update the retransmission delay */
1723   if (GNUNET_YES == work)
1724   {
1725     if (GNUNET_SCHEDULER_NO_TASK != rel->retry_task)
1726     {
1727       GNUNET_SCHEDULER_cancel (rel->retry_task);
1728       if (NULL == rel->head_sent)
1729       {
1730         rel->retry_task = GNUNET_SCHEDULER_NO_TASK;
1731       }
1732       else
1733       {
1734         struct GNUNET_TIME_Absolute new_target;
1735         struct GNUNET_TIME_Relative delay;
1736
1737         delay = GNUNET_TIME_relative_multiply (rel->retry_timer,
1738                                                MESH_RETRANSMIT_MARGIN);
1739         new_target = GNUNET_TIME_absolute_add (rel->head_sent->timestamp,
1740                                                delay);
1741         delay = GNUNET_TIME_absolute_get_remaining (new_target);
1742         rel->retry_task =
1743             GNUNET_SCHEDULER_add_delayed (delay,
1744                                           &channel_retransmit_message,
1745                                           rel);
1746       }
1747     }
1748     else
1749       GNUNET_break (0);
1750   }
1751 }
1752
1753
1754 /**
1755  * Handler for channel create messages.
1756  *
1757  * Does not have fwd parameter because it's always 'FWD': channel is incoming.
1758  *
1759  * @param t Tunnel this channel will be in.
1760  * @param msg Channel crate message.
1761  */
1762 struct MeshChannel *
1763 GMCH_handle_create (struct MeshTunnel3 *t,
1764                     const struct GNUNET_MESH_ChannelCreate *msg)
1765 {
1766   MESH_ChannelNumber chid;
1767   struct MeshChannel *ch;
1768   struct MeshClient *c;
1769   uint32_t port;
1770
1771   chid = ntohl (msg->chid);
1772
1773   ch = GMT_get_channel (t, chid);
1774   if (NULL == ch)
1775   {
1776     /* Create channel */
1777     ch = channel_new (t, NULL, 0);
1778     ch->gid = chid;
1779   }
1780   channel_set_options (ch, ntohl (msg->opt));
1781
1782   /* Find a destination client */
1783   port = ntohl (msg->port);
1784   LOG (GNUNET_ERROR_TYPE_DEBUG, "   port %u\n", port);
1785   c = GML_client_get_by_port (port);
1786   if (NULL == c)
1787   {
1788     /* TODO send reject */
1789     LOG (GNUNET_ERROR_TYPE_DEBUG, "  no client has port registered\n");
1790     if (is_loopback (ch))
1791     {
1792       LOG (GNUNET_ERROR_TYPE_DEBUG, "  loopback: destroy on handler\n");
1793       channel_send_nack (ch);
1794     }
1795     else
1796     {
1797       LOG (GNUNET_ERROR_TYPE_DEBUG, "  not loopback: destroy now\n");
1798       channel_send_nack (ch);
1799       channel_destroy (ch);
1800     }
1801     return NULL;
1802   }
1803   else
1804   {
1805     LOG (GNUNET_ERROR_TYPE_DEBUG, "  client %p has port registered\n", c);
1806   }
1807
1808   add_destination (ch, c);
1809   if (GNUNET_YES == ch->reliable)
1810     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! Reliable\n");
1811   else
1812     LOG (GNUNET_ERROR_TYPE_DEBUG, "!!! Not Reliable\n");
1813
1814   GMCH_send_create (ch);
1815   channel_send_ack (ch, GNUNET_YES);
1816
1817   return ch;
1818 }
1819
1820
1821 /**
1822  * Handler for channel NACK messages.
1823  *
1824  * NACK messages always go dest -> root, no need for 'fwd' or 'msg' parameter.
1825  *
1826  * @param ch Channel.
1827  */
1828 void
1829 GMCH_handle_nack (struct MeshChannel *ch)
1830 {
1831   send_client_nack (ch);
1832   channel_destroy (ch);
1833 }
1834
1835
1836 /**
1837  * Handler for channel ack messages.
1838  *
1839  * @param ch Channel.
1840  * @param msg Message.
1841  * @param fwd Is this message fwd? This only is meaningful in loopback channels.
1842  *            #GNUNET_YES if message is FWD on the respective channel (loopback)
1843  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
1844  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
1845  */
1846 void
1847 GMCH_handle_ack (struct MeshChannel *ch,
1848                  const struct GNUNET_MESH_ChannelManage *msg,
1849                  int fwd)
1850 {
1851   /* If this is a remote (non-loopback) channel, find 'fwd'. */
1852   if (GNUNET_SYSERR == fwd)
1853   {
1854     if (is_loopback (ch))
1855     {
1856       /* It is a loopback channel after all... */
1857       GNUNET_break (0);
1858       return;
1859     }
1860     fwd = (NULL != ch->dest) ? GNUNET_YES : GNUNET_NO;
1861   }
1862
1863   channel_confirm (ch, !fwd);
1864 }
1865
1866
1867 /**
1868  * Handler for channel destroy messages.
1869  *
1870  * @param ch Channel to be destroyed of.
1871  * @param msg Message.
1872  * @param fwd Is this message fwd? This only is meaningful in loopback channels.
1873  *            #GNUNET_YES if message is FWD on the respective channel (loopback)
1874  *            #GNUNET_NO if message is BCK on the respective channel (loopback)
1875  *            #GNUNET_SYSERR if message on a one-ended channel (remote)
1876  */
1877 void
1878 GMCH_handle_destroy (struct MeshChannel *ch,
1879                      const struct GNUNET_MESH_ChannelManage *msg,
1880                      int fwd)
1881 {
1882   struct MeshTunnel3 *t;
1883
1884   /* If this is a remote (non-loopback) channel, find 'fwd'. */
1885   if (GNUNET_SYSERR == fwd)
1886   {
1887     if (is_loopback (ch))
1888     {
1889       /* It is a loopback channel after all... */
1890       GNUNET_break (0);
1891       return;
1892     }
1893     fwd = (NULL != ch->dest) ? GNUNET_YES : GNUNET_NO;
1894   }
1895
1896   GMCH_debug (ch);
1897   if ( (fwd && NULL == ch->dest) || (!fwd && NULL == ch->root) )
1898   {
1899     /* Not for us (don't destroy twice a half-open loopback channel) */
1900     return;
1901   }
1902
1903   t = ch->t;
1904   GMCH_send_destroy (ch);
1905   channel_destroy (ch);
1906   GMT_destroy_if_empty (t);
1907 }
1908
1909
1910 /**
1911  * Sends an already built message on a channel.
1912  *
1913  * If the channel is on a loopback tunnel, notifies the appropriate destination
1914  * client locally.
1915  *
1916  * On a normal channel passes the message to the tunnel for encryption and
1917  * sending on a connection.
1918  *
1919  * This function DOES NOT save the message for retransmission.
1920  *
1921  * @param message Message to send. Function makes a copy of it.
1922  * @param ch Channel on which this message is transmitted.
1923  * @param fwd Is this a fwd message?
1924  */
1925 void
1926 GMCH_send_prebuilt_message (const struct GNUNET_MessageHeader *message,
1927                             struct MeshChannel *ch, int fwd)
1928 {
1929   LOG (GNUNET_ERROR_TYPE_DEBUG, "GMCH Send %s %s on channel %s\n",
1930        fwd ? "FWD" : "BCK", GNUNET_MESH_DEBUG_M2S (ntohs (message->type)), 
1931        GMCH_2s (ch));
1932
1933   if (GMT_is_loopback (ch->t))
1934   {
1935     handle_loopback (ch, message, fwd);
1936     return;
1937   }
1938
1939   if (GNUNET_YES == ch->reliable
1940       && ntohs (message->type) == GNUNET_MESSAGE_TYPE_MESH_DATA)
1941   {
1942     struct MeshReliableMessage *copy;
1943
1944     copy = channel_save_copy (ch, message, fwd);
1945     copy->q = GMT_send_prebuilt_message (message, ch->t, ch, fwd,
1946                                           &message_sent, copy);
1947   }
1948   else
1949     GMT_send_prebuilt_message (message, ch->t, ch, fwd, NULL, NULL);
1950 }
1951
1952
1953 /**
1954  * Get the static string for identification of the channel.
1955  *
1956  * @param ch Channel.
1957  *
1958  * @return Static string with the channel IDs.
1959  */
1960 const char *
1961 GMCH_2s (const struct MeshChannel *ch)
1962 {
1963   static char buf[64];
1964
1965   if (NULL == ch)
1966     return "(NULL Channel)";
1967
1968   sprintf (buf, "%s:%X (%X / %X)",
1969            GMT_2s (ch->t), ch->gid, ch->lid_root, ch->lid_dest);
1970
1971   return buf;
1972 }