Date: Tue, 6 Jul 2010 06:36:52 GMT From: Hans Petter Selasky <hselasky@FreeBSD.org> To: Perforce Change Reviews <perforce@FreeBSD.org> Subject: PERFORCE change 180517 for review Message-ID: <201007060636.o666aq6d050676@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://p4web.freebsd.org/@@180517?ac=10 Change 180517 by hselasky@hselasky_laptop001 on 2010/07/06 06:35:58 USB CORE: (new feature) - add support for power mode filtering due to some USB hardware which does not support power saving. - return correct power mode for root HUBs by ugen ioctl. - patch by: HPS @ Affected files ... .. //depot/projects/usb/src/sys/dev/usb/controller/octusb.c#6 edit .. //depot/projects/usb/src/sys/dev/usb/usb_controller.h#20 edit .. //depot/projects/usb/src/sys/dev/usb/usb_device.c#70 edit .. //depot/projects/usb/src/sys/dev/usb/usb_generic.c#31 edit .. //depot/projects/usb/src/sys/dev/usb/usb_hub.c#47 edit .. //depot/projects/usb/src/sys/dev/usb/usbdi.h#18 edit Differences ... ==== //depot/projects/usb/src/sys/dev/usb/controller/octusb.c#6 (text+ko) ==== @@ -1435,9 +1435,6 @@ USB_BUS_LOCK_ASSERT(&sc->sc_bus, MA_OWNED); - /* XXX disable power save mode, hence it is not supported */ - udev->power_mode = USB_POWER_MODE_ON; - /* buffer reset */ ptr = (const void *)&sc->sc_hub_desc.temp; len = 0; @@ -1900,6 +1897,13 @@ DPRINTF("Nothing to do.\n"); } +static void +octusb_get_power_mode(struct usb_device *udev, int8_t *pmode) +{ + /* power save is not supported */ + *pmode = USB_POWER_MODE_ON; +} + struct usb_bus_methods octusb_bus_methods = { .endpoint_init = octusb_ep_init, .xfer_setup = octusb_xfer_setup, @@ -1910,4 +1914,5 @@ .set_hw_power = octusb_set_hw_power, .roothub_exec = octusb_roothub_exec, .xfer_poll = octusb_do_poll, + .get_power_mode = octusb_get_power_mode, }; ==== //depot/projects/usb/src/sys/dev/usb/usb_controller.h#20 (text+ko) ==== @@ -102,6 +102,10 @@ /* Optional transfer polling support */ void (*xfer_poll) (struct usb_bus *); + + /* Optional fixed power mode support */ + + void (*get_power_mode) (struct usb_device *udev, int8_t *pmode); }; /* ==== //depot/projects/usb/src/sys/dev/usb/usb_device.c#70 (text+ko) ==== @@ -1528,7 +1528,7 @@ * of USB devices out there that do not work very well with * automatic suspend and resume! */ - udev->power_mode = USB_POWER_MODE_ON; + udev->power_mode = usbd_filter_power_mode(udev, USB_POWER_MODE_ON); udev->pwr_save.last_xfer_time = ticks; /* we are not ready yet */ udev->refcount = 1; ==== //depot/projects/usb/src/sys/dev/usb/usb_generic.c#31 (text+ko) ==== @@ -1791,10 +1791,9 @@ { struct usb_device *udev = f->udev; - if ((udev == NULL) || - (udev->parent_hub == NULL)) { + if (udev == NULL) return (USB_POWER_MODE_ON); - } + return (udev->power_mode); } ==== //depot/projects/usb/src/sys/dev/usb/usb_hub.c#47 (text+ko) ==== @@ -2132,12 +2132,39 @@ { /* filter input argument */ if ((power_mode != USB_POWER_MODE_ON) && - (power_mode != USB_POWER_MODE_OFF)) { + (power_mode != USB_POWER_MODE_OFF)) power_mode = USB_POWER_MODE_SAVE; - } + + power_mode = usbd_filter_power_mode(udev, power_mode); + udev->power_mode = power_mode; /* update copy of power mode */ #if USB_HAVE_POWERD usb_bus_power_update(udev->bus); #endif } + +/*------------------------------------------------------------------------* + * usbd_filter_power_mode + * + * This function filters the power mode based on hardware requirements. + *------------------------------------------------------------------------*/ +uint8_t +usbd_filter_power_mode(struct usb_device *udev, uint8_t power_mode) +{ + struct usb_bus_methods *mtod; + int8_t temp; + + mtod = udev->bus->methods; + temp = -1; + + if (mtod->get_power_mode != NULL) + (mtod->get_power_mode) (udev, &temp); + + /* check if we should not filter */ + if (temp < 0) + return (power_mode); + + /* use fixed power mode given by hardware driver */ + return (temp); +} ==== //depot/projects/usb/src/sys/dev/usb/usbdi.h#18 (text+ko) ==== @@ -479,6 +479,7 @@ uint8_t usbd_get_bus_index(struct usb_device *udev); uint8_t usbd_get_device_index(struct usb_device *udev); void usbd_set_power_mode(struct usb_device *udev, uint8_t power_mode); +uint8_t usbd_filter_power_mode(struct usb_device *udev, uint8_t power_mode); uint8_t usbd_device_attached(struct usb_device *udev); void usbd_xfer_status(struct usb_xfer *xfer, int *actlen, int *sumlen,
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201007060636.o666aq6d050676>