netfilter-devel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH net,v2 0/9] Netfilter/IPVS fixes for net
@ 2026-09-07 17:17 Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 1/9] ipvs: reject invalid states in connection template sync records Pablo Neira Ayuso
                   ` (8 more replies)
  0 siblings, 9 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

v2: Keep back all the patches that Jakub's LLMs are complaining
    about.

-o-

The following patchset contains Netfilter/IPVS fixes for net:
 
1) Reject malformed messages in IPVS sync, from Kyle Zeng.
 
2) Fix possible stale infoleak in IPVS sync, also from Kyle Zeng.
 
3) Out-of-bound read in the SIP conntrack helper, from
   Joas Antonio dos Santos.
 
4) UaF on cttimeout module removal, from Chengfeng Ye.
 
5) Unregister nf_loggers before netns teardown to fix UaF,
   also from Chengfeng Ye.
 
6) Fix race in nfnetlink_log due to concurrent instance destruction,
   from Florian Westphal.
 
7) Remove arp_table 32bit compat interface, this is already off in
    many distributions, from Florian Westphal.
 
8) Set IP6T_F_PROTO flag is e->ipv6.proto is set on to deal with
    insufficient validation of xtables extensions when used from
    legacy ip6tables, from Florian.
 
9) Set on the NLM_F_DUMP_FILTERED flag when all is filtering out
   in ctnetlink, from Ilya Maximets.

Please, pull these changes from:

  git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf.git nf-26-09-07

Thanks.

----------------------------------------------------------------

The following changes since commit 1d2929d0850fff683b8aff051275945e65f082c8:

  net: psp: do not inherit the Rx association on clone (2026-09-01 15:12:24 +0200)

are available in the Git repository at:

  git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf.git nf-26-09-07

for you to fetch changes up to 7a099b347fef536a84068076e2d384f044e5cfc5:

  netfilter: report NLM_F_DUMP_FILTERED when all is filtered out (2026-09-07 18:48:56 +0200)

----------------------------------------------------------------
netfilter pull request 26-09-07

----------------------------------------------------------------
Chengfeng Ye (2):
      netfilter: cttimeout: prevent UAF during module unload
      netfilter: nf_log: unregister loggers before per-net teardown

Florian Westphal (3):
      netfilter: nfnetlink_log: cope with concurrent instance destruction
      netfilter: arp_tables: remove the 32bit compat interface
      netfilter: ip6_tables: set F_PROTO when proto value is nonzero

Ilya Maximets (1):
      netfilter: report NLM_F_DUMP_FILTERED when all is filtered out

Joas Antonio dos Santos (1):
      netfilter: nf_conntrack_sip: fix OOB read in sip_skip_whitespace()

Kyle Zeng (2):
      ipvs: reject invalid states in connection template sync records
      ipvs: fix reversed sequence option serialization

 include/linux/netfilter_arp/arp_tables.h |  19 --
 net/ipv4/netfilter/arp_tables.c          | 472 +------------------------------
 net/ipv6/netfilter/ip6_tables.c          |   5 +
 net/netfilter/Kconfig                    |   2 +-
 net/netfilter/ipvs/ip_vs_sync.c          |  20 +-
 net/netfilter/nf_conntrack_netlink.c     |   2 +
 net/netfilter/nf_conntrack_sip.c         |   2 +-
 net/netfilter/nf_log_syslog.c            |   2 +-
 net/netfilter/nfnetlink_cttimeout.c      |   2 +-
 net/netfilter/nfnetlink_log.c            |  15 +-
 10 files changed, 34 insertions(+), 507 deletions(-)

^ permalink raw reply	[flat|nested] 18+ messages in thread

* [PATCH net 1/9] ipvs: reject invalid states in connection template sync records
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-08 21:00   ` patchwork-bot+netdevbpf
  2026-09-07 17:17 ` [PATCH net 2/9] ipvs: fix reversed sequence option serialization Pablo Neira Ayuso
                   ` (7 subsequent siblings)
  8 siblings, 1 reply; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Kyle Zeng <kylebot@openai.com>

IPVS sync receivers validate protocol states before creating or updating a
connection. For connection templates, however, they only log states outside
the template state range and still store the value in the connection.

A template can be returned by ordinary connection lookup. TCP and SCTP then
use the invalid state as an index into their transition tables.

Reject invalid template states in both sync protocol versions before
looking up or modifying a connection. The version 1 path handles both
IPv4 and IPv6 records.

Fixes: 275411430f89 ("ipvs: add assured state for conn templates")
Cc: stable@vger.kernel.org
Assisted-by: Codex:gpt-5.6-sol
Signed-off-by: Kyle Zeng <kylebot@openai.com>
Acked-by: Julian Anastasov <ja@ssi.bg>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/netfilter/ipvs/ip_vs_sync.c | 16 ++++++++--------
 1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/net/netfilter/ipvs/ip_vs_sync.c b/net/netfilter/ipvs/ip_vs_sync.c
index ea5fdd4f4ce7..1deb063cd72c 100644
--- a/net/netfilter/ipvs/ip_vs_sync.c
+++ b/net/netfilter/ipvs/ip_vs_sync.c
@@ -999,10 +999,10 @@ static void ip_vs_process_message_v0(struct netns_ipvs *ipvs, const char *buffer
 					pp->name, state);
 				continue;
 			}
-		} else {
-			if (state >= IP_VS_CTPL_S_LAST)
-				IP_VS_DBG(7, "BACKUP v0, Invalid tpl state %u\n",
-					  state);
+		} else if (state >= IP_VS_CTPL_S_LAST) {
+			IP_VS_DBG(7, "BACKUP v0, Invalid tpl state %u\n",
+				  state);
+			continue;
 		}
 
 		ip_vs_conn_fill_param(ipvs, AF_INET, s->protocol,
@@ -1159,10 +1159,10 @@ static inline int ip_vs_proc_sync_conn(struct netns_ipvs *ipvs, __u8 *p, __u8 *m
 			retc = 40;
 			goto out;
 		}
-	} else {
-		if (state >= IP_VS_CTPL_S_LAST)
-			IP_VS_DBG(7, "BACKUP, Invalid tpl state %u\n",
-				  state);
+	} else if (state >= IP_VS_CTPL_S_LAST) {
+		IP_VS_DBG(7, "BACKUP, Invalid tpl state %u\n", state);
+		retc = 40;
+		goto out;
 	}
 	if (ip_vs_conn_fill_param_sync(ipvs, af, s, &param, pe_data,
 				       pe_data_len, pe_name, pe_name_len)) {
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 2/9] ipvs: fix reversed sequence option serialization
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 1/9] ipvs: reject invalid states in connection template sync records Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 3/9] netfilter: nf_conntrack_sip: fix OOB read in sip_skip_whitespace() Pablo Neira Ayuso
                   ` (6 subsequent siblings)
  8 siblings, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Kyle Zeng <kylebot@openai.com>

hton_seq() expects the host-order source first and the unaligned
network-order destination second. The version 1 sync sender passes these
arguments in reverse for both sequence blocks. This leaves 24 bytes of the
kmalloc-backed message unwritten. It may disclose stale heap data and
replace the live connection sequence state with values read from the
buffer.

Pass the connection sequence state as the source and the message payload as
the destination for both blocks.

Fixes: 986a07579533 ("IPVS: Backup, Change sending to Version 1 format")
Assisted-by: Codex:gpt-5.6-sol
Signed-off-by: Kyle Zeng <kylebot@openai.com>
Acked-by: Julian Anastasov <ja@ssi.bg>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/netfilter/ipvs/ip_vs_sync.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/net/netfilter/ipvs/ip_vs_sync.c b/net/netfilter/ipvs/ip_vs_sync.c
index 1deb063cd72c..5383aeafb0ae 100644
--- a/net/netfilter/ipvs/ip_vs_sync.c
+++ b/net/netfilter/ipvs/ip_vs_sync.c
@@ -747,9 +747,9 @@ void ip_vs_sync_conn(struct netns_ipvs *ipvs, struct ip_vs_conn *cp, int pkts)
 	if (cp->flags & IP_VS_CONN_F_SEQ_MASK) {
 		*(p++) = IPVS_OPT_SEQ_DATA;
 		*(p++) = sizeof(struct ip_vs_sync_conn_options);
-		hton_seq((struct ip_vs_seq *)p, &cp->in_seq);
+		hton_seq(&cp->in_seq, (struct ip_vs_seq *)p);
 		p += sizeof(struct ip_vs_seq);
-		hton_seq((struct ip_vs_seq *)p, &cp->out_seq);
+		hton_seq(&cp->out_seq, (struct ip_vs_seq *)p);
 		p += sizeof(struct ip_vs_seq);
 	}
 	/* Handle pe data */
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 3/9] netfilter: nf_conntrack_sip: fix OOB read in sip_skip_whitespace()
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 1/9] ipvs: reject invalid states in connection template sync records Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 2/9] ipvs: fix reversed sequence option serialization Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 4/9] netfilter: cttimeout: prevent UAF during module unload Pablo Neira Ayuso
                   ` (5 subsequent siblings)
  8 siblings, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Joas Antonio dos Santos <joasantonio108@gmail.com>

sip_skip_whitespace() returns dptr unchanged when its own loop
exhausts the buffer (dptr == limit), instead of NULL like its sibling
sip_follow_continuation() returns on its own "no more data" path.

ct_sip_get_header() only checks for NULL after calling it:

  dptr = sip_skip_whitespace(dptr, limit);
  if (dptr == NULL)
          break;
  if (*dptr != ':' || ++dptr >= limit)
          break;

so a recognized header name followed only by spaces/tabs running to
the exact end of the SIP payload, with no colon, makes the very next
statement read one byte past the buffer.

Make both "no more data" outcomes return NULL, matching the
convention sip_follow_continuation() already uses and that both
existing callers already check for.

Fixes: ea45f12a2766d ("[NETFILTER]: nf_conntrack_sip: parse SIP headers properly")
Signed-off-by: Joas Antonio dos Santos <joasantonio108@gmail.com>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/netfilter/nf_conntrack_sip.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/net/netfilter/nf_conntrack_sip.c b/net/netfilter/nf_conntrack_sip.c
index 3ccf34fc1c53..64bc440b1181 100644
--- a/net/netfilter/nf_conntrack_sip.c
+++ b/net/netfilter/nf_conntrack_sip.c
@@ -423,7 +423,7 @@ static const char *sip_skip_whitespace(const char *dptr, const char *limit)
 		dptr = sip_follow_continuation(dptr, limit);
 		break;
 	}
-	return dptr;
+	return dptr < limit ? dptr : NULL;
 }
 
 /* Search within a SIP header value, dealing with continuation lines */
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 4/9] netfilter: cttimeout: prevent UAF during module unload
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
                   ` (2 preceding siblings ...)
  2026-09-07 17:17 ` [PATCH net 3/9] netfilter: nf_conntrack_sip: fix OOB read in sip_skip_whitespace() Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-08 18:04   ` netdev-bot+sashiko
  2026-09-07 17:17 ` [PATCH net 5/9] netfilter: nf_log: unregister loggers before per-net teardown Pablo Neira Ayuso
                   ` (4 subsequent siblings)
  8 siblings, 1 reply; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Chengfeng Ye <nicoyip.dev@gmail.com>

nf_ct_set_timeout() protects the timeout hook dereference and policy lookup
with rcu_read_lock(). cttimeout_exit(), however, unregisters the per-net
operations before it clears the hook.

This allows the following interleaving:

  CPU 0                              CPU 1
  cttimeout_exit()                   nf_ct_set_timeout()
    unregister_pernet_subsys()         rcu_read_lock()
      kfree(pernet)                     h = nf_ct_timeout_hook
                                        h->timeout_find_get()
                                          nfct_timeout_pernet()

The hook still points to ctnl_timeout_find_get() when CPU 1 looks up the
already freed per-net timeout list. KASAN reported:

  BUG: KASAN: slab-use-after-free in ctnl_timeout_find_get
  Read of size 8 by task poc/90
  Call Trace:
   ctnl_timeout_find_get+0x271/0x2a0 [nfnetlink_cttimeout]
   nf_ct_set_timeout+0x7b/0x3c0
   xt_ct_tg_check+0x724/0xb20
   xt_check_target+0x234/0xa90
   do_ipt_set_ctl+0x570/0x1270
  Allocated by task 89:
   __kmalloc_noprof+0x16e/0x460
   ops_init+0x6d/0x420
   register_pernet_operations+0x2f6/0x670
  Freed by task 91:
   kfree+0x131/0x390
   ops_undo_list+0x3d4/0x730
   unregister_pernet_operations+0x232/0x490
   unregister_pernet_subsys+0x1c/0x30
   cttimeout_exit+0x52/0x970 [nfnetlink_cttimeout]

Clear the hook and wait for existing readers before unregistering the
per-net operations. This blocks new policy lookups and ensures readers that
observed the hook finish before the per-net storage is freed.

Fixes: ebfbe67568a7 ("netfilter: cttimeout: use net_generic infra")
Cc: stable@vger.kernel.org
Signed-off-by: Chengfeng Ye <nicoyip.dev@gmail.com>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/netfilter/nfnetlink_cttimeout.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/net/netfilter/nfnetlink_cttimeout.c b/net/netfilter/nfnetlink_cttimeout.c
index 66c2016f6049..132c02ac7c4e 100644
--- a/net/netfilter/nfnetlink_cttimeout.c
+++ b/net/netfilter/nfnetlink_cttimeout.c
@@ -652,9 +652,9 @@ static void __exit cttimeout_exit(void)
 {
 	nfnetlink_subsys_unregister(&cttimeout_subsys);
 
-	unregister_pernet_subsys(&cttimeout_ops);
 	RCU_INIT_POINTER(nf_ct_timeout_hook, NULL);
 	synchronize_net();
+	unregister_pernet_subsys(&cttimeout_ops);
 }
 
 module_init(cttimeout_init);
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 5/9] netfilter: nf_log: unregister loggers before per-net teardown
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
                   ` (3 preceding siblings ...)
  2026-09-07 17:17 ` [PATCH net 4/9] netfilter: cttimeout: prevent UAF during module unload Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 6/9] netfilter: nfnetlink_log: cope with concurrent instance destruction Pablo Neira Ayuso
                   ` (3 subsequent siblings)
  8 siblings, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Chengfeng Ye <nicoyip.dev@gmail.com>

nf_log_syslog and nfnetlink_log unregister their per-network namespace
operations before unregistering their global logger backends. This
leaves a window where a sysctl or netlink writer can rebind the still-
registered logger after the per-net pre-exit callback cleared the old
selection.

The race looks like this:

  CPU 0                                 CPU 1
  ----                                  ----
  unregister_pernet_subsys()
    nf_log_unset(net, logger)
      net->nf.nf_loggers[pf] = NULL

                                        lock nf_log_mutex
                                        find logger in loggers[][]
                                        net->nf.nf_loggers[pf] = logger
                                        unlock nf_log_mutex

  nf_log_unregister(logger)
    lock nf_log_mutex
    loggers[pf][type] = NULL
    unlock nf_log_mutex
    synchronize_rcu()
  module exit returns
  module core frees backend memory

Later, a sysctl read or packet logging operation can dereference the
stale per-net logger pointer.

Fix this by unregistering the global logger backends before tearing down
per-net state. Once the global registrations are gone, later writers can
no longer rebind the logger. unregister_pernet_subsys() already waits
for an RCU grace period after the pre-exit callback clears the per-net
selection, while nf_log_unregister() continues to cover readers of the
global logger table.

Apply this ordering fix to both nf_log backends that combine per-net
teardown with global logger registration.

Fixes: 5b023fc8d8e0 ("netfilter: enable per netns support for nf_loggers")
Cc: stable@vger.kernel.org
Signed-off-by: Chengfeng Ye <nicoyip.dev@gmail.com>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/netfilter/nf_log_syslog.c | 2 +-
 net/netfilter/nfnetlink_log.c | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/net/netfilter/nf_log_syslog.c b/net/netfilter/nf_log_syslog.c
index f24288088c0d..c3fd398ffcd7 100644
--- a/net/netfilter/nf_log_syslog.c
+++ b/net/netfilter/nf_log_syslog.c
@@ -1073,12 +1073,12 @@ static int __init nf_log_syslog_init(void)
 
 static void __exit nf_log_syslog_exit(void)
 {
-	unregister_pernet_subsys(&nf_log_syslog_net_ops);
 	nf_log_unregister(&nf_ip_logger);
 	nf_log_unregister(&nf_arp_logger);
 	nf_log_unregister(&nf_ip6_logger);
 	nf_log_unregister(&nf_netdev_logger);
 	nf_log_unregister(&nf_bridge_logger);
+	unregister_pernet_subsys(&nf_log_syslog_net_ops);
 }
 
 module_init(nf_log_syslog_init);
diff --git a/net/netfilter/nfnetlink_log.c b/net/netfilter/nfnetlink_log.c
index 6c7fa2ed34f5..9d7fec570abe 100644
--- a/net/netfilter/nfnetlink_log.c
+++ b/net/netfilter/nfnetlink_log.c
@@ -1233,8 +1233,8 @@ static void __exit nfnetlink_log_fini(void)
 {
 	nfnetlink_subsys_unregister(&nfulnl_subsys);
 	netlink_unregister_notifier(&nfulnl_rtnl_notifier);
-	unregister_pernet_subsys(&nfnl_log_net_ops);
 	nf_log_unregister(&nfulnl_logger);
+	unregister_pernet_subsys(&nfnl_log_net_ops);
 }
 
 MODULE_DESCRIPTION("netfilter userspace logging");
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 6/9] netfilter: nfnetlink_log: cope with concurrent instance destruction
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
                   ` (4 preceding siblings ...)
  2026-09-07 17:17 ` [PATCH net 5/9] netfilter: nf_log: unregister loggers before per-net teardown Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 7/9] netfilter: arp_tables: remove the 32bit compat interface Pablo Neira Ayuso
                   ` (2 subsequent siblings)
  8 siblings, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Florian Westphal <fw@strlen.de>

Instances are refcounted. However, only memory release happens on the
1 -> 0 transition; the unlink from hashes can occur with any refcount.

Uncooperative userspace can force a situation where a queue is pending
for destruction from netlink event while a different socket with same
portid processes an UNBIND request.

With right timing, this will unhash the instance again:

Oops: general protection fault, [..]
Call Trace:
 <TASK>
 nfulnl_recv_config+0x31a/0xd50
 nfnetlink_rcv_msg+0x7c2/0xeb0

Fixes: 0597f2680d66 ("[NETFILTER]: Add new "nfnetlink_log" userspace packet logging facility")
Reported-by: Eulgyu Kim <eulgyukim@snu.ac.kr>
Reported-by: Jaeyoung Chung <jjy600901@snu.ac.kr>
Signed-off-by: Florian Westphal <fw@strlen.de>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/netfilter/nfnetlink_log.c | 13 +++++++++----
 1 file changed, 9 insertions(+), 4 deletions(-)

diff --git a/net/netfilter/nfnetlink_log.c b/net/netfilter/nfnetlink_log.c
index 9d7fec570abe..d923f2cb1398 100644
--- a/net/netfilter/nfnetlink_log.c
+++ b/net/netfilter/nfnetlink_log.c
@@ -228,13 +228,18 @@ static void __nfulnl_flush(struct nfulnl_instance *inst);
 static void
 __instance_destroy(struct nfulnl_instance *inst)
 {
+	spin_lock(&inst->lock);
+	if (inst->copy_mode == NFULNL_COPY_DISABLED) {
+		/* attempt to UNBIND a queue already pending
+		 * destruction via netlink close event. Ignore.
+		 */
+		spin_unlock(&inst->lock);
+		return;
+	}
+
 	/* first pull it out of the global list */
 	hlist_del_rcu(&inst->hlist);
 
-	/* then flush all pending packets from skb */
-
-	spin_lock(&inst->lock);
-
 	/* lockless readers wont be able to use us */
 	inst->copy_mode = NFULNL_COPY_DISABLED;
 
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 7/9] netfilter: arp_tables: remove the 32bit compat interface
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
                   ` (5 preceding siblings ...)
  2026-09-07 17:17 ` [PATCH net 6/9] netfilter: nfnetlink_log: cope with concurrent instance destruction Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-08 18:04   ` netdev-bot+sashiko
  2026-09-07 17:17 ` [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero Pablo Neira Ayuso
  2026-09-07 17:17 ` [PATCH net 9/9] netfilter: report NLM_F_DUMP_FILTERED when all is filtered out Pablo Neira Ayuso
  8 siblings, 1 reply; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Florian Westphal <fw@strlen.de>

This feature is required to use 32bit arptables binary on 64bit kernels.
It's already off in many distributions including Debian and Fedora for
many years.

Zap arptables first, it's the most esoteric of the 4 flavors.

Signed-off-by: Florian Westphal <fw@strlen.de>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 include/linux/netfilter_arp/arp_tables.h |  19 -
 net/ipv4/netfilter/arp_tables.c          | 472 +----------------------
 net/netfilter/Kconfig                    |   2 +-
 3 files changed, 4 insertions(+), 489 deletions(-)

diff --git a/include/linux/netfilter_arp/arp_tables.h b/include/linux/netfilter_arp/arp_tables.h
index 05631a25e622..8b8d472eff34 100644
--- a/include/linux/netfilter_arp/arp_tables.h
+++ b/include/linux/netfilter_arp/arp_tables.h
@@ -56,23 +56,4 @@ void arpt_unregister_table(struct net *net, const char *name);
 extern unsigned int arpt_do_table(void *priv, struct sk_buff *skb,
 				  const struct nf_hook_state *state);
 
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-#include <net/compat.h>
-
-struct compat_arpt_entry {
-	struct arpt_arp arp;
-	__u16 target_offset;
-	__u16 next_offset;
-	compat_uint_t comefrom;
-	struct compat_xt_counters counters;
-	unsigned char elems[];
-};
-
-static inline struct xt_entry_target *
-compat_arpt_get_target(struct compat_arpt_entry *e)
-{
-	return (void *)e + e->target_offset;
-}
-
-#endif /* CONFIG_COMPAT */
 #endif /* _ARPTABLES_H */
diff --git a/net/ipv4/netfilter/arp_tables.c b/net/ipv4/netfilter/arp_tables.c
index a87e07e80d0d..db307fa49f3f 100644
--- a/net/ipv4/netfilter/arp_tables.c
+++ b/net/ipv4/netfilter/arp_tables.c
@@ -23,7 +23,6 @@
 #include <linux/init.h>
 #include <linux/mutex.h>
 #include <linux/err.h>
-#include <net/compat.h>
 #include <net/sock.h>
 #include <linux/uaccess.h>
 
@@ -724,80 +723,6 @@ static int copy_entries_to_user(unsigned int total_size,
 	return ret;
 }
 
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-static void compat_standard_from_user(void *dst, const void *src)
-{
-	int v = *(compat_int_t *)src;
-
-	if (v > 0)
-		v += xt_compat_calc_jump(NFPROTO_ARP, v);
-	memcpy(dst, &v, sizeof(v));
-}
-
-static int compat_standard_to_user(void __user *dst, const void *src)
-{
-	compat_int_t cv = *(int *)src;
-
-	if (cv > 0)
-		cv -= xt_compat_calc_jump(NFPROTO_ARP, cv);
-	return copy_to_user(dst, &cv, sizeof(cv)) ? -EFAULT : 0;
-}
-
-static int compat_calc_entry(const struct arpt_entry *e,
-			     const struct xt_table_info *info,
-			     const void *base, struct xt_table_info *newinfo)
-{
-	const struct xt_entry_target *t;
-	unsigned int entry_offset;
-	int off, i, ret;
-
-	off = sizeof(struct arpt_entry) - sizeof(struct compat_arpt_entry);
-	entry_offset = (void *)e - base;
-
-	t = arpt_get_target_c(e);
-	off += xt_compat_target_offset(t->u.kernel.target);
-	newinfo->size -= off;
-	ret = xt_compat_add_offset(NFPROTO_ARP, entry_offset, off);
-	if (ret)
-		return ret;
-
-	for (i = 0; i < NF_ARP_NUMHOOKS; i++) {
-		if (info->hook_entry[i] &&
-		    (e < (struct arpt_entry *)(base + info->hook_entry[i])))
-			newinfo->hook_entry[i] -= off;
-		if (info->underflow[i] &&
-		    (e < (struct arpt_entry *)(base + info->underflow[i])))
-			newinfo->underflow[i] -= off;
-	}
-	return 0;
-}
-
-static int compat_table_info(const struct xt_table_info *info,
-			     struct xt_table_info *newinfo)
-{
-	struct arpt_entry *iter;
-	const void *loc_cpu_entry;
-	int ret;
-
-	if (!newinfo || !info)
-		return -EINVAL;
-
-	/* we dont care about newinfo->entries */
-	memcpy(newinfo, info, offsetof(struct xt_table_info, entries));
-	newinfo->initial_entries = 0;
-	loc_cpu_entry = info->entries;
-	ret = xt_compat_init_offsets(NFPROTO_ARP, info->number);
-	if (ret)
-		return ret;
-	xt_entry_foreach(iter, loc_cpu_entry, info->size) {
-		ret = compat_calc_entry(iter, info, loc_cpu_entry, newinfo);
-		if (ret != 0)
-			return ret;
-	}
-	return 0;
-}
-#endif
-
 static int get_info(struct net *net, void __user *user, const int *len)
 {
 	char name[XT_TABLE_MAXNAMELEN];
@@ -811,23 +736,11 @@ static int get_info(struct net *net, void __user *user, const int *len)
 		return -EFAULT;
 
 	name[XT_TABLE_MAXNAMELEN-1] = '\0';
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-	if (in_compat_syscall())
-		xt_compat_lock(NFPROTO_ARP);
-#endif
 	t = xt_request_find_table_lock(net, NFPROTO_ARP, name);
 	if (!IS_ERR(t)) {
 		struct arpt_getinfo info;
 		const struct xt_table_info *private = t->private;
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-		struct xt_table_info tmp;
 
-		if (in_compat_syscall()) {
-			ret = compat_table_info(private, &tmp);
-			xt_compat_flush_offsets(NFPROTO_ARP);
-			private = &tmp;
-		}
-#endif
 		memset(&info, 0, sizeof(info));
 		info.valid_hooks = t->valid_hooks;
 		memcpy(info.hook_entry, private->hook_entry,
@@ -846,10 +759,7 @@ static int get_info(struct net *net, void __user *user, const int *len)
 		module_put(t->me);
 	} else
 		ret = PTR_ERR(t);
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-	if (in_compat_syscall())
-		xt_compat_unlock(NFPROTO_ARP);
-#endif
+
 	return ret;
 }
 
@@ -1059,367 +969,6 @@ static int do_add_counters(struct net *net, sockptr_t arg, unsigned int len)
 	return ret;
 }
 
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-struct compat_arpt_replace {
-	char				name[XT_TABLE_MAXNAMELEN];
-	u32				valid_hooks;
-	u32				num_entries;
-	u32				size;
-	u32				hook_entry[NF_ARP_NUMHOOKS];
-	u32				underflow[NF_ARP_NUMHOOKS];
-	u32				num_counters;
-	compat_uptr_t			counters;
-	struct compat_arpt_entry	entries[];
-};
-
-static inline void compat_release_entry(struct compat_arpt_entry *e)
-{
-	struct xt_entry_target *t;
-
-	t = compat_arpt_get_target(e);
-	module_put(t->u.kernel.target->me);
-}
-
-static int
-check_compat_entry_size_and_hooks(struct compat_arpt_entry *e,
-				  struct xt_table_info *newinfo,
-				  unsigned int *size,
-				  const unsigned char *base,
-				  const unsigned char *limit)
-{
-	struct xt_entry_target *t;
-	struct xt_target *target;
-	unsigned int entry_offset;
-	int ret, off;
-
-	if ((unsigned long)e % __alignof__(struct compat_arpt_entry) != 0 ||
-	    (unsigned char *)e + sizeof(struct compat_arpt_entry) >= limit ||
-	    (unsigned char *)e + e->next_offset > limit)
-		return -EINVAL;
-
-	if (e->next_offset < sizeof(struct compat_arpt_entry) +
-			     sizeof(struct compat_xt_entry_target))
-		return -EINVAL;
-
-	if (!arp_checkentry(&e->arp))
-		return -EINVAL;
-
-	ret = xt_compat_check_entry_offsets(e, e->elems, e->target_offset,
-					    e->next_offset);
-	if (ret)
-		return ret;
-
-	off = sizeof(struct arpt_entry) - sizeof(struct compat_arpt_entry);
-	entry_offset = (void *)e - (void *)base;
-
-	t = compat_arpt_get_target(e);
-	target = xt_request_find_target(NFPROTO_ARP, t->u.user.name,
-					t->u.user.revision);
-	if (IS_ERR(target)) {
-		ret = PTR_ERR(target);
-		goto out;
-	}
-	t->u.kernel.target = target;
-
-	off += xt_compat_target_offset(target);
-	*size += off;
-	ret = xt_compat_add_offset(NFPROTO_ARP, entry_offset, off);
-	if (ret)
-		goto release_target;
-
-	return 0;
-
-release_target:
-	module_put(t->u.kernel.target->me);
-out:
-	return ret;
-}
-
-static void
-compat_copy_entry_from_user(struct compat_arpt_entry *e, void **dstptr,
-			    unsigned int *size,
-			    struct xt_table_info *newinfo, unsigned char *base)
-{
-	struct xt_entry_target *t;
-	struct arpt_entry *de;
-	unsigned int origsize;
-	int h;
-
-	origsize = *size;
-	de = *dstptr;
-	memcpy(de, e, sizeof(struct arpt_entry));
-	memcpy(&de->counters, &e->counters, sizeof(e->counters));
-
-	*dstptr += sizeof(struct arpt_entry);
-	*size += sizeof(struct arpt_entry) - sizeof(struct compat_arpt_entry);
-
-	de->target_offset = e->target_offset - (origsize - *size);
-	t = compat_arpt_get_target(e);
-	xt_compat_target_from_user(t, dstptr, size);
-
-	de->next_offset = e->next_offset - (origsize - *size);
-	for (h = 0; h < NF_ARP_NUMHOOKS; h++) {
-		if ((unsigned char *)de - base < newinfo->hook_entry[h])
-			newinfo->hook_entry[h] -= origsize - *size;
-		if ((unsigned char *)de - base < newinfo->underflow[h])
-			newinfo->underflow[h] -= origsize - *size;
-	}
-}
-
-static int translate_compat_table(struct net *net,
-				  struct xt_table_info **pinfo,
-				  void **pentry0,
-				  const struct compat_arpt_replace *compatr)
-{
-	unsigned int i, j;
-	struct xt_table_info *newinfo, *info;
-	void *pos, *entry0, *entry1;
-	struct compat_arpt_entry *iter0;
-	struct arpt_replace repl;
-	unsigned int size;
-	int ret;
-
-	info = *pinfo;
-	entry0 = *pentry0;
-	size = compatr->size;
-	info->number = compatr->num_entries;
-
-	j = 0;
-	xt_compat_lock(NFPROTO_ARP);
-	ret = xt_compat_init_offsets(NFPROTO_ARP, compatr->num_entries);
-	if (ret)
-		goto out_unlock;
-	/* Walk through entries, checking offsets. */
-	xt_entry_foreach(iter0, entry0, compatr->size) {
-		ret = check_compat_entry_size_and_hooks(iter0, info, &size,
-							entry0,
-							entry0 + compatr->size);
-		if (ret != 0)
-			goto out_unlock;
-		++j;
-	}
-
-	ret = -EINVAL;
-	if (j != compatr->num_entries)
-		goto out_unlock;
-
-	ret = -ENOMEM;
-	newinfo = xt_alloc_table_info(size);
-	if (!newinfo)
-		goto out_unlock;
-
-	memset(newinfo->entries, 0, size);
-
-	newinfo->number = compatr->num_entries;
-	for (i = 0; i < NF_ARP_NUMHOOKS; i++) {
-		newinfo->hook_entry[i] = compatr->hook_entry[i];
-		newinfo->underflow[i] = compatr->underflow[i];
-	}
-	entry1 = newinfo->entries;
-	pos = entry1;
-	size = compatr->size;
-	xt_entry_foreach(iter0, entry0, compatr->size)
-		compat_copy_entry_from_user(iter0, &pos, &size,
-					    newinfo, entry1);
-
-	/* all module references in entry0 are now gone */
-
-	xt_compat_flush_offsets(NFPROTO_ARP);
-	xt_compat_unlock(NFPROTO_ARP);
-
-	memcpy(&repl, compatr, sizeof(*compatr));
-
-	for (i = 0; i < NF_ARP_NUMHOOKS; i++) {
-		repl.hook_entry[i] = newinfo->hook_entry[i];
-		repl.underflow[i] = newinfo->underflow[i];
-	}
-
-	repl.num_counters = 0;
-	repl.counters = NULL;
-	repl.size = newinfo->size;
-	ret = translate_table(net, newinfo, entry1, &repl);
-	if (ret)
-		goto free_newinfo;
-
-	*pinfo = newinfo;
-	*pentry0 = entry1;
-	xt_free_table_info(info);
-	return 0;
-
-free_newinfo:
-	xt_free_table_info(newinfo);
-	return ret;
-out_unlock:
-	xt_compat_flush_offsets(NFPROTO_ARP);
-	xt_compat_unlock(NFPROTO_ARP);
-	xt_entry_foreach(iter0, entry0, compatr->size) {
-		if (j-- == 0)
-			break;
-		compat_release_entry(iter0);
-	}
-	return ret;
-}
-
-static int compat_do_replace(struct net *net, sockptr_t arg, unsigned int len)
-{
-	int ret;
-	struct compat_arpt_replace tmp;
-	struct xt_table_info *newinfo;
-	void *loc_cpu_entry;
-	struct arpt_entry *iter;
-
-	if (len < sizeof(tmp))
-		return -EINVAL;
-	if (copy_from_sockptr(&tmp, arg, sizeof(tmp)) != 0)
-		return -EFAULT;
-
-	/* overflow check */
-	if (tmp.num_counters >= INT_MAX / sizeof(struct xt_counters))
-		return -ENOMEM;
-	if (tmp.num_counters == 0)
-		return -EINVAL;
-	if ((u64)len < (u64)tmp.size + sizeof(tmp))
-		return -EINVAL;
-
-	tmp.name[sizeof(tmp.name)-1] = 0;
-
-	newinfo = xt_alloc_table_info(tmp.size);
-	if (!newinfo)
-		return -ENOMEM;
-
-	loc_cpu_entry = newinfo->entries;
-	if (copy_from_sockptr_offset(loc_cpu_entry, arg, sizeof(tmp),
-			tmp.size) != 0) {
-		ret = -EFAULT;
-		goto free_newinfo;
-	}
-
-	ret = translate_compat_table(net, &newinfo, &loc_cpu_entry, &tmp);
-	if (ret != 0)
-		goto free_newinfo;
-
-	ret = __do_replace(net, tmp.name, tmp.valid_hooks, newinfo,
-			   tmp.num_counters, compat_ptr(tmp.counters));
-	if (ret)
-		goto free_newinfo_untrans;
-	return 0;
-
- free_newinfo_untrans:
-	xt_entry_foreach(iter, loc_cpu_entry, newinfo->size)
-		cleanup_entry(iter, net);
- free_newinfo:
-	xt_free_table_info(newinfo);
-	return ret;
-}
-
-static int compat_copy_entry_to_user(struct arpt_entry *e, void __user **dstptr,
-				     compat_uint_t *size,
-				     struct xt_counters *counters,
-				     unsigned int i)
-{
-	struct xt_entry_target *t;
-	struct compat_arpt_entry __user *ce;
-	u_int16_t target_offset, next_offset;
-	compat_uint_t origsize;
-	int ret;
-
-	origsize = *size;
-	ce = *dstptr;
-	if (copy_to_user(ce, e, offsetof(struct compat_arpt_entry, counters)) ||
-	    copy_to_user(&ce->counters, &counters[i], sizeof(counters[i])))
-		return -EFAULT;
-
-	*dstptr += sizeof(struct compat_arpt_entry);
-	*size -= sizeof(struct arpt_entry) - sizeof(struct compat_arpt_entry);
-
-	target_offset = e->target_offset - (origsize - *size);
-
-	t = arpt_get_target(e);
-	ret = xt_compat_target_to_user(t, dstptr, size);
-	if (ret)
-		return ret;
-	next_offset = e->next_offset - (origsize - *size);
-	if (put_user(target_offset, &ce->target_offset) != 0 ||
-	    put_user(next_offset, &ce->next_offset) != 0)
-		return -EFAULT;
-	return 0;
-}
-
-static int compat_copy_entries_to_user(unsigned int total_size,
-				       struct xt_table *table,
-				       void __user *userptr)
-{
-	struct xt_counters *counters;
-	const struct xt_table_info *private = table->private;
-	void __user *pos;
-	unsigned int size;
-	int ret = 0;
-	unsigned int i = 0;
-	struct arpt_entry *iter;
-
-	counters = alloc_counters(table);
-	if (IS_ERR(counters))
-		return PTR_ERR(counters);
-
-	pos = userptr;
-	size = total_size;
-	xt_entry_foreach(iter, private->entries, total_size) {
-		ret = compat_copy_entry_to_user(iter, &pos,
-						&size, counters, i++);
-		if (ret != 0)
-			break;
-	}
-	vfree(counters);
-	return ret;
-}
-
-struct compat_arpt_get_entries {
-	char name[XT_TABLE_MAXNAMELEN];
-	compat_uint_t size;
-	struct compat_arpt_entry entrytable[];
-};
-
-static int compat_get_entries(struct net *net,
-			      struct compat_arpt_get_entries __user *uptr,
-			      int *len)
-{
-	int ret;
-	struct compat_arpt_get_entries get;
-	struct xt_table *t;
-
-	if (*len < sizeof(get))
-		return -EINVAL;
-	if (copy_from_user(&get, uptr, sizeof(get)) != 0)
-		return -EFAULT;
-	if (*len != sizeof(struct compat_arpt_get_entries) + get.size)
-		return -EINVAL;
-
-	get.name[sizeof(get.name) - 1] = '\0';
-
-	xt_compat_lock(NFPROTO_ARP);
-	t = xt_find_table_lock(net, NFPROTO_ARP, get.name);
-	if (!IS_ERR(t)) {
-		const struct xt_table_info *private = t->private;
-		struct xt_table_info info;
-
-		ret = compat_table_info(private, &info);
-		if (!ret && get.size == info.size) {
-			ret = compat_copy_entries_to_user(private->size,
-							  t, uptr->entrytable);
-		} else if (!ret)
-			ret = -EAGAIN;
-
-		xt_compat_flush_offsets(NFPROTO_ARP);
-		module_put(t->me);
-		xt_table_unlock(t);
-	} else
-		ret = PTR_ERR(t);
-
-	xt_compat_unlock(NFPROTO_ARP);
-	return ret;
-}
-#endif
-
 static int do_arpt_set_ctl(struct sock *sk, int cmd, sockptr_t arg,
 		unsigned int len)
 {
@@ -1432,12 +981,7 @@ static int do_arpt_set_ctl(struct sock *sk, int cmd, sockptr_t arg,
 
 	switch (cmd) {
 	case ARPT_SO_SET_REPLACE:
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-		if (in_compat_syscall())
-			ret = compat_do_replace(sock_net(sk), arg, len);
-		else
-#endif
-			ret = do_replace(sock_net(sk), arg, len);
+		ret = do_replace(sock_net(sk), arg, len);
 		break;
 
 	case ARPT_SO_SET_ADD_COUNTERS:
@@ -1466,12 +1010,7 @@ static int do_arpt_get_ctl(struct sock *sk, int cmd, void __user *user, int *len
 		break;
 
 	case ARPT_SO_GET_ENTRIES:
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-		if (in_compat_syscall())
-			ret = compat_get_entries(sock_net(sk), user, len);
-		else
-#endif
-			ret = get_entries(sock_net(sk), user, len);
+		ret = get_entries(sock_net(sk), user, len);
 		break;
 
 	case ARPT_SO_GET_REVISION_TARGET: {
@@ -1568,11 +1107,6 @@ static struct xt_target arpt_builtin_tg[] __read_mostly = {
 		.name             = XT_STANDARD_TARGET,
 		.targetsize       = sizeof(int),
 		.family           = NFPROTO_ARP,
-#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
-		.compatsize       = sizeof(compat_int_t),
-		.compat_from_user = compat_standard_from_user,
-		.compat_to_user   = compat_standard_to_user,
-#endif
 	},
 	{
 		.name             = XT_ERROR_TARGET,
diff --git a/net/netfilter/Kconfig b/net/netfilter/Kconfig
index 4c04cd8d40a2..09874c26fd13 100644
--- a/net/netfilter/Kconfig
+++ b/net/netfilter/Kconfig
@@ -739,7 +739,7 @@ config NETFILTER_XTABLES_COMPAT
 	bool "Netfilter Xtables 32bit support"
 	depends on COMPAT
 	help
-	   This option provides a translation layer to run 32bit arp,ip(6),ebtables
+	   This option provides a translation layer to run 32bit ip(6),ebtables
 	   binaries on 64bit kernels.
 
 	   If unsure, say N.
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
                   ` (6 preceding siblings ...)
  2026-09-07 17:17 ` [PATCH net 7/9] netfilter: arp_tables: remove the 32bit compat interface Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  2026-09-08 18:04   ` netdev-bot+sashiko
  2026-09-07 17:17 ` [PATCH net 9/9] netfilter: report NLM_F_DUMP_FILTERED when all is filtered out Pablo Neira Ayuso
  8 siblings, 1 reply; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Florian Westphal <fw@strlen.de>

The ip6tables traverser doesn't search the extension header chain unless
userspace did set the IP6T_F_PROTO flag.

This also means that userspace that sets the e->ipv6.proto flag can bypass
the protocol check for the rule by not setting this flag.

That in turn means that all ip6_tables modules and targets that want to
reject rules without '-p' flag MUST also check for that flag.

Not all do, likely because they got copied from iptables which lacks
this flag (no extension headers).

Instead of fixing up all the relevant targets, emulate ip6tables behaviour
in the kernel (like nft_compat.c) and set the flag if the protocol is set.

Reported-by: Zhiling Zou <zhilinz@nebusec.ai>
Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2")
Signed-off-by: Florian Westphal <fw@strlen.de>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/ipv6/netfilter/ip6_tables.c | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
index f42fb96ef64b..313c4aac377a 100644
--- a/net/ipv6/netfilter/ip6_tables.c
+++ b/net/ipv6/netfilter/ip6_tables.c
@@ -647,6 +647,11 @@ check_entry_size_and_hooks(struct ip6t_entry *e,
 	/* Clear counters and comefrom */
 	e->counters = ((struct xt_counters) { 0, 0 });
 	e->comefrom = 0;
+
+	/* set F_PROTO, else ip6_packet_match won't do the right thing. */
+	if (e->ipv6.proto)
+		e->ipv6.flags |= IP6T_F_PROTO;
+
 	return 0;
 }
 
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* [PATCH net 9/9] netfilter: report NLM_F_DUMP_FILTERED when all is filtered out
  2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
                   ` (7 preceding siblings ...)
  2026-09-07 17:17 ` [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero Pablo Neira Ayuso
@ 2026-09-07 17:17 ` Pablo Neira Ayuso
  8 siblings, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-07 17:17 UTC (permalink / raw)
  To: netfilter-devel; +Cc: davem, netdev, kuba, pabeni, edumazet, horms, fw, ja

From: Ilya Maximets <i.maximets@ovn.org>

NLM_F_DUMP_FILTERED is only set on data elements in the conntrack dump.
But when everything is filtered out it is confusing for the user space,
since the flag is not reported anymore and it looks like the table was
empty, which may or may not be the case.

'answer_flags' were introduced precisely for this use case, and the
conntrack dump should set the flag in there in case the filtering was
applied.

This is important, for example, to be able to tell if the filters are
supported or not by the kernel without modifying the kernel state.

With the proper reporting of NLM_F_DUMP_FILTERED on NLMSG_DONE, an
application in user space can just try and dump with an arbitrary
filter without worrying that there could be no matching entry.  The
reported flag will signal that the filtering was applied and therefore
supported.

Fixes: cb8aa9a3affb ("netfilter: ctnetlink: add kernel side filtering for dump")
Cc: stable@vger.kernel.org
Signed-off-by: Ilya Maximets <i.maximets@ovn.org>
Reviewed-by: Florian Westphal <fw@strlen.de>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
---
 net/netfilter/nf_conntrack_netlink.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/net/netfilter/nf_conntrack_netlink.c b/net/netfilter/nf_conntrack_netlink.c
index 9b4e29557ec3..579ada063b1b 100644
--- a/net/netfilter/nf_conntrack_netlink.c
+++ b/net/netfilter/nf_conntrack_netlink.c
@@ -1077,6 +1077,8 @@ static int ctnetlink_start(struct netlink_callback *cb)
 	}
 
 	cb->data = filter;
+	if (filter)
+		cb->answer_flags = NLM_F_DUMP_FILTERED;
 	return 0;
 }
 
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 18+ messages in thread

* Re: [PATCH net 4/9] netfilter: cttimeout: prevent UAF during module unload
  2026-09-07 17:17 ` [PATCH net 4/9] netfilter: cttimeout: prevent UAF during module unload Pablo Neira Ayuso
@ 2026-09-08 18:04   ` netdev-bot+sashiko
  2026-09-08 20:24     ` Pablo Neira Ayuso
  0 siblings, 1 reply; 18+ messages in thread
From: netdev-bot+sashiko @ 2026-09-08 18:04 UTC (permalink / raw)
  To: pablo; +Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

Thank you for your contribution! Sashiko AI review found 1 potential
issue(s) to consider:

Critical: 0 · High: 1 · Medium: 0 · Low: 0

- [High] cttimeout_exit() only drains RCU readers that reach the per-net
  timeout storage through nf_ct_timeout_hook.

--

netfilter: cttimeout: prevent UAF during module unload

This reorders cttimeout_exit() so that nf_ct_timeout_hook is cleared and
synchronize_net() is called before unregister_pernet_subsys() frees the
per-net timeout storage.  That closes the window where nf_ct_set_timeout()
could still reach the freed nfct_timeout_pernet blob through the hook.

> diff --git a/net/netfilter/nfnetlink_cttimeout.c b/net/netfilter/nfnetlink_cttimeout.c
> index 66c2016f6049d..132c02ac7c4ea 100644
> --- a/net/netfilter/nfnetlink_cttimeout.c
> +++ b/net/netfilter/nfnetlink_cttimeout.c
> @@ -652,9 +652,9 @@ static void __exit cttimeout_exit(void)
>  {
>  	nfnetlink_subsys_unregister(&cttimeout_subsys);
>  
> -	unregister_pernet_subsys(&cttimeout_ops);
>  	RCU_INIT_POINTER(nf_ct_timeout_hook, NULL);
>  	synchronize_net();
> +	unregister_pernet_subsys(&cttimeout_ops);
>  }

[Severity: High]
Does this leave the same per-net object reachable from the netlink dump
path during unload?

cttimeout_get_timeout() starts the dump without a module reference:

net/netfilter/nfnetlink_cttimeout.c:cttimeout_get_timeout() {
	if (info->nlh->nlmsg_flags & NLM_F_DUMP) {
		struct netlink_dump_control c = {
			.dump = ctnl_timeout_dump,
		};
		return netlink_dump_start(info->sk, skb, info->nlh, &c);
	}

With no .module set, __netlink_dump_start()'s try_module_get(control->module)
is try_module_get(NULL), which succeeds without taking anything, and
cb->module stays NULL.  nf_tables_api.c and nfnetlink_hook.c pass
.module = THIS_MODULE in their netlink_dump_control for comparison.

ctnl_timeout_dump() reads the per-net blob that unregister_pernet_subsys()
frees, and it is not gated by nf_ct_timeout_hook:

net/netfilter/nfnetlink_cttimeout.c:ctnl_timeout_dump() {
	rcu_read_lock();
	pernet = nfct_timeout_pernet(net);
	list_for_each_entry_rcu(cur, &pernet->nfct_timeout_list, head) {

Is the following sequence possible?

1. IPCTNL_MSG_TIMEOUT_NEW creates one policy; cttimeout_new_timeout() does
   __module_get(THIS_MODULE).
2. A NLM_F_DUMP IPCTNL_MSG_TIMEOUT_GET parks the dump: with one entry
   present ctnl_timeout_dump() returns skb->len > 0, netlink_dump() queues
   the skb and leaves nlk->cb_running set with cb->dump =
   ctnl_timeout_dump.
3. IPCTNL_MSG_TIMEOUT_DELETE removes the policy, and ctnl_timeout_del()
   does module_put(THIS_MODULE), so the module refcount is back to zero
   while the dump is still parked.
4. rmmod runs cttimeout_exit().  The synchronize_rcu() inside
   nfnetlink_subsys_unregister() and the new synchronize_net() only wait
   for RCU read-side sections, and a parked dump is not in one, so
   unregister_pernet_subsys() frees the nfct_timeout_pernet allocation and
   the module text goes away.
5. The next recvmsg() on that netlink socket resumes the dump:

net/netlink/af_netlink.c:netlink_recvmsg() {
	if (READ_ONCE(nlk->cb_running) &&
	    atomic_read(&sk->sk_rmem_alloc) <= sk->sk_rcvbuf / 2) {
		ret = netlink_dump(sk, false);

which is an indirect call through cb->dump into freed module text, and
then a read of the freed pernet->nfct_timeout_list.

Should the dump control also carry .module = THIS_MODULE so the parked
dump pins the module across the unload, given the commit is aimed at the
same freed nfct_timeout_pernet object during module unload?

Note that a dump over an empty policy list does not park: ctnl_timeout_dump()
returns 0 there and netlink_dump() finishes the dump immediately, so the
create/park/delete order above is what makes it reproducible.

-- 
Sashiko AI review · https://netdev-ai.bots.linux.dev/sashiko/#/patchset/20260907171732.1407739-2-pablo%40netfilter.org

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH net 7/9] netfilter: arp_tables: remove the 32bit compat interface
  2026-09-07 17:17 ` [PATCH net 7/9] netfilter: arp_tables: remove the 32bit compat interface Pablo Neira Ayuso
@ 2026-09-08 18:04   ` netdev-bot+sashiko
  2026-09-08 20:32     ` Pablo Neira Ayuso
  0 siblings, 1 reply; 18+ messages in thread
From: netdev-bot+sashiko @ 2026-09-08 18:04 UTC (permalink / raw)
  To: pablo; +Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

Thank you for your contribution! Sashiko AI review found 1 potential
issue(s) to consider:

Critical: 0 · High: 0 · Medium: 0 · Low: 1

- [Low] The arptables 32-bit compat interface is only partially removed.

--

netfilter: arp_tables: remove the 32bit compat interface

This removes all arptables-specific 32-bit compat translation code from
net/ipv4/netfilter/arp_tables.c, drops struct compat_arpt_entry and its
accessor from include/linux/netfilter_arp/arp_tables.h, and updates the
NETFILTER_XTABLES_COMPAT help text to no longer mention arp.

> diff --git a/net/ipv4/netfilter/arp_tables.c b/net/ipv4/netfilter/arp_tables.c
> index a87e07e80d0de..db307fa49f3f6 100644
> --- a/net/ipv4/netfilter/arp_tables.c
> +++ b/net/ipv4/netfilter/arp_tables.c

[ ... ]

> @@ -811,23 +736,11 @@ static int get_info(struct net *net, void __user *user, const int *len)
>  		return -EFAULT;
>  
>  	name[XT_TABLE_MAXNAMELEN-1] = '\0';
> -#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
> -	if (in_compat_syscall())
> -		xt_compat_lock(NFPROTO_ARP);
> -#endif
>  	t = xt_request_find_table_lock(net, NFPROTO_ARP, name);
>  	if (!IS_ERR(t)) {
>  		struct arpt_getinfo info;
>  		const struct xt_table_info *private = t->private;
> -#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
> -		struct xt_table_info tmp;
>  
> -		if (in_compat_syscall()) {
> -			ret = compat_table_info(private, &tmp);
> -			xt_compat_flush_offsets(NFPROTO_ARP);
> -			private = &tmp;
> -		}
> -#endif
>  		memset(&info, 0, sizeof(info));
>  		info.valid_hooks = t->valid_hooks;
>  		memcpy(info.hook_entry, private->hook_entry,

[ ... ]

> @@ -1432,12 +981,7 @@ static int do_arpt_set_ctl(struct sock *sk, int cmd, sockptr_t arg,
>  
>  	switch (cmd) {
>  	case ARPT_SO_SET_REPLACE:
> -#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
> -		if (in_compat_syscall())
> -			ret = compat_do_replace(sock_net(sk), arg, len);
> -		else
> -#endif
> -			ret = do_replace(sock_net(sk), arg, len);
> +		ret = do_replace(sock_net(sk), arg, len);
>  		break;
>  
>  	case ARPT_SO_SET_ADD_COUNTERS:

[Severity: Low]

Should the two arptables ctl handlers also stop accepting compat callers?
Both do_arpt_set_ctl() and do_arpt_get_ctl() still start with:

	if (!xt_compat_check())
		return -EPERM;

and that helper intentionally lets 32-bit callers continue when
CONFIG_NETFILTER_XTABLES_COMPAT is set:

include/linux/netfilter/x_tables.h:xt_compat_check() {
	if (!in_compat_syscall())
		return true;

	pr_warn_once("%s %s\n",
		     "xtables 32bit compat interface no longer supported",
		     "in namespaces and will be removed soon.");

	if (!capable(CAP_NET_ADMIN))
		return false;
#endif
	return true;
}

So a 32-bit task with CAP_NET_ADMIN now falls straight into the native
handlers, which gives three different behaviours:

ARPT_SO_GET_INFO succeeds and copies out the native xt_table_info values,
since the compat_table_info() rescaling above is gone:

		memcpy(info.hook_entry, private->hook_entry,
		       sizeof(info.hook_entry));
		memcpy(info.underflow, private->underflow,
		       sizeof(info.underflow));
		info.num_entries = private->number;
		info.size = private->size;

Are those offsets and size still meaningful to a caller that will walk them
using the 32-bit struct arpt_entry layout?

ARPT_SO_SET_REPLACE and ARPT_SO_GET_ENTRIES end up failing with -EINVAL
purely as a side effect of header size arithmetic in do_replace() and
get_entries() (76 vs 80 bytes for the replace header, 36 + size vs
40 + size for the get_entries header) rather than a defined unsupported
error.  Would an explicit rejection be clearer here, for example:

	if (in_compat_syscall())
		return -EOPNOTSUPP;

ARPT_SO_SET_ADD_COUNTERS keeps a working 32-bit ABI, because
do_add_counters() -> xt_copy_counters() still carries its own compat branch
that converts compat_xt_counters_info for every family, NFPROTO_ARP
included:

net/netfilter/x_tables.c:xt_copy_counters() {
#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
	if (in_compat_syscall()) {
		/* structures only differ in size due to alignment */
		struct compat_xt_counters_info compat_tmp;
	...
}

Does "remove the 32bit compat interface" then hold for that sockopt?  If
leaving the shared counter path compat-capable until the other three
flavors are converted is intended, could the commit message say so?

One more asymmetry: the ip_tables, ip6_tables and ebtables ctl handlers
still branch on in_compat_syscall() after the same xt_compat_check() call,
so the shared helper now means "translate" for those flavors and "warn,
then run the native path" for arptables.  Along the same lines, a 32-bit
task without CAP_NET_ADMIN now gets -EPERM plus a warning about a compat
interface that no longer exists for this flavor.

> @@ -1466,12 +1010,7 @@ static int do_arpt_get_ctl(struct sock *sk, int cmd, void __user *user, int *len
>  		break;
>  
>  	case ARPT_SO_GET_ENTRIES:
> -#ifdef CONFIG_NETFILTER_XTABLES_COMPAT
> -		if (in_compat_syscall())
> -			ret = compat_get_entries(sock_net(sk), user, len);
> -		else
> -#endif
> -			ret = get_entries(sock_net(sk), user, len);
> +		ret = get_entries(sock_net(sk), user, len);
>  		break;
>  
>  	case ARPT_SO_GET_REVISION_TARGET: {

[ ... ]

-- 
Sashiko AI review · https://netdev-ai.bots.linux.dev/sashiko/#/patchset/20260907171732.1407739-2-pablo%40netfilter.org

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero
  2026-09-07 17:17 ` [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero Pablo Neira Ayuso
@ 2026-09-08 18:04   ` netdev-bot+sashiko
  2026-09-08 20:22     ` Pablo Neira Ayuso
  2026-09-08 20:35     ` Pablo Neira Ayuso
  0 siblings, 2 replies; 18+ messages in thread
From: netdev-bot+sashiko @ 2026-09-08 18:04 UTC (permalink / raw)
  To: pablo; +Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

Thank you for your contribution! Sashiko AI review found 1 potential
issue(s) to consider:

Critical: 0 · High: 0 · Medium: 0 · Low: 1

- [Low] Stale/contradicted UAPI documentation for `struct
  ip6t_ip6::proto`.

--

netfilter: ip6_tables: set F_PROTO when proto value is nonzero

This makes the kernel set IP6T_F_PROTO for any rule that carries a nonzero
ipv6.proto, so ip6_packet_match() always performs the protocol comparison
and extension header walk instead of skipping it when userspace left the
flag clear. It mirrors the normalisation already done in nft_compat.c.

> diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
> index f42fb96ef64b6..313c4aac377aa 100644
> --- a/net/ipv6/netfilter/ip6_tables.c
> +++ b/net/ipv6/netfilter/ip6_tables.c
> @@ -647,6 +647,11 @@ check_entry_size_and_hooks(struct ip6t_entry *e,
>  	/* Clear counters and comefrom */
>  	e->counters = ((struct xt_counters) { 0, 0 });
>  	e->comefrom = 0;
> +
> +	/* set F_PROTO, else ip6_packet_match won't do the right thing. */
> +	if (e->ipv6.proto)
> +		e->ipv6.flags |= IP6T_F_PROTO;
> +
>  	return 0;
>  }

[Severity: Low]
Should the uapi header comment be updated in the same patch?  The
description of struct ip6t_ip6::proto in
include/uapi/linux/netfilter_ipv6/ip6_tables.h still documents the
opposite contract:

	/* Upper protocol number
	 * ...
	 * - You also need to set IP6T_FLAGS_PROTO to "flags" to check protocol.
	 */
	__u16 proto;

After this change, a non-standard userspace that follows that comment and
sets proto = IPPROTO_TCP while leaving flags = 0 (expecting a
protocol-agnostic rule) gets a protocol-narrowed rule instead, and
ip6_packet_match() now takes the flag-gated branch, including the
ipv6_find_hdr() walk and its *hotdrop = true path when the lookup fails
with _frag_off == 0:

	if (ip6info->flags & IP6T_F_PROTO) {
		...
		protohdr = ipv6_find_hdr(skb, protoff, -1, &_frag_off, NULL);
		if (protohdr < 0) {
			if (_frag_off == 0)
				*hotdrop = true;

Standard ip6tables always sets IP6T_F_PROTO together with -p, so this only
affects hand-crafted rule blobs, and the resulting rule is stricter rather
than unsafe.  Still, the field's documented meaning changes here.

While in that comment, IP6T_FLAGS_PROTO does not exist anywhere in the
tree; the macro defined a few lines below is IP6T_F_PROTO.  That name is a
pre-existing typo and was not introduced by this patch, but it sits in the
same sentence this change invalidates.

-- 
Sashiko AI review · https://netdev-ai.bots.linux.dev/sashiko/#/patchset/20260907171732.1407739-2-pablo%40netfilter.org

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero
  2026-09-08 18:04   ` netdev-bot+sashiko
@ 2026-09-08 20:22     ` Pablo Neira Ayuso
  2026-09-08 20:35     ` Pablo Neira Ayuso
  1 sibling, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-08 20:22 UTC (permalink / raw)
  To: netdev-bot+sashiko
  Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

On Tue, Sep 08, 2026 at 06:04:04PM +0000, netdev-bot+sashiko@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 1 potential
> issue(s) to consider:
> 
> Critical: 0 · High: 0 · Medium: 0 · Low: 1
> 
> - [Low] Stale/contradicted UAPI documentation for `struct
>   ip6t_ip6::proto`.
> 
> --
> 
> netfilter: ip6_tables: set F_PROTO when proto value is nonzero
> 
> This makes the kernel set IP6T_F_PROTO for any rule that carries a nonzero
> ipv6.proto, so ip6_packet_match() always performs the protocol comparison
> and extension header walk instead of skipping it when userspace left the
> flag clear. It mirrors the normalisation already done in nft_compat.c.
> 
> > diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
> > index f42fb96ef64b6..313c4aac377aa 100644
> > --- a/net/ipv6/netfilter/ip6_tables.c
> > +++ b/net/ipv6/netfilter/ip6_tables.c
> > @@ -647,6 +647,11 @@ check_entry_size_and_hooks(struct ip6t_entry *e,
> >  	/* Clear counters and comefrom */
> >  	e->counters = ((struct xt_counters) { 0, 0 });
> >  	e->comefrom = 0;
> > +
> > +	/* set F_PROTO, else ip6_packet_match won't do the right thing. */
> > +	if (e->ipv6.proto)
> > +		e->ipv6.flags |= IP6T_F_PROTO;
> > +
> >  	return 0;
> >  }
> 
> [Severity: Low]
> Should the uapi header comment be updated in the same patch?

No.

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH net 4/9] netfilter: cttimeout: prevent UAF during module unload
  2026-09-08 18:04   ` netdev-bot+sashiko
@ 2026-09-08 20:24     ` Pablo Neira Ayuso
  0 siblings, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-08 20:24 UTC (permalink / raw)
  To: netdev-bot+sashiko
  Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

On Tue, Sep 08, 2026 at 06:04:01PM +0000, netdev-bot+sashiko@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 1 potential
> issue(s) to consider:
> 
> Critical: 0 · High: 1 · Medium: 0 · Low: 0
> 
> - [High] cttimeout_exit() only drains RCU readers that reach the per-net
>   timeout storage through nf_ct_timeout_hook.
> 
> --
> 
> netfilter: cttimeout: prevent UAF during module unload
> 
> This reorders cttimeout_exit() so that nf_ct_timeout_hook is cleared and
> synchronize_net() is called before unregister_pernet_subsys() frees the
> per-net timeout storage.  That closes the window where nf_ct_set_timeout()
> could still reach the freed nfct_timeout_pernet blob through the hook.
> 
> > diff --git a/net/netfilter/nfnetlink_cttimeout.c b/net/netfilter/nfnetlink_cttimeout.c
> > index 66c2016f6049d..132c02ac7c4ea 100644
> > --- a/net/netfilter/nfnetlink_cttimeout.c
> > +++ b/net/netfilter/nfnetlink_cttimeout.c
> > @@ -652,9 +652,9 @@ static void __exit cttimeout_exit(void)
> >  {
> >  	nfnetlink_subsys_unregister(&cttimeout_subsys);
> >  
> > -	unregister_pernet_subsys(&cttimeout_ops);
> >  	RCU_INIT_POINTER(nf_ct_timeout_hook, NULL);
> >  	synchronize_net();
> > +	unregister_pernet_subsys(&cttimeout_ops);
> >  }
> 
> [Severity: High]
> Does this leave the same per-net object reachable from the netlink dump
> path during unload?
> 
> cttimeout_get_timeout() starts the dump without a module reference:
> 
> net/netfilter/nfnetlink_cttimeout.c:cttimeout_get_timeout() {
> 	if (info->nlh->nlmsg_flags & NLM_F_DUMP) {
> 		struct netlink_dump_control c = {
> 			.dump = ctnl_timeout_dump,
> 		};
> 		return netlink_dump_start(info->sk, skb, info->nlh, &c);
> 	}
> 
> With no .module set, __netlink_dump_start()'s try_module_get(control->module)
> is try_module_get(NULL), which succeeds without taking anything, and
> cb->module stays NULL.  nf_tables_api.c and nfnetlink_hook.c pass
> .module = THIS_MODULE in their netlink_dump_control for comparison.

This is a pre-existing issue. I can follow up on this.

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH net 7/9] netfilter: arp_tables: remove the 32bit compat interface
  2026-09-08 18:04   ` netdev-bot+sashiko
@ 2026-09-08 20:32     ` Pablo Neira Ayuso
  0 siblings, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-08 20:32 UTC (permalink / raw)
  To: netdev-bot+sashiko
  Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

On Tue, Sep 08, 2026 at 06:04:02PM +0000, netdev-bot+sashiko@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 1 potential
> issue(s) to consider:
> 
> Critical: 0 · High: 0 · Medium: 0 · Low: 1

This rising a lot of issues, because arptables 32bit gets broken.

We can follow up to break it more "nicely", but it is not a big issue.

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero
  2026-09-08 18:04   ` netdev-bot+sashiko
  2026-09-08 20:22     ` Pablo Neira Ayuso
@ 2026-09-08 20:35     ` Pablo Neira Ayuso
  1 sibling, 0 replies; 18+ messages in thread
From: Pablo Neira Ayuso @ 2026-09-08 20:35 UTC (permalink / raw)
  To: netdev-bot+sashiko
  Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

On Tue, Sep 08, 2026 at 06:04:04PM +0000, netdev-bot+sashiko@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 1 potential
> issue(s) to consider:
> 
> Critical: 0 · High: 0 · Medium: 0 · Low: 1
> 
> - [Low] Stale/contradicted UAPI documentation for `struct
>   ip6t_ip6::proto`.
> 
> --
> 
> netfilter: ip6_tables: set F_PROTO when proto value is nonzero
> 
> This makes the kernel set IP6T_F_PROTO for any rule that carries a nonzero
> ipv6.proto, so ip6_packet_match() always performs the protocol comparison
> and extension header walk instead of skipping it when userspace left the
> flag clear. It mirrors the normalisation already done in nft_compat.c.
> 
> > diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
> > index f42fb96ef64b6..313c4aac377aa 100644
> > --- a/net/ipv6/netfilter/ip6_tables.c
> > +++ b/net/ipv6/netfilter/ip6_tables.c
> > @@ -647,6 +647,11 @@ check_entry_size_and_hooks(struct ip6t_entry *e,
> >  	/* Clear counters and comefrom */
> >  	e->counters = ((struct xt_counters) { 0, 0 });
> >  	e->comefrom = 0;
> > +
> > +	/* set F_PROTO, else ip6_packet_match won't do the right thing. */
> > +	if (e->ipv6.proto)
> > +		e->ipv6.flags |= IP6T_F_PROTO;
> > +
> >  	return 0;
> >  }
> 
> [Severity: Low]
> Should the uapi header comment be updated in the same patch?  The
> description of struct ip6t_ip6::proto in
> include/uapi/linux/netfilter_ipv6/ip6_tables.h still documents the
> opposite contract:
> 
> 	/* Upper protocol number
> 	 * ...
> 	 * - You also need to set IP6T_FLAGS_PROTO to "flags" to check protocol.
> 	 */

That is still the indeed recommended practise, so no, comment must be
not updated.

This is just makes a work-around for broken userspace code that has no
real usecase other than triggering a bug.

Quite a bit of noise from LLM, one pre-existing issue found, but other
than that, just lengthy text noise.

^ permalink raw reply	[flat|nested] 18+ messages in thread

* Re: [PATCH net 1/9] ipvs: reject invalid states in connection template sync records
  2026-09-07 17:17 ` [PATCH net 1/9] ipvs: reject invalid states in connection template sync records Pablo Neira Ayuso
@ 2026-09-08 21:00   ` patchwork-bot+netdevbpf
  0 siblings, 0 replies; 18+ messages in thread
From: patchwork-bot+netdevbpf @ 2026-09-08 21:00 UTC (permalink / raw)
  To: Pablo Neira Ayuso
  Cc: netfilter-devel, davem, netdev, kuba, pabeni, edumazet, horms, fw,
	ja

Hello:

This series was applied to netdev/net.git (main)
by Pablo Neira Ayuso <pablo@netfilter.org>:

On Mon,  7 Sep 2026 19:17:24 +0200 you wrote:
> From: Kyle Zeng <kylebot@openai.com>
> 
> IPVS sync receivers validate protocol states before creating or updating a
> connection. For connection templates, however, they only log states outside
> the template state range and still store the value in the connection.
> 
> A template can be returned by ordinary connection lookup. TCP and SCTP then
> use the invalid state as an index into their transition tables.
> 
> [...]

Here is the summary with links:
  - [net,1/9] ipvs: reject invalid states in connection template sync records
    https://git.kernel.org/netdev/net/c/74cb39735b6c
  - [net,2/9] ipvs: fix reversed sequence option serialization
    https://git.kernel.org/netdev/net/c/b04578b74f2d
  - [net,3/9] netfilter: nf_conntrack_sip: fix OOB read in sip_skip_whitespace()
    https://git.kernel.org/netdev/net/c/e8f8231824b5
  - [net,4/9] netfilter: cttimeout: prevent UAF during module unload
    https://git.kernel.org/netdev/net/c/fec9b1de0d02
  - [net,5/9] netfilter: nf_log: unregister loggers before per-net teardown
    https://git.kernel.org/netdev/net/c/2c018cc4842c
  - [net,6/9] netfilter: nfnetlink_log: cope with concurrent instance destruction
    https://git.kernel.org/netdev/net/c/387d744fa7e4
  - [net,7/9] netfilter: arp_tables: remove the 32bit compat interface
    https://git.kernel.org/netdev/net/c/0bd7ed1a3263
  - [net,8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero
    https://git.kernel.org/netdev/net/c/da4afc5a956d
  - [net,9/9] netfilter: report NLM_F_DUMP_FILTERED when all is filtered out
    https://git.kernel.org/netdev/net/c/7a099b347fef

You are awesome, thank you!
-- 
Deet-doot-dot, I am a bot.
https://korg.docs.kernel.org/patchwork/pwbot.html



^ permalink raw reply	[flat|nested] 18+ messages in thread

end of thread, other threads:[~2026-09-08 21:01 UTC | newest]

Thread overview: 18+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-09-07 17:17 [PATCH net,v2 0/9] Netfilter/IPVS fixes for net Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 1/9] ipvs: reject invalid states in connection template sync records Pablo Neira Ayuso
2026-09-08 21:00   ` patchwork-bot+netdevbpf
2026-09-07 17:17 ` [PATCH net 2/9] ipvs: fix reversed sequence option serialization Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 3/9] netfilter: nf_conntrack_sip: fix OOB read in sip_skip_whitespace() Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 4/9] netfilter: cttimeout: prevent UAF during module unload Pablo Neira Ayuso
2026-09-08 18:04   ` netdev-bot+sashiko
2026-09-08 20:24     ` Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 5/9] netfilter: nf_log: unregister loggers before per-net teardown Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 6/9] netfilter: nfnetlink_log: cope with concurrent instance destruction Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 7/9] netfilter: arp_tables: remove the 32bit compat interface Pablo Neira Ayuso
2026-09-08 18:04   ` netdev-bot+sashiko
2026-09-08 20:32     ` Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 8/9] netfilter: ip6_tables: set F_PROTO when proto value is nonzero Pablo Neira Ayuso
2026-09-08 18:04   ` netdev-bot+sashiko
2026-09-08 20:22     ` Pablo Neira Ayuso
2026-09-08 20:35     ` Pablo Neira Ayuso
2026-09-07 17:17 ` [PATCH net 9/9] netfilter: report NLM_F_DUMP_FILTERED when all is filtered out Pablo Neira Ayuso

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).