aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBart Polot <bart@net.in.tum.de>2011-08-30 09:10:02 +0000
committerBart Polot <bart@net.in.tum.de>2011-08-30 09:10:02 +0000
commitd89572e31baedfab391428de67a376abc14ff849 (patch)
tree52c41e70cea4ef022967313081c4e941023b06ad
parent3c9b3f415156a699558e7494862c4bbbe22c31f0 (diff)
downloadgnunet-d89572e31baedfab391428de67a376abc14ff849.tar.gz
gnunet-d89572e31baedfab391428de67a376abc14ff849.zip
Fix tests, peer commands api <-> service
-rw-r--r--src/mesh/gnunet-service-mesh.c3
-rw-r--r--src/mesh/mesh_api_new.c444
-rw-r--r--src/mesh/test_mesh_api.c35
3 files changed, 271 insertions, 211 deletions
diff --git a/src/mesh/gnunet-service-mesh.c b/src/mesh/gnunet-service-mesh.c
index fdc0007ed..71d611287 100644
--- a/src/mesh/gnunet-service-mesh.c
+++ b/src/mesh/gnunet-service-mesh.c
@@ -2167,6 +2167,8 @@ handle_local_tunnel_create (void *cls, struct GNUNET_SERVER_Client *client,
2167 struct MeshClient *c; 2167 struct MeshClient *c;
2168 GNUNET_HashCode hash; 2168 GNUNET_HashCode hash;
2169 2169
2170 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "MESH: new tunnel requested\n");
2171
2170 /* Sanity check for client registration */ 2172 /* Sanity check for client registration */
2171 if (NULL == (c = retrieve_client (client))) 2173 if (NULL == (c = retrieve_client (client)))
2172 { 2174 {
@@ -2250,6 +2252,7 @@ handle_local_tunnel_destroy (void *cls, struct GNUNET_SERVER_Client *client,
2250 MESH_TunnelNumber tid; 2252 MESH_TunnelNumber tid;
2251 GNUNET_HashCode hash; 2253 GNUNET_HashCode hash;
2252 2254
2255 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "MESH: destroying tunnel\n");
2253 2256
2254 /* Sanity check for client registration */ 2257 /* Sanity check for client registration */
2255 if (NULL == (c = retrieve_client (client))) 2258 if (NULL == (c = retrieve_client (client)))
diff --git a/src/mesh/mesh_api_new.c b/src/mesh/mesh_api_new.c
index e6e6fdaa8..36b66ed0d 100644
--- a/src/mesh/mesh_api_new.c
+++ b/src/mesh/mesh_api_new.c
@@ -28,7 +28,7 @@
28 * - DATA STRUCTURES 28 * - DATA STRUCTURES
29 * - AUXILIARY FUNCTIONS 29 * - AUXILIARY FUNCTIONS
30 * - RECEIVE HANDLERS 30 * - RECEIVE HANDLERS
31 * - SEND CALLBACKS 31 * - SEND FUNCTIONS
32 * - API CALL DEFINITIONS 32 * - API CALL DEFINITIONS
33 */ 33 */
34 34
@@ -51,11 +51,36 @@ extern "C"
51#include "mesh.h" 51#include "mesh.h"
52#include "mesh_protocol.h" 52#include "mesh_protocol.h"
53 53
54#define MESH_API_MAX_QUEUE 10
55
54/******************************************************************************/ 56/******************************************************************************/
55/************************ DATA STRUCTURES ****************************/ 57/************************ DATA STRUCTURES ****************************/
56/******************************************************************************/ 58/******************************************************************************/
57 59
58/** 60/**
61 * Transmission queue to the service
62 */
63struct GNUNET_MESH_queue
64{
65 /**
66 * Double Linked list
67 */
68 struct GNUNET_MESH_queue *next;
69 struct GNUNET_MESH_queue *prev;
70
71 /**
72 * Size of the data to follow
73 */
74 uint16_t size;
75
76 /**
77 * Data itself
78 */
79 void *data;
80};
81
82
83/**
59 * Opaque handle to the service. 84 * Opaque handle to the service.
60 */ 85 */
61struct GNUNET_MESH_Handle 86struct GNUNET_MESH_Handle
@@ -105,6 +130,12 @@ struct GNUNET_MESH_Handle
105 * Closure for all the handlers given by the client 130 * Closure for all the handlers given by the client
106 */ 131 */
107 void *cls; 132 void *cls;
133
134 /**
135 * Messages to send to the service
136 */
137 struct GNUNET_MESH_queue *queue_head;
138 struct GNUNET_MESH_queue *queue_tail;
108}; 139};
109 140
110/** 141/**
@@ -143,6 +174,11 @@ struct GNUNET_MESH_Tunnel
143 * All peers added to the tunnel 174 * All peers added to the tunnel
144 */ 175 */
145 GNUNET_PEER_Id *peers; 176 GNUNET_PEER_Id *peers;
177
178 /**
179 * Number of peer added to the tunnel
180 */
181 uint32_t npeers;
146 182
147 /** 183 /**
148 * Closure for the connect/disconnect handlers 184 * Closure for the connect/disconnect handlers
@@ -157,7 +193,8 @@ struct GNUNET_MESH_Tunnel
157 193
158struct GNUNET_MESH_TransmitHandle 194struct GNUNET_MESH_TransmitHandle
159{ 195{
160 // TODO 196 struct GNUNET_MESH_Tunnel *t;
197 struct GNUNET_MESH_queue *q;
161}; 198};
162 199
163/******************************************************************************/ 200/******************************************************************************/
@@ -185,6 +222,21 @@ retrieve_tunnel (struct GNUNET_MESH_Handle *h, MESH_TunnelNumber tid)
185 return NULL; 222 return NULL;
186} 223}
187 224
225/**
226 * Get the length of the transmission queue
227 * @param h mesh handle whose queue is to be measured
228 */
229static uint32_t
230get_queue_length (struct GNUNET_MESH_Handle *h)
231{
232 struct GNUNET_MESH_queue *q;
233 uint32_t i;
234
235 /* count */
236 for (q = h->queue_head, i = 0; NULL != q; q = q->next, i++);
237
238 return i;
239}
188 240
189 241
190/******************************************************************************/ 242/******************************************************************************/
@@ -387,13 +439,11 @@ msg_received (void *cls, const struct GNUNET_MessageHeader *msg)
387 439
388 440
389/******************************************************************************/ 441/******************************************************************************/
390/************************ SEND CALLBACKS ****************************/ 442/************************ SEND FUNCTIONS ****************************/
391/******************************************************************************/ 443/******************************************************************************/
392 444
393
394/** 445/**
395 * Function called to send a connect message to the service, specifying the 446 * Function called to send a message to the service.
396 * types and applications that the client is interested in.
397 * "buf" will be NULL and "size" zero if the socket was closed for writing in 447 * "buf" will be NULL and "size" zero if the socket was closed for writing in
398 * the meantime. 448 * the meantime.
399 * 449 *
@@ -403,162 +453,75 @@ msg_received (void *cls, const struct GNUNET_MessageHeader *msg)
403 * @return number of bytes written to buf 453 * @return number of bytes written to buf
404 */ 454 */
405static size_t 455static size_t
406send_connect_packet (void *cls, size_t size, void *buf) 456send_raw (void *cls, size_t size, void *buf)
407{ 457{
408 struct GNUNET_MESH_Handle *h = cls; 458 struct GNUNET_MESH_Handle *h = cls;
409 struct GNUNET_MESH_ClientConnect *msg; 459 struct GNUNET_MESH_queue *q;
410 GNUNET_MESH_ApplicationType *apps;
411 uint16_t napps;
412 uint16_t *types;
413 uint16_t ntypes;
414 460
415 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Send connect packet()\n", size); 461 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Send packet() Buffer %u\n", size);
416 h->th = NULL; 462 h->th = NULL;
417 if (0 == size || NULL == buf) 463 if (0 == size || NULL == buf)
418 { 464 {
419 // FIXME: disconnect, reconnect, retry? 465 // FIXME: disconnect, reconnect, retry?
420 return 0; 466 return 0;
421 } 467 }
468 q = h->queue_head;
422 if (sizeof (struct GNUNET_MessageHeader) > size) 469 if (sizeof (struct GNUNET_MessageHeader) > size)
423 { 470 {
424 GNUNET_break (0); 471 GNUNET_break (0);
425 // FIXME: disconnect, reconnect, retry! 472 GNUNET_assert (sizeof (struct GNUNET_MessageHeader) > q->size);
473 h->th = GNUNET_CLIENT_notify_transmit_ready (h->client, q->size,
474 GNUNET_TIME_UNIT_FOREVER_REL,
475 GNUNET_YES, &send_raw, h);
426 return 0; 476 return 0;
427 } 477 }
428 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 478 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: type: %i\n",
429 "mesh: Send connect packet: %lu bytes buffer\n", size); 479 ntohs(((struct GNUNET_MessageHeader *)q->data)->type));
430 msg = (struct GNUNET_MESH_ClientConnect *) buf; 480 memcpy(buf, q->data, q->size);
431 msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT); 481 GNUNET_free (q->data);
432 482 size = q->size;
433 for (ntypes = 0, types = NULL; ntypes < h->n_handlers; ntypes++) 483 GNUNET_CONTAINER_DLL_remove(h->queue_head, h->queue_tail, q);
484 GNUNET_free(q);
485 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: size: %u\n", size);
486
487 if (NULL != h->queue_head)
434 { 488 {
435 types = GNUNET_realloc (types, sizeof (uint16_t) * (ntypes + 1)); 489 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: next size: %u\n",
436 types[ntypes] = h->message_handlers[ntypes].type; 490 h->queue_head->size);
491 h->th = GNUNET_CLIENT_notify_transmit_ready (h->client, h->queue_head->size,
492 GNUNET_TIME_UNIT_FOREVER_REL,
493 GNUNET_YES, &send_raw, h);
437 } 494 }
495 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Send packet() END\n");
438 496
439 for (napps = 0, apps = NULL; napps < h->n_applications; napps++) 497 return size;
440 {
441 apps =
442 GNUNET_realloc (apps,
443 sizeof (GNUNET_MESH_ApplicationType) * (napps + 1));
444 apps[napps] = h->applications[napps];
445 }
446
447 msg->header.size =
448 htons (sizeof (struct GNUNET_MESH_ClientConnect) +
449 sizeof (uint16_t) * ntypes +
450 sizeof (GNUNET_MESH_ApplicationType) * napps);
451 memcpy (&msg[1], types, sizeof (uint16_t) * ntypes);
452 types = (uint16_t *) & msg[1];
453 memcpy (&types[ntypes], apps, sizeof (GNUNET_MESH_ApplicationType) * napps);
454 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
455 "mesh: Sent %lu bytes long message %d types and %d apps\n",
456 ntohs (msg->header.size), ntypes, napps);
457 msg->applications = htons (napps);
458 msg->types = htons (ntypes);
459
460 /* start listening */
461 GNUNET_CLIENT_receive (h->client, &msg_received, h,
462 GNUNET_TIME_UNIT_FOREVER_REL);
463 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Send connect packet() END\n",
464 size);
465
466 return ntohs (msg->header.size);
467} 498}
468 499
469
470/** 500/**
471 * Function called to send a create tunnel message, specifying the tunnel 501 * Auxiliary function to send a packet to the service
472 * number chosen by the client. 502 * Takes care of creating a new queue element and calling the tmt_rdy function
473 * "buf" will be NULL and "size" zero if the socket was closed for 503 * if necessary.
474 * writing in the meantime. 504 * @param h mesh handle
475 * 505 * @param size size of the packet to transmit
476 * @param cls closure, the tunnel handle 506 * @param data packet itself
477 * @param size number of bytes available in buf
478 * @param buf where the callee should write the create tunnel message
479 * @return number of bytes written to buf
480 */ 507 */
481static size_t 508static void
482send_tunnel_create_packet (void *cls, size_t size, void *buf) 509send_packet (struct GNUNET_MESH_Handle *h, size_t size, void *data)
483{ 510{
484 struct GNUNET_MESH_Tunnel *t = cls; 511 struct GNUNET_MESH_queue *q;
485 struct GNUNET_MESH_Handle *h;
486 struct GNUNET_MESH_TunnelMessage *msg;
487 512
488 h = t->mesh; 513 q = GNUNET_malloc (sizeof (struct GNUNET_MESH_queue));
489 h->th = NULL; 514 q->size = size;
490 if (0 == size || buf == NULL) 515 q->data = data;
516 GNUNET_CONTAINER_DLL_insert_tail (h->queue_head, h->queue_tail, q);
517 if (NULL == h->th)
491 { 518 {
492 // FIXME: disconnect, reconnect, retry? 519 h->th = GNUNET_CLIENT_notify_transmit_ready (h->client, size,
493 return 0; 520 GNUNET_TIME_UNIT_FOREVER_REL,
494 } 521 GNUNET_YES, &send_raw, h);
495 if (sizeof (struct GNUNET_MESH_TunnelMessage) > size)
496 {
497 GNUNET_break (0);
498 // FIXME: disconnect, reconnect, retry?
499 return 0;
500 } 522 }
501 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
502 "Send create tunnel packet: %lu bytes buffer\n", size);
503 msg = (struct GNUNET_MESH_TunnelMessage *) buf;
504 msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE);
505
506 msg->header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage));
507 msg->tunnel_id = htonl (t->tid);
508
509 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sent %lu bytes long message\n",
510 ntohs (msg->header.size));
511
512 return sizeof (struct GNUNET_MESH_TunnelMessage);
513} 523}
514 524
515
516/**
517 * Function called to send a destroy tunnel message, specifying the tunnel
518 * number chosen by the client.
519 * "buf" will be NULL and "size" zero if the socket was closed for
520 * writing in the meantime.
521 *
522 * @param cls closure, the tunnel handle
523 * @param size number of bytes available in buf
524 * @param buf where the callee should write the create tunnel message
525 * @return number of bytes written to buf
526 */
527static size_t
528send_tunnel_destroy_packet (void *cls, size_t size, void *buf)
529{
530 struct GNUNET_MESH_Tunnel *t = cls;
531 struct GNUNET_MESH_Handle *h;
532 struct GNUNET_MESH_TunnelMessage *msg;
533
534 h = t->mesh;
535 h->th = NULL;
536 if (0 == size || buf == NULL)
537 {
538 return 0;
539 }
540 if (sizeof (struct GNUNET_MESH_TunnelMessage) > size)
541 {
542 GNUNET_break (0);
543 // FIXME: disconnect, reconnect, retry!
544 return 0;
545 }
546 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
547 "Send tunnel destroy packet: %lu bytes buffer\n", size);
548 msg = (struct GNUNET_MESH_TunnelMessage *) buf;
549 msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY);
550
551 msg->header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage));
552 msg->tunnel_id = htonl (t->tid);
553
554 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sent %lu bytes long message\n",
555 ntohs (msg->header.size));
556 GNUNET_free (t);
557
558 return sizeof (struct GNUNET_MESH_TunnelMessage);
559}
560
561
562/******************************************************************************/ 525/******************************************************************************/
563/********************** API CALL DEFINITIONS *************************/ 526/********************** API CALL DEFINITIONS *************************/
564/******************************************************************************/ 527/******************************************************************************/
@@ -585,6 +548,11 @@ GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, void *cls,
585 const GNUNET_MESH_ApplicationType *stypes) 548 const GNUNET_MESH_ApplicationType *stypes)
586{ 549{
587 struct GNUNET_MESH_Handle *h; 550 struct GNUNET_MESH_Handle *h;
551 struct GNUNET_MESH_ClientConnect *msg;
552 GNUNET_MESH_ApplicationType *apps;
553 uint16_t napps;
554 uint16_t *types;
555 uint16_t ntypes;
588 size_t size; 556 size_t size;
589 557
590 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: GNUNET_MESH_connect()\n"); 558 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: GNUNET_MESH_connect()\n");
@@ -604,24 +572,39 @@ GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, void *cls,
604 h->applications = stypes; 572 h->applications = stypes;
605 h->next_tid = 0x80000000; 573 h->next_tid = 0x80000000;
606 574
575 /* count handlers and apps, calculate size */
607 for (h->n_handlers = 0; handlers[h->n_handlers].type; h->n_handlers++) ; 576 for (h->n_handlers = 0; handlers[h->n_handlers].type; h->n_handlers++) ;
608 for (h->n_applications = 0; stypes[h->n_applications]; h->n_applications++) ; 577 for (h->n_applications = 0; stypes[h->n_applications]; h->n_applications++) ;
609
610 size = sizeof (struct GNUNET_MESH_ClientConnect); 578 size = sizeof (struct GNUNET_MESH_ClientConnect);
611 size += h->n_handlers * sizeof (uint16_t); 579 size += h->n_handlers * sizeof (uint16_t);
612 size += h->n_applications * sizeof (GNUNET_MESH_ApplicationType); 580 size += h->n_applications * sizeof (GNUNET_MESH_ApplicationType);
613 581
614 if (NULL != h->th) 582 /* build connection packet */
583 msg = GNUNET_malloc(size);
584 msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT);
585 msg->header.size = htons (size);
586 types = (uint16_t *) &msg[1];
587 for (ntypes = 0; ntypes < h->n_handlers; ntypes++)
615 { 588 {
616 /* FIXME implement queue system instead */ 589 types[ntypes] = h->message_handlers[ntypes].type;
617 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "mesh: overwriting th of mesh\n"); 590 }
618 GNUNET_CLIENT_notify_transmit_ready_cancel (h->th); 591 apps = (GNUNET_MESH_ApplicationType *) &types[ntypes];
592 for (napps = 0; napps < h->n_applications; napps++)
593 {
594 apps[napps] = h->applications[napps];
619 } 595 }
620 h->th = 596 msg->applications = htons (napps);
621 GNUNET_CLIENT_notify_transmit_ready (h->client, size, 597 msg->types = htons (ntypes);
622 GNUNET_TIME_UNIT_FOREVER_REL, 598
623 GNUNET_YES, &send_connect_packet, 599 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
624 (void *) h); 600 "mesh: Sending %lu bytes long message %d types and %d apps\n",
601 ntohs (msg->header.size), ntypes, napps);
602
603 send_packet(h, size, msg);
604
605 GNUNET_CLIENT_receive (h->client, &msg_received, h,
606 GNUNET_TIME_UNIT_FOREVER_REL);
607
625 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: GNUNET_MESH_connect() END\n"); 608 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: GNUNET_MESH_connect() END\n");
626 609
627 return h; 610 return h;
@@ -663,33 +646,27 @@ GNUNET_MESH_tunnel_create (struct GNUNET_MESH_Handle *h,
663 GNUNET_MESH_TunnelDisconnectHandler 646 GNUNET_MESH_TunnelDisconnectHandler
664 disconnect_handler, void *handler_cls) 647 disconnect_handler, void *handler_cls)
665{ 648{
666 struct GNUNET_MESH_Tunnel *tunnel; 649 struct GNUNET_MESH_Tunnel *t;
650 struct GNUNET_MESH_TunnelMessage *msg;
667 651
668 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Creating new tunnel\n"); 652 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Creating new tunnel\n");
669 tunnel = GNUNET_malloc (sizeof (struct GNUNET_MESH_Tunnel)); 653 t = GNUNET_malloc (sizeof (struct GNUNET_MESH_Tunnel));
670 654
671 tunnel->connect_handler = connect_handler; 655 t->connect_handler = connect_handler;
672 tunnel->disconnect_handler = disconnect_handler; 656 t->disconnect_handler = disconnect_handler;
673 tunnel->cls = handler_cls; 657 t->cls = handler_cls;
674 tunnel->mesh = h; 658 t->mesh = h;
675 tunnel->tid = h->next_tid++; 659 t->tid = h->next_tid++;
676 h->next_tid |= GNUNET_MESH_LOCAL_TUNNEL_ID_MARK; // keep in range 660 h->next_tid |= GNUNET_MESH_LOCAL_TUNNEL_ID_MARK; // keep in range
677 if (NULL != h->th) 661
678 { 662 msg = GNUNET_malloc (sizeof (struct GNUNET_MESH_TunnelMessage));
679 /* FIXME implement queue system instead */ 663 msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE);
680 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "mesh: overwriting th of mesh\n"); 664 msg->header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage));
681 GNUNET_CLIENT_notify_transmit_ready_cancel (h->th); 665 msg->tunnel_id = htonl (t->tid);
682 } 666
683 h->th = 667 send_packet(h, sizeof (struct GNUNET_MESH_TunnelMessage), msg);
684 GNUNET_CLIENT_notify_transmit_ready (h->client, 668
685 sizeof (struct 669 return t;
686 GNUNET_MESH_TunnelMessage),
687 GNUNET_TIME_UNIT_FOREVER_REL,
688 GNUNET_YES,
689 &send_tunnel_create_packet,
690 (void *) tunnel);
691
692 return tunnel;
693} 670}
694 671
695 672
@@ -701,21 +678,20 @@ GNUNET_MESH_tunnel_create (struct GNUNET_MESH_Handle *h,
701void 678void
702GNUNET_MESH_tunnel_destroy (struct GNUNET_MESH_Tunnel *tun) 679GNUNET_MESH_tunnel_destroy (struct GNUNET_MESH_Tunnel *tun)
703{ 680{
681 struct GNUNET_MESH_Handle *h;
682 struct GNUNET_MESH_TunnelMessage *msg;
683
704 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Destroying tunnel\n"); 684 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "mesh: Destroying tunnel\n");
705 if (NULL != tun->mesh->th) 685
706 { 686 h = tun->mesh;
707 /* FIXME implement queue system instead */ 687 msg = GNUNET_malloc (sizeof (struct GNUNET_MESH_TunnelMessage));
708 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "mesh: overwriting th of mesh\n"); 688 msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY);
709 GNUNET_CLIENT_notify_transmit_ready_cancel (tun->mesh->th); 689 msg->header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage));
710 } 690 msg->tunnel_id = htonl (tun->tid);
711 tun->mesh->th = 691
712 GNUNET_CLIENT_notify_transmit_ready (tun->mesh->client, 692 GNUNET_free (tun);
713 sizeof (struct 693
714 GNUNET_MESH_TunnelMessage), 694 send_packet(h, sizeof (struct GNUNET_MESH_TunnelMessage), msg);
715 GNUNET_TIME_UNIT_FOREVER_REL,
716 GNUNET_YES,
717 &send_tunnel_destroy_packet,
718 (void *) tun);
719} 695}
720 696
721 697
@@ -732,13 +708,34 @@ GNUNET_MESH_peer_request_connect_add (struct GNUNET_MESH_Tunnel *tunnel,
732 struct GNUNET_TIME_Relative timeout, 708 struct GNUNET_TIME_Relative timeout,
733 const struct GNUNET_PeerIdentity *peer) 709 const struct GNUNET_PeerIdentity *peer)
734{ 710{
735 static GNUNET_PEER_Id peer_id; 711 struct GNUNET_MESH_PeerControl *msg;
712 GNUNET_PEER_Id peer_id;
713 int i;
736 714
737 peer_id = GNUNET_PEER_intern (peer); 715 peer_id = GNUNET_PEER_intern (peer);
716 for (i = 0; i < tunnel->npeers; i++)
717 {
718 if (tunnel->peers[i] == peer_id)
719 {
720 GNUNET_PEER_change_rc (peer_id, -1);
721 return;
722 }
723 }
724 tunnel->npeers++;
725 tunnel->peers = GNUNET_realloc (tunnel->peers,
726 tunnel->npeers * sizeof (GNUNET_PEER_Id));
727 tunnel->peers[tunnel->npeers - 1] = peer_id;
728
729 msg = GNUNET_malloc (sizeof (struct GNUNET_MESH_PeerControl));
730 msg->header.size = htons (sizeof (struct GNUNET_MESH_PeerControl));
731 msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT_PEER_ADD);
732 msg->tunnel_id = htonl(tunnel->tid);
733 memcpy (&msg->peer, peer, sizeof (struct GNUNET_PeerIdentity));
734
735 send_packet(tunnel->mesh, sizeof (struct GNUNET_MESH_PeerControl), msg);
738 736
739 /* FIXME ACTUALLY DO STUFF */ 737// tunnel->connect_handler (tunnel->cls, peer, NULL); FIXME call this later
740 tunnel->peers = &peer_id; 738// TODO: remember timeout
741 tunnel->connect_handler (tunnel->cls, peer, NULL);
742 return; 739 return;
743} 740}
744 741
@@ -754,9 +751,37 @@ void
754GNUNET_MESH_peer_request_connect_del (struct GNUNET_MESH_Tunnel *tunnel, 751GNUNET_MESH_peer_request_connect_del (struct GNUNET_MESH_Tunnel *tunnel,
755 const struct GNUNET_PeerIdentity *peer) 752 const struct GNUNET_PeerIdentity *peer)
756{ 753{
757 /* FIXME ACTUALLY DO STUFF */ 754 struct GNUNET_MESH_PeerControl *msg;
758 tunnel->peers = NULL; 755 GNUNET_PEER_Id peer_id;
759 tunnel->disconnect_handler (tunnel->cls, peer); 756 int i;
757
758 peer_id = GNUNET_PEER_search (peer);
759 if (0 == peer_id) return;
760 for (i = 0; i < tunnel->npeers; i++)
761 {
762 if (tunnel->peers[i] == peer_id)
763 {
764 GNUNET_PEER_change_rc (peer_id, -1);
765 tunnel->npeers--;
766 while (i < tunnel->npeers)
767 {
768 tunnel->peers[i] = tunnel->peers[i+1];
769 i++;
770 }
771 tunnel->peers = GNUNET_realloc (tunnel->peers,
772 tunnel->npeers * sizeof (GNUNET_PEER_Id));
773 msg = GNUNET_malloc (sizeof (struct GNUNET_MESH_PeerControl));
774 msg->header.size = htons(sizeof (struct GNUNET_MESH_PeerControl));
775 msg->header.type = htons(GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT_PEER_DEL);
776 msg->tunnel_id = htonl(tunnel->tid);
777 memcpy (&msg->peer, peer, sizeof (struct GNUNET_PeerIdentity));
778
779 send_packet(tunnel->mesh, sizeof (struct GNUNET_MESH_PeerControl), msg);
780
781 return;
782 }
783 }
784 // TODO: remember timeout
760 return; 785 return;
761} 786}
762 787
@@ -775,6 +800,15 @@ GNUNET_MESH_peer_request_connect_by_type (struct GNUNET_MESH_Tunnel *tunnel,
775 struct GNUNET_TIME_Relative timeout, 800 struct GNUNET_TIME_Relative timeout,
776 GNUNET_MESH_ApplicationType app_type) 801 GNUNET_MESH_ApplicationType app_type)
777{ 802{
803 struct GNUNET_MESH_ConnectPeerByType *msg;
804 msg = GNUNET_malloc (sizeof (struct GNUNET_MESH_ConnectPeerByType));
805 msg->header.size = htons(sizeof (struct GNUNET_MESH_ConnectPeerByType));
806 msg->header.type = htons(GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT_PEER_BY_TYPE);
807 msg->tunnel_id = htonl(tunnel->tid);
808 msg->type = htonl(app_type);
809
810 send_packet(tunnel->mesh, sizeof (struct GNUNET_MESH_ConnectPeerByType), msg);
811 // TODO: remember timeout
778 return; 812 return;
779} 813}
780 814
@@ -813,11 +847,43 @@ GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork,
813 struct GNUNET_MESH_TransmitHandle *handle; 847 struct GNUNET_MESH_TransmitHandle *handle;
814 848
815 handle = GNUNET_malloc (sizeof (struct GNUNET_MESH_TransmitHandle)); 849 handle = GNUNET_malloc (sizeof (struct GNUNET_MESH_TransmitHandle));
850 handle->t = tunnel;
851 handle->q = GNUNET_malloc (sizeof (struct GNUNET_MESH_queue));
852 handle->q->size = notify_size;
853 handle->q->data = GNUNET_malloc (notify_size);
854
855 if (get_queue_length(tunnel->mesh) < MESH_API_MAX_QUEUE)
856 {
857 notify (notify_cls, notify_size, handle->q->data);
858 GNUNET_CONTAINER_DLL_insert_tail(tunnel->mesh->queue_head,
859 tunnel->mesh->queue_tail,
860 handle->q);
861 } else {
862 // TODO dataless - queue
863 }
816 864
817 return handle; 865 return handle;
818} 866}
819 867
820 868
869/**
870 * Cancel the specified transmission-ready notification.
871 *
872 * @param th handle that was returned by "notify_transmit_ready".
873 */
874void
875GNUNET_MESH_notify_transmit_ready_cancel (struct GNUNET_MESH_TransmitHandle *th)
876{
877 GNUNET_CONTAINER_DLL_remove(th->t->mesh->queue_head,
878 th->t->mesh->queue_tail,
879 th->q);
880 // TODO remove from dataless queue
881 GNUNET_free (th->q->data);
882 GNUNET_free (th->q);
883 GNUNET_free (th);
884}
885
886
821#if 0 /* keep Emacsens' auto-indent happy */ 887#if 0 /* keep Emacsens' auto-indent happy */
822{ 888{
823#endif 889#endif
diff --git a/src/mesh/test_mesh_api.c b/src/mesh/test_mesh_api.c
index fbef7ee19..8e7bca807 100644
--- a/src/mesh/test_mesh_api.c
+++ b/src/mesh/test_mesh_api.c
@@ -67,33 +67,25 @@ static struct GNUNET_MESH_MessageHandler handlers[] = { {&callback, 1, 0},
67static void 67static void
68do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) 68do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
69{ 69{
70 fprintf (stderr, "++++++++ STARTING SHUTDOWN\n");
71 fprintf (stderr, "+++++++++ ABORT TASK\n");
72 if (0 != abort_task) 70 if (0 != abort_task)
73 { 71 {
74 GNUNET_SCHEDULER_cancel (abort_task); 72 GNUNET_SCHEDULER_cancel (abort_task);
75 } 73 }
76 fprintf (stderr, "+++++++++ DISCONNECT MESH\n");
77 if (NULL != mesh) 74 if (NULL != mesh)
78 { 75 {
79 GNUNET_MESH_disconnect (mesh); 76 GNUNET_MESH_disconnect (mesh);
80 } 77 }
81 fprintf (stderr, "+++++++++ KILL PROCESS\n");
82 if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) 78 if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM))
83 { 79 {
84 GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); 80 GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill");
85 } 81 }
86 fprintf (stderr, "+++++++++ WAIT\n");
87 GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (arm_pid)); 82 GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (arm_pid));
88 fprintf (stderr, "+++++++++ PROCESS CLOSE\n");
89 GNUNET_OS_process_close (arm_pid); 83 GNUNET_OS_process_close (arm_pid);
90 fprintf (stderr, "++++++++ END SHUTDOWN\n");
91} 84}
92 85
93static void 86static void
94do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) 87do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
95{ 88{
96 fprintf (stderr, "++++++++ STARTING ABORT\n");
97 if (0 != test_task) 89 if (0 != test_task)
98 { 90 {
99 GNUNET_SCHEDULER_cancel (test_task); 91 GNUNET_SCHEDULER_cancel (test_task);
@@ -101,16 +93,15 @@ do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
101 result = GNUNET_SYSERR; 93 result = GNUNET_SYSERR;
102 abort_task = 0; 94 abort_task = 0;
103 do_shutdown (cls, tc); 95 do_shutdown (cls, tc);
104 fprintf (stderr, "++++++++ END ABORT\n");
105} 96}
106 97
107static void 98static void
108test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) 99test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
109{ 100{
110 struct GNUNET_CONFIGURATION_Handle *cfg = cls; 101 struct GNUNET_CONFIGURATION_Handle *cfg = cls;
111 static const GNUNET_MESH_ApplicationType app[] = { 1, 2, 3, 0 }; 102 static const GNUNET_MESH_ApplicationType app[] = { 1, 2, 3, 4, 5, 6, 7, 8, 0};
103 struct GNUNET_MESH_Tunnel *t;
112 104
113 fprintf (stderr, "++++++++ STARTING TEST\n");
114 test_task = (GNUNET_SCHEDULER_TaskIdentifier) 0; 105 test_task = (GNUNET_SCHEDULER_TaskIdentifier) 0;
115 mesh = GNUNET_MESH_connect (cfg, NULL, NULL, handlers, app); 106 mesh = GNUNET_MESH_connect (cfg, NULL, NULL, handlers, app);
116 if (NULL == mesh) 107 if (NULL == mesh)
@@ -123,10 +114,16 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
123 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "YAY! CONNECTED TO MESH :D\n"); 114 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "YAY! CONNECTED TO MESH :D\n");
124 } 115 }
125 116
117 t = GNUNET_MESH_tunnel_create(mesh,
118 NULL,
119 NULL,
120 NULL);
121
122 GNUNET_MESH_tunnel_destroy(t);
123
126 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply 124 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
127 (GNUNET_TIME_UNIT_SECONDS, 3), &do_shutdown, 125 (GNUNET_TIME_UNIT_SECONDS, 5), &do_shutdown,
128 NULL); 126 NULL);
129 fprintf (stderr, "++++++++ END TEST\n");
130} 127}
131 128
132 129
@@ -134,8 +131,7 @@ static void
134run (void *cls, char *const *args, const char *cfgfile, 131run (void *cls, char *const *args, const char *cfgfile,
135 const struct GNUNET_CONFIGURATION_Handle *cfg) 132 const struct GNUNET_CONFIGURATION_Handle *cfg)
136{ 133{
137 fprintf (stderr, "++++++++ STARTING RUN\n"); 134 GNUNET_log_setup ("test_mesh_api",
138 GNUNET_log_setup ("test_mesh_small",
139#if VERBOSE 135#if VERBOSE
140 "DEBUG", 136 "DEBUG",
141#else 137#else
@@ -154,12 +150,9 @@ run (void *cls, char *const *args, const char *cfgfile,
154 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply 150 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
155 (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort, 151 (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort,
156 NULL); 152 NULL);
157 test_task =
158 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &test,
159 (void *) cfg);
160// GNUNET_SCHEDULER_add_now (&test, (void *)cfg);
161 153
162 fprintf (stderr, "++++++++ END RUN\n"); 154 test_task = GNUNET_SCHEDULER_add_now (&test, (void *)cfg);
155
163} 156}
164 157
165 158
@@ -179,7 +172,6 @@ main (int argc, char *argv[])
179 GNUNET_GETOPT_OPTION_END 172 GNUNET_GETOPT_OPTION_END
180 }; 173 };
181 174
182 fprintf (stderr, "++++++++ STARTING TEST_API\n");
183 ret = 175 ret =
184 GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, 176 GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2,
185 "test-mesh-api", "nohelp", options, &run, NULL); 177 "test-mesh-api", "nohelp", options, &run, NULL);
@@ -196,6 +188,5 @@ main (int argc, char *argv[])
196 return 1; 188 return 1;
197 } 189 }
198 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test ok\n"); 190 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test ok\n");
199 fprintf (stderr, "++++++++ END TEST_API\n");
200 return 0; 191 return 0;
201} 192}