1 /**
2 ******************************************************************************
3 * @file stm32f7xx_hal_dma.c
4 * @author MCD Application Team
5 * @brief DMA HAL module driver.
6 *
7 * This file provides firmware functions to manage the following
8 * functionalities of the Direct Memory Access (DMA) peripheral:
9 * + Initialization and de-initialization functions
10 * + IO operation functions
11 * + Peripheral State and errors functions
12 @verbatim
13 ==============================================================================
14 ##### How to use this driver #####
15 ==============================================================================
16 [..]
17 (#) Enable and configure the peripheral to be connected to the DMA Stream
18 (except for internal SRAM/FLASH memories: no initialization is
19 necessary) please refer to Reference manual for connection between peripherals
20 and DMA requests.
21
22 (#) For a given Stream, program the required configuration through the following parameters:
23 Transfer Direction, Source and Destination data formats,
24 Circular, Normal or peripheral flow control mode, Stream Priority level,
25 Source and Destination Increment mode, FIFO mode and its Threshold (if needed),
26 Burst mode for Source and/or Destination (if needed) using HAL_DMA_Init() function.
27
28 -@- Prior to HAL_DMA_Init() the clock must be enabled for DMA through the following macros:
29 __HAL_RCC_DMA1_CLK_ENABLE() or __HAL_RCC_DMA2_CLK_ENABLE().
30
31 *** Polling mode IO operation ***
32 =================================
33 [..]
34 (+) Use HAL_DMA_Start() to start DMA transfer after the configuration of Source
35 address and destination address and the Length of data to be transferred.
36 (+) Use HAL_DMA_PollForTransfer() to poll for the end of current transfer, in this
37 case a fixed Timeout can be configured by User depending from his application.
38 (+) Use HAL_DMA_Abort() function to abort the current transfer.
39
40 *** Interrupt mode IO operation ***
41 ===================================
42 [..]
43 (+) Configure the DMA interrupt priority using HAL_NVIC_SetPriority()
44 (+) Enable the DMA IRQ handler using HAL_NVIC_EnableIRQ()
45 (+) Select Callbacks functions using HAL_DMA_RegisterCallback()
46 (+) Use HAL_DMA_Start_IT() to start DMA transfer after the configuration of
47 Source address and destination address and the Length of data to be transferred. In this
48 case the DMA interrupt is configured
49 (+) Use HAL_DMA_IRQHandler() called under DMA_IRQHandler() Interrupt subroutine
50 (+) At the end of data transfer HAL_DMA_IRQHandler() function is executed and user can
51 add his own function by customization of function pointer XferCpltCallback and
52 XferErrorCallback (i.e a member of DMA handle structure).
53 [..]
54 (#) Use HAL_DMA_GetState() function to return the DMA state and HAL_DMA_GetError() in case of error
55 detection.
56
57 (#) Use HAL_DMA_Abort_IT() function to abort the current transfer
58
59 -@- In Memory-to-Memory transfer mode, Circular mode is not allowed.
60
61 -@- The FIFO is used mainly to reduce bus usage and to allow data packing/unpacking: it is
62 possible to set different Data Sizes for the Peripheral and the Memory (ie. you can set
63 Half-Word data size for the peripheral to access its data register and set Word data size
64 for the Memory to gain in access time. Each two half words will be packed and written in
65 a single access to a Word in the Memory).
66
67 -@- When FIFO is disabled, it is not allowed to configure different Data Sizes for Source
68 and Destination. In this case the Peripheral Data Size will be applied to both Source
69 and Destination.
70
71 *** DMA HAL driver macros list ***
72 =============================================
73 [..]
74 Below the list of most used macros in DMA HAL driver.
75
76 (+) __HAL_DMA_ENABLE: Enable the specified DMA Stream.
77 (+) __HAL_DMA_DISABLE: Disable the specified DMA Stream.
78 (+) __HAL_DMA_GET_IT_SOURCE: Check whether the specified DMA Stream interrupt has occurred or not.
79
80 [..]
81 (@) You can refer to the DMA HAL driver header file for more useful macros
82
83 @endverbatim
84 ******************************************************************************
85 * @attention
86 *
87 * Copyright (c) 2017 STMicroelectronics.
88 * All rights reserved.
89 *
90 * This software is licensed under terms that can be found in the LICENSE file in
91 * the root directory of this software component.
92 * If no LICENSE file comes with this software, it is provided AS-IS.
93 *
94 ******************************************************************************
95 */
96
97 /* Includes ------------------------------------------------------------------*/
98 #include "stm32f7xx_hal.h"
99
100 /** @addtogroup STM32F7xx_HAL_Driver
101 * @{
102 */
103
104 /** @defgroup DMA DMA
105 * @brief DMA HAL module driver
106 * @{
107 */
108
109 #ifdef HAL_DMA_MODULE_ENABLED
110
111 /* Private types -------------------------------------------------------------*/
112 typedef struct
113 {
114 __IO uint32_t ISR; /*!< DMA interrupt status register */
115 __IO uint32_t Reserved0;
116 __IO uint32_t IFCR; /*!< DMA interrupt flag clear register */
117 } DMA_Base_Registers;
118
119 /* Private variables ---------------------------------------------------------*/
120 /* Private constants ---------------------------------------------------------*/
121 /** @addtogroup DMA_Private_Constants
122 * @{
123 */
124 #define HAL_TIMEOUT_DMA_ABORT ((uint32_t)5) /* 5 ms */
125 /**
126 * @}
127 */
128 /* Private macros ------------------------------------------------------------*/
129 /* Private functions ---------------------------------------------------------*/
130 /** @addtogroup DMA_Private_Functions
131 * @{
132 */
133 static void DMA_SetConfig(DMA_HandleTypeDef *hdma, uint32_t SrcAddress, uint32_t DstAddress, uint32_t DataLength);
134 static uint32_t DMA_CalcBaseAndBitshift(DMA_HandleTypeDef *hdma);
135 static HAL_StatusTypeDef DMA_CheckFifoParam(DMA_HandleTypeDef *hdma);
136
137 /**
138 * @}
139 */
140
141 /* Exported functions ---------------------------------------------------------*/
142 /** @addtogroup DMA_Exported_Functions
143 * @{
144 */
145
146 /** @addtogroup DMA_Exported_Functions_Group1
147 *
148 @verbatim
149 ===============================================================================
150 ##### Initialization and de-initialization functions #####
151 ===============================================================================
152 [..]
153 This section provides functions allowing to initialize the DMA Stream source
154 and destination addresses, incrementation and data sizes, transfer direction,
155 circular/normal mode selection, memory-to-memory mode selection and Stream priority value.
156 [..]
157 The HAL_DMA_Init() function follows the DMA configuration procedures as described in
158 reference manual.
159
160 @endverbatim
161 * @{
162 */
163
164 /**
165 * @brief Initialize the DMA according to the specified
166 * parameters in the DMA_InitTypeDef and create the associated handle.
167 * @param hdma Pointer to a DMA_HandleTypeDef structure that contains
168 * the configuration information for the specified DMA Stream.
169 * @retval HAL status
170 */
HAL_DMA_Init(DMA_HandleTypeDef * hdma)171 HAL_StatusTypeDef HAL_DMA_Init(DMA_HandleTypeDef *hdma)
172 {
173 uint32_t tmp = 0U;
174 uint32_t tickstart = HAL_GetTick();
175 DMA_Base_Registers *regs;
176
177 /* Check the DMA peripheral state */
178 if(hdma == NULL)
179 {
180 return HAL_ERROR;
181 }
182
183 /* Check the parameters */
184 assert_param(IS_DMA_STREAM_ALL_INSTANCE(hdma->Instance));
185 assert_param(IS_DMA_CHANNEL(hdma->Init.Channel));
186 assert_param(IS_DMA_DIRECTION(hdma->Init.Direction));
187 assert_param(IS_DMA_PERIPHERAL_INC_STATE(hdma->Init.PeriphInc));
188 assert_param(IS_DMA_MEMORY_INC_STATE(hdma->Init.MemInc));
189 assert_param(IS_DMA_PERIPHERAL_DATA_SIZE(hdma->Init.PeriphDataAlignment));
190 assert_param(IS_DMA_MEMORY_DATA_SIZE(hdma->Init.MemDataAlignment));
191 assert_param(IS_DMA_MODE(hdma->Init.Mode));
192 assert_param(IS_DMA_PRIORITY(hdma->Init.Priority));
193 assert_param(IS_DMA_FIFO_MODE_STATE(hdma->Init.FIFOMode));
194 /* Check the memory burst, peripheral burst and FIFO threshold parameters only
195 when FIFO mode is enabled */
196 if(hdma->Init.FIFOMode != DMA_FIFOMODE_DISABLE)
197 {
198 assert_param(IS_DMA_FIFO_THRESHOLD(hdma->Init.FIFOThreshold));
199 assert_param(IS_DMA_MEMORY_BURST(hdma->Init.MemBurst));
200 assert_param(IS_DMA_PERIPHERAL_BURST(hdma->Init.PeriphBurst));
201 }
202
203 /* Change DMA peripheral state */
204 hdma->State = HAL_DMA_STATE_BUSY;
205
206 /* Allocate lock resource */
207 __HAL_UNLOCK(hdma);
208
209
210 /* Disable the peripheral */
211 __HAL_DMA_DISABLE(hdma);
212
213 /* Check if the DMA Stream is effectively disabled */
214 while((hdma->Instance->CR & DMA_SxCR_EN) != RESET)
215 {
216 /* Check for the Timeout */
217 if((HAL_GetTick() - tickstart ) > HAL_TIMEOUT_DMA_ABORT)
218 {
219 /* Update error code */
220 hdma->ErrorCode = HAL_DMA_ERROR_TIMEOUT;
221
222 /* Change the DMA state */
223 hdma->State = HAL_DMA_STATE_TIMEOUT;
224
225 return HAL_TIMEOUT;
226 }
227 }
228
229 /* Get the CR register value */
230 tmp = hdma->Instance->CR;
231
232 /* Clear CHSEL, MBURST, PBURST, PL, MSIZE, PSIZE, MINC, PINC, CIRC, DIR, CT and DBM bits */
233 tmp &= ((uint32_t)~(DMA_SxCR_CHSEL | DMA_SxCR_MBURST | DMA_SxCR_PBURST | \
234 DMA_SxCR_PL | DMA_SxCR_MSIZE | DMA_SxCR_PSIZE | \
235 DMA_SxCR_MINC | DMA_SxCR_PINC | DMA_SxCR_CIRC | \
236 DMA_SxCR_DIR | DMA_SxCR_CT | DMA_SxCR_DBM));
237
238 /* Prepare the DMA Stream configuration */
239 tmp |= hdma->Init.Channel | hdma->Init.Direction |
240 hdma->Init.PeriphInc | hdma->Init.MemInc |
241 hdma->Init.PeriphDataAlignment | hdma->Init.MemDataAlignment |
242 hdma->Init.Mode | hdma->Init.Priority;
243
244 /* the Memory burst and peripheral burst are not used when the FIFO is disabled */
245 if(hdma->Init.FIFOMode == DMA_FIFOMODE_ENABLE)
246 {
247 /* Get memory burst and peripheral burst */
248 tmp |= hdma->Init.MemBurst | hdma->Init.PeriphBurst;
249 }
250
251 /* Write to DMA Stream CR register */
252 hdma->Instance->CR = tmp;
253
254 /* Get the FCR register value */
255 tmp = hdma->Instance->FCR;
256
257 /* Clear Direct mode and FIFO threshold bits */
258 tmp &= (uint32_t)~(DMA_SxFCR_DMDIS | DMA_SxFCR_FTH);
259
260 /* Prepare the DMA Stream FIFO configuration */
261 tmp |= hdma->Init.FIFOMode;
262
263 /* The FIFO threshold is not used when the FIFO mode is disabled */
264 if(hdma->Init.FIFOMode == DMA_FIFOMODE_ENABLE)
265 {
266 /* Get the FIFO threshold */
267 tmp |= hdma->Init.FIFOThreshold;
268
269 /* Check compatibility between FIFO threshold level and size of the memory burst */
270 /* for INCR4, INCR8, INCR16 bursts */
271 if (hdma->Init.MemBurst != DMA_MBURST_SINGLE)
272 {
273 if (DMA_CheckFifoParam(hdma) != HAL_OK)
274 {
275 /* Update error code */
276 hdma->ErrorCode = HAL_DMA_ERROR_PARAM;
277
278 /* Change the DMA state */
279 hdma->State = HAL_DMA_STATE_READY;
280
281 return HAL_ERROR;
282 }
283 }
284 }
285
286 /* Write to DMA Stream FCR */
287 hdma->Instance->FCR = tmp;
288
289 /* Initialize StreamBaseAddress and StreamIndex parameters to be used to calculate
290 DMA steam Base Address needed by HAL_DMA_IRQHandler() and HAL_DMA_PollForTransfer() */
291 regs = (DMA_Base_Registers *)DMA_CalcBaseAndBitshift(hdma);
292
293 /* Clear all interrupt flags */
294 regs->IFCR = 0x3FU << hdma->StreamIndex;
295
296 /* Initialize the error code */
297 hdma->ErrorCode = HAL_DMA_ERROR_NONE;
298
299 /* Initialize the DMA state */
300 hdma->State = HAL_DMA_STATE_READY;
301
302 return HAL_OK;
303 }
304
305 /**
306 * @brief DeInitializes the DMA peripheral
307 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
308 * the configuration information for the specified DMA Stream.
309 * @retval HAL status
310 */
HAL_DMA_DeInit(DMA_HandleTypeDef * hdma)311 HAL_StatusTypeDef HAL_DMA_DeInit(DMA_HandleTypeDef *hdma)
312 {
313 DMA_Base_Registers *regs;
314
315 /* Check the DMA peripheral state */
316 if(hdma == NULL)
317 {
318 return HAL_ERROR;
319 }
320
321 /* Check the DMA peripheral state */
322 if(hdma->State == HAL_DMA_STATE_BUSY)
323 {
324 /* Return error status */
325 return HAL_BUSY;
326 }
327
328 /* Check the parameters */
329 assert_param(IS_DMA_STREAM_ALL_INSTANCE(hdma->Instance));
330
331 /* Disable the selected DMA Streamx */
332 __HAL_DMA_DISABLE(hdma);
333
334 /* Reset DMA Streamx control register */
335 hdma->Instance->CR = 0U;
336
337 /* Reset DMA Streamx number of data to transfer register */
338 hdma->Instance->NDTR = 0U;
339
340 /* Reset DMA Streamx peripheral address register */
341 hdma->Instance->PAR = 0U;
342
343 /* Reset DMA Streamx memory 0 address register */
344 hdma->Instance->M0AR = 0U;
345
346 /* Reset DMA Streamx memory 1 address register */
347 hdma->Instance->M1AR = 0U;
348
349 /* Reset DMA Streamx FIFO control register */
350 hdma->Instance->FCR = (uint32_t)0x00000021U;
351
352 /* Get DMA steam Base Address */
353 regs = (DMA_Base_Registers *)DMA_CalcBaseAndBitshift(hdma);
354
355 /* Clear all interrupt flags at correct offset within the register */
356 regs->IFCR = 0x3FU << hdma->StreamIndex;
357
358 /* Clean all callbacks */
359 hdma->XferCpltCallback = NULL;
360 hdma->XferHalfCpltCallback = NULL;
361 hdma->XferM1CpltCallback = NULL;
362 hdma->XferM1HalfCpltCallback = NULL;
363 hdma->XferErrorCallback = NULL;
364 hdma->XferAbortCallback = NULL;
365
366 /* Reset the error code */
367 hdma->ErrorCode = HAL_DMA_ERROR_NONE;
368
369 /* Reset the DMA state */
370 hdma->State = HAL_DMA_STATE_RESET;
371
372 /* Release Lock */
373 __HAL_UNLOCK(hdma);
374
375 return HAL_OK;
376 }
377
378 /**
379 * @}
380 */
381
382 /** @addtogroup DMA_Exported_Functions_Group2
383 *
384 @verbatim
385 ===============================================================================
386 ##### IO operation functions #####
387 ===============================================================================
388 [..] This section provides functions allowing to:
389 (+) Configure the source, destination address and data length and Start DMA transfer
390 (+) Configure the source, destination address and data length and
391 Start DMA transfer with interrupt
392 (+) Abort DMA transfer
393 (+) Poll for transfer complete
394 (+) Handle DMA interrupt request
395
396 @endverbatim
397 * @{
398 */
399
400 /**
401 * @brief Starts the DMA Transfer.
402 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
403 * the configuration information for the specified DMA Stream.
404 * @param SrcAddress The source memory Buffer address
405 * @param DstAddress The destination memory Buffer address
406 * @param DataLength The length of data to be transferred from source to destination
407 * @retval HAL status
408 */
HAL_DMA_Start(DMA_HandleTypeDef * hdma,uint32_t SrcAddress,uint32_t DstAddress,uint32_t DataLength)409 HAL_StatusTypeDef HAL_DMA_Start(DMA_HandleTypeDef *hdma, uint32_t SrcAddress, uint32_t DstAddress, uint32_t DataLength)
410 {
411 HAL_StatusTypeDef status = HAL_OK;
412
413 /* Check the parameters */
414 assert_param(IS_DMA_BUFFER_SIZE(DataLength));
415
416 /* Process locked */
417 __HAL_LOCK(hdma);
418
419 if(HAL_DMA_STATE_READY == hdma->State)
420 {
421 /* Change DMA peripheral state */
422 hdma->State = HAL_DMA_STATE_BUSY;
423
424 /* Initialize the error code */
425 hdma->ErrorCode = HAL_DMA_ERROR_NONE;
426
427 /* Configure the source, destination address and the data length */
428 DMA_SetConfig(hdma, SrcAddress, DstAddress, DataLength);
429
430 /* Enable the Peripheral */
431 __HAL_DMA_ENABLE(hdma);
432 }
433 else
434 {
435 /* Process unlocked */
436 __HAL_UNLOCK(hdma);
437
438 /* Return error status */
439 status = HAL_BUSY;
440 }
441 return status;
442 }
443
444 /**
445 * @brief Start the DMA Transfer with interrupt enabled.
446 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
447 * the configuration information for the specified DMA Stream.
448 * @param SrcAddress The source memory Buffer address
449 * @param DstAddress The destination memory Buffer address
450 * @param DataLength The length of data to be transferred from source to destination
451 * @retval HAL status
452 */
HAL_DMA_Start_IT(DMA_HandleTypeDef * hdma,uint32_t SrcAddress,uint32_t DstAddress,uint32_t DataLength)453 HAL_StatusTypeDef HAL_DMA_Start_IT(DMA_HandleTypeDef *hdma, uint32_t SrcAddress, uint32_t DstAddress, uint32_t DataLength)
454 {
455 HAL_StatusTypeDef status = HAL_OK;
456
457 /* calculate DMA base and stream number */
458 DMA_Base_Registers *regs = (DMA_Base_Registers *)hdma->StreamBaseAddress;
459
460 /* Check the parameters */
461 assert_param(IS_DMA_BUFFER_SIZE(DataLength));
462
463 /* Process locked */
464 __HAL_LOCK(hdma);
465
466 if(HAL_DMA_STATE_READY == hdma->State)
467 {
468 /* Change DMA peripheral state */
469 hdma->State = HAL_DMA_STATE_BUSY;
470
471 /* Initialize the error code */
472 hdma->ErrorCode = HAL_DMA_ERROR_NONE;
473
474 /* Configure the source, destination address and the data length */
475 DMA_SetConfig(hdma, SrcAddress, DstAddress, DataLength);
476
477 /* Clear all interrupt flags at correct offset within the register */
478 regs->IFCR = 0x3FU << hdma->StreamIndex;
479
480 /* Enable Common interrupts*/
481 hdma->Instance->CR |= DMA_IT_TC | DMA_IT_TE | DMA_IT_DME;
482 hdma->Instance->FCR |= DMA_IT_FE;
483
484 if(hdma->XferHalfCpltCallback != NULL)
485 {
486 hdma->Instance->CR |= DMA_IT_HT;
487 }
488
489 /* Enable the Peripheral */
490 __HAL_DMA_ENABLE(hdma);
491 }
492 else
493 {
494 /* Process unlocked */
495 __HAL_UNLOCK(hdma);
496
497 /* Return error status */
498 status = HAL_BUSY;
499 }
500
501 return status;
502 }
503
504 /**
505 * @brief Aborts the DMA Transfer.
506 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
507 * the configuration information for the specified DMA Stream.
508 *
509 * @note After disabling a DMA Stream, a check for wait until the DMA Stream is
510 * effectively disabled is added. If a Stream is disabled
511 * while a data transfer is ongoing, the current data will be transferred
512 * and the Stream will be effectively disabled only after the transfer of
513 * this single data is finished.
514 * @retval HAL status
515 */
HAL_DMA_Abort(DMA_HandleTypeDef * hdma)516 HAL_StatusTypeDef HAL_DMA_Abort(DMA_HandleTypeDef *hdma)
517 {
518 /* calculate DMA base and stream number */
519 DMA_Base_Registers *regs = (DMA_Base_Registers *)hdma->StreamBaseAddress;
520
521 uint32_t tickstart = HAL_GetTick();
522
523 if(hdma->State != HAL_DMA_STATE_BUSY)
524 {
525 hdma->ErrorCode = HAL_DMA_ERROR_NO_XFER;
526
527 /* Process Unlocked */
528 __HAL_UNLOCK(hdma);
529
530 return HAL_ERROR;
531 }
532 else
533 {
534 /* Disable all the transfer interrupts */
535 hdma->Instance->CR &= ~(DMA_IT_TC | DMA_IT_TE | DMA_IT_DME);
536 hdma->Instance->FCR &= ~(DMA_IT_FE);
537
538 if((hdma->XferHalfCpltCallback != NULL) || (hdma->XferM1HalfCpltCallback != NULL))
539 {
540 hdma->Instance->CR &= ~(DMA_IT_HT);
541 }
542
543 /* Disable the stream */
544 __HAL_DMA_DISABLE(hdma);
545
546 /* Check if the DMA Stream is effectively disabled */
547 while((hdma->Instance->CR & DMA_SxCR_EN) != RESET)
548 {
549 /* Check for the Timeout */
550 if((HAL_GetTick() - tickstart ) > HAL_TIMEOUT_DMA_ABORT)
551 {
552 /* Update error code */
553 hdma->ErrorCode = HAL_DMA_ERROR_TIMEOUT;
554
555 /* Change the DMA state */
556 hdma->State = HAL_DMA_STATE_TIMEOUT;
557
558 /* Process Unlocked */
559 __HAL_UNLOCK(hdma);
560
561 return HAL_TIMEOUT;
562 }
563 }
564
565 /* Clear all interrupt flags at correct offset within the register */
566 regs->IFCR = 0x3FU << hdma->StreamIndex;
567
568 /* Change the DMA state*/
569 hdma->State = HAL_DMA_STATE_READY;
570
571 /* Process Unlocked */
572 __HAL_UNLOCK(hdma);
573
574 }
575 return HAL_OK;
576 }
577
578 /**
579 * @brief Aborts the DMA Transfer in Interrupt mode.
580 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
581 * the configuration information for the specified DMA Stream.
582 * @retval HAL status
583 */
HAL_DMA_Abort_IT(DMA_HandleTypeDef * hdma)584 HAL_StatusTypeDef HAL_DMA_Abort_IT(DMA_HandleTypeDef *hdma)
585 {
586 if(hdma->State != HAL_DMA_STATE_BUSY)
587 {
588 hdma->ErrorCode = HAL_DMA_ERROR_NO_XFER;
589 return HAL_ERROR;
590 }
591 else
592 {
593 /* Set Abort State */
594 hdma->State = HAL_DMA_STATE_ABORT;
595
596 /* Disable the stream */
597 __HAL_DMA_DISABLE(hdma);
598 }
599
600 return HAL_OK;
601 }
602
603 /**
604 * @brief Polling for transfer complete.
605 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
606 * the configuration information for the specified DMA Stream.
607 * @param CompleteLevel Specifies the DMA level complete.
608 * @note The polling mode is kept in this version for legacy. it is recommended to use the IT model instead.
609 * This model could be used for debug purpose.
610 * @note The HAL_DMA_PollForTransfer API cannot be used in circular and double buffering mode (automatic circular mode).
611 * @param Timeout Timeout duration.
612 * @retval HAL status
613 */
HAL_DMA_PollForTransfer(DMA_HandleTypeDef * hdma,HAL_DMA_LevelCompleteTypeDef CompleteLevel,uint32_t Timeout)614 HAL_StatusTypeDef HAL_DMA_PollForTransfer(DMA_HandleTypeDef *hdma, HAL_DMA_LevelCompleteTypeDef CompleteLevel, uint32_t Timeout)
615 {
616 HAL_StatusTypeDef status = HAL_OK;
617 uint32_t mask_cpltlevel;
618 uint32_t tickstart = HAL_GetTick();
619 uint32_t tmpisr;
620
621 /* calculate DMA base and stream number */
622 DMA_Base_Registers *regs;
623
624 if(HAL_DMA_STATE_BUSY != hdma->State)
625 {
626 /* No transfer ongoing */
627 hdma->ErrorCode = HAL_DMA_ERROR_NO_XFER;
628 __HAL_UNLOCK(hdma);
629 return HAL_ERROR;
630 }
631
632 /* Polling mode not supported in circular mode and double buffering mode */
633 if ((hdma->Instance->CR & DMA_SxCR_CIRC) != RESET)
634 {
635 hdma->ErrorCode = HAL_DMA_ERROR_NOT_SUPPORTED;
636 return HAL_ERROR;
637 }
638
639 /* Get the level transfer complete flag */
640 if(CompleteLevel == HAL_DMA_FULL_TRANSFER)
641 {
642 /* Transfer Complete flag */
643 mask_cpltlevel = DMA_FLAG_TCIF0_4 << hdma->StreamIndex;
644 }
645 else
646 {
647 /* Half Transfer Complete flag */
648 mask_cpltlevel = DMA_FLAG_HTIF0_4 << hdma->StreamIndex;
649 }
650
651 regs = (DMA_Base_Registers *)hdma->StreamBaseAddress;
652 tmpisr = regs->ISR;
653
654 while(((tmpisr & mask_cpltlevel) == RESET) && ((hdma->ErrorCode & HAL_DMA_ERROR_TE) == RESET))
655 {
656 /* Check for the Timeout (Not applicable in circular mode)*/
657 if(Timeout != HAL_MAX_DELAY)
658 {
659 if((Timeout == 0)||((HAL_GetTick() - tickstart ) > Timeout))
660 {
661 /* Update error code */
662 hdma->ErrorCode = HAL_DMA_ERROR_TIMEOUT;
663
664 /* Change the DMA state */
665 hdma->State = HAL_DMA_STATE_READY;
666
667 /* Process Unlocked */
668 __HAL_UNLOCK(hdma);
669
670 return HAL_TIMEOUT;
671 }
672 }
673
674 /* Get the ISR register value */
675 tmpisr = regs->ISR;
676
677 if((tmpisr & (DMA_FLAG_TEIF0_4 << hdma->StreamIndex)) != RESET)
678 {
679 /* Update error code */
680 hdma->ErrorCode |= HAL_DMA_ERROR_TE;
681
682 /* Clear the transfer error flag */
683 regs->IFCR = DMA_FLAG_TEIF0_4 << hdma->StreamIndex;
684 }
685
686 if((tmpisr & (DMA_FLAG_FEIF0_4 << hdma->StreamIndex)) != RESET)
687 {
688 /* Update error code */
689 hdma->ErrorCode |= HAL_DMA_ERROR_FE;
690
691 /* Clear the FIFO error flag */
692 regs->IFCR = DMA_FLAG_FEIF0_4 << hdma->StreamIndex;
693 }
694
695 if((tmpisr & (DMA_FLAG_DMEIF0_4 << hdma->StreamIndex)) != RESET)
696 {
697 /* Update error code */
698 hdma->ErrorCode |= HAL_DMA_ERROR_DME;
699
700 /* Clear the Direct Mode error flag */
701 regs->IFCR = DMA_FLAG_DMEIF0_4 << hdma->StreamIndex;
702 }
703 }
704
705 if(hdma->ErrorCode != HAL_DMA_ERROR_NONE)
706 {
707 if((hdma->ErrorCode & HAL_DMA_ERROR_TE) != RESET)
708 {
709 HAL_DMA_Abort(hdma);
710
711 /* Clear the half transfer and transfer complete flags */
712 regs->IFCR = (DMA_FLAG_HTIF0_4 | DMA_FLAG_TCIF0_4) << hdma->StreamIndex;
713
714 /* Change the DMA state */
715 hdma->State= HAL_DMA_STATE_READY;
716
717 /* Process Unlocked */
718 __HAL_UNLOCK(hdma);
719
720 return HAL_ERROR;
721 }
722 }
723
724 /* Get the level transfer complete flag */
725 if(CompleteLevel == HAL_DMA_FULL_TRANSFER)
726 {
727 /* Clear the half transfer and transfer complete flags */
728 regs->IFCR = (DMA_FLAG_HTIF0_4 | DMA_FLAG_TCIF0_4) << hdma->StreamIndex;
729
730 hdma->State = HAL_DMA_STATE_READY;
731
732 /* Process Unlocked */
733 __HAL_UNLOCK(hdma);
734
735 }
736 else
737 {
738 /* Clear the half transfer flag */
739 regs->IFCR = (DMA_FLAG_HTIF0_4) << hdma->StreamIndex;
740 }
741
742 return status;
743 }
744
745 /**
746 * @brief Handles DMA interrupt request.
747 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
748 * the configuration information for the specified DMA Stream.
749 * @retval None
750 */
HAL_DMA_IRQHandler(DMA_HandleTypeDef * hdma)751 void HAL_DMA_IRQHandler(DMA_HandleTypeDef *hdma)
752 {
753 uint32_t tmpisr;
754 __IO uint32_t count = 0;
755 uint32_t timeout = SystemCoreClock / 9600;
756
757 /* calculate DMA base and stream number */
758 DMA_Base_Registers *regs = (DMA_Base_Registers *)hdma->StreamBaseAddress;
759
760 tmpisr = regs->ISR;
761
762 /* Transfer Error Interrupt management ***************************************/
763 if ((tmpisr & (DMA_FLAG_TEIF0_4 << hdma->StreamIndex)) != RESET)
764 {
765 if(__HAL_DMA_GET_IT_SOURCE(hdma, DMA_IT_TE) != RESET)
766 {
767 /* Disable the transfer error interrupt */
768 hdma->Instance->CR &= ~(DMA_IT_TE);
769
770 /* Clear the transfer error flag */
771 regs->IFCR = DMA_FLAG_TEIF0_4 << hdma->StreamIndex;
772
773 /* Update error code */
774 hdma->ErrorCode |= HAL_DMA_ERROR_TE;
775 }
776 }
777 /* FIFO Error Interrupt management ******************************************/
778 if ((tmpisr & (DMA_FLAG_FEIF0_4 << hdma->StreamIndex)) != RESET)
779 {
780 if(__HAL_DMA_GET_IT_SOURCE(hdma, DMA_IT_FE) != RESET)
781 {
782 /* Clear the FIFO error flag */
783 regs->IFCR = DMA_FLAG_FEIF0_4 << hdma->StreamIndex;
784
785 /* Update error code */
786 hdma->ErrorCode |= HAL_DMA_ERROR_FE;
787 }
788 }
789 /* Direct Mode Error Interrupt management ***********************************/
790 if ((tmpisr & (DMA_FLAG_DMEIF0_4 << hdma->StreamIndex)) != RESET)
791 {
792 if(__HAL_DMA_GET_IT_SOURCE(hdma, DMA_IT_DME) != RESET)
793 {
794 /* Clear the direct mode error flag */
795 regs->IFCR = DMA_FLAG_DMEIF0_4 << hdma->StreamIndex;
796
797 /* Update error code */
798 hdma->ErrorCode |= HAL_DMA_ERROR_DME;
799 }
800 }
801 /* Half Transfer Complete Interrupt management ******************************/
802 if ((tmpisr & (DMA_FLAG_HTIF0_4 << hdma->StreamIndex)) != RESET)
803 {
804 if(__HAL_DMA_GET_IT_SOURCE(hdma, DMA_IT_HT) != RESET)
805 {
806 /* Clear the half transfer complete flag */
807 regs->IFCR = DMA_FLAG_HTIF0_4 << hdma->StreamIndex;
808
809 /* Multi_Buffering mode enabled */
810 if(((hdma->Instance->CR) & (uint32_t)(DMA_SxCR_DBM)) != RESET)
811 {
812 /* Current memory buffer used is Memory 0 */
813 if((hdma->Instance->CR & DMA_SxCR_CT) == RESET)
814 {
815 if(hdma->XferHalfCpltCallback != NULL)
816 {
817 /* Half transfer callback */
818 hdma->XferHalfCpltCallback(hdma);
819 }
820 }
821 /* Current memory buffer used is Memory 1 */
822 else
823 {
824 if(hdma->XferM1HalfCpltCallback != NULL)
825 {
826 /* Half transfer callback */
827 hdma->XferM1HalfCpltCallback(hdma);
828 }
829 }
830 }
831 else
832 {
833 /* Disable the half transfer interrupt if the DMA mode is not CIRCULAR */
834 if((hdma->Instance->CR & DMA_SxCR_CIRC) == RESET)
835 {
836 /* Disable the half transfer interrupt */
837 hdma->Instance->CR &= ~(DMA_IT_HT);
838 }
839
840 if(hdma->XferHalfCpltCallback != NULL)
841 {
842 /* Half transfer callback */
843 hdma->XferHalfCpltCallback(hdma);
844 }
845 }
846 }
847 }
848 /* Transfer Complete Interrupt management ***********************************/
849 if ((tmpisr & (DMA_FLAG_TCIF0_4 << hdma->StreamIndex)) != RESET)
850 {
851 if(__HAL_DMA_GET_IT_SOURCE(hdma, DMA_IT_TC) != RESET)
852 {
853 /* Clear the transfer complete flag */
854 regs->IFCR = DMA_FLAG_TCIF0_4 << hdma->StreamIndex;
855
856 if(HAL_DMA_STATE_ABORT == hdma->State)
857 {
858 /* Disable all the transfer interrupts */
859 hdma->Instance->CR &= ~(DMA_IT_TC | DMA_IT_TE | DMA_IT_DME);
860 hdma->Instance->FCR &= ~(DMA_IT_FE);
861
862 if((hdma->XferHalfCpltCallback != NULL) || (hdma->XferM1HalfCpltCallback != NULL))
863 {
864 hdma->Instance->CR &= ~(DMA_IT_HT);
865 }
866
867 /* Clear all interrupt flags at correct offset within the register */
868 regs->IFCR = 0x3FU << hdma->StreamIndex;
869
870 /* Change the DMA state */
871 hdma->State = HAL_DMA_STATE_READY;
872
873 /* Process Unlocked */
874 __HAL_UNLOCK(hdma);
875
876 if(hdma->XferAbortCallback != NULL)
877 {
878 hdma->XferAbortCallback(hdma);
879 }
880 return;
881 }
882
883 if(((hdma->Instance->CR) & (uint32_t)(DMA_SxCR_DBM)) != RESET)
884 {
885 /* Current memory buffer used is Memory 0 */
886 if((hdma->Instance->CR & DMA_SxCR_CT) == RESET)
887 {
888 if(hdma->XferM1CpltCallback != NULL)
889 {
890 /* Transfer complete Callback for memory1 */
891 hdma->XferM1CpltCallback(hdma);
892 }
893 }
894 /* Current memory buffer used is Memory 1 */
895 else
896 {
897 if(hdma->XferCpltCallback != NULL)
898 {
899 /* Transfer complete Callback for memory0 */
900 hdma->XferCpltCallback(hdma);
901 }
902 }
903 }
904 /* Disable the transfer complete interrupt if the DMA mode is not CIRCULAR */
905 else
906 {
907 if((hdma->Instance->CR & DMA_SxCR_CIRC) == RESET)
908 {
909 /* Disable the transfer complete interrupt */
910 hdma->Instance->CR &= ~(DMA_IT_TC);
911
912 /* Change the DMA state */
913 hdma->State = HAL_DMA_STATE_READY;
914
915 /* Process Unlocked */
916 __HAL_UNLOCK(hdma);
917
918 }
919
920 if(hdma->XferCpltCallback != NULL)
921 {
922 /* Transfer complete callback */
923 hdma->XferCpltCallback(hdma);
924 }
925 }
926 }
927 }
928
929 /* manage error case */
930 if(hdma->ErrorCode != HAL_DMA_ERROR_NONE)
931 {
932 if((hdma->ErrorCode & HAL_DMA_ERROR_TE) != RESET)
933 {
934 hdma->State = HAL_DMA_STATE_ABORT;
935
936 /* Disable the stream */
937 __HAL_DMA_DISABLE(hdma);
938
939 do
940 {
941 if (++count > timeout)
942 {
943 break;
944 }
945 }
946 while((hdma->Instance->CR & DMA_SxCR_EN) != RESET);
947
948 /* Change the DMA state */
949 hdma->State = HAL_DMA_STATE_READY;
950
951 /* Process Unlocked */
952 __HAL_UNLOCK(hdma);
953
954 }
955
956 if(hdma->XferErrorCallback != NULL)
957 {
958 /* Transfer error callback */
959 hdma->XferErrorCallback(hdma);
960 }
961 }
962 }
963
964 /**
965 * @brief Register callbacks
966 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
967 * the configuration information for the specified DMA Stream.
968 * @param CallbackID User Callback identifier
969 * a DMA_HandleTypeDef structure as parameter.
970 * @param pCallback pointer to private callbacsk function which has pointer to
971 * a DMA_HandleTypeDef structure as parameter.
972 * @retval HAL status
973 */
HAL_DMA_RegisterCallback(DMA_HandleTypeDef * hdma,HAL_DMA_CallbackIDTypeDef CallbackID,void (* pCallback)(DMA_HandleTypeDef * _hdma))974 HAL_StatusTypeDef HAL_DMA_RegisterCallback(DMA_HandleTypeDef *hdma, HAL_DMA_CallbackIDTypeDef CallbackID, void (* pCallback)(DMA_HandleTypeDef *_hdma))
975 {
976
977 HAL_StatusTypeDef status = HAL_OK;
978
979 /* Process locked */
980 __HAL_LOCK(hdma);
981
982 if(HAL_DMA_STATE_READY == hdma->State)
983 {
984 switch (CallbackID)
985 {
986 case HAL_DMA_XFER_CPLT_CB_ID:
987 hdma->XferCpltCallback = pCallback;
988 break;
989
990 case HAL_DMA_XFER_HALFCPLT_CB_ID:
991 hdma->XferHalfCpltCallback = pCallback;
992 break;
993
994 case HAL_DMA_XFER_M1CPLT_CB_ID:
995 hdma->XferM1CpltCallback = pCallback;
996 break;
997
998 case HAL_DMA_XFER_M1HALFCPLT_CB_ID:
999 hdma->XferM1HalfCpltCallback = pCallback;
1000 break;
1001
1002 case HAL_DMA_XFER_ERROR_CB_ID:
1003 hdma->XferErrorCallback = pCallback;
1004 break;
1005
1006 case HAL_DMA_XFER_ABORT_CB_ID:
1007 hdma->XferAbortCallback = pCallback;
1008 break;
1009
1010 default:
1011 /* Return error status */
1012 status = HAL_ERROR;
1013 break;
1014 }
1015 }
1016 else
1017 {
1018 /* Return error status */
1019 status = HAL_ERROR;
1020 }
1021
1022 /* Release Lock */
1023 __HAL_UNLOCK(hdma);
1024
1025 return status;
1026 }
1027
1028 /**
1029 * @brief UnRegister callbacks
1030 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
1031 * the configuration information for the specified DMA Stream.
1032 * @param CallbackID User Callback identifier
1033 * a HAL_DMA_CallbackIDTypeDef ENUM as parameter.
1034 * @retval HAL status
1035 */
HAL_DMA_UnRegisterCallback(DMA_HandleTypeDef * hdma,HAL_DMA_CallbackIDTypeDef CallbackID)1036 HAL_StatusTypeDef HAL_DMA_UnRegisterCallback(DMA_HandleTypeDef *hdma, HAL_DMA_CallbackIDTypeDef CallbackID)
1037 {
1038 HAL_StatusTypeDef status = HAL_OK;
1039
1040 /* Process locked */
1041 __HAL_LOCK(hdma);
1042
1043 if(HAL_DMA_STATE_READY == hdma->State)
1044 {
1045 switch (CallbackID)
1046 {
1047 case HAL_DMA_XFER_CPLT_CB_ID:
1048 hdma->XferCpltCallback = NULL;
1049 break;
1050
1051 case HAL_DMA_XFER_HALFCPLT_CB_ID:
1052 hdma->XferHalfCpltCallback = NULL;
1053 break;
1054
1055 case HAL_DMA_XFER_M1CPLT_CB_ID:
1056 hdma->XferM1CpltCallback = NULL;
1057 break;
1058
1059 case HAL_DMA_XFER_M1HALFCPLT_CB_ID:
1060 hdma->XferM1HalfCpltCallback = NULL;
1061 break;
1062
1063 case HAL_DMA_XFER_ERROR_CB_ID:
1064 hdma->XferErrorCallback = NULL;
1065 break;
1066
1067 case HAL_DMA_XFER_ABORT_CB_ID:
1068 hdma->XferAbortCallback = NULL;
1069 break;
1070
1071 case HAL_DMA_XFER_ALL_CB_ID:
1072 hdma->XferCpltCallback = NULL;
1073 hdma->XferHalfCpltCallback = NULL;
1074 hdma->XferM1CpltCallback = NULL;
1075 hdma->XferM1HalfCpltCallback = NULL;
1076 hdma->XferErrorCallback = NULL;
1077 hdma->XferAbortCallback = NULL;
1078 break;
1079
1080 default:
1081 status = HAL_ERROR;
1082 break;
1083 }
1084 }
1085 else
1086 {
1087 status = HAL_ERROR;
1088 }
1089
1090 /* Release Lock */
1091 __HAL_UNLOCK(hdma);
1092
1093 return status;
1094 }
1095
1096 /**
1097 * @}
1098 */
1099
1100 /** @addtogroup DMA_Exported_Functions_Group3
1101 *
1102 @verbatim
1103 ===============================================================================
1104 ##### State and Errors functions #####
1105 ===============================================================================
1106 [..]
1107 This subsection provides functions allowing to
1108 (+) Check the DMA state
1109 (+) Get error code
1110
1111 @endverbatim
1112 * @{
1113 */
1114
1115 /**
1116 * @brief Returns the DMA state.
1117 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
1118 * the configuration information for the specified DMA Stream.
1119 * @retval HAL state
1120 */
HAL_DMA_GetState(DMA_HandleTypeDef * hdma)1121 HAL_DMA_StateTypeDef HAL_DMA_GetState(DMA_HandleTypeDef *hdma)
1122 {
1123 return hdma->State;
1124 }
1125
1126 /**
1127 * @brief Return the DMA error code
1128 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
1129 * the configuration information for the specified DMA Stream.
1130 * @retval DMA Error Code
1131 */
HAL_DMA_GetError(DMA_HandleTypeDef * hdma)1132 uint32_t HAL_DMA_GetError(DMA_HandleTypeDef *hdma)
1133 {
1134 return hdma->ErrorCode;
1135 }
1136
1137 /**
1138 * @}
1139 */
1140
1141 /**
1142 * @}
1143 */
1144
1145 /** @addtogroup DMA_Private_Functions
1146 * @{
1147 */
1148
1149 /**
1150 * @brief Sets the DMA Transfer parameter.
1151 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
1152 * the configuration information for the specified DMA Stream.
1153 * @param SrcAddress The source memory Buffer address
1154 * @param DstAddress The destination memory Buffer address
1155 * @param DataLength The length of data to be transferred from source to destination
1156 * @retval HAL status
1157 */
DMA_SetConfig(DMA_HandleTypeDef * hdma,uint32_t SrcAddress,uint32_t DstAddress,uint32_t DataLength)1158 static void DMA_SetConfig(DMA_HandleTypeDef *hdma, uint32_t SrcAddress, uint32_t DstAddress, uint32_t DataLength)
1159 {
1160 /* Clear DBM bit */
1161 hdma->Instance->CR &= (uint32_t)(~DMA_SxCR_DBM);
1162
1163 /* Configure DMA Stream data length */
1164 hdma->Instance->NDTR = DataLength;
1165
1166 /* Memory to Peripheral */
1167 if((hdma->Init.Direction) == DMA_MEMORY_TO_PERIPH)
1168 {
1169 /* Configure DMA Stream destination address */
1170 hdma->Instance->PAR = DstAddress;
1171
1172 /* Configure DMA Stream source address */
1173 hdma->Instance->M0AR = SrcAddress;
1174 }
1175 /* Peripheral to Memory */
1176 else
1177 {
1178 /* Configure DMA Stream source address */
1179 hdma->Instance->PAR = SrcAddress;
1180
1181 /* Configure DMA Stream destination address */
1182 hdma->Instance->M0AR = DstAddress;
1183 }
1184 }
1185
1186 /**
1187 * @brief Returns the DMA Stream base address depending on stream number
1188 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
1189 * the configuration information for the specified DMA Stream.
1190 * @retval Stream base address
1191 */
DMA_CalcBaseAndBitshift(DMA_HandleTypeDef * hdma)1192 static uint32_t DMA_CalcBaseAndBitshift(DMA_HandleTypeDef *hdma)
1193 {
1194 uint32_t stream_number = (((uint32_t)hdma->Instance & 0xFFU) - 16U) / 24U;
1195
1196 /* lookup table for necessary bitshift of flags within status registers */
1197 static const uint8_t flagBitshiftOffset[8U] = {0U, 6U, 16U, 22U, 0U, 6U, 16U, 22U};
1198 hdma->StreamIndex = flagBitshiftOffset[stream_number];
1199
1200 if (stream_number > 3U)
1201 {
1202 /* return pointer to HISR and HIFCR */
1203 hdma->StreamBaseAddress = (((uint32_t)hdma->Instance & (uint32_t)(~0x3FFU)) + 4U);
1204 }
1205 else
1206 {
1207 /* return pointer to LISR and LIFCR */
1208 hdma->StreamBaseAddress = ((uint32_t)hdma->Instance & (uint32_t)(~0x3FFU));
1209 }
1210
1211 return hdma->StreamBaseAddress;
1212 }
1213
1214 /**
1215 * @brief Check compatibility between FIFO threshold level and size of the memory burst
1216 * @param hdma pointer to a DMA_HandleTypeDef structure that contains
1217 * the configuration information for the specified DMA Stream.
1218 * @retval HAL status
1219 */
DMA_CheckFifoParam(DMA_HandleTypeDef * hdma)1220 static HAL_StatusTypeDef DMA_CheckFifoParam(DMA_HandleTypeDef *hdma)
1221 {
1222 HAL_StatusTypeDef status = HAL_OK;
1223 uint32_t tmp = hdma->Init.FIFOThreshold;
1224
1225 /* Memory Data size equal to Byte */
1226 if(hdma->Init.MemDataAlignment == DMA_MDATAALIGN_BYTE)
1227 {
1228 switch (tmp)
1229 {
1230 case DMA_FIFO_THRESHOLD_1QUARTERFULL:
1231 case DMA_FIFO_THRESHOLD_3QUARTERSFULL:
1232 if ((hdma->Init.MemBurst & DMA_SxCR_MBURST_1) == DMA_SxCR_MBURST_1)
1233 {
1234 status = HAL_ERROR;
1235 }
1236 break;
1237 case DMA_FIFO_THRESHOLD_HALFFULL:
1238 if (hdma->Init.MemBurst == DMA_MBURST_INC16)
1239 {
1240 status = HAL_ERROR;
1241 }
1242 break;
1243 case DMA_FIFO_THRESHOLD_FULL:
1244 break;
1245 default:
1246 break;
1247 }
1248 }
1249
1250 /* Memory Data size equal to Half-Word */
1251 else if (hdma->Init.MemDataAlignment == DMA_MDATAALIGN_HALFWORD)
1252 {
1253 switch (tmp)
1254 {
1255 case DMA_FIFO_THRESHOLD_1QUARTERFULL:
1256 case DMA_FIFO_THRESHOLD_3QUARTERSFULL:
1257 status = HAL_ERROR;
1258 break;
1259 case DMA_FIFO_THRESHOLD_HALFFULL:
1260 if ((hdma->Init.MemBurst & DMA_SxCR_MBURST_1) == DMA_SxCR_MBURST_1)
1261 {
1262 status = HAL_ERROR;
1263 }
1264 break;
1265 case DMA_FIFO_THRESHOLD_FULL:
1266 if (hdma->Init.MemBurst == DMA_MBURST_INC16)
1267 {
1268 status = HAL_ERROR;
1269 }
1270 break;
1271 default:
1272 break;
1273 }
1274 }
1275
1276 /* Memory Data size equal to Word */
1277 else
1278 {
1279 switch (tmp)
1280 {
1281 case DMA_FIFO_THRESHOLD_1QUARTERFULL:
1282 case DMA_FIFO_THRESHOLD_HALFFULL:
1283 case DMA_FIFO_THRESHOLD_3QUARTERSFULL:
1284 status = HAL_ERROR;
1285 break;
1286 case DMA_FIFO_THRESHOLD_FULL:
1287 if ((hdma->Init.MemBurst & DMA_SxCR_MBURST_1) == DMA_SxCR_MBURST_1)
1288 {
1289 status = HAL_ERROR;
1290 }
1291 break;
1292 default:
1293 break;
1294 }
1295 }
1296
1297 return status;
1298 }
1299
1300 /**
1301 * @}
1302 */
1303
1304 #endif /* HAL_DMA_MODULE_ENABLED */
1305 /**
1306 * @}
1307 */
1308
1309 /**
1310 * @}
1311 */
1312
1313