Legend:
Page
Library
Module
Module type
Parameter
Class
Class type
Source
Source file LLProof_check.ml
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208(* This file is free software, part of Zipperposition. See file "license" for more details. *)(** {1 Check LLProof} *)openLogtkmoduleT=TypedSTermmoduleF=T.FormmoduleTy=T.TymoduleFmt=CCFormatmoduleP=LLProoftypeproof=LLProof.ttypeform=F.t(** {2 Types} *)typeres=|R_ok|R_failtypestats={n_ok:int;n_fail:int;n_skip_esa:int;(** steps skipped because ESA *)n_skip_tags:int;(** steps skipped because of theory tags *)n_skip_trivial:int;(** steps skipped because they are trivial *)n_skip:int;}letsection=LLProof.sectionletprof_check=ZProf.make"llproof.check.step"letstat_check=Util.mk_stat"llproof.check.step"letpp_resout=function|R_ok->Fmt.fprintfout"@{<Green>OK@}"|R_fail->Fmt.fprintfout"@{<Red>FAIL@}"letpp_statsout(s:stats)=Fmt.fprintfout"(@[<hv>:ok %d@ :fail %d@ :skip %d (:esa %d@ :tags %d)@])"s.n_oks.n_fails.n_skips.n_skip_esas.n_skip_tagsexceptionErrorofstringleterrormsg=raise(Errormsg)leterrorfmsg=Fmt.ksprintf~f:errormsglet()=Printexc.register_printer(function|Errormsg->Some(Util.err_spf"llproof_check: %s"msg)|_->None)(** {2 Checking Proofs} *)letinstantiate(f:form)(inst:LLProof.inst):form=letf=T.rename_all_varsfinletvars,body=T.unfold_binderBinder.ForallfinifList.lengthvars<>List.lengthinstthen(errorf"mismatched arities in instantiate `%a`@ :with %a"T.ppfLLProof.pp_instinst);letsubst=List.fold_left2Var.Subst.addVar.Subst.emptyvarsinstinletf'=T.Subst.evalsubstbodyinUtil.debugf~section5"(@[<hv>instantiate@ :inst %a@ :from %a@ :into %a@ :subst {%a}@])"(funk->kLLProof.pp_instinstT.ppfT.ppf'(Var.Subst.ppT.pp_with_ty)subst);f'letconcl_of_parent(p:LLProof.parent):form=matchp.LLProof.p_instwith|[]->P.conclp.LLProof.p_proof|r->letf=P.conclp.LLProof.p_proofininstantiatefrletopen_forall=T.unfold_binderBinder.Foralltypecheck_step_res=|CS_checkofres|CS_skipof[`ESA|`Other|`Tags|`Trivial]letpp_csrout=function|CS_checkr->pp_resoutr|CS_skipr->lets=matchrwith|`ESA->"esa"|`Tags->"tags"|`Other->"other"|`Trivial->"trivial"inFmt.fprintfout"@{<Yellow>SKIP@} (%s)"sletconv_res=function|LLProver.R_ok->R_ok|LLProver.R_fail->R_failletn_proof=ref0(* proof counter *)letprove~dot_prefix(a:formlist)(b:form)=letmoduleTT=LLTermin(* convert into {!LLTerm.t} *)letctx=TT.Conv.create()inleta=List.map(TT.Conv.of_termctx)ainletb=TT.Conv.of_termctxbin(* prove [a ∧ -b ⇒ ⊥] *)letres,final_state=LLProver.proveabinUtil.debugf~section5"(@[proof-stats@ %a@])"(funk->kLLProver.pp_statsfinal_state);(* print state, maybe *)beginmatchdot_prefixwith|None->()|Someprefix->letp_id=CCRef.incr_then_getn_proofinletfile=Printf.sprintf"%s_%d.dot"prefixp_idinUtil.debugf~section2"print proof %d@ into `%s`"(funk->kp_idfile);CCIO.with_outfile(funoc->letout=Format.formatter_of_out_channelocinFmt.fprintfout"%a@."LLProver.pp_dotfinal_state);end;conv_resresletcheck_step_?dot_prefix(p:proof):check_step_res=letconcl=P.conclpinUtil.incr_statstat_check;beginmatchP.steppwith|P.Goal|P.Assert|P.By_def_|P.Define_->CS_checkR_ok|P.Negated_goalp'->(* [p'] should prove [not concl] *)CS_check(prove~dot_prefix[P.conclp'](F.not_concl))|P.Trivial->CS_skip`Other(* axiom of the theory *)|P.Instantiate{tags;_}whennot(LLProver.can_checktags)->CS_skip`Tags|P.Instantiate{form=p';inst;_}->(* re-instantiate and check we get the same thing *)letp'_inst=instantiate(LLProof.conclp')instinletvars,body_concl=open_forallconclin(* now remove free variables by using fresh constants *)letsubst=vars|>List.mapi(funiv->v,T.const~ty:(Var.tyv)(ID.makef"sk_%d"i))|>Var.Subst.of_listinCS_check(prove~dot_prefix[T.Subst.evalsubstp'_inst](T.Subst.evalsubstbody_concl))|P.Esa(_,_)->CS_skip`ESA(* TODO *)|P.Inference{parents;tags;intros;_}->ifLLProver.can_checktagsthen((* within the fragment of {!Tab.prove} *)letall_premises=List.mapconcl_of_parentparentsandconcl=instantiateconclintrosinCS_check(prove~dot_prefixall_premisesconcl))elseCS_skip`Tagsendletcheck_step?dot_prefixp=ZProf.with_profprof_check(check_step_?dot_prefix)pletcheck?dot_prefix?(before_check=fun_->())?(on_check=fun__->())(p:proof):res*stats=lettbl=P.Tbl.create64inletstats=ref{n_ok=0;n_fail=0;n_skip_esa=0;n_skip_tags=0;n_skip_trivial=0;n_skip=0;}inletupd_statsf=stats:=f!statsinletreccheck(p:proof):unit=ifnot(P.Tbl.memtblp)then(before_checkp;Util.debugf~section3"(@[@{<Yellow>start_checking_proof@}@ %a@])"(funk->kP.ppp);letres=check_step?dot_prefixpinP.Tbl.addtblpres;Util.debugf~section3"(@[<hv>@{<Yellow>done_checking_proof@}@ :of %a@ :res %a@])"(funk->kP.ppppp_csrres);on_checkpres;beginmatchreswith|CS_checkR_ok->P.set_check_respP.R_ok;upd_stats(funs->{swithn_ok=s.n_ok+1})|CS_checkR_fail->P.set_check_respP.R_fail;upd_stats(funs->{swithn_fail=s.n_fail+1})|CS_skipr->P.set_check_respP.R_skip;upd_stats(funs->{swithn_skip=s.n_skip+1;n_skip_esa=ifr=`ESAthens.n_skip_esa+1elses.n_skip_esa;n_skip_tags=ifr=`Tagsthens.n_skip_tags+1elses.n_skip_tags;n_skip_trivial=ifr=`Trivialthens.n_skip_trivial+1elses.n_skip_trivial;})end;(* now check premises *)List.itercheck(P.premisesp));incheckp;if!stats.n_fail=0thenR_ok,!statselseR_fail,!stats