Skip to content

Commit 0ce93b0

Browse files
committed
NVS: add more nvs function support
1. str,i8,u8,u16,u32 support 2. add partition_nvs.csv file 3. add nvs_partition_gen.py file for generate nvs partiton
1 parent a7e68eb commit 0ce93b0

File tree

3 files changed

+1392
-0
lines changed

3 files changed

+1392
-0
lines changed

m5stack/esp32_nvs.c

Lines changed: 273 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,273 @@
1+
/*
2+
* This file is part of the MicroPython project, http://micropython.org/
3+
*
4+
* The MIT License (MIT)
5+
*
6+
* Copyright (c) 2021 by Thorsten von Eicken
7+
*
8+
* Permission is hereby granted, free of charge, to any person obtaining a copy
9+
* of this software and associated documentation files (the "Software"), to deal
10+
* in the Software without restriction, including without limitation the rights
11+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
12+
* copies of the Software, and to permit persons to whom the Software is
13+
* furnished to do so, subject to the following conditions:
14+
*
15+
* The above copyright notice and this permission notice shall be included in
16+
* all copies or substantial portions of the Software.
17+
*
18+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
21+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24+
* THE SOFTWARE.
25+
*/
26+
27+
#include <string.h>
28+
29+
#include "py/runtime.h"
30+
#include "py/mperrno.h"
31+
#include "mphalport.h"
32+
#include "modesp32.h"
33+
#include "nvs_flash.h"
34+
#include "nvs.h"
35+
36+
// This file implements the NVS (Non-Volatile Storage) class in the esp32 module.
37+
// It provides simple access to the NVS feature provided by ESP-IDF.
38+
39+
// NVS python object that represents an NVS namespace.
40+
typedef struct _esp32_nvs_obj_t {
41+
mp_obj_base_t base;
42+
nvs_handle_t namespace;
43+
} esp32_nvs_obj_t;
44+
45+
// *esp32_nvs_new allocates a python NVS object given a handle to an esp-idf namespace C obj.
46+
STATIC esp32_nvs_obj_t *esp32_nvs_new(nvs_handle_t namespace) {
47+
esp32_nvs_obj_t *self = m_new_obj(esp32_nvs_obj_t);
48+
self->base.type = &esp32_nvs_type;
49+
self->namespace = namespace;
50+
return self;
51+
}
52+
53+
// esp32_nvs_print prints an NVS object, unfortunately it doesn't seem possible to extract the
54+
// namespace string or anything else from the opaque handle provided by esp-idf.
55+
STATIC void esp32_nvs_print(const mp_print_t *print, mp_obj_t self_in, mp_print_kind_t kind) {
56+
// esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
57+
mp_printf(print, "<NVS namespace>");
58+
}
59+
60+
// esp32_nvs_make_new constructs a handle to an NVS namespace.
61+
STATIC mp_obj_t esp32_nvs_make_new(const mp_obj_type_t *type, size_t n_args, size_t n_kw, const mp_obj_t *all_args) {
62+
// Check args
63+
mp_arg_check_num(n_args, n_kw, 1, 1, false);
64+
65+
// Get requested nvs namespace
66+
const char *ns_name = mp_obj_str_get_str(all_args[0]);
67+
nvs_handle_t namespace;
68+
check_esp_err(nvs_open(ns_name, NVS_READWRITE, &namespace));
69+
return MP_OBJ_FROM_PTR(esp32_nvs_new(namespace));
70+
}
71+
72+
// esp32_nvs_set_i8 sets a 8-bit integer value
73+
STATIC mp_obj_t esp32_nvs_set_i8(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
74+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
75+
const char *key = mp_obj_str_get_str(key_in);
76+
int8_t value = (int8_t)mp_obj_get_int(value_in);
77+
check_esp_err(nvs_set_i8(self->namespace, key, value));
78+
return mp_const_none;
79+
}
80+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_set_i8_obj, esp32_nvs_set_i8);
81+
82+
// esp32_nvs_get_i8 reads a 8-bit integer value
83+
STATIC mp_obj_t esp32_nvs_get_i8(mp_obj_t self_in, mp_obj_t key_in) {
84+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
85+
const char *key = mp_obj_str_get_str(key_in);
86+
int8_t value;
87+
check_esp_err(nvs_get_i8(self->namespace, key, &value));
88+
return mp_obj_new_int(value);
89+
}
90+
STATIC MP_DEFINE_CONST_FUN_OBJ_2(esp32_nvs_get_i8_obj, esp32_nvs_get_i8);
91+
92+
// esp32_nvs_set_u8 sets a 8-bit unsigned integer value
93+
STATIC mp_obj_t esp32_nvs_set_u8(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
94+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
95+
const char *key = mp_obj_str_get_str(key_in);
96+
uint8_t value = (uint8_t)mp_obj_get_int(value_in);
97+
check_esp_err(nvs_set_u8(self->namespace, key, value));
98+
return mp_const_none;
99+
}
100+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_set_u8_obj, esp32_nvs_set_u8);
101+
102+
// esp32_nvs_get_u8 reads a 8-bit unsigned integer value
103+
STATIC mp_obj_t esp32_nvs_get_u8(mp_obj_t self_in, mp_obj_t key_in) {
104+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
105+
const char *key = mp_obj_str_get_str(key_in);
106+
uint8_t value;
107+
check_esp_err(nvs_get_u8(self->namespace, key, &value));
108+
return mp_obj_new_int(value);
109+
}
110+
STATIC MP_DEFINE_CONST_FUN_OBJ_2(esp32_nvs_get_u8_obj, esp32_nvs_get_u8);
111+
112+
// esp32_nvs_set_u16 sets a 16-bit unsigned integer value
113+
STATIC mp_obj_t esp32_nvs_set_u16(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
114+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
115+
const char *key = mp_obj_str_get_str(key_in);
116+
uint16_t value = (uint16_t)mp_obj_get_int(value_in);
117+
check_esp_err(nvs_set_u16(self->namespace, key, value));
118+
return mp_const_none;
119+
}
120+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_set_u16_obj, esp32_nvs_set_u16);
121+
122+
// esp32_nvs_get_u16 reads a 16-bit unsigned integer value
123+
STATIC mp_obj_t esp32_nvs_get_u16(mp_obj_t self_in, mp_obj_t key_in) {
124+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
125+
const char *key = mp_obj_str_get_str(key_in);
126+
uint16_t value;
127+
check_esp_err(nvs_get_u16(self->namespace, key, &value));
128+
return mp_obj_new_int(value);
129+
}
130+
STATIC MP_DEFINE_CONST_FUN_OBJ_2(esp32_nvs_get_u16_obj, esp32_nvs_get_u16);
131+
132+
// esp32_nvs_set_i32 sets a 32-bit integer value
133+
STATIC mp_obj_t esp32_nvs_set_i32(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
134+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
135+
const char *key = mp_obj_str_get_str(key_in);
136+
int32_t value = mp_obj_get_int(value_in);
137+
check_esp_err(nvs_set_i32(self->namespace, key, value));
138+
return mp_const_none;
139+
}
140+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_set_i32_obj, esp32_nvs_set_i32);
141+
142+
// esp32_nvs_get_i32 reads a 32-bit integer value
143+
STATIC mp_obj_t esp32_nvs_get_i32(mp_obj_t self_in, mp_obj_t key_in) {
144+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
145+
const char *key = mp_obj_str_get_str(key_in);
146+
int32_t value;
147+
check_esp_err(nvs_get_i32(self->namespace, key, &value));
148+
return mp_obj_new_int(value);
149+
}
150+
STATIC MP_DEFINE_CONST_FUN_OBJ_2(esp32_nvs_get_i32_obj, esp32_nvs_get_i32);
151+
152+
// esp32_nvs_set_u32 sets a 32-bit unsigned integer value
153+
STATIC mp_obj_t esp32_nvs_set_u32(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
154+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
155+
const char *key = mp_obj_str_get_str(key_in);
156+
uint32_t value = mp_obj_get_int(value_in);
157+
check_esp_err(nvs_set_u32(self->namespace, key, value));
158+
return mp_const_none;
159+
}
160+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_set_u32_obj, esp32_nvs_set_u32);
161+
162+
// esp32_nvs_get_u32 reads a 32-bit unsigned integer value
163+
STATIC mp_obj_t esp32_nvs_get_u32(mp_obj_t self_in, mp_obj_t key_in) {
164+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
165+
const char *key = mp_obj_str_get_str(key_in);
166+
uint32_t value;
167+
check_esp_err(nvs_get_u32(self->namespace, key, &value));
168+
return mp_obj_new_int(value);
169+
}
170+
STATIC MP_DEFINE_CONST_FUN_OBJ_2(esp32_nvs_get_u32_obj, esp32_nvs_get_u32);
171+
172+
// esp32_nvs_set_blob writes a buffer object into a binary blob value.
173+
STATIC mp_obj_t esp32_nvs_set_blob(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
174+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
175+
const char *key = mp_obj_str_get_str(key_in);
176+
mp_buffer_info_t value;
177+
mp_get_buffer_raise(value_in, &value, MP_BUFFER_READ);
178+
check_esp_err(nvs_set_blob(self->namespace, key, value.buf, value.len));
179+
return mp_const_none;
180+
}
181+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_set_blob_obj, esp32_nvs_set_blob);
182+
183+
// esp32_nvs_get_blob reads a binary blob value into a bytearray. Returns actual length.
184+
STATIC mp_obj_t esp32_nvs_get_blob(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
185+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
186+
const char *key = mp_obj_str_get_str(key_in);
187+
// get buffer to be filled
188+
mp_buffer_info_t value;
189+
mp_get_buffer_raise(value_in, &value, MP_BUFFER_WRITE);
190+
size_t length = value.len;
191+
// fill the buffer with the value, will raise an esp-idf error if the length of
192+
// the provided buffer (bytearray) is too small
193+
check_esp_err(nvs_get_blob(self->namespace, key, value.buf, &length));
194+
return MP_OBJ_NEW_SMALL_INT(length);
195+
}
196+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_get_blob_obj, esp32_nvs_get_blob);
197+
198+
// esp32_nvs_set_str sets a string value
199+
STATIC mp_obj_t esp32_nvs_set_str(mp_obj_t self_in, mp_obj_t key_in, mp_obj_t value_in) {
200+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
201+
const char *key = mp_obj_str_get_str(key_in);
202+
const char *value = mp_obj_str_get_str(value_in);
203+
check_esp_err(nvs_set_str(self->namespace, key, value));
204+
return mp_const_none;
205+
}
206+
STATIC MP_DEFINE_CONST_FUN_OBJ_3(esp32_nvs_set_str_obj, esp32_nvs_set_str);
207+
208+
// esp32_nvs_get_str read string value. Returns the string value.
209+
STATIC mp_obj_t esp32_nvs_get_str(mp_obj_t self_in, mp_obj_t key_in) {
210+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
211+
const char *key = mp_obj_str_get_str(key_in);
212+
size_t length = 0;
213+
mp_obj_t str = mp_const_none;
214+
215+
// read string length.
216+
check_esp_err(nvs_get_str(self->namespace, key, NULL, &length));
217+
if (length > 0) {
218+
char *read_str = malloc(length);
219+
if (read_str) {
220+
check_esp_err(nvs_get_str(self->namespace, key, read_str, &length));
221+
str = mp_obj_new_str(read_str, strlen(read_str));
222+
free(read_str);
223+
}
224+
return str;
225+
}
226+
return mp_const_none;
227+
}
228+
STATIC MP_DEFINE_CONST_FUN_OBJ_2(esp32_nvs_get_str_obj, esp32_nvs_get_str);
229+
230+
// esp32_nvs_erase_key erases one key.
231+
STATIC mp_obj_t esp32_nvs_erase_key(mp_obj_t self_in, mp_obj_t key_in) {
232+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
233+
const char *key = mp_obj_str_get_str(key_in);
234+
check_esp_err(nvs_erase_key(self->namespace, key));
235+
return mp_const_none;
236+
}
237+
STATIC MP_DEFINE_CONST_FUN_OBJ_2(esp32_nvs_erase_key_obj, esp32_nvs_erase_key);
238+
239+
// esp32_nvs_commit commits any changes to flash.
240+
STATIC mp_obj_t esp32_nvs_commit(mp_obj_t self_in) {
241+
esp32_nvs_obj_t *self = MP_OBJ_TO_PTR(self_in);
242+
check_esp_err(nvs_commit(self->namespace));
243+
return mp_const_none;
244+
}
245+
STATIC MP_DEFINE_CONST_FUN_OBJ_1(esp32_nvs_commit_obj, esp32_nvs_commit);
246+
247+
STATIC const mp_rom_map_elem_t esp32_nvs_locals_dict_table[] = {
248+
{ MP_ROM_QSTR(MP_QSTR_get_u8), MP_ROM_PTR(&esp32_nvs_get_u8_obj) },
249+
{ MP_ROM_QSTR(MP_QSTR_set_u8), MP_ROM_PTR(&esp32_nvs_set_u8_obj) },
250+
{ MP_ROM_QSTR(MP_QSTR_get_i8), MP_ROM_PTR(&esp32_nvs_get_i8_obj) },
251+
{ MP_ROM_QSTR(MP_QSTR_set_i8), MP_ROM_PTR(&esp32_nvs_set_i8_obj) },
252+
{ MP_ROM_QSTR(MP_QSTR_get_u16), MP_ROM_PTR(&esp32_nvs_get_u16_obj) },
253+
{ MP_ROM_QSTR(MP_QSTR_set_u16), MP_ROM_PTR(&esp32_nvs_set_u16_obj) },
254+
{ MP_ROM_QSTR(MP_QSTR_get_i32), MP_ROM_PTR(&esp32_nvs_get_i32_obj) },
255+
{ MP_ROM_QSTR(MP_QSTR_set_i32), MP_ROM_PTR(&esp32_nvs_set_i32_obj) },
256+
{ MP_ROM_QSTR(MP_QSTR_get_u32), MP_ROM_PTR(&esp32_nvs_get_u32_obj) },
257+
{ MP_ROM_QSTR(MP_QSTR_set_u32), MP_ROM_PTR(&esp32_nvs_set_u32_obj) },
258+
{ MP_ROM_QSTR(MP_QSTR_get_blob), MP_ROM_PTR(&esp32_nvs_get_blob_obj) },
259+
{ MP_ROM_QSTR(MP_QSTR_set_blob), MP_ROM_PTR(&esp32_nvs_set_blob_obj) },
260+
{ MP_ROM_QSTR(MP_QSTR_get_str), MP_ROM_PTR(&esp32_nvs_get_str_obj) },
261+
{ MP_ROM_QSTR(MP_QSTR_set_str), MP_ROM_PTR(&esp32_nvs_set_str_obj) },
262+
{ MP_ROM_QSTR(MP_QSTR_erase_key), MP_ROM_PTR(&esp32_nvs_erase_key_obj) },
263+
{ MP_ROM_QSTR(MP_QSTR_commit), MP_ROM_PTR(&esp32_nvs_commit_obj) },
264+
};
265+
STATIC MP_DEFINE_CONST_DICT(esp32_nvs_locals_dict, esp32_nvs_locals_dict_table);
266+
267+
const mp_obj_type_t esp32_nvs_type = {
268+
{ &mp_type_type },
269+
.name = MP_QSTR_NVS,
270+
.print = esp32_nvs_print,
271+
.make_new = esp32_nvs_make_new,
272+
.locals_dict = (mp_obj_dict_t *)&esp32_nvs_locals_dict,
273+
};

m5stack/partition_nvs.csv

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
key,type,encoding,value
2+
uiflow,namespace,,
3+
ssid,data,string,
4+
pswd,data,string,
5+
ssid1,data,string,
6+
pswd1,data,string,
7+
ssid2,data,string,
8+
pswd2,data,string,

0 commit comments

Comments
 (0)