mirror of
https://github.com/Z3Prover/z3
synced 2025-04-15 21:38:44 +00:00
Add new probes for arithmetic. Check for LIA and LRA (and activate qe if applicable). Modify echo tactic to send results to the regular stream.
Signed-off-by: Leonardo de Moura <leonardo@microsoft.com>
This commit is contained in:
parent
18bae81731
commit
97bf9418f7
|
@ -981,14 +981,6 @@ br_status arith_rewriter::mk_to_real_core(expr * arg, expr_ref & result) {
|
||||||
result = m_util.mk_numeral(a, false);
|
result = m_util.mk_numeral(a, false);
|
||||||
return BR_DONE;
|
return BR_DONE;
|
||||||
}
|
}
|
||||||
#if 0
|
|
||||||
// The following rewriting rule is not correct.
|
|
||||||
// It is used only for making experiments.
|
|
||||||
if (m_util.is_to_int(arg)) {
|
|
||||||
result = to_app(arg)->get_arg(0);
|
|
||||||
return BR_DONE;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
// push to_real over OP_ADD, OP_MUL
|
// push to_real over OP_ADD, OP_MUL
|
||||||
if (m_push_to_real) {
|
if (m_push_to_real) {
|
||||||
if (m_util.is_add(arg) || m_util.is_mul(arg)) {
|
if (m_util.is_add(arg) || m_util.is_mul(arg)) {
|
||||||
|
|
|
@ -34,9 +34,9 @@ public:
|
||||||
expr_dependency_ref & core) {
|
expr_dependency_ref & core) {
|
||||||
#pragma omp critical (echo_tactic)
|
#pragma omp critical (echo_tactic)
|
||||||
{
|
{
|
||||||
m_ctx.diagnostic_stream() << m_msg;
|
m_ctx.regular_stream() << m_msg;
|
||||||
if (m_newline)
|
if (m_newline)
|
||||||
m_ctx.diagnostic_stream() << std::endl;
|
m_ctx.regular_stream() << std::endl;
|
||||||
}
|
}
|
||||||
skip_tactic::operator()(in, result, mc, pc, core);
|
skip_tactic::operator()(in, result, mc, pc, core);
|
||||||
}
|
}
|
||||||
|
|
|
@ -313,23 +313,28 @@ struct is_non_nira_functor {
|
||||||
bool m_int;
|
bool m_int;
|
||||||
bool m_real;
|
bool m_real;
|
||||||
bool m_quant;
|
bool m_quant;
|
||||||
|
bool m_linear;
|
||||||
|
|
||||||
is_non_nira_functor(ast_manager & _m, bool _int, bool _real, bool _quant):m(_m), u(m), m_int(_int), m_real(_real), m_quant(_quant) {}
|
is_non_nira_functor(ast_manager & _m, bool _int, bool _real, bool _quant, bool linear):m(_m), u(m), m_int(_int), m_real(_real), m_quant(_quant), m_linear(linear) {}
|
||||||
|
|
||||||
|
void throw_found() {
|
||||||
|
throw found();
|
||||||
|
}
|
||||||
|
|
||||||
void operator()(var * x) {
|
void operator()(var * x) {
|
||||||
if (!m_quant)
|
if (!m_quant)
|
||||||
throw found();
|
throw_found();
|
||||||
sort * s = x->get_sort();
|
sort * s = x->get_sort();
|
||||||
if (m_int && u.is_int(s))
|
if (m_int && u.is_int(s))
|
||||||
return;
|
return;
|
||||||
if (m_real && u.is_real(s))
|
if (m_real && u.is_real(s))
|
||||||
return;
|
return;
|
||||||
throw found();
|
throw_found();
|
||||||
}
|
}
|
||||||
|
|
||||||
void operator()(quantifier *) {
|
void operator()(quantifier *) {
|
||||||
if (!m_quant)
|
if (!m_quant)
|
||||||
throw found();
|
throw_found();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool compatible_sort(app * n) const {
|
bool compatible_sort(app * n) const {
|
||||||
|
@ -344,35 +349,92 @@ struct is_non_nira_functor {
|
||||||
|
|
||||||
void operator()(app * n) {
|
void operator()(app * n) {
|
||||||
if (!compatible_sort(n))
|
if (!compatible_sort(n))
|
||||||
throw found();
|
throw_found();
|
||||||
family_id fid = n->get_family_id();
|
family_id fid = n->get_family_id();
|
||||||
if (fid == m.get_basic_family_id())
|
if (fid == m.get_basic_family_id())
|
||||||
return;
|
return;
|
||||||
if (fid == u.get_family_id())
|
if (fid == u.get_family_id()) {
|
||||||
|
switch (n->get_decl_kind()) {
|
||||||
|
case OP_LE: case OP_GE: case OP_LT: case OP_GT:
|
||||||
|
case OP_ADD: case OP_UMINUS: case OP_SUB: case OP_ABS:
|
||||||
|
case OP_NUM:
|
||||||
|
return;
|
||||||
|
case OP_MUL:
|
||||||
|
if (m_linear) {
|
||||||
|
if (n->get_num_args() != 2)
|
||||||
|
throw_found();
|
||||||
|
if (!u.is_numeral(n->get_arg(0)))
|
||||||
|
throw_found();
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
case OP_IDIV: case OP_DIV: case OP_REM: case OP_MOD:
|
||||||
|
if (m_linear && !u.is_numeral(n->get_arg(1)))
|
||||||
|
throw_found();
|
||||||
|
return;
|
||||||
|
case OP_IS_INT:
|
||||||
|
if (m_real)
|
||||||
|
throw_found();
|
||||||
|
return;
|
||||||
|
case OP_TO_INT:
|
||||||
|
case OP_TO_REAL:
|
||||||
|
return;
|
||||||
|
case OP_POWER:
|
||||||
|
if (m_linear)
|
||||||
|
throw_found();
|
||||||
|
return;
|
||||||
|
case OP_IRRATIONAL_ALGEBRAIC_NUM:
|
||||||
|
if (m_linear || !m_real)
|
||||||
|
throw_found();
|
||||||
|
return;
|
||||||
|
default:
|
||||||
|
throw_found();
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (is_uninterp_const(n))
|
if (is_uninterp_const(n))
|
||||||
return;
|
return;
|
||||||
throw found();
|
throw_found();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
static bool is_qfnia(goal const & g) {
|
static bool is_qfnia(goal const & g) {
|
||||||
is_non_nira_functor p(g.m(), true, false, false);
|
is_non_nira_functor p(g.m(), true, false, false, false);
|
||||||
return !test(g, p);
|
return !test(g, p);
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool is_qfnra(goal const & g) {
|
static bool is_qfnra(goal const & g) {
|
||||||
is_non_nira_functor p(g.m(), false, true, false);
|
is_non_nira_functor p(g.m(), false, true, false, false);
|
||||||
return !test(g, p);
|
return !test(g, p);
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool is_nia(goal const & g) {
|
static bool is_nia(goal const & g) {
|
||||||
is_non_nira_functor p(g.m(), true, false, true);
|
is_non_nira_functor p(g.m(), true, false, true, false);
|
||||||
return !test(g, p);
|
return !test(g, p);
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool is_nra(goal const & g) {
|
static bool is_nra(goal const & g) {
|
||||||
is_non_nira_functor p(g.m(), false, true, true);
|
is_non_nira_functor p(g.m(), false, true, true, false);
|
||||||
|
return !test(g, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool is_nira(goal const & g) {
|
||||||
|
is_non_nira_functor p(g.m(), true, true, true, false);
|
||||||
|
return !test(g, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool is_lra(goal const & g) {
|
||||||
|
is_non_nira_functor p(g.m(), false, true, true, true);
|
||||||
|
return !test(g, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool is_lia(goal const & g) {
|
||||||
|
is_non_nira_functor p(g.m(), true, false, true, true);
|
||||||
|
return !test(g, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool is_lira(goal const & g) {
|
||||||
|
is_non_nira_functor p(g.m(), true, true, true, true);
|
||||||
return !test(g, p);
|
return !test(g, p);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -404,6 +466,34 @@ public:
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class is_nira_probe : public probe {
|
||||||
|
public:
|
||||||
|
virtual result operator()(goal const & g) {
|
||||||
|
return is_nira(g);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
class is_lia_probe : public probe {
|
||||||
|
public:
|
||||||
|
virtual result operator()(goal const & g) {
|
||||||
|
return is_lia(g);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
class is_lra_probe : public probe {
|
||||||
|
public:
|
||||||
|
virtual result operator()(goal const & g) {
|
||||||
|
return is_lra(g);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
class is_lira_probe : public probe {
|
||||||
|
public:
|
||||||
|
virtual result operator()(goal const & g) {
|
||||||
|
return is_lira(g);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
probe * mk_is_qfnia_probe() {
|
probe * mk_is_qfnia_probe() {
|
||||||
return alloc(is_qfnia_probe);
|
return alloc(is_qfnia_probe);
|
||||||
}
|
}
|
||||||
|
@ -419,3 +509,19 @@ probe * mk_is_nia_probe() {
|
||||||
probe * mk_is_nra_probe() {
|
probe * mk_is_nra_probe() {
|
||||||
return alloc(is_nra_probe);
|
return alloc(is_nra_probe);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
probe * mk_is_nira_probe() {
|
||||||
|
return alloc(is_nira_probe);
|
||||||
|
}
|
||||||
|
|
||||||
|
probe * mk_is_lia_probe() {
|
||||||
|
return alloc(is_lia_probe);
|
||||||
|
}
|
||||||
|
|
||||||
|
probe * mk_is_lra_probe() {
|
||||||
|
return alloc(is_lra_probe);
|
||||||
|
}
|
||||||
|
|
||||||
|
probe * mk_is_lira_probe() {
|
||||||
|
return alloc(is_lira_probe);
|
||||||
|
}
|
||||||
|
|
|
@ -49,11 +49,19 @@ probe * mk_is_qfnia_probe();
|
||||||
probe * mk_is_qfnra_probe();
|
probe * mk_is_qfnra_probe();
|
||||||
probe * mk_is_nia_probe();
|
probe * mk_is_nia_probe();
|
||||||
probe * mk_is_nra_probe();
|
probe * mk_is_nra_probe();
|
||||||
|
probe * mk_is_nira_probe();
|
||||||
|
probe * mk_is_lia_probe();
|
||||||
|
probe * mk_is_lra_probe();
|
||||||
|
probe * mk_is_lira_probe();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
ADD_PROBE("is-qfnia", "true if the goal is in QF_NIA (quantifier-free nonlinear integer arithmetic).", "mk_is_qfnia_probe()")
|
ADD_PROBE("is-qfnia", "true if the goal is in QF_NIA (quantifier-free nonlinear integer arithmetic).", "mk_is_qfnia_probe()")
|
||||||
ADD_PROBE("is-qfnra", "true if the goal is in QF_NRA (quantifier-free nonlinear real arithmetic).", "mk_is_qfnra_probe()")
|
ADD_PROBE("is-qfnra", "true if the goal is in QF_NRA (quantifier-free nonlinear real arithmetic).", "mk_is_qfnra_probe()")
|
||||||
ADD_PROBE("is-nia", "true if the goal is in NIA (nonlinear integer arithmetic, formula may have quantifiers).", "mk_is_nia_probe()")
|
ADD_PROBE("is-nia", "true if the goal is in NIA (nonlinear integer arithmetic, formula may have quantifiers).", "mk_is_nia_probe()")
|
||||||
ADD_PROBE("is-nra", "true if the goal is in NRA (nonlinear real arithmetic, formula may have quantifiers).", "mk_is_nra_probe()")
|
ADD_PROBE("is-nra", "true if the goal is in NRA (nonlinear real arithmetic, formula may have quantifiers).", "mk_is_nra_probe()")
|
||||||
|
ADD_PROBE("is-nira", "true if the goal is in NIRA (nonlinear integer and real arithmetic, formula may have quantifiers).", "mk_is_nira_probe()")
|
||||||
|
ADD_PROBE("is-lia", "true if the goal is in LIA (linear integer arithmetic, formula may have quantifiers).", "mk_is_lia_probe()")
|
||||||
|
ADD_PROBE("is-lra", "true if the goal is in LRA (linear real arithmetic, formula may have quantifiers).", "mk_is_lra_probe()")
|
||||||
|
ADD_PROBE("is-lira", "true if the goal is in LIRA (linear integer and real arithmetic, formula may have quantifiers).", "mk_is_lira_probe()")
|
||||||
*/
|
*/
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -26,22 +26,18 @@ Notes:
|
||||||
#include"qfnra_tactic.h"
|
#include"qfnra_tactic.h"
|
||||||
#include"nra_tactic.h"
|
#include"nra_tactic.h"
|
||||||
#include"probe_arith.h"
|
#include"probe_arith.h"
|
||||||
|
#include"quant_tactics.h"
|
||||||
|
|
||||||
tactic * mk_default_tactic(ast_manager & m, params_ref const & p) {
|
tactic * mk_default_tactic(ast_manager & m, params_ref const & p) {
|
||||||
tactic * st = using_params(and_then(mk_simplify_tactic(m),
|
tactic * st = using_params(and_then(mk_simplify_tactic(m),
|
||||||
cond(mk_is_qfbv_probe(),
|
cond(mk_is_qfbv_probe(), mk_qfbv_tactic(m),
|
||||||
mk_qfbv_tactic(m),
|
cond(mk_is_qflia_probe(), mk_qflia_tactic(m),
|
||||||
cond(mk_is_qflia_probe(),
|
cond(mk_is_qflra_probe(), mk_qflra_tactic(m),
|
||||||
mk_qflia_tactic(m),
|
cond(mk_is_qfnra_probe(), mk_qfnra_tactic(m),
|
||||||
cond(mk_is_qflra_probe(),
|
cond(mk_is_qfnia_probe(), mk_qfnia_tactic(m),
|
||||||
mk_qflra_tactic(m),
|
cond(mk_is_nra_probe(), mk_nra_tactic(m),
|
||||||
cond(mk_is_qfnra_probe(),
|
cond(mk_is_lira_probe(), mk_lira_tactic(m, p),
|
||||||
mk_qfnra_tactic(m),
|
mk_smt_tactic())))))))),
|
||||||
cond(mk_is_qfnia_probe(),
|
|
||||||
mk_qfnia_tactic(m),
|
|
||||||
cond(mk_is_nra_probe(),
|
|
||||||
mk_nra_tactic(m),
|
|
||||||
mk_smt_tactic()))))))),
|
|
||||||
p);
|
p);
|
||||||
return st;
|
return st;
|
||||||
}
|
}
|
||||||
|
|
|
@ -72,6 +72,8 @@ tactic * mk_tactic_for_logic(ast_manager & m, params_ref const & p, symbol const
|
||||||
return mk_uflra_tactic(m, p);
|
return mk_uflra_tactic(m, p);
|
||||||
else if (logic=="LRA")
|
else if (logic=="LRA")
|
||||||
return mk_lra_tactic(m, p);
|
return mk_lra_tactic(m, p);
|
||||||
|
else if (logic=="LIA")
|
||||||
|
return mk_lia_tactic(m, p);
|
||||||
else if (logic=="UFBV")
|
else if (logic=="UFBV")
|
||||||
return mk_ufbv_tactic(m, p);
|
return mk_ufbv_tactic(m, p);
|
||||||
else if (logic=="BV")
|
else if (logic=="BV")
|
||||||
|
|
|
@ -104,3 +104,10 @@ tactic * mk_lra_tactic(ast_manager & m, params_ref const & p) {
|
||||||
return st;
|
return st;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
tactic * mk_lia_tactic(ast_manager & m, params_ref const & p) {
|
||||||
|
return mk_lra_tactic(m, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
tactic * mk_lira_tactic(ast_manager & m, params_ref const & p) {
|
||||||
|
return mk_lra_tactic(m, p);
|
||||||
|
}
|
||||||
|
|
|
@ -29,5 +29,7 @@ tactic * mk_auflia_tactic(ast_manager & m, params_ref const & p);
|
||||||
tactic * mk_auflira_tactic(ast_manager & m, params_ref const & p);
|
tactic * mk_auflira_tactic(ast_manager & m, params_ref const & p);
|
||||||
tactic * mk_aufnira_tactic(ast_manager & m, params_ref const & p);
|
tactic * mk_aufnira_tactic(ast_manager & m, params_ref const & p);
|
||||||
tactic * mk_lra_tactic(ast_manager & m, params_ref const & p);
|
tactic * mk_lra_tactic(ast_manager & m, params_ref const & p);
|
||||||
|
tactic * mk_lia_tactic(ast_manager & m, params_ref const & p);
|
||||||
|
tactic * mk_lira_tactic(ast_manager & m, params_ref const & p);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Reference in a new issue