usb: add device connection/disconnection detection
Provide a function to detect USB device insertion/removal in order to avoid having to do USB enumeration in a tight loop when trying to detect peripheral hotplugging. Signed-off-by: Vincent Palatin <vpalatin@chromium.org> Reviewed-by: Stefan Reinauer <reinauer@chromium.org> Tested-by: Stefan Reinauer <reinauer@chromium.org> Signed-off-by: Simon Glass <sjg@chromium.org>
This commit is contained in:
parent
6a72e804a2
commit
08f3bb0bcd
26
common/usb.c
26
common/usb.c
|
@ -148,6 +148,32 @@ int usb_stop(void)
|
|||
return 0;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* Detect if a USB device has been plugged or unplugged.
|
||||
*/
|
||||
int usb_detect_change(void)
|
||||
{
|
||||
int i, j;
|
||||
int change = 0;
|
||||
|
||||
for (j = 0; j < USB_MAX_DEVICE; j++) {
|
||||
for (i = 0; i < usb_dev[j].maxchild; i++) {
|
||||
struct usb_port_status status;
|
||||
|
||||
if (usb_get_port_status(&usb_dev[j], i + 1,
|
||||
&status) < 0)
|
||||
/* USB request failed */
|
||||
continue;
|
||||
|
||||
if (le16_to_cpu(status.wPortChange) &
|
||||
USB_PORT_STAT_C_CONNECTION)
|
||||
change++;
|
||||
}
|
||||
}
|
||||
|
||||
return change;
|
||||
}
|
||||
|
||||
/*
|
||||
* disables the asynch behaviour of the control message. This is used for data
|
||||
* transfers that uses the exclusiv access to the control and bulk messages.
|
||||
|
|
|
@ -79,7 +79,7 @@ static int usb_get_hub_status(struct usb_device *dev, void *data)
|
|||
data, sizeof(struct usb_hub_status), USB_CNTL_TIMEOUT);
|
||||
}
|
||||
|
||||
static int usb_get_port_status(struct usb_device *dev, int port, void *data)
|
||||
int usb_get_port_status(struct usb_device *dev, int port, void *data)
|
||||
{
|
||||
return usb_control_msg(dev, usb_rcvctrlpipe(dev, 0),
|
||||
USB_REQ_GET_STATUS, USB_DIR_IN | USB_RT_PORT, 0, port,
|
||||
|
|
|
@ -265,6 +265,7 @@ int usb_kbd_deregister(int force);
|
|||
/* routines */
|
||||
int usb_init(void); /* initialize the USB Controller */
|
||||
int usb_stop(void); /* stop the USB Controller */
|
||||
int usb_detect_change(void); /* detect if a USB device has been (un)plugged */
|
||||
|
||||
|
||||
int usb_set_protocol(struct usb_device *dev, int ifnum, int protocol);
|
||||
|
@ -290,6 +291,7 @@ int usb_get_class_descriptor(struct usb_device *dev, int ifnum,
|
|||
int usb_clear_halt(struct usb_device *dev, int pipe);
|
||||
int usb_string(struct usb_device *dev, int index, char *buf, size_t size);
|
||||
int usb_set_interface(struct usb_device *dev, int interface, int alternate);
|
||||
int usb_get_port_status(struct usb_device *dev, int port, void *data);
|
||||
|
||||
/* big endian -> little endian conversion */
|
||||
/* some CPUs are already little endian e.g. the ARM920T */
|
||||
|
|
Loading…
Reference in New Issue