aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/net/ndp.c36
1 files changed, 25 insertions, 11 deletions
diff --git a/src/net/ndp.c b/src/net/ndp.c
index 75e531648..c8e8ebad3 100644
--- a/src/net/ndp.c
+++ b/src/net/ndp.c
@@ -789,29 +789,43 @@ static int ndp_prefix_fetch_ip6 ( struct settings *settings, void *data,
container_of ( ndpset->settings.parent, struct net_device,
settings.settings );
struct ndp_prefix_information_option *prefix = prefset->prefix;
- struct in6_addr ip6;
+ struct in6_addr *ip6 = &prefix->prefix;
+ struct in6_addr slaac;
int prefix_len;
+ int rc;
/* Skip dead prefixes */
if ( ! prefix->valid )
return -ENOENT;
/* Construct IPv6 address via SLAAC, if applicable */
- memcpy ( &ip6, &prefix->prefix, sizeof ( ip6 ) );
if ( prefix->flags & NDP_PREFIX_AUTONOMOUS ) {
- prefix_len = ipv6_eui64 ( &ip6, netdev );
- if ( prefix_len < 0 )
- return prefix_len;
- if ( prefix_len != prefix->prefix_len )
- return -EINVAL;
+ memcpy ( &slaac, ip6, sizeof ( slaac ) );
+ prefix_len = ipv6_eui64 ( &slaac, netdev );
+ if ( prefix_len == prefix->prefix_len ) {
+ /* Correctly configured prefix: use SLAAC address */
+ ip6 = &slaac;
+ } else if ( prefix_len < 0 ) {
+ /* Link layer does not support SLAAC */
+ rc = prefix_len;
+ DBGC ( netdev, "NDP %s does not support SLAAC: %s\n",
+ netdev->name, strerror ( rc ) );
+ } else {
+ /* Prefix length incorrect: assume a badly
+ * configured router and ignore SLAAC address.
+ */
+ DBGC ( netdev, "NDP %s ignoring misconfigured SLAAC "
+ "on prefix %s/%d\n", netdev->name,
+ inet6_ntoa ( ip6 ), prefix->prefix_len );
+ }
}
/* Fill in IPv6 address */
- if ( len > sizeof ( ip6 ) )
- len = sizeof ( ip6 );
- memcpy ( data, &ip6, len );
+ if ( len > sizeof ( *ip6 ) )
+ len = sizeof ( *ip6 );
+ memcpy ( data, ip6, len );
- return sizeof ( ip6 );
+ return sizeof ( *ip6 );
}
/**