ESP32 以色列国防军。这个 table 是放在 SPI FLASH 中并从中读取还是加载到 RAM 中

ESP32 IDF. Will this table be placed in the SPI FLASH and read from it or it will be loaded to the RAM

ESP32专家提问

示例:

const uint8_t * const data[] = {
    (const uint8_t[]){0xB5, 0x62, 0x06, 0x04, 0x04, 0x00, 0xFF, 0x87, 0x01, 0x00, 0x95, 0xF7, 0xff, 0xff},
    (const uint8_t[]){0xB5, 0x62, 0x06, 0x04, 0x04, 0x00, 0xFF, 0xFF, 0x02, 0x00, 0x0E, 0x61, 0xff, 0xff},
    (const uint8_t[]){0xB5, 0x62, 0x06, 0x04, 0x04, 0x00, 0x00, 0x00, 0x02, 0x00, 0x10, 0x68, 0xff, 0xff},
    (const uint8_t[]){0xB5, 0x62, 0x06, 0x09, 0x0D, 0x00, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x00, 0x00, 0x07, 0x1F, 0x9E, 0xff, 0xff},
    (const uint8_t[]){0xB5, 0x62, 0x06, 0x04, 0x04, 0x00, 0x00, 0x00, 0x08, 0x00, 0x16, 0x74, 0xff, 0xff},
    (const uint8_t[]){0xB5, 0x62, 0x06, 0x09, 0x0D, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x17, 0x31, 0xff, 0xff},
};

我的问题: SPI 闪存是否映射到地址space? 如果是,这个数组(和复合字面量)是否会放在FLASH中而不是在启动时复制到RAM中?

是的。

来自ESP-IDF Programming Guide

DROM (data stored in flash)

By default, constant data is placed by the linker into a region mapped to the MMU flash cache. This is the same as the IROM (code executed from flash) section, but is for read-only data not executable code.

The only constant data not placed into this memory type by default are literal constants which are embedded by the compiler into application code. These are placed as the surrounding function’s executable instructions.

The DRAM_ATTR attribute can be used to force constants from DROM into the DRAM (Data RAM) section (see above).

在 C/C++ 代码中使用 const 修饰符将告诉链接器将数据保留在闪存中是安全的。 ESP32 编译器和链接器足够智能,可以自动执行此操作,因此不需要 Arduino 使用的 _FPROGMEM 等宏。

您可以通过构建声明一个非常大的已初始化数组的简单程序来确认这一点。该程序需要对数组做一些事情,这样数组就不会被优化掉。 运行 它曾经与声明的数组 const 一起输出空闲堆 space。 运行 再次使用未声明的数组 const。第二次您应该看到较小数量的堆 space 可用,数组使用差异。