Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/dnsviz/dnsviz.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCasey Deccio <casey@deccio.net>2016-08-02 20:01:27 +0300
committerCasey Deccio <casey@deccio.net>2016-08-02 20:01:27 +0300
commitcebbb54a6bc00ffe83b32af4cd285fc205e76706 (patch)
tree61040f1aa611f8166e0057ad35fb30373008174a
parent18e8294ecafb1943fca908da4aeb112f1bef37f8 (diff)
Allow analysis of domain beyond explicit delegation
Allow analysis of domain beyond explicit delegation, if specified on command line.
-rw-r--r--dnsviz/analysis/online.py35
-rw-r--r--dnsviz/commands/probe.py30
2 files changed, 33 insertions, 32 deletions
diff --git a/dnsviz/analysis/online.py b/dnsviz/analysis/online.py
index 4926535..272842e 100644
--- a/dnsviz/analysis/online.py
+++ b/dnsviz/analysis/online.py
@@ -963,10 +963,11 @@ class Analyst(object):
qname_only = True
analysis_type = ANALYSIS_TYPE_AUTHORITATIVE
- clone_attrnames = ['dlv_domain', 'try_ipv4', 'try_ipv6', 'client_ipv4', 'client_ipv6', 'logger', 'ceiling', 'edns_diagnostics', 'follow_ns', 'explicit_delegations', 'odd_ports', 'explicit_only', 'analysis_cache', 'cache_level', 'analysis_cache_lock', 'transport_manager', 'th_factories', 'resolver']
+ clone_attrnames = ['dlv_domain', 'try_ipv4', 'try_ipv6', 'client_ipv4', 'client_ipv6', 'logger', 'ceiling', 'edns_diagnostics', 'follow_ns', 'explicit_delegations', 'stop_at_explicit', 'odd_ports', 'explicit_only', 'analysis_cache', 'cache_level', 'analysis_cache_lock', 'transport_manager', 'th_factories', 'resolver']
def __init__(self, name, dlv_domain=None, try_ipv4=True, try_ipv6=True, client_ipv4=None, client_ipv6=None, logger=_logger, ceiling=None, edns_diagnostics=False,
- follow_ns=False, follow_mx=False, trace=None, explicit_delegations=None, odd_ports=None, extra_rdtypes=None, explicit_only=False, analysis_cache=None, cache_level=None, analysis_cache_lock=None, th_factories=None, transport_manager=None, resolver=None):
+ follow_ns=False, follow_mx=False, trace=None, explicit_delegations=None, stop_at_explicit=None, odd_ports=None, extra_rdtypes=None, explicit_only=False,
+ analysis_cache=None, cache_level=None, analysis_cache_lock=None, th_factories=None, transport_manager=None, resolver=None):
if transport_manager is None:
self.transport_manager = transport.DNSQueryTransportManager()
@@ -988,6 +989,11 @@ class Analyst(object):
else:
self.explicit_delegations = explicit_delegations
+ if stop_at_explicit is None:
+ self.stop_at_explicit = {}
+ else:
+ self.stop_at_explicit = stop_at_explicit
+
if odd_ports is None:
self.odd_ports = {}
else:
@@ -1008,7 +1014,7 @@ class Analyst(object):
c = self.name
try:
while True:
- if (c, dns.rdatatype.NS) in self.explicit_delegations:
+ if (c, dns.rdatatype.NS) in self.explicit_delegations and self.stop_at_explicit[c]:
break
c = c.parent()
except dns.name.NoParent:
@@ -1025,7 +1031,6 @@ class Analyst(object):
ceiling = c
self.local_ceiling = self._detect_ceiling(ceiling)[0]
- self._fix_explicit_delegation()
self.try_ipv4 = try_ipv4
self.try_ipv6 = try_ipv6
@@ -1119,24 +1124,6 @@ class Analyst(object):
return ceiling, True
return self._detect_ceiling(ceiling.parent())
- def _fix_explicit_delegation(self):
- if self.local_ceiling is None:
- return
-
- # at this point, if self.name or any ancestor below self.local_ceiling has an
- # explicit delegation, then it is obsolete and needs to be applied to
- # self.local_ceiling instead.
- n = self.name
- explicit_delegation = None
- while n != self.local_ceiling:
- if (n, dns.rdatatype.NS) in self.explicit_delegations:
- if explicit_delegation is None:
- explicit_delegation = self.explicit_delegations[(n, dns.rdatatype.NS)]
- del self.explicit_delegations[(n, dns.rdatatype.NS)]
- n = n.parent()
- if explicit_delegation is not None:
- self.explicit_delegations[(self.local_ceiling, dns.rdatatype.NS)] = explicit_delegation
-
def _get_servers_from_hints(self, name, hints):
servers = set()
for rdata in hints[(name, dns.rdatatype.NS)]:
@@ -1484,10 +1471,10 @@ class Analyst(object):
# ceiling or the name is a subdomain of the ceiling
if name == dns.name.root:
parent_obj = None
+ elif (name, dns.rdatatype.NS) in self.explicit_delegations and self.stop_at_explicit[name]:
+ parent_obj = None
elif self.local_ceiling is not None and self.local_ceiling.is_subdomain(name):
parent_obj = self._analyze_stub(name.parent())
- elif (name, dns.rdatatype.NS) in self.explicit_delegations:
- parent_obj = None
else:
parent_obj = self._analyze(name.parent())
diff --git a/dnsviz/commands/probe.py b/dnsviz/commands/probe.py
index e27916a..ccbedda 100644
--- a/dnsviz/commands/probe.py
+++ b/dnsviz/commands/probe.py
@@ -78,6 +78,7 @@ A_ROOT_IPV6 = IPAddr('2001:503:ba3e::2:30')
BRACKETS_RE = re.compile(r'^\[(.*)\]$')
PORT_RE = re.compile(r'^(.*):(\d+)$')
+STOP_RE = re.compile(r'^(.*)\+$')
NAME_VAL_DELIM_RE = re.compile(r'\s*=\s*')
#XXX this is a hack required for inter-process sharing of dns.name.Name
@@ -115,13 +116,13 @@ def _init_subprocess():
def _analyze(args):
(cls, name, dlv_domain, try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, \
- extra_rdtypes, explicit_only, cache, cache_level, cache_lock, th_factories) = args
+ stop_at_explicit, extra_rdtypes, explicit_only, cache, cache_level, cache_lock, th_factories) = args
if ceiling is not None and name.is_subdomain(ceiling):
c = ceiling
else:
c = name
try:
- a = cls(name, dlv_domain=dlv_domain, try_ipv4=try_ipv4, try_ipv6=try_ipv6, client_ipv4=client_ipv4, client_ipv6=client_ipv6, ceiling=c, edns_diagnostics=edns_diagnostics, explicit_delegations=explicit_delegations, odd_ports=odd_ports, extra_rdtypes=extra_rdtypes, explicit_only=explicit_only, analysis_cache=cache, cache_level=cache_level, analysis_cache_lock=cache_lock, transport_manager=tm, th_factories=th_factories, resolver=full_resolver)
+ a = cls(name, dlv_domain=dlv_domain, try_ipv4=try_ipv4, try_ipv6=try_ipv6, client_ipv4=client_ipv4, client_ipv6=client_ipv6, ceiling=c, edns_diagnostics=edns_diagnostics, explicit_delegations=explicit_delegations, stop_at_explicit=stop_at_explicit, odd_ports=odd_ports, extra_rdtypes=extra_rdtypes, explicit_only=explicit_only, analysis_cache=cache, cache_level=cache_level, analysis_cache_lock=cache_lock, transport_manager=tm, th_factories=th_factories, resolver=full_resolver)
return a.analyze()
# re-raise a KeyboardInterrupt, as this means we've been interrupted
except KeyboardInterrupt:
@@ -140,13 +141,14 @@ def _analyze(args):
class BulkAnalyst(object):
analyst_cls = PrivateAnalyst
- def __init__(self, try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, cache_level, extra_rdtypes, explicit_only, dlv_domain, th_factories):
+ def __init__(self, try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, stop_at_explicit, cache_level, extra_rdtypes, explicit_only, dlv_domain, th_factories):
self.try_ipv4 = try_ipv4
self.try_ipv6 = try_ipv6
self.client_ipv4 = client_ipv4
self.client_ipv6 = client_ipv6
self.ceiling = ceiling
self.edns_diagnostics = edns_diagnostics
+ self.stop_at_explicit = stop_at_explicit
self.cache_level = cache_level
self.extra_rdtypes = extra_rdtypes
self.explicit_only = explicit_only
@@ -158,7 +160,7 @@ class BulkAnalyst(object):
def _name_to_args_iter(self, names):
for name in names:
- yield (self.analyst_cls, name, self.dlv_domain, self.try_ipv4, self.try_ipv6, self.client_ipv4, self.client_ipv6, self.ceiling, self.edns_diagnostics, self.extra_rdtypes, self.explicit_only, self.cache, self.cache_level, self.cache_lock, self.th_factories)
+ yield (self.analyst_cls, name, self.dlv_domain, self.try_ipv4, self.try_ipv6, self.client_ipv4, self.client_ipv6, self.ceiling, self.edns_diagnostics, self.stop_at_explicit, self.extra_rdtypes, self.explicit_only, self.cache, self.cache_level, self.cache_lock, self.th_factories)
def analyze(self, names, flush_func=None):
name_objs = []
@@ -236,8 +238,8 @@ class RecursiveMultiProcessAnalyst(MultiProcessAnalystMixin, PrivateRecursiveAna
class ParallelAnalystMixin(object):
analyst_cls = MultiProcessAnalyst
- def __init__(self, try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, cache_level, extra_rdtypes, explicit_only, dlv_domain, th_factories, processes):
- super(ParallelAnalystMixin, self).__init__(try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, cache_level, extra_rdtypes, explicit_only, dlv_domain, th_factories)
+ def __init__(self, try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, stop_at_explicit, cache_level, extra_rdtypes, explicit_only, dlv_domain, th_factories, processes):
+ super(ParallelAnalystMixin, self).__init__(try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, stop_at_explicit, cache_level, extra_rdtypes, explicit_only, dlv_domain, th_factories)
self.manager = multiprocessing.managers.SyncManager()
self.manager.start()
@@ -507,6 +509,7 @@ def main(argv):
# get all the -x options
explicit_delegations = {}
odd_ports = {}
+ stop_at_explicit = {}
client_ipv4 = None
client_ipv6 = None
for opt, arg in opts:
@@ -518,11 +521,22 @@ def main(argv):
sys.exit(1)
domain = domain.strip()
mappings = mappings.strip()
+
+ match = STOP_RE.search(domain)
+ if match is not None:
+ domain = match.group(1)
+
try:
domain = dns.name.from_text(domain)
except dns.exception.DNSException:
usage('The domain name was invalid: "%s"' % domain)
sys.exit(1)
+
+ if match is not None:
+ stop_at_explicit[domain] = True
+ else:
+ stop_at_explicit[domain] = False
+
if not mappings:
usage('Incorrect usage of -x option: "%s"' % arg)
sys.exit(1)
@@ -826,9 +840,9 @@ def main(argv):
name_objs.append(OnlineDomainNameAnalysis.deserialize(name, analysis_structured, cache))
else:
if '-t' in opts:
- a = cls(try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, cache_level, rdtypes, explicit_only, dlv_domain, th_factories, processes)
+ a = cls(try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, stop_at_explicit, cache_level, rdtypes, explicit_only, dlv_domain, th_factories, processes)
else:
- a = cls(try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, cache_level, rdtypes, explicit_only, dlv_domain, th_factories)
+ a = cls(try_ipv4, try_ipv6, client_ipv4, client_ipv6, ceiling, edns_diagnostics, stop_at_explicit, cache_level, rdtypes, explicit_only, dlv_domain, th_factories)
if flush:
fh.write('{')
a.analyze(names, _flush)