1 /**
2   ******************************************************************************
3   * @file    stm32f4xx_ll_usb.c
4   * @author  MCD Application Team
5   * @brief   USB Low Layer HAL module driver.
6   *
7   *          This file provides firmware functions to manage the following
8   *          functionalities of the USB Peripheral Controller:
9   *           + Initialization/de-initialization functions
10   *           + I/O operation functions
11   *           + Peripheral Control functions
12   *           + Peripheral State functions
13   *
14   ******************************************************************************
15   * @attention
16   *
17   * Copyright (c) 2016 STMicroelectronics.
18   * All rights reserved.
19   *
20   * This software is licensed under terms that can be found in the LICENSE file
21   * in the root directory of this software component.
22   * If no LICENSE file comes with this software, it is provided AS-IS.
23   *
24   ******************************************************************************
25   @verbatim
26   ==============================================================================
27                     ##### How to use this driver #####
28   ==============================================================================
29     [..]
30       (#) Fill parameters of Init structure in USB_OTG_CfgTypeDef structure.
31 
32       (#) Call USB_CoreInit() API to initialize the USB Core peripheral.
33 
34       (#) The upper HAL HCD/PCD driver will call the right routines for its internal processes.
35 
36   @endverbatim
37 
38   ******************************************************************************
39   */
40 
41 /* Includes ------------------------------------------------------------------*/
42 #include "stm32f4xx_hal.h"
43 
44 /** @addtogroup STM32F4xx_LL_USB_DRIVER
45   * @{
46   */
47 
48 #if defined (HAL_PCD_MODULE_ENABLED) || defined (HAL_HCD_MODULE_ENABLED)
49 #if defined (USB_OTG_FS) || defined (USB_OTG_HS)
50 /* Private typedef -----------------------------------------------------------*/
51 /* Private define ------------------------------------------------------------*/
52 /* Private macro -------------------------------------------------------------*/
53 /* Private variables ---------------------------------------------------------*/
54 /* Private function prototypes -----------------------------------------------*/
55 /* Private functions ---------------------------------------------------------*/
56 #if defined (USB_OTG_FS) || defined (USB_OTG_HS)
57 static HAL_StatusTypeDef USB_CoreReset(USB_OTG_GlobalTypeDef *USBx);
58 
59 /* Exported functions --------------------------------------------------------*/
60 /** @defgroup USB_LL_Exported_Functions USB Low Layer Exported Functions
61   * @{
62   */
63 
64 /** @defgroup USB_LL_Exported_Functions_Group1 Initialization/de-initialization functions
65   *  @brief    Initialization and Configuration functions
66   *
67 @verbatim
68  ===============================================================================
69                       ##### Initialization/de-initialization functions #####
70  ===============================================================================
71 
72 @endverbatim
73   * @{
74   */
75 
76 /**
77   * @brief  Initializes the USB Core
78   * @param  USBx USB Instance
79   * @param  cfg pointer to a USB_OTG_CfgTypeDef structure that contains
80   *         the configuration information for the specified USBx peripheral.
81   * @retval HAL status
82   */
USB_CoreInit(USB_OTG_GlobalTypeDef * USBx,USB_OTG_CfgTypeDef cfg)83 HAL_StatusTypeDef USB_CoreInit(USB_OTG_GlobalTypeDef *USBx, USB_OTG_CfgTypeDef cfg)
84 {
85   HAL_StatusTypeDef ret;
86   if (cfg.phy_itface == USB_OTG_ULPI_PHY)
87   {
88     USBx->GCCFG &= ~(USB_OTG_GCCFG_PWRDWN);
89 
90     /* Init The ULPI Interface */
91     USBx->GUSBCFG &= ~(USB_OTG_GUSBCFG_TSDPS | USB_OTG_GUSBCFG_ULPIFSLS | USB_OTG_GUSBCFG_PHYSEL);
92 
93     /* Select vbus source */
94     USBx->GUSBCFG &= ~(USB_OTG_GUSBCFG_ULPIEVBUSD | USB_OTG_GUSBCFG_ULPIEVBUSI);
95     if (cfg.use_external_vbus == 1U)
96     {
97       USBx->GUSBCFG |= USB_OTG_GUSBCFG_ULPIEVBUSD;
98     }
99 
100     /* Reset after a PHY select */
101     ret = USB_CoreReset(USBx);
102   }
103   else /* FS interface (embedded Phy) */
104   {
105     /* Select FS Embedded PHY */
106     USBx->GUSBCFG |= USB_OTG_GUSBCFG_PHYSEL;
107 
108     /* Reset after a PHY select */
109     ret = USB_CoreReset(USBx);
110 
111     if (cfg.battery_charging_enable == 0U)
112     {
113       /* Activate the USB Transceiver */
114       USBx->GCCFG |= USB_OTG_GCCFG_PWRDWN;
115     }
116     else
117     {
118       /* Deactivate the USB Transceiver */
119       USBx->GCCFG &= ~(USB_OTG_GCCFG_PWRDWN);
120     }
121   }
122 
123   if (cfg.dma_enable == 1U)
124   {
125     USBx->GAHBCFG |= USB_OTG_GAHBCFG_HBSTLEN_2;
126     USBx->GAHBCFG |= USB_OTG_GAHBCFG_DMAEN;
127   }
128 
129   return ret;
130 }
131 
132 
133 /**
134   * @brief  Set the USB turnaround time
135   * @param  USBx USB Instance
136   * @param  hclk: AHB clock frequency
137   * @retval USB turnaround time In PHY Clocks number
138   */
USB_SetTurnaroundTime(USB_OTG_GlobalTypeDef * USBx,uint32_t hclk,uint8_t speed)139 HAL_StatusTypeDef USB_SetTurnaroundTime(USB_OTG_GlobalTypeDef *USBx,
140                                         uint32_t hclk, uint8_t speed)
141 {
142   uint32_t UsbTrd;
143 
144   /* The USBTRD is configured according to the tables below, depending on AHB frequency
145   used by application. In the low AHB frequency range it is used to stretch enough the USB response
146   time to IN tokens, the USB turnaround time, so to compensate for the longer AHB read access
147   latency to the Data FIFO */
148   if (speed == USBD_FS_SPEED)
149   {
150     if ((hclk >= 14200000U) && (hclk < 15000000U))
151     {
152       /* hclk Clock Range between 14.2-15 MHz */
153       UsbTrd = 0xFU;
154     }
155     else if ((hclk >= 15000000U) && (hclk < 16000000U))
156     {
157       /* hclk Clock Range between 15-16 MHz */
158       UsbTrd = 0xEU;
159     }
160     else if ((hclk >= 16000000U) && (hclk < 17200000U))
161     {
162       /* hclk Clock Range between 16-17.2 MHz */
163       UsbTrd = 0xDU;
164     }
165     else if ((hclk >= 17200000U) && (hclk < 18500000U))
166     {
167       /* hclk Clock Range between 17.2-18.5 MHz */
168       UsbTrd = 0xCU;
169     }
170     else if ((hclk >= 18500000U) && (hclk < 20000000U))
171     {
172       /* hclk Clock Range between 18.5-20 MHz */
173       UsbTrd = 0xBU;
174     }
175     else if ((hclk >= 20000000U) && (hclk < 21800000U))
176     {
177       /* hclk Clock Range between 20-21.8 MHz */
178       UsbTrd = 0xAU;
179     }
180     else if ((hclk >= 21800000U) && (hclk < 24000000U))
181     {
182       /* hclk Clock Range between 21.8-24 MHz */
183       UsbTrd = 0x9U;
184     }
185     else if ((hclk >= 24000000U) && (hclk < 27700000U))
186     {
187       /* hclk Clock Range between 24-27.7 MHz */
188       UsbTrd = 0x8U;
189     }
190     else if ((hclk >= 27700000U) && (hclk < 32000000U))
191     {
192       /* hclk Clock Range between 27.7-32 MHz */
193       UsbTrd = 0x7U;
194     }
195     else /* if(hclk >= 32000000) */
196     {
197       /* hclk Clock Range between 32-200 MHz */
198       UsbTrd = 0x6U;
199     }
200   }
201   else if (speed == USBD_HS_SPEED)
202   {
203     UsbTrd = USBD_HS_TRDT_VALUE;
204   }
205   else
206   {
207     UsbTrd = USBD_DEFAULT_TRDT_VALUE;
208   }
209 
210   USBx->GUSBCFG &= ~USB_OTG_GUSBCFG_TRDT;
211   USBx->GUSBCFG |= (uint32_t)((UsbTrd << 10) & USB_OTG_GUSBCFG_TRDT);
212 
213   return HAL_OK;
214 }
215 
216 /**
217   * @brief  USB_EnableGlobalInt
218   *         Enables the controller's Global Int in the AHB Config reg
219   * @param  USBx  Selected device
220   * @retval HAL status
221   */
USB_EnableGlobalInt(USB_OTG_GlobalTypeDef * USBx)222 HAL_StatusTypeDef USB_EnableGlobalInt(USB_OTG_GlobalTypeDef *USBx)
223 {
224   USBx->GAHBCFG |= USB_OTG_GAHBCFG_GINT;
225   return HAL_OK;
226 }
227 
228 /**
229   * @brief  USB_DisableGlobalInt
230   *         Disable the controller's Global Int in the AHB Config reg
231   * @param  USBx  Selected device
232   * @retval HAL status
233   */
USB_DisableGlobalInt(USB_OTG_GlobalTypeDef * USBx)234 HAL_StatusTypeDef USB_DisableGlobalInt(USB_OTG_GlobalTypeDef *USBx)
235 {
236   USBx->GAHBCFG &= ~USB_OTG_GAHBCFG_GINT;
237   return HAL_OK;
238 }
239 
240 /**
241   * @brief  USB_SetCurrentMode Set functional mode
242   * @param  USBx  Selected device
243   * @param  mode  current core mode
244   *          This parameter can be one of these values:
245   *            @arg USB_DEVICE_MODE Peripheral mode
246   *            @arg USB_HOST_MODE Host mode
247   * @retval HAL status
248   */
USB_SetCurrentMode(USB_OTG_GlobalTypeDef * USBx,USB_OTG_ModeTypeDef mode)249 HAL_StatusTypeDef USB_SetCurrentMode(USB_OTG_GlobalTypeDef *USBx, USB_OTG_ModeTypeDef mode)
250 {
251   uint32_t ms = 0U;
252 
253   USBx->GUSBCFG &= ~(USB_OTG_GUSBCFG_FHMOD | USB_OTG_GUSBCFG_FDMOD);
254 
255   if (mode == USB_HOST_MODE)
256   {
257     USBx->GUSBCFG |= USB_OTG_GUSBCFG_FHMOD;
258 
259     do
260     {
261       HAL_Delay(1U);
262       ms++;
263     } while ((USB_GetMode(USBx) != (uint32_t)USB_HOST_MODE) && (ms < 50U));
264   }
265   else if (mode == USB_DEVICE_MODE)
266   {
267     USBx->GUSBCFG |= USB_OTG_GUSBCFG_FDMOD;
268 
269     do
270     {
271       HAL_Delay(1U);
272       ms++;
273     } while ((USB_GetMode(USBx) != (uint32_t)USB_DEVICE_MODE) && (ms < 50U));
274   }
275   else
276   {
277     return HAL_ERROR;
278   }
279 
280   if (ms == 50U)
281   {
282     return HAL_ERROR;
283   }
284 
285   return HAL_OK;
286 }
287 
288 /**
289   * @brief  USB_DevInit Initializes the USB_OTG controller registers
290   *         for device mode
291   * @param  USBx  Selected device
292   * @param  cfg   pointer to a USB_OTG_CfgTypeDef structure that contains
293   *         the configuration information for the specified USBx peripheral.
294   * @retval HAL status
295   */
USB_DevInit(USB_OTG_GlobalTypeDef * USBx,USB_OTG_CfgTypeDef cfg)296 HAL_StatusTypeDef USB_DevInit(USB_OTG_GlobalTypeDef *USBx, USB_OTG_CfgTypeDef cfg)
297 {
298   HAL_StatusTypeDef ret = HAL_OK;
299   uint32_t USBx_BASE = (uint32_t)USBx;
300   uint32_t i;
301 
302   for (i = 0U; i < 15U; i++)
303   {
304     USBx->DIEPTXF[i] = 0U;
305   }
306 
307 #if defined(STM32F446xx) || defined(STM32F469xx) || defined(STM32F479xx) || defined(STM32F412Zx) || defined(STM32F412Vx) || defined(STM32F412Rx) || defined(STM32F412Cx) || defined(STM32F413xx) || defined(STM32F423xx)
308   /* VBUS Sensing setup */
309   if (cfg.vbus_sensing_enable == 0U)
310   {
311     USBx_DEVICE->DCTL |= USB_OTG_DCTL_SDIS;
312 
313     /* Deactivate VBUS Sensing B */
314     USBx->GCCFG &= ~USB_OTG_GCCFG_VBDEN;
315 
316     /* B-peripheral session valid override enable */
317     USBx->GOTGCTL |= USB_OTG_GOTGCTL_BVALOEN;
318     USBx->GOTGCTL |= USB_OTG_GOTGCTL_BVALOVAL;
319   }
320   else
321   {
322     /* Enable HW VBUS sensing */
323     USBx->GCCFG |= USB_OTG_GCCFG_VBDEN;
324   }
325 #else
326   /* VBUS Sensing setup */
327   if (cfg.vbus_sensing_enable == 0U)
328   {
329     /*
330      * Disable HW VBUS sensing. VBUS is internally considered to be always
331      * at VBUS-Valid level (5V).
332      */
333     USBx_DEVICE->DCTL |= USB_OTG_DCTL_SDIS;
334     USBx->GCCFG |= USB_OTG_GCCFG_NOVBUSSENS;
335     USBx->GCCFG &= ~USB_OTG_GCCFG_VBUSBSEN;
336     USBx->GCCFG &= ~USB_OTG_GCCFG_VBUSASEN;
337   }
338   else
339   {
340     /* Enable HW VBUS sensing */
341     USBx->GCCFG &= ~USB_OTG_GCCFG_NOVBUSSENS;
342     USBx->GCCFG |= USB_OTG_GCCFG_VBUSBSEN;
343   }
344 #endif /* defined(STM32F446xx) || defined(STM32F469xx) || defined(STM32F479xx) || defined(STM32F412Zx) || defined(STM32F412Vx) || defined(STM32F412Rx) || defined(STM32F412Cx) || defined(STM32F413xx) || defined(STM32F423xx) */
345 
346   /* Restart the Phy Clock */
347   USBx_PCGCCTL = 0U;
348 
349   /* Device mode configuration */
350   USBx_DEVICE->DCFG |= DCFG_FRAME_INTERVAL_80;
351 
352   if (cfg.phy_itface == USB_OTG_ULPI_PHY)
353   {
354     if (cfg.speed == USBD_HS_SPEED)
355     {
356       /* Set Core speed to High speed mode */
357       (void)USB_SetDevSpeed(USBx, USB_OTG_SPEED_HIGH);
358     }
359     else
360     {
361       /* Set Core speed to Full speed mode */
362       (void)USB_SetDevSpeed(USBx, USB_OTG_SPEED_HIGH_IN_FULL);
363     }
364   }
365   else
366   {
367     /* Set Core speed to Full speed mode */
368     (void)USB_SetDevSpeed(USBx, USB_OTG_SPEED_FULL);
369   }
370 
371   /* Flush the FIFOs */
372   if (USB_FlushTxFifo(USBx, 0x10U) != HAL_OK) /* all Tx FIFOs */
373   {
374     ret = HAL_ERROR;
375   }
376 
377   if (USB_FlushRxFifo(USBx) != HAL_OK)
378   {
379     ret = HAL_ERROR;
380   }
381 
382   /* Clear all pending Device Interrupts */
383   USBx_DEVICE->DIEPMSK = 0U;
384   USBx_DEVICE->DOEPMSK = 0U;
385   USBx_DEVICE->DAINTMSK = 0U;
386 
387   for (i = 0U; i < cfg.dev_endpoints; i++)
388   {
389     if ((USBx_INEP(i)->DIEPCTL & USB_OTG_DIEPCTL_EPENA) == USB_OTG_DIEPCTL_EPENA)
390     {
391       if (i == 0U)
392       {
393         USBx_INEP(i)->DIEPCTL = USB_OTG_DIEPCTL_SNAK;
394       }
395       else
396       {
397         USBx_INEP(i)->DIEPCTL = USB_OTG_DIEPCTL_EPDIS | USB_OTG_DIEPCTL_SNAK;
398       }
399     }
400     else
401     {
402       USBx_INEP(i)->DIEPCTL = 0U;
403     }
404 
405     USBx_INEP(i)->DIEPTSIZ = 0U;
406     USBx_INEP(i)->DIEPINT  = 0xFB7FU;
407   }
408 
409   for (i = 0U; i < cfg.dev_endpoints; i++)
410   {
411     if ((USBx_OUTEP(i)->DOEPCTL & USB_OTG_DOEPCTL_EPENA) == USB_OTG_DOEPCTL_EPENA)
412     {
413       if (i == 0U)
414       {
415         USBx_OUTEP(i)->DOEPCTL = USB_OTG_DOEPCTL_SNAK;
416       }
417       else
418       {
419         USBx_OUTEP(i)->DOEPCTL = USB_OTG_DOEPCTL_EPDIS | USB_OTG_DOEPCTL_SNAK;
420       }
421     }
422     else
423     {
424       USBx_OUTEP(i)->DOEPCTL = 0U;
425     }
426 
427     USBx_OUTEP(i)->DOEPTSIZ = 0U;
428     USBx_OUTEP(i)->DOEPINT  = 0xFB7FU;
429   }
430 
431   USBx_DEVICE->DIEPMSK &= ~(USB_OTG_DIEPMSK_TXFURM);
432 
433   /* Disable all interrupts. */
434   USBx->GINTMSK = 0U;
435 
436   /* Clear any pending interrupts */
437   USBx->GINTSTS = 0xBFFFFFFFU;
438 
439   /* Enable the common interrupts */
440   if (cfg.dma_enable == 0U)
441   {
442     USBx->GINTMSK |= USB_OTG_GINTMSK_RXFLVLM;
443   }
444 
445   /* Enable interrupts matching to the Device mode ONLY */
446   USBx->GINTMSK |= USB_OTG_GINTMSK_USBSUSPM | USB_OTG_GINTMSK_USBRST |
447                    USB_OTG_GINTMSK_ENUMDNEM | USB_OTG_GINTMSK_IEPINT |
448                    USB_OTG_GINTMSK_OEPINT   | USB_OTG_GINTMSK_IISOIXFRM |
449                    USB_OTG_GINTMSK_PXFRM_IISOOXFRM | USB_OTG_GINTMSK_WUIM;
450 
451   if (cfg.Sof_enable != 0U)
452   {
453     USBx->GINTMSK |= USB_OTG_GINTMSK_SOFM;
454   }
455 
456   if (cfg.vbus_sensing_enable == 1U)
457   {
458     USBx->GINTMSK |= (USB_OTG_GINTMSK_SRQIM | USB_OTG_GINTMSK_OTGINT);
459   }
460 
461   return ret;
462 }
463 
464 /**
465   * @brief  USB_FlushTxFifo Flush a Tx FIFO
466   * @param  USBx  Selected device
467   * @param  num  FIFO number
468   *         This parameter can be a value from 1 to 15
469             15 means Flush all Tx FIFOs
470   * @retval HAL status
471   */
USB_FlushTxFifo(USB_OTG_GlobalTypeDef * USBx,uint32_t num)472 HAL_StatusTypeDef USB_FlushTxFifo(USB_OTG_GlobalTypeDef *USBx, uint32_t num)
473 {
474   __IO uint32_t count = 0U;
475 
476   /* Wait for AHB master IDLE state. */
477   do
478   {
479     count++;
480 
481     if (count > 200000U)
482     {
483       return HAL_TIMEOUT;
484     }
485   } while ((USBx->GRSTCTL & USB_OTG_GRSTCTL_AHBIDL) == 0U);
486 
487   /* Flush TX Fifo */
488   count = 0U;
489   USBx->GRSTCTL = (USB_OTG_GRSTCTL_TXFFLSH | (num << 6));
490 
491   do
492   {
493     count++;
494 
495     if (count > 200000U)
496     {
497       return HAL_TIMEOUT;
498     }
499   } while ((USBx->GRSTCTL & USB_OTG_GRSTCTL_TXFFLSH) == USB_OTG_GRSTCTL_TXFFLSH);
500 
501   return HAL_OK;
502 }
503 
504 /**
505   * @brief  USB_FlushRxFifo  Flush Rx FIFO
506   * @param  USBx  Selected device
507   * @retval HAL status
508   */
USB_FlushRxFifo(USB_OTG_GlobalTypeDef * USBx)509 HAL_StatusTypeDef USB_FlushRxFifo(USB_OTG_GlobalTypeDef *USBx)
510 {
511   __IO uint32_t count = 0U;
512 
513   /* Wait for AHB master IDLE state. */
514   do
515   {
516     count++;
517 
518     if (count > 200000U)
519     {
520       return HAL_TIMEOUT;
521     }
522   } while ((USBx->GRSTCTL & USB_OTG_GRSTCTL_AHBIDL) == 0U);
523 
524   /* Flush RX Fifo */
525   count = 0U;
526   USBx->GRSTCTL = USB_OTG_GRSTCTL_RXFFLSH;
527 
528   do
529   {
530     count++;
531 
532     if (count > 200000U)
533     {
534       return HAL_TIMEOUT;
535     }
536   } while ((USBx->GRSTCTL & USB_OTG_GRSTCTL_RXFFLSH) == USB_OTG_GRSTCTL_RXFFLSH);
537 
538   return HAL_OK;
539 }
540 
541 /**
542   * @brief  USB_SetDevSpeed  Initializes the DevSpd field of DCFG register
543   *         depending the PHY type and the enumeration speed of the device.
544   * @param  USBx  Selected device
545   * @param  speed  device speed
546   *          This parameter can be one of these values:
547   *            @arg USB_OTG_SPEED_HIGH: High speed mode
548   *            @arg USB_OTG_SPEED_HIGH_IN_FULL: High speed core in Full Speed mode
549   *            @arg USB_OTG_SPEED_FULL: Full speed mode
550   * @retval  Hal status
551   */
USB_SetDevSpeed(USB_OTG_GlobalTypeDef * USBx,uint8_t speed)552 HAL_StatusTypeDef USB_SetDevSpeed(USB_OTG_GlobalTypeDef *USBx, uint8_t speed)
553 {
554   uint32_t USBx_BASE = (uint32_t)USBx;
555 
556   USBx_DEVICE->DCFG |= speed;
557   return HAL_OK;
558 }
559 
560 /**
561   * @brief  USB_GetDevSpeed  Return the Dev Speed
562   * @param  USBx  Selected device
563   * @retval speed  device speed
564   *          This parameter can be one of these values:
565   *            @arg USBD_HS_SPEED: High speed mode
566   *            @arg USBD_FS_SPEED: Full speed mode
567   */
USB_GetDevSpeed(USB_OTG_GlobalTypeDef * USBx)568 uint8_t USB_GetDevSpeed(USB_OTG_GlobalTypeDef *USBx)
569 {
570   uint32_t USBx_BASE = (uint32_t)USBx;
571   uint8_t speed;
572   uint32_t DevEnumSpeed = USBx_DEVICE->DSTS & USB_OTG_DSTS_ENUMSPD;
573 
574   if (DevEnumSpeed == DSTS_ENUMSPD_HS_PHY_30MHZ_OR_60MHZ)
575   {
576     speed = USBD_HS_SPEED;
577   }
578   else if ((DevEnumSpeed == DSTS_ENUMSPD_FS_PHY_30MHZ_OR_60MHZ) ||
579            (DevEnumSpeed == DSTS_ENUMSPD_FS_PHY_48MHZ))
580   {
581     speed = USBD_FS_SPEED;
582   }
583   else
584   {
585     speed = 0xFU;
586   }
587 
588   return speed;
589 }
590 
591 /**
592   * @brief  Activate and configure an endpoint
593   * @param  USBx  Selected device
594   * @param  ep pointer to endpoint structure
595   * @retval HAL status
596   */
USB_ActivateEndpoint(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep)597 HAL_StatusTypeDef USB_ActivateEndpoint(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep)
598 {
599   uint32_t USBx_BASE = (uint32_t)USBx;
600   uint32_t epnum = (uint32_t)ep->num;
601 
602   if (ep->is_in == 1U)
603   {
604     USBx_DEVICE->DAINTMSK |= USB_OTG_DAINTMSK_IEPM & (uint32_t)(1UL << (ep->num & EP_ADDR_MSK));
605 
606     if ((USBx_INEP(epnum)->DIEPCTL & USB_OTG_DIEPCTL_USBAEP) == 0U)
607     {
608       USBx_INEP(epnum)->DIEPCTL |= (ep->maxpacket & USB_OTG_DIEPCTL_MPSIZ) |
609                                    ((uint32_t)ep->type << 18) | (epnum << 22) |
610                                    USB_OTG_DIEPCTL_SD0PID_SEVNFRM |
611                                    USB_OTG_DIEPCTL_USBAEP;
612     }
613   }
614   else
615   {
616     USBx_DEVICE->DAINTMSK |= USB_OTG_DAINTMSK_OEPM & ((uint32_t)(1UL << (ep->num & EP_ADDR_MSK)) << 16);
617 
618     if (((USBx_OUTEP(epnum)->DOEPCTL) & USB_OTG_DOEPCTL_USBAEP) == 0U)
619     {
620       USBx_OUTEP(epnum)->DOEPCTL |= (ep->maxpacket & USB_OTG_DOEPCTL_MPSIZ) |
621                                     ((uint32_t)ep->type << 18) |
622                                     USB_OTG_DIEPCTL_SD0PID_SEVNFRM |
623                                     USB_OTG_DOEPCTL_USBAEP;
624     }
625   }
626   return HAL_OK;
627 }
628 
629 /**
630   * @brief  Activate and configure a dedicated endpoint
631   * @param  USBx  Selected device
632   * @param  ep pointer to endpoint structure
633   * @retval HAL status
634   */
USB_ActivateDedicatedEndpoint(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep)635 HAL_StatusTypeDef USB_ActivateDedicatedEndpoint(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep)
636 {
637   uint32_t USBx_BASE = (uint32_t)USBx;
638   uint32_t epnum = (uint32_t)ep->num;
639 
640   /* Read DEPCTLn register */
641   if (ep->is_in == 1U)
642   {
643     if (((USBx_INEP(epnum)->DIEPCTL) & USB_OTG_DIEPCTL_USBAEP) == 0U)
644     {
645       USBx_INEP(epnum)->DIEPCTL |= (ep->maxpacket & USB_OTG_DIEPCTL_MPSIZ) |
646                                    ((uint32_t)ep->type << 18) | (epnum << 22) |
647                                    USB_OTG_DIEPCTL_SD0PID_SEVNFRM |
648                                    USB_OTG_DIEPCTL_USBAEP;
649     }
650 
651     USBx_DEVICE->DEACHMSK |= USB_OTG_DAINTMSK_IEPM & (uint32_t)(1UL << (ep->num & EP_ADDR_MSK));
652   }
653   else
654   {
655     if (((USBx_OUTEP(epnum)->DOEPCTL) & USB_OTG_DOEPCTL_USBAEP) == 0U)
656     {
657       USBx_OUTEP(epnum)->DOEPCTL |= (ep->maxpacket & USB_OTG_DOEPCTL_MPSIZ) |
658                                     ((uint32_t)ep->type << 18) | (epnum << 22) |
659                                     USB_OTG_DOEPCTL_USBAEP;
660     }
661 
662     USBx_DEVICE->DEACHMSK |= USB_OTG_DAINTMSK_OEPM & ((uint32_t)(1UL << (ep->num & EP_ADDR_MSK)) << 16);
663   }
664 
665   return HAL_OK;
666 }
667 
668 /**
669   * @brief  De-activate and de-initialize an endpoint
670   * @param  USBx  Selected device
671   * @param  ep pointer to endpoint structure
672   * @retval HAL status
673   */
USB_DeactivateEndpoint(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep)674 HAL_StatusTypeDef USB_DeactivateEndpoint(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep)
675 {
676   uint32_t USBx_BASE = (uint32_t)USBx;
677   uint32_t epnum = (uint32_t)ep->num;
678 
679   /* Read DEPCTLn register */
680   if (ep->is_in == 1U)
681   {
682     if ((USBx_INEP(epnum)->DIEPCTL & USB_OTG_DIEPCTL_EPENA) == USB_OTG_DIEPCTL_EPENA)
683     {
684       USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_SNAK;
685       USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_EPDIS;
686     }
687 
688     USBx_DEVICE->DEACHMSK &= ~(USB_OTG_DAINTMSK_IEPM & (uint32_t)(1UL << (ep->num & EP_ADDR_MSK)));
689     USBx_DEVICE->DAINTMSK &= ~(USB_OTG_DAINTMSK_IEPM & (uint32_t)(1UL << (ep->num & EP_ADDR_MSK)));
690     USBx_INEP(epnum)->DIEPCTL &= ~(USB_OTG_DIEPCTL_USBAEP |
691                                    USB_OTG_DIEPCTL_MPSIZ |
692                                    USB_OTG_DIEPCTL_TXFNUM |
693                                    USB_OTG_DIEPCTL_SD0PID_SEVNFRM |
694                                    USB_OTG_DIEPCTL_EPTYP);
695   }
696   else
697   {
698     if ((USBx_OUTEP(epnum)->DOEPCTL & USB_OTG_DOEPCTL_EPENA) == USB_OTG_DOEPCTL_EPENA)
699     {
700       USBx_OUTEP(epnum)->DOEPCTL |= USB_OTG_DOEPCTL_SNAK;
701       USBx_OUTEP(epnum)->DOEPCTL |= USB_OTG_DOEPCTL_EPDIS;
702     }
703 
704     USBx_DEVICE->DEACHMSK &= ~(USB_OTG_DAINTMSK_OEPM & ((uint32_t)(1UL << (ep->num & EP_ADDR_MSK)) << 16));
705     USBx_DEVICE->DAINTMSK &= ~(USB_OTG_DAINTMSK_OEPM & ((uint32_t)(1UL << (ep->num & EP_ADDR_MSK)) << 16));
706     USBx_OUTEP(epnum)->DOEPCTL &= ~(USB_OTG_DOEPCTL_USBAEP |
707                                     USB_OTG_DOEPCTL_MPSIZ |
708                                     USB_OTG_DOEPCTL_SD0PID_SEVNFRM |
709                                     USB_OTG_DOEPCTL_EPTYP);
710   }
711 
712   return HAL_OK;
713 }
714 
715 /**
716   * @brief  De-activate and de-initialize a dedicated endpoint
717   * @param  USBx  Selected device
718   * @param  ep pointer to endpoint structure
719   * @retval HAL status
720   */
USB_DeactivateDedicatedEndpoint(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep)721 HAL_StatusTypeDef USB_DeactivateDedicatedEndpoint(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep)
722 {
723   uint32_t USBx_BASE = (uint32_t)USBx;
724   uint32_t epnum = (uint32_t)ep->num;
725 
726   /* Read DEPCTLn register */
727   if (ep->is_in == 1U)
728   {
729     if ((USBx_INEP(epnum)->DIEPCTL & USB_OTG_DIEPCTL_EPENA) == USB_OTG_DIEPCTL_EPENA)
730     {
731       USBx_INEP(epnum)->DIEPCTL  |= USB_OTG_DIEPCTL_SNAK;
732       USBx_INEP(epnum)->DIEPCTL  |= USB_OTG_DIEPCTL_EPDIS;
733     }
734 
735     USBx_INEP(epnum)->DIEPCTL &= ~ USB_OTG_DIEPCTL_USBAEP;
736     USBx_DEVICE->DAINTMSK &= ~(USB_OTG_DAINTMSK_IEPM & (uint32_t)(1UL << (ep->num & EP_ADDR_MSK)));
737   }
738   else
739   {
740     if ((USBx_OUTEP(epnum)->DOEPCTL & USB_OTG_DOEPCTL_EPENA) == USB_OTG_DOEPCTL_EPENA)
741     {
742       USBx_OUTEP(epnum)->DOEPCTL  |= USB_OTG_DOEPCTL_SNAK;
743       USBx_OUTEP(epnum)->DOEPCTL  |= USB_OTG_DOEPCTL_EPDIS;
744     }
745 
746     USBx_OUTEP(epnum)->DOEPCTL &= ~USB_OTG_DOEPCTL_USBAEP;
747     USBx_DEVICE->DAINTMSK &= ~(USB_OTG_DAINTMSK_OEPM & ((uint32_t)(1UL << (ep->num & EP_ADDR_MSK)) << 16));
748   }
749 
750   return HAL_OK;
751 }
752 
753 /**
754   * @brief  USB_EPStartXfer : setup and starts a transfer over an EP
755   * @param  USBx  Selected device
756   * @param  ep pointer to endpoint structure
757   * @param  dma USB dma enabled or disabled
758   *          This parameter can be one of these values:
759   *           0 : DMA feature not used
760   *           1 : DMA feature used
761   * @retval HAL status
762   */
USB_EPStartXfer(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep,uint8_t dma)763 HAL_StatusTypeDef USB_EPStartXfer(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep, uint8_t dma)
764 {
765   uint32_t USBx_BASE = (uint32_t)USBx;
766   uint32_t epnum = (uint32_t)ep->num;
767   uint16_t pktcnt;
768 
769   /* IN endpoint */
770   if (ep->is_in == 1U)
771   {
772     /* Zero Length Packet? */
773     if (ep->xfer_len == 0U)
774     {
775       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_PKTCNT);
776       USBx_INEP(epnum)->DIEPTSIZ |= (USB_OTG_DIEPTSIZ_PKTCNT & (1U << 19));
777       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_XFRSIZ);
778     }
779     else
780     {
781       /* Program the transfer size and packet count
782       * as follows: xfersize = N * maxpacket +
783       * short_packet pktcnt = N + (short_packet
784       * exist ? 1 : 0)
785       */
786       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_XFRSIZ);
787       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_PKTCNT);
788       USBx_INEP(epnum)->DIEPTSIZ |= (USB_OTG_DIEPTSIZ_PKTCNT &
789                                      (((ep->xfer_len + ep->maxpacket - 1U) / ep->maxpacket) << 19));
790 
791       USBx_INEP(epnum)->DIEPTSIZ |= (USB_OTG_DIEPTSIZ_XFRSIZ & ep->xfer_len);
792 
793       if (ep->type == EP_TYPE_ISOC)
794       {
795         USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_MULCNT);
796         USBx_INEP(epnum)->DIEPTSIZ |= (USB_OTG_DIEPTSIZ_MULCNT & (1U << 29));
797       }
798     }
799 
800     if (dma == 1U)
801     {
802       if ((uint32_t)ep->dma_addr != 0U)
803       {
804         USBx_INEP(epnum)->DIEPDMA = (uint32_t)(ep->dma_addr);
805       }
806 
807       if (ep->type == EP_TYPE_ISOC)
808       {
809         if ((USBx_DEVICE->DSTS & (1U << 8)) == 0U)
810         {
811           USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_SODDFRM;
812         }
813         else
814         {
815           USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_SD0PID_SEVNFRM;
816         }
817       }
818 
819       /* EP enable, IN data in FIFO */
820       USBx_INEP(epnum)->DIEPCTL |= (USB_OTG_DIEPCTL_CNAK | USB_OTG_DIEPCTL_EPENA);
821     }
822     else
823     {
824       /* EP enable, IN data in FIFO */
825       USBx_INEP(epnum)->DIEPCTL |= (USB_OTG_DIEPCTL_CNAK | USB_OTG_DIEPCTL_EPENA);
826 
827       if (ep->type != EP_TYPE_ISOC)
828       {
829         /* Enable the Tx FIFO Empty Interrupt for this EP */
830         if (ep->xfer_len > 0U)
831         {
832           USBx_DEVICE->DIEPEMPMSK |= 1UL << (ep->num & EP_ADDR_MSK);
833         }
834       }
835       else
836       {
837         if ((USBx_DEVICE->DSTS & (1U << 8)) == 0U)
838         {
839           USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_SODDFRM;
840         }
841         else
842         {
843           USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_SD0PID_SEVNFRM;
844         }
845 
846         (void)USB_WritePacket(USBx, ep->xfer_buff, ep->num, (uint16_t)ep->xfer_len, dma);
847       }
848     }
849   }
850   else /* OUT endpoint */
851   {
852     /* Program the transfer size and packet count as follows:
853     * pktcnt = N
854     * xfersize = N * maxpacket
855     */
856     USBx_OUTEP(epnum)->DOEPTSIZ &= ~(USB_OTG_DOEPTSIZ_XFRSIZ);
857     USBx_OUTEP(epnum)->DOEPTSIZ &= ~(USB_OTG_DOEPTSIZ_PKTCNT);
858 
859     if (ep->xfer_len == 0U)
860     {
861       USBx_OUTEP(epnum)->DOEPTSIZ |= (USB_OTG_DOEPTSIZ_XFRSIZ & ep->maxpacket);
862       USBx_OUTEP(epnum)->DOEPTSIZ |= (USB_OTG_DOEPTSIZ_PKTCNT & (1U << 19));
863     }
864     else
865     {
866       pktcnt = (uint16_t)((ep->xfer_len + ep->maxpacket - 1U) / ep->maxpacket);
867       ep->xfer_size = ep->maxpacket * pktcnt;
868 
869       USBx_OUTEP(epnum)->DOEPTSIZ |= USB_OTG_DOEPTSIZ_PKTCNT & ((uint32_t)pktcnt << 19);
870       USBx_OUTEP(epnum)->DOEPTSIZ |= USB_OTG_DOEPTSIZ_XFRSIZ & ep->xfer_size;
871     }
872 
873     if (dma == 1U)
874     {
875       if ((uint32_t)ep->xfer_buff != 0U)
876       {
877         USBx_OUTEP(epnum)->DOEPDMA = (uint32_t)(ep->xfer_buff);
878       }
879     }
880 
881     if (ep->type == EP_TYPE_ISOC)
882     {
883       if ((USBx_DEVICE->DSTS & (1U << 8)) == 0U)
884       {
885         USBx_OUTEP(epnum)->DOEPCTL |= USB_OTG_DOEPCTL_SODDFRM;
886       }
887       else
888       {
889         USBx_OUTEP(epnum)->DOEPCTL |= USB_OTG_DOEPCTL_SD0PID_SEVNFRM;
890       }
891     }
892     /* EP enable */
893     USBx_OUTEP(epnum)->DOEPCTL |= (USB_OTG_DOEPCTL_CNAK | USB_OTG_DOEPCTL_EPENA);
894   }
895 
896   return HAL_OK;
897 }
898 
899 /**
900   * @brief  USB_EP0StartXfer : setup and starts a transfer over the EP  0
901   * @param  USBx  Selected device
902   * @param  ep pointer to endpoint structure
903   * @param  dma USB dma enabled or disabled
904   *          This parameter can be one of these values:
905   *           0 : DMA feature not used
906   *           1 : DMA feature used
907   * @retval HAL status
908   */
USB_EP0StartXfer(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep,uint8_t dma)909 HAL_StatusTypeDef USB_EP0StartXfer(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep, uint8_t dma)
910 {
911   uint32_t USBx_BASE = (uint32_t)USBx;
912   uint32_t epnum = (uint32_t)ep->num;
913 
914   /* IN endpoint */
915   if (ep->is_in == 1U)
916   {
917     /* Zero Length Packet? */
918     if (ep->xfer_len == 0U)
919     {
920       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_PKTCNT);
921       USBx_INEP(epnum)->DIEPTSIZ |= (USB_OTG_DIEPTSIZ_PKTCNT & (1U << 19));
922       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_XFRSIZ);
923     }
924     else
925     {
926       /* Program the transfer size and packet count
927       * as follows: xfersize = N * maxpacket +
928       * short_packet pktcnt = N + (short_packet
929       * exist ? 1 : 0)
930       */
931       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_XFRSIZ);
932       USBx_INEP(epnum)->DIEPTSIZ &= ~(USB_OTG_DIEPTSIZ_PKTCNT);
933 
934       if (ep->xfer_len > ep->maxpacket)
935       {
936         ep->xfer_len = ep->maxpacket;
937       }
938       USBx_INEP(epnum)->DIEPTSIZ |= (USB_OTG_DIEPTSIZ_PKTCNT & (1U << 19));
939       USBx_INEP(epnum)->DIEPTSIZ |= (USB_OTG_DIEPTSIZ_XFRSIZ & ep->xfer_len);
940     }
941 
942     if (dma == 1U)
943     {
944       if ((uint32_t)ep->dma_addr != 0U)
945       {
946         USBx_INEP(epnum)->DIEPDMA = (uint32_t)(ep->dma_addr);
947       }
948 
949       /* EP enable, IN data in FIFO */
950       USBx_INEP(epnum)->DIEPCTL |= (USB_OTG_DIEPCTL_CNAK | USB_OTG_DIEPCTL_EPENA);
951     }
952     else
953     {
954       /* EP enable, IN data in FIFO */
955       USBx_INEP(epnum)->DIEPCTL |= (USB_OTG_DIEPCTL_CNAK | USB_OTG_DIEPCTL_EPENA);
956 
957       /* Enable the Tx FIFO Empty Interrupt for this EP */
958       if (ep->xfer_len > 0U)
959       {
960         USBx_DEVICE->DIEPEMPMSK |= 1UL << (ep->num & EP_ADDR_MSK);
961       }
962     }
963   }
964   else /* OUT endpoint */
965   {
966     /* Program the transfer size and packet count as follows:
967     * pktcnt = N
968     * xfersize = N * maxpacket
969     */
970     USBx_OUTEP(epnum)->DOEPTSIZ &= ~(USB_OTG_DOEPTSIZ_XFRSIZ);
971     USBx_OUTEP(epnum)->DOEPTSIZ &= ~(USB_OTG_DOEPTSIZ_PKTCNT);
972 
973     if (ep->xfer_len > 0U)
974     {
975       ep->xfer_len = ep->maxpacket;
976     }
977 
978     /* Store transfer size, for EP0 this is equal to endpoint max packet size */
979     ep->xfer_size = ep->maxpacket;
980 
981     USBx_OUTEP(epnum)->DOEPTSIZ |= (USB_OTG_DOEPTSIZ_PKTCNT & (1U << 19));
982     USBx_OUTEP(epnum)->DOEPTSIZ |= (USB_OTG_DOEPTSIZ_XFRSIZ & ep->xfer_size);
983 
984     if (dma == 1U)
985     {
986       if ((uint32_t)ep->xfer_buff != 0U)
987       {
988         USBx_OUTEP(epnum)->DOEPDMA = (uint32_t)(ep->xfer_buff);
989       }
990     }
991 
992     /* EP enable */
993     USBx_OUTEP(epnum)->DOEPCTL |= (USB_OTG_DOEPCTL_CNAK | USB_OTG_DOEPCTL_EPENA);
994   }
995 
996   return HAL_OK;
997 }
998 
999 
1000 /**
1001    * @brief  USB_EPStoptXfer  Stop transfer on an EP
1002    * @param  USBx  usb device instance
1003    * @param  ep pointer to endpoint structure
1004    * @retval HAL status
1005    */
USB_EPStopXfer(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep)1006 HAL_StatusTypeDef USB_EPStopXfer(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep)
1007 {
1008   __IO uint32_t count = 0U;
1009   HAL_StatusTypeDef ret = HAL_OK;
1010   uint32_t USBx_BASE = (uint32_t)USBx;
1011 
1012   /* IN endpoint */
1013   if (ep->is_in == 1U)
1014   {
1015     /* EP enable, IN data in FIFO */
1016     if (((USBx_INEP(ep->num)->DIEPCTL) & USB_OTG_DIEPCTL_EPENA) == USB_OTG_DIEPCTL_EPENA)
1017     {
1018       USBx_INEP(ep->num)->DIEPCTL |= (USB_OTG_DIEPCTL_SNAK);
1019       USBx_INEP(ep->num)->DIEPCTL |= (USB_OTG_DIEPCTL_EPDIS);
1020 
1021       do
1022       {
1023         count++;
1024 
1025         if (count > 10000U)
1026         {
1027           ret = HAL_ERROR;
1028           break;
1029         }
1030       } while (((USBx_INEP(ep->num)->DIEPCTL) & USB_OTG_DIEPCTL_EPENA) ==  USB_OTG_DIEPCTL_EPENA);
1031     }
1032   }
1033   else /* OUT endpoint */
1034   {
1035     if (((USBx_OUTEP(ep->num)->DOEPCTL) & USB_OTG_DOEPCTL_EPENA) == USB_OTG_DOEPCTL_EPENA)
1036     {
1037       USBx_OUTEP(ep->num)->DOEPCTL |= (USB_OTG_DOEPCTL_SNAK);
1038       USBx_OUTEP(ep->num)->DOEPCTL |= (USB_OTG_DOEPCTL_EPDIS);
1039 
1040       do
1041       {
1042         count++;
1043 
1044         if (count > 10000U)
1045         {
1046           ret = HAL_ERROR;
1047           break;
1048         }
1049       } while (((USBx_OUTEP(ep->num)->DOEPCTL) & USB_OTG_DOEPCTL_EPENA) ==  USB_OTG_DOEPCTL_EPENA);
1050     }
1051   }
1052 
1053   return ret;
1054 }
1055 
1056 
1057 /**
1058   * @brief  USB_WritePacket : Writes a packet into the Tx FIFO associated
1059   *         with the EP/channel
1060   * @param  USBx  Selected device
1061   * @param  src   pointer to source buffer
1062   * @param  ch_ep_num  endpoint or host channel number
1063   * @param  len  Number of bytes to write
1064   * @param  dma USB dma enabled or disabled
1065   *          This parameter can be one of these values:
1066   *           0 : DMA feature not used
1067   *           1 : DMA feature used
1068   * @retval HAL status
1069   */
USB_WritePacket(USB_OTG_GlobalTypeDef * USBx,uint8_t * src,uint8_t ch_ep_num,uint16_t len,uint8_t dma)1070 HAL_StatusTypeDef USB_WritePacket(USB_OTG_GlobalTypeDef *USBx, uint8_t *src,
1071                                   uint8_t ch_ep_num, uint16_t len, uint8_t dma)
1072 {
1073   uint32_t USBx_BASE = (uint32_t)USBx;
1074   uint8_t *pSrc = src;
1075   uint32_t count32b;
1076   uint32_t i;
1077 
1078   if (dma == 0U)
1079   {
1080     count32b = ((uint32_t)len + 3U) / 4U;
1081     for (i = 0U; i < count32b; i++)
1082     {
1083       USBx_DFIFO((uint32_t)ch_ep_num) = __UNALIGNED_UINT32_READ(pSrc);
1084       pSrc++;
1085       pSrc++;
1086       pSrc++;
1087       pSrc++;
1088     }
1089   }
1090 
1091   return HAL_OK;
1092 }
1093 
1094 /**
1095   * @brief  USB_ReadPacket : read a packet from the RX FIFO
1096   * @param  USBx  Selected device
1097   * @param  dest  source pointer
1098   * @param  len  Number of bytes to read
1099   * @retval pointer to destination buffer
1100   */
USB_ReadPacket(USB_OTG_GlobalTypeDef * USBx,uint8_t * dest,uint16_t len)1101 void *USB_ReadPacket(USB_OTG_GlobalTypeDef *USBx, uint8_t *dest, uint16_t len)
1102 {
1103   uint32_t USBx_BASE = (uint32_t)USBx;
1104   uint8_t *pDest = dest;
1105   uint32_t pData;
1106   uint32_t i;
1107   uint32_t count32b = (uint32_t)len >> 2U;
1108   uint16_t remaining_bytes = len % 4U;
1109 
1110   for (i = 0U; i < count32b; i++)
1111   {
1112     __UNALIGNED_UINT32_WRITE(pDest, USBx_DFIFO(0U));
1113     pDest++;
1114     pDest++;
1115     pDest++;
1116     pDest++;
1117   }
1118 
1119   /* When Number of data is not word aligned, read the remaining byte */
1120   if (remaining_bytes != 0U)
1121   {
1122     i = 0U;
1123     __UNALIGNED_UINT32_WRITE(&pData, USBx_DFIFO(0U));
1124 
1125     do
1126     {
1127       *(uint8_t *)pDest = (uint8_t)(pData >> (8U * (uint8_t)(i)));
1128       i++;
1129       pDest++;
1130       remaining_bytes--;
1131     } while (remaining_bytes != 0U);
1132   }
1133 
1134   return ((void *)pDest);
1135 }
1136 
1137 /**
1138   * @brief  USB_EPSetStall : set a stall condition over an EP
1139   * @param  USBx  Selected device
1140   * @param  ep pointer to endpoint structure
1141   * @retval HAL status
1142   */
USB_EPSetStall(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep)1143 HAL_StatusTypeDef USB_EPSetStall(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep)
1144 {
1145   uint32_t USBx_BASE = (uint32_t)USBx;
1146   uint32_t epnum = (uint32_t)ep->num;
1147 
1148   if (ep->is_in == 1U)
1149   {
1150     if (((USBx_INEP(epnum)->DIEPCTL & USB_OTG_DIEPCTL_EPENA) == 0U) && (epnum != 0U))
1151     {
1152       USBx_INEP(epnum)->DIEPCTL &= ~(USB_OTG_DIEPCTL_EPDIS);
1153     }
1154     USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_STALL;
1155   }
1156   else
1157   {
1158     if (((USBx_OUTEP(epnum)->DOEPCTL & USB_OTG_DOEPCTL_EPENA) == 0U) && (epnum != 0U))
1159     {
1160       USBx_OUTEP(epnum)->DOEPCTL &= ~(USB_OTG_DOEPCTL_EPDIS);
1161     }
1162     USBx_OUTEP(epnum)->DOEPCTL |= USB_OTG_DOEPCTL_STALL;
1163   }
1164 
1165   return HAL_OK;
1166 }
1167 
1168 /**
1169   * @brief  USB_EPClearStall : Clear a stall condition over an EP
1170   * @param  USBx  Selected device
1171   * @param  ep pointer to endpoint structure
1172   * @retval HAL status
1173   */
USB_EPClearStall(USB_OTG_GlobalTypeDef * USBx,USB_OTG_EPTypeDef * ep)1174 HAL_StatusTypeDef USB_EPClearStall(USB_OTG_GlobalTypeDef *USBx, USB_OTG_EPTypeDef *ep)
1175 {
1176   uint32_t USBx_BASE = (uint32_t)USBx;
1177   uint32_t epnum = (uint32_t)ep->num;
1178 
1179   if (ep->is_in == 1U)
1180   {
1181     USBx_INEP(epnum)->DIEPCTL &= ~USB_OTG_DIEPCTL_STALL;
1182     if ((ep->type == EP_TYPE_INTR) || (ep->type == EP_TYPE_BULK))
1183     {
1184       USBx_INEP(epnum)->DIEPCTL |= USB_OTG_DIEPCTL_SD0PID_SEVNFRM; /* DATA0 */
1185     }
1186   }
1187   else
1188   {
1189     USBx_OUTEP(epnum)->DOEPCTL &= ~USB_OTG_DOEPCTL_STALL;
1190     if ((ep->type == EP_TYPE_INTR) || (ep->type == EP_TYPE_BULK))
1191     {
1192       USBx_OUTEP(epnum)->DOEPCTL |= USB_OTG_DOEPCTL_SD0PID_SEVNFRM; /* DATA0 */
1193     }
1194   }
1195   return HAL_OK;
1196 }
1197 
1198 /**
1199   * @brief  USB_StopDevice : Stop the usb device mode
1200   * @param  USBx  Selected device
1201   * @retval HAL status
1202   */
USB_StopDevice(USB_OTG_GlobalTypeDef * USBx)1203 HAL_StatusTypeDef USB_StopDevice(USB_OTG_GlobalTypeDef *USBx)
1204 {
1205   HAL_StatusTypeDef ret;
1206   uint32_t USBx_BASE = (uint32_t)USBx;
1207   uint32_t i;
1208 
1209   /* Clear Pending interrupt */
1210   for (i = 0U; i < 15U; i++)
1211   {
1212     USBx_INEP(i)->DIEPINT = 0xFB7FU;
1213     USBx_OUTEP(i)->DOEPINT = 0xFB7FU;
1214   }
1215 
1216   /* Clear interrupt masks */
1217   USBx_DEVICE->DIEPMSK  = 0U;
1218   USBx_DEVICE->DOEPMSK  = 0U;
1219   USBx_DEVICE->DAINTMSK = 0U;
1220 
1221   /* Flush the FIFO */
1222   ret = USB_FlushRxFifo(USBx);
1223   if (ret != HAL_OK)
1224   {
1225     return ret;
1226   }
1227 
1228   ret = USB_FlushTxFifo(USBx,  0x10U);
1229   if (ret != HAL_OK)
1230   {
1231     return ret;
1232   }
1233 
1234   return ret;
1235 }
1236 
1237 /**
1238   * @brief  USB_SetDevAddress : Stop the usb device mode
1239   * @param  USBx  Selected device
1240   * @param  address  new device address to be assigned
1241   *          This parameter can be a value from 0 to 255
1242   * @retval HAL status
1243   */
USB_SetDevAddress(USB_OTG_GlobalTypeDef * USBx,uint8_t address)1244 HAL_StatusTypeDef  USB_SetDevAddress(USB_OTG_GlobalTypeDef *USBx, uint8_t address)
1245 {
1246   uint32_t USBx_BASE = (uint32_t)USBx;
1247 
1248   USBx_DEVICE->DCFG &= ~(USB_OTG_DCFG_DAD);
1249   USBx_DEVICE->DCFG |= ((uint32_t)address << 4) & USB_OTG_DCFG_DAD;
1250 
1251   return HAL_OK;
1252 }
1253 
1254 /**
1255   * @brief  USB_DevConnect : Connect the USB device by enabling Rpu
1256   * @param  USBx  Selected device
1257   * @retval HAL status
1258   */
USB_DevConnect(USB_OTG_GlobalTypeDef * USBx)1259 HAL_StatusTypeDef  USB_DevConnect(USB_OTG_GlobalTypeDef *USBx)
1260 {
1261   uint32_t USBx_BASE = (uint32_t)USBx;
1262 
1263   /* In case phy is stopped, ensure to ungate and restore the phy CLK */
1264   USBx_PCGCCTL &= ~(USB_OTG_PCGCCTL_STOPCLK | USB_OTG_PCGCCTL_GATECLK);
1265 
1266   USBx_DEVICE->DCTL &= ~USB_OTG_DCTL_SDIS;
1267 
1268   return HAL_OK;
1269 }
1270 
1271 /**
1272   * @brief  USB_DevDisconnect : Disconnect the USB device by disabling Rpu
1273   * @param  USBx  Selected device
1274   * @retval HAL status
1275   */
USB_DevDisconnect(USB_OTG_GlobalTypeDef * USBx)1276 HAL_StatusTypeDef  USB_DevDisconnect(USB_OTG_GlobalTypeDef *USBx)
1277 {
1278   uint32_t USBx_BASE = (uint32_t)USBx;
1279 
1280   /* In case phy is stopped, ensure to ungate and restore the phy CLK */
1281   USBx_PCGCCTL &= ~(USB_OTG_PCGCCTL_STOPCLK | USB_OTG_PCGCCTL_GATECLK);
1282 
1283   USBx_DEVICE->DCTL |= USB_OTG_DCTL_SDIS;
1284 
1285   return HAL_OK;
1286 }
1287 
1288 /**
1289   * @brief  USB_ReadInterrupts: return the global USB interrupt status
1290   * @param  USBx  Selected device
1291   * @retval HAL status
1292   */
USB_ReadInterrupts(USB_OTG_GlobalTypeDef * USBx)1293 uint32_t  USB_ReadInterrupts(USB_OTG_GlobalTypeDef *USBx)
1294 {
1295   uint32_t tmpreg;
1296 
1297   tmpreg = USBx->GINTSTS;
1298   tmpreg &= USBx->GINTMSK;
1299 
1300   return tmpreg;
1301 }
1302 
1303 /**
1304   * @brief  USB_ReadDevAllOutEpInterrupt: return the USB device OUT endpoints interrupt status
1305   * @param  USBx  Selected device
1306   * @retval HAL status
1307   */
USB_ReadDevAllOutEpInterrupt(USB_OTG_GlobalTypeDef * USBx)1308 uint32_t USB_ReadDevAllOutEpInterrupt(USB_OTG_GlobalTypeDef *USBx)
1309 {
1310   uint32_t USBx_BASE = (uint32_t)USBx;
1311   uint32_t tmpreg;
1312 
1313   tmpreg  = USBx_DEVICE->DAINT;
1314   tmpreg &= USBx_DEVICE->DAINTMSK;
1315 
1316   return ((tmpreg & 0xffff0000U) >> 16);
1317 }
1318 
1319 /**
1320   * @brief  USB_ReadDevAllInEpInterrupt: return the USB device IN endpoints interrupt status
1321   * @param  USBx  Selected device
1322   * @retval HAL status
1323   */
USB_ReadDevAllInEpInterrupt(USB_OTG_GlobalTypeDef * USBx)1324 uint32_t USB_ReadDevAllInEpInterrupt(USB_OTG_GlobalTypeDef *USBx)
1325 {
1326   uint32_t USBx_BASE = (uint32_t)USBx;
1327   uint32_t tmpreg;
1328 
1329   tmpreg  = USBx_DEVICE->DAINT;
1330   tmpreg &= USBx_DEVICE->DAINTMSK;
1331 
1332   return ((tmpreg & 0xFFFFU));
1333 }
1334 
1335 /**
1336   * @brief  Returns Device OUT EP Interrupt register
1337   * @param  USBx  Selected device
1338   * @param  epnum  endpoint number
1339   *          This parameter can be a value from 0 to 15
1340   * @retval Device OUT EP Interrupt register
1341   */
USB_ReadDevOutEPInterrupt(USB_OTG_GlobalTypeDef * USBx,uint8_t epnum)1342 uint32_t USB_ReadDevOutEPInterrupt(USB_OTG_GlobalTypeDef *USBx, uint8_t epnum)
1343 {
1344   uint32_t USBx_BASE = (uint32_t)USBx;
1345   uint32_t tmpreg;
1346 
1347   tmpreg  = USBx_OUTEP((uint32_t)epnum)->DOEPINT;
1348   tmpreg &= USBx_DEVICE->DOEPMSK;
1349 
1350   return tmpreg;
1351 }
1352 
1353 /**
1354   * @brief  Returns Device IN EP Interrupt register
1355   * @param  USBx  Selected device
1356   * @param  epnum  endpoint number
1357   *          This parameter can be a value from 0 to 15
1358   * @retval Device IN EP Interrupt register
1359   */
USB_ReadDevInEPInterrupt(USB_OTG_GlobalTypeDef * USBx,uint8_t epnum)1360 uint32_t USB_ReadDevInEPInterrupt(USB_OTG_GlobalTypeDef *USBx, uint8_t epnum)
1361 {
1362   uint32_t USBx_BASE = (uint32_t)USBx;
1363   uint32_t tmpreg;
1364   uint32_t msk;
1365   uint32_t emp;
1366 
1367   msk = USBx_DEVICE->DIEPMSK;
1368   emp = USBx_DEVICE->DIEPEMPMSK;
1369   msk |= ((emp >> (epnum & EP_ADDR_MSK)) & 0x1U) << 7;
1370   tmpreg = USBx_INEP((uint32_t)epnum)->DIEPINT & msk;
1371 
1372   return tmpreg;
1373 }
1374 
1375 /**
1376   * @brief  USB_ClearInterrupts: clear a USB interrupt
1377   * @param  USBx  Selected device
1378   * @param  interrupt  flag
1379   * @retval None
1380   */
USB_ClearInterrupts(USB_OTG_GlobalTypeDef * USBx,uint32_t interrupt)1381 void  USB_ClearInterrupts(USB_OTG_GlobalTypeDef *USBx, uint32_t interrupt)
1382 {
1383   USBx->GINTSTS |= interrupt;
1384 }
1385 
1386 /**
1387   * @brief  Returns USB core mode
1388   * @param  USBx  Selected device
1389   * @retval return core mode : Host or Device
1390   *          This parameter can be one of these values:
1391   *           0 : Host
1392   *           1 : Device
1393   */
USB_GetMode(USB_OTG_GlobalTypeDef * USBx)1394 uint32_t USB_GetMode(USB_OTG_GlobalTypeDef *USBx)
1395 {
1396   return ((USBx->GINTSTS) & 0x1U);
1397 }
1398 
1399 /**
1400   * @brief  Activate EP0 for Setup transactions
1401   * @param  USBx  Selected device
1402   * @retval HAL status
1403   */
USB_ActivateSetup(USB_OTG_GlobalTypeDef * USBx)1404 HAL_StatusTypeDef  USB_ActivateSetup(USB_OTG_GlobalTypeDef *USBx)
1405 {
1406   uint32_t USBx_BASE = (uint32_t)USBx;
1407 
1408   /* Set the MPS of the IN EP0 to 64 bytes */
1409   USBx_INEP(0U)->DIEPCTL &= ~USB_OTG_DIEPCTL_MPSIZ;
1410 
1411   USBx_DEVICE->DCTL |= USB_OTG_DCTL_CGINAK;
1412 
1413   return HAL_OK;
1414 }
1415 
1416 /**
1417   * @brief  Prepare the EP0 to start the first control setup
1418   * @param  USBx  Selected device
1419   * @param  dma USB dma enabled or disabled
1420   *          This parameter can be one of these values:
1421   *           0 : DMA feature not used
1422   *           1 : DMA feature used
1423   * @param  psetup  pointer to setup packet
1424   * @retval HAL status
1425   */
USB_EP0_OutStart(USB_OTG_GlobalTypeDef * USBx,uint8_t dma,uint8_t * psetup)1426 HAL_StatusTypeDef USB_EP0_OutStart(USB_OTG_GlobalTypeDef *USBx, uint8_t dma, uint8_t *psetup)
1427 {
1428   uint32_t USBx_BASE = (uint32_t)USBx;
1429   uint32_t gSNPSiD = *(__IO uint32_t *)(&USBx->CID + 0x1U);
1430 
1431   if (gSNPSiD > USB_OTG_CORE_ID_300A)
1432   {
1433     if ((USBx_OUTEP(0U)->DOEPCTL & USB_OTG_DOEPCTL_EPENA) == USB_OTG_DOEPCTL_EPENA)
1434     {
1435       return HAL_OK;
1436     }
1437   }
1438 
1439   USBx_OUTEP(0U)->DOEPTSIZ = 0U;
1440   USBx_OUTEP(0U)->DOEPTSIZ |= (USB_OTG_DOEPTSIZ_PKTCNT & (1U << 19));
1441   USBx_OUTEP(0U)->DOEPTSIZ |= (3U * 8U);
1442   USBx_OUTEP(0U)->DOEPTSIZ |=  USB_OTG_DOEPTSIZ_STUPCNT;
1443 
1444   if (dma == 1U)
1445   {
1446     USBx_OUTEP(0U)->DOEPDMA = (uint32_t)psetup;
1447     /* EP enable */
1448     USBx_OUTEP(0U)->DOEPCTL |= USB_OTG_DOEPCTL_EPENA | USB_OTG_DOEPCTL_USBAEP;
1449   }
1450 
1451   return HAL_OK;
1452 }
1453 
1454 /**
1455   * @brief  Reset the USB Core (needed after USB clock settings change)
1456   * @param  USBx  Selected device
1457   * @retval HAL status
1458   */
USB_CoreReset(USB_OTG_GlobalTypeDef * USBx)1459 static HAL_StatusTypeDef USB_CoreReset(USB_OTG_GlobalTypeDef *USBx)
1460 {
1461   __IO uint32_t count = 0U;
1462 
1463   /* Wait for AHB master IDLE state. */
1464   do
1465   {
1466     count++;
1467 
1468     if (count > 200000U)
1469     {
1470       return HAL_TIMEOUT;
1471     }
1472   } while ((USBx->GRSTCTL & USB_OTG_GRSTCTL_AHBIDL) == 0U);
1473 
1474   /* Core Soft Reset */
1475   count = 0U;
1476   USBx->GRSTCTL |= USB_OTG_GRSTCTL_CSRST;
1477 
1478   do
1479   {
1480     count++;
1481 
1482     if (count > 200000U)
1483     {
1484       return HAL_TIMEOUT;
1485     }
1486   } while ((USBx->GRSTCTL & USB_OTG_GRSTCTL_CSRST) == USB_OTG_GRSTCTL_CSRST);
1487 
1488   return HAL_OK;
1489 }
1490 
1491 /**
1492   * @brief  USB_HostInit : Initializes the USB OTG controller registers
1493   *         for Host mode
1494   * @param  USBx  Selected device
1495   * @param  cfg   pointer to a USB_OTG_CfgTypeDef structure that contains
1496   *         the configuration information for the specified USBx peripheral.
1497   * @retval HAL status
1498   */
USB_HostInit(USB_OTG_GlobalTypeDef * USBx,USB_OTG_CfgTypeDef cfg)1499 HAL_StatusTypeDef USB_HostInit(USB_OTG_GlobalTypeDef *USBx, USB_OTG_CfgTypeDef cfg)
1500 {
1501   HAL_StatusTypeDef ret = HAL_OK;
1502   uint32_t USBx_BASE = (uint32_t)USBx;
1503   uint32_t i;
1504 
1505   /* Restart the Phy Clock */
1506   USBx_PCGCCTL = 0U;
1507 
1508 #if defined(STM32F446xx) || defined(STM32F469xx) || defined(STM32F479xx) || defined(STM32F412Zx) || defined(STM32F412Vx) || defined(STM32F412Rx) || defined(STM32F412Cx) || defined(STM32F413xx) || defined(STM32F423xx)
1509   /* Disable HW VBUS sensing */
1510   USBx->GCCFG &= ~(USB_OTG_GCCFG_VBDEN);
1511 #else
1512   /*
1513   * Disable HW VBUS sensing. VBUS is internally considered to be always
1514   * at VBUS-Valid level (5V).
1515   */
1516   USBx->GCCFG |= USB_OTG_GCCFG_NOVBUSSENS;
1517   USBx->GCCFG &= ~USB_OTG_GCCFG_VBUSBSEN;
1518   USBx->GCCFG &= ~USB_OTG_GCCFG_VBUSASEN;
1519 #endif /* defined(STM32F446xx) || defined(STM32F469xx) || defined(STM32F479xx) || defined(STM32F412Zx) || defined(STM32F412Vx) || defined(STM32F412Rx) || defined(STM32F412Cx) || defined(STM32F413xx) || defined(STM32F423xx) */
1520 #if defined(STM32F412Zx) || defined(STM32F412Vx) || defined(STM32F412Rx) || defined(STM32F412Cx) || defined(STM32F413xx) || defined(STM32F423xx)
1521   /* Disable Battery chargin detector */
1522   USBx->GCCFG &= ~(USB_OTG_GCCFG_BCDEN);
1523 #endif /* defined(STM32F412Zx) || defined(STM32F412Vx) || defined(STM32F412Rx) || defined(STM32F412Cx) || defined(STM32F413xx) || defined(STM32F423xx) */
1524 
1525   if ((USBx->CID & (0x1U << 8)) != 0U)
1526   {
1527     if (cfg.speed == USBH_FSLS_SPEED)
1528     {
1529       /* Force Device Enumeration to FS/LS mode only */
1530       USBx_HOST->HCFG |= USB_OTG_HCFG_FSLSS;
1531     }
1532     else
1533     {
1534       /* Set default Max speed support */
1535       USBx_HOST->HCFG &= ~(USB_OTG_HCFG_FSLSS);
1536     }
1537   }
1538   else
1539   {
1540     /* Set default Max speed support */
1541     USBx_HOST->HCFG &= ~(USB_OTG_HCFG_FSLSS);
1542   }
1543 
1544   /* Make sure the FIFOs are flushed. */
1545   if (USB_FlushTxFifo(USBx, 0x10U) != HAL_OK) /* all Tx FIFOs */
1546   {
1547     ret = HAL_ERROR;
1548   }
1549 
1550   if (USB_FlushRxFifo(USBx) != HAL_OK)
1551   {
1552     ret = HAL_ERROR;
1553   }
1554 
1555   /* Clear all pending HC Interrupts */
1556   for (i = 0U; i < cfg.Host_channels; i++)
1557   {
1558     USBx_HC(i)->HCINT = 0xFFFFFFFFU;
1559     USBx_HC(i)->HCINTMSK = 0U;
1560   }
1561 
1562   /* Disable all interrupts. */
1563   USBx->GINTMSK = 0U;
1564 
1565   /* Clear any pending interrupts */
1566   USBx->GINTSTS = 0xFFFFFFFFU;
1567 
1568   if ((USBx->CID & (0x1U << 8)) != 0U)
1569   {
1570     /* set Rx FIFO size */
1571     USBx->GRXFSIZ  = 0x200U;
1572     USBx->DIEPTXF0_HNPTXFSIZ = (uint32_t)(((0x100U << 16) & USB_OTG_NPTXFD) | 0x200U);
1573     USBx->HPTXFSIZ = (uint32_t)(((0xE0U << 16) & USB_OTG_HPTXFSIZ_PTXFD) | 0x300U);
1574   }
1575   else
1576   {
1577     /* set Rx FIFO size */
1578     USBx->GRXFSIZ  = 0x80U;
1579     USBx->DIEPTXF0_HNPTXFSIZ = (uint32_t)(((0x60U << 16) & USB_OTG_NPTXFD) | 0x80U);
1580     USBx->HPTXFSIZ = (uint32_t)(((0x40U << 16)& USB_OTG_HPTXFSIZ_PTXFD) | 0xE0U);
1581   }
1582 
1583   /* Enable the common interrupts */
1584   if (cfg.dma_enable == 0U)
1585   {
1586     USBx->GINTMSK |= USB_OTG_GINTMSK_RXFLVLM;
1587   }
1588 
1589   /* Enable interrupts matching to the Host mode ONLY */
1590   USBx->GINTMSK |= (USB_OTG_GINTMSK_PRTIM            | USB_OTG_GINTMSK_HCIM | \
1591                     USB_OTG_GINTMSK_SOFM             | USB_OTG_GINTSTS_DISCINT | \
1592                     USB_OTG_GINTMSK_PXFRM_IISOOXFRM  | USB_OTG_GINTMSK_WUIM);
1593 
1594   return ret;
1595 }
1596 
1597 /**
1598   * @brief  USB_InitFSLSPClkSel : Initializes the FSLSPClkSel field of the
1599   *         HCFG register on the PHY type and set the right frame interval
1600   * @param  USBx  Selected device
1601   * @param  freq  clock frequency
1602   *          This parameter can be one of these values:
1603   *           HCFG_48_MHZ : Full Speed 48 MHz Clock
1604   *           HCFG_6_MHZ : Low Speed 6 MHz Clock
1605   * @retval HAL status
1606   */
USB_InitFSLSPClkSel(USB_OTG_GlobalTypeDef * USBx,uint8_t freq)1607 HAL_StatusTypeDef USB_InitFSLSPClkSel(USB_OTG_GlobalTypeDef *USBx, uint8_t freq)
1608 {
1609   uint32_t USBx_BASE = (uint32_t)USBx;
1610 
1611   USBx_HOST->HCFG &= ~(USB_OTG_HCFG_FSLSPCS);
1612   USBx_HOST->HCFG |= (uint32_t)freq & USB_OTG_HCFG_FSLSPCS;
1613 
1614   if (freq == HCFG_48_MHZ)
1615   {
1616     USBx_HOST->HFIR = 48000U;
1617   }
1618   else if (freq == HCFG_6_MHZ)
1619   {
1620     USBx_HOST->HFIR = 6000U;
1621   }
1622   else
1623   {
1624     /* ... */
1625   }
1626 
1627   return HAL_OK;
1628 }
1629 
1630 /**
1631   * @brief  USB_OTG_ResetPort : Reset Host Port
1632   * @param  USBx  Selected device
1633   * @retval HAL status
1634   * @note (1)The application must wait at least 10 ms
1635   *   before clearing the reset bit.
1636   */
USB_ResetPort(USB_OTG_GlobalTypeDef * USBx)1637 HAL_StatusTypeDef USB_ResetPort(USB_OTG_GlobalTypeDef *USBx)
1638 {
1639   uint32_t USBx_BASE = (uint32_t)USBx;
1640 
1641   __IO uint32_t hprt0 = 0U;
1642 
1643   hprt0 = USBx_HPRT0;
1644 
1645   hprt0 &= ~(USB_OTG_HPRT_PENA | USB_OTG_HPRT_PCDET |
1646              USB_OTG_HPRT_PENCHNG | USB_OTG_HPRT_POCCHNG);
1647 
1648   USBx_HPRT0 = (USB_OTG_HPRT_PRST | hprt0);
1649   HAL_Delay(100U);                                 /* See Note #1 */
1650   USBx_HPRT0 = ((~USB_OTG_HPRT_PRST) & hprt0);
1651   HAL_Delay(10U);
1652 
1653   return HAL_OK;
1654 }
1655 
1656 /**
1657   * @brief  USB_DriveVbus : activate or de-activate vbus
1658   * @param  state  VBUS state
1659   *          This parameter can be one of these values:
1660   *           0 : Deactivate VBUS
1661   *           1 : Activate VBUS
1662   * @retval HAL status
1663   */
USB_DriveVbus(USB_OTG_GlobalTypeDef * USBx,uint8_t state)1664 HAL_StatusTypeDef USB_DriveVbus(USB_OTG_GlobalTypeDef *USBx, uint8_t state)
1665 {
1666   uint32_t USBx_BASE = (uint32_t)USBx;
1667   __IO uint32_t hprt0 = 0U;
1668 
1669   hprt0 = USBx_HPRT0;
1670 
1671   hprt0 &= ~(USB_OTG_HPRT_PENA | USB_OTG_HPRT_PCDET |
1672              USB_OTG_HPRT_PENCHNG | USB_OTG_HPRT_POCCHNG);
1673 
1674   if (((hprt0 & USB_OTG_HPRT_PPWR) == 0U) && (state == 1U))
1675   {
1676     USBx_HPRT0 = (USB_OTG_HPRT_PPWR | hprt0);
1677   }
1678   if (((hprt0 & USB_OTG_HPRT_PPWR) == USB_OTG_HPRT_PPWR) && (state == 0U))
1679   {
1680     USBx_HPRT0 = ((~USB_OTG_HPRT_PPWR) & hprt0);
1681   }
1682   return HAL_OK;
1683 }
1684 
1685 /**
1686   * @brief  Return Host Core speed
1687   * @param  USBx  Selected device
1688   * @retval speed : Host speed
1689   *          This parameter can be one of these values:
1690   *            @arg HCD_SPEED_HIGH: High speed mode
1691   *            @arg HCD_SPEED_FULL: Full speed mode
1692   *            @arg HCD_SPEED_LOW: Low speed mode
1693   */
USB_GetHostSpeed(USB_OTG_GlobalTypeDef * USBx)1694 uint32_t USB_GetHostSpeed(USB_OTG_GlobalTypeDef *USBx)
1695 {
1696   uint32_t USBx_BASE = (uint32_t)USBx;
1697   __IO uint32_t hprt0 = 0U;
1698 
1699   hprt0 = USBx_HPRT0;
1700   return ((hprt0 & USB_OTG_HPRT_PSPD) >> 17);
1701 }
1702 
1703 /**
1704   * @brief  Return Host Current Frame number
1705   * @param  USBx  Selected device
1706   * @retval current frame number
1707   */
USB_GetCurrentFrame(USB_OTG_GlobalTypeDef * USBx)1708 uint32_t USB_GetCurrentFrame(USB_OTG_GlobalTypeDef *USBx)
1709 {
1710   uint32_t USBx_BASE = (uint32_t)USBx;
1711 
1712   return (USBx_HOST->HFNUM & USB_OTG_HFNUM_FRNUM);
1713 }
1714 
1715 /**
1716   * @brief  Initialize a host channel
1717   * @param  USBx  Selected device
1718   * @param  ch_num  Channel number
1719   *         This parameter can be a value from 1 to 15
1720   * @param  epnum  Endpoint number
1721   *          This parameter can be a value from 1 to 15
1722   * @param  dev_address  Current device address
1723   *          This parameter can be a value from 0 to 255
1724   * @param  speed  Current device speed
1725   *          This parameter can be one of these values:
1726   *            @arg USB_OTG_SPEED_HIGH: High speed mode
1727   *            @arg USB_OTG_SPEED_FULL: Full speed mode
1728   *            @arg USB_OTG_SPEED_LOW: Low speed mode
1729   * @param  ep_type  Endpoint Type
1730   *          This parameter can be one of these values:
1731   *            @arg EP_TYPE_CTRL: Control type
1732   *            @arg EP_TYPE_ISOC: Isochronous type
1733   *            @arg EP_TYPE_BULK: Bulk type
1734   *            @arg EP_TYPE_INTR: Interrupt type
1735   * @param  mps  Max Packet Size
1736   *          This parameter can be a value from 0 to 32K
1737   * @retval HAL state
1738   */
USB_HC_Init(USB_OTG_GlobalTypeDef * USBx,uint8_t ch_num,uint8_t epnum,uint8_t dev_address,uint8_t speed,uint8_t ep_type,uint16_t mps)1739 HAL_StatusTypeDef USB_HC_Init(USB_OTG_GlobalTypeDef *USBx, uint8_t ch_num,
1740                               uint8_t epnum, uint8_t dev_address, uint8_t speed,
1741                               uint8_t ep_type, uint16_t mps)
1742 {
1743   HAL_StatusTypeDef ret = HAL_OK;
1744   uint32_t USBx_BASE = (uint32_t)USBx;
1745   uint32_t HCcharEpDir;
1746   uint32_t HCcharLowSpeed;
1747   uint32_t HostCoreSpeed;
1748 
1749   /* Clear old interrupt conditions for this host channel. */
1750   USBx_HC((uint32_t)ch_num)->HCINT = 0xFFFFFFFFU;
1751 
1752   /* Enable channel interrupts required for this transfer. */
1753   switch (ep_type)
1754   {
1755     case EP_TYPE_CTRL:
1756     case EP_TYPE_BULK:
1757       USBx_HC((uint32_t)ch_num)->HCINTMSK = USB_OTG_HCINTMSK_XFRCM  |
1758                                             USB_OTG_HCINTMSK_STALLM |
1759                                             USB_OTG_HCINTMSK_TXERRM |
1760                                             USB_OTG_HCINTMSK_DTERRM |
1761                                             USB_OTG_HCINTMSK_AHBERR |
1762                                             USB_OTG_HCINTMSK_NAKM;
1763 
1764       if ((epnum & 0x80U) == 0x80U)
1765       {
1766         USBx_HC((uint32_t)ch_num)->HCINTMSK |= USB_OTG_HCINTMSK_BBERRM;
1767       }
1768       else
1769       {
1770         if ((USBx->CID & (0x1U << 8)) != 0U)
1771         {
1772           USBx_HC((uint32_t)ch_num)->HCINTMSK |= USB_OTG_HCINTMSK_NYET |
1773                                                  USB_OTG_HCINTMSK_ACKM;
1774         }
1775       }
1776       break;
1777 
1778     case EP_TYPE_INTR:
1779       USBx_HC((uint32_t)ch_num)->HCINTMSK = USB_OTG_HCINTMSK_XFRCM  |
1780                                             USB_OTG_HCINTMSK_STALLM |
1781                                             USB_OTG_HCINTMSK_TXERRM |
1782                                             USB_OTG_HCINTMSK_DTERRM |
1783                                             USB_OTG_HCINTMSK_NAKM   |
1784                                             USB_OTG_HCINTMSK_AHBERR |
1785                                             USB_OTG_HCINTMSK_FRMORM;
1786 
1787       if ((epnum & 0x80U) == 0x80U)
1788       {
1789         USBx_HC((uint32_t)ch_num)->HCINTMSK |= USB_OTG_HCINTMSK_BBERRM;
1790       }
1791 
1792       break;
1793 
1794     case EP_TYPE_ISOC:
1795       USBx_HC((uint32_t)ch_num)->HCINTMSK = USB_OTG_HCINTMSK_XFRCM  |
1796                                             USB_OTG_HCINTMSK_ACKM   |
1797                                             USB_OTG_HCINTMSK_AHBERR |
1798                                             USB_OTG_HCINTMSK_FRMORM;
1799 
1800       if ((epnum & 0x80U) == 0x80U)
1801       {
1802         USBx_HC((uint32_t)ch_num)->HCINTMSK |= (USB_OTG_HCINTMSK_TXERRM | USB_OTG_HCINTMSK_BBERRM);
1803       }
1804       break;
1805 
1806     default:
1807       ret = HAL_ERROR;
1808       break;
1809   }
1810 
1811   /* Enable host channel Halt interrupt */
1812   USBx_HC((uint32_t)ch_num)->HCINTMSK |= USB_OTG_HCINTMSK_CHHM;
1813 
1814   /* Enable the top level host channel interrupt. */
1815   USBx_HOST->HAINTMSK |= 1UL << (ch_num & 0xFU);
1816 
1817   /* Make sure host channel interrupts are enabled. */
1818   USBx->GINTMSK |= USB_OTG_GINTMSK_HCIM;
1819 
1820   /* Program the HCCHAR register */
1821   if ((epnum & 0x80U) == 0x80U)
1822   {
1823     HCcharEpDir = (0x1U << 15) & USB_OTG_HCCHAR_EPDIR;
1824   }
1825   else
1826   {
1827     HCcharEpDir = 0U;
1828   }
1829 
1830   HostCoreSpeed = USB_GetHostSpeed(USBx);
1831 
1832   /* LS device plugged to HUB */
1833   if ((speed == HPRT0_PRTSPD_LOW_SPEED) && (HostCoreSpeed != HPRT0_PRTSPD_LOW_SPEED))
1834   {
1835     HCcharLowSpeed = (0x1U << 17) & USB_OTG_HCCHAR_LSDEV;
1836   }
1837   else
1838   {
1839     HCcharLowSpeed = 0U;
1840   }
1841 
1842   USBx_HC((uint32_t)ch_num)->HCCHAR = (((uint32_t)dev_address << 22) & USB_OTG_HCCHAR_DAD) |
1843                                       ((((uint32_t)epnum & 0x7FU) << 11) & USB_OTG_HCCHAR_EPNUM) |
1844                                       (((uint32_t)ep_type << 18) & USB_OTG_HCCHAR_EPTYP) |
1845                                       ((uint32_t)mps & USB_OTG_HCCHAR_MPSIZ) | HCcharEpDir | HCcharLowSpeed;
1846 
1847   if ((ep_type == EP_TYPE_INTR) || (ep_type == EP_TYPE_ISOC))
1848   {
1849     USBx_HC((uint32_t)ch_num)->HCCHAR |= USB_OTG_HCCHAR_ODDFRM;
1850   }
1851 
1852   return ret;
1853 }
1854 
1855 /**
1856   * @brief  Start a transfer over a host channel
1857   * @param  USBx  Selected device
1858   * @param  hc  pointer to host channel structure
1859   * @param  dma USB dma enabled or disabled
1860   *          This parameter can be one of these values:
1861   *           0 : DMA feature not used
1862   *           1 : DMA feature used
1863   * @retval HAL state
1864   */
USB_HC_StartXfer(USB_OTG_GlobalTypeDef * USBx,USB_OTG_HCTypeDef * hc,uint8_t dma)1865 HAL_StatusTypeDef USB_HC_StartXfer(USB_OTG_GlobalTypeDef *USBx, USB_OTG_HCTypeDef *hc, uint8_t dma)
1866 {
1867   uint32_t USBx_BASE = (uint32_t)USBx;
1868   uint32_t ch_num = (uint32_t)hc->ch_num;
1869   __IO uint32_t tmpreg;
1870   uint8_t  is_oddframe;
1871   uint16_t len_words;
1872   uint16_t num_packets;
1873   uint16_t max_hc_pkt_count = 256U;
1874 
1875   if (((USBx->CID & (0x1U << 8)) != 0U) && (hc->speed == USBH_HS_SPEED))
1876   {
1877     /* in DMA mode host Core automatically issues ping  in case of NYET/NAK */
1878     if ((dma == 1U) && ((hc->ep_type == EP_TYPE_CTRL) || (hc->ep_type == EP_TYPE_BULK)))
1879     {
1880       USBx_HC((uint32_t)ch_num)->HCINTMSK &= ~(USB_OTG_HCINTMSK_NYET |
1881                                                USB_OTG_HCINTMSK_ACKM |
1882                                                USB_OTG_HCINTMSK_NAKM);
1883     }
1884 
1885     if ((dma == 0U) && (hc->do_ping == 1U))
1886     {
1887       (void)USB_DoPing(USBx, hc->ch_num);
1888       return HAL_OK;
1889     }
1890 
1891   }
1892 
1893   /* Compute the expected number of packets associated to the transfer */
1894   if (hc->xfer_len > 0U)
1895   {
1896     num_packets = (uint16_t)((hc->xfer_len + hc->max_packet - 1U) / hc->max_packet);
1897 
1898     if (num_packets > max_hc_pkt_count)
1899     {
1900       num_packets = max_hc_pkt_count;
1901       hc->XferSize = (uint32_t)num_packets * hc->max_packet;
1902     }
1903   }
1904   else
1905   {
1906     num_packets = 1U;
1907   }
1908 
1909   /*
1910    * For IN channel HCTSIZ.XferSize is expected to be an integer multiple of
1911    * max_packet size.
1912    */
1913   if (hc->ep_is_in != 0U)
1914   {
1915     hc->XferSize = (uint32_t)num_packets * hc->max_packet;
1916   }
1917   else
1918   {
1919     hc->XferSize = hc->xfer_len;
1920   }
1921 
1922   /* Initialize the HCTSIZn register */
1923   USBx_HC(ch_num)->HCTSIZ = (hc->XferSize & USB_OTG_HCTSIZ_XFRSIZ) |
1924                             (((uint32_t)num_packets << 19) & USB_OTG_HCTSIZ_PKTCNT) |
1925                             (((uint32_t)hc->data_pid << 29) & USB_OTG_HCTSIZ_DPID);
1926 
1927   if (dma != 0U)
1928   {
1929     /* xfer_buff MUST be 32-bits aligned */
1930     USBx_HC(ch_num)->HCDMA = (uint32_t)hc->xfer_buff;
1931   }
1932 
1933   is_oddframe = (((uint32_t)USBx_HOST->HFNUM & 0x01U) != 0U) ? 0U : 1U;
1934   USBx_HC(ch_num)->HCCHAR &= ~USB_OTG_HCCHAR_ODDFRM;
1935   USBx_HC(ch_num)->HCCHAR |= (uint32_t)is_oddframe << 29;
1936 
1937   /* Set host channel enable */
1938   tmpreg = USBx_HC(ch_num)->HCCHAR;
1939   tmpreg &= ~USB_OTG_HCCHAR_CHDIS;
1940 
1941   /* make sure to set the correct ep direction */
1942   if (hc->ep_is_in != 0U)
1943   {
1944     tmpreg |= USB_OTG_HCCHAR_EPDIR;
1945   }
1946   else
1947   {
1948     tmpreg &= ~USB_OTG_HCCHAR_EPDIR;
1949   }
1950   tmpreg |= USB_OTG_HCCHAR_CHENA;
1951   USBx_HC(ch_num)->HCCHAR = tmpreg;
1952 
1953   if (dma != 0U) /* dma mode */
1954   {
1955     return HAL_OK;
1956   }
1957 
1958   if ((hc->ep_is_in == 0U) && (hc->xfer_len > 0U))
1959   {
1960     switch (hc->ep_type)
1961     {
1962       /* Non periodic transfer */
1963       case EP_TYPE_CTRL:
1964       case EP_TYPE_BULK:
1965 
1966         len_words = (uint16_t)((hc->xfer_len + 3U) / 4U);
1967 
1968         /* check if there is enough space in FIFO space */
1969         if (len_words > (USBx->HNPTXSTS & 0xFFFFU))
1970         {
1971           /* need to process data in nptxfempty interrupt */
1972           USBx->GINTMSK |= USB_OTG_GINTMSK_NPTXFEM;
1973         }
1974         break;
1975 
1976       /* Periodic transfer */
1977       case EP_TYPE_INTR:
1978       case EP_TYPE_ISOC:
1979         len_words = (uint16_t)((hc->xfer_len + 3U) / 4U);
1980         /* check if there is enough space in FIFO space */
1981         if (len_words > (USBx_HOST->HPTXSTS & 0xFFFFU)) /* split the transfer */
1982         {
1983           /* need to process data in ptxfempty interrupt */
1984           USBx->GINTMSK |= USB_OTG_GINTMSK_PTXFEM;
1985         }
1986         break;
1987 
1988       default:
1989         break;
1990     }
1991 
1992     /* Write packet into the Tx FIFO. */
1993     (void)USB_WritePacket(USBx, hc->xfer_buff, hc->ch_num, (uint16_t)hc->xfer_len, 0);
1994   }
1995 
1996   return HAL_OK;
1997 }
1998 
1999 /**
2000   * @brief Read all host channel interrupts status
2001   * @param  USBx  Selected device
2002   * @retval HAL state
2003   */
USB_HC_ReadInterrupt(USB_OTG_GlobalTypeDef * USBx)2004 uint32_t USB_HC_ReadInterrupt(USB_OTG_GlobalTypeDef *USBx)
2005 {
2006   uint32_t USBx_BASE = (uint32_t)USBx;
2007 
2008   return ((USBx_HOST->HAINT) & 0xFFFFU);
2009 }
2010 
2011 /**
2012   * @brief  Halt a host channel
2013   * @param  USBx  Selected device
2014   * @param  hc_num  Host Channel number
2015   *         This parameter can be a value from 1 to 15
2016   * @retval HAL state
2017   */
USB_HC_Halt(USB_OTG_GlobalTypeDef * USBx,uint8_t hc_num)2018 HAL_StatusTypeDef USB_HC_Halt(USB_OTG_GlobalTypeDef *USBx, uint8_t hc_num)
2019 {
2020   uint32_t USBx_BASE = (uint32_t)USBx;
2021   uint32_t hcnum = (uint32_t)hc_num;
2022   __IO uint32_t count = 0U;
2023   uint32_t HcEpType = (USBx_HC(hcnum)->HCCHAR & USB_OTG_HCCHAR_EPTYP) >> 18;
2024   uint32_t ChannelEna = (USBx_HC(hcnum)->HCCHAR & USB_OTG_HCCHAR_CHENA) >> 31;
2025 
2026   if (((USBx->GAHBCFG & USB_OTG_GAHBCFG_DMAEN) == USB_OTG_GAHBCFG_DMAEN) &&
2027       (ChannelEna == 0U))
2028   {
2029     return HAL_OK;
2030   }
2031 
2032   /* Check for space in the request queue to issue the halt. */
2033   if ((HcEpType == HCCHAR_CTRL) || (HcEpType == HCCHAR_BULK))
2034   {
2035     USBx_HC(hcnum)->HCCHAR |= USB_OTG_HCCHAR_CHDIS;
2036 
2037     if ((USBx->GAHBCFG & USB_OTG_GAHBCFG_DMAEN) == 0U)
2038     {
2039       if ((USBx->HNPTXSTS & (0xFFU << 16)) == 0U)
2040       {
2041         USBx_HC(hcnum)->HCCHAR &= ~USB_OTG_HCCHAR_CHENA;
2042         USBx_HC(hcnum)->HCCHAR |= USB_OTG_HCCHAR_CHENA;
2043         do
2044         {
2045           count++;
2046 
2047           if (count > 1000U)
2048           {
2049             break;
2050           }
2051         } while ((USBx_HC(hcnum)->HCCHAR & USB_OTG_HCCHAR_CHENA) == USB_OTG_HCCHAR_CHENA);
2052       }
2053       else
2054       {
2055         USBx_HC(hcnum)->HCCHAR |= USB_OTG_HCCHAR_CHENA;
2056       }
2057     }
2058   }
2059   else
2060   {
2061     USBx_HC(hcnum)->HCCHAR |= USB_OTG_HCCHAR_CHDIS;
2062 
2063     if ((USBx_HOST->HPTXSTS & (0xFFU << 16)) == 0U)
2064     {
2065       USBx_HC(hcnum)->HCCHAR &= ~USB_OTG_HCCHAR_CHENA;
2066       USBx_HC(hcnum)->HCCHAR |= USB_OTG_HCCHAR_CHENA;
2067       do
2068       {
2069         count++;
2070 
2071         if (count > 1000U)
2072         {
2073           break;
2074         }
2075       } while ((USBx_HC(hcnum)->HCCHAR & USB_OTG_HCCHAR_CHENA) == USB_OTG_HCCHAR_CHENA);
2076     }
2077     else
2078     {
2079       USBx_HC(hcnum)->HCCHAR |= USB_OTG_HCCHAR_CHENA;
2080     }
2081   }
2082 
2083   return HAL_OK;
2084 }
2085 
2086 /**
2087   * @brief  Initiate Do Ping protocol
2088   * @param  USBx  Selected device
2089   * @param  hc_num  Host Channel number
2090   *         This parameter can be a value from 1 to 15
2091   * @retval HAL state
2092   */
USB_DoPing(USB_OTG_GlobalTypeDef * USBx,uint8_t ch_num)2093 HAL_StatusTypeDef USB_DoPing(USB_OTG_GlobalTypeDef *USBx, uint8_t ch_num)
2094 {
2095   uint32_t USBx_BASE = (uint32_t)USBx;
2096   uint32_t chnum = (uint32_t)ch_num;
2097   uint32_t num_packets = 1U;
2098   uint32_t tmpreg;
2099 
2100   USBx_HC(chnum)->HCTSIZ = ((num_packets << 19) & USB_OTG_HCTSIZ_PKTCNT) |
2101                            USB_OTG_HCTSIZ_DOPING;
2102 
2103   /* Set host channel enable */
2104   tmpreg = USBx_HC(chnum)->HCCHAR;
2105   tmpreg &= ~USB_OTG_HCCHAR_CHDIS;
2106   tmpreg |= USB_OTG_HCCHAR_CHENA;
2107   USBx_HC(chnum)->HCCHAR = tmpreg;
2108 
2109   return HAL_OK;
2110 }
2111 
2112 /**
2113   * @brief  Stop Host Core
2114   * @param  USBx  Selected device
2115   * @retval HAL state
2116   */
USB_StopHost(USB_OTG_GlobalTypeDef * USBx)2117 HAL_StatusTypeDef USB_StopHost(USB_OTG_GlobalTypeDef *USBx)
2118 {
2119   HAL_StatusTypeDef ret = HAL_OK;
2120   uint32_t USBx_BASE = (uint32_t)USBx;
2121   __IO uint32_t count = 0U;
2122   uint32_t value;
2123   uint32_t i;
2124 
2125   (void)USB_DisableGlobalInt(USBx);
2126 
2127   /* Flush USB FIFO */
2128   if (USB_FlushTxFifo(USBx, 0x10U) != HAL_OK) /* all Tx FIFOs */
2129   {
2130     ret = HAL_ERROR;
2131   }
2132 
2133   if (USB_FlushRxFifo(USBx) != HAL_OK)
2134   {
2135     ret = HAL_ERROR;
2136   }
2137 
2138   /* Flush out any leftover queued requests. */
2139   for (i = 0U; i <= 15U; i++)
2140   {
2141     value = USBx_HC(i)->HCCHAR;
2142     value |=  USB_OTG_HCCHAR_CHDIS;
2143     value &= ~USB_OTG_HCCHAR_CHENA;
2144     value &= ~USB_OTG_HCCHAR_EPDIR;
2145     USBx_HC(i)->HCCHAR = value;
2146   }
2147 
2148   /* Halt all channels to put them into a known state. */
2149   for (i = 0U; i <= 15U; i++)
2150   {
2151     value = USBx_HC(i)->HCCHAR;
2152     value |= USB_OTG_HCCHAR_CHDIS;
2153     value |= USB_OTG_HCCHAR_CHENA;
2154     value &= ~USB_OTG_HCCHAR_EPDIR;
2155     USBx_HC(i)->HCCHAR = value;
2156 
2157     do
2158     {
2159       count++;
2160 
2161       if (count > 1000U)
2162       {
2163         break;
2164       }
2165     } while ((USBx_HC(i)->HCCHAR & USB_OTG_HCCHAR_CHENA) == USB_OTG_HCCHAR_CHENA);
2166   }
2167 
2168   /* Clear any pending Host interrupts */
2169   USBx_HOST->HAINT = 0xFFFFFFFFU;
2170   USBx->GINTSTS = 0xFFFFFFFFU;
2171 
2172   (void)USB_EnableGlobalInt(USBx);
2173 
2174   return ret;
2175 }
2176 
2177 /**
2178   * @brief  USB_ActivateRemoteWakeup active remote wakeup signalling
2179   * @param  USBx Selected device
2180   * @retval HAL status
2181   */
USB_ActivateRemoteWakeup(USB_OTG_GlobalTypeDef * USBx)2182 HAL_StatusTypeDef USB_ActivateRemoteWakeup(USB_OTG_GlobalTypeDef *USBx)
2183 {
2184   uint32_t USBx_BASE = (uint32_t)USBx;
2185 
2186   if ((USBx_DEVICE->DSTS & USB_OTG_DSTS_SUSPSTS) == USB_OTG_DSTS_SUSPSTS)
2187   {
2188     /* active Remote wakeup signalling */
2189     USBx_DEVICE->DCTL |= USB_OTG_DCTL_RWUSIG;
2190   }
2191 
2192   return HAL_OK;
2193 }
2194 
2195 /**
2196   * @brief  USB_DeActivateRemoteWakeup de-active remote wakeup signalling
2197   * @param  USBx Selected device
2198   * @retval HAL status
2199   */
USB_DeActivateRemoteWakeup(USB_OTG_GlobalTypeDef * USBx)2200 HAL_StatusTypeDef USB_DeActivateRemoteWakeup(USB_OTG_GlobalTypeDef *USBx)
2201 {
2202   uint32_t USBx_BASE = (uint32_t)USBx;
2203 
2204   /* active Remote wakeup signalling */
2205   USBx_DEVICE->DCTL &= ~(USB_OTG_DCTL_RWUSIG);
2206 
2207   return HAL_OK;
2208 }
2209 #endif /* defined (USB_OTG_FS) || defined (USB_OTG_HS) */
2210 
2211 
2212 /**
2213   * @}
2214   */
2215 
2216 /**
2217   * @}
2218   */
2219 #endif /* defined (USB_OTG_FS) || defined (USB_OTG_HS) */
2220 #endif /* defined (HAL_PCD_MODULE_ENABLED) || defined (HAL_HCD_MODULE_ENABLED) */
2221 
2222 /**
2223   * @}
2224   */
2225