From 39cbe772a67aece69dc30f8f394bba2eea9ca762 Mon Sep 17 00:00:00 2001 From: Thomas Haller Date: Fri, 3 Jan 2014 17:03:35 +0100 Subject: [PATCH] core/rdisc: add autoconf addresses as /64 (instead of /128) This feature needs support from the kernel and libnl. If there is no system support, NM acts as before, adding the autoconf address as /128. It does so, to prevent the kernel from adding a route for this prefix. With system support, we add the address as /64 and set the flag IFA_F_NOPREFIXROUTE. https://bugzilla.redhat.com/show_bug.cgi?id=1044590 https://bugzilla.redhat.com/show_bug.cgi?id=1045118 Signed-off-by: Thomas Haller --- src/devices/nm-device.c | 28 +++++++++++++++++++++++++++- 1 file changed, 27 insertions(+), 1 deletion(-) diff --git a/src/devices/nm-device.c b/src/devices/nm-device.c index 90ffff4b32..c6581b4b61 100644 --- a/src/devices/nm-device.c +++ b/src/devices/nm-device.c @@ -36,6 +36,7 @@ #include #include #include +#include #include "libgsystem.h" #include "nm-glib-compat.h" @@ -74,6 +75,11 @@ #include "nm-device-bond.h" #include "nm-device-team.h" +/* workaround for older libnl version, that does not define this flag. */ +#ifndef IFA_F_NOPREFIXROUTE +#define IFA_F_NOPREFIXROUTE 0x200 +#endif + static void impl_device_disconnect (NMDevice *device, DBusGMethodInvocation *context); #include "nm-device-glue.h" @@ -3313,6 +3319,25 @@ rdisc_config_changed (NMRDisc *rdisc, NMRDiscConfigMap changed, NMDevice *device NMConnection *connection; int i; NMDeviceStateReason reason; + static int system_support = -1; + guint ifa_flags; + + if (system_support == -1) { + /* + * Check, if both libnl and the kernel are recent enough, + * to help user space handling RA. If it's not supported, + * we must add autoconf addresses as /128. + * The reason for /128 is to prevent the kernel from adding + * a prefix route for this address. + **/ + system_support = nm_platform_check_support_libnl_extended_ifa_flags () && + nm_platform_check_support_kernel_extended_ifa_flags (); + } + + /* without system_support, this flag will be ignored. + * Still, we set it (why not?). + **/ + ifa_flags = IFA_F_NOPREFIXROUTE; g_return_if_fail (priv->act_request); connection = nm_device_get_connection (device); @@ -3346,11 +3371,12 @@ rdisc_config_changed (NMRDisc *rdisc, NMRDiscConfigMap changed, NMDevice *device memset (&address, 0, sizeof (address)); address.address = discovered_address->address; - address.plen = 128; + address.plen = system_support ? 64 : 128; address.timestamp = discovered_address->timestamp; address.lifetime = discovered_address->lifetime; address.preferred = discovered_address->preferred; address.source = NM_PLATFORM_SOURCE_RDISC; + address.flags = ifa_flags; nm_ip6_config_add_address (priv->ac_ip6_config, &address); }