diff options
author | Christian Grothoff <christian@grothoff.org> | 2019-04-22 11:48:12 +0200 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2019-04-22 11:48:12 +0200 |
commit | 38300a8d3b441cc492adcd72d4a60b861eea0e95 (patch) | |
tree | 5a1b3dd4cb7dee4fb9ec819399eb015a4ad5f262 /src/transport/gnunet-service-tng.c | |
parent | 2429db6e434feff044cafc71bd25efe104799b47 (diff) | |
download | gnunet-38300a8d3b441cc492adcd72d4a60b861eea0e95.tar.gz gnunet-38300a8d3b441cc492adcd72d4a60b861eea0e95.zip |
changing UUID types (in preparation for RTT tracking)
Diffstat (limited to 'src/transport/gnunet-service-tng.c')
-rw-r--r-- | src/transport/gnunet-service-tng.c | 137 |
1 files changed, 116 insertions, 21 deletions
diff --git a/src/transport/gnunet-service-tng.c b/src/transport/gnunet-service-tng.c index c4974ca23..a35357d9b 100644 --- a/src/transport/gnunet-service-tng.c +++ b/src/transport/gnunet-service-tng.c | |||
@@ -25,6 +25,21 @@ | |||
25 | * TODO: | 25 | * TODO: |
26 | * Implement next: | 26 | * Implement next: |
27 | * - track RTT, distance, loss, etc. => requires extra data structures! | 27 | * - track RTT, distance, loss, etc. => requires extra data structures! |
28 | * => fragment UUIDs should be 'sequential' 32-bit numbers, for cummulative | ||
29 | * acks with Bitmask | ||
30 | * => fragments carry their own offsets, so receiver will NOT require | ||
31 | * seeing all the possible values | ||
32 | * => can generate 'fresh' UUIDs for each retransmission to track it | ||
33 | * => but need to keep 'map' of 32-bit UUID to queue! | ||
34 | * => message UUIDs are currently overkill with 256 bits | ||
35 | * => cummulative acks for messages include full UUID list | ||
36 | * => message UUID size should be chosen to result in 8 byte alignment | ||
37 | * => could encode 32-bit counter + 32-bit queue UUID in 64-bit message | ||
38 | * UUID? | ||
39 | * => Use multihashmap32 on counter for lookup in hashmap? | ||
40 | * => FIXME: 2x32 bit introduced, but still set to random value | ||
41 | * instead of using the generators! | ||
42 | * (and generators not initialized to random starting values either) | ||
28 | * - consider replacing random `struct GNUNET_ShortHashCode` message UUIDs | 43 | * - consider replacing random `struct GNUNET_ShortHashCode` message UUIDs |
29 | * with (incrementing) 64-bit numbers (compacting both | 44 | * with (incrementing) 64-bit numbers (compacting both |
30 | * `struct TransportReliabilityBox` and `struct | 45 | * `struct TransportReliabilityBox` and `struct |
@@ -260,9 +275,16 @@ GNUNET_NETWORK_STRUCT_BEGIN | |||
260 | struct MessageUUIDP | 275 | struct MessageUUIDP |
261 | { | 276 | { |
262 | /** | 277 | /** |
263 | * Unique value. | 278 | * Unique value, generated by incrementing the |
279 | * `message_uuid_ctr` of `struct Neighbour`. | ||
264 | */ | 280 | */ |
265 | struct GNUNET_ShortHashCode uuid; // FIXME: change to 8 bytes | 281 | uint32_t uuid GNUNET_PACKED; |
282 | |||
283 | /** | ||
284 | * UUID of the queue that was used to transmit this message. | ||
285 | * Used to map acknowledgements back to the respective queue. | ||
286 | */ | ||
287 | uint32_t queue_uuid GNUNET_PACKED; | ||
266 | }; | 288 | }; |
267 | 289 | ||
268 | 290 | ||
@@ -274,7 +296,7 @@ struct FragmentUUIDP | |||
274 | /** | 296 | /** |
275 | * Unique value identifying a fragment, in NBO. | 297 | * Unique value identifying a fragment, in NBO. |
276 | */ | 298 | */ |
277 | uint32_t uuid GNUNET_PACKED; // FIXME: change to 2x 2 bytes? | 299 | uint32_t uuid GNUNET_PACKED; |
278 | }; | 300 | }; |
279 | 301 | ||
280 | 302 | ||
@@ -1278,6 +1300,14 @@ struct Queue | |||
1278 | uint32_t qid; | 1300 | uint32_t qid; |
1279 | 1301 | ||
1280 | /** | 1302 | /** |
1303 | * UUID used to map acknowledgements back to the queue that | ||
1304 | * was used for transmission. Note that @e queue_uuid-s are | ||
1305 | * only unique per neighbour (generated via `queue_uuid_gen` | ||
1306 | * of `struct Neighbour`). | ||
1307 | */ | ||
1308 | uint32_t queue_uuid; | ||
1309 | |||
1310 | /** | ||
1281 | * Maximum transmission unit supported by this queue. | 1311 | * Maximum transmission unit supported by this queue. |
1282 | */ | 1312 | */ |
1283 | uint32_t mtu; | 1313 | uint32_t mtu; |
@@ -1426,7 +1456,7 @@ struct Neighbour | |||
1426 | * reassembly. May be NULL if we currently have no fragments from | 1456 | * reassembly. May be NULL if we currently have no fragments from |
1427 | * this @e pid (lazy initialization). | 1457 | * this @e pid (lazy initialization). |
1428 | */ | 1458 | */ |
1429 | struct GNUNET_CONTAINER_MultiShortmap *reassembly_map; | 1459 | struct GNUNET_CONTAINER_MultiHashMap32 *reassembly_map; |
1430 | 1460 | ||
1431 | /** | 1461 | /** |
1432 | * Heap with `struct ReassemblyContext` structs for fragments under | 1462 | * Heap with `struct ReassemblyContext` structs for fragments under |
@@ -1497,6 +1527,26 @@ struct Neighbour | |||
1497 | struct GNUNET_TIME_Absolute earliest_timeout; | 1527 | struct GNUNET_TIME_Absolute earliest_timeout; |
1498 | 1528 | ||
1499 | /** | 1529 | /** |
1530 | * Incremented by one for each queue to generate | ||
1531 | * unique queue identifiers. Initially set to a random value. | ||
1532 | * | ||
1533 | * FIXME: Deal with wrap around (might be triggered by very | ||
1534 | * persistent adversary). | ||
1535 | */ | ||
1536 | uint32_t queue_uuid_gen; | ||
1537 | |||
1538 | /** | ||
1539 | * Incremented by one for each message sent to this neighbour, to | ||
1540 | * uniquely identify that message in replies (note that fragments | ||
1541 | * use another additional counter). Initially set to a random value. | ||
1542 | * | ||
1543 | * It should be safe to assume that by the time this value may wrap | ||
1544 | * around, the original message is long "gone" and no longer | ||
1545 | * relevant. | ||
1546 | */ | ||
1547 | uint32_t message_uuid_ctr; | ||
1548 | |||
1549 | /** | ||
1500 | * Do we have a confirmed working queue and are thus visible to | 1550 | * Do we have a confirmed working queue and are thus visible to |
1501 | * CORE? | 1551 | * CORE? |
1502 | */ | 1552 | */ |
@@ -2421,9 +2471,9 @@ free_reassembly_context (struct ReassemblyContext *rc) | |||
2421 | 2471 | ||
2422 | GNUNET_assert (rc == GNUNET_CONTAINER_heap_remove_node (rc->hn)); | 2472 | GNUNET_assert (rc == GNUNET_CONTAINER_heap_remove_node (rc->hn)); |
2423 | GNUNET_assert (GNUNET_OK == | 2473 | GNUNET_assert (GNUNET_OK == |
2424 | GNUNET_CONTAINER_multishortmap_remove (n->reassembly_map, | 2474 | GNUNET_CONTAINER_multihashmap32_remove (n->reassembly_map, |
2425 | &rc->msg_uuid.uuid, | 2475 | rc->msg_uuid.uuid, |
2426 | rc)); | 2476 | rc)); |
2427 | GNUNET_free (rc); | 2477 | GNUNET_free (rc); |
2428 | } | 2478 | } |
2429 | 2479 | ||
@@ -2467,9 +2517,7 @@ reassembly_cleanup_task (void *cls) | |||
2467 | * @return #GNUNET_OK (continue iteration) | 2517 | * @return #GNUNET_OK (continue iteration) |
2468 | */ | 2518 | */ |
2469 | static int | 2519 | static int |
2470 | free_reassembly_cb (void *cls, | 2520 | free_reassembly_cb (void *cls, uint32_t key, void *value) |
2471 | const struct GNUNET_ShortHashCode *key, | ||
2472 | void *value) | ||
2473 | { | 2521 | { |
2474 | struct ReassemblyContext *rc = value; | 2522 | struct ReassemblyContext *rc = value; |
2475 | 2523 | ||
@@ -2499,10 +2547,10 @@ free_neighbour (struct Neighbour *neighbour) | |||
2499 | GNUNET_SCHEDULER_cancel (neighbour->timeout_task); | 2547 | GNUNET_SCHEDULER_cancel (neighbour->timeout_task); |
2500 | if (NULL != neighbour->reassembly_map) | 2548 | if (NULL != neighbour->reassembly_map) |
2501 | { | 2549 | { |
2502 | GNUNET_CONTAINER_multishortmap_iterate (neighbour->reassembly_map, | 2550 | GNUNET_CONTAINER_multihashmap32_iterate (neighbour->reassembly_map, |
2503 | &free_reassembly_cb, | 2551 | &free_reassembly_cb, |
2504 | NULL); | 2552 | NULL); |
2505 | GNUNET_CONTAINER_multishortmap_destroy (neighbour->reassembly_map); | 2553 | GNUNET_CONTAINER_multihashmap32_destroy (neighbour->reassembly_map); |
2506 | neighbour->reassembly_map = NULL; | 2554 | neighbour->reassembly_map = NULL; |
2507 | GNUNET_CONTAINER_heap_destroy (neighbour->reassembly_heap); | 2555 | GNUNET_CONTAINER_heap_destroy (neighbour->reassembly_heap); |
2508 | neighbour->reassembly_heap = NULL; | 2556 | neighbour->reassembly_heap = NULL; |
@@ -4242,6 +4290,48 @@ send_fragment_ack (struct ReassemblyContext *rc) | |||
4242 | 4290 | ||
4243 | 4291 | ||
4244 | /** | 4292 | /** |
4293 | * Closure for #find_by_message_uuid. | ||
4294 | */ | ||
4295 | struct FindByMessageUuidContext | ||
4296 | { | ||
4297 | /** | ||
4298 | * UUID to look for. | ||
4299 | */ | ||
4300 | struct MessageUUIDP message_uuid; | ||
4301 | |||
4302 | /** | ||
4303 | * Set to the reassembly context if found. | ||
4304 | */ | ||
4305 | struct ReassemblyContext *rc; | ||
4306 | }; | ||
4307 | |||
4308 | |||
4309 | /** | ||
4310 | * Iterator called to find a reassembly context by the message UUID in the | ||
4311 | * multihashmap32. | ||
4312 | * | ||
4313 | * @param cls a `struct FindByMessageUuidContext` | ||
4314 | * @param key a key (unused) | ||
4315 | * @param value a `struct ReassemblyContext` | ||
4316 | * @return #GNUNET_YES if not found, #GNUNET_NO if found | ||
4317 | */ | ||
4318 | static int | ||
4319 | find_by_message_uuid (void *cls, uint32_t key, void *value) | ||
4320 | { | ||
4321 | struct FindByMessageUuidContext *fc = cls; | ||
4322 | struct ReassemblyContext *rc = value; | ||
4323 | |||
4324 | (void) key; | ||
4325 | if (0 == GNUNET_memcmp (&fc->message_uuid, &rc->msg_uuid)) | ||
4326 | { | ||
4327 | fc->rc = rc; | ||
4328 | return GNUNET_NO; | ||
4329 | } | ||
4330 | return GNUNET_YES; | ||
4331 | } | ||
4332 | |||
4333 | |||
4334 | /** | ||
4245 | * Communicator gave us a fragment. Process the request. | 4335 | * Communicator gave us a fragment. Process the request. |
4246 | * | 4336 | * |
4247 | * @param cls a `struct CommunicatorMessageContext` (must call | 4337 | * @param cls a `struct CommunicatorMessageContext` (must call |
@@ -4262,6 +4352,7 @@ handle_fragment_box (void *cls, const struct TransportFragmentBoxMessage *fb) | |||
4262 | char *target; | 4352 | char *target; |
4263 | struct GNUNET_TIME_Relative cdelay; | 4353 | struct GNUNET_TIME_Relative cdelay; |
4264 | int ack_now; | 4354 | int ack_now; |
4355 | struct FindByMessageUuidContext fc; | ||
4265 | 4356 | ||
4266 | n = GNUNET_CONTAINER_multipeermap_get (neighbours, &cmc->im.sender); | 4357 | n = GNUNET_CONTAINER_multipeermap_get (neighbours, &cmc->im.sender); |
4267 | if (NULL == n) | 4358 | if (NULL == n) |
@@ -4275,7 +4366,7 @@ handle_fragment_box (void *cls, const struct TransportFragmentBoxMessage *fb) | |||
4275 | } | 4366 | } |
4276 | if (NULL == n->reassembly_map) | 4367 | if (NULL == n->reassembly_map) |
4277 | { | 4368 | { |
4278 | n->reassembly_map = GNUNET_CONTAINER_multishortmap_create (8, GNUNET_YES); | 4369 | n->reassembly_map = GNUNET_CONTAINER_multihashmap32_create (8); |
4279 | n->reassembly_heap = | 4370 | n->reassembly_heap = |
4280 | GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); | 4371 | GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); |
4281 | n->reassembly_timeout_task = | 4372 | n->reassembly_timeout_task = |
@@ -4284,9 +4375,13 @@ handle_fragment_box (void *cls, const struct TransportFragmentBoxMessage *fb) | |||
4284 | n); | 4375 | n); |
4285 | } | 4376 | } |
4286 | msize = ntohs (fb->msg_size); | 4377 | msize = ntohs (fb->msg_size); |
4287 | rc = | 4378 | fc.message_uuid = fb->msg_uuid; |
4288 | GNUNET_CONTAINER_multishortmap_get (n->reassembly_map, &fb->msg_uuid.uuid); | 4379 | fc.rc = NULL; |
4289 | if (NULL == rc) | 4380 | GNUNET_CONTAINER_multihashmap32_get_multiple (n->reassembly_map, |
4381 | fb->msg_uuid.uuid, | ||
4382 | &find_by_message_uuid, | ||
4383 | &fc); | ||
4384 | if (NULL == (rc = fc.rc)) | ||
4290 | { | 4385 | { |
4291 | rc = GNUNET_malloc (sizeof (*rc) + msize + /* reassembly payload buffer */ | 4386 | rc = GNUNET_malloc (sizeof (*rc) + msize + /* reassembly payload buffer */ |
4292 | (msize + 7) / 8 * sizeof (uint8_t) /* bitfield */); | 4387 | (msize + 7) / 8 * sizeof (uint8_t) /* bitfield */); |
@@ -4300,11 +4395,11 @@ handle_fragment_box (void *cls, const struct TransportFragmentBoxMessage *fb) | |||
4300 | rc, | 4395 | rc, |
4301 | rc->reassembly_timeout.abs_value_us); | 4396 | rc->reassembly_timeout.abs_value_us); |
4302 | GNUNET_assert (GNUNET_OK == | 4397 | GNUNET_assert (GNUNET_OK == |
4303 | GNUNET_CONTAINER_multishortmap_put ( | 4398 | GNUNET_CONTAINER_multihashmap32_put ( |
4304 | n->reassembly_map, | 4399 | n->reassembly_map, |
4305 | &rc->msg_uuid.uuid, | 4400 | rc->msg_uuid.uuid, |
4306 | rc, | 4401 | rc, |
4307 | GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); | 4402 | GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); |
4308 | target = (char *) &rc[1]; | 4403 | target = (char *) &rc[1]; |
4309 | rc->bitfield = (uint8_t *) (target + rc->msg_size); | 4404 | rc->bitfield = (uint8_t *) (target + rc->msg_size); |
4310 | rc->msg_missing = rc->msg_size; | 4405 | rc->msg_missing = rc->msg_size; |