3
0
Fork 0
mirror of https://github.com/Z3Prover/z3 synced 2025-05-03 22:05:45 +00:00

working on smt2 and api

This commit is contained in:
Ken McMillan 2013-03-26 17:25:54 -07:00
parent 2b93537366
commit 78848f3ddd
30 changed files with 1307 additions and 94 deletions

View file

@ -240,6 +240,8 @@ protected:
symbol m_produce_unsat_cores;
symbol m_produce_models;
symbol m_produce_assignments;
symbol m_produce_interpolants;
symbol m_check_interpolants;
symbol m_regular_output_channel;
symbol m_diagnostic_output_channel;
symbol m_random_seed;
@ -253,7 +255,9 @@ protected:
return
s == m_print_success || s == m_print_warning || s == m_expand_definitions ||
s == m_interactive_mode || s == m_produce_proofs || s == m_produce_unsat_cores ||
s == m_produce_models || s == m_produce_assignments || s == m_regular_output_channel || s == m_diagnostic_output_channel ||
s == m_produce_models || s == m_produce_assignments || s == m_produce_interpolants ||
s == m_check_interpolants ||
s == m_regular_output_channel || s == m_diagnostic_output_channel ||
s == m_random_seed || s == m_verbosity || s == m_global_decls;
}
@ -270,6 +274,8 @@ public:
m_produce_unsat_cores(":produce-unsat-cores"),
m_produce_models(":produce-models"),
m_produce_assignments(":produce-assignments"),
m_produce_interpolants(":produce-interpolants"),
m_check_interpolants(":check-interpolants"),
m_regular_output_channel(":regular-output-channel"),
m_diagnostic_output_channel(":diagnostic-output-channel"),
m_random_seed(":random-seed"),
@ -337,6 +343,13 @@ class set_option_cmd : public set_get_option_cmd {
check_not_initialized(ctx, m_produce_proofs);
ctx.set_produce_proofs(to_bool(value));
}
else if (m_option == m_produce_interpolants) {
check_not_initialized(ctx, m_produce_interpolants);
ctx.set_produce_interpolants(to_bool(value));
}
else if (m_option == m_check_interpolants) {
ctx.set_check_interpolants(to_bool(value));
}
else if (m_option == m_produce_unsat_cores) {
check_not_initialized(ctx, m_produce_unsat_cores);
ctx.set_produce_unsat_cores(to_bool(value));
@ -485,6 +498,9 @@ public:
else if (opt == m_produce_proofs) {
print_bool(ctx, ctx.produce_proofs());
}
else if (opt == m_produce_interpolants) {
print_bool(ctx, ctx.produce_interpolants());
}
else if (opt == m_produce_unsat_cores) {
print_bool(ctx, ctx.produce_unsat_cores());
}

View file

@ -38,6 +38,9 @@ Notes:
#include"model_evaluator.h"
#include"for_each_expr.h"
#include"scoped_timer.h"
#include"interpolant_cmds.h"
//FIXME Does this break modularity?
// #include"smt_solver.h"
func_decls::func_decls(ast_manager & m, func_decl * f):
m_decls(TAG(func_decl*, f, 0)) {
@ -323,6 +326,7 @@ cmd_context::cmd_context(bool main_ctx, ast_manager * m, symbol const & l):
install_basic_cmds(*this);
install_ext_basic_cmds(*this);
install_core_tactic_cmds(*this);
install_interpolant_cmds(*this);
SASSERT(m != 0 || !has_manager());
if (m)
init_external_manager();
@ -380,6 +384,19 @@ void cmd_context::set_produce_proofs(bool f) {
m_params.m_proof = f;
}
void cmd_context::set_produce_interpolants(bool f) {
// can only be set before initialization
// FIXME currently synonym for produce_proofs
// also sets the default solver to be simple smt
SASSERT(!has_manager());
m_params.m_proof = f;
// set_solver_factory(mk_smt_solver_factory());
}
void cmd_context::set_check_interpolants(bool f) {
m_params.m_check_interpolants = f;
}
bool cmd_context::produce_models() const {
return m_params.m_model;
}
@ -388,6 +405,15 @@ bool cmd_context::produce_proofs() const {
return m_params.m_proof;
}
bool cmd_context::produce_interpolants() const {
// FIXME currently synonym for produce_proofs
return m_params.m_proof;
}
bool cmd_context::check_interpolants() const {
return m_params.m_check_interpolants;
}
bool cmd_context::produce_unsat_cores() const {
return m_params.m_unsat_core;
}
@ -1456,11 +1482,27 @@ void cmd_context::validate_model() {
}
}
// FIXME: really interpolants_enabled ought to be a parameter to the solver factory,
// but this is a global change, so for now, we use an alternate solver factory
// for interpolation
void cmd_context::mk_solver() {
bool proofs_enabled, models_enabled, unsat_core_enabled;
params_ref p;
m_params.get_solver_params(m(), p, proofs_enabled, models_enabled, unsat_core_enabled);
m_solver = (*m_solver_factory)(m(), p, proofs_enabled, models_enabled, unsat_core_enabled, m_logic);
if(produce_interpolants()){
SASSERT(m_interpolating_solver_factory);
m_solver = (*m_interpolating_solver_factory)(m(), p, true /* must have proofs */, models_enabled, unsat_core_enabled, m_logic);
}
else
m_solver = (*m_solver_factory)(m(), p, proofs_enabled, models_enabled, unsat_core_enabled, m_logic);
}
void cmd_context::set_interpolating_solver_factory(solver_factory * f) {
SASSERT(!has_manager());
m_interpolating_solver_factory = f;
}
void cmd_context::set_solver_factory(solver_factory * f) {

View file

@ -186,6 +186,7 @@ protected:
svector<scope> m_scopes;
scoped_ptr<solver_factory> m_solver_factory;
scoped_ptr<solver_factory> m_interpolating_solver_factory;
ref<solver> m_solver;
ref<check_sat_result> m_check_sat_result;
@ -253,6 +254,7 @@ public:
void cancel() { set_cancel(true); }
void reset_cancel() { set_cancel(false); }
context_params & params() { return m_params; }
solver_factory &get_solver_factory() { return *m_solver_factory; }
void global_params_updated(); // this method should be invoked when global (and module) params are updated.
bool set_logic(symbol const & s);
bool has_logic() const { return m_logic != symbol::null; }
@ -275,12 +277,16 @@ public:
void set_random_seed(unsigned s) { m_random_seed = s; }
bool produce_models() const;
bool produce_proofs() const;
bool produce_interpolants() const;
bool check_interpolants() const;
bool produce_unsat_cores() const;
bool well_sorted_check_enabled() const;
bool validate_model_enabled() const;
void set_produce_models(bool flag);
void set_produce_unsat_cores(bool flag);
void set_produce_proofs(bool flag);
void set_produce_interpolants(bool flag);
void set_check_interpolants(bool flag);
bool produce_assignments() const { return m_produce_assignments; }
void set_produce_assignments(bool flag) { m_produce_assignments = flag; }
void set_status(status st) { m_status = st; }
@ -294,6 +300,7 @@ public:
sexpr_manager & sm() const { if (!m_sexpr_manager) const_cast<cmd_context*>(this)->m_sexpr_manager = alloc(sexpr_manager); return *m_sexpr_manager; }
void set_solver_factory(solver_factory * s);
void set_interpolating_solver_factory(solver_factory * s);
void set_check_sat_result(check_sat_result * r) { m_check_sat_result = r; }
check_sat_result * get_check_sat_result() const { return m_check_sat_result.get(); }
check_sat_state cs_state() const;

View file

@ -61,6 +61,9 @@ void context_params::set(char const * param, char const * value) {
else if (p == "proof") {
set_bool(m_proof, param, value);
}
else if (p == "check_interpolants") {
set_bool(m_check_interpolants, param, value);
}
else if (p == "model") {
set_bool(m_model, param, value);
}
@ -96,6 +99,7 @@ void context_params::updt_params(params_ref const & p) {
m_well_sorted_check = p.get_bool("type_check", p.get_bool("well_sorted_check", true));
m_auto_config = p.get_bool("auto_config", true);
m_proof = p.get_bool("proof", false);
m_check_interpolants = p.get_bool("check_interpolants", false);
m_model = p.get_bool("model", true);
m_model_validate = p.get_bool("model_validate", false);
m_trace = p.get_bool("trace", false);
@ -111,6 +115,7 @@ void context_params::collect_param_descrs(param_descrs & d) {
d.insert("type_check", CPK_BOOL, "type checker (alias for well_sorted_check)", "true");
d.insert("auto_config", CPK_BOOL, "use heuristics to automatically select solver and configure it", "true");
d.insert("proof", CPK_BOOL, "proof generation, it must be enabled when the Z3 context is created", "false");
d.insert("check_interpolants", CPK_BOOL, "check correctness of interpolants", "false");
d.insert("model", CPK_BOOL, "model generation for solvers, this parameter can be overwritten when creating a solver", "true");
d.insert("model_validate", CPK_BOOL, "validate models produced by solvers", "false");
d.insert("trace", CPK_BOOL, "trace generation for VCC", "false");

View file

@ -29,6 +29,8 @@ class context_params {
public:
bool m_auto_config;
bool m_proof;
bool m_interpolants;
bool m_check_interpolants;
bool m_debug_ref_count;
bool m_trace;
std::string m_trace_file_name;

View file

@ -0,0 +1,120 @@
/*++
Copyright (c) 2013 Microsoft Corporation
Module Name:
interpolant_cmds.cpp
Abstract:
Commands for interpolation.
Author:
Leonardo (leonardo) 2011-12-23
Notes:
--*/
#include<sstream>
#include"cmd_context.h"
#include"cmd_util.h"
#include"scoped_timer.h"
#include"scoped_ctrl_c.h"
#include"cancel_eh.h"
#include"ast_pp.h"
#include"ast_smt_pp.h"
#include"ast_smt2_pp.h"
#include"parametric_cmd.h"
#include"mpq.h"
#include"expr2var.h"
#include"pp.h"
#include"pp_params.hpp"
#include"iz3interp.h"
#include"iz3checker.h"
static void get_interpolant_and_maybe_check(cmd_context & ctx, expr * t, bool check) {
// get the proof, if there is one
if (!ctx.produce_interpolants())
throw cmd_exception("interpolation is not enabled, use command (set-option :produce-interpolants true)");
if (!ctx.has_manager() ||
ctx.cs_state() != cmd_context::css_unsat)
throw cmd_exception("proof is not available");
expr_ref pr(ctx.m());
pr = ctx.get_check_sat_result()->get_proof();
if (pr == 0)
throw cmd_exception("proof is not available");
// get the assertions
ptr_vector<expr>::const_iterator it = ctx.begin_assertions();
ptr_vector<expr>::const_iterator end = ctx.end_assertions();
ptr_vector<ast> cnsts(end - it);
for (int i = 0; it != end; ++it, ++i)
cnsts[i] = *it;
// compute an interpolant
ptr_vector<ast> interps;
try {
iz3interpolate(ctx.m(),pr.get(),cnsts,t,interps,0);
}
catch (iz3_bad_tree &) {
throw cmd_exception("interpolation pattern contains non-asserted formula");
}
catch (iz3_incompleteness &) {
throw cmd_exception("incompleteness in interpolator");
}
// if we lived, print it out
for(unsigned i = 0; i < interps.size(); i++){
ctx.regular_stream() << mk_pp(interps[i], ctx.m()) << std::endl;
#if 0
ast_smt_pp pp(ctx.m());
pp.set_logic(ctx.get_logic().str().c_str());
pp.display_smt2(ctx.regular_stream(), to_expr(interps[i]));
ctx.regular_stream() << std::endl;
#endif
}
// verify, for the paranoid...
if(check || ctx.check_interpolants()){
std::ostringstream err;
ast_manager &_m = ctx.m();
// need a solver -- make one here FIXME is this right?
bool proofs_enabled, models_enabled, unsat_core_enabled;
params_ref p;
ctx.params().get_solver_params(_m, p, proofs_enabled, models_enabled, unsat_core_enabled);
scoped_ptr<solver> sp = (ctx.get_solver_factory())(_m, p, false, true, false, ctx.get_logic());
if(iz3check(_m,sp.get(),err,cnsts,t,interps))
ctx.regular_stream() << "correct\n";
else
ctx.regular_stream() << "incorrect: " << err.str().c_str() << "\n";
}
for(unsigned i = 0; i < interps.size(); i++){
ctx.m().dec_ref(interps[i]);
}
}
static void get_interpolant(cmd_context & ctx, expr * t) {
get_interpolant_and_maybe_check(ctx,t,false);
}
static void get_and_check_interpolant(cmd_context & ctx, expr * t) {
get_interpolant_and_maybe_check(ctx,t,true);
}
UNARY_CMD(get_interpolant_cmd, "get-interpolant", "<fmla>", "get interpolant for marked positions in fmla", CPK_EXPR, expr *, get_interpolant(ctx, arg););
// UNARY_CMD(get_and_check_interpolant_cmd, "get-and-check-interpolant", "<fmla>", "get and check interpolant for marked positions in fmla", CPK_EXPR, expr *, get_and_check_interpolant(ctx, arg););
void install_interpolant_cmds(cmd_context & ctx) {
ctx.insert(alloc(get_interpolant_cmd));
// ctx.insert(alloc(get_and_check_interpolant_cmd));
}

View file

@ -0,0 +1,24 @@
/*++
Copyright (c) 2011 Microsoft Corporation
Module Name:
interpolant_cmds.h
Abstract:
Commands for interpolation.
Author:
Leonardo (leonardo) 2011-12-23
Notes:
--*/
#ifndef _INTERPOLANT_CMDS_H_
#define _INTERPOLANT_CMDS_H_
class cmd_context;
void install_interpolant_cmds(cmd_context & ctx);
#endif