Skip to content

Commit

Permalink
arch:hpmicro:sdmmc fix several bugs.
Browse files Browse the repository at this point in the history
- fixed the issue that the timeout feature is not working
- fixed the multi-block read/write issue
- fixed the clock_freq setting issue

Signed-off-by: Fan YANG <[email protected]>
  • Loading branch information
helloeagleyang committed Aug 8, 2024
1 parent 2c88c06 commit d575264
Show file tree
Hide file tree
Showing 4 changed files with 25 additions and 8 deletions.
2 changes: 2 additions & 0 deletions arch/risc-v/src/hpmicro/hpm_sdk/drivers/src/hpm_sdxc_drv.c
Original file line number Diff line number Diff line change
Expand Up @@ -498,6 +498,8 @@ void sdxc_init(SDXC_Type *base, const sdxc_config_t *config)

prot_ctrl |= SDXC_PROT_CTRL_SD_BUS_PWR_VDD1_MASK;

sdxc_enable_tm_clock(base);

sdxc_set_data_timeout(base, config->data_timeout, NULL);

base->PROT_CTRL = prot_ctrl;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -79,21 +79,22 @@ static inline void sdxc_select_cardclk_delay_source(SDXC_Type *base, bool loopba
}
}

/**
* @brief Set the Card Clock Delay chain
* @note This feature is not supported on this SoC
*/
static inline void sdxc_set_cardclk_delay_chain(SDXC_Type *base, uint32_t number_of_delaycells)
{
base->MISC_CTRL1 = (base->MISC_CTRL1 & ~SDXC_MISC_CTRL1_CARDCLK_DLYSEL_MASK) |
SDXC_MISC_CTRL1_CARDCLK_DLYSEL_SET(number_of_delaycells);
}

/**
* @brief Set SDXC data strobe delay chain
* @note This feature is not supported on this SoC
* @param [in] base SDXC base
* @param [in] num_of_delaycells Number of delay cells for Data strobe
*/
static inline void sdxc_set_data_strobe_delay(SDXC_Type *base, uint8_t num_of_delaycells)
{
base->MISC_CTRL1 = (base->MISC_CTRL1 & ~SDXC_MISC_CTRL1_STROBE_DLYSEL_MASK) |
SDXC_MISC_CTRL1_STROBE_DLYSEL_SET(num_of_delaycells);
}

static inline uint32_t sdxc_get_default_strobe_delay(SDXC_Type *base)
Expand Down
10 changes: 9 additions & 1 deletion arch/risc-v/src/hpmicro/hpm_sdk/soc/HPM6750/hpm_sdxc_soc_drv.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2021-2023 HPMicro
* Copyright (c) 2021-2024 HPMicro
*
* SPDX-License-Identifier: BSD-3-Clause
*
Expand All @@ -15,6 +15,14 @@
extern "C" {
#endif

/**
* @brief Enable TMCLK (for Data timeout detection)
*/
static inline void sdxc_enable_tm_clock(SDXC_Type *base)
{
volatile uint32_t *reg = (base == HPM_SDXC0) ? &HPM_CONCTL->CTRL4 : &HPM_CONCTL->CTRL5;
(*reg) |= (1UL << 10);
}

/**
* @brief Wait at least 74 clocks until card is ready to receive the first command
Expand Down
12 changes: 9 additions & 3 deletions arch/risc-v/src/hpmicro/hpm_sdmmc.c
Original file line number Diff line number Diff line change
Expand Up @@ -396,7 +396,7 @@ static void hpm_sdmmc_reset(FAR struct sdio_dev_s *dev)
flags = enter_critical_section();
clock_add_to_group(priv->clock_name, 0);
sdxc_config_t sdxc_config;
sdxc_config.data_timeout = 0xf;
sdxc_config.data_timeout = 1000;
sdxc_init(priv->base, &sdxc_config);
leave_critical_section(flags);
}
Expand Down Expand Up @@ -472,7 +472,7 @@ static void hpm_sdmmc_clock(FAR struct sdio_dev_s *dev, enum sdio_clock_e rate)
struct hpm_sdmmc_dev_s *priv = (struct hpm_sdmmc_dev_s *)dev;

bool need_disable = false;
bool clock_freq = 0;
uint32_t clock_freq = 0;
switch (rate)
{
default:
Expand Down Expand Up @@ -588,6 +588,7 @@ static int hpm_sdmmc_interrupt(int irq, void *context, void *arg)
{
priv->remaining = 0;
hpm_sdmmc_endxfer(priv, SDIOWAIT_ERROR);
break;
}

sdxc_clear_interrupt_status(priv->base, mask);
Expand Down Expand Up @@ -681,6 +682,11 @@ static int hpm_sdmmc_sendcmd(FAR struct sdio_dev_s *dev, uint32_t cmd, uint32_t
break;
}

if (cmd & MMCSD_MULTIBLOCK)
{
sdxc_cmd->cmd_flags |= SDXC_CMD_XFER_MULTI_BLK_SEL_MASK | SDXC_CMD_XFER_BLOCK_COUNT_ENABLE_MASK;
}

if ((sdxc_cmd->cmd_flags & SDXC_CMD_XFER_DATA_PRESENT_SEL_MASK) != 0U)
{
if (priv->dma_mode == HPM_SDMMC_DMA_MODE_ADMA2)
Expand Down Expand Up @@ -753,7 +759,7 @@ static int hpm_sdmmc_waitresponse(FAR struct sdio_dev_s *dev, uint32_t cmd)
{
struct hpm_sdmmc_dev_s *priv = (struct hpm_sdmmc_dev_s *)dev;

int32_t timeout;
int32_t timeout = HPM_SDMMC_CMDTIMEOUT;
uint32_t events = SDXC_INT_STAT_CMD_COMPLETE_MASK;
switch (cmd & MMCSD_RESPONSE_MASK)
{
Expand Down

0 comments on commit d575264

Please sign in to comment.