Ran across an exploit for glibc today which involves the getaddrinfo() call for DNS resolution. I'm running Ubuntu 12.04 on two Bind9 boxes that face the internet. I'm not sure I totally understand the exploit, but it seems to be caused by a large reply from a malicous DNS server. One of the mitigations is a "firewall that drops UDP DNS packets > 512 bytes" so I've configured netfilter on the DNS servers to drop any UDP > 512 bytes coming from, or going to, port 53:
-A INPUT -i lo -j ACCEPT
-A INPUT -p udp --sport 53 -m length --length 511:65535 -j DROP
-A INPUT -p udp --dport 53 -m length --length 511:65535 -j DROP
-A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
Is there a better way to do this with a Bind setting or anything? I've tested the rule with scapy and it does indeed block a UDP packet > 512 tossed at port 53.
UPDATED per responses:
-A INPUT -i lo -j ACCEPT
-A INPUT -p udp --sport 53 -m length --length 949:65535 -j DROP
-A INPUT -p udp --dport 53 -m length --length 949:65535 -j DROP
-A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
and /etc/bind/named.conf.options
options {
...
// 2016-02-17 - tmb - glibc exploit mitigation
edns-udp-size 900 ;
max-udp-size 900 ;
};
UPDATE 2: As pointed out by atdre below, Cloudflare tried the above technique and although the entire payload could not be transferred, memory corruption was still a possibility. I think I'll look into Unbound.
While A firewall that drops UDP DNS packets > 512 bytes. mitigates the exploit (over UDP specifically, TCP can still be an attack vector) it's also not correct behaviour and breaks other functionality instead.
Since the introduction of EDNS0 there is no such limit in the DNS spec and you will cause breakages for valid traffic by just dropping packets.
What birdwes suggests, with configuring a resolver nameserver to limit response sizes back to its clients is a better way as clients will at least be properly notified (truncated response) as per the specs instead of just silence and eventually a timeout, but the proper solution is to install patched glibc (that's where something is wrong, the size is not wrong).
If you are running bind locally, this gives you a test:
as described here: https://www.dns-oarc.net/oarc/services/replysizetest .
You will get a reply like this:
and you can add the bind option
in the file named.conf
as described here: https://labs.ripe.net/Members/anandb/content-testing-your-resolver-dns-reply-size-issues .
I would use this in conjunction with other mitigations too.
After a bit of testing, CloudFlare determined that limiting the response size of DNS packets and turning off EDNS0 support did not remediate CVE-2015-7547. You can test for yourself using the author's PoC code, available as linked gists throughout the post.
You can read about their conclusions and well as see the results of their tests here -- https://blog.cloudflare.com/a-tale-of-a-dns-exploit-cve-2015-7547/
CloudFlare says,
Giving the following three useful utilities as open-source resolvers that you can install and configure:
They also go on to say,