From b0b3c14c11afe55cd71f9c1b8a89d9e5a65c9799 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Wed, 26 Dec 2012 18:08:01 -0500 Subject: Eliminate MaxOnionsPending; replace it with MaxOnionQueueDelay The right way to set "MaxOnionsPending" was to adjust it until the processing delay was appropriate. So instead, let's measure how long it takes to process onionskins (sampling them once we have a big number), and then limit the queue based on its expected time to finish. This change is extra-necessary for ntor, since there is no longer a reasonable way to set MaxOnionsPending without knowing what mix of onionskins you'll get. This patch also reserves 1/3 of the onionskin spots for ntor handshakes, on the theory that TAP handshakes shouldn't be allowed to starve their speedier cousins. We can change this later if need be. Resolves 7291. --- src/or/cpuworker.h | 3 +++ 1 file changed, 3 insertions(+) (limited to 'src/or/cpuworker.h') diff --git a/src/or/cpuworker.h b/src/or/cpuworker.h index f607e7d484..df6917237e 100644 --- a/src/or/cpuworker.h +++ b/src/or/cpuworker.h @@ -22,5 +22,8 @@ int assign_onionskin_to_cpuworker(connection_t *cpuworker, or_circuit_t *circ, struct create_cell_t *onionskin); +uint64_t estimated_usec_for_onionskins(uint32_t n_requests, + uint16_t onionskin_type); + #endif -- cgit v1.2.3-54-g00ecf From 30e139389bd8301f62ee24481d0f5484544fc5de Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Thu, 3 Jan 2013 13:20:20 -0500 Subject: Record and report the overhead of how we handle onionskins. --- changes/timed_onionqueue | 4 ++++ src/or/cpuworker.c | 48 ++++++++++++++++++++++++++++++++++++++++++++++++ src/or/cpuworker.h | 2 ++ src/or/main.c | 3 +++ 4 files changed, 57 insertions(+) (limited to 'src/or/cpuworker.h') diff --git a/changes/timed_onionqueue b/changes/timed_onionqueue index d0900ba342..fe54d78ac8 100644 --- a/changes/timed_onionqueue +++ b/changes/timed_onionqueue @@ -5,3 +5,7 @@ estimate the time it will take to process an onionskin based on average processing time of previous onionskins. Closes ticket 7291. You'll never have to configure MaxOnionsPending again. + + - We compute the overhead from passing onionskins back and forth to + cpuworkers, and report it when dumping statistics in response to + SIGUSR1. diff --git a/src/or/cpuworker.c b/src/or/cpuworker.c index a6262241e3..42f7b9572c 100644 --- a/src/or/cpuworker.c +++ b/src/or/cpuworker.c @@ -235,6 +235,54 @@ estimated_usec_for_onionskins(uint32_t n_requests, uint16_t onionskin_type) } } +/** Compute the absolute and relative overhead of using the cpuworker + * framework for onionskins of type onionskin_type.*/ +static int +get_overhead_for_onionskins(uint32_t *usec_out, double *frac_out, + uint16_t onionskin_type) +{ + uint64_t overhead; + + *usec_out = 0; + *frac_out = 0.0; + + if (onionskin_type > MAX_ONION_HANDSHAKE_TYPE) /* should be impossible */ + return -1; + if (onionskins_n_processed[onionskin_type] == 0 || + onionskins_usec_internal[onionskin_type] == 0 || + onionskins_usec_roundtrip[onionskin_type] == 0) + return -1; + + overhead = onionskins_usec_roundtrip[onionskin_type] - + onionskins_usec_internal[onionskin_type]; + + *usec_out = (uint32_t)(overhead / onionskins_n_processed[onionskin_type]); + *frac_out = U64_TO_DBL(overhead) / onionskins_usec_internal[onionskin_type]; + + return 0; +} + +/** If we've measured overhead for onionskins of type onionskin_type, + * log it. */ +void +cpuworker_log_onionskin_overhead(int severity, int onionskin_type, + const char *onionskin_type_name) +{ + uint32_t overhead; + double relative_overhead; + int r; + + r = get_overhead_for_onionskins(&overhead, &relative_overhead, + onionskin_type); + if (!overhead || r<0) + return; + + log_fn(severity, LD_OR, + "%s onionskins have averaged %u usec overhead (%.2f%%) in " + "cpuworker code ", + onionskin_type_name, (unsigned)overhead, relative_overhead*100); +} + /** Called when we get data from a cpuworker. If the answer is not complete, * wait for a complete answer. If the answer is complete, * process it as appropriate. diff --git a/src/or/cpuworker.h b/src/or/cpuworker.h index df6917237e..2da0249b96 100644 --- a/src/or/cpuworker.h +++ b/src/or/cpuworker.h @@ -24,6 +24,8 @@ int assign_onionskin_to_cpuworker(connection_t *cpuworker, uint64_t estimated_usec_for_onionskins(uint32_t n_requests, uint16_t onionskin_type); +void cpuworker_log_onionskin_overhead(int severity, int onionskin_type, + const char *onionskin_type_name); #endif diff --git a/src/or/main.c b/src/or/main.c index abb1e34fcd..3745ccb8ce 100644 --- a/src/or/main.c +++ b/src/or/main.c @@ -2202,6 +2202,9 @@ dumpstats(int severity) 100*(U64_TO_DBL(stats_n_data_bytes_received) / U64_TO_DBL(stats_n_data_cells_received*RELAY_PAYLOAD_SIZE)) ); + cpuworker_log_onionskin_overhead(severity, ONION_HANDSHAKE_TYPE_TAP, "TAP"); + cpuworker_log_onionskin_overhead(severity, ONION_HANDSHAKE_TYPE_NTOR,"ntor"); + if (now - time_of_process_start >= 0) elapsed = now - time_of_process_start; else -- cgit v1.2.3-54-g00ecf