diff options
| author | Changli Gao <xiaosuo@gmail.com> | 2011-02-21 20:55:18 -0500 |
|---|---|---|
| committer | David S. Miller <davem@davemloft.net> | 2011-02-28 15:28:50 -0500 |
| commit | 696ea472e19c6d1fa843bb1abce73b9c3a414391 (patch) | |
| tree | 8b3daa80cdb971246902717ad4e33d5db45d1b0e /net/llc | |
| parent | 985076720187af7ac0c2de4dfe912acba9b4f586 (diff) | |
llc: avoid skb_clone() if there is only one handler
Signed-off-by: Changli Gao <xiaosuo@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/llc')
| -rw-r--r-- | net/llc/llc_input.c | 25 |
1 files changed, 13 insertions, 12 deletions
diff --git a/net/llc/llc_input.c b/net/llc/llc_input.c index f99687439139..058f1e9a9128 100644 --- a/net/llc/llc_input.c +++ b/net/llc/llc_input.c | |||
| @@ -181,25 +181,26 @@ int llc_rcv(struct sk_buff *skb, struct net_device *dev, | |||
| 181 | * LLC functionality | 181 | * LLC functionality |
| 182 | */ | 182 | */ |
| 183 | rcv = rcu_dereference(sap->rcv_func); | 183 | rcv = rcu_dereference(sap->rcv_func); |
| 184 | if (rcv) { | ||
| 185 | struct sk_buff *cskb = skb_clone(skb, GFP_ATOMIC); | ||
| 186 | if (cskb) | ||
| 187 | rcv(cskb, dev, pt, orig_dev); | ||
| 188 | } | ||
| 189 | dest = llc_pdu_type(skb); | 184 | dest = llc_pdu_type(skb); |
| 190 | if (unlikely(!dest || !llc_type_handlers[dest - 1])) | 185 | if (unlikely(!dest || !llc_type_handlers[dest - 1])) { |
| 191 | goto drop_put; | 186 | if (rcv) |
| 192 | llc_type_handlers[dest - 1](sap, skb); | 187 | rcv(skb, dev, pt, orig_dev); |
| 193 | out_put: | 188 | else |
| 189 | kfree_skb(skb); | ||
| 190 | } else { | ||
| 191 | if (rcv) { | ||
| 192 | struct sk_buff *cskb = skb_clone(skb, GFP_ATOMIC); | ||
| 193 | if (cskb) | ||
| 194 | rcv(cskb, dev, pt, orig_dev); | ||
| 195 | } | ||
| 196 | llc_type_handlers[dest - 1](sap, skb); | ||
| 197 | } | ||
| 194 | llc_sap_put(sap); | 198 | llc_sap_put(sap); |
| 195 | out: | 199 | out: |
| 196 | return 0; | 200 | return 0; |
| 197 | drop: | 201 | drop: |
| 198 | kfree_skb(skb); | 202 | kfree_skb(skb); |
| 199 | goto out; | 203 | goto out; |
| 200 | drop_put: | ||
| 201 | kfree_skb(skb); | ||
| 202 | goto out_put; | ||
| 203 | handle_station: | 204 | handle_station: |
| 204 | if (!llc_station_handler) | 205 | if (!llc_station_handler) |
| 205 | goto drop; | 206 | goto drop; |
