]>
Commit | Line | Data |
---|---|---|
97bb1c57 AF |
1 | From: Eric Dumazet <eric.dumazet@gmail.com> |
2 | Date: Mon, 28 Nov 2011 20:30:35 +0000 | |
3 | Subject: [PATCH 2/3] flow_dissector: use a 64bit load/store | |
4 | MIME-Version: 1.0 | |
5 | Content-Type: text/plain; charset=UTF-8 | |
6 | Content-Transfer-Encoding: 8bit | |
7 | ||
8 | commit 4d77d2b567ec66a443792d99e96ac760991d80d0 upstream. | |
9 | ||
10 | Le lundi 28 novembre 2011 à 19:06 -0500, David Miller a écrit : | |
11 | > From: Dimitris Michailidis <dm@chelsio.com> | |
12 | > Date: Mon, 28 Nov 2011 08:25:39 -0800 | |
13 | > | |
14 | > >> +bool skb_flow_dissect(const struct sk_buff *skb, struct flow_keys | |
15 | > >> *flow) | |
16 | > >> +{ | |
17 | > >> + int poff, nhoff = skb_network_offset(skb); | |
18 | > >> + u8 ip_proto; | |
19 | > >> + u16 proto = skb->protocol; | |
20 | > > | |
21 | > > __be16 instead of u16 for proto? | |
22 | > | |
23 | > I'll take care of this when I apply these patches. | |
24 | ||
25 | ( CC trimmed ) | |
26 | ||
27 | Thanks David ! | |
28 | ||
29 | Here is a small patch to use one 64bit load/store on x86_64 instead of | |
30 | two 32bit load/stores. | |
31 | ||
32 | [PATCH net-next] flow_dissector: use a 64bit load/store | |
33 | ||
34 | gcc compiler is smart enough to use a single load/store if we | |
35 | memcpy(dptr, sptr, 8) on x86_64, regardless of | |
36 | CONFIG_CC_OPTIMIZE_FOR_SIZE | |
37 | ||
38 | In IP header, daddr immediately follows saddr, this wont change in the | |
39 | future. We only need to make sure our flow_keys (src,dst) fields wont | |
40 | break the rule. | |
41 | ||
42 | Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com> | |
43 | Signed-off-by: David S. Miller <davem@davemloft.net> | |
44 | ||
45 | diff --git a/include/net/flow_keys.h b/include/net/flow_keys.h | |
46 | index e4cb285..80461c1 100644 | |
47 | --- a/include/net/flow_keys.h | |
48 | +++ b/include/net/flow_keys.h | |
49 | @@ -2,6 +2,7 @@ | |
50 | #define _NET_FLOW_KEYS_H | |
51 | ||
52 | struct flow_keys { | |
53 | + /* (src,dst) must be grouped, in the same way than in IP header */ | |
54 | __be32 src; | |
55 | __be32 dst; | |
56 | union { | |
57 | diff --git a/net/core/flow_dissector.c b/net/core/flow_dissector.c | |
58 | index f0516d9..0985b9b 100644 | |
59 | --- a/net/core/flow_dissector.c | |
60 | +++ b/net/core/flow_dissector.c | |
61 | @@ -8,6 +8,16 @@ | |
62 | #include <linux/ppp_defs.h> | |
63 | #include <net/flow_keys.h> | |
64 | ||
65 | +/* copy saddr & daddr, possibly using 64bit load/store | |
66 | + * Equivalent to : flow->src = iph->saddr; | |
67 | + * flow->dst = iph->daddr; | |
68 | + */ | |
69 | +static void iph_to_flow_copy_addrs(struct flow_keys *flow, const struct iphdr *iph) | |
70 | +{ | |
71 | + BUILD_BUG_ON(offsetof(typeof(*flow), dst) != | |
72 | + offsetof(typeof(*flow), src) + sizeof(flow->src)); | |
73 | + memcpy(&flow->src, &iph->saddr, sizeof(flow->src) + sizeof(flow->dst)); | |
74 | +} | |
75 | ||
76 | bool skb_flow_dissect(const struct sk_buff *skb, struct flow_keys *flow) | |
77 | { | |
78 | @@ -31,8 +41,7 @@ ip: | |
79 | ip_proto = 0; | |
80 | else | |
81 | ip_proto = iph->protocol; | |
82 | - flow->src = iph->saddr; | |
83 | - flow->dst = iph->daddr; | |
84 | + iph_to_flow_copy_addrs(flow, iph); | |
85 | nhoff += iph->ihl * 4; | |
86 | break; | |
87 | } | |
88 | -- | |
89 | 1.7.10 | |
90 |