1 /* 2 * usb port device code 3 * 4 * Copyright (C) 2012 Intel Corp 5 * 6 * Author: Lan Tianyu <tianyu.lan@intel.com> 7 * 8 * This program is free software; you can redistribute it and/or modify 9 * it under the terms of the GNU General Public License version 2 as 10 * published by the Free Software Foundation. 11 * 12 * This program is distributed in the hope that it will be useful, but 13 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15 * for more details. 16 * 17 */ 18 19 #include <linux/slab.h> 20 #include <linux/pm_qos.h> 21 22 #include "hub.h" 23 24 static const struct attribute_group *port_dev_group[]; 25 26 static ssize_t connect_type_show(struct device *dev, 27 struct device_attribute *attr, char *buf) 28 { 29 struct usb_port *port_dev = to_usb_port(dev); 30 char *result; 31 32 switch (port_dev->connect_type) { 33 case USB_PORT_CONNECT_TYPE_HOT_PLUG: 34 result = "hotplug"; 35 break; 36 case USB_PORT_CONNECT_TYPE_HARD_WIRED: 37 result = "hardwired"; 38 break; 39 case USB_PORT_NOT_USED: 40 result = "not used"; 41 break; 42 default: 43 result = "unknown"; 44 break; 45 } 46 47 return sprintf(buf, "%s\n", result); 48 } 49 static DEVICE_ATTR_RO(connect_type); 50 51 static struct attribute *port_dev_attrs[] = { 52 &dev_attr_connect_type.attr, 53 NULL, 54 }; 55 56 static struct attribute_group port_dev_attr_grp = { 57 .attrs = port_dev_attrs, 58 }; 59 60 static const struct attribute_group *port_dev_group[] = { 61 &port_dev_attr_grp, 62 NULL, 63 }; 64 65 static void usb_port_device_release(struct device *dev) 66 { 67 struct usb_port *port_dev = to_usb_port(dev); 68 69 kfree(port_dev); 70 } 71 72 #ifdef CONFIG_PM_RUNTIME 73 static int usb_port_runtime_resume(struct device *dev) 74 { 75 struct usb_port *port_dev = to_usb_port(dev); 76 struct usb_device *hdev = to_usb_device(dev->parent->parent); 77 struct usb_interface *intf = to_usb_interface(dev->parent); 78 struct usb_hub *hub = usb_hub_to_struct_hub(hdev); 79 int port1 = port_dev->portnum; 80 int retval; 81 82 if (!hub) 83 return -EINVAL; 84 85 usb_autopm_get_interface(intf); 86 set_bit(port1, hub->busy_bits); 87 88 retval = usb_hub_set_port_power(hdev, hub, port1, true); 89 if (port_dev->child && !retval) { 90 /* 91 * Attempt to wait for usb hub port to be reconnected in order 92 * to make the resume procedure successful. The device may have 93 * disconnected while the port was powered off, so ignore the 94 * return status. 95 */ 96 retval = hub_port_debounce_be_connected(hub, port1); 97 if (retval < 0) 98 dev_dbg(&port_dev->dev, "can't get reconnection after setting port power on, status %d\n", 99 retval); 100 usb_clear_port_feature(hdev, port1, USB_PORT_FEAT_C_ENABLE); 101 retval = 0; 102 } 103 104 clear_bit(port1, hub->busy_bits); 105 usb_autopm_put_interface(intf); 106 return retval; 107 } 108 109 static int usb_port_runtime_suspend(struct device *dev) 110 { 111 struct usb_port *port_dev = to_usb_port(dev); 112 struct usb_device *hdev = to_usb_device(dev->parent->parent); 113 struct usb_interface *intf = to_usb_interface(dev->parent); 114 struct usb_hub *hub = usb_hub_to_struct_hub(hdev); 115 int port1 = port_dev->portnum; 116 int retval; 117 118 if (!hub) 119 return -EINVAL; 120 121 if (dev_pm_qos_flags(&port_dev->dev, PM_QOS_FLAG_NO_POWER_OFF) 122 == PM_QOS_FLAGS_ALL) 123 return -EAGAIN; 124 125 usb_autopm_get_interface(intf); 126 set_bit(port1, hub->busy_bits); 127 retval = usb_hub_set_port_power(hdev, hub, port1, false); 128 usb_clear_port_feature(hdev, port1, USB_PORT_FEAT_C_CONNECTION); 129 usb_clear_port_feature(hdev, port1, USB_PORT_FEAT_C_ENABLE); 130 clear_bit(port1, hub->busy_bits); 131 usb_autopm_put_interface(intf); 132 return retval; 133 } 134 #endif 135 136 static const struct dev_pm_ops usb_port_pm_ops = { 137 #ifdef CONFIG_PM_RUNTIME 138 .runtime_suspend = usb_port_runtime_suspend, 139 .runtime_resume = usb_port_runtime_resume, 140 #endif 141 }; 142 143 struct device_type usb_port_device_type = { 144 .name = "usb_port", 145 .release = usb_port_device_release, 146 .pm = &usb_port_pm_ops, 147 }; 148 149 int usb_hub_create_port_device(struct usb_hub *hub, int port1) 150 { 151 struct usb_port *port_dev = NULL; 152 int retval; 153 154 port_dev = kzalloc(sizeof(*port_dev), GFP_KERNEL); 155 if (!port_dev) { 156 retval = -ENOMEM; 157 goto exit; 158 } 159 160 hub->ports[port1 - 1] = port_dev; 161 port_dev->portnum = port1; 162 port_dev->power_is_on = true; 163 port_dev->dev.parent = hub->intfdev; 164 port_dev->dev.groups = port_dev_group; 165 port_dev->dev.type = &usb_port_device_type; 166 dev_set_name(&port_dev->dev, "port%d", port1); 167 168 retval = device_register(&port_dev->dev); 169 if (retval) 170 goto error_register; 171 172 pm_runtime_set_active(&port_dev->dev); 173 174 /* It would be dangerous if user space couldn't 175 * prevent usb device from being powered off. So don't 176 * enable port runtime pm if failed to expose port's pm qos. 177 */ 178 if (!dev_pm_qos_expose_flags(&port_dev->dev, 179 PM_QOS_FLAG_NO_POWER_OFF)) 180 pm_runtime_enable(&port_dev->dev); 181 182 device_enable_async_suspend(&port_dev->dev); 183 return 0; 184 185 error_register: 186 put_device(&port_dev->dev); 187 exit: 188 return retval; 189 } 190 191 void usb_hub_remove_port_device(struct usb_hub *hub, 192 int port1) 193 { 194 device_unregister(&hub->ports[port1 - 1]->dev); 195 } 196 197