esp32 nvs flash读写的特点
时间: 2023-11-12 14:07:59 浏览: 188
ESP32的NVS(Non-volatile storage)是一种非易失性存储,可以在ESP32芯片上保存数据,即使断电也不会丢失。NVS主要是用来存储配置信息、设备ID、网络参数等应用数据,可以在应用程序中进行读写操作。
NVS具有以下特点:
1. 快速读写:ESP32的NVS存储空间采用了抽象的键值对(key-value)方式,读写速度非常快。
2. 容量大:ESP32的NVS存储空间容量较大,可以存储数百到数千个键值对数据。
3. 安全可靠:ESP32的NVS存储空间采用了校验和和CRC校验等机制,保证数据的安全性和可靠性。
4. 易于使用:ESP32的NVS存储空间对外提供了简单的API接口,应用程序可以方便地读写NVS存储空间中的数据。
总的来说,ESP32的NVS存储空间具有容量大、读写速度快、安全可靠、易于使用等特点,非常适合用于存储应用程序中的配置信息和应用数据。
相关问题
esp32 nvs读写idf完整代码
下面是ESP32 NVS读写的完整代码示例,使用ESP-IDF开发框架:
```
#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "nvs_flash.h"
#include "nvs.h"
#define STORAGE_NAMESPACE "storage"
void nvs_write(void)
{
nvs_handle my_handle;
esp_err_t err = nvs_open(STORAGE_NAMESPACE, NVS_READWRITE, &my_handle);
if (err != ESP_OK) {
printf("Error (%s) opening NVS handle!\n", esp_err_to_name(err));
} else {
// Write values including string, binary and integer
uint8_t buf[] = {0x00, 0x01, 0x02, 0x03};
err = nvs_set_i32(my_handle, "int_val", 123);
err = nvs_set_str(my_handle, "string_val", "Hello world");
err = nvs_set_blob(my_handle, "blob_val", buf, sizeof(buf));
printf((err != ESP_OK) ? "Failed to write NVS\n" : "NVS write done\n");
// Close handle
nvs_close(my_handle);
}
}
void nvs_read(void)
{
nvs_handle my_handle;
esp_err_t err = nvs_open(STORAGE_NAMESPACE, NVS_READWRITE, &my_handle);
if (err != ESP_OK) {
printf("Error (%s) opening NVS handle!\n", esp_err_to_name(err));
} else {
// Read values including string, binary and integer
int int_val;
char str_val[20];
size_t size = sizeof(str_val);
uint8_t buf[4];
err = nvs_get_i32(my_handle, "int_val", &int_val);
err = nvs_get_str(my_handle, "string_val", str_val, &size);
err = nvs_get_blob(my_handle, "blob_val", buf, &size);
printf("int_val=%d, string_val=%s, blob_val=%02x%02x%02x%02x\n", int_val, str_val, buf[0], buf[1], buf[2], buf[3]);
// Close handle
nvs_close(my_handle);
}
}
void app_main()
{
// Initialize NVS
esp_err_t err = nvs_flash_init();
if (err == ESP_ERR_NVS_NO_FREE_PAGES || err == ESP_ERR_NVS_NEW_VERSION_FOUND) {
// NVS partition was truncated and needs to be erased
printf("NVS partition was truncated and needs to be erased\n");
err = nvs_flash_erase();
if (err != ESP_OK) {
printf("Failed to erase NVS partition (%s)\n", esp_err_to_name(err));
return;
}
// Retry nvs_flash_init
err = nvs_flash_init();
}
if (err != ESP_OK) {
printf("Failed to initialize NVS (%s)\n", esp_err_to_name(err));
return;
}
// Write and read NVS values
nvs_write();
nvs_read();
}
```
此代码在ESP32上使用NVS Flash存储写入和读取值,并使用ESP-IDF开发框架进行编写。在使用此代码之前,应该先在ESP32上执行`nvs_flash_init()`进行初始化。
esp32 读写flash idf完整代码
以下是 ESP32 IDF 中读写 Flash 的完整代码示例:
```c
#include <stdio.h>
#include "esp_log.h"
#include "esp_system.h"
#include "nvs_flash.h"
#include "driver/gpio.h"
#include "driver/spi_master.h"
#include "esp_partition.h"
static const char* TAG = "flash-example";
#define SPI_DMA_CHAN 2
#define FLASH_SECTOR_SIZE 0x1000
#define SPI_FLASH_MOSI_PIN 23
#define SPI_FLASH_MISO_PIN 19
#define SPI_FLASH_CLK_PIN 18
#define SPI_FLASH_CS_PIN 5
// Function to initialize SPI bus
static void spi_init()
{
// Define bus configuration
spi_bus_config_t buscfg = {
.miso_io_num = SPI_FLASH_MISO_PIN,
.mosi_io_num = SPI_FLASH_MOSI_PIN,
.sclk_io_num = SPI_FLASH_CLK_PIN,
.quadwp_io_num = -1,
.quadhd_io_num = -1,
.max_transfer_sz = 0
};
// Define device configuration
spi_device_interface_config_t devcfg = {
.clock_speed_hz = 10*1000*1000, // Clock out at 10 MHz
.mode = 0, // SPI mode 0
.spics_io_num = SPI_FLASH_CS_PIN, // CS pin
.queue_size = 7, // We want to be able to queue 7 transactions at a time
.pre_cb = NULL, // No pre-transfer callback
.post_cb = NULL, // No post-transfer callback
.flags = SPI_DEVICE_NO_DUMMY
};
// Initialize the SPI bus
esp_err_t ret = spi_bus_initialize(VSPI_HOST, &buscfg, SPI_DMA_CHAN);
ESP_ERROR_CHECK(ret);
// Attach the flash chip to the SPI bus
spi_device_handle_t spi_handle;
ret = spi_bus_add_device(VSPI_HOST, &devcfg, &spi_handle);
ESP_ERROR_CHECK(ret);
}
// Function to read from flash
static void read_flash()
{
ESP_LOGI(TAG, "Reading flash...");
// Open flash partition
const esp_partition_t* partition = esp_partition_find_first(ESP_PARTITION_TYPE_DATA, ESP_PARTITION_SUBTYPE_ANY, "my_partition");
if (!partition) {
ESP_LOGE(TAG, "Partition not found");
return;
}
// Initialize SPI bus
spi_init();
// Set up transfer
spi_transaction_t t = {
.flags = SPI_TRANS_USE_RXDATA | SPI_TRANS_USE_TXDATA,
.cmd = 0x03, // Read command
.addr = 0x0, // Start address of read
.length = 8*FLASH_SECTOR_SIZE // Read data size
};
// Read data from flash
uint8_t* data = malloc(FLASH_SECTOR_SIZE);
t.rx_buffer = data;
for (int i = 0; i < partition->size; i += FLASH_SECTOR_SIZE) {
t.addr = i;
esp_err_t ret = spi_device_polling_transmit(spi_handle, &t);
ESP_ERROR_CHECK(ret);
ESP_LOGI(TAG, "Data at address 0x%x:", i);
for (int j = 0; j < FLASH_SECTOR_SIZE; j++) {
printf("%02x ", data[j]);
}
printf("\n");
}
// Clean up
free(data);
spi_bus_remove_device(spi_handle);
spi_bus_free(VSPI_HOST);
}
// Function to write to flash
static void write_flash()
{
ESP_LOGI(TAG, "Writing flash...");
// Open flash partition
const esp_partition_t* partition = esp_partition_find_first(ESP_PARTITION_TYPE_DATA, ESP_PARTITION_SUBTYPE_ANY, "my_partition");
if (!partition) {
ESP_LOGE(TAG, "Partition not found");
return;
}
// Initialize SPI bus
spi_init();
// Erase flash sector
esp_err_t ret = spi_flash_erase_sector(partition->address);
ESP_ERROR_CHECK(ret);
// Set up transfer
spi_transaction_t t = {
.flags = SPI_TRANS_USE_RXDATA | SPI_TRANS_USE_TXDATA,
.cmd = 0x02, // Write command
.addr = 0x0, // Start address of write
.length = 8*FLASH_SECTOR_SIZE // Write data size
};
// Write data to flash
uint8_t* data = malloc(FLASH_SECTOR_SIZE);
for (int i = 0; i < FLASH_SECTOR_SIZE; i++) {
data[i] = i % 255;
}
t.tx_buffer = data;
ret = spi_device_polling_transmit(spi_handle, &t);
ESP_ERROR_CHECK(ret);
// Clean up
free(data);
spi_bus_remove_device(spi_handle);
spi_bus_free(VSPI_HOST);
}
void app_main()
{
// Initialize NVS
esp_err_t ret = nvs_flash_init();
if (ret == ESP_ERR_NVS_NO_FREE_PAGES || ret == ESP_ERR_NVS_NEW_VERSION_FOUND) {
ESP_ERROR_CHECK(nvs_flash_erase());
ret = nvs_flash_init();
}
ESP_ERROR_CHECK(ret);
// Write data to flash
write_flash();
// Read data from flash
read_flash();
}
```
这个示例代码演示了如何使用 ESP32 的 SPI 总线来读写 Flash。其中,`spi_init()` 函数初始化了 SPI 总线,`read_flash()` 函数从 Flash 中读取数据,`write_flash()` 函数将数据写入 Flash。在这个示例代码中,我们使用了 SPI 总线连接的 Flash,但是也可以连接其他的 SPI 设备。同时,我们使用了 ESP-IDF 中提供的 `spi_device_polling_transmit()` 函数来进行数据的读写。如果你需要进行更高级的操作,可以使用 `spi_device_queue_trans()` 函数来设置队列,并使用回调函数来处理数据。
阅读全文