Skip to content

Commit b627c3d

Browse files
committed
Replace unsound struct-cast simplification
Previously the simplifier would simplify ((struct A)x) into (x) if x.type() and A were structurally compatible (i.e. had the same named and typed fields). However this isn't really a sound simplification, as it changes the type of the expression. I therefore replace the rule with one that only applies within the common-case member expression, i.e. simplifiying ((struct A)x).y -> x.y, which does not change the type of the outer expression.
1 parent a22dd1c commit b627c3d

File tree

2 files changed

+14
-1
lines changed

2 files changed

+14
-1
lines changed

src/util/simplify_expr.cpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ Author: Daniel Kroening, [email protected]
2525
#include "rational_tools.h"
2626
#include "config.h"
2727
#include "base_type.h"
28+
#include "type_eq.h"
2829
#include "namespace.h"
2930
#include "threeval.h"
3031
#include "pointer_predicates.h"
@@ -214,7 +215,7 @@ bool simplify_exprt::simplify_typecast(exprt &expr)
214215
}
215216

216217
// eliminate redundant typecasts
217-
if(base_type_eq(expr.type(), expr.op0().type(), ns))
218+
if(type_eq(expr.type(), expr.op0().type(), ns))
218219
{
219220
exprt tmp;
220221
tmp.swap(expr.op0());

src/util/simplify_expr_struct.cpp

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ Author: Daniel Kroening, [email protected]
1515
#include "std_expr.h"
1616
#include "pointer_offset_size.h"
1717
#include "arith_tools.h"
18+
#include "base_type.h"
1819

1920
bool simplify_exprt::simplify_member(exprt &expr)
2021
{
@@ -208,6 +209,17 @@ bool simplify_exprt::simplify_member(exprt &expr)
208209
}
209210
}
210211
}
212+
else if(op.id() == ID_typecast)
213+
{
214+
// Try to look through member(cast(x)) if the cast is between structurally
215+
// identical types:
216+
if(base_type_eq(op_type, op.op0().type(), ns))
217+
{
218+
expr.op0() = op.op0();
219+
simplify_member(expr);
220+
return false;
221+
}
222+
}
211223
else if(op.id()==ID_if)
212224
{
213225
const if_exprt &if_expr=to_if_expr(op);

0 commit comments

Comments
 (0)