• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2   ******************************************************************************
3   * @file    stm32f4xx_hal_hcd.c
4   * @author  MCD Application Team
5   * @brief   HCD HAL module driver.
6   *          This file provides firmware functions to manage the following
7   *          functionalities of the USB Peripheral Controller:
8   *           + Initialization and de-initialization functions
9   *           + IO operation functions
10   *           + Peripheral Control functions
11   *           + Peripheral State functions
12   *
13   @verbatim
14   ==============================================================================
15                     ##### How to use this driver #####
16   ==============================================================================
17   [..]
18     (#)Declare a HCD_HandleTypeDef handle structure, for example:
19        HCD_HandleTypeDef  hhcd;
20 
21     (#)Fill parameters of Init structure in HCD handle
22 
23     (#)Call HAL_HCD_Init() API to initialize the HCD peripheral (Core, Host core, ...)
24 
25     (#)Initialize the HCD low level resources through the HAL_HCD_MspInit() API:
26         (##) Enable the HCD/USB Low Level interface clock using the following macros
27              (+++) __HAL_RCC_USB_OTG_FS_CLK_ENABLE();
28              (+++) __HAL_RCC_USB_OTG_HS_CLK_ENABLE(); (For High Speed Mode)
29              (+++) __HAL_RCC_USB_OTG_HS_ULPI_CLK_ENABLE(); (For High Speed Mode)
30 
31         (##) Initialize the related GPIO clocks
32         (##) Configure HCD pin-out
33         (##) Configure HCD NVIC interrupt
34 
35     (#)Associate the Upper USB Host stack to the HAL HCD Driver:
36         (##) hhcd.pData = phost;
37 
38     (#)Enable HCD transmission and reception:
39         (##) HAL_HCD_Start();
40 
41   @endverbatim
42   ******************************************************************************
43   * @attention
44   *
45   * <h2><center>&copy; Copyright (c) 2016 STMicroelectronics.
46   * All rights reserved.</center></h2>
47   *
48   * This software component is licensed by ST under BSD 3-Clause license,
49   * the "License"; You may not use this file except in compliance with the
50   * License. You may obtain a copy of the License at:
51   *                        opensource.org/licenses/BSD-3-Clause
52   *
53   ******************************************************************************
54   */
55 
56 /* Includes ------------------------------------------------------------------*/
57 #include "stm32f4xx_hal.h"
58 
59 /** @addtogroup STM32F4xx_HAL_Driver
60   * @{
61   */
62 
63 #ifdef HAL_HCD_MODULE_ENABLED
64 #if defined (USB_OTG_FS) || defined (USB_OTG_HS)
65 
66 /** @defgroup HCD HCD
67   * @brief HCD HAL module driver
68   * @{
69   */
70 
71 /* Private typedef -----------------------------------------------------------*/
72 /* Private define ------------------------------------------------------------*/
73 /* Private macro -------------------------------------------------------------*/
74 /* Private variables ---------------------------------------------------------*/
75 /* Private function prototypes -----------------------------------------------*/
76 /** @defgroup HCD_Private_Functions HCD Private Functions
77   * @{
78   */
79 static void HCD_HC_IN_IRQHandler(HCD_HandleTypeDef *hhcd, uint8_t chnum);
80 static void HCD_HC_OUT_IRQHandler(HCD_HandleTypeDef *hhcd, uint8_t chnum);
81 static void HCD_RXQLVL_IRQHandler(HCD_HandleTypeDef *hhcd);
82 static void HCD_Port_IRQHandler(HCD_HandleTypeDef *hhcd);
83 /**
84   * @}
85   */
86 
87 /* Exported functions --------------------------------------------------------*/
88 /** @defgroup HCD_Exported_Functions HCD Exported Functions
89   * @{
90   */
91 
92 /** @defgroup HCD_Exported_Functions_Group1 Initialization and de-initialization functions
93   *  @brief    Initialization and Configuration functions
94   *
95 @verbatim
96  ===============================================================================
97           ##### Initialization and de-initialization functions #####
98  ===============================================================================
99     [..]  This section provides functions allowing to:
100 
101 @endverbatim
102   * @{
103   */
104 
105 /**
106   * @brief  Initialize the host driver.
107   * @param  hhcd HCD handle
108   * @retval HAL status
109   */
HAL_HCD_Init(HCD_HandleTypeDef * hhcd)110 HAL_StatusTypeDef HAL_HCD_Init(HCD_HandleTypeDef *hhcd)
111 {
112   USB_OTG_GlobalTypeDef *USBx;
113 
114   /* Check the HCD handle allocation */
115   if (hhcd == NULL)
116   {
117     return HAL_ERROR;
118   }
119 
120   /* Check the parameters */
121   assert_param(IS_HCD_ALL_INSTANCE(hhcd->Instance));
122 
123   USBx = hhcd->Instance;
124 
125   if (hhcd->State == HAL_HCD_STATE_RESET)
126   {
127     /* Allocate lock resource and initialize it */
128     hhcd->Lock = HAL_UNLOCKED;
129 
130 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
131     hhcd->SOFCallback = HAL_HCD_SOF_Callback;
132     hhcd->ConnectCallback = HAL_HCD_Connect_Callback;
133     hhcd->DisconnectCallback = HAL_HCD_Disconnect_Callback;
134     hhcd->PortEnabledCallback = HAL_HCD_PortEnabled_Callback;
135     hhcd->PortDisabledCallback = HAL_HCD_PortDisabled_Callback;
136     hhcd->HC_NotifyURBChangeCallback = HAL_HCD_HC_NotifyURBChange_Callback;
137 
138     if (hhcd->MspInitCallback == NULL)
139     {
140       hhcd->MspInitCallback = HAL_HCD_MspInit;
141     }
142 
143     /* Init the low level hardware */
144     hhcd->MspInitCallback(hhcd);
145 #else
146     /* Init the low level hardware : GPIO, CLOCK, NVIC... */
147     HAL_HCD_MspInit(hhcd);
148 #endif /* (USE_HAL_HCD_REGISTER_CALLBACKS) */
149   }
150 
151   hhcd->State = HAL_HCD_STATE_BUSY;
152 
153   /* Disable DMA mode for FS instance */
154   if ((USBx->CID & (0x1U << 8)) == 0U)
155   {
156     hhcd->Init.dma_enable = 0U;
157   }
158 
159   /* Disable the Interrupts */
160   __HAL_HCD_DISABLE(hhcd);
161 
162   /* Init the Core (common init.) */
163   (void)USB_CoreInit(hhcd->Instance, hhcd->Init);
164 
165   /* Force Host Mode*/
166   (void)USB_SetCurrentMode(hhcd->Instance, USB_HOST_MODE);
167 
168   /* Init Host */
169   (void)USB_HostInit(hhcd->Instance, hhcd->Init);
170 
171   hhcd->State = HAL_HCD_STATE_READY;
172 
173   return HAL_OK;
174 }
175 
176 /**
177   * @brief  Initialize a host channel.
178   * @param  hhcd HCD handle
179   * @param  ch_num Channel number.
180   *         This parameter can be a value from 1 to 15
181   * @param  epnum Endpoint number.
182   *          This parameter can be a value from 1 to 15
183   * @param  dev_address Current device address
184   *          This parameter can be a value from 0 to 255
185   * @param  speed Current device speed.
186   *          This parameter can be one of these values:
187   *            HCD_DEVICE_SPEED_HIGH: High speed mode,
188   *            HCD_DEVICE_SPEED_FULL: Full speed mode,
189   *            HCD_DEVICE_SPEED_LOW: Low speed mode
190   * @param  ep_type Endpoint Type.
191   *          This parameter can be one of these values:
192   *            EP_TYPE_CTRL: Control type,
193   *            EP_TYPE_ISOC: Isochronous type,
194   *            EP_TYPE_BULK: Bulk type,
195   *            EP_TYPE_INTR: Interrupt type
196   * @param  mps Max Packet Size.
197   *          This parameter can be a value from 0 to32K
198   * @retval HAL status
199   */
HAL_HCD_HC_Init(HCD_HandleTypeDef * hhcd,uint8_t ch_num,uint8_t epnum,uint8_t dev_address,uint8_t speed,uint8_t ep_type,uint16_t mps)200 HAL_StatusTypeDef HAL_HCD_HC_Init(HCD_HandleTypeDef *hhcd,
201                                   uint8_t ch_num,
202                                   uint8_t epnum,
203                                   uint8_t dev_address,
204                                   uint8_t speed,
205                                   uint8_t ep_type,
206                                   uint16_t mps)
207 {
208   HAL_StatusTypeDef status;
209 
210   __HAL_LOCK(hhcd);
211   hhcd->hc[ch_num].do_ping = 0U;
212   hhcd->hc[ch_num].dev_addr = dev_address;
213   hhcd->hc[ch_num].max_packet = mps;
214   hhcd->hc[ch_num].ch_num = ch_num;
215   hhcd->hc[ch_num].ep_type = ep_type;
216   hhcd->hc[ch_num].ep_num = epnum & 0x7FU;
217 
218   if ((epnum & 0x80U) == 0x80U)
219   {
220     hhcd->hc[ch_num].ep_is_in = 1U;
221   }
222   else
223   {
224     hhcd->hc[ch_num].ep_is_in = 0U;
225   }
226 
227   hhcd->hc[ch_num].speed = speed;
228 
229   status =  USB_HC_Init(hhcd->Instance,
230                         ch_num,
231                         epnum,
232                         dev_address,
233                         speed,
234                         ep_type,
235                         mps);
236   __HAL_UNLOCK(hhcd);
237 
238   return status;
239 }
240 
241 /**
242   * @brief  Halt a host channel.
243   * @param  hhcd HCD handle
244   * @param  ch_num Channel number.
245   *         This parameter can be a value from 1 to 15
246   * @retval HAL status
247   */
HAL_HCD_HC_Halt(HCD_HandleTypeDef * hhcd,uint8_t ch_num)248 HAL_StatusTypeDef HAL_HCD_HC_Halt(HCD_HandleTypeDef *hhcd, uint8_t ch_num)
249 {
250   HAL_StatusTypeDef status = HAL_OK;
251 
252   __HAL_LOCK(hhcd);
253   (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
254   __HAL_UNLOCK(hhcd);
255 
256   return status;
257 }
258 
259 /**
260   * @brief  DeInitialize the host driver.
261   * @param  hhcd HCD handle
262   * @retval HAL status
263   */
HAL_HCD_DeInit(HCD_HandleTypeDef * hhcd)264 HAL_StatusTypeDef HAL_HCD_DeInit(HCD_HandleTypeDef *hhcd)
265 {
266   /* Check the HCD handle allocation */
267   if (hhcd == NULL)
268   {
269     return HAL_ERROR;
270   }
271 
272   hhcd->State = HAL_HCD_STATE_BUSY;
273 
274 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
275   if (hhcd->MspDeInitCallback == NULL)
276   {
277     hhcd->MspDeInitCallback = HAL_HCD_MspDeInit; /* Legacy weak MspDeInit  */
278   }
279 
280   /* DeInit the low level hardware */
281   hhcd->MspDeInitCallback(hhcd);
282 #else
283   /* DeInit the low level hardware: CLOCK, NVIC.*/
284   HAL_HCD_MspDeInit(hhcd);
285 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
286 
287   __HAL_HCD_DISABLE(hhcd);
288 
289   hhcd->State = HAL_HCD_STATE_RESET;
290 
291   return HAL_OK;
292 }
293 
294 /**
295   * @brief  Initialize the HCD MSP.
296   * @param  hhcd HCD handle
297   * @retval None
298   */
HAL_HCD_MspInit(HCD_HandleTypeDef * hhcd)299 __weak void  HAL_HCD_MspInit(HCD_HandleTypeDef *hhcd)
300 {
301   /* Prevent unused argument(s) compilation warning */
302   UNUSED(hhcd);
303 
304   /* NOTE : This function should not be modified, when the callback is needed,
305             the HAL_HCD_MspInit could be implemented in the user file
306    */
307 }
308 
309 /**
310   * @brief  DeInitialize the HCD MSP.
311   * @param  hhcd HCD handle
312   * @retval None
313   */
HAL_HCD_MspDeInit(HCD_HandleTypeDef * hhcd)314 __weak void  HAL_HCD_MspDeInit(HCD_HandleTypeDef *hhcd)
315 {
316   /* Prevent unused argument(s) compilation warning */
317   UNUSED(hhcd);
318 
319   /* NOTE : This function should not be modified, when the callback is needed,
320             the HAL_HCD_MspDeInit could be implemented in the user file
321    */
322 }
323 
324 /**
325   * @}
326   */
327 
328 /** @defgroup HCD_Exported_Functions_Group2 Input and Output operation functions
329   *  @brief   HCD IO operation functions
330   *
331 @verbatim
332  ===============================================================================
333                       ##### IO operation functions #####
334  ===============================================================================
335  [..] This subsection provides a set of functions allowing to manage the USB Host Data
336     Transfer
337 
338 @endverbatim
339   * @{
340   */
341 
342 /**
343   * @brief  Submit a new URB for processing.
344   * @param  hhcd HCD handle
345   * @param  ch_num Channel number.
346   *         This parameter can be a value from 1 to 15
347   * @param  direction Channel number.
348   *          This parameter can be one of these values:
349   *           0 : Output / 1 : Input
350   * @param  ep_type Endpoint Type.
351   *          This parameter can be one of these values:
352   *            EP_TYPE_CTRL: Control type/
353   *            EP_TYPE_ISOC: Isochronous type/
354   *            EP_TYPE_BULK: Bulk type/
355   *            EP_TYPE_INTR: Interrupt type/
356   * @param  token Endpoint Type.
357   *          This parameter can be one of these values:
358   *            0: HC_PID_SETUP / 1: HC_PID_DATA1
359   * @param  pbuff pointer to URB data
360   * @param  length Length of URB data
361   * @param  do_ping activate do ping protocol (for high speed only).
362   *          This parameter can be one of these values:
363   *           0 : do ping inactive / 1 : do ping active
364   * @retval HAL status
365   */
HAL_HCD_HC_SubmitRequest(HCD_HandleTypeDef * hhcd,uint8_t ch_num,uint8_t direction,uint8_t ep_type,uint8_t token,uint8_t * pbuff,uint16_t length,uint8_t do_ping)366 HAL_StatusTypeDef HAL_HCD_HC_SubmitRequest(HCD_HandleTypeDef *hhcd,
367                                            uint8_t ch_num,
368                                            uint8_t direction,
369                                            uint8_t ep_type,
370                                            uint8_t token,
371                                            uint8_t *pbuff,
372                                            uint16_t length,
373                                            uint8_t do_ping)
374 {
375   hhcd->hc[ch_num].ep_is_in = direction;
376   hhcd->hc[ch_num].ep_type  = ep_type;
377 
378   if (token == 0U)
379   {
380     hhcd->hc[ch_num].data_pid = HC_PID_SETUP;
381     hhcd->hc[ch_num].do_ping = do_ping;
382   }
383   else
384   {
385     hhcd->hc[ch_num].data_pid = HC_PID_DATA1;
386   }
387 
388   /* Manage Data Toggle */
389   switch (ep_type)
390   {
391     case EP_TYPE_CTRL:
392       if ((token == 1U) && (direction == 0U)) /*send data */
393       {
394         if (length == 0U)
395         {
396           /* For Status OUT stage, Length==0, Status Out PID = 1 */
397           hhcd->hc[ch_num].toggle_out = 1U;
398         }
399 
400         /* Set the Data Toggle bit as per the Flag */
401         if (hhcd->hc[ch_num].toggle_out == 0U)
402         {
403           /* Put the PID 0 */
404           hhcd->hc[ch_num].data_pid = HC_PID_DATA0;
405         }
406         else
407         {
408           /* Put the PID 1 */
409           hhcd->hc[ch_num].data_pid = HC_PID_DATA1;
410         }
411       }
412       break;
413 
414     case EP_TYPE_BULK:
415       if (direction == 0U)
416       {
417         /* Set the Data Toggle bit as per the Flag */
418         if (hhcd->hc[ch_num].toggle_out == 0U)
419         {
420           /* Put the PID 0 */
421           hhcd->hc[ch_num].data_pid = HC_PID_DATA0;
422         }
423         else
424         {
425           /* Put the PID 1 */
426           hhcd->hc[ch_num].data_pid = HC_PID_DATA1;
427         }
428       }
429       else
430       {
431         if (hhcd->hc[ch_num].toggle_in == 0U)
432         {
433           hhcd->hc[ch_num].data_pid = HC_PID_DATA0;
434         }
435         else
436         {
437           hhcd->hc[ch_num].data_pid = HC_PID_DATA1;
438         }
439       }
440 
441       break;
442     case EP_TYPE_INTR:
443       if (direction == 0U)
444       {
445         /* Set the Data Toggle bit as per the Flag */
446         if (hhcd->hc[ch_num].toggle_out == 0U)
447         {
448           /* Put the PID 0 */
449           hhcd->hc[ch_num].data_pid = HC_PID_DATA0;
450         }
451         else
452         {
453           /* Put the PID 1 */
454           hhcd->hc[ch_num].data_pid = HC_PID_DATA1;
455         }
456       }
457       else
458       {
459         if (hhcd->hc[ch_num].toggle_in == 0U)
460         {
461           hhcd->hc[ch_num].data_pid = HC_PID_DATA0;
462         }
463         else
464         {
465           hhcd->hc[ch_num].data_pid = HC_PID_DATA1;
466         }
467       }
468       break;
469 
470     case EP_TYPE_ISOC:
471       hhcd->hc[ch_num].data_pid = HC_PID_DATA0;
472       break;
473 
474     default:
475       break;
476   }
477 
478   hhcd->hc[ch_num].xfer_buff = pbuff;
479   hhcd->hc[ch_num].xfer_len  = length;
480   hhcd->hc[ch_num].urb_state = URB_IDLE;
481   hhcd->hc[ch_num].xfer_count = 0U;
482   hhcd->hc[ch_num].ch_num = ch_num;
483   hhcd->hc[ch_num].state = HC_IDLE;
484 
485   return USB_HC_StartXfer(hhcd->Instance, &hhcd->hc[ch_num], (uint8_t)hhcd->Init.dma_enable);
486 }
487 
488 /**
489   * @brief  Handle HCD interrupt request.
490   * @param  hhcd HCD handle
491   * @retval None
492   */
HAL_HCD_IRQHandler(HCD_HandleTypeDef * hhcd)493 void HAL_HCD_IRQHandler(HCD_HandleTypeDef *hhcd)
494 {
495   USB_OTG_GlobalTypeDef *USBx = hhcd->Instance;
496   uint32_t USBx_BASE = (uint32_t)USBx;
497   uint32_t i;
498   uint32_t interrupt;
499 
500   /* Ensure that we are in device mode */
501   if (USB_GetMode(hhcd->Instance) == USB_OTG_MODE_HOST)
502   {
503     /* Avoid spurious interrupt */
504     if (__HAL_HCD_IS_INVALID_INTERRUPT(hhcd))
505     {
506       return;
507     }
508 
509     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_PXFR_INCOMPISOOUT))
510     {
511       /* Incorrect mode, acknowledge the interrupt */
512       __HAL_HCD_CLEAR_FLAG(hhcd, USB_OTG_GINTSTS_PXFR_INCOMPISOOUT);
513     }
514 
515     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_IISOIXFR))
516     {
517       /* Incorrect mode, acknowledge the interrupt */
518       __HAL_HCD_CLEAR_FLAG(hhcd, USB_OTG_GINTSTS_IISOIXFR);
519     }
520 
521     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_PTXFE))
522     {
523       /* Incorrect mode, acknowledge the interrupt */
524       __HAL_HCD_CLEAR_FLAG(hhcd, USB_OTG_GINTSTS_PTXFE);
525     }
526 
527     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_MMIS))
528     {
529       /* Incorrect mode, acknowledge the interrupt */
530       __HAL_HCD_CLEAR_FLAG(hhcd, USB_OTG_GINTSTS_MMIS);
531     }
532 
533     /* Handle Host Disconnect Interrupts */
534     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_DISCINT))
535     {
536       __HAL_HCD_CLEAR_FLAG(hhcd, USB_OTG_GINTSTS_DISCINT);
537 
538       if ((USBx_HPRT0 & USB_OTG_HPRT_PCSTS) == 0U)
539       {
540         /* Flush USB Fifo */
541         (void)USB_FlushTxFifo(USBx, 0x10U);
542         (void)USB_FlushRxFifo(USBx);
543 
544         /* Restore FS Clock */
545         (void)USB_InitFSLSPClkSel(hhcd->Instance, HCFG_48_MHZ);
546 
547         /* Handle Host Port Disconnect Interrupt */
548 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
549         hhcd->DisconnectCallback(hhcd);
550 #else
551         HAL_HCD_Disconnect_Callback(hhcd);
552 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
553       }
554     }
555 
556     /* Handle Host Port Interrupts */
557     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_HPRTINT))
558     {
559       HCD_Port_IRQHandler(hhcd);
560     }
561 
562     /* Handle Host SOF Interrupt */
563     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_SOF))
564     {
565 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
566       hhcd->SOFCallback(hhcd);
567 #else
568       HAL_HCD_SOF_Callback(hhcd);
569 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
570 
571       __HAL_HCD_CLEAR_FLAG(hhcd, USB_OTG_GINTSTS_SOF);
572     }
573 
574     /* Handle Rx Queue Level Interrupts */
575     if ((__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_RXFLVL)) != 0U)
576     {
577       USB_MASK_INTERRUPT(hhcd->Instance, USB_OTG_GINTSTS_RXFLVL);
578 
579       HCD_RXQLVL_IRQHandler(hhcd);
580 
581       USB_UNMASK_INTERRUPT(hhcd->Instance, USB_OTG_GINTSTS_RXFLVL);
582     }
583 
584     /* Handle Host channel Interrupt */
585     if (__HAL_HCD_GET_FLAG(hhcd, USB_OTG_GINTSTS_HCINT))
586     {
587       interrupt = USB_HC_ReadInterrupt(hhcd->Instance);
588       for (i = 0U; i < hhcd->Init.Host_channels; i++)
589       {
590         if ((interrupt & (1UL << (i & 0xFU))) != 0U)
591         {
592           if ((USBx_HC(i)->HCCHAR & USB_OTG_HCCHAR_EPDIR) == USB_OTG_HCCHAR_EPDIR)
593           {
594             HCD_HC_IN_IRQHandler(hhcd, (uint8_t)i);
595           }
596           else
597           {
598             HCD_HC_OUT_IRQHandler(hhcd, (uint8_t)i);
599           }
600         }
601       }
602       __HAL_HCD_CLEAR_FLAG(hhcd, USB_OTG_GINTSTS_HCINT);
603     }
604   }
605 }
606 
607 
608 /**
609   * @brief  Handles HCD Wakeup interrupt request.
610   * @param  hhcd HCD handle
611   * @retval HAL status
612   */
HAL_HCD_WKUP_IRQHandler(HCD_HandleTypeDef * hhcd)613 void HAL_HCD_WKUP_IRQHandler(HCD_HandleTypeDef *hhcd)
614 {
615   UNUSED(hhcd);
616 }
617 
618 
619 /**
620   * @brief  SOF callback.
621   * @param  hhcd HCD handle
622   * @retval None
623   */
HAL_HCD_SOF_Callback(HCD_HandleTypeDef * hhcd)624 __weak void HAL_HCD_SOF_Callback(HCD_HandleTypeDef *hhcd)
625 {
626   /* Prevent unused argument(s) compilation warning */
627   UNUSED(hhcd);
628 
629   /* NOTE : This function should not be modified, when the callback is needed,
630             the HAL_HCD_SOF_Callback could be implemented in the user file
631    */
632 }
633 
634 /**
635   * @brief Connection Event callback.
636   * @param  hhcd HCD handle
637   * @retval None
638   */
HAL_HCD_Connect_Callback(HCD_HandleTypeDef * hhcd)639 __weak void HAL_HCD_Connect_Callback(HCD_HandleTypeDef *hhcd)
640 {
641   /* Prevent unused argument(s) compilation warning */
642   UNUSED(hhcd);
643 
644   /* NOTE : This function should not be modified, when the callback is needed,
645             the HAL_HCD_Connect_Callback could be implemented in the user file
646    */
647 }
648 
649 /**
650   * @brief  Disconnection Event callback.
651   * @param  hhcd HCD handle
652   * @retval None
653   */
HAL_HCD_Disconnect_Callback(HCD_HandleTypeDef * hhcd)654 __weak void HAL_HCD_Disconnect_Callback(HCD_HandleTypeDef *hhcd)
655 {
656   /* Prevent unused argument(s) compilation warning */
657   UNUSED(hhcd);
658 
659   /* NOTE : This function should not be modified, when the callback is needed,
660             the HAL_HCD_Disconnect_Callback could be implemented in the user file
661    */
662 }
663 
664 /**
665   * @brief  Port Enabled  Event callback.
666   * @param  hhcd HCD handle
667   * @retval None
668   */
HAL_HCD_PortEnabled_Callback(HCD_HandleTypeDef * hhcd)669 __weak void HAL_HCD_PortEnabled_Callback(HCD_HandleTypeDef *hhcd)
670 {
671   /* Prevent unused argument(s) compilation warning */
672   UNUSED(hhcd);
673 
674   /* NOTE : This function should not be modified, when the callback is needed,
675             the HAL_HCD_Disconnect_Callback could be implemented in the user file
676    */
677 }
678 
679 /**
680   * @brief  Port Disabled  Event callback.
681   * @param  hhcd HCD handle
682   * @retval None
683   */
HAL_HCD_PortDisabled_Callback(HCD_HandleTypeDef * hhcd)684 __weak void HAL_HCD_PortDisabled_Callback(HCD_HandleTypeDef *hhcd)
685 {
686   /* Prevent unused argument(s) compilation warning */
687   UNUSED(hhcd);
688 
689   /* NOTE : This function should not be modified, when the callback is needed,
690             the HAL_HCD_Disconnect_Callback could be implemented in the user file
691    */
692 }
693 
694 /**
695   * @brief  Notify URB state change callback.
696   * @param  hhcd HCD handle
697   * @param  chnum Channel number.
698   *         This parameter can be a value from 1 to 15
699   * @param  urb_state:
700   *          This parameter can be one of these values:
701   *            URB_IDLE/
702   *            URB_DONE/
703   *            URB_NOTREADY/
704   *            URB_NYET/
705   *            URB_ERROR/
706   *            URB_STALL/
707   * @retval None
708   */
HAL_HCD_HC_NotifyURBChange_Callback(HCD_HandleTypeDef * hhcd,uint8_t chnum,HCD_URBStateTypeDef urb_state)709 __weak void HAL_HCD_HC_NotifyURBChange_Callback(HCD_HandleTypeDef *hhcd, uint8_t chnum, HCD_URBStateTypeDef urb_state)
710 {
711   /* Prevent unused argument(s) compilation warning */
712   UNUSED(hhcd);
713   UNUSED(chnum);
714   UNUSED(urb_state);
715 
716   /* NOTE : This function should not be modified, when the callback is needed,
717             the HAL_HCD_HC_NotifyURBChange_Callback could be implemented in the user file
718    */
719 }
720 
721 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
722 /**
723   * @brief  Register a User USB HCD Callback
724   *         To be used instead of the weak predefined callback
725   * @param  hhcd USB HCD handle
726   * @param  CallbackID ID of the callback to be registered
727   *         This parameter can be one of the following values:
728   *          @arg @ref HAL_HCD_SOF_CB_ID USB HCD SOF callback ID
729   *          @arg @ref HAL_HCD_CONNECT_CB_ID USB HCD Connect callback ID
730   *          @arg @ref HAL_HCD_DISCONNECT_CB_ID OTG HCD Disconnect callback ID
731   *          @arg @ref HAL_HCD_PORT_ENABLED_CB_ID USB HCD Port Enable callback ID
732   *          @arg @ref HAL_HCD_PORT_DISABLED_CB_ID USB HCD Port Disable callback ID
733   *          @arg @ref HAL_HCD_MSPINIT_CB_ID MspDeInit callback ID
734   *          @arg @ref HAL_HCD_MSPDEINIT_CB_ID MspDeInit callback ID
735   * @param  pCallback pointer to the Callback function
736   * @retval HAL status
737   */
HAL_HCD_RegisterCallback(HCD_HandleTypeDef * hhcd,HAL_HCD_CallbackIDTypeDef CallbackID,pHCD_CallbackTypeDef pCallback)738 HAL_StatusTypeDef HAL_HCD_RegisterCallback(HCD_HandleTypeDef *hhcd,
739                                            HAL_HCD_CallbackIDTypeDef CallbackID,
740                                            pHCD_CallbackTypeDef pCallback)
741 {
742   HAL_StatusTypeDef status = HAL_OK;
743 
744   if (pCallback == NULL)
745   {
746     /* Update the error code */
747     hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
748     return HAL_ERROR;
749   }
750   /* Process locked */
751   __HAL_LOCK(hhcd);
752 
753   if (hhcd->State == HAL_HCD_STATE_READY)
754   {
755     switch (CallbackID)
756     {
757       case HAL_HCD_SOF_CB_ID :
758         hhcd->SOFCallback = pCallback;
759         break;
760 
761       case HAL_HCD_CONNECT_CB_ID :
762         hhcd->ConnectCallback = pCallback;
763         break;
764 
765       case HAL_HCD_DISCONNECT_CB_ID :
766         hhcd->DisconnectCallback = pCallback;
767         break;
768 
769       case HAL_HCD_PORT_ENABLED_CB_ID :
770         hhcd->PortEnabledCallback = pCallback;
771         break;
772 
773       case HAL_HCD_PORT_DISABLED_CB_ID :
774         hhcd->PortDisabledCallback = pCallback;
775         break;
776 
777       case HAL_HCD_MSPINIT_CB_ID :
778         hhcd->MspInitCallback = pCallback;
779         break;
780 
781       case HAL_HCD_MSPDEINIT_CB_ID :
782         hhcd->MspDeInitCallback = pCallback;
783         break;
784 
785       default :
786         /* Update the error code */
787         hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
788         /* Return error status */
789         status =  HAL_ERROR;
790         break;
791     }
792   }
793   else if (hhcd->State == HAL_HCD_STATE_RESET)
794   {
795     switch (CallbackID)
796     {
797       case HAL_HCD_MSPINIT_CB_ID :
798         hhcd->MspInitCallback = pCallback;
799         break;
800 
801       case HAL_HCD_MSPDEINIT_CB_ID :
802         hhcd->MspDeInitCallback = pCallback;
803         break;
804 
805       default :
806         /* Update the error code */
807         hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
808         /* Return error status */
809         status =  HAL_ERROR;
810         break;
811     }
812   }
813   else
814   {
815     /* Update the error code */
816     hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
817     /* Return error status */
818     status =  HAL_ERROR;
819   }
820 
821   /* Release Lock */
822   __HAL_UNLOCK(hhcd);
823   return status;
824 }
825 
826 /**
827   * @brief  Unregister an USB HCD Callback
828   *         USB HCD callback is redirected to the weak predefined callback
829   * @param  hhcd USB HCD handle
830   * @param  CallbackID ID of the callback to be unregistered
831   *         This parameter can be one of the following values:
832   *          @arg @ref HAL_HCD_SOF_CB_ID USB HCD SOF callback ID
833   *          @arg @ref HAL_HCD_CONNECT_CB_ID USB HCD Connect callback ID
834   *          @arg @ref HAL_HCD_DISCONNECT_CB_ID OTG HCD Disconnect callback ID
835   *          @arg @ref HAL_HCD_PORT_ENABLED_CB_ID USB HCD Port Enabled callback ID
836   *          @arg @ref HAL_HCD_PORT_DISABLED_CB_ID USB HCD Port Disabled callback ID
837   *          @arg @ref HAL_HCD_MSPINIT_CB_ID MspDeInit callback ID
838   *          @arg @ref HAL_HCD_MSPDEINIT_CB_ID MspDeInit callback ID
839   * @retval HAL status
840   */
HAL_HCD_UnRegisterCallback(HCD_HandleTypeDef * hhcd,HAL_HCD_CallbackIDTypeDef CallbackID)841 HAL_StatusTypeDef HAL_HCD_UnRegisterCallback(HCD_HandleTypeDef *hhcd, HAL_HCD_CallbackIDTypeDef CallbackID)
842 {
843   HAL_StatusTypeDef status = HAL_OK;
844 
845   /* Process locked */
846   __HAL_LOCK(hhcd);
847 
848   /* Setup Legacy weak Callbacks  */
849   if (hhcd->State == HAL_HCD_STATE_READY)
850   {
851     switch (CallbackID)
852     {
853       case HAL_HCD_SOF_CB_ID :
854         hhcd->SOFCallback = HAL_HCD_SOF_Callback;
855         break;
856 
857       case HAL_HCD_CONNECT_CB_ID :
858         hhcd->ConnectCallback = HAL_HCD_Connect_Callback;
859         break;
860 
861       case HAL_HCD_DISCONNECT_CB_ID :
862         hhcd->DisconnectCallback = HAL_HCD_Disconnect_Callback;
863         break;
864 
865       case HAL_HCD_PORT_ENABLED_CB_ID :
866         hhcd->PortEnabledCallback = HAL_HCD_PortEnabled_Callback;
867         break;
868 
869       case HAL_HCD_PORT_DISABLED_CB_ID :
870         hhcd->PortDisabledCallback = HAL_HCD_PortDisabled_Callback;
871         break;
872 
873       case HAL_HCD_MSPINIT_CB_ID :
874         hhcd->MspInitCallback = HAL_HCD_MspInit;
875         break;
876 
877       case HAL_HCD_MSPDEINIT_CB_ID :
878         hhcd->MspDeInitCallback = HAL_HCD_MspDeInit;
879         break;
880 
881       default :
882         /* Update the error code */
883         hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
884 
885         /* Return error status */
886         status =  HAL_ERROR;
887         break;
888     }
889   }
890   else if (hhcd->State == HAL_HCD_STATE_RESET)
891   {
892     switch (CallbackID)
893     {
894       case HAL_HCD_MSPINIT_CB_ID :
895         hhcd->MspInitCallback = HAL_HCD_MspInit;
896         break;
897 
898       case HAL_HCD_MSPDEINIT_CB_ID :
899         hhcd->MspDeInitCallback = HAL_HCD_MspDeInit;
900         break;
901 
902       default :
903         /* Update the error code */
904         hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
905 
906         /* Return error status */
907         status =  HAL_ERROR;
908         break;
909     }
910   }
911   else
912   {
913     /* Update the error code */
914     hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
915 
916     /* Return error status */
917     status =  HAL_ERROR;
918   }
919 
920   /* Release Lock */
921   __HAL_UNLOCK(hhcd);
922   return status;
923 }
924 
925 /**
926   * @brief  Register USB HCD Host Channel Notify URB Change Callback
927   *         To be used instead of the weak HAL_HCD_HC_NotifyURBChange_Callback() predefined callback
928   * @param  hhcd HCD handle
929   * @param  pCallback pointer to the USB HCD Host Channel Notify URB Change Callback function
930   * @retval HAL status
931   */
HAL_HCD_RegisterHC_NotifyURBChangeCallback(HCD_HandleTypeDef * hhcd,pHCD_HC_NotifyURBChangeCallbackTypeDef pCallback)932 HAL_StatusTypeDef HAL_HCD_RegisterHC_NotifyURBChangeCallback(HCD_HandleTypeDef *hhcd,
933                                                              pHCD_HC_NotifyURBChangeCallbackTypeDef pCallback)
934 {
935   HAL_StatusTypeDef status = HAL_OK;
936 
937   if (pCallback == NULL)
938   {
939     /* Update the error code */
940     hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
941 
942     return HAL_ERROR;
943   }
944 
945   /* Process locked */
946   __HAL_LOCK(hhcd);
947 
948   if (hhcd->State == HAL_HCD_STATE_READY)
949   {
950     hhcd->HC_NotifyURBChangeCallback = pCallback;
951   }
952   else
953   {
954     /* Update the error code */
955     hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
956 
957     /* Return error status */
958     status =  HAL_ERROR;
959   }
960 
961   /* Release Lock */
962   __HAL_UNLOCK(hhcd);
963 
964   return status;
965 }
966 
967 /**
968   * @brief  Unregister the USB HCD Host Channel Notify URB Change Callback
969   *         USB HCD Host Channel Notify URB Change Callback is redirected
970   *         to the weak HAL_HCD_HC_NotifyURBChange_Callback() predefined callback
971   * @param  hhcd HCD handle
972   * @retval HAL status
973   */
HAL_HCD_UnRegisterHC_NotifyURBChangeCallback(HCD_HandleTypeDef * hhcd)974 HAL_StatusTypeDef HAL_HCD_UnRegisterHC_NotifyURBChangeCallback(HCD_HandleTypeDef *hhcd)
975 {
976   HAL_StatusTypeDef status = HAL_OK;
977 
978   /* Process locked */
979   __HAL_LOCK(hhcd);
980 
981   if (hhcd->State == HAL_HCD_STATE_READY)
982   {
983     hhcd->HC_NotifyURBChangeCallback = HAL_HCD_HC_NotifyURBChange_Callback; /* Legacy weak DataOutStageCallback  */
984   }
985   else
986   {
987     /* Update the error code */
988     hhcd->ErrorCode |= HAL_HCD_ERROR_INVALID_CALLBACK;
989 
990     /* Return error status */
991     status =  HAL_ERROR;
992   }
993 
994   /* Release Lock */
995   __HAL_UNLOCK(hhcd);
996 
997   return status;
998 }
999 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
1000 
1001 /**
1002   * @}
1003   */
1004 
1005 /** @defgroup HCD_Exported_Functions_Group3 Peripheral Control functions
1006   *  @brief   Management functions
1007   *
1008 @verbatim
1009  ===============================================================================
1010                       ##### Peripheral Control functions #####
1011  ===============================================================================
1012     [..]
1013     This subsection provides a set of functions allowing to control the HCD data
1014     transfers.
1015 
1016 @endverbatim
1017   * @{
1018   */
1019 
1020 /**
1021   * @brief  Start the host driver.
1022   * @param  hhcd HCD handle
1023   * @retval HAL status
1024   */
HAL_HCD_Start(HCD_HandleTypeDef * hhcd)1025 HAL_StatusTypeDef HAL_HCD_Start(HCD_HandleTypeDef *hhcd)
1026 {
1027   __HAL_LOCK(hhcd);
1028   /* Enable port power */
1029   (void)USB_DriveVbus(hhcd->Instance, 1U);
1030 
1031   /* Enable global interrupt */
1032   __HAL_HCD_ENABLE(hhcd);
1033   __HAL_UNLOCK(hhcd);
1034 
1035   return HAL_OK;
1036 }
1037 
1038 /**
1039   * @brief  Stop the host driver.
1040   * @param  hhcd HCD handle
1041   * @retval HAL status
1042   */
1043 
HAL_HCD_Stop(HCD_HandleTypeDef * hhcd)1044 HAL_StatusTypeDef HAL_HCD_Stop(HCD_HandleTypeDef *hhcd)
1045 {
1046   __HAL_LOCK(hhcd);
1047   (void)USB_StopHost(hhcd->Instance);
1048   __HAL_UNLOCK(hhcd);
1049 
1050   return HAL_OK;
1051 }
1052 
1053 /**
1054   * @brief  Reset the host port.
1055   * @param  hhcd HCD handle
1056   * @retval HAL status
1057   */
HAL_HCD_ResetPort(HCD_HandleTypeDef * hhcd)1058 HAL_StatusTypeDef HAL_HCD_ResetPort(HCD_HandleTypeDef *hhcd)
1059 {
1060   return (USB_ResetPort(hhcd->Instance));
1061 }
1062 
1063 /**
1064   * @}
1065   */
1066 
1067 /** @defgroup HCD_Exported_Functions_Group4 Peripheral State functions
1068   *  @brief   Peripheral State functions
1069   *
1070 @verbatim
1071  ===============================================================================
1072                       ##### Peripheral State functions #####
1073  ===============================================================================
1074     [..]
1075     This subsection permits to get in run-time the status of the peripheral
1076     and the data flow.
1077 
1078 @endverbatim
1079   * @{
1080   */
1081 
1082 /**
1083   * @brief  Return the HCD handle state.
1084   * @param  hhcd HCD handle
1085   * @retval HAL state
1086   */
HAL_HCD_GetState(HCD_HandleTypeDef * hhcd)1087 HCD_StateTypeDef HAL_HCD_GetState(HCD_HandleTypeDef *hhcd)
1088 {
1089   return hhcd->State;
1090 }
1091 
1092 /**
1093   * @brief  Return  URB state for a channel.
1094   * @param  hhcd HCD handle
1095   * @param  chnum Channel number.
1096   *         This parameter can be a value from 1 to 15
1097   * @retval URB state.
1098   *          This parameter can be one of these values:
1099   *            URB_IDLE/
1100   *            URB_DONE/
1101   *            URB_NOTREADY/
1102   *            URB_NYET/
1103   *            URB_ERROR/
1104   *            URB_STALL
1105   */
HAL_HCD_HC_GetURBState(HCD_HandleTypeDef * hhcd,uint8_t chnum)1106 HCD_URBStateTypeDef HAL_HCD_HC_GetURBState(HCD_HandleTypeDef *hhcd, uint8_t chnum)
1107 {
1108   return hhcd->hc[chnum].urb_state;
1109 }
1110 
1111 
1112 /**
1113   * @brief  Return the last host transfer size.
1114   * @param  hhcd HCD handle
1115   * @param  chnum Channel number.
1116   *         This parameter can be a value from 1 to 15
1117   * @retval last transfer size in byte
1118   */
HAL_HCD_HC_GetXferCount(HCD_HandleTypeDef * hhcd,uint8_t chnum)1119 uint32_t HAL_HCD_HC_GetXferCount(HCD_HandleTypeDef *hhcd, uint8_t chnum)
1120 {
1121   return hhcd->hc[chnum].xfer_count;
1122 }
1123 
1124 /**
1125   * @brief  Return the Host Channel state.
1126   * @param  hhcd HCD handle
1127   * @param  chnum Channel number.
1128   *         This parameter can be a value from 1 to 15
1129   * @retval Host channel state
1130   *          This parameter can be one of these values:
1131   *            HC_IDLE/
1132   *            HC_XFRC/
1133   *            HC_HALTED/
1134   *            HC_NYET/
1135   *            HC_NAK/
1136   *            HC_STALL/
1137   *            HC_XACTERR/
1138   *            HC_BBLERR/
1139   *            HC_DATATGLERR
1140   */
HAL_HCD_HC_GetState(HCD_HandleTypeDef * hhcd,uint8_t chnum)1141 HCD_HCStateTypeDef  HAL_HCD_HC_GetState(HCD_HandleTypeDef *hhcd, uint8_t chnum)
1142 {
1143   return hhcd->hc[chnum].state;
1144 }
1145 
1146 /**
1147   * @brief  Return the current Host frame number.
1148   * @param  hhcd HCD handle
1149   * @retval Current Host frame number
1150   */
HAL_HCD_GetCurrentFrame(HCD_HandleTypeDef * hhcd)1151 uint32_t HAL_HCD_GetCurrentFrame(HCD_HandleTypeDef *hhcd)
1152 {
1153   return (USB_GetCurrentFrame(hhcd->Instance));
1154 }
1155 
1156 /**
1157   * @brief  Return the Host enumeration speed.
1158   * @param  hhcd HCD handle
1159   * @retval Enumeration speed
1160   */
HAL_HCD_GetCurrentSpeed(HCD_HandleTypeDef * hhcd)1161 uint32_t HAL_HCD_GetCurrentSpeed(HCD_HandleTypeDef *hhcd)
1162 {
1163   return (USB_GetHostSpeed(hhcd->Instance));
1164 }
1165 
1166 /**
1167   * @}
1168   */
1169 
1170 /**
1171   * @}
1172   */
1173 
1174 /** @addtogroup HCD_Private_Functions
1175   * @{
1176   */
1177 /**
1178   * @brief  Handle Host Channel IN interrupt requests.
1179   * @param  hhcd HCD handle
1180   * @param  chnum Channel number.
1181   *         This parameter can be a value from 1 to 15
1182   * @retval none
1183   */
HCD_HC_IN_IRQHandler(HCD_HandleTypeDef * hhcd,uint8_t chnum)1184 static void HCD_HC_IN_IRQHandler(HCD_HandleTypeDef *hhcd, uint8_t chnum)
1185 {
1186   USB_OTG_GlobalTypeDef *USBx = hhcd->Instance;
1187   uint32_t USBx_BASE = (uint32_t)USBx;
1188   uint32_t ch_num = (uint32_t)chnum;
1189 
1190   uint32_t tmpreg;
1191 
1192   if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_AHBERR) == USB_OTG_HCINT_AHBERR)
1193   {
1194     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_AHBERR);
1195     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1196   }
1197   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_BBERR) == USB_OTG_HCINT_BBERR)
1198   {
1199     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_BBERR);
1200     hhcd->hc[ch_num].state = HC_BBLERR;
1201     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1202     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1203   }
1204   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_ACK) == USB_OTG_HCINT_ACK)
1205   {
1206     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_ACK);
1207   }
1208   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_STALL) == USB_OTG_HCINT_STALL)
1209   {
1210     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1211     hhcd->hc[ch_num].state = HC_STALL;
1212     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NAK);
1213     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_STALL);
1214     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1215   }
1216   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_DTERR) == USB_OTG_HCINT_DTERR)
1217   {
1218     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1219     hhcd->hc[ch_num].state = HC_DATATGLERR;
1220     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NAK);
1221     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_DTERR);
1222     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1223   }
1224   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_TXERR) == USB_OTG_HCINT_TXERR)
1225   {
1226     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1227     hhcd->hc[ch_num].state = HC_XACTERR;
1228     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1229     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_TXERR);
1230   }
1231   else
1232   {
1233     /* ... */
1234   }
1235 
1236   if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_FRMOR) == USB_OTG_HCINT_FRMOR)
1237   {
1238     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1239     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1240     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_FRMOR);
1241   }
1242   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_XFRC) == USB_OTG_HCINT_XFRC)
1243   {
1244     if (hhcd->Init.dma_enable != 0U)
1245     {
1246       hhcd->hc[ch_num].xfer_count = hhcd->hc[ch_num].XferSize - \
1247                                     (USBx_HC(ch_num)->HCTSIZ & USB_OTG_HCTSIZ_XFRSIZ);
1248     }
1249 
1250     hhcd->hc[ch_num].state = HC_XFRC;
1251     hhcd->hc[ch_num].ErrCnt = 0U;
1252     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_XFRC);
1253 
1254     if ((hhcd->hc[ch_num].ep_type == EP_TYPE_CTRL) ||
1255         (hhcd->hc[ch_num].ep_type == EP_TYPE_BULK))
1256     {
1257       __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1258       (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1259       __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NAK);
1260     }
1261     else if (hhcd->hc[ch_num].ep_type == EP_TYPE_INTR)
1262     {
1263       USBx_HC(ch_num)->HCCHAR |= USB_OTG_HCCHAR_ODDFRM;
1264       hhcd->hc[ch_num].urb_state = URB_DONE;
1265 
1266 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
1267       hhcd->HC_NotifyURBChangeCallback(hhcd, (uint8_t)ch_num, hhcd->hc[ch_num].urb_state);
1268 #else
1269       HAL_HCD_HC_NotifyURBChange_Callback(hhcd, (uint8_t)ch_num, hhcd->hc[ch_num].urb_state);
1270 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
1271     }
1272     else if (hhcd->hc[ch_num].ep_type == EP_TYPE_ISOC)
1273     {
1274       hhcd->hc[ch_num].urb_state = URB_DONE;
1275       hhcd->hc[ch_num].toggle_in ^= 1U;
1276 
1277 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
1278       hhcd->HC_NotifyURBChangeCallback(hhcd, (uint8_t)ch_num, hhcd->hc[ch_num].urb_state);
1279 #else
1280       HAL_HCD_HC_NotifyURBChange_Callback(hhcd, (uint8_t)ch_num, hhcd->hc[ch_num].urb_state);
1281 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
1282     }
1283     else
1284     {
1285       /* ... */
1286     }
1287 
1288     if (hhcd->Init.dma_enable == 1U)
1289     {
1290       if (((hhcd->hc[ch_num].XferSize / hhcd->hc[ch_num].max_packet) & 1U) != 0U)
1291       {
1292         hhcd->hc[ch_num].toggle_in ^= 1U;
1293       }
1294     }
1295     else
1296     {
1297       hhcd->hc[ch_num].toggle_in ^= 1U;
1298     }
1299   }
1300   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_CHH) == USB_OTG_HCINT_CHH)
1301   {
1302     __HAL_HCD_MASK_HALT_HC_INT(ch_num);
1303 
1304     if (hhcd->hc[ch_num].state == HC_XFRC)
1305     {
1306       hhcd->hc[ch_num].urb_state = URB_DONE;
1307     }
1308     else if (hhcd->hc[ch_num].state == HC_STALL)
1309     {
1310       hhcd->hc[ch_num].urb_state = URB_STALL;
1311     }
1312     else if ((hhcd->hc[ch_num].state == HC_XACTERR) ||
1313              (hhcd->hc[ch_num].state == HC_DATATGLERR))
1314     {
1315       hhcd->hc[ch_num].ErrCnt++;
1316       if (hhcd->hc[ch_num].ErrCnt > 2U)
1317       {
1318         hhcd->hc[ch_num].ErrCnt = 0U;
1319         hhcd->hc[ch_num].urb_state = URB_ERROR;
1320       }
1321       else
1322       {
1323         hhcd->hc[ch_num].urb_state = URB_NOTREADY;
1324 
1325         /* re-activate the channel */
1326         tmpreg = USBx_HC(ch_num)->HCCHAR;
1327         tmpreg &= ~USB_OTG_HCCHAR_CHDIS;
1328         tmpreg |= USB_OTG_HCCHAR_CHENA;
1329         USBx_HC(ch_num)->HCCHAR = tmpreg;
1330       }
1331     }
1332     else if (hhcd->hc[ch_num].state == HC_NAK)
1333     {
1334       hhcd->hc[ch_num].urb_state  = URB_NOTREADY;
1335 
1336       /* re-activate the channel */
1337       tmpreg = USBx_HC(ch_num)->HCCHAR;
1338       tmpreg &= ~USB_OTG_HCCHAR_CHDIS;
1339       tmpreg |= USB_OTG_HCCHAR_CHENA;
1340       USBx_HC(ch_num)->HCCHAR = tmpreg;
1341     }
1342     else if (hhcd->hc[ch_num].state == HC_BBLERR)
1343     {
1344       hhcd->hc[ch_num].ErrCnt++;
1345       hhcd->hc[ch_num].urb_state = URB_ERROR;
1346     }
1347     else
1348     {
1349       /* ... */
1350     }
1351     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_CHH);
1352     HAL_HCD_HC_NotifyURBChange_Callback(hhcd, (uint8_t)ch_num, hhcd->hc[ch_num].urb_state);
1353   }
1354   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_NAK) == USB_OTG_HCINT_NAK)
1355   {
1356     if (hhcd->hc[ch_num].ep_type == EP_TYPE_INTR)
1357     {
1358       hhcd->hc[ch_num].ErrCnt = 0U;
1359       __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1360       (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1361     }
1362     else if ((hhcd->hc[ch_num].ep_type == EP_TYPE_CTRL) ||
1363              (hhcd->hc[ch_num].ep_type == EP_TYPE_BULK))
1364     {
1365       hhcd->hc[ch_num].ErrCnt = 0U;
1366 
1367       if (hhcd->Init.dma_enable == 0U)
1368       {
1369         hhcd->hc[ch_num].state = HC_NAK;
1370         __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1371         (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1372       }
1373     }
1374     else
1375     {
1376       /* ... */
1377     }
1378     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NAK);
1379   }
1380   else
1381   {
1382     /* ... */
1383   }
1384 }
1385 
1386 /**
1387   * @brief  Handle Host Channel OUT interrupt requests.
1388   * @param  hhcd HCD handle
1389   * @param  chnum Channel number.
1390   *         This parameter can be a value from 1 to 15
1391   * @retval none
1392   */
HCD_HC_OUT_IRQHandler(HCD_HandleTypeDef * hhcd,uint8_t chnum)1393 static void HCD_HC_OUT_IRQHandler(HCD_HandleTypeDef *hhcd, uint8_t chnum)
1394 {
1395   USB_OTG_GlobalTypeDef *USBx = hhcd->Instance;
1396   uint32_t USBx_BASE = (uint32_t)USBx;
1397   uint32_t ch_num = (uint32_t)chnum;
1398   uint32_t tmpreg;
1399   uint32_t num_packets;
1400 
1401   if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_AHBERR) == USB_OTG_HCINT_AHBERR)
1402   {
1403     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_AHBERR);
1404     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1405   }
1406   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_ACK) == USB_OTG_HCINT_ACK)
1407   {
1408     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_ACK);
1409 
1410     if (hhcd->hc[ch_num].do_ping == 1U)
1411     {
1412       hhcd->hc[ch_num].do_ping = 0U;
1413       hhcd->hc[ch_num].urb_state  = URB_NOTREADY;
1414       __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1415       (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1416     }
1417   }
1418   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_FRMOR) == USB_OTG_HCINT_FRMOR)
1419   {
1420     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1421     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1422     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_FRMOR);
1423   }
1424   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_XFRC) == USB_OTG_HCINT_XFRC)
1425   {
1426     hhcd->hc[ch_num].ErrCnt = 0U;
1427 
1428     /* transaction completed with NYET state, update do ping state */
1429     if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_NYET) == USB_OTG_HCINT_NYET)
1430     {
1431       hhcd->hc[ch_num].do_ping = 1U;
1432       __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NYET);
1433     }
1434     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1435     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1436     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_XFRC);
1437     hhcd->hc[ch_num].state = HC_XFRC;
1438   }
1439   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_NYET) == USB_OTG_HCINT_NYET)
1440   {
1441     hhcd->hc[ch_num].state = HC_NYET;
1442     hhcd->hc[ch_num].do_ping = 1U;
1443     hhcd->hc[ch_num].ErrCnt = 0U;
1444     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1445     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1446     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NYET);
1447   }
1448   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_STALL) == USB_OTG_HCINT_STALL)
1449   {
1450     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_STALL);
1451     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1452     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1453     hhcd->hc[ch_num].state = HC_STALL;
1454   }
1455   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_NAK) == USB_OTG_HCINT_NAK)
1456   {
1457     hhcd->hc[ch_num].ErrCnt = 0U;
1458     hhcd->hc[ch_num].state = HC_NAK;
1459 
1460     if (hhcd->hc[ch_num].do_ping == 0U)
1461     {
1462       if (hhcd->hc[ch_num].speed == HCD_DEVICE_SPEED_HIGH)
1463       {
1464         hhcd->hc[ch_num].do_ping = 1U;
1465       }
1466     }
1467 
1468     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1469     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1470     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NAK);
1471   }
1472   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_TXERR) == USB_OTG_HCINT_TXERR)
1473   {
1474     if (hhcd->Init.dma_enable == 0U)
1475     {
1476       hhcd->hc[ch_num].state = HC_XACTERR;
1477       __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1478       (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1479     }
1480     else
1481     {
1482       hhcd->hc[ch_num].ErrCnt++;
1483       if (hhcd->hc[ch_num].ErrCnt > 2U)
1484       {
1485         hhcd->hc[ch_num].ErrCnt = 0U;
1486         hhcd->hc[ch_num].urb_state = URB_ERROR;
1487         HAL_HCD_HC_NotifyURBChange_Callback(hhcd, (uint8_t)ch_num,
1488                                             hhcd->hc[ch_num].urb_state);
1489       }
1490       else
1491       {
1492         hhcd->hc[ch_num].urb_state = URB_NOTREADY;
1493       }
1494     }
1495     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_TXERR);
1496   }
1497   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_DTERR) == USB_OTG_HCINT_DTERR)
1498   {
1499     __HAL_HCD_UNMASK_HALT_HC_INT(ch_num);
1500     (void)USB_HC_Halt(hhcd->Instance, (uint8_t)ch_num);
1501     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_NAK);
1502     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_DTERR);
1503     hhcd->hc[ch_num].state = HC_DATATGLERR;
1504   }
1505   else if ((USBx_HC(ch_num)->HCINT & USB_OTG_HCINT_CHH) == USB_OTG_HCINT_CHH)
1506   {
1507     __HAL_HCD_MASK_HALT_HC_INT(ch_num);
1508 
1509     if (hhcd->hc[ch_num].state == HC_XFRC)
1510     {
1511       hhcd->hc[ch_num].urb_state  = URB_DONE;
1512       if ((hhcd->hc[ch_num].ep_type == EP_TYPE_BULK) ||
1513           (hhcd->hc[ch_num].ep_type == EP_TYPE_INTR))
1514       {
1515         if (hhcd->Init.dma_enable == 0U)
1516         {
1517           hhcd->hc[ch_num].toggle_out ^= 1U;
1518         }
1519 
1520         if ((hhcd->Init.dma_enable == 1U) && (hhcd->hc[ch_num].xfer_len > 0U))
1521         {
1522           num_packets = (hhcd->hc[ch_num].xfer_len + hhcd->hc[ch_num].max_packet - 1U) / hhcd->hc[ch_num].max_packet;
1523 
1524           if ((num_packets & 1U) != 0U)
1525           {
1526             hhcd->hc[ch_num].toggle_out ^= 1U;
1527           }
1528         }
1529       }
1530     }
1531     else if (hhcd->hc[ch_num].state == HC_NAK)
1532     {
1533       hhcd->hc[ch_num].urb_state = URB_NOTREADY;
1534     }
1535     else if (hhcd->hc[ch_num].state == HC_NYET)
1536     {
1537       hhcd->hc[ch_num].urb_state  = URB_NOTREADY;
1538     }
1539     else if (hhcd->hc[ch_num].state == HC_STALL)
1540     {
1541       hhcd->hc[ch_num].urb_state  = URB_STALL;
1542     }
1543     else if ((hhcd->hc[ch_num].state == HC_XACTERR) ||
1544              (hhcd->hc[ch_num].state == HC_DATATGLERR))
1545     {
1546       hhcd->hc[ch_num].ErrCnt++;
1547       if (hhcd->hc[ch_num].ErrCnt > 2U)
1548       {
1549         hhcd->hc[ch_num].ErrCnt = 0U;
1550         hhcd->hc[ch_num].urb_state = URB_ERROR;
1551       }
1552       else
1553       {
1554         hhcd->hc[ch_num].urb_state = URB_NOTREADY;
1555 
1556         /* re-activate the channel  */
1557         tmpreg = USBx_HC(ch_num)->HCCHAR;
1558         tmpreg &= ~USB_OTG_HCCHAR_CHDIS;
1559         tmpreg |= USB_OTG_HCCHAR_CHENA;
1560         USBx_HC(ch_num)->HCCHAR = tmpreg;
1561       }
1562     }
1563     else
1564     {
1565       /* ... */
1566     }
1567 
1568     __HAL_HCD_CLEAR_HC_INT(ch_num, USB_OTG_HCINT_CHH);
1569     HAL_HCD_HC_NotifyURBChange_Callback(hhcd, (uint8_t)ch_num, hhcd->hc[ch_num].urb_state);
1570   }
1571   else
1572   {
1573     /* ... */
1574   }
1575 }
1576 
1577 /**
1578   * @brief  Handle Rx Queue Level interrupt requests.
1579   * @param  hhcd HCD handle
1580   * @retval none
1581   */
HCD_RXQLVL_IRQHandler(HCD_HandleTypeDef * hhcd)1582 static void HCD_RXQLVL_IRQHandler(HCD_HandleTypeDef *hhcd)
1583 {
1584   USB_OTG_GlobalTypeDef *USBx = hhcd->Instance;
1585   uint32_t USBx_BASE = (uint32_t)USBx;
1586   uint32_t pktsts;
1587   uint32_t pktcnt;
1588   uint32_t GrxstspReg;
1589   uint32_t xferSizePktCnt;
1590   uint32_t tmpreg;
1591   uint32_t ch_num;
1592 
1593   GrxstspReg = hhcd->Instance->GRXSTSP;
1594   ch_num = GrxstspReg & USB_OTG_GRXSTSP_EPNUM;
1595   pktsts = (GrxstspReg & USB_OTG_GRXSTSP_PKTSTS) >> 17;
1596   pktcnt = (GrxstspReg & USB_OTG_GRXSTSP_BCNT) >> 4;
1597 
1598   switch (pktsts)
1599   {
1600     case GRXSTS_PKTSTS_IN:
1601       /* Read the data into the host buffer. */
1602       if ((pktcnt > 0U) && (hhcd->hc[ch_num].xfer_buff != (void *)0))
1603       {
1604         if ((hhcd->hc[ch_num].xfer_count + pktcnt) <= hhcd->hc[ch_num].xfer_len)
1605         {
1606           (void)USB_ReadPacket(hhcd->Instance,
1607                                hhcd->hc[ch_num].xfer_buff, (uint16_t)pktcnt);
1608 
1609           /* manage multiple Xfer */
1610           hhcd->hc[ch_num].xfer_buff += pktcnt;
1611           hhcd->hc[ch_num].xfer_count += pktcnt;
1612 
1613           /* get transfer size packet count */
1614           xferSizePktCnt = (USBx_HC(ch_num)->HCTSIZ & USB_OTG_HCTSIZ_PKTCNT) >> 19;
1615 
1616           if ((hhcd->hc[ch_num].max_packet == pktcnt) && (xferSizePktCnt > 0U))
1617           {
1618             /* re-activate the channel when more packets are expected */
1619             tmpreg = USBx_HC(ch_num)->HCCHAR;
1620             tmpreg &= ~USB_OTG_HCCHAR_CHDIS;
1621             tmpreg |= USB_OTG_HCCHAR_CHENA;
1622             USBx_HC(ch_num)->HCCHAR = tmpreg;
1623             hhcd->hc[ch_num].toggle_in ^= 1U;
1624           }
1625         }
1626         else
1627         {
1628           hhcd->hc[ch_num].urb_state = URB_ERROR;
1629         }
1630       }
1631       break;
1632 
1633     case GRXSTS_PKTSTS_DATA_TOGGLE_ERR:
1634       break;
1635 
1636     case GRXSTS_PKTSTS_IN_XFER_COMP:
1637     case GRXSTS_PKTSTS_CH_HALTED:
1638     default:
1639       break;
1640   }
1641 }
1642 
1643 /**
1644   * @brief  Handle Host Port interrupt requests.
1645   * @param  hhcd HCD handle
1646   * @retval None
1647   */
HCD_Port_IRQHandler(HCD_HandleTypeDef * hhcd)1648 static void HCD_Port_IRQHandler(HCD_HandleTypeDef *hhcd)
1649 {
1650   USB_OTG_GlobalTypeDef *USBx = hhcd->Instance;
1651   uint32_t USBx_BASE = (uint32_t)USBx;
1652   __IO uint32_t hprt0;
1653   __IO uint32_t hprt0_dup;
1654 
1655   /* Handle Host Port Interrupts */
1656   hprt0 = USBx_HPRT0;
1657   hprt0_dup = USBx_HPRT0;
1658 
1659   hprt0_dup &= ~(USB_OTG_HPRT_PENA | USB_OTG_HPRT_PCDET | \
1660                  USB_OTG_HPRT_PENCHNG | USB_OTG_HPRT_POCCHNG);
1661 
1662   /* Check whether Port Connect detected */
1663   if ((hprt0 & USB_OTG_HPRT_PCDET) == USB_OTG_HPRT_PCDET)
1664   {
1665     if ((hprt0 & USB_OTG_HPRT_PCSTS) == USB_OTG_HPRT_PCSTS)
1666     {
1667 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
1668       hhcd->ConnectCallback(hhcd);
1669 #else
1670       HAL_HCD_Connect_Callback(hhcd);
1671 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
1672     }
1673     hprt0_dup |= USB_OTG_HPRT_PCDET;
1674   }
1675 
1676   /* Check whether Port Enable Changed */
1677   if ((hprt0 & USB_OTG_HPRT_PENCHNG) == USB_OTG_HPRT_PENCHNG)
1678   {
1679     hprt0_dup |= USB_OTG_HPRT_PENCHNG;
1680 
1681     if ((hprt0 & USB_OTG_HPRT_PENA) == USB_OTG_HPRT_PENA)
1682     {
1683       if (hhcd->Init.phy_itface  == USB_OTG_EMBEDDED_PHY)
1684       {
1685         if ((hprt0 & USB_OTG_HPRT_PSPD) == (HPRT0_PRTSPD_LOW_SPEED << 17))
1686         {
1687           (void)USB_InitFSLSPClkSel(hhcd->Instance, HCFG_6_MHZ);
1688         }
1689         else
1690         {
1691           (void)USB_InitFSLSPClkSel(hhcd->Instance, HCFG_48_MHZ);
1692         }
1693       }
1694       else
1695       {
1696         if (hhcd->Init.speed == HCD_SPEED_FULL)
1697         {
1698           USBx_HOST->HFIR = 60000U;
1699         }
1700       }
1701 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
1702       hhcd->PortEnabledCallback(hhcd);
1703 #else
1704       HAL_HCD_PortEnabled_Callback(hhcd);
1705 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
1706 
1707     }
1708     else
1709     {
1710 #if (USE_HAL_HCD_REGISTER_CALLBACKS == 1U)
1711       hhcd->PortDisabledCallback(hhcd);
1712 #else
1713       HAL_HCD_PortDisabled_Callback(hhcd);
1714 #endif /* USE_HAL_HCD_REGISTER_CALLBACKS */
1715     }
1716   }
1717 
1718   /* Check for an overcurrent */
1719   if ((hprt0 & USB_OTG_HPRT_POCCHNG) == USB_OTG_HPRT_POCCHNG)
1720   {
1721     hprt0_dup |= USB_OTG_HPRT_POCCHNG;
1722   }
1723 
1724   /* Clear Port Interrupts */
1725   USBx_HPRT0 = hprt0_dup;
1726 }
1727 
1728 /**
1729   * @}
1730   */
1731 
1732 /**
1733   * @}
1734   */
1735 
1736 #endif /* defined (USB_OTG_FS) || defined (USB_OTG_HS) */
1737 #endif /* HAL_HCD_MODULE_ENABLED */
1738 
1739 /**
1740   * @}
1741   */
1742 
1743 /**
1744   * @}
1745   */
1746 
1747 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
1748