diff options
| -rw-r--r-- | drivers/net/usb/cdc_ncm.c | 19 |
1 files changed, 12 insertions, 7 deletions
diff --git a/drivers/net/usb/cdc_ncm.c b/drivers/net/usb/cdc_ncm.c index d776c4a8d3c1..04e8ce14a1d0 100644 --- a/drivers/net/usb/cdc_ncm.c +++ b/drivers/net/usb/cdc_ncm.c | |||
| @@ -54,7 +54,7 @@ | |||
| 54 | #include <linux/usb/usbnet.h> | 54 | #include <linux/usb/usbnet.h> |
| 55 | #include <linux/usb/cdc.h> | 55 | #include <linux/usb/cdc.h> |
| 56 | 56 | ||
| 57 | #define DRIVER_VERSION "30-Nov-2010" | 57 | #define DRIVER_VERSION "17-Jan-2011" |
| 58 | 58 | ||
| 59 | /* CDC NCM subclass 3.2.1 */ | 59 | /* CDC NCM subclass 3.2.1 */ |
| 60 | #define USB_CDC_NCM_NDP16_LENGTH_MIN 0x10 | 60 | #define USB_CDC_NCM_NDP16_LENGTH_MIN 0x10 |
| @@ -868,15 +868,19 @@ static void cdc_ncm_tx_timeout(unsigned long arg) | |||
| 868 | if (ctx->tx_timer_pending != 0) { | 868 | if (ctx->tx_timer_pending != 0) { |
| 869 | ctx->tx_timer_pending--; | 869 | ctx->tx_timer_pending--; |
| 870 | restart = 1; | 870 | restart = 1; |
| 871 | } else | 871 | } else { |
| 872 | restart = 0; | 872 | restart = 0; |
| 873 | } | ||
| 873 | 874 | ||
| 874 | spin_unlock(&ctx->mtx); | 875 | spin_unlock(&ctx->mtx); |
| 875 | 876 | ||
| 876 | if (restart) | 877 | if (restart) { |
| 878 | spin_lock(&ctx->mtx); | ||
| 877 | cdc_ncm_tx_timeout_start(ctx); | 879 | cdc_ncm_tx_timeout_start(ctx); |
| 878 | else if (ctx->netdev != NULL) | 880 | spin_unlock(&ctx->mtx); |
| 881 | } else if (ctx->netdev != NULL) { | ||
| 879 | usbnet_start_xmit(NULL, ctx->netdev); | 882 | usbnet_start_xmit(NULL, ctx->netdev); |
| 883 | } | ||
| 880 | } | 884 | } |
| 881 | 885 | ||
| 882 | static struct sk_buff * | 886 | static struct sk_buff * |
| @@ -900,7 +904,6 @@ cdc_ncm_tx_fixup(struct usbnet *dev, struct sk_buff *skb, gfp_t flags) | |||
| 900 | skb_out = cdc_ncm_fill_tx_frame(ctx, skb); | 904 | skb_out = cdc_ncm_fill_tx_frame(ctx, skb); |
| 901 | if (ctx->tx_curr_skb != NULL) | 905 | if (ctx->tx_curr_skb != NULL) |
| 902 | need_timer = 1; | 906 | need_timer = 1; |
| 903 | spin_unlock(&ctx->mtx); | ||
| 904 | 907 | ||
| 905 | /* Start timer, if there is a remaining skb */ | 908 | /* Start timer, if there is a remaining skb */ |
| 906 | if (need_timer) | 909 | if (need_timer) |
| @@ -908,6 +911,8 @@ cdc_ncm_tx_fixup(struct usbnet *dev, struct sk_buff *skb, gfp_t flags) | |||
| 908 | 911 | ||
| 909 | if (skb_out) | 912 | if (skb_out) |
| 910 | dev->net->stats.tx_packets += ctx->tx_curr_frame_num; | 913 | dev->net->stats.tx_packets += ctx->tx_curr_frame_num; |
| 914 | |||
| 915 | spin_unlock(&ctx->mtx); | ||
| 911 | return skb_out; | 916 | return skb_out; |
| 912 | 917 | ||
| 913 | error: | 918 | error: |
| @@ -1020,8 +1025,8 @@ static int cdc_ncm_rx_fixup(struct usbnet *dev, struct sk_buff *skb_in) | |||
| 1020 | if (((offset + temp) > actlen) || | 1025 | if (((offset + temp) > actlen) || |
| 1021 | (temp > CDC_NCM_MAX_DATAGRAM_SIZE) || (temp < ETH_HLEN)) { | 1026 | (temp > CDC_NCM_MAX_DATAGRAM_SIZE) || (temp < ETH_HLEN)) { |
| 1022 | pr_debug("invalid frame detected (ignored)" | 1027 | pr_debug("invalid frame detected (ignored)" |
| 1023 | "offset[%u]=%u, length=%u, skb=%p\n", | 1028 | "offset[%u]=%u, length=%u, skb=%p\n", |
| 1024 | x, offset, temp, skb_in); | 1029 | x, offset, temp, skb_in); |
| 1025 | if (!x) | 1030 | if (!x) |
| 1026 | goto error; | 1031 | goto error; |
| 1027 | break; | 1032 | break; |
