From 6776eda81f7712d24b4a54943642cf90af7ee4d8 Mon Sep 17 00:00:00 2001 From: Christian Grothoff Date: Fri, 22 Jan 2010 17:54:18 +0000 Subject: [PATCH] stuff --- BUGS | 34 +++++---- TODO | 6 +- src/include/gnunet_core_service.h | 1 + src/topology/gnunet-daemon-topology.c | 100 ++++++++++++++++++++++---- 4 files changed, 109 insertions(+), 32 deletions(-) diff --git a/BUGS b/BUGS index 94623b45b..1d9398c9b 100644 --- a/BUGS +++ b/BUGS @@ -8,10 +8,6 @@ sane end-user should care about this codebase yet anyway. [On W32, we need to select after calling socket before doing connect etc.] * TRANSPORT: - - transport_api: support forcing disconnects through low quotas! - (required for working F2F support!) - - API: consider having core provide deadline information for each message - (likely important for DV plugin which wants to loop back!) - implement transport API to pretty-print transport address + transport_api extension (API extension!) + service-transport extension (protocol extension) @@ -51,15 +47,8 @@ sane end-user should care about this codebase yet anyway. + How necessary is ACKing in the first place? (alternatives?) + Should we transmit ACKs in response to every HELLO? (would that fully address the problem?) - - latency measurements implemented in the transport - plugins makes it only work for bi-di transports - and results in code replication - - should latency be included in the ReceiveCallback and - NotifyConnect or passed on request? - - FIXME's with latency being simply set to 0 in a few places - [./transport/gnunet-service-transport.c:173]: (style) struct or union member 'TransportPlugin::rebuild' is never used - [./transport/plugin_transport_tcp.c:391]: (style) struct or union member 'Plugin::address_update_task' is never used - * FS: - [./fs/gnunet-service-fs.c:208]: (style) struct or union member 'LocalGetContext::results_bf_size' is never used - [./fs/gnunet-service-fs.c:501]: (style) struct or union member 'PendingRequest::used_pids_size' is never used @@ -69,10 +58,27 @@ sane end-user should care about this codebase yet anyway. - [./fs/gnunet-service-fs.c:688]: (style) struct or union member 'ConnectedPeer::pending_requests' is never used - [./fs/gnunet-service-fs.c:694]: (style) struct or union member 'ConnectedPeer::last_p2p_replies_woff' is never used - [./fs/gnunet-service-fs.c:700]: (style) struct or union member 'ConnectedPeer::last_client_replies_woff' is never used - * TOPOLOGY: - - [./topology/gnunet-daemon-topology.c:94]: (style) struct or union member 'PeerList::last_hello_sent' is never used - + - If the topology daemon crashes, peers that were put on the + blacklist with transport will never be removed from it (until + transport service dies); we should use the blacklist notification + API to learn about the exact set of blacklisted peers at all times + (FIXME: the transport_api implementation of blacklisting + also does not work nicely for this since it won't let us know about + disconnect-reconnect events and the implicit whitelisting + that might happen here; that's not so bad since we will + re-blacklist on pre-connect attempts anyway, so this is + a minor issue). + - the code uses the term 'blacklist' for both peers that are forbidden + to connect (i.e. F2F mode) as well as peers that we currently + won't try to actively connect to ourselves (since we just tried); + This is confusing. We need two distinct terms. + - move code to use hash table instead of linked list + - instead of periodically discarding blacklisted entries, + simply add task that is triggered at the right time (earlier free, + more balanced load) + - check if new HELLO learned is different from old HELLO + before resetting entire state! * SETUP: - auto-generate "defaults.conf" using gnunet-setup from "config.scm" - integrate all options into "config.scm" diff --git a/TODO b/TODO index 2d181fe6f..a407f9052 100644 --- a/TODO +++ b/TODO @@ -21,8 +21,6 @@ Urgent items (before announcing ng.gnunet.org): - main service not implemented [Nate] - testcases crash & burn (no surprise) * CORE: - - request disconnect not implemented [Christian] - - various notification options not implemented [Christian] - outbound message monitoring not supported [Christian] - test currently fails spectacularly [segv of transport service] => need transport to work first! @@ -30,9 +28,7 @@ Urgent items (before announcing ng.gnunet.org): * TOPOLOGY: - needs testing [need transport first] * HOSTLIST: - - test fails (looks like it works, but that's because of a bad - connectivity notification; somehow core is unable to send - messages successfully via transport) [need transport first] + - needs testing [need transport first] * FS (basic anonymous FS only) - implement FS service (P2P operations) + how to send queries (soliciting is not there in core; do we diff --git a/src/include/gnunet_core_service.h b/src/include/gnunet_core_service.h index 6f49dc71a..d35e6fb85 100644 --- a/src/include/gnunet_core_service.h +++ b/src/include/gnunet_core_service.h @@ -269,6 +269,7 @@ typedef void */ struct GNUNET_CORE_InformationRequestContext; + /** * Obtain statistics and/or change preferences for the given peer. * diff --git a/src/topology/gnunet-daemon-topology.c b/src/topology/gnunet-daemon-topology.c index 3bcc29704..727d53815 100644 --- a/src/topology/gnunet-daemon-topology.c +++ b/src/topology/gnunet-daemon-topology.c @@ -22,14 +22,6 @@ * @file topology/gnunet-daemon-topology.c * @brief code for maintaining the mesh topology * @author Christian Grothoff - * - * OPTIMIZATIONS: - * - move code to use hash table instead of linked list - * - instead of periodically discarding blacklisted entries, - * simply add task that is triggered at the right time (earlier free, - * more balanced load) - * - check if new HELLO learned is different from old HELLO - * before resetting entire state! */ #include @@ -100,6 +92,12 @@ struct PeerList */ struct GNUNET_CONTAINER_BloomFilter *filter; + /** + * Our request handle for *whitelisting* this peer (NULL if + * no whitelisting request is pending). + */ + struct GNUNET_TRANSPORT_BlacklistRequest *wh; + /** * Is this peer listed here because he is a friend? */ @@ -110,6 +108,11 @@ struct PeerList */ int is_connected; + /** + * Are we currently blocking this peer (via blacklist)? + */ + int is_blocked; + /** * Until what time should we not try to connect again * to this peer? @@ -269,13 +272,19 @@ disconnect_done (void *cls, /** * Force a disconnect from the specified peer. - * FIXME: this policy change is never undone; how do we reconnect ever? */ static void -force_disconnect (const struct GNUNET_PeerIdentity *peer) +force_disconnect (struct PeerList *pl) { + const struct GNUNET_PeerIdentity *peer = &pl->id; struct DisconnectList *dl; + if (NULL != dl->wh) + { + GNUNET_TRANSPORT_blacklist_cancel (dl->wh); + dl->wh = NULL; + } + pl->is_blocked = GNUNET_YES; dl = GNUNET_malloc (sizeof (struct DisconnectList)); dl->peer = *peer; GNUNET_CONTAINER_DLL_insert (disconnect_head, @@ -290,6 +299,63 @@ force_disconnect (const struct GNUNET_PeerIdentity *peer) } + +/** + * Function called once our request to 'whitelist' a peer + * has completed. + * + * @param cls our 'struct PeerList' + * @param tc unused + */ +static void +whitelist_done (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PeerList *pl = cls; + + pl->wh = NULL; +} + + +/** + * Whitelist all peers that we blacklisted; we've passed + * the minimum number of friends. + */ +static void +whitelist_peers () +{ + struct PeerList *pl; + struct DisconnectList *dl; + + /* first, cancel all blacklisting requests */ + while (NULL != (dl = disconnect_head)) + { + GNUNET_CONTAINER_DLL_remove (disconnect_head, + disconnect_tail, + dl); + GNUNET_TRANSPORT_blacklist_cancel (dl->rh); + GNUNET_free (dl); + } + /* then, specifically whitelist all peers that we + know to have blacklisted */ + pl = peers; + while (pl != NULL) + { + if (pl->is_blocked) + { + pl->wh = GNUNET_TRANSPORT_blacklist (sched, cfg, + peer, + GNUNET_TIME_UNIT_FOREVER_ZERO, + GNUNET_TIME_UNIT_FOREVER_REL, + &whitelist_done, + pl); + pl->is_blocked = GNUNET_NO; + } + pl = pl->next; + } +} + + /** * Function called by core when our attempt to connect succeeded. */ @@ -434,6 +500,8 @@ free_peer (struct PeerList *peer) prev->next = pos->next; if (pos->hello_req != NULL) GNUNET_CORE_notify_transmit_ready_cancel (pos->hello_req); + if (pos->wh != NULL) + GNUNET_TRANSPORT_blacklist_cancel (pos->wh); if (pos->connect_req != NULL) GNUNET_CORE_peer_request_connect_cancel (pos->connect_req); if (pos->hello_delay_task != GNUNET_SCHEDULER_NO_TASK) @@ -611,7 +679,7 @@ connect_notify (void *cls, "Connection to `%s' is forbidden, forcing disconnect!\n", GNUNET_i2s (peer)); #endif - force_disconnect (&pos->id); + force_disconnect (pos); return; } } @@ -622,7 +690,12 @@ connect_notify (void *cls, } pos->is_connected = GNUNET_YES; if (pos->is_friend) - friend_count++; + { + if ( (friend_count == minimum_friend_count - 1) && + (GNUNET_YES != friends_only) ) + whitelist_peers (); + friend_count++; + } reschedule_hellos (pos); } @@ -646,7 +719,7 @@ drop_non_friends () "Connection to `%s' is not from a friend, forcing disconnect!\n", GNUNET_i2s (&pos->id)); #endif - force_disconnect (&pos->id); + force_disconnect (pos); } pos = pos->next; } @@ -884,6 +957,7 @@ discard_old_blacklist_entries (void *cls, next = pos->next; if ( (GNUNET_NO == pos->is_friend) && (GNUNET_NO == pos->is_connected) && + (GNUNET_NO == pos->is_blocked) && (0 == GNUNET_TIME_absolute_get_remaining (pos->blacklisted_until).value) ) free_peer (pos); } -- 2.25.1