<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>ipsidixit.net &#187; rdisc6</title>
	<atom:link href="http://www.ipsidixit.net/tag/rdisc6/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.ipsidixit.net</link>
	<description>A far off place</description>
	<lastBuildDate>Thu, 08 Dec 2011 06:30:10 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>IPv6 and DNS</title>
		<link>http://www.ipsidixit.net/2010/04/02/243/</link>
		<comments>http://www.ipsidixit.net/2010/04/02/243/#comments</comments>
		<pubDate>Fri, 02 Apr 2010 08:33:37 +0000</pubDate>
		<dc:creator>sgroarke</dc:creator>
				<category><![CDATA[FPage]]></category>
		<category><![CDATA[C]]></category>
		<category><![CDATA[DNS]]></category>
		<category><![CDATA[icmp6]]></category>
		<category><![CDATA[IPv6]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[ndisc6]]></category>
		<category><![CDATA[network]]></category>
		<category><![CDATA[nslookup]]></category>
		<category><![CDATA[ping6]]></category>
		<category><![CDATA[rdisc6]]></category>
		<category><![CDATA[rdnss]]></category>
		<category><![CDATA[rdnssd]]></category>
		<category><![CDATA[tcpdump]]></category>
		<category><![CDATA[ubuntu]]></category>

		<guid isPermaLink="false">http://www.ipsidixit.net/2010/04/02/243/</guid>
		<description><![CDATA[<p>IPv6 DNS &#8211; It works for me&#8230;.. but it shouldn&#8217;t.</p> <p>When in my IPv6 environment I perform a test ping to, say, Google, it seems to work great:</p> ping6 ipv6.google.com PING ipv6.google.com(2a00:1450:8006::6a) 56 data bytes 64 bytes from 2a00:1450:8006::6a: icmp_seq=1 ttl=55 time=49.3 ms 64 bytes from 2a00:1450:8006::6a: icmp_seq=2 ttl=55 time=44.6 ms . . . [...]]]></description>
			<content:encoded><![CDATA[<p><img class="alignleft size-full wp-image-227" style="margin-top: 10px; margin-bottom: 10px; margin-left: 15px; margin-right: 15px;" title="IPv6 Logo" src="http://www.ipsidixit.net/wp-content/2010/02/IPv6-logo.png" alt="" width="100" height="60" />IPv6 DNS &#8211; It works for me&#8230;.. but it shouldn&#8217;t.</p>
<p>When in my IPv6 environment I perform a test ping to, say, Google, it seems to work great:</p>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">ping6 ipv6.google.com</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">PING ipv6.google.com(2a00:1450:8006::6a) 56 data bytes</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">64 bytes from 2a00:1450:8006::6a: icmp_seq=1 ttl=55 time=49.3 ms</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">64 bytes from 2a00:1450:8006::6a: icmp_seq=2 ttl=55 time=44.6 ms</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">.</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">.</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">.</span></div>
<p>Which is lovely. But I then ask myself how the ping6 command actually gets to know that name ipv6.google.com lives at IPv6 global address 2a00:1450:8006::6a. How is the domain name being resolved? And I find that I actually don&#8217;t know. I&#8217;m perfectly familiar with IPv4 DNS. So what&#8217;s going on here?</p>
<h2>I&#8217;m cheating</h2>
<p>I discover, upon investigation, that in fact I&#8217;m &#8220;cheating&#8221;. By that I mean that my attempt to set up a &#8220;pure&#8221; IPv6 environment (albeit in parallel with IPv4) that does not rely upon or touch IPv4 in any way has not been achieved &#8211; It turns out that my DNS is currently entirely dependent upon the existing IPv4 infrastructure! And before going ahead and trying to rectify that, it&#8217;s actually rather educational to understand how it is actually working at all.</p>
<p><span id="more-243"></span>So I run tcpdump on the IPv6 interface and take a look at what&#8217;s going on when I kick off the <em>ping6</em>:</p>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">13:28:36.671682 IP (tos 0&#215;0, ttl 64, id 45341, offset 0, flags [DF], proto UDP (17), length 61)</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> 11.11.11.11.48231 &gt; 212.XXX.XXX.XXX: [udp sum ok] 8831+ AAAA? ipv6.google.com. (33)</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">13:28:36.765503 IP (tos 0&#215;0, ttl 60, id 0, offset 0, flags [DF], proto UDP (17), length 250)</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> 212.XXX.XXX.XXX &gt; 11.11.11.11.48231: 8831 q: AAAA? ipv6.google.com. 7/0/0 ipv6.google.com. [1h49m54s] CNAME[|domain]</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">13:28:36.767123 IP (tos 0&#215;0, ttl 64, id 45365, offset 0, flags [DF], proto UDP (17), length 118)</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> 11.11.11.11.56346 &gt; 212.XXX.XXX.XXX: 37833+[|domain]</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">13:28:37.042646 IP (tos 0&#215;0, ttl 60, id 0, offset 0, flags [DF], proto UDP (17), length 178)</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> 212.XXX.XXX.XXX &gt; 11.11.11.11.56346: 37833 NXDomain q:[|domain]</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">.</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">.</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">.</span></div>
<div>So what&#8217;s all that about then?</div>
<div>We appear to have a perfectly standard IPv4 exchange taking place, but with a few odd bits mixed in! Taking it a step at a time&#8230;..</div>
<ul>
<li>A DNS query (UDP &#8211; port 53 &#8211; IPv4 &#8211; standard stuff) goes out for <em>ipv6.google.com</em>. The odd looking bit is the DNS query type: &#8220;AAAA&#8221;. What&#8217;s that? That actually signifies that this is an IPv6 query. Special.</li>
<li>And sure enough we get a response from the IPv4 DNS. It does not decode it here, but in the CNAME response data is the full IPv6 address required.</li>
<li>In fact it returns, as DNS queries often do, more than one address. It returns a selection of 6 of them, of which one gets selected for use.</li>
<li>And we then get a rather odd repeating pattern of subsequent PTR resolution attempts, which is a bit confusing. We&#8217;ll ignore that bit for now.</li>
</ul>
<p>So: in fact our IPv6 DNS is running (with great success!) but&#8230;&#8230;&#8230;&#8230;. over an entirely IPv4 infrastructure.</p>
<p>It&#8217;s fabulous that it all works so easily and seamlessly. <img src='http://www.ipsidixit.net/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' />  However, for the purposes of my voyage in to IPv6, I&#8217;d actually rather not use the IPv4 side of things at all. What if IPv4 wasn&#8217;t available to me? So what to do?</p>
<h2>Pure IPv6 Name Resolution &#8211; IPv6 DNS</h2>
<p>So we want to shift the DNS function off IPv4 and to make use of the IPv6 infrastructure. Where to being? Well, since setting up all the IPv6 I had noticed some new bit &#8216;n bobs appearing in my logs, as you do with new things. And I&#8217;d mostly ignored them for now. Again, as you do. But this one was appearing rather regularly, and now seemed rather interesting&#8230;</p>
<pre style="padding-left: 30px;">Mar 30 09:45:30 xxxxx radvd[2351]: RDNSS address 2a01:e00::1 received on eth0 from fe80::207:cbff:fea5:XXX is not advertised by us</pre>
<p>What&#8217;s that all about? Looking at the elements:</p>
<p style="padding-left: 30px;">
<ul>
<li style="padding-left: 30px;"><em>eth0</em> is my external (Internet-facing) interface</li>
<li style="padding-left: 30px;">the <em>fe80:</em> address is the IPv6 <em>link</em> address of my adjacent router (i.e. the ISP&#8217;s IPv6 router)</li>
<li style="padding-left: 30px;"><em>2a01:e00::1</em> is a normalish looking IPv6 global address. And sometimes I see the same log with <em>2a01:e00::2</em> in it instead.</li>
<li style="padding-left: 30px;">The RDNSS rather gives it away! &#8220;DNS.&#8221; Is this to do with DNS perhaps&#8230;?</li>
<li style="padding-left: 30px;">&#8220;&#8230;is not advertised by us&#8221; &#8211; What&#8217;s that all about?</li>
</ul>
<p>&nbsp;</p>
<p>Grabbing the incoming packet that seems to generate these logs I see more when fully decoded. The packet concerned is an expected <em>Router Advertisement</em> (RA) but it has some options on it:</p>
<p style="padding-left: 30px;">
<ul>
<li style="padding-left: 30px;">Prefix Information: this we expect. It tells me the 64-bit prefix that is &#8220;mine&#8221; to use for global IPv6 addresses.</li>
<li style="padding-left: 30px;">Recursive DNS Server: woah! That acronymises as RDNSS. And it hands me two &#8220;Recursive DNS Servers&#8221;: <em>2a01:e00::1</em> and <em>::2</em>. So that&#8217;s where they come from.</li>
<li style="padding-left: 30px;">MTU: an MTU of 1480 is specified in there too. I see that in fact my interface MTU is 1500. Should I worry? perhaps yes. But I&#8217;ll leave that for now and come back to it.</li>
<li style="padding-left: 30px;">Source link-layer address: we can ignore that. <img src='http://www.ipsidixit.net/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' /> </li>
</ul>
<p>&nbsp;</p>
<h2>Manual test of IPv6 DNS</h2>
<p>Before jumping in to new software subsystems, let&#8217;s try a manual test and see what happens. Just as one can use nslookup on the command line to check name resolution for IPv4, so one can use it for IPv6 too. Specify the name to be resolved and the server to us (or else we will default as per /etc/resolv.conf) and see what happens, checking with tcpdump:</p>
<pre style="padding-left: 30px;"><span style="font-family: 'Courier New';"> </span><span style="font-size: medium;">nslookup ipv6.google.com 2a01:e00::1</span></pre>
<p>And I see the following packet sequence result:</p>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">10:23:43.522926 IP6 (hlim 64, next-header UDP (17) payload length: 41) 2a01:XXX:8b25:7ea0:240:63ff:fef5:f93c.52838 &gt; dns2.proxad.net.domain: [udp sum ok] 9362+ A? ipv6.google.com. (33)</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"><br />
</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">10:23:43.577684 IP6 (hlim 255, next-header ICMPv6 (58) payload length: 32) fe80::207:cbff:fea5:XXX &gt; ff02::1:fff5:XXX: [icmp6 sum ok] ICMP6, neighbor solicitation, length 32, who has 2a01:XXX:8b25:7ea0:240:63ff:fef5:f93c</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> source link-address option (1), length 8 (1): 00:07:cb:a5:1a:68</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> 0&#215;0000:  0007 cba5 1a68</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"><br />
</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">10:23:43.577937 IP6 (hlim 255, next-header ICMPv6 (58) payload length: 32) 2a01:XXX:8b25:7ea0:240:63ff:fef5:f93c &gt; fe80::207:cbff:fea5:XXX: [icmp6 sum ok] ICMP6, neighbor advertisement, length 32, tgt is 2a01:XXX:8b25:7ea0:240:63ff:fef5:f93c, Flags [router, solicited, override]</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> destination link-address option (2), length 8 (1): 00:40:63:f5:f9:3c</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"> 0&#215;0000:  0040 63f5 f93c</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';"><br />
</span></div>
<div style="padding-left: 30px;"><span style="font-family: 'Courier New';">10:23:43.578294 IP6 (hlim 60, next-header UDP (17) payload length: 112) dns2.proxad.net.domain &gt; 2a01:XXX:8b25:7ea0:240:63ff:fef5:f93c.52838: [udp sum ok] 9362 q: A? ipv6.google.com. 1/1/0 ipv6.google.com. [2h44m2s] CNAME ipv6.l.google.com. ns: l.google.com. [10m] SOA ns4.google.com. dns-admin.google.com. 1411041 900 900 1800 60 (104)</span></div>
<p>Key here are the first and fourth packets: DNS request out, and DNS response back. All in IPv6. No IPv4 there at all. That&#8217;s good. We can see our IPv6 DNS server and, in principle, they work.</p>
<h2>A secret &#8211; ndisc6</h2>
<p>Time to let you in on a little secret to make life much easier&#8230; While tcpdumps and so on are instructive up to a point, and force one to think a little about what is being seen, they are also pretty tedious. A lot of what we need to achieve here can be done using much more accessible tools! Do yourself a big favour and install the ndisc6 package on your linux system. The <a id="p49f" title="creator's web page" href="http://www.remlab.net/ndisc6/"><span style="color: #000000;">creator&#8217;s web page</span></a> gives you a little more information, but just as an example, look at this command + output:</p>
<div><span style="font-size: medium;"><strong>rdisc6  eth0</strong></span></div>
<div><span style="font-family: 'Courier New';">Soliciting ff02::2 (ff02::2) on eth0&#8230;</span></div>
<div><span style="font-family: 'Courier New';">Hop limit                 :           64 (      0&#215;40)</span></div>
<div><span style="font-family: 'Courier New';">Stateful address conf.    :           No</span></div>
<div><span style="font-family: 'Courier New';">Stateful other conf.      :           No</span></div>
<div><span style="font-family: 'Courier New';">Router preference         :       medium</span></div>
<div><span style="font-family: 'Courier New';">Router lifetime           :         1800 (0&#215;00000708) seconds</span></div>
<div><span style="font-family: 'Courier New';">Reachable time            :  unspecified (0&#215;00000000)</span></div>
<div><span style="font-family: 'Courier New';">Retransmit time           :  unspecified (0&#215;00000000)</span></div>
<div><span style="font-family: 'Courier New';"> Source link-layer address: 00:40:63:F5:F9:3C</span></div>
<div><span style="font-family: 'Courier New';"> from fe80::240:63ff:fef5:f93c</span></div>
<div><span style="font-family: 'Courier New';">Hop limit                 :           64 (      0&#215;40)</span></div>
<div><span style="font-family: 'Courier New';">Stateful address conf.    :           No</span></div>
<div><span style="font-family: 'Courier New';">Stateful other conf.      :           No</span></div>
<div><span style="font-family: 'Courier New';">Router preference         :       medium</span></div>
<div><span style="font-family: 'Courier New';">Router lifetime           :         1800 (0&#215;00000708) seconds</span></div>
<div><span style="font-family: 'Courier New';">Reachable time            :  unspecified (0&#215;00000000)</span></div>
<div><span style="font-family: 'Courier New';">Retransmit time           :  unspecified (0&#215;00000000)</span></div>
<div><span style="font-family: 'Courier New';"> Prefix                   : 2a01:XXX:8b25:7ea0::/64</span></div>
<div><span style="font-family: 'Courier New';"> Valid time              :        86400 (0&#215;00015180) seconds</span></div>
<div><span style="font-family: 'Courier New';"> Pref. time              :        86400 (0&#215;00015180) seconds</span></div>
<div><span style="font-family: 'Courier New';"> Recursive DNS server     : 2a01:e00::2</span></div>
<div><span style="font-family: 'Courier New';"> Recursive DNS server     : 2a01:e00::1</span></div>
<div><span style="font-family: 'Courier New';"> DNS servers lifetime    :          600 (0&#215;00000258) seconds</span></div>
<div><span style="font-family: 'Courier New';"> MTU                      :         1480 bytes (valid)</span></div>
<div><span style="font-family: 'Courier New';"> Source link-layer address: 00:07:CB:A5:1A:68</span></div>
<div><span style="font-family: 'Courier New';"> from fe80::207:cbff:fea5:1a68</span></div>
<p>Wow. Look at all that! Useful.</p>
<p>Now to move on to integrating this into the system so all IPv6 names get resolved this was.</p>
<h2>rdnssd &#8211; Recursive DNS Server daemon</h2>
<p>I think I should start out with a warning here: this next step is the entirely logical and sensible thing to do. But in fact read through to the end: it&#8217;s not going to work &#8211; the Linux IPv6 userspace tools are simply not quite here they should be yet&#8230; But it&#8217;s instructive to look at this, if only for the learning it provides.</p>
<p>Let&#8217;s set up the required sub-system to handle IPv6 DNS requests from this system and the users who will later traverse it. The first step is simply to install the required package:</p>
<p style="padding-left: 30px;"><span style="font-family: 'Courier New';">apt-get install rdnssd</span></p>
<p>This package may have other dependencies, which should get automatically fulfilled, e.g. <em>resolvconf</em>)</p>
<div>Just what is rdnssd? The best summary of it I can see is the first paragraph of the associated <em>man</em> page:</div>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">rdnssd is a daemon program providing client-side support for DNS configuration using the Recursive</span></div>
<div><span style="font-family: 'Courier New';">DNS Server (RDNSS) option, as described in RFC 5006. Its purpose is to supply IPv6 DNS resolvers</span></div>
<div><span style="font-family: 'Courier New';">through stateless autoconfiguration, carried by Router Advertisements.</span></div>
<div><span style="font-family: 'Courier New';"><br />
</span></div>
</blockquote>
<p>That pretty much sums it up. It&#8217;s just what we need here!</p>
<div>The second paragraph is also quite illuminating:</div>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">rdnssd parses RDNSS options and keeps track of resolvers to write nameservers entries to a</span></div>
<div><span style="font-family: 'Courier New';">resolv.conf(5) configuration file. By default, it writes its own separate file, and may call an</span></div>
<div><span style="font-family: 'Courier New';">external hook to merge it with the main /etc/resolv.conf. This is aimed at easing coexistence with</span></div>
<div><span style="font-family: 'Courier New';">concurrent daemons, especially IPv4 ones, updating /etc/resolv.conf too.</span></div>
</blockquote>
<p>So, we&#8217;ve installed it. What&#8217;s it doing? Straight after installing the package a ps -ef shows me that the process is running. I rerun my ping6 and nslookup (without specifying th IPv6 DNS this time) and tcpdump shows me no change: the DNS is still taking place over IPv4.</p>
<p>As mentioned at the start of thus sub-section, we have a problem here. A big, fat problem. We want this daemon to pick up our DNS server from the RA and use them. Which is fine. But check out the last para of the rdnssd man page:</p>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">When rdnssd uses a raw socket instead of the netlink kernel interface, it does not validate received</span></div>
<div><span style="font-family: 'Courier New';">Neighbor Discovery traffic in any way. For example, it will always consider Router Advertisement</span></div>
<div><span style="font-family: 'Courier New';">packets, whereas it should not if the host is configured as a router. When the netlink interface is</span></div>
<div><span style="font-family: 'Courier New';">used, such validation is done by the kernel.</span></div>
</blockquote>
<p>What that boils down to is that if we&#8217;re running as a <em>router</em> (and we are, since in <em>/etc/sysctl.conf</em> we have <em>net.ipv6.conf.all.forwarding=1</em>) the kernel will simply not pass the RA up to user-space at all. So rdnssd never gets the chance to see it, and thus never acts upon it. Which is a bummer.</p>
<p>Just to experiment, you can dynamically drop down to <em>/proc/sys/net/ipv6/conf/all/forwarding</em> and set it to &#8217;0&#8242;. (radvd will bitch and moan, but ignore that.) Force a RA refresh if required, using rdisc eth0, and you will see rdnssd do its stuff and change the <em>/etc/resolv.conf</em> to point at the IPv6 servers. But we can&#8217;t leave it that way, alas. We&#8217;ve hit a bit of a blocker here &#8211; picking up the IPv6 DNS servers automatically from the ISP seems to not be achievable at the moment using rdnssd &#8211; the kernel&#8217;s policies for what is allowed and when prevent it.</p>
<h2>So what do we do?</h2>
<p>We now understand what we&#8217;re trying to do. We also understand how it should be doable. But currently there&#8217;s a blocker. What to do?</p>
<p>As always in such matters, there&#8217;s an easy, pragmatic way forward and a tricky, hacky way forward! The sensible path to take is very simple indeed. We know the IPv6 addresses of our DNS servers (and if we forget we can just do a rdisc eth0 to find them out again) The obvious thing to do it to statically configure them in to the existing <em>/etc/resolv.conf</em> and then, when we later use IPv6 from a device on the internal network, configure them there too.</p>
<p>That&#8217;s what I would recommend. That&#8217;s what you should do. You can specify a mixture of IPv6 and IPv4 name-server in the <em>/etc/resolv.conf file</em>. If you specify the IPv6 servers first, then all DNS on the system will (if available) use the IPv6 name servers. I suppose this does slightly violate still our desire to keep IPv4 and IPv6 separate (since IPv4 name resolution will now also use IPv6) but since it tilts the bias in favour if IPv6, with a seamless fallback to IPv4, I think I can live with that.</p>
<h2>OK &#8211; but what about more wacky solutions?</h2>
<div><strong><em>[Remember, stop here unless you're wanting to have some fun</em></strong><em><strong> and</strong></em><strong><em> you are comfortable with building your own software.]</em></strong></div>
<p>One approach that would give us a partial solution would be to admit we were wrong originally, and instead of using radvd to propagate simple prefix information into our internal networks we should instead use a fully-fledged IPv6 DHCP server that can propagate addressing and DNS information. This would solve the problem of devices inside the network needing to have the IPv6 DNSs statically configured on them. However even this would not solve the root issue here: our inability to automatically pick up the IPv6 DNS information from received RAs when we&#8217;re configured to operate as a router.</p>
<p>The problem there is not, directly, rdnssd itself. The problem is the kernel. An architectural decision has been taken to stop the kernel sending RA DNS data up to userspace if the system is functioning as a router. Good or bad decision? Bad in my view. I can understand why it is sensible default behaviour, yes. But I do not understand why it&#8217;s been made unchangeable. But that&#8217;s how it is, for now anyway.</p>
<p>The solution I&#8217;m going to go for is to actually bypass the policing mechanism itself. The kernel only manages to stop the DNS being sent to userspace when userspace uses the Netlink mechanism to talk down. So why not just bypass that and get the raw data we want? This should bre easy enough to do, as rdnssd itself used to work this way, before the kernel started using Netlink to talk to userspace. So we might be able to build rdnssd to behave as it used to and get the data, right?</p>
<h3>Hack and build rdnssd</h3>
<p>The existing rndssd code makes provision for kernels <em>with </em> the netlink capability which causes us problems and for older kernels <em>without</em> that capability. So all the code we need is already in place. All we really need to do is change the default behaviour of <em>rdnssd</em> to the old way and we&#8217;ll be all set. One could of course do this properly and completely using command line options. Here&#8217;s what you might do in terms of changes to the <em>rdnssd</em> code-base:</p>
<h3>Edit rdnssd.c</h3>
<p>In <em>usage()</em>, ad a line such as:</p>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">&#8221;  -n  &#8211;no-netlink  use old method to pick up kernel notificationsn&#8221;</span></div>
</blockquote>
<p>In <em>main() </em>drop in appropriate parameter parsing:</p>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">static const struct option opts[] =</span></div>
<div><span style="font-family: 'Courier New';"> {</span></div>
<div><span style="font-family: 'Courier New';"> { &#8220;foreground&#8221;,         no_argument,            NULL, &#8216;f&#8217; },</span></div>
<div><span style="font-family: 'Courier New';"> { &#8220;no-netlink&#8221;,         no_argument,            NULL, &#8216;n&#8217;},</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
</blockquote>
<p>and an appropriate global:</p>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'courier new';">bool nonetlink = false;</span></div>
</blockquote>
<p>and then in the main parsing switch add:</p>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">case &#8216;n&#8217;:</span></div>
<div><span style="font-family: 'Courier New';"> nonetlink = true;</span></div>
<div><span style="font-family: 'Courier New';"> break;</span></div>
</blockquote>
<p>Then finally up in worker() we act upon it.</p>
<p>Before we had:</p>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">static int worker (int pipe, const char *resolvpath, const char *username)</span></div>
<div><span style="font-family: 'Courier New';">{</span></div>
<div><span style="font-family: 'Courier New';"> sigset_t emptyset;</span></div>
<div><span style="font-family: 'Courier New';"> int rval = 0, sock = -1;</span></div>
<div><span style="font-family: 'Courier New';"> const rdnss_src_t *src;</span></div>
<div><span style="font-family: 'Courier New';">#ifdef __linux__</span></div>
<div><span style="font-family: 'Courier New';"> src = &amp;rdnss_netlink;</span></div>
<div><span style="font-family: 'Courier New';"> sock = src-&gt;setup ();</span></div>
<div><span style="font-family: 'Courier New';">#endif</span></div>
<div><span style="font-family: 'Courier New';"> if (sock == -1)</span></div>
<div><span style="font-family: 'Courier New';"> {</span></div>
<div><span style="font-family: 'Courier New';"> src = &amp;rdnss_icmp;</span></div>
<div><span style="font-family: 'Courier New';"> sock = src-&gt;setup ();</span></div>
<div><span style="font-family: 'Courier New';"> }</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
</blockquote>
<p>Change it to something like:</p>
<blockquote style="border: none; margin: 0 0 0 40px;">
<div><span style="font-family: 'Courier New';">static int worker (int pipe, const char *resolvpath, const char *username)</span></div>
<div><span style="font-family: 'Courier New';">{</span></div>
<div><span style="font-family: 'Courier New';"> sigset_t emptyset;</span></div>
<div><span style="font-family: 'Courier New';"> int rval = 0, sock = -1;</span></div>
<div><span style="font-family: 'Courier New';"> const rdnss_src_t *src;</span></div>
<div><span style="font-family: 'Courier New';">#ifdef __linux__</span></div>
<div><span style="font-family: 'Courier New';"> if (!nonetlink) {</span></div>
<div><span style="font-family: 'Courier New';"> src = &amp;rdnss_netlink;</span></div>
<div><span style="font-family: 'Courier New';"> sock = src-&gt;setup ();</span></div>
<div><span style="font-family: 'Courier New';"> }</span></div>
<div><span style="font-family: 'Courier New';">#endif</span></div>
<div><span style="font-family: 'Courier New';"> if (sock == -1)</span></div>
<div><span style="font-family: 'Courier New';"> {</span></div>
<div><span style="font-family: 'Courier New';"> src = &amp;rdnss_icmp;</span></div>
<div><span style="font-family: 'Courier New';"> sock = src-&gt;setup ();</span></div>
<div><span style="font-family: 'Courier New';"> }</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
<div><span style="font-family: 'Courier New';">.</span></div>
</blockquote>
<p>and we&#8217;re good. Build, install and use as before, but using the new cli parameter &#8220;-n&#8221; as required to force the old behaviour.</p>
<p><a title="rdnssd.c - proof of concept" href="http://www.ipsidixit.net/wp-content/2010/04/rdnssd.c" target="_blank">Attached is a version of rdnssd.c </a>based off version 0.9.9 for reference.</p>
<p>For finishing touches, set up an rdnssd hook-file which puts the IPv6 nameservers first in /etc/resolv.conf, and then have the original IPv4 servers appended after them.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.ipsidixit.net/2010/04/02/243/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>

