src/HOL/Tools/metis_tools.ML
changeset 32091 30e2ffbba718
parent 32010 cb1a1c94b4cd
child 32262 73cd8f74cf2a
equal deleted inserted replaced
32090:39acf19e9f3a 32091:30e2ffbba718
   268 
   268 
   269   (*for debugging only*)
   269   (*for debugging only*)
   270   fun print_thpair (fth,th) =
   270   fun print_thpair (fth,th) =
   271     (Output.debug (fn () => "=============================================");
   271     (Output.debug (fn () => "=============================================");
   272      Output.debug (fn () => "Metis: " ^ Metis.Thm.toString fth);
   272      Output.debug (fn () => "Metis: " ^ Metis.Thm.toString fth);
   273      Output.debug (fn () => "Isabelle: " ^ Display.string_of_thm th));
   273      Output.debug (fn () => "Isabelle: " ^ Display.string_of_thm_without_context th));
   274 
   274 
   275   fun lookth thpairs (fth : Metis.Thm.thm) =
   275   fun lookth thpairs (fth : Metis.Thm.thm) =
   276     valOf (AList.lookup (uncurry Metis.Thm.equal) thpairs fth)
   276     valOf (AList.lookup (uncurry Metis.Thm.equal) thpairs fth)
   277     handle Option => error ("Failed to find a Metis theorem " ^ Metis.Thm.toString fth);
   277     handle Option => error ("Failed to find a Metis theorem " ^ Metis.Thm.toString fth);
   278 
   278 
   308               let val v = find_var x
   308               let val v = find_var x
   309                   val t = fol_term_to_hol_RAW ctxt y (*we call infer_types below*)
   309                   val t = fol_term_to_hol_RAW ctxt y (*we call infer_types below*)
   310               in  SOME (cterm_of thy (Var v), t)  end
   310               in  SOME (cterm_of thy (Var v), t)  end
   311               handle Option =>
   311               handle Option =>
   312                   (Output.debug (fn() => "List.find failed for the variable " ^ x ^
   312                   (Output.debug (fn() => "List.find failed for the variable " ^ x ^
   313                                          " in " ^ Display.string_of_thm i_th);
   313                                          " in " ^ Display.string_of_thm ctxt i_th);
   314                    NONE)
   314                    NONE)
   315         fun remove_typeinst (a, t) =
   315         fun remove_typeinst (a, t) =
   316               case Recon.strip_prefix ResClause.schematic_var_prefix a of
   316               case Recon.strip_prefix ResClause.schematic_var_prefix a of
   317                   SOME b => SOME (b, t)
   317                   SOME b => SOME (b, t)
   318                 | NONE   => case Recon.strip_prefix ResClause.tvar_prefix a of
   318                 | NONE   => case Recon.strip_prefix ResClause.tvar_prefix a of
   319                   SOME _ => NONE          (*type instantiations are forbidden!*)
   319                   SOME _ => NONE          (*type instantiations are forbidden!*)
   320                 | NONE   => SOME (a,t)    (*internal Metis var?*)
   320                 | NONE   => SOME (a,t)    (*internal Metis var?*)
   321         val _ = Output.debug (fn () => "  isa th: " ^ Display.string_of_thm i_th)
   321         val _ = Output.debug (fn () => "  isa th: " ^ Display.string_of_thm ctxt i_th)
   322         val substs = List.mapPartial remove_typeinst (Metis.Subst.toList fsubst)
   322         val substs = List.mapPartial remove_typeinst (Metis.Subst.toList fsubst)
   323         val (vars,rawtms) = ListPair.unzip (List.mapPartial subst_translation substs)
   323         val (vars,rawtms) = ListPair.unzip (List.mapPartial subst_translation substs)
   324         val tms = infer_types ctxt rawtms;
   324         val tms = infer_types ctxt rawtms;
   325         val ctm_of = cterm_incr_types thy (1 + Thm.maxidx_of i_th)
   325         val ctm_of = cterm_incr_types thy (1 + Thm.maxidx_of i_th)
   326         val substs' = ListPair.zip (vars, map ctm_of tms)
   326         val substs' = ListPair.zip (vars, map ctm_of tms)
   348 
   348 
   349   fun resolve_inf ctxt thpairs atm th1 th2 =
   349   fun resolve_inf ctxt thpairs atm th1 th2 =
   350     let
   350     let
   351       val thy = ProofContext.theory_of ctxt
   351       val thy = ProofContext.theory_of ctxt
   352       val i_th1 = lookth thpairs th1 and i_th2 = lookth thpairs th2
   352       val i_th1 = lookth thpairs th1 and i_th2 = lookth thpairs th2
   353       val _ = Output.debug (fn () => "  isa th1 (pos): " ^ Display.string_of_thm i_th1)
   353       val _ = Output.debug (fn () => "  isa th1 (pos): " ^ Display.string_of_thm ctxt i_th1)
   354       val _ = Output.debug (fn () => "  isa th2 (neg): " ^ Display.string_of_thm i_th2)
   354       val _ = Output.debug (fn () => "  isa th2 (neg): " ^ Display.string_of_thm ctxt i_th2)
   355     in
   355     in
   356       if is_TrueI i_th1 then i_th2 (*Trivial cases where one operand is type info*)
   356       if is_TrueI i_th1 then i_th2 (*Trivial cases where one operand is type info*)
   357       else if is_TrueI i_th2 then i_th1
   357       else if is_TrueI i_th2 then i_th1
   358       else
   358       else
   359         let
   359         let
   426         val _ = Output.debug (fn () => "abstraction: " ^ Syntax.string_of_term ctxt tm_abs)
   426         val _ = Output.debug (fn () => "abstraction: " ^ Syntax.string_of_term ctxt tm_abs)
   427         val _ = Output.debug (fn () => "i_tm: " ^ Syntax.string_of_term ctxt i_tm)
   427         val _ = Output.debug (fn () => "i_tm: " ^ Syntax.string_of_term ctxt i_tm)
   428         val _ = Output.debug (fn () => "located term: " ^ Syntax.string_of_term ctxt tm_subst)
   428         val _ = Output.debug (fn () => "located term: " ^ Syntax.string_of_term ctxt tm_subst)
   429         val imax = maxidx_of_term (i_tm $ tm_abs $ tm_subst)  (*ill typed but gives right max*)
   429         val imax = maxidx_of_term (i_tm $ tm_abs $ tm_subst)  (*ill typed but gives right max*)
   430         val subst' = incr_indexes (imax+1) (if pos then subst_em else ssubst_em)
   430         val subst' = incr_indexes (imax+1) (if pos then subst_em else ssubst_em)
   431         val _ = Output.debug (fn () => "subst' " ^ Display.string_of_thm subst')
   431         val _ = Output.debug (fn () => "subst' " ^ Display.string_of_thm ctxt subst')
   432         val eq_terms = map (pairself (cterm_of thy))
   432         val eq_terms = map (pairself (cterm_of thy))
   433                            (ListPair.zip (OldTerm.term_vars (prop_of subst'), [tm_abs, tm_subst, i_tm]))
   433                            (ListPair.zip (OldTerm.term_vars (prop_of subst'), [tm_abs, tm_subst, i_tm]))
   434     in  cterm_instantiate eq_terms subst'  end;
   434     in  cterm_instantiate eq_terms subst'  end;
   435 
   435 
   436   val factor = Seq.hd o distinct_subgoals_tac;
   436   val factor = Seq.hd o distinct_subgoals_tac;
   454     | translate isFO ctxt thpairs ((fol_th, inf) :: infpairs) =
   454     | translate isFO ctxt thpairs ((fol_th, inf) :: infpairs) =
   455         let val _ = Output.debug (fn () => "=============================================")
   455         let val _ = Output.debug (fn () => "=============================================")
   456             val _ = Output.debug (fn () => "METIS THM: " ^ Metis.Thm.toString fol_th)
   456             val _ = Output.debug (fn () => "METIS THM: " ^ Metis.Thm.toString fol_th)
   457             val _ = Output.debug (fn () => "INFERENCE: " ^ Metis.Proof.inferenceToString inf)
   457             val _ = Output.debug (fn () => "INFERENCE: " ^ Metis.Proof.inferenceToString inf)
   458             val th = Meson.flexflex_first_order (step ctxt isFO thpairs (fol_th, inf))
   458             val th = Meson.flexflex_first_order (step ctxt isFO thpairs (fol_th, inf))
   459             val _ = Output.debug (fn () => "ISABELLE THM: " ^ Display.string_of_thm th)
   459             val _ = Output.debug (fn () => "ISABELLE THM: " ^ Display.string_of_thm ctxt th)
   460             val _ = Output.debug (fn () => "=============================================")
   460             val _ = Output.debug (fn () => "=============================================")
   461             val n_metis_lits = length (filter real_literal (Metis.LiteralSet.toList (Metis.Thm.clause fol_th)))
   461             val n_metis_lits = length (filter real_literal (Metis.LiteralSet.toList (Metis.Thm.clause fol_th)))
   462         in
   462         in
   463             if nprems_of th = n_metis_lits then ()
   463             if nprems_of th = n_metis_lits then ()
   464             else error "Metis: proof reconstruction has gone wrong";
   464             else error "Metis: proof reconstruction has gone wrong";
   574   fun FOL_SOLVE mode ctxt cls ths0 =
   574   fun FOL_SOLVE mode ctxt cls ths0 =
   575     let val thy = ProofContext.theory_of ctxt
   575     let val thy = ProofContext.theory_of ctxt
   576         val th_cls_pairs = map (fn th => (Thm.get_name_hint th, ResAxioms.cnf_axiom thy th)) ths0
   576         val th_cls_pairs = map (fn th => (Thm.get_name_hint th, ResAxioms.cnf_axiom thy th)) ths0
   577         val ths = List.concat (map #2 th_cls_pairs)
   577         val ths = List.concat (map #2 th_cls_pairs)
   578         val _ = Output.debug (fn () => "FOL_SOLVE: CONJECTURE CLAUSES")
   578         val _ = Output.debug (fn () => "FOL_SOLVE: CONJECTURE CLAUSES")
   579         val _ = app (fn th => Output.debug (fn () => Display.string_of_thm th)) cls
   579         val _ = app (fn th => Output.debug (fn () => Display.string_of_thm ctxt th)) cls
   580         val _ = Output.debug (fn () => "THEOREM CLAUSES")
   580         val _ = Output.debug (fn () => "THEOREM CLAUSES")
   581         val _ = app (fn th => Output.debug (fn () => Display.string_of_thm th)) ths
   581         val _ = app (fn th => Output.debug (fn () => Display.string_of_thm ctxt th)) ths
   582         val {isFO,axioms,tfrees} = build_map mode ctxt cls ths
   582         val {isFO,axioms,tfrees} = build_map mode ctxt cls ths
   583         val _ = if null tfrees then ()
   583         val _ = if null tfrees then ()
   584                 else (Output.debug (fn () => "TFREE CLAUSES");
   584                 else (Output.debug (fn () => "TFREE CLAUSES");
   585                       app (fn tf => Output.debug (fn _ => ResClause.tptp_of_typeLit true tf)) tfrees)
   585                       app (fn tf => Output.debug (fn _ => ResClause.tptp_of_typeLit true tf)) tfrees)
   586         val _ = Output.debug (fn () => "CLAUSES GIVEN TO METIS")
   586         val _ = Output.debug (fn () => "CLAUSES GIVEN TO METIS")
   602                                (*add constraints arising from converting goal to clause form*)
   602                                (*add constraints arising from converting goal to clause form*)
   603                   val proof = Metis.Proof.proof mth
   603                   val proof = Metis.Proof.proof mth
   604                   val result = translate isFO ctxt' axioms proof
   604                   val result = translate isFO ctxt' axioms proof
   605                   and used = List.mapPartial (used_axioms axioms) proof
   605                   and used = List.mapPartial (used_axioms axioms) proof
   606                   val _ = Output.debug (fn () => "METIS COMPLETED...clauses actually used:")
   606                   val _ = Output.debug (fn () => "METIS COMPLETED...clauses actually used:")
   607 	          val _ = app (fn th => Output.debug (fn () => Display.string_of_thm th)) used
   607 	          val _ = app (fn th => Output.debug (fn () => Display.string_of_thm ctxt th)) used
   608 	          val unused = filter (fn (a,cls) => not (common_thm used cls)) th_cls_pairs
   608 	          val unused = filter (fn (a,cls) => not (common_thm used cls)) th_cls_pairs
   609               in
   609               in
   610                   if null unused then ()
   610                   if null unused then ()
   611                   else warning ("Metis: unused theorems " ^ commas_quote (map #1 unused));
   611                   else warning ("Metis: unused theorems " ^ commas_quote (map #1 unused));
   612                   case result of
   612                   case result of
   613                       (_,ith)::_ => 
   613                       (_,ith)::_ => 
   614                           (Output.debug (fn () => "success: " ^ Display.string_of_thm ith); 
   614                           (Output.debug (fn () => "success: " ^ Display.string_of_thm ctxt ith); 
   615                            [ith])
   615                            [ith])
   616                     | _ => (Output.debug (fn () => "Metis: no result"); 
   616                     | _ => (Output.debug (fn () => "Metis: no result"); 
   617                             [])
   617                             [])
   618               end
   618               end
   619           | Metis.Resolution.Satisfiable _ => 
   619           | Metis.Resolution.Satisfiable _ => 
   621 	       [])
   621 	       [])
   622     end;
   622     end;
   623 
   623 
   624   fun metis_general_tac mode ctxt ths i st0 =
   624   fun metis_general_tac mode ctxt ths i st0 =
   625     let val _ = Output.debug (fn () =>
   625     let val _ = Output.debug (fn () =>
   626           "Metis called with theorems " ^ cat_lines (map Display.string_of_thm ths))
   626           "Metis called with theorems " ^ cat_lines (map (Display.string_of_thm ctxt) ths))
   627     in
   627     in
   628        if exists_type ResAxioms.type_has_empty_sort (prop_of st0)  
   628        if exists_type ResAxioms.type_has_empty_sort (prop_of st0)  
   629        then (warning "Proof state contains the empty sort"; Seq.empty)
   629        then (warning "Proof state contains the empty sort"; Seq.empty)
   630        else 
   630        else 
   631 	 (Meson.MESON ResAxioms.neg_clausify (fn cls => resolve_tac (FOL_SOLVE mode ctxt cls ths) 1) i
   631 	 (Meson.MESON ResAxioms.neg_clausify (fn cls => resolve_tac (FOL_SOLVE mode ctxt cls ths) 1) i