From 140cb81ac8c625942a1d695875932c615767a526 Mon Sep 17 00:00:00 2001 From: Johan Hovold Date: Mon, 26 May 2014 19:23:38 +0200 Subject: USB: cdc-acm: fix broken runtime suspend The current ACM runtime-suspend implementation is broken in several ways: Firstly, it buffers only the first write request being made while suspended -- any further writes are silently dropped. Secondly, writes being dropped also leak write urbs, which are never reclaimed (until the device is unbound). Thirdly, even the single buffered write is not cleared at shutdown (which may happen before the device is resumed), something which can lead to another urb leak as well as a PM usage-counter leak. Fix this by implementing a delayed-write queue using urb anchors and making sure to discard the queue properly at shutdown. Fixes: 11ea859d64b6 ("USB: additional power savings for cdc-acm devices that support remote wakeup") Reported-by: Xiao Jin Cc: # v2.6.27 Signed-off-by: Johan Hovold Signed-off-by: Greg Kroah-Hartman --- drivers/usb/class/cdc-acm.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/usb/class/cdc-acm.h') diff --git a/drivers/usb/class/cdc-acm.h b/drivers/usb/class/cdc-acm.h index e38dc785808..80826f843e0 100644 --- a/drivers/usb/class/cdc-acm.h +++ b/drivers/usb/class/cdc-acm.h @@ -120,7 +120,7 @@ struct acm { unsigned int throttled:1; /* actually throttled */ unsigned int throttle_req:1; /* throttle requested */ u8 bInterval; - struct acm_wb *delayed_wb; /* write queued for a device about to be woken */ + struct usb_anchor delayed; /* writes queued for a device about to be woken */ }; #define CDC_DATA_INTERFACE_TYPE 0x0a -- cgit v1.2.3-70-g09d2 From d1b781002b31247d38a2892c51b88348d6a8f201 Mon Sep 17 00:00:00 2001 From: Oliver Neukum Date: Mon, 19 May 2014 13:55:25 +0200 Subject: USB: cdc-acm: use BIT macro Converting the header to BIT for readability. No functional change. Signed-off-by: Oliver Neukum Signed-off-by: Greg Kroah-Hartman --- drivers/usb/class/cdc-acm.h | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'drivers/usb/class/cdc-acm.h') diff --git a/drivers/usb/class/cdc-acm.h b/drivers/usb/class/cdc-acm.h index 80826f843e0..fc75651afe1 100644 --- a/drivers/usb/class/cdc-acm.h +++ b/drivers/usb/class/cdc-acm.h @@ -126,9 +126,9 @@ struct acm { #define CDC_DATA_INTERFACE_TYPE 0x0a /* constants describing various quirks and errors */ -#define NO_UNION_NORMAL 1 -#define SINGLE_RX_URB 2 -#define NO_CAP_LINE 4 -#define NOT_A_MODEM 8 -#define NO_DATA_INTERFACE 16 -#define IGNORE_DEVICE 32 +#define NO_UNION_NORMAL BIT(0) +#define SINGLE_RX_URB BIT(1) +#define NO_CAP_LINE BIT(2) +#define NOT_A_MODEM BIT(3) +#define NO_DATA_INTERFACE BIT(4) +#define IGNORE_DEVICE BIT(5) -- cgit v1.2.3-70-g09d2