feat(sdmmc): Concurrent use of SDMMC peripheral

Host and device (card, etc.) initialization is not thread-safe.
After initialization transactions are serialized and guarded by mutex.
Changed `SDMMC_HOST_DEFAULT()` default deinit function to `sdmmc_host_deinit_slot`
which has a slot number as argument.
This commit is contained in:
Adam Múdry
2024-08-06 10:34:13 +02:00
committed by BOT
parent c81c37fe1e
commit d29f0f3e21
7 changed files with 313 additions and 46 deletions

View File

@@ -26,7 +26,8 @@ extern "C" {
.flags = SDMMC_HOST_FLAG_8BIT | \
SDMMC_HOST_FLAG_4BIT | \
SDMMC_HOST_FLAG_1BIT | \
SDMMC_HOST_FLAG_DDR, \
SDMMC_HOST_FLAG_DDR | \
SDMMC_HOST_FLAG_DEINIT_ARG, \
.slot = SDMMC_HOST_SLOT_1, \
.max_freq_khz = SDMMC_FREQ_DEFAULT, \
.io_voltage = 3.3f, \
@@ -37,7 +38,7 @@ extern "C" {
.set_card_clk = &sdmmc_host_set_card_clk, \
.set_cclk_always_on = &sdmmc_host_set_cclk_always_on, \
.do_transaction = &sdmmc_host_do_transaction, \
.deinit = &sdmmc_host_deinit, \
.deinit_p = &sdmmc_host_deinit_slot, \
.io_int_enable = sdmmc_host_io_int_enable, \
.io_int_wait = sdmmc_host_io_int_wait, \
.command_timeout_ms = 0, \

View File

@@ -56,6 +56,14 @@ typedef struct {
*/
} sdmmc_slot_config_t;
/**
* SD/MMC host state structure
*/
typedef struct {
bool host_initialized; ///< Whether the host is initialized
int num_of_init_slots; ///< Number of initialized slots
} sdmmc_host_state_t;
/**
* @brief Initialize SDMMC host peripheral
*
@@ -198,13 +206,31 @@ esp_err_t sdmmc_host_io_int_enable(int slot);
esp_err_t sdmmc_host_io_int_wait(int slot, TickType_t timeout_ticks);
/**
* @brief Disable SDMMC host and release allocated resources
* @brief Disable SDMMC host and release allocated resources gracefully
*
* @note If there are more than 1 active slots, this function will just decrease the reference count
* and won't actually disable the host until the last slot is disabled
*
* @note This function is not thread safe
*
* @param slot slot number (SDMMC_HOST_SLOT_0 or SDMMC_HOST_SLOT_1)
* @return
* - ESP_OK on success
* - ESP_ERR_INVALID_STATE if SDMMC host has not been initialized
* - ESP_ERR_INVALID_ARG if invalid slot number is used
*/
esp_err_t sdmmc_host_deinit_slot(int slot);
/**
* @brief Disable SDMMC host and release allocated resources forcefully
*
* @note This function will deinitialize the host immediately, regardless of the number of active slots
*
* @note This function is not thread safe
*
* @return
* - ESP_OK on success
* - ESP_ERR_INVALID_STATE if sdmmc_host_init function has not been called
* - ESP_ERR_INVALID_STATE if SDMMC host has not been initialized
*/
esp_err_t sdmmc_host_deinit(void);
@@ -255,6 +281,17 @@ esp_err_t sdmmc_host_set_input_delay(int slot, sdmmc_delay_phase_t delay_phase);
*/
esp_err_t sdmmc_host_get_dma_info(int slot, esp_dma_mem_info_t *dma_mem_info);
/**
* @brief Get the state of SDMMC host
*
* @param[out] state output parameter for SDMMC host state structure
*
* @return
* - ESP_OK on success
* - ESP_ERR_INVALID_ARG on invalid argument
*/
esp_err_t sdmmc_host_get_state(sdmmc_host_state_t* state);
#ifdef __cplusplus
}
#endif