mirror of
https://gitlab.isc.org/isc-projects/bind9
synced 2025-09-02 15:45:25 +00:00
Merge branch '2809-doh-quota-systest-fix-on-fbsd11' into 'main'
Resolve "Fix the DoH quota stress test on FreeBSD 11" Closes #2809 See merge request isc-projects/bind9!5304
This commit is contained in:
@@ -35,6 +35,7 @@ options {
|
|||||||
also-notify { 10.53.0.2 port @PORT@; };
|
also-notify { 10.53.0.2 port @PORT@; };
|
||||||
statistics-file "named.stats";
|
statistics-file "named.stats";
|
||||||
dnssec-validation yes;
|
dnssec-validation yes;
|
||||||
|
tcp-initial-timeout 1200;
|
||||||
};
|
};
|
||||||
|
|
||||||
zone "." {
|
zone "." {
|
||||||
|
@@ -19,8 +19,6 @@ import time
|
|||||||
|
|
||||||
from functools import reduce
|
from functools import reduce
|
||||||
|
|
||||||
# this number should exceed default HTTP quota value
|
|
||||||
NCONNECTIONS = 320
|
|
||||||
MULTIDIG_INSTANCES = 10
|
MULTIDIG_INSTANCES = 10
|
||||||
CONNECT_TRIES = 5
|
CONNECT_TRIES = 5
|
||||||
|
|
||||||
@@ -61,8 +59,7 @@ def get_dig_path():
|
|||||||
# A simple class which creates the given number of TCP connections to
|
# A simple class which creates the given number of TCP connections to
|
||||||
# the given host in order to stress the BIND's quota facility
|
# the given host in order to stress the BIND's quota facility
|
||||||
class TCPConnector:
|
class TCPConnector:
|
||||||
def __init__(self, nconnections, host, port):
|
def __init__(self, host, port):
|
||||||
self.number_of_connections = nconnections
|
|
||||||
self.host = host
|
self.host = host
|
||||||
self.port = port
|
self.port = port
|
||||||
self.connections = []
|
self.connections = []
|
||||||
@@ -85,10 +82,6 @@ class TCPConnector:
|
|||||||
finally:
|
finally:
|
||||||
tries -= 1
|
tries -= 1
|
||||||
|
|
||||||
def connect_all(self):
|
|
||||||
for _ in range(1, self.number_of_connections + 1):
|
|
||||||
self.connect_one()
|
|
||||||
|
|
||||||
# Close an established connection (randomly)
|
# Close an established connection (randomly)
|
||||||
def disconnect_random(self):
|
def disconnect_random(self):
|
||||||
pos = random.randint(0, len(self.connections) - 1)
|
pos = random.randint(0, len(self.connections) - 1)
|
||||||
@@ -138,7 +131,6 @@ class SubDIG:
|
|||||||
with open(os.devnull, 'w') as devnull:
|
with open(os.devnull, 'w') as devnull:
|
||||||
self.sub_process = subprocess.Popen(self.get_command(), shell=True,
|
self.sub_process = subprocess.Popen(self.get_command(), shell=True,
|
||||||
stdout=devnull)
|
stdout=devnull)
|
||||||
jitter()
|
|
||||||
|
|
||||||
def wait(self, timeout=None):
|
def wait(self, timeout=None):
|
||||||
res = None
|
res = None
|
||||||
@@ -185,6 +177,13 @@ class MultiDIG:
|
|||||||
return reduce(lambda a, b: (a and b), map(lambda p: (p.alive()),
|
return reduce(lambda a, b: (a and b), map(lambda p: (p.alive()),
|
||||||
self.digs))
|
self.digs))
|
||||||
|
|
||||||
|
def completed(self):
|
||||||
|
total = 0
|
||||||
|
for p in self.digs:
|
||||||
|
if not p.alive():
|
||||||
|
total += 1
|
||||||
|
return total
|
||||||
|
|
||||||
|
|
||||||
# The test's main logic
|
# The test's main logic
|
||||||
def run_test(http_secure=True):
|
def run_test(http_secure=True):
|
||||||
@@ -195,19 +194,17 @@ def run_test(http_secure=True):
|
|||||||
assert subdig.wait() == 0, "DIG was expected to succeed"
|
assert subdig.wait() == 0, "DIG was expected to succeed"
|
||||||
# Let's create a lot of TCP connections to the server stress the
|
# Let's create a lot of TCP connections to the server stress the
|
||||||
# HTTP quota
|
# HTTP quota
|
||||||
connector = TCPConnector(NCONNECTIONS, get_http_host(),
|
connector = TCPConnector(get_http_host(),
|
||||||
get_http_port(http_secure=http_secure))
|
get_http_port(http_secure=http_secure))
|
||||||
# Let's make queries until the quota kicks in
|
# Let's make queries until the quota kicks in
|
||||||
subdig = SubDIG(http_secure=http_secure, extra_args=query_args)
|
subdig = SubDIG(http_secure=http_secure, extra_args=query_args)
|
||||||
subdig.run()
|
subdig.run()
|
||||||
while True:
|
while True:
|
||||||
|
connector.connect_one()
|
||||||
subdig = SubDIG(http_secure=http_secure, extra_args=query_args)
|
subdig = SubDIG(http_secure=http_secure, extra_args=query_args)
|
||||||
connector.connect_all()
|
|
||||||
time.sleep(2)
|
|
||||||
subdig.run()
|
subdig.run()
|
||||||
if subdig.wait(timeout=2) is None:
|
if subdig.wait(timeout=5) is None:
|
||||||
break
|
break
|
||||||
connector.disconnect_all()
|
|
||||||
|
|
||||||
# At this point quota has kicked in. Additionally, let's create a
|
# At this point quota has kicked in. Additionally, let's create a
|
||||||
# bunch of dig processes all trying to make a query against the
|
# bunch of dig processes all trying to make a query against the
|
||||||
@@ -218,9 +215,12 @@ def run_test(http_secure=True):
|
|||||||
# Wait for the dig instance to complete. Not a single instance has
|
# Wait for the dig instance to complete. Not a single instance has
|
||||||
# a chance to complete successfully because of the exceeded quota
|
# a chance to complete successfully because of the exceeded quota
|
||||||
assert subdig.wait(timeout=5) is None,\
|
assert subdig.wait(timeout=5) is None,\
|
||||||
"Single DIG instance has stopped prematurely"
|
"The single DIG instance has stopped prematurely"
|
||||||
assert subdig.alive(), "Single DIG instance is expected to be alive"
|
assert subdig.alive(), "The single DIG instance is expected to be alive"
|
||||||
assert multidig.alive(), "Multiple DIG instances are expected to be alive"
|
assert multidig.alive(), \
|
||||||
|
("The DIG instances from the set are all expected to "
|
||||||
|
"be alive, but {} of them have completed")\
|
||||||
|
.format(multidig.completed())
|
||||||
# Let's close opened connections (in random order) to let all dig
|
# Let's close opened connections (in random order) to let all dig
|
||||||
# processes to complete
|
# processes to complete
|
||||||
connector.disconnect_all()
|
connector.disconnect_all()
|
||||||
|
Reference in New Issue
Block a user