X-Git-Url: https://git.librecmc.org/?a=blobdiff_plain;f=src%2Ffs%2Fgnunet-service-fs.c;h=06ac91c73d5f1a21f9b79d59f6454801106b0df7;hb=1f09f4f7716db5939ec1c9a278b5661616dd72d6;hp=866860c0a218db50f2dfaedee417ee7047ae3599;hpb=a2d9b4434076254811584a4a0ffa8881d0903db8;p=oweals%2Fgnunet.git diff --git a/src/fs/gnunet-service-fs.c b/src/fs/gnunet-service-fs.c index 866860c0a..06ac91c73 100644 --- a/src/fs/gnunet-service-fs.c +++ b/src/fs/gnunet-service-fs.c @@ -25,8 +25,6 @@ * * To use: * - consider re-issue GSF_dht_lookup_ after non-DHT reply received - * - implement 'SUPPORT_DELAYS' - * */ #include "platform.h" #include @@ -93,6 +91,12 @@ struct GNUNET_DHT_Handle *GSF_dht; */ struct GNUNET_LOAD_Value *GSF_rt_entry_lifetime; +/** + * Running average of the observed latency to other peers (round trip). + * Initialized to 5s as the initial default. + */ +struct GNUNET_TIME_Relative GSF_avg_latency = { 500 }; + /** * Typical priorities we're seeing from other peers right now. Since * most priorities will be zero, this value is the weighted average of @@ -172,7 +176,6 @@ age_cover_counters (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - /** * We've just now completed a datastore request. Update our * datastore load calculations. @@ -212,6 +215,36 @@ GSF_test_get_load_too_high_ (uint32_t priority) } +/** + * We've received peer performance information. Update + * our running average for the P2P latency. + * + * @param atsi performance information + * @param atsi_count number of 'atsi' records + */ +static void +update_latencies (const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + unsigned int i; + + for (i = 0; i < atsi_count; i++) + { + if (ntohl (atsi[i].type) == GNUNET_ATS_QUALITY_NET_DELAY) + { + GSF_avg_latency.rel_value = + (GSF_avg_latency.rel_value * 31 + + GNUNET_MIN (5000, ntohl (atsi[i].value))) / 32; + GNUNET_STATISTICS_set (GSF_stats, + gettext_noop + ("# running average P2P latency (ms)"), + GSF_avg_latency.rel_value, GNUNET_NO); + break; + } + } +} + + /** * Handle P2P "PUT" message. * @@ -220,13 +253,15 @@ GSF_test_get_load_too_high_ (uint32_t priority) * for loopback messages where we are both sender and receiver) * @param message the actual message * @param atsi performance information + * @param atsi_count number of records in 'atsi' * @return GNUNET_OK to keep the connection open, * GNUNET_SYSERR to close it (signal serious error) */ static int handle_p2p_put (void *cls, const struct GNUNET_PeerIdentity *other, const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi) + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { struct GSF_ConnectedPeer *cp; @@ -237,6 +272,7 @@ handle_p2p_put (void *cls, const struct GNUNET_PeerIdentity *other, return GNUNET_OK; } GSF_cover_content_count++; + update_latencies (atsi, atsi_count); return GSF_handle_p2p_content_ (cp, message); } @@ -258,6 +294,13 @@ consider_request_for_forwarding (void *cls, { struct GSF_PendingRequest *pr = cls; + if (GNUNET_YES != GSF_pending_request_test_target_ (pr, peer)) + { + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# Loopback routes suppressed"), 1, + GNUNET_NO); + return; + } GSF_plan_add_ (cp, pr); } @@ -290,20 +333,24 @@ consider_forwarding (void *cls, struct GSF_PendingRequest *pr, * for loopback messages where we are both sender and receiver) * @param message the actual message * @param atsi performance information + * @param atsi_count number of records in 'atsi' * @return GNUNET_OK to keep the connection open, * GNUNET_SYSERR to close it (signal serious error) */ static int handle_p2p_get (void *cls, const struct GNUNET_PeerIdentity *other, const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi) + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { struct GSF_PendingRequest *pr; pr = GSF_handle_p2p_query_ (other, message); if (NULL == pr) return GNUNET_SYSERR; + GSF_pending_request_get_data_ (pr)->has_started = GNUNET_YES; GSF_local_lookup_ (pr, &consider_forwarding, NULL); + update_latencies (atsi, atsi_count); return GNUNET_OK; } @@ -326,11 +373,9 @@ start_p2p_processing (void *cls, struct GSF_PendingRequest *pr, struct GSF_PendingRequestData *prd; prd = GSF_pending_request_get_data_ (pr); -#if DEBUG_FS_CLIENT GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Finished database lookup for local request `%s' with result %d\n", GNUNET_h2s (&prd->query), result); -#endif GNUNET_SERVER_receive_done (client, GNUNET_OK); if (GNUNET_BLOCK_EVALUATION_OK_LAST == result) return; /* we're done, 'pr' was already destroyed... */ @@ -356,14 +401,25 @@ handle_start_search (void *cls, struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message) { struct GSF_PendingRequest *pr; + int ret; - pr = GSF_local_client_start_search_handler_ (client, message); - if (NULL == pr) + pr = NULL; + ret = GSF_local_client_start_search_handler_ (client, message, &pr); + switch (ret) { - /* GNUNET_SERVER_receive_done was already called! */ - return; + case GNUNET_SYSERR: + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + break; + case GNUNET_NO: + GNUNET_SERVER_receive_done (client, GNUNET_OK); + break; + case GNUNET_YES: + GSF_pending_request_get_data_ (pr)->has_started = GNUNET_YES; + GSF_local_lookup_ (pr, &start_p2p_processing, client); + break; + default: + GNUNET_assert (0); } - GSF_local_lookup_ (pr, &start_p2p_processing, client); } @@ -424,7 +480,16 @@ consider_peer_for_forwarding (void *cls, const GNUNET_HashCode * key, struct GSF_PendingRequest *pr) { struct GSF_ConnectedPeer *cp = cls; + struct GNUNET_PeerIdentity pid; + GSF_connected_peer_get_identity_ (cp, &pid); + if (GNUNET_YES != GSF_pending_request_test_target_ (pr, &pid)) + { + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# Loopback routes suppressed"), 1, + GNUNET_NO); + return GNUNET_YES; + } GSF_plan_add_ (cp, pr); return GNUNET_YES; } @@ -436,16 +501,18 @@ consider_peer_for_forwarding (void *cls, const GNUNET_HashCode * key, * @param cls closure, not used * @param peer peer identity this notification is about * @param atsi performance information + * @param atsi_count number of records in 'atsi' */ static void peer_connect_handler (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi) + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { struct GSF_ConnectedPeer *cp; if (0 == memcmp (&my_id, peer, sizeof (struct GNUNET_PeerIdentity))) return; - cp = GSF_peer_connect_handler_ (peer, atsi); + cp = GSF_peer_connect_handler_ (peer, atsi, atsi_count); if (NULL == cp) return; GSF_iterate_pending_requests_ (&consider_peer_for_forwarding, cp); @@ -504,12 +571,10 @@ main_init (struct GNUNET_SERVER_Handle *server, {NULL, NULL, 0, 0} }; - GSF_core = GNUNET_CORE_connect (GSF_cfg, 2, /* larger? */ - NULL, &peer_init_handler, - &peer_connect_handler, - &GSF_peer_disconnect_handler_, - NULL, GNUNET_NO, - NULL, GNUNET_NO, p2p_handlers); + GSF_core = + GNUNET_CORE_connect (GSF_cfg, 1, NULL, &peer_init_handler, + &peer_connect_handler, &GSF_peer_disconnect_handler_, + NULL, GNUNET_NO, NULL, GNUNET_NO, p2p_handlers); if (NULL == GSF_core) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR,