src/HOL/Tools/res_axioms.ML
changeset 24669 4579eac2c997
parent 24632 779fc4fcbf8b
child 24742 73b8b42a36b6
equal deleted inserted replaced
24668:4058b7b0925c 24669:4579eac2c997
     5 Transformation of axiom rules (elim/intro/etc) into CNF forms.
     5 Transformation of axiom rules (elim/intro/etc) into CNF forms.
     6 *)
     6 *)
     7 
     7 
     8 signature RES_AXIOMS =
     8 signature RES_AXIOMS =
     9 sig
     9 sig
    10   val cnf_axiom : string * thm -> thm list
    10   val cnf_axiom: thm -> thm list
    11   val cnf_name : string -> thm list
    11   val meta_cnf_axiom: thm -> thm list
    12   val meta_cnf_axiom : thm -> thm list
    12   val pairname: thm -> string * thm
    13   val pairname : thm -> string * thm
    13   val skolem_thm: thm -> thm list
    14   val skolem_thm : thm -> thm list
    14   val cnf_rules_pairs: (string * thm) list -> (thm * (string * int)) list
    15   val cnf_rules_pairs : (string * thm) list -> (thm * (string * int)) list
    15   val cnf_rules_of_ths: thm list -> thm list
    16   val meson_method_setup : theory -> theory
    16   val neg_clausify: thm list -> thm list
    17   val setup : theory -> theory
    17   val expand_defs_tac: thm -> tactic
    18   val clause_cache_setup : theory -> theory
       
    19   val assume_abstract_list: string -> thm list -> thm list
    18   val assume_abstract_list: string -> thm list -> thm list
    20   val neg_conjecture_clauses: thm -> int -> thm list * (string * typ) list
    19   val neg_conjecture_clauses: thm -> int -> thm list * (string * typ) list
    21   val claset_rules_of: Proof.context -> (string * thm) list   (*FIXME DELETE*)
    20   val claset_rules_of: Proof.context -> (string * thm) list   (*FIXME DELETE*)
    22   val simpset_rules_of: Proof.context -> (string * thm) list  (*FIXME DELETE*)
    21   val simpset_rules_of: Proof.context -> (string * thm) list  (*FIXME DELETE*)
    23   val atpset_rules_of: Proof.context -> (string * thm) list
    22   val atpset_rules_of: Proof.context -> (string * thm) list
       
    23   val meson_method_setup: theory -> theory
       
    24   val clause_cache_setup: theory -> theory
       
    25   val setup: theory -> theory
    24 end;
    26 end;
    25 
    27 
    26 structure ResAxioms =
    28 structure ResAxioms: RES_AXIOMS =
    27 struct
    29 struct
    28 
    30 
    29 (*For running the comparison between combinators and abstractions.
    31 (*For running the comparison between combinators and abstractions.
    30   CANNOT be a ref, as the setting is used while Isabelle is built.
    32   CANNOT be a ref, as the setting is used while Isabelle is built.
    31   Currently TRUE: the combinator code cannot be used with proof reconstruction
    33   Currently TRUE: the combinator code cannot be used with proof reconstruction
    47 (*Populate the abstraction cache with common combinators.*)
    49 (*Populate the abstraction cache with common combinators.*)
    48 fun seed th net =
    50 fun seed th net =
    49   let val (_,ct) = Thm.dest_abs NONE (Thm.rhs_of th)
    51   let val (_,ct) = Thm.dest_abs NONE (Thm.rhs_of th)
    50       val t = Logic.legacy_varify (term_of ct)
    52       val t = Logic.legacy_varify (term_of ct)
    51   in  Net.insert_term Thm.eq_thm (t, th) net end;
    53   in  Net.insert_term Thm.eq_thm (t, th) net end;
    52   
    54 
    53 val abstraction_cache = ref 
    55 val abstraction_cache = ref
    54       (seed (thm"ATP_Linkup.I_simp") 
    56       (seed (thm"ATP_Linkup.I_simp")
    55        (seed (thm"ATP_Linkup.B_simp") 
    57        (seed (thm"ATP_Linkup.B_simp")
    56 	(seed (thm"ATP_Linkup.K_simp") Net.empty)));
    58         (seed (thm"ATP_Linkup.K_simp") Net.empty)));
    57 
    59 
    58 
    60 
    59 (**** Transformation of Elimination Rules into First-Order Formulas****)
    61 (**** Transformation of Elimination Rules into First-Order Formulas****)
    60 
    62 
    61 val cfalse = cterm_of HOL.thy HOLogic.false_const;
    63 val cfalse = cterm_of HOL.thy HOLogic.false_const;
    64 (*Converts an elim-rule into an equivalent theorem that does not have the
    66 (*Converts an elim-rule into an equivalent theorem that does not have the
    65   predicate variable.  Leaves other theorems unchanged.  We simply instantiate the
    67   predicate variable.  Leaves other theorems unchanged.  We simply instantiate the
    66   conclusion variable to False.*)
    68   conclusion variable to False.*)
    67 fun transform_elim th =
    69 fun transform_elim th =
    68   case concl_of th of    (*conclusion variable*)
    70   case concl_of th of    (*conclusion variable*)
    69        Const("Trueprop",_) $ (v as Var(_,Type("bool",[]))) => 
    71        Const("Trueprop",_) $ (v as Var(_,Type("bool",[]))) =>
    70            Thm.instantiate ([], [(cterm_of HOL.thy v, cfalse)]) th
    72            Thm.instantiate ([], [(cterm_of HOL.thy v, cfalse)]) th
    71     | v as Var(_, Type("prop",[])) => 
    73     | v as Var(_, Type("prop",[])) =>
    72            Thm.instantiate ([], [(cterm_of HOL.thy v, ctp_false)]) th
    74            Thm.instantiate ([], [(cterm_of HOL.thy v, ctp_false)]) th
    73     | _ => th;
    75     | _ => th;
    74 
    76 
    75 (**** Transformation of Clasets and Simpsets into First-Order Axioms ****)
    77 (**** Transformation of Clasets and Simpsets into First-Order Axioms ****)
    76 
    78 
   165 end;
   167 end;
   166 
   168 
   167 (*Removes the lambdas from an equation of the form t = (%x. u).  A non-negative n,
   169 (*Removes the lambdas from an equation of the form t = (%x. u).  A non-negative n,
   168   serves as an upper bound on how many to remove.*)
   170   serves as an upper bound on how many to remove.*)
   169 fun strip_lambdas 0 th = th
   171 fun strip_lambdas 0 th = th
   170   | strip_lambdas n th = 
   172   | strip_lambdas n th =
   171       case prop_of th of
   173       case prop_of th of
   172 	  _ $ (Const ("op =", _) $ _ $ Abs (x,_,_)) =>
   174           _ $ (Const ("op =", _) $ _ $ Abs (x,_,_)) =>
   173 	      strip_lambdas (n-1) (freeze_thm (th RS xfun_cong x))
   175               strip_lambdas (n-1) (freeze_thm (th RS xfun_cong x))
   174 	| _ => th;
   176         | _ => th;
   175 
   177 
   176 (*Convert meta- to object-equality. Fails for theorems like split_comp_eq,
   178 (*Convert meta- to object-equality. Fails for theorems like split_comp_eq,
   177   where some types have the empty sort.*)
   179   where some types have the empty sort.*)
   178 val meta_eq_to_obj_eq = thm "meta_eq_to_obj_eq";
   180 val meta_eq_to_obj_eq = thm "meta_eq_to_obj_eq";
   179 fun mk_object_eq th = th RS meta_eq_to_obj_eq
   181 fun mk_object_eq th = th RS meta_eq_to_obj_eq
   200 
   202 
   201 fun eq_absdef (th1, th2) =
   203 fun eq_absdef (th1, th2) =
   202     Context.joinable (theory_of_thm th1, theory_of_thm th2)  andalso
   204     Context.joinable (theory_of_thm th1, theory_of_thm th2)  andalso
   203     rhs_of th1 aconv rhs_of th2;
   205     rhs_of th1 aconv rhs_of th2;
   204 
   206 
   205 fun lambda_free (Abs _) = false
   207 val lambda_free = not o Term.has_abs;
   206   | lambda_free (t $ u) = lambda_free t andalso lambda_free u
   208 
   207   | lambda_free _ = true;
   209 val monomorphic = not o Term.exists_type (Term.exists_subtype Term.is_TVar);
   208 
       
   209 fun monomorphic t =
       
   210   Term.fold_types (Term.fold_atyps (fn TVar _ => K false | _ => I)) t true;
       
   211 
   210 
   212 fun dest_abs_list ct =
   211 fun dest_abs_list ct =
   213   let val (cv,ct') = Thm.dest_abs NONE ct
   212   let val (cv,ct') = Thm.dest_abs NONE ct
   214       val (cvs,cu) = dest_abs_list ct'
   213       val (cvs,cu) = dest_abs_list ct'
   215   in (cv::cvs, cu) end
   214   in (cv::cvs, cu) end
   216   handle CTERM _ => ([],ct);
   215   handle CTERM _ => ([],ct);
   217 
   216 
   218 fun lambda_list [] u = u
       
   219   | lambda_list (v::vs) u = lambda v (lambda_list vs u);
       
   220 
       
   221 fun abstract_rule_list [] [] th = th
   217 fun abstract_rule_list [] [] th = th
   222   | abstract_rule_list (v::vs) (ct::cts) th = abstract_rule v ct (abstract_rule_list vs cts th)
   218   | abstract_rule_list (v::vs) (ct::cts) th = abstract_rule v ct (abstract_rule_list vs cts th)
   223   | abstract_rule_list _ _ th = raise THM ("abstract_rule_list", 0, [th]);
   219   | abstract_rule_list _ _ th = raise THM ("abstract_rule_list", 0, [th]);
   224 
   220 
   225 
   221 
   226 val Envir.Envir {asol = tenv0, iTs = tyenv0, ...} = Envir.empty 0
   222 val Envir.Envir {asol = tenv0, iTs = tyenv0, ...} = Envir.empty 0
   227 
   223 
   228 (*Does an existing abstraction definition have an RHS that matches the one we need now?
   224 (*Does an existing abstraction definition have an RHS that matches the one we need now?
   229   thy is the current theory, which must extend that of theorem th.*)
   225   thy is the current theory, which must extend that of theorem th.*)
   230 fun match_rhs thy t th =
   226 fun match_rhs thy t th =
   231   let val _ = Output.debug (fn()=> "match_rhs: " ^ string_of_cterm (cterm_of thy t) ^ 
   227   let val _ = Output.debug (fn()=> "match_rhs: " ^ string_of_cterm (cterm_of thy t) ^
   232                                    " against\n" ^ string_of_thm th);
   228                                    " against\n" ^ string_of_thm th);
   233       val (tyenv,tenv) = Pattern.first_order_match thy (rhs_of th, t) (tyenv0,tenv0)
   229       val (tyenv,tenv) = Pattern.first_order_match thy (rhs_of th, t) (tyenv0,tenv0)
   234       val term_insts = map Meson.term_pair_of (Vartab.dest tenv)
   230       val term_insts = map Meson.term_pair_of (Vartab.dest tenv)
   235       val ct_pairs = if subthy (theory_of_thm th, thy) andalso 
   231       val ct_pairs = if subthy (theory_of_thm th, thy) andalso
   236                         forall lambda_free (map #2 term_insts) 
   232                         forall lambda_free (map #2 term_insts)
   237                      then map (pairself (cterm_of thy)) term_insts
   233                      then map (pairself (cterm_of thy)) term_insts
   238                      else raise Pattern.MATCH (*Cannot allow lambdas in the instantiation*)
   234                      else raise Pattern.MATCH (*Cannot allow lambdas in the instantiation*)
   239       fun ctyp2 (ixn, (S, T)) = (ctyp_of thy (TVar (ixn, S)), ctyp_of thy T)
   235       fun ctyp2 (ixn, (S, T)) = (ctyp_of thy (TVar (ixn, S)), ctyp_of thy T)
   240       val th' = cterm_instantiate ct_pairs th
   236       val th' = cterm_instantiate ct_pairs th
   241   in  SOME (th, instantiate (map ctyp2 (Vartab.dest tyenv), []) th')  end
   237   in  SOME (th, instantiate (map ctyp2 (Vartab.dest tyenv), []) th')  end
   257                 val _ = Output.debug (fn()=>"Nested lambda: " ^ string_of_cterm cta);
   253                 val _ = Output.debug (fn()=>"Nested lambda: " ^ string_of_cterm cta);
   258                 val (u'_th,defs) = abstract thy cta
   254                 val (u'_th,defs) = abstract thy cta
   259                 val _ = Output.debug (fn()=>"Returned " ^ string_of_thm u'_th);
   255                 val _ = Output.debug (fn()=>"Returned " ^ string_of_thm u'_th);
   260                 val cu' = Thm.rhs_of u'_th
   256                 val cu' = Thm.rhs_of u'_th
   261                 val u' = term_of cu'
   257                 val u' = term_of cu'
   262                 val abs_v_u = lambda_list (map term_of cvs) u'
   258                 val abs_v_u = fold_rev (lambda o term_of) cvs u'
   263                 (*get the formal parameters: ALL variables free in the term*)
   259                 (*get the formal parameters: ALL variables free in the term*)
   264                 val args = term_frees abs_v_u
   260                 val args = term_frees abs_v_u
   265                 val _ = Output.debug (fn()=>Int.toString (length args) ^ " arguments");
   261                 val _ = Output.debug (fn()=>Int.toString (length args) ^ " arguments");
   266                 val rhs = list_abs_free (map dest_Free args, abs_v_u)
   262                 val rhs = list_abs_free (map dest_Free args, abs_v_u)
   267                       (*Forms a lambda-abstraction over the formal parameters*)
   263                       (*Forms a lambda-abstraction over the formal parameters*)
   268                 val _ = Output.debug (fn()=>"Looking up " ^ string_of_cterm cu');
   264                 val _ = Output.debug (fn()=>"Looking up " ^ string_of_cterm cu');
   269                 val thy = theory_of_thm u'_th
   265                 val thy = theory_of_thm u'_th
   270                 val (ax,ax',thy) =
   266                 val (ax,ax',thy) =
   271                  case List.mapPartial (match_rhs thy abs_v_u) 
   267                  case List.mapPartial (match_rhs thy abs_v_u)
   272                          (Net.match_term (!abstraction_cache) u') of
   268                          (Net.match_term (!abstraction_cache) u') of
   273                      (ax,ax')::_ => 
   269                      (ax,ax')::_ =>
   274                        (Output.debug (fn()=>"Re-using axiom " ^ string_of_thm ax);
   270                        (Output.debug (fn()=>"Re-using axiom " ^ string_of_thm ax);
   275                         (ax,ax',thy))
   271                         (ax,ax',thy))
   276                    | [] =>
   272                    | [] =>
   277                       let val _ = Output.debug (fn()=>"Lookup was empty");
   273                       let val _ = Output.debug (fn()=>"Lookup was empty");
   278                           val Ts = map type_of args
   274                           val Ts = map type_of args
   289                                      |> mk_object_eq |> strip_lambdas (length args)
   285                                      |> mk_object_eq |> strip_lambdas (length args)
   290                                      |> mk_meta_eq |> Meson.generalize
   286                                      |> mk_meta_eq |> Meson.generalize
   291                           val (_,ax') = Option.valOf (match_rhs thy abs_v_u ax)
   287                           val (_,ax') = Option.valOf (match_rhs thy abs_v_u ax)
   292                           val _ = Output.debug (fn()=> "Declaring: " ^ string_of_thm ax ^ "\n" ^
   288                           val _ = Output.debug (fn()=> "Declaring: " ^ string_of_thm ax ^ "\n" ^
   293                                                        "Instance: " ^ string_of_thm ax');
   289                                                        "Instance: " ^ string_of_thm ax');
   294                           val _ = abstraction_cache := Net.insert_term eq_absdef 
   290                           val _ = abstraction_cache := Net.insert_term eq_absdef
   295                                             ((Logic.varify u'), ax) (!abstraction_cache)
   291                                             ((Logic.varify u'), ax) (!abstraction_cache)
   296                             handle Net.INSERT =>
   292                             handle Net.INSERT =>
   297                               raise THM ("declare_absfuns: INSERT", 0, [th,u'_th,ax])
   293                               raise THM ("declare_absfuns: INSERT", 0, [th,u'_th,ax])
   298                        in  (ax,ax',thy)  end
   294                        in  (ax,ax',thy)  end
   299             in Output.debug (fn()=>"Lookup result: " ^ string_of_thm ax');
   295             in Output.debug (fn()=>"Lookup result: " ^ string_of_thm ax');
   330                 val (vs,Tvs) = ListPair.unzip (map (dest_Free o term_of) cvs)
   326                 val (vs,Tvs) = ListPair.unzip (map (dest_Free o term_of) cvs)
   331                 val (u'_th,defs) = abstract cta
   327                 val (u'_th,defs) = abstract cta
   332                 val cu' = Thm.rhs_of u'_th
   328                 val cu' = Thm.rhs_of u'_th
   333                 val u' = term_of cu'
   329                 val u' = term_of cu'
   334                 (*Could use Thm.cabs instead of lambda to work at level of cterms*)
   330                 (*Could use Thm.cabs instead of lambda to work at level of cterms*)
   335                 val abs_v_u = lambda_list (map term_of cvs) (term_of cu')
   331                 val abs_v_u = fold_rev (lambda o term_of) cvs (term_of cu')
   336                 (*get the formal parameters: free variables not present in the defs
   332                 (*get the formal parameters: free variables not present in the defs
   337                   (to avoid taking abstraction function names as parameters) *)
   333                   (to avoid taking abstraction function names as parameters) *)
   338                 val args = filter (valid_name defs) (term_frees abs_v_u)
   334                 val args = filter (valid_name defs) (term_frees abs_v_u)
   339                 val crhs = list_cabs (map cterm args, cterm abs_v_u)
   335                 val crhs = list_cabs (map cterm args, cterm abs_v_u)
   340                       (*Forms a lambda-abstraction over the formal parameters*)
   336                       (*Forms a lambda-abstraction over the formal parameters*)
   341                 val rhs = term_of crhs
   337                 val rhs = term_of crhs
   342                 val (ax,ax') =
   338                 val (ax,ax') =
   343                  case List.mapPartial (match_rhs thy abs_v_u) 
   339                  case List.mapPartial (match_rhs thy abs_v_u)
   344                         (Net.match_term (!abstraction_cache) u') of
   340                         (Net.match_term (!abstraction_cache) u') of
   345                      (ax,ax')::_ => 
   341                      (ax,ax')::_ =>
   346                        (Output.debug (fn()=>"Re-using axiom " ^ string_of_thm ax);
   342                        (Output.debug (fn()=>"Re-using axiom " ^ string_of_thm ax);
   347                         (ax,ax'))
   343                         (ax,ax'))
   348                    | [] =>
   344                    | [] =>
   349                       let val Ts = map type_of args
   345                       let val Ts = map type_of args
   350                           val const_ty = Ts ---> (Tvs ---> typ_of (ctyp_of_term cu'))
   346                           val const_ty = Ts ---> (Tvs ---> typ_of (ctyp_of_term cu'))
   414 
   410 
   415 (*Generate Skolem functions for a theorem supplied in nnf*)
   411 (*Generate Skolem functions for a theorem supplied in nnf*)
   416 fun skolem_of_nnf s th =
   412 fun skolem_of_nnf s th =
   417   map (skolem_of_def o assume o (cterm_of (theory_of_thm th))) (assume_skofuns s th);
   413   map (skolem_of_def o assume o (cterm_of (theory_of_thm th))) (assume_skofuns s th);
   418 
   414 
   419 fun assert_lambda_free ths msg = 
   415 fun assert_lambda_free ths msg =
   420   case filter (not o lambda_free o prop_of) ths of
   416   case filter (not o lambda_free o prop_of) ths of
   421       [] => ()
   417       [] => ()
   422     | ths' => error (msg ^ "\n" ^ cat_lines (map string_of_thm ths'));
   418     | ths' => error (msg ^ "\n" ^ cat_lines (map string_of_thm ths'));
   423 
   419 
   424 fun assume_abstract s th =
   420 fun assume_abstract s th =
   449 
   445 
   450 (*Keep the full complexity of the original name*)
   446 (*Keep the full complexity of the original name*)
   451 fun flatten_name s = space_implode "_X" (NameSpace.explode s);
   447 fun flatten_name s = space_implode "_X" (NameSpace.explode s);
   452 
   448 
   453 fun fake_name th =
   449 fun fake_name th =
   454   if PureThy.has_name_hint th then flatten_name (PureThy.get_name_hint th) 
   450   if PureThy.has_name_hint th then flatten_name (PureThy.get_name_hint th)
   455   else gensym "unknown_thm_";
   451   else gensym "unknown_thm_";
   456 
   452 
   457 (*Skolemize a named theorem, with Skolem functions as additional premises.*)
   453 (*Skolemize a named theorem, with Skolem functions as additional premises.*)
   458 fun skolem_thm th =
   454 fun skolem_thm th =
   459   let val nnfth = to_nnf th and s = fake_name th
   455   let val nnfth = to_nnf th and s = fake_name th
   481   fun copy (ref tab) : T = ref tab;
   477   fun copy (ref tab) : T = ref tab;
   482   val extend = copy;
   478   val extend = copy;
   483   fun merge _ (ref tab1, ref tab2) : T = ref (Thmtab.merge (K true) (tab1, tab2));
   479   fun merge _ (ref tab1, ref tab2) : T = ref (Thmtab.merge (K true) (tab1, tab2));
   484 );
   480 );
   485 
   481 
   486 (*The cache prevents repeated clausification of a theorem, and also repeated declaration of 
   482 (*The cache prevents repeated clausification of a theorem, and also repeated declaration of
   487   Skolem functions. The global one holds theorems proved prior to this point. Theory data
   483   Skolem functions. The global one holds theorems proved prior to this point. Theory data
   488   holds the remaining ones.*)
   484   holds the remaining ones.*)
   489 val global_clause_cache = ref (Thmtab.empty : (thm list) Thmtab.table);
   485 val global_clause_cache = ref (Thmtab.empty : (thm list) Thmtab.table);
   490 
   486 
   491 (*Populate the clause cache using the supplied theorem. Return the clausal form
   487 (*Populate the clause cache using the supplied theorem. Return the clausal form
   493 fun skolem_cache_thm clause_cache th thy =
   489 fun skolem_cache_thm clause_cache th thy =
   494   case Thmtab.lookup (!clause_cache) th of
   490   case Thmtab.lookup (!clause_cache) th of
   495       NONE =>
   491       NONE =>
   496         (case skolem thy (Thm.transfer thy th) of
   492         (case skolem thy (Thm.transfer thy th) of
   497              NONE => ([th],thy)
   493              NONE => ([th],thy)
   498            | SOME (cls,thy') => 
   494            | SOME (cls,thy') =>
   499                  (if null cls 
   495                  (if null cls
   500                   then warning ("skolem_cache: empty clause set for " ^ string_of_thm th)
   496                   then warning ("skolem_cache: empty clause set for " ^ string_of_thm th)
   501                   else ();
   497                   else ();
   502                   change clause_cache (Thmtab.update (th, cls)); 
   498                   change clause_cache (Thmtab.update (th, cls));
   503                   (cls,thy')))
   499                   (cls,thy')))
   504     | SOME cls => (cls,thy);
   500     | SOME cls => (cls,thy);
   505 
   501 
   506 (*Exported function to convert Isabelle theorems into axiom clauses*)
   502 (*Exported function to convert Isabelle theorems into axiom clauses*)
   507 fun cnf_axiom th =
   503 fun cnf_axiom th =
   508   let val cache = ThmCache.get (Thm.theory_of_thm th)
   504   let val cache = ThmCache.get (Thm.theory_of_thm th)
   509                   handle ERROR _ => global_clause_cache
   505                   handle ERROR _ => global_clause_cache
   510       val in_cache = if cache = global_clause_cache then NONE else Thmtab.lookup (!cache) th
   506       val in_cache = if cache = global_clause_cache then NONE else Thmtab.lookup (!cache) th
   511   in
   507   in
   512      case in_cache of
   508      case in_cache of
   513        NONE => 
   509        NONE =>
   514 	 (case Thmtab.lookup (!global_clause_cache) th of
   510          (case Thmtab.lookup (!global_clause_cache) th of
   515 	   NONE => 
   511            NONE =>
   516 	     let val cls = map Goal.close_result (skolem_thm th)
   512              let val cls = map Goal.close_result (skolem_thm th)
   517 	     in Output.debug (fn () => Int.toString (length cls) ^ " clauses inserted into cache: " ^ 
   513              in Output.debug (fn () => Int.toString (length cls) ^ " clauses inserted into cache: " ^
   518 	                         (if PureThy.has_name_hint th then PureThy.get_name_hint th
   514                                  (if PureThy.has_name_hint th then PureThy.get_name_hint th
   519 	                          else string_of_thm th));
   515                                   else string_of_thm th));
   520 		change cache (Thmtab.update (th, cls)); cls 
   516                 change cache (Thmtab.update (th, cls)); cls
   521 	     end
   517              end
   522 	 | SOME cls => cls)
   518          | SOME cls => cls)
   523      | SOME cls => cls
   519      | SOME cls => cls
   524   end;
   520   end;
   525 
   521 
   526 fun pairname th = (PureThy.get_name_hint th, th);
   522 fun pairname th = (PureThy.get_name_hint th, th);
   527 
   523 
   579 fun skolem_cache clause_cache th thy = #2 (skolem_cache_thm clause_cache th thy);
   575 fun skolem_cache clause_cache th thy = #2 (skolem_cache_thm clause_cache th thy);
   580 
   576 
   581 (*The cache can be kept smaller by inspecting the prop of each thm. Can ignore all that are
   577 (*The cache can be kept smaller by inspecting the prop of each thm. Can ignore all that are
   582   lambda_free, but then the individual theory caches become much bigger.*)
   578   lambda_free, but then the individual theory caches become much bigger.*)
   583 
   579 
   584 fun clause_cache_setup thy = 
   580 fun clause_cache_setup thy =
   585   fold (skolem_cache global_clause_cache) (map #2 (PureThy.all_thms_of thy)) thy;
   581   fold (skolem_cache global_clause_cache) (map #2 (PureThy.all_thms_of thy)) thy;
   586 
   582 
   587 
   583 
   588 (*** meson proof methods ***)
   584 (*** meson proof methods ***)
   589 
   585 
   603 fun expand_defs_tac st0 st =
   599 fun expand_defs_tac st0 st =
   604   let val hyps0 = #hyps (rep_thm st0)
   600   let val hyps0 = #hyps (rep_thm st0)
   605       val hyps = #hyps (crep_thm st)
   601       val hyps = #hyps (crep_thm st)
   606       val newhyps = filter_out (member (op aconv) hyps0 o Thm.term_of) hyps
   602       val newhyps = filter_out (member (op aconv) hyps0 o Thm.term_of) hyps
   607       val defs = filter (is_absko o Thm.term_of) newhyps
   603       val defs = filter (is_absko o Thm.term_of) newhyps
   608       val remaining_hyps = filter_out (member (op aconv) (map Thm.term_of defs)) 
   604       val remaining_hyps = filter_out (member (op aconv) (map Thm.term_of defs))
   609                                       (map Thm.term_of hyps)
   605                                       (map Thm.term_of hyps)
   610       val fixed = term_frees (concl_of st) @
   606       val fixed = term_frees (concl_of st) @
   611                   foldl (gen_union (op aconv)) [] (map term_frees remaining_hyps)
   607                   foldl (gen_union (op aconv)) [] (map term_frees remaining_hyps)
   612   in  Output.debug (fn _ => "expand_defs_tac: " ^ string_of_thm st);
   608   in  Output.debug (fn _ => "expand_defs_tac: " ^ string_of_thm st);
   613       Output.debug (fn _ => "  st0: " ^ string_of_thm st0);
   609       Output.debug (fn _ => "  st0: " ^ string_of_thm st0);
   650   let val st = Seq.hd (neg_skolemize_tac n st0)
   646   let val st = Seq.hd (neg_skolemize_tac n st0)
   651       val (params,_,_) = strip_context (Logic.nth_prem (n, Thm.prop_of st))
   647       val (params,_,_) = strip_context (Logic.nth_prem (n, Thm.prop_of st))
   652   in (neg_clausify (Option.valOf (metahyps_thms n st)), params) end
   648   in (neg_clausify (Option.valOf (metahyps_thms n st)), params) end
   653   handle Option => raise ERROR "unable to Skolemize subgoal";
   649   handle Option => raise ERROR "unable to Skolemize subgoal";
   654 
   650 
   655 (*Conversion of a subgoal to conjecture clauses. Each clause has  
   651 (*Conversion of a subgoal to conjecture clauses. Each clause has
   656   leading !!-bound universal variables, to express generality. *)
   652   leading !!-bound universal variables, to express generality. *)
   657 val neg_clausify_tac = 
   653 val neg_clausify_tac =
   658   neg_skolemize_tac THEN' 
   654   neg_skolemize_tac THEN'
   659   SUBGOAL
   655   SUBGOAL
   660     (fn (prop,_) =>
   656     (fn (prop,_) =>
   661      let val ts = Logic.strip_assums_hyp prop
   657      let val ts = Logic.strip_assums_hyp prop
   662      in EVERY1 
   658      in EVERY1
   663 	 [METAHYPS
   659          [METAHYPS
   664 	    (fn hyps => 
   660             (fn hyps =>
   665               (Method.insert_tac
   661               (Method.insert_tac
   666                 (map forall_intr_vars (neg_clausify hyps)) 1)),
   662                 (map forall_intr_vars (neg_clausify hyps)) 1)),
   667 	  REPEAT_DETERM_N (length ts) o (etac thin_rl)]
   663           REPEAT_DETERM_N (length ts) o (etac thin_rl)]
   668      end);
   664      end);
   669 
   665 
   670 (** The Skolemization attribute **)
   666 (** The Skolemization attribute **)
   671 
   667 
   672 fun conj2_rule (th1,th2) = conjI OF [th1,th2];
   668 fun conj2_rule (th1,th2) = conjI OF [th1,th2];
   683 val setup_attrs = Attrib.add_attributes
   679 val setup_attrs = Attrib.add_attributes
   684   [("skolem", Attrib.no_args skolem_attr, "skolemization of a theorem"),
   680   [("skolem", Attrib.no_args skolem_attr, "skolemization of a theorem"),
   685    ("clausify", clausify, "conversion of theorem to clauses")];
   681    ("clausify", clausify, "conversion of theorem to clauses")];
   686 
   682 
   687 val setup_methods = Method.add_methods
   683 val setup_methods = Method.add_methods
   688   [("neg_clausify", Method.no_args (Method.SIMPLE_METHOD' neg_clausify_tac), 
   684   [("neg_clausify", Method.no_args (Method.SIMPLE_METHOD' neg_clausify_tac),
   689     "conversion of goal to conjecture clauses")];
   685     "conversion of goal to conjecture clauses")];
   690      
   686 
   691 val setup = clause_cache_setup #> ThmCache.init #> setup_attrs #> setup_methods;
   687 val setup = clause_cache_setup #> ThmCache.init #> setup_attrs #> setup_methods;
   692 
   688 
   693 end;
   689 end;