From: Eric Dumazet <dada1@cosmosbay.com>
To: linux-kernel@vger.kernel.org,
netfilter-devel@lists.netfilter.org, netdev@vger.kernel.org
Cc: Andi Kleen <ak@suse.de>
Subject: [PATCH 2/3] netfilter : 3 patches to boost ip_tables performance
Date: Wed, 21 Sep 2005 23:32:24 +0200 [thread overview]
Message-ID: <4331D168.6090604@cosmosbay.com> (raw)
In-Reply-To: <43308324.70403@cosmosbay.com>
[-- Attachment #1: Type: text/plain, Size: 330 bytes --]
Patch 2/3 (please apply after Patch 1/3)
2) Loop unrolling
It seems that with current compilers and CFLAGS, the code from
ip_packet_match() is very bad, using lot of mispredicted conditional branches
I made some patches and generated code on i386 and x86_64
is much better.
Signed-off-by: Eric Dumazet <dada1@cosmosbay.com>
[-- Attachment #2: patch_ip_tables_numa.2 --]
[-- Type: text/plain, Size: 3958 bytes --]
--- linux-2.6/net/ipv4/netfilter/ip_tables.c 2005-09-21 23:55:30.000000000 +0200
+++ linux-2.6-ed/net/ipv4/netfilter/ip_tables.c 2005-09-22 00:39:29.000000000 +0200
@@ -125,6 +125,27 @@
#define up(x) do { printk("UP:%u:" #x "\n", __LINE__); up(x); } while(0)
#endif
+/*
+ * Special macro to compare IFNAMSIZ 'strings', with mask.
+ * Best results if feeded with 3 args pointing to 'unsigned long' types
+ * Loop is manually unrolled for performance reasons.
+ * gcc generates code without branches, IFNAMSIZ being a constant
+ */
+#define compare_if_lstrings(ret, devname, expect, expect_mask) \
+ ret = ((devname)[0] ^ (expect)[0]) & (expect_mask)[0]; \
+ if (IFNAMSIZ > sizeof(*devname)) \
+ ret |= ((devname)[1] ^ (expect)[1]) & (expect_mask)[1]; \
+ if (IFNAMSIZ > 2 * sizeof(*devname)) \
+ ret |= ((devname)[2] ^ (expect)[2]) & (expect_mask)[2]; \
+ if (IFNAMSIZ > 3 * sizeof(*devname)) \
+ ret |= ((devname)[3] ^ (expect)[3]) & (expect_mask)[3]; \
+ /* just in case IFNAMSIZ is enlarged */ \
+ if (IFNAMSIZ > 4 * sizeof(*devname)) { \
+ int i; \
+ for (i = 4 ; (i < IFNAMSIZ/sizeof(*devname)); i++) \
+ ret |= ((devname)[i] ^ (expect)[i]) & (expect_mask)[i]; \
+ }
+
/* Returns whether matches rule or not. */
static inline int
ip_packet_match(const struct iphdr *ip,
@@ -133,16 +154,22 @@
const struct ipt_ip *ipinfo,
int isfrag)
{
- size_t i;
+ int bool1, bool2;
unsigned long ret;
#define FWINV(bool,invflg) ((bool) ^ !!(ipinfo->invflags & invflg))
- if (FWINV((ip->saddr&ipinfo->smsk.s_addr) != ipinfo->src.s_addr,
- IPT_INV_SRCIP)
- || FWINV((ip->daddr&ipinfo->dmsk.s_addr) != ipinfo->dst.s_addr,
- IPT_INV_DSTIP)) {
- dprintf("Source or dest mismatch.\n");
+ bool1 = ((ip->saddr&ipinfo->smsk.s_addr) != ipinfo->src.s_addr);
+ bool1 ^= !!(ipinfo->invflags & IPT_INV_SRCIP);
+
+ bool2 = ((ip->daddr&ipinfo->dmsk.s_addr) != ipinfo->dst.s_addr);
+ bool2 ^= !!(ipinfo->invflags & IPT_INV_DSTIP);
+
+ if ((bool1 | bool2) != 0) {
+ if (bool1)
+ dprintf("Source%s mismatch.\n", bool2 ? " and Dest":"");
+ else
+ dprintf("Dest mismatch.\n");
dprintf("SRC: %u.%u.%u.%u. Mask: %u.%u.%u.%u. Target: %u.%u.%u.%u.%s\n",
NIPQUAD(ip->saddr),
@@ -157,27 +184,26 @@
return 0;
}
- /* Look for ifname matches; this should unroll nicely. */
- for (i = 0, ret = 0; i < IFNAMSIZ/sizeof(unsigned long); i++) {
- ret |= (((const unsigned long *)indev)[i]
- ^ ((const unsigned long *)ipinfo->iniface)[i])
- & ((const unsigned long *)ipinfo->iniface_mask)[i];
- }
+ compare_if_lstrings(ret,
+ (const unsigned long *)indev,
+ (const unsigned long *)ipinfo->iniface,
+ (const unsigned long *)ipinfo->iniface_mask);
- if (FWINV(ret != 0, IPT_INV_VIA_IN)) {
+ bool1 = FWINV(ret != 0, IPT_INV_VIA_IN);
+ if (bool1) {
dprintf("VIA in mismatch (%s vs %s).%s\n",
indev, ipinfo->iniface,
ipinfo->invflags&IPT_INV_VIA_IN ?" (INV)":"");
return 0;
}
- for (i = 0, ret = 0; i < IFNAMSIZ/sizeof(unsigned long); i++) {
- ret |= (((const unsigned long *)outdev)[i]
- ^ ((const unsigned long *)ipinfo->outiface)[i])
- & ((const unsigned long *)ipinfo->outiface_mask)[i];
- }
+ compare_if_lstrings(ret,
+ (const unsigned long *)outdev,
+ (const unsigned long *)ipinfo->outiface,
+ (const unsigned long *)ipinfo->outiface_mask);
- if (FWINV(ret != 0, IPT_INV_VIA_OUT)) {
+ bool1 = FWINV(ret != 0, IPT_INV_VIA_OUT);
+ if (bool1) {
dprintf("VIA out mismatch (%s vs %s).%s\n",
outdev, ipinfo->outiface,
ipinfo->invflags&IPT_INV_VIA_OUT ?" (INV)":"");
@@ -185,8 +211,9 @@
}
/* Check specific protocol */
- if (ipinfo->proto
- && FWINV(ip->protocol != ipinfo->proto, IPT_INV_PROTO)) {
+ bool1 = FWINV(ip->protocol != ipinfo->proto, IPT_INV_PROTO) ;
+ bool1 &= (ipinfo->proto != 0);
+ if (bool1) {
dprintf("Packet protocol %hi does not match %hi.%s\n",
ip->protocol, ipinfo->proto,
ipinfo->invflags&IPT_INV_PROTO ? " (INV)":"");
next prev parent reply other threads:[~2005-09-21 21:32 UTC|newest]
Thread overview: 72+ messages / expand[flat|nested] mbox.gz Atom feed top
2005-09-19 17:09 [PATCH, netfilter] NUMA aware ipv4/netfilter/ip_tables.c Eric dumazet
2005-09-19 17:20 ` Eric Dumazet
2005-09-19 17:48 ` Andi Kleen
2005-09-19 19:09 ` Eric Dumazet
2005-09-20 9:47 ` Eric Dumazet
2005-09-20 16:30 ` Andi Kleen
2005-09-20 17:02 ` Eric Dumazet
2005-09-20 21:45 ` [PATCH] Adds sys_set_mempolicy() in include/linux/syscalls.h , " Eric Dumazet
2005-09-20 21:45 ` Eric Dumazet
2005-09-20 21:46 ` [PATCH] Adds sys_set_mempolicy() in include/linux/syscalls.h Eric Dumazet
2005-09-21 21:24 ` [PATCH 0/3] netfilter : 3 patches to boost ip_tables performance Eric Dumazet
2005-09-21 22:43 ` Christoph Lameter
2005-09-22 0:34 ` David S. Miller
2005-09-22 0:34 ` David S. Miller
2005-09-22 1:44 ` Christoph Lameter
2005-09-22 12:11 ` Eric Dumazet
2005-09-22 12:11 ` Eric Dumazet
2005-09-22 12:49 ` Christoph Hellwig
2005-09-22 12:54 ` Andi Kleen
2005-09-22 12:58 ` Christoph Hellwig
2005-09-22 13:05 ` Andi Kleen
2005-09-22 15:37 ` Christoph Lameter
2005-09-22 15:50 ` Eric Dumazet
2005-09-22 15:50 ` Eric Dumazet
2005-09-22 15:55 ` Christoph Lameter
2005-09-23 17:11 ` Harald Welte
2005-09-23 17:44 ` Christoph Lameter
2005-09-23 18:04 ` Dave Hansen
2005-09-26 17:58 ` vmalloc_node Christoph Lameter
2005-09-26 18:10 ` vmalloc_node Dave Hansen
2005-09-23 17:47 ` [PATCH 0/3] netfilter : 3 patches to boost ip_tables performance Eric Dumazet
2005-09-23 18:00 ` Kyle Moffett
2005-09-22 4:18 ` James Morris
2005-09-22 4:18 ` James Morris
2005-09-22 5:07 ` Eric Dumazet
2005-09-22 13:03 ` Andi Kleen
2005-09-22 13:30 ` Eric Dumazet
2005-09-23 17:09 ` Harald Welte
2005-09-27 16:23 ` Andi Kleen
2005-09-28 0:25 ` Henrik Nordstrom
2005-09-28 8:32 ` Harald Welte
2005-09-28 8:32 ` Harald Welte
2005-09-28 8:37 ` Andi Kleen
2005-09-28 8:37 ` Andi Kleen
2005-10-04 17:01 ` Patrick McHardy
2005-10-05 16:53 ` Andi Kleen
2005-10-07 2:38 ` Harald Welte
2005-10-06 17:59 ` Andi Kleen
2005-10-07 17:08 ` Patrick McHardy
2005-10-07 17:21 ` Andi Kleen
2005-10-07 17:50 ` Patrick McHardy
2005-09-28 10:34 ` Henrik Nordstrom
2005-09-28 10:34 ` Henrik Nordstrom
2005-11-25 11:23 ` [PATCH] netfilter : zap get_cpu()/put_cpu() calls from ip_tables Eric Dumazet
2005-11-25 11:28 ` [PATCH (resent with the attachment !)] " Eric Dumazet
2005-11-25 18:20 ` Patrick McHardy
2005-09-21 21:29 ` [PATCH 1/3] netfilter : 3 patches to boost ip_tables performance Eric Dumazet
2005-09-22 12:57 ` Harald Welte
2005-09-22 12:57 ` Harald Welte
2005-09-22 13:17 ` Eric Dumazet
2005-09-22 13:17 ` Eric Dumazet
2005-09-21 21:32 ` Eric Dumazet [this message]
2005-09-22 12:48 ` [PATCH 2/3] " Harald Welte
2005-09-22 12:48 ` Harald Welte
2005-09-22 13:05 ` Eric Dumazet
2005-09-23 4:02 ` Willy Tarreau
2005-09-23 5:14 ` Eric Dumazet
2005-09-23 11:33 ` Willy Tarreau
2005-09-23 14:00 ` Tim Mattox
2005-09-21 21:37 ` [PATCH 3/3] " Eric Dumazet
2005-09-22 12:50 ` Harald Welte
2005-09-22 12:50 ` Harald Welte
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=4331D168.6090604@cosmosbay.com \
--to=dada1@cosmosbay.com \
--cc=ak@suse.de \
--cc=linux-kernel@vger.kernel.org \
--cc=netdev@vger.kernel.org \
--cc=netfilter-devel@lists.netfilter.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
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.