* [PATCH nf-next 0/3] Additional nf_hook_entry compaction
@ 2016-11-15 22:48 Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 1/3] netfilter: introduce accessor functions for hook entries Aaron Conole
` (3 more replies)
0 siblings, 4 replies; 5+ messages in thread
From: Aaron Conole @ 2016-11-15 22:48 UTC (permalink / raw)
To: netfilter-devel
Cc: Pablo Neira Ayuso, Florian Westphal, Jozsef Kadlecsik, coreteam,
David S . Miller
This series introduces a set of accessors, compacts the nf_hook_entry, and
rearranges some of the loops in preparation for the final set of work going
to an array based hook system.
After this series, the nf_hook_entry should fit in a cacheline on a modern
Intel i7.
Tested on bare-metal system.
Aaron Conole (3):
netfilter: introduce accessor functions for hook entries
netfilter: decouple nf_hook_entry and nf_hook_ops
netfilter: convert while loops to for loops
include/linux/netfilter.h | 31 ++++++++++++++++++++++++++++++-
net/bridge/br_netfilter_hooks.c | 8 ++++----
net/netfilter/core.c | 16 ++++++----------
net/netfilter/nf_queue.c | 5 ++---
4 files changed, 42 insertions(+), 18 deletions(-)
--
2.7.4
^ permalink raw reply [flat|nested] 5+ messages in thread
* [PATCH nf-next 1/3] netfilter: introduce accessor functions for hook entries
2016-11-15 22:48 [PATCH nf-next 0/3] Additional nf_hook_entry compaction Aaron Conole
@ 2016-11-15 22:48 ` Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 2/3] netfilter: decouple nf_hook_entry and nf_hook_ops Aaron Conole
` (2 subsequent siblings)
3 siblings, 0 replies; 5+ messages in thread
From: Aaron Conole @ 2016-11-15 22:48 UTC (permalink / raw)
To: netfilter-devel
Cc: Pablo Neira Ayuso, Florian Westphal, Jozsef Kadlecsik, coreteam,
David S . Miller
This allows easier future refactoring.
Signed-off-by: Aaron Conole <aconole@bytheb.org>
---
include/linux/netfilter.h | 27 +++++++++++++++++++++++++++
net/bridge/br_netfilter_hooks.c | 2 +-
net/netfilter/core.c | 10 ++++------
net/netfilter/nf_queue.c | 5 ++---
4 files changed, 34 insertions(+), 10 deletions(-)
diff --git a/include/linux/netfilter.h b/include/linux/netfilter.h
index 6923014..575aa19 100644
--- a/include/linux/netfilter.h
+++ b/include/linux/netfilter.h
@@ -79,6 +79,33 @@ struct nf_hook_entry {
const struct nf_hook_ops *orig_ops;
};
+static inline void
+nf_hook_entry_init(struct nf_hook_entry *entry, const struct nf_hook_ops *ops)
+{
+ entry->next = NULL;
+ entry->ops = *ops;
+ entry->orig_ops = ops;
+}
+
+static inline int
+nf_hook_entry_priority(const struct nf_hook_entry *entry)
+{
+ return entry->ops.priority;
+}
+
+static inline int
+nf_hook_entry_hookfn(const struct nf_hook_entry *entry, struct sk_buff *skb,
+ struct nf_hook_state *state)
+{
+ return entry->ops.hook(entry->ops.priv, skb, state);
+}
+
+static inline const struct nf_hook_ops *
+nf_hook_entry_ops(const struct nf_hook_entry *entry)
+{
+ return entry->orig_ops;
+}
+
static inline void nf_hook_state_init(struct nf_hook_state *p,
unsigned int hook,
u_int8_t pf,
diff --git a/net/bridge/br_netfilter_hooks.c b/net/bridge/br_netfilter_hooks.c
index 8155bd2..ef8cfa7 100644
--- a/net/bridge/br_netfilter_hooks.c
+++ b/net/bridge/br_netfilter_hooks.c
@@ -1010,7 +1010,7 @@ int br_nf_hook_thresh(unsigned int hook, struct net *net,
elem = rcu_dereference(net->nf.hooks[NFPROTO_BRIDGE][hook]);
- while (elem && (elem->ops.priority <= NF_BR_PRI_BRNF))
+ while (elem && (nf_hook_entry_priority(elem) <= NF_BR_PRI_BRNF))
elem = rcu_dereference(elem->next);
if (!elem)
diff --git a/net/netfilter/core.c b/net/netfilter/core.c
index de30e08..2bb46e2 100644
--- a/net/netfilter/core.c
+++ b/net/netfilter/core.c
@@ -102,15 +102,13 @@ int nf_register_net_hook(struct net *net, const struct nf_hook_ops *reg)
if (!entry)
return -ENOMEM;
- entry->orig_ops = reg;
- entry->ops = *reg;
- entry->next = NULL;
+ nf_hook_entry_init(entry, reg);
mutex_lock(&nf_hook_mutex);
/* Find the spot in the list */
while ((p = nf_entry_dereference(*pp)) != NULL) {
- if (reg->priority < p->orig_ops->priority)
+ if (reg->priority < nf_hook_entry_priority(p))
break;
pp = &p->next;
}
@@ -140,7 +138,7 @@ void nf_unregister_net_hook(struct net *net, const struct nf_hook_ops *reg)
mutex_lock(&nf_hook_mutex);
while ((p = nf_entry_dereference(*pp)) != NULL) {
- if (p->orig_ops == reg) {
+ if (nf_hook_entry_ops(p) == reg) {
rcu_assign_pointer(*pp, p->next);
break;
}
@@ -311,7 +309,7 @@ int nf_hook_slow(struct sk_buff *skb, struct nf_hook_state *state,
int ret;
do {
- verdict = entry->ops.hook(entry->ops.priv, skb, state);
+ verdict = nf_hook_entry_hookfn(entry, skb, state);
switch (verdict & NF_VERDICT_MASK) {
case NF_ACCEPT:
entry = rcu_dereference(entry->next);
diff --git a/net/netfilter/nf_queue.c b/net/netfilter/nf_queue.c
index 77cba9f..4a76624 100644
--- a/net/netfilter/nf_queue.c
+++ b/net/netfilter/nf_queue.c
@@ -185,7 +185,7 @@ static unsigned int nf_iterate(struct sk_buff *skb,
do {
repeat:
- verdict = (*entryp)->ops.hook((*entryp)->ops.priv, skb, state);
+ verdict = nf_hook_entry_hookfn((*entryp), skb, state);
if (verdict != NF_ACCEPT) {
if (verdict != NF_REPEAT)
return verdict;
@@ -200,7 +200,6 @@ static unsigned int nf_iterate(struct sk_buff *skb,
void nf_reinject(struct nf_queue_entry *entry, unsigned int verdict)
{
struct nf_hook_entry *hook_entry = entry->hook;
- struct nf_hook_ops *elem = &hook_entry->ops;
struct sk_buff *skb = entry->skb;
const struct nf_afinfo *afinfo;
int err;
@@ -209,7 +208,7 @@ void nf_reinject(struct nf_queue_entry *entry, unsigned int verdict)
/* Continue traversal iff userspace said ok... */
if (verdict == NF_REPEAT)
- verdict = elem->hook(elem->priv, skb, &entry->state);
+ verdict = nf_hook_entry_hookfn(hook_entry, skb, &entry->state);
if (verdict == NF_ACCEPT) {
afinfo = nf_get_afinfo(entry->state.pf);
--
2.7.4
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH nf-next 2/3] netfilter: decouple nf_hook_entry and nf_hook_ops
2016-11-15 22:48 [PATCH nf-next 0/3] Additional nf_hook_entry compaction Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 1/3] netfilter: introduce accessor functions for hook entries Aaron Conole
@ 2016-11-15 22:48 ` Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 3/3] netfilter: convert while loops to for loops Aaron Conole
2016-12-04 20:11 ` [PATCH nf-next 0/3] Additional nf_hook_entry compaction Pablo Neira Ayuso
3 siblings, 0 replies; 5+ messages in thread
From: Aaron Conole @ 2016-11-15 22:48 UTC (permalink / raw)
To: netfilter-devel
Cc: Pablo Neira Ayuso, Florian Westphal, Jozsef Kadlecsik, coreteam,
David S . Miller
From: Aaron Conole <aconole@redhat.com>
During nfhook traversal we only need a very small subset of
nf_hook_ops members.
We need:
- next element
- hook function to call
- hook function priv argument
Bridge netfilter also needs 'thresh'; can be obtained via ->orig_ops.
nf_hook_entry struct is now 32 bytes on x86_64.
A followup patch will turn the run-time list into an array that only
stores hook functions plus their priv arguments, eliminating the ->next
element.
Suggested-by: Florian Westphal <fw@strlen.de>
Signed-off-by: Aaron Conole <aconole@bytheb.org>
---
include/linux/netfilter.h | 10 ++++++----
1 file changed, 6 insertions(+), 4 deletions(-)
diff --git a/include/linux/netfilter.h b/include/linux/netfilter.h
index 575aa19..a4b97be 100644
--- a/include/linux/netfilter.h
+++ b/include/linux/netfilter.h
@@ -75,7 +75,8 @@ struct nf_hook_ops {
struct nf_hook_entry {
struct nf_hook_entry __rcu *next;
- struct nf_hook_ops ops;
+ nf_hookfn *hook;
+ void *priv;
const struct nf_hook_ops *orig_ops;
};
@@ -83,21 +84,22 @@ static inline void
nf_hook_entry_init(struct nf_hook_entry *entry, const struct nf_hook_ops *ops)
{
entry->next = NULL;
- entry->ops = *ops;
+ entry->hook = ops->hook;
+ entry->priv = ops->priv;
entry->orig_ops = ops;
}
static inline int
nf_hook_entry_priority(const struct nf_hook_entry *entry)
{
- return entry->ops.priority;
+ return entry->orig_ops->priority;
}
static inline int
nf_hook_entry_hookfn(const struct nf_hook_entry *entry, struct sk_buff *skb,
struct nf_hook_state *state)
{
- return entry->ops.hook(entry->ops.priv, skb, state);
+ return entry->hook(entry->priv, skb, state);
}
static inline const struct nf_hook_ops *
--
2.7.4
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH nf-next 3/3] netfilter: convert while loops to for loops
2016-11-15 22:48 [PATCH nf-next 0/3] Additional nf_hook_entry compaction Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 1/3] netfilter: introduce accessor functions for hook entries Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 2/3] netfilter: decouple nf_hook_entry and nf_hook_ops Aaron Conole
@ 2016-11-15 22:48 ` Aaron Conole
2016-12-04 20:11 ` [PATCH nf-next 0/3] Additional nf_hook_entry compaction Pablo Neira Ayuso
3 siblings, 0 replies; 5+ messages in thread
From: Aaron Conole @ 2016-11-15 22:48 UTC (permalink / raw)
To: netfilter-devel
Cc: Pablo Neira Ayuso, Florian Westphal, Jozsef Kadlecsik, coreteam,
David S . Miller
This is to facilitate converting from a singly-linked list to an array
of elements.
Signed-off-by: Aaron Conole <aconole@bytheb.org>
---
net/bridge/br_netfilter_hooks.c | 8 ++++----
net/netfilter/core.c | 6 ++----
2 files changed, 6 insertions(+), 8 deletions(-)
diff --git a/net/bridge/br_netfilter_hooks.c b/net/bridge/br_netfilter_hooks.c
index ef8cfa7..1434de1 100644
--- a/net/bridge/br_netfilter_hooks.c
+++ b/net/bridge/br_netfilter_hooks.c
@@ -1008,10 +1008,10 @@ int br_nf_hook_thresh(unsigned int hook, struct net *net,
struct nf_hook_state state;
int ret;
- elem = rcu_dereference(net->nf.hooks[NFPROTO_BRIDGE][hook]);
-
- while (elem && (nf_hook_entry_priority(elem) <= NF_BR_PRI_BRNF))
- elem = rcu_dereference(elem->next);
+ for (elem = rcu_dereference(net->nf.hooks[NFPROTO_BRIDGE][hook]);
+ nf_hook_entry_priority(elem) <= NF_BR_PRI_BRNF;
+ elem = rcu_dereference(elem->next))
+ ;
if (!elem)
return okfn(net, sk, skb);
diff --git a/net/netfilter/core.c b/net/netfilter/core.c
index 2bb46e2..ce6adfa 100644
--- a/net/netfilter/core.c
+++ b/net/netfilter/core.c
@@ -107,10 +107,9 @@ int nf_register_net_hook(struct net *net, const struct nf_hook_ops *reg)
mutex_lock(&nf_hook_mutex);
/* Find the spot in the list */
- while ((p = nf_entry_dereference(*pp)) != NULL) {
+ for (; (p = nf_entry_dereference(*pp)) != NULL; pp = &p->next) {
if (reg->priority < nf_hook_entry_priority(p))
break;
- pp = &p->next;
}
rcu_assign_pointer(entry->next, p);
rcu_assign_pointer(*pp, entry);
@@ -137,12 +136,11 @@ void nf_unregister_net_hook(struct net *net, const struct nf_hook_ops *reg)
return;
mutex_lock(&nf_hook_mutex);
- while ((p = nf_entry_dereference(*pp)) != NULL) {
+ for (; (p = nf_entry_dereference(*pp)) != NULL; pp = &p->next) {
if (nf_hook_entry_ops(p) == reg) {
rcu_assign_pointer(*pp, p->next);
break;
}
- pp = &p->next;
}
mutex_unlock(&nf_hook_mutex);
if (!p) {
--
2.7.4
^ permalink raw reply related [flat|nested] 5+ messages in thread
* Re: [PATCH nf-next 0/3] Additional nf_hook_entry compaction
2016-11-15 22:48 [PATCH nf-next 0/3] Additional nf_hook_entry compaction Aaron Conole
` (2 preceding siblings ...)
2016-11-15 22:48 ` [PATCH nf-next 3/3] netfilter: convert while loops to for loops Aaron Conole
@ 2016-12-04 20:11 ` Pablo Neira Ayuso
3 siblings, 0 replies; 5+ messages in thread
From: Pablo Neira Ayuso @ 2016-12-04 20:11 UTC (permalink / raw)
To: Aaron Conole
Cc: netfilter-devel, Florian Westphal, Jozsef Kadlecsik, coreteam,
David S . Miller
On Tue, Nov 15, 2016 at 05:48:43PM -0500, Aaron Conole wrote:
> This series introduces a set of accessors, compacts the nf_hook_entry, and
> rearranges some of the loops in preparation for the final set of work going
> to an array based hook system.
>
> After this series, the nf_hook_entry should fit in a cacheline on a modern
> Intel i7.
Series applied, thanks Aaron.
^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2016-12-04 20:11 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2016-11-15 22:48 [PATCH nf-next 0/3] Additional nf_hook_entry compaction Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 1/3] netfilter: introduce accessor functions for hook entries Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 2/3] netfilter: decouple nf_hook_entry and nf_hook_ops Aaron Conole
2016-11-15 22:48 ` [PATCH nf-next 3/3] netfilter: convert while loops to for loops Aaron Conole
2016-12-04 20:11 ` [PATCH nf-next 0/3] Additional nf_hook_entry compaction Pablo Neira Ayuso
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.