aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/net/netns/x_tables.h6
-rw-r--r--net/bridge/netfilter/Kconfig6
-rw-r--r--net/bridge/netfilter/Makefile2
-rw-r--r--net/bridge/netfilter/nft_reject_bridge.c67
-rw-r--r--net/ipv4/netfilter/Makefile1
-rw-r--r--net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c2
-rw-r--r--net/netfilter/nf_tables_api.c137
-rw-r--r--net/netfilter/nfnetlink_acct.c12
-rw-r--r--net/netfilter/xt_LED.c4
-rw-r--r--net/netfilter/xt_hashlimit.c31
10 files changed, 133 insertions, 135 deletions
diff --git a/include/net/netns/x_tables.h b/include/net/netns/x_tables.h
index 02fe40f8c8fd..c24060ee411e 100644
--- a/include/net/netns/x_tables.h
+++ b/include/net/netns/x_tables.h
@@ -15,11 +15,5 @@ struct netns_xt {
15 struct ebt_table *frame_filter; 15 struct ebt_table *frame_filter;
16 struct ebt_table *frame_nat; 16 struct ebt_table *frame_nat;
17#endif 17#endif
18#if IS_ENABLED(CONFIG_IP_NF_TARGET_ULOG)
19 bool ulog_warn_deprecated;
20#endif
21#if IS_ENABLED(CONFIG_BRIDGE_EBT_ULOG)
22 bool ebt_ulog_warn_deprecated;
23#endif
24}; 18};
25#endif 19#endif
diff --git a/net/bridge/netfilter/Kconfig b/net/bridge/netfilter/Kconfig
index 4ce0b313f72c..9cebf47ac840 100644
--- a/net/bridge/netfilter/Kconfig
+++ b/net/bridge/netfilter/Kconfig
@@ -14,6 +14,12 @@ 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 NFT_BRIDGE_REJECT
18 tristate "Netfilter nf_tables bridge reject support"
19 depends on NFT_REJECT && NFT_REJECT_IPV4 && NFT_REJECT_IPV6
20 help
21 Add support to reject packets.
22
17config NF_LOG_BRIDGE 23config NF_LOG_BRIDGE
18 tristate "Bridge packet logging" 24 tristate "Bridge packet logging"
19 25
diff --git a/net/bridge/netfilter/Makefile b/net/bridge/netfilter/Makefile
index 1f78ea0d90e4..be4d0cea78ce 100644
--- a/net/bridge/netfilter/Makefile
+++ b/net/bridge/netfilter/Makefile
@@ -4,6 +4,7 @@
4 4
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
7obj-$(CONFIG_NFT_BRIDGE_REJECT) += nft_reject_bridge.o
7 8
8# packet logging 9# packet logging
9obj-$(CONFIG_NF_LOG_BRIDGE) += nf_log_bridge.o 10obj-$(CONFIG_NF_LOG_BRIDGE) += nf_log_bridge.o
@@ -36,5 +37,4 @@ obj-$(CONFIG_BRIDGE_EBT_SNAT) += ebt_snat.o
36 37
37# watchers 38# watchers
38obj-$(CONFIG_BRIDGE_EBT_LOG) += ebt_log.o 39obj-$(CONFIG_BRIDGE_EBT_LOG) += ebt_log.o
39obj-$(CONFIG_BRIDGE_EBT_ULOG) += ebt_ulog.o
40obj-$(CONFIG_BRIDGE_EBT_NFLOG) += ebt_nflog.o 40obj-$(CONFIG_BRIDGE_EBT_NFLOG) += ebt_nflog.o
diff --git a/net/bridge/netfilter/nft_reject_bridge.c b/net/bridge/netfilter/nft_reject_bridge.c
new file mode 100644
index 000000000000..ee3ffe93e14e
--- /dev/null
+++ b/net/bridge/netfilter/nft_reject_bridge.c
@@ -0,0 +1,67 @@
1/*
2 * Copyright (c) 2014 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/kernel.h>
10#include <linux/init.h>
11#include <linux/module.h>
12#include <linux/netlink.h>
13#include <linux/netfilter.h>
14#include <linux/netfilter/nf_tables.h>
15#include <net/netfilter/nf_tables.h>
16#include <net/netfilter/nft_reject.h>
17
18static void nft_reject_bridge_eval(const struct nft_expr *expr,
19 struct nft_data data[NFT_REG_MAX + 1],
20 const struct nft_pktinfo *pkt)
21{
22 switch (eth_hdr(pkt->skb)->h_proto) {
23 case htons(ETH_P_IP):
24 return nft_reject_ipv4_eval(expr, data, pkt);
25 case htons(ETH_P_IPV6):
26 return nft_reject_ipv6_eval(expr, data, pkt);
27 default:
28 /* No explicit way to reject this protocol, drop it. */
29 data[NFT_REG_VERDICT].verdict = NF_DROP;
30 break;
31 }
32}
33
34static struct nft_expr_type nft_reject_bridge_type;
35static const struct nft_expr_ops nft_reject_bridge_ops = {
36 .type = &nft_reject_bridge_type,
37 .size = NFT_EXPR_SIZE(sizeof(struct nft_reject)),
38 .eval = nft_reject_bridge_eval,
39 .init = nft_reject_init,
40 .dump = nft_reject_dump,
41};
42
43static struct nft_expr_type nft_reject_bridge_type __read_mostly = {
44 .family = NFPROTO_BRIDGE,
45 .name = "reject",
46 .ops = &nft_reject_bridge_ops,
47 .policy = nft_reject_policy,
48 .maxattr = NFTA_REJECT_MAX,
49 .owner = THIS_MODULE,
50};
51
52static int __init nft_reject_bridge_module_init(void)
53{
54 return nft_register_expr(&nft_reject_bridge_type);
55}
56
57static void __exit nft_reject_bridge_module_exit(void)
58{
59 nft_unregister_expr(&nft_reject_bridge_type);
60}
61
62module_init(nft_reject_bridge_module_init);
63module_exit(nft_reject_bridge_module_exit);
64
65MODULE_LICENSE("GPL");
66MODULE_AUTHOR("Pablo Neira Ayuso <pablo@netfilter.org>");
67MODULE_ALIAS_NFT_AF_EXPR(AF_BRIDGE, "reject");
diff --git a/net/ipv4/netfilter/Makefile b/net/ipv4/netfilter/Makefile
index 245db9df3337..33001621465b 100644
--- a/net/ipv4/netfilter/Makefile
+++ b/net/ipv4/netfilter/Makefile
@@ -57,7 +57,6 @@ obj-$(CONFIG_IP_NF_TARGET_ECN) += ipt_ECN.o
57obj-$(CONFIG_IP_NF_TARGET_MASQUERADE) += ipt_MASQUERADE.o 57obj-$(CONFIG_IP_NF_TARGET_MASQUERADE) += ipt_MASQUERADE.o
58obj-$(CONFIG_IP_NF_TARGET_REJECT) += ipt_REJECT.o 58obj-$(CONFIG_IP_NF_TARGET_REJECT) += ipt_REJECT.o
59obj-$(CONFIG_IP_NF_TARGET_SYNPROXY) += ipt_SYNPROXY.o 59obj-$(CONFIG_IP_NF_TARGET_SYNPROXY) += ipt_SYNPROXY.o
60obj-$(CONFIG_IP_NF_TARGET_ULOG) += ipt_ULOG.o
61 60
62# generic ARP tables 61# generic ARP tables
63obj-$(CONFIG_IP_NF_ARPTABLES) += arp_tables.o 62obj-$(CONFIG_IP_NF_ARPTABLES) += arp_tables.o
diff --git a/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c b/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
index 4ce44c4bc57b..a054fe083431 100644
--- a/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
+++ b/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
@@ -358,7 +358,7 @@ static struct nf_sockopt_ops so_getorigdst = {
358 .pf = PF_INET, 358 .pf = PF_INET,
359 .get_optmin = SO_ORIGINAL_DST, 359 .get_optmin = SO_ORIGINAL_DST,
360 .get_optmax = SO_ORIGINAL_DST+1, 360 .get_optmax = SO_ORIGINAL_DST+1,
361 .get = &getorigdst, 361 .get = getorigdst,
362 .owner = THIS_MODULE, 362 .owner = THIS_MODULE,
363}; 363};
364 364
diff --git a/net/netfilter/nf_tables_api.c b/net/netfilter/nf_tables_api.c
index 8746ff9a8357..93692d692ebc 100644
--- a/net/netfilter/nf_tables_api.c
+++ b/net/netfilter/nf_tables_api.c
@@ -2247,80 +2247,7 @@ err:
2247 return err; 2247 return err;
2248} 2248}
2249 2249
2250static int nf_tables_dump_sets_table(struct nft_ctx *ctx, struct sk_buff *skb, 2250static int nf_tables_dump_sets(struct sk_buff *skb, struct netlink_callback *cb)
2251 struct netlink_callback *cb)
2252{
2253 const struct nft_set *set;
2254 unsigned int idx = 0, s_idx = cb->args[0];
2255
2256 if (cb->args[1])
2257 return skb->len;
2258
2259 rcu_read_lock();
2260 cb->seq = ctx->net->nft.base_seq;
2261
2262 list_for_each_entry_rcu(set, &ctx->table->sets, list) {
2263 if (idx < s_idx)
2264 goto cont;
2265 if (nf_tables_fill_set(skb, ctx, set, NFT_MSG_NEWSET,
2266 NLM_F_MULTI) < 0) {
2267 cb->args[0] = idx;
2268 goto done;
2269 }
2270 nl_dump_check_consistent(cb, nlmsg_hdr(skb));
2271cont:
2272 idx++;
2273 }
2274 cb->args[1] = 1;
2275done:
2276 rcu_read_unlock();
2277 return skb->len;
2278}
2279
2280static int nf_tables_dump_sets_family(struct nft_ctx *ctx, struct sk_buff *skb,
2281 struct netlink_callback *cb)
2282{
2283 const struct nft_set *set;
2284 unsigned int idx, s_idx = cb->args[0];
2285 struct nft_table *table, *cur_table = (struct nft_table *)cb->args[2];
2286
2287 if (cb->args[1])
2288 return skb->len;
2289
2290 rcu_read_lock();
2291 cb->seq = ctx->net->nft.base_seq;
2292
2293 list_for_each_entry_rcu(table, &ctx->afi->tables, list) {
2294 if (cur_table) {
2295 if (cur_table != table)
2296 continue;
2297
2298 cur_table = NULL;
2299 }
2300 ctx->table = table;
2301 idx = 0;
2302 list_for_each_entry_rcu(set, &ctx->table->sets, list) {
2303 if (idx < s_idx)
2304 goto cont;
2305 if (nf_tables_fill_set(skb, ctx, set, NFT_MSG_NEWSET,
2306 NLM_F_MULTI) < 0) {
2307 cb->args[0] = idx;
2308 cb->args[2] = (unsigned long) table;
2309 goto done;
2310 }
2311 nl_dump_check_consistent(cb, nlmsg_hdr(skb));
2312cont:
2313 idx++;
2314 }
2315 }
2316 cb->args[1] = 1;
2317done:
2318 rcu_read_unlock();
2319 return skb->len;
2320}
2321
2322static int nf_tables_dump_sets_all(struct nft_ctx *ctx, struct sk_buff *skb,
2323 struct netlink_callback *cb)
2324{ 2251{
2325 const struct nft_set *set; 2252 const struct nft_set *set;
2326 unsigned int idx, s_idx = cb->args[0]; 2253 unsigned int idx, s_idx = cb->args[0];
@@ -2328,6 +2255,7 @@ static int nf_tables_dump_sets_all(struct nft_ctx *ctx, struct sk_buff *skb,
2328 struct nft_table *table, *cur_table = (struct nft_table *)cb->args[2]; 2255 struct nft_table *table, *cur_table = (struct nft_table *)cb->args[2];
2329 struct net *net = sock_net(skb->sk); 2256 struct net *net = sock_net(skb->sk);
2330 int cur_family = cb->args[3]; 2257 int cur_family = cb->args[3];
2258 struct nft_ctx *ctx = cb->data, ctx_set;
2331 2259
2332 if (cb->args[1]) 2260 if (cb->args[1])
2333 return skb->len; 2261 return skb->len;
@@ -2336,28 +2264,34 @@ static int nf_tables_dump_sets_all(struct nft_ctx *ctx, struct sk_buff *skb,
2336 cb->seq = net->nft.base_seq; 2264 cb->seq = net->nft.base_seq;
2337 2265
2338 list_for_each_entry_rcu(afi, &net->nft.af_info, list) { 2266 list_for_each_entry_rcu(afi, &net->nft.af_info, list) {
2267 if (ctx->afi && ctx->afi != afi)
2268 continue;
2269
2339 if (cur_family) { 2270 if (cur_family) {
2340 if (afi->family != cur_family) 2271 if (afi->family != cur_family)
2341 continue; 2272 continue;
2342 2273
2343 cur_family = 0; 2274 cur_family = 0;
2344 } 2275 }
2345
2346 list_for_each_entry_rcu(table, &afi->tables, list) { 2276 list_for_each_entry_rcu(table, &afi->tables, list) {
2277 if (ctx->table && ctx->table != table)
2278 continue;
2279
2347 if (cur_table) { 2280 if (cur_table) {
2348 if (cur_table != table) 2281 if (cur_table != table)
2349 continue; 2282 continue;
2350 2283
2351 cur_table = NULL; 2284 cur_table = NULL;
2352 } 2285 }
2353
2354 ctx->table = table;
2355 ctx->afi = afi;
2356 idx = 0; 2286 idx = 0;
2357 list_for_each_entry_rcu(set, &ctx->table->sets, list) { 2287 list_for_each_entry_rcu(set, &table->sets, list) {
2358 if (idx < s_idx) 2288 if (idx < s_idx)
2359 goto cont; 2289 goto cont;
2360 if (nf_tables_fill_set(skb, ctx, set, 2290
2291 ctx_set = *ctx;
2292 ctx_set.table = table;
2293 ctx_set.afi = afi;
2294 if (nf_tables_fill_set(skb, &ctx_set, set,
2361 NFT_MSG_NEWSET, 2295 NFT_MSG_NEWSET,
2362 NLM_F_MULTI) < 0) { 2296 NLM_F_MULTI) < 0) {
2363 cb->args[0] = idx; 2297 cb->args[0] = idx;
@@ -2379,31 +2313,10 @@ done:
2379 return skb->len; 2313 return skb->len;
2380} 2314}
2381 2315
2382static int nf_tables_dump_sets(struct sk_buff *skb, struct netlink_callback *cb) 2316static int nf_tables_dump_sets_done(struct netlink_callback *cb)
2383{ 2317{
2384 const struct nfgenmsg *nfmsg = nlmsg_data(cb->nlh); 2318 kfree(cb->data);
2385 struct nlattr *nla[NFTA_SET_MAX + 1]; 2319 return 0;
2386 struct nft_ctx ctx;
2387 int err, ret;
2388
2389 err = nlmsg_parse(cb->nlh, sizeof(*nfmsg), nla, NFTA_SET_MAX,
2390 nft_set_policy);
2391 if (err < 0)
2392 return err;
2393
2394 err = nft_ctx_init_from_setattr(&ctx, cb->skb, cb->nlh, (void *)nla);
2395 if (err < 0)
2396 return err;
2397
2398 if (ctx.table == NULL) {
2399 if (ctx.afi == NULL)
2400 ret = nf_tables_dump_sets_all(&ctx, skb, cb);
2401 else
2402 ret = nf_tables_dump_sets_family(&ctx, skb, cb);
2403 } else
2404 ret = nf_tables_dump_sets_table(&ctx, skb, cb);
2405
2406 return ret;
2407} 2320}
2408 2321
2409#define NFT_SET_INACTIVE (1 << 15) /* Internal set flag */ 2322#define NFT_SET_INACTIVE (1 << 15) /* Internal set flag */
@@ -2426,7 +2339,17 @@ static int nf_tables_getset(struct sock *nlsk, struct sk_buff *skb,
2426 if (nlh->nlmsg_flags & NLM_F_DUMP) { 2339 if (nlh->nlmsg_flags & NLM_F_DUMP) {
2427 struct netlink_dump_control c = { 2340 struct netlink_dump_control c = {
2428 .dump = nf_tables_dump_sets, 2341 .dump = nf_tables_dump_sets,
2342 .done = nf_tables_dump_sets_done,
2429 }; 2343 };
2344 struct nft_ctx *ctx_dump;
2345
2346 ctx_dump = kmalloc(sizeof(*ctx_dump), GFP_KERNEL);
2347 if (ctx_dump == NULL)
2348 return -ENOMEM;
2349
2350 *ctx_dump = ctx;
2351 c.data = ctx_dump;
2352
2430 return netlink_dump_start(nlsk, skb, nlh, &c); 2353 return netlink_dump_start(nlsk, skb, nlh, &c);
2431 } 2354 }
2432 2355
@@ -3150,6 +3073,9 @@ static int nf_tables_newsetelem(struct sock *nlsk, struct sk_buff *skb,
3150 struct nft_ctx ctx; 3073 struct nft_ctx ctx;
3151 int rem, err = 0; 3074 int rem, err = 0;
3152 3075
3076 if (nla[NFTA_SET_ELEM_LIST_ELEMENTS] == NULL)
3077 return -EINVAL;
3078
3153 err = nft_ctx_init_from_elemattr(&ctx, skb, nlh, nla, true); 3079 err = nft_ctx_init_from_elemattr(&ctx, skb, nlh, nla, true);
3154 if (err < 0) 3080 if (err < 0)
3155 return err; 3081 return err;
@@ -3233,6 +3159,9 @@ static int nf_tables_delsetelem(struct sock *nlsk, struct sk_buff *skb,
3233 struct nft_ctx ctx; 3159 struct nft_ctx ctx;
3234 int rem, err = 0; 3160 int rem, err = 0;
3235 3161
3162 if (nla[NFTA_SET_ELEM_LIST_ELEMENTS] == NULL)
3163 return -EINVAL;
3164
3236 err = nft_ctx_init_from_elemattr(&ctx, skb, nlh, nla, false); 3165 err = nft_ctx_init_from_elemattr(&ctx, skb, nlh, nla, false);
3237 if (err < 0) 3166 if (err < 0)
3238 return err; 3167 return err;
diff --git a/net/netfilter/nfnetlink_acct.c b/net/netfilter/nfnetlink_acct.c
index 2baa125c2e8d..3ea0eacbd970 100644
--- a/net/netfilter/nfnetlink_acct.c
+++ b/net/netfilter/nfnetlink_acct.c
@@ -41,6 +41,7 @@ struct nf_acct {
41}; 41};
42 42
43#define NFACCT_F_QUOTA (NFACCT_F_QUOTA_PKTS | NFACCT_F_QUOTA_BYTES) 43#define NFACCT_F_QUOTA (NFACCT_F_QUOTA_PKTS | NFACCT_F_QUOTA_BYTES)
44#define NFACCT_OVERQUOTA_BIT 2 /* NFACCT_F_OVERQUOTA */
44 45
45static int 46static int
46nfnl_acct_new(struct sock *nfnl, struct sk_buff *skb, 47nfnl_acct_new(struct sock *nfnl, struct sk_buff *skb,
@@ -77,7 +78,8 @@ nfnl_acct_new(struct sock *nfnl, struct sk_buff *skb,
77 smp_mb__before_atomic(); 78 smp_mb__before_atomic();
78 /* reset overquota flag if quota is enabled. */ 79 /* reset overquota flag if quota is enabled. */
79 if ((matching->flags & NFACCT_F_QUOTA)) 80 if ((matching->flags & NFACCT_F_QUOTA))
80 clear_bit(NFACCT_F_OVERQUOTA, &matching->flags); 81 clear_bit(NFACCT_OVERQUOTA_BIT,
82 &matching->flags);
81 return 0; 83 return 0;
82 } 84 }
83 return -EBUSY; 85 return -EBUSY;
@@ -129,6 +131,7 @@ nfnl_acct_fill_info(struct sk_buff *skb, u32 portid, u32 seq, u32 type,
129 struct nfgenmsg *nfmsg; 131 struct nfgenmsg *nfmsg;
130 unsigned int flags = portid ? NLM_F_MULTI : 0; 132 unsigned int flags = portid ? NLM_F_MULTI : 0;
131 u64 pkts, bytes; 133 u64 pkts, bytes;
134 u32 old_flags;
132 135
133 event |= NFNL_SUBSYS_ACCT << 8; 136 event |= NFNL_SUBSYS_ACCT << 8;
134 nlh = nlmsg_put(skb, portid, seq, event, sizeof(*nfmsg), flags); 137 nlh = nlmsg_put(skb, portid, seq, event, sizeof(*nfmsg), flags);
@@ -143,12 +146,13 @@ nfnl_acct_fill_info(struct sk_buff *skb, u32 portid, u32 seq, u32 type,
143 if (nla_put_string(skb, NFACCT_NAME, acct->name)) 146 if (nla_put_string(skb, NFACCT_NAME, acct->name))
144 goto nla_put_failure; 147 goto nla_put_failure;
145 148
149 old_flags = acct->flags;
146 if (type == NFNL_MSG_ACCT_GET_CTRZERO) { 150 if (type == NFNL_MSG_ACCT_GET_CTRZERO) {
147 pkts = atomic64_xchg(&acct->pkts, 0); 151 pkts = atomic64_xchg(&acct->pkts, 0);
148 bytes = atomic64_xchg(&acct->bytes, 0); 152 bytes = atomic64_xchg(&acct->bytes, 0);
149 smp_mb__before_atomic(); 153 smp_mb__before_atomic();
150 if (acct->flags & NFACCT_F_QUOTA) 154 if (acct->flags & NFACCT_F_QUOTA)
151 clear_bit(NFACCT_F_OVERQUOTA, &acct->flags); 155 clear_bit(NFACCT_OVERQUOTA_BIT, &acct->flags);
152 } else { 156 } else {
153 pkts = atomic64_read(&acct->pkts); 157 pkts = atomic64_read(&acct->pkts);
154 bytes = atomic64_read(&acct->bytes); 158 bytes = atomic64_read(&acct->bytes);
@@ -160,7 +164,7 @@ nfnl_acct_fill_info(struct sk_buff *skb, u32 portid, u32 seq, u32 type,
160 if (acct->flags & NFACCT_F_QUOTA) { 164 if (acct->flags & NFACCT_F_QUOTA) {
161 u64 *quota = (u64 *)acct->data; 165 u64 *quota = (u64 *)acct->data;
162 166
163 if (nla_put_be32(skb, NFACCT_FLAGS, htonl(acct->flags)) || 167 if (nla_put_be32(skb, NFACCT_FLAGS, htonl(old_flags)) ||
164 nla_put_be64(skb, NFACCT_QUOTA, cpu_to_be64(*quota))) 168 nla_put_be64(skb, NFACCT_QUOTA, cpu_to_be64(*quota)))
165 goto nla_put_failure; 169 goto nla_put_failure;
166 } 170 }
@@ -412,7 +416,7 @@ int nfnl_acct_overquota(const struct sk_buff *skb, struct nf_acct *nfacct)
412 ret = now > *quota; 416 ret = now > *quota;
413 417
414 if (now >= *quota && 418 if (now >= *quota &&
415 !test_and_set_bit(NFACCT_F_OVERQUOTA, &nfacct->flags)) { 419 !test_and_set_bit(NFACCT_OVERQUOTA_BIT, &nfacct->flags)) {
416 nfnl_overquota_report(nfacct); 420 nfnl_overquota_report(nfacct);
417 } 421 }
418 422
diff --git a/net/netfilter/xt_LED.c b/net/netfilter/xt_LED.c
index 993de2ba89d3..f14bcf23dc9f 100644
--- a/net/netfilter/xt_LED.c
+++ b/net/netfilter/xt_LED.c
@@ -133,9 +133,7 @@ static int led_tg_check(const struct xt_tgchk_param *par)
133 133
134 err = led_trigger_register(&ledinternal->netfilter_led_trigger); 134 err = led_trigger_register(&ledinternal->netfilter_led_trigger);
135 if (err) { 135 if (err) {
136 pr_warning("led_trigger_register() failed\n"); 136 pr_err("Trigger name is already in use.\n");
137 if (err == -EEXIST)
138 pr_warning("Trigger name is already in use.\n");
139 goto exit_alloc; 137 goto exit_alloc;
140 } 138 }
141 139
diff --git a/net/netfilter/xt_hashlimit.c b/net/netfilter/xt_hashlimit.c
index a3910fc2122b..47dc6836830a 100644
--- a/net/netfilter/xt_hashlimit.c
+++ b/net/netfilter/xt_hashlimit.c
@@ -104,7 +104,7 @@ struct xt_hashlimit_htable {
104 spinlock_t lock; /* lock for list_head */ 104 spinlock_t lock; /* lock for list_head */
105 u_int32_t rnd; /* random seed for hash */ 105 u_int32_t rnd; /* random seed for hash */
106 unsigned int count; /* number entries in table */ 106 unsigned int count; /* number entries in table */
107 struct timer_list timer; /* timer for gc */ 107 struct delayed_work gc_work;
108 108
109 /* seq_file stuff */ 109 /* seq_file stuff */
110 struct proc_dir_entry *pde; 110 struct proc_dir_entry *pde;
@@ -213,7 +213,7 @@ dsthash_free(struct xt_hashlimit_htable *ht, struct dsthash_ent *ent)
213 call_rcu_bh(&ent->rcu, dsthash_free_rcu); 213 call_rcu_bh(&ent->rcu, dsthash_free_rcu);
214 ht->count--; 214 ht->count--;
215} 215}
216static void htable_gc(unsigned long htlong); 216static void htable_gc(struct work_struct *work);
217 217
218static int htable_create(struct net *net, struct xt_hashlimit_mtinfo1 *minfo, 218static int htable_create(struct net *net, struct xt_hashlimit_mtinfo1 *minfo,
219 u_int8_t family) 219 u_int8_t family)
@@ -273,9 +273,9 @@ static int htable_create(struct net *net, struct xt_hashlimit_mtinfo1 *minfo,
273 } 273 }
274 hinfo->net = net; 274 hinfo->net = net;
275 275
276 setup_timer(&hinfo->timer, htable_gc, (unsigned long)hinfo); 276 INIT_DEFERRABLE_WORK(&hinfo->gc_work, htable_gc);
277 hinfo->timer.expires = jiffies + msecs_to_jiffies(hinfo->cfg.gc_interval); 277 queue_delayed_work(system_power_efficient_wq, &hinfo->gc_work,
278 add_timer(&hinfo->timer); 278 msecs_to_jiffies(hinfo->cfg.gc_interval));
279 279
280 hlist_add_head(&hinfo->node, &hashlimit_net->htables); 280 hlist_add_head(&hinfo->node, &hashlimit_net->htables);
281 281
@@ -300,29 +300,30 @@ static void htable_selective_cleanup(struct xt_hashlimit_htable *ht,
300{ 300{
301 unsigned int i; 301 unsigned int i;
302 302
303 /* lock hash table and iterate over it */
304 spin_lock_bh(&ht->lock);
305 for (i = 0; i < ht->cfg.size; i++) { 303 for (i = 0; i < ht->cfg.size; i++) {
306 struct dsthash_ent *dh; 304 struct dsthash_ent *dh;
307 struct hlist_node *n; 305 struct hlist_node *n;
306
307 spin_lock_bh(&ht->lock);
308 hlist_for_each_entry_safe(dh, n, &ht->hash[i], node) { 308 hlist_for_each_entry_safe(dh, n, &ht->hash[i], node) {
309 if ((*select)(ht, dh)) 309 if ((*select)(ht, dh))
310 dsthash_free(ht, dh); 310 dsthash_free(ht, dh);
311 } 311 }
312 spin_unlock_bh(&ht->lock);
313 cond_resched();
312 } 314 }
313 spin_unlock_bh(&ht->lock);
314} 315}
315 316
316/* hash table garbage collector, run by timer */ 317static void htable_gc(struct work_struct *work)
317static void htable_gc(unsigned long htlong)
318{ 318{
319 struct xt_hashlimit_htable *ht = (struct xt_hashlimit_htable *)htlong; 319 struct xt_hashlimit_htable *ht;
320
321 ht = container_of(work, struct xt_hashlimit_htable, gc_work.work);
320 322
321 htable_selective_cleanup(ht, select_gc); 323 htable_selective_cleanup(ht, select_gc);
322 324
323 /* re-add the timer accordingly */ 325 queue_delayed_work(system_power_efficient_wq,
324 ht->timer.expires = jiffies + msecs_to_jiffies(ht->cfg.gc_interval); 326 &ht->gc_work, msecs_to_jiffies(ht->cfg.gc_interval));
325 add_timer(&ht->timer);
326} 327}
327 328
328static void htable_remove_proc_entry(struct xt_hashlimit_htable *hinfo) 329static void htable_remove_proc_entry(struct xt_hashlimit_htable *hinfo)
@@ -341,7 +342,7 @@ static void htable_remove_proc_entry(struct xt_hashlimit_htable *hinfo)
341 342
342static void htable_destroy(struct xt_hashlimit_htable *hinfo) 343static void htable_destroy(struct xt_hashlimit_htable *hinfo)
343{ 344{
344 del_timer_sync(&hinfo->timer); 345 cancel_delayed_work_sync(&hinfo->gc_work);
345 htable_remove_proc_entry(hinfo); 346 htable_remove_proc_entry(hinfo);
346 htable_selective_cleanup(hinfo, select_all); 347 htable_selective_cleanup(hinfo, select_all);
347 kfree(hinfo->name); 348 kfree(hinfo->name);