@@ -19,8 +19,12 @@ Author: Qinheping Hu
19
19
#include < util/replace_symbol.h>
20
20
#include < util/simplify_expr.h>
21
21
22
+ #include < analyses/local_may_alias.h>
22
23
#include < analyses/natural_loops.h>
24
+ #include < goto-instrument/contracts/cfg_info.h>
25
+ #include < goto-instrument/contracts/utils.h>
23
26
#include < goto-instrument/havoc_utils.h>
27
+ #include < goto-instrument/loop_utils.h>
24
28
25
29
#include " cegis_verifier.h"
26
30
#include " expr_enumerator.h"
@@ -82,17 +86,21 @@ void enumerative_loop_contracts_synthesizert::init_candidates()
82
86
{
83
87
for (auto &function_p : goto_model.goto_functions .function_map )
84
88
{
85
- natural_loopst natural_loops;
89
+ natural_loops_mutablet natural_loops;
86
90
natural_loops (function_p.second .body );
87
91
92
+ // TODO: use global may alias instead.
93
+ local_may_aliast local_may_alias (function_p.second );
94
+
88
95
// Initialize invariants for unannotated loops as true
89
96
for (const auto &loop_head_and_content : natural_loops.loop_map )
90
97
{
91
98
goto_programt::const_targett loop_end =
92
- get_loop_end_from_loop_head_and_content (
99
+ get_loop_end_from_loop_head_and_content_mutable (
93
100
loop_head_and_content.first , loop_head_and_content.second );
94
101
95
102
loop_idt new_id (function_p.first , loop_end->loop_number );
103
+ loop_cfg_infot cfg_info (function_p.second , loop_head_and_content.second );
96
104
97
105
log.debug () << " Initialize candidates for the loop at "
98
106
<< loop_end->source_location () << messaget::eom;
@@ -116,6 +124,17 @@ void enumerative_loop_contracts_synthesizert::init_candidates()
116
124
if (loop_end->condition ().find (ID_C_spec_assigns).is_nil ())
117
125
{
118
126
assigns_map[new_id] = {};
127
+
128
+ // Infer loop assigns using alias analysis.
129
+ get_assigns (
130
+ local_may_alias, loop_head_and_content.second , assigns_map[new_id]);
131
+
132
+ // remove loop-local symbols from the inferred set
133
+ cfg_info.erase_locals (assigns_map[new_id]);
134
+
135
+ // If the set contains pairs (i, a[i]),
136
+ // we widen them to (i, __CPROVER_POINTER_OBJECT(a))
137
+ widen_assigns (assigns_map[new_id], ns);
119
138
}
120
139
}
121
140
}
@@ -127,7 +146,6 @@ void enumerative_loop_contracts_synthesizert::synthesize_assigns(
127
146
const exprt &checked_pointer,
128
147
const std::list<loop_idt> cause_loop_ids)
129
148
{
130
- namespacet ns (goto_model.symbol_table );
131
149
auto new_assign = checked_pointer;
132
150
133
151
// Add the new assigns target to the most-inner loop that doesn't contain
@@ -242,7 +260,6 @@ exprt enumerative_loop_contracts_synthesizert::synthesize_strengthening_clause(
242
260
// | StartBool <= StartBool | StartBool < StartBool
243
261
// Start -> Start + Start | terminal_symbols
244
262
// where a0, and a1 are symbol expressions.
245
- namespacet ns (goto_model.symbol_table );
246
263
enumerator_factoryt factory = enumerator_factoryt (ns);
247
264
recursive_enumerator_placeholdert start_bool_ph (factory, " StartBool" , ns);
248
265
recursive_enumerator_placeholdert start_ph (factory, " Start" , ns);
0 commit comments