summaryrefslogtreecommitdiff
path: root/src/test/test_stats.c
diff options
context:
space:
mode:
authorDavid Goulet <dgoulet@torproject.org>2021-10-20 09:59:04 -0400
committerDavid Goulet <dgoulet@torproject.org>2021-10-20 10:00:03 -0400
commit7a8108ea87320da3008e65747baa43c1bbcf13c2 (patch)
tree380e171d32b66081529847027a2eb4415061df10 /src/test/test_stats.c
parent3752a71ded247cd6b32e0ee6c3dfaf906a63a915 (diff)
downloadtor-7a8108ea87320da3008e65747baa43c1bbcf13c2.tar.gz
tor-7a8108ea87320da3008e65747baa43c1bbcf13c2.zip
relay: Overload state on DNS timeout is now X% over Y secs
With this commit, we will only report a general overload state if we've seen more than X% of DNS timeout errors over Y seconds. Previous behavior was to report when a single timeout occured which is really too small of a threshold. The value X is a consensus parameters called "overload_dns_timeout_scale_percent" which is a scaled percentage (factor of 1000) so we can represent decimal points for X like 0.5% for instance. Its default is 1000 which ends up being 1%. The value Y is a consensus parameters called "overload_dns_timeout_period_secs" which is the time period for which will gather DNS errors and once over, we assess if that X% has been reached ultimately triggering a general overload signal. Closes #40491 Signed-off-by: David Goulet <dgoulet@torproject.org>
Diffstat (limited to 'src/test/test_stats.c')
-rw-r--r--src/test/test_stats.c78
1 files changed, 78 insertions, 0 deletions
diff --git a/src/test/test_stats.c b/src/test/test_stats.c
index 081ae22cd5..e85ad40699 100644
--- a/src/test/test_stats.c
+++ b/src/test/test_stats.c
@@ -51,6 +51,8 @@
#include "feature/stats/bw_array_st.h"
#include "feature/relay/router.h"
+#include <event2/dns.h>
+
/** Run unit tests for some stats code. */
static void
test_stats(void *arg)
@@ -865,6 +867,81 @@ test_overload_stats(void *arg)
tor_free(stats_str);
}
+/** Test the overload stats logic. */
+static void
+test_overload_dns_timeout(void *arg)
+{
+ char *stats_str = NULL;
+ (void) arg;
+
+ /* Lets simulate a series of timeouts but below our default 1% threshold. */
+
+ for (int i = 0; i < 1000; i++) {
+ /* This should trigger 9 timeouts which is just below 1% (10) */
+ if (i > 0 && !(i % 100)) {
+ rep_hist_note_dns_error(0, DNS_ERR_TIMEOUT);
+ } else {
+ rep_hist_note_dns_error(0, DNS_ERR_NONE);
+ }
+ }
+
+ /* No overload yet. */
+ stats_str = rep_hist_get_overload_general_line();
+ tt_assert(!stats_str);
+
+ /* Move it 10 minutes in the future and see if we get a general overload. */
+ update_approx_time(approx_time() + (10 * 60));
+
+ /* This query should NOT trigger the general overload because we are below
+ * our default of 1%. */
+ rep_hist_note_dns_error(0, DNS_ERR_NONE);
+ stats_str = rep_hist_get_overload_general_line();
+ tt_assert(!stats_str);
+
+ /* We'll now go above our 1% threshold. */
+ for (int i = 0; i < 1000; i++) {
+ /* This should trigger 10 timeouts which is our threshold of 1% (10) */
+ if (!(i % 10)) {
+ rep_hist_note_dns_error(0, DNS_ERR_TIMEOUT);
+ } else {
+ rep_hist_note_dns_error(0, DNS_ERR_NONE);
+ }
+ }
+
+ /* Move it 10 minutes in the future and see if we get a general overload. */
+ update_approx_time(approx_time() + (10 * 60));
+
+ /* This query should trigger the general overload because we are above 1%. */
+ rep_hist_note_dns_error(0, DNS_ERR_NONE);
+ stats_str = rep_hist_get_overload_general_line();
+ tt_assert(stats_str);
+ tor_free(stats_str);
+
+ /* Move 72h in the future, we should NOT get an overload anymore. */
+ update_approx_time(approx_time() + (72 * 3600));
+
+ stats_str = rep_hist_get_overload_general_line();
+ tt_assert(!stats_str);
+
+ /* This query should NOT trigger the general overload. */
+ rep_hist_note_dns_error(0, DNS_ERR_TIMEOUT);
+ stats_str = rep_hist_get_overload_general_line();
+ tt_assert(!stats_str);
+
+ /* Move it 10 minutes in the future and see if we get a general overload. We
+ * have now 100% of requests timing out. */
+ update_approx_time(approx_time() + (10 * 60));
+
+ /* This query should trigger the general overload with 50% of timeouts. */
+ rep_hist_note_dns_error(0, DNS_ERR_NONE);
+ stats_str = rep_hist_get_overload_general_line();
+ tt_assert(stats_str);
+ tor_free(stats_str);
+
+ done:
+ tor_free(stats_str);
+}
+
#define ENT(name) \
{ #name, test_ ## name , 0, NULL, NULL }
#define FORK(name) \
@@ -881,6 +958,7 @@ struct testcase_t stats_tests[] = {
FORK(rephist_v3_onions),
FORK(load_stats_file),
FORK(overload_stats),
+ FORK(overload_dns_timeout),
END_OF_TESTCASES
};