[USB_SPEED_HIGH] = "high-speed",
[USB_SPEED_WIRELESS] = "wireless",
[USB_SPEED_SUPER] = "super-speed",
+ [USB_SPEED_SUPER_PLUS] = "super-speed-plus",
};
const char *usb_speed_string(enum usb_device_speed speed)
if (usb_endpoint_xfer_int(d)) {
i = 1;
switch (to_usb_device(ddev)->speed) {
+ case USB_SPEED_SUPER_PLUS:
case USB_SPEED_SUPER:
case USB_SPEED_HIGH:
/* Many device manufacturers are using full-speed
}
/* Parse a possible SuperSpeed endpoint companion descriptor */
- if (to_usb_device(ddev)->speed == USB_SPEED_SUPER)
+ if (to_usb_device(ddev)->speed >= USB_SPEED_SUPER)
usb_parse_ss_endpoint_companion(ddev, cfgno,
inum, asnum, endpoint, buffer, size);
break;
case USB_ENDPOINT_XFER_INT:
type = "Int.";
- if (speed == USB_SPEED_HIGH || speed == USB_SPEED_SUPER)
+ if (speed == USB_SPEED_HIGH || speed >= USB_SPEED_SUPER)
interval = 1 << (desc->bInterval - 1);
else
interval = desc->bInterval;
return start;
}
interval *= (speed == USB_SPEED_HIGH ||
- speed == USB_SPEED_SUPER) ? 125 : 1000;
+ speed >= USB_SPEED_SUPER) ? 125 : 1000;
if (interval % 1000)
unit = 'u';
else {
if (start > end)
return start;
- if (speed == USB_SPEED_SUPER)
+ if (speed >= USB_SPEED_SUPER)
mul = 8;
else
mul = 2;
speed = "480"; break;
case USB_SPEED_SUPER:
speed = "5000"; break;
+ case USB_SPEED_SUPER_PLUS:
+ speed = "10000"; break;
default:
speed = "??";
}
/* super/high speed reserves 80%, full/low reserves 90% */
if (usbdev->speed == USB_SPEED_HIGH ||
- usbdev->speed == USB_SPEED_SUPER)
+ usbdev->speed >= USB_SPEED_SUPER)
max = 800;
else
max = FRAME_TIME_MAX_USECS_ALLOC;
* The xHCI driver has its own irq management
* make sure irq setup is not touched for xhci in generic hcd code
*/
- if ((driver->flags & HCD_MASK) != HCD_USB3) {
+ if ((driver->flags & HCD_MASK) < HCD_USB3) {
if (!dev->irq) {
dev_err(&dev->dev,
"Found HC with no IRQ. Check BIOS/PCI %s setup!\n",
retval = usb_get_bos_descriptor(usb_dev);
if (!retval) {
usb_dev->lpm_capable = usb_device_supports_lpm(usb_dev);
- } else if (usb_dev->speed == USB_SPEED_SUPER) {
+ } else if (usb_dev->speed >= USB_SPEED_SUPER) {
mutex_unlock(&usb_bus_list_lock);
dev_dbg(parent_dev, "can't read %s bos descriptor %d\n",
dev_name(&usb_dev->dev), retval);
hcd = bus_to_hcd(dev->bus);
if (!hcd->driver->alloc_streams || !hcd->driver->free_streams)
return -EINVAL;
- if (dev->speed != USB_SPEED_SUPER)
+ if (dev->speed < USB_SPEED_SUPER)
return -EINVAL;
if (dev->state < USB_STATE_CONFIGURED)
return -ENODEV;
dev = interface_to_usbdev(interface);
hcd = bus_to_hcd(dev->bus);
- if (dev->speed != USB_SPEED_SUPER)
+ if (dev->speed < USB_SPEED_SUPER)
return -EINVAL;
/* Double-free is not allowed */
unsigned int hub_u1_del;
unsigned int hub_u2_del;
- if (!udev->lpm_capable || udev->speed != USB_SPEED_SUPER)
+ if (!udev->lpm_capable || udev->speed < USB_SPEED_SUPER)
return;
hub = usb_hub_to_struct_hub(udev->parent);
*/
static bool use_new_scheme(struct usb_device *udev, int retry)
{
- if (udev->speed == USB_SPEED_SUPER)
+ if (udev->speed >= USB_SPEED_SUPER)
return false;
return USE_NEW_SCHEME(retry);
struct usb_hcd *hcd;
if (!udev || !udev->parent ||
- udev->speed != USB_SPEED_SUPER ||
+ udev->speed < USB_SPEED_SUPER ||
!udev->lpm_capable ||
udev->state < USB_STATE_DEFAULT)
return 0;
struct usb_port *port_dev;
if (!udev || !udev->parent ||
- udev->speed != USB_SPEED_SUPER ||
+ udev->speed < USB_SPEED_SUPER ||
!udev->lpm_capable ||
udev->state < USB_STATE_DEFAULT)
return;
retval = -ENODEV;
- if (oldspeed != USB_SPEED_UNKNOWN && oldspeed != udev->speed) {
+ /* Don't allow speed changes at reset, except usb 3.0 to faster */
+ if (oldspeed != USB_SPEED_UNKNOWN && oldspeed != udev->speed &&
+ !(oldspeed == USB_SPEED_SUPER && udev->speed > oldspeed)) {
dev_dbg(&udev->dev, "device reset changed speed!\n");
goto fail;
}
* reported as 0xff in the device descriptor). WUSB1.0[4.8.1].
*/
switch (udev->speed) {
+ case USB_SPEED_SUPER_PLUS:
case USB_SPEED_SUPER:
case USB_SPEED_WIRELESS: /* fixed at 512 */
udev->ep0.desc.wMaxPacketSize = cpu_to_le16(512);
else
speed = usb_speed_string(udev->speed);
- if (udev->speed != USB_SPEED_SUPER)
+ if (udev->speed < USB_SPEED_SUPER)
dev_info(&udev->dev,
"%s %s USB device number %d using %s\n",
(udev->config) ? "reset" : "new", speed,
devnum, retval);
goto fail;
}
- if (udev->speed == USB_SPEED_SUPER) {
+ if (udev->speed >= USB_SPEED_SUPER) {
devnum = udev->devnum;
dev_info(&udev->dev,
- "%s SuperSpeed USB device number %d using %s\n",
+ "%s SuperSpeed%s USB device number %d using %s\n",
(udev->config) ? "reset" : "new",
+ (udev->speed == USB_SPEED_SUPER_PLUS) ? "Plus" : "",
devnum, udev->bus->controller->driver->name);
}
* got from those devices show they aren't superspeed devices. Warm
* reset the port attached by the devices can fix them.
*/
- if ((udev->speed == USB_SPEED_SUPER) &&
+ if ((udev->speed >= USB_SPEED_SUPER) &&
(le16_to_cpu(udev->descriptor.bcdUSB) < 0x0300)) {
dev_err(&udev->dev, "got a wrong device descriptor, "
"warm reset device\n");
}
if (udev->descriptor.bMaxPacketSize0 == 0xff ||
- udev->speed == USB_SPEED_SUPER)
+ udev->speed >= USB_SPEED_SUPER)
i = 512;
else
i = udev->descriptor.bMaxPacketSize0;
udev->level = hdev->level + 1;
udev->wusb = hub_is_wusb(hub);
- /* Only USB 3.0 devices are connected to SuperSpeed hubs. */
+ /* Devices connected to SuperSpeed hubs are USB 3.0 or later */
if (hub_is_superspeed(hub->hdev))
udev->speed = USB_SPEED_SUPER;
else
/* SuperSpeed isoc endpoints have up to 16 bursts of up to
* 3 packets each
*/
- if (dev->speed == USB_SPEED_SUPER) {
+ if (dev->speed >= USB_SPEED_SUPER) {
int burst = 1 + ep->ss_ep_comp.bMaxBurst;
int mult = USB_SS_MULT(ep->ss_ep_comp.bmAttributes);
max *= burst;
}
/* too big? */
switch (dev->speed) {
+ case USB_SPEED_SUPER_PLUS:
case USB_SPEED_SUPER: /* units are 125us */
/* Handle up to 2^(16-1) microframes */
if (urb->interval > (1 << 15))
struct usb_host_config *c)
{
/* SuperSpeed power is in 8 mA units; others are in 2 mA units */
- unsigned mul = (udev->speed == USB_SPEED_SUPER ? 8 : 2);
+ unsigned mul = (udev->speed >= USB_SPEED_SUPER ? 8 : 2);
return c->desc.bMaxPower * mul;
}
USB_SPEED_HIGH, /* usb 2.0 */
USB_SPEED_WIRELESS, /* wireless (usb 2.5) */
USB_SPEED_SUPER, /* usb 3.0 */
+ USB_SPEED_SUPER_PLUS, /* usb 3.1 */
};