diff options
| author | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2011-02-15 18:44:29 +0000 | 
|---|---|---|
| committer | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2011-02-15 18:44:29 +0000 | 
| commit | 60d8f68906f28d369f35b624e129deee5092c86d (patch) | |
| tree | 5c45e6bea6107dca69f8e3095a6ddda4e7c219a6 /os/hal | |
| parent | 35ff7323526f5225d1a00c7812291e9fcdbfafac (diff) | |
| download | ChibiOS-60d8f68906f28d369f35b624e129deee5092c86d.tar.gz ChibiOS-60d8f68906f28d369f35b624e129deee5092c86d.tar.bz2 ChibiOS-60d8f68906f28d369f35b624e129deee5092c86d.zip  | |
More improvements to the generic USB driver, implemented suspend and wakeup handling in the STM32 USB driver.
git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@2742 35acf78f-673a-0410-8e92-d51de3d6d3f4
Diffstat (limited to 'os/hal')
| -rw-r--r-- | os/hal/include/usb.h | 92 | ||||
| -rw-r--r-- | os/hal/platforms/STM32/usb_lld.c | 33 | ||||
| -rw-r--r-- | os/hal/platforms/STM32/usb_lld.h | 7 | 
3 files changed, 129 insertions, 3 deletions
diff --git a/os/hal/include/usb.h b/os/hal/include/usb.h index a7b183fe4..d569a6031 100644 --- a/os/hal/include/usb.h +++ b/os/hal/include/usb.h @@ -77,6 +77,96 @@  #define USB_LATE_SET_ADDRESS                1
  /**
 + * @brief   Helper macro for index values into descriptor strings.
 + */
 +#define USB_DESC_INDEX(i) ((uint8_t)(i))
 +
 +/**
 + * @brief   Helper macro for byte values into descriptor strings.
 + */
 +#define USB_DESC_BYTE(b) ((uint8_t)(b))
 +
 +/**
 + * @brief   Helper macro for word values into descriptor strings.
 + */
 +#define USB_DESC_WORD(w)                                                    \
 +  (uint8_t)((w) & 255),                                                     \
 +  (uint8_t)(((w) >> 8) & 255)
 +
 +/**
 + * @brief   Helper macro for BCD values into descriptor strings.
 + */
 +#define USB_DESC_BCD(bcd)                                                  \
 +  (uint8_t)((bcd) & 255),                                                   \
 +  (uint8_t)(((bcd) >> 8) & 255)
 +
 +/**
 + * @brief   Device Descriptor helper macro.
 + */
 +#define USB_DESC_DEVICE(bcdUSB, bDeviceClass, bDeviceSubClass,              \
 +                        bDeviceProtocol, bMaxPacketSize, idVendor,          \
 +                        idProduct, bcdDevice, iManufacturer,                \
 +                        iProduct, iSerialNumber, bNumConfigurations)        \
 +  USB_DESC_BYTE(18),                                                        \
 +  USB_DESC_BYTE(USB_DESCRIPTOR_DEVICE),                                     \
 +  USB_DESC_BCD(bcdUSB),                                                     \
 +  USB_DESC_BYTE(bDeviceClass),                                              \
 +  USB_DESC_BYTE(bDeviceSubClass),                                           \
 +  USB_DESC_BYTE(bDeviceProtocol),                                           \
 +  USB_DESC_BYTE(bMaxPacketSize),                                            \
 +  USB_DESC_WORD(idVendor),                                                  \
 +  USB_DESC_WORD(idProduct),                                                 \
 +  USB_DESC_BCD(bcdDevice),                                                  \
 +  USB_DESC_INDEX(iManufacturer),                                            \
 +  USB_DESC_INDEX(iProduct),                                                 \
 +  USB_DESC_INDEX(iSerialNumber),                                            \
 +  USB_DESC_BYTE(bNumConfigurations)
 +
 +/**
 + * @brief   Configuration Descriptor helper macro.
 + */
 +#define USB_DESC_CONFIGURATION(wTotalLength, bNumInterfaces,                \
 +                               bConfigurationValue, iConfiguration,         \
 +                               bmAttributes, bMaxPower)                     \
 +  USB_DESC_BYTE(9),                                                         \
 +  USB_DESC_BYTE(USB_DESCRIPTOR_CONFIGURATION),                              \
 +  USB_DESC_WORD(wTotalLength),                                              \
 +  USB_DESC_BYTE(bNumInterfaces),                                            \
 +  USB_DESC_BYTE(bConfigurationValue),                                       \
 +  USB_DESC_INDEX(iConfiguration),                                           \
 +  USB_DESC_BYTE(bmAttributes),                                              \
 +  USB_DESC_BYTE(bMaxPower)
 +
 +/**
 + * @brief   Interface Descriptor helper macro.
 + */
 +#define USB_DESC_INTERFACE(bInterfaceNumber, bAlternateSetting,             \
 +                           bNumEndpoints, bInterfaceClass,                  \
 +                           bInterfaceSubClass, bInterfaceProtocol,          \
 +                           iInterface)                                      \
 +  USB_DESC_BYTE(9),                                                         \
 +  USB_DESC_BYTE(USB_DESCRIPTOR_INTERFACE),                                  \
 +  USB_DESC_BYTE(bInterfaceNumber),                                          \
 +  USB_DESC_BYTE(bAlternateSetting),                                         \
 +  USB_DESC_BYTE(bNumEndpoints),                                             \
 +  USB_DESC_BYTE(bInterfaceClass),                                           \
 +  USB_DESC_BYTE(bInterfaceSubClass),                                        \
 +  USB_DESC_BYTE(bInterfaceProtocol),                                        \
 +  USB_DESC_INDEX(iInterface)
 +
 +/**
 + * @brief   Endpoint Descriptor helper macro.
 + */
 +#define USB_DESC_ENDPOINT(bEndpointAddress, bmAttributes, wMaxPacketSize,   \
 +                          bInterval)                                        \
 +  USB_DESC_BYTE(7),                                                         \
 +  USB_DESC_BYTE(USB_DESCRIPTOR_ENDPOINT),                                   \
 +  USB_DESC_BYTE(bEndpointAddress),                                          \
 +  USB_DESC_BYTE(bmAttributes),                                              \
 +  USB_DESC_WORD(wMaxPacketSize),                                            \
 +  USB_DESC_BYTE(bInterval)
 +
 +/**
   * @brief   Returned by some functions to report a busy endpoint.
   */
  #define USB_ENDPOINT_BUSY                   ((size_t)0xFFFFFFFF)
 @@ -151,7 +241,7 @@ typedef enum {    USB_EVENT_ADDRESS = 1,                /**< Address assigned.              */
    USB_EVENT_CONFIGURED = 2,             /**< Configuration selected.        */
    USB_EVENT_SUSPEND = 3,                /**< Entering suspend mode.         */
 -  USB_EVENT_RESUME = 4,                 /**< Leaving suspend mode.          */
 +  USB_EVENT_WAKEUP = 4,                 /**< Leaving suspend mode.          */
    USB_EVENT_STALLED = 5,                /**< Endpoint 0 error, stalled.     */
  } usbevent_t;
 diff --git a/os/hal/platforms/STM32/usb_lld.c b/os/hal/platforms/STM32/usb_lld.c index f3bfa15f4..eb3d6ab7a 100644 --- a/os/hal/platforms/STM32/usb_lld.c +++ b/os/hal/platforms/STM32/usb_lld.c @@ -199,6 +199,35 @@ CH_IRQ_HANDLER(USB_LP_IRQHandler) {      STM32_USB->ISTR = ~ISTR_RESET;
    }
 +  /* USB bus SUSPEND condition handling.*/
 +  if (istr & ISTR_SUSP) {
 +    STM32_USB->CNTR |= CNTR_FSUSP;
 +    if (usbp->config->event_cb)
 +      usbp->config->event_cb(usbp, USB_EVENT_SUSPEND);
 +#if STM32_USB_LOW_POWER_ON_SUSPEND
 +    STM32_USB->CNTR |= CNTR_LP_MODE;
 +#endif
 +    STM32_USB->ISTR = ~ISTR_SUSP;
 +  }
 +
 +  /* USB bus WAKEUP condition handling.*/
 +  if (istr & ISTR_WKUP) {
 +    uint32_t fnr = STM32_USB->FNR;
 +    if (!(fnr & FNR_RXDP)) {
 +      STM32_USB->CNTR &= ~CNTR_FSUSP;
 +      if (usbp->config->event_cb)
 +        usbp->config->event_cb(usbp, USB_EVENT_WAKEUP);
 +    }
 +#if STM32_USB_LOW_POWER_ON_SUSPEND
 +    else {
 +      /* Just noise, going back in SUSPEND mode, reference manual 22.4.5,
 +         table 169.*/
 +      STM32_USB->CNTR |= CNTR_LP_MODE;
 +    }
 +#endif
 +    STM32_USB->ISTR = ~ISTR_WKUP;
 +  }
 +
    /* SOF handling.*/
    if (istr & ISTR_SOF) {
      if (usbp->config->sof_cb)
 @@ -371,8 +400,8 @@ void usb_lld_reset(USBDriver *usbp) {    STM32_USB->BTABLE = 0;
    STM32_USB->ISTR   = 0;
    STM32_USB->DADDR  = DADDR_EF;
 -  cntr              = /*CNTR_ESOFM | */ CNTR_RESETM  | /*CNTR_SUSPM |*/
 -                      /*CNTR_WKUPM | CNTR_ERRM | CNTR_PMAOVRM |*/ CNTR_CTRM;
 +  cntr              = /*CNTR_ESOFM | */ CNTR_RESETM  | CNTR_SUSPM |
 +                      CNTR_WKUPM | /*CNTR_ERRM | CNTR_PMAOVRM |*/ CNTR_CTRM;
    /* The SOF interrupt is only enabled if a callback is defined for
       this service because it is an high rate source.*/
    if (usbp->config->sof_cb != NULL)
 diff --git a/os/hal/platforms/STM32/usb_lld.h b/os/hal/platforms/STM32/usb_lld.h index 42f32560e..a505e3e08 100644 --- a/os/hal/platforms/STM32/usb_lld.h +++ b/os/hal/platforms/STM32/usb_lld.h @@ -60,6 +60,13 @@  #endif
  /**
 + * @brief   Enables the USB device low power mode on suspend.
 + */
 +#if !defined(STM32_USB_LOW_POWER_ON_SUSPEND) || defined(__DOXYGEN__)
 +#define STM32_USB_LOW_POWER_ON_SUSPEND      FALSE
 +#endif
 +
 +/**
   * @brief   USB1 interrupt priority level setting.
   */
  #if !defined(STM32_USB_USB1_HP_IRQ_PRIORITY) || defined(__DOXYGEN__)
  | 
