From 3459fe322b45bd1443fca8e12126d3919aa8784c Mon Sep 17 00:00:00 2001 From: Jeff Epler Date: Thu, 8 Dec 2022 15:21:20 -0600 Subject: [PATCH] Withdraw the _environ module This existed solely for testing, so expose it a different way during the unix coverage build Also turn off os.getenv support on samd21. --- devices/ble_hci/common-hal/_bleio/Adapter.c | 8 +- docs/environment.rst | 36 ++++-- ports/atmel-samd/mpconfigport.mk | 1 + ports/espressif/common-hal/_bleio/Adapter.c | 8 +- ports/espressif/supervisor/port.c | 4 +- ports/nrf/common-hal/_bleio/Adapter.c | 8 +- ports/unix/coverage.c | 1 + ports/unix/main.c | 8 ++ .../unix/variants/coverage/mpconfigvariant.mk | 5 +- py/circuitpy_defns.mk | 4 +- py/circuitpy_mpconfig.mk | 4 +- shared-bindings/_environ/__init__.c | 108 ------------------ shared-bindings/_environ/__init__.h | 37 ------ shared-bindings/os/__init__.c | 4 + shared-bindings/os/__init__.h | 2 + shared-bindings/os/getenv.c | 1 + shared-module/os/__init__.c | 15 --- shared-module/{_environ => os}/__init__.h | 6 +- .../{_environ/__init__.c => os/getenv.c} | 39 ++++--- supervisor/shared/filesystem.c | 2 +- supervisor/shared/web_workflow/web_workflow.c | 14 +-- tests/circuitpython/environ_test.py | 4 +- 22 files changed, 93 insertions(+), 226 deletions(-) delete mode 100644 shared-bindings/_environ/__init__.c delete mode 100644 shared-bindings/_environ/__init__.h create mode 100644 shared-bindings/os/getenv.c rename shared-module/{_environ => os}/__init__.h (89%) rename shared-module/{_environ/__init__.c => os/getenv.c} (88%) diff --git a/devices/ble_hci/common-hal/_bleio/Adapter.c b/devices/ble_hci/common-hal/_bleio/Adapter.c index 018b65de12..f558d66d40 100644 --- a/devices/ble_hci/common-hal/_bleio/Adapter.c +++ b/devices/ble_hci/common-hal/_bleio/Adapter.c @@ -49,8 +49,8 @@ #include "shared-bindings/_bleio/ScanEntry.h" #include "shared-bindings/time/__init__.h" -#if CIRCUITPY_ENVIRON -#include "shared-bindings/_environ/__init__.h" +#if CIRCUITPY_OS_GETENV +#include "shared-bindings/os/__init__.h" #endif #define MSEC_TO_UNITS(TIME, RESOLUTION) (((TIME) * 1000) / (RESOLUTION)) @@ -284,8 +284,8 @@ char default_ble_name[] = { 'C', 'I', 'R', 'C', 'U', 'I', 'T', 'P', 'Y', 0, 0, 0 STATIC void bleio_adapter_hci_init(bleio_adapter_obj_t *self) { mp_int_t name_len = 0; - #if CIRCUITPY_ENVIRON - mp_obj_t name = common_hal__environ_get_key("CIRCUITPY_BLE_NAME"); + #if CIRCUITPY_OS_GETENV + mp_obj_t name = common_hal_os_getenv("CIRCUITPY_BLE_NAME", mp_const_none); if (name != mp_const_none) { mp_arg_validate_type_string(name, MP_QSTR_CIRCUITPY_BLE_NAME); self->name = name; diff --git a/docs/environment.rst b/docs/environment.rst index 457e5c3f88..0a370d64d9 100644 --- a/docs/environment.rst +++ b/docs/environment.rst @@ -6,23 +6,33 @@ variables are commonly used to store "secrets" such as Wi-Fi passwords and API keys. This method *does not* make them secure. It only separates them from the code. -CircuitPython supports these by parsing a subset of the `toml `_ file format internally. +CircuitPython uses a file called ``settings.toml`` at the drive root (no +folder) as the environment. User code can access the values from the file +using `os.getenv()`. It is recommended to save any values used repeatedly in a +variable because `os.getenv()` will parse the ``settings.toml`` file contents +on every access. -Here is a simple example: +CircuitPython only supports a subset of the full toml specification, see below +for more details. The subset is very "Python-like", which is a key reason we +selected the format. -.. code-block:: bash +Due to technical limitations it probably also accepts some files that are +not valid TOML files; bugs of this nature are subject to change (i.e., be +fixed) without the usual deprecation period for incompatible changes. - KEY1="value1" - # Comment - KEY2="value2\ncontains a newline" +File format example: - [SECTION] # Only values in the "root table" are parsed - SECTION_VALUE = ... # so this value cannot be seen by getenv +.. code-block:: + + str_key="Hello world" # with trailing comment + int_key = 7 + unicode_key="👨" + unicode_key2="\\U0001f468" # same as above + escape_codes="supported, including \\r\\n\\"\\\\" + # comment + [subtable] + subvalue="cannot retrieve this using _environ or getenv" -CircuitPython uses the ``settings.toml`` at the drive root (no folder) as the environment. -User code can access the values from the file using `os.getenv()`. It is -recommended to save any values used repeatedly in a variable because `os.getenv()` -will parse the ``settings.toml`` file contents on every access. Details of the toml language subset ----------------------------------- @@ -36,6 +46,8 @@ Details of the toml language subset * Duplicate keys are not diagnosed. * Comments are supported * Only values from the "root table" can be retrieved +* due to technical limitations, the content of multi-line + strings can erroneously be parsed as a value. CircuitPython behavior ---------------------- diff --git a/ports/atmel-samd/mpconfigport.mk b/ports/atmel-samd/mpconfigport.mk index 05aed89eb2..72b1302227 100644 --- a/ports/atmel-samd/mpconfigport.mk +++ b/ports/atmel-samd/mpconfigport.mk @@ -33,6 +33,7 @@ CIRCUITPY_BLEIO_HCI = 0 CIRCUITPY_BUILTINS_POW3 ?= 0 CIRCUITPY_COMPUTED_GOTO_SAVE_SPACE ?= 1 CIRCUITPY_COUNTIO ?= 0 +CIRCUITPY_OS_GETENV ?= 0 # Not enough RAM for framebuffers CIRCUITPY_FRAMEBUFFERIO ?= 0 CIRCUITPY_FREQUENCYIO ?= 0 diff --git a/ports/espressif/common-hal/_bleio/Adapter.c b/ports/espressif/common-hal/_bleio/Adapter.c index f89848f782..7da1cd0b8c 100644 --- a/ports/espressif/common-hal/_bleio/Adapter.c +++ b/ports/espressif/common-hal/_bleio/Adapter.c @@ -59,8 +59,8 @@ #include "esp_bt.h" #include "esp_nimble_hci.h" -#if CIRCUITPY_ENVIRON -#include "shared-module/_environ/__init__.h" +#if CIRCUITPY_OS_GETENV +#include "shared-module/os/__init__.h" #endif bleio_connection_internal_t bleio_connections[BLEIO_TOTAL_CONNECTION_COUNT]; @@ -101,9 +101,9 @@ void common_hal_bleio_adapter_set_enabled(bleio_adapter_obj_t *self, bool enable ble_hs_cfg.sync_cb = _on_sync; // ble_hs_cfg.store_status_cb = ble_store_util_status_rr; - #if CIRCUITPY_ENVIRON + #if CIRCUITPY_OS_GETENV char ble_name[1 + MYNEWT_VAL_BLE_SVC_GAP_DEVICE_NAME_MAX_LENGTH]; - _environ_err_t result = _environ_get_key_str("CIRCUITPY_BLE_NAME", ble_name, sizeof(ble_name)); + os_environ_err_t result = common_hal_os_environ_get_key_str("CIRCUITPY_BLE_NAME", ble_name, sizeof(ble_name)); if (result == ENVIRON_OK) { ble_svc_gap_device_name_set(ble_name); } else diff --git a/ports/espressif/supervisor/port.c b/ports/espressif/supervisor/port.c index e89fb8c976..2792792455 100644 --- a/ports/espressif/supervisor/port.c +++ b/ports/espressif/supervisor/port.c @@ -55,7 +55,7 @@ #include "shared-bindings/microcontroller/RunMode.h" #include "shared-bindings/rtc/__init__.h" #include "shared-bindings/socketpool/__init__.h" -#include "shared-module/_environ/__init__.h" +#include "shared-module/os/__init__.h" #include "peripherals/rmt.h" #include "peripherals/timer.h" @@ -519,7 +519,7 @@ void port_idle_until_interrupt(void) { void port_post_boot_py(bool heap_valid) { if (!heap_valid && filesystem_present()) { mp_int_t reserved; - if (_environ_get_key_int("CIRCUITPY_RESERVED_PSRAM", &reserved) == ENVIRON_OK) { + if (common_hal_os_environ_get_key_int("CIRCUITPY_RESERVED_PSRAM", &reserved) == ENVIRON_OK) { common_hal_espidf_set_reserved_psram(reserved); } common_hal_espidf_reserve_psram(); diff --git a/ports/nrf/common-hal/_bleio/Adapter.c b/ports/nrf/common-hal/_bleio/Adapter.c index 012430704a..f9e3bddc72 100644 --- a/ports/nrf/common-hal/_bleio/Adapter.c +++ b/ports/nrf/common-hal/_bleio/Adapter.c @@ -52,8 +52,8 @@ #include "shared-bindings/_bleio/ScanEntry.h" #include "shared-bindings/time/__init__.h" -#if CIRCUITPY_ENVIRON -#include "shared-bindings/_environ/__init__.h" +#if CIRCUITPY_OS_GETENV +#include "shared-bindings/os/getenv.h" #endif #define BLE_MIN_CONN_INTERVAL MSEC_TO_UNITS(15, UNIT_0_625_MS) @@ -345,8 +345,8 @@ STATIC void bleio_adapter_reset_name(bleio_adapter_obj_t *self) { mp_int_t name_len = 0; - #if CIRCUITPY_ENVIRON - mp_obj_t ble_name = common_hal__environ_get_key("CIRCUITPY_BLE_NAME"); + #if CIRCUITPY_OS_GETENV + mp_obj_t ble_name = common_hal_os_environ_get_key("CIRCUITPY_BLE_NAME"); if (ble_name != mp_const_none) { common_hal_bleio_adapter_set_name(self, mp_obj_str_get_str(ble_name)); return; diff --git a/ports/unix/coverage.c b/ports/unix/coverage.c index 0e4c6dbd48..8463c169e4 100644 --- a/ports/unix/coverage.c +++ b/ports/unix/coverage.c @@ -95,6 +95,7 @@ STATIC const mp_rom_map_elem_t rawfile_locals_dict_table[] = { { MP_ROM_QSTR(MP_QSTR_readinto), MP_ROM_PTR(&mp_stream_readinto_obj) }, { MP_ROM_QSTR(MP_QSTR_readline), MP_ROM_PTR(&mp_stream_unbuffered_readline_obj) }, { MP_ROM_QSTR(MP_QSTR_ioctl), MP_ROM_PTR(&mp_stream_ioctl_obj) }, + { MP_ROM_QSTR(MP_QSTR_ioctl), MP_ROM_PTR(&mp_stream_ioctl_obj) }, }; STATIC MP_DEFINE_CONST_DICT(rawfile_locals_dict, rawfile_locals_dict_table); diff --git a/ports/unix/main.c b/ports/unix/main.c index 5ebcf9193b..aa7c92dcff 100644 --- a/ports/unix/main.c +++ b/ports/unix/main.c @@ -420,6 +420,13 @@ STATIC void set_sys_argv(char *argv[], int argc, int start_arg) { #define PATHLIST_SEP_CHAR ':' #endif +mp_obj_t common_hal_os_getenv_path(const char *path, const char *key, mp_obj_t default_); +STATIC mp_obj_t get_key(mp_obj_t path_in, mp_obj_t key_to_get_in) { + return common_hal_os_getenv_path(mp_obj_str_get_str(path_in), + mp_obj_str_get_str(key_to_get_in), mp_const_none); +} +MP_DEFINE_CONST_FUN_OBJ_2(get_key_obj, get_key); + MP_NOINLINE int main_(int argc, char **argv); int main(int argc, char **argv) { @@ -540,6 +547,7 @@ MP_NOINLINE int main_(int argc, char **argv) { MP_DECLARE_CONST_FUN_OBJ_0(extra_cpp_coverage_obj); mp_store_global(MP_QSTR_extra_coverage, MP_OBJ_FROM_PTR(&extra_coverage_obj)); mp_store_global(MP_QSTR_extra_cpp_coverage, MP_OBJ_FROM_PTR(&extra_cpp_coverage_obj)); + mp_store_global(MP_QSTR_get_key, MP_OBJ_FROM_PTR(&get_key_obj)); } #endif diff --git a/ports/unix/variants/coverage/mpconfigvariant.mk b/ports/unix/variants/coverage/mpconfigvariant.mk index a0e0f4f3bb..e351fc0836 100644 --- a/ports/unix/variants/coverage/mpconfigvariant.mk +++ b/ports/unix/variants/coverage/mpconfigvariant.mk @@ -33,7 +33,6 @@ SRC_BITMAP := \ shared-bindings/aesio/__init__.c \ shared-bindings/bitmaptools/__init__.c \ shared-bindings/displayio/Bitmap.c \ - shared-bindings/_environ/__init__.c \ shared-bindings/rainbowio/__init__.c \ shared-bindings/traceback/__init__.c \ shared-bindings/util.c \ @@ -45,7 +44,7 @@ SRC_BITMAP := \ shared-module/displayio/Bitmap.c \ shared-module/displayio/ColorConverter.c \ shared-module/displayio/ColorConverter.c \ - shared-module/_environ/__init__.c \ + shared-module/os/getenv.c \ shared-module/rainbowio/__init__.c \ shared-module/traceback/__init__.c \ shared-module/zlib/__init__.c \ @@ -56,7 +55,7 @@ CFLAGS += \ -DCIRCUITPY_AESIO=1 \ -DCIRCUITPY_BITMAPTOOLS=1 \ -DCIRCUITPY_DISPLAYIO_UNIX=1 \ - -DCIRCUITPY_ENVIRON=1 \ + -DCIRCUITPY_OS_GETENV=1 \ -DCIRCUITPY_GIFIO=1 \ -DCIRCUITPY_RAINBOWIO=1 \ -DCIRCUITPY_TRACEBACK=1 \ diff --git a/py/circuitpy_defns.mk b/py/circuitpy_defns.mk index 7d8fa6bada..df3f664864 100644 --- a/py/circuitpy_defns.mk +++ b/py/circuitpy_defns.mk @@ -182,9 +182,6 @@ endif ifeq ($(CIRCUITPY_DISPLAYIO),1) SRC_PATTERNS += displayio/% endif -ifeq ($(CIRCUITPY_ENVIRON),1) -SRC_PATTERNS += _environ/% -endif ifeq ($(CIRCUITPY__EVE),1) SRC_PATTERNS += _eve/% endif @@ -618,6 +615,7 @@ SRC_SHARED_MODULE_ALL = \ onewireio/__init__.c \ onewireio/OneWire.c \ os/__init__.c \ + os/getenv.c \ paralleldisplay/ParallelBus.c \ qrio/__init__.c \ qrio/QRDecoder.c \ diff --git a/py/circuitpy_mpconfig.mk b/py/circuitpy_mpconfig.mk index a6a1118d2d..f0e145998b 100644 --- a/py/circuitpy_mpconfig.mk +++ b/py/circuitpy_mpconfig.mk @@ -215,8 +215,8 @@ CFLAGS += -DCIRCUITPY_DUALBANK=$(CIRCUITPY_DUALBANK) CIRCUITPY_ENABLE_MPY_NATIVE ?= 0 CFLAGS += -DCIRCUITPY_ENABLE_MPY_NATIVE=$(CIRCUITPY_ENABLE_MPY_NATIVE) -CIRCUITPY_ENVIRON ?= $(CIRCUITPY_FULL_BUILD) -CFLAGS += -DCIRCUITPY_ENVIRON=$(CIRCUITPY_ENVIRON) +CIRCUITPY_OS_GETENV ?= $(CIRCUITPY_FULL_BUILD) +CFLAGS += -DCIRCUITPY_OS_GETENV=$(CIRCUITPY_OS_GETENV) CIRCUITPY_ERRNO ?= $(CIRCUITPY_FULL_BUILD) CFLAGS += -DCIRCUITPY_ERRNO=$(CIRCUITPY_ERRNO) diff --git a/shared-bindings/_environ/__init__.c b/shared-bindings/_environ/__init__.c deleted file mode 100644 index a35181b754..0000000000 --- a/shared-bindings/_environ/__init__.c +++ /dev/null @@ -1,108 +0,0 @@ -/* - * This file is part of the Micro Python project, http://micropython.org/ - * - * The MIT License (MIT) - * - * SPDX-FileCopyrightText: Copyright (c) 2022 Scott Shawcroft for Adafruit Industries - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - */ - -#include - -#include "extmod/vfs.h" -#include "lib/oofatfs/ff.h" -#include "lib/oofatfs/diskio.h" -#include "py/mpstate.h" -#include "py/obj.h" -#include "py/objstr.h" -#include "py/runtime.h" -#include "shared-bindings/_environ/__init__.h" - -//| """Functions to manage environment variables from a settings.toml file. -//| -//| This library can read a subset of `toml files `_. -//| -//| It is recommended to not use this module directly. Instead, retrieve string -//| values using `os.getenv`. -//| -//| Due to technical limitations it probably also accepts some files that are -//| not valid TOML files; bugs of this nature are subject to change (i.e., be -//| fixed) without the usual deprecation period for incompatible changes. -//| -//| Details of the format understood by this module: -//| * the content is required to be in UTF-8 encoding -//| * the supported data types are string and integer -//| * only integers and basic strings are supported -//| * only integers supported by strtol are supported (no 0o, no 0b, no -//| underscores 1_000, 011 is 9, not 11) -//| * In quoted strings, all standard eescape codes, including ``\\uxxxx`` -//| and ``\\Uxxxxxxxx``, are supported -//| * only bare keys are supported -//| * duplicate keys are not diagnosed. -//| * comments are supported -//| * only values from the "root table" can be retrieved (parsing ends when it -//| encounters a line starting with [) -//| * due to technical limitations, the content of multi-line -//| strings can erroneously be parsed as a value. -//| -//| File format example: -//| -//| .. code-block:: -//| -//| str_key="Hello world" # with trailing comment -//| int_key = 7 -//| unicode_key="👨" -//| unicode_key2="\\U0001f468" # same as above -//| escape_codes="supported, including \\r\\n\\"\\\\" -//| # comment -//| [subtable] -//| subvalue="cannot retrieve this using _environ or getenv" -//| -//| """ -//| -//| import typing -//| - -//| def get_key(_environ_path: str, key_to_get: str) -> Union[str, int, None]: -//| """Get the value for the given key from the given .env file. -//| -//| Returns None if the key isn't found""" -//| ... -//| -STATIC mp_obj_t __environ_get_key(mp_obj_t path_in, mp_obj_t key_to_get_in) { - return common_hal__environ_get_key_path(mp_obj_str_get_str(path_in), - mp_obj_str_get_str(key_to_get_in)); -} -MP_DEFINE_CONST_FUN_OBJ_2(_environ_get_key_obj, __environ_get_key); - -STATIC const mp_rom_map_elem_t _environ_module_globals_table[] = { - { MP_ROM_QSTR(MP_QSTR___name__), MP_ROM_QSTR(MP_QSTR__environ) }, - - { MP_ROM_QSTR(MP_QSTR_get_key), MP_ROM_PTR(&_environ_get_key_obj) }, -}; - -STATIC MP_DEFINE_CONST_DICT(_environ_module_globals, _environ_module_globals_table); - -const mp_obj_module_t _environ_module = { - .base = { &mp_type_module }, - .globals = (mp_obj_dict_t *)&_environ_module_globals, -}; - -MP_REGISTER_MODULE(MP_QSTR__environ, _environ_module, CIRCUITPY_ENVIRON); diff --git a/shared-bindings/_environ/__init__.h b/shared-bindings/_environ/__init__.h deleted file mode 100644 index 7779f3ac82..0000000000 --- a/shared-bindings/_environ/__init__.h +++ /dev/null @@ -1,37 +0,0 @@ -/* - * This file is part of the MicroPython project, http://micropython.org/ - * - * The MIT License (MIT) - * - * Copyright (c) 2022 Scott Shawcroft for Adafruit Industries - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - */ - -#pragma once - -#include -#include - -#include "py/objtuple.h" - -#include "shared-module/_environ/__init__.h" - -mp_obj_t common_hal__environ_get_key_path(const char *path, const char *key); -mp_obj_t common_hal__environ_get_key(const char *key); diff --git a/shared-bindings/os/__init__.c b/shared-bindings/os/__init__.c index 1260903203..b2fb8ff095 100644 --- a/shared-bindings/os/__init__.c +++ b/shared-bindings/os/__init__.c @@ -92,6 +92,7 @@ MP_DEFINE_CONST_FUN_OBJ_0(os_getcwd_obj, os_getcwd); //| ... //| STATIC mp_obj_t os_getenv(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args) { + #if CIRCUITPY_OS_GETENV enum { ARG_key, ARG_default }; static const mp_arg_t allowed_args[] = { { MP_QSTR_key, MP_ARG_REQUIRED | MP_ARG_OBJ }, @@ -101,6 +102,9 @@ STATIC mp_obj_t os_getenv(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_ mp_arg_parse_all(n_args, pos_args, kw_args, MP_ARRAY_SIZE(allowed_args), allowed_args, args); return common_hal_os_getenv(mp_obj_str_get_str(args[ARG_key].u_obj), args[ARG_default].u_obj); + #else + return mp_const_none; + #endif } STATIC MP_DEFINE_CONST_FUN_OBJ_KW(os_getenv_obj, 1, os_getenv); diff --git a/shared-bindings/os/__init__.h b/shared-bindings/os/__init__.h index 00d8c28a50..49b12cd52a 100644 --- a/shared-bindings/os/__init__.h +++ b/shared-bindings/os/__init__.h @@ -38,6 +38,8 @@ mp_obj_t common_hal_os_uname(void); void common_hal_os_chdir(const char *path); mp_obj_t common_hal_os_getcwd(void); mp_obj_t common_hal_os_getenv(const char *key, mp_obj_t default_); +mp_obj_t common_hal_os_getenv_path(const char *path, const char *key, mp_obj_t default_); + mp_obj_t common_hal_os_listdir(const char *path); void common_hal_os_mkdir(const char *path); void common_hal_os_remove(const char *path); diff --git a/shared-bindings/os/getenv.c b/shared-bindings/os/getenv.c new file mode 100644 index 0000000000..fdb5f0bb50 --- /dev/null +++ b/shared-bindings/os/getenv.c @@ -0,0 +1 @@ +// this file needs to exist but does not have any content diff --git a/shared-module/os/__init__.c b/shared-module/os/__init__.c index 57e7e62932..4a4c02e636 100644 --- a/shared-module/os/__init__.c +++ b/shared-module/os/__init__.c @@ -36,10 +36,6 @@ #include "py/runtime.h" #include "shared-bindings/os/__init__.h" -#if CIRCUITPY_ENVIRON -#include "shared-bindings/_environ/__init__.h" -#endif - // This provides all VFS related OS functions so that ports can share the code // as needed. It does not provide uname. @@ -111,17 +107,6 @@ mp_obj_t common_hal_os_getcwd(void) { return mp_vfs_getcwd(); } -mp_obj_t common_hal_os_getenv(const char *key, mp_obj_t default_) { - #if CIRCUITPY_ENVIRON - mp_obj_t env_obj = common_hal__environ_get_key(key); - // TODO must be a str object - if (env_obj != mp_const_none) { - return env_obj; - } - #endif - return default_; -} - mp_obj_t common_hal_os_listdir(const char *path) { mp_obj_t path_out; mp_vfs_mount_t *vfs = lookup_dir_path(path, &path_out); diff --git a/shared-module/_environ/__init__.h b/shared-module/os/__init__.h similarity index 89% rename from shared-module/_environ/__init__.h rename to shared-module/os/__init__.h index c96eb028b8..48bd06195e 100644 --- a/shared-module/_environ/__init__.h +++ b/shared-module/os/__init__.h @@ -33,13 +33,13 @@ typedef enum { ENVIRON_ERR_LENGTH, ENVIRON_ERR_NOT_FOUND, ENVIRON_ERR_UNEXPECTED = 0xff00, // logical or'd with the byte value -} _environ_err_t; +} os_environ_err_t; // Allocation free version that returns the full length of the value. // If it fits, the return value is 0-terminated. If the value doesn't fit, // *value_len may be an over-estimate but never an under-estimate. -_environ_err_t _environ_get_key_str(const char *key, char *value, size_t value_len); +os_environ_err_t common_hal_os_environ_get_key_str(const char *key, char *value, size_t value_len); // Returns ENVIRON_ERR_OK and sets value to the read value. Returns // ENVIRON_ERR_... if the value was not numeric. allocation-free. -_environ_err_t _environ_get_key_int(const char *key, mp_int_t *value); +os_environ_err_t common_hal_os_environ_get_key_int(const char *key, mp_int_t *value); diff --git a/shared-module/_environ/__init__.c b/shared-module/os/getenv.c similarity index 88% rename from shared-module/_environ/__init__.c rename to shared-module/os/getenv.c index 7e6e133e1a..ec9edbacac 100644 --- a/shared-module/_environ/__init__.c +++ b/shared-module/os/getenv.c @@ -27,7 +27,8 @@ #include #include -#include "shared-bindings/_environ/__init__.h" +#include "shared-bindings/os/__init__.h" +#include "shared-module/os/__init__.h" #include "py/gc.h" #include "py/misc.h" @@ -177,7 +178,7 @@ STATIC bool key_matches(file_arg *active_file, const char *key) { return true; } -STATIC _environ_err_t read_unicode_escape(file_arg *active_file, int sz, vstr_t *buf) { +STATIC os_environ_err_t read_unicode_escape(file_arg *active_file, int sz, vstr_t *buf) { char hex_buf[sz + 1]; for (int i = 0; i < sz; i++) { hex_buf[i] = get_next_byte(active_file); @@ -196,7 +197,7 @@ STATIC _environ_err_t read_unicode_escape(file_arg *active_file, int sz, vstr_t } // Read a quoted string -STATIC _environ_err_t read_string_value(file_arg *active_file, vstr_t *buf) { +STATIC os_environ_err_t read_string_value(file_arg *active_file, vstr_t *buf) { while (true) { int character = get_next_byte(active_file); switch (character) { @@ -243,7 +244,7 @@ STATIC _environ_err_t read_string_value(file_arg *active_file, vstr_t *buf) { case 'U': case 'u': { int sz = (character == 'u') ? 4 : 8; - _environ_err_t res; + os_environ_err_t res; res = read_unicode_escape(active_file, sz, buf); if (res != ENVIRON_OK) { return res; @@ -261,7 +262,7 @@ STATIC _environ_err_t read_string_value(file_arg *active_file, vstr_t *buf) { } // Read a numeric value (non-quoted value) as a string -STATIC _environ_err_t read_bare_value(file_arg *active_file, vstr_t *buf, int first_character) { +STATIC os_environ_err_t read_bare_value(file_arg *active_file, vstr_t *buf, int first_character) { int character = first_character; while (true) { switch (character) { @@ -291,13 +292,13 @@ STATIC mp_int_t read_value(file_arg *active_file, vstr_t *buf, bool *quoted) { } } -STATIC _environ_err_t _environ_get_key_vstr(const char *path, const char *key, vstr_t *buf, bool *quoted) { +STATIC os_environ_err_t os_environ_get_key_vstr(const char *path, const char *key, vstr_t *buf, bool *quoted) { file_arg active_file; if (!open_file(path, &active_file)) { return ENVIRON_ERR_OPEN; } - _environ_err_t result = ENVIRON_ERR_NOT_FOUND; + os_environ_err_t result = ENVIRON_ERR_NOT_FOUND; while (!is_eof(&active_file)) { if (key_matches(&active_file, key)) { result = read_value(&active_file, buf, quoted); @@ -307,10 +308,10 @@ STATIC _environ_err_t _environ_get_key_vstr(const char *path, const char *key, v return result; } -STATIC _environ_err_t _environ_get_key_buf_terminated(const char *key, char *value, size_t value_len, bool *quoted) { +STATIC os_environ_err_t os_environ_get_key_buf_terminated(const char *key, char *value, size_t value_len, bool *quoted) { vstr_t buf; vstr_init_fixed_buf(&buf, value_len, value); - _environ_err_t result = _environ_get_key_vstr(ENVIRON_PATH, key, &buf, quoted); + os_environ_err_t result = os_environ_get_key_vstr(ENVIRON_PATH, key, &buf, quoted); if (result == ENVIRON_OK) { vstr_add_byte_nonstd(&buf, 0); @@ -322,16 +323,16 @@ STATIC _environ_err_t _environ_get_key_buf_terminated(const char *key, char *val return result; } -_environ_err_t _environ_get_key_str(const char *key, char *value, size_t value_len) { +os_environ_err_t common_hal_os_environ_get_key_str(const char *key, char *value, size_t value_len) { bool quoted; - _environ_err_t result = _environ_get_key_buf_terminated(key, value, value_len, "ed); + os_environ_err_t result = os_environ_get_key_buf_terminated(key, value, value_len, "ed); if (result == ENVIRON_OK && !quoted) { result = ENVIRON_ERR_UNEXPECTED | value[0]; } return result; } -STATIC void throw__environ_error(_environ_err_t error) { +STATIC void throw__environ_error(os_environ_err_t error) { if (error == ENVIRON_OK) { return; } @@ -360,14 +361,14 @@ STATIC void throw__environ_error(_environ_err_t error) { } } -mp_obj_t common_hal__environ_get_key_path(const char *path, const char *key) { +mp_obj_t common_hal_os_getenv_path(const char *path, const char *key, mp_obj_t default_) { vstr_t buf; bool quoted; vstr_init(&buf, 64); - _environ_err_t result = _environ_get_key_vstr(path, key, &buf, "ed); + os_environ_err_t result = os_environ_get_key_vstr(path, key, &buf, "ed); if (result == ENVIRON_ERR_NOT_FOUND) { - return mp_const_none; + return default_; } throw__environ_error(result); @@ -378,14 +379,14 @@ mp_obj_t common_hal__environ_get_key_path(const char *path, const char *key) { } } -mp_obj_t common_hal__environ_get_key(const char *key) { - return common_hal__environ_get_key_path(ENVIRON_PATH, key); +mp_obj_t common_hal_os_getenv(const char *key, mp_obj_t default_) { + return common_hal_os_getenv_path(ENVIRON_PATH, key, default_); } -_environ_err_t _environ_get_key_int(const char *key, mp_int_t *value) { +os_environ_err_t common_hal_os_environ_get_key_int(const char *key, mp_int_t *value) { char buf[16]; bool quoted; - _environ_err_t result = _environ_get_key_buf_terminated(key, buf, sizeof(buf), "ed); + os_environ_err_t result = os_environ_get_key_buf_terminated(key, buf, sizeof(buf), "ed); if (result != ENVIRON_OK) { return result; } diff --git a/supervisor/shared/filesystem.c b/supervisor/shared/filesystem.c index 2c963b78ef..1eab59c384 100644 --- a/supervisor/shared/filesystem.c +++ b/supervisor/shared/filesystem.c @@ -129,7 +129,7 @@ bool filesystem_init(bool create_allowed, bool force_create) { make_empty_file(&vfs_fat->fatfs, "/.metadata_never_index"); make_empty_file(&vfs_fat->fatfs, "/.Trashes"); make_empty_file(&vfs_fat->fatfs, "/.fseventsd/no_log"); - #if CIRCUITPY_ENVIRON + #if CIRCUITPY_OS_GETENV make_empty_file(&vfs_fat->fatfs, "/settings.toml"); #endif // make a sample code.py file diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index d54f853891..ab9ded66a3 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -64,8 +64,8 @@ #include "shared-bindings/wifi/__init__.h" #endif -#if CIRCUITPY_ENVIRON -#include "shared-module/_environ/__init__.h" +#if CIRCUITPY_OS_GETENV +#include "shared-module/os/__init__.h" #endif enum request_state { @@ -244,19 +244,19 @@ void supervisor_web_workflow_status(void) { #endif void supervisor_start_web_workflow(void) { - #if CIRCUITPY_WEB_WORKFLOW && CIRCUITPY_WIFI && CIRCUITPY_ENVIRON + #if CIRCUITPY_WEB_WORKFLOW && CIRCUITPY_WIFI && CIRCUITPY_OS_GETENV char ssid[33]; char password[64]; size_t ssid_len = 0; size_t password_len = 0; - _environ_err_t result = _environ_get_key_str("CIRCUITPY_WIFI_SSID", ssid, sizeof(ssid)); + os_environ_err_t result = common_hal_os_environ_get_key_str("CIRCUITPY_WIFI_SSID", ssid, sizeof(ssid)); if (result != ENVIRON_OK) { return; } - result = _environ_get_key_str("CIRCUITPY_WIFI_PASSWORD", password, sizeof(password)); + result = common_hal_os_environ_get_key_str("CIRCUITPY_WIFI_PASSWORD", password, sizeof(password)); if (result != ENVIRON_OK) { return; } @@ -283,7 +283,7 @@ void supervisor_start_web_workflow(void) { mp_int_t new_port = web_api_port; // (leaves new_port unchanged on any failure) - (void)_environ_get_key_int("CIRCUITPY_WEB_API_PORT", &new_port); + (void)common_hal_os_environ_get_key_int("CIRCUITPY_WEB_API_PORT", &new_port); bool first_start = pool.base.type != &socketpool_socketpool_type; bool port_changed = new_port != web_api_port; @@ -320,7 +320,7 @@ void supervisor_start_web_workflow(void) { const size_t api_password_len = sizeof(_api_password) - 1; - result = _environ_get_key_str("CIRCUITPY_WEB_API_PASSWORD", _api_password + 1, api_password_len); + result = common_hal_os_environ_get_key_str("CIRCUITPY_WEB_API_PASSWORD", _api_password + 1, api_password_len); if (result == ENVIRON_OK) { _api_password[0] = ':'; _base64_in_place(_api_password, strlen(_api_password), sizeof(_api_password) - 1); diff --git a/tests/circuitpython/environ_test.py b/tests/circuitpython/environ_test.py index 46ceff5c9d..8dfab8812c 100644 --- a/tests/circuitpython/environ_test.py +++ b/tests/circuitpython/environ_test.py @@ -1,8 +1,8 @@ import os try: - from _environ import get_key -except: + get_key +except NameError: # Because run-tests.py suppresses site-packages, this test can't be run # on the host interpreter. However, it can be run manually to # generate/update the expected file.