Skip to content

Commit fc882fc

Browse files
idoschdavem330
authored andcommitted
ipv6: Regenerate host route according to node pointer upon interface up
When an interface is brought back up, the kernel tries to restore the host routes tied to its permanent addresses. However, if the host route was removed from the FIB, then we need to reinsert it. This is done by releasing the current dst and allocating a new, so as to not reuse a dst with obsolete values. Since this function is called under RTNL and using the same explanation from the previous patch, we can test if the route is in the FIB by checking its node pointer instead of its reference count. Tested using the following script and Andrey's reproducer mentioned in commit 8048ced ("net: ipv6: regenerate host route if moved to gc list") and linked below: $ ip link set dev lo up $ ip link add dummy1 type dummy $ ip -6 address add cafe::1/64 dev dummy1 $ ip link set dev lo down # cafe::1/128 is removed $ ip link set dev dummy1 up $ ip link set dev lo up The host route is correctly regenerated. Signed-off-by: Ido Schimmel <idosch@mellanox.com> Link: http://lkml.kernel.org/r/CAAeHK+zSe82vc5gCRgr_EoUwiALPnWVdWJBPwJZBpbxYz=kGJw@mail.gmail.com Signed-off-by: Jiri Pirko <jiri@mellanox.com> Signed-off-by: David S. Miller <davem@davemloft.net>
1 parent 9217d8c commit fc882fc

File tree

1 file changed

+2
-2
lines changed

1 file changed

+2
-2
lines changed

net/ipv6/addrconf.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3321,11 +3321,11 @@ static void addrconf_gre_config(struct net_device *dev)
33213321
static int fixup_permanent_addr(struct inet6_dev *idev,
33223322
struct inet6_ifaddr *ifp)
33233323
{
3324-
/* rt6i_ref == 0 means the host route was removed from the
3324+
/* !rt6i_node means the host route was removed from the
33253325
* FIB, for example, if 'lo' device is taken down. In that
33263326
* case regenerate the host route.
33273327
*/
3328-
if (!ifp->rt || !atomic_read(&ifp->rt->rt6i_ref)) {
3328+
if (!ifp->rt || !ifp->rt->rt6i_node) {
33293329
struct rt6_info *rt, *prev;
33303330

33313331
rt = addrconf_dst_alloc(idev, &ifp->addr, false);

0 commit comments

Comments
 (0)