Skip to content

Commit bedb2cd

Browse files
committed
feat: update structure for initial SPI Flash support
1 parent 57e00cf commit bedb2cd

File tree

19 files changed

+402
-3
lines changed

19 files changed

+402
-3
lines changed

example/build.sh

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
#!/bin/bash
22

3+
set -eo pipefail
4+
35
TARGETS="esp8266 esp32 esp32s2 esp32s3 esp32c2 esp32c3 esp32c5 esp32c6 esp32c61 esp32h2 esp32p4"
46

57
ESP8266_LINUX_TOOLCHAIN_URL="https://dl.espressif.com/dl/xtensa-lx106-elf-gcc8_4_0-esp-2020r3-linux-amd64.tar.gz"

include/esp-stub-lib/flash.h

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
#include <stdint.h>
1010
#include "err.h"
1111

12-
typedef struct stub_flash_info {
12+
typedef struct stub_lib_flash_info {
1313
uint32_t id;
1414
uint32_t size;
1515
uint32_t block_size;
@@ -23,9 +23,30 @@ typedef struct stub_flash_info {
2323
extern "C" {
2424
#endif // __cplusplus
2525

26+
/**
27+
* @brief Initialize SPI Flash before any use.
28+
*
29+
* Configure SPI, Flash ID, flash size, and the internal ROM's config
30+
*
31+
* @param state Unused
32+
*
33+
* @return Error code:
34+
* - STUB_LIB_OK - success
35+
* - STUB_LIB_ERR_FLASH_INIT_UNKNOWN_FLASH_ID - can't get size from flash id
36+
*/
2637
stub_lib_err_t stub_lib_flash_init(void **state);
2738
void stub_lib_flash_deinit(const void *state);
39+
40+
/**
41+
* @brief Retrieve SPI Flash information.
42+
*
43+
* @param[out] info Pointer to receive the result.
44+
*
45+
* @return Always returns STUB_LIB_OK.
46+
*/
2847
stub_lib_err_t stub_lib_flash_get_info(stub_lib_flash_info_t *info);
48+
49+
void stub_lib_flash_info_print(const stub_lib_flash_info_t *info);
2950
stub_lib_err_t stub_lib_flash_read_buff(uint32_t addr, void *buffer, uint32_t size);
3051
stub_lib_err_t stub_lib_flash_write_buff(uint32_t addr, const void *buffer, uint32_t size, int encrypt);
3152
stub_lib_err_t stub_lib_flash_erase_area(uint32_t addr, uint32_t size);

src/flash.c

Lines changed: 39 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,11 +6,23 @@
66

77
#include <flash.h>
88
#include <err.h>
9+
#include <log.h>
910
#include <target/flash.h>
11+
#include <private/rom_flash_config.h>
1012

1113
stub_lib_err_t stub_lib_flash_init(void **state)
1214
{
1315
stub_target_flash_init(state);
16+
uint32_t flash_id = stub_target_flash_get_flash_id();
17+
uint32_t flash_size = stub_target_flash_id_to_flash_size(flash_id);
18+
if (flash_size == 0) {
19+
STUB_LOGE("Invalid flash size: 0\n");
20+
return STUB_LIB_FAIL;
21+
}
22+
STUB_LOG_TRACEF("Flash size: %d MB\n", flash_size / (1024 * 1024));
23+
24+
stub_target_flash_update_config(flash_id, flash_size);
25+
1426
return STUB_LIB_OK;
1527
}
1628

@@ -21,7 +33,32 @@ void stub_lib_flash_deinit(const void *state)
2133

2234
stub_lib_err_t stub_lib_flash_get_info(stub_lib_flash_info_t *info)
2335
{
24-
(void)info;
25-
// TODO: implement
36+
const esp_rom_spiflash_chip_t * chip = stub_target_flash_get_config();
37+
38+
info->id = chip->flash_id;
39+
info->size = chip->chip_size;
40+
info->block_size = chip->block_size;
41+
info->sector_size = chip->sector_size;
42+
info->page_size = chip->page_size;
43+
info->mode = 0; // TODO: Implement
44+
info->encrypted = 0; // TODO: Implement
45+
2646
return STUB_LIB_OK;
2747
}
48+
49+
void stub_lib_flash_info_print(const stub_lib_flash_info_t *info)
50+
{
51+
(void)info;
52+
STUB_LOGI("Flash info:\n"
53+
"\tid: 0x%x, size: %d KB,\n"
54+
"\tblock: %d KB (0x%x), sector: %d B (0x%x), page: %d B (0x%x),\n"
55+
"\tmode: %d, enc: %d\n",
56+
info->id,
57+
info->size / 1024,
58+
info->block_size / 1024, info->block_size,
59+
info->sector_size, info->sector_size,
60+
info->page_size, info->page_size,
61+
info->mode,
62+
info->encrypted
63+
);
64+
}

src/target/common/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
set(common_srcs
2+
src/flash.c
23
)
34

45
add_library(${ESP_COMMON_LIB} STATIC ${common_srcs})
Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
/*
2+
* SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
3+
*
4+
* SPDX-License-Identifier: Apache-2.0 OR MIT
5+
*/
6+
7+
#pragma once
8+
9+
#include <stdbool.h>
10+
#include <stdint.h>
11+
12+
typedef struct esp_rom_spiflash_chip {
13+
uint32_t flash_id;
14+
uint32_t chip_size; // chip size in bytes
15+
uint32_t block_size;
16+
uint32_t sector_size;
17+
uint32_t page_size;
18+
uint32_t status_mask;
19+
} esp_rom_spiflash_chip_t;
20+
21+
/**
22+
* @brief SPI Flash init
23+
*
24+
* @param spiconfig
25+
* (for ESP32 chip)
26+
* - 0 for default SPI pins
27+
* - 1 for default HSPI pins
28+
* - other for custom pin configuration
29+
*
30+
* (for S2, C3, S3 chips)
31+
* - 0 for auto SPI configuration from eFuse is supported
32+
* - value for custom pin configuration
33+
*
34+
* (others chips)
35+
* - 0 is only a compatibility value, auto SPI configuration is not supported
36+
*
37+
* @param legacy
38+
* - false is only a deprecated compatibility API value, for all chips
39+
*
40+
*/
41+
extern void esp_rom_spiflash_attach(uint32_t spiconfig, bool legacy);
42+
43+
/**
44+
* @brief Read SPI flash pin configuration from eFuse
45+
*
46+
* Available only for ESP32, S2, C3, S3
47+
*
48+
* @return Configuration value:
49+
* - 0 for default SPI pins
50+
* - other value for custom configuration
51+
*/
52+
uint32_t ets_efuse_get_spiconfig(void);
53+
54+
/**
55+
* @brief Initialize internal ROM config's flash_id from hw registers
56+
*
57+
*/
58+
extern void esp_rom_spi_flash_update_id(void);
59+
60+
/**
61+
* @brief Initialize internal ROM config from arguments
62+
*
63+
* @return Always returns 0.
64+
*/
65+
extern int esp_rom_spiflash_config_param(uint32_t flash_id, uint32_t chip_size,
66+
uint32_t block_size, uint32_t sector_size,
67+
uint32_t page_size, uint32_t status_mask);
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
/*
2+
* SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
3+
*
4+
* SPDX-License-Identifier: Apache-2.0 OR MIT
5+
*/
6+
7+
#pragma once
8+
9+
#include "rom_flash.h"
10+
11+
typedef struct {
12+
esp_rom_spiflash_chip_t chip;
13+
uint8_t dummy_len_plus[3];
14+
uint8_t sig_matrix;
15+
} esp_rom_spiflash_legacy_data_t;
16+
17+
extern esp_rom_spiflash_legacy_data_t *rom_spiflash_legacy_data;
18+
19+
#define g_rom_flashchip (rom_spiflash_legacy_data->chip)
20+
#define g_rom_spiflash_dummy_len_plus (rom_spiflash_legacy_data->dummy_len_plus)

src/target/common/include/target/flash.h

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,5 +6,46 @@
66

77
#pragma once
88

9+
#include <stdint.h>
10+
11+
struct esp_rom_spiflash_chip;
12+
13+
/**
14+
* @brief Initialize SPI Flash hardware.
15+
*
16+
* Configure SPI pins, registers, mode, etc.
17+
*
18+
* @param state Unused
19+
*/
920
void stub_target_flash_init(void *state);
1021
void stub_target_flash_deinit(const void *state);
22+
23+
/**
24+
* @brief Retrieve Flash ID (aka flash device id, aka flash chip id) from internal hw.
25+
*
26+
* @return Flash ID, that includes manufacture and size information.
27+
*/
28+
uint32_t stub_target_flash_get_flash_id(void);
29+
30+
/**
31+
* @brief Get a pointer to the internal SPI flash config in ROM.
32+
*
33+
* @return Always a non-NULL, but the structure may be uninitialized or incorrect.
34+
*/
35+
const struct esp_rom_spiflash_chip *stub_target_flash_get_config(void);
36+
37+
/**
38+
* @brief Set correct values to the internal SPI flash config in ROM
39+
*
40+
*/
41+
void stub_target_flash_update_config(uint32_t flash_id, uint32_t flash_size);
42+
43+
/**
44+
* @brief Infer flash size (in bytes) from Flash ID
45+
*
46+
* @param flash_id Raw Flash ID value
47+
*
48+
* @return Flash size in bytes, or:
49+
* - 0 if flash_id is unknown
50+
*/
51+
uint32_t stub_target_flash_id_to_flash_size(uint32_t flash_id);

src/target/common/src/flash.c

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
/*
2+
* SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
3+
*
4+
* SPDX-License-Identifier: Apache-2.0 OR MIT
5+
*/
6+
7+
#include <stdint.h>
8+
#include <log.h>
9+
#include <target/flash.h>
10+
#include <private/rom_flash.h>
11+
12+
/* Flash geometry constants */
13+
#define STUB_FLASH_SECTOR_SIZE 0x1000
14+
#define STUB_FLASH_BLOCK_SIZE 0x10000
15+
#define STUB_FLASH_PAGE_SIZE 0x100
16+
#define STUB_FLASH_STATUS_MASK 0xFFFF
17+
18+
void stub_target_flash_update_config(uint32_t flash_id, uint32_t flash_size)
19+
{
20+
(void)esp_rom_spiflash_config_param(flash_id,
21+
flash_size,
22+
STUB_FLASH_BLOCK_SIZE,
23+
STUB_FLASH_SECTOR_SIZE,
24+
STUB_FLASH_PAGE_SIZE,
25+
STUB_FLASH_STATUS_MASK);
26+
}
27+
28+
uint32_t stub_target_flash_id_to_flash_size(uint32_t flash_id)
29+
{
30+
const uint32_t id = flash_id & 0xff;
31+
switch (id) {
32+
case 0x12: // 256 KB
33+
case 0x13:
34+
case 0x14: // 1 MB
35+
case 0x15:
36+
case 0x16:
37+
case 0x17:
38+
case 0x18:
39+
case 0x19: // 32 MB
40+
case 0x1A: // 64 MB
41+
case 0x1B: // 128 MB
42+
case 0x1C: // 256 MB
43+
return 1u << id;
44+
case 0x39:
45+
return 32 * 1024 * 1024;
46+
}
47+
48+
STUB_LOGE("Unknown flash_id: 0x%x", flash_id);
49+
return 0;
50+
}

src/target/esp32/src/flash.c

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,13 @@
44
* SPDX-License-Identifier: Apache-2.0 OR MIT
55
*/
66

7+
#include <stdint.h>
8+
79
#include <target/flash.h>
10+
#include <private/rom_flash.h>
11+
12+
extern esp_rom_spiflash_chip_t g_rom_flashchip;
13+
extern uint8_t g_rom_spiflash_dummy_len_plus[];
814

915
void stub_target_flash_init(void *state)
1016
{
@@ -17,3 +23,14 @@ void stub_target_flash_deinit(const void *state)
1723
(void)state;
1824
// TODO: Implement
1925
}
26+
27+
const struct esp_rom_spiflash_chip *stub_target_flash_get_config(void)
28+
{
29+
return &g_rom_flashchip;
30+
}
31+
32+
uint32_t stub_target_flash_get_flash_id(void)
33+
{
34+
// TODO: Implement
35+
return 0;
36+
}

src/target/esp32c2/src/flash.c

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,11 @@
44
* SPDX-License-Identifier: Apache-2.0 OR MIT
55
*/
66

7+
#include <stdint.h>
8+
79
#include <target/flash.h>
10+
#include <private/rom_flash.h>
11+
#include <private/rom_flash_config.h>
812

913
void stub_target_flash_init(void *state)
1014
{
@@ -17,3 +21,14 @@ void stub_target_flash_deinit(const void *state)
1721
(void)state;
1822
// TODO: Implement
1923
}
24+
25+
const struct esp_rom_spiflash_chip *stub_target_flash_get_config(void)
26+
{
27+
return &g_rom_flashchip;
28+
}
29+
30+
uint32_t stub_target_flash_get_flash_id(void)
31+
{
32+
esp_rom_spi_flash_update_id();
33+
return stub_target_flash_get_config()->flash_id;
34+
}

0 commit comments

Comments
 (0)