Patch Detail
get:
Show a patch.
patch:
Update a patch.
put:
Update a patch.
GET /api/1.1/patches/2228002/?format=api
{ "id": 2228002, "url": "http://patchwork.ozlabs.org/api/1.1/patches/2228002/?format=api", "web_url": "http://patchwork.ozlabs.org/project/netfilter-devel/patch/20260424190513.32823-12-pablo@netfilter.org/", "project": { "id": 26, "url": "http://patchwork.ozlabs.org/api/1.1/projects/26/?format=api", "name": "Netfilter Development", "link_name": "netfilter-devel", "list_id": "netfilter-devel.vger.kernel.org", "list_email": "netfilter-devel@vger.kernel.org", "web_url": null, "scm_url": null, "webscm_url": null }, "msgid": "<20260424190513.32823-12-pablo@netfilter.org>", "date": "2026-04-24T19:05:13", "name": "[net,11/11] ipvs: fix the spin_lock usage for RT build", "commit_ref": null, "pull_url": null, "state": "new", "archived": false, "hash": "8661203b5be6cafbd306144a67533b7bfc216245", "submitter": { "id": 1315, "url": "http://patchwork.ozlabs.org/api/1.1/people/1315/?format=api", "name": "Pablo Neira Ayuso", "email": "pablo@netfilter.org" }, "delegate": null, "mbox": "http://patchwork.ozlabs.org/project/netfilter-devel/patch/20260424190513.32823-12-pablo@netfilter.org/mbox/", "series": [ { "id": 501399, "url": "http://patchwork.ozlabs.org/api/1.1/series/501399/?format=api", "web_url": "http://patchwork.ozlabs.org/project/netfilter-devel/list/?series=501399", "date": "2026-04-24T19:05:02", "name": "[net,01/11] netfilter: arp_tables: fix IEEE1394 ARP payload parsing", "version": 1, "mbox": "http://patchwork.ozlabs.org/series/501399/mbox/" } ], "comments": "http://patchwork.ozlabs.org/api/patches/2228002/comments/", "check": "pending", "checks": "http://patchwork.ozlabs.org/api/patches/2228002/checks/", "tags": {}, "headers": { "Return-Path": "\n <netfilter-devel+bounces-12191-incoming=patchwork.ozlabs.org@vger.kernel.org>", "X-Original-To": [ "incoming@patchwork.ozlabs.org", "netfilter-devel@vger.kernel.org" ], "Delivered-To": "patchwork-incoming@legolas.ozlabs.org", "Authentication-Results": [ "legolas.ozlabs.org;\n\tdkim=pass (2048-bit key;\n unprotected) header.d=netfilter.org header.i=@netfilter.org\n header.a=rsa-sha256 header.s=2025 header.b=XXi4FfPd;\n\tdkim-atps=neutral", "legolas.ozlabs.org;\n spf=pass (sender SPF authorized) smtp.mailfrom=vger.kernel.org\n (client-ip=2600:3c0a:e001:db::12fc:5321; helo=sea.lore.kernel.org;\n envelope-from=netfilter-devel+bounces-12191-incoming=patchwork.ozlabs.org@vger.kernel.org;\n receiver=patchwork.ozlabs.org)", "smtp.subspace.kernel.org;\n\tdkim=pass (2048-bit key) header.d=netfilter.org header.i=@netfilter.org\n header.b=\"XXi4FfPd\"", "smtp.subspace.kernel.org;\n arc=none smtp.client-ip=217.70.190.124", "smtp.subspace.kernel.org;\n dmarc=none (p=none dis=none) header.from=netfilter.org", "smtp.subspace.kernel.org;\n spf=pass smtp.mailfrom=netfilter.org" ], "Received": [ "from sea.lore.kernel.org (sea.lore.kernel.org\n [IPv6:2600:3c0a:e001:db::12fc:5321])\n\t(using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)\n\t key-exchange x25519)\n\t(No client certificate requested)\n\tby legolas.ozlabs.org (Postfix) with ESMTPS id 4g2Mx1078sz1y2d\n\tfor <incoming@patchwork.ozlabs.org>; Sat, 25 Apr 2026 05:10:29 +1000 (AEST)", "from smtp.subspace.kernel.org (conduit.subspace.kernel.org\n [100.90.174.1])\n\tby sea.lore.kernel.org (Postfix) with ESMTP id 451F93058E01\n\tfor <incoming@patchwork.ozlabs.org>; Fri, 24 Apr 2026 19:06:07 +0000 (UTC)", "from localhost.localdomain (localhost.localdomain [127.0.0.1])\n\tby smtp.subspace.kernel.org (Postfix) with ESMTP id 686233FA5D9;\n\tFri, 24 Apr 2026 19:06:03 +0000 (UTC)", "from mail.netfilter.org (mail.netfilter.org [217.70.190.124])\n\t(using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits))\n\t(No client certificate requested)\n\tby smtp.subspace.kernel.org (Postfix) with ESMTPS id 6690F35AC19;\n\tFri, 24 Apr 2026 19:06:01 +0000 (UTC)", "from localhost.localdomain (mail-agni [217.70.190.124])\n\tby mail.netfilter.org (Postfix) with ESMTPSA id 3461E60284;\n\tFri, 24 Apr 2026 21:05:59 +0200 (CEST)" ], "ARC-Seal": "i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116;\n\tt=1777057563; cv=none;\n b=fSBiJSSbO+nJ1bydibJp7qcdjj8tglPUTdz67CIomMuTmD+wyvjHtml7D5AfJ9/snbOzjL3iSLQ4M0G46d4Nt+6C9t6OYhKoehwswUWF58043gAEBgAPYjQohPvHSk+wF2hiRYrYntN+xQh32NrRnilICVETu67WAlTBAhqDHdM=", "ARC-Message-Signature": "i=1; a=rsa-sha256; d=subspace.kernel.org;\n\ts=arc-20240116; t=1777057563; c=relaxed/simple;\n\tbh=CvKUyzG4xOLNVTgoxxq7GPtF3UVmlvmYN65uLGVH9TA=;\n\th=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References:\n\t MIME-Version;\n b=G5xV0CEebKhSdK6GRzAMYwkTkTj1inwXlVPbIvO9uPqS1NWFlZ6pHvO13OTVercqKzEJl86AJUjMSAX0hq7PkuHI8sfvEafIykGAJ7q1611mLEfl1/oyiiEYPeHfidsL9fOVlAQlVyZA1n9zzywcjp6RsTWVAsG3ZaUpDmWhXPA=", "ARC-Authentication-Results": "i=1; smtp.subspace.kernel.org;\n dmarc=none (p=none dis=none) header.from=netfilter.org;\n spf=pass smtp.mailfrom=netfilter.org;\n dkim=pass (2048-bit key) header.d=netfilter.org header.i=@netfilter.org\n header.b=XXi4FfPd; arc=none smtp.client-ip=217.70.190.124", "DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/relaxed; d=netfilter.org;\n\ts=2025; t=1777057559;\n\tbh=rbtKElw/LZcbhhYls6Gb7oYe+cPZR1+xaNk5gqRvTs8=;\n\th=From:To:Cc:Subject:Date:In-Reply-To:References:From;\n\tb=XXi4FfPdxjUtuZUX9m2weu3Loqt62MpLtWeJQWh2ewAODOHvkXj9zTAPpW1468bBN\n\t +xrV04CYlxMI6RjjIELpQtAoIzpmZ9w8fh/RSvd3DydubCiMuP4ac59P3lG4xnvMOQ\n\t nFQe43m+UmRTNzwlodqfQGV8lTcigokHuvS76TTegmE7pbtYYfUNc72wqCPNhidTsv\n\t vVrOmfk8Z/kcuW9yzDbV9LFfRNboM2r39u2A14OTwtDqjSyLG2oX8I3dk27ikg/ifv\n\t IwXP7diQ8ImAoo3Ik0QXxxDPbyKvQh533uZUqzH8ocP7uzP0sELnvOkNyWb/I0xRUN\n\t PiUlMRE+wYqIA==", "From": "Pablo Neira Ayuso <pablo@netfilter.org>", "To": "netfilter-devel@vger.kernel.org", "Cc": "davem@davemloft.net,\n\tnetdev@vger.kernel.org,\n\tkuba@kernel.org,\n\tpabeni@redhat.com,\n\tedumazet@google.com,\n\tfw@strlen.de,\n\thorms@kernel.org", "Subject": "[PATCH net 11/11] ipvs: fix the spin_lock usage for RT build", "Date": "Fri, 24 Apr 2026 21:05:13 +0200", "Message-ID": "<20260424190513.32823-12-pablo@netfilter.org>", "X-Mailer": "git-send-email 2.47.3", "In-Reply-To": "<20260424190513.32823-1-pablo@netfilter.org>", "References": "<20260424190513.32823-1-pablo@netfilter.org>", "Precedence": "bulk", "X-Mailing-List": "netfilter-devel@vger.kernel.org", "List-Id": "<netfilter-devel.vger.kernel.org>", "List-Subscribe": "<mailto:netfilter-devel+subscribe@vger.kernel.org>", "List-Unsubscribe": "<mailto:netfilter-devel+unsubscribe@vger.kernel.org>", "MIME-Version": "1.0", "Content-Transfer-Encoding": "8bit" }, "content": "From: Julian Anastasov <ja@ssi.bg>\n\nsyzbot reports for sleeping function called from invalid context [1].\nThe recently added code for resizable hash tables uses\nhlist_bl bit locks in combination with spin_lock for\nthe connection fields (cp->lock).\n\nFix the following problems:\n\n* avoid using spin_lock(&cp->lock) under locked bit lock\nbecause it sleeps on PREEMPT_RT\n\n* as the recent changes call ip_vs_conn_hash() only for newly\nallocated connection, the spin_lock can be removed there because\nthe connection is still not linked to table and does not need\ncp->lock protection.\n\n* the lock can be removed also from ip_vs_conn_unlink() where we\nare the last connection user.\n\n* the last place that is fixed is ip_vs_conn_fill_cport()\nwhere now the cp->lock is locked before the other locks to\nensure other packets do not modify the cp->flags in non-atomic\nway. Here we make sure cport and flags are changed only once\nif two or more packets race to fill the cport. Also, we fill\ncport early, so that if we race with resizing there will be\nvalid cport key for the hashing. Add a warning if too many\nhash table changes occur for our RCU read-side critical\nsection which is error condition but minor because the\nconnection still can expire gracefully. Problems reported\nby Sashiko.\n\n[1]:\nBUG: sleeping function called from invalid context at kernel/locking/spinlock_rt.c:48\nin_atomic(): 1, irqs_disabled(): 0, non_block: 0, pid: 16, name: ktimers/0\npreempt_count: 2, expected: 0\nRCU nest depth: 3, expected: 3\n8 locks held by ktimers/0/16:\n #0: ffffffff8de5f260 (local_bh){.+.+}-{1:3}, at: __local_bh_disable_ip+0x3c/0x420 kernel/softirq.c:163\n #1: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: __local_bh_disable_ip+0x3c/0x420 kernel/softirq.c:163\n #2: ffff8880b8826360 (&base->expiry_lock){+...}-{3:3}, at: spin_lock include/linux/spinlock_rt.h:45 [inline]\n #2: ffff8880b8826360 (&base->expiry_lock){+...}-{3:3}, at: timer_base_lock_expiry kernel/time/timer.c:1502 [inline]\n #2: ffff8880b8826360 (&base->expiry_lock){+...}-{3:3}, at: __run_timer_base+0x120/0x9f0 kernel/time/timer.c:2384\n #3: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: rcu_lock_acquire include/linux/rcupdate.h:300 [inline]\n #3: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: rcu_read_lock include/linux/rcupdate.h:838 [inline]\n #3: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: __rt_spin_lock kernel/locking/spinlock_rt.c:50 [inline]\n #3: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: rt_spin_lock+0x1e0/0x400 kernel/locking/spinlock_rt.c:57\n #4: ffffc90000157a80 ((&cp->timer)){+...}-{0:0}, at: call_timer_fn+0xd4/0x5e0 kernel/time/timer.c:1745\n #5: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: rcu_lock_acquire include/linux/rcupdate.h:300 [inline]\n #5: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: rcu_read_lock include/linux/rcupdate.h:838 [inline]\n #5: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: ip_vs_conn_unlink net/netfilter/ipvs/ip_vs_conn.c:315 [inline]\n #5: ffffffff8dfc80c0 (rcu_read_lock){....}-{1:3}, at: ip_vs_conn_expire+0x257/0x2390 net/netfilter/ipvs/ip_vs_conn.c:1260\n #6: ffffffff8de5f260 (local_bh){.+.+}-{1:3}, at: __local_bh_disable_ip+0x3c/0x420 kernel/softirq.c:163\n #7: ffff888068d4c3f0 (&cp->lock#2){+...}-{3:3}, at: spin_lock include/linux/spinlock_rt.h:45 [inline]\n #7: ffff888068d4c3f0 (&cp->lock#2){+...}-{3:3}, at: ip_vs_conn_unlink net/netfilter/ipvs/ip_vs_conn.c:324 [inline]\n #7: ffff888068d4c3f0 (&cp->lock#2){+...}-{3:3}, at: ip_vs_conn_expire+0xd4a/0x2390 net/netfilter/ipvs/ip_vs_conn.c:1260\nPreemption disabled at:\n[<ffffffff898a6358>] bit_spin_lock include/linux/bit_spinlock.h:38 [inline]\n[<ffffffff898a6358>] hlist_bl_lock+0x18/0x110 include/linux/list_bl.h:149\nCPU: 0 UID: 0 PID: 16 Comm: ktimers/0 Tainted: G W L syzkaller #0 PREEMPT_{RT,(full)}\nTainted: [W]=WARN, [L]=SOFTLOCKUP\nHardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 03/18/2026\nCall Trace:\n <TASK>\n dump_stack_lvl+0xe8/0x150 lib/dump_stack.c:120\n __might_resched+0x329/0x480 kernel/sched/core.c:9162\n __rt_spin_lock kernel/locking/spinlock_rt.c:48 [inline]\n rt_spin_lock+0xc2/0x400 kernel/locking/spinlock_rt.c:57\n spin_lock include/linux/spinlock_rt.h:45 [inline]\n ip_vs_conn_unlink net/netfilter/ipvs/ip_vs_conn.c:324 [inline]\n ip_vs_conn_expire+0xd4a/0x2390 net/netfilter/ipvs/ip_vs_conn.c:1260\n call_timer_fn+0x192/0x5e0 kernel/time/timer.c:1748\n expire_timers kernel/time/timer.c:1799 [inline]\n __run_timers kernel/time/timer.c:2374 [inline]\n __run_timer_base+0x6a3/0x9f0 kernel/time/timer.c:2386\n run_timer_base kernel/time/timer.c:2395 [inline]\n run_timer_softirq+0xb7/0x170 kernel/time/timer.c:2405\n handle_softirqs+0x1de/0x6d0 kernel/softirq.c:622\n __do_softirq kernel/softirq.c:656 [inline]\n run_ktimerd+0x69/0x100 kernel/softirq.c:1151\n smpboot_thread_fn+0x541/0xa50 kernel/smpboot.c:160\n kthread+0x388/0x470 kernel/kthread.c:436\n ret_from_fork+0x514/0xb70 arch/x86/kernel/process.c:158\n ret_from_fork_asm+0x1a/0x30 arch/x86/entry/entry_64.S:245\n </TASK>\n\nReported-by: syzbot+504e778ddaecd36fdd17@syzkaller.appspotmail.com\nLink: https://sashiko.dev/#/patchset/20260415200216.79699-1-ja%40ssi.bg\nLink: https://sashiko.dev/#/patchset/20260420165539.85174-4-ja%40ssi.bg\nLink: https://sashiko.dev/#/patchset/20260422135823.50489-4-ja%40ssi.bg\nFixes: 2fa7cc9c7025 (\"ipvs: switch to per-net connection table\")\nSigned-off-by: Julian Anastasov <ja@ssi.bg>\nSigned-off-by: Pablo Neira Ayuso <pablo@netfilter.org>\n---\n net/netfilter/ipvs/ip_vs_conn.c | 69 +++++++++++++++++----------------\n 1 file changed, 36 insertions(+), 33 deletions(-)", "diff": "diff --git a/net/netfilter/ipvs/ip_vs_conn.c b/net/netfilter/ipvs/ip_vs_conn.c\nindex 84a4921a7865..9e23cda84825 100644\n--- a/net/netfilter/ipvs/ip_vs_conn.c\n+++ b/net/netfilter/ipvs/ip_vs_conn.c\n@@ -267,27 +267,20 @@ static inline int ip_vs_conn_hash(struct ip_vs_conn *cp)\n \t\thash_key2 = hash_key;\n \t\tuse2 = false;\n \t}\n+\n \tconn_tab_lock(t, cp, hash_key, hash_key2, use2, true /* new_hash */,\n \t\t &head, &head2);\n-\tspin_lock(&cp->lock);\n-\n-\tif (!(cp->flags & IP_VS_CONN_F_HASHED)) {\n-\t\tcp->flags |= IP_VS_CONN_F_HASHED;\n-\t\tWRITE_ONCE(cp->hn0.hash_key, hash_key);\n-\t\tWRITE_ONCE(cp->hn1.hash_key, hash_key2);\n-\t\trefcount_inc(&cp->refcnt);\n-\t\thlist_bl_add_head_rcu(&cp->hn0.node, head);\n-\t\tif (use2)\n-\t\t\thlist_bl_add_head_rcu(&cp->hn1.node, head2);\n-\t\tret = 1;\n-\t} else {\n-\t\tpr_err(\"%s(): request for already hashed, called from %pS\\n\",\n-\t\t __func__, __builtin_return_address(0));\n-\t\tret = 0;\n-\t}\n \n-\tspin_unlock(&cp->lock);\n+\tcp->flags |= IP_VS_CONN_F_HASHED;\n+\tWRITE_ONCE(cp->hn0.hash_key, hash_key);\n+\tWRITE_ONCE(cp->hn1.hash_key, hash_key2);\n+\trefcount_inc(&cp->refcnt);\n+\thlist_bl_add_head_rcu(&cp->hn0.node, head);\n+\tif (use2)\n+\t\thlist_bl_add_head_rcu(&cp->hn1.node, head2);\n+\n \tconn_tab_unlock(head, head2);\n+\tret = 1;\n \n \t/* Schedule resizing if load increases */\n \tif (atomic_read(&ipvs->conn_count) > t->u_thresh &&\n@@ -321,7 +314,6 @@ static inline bool ip_vs_conn_unlink(struct ip_vs_conn *cp)\n \n \tconn_tab_lock(t, cp, hash_key, hash_key2, use2, false /* new_hash */,\n \t\t &head, &head2);\n-\tspin_lock(&cp->lock);\n \n \tif (cp->flags & IP_VS_CONN_F_HASHED) {\n \t\t/* Decrease refcnt and unlink conn only if we are last user */\n@@ -334,7 +326,6 @@ static inline bool ip_vs_conn_unlink(struct ip_vs_conn *cp)\n \t\t}\n \t}\n \n-\tspin_unlock(&cp->lock);\n \tconn_tab_unlock(head, head2);\n \n \trcu_read_unlock();\n@@ -637,6 +628,7 @@ void ip_vs_conn_fill_cport(struct ip_vs_conn *cp, __be16 cport)\n \tstruct ip_vs_conn_hnode *hn;\n \tu32 hash_key, hash_key_new;\n \tstruct ip_vs_conn_param p;\n+\tbool by_me = false;\n \tint ntbl;\n \tint dir;\n \n@@ -664,8 +656,11 @@ void ip_vs_conn_fill_cport(struct ip_vs_conn *cp, __be16 cport)\n \t\tt = rcu_dereference(t->new_tbl);\n \t\tntbl++;\n \t\t/* We are lost? */\n-\t\tif (ntbl >= 2)\n+\t\tif (ntbl >= 2) {\n+\t\t\tIP_VS_ERR_RL(\"%s(): Too many ht changes for dir %d\\n\",\n+\t\t\t\t __func__, dir);\n \t\t\treturn;\n+\t\t}\n \t}\n \n \t/* Rehashing during resize? Use the recent table for adds */\n@@ -683,10 +678,13 @@ void ip_vs_conn_fill_cport(struct ip_vs_conn *cp, __be16 cport)\n \tif (head > head2 && t == t2)\n \t\tswap(head, head2);\n \n+\t/* Protect the cp->flags modification */\n+\tspin_lock_bh(&cp->lock);\n+\n \t/* Lock seqcount only for the old bucket, even if we are on new table\n \t * because it affects the del operation, not the adding.\n \t */\n-\tspin_lock_bh(&t->lock[hash_key & t->lock_mask].l);\n+\tspin_lock(&t->lock[hash_key & t->lock_mask].l);\n \tpreempt_disable_nested();\n \twrite_seqcount_begin(&t->seqc[hash_key & t->seqc_mask]);\n \n@@ -704,14 +702,23 @@ void ip_vs_conn_fill_cport(struct ip_vs_conn *cp, __be16 cport)\n \t\thlist_bl_unlock(head);\n \t\twrite_seqcount_end(&t->seqc[hash_key & t->seqc_mask]);\n \t\tpreempt_enable_nested();\n-\t\tspin_unlock_bh(&t->lock[hash_key & t->lock_mask].l);\n+\t\tspin_unlock(&t->lock[hash_key & t->lock_mask].l);\n+\t\tspin_unlock_bh(&cp->lock);\n \t\thash_key = hash_key_new;\n \t\tgoto retry;\n \t}\n \n-\tspin_lock(&cp->lock);\n-\tif ((cp->flags & IP_VS_CONN_F_NO_CPORT) &&\n-\t (cp->flags & IP_VS_CONN_F_HASHED)) {\n+\t/* Fill cport once, even if multiple packets try to do it */\n+\tif (cp->flags & IP_VS_CONN_F_NO_CPORT && (!cp->cport || by_me)) {\n+\t\t/* If we race with resizing make sure cport is set for dir 1 */\n+\t\tif (!cp->cport) {\n+\t\t\tcp->cport = cport;\n+\t\t\tby_me = true;\n+\t\t}\n+\t\tif (!dir) {\n+\t\t\tatomic_dec(&ipvs->no_cport_conns[af_id]);\n+\t\t\tcp->flags &= ~IP_VS_CONN_F_NO_CPORT;\n+\t\t}\n \t\t/* We do not recalc hash_key_r under lock, we assume the\n \t\t * parameters in cp do not change, i.e. cport is\n \t\t * the only possible change.\n@@ -726,21 +733,17 @@ void ip_vs_conn_fill_cport(struct ip_vs_conn *cp, __be16 cport)\n \t\t\thlist_bl_del_rcu(&hn->node);\n \t\t\thlist_bl_add_head_rcu(&hn->node, head_new);\n \t\t}\n-\t\tif (!dir) {\n-\t\t\tatomic_dec(&ipvs->no_cport_conns[af_id]);\n-\t\t\tcp->flags &= ~IP_VS_CONN_F_NO_CPORT;\n-\t\t\tcp->cport = cport;\n-\t\t}\n \t}\n-\tspin_unlock(&cp->lock);\n \n \tif (head != head2)\n \t\thlist_bl_unlock(head2);\n \thlist_bl_unlock(head);\n \twrite_seqcount_end(&t->seqc[hash_key & t->seqc_mask]);\n \tpreempt_enable_nested();\n-\tspin_unlock_bh(&t->lock[hash_key & t->lock_mask].l);\n-\tif (dir--)\n+\tspin_unlock(&t->lock[hash_key & t->lock_mask].l);\n+\n+\tspin_unlock_bh(&cp->lock);\n+\tif (dir-- && by_me)\n \t\tgoto next_dir;\n }\n \n", "prefixes": [ "net", "11/11" ] }