[CVE-2020-8616] BIND does not sufficiently limit the number of fetches performed when processing referrals
As reported to ISC Security Officer by researcher Lior Shafir, Tel-Aviv University:
Dear BIND team,
The email reports on a BIND recursion behavior which we believe might become a potential DDoS/DoS vulnerability, against recursive and authoritative DNS servers.
This observation is part of our ongoing academic research focusing on DNS inefficiencies and vulnerabilities. In part we research the interaction between recursive resolvers and the authoritative hierarchy. Our main experimental platform includes BIND 9 recursive and authoritative server instances.
We observe that the information in the NS referral response at the different recursive steps, and the actions taken by the recursive resolvers in response to receiving it, might introduce large undesired overheads, that in extreme cases, might be used by attackers to perform a DoS attack with high amplification. More specifically, we found that an NS referral response that contains multiple name-servers, but without their corresponding IP-addresses (glue-records), either because the name-servers are out-of-bailiwick, or due to missing glue-records in the referral response, forces the recursive resolver to issue ‘fetches’ for all the name-servers in the referral response. We observed that the only limitation on the number of fetches that BIND 9 recursive resolver issues as a result of a single referral response, is set indirectly by the global 'max-recursion-queries' threshold, however, aside from that, there is no specific limit on the number of name-servers (without glue records) in the referral response, each of which in a ‘fetch’ to obtain the name-server IP address.
We consider a threat model, in which the attacker targets an authoritative server, e.g., ‘ns.victim.com’. We assume that the attacker operates or has access to an authoritative server, e.g., ‘ns.attacker.foo.com’. The attacker sends DNS ‘A’ client requests to resolve ‘example.attacker.foo.com’ (either to a single resolver or through a botnet to multiple recursive resolvers as in Mirai). The requests arrive at the attacker’s authoritative server (e.g., ns.attacker.foo.com) which crafts a different referral response for each one of the requests as follows: Each referral response includes many faked non-existing subdomains of the victim: fake1.victim.com, fake2.victim.com, … , but does not include their corresponding glue-records. This forces the recursive resolver to initiate a fetch (‘A’ request) to resolve the IP address of each one of the name-servers in the NS referral response.
We experimented this attack in our setup using multiple versions of BIND 9.11 and 9.12 (e.g., 9.12.3). Our results show that a single NS referral response of 20 name-servers results in more than 90 packets (sent and received) between the recursive resolver and the victim authoritative server (the BIND resolver issues a fetch for each one of the name-servers in the referral, with an additional retry after it receives NXDOMAIN response from the victim authoritative). The amplification factor of this example attack is already 45, and we believe a factor of more than 100 is attainable, i.e., 200 packets as a result of one attacker requests (=2 packets) (corresponding experiments are being performed). Notice, this amplification is much higher than the one in the NXDOMAIN attack (e.g., in the Mirai on Oct. 2016).
According to our analysis, the code that issues these additional fetches is in resolver.c as part of the fctx_getaddresses function bind9/lib/dns/resolver.c, line 3660 (master branch)
for (result = dns_rdataset_first(&fctx->nameservers);
result == ISC_R_SUCCESS;
result = dns_rdataset_next(&fctx->nameservers))
{
bool overquota = false;
dns_rdataset_current(&fctx->nameservers, &rdata);
/*
* Extract the name from the NS record.
*/
result = dns_rdata_tostruct(&rdata, &ns, NULL);
if (result != ISC_R_SUCCESS)
continue;
findname(fctx, &ns.name, 0, stdoptions, 0, now,
&overquota, &need_alternate);
if (!overquota)
all_spilled = false;
dns_rdata_reset(&rdata);
dns_rdata_freestruct(&ns);
}
We provide here a general description of this potential security vulnerability. If requested and necessary, we can provide more details about our experiments, results, evaluations including figures and tables that describe the threat, its execution, and the impact of such possible attack.