@@ -160,13 +160,17 @@ class empty_replace_function_bodiest : public replace_function_bodiest
160
160
}
161
161
};
162
162
163
- class havoc_replace_function_bodiest : public replace_function_bodiest
163
+ class havoc_replace_function_bodiest : public replace_function_bodiest ,
164
+ private messaget
164
165
{
165
166
public:
166
167
havoc_replace_function_bodiest (
167
168
std::vector<irep_idt> globals_to_havoc,
168
- std::regex parameters_to_havoc)
169
- : globals_to_havoc(std::move(globals_to_havoc)),
169
+ std::regex parameters_to_havoc,
170
+ message_handlert &message_handler)
171
+ : replace_function_bodiest(),
172
+ messaget (message_handler),
173
+ globals_to_havoc(std::move(globals_to_havoc)),
170
174
parameters_to_havoc(std::move(parameters_to_havoc))
171
175
{
172
176
}
@@ -190,26 +194,35 @@ class havoc_replace_function_bodiest : public replace_function_bodiest
190
194
{
191
195
if (
192
196
parameter.type ().id () == ID_pointer &&
193
- !is_constant_or_has_constant_components (
194
- parameter.type ().subtype (), ns) &&
195
197
std::regex_match (
196
198
id2string (parameter.get_base_name ()), parameters_to_havoc))
197
199
{
198
- // if (param != nullptr) { *param = nondet(); }
199
- auto goto_instruction = add_instruction ();
200
- auto assign_instruction = add_instruction ();
201
- auto label_instruction = add_instruction ();
202
- goto_instruction->make_goto (
203
- label_instruction,
204
- equal_exprt (
205
- symbol_exprt (parameter.get_identifier (), parameter.type ()),
206
- null_pointer_exprt (to_pointer_type (parameter.type ()))));
207
- assign_instruction->make_assignment ();
208
- assign_instruction->code = code_assignt (
209
- dereference_exprt (
210
- symbol_exprt (parameter.get_identifier (), parameter.type ())),
211
- side_effect_expr_nondett (parameter.type ().subtype ()));
212
- label_instruction->make_skip ();
200
+ if (
201
+ !is_constant_or_has_constant_components (
202
+ parameter.type ().subtype (), ns))
203
+ {
204
+ // if (param != nullptr) { *param = nondet(); }
205
+ auto goto_instruction = add_instruction ();
206
+ auto assign_instruction = add_instruction ();
207
+ auto label_instruction = add_instruction ();
208
+ goto_instruction->make_goto (
209
+ label_instruction,
210
+ equal_exprt (
211
+ symbol_exprt (parameter.get_identifier (), parameter.type ()),
212
+ null_pointer_exprt (to_pointer_type (parameter.type ()))));
213
+ assign_instruction->make_assignment ();
214
+ assign_instruction->code = code_assignt (
215
+ dereference_exprt (
216
+ symbol_exprt (parameter.get_identifier (), parameter.type ())),
217
+ side_effect_expr_nondett (parameter.type ().subtype ()));
218
+ label_instruction->make_skip ();
219
+ }
220
+ else if (!parameter.type ().subtype ().get_bool (ID_C_constant))
221
+ {
222
+ warning () << " warning: not havoccing non-const pointer parameter '"
223
+ << parameter.get_base_name () << " ' of " << function_name
224
+ << " because it has const members" << messaget::eom;
225
+ }
213
226
}
214
227
}
215
228
@@ -249,12 +262,13 @@ class replace_function_bodies_errort : public std::runtime_error
249
262
250
263
std::unique_ptr<replace_function_bodiest> replace_function_body_options_factory (
251
264
const std::string &options,
252
- const symbol_tablet &symbol_table)
265
+ const symbol_tablet &symbol_table,
266
+ message_handlert &message_handler)
253
267
{
254
268
if (options.empty () || options == " nondet-return" )
255
269
{
256
270
return util_make_unique<havoc_replace_function_bodiest>(
257
- std::vector<irep_idt>{}, std::regex{});
271
+ std::vector<irep_idt>{}, std::regex{}, message_handler );
258
272
}
259
273
260
274
if (options == " assume-false" )
@@ -308,18 +322,27 @@ std::unique_ptr<replace_function_bodiest> replace_function_body_options_factory(
308
322
}
309
323
std::vector<irep_idt> globals_to_havoc;
310
324
namespacet ns (symbol_table);
325
+ messaget messages (message_handler);
311
326
for (auto const &symbol : symbol_table.symbols )
312
327
{
313
328
if (
314
329
symbol.second .is_lvalue && symbol.second .is_static_lifetime &&
315
- !is_constant_or_has_constant_components (symbol.second .type , ns) &&
316
330
std::regex_match (id2string (symbol.first ), globals_regex))
317
331
{
318
- globals_to_havoc.push_back (symbol.first );
332
+ if (!is_constant_or_has_constant_components (symbol.second .type , ns))
333
+ {
334
+ globals_to_havoc.push_back (symbol.first );
335
+ }
336
+ else if (!symbol.second .type .get_bool (ID_C_constant))
337
+ {
338
+ messages.warning () << " warning: not havoccing non-const global '"
339
+ << symbol.first << " ' because it has const members"
340
+ << messaget::eom;
341
+ }
319
342
}
320
343
}
321
344
return util_make_unique<havoc_replace_function_bodiest>(
322
- std::move (globals_to_havoc), std::move (params_regex));
345
+ std::move (globals_to_havoc), std::move (params_regex), message_handler );
323
346
}
324
347
throw replace_function_bodies_errort (" Can't parse \" " + options + " \" " );
325
348
}
@@ -328,7 +351,8 @@ std::unique_ptr<replace_function_bodiest> replace_function_body_options_factory(
328
351
// / \see replace_function_bodies() for information of how the cmdline is parsed
329
352
replace_function_body_optionst parse_replace_function_body_optionst (
330
353
const cmdlinet &cmdline,
331
- const symbol_tablet &symbol_table)
354
+ const symbol_tablet &symbol_table,
355
+ message_handlert &message_handler)
332
356
{
333
357
if (
334
358
cmdline.isset (" replace-function-body" ) &&
@@ -343,7 +367,9 @@ replace_function_body_optionst parse_replace_function_body_optionst(
343
367
only_generate ? cmdline.get_value (" generate-function-body" )
344
368
: cmdline.get_value (" replace-function-body" ));
345
369
auto replace_function_bodies = replace_function_body_options_factory (
346
- cmdline.get_value (" replace-function-body-options" ), symbol_table);
370
+ cmdline.get_value (" replace-function-body-options" ),
371
+ symbol_table,
372
+ message_handler);
347
373
return {function_regex, only_generate, std::move (replace_function_bodies)};
348
374
}
349
375
@@ -430,7 +456,7 @@ void replace_function_bodies(
430
456
{
431
457
messaget messages (message_handler);
432
458
messages.warning ()
433
- << " Replace function bodies: No function name matched regex"
459
+ << " warning: Replace function bodies: No function name matched regex"
434
460
<< messaget::eom;
435
461
}
436
462
}
0 commit comments