Skip to main content
JBond.1
Senior
October 29, 2023
Question

SDCARD does not work with 4bits wide bus

  • October 29, 2023
  • 4 replies
  • 6127 views

Hi I have STM32F407 and after updating STM32CubeMX 6.6.1 -> 6.9.2 I faced the same issue with SD card:
https://community.st.com/t5/stm32cubemx-mcus/sdcard-does-not-work-fr-not-ready-when-migrating-from-fw-f4-v1/m-p/115499#M3876

It seems that with previous version we were working with 1bit wide bus even if we set 4bit wide bus. Although GPIOS were set for 4bits (SDIO_D0, SDIO_D1, SDIO_D2, SDIO_D3).


So after upgrading it changed to 4bits wide bus, but now we get `FR_NOT_READY`, `HAL_SD_ERROR_REQUEST_NOT_APPLICABLE`

/* If requested card supports wide bus operation */
 if((scr[1U] & SDMMC_WIDE_BUS_SUPPORT) != SDMMC_ALLZERO)
 {
 //...
 return HAL_SD_ERROR_NONE;
 }
 else
 {
 return HAL_SD_ERROR_REQUEST_NOT_APPLICABLE;
 }

 

How do I fix this and make SD card work with 4bits wide bus?

This topic has been closed for replies.

4 replies

JBond.1
JBond.1Author
Senior
October 29, 2023

I think STM32CubeMX has introduced a bug?

Initialization needs to be done with 1B and after that it should switch to 4B mode?

 

static void MX_SDIO_SD_Init(void)
{

 /* USER CODE BEGIN SDIO_Init 0 */

 /* USER CODE END SDIO_Init 0 */

 /* USER CODE BEGIN SDIO_Init 1 */

 /* USER CODE END SDIO_Init 1 */
 hsd.Instance = SDIO;
 hsd.Init.ClockEdge = SDIO_CLOCK_EDGE_RISING;
 hsd.Init.ClockBypass = SDIO_CLOCK_BYPASS_DISABLE;
 hsd.Init.ClockPowerSave = SDIO_CLOCK_POWER_SAVE_DISABLE;
 hsd.Init.BusWide = SDIO_BUS_WIDE_4B; // Initialization needs to be done with 1B?
 hsd.Init.HardwareFlowControl = SDIO_HARDWARE_FLOW_CONTROL_DISABLE;
 hsd.Init.ClockDiv = 12;
 /* USER CODE BEGIN SDIO_Init 2 */
 hsd.Init.BusWide = SDIO_BUS_WIDE_1B; // FIX?
 /* USER CODE END SDIO_Init 2 */

}

 

Now we need to override `hsd.Init.BusWide = SDIO_BUS_WIDE_1B;` for initialization to use 1bit and after initialization it switches to 4bit, no?

 

__weak uint8_t BSP_SD_Init(void)
{
 uint8_t sd_state = MSD_OK;
 /* Check if the SD card is plugged in the slot */
 if (BSP_SD_IsDetected() != SD_PRESENT)
 {
 return MSD_ERROR;
 }
 /* HAL SD initialization */
 sd_state = HAL_SD_Init(&hsd);
 /* Configure SD Bus width (4 bits mode selected) */
 if (sd_state == MSD_OK)
 {
 /* Enable wide operation */
 if (HAL_SD_ConfigWideBusOperation(&hsd, SDIO_BUS_WIDE_4B) != HAL_OK)
 {
 sd_state = MSD_ERROR;
 }
 }

 return sd_state;
}

 

Can STM32CubeMX team comment on this?

So STM32CubeMX 6.6.1 was correct and new versions have introduced a bug?

AScha.3
Super User
October 29, 2023

just search here in forum - see discussion + solution .

"If you feel a post has answered your question, please click ""Accept as Solution""."
TDK
Super User
October 29, 2023

There is this thread:

https://community.st.com/t5/stm32cubemx-mcus/sdcard-does-not-work-fr-not-ready-when-migrating-from-fw-f4-v1/td-p/115499

But it looks like the ST member who responded doesn't realize how SD works and thinks the change was a fix, rather than a bug/regression. So good luck with that.

"If you feel a post has answered your question, please click ""Accept as Solution""."
Ghofrane GSOURI
Technical Moderator
October 31, 2023

Hello @JBond.1 @TDK @AScha.3 

Thank you all  for your detailed explanation , and it's thanks to your contribution  that we're going to have a more mature version of MX.

An internal ticket is raised to dev team in order to fix this issue asap .

Internal ticket number: 155983 

 

Ghofrane

 

To give better visibility on the answered topics, please click on Accept as Solution on the reply which solved your issue or answered your question.
Marcelo Jimenez
Associate
December 7, 2023

Hi,

After some debugging, I found that there is a parameter called SDMMC clock divide factor that defaults to zero. The path to it is Connectivity -> SDMMC1 -> Configuration -> Parameter Settings -> SDMMC clock divide factor. I have set it to 1, which means one half of the kernel clock frequency, and now everything works, even with the triple initialization. I had 200 MHz in the original frequency, so I think this means the controller will operate at 100 MHz.

 

I suggest anyone with a similar problem to test increasing this parameter until the device works, maybe to a binary search, should take less than 10 attempts.

 

By the way, I am using 4 bit mode, so I still hope I can get a good speed from the card. Still, without a level converter circuit to 1.8 Volts, I know it is not possible to go full speed.

 

I did some changes to the original code, which I got from a tutorial video from ST. If anyone is interested, here is the code:

/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_DMA_Init();
MX_MDMA_Init();
MX_ADC3_Init();
MX_TIM1_Init();
MX_USART1_UART_Init();
MX_SDMMC1_SD_Init();
MX_FATFS_Init();
/* USER CODE BEGIN 2 */
...
res = f_mkfs((TCHAR const *)"", FM_ANY, 0, rtext, sizeof rtext);
if (res != FR_OK) {
 Error_Handler();
}
res = f_mount(&SDFatFS, (TCHAR const *)"", 1);
if (res != FR_OK) {
 Error_Handler();
}
// Open file for writing (Create)
res = f_open(&SDFile, "STM32.TXT", FA_CREATE_ALWAYS | FA_WRITE);
if (res != FR_OK) {
 Error_Handler();
}
// Write to the text file
res = f_write(&SDFile, wtext, strlen((char *)wtext), (void *)&bytes_written);
if ((bytes_written == 0) || (res != FR_OK)) {
 Error_Handler();
}
f_close(&SDFile);
/* FS == NULL -> umount */
res = f_mount(NULL, "", 0);
/* USER CODE END 2 */

 

AScha.3
Super User
December 7, 2023

btw

i wrote, you should set a max. clk of 50MHz...

>3. clock smmc with 50MHz , or lower until its working.

"If you feel a post has answered your question, please click ""Accept as Solution""."