Skip to content

Commit 68e4ed3

Browse files
fix #2531
Signed-off-by: Nikolaj Bjorner <[email protected]>
1 parent 000e485 commit 68e4ed3

File tree

5 files changed

+85
-11
lines changed

5 files changed

+85
-11
lines changed

src/ast/for_each_expr.cpp

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,3 +63,49 @@ bool has_skolem_functions(expr * n) {
6363
}
6464
return false;
6565
}
66+
67+
subterms::subterms(expr_ref_vector const& es): m_es(es) {}
68+
subterms::subterms(expr_ref& e) : m_es(e.m()) { m_es.push_back(e); }
69+
subterms::iterator subterms::begin() { return iterator(*this, true); }
70+
subterms::iterator subterms::end() { return iterator(*this, false); }
71+
subterms::iterator::iterator(subterms& f, bool start): m_es(f.m_es) {
72+
if (!start) m_es.reset();
73+
}
74+
expr* subterms::iterator::operator*() {
75+
return m_es.back();
76+
}
77+
subterms::iterator subterms::iterator::operator++(int) {
78+
iterator tmp = *this;
79+
++*this;
80+
return tmp;
81+
}
82+
subterms::iterator& subterms::iterator::operator++() {
83+
expr* e = m_es.back();
84+
m_visited.mark(e, true);
85+
if (is_app(e)) {
86+
for (expr* arg : *to_app(e)) {
87+
m_es.push_back(arg);
88+
}
89+
}
90+
while (m_visited.is_marked(m_es.back())) {
91+
m_es.pop_back();
92+
}
93+
return *this;
94+
}
95+
96+
bool subterms::iterator::operator==(iterator const& other) const {
97+
// ignore state of visited
98+
if (other.m_es.size() != m_es.size()) {
99+
return false;
100+
}
101+
for (unsigned i = m_es.size(); i-- > 0; ) {
102+
if (m_es.get(i) != other.m_es.get(i))
103+
return false;
104+
}
105+
return true;
106+
}
107+
108+
bool subterms::iterator::operator!=(iterator const& other) const {
109+
return !(*this == other);
110+
}
111+

src/ast/for_each_expr.h

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -167,5 +167,25 @@ unsigned get_num_exprs(expr * n, expr_fast_mark1 & visited);
167167

168168
bool has_skolem_functions(expr * n);
169169

170+
class subterms {
171+
expr_ref_vector m_es;
172+
public:
173+
class iterator {
174+
expr_ref_vector m_es;
175+
expr_mark m_visited;
176+
public:
177+
iterator(subterms& f, bool start);
178+
expr* operator*();
179+
iterator operator++(int);
180+
iterator& operator++();
181+
bool operator==(iterator const& other) const;
182+
bool operator!=(iterator const& other) const;
183+
};
184+
subterms(expr_ref_vector const& es);
185+
subterms(expr_ref& e);
186+
iterator begin();
187+
iterator end();
188+
};
189+
170190
#endif /* FOR_EACH_EXPR_H_ */
171191

src/qe/nlqsat.cpp

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -666,15 +666,14 @@ namespace qe {
666666

667667
// expr -> nlsat::solver
668668

669-
void hoist(expr_ref& fml) {
669+
bool hoist(expr_ref& fml) {
670670
expr_ref_vector paxioms(m);
671671
ackermanize_div(fml, paxioms);
672672
quantifier_hoister hoist(m);
673673
vector<app_ref_vector> qvars;
674674
app_ref_vector vars(m);
675675
bool is_forall = false;
676676
pred_abs abs(m);
677-
678677
expr_ref fml_a(m.mk_and(fml, mk_and(paxioms)), m);
679678
abs.get_free_vars(fml_a, vars);
680679
insert_set(m_free_vars, vars);
@@ -752,6 +751,7 @@ namespace qe {
752751
}
753752
}
754753
TRACE("qe", tout << fml << "\n";);
754+
return true;
755755
}
756756

757757

@@ -836,7 +836,10 @@ namespace qe {
836836
}
837837
reset();
838838
TRACE("qe", tout << fml << "\n";);
839-
hoist(fml);
839+
if (!hoist(fml)) {
840+
result.push_back(in.get());
841+
return;
842+
}
840843
TRACE("qe", tout << "ex: " << fml << "\n";);
841844
lbool is_sat = check_sat();
842845

src/qe/qsat.cpp

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -511,14 +511,14 @@ namespace qe {
511511

512512
bool pred_abs::validate_defs(model& model) const {
513513
bool valid = true;
514-
obj_map<expr, expr*>::iterator it = m_pred2lit.begin(), end = m_pred2lit.end();
515-
for (; it != end; ++it) {
514+
for (auto& kv : m_pred2lit) {
516515
expr_ref val_a(m), val_b(m);
517-
expr* a = it->m_key;
518-
expr* b = it->m_value;
516+
expr* a = kv.m_key;
517+
expr* b = kv.m_value;
519518
val_a = model(a);
520519
val_b = model(b);
521-
if (val_a != val_b) {
520+
if ((m.is_true(val_a) && m.is_false(val_b)) ||
521+
(m.is_false(val_a) && m.is_true(val_b))) {
522522
TRACE("qe",
523523
tout << mk_pp(a, m) << " := " << val_a << "\n";
524524
tout << mk_pp(b, m) << " := " << val_b << "\n";

src/smt/theory_seq.cpp

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -339,6 +339,7 @@ final_check_status theory_seq::final_check_eh() {
339339
m_rep.reset_cache();
340340
m_reset_cache = false;
341341
}
342+
342343
m_new_propagation = false;
343344
TRACE("seq", display(tout << "level: " << get_context().get_scope_level() << "\n"););
344345
TRACE("seq_verbose", get_context().display(tout););
@@ -3320,7 +3321,7 @@ bool theory_seq::solve_nc(unsigned idx) {
33203321
expr_ref c = canonize(n.contains(), deps);
33213322
expr* a = nullptr, *b = nullptr;
33223323

3323-
CTRACE("seq", c != n.contains(), tout << n.contains() << " => " << c << "\n";);
3324+
CTRACE("seq", c != n.contains(), tout << n.contains() << " =>\n" << c << "\n";);
33243325

33253326

33263327
if (m.is_true(c)) {
@@ -3334,6 +3335,9 @@ bool theory_seq::solve_nc(unsigned idx) {
33343335
}
33353336

33363337
if (ctx.get_assignment(len_gt) == l_true) {
3338+
VERIFY(m_util.str.is_contains(n.contains(), a, b));
3339+
enforce_length(a);
3340+
enforce_length(b);
33373341
TRACE("seq", tout << len_gt << " is true\n";);
33383342
return true;
33393343
}
@@ -3605,6 +3609,7 @@ bool theory_seq::internalize_term(app* term) {
36053609
}
36063610

36073611
void theory_seq::add_length(expr* e, expr* l) {
3612+
TRACE("seq", tout << get_context().get_scope_level() << " " << mk_pp(e, m) << "\n";);
36083613
SASSERT(!m_length.contains(l));
36093614
m_length.push_back(l);
36103615
m_has_length.insert(e);
@@ -4278,9 +4283,9 @@ bool theory_seq::can_propagate() {
42784283

42794284
expr_ref theory_seq::canonize(expr* e, dependency*& eqs) {
42804285
expr_ref result = expand(e, eqs);
4281-
TRACE("seq", tout << mk_pp(e, m) << " expands to " << result << "\n";);
4286+
TRACE("seq", tout << mk_pp(e, m) << " expands to\n" << result << "\n";);
42824287
m_rewrite(result);
4283-
TRACE("seq", tout << mk_pp(e, m) << " rewrites to " << result << "\n";);
4288+
TRACE("seq", tout << mk_pp(e, m) << " rewrites to\n" << result << "\n";);
42844289
return result;
42854290
}
42864291

0 commit comments

Comments
 (0)