aboutsummaryrefslogtreecommitdiffstats
path: root/net
diff options
context:
space:
mode:
authorPablo Neira Ayuso <pablo@netfilter.org>2014-06-22 18:28:18 -0400
committerPablo Neira Ayuso <pablo@netfilter.org>2014-06-27 07:20:47 -0400
commit960649d1923c31a7f771162fa0eef00210044262 (patch)
tree7e9b8e09933598eb9604a710874e2a3ade7efd3d /net
parent35b9395104d51f4b85847fa72a1bf4136d36c56e (diff)
netfilter: bridge: add generic packet logger
This adds the generic plain text packet loggger for bridged packets. It routes the logging message to the real protocol packet logger. I decided not to refactor the ebt_log code for two reasons: 1) The ebt_log output is not consistent with the IPv4 and IPv6 Netfilter packet loggers. The output is different for no good reason and it adds redundant code to handle packet logging. 2) To avoid breaking backward compatibility for applications outthere that are parsing the specific ebt_log output, the ebt_log output has been left as is. So only nftables will use the new consistent logging format for logged bridged packets. More decisions coming in this patch: 1) This also removes ebt_log as default logger for bridged packets. Thus, nf_log_packet() routes packet to this new packet logger instead. This doesn't break backward compatibility since nf_log_packet() is not used to log packets in plain text format from anywhere in the ebtables/netfilter bridge code. 2) The new bridge packet logger also performs a lazy request to register the real IPv4, ARP and IPv6 netfilter packet loggers. If the real protocol logger is no available (not compiled or the module is not available in the system, not packet logging happens. Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
Diffstat (limited to 'net')
-rw-r--r--net/bridge/netfilter/Kconfig3
-rw-r--r--net/bridge/netfilter/Makefile3
-rw-r--r--net/bridge/netfilter/ebt_log.c48
-rw-r--r--net/bridge/netfilter/nf_log_bridge.c96
-rw-r--r--net/netfilter/nf_log.c7
5 files changed, 114 insertions, 43 deletions
diff --git a/net/bridge/netfilter/Kconfig b/net/bridge/netfilter/Kconfig
index 3a76ac7b7141..4ce0b313f72c 100644
--- a/net/bridge/netfilter/Kconfig
+++ b/net/bridge/netfilter/Kconfig
@@ -14,6 +14,9 @@ config NFT_BRIDGE_META
14 help 14 help
15 Add support for bridge dedicated meta key. 15 Add support for bridge dedicated meta key.
16 16
17config NF_LOG_BRIDGE
18 tristate "Bridge packet logging"
19
17endif # NF_TABLES_BRIDGE 20endif # NF_TABLES_BRIDGE
18 21
19menuconfig BRIDGE_NF_EBTABLES 22menuconfig BRIDGE_NF_EBTABLES
diff --git a/net/bridge/netfilter/Makefile b/net/bridge/netfilter/Makefile
index 6f2f3943d66f..1f78ea0d90e4 100644
--- a/net/bridge/netfilter/Makefile
+++ b/net/bridge/netfilter/Makefile
@@ -5,6 +5,9 @@
5obj-$(CONFIG_NF_TABLES_BRIDGE) += nf_tables_bridge.o 5obj-$(CONFIG_NF_TABLES_BRIDGE) += nf_tables_bridge.o
6obj-$(CONFIG_NFT_BRIDGE_META) += nft_meta_bridge.o 6obj-$(CONFIG_NFT_BRIDGE_META) += nft_meta_bridge.o
7 7
8# packet logging
9obj-$(CONFIG_NF_LOG_BRIDGE) += nf_log_bridge.o
10
8obj-$(CONFIG_BRIDGE_NF_EBTABLES) += ebtables.o 11obj-$(CONFIG_BRIDGE_NF_EBTABLES) += ebtables.o
9 12
10# tables 13# tables
diff --git a/net/bridge/netfilter/ebt_log.c b/net/bridge/netfilter/ebt_log.c
index 0577477aacd8..17f2e4bc2a29 100644
--- a/net/bridge/netfilter/ebt_log.c
+++ b/net/bridge/netfilter/ebt_log.c
@@ -186,6 +186,10 @@ ebt_log_tg(struct sk_buff *skb, const struct xt_action_param *par)
186 li.u.log.level = info->loglevel; 186 li.u.log.level = info->loglevel;
187 li.u.log.logflags = info->bitmask; 187 li.u.log.logflags = info->bitmask;
188 188
189 /* Remember that we have to use ebt_log_packet() not to break backward
190 * compatibility. We cannot use the default bridge packet logger via
191 * nf_log_packet() with NFT_LOG_TYPE_LOG here. --Pablo
192 */
189 if (info->bitmask & EBT_LOG_NFLOG) 193 if (info->bitmask & EBT_LOG_NFLOG)
190 nf_log_packet(net, NFPROTO_BRIDGE, par->hooknum, skb, 194 nf_log_packet(net, NFPROTO_BRIDGE, par->hooknum, skb,
191 par->in, par->out, &li, "%s", info->prefix); 195 par->in, par->out, &li, "%s", info->prefix);
@@ -205,55 +209,13 @@ static struct xt_target ebt_log_tg_reg __read_mostly = {
205 .me = THIS_MODULE, 209 .me = THIS_MODULE,
206}; 210};
207 211
208static struct nf_logger ebt_log_logger __read_mostly = {
209 .name = "ebt_log",
210 .type = NF_LOG_TYPE_LOG,
211 .logfn = &ebt_log_packet,
212 .me = THIS_MODULE,
213};
214
215static int __net_init ebt_log_net_init(struct net *net)
216{
217 nf_log_set(net, NFPROTO_BRIDGE, &ebt_log_logger);
218 return 0;
219}
220
221static void __net_exit ebt_log_net_fini(struct net *net)
222{
223 nf_log_unset(net, &ebt_log_logger);
224}
225
226static struct pernet_operations ebt_log_net_ops = {
227 .init = ebt_log_net_init,
228 .exit = ebt_log_net_fini,
229};
230
231static int __init ebt_log_init(void) 212static int __init ebt_log_init(void)
232{ 213{
233 int ret; 214 return xt_register_target(&ebt_log_tg_reg);
234
235 ret = register_pernet_subsys(&ebt_log_net_ops);
236 if (ret < 0)
237 goto err_pernet;
238
239 ret = xt_register_target(&ebt_log_tg_reg);
240 if (ret < 0)
241 goto err_target;
242
243 nf_log_register(NFPROTO_BRIDGE, &ebt_log_logger);
244
245 return ret;
246
247err_target:
248 unregister_pernet_subsys(&ebt_log_net_ops);
249err_pernet:
250 return ret;
251} 215}
252 216
253static void __exit ebt_log_fini(void) 217static void __exit ebt_log_fini(void)
254{ 218{
255 unregister_pernet_subsys(&ebt_log_net_ops);
256 nf_log_unregister(&ebt_log_logger);
257 xt_unregister_target(&ebt_log_tg_reg); 219 xt_unregister_target(&ebt_log_tg_reg);
258} 220}
259 221
diff --git a/net/bridge/netfilter/nf_log_bridge.c b/net/bridge/netfilter/nf_log_bridge.c
new file mode 100644
index 000000000000..5d9953a90929
--- /dev/null
+++ b/net/bridge/netfilter/nf_log_bridge.c
@@ -0,0 +1,96 @@
1/*
2 * (C) 2014 by Pablo Neira Ayuso <pablo@netfilter.org>
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License version 2 as
6 * published by the Free Software Foundation.
7 */
8
9#include <linux/module.h>
10#include <linux/spinlock.h>
11#include <linux/skbuff.h>
12#include <linux/if_bridge.h>
13#include <linux/ip.h>
14#include <net/route.h>
15
16#include <linux/netfilter.h>
17#include <net/netfilter/nf_log.h>
18
19static void nf_log_bridge_packet(struct net *net, u_int8_t pf,
20 unsigned int hooknum,
21 const struct sk_buff *skb,
22 const struct net_device *in,
23 const struct net_device *out,
24 const struct nf_loginfo *loginfo,
25 const char *prefix)
26{
27 switch (eth_hdr(skb)->h_proto) {
28 case htons(ETH_P_IP):
29 nf_log_packet(net, NFPROTO_IPV4, hooknum, skb, in, out,
30 loginfo, "%s", prefix);
31 break;
32 case htons(ETH_P_IPV6):
33 nf_log_packet(net, NFPROTO_IPV6, hooknum, skb, in, out,
34 loginfo, "%s", prefix);
35 break;
36 case htons(ETH_P_ARP):
37 case htons(ETH_P_RARP):
38 nf_log_packet(net, NFPROTO_ARP, hooknum, skb, in, out,
39 loginfo, "%s", prefix);
40 break;
41 }
42}
43
44static struct nf_logger nf_bridge_logger __read_mostly = {
45 .name = "nf_log_bridge",
46 .type = NF_LOG_TYPE_LOG,
47 .logfn = nf_log_bridge_packet,
48 .me = THIS_MODULE,
49};
50
51static int __net_init nf_log_bridge_net_init(struct net *net)
52{
53 nf_log_set(net, NFPROTO_BRIDGE, &nf_bridge_logger);
54 return 0;
55}
56
57static void __net_exit nf_log_bridge_net_exit(struct net *net)
58{
59 nf_log_unset(net, &nf_bridge_logger);
60}
61
62static struct pernet_operations nf_log_bridge_net_ops = {
63 .init = nf_log_bridge_net_init,
64 .exit = nf_log_bridge_net_exit,
65};
66
67static int __init nf_log_bridge_init(void)
68{
69 int ret;
70
71 /* Request to load the real packet loggers. */
72 nf_logger_request_module(NFPROTO_IPV4, NF_LOG_TYPE_LOG);
73 nf_logger_request_module(NFPROTO_IPV6, NF_LOG_TYPE_LOG);
74 nf_logger_request_module(NFPROTO_ARP, NF_LOG_TYPE_LOG);
75
76 ret = register_pernet_subsys(&nf_log_bridge_net_ops);
77 if (ret < 0)
78 return ret;
79
80 nf_log_register(NFPROTO_BRIDGE, &nf_bridge_logger);
81 return 0;
82}
83
84static void __exit nf_log_bridge_exit(void)
85{
86 unregister_pernet_subsys(&nf_log_bridge_net_ops);
87 nf_log_unregister(&nf_bridge_logger);
88}
89
90module_init(nf_log_bridge_init);
91module_exit(nf_log_bridge_exit);
92
93MODULE_AUTHOR("Pablo Neira Ayuso <pablo@netfilter.org>");
94MODULE_DESCRIPTION("Netfilter bridge packet logging");
95MODULE_LICENSE("GPL");
96MODULE_ALIAS_NF_LOGGER(AF_BRIDGE, 0);
diff --git a/net/netfilter/nf_log.c b/net/netfilter/nf_log.c
index 0b2161c689e0..daad6022c689 100644
--- a/net/netfilter/nf_log.c
+++ b/net/netfilter/nf_log.c
@@ -132,6 +132,13 @@ void nf_log_unbind_pf(struct net *net, u_int8_t pf)
132} 132}
133EXPORT_SYMBOL(nf_log_unbind_pf); 133EXPORT_SYMBOL(nf_log_unbind_pf);
134 134
135void nf_logger_request_module(int pf, enum nf_log_type type)
136{
137 if (loggers[pf][type] == NULL)
138 request_module("nf-logger-%u-%u", pf, type);
139}
140EXPORT_SYMBOL_GPL(nf_logger_request_module);
141
135int nf_logger_find_get(int pf, enum nf_log_type type) 142int nf_logger_find_get(int pf, enum nf_log_type type)
136{ 143{
137 struct nf_logger *logger; 144 struct nf_logger *logger;