Legend:
Page
Library
Module
Module type
Parameter
Class
Class type
Source
Source file z3cfg.ml
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133moduleB=Kernel.BasicmoduleL=Common.LogmoduleU=Common.UniversesmoduleZ=Z3moduleZS=Z.SolveropenUtils(** Concrete configuration. *)letcfg=[`Modeltrue;(* Generate a model *)`Prooffalse;(* Give a proof if unsatisfiable *)`Tracefalse(* Do not generate trace *);]letstring_of_cfg_itemitem=matchitemwith|`Modelb->("model",string_of_boolb)|`Proofb->("proof",string_of_boolb)|`Traceb->("trace",string_of_boolb)|`TraceFilefile->("trace_file_name",file)letstring_of_cfgcfg=List.mapstring_of_cfg_itemcfg(** Z3 context elaborated from a Z3 configuration *)letctx=Z.mk_context(string_of_cfgcfg)moduletypeZ3LOGIC=Utils.LOGICwithtypet=Z.Expr.exprandtypesmt_model=Z.Model.modelandtypectx=Z.contextmoduleMake(ZL:Z3LOGIC)=struct(** Set containing all the variables used by Z3 *)moduleSSet=Set.Make(structtypet=stringletcompare=compareend)(* Set of Z3 variables *)letvars=refSSet.empty(* Z3 Solver *)letsolver=Z3.Solver.mk_simple_solverctx(** [add expr] add the asserition [expr] in the Z3 solver. [expr] should be a predicate. *)letaddexpr=Z3.Solver.addsolver[expr](** [mk_var s] construct a Z3 expression from the Z3 variable [s]. *)letmk_vars=vars:=SSet.adds!vars;ZL.mk_varctxsletvars_of_univsunivs=letf=function|U.Varname->vars:=SSet.add(ZL.mk_namename)!vars|_->()inList.iterfunivsletvars_of_pred=function|U.Axiom(s,s')->vars_of_univs[s;s']|U.Cumul(s,s')->vars_of_univs[s;s']|U.Rule(s,s',s'')->vars_of_univs[s;s';s''](** [mk_pred p] construct the Z3 predicate from a universe predicate *)letmk_predp=(* register variables first to add bounds constraints afterward *)vars_of_predp;matchpwith|U.Axiom(s,s')->ZL.mk_axiomctx(ZL.mk_univctxs)(ZL.mk_univctxs')|U.Cumul(s,s')->ZL.mk_cumulctx(ZL.mk_univctxs)(ZL.mk_univctxs')|U.Rule(s,s',s'')->ZL.mk_rulectx(ZL.mk_univctxs)(ZL.mk_univctxs')(ZL.mk_univctxs'')(** [mk_theory m] construct a Z3 theory for the non-interpreted predicate using the theory [t]. *)letmk_theoryt=List.iter(fun(p,b)->ifbthenadd(mk_predp)elseadd(Z.Boolean.mk_notctx(mk_predp)))t(** [register_vars vars i] give bound for each variable [var] between [0] and [i] *)letregister_varsvarsi=SSet.iter(funvar->add(ZL.mk_boundsctxvari))vars(** [mk_cstr c] construct the Z3 constraint from the universe constraint [c] *)letmk_cstrc=letopenUinmatchcwith|Predp->mk_predp|EqVar(l,r)->Z.Boolean.mk_eqctx(mk_var(ZL.mk_namel))(mk_var(ZL.mk_namer))(** [check theory_of i] solves the current constraints with at most [i] universes. If no solution is found, [check] is called recursively on [i+1]. *)letreccheckenvi=ifi>env.maxthenraiseNoSolution;ZS.pushsolver;lettheory=env.mk_theoryiinifZL.logic=`Qfufthenmk_theorytheory;register_vars!varsi;matchZS.checksolver[]with|ZS.UNSATISFIABLE->L.log_solver"[SOLVER] No solution found with %d universes"i;ZS.popsolver1;checkenv(i+1)|ZS.UNKNOWN->assertfalse|ZS.SATISFIABLE->(matchZS.get_modelsolverwith|None->assertfalse|Somemodel->letmodel(cst:B.name):U.univ=letvar=ZL.mk_namecstinZL.solution_of_varctximodelvarin(i,model))(** [solve mk_theory] tries to solve the constraints *)letsolveenv=L.log_solver"[SOLVER] Solving...";checkenvenv.minletadd:U.cstr->unit=funcstr->add(mk_cstrcstr)endmoduleSyn:Z3LOGIC=Z3synmoduleArith=Z3arith.Make