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