From a46a44db26cd9e8b73b95cb1f498139ace19f769 Mon Sep 17 00:00:00 2001 From: foamyguy Date: Fri, 15 Jul 2022 16:25:57 -0500 Subject: [PATCH 01/44] adding edit page --- .../shared/web_workflow/static/directory.html | 2 +- .../shared/web_workflow/static/edit.html | 40 +++++++++ supervisor/shared/web_workflow/static/edit.js | 90 +++++++++++++++++++ supervisor/shared/web_workflow/web_workflow.c | 4 + 4 files changed, 135 insertions(+), 1 deletion(-) create mode 100644 supervisor/shared/web_workflow/static/edit.html create mode 100644 supervisor/shared/web_workflow/static/edit.js diff --git a/supervisor/shared/web_workflow/static/directory.html b/supervisor/shared/web_workflow/static/directory.html index d0ca1a3b32..7eeff1542e 100644 --- a/supervisor/shared/web_workflow/static/directory.html +++ b/supervisor/shared/web_workflow/static/directory.html @@ -8,7 +8,7 @@

 

- + diff --git a/supervisor/shared/web_workflow/static/edit.html b/supervisor/shared/web_workflow/static/edit.html new file mode 100644 index 0000000000..417cebbed0 --- /dev/null +++ b/supervisor/shared/web_workflow/static/edit.html @@ -0,0 +1,40 @@ + + + + + Code Edit + + + + + + + + + + + +

Loading

+
+ + + + diff --git a/supervisor/shared/web_workflow/static/edit.js b/supervisor/shared/web_workflow/static/edit.js new file mode 100644 index 0000000000..a3f8a7d5a9 --- /dev/null +++ b/supervisor/shared/web_workflow/static/edit.js @@ -0,0 +1,90 @@ +let editor; +require(["ace/ace", "ace/ext/settings_menu"], function (ace) { + editor = ace.edit("code_textarea"); + ace.config.set('basePath', 'https://cdnjs.cloudflare.com/ajax/libs/ace/1.6.0/'); + console.log("after create editor"); + console.log(editor); + + editor.session.setMode("ace/mode/python"); + ace.require('ace/ext/settings_menu').init(editor); + editor.commands.addCommands([{ + name: "showSettingsMenu", + bindKey: {win: "Ctrl-e", mac: "Ctrl-e"}, + exec: function (editor) { + console.log("ctrl-e") + editor.showSettingsMenu(); + }, + readOnly: true + }, { + name: "infoDocsSearch", + bindKey: {win: "Ctrl-i", mac: "Ctrl-i"}, + exec: function (editor) { + window.open(`https://docs.circuitpython.org/en/latest/search.html?q=${editor.getSelectedText()}`, '_blank'); + }, + readOnly: true + },{ + name: 'Save', + bindKey: {win: 'Ctrl-S', mac: 'Command-S'}, + exec: function (editor) { + console.log("ctrl-s save"); + save(); + + } + },{ + name: "replaceCtrlR", + bindKey: {win: "Ctrl-r", mac: "Ctrl-r"}, + exec: function (editor_arg) { + console.log("override ctrl r"); + editor.execCommand('replace'); + console.log(editor); + }, + readOnly: true + }]); + + +}); + +let filename = location.hash.substring(1); +let $output_text = document.querySelector("#output_text"); +/*let $code_text = document.querySelector("#code_textarea");*/ + +fetch(`/fs/${filename}`) + .then(function (response) { + $output_text.innerText = `Loading Status: ${response.status}`; + return response.status === 200 ? response.text() : ""; + }) + .then(function (data) { + editor.setValue(data, -1) + }); + +function save() { + $output_text.innerText = "Saving..." + const requestOptions = { + method: 'PUT', + body: editor.getValue() + }; + fetch(`/fs/${filename}`, requestOptions) + .then(function (response) { + $output_text.innerText = `Saving Status: ${response.status}`; + return response.text(); + }) + .then(function (data) { + console.log("after fetch: " + data); + }); +} + +document.querySelector("#save_btn").onclick = function () { + console.log("Click Save!"); + save(); +} +document.querySelector("#docs_btn").onclick = function () { + window.open(`https://docs.circuitpython.org/en/latest/search.html?q=${editor.getSelectedText()}`, '_blank'); +} + +document.querySelector("#undo_btn").onclick = function () { + editor.undo(); +} + +document.querySelector("#redo_btn").onclick = function () { + editor.redo(); +} diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 6cf765b8f9..5eeb49a570 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -839,6 +839,8 @@ STATIC_FILE(directory_html); STATIC_FILE(directory_js); STATIC_FILE(welcome_html); STATIC_FILE(welcome_js); +STATIC_FILE(edit_html); +STATIC_FILE(edit_js); STATIC_FILE(serial_html); STATIC_FILE(serial_js); STATIC_FILE(blinka_16x16_ico); @@ -1047,6 +1049,8 @@ static bool _reply(socketpool_socket_obj_t *socket, _request *request) { _REPLY_STATIC(socket, request, welcome_js); } else if (strcmp(request->path, "/serial.js") == 0) { _REPLY_STATIC(socket, request, serial_js); + } else if (strcmp(request->path, "/edit.js") == 0) { + _REPLY_STATIC(socket, request, edit_js); } else if (strcmp(request->path, "/favicon.ico") == 0) { // TODO: Autogenerate this based on the blinka bitmap and change the // palette based on MAC address. From 78b4159448c6ec54da110eb3ddf380847def650e Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Wed, 13 Jul 2022 16:51:01 -0700 Subject: [PATCH 02/44] Allow for dynamic reconfigure including port --- docs/environment.rst | 4 + docs/workflows.md | 4 +- ports/espressif/common-hal/mdns/Server.c | 6 +- shared-bindings/mdns/Server.c | 3 + .../shared/web_workflow/static/welcome.js | 2 +- supervisor/shared/web_workflow/web_workflow.c | 93 +++++++++++++------ 6 files changed, 79 insertions(+), 33 deletions(-) diff --git a/docs/environment.rst b/docs/environment.rst index 4d12009848..b1619f37bf 100644 --- a/docs/environment.rst +++ b/docs/environment.rst @@ -39,6 +39,10 @@ CIRCUITPY_WEB_API_PASSWORD ~~~~~~~~~~~~~~~~~~~~~~~~~~ Password required to make modifications to the board from the Web Workflow. +CIRCUITPY_WEB_API_PORT +~~~~~~~~~~~~~~~~~~~~~~ +TCP port number used for the web HTTP API. Defaults to 80 when omitted. + CIRCUITPY_WIFI_PASSWORD ~~~~~~~~~~~~~~~~~~~~~~~ Wi-Fi password used to auto connect to CIRCUITPY_WIFI_SSID. diff --git a/docs/workflows.md b/docs/workflows.md index 2196d1111a..8530269534 100644 --- a/docs/workflows.md +++ b/docs/workflows.md @@ -72,7 +72,7 @@ Read-only characteristic that returns the UTF-8 encoded version string. The web workflow is depends on adding Wi-Fi credentials into the `/.env` file. The keys are `CIRCUITPY_WIFI_SSID` and `CIRCUITPY_WIFI_PASSWORD`. Once these are defined, CircuitPython will automatically connect to the network and start the webserver used for the workflow. The webserver -is on port 80. It also enables MDNS. +is on port 80 unless overridden by `CIRCUITPY_WEB_API_PORT`. It also enables MDNS. Here is an example `/.env`: @@ -83,6 +83,8 @@ CIRCUITPY_WIFI_PASSWORD='secretpassword' # To enable modifying files from the web. Change this too! CIRCUITPY_WEB_API_PASSWORD='passw0rd' + +CIRCUITPY_WEB_API_PORT=80 ``` MDNS is used to resolve [`circuitpython.local`](http://circuitpython.local) to a device specific diff --git a/ports/espressif/common-hal/mdns/Server.c b/ports/espressif/common-hal/mdns/Server.c index c6c2a748a9..d657a84eb7 100644 --- a/ports/espressif/common-hal/mdns/Server.c +++ b/ports/espressif/common-hal/mdns/Server.c @@ -204,5 +204,9 @@ mp_obj_t common_hal_mdns_server_find(mdns_server_obj_t *self, const char *servic } void common_hal_mdns_server_advertise_service(mdns_server_obj_t *self, const char *service_type, const char *protocol, mp_int_t port) { - mdns_service_add(NULL, service_type, protocol, port, NULL, 0); + if (mdns_service_exists(service_type, protocol, NULL)) { + mdns_service_port_set(service_type, protocol, port); + } else { + mdns_service_add(NULL, service_type, protocol, port, NULL, 0); + } } diff --git a/shared-bindings/mdns/Server.c b/shared-bindings/mdns/Server.c index 97574ff0e2..e11c1c4730 100644 --- a/shared-bindings/mdns/Server.c +++ b/shared-bindings/mdns/Server.c @@ -161,6 +161,9 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_KW(mdns_server_find_obj, 1, _mdns_server_find); //| def advertise_service(self, *, service_type: str, protocol: str, port: int) -> None: //| """Respond to queries for the given service with the given port. //| +//| service_type and protocol can only occur on one port. Any call after the first will +//| update the entry's port. +//| //| :param str service_type: The service type such as "_http" //| :param str protocol: The service protocol such as "_tcp" //| :param int port: The port used by the service""" diff --git a/supervisor/shared/web_workflow/static/welcome.js b/supervisor/shared/web_workflow/static/welcome.js index 79efb7e9a8..d53950d37c 100644 --- a/supervisor/shared/web_workflow/static/welcome.js +++ b/supervisor/shared/web_workflow/static/welcome.js @@ -44,7 +44,7 @@ async function find_devices() { li.appendChild(a); var port = ""; if (device.port != 80) { - port = ":" + version_info.port; + port = ":" + device.port; } var server; if (mdns_works) { diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 81730c92d0..c586b9e24b 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -98,6 +98,7 @@ typedef struct { static wifi_radio_error_t wifi_status = WIFI_RADIO_ERROR_NONE; static mdns_server_obj_t mdns; +static uint32_t web_api_port = 80; static socketpool_socketpool_obj_t pool; static socketpool_socket_obj_t listening; @@ -189,6 +190,9 @@ void supervisor_web_workflow_status(void) { } mp_printf(&mp_plat_print, "%s", _our_ip_encoded); + if (web_api_port != 80) { + mp_printf(&mp_plat_print, ":%d", web_api_port); + } // TODO: Use these unicode to show signal strength: ▂▄▆█ } } else { @@ -199,11 +203,6 @@ void supervisor_web_workflow_status(void) { void supervisor_start_web_workflow(void) { #if CIRCUITPY_WEB_WORKFLOW && CIRCUITPY_WIFI - if (common_hal_wifi_radio_get_enabled(&common_hal_wifi_radio_obj) && - wifi_radio_get_ipv4_address(&common_hal_wifi_radio_obj) != 0) { - // Already started. - return; - } char ssid[33]; char password[64]; @@ -218,8 +217,10 @@ void supervisor_start_web_workflow(void) { password_len <= 0 || (size_t)password_len >= sizeof(password)) { return; } - common_hal_wifi_init(false); - common_hal_wifi_radio_set_enabled(&common_hal_wifi_radio_obj, true); + if (!common_hal_wifi_radio_get_enabled(&common_hal_wifi_radio_obj)) { + common_hal_wifi_init(false); + common_hal_wifi_radio_set_enabled(&common_hal_wifi_radio_obj, true); + } // TODO: Do our own scan so that we can find the channel we want before calling connect. // Otherwise, connect will do a full slow scan to pick the best AP. @@ -227,6 +228,9 @@ void supervisor_start_web_workflow(void) { // NUL terminate the strings because dotenv doesn't. ssid[ssid_len] = '\0'; password[password_len] = '\0'; + // We can all connect again because it will return early if we're already connected to the + // network. If we are connected to a different network, then it will disconnect before + // attempting to connect to the given network. wifi_status = common_hal_wifi_radio_connect( &common_hal_wifi_radio_obj, (uint8_t *)ssid, ssid_len, (uint8_t *)password, password_len, 0, 0.1, NULL, 0); @@ -236,21 +240,46 @@ void supervisor_start_web_workflow(void) { return; } - mdns_server_construct(&mdns, true); - common_hal_mdns_server_set_instance_name(&mdns, MICROPY_HW_BOARD_NAME); - common_hal_mdns_server_advertise_service(&mdns, "_circuitpython", "_tcp", 80); + char port_encoded[6]; + size_t port_len = 0; + size_t new_port = web_api_port; + #if CIRCUITPY_DOTENV + port_len = dotenv_get_key("/.env", "CIRCUITPY_WEB_API_PORT", port_encoded, sizeof(port_encoded) - 1); + #endif + if (0 < port_len && port_len < sizeof(port_encoded)) { + new_port = strtoul(port_encoded, NULL, 10); + } - pool.base.type = &socketpool_socketpool_type; - common_hal_socketpool_socketpool_construct(&pool, &common_hal_wifi_radio_obj); + bool first_start = mdns.base.type != &mdns_server_type; + bool port_changed = new_port != web_api_port; - ESP_LOGI(TAG, "Starting web workflow"); - listening.base.type = &socketpool_socket_type; - socketpool_socket(&pool, SOCKETPOOL_AF_INET, SOCKETPOOL_SOCK_STREAM, &listening); - common_hal_socketpool_socket_settimeout(&listening, 0); - // Bind to any ip. - // TODO: Make this port .env configurable. - common_hal_socketpool_socket_bind(&listening, "", 0, 80); - common_hal_socketpool_socket_listen(&listening, 1); + if (first_start) { + ESP_LOGI(TAG, "Starting web workflow"); + mdns_server_construct(&mdns, true); + mdns.base.type = &mdns_server_type; + common_hal_mdns_server_set_instance_name(&mdns, MICROPY_HW_BOARD_NAME); + pool.base.type = &socketpool_socketpool_type; + common_hal_socketpool_socketpool_construct(&pool, &common_hal_wifi_radio_obj); + + listening.base.type = &socketpool_socket_type; + active.base.type = &socketpool_socket_type; + active.num = -1; + active.connected = false; + + websocket_init(); + } + if (port_changed) { + common_hal_socketpool_socket_close(&listening); + } + if (first_start || port_changed) { + web_api_port = new_port; + common_hal_mdns_server_advertise_service(&mdns, "_circuitpython", "_tcp", web_api_port); + socketpool_socket(&pool, SOCKETPOOL_AF_INET, SOCKETPOOL_SOCK_STREAM, &listening); + common_hal_socketpool_socket_settimeout(&listening, 0); + // Bind to any ip. + common_hal_socketpool_socket_bind(&listening, "", 0, web_api_port); + common_hal_socketpool_socket_listen(&listening, 1); + } mp_int_t api_password_len = dotenv_get_key("/.env", "CIRCUITPY_WEB_API_PASSWORD", _api_password + 1, sizeof(_api_password) - 2); if (api_password_len > 0) { @@ -259,12 +288,6 @@ void supervisor_start_web_workflow(void) { _base64_in_place(_api_password, api_password_len + 1, sizeof(_api_password)); } - active.base.type = &socketpool_socket_type; - active.num = -1; - active.connected = false; - - websocket_init(); - // TODO: // GET /cp/serial.txt // - Most recent 1k of serial output. @@ -529,7 +552,13 @@ static void _reply_redirect(socketpool_socket_obj_t *socket, _request *request, _send_str(socket, "http"); } - _send_strs(socket, "://", hostname, ".local", path, "\r\n", NULL); + _send_strs(socket, "://", hostname, ".local", NULL); + if (web_api_port != 80) { + char encoded_port[6]; + snprintf(encoded_port, sizeof(encoded_port), "%d", web_api_port); + _send_strs(socket, ":", encoded_port, NULL); + } + _send_strs(socket, path, "\r\n", NULL); _cors_header(socket, request); _send_str(socket, "\r\n"); } @@ -647,7 +676,7 @@ static void _reply_with_devices_json(socketpool_socket_obj_t *socket, _request * } const char *hostname = common_hal_mdns_remoteservice_get_hostname(&found_devices[i]); const char *instance_name = common_hal_mdns_remoteservice_get_instance_name(&found_devices[i]); - char port_encoded[4]; + char port_encoded[6]; int port = common_hal_mdns_remoteservice_get_port(&found_devices[i]); snprintf(port_encoded, sizeof(port_encoded), "%d", port); char ip_encoded[4 * 4]; @@ -675,6 +704,8 @@ static void _reply_with_version_json(socketpool_socket_obj_t *socket, _request * char encoded_creation_id[11]; // 2 ** 32 is 10 decimal digits plus one for \0 snprintf(encoded_creation_id, sizeof(encoded_creation_id), "%u", CIRCUITPY_CREATION_ID); const char *hostname = common_hal_mdns_server_get_hostname(&mdns); + char encoded_port[6]; + snprintf(encoded_port, sizeof(encoded_port), "%d", web_api_port); _send_chunks(socket, "{\"web_api_version\": 1, ", "\"version\": \"", MICROPY_GIT_TAG, "\", ", @@ -685,7 +716,7 @@ static void _reply_with_version_json(socketpool_socket_obj_t *socket, _request * "\"creator_id\": ", encoded_creator_id, ", ", "\"creation_id\": ", encoded_creation_id, ", ", "\"hostname\": \"", hostname, "\", ", - "\"port\": 80, ", + "\"port\": ", encoded_port, ", ", "\"ip\": \"", _our_ip_encoded, "\"}", NULL); // Empty chunk signals the end of the response. @@ -1173,7 +1204,9 @@ static void _process_request(socketpool_socket_obj_t *socket, _request *request) request->authenticated = memcmp(request->header_value, prefix, strlen(prefix)) == 0 && strcmp(_api_password, request->header_value + strlen(prefix)) == 0; } else if (strcmp(request->header_key, "Host") == 0) { - request->redirect = strcmp(request->header_value, "circuitpython.local") == 0; + // Do a prefix check so that port is ignored. + const char *cp_local = "circuitpython.local"; + request->redirect = memcmp(request->header_value, cp_local, strlen(cp_local)) == 0; } else if (strcmp(request->header_key, "Content-Length") == 0) { request->content_length = strtoul(request->header_value, NULL, 10); } else if (strcmp(request->header_key, "Expect") == 0) { From 584e27139e3d7e1e97ace249aba96c7ab9453123 Mon Sep 17 00:00:00 2001 From: foamyguy Date: Fri, 15 Jul 2022 19:49:03 -0500 Subject: [PATCH 03/44] add back /edit/ handler and specify ES6 quote chars for jsmin --- supervisor/shared/web_workflow/static/edit.js | 2 -- supervisor/shared/web_workflow/web_workflow.c | 10 ++++++++++ tools/gen_web_workflow_static.py | 4 +++- 3 files changed, 13 insertions(+), 3 deletions(-) diff --git a/supervisor/shared/web_workflow/static/edit.js b/supervisor/shared/web_workflow/static/edit.js index a3f8a7d5a9..11d569abe2 100644 --- a/supervisor/shared/web_workflow/static/edit.js +++ b/supervisor/shared/web_workflow/static/edit.js @@ -40,8 +40,6 @@ require(["ace/ace", "ace/ext/settings_menu"], function (ace) { }, readOnly: true }]); - - }); let filename = location.hash.substring(1); diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 5eeb49a570..c7f30f8bf6 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -1013,6 +1013,16 @@ static bool _reply(socketpool_socket_obj_t *socket, _request *request) { } } } + } else if (strcmp(request->path, "/edit/") == 0) { + if (!request->authenticated) { + if (_api_password[0] != '\0') { + _reply_unauthorized(socket, request); + } else { + _reply_forbidden(socket, request); + } + } else { + _REPLY_STATIC(socket, request, edit_html); + } } else if (memcmp(request->path, "/cp/", 4) == 0) { const char *path = request->path + 3; if (strcmp(request->method, "GET") != 0) { diff --git a/tools/gen_web_workflow_static.py b/tools/gen_web_workflow_static.py index b8c5baf619..172a80dac0 100644 --- a/tools/gen_web_workflow_static.py +++ b/tools/gen_web_workflow_static.py @@ -29,7 +29,9 @@ for f in args.files: if f.name.endswith(".html"): uncompressed = minify_html.minify(uncompressed.decode("utf-8")).encode("utf-8") elif f.name.endswith(".js"): - uncompressed = jsmin.jsmin(uncompressed.decode("utf-8")).encode("utf-8") + uncompressed = jsmin.jsmin(uncompressed.decode("utf-8"), quote_chars="'\"`").encode( + "utf-8" + ) compressed = gzip.compress(uncompressed) clen = len(compressed) compressed = ", ".join([hex(x) for x in compressed]) From 541e448100bd9c892a55b43b377cdf083a15cfd2 Mon Sep 17 00:00:00 2001 From: foamyguy Date: Fri, 15 Jul 2022 19:56:29 -0500 Subject: [PATCH 04/44] set the href for edit links in the directory list --- supervisor/shared/web_workflow/static/directory.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/supervisor/shared/web_workflow/static/directory.js b/supervisor/shared/web_workflow/static/directory.js index b2b76648c2..9dbe8384d6 100644 --- a/supervisor/shared/web_workflow/static/directory.js +++ b/supervisor/shared/web_workflow/static/directory.js @@ -91,6 +91,9 @@ async function refresh_list() { delete_button.disabled = !editable; delete_button.onclick = del; + let edit_url = new URL("/edit/#" + f.name, url_base); + let edit_link = clone.querySelector(".edit_link"); + edit_link.href = edit_url new_children.push(clone); } From 66d5fa9a55e7aa3763037b8ceb45dc33c7cb29bd Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Mon, 25 Jul 2022 16:19:27 -0700 Subject: [PATCH 05/44] Save space on Feather S3 4mb with -Os --- .../adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk b/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk index 39804bad26..1b4c4015f5 100644 --- a/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk +++ b/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk @@ -16,4 +16,4 @@ CIRCUITPY_ESP_FLASH_MODE = qio CIRCUITPY_ESP_FLASH_FREQ = 40m CIRCUITPY_ESP_FLASH_SIZE = 4MB -CIRCUITPY_PS2IO = 0 +OPTIMIZATION_FLAGS = -Os From f4927dd2d6e1503bd86415ed8187d250f313fdbe Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Mon, 25 Jul 2022 16:58:54 -0700 Subject: [PATCH 06/44] Use mp_printf instead of snprintf --- supervisor/shared/web_workflow/web_workflow.c | 99 +++++++++---------- 1 file changed, 49 insertions(+), 50 deletions(-) diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 055fdcbd29..e641bb8605 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -306,6 +306,10 @@ static void _send_raw(socketpool_socket_obj_t *socket, const uint8_t *buf, int l } } +STATIC void _print_raw(void *env, const char *str, size_t len) { + _send_raw((socketpool_socket_obj_t *)env, (const uint8_t *)str, (size_t)len); +} + static void _send_str(socketpool_socket_obj_t *socket, const char *str) { _send_raw(socket, (const uint8_t *)str, strlen(str)); } @@ -324,14 +328,19 @@ static void _send_strs(socketpool_socket_obj_t *socket, ...) { } static void _send_chunk(socketpool_socket_obj_t *socket, const char *chunk) { - char encoded_len[sizeof(size_t) * 2 + 1]; - int len = snprintf(encoded_len, sizeof(encoded_len), "%X", strlen(chunk)); - _send_raw(socket, (const uint8_t *)encoded_len, len); - _send_raw(socket, (const uint8_t *)"\r\n", 2); + mp_print_t _socket_print = {socket, _print_raw}; + mp_printf(&_socket_print, "%X\r\n", strlen(chunk)); _send_raw(socket, (const uint8_t *)chunk, strlen(chunk)); _send_raw(socket, (const uint8_t *)"\r\n", 2); } +STATIC void _print_chunk(void *env, const char *str, size_t len) { + mp_print_t _socket_print = {socket, _print_raw}; + mp_printf(&_socket_print, "%X\r\n", len); + _send_raw((socketpool_socket_obj_t *)env, (const uint8_t *)str, len); + _send_raw((socketpool_socket_obj_t *)env, (const uint8_t *)"\r\n", 2); +} + // A bit of a misnomer because it sends all arguments as one chunk. // The last argument must be NULL! Otherwise, it won't stop. static void _send_chunks(socketpool_socket_obj_t *socket, ...) { @@ -349,9 +358,9 @@ static void _send_chunks(socketpool_socket_obj_t *socket, ...) { } va_end(strs_to_count); - char encoded_len[sizeof(size_t) * 2 + 1]; - snprintf(encoded_len, sizeof(encoded_len), "%X", chunk_len); - _send_strs(socket, encoded_len, "\r\n", NULL); + + mp_print_t _socket_print = {socket, _print_raw}; + mp_printf(&_socket_print, "%X\r\n", chunk_len); str = va_arg(strs_to_send, const char *); while (str != NULL) { @@ -556,9 +565,8 @@ static void _reply_redirect(socketpool_socket_obj_t *socket, _request *request, _send_strs(socket, "://", hostname, ".local", NULL); if (web_api_port != 80) { - char encoded_port[6]; - snprintf(encoded_port, sizeof(encoded_port), "%d", web_api_port); - _send_strs(socket, ":", encoded_port, NULL); + mp_print_t _socket_print = {socket, _print_raw}; + mp_printf(&_socket_print, ":%d", web_api_port); } _send_strs(socket, path, "\r\n", NULL); _cors_header(socket, request); @@ -569,6 +577,7 @@ static void _reply_directory_json(socketpool_socket_obj_t *socket, _request *req socketpool_socket_send(socket, (const uint8_t *)OK_JSON, strlen(OK_JSON)); _cors_header(socket, request); _send_str(socket, "\r\n"); + mp_print_t _socket_print = {socket, _print_chunk}; _send_chunk(socket, "["); bool first = true; @@ -589,7 +598,7 @@ static void _reply_directory_json(socketpool_socket_obj_t *socket, _request *req } // We use nanoseconds past Jan 1, 1970 for consistency with BLE API and // LittleFS. - _send_chunk(socket, ", \"modified_ns\": "); + _send_chunk(socket, ", "); uint64_t truncated_time = timeutils_mktime(1980 + (file_info.fdate >> 9), (file_info.fdate >> 5) & 0xf, @@ -598,15 +607,13 @@ static void _reply_directory_json(socketpool_socket_obj_t *socket, _request *req (file_info.ftime >> 5) & 0x1f, (file_info.ftime & 0x1f) * 2) * 1000000000ULL; - char encoded_number[32]; - snprintf(encoded_number, sizeof(encoded_number), "%lld", truncated_time); - _send_chunks(socket, encoded_number, ", \"file_size\": ", NULL); + mp_printf(&_socket_print, "\"modified_ns\": %lld, ", truncated_time); size_t file_size = 0; if ((file_info.fattrib & AM_DIR) == 0) { file_size = file_info.fsize; } - snprintf(encoded_number, sizeof(encoded_number), "%d", file_size); - _send_chunks(socket, encoded_number, "}", NULL); + mp_printf(&_socket_print, "\"file_size\": %d }", file_size); + first = false; res = f_readdir(dir, &file_info); } @@ -619,9 +626,9 @@ static void _reply_with_file(socketpool_socket_obj_t *socket, _request *request, char encoded_len[10]; snprintf(encoded_len, sizeof(encoded_len), "%d", total_length); - _send_strs(socket, - "HTTP/1.1 200 OK\r\n", - "Content-Length: ", encoded_len, "\r\n", NULL); + _send_str(socket, "HTTP/1.1 200 OK\r\n"); + mp_print_t _socket_print = {socket, _print_raw}; + mp_printf(&_socket_print, "Content-Length: %d\r\n", total_length); // TODO: Make this a table to save space. if (_endswith(filename, ".txt") || _endswith(filename, ".py")) { _send_str(socket, "Content-Type: text/plain\r\n"); @@ -669,27 +676,23 @@ static void _reply_with_devices_json(socketpool_socket_obj_t *socket, _request * socketpool_socket_send(socket, (const uint8_t *)OK_JSON, strlen(OK_JSON)); _cors_header(socket, request); _send_str(socket, "\r\n"); - char total_encoded[4]; - snprintf(total_encoded, sizeof(total_encoded), "%d", total_results); - _send_chunks(socket, "{\"total\": ", total_encoded, ", \"devices\": [", NULL); + mp_print_t _socket_print = {socket, _print_chunk}; + + mp_printf(&_socket_print, "{\"total\": %d, \"devices\": [", total_results); for (size_t i = 0; i < count; i++) { if (i > 0) { _send_chunk(socket, ","); } const char *hostname = common_hal_mdns_remoteservice_get_hostname(&found_devices[i]); const char *instance_name = common_hal_mdns_remoteservice_get_instance_name(&found_devices[i]); - char port_encoded[6]; int port = common_hal_mdns_remoteservice_get_port(&found_devices[i]); - snprintf(port_encoded, sizeof(port_encoded), "%d", port); - char ip_encoded[4 * 4]; uint32_t ipv4_address = mdns_remoteservice_get_ipv4_address(&found_devices[i]); uint8_t *octets = (uint8_t *)&ipv4_address; - snprintf(ip_encoded, sizeof(ip_encoded), "%d.%d.%d.%d", octets[0], octets[1], octets[2], octets[3]); - _send_chunks(socket, - "{\"hostname\": \"", hostname, "\", ", - "\"instance_name\": \"", instance_name, "\", ", - "\"port\": ", port_encoded, ", ", - "\"ip\": \"", ip_encoded, "\"}", NULL); + mp_printf(&_socket_print, + "{\"hostname\": \"%s\", " + "\"instance_name\": \"%s\", " + "\"port\": %d, " + "\"ip\": \"%d.%d.%d.%d\"}", hostname, instance_name, port, octets[0], octets[1], octets[2], octets[3]); common_hal_mdns_remoteservice_deinit(&found_devices[i]); } _send_chunk(socket, "]}"); @@ -701,26 +704,22 @@ static void _reply_with_version_json(socketpool_socket_obj_t *socket, _request * _send_str(socket, OK_JSON); _cors_header(socket, request); _send_str(socket, "\r\n"); - char encoded_creator_id[11]; // 2 ** 32 is 10 decimal digits plus one for \0 - snprintf(encoded_creator_id, sizeof(encoded_creator_id), "%u", CIRCUITPY_CREATOR_ID); - char encoded_creation_id[11]; // 2 ** 32 is 10 decimal digits plus one for \0 - snprintf(encoded_creation_id, sizeof(encoded_creation_id), "%u", CIRCUITPY_CREATION_ID); + mp_print_t _socket_print = {socket, _print_chunk}; + const char *hostname = common_hal_mdns_server_get_hostname(&mdns); - char encoded_port[6]; - snprintf(encoded_port, sizeof(encoded_port), "%d", web_api_port); - _send_chunks(socket, - "{\"web_api_version\": 1, ", - "\"version\": \"", MICROPY_GIT_TAG, "\", ", - "\"build_date\": \"", MICROPY_BUILD_DATE, "\", ", - "\"board_name\": \"", MICROPY_HW_BOARD_NAME, "\", ", - "\"mcu_name\": \"", MICROPY_HW_MCU_NAME, "\", ", - "\"board_id\": \"", CIRCUITPY_BOARD_ID, "\", ", - "\"creator_id\": ", encoded_creator_id, ", ", - "\"creation_id\": ", encoded_creation_id, ", ", - "\"hostname\": \"", hostname, "\", ", - "\"port\": ", encoded_port, ", ", - "\"ip\": \"", _our_ip_encoded, - "\"}", NULL); + // Note: this leverages the fact that C concats consecutive string literals together. + mp_printf(&_socket_print, + "{\"web_api_version\": 1, " + "\"version\": \"" MICROPY_GIT_TAG "\", " + "\"build_date\": \"" MICROPY_BUILD_DATE "\", " + "\"board_name\": \"" MICROPY_HW_BOARD_NAME "\", " + "\"mcu_name\": \"" MICROPY_HW_MCU_NAME "\", " + "\"board_id\": \"" CIRCUITPY_BOARD_ID "\", " + "\"creator_id\": %u, " + "\"creation_id\": %u, " + "\"hostname\": \"%s\", " + "\"port\": %d, " + "\"ip\": \"%s\"}", CIRCUITPY_CREATOR_ID, CIRCUITPY_CREATION_ID, hostname, web_api_port, _our_ip_encoded); // Empty chunk signals the end of the response. _send_chunk(socket, ""); } From a33985a73ff60968314ca7d0abed9599c83d6c7f Mon Sep 17 00:00:00 2001 From: foamyguy Date: Mon, 25 Jul 2022 19:15:43 -0500 Subject: [PATCH 07/44] change to basic diff --git a/supervisor/shared/web_workflow/static/edit.js b/supervisor/shared/web_workflow/static/edit.js index 11d569abe2..5d9e4fdfe3 100644 --- a/supervisor/shared/web_workflow/static/edit.js +++ b/supervisor/shared/web_workflow/static/edit.js @@ -1,50 +1,6 @@ -let editor; -require(["ace/ace", "ace/ext/settings_menu"], function (ace) { - editor = ace.edit("code_textarea"); - ace.config.set('basePath', 'https://cdnjs.cloudflare.com/ajax/libs/ace/1.6.0/'); - console.log("after create editor"); - console.log(editor); - - editor.session.setMode("ace/mode/python"); - ace.require('ace/ext/settings_menu').init(editor); - editor.commands.addCommands([{ - name: "showSettingsMenu", - bindKey: {win: "Ctrl-e", mac: "Ctrl-e"}, - exec: function (editor) { - console.log("ctrl-e") - editor.showSettingsMenu(); - }, - readOnly: true - }, { - name: "infoDocsSearch", - bindKey: {win: "Ctrl-i", mac: "Ctrl-i"}, - exec: function (editor) { - window.open(`https://docs.circuitpython.org/en/latest/search.html?q=${editor.getSelectedText()}`, '_blank'); - }, - readOnly: true - },{ - name: 'Save', - bindKey: {win: 'Ctrl-S', mac: 'Command-S'}, - exec: function (editor) { - console.log("ctrl-s save"); - save(); - - } - },{ - name: "replaceCtrlR", - bindKey: {win: "Ctrl-r", mac: "Ctrl-r"}, - exec: function (editor_arg) { - console.log("override ctrl r"); - editor.execCommand('replace'); - console.log(editor); - }, - readOnly: true - }]); -}); - +let $editor = document.querySelector("#code_textarea"); let filename = location.hash.substring(1); let $output_text = document.querySelector("#output_text"); -/*let $code_text = document.querySelector("#code_textarea");*/ fetch(`/fs/${filename}`) .then(function (response) { @@ -52,14 +8,14 @@ fetch(`/fs/${filename}`) return response.status === 200 ? response.text() : ""; }) .then(function (data) { - editor.setValue(data, -1) + $editor.value = data; }); function save() { $output_text.innerText = "Saving..." const requestOptions = { method: 'PUT', - body: editor.getValue() + body: $editor.value }; fetch(`/fs/${filename}`, requestOptions) .then(function (response) { @@ -74,15 +30,4 @@ function save() { document.querySelector("#save_btn").onclick = function () { console.log("Click Save!"); save(); -} -document.querySelector("#docs_btn").onclick = function () { - window.open(`https://docs.circuitpython.org/en/latest/search.html?q=${editor.getSelectedText()}`, '_blank'); -} - -document.querySelector("#undo_btn").onclick = function () { - editor.undo(); -} - -document.querySelector("#redo_btn").onclick = function () { - editor.redo(); -} +} \ No newline at end of file From 0ef6871a931c1d7feec7d3bfe0b26175e158ba4e Mon Sep 17 00:00:00 2001 From: foamyguy Date: Mon, 25 Jul 2022 19:30:44 -0500 Subject: [PATCH 08/44] save with ctrl-s --- supervisor/shared/web_workflow/static/edit.js | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/supervisor/shared/web_workflow/static/edit.js b/supervisor/shared/web_workflow/static/edit.js index 5d9e4fdfe3..d73a9db94c 100644 --- a/supervisor/shared/web_workflow/static/edit.js +++ b/supervisor/shared/web_workflow/static/edit.js @@ -30,4 +30,18 @@ function save() { document.querySelector("#save_btn").onclick = function () { console.log("Click Save!"); save(); +} + +let isCtrl = false; +document.onkeyup=function(e){ + if(e.keyCode === 17) isCtrl=false; +} + +document.onkeydown=function(e){ + if(e.keyCode === 17) isCtrl=true; + if(e.keyCode === 83 && isCtrl === true) { + //ctrl-s pressed + save(); + return false; + } } \ No newline at end of file From 4c4a7072b0644f7cc0f4ee1ea4be9d4eb12c8ab7 Mon Sep 17 00:00:00 2001 From: Jeff Epler Date: Sun, 24 Jul 2022 14:12:06 -0500 Subject: [PATCH 09/44] readline: make ctrl-l clear screen & redraw line .. similar to how standard Python does it. The specific escape sequence is chosen for compatibility with the built-in `terminalio.Terminal`. Closes: #6635 --- shared/readline/readline.c | 11 +++++++++++ shared/readline/readline.h | 1 + 2 files changed, 12 insertions(+) diff --git a/shared/readline/readline.c b/shared/readline/readline.c index 23183342a7..908aec8426 100644 --- a/shared/readline/readline.c +++ b/shared/readline/readline.c @@ -177,6 +177,17 @@ int readline_process_char(int c) { vstr_cut_tail_bytes(rl.line, rl.line->len - rl.cursor_pos); // set redraw parameters redraw_from_cursor = true; + #endif + } else if (c == CHAR_CTRL_L) { + // CTRL-L is clear screen / redraw. This specific sequence is used + // (instead of a slightly more minimal sequence) for compatibility + // with the built-in Terminal class + mp_hal_stdout_tx_str("I'm a little teapot\x1b[;H\x1b[2J"); + mp_hal_stdout_tx_str(rl.prompt); + mp_hal_stdout_tx_strn(rl.line->buf + rl.orig_line_len, rl.cursor_pos - rl.orig_line_len); + // set redraw parameters + redraw_from_cursor = true; + #if MICROPY_REPL_EMACS_KEYS } else if (c == CHAR_CTRL_N) { // CTRL-N is go to next line in history goto down_arrow_key; diff --git a/shared/readline/readline.h b/shared/readline/readline.h index 4658ee19e8..9af19b181e 100644 --- a/shared/readline/readline.h +++ b/shared/readline/readline.h @@ -35,6 +35,7 @@ #define CHAR_CTRL_E (5) #define CHAR_CTRL_F (6) #define CHAR_CTRL_K (11) +#define CHAR_CTRL_L (12) #define CHAR_CTRL_N (14) #define CHAR_CTRL_P (16) #define CHAR_CTRL_U (21) From 1a7082ff1d869e31908d885041d173f848b53927 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Tue, 26 Jul 2022 08:37:33 -0700 Subject: [PATCH 10/44] Add newline for pre-commit --- supervisor/shared/web_workflow/static/edit.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/supervisor/shared/web_workflow/static/edit.js b/supervisor/shared/web_workflow/static/edit.js index d73a9db94c..60dd8b1073 100644 --- a/supervisor/shared/web_workflow/static/edit.js +++ b/supervisor/shared/web_workflow/static/edit.js @@ -44,4 +44,4 @@ document.onkeydown=function(e){ save(); return false; } -} \ No newline at end of file +} From 920c68e9d5965a59b96ab3d91a895e5801f99f86 Mon Sep 17 00:00:00 2001 From: Jeff Epler Date: Tue, 26 Jul 2022 11:39:18 -0500 Subject: [PATCH 11/44] Update shared/readline/readline.c Co-authored-by: Scott Shawcroft --- shared/readline/readline.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/shared/readline/readline.c b/shared/readline/readline.c index 908aec8426..d8602a9e28 100644 --- a/shared/readline/readline.c +++ b/shared/readline/readline.c @@ -182,7 +182,7 @@ int readline_process_char(int c) { // CTRL-L is clear screen / redraw. This specific sequence is used // (instead of a slightly more minimal sequence) for compatibility // with the built-in Terminal class - mp_hal_stdout_tx_str("I'm a little teapot\x1b[;H\x1b[2J"); + mp_hal_stdout_tx_str("\x1b[;H\x1b[2J"); mp_hal_stdout_tx_str(rl.prompt); mp_hal_stdout_tx_strn(rl.line->buf + rl.orig_line_len, rl.cursor_pos - rl.orig_line_len); // set redraw parameters From f9cc4ec61b31b0210c9c42ce570a70daa983705a Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Tue, 26 Jul 2022 11:51:10 -0700 Subject: [PATCH 12/44] Fix print chunk --- supervisor/shared/web_workflow/web_workflow.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index e641bb8605..5225cfe13e 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -335,7 +335,7 @@ static void _send_chunk(socketpool_socket_obj_t *socket, const char *chunk) { } STATIC void _print_chunk(void *env, const char *str, size_t len) { - mp_print_t _socket_print = {socket, _print_raw}; + mp_print_t _socket_print = {env, _print_raw}; mp_printf(&_socket_print, "%X\r\n", len); _send_raw((socketpool_socket_obj_t *)env, (const uint8_t *)str, len); _send_raw((socketpool_socket_obj_t *)env, (const uint8_t *)"\r\n", 2); From 0a6f9112b166b79776d5f0b5b3391cfcac8afd9f Mon Sep 17 00:00:00 2001 From: Dan Halbert Date: Wed, 27 Jul 2022 14:50:57 -0400 Subject: [PATCH 13/44] update mpy-cross macOS build to macos 11; make macos mpy-cross names consistent --- .github/workflows/build.yml | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 8dc31a3ff6..b767a92376 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -143,7 +143,7 @@ jobs: mpy-cross-mac: - runs-on: macos-10.15 + runs-on: macos-11 steps: - name: Dump GitHub context env: @@ -176,7 +176,7 @@ jobs: run: make -C mpy-cross -j2 - uses: actions/upload-artifact@v2 with: - name: mpy-cross-macos-catalina + name: mpy-cross-macos-11-x64 path: mpy-cross/mpy-cross - name: Select SDK for M1 build run: sudo xcode-select -switch /Applications/Xcode_12.3.app @@ -184,19 +184,19 @@ jobs: run: make -C mpy-cross -j2 -f Makefile.m1 V=2 - uses: actions/upload-artifact@v2 with: - name: mpy-cross-macos-bigsur-arm64 + name: mpy-cross-macos-11-arm64 path: mpy-cross/mpy-cross-arm64 - name: Make universal binary - run: lipo -create -output mpy-cross-macos-universal mpy-cross/mpy-cross mpy-cross/mpy-cross-arm64 + run: lipo -create -output mpy-cross-macos-11-universal mpy-cross/mpy-cross mpy-cross/mpy-cross-arm64 - uses: actions/upload-artifact@v2 with: - name: mpy-cross-macos-universal - path: mpy-cross-macos-universal + name: mpy-cross-macos-11-universal + path: mpy-cross-macos-11-universal - name: Upload mpy-cross build to S3 run: | - [ -z "$AWS_ACCESS_KEY_ID" ] || aws s3 cp mpy-cross-macos-universal s3://adafruit-circuit-python/bin/mpy-cross/mpy-cross-macos-universal-${{ env.CP_VERSION }} --no-progress --region us-east-1 - [ -z "$AWS_ACCESS_KEY_ID" ] || aws s3 cp mpy-cross/mpy-cross-arm64 s3://adafruit-circuit-python/bin/mpy-cross/mpy-cross-macos-bigsur-${{ env.CP_VERSION }}-arm64 --no-progress --region us-east-1 - [ -z "$AWS_ACCESS_KEY_ID" ] || aws s3 cp mpy-cross/mpy-cross s3://adafruit-circuit-python/bin/mpy-cross/mpy-cross-macos-catalina-${{ env.CP_VERSION }} --no-progress --region us-east-1 + [ -z "$AWS_ACCESS_KEY_ID" ] || aws s3 cp mpy-cross-macos-universal s3://adafruit-circuit-python/bin/mpy-cross/mpy-cross-macos-11-${{ env.CP_VERSION }}-universal --no-progress --region us-east-1 + [ -z "$AWS_ACCESS_KEY_ID" ] || aws s3 cp mpy-cross/mpy-cross-arm64 s3://adafruit-circuit-python/bin/mpy-cross/mpy-cross-macos-11-${{ env.CP_VERSION }}-arm64 --no-progress --region us-east-1 + [ -z "$AWS_ACCESS_KEY_ID" ] || aws s3 cp mpy-cross/mpy-cross s3://adafruit-circuit-python/bin/mpy-cross/mpy-cross-macos-11-${{ env.CP_VERSION }}-x64 --no-progress --region us-east-1 env: AWS_PAGER: '' AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }} From bea955222ab200027b6b2fcdf9164e9c8fc4a3d1 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Wed, 27 Jul 2022 12:15:13 -0700 Subject: [PATCH 14/44] Improve USB to Serial/JTAG TX It had a tight 5ms timeout before that caused some characters to drop. Now the wait is longer and reset after a successful transmit. This follows what MicroPython does. Fixes #6220 --- ports/espressif/supervisor/usb_serial_jtag.c | 27 +++++++++++++------- 1 file changed, 18 insertions(+), 9 deletions(-) diff --git a/ports/espressif/supervisor/usb_serial_jtag.c b/ports/espressif/supervisor/usb_serial_jtag.c index 064d7d668c..33f0ec3a8e 100644 --- a/ports/espressif/supervisor/usb_serial_jtag.c +++ b/ports/espressif/supervisor/usb_serial_jtag.c @@ -98,14 +98,23 @@ bool usb_serial_jtag_bytes_available(void) { } void usb_serial_jtag_write(const char *text, uint32_t length) { - if (USB_SERIAL_JTAG.fram_num.sof_frame_index > 0) { - size_t total_written = 0; - uint32_t start_time = supervisor_ticks_ms32(); - // Time out after 5 milliseconds in case usb isn't actually reading CDC. - while (total_written < length && start_time - supervisor_ticks_ms32() < 5) { - total_written += usb_serial_jtag_ll_write_txfifo((const uint8_t *)(text + total_written), length - total_written); - RUN_BACKGROUND_TASKS; - } - usb_serial_jtag_ll_txfifo_flush(); + if (!usb_serial_jtag_connected()) { + return; } + size_t total_written = 0; + while (total_written < length) { + uint32_t start_time = supervisor_ticks_ms32(); + // Wait until we can write to the FIFO again. If it takes too long, then + // assume we're disconnected. + while (!usb_serial_jtag_ll_txfifo_writable()) { + uint32_t now = supervisor_ticks_ms32(); + if (now - start_time > 200) { + connected = false; + return; + } + } + total_written += usb_serial_jtag_ll_write_txfifo((const uint8_t *)(text + total_written), length - total_written); + RUN_BACKGROUND_TASKS; + } + usb_serial_jtag_ll_txfifo_flush(); } From db6c9836b089222650a66ebace2a479c8aa8bff2 Mon Sep 17 00:00:00 2001 From: Dan Halbert Date: Wed, 27 Jul 2022 22:28:00 -0400 Subject: [PATCH 15/44] don't need to select macOS sdk any more --- .github/workflows/build.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index b767a92376..94837e4082 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -178,8 +178,6 @@ jobs: with: name: mpy-cross-macos-11-x64 path: mpy-cross/mpy-cross - - name: Select SDK for M1 build - run: sudo xcode-select -switch /Applications/Xcode_12.3.app - name: Build mpy-cross (arm64) run: make -C mpy-cross -j2 -f Makefile.m1 V=2 - uses: actions/upload-artifact@v2 From 8b4a5816bd557e4644eba4b13a5c574a2143ac5e Mon Sep 17 00:00:00 2001 From: Dan Halbert Date: Wed, 27 Jul 2022 22:51:14 -0400 Subject: [PATCH 16/44] don't specify -sdk in Makefile.m1 for mpy-cross --- mpy-cross/Makefile.m1 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mpy-cross/Makefile.m1 b/mpy-cross/Makefile.m1 index 34e9841540..13431f708b 100644 --- a/mpy-cross/Makefile.m1 +++ b/mpy-cross/Makefile.m1 @@ -7,4 +7,4 @@ BUILD=build-arm64 include mpy-cross.mk # Because mpy-cross.mk unconditionally overwrites CC for Darwin, we must set it BELOW the inclusion -CC := $(shell xcrun --sdk macosx11.1 --find clang) -isysroot $(shell xcrun --sdk macosx11.1 --show-sdk-path) -target arm64-apple-macos11 +CC := $(shell xcrun --find clang) -isysroot $(shell xcrun --show-sdk-path) -target arm64-apple-macos11 From 2a0e4f7ee22e8c133efeba8e199fd9a30b10f964 Mon Sep 17 00:00:00 2001 From: Andy Warburton Date: Thu, 28 Jul 2022 12:03:22 +0100 Subject: [PATCH 17/44] added css support to web workflow Added a bare minimum css implementation to web workflow to improve readability --- supervisor/shared/web_workflow/static/directory.html | 1 + supervisor/shared/web_workflow/static/serial.html | 1 + supervisor/shared/web_workflow/static/style.css | 7 +++++++ supervisor/shared/web_workflow/static/welcome.html | 1 + supervisor/shared/web_workflow/web_workflow.c | 3 +++ 5 files changed, 13 insertions(+) create mode 100644 supervisor/shared/web_workflow/static/style.css diff --git a/supervisor/shared/web_workflow/static/directory.html b/supervisor/shared/web_workflow/static/directory.html index d0ca1a3b32..0586cd0a54 100644 --- a/supervisor/shared/web_workflow/static/directory.html +++ b/supervisor/shared/web_workflow/static/directory.html @@ -4,6 +4,7 @@ +

 

diff --git a/supervisor/shared/web_workflow/static/serial.html b/supervisor/shared/web_workflow/static/serial.html index 0c13248904..5dfcb6cc7d 100644 --- a/supervisor/shared/web_workflow/static/serial.html +++ b/supervisor/shared/web_workflow/static/serial.html @@ -5,6 +5,7 @@ +
diff --git a/supervisor/shared/web_workflow/static/style.css b/supervisor/shared/web_workflow/static/style.css new file mode 100644 index 0000000000..7aa3eda00b --- /dev/null +++ b/supervisor/shared/web_workflow/static/style.css @@ -0,0 +1,7 @@ +body { + max-width: 960px; + margin: 20px auto; + font-size: 18px; + font-family: "Proxima Nova", Verdana, sans-serif; + line-height: 20.7px; +} \ No newline at end of file diff --git a/supervisor/shared/web_workflow/static/welcome.html b/supervisor/shared/web_workflow/static/welcome.html index 139e9eba39..d63b47584f 100644 --- a/supervisor/shared/web_workflow/static/welcome.html +++ b/supervisor/shared/web_workflow/static/welcome.html @@ -5,6 +5,7 @@ +

 Welcome!

diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index ff1c4060c3..a9435cc258 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -861,6 +861,7 @@ STATIC_FILE(directory_html); STATIC_FILE(directory_js); STATIC_FILE(welcome_html); STATIC_FILE(welcome_js); +STATIC_FILE(style_css); STATIC_FILE(serial_html); STATIC_FILE(serial_js); STATIC_FILE(blinka_16x16_ico); @@ -1070,6 +1071,8 @@ static bool _reply(socketpool_socket_obj_t *socket, _request *request) { _REPLY_STATIC(socket, request, welcome_js); } else if (strcmp(request->path, "/serial.js") == 0) { _REPLY_STATIC(socket, request, serial_js); + } else if (strcmp(request->path, "/style.css") == 0) { + _REPLY_STATIC(socket, request, style_css); } else if (strcmp(request->path, "/favicon.ico") == 0) { // TODO: Autogenerate this based on the blinka bitmap and change the // palette based on MAC address. From 555bf7cc12dd4f6b3d990b6a918aa3461e1f3123 Mon Sep 17 00:00:00 2001 From: Michael Himing Date: Tue, 26 Jul 2022 21:07:55 +1000 Subject: [PATCH 18/44] Add board: seeed_xiao_esp32c3 --- .../boards/seeed_xiao_esp32c3/board.c | 26 +++++++++++ .../boards/seeed_xiao_esp32c3/mpconfigboard.h | 14 ++++++ .../seeed_xiao_esp32c3/mpconfigboard.mk | 10 +++++ .../boards/seeed_xiao_esp32c3/pins.c | 43 +++++++++++++++++++ .../boards/seeed_xiao_esp32c3/sdkconfig | 5 +++ 5 files changed, 98 insertions(+) create mode 100644 ports/espressif/boards/seeed_xiao_esp32c3/board.c create mode 100644 ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.h create mode 100644 ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.mk create mode 100644 ports/espressif/boards/seeed_xiao_esp32c3/pins.c create mode 100644 ports/espressif/boards/seeed_xiao_esp32c3/sdkconfig diff --git a/ports/espressif/boards/seeed_xiao_esp32c3/board.c b/ports/espressif/boards/seeed_xiao_esp32c3/board.c new file mode 100644 index 0000000000..f5fd5702c3 --- /dev/null +++ b/ports/espressif/boards/seeed_xiao_esp32c3/board.c @@ -0,0 +1,26 @@ +#include "shared-bindings/microcontroller/Pin.h" +#include "supervisor/board.h" + +#include "components/driver/include/driver/gpio.h" + +void board_init(void) { + // Debug UART + #ifdef DEBUG + common_hal_never_reset_pin(&pin_GPIO20); + common_hal_never_reset_pin(&pin_GPIO21); + #endif +} + +bool board_requests_safe_mode(void) { + return false; +} + +bool espressif_board_reset_pin_number(gpio_num_t pin_number) { + return false; +} + +void reset_board(void) { +} + +void board_deinit(void) { +} diff --git a/ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.h b/ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.h new file mode 100644 index 0000000000..638be9d197 --- /dev/null +++ b/ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.h @@ -0,0 +1,14 @@ +#define MICROPY_HW_BOARD_NAME "Seeed Studio XIAO ESP32C3" +#define MICROPY_HW_MCU_NAME "ESP32-C3FN4" + +#define DEFAULT_I2C_BUS_SCL (&pin_GPIO7) +#define DEFAULT_I2C_BUS_SDA (&pin_GPIO6) + +#define DEFAULT_SPI_BUS_SCK (&pin_GPIO8) +#define DEFAULT_SPI_BUS_MOSI (&pin_GPIO10) +#define DEFAULT_SPI_BUS_MISO (&pin_GPIO9) + +#define DEFAULT_UART_BUS_RX (&pin_GPIO20) +#define DEFAULT_UART_BUS_TX (&pin_GPIO21) + +#define CIRCUITPY_ESP_USB_SERIAL_JTAG (1) diff --git a/ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.mk b/ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.mk new file mode 100644 index 0000000000..9e14c9ac7f --- /dev/null +++ b/ports/espressif/boards/seeed_xiao_esp32c3/mpconfigboard.mk @@ -0,0 +1,10 @@ +CIRCUITPY_CREATOR_ID = 0x000C2886 +CIRCUITPY_CREATION_ID = 0x00C30001 + +IDF_TARGET = esp32c3 + +INTERNAL_FLASH_FILESYSTEM = 1 + +CIRCUITPY_ESP_FLASH_MODE = qio +CIRCUITPY_ESP_FLASH_FREQ = 80m +CIRCUITPY_ESP_FLASH_SIZE = 4MB diff --git a/ports/espressif/boards/seeed_xiao_esp32c3/pins.c b/ports/espressif/boards/seeed_xiao_esp32c3/pins.c new file mode 100644 index 0000000000..5fc475d564 --- /dev/null +++ b/ports/espressif/boards/seeed_xiao_esp32c3/pins.c @@ -0,0 +1,43 @@ +#include "shared-bindings/board/__init__.h" + +STATIC const mp_rom_map_elem_t board_module_globals_table[] = { + CIRCUITPYTHON_BOARD_DICT_STANDARD_ITEMS + + { MP_ROM_QSTR(MP_QSTR_D0), MP_ROM_PTR(&pin_GPIO2) }, + { MP_ROM_QSTR(MP_QSTR_A0), MP_ROM_PTR(&pin_GPIO2) }, + + { MP_ROM_QSTR(MP_QSTR_D1), MP_ROM_PTR(&pin_GPIO3) }, + { MP_ROM_QSTR(MP_QSTR_A1), MP_ROM_PTR(&pin_GPIO3) }, + + { MP_ROM_QSTR(MP_QSTR_D2), MP_ROM_PTR(&pin_GPIO4) }, + { MP_ROM_QSTR(MP_QSTR_A2), MP_ROM_PTR(&pin_GPIO4) }, + + { MP_ROM_QSTR(MP_QSTR_D3), MP_ROM_PTR(&pin_GPIO5) }, + { MP_ROM_QSTR(MP_QSTR_A3), MP_ROM_PTR(&pin_GPIO5) }, + + { MP_ROM_QSTR(MP_QSTR_D4), MP_ROM_PTR(&pin_GPIO6) }, + { MP_ROM_QSTR(MP_QSTR_SDA), MP_ROM_PTR(&pin_GPIO6) }, + + { MP_ROM_QSTR(MP_QSTR_D5), MP_ROM_PTR(&pin_GPIO7) }, + { MP_ROM_QSTR(MP_QSTR_SCL), MP_ROM_PTR(&pin_GPIO7) }, + + { MP_ROM_QSTR(MP_QSTR_D6), MP_ROM_PTR(&pin_GPIO21) }, + { MP_ROM_QSTR(MP_QSTR_TX), MP_ROM_PTR(&pin_GPIO21) }, + + { MP_ROM_QSTR(MP_QSTR_D7), MP_ROM_PTR(&pin_GPIO20) }, + { MP_ROM_QSTR(MP_QSTR_RX), MP_ROM_PTR(&pin_GPIO20) }, + + { MP_ROM_QSTR(MP_QSTR_D8), MP_ROM_PTR(&pin_GPIO8) }, + { MP_ROM_QSTR(MP_QSTR_SCK), MP_ROM_PTR(&pin_GPIO8) }, + + { MP_ROM_QSTR(MP_QSTR_D9), MP_ROM_PTR(&pin_GPIO9) }, + { MP_ROM_QSTR(MP_QSTR_MISO), MP_ROM_PTR(&pin_GPIO9) }, + + { MP_ROM_QSTR(MP_QSTR_D10), MP_ROM_PTR(&pin_GPIO10) }, + { MP_ROM_QSTR(MP_QSTR_MOSI), MP_ROM_PTR(&pin_GPIO10) }, + + { MP_ROM_QSTR(MP_QSTR_I2C), MP_ROM_PTR(&board_i2c_obj) }, + { MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_spi_obj) }, + { MP_ROM_QSTR(MP_QSTR_UART), MP_ROM_PTR(&board_uart_obj) }, +}; +MP_DEFINE_CONST_DICT(board_module_globals, board_module_globals_table); diff --git a/ports/espressif/boards/seeed_xiao_esp32c3/sdkconfig b/ports/espressif/boards/seeed_xiao_esp32c3/sdkconfig new file mode 100644 index 0000000000..b2c9bc0fe6 --- /dev/null +++ b/ports/espressif/boards/seeed_xiao_esp32c3/sdkconfig @@ -0,0 +1,5 @@ +# +# LWIP +# +CONFIG_LWIP_LOCAL_HOSTNAME="seeed-xiao-esp32c3" +# end of LWIP From ddeb833a3ac106d35a362e9eada26d652a16a8a0 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Thu, 28 Jul 2022 07:43:39 -0700 Subject: [PATCH 19/44] Shrink Feather S3 4mb build with -Os --- .../adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk b/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk index 39804bad26..1b4c4015f5 100644 --- a/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk +++ b/ports/espressif/boards/adafruit_feather_esp32s3_4mbflash_2mbpsram/mpconfigboard.mk @@ -16,4 +16,4 @@ CIRCUITPY_ESP_FLASH_MODE = qio CIRCUITPY_ESP_FLASH_FREQ = 40m CIRCUITPY_ESP_FLASH_SIZE = 4MB -CIRCUITPY_PS2IO = 0 +OPTIMIZATION_FLAGS = -Os From 2baf3455bd22590e241e08fdec20c12af9826d40 Mon Sep 17 00:00:00 2001 From: David Glaude Date: Thu, 28 Jul 2022 16:46:56 +0200 Subject: [PATCH 20/44] Add board.LED (alias of board.LED_R part of RGB) Totally untested change (will try with the artifact), but I think every board should have a board.LED if possible to be able to use the learn guide basic instruction. --- ports/raspberrypi/boards/pimoroni_interstate75/pins.c | 1 + 1 file changed, 1 insertion(+) diff --git a/ports/raspberrypi/boards/pimoroni_interstate75/pins.c b/ports/raspberrypi/boards/pimoroni_interstate75/pins.c index 2460ebc76a..801a418015 100644 --- a/ports/raspberrypi/boards/pimoroni_interstate75/pins.c +++ b/ports/raspberrypi/boards/pimoroni_interstate75/pins.c @@ -22,6 +22,7 @@ STATIC const mp_rom_map_elem_t board_module_globals_table[] = { { MP_ROM_QSTR(MP_QSTR_SW_A), MP_ROM_PTR(&pin_GPIO14) }, + { MP_ROM_QSTR(MP_QSTR_LED), MP_ROM_PTR(&pin_GPIO16) }, { MP_ROM_QSTR(MP_QSTR_LED_R), MP_ROM_PTR(&pin_GPIO16) }, { MP_ROM_QSTR(MP_QSTR_LED_G), MP_ROM_PTR(&pin_GPIO17) }, { MP_ROM_QSTR(MP_QSTR_LED_B), MP_ROM_PTR(&pin_GPIO18) }, From ccd60632845f4d3b38cc5424844985478ec115a7 Mon Sep 17 00:00:00 2001 From: Andy Warburton Date: Thu, 28 Jul 2022 16:08:05 +0100 Subject: [PATCH 21/44] Update welcome.html Made html more semantic. --- .../shared/web_workflow/static/welcome.html | 26 +++++++++++++------ 1 file changed, 18 insertions(+), 8 deletions(-) diff --git a/supervisor/shared/web_workflow/static/welcome.html b/supervisor/shared/web_workflow/static/welcome.html index d63b47584f..321fe09d43 100644 --- a/supervisor/shared/web_workflow/static/welcome.html +++ b/supervisor/shared/web_workflow/static/welcome.html @@ -8,16 +8,26 @@ +

 Welcome!

- Welcome to CircuitPython's Web API. Go to the file browser to work with files in the CIRCUITPY drive. Go to the serial terminal to see code output and interact with the REPL. Make sure you've set CIRCUITPY_WEB_API_PASSWORD='somepassword' in /.env. Provide the password when the browser prompts for it. Leave the username blank. + +

Welcome to CircuitPython's Web API. Go to the file browser to work with files in the CIRCUITPY drive. Go to the serial terminal to see code output and interact with the REPL. Make sure you've set CIRCUITPY_WEB_API_PASSWORD='somepassword' in /.env. Provide the password when the browser prompts for it. Leave the username blank.

+

Device Info

- Board:
- Version:
- Hostname:
- IP: -

Other Devices

- Here are other CircuitPython devices on your network: + +
+
Board:
+
+
Version:
+
+
Hostname:
+
+
IP:
+
+
Other Devices
+
+

Here are other CircuitPython devices on your network:

    -
+ From 1332bb6534fe1888f8c4ca10ed3d36df2b64ff06 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Thu, 28 Jul 2022 08:16:16 -0700 Subject: [PATCH 22/44] Add newline --- supervisor/shared/web_workflow/static/style.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/supervisor/shared/web_workflow/static/style.css b/supervisor/shared/web_workflow/static/style.css index 7aa3eda00b..f6ef757b3f 100644 --- a/supervisor/shared/web_workflow/static/style.css +++ b/supervisor/shared/web_workflow/static/style.css @@ -4,4 +4,4 @@ body { font-size: 18px; font-family: "Proxima Nova", Verdana, sans-serif; line-height: 20.7px; -} \ No newline at end of file +} From df14f953981500b56b19753215adee2d64ab03c5 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Thu, 28 Jul 2022 08:16:51 -0700 Subject: [PATCH 23/44] Delete trailing spaces --- supervisor/shared/web_workflow/web_workflow.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index a9435cc258..b87493b1bc 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -1072,7 +1072,7 @@ static bool _reply(socketpool_socket_obj_t *socket, _request *request) { } else if (strcmp(request->path, "/serial.js") == 0) { _REPLY_STATIC(socket, request, serial_js); } else if (strcmp(request->path, "/style.css") == 0) { - _REPLY_STATIC(socket, request, style_css); + _REPLY_STATIC(socket, request, style_css); } else if (strcmp(request->path, "/favicon.ico") == 0) { // TODO: Autogenerate this based on the blinka bitmap and change the // palette based on MAC address. From 8b6e4cc4e80834b452dc0a912bb8cd6cca049ec3 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Thu, 28 Jul 2022 08:18:52 -0700 Subject: [PATCH 24/44] Delete trailing spaces --- supervisor/shared/web_workflow/static/welcome.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/supervisor/shared/web_workflow/static/welcome.html b/supervisor/shared/web_workflow/static/welcome.html index 321fe09d43..a7976055d3 100644 --- a/supervisor/shared/web_workflow/static/welcome.html +++ b/supervisor/shared/web_workflow/static/welcome.html @@ -28,6 +28,6 @@

Here are other CircuitPython devices on your network:

    -
+ From babd4ee618b87b043eca95b6e97aa01f72cf465e Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Thu, 28 Jul 2022 08:43:36 -0700 Subject: [PATCH 25/44] Tweaks based on review comments --- shared-bindings/mdns/Server.c | 4 ++-- supervisor/shared/web_workflow/web_workflow.c | 10 ++++++---- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/shared-bindings/mdns/Server.c b/shared-bindings/mdns/Server.c index e11c1c4730..bcf761d72a 100644 --- a/shared-bindings/mdns/Server.c +++ b/shared-bindings/mdns/Server.c @@ -161,8 +161,8 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_KW(mdns_server_find_obj, 1, _mdns_server_find); //| def advertise_service(self, *, service_type: str, protocol: str, port: int) -> None: //| """Respond to queries for the given service with the given port. //| -//| service_type and protocol can only occur on one port. Any call after the first will -//| update the entry's port. +//| ``service_type`` and ``protocol`` can only occur on one port. Any call after the first +//| will update the entry's port. //| //| :param str service_type: The service type such as "_http" //| :param str protocol: The service protocol such as "_tcp" diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 5225cfe13e..98ee007328 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -247,6 +247,7 @@ void supervisor_start_web_workflow(void) { port_len = dotenv_get_key("/.env", "CIRCUITPY_WEB_API_PORT", port_encoded, sizeof(port_encoded) - 1); #endif if (0 < port_len && port_len < sizeof(port_encoded)) { + port_encoded[port_len] = '\0'; new_port = strtoul(port_encoded, NULL, 10); } @@ -623,8 +624,6 @@ static void _reply_directory_json(socketpool_socket_obj_t *socket, _request *req static void _reply_with_file(socketpool_socket_obj_t *socket, _request *request, const char *filename, FIL *active_file) { uint32_t total_length = f_size(active_file); - char encoded_len[10]; - snprintf(encoded_len, sizeof(encoded_len), "%d", total_length); _send_str(socket, "HTTP/1.1 200 OK\r\n"); mp_print_t _socket_print = {socket, _print_raw}; @@ -1209,9 +1208,12 @@ static void _process_request(socketpool_socket_obj_t *socket, _request *request) request->authenticated = strncmp(request->header_value, prefix, strlen(prefix)) == 0 && strcmp(_api_password, request->header_value + strlen(prefix)) == 0; } else if (strcasecmp(request->header_key, "Host") == 0) { - // Do a prefix check so that port is ignored. + // Do a prefix check so that port is ignored. Length must be the same or the + // header ends in :. const char *cp_local = "circuitpython.local"; - request->redirect = strncmp(request->header_value, cp_local, strlen(cp_local)) == 0; + request->redirect = strncmp(request->header_value, cp_local, strlen(cp_local)) == 0 && + (strlen(request->header_value) == strlen(cp_local) || + request->header_value[strlen(cp_local)] == ':'); } else if (strcasecmp(request->header_key, "Content-Length") == 0) { request->content_length = strtoul(request->header_value, NULL, 10); } else if (strcasecmp(request->header_key, "Expect") == 0) { From ac53e7e4390d91b3791e6a0de3e087ad2cb94948 Mon Sep 17 00:00:00 2001 From: Andy Warburton Date: Thu, 28 Jul 2022 16:57:02 +0100 Subject: [PATCH 26/44] further refinements --- supervisor/shared/web_workflow/static/welcome.html | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/supervisor/shared/web_workflow/static/welcome.html b/supervisor/shared/web_workflow/static/welcome.html index a7976055d3..125158fd8d 100644 --- a/supervisor/shared/web_workflow/static/welcome.html +++ b/supervisor/shared/web_workflow/static/welcome.html @@ -13,7 +13,7 @@

Welcome to CircuitPython's Web API. Go to the file browser to work with files in the CIRCUITPY drive. Go to the serial terminal to see code output and interact with the REPL. Make sure you've set CIRCUITPY_WEB_API_PASSWORD='somepassword' in /.env. Provide the password when the browser prompts for it. Leave the username blank.

-

Device Info

+

Device Info:

Board:
@@ -22,12 +22,12 @@
Hostname:
-
IP:
-
-
Other Devices
+
IP:
+
+

Here are other CircuitPython devices on your network:

    -
+ From b11eb12da53f6c0f87642f7cdee157160d3cd33b Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Thu, 28 Jul 2022 11:00:26 -0700 Subject: [PATCH 27/44] Fix modified time. Use snprintf for uint64_t printing. --- supervisor/shared/web_workflow/web_workflow.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 98ee007328..a4679c0932 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -608,7 +608,11 @@ static void _reply_directory_json(socketpool_socket_obj_t *socket, _request *req (file_info.ftime >> 5) & 0x1f, (file_info.ftime & 0x1f) * 2) * 1000000000ULL; - mp_printf(&_socket_print, "\"modified_ns\": %lld, ", truncated_time); + // Use snprintf because mp_printf doesn't support 64 bit numbers by + // default. + char encoded_time[32]; + snprintf(encoded_time, sizeof(encoded_time), "%llu", truncated_time); + mp_printf(&_socket_print, "\"modified_ns\": %s, ", encoded_time); size_t file_size = 0; if ((file_info.fattrib & AM_DIR) == 0) { file_size = file_info.fsize; From 35797ff3f07ef2cee2841125b2bf1d235595d43d Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Thu, 28 Jul 2022 12:52:41 -0700 Subject: [PATCH 28/44] Remove trailing spaces --- supervisor/shared/web_workflow/static/welcome.html | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/supervisor/shared/web_workflow/static/welcome.html b/supervisor/shared/web_workflow/static/welcome.html index 125158fd8d..e075c0200d 100644 --- a/supervisor/shared/web_workflow/static/welcome.html +++ b/supervisor/shared/web_workflow/static/welcome.html @@ -25,9 +25,9 @@
IP:
- +

Here are other CircuitPython devices on your network:

    -
+ From cfa7de7592a43792fd58ec3e5142992d2cb2ae64 Mon Sep 17 00:00:00 2001 From: Dan Halbert Date: Thu, 28 Jul 2022 18:14:32 -0400 Subject: [PATCH 29/44] fix name for macOS mpy-cross universal build --- .github/workflows/build.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 94837e4082..84224a1c1a 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -185,11 +185,11 @@ jobs: name: mpy-cross-macos-11-arm64 path: mpy-cross/mpy-cross-arm64 - name: Make universal binary - run: lipo -create -output mpy-cross-macos-11-universal mpy-cross/mpy-cross mpy-cross/mpy-cross-arm64 + run: lipo -create -output mpy-cross-macos-universal mpy-cross/mpy-cross mpy-cross/mpy-cross-arm64 - uses: actions/upload-artifact@v2 with: name: mpy-cross-macos-11-universal - path: mpy-cross-macos-11-universal + path: mpy-cross-macos-universal - name: Upload mpy-cross build to S3 run: | [ -z "$AWS_ACCESS_KEY_ID" ] || aws s3 cp mpy-cross-macos-universal s3://adafruit-circuit-python/bin/mpy-cross/mpy-cross-macos-11-${{ env.CP_VERSION }}-universal --no-progress --region us-east-1 From d6344812e8ca7032b50f4c0f0aedb88448183f02 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Wed, 27 Jul 2022 17:00:38 -0700 Subject: [PATCH 30/44] Lots of web workflow, C3 and title bar fixes * Fixes #6221 - C3 hang on `import wifi`. Enabling the WiFi PHY was disabling USB. Now boards that use it set CONFIG_ESP_PHY_ENABLE_USB explicitly. * Fixes #6655 - Allows pasting into the web serial page. Fixes reading more than 0xf bytes at a time. * Fixes #6653 - Fixes web socket encoding of payloads >125 bytes. Can happen when printing a long string. * Fixes C3 responsiveness when waiting for key to enter REPL. (It now correctly stops sleeping.) * Disables title bar updates when in raw REPL. Related to #6548. * Adds version to title bar. --- main.c | 4 + .../boards/adafruit_qtpy_esp32c3/sdkconfig | 8 ++ .../boards/beetle-esp32-c3/sdkconfig | 6 ++ .../espressif/boards/lolin_c3_mini/sdkconfig | 6 ++ ports/espressif/common-hal/wifi/__init__.c | 3 +- ports/espressif/esp-idf | 2 +- ports/espressif/supervisor/port.c | 9 +- ports/espressif/supervisor/usb_serial_jtag.c | 27 +++--- supervisor/port.h | 12 ++- .../esp_port.h => supervisor/shared/port.c | 14 ++- supervisor/shared/serial.c | 12 ++- supervisor/shared/title_bar.c | 93 +++++++++++++++++++ supervisor/shared/title_bar.h | 34 +++++++ .../shared/web_workflow/static/serial.js | 4 +- supervisor/shared/web_workflow/web_workflow.c | 54 +++++++---- supervisor/shared/web_workflow/web_workflow.h | 1 + supervisor/shared/web_workflow/websocket.c | 22 ++++- supervisor/shared/workflow.c | 20 ---- supervisor/supervisor.mk | 2 + 19 files changed, 262 insertions(+), 71 deletions(-) rename ports/espressif/supervisor/esp_port.h => supervisor/shared/port.c (78%) create mode 100644 supervisor/shared/title_bar.c create mode 100644 supervisor/shared/title_bar.h diff --git a/main.c b/main.c index 5fcb2d61a6..d310f571a6 100644 --- a/main.c +++ b/main.c @@ -57,6 +57,7 @@ #include "supervisor/shared/stack.h" #include "supervisor/shared/status_leds.h" #include "supervisor/shared/tick.h" +#include "supervisor/shared/title_bar.h" #include "supervisor/shared/traceback.h" #include "supervisor/shared/translate/translate.h" #include "supervisor/shared/workflow.h" @@ -822,7 +823,9 @@ STATIC int run_repl(bool first_run) { status_led_deinit(); #endif if (pyexec_mode_kind == PYEXEC_MODE_RAW_REPL) { + supervisor_title_bar_suspend(); exit_code = pyexec_raw_repl(); + supervisor_title_bar_resume(); } else { exit_code = pyexec_friendly_repl(); } @@ -914,6 +917,7 @@ int __attribute__((used)) main(void) { run_boot_py(safe_mode); supervisor_workflow_start(); + supervisor_title_bar_start(); // Boot script is finished, so now go into REPL or run code.py. int exit_code = PYEXEC_FORCED_EXIT; diff --git a/ports/espressif/boards/adafruit_qtpy_esp32c3/sdkconfig b/ports/espressif/boards/adafruit_qtpy_esp32c3/sdkconfig index f9b0292400..5111900c7e 100644 --- a/ports/espressif/boards/adafruit_qtpy_esp32c3/sdkconfig +++ b/ports/espressif/boards/adafruit_qtpy_esp32c3/sdkconfig @@ -30,6 +30,14 @@ CONFIG_PARTITION_TABLE_FILENAME="esp-idf-config/partitions-4MB-no-uf2.csv" # # Component config # +# + +# +# PHY +# +CONFIG_ESP_PHY_ENABLE_USB=y +# end of PHY + # # ESP System Settings # diff --git a/ports/espressif/boards/beetle-esp32-c3/sdkconfig b/ports/espressif/boards/beetle-esp32-c3/sdkconfig index 129c537108..331a5d14dc 100644 --- a/ports/espressif/boards/beetle-esp32-c3/sdkconfig +++ b/ports/espressif/boards/beetle-esp32-c3/sdkconfig @@ -1,3 +1,9 @@ +# +# PHY +# +CONFIG_ESP_PHY_ENABLE_USB=y +# end of PHY + # # LWIP # diff --git a/ports/espressif/boards/lolin_c3_mini/sdkconfig b/ports/espressif/boards/lolin_c3_mini/sdkconfig index 2cb6b06589..c548ee3c69 100644 --- a/ports/espressif/boards/lolin_c3_mini/sdkconfig +++ b/ports/espressif/boards/lolin_c3_mini/sdkconfig @@ -1,3 +1,9 @@ +# +# PHY +# +CONFIG_ESP_PHY_ENABLE_USB=y +# end of PHY + # # LWIP # diff --git a/ports/espressif/common-hal/wifi/__init__.c b/ports/espressif/common-hal/wifi/__init__.c index 885cc98f96..ca0533525d 100644 --- a/ports/espressif/common-hal/wifi/__init__.c +++ b/ports/espressif/common-hal/wifi/__init__.c @@ -44,6 +44,7 @@ wifi_radio_obj_t common_hal_wifi_radio_obj; #include "components/log/include/esp_log.h" #include "supervisor/port.h" +#include "supervisor/shared/title_bar.h" #include "supervisor/workflow.h" #include "esp_ipc.h" @@ -55,7 +56,7 @@ wifi_radio_obj_t common_hal_wifi_radio_obj; static const char *TAG = "CP wifi"; STATIC void schedule_background_on_cp_core(void *arg) { - supervisor_workflow_request_background(); + supervisor_title_bar_request_update(false); // CircuitPython's VM is run in a separate FreeRTOS task from wifi callbacks. So, we have to // notify the main task every time in case it's waiting for us. diff --git a/ports/espressif/esp-idf b/ports/espressif/esp-idf index 0180c0cb80..ddb7ddbcb6 160000 --- a/ports/espressif/esp-idf +++ b/ports/espressif/esp-idf @@ -1 +1 @@ -Subproject commit 0180c0cb80f052919badc15df164e8edde6344ad +Subproject commit ddb7ddbcb613a582e0a91eda8b1d2510dd0a2d83 diff --git a/ports/espressif/supervisor/port.c b/ports/espressif/supervisor/port.c index adefff3f71..5245c9f025 100644 --- a/ports/espressif/supervisor/port.c +++ b/ports/espressif/supervisor/port.c @@ -30,7 +30,6 @@ #include "supervisor/board.h" #include "supervisor/port.h" #include "py/runtime.h" -#include "supervisor/esp_port.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" @@ -390,6 +389,14 @@ void port_wake_main_task() { xTaskNotifyGive(circuitpython_task); } +void port_wake_main_task_from_isr() { + BaseType_t xHigherPriorityTaskWoken = pdFALSE; + vTaskNotifyGiveFromISR(circuitpython_task, &xHigherPriorityTaskWoken); + if (xHigherPriorityTaskWoken == pdTRUE) { + portYIELD_FROM_ISR(); + } +} + void sleep_timer_cb(void *arg) { port_wake_main_task(); } diff --git a/ports/espressif/supervisor/usb_serial_jtag.c b/ports/espressif/supervisor/usb_serial_jtag.c index 33f0ec3a8e..c666c9bb3c 100644 --- a/ports/espressif/supervisor/usb_serial_jtag.c +++ b/ports/espressif/supervisor/usb_serial_jtag.c @@ -28,19 +28,23 @@ #include "py/ringbuf.h" #include "py/runtime.h" #include "py/mphal.h" -#include "usb_serial_jtag.h" +#include "supervisor/port.h" +#include "supervisor/usb_serial_jtag.h" #include "hal/usb_serial_jtag_ll.h" #include "esp_intr_alloc.h" #include "soc/periph_defs.h" -#include "supervisor/esp_port.h" #define USB_SERIAL_JTAG_BUF_SIZE (64) STATIC ringbuf_t ringbuf; STATIC uint8_t buf[128]; -STATIC bool connected; +STATIC volatile bool connected; + +#if CIRCUITPY_ESP_USB_SERIAL_JTAG && !CONFIG_ESP_PHY_ENABLE_USB +#error "CONFIG_ESP_PHY_ENABLE_USB must be enabled in sdkconfig" +#endif static void usb_serial_jtag_isr_handler(void *arg) { uint32_t flags = usb_serial_jtag_ll_get_intsts_mask(); @@ -49,6 +53,11 @@ static void usb_serial_jtag_isr_handler(void *arg) { usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_SOF); } + if (flags & USB_SERIAL_JTAG_INTR_TOKEN_REC_IN_EP1) { + usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_TOKEN_REC_IN_EP1); + connected = true; + } + if (flags & USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT) { usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT); size_t req_len = ringbuf_num_empty(&ringbuf); @@ -64,25 +73,19 @@ static void usb_serial_jtag_isr_handler(void *arg) { ringbuf_put(&ringbuf, rx_buf[i]); } } - vTaskNotifyGiveFromISR(circuitpython_task, NULL); + port_wake_main_task_from_isr(); } } void usb_serial_jtag_init(void) { ringbuf_init(&ringbuf, buf, sizeof(buf)); - usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_SOF | USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT); - usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SOF | USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT); + usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_SOF | USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT | USB_SERIAL_JTAG_INTR_TOKEN_REC_IN_EP1); + usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SOF | USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT | USB_SERIAL_JTAG_INTR_TOKEN_REC_IN_EP1); ESP_ERROR_CHECK(esp_intr_alloc(ETS_USB_SERIAL_JTAG_INTR_SOURCE, ESP_INTR_FLAG_LEVEL1, usb_serial_jtag_isr_handler, NULL, NULL)); } bool usb_serial_jtag_connected(void) { - // Make connected sticky. Otherwise we'll be disconnected every time the SOF - // index is 0. (It's only ~15 bits so it wraps around frequently.) - if (connected) { - return true; - } - connected = USB_SERIAL_JTAG.fram_num.sof_frame_index > 0; return connected; } diff --git a/supervisor/port.h b/supervisor/port.h index 0a8cdfd342..d693d49440 100644 --- a/supervisor/port.h +++ b/supervisor/port.h @@ -99,8 +99,14 @@ void port_background_task(void); void port_start_background_task(void); void port_finish_background_task(void); -// Some ports need special handling to wake the main task from an interrupt -// context or other task. The port must implement the necessary code in this -// function. A default weak implementation is provided that does nothing. +// Some ports need special handling to wake the main task from another task. The +// port must implement the necessary code in this function. A default weak +// implementation is provided that does nothing. void port_wake_main_task(void); + +// Some ports need special handling to wake the main task from an interrupt +// context. The port must implement the necessary code in this function. A +// default weak implementation is provided that does nothing. +void port_wake_main_task_from_isr(void); + #endif // MICROPY_INCLUDED_SUPERVISOR_PORT_H diff --git a/ports/espressif/supervisor/esp_port.h b/supervisor/shared/port.c similarity index 78% rename from ports/espressif/supervisor/esp_port.h rename to supervisor/shared/port.c index 90ba3f65f1..5d4eeea093 100644 --- a/ports/espressif/supervisor/esp_port.h +++ b/supervisor/shared/port.c @@ -3,7 +3,7 @@ * * The MIT License (MIT) * - * Copyright (c) 2019 Lucian Copeland for Adafruit Industries + * 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 @@ -24,12 +24,10 @@ * THE SOFTWARE. */ -#ifndef MICROPY_INCLUDED_ESPRESSIF_SUPERVISOR_PORT_H -#define MICROPY_INCLUDED_ESPRESSIF_SUPERVISOR_PORT_H +#include "supervisor/port.h" -#include "freertos/FreeRTOS.h" -#include "freertos/task.h" +MP_WEAK void port_wake_main_task(void) { +} -extern TaskHandle_t circuitpython_task; - -#endif // MICROPY_INCLUDED_ESPRESSIF_SUPERVISOR_PORT_H +MP_WEAK void port_wake_main_task_from_isr(void) { +} diff --git a/supervisor/shared/serial.c b/supervisor/shared/serial.c index 710046e62e..974dd12b32 100644 --- a/supervisor/shared/serial.c +++ b/supervisor/shared/serial.c @@ -207,10 +207,17 @@ char serial_read(void) { #if CIRCUITPY_WEB_WORKFLOW if (websocket_available()) { - return websocket_read_char(); + char c = websocket_read_char(); + if (c != -1) { + return c; + } } #endif + if (port_serial_bytes_available() > 0) { + return port_serial_read(); + } + #if CIRCUITPY_USB_CDC if (!usb_cdc_console_enabled()) { return -1; @@ -220,9 +227,6 @@ char serial_read(void) { return (char)tud_cdc_read_char(); #endif - if (port_serial_bytes_available() > 0) { - return port_serial_read(); - } return -1; } diff --git a/supervisor/shared/title_bar.c b/supervisor/shared/title_bar.c new file mode 100644 index 0000000000..b836765ba3 --- /dev/null +++ b/supervisor/shared/title_bar.c @@ -0,0 +1,93 @@ +/* + * 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. + */ + +#include +#include "genhdr/mpversion.h" +#include "py/mpconfig.h" +#include "supervisor/background_callback.h" +#include "supervisor/serial.h" +#include "supervisor/shared/title_bar.h" + +#if CIRCUITPY_WEB_WORKFLOW +#include "supervisor/shared/web_workflow/web_workflow.h" +#endif +static background_callback_t title_bar_background_cb; + +static bool _forced_dirty = false; +static bool _suspended = false; + +static void title_bar_background(void *data) { + if (_suspended) { + return; + } + bool dirty = _forced_dirty; + + #if CIRCUITPY_WEB_WORKFLOW + dirty = dirty || supervisor_web_workflow_status_dirty(); + #endif + + if (!dirty) { + return; + } + _forced_dirty = false; + #if CIRCUITPY_STATUS_BAR + // Neighboring "" "" are concatenated by the compiler. Without this separation, the hex code + // doesn't get terminated after two following characters and the value is invalid. + // This is the OSC command to set the title and the icon text. It can be up to 255 characters + // but some may be cut off. + serial_write("\x1b" "]0;"); + serial_write("🐍 "); + #if CIRCUITPY_WEB_WORKFLOW + supervisor_web_workflow_status(); + #endif + serial_write("|"); + serial_write(MICROPY_GIT_TAG); + // Send string terminator + serial_write("\x1b" "\\"); + #endif +} + +void supervisor_title_bar_start(void) { + title_bar_background_cb.fun = title_bar_background; + title_bar_background_cb.data = NULL; + supervisor_title_bar_request_update(true); +} + +void supervisor_title_bar_request_update(bool force_dirty) { + if (force_dirty) { + _forced_dirty = true; + } + background_callback_add_core(&title_bar_background_cb); +} + +void supervisor_title_bar_suspend(void) { + _suspended = true; +} + +void supervisor_title_bar_resume(void) { + _suspended = false; + supervisor_title_bar_request_update(false); +} diff --git a/supervisor/shared/title_bar.h b/supervisor/shared/title_bar.h new file mode 100644 index 0000000000..778d768086 --- /dev/null +++ b/supervisor/shared/title_bar.h @@ -0,0 +1,34 @@ +/* + * 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 + +void supervisor_title_bar_start(void); +void supervisor_title_bar_suspend(void); +void supervisor_title_bar_resume(void); +void supervisor_title_bar_request_update(bool force_dirty); diff --git a/supervisor/shared/web_workflow/static/serial.js b/supervisor/shared/web_workflow/static/serial.js index 86ec077e92..5c644795a0 100644 --- a/supervisor/shared/web_workflow/static/serial.js +++ b/supervisor/shared/web_workflow/static/serial.js @@ -63,10 +63,12 @@ input.addEventListener("beforeinput", function(e) { input.value = ""; input.focus(); e.preventDefault(); - } else if (e.inputType == "insertText") { + } else if (e.inputType == "insertText" || e.inputType == "insertFromPaste") { ws.send(e.data); } else if (e.inputType == "deleteContentBackward") { ws.send("\b"); + } else { + console.log(e); } }); diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index bd7b150765..ca68155e36 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -95,7 +95,12 @@ typedef struct { char websocket_key[24 + 1]; } _request; -static wifi_radio_error_t wifi_status = WIFI_RADIO_ERROR_NONE; +static wifi_radio_error_t _wifi_status = WIFI_RADIO_ERROR_NONE; + +// Store last status state to compute dirty. +static bool _last_enabled = false; +static uint32_t _last_ip = 0; +static wifi_radio_error_t _last_wifi_status = WIFI_RADIO_ERROR_NONE; static mdns_server_obj_t mdns; static uint32_t web_api_port = 80; @@ -108,6 +113,7 @@ static _request active_request; static char _api_password[64]; +// Store the encoded IP so we don't duplicate work. static uint32_t _encoded_ip = 0; static char _our_ip_encoded[4 * 4]; @@ -170,25 +176,41 @@ static bool _base64_in_place(char *buf, size_t in_len, size_t out_len) { return true; } +STATIC void _update_encoded_ip(void) { + uint32_t ipv4_address = 0; + if (common_hal_wifi_radio_get_enabled(&common_hal_wifi_radio_obj)) { + ipv4_address = wifi_radio_get_ipv4_address(&common_hal_wifi_radio_obj); + } + if (_encoded_ip != ipv4_address) { + uint8_t *octets = (uint8_t *)&ipv4_address; + snprintf(_our_ip_encoded, sizeof(_our_ip_encoded), "%d.%d.%d.%d", octets[0], octets[1], octets[2], octets[3]); + _encoded_ip = ipv4_address; + } +} + +bool supervisor_web_workflow_status_dirty(void) { + return common_hal_wifi_radio_get_enabled(&common_hal_wifi_radio_obj) != _last_enabled || + _encoded_ip != _last_ip || + _last_wifi_status != _wifi_status; +} void supervisor_web_workflow_status(void) { serial_write_compressed(translate("Wi-Fi: ")); - if (common_hal_wifi_radio_get_enabled(&common_hal_wifi_radio_obj)) { + _last_enabled = common_hal_wifi_radio_get_enabled(&common_hal_wifi_radio_obj); + if (_last_enabled) { uint32_t ipv4_address = wifi_radio_get_ipv4_address(&common_hal_wifi_radio_obj); - if (wifi_status == WIFI_RADIO_ERROR_AUTH_EXPIRE || - wifi_status == WIFI_RADIO_ERROR_AUTH_FAIL) { + _last_wifi_status = _wifi_status; + if (_wifi_status == WIFI_RADIO_ERROR_AUTH_EXPIRE || + _wifi_status == WIFI_RADIO_ERROR_AUTH_FAIL) { serial_write_compressed(translate("Authentication failure")); - } else if (wifi_status != WIFI_RADIO_ERROR_NONE) { - mp_printf(&mp_plat_print, "%d", wifi_status); + } else if (_wifi_status != WIFI_RADIO_ERROR_NONE) { + mp_printf(&mp_plat_print, "%d", _wifi_status); } else if (ipv4_address == 0) { + _last_ip = 0; serial_write_compressed(translate("No IP")); } else { - if (_encoded_ip != ipv4_address) { - uint8_t *octets = (uint8_t *)&ipv4_address; - snprintf(_our_ip_encoded, sizeof(_our_ip_encoded), "%d.%d.%d.%d", octets[0], octets[1], octets[2], octets[3]); - _encoded_ip = ipv4_address; - } - + _update_encoded_ip(); + _last_ip = _encoded_ip; mp_printf(&mp_plat_print, "%s", _our_ip_encoded); if (web_api_port != 80) { mp_printf(&mp_plat_print, ":%d", web_api_port); @@ -231,11 +253,11 @@ void supervisor_start_web_workflow(void) { // We can all connect again because it will return early if we're already connected to the // network. If we are connected to a different network, then it will disconnect before // attempting to connect to the given network. - wifi_status = common_hal_wifi_radio_connect( + _wifi_status = common_hal_wifi_radio_connect( &common_hal_wifi_radio_obj, (uint8_t *)ssid, ssid_len, (uint8_t *)password, password_len, 0, 0.1, NULL, 0); - if (wifi_status != WIFI_RADIO_ERROR_NONE) { + if (_wifi_status != WIFI_RADIO_ERROR_NONE) { common_hal_wifi_radio_set_enabled(&common_hal_wifi_radio_obj, false); return; } @@ -290,8 +312,6 @@ void supervisor_start_web_workflow(void) { } // TODO: - // GET /cp/serial.txt - // - Most recent 1k of serial output. // GET /edit/ // - Super basic editor #endif @@ -406,6 +426,7 @@ static bool _origin_ok(const char *origin) { return true; } + _update_encoded_ip(); end = origin + strlen(http) + strlen(_our_ip_encoded); if (strncmp(origin + strlen(http), _our_ip_encoded, strlen(_our_ip_encoded)) == 0 && (end[0] == '\0' || end[0] == ':')) { @@ -710,6 +731,7 @@ static void _reply_with_version_json(socketpool_socket_obj_t *socket, _request * mp_print_t _socket_print = {socket, _print_chunk}; const char *hostname = common_hal_mdns_server_get_hostname(&mdns); + _update_encoded_ip(); // Note: this leverages the fact that C concats consecutive string literals together. mp_printf(&_socket_print, "{\"web_api_version\": 1, " diff --git a/supervisor/shared/web_workflow/web_workflow.h b/supervisor/shared/web_workflow/web_workflow.h index f233c06e48..a325b0667e 100644 --- a/supervisor/shared/web_workflow/web_workflow.h +++ b/supervisor/shared/web_workflow/web_workflow.h @@ -31,6 +31,7 @@ // This background function should be called repeatedly. It cannot be done based // on events. void supervisor_web_workflow_background(void); +bool supervisor_web_workflow_status_dirty(void); void supervisor_web_workflow_status(void); void supervisor_start_web_workflow(void); void supervisor_stop_web_workflow(void); diff --git a/supervisor/shared/web_workflow/websocket.c b/supervisor/shared/web_workflow/websocket.c index 313e18a86d..5a42eefb35 100644 --- a/supervisor/shared/web_workflow/websocket.c +++ b/supervisor/shared/web_workflow/websocket.c @@ -26,6 +26,8 @@ #include "supervisor/shared/web_workflow/websocket.h" +#include "supervisor/shared/title_bar.h" + // TODO: Remove ESP specific stuff. For now, it is useful as we refine the server. #include "esp_log.h" @@ -59,6 +61,9 @@ void websocket_handoff(socketpool_socket_obj_t *socket) { // Mark the original socket object as closed without telling the lower level. socket->connected = false; socket->num = -1; + + // Send the title bar for the new client. + supervisor_title_bar_request_update(true); } bool websocket_connected(void) { @@ -94,7 +99,7 @@ static void _read_next_frame_header(void) { } if (cp_serial.frame_index == 1 && _read_byte(&h)) { cp_serial.frame_index++; - uint8_t len = h & 0xf; + uint8_t len = h & 0x7f; cp_serial.masked = (h >> 7) == 1; if (len <= 125) { cp_serial.payload_remaining = len; @@ -194,7 +199,9 @@ bool websocket_available(void) { char websocket_read_char(void) { uint8_t c; - _read_next_payload_byte(&c); + if (!_read_next_payload_byte(&c)) { + c = -1; + } return c; } @@ -215,13 +222,20 @@ static void _websocket_send(_websocket *ws, const char *text, size_t len) { } frame_header[1] = payload_len; _send_raw(&ws->socket, (const uint8_t *)frame_header, 2); + uint8_t extended_len[4]; if (payload_len == 126) { - _send_raw(&ws->socket, (const uint8_t *)&len, 2); + extended_len[0] = (len >> 8) & 0xff; + extended_len[1] = len & 0xff; + _send_raw(&ws->socket, extended_len, 2); } else if (payload_len == 127) { uint32_t zero = 0; // 64 bits where top four bytes are zero. _send_raw(&ws->socket, (const uint8_t *)&zero, 4); - _send_raw(&ws->socket, (const uint8_t *)&len, 4); + extended_len[0] = (len >> 24) & 0xff; + extended_len[1] = (len >> 16) & 0xff; + extended_len[2] = (len >> 8) & 0xff; + extended_len[3] = len & 0xff; + _send_raw(&ws->socket, extended_len, 4); } _send_raw(&ws->socket, (const uint8_t *)text, len); char copy[len]; diff --git a/supervisor/shared/workflow.c b/supervisor/shared/workflow.c index 23532181c6..7b14c663c4 100644 --- a/supervisor/shared/workflow.c +++ b/supervisor/shared/workflow.c @@ -46,27 +46,7 @@ #endif static background_callback_t workflow_background_cb; -#if CIRCUITPY_STATUS_BAR -static void supervisor_workflow_update_status_bar(void) { - // Neighboring "" "" are concatenated by the compiler. Without this separation, the hex code - // doesn't get terminated after two following characters and the value is invalid. - // This is the OSC command to set the title and the icon text. It can be up to 255 characters - // but some may be cut off. - serial_write("\x1b" "]0;"); - serial_write("🐍 "); - #if CIRCUITPY_WEB_WORKFLOW - supervisor_web_workflow_status(); - #endif - // Send string terminator - serial_write("\x1b" "\\"); -} -#endif - static void workflow_background(void *data) { - #if CIRCUITPY_STATUS_BAR - supervisor_workflow_update_status_bar(); - #endif - #if CIRCUITPY_WEB_WORKFLOW supervisor_web_workflow_background(); #endif diff --git a/supervisor/supervisor.mk b/supervisor/supervisor.mk index 5b8cb513a7..912b5c5f37 100644 --- a/supervisor/supervisor.mk +++ b/supervisor/supervisor.mk @@ -8,12 +8,14 @@ SRC_SUPERVISOR = \ supervisor/shared/lock.c \ supervisor/shared/memory.c \ supervisor/shared/micropython.c \ + supervisor/shared/port.c \ supervisor/shared/reload.c \ supervisor/shared/safe_mode.c \ supervisor/shared/serial.c \ supervisor/shared/stack.c \ supervisor/shared/status_leds.c \ supervisor/shared/tick.c \ + supervisor/shared/title_bar.c \ supervisor/shared/traceback.c \ supervisor/shared/translate/translate.c \ supervisor/shared/workflow.c From 312e29889044f8b97494a01bb9336a582661022a Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Fri, 29 Jul 2022 11:02:35 -0700 Subject: [PATCH 31/44] Fix other ESP builds and arduino_nano_33_iot --- ports/espressif/common-hal/alarm/pin/PinAlarm.c | 8 ++------ .../espressif/common-hal/alarm/time/TimeAlarm.c | 4 ++-- .../common-hal/alarm/touch/TouchAlarm.c | 8 ++------ ports/espressif/supervisor/usb.c | 1 - supervisor/shared/title_bar.c | 17 +++++++++++++++-- 5 files changed, 21 insertions(+), 17 deletions(-) diff --git a/ports/espressif/common-hal/alarm/pin/PinAlarm.c b/ports/espressif/common-hal/alarm/pin/PinAlarm.c index 6318cc2cca..62496ec4c6 100644 --- a/ports/espressif/common-hal/alarm/pin/PinAlarm.c +++ b/ports/espressif/common-hal/alarm/pin/PinAlarm.c @@ -27,7 +27,7 @@ #include "py/runtime.h" -#include "supervisor/esp_port.h" +#include "supervisor/port.h" #include "shared-bindings/alarm/pin/PinAlarm.h" #include "shared-bindings/microcontroller/Pin.h" #include "shared-bindings/microcontroller/__init__.h" @@ -90,11 +90,7 @@ STATIC void gpio_interrupt(void *arg) { gpio_ll_intr_disable(&GPIO, 32 + i); } } - BaseType_t high_task_wakeup; - vTaskNotifyGiveFromISR(circuitpython_task, &high_task_wakeup); - if (high_task_wakeup) { - portYIELD_FROM_ISR(); - } + port_wake_main_task_from_isr(); } bool alarm_pin_pinalarm_woke_this_cycle(void) { diff --git a/ports/espressif/common-hal/alarm/time/TimeAlarm.c b/ports/espressif/common-hal/alarm/time/TimeAlarm.c index 256d96a75f..973da33c67 100644 --- a/ports/espressif/common-hal/alarm/time/TimeAlarm.c +++ b/ports/espressif/common-hal/alarm/time/TimeAlarm.c @@ -27,7 +27,7 @@ #include "esp_sleep.h" #include "py/runtime.h" -#include "supervisor/esp_port.h" +#include "supervisor/port.h" #include "components/esp_timer/include/esp_timer.h" @@ -66,7 +66,7 @@ STATIC bool woke_up = false; STATIC void timer_callback(void *arg) { (void)arg; woke_up = true; - xTaskNotifyGive(circuitpython_task); + port_wake_main_task(); } bool alarm_time_timealarm_woke_this_cycle(void) { diff --git a/ports/espressif/common-hal/alarm/touch/TouchAlarm.c b/ports/espressif/common-hal/alarm/touch/TouchAlarm.c index 02f176cbf7..fc44c1dcc0 100644 --- a/ports/espressif/common-hal/alarm/touch/TouchAlarm.c +++ b/ports/espressif/common-hal/alarm/touch/TouchAlarm.c @@ -30,7 +30,7 @@ #include "esp_sleep.h" #include "peripherals/touch.h" -#include "supervisor/esp_port.h" +#include "supervisor/port.h" static uint16_t touch_channel_mask; static volatile bool woke_up = false; @@ -86,11 +86,7 @@ mp_obj_t alarm_touch_touchalarm_create_wakeup_alarm(void) { STATIC void touch_interrupt(void *arg) { (void)arg; woke_up = true; - BaseType_t task_wakeup; - vTaskNotifyGiveFromISR(circuitpython_task, &task_wakeup); - if (task_wakeup) { - portYIELD_FROM_ISR(); - } + port_wake_main_task_from_isr(); } void alarm_touch_touchalarm_set_alarm(const bool deep_sleep, const size_t n_alarms, const mp_obj_t *alarms) { diff --git a/ports/espressif/supervisor/usb.c b/ports/espressif/supervisor/usb.c index a4f26b366c..61e6b5f09d 100644 --- a/ports/espressif/supervisor/usb.c +++ b/ports/espressif/supervisor/usb.c @@ -27,7 +27,6 @@ #include "py/runtime.h" #include "supervisor/usb.h" -#include "supervisor/esp_port.h" #include "supervisor/port.h" #include "shared/runtime/interrupt_char.h" #include "shared/readline/readline.h" diff --git a/supervisor/shared/title_bar.c b/supervisor/shared/title_bar.c index b836765ba3..7fa3116b47 100644 --- a/supervisor/shared/title_bar.c +++ b/supervisor/shared/title_bar.c @@ -40,6 +40,9 @@ static bool _forced_dirty = false; static bool _suspended = false; static void title_bar_background(void *data) { + #if !CIRCUITPY_STATUS_BAR + return; + #endif if (_suspended) { return; } @@ -53,7 +56,6 @@ static void title_bar_background(void *data) { return; } _forced_dirty = false; - #if CIRCUITPY_STATUS_BAR // Neighboring "" "" are concatenated by the compiler. Without this separation, the hex code // doesn't get terminated after two following characters and the value is invalid. // This is the OSC command to set the title and the icon text. It can be up to 255 characters @@ -67,16 +69,21 @@ static void title_bar_background(void *data) { serial_write(MICROPY_GIT_TAG); // Send string terminator serial_write("\x1b" "\\"); - #endif } void supervisor_title_bar_start(void) { + #if !CIRCUITPY_STATUS_BAR + return; + #endif title_bar_background_cb.fun = title_bar_background; title_bar_background_cb.data = NULL; supervisor_title_bar_request_update(true); } void supervisor_title_bar_request_update(bool force_dirty) { + #if !CIRCUITPY_STATUS_BAR + return; + #endif if (force_dirty) { _forced_dirty = true; } @@ -84,10 +91,16 @@ void supervisor_title_bar_request_update(bool force_dirty) { } void supervisor_title_bar_suspend(void) { + #if !CIRCUITPY_STATUS_BAR + return; + #endif _suspended = true; } void supervisor_title_bar_resume(void) { + #if !CIRCUITPY_STATUS_BAR + return; + #endif _suspended = false; supervisor_title_bar_request_update(false); } From 1348cb435bd01cf995c3f54408f2d1b570b43c34 Mon Sep 17 00:00:00 2001 From: Dan Halbert Date: Fri, 29 Jul 2022 19:07:33 -0400 Subject: [PATCH 32/44] Fix SAMD I2C frequency check --- ports/atmel-samd/common-hal/busio/I2C.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ports/atmel-samd/common-hal/busio/I2C.c b/ports/atmel-samd/common-hal/busio/I2C.c index 2ca193c99f..06d627d2e7 100644 --- a/ports/atmel-samd/common-hal/busio/I2C.c +++ b/ports/atmel-samd/common-hal/busio/I2C.c @@ -123,7 +123,7 @@ void common_hal_busio_i2c_construct(busio_i2c_obj_t *self, // The maximum frequency divisor gives a clock rate of around 48MHz/2/255 // but set_baudrate does not diagnose this problem. (This is not the // exact cutoff, but no frequency well under 100kHz is available) - if (frequency < 95000 && + if (frequency < 95000 || i2c_m_sync_set_baudrate(&self->i2c_desc, 0, frequency / 1000) != ERR_NONE) { reset_pin_number(sda->number); reset_pin_number(scl->number); From 9baa2724a79c8873358b63611179bfbfd76d640e Mon Sep 17 00:00:00 2001 From: Dan Halbert Date: Mon, 1 Aug 2022 00:27:25 -0400 Subject: [PATCH 33/44] code formatting suggestion --- ports/atmel-samd/common-hal/busio/I2C.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ports/atmel-samd/common-hal/busio/I2C.c b/ports/atmel-samd/common-hal/busio/I2C.c index 06d627d2e7..d97fa227b2 100644 --- a/ports/atmel-samd/common-hal/busio/I2C.c +++ b/ports/atmel-samd/common-hal/busio/I2C.c @@ -123,8 +123,8 @@ void common_hal_busio_i2c_construct(busio_i2c_obj_t *self, // The maximum frequency divisor gives a clock rate of around 48MHz/2/255 // but set_baudrate does not diagnose this problem. (This is not the // exact cutoff, but no frequency well under 100kHz is available) - if (frequency < 95000 || - i2c_m_sync_set_baudrate(&self->i2c_desc, 0, frequency / 1000) != ERR_NONE) { + if ((frequency < 95000) || + (i2c_m_sync_set_baudrate(&self->i2c_desc, 0, frequency / 1000) != ERR_NONE)) { reset_pin_number(sda->number); reset_pin_number(scl->number); common_hal_busio_i2c_deinit(self); From 9661d3256c00185c2cf50090945504947ea4ceee Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Fri, 29 Jul 2022 17:01:41 -0700 Subject: [PATCH 34/44] Add more ESP32 boards and enable web workflow --- locale/circuitpython.pot | 17 ++- ports/atmel-samd/boards/pybadge/board.c | 2 - .../boards/adafruit_feather_esp32_v2/board.c | 16 ++ .../mpconfigboard.mk | 3 - .../boards/adafruit_qtpy_esp32_pico/board.c | 52 +++++++ .../adafruit_qtpy_esp32_pico/mpconfigboard.h | 49 +++++++ .../adafruit_qtpy_esp32_pico/mpconfigboard.mk | 15 ++ .../boards/adafruit_qtpy_esp32_pico/pins.c | 63 ++++++++ .../boards/adafruit_qtpy_esp32_pico/sdkconfig | 52 +++++++ .../boards/hardkernel_odroid_go/board.c | 138 ++++++++++++++++++ .../hardkernel_odroid_go/mpconfigboard.h | 42 ++++++ .../hardkernel_odroid_go/mpconfigboard.mk | 15 ++ .../boards/hardkernel_odroid_go/pins.c | 10 ++ .../boards/hardkernel_odroid_go/sdkconfig | 54 +++++++ .../common-hal/microcontroller/Pin.c | 2 + .../esp-idf-config/partitions-16MB-no-uf2.csv | 9 ++ .../sdkconfig-16MB-no-uf2.defaults | 18 +++ supervisor/shared/web_workflow/web_workflow.c | 12 +- 18 files changed, 551 insertions(+), 18 deletions(-) create mode 100644 ports/espressif/boards/adafruit_qtpy_esp32_pico/board.c create mode 100644 ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h create mode 100644 ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk create mode 100644 ports/espressif/boards/adafruit_qtpy_esp32_pico/pins.c create mode 100644 ports/espressif/boards/adafruit_qtpy_esp32_pico/sdkconfig create mode 100644 ports/espressif/boards/hardkernel_odroid_go/board.c create mode 100644 ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h create mode 100644 ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk create mode 100644 ports/espressif/boards/hardkernel_odroid_go/pins.c create mode 100644 ports/espressif/boards/hardkernel_odroid_go/sdkconfig create mode 100644 ports/espressif/esp-idf-config/partitions-16MB-no-uf2.csv create mode 100644 ports/espressif/esp-idf-config/sdkconfig-16MB-no-uf2.defaults diff --git a/locale/circuitpython.pot b/locale/circuitpython.pot index 1607df3ec8..decd4816a3 100644 --- a/locale/circuitpython.pot +++ b/locale/circuitpython.pot @@ -958,10 +958,6 @@ msgstr "" msgid "Failed to connect: timeout" msgstr "" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "" @@ -1548,7 +1544,7 @@ msgstr "" msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1616,7 +1612,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3759,11 +3755,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/ports/atmel-samd/boards/pybadge/board.c b/ports/atmel-samd/boards/pybadge/board.c index b7646cabe1..17b7b180ed 100644 --- a/ports/atmel-samd/boards/pybadge/board.c +++ b/ports/atmel-samd/boards/pybadge/board.c @@ -33,8 +33,6 @@ #include "shared-module/displayio/mipi_constants.h" #include "supervisor/shared/board.h" -displayio_fourwire_obj_t board_display_obj; - #define DELAY 0x80 uint8_t display_init_sequence[] = { diff --git a/ports/espressif/boards/adafruit_feather_esp32_v2/board.c b/ports/espressif/boards/adafruit_feather_esp32_v2/board.c index 4c433a9da8..a76c5da36c 100644 --- a/ports/espressif/boards/adafruit_feather_esp32_v2/board.c +++ b/ports/espressif/boards/adafruit_feather_esp32_v2/board.c @@ -47,3 +47,19 @@ void reset_board(void) { void board_deinit(void) { } + +bool espressif_board_reset_pin_number(gpio_num_t pin_number) { + // Pull LED down on reset rather than the default up + if (pin_number == 13) { + gpio_config_t cfg = { + .pin_bit_mask = BIT64(pin_number), + .mode = GPIO_MODE_DISABLE, + .pull_up_en = false, + .pull_down_en = true, + .intr_type = GPIO_INTR_DISABLE, + }; + gpio_config(&cfg); + return true; + } + return false; +} diff --git a/ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.mk b/ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.mk index f25eda463f..21a87a9456 100644 --- a/ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.mk +++ b/ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.mk @@ -10,9 +10,6 @@ LONGINT_IMPL = MPZ # so increase it to 32. CFLAGS += -DCFG_TUD_TASK_QUEUE_SZ=32 -CIRCUITPY_STATUS_BAR = 0 -CIRCUITPY_WEB_WORKFLOW = 0 - CIRCUITPY_ESP_FLASH_MODE = dio CIRCUITPY_ESP_FLASH_FREQ = 40m CIRCUITPY_ESP_FLASH_SIZE = 8MB diff --git a/ports/espressif/boards/adafruit_qtpy_esp32_pico/board.c b/ports/espressif/boards/adafruit_qtpy_esp32_pico/board.c new file mode 100644 index 0000000000..0eca2f0969 --- /dev/null +++ b/ports/espressif/boards/adafruit_qtpy_esp32_pico/board.c @@ -0,0 +1,52 @@ +/* + * This file is part of the MicroPython project, http://micropython.org/ + * + * The MIT License (MIT) + * + * Copyright (c) 2020 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 "supervisor/board.h" +#include "mpconfigboard.h" +#include "shared-bindings/microcontroller/Pin.h" +#include "components/driver/include/driver/gpio.h" +#include "components/hal/include/hal/gpio_hal.h" +#include "common-hal/microcontroller/Pin.h" + +void board_init(void) { + reset_board(); +} + +bool board_requests_safe_mode(void) { + return false; +} + +void reset_board(void) { + // Turn on NeoPixel power by default. + gpio_set_direction(8, GPIO_MODE_DEF_OUTPUT); + gpio_set_level(8, true); +} + +void board_deinit(void) { + // Turn off NeoPixel + gpio_set_direction(8, GPIO_MODE_DEF_OUTPUT); + gpio_set_level(8, false); +} diff --git a/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h b/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h new file mode 100644 index 0000000000..42a575aa68 --- /dev/null +++ b/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h @@ -0,0 +1,49 @@ +/* + * This file is part of the MicroPython project, http://micropython.org/ + * + * The MIT License (MIT) + * + * Copyright (c) 2022 Dan Halbert 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. + */ + +#define MICROPY_HW_BOARD_NAME "Adafruit QT Py ESP32 PICO" +#define MICROPY_HW_MCU_NAME "ESP32" + +#define MICROPY_HW_NEOPIXEL (&pin_GPIO5) + +#define CIRCUITPY_BOARD_I2C (2) +#define CIRCUITPY_BOARD_I2C_PIN {{.scl = &pin_GPIO33, .sda = &pin_GPIO4}, \ + {.scl = &pin_GPIO19, .sda = &pin_GPIO22}} + +#define CIRCUITPY_BOARD_SPI (1) +#define CIRCUITPY_BOARD_SPI_PIN {{.clock = &pin_GPIO14, .mosi = &pin_GPIO13, .miso = &pin_GPIO12}} + +#define CIRCUITPY_BOARD_UART (1) +#define CIRCUITPY_BOARD_UART_PIN {{.tx = &pin_GPIO32, .rx = &pin_GPIO7}} + +#define CIRCUITPY_BOOT_BUTTON (&pin_GPIO0) + +// Explanation of how a user got into safe mode +#define BOARD_USER_SAFE_MODE_ACTION translate("pressing BOOT button at start up.\n") + +// UART pins attached to the USB-serial converter chip +#define CIRCUITPY_CONSOLE_UART_TX (&pin_GPIO1) +#define CIRCUITPY_CONSOLE_UART_RX (&pin_GPIO3) diff --git a/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk b/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk new file mode 100644 index 0000000000..53d7f109c1 --- /dev/null +++ b/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk @@ -0,0 +1,15 @@ +CIRCUITPY_CREATOR_ID = 0x0000239A +CIRCUITPY_CREATION_ID = 0x00320002 + +IDF_TARGET = esp32 + +INTERNAL_FLASH_FILESYSTEM = 1 +LONGINT_IMPL = MPZ + +# The default queue depth of 16 overflows on release builds, +# so increase it to 32. +CFLAGS += -DCFG_TUD_TASK_QUEUE_SZ=32 + +CIRCUITPY_ESP_FLASH_MODE = dio +CIRCUITPY_ESP_FLASH_FREQ = 40m +CIRCUITPY_ESP_FLASH_SIZE = 8MB diff --git a/ports/espressif/boards/adafruit_qtpy_esp32_pico/pins.c b/ports/espressif/boards/adafruit_qtpy_esp32_pico/pins.c new file mode 100644 index 0000000000..5d760603c1 --- /dev/null +++ b/ports/espressif/boards/adafruit_qtpy_esp32_pico/pins.c @@ -0,0 +1,63 @@ +#include "shared-bindings/board/__init__.h" + +CIRCUITPY_BOARD_BUS_SINGLETON(stemma_i2c, i2c, 1) + +STATIC const mp_rom_map_elem_t board_module_globals_table[] = { + CIRCUITPYTHON_BOARD_DICT_STANDARD_ITEMS + + { MP_ROM_QSTR(MP_QSTR_BUTTON), MP_ROM_PTR(&pin_GPIO0) }, + { MP_ROM_QSTR(MP_QSTR_BOOT0), MP_ROM_PTR(&pin_GPIO0) }, + { MP_ROM_QSTR(MP_QSTR_D0), MP_ROM_PTR(&pin_GPIO0) }, + + { MP_ROM_QSTR(MP_QSTR_A0), MP_ROM_PTR(&pin_GPIO26) }, + { MP_ROM_QSTR(MP_QSTR_D18), MP_ROM_PTR(&pin_GPIO26) }, + + { MP_ROM_QSTR(MP_QSTR_A1), MP_ROM_PTR(&pin_GPIO25) }, + { MP_ROM_QSTR(MP_QSTR_D17), MP_ROM_PTR(&pin_GPIO25) }, + + { MP_ROM_QSTR(MP_QSTR_A2), MP_ROM_PTR(&pin_GPIO27) }, + { MP_ROM_QSTR(MP_QSTR_D9), MP_ROM_PTR(&pin_GPIO27) }, + + { MP_ROM_QSTR(MP_QSTR_A3), MP_ROM_PTR(&pin_GPIO15) }, + { MP_ROM_QSTR(MP_QSTR_D8), MP_ROM_PTR(&pin_GPIO15) }, + + { MP_ROM_QSTR(MP_QSTR_SDA), MP_ROM_PTR(&pin_GPIO4) }, + { MP_ROM_QSTR(MP_QSTR_D7), MP_ROM_PTR(&pin_GPIO4) }, + { MP_ROM_QSTR(MP_QSTR_A4), MP_ROM_PTR(&pin_GPIO4) }, + + { MP_ROM_QSTR(MP_QSTR_SCL), MP_ROM_PTR(&pin_GPIO33) }, + { MP_ROM_QSTR(MP_QSTR_D6), MP_ROM_PTR(&pin_GPIO33) }, + { MP_ROM_QSTR(MP_QSTR_A5), MP_ROM_PTR(&pin_GPIO33) }, + + { MP_ROM_QSTR(MP_QSTR_TX), MP_ROM_PTR(&pin_GPIO32) }, + { MP_ROM_QSTR(MP_QSTR_D5), MP_ROM_PTR(&pin_GPIO32) }, + { MP_ROM_QSTR(MP_QSTR_A6), MP_ROM_PTR(&pin_GPIO32) }, + + { MP_ROM_QSTR(MP_QSTR_RX), MP_ROM_PTR(&pin_GPIO7) }, + { MP_ROM_QSTR(MP_QSTR_D16), MP_ROM_PTR(&pin_GPIO7) }, + { MP_ROM_QSTR(MP_QSTR_A7), MP_ROM_PTR(&pin_GPIO7) }, + + { MP_ROM_QSTR(MP_QSTR_MOSI), MP_ROM_PTR(&pin_GPIO13) }, + { MP_ROM_QSTR(MP_QSTR_D35), MP_ROM_PTR(&pin_GPIO13) }, + + { MP_ROM_QSTR(MP_QSTR_SCK), MP_ROM_PTR(&pin_GPIO14) }, + { MP_ROM_QSTR(MP_QSTR_D36), MP_ROM_PTR(&pin_GPIO14) }, + + { MP_ROM_QSTR(MP_QSTR_MISO), MP_ROM_PTR(&pin_GPIO12) }, + { MP_ROM_QSTR(MP_QSTR_D37), MP_ROM_PTR(&pin_GPIO12) }, + + { MP_ROM_QSTR(MP_QSTR_NEOPIXEL_POWER), MP_ROM_PTR(&pin_GPIO8) }, + { MP_ROM_QSTR(MP_QSTR_NEOPIXEL), MP_ROM_PTR(&pin_GPIO5) }, + + { MP_ROM_QSTR(MP_QSTR_SCL1), MP_ROM_PTR(&pin_GPIO19) }, + { MP_ROM_QSTR(MP_QSTR_D40), MP_ROM_PTR(&pin_GPIO19) }, + + { MP_ROM_QSTR(MP_QSTR_SDA1), MP_ROM_PTR(&pin_GPIO22) }, + { MP_ROM_QSTR(MP_QSTR_D41), MP_ROM_PTR(&pin_GPIO22) }, + + { MP_ROM_QSTR(MP_QSTR_I2C), MP_ROM_PTR(&board_i2c_obj) }, + { MP_ROM_QSTR(MP_QSTR_STEMMA_I2C), MP_ROM_PTR(&board_stemma_i2c_obj) }, + { MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_spi_obj) }, + { MP_ROM_QSTR(MP_QSTR_UART), MP_ROM_PTR(&board_uart_obj) }, +}; +MP_DEFINE_CONST_DICT(board_module_globals, board_module_globals_table); diff --git a/ports/espressif/boards/adafruit_qtpy_esp32_pico/sdkconfig b/ports/espressif/boards/adafruit_qtpy_esp32_pico/sdkconfig new file mode 100644 index 0000000000..f2e8085d3e --- /dev/null +++ b/ports/espressif/boards/adafruit_qtpy_esp32_pico/sdkconfig @@ -0,0 +1,52 @@ +# +# Partition Table +# +CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="esp-idf-config/partitions-8MB-no-uf2.csv" +CONFIG_PARTITION_TABLE_FILENAME="esp-idf-config/partitions-8MB-no-uf2.csv" +# end of Partition Table + +# +# SPI RAM config +# +# CONFIG_SPIRAM_TYPE_AUTO is not set +CONFIG_SPIRAM_TYPE_ESPPSRAM16=y +# CONFIG_SPIRAM_TYPE_ESPPSRAM32 is not set +# CONFIG_SPIRAM_TYPE_ESPPSRAM64 is not set +CONFIG_SPIRAM_SIZE=2097152 +CONFIG_SPIRAM_SPEED_40M=y +CONFIG_SPIRAM=y +CONFIG_SPIRAM_BOOT_INIT=y +CONFIG_SPIRAM_IGNORE_NOTFOUND=y +CONFIG_SPIRAM_USE_MEMMAP=y +# CONFIG_SPIRAM_USE_CAPS_ALLOC is not set +# CONFIG_SPIRAM_USE_MALLOC is not set +CONFIG_SPIRAM_MEMTEST=y +# CONFIG_SPIRAM_ALLOW_BSS_SEG_EXTERNAL_MEMORY is not set +# CONFIG_SPIRAM_ALLOW_NOINIT_SEG_EXTERNAL_MEMORY is not set +CONFIG_SPIRAM_CACHE_WORKAROUND=y + +# +# SPI RAM config +# +CONFIG_ESP32_SPIRAM_SUPPORT=y +# CONFIG_SPIRAM_TYPE_AUTO is not set +# CONFIG_SPIRAM_TYPE_ESPPSRAM32 is not set +# CONFIG_SPIRAM_TYPE_ESPPSRAM64 is not set + +### # Uncomment to send log output to TX/RX pins on Feather ESP32V2 +### # +### # ESP System Settings +### # +### CONFIG_ESP_SYSTEM_PANIC_PRINT_HALT=y +### # CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT is not set +### CONFIG_ESP_CONSOLE_UART_CUSTOM=y +### # CONFIG_ESP_CONSOLE_NONE is not set +### CONFIG_ESP_CONSOLE_UART=y +### CONFIG_ESP_CONSOLE_UART_CUSTOM_NUM_0=y +### # CONFIG_ESP_CONSOLE_UART_CUSTOM_NUM_1 is not set +### CONFIG_ESP_CONSOLE_UART_NUM=0 +### CONFIG_ESP_CONSOLE_UART_TX_GPIO=8 +### CONFIG_ESP_CONSOLE_UART_RX_GPIO=7 +### CONFIG_ESP_CONSOLE_UART_BAUDRATE=115200 +### # CONFIG_ESP_SYSTEM_CHECK_INT_LEVEL_5 is not set +### # end of ESP System Settings diff --git a/ports/espressif/boards/hardkernel_odroid_go/board.c b/ports/espressif/boards/hardkernel_odroid_go/board.c new file mode 100644 index 0000000000..eff481e63d --- /dev/null +++ b/ports/espressif/boards/hardkernel_odroid_go/board.c @@ -0,0 +1,138 @@ +/* + * This file is part of the MicroPython project, http://micropython.org/ + * + * The MIT License (MIT) + * + * Copyright (c) 2020 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 "supervisor/board.h" +#include "mpconfigboard.h" +#include "shared-bindings/busio/SPI.h" +#include "shared-bindings/displayio/FourWire.h" +#include "shared-module/displayio/__init__.h" +#include "shared-module/displayio/mipi_constants.h" + +#include "common-hal/microcontroller/Pin.h" + +#define DELAY 0x80 + +uint8_t display_init_sequence[] = { + 0x0f, 3, 0x03, 0x80, 0x02, // RDDSDR + 0xcf, 3, 0x00, 0xcf, 0x30, // PWCRTLB + 0xed, 4, 0x64, 0x03, 0x12, 0x81, // PWRONCTRL, b"\x64\x03\x12\x81"), + 0xe8, 3, 0x85, 0x00, 0x78, // (_DTCTRLA, b"\x85\x00\x78"), + 0xcb, 5, 0x39, 0x2c, 0x00, 0x34, 0x02, // (_PWCTRLA, b"\x39\x2c\x00\x34\x02"), + 0xf7, 1, 0x20, // (_PRCTRL, b"\x20"), + 0xea, 2, 0x00, 0x00, // (_DTCTRLB, b"\x00\x00"), + 0xc0, 1, 0x1b, // (_PWCTRL1, b"\x1b"), + 0xc1, 1, 0x12, // (_PWCTRL2, b"\x12"), + 0xc5, 2, 0x3e, 0x3c, // (_VMCTRL1, b"\x3e\x3c"), + 0xc7, 1, 0x91, // (_VMCTRL2, b"\x91"), + 0x36, 1, 0xa8, // (_MADCTL, b"\xa8"), + 0x3a, 1, 0x55, // (_PIXSET, b"\x55"), + 0xb1, 2, 0x00, 0x1b, // (_FRMCTR1, b"\x00\x1b"), + 0xb6, 3, 0x0a, 0xa2, 0x27, // (_DISCTRL, b"\x0a\xa2\x27"), + 0xf6, 2, 0x01, 0x30, // (_INTFACE, b"\x01\x30"), + 0xf2, 1, 0x00, // (_ENA3G, b"\x00"), + 0x26, 1, 0x01, // (_GAMSET, b"\x01"), + 0xe0, 15, 0x0f, 0x31, 0x2b, 0x0c, 0x0e, 0x08, 0x4e, 0xf1, 0x37, 0x07, 0x10, 0x03, 0x0e, 0x09, 0x00, + // (_PGAMCTRL, b"\x0f\x31\x2b\x0c\x0e\x08\x4e\xf1\x37\x07\x10\x03\x0e\x09\x00"), + 0xe1, 15, 0x00, 0x0e, 0x14, 0x03, 0x11, 0x07, 0x31, 0xc1, 0x48, 0x08, 0x0f, 0x0c, 0x31, 0x36, 0x0f, + // (_NGAMCTRL, b"\x00\x0e\x14\x03\x11\x07\x31\xc1\x48\x08\x0f\x0c\x31\x36\x0f")): + 0x11, 0 | DELAY, 10, // _SLPOUT + 0x29, 0 | DELAY, 100, // _DISPON +}; + +void board_init(void) { + busio_spi_obj_t *spi = &displays[0].fourwire_bus.inline_bus; + common_hal_busio_spi_construct(spi, &pin_GPIO18, &pin_GPIO23, NULL, false); + common_hal_busio_spi_never_reset(spi); + + displayio_fourwire_obj_t *bus = &displays[0].fourwire_bus; + bus->base.type = &displayio_fourwire_type; + common_hal_displayio_fourwire_construct(bus, + spi, + &pin_GPIO21, // TFT_DC Command or data + &pin_GPIO5, // TFT_CS Chip select + NULL, // TFT_RST Reset + 40000000, // Baudrate + 0, // Polarity + 0); // Phase + + displayio_display_obj_t *display = &displays[0].display; + display->base.type = &displayio_display_type; + common_hal_displayio_display_construct(display, + bus, + 320, // Width (after rotation) + 240, // Height (after rotation) + 0, // column start + 0, // row start + 0, // rotation + 16, // Color depth + false, // grayscale + false, // pixels in byte share row. only used for depth < 8 + 1, // bytes per cell. Only valid for depths < 8 + false, // reverse_pixels_in_byte. Only valid for depths < 8 + true, // reverse_pixels_in_word + MIPI_COMMAND_SET_COLUMN_ADDRESS, // Set column command + MIPI_COMMAND_SET_PAGE_ADDRESS, // Set row command + MIPI_COMMAND_WRITE_MEMORY_START, // Write memory command + display_init_sequence, + sizeof(display_init_sequence), + &pin_GPIO14, // backlight pin + NO_BRIGHTNESS_COMMAND, + 1.0f, // brightness (ignored) + true, // auto_brightness + false, // single_byte_bounds + false, // data_as_commands + true, // auto_refresh + 60, // native_frames_per_second + true, // backlight_on_high + false, // SH1107_addressing + 50000); // backlight pwm frequency +} + +bool board_requests_safe_mode(void) { + return false; +} + +void reset_board(void) { +} + +void board_deinit(void) { +} + +bool espressif_board_reset_pin_number(gpio_num_t pin_number) { + // Pull LED down on reset rather than the default up + if (pin_number == 2) { + gpio_config_t cfg = { + .pin_bit_mask = BIT64(pin_number), + .mode = GPIO_MODE_DISABLE, + .pull_up_en = false, + .pull_down_en = true, + .intr_type = GPIO_INTR_DISABLE, + }; + gpio_config(&cfg); + return true; + } + return false; +} diff --git a/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h b/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h new file mode 100644 index 0000000000..423890f2e1 --- /dev/null +++ b/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h @@ -0,0 +1,42 @@ +/* + * This file is part of the MicroPython project, http://micropython.org/ + * + * The MIT License (MIT) + * + * Copyright (c) 2022 Dan Halbert 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. + */ + +#define MICROPY_HW_BOARD_NAME "Hardkernel Odroid Go" +#define MICROPY_HW_MCU_NAME "ESP32" + +#define MICROPY_HW_LED_STATUS (&pin_GPIO2) + +#define CIRCUITPY_BOARD_SPI (1) +#define CIRCUITPY_BOARD_SPI_PIN {{.clock = &pin_GPIO18, .mosi = &pin_GPIO23, .miso = &pin_GPIO19}} + +#define CIRCUITPY_BOOT_BUTTON (&pin_GPIO0) + +// Explanation of how a user got into safe mode +#define BOARD_USER_SAFE_MODE_ACTION translate("pressing VOLUME button at start up.\n") + +// UART pins attached to the USB-serial converter chip +#define CIRCUITPY_CONSOLE_UART_TX (&pin_GPIO1) +#define CIRCUITPY_CONSOLE_UART_RX (&pin_GPIO3) diff --git a/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk b/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk new file mode 100644 index 0000000000..1e08a80972 --- /dev/null +++ b/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk @@ -0,0 +1,15 @@ +CIRCUITPY_CREATOR_ID = 0x0000239A +CIRCUITPY_CREATION_ID = 0x00320002 + +IDF_TARGET = esp32 + +INTERNAL_FLASH_FILESYSTEM = 1 +LONGINT_IMPL = MPZ + +# The default queue depth of 16 overflows on release builds, +# so increase it to 32. +CFLAGS += -DCFG_TUD_TASK_QUEUE_SZ=32 + +CIRCUITPY_ESP_FLASH_MODE = dio +CIRCUITPY_ESP_FLASH_FREQ = 40m +CIRCUITPY_ESP_FLASH_SIZE = 16MB diff --git a/ports/espressif/boards/hardkernel_odroid_go/pins.c b/ports/espressif/boards/hardkernel_odroid_go/pins.c new file mode 100644 index 0000000000..4d4ff5258e --- /dev/null +++ b/ports/espressif/boards/hardkernel_odroid_go/pins.c @@ -0,0 +1,10 @@ +#include "shared-bindings/board/__init__.h" + +STATIC const mp_rom_map_elem_t board_module_globals_table[] = { + CIRCUITPYTHON_BOARD_DICT_STANDARD_ITEMS + + { MP_ROM_QSTR(MP_QSTR_BTN_VOLUME), MP_ROM_PTR(&pin_GPIO0) }, + + { MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_spi_obj) }, +}; +MP_DEFINE_CONST_DICT(board_module_globals, board_module_globals_table); diff --git a/ports/espressif/boards/hardkernel_odroid_go/sdkconfig b/ports/espressif/boards/hardkernel_odroid_go/sdkconfig new file mode 100644 index 0000000000..f220cff390 --- /dev/null +++ b/ports/espressif/boards/hardkernel_odroid_go/sdkconfig @@ -0,0 +1,54 @@ +# +# Partition Table +# +CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="esp-idf-config/partitions-16MB-no-uf2.csv" +CONFIG_PARTITION_TABLE_FILENAME="esp-idf-config/partitions-16MB-no-uf2.csv" +# end of Partition Table + +CONFIG_ESP_INT_WDT_TIMEOUT_MS=3000 + +# +# SPI RAM config +# +# CONFIG_SPIRAM_TYPE_AUTO is not set +# CONFIG_SPIRAM_TYPE_ESPPSRAM16 is not set +CONFIG_SPIRAM_TYPE_ESPPSRAM32=y +# CONFIG_SPIRAM_TYPE_ESPPSRAM64 is not set +CONFIG_SPIRAM_SIZE=4194304 +CONFIG_SPIRAM_SPEED_40M=y +CONFIG_SPIRAM=y +CONFIG_SPIRAM_BOOT_INIT=y +CONFIG_SPIRAM_IGNORE_NOTFOUND=y +CONFIG_SPIRAM_USE_MEMMAP=y +# CONFIG_SPIRAM_USE_CAPS_ALLOC is not set +# CONFIG_SPIRAM_USE_MALLOC is not set +CONFIG_SPIRAM_MEMTEST=y +# CONFIG_SPIRAM_ALLOW_BSS_SEG_EXTERNAL_MEMORY is not set +# CONFIG_SPIRAM_ALLOW_NOINIT_SEG_EXTERNAL_MEMORY is not set +CONFIG_SPIRAM_CACHE_WORKAROUND=y + +# +# SPI RAM config +# +CONFIG_ESP32_SPIRAM_SUPPORT=y +# CONFIG_SPIRAM_TYPE_AUTO is not set +# CONFIG_SPIRAM_TYPE_ESPPSRAM32 is not set +# CONFIG_SPIRAM_TYPE_ESPPSRAM64 is not set + +### # Uncomment to send log output to TX/RX pins on Feather ESP32V2 +### # +### # ESP System Settings +### # +CONFIG_ESP_SYSTEM_PANIC_PRINT_HALT=y +### # CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT is not set +CONFIG_ESP_CONSOLE_UART_CUSTOM=y +### # CONFIG_ESP_CONSOLE_NONE is not set +CONFIG_ESP_CONSOLE_UART=y +CONFIG_ESP_CONSOLE_UART_CUSTOM_NUM_0=y +### # CONFIG_ESP_CONSOLE_UART_CUSTOM_NUM_1 is not set +CONFIG_ESP_CONSOLE_UART_NUM=0 +CONFIG_ESP_CONSOLE_UART_TX_GPIO=12 +CONFIG_ESP_CONSOLE_UART_RX_GPIO=15 +CONFIG_ESP_CONSOLE_UART_BAUDRATE=115200 +### # CONFIG_ESP_SYSTEM_CHECK_INT_LEVEL_5 is not set +### # end of ESP System Settings diff --git a/ports/espressif/common-hal/microcontroller/Pin.c b/ports/espressif/common-hal/microcontroller/Pin.c index 201fa0ac2b..6e733b9095 100644 --- a/ports/espressif/common-hal/microcontroller/Pin.c +++ b/ports/espressif/common-hal/microcontroller/Pin.c @@ -48,6 +48,8 @@ static const uint64_t pin_mask_reset_forbidden = GPIO_SEL_3 | // RXD0 // Never ever reset pins used to communicate with SPI flash and PSRAM. GPIO_SEL_6 | // CLK + GPIO_SEL_7 | + GPIO_SEL_8 | GPIO_SEL_9 | // (PSRAM) SD2 GPIO_SEL_10 | // (PSRAM) SD3 GPIO_SEL_11 | // CMD diff --git a/ports/espressif/esp-idf-config/partitions-16MB-no-uf2.csv b/ports/espressif/esp-idf-config/partitions-16MB-no-uf2.csv new file mode 100644 index 0000000000..8e73e8d056 --- /dev/null +++ b/ports/espressif/esp-idf-config/partitions-16MB-no-uf2.csv @@ -0,0 +1,9 @@ +# ESP-IDF Partition Table +# Name, Type, SubType, Offset, Size, Flags +# bootloader.bin,, 0x1000, 32K +# partition table,, 0x8000, 4K +nvs, data, nvs, 0x9000, 20K, +otadata, data, ota, 0xe000, 8K, +ota_0, 0, ota_0, 0x10000, 2048K, +ota_1, 0, ota_1, 0x210000, 2048K, +user_fs, data, fat, 0x410000, 12224K, diff --git a/ports/espressif/esp-idf-config/sdkconfig-16MB-no-uf2.defaults b/ports/espressif/esp-idf-config/sdkconfig-16MB-no-uf2.defaults new file mode 100644 index 0000000000..6065abcd93 --- /dev/null +++ b/ports/espressif/esp-idf-config/sdkconfig-16MB-no-uf2.defaults @@ -0,0 +1,18 @@ +# +# Serial flasher config +# +# CONFIG_ESPTOOLPY_FLASHSIZE_1MB is not set +# CONFIG_ESPTOOLPY_FLASHSIZE_2MB is not set +# CONFIG_ESPTOOLPY_FLASHSIZE_4MB is not set +# CONFIG_ESPTOOLPY_FLASHSIZE_8MB is not set +CONFIG_ESPTOOLPY_FLASHSIZE_16MB=y +CONFIG_ESPTOOLPY_FLASHSIZE="16MB" +CONFIG_ESPTOOLPY_FLASHSIZE_DETECT=y +# end of Serial flasher config + +CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="esp-idf-config/partitions-16MB-no-uf2.csv" +# +# Partition Table +# +CONFIG_PARTITION_TABLE_FILENAME="esp-idf-config/partitions-16MB-no-uf2.csv" +# end of Partition Table diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 0f92f635a4..2906b4492c 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -622,18 +622,16 @@ static void _reply_directory_json(socketpool_socket_obj_t *socket, _request *req // LittleFS. _send_chunk(socket, ", "); - uint64_t truncated_time = timeutils_mktime(1980 + (file_info.fdate >> 9), + uint32_t truncated_time = timeutils_mktime(1980 + (file_info.fdate >> 9), (file_info.fdate >> 5) & 0xf, file_info.fdate & 0x1f, file_info.ftime >> 11, (file_info.ftime >> 5) & 0x1f, - (file_info.ftime & 0x1f) * 2) * 1000000000ULL; + (file_info.ftime & 0x1f) * 2); - // Use snprintf because mp_printf doesn't support 64 bit numbers by - // default. - char encoded_time[32]; - snprintf(encoded_time, sizeof(encoded_time), "%llu", truncated_time); - mp_printf(&_socket_print, "\"modified_ns\": %s, ", encoded_time); + // Manually append zeros to make the time nanoseconds. Support for printing 64 bit numbers + // varies across chipsets. + mp_printf(&_socket_print, "\"modified_ns\": %lu000000000, ", truncated_time); size_t file_size = 0; if ((file_info.fattrib & AM_DIR) == 0) { file_size = file_info.fsize; From f0c6a8c49a3702aba4b41a4bb9c22d3e09e2247b Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Mon, 1 Aug 2022 15:52:01 -0700 Subject: [PATCH 35/44] Odroid pin defs --- .../boards/hardkernel_odroid_go/board.c | 44 ++++++++--------- .../hardkernel_odroid_go/mpconfigboard.mk | 4 +- .../boards/hardkernel_odroid_go/pins.c | 47 +++++++++++++++++++ 3 files changed, 71 insertions(+), 24 deletions(-) diff --git a/ports/espressif/boards/hardkernel_odroid_go/board.c b/ports/espressif/boards/hardkernel_odroid_go/board.c index eff481e63d..2249adeacd 100644 --- a/ports/espressif/boards/hardkernel_odroid_go/board.c +++ b/ports/espressif/boards/hardkernel_odroid_go/board.c @@ -35,31 +35,31 @@ #define DELAY 0x80 +// ILI9341 init sequence from: +// https://github.com/hardkernel/ODROID-GO-MicroPython/blob/loboris/odroid_go/utils/lcd/lcd.py#L55 uint8_t display_init_sequence[] = { 0x0f, 3, 0x03, 0x80, 0x02, // RDDSDR 0xcf, 3, 0x00, 0xcf, 0x30, // PWCRTLB - 0xed, 4, 0x64, 0x03, 0x12, 0x81, // PWRONCTRL, b"\x64\x03\x12\x81"), - 0xe8, 3, 0x85, 0x00, 0x78, // (_DTCTRLA, b"\x85\x00\x78"), - 0xcb, 5, 0x39, 0x2c, 0x00, 0x34, 0x02, // (_PWCTRLA, b"\x39\x2c\x00\x34\x02"), - 0xf7, 1, 0x20, // (_PRCTRL, b"\x20"), - 0xea, 2, 0x00, 0x00, // (_DTCTRLB, b"\x00\x00"), - 0xc0, 1, 0x1b, // (_PWCTRL1, b"\x1b"), - 0xc1, 1, 0x12, // (_PWCTRL2, b"\x12"), - 0xc5, 2, 0x3e, 0x3c, // (_VMCTRL1, b"\x3e\x3c"), - 0xc7, 1, 0x91, // (_VMCTRL2, b"\x91"), - 0x36, 1, 0xa8, // (_MADCTL, b"\xa8"), - 0x3a, 1, 0x55, // (_PIXSET, b"\x55"), - 0xb1, 2, 0x00, 0x1b, // (_FRMCTR1, b"\x00\x1b"), - 0xb6, 3, 0x0a, 0xa2, 0x27, // (_DISCTRL, b"\x0a\xa2\x27"), - 0xf6, 2, 0x01, 0x30, // (_INTFACE, b"\x01\x30"), - 0xf2, 1, 0x00, // (_ENA3G, b"\x00"), - 0x26, 1, 0x01, // (_GAMSET, b"\x01"), - 0xe0, 15, 0x0f, 0x31, 0x2b, 0x0c, 0x0e, 0x08, 0x4e, 0xf1, 0x37, 0x07, 0x10, 0x03, 0x0e, 0x09, 0x00, - // (_PGAMCTRL, b"\x0f\x31\x2b\x0c\x0e\x08\x4e\xf1\x37\x07\x10\x03\x0e\x09\x00"), - 0xe1, 15, 0x00, 0x0e, 0x14, 0x03, 0x11, 0x07, 0x31, 0xc1, 0x48, 0x08, 0x0f, 0x0c, 0x31, 0x36, 0x0f, - // (_NGAMCTRL, b"\x00\x0e\x14\x03\x11\x07\x31\xc1\x48\x08\x0f\x0c\x31\x36\x0f")): - 0x11, 0 | DELAY, 10, // _SLPOUT - 0x29, 0 | DELAY, 100, // _DISPON + 0xed, 4, 0x64, 0x03, 0x12, 0x81, // PWRONCTRL + 0xe8, 3, 0x85, 0x00, 0x78, // DTCTRLA + 0xcb, 5, 0x39, 0x2c, 0x00, 0x34, 0x02, // PWCTRLA + 0xf7, 1, 0x20, // PRCTRL + 0xea, 2, 0x00, 0x00, // DTCTRLB + 0xc0, 1, 0x1b, // PWCTRL1 + 0xc1, 1, 0x12, // PWCTRL2 + 0xc5, 2, 0x3e, 0x3c, // VMCTRL1 + 0xc7, 1, 0x91, // VMCTRL2 + 0x36, 1, 0xa8, // MADCTL + 0x3a, 1, 0x55, // PIXSET + 0xb1, 2, 0x00, 0x1b, // FRMCTR1 + 0xb6, 3, 0x0a, 0xa2, 0x27, // DISCTRL + 0xf6, 2, 0x01, 0x30, // INTFACE + 0xf2, 1, 0x00, // ENA3G + 0x26, 1, 0x01, // GAMSET + 0xe0, 15, 0x0f, 0x31, 0x2b, 0x0c, 0x0e, 0x08, 0x4e, 0xf1, 0x37, 0x07, 0x10, 0x03, 0x0e, 0x09, 0x00, // PGAMCTRL + 0xe1, 15, 0x00, 0x0e, 0x14, 0x03, 0x11, 0x07, 0x31, 0xc1, 0x48, 0x08, 0x0f, 0x0c, 0x31, 0x36, 0x0f, // NGAMCTRL + 0x11, 0 | DELAY, 10, // SLPOUT + 0x29, 0 | DELAY, 100, // DISPON }; void board_init(void) { diff --git a/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk b/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk index 1e08a80972..80cd6cd11c 100644 --- a/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk +++ b/ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.mk @@ -1,5 +1,5 @@ -CIRCUITPY_CREATOR_ID = 0x0000239A -CIRCUITPY_CREATION_ID = 0x00320002 +CIRCUITPY_CREATOR_ID = 0x0D10D000 +CIRCUITPY_CREATION_ID = 0x00320060 IDF_TARGET = esp32 diff --git a/ports/espressif/boards/hardkernel_odroid_go/pins.c b/ports/espressif/boards/hardkernel_odroid_go/pins.c index 4d4ff5258e..c7152bf365 100644 --- a/ports/espressif/boards/hardkernel_odroid_go/pins.c +++ b/ports/espressif/boards/hardkernel_odroid_go/pins.c @@ -1,10 +1,57 @@ #include "shared-bindings/board/__init__.h" +// Pin names from: https://wiki.odroid.com/odroid_go/odroid_go + STATIC const mp_rom_map_elem_t board_module_globals_table[] = { CIRCUITPYTHON_BOARD_DICT_STANDARD_ITEMS + // Left side + { MP_ROM_QSTR(MP_QSTR_BATTERY), MP_ROM_PTR(&pin_GPIO36) }, + + { MP_ROM_QSTR(MP_QSTR_BTN_START), MP_ROM_PTR(&pin_GPIO39) }, + + { MP_ROM_QSTR(MP_QSTR_BTN_AXIS_X), MP_ROM_PTR(&pin_GPIO34) }, + + { MP_ROM_QSTR(MP_QSTR_BTN_AXIS_Y), MP_ROM_PTR(&pin_GPIO35) }, + + { MP_ROM_QSTR(MP_QSTR_BTN_A), MP_ROM_PTR(&pin_GPIO32) }, + + { MP_ROM_QSTR(MP_QSTR_BTN_B), MP_ROM_PTR(&pin_GPIO33) }, + + { MP_ROM_QSTR(MP_QSTR_SPEAKER_IN_M), MP_ROM_PTR(&pin_GPIO25) }, + + { MP_ROM_QSTR(MP_QSTR_SPEAKER_IN_P), MP_ROM_PTR(&pin_GPIO26) }, + + { MP_ROM_QSTR(MP_QSTR_BTN_SELECT), MP_ROM_PTR(&pin_GPIO27) }, + + { MP_ROM_QSTR(MP_QSTR_BACKLIGHT_PWM), MP_ROM_PTR(&pin_GPIO14) }, + + { MP_ROM_QSTR(MP_QSTR_EXT3), MP_ROM_PTR(&pin_GPIO12) }, + + { MP_ROM_QSTR(MP_QSTR_BTN_MENU), MP_ROM_PTR(&pin_GPIO13) }, + + // Right side. + { MP_ROM_QSTR(MP_QSTR_MOSI), MP_ROM_PTR(&pin_GPIO23) }, + { MP_ROM_QSTR(MP_QSTR_EXT8), MP_ROM_PTR(&pin_GPIO23) }, + + { MP_ROM_QSTR(MP_QSTR_SD_CS), MP_ROM_PTR(&pin_GPIO22) }, + + { MP_ROM_QSTR(MP_QSTR_MISO), MP_ROM_PTR(&pin_GPIO19) }, + { MP_ROM_QSTR(MP_QSTR_EXT7), MP_ROM_PTR(&pin_GPIO19) }, + + { MP_ROM_QSTR(MP_QSTR_SCK), MP_ROM_PTR(&pin_GPIO18) }, + { MP_ROM_QSTR(MP_QSTR_EXT2), MP_ROM_PTR(&pin_GPIO18) }, + + { MP_ROM_QSTR(MP_QSTR_LCD_CS), MP_ROM_PTR(&pin_GPIO5) }, + + { MP_ROM_QSTR(MP_QSTR_EXT5), MP_ROM_PTR(&pin_GPIO4) }, + { MP_ROM_QSTR(MP_QSTR_BTN_VOLUME), MP_ROM_PTR(&pin_GPIO0) }, + { MP_ROM_QSTR(MP_QSTR_LED), MP_ROM_PTR(&pin_GPIO2) }, + + { MP_ROM_QSTR(MP_QSTR_EXT4), MP_ROM_PTR(&pin_GPIO15) }, + { MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_spi_obj) }, }; MP_DEFINE_CONST_DICT(board_module_globals, board_module_globals_table); From da8451b7cc4317d9e7a8ad8e687fda58e107ccbf Mon Sep 17 00:00:00 2001 From: foamyguy Date: Mon, 1 Aug 2022 21:56:11 -0500 Subject: [PATCH 36/44] fix edit URL for files inside of directories --- supervisor/shared/web_workflow/static/directory.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/supervisor/shared/web_workflow/static/directory.js b/supervisor/shared/web_workflow/static/directory.js index 9dbe8384d6..91389343d6 100644 --- a/supervisor/shared/web_workflow/static/directory.js +++ b/supervisor/shared/web_workflow/static/directory.js @@ -63,6 +63,7 @@ async function refresh_list() { var icon = "⬇"; var file_path = current_path + f.name; let api_url = new URL("/fs" + file_path, url_base); + let edit_url = "/edit/#" + file_path; if (f.directory) { file_path = "#" + file_path + "/"; api_url += "/"; @@ -91,7 +92,7 @@ async function refresh_list() { delete_button.disabled = !editable; delete_button.onclick = del; - let edit_url = new URL("/edit/#" + f.name, url_base); + edit_url = new URL(edit_url, url_base); let edit_link = clone.querySelector(".edit_link"); edit_link.href = edit_url From 1448bcab6bbfc0ec82d1921cda1e55752d50e2bd Mon Sep 17 00:00:00 2001 From: Andy Warburton Date: Tue, 2 Aug 2022 16:36:20 +0100 Subject: [PATCH 37/44] added remote CSS links to web work flow added remote css URL to pull additional CSS from the circuitpython.org site (apologies for the black background - this is temporary, I'll send an update to the CP.org css *very* shortly that will undo this) --- supervisor/shared/web_workflow/static/directory.html | 1 + supervisor/shared/web_workflow/static/serial.html | 1 + supervisor/shared/web_workflow/static/welcome.html | 1 + 3 files changed, 3 insertions(+) diff --git a/supervisor/shared/web_workflow/static/directory.html b/supervisor/shared/web_workflow/static/directory.html index 0466cb717d..de26686c10 100644 --- a/supervisor/shared/web_workflow/static/directory.html +++ b/supervisor/shared/web_workflow/static/directory.html @@ -5,6 +5,7 @@ +

 

diff --git a/supervisor/shared/web_workflow/static/serial.html b/supervisor/shared/web_workflow/static/serial.html index 5dfcb6cc7d..9f7c3c5ede 100644 --- a/supervisor/shared/web_workflow/static/serial.html +++ b/supervisor/shared/web_workflow/static/serial.html @@ -6,6 +6,7 @@ +
diff --git a/supervisor/shared/web_workflow/static/welcome.html b/supervisor/shared/web_workflow/static/welcome.html index e075c0200d..8a98182bb5 100644 --- a/supervisor/shared/web_workflow/static/welcome.html +++ b/supervisor/shared/web_workflow/static/welcome.html @@ -6,6 +6,7 @@ + From 5d653772cd0c8827c689eb94752873b7fb08a1d4 Mon Sep 17 00:00:00 2001 From: Andy Warburton Date: Tue, 2 Aug 2022 16:43:40 +0100 Subject: [PATCH 38/44] added version number to file name added version number to file name --- supervisor/shared/web_workflow/static/directory.html | 2 +- supervisor/shared/web_workflow/static/serial.html | 2 +- supervisor/shared/web_workflow/static/welcome.html | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/supervisor/shared/web_workflow/static/directory.html b/supervisor/shared/web_workflow/static/directory.html index de26686c10..b88e74684b 100644 --- a/supervisor/shared/web_workflow/static/directory.html +++ b/supervisor/shared/web_workflow/static/directory.html @@ -5,7 +5,7 @@ - +

 

diff --git a/supervisor/shared/web_workflow/static/serial.html b/supervisor/shared/web_workflow/static/serial.html index 9f7c3c5ede..9193953443 100644 --- a/supervisor/shared/web_workflow/static/serial.html +++ b/supervisor/shared/web_workflow/static/serial.html @@ -6,7 +6,7 @@ - +
diff --git a/supervisor/shared/web_workflow/static/welcome.html b/supervisor/shared/web_workflow/static/welcome.html index 8a98182bb5..3ed978cfe7 100644 --- a/supervisor/shared/web_workflow/static/welcome.html +++ b/supervisor/shared/web_workflow/static/welcome.html @@ -6,7 +6,7 @@ - + From 063e168810cdc70e002782b924d0c4271bfa71df Mon Sep 17 00:00:00 2001 From: Neradoc Date: Tue, 2 Aug 2022 18:40:10 +0200 Subject: [PATCH 39/44] Add Authorization to Allow-Headers in web workflow Makes Safari happy --- docs/workflows.md | 3 ++- supervisor/shared/web_workflow/web_workflow.c | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/docs/workflows.md b/docs/workflows.md index 8530269534..345379b9f8 100644 --- a/docs/workflows.md +++ b/docs/workflows.md @@ -82,6 +82,7 @@ CIRCUITPY_WIFI_SSID='scottswifi' CIRCUITPY_WIFI_PASSWORD='secretpassword' # To enable modifying files from the web. Change this too! +# Leave the User field blank in the browser. CIRCUITPY_WEB_API_PASSWORD='passw0rd' CIRCUITPY_WEB_API_PORT=80 @@ -121,7 +122,7 @@ The web server will allow requests from `cpy-XXXXXX.local`, `127.0.0.1`, the dev ### File REST API All file system related APIs are protected by HTTP basic authentication. It is *NOT* secure but will hopefully prevent some griefing in shared settings. The password is sent unencrypted so do not reuse -a password with something important. +a password with something important. The user field is left blank. The password is taken from `/.env` with the key `CIRCUITPY_WEB_API_PASSWORD`. If this is unset, the server will respond with `403 Forbidden`. When a password is set, but not provided in a request, it diff --git a/supervisor/shared/web_workflow/web_workflow.c b/supervisor/shared/web_workflow/web_workflow.c index 4c768e320b..a93ce529d3 100644 --- a/supervisor/shared/web_workflow/web_workflow.c +++ b/supervisor/shared/web_workflow/web_workflow.c @@ -492,7 +492,7 @@ static void _reply_access_control(socketpool_socket_obj_t *socket, _request *req "HTTP/1.1 204 No Content\r\n", "Content-Length: 0\r\n", "Access-Control-Expose-Headers: Access-Control-Allow-Methods\r\n", - "Access-Control-Allow-Headers: X-Timestamp, Content-Type\r\n", + "Access-Control-Allow-Headers: X-Timestamp, Content-Type, Authorization\r\n", "Access-Control-Allow-Methods:GET, OPTIONS", NULL); if (!_usb_active()) { _send_str(socket, ", PUT, DELETE"); From 74e841d8355200f8ca1f7df682d9bf1943390aa0 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Tue, 2 Aug 2022 12:01:42 -0700 Subject: [PATCH 40/44] Read fuses to know what flash and ram pins to never reset --- ports/espressif/Makefile | 2 + .../adafruit_qtpy_esp32_pico/mpconfigboard.mk | 2 +- .../common-hal/microcontroller/Pin.c | 12 +-- ports/espressif/supervisor/port.c | 97 +++++++++++++++++++ 4 files changed, 101 insertions(+), 12 deletions(-) diff --git a/ports/espressif/Makefile b/ports/espressif/Makefile index 204802cb16..febc6764bb 100644 --- a/ports/espressif/Makefile +++ b/ports/espressif/Makefile @@ -98,6 +98,8 @@ INC += \ -isystem esp-idf/components/bt/host/nimble/port/include \ -isystem esp-idf/components/driver/include \ -isystem esp-idf/components/driver/$(IDF_TARGET)/include \ + -isystem esp-idf/components/efuse/include \ + -isystem esp-idf/components/efuse/$(IDF_TARGET)/include \ -isystem esp-idf/components/$(IDF_TARGET)/include \ -isystem esp-idf/components/esp_adc_cal/include \ -isystem esp-idf/components/esp_common/include \ diff --git a/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk b/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk index 53d7f109c1..5b14bad0dc 100644 --- a/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk +++ b/ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.mk @@ -1,5 +1,5 @@ CIRCUITPY_CREATOR_ID = 0x0000239A -CIRCUITPY_CREATION_ID = 0x00320002 +CIRCUITPY_CREATION_ID = 0x00320003 IDF_TARGET = esp32 diff --git a/ports/espressif/common-hal/microcontroller/Pin.c b/ports/espressif/common-hal/microcontroller/Pin.c index 6e733b9095..4ac98c7927 100644 --- a/ports/espressif/common-hal/microcontroller/Pin.c +++ b/ports/espressif/common-hal/microcontroller/Pin.c @@ -46,17 +46,7 @@ static const uint64_t pin_mask_reset_forbidden = // Never ever reset serial pins for bootloader and possibly USB-serial converter. GPIO_SEL_1 | // TXD0 GPIO_SEL_3 | // RXD0 - // Never ever reset pins used to communicate with SPI flash and PSRAM. - GPIO_SEL_6 | // CLK - GPIO_SEL_7 | - GPIO_SEL_8 | - GPIO_SEL_9 | // (PSRAM) SD2 - GPIO_SEL_10 | // (PSRAM) SD3 - GPIO_SEL_11 | // CMD - GPIO_SEL_16 | // SPIHD - GPIO_SEL_17 | // SPIDO - GPIO_SEL_18 | // SPIWP - GPIO_SEL_23 | // SPIDI + // SPI flash and PSRAM pins are protected at runtime in supervisor/port.c. #endif // ESP32 #if defined(CONFIG_IDF_TARGET_ESP32C3) diff --git a/ports/espressif/supervisor/port.c b/ports/espressif/supervisor/port.c index 5245c9f025..9f58e8625b 100644 --- a/ports/espressif/supervisor/port.c +++ b/ports/espressif/supervisor/port.c @@ -81,11 +81,19 @@ #include "soc/cache_memory.h" #endif +#include "soc/efuse_reg.h" #include "soc/rtc_cntl_reg.h" #include "esp_debug_helpers.h" +#include "bootloader_flash_config.h" +#include "esp_efuse.h" #include "esp_ipc.h" +#include "esp_rom_efuse.h" + +#ifdef CONFIG_IDF_TARGET_ESP32 +#include "esp32/rom/efuse.h" +#endif #ifdef CONFIG_SPIRAM #include "esp32/spiram.h" @@ -134,6 +142,93 @@ STATIC void tick_timer_cb(void *arg) { void sleep_timer_cb(void *arg); +// The ESP-IDF determines these pins at runtime so we do too. This code is based on: +// https://github.com/espressif/esp-idf/blob/6d85d53ceec30c818a92c2fff8f5437d21c4720f/components/esp_hw_support/port/esp32/spiram_psram.c#L810 +// IO-pins for PSRAM. +// WARNING: PSRAM shares all but the CS and CLK pins with the flash, so these defines +// hardcode the flash pins as well, making this code incompatible with either a setup +// that has the flash on non-standard pins or ESP32s with built-in flash. +#define PSRAM_SPIQ_SD0_IO 7 +#define PSRAM_SPID_SD1_IO 8 +#define PSRAM_SPIWP_SD3_IO 10 +#define PSRAM_SPIHD_SD2_IO 9 + +#define FLASH_HSPI_CLK_IO 14 +#define FLASH_HSPI_CS_IO 15 +#define PSRAM_HSPI_SPIQ_SD0_IO 12 +#define PSRAM_HSPI_SPID_SD1_IO 13 +#define PSRAM_HSPI_SPIWP_SD3_IO 2 +#define PSRAM_HSPI_SPIHD_SD2_IO 4 + +// PSRAM clock and cs IO should be configured based on hardware design. +// For ESP32-WROVER or ESP32-WROVER-B module, the clock IO is IO17, the cs IO is IO16, +// they are the default value for these two configs. +#define D0WD_PSRAM_CLK_IO CONFIG_D0WD_PSRAM_CLK_IO // Default value is 17 +#define D0WD_PSRAM_CS_IO CONFIG_D0WD_PSRAM_CS_IO // Default value is 16 + +#define D2WD_PSRAM_CLK_IO CONFIG_D2WD_PSRAM_CLK_IO // Default value is 9 +#define D2WD_PSRAM_CS_IO CONFIG_D2WD_PSRAM_CS_IO // Default value is 10 + +// There is no reason to change the pin of an embedded psram. +// So define the number of pin directly, instead of configurable. +#define D0WDR2_V3_PSRAM_CLK_IO 6 +#define D0WDR2_V3_PSRAM_CS_IO 16 + +// For ESP32-PICO chip, the psram share clock with flash. The flash clock pin is fixed, which is IO6. +#define PICO_PSRAM_CLK_IO 6 +#define PICO_PSRAM_CS_IO CONFIG_PICO_PSRAM_CS_IO // Default value is 10 + +#define PICO_V3_02_PSRAM_CLK_IO 10 +#define PICO_V3_02_PSRAM_CS_IO 9 + +static void _never_reset_spi_ram_flash(void) { + #if defined(CONFIG_IDF_TARGET_ESP32) + uint32_t pkg_ver = esp_efuse_get_pkg_ver(); + if (pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32D2WDQ5) { + never_reset_pin_number(D2WD_PSRAM_CLK_IO); + never_reset_pin_number(D2WD_PSRAM_CS_IO); + } else if (pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32PICOD4 && esp_efuse_get_chip_ver() >= 3) { + // This chip is ESP32-PICO-V3 and doesn't have PSRAM. + } else if ((pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32PICOD2) || (pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32PICOD4)) { + never_reset_pin_number(PICO_PSRAM_CLK_IO); + never_reset_pin_number(PICO_PSRAM_CS_IO); + } else if (pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32PICOV302) { + never_reset_pin_number(PICO_V3_02_PSRAM_CLK_IO); + never_reset_pin_number(PICO_V3_02_PSRAM_CS_IO); + } else if ((pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32D0WDQ6) || (pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32D0WDQ5)) { + never_reset_pin_number(D0WD_PSRAM_CLK_IO); + never_reset_pin_number(D0WD_PSRAM_CS_IO); + } else if (pkg_ver == EFUSE_RD_CHIP_VER_PKG_ESP32D0WDR2V3) { + never_reset_pin_number(D0WDR2_V3_PSRAM_CLK_IO); + never_reset_pin_number(D0WDR2_V3_PSRAM_CS_IO); + } + + const uint32_t spiconfig = esp_rom_efuse_get_flash_gpio_info(); + if (spiconfig == ESP_ROM_EFUSE_FLASH_DEFAULT_SPI) { + never_reset_pin_number(SPI_IOMUX_PIN_NUM_CLK); + never_reset_pin_number(SPI_IOMUX_PIN_NUM_CS); + never_reset_pin_number(PSRAM_SPIQ_SD0_IO); + never_reset_pin_number(PSRAM_SPID_SD1_IO); + never_reset_pin_number(PSRAM_SPIWP_SD3_IO); + never_reset_pin_number(PSRAM_SPIHD_SD2_IO); + } else if (spiconfig == ESP_ROM_EFUSE_FLASH_DEFAULT_HSPI) { + never_reset_pin_number(FLASH_HSPI_CLK_IO); + never_reset_pin_number(FLASH_HSPI_CS_IO); + never_reset_pin_number(PSRAM_HSPI_SPIQ_SD0_IO); + never_reset_pin_number(PSRAM_HSPI_SPID_SD1_IO); + never_reset_pin_number(PSRAM_HSPI_SPIWP_SD3_IO); + never_reset_pin_number(PSRAM_HSPI_SPIHD_SD2_IO); + } else { + never_reset_pin_number(EFUSE_SPICONFIG_RET_SPICLK(spiconfig)); + never_reset_pin_number(EFUSE_SPICONFIG_RET_SPICS0(spiconfig)); + never_reset_pin_number(EFUSE_SPICONFIG_RET_SPIQ(spiconfig)); + never_reset_pin_number(EFUSE_SPICONFIG_RET_SPID(spiconfig)); + never_reset_pin_number(EFUSE_SPICONFIG_RET_SPIHD(spiconfig)); + never_reset_pin_number(bootloader_flash_get_wp_pin()); + } + #endif +} + safe_mode_t port_init(void) { esp_timer_create_args_t args; args.callback = &tick_timer_cb; @@ -214,6 +309,8 @@ safe_mode_t port_init(void) { } #endif + _never_reset_spi_ram_flash(); + if (heap == NULL) { size_t heap_total = heap_caps_get_total_size(MALLOC_CAP_8BIT); heap_size = MIN(heap_caps_get_largest_free_block(MALLOC_CAP_8BIT), heap_total / 2); From b67f3585e85159f93b6a7cf65e00a77cc6b643b3 Mon Sep 17 00:00:00 2001 From: Andy Warburton Date: Tue, 2 Aug 2022 21:10:39 +0100 Subject: [PATCH 41/44] css tweaks for edit.html added remote css support to webworkflow edit.html and moved in page css out to the external stylesheet. --- supervisor/shared/web_workflow/static/edit.html | 14 ++------------ supervisor/shared/web_workflow/static/style.css | 12 ++++++++++++ 2 files changed, 14 insertions(+), 12 deletions(-) diff --git a/supervisor/shared/web_workflow/static/edit.html b/supervisor/shared/web_workflow/static/edit.html index c223a11047..e11b094d2c 100644 --- a/supervisor/shared/web_workflow/static/edit.html +++ b/supervisor/shared/web_workflow/static/edit.html @@ -3,18 +3,8 @@ Code Edit - - + + diff --git a/supervisor/shared/web_workflow/static/style.css b/supervisor/shared/web_workflow/static/style.css index f6ef757b3f..17564af4fd 100644 --- a/supervisor/shared/web_workflow/static/style.css +++ b/supervisor/shared/web_workflow/static/style.css @@ -5,3 +5,15 @@ body { font-family: "Proxima Nova", Verdana, sans-serif; line-height: 20.7px; } + + +/* for edit.html */ +#code_textarea { + width: 90%; + height: 600px; +} + +#output_text { + margin: 0; + font-size: 0.7em; +} From 1c69fe1727bdc5e9bcd23abaf566330cf90bae74 Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Tue, 2 Aug 2022 14:11:09 -0700 Subject: [PATCH 42/44] Fix S2/S3 USB The new Kconfig that fixed C3 added a dependency on USB_OTG_SUPPORTED that is only calculated if we include the usb module in cmake. Fixes #6679 --- ports/espressif/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ports/espressif/CMakeLists.txt b/ports/espressif/CMakeLists.txt index 4c834397b9..1c79b448fe 100644 --- a/ports/espressif/CMakeLists.txt +++ b/ports/espressif/CMakeLists.txt @@ -6,7 +6,7 @@ set(ENV{IDF_PATH} ${CMAKE_SOURCE_DIR}/esp-idf) # The component list here determines what options we get in menuconfig and what the ninja file # can build. -set(COMPONENTS esptool_py soc driver log main esp-tls mbedtls mdns esp_event esp_adc_cal esp_netif esp_wifi lwip wpa_supplicant freertos bt) +set(COMPONENTS esptool_py soc driver log main esp-tls mbedtls mdns esp_event esp_adc_cal esp_netif esp_wifi lwip wpa_supplicant freertos bt usb) include($ENV{IDF_PATH}/tools/cmake/project.cmake) project(circuitpython) From 9de8ae70b64b291d0df18e3cff8813488b07a5ab Mon Sep 17 00:00:00 2001 From: Scott Shawcroft Date: Tue, 2 Aug 2022 15:25:19 -0700 Subject: [PATCH 43/44] Fix C3 when pasting 128+ characters The ringbuf used to fill up and the recv interrupt would block CP. Now it'll disable the interrupt until we have enough room in the ringbuf. Fixes #6678 --- ports/espressif/supervisor/usb_serial_jtag.c | 50 +++++++++++++------- 1 file changed, 34 insertions(+), 16 deletions(-) diff --git a/ports/espressif/supervisor/usb_serial_jtag.c b/ports/espressif/supervisor/usb_serial_jtag.c index c666c9bb3c..646d2c3a5e 100644 --- a/ports/espressif/supervisor/usb_serial_jtag.c +++ b/ports/espressif/supervisor/usb_serial_jtag.c @@ -46,6 +46,29 @@ STATIC volatile bool connected; #error "CONFIG_ESP_PHY_ENABLE_USB must be enabled in sdkconfig" #endif +// Make sure the recv interrupt is disabled during this. Otherwise, it could reorder data if it +// interrupts itself. +static void _copy_out_of_fifo(void) { + size_t req_len = ringbuf_num_empty(&ringbuf); + if (req_len == 0) { + // Disable the interrupt so that CircuitPython can run and process the ringbuf. It will + // re-enable the interrupt once the ringbuf is empty. + usb_serial_jtag_ll_disable_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT); + } + if (req_len > USB_SERIAL_JTAG_BUF_SIZE) { + req_len = USB_SERIAL_JTAG_BUF_SIZE; + } + uint8_t rx_buf[USB_SERIAL_JTAG_BUF_SIZE]; + size_t len = usb_serial_jtag_ll_read_rxfifo(rx_buf, req_len); + for (size_t i = 0; i < len; ++i) { + if (rx_buf[i] == mp_interrupt_char) { + mp_sched_keyboard_interrupt(); + } else { + ringbuf_put(&ringbuf, rx_buf[i]); + } + } +} + static void usb_serial_jtag_isr_handler(void *arg) { uint32_t flags = usb_serial_jtag_ll_get_intsts_mask(); @@ -60,25 +83,13 @@ static void usb_serial_jtag_isr_handler(void *arg) { if (flags & USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT) { usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT); - size_t req_len = ringbuf_num_empty(&ringbuf); - if (req_len > USB_SERIAL_JTAG_BUF_SIZE) { - req_len = USB_SERIAL_JTAG_BUF_SIZE; - } - uint8_t rx_buf[USB_SERIAL_JTAG_BUF_SIZE]; - size_t len = usb_serial_jtag_ll_read_rxfifo(rx_buf, req_len); - for (size_t i = 0; i < len; ++i) { - if (rx_buf[i] == mp_interrupt_char) { - mp_sched_keyboard_interrupt(); - } else { - ringbuf_put(&ringbuf, rx_buf[i]); - } - } + _copy_out_of_fifo(); port_wake_main_task_from_isr(); } } void usb_serial_jtag_init(void) { - ringbuf_init(&ringbuf, buf, sizeof(buf)); + ringbuf_init(&ringbuf, buf, sizeof(buf) - 1); usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_SOF | USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT | USB_SERIAL_JTAG_INTR_TOKEN_REC_IN_EP1); usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SOF | USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT | USB_SERIAL_JTAG_INTR_TOKEN_REC_IN_EP1); ESP_ERROR_CHECK(esp_intr_alloc(ETS_USB_SERIAL_JTAG_INTR_SOURCE, ESP_INTR_FLAG_LEVEL1, @@ -93,11 +104,18 @@ char usb_serial_jtag_read_char(void) { if (ringbuf_num_filled(&ringbuf) == 0) { return -1; } - return ringbuf_get(&ringbuf); + char c = ringbuf_get(&ringbuf); + // Maybe re-enable the recv interrupt if we've emptied the ringbuf. + if (ringbuf_num_filled(&ringbuf) == 0) { + usb_serial_jtag_ll_disable_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT); + _copy_out_of_fifo(); + usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT); + } + return c; } bool usb_serial_jtag_bytes_available(void) { - return ringbuf_num_filled(&ringbuf); + return ringbuf_num_filled(&ringbuf) > 0; } void usb_serial_jtag_write(const char *text, uint32_t length) { From 8bd54726e4c9a24f3b247fc7137129170aed1a09 Mon Sep 17 00:00:00 2001 From: Hosted Weblate Date: Wed, 3 Aug 2022 03:31:53 +0200 Subject: [PATCH 44/44] Update translation files Updated by "Update PO files to match POT (msgmerge)" hook in Weblate. Translation: CircuitPython/main Translate-URL: https://hosted.weblate.org/projects/circuitpython/main/ --- locale/ID.po | 17 +++++++++++------ locale/cs.po | 20 ++++++++++++++------ locale/de_DE.po | 20 ++++++++++++++------ locale/el.po | 17 +++++++++++------ locale/en_GB.po | 20 ++++++++++++++------ locale/es.po | 20 ++++++++++++++------ locale/fil.po | 17 +++++++++++------ locale/fr.po | 20 ++++++++++++++------ locale/hi.po | 17 +++++++++++------ locale/it_IT.po | 17 +++++++++++------ locale/ja.po | 17 +++++++++++------ locale/ko.po | 17 +++++++++++------ locale/nl.po | 20 ++++++++++++++------ locale/pl.po | 17 +++++++++++------ locale/pt_BR.po | 20 ++++++++++++++------ locale/ru.po | 20 ++++++++++++++------ locale/sv.po | 20 ++++++++++++++------ locale/tr.po | 17 +++++++++++------ locale/zh_Latn_pinyin.po | 20 ++++++++++++++------ 19 files changed, 239 insertions(+), 114 deletions(-) diff --git a/locale/ID.po b/locale/ID.po index 457615d505..c0f9237a9d 100644 --- a/locale/ID.po +++ b/locale/ID.po @@ -971,10 +971,6 @@ msgstr "Gagal terhubung: kesalahan internal" msgid "Failed to connect: timeout" msgstr "Gagal terhubung: habis waktu" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Gagal mengurai file MP3" @@ -1564,7 +1560,7 @@ msgstr "Hanya 8 atau 16 bit mono dengan " msgid "Only IPv4 addresses supported" msgstr "Hanya alamat IPv4 yang didukung" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Hanysa socket IPv4 yang didukung" @@ -1636,7 +1632,7 @@ msgstr "Waktu habis" msgid "Out of memory" msgstr "Kehabisan memori" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Kehabisan socket" @@ -3791,11 +3787,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/cs.po b/locale/cs.po index 9c042c6c51..02405a1bd0 100644 --- a/locale/cs.po +++ b/locale/cs.po @@ -969,10 +969,6 @@ msgstr "Připojení se nezdařilo: interní chyba" msgid "Failed to connect: timeout" msgstr "Nepodařilo se připojit: časový limit" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Chyba inicializace WiFi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Soubor MP3 se nepodařilo analyzovat" @@ -1564,7 +1560,7 @@ msgstr "" msgid "Only IPv4 addresses supported" msgstr "Pouze IPv4 adresy podporovány" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Pouze IPv4 sokety podporovány" @@ -1632,7 +1628,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3777,11 +3773,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4333,6 +4338,9 @@ msgstr "" msgid "zi must be of shape (n_section, 2)" msgstr "" +#~ msgid "Failed to init wifi" +#~ msgstr "Chyba inicializace WiFi" + #~ msgid "%q must be a tuple of length 2" #~ msgstr "%q musí být n-tice délky 2" diff --git a/locale/de_DE.po b/locale/de_DE.po index 8f46245988..0dc5be2557 100644 --- a/locale/de_DE.po +++ b/locale/de_DE.po @@ -976,10 +976,6 @@ msgstr "Verbindung fehlgeschlagen: interner Fehler" msgid "Failed to connect: timeout" msgstr "Verbindung nicht erfolgreich: timeout" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Wifi Initialisierung ist fehlgeschlagen" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "MP3-Datei konnte nicht analysiert werden" @@ -1579,7 +1575,7 @@ msgstr "Nur 8 oder 16 bit mono mit " msgid "Only IPv4 addresses supported" msgstr "Nur IPv4-Adressen werden unterstützt" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Nur IPv4-Sockets werden unterstützt" @@ -1651,7 +1647,7 @@ msgstr "Zeit für Vorgang abgelaufen" msgid "Out of memory" msgstr "Kein Speicher mehr verfügbar" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Keine Sockets mehr verfügbar" @@ -3854,11 +3850,20 @@ msgstr "pow() drittes Argument darf nicht 0 sein" msgid "pow() with 3 arguments requires integers" msgstr "pow() mit 3 Argumenten erfordert Integer" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4415,6 +4420,9 @@ msgstr "zi muss eine Gleitkommazahl sein" msgid "zi must be of shape (n_section, 2)" msgstr "zi muss die Form (n_section, 2) haben" +#~ msgid "Failed to init wifi" +#~ msgstr "Wifi Initialisierung ist fehlgeschlagen" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "Eingabe muss ein Tensor von Rang 2 sein" diff --git a/locale/el.po b/locale/el.po index e7abd4d7ff..be14e4289c 100644 --- a/locale/el.po +++ b/locale/el.po @@ -958,10 +958,6 @@ msgstr "" msgid "Failed to connect: timeout" msgstr "" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "" @@ -1548,7 +1544,7 @@ msgstr "" msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1616,7 +1612,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3759,11 +3755,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/en_GB.po b/locale/en_GB.po index f3b8bedb75..eb462b4dad 100644 --- a/locale/en_GB.po +++ b/locale/en_GB.po @@ -972,10 +972,6 @@ msgstr "Failed to connect: internal error" msgid "Failed to connect: timeout" msgstr "Failed to connect: timeout" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Failed to init WiFi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Failed to parse MP3 file" @@ -1565,7 +1561,7 @@ msgstr "Only 8 or 16 bit mono with " msgid "Only IPv4 addresses supported" msgstr "Only IPv4 addresses supported" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Only IPv4 sockets supported" @@ -1636,7 +1632,7 @@ msgstr "Operation timed out" msgid "Out of memory" msgstr "Out of memory" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Out of sockets" @@ -3796,11 +3792,20 @@ msgstr "pow() 3rd argument cannot be 0" msgid "pow() with 3 arguments requires integers" msgstr "pow() with 3 arguments requires integers" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4354,6 +4359,9 @@ msgstr "zi must be of float type" msgid "zi must be of shape (n_section, 2)" msgstr "zi must be of shape (n_section, 2)" +#~ msgid "Failed to init wifi" +#~ msgstr "Failed to init WiFi" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "input must be a tensor of rank 2" diff --git a/locale/es.po b/locale/es.po index 3652d1847e..ea5c7abbfc 100644 --- a/locale/es.po +++ b/locale/es.po @@ -979,10 +979,6 @@ msgstr "Error al conectar: error interno" msgid "Failed to connect: timeout" msgstr "Error al conectar: tiempo de espera agotado" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Fallo al inicializar wifi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Error al analizar el archivo MP3" @@ -1585,7 +1581,7 @@ msgstr "Solo mono de 8 ó 16 bit con " msgid "Only IPv4 addresses supported" msgstr "Solo hay capacidad para direcciones IPv4" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Solo se admiten sockets IPv4" @@ -1657,7 +1653,7 @@ msgstr "Tiempo de espera agotado" msgid "Out of memory" msgstr "Memoria agotada" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Se acabaron los enchufes" @@ -3840,11 +3836,20 @@ msgstr "el 3er argumento de pow() no puede ser 0" msgid "pow() with 3 arguments requires integers" msgstr "pow() con 3 argumentos requiere enteros" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4399,6 +4404,9 @@ msgstr "zi debe ser de tipo flotante" msgid "zi must be of shape (n_section, 2)" msgstr "zi debe ser una forma (n_section,2)" +#~ msgid "Failed to init wifi" +#~ msgstr "Fallo al inicializar wifi" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "Entrada tiene que ser un tensor de rango 2" diff --git a/locale/fil.po b/locale/fil.po index 4cf9806fa3..2ce57b913a 100644 --- a/locale/fil.po +++ b/locale/fil.po @@ -969,10 +969,6 @@ msgstr "" msgid "Failed to connect: timeout" msgstr "" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "" @@ -1564,7 +1560,7 @@ msgstr "Tanging 8 o 16 na bit mono na may " msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1632,7 +1628,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3798,11 +3794,20 @@ msgstr "pow() 3rd argument ay hindi maaring 0" msgid "pow() with 3 arguments requires integers" msgstr "pow() na may 3 argumento kailangan ng integers" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/fr.po b/locale/fr.po index 8cf8e5cb77..ff498bf168 100644 --- a/locale/fr.po +++ b/locale/fr.po @@ -993,10 +993,6 @@ msgstr "Impossible de se connecter : erreur interne" msgid "Failed to connect: timeout" msgstr "Impossible de se connecter: délai dépassé" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Echec de l'initialisation du Wifi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Impossible d'analyser le fichier MP3" @@ -1608,7 +1604,7 @@ msgstr "Uniquement 8 ou 16 bit mono avec " msgid "Only IPv4 addresses supported" msgstr "Seulement les adresses IPv4 sont supportées" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Seulement les sockets IPv4 sont supportés" @@ -1680,7 +1676,7 @@ msgstr "Timeout de l'opération" msgid "Out of memory" msgstr "Hors de mémoire" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Plus de sockets" @@ -3885,11 +3881,20 @@ msgstr "le 3e argument de pow() ne peut être 0" msgid "pow() with 3 arguments requires integers" msgstr "pow() avec 3 arguments nécessite des entiers" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "presser le bouton SW38 au démarrage.\n" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4444,6 +4449,9 @@ msgstr "zi doit être de type float" msgid "zi must be of shape (n_section, 2)" msgstr "zi doit être de forme (n_section, 2)" +#~ msgid "Failed to init wifi" +#~ msgstr "Echec de l'initialisation du Wifi" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "l'entrée doit être un tenseur de rang 2" diff --git a/locale/hi.po b/locale/hi.po index aea67d4580..76817fd84f 100644 --- a/locale/hi.po +++ b/locale/hi.po @@ -958,10 +958,6 @@ msgstr "" msgid "Failed to connect: timeout" msgstr "" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "" @@ -1548,7 +1544,7 @@ msgstr "" msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1616,7 +1612,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3759,11 +3755,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/it_IT.po b/locale/it_IT.po index e418f789f9..168b23e23d 100644 --- a/locale/it_IT.po +++ b/locale/it_IT.po @@ -974,10 +974,6 @@ msgstr "" msgid "Failed to connect: timeout" msgstr "" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "" @@ -1571,7 +1567,7 @@ msgstr "" msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1639,7 +1635,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3811,11 +3807,20 @@ msgstr "il terzo argomento di pow() non può essere 0" msgid "pow() with 3 arguments requires integers" msgstr "pow() con 3 argomenti richiede interi" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/ja.po b/locale/ja.po index 7fb9268a9d..844b3bd2d5 100644 --- a/locale/ja.po +++ b/locale/ja.po @@ -967,10 +967,6 @@ msgstr "接続失敗: 内部エラー" msgid "Failed to connect: timeout" msgstr "接続失敗: タイムアウト" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "MP3ファイルのパーズに失敗" @@ -1561,7 +1557,7 @@ msgstr "8または16ビットの " msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1629,7 +1625,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3780,11 +3776,20 @@ msgstr "pow()の3つ目の引数は0にできません" msgid "pow() with 3 arguments requires integers" msgstr "pow()の第3引数には整数が必要" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/ko.po b/locale/ko.po index fce40622bd..4334a2dbc1 100644 --- a/locale/ko.po +++ b/locale/ko.po @@ -961,10 +961,6 @@ msgstr "" msgid "Failed to connect: timeout" msgstr "" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "" @@ -1551,7 +1547,7 @@ msgstr "" msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1619,7 +1615,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3763,11 +3759,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/nl.po b/locale/nl.po index 55b10b872a..b4e9e6c484 100644 --- a/locale/nl.po +++ b/locale/nl.po @@ -966,10 +966,6 @@ msgstr "Verbinding mislukt: interne fout" msgid "Failed to connect: timeout" msgstr "Verbinding mislukt: timeout" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Kon WiFi niet initialiseren" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Mislukt om MP3 bestand te ontleden" @@ -1561,7 +1557,7 @@ msgstr "Alleen 8 of 16 bit mono met " msgid "Only IPv4 addresses supported" msgstr "Alleen IPv4 adressen worden ondersteund" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Alleen IPv4-sockets ondersteund" @@ -1633,7 +1629,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Geen sockets meer beschikbaar" @@ -3796,11 +3792,20 @@ msgstr "derde argument van pow() mag geen 0 zijn" msgid "pow() with 3 arguments requires integers" msgstr "pow() met 3 argumenten vereist integers" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4354,6 +4359,9 @@ msgstr "zi moet van type float zijn" msgid "zi must be of shape (n_section, 2)" msgstr "zi moet vorm (n_section, 2) hebben" +#~ msgid "Failed to init wifi" +#~ msgstr "Kon WiFi niet initialiseren" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "invoer moet een tensor van rang 2 zijn" diff --git a/locale/pl.po b/locale/pl.po index 3041284599..afadb604d0 100644 --- a/locale/pl.po +++ b/locale/pl.po @@ -967,10 +967,6 @@ msgstr "Nie udało się połączyć: błąd wewnętrzny" msgid "Failed to connect: timeout" msgstr "Nie udało się połączyć: upłynął limit czasu" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Nie można przeanalizować pliku MP3" @@ -1559,7 +1555,7 @@ msgstr "Tylko 8 lub 16 bitów mono z " msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1627,7 +1623,7 @@ msgstr "" msgid "Out of memory" msgstr "Brak pamięci" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3772,11 +3768,20 @@ msgstr "trzeci argument pow() nie może być 0" msgid "pow() with 3 arguments requires integers" msgstr "trzyargumentowe pow() wymaga liczb całkowitych" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/pt_BR.po b/locale/pt_BR.po index 38cf9c7ff0..3ddb5d65a8 100644 --- a/locale/pt_BR.po +++ b/locale/pt_BR.po @@ -985,10 +985,6 @@ msgstr "Falha ao conectar: erro interno" msgid "Failed to connect: timeout" msgstr "Falha ao conectar: tempo limite" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Houve uma falha ao iniciar o wifi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Falha ao analisar o arquivo MP3" @@ -1590,7 +1586,7 @@ msgstr "Apenas mono com 8 ou 16 bits com " msgid "Only IPv4 addresses supported" msgstr "Somente os endereços IPv4 são suportados" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Apenas soquetes IPv4 são suportados" @@ -1662,7 +1658,7 @@ msgstr "A operação expirou" msgid "Out of memory" msgstr "Sem memória" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Sem soquetes" @@ -3862,11 +3858,20 @@ msgstr "O terceiro argumento pow() não pode ser 0" msgid "pow() with 3 arguments requires integers" msgstr "o pow() com 3 argumentos requer números inteiros" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "pressionando o botão SW38 na inicialização.\n" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4420,6 +4425,9 @@ msgstr "zi deve ser de um tipo float" msgid "zi must be of shape (n_section, 2)" msgstr "zi deve estar na forma (n_section, 2)" +#~ msgid "Failed to init wifi" +#~ msgstr "Houve uma falha ao iniciar o wifi" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "a entrada dos dados deve ser um tensor de nível 2" diff --git a/locale/ru.po b/locale/ru.po index e993d00aec..d4e434ad67 100644 --- a/locale/ru.po +++ b/locale/ru.po @@ -983,10 +983,6 @@ msgstr "Не удалось подключиться: внутренняя ош msgid "Failed to connect: timeout" msgstr "Не удалось подключиться: тайм-аут" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Не удалось инициировать wifi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Не удалось распарсить файл MP3" @@ -1588,7 +1584,7 @@ msgstr "Только 8- или 16-битное моно с " msgid "Only IPv4 addresses supported" msgstr "Поддерживаются только адреса IPv4" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Поддерживаются только сокеты IPv4" @@ -1658,7 +1654,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3808,11 +3804,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4364,6 +4369,9 @@ msgstr "zi должно быть типа float" msgid "zi must be of shape (n_section, 2)" msgstr "zi должен иметь форму (n_section, 2)" +#~ msgid "Failed to init wifi" +#~ msgstr "Не удалось инициировать wifi" + #~ msgid "%q must be a tuple of length 2" #~ msgstr "%q должен быть кортежем длинной 2" diff --git a/locale/sv.po b/locale/sv.po index 8c60691712..e5ae4df26e 100644 --- a/locale/sv.po +++ b/locale/sv.po @@ -972,10 +972,6 @@ msgstr "Det gick inte att ansluta: internt fel" msgid "Failed to connect: timeout" msgstr "Det gick inte att ansluta: timeout" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Kunde inte initiera WiFi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Det gick inte att tolka MP3-filen" @@ -1571,7 +1567,7 @@ msgstr "Endast 8 eller 16 bitars mono med " msgid "Only IPv4 addresses supported" msgstr "Endast IPv4-adresser stöds" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "Endast IPv4-socket stöds" @@ -1642,7 +1638,7 @@ msgstr "Åtgärden orsakade timeout" msgid "Out of memory" msgstr "Slut på minne" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "Slut på sockets" @@ -3821,11 +3817,20 @@ msgstr "pow() 3: e argument kan inte vara 0" msgid "pow() with 3 arguments requires integers" msgstr "pow() med 3 argument kräver heltal" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "genom att trycka på SW38-knappen vid start.\n" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4379,6 +4384,9 @@ msgstr "zi måste vara av typ float" msgid "zi must be of shape (n_section, 2)" msgstr "zi måste vara i formen (n_section, 2)" +#~ msgid "Failed to init wifi" +#~ msgstr "Kunde inte initiera WiFi" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "indata måste vara en tensor av rank 2" diff --git a/locale/tr.po b/locale/tr.po index a2d8d41ea7..f8d52779ef 100644 --- a/locale/tr.po +++ b/locale/tr.po @@ -975,10 +975,6 @@ msgstr "" msgid "Failed to connect: timeout" msgstr "" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "" @@ -1565,7 +1561,7 @@ msgstr "" msgid "Only IPv4 addresses supported" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "" @@ -1633,7 +1629,7 @@ msgstr "" msgid "Out of memory" msgstr "" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "" @@ -3779,11 +3775,20 @@ msgstr "" msgid "pow() with 3 arguments requires integers" msgstr "" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" diff --git a/locale/zh_Latn_pinyin.po b/locale/zh_Latn_pinyin.po index 5985e012b0..b98cab412f 100644 --- a/locale/zh_Latn_pinyin.po +++ b/locale/zh_Latn_pinyin.po @@ -981,10 +981,6 @@ msgstr "Liánjiē shībài: Nèibù cuòwù" msgid "Failed to connect: timeout" msgstr "Liánjiē shībài: Chāoshí" -#: ports/espressif/common-hal/wifi/__init__.c -msgid "Failed to init wifi" -msgstr "Wúfǎ chūshǐhuà wifi" - #: shared-module/audiomp3/MP3Decoder.c msgid "Failed to parse MP3 file" msgstr "Wúfǎ jiěxī MP3 wénjiàn" @@ -1584,7 +1580,7 @@ msgstr "Zhǐyǒu 8 huò 16 wèi dānwèi " msgid "Only IPv4 addresses supported" msgstr "Jǐn zhīchí IPv4 dìzhǐ" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Only IPv4 sockets supported" msgstr "jǐn zhī chí IPv4 tào jiē zì" @@ -1656,7 +1652,7 @@ msgstr "cāo zuò yǐ fēn shí" msgid "Out of memory" msgstr "nèi cún bù zú" -#: ports/espressif/common-hal/socketpool/SocketPool.c +#: ports/espressif/common-hal/socketpool/Socket.c msgid "Out of sockets" msgstr "tào jiē zì wài" @@ -3830,11 +3826,20 @@ msgstr "pow() 3 cān shǔ bùnéng wéi 0" msgid "pow() with 3 arguments requires integers" msgstr "pow() yǒu 3 cānshù xūyào zhěngshù" +#: ports/espressif/boards/adafruit_qtpy_esp32_pico/mpconfigboard.h +msgid "pressing BOOT button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_feather_esp32_v2/mpconfigboard.h msgid "pressing SW38 button at start up.\n" msgstr "" +#: ports/espressif/boards/hardkernel_odroid_go/mpconfigboard.h +msgid "pressing VOLUME button at start up.\n" +msgstr "" + #: ports/espressif/boards/adafruit_qtpy_esp32c3/mpconfigboard.h +#: ports/espressif/boards/beetle-esp32-c3/mpconfigboard.h #: ports/espressif/boards/lolin_c3_mini/mpconfigboard.h #: supervisor/shared/safe_mode.c msgid "pressing boot button at start up.\n" @@ -4391,6 +4396,9 @@ msgstr "zi bìxū wèi fú diǎn xíng" msgid "zi must be of shape (n_section, 2)" msgstr "zi bìxū jùyǒu xíngzhuàng (n_section,2)" +#~ msgid "Failed to init wifi" +#~ msgstr "Wúfǎ chūshǐhuà wifi" + #~ msgid "input must be a tensor of rank 2" #~ msgstr "shū rù bì xū shì děng jí 2 de zhāng liàng"
TypeSizePathModified