aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/include/gnunet_constants.h4
-rw-r--r--src/include/gnunet_protocols.h5
-rw-r--r--src/mesh/gnunet-service-mesh.c295
-rw-r--r--src/mesh/mesh.h25
-rw-r--r--src/mesh/mesh_api.c137
-rw-r--r--src/mesh/mesh_common.c5
6 files changed, 154 insertions, 317 deletions
diff --git a/src/include/gnunet_constants.h b/src/include/gnunet_constants.h
index 3a80c26be..99dd5bfcf 100644
--- a/src/include/gnunet_constants.h
+++ b/src/include/gnunet_constants.h
@@ -49,7 +49,7 @@ extern "C"
49 * After how long do we consider a connection to a peer dead 49 * After how long do we consider a connection to a peer dead
50 * if we don't receive messages from the peer? 50 * if we don't receive messages from the peer?
51 */ 51 */
52#define GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 5) 52#define GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_YEARS, 5)
53 53
54/** 54/**
55 * How long do we delay reading more from a peer after a quota violation? 55 * How long do we delay reading more from a peer after a quota violation?
@@ -61,7 +61,7 @@ extern "C"
61 * even if we assume that the service commonly does not 61 * even if we assume that the service commonly does not
62 * respond instantly (DNS, Database, etc.). 62 * respond instantly (DNS, Database, etc.).
63 */ 63 */
64#define GNUNET_CONSTANTS_SERVICE_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 10) 64#define GNUNET_CONSTANTS_SERVICE_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_YEARS, 10)
65 65
66/** 66/**
67 * How long do we delay messages to get larger packet sizes (CORKing)? 67 * How long do we delay messages to get larger packet sizes (CORKing)?
diff --git a/src/include/gnunet_protocols.h b/src/include/gnunet_protocols.h
index c8e6a4d00..7d6bbde2c 100644
--- a/src/include/gnunet_protocols.h
+++ b/src/include/gnunet_protocols.h
@@ -862,6 +862,11 @@ extern "C"
862#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY 274 862#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY 274
863 863
864/** 864/**
865 * Payload client <-> service
866 */
867#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA 275
868
869/**
865 * Local ACK for data. 870 * Local ACK for data.
866 */ 871 */
867#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK 286 872#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK 286
diff --git a/src/mesh/gnunet-service-mesh.c b/src/mesh/gnunet-service-mesh.c
index 467e4d614..2122c28a5 100644
--- a/src/mesh/gnunet-service-mesh.c
+++ b/src/mesh/gnunet-service-mesh.c
@@ -1804,6 +1804,7 @@ tunnel_get_by_local_id (struct MeshClient *c, MESH_TunnelNumber tid)
1804 } 1804 }
1805 else 1805 else
1806 { 1806 {
1807 GNUNET_assert (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_CLI);
1807 return GNUNET_CONTAINER_multihashmap32_get (c->own_tunnels, tid); 1808 return GNUNET_CONTAINER_multihashmap32_get (c->own_tunnels, tid);
1808 } 1809 }
1809} 1810}
@@ -1972,7 +1973,6 @@ tunnel_notify_connection_broken (struct MeshTunnel *t, GNUNET_PEER_Id p1,
1972static void 1973static void
1973send_local_ack (struct MeshTunnel *t, 1974send_local_ack (struct MeshTunnel *t,
1974 struct MeshClient *c, 1975 struct MeshClient *c,
1975 uint32_t ack,
1976 int is_fwd) 1976 int is_fwd)
1977{ 1977{
1978 struct GNUNET_MESH_LocalAck msg; 1978 struct GNUNET_MESH_LocalAck msg;
@@ -1980,8 +1980,7 @@ send_local_ack (struct MeshTunnel *t,
1980 msg.header.size = htons (sizeof (msg)); 1980 msg.header.size = htons (sizeof (msg));
1981 msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); 1981 msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK);
1982 msg.tunnel_id = htonl (is_fwd ? t->local_tid : t->local_tid_dest); 1982 msg.tunnel_id = htonl (is_fwd ? t->local_tid : t->local_tid_dest);
1983 msg.ack = htonl (ack); 1983 GNUNET_SERVER_notification_context_unicast (nc,
1984 GNUNET_SERVER_notification_context_unicast(nc,
1985 c->handle, 1984 c->handle,
1986 &msg.header, 1985 &msg.header,
1987 GNUNET_NO); 1986 GNUNET_NO);
@@ -2078,6 +2077,8 @@ tunnel_send_fwd_ack (struct MeshTunnel *t, uint16_t type)
2078 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending ACK, nobuffer\n"); 2077 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending ACK, nobuffer\n");
2079 return; 2078 return;
2080 } 2079 }
2080 if (GNUNET_YES == t->reliable && NULL != t->client)
2081 tunnel_send_fwd_data_ack (t);
2081 break; 2082 break;
2082 case GNUNET_MESSAGE_TYPE_MESH_ACK: 2083 case GNUNET_MESSAGE_TYPE_MESH_ACK:
2083 if (NULL != t->owner && GNUNET_YES == t->reliable) 2084 if (NULL != t->owner && GNUNET_YES == t->reliable)
@@ -2096,11 +2097,12 @@ tunnel_send_fwd_ack (struct MeshTunnel *t, uint16_t type)
2096 } 2097 }
2097 2098
2098 /* Check if we need to transmit the ACK */ 2099 /* Check if we need to transmit the ACK */
2099 if (t->queue_max > t->next_fc.queue_n * 4 && 2100 if (NULL == t->owner &&
2101 t->queue_max > t->next_fc.queue_n * 4 &&
2100 GMC_is_pid_bigger(t->prev_fc.last_ack_sent, t->prev_fc.last_pid_recv) && 2102 GMC_is_pid_bigger(t->prev_fc.last_ack_sent, t->prev_fc.last_pid_recv) &&
2101 GNUNET_NO == t->force_ack) 2103 GNUNET_NO == t->force_ack)
2102 { 2104 {
2103 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending ACK, buffer free\n"); 2105 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending FWD ACK, buffer free\n");
2104 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 2106 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2105 " t->qmax: %u, t->qn: %u\n", 2107 " t->qmax: %u, t->qn: %u\n",
2106 t->queue_max, t->next_fc.queue_n); 2108 t->queue_max, t->next_fc.queue_n);
@@ -2124,7 +2126,7 @@ tunnel_send_fwd_ack (struct MeshTunnel *t, uint16_t type)
2124 2126
2125 t->prev_fc.last_ack_sent = ack; 2127 t->prev_fc.last_ack_sent = ack;
2126 if (NULL != t->owner) 2128 if (NULL != t->owner)
2127 send_local_ack (t, t->owner, ack, GNUNET_YES); 2129 send_local_ack (t, t->owner, GNUNET_YES);
2128 else if (0 != t->prev_hop) 2130 else if (0 != t->prev_hop)
2129 send_ack (t, t->prev_hop, ack); 2131 send_ack (t, t->prev_hop, ack);
2130 else 2132 else
@@ -2196,7 +2198,7 @@ tunnel_send_bck_ack (struct MeshTunnel *t, uint16_t type)
2196 t->next_fc.last_ack_sent = ack; 2198 t->next_fc.last_ack_sent = ack;
2197 2199
2198 if (NULL != t->client) 2200 if (NULL != t->client)
2199 send_local_ack (t, t->client, ack, GNUNET_NO); 2201 send_local_ack (t, t->client, GNUNET_NO);
2200 else if (0 != t->next_hop) 2202 else if (0 != t->next_hop)
2201 send_ack (t, t->next_hop, ack); 2203 send_ack (t, t->next_hop, ack);
2202 else 2204 else
@@ -2206,37 +2208,54 @@ tunnel_send_bck_ack (struct MeshTunnel *t, uint16_t type)
2206 2208
2207 2209
2208/** 2210/**
2209 * Modify the unicast message TID from global to local and send to client. 2211 * Modify the mesh message TID from global to local and send to client.
2210 * 2212 *
2211 * @param t Tunnel on which to send the message. 2213 * @param t Tunnel on which to send the message.
2212 * @param msg Message to modify and send. 2214 * @param msg Message to modify and send.
2215 * @param c Client to send to.
2216 * @param tid Tunnel ID to use (c can be both owner and client).
2213 */ 2217 */
2214static void 2218static void
2215tunnel_send_client_ucast (struct MeshTunnel *t, 2219tunnel_send_client_data (struct MeshTunnel *t,
2216 const struct GNUNET_MESH_Data *msg) 2220 const struct GNUNET_MESH_Data *msg,
2221 struct MeshClient *c, MESH_TunnelNumber tid)
2217{ 2222{
2218 struct GNUNET_MESH_Data *copy; 2223 struct GNUNET_MESH_LocalData *copy;
2219 uint16_t size = ntohs (msg->header.size); 2224 uint16_t size = ntohs (msg->header.size) - sizeof (struct GNUNET_MESH_Data);
2220 char cbuf[size]; 2225 char cbuf[size + sizeof (struct GNUNET_MESH_LocalData)];
2221 2226
2222 if (size < sizeof (struct GNUNET_MESH_Data) + 2227 if (size < sizeof (struct GNUNET_MessageHeader))
2223 sizeof (struct GNUNET_MessageHeader))
2224 { 2228 {
2225 GNUNET_break_op (0); 2229 GNUNET_break_op (0);
2226 return; 2230 return;
2227 } 2231 }
2228 if (NULL == t->client) 2232 if (NULL == c)
2229 { 2233 {
2230 GNUNET_break (0); 2234 GNUNET_break (0);
2231 return; 2235 return;
2232 } 2236 }
2233 copy = (struct GNUNET_MESH_Data *) cbuf; 2237 copy = (struct GNUNET_MESH_LocalData *) cbuf;
2234 memcpy (copy, msg, size); 2238 memcpy (&copy[1], &msg[1], size);
2235 copy->tid = htonl (t->local_tid_dest); 2239 copy->header.size = htons (sizeof (struct GNUNET_MESH_LocalData) + size);
2236 GNUNET_SERVER_notification_context_unicast (nc, t->client->handle, 2240 copy->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA);
2241 copy->tid = htonl (tid);
2242 GNUNET_SERVER_notification_context_unicast (nc, c->handle,
2237 &copy->header, GNUNET_NO); 2243 &copy->header, GNUNET_NO);
2238} 2244}
2239 2245
2246/**
2247 * Modify the unicast message TID from global to local and send to client.
2248 *
2249 * @param t Tunnel on which to send the message.
2250 * @param msg Message to modify and send.
2251 */
2252static void
2253tunnel_send_client_ucast (struct MeshTunnel *t,
2254 const struct GNUNET_MESH_Data *msg)
2255{
2256 tunnel_send_client_data (t, msg, t->client, t->local_tid_dest);
2257}
2258
2240 2259
2241/** 2260/**
2242 * Modify the to_origin message TID from global to local and send to client. 2261 * Modify the to_origin message TID from global to local and send to client.
@@ -2248,26 +2267,7 @@ static void
2248tunnel_send_client_to_orig (struct MeshTunnel *t, 2267tunnel_send_client_to_orig (struct MeshTunnel *t,
2249 const struct GNUNET_MESH_Data *msg) 2268 const struct GNUNET_MESH_Data *msg)
2250{ 2269{
2251 struct GNUNET_MESH_Data *copy; 2270 tunnel_send_client_data (t, msg, t->owner, t->local_tid);
2252 uint16_t size = ntohs (msg->header.size);
2253 char cbuf[size];
2254
2255 if (size < sizeof (struct GNUNET_MESH_Data) +
2256 sizeof (struct GNUNET_MessageHeader))
2257 {
2258 GNUNET_break_op (0);
2259 return;
2260 }
2261 if (NULL == t->owner)
2262 {
2263 GNUNET_break (0);
2264 return;
2265 }
2266 copy = (struct GNUNET_MESH_Data *) cbuf;
2267 memcpy (cbuf, msg, size);
2268 copy->tid = htonl (t->local_tid);
2269 GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle,
2270 &copy->header, GNUNET_NO);
2271} 2271}
2272 2272
2273 2273
@@ -3664,7 +3664,8 @@ handle_mesh_unicast (void *cls, const struct GNUNET_PeerIdentity *peer,
3664 { 3664 {
3665// GNUNET_STATISTICS_update (stats, "# duplicate PID", 1, GNUNET_NO); 3665// GNUNET_STATISTICS_update (stats, "# duplicate PID", 1, GNUNET_NO);
3666 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, 3666 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
3667 " Pid %u not expected, sending FWD ACK!\n", pid); 3667 " Pid %u not expected (%u), sending FWD ACK!\n",
3668 pid, t->prev_fc.last_pid_recv + 1);
3668 tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_DATA_ACK); 3669 tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_DATA_ACK);
3669 } 3670 }
3670 return GNUNET_OK; 3671 return GNUNET_OK;
@@ -4513,24 +4514,25 @@ handle_local_tunnel_destroy (void *cls, struct GNUNET_SERVER_Client *client,
4513 4514
4514 4515
4515/** 4516/**
4516 * Handler for client traffic directed to one peer 4517 * Handler for client traffic
4517 * 4518 *
4518 * @param cls closure 4519 * @param cls closure
4519 * @param client identification of the client 4520 * @param client identification of the client
4520 * @param message the actual message 4521 * @param message the actual message
4521 */ 4522 */
4522static void 4523static void
4523handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client, 4524handle_local_data (void *cls, struct GNUNET_SERVER_Client *client,
4524 const struct GNUNET_MessageHeader *message) 4525 const struct GNUNET_MessageHeader *message)
4525{ 4526{
4527 struct GNUNET_MESH_LocalData *data_msg;
4526 struct MeshClient *c; 4528 struct MeshClient *c;
4527 struct MeshTunnel *t; 4529 struct MeshTunnel *t;
4528 struct GNUNET_MESH_Data *data_msg; 4530 struct MeshFlowControl *fc;
4529 MESH_TunnelNumber tid; 4531 MESH_TunnelNumber tid;
4530 size_t size; 4532 size_t size;
4531 4533
4532 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 4534 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
4533 "Got a unicast request from a client!\n"); 4535 "Got data from a client!\n");
4534 4536
4535 /* Sanity check for client registration */ 4537 /* Sanity check for client registration */
4536 if (NULL == (c = client_get (client))) 4538 if (NULL == (c = client_get (client)))
@@ -4541,12 +4543,11 @@ handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client,
4541 } 4543 }
4542 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); 4544 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id);
4543 4545
4544 data_msg = (struct GNUNET_MESH_Data *) message; 4546 data_msg = (struct GNUNET_MESH_LocalData *) message;
4545 4547
4546 /* Sanity check for message size */ 4548 /* Sanity check for message size */
4547 size = ntohs (message->size); 4549 size = ntohs (message->size) - sizeof (struct GNUNET_MESH_LocalData);
4548 if (sizeof (struct GNUNET_MESH_Data) + 4550 if (size < sizeof (struct GNUNET_MessageHeader))
4549 sizeof (struct GNUNET_MessageHeader) > size)
4550 { 4551 {
4551 GNUNET_break (0); 4552 GNUNET_break (0);
4552 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); 4553 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
@@ -4555,29 +4556,30 @@ handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client,
4555 4556
4556 /* Tunnel exists? */ 4557 /* Tunnel exists? */
4557 tid = ntohl (data_msg->tid); 4558 tid = ntohl (data_msg->tid);
4558 t = tunnel_get_by_local_id (c, tid); 4559 if (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_CLI)
4559 if (NULL == t)
4560 { 4560 {
4561 GNUNET_break (0); 4561 GNUNET_break (0);
4562 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); 4562 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4563 return; 4563 return;
4564 } 4564 }
4565 4565 t = tunnel_get_by_local_id (c, tid);
4566 /* Is it a local tunnel? Then, does client own the tunnel? */ 4566 if (NULL == t)
4567 if (t->owner->handle != client)
4568 { 4567 {
4569 GNUNET_break (0); 4568 GNUNET_break (0);
4570 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); 4569 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4571 return; 4570 return;
4572 } 4571 }
4573 4572
4574 /* PID should be as expected: client<->service communication */ 4573 /* Is the client in the tunnel? */
4575 if (ntohl (data_msg->pid) != t->prev_fc.last_pid_recv + 1) 4574 if ( !( (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV &&
4575 t->owner &&
4576 t->owner->handle == client)
4577 ||
4578 (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV &&
4579 t->client &&
4580 t->client->handle == client) ) )
4576 { 4581 {
4577 GNUNET_break (0); 4582 GNUNET_break (0);
4578 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
4579 "Unicast PID, expected %u, got %u\n",
4580 t->prev_fc.last_pid_recv + 1, ntohl (data_msg->pid));
4581 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); 4583 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4582 return; 4584 return;
4583 } 4585 }
@@ -4587,14 +4589,18 @@ handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client,
4587 */ 4589 */
4588 { 4590 {
4589 struct GNUNET_MESH_Data *payload; 4591 struct GNUNET_MESH_Data *payload;
4592 char cbuf[sizeof(struct GNUNET_MESH_Data) + size];
4590 4593
4594 fc = tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV ? &t->prev_fc : &t->next_fc;
4591 if (GNUNET_YES == t->reliable) 4595 if (GNUNET_YES == t->reliable)
4592 { 4596 {
4593 struct MeshSentMessage *copy; 4597 struct MeshSentMessage *copy;
4594 4598
4595 copy = GNUNET_malloc (sizeof (struct MeshSentMessage) + size); 4599 copy = GNUNET_malloc (sizeof (struct MeshSentMessage)
4600 + sizeof(struct GNUNET_MESH_Data)
4601 + size);
4596 copy->t = t; 4602 copy->t = t;
4597 copy->id = ntohl (data_msg->pid); 4603 copy->id = fc->last_pid_recv + 1;
4598 copy->is_forward = GNUNET_YES; 4604 copy->is_forward = GNUNET_YES;
4599 copy->retry_timer = GNUNET_TIME_UNIT_MINUTES; 4605 copy->retry_timer = GNUNET_TIME_UNIT_MINUTES;
4600 copy->retry_task = GNUNET_SCHEDULER_add_delayed (copy->retry_timer, 4606 copy->retry_task = GNUNET_SCHEDULER_add_delayed (copy->retry_timer,
@@ -4616,152 +4622,25 @@ handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client,
4616 } 4622 }
4617 else 4623 else
4618 { 4624 {
4619 static struct GNUNET_MESH_Data data_message; 4625 payload = (struct GNUNET_MESH_Data *) cbuf;
4620 payload = &data_message;
4621 } 4626 }
4622 memcpy (payload, data_msg, size); 4627 memcpy (&payload[1], &data_msg[1], size);
4623 payload->oid = my_full_id; 4628 payload->header.size = htons (sizeof (struct GNUNET_MESH_Data) + size);
4629 payload->header.type = htons (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV ?
4630 GNUNET_MESSAGE_TYPE_MESH_UNICAST :
4631 GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN);
4632 GNUNET_PEER_resolve(t->id.oid, &payload->oid);;
4624 payload->tid = htonl (t->id.tid); 4633 payload->tid = htonl (t->id.tid);
4625 payload->ttl = htonl (default_ttl); 4634 payload->ttl = htonl (default_ttl);
4635 payload->pid = htonl (fc->last_pid_recv + 1);
4626 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 4636 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
4627 " calling generic handler...\n"); 4637 " calling generic handler...\n");
4628 handle_mesh_unicast (NULL, &my_full_id, &payload->header); 4638 if (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV)
4629 } 4639 handle_mesh_unicast (NULL, &my_full_id, &payload->header);
4630 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "receive done OK\n");
4631 GNUNET_SERVER_receive_done (client, GNUNET_OK);
4632
4633 return;
4634}
4635
4636
4637/**
4638 * Handler for client traffic directed to the origin
4639 *
4640 * @param cls closure
4641 * @param client identification of the client
4642 * @param message the actual message
4643 */
4644static void
4645handle_local_to_origin (void *cls, struct GNUNET_SERVER_Client *client,
4646 const struct GNUNET_MessageHeader *message)
4647{
4648 struct GNUNET_MESH_Data *data_msg;
4649 struct MeshFlowControl *fc;
4650 struct MeshClient *c;
4651 struct MeshTunnel *t;
4652 MESH_TunnelNumber tid;
4653 size_t size;
4654
4655 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
4656 "Got a ToOrigin request from a client!\n");
4657 /* Sanity check for client registration */
4658 if (NULL == (c = client_get (client)))
4659 {
4660 GNUNET_break (0);
4661 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4662 return;
4663 }
4664 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id);
4665
4666 data_msg = (struct GNUNET_MESH_Data *) message;
4667
4668 /* Sanity check for message size */
4669 size = ntohs (message->size);
4670 if (sizeof (struct GNUNET_MESH_Data) +
4671 sizeof (struct GNUNET_MessageHeader) > size)
4672 {
4673 GNUNET_break (0);
4674 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4675 return;
4676 }
4677
4678 /* Tunnel exists? */
4679 tid = ntohl (data_msg->tid);
4680 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tid);
4681 if (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV)
4682 {
4683 GNUNET_break (0);
4684 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4685 return;
4686 }
4687 t = tunnel_get_by_local_id (c, tid);
4688 if (NULL == t)
4689 {
4690 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tunnel %X unknown.\n", tid);
4691 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " for client %u.\n", c->id);
4692 GNUNET_break (0);
4693 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4694 return;
4695 }
4696
4697 /* It should be sent by someone who has this as incoming tunnel. */
4698 if (t->client != c)
4699 {
4700 GNUNET_break (0);
4701 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4702 return;
4703 }
4704
4705 /* PID should be as expected */
4706 fc = &t->next_fc;
4707 if (ntohl (data_msg->pid) != fc->last_pid_recv + 1)
4708 {
4709 GNUNET_break (0);
4710 GNUNET_log (GNUNET_ERROR_TYPE_WARNING,
4711 "To Origin PID, expected %u, got %u\n",
4712 fc->last_pid_recv + 1,
4713 ntohl (data_msg->pid));
4714 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4715 return;
4716 }
4717
4718 /* Ok, everything is correct, send the message
4719 * (pretend we got it from a mesh peer)
4720 */
4721 {
4722 struct GNUNET_MESH_Data *payload;
4723
4724 if (GNUNET_YES == t->reliable)
4725 {
4726 struct MeshSentMessage *copy;
4727
4728 copy = GNUNET_malloc (sizeof (struct MeshSentMessage) + size);
4729 copy->t = t;
4730 copy->id = ntohl (data_msg->pid);
4731 copy->is_forward = GNUNET_NO;
4732 copy->retry_timer = GNUNET_TIME_UNIT_MINUTES;
4733 copy->retry_task = GNUNET_SCHEDULER_add_delayed (copy->retry_timer,
4734 &tunnel_retransmit_message,
4735 copy);
4736 if (GNUNET_OK !=
4737 GNUNET_CONTAINER_multihashmap32_put (t->sent_messages_bck,
4738 copy->id,
4739 copy,
4740 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST))
4741 {
4742 GNUNET_break (0);
4743 GNUNET_SCHEDULER_cancel (copy->retry_task);
4744 GNUNET_free (copy);
4745 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
4746 return;
4747 }
4748 payload = (struct GNUNET_MESH_Data *) &copy[1];
4749 }
4750 else 4640 else
4751 { 4641 handle_mesh_to_orig (NULL, &my_full_id, &payload->header);
4752 static struct GNUNET_MESH_Data data_message;
4753 payload = &data_message;
4754 }
4755
4756 memcpy (payload, data_msg, size);
4757 GNUNET_PEER_resolve (t->id.oid, &payload->oid);
4758 payload->tid = htonl (t->id.tid);
4759 payload->ttl = htonl (default_ttl);
4760
4761 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
4762 " calling generic handler...\n");
4763 handle_mesh_to_orig (NULL, &my_full_id, &payload->header);
4764 } 4642 }
4643 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "receive done OK\n");
4765 GNUNET_SERVER_receive_done (client, GNUNET_OK); 4644 GNUNET_SERVER_receive_done (client, GNUNET_OK);
4766 4645
4767 return; 4646 return;
@@ -4783,7 +4662,6 @@ handle_local_ack (void *cls, struct GNUNET_SERVER_Client *client,
4783 struct MeshTunnel *t; 4662 struct MeshTunnel *t;
4784 struct MeshClient *c; 4663 struct MeshClient *c;
4785 MESH_TunnelNumber tid; 4664 MESH_TunnelNumber tid;
4786 uint32_t ack;
4787 4665
4788 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a local ACK\n"); 4666 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a local ACK\n");
4789 /* Sanity check for client registration */ 4667 /* Sanity check for client registration */
@@ -4810,20 +4688,17 @@ handle_local_ack (void *cls, struct GNUNET_SERVER_Client *client,
4810 return; 4688 return;
4811 } 4689 }
4812 4690
4813 ack = ntohl (msg->ack);
4814 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ack %u\n", ack);
4815
4816 /* Does client own tunnel? I.E: Is this an ACK for BCK traffic? */ 4691 /* Does client own tunnel? I.E: Is this an ACK for BCK traffic? */
4817 if (t->owner == c) 4692 if (t->owner == c)
4818 { 4693 {
4819 /* The client owns the tunnel, ACK is for data to_origin, send BCK ACK. */ 4694 /* The client owns the tunnel, ACK is for data to_origin, send BCK ACK. */
4820 t->prev_fc.last_ack_recv = ack; 4695 t->prev_fc.last_ack_recv++;
4821 tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); 4696 tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK);
4822 } 4697 }
4823 else 4698 else
4824 { 4699 {
4825 /* The client doesn't own the tunnel, this ACK is for FWD traffic. */ 4700 /* The client doesn't own the tunnel, this ACK is for FWD traffic. */
4826 t->next_fc.last_ack_recv = ack; 4701 t->next_fc.last_ack_recv++;
4827 tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); 4702 tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK);
4828 } 4703 }
4829 4704
@@ -4975,10 +4850,8 @@ static struct GNUNET_SERVER_MessageHandler client_handlers[] = {
4975 {&handle_local_tunnel_destroy, NULL, 4850 {&handle_local_tunnel_destroy, NULL,
4976 GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY, 4851 GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY,
4977 sizeof (struct GNUNET_MESH_TunnelMessage)}, 4852 sizeof (struct GNUNET_MESH_TunnelMessage)},
4978 {&handle_local_unicast, NULL, 4853 {&handle_local_data, NULL,
4979 GNUNET_MESSAGE_TYPE_MESH_UNICAST, 0}, 4854 GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA, 0},
4980 {&handle_local_to_origin, NULL,
4981 GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN, 0},
4982 {&handle_local_ack, NULL, 4855 {&handle_local_ack, NULL,
4983 GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK, 4856 GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK,
4984 sizeof (struct GNUNET_MESH_LocalAck)}, 4857 sizeof (struct GNUNET_MESH_LocalAck)},
diff --git a/src/mesh/mesh.h b/src/mesh/mesh.h
index 90502b00b..803bf9033 100644
--- a/src/mesh/mesh.h
+++ b/src/mesh/mesh.h
@@ -197,6 +197,27 @@ struct GNUNET_MESH_TunnelNotification
197 197
198 198
199/** 199/**
200 * Message for mesh data traffic.
201 */
202struct GNUNET_MESH_LocalData
203{
204 /**
205 * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA
206 */
207 struct GNUNET_MessageHeader header;
208
209 /**
210 * TID of the tunnel
211 */
212 uint32_t tid GNUNET_PACKED;
213
214 /**
215 * Payload follows
216 */
217};
218
219
220/**
200 * Message to allow the client send more data to the service 221 * Message to allow the client send more data to the service
201 * (always service -> client). 222 * (always service -> client).
202 */ 223 */
@@ -212,10 +233,6 @@ struct GNUNET_MESH_LocalAck
212 */ 233 */
213 MESH_TunnelNumber tunnel_id GNUNET_PACKED; 234 MESH_TunnelNumber tunnel_id GNUNET_PACKED;
214 235
215 /**
216 * ID of the last packet allowed.
217 */
218 uint32_t ack GNUNET_PACKED;
219}; 236};
220 237
221 238
diff --git a/src/mesh/mesh_api.c b/src/mesh/mesh_api.c
index 09cf67163..b4d319e58 100644
--- a/src/mesh/mesh_api.c
+++ b/src/mesh/mesh_api.c
@@ -304,24 +304,10 @@ struct GNUNET_MESH_Tunnel
304 int reliable; 304 int reliable;
305 305
306 /** 306 /**
307 * Maximum allowed PID to send (last ACK recevied). 307 * Are we allowed to send to the service?
308 */ 308 */
309 uint32_t last_ack_recv; 309 int allow_send;
310 310
311 /**
312 * Last PID received from the service.
313 */
314 uint32_t last_pid_recv;
315
316 /**
317 * Last packet ID sent to the service.
318 */
319 uint32_t last_pid_sent;
320
321 /**
322 * Last ACK value sent to the service: how much are we willing to accept?
323 */
324 uint32_t last_ack_sent;
325}; 311};
326 312
327 313
@@ -402,10 +388,9 @@ message_ready_size (struct GNUNET_MESH_Handle *h)
402 LOG (GNUNET_ERROR_TYPE_DEBUG, "# message internal\n"); 388 LOG (GNUNET_ERROR_TYPE_DEBUG, "# message internal\n");
403 return th->size; 389 return th->size;
404 } 390 }
405 if (GNUNET_YES == GMC_is_pid_bigger(t->last_ack_recv, t->last_pid_sent)) 391 if (GNUNET_YES == t->allow_send)
406 { 392 {
407 LOG (GNUNET_ERROR_TYPE_DEBUG, "# message payload ok (%u =< %u)\n", 393 LOG (GNUNET_ERROR_TYPE_DEBUG, "# message payload ok\n");
408 t->last_pid_sent + 1, t->last_ack_recv);
409 return th->size; 394 return th->size;
410 } 395 }
411 } 396 }
@@ -463,10 +448,7 @@ create_tunnel (struct GNUNET_MESH_Handle *h, MESH_TunnelNumber tid)
463 { 448 {
464 t->tid = tid; 449 t->tid = tid;
465 } 450 }
466 t->last_ack_recv = (uint32_t) -1; 451 t->allow_send = GNUNET_NO;
467 t->last_pid_recv = (uint32_t) -1;
468 t->last_ack_sent = (uint32_t) -1;
469 t->last_pid_sent = (uint32_t) -1;
470 t->buffering = GNUNET_YES; 452 t->buffering = GNUNET_YES;
471 return t; 453 return t;
472} 454}
@@ -610,14 +592,10 @@ send_ack (struct GNUNET_MESH_Tunnel *t)
610{ 592{
611 struct GNUNET_MESH_LocalAck msg; 593 struct GNUNET_MESH_LocalAck msg;
612 594
613 t->last_ack_sent = t->last_pid_recv + 1; 595 LOG (GNUNET_ERROR_TYPE_DEBUG, "Sending ACK on tunnel %X\n", t->tid);
614 LOG (GNUNET_ERROR_TYPE_DEBUG,
615 "Sending ACK on tunnel %X: %u\n",
616 t->tid, t->last_ack_sent);
617 msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); 596 msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK);
618 msg.header.size = htons (sizeof (msg)); 597 msg.header.size = htons (sizeof (msg));
619 msg.tunnel_id = htonl (t->tid); 598 msg.tunnel_id = htonl (t->tid);
620 msg.ack = htonl (t->last_ack_sent);
621 599
622#if DEBUG_ACK 600#if DEBUG_ACK
623 t->mesh->acks_sent++; 601 t->mesh->acks_sent++;
@@ -744,10 +722,7 @@ do_reconnect (struct GNUNET_MESH_Handle *h)
744 */ 722 */
745 continue; 723 continue;
746 } 724 }
747 t->last_ack_sent = (uint32_t) -1; 725 t->allow_send = GNUNET_NO;
748 t->last_pid_sent = (uint32_t) -1;
749 t->last_ack_recv = (uint32_t) -1;
750 t->last_pid_recv = (uint32_t) -1;
751 tmsg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE); 726 tmsg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE);
752 tmsg.header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage)); 727 tmsg.header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage));
753 tmsg.tunnel_id = htonl (t->tid); 728 tmsg.tunnel_id = htonl (t->tid);
@@ -831,7 +806,7 @@ process_tunnel_created (struct GNUNET_MESH_Handle *h,
831 if (NULL != h->new_tunnel) 806 if (NULL != h->new_tunnel)
832 { 807 {
833 t = create_tunnel (h, tid); 808 t = create_tunnel (h, tid);
834 t->last_ack_sent = 0; 809 t->allow_send = GNUNET_NO;
835 t->peer = GNUNET_PEER_intern (&msg->peer); 810 t->peer = GNUNET_PEER_intern (&msg->peer);
836 t->mesh = h; 811 t->mesh = h;
837 t->tid = tid; 812 t->tid = tid;
@@ -907,50 +882,28 @@ process_incoming_data (struct GNUNET_MESH_Handle *h,
907 const struct GNUNET_MESH_MessageHandler *handler; 882 const struct GNUNET_MESH_MessageHandler *handler;
908 const struct GNUNET_PeerIdentity *peer; 883 const struct GNUNET_PeerIdentity *peer;
909 struct GNUNET_PeerIdentity id; 884 struct GNUNET_PeerIdentity id;
910 struct GNUNET_MESH_Data *dmsg; 885 struct GNUNET_MESH_LocalData *dmsg;
911 struct GNUNET_MESH_Tunnel *t; 886 struct GNUNET_MESH_Tunnel *t;
912 unsigned int i; 887 unsigned int i;
913 uint32_t pid;
914 uint16_t type; 888 uint16_t type;
915 889
916 LOG (GNUNET_ERROR_TYPE_DEBUG, "Got a data message!\n"); 890 LOG (GNUNET_ERROR_TYPE_DEBUG, "Got a data message!\n");
917 type = ntohs (message->type); 891
918 switch (type) 892 dmsg = (struct GNUNET_MESH_LocalData *) message;
919 { 893
920 case GNUNET_MESSAGE_TYPE_MESH_UNICAST: 894 t = retrieve_tunnel (h, ntohl (dmsg->tid));
921 case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: 895 payload = (struct GNUNET_MessageHeader *) &dmsg[1];
922 dmsg = (struct GNUNET_MESH_Data *) message; 896 GNUNET_PEER_resolve (t->peer, &id);
923 897 peer = &id;
924 t = retrieve_tunnel (h, ntohl (dmsg->tid)); 898 LOG (GNUNET_ERROR_TYPE_DEBUG, " %s data on tunnel %s [%X]\n",
925 payload = (struct GNUNET_MessageHeader *) &dmsg[1]; 899 t->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV ? "fwd" : "bck",
926 GNUNET_PEER_resolve (t->peer, &id); 900 GNUNET_i2s (peer), ntohl (dmsg->tid));
927 peer = &id;
928 pid = ntohl (dmsg->pid);
929 LOG (GNUNET_ERROR_TYPE_DEBUG, " %s data on tunnel %s [%X]\n",
930 type == GNUNET_MESSAGE_TYPE_MESH_UNICAST ? "fwd" : "bck",
931 GNUNET_i2s (peer), ntohl (dmsg->tid));
932 break;
933 default:
934 GNUNET_break (0);
935 return;
936 }
937 LOG (GNUNET_ERROR_TYPE_DEBUG, " pid %u\n", pid);
938 if (NULL == t) 901 if (NULL == t)
939 { 902 {
940 /* Tunnel was ignored/destroyed, probably service didn't get it yet */ 903 /* Tunnel was ignored/destroyed, probably service didn't get it yet */
941 LOG (GNUNET_ERROR_TYPE_DEBUG, " ignored!\n"); 904 LOG (GNUNET_ERROR_TYPE_DEBUG, " ignored!\n");
942 return; 905 return;
943 } 906 }
944 if (GNUNET_YES ==
945 GMC_is_pid_bigger(pid, t->last_ack_sent))
946 {
947 GNUNET_break (0);
948 LOG (GNUNET_ERROR_TYPE_DEBUG,
949 " unauthorized message! (%u, ACK %u)\n",
950 pid, t->last_ack_sent);
951 // FIXME fc what now? accept? reject?
952 }
953 t->last_pid_recv = pid;
954 type = ntohs (payload->type); 907 type = ntohs (payload->type);
955 for (i = 0; i < h->n_handlers; i++) 908 for (i = 0; i < h->n_handlers; i++)
956 { 909 {
@@ -988,7 +941,6 @@ process_ack (struct GNUNET_MESH_Handle *h,
988 struct GNUNET_MESH_LocalAck *msg; 941 struct GNUNET_MESH_LocalAck *msg;
989 struct GNUNET_MESH_Tunnel *t; 942 struct GNUNET_MESH_Tunnel *t;
990 MESH_TunnelNumber tid; 943 MESH_TunnelNumber tid;
991 uint32_t ack;
992 944
993 LOG (GNUNET_ERROR_TYPE_DEBUG, "Got an ACK!\n"); 945 LOG (GNUNET_ERROR_TYPE_DEBUG, "Got an ACK!\n");
994 h->acks_recv++; 946 h->acks_recv++;
@@ -1000,15 +952,11 @@ process_ack (struct GNUNET_MESH_Handle *h,
1000 LOG (GNUNET_ERROR_TYPE_WARNING, "ACK on unknown tunnel %X\n", tid); 952 LOG (GNUNET_ERROR_TYPE_WARNING, "ACK on unknown tunnel %X\n", tid);
1001 return; 953 return;
1002 } 954 }
1003 ack = ntohl (msg->ack); 955 LOG (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X!\n", t->tid);
1004 LOG (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X, ack %u!\n", t->tid, ack); 956 t->allow_send = GNUNET_YES;
1005 if (GNUNET_YES == GMC_is_pid_bigger(ack, t->last_ack_recv))
1006 t->last_ack_recv = ack;
1007 else
1008 return;
1009 if (NULL == h->th && 0 < t->packet_size) 957 if (NULL == h->th && 0 < t->packet_size)
1010 { 958 {
1011 LOG (GNUNET_ERROR_TYPE_DEBUG, " tmt rdy was NULL, requesting!\n", t->tid, ack); 959 LOG (GNUNET_ERROR_TYPE_DEBUG, " tmt rdy was NULL, requesting!\n");
1012 h->th = 960 h->th =
1013 GNUNET_CLIENT_notify_transmit_ready (h->client, t->packet_size, 961 GNUNET_CLIENT_notify_transmit_ready (h->client, t->packet_size,
1014 GNUNET_TIME_UNIT_FOREVER_REL, 962 GNUNET_TIME_UNIT_FOREVER_REL,
@@ -1135,8 +1083,7 @@ msg_received (void *cls, const struct GNUNET_MessageHeader *msg)
1135 process_tunnel_destroy (h, (struct GNUNET_MESH_TunnelMessage *) msg); 1083 process_tunnel_destroy (h, (struct GNUNET_MESH_TunnelMessage *) msg);
1136 break; 1084 break;
1137 /* Notify of a new data packet in the tunnel */ 1085 /* Notify of a new data packet in the tunnel */
1138 case GNUNET_MESSAGE_TYPE_MESH_UNICAST: 1086 case GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA:
1139 case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN:
1140 process_incoming_data (h, msg); 1087 process_incoming_data (h, msg);
1141 break; 1088 break;
1142 case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK: 1089 case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK:
@@ -1211,46 +1158,35 @@ send_callback (void *cls, size_t size, void *buf)
1211 t = th->tunnel; 1158 t = th->tunnel;
1212 if (GNUNET_YES == th_is_payload (th)) 1159 if (GNUNET_YES == th_is_payload (th))
1213 { 1160 {
1214 struct GNUNET_MESH_Data *dmsg; 1161 struct GNUNET_MESH_LocalData *dmsg;
1215 struct GNUNET_MessageHeader *mh; 1162 struct GNUNET_MessageHeader *mh;
1216 1163
1217 LOG (GNUNET_ERROR_TYPE_DEBUG, "# payload\n"); 1164 LOG (GNUNET_ERROR_TYPE_DEBUG, "# payload\n");
1218 if (GNUNET_NO == GMC_is_pid_bigger (t->last_ack_recv, t->last_pid_sent)) 1165 if (GNUNET_NO == t->allow_send)
1219 { 1166 {
1220 /* This tunnel is not ready to transmit yet, try next message */ 1167 /* This tunnel is not ready to transmit yet, try next message */
1221 next = th->next; 1168 next = th->next;
1222 continue; 1169 continue;
1223 } 1170 }
1224 t->packet_size = 0; 1171 t->packet_size = 0;
1172 t->allow_send = GNUNET_NO;
1225 GNUNET_assert (size >= th->size); 1173 GNUNET_assert (size >= th->size);
1226 dmsg = (struct GNUNET_MESH_Data *) cbuf; 1174 dmsg = (struct GNUNET_MESH_LocalData *) cbuf;
1227 mh = (struct GNUNET_MessageHeader *) &dmsg[1]; 1175 mh = (struct GNUNET_MessageHeader *) &dmsg[1];
1228 psize = th->notify (th->notify_cls, 1176 psize = th->notify (th->notify_cls,
1229 size - sizeof (struct GNUNET_MESH_Data), 1177 size - sizeof (struct GNUNET_MESH_LocalData),
1230 mh); 1178 mh);
1231 if (psize > 0) 1179 if (psize > 0)
1232 { 1180 {
1233 psize += sizeof (struct GNUNET_MESH_Data); 1181 psize += sizeof (struct GNUNET_MESH_LocalData);
1234 GNUNET_assert (size >= psize); 1182 GNUNET_assert (size >= psize);
1235 dmsg->header.size = htons (psize); 1183 dmsg->header.size = htons (psize);
1236 dmsg->tid = htonl (t->tid); 1184 dmsg->tid = htonl (t->tid);
1237 dmsg->pid = htonl (t->last_pid_sent + 1);
1238 dmsg->ttl = 0;
1239 memset (&dmsg->oid, 0, sizeof (struct GNUNET_PeerIdentity));
1240 t->last_pid_sent++;
1241 }
1242 if (t->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV)
1243 {
1244 dmsg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN);
1245 LOG (GNUNET_ERROR_TYPE_DEBUG, "# to origin, type %s\n",
1246 GNUNET_MESH_DEBUG_M2S (ntohs (mh->type)));
1247 }
1248 else
1249 {
1250 dmsg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_UNICAST);
1251 LOG (GNUNET_ERROR_TYPE_DEBUG, "# unicast, type %s\n",
1252 GNUNET_MESH_DEBUG_M2S (ntohs (mh->type)));
1253 } 1185 }
1186 dmsg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA);
1187 LOG (GNUNET_ERROR_TYPE_DEBUG, "# payload type %s\n",
1188 GNUNET_MESH_DEBUG_M2S (ntohs (mh->type)));
1189
1254 } 1190 }
1255 else 1191 else
1256 { 1192 {
@@ -1491,7 +1427,7 @@ GNUNET_MESH_tunnel_create (struct GNUNET_MESH_Handle *h,
1491 msg.port = htonl (port); 1427 msg.port = htonl (port);
1492 msg.peer = *peer; 1428 msg.peer = *peer;
1493 msg.options = 0; 1429 msg.options = 0;
1494 t->last_ack_sent = 0; 1430 t->allow_send = 0;
1495 send_packet (h, &msg.header, t); 1431 send_packet (h, &msg.header, t);
1496 return t; 1432 return t;
1497} 1433}
@@ -1575,6 +1511,7 @@ GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork,
1575 GNUNET_assert (NULL != tunnel); 1511 GNUNET_assert (NULL != tunnel);
1576 LOG (GNUNET_ERROR_TYPE_DEBUG, "MESH NOTIFY TRANSMIT READY\n"); 1512 LOG (GNUNET_ERROR_TYPE_DEBUG, "MESH NOTIFY TRANSMIT READY\n");
1577 LOG (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tunnel->tid); 1513 LOG (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tunnel->tid);
1514 LOG (GNUNET_ERROR_TYPE_DEBUG, " allow_send %d\n", tunnel->allow_send);
1578 if (tunnel->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) 1515 if (tunnel->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV)
1579 LOG (GNUNET_ERROR_TYPE_DEBUG, " to origin\n"); 1516 LOG (GNUNET_ERROR_TYPE_DEBUG, " to origin\n");
1580 else 1517 else
@@ -1585,7 +1522,7 @@ GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork,
1585 th = GNUNET_malloc (sizeof (struct GNUNET_MESH_TransmitHandle)); 1522 th = GNUNET_malloc (sizeof (struct GNUNET_MESH_TransmitHandle));
1586 th->tunnel = tunnel; 1523 th->tunnel = tunnel;
1587 th->timeout = GNUNET_TIME_relative_to_absolute (maxdelay); 1524 th->timeout = GNUNET_TIME_relative_to_absolute (maxdelay);
1588 th->size = notify_size + sizeof (struct GNUNET_MESH_Data); 1525 th->size = notify_size + sizeof (struct GNUNET_MESH_LocalData);
1589 tunnel->packet_size = th->size; 1526 tunnel->packet_size = th->size;
1590 LOG (GNUNET_ERROR_TYPE_DEBUG, " total size %u\n", th->size); 1527 LOG (GNUNET_ERROR_TYPE_DEBUG, " total size %u\n", th->size);
1591 th->notify = notify; 1528 th->notify = notify;
@@ -1593,7 +1530,7 @@ GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork,
1593 add_to_queue (tunnel->mesh, th); 1530 add_to_queue (tunnel->mesh, th);
1594 if (NULL != tunnel->mesh->th) 1531 if (NULL != tunnel->mesh->th)
1595 return th; 1532 return th;
1596 if (!GMC_is_pid_bigger (tunnel->last_ack_recv, tunnel->last_pid_sent)) 1533 if (GNUNET_NO == tunnel->allow_send)
1597 return th; 1534 return th;
1598 LOG (GNUNET_ERROR_TYPE_DEBUG, " call client notify tmt rdy\n"); 1535 LOG (GNUNET_ERROR_TYPE_DEBUG, " call client notify tmt rdy\n");
1599 tunnel->mesh->th = 1536 tunnel->mesh->th =
diff --git a/src/mesh/mesh_common.c b/src/mesh/mesh_common.c
index 697fadd91..c9082b70b 100644
--- a/src/mesh/mesh_common.c
+++ b/src/mesh/mesh_common.c
@@ -136,6 +136,11 @@ GNUNET_MESH_DEBUG_M2S (uint16_t m)
136 case 274: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY"; 136 case 274: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY";
137 137
138 /** 138 /**
139 * Local payload traffic
140 */
141 case 275: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_DATA";
142
143 /**
139 * Local ACK for data. 144 * Local ACK for data.
140 */ 145 */
141 case 286: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK"; 146 case 286: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK";