Skip to content

Commit 711cc67

Browse files
committed
Dump-C: retain anonymous compound member types
Reproduce anonymous unions/structs/enums as such.
1 parent 22fec4c commit 711cc67

File tree

3 files changed

+29
-6
lines changed

3 files changed

+29
-6
lines changed

regression/goto-instrument/dump-type-header/main.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,10 @@ struct A
22
{
33
int a;
44
int b;
5+
union
6+
{
7+
int x;
8+
} u;
59
};
610

711
int main()

regression/goto-instrument/dump-type-header/test.desc

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,5 +8,7 @@ struct A
88
signed int a;
99
// b
1010
signed int b;
11+
// u
12+
union \{ signed int x; \} u;
1113
--
1214
^warning: ignoring

src/goto-instrument/dump_c.cpp

Lines changed: 23 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ Author: Daniel Kroening, [email protected]
2020
#include <util/find_symbols.h>
2121
#include <util/get_base_name.h>
2222
#include <util/invariant.h>
23+
#include <util/prefix.h>
2324
#include <util/replace_symbol.h>
2425
#include <util/string_utils.h>
2526

@@ -495,9 +496,14 @@ void dump_ct::convert_compound(
495496
while(non_array_type->id()==ID_array)
496497
non_array_type = &(to_array_type(*non_array_type).element_type());
497498

499+
bool is_anon =
500+
can_cast_type<tag_typet>(comp.type()) &&
501+
has_prefix(
502+
id2string(to_tag_type(comp.type()).get_identifier()), "tag-#anon");
503+
498504
if(recursive)
499505
{
500-
if(non_array_type->id()!=ID_pointer)
506+
if(non_array_type->id() != ID_pointer && !is_anon)
501507
convert_compound(comp.type(), comp.type(), recursive, os);
502508
else
503509
collect_typedefs(comp.type(), true);
@@ -511,7 +517,22 @@ void dump_ct::convert_compound(
511517
// component names such as "main" would collide with other objects in the
512518
// namespace
513519
std::string fake_unique_name="NO/SUCH/NS::"+id2string(comp_name);
514-
std::string s=make_decl(fake_unique_name, comp.type());
520+
typet comp_type_to_use = comp.type();
521+
if(is_anon)
522+
{
523+
comp_type_to_use = ns.follow(comp.type());
524+
comp_type_to_use.remove(ID_tag);
525+
if(
526+
recursive && (comp_type_to_use.id() == ID_struct ||
527+
comp_type_to_use.id() == ID_union))
528+
{
529+
const auto &sub_comps =
530+
to_struct_union_type(comp_type_to_use).components();
531+
for(const auto &sc : sub_comps)
532+
convert_compound(sc.type(), sc.type(), recursive, os);
533+
}
534+
}
535+
std::string s = make_decl(fake_unique_name, comp_type_to_use);
515536
POSTCONDITION(s.find("NO/SUCH/NS")==std::string::npos);
516537

517538
if(comp_type.id()==ID_c_bit_field &&
@@ -1523,10 +1544,6 @@ void dump_ct::cleanup_type(typet &type)
15231544

15241545
if(type.id()==ID_array)
15251546
cleanup_expr(to_array_type(type).size());
1526-
1527-
POSTCONDITION(
1528-
(type.id()!=ID_union && type.id()!=ID_struct) ||
1529-
!type.get(ID_tag).empty());
15301547
}
15311548

15321549
static expr2c_configurationt expr2c_configuration()

0 commit comments

Comments
 (0)