@@ -1007,33 +1007,52 @@ void c_typecheck_baset::typecheck_compound_body(
1007
1007
}
1008
1008
}
1009
1009
1010
- // We allow an incomplete (C99) array as _last_ member!
1011
- // Zero-length is allowed everywhere.
1012
-
1013
- if (type.id ()==ID_struct ||
1014
- type.id ()==ID_union)
1010
+ // We allow an incomplete array as _last_ member of a struct,
1011
+ // C11 6.7.2.1 §18. These are called "flexible array members".
1012
+ // Zero-length (a gcc extension) is allowed everywhere.
1013
+ if (type.id () == ID_struct)
1015
1014
{
1016
1015
for (struct_union_typet::componentst::iterator
1017
1016
it=components.begin ();
1018
1017
it!=components.end ();
1019
1018
it++)
1020
1019
{
1021
- typet &c_type= it->type ();
1020
+ typet &component_type = it->type ();
1022
1021
1023
- if (c_type.id ()==ID_array &&
1024
- to_array_type (c_type).is_incomplete ())
1022
+ if (
1023
+ component_type.id () == ID_array &&
1024
+ to_array_type (component_type).is_incomplete ())
1025
1025
{
1026
1026
// needs to be last member
1027
- if (type. id ()==ID_struct && it!= --components.end ())
1027
+ if (it != --components.end ())
1028
1028
{
1029
1029
error ().source_location =it->source_location ();
1030
1030
error () << " flexible struct member must be last member" << eom;
1031
1031
throw 0 ;
1032
1032
}
1033
1033
1034
1034
// make it zero-length
1035
- to_array_type (c_type).size () = from_integer (0 , c_index_type ());
1036
- c_type.set (ID_C_flexible_array_member, true );
1035
+ to_array_type (component_type).size () = from_integer (0 , c_index_type ());
1036
+ component_type.set (ID_C_flexible_array_member, true );
1037
+ }
1038
+ }
1039
+ }
1040
+
1041
+ // Flexible array members are not allowed in unions in ISO C.
1042
+ // We allow this as an extension on Windows.
1043
+ if (type.id () == ID_union && config.ansi_c .os != configt::ansi_ct::ost::OS_WIN)
1044
+ {
1045
+ for (const auto &component : components)
1046
+ {
1047
+ auto &component_type = component.type ();
1048
+
1049
+ if (
1050
+ component_type.id () == ID_array &&
1051
+ to_array_type (component_type).is_incomplete ())
1052
+ {
1053
+ throw invalid_source_file_exceptiont (
1054
+ " flexible array members are not allowed in a union" ,
1055
+ component.source_location ());
1037
1056
}
1038
1057
}
1039
1058
}
0 commit comments