diff --git a/include/esp-stub-lib/flash.h b/include/esp-stub-lib/flash.h index 2c36886..4d950ee 100644 --- a/include/esp-stub-lib/flash.h +++ b/include/esp-stub-lib/flash.h @@ -26,6 +26,7 @@ extern "C" { stub_lib_err_t stub_lib_flash_init(void **state); void stub_lib_flash_deinit(const void *state); stub_lib_err_t stub_lib_flash_get_info(stub_lib_flash_info_t *info); +void stub_lib_flash_info_print(const stub_lib_flash_info_t *info); stub_lib_err_t stub_lib_flash_read_buff(uint32_t addr, void *buffer, uint32_t size); stub_lib_err_t stub_lib_flash_write_buff(uint32_t addr, const void *buffer, uint32_t size, int encrypt); stub_lib_err_t stub_lib_flash_erase_area(uint32_t addr, uint32_t size); diff --git a/include/target/flash.h b/include/target/flash.h index e285850..a3e77d6 100644 --- a/include/target/flash.h +++ b/include/target/flash.h @@ -6,5 +6,17 @@ #pragma once -void stub_target_flash_init(void *state); -void stub_target_flash_deinit(const void *state); +#include + +typedef struct esp_rom_spiflash_chip { + uint32_t flash_id; + uint32_t chip_size; // chip size in bytes + uint32_t block_size; + uint32_t sector_size; + uint32_t page_size; + uint32_t status_mask; +} esp_rom_spiflash_chip_t; + +void stub_target_flash_init(void); +uint32_t stub_target_flash_get_flash_id(void); +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void); diff --git a/include/target/impl/flash_get_config_from_rom.h b/include/target/impl/flash_get_config_from_rom.h new file mode 100644 index 0000000..9a4a4a5 --- /dev/null +++ b/include/target/impl/flash_get_config_from_rom.h @@ -0,0 +1,25 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include +#include + +typedef struct { + esp_rom_spiflash_chip_t chip; + uint8_t dummy_len_plus[3]; + uint8_t sig_matrix; +} esp_rom_spiflash_legacy_data_t; + +/* ROM's flash config data */ +extern esp_rom_spiflash_legacy_data_t *rom_spiflash_legacy_data; + +inline static +const esp_rom_spiflash_chip_t *flash_impl_get_config_from_rom() +{ + return &rom_spiflash_legacy_data->chip; +} diff --git a/include/target/impl/flash_get_config_from_rom_old.h b/include/target/impl/flash_get_config_from_rom_old.h new file mode 100644 index 0000000..76b9e8d --- /dev/null +++ b/include/target/impl/flash_get_config_from_rom_old.h @@ -0,0 +1,18 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +/* ROM's flash config data for some old chips */ +extern esp_rom_spiflash_chip_t g_rom_flashchip; + +inline static +const esp_rom_spiflash_chip_t *flash_impl_get_config_from_rom_old(void) +{ + return &g_rom_flashchip; +} diff --git a/include/target/impl/flash_get_id_from_rom.h b/include/target/impl/flash_get_id_from_rom.h new file mode 100644 index 0000000..b76a1c4 --- /dev/null +++ b/include/target/impl/flash_get_id_from_rom.h @@ -0,0 +1,56 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#include +#include +#include + +#include + +/** + * @brief Sets the correct flash_id in the flash config from SPI_MEM_FLASH_RDID in ROM code + * + */ +extern void esp_rom_spi_flash_update_id(void); + +inline static +uint32_t flash_impl_get_id_from_rdid_reg(void) +{ + WRITE_PERI_REG(PERIPHS_SPI_FLASH_C0, 0); + WRITE_PERI_REG(PERIPHS_SPI_FLASH_CMD, PERIPHS_SPI_FLASH_BITS_RDID); + while (READ_PERI_REG(PERIPHS_SPI_FLASH_CMD) != 0) + ; + uint32_t rdid = READ_PERI_REG(PERIPHS_SPI_FLASH_C0) & 0xffffff; + return ((rdid & 0xff) << 16) | (rdid & 0xff00) | ((rdid & 0xff0000) >> 16);; +} + +inline static +uint32_t flash_impl_get_id_from_config(void) +{ + + esp_rom_spi_flash_update_id(); + return stub_target_flash_get_config()->flash_id; +} + +inline static +uint32_t flash_impl_get_id_from_rom(void) +{ + // TODO: remove dev tracing + STUB_LOG_TRACEF("Uninit ROM's flash_id: 0x%x\n", stub_target_flash_get_config()->flash_id); + + // TODO: it's just for development. remove this option then + uint32_t rdid = flash_impl_get_id_from_rdid_reg(); + (void)rdid; + STUB_LOG_TRACEF("Flash ID: 0x%x (from SPI RDID)\n", rdid); + + uint32_t id = flash_impl_get_id_from_config(); + STUB_LOG_TRACEF("Flash ID: 0x%x (from ROM code)\n", stub_target_flash_get_config()->flash_id); + return id; +} diff --git a/include/target/impl/flash_init_auto_spiconfig.h b/include/target/impl/flash_init_auto_spiconfig.h new file mode 100644 index 0000000..d7f10d2 --- /dev/null +++ b/include/target/impl/flash_init_auto_spiconfig.h @@ -0,0 +1,31 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include +#include + +#include + +/** + * @brief SPI Flash init + * + * @param spiconfig: 0 - auto from efuse; a special value - for pins + * + * @param legacy: Deprecated compatibility API value, must be false + * + */ +extern void esp_rom_spiflash_attach(uint32_t spiconfig, bool legacy); + +inline static +void flash_impl_init_auto_spiconfig(void) +{ + STUB_LOG_TRACE(); + // Do not call ets_efuse_get_spiconfig here because + // it is called inside of esp_rom_spiflash_attach() when spiconfig=0 + esp_rom_spiflash_attach(0, false); +} diff --git a/include/target/impl/flash_init_no_spiconfig.h b/include/target/impl/flash_init_no_spiconfig.h new file mode 100644 index 0000000..ebaffac --- /dev/null +++ b/include/target/impl/flash_init_no_spiconfig.h @@ -0,0 +1,29 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include +#include + +#include + +/** + * @brief SPI Flash init. CONFIG SPI is unsupported + * + * @param spiconfig: Deprecated compatibility API value, must be 0 + * + * @param legacy: Deprecated compatibility API value, must be false + * + */ +extern void esp_rom_spiflash_attach(uint32_t spiconfig, bool legacy); + +inline static +void flash_impl_init_no_spiconfig(void) +{ + STUB_LOG_TRACE(); + esp_rom_spiflash_attach(0, false); +} diff --git a/src/esp32/src/flash.c b/src/esp32/src/flash.c index 94895f2..16fe9eb 100644 --- a/src/esp32/src/flash.c +++ b/src/esp32/src/flash.c @@ -4,16 +4,157 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include + +#include +#include +#include #include +#include + +#include "soc/reg_base.h" +#include "soc/spi_reg.h" + +#define SPI_FLASH_CMD_RDID 0x9F +#define ESP_ROM_SPIFLASH_BUSY_FLAG BIT(0) + +#define GPIO_STRAP_REG (DR_REG_GPIO_BASE + 0x0038) +#define PERIPHS_SPI_FLASH_CMD SPI_CMD_REG(1) +#define PERIPHS_SPI_FLASH_STATUS SPI_RD_STATUS_REG(1) +#define PERIPHS_SPI_FLASH_USRREG SPI_USER_REG(1) +#define PERIPHS_SPI_FLASH_USRREG2 SPI_USER2_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_W0_REG(1) +#define PERIPHS_SPI_MOSI_DLEN_REG SPI_MOSI_DLEN_REG(1) +#define PERIPHS_SPI_MISO_DLEN_REG SPI_MISO_DLEN_REG(1) + +/* XXX0_10XX */ +#define IS_HSPI_BOOT(strap_val) (((strap_val)&0x1c)==0x08) + +/* ROM */ + +/** + * @brief Read spi flash pin configuration from Efuse + * + * @return + * - 0 for default SPI pins. + * - 1 for default HSPI pins. + * - Other values define a custom pin configuration mask. Pins are encoded as per the EFUSE_SPICONFIG_RET_SPICLK, + * EFUSE_SPICONFIG_RET_SPIQ, EFUSE_SPICONFIG_RET_SPID, EFUSE_SPICONFIG_RET_SPICS0, EFUSE_SPICONFIG_RET_SPIHD macros. + * WP pin (for quad I/O modes) is not saved in efuse and not returned by this function. + */ +extern uint32_t ets_efuse_get_spiconfig(void); +/** + * @brief SPI Flash init, clock divisor is 4, use 1 line Slow read mode. + * Please do not call this function in SDK. + * + * @param uint32_t ishspi: 0 for spi, 1 for hspi, flash pad decided by strapping + * else, bit[5:0] spiclk, bit[11:6] spiq, bit[17:12] spid, bit[23:18] spics0, bit[29:24] spihd + * + * @param uint8_t legacy: always keeping false. + * + * @return None + */ +extern void esp_rom_spiflash_attach(uint32_t ishspi, bool legacy); + +// TODO: avoid common code and update execute_command() +static uint32_t flash_exec_usr_cmd(uint32_t cmd) +{ + uint32_t status_value = ESP_ROM_SPIFLASH_BUSY_FLAG; + + while (ESP_ROM_SPIFLASH_BUSY_FLAG == (status_value & ESP_ROM_SPIFLASH_BUSY_FLAG)) { + WRITE_PERI_REG(PERIPHS_SPI_FLASH_STATUS, 0); /* clear register */ + WRITE_PERI_REG(PERIPHS_SPI_FLASH_CMD, SPI_USR | cmd); //TODO cmd is bit(0), this is a useless bit + while (READ_PERI_REG(PERIPHS_SPI_FLASH_CMD) != 0) + ; + status_value = READ_PERI_REG(PERIPHS_SPI_FLASH_STATUS) & stub_target_flash_get_config()->status_mask; + } + + return status_value; +} + +static void flash_spi_wait_ready(void) +{ + uint32_t status_value = ESP_ROM_SPIFLASH_BUSY_FLAG; + + while (ESP_ROM_SPIFLASH_BUSY_FLAG == (status_value & ESP_ROM_SPIFLASH_BUSY_FLAG)) { + WRITE_PERI_REG(PERIPHS_SPI_FLASH_STATUS, 0); /* clear register */ + WRITE_PERI_REG(PERIPHS_SPI_FLASH_CMD, SPI_FLASH_RDSR); + while (READ_PERI_REG(PERIPHS_SPI_FLASH_CMD) != 0) + ; + status_value = READ_PERI_REG(PERIPHS_SPI_FLASH_STATUS) & stub_target_flash_get_config()->status_mask; + } +} + +static uint32_t flash_spi_cmd_run(uint32_t cmd, + uint8_t data_bits[], + uint32_t data_bits_num, + uint32_t read_bits_num) +{ + uint32_t old_spi_usr = READ_PERI_REG(PERIPHS_SPI_FLASH_USRREG); + uint32_t old_spi_usr2 = READ_PERI_REG(PERIPHS_SPI_FLASH_USRREG2); + uint32_t flags = SPI_USR_COMMAND; + + flash_spi_wait_ready(); + + if (read_bits_num > 0) { + flags |= SPI_USR_MISO; + WRITE_PERI_REG(PERIPHS_SPI_MISO_DLEN_REG, read_bits_num - 1); + } + if (data_bits_num > 0) { + flags |= SPI_USR_MOSI; + WRITE_PERI_REG(PERIPHS_SPI_MOSI_DLEN_REG, data_bits_num - 1); + } + + WRITE_PERI_REG(PERIPHS_SPI_FLASH_USRREG, flags); + WRITE_PERI_REG(PERIPHS_SPI_FLASH_USRREG2, (7 << SPI_USR_COMMAND_BITLEN_S) | cmd); + if (data_bits_num == 0) { + WRITE_PERI_REG(PERIPHS_SPI_FLASH_C0, 0); + } else { + for (uint32_t i = 0; i <= data_bits_num / 32; i += 32) { + WRITE_PERI_REG(PERIPHS_SPI_FLASH_C0 + i / 8, *((uint32_t *)&data_bits[i / 8])); + } + } + flash_exec_usr_cmd(0); + uint32_t status = READ_PERI_REG(PERIPHS_SPI_FLASH_C0); + /* restore some SPI controller registers */ + WRITE_PERI_REG(PERIPHS_SPI_FLASH_USRREG, old_spi_usr); + WRITE_PERI_REG(PERIPHS_SPI_FLASH_USRREG2, old_spi_usr2); + + return status; +} + +static inline uint32_t get_id_from_rdid_cmd(void) +{ + uint32_t rdid = flash_spi_cmd_run(SPI_FLASH_CMD_RDID, NULL, 0, 24); + return ((rdid & 0xff) << 16) | (rdid & 0xff00) | ((rdid & 0xff0000) >> 16); +} + +void stub_target_flash_init(void) +{ + STUB_LOG_TRACE(); + uint32_t ishspi = 0; + uint32_t spiconfig = ets_efuse_get_spiconfig(); + const uint32_t strapping = REG_READ(GPIO_STRAP_REG); + if (IS_HSPI_BOOT(strapping)) { + ishspi = 1; + } + if (spiconfig) { + ishspi = spiconfig; + } + esp_rom_spiflash_attach(ishspi, false); +} -void stub_target_flash_init(void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + // TODO: remove dev tracing + STUB_LOG_TRACEF("Uninit ROM's flash_id: 0x%x\n", stub_target_flash_get_config()->flash_id); + uint32_t id = get_id_from_rdid_cmd(); + STUB_LOG_TRACEF("Flash ID: 0x%x (from SPI RDID)\n", id); + return id; } -void stub_target_flash_deinit(const void *state) +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) { - (void)state; - // TODO: Implement + return flash_impl_get_config_from_rom_old(); } diff --git a/src/esp32c2/include/soc/spi_mem_reg.h b/src/esp32c2/include/soc/spi_mem_reg.h index 3a1f9d0..6cd9848 100644 --- a/src/esp32c2/include/soc/spi_mem_reg.h +++ b/src/esp32c2/include/soc/spi_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_SPI0_BASE - (i) * 0x1000) diff --git a/src/esp32c2/include/target_spec/periph_defs.h b/src/esp32c2/include/target_spec/periph_defs.h new file mode 100644 index 0000000..5878b72 --- /dev/null +++ b/src/esp32c2/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32c2/src/flash.c b/src/esp32c2/src/flash.c index 94895f2..899a325 100644 --- a/src/esp32c2/src/flash.c +++ b/src/esp32c2/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_no_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp32c3/include/soc/spi_mem_reg.h b/src/esp32c3/include/soc/spi_mem_reg.h index 21aef3d..278080a 100644 --- a/src/esp32c3/include/soc/spi_mem_reg.h +++ b/src/esp32c3/include/soc/spi_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_SPI0_BASE - (i) * 0x1000) diff --git a/src/esp32c3/include/target_spec/periph_defs.h b/src/esp32c3/include/target_spec/periph_defs.h new file mode 100644 index 0000000..5878b72 --- /dev/null +++ b/src/esp32c3/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32c3/src/flash.c b/src/esp32c3/src/flash.c index 94895f2..041bfb8 100644 --- a/src/esp32c3/src/flash.c +++ b/src/esp32c3/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_auto_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp32c5/include/soc/spi1_mem_reg.h b/src/esp32c5/include/soc/spi1_mem_reg.h index 94e22e5..4fabbb1 100644 --- a/src/esp32c5/include/soc/spi1_mem_reg.h +++ b/src/esp32c5/include/soc/spi1_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_SPIMEM0_BASE + (i) * 0x1000) // SPIMEM0 and SPIMEM1 diff --git a/src/esp32c5/include/target_spec/periph_defs.h b/src/esp32c5/include/target_spec/periph_defs.h new file mode 100644 index 0000000..ed8effb --- /dev/null +++ b/src/esp32c5/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32c5/src/flash.c b/src/esp32c5/src/flash.c index 94895f2..899a325 100644 --- a/src/esp32c5/src/flash.c +++ b/src/esp32c5/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_no_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp32c6/include/soc/spi_mem_reg.h b/src/esp32c6/include/soc/spi_mem_reg.h index 8b82e8b..e673e6b 100644 --- a/src/esp32c6/include/soc/spi_mem_reg.h +++ b/src/esp32c6/include/soc/spi_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_SPI0_BASE + (i) * 0x1000) // SPIMEM0 and SPIMEM1 diff --git a/src/esp32c6/include/target_spec/periph_defs.h b/src/esp32c6/include/target_spec/periph_defs.h new file mode 100644 index 0000000..5878b72 --- /dev/null +++ b/src/esp32c6/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32c6/src/flash.c b/src/esp32c6/src/flash.c index 94895f2..899a325 100644 --- a/src/esp32c6/src/flash.c +++ b/src/esp32c6/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_no_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp32c61/include/soc/spi1_mem_reg.h b/src/esp32c61/include/soc/spi1_mem_reg.h index c787b2c..ee58aad 100644 --- a/src/esp32c61/include/soc/spi1_mem_reg.h +++ b/src/esp32c61/include/soc/spi1_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_MSPI0_BASE + (i) * 0x1000) // SPIMEM0 and SPIMEM1 diff --git a/src/esp32c61/include/target_spec/periph_defs.h b/src/esp32c61/include/target_spec/periph_defs.h new file mode 100644 index 0000000..ed8effb --- /dev/null +++ b/src/esp32c61/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32c61/src/flash.c b/src/esp32c61/src/flash.c index 94895f2..899a325 100644 --- a/src/esp32c61/src/flash.c +++ b/src/esp32c61/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_no_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp32h2/include/soc/spi_mem_reg.h b/src/esp32h2/include/soc/spi_mem_reg.h index 21ca551..2c8edb8 100644 --- a/src/esp32h2/include/soc/spi_mem_reg.h +++ b/src/esp32h2/include/soc/spi_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_SPI0_BASE + (i) * 0x1000) diff --git a/src/esp32h2/include/target_spec/periph_defs.h b/src/esp32h2/include/target_spec/periph_defs.h new file mode 100644 index 0000000..5878b72 --- /dev/null +++ b/src/esp32h2/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32h2/src/flash.c b/src/esp32h2/src/flash.c index 94895f2..899a325 100644 --- a/src/esp32h2/src/flash.c +++ b/src/esp32h2/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_no_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp32p4/include/soc/spi1_mem_c_reg.h b/src/esp32p4/include/soc/spi1_mem_c_reg.h index 31b2a87..9e032b5 100644 --- a/src/esp32p4/include/soc/spi1_mem_c_reg.h +++ b/src/esp32p4/include/soc/spi1_mem_c_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" /** SPI1_MEM_C_CMD_REG register diff --git a/src/esp32p4/include/target_spec/periph_defs.h b/src/esp32p4/include/target_spec/periph_defs.h new file mode 100644 index 0000000..b431315 --- /dev/null +++ b/src/esp32p4/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI1_MEM_C_CMD_REG +#define PERIPHS_SPI_FLASH_C0 SPI1_MEM_C_W0_REG + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI1_MEM_C_FLASH_RDID diff --git a/src/esp32p4/src/flash.c b/src/esp32p4/src/flash.c index 94895f2..899a325 100644 --- a/src/esp32p4/src/flash.c +++ b/src/esp32p4/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_no_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp32s2/include/soc/spi_mem_reg.h b/src/esp32s2/include/soc/spi_mem_reg.h index a1a2fa8..5ac96fb 100644 --- a/src/esp32s2/include/soc/spi_mem_reg.h +++ b/src/esp32s2/include/soc/spi_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_SPI0_BASE - (i) * 0x1000) diff --git a/src/esp32s2/include/target_spec/periph_defs.h b/src/esp32s2/include/target_spec/periph_defs.h new file mode 100644 index 0000000..5878b72 --- /dev/null +++ b/src/esp32s2/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32s2/src/flash.c b/src/esp32s2/src/flash.c index 94895f2..4ed2252 100644 --- a/src/esp32s2/src/flash.c +++ b/src/esp32s2/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_auto_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom_old(); } diff --git a/src/esp32s3/include/soc/spi_mem_reg.h b/src/esp32s3/include/soc/spi_mem_reg.h index 523537c..4759e27 100644 --- a/src/esp32s3/include/soc/spi_mem_reg.h +++ b/src/esp32s3/include/soc/spi_mem_reg.h @@ -5,7 +5,7 @@ */ #pragma once -#include +#include #include "reg_base.h" #define REG_SPI_MEM_BASE(i) (DR_REG_SPI0_BASE - (i) * 0x1000) diff --git a/src/esp32s3/include/target_spec/periph_defs.h b/src/esp32s3/include/target_spec/periph_defs.h new file mode 100644 index 0000000..5878b72 --- /dev/null +++ b/src/esp32s3/include/target_spec/periph_defs.h @@ -0,0 +1,14 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +#pragma once + +#include + +#define PERIPHS_SPI_FLASH_CMD SPI_MEM_CMD_REG(1) +#define PERIPHS_SPI_FLASH_C0 SPI_MEM_W0_REG(1) + +#define PERIPHS_SPI_FLASH_BITS_RDID SPI_MEM_FLASH_RDID diff --git a/src/esp32s3/src/flash.c b/src/esp32s3/src/flash.c index 94895f2..041bfb8 100644 --- a/src/esp32s3/src/flash.c +++ b/src/esp32s3/src/flash.c @@ -4,16 +4,26 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include +#include #include +#include +#include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + flash_impl_init_auto_spiconfig(); } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; - // TODO: Implement + STUB_LOG_TRACE(); + return flash_impl_get_id_from_rom(); +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom(); } diff --git a/src/esp8266/src/flash.c b/src/esp8266/src/flash.c index 94895f2..0d41d5e 100644 --- a/src/esp8266/src/flash.c +++ b/src/esp8266/src/flash.c @@ -4,16 +4,24 @@ * SPDX-License-Identifier: Apache-2.0 OR MIT */ +#include #include +#include -void stub_target_flash_init(void *state) +void stub_target_flash_init(void) { - (void)state; + STUB_LOG_TRACE(); // TODO: Implement } -void stub_target_flash_deinit(const void *state) +uint32_t stub_target_flash_get_flash_id(void) { - (void)state; + STUB_LOG_TRACE(); // TODO: Implement + return 0; +} + +const esp_rom_spiflash_chip_t * stub_target_flash_get_config(void) +{ + return flash_impl_get_config_from_rom_old(); } diff --git a/src/flash.c b/src/flash.c index 1a6bdfd..92559bf 100644 --- a/src/flash.c +++ b/src/flash.c @@ -6,22 +6,109 @@ #include #include +#include #include +/* Flash geometry constants */ +#define STUB_FLASH_SECTOR_SIZE 0x1000 +#define STUB_FLASH_BLOCK_SIZE 0x10000 +#define STUB_FLASH_PAGE_SIZE 0x100 +#define STUB_FLASH_STATUS_MASK 0xFFFF + +extern int esp_rom_spiflash_config_param(uint32_t flash_id, uint32_t chip_size, + uint32_t block_size, uint32_t sector_size, + uint32_t page_size, uint32_t status_mask); + +static uint32_t flash_id_to_flash_size(uint32_t flash_id) +{ + // TODO: remove dev tracing + STUB_LOG_TRACEF("flash_id: 0x%x\n", flash_id); + + const uint32_t id = flash_id & 0xff; + switch (id) { + case 0x12: // 256 KB + case 0x13: + case 0x14: // 1 MB + case 0x15: + case 0x16: + case 0x17: + case 0x18: + case 0x19: // 32 MB + case 0x1A: // 64 MB + case 0x1B: // 128 MB + case 0x1C: // 256 MB + return 1u << id; + case 0x39: + return 32 * 1024 * 1024; + } + + STUB_LOGE("Unknown flash_id! 0x%x", flash_id); + return 0; +} + +static void flash_update_config(uint32_t flash_id, uint32_t flash_size) +{ + esp_rom_spiflash_config_param(flash_id, + flash_size, + STUB_FLASH_BLOCK_SIZE, + STUB_FLASH_SECTOR_SIZE, + STUB_FLASH_PAGE_SIZE, + STUB_FLASH_STATUS_MASK); +} + stub_lib_err_t stub_lib_flash_init(void **state) { - stub_target_flash_init(state); + (void)state; + STUB_LOG_TRACE(); + + stub_target_flash_init(); + uint32_t flash_id = stub_target_flash_get_flash_id(); + uint32_t flash_size = flash_id_to_flash_size(flash_id); + if (flash_size == 0) { + STUB_LOGE("Invalid flash size: 0\n"); + return STUB_LIB_FAIL; + } + STUB_LOG_TRACEF("Flash size: %d MB\n", flash_size / (1024 * 1024)); + + flash_update_config(flash_id, flash_size); + STUB_LOG_TRACEF("config_param has been set\n"); + return STUB_LIB_OK; } void stub_lib_flash_deinit(const void *state) { - stub_target_flash_deinit(state); + (void)state; } stub_lib_err_t stub_lib_flash_get_info(stub_lib_flash_info_t *info) { - (void)info; - // TODO: implement + const esp_rom_spiflash_chip_t * chip = stub_target_flash_get_config(); + + info->id = chip->flash_id; + info->size = chip->chip_size; + info->block_size = chip->block_size; + info->sector_size = chip->sector_size; + info->page_size = chip->page_size; + info->mode = 0; // TODO: Implement + info->encrypted = 0; // TODO: Implement + return STUB_LIB_OK; } + +void stub_lib_flash_info_print(const stub_lib_flash_info_t *info) +{ + (void)info; + STUB_LOGI("Flash info:\n" + "\tid: 0x%x, size: %d KB,\n" + "\tblock: %d KB (0x%x), sector: %d B (0x%x), page: %d B (0x%x),\n" + "\tmode: %d, enc: %d\n", + info->id, + info->size / 1024, + info->block_size / 1024, info->block_size, + info->sector_size, info->sector_size, + info->page_size, info->page_size, + info->mode, + info->encrypted + ); +}