@@ -516,8 +516,6 @@ void value_sett::get_value_set_rec(
516516 std::cout << " GET_VALUE_SET_REC SUFFIX: " << suffix << ' \n ' ;
517517#endif
518518
519- const typet &expr_type=ns.follow (expr.type ());
520-
521519 if (expr.id ()==ID_unknown || expr.id ()==ID_invalid)
522520 {
523521 insert (dest, exprt (ID_unknown, original_type));
@@ -539,17 +537,20 @@ void value_sett::get_value_set_rec(
539537 }
540538 else if (expr.id ()==ID_member)
541539 {
542- const typet &type = ns. follow ( to_member_expr (expr).compound (). type () );
540+ const exprt &compound = to_member_expr (expr).compound ();
543541
544542 DATA_INVARIANT (
545- type.id () == ID_struct || type.id () == ID_union,
543+ compound.type ().id () == ID_struct ||
544+ compound.type ().id () == ID_struct_tag ||
545+ compound.type ().id () == ID_union ||
546+ compound.type ().id () == ID_union_tag,
546547 " compound of member expression must be struct or union" );
547548
548549 const std::string &component_name=
549550 expr.get_string (ID_component_name);
550551
551552 get_value_set_rec (
552- to_member_expr (expr). compound () ,
553+ compound,
553554 dest,
554555 includes_nondet_pointer,
555556 " ." + component_name + suffix,
@@ -559,7 +560,7 @@ void value_sett::get_value_set_rec(
559560 else if (expr.id ()==ID_symbol)
560561 {
561562 auto entry_index = get_index_of_symbol (
562- to_symbol_expr (expr).get_identifier (), expr_type , suffix, ns);
563+ to_symbol_expr (expr).get_identifier (), expr. type () , suffix, ns);
563564
564565 if (entry_index.has_value ())
565566 make_union (dest, find_entry (*entry_index)->object_map );
@@ -624,11 +625,11 @@ void value_sett::get_value_set_rec(
624625 {
625626 insert (
626627 dest,
627- exprt (ID_null_object, to_pointer_type (expr_type ).base_type ()),
628+ exprt (ID_null_object, to_pointer_type (expr. type () ).base_type ()),
628629 mp_integer{0 });
629630 }
630- else if (expr_type. id ()==ID_unsignedbv ||
631- expr_type. id ()== ID_signedbv)
631+ else if (
632+ expr. type (). id () == ID_unsignedbv || expr. type (). id () == ID_signedbv)
632633 {
633634 // an integer constant got turned into a pointer
634635 insert (dest, exprt (ID_integer_address, unsigned_char_type ()));
@@ -703,7 +704,7 @@ void value_sett::get_value_set_rec(
703704 // special case for plus/minus and exactly one pointer
704705 std::optional<exprt> ptr_operand;
705706 if (
706- expr_type .id () == ID_pointer &&
707+ expr. type () .id () == ID_pointer &&
707708 (expr.id () == ID_plus || expr.id () == ID_minus))
708709 {
709710 bool non_const_offset = false ;
@@ -879,10 +880,10 @@ void value_sett::get_value_set_rec(
879880 statement==ID_cpp_new_array)
880881 {
881882 PRECONDITION (suffix.empty ());
882- PRECONDITION (expr_type .id () == ID_pointer);
883+ PRECONDITION (expr. type () .id () == ID_pointer);
883884
884885 dynamic_object_exprt dynamic_object (
885- to_pointer_type (expr_type ).base_type ());
886+ to_pointer_type (expr. type () ).base_type ());
886887 dynamic_object.set_instance (location_number);
887888 dynamic_object.valid ()=true_exprt ();
888889
@@ -893,7 +894,10 @@ void value_sett::get_value_set_rec(
893894 }
894895 else if (expr.id ()==ID_struct)
895896 {
896- const auto &struct_components = to_struct_type (expr_type).components ();
897+ const auto &struct_components =
898+ expr.type ().id () == ID_struct_tag
899+ ? ns.follow_tag (to_struct_tag_type (expr.type ())).components ()
900+ : to_struct_type (expr.type ()).components ();
897901 INVARIANT (
898902 struct_components.size () == expr.operands ().size (),
899903 " struct expression should have an operand per component" );
@@ -950,7 +954,9 @@ void value_sett::get_value_set_rec(
950954
951955 // If the suffix is empty we're looking for the whole struct:
952956 // default to combining both options as below.
953- if (expr_type.id () == ID_struct && !suffix.empty ())
957+ if (
958+ (expr.type ().id () == ID_struct_tag || expr.type ().id () == ID_struct) &&
959+ !suffix.empty ())
954960 {
955961 irep_idt component_name = with_expr.where ().get (ID_component_name);
956962 if (suffix_starts_with_field (suffix, id2string (component_name)))
@@ -966,7 +972,12 @@ void value_sett::get_value_set_rec(
966972 original_type,
967973 ns);
968974 }
969- else if (to_struct_type (expr_type).has_component (component_name))
975+ else if (
976+ (expr.type ().id () == ID_struct &&
977+ to_struct_type (expr.type ()).has_component (component_name)) ||
978+ (expr.type ().id () == ID_struct_tag &&
979+ ns.follow_tag (to_struct_tag_type (expr.type ()))
980+ .has_component (component_name)))
970981 {
971982 // Looking for a non-overwritten member, look through this expression
972983 get_value_set_rec (
@@ -998,7 +1009,7 @@ void value_sett::get_value_set_rec(
9981009 ns);
9991010 }
10001011 }
1001- else if (expr_type .id () == ID_array && !suffix.empty ())
1012+ else if (expr. type () .id () == ID_array && !suffix.empty ())
10021013 {
10031014 std::string new_value_suffix;
10041015 if (has_prefix (suffix, " []" ))
@@ -1105,8 +1116,9 @@ void value_sett::get_value_set_rec(
11051116
11061117 bool found=false ;
11071118
1108- const typet &op_type = ns.follow (byte_extract_expr.op ().type ());
1109- if (op_type.id () == ID_struct)
1119+ if (
1120+ byte_extract_expr.op ().type ().id () == ID_struct ||
1121+ byte_extract_expr.op ().type ().id () == ID_struct_tag)
11101122 {
11111123 exprt offset = byte_extract_expr.offset ();
11121124 if (eval_pointer_offset (offset, ns))
@@ -1115,7 +1127,10 @@ void value_sett::get_value_set_rec(
11151127 const auto offset_int = numeric_cast<mp_integer>(offset);
11161128 const auto type_size = pointer_offset_size (expr.type (), ns);
11171129
1118- const struct_typet &struct_type = to_struct_type (op_type);
1130+ const struct_typet &struct_type =
1131+ byte_extract_expr.op ().type ().id () == ID_struct_tag
1132+ ? ns.follow_tag (to_struct_tag_type (byte_extract_expr.op ().type ()))
1133+ : to_struct_type (byte_extract_expr.op ().type ());
11191134
11201135 for (const auto &c : struct_type.components ())
11211136 {
@@ -1150,10 +1165,17 @@ void value_sett::get_value_set_rec(
11501165 }
11511166 }
11521167
1153- if (op_type.id () == ID_union)
1168+ if (
1169+ byte_extract_expr.op ().type ().id () == ID_union ||
1170+ byte_extract_expr.op ().type ().id () == ID_union_tag)
11541171 {
11551172 // just collect them all
1156- for (const auto &c : to_union_type (op_type).components ())
1173+ const auto &components =
1174+ byte_extract_expr.op ().type ().id () == ID_union_tag
1175+ ? ns.follow_tag (to_union_tag_type (byte_extract_expr.op ().type ()))
1176+ .components ()
1177+ : to_union_type (byte_extract_expr.op ().type ()).components ();
1178+ for (const auto &c : components)
11571179 {
11581180 const irep_idt &name = c.get_name ();
11591181 member_exprt member (byte_extract_expr.op (), name, c.type ());
@@ -1429,13 +1451,13 @@ void value_sett::get_reference_set_rec(
14291451 // We cannot introduce a cast from scalar to non-scalar,
14301452 // thus, we can only adjust the types of structs and unions.
14311453
1432- const typet &final_object_type = ns. follow (object. type ());
1433-
1434- if (final_object_type .id ()==ID_struct ||
1435- final_object_type. id ()== ID_union)
1454+ if (
1455+ object. type (). id () == ID_struct ||
1456+ object. type () .id () == ID_struct_tag ||
1457+ object. type (). id () == ID_union || object. type (). id () == ID_union_tag )
14361458 {
14371459 // adjust type?
1438- if (ns. follow ( struct_op.type ())!=final_object_type )
1460+ if (struct_op.type () != object. type () )
14391461 {
14401462 member_expr.compound () =
14411463 typecast_exprt (member_expr.compound (), struct_op.type ());
@@ -1478,11 +1500,14 @@ void value_sett::assign(
14781500 output (std::cout);
14791501#endif
14801502
1481- const typet &type=ns.follow (lhs.type ());
1482-
1483- if (type.id () == ID_struct)
1503+ if (lhs.type ().id () == ID_struct || lhs.type ().id () == ID_struct_tag)
14841504 {
1485- for (const auto &c : to_struct_type (type).components ())
1505+ const auto &components =
1506+ lhs.type ().id () == ID_struct_tag
1507+ ? ns.follow_tag (to_struct_tag_type (lhs.type ())).components ()
1508+ : to_struct_type (lhs.type ()).components ();
1509+
1510+ for (const auto &c : components)
14861511 {
14871512 const typet &subtype = c.type ();
14881513 const irep_idt &name = c.get_name ();
@@ -1513,12 +1538,20 @@ void value_sett::assign(
15131538 " rhs.type():\n " +
15141539 rhs.type ().pretty () + " \n " + " lhs.type():\n " + lhs.type ().pretty ());
15151540
1516- const typet &followed = ns.follow (rhs.type ());
1541+ if (rhs.type ().id () == ID_struct_tag || rhs.type ().id () == ID_union_tag)
1542+ {
1543+ const struct_union_typet &rhs_struct_union_type =
1544+ ns.follow_tag (to_struct_or_union_tag_type (rhs.type ()));
1545+
1546+ const typet &rhs_subtype = rhs_struct_union_type.component_type (name);
1547+ rhs_member = simplify_expr (member_exprt{rhs, name, rhs_subtype}, ns);
15171548
1518- if (followed.id () == ID_struct || followed.id () == ID_union)
1549+ assign (lhs_member, rhs_member, ns, true , add_to_sets);
1550+ }
1551+ else if (rhs.type ().id () == ID_struct || rhs.type ().id () == ID_union)
15191552 {
15201553 const struct_union_typet &rhs_struct_union_type =
1521- to_struct_union_type (followed );
1554+ to_struct_union_type (rhs. type () );
15221555
15231556 const typet &rhs_subtype = rhs_struct_union_type.component_type (name);
15241557 rhs_member = simplify_expr (member_exprt{rhs, name, rhs_subtype}, ns);
@@ -1528,30 +1561,30 @@ void value_sett::assign(
15281561 }
15291562 }
15301563 }
1531- else if (type.id ()== ID_array)
1564+ else if (lhs. type () .id () == ID_array)
15321565 {
15331566 const index_exprt lhs_index (
15341567 lhs,
15351568 exprt (ID_unknown, c_index_type ()),
1536- to_array_type (type).element_type ());
1569+ to_array_type (lhs. type () ).element_type ());
15371570
15381571 if (rhs.id ()==ID_unknown ||
15391572 rhs.id ()==ID_invalid)
15401573 {
15411574 assign (
15421575 lhs_index,
1543- exprt (rhs.id (), to_array_type (type).element_type ()),
1576+ exprt (rhs.id (), to_array_type (lhs. type () ).element_type ()),
15441577 ns,
15451578 is_simplified,
15461579 add_to_sets);
15471580 }
15481581 else
15491582 {
15501583 DATA_INVARIANT (
1551- rhs.type () == type,
1584+ rhs.type () == lhs. type () ,
15521585 " value_sett::assign types should match, got: "
15531586 " rhs.type():\n " +
1554- rhs.type ().pretty () + " \n " + " type:\n " + type.pretty ());
1587+ rhs.type ().pretty () + " \n " + " type:\n " + lhs. type () .pretty ());
15551588
15561589 if (rhs.id ()==ID_array_of)
15571590 {
@@ -1575,7 +1608,7 @@ void value_sett::assign(
15751608 const index_exprt op0_index (
15761609 to_with_expr (rhs).old (),
15771610 exprt (ID_unknown, c_index_type ()),
1578- to_array_type (type).element_type ());
1611+ to_array_type (lhs. type () ).element_type ());
15791612
15801613 assign (lhs_index, op0_index, ns, is_simplified, add_to_sets);
15811614 assign (
@@ -1586,7 +1619,7 @@ void value_sett::assign(
15861619 const index_exprt rhs_index (
15871620 rhs,
15881621 exprt (ID_unknown, c_index_type ()),
1589- to_array_type (type).element_type ());
1622+ to_array_type (lhs. type () ).element_type ());
15901623 assign (lhs_index, rhs_index, ns, is_simplified, true );
15911624 }
15921625 }
@@ -1683,15 +1716,17 @@ void value_sett::assign_rec(
16831716 {
16841717 const auto &lhs_member_expr = to_member_expr (lhs);
16851718 const auto &component_name = lhs_member_expr.get_component_name ();
1686-
1687- const typet &type = ns.follow (lhs_member_expr.compound ().type ());
1719+ const exprt &compound = lhs_member_expr.compound ();
16881720
16891721 DATA_INVARIANT (
1690- type.id () == ID_struct || type.id () == ID_union,
1722+ compound.type ().id () == ID_struct ||
1723+ compound.type ().id () == ID_struct_tag ||
1724+ compound.type ().id () == ID_union ||
1725+ compound.type ().id () == ID_union_tag,
16911726 " operand 0 of member expression must be struct or union" );
16921727
16931728 assign_rec (
1694- lhs_member_expr. compound () ,
1729+ compound,
16951730 values_rhs,
16961731 " ." + id2string (component_name) + suffix,
16971732 ns,
0 commit comments