GNUnet 0.22.0
gnunet-communicator-udp.c
Go to the documentation of this file.
1/*
2 This file is part of GNUnet
3 Copyright (C) 2010-2014, 2018, 2019 GNUnet e.V.
4
5 GNUnet is free software: you can redistribute it and/or modify it
6 under the terms of the GNU Affero General Public License as published
7 by the Free Software Foundation, either version 3 of the License,
8 or (at your 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 Affero General Public License for more details.
14 :
15 You should have received a copy of the GNU Affero General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>.
17
18 SPDX-License-Identifier: AGPL3.0-or-later
19 */
20
40#include "platform.h"
41#include "gnunet_common.h"
42#include "gnunet_util_lib.h"
43#include "gnunet_protocols.h"
44#include "gnunet_signatures.h"
45#include "gnunet_constants.h"
46#include "gnunet_nat_service.h"
50
54#define DEFAULT_REKEY_TIME_INTERVAL GNUNET_TIME_UNIT_DAYS
55
59#define PROTO_QUEUE_TIMEOUT GNUNET_TIME_UNIT_MINUTES
60
64#define BROADCAST_FREQUENCY GNUNET_TIME_UNIT_MINUTES
65
69#define INTERFACE_SCAN_FREQUENCY \
70 GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 5)
71
76#define ADDRESS_VALIDITY_PERIOD GNUNET_TIME_UNIT_HOURS
77
78#define WORKING_QUEUE_INTERVALL \
79 GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MICROSECONDS,1)
80
84#define AES_KEY_SIZE (256 / 8)
85
89#define AES_IV_SIZE (96 / 8)
90
94#define GCM_TAG_SIZE (128 / 8)
95
96#define GENERATE_AT_ONCE 64
97
107#define KCN_THRESHOLD 96
108
115#define KCN_TARGET 128
116
126#define MAX_SQN_DELTA 160
127
137#define MAX_SECRETS 256
138
143#define DEFAULT_REKEY_MAX_BYTES (1024LLU * 1024 * 1024 * 4LLU)
144
149#define COMMUNICATOR_ADDRESS_PREFIX "udp"
150
154#define COMMUNICATOR_CONFIG_SECTION "communicator-udp"
155
157
158
165{
170
175
180
185
191};
192
193
199{
204
210
211};
212
213
219{
224
229
235
236 /* followed by messages */
237
238 /* padding may follow actual messages */
239};
240
241
246struct UDPAck
247{
252
258
263};
264
265
275{
280
285
290};
291
292
300{
305
311};
312
313
318struct UDPBox
319{
328
337
338};
339
344{
349
354};
355
357
361struct SharedSecret;
362
363
369{
374
379
388
393
398};
399
400
405struct SenderAddress;
406
411struct ReceiverAddress;
412
417{
422
427
432
437
442
447
452
457
463
470
474 unsigned int active_kce_count;
475
480
485
490};
491
492
498{
503
508
513
518
522 struct sockaddr *address;
523
527 socklen_t address_len;
528
533
538
542 unsigned int num_secrets;
543
548 unsigned int acks_available;
549
554
559
564
569
574};
575
576
582{
587
592
597
602
607
612
618
622 struct sockaddr *address;
623
627 socklen_t address_len;
628
633
638
643
648
653
658
664
669
673 size_t kx_mtu;
674
678 size_t d_mtu;
679
683 unsigned int num_secrets;
684
689 unsigned int acks_available;
690
695
700};
701
706{
711
716
721
725 struct sockaddr *sa;
726
730 struct sockaddr *ba;
731
736
741 struct ipv6_mreq mcreq;
742
746 socklen_t salen;
747
751 int found;
752};
753
758
762static unsigned long long rekey_max_bytes;
763
768
773
778
783
788
793
798
803
808
813
818
823
828
832static int have_v6_socket;
833
838
843
848
852static const struct GNUNET_CONFIGURATION_Handle *cfg;
853
858
863
867static struct GNUNET_NAT_Handle *nat;
868
872static uint16_t my_port;
873
878
882static int disable_v6;
883
885
886
887static void
890{
892 key.type = htonl (GNUNET_PUBLIC_KEY_TYPE_EDDSA);
893 key.eddsa_key = *edpk;
895}
896
897
898static void
901{
903 key.type = htonl (GNUNET_PUBLIC_KEY_TYPE_EDDSA);
904 key.eddsa_key = *edpk;
906}
907
908
914static void
916{
917 if (AF_INET6 == bi->sa->sa_family)
918 {
919 /* Leave the multicast group */
921 IPPROTO_IPV6,
922 IPV6_LEAVE_GROUP,
923 &bi->mcreq,
924 sizeof(bi->mcreq)))
925 {
927 }
928 }
931 GNUNET_free (bi->sa);
932 GNUNET_free (bi->ba);
933 GNUNET_free (bi);
934}
935
936
937static int
938secret_destroy (struct SharedSecret *ss);
939
945static void
947{
948 struct SharedSecret *ss;
949 receiver->receiver_destroy_called = GNUNET_YES;
950
952 "Disconnecting receiver for peer `%s'\n",
953 GNUNET_i2s (&receiver->target));
954 if (NULL != receiver->kx_qh)
955 {
957 receiver->kx_qh = NULL;
958 receiver->kx_mq = NULL;
959 }
960 if (NULL != receiver->d_qh)
961 {
963 receiver->d_qh = NULL;
964 }
965 else if (NULL != receiver->d_mq)
966 {
968 receiver->d_mq = NULL;
969 }
970 if (NULL != receiver->udp_sock)
971 {
974 receiver->udp_sock = NULL;
975 }
978 &receiver->key,
979 receiver));
982 "# receivers active",
984 GNUNET_NO);
985 while (NULL != (ss = receiver->ss_head))
986 {
987 secret_destroy (ss);
988 }
989 GNUNET_free (receiver->address);
990 GNUNET_free (receiver->foreign_addr);
992}
993
994
1000static void
1002{
1003 struct SharedSecret *ss = kce->ss;
1004
1005 ss->active_kce_count--;
1008 &kce->kid,
1009 kce));
1010 GNUNET_free (kce);
1011}
1012
1013
1021static void
1022get_kid (const struct GNUNET_ShortHashCode *msec,
1023 uint32_t serial,
1024 struct GNUNET_ShortHashCode *kid)
1025{
1026 uint32_t sid = htonl (serial);
1027 struct GNUNET_ShortHashCode prk;
1029 &sid, sizeof (sid),
1030 msec, sizeof (*msec));
1031
1033 sizeof(*kid),
1034 &prk,
1035 "gnunet-communicator-udp-kid",
1036 strlen ("gnunet-communicator-udp-kid"),
1037 NULL,
1038 0);
1039}
1040
1041
1048static void
1049kce_generate (struct SharedSecret *ss, uint32_t seq)
1050{
1051 struct KeyCacheEntry *kce;
1052
1053 GNUNET_assert (0 < seq);
1054 kce = GNUNET_new (struct KeyCacheEntry);
1055 kce->ss = ss;
1056 kce->sequence_number = seq;
1057 get_kid (&ss->master, seq, &kce->kid);
1062 key_cache,
1063 &kce->kid,
1064 kce,
1067 "# KIDs active",
1069 GNUNET_NO);
1070}
1071
1072
1079static int
1081{
1082 struct SenderAddress *sender;
1083 struct ReceiverAddress *receiver;
1084 struct KeyCacheEntry *kce;
1085
1087 "secret %s destroy %u\n",
1088 GNUNET_sh2s (&ss->master),
1090 if (NULL != (sender = ss->sender))
1091 {
1092 GNUNET_CONTAINER_DLL_remove (sender->ss_head, sender->ss_tail, ss);
1093 sender->num_secrets--;
1095 "%u sender->num_secrets %u allowed %u used, %u available\n",
1097 sender->acks_available);
1099 if (NULL != ss->sender->kce_task)
1100 {
1102 ss->sender->kce_task = NULL;
1103 }
1104 }
1105 if (NULL != (receiver = ss->receiver))
1106 {
1107 GNUNET_CONTAINER_DLL_remove (receiver->ss_head, receiver->ss_tail, ss);
1108 receiver->num_secrets--;
1109 receiver->acks_available -= (ss->sequence_allowed - ss->sequence_used);
1111 "%u receiver->num_secrets\n",
1112 receiver->num_secrets);
1113 }
1114 while (NULL != (kce = ss->kce_head))
1115 kce_destroy (kce);
1116 GNUNET_STATISTICS_update (stats, "# Secrets active", -1, GNUNET_NO);
1118 "# KIDs active",
1120 GNUNET_NO);
1121 GNUNET_free (ss);
1122 return GNUNET_YES;
1123}
1124
1125
1132static void
1134{
1135 struct SharedSecret *ss;
1138 GNUNET_YES ==
1142 "# senders active",
1144 GNUNET_NO);
1145 while (NULL != (ss = sender->ss_head))
1146 {
1147 secret_destroy (ss);
1148 }
1151}
1152
1153
1162static void
1164 uint32_t serial,
1165 char key[AES_KEY_SIZE],
1166 char iv[AES_IV_SIZE])
1167{
1168 uint32_t sid = htonl (serial);
1169
1172 msec,
1173 "gnunet-communicator-udp-key",
1174 strlen ("gnunet-communicator-udp-key"),
1175 &sid, sizeof (sid),
1176 NULL,
1177 0);
1180 msec,
1181 "gnunet-communicator-udp-iv",
1182 strlen ("gnunet-communicator-udp-iv"),
1183 &sid, sizeof (sid),
1184 NULL,
1185 0);
1186}
1187
1188
1194static void
1196{
1197 sender->timeout =
1200}
1201
1202
1208static void
1210{
1211 receiver->timeout =
1214 receiver->timeout.abs_value_us);
1215}
1216
1217
1223static void
1225{
1226 struct GNUNET_TIME_Relative st;
1227 struct GNUNET_TIME_Relative rt;
1228 struct GNUNET_TIME_Relative delay;
1229 struct ReceiverAddress *receiver;
1230 struct SenderAddress *sender;
1231
1232 (void) cls;
1233 timeout_task = NULL;
1236 {
1238 if (0 != rt.rel_value_us)
1239 break;
1241 "Receiver timed out\n");
1243 }
1245 while (NULL != (sender = GNUNET_CONTAINER_heap_peek (senders_heap)))
1246 {
1247 if (GNUNET_YES != sender->sender_destroy_called)
1248 {
1250 if (0 != st.rel_value_us)
1251 break;
1252 sender_destroy (sender);
1253 }
1254 }
1255 delay = GNUNET_TIME_relative_min (rt, st);
1256 if (delay.rel_value_us < GNUNET_TIME_UNIT_FOREVER_REL.rel_value_us)
1258}
1259
1260
1266static void
1268{
1270 sizeof(ss->cmac),
1271 &ss->master,
1272 "gnunet-communicator-udp-cmac",
1273 strlen ("gnunet-communicator-udp-cmac"),
1274 NULL,
1275 0);
1276}
1277
1278
1287static void
1289 const void *plaintext,
1290 size_t plaintext_len)
1291{
1292 const struct GNUNET_MessageHeader *hdr = plaintext;
1293 const char *pos = plaintext;
1294
1295 while (ntohs (hdr->size) <= plaintext_len)
1296 {
1298 "# bytes given to core",
1299 ntohs (hdr->size),
1300 GNUNET_NO);
1302 "Giving %u bytes to TNG\n", ntohs (hdr->size));
1305 &sender->target,
1306 hdr,
1308 NULL /* no flow control possible */
1309 ,
1310 NULL));
1311 /* move on to next message, if any */
1312 plaintext_len -= ntohs (hdr->size);
1313 if (plaintext_len < sizeof(*hdr))
1314 break;
1315 pos += ntohs (hdr->size);
1316 hdr = (const struct GNUNET_MessageHeader *) pos;
1317 // TODO for now..., we do not actually sen >1msg or have a way of telling
1318 // if we are done
1319 break;
1320 }
1322 "# bytes padding discarded",
1323 plaintext_len,
1324 GNUNET_NO);
1325}
1326
1327
1336static void
1338 uint32_t serial,
1339 gcry_cipher_hd_t *cipher)
1340{
1341 char key[AES_KEY_SIZE];
1342 char iv[AES_IV_SIZE];
1343 int rc;
1344
1345 GNUNET_assert (0 ==
1346 gcry_cipher_open (cipher,
1347 GCRY_CIPHER_AES256 /* low level: go for speed */
1348 ,
1349 GCRY_CIPHER_MODE_GCM,
1350 0 /* flags */));
1351 get_iv_key (msec, serial, key, iv);
1352 rc = gcry_cipher_setkey (*cipher, key, sizeof(key));
1353 GNUNET_assert ((0 == rc) || ((char) rc == GPG_ERR_WEAK_KEY));
1354 rc = gcry_cipher_setiv (*cipher, iv, sizeof(iv));
1355 GNUNET_assert ((0 == rc) || ((char) rc == GPG_ERR_WEAK_KEY));
1356}
1357
1358
1371static int
1372try_decrypt (const struct SharedSecret *ss,
1373 const uint8_t *tag,
1374 uint32_t serial,
1375 const char *in_buf,
1376 size_t in_buf_size,
1377 char *out_buf)
1378{
1379 gcry_cipher_hd_t cipher;
1380
1381 setup_cipher (&ss->master, serial, &cipher);
1383 0 ==
1384 gcry_cipher_decrypt (cipher, out_buf, in_buf_size, in_buf, in_buf_size));
1385 if (0 != gcry_cipher_checktag (cipher, tag, GCM_TAG_SIZE))
1386 {
1387 gcry_cipher_close (cipher);
1389 "# AEAD authentication failures",
1390 1,
1391 GNUNET_NO);
1392 return GNUNET_SYSERR;
1393 }
1394 gcry_cipher_close (cipher);
1395 return GNUNET_OK;
1396}
1397
1398
1405static struct SharedSecret *
1407 )
1408{
1409 struct SharedSecret *ss;
1410
1411 ss = GNUNET_new (struct SharedSecret);
1413 calculate_cmac (ss);
1414 return ss;
1415}
1416
1417
1424static struct SharedSecret *
1427{
1428 struct SharedSecret *ss;
1429
1430 ss = GNUNET_new (struct SharedSecret);
1432 &ss->master);
1434 "New receiver SS master: %s\n", GNUNET_sh2s (&ss->master));
1435 calculate_cmac (ss);
1436 return ss;
1437}
1438
1439
1447static struct SharedSecret *
1449 ,
1450 struct ReceiverAddress *receiver)
1451{
1452 struct SharedSecret *ss;
1453
1454 ss = GNUNET_new (struct SharedSecret);
1455 GNUNET_CRYPTO_eddsa_kem_encaps (&receiver->target.public_key, ephemeral,
1456 &ss->master);
1457 calculate_cmac (ss);
1458 ss->receiver = receiver;
1459 GNUNET_CONTAINER_DLL_insert (receiver->ss_head, receiver->ss_tail, ss);
1460 receiver->num_secrets++;
1461 GNUNET_STATISTICS_update (stats, "# Secrets active", 1, GNUNET_NO);
1462 return ss;
1463}
1464
1465
1473static struct SharedSecret *
1476 struct ReceiverAddress *receiver)
1477{
1478 struct SharedSecret *ss;
1479
1480 ss = GNUNET_new (struct SharedSecret);
1482 c, &ss->master);
1484 "New sender SS master: %s\n", GNUNET_sh2s (&ss->master));
1485 calculate_cmac (ss);
1486 ss->receiver = receiver;
1487 GNUNET_CONTAINER_DLL_insert (receiver->ss_head, receiver->ss_tail, ss);
1488 receiver->num_secrets++;
1489 GNUNET_STATISTICS_update (stats, "# Secrets active", 1, GNUNET_NO);
1490 return ss;
1491}
1492
1493
1501static void
1503
1504
1512static unsigned int
1513purge_secrets (struct SharedSecret *ss_list_tail)
1514{
1515 struct SharedSecret *pos;
1516 struct SharedSecret *ss_to_purge;
1517 unsigned int deleted = 0;
1518
1520 "Purging secrets.\n");
1521 pos = ss_list_tail;
1522 while (NULL != pos)
1523 {
1524 ss_to_purge = pos;
1525 pos = pos->prev;
1526
1527 // FIXME we may also want to purge old unacked.
1528 if (rekey_max_bytes <= ss_to_purge->bytes_sent)
1529 {
1530 secret_destroy (ss_to_purge);
1531 deleted++;
1532 }
1533 }
1535 "Finished purging all, deleted %u.\n", deleted);
1536 return deleted;
1537}
1538
1539
1540static void
1541add_acks (struct SharedSecret *ss, int acks_to_add)
1542{
1543
1544 struct ReceiverAddress *receiver = ss->receiver;
1545
1546 GNUNET_assert (NULL != ss);
1547 GNUNET_assert (NULL != receiver);
1548
1549 if (NULL == receiver->d_qh)
1550 {
1551 receiver->d_qh =
1553 &receiver->target,
1554 receiver->foreign_addr,
1555 receiver->d_mtu,
1556 acks_to_add,
1557 1, /* Priority */
1558 receiver->nt,
1560 receiver->d_mq);
1561 }
1562 else
1563 {
1565 receiver->d_qh,
1566 acks_to_add,
1567 1);
1568 }
1569
1571 "Tell transport we have %u more acks!\n",
1572 acks_to_add);
1573
1574 // Until here for alternative 1
1575
1576 /* move ss to head to avoid discarding it anytime soon! */
1577
1578 // GNUNET_CONTAINER_DLL_remove (receiver->ss_head, receiver->ss_tail, ss);
1579 // GNUNET_CONTAINER_DLL_insert (receiver->ss_head, receiver->ss_tail, ss);
1580}
1581
1582
1593static int
1594handle_ack (void *cls, const struct GNUNET_HashCode *key, void *value)
1595{
1596 const struct UDPAck *ack = cls;
1597 struct ReceiverAddress *receiver = value;
1598 uint32_t acks_to_add;
1599 uint32_t allowed;
1600
1602 "in handle ack with cmac %s\n",
1603 GNUNET_h2s (&ack->cmac));
1604
1605 (void) key;
1606 for (struct SharedSecret *ss = receiver->ss_head; NULL != ss; ss = ss->next)
1607 {
1608 if (0 == memcmp (&ack->cmac, &ss->cmac, sizeof(struct GNUNET_HashCode)))
1609 {
1610
1612 "Found matching cmac\n");
1613
1614 allowed = ntohl (ack->sequence_ack);
1615
1616 if (allowed <= ss->sequence_allowed)
1617 {
1619 "Ignoring ack, not giving us increased window\n.");
1620 return GNUNET_NO;
1621 }
1622 acks_to_add = (allowed - ss->sequence_allowed);
1623 GNUNET_assert (0 != acks_to_add);
1624 receiver->acks_available += (allowed - ss->sequence_allowed);
1625 ss->sequence_allowed = allowed;
1626 add_acks (ss, acks_to_add);
1628 "New sequence allows until %u (+%u). Acks available to us: %u. For secret %s\n",
1629 allowed,
1630 acks_to_add,
1631 receiver->acks_available,
1632 GNUNET_sh2s (&ss->master));
1633 return GNUNET_NO;
1634 }
1635 }
1637 "Matching cmac not found for ack!\n");
1638 return GNUNET_YES;
1639}
1640
1641
1650static void
1652{
1653 struct UDPAck ack;
1654 GNUNET_assert (NULL != ss->sender);
1656 "Considering SS UDPAck %s\n",
1657 GNUNET_i2s_full (&ss->sender->target));
1658
1660 "Sender has %u acks available.\n",
1661 ss->sender->acks_available);
1662 /* drop ancient KeyCacheEntries */
1663 while ((NULL != ss->kce_head) &&
1664 (MAX_SQN_DELTA <
1666 kce_destroy (ss->kce_tail);
1667
1668
1670 ack.header.size = htons (sizeof(ack));
1671 ack.sequence_ack = htonl (ss->sequence_allowed);
1672 ack.cmac = ss->cmac;
1674 "Notifying transport with UDPAck %s, sequence %u and master %s\n",
1676 ss->sequence_allowed,
1677 GNUNET_sh2s (&(ss->master)));
1679 &ss->sender->target,
1681 &ack.header);
1682}
1683
1684
1685static void
1687{
1688 struct SharedSecret *ss = cls;
1689 ss->sender->kce_task = NULL;
1690
1692 "Precomputing %u keys for master %s\n",
1694 GNUNET_sh2s (&ss->master));
1695 if ((ss->override_available_acks != GNUNET_YES) &&
1696 (KCN_TARGET < ss->sender->acks_available))
1697 return;
1698 for (int i = 0; i < GENERATE_AT_ONCE; i++)
1699 kce_generate (ss, ++ss->sequence_allowed);
1700
1705 if (KCN_TARGET > ss->sender->acks_available)
1706 {
1710 ss);
1711 return;
1712 }
1714 "We have enough keys (ACKs: %u).\n", ss->sender->acks_available);
1718 consider_ss_ack (ss);
1719}
1720
1721
1730static void
1732 const void *buf,
1733 size_t buf_size)
1734{
1735 const struct GNUNET_MessageHeader *hdr;
1736 const struct UDPAck *ack;
1737 const struct UDPRekey *rekey;
1738 struct SharedSecret *ss_rekey;
1739 const char *buf_pos = buf;
1740 size_t bytes_remaining = buf_size;
1741 uint16_t type;
1742
1743 hdr = (struct GNUNET_MessageHeader*) buf_pos;
1744 if (sizeof(*hdr) > bytes_remaining)
1745 {
1746 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Plaintext too short, dropping...\n");
1747 return; /* no data left */
1748 }
1750 "try_handle_plaintext of size %llu (%u %lu) and type %u\n",
1751 (unsigned long long) bytes_remaining,
1752 ntohs (hdr->size),
1753 sizeof(*hdr),
1754 ntohs (hdr->type));
1755 if (ntohs (hdr->size) > bytes_remaining)
1756 return; /* buffer too short for indicated message length */
1757 type = ntohs (hdr->type);
1758 switch (type)
1759 {
1761 rekey = (struct UDPRekey*) buf_pos;
1762 ss_rekey = setup_shared_secret_dec (&rekey->ephemeral);
1763 ss_rekey->sender = sender;
1764 GNUNET_CONTAINER_DLL_insert (sender->ss_head, sender->ss_tail, ss_rekey);
1765 sender->num_secrets++;
1767 "Received rekey secret with cmac %s\n",
1768 GNUNET_h2s (&(ss_rekey->cmac)));
1770 "Received secret with master %s.\n",
1771 GNUNET_sh2s (&(ss_rekey->master)));
1773 "We have %u sequence_allowed.\n",
1774 ss_rekey->sequence_allowed);
1776 "We have a sender %p\n",
1777 ss_rekey->sender);
1779 "We have %u acks available.\n",
1780 ss_rekey->sender->acks_available);
1782 "# rekeying successful",
1783 1,
1784 GNUNET_NO);
1787 // FIXME
1788 kce_generate_cb (ss_rekey);
1789 /* ss_rekey->sender->kce_task = GNUNET_SCHEDULER_add_delayed (
1790 WORKING_QUEUE_INTERVALL,
1791 kce_generate_cb,
1792 ss_rekey);*/
1793 // FIXME: Theoretically, this could be an Ack
1794 buf_pos += ntohs (hdr->size);
1795 bytes_remaining -= ntohs (hdr->size);
1796 pass_plaintext_to_core (sender, buf_pos, bytes_remaining);
1797 if (0 == purge_secrets (sender->ss_tail))
1798 {
1799 // No secret purged. Delete oldest.
1800 if (sender->num_secrets > MAX_SECRETS)
1801 {
1802 secret_destroy (sender->ss_tail);
1803 }
1804 }
1805 break;
1807 /* lookup master secret by 'cmac', then update sequence_max */
1808 ack = (struct UDPAck*) buf_pos;
1810 &sender->key,
1811 &handle_ack,
1812 (void *) ack);
1813 /* There could be more messages after the ACK, handle those as well */
1814 buf_pos += ntohs (hdr->size);
1815 bytes_remaining -= ntohs (hdr->size);
1816 pass_plaintext_to_core (sender, buf_pos, bytes_remaining);
1817 break;
1818
1820 /* skip padding */
1821 break;
1822
1823 default:
1824 pass_plaintext_to_core (sender, buf_pos, bytes_remaining);
1825 }
1826 return;
1827}
1828
1829
1837static void
1838decrypt_box (const struct UDPBox *box,
1839 size_t box_len,
1840 struct KeyCacheEntry *kce)
1841{
1842 struct SharedSecret *ss = kce->ss;
1843 struct SharedSecret *ss_c = ss->sender->ss_tail;
1844 struct SharedSecret *ss_tmp;
1845 int ss_destroyed = 0;
1846 char out_buf[box_len - sizeof(*box)];
1847
1848 GNUNET_assert (NULL != ss->sender);
1849 if (GNUNET_OK != try_decrypt (ss,
1850 box->gcm_tag,
1851 kce->sequence_number,
1852 (const char *) &box[1],
1853 sizeof(out_buf),
1854 out_buf))
1855 {
1856 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed decryption.\n");
1858 "# Decryption failures with valid KCE",
1859 1,
1860 GNUNET_NO);
1861 kce_destroy (kce);
1862 ss->sender->acks_available--;
1863 return;
1864 }
1865 kce_destroy (kce);
1866 kce = NULL;
1867 ss->bytes_sent += box_len;
1868 ss->sender->acks_available--;
1869 ss->sequence_used++;
1871 "# bytes decrypted with BOX",
1872 sizeof(out_buf),
1873 GNUNET_NO);
1875 "# messages decrypted with BOX",
1876 1,
1877 GNUNET_NO);
1879 "decrypted UDPBox with kid %s\n",
1880 GNUNET_sh2s (&box->kid));
1881 try_handle_plaintext (ss->sender, out_buf, sizeof(out_buf));
1882
1883 while (NULL != ss_c)
1884 {
1885 if (ss_c->bytes_sent >= rekey_max_bytes)
1886 {
1888 "Removing SS because rekey bytes reached.\n");
1889 ss_tmp = ss_c->prev;
1890 if (ss == ss_c)
1891 ss_destroyed = 1;
1892 secret_destroy (ss_c);
1893 ss_c = ss_tmp;
1894 continue;
1895 }
1896 ss_c = ss_c->prev;
1897 }
1898 if (1 == ss_destroyed)
1899 return;
1901 "Sender has %u ack left.\n",
1902 ss->sender->acks_available);
1903 if ((KCN_THRESHOLD > ss->sender->acks_available) &&
1904 (NULL == ss->sender->kce_task) &&
1906 {
1908 "Sender has %u ack left which is under threshold.\n",
1909 ss->sender->acks_available);
1913 ss);
1914 }
1915}
1916
1917
1922{
1926 const struct sockaddr *address;
1927
1931 socklen_t address_len;
1932
1937};
1938
1939
1951static struct SenderAddress *
1953 const struct sockaddr *address,
1954 socklen_t address_len)
1955{
1956 struct SenderAddress *sender;
1957 struct GNUNET_HashContext *hsh;
1958 struct GNUNET_HashCode sender_key;
1959
1961 GNUNET_CRYPTO_hash_context_read (hsh, address, address_len);
1962 GNUNET_CRYPTO_hash_context_read (hsh, target, sizeof(*target));
1963 GNUNET_CRYPTO_hash_context_finish (hsh, &sender_key);
1964
1965 sender = GNUNET_CONTAINER_multihashmap_get (senders, &sender_key);
1966 if (NULL != sender)
1967 {
1969 return sender;
1970 }
1971 sender = GNUNET_new (struct SenderAddress);
1972 sender->key = sender_key;
1973 sender->target = *target;
1974 sender->address = GNUNET_memdup (address, address_len);
1975 sender->address_len = address_len;
1977 senders,
1978 &sender->key,
1979 sender,
1982 "# senders active",
1984 GNUNET_NO);
1985 sender->timeout =
1988 sender,
1989 sender->timeout.abs_value_us);
1990 sender->nt = GNUNET_NT_scanner_get_type (is, address, address_len);
1991 if (NULL == timeout_task)
1993 return sender;
1994}
1995
1996
2004static int
2006 const struct UDPConfirmation *uc)
2007{
2008 struct UdpHandshakeSignature uhs;
2009
2010 uhs.purpose.purpose = htonl (
2012 uhs.purpose.size = htonl (sizeof(uhs));
2013 uhs.sender = uc->sender;
2014 uhs.receiver = my_identity;
2015 uhs.enc = *enc;
2016 uhs.monotonic_time = uc->monotonic_time;
2019 &uhs,
2020 &uc->sender_sig,
2021 &uc->sender.public_key);
2022}
2023
2024
2033static char *
2034sockaddr_to_udpaddr_string (const struct sockaddr *address,
2035 socklen_t address_len)
2036{
2037 char *ret;
2038
2039 switch (address->sa_family)
2040 {
2041 case AF_INET:
2043 "%s-%s",
2045 GNUNET_a2s (address, address_len));
2046 break;
2047
2048 case AF_INET6:
2050 "%s-%s",
2052 GNUNET_a2s (address, address_len));
2053 break;
2054
2055 default:
2056 GNUNET_assert (0);
2057 }
2058 return ret;
2059}
2060
2061
2062static struct GNUNET_NETWORK_Handle *
2064{
2066
2067 if (NULL == receiver->udp_sock)
2069 else
2070 udp_sock = receiver->udp_sock;
2071
2072 return udp_sock;
2073}
2074
2075
2083static struct sockaddr *
2084udp_address_to_sockaddr (const char *bindto, socklen_t *sock_len)
2085{
2086 struct sockaddr *in;
2087 unsigned int port;
2088 char dummy[2];
2089 char *colon;
2090 char *cp;
2091
2092 if (1 == sscanf (bindto, "%u%1s", &port, dummy))
2093 {
2094 /* interpreting value as just a PORT number */
2095 if (port > UINT16_MAX)
2096 {
2098 "BINDTO specification `%s' invalid: value too large for port\n",
2099 bindto);
2100 return NULL;
2101 }
2102 if (GNUNET_YES == disable_v6)
2103 {
2104 struct sockaddr_in *i4;
2105
2106 i4 = GNUNET_malloc (sizeof(struct sockaddr_in));
2107 i4->sin_family = AF_INET;
2108 i4->sin_port = htons ((uint16_t) port);
2109 *sock_len = sizeof(struct sockaddr_in);
2110 in = (struct sockaddr *) i4;
2111 }
2112 else
2113 {
2114 struct sockaddr_in6 *i6;
2115
2116 i6 = GNUNET_malloc (sizeof(struct sockaddr_in6));
2117 i6->sin6_family = AF_INET6;
2118 i6->sin6_port = htons ((uint16_t) port);
2119 *sock_len = sizeof(struct sockaddr_in6);
2120 in = (struct sockaddr *) i6;
2121 }
2122 return in;
2123 }
2124 cp = GNUNET_strdup (bindto);
2125 colon = strrchr (cp, ':');
2126 if (NULL != colon)
2127 {
2128 /* interpret value after colon as port */
2129 *colon = '\0';
2130 colon++;
2131 if (1 == sscanf (colon, "%u%1s", &port, dummy))
2132 {
2133 /* interpreting value as just a PORT number */
2134 if (port > UINT16_MAX)
2135 {
2137 "BINDTO specification `%s' invalid: value too large for port\n",
2138 bindto);
2139 GNUNET_free (cp);
2140 return NULL;
2141 }
2142 }
2143 else
2144 {
2145 GNUNET_log (
2147 "BINDTO specification `%s' invalid: last ':' not followed by number\n",
2148 bindto);
2149 GNUNET_free (cp);
2150 return NULL;
2151 }
2152 }
2153 else
2154 {
2155 /* interpret missing port as 0, aka pick any free one */
2156 port = 0;
2157 }
2158 {
2159 /* try IPv4 */
2160 struct sockaddr_in v4;
2161
2162 memset (&v4, 0, sizeof(v4));
2163 if (1 == inet_pton (AF_INET, cp, &v4.sin_addr))
2164 {
2165 v4.sin_family = AF_INET;
2166 v4.sin_port = htons ((uint16_t) port);
2167#if HAVE_SOCKADDR_IN_SIN_LEN
2168 v4.sin_len = sizeof(struct sockaddr_in);
2169#endif
2170 in = GNUNET_memdup (&v4, sizeof(struct sockaddr_in));
2171 *sock_len = sizeof(struct sockaddr_in);
2172 GNUNET_free (cp);
2173 return in;
2174 }
2175 }
2176 {
2177 /* try IPv6 */
2178 struct sockaddr_in6 v6;
2179 const char *start;
2180
2181 memset (&v6, 0, sizeof(v6));
2182 start = cp;
2183 if (('[' == *cp) && (']' == cp[strlen (cp) - 1]))
2184 {
2185 start++; /* skip over '[' */
2186 cp[strlen (cp) - 1] = '\0'; /* eat ']' */
2187 }
2188 if (1 == inet_pton (AF_INET6, start, &v6.sin6_addr))
2189 {
2190 v6.sin6_family = AF_INET6;
2191 v6.sin6_port = htons ((uint16_t) port);
2192#if HAVE_SOCKADDR_IN_SIN_LEN
2193 v6.sin6_len = sizeof(struct sockaddr_in6);
2194#endif
2195 in = GNUNET_memdup (&v6, sizeof(v6));
2196 *sock_len = sizeof(v6);
2197 GNUNET_free (cp);
2198 return in;
2199 }
2200 }
2201 /* #5528 FIXME (feature!): maybe also try getnameinfo()? */
2202 GNUNET_free (cp);
2203 return NULL;
2204}
2205
2206
2207static void
2208sock_read (void *cls);
2209
2210
2211static enum GNUNET_GenericReturnValue
2213 const char *address,
2215{
2216 struct GNUNET_HashContext *hsh;
2217 struct ReceiverAddress *receiver;
2218 struct GNUNET_HashCode receiver_key;
2219 const char *path;
2220 struct sockaddr *in;
2221 socklen_t in_len;
2222
2223 if (0 != strncmp (address,
2225 strlen (COMMUNICATOR_ADDRESS_PREFIX "-")))
2226 {
2227 GNUNET_break_op (0);
2228 return GNUNET_SYSERR;
2229 }
2230 path = &address[strlen (COMMUNICATOR_ADDRESS_PREFIX "-")];
2231 in = udp_address_to_sockaddr (path, &in_len);
2232
2233 if (NULL == in)
2234 {
2236 "Failed to setup UDP socket address\n");
2237 return GNUNET_SYSERR;
2238 }
2239 if ((AF_INET6 == in->sa_family) &&
2241 {
2243 "IPv6 disabled, skipping %s\n", address);
2244 GNUNET_free (in);
2245 return GNUNET_SYSERR;
2246 }
2247 else if (AF_INET == in->sa_family)
2248 {
2249 struct sockaddr_in *sin = (struct sockaddr_in *) in;
2250 if (0 == sin->sin_port)
2251 {
2252 GNUNET_free (in);
2253 return GNUNET_NO;
2254 }
2255 }
2256
2258 GNUNET_CRYPTO_hash_context_read (hsh, in, in_len);
2259 GNUNET_CRYPTO_hash_context_read (hsh, peer, sizeof(*peer));
2260 GNUNET_CRYPTO_hash_context_finish (hsh, &receiver_key);
2261
2263 if (NULL != receiver)
2264 {
2266 "receiver %s already exist or is being connected to\n",
2267 address);
2268 return GNUNET_NO;
2269 }
2270
2272 receiver->udp_sock = udp_sock;
2273 receiver->key = receiver_key;
2274 receiver->address = in;
2275 receiver->address_len = in_len;
2276 receiver->target = *peer;
2277 eddsa_pub_to_hpke_key (&receiver->target.public_key,
2278 &receiver->target_hpke_key);
2279 receiver->nt = GNUNET_NT_scanner_get_type (is, in, in_len);
2281 receivers,
2282 &receiver->key,
2283 receiver,
2286 "Added %s to receivers with address %s and sock %p\n",
2287 GNUNET_i2s_full (&receiver->target),
2288 address,
2289 udp_sock);
2290 receiver->timeout =
2293 receiver,
2294 receiver->timeout.abs_value_us);
2296 "# receivers active",
2298 GNUNET_NO);
2299 receiver->foreign_addr =
2300 sockaddr_to_udpaddr_string (receiver->address, receiver->address_len);
2301 if (NULL != udp_sock)
2304 udp_sock,
2305 &sock_read,
2306 udp_sock);
2308 if (NULL == timeout_task)
2310 return GNUNET_OK;
2311}
2312
2313
2319static void
2320sock_read (void *cls)
2321{
2322 struct sockaddr_storage sa;
2323 struct sockaddr_in *addr_verify;
2324 socklen_t salen = sizeof(sa);
2325 char buf[UINT16_MAX];
2326 ssize_t rcvd;
2327
2328 struct GNUNET_NETWORK_Handle *udp_sock = cls;
2330 udp_sock,
2331 &sock_read,
2332 udp_sock);
2333 while (1)
2334 {
2336 buf,
2337 sizeof(buf),
2338 (struct sockaddr *) &sa,
2339 &salen);
2340 if (-1 == rcvd)
2341 {
2342 struct sockaddr *addr = (struct sockaddr*) &sa;
2343
2344 if (EAGAIN == errno)
2345 break; // We are done reading data
2347 "Failed to recv from %s family %d failed sock %p\n",
2348 GNUNET_a2s ((struct sockaddr*) &sa,
2349 sizeof (*addr)),
2350 addr->sa_family,
2351 udp_sock);
2353 return;
2354 }
2356 "Read %llu bytes\n",
2357 (unsigned long long) rcvd);
2358 if (0 == rcvd)
2359 {
2360 GNUNET_break_op (0);
2362 "Read 0 bytes from UDP socket\n");
2363 return;
2364 }
2365
2366 /* first, see if it is a GNUNET_BurstMessage */
2367 if (rcvd == sizeof (struct GNUNET_BurstMessage))
2368 {
2369 struct GNUNET_BurstMessage *bm = (struct GNUNET_BurstMessage *) buf;
2370 struct sockaddr *addr = (struct sockaddr*) &sa;
2371 char *address = sockaddr_to_udpaddr_string (addr, sizeof (*addr));
2372
2373 GNUNET_assert (0 == bm->local_port);
2375 "Received a burst message for default port\n");
2376 create_receiver (&bm->peer,
2377 address,
2378 NULL);
2382 return;
2383 }
2384 /* second, see if it is a UDPBox */
2385 if (rcvd > sizeof(struct UDPBox))
2386 {
2387 const struct UDPBox *box;
2388 struct KeyCacheEntry *kce;
2389
2390 box = (const struct UDPBox *) buf;
2392 if (NULL != kce)
2393 {
2395 "Found KCE with kid %s\n",
2396 GNUNET_sh2s (&box->kid));
2397 decrypt_box (box, (size_t) rcvd, kce);
2398 continue;
2399 }
2400 }
2401
2402 /* next, check if it is a broadcast */
2403 if (sizeof(struct UDPBroadcast) == rcvd)
2404 {
2405 const struct UDPBroadcast *ub;
2406 struct UdpBroadcastSignature uhs;
2407 struct GNUNET_PeerIdentity sender;
2408
2409 addr_verify = GNUNET_memdup (&sa, salen);
2410 addr_verify->sin_port = 0;
2412 "received UDPBroadcast from %s\n",
2413 GNUNET_a2s ((const struct sockaddr *) addr_verify, salen));
2414 ub = (const struct UDPBroadcast *) buf;
2415 uhs.purpose.purpose = htonl (
2417 uhs.purpose.size = htonl (sizeof(uhs));
2418 uhs.sender = ub->sender;
2419 sender = ub->sender;
2420 if (0 == memcmp (&sender, &my_identity, sizeof (struct
2422 {
2424 "Received our own broadcast\n");
2425 GNUNET_free (addr_verify);
2426 continue;
2427 }
2429 "checking UDPBroadcastSignature for %s\n",
2430 GNUNET_i2s (&sender));
2431 GNUNET_CRYPTO_hash ((struct sockaddr *) addr_verify, salen,
2432 &uhs.h_address);
2433 if (GNUNET_OK ==
2436 &uhs,
2437 &ub->sender_sig,
2438 &ub->sender.public_key))
2439 {
2440 char *addr_s;
2442
2443 addr_s =
2444 sockaddr_to_udpaddr_string ((const struct sockaddr *) &sa, salen);
2445 GNUNET_STATISTICS_update (stats, "# broadcasts received", 1, GNUNET_NO);
2446 /* use our own mechanism to determine network type */
2447 nt =
2448 GNUNET_NT_scanner_get_type (is, (const struct sockaddr *) &sa, salen);
2450 "validating address %s received from UDPBroadcast\n",
2451 GNUNET_i2s (&sender));
2453 GNUNET_free (addr_s);
2454 GNUNET_free (addr_verify);
2455 continue;
2456 }
2457 else
2458 {
2460 "VerifyingPeer %s is verifying UDPBroadcast\n",
2463 "Verifying UDPBroadcast from %s failed\n",
2464 GNUNET_i2s (&ub->sender));
2465 }
2466 GNUNET_free (addr_verify);
2467 /* continue with KX, mostly for statistics... */
2468 }
2469
2470
2471 /* finally, test if it is a KX */
2472 if (rcvd < sizeof(struct UDPConfirmation) + sizeof(struct InitialKX))
2473 {
2475 "# messages dropped (no kid, too small for KX)",
2476 1,
2477 GNUNET_NO);
2478 continue;
2479 }
2481 "Got KX\n");
2482 {
2483 const struct InitialKX *kx;
2484 struct SharedSecret *ss;
2485 char pbuf[rcvd - sizeof(struct InitialKX)];
2486 const struct UDPConfirmation *uc;
2487 struct SenderAddress *sender;
2488
2489 kx = (const struct InitialKX *) buf;
2492 "Before DEC\n");
2493
2494 if (GNUNET_OK != try_decrypt (ss,
2495 kx->gcm_tag,
2496 0,
2497 &buf[sizeof(*kx)],
2498 sizeof(pbuf),
2499 pbuf))
2500 {
2502 "Unable to decrypt tag, dropping...\n");
2503 GNUNET_free (ss);
2505 stats,
2506 "# messages dropped (no kid, AEAD decryption failed)",
2507 1,
2508 GNUNET_NO);
2509 continue;
2510 }
2512 "Before VERIFY\n");
2513
2514 uc = (const struct UDPConfirmation *) pbuf;
2515
2516 if (GNUNET_OK != verify_confirmation (&kx->enc, uc)) // TODO: need ephemeral instead of representative
2517 {
2518 GNUNET_break_op (0);
2519 GNUNET_free (ss);
2521 "# messages dropped (sender signature invalid)",
2522 1,
2523 GNUNET_NO);
2524 continue;
2525 }
2527 "Before SETUP_SENDER\n");
2528
2529 calculate_cmac (ss);
2530 sender = setup_sender (&uc->sender, (const struct sockaddr *) &sa, salen);
2531 ss->sender = sender;
2532 GNUNET_CONTAINER_DLL_insert (sender->ss_head, sender->ss_tail, ss);
2533 if ((KCN_THRESHOLD > ss->sender->acks_available) &&
2534 (NULL == ss->sender->kce_task) &&
2536 {
2537 // TODO This task must be per sender! FIXME: This is a nice todo, but I do not know what must be done here to fix.
2541 ss);
2542 }
2543 sender->num_secrets++;
2544 GNUNET_STATISTICS_update (stats, "# Secrets active", 1, GNUNET_NO);
2546 "# messages decrypted without BOX",
2547 1,
2548 GNUNET_NO);
2549 try_handle_plaintext (sender, &uc[1], sizeof(pbuf) - sizeof(*uc));
2550 if (0 == purge_secrets (sender->ss_tail))
2551 {
2552 // No secret purged. Delete oldest.
2553 if (sender->num_secrets > MAX_SECRETS)
2554 {
2555 secret_destroy (sender->ss_tail);
2556 }
2557 }
2558 }
2559 }
2560}
2561
2562
2570static void
2571do_pad (gcry_cipher_hd_t out_cipher, char *dgram, size_t pad_size)
2572{
2573 char pad[pad_size];
2574
2576 if (sizeof(pad) > sizeof(struct GNUNET_MessageHeader))
2577 {
2578 struct GNUNET_MessageHeader hdr =
2579 { .size = htons (sizeof(pad)),
2581
2582 memcpy (pad, &hdr, sizeof(hdr));
2583 }
2585 0 ==
2586 gcry_cipher_encrypt (out_cipher, dgram, sizeof(pad), pad, sizeof(pad)));
2587}
2588
2589
2590static void
2593 struct GNUNET_MQ_Handle *mq)
2594{
2595 uint16_t msize = ntohs (msg->size);
2596 struct UdpHandshakeSignature uhs;
2597 struct UDPConfirmation uc;
2598 struct InitialKX kx;
2599 char dgram[receiver->kx_mtu + sizeof(uc) + sizeof(kx)];
2600 size_t dpos;
2601 gcry_cipher_hd_t out_cipher;
2602 struct SharedSecret *ss;
2603
2604 if (msize > receiver->kx_mtu)
2605 {
2606 GNUNET_break (0);
2607 if (GNUNET_YES != receiver->receiver_destroy_called)
2609 return;
2610 }
2612
2613 /* setup key material */
2615
2616 if (0 == purge_secrets (receiver->ss_tail))
2617 {
2618 // No secret purged. Delete oldest.
2619 if (receiver->num_secrets > MAX_SECRETS)
2620 {
2621 secret_destroy (receiver->ss_tail);
2622 }
2623 }
2624
2625 setup_cipher (&ss->master, 0, &out_cipher);
2626 /* compute 'uc' */
2627 uc.sender = my_identity;
2628 uc.monotonic_time =
2630 uhs.purpose.purpose = htonl (
2632 uhs.purpose.size = htonl (sizeof(uhs));
2633 uhs.sender = my_identity;
2634 uhs.receiver = receiver->target;
2635 uhs.monotonic_time = uc.monotonic_time;
2637 &uhs,
2638 &uc.sender_sig);
2639 /* Leave space for kx */
2640 dpos = sizeof(kx);
2641 /* Append encrypted uc to dgram */
2642 GNUNET_assert (0 == gcry_cipher_encrypt (out_cipher,
2643 &dgram[dpos],
2644 sizeof(uc),
2645 &uc,
2646 sizeof(uc)));
2647 dpos += sizeof(uc);
2648 /* Append encrypted payload to dgram */
2650 0 == gcry_cipher_encrypt (out_cipher, &dgram[dpos], msize, msg, msize));
2651 dpos += msize;
2652 do_pad (out_cipher, &dgram[dpos], sizeof(dgram) - dpos);
2653 /* Datagram starts with kx */
2654 kx.enc = uhs.enc;
2656 0 == gcry_cipher_gettag (out_cipher, kx.gcm_tag, sizeof(kx.gcm_tag)));
2657 gcry_cipher_close (out_cipher);
2658 memcpy (dgram, &kx, sizeof(kx));
2660 dgram,
2661 sizeof(dgram),
2662 receiver->address,
2663 receiver->address_len))
2664 {
2667 "Sending KX with payload size %u to %s family %d failed sock %p\n",
2668 msize,
2669 GNUNET_a2s (receiver->address,
2670 receiver->address_len),
2671 receiver->address->sa_family,
2675 return;
2676 }
2678 "Sending KX with payload size %u to %s with socket %p\n",
2679 msize,
2680 GNUNET_a2s (receiver->address,
2681 receiver->address_len),
2684}
2685
2686
2695static void
2697 const struct GNUNET_MessageHeader *msg,
2698 void *impl_state)
2699{
2700 struct ReceiverAddress *receiver = impl_state;
2701
2702 GNUNET_assert (mq == receiver->kx_mq);
2704}
2705
2706
2707static void
2709 UDPRekey *rekey)
2710{
2711 struct SharedSecret *ss_rekey;
2712
2714 /* setup key material */
2715 ss_rekey = setup_shared_secret_ephemeral (&rekey->ephemeral,
2716 receiver);
2717 ss_rekey->sequence_allowed = 0;
2719 "Setup secret with k = %s\n",
2720 GNUNET_sh2s (&ss_rekey->master));
2722 "Setup secret with H(k) = %s\n",
2723 GNUNET_h2s (&(ss_rekey->cmac)));
2724
2725 /* Append encrypted payload to dgram */
2727 rekey->header.size = htons (sizeof (struct UDPRekey));
2728}
2729
2730
2739static void
2741 const struct GNUNET_MessageHeader *msg,
2742 void *impl_state)
2743{
2744 struct ReceiverAddress *receiver = impl_state;
2745 struct UDPRekey rekey;
2746 struct SharedSecret *ss;
2747 int inject_rekey = GNUNET_NO;
2748 uint16_t msize = ntohs (msg->size);
2749
2750 GNUNET_assert (mq == receiver->d_mq);
2751 if ((msize > receiver->d_mtu) ||
2752 (0 == receiver->acks_available))
2753 {
2755 "msize: %u, mtu: %llu, acks: %u\n",
2756 (unsigned int) msize,
2757 (unsigned long long) receiver->d_mtu,
2758 receiver->acks_available);
2759
2760 GNUNET_break (0);
2761 if (GNUNET_YES != receiver->receiver_destroy_called)
2763 return;
2764 }
2766
2767 if (receiver->num_secrets > MAX_SECRETS)
2768 {
2769 if ((0 == purge_secrets (receiver->ss_tail)) &&
2770 (NULL != receiver->ss_tail))
2771 {
2772 // No secret purged. Delete oldest.
2773 secret_destroy (receiver->ss_tail);
2774 }
2775 }
2776 /* begin "BOX" encryption method, scan for ACKs from tail! */
2777 ss = receiver->ss_tail;
2778 struct SharedSecret *ss_tmp;
2779 while (NULL != ss)
2780 {
2781 size_t payload_len = sizeof(struct UDPBox) + receiver->d_mtu;
2783 "Considering SS %s sequence used: %u sequence allowed: %u bytes sent: %lu.\n",
2784 GNUNET_sh2s (&ss->master), ss->sequence_used,
2785 ss->sequence_allowed, ss->bytes_sent);
2786 if (ss->sequence_used >= ss->sequence_allowed)
2787 {
2788 // GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
2789 // "Skipping ss because no acks to use.\n");
2790 ss = ss->prev;
2791 continue;
2792 }
2793 if (ss->bytes_sent >= rekey_max_bytes)
2794 {
2796 "Skipping ss because rekey bytes reached.\n");
2797 // FIXME cleanup ss with too many bytes sent!
2798 ss_tmp = ss->prev;
2799 secret_destroy (ss);
2800 ss = ss_tmp;
2801 continue;
2802 }
2803 if (ss->bytes_sent > rekey_max_bytes * 0.7)
2804 {
2805 if (ss->rekey_initiated == GNUNET_NO)
2806 {
2808 "Injecting rekey for ss with byte sent %lu\n",
2809 (unsigned long) ss->bytes_sent);
2810 create_rekey (receiver, ss, &rekey);
2812 payload_len += sizeof (rekey);
2814 }
2815 }
2816 if (0 < ss->sequence_used)
2818 "Trying to send UDPBox with shared secrect %s sequence_used %u and ss->sequence_allowed %u\n",
2819 GNUNET_sh2s (&ss->master),
2820 ss->sequence_used,
2821 ss->sequence_allowed);
2822
2823 char dgram[payload_len];
2824 struct UDPBox *box;
2825 gcry_cipher_hd_t out_cipher;
2826 size_t dpos;
2827
2828 box = (struct UDPBox *) dgram;
2829 ss->sequence_used++;
2830 get_kid (&ss->master, ss->sequence_used, &box->kid);
2831 setup_cipher (&ss->master, ss->sequence_used, &out_cipher);
2832 /* Append encrypted payload to dgram */
2833 dpos = sizeof(struct UDPBox);
2834 if (GNUNET_YES == inject_rekey)
2835 {
2837 0 == gcry_cipher_encrypt (out_cipher, &dgram[dpos], sizeof (rekey),
2838 &rekey, sizeof (rekey)));
2839 dpos += sizeof (rekey);
2840 }
2842 0 == gcry_cipher_encrypt (out_cipher, &dgram[dpos], msize, msg, msize));
2843 dpos += msize;
2844 do_pad (out_cipher, &dgram[dpos], sizeof(dgram) - dpos);
2845 GNUNET_assert (0 == gcry_cipher_gettag (out_cipher,
2846 box->gcm_tag,
2847 sizeof(box->gcm_tag)));
2848 gcry_cipher_close (out_cipher);
2849
2851 dgram,
2852 payload_len, // FIXME why always send sizeof dgram?
2853 receiver->address,
2854 receiver->address_len))
2855 {
2858 "Sending UDPBox to %s family %d failed sock %p failed\n",
2859 GNUNET_a2s (receiver->address,
2860 receiver->address_len),
2861 receiver->address->sa_family,
2864 return;
2865 }
2867 "Sending UDPBox with payload size %u, %u acks left, %lu bytes sent with socket %p\n",
2868 msize,
2869 receiver->acks_available,
2870 (unsigned long) ss->bytes_sent,
2872 ss->bytes_sent += sizeof (dgram);
2873 receiver->acks_available--;
2875 return;
2876 }
2878 "No suitable ss found, sending as KX...\n");
2880}
2881
2882
2891static void
2892mq_destroy_d (struct GNUNET_MQ_Handle *mq, void *impl_state)
2893{
2894 struct ReceiverAddress *receiver = impl_state;
2896 "Default MQ destroyed\n");
2897 if (mq == receiver->d_mq)
2898 {
2899 receiver->d_mq = NULL;
2900 if (GNUNET_YES != receiver->receiver_destroy_called)
2902 }
2903}
2904
2905
2914static void
2915mq_destroy_kx (struct GNUNET_MQ_Handle *mq, void *impl_state)
2916{
2917 struct ReceiverAddress *receiver = impl_state;
2919 "KX MQ destroyed\n");
2920 if (mq == receiver->kx_mq)
2921 {
2922 receiver->kx_mq = NULL;
2923 if (GNUNET_YES != receiver->receiver_destroy_called)
2925 }
2926}
2927
2928
2935static void
2936mq_cancel (struct GNUNET_MQ_Handle *mq, void *impl_state)
2937{
2938 /* Cancellation is impossible with UDP; bail */
2939 GNUNET_assert (0);
2940}
2941
2942
2952static void
2953mq_error (void *cls, enum GNUNET_MQ_Error error)
2954{
2955 struct ReceiverAddress *receiver = cls;
2956
2958 "MQ error in queue to %s: %d\n",
2959 GNUNET_i2s (&receiver->target),
2960 (int) error);
2962}
2963
2964
2972static void
2974{
2975 size_t base_mtu;
2976
2977 switch (receiver->address->sa_family)
2978 {
2979 case AF_INET:
2980 base_mtu = 1480 /* Ethernet MTU, 1500 - Ethernet header - VLAN tag */
2981 - sizeof(struct GNUNET_TUN_IPv4Header) /* 20 */
2982 - sizeof(struct GNUNET_TUN_UdpHeader) /* 8 */;
2983 break;
2984
2985 case AF_INET6:
2986 base_mtu = 1280 /* Minimum MTU required by IPv6 */
2987 - sizeof(struct GNUNET_TUN_IPv6Header) /* 40 */
2988 - sizeof(struct GNUNET_TUN_UdpHeader) /* 8 */;
2989 break;
2990
2991 default:
2992 GNUNET_assert (0);
2993 break;
2994 }
2995 /* MTU based on full KX messages */
2996 receiver->kx_mtu = base_mtu - sizeof(struct InitialKX) /* 48 */
2997 - sizeof(struct UDPConfirmation); /* 104 */
2998 /* MTU based on BOXed messages */
2999 receiver->d_mtu = base_mtu - sizeof(struct UDPBox);
3000
3002 "Setting up MQs and QHs\n");
3003 /* => Effective MTU for CORE will range from 1080 (IPv6 + KX) to
3004 1404 (IPv4 + Box) bytes, depending on circumstances... */
3005 if (NULL == receiver->kx_mq)
3008 &mq_cancel,
3009 receiver,
3010 NULL,
3011 &mq_error,
3012 receiver);
3013 if (NULL == receiver->d_mq)
3015 &mq_destroy_d,
3016 &mq_cancel,
3017 receiver,
3018 NULL,
3019 &mq_error,
3020 receiver);
3021
3022 receiver->kx_qh =
3024 &receiver->target,
3025 receiver->foreign_addr,
3026 receiver->kx_mtu,
3028 0, /* Priority */
3029 receiver->nt,
3031 receiver->kx_mq);
3032}
3033
3034
3053static int
3054mq_init (void *cls, const struct GNUNET_PeerIdentity *peer, const char *address)
3055{
3056 (void) cls;
3058 "create receiver for mq_init\n");
3059 return create_receiver (peer,
3060 address,
3061 NULL);
3062}
3063
3064
3073static int
3075 const struct GNUNET_HashCode *target,
3076 void *value)
3077{
3078 struct ReceiverAddress *receiver = value;
3079
3080 (void) cls;
3081 (void) target;
3083 return GNUNET_OK;
3084}
3085
3086
3095static int
3097 const struct GNUNET_HashCode *target,
3098 void *value)
3099{
3100 struct SenderAddress *sender = value;
3101
3102 (void) cls;
3103 (void) target;
3104
3105
3106 sender_destroy (sender);
3107 return GNUNET_OK;
3108}
3109
3110
3116static void
3117do_shutdown (void *cls)
3118{
3120 "do_shutdown\n");
3121 GNUNET_stop_burst (NULL);
3122 if (NULL != nat)
3123 {
3125 nat = NULL;
3126 }
3127 while (NULL != bi_head)
3129 if (NULL != broadcast_task)
3130 {
3132 broadcast_task = NULL;
3133 }
3134 if (NULL != timeout_task)
3135 {
3137 timeout_task = NULL;
3138 }
3139 if (NULL != read_task)
3140 {
3142 read_task = NULL;
3143 }
3144 if (NULL != default_udp_sock)
3145 {
3148 default_udp_sock = NULL;
3149 }
3152 NULL);
3156 NULL);
3161 if (NULL != timeout_task)
3162 {
3164 timeout_task = NULL;
3165 }
3166 if (NULL != ch)
3167 {
3169 ch = NULL;
3170 }
3171 if (NULL != ah)
3172 {
3174 ah = NULL;
3175 }
3176 if (NULL != stats)
3177 {
3179 stats = NULL;
3180 }
3181 if (NULL != my_private_key)
3182 {
3184 my_private_key = NULL;
3185 }
3186 if (NULL != is)
3187 {
3189 is = NULL;
3190 }
3192 "do_shutdown finished\n");
3193}
3194
3195
3197{
3198 const struct UDPAck *ack;
3199
3201};
3202
3203static int
3204handle_ack_by_sender (void *cls, const struct GNUNET_HashCode *key, void *value)
3205{
3206 struct ReceiverAddress *receiver = value;
3207 struct AckInfo *ai = cls;
3208
3209 if (0 != GNUNET_memcmp (ai->sender, &receiver->target))
3210 {
3211 return GNUNET_YES;
3212 }
3213 handle_ack ((void*) ai->ack, key, receiver);
3214 return GNUNET_YES;
3215}
3216
3217
3227static void
3228enc_notify_cb (void *cls,
3229 const struct GNUNET_PeerIdentity *sender,
3230 const struct GNUNET_MessageHeader *msg)
3231{
3232 struct AckInfo ai;
3233
3234 (void) cls;
3236 "Storing UDPAck received from backchannel from %s\n",
3239 (ntohs (msg->size) != sizeof(struct UDPAck)))
3240 {
3241 GNUNET_break_op (0);
3242 return;
3243 }
3244 ai.ack = (const struct UDPAck *) msg;
3245 ai.sender = sender;
3248 &ai);
3249}
3250
3251
3265static void
3267 void **app_ctx,
3268 int add_remove,
3270 const struct sockaddr *addr,
3271 socklen_t addrlen)
3272{
3273 char *my_addr;
3275
3276 if (GNUNET_YES == add_remove)
3277 {
3279
3280 GNUNET_asprintf (&my_addr,
3281 "%s-%s",
3283 GNUNET_a2s (addr, addrlen));
3284 nt = GNUNET_NT_scanner_get_type (is, addr, addrlen);
3285 ai =
3287 my_addr,
3288 nt,
3290 GNUNET_free (my_addr);
3291 *app_ctx = ai;
3292 }
3293 else
3294 {
3295 ai = *app_ctx;
3297 *app_ctx = NULL;
3298 }
3299}
3300
3301
3307static void
3308ifc_broadcast (void *cls)
3309{
3310 struct BroadcastInterface *bi = cls;
3311 struct GNUNET_TIME_Relative delay;
3312
3313 delay = BROADCAST_FREQUENCY;
3314 delay.rel_value_us =
3316 bi->broadcast_task =
3318
3319 switch (bi->sa->sa_family)
3320 {
3321 case AF_INET: {
3322 static int yes = 1;
3323 static int no = 0;
3324 ssize_t sent;
3325
3326 if (GNUNET_OK !=
3328 SOL_SOCKET,
3329 SO_BROADCAST,
3330 &yes,
3331 sizeof(int)))
3333 "setsockopt");
3335 "creating UDPBroadcast from %s\n",
3336 GNUNET_i2s (&(bi->bcm.sender)));
3338 "sending UDPBroadcast to add %s\n",
3339 GNUNET_a2s (bi->ba, bi->salen));
3341 &bi->bcm,
3342 sizeof(bi->bcm),
3343 bi->ba,
3344 bi->salen);
3345 if (-1 == sent)
3347 "sendto");
3349 SOL_SOCKET,
3350 SO_BROADCAST,
3351 &no,
3352 sizeof(int)))
3354 "setsockopt");
3355 break;
3356 }
3357
3358 case AF_INET6: {
3359 ssize_t sent;
3360 struct sockaddr_in6 dst;
3361
3362 dst.sin6_family = AF_INET6;
3363 dst.sin6_port = htons (my_port);
3364 dst.sin6_addr = bi->mcreq.ipv6mr_multiaddr;
3365 dst.sin6_scope_id = ((struct sockaddr_in6 *) bi->ba)->sin6_scope_id;
3366
3368 "sending UDPBroadcast\n");
3370 &bi->bcm,
3371 sizeof(bi->bcm),
3372 (const struct sockaddr *) &dst,
3373 sizeof(dst));
3374 if (-1 == sent)
3376 break;
3377 }
3378
3379 default:
3380 GNUNET_break (0);
3381 break;
3382 }
3383}
3384
3385
3400static int
3401iface_proc (void *cls,
3402 const char *name,
3403 int isDefault,
3404 const struct sockaddr *addr,
3405 const struct sockaddr *broadcast_addr,
3406 const struct sockaddr *netmask,
3407 socklen_t addrlen)
3408{
3409 struct BroadcastInterface *bi;
3410 enum GNUNET_NetworkType network;
3411 struct UdpBroadcastSignature ubs;
3412
3413 (void) cls;
3414 (void) netmask;
3415 if (NULL == addr)
3416 return GNUNET_YES; /* need to know our address! */
3417 network = GNUNET_NT_scanner_get_type (is, addr, addrlen);
3418 if (GNUNET_NT_LOOPBACK == network)
3419 {
3420 /* Broadcasting on loopback does not make sense */
3421 return GNUNET_YES;
3422 }
3423 for (bi = bi_head; NULL != bi; bi = bi->next)
3424 {
3425 if ((bi->salen == addrlen) && (0 == memcmp (addr, bi->sa, addrlen)))
3426 {
3427 bi->found = GNUNET_YES;
3428 return GNUNET_OK;
3429 }
3430 }
3431
3432 if ((AF_INET6 == addr->sa_family) && (NULL == broadcast_addr))
3433 return GNUNET_OK; /* broadcast_addr is required for IPv6! */
3434 if ((AF_INET6 == addr->sa_family) && (GNUNET_YES != have_v6_socket))
3435 return GNUNET_OK; /* not using IPv6 */
3436
3437 bi = GNUNET_new (struct BroadcastInterface);
3438 bi->sa = GNUNET_memdup (addr,
3439 addrlen);
3440 if ( (NULL != broadcast_addr) &&
3441 (addrlen == sizeof (struct sockaddr_in)) )
3442 {
3443 struct sockaddr_in *ba;
3444
3445 ba = GNUNET_memdup (broadcast_addr,
3446 addrlen);
3447 ba->sin_port = htons (2086); /* always GNUnet port, ignore configuration! */
3448 bi->ba = (struct sockaddr *) ba;
3449 }
3450 bi->salen = addrlen;
3451 bi->found = GNUNET_YES;
3452 bi->bcm.sender = my_identity;
3453 ubs.purpose.purpose = htonl (
3455 ubs.purpose.size = htonl (sizeof(ubs));
3456 ubs.sender = my_identity;
3458 "creating UDPBroadcastSignature for %s\n",
3459 GNUNET_a2s (addr, addrlen));
3460 GNUNET_CRYPTO_hash (addr, addrlen, &ubs.h_address);
3462 &ubs,
3463 &bi->bcm.sender_sig);
3464 if (NULL != bi->ba)
3465 {
3468 }
3469 if ((AF_INET6 == addr->sa_family) && (NULL != broadcast_addr))
3470 {
3471 /* Create IPv6 multicast request */
3472 const struct sockaddr_in6 *s6 =
3473 (const struct sockaddr_in6 *) broadcast_addr;
3474
3476 1 == inet_pton (AF_INET6, "FF05::13B", &bi->mcreq.ipv6mr_multiaddr));
3477
3478 /* http://tools.ietf.org/html/rfc2553#section-5.2:
3479 *
3480 * IPV6_JOIN_GROUP
3481 *
3482 * Join a multicast group on a specified local interface. If the
3483 * interface index is specified as 0, the kernel chooses the local
3484 * interface. For example, some kernels look up the multicast
3485 * group in the normal IPv6 routing table and using the resulting
3486 * interface; we do this for each interface, so no need to use
3487 * zero (anymore...).
3488 */
3489 bi->mcreq.ipv6mr_interface = s6->sin6_scope_id;
3490
3491 /* Join the multicast group */
3493 IPPROTO_IPV6,
3494 IPV6_JOIN_GROUP,
3495 &bi->mcreq,
3496 sizeof(bi->mcreq)))
3497 {
3499 }
3500 }
3501 return GNUNET_OK;
3502}
3503
3504
3510static void
3511do_broadcast (void *cls)
3512{
3513 struct BroadcastInterface *bin;
3514
3515 (void) cls;
3516 for (struct BroadcastInterface *bi = bi_head; NULL != bi; bi = bi->next)
3517 bi->found = GNUNET_NO;
3519 for (struct BroadcastInterface *bi = bi_head; NULL != bi; bi = bin)
3520 {
3521 bin = bi->next;
3522 if (GNUNET_NO == bi->found)
3523 bi_destroy (bi);
3524 }
3526 &do_broadcast,
3527 NULL);
3528}
3529
3530
3531static void
3533 const struct sockaddr *addr,
3534 socklen_t addrlen)
3535{
3536 /* FIXME: support reversal: #5529 */
3538 "No connection reversal implemented!\n");
3539}
3540
3541
3542static void
3544{
3546 sizeof (*sock_info->actual_address
3547 ));
3548 create_receiver (sock_info->pid,
3549 address,
3550 default_udp_sock == sock_info->udp_sock ?
3551 NULL : sock_info->udp_sock);
3553 GNUNET_free (sock_info);
3554}
3555
3556
3557static void
3558start_burst (const char *addr,
3559 struct GNUNET_TIME_Relative rtt,
3560 struct GNUNET_PeerIdentity *pid)
3561{
3562 struct GNUNET_UdpSocketInfo *sock_info;
3563
3565 "Communicator was called to start burst to address %s from %s\n",
3566 addr,
3567 my_ipv4);
3568
3569 GNUNET_stop_burst (NULL);
3570
3571 sock_info = GNUNET_new (struct GNUNET_UdpSocketInfo);
3572 sock_info->pid = GNUNET_new (struct GNUNET_PeerIdentity);
3573 sock_info->address = GNUNET_strdup (addr);
3574 sock_info->bind_address = my_ipv4;
3575 sock_info->has_port = GNUNET_YES;
3576 sock_info->udp_sock = default_udp_sock;
3577 sock_info->rtt = rtt;
3578 GNUNET_memcpy (sock_info->pid, pid, sizeof (struct GNUNET_PeerIdentity));
3579 sock_info->std_port = my_port;
3581 "1 sock addr %s addr %s rtt %lu %u\n",
3582 sock_info->address,
3583 addr,
3584 (unsigned long) sock_info->rtt.rel_value_us,
3585 my_port);
3586 burst_task = GNUNET_get_udp_socket (sock_info,
3588 GNUNET_free (sock_info);
3589}
3590
3591
3592static void
3593run (void *cls,
3594 char *const *args,
3595 const char *cfgfile,
3596 const struct GNUNET_CONFIGURATION_Handle *c)
3597{
3598 const struct sockaddr_in *v4;
3599 char *bindto;
3600 struct sockaddr *in;
3601 socklen_t in_len;
3602 struct sockaddr_storage in_sto;
3603 socklen_t sto_len;
3604
3606 "Entering the run method of udp communicator.\n");
3607
3608 cfg = c;
3609 if (GNUNET_OK !=
3612 "BINDTO",
3613 &bindto))
3614 {
3617 "BINDTO");
3618 return;
3619 }
3621 "The udp communicator will bind to %s\n",
3622 bindto);
3623 if (GNUNET_OK !=
3626 "REKEY_INTERVAL",
3629
3630 if (GNUNET_OK !=
3633 "REKEY_MAX_BYTES",
3635 {
3637 }
3639 if ((GNUNET_NO == GNUNET_NETWORK_test_pf (PF_INET6)) ||
3640 (GNUNET_YES ==
3643 "DISABLE_V6")))
3644 {
3646 }
3647
3648 in = udp_address_to_sockaddr (bindto, &in_len);
3649 if (NULL == in)
3650 {
3652 "Failed to setup UDP socket address with path `%s'\n",
3653 bindto);
3654 GNUNET_free (bindto);
3655 return;
3656 }
3658 GNUNET_NETWORK_socket_create (in->sa_family,
3659 SOCK_DGRAM,
3660 IPPROTO_UDP);
3661 if (NULL == default_udp_sock)
3662 {
3665 "Failed to create socket for %s family %d\n",
3666 GNUNET_a2s (in,
3667 in_len),
3668 in->sa_family);
3669 GNUNET_free (in);
3670 GNUNET_free (bindto);
3671 return;
3672 }
3673 if (AF_INET6 == in->sa_family)
3675 if (GNUNET_OK !=
3677 in,
3678 in_len))
3679 {
3681 "bind",
3682 bindto);
3684 "Failed to bind socket for %s family %d sock %p\n",
3685 GNUNET_a2s (in,
3686 in_len),
3687 in->sa_family,
3690 default_udp_sock = NULL;
3691 GNUNET_free (in);
3692 GNUNET_free (bindto);
3693 return;
3694 }
3695
3696 /* We might have bound to port 0, allowing the OS to figure it out;
3697 thus, get the real IN-address from the socket */
3698 sto_len = sizeof(in_sto);
3699 if (0 != getsockname (GNUNET_NETWORK_get_fd (default_udp_sock),
3700 (struct sockaddr *) &in_sto,
3701 &sto_len))
3702 {
3703 memcpy (&in_sto, in, in_len);
3704 sto_len = in_len;
3705 }
3706 GNUNET_free (in);
3707 GNUNET_free (bindto);
3708 in = (struct sockaddr *) &in_sto;
3709 in_len = sto_len;
3711 "transport",
3712 "Bound to `%s' sock %p\n",
3713 GNUNET_a2s ((const struct sockaddr *) &in_sto,
3714 sto_len),
3716 switch (in->sa_family)
3717 {
3718 case AF_INET:
3719 v4 = (const struct sockaddr_in *) in;
3720
3721 my_ipv4 = GNUNET_malloc (INET_ADDRSTRLEN);
3722 my_port = ntohs (((struct sockaddr_in *) in)->sin_port);
3723 inet_ntop (AF_INET, &v4->sin_addr, my_ipv4, in_len);
3724 break;
3725
3726 case AF_INET6:
3727 my_port = ntohs (((struct sockaddr_in6 *) in)->sin6_port);
3728 break;
3729
3730 default:
3731 GNUNET_break (0);
3732 my_port = 0;
3733 }
3734 stats = GNUNET_STATISTICS_create ("communicator-udp", cfg);
3744 if (NULL == my_private_key)
3745 {
3746 GNUNET_log (
3748 _ (
3749 "Transport service is lacking key configuration settings. Exiting.\n"));
3751 return;
3752 }
3755 /* start reading */
3758 &sock_read,
3764 &mq_init,
3765 NULL,
3767 NULL,
3768 &start_burst);
3769 if (NULL == ch)
3770 {
3771 GNUNET_break (0);
3773 return;
3774 }
3776 if (NULL == ah)
3777 {
3778 GNUNET_break (0);
3780 return;
3781 }
3782 /* start broadcasting */
3783 if (GNUNET_YES !=
3786 "DISABLE_BROADCAST"))
3787 {
3789 }
3792 IPPROTO_UDP,
3793 1 /* one address */,
3794 (const struct sockaddr **) &in,
3795 &in_len,
3798 NULL /* closure */);
3799}
3800
3801
3802GNUNET_DAEMON_MAIN ("gnunet-communicator-udp", _ ("GNUnet UDP communicator"), &
3803 run)
3804/* end of gnunet-communicator-udp.c */
struct GNUNET_MQ_Handle * mq
Definition: 003.c:5
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
static int start
Set if we are to start default services (including ARM).
Definition: gnunet-arm.c:38
static int ret
Final status code.
Definition: gnunet-arm.c:93
static uint16_t port
Port number.
Definition: gnunet-bcd.c:147
static struct GNUNET_NETWORK_Handle * udp_sock
Our socket.
static void inject_rekey(struct Queue *queue)
Inject a struct TCPRekey message into the queue's plaintext buffer.
#define AES_KEY_SIZE
AES key size.
static struct BroadcastInterface * bi_tail
Broadcast interface tasks.
#define DEFAULT_REKEY_TIME_INTERVAL
How often do we rekey based on time (at least)
static int try_decrypt(const struct SharedSecret *ss, const uint8_t *tag, uint32_t serial, const char *in_buf, size_t in_buf_size, char *out_buf)
Try to decrypt buf using shared secret ss and key/iv derived using serial.
#define WORKING_QUEUE_INTERVALL
static void kce_destroy(struct KeyCacheEntry *kce)
Free memory used by key cache entry.
static int handle_ack(void *cls, const struct GNUNET_HashCode *key, void *value)
We received an ACK for pid.
static void create_rekey(struct ReceiverAddress *receiver, struct SharedSecret *ss, struct UDPRekey *rekey)
static void mq_destroy_d(struct GNUNET_MQ_Handle *mq, void *impl_state)
Signature of functions implementing the destruction of a message queue.
static int secret_destroy(struct SharedSecret *ss)
Destroy ss and associated key cache entries.
#define GCM_TAG_SIZE
Size of the GCM tag.
static void get_iv_key(const struct GNUNET_ShortHashCode *msec, uint32_t serial, char key[(256/8)], char iv[(96/8)])
Compute key and iv.
static struct GNUNET_PeerIdentity my_identity
Our public key.
static void mq_send_kx(struct GNUNET_MQ_Handle *mq, const struct GNUNET_MessageHeader *msg, void *impl_state)
Signature of functions implementing the sending functionality of a message queue.
static struct SharedSecret * setup_initial_shared_secret_ephemeral(struct GNUNET_CRYPTO_HpkeEncapsulation *c, struct ReceiverAddress *receiver)
Setup new shared secret for encryption using KEM for initial handshake.
#define COMMUNICATOR_ADDRESS_PREFIX
Address prefix used by the communicator.
static void kce_generate(struct SharedSecret *ss, uint32_t seq)
Setup key cache entry for sequence number seq and shared secret ss.
static void setup_cipher(const struct GNUNET_ShortHashCode *msec, uint32_t serial, gcry_cipher_hd_t *cipher)
Setup cipher based on shared secret msec and serial number serial.
static void add_acks(struct SharedSecret *ss, int acks_to_add)
#define ADDRESS_VALIDITY_PERIOD
How long do we believe our addresses to remain up (before the other peer should revalidate).
static void mq_destroy_kx(struct GNUNET_MQ_Handle *mq, void *impl_state)
Signature of functions implementing the destruction of a message queue.
static void eddsa_priv_to_hpke_key(struct GNUNET_CRYPTO_EddsaPrivateKey *edpk, struct GNUNET_CRYPTO_EcdhePrivateKey *pk)
static int get_receiver_delete_it(void *cls, const struct GNUNET_HashCode *target, void *value)
Iterator over all receivers to clean up.
static void try_connection_reversal(void *cls, const struct sockaddr *addr, socklen_t addrlen)
static struct GNUNET_SCHEDULER_Task * broadcast_task
ID of master broadcast task.
static struct GNUNET_NT_InterfaceScanner * is
Network scanner to determine network types.
static int verify_confirmation(const struct GNUNET_CRYPTO_HpkeEncapsulation *enc, const struct UDPConfirmation *uc)
Check signature from uc against ephemeral.
static int disable_v6
IPv6 disabled or not.
static struct GNUNET_STATISTICS_Handle * stats
For logging statistics.
static const struct GNUNET_CONFIGURATION_Handle * cfg
Our configuration.
static void enc_notify_cb(void *cls, const struct GNUNET_PeerIdentity *sender, const struct GNUNET_MessageHeader *msg)
Function called when the transport service has received a backchannel message for this communicator (...
static struct SenderAddress * setup_sender(const struct GNUNET_PeerIdentity *target, const struct sockaddr *address, socklen_t address_len)
Create sender address for target.
static struct GNUNET_TIME_Relative rekey_interval
The rekey interval.
static void start_burst(const char *addr, struct GNUNET_TIME_Relative rtt, struct GNUNET_PeerIdentity *pid)
static void reschedule_receiver_timeout(struct ReceiverAddress *receiver)
Increment receiver timeout due to activity.
static struct SharedSecret * setup_shared_secret_ephemeral(struct GNUNET_CRYPTO_HpkeEncapsulation *ephemeral, struct ReceiverAddress *receiver)
Setup new shared secret for encryption using KEM.
static void get_kid(const struct GNUNET_ShortHashCode *msec, uint32_t serial, struct GNUNET_ShortHashCode *kid)
Compute kid.
static void do_pad(gcry_cipher_hd_t out_cipher, char *dgram, size_t pad_size)
Pad dgram by pad_size using out_cipher.
static void mq_send_d(struct GNUNET_MQ_Handle *mq, const struct GNUNET_MessageHeader *msg, void *impl_state)
Signature of functions implementing the sending functionality of a message queue.
static void sock_read(void *cls)
Socket read task.
static void reschedule_sender_timeout(struct SenderAddress *sender)
Increment sender timeout due to activity.
static struct GNUNET_CONTAINER_Heap * senders_heap
Expiration heap for senders (contains struct SenderAddress)
static void do_shutdown(void *cls)
Shutdown the UNIX communicator.
static int get_sender_delete_it(void *cls, const struct GNUNET_HashCode *target, void *value)
Iterator over all senders to clean up.
#define COMMUNICATOR_CONFIG_SECTION
Configuration section used by the communicator.
static void nat_address_cb(void *cls, void **app_ctx, int add_remove, enum GNUNET_NAT_AddressClass ac, const struct sockaddr *addr, socklen_t addrlen)
Signature of the callback passed to GNUNET_NAT_register() for a function to call whenever our set of ...
static struct GNUNET_TRANSPORT_CommunicatorHandle * ch
Our environment.
static void sender_destroy(struct SenderAddress *sender)
Functions with this signature are called whenever we need to close a sender's state due to timeout.
static struct SharedSecret * setup_initial_shared_secret_dec(const struct GNUNET_CRYPTO_HpkeEncapsulation *c)
Setup shared secret for decryption for initial handshake.
static void setup_receiver_mq(struct ReceiverAddress *receiver)
Setup the MQ for the receiver.
static struct sockaddr * udp_address_to_sockaddr(const char *bindto, socklen_t *sock_len)
Convert UDP bind specification to a struct sockaddr *
static int handle_ack_by_sender(void *cls, const struct GNUNET_HashCode *key, void *value)
static void run(void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c)
#define DEFAULT_REKEY_MAX_BYTES
Default value for how often we do rekey based on number of bytes transmitted? (additionally randomize...
static struct GNUNET_NAT_Handle * nat
Connection to NAT service.
static struct GNUNET_CONTAINER_MultiHashMap * receivers
Receivers (map from peer identity to struct ReceiverAddress)
#define GENERATE_AT_ONCE
static void kce_generate_cb(void *cls)
static struct GNUNET_SCHEDULER_Task * read_task
ID of read task.
static void try_handle_plaintext(struct SenderAddress *sender, const void *buf, size_t buf_size)
Test if we have received a valid message in plaintext.
static void receiver_destroy(struct ReceiverAddress *receiver)
Destroys a receiving state due to timeout or shutdown.
static struct GNUNET_CONTAINER_MultiShortmap * key_cache
Cache of pre-generated key IDs.
static void udp_socket_notify(struct GNUNET_UdpSocketInfo *sock_info)
#define KCN_TARGET
How many KCNs do we keep around after we hit the KCN_THRESHOLD? Should be larger than KCN_THRESHOLD s...
static void mq_cancel(struct GNUNET_MQ_Handle *mq, void *impl_state)
Implementation function that cancels the currently sent message.
static struct GNUNET_TRANSPORT_ApplicationHandle * ah
Our handle to report addresses for validation to TRANSPORT.
static void bi_destroy(struct BroadcastInterface *bi)
An interface went away, stop broadcasting on it.
static int have_v6_socket
GNUNET_YES if udp_sock supports IPv6.
static void pass_plaintext_to_core(struct SenderAddress *sender, const void *plaintext, size_t plaintext_len)
We received plaintext_len bytes of plaintext from a sender.
static struct GNUNET_CONTAINER_MultiHashMap * senders
Senders (map from peer identity to struct SenderAddress)
static int mq_init(void *cls, const struct GNUNET_PeerIdentity *peer, const char *address)
Function called by the transport service to initialize a message queue given address information abou...
static void do_broadcast(void *cls)
Scan interfaces to broadcast our presence on the LAN.
#define INTERFACE_SCAN_FREQUENCY
How often do we scan for changes to our network interfaces?
static struct GNUNET_CONTAINER_Heap * receivers_heap
Expiration heap for receivers (contains struct ReceiverAddress)
static uint16_t my_port
Port number to which we are actually bound.
static char * sockaddr_to_udpaddr_string(const struct sockaddr *address, socklen_t address_len)
Converts address to the address string format used by this communicator in HELLOs.
static void check_timeouts(void *cls)
Task run to check #receiver_heap and #sender_heap for timeouts.
static void calculate_cmac(struct SharedSecret *ss)
Calculate cmac from master in ss.
static struct GNUNET_SCHEDULER_Task * timeout_task
ID of timeout task.
char * my_ipv4
Our ipv4 address.
static struct GNUNET_SCHEDULER_Task * burst_task
static struct SharedSecret * setup_shared_secret_dec(const struct GNUNET_CRYPTO_HpkeEncapsulation *ephemeral)
Setup shared secret for decryption.
#define MAX_SQN_DELTA
What is the maximum delta between KCN sequence numbers that we allow.
static struct GNUNET_CRYPTO_EddsaPrivateKey * my_private_key
Our private key.
#define KCN_THRESHOLD
If we fall below this number of available KCNs, we generate additional ACKs until we reach KCN_TARGET...
#define MAX_SECRETS
How many shared master secrets do we keep around at most per sender? Should be large enough so that w...
static struct BroadcastInterface * bi_head
Broadcast interface tasks.
static enum GNUNET_GenericReturnValue create_receiver(const struct GNUNET_PeerIdentity *peer, const char *address, struct GNUNET_NETWORK_Handle *udp_sock)
static void eddsa_pub_to_hpke_key(struct GNUNET_CRYPTO_EddsaPublicKey *edpk, struct GNUNET_CRYPTO_EcdhePublicKey *pk)
static struct GNUNET_NETWORK_Handle * get_socket(struct ReceiverAddress *receiver)
static void send_msg_with_kx(const struct GNUNET_MessageHeader *msg, struct ReceiverAddress *receiver, struct GNUNET_MQ_Handle *mq)
static struct GNUNET_NETWORK_Handle * default_udp_sock
Our socket.
static void mq_error(void *cls, enum GNUNET_MQ_Error error)
Generic error handler, called with the appropriate error code and the same closure specified at the c...
static int iface_proc(void *cls, const char *name, int isDefault, const struct sockaddr *addr, const struct sockaddr *broadcast_addr, const struct sockaddr *netmask, socklen_t addrlen)
Callback function invoked for each interface found.
static void ifc_broadcast(void *cls)
Broadcast our presence on one of our interfaces.
static struct GNUNET_CRYPTO_EcdhePrivateKey my_x25519_private_key
Our private key for HPKE.
static void decrypt_box(const struct UDPBox *box, size_t box_len, struct KeyCacheEntry *kce)
We received a box with matching kce.
static unsigned int purge_secrets(struct SharedSecret *ss_list_tail)
Best effort try to purge some secrets.
static void consider_ss_ack(struct SharedSecret *ss)
We established a shared secret with a sender.
static unsigned long long rekey_max_bytes
How often we do rekey based on number of bytes transmitted.
#define AES_IV_SIZE
AES (GCM) IV size.
#define BROADCAST_FREQUENCY
How often do we broadcast our presence on the LAN?
static struct GNUNET_TRANSPORT_AddressIdentifier * ai
Handle to the operation that publishes our address.
static struct GNUNET_SCHEDULER_Task * st
The shutdown task.
static char * address
GNS address for this phone.
struct GNUNET_HashCode key
The key used in the DHT.
static OpusEncoder * enc
OPUS encoder.
static struct in_addr dummy
Target "dummy" address of the packet we pretend to respond to.
struct GNUNET_CRYPTO_PrivateKey pk
Private key from command line option, or NULL.
static char * name
Name (label) of the records to list.
static char * value
Value of the record to add/remove.
static uint32_t type
Type string converted to DNS type value.
static struct GNUNET_NAT_AUTO_Test * nt
Handle to a NAT test operation.
static struct GNUNET_PeerIdentity pid
Identity of the peer we transmit to / connect to.
static struct GNUNET_FS_UnindexContext * uc
commonly used definitions; globals in this file are exempt from the rule that the module name ("commo...
Constants for network protocols.
API to create, modify and access statistics.
Bandwidth allocation API for applications to interact with.
API of the transport service towards the communicator processes.
void GNUNET_TRANSPORT_communicator_address_remove(struct GNUNET_TRANSPORT_AddressIdentifier *ai)
Notify transport service about an address that this communicator no longer provides for this peer.
int GNUNET_TRANSPORT_communicator_receive(struct GNUNET_TRANSPORT_CommunicatorHandle *handle, const struct GNUNET_PeerIdentity *sender, const struct GNUNET_MessageHeader *msg, struct GNUNET_TIME_Relative expected_addr_validity, GNUNET_TRANSPORT_MessageCompletedCallback cb, void *cb_cls)
Notify transport service that the communicator has received a message.
void GNUNET_TRANSPORT_communicator_burst_finished(struct GNUNET_TRANSPORT_CommunicatorHandle *ch)
The communicator tells the transport service that it finished the burst.
void GNUNET_TRANSPORT_communicator_mq_del(struct GNUNET_TRANSPORT_QueueHandle *qh)
Notify transport service that an MQ became unavailable due to a disconnect or timeout.
void GNUNET_TRANSPORT_application_done(struct GNUNET_TRANSPORT_ApplicationHandle *ch)
Shutdown TRANSPORT application client.
#define GNUNET_TRANSPORT_QUEUE_LENGTH_UNLIMITED
Queue length.
struct GNUNET_TRANSPORT_QueueHandle * GNUNET_TRANSPORT_communicator_mq_add(struct GNUNET_TRANSPORT_CommunicatorHandle *ch, const struct GNUNET_PeerIdentity *peer, const char *address, uint32_t mtu, uint64_t q_len, uint32_t priority, enum GNUNET_NetworkType nt, enum GNUNET_TRANSPORT_ConnectionStatus cs, struct GNUNET_MQ_Handle *mq)
Notify transport service that a MQ became available due to an "inbound" connection or because the com...
void GNUNET_TRANSPORT_application_validate(struct GNUNET_TRANSPORT_ApplicationHandle *ch, const struct GNUNET_PeerIdentity *peer, enum GNUNET_NetworkType nt, const char *addr)
An application (or a communicator) has received a HELLO (or other address data of another peer) and w...
void GNUNET_TRANSPORT_communicator_mq_update(struct GNUNET_TRANSPORT_CommunicatorHandle *ch, const struct GNUNET_TRANSPORT_QueueHandle *u_qh, uint64_t q_len, uint32_t priority)
Notify transport service that an MQ was updated.
void GNUNET_TRANSPORT_communicator_notify(struct GNUNET_TRANSPORT_CommunicatorHandle *ch, const struct GNUNET_PeerIdentity *pid, const char *comm, const struct GNUNET_MessageHeader *header)
The communicator asks the transport service to route a message via a different path to another commun...
void GNUNET_TRANSPORT_communicator_disconnect(struct GNUNET_TRANSPORT_CommunicatorHandle *ch)
Disconnect from the transport service.
struct GNUNET_TRANSPORT_ApplicationHandle * GNUNET_TRANSPORT_application_init(const struct GNUNET_CONFIGURATION_Handle *cfg)
Initialize the TRANSPORT application client handle.
struct GNUNET_TRANSPORT_CommunicatorHandle * GNUNET_TRANSPORT_communicator_connect(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *config_section_name, const char *addr_prefix, enum GNUNET_TRANSPORT_CommunicatorCharacteristics cc, GNUNET_TRANSPORT_CommunicatorMqInit mq_init, void *mq_init_cls, GNUNET_TRANSPORT_CommunicatorNotify notify_cb, void *notify_cb_cls, GNUNET_TRANSPORT_StartBurstNotify sb)
Connect to the transport service.
struct GNUNET_TRANSPORT_AddressIdentifier * GNUNET_TRANSPORT_communicator_address_add(struct GNUNET_TRANSPORT_CommunicatorHandle *ch, const char *address, enum GNUNET_NetworkType nt, struct GNUNET_TIME_Relative expiration)
Notify transport service about an address that this communicator provides for this peer.
@ GNUNET_TRANSPORT_CC_UNRELIABLE
Transmission is unreliable (e.g.
@ GNUNET_TRANSPORT_CS_OUTBOUND
this is an outbound connection (transport initiated)
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_get_value_size(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, unsigned long long *size)
Get a configuration value that should be a size in bytes.
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_get_value_yesno(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option)
Get a configuration value that should be in a set of "YES" or "NO".
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_get_value_time(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, struct GNUNET_TIME_Relative *time)
Get a configuration value that should be a relative time.
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_get_value_string(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, char **value)
Get a configuration value that should be a string.
#define GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT
After how long do we consider a connection to a peer dead if we don't receive messages from the peer?
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_eddsa_kem_decaps(const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, const struct GNUNET_CRYPTO_HpkeEncapsulation *c, struct GNUNET_ShortHashCode *prk)
Decapsulate a key for a private EdDSA key.
Definition: crypto_hpke.c:407
uint64_t GNUNET_CRYPTO_random_u64(enum GNUNET_CRYPTO_Quality mode, uint64_t max)
Generate a random unsigned 64-bit value.
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_hpke_elligator_kem_decaps(const struct GNUNET_CRYPTO_EcdhePrivateKey *skR, const struct GNUNET_CRYPTO_HpkeEncapsulation *c, struct GNUNET_ShortHashCode *shared_secret)
Carries out ecdh decapsulation with own private key and the representative of the received public key...
Definition: crypto_hpke.c:470
void GNUNET_CRYPTO_random_block(enum GNUNET_CRYPTO_Quality mode, void *buffer, size_t length)
Fill block with a random values.
void GNUNET_CRYPTO_eddsa_key_get_public(const struct GNUNET_CRYPTO_EddsaPrivateKey *priv, struct GNUNET_CRYPTO_EddsaPublicKey *pub)
Extract the public key for the given private key.
Definition: crypto_ecc.c:201
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_hpke_elligator_kem_encaps(const struct GNUNET_CRYPTO_EcdhePublicKey *pkR, struct GNUNET_CRYPTO_HpkeEncapsulation *c, struct GNUNET_ShortHashCode *shared_secret)
Carries out ecdh encapsulation with given public key and the private key from a freshly created ephem...
Definition: crypto_hpke.c:449
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_eddsa_kem_encaps(const struct GNUNET_CRYPTO_EddsaPublicKey *pub, struct GNUNET_CRYPTO_HpkeEncapsulation *c, struct GNUNET_ShortHashCode *prk)
Encapsulate key material for a EdDSA public key.
Definition: crypto_hpke.c:312
#define GNUNET_CRYPTO_eddsa_sign(priv, ps, sig)
EdDSA sign a given block.
#define GNUNET_CRYPTO_eddsa_verify(purp, ps, sig, pub)
Verify EdDSA signature.
struct GNUNET_CRYPTO_EddsaPrivateKey * GNUNET_CRYPTO_eddsa_key_create_from_configuration(const struct GNUNET_CONFIGURATION_Handle *cfg)
Create a new private key by reading our peer's key from the file specified in the configuration.
@ GNUNET_CRYPTO_QUALITY_WEAK
No good quality of the operation is needed (i.e., random numbers can be pseudo-random).
#define GNUNET_CONTAINER_DLL_remove(head, tail, element)
Remove an element from a DLL.
#define GNUNET_CONTAINER_DLL_insert(head, tail, element)
Insert an element at the head of a DLL.
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_hkdf_extract(struct GNUNET_ShortHashCode *prk, const void *salt, size_t salt_len, const void *ikm, size_t ikm_len)
HKDF-Extract using SHA256.
Definition: crypto_hkdf.c:224
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:41
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_hkdf_expand(void *result, size_t out_len, const struct GNUNET_ShortHashCode *prk,...)
HKDF-Expand using SHA256.
Definition: crypto_hkdf.c:156
int GNUNET_CONTAINER_multihashmap_iterate(struct GNUNET_CONTAINER_MultiHashMap *map, GNUNET_CONTAINER_MultiHashMapIteratorCallback it, void *it_cls)
Iterate over all entries in the map.
void * GNUNET_CONTAINER_multihashmap_get(const struct GNUNET_CONTAINER_MultiHashMap *map, const struct GNUNET_HashCode *key)
Given a key find a value in the map matching the key.
enum GNUNET_GenericReturnValue GNUNET_CONTAINER_multihashmap_remove(struct GNUNET_CONTAINER_MultiHashMap *map, const struct GNUNET_HashCode *key, const void *value)
Remove the given key-value pair from the map.
struct GNUNET_CONTAINER_MultiShortmap * GNUNET_CONTAINER_multishortmap_create(unsigned int len, int do_not_copy_keys)
Create a multi peer map (hash map for public keys of peers).
enum GNUNET_GenericReturnValue GNUNET_CONTAINER_multishortmap_put(struct GNUNET_CONTAINER_MultiShortmap *map, const struct GNUNET_ShortHashCode *key, void *value, enum GNUNET_CONTAINER_MultiHashMapOption opt)
Store a key-value pair in the map.
enum GNUNET_GenericReturnValue GNUNET_CONTAINER_multihashmap_put(struct GNUNET_CONTAINER_MultiHashMap *map, const struct GNUNET_HashCode *key, void *value, enum GNUNET_CONTAINER_MultiHashMapOption opt)
Store a key-value pair in the map.
void * GNUNET_CONTAINER_multishortmap_get(const struct GNUNET_CONTAINER_MultiShortmap *map, const struct GNUNET_ShortHashCode *key)
Given a key find a value in the map matching the key.
unsigned int GNUNET_CONTAINER_multihashmap_size(const struct GNUNET_CONTAINER_MultiHashMap *map)
Get the number of key-value pairs in the map.
void GNUNET_CONTAINER_multihashmap_destroy(struct GNUNET_CONTAINER_MultiHashMap *map)
Destroy a hash map.
struct GNUNET_CONTAINER_MultiHashMap * GNUNET_CONTAINER_multihashmap_create(unsigned int len, int do_not_copy_keys)
Create a multi hash map.
void GNUNET_CONTAINER_multishortmap_destroy(struct GNUNET_CONTAINER_MultiShortmap *map)
Destroy a hash map.
enum GNUNET_GenericReturnValue GNUNET_CONTAINER_multihashmap_get_multiple(struct GNUNET_CONTAINER_MultiHashMap *map, const struct GNUNET_HashCode *key, GNUNET_CONTAINER_MultiHashMapIteratorCallback it, void *it_cls)
Iterate over all entries in the map that match a particular key.
unsigned int GNUNET_CONTAINER_multishortmap_size(const struct GNUNET_CONTAINER_MultiShortmap *map)
Get the number of key-value pairs in the map.
int GNUNET_CONTAINER_multishortmap_remove(struct GNUNET_CONTAINER_MultiShortmap *map, const struct GNUNET_ShortHashCode *key, const void *value)
Remove the given key-value pair from the map.
@ GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE
Allow multiple values with the same key.
void * GNUNET_CONTAINER_heap_remove_node(struct GNUNET_CONTAINER_HeapNode *node)
Removes a node from the heap.
void * GNUNET_CONTAINER_heap_peek(const struct GNUNET_CONTAINER_Heap *heap)
Get element stored at the root of heap.
void GNUNET_CONTAINER_heap_update_cost(struct GNUNET_CONTAINER_HeapNode *node, GNUNET_CONTAINER_HeapCostType new_cost)
Updates the cost of any node in the tree.
struct GNUNET_CONTAINER_HeapNode * GNUNET_CONTAINER_heap_insert(struct GNUNET_CONTAINER_Heap *heap, void *element, GNUNET_CONTAINER_HeapCostType cost)
Inserts a new element into the heap.
struct GNUNET_CONTAINER_Heap * GNUNET_CONTAINER_heap_create(enum GNUNET_CONTAINER_HeapOrder order)
Create a new heap.
void GNUNET_CONTAINER_heap_destroy(struct GNUNET_CONTAINER_Heap *heap)
Destroys the heap.
@ GNUNET_CONTAINER_HEAP_ORDER_MIN
Heap with the minimum cost at the root.
#define GNUNET_NETWORK_STRUCT_BEGIN
Define as empty, GNUNET_PACKED should suffice, but this won't work on W32.
uint16_t type
The type of the message (GNUNET_MESSAGE_TYPE_XXXX), in big-endian format.
#define GNUNET_log(kind,...)
void GNUNET_CRYPTO_hash_context_read(struct GNUNET_HashContext *hc, const void *buf, size_t size)
Add data to be hashed.
Definition: crypto_hash.c:366
#define GNUNET_NETWORK_STRUCT_END
Define as empty, GNUNET_PACKED should suffice, but this won't work on W32;.
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
void GNUNET_CRYPTO_hash_context_finish(struct GNUNET_HashContext *hc, struct GNUNET_HashCode *r_hash)
Finish the hash computation.
Definition: crypto_hash.c:390
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_hpke_sk_to_x25519(const struct GNUNET_CRYPTO_PrivateKey *sk, struct GNUNET_CRYPTO_EcdhePrivateKey *x25519)
Convert a GNUnet identity key to a key sutiable for HPKE (X25519)
Definition: crypto_hpke.c:1013
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
enum GNUNET_GenericReturnValue GNUNET_CRYPTO_hpke_pk_to_x25519(const struct GNUNET_CRYPTO_PublicKey *pk, struct GNUNET_CRYPTO_EcdhePublicKey *x25519)
Convert a GNUnet identity key to a key sutiable for HPKE (X25519)
Definition: crypto_hpke.c:989
GNUNET_GenericReturnValue
Named constants for return values.
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format.
struct GNUNET_HashContext * GNUNET_CRYPTO_hash_context_start(void)
Start incremental hashing operation.
Definition: crypto_hash.c:350
#define GNUNET_PACKED
gcc-ism to get packed structs.
@ GNUNET_PUBLIC_KEY_TYPE_EDDSA
EDDSA identity.
@ GNUNET_OK
@ GNUNET_YES
@ GNUNET_NO
@ GNUNET_SYSERR
#define GNUNET_break_op(cond)
Use this for assertion violations caused by other peers (i.e.
const char * GNUNET_i2s(const struct GNUNET_PeerIdentity *pid)
Convert a peer identity to a string (for printing debug messages).
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
const char * GNUNET_sh2s(const struct GNUNET_ShortHashCode *shc)
Convert a short hash value to a string (for printing debug messages).
const char * GNUNET_i2s_full(const struct GNUNET_PeerIdentity *pid)
Convert a peer identity to a string (for printing debug messages).
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur.
const char * GNUNET_h2s(const struct GNUNET_HashCode *hc)
Convert a hash value to a string (for printing debug messages).
const char * GNUNET_a2s(const struct sockaddr *addr, socklen_t addrlen)
Convert a "struct sockaddr*" (IPv4 or IPv6 address) to a string (for printing debug messages).
void GNUNET_log_config_missing(enum GNUNET_ErrorType kind, const char *section, const char *option)
Log error message about missing configuration option.
#define GNUNET_log_strerror(level, cmd)
Log an error message at log-level 'level' that indicates a failure of the command 'cmd' with the mess...
void GNUNET_log_from_nocheck(enum GNUNET_ErrorType kind, const char *comp, const char *message,...) __attribute__((format(printf
Log function that specifies an alternative component.
#define GNUNET_log_strerror_file(level, cmd, filename)
Log an error message at log-level 'level' that indicates a failure of the command 'cmd' with the mess...
@ GNUNET_ERROR_TYPE_WARNING
@ GNUNET_ERROR_TYPE_ERROR
@ GNUNET_ERROR_TYPE_DEBUG
@ GNUNET_ERROR_TYPE_INFO
int int GNUNET_asprintf(char **buf, const char *format,...) __attribute__((format(printf
Like asprintf, just portable.
#define GNUNET_strdup(a)
Wrapper around GNUNET_xstrdup_.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
#define GNUNET_malloc(size)
Wrapper around malloc.
#define GNUNET_free(ptr)
Wrapper around free.
#define GNUNET_memdup(buf, size)
Allocate and initialize a block of memory.
GNUNET_MQ_Error
Error codes for the queue.
struct GNUNET_MQ_Handle * GNUNET_MQ_queue_for_callbacks(GNUNET_MQ_SendImpl send, GNUNET_MQ_DestroyImpl destroy, GNUNET_MQ_CancelImpl cancel, void *impl_state, const struct GNUNET_MQ_MessageHandler *handlers, GNUNET_MQ_ErrorHandler error_handler, void *cls)
Create a message queue for the specified handlers.
Definition: mq.c:482
void GNUNET_MQ_impl_send_continue(struct GNUNET_MQ_Handle *mq)
Call the send implementation for the next queued message, if any.
Definition: mq.c:437
void GNUNET_MQ_destroy(struct GNUNET_MQ_Handle *mq)
Destroy the message queue.
Definition: mq.c:700
struct GNUNET_SCHEDULER_Task * GNUNET_get_udp_socket(struct GNUNET_UdpSocketInfo *sock_info, GNUNET_NotifyUdpSocket nus)
Method to get a UDP socket for a peer that is natted.
Definition: nat.c:509
struct GNUNET_NAT_Handle * GNUNET_NAT_register(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *config_section, uint8_t proto, unsigned int num_addrs, const struct sockaddr **addrs, const socklen_t *addrlens, GNUNET_NAT_AddressCallback address_callback, GNUNET_NAT_ReversalCallback reversal_callback, void *callback_cls)
Attempt to enable port redirection and detect public IP address contacting UPnP or NAT-PMP routers on...
Definition: nat_api.c:366
void GNUNET_NAT_unregister(struct GNUNET_NAT_Handle *nh)
Stop port redirection and public IP address detection for the given handle.
Definition: nat_api.c:703
void GNUNET_stop_burst(struct GNUNET_NETWORK_Handle *do_not_touch)
Method to stop all sockets we established to the other peer.
Definition: nat.c:564
GNUNET_NAT_AddressClass
Some addresses contain sensitive information or are not suitable for global distribution.
enum GNUNET_GenericReturnValue GNUNET_NETWORK_socket_close(struct GNUNET_NETWORK_Handle *desc)
Close a socket.
Definition: network.c:508
int GNUNET_NETWORK_get_fd(const struct GNUNET_NETWORK_Handle *desc)
Return file descriptor for this network handle.
Definition: network.c:1001
ssize_t GNUNET_NETWORK_socket_recvfrom(const struct GNUNET_NETWORK_Handle *desc, void *buffer, size_t length, struct sockaddr *src_addr, socklen_t *addrlen)
Read data from a socket (always non-blocking).
Definition: network.c:688
struct GNUNET_NETWORK_Handle * GNUNET_NETWORK_socket_create(int domain, int type, int protocol)
Create a new socket.
Definition: network.c:833
enum GNUNET_GenericReturnValue GNUNET_NETWORK_test_pf(int pf)
Test if the given protocol family is supported by this system.
Definition: network.c:79
enum GNUNET_GenericReturnValue GNUNET_NETWORK_socket_bind(struct GNUNET_NETWORK_Handle *desc, const struct sockaddr *address, socklen_t address_len)
Bind a socket to a particular address.
Definition: network.c:439
int GNUNET_NETWORK_socket_setsockopt(struct GNUNET_NETWORK_Handle *fd, int level, int option_name, const void *option_value, socklen_t option_len)
Set socket option.
Definition: network.c:806
ssize_t GNUNET_NETWORK_socket_sendto(const struct GNUNET_NETWORK_Handle *desc, const void *message, size_t length, const struct sockaddr *dest_addr, socklen_t dest_len)
Send data to a particular destination (always non-blocking).
Definition: network.c:772
GNUNET_NetworkType
Types of networks (with separate quotas) we support.
Definition: gnunet_nt_lib.h:44
void GNUNET_NT_scanner_done(struct GNUNET_NT_InterfaceScanner *is)
Terminate interface scanner.
Definition: nt.c:428
struct GNUNET_NT_InterfaceScanner * GNUNET_NT_scanner_init(void)
Initialize the address characterization client handle.
Definition: nt.c:407
enum GNUNET_NetworkType GNUNET_NT_scanner_get_type(struct GNUNET_NT_InterfaceScanner *is, const struct sockaddr *addr, socklen_t addrlen)
Returns where the address is located: loopback, LAN or WAN.
Definition: nt.c:309
@ GNUNET_NT_LOOPBACK
Loopback (same host).
Definition: gnunet_nt_lib.h:53
void GNUNET_OS_network_interfaces_list(GNUNET_OS_NetworkInterfaceProcessor proc, void *proc_cls)
Enumerate all network interfaces.
Definition: os_network.c:397
#define GNUNET_DAEMON_MAIN(daemon_name, daemon_help, init_cb)
#define GNUNET_MESSAGE_TYPE_COMMUNICATOR_UDP_REKEY
UDP Rekey.
#define GNUNET_MESSAGE_TYPE_COMMUNICATOR_UDP_PAD
UDP communicator padding.
#define GNUNET_MESSAGE_TYPE_COMMUNICATOR_UDP_ACK
UDP KX acknowledgement.
void GNUNET_SCHEDULER_shutdown(void)
Request the shutdown of a scheduler.
Definition: scheduler.c:566
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_read_net(struct GNUNET_TIME_Relative delay, struct GNUNET_NETWORK_Handle *rfd, GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run with a specified delay or when the specified file descriptor is ready f...
Definition: scheduler.c:1510
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_shutdown(GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run on shutdown, that is when a CTRL-C signal is received,...
Definition: scheduler.c:1338
void * GNUNET_SCHEDULER_cancel(struct GNUNET_SCHEDULER_Task *task)
Cancel the task with the specified identifier.
Definition: scheduler.c:979
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_now(GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run as soon as possible.
Definition: scheduler.c:1303
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_delayed(struct GNUNET_TIME_Relative delay, GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run with a specified delay.
Definition: scheduler.c:1276
struct GNUNET_STATISTICS_Handle * GNUNET_STATISTICS_create(const char *subsystem, const struct GNUNET_CONFIGURATION_Handle *cfg)
Get handle for the statistics service.
void GNUNET_STATISTICS_set(struct GNUNET_STATISTICS_Handle *handle, const char *name, uint64_t value, int make_persistent)
Set statistic value for the peer.
void GNUNET_STATISTICS_update(struct GNUNET_STATISTICS_Handle *handle, const char *name, int64_t delta, int make_persistent)
Set statistic value for the peer.
void GNUNET_STATISTICS_destroy(struct GNUNET_STATISTICS_Handle *h, int sync_first)
Destroy a handle (free all state associated with it).
struct GNUNET_TIME_Relative GNUNET_TIME_relative_min(struct GNUNET_TIME_Relative t1, struct GNUNET_TIME_Relative t2)
Return the minimum of two relative time values.
Definition: time.c:344
#define GNUNET_TIME_UNIT_FOREVER_REL
Constant used to specify "forever".
struct GNUNET_TIME_Relative GNUNET_TIME_absolute_get_remaining(struct GNUNET_TIME_Absolute future)
Given a timestamp in the future, how much time remains until then?
Definition: time.c:406
struct GNUNET_TIME_Absolute GNUNET_TIME_relative_to_absolute(struct GNUNET_TIME_Relative rel)
Convert relative time to an absolute time in the future.
Definition: time.c:316
struct GNUNET_TIME_Absolute GNUNET_TIME_absolute_get_monotonic(const struct GNUNET_CONFIGURATION_Handle *cfg)
Obtain the current time and make sure it is monotonically increasing.
Definition: time.c:862
struct GNUNET_TIME_AbsoluteNBO GNUNET_TIME_absolute_hton(struct GNUNET_TIME_Absolute a)
Convert absolute time to network byte order.
Definition: time.c:640
#define _(String)
GNU gettext support macro.
Definition: platform.h:178
void receiver(void *cls, const void *buf, size_t available, const struct sockaddr *addr, socklen_t addrlen, int errCode)
Callback to read from the SOCKS5 proxy.
Definition: socks.c:330
#define GNUNET_SIGNATURE_PURPOSE_COMMUNICATOR_UDP_BROADCAST
Signature used by UDP broadcasts.
#define GNUNET_SIGNATURE_PURPOSE_COMMUNICATOR_UDP_HANDSHAKE
Signature used by UDP communicator handshake.
const struct UDPAck * ack
const struct GNUNET_PeerIdentity * sender
Interface we broadcast our presence on.
socklen_t salen
Number of bytes in sa.
struct ipv6_mreq mcreq
If this is an IPv6 interface, this is the request we use to join/leave the group.
struct BroadcastInterface * next
Kept in a DLL.
int found
Was this interface found in the last iface_proc() scan?
struct UDPBroadcast bcm
Message we broadcast on this interface.
struct sockaddr * ba
Broadcast address to use on the interface.
struct GNUNET_SCHEDULER_Task * broadcast_task
Task for this broadcast interface.
struct BroadcastInterface * prev
Kept in a DLL.
struct sockaddr * sa
Sender's address of the interface.
Message send during burst mode.
struct GNUNET_PeerIdentity peer
The peer who send the msg.
unsigned int local_port
The local port the message was send from.
Handle to a node in a heap.
Internal representation of the hash map.
Internal representation of the hash map.
header of what an ECC signature signs this must be followed by "size - 8" bytes of the actual signed ...
uint32_t size
How many bytes does this signature sign? (including this purpose header); in network byte order (!...
uint32_t purpose
What does this signature vouch for? This must contain a GNUNET_SIGNATURE_PURPOSE_XXX constant (from g...
Private ECC key encoded for transmission.
Public ECC key (always for Curve25519) encoded in a format suitable for network transmission and encr...
Private ECC key encoded for transmission.
Public ECC key (always for curve Ed25519) encoded in a format suitable for network transmission and E...
an ECC signature using EdDSA.
HPKE DHKEM encapsulation (X25519) See RFC 9180.
A private key for an identity as per LSD0001.
An identity key as per LSD0001.
A 512-bit hashcode.
Handle to a message queue.
Definition: mq.c:87
Header for all communications.
Handle for active NAT registrations.
Definition: nat_api.c:72
handle to a socket
Definition: network.c:53
Handle to the interface scanner.
Definition: nt.c:104
The identity of the host (wraps the signing key of the peer).
struct GNUNET_CRYPTO_EddsaPublicKey public_key
Entry in list of pending tasks.
Definition: scheduler.c:135
Handle for the service.
A 256-bit hashcode.
Time for absolute time used by GNUnet, in microseconds and in network byte order.
Time for absolute times used by GNUnet, in microseconds.
uint64_t abs_value_us
The actual value.
Time for relative time used by GNUnet, in microseconds.
uint64_t rel_value_us
The actual value.
Internal representation of an address a communicator is currently providing for the transport service...
Handle to the TRANSPORT subsystem for application management.
Opaque handle to the transport service for communicators.
Handle returned to identify the internal data structure the transport API has created to manage a mes...
Standard IPv4 header.
Standard IPv6 header.
UDP packet header.
Struct with the socket we like to use to send messages to another peer.
const char * bind_address
Our address without port.
enum GNUNET_GenericReturnValue has_port
Flag indicating, if the address is without port information.
struct GNUNET_TIME_Relative rtt
The actual RTT between the peers.
char * address
The address of the other peer without port.
unsigned int std_port
Default local port we are bound to.
struct sockaddr * actual_address
The address of the other peer we received a burst message from.
struct GNUNET_NETWORK_Handle * udp_sock
struct GNUNET_PeerIdentity * pid
The peer we like to connect to.
"Plaintext" header at beginning of KX message.
uint8_t gcm_tag[(128/8)]
HMAC for the following encrypted message, using GCM.
struct GNUNET_CRYPTO_HpkeEncapsulation enc
Representative of ephemeral key for KX.
Pre-generated "kid" code (key and IV identification code) to quickly derive master key for a struct U...
struct GNUNET_ShortHashCode kid
Key and IV identification code.
uint32_t sequence_number
Sequence number used to derive this entry from master key.
struct KeyCacheEntry * next
Kept in a DLL.
struct KeyCacheEntry * prev
Kept in a DLL.
struct SharedSecret * ss
Corresponding shared secret.
Information we track per receiving address we have recently been in contact with (encryption to recei...
struct GNUNET_CONTAINER_HeapNode * hn
Entry in sender expiration heap.
struct GNUNET_TIME_Absolute rekey_timeout
Timeout for this receiver address.
struct SharedSecret * ss_tail
Shared secrets we received with target, last used is tail.
char * foreign_addr
Address of the receiver in the human-readable format with the COMMUNICATOR_ADDRESS_PREFIX.
struct GNUNET_SCHEDULER_Task * read_task
Read task, if this receiver has its own socket.
unsigned int acks_available
Number of BOX keys from ACKs we have currently available for this receiver.
struct SharedSecret * ss_head
Shared secrets we received from target, first used is head.
struct GNUNET_TRANSPORT_QueueHandle * kx_qh
handle for KX queue with the ch.
unsigned int num_secrets
Length of the DLL at ss_head.
struct GNUNET_TIME_Absolute timeout
Timeout for this receiver address.
size_t kx_mtu
MTU we allowed transport for this receiver's KX queue.
struct sockaddr * address
Address of the other peer.
struct GNUNET_PeerIdentity target
To whom are we talking to.
socklen_t address_len
Length of the address.
struct GNUNET_MQ_Handle * kx_mq
KX message queue we are providing for the ch.
int receiver_destroy_called
receiver_destroy already called on receiver.
struct GNUNET_NETWORK_Handle * udp_sock
Socket this receiver got via NAT traversal.
size_t d_mtu
MTU we allowed transport for this receiver's default queue.
enum GNUNET_NetworkType nt
Which network type does this queue use?
struct GNUNET_MQ_Handle * d_mq
Default message queue we are providing for the ch.
struct GNUNET_CRYPTO_EcdhePublicKey target_hpke_key
To whom are we talking to.
struct GNUNET_TRANSPORT_QueueHandle * d_qh
handle for default queue with the ch.
struct GNUNET_HashCode key
The address key for this entry.
Closure for #find_sender_by_address()
const struct sockaddr * address
Address we are looking for.
struct SenderAddress * sender
Return value to set if we found a match.
socklen_t address_len
Number of bytes in address.
Information we track per sender address we have recently been in contact with (we decrypt messages fr...
struct GNUNET_PeerIdentity target
To whom are we talking to.
struct GNUNET_CONTAINER_HeapNode * hn
Entry in sender expiration heap.
struct sockaddr * address
Address of the other peer.
socklen_t address_len
Length of the address.
enum GNUNET_NetworkType nt
Which network type does this queue use?
unsigned int acks_available
Number of BOX keys from ACKs we have currently available for this sender.
unsigned int num_secrets
Length of the DLL at ss_head.
int kce_send_ack_on_finish
When KCE finishes, send ACK if GNUNET_YES.
struct GNUNET_TIME_Absolute timeout
Timeout for this sender.
int kce_task_finished
Is the kce_task finished?
struct GNUNET_SCHEDULER_Task * kce_task
ID of kce working queue task.
struct GNUNET_HashCode key
The address key for this entry.
struct SharedSecret * ss_head
Shared secrets we used with target, first used is head.
int sender_destroy_called
sender_destroy already called on sender.
struct SharedSecret * ss_tail
Shared secrets we used with target, last used is tail.
Shared secret we generated for a particular sender or receiver.
struct KeyCacheEntry * kce_tail
Kept in a DLL, sorted by sequence number.
uint32_t sequence_allowed
Up to which sequence number did the other peer allow us to use this key, or up to which number did we...
struct SharedSecret * next
Kept in a DLL.
unsigned int active_kce_count
Number of active KCN entries.
uint32_t sequence_used
Up to which sequence number did we use this master already? (for encrypting only)
size_t bytes_sent
Bytes sent with this shared secret.
struct SharedSecret * prev
Kept in a DLL.
struct SenderAddress * sender
Sender we use this shared secret with, or NULL.
struct KeyCacheEntry * kce_head
Kept in a DLL, sorted by sequence number.
struct GNUNET_HashCode cmac
CMAC is used to identify master in ACKs.
struct ReceiverAddress * receiver
Receiver we use this shared secret with, or NULL.
struct GNUNET_ShortHashCode master
Master shared secret.
int override_available_acks
Also precompute keys despite sufficient acks (for rekey)
int rekey_initiated
rekey initiated for this secret?
UDP key acknowledgement.
uint32_t sequence_ack
Sequence acknowledgement limit.
struct GNUNET_HashCode cmac
CMAC of the base key being acknowledged.
struct GNUNET_MessageHeader header
Type is GNUNET_MESSAGE_TYPE_COMMUNICATOR_UDP_ACK.
UDP message box.
uint8_t gcm_tag[(128/8)]
128-bit authentication tag for the following encrypted message, from GCM.
struct GNUNET_ShortHashCode kid
Key and IV identification code.
Broadcast by peer in LAN announcing its presence.
struct GNUNET_CRYPTO_EddsaSignature sender_sig
Sender's signature of type GNUNET_SIGNATURE_PURPOSE_COMMUNICATOR_UDP_BROADCAST.
struct GNUNET_PeerIdentity sender
Sender's peer identity.
Encrypted continuation of UDP initial handshake, followed by message header with payload.
struct GNUNET_PeerIdentity sender
Sender's identity.
struct GNUNET_CRYPTO_EddsaSignature sender_sig
Sender's signature of type GNUNET_SIGNATURE_PURPOSE_COMMUNICATOR_UDP_HANDSHAKE.
struct GNUNET_TIME_AbsoluteNBO monotonic_time
Monotonic time of sender, to possibly help detect replay attacks (if receiver persists times by sende...
Plaintext of a rekey payload in a UDPBox.
struct GNUNET_CRYPTO_HpkeEncapsulation ephemeral
Ephemeral key to rekey with.
struct GNUNET_MessageHeader header
Type is GNUNET_MESSAGE_TYPE_COMMUNICATOR_UDP_REKEY.
Signature we use to verify that the broadcast was really made by the peer that claims to have made it...
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
Purpose must be GNUNET_SIGNATURE_PURPOSE_COMMUNICATOR_UDP_BROADCAST.
struct GNUNET_HashCode h_address
Hash of the sender's UDP address.
struct GNUNET_PeerIdentity sender
Identity of the inititor of the UDP broadcast.
Signature we use to verify that the ephemeral key was really chosen by the specified sender.
struct GNUNET_CRYPTO_HpkeEncapsulation enc
Ephemeral key used by the sender.
struct GNUNET_PeerIdentity receiver
Presumed identity of the target of the UDP connection (UDP server)
struct GNUNET_TIME_AbsoluteNBO monotonic_time
Monotonic time of sender, to possibly help detect replay attacks (if receiver persists times by sende...
struct GNUNET_CRYPTO_EccSignaturePurpose purpose
Purpose must be GNUNET_SIGNATURE_PURPOSE_COMMUNICATOR_UDP_HANDSHAKE.
struct GNUNET_PeerIdentity sender
Identity of the inititor of the UDP connection (UDP client).