cancel
Showing results for 
Search instead for 
Did you mean: 

Solution for STM32-F7 SDMMC in 4-Bit wide bus mode issue

Intector
Associate III

Hey,

I'm working on a project to connect my UHF RFID reader with ProfiNet via the NSHIELD 52-RE extension board. I chose the NUCLEO-F767ZI board for the development because it has an Ethernet interface, which I'm using for the web interface. The content for the web interface is stored on an SD Card connected to the SDMMC1 port of the F7 board. The issue I found is rooted in how the STM32CubeMX generates the code for the project, particularly for the SD card driver. The generated code contains a HAL_SD_Init with an SDMMC_BUS_WIDE_4B setting in the SD_HandleTypeDef.Init structure, which is OK so far. In the next step, the code calls the HAL_SD_ConfigWideBusOperation, which is when the issue appears. The SD_WideBus_Enable routine, which the HAL_SD_ConfigWideBusOperation calls, is reading the SCR register of the SD-Card, and this will fail because the card is initialized in 4-bit bus mode. I have this little workaround, which is somewhat annoying, but it works for now. 

this is the original generated code from the STM32CubeMX:

 

 

 

 

	hsd1.Instance = SDMMC1;
	hsd1.Init.ClockEdge = SDMMC_CLOCK_EDGE_RISING;
	hsd1.Init.ClockBypass = SDMMC_CLOCK_BYPASS_DISABLE;
	hsd1.Init.ClockPowerSave = SDMMC_CLOCK_POWER_SAVE_DISABLE;
	hsd1.Init.BusWide = SDMMC_BUS_WIDE_4B;
	hsd1.Init.HardwareFlowControl = SDMMC_HARDWARE_FLOW_CONTROL_DISABLE;
	hsd1.Init.ClockDiv = 0;
	if (HAL_SD_Init(&hsd1) != HAL_OK)
	{
		Error_Handler();
	}
	if (HAL_SD_ConfigWideBusOperation(&hsd1, SDMMC_BUS_WIDE_4B) != HAL_OK)
	{
		Error_Handler();
	}

 

 

 

 

here is my workaround:

 

 

 

 

	hsd1.Instance = SDMMC1;
	hsd1.Init.ClockEdge = SDMMC_CLOCK_EDGE_RISING;
	hsd1.Init.ClockBypass = SDMMC_CLOCK_BYPASS_DISABLE;
	hsd1.Init.ClockPowerSave = SDMMC_CLOCK_POWER_SAVE_DISABLE;
	hsd1.Init.BusWide = SDMMC_BUS_WIDE_4B;
	hsd1.Init.HardwareFlowControl = SDMMC_HARDWARE_FLOW_CONTROL_DISABLE;
	hsd1.Init.ClockDiv = 0;
	if (HAL_SD_Init(&hsd1) != HAL_OK)
	{
		Error_Handler();
	}

	// correcting SD-Card clock divider
	if (HAL_SD_InitCard_FIX(&hsd1) != HAL_OK)
	{
		Error_Handler();
	}
	
	if (HAL_SD_ConfigWideBusOperation(&hsd1, SDMMC_BUS_WIDE_4B) != HAL_OK)
	{
		Error_Handler();
	}

 

 

 

 

 

this function has to be added at the end between USER CODE BEGIN 1 and USER CODE END 1:

 

 

 

 

/* USER CODE BEGIN 1 */
HAL_StatusTypeDef HAL_SD_InitCard_FIX(SD_HandleTypeDef *hsd)
{
	HAL_StatusTypeDef status;
	SD_InitTypeDef Init;
 
	/* Default SDMMC peripheral configuration for SD card initialization */
	Init.ClockEdge           = SDMMC_CLOCK_EDGE_RISING;
	Init.ClockBypass         = SDMMC_CLOCK_BYPASS_DISABLE;
	Init.ClockPowerSave      = SDMMC_CLOCK_POWER_SAVE_DISABLE;
	Init.BusWide             = SDMMC_BUS_WIDE_1B;
	Init.HardwareFlowControl = SDMMC_HARDWARE_FLOW_CONTROL_DISABLE;
	Init.ClockDiv            = SDMMC_INIT_CLK_DIV;

	/* Initialize SDMMC peripheral interface with default configuration */
	status = SDMMC_Init(hsd->Instance, Init);
	if (status != HAL_OK)
	{
		return HAL_ERROR;
	}

	return HAL_OK;
}

/* USER CODE END 1 */

 

 

 

 

The function declaration is added to the end of the sdmmc.h:

 

 

 

 

/* USER CODE BEGIN Prototypes */
HAL_StatusTypeDef HAL_SD_InitCard_FIX(SD_HandleTypeDef *hsd);

/* USER CODE END Prototypes */

 

 

 

 

 

Since STM32CubeMX will overwrite everything outside of the "USER CODE" definitions, the view lines for the fix have to be copied every time the code is generated by STM32CubeMX. I wish there were a better way to do this, but until the makers of STM32CubeMX decide to change the code regarding this issue, I have to copy the code. 

However, I posted this in hope to safe others some time in their projects. 

and never forget:

"Always be yourself. Unless you can be a pirate. Then always be a pirate."

 

1 REPLY 1
Semer CHERNI
ST Employee

Hello @Intector 

First let me thank you for posting.

In fact this is a known issue and a permanent solution is under analysis.
The solution you proposed is an excellent temporary solution to the make it work.

KR,
Semer.

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.