mirror of
https://github.com/espressif/esp-idf.git
synced 2026-04-27 19:13:21 +00:00
feat(esp_libc): add full support for picolibc
This commit is contained in:
+16
-5
@@ -74,11 +74,22 @@ else()
|
||||
list(APPEND cxx_compile_options "-fno-exceptions")
|
||||
endif()
|
||||
|
||||
if(CONFIG_COMPILER_CXX_RTTI)
|
||||
list(APPEND cxx_compile_options "-frtti")
|
||||
else()
|
||||
list(APPEND cxx_compile_options "-fno-rtti")
|
||||
list(APPEND link_options "-fno-rtti") # used to invoke correct multilib variant (no-rtti) during linking
|
||||
if(CONFIG_IDF_TOOLCHAIN_GCC)
|
||||
if(CONFIG_COMPILER_CXX_RTTI)
|
||||
idf_toolchain_remove_flags(CXX_COMPILE_OPTIONS "-fno-rtti"
|
||||
LINK_OPTIONS "-fno-rtti")
|
||||
else()
|
||||
idf_toolchain_add_flags(CXX_COMPILE_OPTIONS "-fno-rtti"
|
||||
LINK_OPTIONS "-fno-rtti")
|
||||
endif()
|
||||
idf_toolchain_rerun_abi_detection()
|
||||
else() # TODO IDF-14338
|
||||
if(CONFIG_COMPILER_CXX_RTTI)
|
||||
list(APPEND cxx_compile_options "-frtti")
|
||||
else()
|
||||
list(APPEND cxx_compile_options "-fno-rtti")
|
||||
list(APPEND link_options "-fno-rtti") # used to invoke correct multilib variant (no-rtti) during linking
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(CONFIG_COMPILER_SAVE_RESTORE_LIBCALLS)
|
||||
|
||||
@@ -706,4 +706,3 @@ mainmenu "Espressif IoT Development Framework Configuration"
|
||||
- CONFIG_ESP_WIFI_EAP_TLS1_3
|
||||
- CONFIG_ESP_WIFI_ENABLE_ROAMING_APP
|
||||
- CONFIG_USB_HOST_EXT_PORT_RESET_ATTEMPTS
|
||||
- CONFIG_LIBC_PICOLIBC
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#include "sys/queue.h"
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
#include <stddef.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
||||
@@ -58,6 +58,7 @@
|
||||
|
||||
#include <tinycrypt/ecc.h>
|
||||
#include <tinycrypt/ecc_platform_specific.h>
|
||||
#include <assert.h>
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
@@ -224,6 +224,37 @@ FORCE_INLINE_ATTR __attribute__((pure)) void *esp_cpu_pc_to_addr(uint32_t pc)
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Set the current CPU core's thread pointer
|
||||
*
|
||||
* Sets the thread pointer register to the given value.
|
||||
*
|
||||
* @param threadptr Pointer to the thread-local storage area
|
||||
*/
|
||||
FORCE_INLINE_ATTR void esp_cpu_set_threadptr(void * threadptr)
|
||||
{
|
||||
#ifdef __XTENSA__
|
||||
xt_utils_set_threadptr(threadptr);
|
||||
#else
|
||||
rv_utils_set_threadptr(threadptr);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get the current CPU core's thread pointer
|
||||
*
|
||||
* @return thread pointer register value
|
||||
*/
|
||||
FORCE_INLINE_ATTR void *esp_cpu_get_threadptr(void)
|
||||
{
|
||||
#ifdef __XTENSA__
|
||||
return xt_utils_get_threadptr();
|
||||
#else
|
||||
return rv_utils_get_threadptr();
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/* ------------------------------------------------- CPU Interrupts ----------------------------------------------------
|
||||
*
|
||||
* ------------------------------------------------------------------------------------------------------------------ */
|
||||
|
||||
@@ -144,7 +144,7 @@ endif()
|
||||
|
||||
if(ESP_TEE_BUILD)
|
||||
rom_linker_script("heap")
|
||||
if(CONFIG_ESP_ROM_HAS_NEWLIB_NANO_FORMAT)
|
||||
if(CONFIG_LIBC_NEWLIB AND CONFIG_ESP_ROM_HAS_NEWLIB_NANO_FORMAT)
|
||||
rom_linker_script("newlib-nano")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -22,18 +22,12 @@ bzero = 0x4000c1f4;
|
||||
div = 0x40056348;
|
||||
__dummy_lock = 0x4000c728;
|
||||
__dummy_lock_try = 0x4000c730;
|
||||
isalnum = 0x40000f04;
|
||||
isalpha = 0x40000f18;
|
||||
isascii = 0x4000c20c;
|
||||
isblank = 0x40000f2c;
|
||||
iscntrl = 0x40000f50;
|
||||
isdigit = 0x40000f64;
|
||||
isgraph = 0x40000f94;
|
||||
islower = 0x40000f78;
|
||||
isprint = 0x40000fa8;
|
||||
ispunct = 0x40000fc0;
|
||||
isspace = 0x40000fd4;
|
||||
isupper = 0x40000fe8;
|
||||
__itoa = 0x40056678;
|
||||
itoa = 0x400566b4;
|
||||
labs = 0x40056370;
|
||||
@@ -49,19 +43,15 @@ memset = 0x4000c44c;
|
||||
qsort = 0x40056424;
|
||||
__sccl = 0x4000c498;
|
||||
setjmp = 0x40056268;
|
||||
strcasecmp = 0x400011cc;
|
||||
strcasestr = 0x40001210;
|
||||
strcat = 0x4000c518;
|
||||
strchr = 0x4000c53c;
|
||||
strcmp = 0x40001274;
|
||||
strcoll = 0x40001398;
|
||||
strcpy = 0x400013ac;
|
||||
strcspn = 0x4000c558;
|
||||
strlcat = 0x40001470;
|
||||
strlcpy = 0x4000c584;
|
||||
strlen = 0x400014c0;
|
||||
strlwr = 0x40001524;
|
||||
strncasecmp = 0x40001550;
|
||||
strncat = 0x4000c5c4;
|
||||
strncmp = 0x4000c5f4;
|
||||
strncpy = 0x400015d4;
|
||||
@@ -70,10 +60,7 @@ strrchr = 0x40001708;
|
||||
strsep = 0x40001734;
|
||||
strspn = 0x4000c648;
|
||||
strstr = 0x4000c674;
|
||||
strupr = 0x4000174c;
|
||||
__submore = 0x40058f3c;
|
||||
toascii = 0x4000c720;
|
||||
tolower = 0x40001868;
|
||||
toupper = 0x40001884;
|
||||
__utoa = 0x400561f0;
|
||||
utoa = 0x40056258;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2023-2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2023-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -59,3 +59,16 @@ __sinit_lock_release = 0x40001e2c;
|
||||
__env_lock = 0x40001fd4;
|
||||
__env_unlock = 0x40001fe0;
|
||||
_getenv_r = 0x40001fbc;
|
||||
tolower = 0x40001868;
|
||||
toupper = 0x40001884;
|
||||
isalnum = 0x40000f04;
|
||||
isalpha = 0x40000f18;
|
||||
isdigit = 0x40000f64;
|
||||
islower = 0x40000f78;
|
||||
isspace = 0x40000fd4;
|
||||
isupper = 0x40000fe8;
|
||||
strcasecmp = 0x400011cc;
|
||||
strcoll = 0x40001398;
|
||||
strlwr = 0x40001524;
|
||||
strncasecmp = 0x40001550;
|
||||
strupr = 0x4000174c;
|
||||
|
||||
@@ -9,41 +9,28 @@ strlen = 0x400004a8;
|
||||
strstr = 0x400004ac;
|
||||
bzero = 0x400004b0;
|
||||
sbrk = 0x400004b8;
|
||||
isalnum = 0x400004bc;
|
||||
isalpha = 0x400004c0;
|
||||
isascii = 0x400004c4;
|
||||
isblank = 0x400004c8;
|
||||
iscntrl = 0x400004cc;
|
||||
isdigit = 0x400004d0;
|
||||
islower = 0x400004d4;
|
||||
isgraph = 0x400004d8;
|
||||
isprint = 0x400004dc;
|
||||
ispunct = 0x400004e0;
|
||||
isspace = 0x400004e4;
|
||||
isupper = 0x400004e8;
|
||||
toupper = 0x400004ec;
|
||||
tolower = 0x400004f0;
|
||||
toascii = 0x400004f4;
|
||||
memccpy = 0x400004f8;
|
||||
memchr = 0x400004fc;
|
||||
memrchr = 0x40000500;
|
||||
strcasecmp = 0x40000504;
|
||||
strcasestr = 0x40000508;
|
||||
strcat = 0x4000050c;
|
||||
strchr = 0x40000514;
|
||||
strcspn = 0x40000518;
|
||||
strcoll = 0x4000051c;
|
||||
strlcat = 0x40000520;
|
||||
strlcpy = 0x40000524;
|
||||
strlwr = 0x40000528;
|
||||
strncasecmp = 0x4000052c;
|
||||
strncat = 0x40000530;
|
||||
strnlen = 0x40000538;
|
||||
strrchr = 0x4000053c;
|
||||
strsep = 0x40000540;
|
||||
strspn = 0x40000544;
|
||||
strtok_r = 0x40000548;
|
||||
strupr = 0x4000054c;
|
||||
longjmp = 0x40000550;
|
||||
setjmp = 0x40000554;
|
||||
abs = 0x40000558;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2021-2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2021-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -63,3 +63,16 @@ puts = 0x4000065c;
|
||||
putc = 0x40000660;
|
||||
putchar = 0x40000664;
|
||||
__errno = 0x40000670;
|
||||
toupper = 0x400004ec;
|
||||
tolower = 0x400004f0;
|
||||
isalnum = 0x400004bc;
|
||||
isalpha = 0x400004c0;
|
||||
isdigit = 0x400004d0;
|
||||
islower = 0x400004d4;
|
||||
isspace = 0x400004e4;
|
||||
isupper = 0x400004e8;
|
||||
strcasecmp = 0x40000504;
|
||||
strcoll = 0x4000051c;
|
||||
strlwr = 0x40000528;
|
||||
strncasecmp = 0x4000052c;
|
||||
strupr = 0x4000054c;
|
||||
|
||||
@@ -9,41 +9,28 @@ strlen = 0x40000374;
|
||||
strstr = 0x40000378;
|
||||
bzero = 0x4000037c;
|
||||
sbrk = 0x40000384;
|
||||
isalnum = 0x40000388;
|
||||
isalpha = 0x4000038c;
|
||||
isascii = 0x40000390;
|
||||
isblank = 0x40000394;
|
||||
iscntrl = 0x40000398;
|
||||
isdigit = 0x4000039c;
|
||||
islower = 0x400003a0;
|
||||
isgraph = 0x400003a4;
|
||||
isprint = 0x400003a8;
|
||||
ispunct = 0x400003ac;
|
||||
isspace = 0x400003b0;
|
||||
isupper = 0x400003b4;
|
||||
toupper = 0x400003b8;
|
||||
tolower = 0x400003bc;
|
||||
toascii = 0x400003c0;
|
||||
memccpy = 0x400003c4;
|
||||
memchr = 0x400003c8;
|
||||
memrchr = 0x400003cc;
|
||||
strcasecmp = 0x400003d0;
|
||||
strcasestr = 0x400003d4;
|
||||
strcat = 0x400003d8;
|
||||
strchr = 0x400003e0;
|
||||
strcspn = 0x400003e4;
|
||||
strcoll = 0x400003e8;
|
||||
strlcat = 0x400003ec;
|
||||
strlcpy = 0x400003f0;
|
||||
strlwr = 0x400003f4;
|
||||
strncasecmp = 0x400003f8;
|
||||
strncat = 0x400003fc;
|
||||
strnlen = 0x40000404;
|
||||
strrchr = 0x40000408;
|
||||
strsep = 0x4000040c;
|
||||
strspn = 0x40000410;
|
||||
strtok_r = 0x40000414;
|
||||
strupr = 0x40000418;
|
||||
longjmp = 0x4000041c;
|
||||
setjmp = 0x40000420;
|
||||
abs = 0x40000424;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -35,3 +35,16 @@ PROVIDE( _fwalk = 0x40000464 );
|
||||
PROVIDE( _fwalk_reent = 0x40000468 );
|
||||
PROVIDE( __swbuf_r = 0x40000474 );
|
||||
__swbuf = 0x40000478;
|
||||
toupper = 0x400003b8;
|
||||
tolower = 0x400003bc;
|
||||
isalnum = 0x40000388;
|
||||
isalpha = 0x4000038c;
|
||||
isdigit = 0x4000039c;
|
||||
islower = 0x400003a0;
|
||||
isspace = 0x400003b0;
|
||||
isupper = 0x400003b4;
|
||||
strcasecmp = 0x400003d0;
|
||||
strcoll = 0x400003e8;
|
||||
strlwr = 0x400003f4;
|
||||
strncasecmp = 0x400003f8;
|
||||
strupr = 0x40000418;
|
||||
|
||||
@@ -24,41 +24,28 @@ strlen = 0x400004d8;
|
||||
strstr = 0x400004dc;
|
||||
bzero = 0x400004e0;
|
||||
sbrk = 0x400004e8;
|
||||
isalnum = 0x400004ec;
|
||||
isalpha = 0x400004f0;
|
||||
isascii = 0x400004f4;
|
||||
isblank = 0x400004f8;
|
||||
iscntrl = 0x400004fc;
|
||||
isdigit = 0x40000500;
|
||||
islower = 0x40000504;
|
||||
isgraph = 0x40000508;
|
||||
isprint = 0x4000050c;
|
||||
ispunct = 0x40000510;
|
||||
isspace = 0x40000514;
|
||||
isupper = 0x40000518;
|
||||
toupper = 0x4000051c;
|
||||
tolower = 0x40000520;
|
||||
toascii = 0x40000524;
|
||||
memccpy = 0x40000528;
|
||||
memchr = 0x4000052c;
|
||||
memrchr = 0x40000530;
|
||||
strcasecmp = 0x40000534;
|
||||
strcasestr = 0x40000538;
|
||||
strcat = 0x4000053c;
|
||||
strchr = 0x40000544;
|
||||
strcspn = 0x40000548;
|
||||
strcoll = 0x4000054c;
|
||||
strlcat = 0x40000550;
|
||||
strlcpy = 0x40000554;
|
||||
strlwr = 0x40000558;
|
||||
strncasecmp = 0x4000055c;
|
||||
strncat = 0x40000560;
|
||||
strnlen = 0x40000568;
|
||||
strrchr = 0x4000056c;
|
||||
strsep = 0x40000570;
|
||||
strspn = 0x40000574;
|
||||
strtok_r = 0x40000578;
|
||||
strupr = 0x4000057c;
|
||||
longjmp = 0x40000580;
|
||||
setjmp = 0x40000584;
|
||||
abs = 0x40000588;
|
||||
|
||||
@@ -37,3 +37,16 @@ __swhatbuf_r = 0x400005d4;
|
||||
__swbuf_r = 0x400005d8;
|
||||
__swbuf = 0x400005dc;
|
||||
__swsetup_r = 0x400005e0;
|
||||
toupper = 0x4000051c;
|
||||
tolower = 0x40000520;
|
||||
isalnum = 0x400004ec;
|
||||
isalpha = 0x400004f0;
|
||||
isdigit = 0x40000500;
|
||||
islower = 0x40000504;
|
||||
isspace = 0x40000514;
|
||||
isupper = 0x40000518;
|
||||
strcasecmp = 0x40000534;
|
||||
strcoll = 0x4000054c;
|
||||
strlwr = 0x40000558;
|
||||
strncasecmp = 0x4000055c;
|
||||
strupr = 0x4000057c;
|
||||
|
||||
@@ -9,41 +9,28 @@ strlen = 0x400004c8;
|
||||
strstr = 0x400004cc;
|
||||
bzero = 0x400004d0;
|
||||
sbrk = 0x400004d8;
|
||||
isalnum = 0x400004dc;
|
||||
isalpha = 0x400004e0;
|
||||
isascii = 0x400004e4;
|
||||
isblank = 0x400004e8;
|
||||
iscntrl = 0x400004ec;
|
||||
isdigit = 0x400004f0;
|
||||
islower = 0x400004f4;
|
||||
isgraph = 0x400004f8;
|
||||
isprint = 0x400004fc;
|
||||
ispunct = 0x40000500;
|
||||
isspace = 0x40000504;
|
||||
isupper = 0x40000508;
|
||||
toupper = 0x4000050c;
|
||||
tolower = 0x40000510;
|
||||
toascii = 0x40000514;
|
||||
memccpy = 0x40000518;
|
||||
memchr = 0x4000051c;
|
||||
memrchr = 0x40000520;
|
||||
strcasecmp = 0x40000524;
|
||||
strcasestr = 0x40000528;
|
||||
strcat = 0x4000052c;
|
||||
strchr = 0x40000534;
|
||||
strcspn = 0x40000538;
|
||||
strcoll = 0x4000053c;
|
||||
strlcat = 0x40000540;
|
||||
strlcpy = 0x40000544;
|
||||
strlwr = 0x40000548;
|
||||
strncasecmp = 0x4000054c;
|
||||
strncat = 0x40000550;
|
||||
strnlen = 0x40000558;
|
||||
strrchr = 0x4000055c;
|
||||
strsep = 0x40000560;
|
||||
strspn = 0x40000564;
|
||||
strtok_r = 0x40000568;
|
||||
strupr = 0x4000056c;
|
||||
longjmp = 0x40000570;
|
||||
setjmp = 0x40000574;
|
||||
abs = 0x40000578;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2022-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -39,3 +39,16 @@ __swhatbuf_r = 0x400005c4;
|
||||
__swbuf_r = 0x400005c8;
|
||||
__swbuf = 0x400005cc;
|
||||
__swsetup_r = 0x400005d0;
|
||||
toupper = 0x4000050c;
|
||||
tolower = 0x40000510;
|
||||
isalnum = 0x400004dc;
|
||||
isalpha = 0x400004e0;
|
||||
isdigit = 0x400004f0;
|
||||
islower = 0x400004f4;
|
||||
isspace = 0x40000504;
|
||||
isupper = 0x40000508;
|
||||
strcasecmp = 0x40000524;
|
||||
strcoll = 0x4000053c;
|
||||
strlwr = 0x40000548;
|
||||
strncasecmp = 0x4000054c;
|
||||
strupr = 0x4000056c;
|
||||
|
||||
@@ -9,41 +9,28 @@ strlen = 0x400004d8;
|
||||
strstr = 0x400004dc;
|
||||
bzero = 0x400004e0;
|
||||
sbrk = 0x400004e8;
|
||||
isalnum = 0x400004ec;
|
||||
isalpha = 0x400004f0;
|
||||
isascii = 0x400004f4;
|
||||
isblank = 0x400004f8;
|
||||
iscntrl = 0x400004fc;
|
||||
isdigit = 0x40000500;
|
||||
islower = 0x40000504;
|
||||
isgraph = 0x40000508;
|
||||
isprint = 0x4000050c;
|
||||
ispunct = 0x40000510;
|
||||
isspace = 0x40000514;
|
||||
isupper = 0x40000518;
|
||||
toupper = 0x4000051c;
|
||||
tolower = 0x40000520;
|
||||
toascii = 0x40000524;
|
||||
memccpy = 0x40000528;
|
||||
memchr = 0x4000052c;
|
||||
memrchr = 0x40000530;
|
||||
strcasecmp = 0x40000534;
|
||||
strcasestr = 0x40000538;
|
||||
strcat = 0x4000053c;
|
||||
strchr = 0x40000544;
|
||||
strcspn = 0x40000548;
|
||||
strcoll = 0x4000054c;
|
||||
strlcat = 0x40000550;
|
||||
strlcpy = 0x40000554;
|
||||
strlwr = 0x40000558;
|
||||
strncasecmp = 0x4000055c;
|
||||
strncat = 0x40000560;
|
||||
strnlen = 0x40000568;
|
||||
strrchr = 0x4000056c;
|
||||
strsep = 0x40000570;
|
||||
strspn = 0x40000574;
|
||||
strtok_r = 0x40000578;
|
||||
strupr = 0x4000057c;
|
||||
longjmp = 0x40000580;
|
||||
setjmp = 0x40000584;
|
||||
abs = 0x40000588;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -39,3 +39,16 @@ __swhatbuf_r = 0x400005d4;
|
||||
__swbuf_r = 0x400005d8;
|
||||
__swbuf = 0x400005dc;
|
||||
__swsetup_r = 0x400005e0;
|
||||
toupper = 0x4000051c;
|
||||
tolower = 0x40000520;
|
||||
isalnum = 0x400004ec;
|
||||
isalpha = 0x400004f0;
|
||||
isdigit = 0x40000500;
|
||||
islower = 0x40000504;
|
||||
isspace = 0x40000514;
|
||||
isupper = 0x40000518;
|
||||
strcasecmp = 0x40000534;
|
||||
strcoll = 0x4000054c;
|
||||
strlwr = 0x40000558;
|
||||
strncasecmp = 0x4000055c;
|
||||
strupr = 0x4000057c;
|
||||
|
||||
@@ -9,41 +9,28 @@ strlen = 0x400004c0;
|
||||
strstr = 0x400004c4;
|
||||
bzero = 0x400004c8;
|
||||
sbrk = 0x400004d0;
|
||||
isalnum = 0x400004d4;
|
||||
isalpha = 0x400004d8;
|
||||
isascii = 0x400004dc;
|
||||
isblank = 0x400004e0;
|
||||
iscntrl = 0x400004e4;
|
||||
isdigit = 0x400004e8;
|
||||
islower = 0x400004ec;
|
||||
isgraph = 0x400004f0;
|
||||
isprint = 0x400004f4;
|
||||
ispunct = 0x400004f8;
|
||||
isspace = 0x400004fc;
|
||||
isupper = 0x40000500;
|
||||
toupper = 0x40000504;
|
||||
tolower = 0x40000508;
|
||||
toascii = 0x4000050c;
|
||||
memccpy = 0x40000510;
|
||||
memchr = 0x40000514;
|
||||
memrchr = 0x40000518;
|
||||
strcasecmp = 0x4000051c;
|
||||
strcasestr = 0x40000520;
|
||||
strcat = 0x40000524;
|
||||
strchr = 0x4000052c;
|
||||
strcspn = 0x40000530;
|
||||
strcoll = 0x40000534;
|
||||
strlcat = 0x40000538;
|
||||
strlcpy = 0x4000053c;
|
||||
strlwr = 0x40000540;
|
||||
strncasecmp = 0x40000544;
|
||||
strncat = 0x40000548;
|
||||
strnlen = 0x40000550;
|
||||
strrchr = 0x40000554;
|
||||
strsep = 0x40000558;
|
||||
strspn = 0x4000055c;
|
||||
strtok_r = 0x40000560;
|
||||
strupr = 0x40000564;
|
||||
longjmp = 0x40000568;
|
||||
setjmp = 0x4000056c;
|
||||
abs = 0x40000570;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2022-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -39,3 +39,16 @@ __swhatbuf_r = 0x400005bc;
|
||||
__swbuf_r = 0x400005c0;
|
||||
__swbuf = 0x400005c4;
|
||||
__swsetup_r = 0x400005c8;
|
||||
toupper = 0x40000504;
|
||||
tolower = 0x40000508;
|
||||
isalnum = 0x400004d4;
|
||||
isalpha = 0x400004d8;
|
||||
isdigit = 0x400004e8;
|
||||
islower = 0x400004ec;
|
||||
isspace = 0x400004fc;
|
||||
isupper = 0x40000500;
|
||||
strcasecmp = 0x4000051c;
|
||||
strcoll = 0x40000534;
|
||||
strlwr = 0x40000540;
|
||||
strncasecmp = 0x40000544;
|
||||
strupr = 0x40000564;
|
||||
|
||||
@@ -9,41 +9,28 @@ strlen = 0x400004b8;
|
||||
strstr = 0x400004bc;
|
||||
bzero = 0x400004c0;
|
||||
sbrk = 0x400004c8;
|
||||
isalnum = 0x400004cc;
|
||||
isalpha = 0x400004d0;
|
||||
isascii = 0x400004d4;
|
||||
isblank = 0x400004d8;
|
||||
iscntrl = 0x400004dc;
|
||||
isdigit = 0x400004e0;
|
||||
islower = 0x400004e4;
|
||||
isgraph = 0x400004e8;
|
||||
isprint = 0x400004ec;
|
||||
ispunct = 0x400004f0;
|
||||
isspace = 0x400004f4;
|
||||
isupper = 0x400004f8;
|
||||
toupper = 0x400004fc;
|
||||
tolower = 0x40000500;
|
||||
toascii = 0x40000504;
|
||||
memccpy = 0x40000508;
|
||||
memchr = 0x4000050c;
|
||||
memrchr = 0x40000510;
|
||||
strcasecmp = 0x40000514;
|
||||
strcasestr = 0x40000518;
|
||||
strcat = 0x4000051c;
|
||||
strchr = 0x40000524;
|
||||
strcspn = 0x40000528;
|
||||
strcoll = 0x4000052c;
|
||||
strlcat = 0x40000530;
|
||||
strlcpy = 0x40000534;
|
||||
strlwr = 0x40000538;
|
||||
strncasecmp = 0x4000053c;
|
||||
strncat = 0x40000540;
|
||||
strnlen = 0x40000548;
|
||||
strrchr = 0x4000054c;
|
||||
strsep = 0x40000550;
|
||||
strspn = 0x40000554;
|
||||
strtok_r = 0x40000558;
|
||||
strupr = 0x4000055c;
|
||||
longjmp = 0x40000560;
|
||||
setjmp = 0x40000564;
|
||||
abs = 0x40000568;
|
||||
|
||||
@@ -39,3 +39,16 @@ __swhatbuf_r = 0x400005b4;
|
||||
__swbuf_r = 0x400005b8;
|
||||
__swbuf = 0x400005bc;
|
||||
__swsetup_r = 0x400005c0;
|
||||
toupper = 0x400004fc;
|
||||
tolower = 0x40000500;
|
||||
isalnum = 0x400004cc;
|
||||
isalpha = 0x400004d0;
|
||||
isdigit = 0x400004e0;
|
||||
islower = 0x400004e4;
|
||||
isspace = 0x400004f4;
|
||||
isupper = 0x400004f8;
|
||||
strcasecmp = 0x40000514;
|
||||
strcoll = 0x4000052c;
|
||||
strlwr = 0x40000538;
|
||||
strncasecmp = 0x4000053c;
|
||||
strupr = 0x4000055c;
|
||||
|
||||
@@ -9,41 +9,28 @@ strlen = 0x4fc00288;
|
||||
strstr = 0x4fc0028c;
|
||||
bzero = 0x4fc00290;
|
||||
sbrk = 0x4fc00298;
|
||||
isalnum = 0x4fc0029c;
|
||||
isalpha = 0x4fc002a0;
|
||||
isascii = 0x4fc002a4;
|
||||
isblank = 0x4fc002a8;
|
||||
iscntrl = 0x4fc002ac;
|
||||
isdigit = 0x4fc002b0;
|
||||
islower = 0x4fc002b4;
|
||||
isgraph = 0x4fc002b8;
|
||||
isprint = 0x4fc002bc;
|
||||
ispunct = 0x4fc002c0;
|
||||
isspace = 0x4fc002c4;
|
||||
isupper = 0x4fc002c8;
|
||||
toupper = 0x4fc002cc;
|
||||
tolower = 0x4fc002d0;
|
||||
toascii = 0x4fc002d4;
|
||||
memccpy = 0x4fc002d8;
|
||||
memchr = 0x4fc002dc;
|
||||
memrchr = 0x4fc002e0;
|
||||
strcasecmp = 0x4fc002e4;
|
||||
strcasestr = 0x4fc002e8;
|
||||
strcat = 0x4fc002ec;
|
||||
strchr = 0x4fc002f4;
|
||||
strcspn = 0x4fc002f8;
|
||||
strcoll = 0x4fc002fc;
|
||||
strlcat = 0x4fc00300;
|
||||
strlcpy = 0x4fc00304;
|
||||
strlwr = 0x4fc00308;
|
||||
strncasecmp = 0x4fc0030c;
|
||||
strncat = 0x4fc00310;
|
||||
strnlen = 0x4fc00318;
|
||||
strrchr = 0x4fc0031c;
|
||||
strsep = 0x4fc00320;
|
||||
strspn = 0x4fc00324;
|
||||
strtok_r = 0x4fc00328;
|
||||
strupr = 0x4fc0032c;
|
||||
longjmp = 0x4fc00330;
|
||||
setjmp = 0x4fc00334;
|
||||
abs = 0x4fc00338;
|
||||
|
||||
@@ -39,3 +39,16 @@ __swhatbuf_r = 0x4fc00384;
|
||||
__swbuf_r = 0x4fc00388;
|
||||
__swbuf = 0x4fc0038c;
|
||||
__swsetup_r = 0x4fc00390;
|
||||
toupper = 0x4fc002cc;
|
||||
tolower = 0x4fc002d0;
|
||||
isalnum = 0x4fc0029c;
|
||||
isalpha = 0x4fc002a0;
|
||||
isdigit = 0x4fc002b0;
|
||||
islower = 0x4fc002b4;
|
||||
isspace = 0x4fc002c4;
|
||||
isupper = 0x4fc002c8;
|
||||
strcasecmp = 0x4fc002e4;
|
||||
strcoll = 0x4fc002fc;
|
||||
strlwr = 0x4fc00308;
|
||||
strncasecmp = 0x4fc0030c;
|
||||
strupr = 0x4fc0032c;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -17,18 +17,12 @@ PROVIDE ( __assert = 0x4001a430 );
|
||||
PROVIDE ( __assert_func = 0x4001a408 );
|
||||
bzero = 0x400078c8;
|
||||
div = 0x40000620;
|
||||
isalnum = 0x400078d8;
|
||||
isalpha = 0x400078e8;
|
||||
isascii = 0x4001aaec;
|
||||
isblank = 0x400078f8;
|
||||
iscntrl = 0x40007918;
|
||||
isdigit = 0x40007930;
|
||||
isgraph = 0x40007968;
|
||||
islower = 0x40007948;
|
||||
isprint = 0x40007980;
|
||||
ispunct = 0x40007994;
|
||||
isspace = 0x400079ac;
|
||||
isupper = 0x400079c4;
|
||||
labs = 0x40000648;
|
||||
ldiv = 0x40000650;
|
||||
longjmp = 0x400005a4;
|
||||
@@ -44,14 +38,11 @@ setjmp = 0x40000540;
|
||||
strcat = 0x4001ad90;
|
||||
strchr = 0x4001adb0;
|
||||
strcmp = 0x40007be4;
|
||||
strcoll = 0x40007ce8;
|
||||
strcpy = 0x40007cfc;
|
||||
strcspn = 0x4001adcc;
|
||||
strlcat = 0x40007db8;
|
||||
strlcpy = 0x4001adf8;
|
||||
strlen = 0x40007e08;
|
||||
strlwr = 0x40007e68;
|
||||
strncasecmp = 0x40007e94;
|
||||
strncat = 0x4001ae34;
|
||||
strncmp = 0x4001ae64;
|
||||
strncpy = 0x40007f20;
|
||||
@@ -62,7 +53,4 @@ strspn = 0x4001aebc;
|
||||
strstr = 0x4001aee8;
|
||||
__strtok_r = 0x4001af18;
|
||||
strtok_r = 0x4001af7c;
|
||||
strupr = 0x40008084;
|
||||
toascii = 0x4001af90;
|
||||
tolower = 0x40008158;
|
||||
toupper = 0x40008174;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2023-2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2023-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -50,3 +50,15 @@ __locale_ctype_ptr_l = 0x40001c24;
|
||||
__locale_mb_cur_max = 0x40001c0c;
|
||||
strcasecmp = 0x40007b38;
|
||||
strcasestr = 0x40007b7c;
|
||||
tolower = 0x40008158;
|
||||
toupper = 0x40008174;
|
||||
isalnum = 0x400078d8;
|
||||
isalpha = 0x400078e8;
|
||||
isdigit = 0x40007930;
|
||||
islower = 0x40007948;
|
||||
isspace = 0x400079ac;
|
||||
isupper = 0x400079c4;
|
||||
strcoll = 0x40007ce8;
|
||||
strlwr = 0x40007e68;
|
||||
strncasecmp = 0x40007e94;
|
||||
strupr = 0x40008084;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -16,41 +16,28 @@ strlen = 0x40001248;
|
||||
strstr = 0x40001254;
|
||||
bzero = 0x40001260;
|
||||
sbrk = 0x40001278;
|
||||
isalnum = 0x40001284;
|
||||
isalpha = 0x40001290;
|
||||
isascii = 0x4000129c;
|
||||
isblank = 0x400012a8;
|
||||
iscntrl = 0x400012b4;
|
||||
isdigit = 0x400012c0;
|
||||
islower = 0x400012cc;
|
||||
isgraph = 0x400012d8;
|
||||
isprint = 0x400012e4;
|
||||
ispunct = 0x400012f0;
|
||||
isspace = 0x400012fc;
|
||||
isupper = 0x40001308;
|
||||
toupper = 0x40001314;
|
||||
tolower = 0x40001320;
|
||||
toascii = 0x4000132c;
|
||||
memccpy = 0x40001338;
|
||||
memchr = 0x40001344;
|
||||
memrchr = 0x40001350;
|
||||
strcasecmp = 0x4000135c;
|
||||
strcasestr = 0x40001368;
|
||||
strcat = 0x40001374;
|
||||
strchr = 0x4000138c;
|
||||
strcspn = 0x40001398;
|
||||
strcoll = 0x400013a4;
|
||||
strlcat = 0x400013b0;
|
||||
strlcpy = 0x400013bc;
|
||||
strlwr = 0x400013c8;
|
||||
strncasecmp = 0x400013d4;
|
||||
strncat = 0x400013e0;
|
||||
strnlen = 0x400013f8;
|
||||
strrchr = 0x40001404;
|
||||
strsep = 0x40001410;
|
||||
strspn = 0x4000141c;
|
||||
strtok_r = 0x40001428;
|
||||
strupr = 0x40001434;
|
||||
longjmp = 0x40001440;
|
||||
setjmp = 0x4000144c;
|
||||
abs = 0x40001458;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -29,3 +29,16 @@ PROVIDE( _fwalk = 0x40001518 );
|
||||
PROVIDE( _fwalk_reent = 0x40001524 );
|
||||
PROVIDE( __swbuf_r = 0x40001548 );
|
||||
__swbuf = 0x40001554;
|
||||
toupper = 0x40001314;
|
||||
tolower = 0x40001320;
|
||||
isalnum = 0x40001284;
|
||||
isalpha = 0x40001290;
|
||||
isdigit = 0x400012c0;
|
||||
islower = 0x400012cc;
|
||||
isspace = 0x400012fc;
|
||||
isupper = 0x40001308;
|
||||
strcasecmp = 0x4000135c;
|
||||
strcoll = 0x400013a4;
|
||||
strlwr = 0x400013c8;
|
||||
strncasecmp = 0x400013d4;
|
||||
strupr = 0x40001434;
|
||||
|
||||
@@ -66,7 +66,9 @@
|
||||
* And so forth...
|
||||
*/
|
||||
*(.rela.*)
|
||||
#if CONFIG_LIBC_NEWLIB
|
||||
*(.got .got.plt) /* TODO: GCC-382 */
|
||||
#endif
|
||||
#if !EH_FRAME_LINKING_ENABLED
|
||||
*(.eh_frame_hdr)
|
||||
*(.eh_frame)
|
||||
|
||||
@@ -384,12 +384,24 @@ SECTIONS
|
||||
|
||||
/* TLS data. */
|
||||
ALIGNED_SYMBOL(4, _thread_local_start)
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata)
|
||||
*(.tdata.*)
|
||||
*(.tbss)
|
||||
*(.tbss.*)
|
||||
_thread_local_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
_flash_rodata_align = ALIGNOF(.flash.rodata);
|
||||
|
||||
|
||||
@@ -188,6 +188,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -262,24 +265,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -292,7 +312,7 @@ SECTIONS
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -310,6 +310,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -384,24 +387,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -414,7 +434,7 @@ SECTIONS
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -359,6 +359,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -433,32 +436,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -466,12 +478,18 @@ SECTIONS
|
||||
*/
|
||||
.flash.rodata_noload (NOLOAD) :
|
||||
{
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/**
|
||||
* This symbol marks the end of flash.rodata. It can be utilized by the MMU
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -355,6 +355,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -429,24 +432,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -459,7 +479,7 @@ SECTIONS
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -204,6 +204,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -278,32 +281,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -311,12 +323,18 @@ SECTIONS
|
||||
*/
|
||||
.flash.rodata_noload (NOLOAD) :
|
||||
{
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/**
|
||||
* This symbol marks the end of flash.rodata. It can be utilized by the MMU
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -357,6 +357,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -431,24 +434,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -461,7 +481,7 @@ SECTIONS
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -346,6 +346,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -420,24 +423,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -450,7 +470,7 @@ SECTIONS
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -191,6 +191,9 @@ SECTIONS
|
||||
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -265,24 +268,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -295,7 +315,7 @@ SECTIONS
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
mapping[rodata_noload]
|
||||
} > default_rodata_seg
|
||||
|
||||
@@ -362,6 +362,9 @@ SECTIONS
|
||||
arrays[flash_rodata]
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -442,32 +445,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > rodata_seg_low
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > rodata_seg_low
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -475,12 +487,18 @@ SECTIONS
|
||||
*/
|
||||
.flash.rodata_noload (NOLOAD) :
|
||||
{
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/**
|
||||
* This symbol marks the end of flash.rodata. It can be utilized by the MMU
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
arrays[rodata_noload]
|
||||
mapping[rodata_noload]
|
||||
|
||||
@@ -388,6 +388,9 @@ SECTIONS
|
||||
arrays[flash_rodata]
|
||||
mapping[flash_rodata]
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
*(.got .got.plt) /* TODO: GCC-439 */
|
||||
#endif
|
||||
*(.irom1.text) /* catch stray ICACHE_RODATA_ATTR */
|
||||
*(.gnu.linkonce.r.*)
|
||||
*(.rodata1)
|
||||
@@ -405,6 +408,7 @@ SECTIONS
|
||||
* Excluding crtbegin.o/crtend.o since IDF doesn't use the toolchain crt.
|
||||
*/
|
||||
ALIGNED_SYMBOL(4, __preinit_array_start)
|
||||
ALIGNED_SYMBOL(4, __bothinit_array_start)
|
||||
KEEP (*(.preinit_array))
|
||||
__preinit_array_end = ABSOLUTE(.);
|
||||
|
||||
@@ -417,6 +421,7 @@ SECTIONS
|
||||
ALIGNED_SYMBOL(4, __init_array_start)
|
||||
KEEP (*(EXCLUDE_FILE (*crtend.* *crtbegin.*) .init_array))
|
||||
__init_array_end = ABSOLUTE(.);
|
||||
__bothinit_array_end = ABSOLUTE(.);
|
||||
|
||||
/* Addresses of memory regions reserved via SOC_RESERVE_MEMORY_REGION() */
|
||||
ALIGNED_SYMBOL(4, soc_reserved_memory_region_start)
|
||||
@@ -466,32 +471,41 @@ SECTIONS
|
||||
|
||||
.flash.tdata :
|
||||
{
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
/* Keep tdata and tbss sections contiguous (no gaps between them).
|
||||
* The TLS runtime code calculates offsets assuming these sections are
|
||||
* adjacent. Gaps would cause incorrect address calculations, leading
|
||||
* to accessing wrong memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
|
||||
/* tdata sections */
|
||||
_thread_local_data_start = ABSOLUTE(.);
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata .tdata.* .gnu.linkonce.td.*)
|
||||
. = ALIGN(ALIGNOF(.flash.tbss));
|
||||
_thread_local_data_end = ABSOLUTE(.);
|
||||
} > rodata_seg_low
|
||||
ASSERT_SECTIONS_GAP(.flash.tdata, .flash.tbss)
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
.flash.tbss (NOLOAD) :
|
||||
{
|
||||
/* tbss sections */
|
||||
_thread_local_bss_start = ABSOLUTE(.);
|
||||
|
||||
*(.tbss .tbss.* .gnu.linkonce.tb.*)
|
||||
*(.tcommon .tcommon.*)
|
||||
|
||||
_thread_local_bss_end = ABSOLUTE(.);
|
||||
} > rodata_seg_low
|
||||
ASSERT(_thread_local_data_end == _thread_local_bss_start,
|
||||
"tdata and tbss must be contiguous.")
|
||||
|
||||
/**
|
||||
* This section contains all the rodata that is not used
|
||||
@@ -499,12 +513,18 @@ SECTIONS
|
||||
*/
|
||||
.flash.rodata_noload (NOLOAD) :
|
||||
{
|
||||
#if CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/* Align the end of flash rodata region as per PMP granularity to allow using the
|
||||
* page alignment gap created while mapping the flash region into the PSRAM memory.
|
||||
*/
|
||||
. = ALIGN(_esp_pmp_align_size);
|
||||
#endif // CONFIG_SPIRAM_RODATA && CONFIG_SPIRAM_PRE_CONFIGURE_MEMORY_PROTECTION
|
||||
/**
|
||||
* This symbol marks the end of flash.rodata. It can be utilized by the MMU
|
||||
* driver to maintain the virtual address.
|
||||
* NOLOAD rodata may not be included in this section.
|
||||
*/
|
||||
_rodata_reserved_end = ADDR(.flash.tbss);
|
||||
_rodata_reserved_end = .;
|
||||
|
||||
arrays[rodata_noload]
|
||||
mapping[rodata_noload]
|
||||
|
||||
@@ -387,12 +387,24 @@ SECTIONS
|
||||
|
||||
/* TLS data. */
|
||||
ALIGNED_SYMBOL(4, _thread_local_start)
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata)
|
||||
*(.tdata.*)
|
||||
*(.tbss)
|
||||
*(.tbss.*)
|
||||
_thread_local_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
_flash_rodata_align = ALIGNOF(.flash.rodata);
|
||||
|
||||
|
||||
@@ -399,12 +399,24 @@ SECTIONS
|
||||
|
||||
/* TLS data. */
|
||||
ALIGNED_SYMBOL(4, _thread_local_start)
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
_picolibc_reent_stub_start = ABSOLUTE(.);
|
||||
KEEP(*(.tdata.errno))
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
/* Reproduce the public fields from struct _reent. */
|
||||
KEEP(*(.tdata.tls_stdin))
|
||||
KEEP(*(.tdata.tls_stdout))
|
||||
KEEP(*(.tdata.tls_stderr))
|
||||
#endif // CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
_picolibc_reent_stub_end = ABSOLUTE(.);
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
*(.tdata)
|
||||
*(.tdata.*)
|
||||
*(.tbss)
|
||||
*(.tbss.*)
|
||||
_thread_local_end = ABSOLUTE(.);
|
||||
} > default_rodata_seg
|
||||
ASSERT_PICOLIBC_REENT_STUB()
|
||||
|
||||
_flash_rodata_align = ALIGNOF(.flash.rodata);
|
||||
|
||||
|
||||
@@ -109,3 +109,14 @@ ASSERT((ADDR(NEXT_SECTION) == ADDR(PREV_SECTION) + SIZEOF(PREV_SECTION)), \
|
||||
#else
|
||||
#define SECTION_AFTER_FLASH_RODATA .flash.tdata
|
||||
#endif
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
# if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
# define PICOLIBC_REENT_STUB 16
|
||||
# else
|
||||
# define PICOLIBC_REENT_STUB 4
|
||||
# endif
|
||||
#define ASSERT_PICOLIBC_REENT_STUB() ASSERT((_picolibc_reent_stub_end - _picolibc_reent_stub_start) == PICOLIBC_REENT_STUB, "Newlib _reent stub have wrong size")
|
||||
#else
|
||||
#define ASSERT_PICOLIBC_REENT_STUB()
|
||||
#endif
|
||||
|
||||
@@ -194,6 +194,21 @@ static void core_intr_matrix_clear(void)
|
||||
#endif // SOC_INT_CLIC_SUPPORTED
|
||||
}
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
FORCE_INLINE_ATTR IRAM_ATTR void init_pre_rtos_tls_area(int cpu_num)
|
||||
{
|
||||
/**
|
||||
* Initialize the TLS area before RTOS starts, in case any code tries to access
|
||||
* TLS variables.
|
||||
*
|
||||
* TODO IDF-14914: Currently, we only initialize errno, which is the first TLS
|
||||
* variable as guaranteed by the linker script.
|
||||
*/
|
||||
static int s_errno_array[SOC_CPU_CORES_NUM];
|
||||
esp_cpu_set_threadptr(&s_errno_array[cpu_num]);
|
||||
}
|
||||
#endif
|
||||
|
||||
#if !CONFIG_ESP_SYSTEM_SINGLE_CORE_MODE
|
||||
void startup_resume_other_cores(void)
|
||||
{
|
||||
@@ -214,6 +229,10 @@ void ESP_SYSTEM_IRAM_ATTR call_start_cpu1(void)
|
||||
);
|
||||
#endif //#ifdef __riscv
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
init_pre_rtos_tls_area(1);
|
||||
#endif
|
||||
|
||||
#if SOC_BRANCH_PREDICTOR_SUPPORTED
|
||||
esp_cpu_branch_prediction_enable();
|
||||
#endif //#if SOC_BRANCH_PREDICTOR_SUPPORTED
|
||||
@@ -935,6 +954,10 @@ void IRAM_ATTR call_start_cpu0(void)
|
||||
// Clear BSS. Please do not attempt to do any complex stuff (like early logging) before this.
|
||||
init_bss(rst_reas);
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
init_pre_rtos_tls_area(0);
|
||||
#endif
|
||||
|
||||
// When the APP is loaded into ram for execution, some hardware initialization steps used to be executed in the
|
||||
// bootloader are done here.
|
||||
#if CONFIG_APP_BUILD_TYPE_RAM
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2021-2022 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2021-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -11,8 +11,20 @@
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
extern void __assert_func(const char *file, int line, const char *func, const char *expr);
|
||||
extern void abort(void);
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
#if defined(__cplusplus) && __cplusplus >= 201103L
|
||||
#define __noreturn [[noreturn]]
|
||||
#elif __has_attribute(__noreturn__)
|
||||
#define __noreturn __attribute__((__noreturn__))
|
||||
#else
|
||||
#define __noreturn
|
||||
#endif
|
||||
#else
|
||||
#define __noreturn
|
||||
#endif
|
||||
|
||||
__noreturn void __assert_func(const char *file, int line, const char *func, const char *expr);
|
||||
__noreturn void abort(void);
|
||||
|
||||
#ifndef __ASSERT_FUNC
|
||||
#ifdef __ASSERT_FUNCTION
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2022-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Unlicense OR CC0-1.0
|
||||
*/
|
||||
@@ -128,13 +128,21 @@ TEST_CASE("heap trace wrapped buffer check", "[heap-trace]")
|
||||
heap_trace_stop();
|
||||
}
|
||||
|
||||
static void print_floats_task(void *ignore)
|
||||
static void trace_libc_allocs_task(void *ignore)
|
||||
{
|
||||
heap_trace_start(HEAP_TRACE_ALL);
|
||||
|
||||
#if CONFIG_LIBC_NEWLIB
|
||||
char buf[16] = { };
|
||||
volatile float f = 12.3456;
|
||||
sprintf(buf, "%.4f", f);
|
||||
TEST_ASSERT_EQUAL_STRING("12.3456", buf);
|
||||
#endif
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
FILE* f = fdopen(100, "r");
|
||||
fclose(f);
|
||||
#endif
|
||||
|
||||
heap_trace_stop();
|
||||
|
||||
vTaskDelete(NULL);
|
||||
@@ -158,11 +166,10 @@ TEST_CASE("can trace allocations made by newlib", "[heap-trace]")
|
||||
- We also do the tracing in the task so we only capture things directly related to it.
|
||||
*/
|
||||
|
||||
xTaskCreate(print_floats_task, "print_float", 4096, NULL, 5, NULL);
|
||||
xTaskCreate(trace_libc_allocs_task, "trace_libc_allocs_task", 4096, NULL, 5, NULL);
|
||||
vTaskDelay(10);
|
||||
|
||||
/* has to be at least a few as newlib allocates via multiple different function calls */
|
||||
TEST_ASSERT(heap_trace_get_count() > 3);
|
||||
TEST_ASSERT(heap_trace_get_count() > 0);
|
||||
}
|
||||
|
||||
TEST_CASE("can stop recording allocs but continue recording frees", "[heap-trace]")
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*
|
||||
* SPDX-FileContributor: 2018-2022 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileContributor: 2018-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*/
|
||||
#ifndef __ARCH_CC_H__
|
||||
#define __ARCH_CC_H__
|
||||
@@ -25,10 +25,18 @@ extern "C" {
|
||||
#endif // BYTE_ORDER
|
||||
|
||||
#define LWIP_DONT_PROVIDE_BYTEORDER_FUNCTIONS
|
||||
#ifndef htons
|
||||
#define htons(x) __builtin_bswap16(x)
|
||||
#endif
|
||||
#ifndef ntohs
|
||||
#define ntohs(x) __builtin_bswap16(x)
|
||||
#endif
|
||||
#ifndef htonl
|
||||
#define htonl(x) __builtin_bswap32(x)
|
||||
#endif
|
||||
#ifndef ntohl
|
||||
#define ntohl(x) __builtin_bswap32(x)
|
||||
#endif
|
||||
|
||||
#ifndef CONFIG_LWIP_ESP_LWIP_ASSERT
|
||||
#define LWIP_NOASSERT 1
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
#include <esp_types.h>
|
||||
|
||||
#include "freertos/FreeRTOS.h"
|
||||
|
||||
@@ -63,7 +63,11 @@ else()
|
||||
list(APPEND srcs
|
||||
"src/picolibc/picolibc_init.c"
|
||||
"src/picolibc/rand.c"
|
||||
"src/picolibc/open_memstream.c")
|
||||
"src/picolibc/open_memstream.c"
|
||||
"src/picolibc/errno.c")
|
||||
if(CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY)
|
||||
list(APPEND srcs "src/picolibc/getreent.c")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
list(APPEND ldfragments "src/newlib.lf" "src/system_libs.lf")
|
||||
|
||||
@@ -7,10 +7,40 @@ menu "LibC"
|
||||
config LIBC_NEWLIB
|
||||
bool "NewLib"
|
||||
config LIBC_PICOLIBC
|
||||
bool "Picolibc (EXPERIMENTAL)"
|
||||
depends on !IDF_TOOLCHAIN_CLANG && IDF_EXPERIMENTAL_FEATURES
|
||||
bool "Picolibc"
|
||||
depends on !IDF_TOOLCHAIN_CLANG
|
||||
endchoice
|
||||
|
||||
config LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
bool "Provides limited interoperability with libraries built using Newlib headers"
|
||||
default y
|
||||
depends on LIBC_PICOLIBC
|
||||
help
|
||||
This option provides limited compatibility with libraries built using Newlib headers by:
|
||||
|
||||
Enabling hidden system-header inclusions that exist in Newlib.
|
||||
Adding tls_stdio, tls_stdout, and tls_stderr variables to Thread Local Storage
|
||||
to allow prebuilt libraries to access them via getreent().
|
||||
Providing an implementation of getreent() that returns the value of the thread-pointer register.
|
||||
|
||||
Limitations:
|
||||
|
||||
1. If your application or an external prebuilt library accesses Newlib "struct _reent" implicitly,
|
||||
this may cause memory corruption on the task stack. You have two options:
|
||||
|
||||
- Use libc API calls instead of directly accessing "struct _reent" fields.
|
||||
- Switch ESP-IDF to use the Newlib implementation by setting CONFIG_LIBC_NEWLIB=y in sdkconfig.
|
||||
|
||||
2. If your application uses a prebuilt library built with Newlib headers, you may encounter
|
||||
unexpected behavior when overriding stdin, stdout, and stderr. External prebuilt libraries
|
||||
can only read these streams, so overriding them will not affect as it was for Newlib.
|
||||
You have two options to fix this:
|
||||
|
||||
- Rebuild the library with Picolibc headers that follow POSIX-standardized stdin, stdout,
|
||||
and stderr declarations.
|
||||
- Switch ESP-IDF to use the Newlib implementation by setting CONFIG_LIBC_NEWLIB=y in sdkconfig.
|
||||
|
||||
|
||||
config LIBC_MISC_IN_IRAM
|
||||
bool "Place misc libc functions (abort/assert/stdatomics) in IRAM" if SPI_FLASH_AUTO_SUSPEND
|
||||
default y
|
||||
@@ -18,7 +48,6 @@ menu "LibC"
|
||||
config LIBC_LOCKS_PLACE_IN_IRAM
|
||||
bool "Place lock API in IRAM"
|
||||
default y
|
||||
depends on LIBC_NEWLIB
|
||||
help
|
||||
Enable this option to include be able to call the lock API from
|
||||
code that runs while cache is disabled, e.g. IRAM interrupts.
|
||||
|
||||
@@ -1,16 +1,24 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include_next <stdio.h>
|
||||
#include "sdkconfig.h"
|
||||
|
||||
#include_next <stdio.h>
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
#include <stddef.h>
|
||||
void flockfile(FILE *);
|
||||
void funlockfile(FILE *);
|
||||
FILE *open_memstream(char **, size_t *);
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -9,6 +9,8 @@
|
||||
|
||||
#if CONFIG_LIBC_NEWLIB
|
||||
#include_next <stdio_ext.h>
|
||||
#else
|
||||
#endif
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
#include <stdio-bufio.h>
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,12 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#include_next <sys/cdefs.h>
|
||||
#include "sdkconfig.h"
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
#include <stdint.h>
|
||||
#include <stddef.h>
|
||||
#endif
|
||||
@@ -0,0 +1,13 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#include "sdkconfig.h"
|
||||
|
||||
#include_next <sys/fcntl.h>
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
#include <time.h>
|
||||
#include <sys/time.h>
|
||||
#endif
|
||||
@@ -1,9 +1,13 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2022-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "sdkconfig.h"
|
||||
|
||||
#if CONFIG_LIBC_NEWLIB
|
||||
/* Newlib sys/time.h defines timerisset, timerclear, timercmp, timeradd, timersub macros
|
||||
for __CYGWIN__ and __rtems__. We want to define these macros in IDF as well.
|
||||
Since we wish to use un-modified newlib headers until a patched newlib version is
|
||||
@@ -20,3 +24,10 @@
|
||||
#define __rtems__
|
||||
#include_next <sys/time.h>
|
||||
#undef __rtems__
|
||||
#else // CONFIG_LIBC_NEWLIB
|
||||
#include_next <sys/time.h>
|
||||
#endif // CONFIG_LIBC_NEWLIB
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
#include <sys/types.h>
|
||||
#endif
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2018-2022 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2018-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -7,6 +7,11 @@
|
||||
#pragma once
|
||||
|
||||
#include <sys/types.h>
|
||||
#include "sdkconfig.h"
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
#include <sys/select.h>
|
||||
#endif
|
||||
|
||||
#include_next <sys/unistd.h>
|
||||
|
||||
|
||||
@@ -16,6 +16,8 @@ if(CONFIG_IDF_TOOLCHAIN_GCC)
|
||||
else()
|
||||
idf_toolchain_remove_flags(LINK_OPTIONS "--specs=nano.specs")
|
||||
endif()
|
||||
|
||||
idf_toolchain_rerun_abi_detection()
|
||||
else() # TODO IDF-14338
|
||||
if(CONFIG_STDATOMIC_S32C1I_SPIRAM_WORKAROUND)
|
||||
idf_build_set_property(COMPILE_OPTIONS "-mdisable-hardware-atomics" APPEND)
|
||||
|
||||
@@ -1,9 +1,7 @@
|
||||
name: 'newlib'
|
||||
version: '4.3.0'
|
||||
cpe: cpe:2.3:a:newlib_project:newlib:{}:*:*:*:*:*:*:*
|
||||
name: 'esp_libc'
|
||||
supplier: 'Organization: Espressif Systems (Shanghai) CO LTD'
|
||||
originator: 'Organization: Red Hat Incorporated'
|
||||
originator: 'Organization: Espressif Systems (Shanghai) CO LTD'
|
||||
description: An open-source C standard library implementation with additional features and patches from Espressif.
|
||||
cve-exclude-list:
|
||||
- cve: CVE-2024-30949
|
||||
reason: A vulnerability was discovered in the gettimeofday system call implementation within the RISC-V libgloss component of Newlib. ESP-IDF does not link against libgloss for RISC-V, hence the issue is not directly applicable. Still, the relevant fix has been patched through https://github.com/espressif/newlib-esp32/commit/047ba47013c2656a1e7838dc86cbc75aeeaa67a7
|
||||
virtpackages:
|
||||
- sbom_newlibc.yml
|
||||
- sbom_picolibc.yml==
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
if: 'LIBC_NEWLIB'
|
||||
name: 'newlib'
|
||||
version: '4.3.0'
|
||||
cpe: cpe:2.3:a:newlib_project:newlib:{}:*:*:*:*:*:*:*
|
||||
supplier: 'Organization: Espressif Systems (Shanghai) CO LTD'
|
||||
originator: 'Organization: Red Hat Incorporated'
|
||||
description: Newlib is a small C standard library for embedded systems
|
||||
cve-exclude-list:
|
||||
- cve: CVE-2024-30949
|
||||
reason: A vulnerability was discovered in the gettimeofday system call implementation within the RISC-V libgloss component of Newlib. ESP-IDF does not link against libgloss for RISC-V, hence the issue is not directly applicable. Still, the relevant fix has been patched through https://github.com/espressif/newlib-esp32/commit/047ba47013c2656a1e7838dc86cbc75aeeaa67a7
|
||||
@@ -0,0 +1,6 @@
|
||||
if: 'LIBC_PICOLIBC'
|
||||
name: 'picolib'
|
||||
version: '1.8.10'
|
||||
supplier: 'Organization: Espressif Systems (Shanghai) CO LTD'
|
||||
originator: 'Organization: keithp.com/picolibc'
|
||||
description: C Libraries for Smaller Embedded Systems
|
||||
@@ -17,9 +17,9 @@
|
||||
#include "sdkconfig.h"
|
||||
|
||||
#if CONFIG_LIBC_LOCKS_PLACE_IN_IRAM
|
||||
#define NEWLIB_LOCKS_IRAM_ATTR IRAM_ATTR
|
||||
#define LIBC_LOCKS_IRAM_ATTR IRAM_ATTR
|
||||
#else
|
||||
#define NEWLIB_LOCKS_IRAM_ATTR
|
||||
#define LIBC_LOCKS_IRAM_ATTR
|
||||
#endif
|
||||
|
||||
/* Notes on our newlib lock implementation:
|
||||
@@ -50,7 +50,7 @@ static portMUX_TYPE lock_init_spinlock = portMUX_INITIALIZER_UNLOCKED;
|
||||
Called by _lock_init*, also called by _lock_acquire* to lazily initialize locks that might have
|
||||
been initialised (to zero only) before the RTOS scheduler started.
|
||||
*/
|
||||
static void NEWLIB_LOCKS_IRAM_ATTR lock_init_generic(_lock_t *lock, uint8_t mutex_type)
|
||||
static void LIBC_LOCKS_IRAM_ATTR lock_init_generic(_lock_t *lock, uint8_t mutex_type)
|
||||
{
|
||||
portENTER_CRITICAL(&lock_init_spinlock);
|
||||
if (*lock) {
|
||||
@@ -81,13 +81,13 @@ static void NEWLIB_LOCKS_IRAM_ATTR lock_init_generic(_lock_t *lock, uint8_t mute
|
||||
portEXIT_CRITICAL(&lock_init_spinlock);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR _lock_init(_lock_t *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR _lock_init(_lock_t *lock)
|
||||
{
|
||||
*lock = 0; // In case lock's memory is uninitialized
|
||||
lock_init_generic(lock, queueQUEUE_TYPE_MUTEX);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR _lock_init_recursive(_lock_t *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR _lock_init_recursive(_lock_t *lock)
|
||||
{
|
||||
*lock = 0; // In case lock's memory is uninitialized
|
||||
lock_init_generic(lock, queueQUEUE_TYPE_RECURSIVE_MUTEX);
|
||||
@@ -103,7 +103,7 @@ void NEWLIB_LOCKS_IRAM_ATTR _lock_init_recursive(_lock_t *lock)
|
||||
re-initialised if it is used again. Caller has to avoid doing
|
||||
this!
|
||||
*/
|
||||
void NEWLIB_LOCKS_IRAM_ATTR _lock_close(_lock_t *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR _lock_close(_lock_t *lock)
|
||||
{
|
||||
portENTER_CRITICAL(&lock_init_spinlock);
|
||||
if (*lock) {
|
||||
@@ -122,7 +122,7 @@ void _lock_close_recursive(_lock_t *lock) __attribute__((alias("_lock_close")));
|
||||
/* Acquire the mutex semaphore for lock. wait up to delay ticks.
|
||||
mutex_type is queueQUEUE_TYPE_RECURSIVE_MUTEX or queueQUEUE_TYPE_MUTEX
|
||||
*/
|
||||
static int NEWLIB_LOCKS_IRAM_ATTR lock_acquire_generic(_lock_t *lock, uint32_t delay, uint8_t mutex_type)
|
||||
static int LIBC_LOCKS_IRAM_ATTR lock_acquire_generic(_lock_t *lock, uint32_t delay, uint8_t mutex_type)
|
||||
{
|
||||
SemaphoreHandle_t h = (SemaphoreHandle_t)(*lock);
|
||||
if (!h) {
|
||||
@@ -164,22 +164,22 @@ static int NEWLIB_LOCKS_IRAM_ATTR lock_acquire_generic(_lock_t *lock, uint32_t d
|
||||
return (success == pdTRUE) ? 0 : -1;
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR _lock_acquire(_lock_t *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR _lock_acquire(_lock_t *lock)
|
||||
{
|
||||
lock_acquire_generic(lock, portMAX_DELAY, queueQUEUE_TYPE_MUTEX);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR _lock_acquire_recursive(_lock_t *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR _lock_acquire_recursive(_lock_t *lock)
|
||||
{
|
||||
lock_acquire_generic(lock, portMAX_DELAY, queueQUEUE_TYPE_RECURSIVE_MUTEX);
|
||||
}
|
||||
|
||||
int NEWLIB_LOCKS_IRAM_ATTR _lock_try_acquire(_lock_t *lock)
|
||||
int LIBC_LOCKS_IRAM_ATTR _lock_try_acquire(_lock_t *lock)
|
||||
{
|
||||
return lock_acquire_generic(lock, 0, queueQUEUE_TYPE_MUTEX);
|
||||
}
|
||||
|
||||
int NEWLIB_LOCKS_IRAM_ATTR _lock_try_acquire_recursive(_lock_t *lock)
|
||||
int LIBC_LOCKS_IRAM_ATTR _lock_try_acquire_recursive(_lock_t *lock)
|
||||
{
|
||||
return lock_acquire_generic(lock, 0, queueQUEUE_TYPE_RECURSIVE_MUTEX);
|
||||
}
|
||||
@@ -187,7 +187,7 @@ int NEWLIB_LOCKS_IRAM_ATTR _lock_try_acquire_recursive(_lock_t *lock)
|
||||
/* Release the mutex semaphore for lock.
|
||||
mutex_type is queueQUEUE_TYPE_RECURSIVE_MUTEX or queueQUEUE_TYPE_MUTEX
|
||||
*/
|
||||
static void NEWLIB_LOCKS_IRAM_ATTR lock_release_generic(_lock_t *lock, uint8_t mutex_type)
|
||||
static void LIBC_LOCKS_IRAM_ATTR lock_release_generic(_lock_t *lock, uint8_t mutex_type)
|
||||
{
|
||||
if (xTaskGetSchedulerState() == taskSCHEDULER_NOT_STARTED) {
|
||||
return; /* locking is a no-op before scheduler is up */
|
||||
@@ -213,12 +213,12 @@ static void NEWLIB_LOCKS_IRAM_ATTR lock_release_generic(_lock_t *lock, uint8_t m
|
||||
}
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR _lock_release(_lock_t *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR _lock_release(_lock_t *lock)
|
||||
{
|
||||
lock_release_generic(lock, queueQUEUE_TYPE_MUTEX);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR _lock_release_recursive(_lock_t *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR _lock_release_recursive(_lock_t *lock)
|
||||
{
|
||||
lock_release_generic(lock, queueQUEUE_TYPE_RECURSIVE_MUTEX);
|
||||
}
|
||||
@@ -291,69 +291,69 @@ static StaticSemaphore_t s_common_recursive_mutex;
|
||||
#define MAYBE_OVERRIDE_LOCK(_lock, _lock_to_use_instead)
|
||||
#endif // ROM_NEEDS_MUTEX_OVERRIDE
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_init(_LOCK_T *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_init(_LOCK_T *lock)
|
||||
{
|
||||
*lock = NULL; /* In case lock's memory is uninitialized */
|
||||
lock_init_generic(lock, queueQUEUE_TYPE_MUTEX);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_init_recursive(_LOCK_T *lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_init_recursive(_LOCK_T *lock)
|
||||
{
|
||||
*lock = NULL; /* In case lock's memory is uninitialized */
|
||||
lock_init_generic(lock, queueQUEUE_TYPE_RECURSIVE_MUTEX);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_close(_LOCK_T lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_close(_LOCK_T lock)
|
||||
{
|
||||
_lock_close(&lock);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_close_recursive(_LOCK_T lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_close_recursive(_LOCK_T lock)
|
||||
{
|
||||
_lock_close_recursive(&lock);
|
||||
}
|
||||
|
||||
/* Separate function, to prevent generating multiple assert strings */
|
||||
static void NEWLIB_LOCKS_IRAM_ATTR check_lock_nonzero(_LOCK_T lock)
|
||||
static void LIBC_LOCKS_IRAM_ATTR check_lock_nonzero(_LOCK_T lock)
|
||||
{
|
||||
assert(lock != NULL && "Uninitialized lock used");
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_acquire(_LOCK_T lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_acquire(_LOCK_T lock)
|
||||
{
|
||||
check_lock_nonzero(lock);
|
||||
MAYBE_OVERRIDE_LOCK(lock, &s_common_mutex);
|
||||
_lock_acquire(&lock);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_acquire_recursive(_LOCK_T lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_acquire_recursive(_LOCK_T lock)
|
||||
{
|
||||
check_lock_nonzero(lock);
|
||||
MAYBE_OVERRIDE_LOCK(lock, &s_common_recursive_mutex);
|
||||
_lock_acquire_recursive(&lock);
|
||||
}
|
||||
|
||||
int NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_try_acquire(_LOCK_T lock)
|
||||
int LIBC_LOCKS_IRAM_ATTR __retarget_lock_try_acquire(_LOCK_T lock)
|
||||
{
|
||||
check_lock_nonzero(lock);
|
||||
MAYBE_OVERRIDE_LOCK(lock, &s_common_mutex);
|
||||
return _lock_try_acquire(&lock);
|
||||
}
|
||||
|
||||
int NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_try_acquire_recursive(_LOCK_T lock)
|
||||
int LIBC_LOCKS_IRAM_ATTR __retarget_lock_try_acquire_recursive(_LOCK_T lock)
|
||||
{
|
||||
check_lock_nonzero(lock);
|
||||
MAYBE_OVERRIDE_LOCK(lock, &s_common_recursive_mutex);
|
||||
return _lock_try_acquire_recursive(&lock);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_release(_LOCK_T lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_release(_LOCK_T lock)
|
||||
{
|
||||
check_lock_nonzero(lock);
|
||||
_lock_release(&lock);
|
||||
}
|
||||
|
||||
void NEWLIB_LOCKS_IRAM_ATTR __retarget_lock_release_recursive(_LOCK_T lock)
|
||||
void LIBC_LOCKS_IRAM_ATTR __retarget_lock_release_recursive(_LOCK_T lock)
|
||||
{
|
||||
check_lock_nonzero(lock);
|
||||
_lock_release_recursive(&lock);
|
||||
|
||||
@@ -0,0 +1,22 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#include <errno.h>
|
||||
|
||||
/*
|
||||
* Picolibc does not initialize 'errno' and places it in the TBSS section.
|
||||
*
|
||||
* To allow convenient initialization and support interoperability with Newlib,
|
||||
* 'errno' is defined in the TDATA section. The linker script ensures that
|
||||
* it is positioned at the beginning of the TDATA segment.
|
||||
*/
|
||||
__thread int errno __attribute__((section(".tdata.errno"))) = 0;
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
int *__errno(void)
|
||||
{
|
||||
return &errno;
|
||||
}
|
||||
#endif
|
||||
@@ -0,0 +1,19 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#include <stdint.h>
|
||||
#include "esp_cpu.h"
|
||||
|
||||
void *__getreent(void)
|
||||
{
|
||||
/*
|
||||
* The linker script provides the basic _reent fields
|
||||
* used to access errno and stdin/stdout/stderr.
|
||||
*
|
||||
* Note: if code accesses other fields in struct _reent
|
||||
* that are not intended to be "public," data corruption may occur.
|
||||
*/
|
||||
return esp_cpu_get_threadptr();
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -33,17 +33,8 @@ static void esp_cleanup_r(struct _reent *rptr)
|
||||
#endif
|
||||
|
||||
#if ESP_ROM_HAS_RETARGETABLE_LOCKING
|
||||
static int __retarget_lock_try_acquire(struct __lock * p)
|
||||
{
|
||||
__retarget_lock_acquire(p);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int __retarget_lock_try_acquire_recursive(struct __lock *p)
|
||||
{
|
||||
__retarget_lock_acquire_recursive(p);
|
||||
return 0;
|
||||
}
|
||||
int __retarget_lock_try_acquire(struct __lock * p);
|
||||
int __retarget_lock_try_acquire_recursive(struct __lock *p);
|
||||
#endif
|
||||
|
||||
static struct syscall_stub_table s_stub_table = {
|
||||
@@ -143,20 +134,10 @@ void esp_reent_cleanup(void)
|
||||
return;
|
||||
}
|
||||
|
||||
#if CONFIG_VFS_SUPPORT_IO
|
||||
FILE *stdin;
|
||||
FILE *stdout;
|
||||
FILE *stderr;
|
||||
void esp_libc_init_global_stdio(const char *stdio_dev)
|
||||
{
|
||||
stdin = fopen(stdio_dev, "r");
|
||||
stdout = fopen(stdio_dev, "w");
|
||||
assert(stdin);
|
||||
assert(stdout);
|
||||
setlinebuf(stdout);
|
||||
stderr = stdout;
|
||||
}
|
||||
#else /* CONFIG_VFS_SUPPORT_IO */
|
||||
/*
|
||||
* Initialize stdin, stdout, and stderr using static memory allocation.
|
||||
* Creating them with fopen() would call malloc() internally.
|
||||
*/
|
||||
static char write_buf[BUFSIZ];
|
||||
static char read_buf[BUFSIZ];
|
||||
|
||||
@@ -166,10 +147,28 @@ static struct __file_bufio __stdout = FDEV_SETUP_BUFIO(1, write_buf, BUFSIZ, rea
|
||||
FILE *stdin = &__stdin.xfile.cfile.file;
|
||||
FILE *stdout = &__stdout.xfile.cfile.file;
|
||||
FILE *stderr = &__stdout.xfile.cfile.file;
|
||||
|
||||
#if CONFIG_LIBC_PICOLIBC_NEWLIB_COMPATIBILITY
|
||||
__thread FILE* tls_stdin = &__stdin.xfile.cfile.file;
|
||||
__thread FILE* tls_stdout = &__stdout.xfile.cfile.file;
|
||||
__thread FILE* tls_stderr = &__stdout.xfile.cfile.file;
|
||||
#endif
|
||||
|
||||
#if CONFIG_VFS_SUPPORT_IO
|
||||
void esp_libc_init_global_stdio(const char *stdio_dev)
|
||||
{
|
||||
int stdin_fd = open(stdio_dev, O_RDONLY);
|
||||
assert(stdin_fd > 0);
|
||||
__stdin.ptr = (void *)(intptr_t)(stdin_fd);
|
||||
|
||||
int stdout_fd = open(stdio_dev, O_WRONLY);
|
||||
assert(stdout_fd > 0);
|
||||
__stdout.ptr = (void *)(intptr_t)(stdout_fd);
|
||||
}
|
||||
#else /* CONFIG_VFS_SUPPORT_IO */
|
||||
void esp_libc_init_global_stdio(void)
|
||||
{
|
||||
__lock_init_recursive(stdin->lock);
|
||||
__lock_init_recursive(stdout->lock);
|
||||
/* Nothing to do. */
|
||||
}
|
||||
#endif /* CONFIG_VFS_SUPPORT_IO */
|
||||
|
||||
|
||||
@@ -105,6 +105,10 @@ int fcntl(int fd, int cmd, ...)
|
||||
return _fcntl_r(__getreent(), fd, cmd, arg);
|
||||
}
|
||||
|
||||
int getpid()
|
||||
{
|
||||
return _getpid_r(__getreent());
|
||||
}
|
||||
#endif // CONFIG_LIBC_PICOLIBC
|
||||
|
||||
void _exit(int __status)
|
||||
|
||||
@@ -131,6 +131,18 @@ FORCE_INLINE_ATTR void __attribute__((always_inline)) rv_utils_set_cycle_count(u
|
||||
#endif
|
||||
}
|
||||
|
||||
FORCE_INLINE_ATTR void rv_utils_set_threadptr(void *ptr)
|
||||
{
|
||||
asm volatile("mv tp, %0" :: "r"(ptr));
|
||||
}
|
||||
|
||||
FORCE_INLINE_ATTR void *rv_utils_get_threadptr(void)
|
||||
{
|
||||
void *thread_ptr;
|
||||
asm volatile("mv %0, tp" : "=r"(thread_ptr));
|
||||
return thread_ptr;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------- CPU Interrupts ----------------------------------------------------
|
||||
*
|
||||
* ------------------------------------------------------------------------------------------------------------------ */
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
|
||||
#include <stdint.h>
|
||||
#include <limits.h>
|
||||
#include <stddef.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include <stddef.h>
|
||||
#include "pmu_reg.h"
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
||||
@@ -36,14 +36,15 @@ if(CONFIG_IDF_TOOLCHAIN_GCC)
|
||||
# Clean compile options that were added by previous configurations and may be outdated
|
||||
idf_toolchain_remove_flags(COMPILE_OPTIONS "-march=")
|
||||
|
||||
if(CONFIG_SOC_CPU_HAS_HWLOOP)
|
||||
set(_march "${_march}_xesploop")
|
||||
endif()
|
||||
if(CONFIG_ESP32P4_SELECTS_REV_LESS_V3)
|
||||
set(_march "${_march}_xesppie")
|
||||
else()
|
||||
if(CONFIG_SOC_CPU_HAS_HWLOOP)
|
||||
set(_march "${_march}_xesploop")
|
||||
endif()
|
||||
|
||||
if(CONFIG_SOC_CPU_HAS_PIE)
|
||||
set(_march "${_march}_xespv")
|
||||
if(CONFIG_ESP32P4_SELECTS_REV_LESS_V3)
|
||||
set(_march "${_march}2p1")
|
||||
if(CONFIG_SOC_CPU_HAS_PIE)
|
||||
set(_march "${_march}_xespv")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
@@ -60,30 +61,8 @@ if(CONFIG_IDF_TOOLCHAIN_GCC)
|
||||
if(NOT CONFIG_SOC_CPU_MISALIGNED_ACCESS_ON_PMP_MISMATCH_ISSUE)
|
||||
idf_toolchain_add_flags(COMPILE_OPTIONS "-mtune=esp-base")
|
||||
endif()
|
||||
idf_toolchain_rerun_abi_detection()
|
||||
else()
|
||||
message(FATAL_ERROR "Unknown Espressif architecture: ${CONFIG_IDF_TARGET_ARCH}")
|
||||
endif()
|
||||
|
||||
# Workaround: Re-run CMake compiler ABI detection after ABI flags are set.
|
||||
#
|
||||
# Problem: CMake performs compiler checks at an early stage during
|
||||
# toolchain.cmake processing. At this early stage, response files are not yet
|
||||
# ready, which causes CMake paths (e.g., CMAKE_<lang>_IMPLICIT_LINK_DIRECTORIES)
|
||||
# to be incorrectly determined.
|
||||
#
|
||||
# Solution: Re-run the ABI detection after ABI flags are present to correctly
|
||||
# determine these paths.
|
||||
#
|
||||
# Note: If the CMake API changes, this solution may need to be revised.
|
||||
set(lang_ext_pairs "C|c" "CXX|cpp")
|
||||
include(${CMAKE_ROOT}/Modules/CMakeDetermineCompilerABI.cmake)
|
||||
foreach(lang_ext ${lang_ext_pairs})
|
||||
string(REPLACE "|" ";" lang_ext_parts ${lang_ext})
|
||||
list(GET lang_ext_parts 0 lang)
|
||||
list(GET lang_ext_parts 1 ext)
|
||||
if(DEFINED CMAKE_${lang}_ABI_COMPILED)
|
||||
unset(CMAKE_${lang}_ABI_COMPILED)
|
||||
cmake_determine_compiler_abi(${lang} ${CMAKE_ROOT}/Modules/CMake${lang}CompilerABI.${ext})
|
||||
endif()
|
||||
endforeach()
|
||||
endif()
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include <stdlib.h>
|
||||
#include <errno.h>
|
||||
#include <unistd.h>
|
||||
#include <sys/select.h>
|
||||
|
||||
#include "esp_tls.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
#!/usr/bin/env python
|
||||
# SPDX-FileCopyrightText: 2016-2024 Espressif Systems (Shanghai) CO LTD
|
||||
# SPDX-FileCopyrightText: 2016-2025 Espressif Systems (Shanghai) CO LTD
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
#
|
||||
# esp32ulp_mapgen utility converts a symbol list provided by nm into an export script
|
||||
@@ -16,50 +16,61 @@ UTIL = os.path.basename(__file__)
|
||||
def name_mangling(name: str) -> str:
|
||||
# Simple and dumb name mangling for namespaced name following GCC algorithm
|
||||
ns, n = name.split('::')
|
||||
return '_ZN{0}{1}{2}{3}E'.format(len(ns), ns, len(n), n)
|
||||
return f'_ZN{len(ns)}{ns}{len(n)}{n}E'
|
||||
|
||||
|
||||
def gen_ld_h_from_sym(f_sym: typing.TextIO, f_ld: typing.TextIO, f_h: typing.TextIO, base_addr: int, prefix: str) -> None:
|
||||
f_ld.write(textwrap.dedent(
|
||||
f"""
|
||||
def gen_ld_h_from_sym(
|
||||
f_sym: typing.TextIO, f_ld: typing.TextIO, f_h: typing.TextIO, base_addr: int, prefix: str
|
||||
) -> None:
|
||||
f_ld.write(
|
||||
textwrap.dedent(
|
||||
f"""
|
||||
/* ULP variable definitions for the linker.
|
||||
* This file is generated automatically by {UTIL} utility.
|
||||
*/
|
||||
""" # noqa: E222
|
||||
))
|
||||
)
|
||||
)
|
||||
cpp_mode = False
|
||||
var_prefix = prefix
|
||||
namespace = ''
|
||||
if '::' in prefix:
|
||||
# C++ mode, let's avoid the extern "C" type and instead use namespace
|
||||
f_h.write(textwrap.dedent(
|
||||
f"""
|
||||
f_h.write(
|
||||
textwrap.dedent(
|
||||
f"""
|
||||
/* ULP variable definitions for the compiler.
|
||||
* This file is generated automatically by {UTIL} utility.
|
||||
*/
|
||||
#pragma once
|
||||
""" # noqa: E222
|
||||
))
|
||||
)
|
||||
)
|
||||
tmp = prefix.split('::')
|
||||
namespace = tmp[0]
|
||||
var_prefix = '_'.join(tmp[1:]) # Limit to a single namespace here to avoid complex mangling rules
|
||||
f_h.write(f'namespace {namespace} {{\n')
|
||||
cpp_mode = True
|
||||
else:
|
||||
f_h.write(textwrap.dedent(
|
||||
f"""
|
||||
f_h.write(
|
||||
textwrap.dedent(
|
||||
f"""
|
||||
/* ULP variable definitions for the compiler.
|
||||
* This file is generated automatically by {UTIL} utility.
|
||||
*/
|
||||
#pragma once
|
||||
#include <stdint.h>
|
||||
#ifdef __cplusplus
|
||||
extern "C" {{
|
||||
#endif\n
|
||||
""" # noqa: E222
|
||||
))
|
||||
)
|
||||
)
|
||||
|
||||
# Format the regular expression to match the readelf output
|
||||
expr = re.compile(r'^.*(?P<address>[a-f0-9]{8})\s+(?P<size>\d+) (OBJECT|NOTYPE)\s+GLOBAL\s+DEFAULT\s+[^ ]+ (?P<name>.*)$')
|
||||
expr = re.compile(
|
||||
r'^.*(?P<address>[a-f0-9]{8})\s+(?P<size>\d+) (OBJECT|NOTYPE)\s+GLOBAL\s+DEFAULT\s+[^ ]+ (?P<name>.*)$'
|
||||
)
|
||||
for line in f_sym:
|
||||
# readelf format output has the following structure:
|
||||
# Num: Value Size Type Bind Vis Ndx Name
|
||||
@@ -90,23 +101,31 @@ def gen_ld_h_from_sym(f_sym: typing.TextIO, f_ld: typing.TextIO, f_h: typing.Tex
|
||||
if cpp_mode:
|
||||
f_h.write('}\n')
|
||||
else:
|
||||
f_h.write(textwrap.dedent(
|
||||
"""
|
||||
f_h.write(
|
||||
textwrap.dedent(
|
||||
"""
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
"""
|
||||
))
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
def main() -> None:
|
||||
description = ('This application generates .h and .ld files for symbols defined in input file. '
|
||||
'The input symbols file can be generated using readelf utility like this: '
|
||||
'<PREFIX>readelf -sW <elf_file> > <symbols_file>')
|
||||
description = (
|
||||
'This application generates .h and .ld files for symbols defined in input file. '
|
||||
'The input symbols file can be generated using readelf utility like this: '
|
||||
'<PREFIX>readelf -sW <elf_file> > <symbols_file>'
|
||||
)
|
||||
|
||||
parser = argparse.ArgumentParser(description=description)
|
||||
parser.add_argument('-s', '--symfile', required=True, help='symbols file name', metavar='SYMFILE', type=argparse.FileType('r'))
|
||||
parser.add_argument('-o', '--outputfile', required=True, help='destination .h and .ld files name prefix', metavar='OUTFILE')
|
||||
parser.add_argument(
|
||||
'-s', '--symfile', required=True, help='symbols file name', metavar='SYMFILE', type=argparse.FileType('r')
|
||||
)
|
||||
parser.add_argument(
|
||||
'-o', '--outputfile', required=True, help='destination .h and .ld files name prefix', metavar='OUTFILE'
|
||||
)
|
||||
parser.add_argument('--base-addr', required=True, help='base address of the ULP memory, to be added to each symbol')
|
||||
parser.add_argument('-p', '--prefix', required=False, help='prefix for generated header file', default='ulp_')
|
||||
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include "sdkconfig.h"
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
#include <unistd.h>
|
||||
#include <errno.h>
|
||||
#include <sys/fcntl.h>
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include <sys/fcntl.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/stat.h>
|
||||
#include "unity.h"
|
||||
#include "test_utils.h"
|
||||
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include <unistd.h>
|
||||
#include <sys/fcntl.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/select.h>
|
||||
#include "unity.h"
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "driver/uart.h"
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
#include <sys/unistd.h>
|
||||
#include <sys/lock.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/select.h>
|
||||
#include <dirent.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/semphr.h"
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2020-2025 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -82,6 +82,18 @@ FORCE_INLINE_ATTR void xt_utils_wait_for_intr(void)
|
||||
asm volatile ("waiti 0\n");
|
||||
}
|
||||
|
||||
FORCE_INLINE_ATTR void xt_utils_set_threadptr(void *ptr)
|
||||
{
|
||||
asm volatile ("wur.threadptr %0" :: "r"(ptr));
|
||||
}
|
||||
|
||||
FORCE_INLINE_ATTR void *xt_utils_get_threadptr(void)
|
||||
{
|
||||
void *thread_ptr;
|
||||
asm volatile ("rur.threadptr %0" : "=r"(thread_ptr));
|
||||
return thread_ptr;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------- CPU Interrupts ----------------------------------------------------
|
||||
*
|
||||
* ------------------------------------------------------------------------------------------------------------------ */
|
||||
|
||||
@@ -58,13 +58,26 @@ Enabling one of these option will cause the corresponding VFS driver to be built
|
||||
Standard Streams and FreeRTOS Tasks
|
||||
-----------------------------------
|
||||
|
||||
ESP-IDF provides two different implementations of standard I/O streams based on the selected LibC implementation defined by :ref:`CONFIG_LIBC`. The behavior of ``stdin``, ``stdout``, and ``stderr`` streams differs between these implementations, particularly regarding how they are shared across FreeRTOS tasks.
|
||||
|
||||
Common to both implementations, each stream (``stdin``, ``stdout``, ``stderr``) has a mutex associated with it to protect the stream from concurrent access by multiple tasks. For example, if two tasks are writing to ``stdout`` at the same time, the mutex ensures that the outputs from each task are not mixed together.
|
||||
|
||||
Newlib
|
||||
^^^^^^
|
||||
|
||||
In ESP-IDF, to save RAM, ``FILE`` objects for ``stdin``, ``stdout``, and ``stderr`` are shared between all FreeRTOS tasks, but the pointers to these objects are unique for every task. This means that:
|
||||
|
||||
- It is possible to change ``stdin``, ``stdout``, and ``stderr`` for any given task without affecting other tasks, e.g., by doing ``stdin = fopen("/dev/uart/1", "r")``.
|
||||
- To change the default ``stdin``, ``stdout``, ``stderr`` streams for new tasks, modify ``_GLOBAL_REENT->_stdin`` (``_stdout``, ``_stderr``) before creating the task.
|
||||
- Closing default ``stdin``, ``stdout``, or ``stderr`` using ``fclose`` closes the ``FILE`` stream object, which will affect all other tasks.
|
||||
|
||||
Each stream (``stdin``, ``stdout``, ``stderr``) has a mutex associated with it. This mutex is used to protect the stream from concurrent access by multiple tasks. For example, if two tasks are writing to ``stdout`` at the same time, the mutex will ensure that the outputs from each task are not mixed together.
|
||||
Picolibc
|
||||
^^^^^^^^
|
||||
|
||||
According to the POSIX standard, all default ``stdin``, ``stdout``, and ``stderr`` streams are global and shared between all FreeRTOS tasks. This means that:
|
||||
|
||||
- Modifying ``stdin``, ``stdout``, or ``stderr`` will affect all other tasks. It is not possible to change standard I/O streams for specific tasks.
|
||||
- If a thread-local stream is needed, it should be implemented in the application code by opening a file stream and using it within tasks, e.g., ``fscanf()``, ``fprintf()``, etc.
|
||||
|
||||
Blocking and non-blocking I/O
|
||||
-----------------------------
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
*/
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/time.h>
|
||||
#include "argtable3/argtable3.h"
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <string.h>
|
||||
#include <sys/time.h>
|
||||
#include "esp_err.h"
|
||||
#include "esp_event.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
#include "esp_vfs.h"
|
||||
#include "esp_vfs_fat.h"
|
||||
#include "esp_err.h"
|
||||
|
||||
@@ -155,3 +155,28 @@ endfunction()
|
||||
function(idf_toolchain_remove_flags)
|
||||
_process_toolchain_flag_options()
|
||||
endfunction()
|
||||
|
||||
# Workaround: Re-run CMake compiler ABI detection after ABI flags are set.
|
||||
#
|
||||
# Problem: CMake performs compiler checks at an early stage during
|
||||
# toolchain.cmake processing. At this early stage, response files are not yet
|
||||
# ready, which causes CMake paths (e.g., CMAKE_<lang>_IMPLICIT_LINK_DIRECTORIES)
|
||||
# to be incorrectly determined.
|
||||
#
|
||||
# Solution: Re-run the ABI detection after ABI flags are present to correctly
|
||||
# determine these paths.
|
||||
#
|
||||
# Note: If the CMake API changes, this solution may need to be revised.
|
||||
macro(idf_toolchain_rerun_abi_detection)
|
||||
set(lang_ext_pairs "C|c" "CXX|cpp")
|
||||
include(${CMAKE_ROOT}/Modules/CMakeDetermineCompilerABI.cmake)
|
||||
foreach(lang_ext ${lang_ext_pairs})
|
||||
string(REPLACE "|" ";" lang_ext_parts ${lang_ext})
|
||||
list(GET lang_ext_parts 0 lang)
|
||||
list(GET lang_ext_parts 1 ext)
|
||||
if(DEFINED CMAKE_${lang}_ABI_COMPILED)
|
||||
unset(CMAKE_${lang}_ABI_COMPILED)
|
||||
cmake_determine_compiler_abi(${lang} ${CMAKE_ROOT}/Modules/CMake${lang}CompilerABI.${ext})
|
||||
endif()
|
||||
endforeach()
|
||||
endmacro()
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
#include "esp_vfs.h"
|
||||
#include "esp_vfs_fat.h"
|
||||
#include "sdkconfig.h"
|
||||
|
||||
Reference in New Issue
Block a user