1

I noticed a routing issue with IPv6 with our LAN. Most of the client PCs are LTSP thin clients. They get one address through SLAAC. Tracepath6 to hosts on the same subnet shows all traffic is direct. But, the laptop I'm working on (Linux Mint 17, standard network manager), gives itself two IPv6 addresses, and sets up routes that all traffic goes to the router first, including traffic in the same subnet:

tracepath6 xxxx:1b0:5256:1337:10:50:0:8
 1?: [LOCALHOST]                        0.183ms pmtu 1500
 1:  xxxx:1b0:5256:1337:10:50:0:1                          1.217ms

Questions:

1) Why do some hosts get one and some hosts more addresses? I've see this happen more often.

2) Why is this machine choosing to route all traffic through the router?

The router is dnsmasq, and indeed only has SLAAC:

Jan 22 11:34:36 gatekeeper dnsmasq-dhcp[9796]: IPv6 router advertisement enabled
Jan 22 11:34:36 gatekeeper dnsmasq-dhcp[9796]: DHCP, IP range 10.102.20.1 -- 10.102.20.254, lease time 12h
Jan 22 11:34:36 gatekeeper dnsmasq-dhcp[9796]: DHCP, IP range 10.101.20.1 -- 10.101.20.254, lease time 12h
Jan 22 11:34:36 gatekeeper dnsmasq-dhcp[9796]: DHCP, IP range 10.100.0.100 -- 10.100.0.254, lease time 12h
Jan 22 11:34:36 gatekeeper dnsmasq-dhcp[9796]: DHCP, IP range 10.50.20.1 -- 10.50.20.254, lease time 12h
Jan 22 11:34:36 gatekeeper dnsmasq-dhcp[9796]: SLAAC on xxxx:1b0:5256:1337:: prefix valid 2h

This is my eth0:

eth0      Link encap:Ethernet  HWaddr 18:67:b0:34:2d:dd
          inet addr:10.50.20.158  Bcast:10.50.255.255  Mask:255.255.0.0
          inet6 addr: fe80::1a67:b0ff:fe34:2ddd/64 Scope:Link
          inet6 addr: xxxx:1b0:5256:1337:2532:eb1a:1151:d2f0/64 Scope:Global
          inet6 addr: xxxx:1b0:5256:1337:1a67:b0ff:fe34:2ddd/64 Scope:Global
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:12094 errors:0 dropped:0 overruns:0 frame:0
          TX packets:17250 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000
          RX bytes:2848542 (2.8 MB)  TX bytes:3002689 (3.0 MB)

These are the IPv4 routes:

> route -n 
Kernel IP routing table Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         10.50.0.1       0.0.0.0         UG    0      0        0 eth0
10.50.0.0       0.0.0.0         255.255.0.0     U     1      0        0 eth0

These are the IPv6 routes:

Kernel IPv6 routing table
Destination                    Next Hop                   Flag Met Ref Use If
fe80::/64                      ::                         U    256 1     0 eth0
::/0                           fe80::213:3bff:fe0f:c02c   UG   1   0     0 eth0
::/0                           fe80::213:3bff:fe0f:c02c   UGDAe 1024 0     0 eth0
::/0                           ::                         !n   -1  1   261 lo
::1/128                        ::                         Un   0   3   243 lo
xxxx:1b0:5256:1337:1a67:b0ff:fe34:2ddd/128 ::                         Un   0   1     0 lo
xxxx:1b0:5256:1337:2532:eb1a:1151:d2f0/128 ::                         Un   0   1    86 lo
fe80::1a67:b0ff:fe34:2ddd/128  ::                         Un   0   1   178 lo
ff00::/8                       ::                         U    256 1     0 eth0
::/0                           ::                         !n   -1  1   261 lo

The following line is not present on hosts that reach other hosts directly:

::/0                           fe80::213:3bff:fe0f:c02c   UG   1   2     0 eth0

fe80::213:3bff:fe0f:c02c indeed is the link-local address of the router, LAN-side.

Edit: the behavior I've been seeing might be random. I rebooted one of the thin clients a bunch of times, and a tracepath6 sometimes shows traffic going through the router, sometimes directly to hosts. It's different almost every reboot, it seems. The routing table is exactly the same each time, also if I enable/disable the dnsmasq off-link option.

Edit2: IPv4 always has a route that states that for your own subnet, it should just send over eth0, for instance. So, when I add this route in IPv6, traffic no longer goes through the router:

/sbin/route -A inet6 add xxxx:1b0:5256:1337::/64 dev eth0

So, why is xxxx:1b0:5256:1337::/64 not included by default (on any machine here)? Shouldn't a route be present that tells the kernel that for the current subnet, just send out over Ethernet (or wlan, whatever)?

Edit3: I just looked with tcpdump+wireshark and saw that the L flag, On-Link, is not set in the router advertisement, despite off-link not being set:

dhcp-range=xxxx:1b0:5256:1337::, ra-only, inifite
2

1) Why do some hosts get one and some hosts more addresses? I've see this happen more often.

IPv6 hosts always get a link-local address. The other addresses depend on a combination of the flags in the RA and the host settings. The RA can signal to the host that a DHCPv6 server might hand out addresses, which the host can act upon. If the RA contains prefixes that allow auto configuration and the host hasn't disabled auto configuration then SLAAC is used.

The original specifications said that the interface-id (the last 64 bits of the IPv6 address) are constructed from the link-layer address (usually the MAC address). But it would then be possible to track devices across the internet. Imagine an often contacted service Google or Dropbox: to whatever network you connect your laptop or mobile phone, the subnet will change but the interface-id will always be the same. Therefore operating systems provide privacy extensions these days.

Privacy extensions make your interface-id change regularly. The exact timers are implementation dependent, but let's assume it changes every hour. Every hour your device configures a new IPv6 address for itself. Old addresses are deprecated, and once your software stops using them they get removed. That way you can end up with multiple addresses.

Also: when an RA contains multiple prefixes with the auto configuration flag set your device will configure addresses in each of them.

2) Why is this machine choosing to route all traffic through the router?

That usually depends on the On-Link flag in the prefixes in the RA. If the on-link flag is set the device can create a route for the /64 to the interface. If the flag is not set then the device can't know if the other addresses in the prefix are on-link and it sends all those packets to the default gateway.

Of course your device can always choose (intentionally or because of a bug) to ignore the on-link flag and send everything to the default gateway anyway.

  • Regarding "1", with the link-local, there are 3 addresses. And the other two are selected right from the start. Regarding "2", I'll investigate what happens when I configure dnsmasq with off-link. If other hosts act the same as this laptop, there may be a bug in Network Manager. – Halfgaar Jan 22 '16 at 12:25
  • Three addresses is common: 1 link-local, 1 constant SLAAC (marked autoconf) and 1 changing SLAAC (marked autoconf temporary). Check with ip -6 addr – Sander Steffann Jan 22 '16 at 12:44
  • And NetworkManager doesn't have the best reputation regarding IPv6 unfortunately :( – Sander Steffann Jan 22 '16 at 12:44
  • Older answer about having multiple addresses: askubuntu.com/questions/141397/… – Sander Steffann Jan 22 '16 at 12:47
  • I've got some results on the on-link/off-link option. At first it seems to be caused by that flag, but in the end it was just because I rebooted a bunch of times. Traffic takes random routes. – Halfgaar Jan 22 '16 at 13:04
2

Apparently, DNSMasq not setting on-link is a bug that is fixed in 2.63, just too new for Debian 7. Need to upgrade to Debian 8 anyway, so doing that today.

Edit, upgrade complete. The DNSmasq config line was changed to:

dhcp-range=::,ra-only,constructor:eth1,infinite

Now the route for the local subnet is added.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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