-
Notifications
You must be signed in to change notification settings - Fork 64
Use picolibc instead of newlib-nano #134
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Use picolibc instead of newlib-nano #134
Conversation
9cd8235 to
50a91d4
Compare
85833fd to
01be64f
Compare
|
These are (finally) passing Zephyr tests using both SDK 0.17 and SDK 0.18-alpha4 (although each requires some additional changes which are wending their way upstream). I think they're ready for review and help getting them upstream. |
| /* Reset current position for subsequent sections */ | ||
| . = LOADADDR(.ER_CODE_SRAM) + SIZEOF(.ER_CODE_SRAM); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How did the linker get confused exactly? Is this really needed?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
. got set to LOADADDR instead of ADDR when building with binutils 2.43. I'm afraid that after spending several hours chasing this down, I didn't dig into the linker code to figure out precisely why that happened.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've re-added this patch as it is necessary even with SDK 0.17.4.
tomi-font
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Had a chat with upstream about these (picolibc) changes. Let's keep them only in this fork until they're not needed anymore (TF-M is moving away from C library usage), in the next release or the one following it.
But it would be good to have someone who understands this a bit to review the changes. Don't know who that could be. cc @frkv @d3zd3z @ceolin @dleach02 @Vge0rge
Sounds good. I'll keep running tests as this series moves forward. This is not buildable using SDK 0.17.2 because of a last-minute oops in that release, but it should be buildable with the upcoming SDK 0.17.3. |
|
I recommend @wearyzen and @adeaarm give it a quick look from TF-M's perspective. The Clang/LLVM toolchain for TF-M was added with no dependency on libc and/or picolib in the core TF-M code, but you still see references to nano.specs in the GNUARM toolchain Zephyr, making this choice for GNUARM toolchain (this change), will take any penalty related to support, any security advisories etc... But the choice to go to picolibc is an active choice in the Zephyr community, and in extension it will impact any vendor who makes use of standard c library function in PSA crypto and PSA crypto driver build as well as in bootloaders... With regards to these commits, I think we should consider them to be marked as commits emitted from zephyr integration, unless they are possible to add upstream in the TF-M project... If they are out-of-tree patches required for Zephyr integration, they would need to be maintained across updated versions of TF-M in our fork |
Yeah this is something we've agreed on and I think just needs to be implemented (documenting the practice basically). In the meantime I don't think we can require that of anyone yet. |
|
True, TF-M plans to remove Additionally, you might want to consider these recent fixes in the scripts: |
|
Sounds like any libc-specific changes will be transient then, which will be nice. |
This adds linker script bits and compiler options so that trusted-firmware-m will build with picolibc. This has not been merged to the Zephyr trusted-firmware-m repository yet, that PR is zephyrproject-rtos/trusted-firmware-m#134 Signed-off-by: Keith Packard <keithp@keithp.com>
This adds linker script bits and compiler options so that trusted-firmware-m will build with picolibc. This has not been merged to the Zephyr trusted-firmware-m repository yet: zephyrproject-rtos/trusted-firmware-m#134 Signed-off-by: Keith Packard <keithp@keithp.com>
This adds linker script bits and compiler options so that trusted-firmware-m will build with picolibc. This has not been merged to the Zephyr trusted-firmware-m repository yet: zephyrproject-rtos/trusted-firmware-m#134 Signed-off-by: Keith Packard <keithp@keithp.com>
|
While trying to build the non-secure MPS4 board with this PR and Zephyr SDK 0.18.0-alpha4 we see below error: Referring to the changes in this PR, I tried below patch and it seems to fix the issue: I am not a linker script expert but if above change looks good then please let me know if you would like to include it in this PR. |
|
D
Diff looks good to me as well :) Thanks for adding the tags and for the support as well. Glad to see that moving forward! |
etienne-lms
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've successfully tested on the few supported STM32 platforms.
For info, while a couple of hundred bytes are saved in flash and RAM when using picolib, I also saw that BL2 footprint was increased by more than 2kByte of flash when console traces are enabled. Observed (from build tests) on various platforms, not only the STM32 ones.
platform/ext/common/picolibc.c
Outdated
| @@ -0,0 +1,48 @@ | |||
| /* | |||
| * Copyright © 2025, Keith Packard <keithp@keithp.com> | |||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Prefer ASCII char only? (replace © with (C))
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
(C) is meaningless. I'll just delete the ©
6f5ffba to
7418104
Compare
What are console traces and how are they enabled? There's nothing obvious in the source tree that I could find. If this ends up enabling 'assert' macros, then that can cause a pretty significant jump in flash usage as the default picolibc assert behavior includes I just reviewed the picolibc code and there's no easy way to disable the verbose assert behavior once enabled. If you want to do this, you'd need to do: |
d3zd3z
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Overall, I think this is a reasonable, and hopefully temporary workaround. As mentioned, TF-M is trying to move away from libc, so we probably can't upstream this. It is kind of frustrating how dependent this is on the SDK, but I'm not sure that can be avoided.
platform/ext/common/picolibc.c
Outdated
| void | ||
| _start(void) | ||
| { | ||
| typedef struct __copy_table { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The rest of TF-M seems to use 4 spaces for indentation, and this should probably match that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In TF-M, the feature will be managed by CONFIG_TFM_INCLUDE_STDLIBC (default OFF, preferred).
If you can upstream Picolib for the other case and include ATfE toolchain support (currently supports only OFF), that would be great and much appreciated.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The rest of TF-M seems to use 4 spaces for indentation, and this should probably match that.
Thanks; I'm not sure how this file ended up with 2-space indentation.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In TF-M, the feature will be managed by CONFIG_TFM_INCLUDE_STDLIBC (default OFF, preferred). If you can upstream Picolib for the other case and include ATfE toolchain support (currently supports only OFF), that would be great and much appreciated.
Happy to help out with this; as ATfE already includes picolibc, this should be pretty easy. I'd like to focus on finishing up the Zephyr integration so it can land in time for Zephyr 4.3.0 if possible. With that, Zephyr 4.3 should be buildable using Zephyr SDK 1.0, and might be close to building with ATfE as well.
7418104 to
d491c61
Compare
|
Rebased atop current zephyr main branch and re-indented the picolibc.c file using four spaces. |
This adds linker script bits and compiler options so that trusted-firmware-m will build with picolibc. This has not been merged to the Zephyr trusted-firmware-m repository yet: zephyrproject-rtos/trusted-firmware-m#134 Signed-off-by: Keith Packard <keithp@keithp.com>
tpambor
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM.
I have tested this PR on STM32H573I-DK and works as expected.
[INF] Starting bootloader
[WRN] This device was provisioned with dummy keys. This device is NOT SECURE
[INF] Primary image: magic=good, swap_type=0x1, copy_done=0x3, image_ok=0x1
[INF] Scratch: magic=unset, swap_type=0x1, copy_done=0x3, image_ok=0x3
[INF] Boot source: primary slot
[INF] Image index: 1, Swap type: none
[INF] Primary image: magic=good, swap_type=0x1, copy_done=0x3, image_ok=0x1
[INF] Scratch: magic=unset, swap_type=0x1, copy_done=0x3, image_ok=0x3
[INF] Boot source: primary slot
[INF] Image index: 0, Swap type: none
[INF] Bootloader chainload address offset: 0x38000
[INF] Image version: v0.0.0
[INF] Jumping to the first image slot
Booting TF-M v2.2.0+d491c6136
[WRN] This device was provisioned with dummy keys. This device is NOT SECURE
[Sec Thread] Secure image initializing!
[INF][PS] Encryption alg: 0x5500200
[INF][Crypto] Init HW accelerator...
[INF][Crypto] Init HW accelerator... complete.
*** Booting Zephyr OS build v4.3.0-1147-g51131b46e396 ***
TF-M IPC on stm32h573i_dk
The version of the PSA Framework API is 257.
The PSA Crypto service minor version is 1.
Generating 256 bytes of random data:
DD F4 89 1F 0D DF 40 0E D5 7F D1 44 1E 71 48 C9
05 9C 89 05 0F 63 FA B4 FB BA A3 3A 34 8F 54 AF
9A 1D 30 00 BF D5 AB 57 A5 45 B5 8D 9E 14 CC 38
DC 24 04 6D ED DA BA 3B F0 98 D0 A3 65 73 15 E6
EE 1C F0 75 7D D8 6B 9E B8 88 46 15 61 7B 30 E4
8F BB 2A 95 3F 2C EE D9 75 84 2B 0F 7D 14 88 E2
DA 13 10 22 4C FA 1B 73 D9 DE 61 6E 8F 7A 17 91
BC 1E 8D 14 8D C9 5F B7 4C C7 49 05 2C 3B B5 C6
F3 D7 EB 53 BD E2 00 54 E4 8E 4A 4D 84 D9 88 B9
A1 FC 0B D9 47 45 DE D8 D8 EF 0F A0 83 9C 71 9F
35 0E 5E F1 08 63 C6 98 CC 9B 94 29 B1 A4 1A 74
5B CD 21 A8 8B F5 25 74 35 41 61 CD 97 1D 6D 4A
56 7C 44 7D 13 50 11 93 F1 AD 11 50 51 C9 37 8B
8C D8 CE 01 CB 1B BC 9E 39 F5 88 4F 9B 24 70 35
D1 AF 81 91 B1 45 44 03 07 E4 77 7B 99 3C 29 0A
81 AC AB D6 83 26 09 85 BD CD 13 CA 7E E3 D9 DA
|
@keith-packard Would you like to get this in? Will this work with both the current SDK and the upcoming one? |
Yes, I'm waiting for this to finish up the SDK 1.0 integration work in Zephyr.
Yes, I've been doing regular A/B testing using SDK 0.17.5 and a version of SDK 1.0 with a couple of additional changes to make it work with current Zephyr (those are integrated into the SDK repo, but aren't in the current SDK 1.0 beta1 version). |
With this change rebased atop the current Zephyr version (c2f9edc), I just ran |
Sounds good, let me know when your testing with SDK 0.17.5 is complete and let's just merge this. |
All finished, no issues with 0.17.5 either. |
|
The default branch of this repository is being changed to |
d491c61 to
e4bafc9
Compare
When processing the .ER_CODE_SRAM section, the location counter is set
to the VMA of that section, so after processing the next section will
use that VMA instead of the next available address in the FLASH
region.
Reset the location counter to the next available FLASH address after
processing this section will ensure that any subsequent FLASH data
is placed in the correct location.
This test fails without this patch:
$ west build -p -b lpcxpresso55s69/lpc55s69/cpu0/ns \
samples/synchronization -T sample.kernel.synchronization
.../ld: address 0x14003e84 of bin/tfm_s.axf section `.ER_TFM_CODE'
is not within region `FLASH'
.../ld: address 0x14005c20 of bin/tfm_s.axf section `.TFM_UNPRIV_CODE'
is not within region `FLASH'
.../ld: bin/tfm_s.axf section `.TFM_PSA_ROT_LINKER_DATA'
will not fit in region `FLASH'
.../ld: address 0x14003e84 of bin/tfm_s.axf section `.ER_TFM_CODE'
is not within region `FLASH'
.../ld: address 0x14005c20 of bin/tfm_s.axf section `.TFM_UNPRIV_CODE'
is not within region `FLASH'
.../ld: ERROR: CMSE stub (.gnu.sgstubs section) too far (0x10008540)
from destination (0x14003ee4)
Note that the linker is generating addresses within the CODE_RAM
memory region rather than the FLASH region.
Signed-off-by: Keith Packard <keithp@keithp.com>
…mplates While the copy table included the default data segment for these templates, the zero table didn't include the default bss segment. Make sure that area gets initialized to zero using the table-based mechanism instead of relying on the startup code to initialize it explicitly. Signed-off-by: Keith Packard <keithp@keithp.com>
…ipts Picolibc uses different names for the list of constructors and heap limits. Add values for __bothinit_array_start, __bothinit_array_end, __heap_start and __heap_end to every linker script. If not using picolibc, these will not have any effect. Signed-off-by: Keith Packard <keithp@keithp.com>
1. Support picolibc stdio. There was already picolibc support code
present in the library for the ARM LLVM toolchain. The
conditionals which selected it have been changed to use
__PICOLIBC__ instead of __clang_major__.
2. Add _exit stub. Code using assert or abort end up calling _exit
through the picolibc signal handling code.
3. Switch to picolibc.specs. This is needed for toolchains which
don't use picolibc by default, and can also be used without
trouble in toolchains where picolibc is the default.
4. Define CONFIG_PICOLIBC when using picolibc. This is enabled
by default, but can be disabled on the cmake command line.
5. Define picolibc_startup to initialize all .data and .bss
segments using the standard tf-m arrays.
6. Add picolibc.c to many source lists when CONFIG_PICOLIBC is
defined. If this file is missign, picolibc_startup will
not be defined which should cause a failure at link time.
Signed-off-by: Keith Packard <keithp@keithp.com>
e4bafc9 to
6b820c4
Compare
Thanks. All rebased without any conflicts. I've started another Zephyr twister run "just to be sure", but I don't expect any new issues to arise. |
And still passes a twister run in Zephyr. I've updated my Zephyr PR related to this (zephyrproject-rtos/zephyr#94367) |
This adds linker script bits and compiler options so that trusted-firmware-m will build with picolibc. This has not been merged to the Zephyr trusted-firmware-m repository yet, that PR is: zephyrproject-rtos/trusted-firmware-m#134 Signed-off-by: Keith Packard <keithp@keithp.com>
tomi-font
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you, I think we can now merge this PR as it has been waiting long enough.
Be aware that my TF-M update PR is not yet merged in the Zephyr repository but it may go in any time. Just rebase your PR on top of it once it's in.
Uh oh!
There was an error while loading. Please reload this page.