summaryrefslogtreecommitdiffstats
path: root/include/net
diff options
context:
space:
mode:
Diffstat (limited to 'include/net')
-rw-r--r--include/net/netfilter/nf_conntrack_ecache.h130
-rw-r--r--include/net/netfilter/nf_conntrack_extend.h2
-rw-r--r--include/net/netns/conntrack.h5
3 files changed, 73 insertions, 64 deletions
diff --git a/include/net/netfilter/nf_conntrack_ecache.h b/include/net/netfilter/nf_conntrack_ecache.h
index 1afb907e015..e7ae297ba38 100644
--- a/include/net/netfilter/nf_conntrack_ecache.h
+++ b/include/net/netfilter/nf_conntrack_ecache.h
@@ -6,61 +6,52 @@
#define _NF_CONNTRACK_ECACHE_H
#include <net/netfilter/nf_conntrack.h>
-#include <linux/interrupt.h>
#include <net/net_namespace.h>
#include <net/netfilter/nf_conntrack_expect.h>
+#include <linux/netfilter/nf_conntrack_common.h>
+#include <linux/netfilter/nf_conntrack_tuple_common.h>
+#include <net/netfilter/nf_conntrack_extend.h>
-/* Connection tracking event bits */
+/* Connection tracking event types */
enum ip_conntrack_events
{
- /* New conntrack */
- IPCT_NEW_BIT = 0,
- IPCT_NEW = (1 << IPCT_NEW_BIT),
-
- /* Expected connection */
- IPCT_RELATED_BIT = 1,
- IPCT_RELATED = (1 << IPCT_RELATED_BIT),
-
- /* Destroyed conntrack */
- IPCT_DESTROY_BIT = 2,
- IPCT_DESTROY = (1 << IPCT_DESTROY_BIT),
-
- /* Status has changed */
- IPCT_STATUS_BIT = 3,
- IPCT_STATUS = (1 << IPCT_STATUS_BIT),
+ IPCT_NEW = 0, /* new conntrack */
+ IPCT_RELATED = 1, /* related conntrack */
+ IPCT_DESTROY = 2, /* destroyed conntrack */
+ IPCT_STATUS = 3, /* status has changed */
+ IPCT_PROTOINFO = 4, /* protocol information has changed */
+ IPCT_HELPER = 5, /* new helper has been set */
+ IPCT_MARK = 6, /* new mark has been set */
+ IPCT_NATSEQADJ = 7, /* NAT is doing sequence adjustment */
+ IPCT_SECMARK = 8, /* new security mark has been set */
+};
- /* Update of protocol info */
- IPCT_PROTOINFO_BIT = 4,
- IPCT_PROTOINFO = (1 << IPCT_PROTOINFO_BIT),
+enum ip_conntrack_expect_events {
+ IPEXP_NEW = 0, /* new expectation */
+};
- /* New helper for conntrack */
- IPCT_HELPER_BIT = 5,
- IPCT_HELPER = (1 << IPCT_HELPER_BIT),
+struct nf_conntrack_ecache {
+ unsigned long cache; /* bitops want long */
+};
- /* Mark is set */
- IPCT_MARK_BIT = 6,
- IPCT_MARK = (1 << IPCT_MARK_BIT),
+static inline struct nf_conntrack_ecache *
+nf_ct_ecache_find(const struct nf_conn *ct)
+{
+ return nf_ct_ext_find(ct, NF_CT_EXT_ECACHE);
+}
- /* NAT sequence adjustment */
- IPCT_NATSEQADJ_BIT = 7,
- IPCT_NATSEQADJ = (1 << IPCT_NATSEQADJ_BIT),
+static inline struct nf_conntrack_ecache *
+nf_ct_ecache_ext_add(struct nf_conn *ct, gfp_t gfp)
+{
+ struct net *net = nf_ct_net(ct);
- /* Secmark is set */
- IPCT_SECMARK_BIT = 8,
- IPCT_SECMARK = (1 << IPCT_SECMARK_BIT),
-};
+ if (!net->ct.sysctl_events)
+ return NULL;
-enum ip_conntrack_expect_events {
- IPEXP_NEW_BIT = 0,
- IPEXP_NEW = (1 << IPEXP_NEW_BIT),
+ return nf_ct_ext_add(ct, NF_CT_EXT_ECACHE, gfp);
};
#ifdef CONFIG_NF_CONNTRACK_EVENTS
-struct nf_conntrack_ecache {
- struct nf_conn *ct;
- unsigned int events;
-};
-
/* This structure is passed to event handler */
struct nf_ct_event {
struct nf_conn *ct;
@@ -76,30 +67,30 @@ extern struct nf_ct_event_notifier *nf_conntrack_event_cb;
extern int nf_conntrack_register_notifier(struct nf_ct_event_notifier *nb);
extern void nf_conntrack_unregister_notifier(struct nf_ct_event_notifier *nb);
-extern void nf_ct_deliver_cached_events(const struct nf_conn *ct);
-extern void __nf_ct_event_cache_init(struct nf_conn *ct);
-extern void nf_ct_event_cache_flush(struct net *net);
+extern void nf_ct_deliver_cached_events(struct nf_conn *ct);
static inline void
nf_conntrack_event_cache(enum ip_conntrack_events event, struct nf_conn *ct)
{
- struct net *net = nf_ct_net(ct);
- struct nf_conntrack_ecache *ecache;
-
- local_bh_disable();
- ecache = per_cpu_ptr(net->ct.ecache, raw_smp_processor_id());
- if (ct != ecache->ct)
- __nf_ct_event_cache_init(ct);
- ecache->events |= event;
- local_bh_enable();
+ struct nf_conntrack_ecache *e;
+
+ if (nf_conntrack_event_cb == NULL)
+ return;
+
+ e = nf_ct_ecache_find(ct);
+ if (e == NULL)
+ return;
+
+ set_bit(event, &e->cache);
}
static inline void
-nf_conntrack_event_report(enum ip_conntrack_events event,
- struct nf_conn *ct,
- u32 pid,
- int report)
+nf_conntrack_eventmask_report(unsigned int eventmask,
+ struct nf_conn *ct,
+ u32 pid,
+ int report)
{
+ struct net *net = nf_ct_net(ct);
struct nf_ct_event_notifier *notify;
rcu_read_lock();
@@ -107,22 +98,32 @@ nf_conntrack_event_report(enum ip_conntrack_events event,
if (notify == NULL)
goto out_unlock;
+ if (!net->ct.sysctl_events)
+ goto out_unlock;
+
if (nf_ct_is_confirmed(ct) && !nf_ct_is_dying(ct)) {
struct nf_ct_event item = {
.ct = ct,
.pid = pid,
.report = report
};
- notify->fcn(event, &item);
+ notify->fcn(eventmask, &item);
}
out_unlock:
rcu_read_unlock();
}
static inline void
+nf_conntrack_event_report(enum ip_conntrack_events event, struct nf_conn *ct,
+ u32 pid, int report)
+{
+ nf_conntrack_eventmask_report(1 << event, ct, pid, report);
+}
+
+static inline void
nf_conntrack_event(enum ip_conntrack_events event, struct nf_conn *ct)
{
- nf_conntrack_event_report(event, ct, 0, 0);
+ nf_conntrack_eventmask_report(1 << event, ct, 0, 0);
}
struct nf_exp_event {
@@ -145,6 +146,7 @@ nf_ct_expect_event_report(enum ip_conntrack_expect_events event,
u32 pid,
int report)
{
+ struct net *net = nf_ct_exp_net(exp);
struct nf_exp_event_notifier *notify;
rcu_read_lock();
@@ -152,13 +154,16 @@ nf_ct_expect_event_report(enum ip_conntrack_expect_events event,
if (notify == NULL)
goto out_unlock;
+ if (!net->ct.sysctl_events)
+ goto out_unlock;
+
{
struct nf_exp_event item = {
.exp = exp,
.pid = pid,
.report = report
};
- notify->fcn(event, &item);
+ notify->fcn(1 << event, &item);
}
out_unlock:
rcu_read_unlock();
@@ -178,6 +183,10 @@ extern void nf_conntrack_ecache_fini(struct net *net);
static inline void nf_conntrack_event_cache(enum ip_conntrack_events event,
struct nf_conn *ct) {}
+static inline void nf_conntrack_eventmask_report(unsigned int eventmask,
+ struct nf_conn *ct,
+ u32 pid,
+ int report) {}
static inline void nf_conntrack_event(enum ip_conntrack_events event,
struct nf_conn *ct) {}
static inline void nf_conntrack_event_report(enum ip_conntrack_events event,
@@ -191,7 +200,6 @@ static inline void nf_ct_expect_event_report(enum ip_conntrack_expect_events e,
struct nf_conntrack_expect *exp,
u32 pid,
int report) {}
-static inline void nf_ct_event_cache_flush(struct net *net) {}
static inline int nf_conntrack_ecache_init(struct net *net)
{
diff --git a/include/net/netfilter/nf_conntrack_extend.h b/include/net/netfilter/nf_conntrack_extend.h
index da8ee52613a..7f8fc5d123c 100644
--- a/include/net/netfilter/nf_conntrack_extend.h
+++ b/include/net/netfilter/nf_conntrack_extend.h
@@ -8,12 +8,14 @@ enum nf_ct_ext_id
NF_CT_EXT_HELPER,
NF_CT_EXT_NAT,
NF_CT_EXT_ACCT,
+ NF_CT_EXT_ECACHE,
NF_CT_EXT_NUM,
};
#define NF_CT_EXT_HELPER_TYPE struct nf_conn_help
#define NF_CT_EXT_NAT_TYPE struct nf_conn_nat
#define NF_CT_EXT_ACCT_TYPE struct nf_conn_counter
+#define NF_CT_EXT_ECACHE_TYPE struct nf_conntrack_ecache
/* Extensions: optional stuff which isn't permanently in struct. */
struct nf_ct_ext {
diff --git a/include/net/netns/conntrack.h b/include/net/netns/conntrack.h
index 9dc58402bc0..505a51cd8c6 100644
--- a/include/net/netns/conntrack.h
+++ b/include/net/netns/conntrack.h
@@ -15,15 +15,14 @@ struct netns_ct {
struct hlist_head *expect_hash;
struct hlist_nulls_head unconfirmed;
struct ip_conntrack_stat *stat;
-#ifdef CONFIG_NF_CONNTRACK_EVENTS
- struct nf_conntrack_ecache *ecache;
-#endif
+ int sysctl_events;
int sysctl_acct;
int sysctl_checksum;
unsigned int sysctl_log_invalid; /* Log invalid packets */
#ifdef CONFIG_SYSCTL
struct ctl_table_header *sysctl_header;
struct ctl_table_header *acct_sysctl_header;
+ struct ctl_table_header *event_sysctl_header;
#endif
int hash_vmalloc;
int expect_vmalloc;