[Dnsmasq-discuss] 2.68rc4: bind-interfaces, FreeBSD, IPv6 2001:... addr fails and loses error code, parallel build brittle

Matthias Andree matthias.andree at gmx.de
Mon Dec 2 21:13:00 GMT 2013

Am 02.12.2013 13:01, schrieb Simon Kelley:
> On 01/12/13 01:59, Matthias Andree wrote:
>> Greetings,
>> testing 2.68rc4, I have found three issues, on FreeBSD 9.2 amd64:
>> 1. the Makefiles might not thoroughly list all dependencies required to
>> build the dnsmasq executable; I found my build miss cache.o when linking
>> (compiling with make -j + high number), re-running make immediately
>> after the failure "solved" the problem.
>> I am using a local UFS file system, so no NFS time skew.
>> I am using GNU make 3.82.
> By "miss cache.o" do you meant that cache.o was not included in the link
> command line, or that the link failed because cache.o had not been
> built. This is mysterious, and there's nothing different about cache.o
> versus the other object files.

The latter, and I suspect that it might have been any other cache.o file.

> I'd be interested to know the status of those addresses, and Duplicate
> Address Detection, since that's the best explanation I have of the
> source of that error return. Is it possible to turn DAD off, and see if
> that fixes things?

Yes, but it is neither the culprit nor does it fix things.

> I'm also interested in what's happening in bpf.c in the interface
> enumeration code:
>          ifr6.ifr_addr = *((struct sockaddr_in6 *) addrs->ifa_addr);
>               if (fd != -1 && ioctl(fd, SIOCGIFAFLAG_IN6, &ifr6) != -1)
>                 {
>                   if (ifr6.ifr_ifru.ifru_flags6 & IN6_IFF_TENTATIVE)
>                     flags |= IFACE_TENTATIVE;
> Should set IFACE_TENTATIVE in flags if the interface is still doing DAD.

The address is marked with only the IN6_IFF_AUTOCONF flag.
IN6_IFF_TENTATIVE in particular is unset.

On the second another 2001:... address, I have automatic | temporary
(private).  Meaning that the ifconfig output renders the interface flags
quite well.  But that's not the issue here.

The flags variable you pass through the callback on line 199 in bpf.c
ends up as 0 for these two aliases on em0.

Anyways I debugged this a bit more, and in network.c you have:

   698	#ifdef HAVE_IPV6
   699	  if (family == AF_INET6 && setsockopt(fd, IPPROTO_IPV6,
IPV6_V6ONLY, &opt, sizeof(opt)) == -1)
   700	    goto err;
   701	#endif
   703	  if ((rc = bind(fd, (struct sockaddr *)addr, sa_len(addr))) == -1)
   704	    goto err;

When this is run on the 2001:. addresses, addr->in6.sin6_scope_id is not
0.  Setting this to 0 only on the 2001:... addresses makes the bind
succeed, and presents me with:

> dnsmasq: started, version 2.68rc4-2-g0861921 cachesize 150
> dnsmasq: compile time options: IPv6 GNU-getopt no-DBus no-i18n no-IDN DHCP DHCPv6 no-Lua TFTP no-conntrack no-ipset auth
> dnsmasq: LOUD WARNING: listening on 2001:BLAH:BLAH:893e:a00:MAC:ADDR:HERE may accept requests via interfaces other than em0
> dnsmasq: LOUD WARNING: use --bind-dynamic rather than --bind-interfaces to avoid DNS amplification attacks via these interface(s)
> dnsmasq: using nameserver
> dnsmasq: read /etc/hosts - 5 addresses

Now we're getting somewhere, apparently FreeBSD chokes if you present a
nonzero sin6_scope_id with a regular unicast address, rather than a
link-local special address (which requires the interface index), whereas
Linux appears to ignore it.

Could you double-check iface_allowed_v6() and the network enumeration
code that calls it, and the code in network.c:703 that calls bind()?
Either needs to zero out the scope_id for non-link-local i'faces.

That aside, I am not sure what this LOUD WARNING is about here, and if
it applies to FreeBSD (it would seem Linux can do reverse path checking,
too, and reject martians if the stuff arrives on the wrong interface's

> I'll commit a fix for the simple errno problem, to make things easier.

Unfortunately, that does not appear to work either, I still get
"dnsmasq: failed to create listening socket for 2001:...c258%em0: No
error: 0". (I am on git master, which is one commit ahead of 3dffbc3eb).

I am attaching an incremental patch (use "git am" to apply it) to the
current Git master that fixes the problem for me. It merely extends the
scope of the errsav copy of the actual errno code.
(Sending a Bcc: to Simon in case the list driver strips it.)

Hope that helps.

Best regards

-------------- next part --------------
A non-text attachment was scrubbed...
Name: fix-errno-saving.patch
Type: text/x-patch
Size: 1643 bytes
Desc: not available
URL: <http://lists.thekelleys.org.uk/pipermail/dnsmasq-discuss/attachments/20131202/fb39510a/attachment.bin>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 198 bytes
Desc: OpenPGP digital signature
URL: <http://lists.thekelleys.org.uk/pipermail/dnsmasq-discuss/attachments/20131202/fb39510a/attachment.pgp>

More information about the Dnsmasq-discuss mailing list