-
Notifications
You must be signed in to change notification settings - Fork 269
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Assignments to bit-fields yield results of bit-field type
Do not pre-emptively cast side effects over bit-fields to the underlying type. sizeof just has a very peculiar semantics, which is discussed in https://www.open-std.org/jtc1/sc22/wg14/www/docs/n2958.htm. Issue was found by CSmith (test generated with random seed 1700653858).
- Loading branch information
1 parent
5eb6fee
commit ed713ff
Showing
4 changed files
with
90 additions
and
8 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
#include <assert.h> | ||
#include <limits.h> | ||
|
||
struct S0 | ||
{ | ||
unsigned f2 : CHAR_BIT + 1; | ||
int x; | ||
}; | ||
|
||
#ifdef _MSC_VER | ||
# define _Static_assert static_assert | ||
#endif | ||
|
||
int main() | ||
{ | ||
struct S0 g = {0}; | ||
// All compilers in compiler explorer appear to agree that comma and | ||
// assignment expressions over bit-fields permit the use of sizeof. With GCC, | ||
// the result is the declared width (rounded to bytes), all others use the | ||
// size of the underlying type. | ||
// https://www.open-std.org/jtc1/sc22/wg14/www/docs/n2958.htm | ||
// for a discussion that this isn't actually specified (while being a | ||
// sizeof/typeof peculiarity) | ||
#if defined(__GNUC__) && !defined(__INTEL_COMPILER) && !defined(__clang__) | ||
# define WIDTH 2 | ||
#else | ||
# define WIDTH sizeof(unsigned) | ||
#endif | ||
_Static_assert(sizeof(++g.f2) == WIDTH, ""); | ||
_Static_assert(sizeof(0, g.f2) == WIDTH, ""); | ||
_Static_assert(sizeof(g.f2 = g.f2) == WIDTH, ""); | ||
if(g.f2 <= -1) | ||
assert(0); | ||
if((g.f2 = g.f2) <= -1) | ||
assert(0); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
CORE | ||
main.c | ||
|
||
^EXIT=0$ | ||
^SIGNAL=0$ | ||
^VERIFICATION SUCCESSFUL$ | ||
-- | ||
^warning: ignoring |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters