diff options
| author | Roy Marples <roy@marples.name> | 2020-03-31 22:33:25 +0100 |
|---|---|---|
| committer | Roy Marples <roy@marples.name> | 2020-03-31 22:33:25 +0100 |
| commit | 67d90035be1ec5286de30b9e50094cae9223b83f (patch) | |
| tree | 5a2adcb16bce8e578e7f247b25aa0e014377dadf /src/ipv6.c | |
| parent | 93df4147ea44a8b6adb439dff48c5647e5ffb9d0 (diff) | |
| download | dhcpcd-67d90035be1ec5286de30b9e50094cae9223b83f.tar.xz | |
ND: If a secondary router adds the same prefix, use it's address
With slaac private, it will generate a new address which would
be wrong.
Diffstat (limited to 'src/ipv6.c')
| -rw-r--r-- | src/ipv6.c | 37 |
1 files changed, 22 insertions, 15 deletions
@@ -1509,17 +1509,26 @@ struct ipv6_addr * ipv6_newaddr(struct interface *ifp, const struct in6_addr *addr, uint8_t prefix_len, unsigned int flags) { - struct ipv6_addr *ia; + struct ipv6_addr *ia, *iaf; char buf[INET6_ADDRSTRLEN]; const char *cbp; bool tempaddr; int addr_flags; +#ifdef IPV6_AF_TEMPORARY + tempaddr = flags & IPV6_AF_TEMPORARY; +#else + tempaddr = false; +#endif + /* If adding a new DHCP / RA derived address, check current flags * from an existing address. */ - ia = ipv6_iffindaddr(ifp, addr, 0); - if (ia != NULL) { - addr_flags = ia->addr_flags; + if (flags & IPV6_AF_AUTOCONF) + iaf = ipv6nd_iffindprefix(ifp, addr, prefix_len); + else + iaf = ipv6_iffindaddr(ifp, addr, 0); + if (iaf != NULL) { + addr_flags = iaf->addr_flags; flags |= IPV6_AF_ADDED; } else addr_flags = IN6_IFF_TENTATIVE; @@ -1540,21 +1549,19 @@ ipv6_newaddr(struct interface *ifp, const struct in6_addr *addr, TAILQ_INIT(&ia->pd_pfxs); #endif -#ifdef IPV6_AF_TEMPORARY - tempaddr = ia->flags & IPV6_AF_TEMPORARY; -#else - tempaddr = false; -#endif - if (prefix_len == 128) goto makepfx; else if (ia->flags & IPV6_AF_AUTOCONF && !tempaddr) { ia->prefix = *addr; - ia->dadcounter = ipv6_makeaddr(&ia->addr, ifp, - &ia->prefix, - ia->prefix_len); - if (ia->dadcounter == -1) - goto err; + if (iaf != NULL) + memcpy(&ia->addr, &iaf->addr, sizeof(ia->addr)); + else { + ia->dadcounter = ipv6_makeaddr(&ia->addr, ifp, + &ia->prefix, + ia->prefix_len); + if (ia->dadcounter == -1) + goto err; + } } else if (ia->flags & IPV6_AF_RAPFX) { ia->prefix = *addr; #ifdef __sun |
