-
Notifications
You must be signed in to change notification settings - Fork 7.4k
posix: mqueue: pop mode as int with va_arg() #67071
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
posix: mqueue: pop mode as int with va_arg() #67071
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.
I'd be slightly tempted to use 'unsigned int' instead of 'int', just to make the two types have the same 'signedness'.
That's a good point - better to be safe than sorry! |
bc20f53
to
100e765
Compare
@keith-packard - fixed! |
There was some discussion about whether it was suitable to have an architecture-specific workaround in mqueue.c after that workaround was copied to a different source file in a PR. The original issue was that newlib and picolibc declare mode_t to be unsigned short instead of unsigned long when __svr4__ is not defined along with __sparc__. This is specifically impactful, because va_arg() deals (mainly) with 32-bit and 64-bit values that are all naturally aligned to 4 bytes. #if defined(__sparc__) && !defined(__sparc_v9__) #ifdef __svr4__ typedef unsigned long __mode_t; #else typedef unsigned short __mode_t; #endif A uint16_t is naturally aligned to 2 bytes, so not only would a 16-bit mode_t be corrupted, it would also generate a warning with recent gcc versions which is promoted to error (rightfully so) when run through CI. mqueue.c:61:35: error: 'mode_t' {aka 'short unsigned int'} is promoted to 'int' when passed through '...' [-Werror] 61 | mode = va_arg(va, mode_t); Instead of using an architecture-specific workaround, simply add a build assert that the size of mode_t is less than or equal to the size of an int, and use an int to retrieve it via va_arg(). Signed-off-by: Christopher Friedt <[email protected]> # Please enter the commit message for your changes. Lines starting # with '#' will be kept; you may remove them yourself if you want to. # An empty message aborts the commit. # # Date: Fri Dec 29 10:06:44 2023 -0500 # # On branch posix-mqueue-always-use-int-for-mode-t-va-arg # Changes to be committed: # modified: lib/posix/mqueue.c # modified: tests/posix/common/testcase.yaml #
100e765
to
aa88d9d
Compare
There was some discussion about whether it was suitable to have an architecture-specific workaround in mqueue.c after that workaround was copied to a different source file in #67007.
The original issue was that newlib and picolibc declare mode_t to be unsigned short (16-bits) instead of unsigned long when
__svr4__
is not defined along with__sparc__
. This is specifically impactful, becauseva_arg()
deals (mainly) with 32-bit and 64-bit values that are all naturally aligned to 4 bytes (or 8 bytes)A uint16_t is naturally aligned to 2 bytes, so not only would a 16-bit mode_t be corrupted, it would also generate a warning with recent gcc versions which is promoted to error (rightfully so) when run through CI.
Instead of using an architecture-specific workaround, simply add a build assert that the size of
mode_t
is less than or equal to the size of an int, and use an int to retrieve it viava_arg()
.Also ensure that we allow testing via
qemu_leon3
which was not part of the fix in 6d126e7.