1 /**
2 ******************************************************************************
3 * @file stm32mp1xx_hal_sd.c
4 * @author MCD Application Team
5 * @brief SD card HAL module driver.
6 * This file provides firmware functions to manage the following
7 * functionalities of the Secure Digital (SD) peripheral:
8 * + Initialization and de-initialization functions
9 * + IO operation functions
10 * + Peripheral Control functions
11 * + Peripheral State functions
12 *
13
14 ******************************************************************************
15 * @attention
16 *
17 * <h2><center>© Copyright (c) 2019 STMicroelectronics.
18 * All rights reserved.</center></h2>
19 *
20 * This software component is licensed by ST under BSD 3-Clause license,
21 * the "License"; You may not use this file except in compliance with the
22 * License. You may obtain a copy of the License at:
23 * opensource.org/licenses/BSD-3-Clause
24 *
25 ******************************************************************************
26 *
27
28 @verbatim
29 ==============================================================================
30 ##### How to use this driver #####
31 ==============================================================================
32 [..]
33 This driver implements a high level communication layer for read and write from/to
34 this memory. The needed STM32 hardware resources (SDMMC and GPIO) are performed by
35 the user in HAL_SD_MspInit() function (MSP layer).
36 Basically, the MSP layer configuration should be the same as we provide in the
37 examples.
38 You can easily tailor this configuration according to hardware resources.
39
40 [..]
41 This driver is a generic layered driver for SDMMC memories which uses the HAL
42 SDMMC driver functions to interface with SD and uSD cards devices.
43 It is used as follows:
44
45 (#)Initialize the SDMMC low level resources by implement the HAL_SD_MspInit() API:
46 (##) Enable the SDMMC interface clock using __HAL_RCC_SDMMC_CLK_ENABLE();
47 (##) SDMMC pins configuration for SD card
48 (+++) Enable the clock for the SDMMC GPIOs using the functions __HAL_RCC_GPIOx_CLK_ENABLE();
49 (+++) Configure these SDMMC pins as alternate function pull-up using HAL_GPIO_Init()
50 and according to your pin assignment;
51 (##) NVIC configuration if you need to use interrupt process when using DMA transfer.
52 (+++) Configure the SDMMC interrupt priorities using functions HAL_NVIC_SetPriority();
53 (+++) Enable the NVIC SDMMC IRQs using function HAL_NVIC_EnableIRQ()
54 (+++) SDMMC interrupts are managed using the macros __HAL_SD_ENABLE_IT()
55 and __HAL_SD_DISABLE_IT() inside the communication process.
56 (+++) SDMMC interrupts pending bits are managed using the macros __HAL_SD_GET_IT()
57 and __HAL_SD_CLEAR_IT()
58 (##) No general propose DMA Configuration is needed, an Internal DMA for SDMMC IP are used.
59
60 (#) At this stage, you can perform SD read/write/erase operations after SD card initialization
61
62
63 *** SD Card Initialization and configuration ***
64 ================================================
65 [..]
66 To initialize the SD Card, use the HAL_SD_Init() function. It Initializes
67 the SD Card and put it into StandBy State (Ready for data transfer).
68 This function provide the following operations:
69
70 (#) Apply the SD Card initialization process at 400KHz and check the SD Card
71 type (Standard Capacity or High Capacity). You can change or adapt this
72 frequency by adjusting the "ClockDiv" field.
73 The SD Card frequency (SDMMC_CK) is computed as follows:
74
75 SDMMC_CK = SDMMCCLK / (2 * ClockDiv)
76
77 In initialization mode and according to the SD Card standard,
78 make sure that the SDMMC_CK frequency doesn't exceed 400KHz.
79
80 (#) Get the SD CID and CSD data. All these information are managed by the SDCardInfo
81 structure. This structure provide also ready computed SD Card capacity
82 and Block size.
83
84 -@- These information are stored in SD handle structure in case of future use.
85
86 (#) Configure the SD Card Data transfer frequency. You can change or adapt this
87 frequency by adjusting the "ClockDiv" field.
88 In transfer mode and according to the SD Card standard, make sure that the
89 SDMMC_CK frequency doesn't exceed 25MHz and 100MHz in High-speed mode switch.
90
91 (#) Select the corresponding SD Card according to the address read with the step 2.
92
93 (#) Configure the SD Card in wide bus mode: 4-bits data.
94
95 *** SD Card Read operation ***
96 ==============================
97 [..]
98 (+) You can read from SD card in polling mode by using function HAL_SD_ReadBlocks().
99 This function support only 512-bytes block length (the block size should be
100 chosen as 512 bytes).
101 You can choose either one block read operation or multiple block read operation
102 by adjusting the "NumberOfBlocks" parameter.
103
104 (+) You can read from SD card in DMA mode by using function HAL_SD_ReadBlocks_DMA().
105 This function support only 512-bytes block length (the block size should be
106 chosen as 512 bytes).
107 You can choose either one block read operation or multiple block read operation
108 by adjusting the "NumberOfBlocks" parameter.
109
110 *** SD Card Write operation ***
111 ===============================
112 [..]
113 (+) You can write to SD card in polling mode by using function HAL_SD_WriteBlocks().
114 This function support only 512-bytes block length (the block size should be
115 chosen as 512 bytes).
116 You can choose either one block read operation or multiple block read operation
117 by adjusting the "NumberOfBlocks" parameter.
118
119 (+) You can write to SD card in DMA mode by using function HAL_SD_WriteBlocks_DMA().
120 This function support only 512-bytes block length (the block size should be
121 chosen as 512 byte).
122 You can choose either one block read operation or multiple block read operation
123 by adjusting the "NumberOfBlocks" parameter.
124
125 *** SD card status ***
126 ======================
127 [..]
128 (+) At any time, you can check the SD Card status and get the SD card state
129 by using the HAL_SD_GetStatusInfo() function. This function checks first if the
130 SD card is still connected and then get the internal SD Card transfer state.
131
132 *** SD HAL driver macros list ***
133 ==================================
134 [..]
135 Below the list of most used macros in SD HAL driver.
136
137 (+) __HAL_SD_ENABLE_IT: Enable the SD device interrupt
138 (+) __HAL_SD_DISABLE_IT: Disable the SD device interrupt
139 (+) __HAL_SD_GET_FLAG:Check whether the specified SD flag is set or not
140 (+) __HAL_SD_CLEAR_FLAG: Clear the SD's pending flags
141
142 (@) You can refer to the SD HAL driver header file for more useful macros
143
144 *** Callback registration ***
145 =============================================
146 [..]
147 The compilation define USE_HAL_SD_REGISTER_CALLBACKS when set to 1
148 allows the user to configure dynamically the driver callbacks.
149
150 Use Functions @ref HAL_SD_RegisterCallback() to register a user callback,
151 it allows to register following callbacks:
152 (+) TxCpltCallback : callback when a transmission transfer is completed.
153 (+) RxCpltCallback : callback when a reception transfer is completed.
154 (+) ErrorCallback : callback when error occurs.
155 (+) AbortCpltCallback : callback when abort is completed.
156 (+) Read_DMADblBuf0CpltCallback : callback when the DMA reception of first buffer is completed.
157 (+) Read_DMADblBuf1CpltCallback : callback when the DMA reception of second buffer is completed.
158 (+) Write_DMADblBuf0CpltCallback : callback when the DMA transmission of first buffer is completed.
159 (+) Write_DMADblBuf1CpltCallback : callback when the DMA transmission of second buffer is completed.
160 (+) MspInitCallback : SD MspInit.
161 (+) MspDeInitCallback : SD MspDeInit.
162 This function takes as parameters the HAL peripheral handle, the Callback ID
163 and a pointer to the user callback function.
164 For specific callbacks TransceiverCallback use dedicated register callbacks:
165 respectively @ref HAL_SD_RegisterTransceiverCallback().
166
167 Use function @ref HAL_SD_UnRegisterCallback() to reset a callback to the default
168 weak (surcharged) function. It allows to reset following callbacks:
169 (+) TxCpltCallback : callback when a transmission transfer is completed.
170 (+) RxCpltCallback : callback when a reception transfer is completed.
171 (+) ErrorCallback : callback when error occurs.
172 (+) AbortCpltCallback : callback when abort is completed.
173 (+) Read_DMADblBuf0CpltCallback : callback when the DMA reception of first buffer is completed.
174 (+) Read_DMADblBuf1CpltCallback : callback when the DMA reception of second buffer is completed.
175 (+) Write_DMADblBuf0CpltCallback : callback when the DMA transmission of first buffer is completed.
176 (+) Write_DMADblBuf1CpltCallback : callback when the DMA transmission of second buffer is completed.
177 (+) MspInitCallback : SD MspInit.
178 (+) MspDeInitCallback : SD MspDeInit.
179 This function) takes as parameters the HAL peripheral handle and the Callback ID.
180 For specific callbacks TransceiverCallback use dedicated unregister callbacks:
181 respectively @ref HAL_SD_UnRegisterTransceiverCallback().
182
183 By default, after the @ref HAL_SD_Init and if the state is HAL_SD_STATE_RESET
184 all callbacks are reset to the corresponding legacy weak (surcharged) functions.
185 Exception done for MspInit and MspDeInit callbacks that are respectively
186 reset to the legacy weak (surcharged) functions in the @ref HAL_SD_Init
187 and @ref HAL_SD_DeInit only when these callbacks are null (not registered beforehand).
188 If not, MspInit or MspDeInit are not null, the @ref HAL_SD_Init and @ref HAL_SD_DeInit
189 keep and use the user MspInit/MspDeInit callbacks (registered beforehand)
190
191 Callbacks can be registered/unregistered in READY state only.
192 Exception done for MspInit/MspDeInit callbacks that can be registered/unregistered
193 in READY or RESET state, thus registered (user) MspInit/DeInit callbacks can be used
194 during the Init/DeInit.
195 In that case first register the MspInit/MspDeInit user callbacks
196 using @ref HAL_SD_RegisterCallback before calling @ref HAL_SD_DeInit
197 or @ref HAL_SD_Init function.
198
199 When The compilation define USE_HAL_SD_REGISTER_CALLBACKS is set to 0 or
200 not defined, the callback registering feature is not available
201 and weak (surcharged) callbacks are used.
202
203 @endverbatim
204
205 /* Includes ------------------------------------------------------------------*/
206 #include "stm32mp1xx_hal.h"
207
208 /** @addtogroup STM32MP1xx_HAL_Driver
209 * @{
210 */
211
212 /** @addtogroup SD
213 * @{
214 */
215
216 #ifdef HAL_SD_MODULE_ENABLED
217
218 /* Private typedef -----------------------------------------------------------*/
219 /* Private define ------------------------------------------------------------*/
220 /** @addtogroup SD_Private_Defines
221 * @{
222 */
223
224 /**
225 * @}
226 */
227
228 /* Private macro -------------------------------------------------------------*/
229 /* Private variables ---------------------------------------------------------*/
230 /* Private function prototypes -----------------------------------------------*/
231 /* Private functions ---------------------------------------------------------*/
232 /** @defgroup SD_Private_Functions SD Private Functions
233 * @{
234 */
235 static uint32_t SD_InitCard(SD_HandleTypeDef *hsd);
236 static uint32_t SD_PowerON(SD_HandleTypeDef *hsd);
237 static uint32_t SD_SendSDStatus(SD_HandleTypeDef *hsd, uint32_t *pSDstatus);
238 static uint32_t SD_SendStatus(SD_HandleTypeDef *hsd, uint32_t *pCardStatus);
239 static uint32_t SD_WideBus_Enable(SD_HandleTypeDef *hsd);
240 static uint32_t SD_WideBus_Disable(SD_HandleTypeDef *hsd);
241 static uint32_t SD_FindSCR(SD_HandleTypeDef *hsd, uint32_t *pSCR);
242 static void SD_PowerOFF(SD_HandleTypeDef *hsd);
243 static void SD_Write_IT(SD_HandleTypeDef *hsd);
244 static void SD_Read_IT(SD_HandleTypeDef *hsd);
245 static uint32_t SD_HighSpeed(SD_HandleTypeDef *hsd);
246 #if (USE_SD_TRANSCEIVER != 0U)
247 static uint32_t SD_UltraHighSpeed(SD_HandleTypeDef *hsd);
248 #endif /* USE_SD_TRANSCEIVER */
249 /**
250 * @}
251 */
252
253 /* Exported functions --------------------------------------------------------*/
254 /** @addtogroup SD_Exported_Functions
255 * @{
256 */
257
258 /** @addtogroup SD_Exported_Functions_Group1
259 * @brief Initialization and de-initialization functions
260 *
261 @verbatim
262 ==============================================================================
263 ##### Initialization and de-initialization functions #####
264 ==============================================================================
265 [..]
266 This section provides functions allowing to initialize/de-initialize the SD
267 card device to be ready for use.
268
269 @endverbatim
270 * @{
271 */
272
273 /**
274 * @brief Initializes the SD according to the specified parameters in the
275 SD_HandleTypeDef and create the associated handle.
276 * @param hsd: Pointer to the SD handle
277 * @retval HAL status
278 */
HAL_SD_Init(SD_HandleTypeDef * hsd)279 HAL_StatusTypeDef HAL_SD_Init(SD_HandleTypeDef *hsd)
280 {
281 HAL_SD_CardStatusTypedef CardStatus;
282 uint32_t speedgrade, unitsize;
283 uint32_t tickstart;
284
285 /* Check the SD handle allocation */
286 if(hsd == NULL)
287 {
288 return HAL_ERROR;
289 }
290
291 /* Check the parameters */
292 assert_param(IS_SDMMC_ALL_INSTANCE(hsd->Instance));
293 assert_param(IS_SDMMC_CLOCK_EDGE(hsd->Init.ClockEdge));
294 assert_param(IS_SDMMC_CLOCK_POWER_SAVE(hsd->Init.ClockPowerSave));
295 assert_param(IS_SDMMC_BUS_WIDE(hsd->Init.BusWide));
296 assert_param(IS_SDMMC_HARDWARE_FLOW_CONTROL(hsd->Init.HardwareFlowControl));
297 assert_param(IS_SDMMC_CLKDIV(hsd->Init.ClockDiv));
298
299 if(hsd->State == HAL_SD_STATE_RESET)
300 {
301 /* Allocate lock resource and initialize it */
302 hsd->Lock = HAL_UNLOCKED;
303 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
304 /* Reset Callback pointers in HAL_SD_STATE_RESET only */
305 hsd->TxCpltCallback = HAL_SD_TxCpltCallback;
306 hsd->RxCpltCallback = HAL_SD_RxCpltCallback;
307 hsd->ErrorCallback = HAL_SD_ErrorCallback;
308 hsd->AbortCpltCallback = HAL_SD_AbortCallback;
309 hsd->Read_DMADblBuf0CpltCallback = HAL_SDEx_Read_DMADoubleBuffer0CpltCallback;
310 hsd->Read_DMADblBuf1CpltCallback = HAL_SDEx_Read_DMADoubleBuffer1CpltCallback;
311 hsd->Write_DMADblBuf0CpltCallback = HAL_SDEx_Write_DMADoubleBuffer0CpltCallback;
312 hsd->Write_DMADblBuf1CpltCallback = HAL_SDEx_Write_DMADoubleBuffer1CpltCallback;
313 #if (USE_SD_TRANSCEIVER != 0U)
314 hsd->DriveTransceiver_1_8V_Callback = HAL_SD_DriveTransceiver_1_8V_Callback;
315 #endif /* USE_SD_TRANSCEIVER */
316
317 if(hsd->MspInitCallback == NULL)
318 {
319 hsd->MspInitCallback = HAL_SD_MspInit;
320 }
321
322 /* Init the low level hardware */
323 hsd->MspInitCallback(hsd);
324 #else
325 /* Init the low level hardware : GPIO, CLOCK, CORTEX...etc */
326 HAL_SD_MspInit(hsd);
327 #endif
328 }
329
330 hsd->State = HAL_SD_STATE_BUSY;
331
332 /* Initialize the Card parameters */
333 if (HAL_SD_InitCard(hsd) != HAL_OK)
334 {
335 return HAL_ERROR;
336 }
337
338 if( HAL_SD_GetCardStatus(hsd, &CardStatus) != HAL_OK)
339 {
340 return HAL_ERROR;
341 }
342 /* Get Initial Card Speed from Card Status*/
343 speedgrade = CardStatus.UhsSpeedGrade;
344 unitsize = CardStatus.UhsAllocationUnitSize;
345 if ((hsd->SdCard.CardType == CARD_SDHC_SDXC) && ((speedgrade != 0U) || (unitsize != 0U)))
346 {
347 hsd->SdCard.CardSpeed = CARD_ULTRA_HIGH_SPEED;
348 }
349 else
350 {
351 if (hsd->SdCard.CardType == CARD_SDHC_SDXC)
352 {
353 hsd->SdCard.CardSpeed = CARD_HIGH_SPEED;
354 }
355 else
356 {
357 hsd->SdCard.CardSpeed = CARD_NORMAL_SPEED;
358 }
359
360 }
361 /* Configure the bus wide */
362 if(HAL_SD_ConfigWideBusOperation(hsd, hsd->Init.BusWide) != HAL_OK)
363 {
364 return HAL_ERROR;
365 }
366 #if (USE_SD_TRANSCEIVER != 0U)
367 if((hsd->SdCard.CardSpeed == CARD_ULTRA_HIGH_SPEED) ||
368 (hsd->SdCard.CardType == CARD_SDHC_SDXC))
369 {
370 hsd->Instance->CLKCR |= 0x00100000U;
371 /* Enable High Speed */
372 if(SD_UltraHighSpeed(hsd) != HAL_SD_ERROR_NONE)
373 {
374 return HAL_ERROR;
375 }
376 }
377 else if (hsd->SdCard.CardSpeed == CARD_HIGH_SPEED)
378 {
379 /* Enable High Speed */
380 if(SD_HighSpeed(hsd) != HAL_SD_ERROR_NONE)
381 {
382 return HAL_ERROR;
383 }
384 }
385 else
386 {
387 /* Normal Speed mode, Nothing todo */
388 }
389 #else
390 if((hsd->SdCard.CardSpeed == CARD_ULTRA_HIGH_SPEED) ||
391 (hsd->SdCard.CardSpeed == CARD_HIGH_SPEED) ||
392 (hsd->SdCard.CardType == CARD_SDHC_SDXC))
393 {
394 /* Enable High Speed */
395 if(SD_HighSpeed(hsd) != HAL_SD_ERROR_NONE)
396 {
397 return HAL_ERROR;
398 }
399 }
400 #endif /* USE_SD_TRANSCEIVER */
401
402
403 /* Verify that SD card is ready to use after Initialization */
404 tickstart = HAL_GetTick();
405 while((HAL_SD_GetCardState(hsd) != HAL_SD_CARD_TRANSFER))
406 {
407 if((HAL_GetTick()-tickstart) >= SDMMC_DATATIMEOUT)
408 {
409 hsd->ErrorCode = HAL_SD_ERROR_TIMEOUT;
410 hsd->State= HAL_SD_STATE_READY;
411 return HAL_TIMEOUT;
412 }
413 }
414
415 /* Initialize the error code */
416 hsd->ErrorCode = HAL_SD_ERROR_NONE;
417
418 /* Initialize the SD operation */
419 hsd->Context = SD_CONTEXT_NONE;
420
421 /* Initialize the SD state */
422 hsd->State = HAL_SD_STATE_READY;
423
424 return HAL_OK;
425 }
426
427 /**
428 * @brief Initializes the SD Card.
429 * @param hsd: Pointer to SD handle
430 * @note This function initializes the SD card. It could be used when a card
431 re-initialization is needed.
432 * @retval HAL status
433 */
HAL_SD_InitCard(SD_HandleTypeDef * hsd)434 HAL_StatusTypeDef HAL_SD_InitCard(SD_HandleTypeDef *hsd)
435 {
436 uint32_t errorstate;
437 HAL_StatusTypeDef status;
438 SD_InitTypeDef Init;
439
440 /* Default SDMMC peripheral configuration for SD card initialization */
441 Init.ClockEdge = SDMMC_CLOCK_EDGE_RISING;
442 Init.ClockPowerSave = SDMMC_CLOCK_POWER_SAVE_DISABLE;
443 Init.BusWide = SDMMC_BUS_WIDE_1B;
444 Init.HardwareFlowControl = SDMMC_HARDWARE_FLOW_CONTROL_DISABLE;
445 Init.ClockDiv = SDMMC_INIT_CLK_DIV;
446
447 #if (USE_SD_TRANSCEIVER != 0U) || defined (USE_SD_DIRPOL)
448 /* Set Transceiver polarity */
449 hsd->Instance->POWER |= SDMMC_POWER_DIRPOL;
450 #endif /* USE_SD_TRANSCEIVER */
451
452 /* Initialize SDMMC peripheral interface with default configuration */
453 status = SDMMC_Init(hsd->Instance, Init);
454 if(status != HAL_OK)
455 {
456 return HAL_ERROR;
457 }
458
459 /* Set Power State to ON */
460 status = SDMMC_PowerState_ON(hsd->Instance);
461 if(status != HAL_OK)
462 {
463 return HAL_ERROR;
464 }
465
466 /* Identify card operating voltage */
467 errorstate = SD_PowerON(hsd);
468 if(errorstate != HAL_SD_ERROR_NONE)
469 {
470 hsd->State = HAL_SD_STATE_READY;
471 hsd->ErrorCode |= errorstate;
472 return HAL_ERROR;
473 }
474
475 /* Card initialization */
476 errorstate = SD_InitCard(hsd);
477 if(errorstate != HAL_SD_ERROR_NONE)
478 {
479 hsd->State = HAL_SD_STATE_READY;
480 hsd->ErrorCode |= errorstate;
481 return HAL_ERROR;
482 }
483
484 return HAL_OK;
485 }
486
487 /**
488 * @brief De-Initializes the SD card.
489 * @param hsd: Pointer to SD handle
490 * @retval HAL status
491 */
HAL_SD_DeInit(SD_HandleTypeDef * hsd)492 HAL_StatusTypeDef HAL_SD_DeInit(SD_HandleTypeDef *hsd)
493 {
494 /* Check the SD handle allocation */
495 if(hsd == NULL)
496 {
497 return HAL_ERROR;
498 }
499
500 /* Check the parameters */
501 assert_param(IS_SDMMC_ALL_INSTANCE(hsd->Instance));
502
503 hsd->State = HAL_SD_STATE_BUSY;
504
505 #if (USE_SD_TRANSCEIVER != 0U)
506 /* Desactivate the 1.8V Mode */
507 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
508 if(hsd->DriveTransceiver_1_8V_Callback == NULL)
509 {
510 hsd->DriveTransceiver_1_8V_Callback = HAL_SD_DriveTransceiver_1_8V_Callback;
511 }
512 hsd->DriveTransceiver_1_8V_Callback(RESET);
513 #else
514 HAL_SD_DriveTransceiver_1_8V_Callback(RESET);
515 #endif
516 #endif /* USE_SD_TRANSCEIVER */
517
518 /* Set SD power state to off */
519 SD_PowerOFF(hsd);
520
521 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
522 if(hsd->MspDeInitCallback == NULL)
523 {
524 hsd->MspDeInitCallback = HAL_SD_MspDeInit;
525 }
526
527 /* DeInit the low level hardware */
528 hsd->MspDeInitCallback(hsd);
529 #else
530 /* De-Initialize the MSP layer */
531 HAL_SD_MspDeInit(hsd);
532 #endif
533
534 hsd->ErrorCode = HAL_SD_ERROR_NONE;
535 hsd->State = HAL_SD_STATE_RESET;
536
537 return HAL_OK;
538 }
539
540
541 /**
542 * @brief Initializes the SD MSP.
543 * @param hsd: Pointer to SD handle
544 * @retval None
545 */
HAL_SD_MspInit(SD_HandleTypeDef * hsd)546 __weak void HAL_SD_MspInit(SD_HandleTypeDef *hsd)
547 {
548 /* Prevent unused argument(s) compilation warning */
549 UNUSED(hsd);
550
551 /* NOTE : This function should not be modified, when the callback is needed,
552 the HAL_SD_MspInit could be implemented in the user file
553 */
554 }
555
556 /**
557 * @brief De-Initialize SD MSP.
558 * @param hsd: Pointer to SD handle
559 * @retval None
560 */
HAL_SD_MspDeInit(SD_HandleTypeDef * hsd)561 __weak void HAL_SD_MspDeInit(SD_HandleTypeDef *hsd)
562 {
563 /* Prevent unused argument(s) compilation warning */
564 UNUSED(hsd);
565
566 /* NOTE : This function should not be modified, when the callback is needed,
567 the HAL_SD_MspDeInit could be implemented in the user file
568 */
569 }
570
571 /**
572 * @}
573 */
574
575 /** @addtogroup SD_Exported_Functions_Group2
576 * @brief Data transfer functions
577 *
578 @verbatim
579 ==============================================================================
580 ##### IO operation functions #####
581 ==============================================================================
582 [..]
583 This subsection provides a set of functions allowing to manage the data
584 transfer from/to SD card.
585
586 @endverbatim
587 * @{
588 */
589
590 /**
591 * @brief Reads block(s) from a specified address in a card. The Data transfer
592 * is managed by polling mode.
593 * @note This API should be followed by a check on the card state through
594 * HAL_SD_GetCardState().
595 * @param hsd: Pointer to SD handle
596 * @param pData: pointer to the buffer that will contain the received data
597 * @param BlockAdd: Block Address from where data is to be read
598 * @param NumberOfBlocks: Number of SD blocks to read
599 * @param Timeout: Specify timeout value
600 * @retval HAL status
601 */
HAL_SD_ReadBlocks(SD_HandleTypeDef * hsd,uint8_t * pData,uint32_t BlockAdd,uint32_t NumberOfBlocks,uint32_t Timeout)602 HAL_StatusTypeDef HAL_SD_ReadBlocks(SD_HandleTypeDef *hsd, uint8_t *pData, uint32_t BlockAdd, uint32_t NumberOfBlocks, uint32_t Timeout)
603 {
604 SDMMC_DataInitTypeDef config;
605 uint32_t errorstate;
606 uint32_t tickstart = HAL_GetTick();
607 uint32_t count, data;
608 uint32_t add = BlockAdd;
609 uint8_t *tempbuff = pData;
610
611 if(NULL == pData)
612 {
613 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
614 return HAL_ERROR;
615 }
616
617 if(hsd->State == HAL_SD_STATE_READY)
618 {
619 hsd->ErrorCode = HAL_SD_ERROR_NONE;
620
621 if((add + NumberOfBlocks) > (hsd->SdCard.LogBlockNbr))
622 {
623 hsd->ErrorCode |= HAL_SD_ERROR_ADDR_OUT_OF_RANGE;
624 return HAL_ERROR;
625 }
626
627 hsd->State = HAL_SD_STATE_BUSY;
628
629 /* Initialize data control register */
630 hsd->Instance->DCTRL = 0U;
631
632 if(hsd->SdCard.CardType != CARD_SDHC_SDXC)
633 {
634 add *= 512U;
635 }
636
637 /* Set Block Size for Card */
638 errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE);
639 if(errorstate != HAL_SD_ERROR_NONE)
640 {
641 /* Clear all the static flags */
642 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
643 hsd->ErrorCode |= errorstate;
644 hsd->State = HAL_SD_STATE_READY;
645 return HAL_ERROR;
646 }
647
648 /* Configure the SD DPSM (Data Path State Machine) */
649 config.DataTimeOut = SDMMC_DATATIMEOUT;
650 config.DataLength = NumberOfBlocks * BLOCKSIZE;
651 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_512B;
652 config.TransferDir = SDMMC_TRANSFER_DIR_TO_SDMMC;
653 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
654 config.DPSM = SDMMC_DPSM_DISABLE;
655 (void)SDMMC_ConfigData(hsd->Instance, &config);
656 __SDMMC_CMDTRANS_ENABLE( hsd->Instance);
657
658 /* Read block(s) in polling mode */
659 if(NumberOfBlocks > 1U)
660 {
661 hsd->Context = SD_CONTEXT_READ_MULTIPLE_BLOCK;
662
663 /* Read Multi Block command */
664 errorstate = SDMMC_CmdReadMultiBlock(hsd->Instance, add);
665 }
666 else
667 {
668 hsd->Context = SD_CONTEXT_READ_SINGLE_BLOCK;
669
670 /* Read Single Block command */
671 errorstate = SDMMC_CmdReadSingleBlock(hsd->Instance, add);
672 }
673 if(errorstate != HAL_SD_ERROR_NONE)
674 {
675 /* Clear all the static flags */
676 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
677 hsd->ErrorCode |= errorstate;
678 hsd->State = HAL_SD_STATE_READY;
679 return HAL_ERROR;
680 }
681
682 /* Poll on SDMMC flags */
683 while(!__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR | SDMMC_FLAG_DCRCFAIL | SDMMC_FLAG_DTIMEOUT | SDMMC_FLAG_DATAEND))
684 {
685 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXFIFOHF))
686 {
687 /* Read data from SDMMC Rx FIFO */
688 for(count = 0U; count < 8U; count++)
689 {
690 data = SDMMC_ReadFIFO(hsd->Instance);
691 *tempbuff = (uint8_t)(data & 0xFFU);
692 tempbuff++;
693 *tempbuff = (uint8_t)((data >> 8U) & 0xFFU);
694 tempbuff++;
695 *tempbuff = (uint8_t)((data >> 16U) & 0xFFU);
696 tempbuff++;
697 *tempbuff = (uint8_t)((data >> 24U) & 0xFFU);
698 tempbuff++;
699 }
700 }
701
702 if(((HAL_GetTick()-tickstart) >= Timeout) || (Timeout == 0U))
703 {
704 /* Clear all the static flags */
705 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
706 hsd->ErrorCode |= HAL_SD_ERROR_TIMEOUT;
707 hsd->State= HAL_SD_STATE_READY;
708 return HAL_TIMEOUT;
709 }
710 }
711 __SDMMC_CMDTRANS_DISABLE( hsd->Instance);
712
713 /* Send stop transmission command in case of multiblock read */
714 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DATAEND) && (NumberOfBlocks > 1U))
715 {
716 if(hsd->SdCard.CardType != CARD_SECURED)
717 {
718 /* Send stop transmission command */
719 errorstate = SDMMC_CmdStopTransfer(hsd->Instance);
720 if(errorstate != HAL_SD_ERROR_NONE)
721 {
722 /* Clear all the static flags */
723 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
724 hsd->ErrorCode |= errorstate;
725 hsd->State = HAL_SD_STATE_READY;
726 return HAL_ERROR;
727 }
728 }
729 }
730
731 /* Get error state */
732 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DTIMEOUT))
733 {
734 /* Clear all the static flags */
735 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
736 hsd->ErrorCode |= HAL_SD_ERROR_DATA_TIMEOUT;
737 hsd->State = HAL_SD_STATE_READY;
738 return HAL_ERROR;
739 }
740 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DCRCFAIL))
741 {
742 /* Clear all the static flags */
743 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
744 hsd->ErrorCode |= HAL_SD_ERROR_DATA_CRC_FAIL;
745 hsd->State = HAL_SD_STATE_READY;
746 return HAL_ERROR;
747 }
748 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR))
749 {
750 /* Clear all the static flags */
751 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
752 hsd->ErrorCode |= HAL_SD_ERROR_RX_OVERRUN;
753 hsd->State = HAL_SD_STATE_READY;
754 return HAL_ERROR;
755 }
756 else
757 {
758 /* Nothing to do */
759 }
760
761 /* Clear all the static flags */
762 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
763
764 hsd->State = HAL_SD_STATE_READY;
765
766 return HAL_OK;
767 }
768 else
769 {
770 hsd->ErrorCode |= HAL_SD_ERROR_BUSY;
771 return HAL_ERROR;
772 }
773 }
774
775 /**
776 * @brief Allows to write block(s) to a specified address in a card. The Data
777 * transfer is managed by polling mode.
778 * @note This API should be followed by a check on the card state through
779 * HAL_SD_GetCardState().
780 * @param hsd: Pointer to SD handle
781 * @param pData: pointer to the buffer that will contain the data to transmit
782 * @param BlockAdd: Block Address where data will be written
783 * @param NumberOfBlocks: Number of SD blocks to write
784 * @param Timeout: Specify timeout value
785 * @retval HAL status
786 */
HAL_SD_WriteBlocks(SD_HandleTypeDef * hsd,uint8_t * pData,uint32_t BlockAdd,uint32_t NumberOfBlocks,uint32_t Timeout)787 HAL_StatusTypeDef HAL_SD_WriteBlocks(SD_HandleTypeDef *hsd, uint8_t *pData, uint32_t BlockAdd, uint32_t NumberOfBlocks, uint32_t Timeout)
788 {
789 SDMMC_DataInitTypeDef config;
790 uint32_t errorstate;
791 uint32_t tickstart = HAL_GetTick();
792 uint32_t count, data;
793 uint32_t add = BlockAdd;
794 uint8_t *tempbuff = pData;
795
796 if(NULL == pData)
797 {
798 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
799 return HAL_ERROR;
800 }
801
802 if(hsd->State == HAL_SD_STATE_READY)
803 {
804 hsd->ErrorCode = HAL_SD_ERROR_NONE;
805
806 if((add + NumberOfBlocks) > (hsd->SdCard.LogBlockNbr))
807 {
808 hsd->ErrorCode |= HAL_SD_ERROR_ADDR_OUT_OF_RANGE;
809 return HAL_ERROR;
810 }
811
812 hsd->State = HAL_SD_STATE_BUSY;
813
814 /* Initialize data control register */
815 hsd->Instance->DCTRL = 0U;
816
817 if(hsd->SdCard.CardType != CARD_SDHC_SDXC)
818 {
819 add *= 512U;
820 }
821
822 /* Set Block Size for Card */
823 errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE);
824 if(errorstate != HAL_SD_ERROR_NONE)
825 {
826 /* Clear all the static flags */
827 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
828 hsd->ErrorCode |= errorstate;
829 hsd->State = HAL_SD_STATE_READY;
830 return HAL_ERROR;
831 }
832
833 /* Configure the SD DPSM (Data Path State Machine) */
834 config.DataTimeOut = SDMMC_DATATIMEOUT;
835 config.DataLength = NumberOfBlocks * BLOCKSIZE;
836 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_512B;
837 config.TransferDir = SDMMC_TRANSFER_DIR_TO_CARD;
838 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
839 config.DPSM = SDMMC_DPSM_DISABLE;
840 (void)SDMMC_ConfigData(hsd->Instance, &config);
841 __SDMMC_CMDTRANS_ENABLE( hsd->Instance);
842
843 /* Write Blocks in Polling mode */
844 if(NumberOfBlocks > 1U)
845 {
846 hsd->Context = SD_CONTEXT_WRITE_MULTIPLE_BLOCK;
847
848 /* Write Multi Block command */
849 errorstate = SDMMC_CmdWriteMultiBlock(hsd->Instance, add);
850 }
851 else
852 {
853 hsd->Context = SD_CONTEXT_WRITE_SINGLE_BLOCK;
854
855 /* Write Single Block command */
856 errorstate = SDMMC_CmdWriteSingleBlock(hsd->Instance, add);
857 }
858 if(errorstate != HAL_SD_ERROR_NONE)
859 {
860 /* Clear all the static flags */
861 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
862 hsd->ErrorCode |= errorstate;
863 hsd->State = HAL_SD_STATE_READY;
864 return HAL_ERROR;
865 }
866
867 /* Write block(s) in polling mode */
868 while(!__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_TXUNDERR | SDMMC_FLAG_DCRCFAIL | SDMMC_FLAG_DTIMEOUT | SDMMC_FLAG_DATAEND))
869 {
870 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_TXFIFOHE))
871 {
872 /* Write data to SDMMC Tx FIFO */
873 for(count = 0U; count < 8U; count++)
874 {
875 data = (uint32_t)(*tempbuff);
876 tempbuff++;
877 data |= ((uint32_t)(*tempbuff) << 8U);
878 tempbuff++;
879 data |= ((uint32_t)(*tempbuff) << 16U);
880 tempbuff++;
881 data |= ((uint32_t)(*tempbuff) << 24U);
882 tempbuff++;
883 (void)SDMMC_WriteFIFO(hsd->Instance, &data);
884 }
885 }
886
887 if(((HAL_GetTick()-tickstart) >= Timeout) || (Timeout == 0U))
888 {
889 /* Clear all the static flags */
890 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
891 hsd->ErrorCode |= errorstate;
892 hsd->State = HAL_SD_STATE_READY;
893 return HAL_TIMEOUT;
894 }
895 }
896 __SDMMC_CMDTRANS_DISABLE( hsd->Instance);
897
898 /* Send stop transmission command in case of multiblock write */
899 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DATAEND) && (NumberOfBlocks > 1U))
900 {
901 if(hsd->SdCard.CardType != CARD_SECURED)
902 {
903 /* Send stop transmission command */
904 errorstate = SDMMC_CmdStopTransfer(hsd->Instance);
905 if(errorstate != HAL_SD_ERROR_NONE)
906 {
907 /* Clear all the static flags */
908 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
909 hsd->ErrorCode |= errorstate;
910 hsd->State = HAL_SD_STATE_READY;
911 return HAL_ERROR;
912 }
913 }
914 }
915
916 /* Get error state */
917 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DTIMEOUT))
918 {
919 /* Clear all the static flags */
920 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
921 hsd->ErrorCode |= HAL_SD_ERROR_DATA_TIMEOUT;
922 hsd->State = HAL_SD_STATE_READY;
923 return HAL_ERROR;
924 }
925 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DCRCFAIL))
926 {
927 /* Clear all the static flags */
928 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
929 hsd->ErrorCode |= HAL_SD_ERROR_DATA_CRC_FAIL;
930 hsd->State = HAL_SD_STATE_READY;
931 return HAL_ERROR;
932 }
933 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_TXUNDERR))
934 {
935 /* Clear all the static flags */
936 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
937 hsd->ErrorCode |= HAL_SD_ERROR_TX_UNDERRUN;
938 hsd->State = HAL_SD_STATE_READY;
939 return HAL_ERROR;
940 }
941 else
942 {
943 /* Nothing to do */
944 }
945
946 /* Clear all the static flags */
947 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
948
949 hsd->State = HAL_SD_STATE_READY;
950
951 return HAL_OK;
952 }
953 else
954 {
955 hsd->ErrorCode |= HAL_SD_ERROR_BUSY;
956 return HAL_ERROR;
957 }
958 }
959
960 /**
961 * @brief Reads block(s) from a specified address in a card. The Data transfer
962 * is managed in interrupt mode.
963 * @note This API should be followed by a check on the card state through
964 * HAL_SD_GetCardState().
965 * @note You could also check the IT transfer process through the SD Rx
966 * interrupt event.
967 * @param hsd: Pointer to SD handle
968 * @param pData: Pointer to the buffer that will contain the received data
969 * @param BlockAdd: Block Address from where data is to be read
970 * @param NumberOfBlocks: Number of blocks to read.
971 * @retval HAL status
972 */
HAL_SD_ReadBlocks_IT(SD_HandleTypeDef * hsd,uint8_t * pData,uint32_t BlockAdd,uint32_t NumberOfBlocks)973 HAL_StatusTypeDef HAL_SD_ReadBlocks_IT(SD_HandleTypeDef *hsd, uint8_t *pData, uint32_t BlockAdd, uint32_t NumberOfBlocks)
974 {
975 SDMMC_DataInitTypeDef config;
976 uint32_t errorstate;
977 uint32_t add = BlockAdd;
978
979 if(NULL == pData)
980 {
981 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
982 return HAL_ERROR;
983 }
984
985 if(hsd->State == HAL_SD_STATE_READY)
986 {
987 hsd->ErrorCode = HAL_SD_ERROR_NONE;
988
989 if((add + NumberOfBlocks) > (hsd->SdCard.LogBlockNbr))
990 {
991 hsd->ErrorCode |= HAL_SD_ERROR_ADDR_OUT_OF_RANGE;
992 return HAL_ERROR;
993 }
994
995 hsd->State = HAL_SD_STATE_BUSY;
996
997 /* Initialize data control register */
998 hsd->Instance->DCTRL = 0U;
999
1000 hsd->pRxBuffPtr = pData;
1001 hsd->RxXferSize = BLOCKSIZE * NumberOfBlocks;
1002
1003 __HAL_SD_ENABLE_IT(hsd, (SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT | SDMMC_IT_RXOVERR | SDMMC_IT_DATAEND | SDMMC_FLAG_RXFIFOHF));
1004
1005 if(hsd->SdCard.CardType != CARD_SDHC_SDXC)
1006 {
1007 add *= 512U;
1008 }
1009
1010 /* Set Block Size for Card */
1011 errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE);
1012 if(errorstate != HAL_SD_ERROR_NONE)
1013 {
1014 /* Clear all the static flags */
1015 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1016 hsd->ErrorCode |= errorstate;
1017 hsd->State = HAL_SD_STATE_READY;
1018 return HAL_ERROR;
1019 }
1020
1021 /* Configure the SD DPSM (Data Path State Machine) */
1022 config.DataTimeOut = SDMMC_DATATIMEOUT;
1023 config.DataLength = BLOCKSIZE * NumberOfBlocks;
1024 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_512B;
1025 config.TransferDir = SDMMC_TRANSFER_DIR_TO_SDMMC;
1026 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
1027 config.DPSM = SDMMC_DPSM_DISABLE;
1028 (void)SDMMC_ConfigData(hsd->Instance, &config);
1029 __SDMMC_CMDTRANS_ENABLE( hsd->Instance);
1030
1031 /* Read Blocks in IT mode */
1032 if(NumberOfBlocks > 1U)
1033 {
1034 hsd->Context = (SD_CONTEXT_READ_MULTIPLE_BLOCK | SD_CONTEXT_IT);
1035
1036 /* Read Multi Block command */
1037 errorstate = SDMMC_CmdReadMultiBlock(hsd->Instance, add);
1038 }
1039 else
1040 {
1041 hsd->Context = (SD_CONTEXT_READ_SINGLE_BLOCK | SD_CONTEXT_IT);
1042
1043 /* Read Single Block command */
1044 errorstate = SDMMC_CmdReadSingleBlock(hsd->Instance, add);
1045 }
1046 if(errorstate != HAL_SD_ERROR_NONE)
1047 {
1048 /* Clear all the static flags */
1049 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1050 hsd->ErrorCode |= errorstate;
1051 hsd->State = HAL_SD_STATE_READY;
1052 return HAL_ERROR;
1053 }
1054
1055 return HAL_OK;
1056 }
1057 else
1058 {
1059 return HAL_BUSY;
1060 }
1061 }
1062
1063 /**
1064 * @brief Writes block(s) to a specified address in a card. The Data transfer
1065 * is managed in interrupt mode.
1066 * @note This API should be followed by a check on the card state through
1067 * HAL_SD_GetCardState().
1068 * @note You could also check the IT transfer process through the SD Tx
1069 * interrupt event.
1070 * @param hsd: Pointer to SD handle
1071 * @param pData: Pointer to the buffer that will contain the data to transmit
1072 * @param BlockAdd: Block Address where data will be written
1073 * @param NumberOfBlocks: Number of blocks to write
1074 * @retval HAL status
1075 */
HAL_SD_WriteBlocks_IT(SD_HandleTypeDef * hsd,uint8_t * pData,uint32_t BlockAdd,uint32_t NumberOfBlocks)1076 HAL_StatusTypeDef HAL_SD_WriteBlocks_IT(SD_HandleTypeDef *hsd, uint8_t *pData, uint32_t BlockAdd, uint32_t NumberOfBlocks)
1077 {
1078 SDMMC_DataInitTypeDef config;
1079 uint32_t errorstate;
1080 uint32_t add = BlockAdd;
1081
1082 if(NULL == pData)
1083 {
1084 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
1085 return HAL_ERROR;
1086 }
1087
1088 if(hsd->State == HAL_SD_STATE_READY)
1089 {
1090 hsd->ErrorCode = HAL_SD_ERROR_NONE;
1091
1092 if((add + NumberOfBlocks) > (hsd->SdCard.LogBlockNbr))
1093 {
1094 hsd->ErrorCode |= HAL_SD_ERROR_ADDR_OUT_OF_RANGE;
1095 return HAL_ERROR;
1096 }
1097
1098 hsd->State = HAL_SD_STATE_BUSY;
1099
1100 /* Initialize data control register */
1101 hsd->Instance->DCTRL = 0U;
1102
1103 hsd->pTxBuffPtr = pData;
1104 hsd->TxXferSize = BLOCKSIZE * NumberOfBlocks;
1105
1106 /* Enable transfer interrupts */
1107 __HAL_SD_ENABLE_IT(hsd, (SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT | SDMMC_IT_TXUNDERR | SDMMC_IT_DATAEND | SDMMC_FLAG_TXFIFOHE));
1108
1109 if(hsd->SdCard.CardType != CARD_SDHC_SDXC)
1110 {
1111 add *= 512U;
1112 }
1113
1114 /* Set Block Size for Card */
1115 errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE);
1116 if(errorstate != HAL_SD_ERROR_NONE)
1117 {
1118 /* Clear all the static flags */
1119 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1120 hsd->ErrorCode |= errorstate;
1121 hsd->State = HAL_SD_STATE_READY;
1122 return HAL_ERROR;
1123 }
1124
1125 /* Configure the SD DPSM (Data Path State Machine) */
1126 config.DataTimeOut = SDMMC_DATATIMEOUT;
1127 config.DataLength = BLOCKSIZE * NumberOfBlocks;
1128 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_512B;
1129 config.TransferDir = SDMMC_TRANSFER_DIR_TO_CARD;
1130 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
1131 config.DPSM = SDMMC_DPSM_DISABLE;
1132 (void)SDMMC_ConfigData(hsd->Instance, &config);
1133
1134 __SDMMC_CMDTRANS_ENABLE( hsd->Instance);
1135
1136 /* Write Blocks in Polling mode */
1137 if(NumberOfBlocks > 1U)
1138 {
1139 hsd->Context = (SD_CONTEXT_WRITE_MULTIPLE_BLOCK| SD_CONTEXT_IT);
1140
1141 /* Write Multi Block command */
1142 errorstate = SDMMC_CmdWriteMultiBlock(hsd->Instance, add);
1143 }
1144 else
1145 {
1146 hsd->Context = (SD_CONTEXT_WRITE_SINGLE_BLOCK | SD_CONTEXT_IT);
1147
1148 /* Write Single Block command */
1149 errorstate = SDMMC_CmdWriteSingleBlock(hsd->Instance, add);
1150 }
1151 if(errorstate != HAL_SD_ERROR_NONE)
1152 {
1153 /* Clear all the static flags */
1154 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1155 hsd->ErrorCode |= errorstate;
1156 hsd->State = HAL_SD_STATE_READY;
1157 return HAL_ERROR;
1158 }
1159
1160 return HAL_OK;
1161 }
1162 else
1163 {
1164 return HAL_BUSY;
1165 }
1166 }
1167
1168 /**
1169 * @brief Reads block(s) from a specified address in a card. The Data transfer
1170 * is managed by DMA mode.
1171 * @note This API should be followed by a check on the card state through
1172 * HAL_SD_GetCardState().
1173 * @note You could also check the DMA transfer process through the SD Rx
1174 * interrupt event.
1175 * @param hsd: Pointer SD handle
1176 * @param pData: Pointer to the buffer that will contain the received data
1177 * @param BlockAdd: Block Address from where data is to be read
1178 * @param NumberOfBlocks: Number of blocks to read.
1179 * @retval HAL status
1180 */
HAL_SD_ReadBlocks_DMA(SD_HandleTypeDef * hsd,uint8_t * pData,uint32_t BlockAdd,uint32_t NumberOfBlocks)1181 HAL_StatusTypeDef HAL_SD_ReadBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, uint32_t BlockAdd, uint32_t NumberOfBlocks)
1182 {
1183 SDMMC_DataInitTypeDef config;
1184 uint32_t errorstate;
1185 uint32_t add = BlockAdd;
1186
1187 if(NULL == pData)
1188 {
1189 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
1190 return HAL_ERROR;
1191 }
1192
1193 if(hsd->State == HAL_SD_STATE_READY)
1194 {
1195 hsd->ErrorCode = HAL_SD_ERROR_NONE;
1196
1197 if((add + NumberOfBlocks) > (hsd->SdCard.LogBlockNbr))
1198 {
1199 hsd->ErrorCode |= HAL_SD_ERROR_ADDR_OUT_OF_RANGE;
1200 return HAL_ERROR;
1201 }
1202
1203 hsd->State = HAL_SD_STATE_BUSY;
1204
1205 /* Initialize data control register */
1206 hsd->Instance->DCTRL = 0U;
1207
1208 hsd->pRxBuffPtr = pData;
1209 hsd->RxXferSize = BLOCKSIZE * NumberOfBlocks;
1210
1211 if(hsd->SdCard.CardType != CARD_SDHC_SDXC)
1212 {
1213 add *= 512U;
1214 }
1215
1216 /* Set Block Size for Card */
1217 errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE);
1218 if(errorstate != HAL_SD_ERROR_NONE)
1219 {
1220 /* Clear all the static flags */
1221 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1222 hsd->ErrorCode |= errorstate;
1223 hsd->State = HAL_SD_STATE_READY;
1224 return HAL_ERROR;
1225 }
1226
1227 /* Configure the SD DPSM (Data Path State Machine) */
1228 config.DataTimeOut = SDMMC_DATATIMEOUT;
1229 config.DataLength = BLOCKSIZE * NumberOfBlocks;
1230 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_512B;
1231 config.TransferDir = SDMMC_TRANSFER_DIR_TO_SDMMC;
1232 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
1233 config.DPSM = SDMMC_DPSM_DISABLE;
1234 (void)SDMMC_ConfigData(hsd->Instance, &config);
1235
1236 /* Enable transfer interrupts */
1237 __HAL_SD_ENABLE_IT(hsd, (SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT | SDMMC_IT_RXOVERR | SDMMC_IT_DATAEND));
1238
1239 __SDMMC_CMDTRANS_ENABLE( hsd->Instance);
1240 hsd->Instance->IDMACTRL = SDMMC_ENABLE_IDMA_SINGLE_BUFF;
1241 hsd->Instance->IDMABASE0 = (uint32_t) pData ;
1242
1243 /* Read Blocks in DMA mode */
1244 if(NumberOfBlocks > 1U)
1245 {
1246 hsd->Context = (SD_CONTEXT_READ_MULTIPLE_BLOCK | SD_CONTEXT_DMA);
1247
1248 /* Read Multi Block command */
1249 errorstate = SDMMC_CmdReadMultiBlock(hsd->Instance, add);
1250 }
1251 else
1252 {
1253 hsd->Context = (SD_CONTEXT_READ_SINGLE_BLOCK | SD_CONTEXT_DMA);
1254
1255 /* Read Single Block command */
1256 errorstate = SDMMC_CmdReadSingleBlock(hsd->Instance, add);
1257 }
1258 if(errorstate != HAL_SD_ERROR_NONE)
1259 {
1260 /* Clear all the static flags */
1261 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1262 __HAL_SD_DISABLE_IT(hsd, (SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT | SDMMC_IT_RXOVERR | SDMMC_IT_DATAEND));
1263 hsd->ErrorCode |= errorstate;
1264 hsd->State = HAL_SD_STATE_READY;
1265 return HAL_ERROR;
1266 }
1267
1268 return HAL_OK;
1269 }
1270 else
1271 {
1272 return HAL_BUSY;
1273 }
1274 }
1275
1276 /**
1277 * @brief Writes block(s) to a specified address in a card. The Data transfer
1278 * is managed by DMA mode.
1279 * @note This API should be followed by a check on the card state through
1280 * HAL_SD_GetCardState().
1281 * @note You could also check the DMA transfer process through the SD Tx
1282 * interrupt event.
1283 * @param hsd: Pointer to SD handle
1284 * @param pData: Pointer to the buffer that will contain the data to transmit
1285 * @param BlockAdd: Block Address where data will be written
1286 * @param NumberOfBlocks: Number of blocks to write
1287 * @retval HAL status
1288 */
HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef * hsd,uint8_t * pData,uint32_t BlockAdd,uint32_t NumberOfBlocks)1289 HAL_StatusTypeDef HAL_SD_WriteBlocks_DMA(SD_HandleTypeDef *hsd, uint8_t *pData, uint32_t BlockAdd, uint32_t NumberOfBlocks)
1290 {
1291 SDMMC_DataInitTypeDef config;
1292 uint32_t errorstate;
1293 uint32_t add = BlockAdd;
1294
1295 if(NULL == pData)
1296 {
1297 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
1298 return HAL_ERROR;
1299 }
1300
1301 if(hsd->State == HAL_SD_STATE_READY)
1302 {
1303 hsd->ErrorCode = HAL_SD_ERROR_NONE;
1304
1305 if((add + NumberOfBlocks) > (hsd->SdCard.LogBlockNbr))
1306 {
1307 hsd->ErrorCode |= HAL_SD_ERROR_ADDR_OUT_OF_RANGE;
1308 return HAL_ERROR;
1309 }
1310
1311 hsd->State = HAL_SD_STATE_BUSY;
1312
1313 /* Initialize data control register */
1314 hsd->Instance->DCTRL = 0U;
1315
1316 hsd->pTxBuffPtr = pData;
1317 hsd->TxXferSize = BLOCKSIZE * NumberOfBlocks;
1318
1319 if(hsd->SdCard.CardType != CARD_SDHC_SDXC)
1320 {
1321 add *= 512U;
1322 }
1323
1324 /* Set Block Size for Card */
1325 errorstate = SDMMC_CmdBlockLength(hsd->Instance, BLOCKSIZE);
1326 if(errorstate != HAL_SD_ERROR_NONE)
1327 {
1328 /* Clear all the static flags */
1329 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1330 hsd->ErrorCode |= errorstate;
1331 hsd->State = HAL_SD_STATE_READY;
1332 return HAL_ERROR;
1333 }
1334 /* Configure the SD DPSM (Data Path State Machine) */
1335 config.DataTimeOut = SDMMC_DATATIMEOUT;
1336 config.DataLength = BLOCKSIZE * NumberOfBlocks;
1337 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_512B;
1338 config.TransferDir = SDMMC_TRANSFER_DIR_TO_CARD;
1339 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
1340 config.DPSM = SDMMC_DPSM_DISABLE;
1341 (void)SDMMC_ConfigData(hsd->Instance, &config);
1342
1343 /* Enable transfer interrupts */
1344 __HAL_SD_ENABLE_IT(hsd, (SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT | SDMMC_IT_TXUNDERR | SDMMC_IT_DATAEND));
1345
1346 __SDMMC_CMDTRANS_ENABLE( hsd->Instance);
1347
1348 hsd->Instance->IDMACTRL = SDMMC_ENABLE_IDMA_SINGLE_BUFF;
1349 hsd->Instance->IDMABASE0 = (uint32_t) pData ;
1350
1351 /* Write Blocks in Polling mode */
1352 if(NumberOfBlocks > 1U)
1353 {
1354 hsd->Context = (SD_CONTEXT_WRITE_MULTIPLE_BLOCK | SD_CONTEXT_DMA);
1355
1356 /* Write Multi Block command */
1357 errorstate = SDMMC_CmdWriteMultiBlock(hsd->Instance, add);
1358 }
1359 else
1360 {
1361 hsd->Context = (SD_CONTEXT_WRITE_SINGLE_BLOCK | SD_CONTEXT_DMA);
1362
1363 /* Write Single Block command */
1364 errorstate = SDMMC_CmdWriteSingleBlock(hsd->Instance, add);
1365 }
1366 if(errorstate != HAL_SD_ERROR_NONE)
1367 {
1368 /* Clear all the static flags */
1369 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1370 __HAL_SD_DISABLE_IT(hsd, (SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT | SDMMC_IT_TXUNDERR | SDMMC_IT_DATAEND));
1371 hsd->ErrorCode |= errorstate;
1372 hsd->State = HAL_SD_STATE_READY;
1373 return HAL_ERROR;
1374 }
1375
1376 return HAL_OK;
1377 }
1378 else
1379 {
1380 return HAL_BUSY;
1381 }
1382 }
1383
1384 /**
1385 * @brief Erases the specified memory area of the given SD card.
1386 * @note This API should be followed by a check on the card state through
1387 * HAL_SD_GetCardState().
1388 * @param hsd: Pointer to SD handle
1389 * @param BlockStartAdd: Start Block address
1390 * @param BlockEndAdd: End Block address
1391 * @retval HAL status
1392 */
HAL_SD_Erase(SD_HandleTypeDef * hsd,uint32_t BlockStartAdd,uint32_t BlockEndAdd)1393 HAL_StatusTypeDef HAL_SD_Erase(SD_HandleTypeDef *hsd, uint32_t BlockStartAdd, uint32_t BlockEndAdd)
1394 {
1395 uint32_t errorstate;
1396 uint32_t start_add = BlockStartAdd;
1397 uint32_t end_add = BlockEndAdd;
1398
1399 if(hsd->State == HAL_SD_STATE_READY)
1400 {
1401 hsd->ErrorCode = HAL_SD_ERROR_NONE;
1402
1403 if(end_add < start_add)
1404 {
1405 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
1406 return HAL_ERROR;
1407 }
1408
1409 if(end_add > (hsd->SdCard.LogBlockNbr))
1410 {
1411 hsd->ErrorCode |= HAL_SD_ERROR_ADDR_OUT_OF_RANGE;
1412 return HAL_ERROR;
1413 }
1414
1415 hsd->State = HAL_SD_STATE_BUSY;
1416
1417 /* Check if the card command class supports erase command */
1418 if(((hsd->SdCard.Class) & SDMMC_CCCC_ERASE) == 0U)
1419 {
1420 /* Clear all the static flags */
1421 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1422 hsd->ErrorCode |= HAL_SD_ERROR_REQUEST_NOT_APPLICABLE;
1423 hsd->State = HAL_SD_STATE_READY;
1424 return HAL_ERROR;
1425 }
1426
1427 if((SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1) & SDMMC_CARD_LOCKED) == SDMMC_CARD_LOCKED)
1428 {
1429 /* Clear all the static flags */
1430 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1431 hsd->ErrorCode |= HAL_SD_ERROR_LOCK_UNLOCK_FAILED;
1432 hsd->State = HAL_SD_STATE_READY;
1433 return HAL_ERROR;
1434 }
1435
1436 /* Get start and end block for high capacity cards */
1437 if(hsd->SdCard.CardType != CARD_SDHC_SDXC)
1438 {
1439 start_add *= 512U;
1440 end_add *= 512U;
1441 }
1442
1443 /* According to sd-card spec 1.0 ERASE_GROUP_START (CMD32) and erase_group_end(CMD33) */
1444 if(hsd->SdCard.CardType != CARD_SECURED)
1445 {
1446 /* Send CMD32 SD_ERASE_GRP_START with argument as addr */
1447 errorstate = SDMMC_CmdSDEraseStartAdd(hsd->Instance, start_add);
1448 if(errorstate != HAL_SD_ERROR_NONE)
1449 {
1450 /* Clear all the static flags */
1451 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1452 hsd->ErrorCode |= errorstate;
1453 hsd->State = HAL_SD_STATE_READY;
1454 return HAL_ERROR;
1455 }
1456
1457 /* Send CMD33 SD_ERASE_GRP_END with argument as addr */
1458 errorstate = SDMMC_CmdSDEraseEndAdd(hsd->Instance, end_add);
1459 if(errorstate != HAL_SD_ERROR_NONE)
1460 {
1461 /* Clear all the static flags */
1462 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1463 hsd->ErrorCode |= errorstate;
1464 hsd->State = HAL_SD_STATE_READY;
1465 return HAL_ERROR;
1466 }
1467 }
1468
1469 /* Send CMD38 ERASE */
1470 errorstate = SDMMC_CmdErase(hsd->Instance);
1471 if(errorstate != HAL_SD_ERROR_NONE)
1472 {
1473 /* Clear all the static flags */
1474 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
1475 hsd->ErrorCode |= errorstate;
1476 hsd->State = HAL_SD_STATE_READY;
1477 return HAL_ERROR;
1478 }
1479
1480 hsd->State = HAL_SD_STATE_READY;
1481
1482 return HAL_OK;
1483 }
1484 else
1485 {
1486 return HAL_BUSY;
1487 }
1488 }
1489
1490 /**
1491 * @brief This function handles SD card interrupt request.
1492 * @param hsd: Pointer to SD handle
1493 * @retval None
1494 */
HAL_SD_IRQHandler(SD_HandleTypeDef * hsd)1495 void HAL_SD_IRQHandler(SD_HandleTypeDef *hsd)
1496 {
1497 uint32_t errorstate;
1498 uint32_t context = hsd->Context;
1499
1500 /* Check for SDMMC interrupt flags */
1501 if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_DATAEND) != RESET)
1502 {
1503 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DATAEND);
1504
1505 __HAL_SD_DISABLE_IT(hsd, SDMMC_IT_DATAEND | SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT |\
1506 SDMMC_IT_TXUNDERR | SDMMC_IT_RXOVERR | SDMMC_IT_TXFIFOHE |\
1507 SDMMC_IT_RXFIFOHF);
1508
1509 __HAL_SD_DISABLE_IT(hsd, SDMMC_IT_IDMABTC);
1510 __SDMMC_CMDTRANS_DISABLE( hsd->Instance);
1511
1512 if((context & SD_CONTEXT_IT) != 0U)
1513 {
1514 if(((context & SD_CONTEXT_READ_MULTIPLE_BLOCK) != 0U) || ((context & SD_CONTEXT_WRITE_MULTIPLE_BLOCK) != 0U))
1515 {
1516 errorstate = SDMMC_CmdStopTransfer(hsd->Instance);
1517 if(errorstate != HAL_SD_ERROR_NONE)
1518 {
1519 hsd->ErrorCode |= errorstate;
1520 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1521 hsd->ErrorCallback(hsd);
1522 #else
1523 HAL_SD_ErrorCallback(hsd);
1524 #endif
1525 }
1526 }
1527
1528 /* Clear all the static flags */
1529 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
1530
1531 hsd->State = HAL_SD_STATE_READY;
1532 if(((context & SD_CONTEXT_READ_SINGLE_BLOCK) != 0U) || ((context & SD_CONTEXT_READ_MULTIPLE_BLOCK) != 0U))
1533 {
1534 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1535 hsd->RxCpltCallback(hsd);
1536 #else
1537 HAL_SD_RxCpltCallback(hsd);
1538 #endif
1539 }
1540 else
1541 {
1542 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1543 hsd->TxCpltCallback(hsd);
1544 #else
1545 HAL_SD_TxCpltCallback(hsd);
1546 #endif
1547 }
1548 }
1549 else if((context & SD_CONTEXT_DMA) != 0U)
1550 {
1551 hsd->Instance->DLEN = 0;
1552 hsd->Instance->DCTRL = 0;
1553 hsd->Instance->IDMACTRL = SDMMC_DISABLE_IDMA;
1554
1555 /* Stop Transfer for Write Single/Multi blocks or Read Multi blocks */
1556 if((context & SD_CONTEXT_READ_SINGLE_BLOCK) == 0U)
1557 {
1558 errorstate = SDMMC_CmdStopTransfer(hsd->Instance);
1559 if(errorstate != HAL_SD_ERROR_NONE)
1560 {
1561 hsd->ErrorCode |= errorstate;
1562 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1563 hsd->ErrorCallback(hsd);
1564 #else
1565 HAL_SD_ErrorCallback(hsd);
1566 #endif
1567 }
1568 }
1569
1570 hsd->State = HAL_SD_STATE_READY;
1571 if(((context & SD_CONTEXT_WRITE_SINGLE_BLOCK) != 0U) || ((context & SD_CONTEXT_WRITE_MULTIPLE_BLOCK) != 0U))
1572 {
1573 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1574 hsd->TxCpltCallback(hsd);
1575 #else
1576 HAL_SD_TxCpltCallback(hsd);
1577 #endif
1578 }
1579 if(((context & SD_CONTEXT_READ_SINGLE_BLOCK) != 0U) || ((context & SD_CONTEXT_READ_MULTIPLE_BLOCK) != 0U))
1580 {
1581 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1582 hsd->RxCpltCallback(hsd);
1583 #else
1584 HAL_SD_RxCpltCallback(hsd);
1585 #endif
1586 }
1587 }
1588 else
1589 {
1590 /* Nothing to do */
1591 }
1592 }
1593
1594 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_TXFIFOHE) != RESET)
1595 {
1596 SD_Write_IT(hsd);
1597 }
1598
1599 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_RXFIFOHF) != RESET)
1600 {
1601 SD_Read_IT(hsd);
1602 }
1603
1604 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT | SDMMC_IT_RXOVERR | SDMMC_IT_TXUNDERR) != RESET)
1605 {
1606 /* Set Error code */
1607 if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_DCRCFAIL) != RESET)
1608 {
1609 hsd->ErrorCode |= HAL_SD_ERROR_DATA_CRC_FAIL;
1610 }
1611 if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_DTIMEOUT) != RESET)
1612 {
1613 hsd->ErrorCode |= HAL_SD_ERROR_DATA_TIMEOUT;
1614 }
1615 if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_RXOVERR) != RESET)
1616 {
1617 hsd->ErrorCode |= HAL_SD_ERROR_RX_OVERRUN;
1618 }
1619 if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_TXUNDERR) != RESET)
1620 {
1621 hsd->ErrorCode |= HAL_SD_ERROR_TX_UNDERRUN;
1622 }
1623
1624 /* Clear All flags */
1625 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
1626
1627 /* Disable all interrupts */
1628 __HAL_SD_DISABLE_IT(hsd, SDMMC_IT_DATAEND | SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT|\
1629 SDMMC_IT_TXUNDERR| SDMMC_IT_RXOVERR);
1630
1631 __SDMMC_CMDTRANS_DISABLE( hsd->Instance);
1632 hsd->Instance->DCTRL |= SDMMC_DCTRL_FIFORST;
1633 hsd->Instance->CMD |= SDMMC_CMD_CMDSTOP;
1634 hsd->ErrorCode |= SDMMC_CmdStopTransfer(hsd->Instance);
1635 hsd->Instance->CMD &= ~(SDMMC_CMD_CMDSTOP);
1636 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DABORT);
1637
1638 if((context & SD_CONTEXT_IT) != 0U)
1639 {
1640 /* Set the SD state to ready to be able to start again the process */
1641 hsd->State = HAL_SD_STATE_READY;
1642 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1643 hsd->ErrorCallback(hsd);
1644 #else
1645 HAL_SD_ErrorCallback(hsd);
1646 #endif
1647 }
1648 else if((context & SD_CONTEXT_DMA) != 0U)
1649 {
1650 if(hsd->ErrorCode != HAL_SD_ERROR_NONE)
1651 {
1652 /* Disable Internal DMA */
1653 __HAL_SD_DISABLE_IT(hsd, SDMMC_IT_IDMABTC);
1654 hsd->Instance->IDMACTRL = SDMMC_DISABLE_IDMA;
1655
1656 /* Set the SD state to ready to be able to start again the process */
1657 hsd->State = HAL_SD_STATE_READY;
1658 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1659 hsd->ErrorCallback(hsd);
1660 #else
1661 HAL_SD_ErrorCallback(hsd);
1662 #endif
1663 }
1664 }
1665 else
1666 {
1667 /* Nothing to do */
1668 }
1669 }
1670
1671 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_IT_IDMABTC) != RESET)
1672 {
1673 if(READ_BIT(hsd->Instance->IDMACTRL, SDMMC_IDMA_IDMABACT) == 0U)
1674 {
1675 /* Current buffer is buffer0, Transfer complete for buffer1 */
1676 if((hsd->Context & SD_CONTEXT_WRITE_MULTIPLE_BLOCK) != 0U)
1677 {
1678 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1679 hsd->Write_DMADblBuf1CpltCallback(hsd);
1680 #else
1681 HAL_SDEx_Write_DMADoubleBuffer1CpltCallback(hsd);
1682 #endif
1683 }
1684 else /* SD_CONTEXT_READ_MULTIPLE_BLOCK */
1685 {
1686 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1687 hsd->Read_DMADblBuf1CpltCallback(hsd);
1688 #else
1689 HAL_SDEx_Read_DMADoubleBuffer1CpltCallback(hsd);
1690 #endif
1691 }
1692 }
1693 else /* SD_DMA_BUFFER1 */
1694 {
1695 /* Current buffer is buffer1, Transfer complete for buffer0 */
1696 if((context & SD_CONTEXT_WRITE_MULTIPLE_BLOCK) != 0U)
1697 {
1698 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1699 hsd->Write_DMADblBuf0CpltCallback(hsd);
1700 #else
1701 HAL_SDEx_Write_DMADoubleBuffer0CpltCallback(hsd);
1702 #endif
1703 }
1704 else /* SD_CONTEXT_READ_MULTIPLE_BLOCK */
1705 {
1706 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1707 hsd->Read_DMADblBuf0CpltCallback(hsd);
1708 #else
1709 HAL_SDEx_Read_DMADoubleBuffer0CpltCallback(hsd);
1710 #endif
1711 }
1712 }
1713 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_IDMABTC);
1714 }
1715 else
1716 {
1717 /* Nothing to do */
1718 }
1719 }
1720
1721 /**
1722 * @brief return the SD state
1723 * @param hsd: Pointer to sd handle
1724 * @retval HAL state
1725 */
HAL_SD_GetState(SD_HandleTypeDef * hsd)1726 HAL_SD_StateTypeDef HAL_SD_GetState(SD_HandleTypeDef *hsd)
1727 {
1728 return hsd->State;
1729 }
1730
1731 /**
1732 * @brief Return the SD error code
1733 * @param hsd : Pointer to a SD_HandleTypeDef structure that contains
1734 * the configuration information.
1735 * @retval SD Error Code
1736 */
HAL_SD_GetError(SD_HandleTypeDef * hsd)1737 uint32_t HAL_SD_GetError(SD_HandleTypeDef *hsd)
1738 {
1739 return hsd->ErrorCode;
1740 }
1741
1742 /**
1743 * @brief Tx Transfer completed callbacks
1744 * @param hsd: Pointer to SD handle
1745 * @retval None
1746 */
HAL_SD_TxCpltCallback(SD_HandleTypeDef * hsd)1747 __weak void HAL_SD_TxCpltCallback(SD_HandleTypeDef *hsd)
1748 {
1749 /* Prevent unused argument(s) compilation warning */
1750 UNUSED(hsd);
1751
1752 /* NOTE : This function should not be modified, when the callback is needed,
1753 the HAL_SD_TxCpltCallback can be implemented in the user file
1754 */
1755 }
1756
1757 /**
1758 * @brief Rx Transfer completed callbacks
1759 * @param hsd: Pointer SD handle
1760 * @retval None
1761 */
HAL_SD_RxCpltCallback(SD_HandleTypeDef * hsd)1762 __weak void HAL_SD_RxCpltCallback(SD_HandleTypeDef *hsd)
1763 {
1764 /* Prevent unused argument(s) compilation warning */
1765 UNUSED(hsd);
1766
1767 /* NOTE : This function should not be modified, when the callback is needed,
1768 the HAL_SD_RxCpltCallback can be implemented in the user file
1769 */
1770 }
1771
1772 /**
1773 * @brief SD error callbacks
1774 * @param hsd: Pointer SD handle
1775 * @retval None
1776 */
HAL_SD_ErrorCallback(SD_HandleTypeDef * hsd)1777 __weak void HAL_SD_ErrorCallback(SD_HandleTypeDef *hsd)
1778 {
1779 /* Prevent unused argument(s) compilation warning */
1780 UNUSED(hsd);
1781
1782 /* NOTE : This function should not be modified, when the callback is needed,
1783 the HAL_SD_ErrorCallback can be implemented in the user file
1784 */
1785 }
1786
1787 /**
1788 * @brief SD Abort callbacks
1789 * @param hsd: Pointer SD handle
1790 * @retval None
1791 */
HAL_SD_AbortCallback(SD_HandleTypeDef * hsd)1792 __weak void HAL_SD_AbortCallback(SD_HandleTypeDef *hsd)
1793 {
1794 /* Prevent unused argument(s) compilation warning */
1795 UNUSED(hsd);
1796
1797 /* NOTE : This function should not be modified, when the callback is needed,
1798 the HAL_SD_AbortCallback can be implemented in the user file
1799 */
1800 }
1801
1802 #if (USE_SD_TRANSCEIVER != 0U)
1803 /**
1804 * @brief Enable/Disable the SD Transceiver 1.8V Mode Callback.
1805 * @param status: Voltage Switch State
1806 * @retval None
1807 */
HAL_SD_DriveTransceiver_1_8V_Callback(FlagStatus status)1808 __weak void HAL_SD_DriveTransceiver_1_8V_Callback(FlagStatus status)
1809 {
1810
1811 /* NOTE : This function should not be modified, when the callback is needed,
1812 the HAL_SD_EnableTransceiver could be implemented in the user file
1813 */
1814 }
1815 #endif /* USE_SD_TRANSCEIVER */
1816
1817 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
1818 /**
1819 * @brief Register a User SD Callback
1820 * To be used instead of the weak (surcharged) predefined callback
1821 * @param hsd : SD handle
1822 * @param CallbackID : ID of the callback to be registered
1823 * This parameter can be one of the following values:
1824 * @arg @ref HAL_SD_TX_CPLT_CB_ID SD Tx Complete Callback ID
1825 * @arg @ref HAL_SD_RX_CPLT_CB_ID SD Rx Complete Callback ID
1826 * @arg @ref HAL_SD_ERROR_CB_ID SD Error Callback ID
1827 * @arg @ref HAL_SD_ABORT_CB_ID SD Abort Callback ID
1828 * @arg @ref HAL_SD_READ_DMA_DBL_BUF0_CPLT_CB_ID SD DMA Rx Double buffer 0 Callback ID
1829 * @arg @ref HAL_SD_READ_DMA_DBL_BUF1_CPLT_CB_ID SD DMA Rx Double buffer 1 Callback ID
1830 * @arg @ref HAL_SD_WRITE_DMA_DBL_BUF0_CPLT_CB_ID SD DMA Tx Double buffer 0 Callback ID
1831 * @arg @ref HAL_SD_WRITE_DMA_DBL_BUF1_CPLT_CB_ID SD DMA Tx Double buffer 1 Callback ID
1832 * @arg @ref HAL_SD_MSP_INIT_CB_ID SD MspInit Callback ID
1833 * @arg @ref HAL_SD_MSP_DEINIT_CB_ID SD MspDeInit Callback ID
1834 * @param pCallback : pointer to the Callback function
1835 * @retval status
1836 */
HAL_SD_RegisterCallback(SD_HandleTypeDef * hsd,HAL_SD_CallbackIDTypeDef CallbackID,pSD_CallbackTypeDef pCallback)1837 HAL_StatusTypeDef HAL_SD_RegisterCallback(SD_HandleTypeDef *hsd, HAL_SD_CallbackIDTypeDef CallbackID, pSD_CallbackTypeDef pCallback)
1838 {
1839 HAL_StatusTypeDef status = HAL_OK;
1840
1841 if(pCallback == NULL)
1842 {
1843 /* Update the error code */
1844 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
1845 return HAL_ERROR;
1846 }
1847
1848 /* Process locked */
1849 __HAL_LOCK(hsd);
1850
1851 if(hsd->State == HAL_SD_STATE_READY)
1852 {
1853 switch (CallbackID)
1854 {
1855 case HAL_SD_TX_CPLT_CB_ID :
1856 hsd->TxCpltCallback = pCallback;
1857 break;
1858 case HAL_SD_RX_CPLT_CB_ID :
1859 hsd->RxCpltCallback = pCallback;
1860 break;
1861 case HAL_SD_ERROR_CB_ID :
1862 hsd->ErrorCallback = pCallback;
1863 break;
1864 case HAL_SD_ABORT_CB_ID :
1865 hsd->AbortCpltCallback = pCallback;
1866 break;
1867 case HAL_SD_READ_DMA_DBL_BUF0_CPLT_CB_ID :
1868 hsd->Read_DMADblBuf0CpltCallback = pCallback;
1869 break;
1870 case HAL_SD_READ_DMA_DBL_BUF1_CPLT_CB_ID :
1871 hsd->Read_DMADblBuf1CpltCallback = pCallback;
1872 break;
1873 case HAL_SD_WRITE_DMA_DBL_BUF0_CPLT_CB_ID :
1874 hsd->Write_DMADblBuf0CpltCallback = pCallback;
1875 break;
1876 case HAL_SD_WRITE_DMA_DBL_BUF1_CPLT_CB_ID :
1877 hsd->Write_DMADblBuf1CpltCallback = pCallback;
1878 break;
1879 case HAL_SD_MSP_INIT_CB_ID :
1880 hsd->MspInitCallback = pCallback;
1881 break;
1882 case HAL_SD_MSP_DEINIT_CB_ID :
1883 hsd->MspDeInitCallback = pCallback;
1884 break;
1885 default :
1886 /* Update the error code */
1887 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
1888 /* update return status */
1889 status = HAL_ERROR;
1890 break;
1891 }
1892 }
1893 else if (hsd->State == HAL_SD_STATE_RESET)
1894 {
1895 switch (CallbackID)
1896 {
1897 case HAL_SD_MSP_INIT_CB_ID :
1898 hsd->MspInitCallback = pCallback;
1899 break;
1900 case HAL_SD_MSP_DEINIT_CB_ID :
1901 hsd->MspDeInitCallback = pCallback;
1902 break;
1903 default :
1904 /* Update the error code */
1905 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
1906 /* update return status */
1907 status = HAL_ERROR;
1908 break;
1909 }
1910 }
1911 else
1912 {
1913 /* Update the error code */
1914 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
1915 /* update return status */
1916 status = HAL_ERROR;
1917 }
1918
1919 /* Release Lock */
1920 __HAL_UNLOCK(hsd);
1921 return status;
1922 }
1923
1924 /**
1925 * @brief Unregister a User SD Callback
1926 * SD Callback is redirected to the weak (surcharged) predefined callback
1927 * @param hsd : SD handle
1928 * @param CallbackID : ID of the callback to be unregistered
1929 * This parameter can be one of the following values:
1930 * @arg @ref HAL_SD_TX_CPLT_CB_ID SD Tx Complete Callback ID
1931 * @arg @ref HAL_SD_RX_CPLT_CB_ID SD Rx Complete Callback ID
1932 * @arg @ref HAL_SD_ERROR_CB_ID SD Error Callback ID
1933 * @arg @ref HAL_SD_ABORT_CB_ID SD Abort Callback ID
1934 * @arg @ref HAL_SD_READ_DMA_DBL_BUF0_CPLT_CB_ID SD DMA Rx Double buffer 0 Callback ID
1935 * @arg @ref HAL_SD_READ_DMA_DBL_BUF1_CPLT_CB_ID SD DMA Rx Double buffer 1 Callback ID
1936 * @arg @ref HAL_SD_WRITE_DMA_DBL_BUF0_CPLT_CB_ID SD DMA Tx Double buffer 0 Callback ID
1937 * @arg @ref HAL_SD_WRITE_DMA_DBL_BUF1_CPLT_CB_ID SD DMA Tx Double buffer 1 Callback ID
1938 * @arg @ref HAL_SD_MSP_INIT_CB_ID SD MspInit Callback ID
1939 * @arg @ref HAL_SD_MSP_DEINIT_CB_ID SD MspDeInit Callback ID
1940 * @retval status
1941 */
HAL_SD_UnRegisterCallback(SD_HandleTypeDef * hsd,HAL_SD_CallbackIDTypeDef CallbackID)1942 HAL_StatusTypeDef HAL_SD_UnRegisterCallback(SD_HandleTypeDef *hsd, HAL_SD_CallbackIDTypeDef CallbackID)
1943 {
1944 HAL_StatusTypeDef status = HAL_OK;
1945
1946 /* Process locked */
1947 __HAL_LOCK(hsd);
1948
1949 if(hsd->State == HAL_SD_STATE_READY)
1950 {
1951 switch (CallbackID)
1952 {
1953 case HAL_SD_TX_CPLT_CB_ID :
1954 hsd->TxCpltCallback = HAL_SD_TxCpltCallback;
1955 break;
1956 case HAL_SD_RX_CPLT_CB_ID :
1957 hsd->RxCpltCallback = HAL_SD_RxCpltCallback;
1958 break;
1959 case HAL_SD_ERROR_CB_ID :
1960 hsd->ErrorCallback = HAL_SD_ErrorCallback;
1961 break;
1962 case HAL_SD_ABORT_CB_ID :
1963 hsd->AbortCpltCallback = HAL_SD_AbortCallback;
1964 break;
1965 case HAL_SD_READ_DMA_DBL_BUF0_CPLT_CB_ID :
1966 hsd->Read_DMADblBuf0CpltCallback = HAL_SDEx_Read_DMADoubleBuffer0CpltCallback;
1967 break;
1968 case HAL_SD_READ_DMA_DBL_BUF1_CPLT_CB_ID :
1969 hsd->Read_DMADblBuf1CpltCallback = HAL_SDEx_Read_DMADoubleBuffer1CpltCallback;
1970 break;
1971 case HAL_SD_WRITE_DMA_DBL_BUF0_CPLT_CB_ID :
1972 hsd->Write_DMADblBuf0CpltCallback = HAL_SDEx_Write_DMADoubleBuffer0CpltCallback;
1973 break;
1974 case HAL_SD_WRITE_DMA_DBL_BUF1_CPLT_CB_ID :
1975 hsd->Write_DMADblBuf1CpltCallback = HAL_SDEx_Write_DMADoubleBuffer1CpltCallback;
1976 break;
1977 case HAL_SD_MSP_INIT_CB_ID :
1978 hsd->MspInitCallback = HAL_SD_MspInit;
1979 break;
1980 case HAL_SD_MSP_DEINIT_CB_ID :
1981 hsd->MspDeInitCallback = HAL_SD_MspDeInit;
1982 break;
1983 default :
1984 /* Update the error code */
1985 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
1986 /* update return status */
1987 status = HAL_ERROR;
1988 break;
1989 }
1990 }
1991 else if (hsd->State == HAL_SD_STATE_RESET)
1992 {
1993 switch (CallbackID)
1994 {
1995 case HAL_SD_MSP_INIT_CB_ID :
1996 hsd->MspInitCallback = HAL_SD_MspInit;
1997 break;
1998 case HAL_SD_MSP_DEINIT_CB_ID :
1999 hsd->MspDeInitCallback = HAL_SD_MspDeInit;
2000 break;
2001 default :
2002 /* Update the error code */
2003 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
2004 /* update return status */
2005 status = HAL_ERROR;
2006 break;
2007 }
2008 }
2009 else
2010 {
2011 /* Update the error code */
2012 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
2013 /* update return status */
2014 status = HAL_ERROR;
2015 }
2016
2017 /* Release Lock */
2018 __HAL_UNLOCK(hsd);
2019 return status;
2020 }
2021
2022 #if (USE_SD_TRANSCEIVER != 0U)
2023 /**
2024 * @brief Register a User SD Transceiver Callback
2025 * To be used instead of the weak (surcharged) predefined callback
2026 * @param hsd : SD handle
2027 * @param pCallback : pointer to the Callback function
2028 * @retval status
2029 */
HAL_SD_RegisterTransceiverCallback(SD_HandleTypeDef * hsd,pSD_TransceiverCallbackTypeDef pCallback)2030 HAL_StatusTypeDef HAL_SD_RegisterTransceiverCallback(SD_HandleTypeDef *hsd, pSD_TransceiverCallbackTypeDef pCallback)
2031 {
2032 HAL_StatusTypeDef status = HAL_OK;
2033
2034 if(pCallback == NULL)
2035 {
2036 /* Update the error code */
2037 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
2038 return HAL_ERROR;
2039 }
2040
2041 /* Process locked */
2042 __HAL_LOCK(hsd);
2043
2044 if(hsd->State == HAL_SD_STATE_READY)
2045 {
2046 hsd->DriveTransceiver_1_8V_Callback = pCallback;
2047 }
2048 else
2049 {
2050 /* Update the error code */
2051 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
2052 /* update return status */
2053 status = HAL_ERROR;
2054 }
2055
2056 /* Release Lock */
2057 __HAL_UNLOCK(hsd);
2058 return status;
2059 }
2060
2061 /**
2062 * @brief Unregister a User SD Transceiver Callback
2063 * SD Callback is redirected to the weak (surcharged) predefined callback
2064 * @param hsd : SD handle
2065 * @retval status
2066 */
HAL_SD_UnRegisterTransceiverCallback(SD_HandleTypeDef * hsd)2067 HAL_StatusTypeDef HAL_SD_UnRegisterTransceiverCallback(SD_HandleTypeDef *hsd)
2068 {
2069 HAL_StatusTypeDef status = HAL_OK;
2070
2071 /* Process locked */
2072 __HAL_LOCK(hsd);
2073
2074 if(hsd->State == HAL_SD_STATE_READY)
2075 {
2076 hsd->DriveTransceiver_1_8V_Callback = HAL_SD_DriveTransceiver_1_8V_Callback;
2077 }
2078 else
2079 {
2080 /* Update the error code */
2081 hsd->ErrorCode |= HAL_SD_ERROR_INVALID_CALLBACK;
2082 /* update return status */
2083 status = HAL_ERROR;
2084 }
2085
2086 /* Release Lock */
2087 __HAL_UNLOCK(hsd);
2088 return status;
2089 }
2090 #endif
2091 #endif
2092
2093 /**
2094 * @}
2095 */
2096
2097 /** @addtogroup SD_Exported_Functions_Group3
2098 * @brief management functions
2099 *
2100 @verbatim
2101 ==============================================================================
2102 ##### Peripheral Control functions #####
2103 ==============================================================================
2104 [..]
2105 This subsection provides a set of functions allowing to control the SD card
2106 operations and get the related information
2107
2108 @endverbatim
2109 * @{
2110 */
2111
2112 /**
2113 * @brief Returns information the information of the card which are stored on
2114 * the CID register.
2115 * @param hsd: Pointer to SD handle
2116 * @param pCID: Pointer to a HAL_SD_CIDTypedef structure that
2117 * contains all CID register parameters
2118 * @retval HAL status
2119 */
HAL_SD_GetCardCID(SD_HandleTypeDef * hsd,HAL_SD_CardCIDTypedef * pCID)2120 HAL_StatusTypeDef HAL_SD_GetCardCID(SD_HandleTypeDef *hsd, HAL_SD_CardCIDTypedef *pCID)
2121 {
2122 pCID->ManufacturerID = (uint8_t)((hsd->CID[0] & 0xFF000000U) >> 24U);
2123
2124 pCID->OEM_AppliID = (uint16_t)((hsd->CID[0] & 0x00FFFF00U) >> 8U);
2125
2126 pCID->ProdName1 = (((hsd->CID[0] & 0x000000FFU) << 24U) | ((hsd->CID[1] & 0xFFFFFF00U) >> 8U));
2127
2128 pCID->ProdName2 = (uint8_t)(hsd->CID[1] & 0x000000FFU);
2129
2130 pCID->ProdRev = (uint8_t)((hsd->CID[2] & 0xFF000000U) >> 24U);
2131
2132 pCID->ProdSN = (((hsd->CID[2] & 0x00FFFFFFU) << 8U) | ((hsd->CID[3] & 0xFF000000U) >> 24U));
2133
2134 pCID->Reserved1 = (uint8_t)((hsd->CID[3] & 0x00F00000U) >> 20U);
2135
2136 pCID->ManufactDate = (uint16_t)((hsd->CID[3] & 0x000FFF00U) >> 8U);
2137
2138 pCID->CID_CRC = (uint8_t)((hsd->CID[3] & 0x000000FEU) >> 1U);
2139
2140 pCID->Reserved2 = 1U;
2141
2142 return HAL_OK;
2143 }
2144
2145 /**
2146 * @brief Returns information the information of the card which are stored on
2147 * the CSD register.
2148 * @param hsd: Pointer to SD handle
2149 * @param pCSD: Pointer to a HAL_SD_CardInfoTypedef structure that
2150 * contains all CSD register parameters
2151 * @retval HAL status
2152 */
HAL_SD_GetCardCSD(SD_HandleTypeDef * hsd,HAL_SD_CardCSDTypedef * pCSD)2153 HAL_StatusTypeDef HAL_SD_GetCardCSD(SD_HandleTypeDef *hsd, HAL_SD_CardCSDTypedef *pCSD)
2154 {
2155 pCSD->CSDStruct = (uint8_t)((hsd->CSD[0] & 0xC0000000U) >> 30U);
2156
2157 pCSD->SysSpecVersion = (uint8_t)((hsd->CSD[0] & 0x3C000000U) >> 26U);
2158
2159 pCSD->Reserved1 = (uint8_t)((hsd->CSD[0] & 0x03000000U) >> 24U);
2160
2161 pCSD->TAAC = (uint8_t)((hsd->CSD[0] & 0x00FF0000U) >> 16U);
2162
2163 pCSD->NSAC = (uint8_t)((hsd->CSD[0] & 0x0000FF00U) >> 8U);
2164
2165 pCSD->MaxBusClkFrec = (uint8_t)(hsd->CSD[0] & 0x000000FFU);
2166
2167 pCSD->CardComdClasses = (uint16_t)((hsd->CSD[1] & 0xFFF00000U) >> 20U);
2168
2169 pCSD->RdBlockLen = (uint8_t)((hsd->CSD[1] & 0x000F0000U) >> 16U);
2170
2171 pCSD->PartBlockRead = (uint8_t)((hsd->CSD[1] & 0x00008000U) >> 15U);
2172
2173 pCSD->WrBlockMisalign = (uint8_t)((hsd->CSD[1] & 0x00004000U) >> 14U);
2174
2175 pCSD->RdBlockMisalign = (uint8_t)((hsd->CSD[1] & 0x00002000U) >> 13U);
2176
2177 pCSD->DSRImpl = (uint8_t)((hsd->CSD[1] & 0x00001000U) >> 12U);
2178
2179 pCSD->Reserved2 = 0U; /*!< Reserved */
2180
2181 if(hsd->SdCard.CardType == CARD_SDSC)
2182 {
2183 pCSD->DeviceSize = (((hsd->CSD[1] & 0x000003FFU) << 2U) | ((hsd->CSD[2] & 0xC0000000U) >> 30U));
2184
2185 pCSD->MaxRdCurrentVDDMin = (uint8_t)((hsd->CSD[2] & 0x38000000U) >> 27U);
2186
2187 pCSD->MaxRdCurrentVDDMax = (uint8_t)((hsd->CSD[2] & 0x07000000U) >> 24U);
2188
2189 pCSD->MaxWrCurrentVDDMin = (uint8_t)((hsd->CSD[2] & 0x00E00000U) >> 21U);
2190
2191 pCSD->MaxWrCurrentVDDMax = (uint8_t)((hsd->CSD[2] & 0x001C0000U) >> 18U);
2192
2193 pCSD->DeviceSizeMul = (uint8_t)((hsd->CSD[2] & 0x00038000U) >> 15U);
2194
2195 hsd->SdCard.BlockNbr = (pCSD->DeviceSize + 1U) ;
2196 hsd->SdCard.BlockNbr *= (1UL << ((pCSD->DeviceSizeMul & 0x07U) + 2U));
2197 hsd->SdCard.BlockSize = (1UL << (pCSD->RdBlockLen & 0x0FU));
2198
2199 hsd->SdCard.LogBlockNbr = (hsd->SdCard.BlockNbr) * ((hsd->SdCard.BlockSize) / 512U);
2200 hsd->SdCard.LogBlockSize = 512U;
2201 }
2202 else if(hsd->SdCard.CardType == CARD_SDHC_SDXC)
2203 {
2204 /* Byte 7 */
2205 pCSD->DeviceSize = (((hsd->CSD[1] & 0x0000003FU) << 16U) | ((hsd->CSD[2] & 0xFFFF0000U) >> 16U));
2206
2207 hsd->SdCard.BlockNbr = ((pCSD->DeviceSize + 1U) * 1024U);
2208 hsd->SdCard.LogBlockNbr = hsd->SdCard.BlockNbr;
2209 hsd->SdCard.BlockSize = 512U;
2210 hsd->SdCard.LogBlockSize = hsd->SdCard.BlockSize;
2211 }
2212 else
2213 {
2214 /* Clear all the static flags */
2215 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
2216 hsd->ErrorCode |= HAL_SD_ERROR_UNSUPPORTED_FEATURE;
2217 hsd->State = HAL_SD_STATE_READY;
2218 return HAL_ERROR;
2219 }
2220
2221 pCSD->EraseGrSize = (uint8_t)((hsd->CSD[2] & 0x00004000U) >> 14U);
2222
2223 pCSD->EraseGrMul = (uint8_t)((hsd->CSD[2] & 0x00003F80U) >> 7U);
2224
2225 pCSD->WrProtectGrSize = (uint8_t)(hsd->CSD[2] & 0x0000007FU);
2226
2227 pCSD->WrProtectGrEnable = (uint8_t)((hsd->CSD[3] & 0x80000000U) >> 31U);
2228
2229 pCSD->ManDeflECC = (uint8_t)((hsd->CSD[3] & 0x60000000U) >> 29U);
2230
2231 pCSD->WrSpeedFact = (uint8_t)((hsd->CSD[3] & 0x1C000000U) >> 26U);
2232
2233 pCSD->MaxWrBlockLen= (uint8_t)((hsd->CSD[3] & 0x03C00000U) >> 22U);
2234
2235 pCSD->WriteBlockPaPartial = (uint8_t)((hsd->CSD[3] & 0x00200000U) >> 21U);
2236
2237 pCSD->Reserved3 = 0;
2238
2239 pCSD->ContentProtectAppli = (uint8_t)((hsd->CSD[3] & 0x00010000U) >> 16U);
2240
2241 pCSD->FileFormatGroup = (uint8_t)((hsd->CSD[3] & 0x00008000U) >> 15U);
2242
2243 pCSD->CopyFlag = (uint8_t)((hsd->CSD[3] & 0x00004000U) >> 14U);
2244
2245 pCSD->PermWrProtect = (uint8_t)((hsd->CSD[3] & 0x00002000U) >> 13U);
2246
2247 pCSD->TempWrProtect = (uint8_t)((hsd->CSD[3] & 0x00001000U) >> 12U);
2248
2249 pCSD->FileFormat = (uint8_t)((hsd->CSD[3] & 0x00000C00U) >> 10U);
2250
2251 pCSD->ECC= (uint8_t)((hsd->CSD[3] & 0x00000300U) >> 8U);
2252
2253 pCSD->CSD_CRC = (uint8_t)((hsd->CSD[3] & 0x000000FEU) >> 1U);
2254
2255 pCSD->Reserved4 = 1;
2256
2257 return HAL_OK;
2258 }
2259
2260 /**
2261 * @brief Gets the SD status info.
2262 * @param hsd: Pointer to SD handle
2263 * @param pStatus: Pointer to the HAL_SD_CardStatusTypedef structure that
2264 * will contain the SD card status information
2265 * @retval HAL status
2266 */
HAL_SD_GetCardStatus(SD_HandleTypeDef * hsd,HAL_SD_CardStatusTypedef * pStatus)2267 HAL_StatusTypeDef HAL_SD_GetCardStatus(SD_HandleTypeDef *hsd, HAL_SD_CardStatusTypedef *pStatus)
2268 {
2269 uint32_t sd_status[16];
2270 uint32_t errorstate;
2271
2272 errorstate = SD_SendSDStatus(hsd, sd_status);
2273 if(errorstate != HAL_SD_ERROR_NONE)
2274 {
2275 /* Clear all the static flags */
2276 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
2277 hsd->ErrorCode |= errorstate;
2278 hsd->State = HAL_SD_STATE_READY;
2279 return HAL_ERROR;
2280 }
2281 else
2282 {
2283 pStatus->DataBusWidth = (uint8_t)((sd_status[0] & 0xC0U) >> 6U);
2284
2285 pStatus->SecuredMode = (uint8_t)((sd_status[0] & 0x20U) >> 5U);
2286
2287 pStatus->CardType = (uint16_t)(((sd_status[0] & 0x00FF0000U) >> 8U) | ((sd_status[0] & 0xFF000000U) >> 24U));
2288
2289 pStatus->ProtectedAreaSize = (((sd_status[1] & 0xFFU) << 24U) | ((sd_status[1] & 0xFF00U) << 8U) |
2290 ((sd_status[1] & 0xFF0000U) >> 8U) | ((sd_status[1] & 0xFF000000U) >> 24U));
2291
2292 pStatus->SpeedClass = (uint8_t)(sd_status[2] & 0xFFU);
2293
2294 pStatus->PerformanceMove = (uint8_t)((sd_status[2] & 0xFF00U) >> 8U);
2295
2296 pStatus->AllocationUnitSize = (uint8_t)((sd_status[2] & 0xF00000U) >> 20U);
2297
2298 pStatus->EraseSize = (uint16_t)(((sd_status[2] & 0xFF000000U) >> 16U) | (sd_status[3] & 0xFFU));
2299
2300 pStatus->EraseTimeout = (uint8_t)((sd_status[3] & 0xFC00U) >> 10U);
2301
2302 pStatus->EraseOffset = (uint8_t)((sd_status[3] & 0x0300U) >> 8U);
2303
2304 pStatus->UhsSpeedGrade = (uint8_t)((sd_status[3] & 0x00F0U) >> 4U);
2305 pStatus->UhsAllocationUnitSize = (uint8_t)(sd_status[3] & 0x000FU) ;
2306 pStatus->VideoSpeedClass = (uint8_t)((sd_status[4] & 0xFF000000U) >> 24U);
2307 }
2308
2309 return HAL_OK;
2310 }
2311
2312 /**
2313 * @brief Gets the SD card info.
2314 * @param hsd: Pointer to SD handle
2315 * @param pCardInfo: Pointer to the HAL_SD_CardInfoTypeDef structure that
2316 * will contain the SD card status information
2317 * @retval HAL status
2318 */
HAL_SD_GetCardInfo(SD_HandleTypeDef * hsd,HAL_SD_CardInfoTypeDef * pCardInfo)2319 HAL_StatusTypeDef HAL_SD_GetCardInfo(SD_HandleTypeDef *hsd, HAL_SD_CardInfoTypeDef *pCardInfo)
2320 {
2321 pCardInfo->CardType = (uint32_t)(hsd->SdCard.CardType);
2322 pCardInfo->CardVersion = (uint32_t)(hsd->SdCard.CardVersion);
2323 pCardInfo->Class = (uint32_t)(hsd->SdCard.Class);
2324 pCardInfo->RelCardAdd = (uint32_t)(hsd->SdCard.RelCardAdd);
2325 pCardInfo->BlockNbr = (uint32_t)(hsd->SdCard.BlockNbr);
2326 pCardInfo->BlockSize = (uint32_t)(hsd->SdCard.BlockSize);
2327 pCardInfo->LogBlockNbr = (uint32_t)(hsd->SdCard.LogBlockNbr);
2328 pCardInfo->LogBlockSize = (uint32_t)(hsd->SdCard.LogBlockSize);
2329
2330 return HAL_OK;
2331 }
2332
2333 /**
2334 * @brief Enables wide bus operation for the requested card if supported by
2335 * card.
2336 * @param hsd: Pointer to SD handle
2337 * @param WideMode: Specifies the SD card wide bus mode
2338 * This parameter can be one of the following values:
2339 * @arg SDMMC_BUS_WIDE_8B: 8-bit data transfer
2340 * @arg SDMMC_BUS_WIDE_4B: 4-bit data transfer
2341 * @arg SDMMC_BUS_WIDE_1B: 1-bit data transfer
2342 * @retval HAL status
2343 */
HAL_SD_ConfigWideBusOperation(SD_HandleTypeDef * hsd,uint32_t WideMode)2344 HAL_StatusTypeDef HAL_SD_ConfigWideBusOperation(SD_HandleTypeDef *hsd, uint32_t WideMode)
2345 {
2346 SDMMC_InitTypeDef Init;
2347 uint32_t errorstate;
2348
2349 /* Check the parameters */
2350 assert_param(IS_SDMMC_BUS_WIDE(WideMode));
2351
2352 /* Change State */
2353 hsd->State = HAL_SD_STATE_BUSY;
2354
2355 if(hsd->SdCard.CardType != CARD_SECURED)
2356 {
2357 if(WideMode == SDMMC_BUS_WIDE_8B)
2358 {
2359 hsd->ErrorCode |= HAL_SD_ERROR_UNSUPPORTED_FEATURE;
2360 }
2361 else if(WideMode == SDMMC_BUS_WIDE_4B)
2362 {
2363 errorstate = SD_WideBus_Enable(hsd);
2364
2365 hsd->ErrorCode |= errorstate;
2366 }
2367 else if(WideMode == SDMMC_BUS_WIDE_1B)
2368 {
2369 errorstate = SD_WideBus_Disable(hsd);
2370
2371 hsd->ErrorCode |= errorstate;
2372 }
2373 else
2374 {
2375 /* WideMode is not a valid argument*/
2376 hsd->ErrorCode |= HAL_SD_ERROR_PARAM;
2377 }
2378 }
2379 else
2380 {
2381 /* MMC Card does not support this feature */
2382 hsd->ErrorCode |= HAL_SD_ERROR_UNSUPPORTED_FEATURE;
2383 }
2384
2385 if(hsd->ErrorCode != HAL_SD_ERROR_NONE)
2386 {
2387 /* Clear all the static flags */
2388 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
2389 hsd->State = HAL_SD_STATE_READY;
2390 return HAL_ERROR;
2391 }
2392 else
2393 {
2394 /* Configure the SDMMC peripheral */
2395 Init.ClockEdge = hsd->Init.ClockEdge;
2396 Init.ClockPowerSave = hsd->Init.ClockPowerSave;
2397 Init.BusWide = WideMode;
2398 Init.HardwareFlowControl = hsd->Init.HardwareFlowControl;
2399
2400 /* Check if user Clock div < Normal speed 25Mhz, no change in Clockdiv */
2401 if(hsd->Init.ClockDiv >= SDMMC_NSpeed_CLK_DIV)
2402 {
2403 Init.ClockDiv = hsd->Init.ClockDiv;
2404 }
2405 else if (hsd->SdCard.CardSpeed == CARD_ULTRA_HIGH_SPEED)
2406 {
2407 /* UltraHigh speed SD card,user Clock div */
2408 Init.ClockDiv = hsd->Init.ClockDiv;
2409 }
2410 else if (hsd->SdCard.CardSpeed == CARD_HIGH_SPEED)
2411 {
2412 /* High speed SD card, Max Frequency = 50Mhz */
2413 Init.ClockDiv = SDMMC_HSpeed_CLK_DIV;
2414 }
2415 else
2416 {
2417 /* No High speed SD card, Max Frequency = 25Mhz */
2418 Init.ClockDiv = SDMMC_NSpeed_CLK_DIV;
2419 }
2420
2421 (void)SDMMC_Init(hsd->Instance, Init);
2422 }
2423
2424 /* Change State */
2425 hsd->State = HAL_SD_STATE_READY;
2426
2427 return HAL_OK;
2428 }
2429
2430 /**
2431 * @brief Gets the current sd card data state.
2432 * @param hsd: pointer to SD handle
2433 * @retval Card state
2434 */
HAL_SD_GetCardState(SD_HandleTypeDef * hsd)2435 HAL_SD_CardStateTypedef HAL_SD_GetCardState(SD_HandleTypeDef *hsd)
2436 {
2437 uint32_t cardstate;
2438 uint32_t errorstate;
2439 uint32_t resp1 = 0;
2440
2441 errorstate = SD_SendStatus(hsd, &resp1);
2442 if(errorstate != HAL_SD_ERROR_NONE)
2443 {
2444 hsd->ErrorCode |= errorstate;
2445 }
2446
2447 cardstate = ((resp1 >> 9U) & 0x0FU);
2448
2449 return (HAL_SD_CardStateTypedef)cardstate;
2450 }
2451
2452 /**
2453 * @brief Abort the current transfer and disable the SD.
2454 * @param hsd: pointer to a SD_HandleTypeDef structure that contains
2455 * the configuration information for SD module.
2456 * @retval HAL status
2457 */
HAL_SD_Abort(SD_HandleTypeDef * hsd)2458 HAL_StatusTypeDef HAL_SD_Abort(SD_HandleTypeDef *hsd)
2459 {
2460 HAL_SD_CardStateTypedef CardState;
2461
2462 /* DIsable All interrupts */
2463 __HAL_SD_DISABLE_IT(hsd, SDMMC_IT_DATAEND | SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT|\
2464 SDMMC_IT_TXUNDERR| SDMMC_IT_RXOVERR);
2465
2466 /* Clear All flags */
2467 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
2468
2469 /* If IDMA Context, disable Internal DMA */
2470 hsd->Instance->IDMACTRL = SDMMC_DISABLE_IDMA;
2471
2472 hsd->State = HAL_SD_STATE_READY;
2473
2474 /* Initialize the SD operation */
2475 hsd->Context = SD_CONTEXT_NONE;
2476
2477 CardState = HAL_SD_GetCardState(hsd);
2478 if((CardState == HAL_SD_CARD_RECEIVING) || (CardState == HAL_SD_CARD_SENDING))
2479 {
2480 hsd->ErrorCode = SDMMC_CmdStopTransfer(hsd->Instance);
2481 }
2482 if(hsd->ErrorCode != HAL_SD_ERROR_NONE)
2483 {
2484 return HAL_ERROR;
2485 }
2486 return HAL_OK;
2487 }
2488
2489 /**
2490 * @brief Abort the current transfer and disable the SD (IT mode).
2491 * @param hsd: pointer to a SD_HandleTypeDef structure that contains
2492 * the configuration information for SD module.
2493 * @retval HAL status
2494 */
HAL_SD_Abort_IT(SD_HandleTypeDef * hsd)2495 HAL_StatusTypeDef HAL_SD_Abort_IT(SD_HandleTypeDef *hsd)
2496 {
2497 HAL_SD_CardStateTypedef CardState;
2498
2499 /* Disable All interrupts */
2500 __HAL_SD_DISABLE_IT(hsd, SDMMC_IT_DATAEND | SDMMC_IT_DCRCFAIL | SDMMC_IT_DTIMEOUT|\
2501 SDMMC_IT_TXUNDERR| SDMMC_IT_RXOVERR);
2502
2503 /* If IDMA Context, disable Internal DMA */
2504 hsd->Instance->IDMACTRL = SDMMC_DISABLE_IDMA;
2505
2506 /* Clear All flags */
2507 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
2508
2509 CardState = HAL_SD_GetCardState(hsd);
2510 hsd->State = HAL_SD_STATE_READY;
2511
2512 if((CardState == HAL_SD_CARD_RECEIVING) || (CardState == HAL_SD_CARD_SENDING))
2513 {
2514 hsd->ErrorCode = SDMMC_CmdStopTransfer(hsd->Instance);
2515 }
2516
2517 if(hsd->ErrorCode != HAL_SD_ERROR_NONE)
2518 {
2519 return HAL_ERROR;
2520 }
2521 else
2522 {
2523 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
2524 hsd->AbortCpltCallback(hsd);
2525 #else
2526 HAL_SD_AbortCallback(hsd);
2527 #endif
2528 }
2529
2530 return HAL_OK;
2531 }
2532
2533 /**
2534 * @}
2535 */
2536
2537 /**
2538 * @}
2539 */
2540
2541 /* Private function ----------------------------------------------------------*/
2542 /** @addtogroup SD_Private_Functions
2543 * @{
2544 */
2545
2546
2547 /**
2548 * @brief Initializes the sd card.
2549 * @param hsd: Pointer to SD handle
2550 * @retval SD Card error state
2551 */
SD_InitCard(SD_HandleTypeDef * hsd)2552 static uint32_t SD_InitCard(SD_HandleTypeDef *hsd)
2553 {
2554 HAL_SD_CardCSDTypedef CSD;
2555 uint32_t errorstate;
2556 uint16_t sd_rca = 1;
2557
2558 /* Check the power State */
2559 if(SDMMC_GetPowerState(hsd->Instance) == 0U)
2560 {
2561 /* Power off */
2562 return HAL_SD_ERROR_REQUEST_NOT_APPLICABLE;
2563 }
2564
2565 if(hsd->SdCard.CardType != CARD_SECURED)
2566 {
2567 /* Send CMD2 ALL_SEND_CID */
2568 errorstate = SDMMC_CmdSendCID(hsd->Instance);
2569 if(errorstate != HAL_SD_ERROR_NONE)
2570 {
2571 return errorstate;
2572 }
2573 else
2574 {
2575 /* Get Card identification number data */
2576 hsd->CID[0] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1);
2577 hsd->CID[1] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP2);
2578 hsd->CID[2] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP3);
2579 hsd->CID[3] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP4);
2580 }
2581 }
2582
2583 if(hsd->SdCard.CardType != CARD_SECURED)
2584 {
2585 /* Send CMD3 SET_REL_ADDR with argument 0 */
2586 /* SD Card publishes its RCA. */
2587 errorstate = SDMMC_CmdSetRelAdd(hsd->Instance, &sd_rca);
2588 if(errorstate != HAL_SD_ERROR_NONE)
2589 {
2590 return errorstate;
2591 }
2592 }
2593 if(hsd->SdCard.CardType != CARD_SECURED)
2594 {
2595 /* Get the SD card RCA */
2596 hsd->SdCard.RelCardAdd = sd_rca;
2597
2598 /* Send CMD9 SEND_CSD with argument as card's RCA */
2599 errorstate = SDMMC_CmdSendCSD(hsd->Instance, (uint32_t)(hsd->SdCard.RelCardAdd << 16U));
2600 if(errorstate != HAL_SD_ERROR_NONE)
2601 {
2602 return errorstate;
2603 }
2604 else
2605 {
2606 /* Get Card Specific Data */
2607 hsd->CSD[0] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1);
2608 hsd->CSD[1] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP2);
2609 hsd->CSD[2] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP3);
2610 hsd->CSD[3] = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP4);
2611 }
2612 }
2613
2614 /* Get the Card Class */
2615 hsd->SdCard.Class = (SDMMC_GetResponse(hsd->Instance, SDMMC_RESP2) >> 20);
2616
2617 /* Get CSD parameters */
2618 if (HAL_SD_GetCardCSD(hsd, &CSD) != HAL_OK)
2619 {
2620 return HAL_SD_ERROR_UNSUPPORTED_FEATURE;
2621 }
2622
2623 /* Select the Card */
2624 errorstate = SDMMC_CmdSelDesel(hsd->Instance, (uint32_t)(((uint32_t)hsd->SdCard.RelCardAdd) << 16));
2625 if(errorstate != HAL_SD_ERROR_NONE)
2626 {
2627 return errorstate;
2628 }
2629
2630 /* All cards are initialized */
2631 return HAL_SD_ERROR_NONE;
2632 }
2633
2634 /**
2635 * @brief Enquires cards about their operating voltage and configures clock
2636 * controls and stores SD information that will be needed in future
2637 * in the SD handle.
2638 * @param hsd: Pointer to SD handle
2639 * @retval error state
2640 */
SD_PowerON(SD_HandleTypeDef * hsd)2641 static uint32_t SD_PowerON(SD_HandleTypeDef *hsd)
2642 {
2643 __IO uint32_t count = 0;
2644 uint32_t response = 0, validvoltage = 0;
2645 uint32_t errorstate;
2646 #if (USE_SD_TRANSCEIVER != 0U)
2647 uint32_t tickstart = HAL_GetTick();
2648 #endif /* USE_SD_TRANSCEIVER */
2649
2650 /* CMD0: GO_IDLE_STATE */
2651 errorstate = SDMMC_CmdGoIdleState(hsd->Instance);
2652 if(errorstate != HAL_SD_ERROR_NONE)
2653 {
2654 return errorstate;
2655 }
2656
2657 /* CMD8: SEND_IF_COND: Command available only on V2.0 cards */
2658 errorstate = SDMMC_CmdOperCond(hsd->Instance);
2659 if(errorstate != HAL_SD_ERROR_NONE)
2660 {
2661 hsd->SdCard.CardVersion = CARD_V1_X;
2662 }
2663 else
2664 {
2665 hsd->SdCard.CardVersion = CARD_V2_X;
2666 }
2667
2668 /* SEND CMD55 APP_CMD with RCA as 0 */
2669 errorstate = SDMMC_CmdAppCommand(hsd->Instance, 0);
2670 if(errorstate != HAL_SD_ERROR_NONE)
2671 {
2672 return HAL_SD_ERROR_UNSUPPORTED_FEATURE;
2673 }
2674 else
2675 {
2676 /* SD CARD */
2677 /* Send ACMD41 SD_APP_OP_COND with Argument 0x80100000 */
2678 while((count < SDMMC_MAX_VOLT_TRIAL) && (validvoltage == 0U))
2679 {
2680 /* SEND CMD55 APP_CMD with RCA as 0 */
2681 errorstate = SDMMC_CmdAppCommand(hsd->Instance, 0);
2682 if(errorstate != HAL_SD_ERROR_NONE)
2683 {
2684 return errorstate;
2685 }
2686
2687 /* Send CMD41 */
2688 errorstate = SDMMC_CmdAppOperCommand(hsd->Instance, SDMMC_VOLTAGE_WINDOW_SD | SDMMC_HIGH_CAPACITY | SD_SWITCH_1_8V_CAPACITY);
2689 if(errorstate != HAL_SD_ERROR_NONE)
2690 {
2691 return HAL_SD_ERROR_UNSUPPORTED_FEATURE;
2692 }
2693
2694 /* Get command response */
2695 response = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1);
2696
2697 /* Get operating voltage*/
2698 validvoltage = (((response >> 31U) == 1U) ? 1U : 0U);
2699
2700 count++;
2701 }
2702
2703 if(count >= SDMMC_MAX_VOLT_TRIAL)
2704 {
2705 return HAL_SD_ERROR_INVALID_VOLTRANGE;
2706 }
2707
2708 if((response & SDMMC_HIGH_CAPACITY) == SDMMC_HIGH_CAPACITY) /* (response &= SD_HIGH_CAPACITY) */
2709 {
2710 hsd->SdCard.CardType = CARD_SDHC_SDXC;
2711 #if (USE_SD_TRANSCEIVER != 0U)
2712 if((response & SD_SWITCH_1_8V_CAPACITY) == SD_SWITCH_1_8V_CAPACITY)
2713 {
2714 hsd->SdCard.CardSpeed = CARD_ULTRA_HIGH_SPEED;
2715
2716 /* Start switching procedue */
2717 hsd->Instance->POWER |= SDMMC_POWER_VSWITCHEN;
2718
2719 /* Send CMD11 to switch 1.8V mode */
2720 errorstate = SDMMC_CmdVoltageSwitch(hsd->Instance);
2721 if(errorstate != HAL_SD_ERROR_NONE)
2722 {
2723 return errorstate;
2724 }
2725
2726 /* Check to CKSTOP */
2727 while(( hsd->Instance->STA & SDMMC_FLAG_CKSTOP) != SDMMC_FLAG_CKSTOP)
2728 {
2729 if((HAL_GetTick() - tickstart) >= SDMMC_DATATIMEOUT)
2730 {
2731 return HAL_SD_ERROR_TIMEOUT;
2732 }
2733 }
2734
2735 /* Clear CKSTOP Flag */
2736 hsd->Instance->ICR = SDMMC_FLAG_CKSTOP;
2737
2738 /* Check to BusyD0 */
2739 if(( hsd->Instance->STA & SDMMC_FLAG_BUSYD0) != SDMMC_FLAG_BUSYD0)
2740 {
2741 /* Error when activate Voltage Switch in SDMMC IP */
2742 return SDMMC_ERROR_UNSUPPORTED_FEATURE;
2743 }
2744 else
2745 {
2746 /* Enable Transceiver Switch PIN */
2747 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
2748 hsd->DriveTransceiver_1_8V_Callback(SET);
2749 #else
2750 HAL_SD_DriveTransceiver_1_8V_Callback(SET);
2751 #endif
2752
2753 /* Switch ready */
2754 hsd->Instance->POWER |= SDMMC_POWER_VSWITCH;
2755
2756 /* Check VSWEND Flag */
2757 while(( hsd->Instance->STA & SDMMC_FLAG_VSWEND) != SDMMC_FLAG_VSWEND)
2758 {
2759 if((HAL_GetTick() - tickstart) >= SDMMC_DATATIMEOUT)
2760 {
2761 return HAL_SD_ERROR_TIMEOUT;
2762 }
2763 }
2764
2765 /* Clear VSWEND Flag */
2766 hsd->Instance->ICR = SDMMC_FLAG_VSWEND;
2767
2768 /* Check BusyD0 status */
2769 if(( hsd->Instance->STA & SDMMC_FLAG_BUSYD0) == SDMMC_FLAG_BUSYD0)
2770 {
2771 /* Error when enabling 1.8V mode */
2772 return HAL_SD_ERROR_INVALID_VOLTRANGE;
2773 }
2774 /* Switch to 1.8V OK */
2775
2776 /* Disable VSWITCH FLAG from SDMMC IP */
2777 hsd->Instance->POWER = 0x13U;
2778
2779 /* Clean Status flags */
2780 hsd->Instance->ICR = 0xFFFFFFFFU;
2781 }
2782
2783 hsd->SdCard.CardSpeed = CARD_ULTRA_HIGH_SPEED;
2784 }
2785 #endif /* USE_SD_TRANSCEIVER */
2786 }
2787 }
2788
2789 return HAL_SD_ERROR_NONE;
2790 }
2791
2792 /**
2793 * @brief Turns the SDMMC output signals off.
2794 * @param hsd: Pointer to SD handle
2795 * @retval None
2796 */
SD_PowerOFF(SD_HandleTypeDef * hsd)2797 static void SD_PowerOFF(SD_HandleTypeDef *hsd)
2798 {
2799 /* Set Power State to OFF */
2800 (void)SDMMC_PowerState_OFF(hsd->Instance);
2801 }
2802
2803 /**
2804 * @brief Send Status info command.
2805 * @param hsd: pointer to SD handle
2806 * @param pSDstatus: Pointer to the buffer that will contain the SD card status
2807 * SD Status register)
2808 * @retval error state
2809 */
SD_SendSDStatus(SD_HandleTypeDef * hsd,uint32_t * pSDstatus)2810 static uint32_t SD_SendSDStatus(SD_HandleTypeDef *hsd, uint32_t *pSDstatus)
2811 {
2812 SDMMC_DataInitTypeDef config;
2813 uint32_t errorstate;
2814 uint32_t tickstart = HAL_GetTick();
2815 uint32_t count;
2816 uint32_t *pData = pSDstatus;
2817
2818 /* Check SD response */
2819 if((SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1) & SDMMC_CARD_LOCKED) == SDMMC_CARD_LOCKED)
2820 {
2821 return HAL_SD_ERROR_LOCK_UNLOCK_FAILED;
2822 }
2823
2824 /* Set block size for card if it is not equal to current block size for card */
2825 errorstate = SDMMC_CmdBlockLength(hsd->Instance, 64);
2826 if(errorstate != HAL_SD_ERROR_NONE)
2827 {
2828 hsd->ErrorCode |= HAL_SD_ERROR_NONE;
2829 return errorstate;
2830 }
2831
2832 /* Send CMD55 */
2833 errorstate = SDMMC_CmdAppCommand(hsd->Instance, (uint32_t)(hsd->SdCard.RelCardAdd << 16));
2834 if(errorstate != HAL_SD_ERROR_NONE)
2835 {
2836 hsd->ErrorCode |= HAL_SD_ERROR_NONE;
2837 return errorstate;
2838 }
2839
2840 /* Configure the SD DPSM (Data Path State Machine) */
2841 config.DataTimeOut = SDMMC_DATATIMEOUT;
2842 config.DataLength = 64;
2843 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_64B;
2844 config.TransferDir = SDMMC_TRANSFER_DIR_TO_SDMMC;
2845 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
2846 config.DPSM = SDMMC_DPSM_ENABLE;
2847 (void)SDMMC_ConfigData(hsd->Instance, &config);
2848
2849 /* Send ACMD13 (SD_APP_STAUS) with argument as card's RCA */
2850 errorstate = SDMMC_CmdStatusRegister(hsd->Instance);
2851 if(errorstate != HAL_SD_ERROR_NONE)
2852 {
2853 hsd->ErrorCode |= HAL_SD_ERROR_NONE;
2854 return errorstate;
2855 }
2856
2857 /* Get status data */
2858 while(!__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR | SDMMC_FLAG_DCRCFAIL | SDMMC_FLAG_DTIMEOUT | SDMMC_FLAG_DATAEND))
2859 {
2860 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXFIFOHF))
2861 {
2862 for(count = 0U; count < 8U; count++)
2863 {
2864 *pData = SDMMC_ReadFIFO(hsd->Instance);
2865 pData++;
2866 }
2867 }
2868
2869 if((HAL_GetTick() - tickstart) >= SDMMC_DATATIMEOUT)
2870 {
2871 return HAL_SD_ERROR_TIMEOUT;
2872 }
2873 }
2874
2875 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DTIMEOUT))
2876 {
2877 return HAL_SD_ERROR_DATA_TIMEOUT;
2878 }
2879 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DCRCFAIL))
2880 {
2881 return HAL_SD_ERROR_DATA_CRC_FAIL;
2882 }
2883 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR))
2884 {
2885 return HAL_SD_ERROR_RX_OVERRUN;
2886 }
2887 else
2888 {
2889 /* Nothing to do */
2890 }
2891
2892 while ((__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DPSMACT)))
2893 {
2894 *pData = SDMMC_ReadFIFO(hsd->Instance);
2895 pData++;
2896
2897 if((HAL_GetTick() - tickstart) >= SDMMC_DATATIMEOUT)
2898 {
2899 return HAL_SD_ERROR_TIMEOUT;
2900 }
2901 }
2902
2903 /* Clear all the static status flags*/
2904 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
2905
2906 return HAL_SD_ERROR_NONE;
2907 }
2908
2909 /**
2910 * @brief Returns the current card's status.
2911 * @param hsd: Pointer to SD handle
2912 * @param pCardStatus: pointer to the buffer that will contain the SD card
2913 * status (Card Status register)
2914 * @retval error state
2915 */
SD_SendStatus(SD_HandleTypeDef * hsd,uint32_t * pCardStatus)2916 static uint32_t SD_SendStatus(SD_HandleTypeDef *hsd, uint32_t *pCardStatus)
2917 {
2918 uint32_t errorstate;
2919
2920 if(pCardStatus == NULL)
2921 {
2922 return HAL_SD_ERROR_PARAM;
2923 }
2924
2925 /* Send Status command */
2926 errorstate = SDMMC_CmdSendStatus(hsd->Instance, (uint32_t)(hsd->SdCard.RelCardAdd << 16));
2927 if(errorstate != HAL_SD_ERROR_NONE)
2928 {
2929 return errorstate;
2930 }
2931
2932 /* Get SD card status */
2933 *pCardStatus = SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1);
2934
2935 return HAL_SD_ERROR_NONE;
2936 }
2937
2938 /**
2939 * @brief Enables the SDMMC wide bus mode.
2940 * @param hsd: pointer to SD handle
2941 * @retval error state
2942 */
SD_WideBus_Enable(SD_HandleTypeDef * hsd)2943 static uint32_t SD_WideBus_Enable(SD_HandleTypeDef *hsd)
2944 {
2945 uint32_t scr[2] = {0, 0};
2946 uint32_t errorstate;
2947
2948 if((SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1) & SDMMC_CARD_LOCKED) == SDMMC_CARD_LOCKED)
2949 {
2950 return HAL_SD_ERROR_LOCK_UNLOCK_FAILED;
2951 }
2952
2953 /* Get SCR Register */
2954 errorstate = SD_FindSCR(hsd, scr);
2955 if(errorstate != HAL_SD_ERROR_NONE)
2956 {
2957 return errorstate;
2958 }
2959
2960 /* If requested card supports wide bus operation */
2961 if((scr[1] & SDMMC_WIDE_BUS_SUPPORT) != SDMMC_ALLZERO)
2962 {
2963 /* Send CMD55 APP_CMD with argument as card's RCA.*/
2964 errorstate = SDMMC_CmdAppCommand(hsd->Instance, (uint32_t)(hsd->SdCard.RelCardAdd << 16));
2965 if(errorstate != HAL_SD_ERROR_NONE)
2966 {
2967 return errorstate;
2968 }
2969
2970 /* Send ACMD6 APP_CMD with argument as 2 for wide bus mode */
2971 errorstate = SDMMC_CmdBusWidth(hsd->Instance, 2);
2972 if(errorstate != HAL_SD_ERROR_NONE)
2973 {
2974 return errorstate;
2975 }
2976
2977 return HAL_SD_ERROR_NONE;
2978 }
2979 else
2980 {
2981 return HAL_SD_ERROR_REQUEST_NOT_APPLICABLE;
2982 }
2983 }
2984
2985 /**
2986 * @brief Disables the SDMMC wide bus mode.
2987 * @param hsd: Pointer to SD handle
2988 * @retval error state
2989 */
SD_WideBus_Disable(SD_HandleTypeDef * hsd)2990 static uint32_t SD_WideBus_Disable(SD_HandleTypeDef *hsd)
2991 {
2992 uint32_t scr[2] = {0, 0};
2993 uint32_t errorstate;
2994
2995 if((SDMMC_GetResponse(hsd->Instance, SDMMC_RESP1) & SDMMC_CARD_LOCKED) == SDMMC_CARD_LOCKED)
2996 {
2997 return HAL_SD_ERROR_LOCK_UNLOCK_FAILED;
2998 }
2999
3000 /* Get SCR Register */
3001 errorstate = SD_FindSCR(hsd, scr);
3002 if(errorstate != HAL_SD_ERROR_NONE)
3003 {
3004 return errorstate;
3005 }
3006
3007 /* If requested card supports 1 bit mode operation */
3008 if((scr[1] & SDMMC_SINGLE_BUS_SUPPORT) != SDMMC_ALLZERO)
3009 {
3010 /* Send CMD55 APP_CMD with argument as card's RCA */
3011 errorstate = SDMMC_CmdAppCommand(hsd->Instance, (uint32_t)(hsd->SdCard.RelCardAdd << 16));
3012 if(errorstate != HAL_SD_ERROR_NONE)
3013 {
3014 return errorstate;
3015 }
3016
3017 /* Send ACMD6 APP_CMD with argument as 0 for single bus mode */
3018 errorstate = SDMMC_CmdBusWidth(hsd->Instance, 0);
3019 if(errorstate != HAL_SD_ERROR_NONE)
3020 {
3021 return errorstate;
3022 }
3023
3024 return HAL_SD_ERROR_NONE;
3025 }
3026 else
3027 {
3028 return HAL_SD_ERROR_REQUEST_NOT_APPLICABLE;
3029 }
3030 }
3031
3032
3033 /**
3034 * @brief Finds the SD card SCR register value.
3035 * @param hsd: Pointer to SD handle
3036 * @param pSCR: pointer to the buffer that will contain the SCR value
3037 * @retval error state
3038 */
SD_FindSCR(SD_HandleTypeDef * hsd,uint32_t * pSCR)3039 static uint32_t SD_FindSCR(SD_HandleTypeDef *hsd, uint32_t *pSCR)
3040 {
3041 SDMMC_DataInitTypeDef config;
3042 uint32_t errorstate;
3043 uint32_t tickstart = HAL_GetTick();
3044 uint32_t index = 0;
3045 uint32_t tempscr[2] = {0, 0};
3046 uint32_t *scr = pSCR;
3047
3048 /* Set Block Size To 8 Bytes */
3049 errorstate = SDMMC_CmdBlockLength(hsd->Instance, 8);
3050 if(errorstate != HAL_SD_ERROR_NONE)
3051 {
3052 return errorstate;
3053 }
3054
3055 /* Send CMD55 APP_CMD with argument as card's RCA */
3056 errorstate = SDMMC_CmdAppCommand(hsd->Instance, (uint32_t)((hsd->SdCard.RelCardAdd) << 16));
3057 if(errorstate != HAL_SD_ERROR_NONE)
3058 {
3059 return errorstate;
3060 }
3061
3062 config.DataTimeOut = SDMMC_DATATIMEOUT;
3063 config.DataLength = 8;
3064 config.DataBlockSize = SDMMC_DATABLOCK_SIZE_8B;
3065 config.TransferDir = SDMMC_TRANSFER_DIR_TO_SDMMC;
3066 config.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
3067 config.DPSM = SDMMC_DPSM_ENABLE;
3068 (void)SDMMC_ConfigData(hsd->Instance, &config);
3069
3070 /* Send ACMD51 SD_APP_SEND_SCR with argument as 0 */
3071 errorstate = SDMMC_CmdSendSCR(hsd->Instance);
3072 if(errorstate != HAL_SD_ERROR_NONE)
3073 {
3074 return errorstate;
3075 }
3076
3077 while(!__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR | SDMMC_FLAG_DCRCFAIL | SDMMC_FLAG_DTIMEOUT | SDMMC_FLAG_DBCKEND | SDMMC_FLAG_DATAEND))
3078 {
3079 if((!__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXFIFOE)) && (index == 0U))
3080 {
3081 tempscr[0] = SDMMC_ReadFIFO(hsd->Instance);
3082 tempscr[1] = SDMMC_ReadFIFO(hsd->Instance);
3083 index++;
3084 }
3085
3086
3087 if((HAL_GetTick() - tickstart) >= SDMMC_DATATIMEOUT)
3088 {
3089 return HAL_SD_ERROR_TIMEOUT;
3090 }
3091 }
3092
3093 if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DTIMEOUT))
3094 {
3095 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DTIMEOUT);
3096
3097 return HAL_SD_ERROR_DATA_TIMEOUT;
3098 }
3099 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DCRCFAIL))
3100 {
3101 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DCRCFAIL);
3102
3103 return HAL_SD_ERROR_DATA_CRC_FAIL;
3104 }
3105 else if(__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR))
3106 {
3107 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_RXOVERR);
3108
3109 return HAL_SD_ERROR_RX_OVERRUN;
3110 }
3111 else
3112 {
3113 /* No error flag set */
3114 /* Clear all the static flags */
3115 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
3116
3117 *scr = (((tempscr[1] & SDMMC_0TO7BITS) << 24) | ((tempscr[1] & SDMMC_8TO15BITS) << 8) |\
3118 ((tempscr[1] & SDMMC_16TO23BITS) >> 8) | ((tempscr[1] & SDMMC_24TO31BITS) >> 24));
3119 scr++;
3120 *scr = (((tempscr[0] & SDMMC_0TO7BITS) << 24) | ((tempscr[0] & SDMMC_8TO15BITS) << 8) |\
3121 ((tempscr[0] & SDMMC_16TO23BITS) >> 8) | ((tempscr[0] & SDMMC_24TO31BITS) >> 24));
3122
3123 }
3124
3125 return HAL_SD_ERROR_NONE;
3126 }
3127
3128 /**
3129 * @brief Wrap up reading in non-blocking mode.
3130 * @param hsd: pointer to a SD_HandleTypeDef structure that contains
3131 * the configuration information.
3132 * @retval None
3133 */
SD_Read_IT(SD_HandleTypeDef * hsd)3134 static void SD_Read_IT(SD_HandleTypeDef *hsd)
3135 {
3136 uint32_t count, data;
3137 uint8_t* tmp;
3138
3139 tmp = hsd->pRxBuffPtr;
3140
3141 /* Read data from SDMMC Rx FIFO */
3142 for(count = 0U; count < 8U; count++)
3143 {
3144 data = SDMMC_ReadFIFO(hsd->Instance);
3145 *tmp = (uint8_t)(data & 0xFFU);
3146 tmp++;
3147 *tmp = (uint8_t)((data >> 8U) & 0xFFU);
3148 tmp++;
3149 *tmp = (uint8_t)((data >> 16U) & 0xFFU);
3150 tmp++;
3151 *tmp = (uint8_t)((data >> 24U) & 0xFFU);
3152 tmp++;
3153 }
3154
3155 hsd->pRxBuffPtr = tmp;
3156 }
3157
3158 /**
3159 * @brief Wrap up writing in non-blocking mode.
3160 * @param hsd: pointer to a SD_HandleTypeDef structure that contains
3161 * the configuration information.
3162 * @retval None
3163 */
SD_Write_IT(SD_HandleTypeDef * hsd)3164 static void SD_Write_IT(SD_HandleTypeDef *hsd)
3165 {
3166 uint32_t count, data;
3167 uint8_t* tmp;
3168
3169 tmp = hsd->pTxBuffPtr;
3170
3171 /* Write data to SDMMC Tx FIFO */
3172 for(count = 0U; count < 8U; count++)
3173 {
3174 data = (uint32_t)(*tmp);
3175 tmp++;
3176 data |= ((uint32_t)(*tmp) << 8U);
3177 tmp++;
3178 data |= ((uint32_t)(*tmp) << 16U);
3179 tmp++;
3180 data |= ((uint32_t)(*tmp) << 24U);
3181 tmp++;
3182 (void)SDMMC_WriteFIFO(hsd->Instance, &data);
3183 }
3184
3185 hsd->pTxBuffPtr = tmp;
3186 }
3187
SD_HighSpeed(SD_HandleTypeDef * hsd)3188 uint32_t SD_HighSpeed(SD_HandleTypeDef *hsd)
3189 {
3190 uint32_t errorstate = HAL_SD_ERROR_NONE;
3191 SDMMC_DataInitTypeDef sdmmc_datainitstructure;
3192 uint32_t SD_hs[16] = {0};
3193 uint32_t count, loop = 0 ;
3194 uint32_t Timeout = HAL_GetTick();
3195
3196 if(hsd->SdCard.CardSpeed == CARD_NORMAL_SPEED)
3197 {
3198 /* Standard Speed Card <= 12.5Mhz */
3199 return HAL_SD_ERROR_REQUEST_NOT_APPLICABLE;
3200 }
3201
3202 if(hsd->SdCard.CardSpeed == CARD_HIGH_SPEED)
3203 {
3204 /* Initialize the Data control register */
3205 hsd->Instance->DCTRL = 0;
3206 errorstate = SDMMC_CmdBlockLength(hsd->Instance, 64);
3207
3208 if (errorstate != HAL_SD_ERROR_NONE)
3209 {
3210 return errorstate;
3211 }
3212
3213 /* Configure the SD DPSM (Data Path State Machine) */
3214 sdmmc_datainitstructure.DataTimeOut = SDMMC_DATATIMEOUT;
3215 sdmmc_datainitstructure.DataLength = 64;
3216 sdmmc_datainitstructure.DataBlockSize = SDMMC_DATABLOCK_SIZE_64B ;
3217 sdmmc_datainitstructure.TransferDir = SDMMC_TRANSFER_DIR_TO_SDMMC;
3218 sdmmc_datainitstructure.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
3219 sdmmc_datainitstructure.DPSM = SDMMC_DPSM_ENABLE;
3220
3221 if ( SDMMC_ConfigData(hsd->Instance, &sdmmc_datainitstructure) != HAL_OK)
3222 {
3223 return (HAL_SD_ERROR_GENERAL_UNKNOWN_ERR);
3224 }
3225
3226
3227 errorstate = SDMMC_CmdSwitch(hsd->Instance,SDMMC_SDR25_SWITCH_PATTERN);
3228 if(errorstate != HAL_SD_ERROR_NONE)
3229 {
3230 return errorstate;
3231 }
3232
3233 while(!__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR | SDMMC_FLAG_DCRCFAIL | SDMMC_FLAG_DTIMEOUT | SDMMC_FLAG_DBCKEND| SDMMC_FLAG_DATAEND ))
3234 {
3235 if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXFIFOHF))
3236 {
3237 for (count = 0U; count < 8U; count++)
3238 {
3239 SD_hs[(8U*loop)+count] = SDMMC_ReadFIFO(hsd->Instance);
3240 }
3241 loop ++;
3242 }
3243
3244 if((HAL_GetTick()-Timeout) >= SDMMC_DATATIMEOUT)
3245 {
3246 hsd->ErrorCode = HAL_SD_ERROR_TIMEOUT;
3247 hsd->State= HAL_SD_STATE_READY;
3248 return HAL_SD_ERROR_TIMEOUT;
3249 }
3250 }
3251
3252 if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DTIMEOUT))
3253 {
3254 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DTIMEOUT);
3255
3256 errorstate = 0;
3257
3258 return errorstate;
3259 }
3260 else if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DCRCFAIL))
3261 {
3262 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DCRCFAIL);
3263
3264 errorstate = SDMMC_ERROR_DATA_CRC_FAIL;
3265
3266 return errorstate;
3267 }
3268 else if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR))
3269 {
3270 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_RXOVERR);
3271
3272 errorstate = SDMMC_ERROR_RX_OVERRUN;
3273
3274 return errorstate;
3275 }
3276 else
3277 {
3278 /* No error flag set */
3279 }
3280
3281 /* Clear all the static flags */
3282 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_FLAGS);
3283
3284 /* Test if the switch mode HS is ok */
3285 if ((((uint8_t*)SD_hs)[13] & 2U) != 2U)
3286 {
3287 errorstate = SDMMC_ERROR_UNSUPPORTED_FEATURE;
3288 }
3289
3290 }
3291
3292 return errorstate;
3293 }
3294
3295 #if (USE_SD_TRANSCEIVER != 0U)
3296 /**
3297 * @brief Switches the SD card to High Speed mode.
3298 * This API must be used after "Transfer State"
3299 * @note This operation should be followed by the configuration
3300 * of PLL to have SDMMCCK clock between 50 and 120 MHz
3301 * @param hsd: SD handle
3302 * @retval SD Card error state
3303 */
SD_UltraHighSpeed(SD_HandleTypeDef * hsd)3304 uint32_t SD_UltraHighSpeed(SD_HandleTypeDef *hsd)
3305 {
3306 uint32_t errorstate = HAL_SD_ERROR_NONE;
3307 SDMMC_DataInitTypeDef sdmmc_datainitstructure;
3308 uint32_t SD_hs[16] = {0};
3309 uint32_t count, loop = 0 ;
3310 uint32_t Timeout = HAL_GetTick();
3311
3312 if(hsd->SdCard.CardSpeed == CARD_NORMAL_SPEED)
3313 {
3314 /* Standard Speed Card <= 12.5Mhz */
3315 return HAL_SD_ERROR_REQUEST_NOT_APPLICABLE;
3316 }
3317
3318 if(hsd->SdCard.CardSpeed == CARD_ULTRA_HIGH_SPEED)
3319 {
3320 /* Initialize the Data control register */
3321 hsd->Instance->DCTRL = 0;
3322 errorstate = SDMMC_CmdBlockLength(hsd->Instance, 64);
3323
3324 if (errorstate != HAL_SD_ERROR_NONE)
3325 {
3326 return errorstate;
3327 }
3328
3329 /* Configure the SD DPSM (Data Path State Machine) */
3330 sdmmc_datainitstructure.DataTimeOut = SDMMC_DATATIMEOUT;
3331 sdmmc_datainitstructure.DataLength = 64;
3332 sdmmc_datainitstructure.DataBlockSize = SDMMC_DATABLOCK_SIZE_64B ;
3333 sdmmc_datainitstructure.TransferDir = SDMMC_TRANSFER_DIR_TO_SDMMC;
3334 sdmmc_datainitstructure.TransferMode = SDMMC_TRANSFER_MODE_BLOCK;
3335 sdmmc_datainitstructure.DPSM = SDMMC_DPSM_ENABLE;
3336
3337 if ( SDMMC_ConfigData(hsd->Instance, &sdmmc_datainitstructure) != HAL_OK)
3338 {
3339 return (HAL_SD_ERROR_GENERAL_UNKNOWN_ERR);
3340 }
3341
3342 errorstate = SDMMC_CmdSwitch(hsd->Instance, SDMMC_SDR104_SWITCH_PATTERN);
3343 if(errorstate != HAL_SD_ERROR_NONE)
3344 {
3345 return errorstate;
3346 }
3347
3348 while(!__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR | SDMMC_FLAG_DCRCFAIL | SDMMC_FLAG_DTIMEOUT | SDMMC_FLAG_DBCKEND| SDMMC_FLAG_DATAEND ))
3349 {
3350 if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXFIFOHF))
3351 {
3352 for (count = 0U; count < 8U; count++)
3353 {
3354 SD_hs[(8U*loop)+count] = SDMMC_ReadFIFO(hsd->Instance);
3355 }
3356 loop ++;
3357 }
3358
3359 if((HAL_GetTick()-Timeout) >= SDMMC_DATATIMEOUT)
3360 {
3361 hsd->ErrorCode = HAL_SD_ERROR_TIMEOUT;
3362 hsd->State= HAL_SD_STATE_READY;
3363 return HAL_SD_ERROR_TIMEOUT;
3364 }
3365 }
3366
3367 if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DTIMEOUT))
3368 {
3369 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DTIMEOUT);
3370
3371 errorstate = 0;
3372
3373 return errorstate;
3374 }
3375 else if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_DCRCFAIL))
3376 {
3377 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_DCRCFAIL);
3378
3379 errorstate = SDMMC_ERROR_DATA_CRC_FAIL;
3380
3381 return errorstate;
3382 }
3383 else if (__HAL_SD_GET_FLAG(hsd, SDMMC_FLAG_RXOVERR))
3384 {
3385 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_FLAG_RXOVERR);
3386
3387 errorstate = SDMMC_ERROR_RX_OVERRUN;
3388
3389 return errorstate;
3390 }
3391 else
3392 {
3393 /* No error flag set */
3394 }
3395
3396 /* Clear all the static flags */
3397 __HAL_SD_CLEAR_FLAG(hsd, SDMMC_STATIC_DATA_FLAGS);
3398
3399 /* Test if the switch mode HS is ok */
3400 if ((((uint8_t*)SD_hs)[13] & 2U) != 2U)
3401 {
3402 errorstate = SDMMC_ERROR_UNSUPPORTED_FEATURE;
3403 }
3404 else
3405 {
3406 #if defined (USE_HAL_SD_REGISTER_CALLBACKS) && (USE_HAL_SD_REGISTER_CALLBACKS == 1U)
3407 hsd->DriveTransceiver_1_8V_Callback(SET);
3408 #else
3409 HAL_SD_DriveTransceiver_1_8V_Callback(SET);
3410 #endif
3411 #if defined (DLYB_SDMMC1) || defined (DLYB_SDMMC2)
3412 /* Enable DelayBlock IP */
3413 /* SDMMC_FB_CLK tuned feedback clock selected as receive clock, for SDR104 */
3414 MODIFY_REG(hsd->Instance->CLKCR, SDMMC_CLKCR_SELCLKRX,SDMMC_CLKCR_SELCLKRX_1);
3415 if (DelayBlock_Enable(DLYB_SDMMC1) != HAL_OK)
3416 {
3417 return (HAL_SD_ERROR_GENERAL_UNKNOWN_ERR);
3418 }
3419 #endif /* (DLYB_SDMMC1) || (DLYB_SDMMC2) */
3420 }
3421 }
3422
3423 return errorstate;
3424 }
3425 #endif /* USE_SD_TRANSCEIVER */
3426
3427 /**
3428 * @brief Read DMA Buffer 0 Transfer completed callbacks
3429 * @param hsd: SD handle
3430 * @retval None
3431 */
HAL_SDEx_Read_DMADoubleBuffer0CpltCallback(SD_HandleTypeDef * hsd)3432 __weak void HAL_SDEx_Read_DMADoubleBuffer0CpltCallback(SD_HandleTypeDef *hsd)
3433 {
3434 /* Prevent unused argument(s) compilation warning */
3435 UNUSED(hsd);
3436
3437 /* NOTE : This function should not be modified, when the callback is needed,
3438 the HAL_SDEx_Read_DMADoubleBuffer0CpltCallback can be implemented in the user file
3439 */
3440 }
3441
3442 /**
3443 * @brief Read DMA Buffer 1 Transfer completed callbacks
3444 * @param hsd: SD handle
3445 * @retval None
3446 */
HAL_SDEx_Read_DMADoubleBuffer1CpltCallback(SD_HandleTypeDef * hsd)3447 __weak void HAL_SDEx_Read_DMADoubleBuffer1CpltCallback(SD_HandleTypeDef *hsd)
3448 {
3449 /* Prevent unused argument(s) compilation warning */
3450 UNUSED(hsd);
3451
3452 /* NOTE : This function should not be modified, when the callback is needed,
3453 the HAL_SDEx_Read_DMADoubleBuffer1CpltCallback can be implemented in the user file
3454 */
3455 }
3456
3457 /**
3458 * @brief Write DMA Buffer 0 Transfer completed callbacks
3459 * @param hsd: SD handle
3460 * @retval None
3461 */
HAL_SDEx_Write_DMADoubleBuffer0CpltCallback(SD_HandleTypeDef * hsd)3462 __weak void HAL_SDEx_Write_DMADoubleBuffer0CpltCallback(SD_HandleTypeDef *hsd)
3463 {
3464 /* Prevent unused argument(s) compilation warning */
3465 UNUSED(hsd);
3466
3467 /* NOTE : This function should not be modified, when the callback is needed,
3468 the HAL_SDEx_Write_DMADoubleBuffer0CpltCallback can be implemented in the user file
3469 */
3470 }
3471
3472 /**
3473 * @brief Write DMA Buffer 1 Transfer completed callbacks
3474 * @param hsd: SD handle
3475 * @retval None
3476 */
HAL_SDEx_Write_DMADoubleBuffer1CpltCallback(SD_HandleTypeDef * hsd)3477 __weak void HAL_SDEx_Write_DMADoubleBuffer1CpltCallback(SD_HandleTypeDef *hsd)
3478 {
3479 /* Prevent unused argument(s) compilation warning */
3480 UNUSED(hsd);
3481
3482 /* NOTE : This function should not be modified, when the callback is needed,
3483 the HAL_SDEx_Write_DMADoubleBuffer0CpltCallback can be implemented in the user file
3484 */
3485 }
3486
3487
3488 /**
3489 * @}
3490 */
3491
3492 #endif /* HAL_SD_MODULE_ENABLED */
3493
3494 /**
3495 * @}
3496 */
3497
3498 /**
3499 * @}
3500 */
3501
3502 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
3503