diff mbox

nfnetlink: add a new subsystem to advertise tables update

Message ID 1348501182-12470-1-git-send-email-nicolas.dichtel@6wind.com
State Rejected
Headers show

Commit Message

Nicolas Dichtel Sept. 24, 2012, 3:39 p.m. UTC
For now, there is no way to be informed, when a netfilter table is updated.

With this patch a netlink message is sent when a table is updated, with the
name of the table and the family.
For this purpose, a new subsystem (with a new group) has been added.

Signed-off-by: Nicolas Dichtel <nicolas.dichtel@6wind.com>
---
 include/linux/netfilter/nfnetlink.h        |  5 ++-
 include/linux/netfilter/nfnetlink_compat.h |  1 +
 include/linux/netfilter/nfnetlink_tables.h | 24 +++++++++++
 include/linux/netfilter/x_tables.h         |  3 +-
 include/net/netfilter/nfnetlink_tables.h   |  6 +++
 net/ipv4/netfilter/arp_tables.c            |  2 +-
 net/ipv4/netfilter/ip_tables.c             |  2 +-
 net/ipv6/netfilter/ip6_tables.c            |  2 +-
 net/netfilter/Kconfig                      |  9 +++++
 net/netfilter/Makefile                     |  1 +
 net/netfilter/nfnetlink_tables.c           | 65 ++++++++++++++++++++++++++++++
 net/netfilter/x_tables.c                   | 11 ++++-
 12 files changed, 124 insertions(+), 7 deletions(-)
 create mode 100644 include/linux/netfilter/nfnetlink_tables.h
 create mode 100644 include/net/netfilter/nfnetlink_tables.h
 create mode 100644 net/netfilter/nfnetlink_tables.c

Comments

Nicolas Dichtel Oct. 2, 2012, 1:06 p.m. UTC | #1
The following patch is an example of a userspace tools (in fact, iptables)
that use the new netlink API to monitor tables activity.

I will also send a patch against libnfnetlink to update linux includes with
this new feature.

Maybe another API can be used for this feature: adding a setsockopt() on an
iptc socket to enable monitoring. When a table is updated, a packet (built with
CMSG_* macro for example) can be sent over all sockets that monitor tables
acitivity (like km sockets in IPsec). I know that this socket was used only with
[g|s]etsockopt(), but this can avoid adding another netlink API.

Comments are welcome.

Regards,
Nicolas

--
To unsubscribe from this list: send the line "unsubscribe netfilter-devel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Nicolas Dichtel Oct. 15, 2012, 1:10 p.m. UTC | #2
Le 02/10/2012 15:06, Nicolas Dichtel a écrit :
> The following patch is an example of a userspace tools (in fact, iptables)
> that use the new netlink API to monitor tables activity.
>
> I will also send a patch against libnfnetlink to update linux includes with
> this new feature.
>
> Maybe another API can be used for this feature: adding a setsockopt() on an
> iptc socket to enable monitoring. When a table is updated, a packet (built with
> CMSG_* macro for example) can be sent over all sockets that monitor tables
> acitivity (like km sockets in IPsec). I know that this socket was used only with
> [g|s]etsockopt(), but this can avoid adding another netlink API.
>
> Comments are welcome.
Any feedback about this patch or the other proposed API?


Regards,
Nicolas
--
To unsubscribe from this list: send the line "unsubscribe netfilter-devel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Nicolas Dichtel Oct. 25, 2012, 12:52 p.m. UTC | #3
Le 15/10/2012 15:10, Nicolas Dichtel a écrit :
> Le 02/10/2012 15:06, Nicolas Dichtel a écrit :
>> The following patch is an example of a userspace tools (in fact, iptables)
>> that use the new netlink API to monitor tables activity.
>>
>> I will also send a patch against libnfnetlink to update linux includes with
>> this new feature.
>>
>> Maybe another API can be used for this feature: adding a setsockopt() on an
>> iptc socket to enable monitoring. When a table is updated, a packet (built with
>> CMSG_* macro for example) can be sent over all sockets that monitor tables
>> acitivity (like km sockets in IPsec). I know that this socket was used only with
>> [g|s]etsockopt(), but this can avoid adding another netlink API.
>>
>> Comments are welcome.
> Any feedback about this patch or the other proposed API?
Still no comment about this feature? Maybe another option to solve the problem?


Regards,
Nicolas
--
To unsubscribe from this list: send the line "unsubscribe netfilter-devel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Pablo Neira Ayuso Oct. 25, 2012, 5:19 p.m. UTC | #4
Hi Nicolas,

On Thu, Oct 25, 2012 at 02:52:48PM +0200, Nicolas Dichtel wrote:
> Le 15/10/2012 15:10, Nicolas Dichtel a écrit :
> >Le 02/10/2012 15:06, Nicolas Dichtel a écrit :
> >>The following patch is an example of a userspace tools (in fact, iptables)
> >>that use the new netlink API to monitor tables activity.
> >>
> >>I will also send a patch against libnfnetlink to update linux includes with
> >>this new feature.
> >>
> >>Maybe another API can be used for this feature: adding a setsockopt() on an
> >>iptc socket to enable monitoring. When a table is updated, a packet (built with
> >>CMSG_* macro for example) can be sent over all sockets that monitor tables
> >>acitivity (like km sockets in IPsec). I know that this socket was used only with
> >>[g|s]etsockopt(), but this can avoid adding another netlink API.
> >>
> >>Comments are welcome.
> >Any feedback about this patch or the other proposed API?
>
> Still no comment about this feature? Maybe another option to solve the problem?

Adding a new nfnetlink subsystem to just reports table updates seems
a bit too much to me.

I'd aim to the nftables proposal that I just made. If this doesn't
happen in a reasonable amount of time, get back to the mailing list
and push us again to get this in.

Thanks.
--
To unsubscribe from this list: send the line "unsubscribe netfilter-devel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Nicolas Dichtel Oct. 26, 2012, 8:05 a.m. UTC | #5
Le 25/10/2012 19:19, Pablo Neira Ayuso a écrit :
> Hi Nicolas,
>
> On Thu, Oct 25, 2012 at 02:52:48PM +0200, Nicolas Dichtel wrote:
>> Le 15/10/2012 15:10, Nicolas Dichtel a écrit :
>>> Le 02/10/2012 15:06, Nicolas Dichtel a écrit :
>>>> The following patch is an example of a userspace tools (in fact, iptables)
>>>> that use the new netlink API to monitor tables activity.
>>>>
>>>> I will also send a patch against libnfnetlink to update linux includes with
>>>> this new feature.
>>>>
>>>> Maybe another API can be used for this feature: adding a setsockopt() on an
>>>> iptc socket to enable monitoring. When a table is updated, a packet (built with
>>>> CMSG_* macro for example) can be sent over all sockets that monitor tables
>>>> acitivity (like km sockets in IPsec). I know that this socket was used only with
>>>> [g|s]etsockopt(), but this can avoid adding another netlink API.
>>>>
>>>> Comments are welcome.
>>> Any feedback about this patch or the other proposed API?
>>
>> Still no comment about this feature? Maybe another option to solve the problem?
>
> Adding a new nfnetlink subsystem to just reports table updates seems
> a bit too much to me.
What about the second proposal? Sending messages through the iptc socket?
If you have some other ideas, we can change the design of the implementation, 
it's not a problem.

>
> I'd aim to the nftables proposal that I just made. If this doesn't
> happen in a reasonable amount of time, get back to the mailing list
> and push us again to get this in.
There seems to be two competitors for the next generation: nftables vs xtables2. 
Can we not start with a first implementation with the current xtables. Then, we 
will work to have a continuity of this feature in the next generation.
--
To unsubscribe from this list: send the line "unsubscribe netfilter-devel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Pablo Neira Ayuso Oct. 26, 2012, 8:44 a.m. UTC | #6
Hi Nicolas,

On Fri, Oct 26, 2012 at 10:05:25AM +0200, Nicolas Dichtel wrote:
> Le 25/10/2012 19:19, Pablo Neira Ayuso a écrit :
> >Hi Nicolas,
> >
> >On Thu, Oct 25, 2012 at 02:52:48PM +0200, Nicolas Dichtel wrote:
> >>Le 15/10/2012 15:10, Nicolas Dichtel a écrit :
> >>>Le 02/10/2012 15:06, Nicolas Dichtel a écrit :
> >>>>The following patch is an example of a userspace tools (in fact, iptables)
> >>>>that use the new netlink API to monitor tables activity.
> >>>>
> >>>>I will also send a patch against libnfnetlink to update linux includes with
> >>>>this new feature.
> >>>>
> >>>>Maybe another API can be used for this feature: adding a setsockopt() on an
> >>>>iptc socket to enable monitoring. When a table is updated, a packet (built with
> >>>>CMSG_* macro for example) can be sent over all sockets that monitor tables
> >>>>acitivity (like km sockets in IPsec). I know that this socket was used only with
> >>>>[g|s]etsockopt(), but this can avoid adding another netlink API.
> >>>>
> >>>>Comments are welcome.
> >>>Any feedback about this patch or the other proposed API?
> >>
> >>Still no comment about this feature? Maybe another option to solve the problem?
> >
> >Adding a new nfnetlink subsystem to just reports table updates seems
> >a bit too much to me.
>
> What about the second proposal? Sending messages through the iptc socket?
> If you have some other ideas, we can change the design of the
> implementation, it's not a problem.

It's been four weeks since you posted your patch and you've been
asking for feedback *every single week* with no results at all. So,
nobody cares.

I see no existing FOSS projects using using this (apart from you
iptables change to report events).

And I already told you, I don't think it makes sense to maintain more
than one firewalling subsystem using netlink as interface.

Please, stop.
--
To unsubscribe from this list: send the line "unsubscribe netfilter-devel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
diff mbox

Patch

diff --git a/include/linux/netfilter/nfnetlink.h b/include/linux/netfilter/nfnetlink.h
index 18341cd..2470a1c 100644
--- a/include/linux/netfilter/nfnetlink.h
+++ b/include/linux/netfilter/nfnetlink.h
@@ -18,6 +18,8 @@  enum nfnetlink_groups {
 #define NFNLGRP_CONNTRACK_EXP_UPDATE	NFNLGRP_CONNTRACK_EXP_UPDATE
 	NFNLGRP_CONNTRACK_EXP_DESTROY,
 #define NFNLGRP_CONNTRACK_EXP_DESTROY	NFNLGRP_CONNTRACK_EXP_DESTROY
+	NFNLGRP_TABLES,
+#define NFNLGRP_TABLES			NFNLGRP_TABLES
 	__NFNLGRP_MAX,
 };
 #define NFNLGRP_MAX	(__NFNLGRP_MAX - 1)
@@ -51,7 +53,8 @@  struct nfgenmsg {
 #define NFNL_SUBSYS_ACCT		7
 #define NFNL_SUBSYS_CTNETLINK_TIMEOUT	8
 #define NFNL_SUBSYS_CTHELPER		9
-#define NFNL_SUBSYS_COUNT		10
+#define NFNL_SUBSYS_TABLES		10
+#define NFNL_SUBSYS_COUNT		11
 
 #ifdef __KERNEL__
 
diff --git a/include/linux/netfilter/nfnetlink_compat.h b/include/linux/netfilter/nfnetlink_compat.h
index ffb9503..a4cab85 100644
--- a/include/linux/netfilter/nfnetlink_compat.h
+++ b/include/linux/netfilter/nfnetlink_compat.h
@@ -13,6 +13,7 @@ 
 #define NF_NETLINK_CONNTRACK_EXP_NEW		0x00000008
 #define NF_NETLINK_CONNTRACK_EXP_UPDATE		0x00000010
 #define NF_NETLINK_CONNTRACK_EXP_DESTROY	0x00000020
+#define NF_NETLINK_TABLES			0x00000040
 
 /* Generic structure for encapsulation optional netfilter information.
  * It is reminiscent of sockaddr, but with sa_family replaced
diff --git a/include/linux/netfilter/nfnetlink_tables.h b/include/linux/netfilter/nfnetlink_tables.h
new file mode 100644
index 0000000..630dc9b
--- /dev/null
+++ b/include/linux/netfilter/nfnetlink_tables.h
@@ -0,0 +1,24 @@ 
+#ifndef _NFNETLINK_TABLES_H
+#define _NFNETLINK_TABLES_H
+
+/* This file describes the netlink messages (i.e. 'protocol packets'),
+ * and not any kind of function definitions.  It is shared between kernel and
+ * userspace.  Don't put kernel specific stuff in here */
+
+#include <linux/types.h>
+#include <linux/netfilter/nfnetlink.h>
+
+enum nftbl_types {
+	NFTBL_UPDATE,
+
+	NFTBL_MSG_MAX
+};
+
+enum nfnl_tables_attr_type {
+        NFTBLA_UNSPEC,
+        NFTBLA_TABLENAME,
+        __NFTBLA_MAX
+};
+#define NFTBLA_MAX (__NFTBLA_MAX - 1)
+
+#endif /* _NFNETLINK_TABLES_H */
diff --git a/include/linux/netfilter/x_tables.h b/include/linux/netfilter/x_tables.h
index 8d674a7..280612d 100644
--- a/include/linux/netfilter/x_tables.h
+++ b/include/linux/netfilter/x_tables.h
@@ -432,7 +432,8 @@  extern struct xt_table *xt_register_table(struct net *net,
 					  struct xt_table_info *newinfo);
 extern void *xt_unregister_table(struct xt_table *table);
 
-extern struct xt_table_info *xt_replace_table(struct xt_table *table,
+extern struct xt_table_info *xt_replace_table(struct net *net,
+					      struct xt_table *table,
 					      unsigned int num_counters,
 					      struct xt_table_info *newinfo,
 					      int *error);
diff --git a/include/net/netfilter/nfnetlink_tables.h b/include/net/netfilter/nfnetlink_tables.h
new file mode 100644
index 0000000..0d87b69
--- /dev/null
+++ b/include/net/netfilter/nfnetlink_tables.h
@@ -0,0 +1,6 @@ 
+#ifndef _KER_NFNETLINK_TABLES_H
+#define _KER_NFNETLINK_TABLES_H
+
+int nfnl_msgtables_send_update(struct net *net, const struct xt_table *table);
+
+#endif /* _KER_NFNETLINK_TABLES_H */
diff --git a/net/ipv4/netfilter/arp_tables.c b/net/ipv4/netfilter/arp_tables.c
index 97e61ea..6fd6002 100644
--- a/net/ipv4/netfilter/arp_tables.c
+++ b/net/ipv4/netfilter/arp_tables.c
@@ -1014,7 +1014,7 @@  static int __do_replace(struct net *net, const char *name,
 		goto put_module;
 	}
 
-	oldinfo = xt_replace_table(t, num_counters, newinfo, &ret);
+	oldinfo = xt_replace_table(net, t, num_counters, newinfo, &ret);
 	if (!oldinfo)
 		goto put_module;
 
diff --git a/net/ipv4/netfilter/ip_tables.c b/net/ipv4/netfilter/ip_tables.c
index 170b1fd..04dfa7f 100644
--- a/net/ipv4/netfilter/ip_tables.c
+++ b/net/ipv4/netfilter/ip_tables.c
@@ -1202,7 +1202,7 @@  __do_replace(struct net *net, const char *name, unsigned int valid_hooks,
 		goto put_module;
 	}
 
-	oldinfo = xt_replace_table(t, num_counters, newinfo, &ret);
+	oldinfo = xt_replace_table(net, t, num_counters, newinfo, &ret);
 	if (!oldinfo)
 		goto put_module;
 
diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
index d7cb045..6741442 100644
--- a/net/ipv6/netfilter/ip6_tables.c
+++ b/net/ipv6/netfilter/ip6_tables.c
@@ -1212,7 +1212,7 @@  __do_replace(struct net *net, const char *name, unsigned int valid_hooks,
 		goto put_module;
 	}
 
-	oldinfo = xt_replace_table(t, num_counters, newinfo, &ret);
+	oldinfo = xt_replace_table(net, t, num_counters, newinfo, &ret);
 	if (!oldinfo)
 		goto put_module;
 
diff --git a/net/netfilter/Kconfig b/net/netfilter/Kconfig
index 3f4b3b4..3ca9de4 100644
--- a/net/netfilter/Kconfig
+++ b/net/netfilter/Kconfig
@@ -32,6 +32,15 @@  config NETFILTER_NETLINK_LOG
 	  and is also scheduled to replace the old syslog-based ipt_LOG
 	  and ip6t_LOG modules.
 
+config NETFILTER_NETLINK_TABLES
+	tristate "Netfilter Tables events over NFNETLINK interface"
+	depends on NETFILTER_XTABLES
+	select NETFILTER_NETLINK
+	default m
+	help
+	  If this option is enabled, the kernel will avertise operations
+	  on xt_tables via NFNETLINK.
+
 config NF_CONNTRACK
 	tristate "Netfilter connection tracking support"
 	default m if NETFILTER_ADVANCED=n
diff --git a/net/netfilter/Makefile b/net/netfilter/Makefile
index 0baa3f1..07d5c5e 100644
--- a/net/netfilter/Makefile
+++ b/net/netfilter/Makefile
@@ -13,6 +13,7 @@  nfnetlink_queue-y := nfnetlink_queue_core.o
 nfnetlink_queue-$(CONFIG_NETFILTER_NETLINK_QUEUE_CT) += nfnetlink_queue_ct.o
 obj-$(CONFIG_NETFILTER_NETLINK_QUEUE) += nfnetlink_queue.o
 obj-$(CONFIG_NETFILTER_NETLINK_LOG) += nfnetlink_log.o
+obj-$(CONFIG_NETFILTER_NETLINK_TABLES) += nfnetlink_tables.o
 
 # connection tracking
 obj-$(CONFIG_NF_CONNTRACK) += nf_conntrack.o
diff --git a/net/netfilter/nfnetlink_tables.c b/net/netfilter/nfnetlink_tables.c
new file mode 100644
index 0000000..dce1092
--- /dev/null
+++ b/net/netfilter/nfnetlink_tables.c
@@ -0,0 +1,65 @@ 
+/*
+ * (C) 2012 by Nicolas Dichtel <nicolas.dichtel@6wind.com>
+ * (C) 2012 by 6WIND <http://www.6wind.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation (or any later at your option).
+ */
+#include <linux/module.h>
+#include <linux/skbuff.h>
+#include <linux/init.h>
+#include <linux/netfilter.h>
+#include <linux/netlink.h>
+#include <linux/netfilter/x_tables.h>
+#include <linux/netfilter/nfnetlink.h>
+#include <linux/netfilter/nfnetlink_tables.h>
+
+int nfnl_msgtables_send_update(struct net *net, const struct xt_table *table)
+{
+	struct sk_buff *skb;
+	struct nlmsghdr *nlh;
+	struct nfgenmsg *nfmsg;
+	int size, err;
+
+	size = NLMSG_ALIGN(sizeof(struct nfgenmsg)) +
+	       nla_total_size(sizeof(char[XT_TABLE_MAXNAMELEN]));
+	skb = nlmsg_new(size, GFP_ATOMIC);
+	if (skb == NULL)
+		goto errout;
+
+	nlh = nlmsg_put(skb, 0, 0, NFNL_SUBSYS_TABLES << 8 | NFTBL_UPDATE,
+			sizeof(struct nfgenmsg), 0);
+	if (nlh == NULL)
+		goto nlmsg_failure;
+
+	nfmsg = nlmsg_data(nlh);
+	nfmsg->nfgen_family = table->af;
+	nfmsg->version = NFNETLINK_V0;
+	nfmsg->res_id = 0;
+
+	if (nla_put_string(skb, NFTBLA_TABLENAME, table->name))
+		 goto nla_put_failure;
+
+	nlmsg_end(skb, nlh);
+
+	err = nfnetlink_send(skb, net, 0, NFNLGRP_TABLES, 0, 0);
+	if (err == -ENOBUFS || err == -EAGAIN)
+		return -ENOBUFS;
+
+	return 0;
+
+nla_put_failure:
+	nlmsg_cancel(skb, nlh);
+nlmsg_failure:
+	kfree_skb(skb);
+errout:
+	if (nfnetlink_set_err(net, 0, NFNLGRP_TABLES, -ENOBUFS) > 0)
+		return -ENOBUFS;
+
+	return 0;
+}
+EXPORT_SYMBOL_GPL(nfnl_msgtables_send_update);
+
+MODULE_LICENSE("GPL");
+MODULE_AUTHOR("Nicolas Dichtel <nicolas.dichtel@6wind.com>");
diff --git a/net/netfilter/x_tables.c b/net/netfilter/x_tables.c
index 8d987c3..8ea4dc3 100644
--- a/net/netfilter/x_tables.c
+++ b/net/netfilter/x_tables.c
@@ -32,6 +32,9 @@ 
 #include <linux/netfilter_ipv4/ip_tables.h>
 #include <linux/netfilter_ipv6/ip6_tables.h>
 #include <linux/netfilter_arp/arp_tables.h>
+#if IS_ENABLED (CONFIG_NETFILTER_NETLINK_TABLES)
+#include <net/netfilter/nfnetlink_tables.h>
+#endif
 
 MODULE_LICENSE("GPL");
 MODULE_AUTHOR("Harald Welte <laforge@netfilter.org>");
@@ -805,7 +808,7 @@  static int xt_jumpstack_alloc(struct xt_table_info *i)
 }
 
 struct xt_table_info *
-xt_replace_table(struct xt_table *table,
+xt_replace_table(struct net *net, struct xt_table *table,
 	      unsigned int num_counters,
 	      struct xt_table_info *newinfo,
 	      int *error)
@@ -843,6 +846,10 @@  xt_replace_table(struct xt_table *table,
 	 */
 	local_bh_enable();
 
+#if IS_ENABLED(CONFIG_NETFILTER_NETLINK_TABLES)
+	nfnl_msgtables_send_update(net, table);
+#endif
+
 #ifdef CONFIG_AUDIT
 	if (audit_enabled) {
 		struct audit_buffer *ab;
@@ -893,7 +900,7 @@  struct xt_table *xt_register_table(struct net *net,
 	/* Simplifies replace_table code. */
 	table->private = bootstrap;
 
-	if (!xt_replace_table(table, 0, newinfo, &ret))
+	if (!xt_replace_table(net, table, 0, newinfo, &ret))
 		goto unlock;
 
 	private = table->private;