The following rules of thumb may be used to build analytics to search for suspicious DNS-related activity. I have provided references that support their use wherever possible.
- Sudden short, large burst of queries for a domain
- Domain resolves to multiple IPs in different ASes, countries, and/or regions (A RRs)
- TTL changes over period of time
- IP assigned to domain changes frequenty over a period of time
- Domain age is less than 5 weeks
- Number of distinct A RRs over period of time
- Number of distinct network names
- Domain age is less than a week
- DNS query is very low-frequency compared to others in environment
- Domain is lexically close to a well-known domain, has an IP outside of the well-known domain’s ASN(s).
This can be achieved using the MaxMind GeoIPASNum database, the Alexa Top 1 Million Names list, the tldextract,pygeoip, and jellyfish Python modules, and the Damerau-Levenshtein lexical distance calculation (made possible by the Jellyfish Python module).
Ideally, one would take a domain name, score its distance to some or all of the Alexa list, exit if the domain is an exact match, and otherwise look up the ASes for the IPs assigned to the name in question and the names that were a very close match (distance 1-2). If there is a match, exit. Otherwise, the name in question may be a typosquatting or bitsquatting attempt.
It would be wise to ensure internationalized domain names (IDNs) are converted to their Punycode representation prior to computation.
computer$ ./parse.py yaho.com Damerau-Levenshtein distance tested is 1 Names: [u'yho.com', u'yah.com', u'yato.com', u'yahoo.com'] IPs: ['18.104.22.168', '22.214.171.124', '126.96.36.199', '188.8.131.52'] ASNS: [u'AS36646 Yahoo', u'AS19324 Dosarrest Internet Security LTD', u'AS42503', u'AS36646 Yahoo'] Test name: yaho.com Test IP: 184.108.40.206 Test ASN: AS42173 The test name's ASN is NOT in the close match name ASNs.
- Watch for clients directly contacting outside nameservers, bypassing approved caching and/or authoritative nameservers.
- Watch for a high number of failed queries for a given client
- Look at substrings in labels that match substrings of well-known domains. Check ASN of IP for domain in question vs. ASN of IP for well-known domain. Mismatches are suspicious.
- Check known-bad domains for nameserver IP’s, registrant info, RRSETs. Compare unknown domains to these. Domains that use the same infrastructure as known-bad domains are likely also bad.