diff --git a/components/soc/esp32s2beta/include/hal/spi_ll.h b/components/soc/esp32s2beta/include/hal/spi_ll.h index 70b0c170ad..3f70b228ef 100644 --- a/components/soc/esp32s2beta/include/hal/spi_ll.h +++ b/components/soc/esp32s2beta/include/hal/spi_ll.h @@ -85,6 +85,9 @@ static inline void spi_ll_master_init(spi_dev_t *hw) //Disable unneeded ints hw->slave.val &= ~SPI_LL_UNUSED_INT_MASK; + + //disable a feature may cause transaction to be too long + hw->user.usr_prep_hold = 0; } /** @@ -778,24 +781,30 @@ static inline void spi_ll_set_address(spi_dev_t *hw, uint64_t addr, int addrlen, { if (lsbfirst) { /* The output address start from the LSB of the highest byte, i.e. - * addr[24] -> addr[31] - * ... - * addr[0] -> addr[7] - * slv_wr_status[24] -> slv_wr_status[31] - * ... - * slv_wr_status[0] -> slv_wr_status[7] - * So swap the byte order to let the LSB sent first. - */ + * addr[24] -> addr[31] + * ... + * addr[0] -> addr[7] + * So swap the byte order to let the LSB sent first. + */ addr = HAL_SWAP64(addr); - hw->addr = addr >> 32; - hw->slv_wr_status = addr; + if (addrlen > 32) { + //The slv_wr_status register bits are sent first, then + //bits in addr register is sent. + hw->slv_wr_status = addr >> 32; + hw->addr = addr; + } else { + //otherwise only addr register is sent + hw->addr = addr >> 32; + } } else { // shift the address to MSB of addr (and maybe slv_wr_status) register. - // output address will be sent from MSB to LSB of addr register, then comes the MSB to LSB of slv_wr_status register. if (addrlen > 32) { - hw->addr = addr >> (addrlen - 32); - hw->slv_wr_status = addr << (64 - addrlen); + // output address will be sent from MSB to LSB of slv_wr_status register, then comes the MSB to + // LSB of addr register. + hw->addr = addr << (64 - addrlen); + hw->slv_wr_status = addr >> (addrlen - 32); } else { + // output address will be sent from MSB to LSB of addr register hw->addr = addr << (32 - addrlen); } } diff --git a/components/soc/esp32s2beta/include/soc/soc.h b/components/soc/esp32s2beta/include/soc/soc.h index 8b5af5bd4f..52f0a42a85 100644 --- a/components/soc/esp32s2beta/include/soc/soc.h +++ b/components/soc/esp32s2beta/include/soc/soc.h @@ -168,7 +168,7 @@ #define APB_CLK_FREQ_ROM ( 40*1000000 ) #define CPU_CLK_FREQ_ROM APB_CLK_FREQ_ROM #define UART_CLK_FREQ_ROM APB_CLK_FREQ_ROM -#define CPU_CLK_FREQ APB_CLK_FREQ +#define CPU_CLK_FREQ APB_CLK_FREQ //this may be incorrect, please refer to ESP32_DEFAULT_CPU_FREQ_MHZ #define APB_CLK_FREQ ( 80*1000000 ) //unit: Hz #define REF_CLK_FREQ ( 1000000 ) #define UART_CLK_FREQ APB_CLK_FREQ diff --git a/components/soc/esp32s2beta/include/soc/spi_caps.h b/components/soc/esp32s2beta/include/soc/spi_caps.h index e28ed76ae7..cb47a14d68 100644 --- a/components/soc/esp32s2beta/include/soc/spi_caps.h +++ b/components/soc/esp32s2beta/include/soc/spi_caps.h @@ -17,7 +17,7 @@ #define SOC_SPI_PERIPH_NUM 4 #define SOC_SPI_DMA_CHAN_NUM 3 -#define SPI_FUNC_NUM 2 +#define SPI_FUNC_NUM 0 #define SPI_IOMUX_PIN_NUM_HD 27 #define SPI_IOMUX_PIN_NUM_CS 29 #define SPI_IOMUX_PIN_NUM_MOSI 32 diff --git a/components/soc/src/hal/spi_hal.c b/components/soc/src/hal/spi_hal.c index 6b7b40c36a..83c00d58a1 100644 --- a/components/soc/src/hal/spi_hal.c +++ b/components/soc/src/hal/spi_hal.c @@ -87,32 +87,32 @@ int spi_hal_master_cal_clock(int fapb, int hz, int duty_cycle) void spi_hal_cal_timing(int eff_clk, bool gpio_is_used, int input_delay_ns, int *dummy_n, int *miso_delay_n) { const int apbclk_kHz = APB_CLK_FREQ / 1000; - //calculate how many apb clocks a period has - const int apbclk_n = APB_CLK_FREQ / eff_clk; + //how many apb clocks a period has + const int spiclk_apb_n = APB_CLK_FREQ / eff_clk; const int gpio_delay_ns = gpio_is_used ? GPIO_MATRIX_DELAY_NS : 0; - //calculate how many apb clocks the delay is, the 1 is to compensate in case ``input_delay_ns`` is rounded off. - int apb_period_n = (1 + input_delay_ns + gpio_delay_ns) * apbclk_kHz / 1000 / 1000; - if (apb_period_n < 0) { - apb_period_n = 0; + //how many apb clocks the delay is, the 1 is to compensate in case ``input_delay_ns`` is rounded off. + int delay_apb_n = (1 + input_delay_ns + gpio_delay_ns) * apbclk_kHz / 1000 / 1000; + if (delay_apb_n < 0) { + delay_apb_n = 0; } - int dummy_required = apb_period_n / apbclk_n; + int dummy_required = delay_apb_n / spiclk_apb_n; int miso_delay = 0; if (dummy_required > 0) { //due to the clock delay between master and slave, there's a range in which data is random //give MISO a delay if needed to make sure we sample at the time MISO is stable - miso_delay = (dummy_required + 1) * apbclk_n - apb_period_n - 1; + miso_delay = (dummy_required + 1) * spiclk_apb_n - delay_apb_n - 1; } else { //if the dummy is not required, maybe we should also delay half a SPI clock if the data comes too early - if (apb_period_n * 4 <= apbclk_n) { + if (delay_apb_n * 4 <= spiclk_apb_n) { miso_delay = -1; } } *dummy_n = dummy_required; *miso_delay_n = miso_delay; - HAL_LOGD(SPI_HAL_TAG, "eff: %d, limit: %dk(/%d), %d dummy, %d delay", eff_clk / 1000, apbclk_kHz / (apb_period_n + 1), apb_period_n, dummy_required, miso_delay); + HAL_LOGD(SPI_HAL_TAG, "eff: %d, limit: %dk(/%d), %d dummy, %d delay", eff_clk / 1000, apbclk_kHz / (delay_apb_n + 1), delay_apb_n, dummy_required, miso_delay); } int spi_hal_get_freq_limit(bool gpio_is_used, int input_delay_ns) @@ -120,11 +120,11 @@ int spi_hal_get_freq_limit(bool gpio_is_used, int input_delay_ns) const int apbclk_kHz = APB_CLK_FREQ / 1000; const int gpio_delay_ns = gpio_is_used ? GPIO_MATRIX_DELAY_NS : 0; - //calculate how many apb clocks the delay is, the 1 is to compensate in case ``input_delay_ns`` is rounded off. - int apb_period_n = (1 + input_delay_ns + gpio_delay_ns) * apbclk_kHz / 1000 / 1000; - if (apb_period_n < 0) { - apb_period_n = 0; + //how many apb clocks the delay is, the 1 is to compensate in case ``input_delay_ns`` is rounded off. + int delay_apb_n = (1 + input_delay_ns + gpio_delay_ns) * apbclk_kHz / 1000 / 1000; + if (delay_apb_n < 0) { + delay_apb_n = 0; } - return APB_CLK_FREQ / (apb_period_n + 1); + return APB_CLK_FREQ / (delay_apb_n + 1); } \ No newline at end of file