Re: [PATCH v5 02/10] USB: Set usb port's DeviceRemovable according acpi information
On Sun, Jan 20, 2013 at 01:53:31AM +0800, Lan Tianyu wrote: ACPI provide _PLD and _UPC aml methods to describe usb port visibility and connectability. This patch is to add usb_hub_adjust_DeviceRemovable() to adjust usb hub port's DeviceRemovable according ACPI information and invoke it in the rh_call_control(). When hub descriptor request is issued at first time, usb port device isn't created and usb port is not bound with acpi. So first hub descriptor request is not changed based on ACPI information. After usb port devices being created, call usb_hub_adjust_DeviceRemovable in the hub_configure() and then set hub port's DeviceRemovable according ACPI information and this also works for non-root hub. Acked-by: Alan Stern st...@rowland.harvard.edu Signed-off-by: Lan Tianyu tianyu@intel.com --- drivers/usb/core/hcd.c |4 drivers/usb/core/hub.c | 43 +++ drivers/usb/core/usb.h |3 +++ 3 files changed, 50 insertions(+) diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c index 5f6da8b..2459896 100644 --- a/drivers/usb/core/hcd.c +++ b/drivers/usb/core/hcd.c @@ -619,6 +619,10 @@ nongeneric: status = hcd-driver-hub_control (hcd, typeReq, wValue, wIndex, tbuf, wLength); + + if (typeReq == GetHubDescriptor) + usb_hub_adjust_deviceremovable(hcd-self.root_hub, + (struct usb_hub_descriptor *)tbuf); break; error: /* protocol stall on error */ diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index f6ff130..f7e1402 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c @@ -1513,6 +1513,8 @@ static int hub_configure(struct usb_hub *hub, dev_err(hub-intfdev, couldn't create port%d device.\n, i + 1); + usb_hub_adjust_deviceremovable(hdev, hub-descriptor); + hub_activate(hub, HUB_INIT); return 0; @@ -5193,6 +5195,47 @@ usb_get_hub_port_connect_type(struct usb_device *hdev, int port1) return hub-ports[port1 - 1]-connect_type; } +void usb_hub_adjust_deviceremovable(struct usb_device *hdev, + struct usb_hub_descriptor *desc) +{ + enum usb_port_connect_type connect_type; + int i; + + if (!hub_is_superspeed(hdev)) { + for (i = 1; i = hdev-maxchild; i++) { + connect_type = usb_get_hub_port_connect_type(hdev, i); + + if (connect_type == USB_PORT_CONNECT_TYPE_HARD_WIRED) { + u8 mask = 1 (i%8); + + if (!(desc-u.hs.DeviceRemovable[i/8] mask)) { + dev_dbg(hdev-dev, usb port%d's DeviceRemovable is changed to 1 according to platform information.\n, + i); + desc-u.hs.DeviceRemovable[i/8] |= mask; + } + } + } + } else { + u16 port_removable = le16_to_cpu(desc-u.ss.DeviceRemovable); + + for (i = 1; i = hdev-maxchild; i++) { + connect_type = usb_get_hub_port_connect_type(hdev, i); + + if (connect_type == USB_PORT_CONNECT_TYPE_HARD_WIRED) { + u16 mask = 1 i; + + if (!(port_removable mask)) { + dev_dbg(hdev-dev, usb port%d's DeviceRemovable is changed to 1 according to platform information.\n, + i); + port_removable |= mask; + } + } + } + + desc-u.ss.DeviceRemovable = cpu_to_le16(port_removable); + } +} + #ifdef CONFIG_ACPI /** * usb_get_hub_port_acpi_handle - Get the usb port's acpi handle diff --git a/drivers/usb/core/usb.h b/drivers/usb/core/usb.h index fb7d8fc..31f32cd 100644 --- a/drivers/usb/core/usb.h +++ b/drivers/usb/core/usb.h @@ -1,5 +1,6 @@ #include linux/pm.h #include linux/acpi.h +#include linux/usb/ch11.h Minor nit, I hate having .h files include other .h files. Please just predefine the structure you need here, instead of including the .h file. thanks, greg k-h -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 02/10] USB: Set usb port's DeviceRemovable according acpi information
ACPI provide _PLD and _UPC aml methods to describe usb port visibility and connectability. This patch is to add usb_hub_adjust_DeviceRemovable() to adjust usb hub port's DeviceRemovable according ACPI information and invoke it in the rh_call_control(). When hub descriptor request is issued at first time, usb port device isn't created and usb port is not bound with acpi. So first hub descriptor request is not changed based on ACPI information. After usb port devices being created, call usb_hub_adjust_DeviceRemovable in the hub_configure() and then set hub port's DeviceRemovable according ACPI information and this also works for non-root hub. Acked-by: Alan Stern st...@rowland.harvard.edu Signed-off-by: Lan Tianyu tianyu@intel.com --- drivers/usb/core/hcd.c |4 drivers/usb/core/hub.c | 43 +++ drivers/usb/core/usb.h |3 +++ 3 files changed, 50 insertions(+) diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c index 5f6da8b..2459896 100644 --- a/drivers/usb/core/hcd.c +++ b/drivers/usb/core/hcd.c @@ -619,6 +619,10 @@ nongeneric: status = hcd-driver-hub_control (hcd, typeReq, wValue, wIndex, tbuf, wLength); + + if (typeReq == GetHubDescriptor) + usb_hub_adjust_deviceremovable(hcd-self.root_hub, + (struct usb_hub_descriptor *)tbuf); break; error: /* protocol stall on error */ diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index f6ff130..f7e1402 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c @@ -1513,6 +1513,8 @@ static int hub_configure(struct usb_hub *hub, dev_err(hub-intfdev, couldn't create port%d device.\n, i + 1); + usb_hub_adjust_deviceremovable(hdev, hub-descriptor); + hub_activate(hub, HUB_INIT); return 0; @@ -5193,6 +5195,47 @@ usb_get_hub_port_connect_type(struct usb_device *hdev, int port1) return hub-ports[port1 - 1]-connect_type; } +void usb_hub_adjust_deviceremovable(struct usb_device *hdev, + struct usb_hub_descriptor *desc) +{ + enum usb_port_connect_type connect_type; + int i; + + if (!hub_is_superspeed(hdev)) { + for (i = 1; i = hdev-maxchild; i++) { + connect_type = usb_get_hub_port_connect_type(hdev, i); + + if (connect_type == USB_PORT_CONNECT_TYPE_HARD_WIRED) { + u8 mask = 1 (i%8); + + if (!(desc-u.hs.DeviceRemovable[i/8] mask)) { + dev_dbg(hdev-dev, usb port%d's DeviceRemovable is changed to 1 according to platform information.\n, + i); + desc-u.hs.DeviceRemovable[i/8] |= mask; + } + } + } + } else { + u16 port_removable = le16_to_cpu(desc-u.ss.DeviceRemovable); + + for (i = 1; i = hdev-maxchild; i++) { + connect_type = usb_get_hub_port_connect_type(hdev, i); + + if (connect_type == USB_PORT_CONNECT_TYPE_HARD_WIRED) { + u16 mask = 1 i; + + if (!(port_removable mask)) { + dev_dbg(hdev-dev, usb port%d's DeviceRemovable is changed to 1 according to platform information.\n, + i); + port_removable |= mask; + } + } + } + + desc-u.ss.DeviceRemovable = cpu_to_le16(port_removable); + } +} + #ifdef CONFIG_ACPI /** * usb_get_hub_port_acpi_handle - Get the usb port's acpi handle diff --git a/drivers/usb/core/usb.h b/drivers/usb/core/usb.h index fb7d8fc..31f32cd 100644 --- a/drivers/usb/core/usb.h +++ b/drivers/usb/core/usb.h @@ -1,5 +1,6 @@ #include linux/pm.h #include linux/acpi.h +#include linux/usb/ch11.h struct dev_state; @@ -182,6 +183,8 @@ extern enum usb_port_connect_type usb_get_hub_port_connect_type(struct usb_device *hdev, int port1); extern void usb_set_hub_port_connect_type(struct usb_device *hdev, int port1, enum usb_port_connect_type type); +extern void usb_hub_adjust_deviceremovable(struct usb_device *hdev, + struct usb_hub_descriptor *desc); #ifdef CONFIG_ACPI extern int usb_acpi_register(void); -- 1.7.9.5 -- To unsubscribe from this list: send the line unsubscribe linux-usb in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html