Skip to content

Commit 5d3e9a8

Browse files
committed
C front-end: initializer lists do not initialise anonymous members
Compilers differ in their handling of anonymous members, also depending on the type of the anonymous member. Make sure we accurately model this while type checking. Consequently, regression tests need to be amened to either be compiler-specific or not rely on anonymous or empty compound types, which dump-c also must not spuriously generate (from incomplete structs or unions). New tests are based on a case found by C-Reduce when starting from an SV-COMP task. Behaviour across different compilers confirmed with Compiler Explorer (https://godbolt.org/).
1 parent d932d6f commit 5d3e9a8

File tree

36 files changed

+218
-49
lines changed

36 files changed

+218
-49
lines changed
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
int blah(void);
22
; // empty!
33

4+
#ifndef _MSC_VER
45
struct some
56
{
67
; // empty
78
};
9+
#endif
810

911
int main() {
1012
}

regression/ansi-c/Union_Initialization2/test.desc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
CORE
22
main.c
33

4-
union member designator found for empty union
4+
(union member designator found for empty union|C requires that a struct or union has at least one member)
55
^SIGNAL=0$
66
^EXIT=(1|64)$
77
--

regression/ansi-c/_Generic1/main.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
struct some: 5 \
1414
)
1515

16+
#ifdef __GNUC__
1617
struct some
1718
{
1819
} s;
@@ -22,7 +23,6 @@ char ch;
2223
long double ld;
2324
short sh;
2425

25-
#ifdef __GNUC__
2626
STATIC_ASSERT(G(i)==3);
2727
STATIC_ASSERT(G(sh)==10);
2828
STATIC_ASSERT(G(ld)==1);
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,39 @@
1+
#ifdef _MSC_VER
2+
// No _Static_assert in Visual Studio
3+
# define _Static_assert(condition, message) static_assert(condition, message)
4+
#endif
5+
16
struct S
27
{
38
struct
49
{
510
int : 1;
11+
#ifndef _MSC_VER
612
int;
13+
#endif
714
int named;
815
};
916
};
1017

18+
_Static_assert(sizeof(struct S) == sizeof(int) * 2, "ignore int;");
19+
1120
struct S s = {.named = 0};
1221

22+
struct S1
23+
{
24+
struct S2
25+
{
26+
int : 1;
27+
int named;
28+
};
29+
};
30+
31+
#ifdef _MSC_VER
32+
_Static_assert(sizeof(struct S1) == sizeof(int) * 2, "");
33+
#else
34+
_Static_assert(sizeof(struct S1) == 0, "");
35+
#endif
36+
1337
int main()
1438
{
1539
}
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
#define static_assert(x) \
2+
struct \
3+
{ \
4+
char some[(x) ? 1 : -1]; \
5+
}
6+
7+
struct a
8+
{
9+
};
10+
struct c
11+
{
12+
struct a;
13+
void *d;
14+
} e =
15+
{
16+
#ifdef not_permitted
17+
{},
18+
#endif
19+
0},
20+
e2;
21+
struct
22+
{
23+
struct c f;
24+
} * g;
25+
int main()
26+
{
27+
g->f;
28+
static_assert(sizeof(e) == sizeof(void *));
29+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
CORE gcc-only
2+
main.c
3+
-Dnot_permitted
4+
cannot initialize 'void \*' with an initializer list
5+
^CONVERSION ERROR$
6+
^EXIT=(1|64)$
7+
^SIGNAL=0$
8+
--
9+
^warning: ignoring
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
CORE gcc-only
2+
main.c
3+
4+
^EXIT=0$
5+
^SIGNAL=0$
6+
--
7+
^warning: ignoring
8+
^CONVERSION ERROR$
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
typedef void(keyhandler_fn_t)(void);
2+
typedef void(irq_keyhandler_fn_t)(int);
3+
4+
void foo()
5+
{
6+
}
7+
8+
struct keyhandler
9+
{
10+
union
11+
{
12+
keyhandler_fn_t *fn;
13+
irq_keyhandler_fn_t *irq_fn;
14+
};
15+
const char *desc;
16+
_Bool x, y;
17+
} key_table[3] = {[0] = {{(keyhandler_fn_t *)(foo)}, "text", 1, 0}};
18+
19+
int main()
20+
{
21+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
CORE
2+
main.c
3+
4+
^EXIT=0$
5+
^SIGNAL=0$
6+
--
7+
^warning: ignoring
8+
^CONVERSION ERROR$

regression/ansi-c/sizeof3/main.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
#define STATIC_ASSERT(condition) \
55
int CONCAT2(some_array, __LINE__)[(condition) ? 1 : -1]
66

7+
#ifndef _MSC_VER
78
struct empty_struct { };
89
union empty_union { };
910

@@ -16,6 +17,7 @@ struct combination {
1617
STATIC_ASSERT(sizeof(struct empty_struct)==0);
1718
STATIC_ASSERT(sizeof(union empty_union)==0);
1819
STATIC_ASSERT(sizeof(struct combination)==sizeof(int));
20+
#endif
1921

2022
int main()
2123
{

0 commit comments

Comments
 (0)