feat(driver_spi): support gpio reserved check

This commit is contained in:
wanckl
2025-04-25 20:55:20 +08:00
parent a952037d82
commit 4c11e81fd9
8 changed files with 240 additions and 272 deletions

View File

@ -97,26 +97,31 @@ typedef spi_common_dma_t spi_dma_chan_t;
*/ */
typedef struct { typedef struct {
union { union {
int mosi_io_num; ///< GPIO pin for Master Out Slave In (=spi_d) signal, or -1 if not used. struct {
int data0_io_num; ///< GPIO pin for spi data0 signal in quad/octal mode, or -1 if not used. union {
int mosi_io_num; ///< [0] GPIO pin for Master Out Slave In (=spi_d) signal, or -1 if not used.
int data0_io_num; ///< [0] GPIO pin for spi data0 signal in dual/quad/octal mode, or -1 if not used.
};
union {
int miso_io_num; ///< [1] GPIO pin for Master In Slave Out (=spi_q) signal, or -1 if not used.
int data1_io_num; ///< [1] GPIO pin for spi data1 signal in dual/quad/octal mode, or -1 if not used.
};
int sclk_io_num; ///< [2] GPIO pin for SPI Clock signal, or -1 if not used.
union {
int quadwp_io_num; ///< [3] GPIO pin for WP (Write Protect) signal, or -1 if not used.
int data2_io_num; ///< [3] GPIO pin for spi data2 signal in quad/octal mode, or -1 if not used.
};
union {
int quadhd_io_num; ///< [4] GPIO pin for HD (Hold) signal, or -1 if not used.
int data3_io_num; ///< [4] GPIO pin for spi data3 signal in quad/octal mode, or -1 if not used.
};
int data4_io_num; ///< [5] GPIO pin for spi data4 signal in octal mode, or -1 if not used.
int data5_io_num; ///< [6] GPIO pin for spi data5 signal in octal mode, or -1 if not used.
int data6_io_num; ///< [7] GPIO pin for spi data6 signal in octal mode, or -1 if not used.
int data7_io_num; ///< [8] GPIO pin for spi data7 signal in octal mode, or -1 if not used.
};
int iocfg[9]; ///< GPIO config in array format follow the above order.
}; };
union {
int miso_io_num; ///< GPIO pin for Master In Slave Out (=spi_q) signal, or -1 if not used.
int data1_io_num; ///< GPIO pin for spi data1 signal in quad/octal mode, or -1 if not used.
};
int sclk_io_num; ///< GPIO pin for SPI Clock signal, or -1 if not used.
union {
int quadwp_io_num; ///< GPIO pin for WP (Write Protect) signal, or -1 if not used.
int data2_io_num; ///< GPIO pin for spi data2 signal in quad/octal mode, or -1 if not used.
};
union {
int quadhd_io_num; ///< GPIO pin for HD (Hold) signal, or -1 if not used.
int data3_io_num; ///< GPIO pin for spi data3 signal in quad/octal mode, or -1 if not used.
};
int data4_io_num; ///< GPIO pin for spi data4 signal in octal mode, or -1 if not used.
int data5_io_num; ///< GPIO pin for spi data5 signal in octal mode, or -1 if not used.
int data6_io_num; ///< GPIO pin for spi data6 signal in octal mode, or -1 if not used.
int data7_io_num; ///< GPIO pin for spi data7 signal in octal mode, or -1 if not used.
bool data_io_default_level; ///< Output data IO default level when no transaction. bool data_io_default_level; ///< Output data IO default level when no transaction.
int max_transfer_sz; ///< Maximum transfer size, in bytes. Defaults to 4092 if 0 when DMA enabled, or to `SOC_SPI_MAXIMUM_BUFFER_SIZE` if DMA is disabled. int max_transfer_sz; ///< Maximum transfer size, in bytes. Defaults to 4092 if 0 when DMA enabled, or to `SOC_SPI_MAXIMUM_BUFFER_SIZE` if DMA is disabled.
uint32_t flags; ///< Abilities of bus to be checked by the driver. Or-ed value of ``SPICOMMON_BUSFLAG_*`` flags. uint32_t flags; ///< Abilities of bus to be checked by the driver. Or-ed value of ``SPICOMMON_BUSFLAG_*`` flags.

View File

@ -53,6 +53,7 @@ typedef enum {
/// Attributes of an SPI bus /// Attributes of an SPI bus
typedef struct { typedef struct {
spi_bus_config_t bus_cfg; ///< Config used to initialize the bus spi_bus_config_t bus_cfg; ///< Config used to initialize the bus
uint64_t gpio_reserve; ///< reserved output gpio bit mask
uint32_t flags; ///< Flags (attributes) of the bus uint32_t flags; ///< Flags (attributes) of the bus
int max_transfer_sz; ///< Maximum length of bytes available to send int max_transfer_sz; ///< Maximum length of bytes available to send
bool dma_enabled; ///< To enable DMA or not bool dma_enabled; ///< To enable DMA or not
@ -156,49 +157,44 @@ esp_err_t spicommon_dma_chan_free(spi_dma_ctx_t *dma_ctx);
* - ``SPICOMMON_BUSFLAG_QUAD``: Combination of ``SPICOMMON_BUSFLAG_DUAL`` and ``SPICOMMON_BUSFLAG_WPHD``. * - ``SPICOMMON_BUSFLAG_QUAD``: Combination of ``SPICOMMON_BUSFLAG_DUAL`` and ``SPICOMMON_BUSFLAG_WPHD``.
* - ``SPICOMMON_BUSFLAG_IO4_IO7``: The bus has spi data4 ~ spi data7 connected. * - ``SPICOMMON_BUSFLAG_IO4_IO7``: The bus has spi data4 ~ spi data7 connected.
* - ``SPICOMMON_BUSFLAG_OCTAL``: Combination of ``SPICOMMON_BUSFLAG_QUAL`` and ``SPICOMMON_BUSFLAG_IO4_IO7``. * - ``SPICOMMON_BUSFLAG_OCTAL``: Combination of ``SPICOMMON_BUSFLAG_QUAL`` and ``SPICOMMON_BUSFLAG_IO4_IO7``.
* @param[out] io_reserved Output the reserved gpio map
* @return * @return
* - ESP_ERR_INVALID_ARG if parameter is invalid * - ESP_ERR_INVALID_ARG if parameter is invalid
* - ESP_OK on success * - ESP_OK on success
*/ */
esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_config_t *bus_config, uint32_t flags, uint32_t *flags_o); esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_config_t *bus_config, uint32_t flags, uint32_t *flags_o, uint64_t *io_reserved);
/** /**
* @brief Free the IO used by a SPI peripheral * @brief Free the IO used by a SPI peripheral
* *
* @param bus_cfg Bus config struct which defines which pins to be used. * @param bus_cfg Bus config struct which defines which pins to be used.
* @param io_reserved Bitmap indicate which pin is reserved
* *
* @return * @return
* - ESP_ERR_INVALID_ARG if parameter is invalid * - ESP_ERR_INVALID_ARG if parameter is invalid
* - ESP_OK on success * - ESP_OK on success
*/ */
esp_err_t spicommon_bus_free_io_cfg(const spi_bus_config_t *bus_cfg); esp_err_t spicommon_bus_free_io_cfg(const spi_bus_config_t *bus_cfg, uint64_t *io_reserved);
/** /**
* @brief Initialize a Chip Select pin for a specific SPI peripheral * @brief Initialize a Chip Select pin for a specific SPI peripheral
* *
* @param host SPI peripheral * @param host SPI peripheral
* @param cs_io_num GPIO pin to route * @param cs_io_num GPIO pin to route
* @param cs_num CS id to route * @param cs_id Hardware CS id to route
* @param force_gpio_matrix If true, CS will always be routed through the GPIO matrix. If false, * @param force_gpio_matrix If true, CS will always be routed through the GPIO matrix. If false,
* if the GPIO number allows it, the routing will happen through the IO_mux. * if the GPIO number allows it, the routing will happen through the IO_mux.
* @param[out] io_reserved Output the reserved gpio map
*/ */
void spicommon_cs_initialize(spi_host_device_t host, int cs_io_num, int cs_num, int force_gpio_matrix); void spicommon_cs_initialize(spi_host_device_t host, int cs_io_num, int cs_id, int force_gpio_matrix, uint64_t *io_reserved);
/** /**
* @brief Free a chip select line * @brief Free a chip select line
* *
* @param cs_gpio_num CS gpio num to free * @param cs_gpio_num CS gpio num to free
* @param io_reserved Bitmap indicate which pin is reserved
*/ */
void spicommon_cs_free_io(int cs_gpio_num); void spicommon_cs_free_io(int cs_gpio_num, uint64_t *io_reserved);
/**
* @brief Check whether all pins used by a host are through IOMUX.
*
* @param host SPI peripheral
*
* @return false if any pins are through the GPIO matrix, otherwise true.
*/
bool spicommon_bus_using_iomux(spi_host_device_t host);
/** /**
* @brief Get the IRQ source for a specific SPI host * @brief Get the IRQ source for a specific SPI host
@ -298,8 +294,7 @@ const spi_dma_ctx_t* spi_bus_get_dma_ctx(spi_host_device_t host_id);
* @param arg The argument to call the destructor * @param arg The argument to call the destructor
* @return Always ESP_OK. * @return Always ESP_OK.
*/ */
esp_err_t spi_bus_register_destroy_func(spi_host_device_t host_id, esp_err_t spi_bus_register_destroy_func(spi_host_device_t host_id, spi_destroy_func_t f, void *arg);
spi_destroy_func_t f, void *arg);
#ifdef __cplusplus #ifdef __cplusplus
} }

View File

@ -17,6 +17,7 @@
#include "driver/spi_master.h" #include "driver/spi_master.h"
#include "driver/gpio.h" #include "driver/gpio.h"
#include "esp_private/gpio.h" #include "esp_private/gpio.h"
#include "esp_private/esp_gpio_reserve.h"
#include "esp_private/periph_ctrl.h" #include "esp_private/periph_ctrl.h"
#include "esp_private/spi_common_internal.h" #include "esp_private/spi_common_internal.h"
#include "esp_private/spi_share_hw_ctrl.h" #include "esp_private/spi_share_hw_ctrl.h"
@ -24,7 +25,6 @@
#include "esp_private/sleep_retention.h" #include "esp_private/sleep_retention.h"
#include "esp_dma_utils.h" #include "esp_dma_utils.h"
#include "hal/spi_hal.h" #include "hal/spi_hal.h"
#include "hal/gpio_hal.h"
#if CONFIG_IDF_TARGET_ESP32 #if CONFIG_IDF_TARGET_ESP32
#include "soc/dport_reg.h" #include "soc/dport_reg.h"
#endif #endif
@ -41,9 +41,9 @@
#define SPI_COMMON_MALLOC_CAPS (MALLOC_CAP_DEFAULT) #define SPI_COMMON_MALLOC_CAPS (MALLOC_CAP_DEFAULT)
#endif #endif
static const char *SPI_TAG = "spi"; static const char *SPI_TAG = "spi_common";
#define SPI_CHECK(a, str, ret_val) ESP_RETURN_ON_FALSE(a, ret_val, SPI_TAG, str) #define SPI_CHECK(a, str, ret_val, ...) ESP_RETURN_ON_FALSE(a, ret_val, SPI_TAG, str, ##__VA_ARGS__)
#define SPI_CHECK_PIN(pin_num, pin_name, check_output) if (check_output) { \ #define SPI_CHECK_PIN(pin_num, pin_name, check_output) if (check_output) { \
SPI_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(pin_num), pin_name" not valid", ESP_ERR_INVALID_ARG); \ SPI_CHECK(GPIO_IS_VALID_OUTPUT_GPIO(pin_num), pin_name" not valid", ESP_ERR_INVALID_ARG); \
} else { \ } else { \
@ -56,8 +56,6 @@ static const char *SPI_TAG = "spi";
}, \ }, \
} }
#define FUNC_GPIO PIN_FUNC_GPIO
typedef struct { typedef struct {
int host_id; int host_id;
_lock_t mutex; // mutex for controller _lock_t mutex; // mutex for controller
@ -80,6 +78,29 @@ static __attribute__((constructor)) void spi_bus_lock_init_main_bus(void)
} }
#endif #endif
esp_err_t spicommon_bus_alloc(spi_host_device_t host_id, const char *name)
{
SPI_CHECK(spicommon_periph_claim(host_id, name), "host already in use", ESP_ERR_INVALID_STATE);
spicommon_bus_context_t *ctx = heap_caps_calloc(1, sizeof(spicommon_bus_context_t), SPI_COMMON_MALLOC_CAPS);
if (!ctx) {
spicommon_periph_free(host_id);
return ESP_ERR_NO_MEM;
}
ctx->host_id = host_id;
bus_ctx[host_id] = ctx;
return ESP_OK;
}
esp_err_t spicommon_bus_free(spi_host_device_t host_id)
{
assert(bus_ctx[host_id]);
spicommon_periph_free(host_id);
free(bus_ctx[host_id]);
bus_ctx[host_id] = NULL;
return ESP_OK;
}
#if SOC_GDMA_SUPPORTED #if SOC_GDMA_SUPPORTED
//NOTE!! If both A and B are not defined, '#if (A==B)' is true, because GCC use 0 stand for undefined symbol //NOTE!! If both A and B are not defined, '#if (A==B)' is true, because GCC use 0 stand for undefined symbol
#if defined(SOC_GDMA_BUS_AXI) && (SOC_GDMA_TRIG_PERIPH_SPI2_BUS == SOC_GDMA_BUS_AXI) #if defined(SOC_GDMA_BUS_AXI) && (SOC_GDMA_TRIG_PERIPH_SPI2_BUS == SOC_GDMA_BUS_AXI)
@ -454,8 +475,8 @@ static void bus_iomux_pins_set_oct(spi_host_device_t host, const spi_bus_config_
bus_config->sclk_io_num, bus_config->data4_io_num, bus_config->data5_io_num, bus_config->data6_io_num, bus_config->data7_io_num bus_config->sclk_io_num, bus_config->data4_io_num, bus_config->data5_io_num, bus_config->data6_io_num, bus_config->data7_io_num
}; };
int io_signals[] = {spi_periph_signal[host].spid_in, spi_periph_signal[host].spiq_in, spi_periph_signal[host].spiwp_in, int io_signals[] = {spi_periph_signal[host].spid_in, spi_periph_signal[host].spiq_in, spi_periph_signal[host].spiwp_in,
spi_periph_signal[host].spihd_in, spi_periph_signal[host].spiclk_in, spi_periph_signal[host].spid4_out, spi_periph_signal[host].spihd_in, spi_periph_signal[host].spiclk_in, spi_periph_signal[host].spid4_in,
spi_periph_signal[host].spid5_out, spi_periph_signal[host].spid6_out, spi_periph_signal[host].spid7_out spi_periph_signal[host].spid5_in, spi_periph_signal[host].spid6_in, spi_periph_signal[host].spid7_in
}; };
for (size_t i = 0; i < sizeof(io_nums) / sizeof(io_nums[0]); i++) { for (size_t i = 0; i < sizeof(io_nums) / sizeof(io_nums[0]); i++) {
if (io_nums[i] > 0) { if (io_nums[i] > 0) {
@ -491,15 +512,28 @@ static void bus_iomux_pins_set_quad(spi_host_device_t host, const spi_bus_config
} }
} }
static void bus_iomux_pins_set(spi_host_device_t host, const spi_bus_config_t* bus_config) // check if the GPIO is already used by others
static void s_spi_common_gpio_check_reserve(gpio_num_t gpio_num)
{ {
#if SOC_SPI_SUPPORT_OCT uint64_t orig_occupied_map = esp_gpio_reserve(BIT64(gpio_num));
if ((bus_config->flags & SPICOMMON_BUSFLAG_OCTAL) == SPICOMMON_BUSFLAG_OCTAL) { if (orig_occupied_map & BIT64(gpio_num)) {
bus_iomux_pins_set_oct(host, bus_config); ESP_LOGW(SPI_TAG, "GPIO %d is conflict with others and be overwritten", gpio_num);
return;
} }
#endif }
bus_iomux_pins_set_quad(host, bus_config);
static void s_spi_common_bus_via_gpio(gpio_num_t gpio_num, int in_sig, int out_sig, uint64_t *io_mask)
{
if (in_sig != -1) {
gpio_input_enable(gpio_num);
esp_rom_gpio_connect_in_signal(gpio_num, in_sig, false);
}
if (out_sig != -1) {
// For gpio_matrix, reserve output pins, see 'esp_gpio_reserve.h'
*io_mask |= BIT64(gpio_num);
s_spi_common_gpio_check_reserve(gpio_num);
esp_rom_gpio_connect_out_signal(gpio_num, out_sig, false, false);
}
gpio_func_sel(gpio_num, PIN_FUNC_GPIO);
} }
/* /*
@ -507,7 +541,7 @@ Do the common stuff to hook up a SPI host to a bus defined by a bunch of GPIO pi
bus config struct and it'll set up the GPIO matrix and enable the device. If a pin is set to non-negative value, bus config struct and it'll set up the GPIO matrix and enable the device. If a pin is set to non-negative value,
it should be able to be initialized. it should be able to be initialized.
*/ */
esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_config_t *bus_config, uint32_t flags, uint32_t* flags_o) esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_config_t *bus_config, uint32_t flags, uint32_t* flags_o, uint64_t *io_reserved)
{ {
#if SOC_SPI_SUPPORT_OCT #if SOC_SPI_SUPPORT_OCT
// In the driver of previous version, spi data4 ~ spi data7 are not in spi_bus_config_t struct. So the new-added pins come as 0 // In the driver of previous version, spi data4 ~ spi data7 are not in spi_bus_config_t struct. So the new-added pins come as 0
@ -521,55 +555,33 @@ esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_conf
#endif //SOC_SPI_SUPPORT_OCT #endif //SOC_SPI_SUPPORT_OCT
uint32_t temp_flag = 0; uint32_t temp_flag = 0;
uint64_t gpio_reserv = 0;
bool miso_need_output;
bool mosi_need_output;
bool sclk_need_output;
if ((flags & SPICOMMON_BUSFLAG_MASTER) != 0) {
//initial for master
miso_need_output = ((flags & SPICOMMON_BUSFLAG_DUAL) != 0) ? true : false;
mosi_need_output = true;
sclk_need_output = true;
} else {
//initial for slave
miso_need_output = true;
mosi_need_output = ((flags & SPICOMMON_BUSFLAG_DUAL) != 0) ? true : false;
sclk_need_output = false;
}
const bool wp_need_output = true;
const bool hd_need_output = true;
//check pin capabilities //check pin capabilities
if (bus_config->sclk_io_num >= 0) { if (bus_config->sclk_io_num >= 0) {
temp_flag |= SPICOMMON_BUSFLAG_SCLK; temp_flag |= SPICOMMON_BUSFLAG_SCLK;
SPI_CHECK_PIN(bus_config->sclk_io_num, "sclk", sclk_need_output); SPI_CHECK_PIN(bus_config->sclk_io_num, "sclk", (flags & SPICOMMON_BUSFLAG_MASTER));
} }
if (bus_config->quadwp_io_num >= 0) { if (bus_config->quadwp_io_num >= 0) {
SPI_CHECK_PIN(bus_config->quadwp_io_num, "wp", wp_need_output); SPI_CHECK_PIN(bus_config->quadwp_io_num, "wp", true);
} }
if (bus_config->quadhd_io_num >= 0) { if (bus_config->quadhd_io_num >= 0) {
SPI_CHECK_PIN(bus_config->quadhd_io_num, "hd", hd_need_output); SPI_CHECK_PIN(bus_config->quadhd_io_num, "hd", true);
} }
#if SOC_SPI_SUPPORT_OCT #if SOC_SPI_SUPPORT_OCT
const bool io4_need_output = true;
const bool io5_need_output = true;
const bool io6_need_output = true;
const bool io7_need_output = true;
// set flags for OCTAL mode according to the existence of spi data4 ~ spi data7 // set flags for OCTAL mode according to the existence of spi data4 ~ spi data7
if (io4_7_enabled) { if (io4_7_enabled) {
temp_flag |= SPICOMMON_BUSFLAG_IO4_IO7; temp_flag |= SPICOMMON_BUSFLAG_IO4_IO7;
if (bus_config->data4_io_num >= 0) { if (bus_config->data4_io_num >= 0) {
SPI_CHECK_PIN(bus_config->data4_io_num, "spi data4", io4_need_output); SPI_CHECK_PIN(bus_config->data4_io_num, "spi data4", true);
} }
if (bus_config->data5_io_num >= 0) { if (bus_config->data5_io_num >= 0) {
SPI_CHECK_PIN(bus_config->data5_io_num, "spi data5", io5_need_output); SPI_CHECK_PIN(bus_config->data5_io_num, "spi data5", true);
} }
if (bus_config->data6_io_num >= 0) { if (bus_config->data6_io_num >= 0) {
SPI_CHECK_PIN(bus_config->data6_io_num, "spi data6", io6_need_output); SPI_CHECK_PIN(bus_config->data6_io_num, "spi data6", true);
} }
if (bus_config->data7_io_num >= 0) { if (bus_config->data7_io_num >= 0) {
SPI_CHECK_PIN(bus_config->data7_io_num, "spi data7", io7_need_output); SPI_CHECK_PIN(bus_config->data7_io_num, "spi data7", true);
} }
} }
#endif //SOC_SPI_SUPPORT_OCT #endif //SOC_SPI_SUPPORT_OCT
@ -580,11 +592,11 @@ esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_conf
} }
if (bus_config->mosi_io_num >= 0) { if (bus_config->mosi_io_num >= 0) {
temp_flag |= SPICOMMON_BUSFLAG_MOSI; temp_flag |= SPICOMMON_BUSFLAG_MOSI;
SPI_CHECK_PIN(bus_config->mosi_io_num, "mosi", mosi_need_output); SPI_CHECK_PIN(bus_config->mosi_io_num, "mosi", (flags & SPICOMMON_BUSFLAG_MASTER) || (temp_flag & SPICOMMON_BUSFLAG_DUAL));
} }
if (bus_config->miso_io_num >= 0) { if (bus_config->miso_io_num >= 0) {
temp_flag |= SPICOMMON_BUSFLAG_MISO; temp_flag |= SPICOMMON_BUSFLAG_MISO;
SPI_CHECK_PIN(bus_config->miso_io_num, "miso", miso_need_output); SPI_CHECK_PIN(bus_config->miso_io_num, "miso", !(flags & SPICOMMON_BUSFLAG_MASTER) || (temp_flag & SPICOMMON_BUSFLAG_DUAL));
} }
//set flags for DUAL mode according to output-capability of MOSI and MISO pins. //set flags for DUAL mode according to output-capability of MOSI and MISO pins.
if ((bus_config->mosi_io_num < 0 || GPIO_IS_VALID_OUTPUT_GPIO(bus_config->mosi_io_num)) && if ((bus_config->mosi_io_num < 0 || GPIO_IS_VALID_OUTPUT_GPIO(bus_config->mosi_io_num)) &&
@ -629,91 +641,64 @@ esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_conf
ESP_LOGE(SPI_TAG, "spi data4 ~ spi data7 are required."); ESP_LOGE(SPI_TAG, "spi data4 ~ spi data7 are required.");
} }
#endif #endif
SPI_CHECK(missing_flag == 0, "not all required capabilities satisfied.", ESP_ERR_INVALID_ARG); SPI_CHECK(false, "not all required capabilities satisfied.", ESP_ERR_INVALID_ARG);
} }
ESP_LOGD(SPI_TAG, "SPI%d use %s.", host + 1, use_iomux ? "iomux pins" : "gpio matrix");
if (use_iomux) { if (use_iomux) {
//All SPI iomux pin selections resolve to 1, so we put that here instead of trying to figure //All SPI iomux pin selections resolve to 1, so we put that here instead of trying to figure
//out which FUNC_GPIOx_xSPIxx to grab; they all are defined to 1 anyway. //out which PIN_FUNC_GPIOx_xSPIxx to grab; they all are defined to 1 anyway.
ESP_LOGD(SPI_TAG, "SPI%d use iomux pins.", host + 1); for (uint8_t i = 0; i < sizeof(bus_config->iocfg) / sizeof(bus_config->iocfg[0]); i++) {
bus_iomux_pins_set(host, bus_config); if (!(flags & SPICOMMON_BUSFLAG_OCTAL) && (i >= 4)) {
break;
}
// For iomux, reserve all configured pins
if (GPIO_IS_VALID_GPIO(bus_config->iocfg[i])) {
gpio_reserv |= BIT64(bus_config->iocfg[i]);
s_spi_common_gpio_check_reserve(bus_config->iocfg[i]);
}
}
bus_iomux_pins_set_quad(host, bus_config);
#if SOC_SPI_SUPPORT_OCT
if (flags & SPICOMMON_BUSFLAG_OCTAL) {
bus_iomux_pins_set_oct(host, bus_config);
}
#endif
} else { } else {
//Use GPIO matrix //Use GPIO matrix
ESP_LOGD(SPI_TAG, "SPI%d use gpio matrix.", host + 1);
if (bus_config->mosi_io_num >= 0) { if (bus_config->mosi_io_num >= 0) {
if (mosi_need_output || (temp_flag & SPICOMMON_BUSFLAG_DUAL)) { int in_sig = (!(flags & SPICOMMON_BUSFLAG_MASTER) || (temp_flag & SPICOMMON_BUSFLAG_DUAL)) ? spi_periph_signal[host].spid_in : -1;
gpio_set_direction(bus_config->mosi_io_num, GPIO_MODE_INPUT_OUTPUT); int out_sig = ((flags & SPICOMMON_BUSFLAG_MASTER) || (temp_flag & SPICOMMON_BUSFLAG_DUAL)) ? spi_periph_signal[host].spid_out : -1;
esp_rom_gpio_connect_out_signal(bus_config->mosi_io_num, spi_periph_signal[host].spid_out, false, false); s_spi_common_bus_via_gpio(bus_config->mosi_io_num, in_sig, out_sig, &gpio_reserv);
} else {
gpio_set_direction(bus_config->mosi_io_num, GPIO_MODE_INPUT);
}
esp_rom_gpio_connect_in_signal(bus_config->mosi_io_num, spi_periph_signal[host].spid_in, false);
#if CONFIG_IDF_TARGET_ESP32S2
PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[bus_config->mosi_io_num]);
#endif
gpio_func_sel(bus_config->mosi_io_num, FUNC_GPIO);
} }
if (bus_config->miso_io_num >= 0) { if (bus_config->miso_io_num >= 0) {
if (miso_need_output || (temp_flag & SPICOMMON_BUSFLAG_DUAL)) { int in_sig = ((flags & SPICOMMON_BUSFLAG_MASTER) || (temp_flag & SPICOMMON_BUSFLAG_DUAL)) ? spi_periph_signal[host].spiq_in : -1;
gpio_set_direction(bus_config->miso_io_num, GPIO_MODE_INPUT_OUTPUT); int out_sig = (!(flags & SPICOMMON_BUSFLAG_MASTER) || (temp_flag & SPICOMMON_BUSFLAG_DUAL)) ? spi_periph_signal[host].spiq_out : -1;
esp_rom_gpio_connect_out_signal(bus_config->miso_io_num, spi_periph_signal[host].spiq_out, false, false); s_spi_common_bus_via_gpio(bus_config->miso_io_num, in_sig, out_sig, &gpio_reserv);
} else {
gpio_set_direction(bus_config->miso_io_num, GPIO_MODE_INPUT);
}
esp_rom_gpio_connect_in_signal(bus_config->miso_io_num, spi_periph_signal[host].spiq_in, false);
#if CONFIG_IDF_TARGET_ESP32S2
PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[bus_config->miso_io_num]);
#endif
gpio_func_sel(bus_config->miso_io_num, FUNC_GPIO);
}
if (bus_config->quadwp_io_num >= 0) {
gpio_set_direction(bus_config->quadwp_io_num, GPIO_MODE_INPUT_OUTPUT);
esp_rom_gpio_connect_out_signal(bus_config->quadwp_io_num, spi_periph_signal[host].spiwp_out, false, false);
esp_rom_gpio_connect_in_signal(bus_config->quadwp_io_num, spi_periph_signal[host].spiwp_in, false);
#if CONFIG_IDF_TARGET_ESP32S2
PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[bus_config->quadwp_io_num]);
#endif
gpio_func_sel(bus_config->quadwp_io_num, FUNC_GPIO);
}
if (bus_config->quadhd_io_num >= 0) {
gpio_set_direction(bus_config->quadhd_io_num, GPIO_MODE_INPUT_OUTPUT);
esp_rom_gpio_connect_out_signal(bus_config->quadhd_io_num, spi_periph_signal[host].spihd_out, false, false);
esp_rom_gpio_connect_in_signal(bus_config->quadhd_io_num, spi_periph_signal[host].spihd_in, false);
#if CONFIG_IDF_TARGET_ESP32S2
PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[bus_config->quadhd_io_num]);
#endif
gpio_func_sel(bus_config->quadhd_io_num, FUNC_GPIO);
} }
if (bus_config->sclk_io_num >= 0) { if (bus_config->sclk_io_num >= 0) {
if (sclk_need_output) { int in_sig = (flags & SPICOMMON_BUSFLAG_MASTER) ? -1 : spi_periph_signal[host].spiclk_in;
gpio_set_direction(bus_config->sclk_io_num, GPIO_MODE_INPUT_OUTPUT); int out_sig = (flags & SPICOMMON_BUSFLAG_MASTER) ? spi_periph_signal[host].spiclk_out : -1;
esp_rom_gpio_connect_out_signal(bus_config->sclk_io_num, spi_periph_signal[host].spiclk_out, false, false); s_spi_common_bus_via_gpio(bus_config->sclk_io_num, in_sig, out_sig, &gpio_reserv);
} else { }
gpio_set_direction(bus_config->sclk_io_num, GPIO_MODE_INPUT); if (bus_config->quadwp_io_num >= 0) {
} s_spi_common_bus_via_gpio(bus_config->quadwp_io_num, spi_periph_signal[host].spiwp_in, spi_periph_signal[host].spiwp_out, &gpio_reserv);
esp_rom_gpio_connect_in_signal(bus_config->sclk_io_num, spi_periph_signal[host].spiclk_in, false); }
#if CONFIG_IDF_TARGET_ESP32S2 if (bus_config->quadhd_io_num >= 0) {
PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[bus_config->sclk_io_num]); s_spi_common_bus_via_gpio(bus_config->quadhd_io_num, spi_periph_signal[host].spihd_in, spi_periph_signal[host].spihd_out, &gpio_reserv);
#endif
gpio_func_sel(bus_config->sclk_io_num, FUNC_GPIO);
} }
#if SOC_SPI_SUPPORT_OCT #if SOC_SPI_SUPPORT_OCT
if ((flags & SPICOMMON_BUSFLAG_OCTAL) == SPICOMMON_BUSFLAG_OCTAL) { if (flags & SPICOMMON_BUSFLAG_OCTAL) {
int io_nums[] = {bus_config->data4_io_num, bus_config->data5_io_num, bus_config->data6_io_num, bus_config->data7_io_num}; int io_nums[] = {bus_config->data4_io_num, bus_config->data5_io_num, bus_config->data6_io_num, bus_config->data7_io_num};
uint8_t io_signals[4][2] = {{spi_periph_signal[host].spid4_out, spi_periph_signal[host].spid4_in}, uint8_t io_signals[4][2] = {
{spi_periph_signal[host].spid4_out, spi_periph_signal[host].spid4_in},
{spi_periph_signal[host].spid5_out, spi_periph_signal[host].spid5_in}, {spi_periph_signal[host].spid5_out, spi_periph_signal[host].spid5_in},
{spi_periph_signal[host].spid6_out, spi_periph_signal[host].spid6_in}, {spi_periph_signal[host].spid6_out, spi_periph_signal[host].spid6_in},
{spi_periph_signal[host].spid7_out, spi_periph_signal[host].spid7_in} {spi_periph_signal[host].spid7_out, spi_periph_signal[host].spid7_in}
}; };
for (size_t i = 0; i < sizeof(io_nums) / sizeof(io_nums[0]); i++) { for (size_t i = 0; i < sizeof(io_nums) / sizeof(io_nums[0]); i++) {
if (io_nums[i] >= 0) { if (io_nums[i] >= 0) {
gpio_set_direction(io_nums[i], GPIO_MODE_INPUT_OUTPUT); s_spi_common_bus_via_gpio(io_nums[i], io_signals[i][1], io_signals[i][0], &gpio_reserv);
esp_rom_gpio_connect_out_signal(io_nums[i], io_signals[i][0], false, false);
esp_rom_gpio_connect_in_signal(io_nums[i], io_signals[i][1], false);
#if CONFIG_IDF_TARGET_ESP32S2
PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[io_nums[i]]);
#endif
gpio_func_sel(io_nums[i], FUNC_GPIO);
} }
} }
} }
@ -723,64 +708,64 @@ esp_err_t spicommon_bus_initialize_io(spi_host_device_t host, const spi_bus_conf
if (flags_o) { if (flags_o) {
*flags_o = temp_flag; *flags_o = temp_flag;
} }
if (io_reserved) {
*io_reserved |= gpio_reserv;
}
return ESP_OK; return ESP_OK;
} }
esp_err_t spicommon_bus_free_io_cfg(const spi_bus_config_t *bus_cfg) esp_err_t spicommon_bus_free_io_cfg(const spi_bus_config_t *bus_cfg, uint64_t *io_reserved)
{ {
int pin_array[] = { for (uint8_t i = 0; i < sizeof(bus_cfg->iocfg) / sizeof(bus_cfg->iocfg[0]); i++) {
bus_cfg->mosi_io_num, #if !SOC_SPI_SUPPORT_OCT
bus_cfg->miso_io_num, if (i > 4) {
bus_cfg->sclk_io_num, break;
bus_cfg->quadwp_io_num, }
bus_cfg->quadhd_io_num, #endif
}; if (GPIO_IS_VALID_GPIO(bus_cfg->iocfg[i]) && (*io_reserved & BIT64(bus_cfg->iocfg[i]))) {
for (int i = 0; i < sizeof(pin_array) / sizeof(int); i ++) { *io_reserved &= ~BIT64(bus_cfg->iocfg[i]);
const int io = pin_array[i]; gpio_output_disable(bus_cfg->iocfg[i]);
if (GPIO_IS_VALID_GPIO(io)) { esp_gpio_revoke(BIT64(bus_cfg->iocfg[i]));
gpio_reset_pin(io);
} }
} }
return ESP_OK; return ESP_OK;
} }
void spicommon_cs_initialize(spi_host_device_t host, int cs_io_num, int cs_num, int force_gpio_matrix) void spicommon_cs_initialize(spi_host_device_t host, int cs_io_num, int cs_id, int force_gpio_matrix, uint64_t *io_reserved)
{ {
if (!force_gpio_matrix && cs_io_num == spi_periph_signal[host].spics0_iomux_pin && cs_num == 0) { uint64_t out_mask = 0;
if (!force_gpio_matrix && cs_io_num == spi_periph_signal[host].spics0_iomux_pin && cs_id == 0) {
out_mask |= BIT64(cs_io_num);
s_spi_common_gpio_check_reserve(cs_io_num);
//The cs0s for all SPI peripherals map to pin mux source 1, so we use that instead of a define. //The cs0s for all SPI peripherals map to pin mux source 1, so we use that instead of a define.
gpio_iomux_input(cs_io_num, spi_periph_signal[host].func, spi_periph_signal[host].spics_in); gpio_iomux_input(cs_io_num, spi_periph_signal[host].func, spi_periph_signal[host].spics_in);
gpio_iomux_output(cs_io_num, spi_periph_signal[host].func); gpio_iomux_output(cs_io_num, spi_periph_signal[host].func);
} else { } else {
//Use GPIO matrix //Use GPIO matrix
if (GPIO_IS_VALID_OUTPUT_GPIO(cs_io_num)) { if (GPIO_IS_VALID_OUTPUT_GPIO(cs_io_num)) {
gpio_set_direction(cs_io_num, GPIO_MODE_INPUT_OUTPUT); out_mask |= BIT64(cs_io_num);
esp_rom_gpio_connect_out_signal(cs_io_num, spi_periph_signal[host].spics_out[cs_num], false, false); s_spi_common_gpio_check_reserve(cs_io_num);
} else { esp_rom_gpio_connect_out_signal(cs_io_num, spi_periph_signal[host].spics_out[cs_id], false, false);
gpio_set_direction(cs_io_num, GPIO_MODE_INPUT);
} }
if (cs_num == 0) { // cs_id 0 is always used by slave for input
if (cs_id == 0) {
gpio_input_enable(cs_io_num);
esp_rom_gpio_connect_in_signal(cs_io_num, spi_periph_signal[host].spics_in, false); esp_rom_gpio_connect_in_signal(cs_io_num, spi_periph_signal[host].spics_in, false);
} }
#if CONFIG_IDF_TARGET_ESP32S2 gpio_func_sel(cs_io_num, PIN_FUNC_GPIO);
PIN_INPUT_ENABLE(GPIO_PIN_MUX_REG[cs_io_num]); }
#endif if (io_reserved) {
gpio_func_sel(cs_io_num, FUNC_GPIO); *io_reserved |= out_mask;
} }
} }
void spicommon_cs_free_io(int cs_gpio_num) void spicommon_cs_free_io(int cs_gpio_num, uint64_t *io_reserved)
{ {
assert(GPIO_IS_VALID_GPIO(cs_gpio_num)); if (GPIO_IS_VALID_GPIO(cs_gpio_num) && (*io_reserved & BIT64(cs_gpio_num))) {
gpio_reset_pin(cs_gpio_num); *io_reserved &= ~BIT64(cs_gpio_num);
} gpio_output_disable(cs_gpio_num);
esp_gpio_revoke(BIT64(cs_gpio_num));
bool spicommon_bus_using_iomux(spi_host_device_t host) }
{
CHECK_IOMUX_PIN(host, spid);
CHECK_IOMUX_PIN(host, spiq);
CHECK_IOMUX_PIN(host, spiwp);
CHECK_IOMUX_PIN(host, spihd);
return true;
} }
spi_bus_lock_handle_t spi_bus_lock_get_by_id(spi_host_device_t host_id) spi_bus_lock_handle_t spi_bus_lock_get_by_id(spi_host_device_t host_id)
@ -802,9 +787,6 @@ static esp_err_t s_bus_create_sleep_retention_cb(void *arg)
esp_err_t spi_bus_initialize(spi_host_device_t host_id, const spi_bus_config_t *bus_config, spi_dma_chan_t dma_chan) esp_err_t spi_bus_initialize(spi_host_device_t host_id, const spi_bus_config_t *bus_config, spi_dma_chan_t dma_chan)
{ {
esp_err_t err = ESP_OK; esp_err_t err = ESP_OK;
spicommon_bus_context_t *ctx = NULL;
spi_bus_attr_t *bus_attr = NULL;
SPI_CHECK(is_valid_host(host_id), "invalid host_id", ESP_ERR_INVALID_ARG); SPI_CHECK(is_valid_host(host_id), "invalid host_id", ESP_ERR_INVALID_ARG);
SPI_CHECK(bus_ctx[host_id] == NULL, "SPI bus already initialized.", ESP_ERR_INVALID_STATE); SPI_CHECK(bus_ctx[host_id] == NULL, "SPI bus already initialized.", ESP_ERR_INVALID_STATE);
#ifdef CONFIG_IDF_TARGET_ESP32 #ifdef CONFIG_IDF_TARGET_ESP32
@ -822,18 +804,9 @@ esp_err_t spi_bus_initialize(spi_host_device_t host_id, const spi_bus_config_t *
SPI_CHECK((bus_config->data_io_default_level == 0), "no support changing io default level ", ESP_ERR_INVALID_ARG); SPI_CHECK((bus_config->data_io_default_level == 0), "no support changing io default level ", ESP_ERR_INVALID_ARG);
#endif #endif
bool spi_chan_claimed = spicommon_periph_claim(host_id, "spi master"); ESP_RETURN_ON_ERROR(spicommon_bus_alloc(host_id, "spi master"), SPI_TAG, "alloc host failed");
SPI_CHECK(spi_chan_claimed, "host_id already in use", ESP_ERR_INVALID_STATE); spi_bus_attr_t *bus_attr = (spi_bus_attr_t *)spi_bus_get_attr(host_id);
spicommon_bus_context_t *ctx = __containerof(bus_attr, spicommon_bus_context_t, bus_attr);
//clean and initialize the context
ctx = (spicommon_bus_context_t *)heap_caps_calloc(1, sizeof(spicommon_bus_context_t), SPI_COMMON_MALLOC_CAPS);
if (!ctx) {
err = ESP_ERR_NO_MEM;
goto cleanup;
}
bus_ctx[host_id] = ctx;
ctx->host_id = host_id;
bus_attr = &ctx->bus_attr;
bus_attr->bus_cfg = *bus_config; bus_attr->bus_cfg = *bus_config;
if (dma_chan != SPI_DMA_DISABLED) { if (dma_chan != SPI_DMA_DISABLED) {
@ -908,7 +881,7 @@ esp_err_t spi_bus_initialize(spi_host_device_t host_id, const spi_bus_config_t *
} }
#endif //CONFIG_PM_ENABLE #endif //CONFIG_PM_ENABLE
err = spicommon_bus_initialize_io(host_id, bus_config, SPICOMMON_BUSFLAG_MASTER | bus_config->flags, &bus_attr->flags); err = spicommon_bus_initialize_io(host_id, bus_config, SPICOMMON_BUSFLAG_MASTER | bus_config->flags, &bus_attr->flags, &bus_attr->gpio_reserve);
if (err != ESP_OK) { if (err != ESP_OK) {
goto cleanup; goto cleanup;
} }
@ -930,9 +903,7 @@ cleanup:
ctx->dma_ctx = NULL; ctx->dma_ctx = NULL;
} }
} }
spicommon_periph_free(host_id); spicommon_bus_free(host_id);
free(bus_ctx[host_id]);
bus_ctx[host_id] = NULL;
return err; return err;
} }
@ -979,7 +950,7 @@ esp_err_t spi_bus_free(spi_host_device_t host_id)
return err; return err;
} }
} }
spicommon_bus_free_io_cfg(&bus_attr->bus_cfg); spicommon_bus_free_io_cfg(&bus_attr->bus_cfg, &bus_attr->gpio_reserve);
#if SOC_SPI_SUPPORT_SLEEP_RETENTION && CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP #if SOC_SPI_SUPPORT_SLEEP_RETENTION && CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP
const periph_retention_module_t retention_id = spi_reg_retention_info[host_id - 1].module_id; const periph_retention_module_t retention_id = spi_reg_retention_info[host_id - 1].module_id;
@ -1006,9 +977,7 @@ esp_err_t spi_bus_free(spi_host_device_t host_id)
spicommon_dma_chan_free(ctx->dma_ctx); spicommon_dma_chan_free(ctx->dma_ctx);
ctx->dma_ctx = NULL; ctx->dma_ctx = NULL;
} }
spicommon_periph_free(host_id); spicommon_bus_free(host_id);
free(ctx);
bus_ctx[host_id] = NULL;
return err; return err;
} }

View File

@ -527,7 +527,7 @@ esp_err_t spi_bus_add_device(spi_host_device_t host_id, const spi_device_interfa
//Set CS pin, CS options //Set CS pin, CS options
if (dev_config->spics_io_num >= 0) { if (dev_config->spics_io_num >= 0) {
spicommon_cs_initialize(host_id, dev_config->spics_io_num, freecs, use_gpio); spicommon_cs_initialize(host_id, dev_config->spics_io_num, freecs, use_gpio, (uint64_t *)&bus_attr->gpio_reserve);
} }
//save a pointer to device in spi_host_t //save a pointer to device in spi_host_t
@ -605,8 +605,9 @@ esp_err_t spi_bus_remove_device(spi_device_handle_t handle)
//return //return
int spics_io_num = handle->cfg.spics_io_num; int spics_io_num = handle->cfg.spics_io_num;
const spi_bus_attr_t* bus_attr = handle->host->bus_attr;
if (spics_io_num >= 0) { if (spics_io_num >= 0) {
spicommon_cs_free_io(spics_io_num); spicommon_cs_free_io(spics_io_num, (uint64_t *)&bus_attr->gpio_reserve);
} }
//Kill queues //Kill queues

View File

@ -61,6 +61,7 @@ typedef struct {
typedef struct { typedef struct {
int id; int id;
_Atomic spi_bus_fsm_t fsm; _Atomic spi_bus_fsm_t fsm;
uint64_t gpio_reserve;
spi_bus_config_t bus_config; spi_bus_config_t bus_config;
spi_dma_ctx_t *dma_ctx; spi_dma_ctx_t *dma_ctx;
spi_slave_interface_config_t cfg; spi_slave_interface_config_t cfg;
@ -145,7 +146,6 @@ static esp_err_t s_spi_create_sleep_retention_cb(void *arg)
esp_err_t spi_slave_initialize(spi_host_device_t host, const spi_bus_config_t *bus_config, const spi_slave_interface_config_t *slave_config, spi_dma_chan_t dma_chan) esp_err_t spi_slave_initialize(spi_host_device_t host, const spi_bus_config_t *bus_config, const spi_slave_interface_config_t *slave_config, spi_dma_chan_t dma_chan)
{ {
bool spi_chan_claimed;
esp_err_t ret = ESP_OK; esp_err_t ret = ESP_OK;
esp_err_t err; esp_err_t err;
SPI_CHECK(is_valid_host(host), "invalid host", ESP_ERR_INVALID_ARG); SPI_CHECK(is_valid_host(host), "invalid host", ESP_ERR_INVALID_ARG);
@ -167,16 +167,13 @@ esp_err_t spi_slave_initialize(spi_host_device_t host, const spi_bus_config_t *b
SPI_CHECK(slave_config->post_trans_cb != NULL, "use feature flag 'SPI_SLAVE_NO_RETURN_RESULT' but no post_trans_cb function sets", ESP_ERR_INVALID_ARG); SPI_CHECK(slave_config->post_trans_cb != NULL, "use feature flag 'SPI_SLAVE_NO_RETURN_RESULT' but no post_trans_cb function sets", ESP_ERR_INVALID_ARG);
} }
spi_chan_claimed = spicommon_periph_claim(host, "spi slave"); SPI_CHECK(spicommon_periph_claim(host, "spi slave"), "host already in use", ESP_ERR_INVALID_STATE);
SPI_CHECK(spi_chan_claimed, "host already in use", ESP_ERR_INVALID_STATE);
// spi_slave_t contains atomic variable, memory must be allocated from internal memory // spi_slave_t contains atomic variable, memory must be allocated from internal memory
spihost[host] = heap_caps_malloc(sizeof(spi_slave_t), MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT); spihost[host] = heap_caps_calloc(1, sizeof(spi_slave_t), MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT);
if (spihost[host] == NULL) { if (spihost[host] == NULL) {
ret = ESP_ERR_NO_MEM; ret = ESP_ERR_NO_MEM;
goto cleanup; goto cleanup;
} }
memset(spihost[host], 0, sizeof(spi_slave_t));
memcpy(&spihost[host]->cfg, slave_config, sizeof(spi_slave_interface_config_t)); memcpy(&spihost[host]->cfg, slave_config, sizeof(spi_slave_interface_config_t));
memcpy(&spihost[host]->bus_config, bus_config, sizeof(spi_bus_config_t)); memcpy(&spihost[host]->bus_config, bus_config, sizeof(spi_bus_config_t));
spihost[host]->id = host; spihost[host]->id = host;
@ -210,13 +207,13 @@ esp_err_t spi_slave_initialize(spi_host_device_t host, const spi_bus_config_t *b
spihost[host]->max_transfer_sz = SOC_SPI_MAXIMUM_BUFFER_SIZE; spihost[host]->max_transfer_sz = SOC_SPI_MAXIMUM_BUFFER_SIZE;
} }
err = spicommon_bus_initialize_io(host, bus_config, SPICOMMON_BUSFLAG_SLAVE | bus_config->flags, &spihost[host]->flags); err = spicommon_bus_initialize_io(host, bus_config, SPICOMMON_BUSFLAG_SLAVE | bus_config->flags, &spihost[host]->flags, &spihost[host]->gpio_reserve);
if (err != ESP_OK) { if (err != ESP_OK) {
ret = err; ret = err;
goto cleanup; goto cleanup;
} }
if (slave_config->spics_io_num >= 0) { if (slave_config->spics_io_num >= 0) {
spicommon_cs_initialize(host, slave_config->spics_io_num, 0, !bus_is_iomux(spihost[host])); spicommon_cs_initialize(host, slave_config->spics_io_num, 0, !bus_is_iomux(spihost[host]), &spihost[host]->gpio_reserve);
// check and save where cs line really route through // check and save where cs line really route through
spihost[host]->cs_iomux = (slave_config->spics_io_num == spi_periph_signal[host].spics0_iomux_pin) && bus_is_iomux(spihost[host]); spihost[host]->cs_iomux = (slave_config->spics_io_num == spi_periph_signal[host].spics0_iomux_pin) && bus_is_iomux(spihost[host]);
spihost[host]->cs_in_signal = spi_periph_signal[host].spics_in; spihost[host]->cs_in_signal = spi_periph_signal[host].spics_in;
@ -334,7 +331,10 @@ esp_err_t spi_slave_free(spi_host_device_t host)
free(spihost[host]->dma_ctx->dmadesc_rx); free(spihost[host]->dma_ctx->dmadesc_rx);
spicommon_dma_chan_free(spihost[host]->dma_ctx); spicommon_dma_chan_free(spihost[host]->dma_ctx);
} }
spicommon_bus_free_io_cfg(&spihost[host]->bus_config); spicommon_bus_free_io_cfg(&spihost[host]->bus_config, &spihost[host]->gpio_reserve);
if (spihost[host]->cfg.spics_io_num >= 0) {
spicommon_cs_free_io(spihost[host]->cfg.spics_io_num, &spihost[host]->gpio_reserve);
}
esp_intr_free(spihost[host]->intr); esp_intr_free(spihost[host]->intr);
#if SOC_SPI_SUPPORT_SLEEP_RETENTION && CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP #if SOC_SPI_SUPPORT_SLEEP_RETENTION && CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP

View File

@ -44,6 +44,9 @@ typedef struct {
typedef struct { typedef struct {
spi_host_device_t host_id; spi_host_device_t host_id;
spi_bus_config_t bus_config;
int cs_io_num;
uint64_t gpio_reserve;
_Atomic spi_bus_fsm_t fsm; _Atomic spi_bus_fsm_t fsm;
spi_dma_ctx_t *dma_ctx; spi_dma_ctx_t *dma_ctx;
uint16_t internal_mem_align_size; uint16_t internal_mem_align_size;
@ -100,7 +103,6 @@ static esp_err_t s_spi_create_sleep_retention_cb(void *arg)
esp_err_t spi_slave_hd_init(spi_host_device_t host_id, const spi_bus_config_t *bus_config, const spi_slave_hd_slot_config_t *config) esp_err_t spi_slave_hd_init(spi_host_device_t host_id, const spi_bus_config_t *bus_config, const spi_slave_hd_slot_config_t *config)
{ {
bool spi_chan_claimed;
bool append_mode = (config->flags & SPI_SLAVE_HD_APPEND_MODE); bool append_mode = (config->flags & SPI_SLAVE_HD_APPEND_MODE);
esp_err_t ret = ESP_OK; esp_err_t ret = ESP_OK;
@ -115,9 +117,8 @@ esp_err_t spi_slave_hd_init(spi_host_device_t host_id, const spi_bus_config_t *b
SPIHD_CHECK((bus_config->intr_flags & ESP_INTR_FLAG_IRAM) == 0, "ESP_INTR_FLAG_IRAM should be disabled when CONFIG_SPI_SLAVE_ISR_IN_IRAM is not set.", ESP_ERR_INVALID_ARG); SPIHD_CHECK((bus_config->intr_flags & ESP_INTR_FLAG_IRAM) == 0, "ESP_INTR_FLAG_IRAM should be disabled when CONFIG_SPI_SLAVE_ISR_IN_IRAM is not set.", ESP_ERR_INVALID_ARG);
#endif #endif
spi_chan_claimed = spicommon_periph_claim(host_id, "slave_hd"); SPIHD_CHECK(spicommon_periph_claim(host_id, "slave_hd"), "host already in use", ESP_ERR_INVALID_STATE);
SPIHD_CHECK(spi_chan_claimed, "host already in use", ESP_ERR_INVALID_STATE); // spi_slave_hd_slot_t contains atomic variable, memory must be allocated from internal memory
spi_slave_hd_slot_t *host = heap_caps_calloc(1, sizeof(spi_slave_hd_slot_t), MALLOC_CAP_INTERNAL); spi_slave_hd_slot_t *host = heap_caps_calloc(1, sizeof(spi_slave_hd_slot_t), MALLOC_CAP_INTERNAL);
if (host == NULL) { if (host == NULL) {
ret = ESP_ERR_NO_MEM; ret = ESP_ERR_NO_MEM;
@ -128,6 +129,8 @@ esp_err_t spi_slave_hd_init(spi_host_device_t host_id, const spi_bus_config_t *b
host->int_spinlock = (portMUX_TYPE)portMUX_INITIALIZER_UNLOCKED; host->int_spinlock = (portMUX_TYPE)portMUX_INITIALIZER_UNLOCKED;
host->append_mode = append_mode; host->append_mode = append_mode;
atomic_store(&host->fsm, SPI_BUS_FSM_ENABLED); atomic_store(&host->fsm, SPI_BUS_FSM_ENABLED);
memcpy(&host->bus_config, bus_config, sizeof(spi_bus_config_t));
host->cs_io_num = config->spics_io_num;
ret = spicommon_dma_chan_alloc(host_id, config->dma_chan, &host->dma_ctx); ret = spicommon_dma_chan_alloc(host_id, config->dma_chan, &host->dma_ctx);
if (ret != ESP_OK) { if (ret != ESP_OK) {
@ -169,12 +172,11 @@ esp_err_t spi_slave_hd_init(spi_host_device_t host_id, const spi_bus_config_t *b
host->internal_mem_align_size = 4; host->internal_mem_align_size = 4;
#endif #endif
ret = spicommon_bus_initialize_io(host_id, bus_config, SPICOMMON_BUSFLAG_SLAVE | bus_config->flags, &host->flags); ret = spicommon_bus_initialize_io(host_id, bus_config, SPICOMMON_BUSFLAG_SLAVE | bus_config->flags, &host->flags, &host->gpio_reserve);
if (ret != ESP_OK) { if (ret != ESP_OK) {
goto cleanup; goto cleanup;
} }
gpio_set_direction(config->spics_io_num, GPIO_MODE_INPUT); spicommon_cs_initialize(host_id, config->spics_io_num, 0, !(bus_config->flags & SPICOMMON_BUSFLAG_NATIVE_PINS), &host->gpio_reserve);
spicommon_cs_initialize(host_id, config->spics_io_num, 0, !(bus_config->flags & SPICOMMON_BUSFLAG_NATIVE_PINS));
spi_slave_hd_hal_config_t hal_config = { spi_slave_hd_hal_config_t hal_config = {
.host_id = host_id, .host_id = host_id,
@ -347,6 +349,8 @@ esp_err_t spi_slave_hd_deinit(spi_host_device_t host_id)
} }
#endif #endif
spicommon_bus_free_io_cfg(&host->bus_config, &host->gpio_reserve);
spicommon_cs_free_io(host->cs_io_num, &host->gpio_reserve);
spicommon_periph_free(host_id); spicommon_periph_free(host_id);
free(host->dma_ctx->dmadesc_tx); free(host->dma_ctx->dmadesc_tx);
free(host->dma_ctx->dmadesc_rx); free(host->dma_ctx->dmadesc_rx);

View File

@ -164,7 +164,7 @@ TEST_CASE("SPI Master clk_source and divider accuracy", "[spi]")
int real_freq_khz; int real_freq_khz;
spi_device_get_actual_freq(handle, &real_freq_khz); spi_device_get_actual_freq(handle, &real_freq_khz);
// (byte_len * 8 / real_freq_hz) * 1000 000, (unit)us // (byte_len * 8 / real_freq_hz) * 1000 000, (unit)us
int trans_cost_us_predict = (float)TEST_CLK_BYTE_LEN * 8 * 1000 / real_freq_khz; int trans_cost_us_predict = (float)TEST_CLK_BYTE_LEN * 8 * 1000 / real_freq_khz + IDF_TARGET_MAX_TRANS_TIME_POLL_DMA;
// transaction and measure time // transaction and measure time
start = esp_timer_get_time(); start = esp_timer_get_time();
@ -481,9 +481,9 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
ESP_LOGI(TAG, "test 4 iomux output pins..."); ESP_LOGI(TAG, "test 4 iomux output pins...");
@ -492,9 +492,9 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
ESP_LOGI(TAG, "test 6 output pins..."); ESP_LOGI(TAG, "test 6 output pins...");
@ -504,9 +504,9 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
ESP_LOGI(TAG, "test 4 output pins..."); ESP_LOGI(TAG, "test 4 output pins...");
@ -516,9 +516,9 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
#if TEST_SOC_HAS_INPUT_ONLY_PINS //There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored. #if TEST_SOC_HAS_INPUT_ONLY_PINS //There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored.
@ -528,7 +528,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
ESP_LOGI(TAG, "test slave 5 output pins and MISO on input-only pin..."); ESP_LOGI(TAG, "test slave 5 output pins and MISO on input-only pin...");
@ -537,7 +537,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
ESP_LOGI(TAG, "test master 3 output pins and MOSI on input-only pin..."); ESP_LOGI(TAG, "test master 3 output pins and MOSI on input-only pin...");
@ -547,7 +547,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
ESP_LOGI(TAG, "test slave 3 output pins and MISO on input-only pin..."); ESP_LOGI(TAG, "test slave 3 output pins and MISO on input-only pin...");
@ -556,7 +556,7 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1, .mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ESP_OK(spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o); TEST_ASSERT_EQUAL_HEX32(flags_expected, flags_o);
//There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored. //There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored.
#endif //#if TEST_SOC_HAS_INPUT_ONLY_PINS #endif //#if TEST_SOC_HAS_INPUT_ONLY_PINS
@ -568,8 +568,8 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
ESP_LOGI(TAG, "check native flag for 4 output pins..."); ESP_LOGI(TAG, "check native flag for 4 output pins...");
flags_expected = SPICOMMON_BUSFLAG_IOMUX_PINS; flags_expected = SPICOMMON_BUSFLAG_IOMUX_PINS;
@ -578,8 +578,8 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
#if TEST_SOC_HAS_INPUT_ONLY_PINS //There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored. #if TEST_SOC_HAS_INPUT_ONLY_PINS //There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored.
ESP_LOGI(TAG, "check dual flag for master 5 output pins and MISO/MOSI on input-only pin..."); ESP_LOGI(TAG, "check dual flag for master 5 output pins and MISO/MOSI on input-only pin...");
@ -588,14 +588,14 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
cfg = (spi_bus_config_t) { cfg = (spi_bus_config_t) {
.mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
ESP_LOGI(TAG, "check dual flag for master 3 output pins and MISO/MOSI on input-only pin..."); ESP_LOGI(TAG, "check dual flag for master 3 output pins and MISO/MOSI on input-only pin...");
flags_expected = SPICOMMON_BUSFLAG_DUAL | SPICOMMON_BUSFLAG_GPIO_PINS; flags_expected = SPICOMMON_BUSFLAG_DUAL | SPICOMMON_BUSFLAG_GPIO_PINS;
@ -603,14 +603,14 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = INPUT_ONLY_PIN, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
cfg = (spi_bus_config_t) { cfg = (spi_bus_config_t) {
.mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1, .mosi_io_num = INPUT_ONLY_PIN, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
//There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored. //There is no input-only pin on esp32c3 and esp32s3, so this test could be ignored.
#endif //#if TEST_SOC_HAS_INPUT_ONLY_PINS #endif //#if TEST_SOC_HAS_INPUT_ONLY_PINS
@ -620,8 +620,8 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = -1, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = -1, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
ESP_LOGI(TAG, "check mosi flag..."); ESP_LOGI(TAG, "check mosi flag...");
flags_expected = SPICOMMON_BUSFLAG_MOSI; flags_expected = SPICOMMON_BUSFLAG_MOSI;
@ -629,8 +629,8 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = -1, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = -1, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
ESP_LOGI(TAG, "check miso flag..."); ESP_LOGI(TAG, "check miso flag...");
flags_expected = SPICOMMON_BUSFLAG_MISO; flags_expected = SPICOMMON_BUSFLAG_MISO;
@ -638,8 +638,8 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = -1, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = -1, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
ESP_LOGI(TAG, "check quad flag..."); ESP_LOGI(TAG, "check quad flag...");
flags_expected = SPICOMMON_BUSFLAG_QUAD; flags_expected = SPICOMMON_BUSFLAG_QUAD;
@ -647,14 +647,14 @@ TEST_CASE("spi bus setting with different pin configs", "[spi]")
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = -1, .quadwp_io_num = spi_periph_signal[TEST_SPI_HOST].spiwp_iomux_pin,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
cfg = (spi_bus_config_t) { cfg = (spi_bus_config_t) {
.mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = -1, .mosi_io_num = spi_periph_signal[TEST_SPI_HOST].spid_iomux_pin, .miso_io_num = spi_periph_signal[TEST_SPI_HOST].spiq_iomux_pin, .sclk_io_num = spi_periph_signal[TEST_SPI_HOST].spiclk_iomux_pin, .quadhd_io_num = spi_periph_signal[TEST_SPI_HOST].spihd_iomux_pin, .quadwp_io_num = -1,
.max_transfer_sz = 8, .flags = flags_expected .max_transfer_sz = 8, .flags = flags_expected
}; };
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_MASTER, &flags_o, NULL));
TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o)); TEST_ASSERT_EQUAL(ESP_ERR_INVALID_ARG, spicommon_bus_initialize_io(TEST_SPI_HOST, &cfg, flags_expected | SPICOMMON_BUSFLAG_SLAVE, &flags_o, NULL));
} }
TEST_CASE("SPI Master no response when switch from host1 (SPI2) to host2 (SPI3)", "[spi]") TEST_CASE("SPI Master no response when switch from host1 (SPI2) to host2 (SPI3)", "[spi]")

View File

@ -1,34 +1,28 @@
# SPDX-FileCopyrightText: 2021-2025 Espressif Systems (Shanghai) CO LTD # SPDX-FileCopyrightText: 2021-2025 Espressif Systems (Shanghai) CO LTD
# SPDX-License-Identifier: Apache-2.0 # SPDX-License-Identifier: Apache-2.0
import pytest import pytest
from pytest_embedded_idf.utils import idf_parametrize from pytest_embedded_idf.utils import idf_parametrize
from pytest_embedded_idf.utils import soc_filtered_targets
# If `test_env` is define, should not run on generic runner
@pytest.mark.generic @pytest.mark.generic
@pytest.mark.parametrize('config', ['release'], indirect=True) @pytest.mark.parametrize('config', ['release'], indirect=True)
@idf_parametrize( @idf_parametrize('target', soc_filtered_targets('SOC_SPI_SUPPORT_SLAVE_HD_VER2 == 1'), indirect=['target'])
'target',
['esp32s2', 'esp32s3', 'esp32c2', 'esp32c3', 'esp32c5', 'esp32c6', 'esp32c61', 'esp32h2', 'esp32p4'],
indirect=['target'],
)
def test_slave_hd_single_dev(case_tester) -> None: # type: ignore def test_slave_hd_single_dev(case_tester) -> None: # type: ignore
for case in case_tester.test_menu: for case in case_tester.test_menu:
if 'test_env' in case.attributes: if 'test_env' in case.attributes:
continue continue # If `test_env` is define, should not run on generic runner
case_tester.run_normal_case(case=case, reset=True, timeout=180) case_tester.run_normal_case(case=case, reset=True, timeout=180)
# if `test_env` not defined, will run on `generic_multi_device` by default
@pytest.mark.generic_multi_device @pytest.mark.generic_multi_device
# TODO: [ESP32C61] IDF-10949
@pytest.mark.temp_skip_ci(targets=['esp32c61'], reason='no multi-dev runner')
@pytest.mark.parametrize('count, config', [(2, 'release')], indirect=True) @pytest.mark.parametrize('count, config', [(2, 'release')], indirect=True)
@idf_parametrize( @idf_parametrize('target', soc_filtered_targets('SOC_SPI_SUPPORT_SLAVE_HD_VER2 == 1'), indirect=['target'])
'target',
['esp32s2', 'esp32s3', 'esp32c2', 'esp32c3', 'esp32c5', 'esp32c6', 'esp32h2', 'esp32p4'],
indirect=['target'],
)
def test_slave_hd_multi_dev(case_tester) -> None: # type: ignore def test_slave_hd_multi_dev(case_tester) -> None: # type: ignore
for case in case_tester.test_menu: for case in case_tester.test_menu:
# if `test_env` not defined, will run on `generic_multi_device` by default
if case.attributes.get('test_env', 'generic_multi_device') == 'generic_multi_device': if case.attributes.get('test_env', 'generic_multi_device') == 'generic_multi_device':
case_tester.run_multi_dev_case(case=case, reset=True) case_tester.run_multi_dev_case(case=case, reset=True)