lkml.org 
[lkml]   [2008]   [May]   [13]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
Patch in this message
/
Date
From
Subject[patch 17/37] can: Fix can_send() handling on dev_queue_xmit() failures
2.6.25-stable review patch.  If anyone has any objections, please let us
know.

------------------
From: Oliver Hartkopp <oliver@hartkopp.net>

[ Upstream commit: c2ab7ac225e29006b7117d6a9fe8f3be8d98b0c2 ]

The tx packet counting and the local loopback of CAN frames should
only happen in the case that the CAN frame has been enqueued to the
netdevice tx queue successfully.

Thanks to Andre Naujoks <nautsch@gmail.com> for reporting this issue.

Signed-off-by: Oliver Hartkopp <oliver@hartkopp.net>
Signed-off-by: Urs Thuermann <urs@isnogud.escape.de>
Signed-off-by: David S. Miller <davem@davemloft.net>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>

---
net/can/af_can.c | 16 ++++++++++++----
1 file changed, 12 insertions(+), 4 deletions(-)

--- a/net/can/af_can.c
+++ b/net/can/af_can.c
@@ -208,6 +208,7 @@ static int can_create(struct net *net, s
*/
int can_send(struct sk_buff *skb, int loop)
{
+ struct sk_buff *newskb = NULL;
int err;

if (skb->dev->type != ARPHRD_CAN) {
@@ -244,8 +245,7 @@ int can_send(struct sk_buff *skb, int lo
* If the interface is not capable to do loopback
* itself, we do it here.
*/
- struct sk_buff *newskb = skb_clone(skb, GFP_ATOMIC);
-
+ newskb = skb_clone(skb, GFP_ATOMIC);
if (!newskb) {
kfree_skb(skb);
return -ENOMEM;
@@ -254,7 +254,6 @@ int can_send(struct sk_buff *skb, int lo
newskb->sk = skb->sk;
newskb->ip_summed = CHECKSUM_UNNECESSARY;
newskb->pkt_type = PACKET_BROADCAST;
- netif_rx(newskb);
}
} else {
/* indication for the CAN driver: no loopback required */
@@ -266,11 +265,20 @@ int can_send(struct sk_buff *skb, int lo
if (err > 0)
err = net_xmit_errno(err);

+ if (err) {
+ if (newskb)
+ kfree_skb(newskb);
+ return err;
+ }
+
+ if (newskb)
+ netif_rx(newskb);
+
/* update statistics */
can_stats.tx_frames++;
can_stats.tx_frames_delta++;

- return err;
+ return 0;
}
EXPORT_SYMBOL(can_send);

--


\
 
 \ /
  Last update: 2008-05-13 22:21    [W:0.320 / U:0.808 seconds]
©2003-2017 Jasper Spaans. hosted at Digital OceanAdvertise on this site