From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mail-pl1-f179.google.com (mail-pl1-f179.google.com [209.85.214.179]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 5C3183FD957 for ; Mon, 20 Jul 2026 16:06:57 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.214.179 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1784563619; cv=none; b=MQOzDjnzbQgl16TwqoqdU5q2qNHFnKfIh4WdT6MT3VwAEGdwY6ao87F9Mj8/1oneM4mdZkl+uEH6sGlfedARb4nwk/ABbjkjyxbNsu1xCNZzIZWERcrNcbRq3PCat++b7+REeiabqivtnrdpp/eNW2NhIMOFOIvwRywVJDPD3rI= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1784563619; c=relaxed/simple; bh=uBKOtoSytIa87hb6P4JZ8OQ+rSgfkcaH5ESrlGek8bc=; h=From:To:Cc:Subject:Date:Message-ID:MIME-Version; b=GRTMU60AfnAcM9EPOON8kYKbleSXzYvfeQxHXxpRRewKoa3KZwpxU+fjvzVqfVMmcYZ4M1Hm1alqLHeghiel3Vq8ftsYrpbL2hbIIYhtXN5QUQm7An30/Ued1smZidU3KjuH0kq1x8PQQFI3hVkTvIPcz6QVmloyCrn6YZI5n9c= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com; spf=pass smtp.mailfrom=gmail.com; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b=N5ROvZjv; arc=none smtp.client-ip=209.85.214.179 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=gmail.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="N5ROvZjv" Received: by mail-pl1-f179.google.com with SMTP id d9443c01a7336-2cca0c5799eso79671565ad.0 for ; Mon, 20 Jul 2026 09:06:57 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20251104; t=1784563617; x=1785168417; darn=vger.kernel.org; h=content-transfer-encoding:mime-version:message-id:date:subject:cc :to:from:from:to:cc:subject:date:message-id:reply-to:content-type; bh=o1b/iXtthE0NdNXxVcrsPqsvYfRN7KhJFOgx8+/tTAY=; b=N5ROvZjvLUG+mxv4q9w/WkYq5UYoiKm6vAD3xeToGIyIAinjJHV+B2shXH/E5hNB7b aKTSdbd8b7AiJQD6yTnAsyUY3LXoiNSvYMw1Gqe9wTrn6sPbjVixth1OXYToAQqiUXmG rCjQ7+TxuekQf+og+JGB60xYqPATzwev8efupdwxv1oC2RKeg/NdtpiXOkhoHdeeSV9s TyNf/X/JthoZgjjQ5w9ZnmNlCfkEyx+PzIPN/ikDUnZ6rncXvPZ8wkPUBaycyroi2ZXl M6VMlrymOMbKGhG8lmbHl5bTnOOfqg71VrRNWAiOPlIih1WyiCSHY6LD4knppw+lEbgK odtA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20251104; t=1784563617; x=1785168417; h=content-transfer-encoding:mime-version:message-id:date:subject:cc :to:from:x-gm-gg:x-gm-message-state:from:to:cc:subject:date :message-id:reply-to:content-type; bh=o1b/iXtthE0NdNXxVcrsPqsvYfRN7KhJFOgx8+/tTAY=; b=DGIb2+0c3tURfWM8IqkswBCPDYn1r6NPRjP231ZyIiIORJsC+U5jzTxPURUNR+DYgp AAYGIU0NbzXHurx4w2CO84rYsuyzX46qXSxx814p4JzOBT1hJG5eb5zGqrOQF0joFFIN MQ5gpfZ146ZqxS7+V3g5BIZh+bLLs2i0dyI4HIdBJNs7XYMhexRx9kAiK/q7Pm46NGud 0bF2W/ZYSrQVw2QamNFN6SkxTyYURcA16pqZvvQvPAthWwDWJrkTOUTYsYL8ErHDwycv f1BVsbMxqdYvqIJC/KRvX5auHquW+AJEZg+MkngXWu9BxPsJUHhVXJvz8OTrVG5nR1DG DH4w== X-Forwarded-Encrypted: i=1; AHgh+RrTUUx8seQ3m8mhqOXWnSv3CIQ3nOe14+sXquqRRBlt7VxggsOYesh5XhkBVbPLMtoBi5ZC2ac4Z6WRdAc=@vger.kernel.org X-Gm-Message-State: AOJu0YyBpV/N90z65Gn+G2BSFNmklaQxxaw2IZ2SE1GuEVcNcM3oXhsu 26Kq6k9n5FCbxYz6o/yOHVBMfkPQtB15eAczmruMPqrDgoH6vfNdLb3g X-Gm-Gg: AR+sD1230bBPYTjrv0N5tr1srjPltf0TyYKQtUyW8AnZtr0x3zmurTjhQTPCiVXZ95e EEI4UC2udHUUJnn1M0FvggWsqFK2Y9jQeRjGibub8bQzy4pfEabvJ8xjSICqwMkRYJnj9lZ5Ifh xBMXv/srMOU+EcBS4cYHYTHbZ9gm6CviKT/TeQlegoSF3YwX2EIkvnjjVGK2ckOuk1z2yMkNy01 UPdOfjA/JHLQXE8WPSUyodAU6feGwfw2RkQ0Six1HoOe2mSNuo0ZZ4rILEJRZTZUcCJeVepmkyL 9bh2kZMZI7a/Xp2wwhs8cV+UQ/x1PtUIhjfx4HRGBS0ZrzBWogVuQBwKIe5nfmAnvDrPJwP/alq T58grQJ5zDgMPTGvONwHr7YE5HkuStZTL3UcCVOyOb1JWzff2iFk5uyLx5h95zETzoEGWRwUNXB oimUPamHfxoqLD/VrJ0oo/tJZApz9vDWI1yzWcSA== X-Received: by 2002:a17:902:ebcb:b0:2c9:b48c:fdde with SMTP id d9443c01a7336-2cf3496cb62mr160713345ad.26.1784563616336; Mon, 20 Jul 2026 09:06:56 -0700 (PDT) Received: from JRT-PC.. (bb116-15-8-251.singnet.com.sg. [116.15.8.251]) by smtp.gmail.com with ESMTPSA id d9443c01a7336-2cf344b16d4sm59389985ad.20.2026.07.20.09.06.52 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 20 Jul 2026 09:06:55 -0700 (PDT) From: James Raphael Tiovalen To: Andrew Lunn , "David S. Miller" , Eric Dumazet , Jakub Kicinski , Paolo Abeni , netdev@vger.kernel.org Cc: James Raphael Tiovalen , stable@vger.kernel.org, Kees Cook , Nikolay Aleksandrov , Ido Schimmel , linux-kernel@vger.kernel.org Subject: [PATCH net] vxlan: mdb: Fix source list corruption on a failed replace Date: Tue, 21 Jul 2026 00:04:24 +0800 Message-ID: <20260720160428.249356-1-jamestiotio@gmail.com> X-Mailer: git-send-email 2.43.0 Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit When replacing the source list of an MDB remote entry, all existing sources are first marked for deletion and vxlan_mdb_remote_srcs_add() is then called to add the new source list. Sources present in the new list have their deletion mark cleared, and any sources left marked afterwards are removed. If vxlan_mdb_remote_srcs_add() fails partway through, its error path deletes all entries on the remote's source list. That rollback is only correct for its other caller, vxlan_mdb_remote_add(), where the remote was just allocated and the list contains solely entries added during the call. On the replace path the list also holds pre-existing sources, so a failed replace tears them down together with their (S, G) forwarding entries instead of leaving the entry unchanged. This is reachable from an existing (*, G) remote. An EXCLUDE filter that loses sources starts forwarding traffic that should be blocked, while an INCLUDE filter that loses sources drops traffic that should be forwarded. Mark entries created during the current pass with a new VXLAN_SGRP_F_NEW flag. On failure, delete only those entries and clear the deletion mark on the pre-existing ones, so a failed replace leaves the source list untouched. Retain the flag until the whole operation succeeds and then clear it. Also stop vxlan_mdb_remote_src_add() from deleting a pre-existing entry it only looked up when adding that entry's forwarding entry fails. Fixes: a3a48de5eade ("vxlan: mdb: Add MDB control path support") Cc: stable@vger.kernel.org Signed-off-by: James Raphael Tiovalen --- drivers/net/vxlan/vxlan_mdb.c | 30 ++++++++++++++++++------------ 1 file changed, 18 insertions(+), 12 deletions(-) diff --git a/drivers/net/vxlan/vxlan_mdb.c b/drivers/net/vxlan/vxlan_mdb.c index 055a4969f593..af7a0d7f95a5 100644 --- a/drivers/net/vxlan/vxlan_mdb.c +++ b/drivers/net/vxlan/vxlan_mdb.c @@ -42,6 +42,7 @@ struct vxlan_mdb_remote { }; #define VXLAN_SGRP_F_DELETE BIT(0) +#define VXLAN_SGRP_F_NEW BIT(1) struct vxlan_mdb_src_entry { struct hlist_node node; @@ -844,6 +845,7 @@ vxlan_mdb_remote_src_add(const struct vxlan_mdb_config *cfg, ent = vxlan_mdb_remote_src_entry_add(remote, &src->addr); if (!ent) return -ENOMEM; + ent->flags |= VXLAN_SGRP_F_NEW; } else if (!(cfg->nlflags & NLM_F_REPLACE)) { NL_SET_ERR_MSG_MOD(extack, "Source entry already exists"); return -EEXIST; @@ -853,15 +855,16 @@ vxlan_mdb_remote_src_add(const struct vxlan_mdb_config *cfg, if (err) goto err_src_del; - /* Clear flags in case source entry was marked for deletion as part of - * replace flow. + /* Clear the deletion mark so the entry survives the replace sweep. + * The new mark is retained until the whole operation succeeds. */ - ent->flags = 0; + ent->flags &= ~VXLAN_SGRP_F_DELETE; return 0; err_src_del: - vxlan_mdb_remote_src_entry_del(ent); + if (ent->flags & VXLAN_SGRP_F_NEW) + vxlan_mdb_remote_src_entry_del(ent); return err; } @@ -889,11 +892,19 @@ static int vxlan_mdb_remote_srcs_add(const struct vxlan_mdb_config *cfg, goto err_src_del; } + hlist_for_each_entry(ent, &remote->src_list, node) + ent->flags &= ~VXLAN_SGRP_F_NEW; + return 0; err_src_del: - hlist_for_each_entry_safe(ent, tmp, &remote->src_list, node) - vxlan_mdb_remote_src_del(cfg->vxlan, &cfg->group, remote, ent); + hlist_for_each_entry_safe(ent, tmp, &remote->src_list, node) { + if (ent->flags & VXLAN_SGRP_F_NEW) + vxlan_mdb_remote_src_del(cfg->vxlan, &cfg->group, remote, + ent); + else + ent->flags &= ~VXLAN_SGRP_F_DELETE; + } return err; } @@ -1069,7 +1080,7 @@ vxlan_mdb_remote_srcs_replace(const struct vxlan_mdb_config *cfg, err = vxlan_mdb_remote_srcs_add(cfg, remote, extack); if (err) - goto err_clear_delete; + return err; hlist_for_each_entry_safe(ent, tmp, &remote->src_list, node) { if (ent->flags & VXLAN_SGRP_F_DELETE) @@ -1078,11 +1089,6 @@ vxlan_mdb_remote_srcs_replace(const struct vxlan_mdb_config *cfg, } return 0; - -err_clear_delete: - hlist_for_each_entry(ent, &remote->src_list, node) - ent->flags &= ~VXLAN_SGRP_F_DELETE; - return err; } static int vxlan_mdb_remote_replace(const struct vxlan_mdb_config *cfg, -- 2.43.0