-
Notifications
You must be signed in to change notification settings - Fork 6.7k
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
libc/common: Add memalign #58012
libc/common: Add memalign #58012
Conversation
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.
tweak ifdef to include __GNUC__
fe6dfbe
to
e278a95
Compare
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.
Just realized that memalign is nonstandard. I won't block, but likely @stephanosio will have some input.
In any case, I appreciate the effort to improve C++ support :-)
Yup, that's why it's not defined in any header file and is only made available with using G++. It's provided as part of the G++ ABI requirements for the C library, but it's not part of the Zephyr C library API.
I'm constantly surprised what people will do 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.
memalign appears to be used internally by the G++, so we need to provide an implementation of this when using C++, even though it's not part of the Zephyr C library API.
I do not think the right solution is to add the non-standard memalign
support just for the purpose of appeasing GNU libstdc++, especially when we already support the standard aligned_alloc
Moreover, libstdc++ should be using aligned_alloc
when it is available:
namespace __gnu_cxx {
#if _GLIBCXX_HAVE_ALIGNED_ALLOC
using ::aligned_alloc;
[...]
#elif _GLIBCXX_HAVE_MEMALIGN
static inline void*
aligned_alloc (std::size_t al, std::size_t sz)
{
// Solaris requires al >= sizeof a word and QNX requires >= sizeof(void*)
// but they both provide posix_memalign, so will use the definition above.
return memalign (al, sz);
}
[...]
while ((p = __gnu_cxx::aligned_alloc (align, sz)) == nullptr)
Something is causing _GLIBCXX_HAVE_ALIGNED_ALLOC
to be not defined and the libstdc++ is falling back to using memalign
, which is a configuration issue and needs to be root-caused and fixed there.
I have created zephyrproject-rtos/sdk-ng#675 to track this. |
We can fix the SDK, but we cannot fix other gcc-based toolchains. How can we tell when a fixed version of the SDK is being used? |
Correct. First of all, we probably should consider upstreaming zephyrproject-rtos/gcc#22, once it is verified working, so that it propagates to all third-party GNU toolchain distributions. After that, we can go about this in one of two ways: a) require using the version of Zephyr SDK or a third-party GNU toolchain that includes the patch, or b) provide the solution proposed in this PR as a workaround for the third-party GNU toolchains that do not have the patch. IMHO, given that this will not be the last time we encounter issues like this, my preference is towards the option 'a'.
The only way to do that would be to check the Zephyr SDK version. |
Yup, I'm already planning on doing that. Given the usual gcc merge process, I expect this to take between a week and infinite weeks.
I don't think we can responsibly adopt that solution at this point -- that would rule out using any existing GCC-based c++ toolchain with Zephyr. We can (and should) plan on removing this kludge when the upstream patch is upstream and included in a GCC release.
Sounds like we need a Kconfig variable driving the inclusion of |
I am afraid that is an inevitable future if we want to properly support libstdc++ in the future (e.g. synchronisation, threading support), unless the third-party GNU toolchain is specifically built for the
Actually, I have another solution in mind. Since we are only adding That will allow the |
Haha. |
Any reason to not stick that test in the common C library malloc.c file instead of the current one? |
Because |
I've started implementing this idea and it doesn't seem very pretty -- it depends on configurations that use both the common C library malloc and libstdc++, so you have a cross-subsystem dependency with either implementation. The other issue is that implementing Given these two issues, I'd like you to reconsider this suggestion and place |
e278a95
to
4b5fb14
Compare
Yes, we will have cross-subsystem dependency either way; under
I thought we were only talking about the common libc The reason that I say this belongs in
That is why I say it would be more logical to put it in the libstdc++ support layer than in a libc. |
No, you're correct, but this makes it different from other 'support' code in lib/cpp as it is a linked dependency between the common C library and libstdc++; you need the common C library to provide this interface whenever it is being used by libstdc++. As you cannot use this implementation with any other C library, it feels disingenuous to have it exist outside of the common C library implementation -- it's only within the context of the common C library that this implementation is valid, so I really think it needs to be placed in that code and not someplace where it could conceivably get adopted for use with some other C library where it cannot work.
But it's a support function that that depends upon internal details about the implementation of
Yup, |
As long as we add But yeah, it would seem both approaches are almost equally as valid depending on how you look at them, and this is a matter of opinion.
Sure, I am fine with placing |
4b5fb14
to
af7d666
Compare
Sorry, I hadn't pushed the update I'd made to the comments in the file yesterday which (I hope) address this concern. Thanks for your review; it's always a challenge to know where to stick kludges like this which don't fit the desired abstraction layering. |
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.
Looks good. Just a minor comment about a typo.
af7d666
to
246c692
Compare
246c692
to
fa101b3
Compare
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.
No object from me. @galak any further thoughts here?
fa101b3
to
eb67332
Compare
Memalign is another name for the posix aligned_alloc function, although it has weaker restrictions on the relationship between the alignment and size. memalign() is used internally by the libstdc++ when built for 'newlib' targets (which includes picolibc) instead of aligned_alloc() due to a bug in gcc, so we need to provide an implementation of this when using that library, even though it's not part of the Zephyr C library API. When a fix for the libstdc++ is merged upstream and can be consider a reasonable dependency for Zephyr, this work-around can be removed. Closes: zephyrproject-rtos#57899 Signed-off-by: Keith Packard <[email protected]>
Make sure the underlying allocation system can support an allocation request generated by the new operator which has stricter alignment requirements than the default. For G++, this ends up using the 'memalign' function which is not part of any C standard. Signed-off-by: Keith Packard <[email protected]>
eb67332
to
112fad1
Compare
Memalign is another name for the posix aligned_alloc function, although it has weaker restrictions on the relationship between the alignment and size.
memalign appears to be used internally by the G++, so we need to provide an implementation of this when using C++, even though it's not part of the Zephyr C library API.
Closes: #57899