int change[SANDBOX_NUM_PORTS];
};
-static struct udevice *hub_find_device(struct udevice *hub, int port)
+static struct udevice *hub_find_device(struct udevice *hub, int port,
+ enum usb_device_speed *speed)
{
struct udevice *dev;
+ struct usb_generic_descriptor **gen_desc;
+ struct usb_device_descriptor **dev_desc;
for (device_find_first_child(hub, &dev);
dev;
struct sandbox_hub_platdata *plat;
plat = dev_get_parent_platdata(dev);
- if (plat->port == port)
+ if (plat->port == port) {
+ gen_desc = plat->plat.desc_list;
+ gen_desc = usb_emul_find_descriptor(gen_desc,
+ USB_DT_DEVICE, 0);
+ dev_desc = (struct usb_device_descriptor **)gen_desc;
+
+ switch (le16_to_cpu((*dev_desc)->bcdUSB)) {
+ case 0x0100:
+ *speed = USB_SPEED_LOW;
+ break;
+ case 0x0101:
+ *speed = USB_SPEED_FULL;
+ break;
+ case 0x0200:
+ default:
+ *speed = USB_SPEED_HIGH;
+ break;
+ }
+
return dev;
+ }
}
return NULL;
int ret = 0;
if ((clear | set) & USB_PORT_STAT_POWER) {
- struct udevice *dev = hub_find_device(hub, port);
+ enum usb_device_speed speed;
+ struct udevice *dev = hub_find_device(hub, port, &speed);
if (dev) {
if (set & USB_PORT_STAT_POWER) {
if (!ret) {
set |= USB_PORT_STAT_CONNECTION |
USB_PORT_STAT_ENABLE;
+ if (speed == USB_SPEED_LOW)
+ set |= USB_PORT_STAT_LOW_SPEED;
+ else if (speed == USB_SPEED_HIGH)
+ set |= USB_PORT_STAT_HIGH_SPEED;
}
} else if (clear & USB_PORT_STAT_POWER) {