diff options
Diffstat (limited to 'freebsd/sys/dev/usb/controller/usb_controller.c')
-rw-r--r-- | freebsd/sys/dev/usb/controller/usb_controller.c | 67 |
1 files changed, 63 insertions, 4 deletions
diff --git a/freebsd/sys/dev/usb/controller/usb_controller.c b/freebsd/sys/dev/usb/controller/usb_controller.c index 37f79364..c0fda652 100644 --- a/freebsd/sys/dev/usb/controller/usb_controller.c +++ b/freebsd/sys/dev/usb/controller/usb_controller.c @@ -288,6 +288,28 @@ usb_resume(device_t dev) } /*------------------------------------------------------------------------* + * usb_bus_reset_async_locked + *------------------------------------------------------------------------*/ +void +usb_bus_reset_async_locked(struct usb_bus *bus) +{ + USB_BUS_LOCK_ASSERT(bus, MA_OWNED); + + DPRINTF("\n"); + + if (bus->reset_msg[0].hdr.pm_qentry.tqe_prev != NULL || + bus->reset_msg[1].hdr.pm_qentry.tqe_prev != NULL) { + DPRINTF("Reset already pending\n"); + return; + } + + device_printf(bus->parent, "Resetting controller\n"); + + usb_proc_msignal(&bus->explore_proc, + &bus->reset_msg[0], &bus->reset_msg[1]); +} + +/*------------------------------------------------------------------------* * usb_shutdown *------------------------------------------------------------------------*/ static int @@ -338,7 +360,13 @@ usb_bus_explore(struct usb_proc_msg *pm) if (bus->no_explore != 0) return; - if (udev && udev->hub) { + if (udev != NULL) { + USB_BUS_UNLOCK(bus); + uhub_explore_handle_re_enumerate(udev); + USB_BUS_LOCK(bus); + } + + if (udev != NULL && udev->hub != NULL) { if (bus->do_probe) { bus->do_probe = 0; @@ -411,7 +439,7 @@ usb_bus_detach(struct usb_proc_msg *pm) /*------------------------------------------------------------------------* * usb_bus_suspend * - * This function is used to suspend the USB contoller. + * This function is used to suspend the USB controller. *------------------------------------------------------------------------*/ static void usb_bus_suspend(struct usb_proc_msg *pm) @@ -421,6 +449,8 @@ usb_bus_suspend(struct usb_proc_msg *pm) usb_error_t err; uint8_t do_unlock; + DPRINTF("\n"); + bus = ((struct usb_bus_msg *)pm)->bus; udev = bus->devices[USB_ROOT_HUB_ADDR]; @@ -466,7 +496,7 @@ usb_bus_suspend(struct usb_proc_msg *pm) /*------------------------------------------------------------------------* * usb_bus_resume * - * This function is used to resume the USB contoller. + * This function is used to resume the USB controller. *------------------------------------------------------------------------*/ static void usb_bus_resume(struct usb_proc_msg *pm) @@ -476,6 +506,8 @@ usb_bus_resume(struct usb_proc_msg *pm) usb_error_t err; uint8_t do_unlock; + DPRINTF("\n"); + bus = ((struct usb_bus_msg *)pm)->bus; udev = bus->devices[USB_ROOT_HUB_ADDR]; @@ -525,9 +557,31 @@ usb_bus_resume(struct usb_proc_msg *pm) } /*------------------------------------------------------------------------* + * usb_bus_reset + * + * This function is used to reset the USB controller. + *------------------------------------------------------------------------*/ +static void +usb_bus_reset(struct usb_proc_msg *pm) +{ + struct usb_bus *bus; + + DPRINTF("\n"); + + bus = ((struct usb_bus_msg *)pm)->bus; + + if (bus->bdev == NULL || bus->no_explore != 0) + return; + + /* a suspend and resume will reset the USB controller */ + usb_bus_suspend(pm); + usb_bus_resume(pm); +} + +/*------------------------------------------------------------------------* * usb_bus_shutdown * - * This function is used to shutdown the USB contoller. + * This function is used to shutdown the USB controller. *------------------------------------------------------------------------*/ static void usb_bus_shutdown(struct usb_proc_msg *pm) @@ -740,6 +794,11 @@ usb_attach_sub(device_t dev, struct usb_bus *bus) bus->resume_msg[1].hdr.pm_callback = &usb_bus_resume; bus->resume_msg[1].bus = bus; + bus->reset_msg[0].hdr.pm_callback = &usb_bus_reset; + bus->reset_msg[0].bus = bus; + bus->reset_msg[1].hdr.pm_callback = &usb_bus_reset; + bus->reset_msg[1].bus = bus; + bus->shutdown_msg[0].hdr.pm_callback = &usb_bus_shutdown; bus->shutdown_msg[0].bus = bus; bus->shutdown_msg[1].hdr.pm_callback = &usb_bus_shutdown; |