aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/usb/host/xhci.h
diff options
context:
space:
mode:
authorAndiry Xu <andiry.xu@amd.com>2011-09-23 17:19:51 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2011-09-26 18:51:10 -0400
commit9574323c39d1f8359a04843075d89c9f32d8b7e6 (patch)
tree38514abe7e4485face5fa1fb081c4a51a6f300c7 /drivers/usb/host/xhci.h
parentfc71ff7583b14347fa1cb592b698f088ecff36e3 (diff)
xHCI: test USB2 software LPM
This patch tests USB2 software LPM for a USB2 LPM-capable device. When a lpm-capable device is addressed, if the host also supports software LPM, apply a test by putting the device into L1 state and resume it to see if the device can do L1 suspend/resume successfully. If the device fails to enter L1 or resume from L1 state, it may not function normally and usbcore may disconnect and re-enumerate it. In this case, store the device's Vid and Pid information, make sure the host will not test LPM for it twice. The test result is per device/host. Some devices claim to be lpm-capable, but fail to enter L1 or resume. So the test is necessary. The xHCI 1.0 errata has modified the USB2.0 LPM implementation. It redefines the HIRD field to BESL, and adds another register Port Hardware LPM Control (PORTHLPMC). However, this should not affect the LPM behavior on xHC which does not implement 1.0 errata. USB2.0 LPM errata defines a new bit BESL in the device's USB 2.0 extension descriptor. If the device reports it uses BESL, driver should use BESL instead of HIRD for it. Signed-off-by: Andiry Xu <andiry.xu@amd.com> Signed-off-by: Sarah Sharp <sarah.a.sharp@linux.intel.com> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/usb/host/xhci.h')
-rw-r--r--drivers/usb/host/xhci.h16
1 files changed, 15 insertions, 1 deletions
diff --git a/drivers/usb/host/xhci.h b/drivers/usb/host/xhci.h
index 8673f985046e..b24c4fce457e 100644
--- a/drivers/usb/host/xhci.h
+++ b/drivers/usb/host/xhci.h
@@ -272,6 +272,7 @@ struct xhci_op_regs {
272 */ 272 */
273#define PORT_PLS_MASK (0xf << 5) 273#define PORT_PLS_MASK (0xf << 5)
274#define XDEV_U0 (0x0 << 5) 274#define XDEV_U0 (0x0 << 5)
275#define XDEV_U2 (0x2 << 5)
275#define XDEV_U3 (0x3 << 5) 276#define XDEV_U3 (0x3 << 5)
276#define XDEV_RESUME (0xf << 5) 277#define XDEV_RESUME (0xf << 5)
277/* true: port has power (see HCC_PPC) */ 278/* true: port has power (see HCC_PPC) */
@@ -362,7 +363,11 @@ struct xhci_op_regs {
362/* Bits 24:31 for port testing */ 363/* Bits 24:31 for port testing */
363 364
364/* USB2 Protocol PORTSPMSC */ 365/* USB2 Protocol PORTSPMSC */
365#define PORT_RWE (1 << 0x3) 366#define PORT_L1S_MASK 7
367#define PORT_L1S_SUCCESS 1
368#define PORT_RWE (1 << 3)
369#define PORT_HIRD(p) (((p) & 0xf) << 4)
370#define PORT_L1DS(p) (((p) & 0xff) << 8)
366 371
367/** 372/**
368 * struct xhci_intr_reg - Interrupt Register Set 373 * struct xhci_intr_reg - Interrupt Register Set
@@ -1324,6 +1329,12 @@ struct s3_save {
1324 u64 erst_dequeue; 1329 u64 erst_dequeue;
1325}; 1330};
1326 1331
1332/* Use for lpm */
1333struct dev_info {
1334 u32 dev_id;
1335 struct list_head list;
1336};
1337
1327struct xhci_bus_state { 1338struct xhci_bus_state {
1328 unsigned long bus_suspended; 1339 unsigned long bus_suspended;
1329 unsigned long next_statechange; 1340 unsigned long next_statechange;
@@ -1387,6 +1398,8 @@ struct xhci_hcd {
1387 struct xhci_erst erst; 1398 struct xhci_erst erst;
1388 /* Scratchpad */ 1399 /* Scratchpad */
1389 struct xhci_scratchpad *scratchpad; 1400 struct xhci_scratchpad *scratchpad;
1401 /* Store LPM test failed devices' information */
1402 struct list_head lpm_failed_devs;
1390 1403
1391 /* slot enabling and address device helpers */ 1404 /* slot enabling and address device helpers */
1392 struct completion addr_dev; 1405 struct completion addr_dev;
@@ -1663,6 +1676,7 @@ int xhci_free_streams(struct usb_hcd *hcd, struct usb_device *udev,
1663 struct usb_host_endpoint **eps, unsigned int num_eps, 1676 struct usb_host_endpoint **eps, unsigned int num_eps,
1664 gfp_t mem_flags); 1677 gfp_t mem_flags);
1665int xhci_address_device(struct usb_hcd *hcd, struct usb_device *udev); 1678int xhci_address_device(struct usb_hcd *hcd, struct usb_device *udev);
1679int xhci_update_device(struct usb_hcd *hcd, struct usb_device *udev);
1666int xhci_update_hub_device(struct usb_hcd *hcd, struct usb_device *hdev, 1680int xhci_update_hub_device(struct usb_hcd *hcd, struct usb_device *hdev,
1667 struct usb_tt *tt, gfp_t mem_flags); 1681 struct usb_tt *tt, gfp_t mem_flags);
1668int xhci_urb_enqueue(struct usb_hcd *hcd, struct urb *urb, gfp_t mem_flags); 1682int xhci_urb_enqueue(struct usb_hcd *hcd, struct urb *urb, gfp_t mem_flags);