@@ -44,10 +44,13 @@ void goto_convertt::remove_assignment(
44
44
45
45
if (statement==ID_assign)
46
46
{
47
- exprt tmp=expr;
48
- tmp.id (ID_code);
49
- // just interpret as code
50
- convert_assign (to_code_assign (to_code (tmp)), dest, mode);
47
+ exprt new_lhs = skip_typecast (expr.op0 ());
48
+ exprt new_rhs =
49
+ typecast_exprt::conditional_cast (expr.op1 (), new_lhs.type ());
50
+ code_assignt assign (std::move (new_lhs), std::move (new_rhs));
51
+ assign.add_source_location () = expr.source_location ();
52
+
53
+ convert_assign (assign, dest, mode);
51
54
}
52
55
else if (statement==ID_assign_plus ||
53
56
statement==ID_assign_minus ||
@@ -99,33 +102,19 @@ void goto_convertt::remove_assignment(
99
102
100
103
const typet &op0_type = expr.op0 ().type ();
101
104
102
- if (op0_type.id ()==ID_c_bool)
103
- {
104
- // C/C++ Booleans get very special treatment.
105
- binary_exprt tmp (expr.op0 (), new_id, expr.op1 (), expr.op1 ().type ());
106
- tmp.op0 ().make_typecast (expr.op1 ().type ());
107
- rhs=typecast_exprt (is_not_zero (tmp, ns), expr.op0 ().type ());
108
- }
109
- else if (op0_type.id () == ID_c_enum_tag)
110
- {
111
- // We convert c_enums to their underlying type, do the
112
- // operation, and then convert back
113
- const auto &enum_type = ns.follow_tag (to_c_enum_tag_type (op0_type));
114
- auto underlying_type = enum_type.subtype ();
115
- auto op0 = typecast_exprt (expr.op0 (), underlying_type);
116
- auto op1 = typecast_exprt (expr.op1 (), underlying_type);
117
- binary_exprt tmp (op0, new_id, op1, underlying_type);
118
- rhs = typecast_exprt (tmp, expr.op0 ().type ());
119
- }
120
- else
121
- {
122
- rhs.id (new_id);
123
- rhs.copy_to_operands (expr.op0 (), expr.op1 ());
124
- rhs.type ()=expr.op0 ().type ();
125
- rhs.add_source_location ()=expr.source_location ();
126
- }
105
+ PRECONDITION (
106
+ op0_type.id () != ID_c_enum_tag && op0_type.id () != ID_c_enum &&
107
+ op0_type.id () != ID_c_bool && op0_type.id () != ID_bool);
108
+ rhs.id (new_id);
109
+ rhs.copy_to_operands (expr.op0 (), expr.op1 ());
110
+ rhs.type () = expr.op0 ().type ();
111
+ rhs.add_source_location () = expr.source_location ();
112
+
113
+ exprt new_lhs = skip_typecast (expr.op0 ());
114
+ rhs = typecast_exprt::conditional_cast (rhs, new_lhs.type ());
115
+ rhs.add_source_location () = expr.source_location ();
127
116
128
- code_assignt assignment (expr. op0 () , rhs);
117
+ code_assignt assignment (new_lhs , rhs);
129
118
assignment.add_source_location ()=expr.source_location ();
130
119
131
120
convert (assignment, dest, mode);
@@ -171,45 +160,34 @@ void goto_convertt::remove_pre(
171
160
172
161
const typet &op_type = expr.op0 ().type ();
173
162
174
- if (op_type.id ()==ID_bool)
175
- {
176
- rhs.copy_to_operands (expr.op0 (), from_integer (1 , signed_int_type ()));
177
- rhs.op0 ().make_typecast (signed_int_type ());
178
- rhs.type ()=signed_int_type ();
179
- rhs=is_not_zero (rhs, ns);
180
- }
181
- else if (op_type.id ()==ID_c_bool)
163
+ PRECONDITION (
164
+ op_type.id () != ID_c_enum_tag && op_type.id () != ID_c_enum &&
165
+ op_type.id () != ID_c_bool && op_type.id () != ID_bool);
166
+
167
+ typet constant_type;
168
+
169
+ if (op_type.id () == ID_pointer)
170
+ constant_type = index_type ();
171
+ else if (is_number (op_type))
172
+ constant_type = op_type;
173
+ else
182
174
{
183
- rhs.copy_to_operands (expr.op0 (), from_integer (1 , signed_int_type ()));
184
- rhs.op0 ().make_typecast (signed_int_type ());
185
- rhs.type ()=signed_int_type ();
186
- rhs=is_not_zero (rhs, ns);
187
- rhs.make_typecast (op_type);
175
+ UNREACHABLE;
188
176
}
189
- else if (op_type.id ()==ID_c_enum ||
190
- op_type.id ()==ID_c_enum_tag)
177
+
178
+ exprt constant;
179
+
180
+ if (constant_type.id () == ID_complex)
191
181
{
192
- rhs.copy_to_operands (expr.op0 (), from_integer (1 , signed_int_type ()));
193
- rhs.op0 ().make_typecast (signed_int_type ());
194
- rhs.type ()=signed_int_type ();
195
- rhs.make_typecast (op_type);
182
+ exprt real = from_integer (1 , constant_type.subtype ());
183
+ exprt imag = from_integer (0 , constant_type.subtype ());
184
+ constant = complex_exprt (real, imag, to_complex_type (constant_type));
196
185
}
197
186
else
198
- {
199
- typet constant_type;
200
-
201
- if (op_type.id ()==ID_pointer)
202
- constant_type=index_type ();
203
- else if (is_number (op_type) || op_type.id ()==ID_c_bool)
204
- constant_type=op_type;
205
- else
206
- {
207
- UNREACHABLE;
208
- }
187
+ constant = from_integer (1 , constant_type);
209
188
210
- rhs.add_to_operands (expr.op0 (), from_integer (1 , constant_type));
211
- rhs.type ()=expr.op0 ().type ();
212
- }
189
+ rhs.add_to_operands (expr.op0 (), std::move (constant));
190
+ rhs.type () = expr.op0 ().type ();
213
191
214
192
code_assignt assignment (expr.op0 (), rhs);
215
193
assignment.add_source_location ()=expr.find_source_location ();
@@ -257,56 +235,34 @@ void goto_convertt::remove_post(
257
235
258
236
const typet &op_type = expr.op0 ().type ();
259
237
260
- if (op_type.id ()==ID_bool)
261
- {
262
- rhs.copy_to_operands (expr.op0 (), from_integer (1 , signed_int_type ()));
263
- rhs.op0 ().make_typecast (signed_int_type ());
264
- rhs.type ()=signed_int_type ();
265
- rhs=is_not_zero (rhs, ns);
266
- }
267
- else if (op_type.id ()==ID_c_bool)
238
+ PRECONDITION (
239
+ op_type.id () != ID_c_enum_tag && op_type.id () != ID_c_enum &&
240
+ op_type.id () != ID_c_bool && op_type.id () != ID_bool);
241
+
242
+ typet constant_type;
243
+
244
+ if (op_type.id () == ID_pointer)
245
+ constant_type = index_type ();
246
+ else if (is_number (op_type))
247
+ constant_type = op_type;
248
+ else
268
249
{
269
- rhs.copy_to_operands (expr.op0 (), from_integer (1 , signed_int_type ()));
270
- rhs.op0 ().make_typecast (signed_int_type ());
271
- rhs.type ()=signed_int_type ();
272
- rhs=is_not_zero (rhs, ns);
273
- rhs.make_typecast (op_type);
250
+ UNREACHABLE;
274
251
}
275
- else if (op_type.id ()==ID_c_enum ||
276
- op_type.id ()==ID_c_enum_tag)
252
+
253
+ exprt constant;
254
+
255
+ if (constant_type.id () == ID_complex)
277
256
{
278
- rhs.copy_to_operands (expr.op0 (), from_integer (1 , signed_int_type ()));
279
- rhs.op0 ().make_typecast (signed_int_type ());
280
- rhs.type ()=signed_int_type ();
281
- rhs.make_typecast (op_type);
257
+ exprt real = from_integer (1 , constant_type.subtype ());
258
+ exprt imag = from_integer (0 , constant_type.subtype ());
259
+ constant = complex_exprt (real, imag, to_complex_type (constant_type));
282
260
}
283
261
else
284
- {
285
- typet constant_type;
262
+ constant = from_integer (1 , constant_type);
286
263
287
- if (op_type.id ()==ID_pointer)
288
- constant_type=index_type ();
289
- else if (is_number (op_type) || op_type.id ()==ID_c_bool)
290
- constant_type=op_type;
291
- else
292
- {
293
- UNREACHABLE;
294
- }
295
-
296
- exprt constant;
297
-
298
- if (constant_type.id ()==ID_complex)
299
- {
300
- exprt real=from_integer (1 , constant_type.subtype ());
301
- exprt imag=from_integer (0 , constant_type.subtype ());
302
- constant=complex_exprt (real, imag, to_complex_type (constant_type));
303
- }
304
- else
305
- constant=from_integer (1 , constant_type);
306
-
307
- rhs.add_to_operands (expr.op0 (), std::move (constant));
308
- rhs.type ()=expr.op0 ().type ();
309
- }
264
+ rhs.add_to_operands (expr.op0 (), std::move (constant));
265
+ rhs.type () = expr.op0 ().type ();
310
266
311
267
code_assignt assignment (expr.op0 (), rhs);
312
268
assignment.add_source_location ()=expr.find_source_location ();
0 commit comments