diff options
author | Christian Grothoff <christian@grothoff.org> | 2017-01-26 18:34:29 +0100 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2017-01-26 18:34:29 +0100 |
commit | 6adc64ee122e9be37c6b83e9b745719b4d5940b8 (patch) | |
tree | aecaf99f25c4630c07573b7b34472fcf67c4d636 /src/cadet | |
parent | 356cd09ec4f7d2c02300d5eae8bec8e6b8e49635 (diff) | |
download | gnunet-6adc64ee122e9be37c6b83e9b745719b4d5940b8.tar.gz gnunet-6adc64ee122e9be37c6b83e9b745719b4d5940b8.zip |
implement random packet drop option, fix retransmission logic
Diffstat (limited to 'src/cadet')
-rw-r--r-- | src/cadet/gnunet-service-cadet-new.c | 22 | ||||
-rw-r--r-- | src/cadet/gnunet-service-cadet-new.h | 5 | ||||
-rw-r--r-- | src/cadet/gnunet-service-cadet-new_channel.c | 29 | ||||
-rw-r--r-- | src/cadet/gnunet-service-cadet-new_peer.c | 55 | ||||
-rw-r--r-- | src/cadet/gnunet-service-cadet-new_tunnels.c | 11 |
5 files changed, 100 insertions, 22 deletions
diff --git a/src/cadet/gnunet-service-cadet-new.c b/src/cadet/gnunet-service-cadet-new.c index f24c9f518..d40d4f10e 100644 --- a/src/cadet/gnunet-service-cadet-new.c +++ b/src/cadet/gnunet-service-cadet-new.c | |||
@@ -188,6 +188,11 @@ struct GNUNET_TIME_Relative ratchet_time; | |||
188 | */ | 188 | */ |
189 | struct GNUNET_TIME_Relative keepalive_period; | 189 | struct GNUNET_TIME_Relative keepalive_period; |
190 | 190 | ||
191 | /** | ||
192 | * Set to non-zero values to create random drops to test retransmissions. | ||
193 | */ | ||
194 | unsigned long long drop_percent; | ||
195 | |||
191 | 196 | ||
192 | /** | 197 | /** |
193 | * Send a message to a client. | 198 | * Send a message to a client. |
@@ -1352,7 +1357,22 @@ run (void *cls, | |||
1352 | "need delay value"); | 1357 | "need delay value"); |
1353 | keepalive_period = GNUNET_TIME_UNIT_MINUTES; | 1358 | keepalive_period = GNUNET_TIME_UNIT_MINUTES; |
1354 | } | 1359 | } |
1355 | 1360 | if (GNUNET_OK != | |
1361 | GNUNET_CONFIGURATION_get_value_number (c, | ||
1362 | "CADET", | ||
1363 | "DROP_PERCENT", | ||
1364 | &drop_percent)) | ||
1365 | { | ||
1366 | drop_percent = 0; | ||
1367 | } | ||
1368 | else | ||
1369 | { | ||
1370 | LOG (GNUNET_ERROR_TYPE_WARNING, "**************************************\n"); | ||
1371 | LOG (GNUNET_ERROR_TYPE_WARNING, "Cadet is running with DROP enabled.\n"); | ||
1372 | LOG (GNUNET_ERROR_TYPE_WARNING, "This is NOT a good idea!\n"); | ||
1373 | LOG (GNUNET_ERROR_TYPE_WARNING, "Remove DROP_PERCENT from config file.\n"); | ||
1374 | LOG (GNUNET_ERROR_TYPE_WARNING, "**************************************\n"); | ||
1375 | } | ||
1356 | my_private_key = GNUNET_CRYPTO_eddsa_key_create_from_configuration (c); | 1376 | my_private_key = GNUNET_CRYPTO_eddsa_key_create_from_configuration (c); |
1357 | if (NULL == my_private_key) | 1377 | if (NULL == my_private_key) |
1358 | { | 1378 | { |
diff --git a/src/cadet/gnunet-service-cadet-new.h b/src/cadet/gnunet-service-cadet-new.h index 721044ac4..dff0d3c8c 100644 --- a/src/cadet/gnunet-service-cadet-new.h +++ b/src/cadet/gnunet-service-cadet-new.h | |||
@@ -235,6 +235,11 @@ extern struct GNUNET_TIME_Relative keepalive_period; | |||
235 | */ | 235 | */ |
236 | extern int shutting_down; | 236 | extern int shutting_down; |
237 | 237 | ||
238 | /** | ||
239 | * Set to non-zero values to create random drops to test retransmissions. | ||
240 | */ | ||
241 | extern unsigned long long drop_percent; | ||
242 | |||
238 | 243 | ||
239 | /** | 244 | /** |
240 | * Send a message to a client. | 245 | * Send a message to a client. |
diff --git a/src/cadet/gnunet-service-cadet-new_channel.c b/src/cadet/gnunet-service-cadet-new_channel.c index e55a9a77d..a923f19dc 100644 --- a/src/cadet/gnunet-service-cadet-new_channel.c +++ b/src/cadet/gnunet-service-cadet-new_channel.c | |||
@@ -1190,6 +1190,8 @@ GCCH_handle_channel_plaintext_data (struct CadetChannel *ch, | |||
1190 | 1, | 1190 | 1, |
1191 | GNUNET_NO); | 1191 | GNUNET_NO); |
1192 | GNUNET_MQ_discard (env); | 1192 | GNUNET_MQ_discard (env); |
1193 | if (GNUNET_YES == ch->reliable) | ||
1194 | send_channel_data_ack (ch); | ||
1193 | return; | 1195 | return; |
1194 | } | 1196 | } |
1195 | 1197 | ||
@@ -1348,16 +1350,38 @@ GCCH_handle_channel_plaintext_data_ack (struct CadetChannel *ch, | |||
1348 | crmn = crm->next; | 1350 | crmn = crm->next; |
1349 | if (ack->mid.mid == crm->data_message->mid.mid) | 1351 | if (ack->mid.mid == crm->data_message->mid.mid) |
1350 | { | 1352 | { |
1353 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
1354 | "Got DATA_ACK with base %u matching message %u on %s\n", | ||
1355 | (unsigned int) mid_base, | ||
1356 | ntohl (crm->data_message->mid.mid), | ||
1357 | GCCH_2s (ch)); | ||
1351 | handle_matching_ack (ch, | 1358 | handle_matching_ack (ch, |
1352 | crm); | 1359 | crm); |
1353 | found = GNUNET_YES; | 1360 | found = GNUNET_YES; |
1354 | continue; | 1361 | continue; |
1355 | } | 1362 | } |
1356 | delta = (unsigned int) (ntohl (crm->data_message->mid.mid) - mid_base) - 1; | 1363 | delta = (unsigned int) (ntohl (crm->data_message->mid.mid) - mid_base) - 1; |
1364 | if (delta >= UINT_MAX - ch->max_pending_messages) | ||
1365 | { | ||
1366 | /* overflow, means crm was way in the past, so this ACK counts for it. */ | ||
1367 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
1368 | "Got DATA_ACK with base %u past %u on %s\n", | ||
1369 | (unsigned int) mid_base, | ||
1370 | ntohl (crm->data_message->mid.mid), | ||
1371 | GCCH_2s (ch)); | ||
1372 | handle_matching_ack (ch, | ||
1373 | crm); | ||
1374 | found = GNUNET_YES; | ||
1375 | continue; | ||
1376 | } | ||
1357 | if (delta >= 64) | 1377 | if (delta >= 64) |
1358 | continue; | 1378 | continue; |
1359 | if (0 != (mid_mask & (1LLU << delta))) | 1379 | if (0 != (mid_mask & (1LLU << delta))) |
1360 | { | 1380 | { |
1381 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
1382 | "Got DATA_ACK with mask for %u on %s\n", | ||
1383 | ntohl (crm->data_message->mid.mid), | ||
1384 | GCCH_2s (ch)); | ||
1361 | handle_matching_ack (ch, | 1385 | handle_matching_ack (ch, |
1362 | crm); | 1386 | crm); |
1363 | found = GNUNET_YES; | 1387 | found = GNUNET_YES; |
@@ -1498,9 +1522,8 @@ data_sent_cb (void *cls) | |||
1498 | GCCH_2s (ch), | 1522 | GCCH_2s (ch), |
1499 | GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_remaining (ch->head_sent->next_retry), | 1523 | GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_remaining (ch->head_sent->next_retry), |
1500 | GNUNET_YES)); | 1524 | GNUNET_YES)); |
1501 | if (crm == ch->head_sent) | 1525 | if (NULL == ch->head_sent->qe) |
1502 | { | 1526 | { |
1503 | /* We are the new head, need to reschedule retry task */ | ||
1504 | if (NULL != ch->retry_data_task) | 1527 | if (NULL != ch->retry_data_task) |
1505 | GNUNET_SCHEDULER_cancel (ch->retry_data_task); | 1528 | GNUNET_SCHEDULER_cancel (ch->retry_data_task); |
1506 | ch->retry_data_task | 1529 | ch->retry_data_task |
@@ -1698,7 +1721,7 @@ GCCH_handle_local_ack (struct CadetChannel *ch, | |||
1698 | } | 1721 | } |
1699 | 1722 | ||
1700 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 1723 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1701 | "Got LOCAL ACK, passing payload message %u to %s-%X on %s\n", | 1724 | "Got LOCAL_ACK, passing payload message %u to %s-%X on %s\n", |
1702 | ntohl (com->mid.mid), | 1725 | ntohl (com->mid.mid), |
1703 | GSC_2s (ccc->c), | 1726 | GSC_2s (ccc->c), |
1704 | ntohl (ccc->ccn.channel_of_client), | 1727 | ntohl (ccc->ccn.channel_of_client), |
diff --git a/src/cadet/gnunet-service-cadet-new_peer.c b/src/cadet/gnunet-service-cadet-new_peer.c index fe40d76b6..97bb1378e 100644 --- a/src/cadet/gnunet-service-cadet-new_peer.c +++ b/src/cadet/gnunet-service-cadet-new_peer.c | |||
@@ -503,6 +503,34 @@ GCP_set_mq (struct CadetPeer *cp, | |||
503 | 503 | ||
504 | 504 | ||
505 | /** | 505 | /** |
506 | * Debug function should NEVER return true in production code, useful to | ||
507 | * simulate losses for testcases. | ||
508 | * | ||
509 | * @return #GNUNET_YES or #GNUNET_NO with the decision to drop. | ||
510 | */ | ||
511 | static int | ||
512 | should_I_drop (void) | ||
513 | { | ||
514 | if (0 == drop_percent) | ||
515 | return GNUNET_NO; | ||
516 | if (GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, | ||
517 | 101) < drop_percent) | ||
518 | return GNUNET_YES; | ||
519 | return GNUNET_NO; | ||
520 | } | ||
521 | |||
522 | |||
523 | /** | ||
524 | * Function called when CORE took one of the messages from | ||
525 | * a message queue manager and transmitted it. | ||
526 | * | ||
527 | * @param cls the `struct CadetPeeer` where we made progress | ||
528 | */ | ||
529 | static void | ||
530 | mqm_send_done (void *cls); | ||
531 | |||
532 | |||
533 | /** | ||
506 | * Transmit current envelope from this @a mqm. | 534 | * Transmit current envelope from this @a mqm. |
507 | * | 535 | * |
508 | * @param mqm mqm to transmit message for now | 536 | * @param mqm mqm to transmit message for now |
@@ -512,10 +540,6 @@ mqm_execute (struct GCP_MessageQueueManager *mqm) | |||
512 | { | 540 | { |
513 | struct CadetPeer *cp = mqm->cp; | 541 | struct CadetPeer *cp = mqm->cp; |
514 | 542 | ||
515 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
516 | "Sending to peer %s from MQM %p\n", | ||
517 | GCP_2s (cp), | ||
518 | mqm); | ||
519 | /* Move entry to the end of the DLL, to be fair. */ | 543 | /* Move entry to the end of the DLL, to be fair. */ |
520 | if (mqm != cp->mqm_tail) | 544 | if (mqm != cp->mqm_tail) |
521 | { | 545 | { |
@@ -526,10 +550,27 @@ mqm_execute (struct GCP_MessageQueueManager *mqm) | |||
526 | cp->mqm_tail, | 550 | cp->mqm_tail, |
527 | mqm); | 551 | mqm); |
528 | } | 552 | } |
529 | GNUNET_MQ_send (cp->core_mq, | ||
530 | mqm->env); | ||
531 | mqm->env = NULL; | ||
532 | cp->mqm_ready_counter--; | 553 | cp->mqm_ready_counter--; |
554 | if (GNUNET_YES == should_I_drop ()) | ||
555 | { | ||
556 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
557 | "DROPPING message to peer %s from MQM %p\n", | ||
558 | GCP_2s (cp), | ||
559 | mqm); | ||
560 | GNUNET_MQ_discard (mqm->env); | ||
561 | mqm->env = NULL; | ||
562 | mqm_send_done (cp); | ||
563 | } | ||
564 | else | ||
565 | { | ||
566 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
567 | "Sending to peer %s from MQM %p\n", | ||
568 | GCP_2s (cp), | ||
569 | mqm); | ||
570 | GNUNET_MQ_send (cp->core_mq, | ||
571 | mqm->env); | ||
572 | mqm->env = NULL; | ||
573 | } | ||
533 | mqm->cb (mqm->cb_cls, | 574 | mqm->cb (mqm->cb_cls, |
534 | GNUNET_YES); | 575 | GNUNET_YES); |
535 | } | 576 | } |
diff --git a/src/cadet/gnunet-service-cadet-new_tunnels.c b/src/cadet/gnunet-service-cadet-new_tunnels.c index 03067a605..592a8c683 100644 --- a/src/cadet/gnunet-service-cadet-new_tunnels.c +++ b/src/cadet/gnunet-service-cadet-new_tunnels.c | |||
@@ -361,17 +361,6 @@ struct CadetTunnel | |||
361 | */ | 361 | */ |
362 | struct CadetTunnelQueueEntry *tq_tail; | 362 | struct CadetTunnelQueueEntry *tq_tail; |
363 | 363 | ||
364 | |||
365 | /** | ||
366 | * Ephemeral message in the queue (to avoid queueing more than one). | ||
367 | */ | ||
368 | struct CadetConnectionQueue *ephm_hKILL; | ||
369 | |||
370 | /** | ||
371 | * Pong message in the queue. | ||
372 | */ | ||
373 | struct CadetConnectionQueue *pong_hKILL; | ||
374 | |||
375 | /** | 364 | /** |
376 | * How long do we wait until we retry the KX? | 365 | * How long do we wait until we retry the KX? |
377 | */ | 366 | */ |