// RUN: %clang_cc1 %s -verify=stock,c -fsyntax-only // RUN: %clang_cc1 %s -verify=stock,cpp -fsyntax-only -x c++ // RUN: %clang_cc1 %s -verify=stock,cpp -fsyntax-only -fms-compatibility -x c++ // RUN: %clang_cc1 %s -verify=stock,c,gnu -fsyntax-only -Wgnu-flexible-array-union-member -Wgnu-empty-struct // RUN: %clang_cc1 %s -verify=stock,c,microsoft -fsyntax-only -fms-compatibility -Wmicrosoft // The test checks that an attempt to initialize union with flexible array // member with an initializer list doesn't crash clang. union { char x[]; } r = {0}; /* gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ struct _name1 { int a; union { int b; char x[]; /* gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ }; } name1 = { 10, 42, /* initializes "b" */ }; struct _name1i { int a; union { int b; char x[]; /* gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ }; } name1i = { .a = 10, .b = 42, }; /* Initialization of flexible array in a union is never allowed. */ struct _name2 { int a; union { int b; char x[]; /* gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ }; } name2 = { 12, 13, { 'c' }, /* c-warning {{excess elements in struct initializer}} cpp-error {{excess elements in struct initializer}} */ }; /* Initialization of flexible array in a union is never allowed. */ struct _name2i { int a; union { int b; char x[]; /* gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} stock-note {{initialized flexible array member 'x' is here}} */ }; } name2i = { .a = 12, .b = 13, /* stock-note {{previous initialization is here}} */ .x = { 'c' }, /* stock-error {{initialization of flexible array member is not allowed}} c-warning {{initializer overrides prior initialization of this subobject}} cpp-error {{initializer partially overrides prior initialization of this subobject}} */ }; /* Flexible array initialization always allowed when not in a union, and when struct has another member. */ struct _okay { int a; char x[]; } okay = { 22, { 'x', 'y', 'z' }, }; struct _okayi { int a; char x[]; } okayi = { .a = 22, .x = { 'x', 'y', 'z' }, }; struct _okay0 { int a; char x[]; } okay0 = { }; struct _flex_extension { char x[]; /* gnu-warning {{flexible array member 'x' in otherwise empty struct is a GNU extension}} microsoft-warning {{flexible array member 'x' in otherwise empty struct is a Microsoft extension}} */ } flex_extension = { { 'x', 'y', 'z' }, }; struct _flex_extensioni { char x[]; /* gnu-warning {{flexible array member 'x' in otherwise empty struct is a GNU extension}} microsoft-warning {{flexible array member 'x' in otherwise empty struct is a Microsoft extension}} */ } flex_extensioni = { .x = { 'x', 'y', 'z' }, }; struct already_hidden { int a; union { int b; struct { struct { } __empty; // gnu-warning {{empty struct is a GNU extension}} char x[]; }; }; }; struct still_zero_sized { struct { } __unused; // gnu-warning {{empty struct is a GNU extension}} int x[]; }; struct warn1 { int a; union { int b; char x[]; /* gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ }; }; struct warn2 { int x[]; /* gnu-warning {{flexible array member 'x' in otherwise empty struct is a GNU extension}} microsoft-warning {{flexible array member 'x' in otherwise empty struct is a Microsoft extension}} */ }; union warn3 { short x[]; /* gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ }; struct quiet1 { int a; short x[]; }; struct _not_at_end { union { short x[]; }; /* stock-warning-re {{field '' with variable sized type '{{.*}}' not at the end of a struct or class is a GNU extension}} gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ int y; } not_at_end = {{}, 3}; struct _not_at_end_s { struct { int a; short x[]; }; /* stock-warning-re {{field '' with variable sized type '{{.*}}' not at the end of a struct or class is a GNU extension}} */ int y; } not_at_end_s = {{}, 3}; struct { int a; union { /* stock-warning-re {{field '' with variable sized type '{{.*}}' not at the end of a struct or class is a GNU extension}} */ short x[]; /* stock-note {{initialized flexible array member 'x' is here}} gnu-warning {{flexible array member 'x' in a union is a GNU extension}} microsoft-warning {{flexible array member 'x' in a union is a Microsoft extension}} */ int b; }; int c; int d; } i_f = { 4, {5}, /* stock-error {{initialization of flexible array member is not allowed}} */ {}, 6}; // expected-no-diagnostics