From patchwork Fri Jan 15 12:27:32 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Greg KH X-Patchwork-Id: 364650 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-18.8 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, HEADER_FROM_DIFFERENT_DOMAINS, INCLUDES_CR_TRAILER, INCLUDES_PATCH, MAILING_LIST_MULTI, SPF_HELO_NONE, SPF_PASS, URIBL_BLOCKED, USER_AGENT_GIT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 034EDC433E0 for ; Fri, 15 Jan 2021 12:34:14 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id AC96522473 for ; Fri, 15 Jan 2021 12:34:13 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1733275AbhAOMdz (ORCPT ); Fri, 15 Jan 2021 07:33:55 -0500 Received: from mail.kernel.org ([198.145.29.99]:39960 "EHLO mail.kernel.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1733274AbhAOMdy (ORCPT ); Fri, 15 Jan 2021 07:33:54 -0500 Received: by mail.kernel.org (Postfix) with ESMTPSA id EF08D235F8; Fri, 15 Jan 2021 12:33:38 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=linuxfoundation.org; s=korg; t=1610714019; bh=kaQy7ys6rWfXfo9e5oLIgJe9emh7z0yyBBYl+dFUjME=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=XIASEfc/JU4DEZqz0W7mu4u3CaWDZmAkq/H6gprAbz1OAoMw4yVjjq6SwbHCuksOe KPdtyQJOM+qwhLS1PTlip+qb0jTRm3PDu2hR3pVLiq6qPtbQcRfarWCI8rBKabX4Lo OChOQjnoH5Ywib0Lu7CN1Jse+gcxD8ivjfbZ4EKo= From: Greg Kroah-Hartman To: linux-kernel@vger.kernel.org Cc: Greg Kroah-Hartman , stable@vger.kernel.org, Sean Tranchetti , David Ahern , Jakub Kicinski Subject: [PATCH 5.4 10/62] net: ipv6: fib: flush exceptions when purging route Date: Fri, 15 Jan 2021 13:27:32 +0100 Message-Id: <20210115121958.899390981@linuxfoundation.org> X-Mailer: git-send-email 2.30.0 In-Reply-To: <20210115121958.391610178@linuxfoundation.org> References: <20210115121958.391610178@linuxfoundation.org> User-Agent: quilt/0.66 MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: stable@vger.kernel.org From: Sean Tranchetti [ Upstream commit d8f5c29653c3f6995e8979be5623d263e92f6b86 ] Route removal is handled by two code paths. The main removal path is via fib6_del_route() which will handle purging any PMTU exceptions from the cache, removing all per-cpu copies of the DST entry used by the route, and releasing the fib6_info struct. The second removal location is during fib6_add_rt2node() during a route replacement operation. This path also calls fib6_purge_rt() to handle cleaning up the per-cpu copies of the DST entries and releasing the fib6_info associated with the older route, but it does not flush any PMTU exceptions that the older route had. Since the older route is removed from the tree during the replacement, we lose any way of accessing it again. As these lingering DSTs and the fib6_info struct are holding references to the underlying netdevice struct as well, unregistering that device from the kernel can never complete. Fixes: 2b760fcf5cfb3 ("ipv6: hook up exception table to store dst cache") Signed-off-by: Sean Tranchetti Reviewed-by: David Ahern Link: https://lore.kernel.org/r/1609892546-11389-1-git-send-email-stranche@quicinc.com Signed-off-by: Jakub Kicinski Signed-off-by: Greg Kroah-Hartman --- net/ipv6/ip6_fib.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) --- a/net/ipv6/ip6_fib.c +++ b/net/ipv6/ip6_fib.c @@ -973,6 +973,8 @@ static void fib6_purge_rt(struct fib6_in { struct fib6_table *table = rt->fib6_table; + /* Flush all cached dst in exception table */ + rt6_flush_exceptions(rt); fib6_drop_pcpu_from(rt, table); if (rt->nh && !list_empty(&rt->nh_list)) @@ -1839,9 +1841,6 @@ static void fib6_del_route(struct fib6_t net->ipv6.rt6_stats->fib_rt_entries--; net->ipv6.rt6_stats->fib_discarded_routes++; - /* Flush all cached dst in exception table */ - rt6_flush_exceptions(rt); - /* Reset round-robin state, if necessary */ if (rcu_access_pointer(fn->rr_ptr) == rt) fn->rr_ptr = NULL;