Skip to content

Commit a9f8ec1

Browse files
updated handling of value initialization for bit-vectors
1 parent ba5cec7 commit a9f8ec1

10 files changed

+112
-36
lines changed

src/ast/converters/generic_model_converter.cpp

+27-12
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ Module Name:
2222
#include "ast/for_each_expr.h"
2323
#include "ast/ast_util.h"
2424
#include "ast/occurs.h"
25+
#include "ast/bv_decl_plugin.h"
2526
#include "ast/rewriter/expr_safe_replace.h"
2627
#include "ast/rewriter/th_rewriter.h"
2728
#include "ast/converters/generic_model_converter.h"
@@ -130,25 +131,32 @@ generic_model_converter * generic_model_converter::copy(ast_translation & transl
130131
return res;
131132
}
132133

133-
void generic_model_converter::convert_initialize_value(expr_ref& var, expr_ref& value) {
134-
for (auto const& e : m_entries) {
135-
switch (e.m_instruction) {
136-
case HIDE:
137-
break;
138-
case ADD:
139-
if (is_uninterp_const(var) && e.m_f == to_app(var)->get_decl())
140-
convert_initialize_value(e.m_def, var, value);
141-
break;
134+
void generic_model_converter::convert_initialize_value(vector<std::pair<expr_ref, expr_ref>> & var2value) {
135+
if (var2value.empty() || m_entries.empty())
136+
return;
137+
for (unsigned i = 0; i < var2value.size(); ++i) {
138+
auto& [var, value] = var2value[i];
139+
for (auto const& e : m_entries) {
140+
switch (e.m_instruction) {
141+
case HIDE:
142+
break;
143+
case ADD:
144+
if (is_uninterp_const(var) && e.m_f == to_app(var)->get_decl())
145+
convert_initialize_value(e.m_def, i, var2value);
146+
break;
147+
}
142148
}
143149
}
144150
}
145151

146-
void generic_model_converter::convert_initialize_value(expr* def, expr_ref& var, expr_ref& value) {
152+
void generic_model_converter::convert_initialize_value(expr* def, unsigned i, vector<std::pair<expr_ref, expr_ref>>& var2value) {
147153

148154
// var = if(c, th, el) = value
149155
// th = value => c = true
150156
// el = value => c = false
151157
expr* c = nullptr, *th = nullptr, *el = nullptr;
158+
auto& [var, value] = var2value[i];
159+
verbose_stream() << "def " << mk_pp(def, m) << "\n";
152160
if (m.is_ite(def, c, th, el)) {
153161
if (value == th) {
154162
var = c;
@@ -164,8 +172,15 @@ void generic_model_converter::convert_initialize_value(expr* def, expr_ref& var,
164172

165173
// var = def = value
166174
// => def = value
167-
if (is_uninterp(def))
168-
var = def;
175+
if (is_uninterp(def)) {
176+
var = def;
177+
return;
178+
}
179+
180+
bv_util bv(m);
181+
if (bv.is_mkbv(def)) {
182+
verbose_stream() << "def\n";
183+
}
169184

170185

171186
}

src/ast/converters/generic_model_converter.h

+2-2
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ class generic_model_converter : public model_converter {
3737
vector<entry> m_entries;
3838

3939
expr_ref simplify_def(entry const& e);
40-
void convert_initialize_value(expr* def, expr_ref& var, expr_ref& value);
40+
void convert_initialize_value(expr* def, unsigned i, vector<std::pair<expr_ref, expr_ref>>& var2value);
4141

4242
public:
4343
generic_model_converter(ast_manager & m, char const* orig) : m(m), m_orig(orig) {}
@@ -62,7 +62,7 @@ class generic_model_converter : public model_converter {
6262

6363
model_converter * translate(ast_translation & translator) override { return copy(translator); }
6464

65-
void convert_initialize_value(expr_ref& var, expr_ref& value) override;
65+
void convert_initialize_value(vector<std::pair<expr_ref, expr_ref>>& var2value) override;
6666

6767
generic_model_converter* copy(ast_translation & translator);
6868

src/ast/converters/model_converter.cpp

+3-3
Original file line numberDiff line numberDiff line change
@@ -108,9 +108,9 @@ class concat_model_converter : public concat_converter<model_converter> {
108108
m_c1->get_units(fmls);
109109
}
110110

111-
void convert_initialize_value(expr_ref& var, expr_ref& value) override {
112-
m_c2->convert_initialize_value(var, value);
113-
m_c1->convert_initialize_value(var, value);
111+
void convert_initialize_value(vector<std::pair<expr_ref, expr_ref>>& var2value) override {
112+
m_c2->convert_initialize_value(var2value);
113+
m_c1->convert_initialize_value(var2value);
114114
}
115115

116116

src/ast/converters/model_converter.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ class model_converter : public converter {
8686

8787
virtual void set_env(ast_pp_util* visitor);
8888

89-
virtual void convert_initialize_value(expr_ref& var, expr_ref& value) { }
89+
virtual void convert_initialize_value(vector<std::pair<expr_ref, expr_ref>> & var2value) { }
9090

9191
/**
9292
\brief we are adding a formula to the context of the model converter.

src/opt/opt_context.cpp

+3-4
Original file line numberDiff line numberDiff line change
@@ -311,11 +311,10 @@ namespace opt {
311311
}
312312
solver& s = get_solver();
313313
s.assert_expr(m_hard_constraints);
314-
for (auto & [var, value] : m_scoped_state.m_values) {
315-
if (m_model_converter)
316-
m_model_converter->convert_initialize_value(var, value);
314+
if (m_model_converter)
315+
m_model_converter->convert_initialize_value(m_scoped_state.m_values);
316+
for (auto & [var, value] : m_scoped_state.m_values)
317317
s.user_propagate_initialize_value(var, value);
318-
}
319318

320319
opt_params optp(m_params);
321320
symbol pri = optp.priority();

src/sat/sat_solver/inc_sat_solver.cpp

+22-8
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,7 @@ class inc_sat_solver : public solver {
7878
// this allows to access the internal state of the SAT solver and carry on partial results.
7979
bool m_internalized_converted; // have internalized formulas been converted back
8080
expr_ref_vector m_internalized_fmls; // formulas in internalized format
81+
vector<std::pair<expr_ref, expr_ref>> m_var2value;
8182

8283
typedef obj_map<expr, sat::literal> dep2asm_t;
8384

@@ -175,9 +176,27 @@ class inc_sat_solver : public solver {
175176
(m.is_not(e, e) && is_uninterp_const(e));
176177
}
177178

179+
void initialize_values() {
180+
if (m_mcs.back())
181+
m_mcs.back()->convert_initialize_value(m_var2value);
182+
if (m_mcs.back())
183+
m_mcs.back()->display(verbose_stream());
184+
185+
for (auto & [var, value] : m_var2value) {
186+
sat::bool_var b = m_map.to_bool_var(var);
187+
if (b != sat::null_bool_var)
188+
m_solver.set_phase(sat::literal(b, m.is_false(value)));
189+
else if (get_euf())
190+
ensure_euf()->user_propagate_initialize_value(var, value);
191+
}
192+
}
193+
178194
lbool check_sat_core(unsigned sz, expr * const * assumptions) override {
179195
m_solver.pop_to_base_level();
180196
m_core.reset();
197+
198+
199+
181200
if (m_solver.inconsistent()) return l_false;
182201
expr_ref_vector _assumptions(m);
183202
obj_map<expr, expr*> asm2fml;
@@ -202,6 +221,8 @@ class inc_sat_solver : public solver {
202221
r = internalize_assumptions(sz, _assumptions.data());
203222
if (r != l_true) return r;
204223

224+
initialize_values();
225+
205226
init_reason_unknown();
206227
m_internalized_converted = false;
207228
bool reason_set = false;
@@ -703,14 +724,7 @@ class inc_sat_solver : public solver {
703724
}
704725

705726
void user_propagate_initialize_value(expr* var, expr* value) override {
706-
expr_ref _var(var, m), _value(value, m);
707-
if (m_mcs.back())
708-
m_mcs.back()->convert_initialize_value(_var, _value);
709-
sat::bool_var b = m_map.to_bool_var(_var);
710-
if (b != sat::null_bool_var)
711-
m_solver.set_phase(sat::literal(b, m.is_false(_value)));
712-
else if (get_euf())
713-
ensure_euf()->user_propagate_initialize_value(_var, _value);
727+
m_var2value.push_back({expr_ref(var, m), expr_ref(value, m) });
714728
}
715729

716730

src/sat/tactic/sat_tactic.cpp

+24-5
Original file line numberDiff line numberDiff line change
@@ -32,13 +32,26 @@ class sat_tactic : public tactic {
3232
sat2goal m_sat2goal;
3333
scoped_ptr<sat::solver> m_solver;
3434
params_ref m_params;
35+
vector<std::pair<expr_ref, expr_ref>>& m_var2value;
3536

36-
imp(ast_manager & _m, params_ref const & p):
37+
imp(ast_manager & _m, params_ref const & p, vector<std::pair<expr_ref, expr_ref>>& var2value):
3738
m(_m),
3839
m_solver(alloc(sat::solver, p, m.limit())),
39-
m_params(p) {
40+
m_params(p),
41+
m_var2value(var2value) {
4042
updt_params(p);
4143
}
44+
45+
void initialize_values(goal_ref const& g, atom2bool_var& map) {
46+
g->mc()->convert_initialize_value(m_var2value);
47+
for (auto & [var, value] : m_var2value) {
48+
if (!m.is_bool(var))
49+
continue;
50+
sat::bool_var b = map.to_bool_var(var);
51+
if (b != sat::null_bool_var)
52+
m_solver->set_phase(sat::literal(b, m.is_false(value)));
53+
}
54+
}
4255

4356
void operator()(goal_ref const & g,
4457
goal_ref_buffer & result) {
@@ -66,6 +79,8 @@ class sat_tactic : public tactic {
6679
g->reset();
6780
g->m().compact_memory();
6881

82+
initialize_values(g, map);
83+
6984
CASSERT("sat_solver", m_solver->check_invariant());
7085
IF_VERBOSE(TACTIC_VERBOSITY_LVL, m_solver->display_status(verbose_stream()););
7186
TRACE("sat_dimacs", m_solver->display_dimacs(tout););
@@ -184,11 +199,14 @@ class sat_tactic : public tactic {
184199
imp * m_imp;
185200
params_ref m_params;
186201
statistics m_stats;
202+
ast_manager& m;
203+
vector<std::pair<expr_ref, expr_ref>> m_var2value;
187204

188205
public:
189206
sat_tactic(ast_manager & m, params_ref const & p):
190207
m_imp(nullptr),
191-
m_params(p) {
208+
m_params(p),
209+
m(m) {
192210
sat_params p1(p);
193211
}
194212

@@ -215,7 +233,7 @@ class sat_tactic : public tactic {
215233

216234
void operator()(goal_ref const & g,
217235
goal_ref_buffer & result) override {
218-
imp proc(g->m(), m_params);
236+
imp proc(g->m(), m_params, m_var2value);
219237
scoped_set_imp set(this, &proc);
220238
try {
221239
proc(g, result);
@@ -247,7 +265,8 @@ class sat_tactic : public tactic {
247265
}
248266

249267
void user_propagate_initialize_value(expr* var, expr* value) override {
250-
268+
verbose_stream() << "initialize-value\n";
269+
m_var2value.push_back({ expr_ref(var, m), expr_ref(value, m) });
251270
}
252271

253272

src/smt/smt_context.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -2920,7 +2920,7 @@ namespace smt {
29202920
}
29212921

29222922
void context::initialize_value(expr* var, expr* value) {
2923-
IF_VERBOSE(10, verbose_stream() << "context initialize " << mk_pp(var, m) << " := " << mk_pp(value, m) << "\n");
2923+
IF_VERBOSE(10, verbose_stream() << "initialize " << mk_pp(var, m) << " := " << mk_pp(value, m) << "\n");
29242924
sort* s = var->get_sort();
29252925
ensure_internalized(var);
29262926

src/smt/theory_bv.cpp

+1
Original file line numberDiff line numberDiff line change
@@ -1792,6 +1792,7 @@ namespace smt {
17921792
void theory_bv::initialize_value(expr* var, expr* value) {
17931793
rational val;
17941794
unsigned sz;
1795+
TRACE("bv", tout << "initializing " << mk_pp(var, m) << " := " << mk_pp(value, m) << "\n");
17951796
if (!m_util.is_numeral(value, val, sz)) {
17961797
IF_VERBOSE(5, verbose_stream() << "value should be a bit-vector " << mk_pp(value, m) << "\n");
17971798
return;

src/tactic/bv/bit_blaster_model_converter.cpp

+28
Original file line numberDiff line numberDiff line change
@@ -222,6 +222,34 @@ struct bit_blaster_model_converter : public model_converter {
222222
// no-op
223223
}
224224

225+
void convert_initialize_value(vector<std::pair<expr_ref, expr_ref>>& var2value) {
226+
if (m_vars.empty() || var2value.empty())
227+
return;
228+
rational r;
229+
bv_util util(m());
230+
for (unsigned j = 0; j < var2value.size(); ++j) {
231+
auto& [var, value] = var2value[j];
232+
if (!is_uninterp_const(var))
233+
continue;
234+
if (!util.is_numeral(value, r))
235+
continue;
236+
unsigned sz = m_vars.size();
237+
for (unsigned i = 0; i < sz; i++) {
238+
if (m_vars.get(i) != to_app(var)->get_decl())
239+
continue;
240+
unsigned k = 0;
241+
expr_ref bit_k(m());
242+
for (auto arg : *to_app(m_bits.get(i))) {
243+
bit_k = m().mk_bool_val(r.get_bit(k));
244+
var2value.push_back({ expr_ref(arg, m()), bit_k });
245+
++k;
246+
}
247+
var2value[i] = var2value.back();
248+
var2value.pop_back();
249+
}
250+
}
251+
}
252+
225253
protected:
226254
bit_blaster_model_converter(ast_manager & m):m_vars(m), m_bits(m), m_newbits(m) { }
227255
public:

0 commit comments

Comments
 (0)