Take the 2-minute tour ×
Server Fault is a question and answer site for system and network administrators. It's 100% free, no registration required.

I'm running Ubuntu 12.04 LTS on a machine on my private network.

I have bind9 installed (v9.8.1-P1) via aptitude, so it appears to have put all the bits in the right places and the service starts automatically. I plan on adding some zones later, but first I'm just trying to get it working as a caching resolver. I installed bind, configured it, and starting using it. Initially I thought it was working ok, but then I found some sites weren't being resolved. I've pinned it down to being linked to the size of the result and bind failing-over to TCP mode.

So: I'm trying to find out why bind is failing when I query for domain info and the result is >512 bytes (causing a truncation and retry on TCP). Specifically it fails with ID mismatches if I point dig at localhost, but works when I query the machine's own IP (192.168.0.2). This appears to be backwards to the problem that most people have when using bind (fails on external ip, works on localhost).

If I do dig @localhost google.com (which has a response of <512 bytes) then it works; I get no warnings, and plenty of output.

$ dig @localhost google.com
; <<>> DiG 9.8.1-P1 <<>> @localhost google.com
[snip lots of output]
;; Query time: 39 msec
;; SERVER: 127.0.0.1#53(127.0.0.1)
;; WHEN: Thu Oct 17 23:08:34 2013
;; MSG SIZE  rcvd: 495

If I do dig @localhost play.google.com (which has a larger response) then I get back something like:

$ dig @localhost play.google.com
;; Truncated, retrying in TCP mode.
;; ERROR: ID mismatch: expected ID 3696, got 27130

This seems to be standard, documented behaviour - when the UDP response is large (here 'large' == 512 bytes) it falls back to TCP. The ID mismatch is not expected though.

If I do dig @192.168.0.2 play.google.com then I still get the warning about using TCP mode, but it otherwise works

$ dig @192.168.0.2 play.google.com
;; Truncated, retrying in TCP mode.
; <<>> DiG 9.8.1-P1 <<>> @192.168.0.2 play.google.com
[snip most of the output]
;; Query time: 5 msec
;; SERVER: 192.168.0.2#53(192.168.0.2)
;; WHEN: Thu Oct 17 23:05:55 2013
;; MSG SIZE  rcvd: 521

At the moment I've not set up any zones in my local instance, so it's just acting as a caching resolver. My options config is pretty much unchanged from standard, I've got the following set:

options {
    directory "/var/cache/bind";
    allow-query { 192.168/16; 127.0.0.1; };
    forwarders { 8.8.8.8; 8.8.4.4; };
    dnssec-validation auto;
    edns-udp-size 4096 ;
    allow-transfer { any; };
    auth-nxdomain no;    # conform to RFC1035
    listen-on-v6 { any; };
};

And my /etc/resolv.conf is just

nameserver 127.0.0.1
search .local

The problem definitely seems linked to the failover to TCP mode: if I do dig +bufsize=4096 @localhost play.google.com then it works; no warning about failover to TCP, no ID mismatch, and a standard looking result. To be honest, if there was a way to force bind to use a much larger UDP buffer, that'd probably be good enough for me, but all I've been able to find mention of is max-udp-size 4096 and that doesn't change the behaviour in any way.

I've also tried setting edns-udp-size 512 in case the problem is some weird EDNS issue with my router (which seems unlikely since the +bufsize=4096 flag works fine).

I've also tried dig +trace @localhost play.google.com; this works. No truncation/TCP warning, and a full result.

I've also tried changing the servers used in the forwarder (e.g. to OpenDNS), but that makes no difference.

There's one last data point: if I repetitively do dig @localhost play.google.com I don't always get an ID mismatch, but sometimes a REFUSED error. I'm much more likely to get a REFUSED error if I dig the non-localhost IP (192.168.0.2) first:

$ dig @localhost play.google.com
;; Truncated, retrying in TCP mode.
; <<>> DiG 9.8.1-P1 <<>> @localhost play.google.com
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: REFUSED, id: 35104
;; flags: qr rd ra; QUERY: 1, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 0
;; QUESTION SECTION:
;play.google.com.       IN  A
;; Query time: 4 msec
;; SERVER: 127.0.0.1#53(127.0.0.1)
;; WHEN: Thu Oct 17 23:20:13 2013
;; MSG SIZE  rcvd: 33

Any insights or things to try would be much appreciated.

share|improve this question

1 Answer 1

up vote 0 down vote accepted

Aha!

netstat -tulpn | grep 53 shows

tcp        0      0 192.168.0.2:53          0.0.0.0:*               LISTEN      9613/named
tcp        0      0 127.0.0.1:53            0.0.0.0:*               LISTEN      1161/dnsmasq

i.e. I somehow have two processes listening on port 53 (the DNS server port). named (aka bind) and dnsmasq. I assume this is the cause of the id mismatch - they're both sending requests and receiving each other's ID.

Turns out that dnsmasq is launched by default as part of the service network-manager. To fix this:

  1. edit /etc/NetworkManager/NetworkManager.conf
  2. comment out the line dns=dnsmasq
  3. do sudo restart network-manager (this will stop the dnsmasq service)
  4. do sudo service bind9 restart (this will relaunch bind9 and cause it to fully own requests coming in on port 53)
  5. done
share|improve this answer
    
It's worth noting that I still had problems with the TCP truncation, and have since switched to using unbound as it appears to be a more reliable validating caching resolver, and has a neat bit of functionality to redirect certain domains to a local ip, which is all I wanted in the first place. –  argibbs Oct 21 '13 at 13:16

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.