src/HOLCF/Tools/pcpodef_package.ML
changeset 29060 d7bde0b4bf72
parent 28965 1de908189869
child 29063 7619f0561cd7
equal deleted inserted replaced
29059:a049c9816c24 29060:d7bde0b4bf72
     1 (*  Title:      HOLCF/Tools/pcpodef_package.ML
     1 (*  Title:      HOLCF/Tools/pcpodef_package.ML
     2     ID:         $Id$
       
     3     Author:     Brian Huffman
     2     Author:     Brian Huffman
     4 
     3 
     5 Primitive domain definitions for HOLCF, similar to Gordon/HOL-style
     4 Primitive domain definitions for HOLCF, similar to Gordon/HOL-style
     6 typedef.
     5 typedef (see also ~~/src/HOL/Tools/typedef_package.ML).
     7 *)
     6 *)
     8 
     7 
     9 signature PCPODEF_PACKAGE =
     8 signature PCPODEF_PACKAGE =
    10 sig
     9 sig
    11   val pcpodef_proof: (bool * string) * (bstring * string list * mixfix) * string
    10   val pcpodef_proof: (bool * string) * (bstring * string list * mixfix) * term
    12     * (string * string) option -> theory -> Proof.state
    11     * (string * string) option -> theory -> Proof.state
    13   val pcpodef_proof_i: (bool * string) * (bstring * string list * mixfix) * term
    12   val pcpodef_proof_cmd: (bool * string) * (bstring * string list * mixfix) * string
    14     * (string * string) option -> theory -> Proof.state
    13     * (string * string) option -> theory -> Proof.state
    15   val cpodef_proof: (bool * string) * (bstring * string list * mixfix) * string
    14   val cpodef_proof: (bool * string) * (bstring * string list * mixfix) * term
    16     * (string * string) option -> theory -> Proof.state
    15     * (string * string) option -> theory -> Proof.state
    17   val cpodef_proof_i: (bool * string) * (bstring * string list * mixfix) * term
    16   val cpodef_proof_cmd: (bool * string) * (bstring * string list * mixfix) * string
    18     * (string * string) option -> theory -> Proof.state
    17     * (string * string) option -> theory -> Proof.state
    19 end;
    18 end;
    20 
    19 
    21 structure PcpodefPackage: PCPODEF_PACKAGE =
    20 structure PcpodefPackage: PCPODEF_PACKAGE =
    22 struct
    21 struct
    23 
    22 
    24 (** theory context references **)
       
    25 
       
    26 val typedef_po = thm "typedef_po";
       
    27 val typedef_cpo = thm "typedef_cpo";
       
    28 val typedef_pcpo = thm "typedef_pcpo";
       
    29 val typedef_lub = thm "typedef_lub";
       
    30 val typedef_thelub = thm "typedef_thelub";
       
    31 val typedef_compact = thm "typedef_compact";
       
    32 val cont_Rep = thm "typedef_cont_Rep";
       
    33 val cont_Abs = thm "typedef_cont_Abs";
       
    34 val Rep_strict = thm "typedef_Rep_strict";
       
    35 val Abs_strict = thm "typedef_Abs_strict";
       
    36 val Rep_strict_iff = thm "typedef_Rep_strict_iff";
       
    37 val Abs_strict_iff = thm "typedef_Abs_strict_iff";
       
    38 val Rep_defined = thm "typedef_Rep_defined";
       
    39 val Abs_defined = thm "typedef_Abs_defined";
       
    40 
       
    41 
       
    42 (** type definitions **)
    23 (** type definitions **)
    43 
    24 
    44 (* prepare_cpodef *)
    25 (* prepare_cpodef *)
    45 
    26 
    46 fun err_in_cpodef msg name =
    27 fun err_in_cpodef msg name =
    47   cat_error msg ("The error(s) above occurred in cpodef " ^ quote name);
    28   cat_error msg ("The error(s) above occurred in cpodef " ^ quote name);
    48 
    29 
    49 fun declare_type_name a = Variable.declare_constraints (Logic.mk_type (TFree (a, dummyS)));
    30 fun declare_type_name a = Variable.declare_constraints (Logic.mk_type (TFree (a, dummyS)));
    50 
    31 
    51 fun adm_const T = Const ("Adm.adm", (T --> HOLogic.boolT) --> HOLogic.boolT);
    32 fun adm_const T = Const (@{const_name adm}, (T --> HOLogic.boolT) --> HOLogic.boolT);
    52 fun mk_adm (x, T, P) = adm_const T $ absfree (x, T, P);
    33 fun mk_adm (x, T, P) = adm_const T $ absfree (x, T, P);
    53 
    34 
    54 fun prepare_pcpodef prep_term pcpo def name (t, vs, mx) raw_set opt_morphs thy =
    35 fun prepare_pcpodef prep_term pcpo def name (t, vs, mx) raw_set opt_morphs thy =
    55   let
    36   let
       
    37     val _ = Theory.requires thy "Pcpodef" "pcpodefs";
    56     val ctxt = ProofContext.init thy;
    38     val ctxt = ProofContext.init thy;
    57     val full = Sign.full_bname thy;
    39     val full = Sign.full_bname thy;
    58 
    40 
    59     (*rhs*)
    41     (*rhs*)
    60     val full_name = full name;
    42     val full_name = full name;
    61     val set = prep_term (ctxt |> fold declare_type_name vs) raw_set;
    43     val set = prep_term (ctxt |> fold declare_type_name vs) raw_set;
    62     val setT = Term.fastype_of set;
    44     val setT = Term.fastype_of set;
    63     val rhs_tfrees = term_tfrees set;
    45     val rhs_tfrees = Term.add_tfrees set [];
    64     val oldT = HOLogic.dest_setT setT handle TYPE _ =>
    46     val oldT = HOLogic.dest_setT setT handle TYPE _ =>
    65       error ("Not a set type: " ^ quote (Syntax.string_of_typ ctxt setT));
    47       error ("Not a set type: " ^ quote (Syntax.string_of_typ ctxt setT));
    66     fun mk_nonempty A =
    48 
    67       HOLogic.mk_exists ("x", oldT, HOLogic.mk_mem (Free ("x", oldT), A));
    49     (*goal*)
    68     fun mk_admissible A =
    50     val goal_UU_mem = HOLogic.mk_mem (Const (@{const_name UU}, oldT), set);
    69       mk_adm ("x", oldT, HOLogic.mk_mem (Free ("x", oldT), A));
    51     val goal_nonempty = HOLogic.mk_exists ("x", oldT, HOLogic.mk_mem (Free ("x", oldT), set));
    70     fun mk_UU_mem A = HOLogic.mk_mem (Const ("Pcpo.UU", oldT), A);
    52     val goal_admissible = mk_adm ("x", oldT, HOLogic.mk_mem (Free ("x", oldT), set));
    71     val goal = if pcpo
    53     val goal = HOLogic.mk_Trueprop
    72       then HOLogic.mk_Trueprop (HOLogic.mk_conj (mk_UU_mem set, mk_admissible set))
    54       (HOLogic.mk_conj (if pcpo then goal_UU_mem else goal_nonempty, goal_admissible));
    73       else HOLogic.mk_Trueprop (HOLogic.mk_conj (mk_nonempty set, mk_admissible set));
       
    74 
    55 
    75     (*lhs*)
    56     (*lhs*)
    76     val defS = Sign.defaultS thy;
    57     val defS = Sign.defaultS thy;
    77     val lhs_tfrees = map (fn v => (v, the_default defS (AList.lookup (op =) rhs_tfrees v))) vs;
    58     val lhs_tfrees = map (fn v => (v, the_default defS (AList.lookup (op =) rhs_tfrees v))) vs;
    78     val lhs_sorts = map snd lhs_tfrees;
    59     val lhs_sorts = map snd lhs_tfrees;
       
    60 
    79     val tname = Syntax.type_name t mx;
    61     val tname = Syntax.type_name t mx;
    80     val full_tname = full tname;
    62     val full_tname = full tname;
    81     val newT = Type (full_tname, map TFree lhs_tfrees);
    63     val newT = Type (full_tname, map TFree lhs_tfrees);
    82 
    64 
    83     val (Rep_name, Abs_name) = the_default ("Rep_" ^ name, "Abs_" ^ name) opt_morphs;
    65     val (Rep_name, Abs_name) = the_default ("Rep_" ^ name, "Abs_" ^ name) opt_morphs;
    84     val RepC = Const (full Rep_name, newT --> oldT);
    66     val RepC = Const (full Rep_name, newT --> oldT);
    85     fun lessC T = Const (@{const_name Porder.sq_le}, T --> T --> HOLogic.boolT);
    67     fun lessC T = Const (@{const_name sq_le}, T --> T --> HOLogic.boolT);
    86     val less_def = Logic.mk_equals (lessC newT,
    68     val less_def = Logic.mk_equals (lessC newT,
    87       Abs ("x", newT, Abs ("y", newT, lessC oldT $ (RepC $ Bound 1) $ (RepC $ Bound 0))));
    69       Abs ("x", newT, Abs ("y", newT, lessC oldT $ (RepC $ Bound 1) $ (RepC $ Bound 0))));
    88 
    70 
    89     fun make_po tac thy1 =
    71     fun make_po tac thy1 =
    90       let
    72       let
    91         val ((_, {type_definition, set_def, ...}), thy2) = thy1
    73         val ((_, {type_definition, set_def, ...}), thy2) = thy1
    92           |> TypedefPackage.add_typedef def (SOME name) (t, vs, mx) set opt_morphs tac;
    74           |> TypedefPackage.add_typedef def (SOME name) (t, vs, mx) set opt_morphs tac;
    93         val lthy3 = thy2
    75         val lthy3 = thy2
    94           |> TheoryTarget.instantiation ([full_tname], lhs_tfrees, @{sort "Porder.po"});
    76           |> TheoryTarget.instantiation ([full_tname], lhs_tfrees, @{sort po});
    95         val less_def' = Syntax.check_term lthy3 less_def;
    77         val less_def' = Syntax.check_term lthy3 less_def;
    96         val ((_, (_, less_definition')), lthy4) = lthy3
    78         val ((_, (_, less_definition')), lthy4) = lthy3
    97           |> Specification.definition (NONE, ((Binding.name ("less_" ^ name ^ "_def"), []), less_def'));
    79           |> Specification.definition (NONE, ((Binding.name ("less_" ^ name ^ "_def"), []), less_def'));
    98         val ctxt_thy = ProofContext.init (ProofContext.theory_of lthy4);
    80         val ctxt_thy = ProofContext.init (ProofContext.theory_of lthy4);
    99         val less_definition = singleton (ProofContext.export lthy4 ctxt_thy) less_definition';
    81         val less_definition = singleton (ProofContext.export lthy4 ctxt_thy) less_definition';
   100         val thy5 = lthy4
    82         val thy5 = lthy4
   101           |> Class.prove_instantiation_instance
    83           |> Class.prove_instantiation_instance
   102               (K (Tactic.rtac (typedef_po OF [type_definition, less_definition]) 1))
    84               (K (Tactic.rtac (@{thm typedef_po} OF [type_definition, less_definition]) 1))
   103           |> LocalTheory.exit_global;
    85           |> LocalTheory.exit_global;
   104       in ((type_definition, less_definition, set_def), thy5) end;
    86       in ((type_definition, less_definition, set_def), thy5) end;
   105 
    87 
   106     fun make_cpo admissible (type_def, less_def, set_def) theory =
    88     fun make_cpo admissible (type_def, less_def, set_def) theory =
   107       let
    89       let
   108         val admissible' = fold_rule (the_list set_def) admissible;
    90         val admissible' = fold_rule (the_list set_def) admissible;
   109         val cpo_thms = map (Thm.transfer theory) [type_def, less_def, admissible'];
    91         val cpo_thms = map (Thm.transfer theory) [type_def, less_def, admissible'];
   110         val theory' = theory
    92         val theory' = theory
   111           |> AxClass.prove_arity (full_tname, lhs_sorts, ["Pcpo.cpo"])
    93           |> AxClass.prove_arity (full_tname, lhs_sorts, @{sort cpo})
   112             (Tactic.rtac (typedef_cpo OF cpo_thms) 1);
    94             (Tactic.rtac (@{thm typedef_cpo} OF cpo_thms) 1);
   113         val cpo_thms' = map (Thm.transfer theory') cpo_thms;
    95         val cpo_thms' = map (Thm.transfer theory') cpo_thms;
   114       in
    96       in
   115         theory'
    97         theory'
   116         |> Sign.add_path name
    98         |> Sign.add_path name
   117         |> PureThy.add_thms
    99         |> PureThy.add_thms
   118             ([(("adm_" ^ name, admissible'), []),
   100           ([(("adm_" ^ name, admissible'), []),
   119               (("cont_" ^ Rep_name, cont_Rep OF cpo_thms'), []),
   101             (("cont_" ^ Rep_name, @{thm typedef_cont_Rep} OF cpo_thms'), []),
   120               (("cont_" ^ Abs_name, cont_Abs OF cpo_thms'), []),
   102             (("cont_" ^ Abs_name, @{thm typedef_cont_Abs} OF cpo_thms'), []),
   121               (("lub_"     ^ name, typedef_lub     OF cpo_thms'), []),
   103             (("lub_" ^ name, @{thm typedef_lub} OF cpo_thms'), []),
   122               (("thelub_"  ^ name, typedef_thelub  OF cpo_thms'), []),
   104             (("thelub_" ^ name, @{thm typedef_thelub} OF cpo_thms'), []),
   123               (("compact_" ^ name, typedef_compact OF cpo_thms'), [])])
   105             (("compact_" ^ name, @{thm typedef_compact} OF cpo_thms'), [])])
   124         |> snd
   106         |> snd
   125         |> Sign.parent_path
   107         |> Sign.parent_path
   126       end;
   108       end;
   127 
   109 
   128     fun make_pcpo UUmem (type_def, less_def, set_def) theory =
   110     fun make_pcpo UUmem (type_def, less_def, set_def) theory =
   129       let
   111       let
   130         val UUmem' = fold_rule (the_list set_def) UUmem;
   112         val UUmem' = fold_rule (the_list set_def) UUmem;
   131         val pcpo_thms = map (Thm.transfer theory) [type_def, less_def, UUmem'];
   113         val pcpo_thms = map (Thm.transfer theory) [type_def, less_def, UUmem'];
   132         val theory' = theory
   114         val theory' = theory
   133           |> AxClass.prove_arity (full_tname, lhs_sorts, ["Pcpo.pcpo"])
   115           |> AxClass.prove_arity (full_tname, lhs_sorts, @{sort pcpo})
   134             (Tactic.rtac (typedef_pcpo OF pcpo_thms) 1);
   116             (Tactic.rtac (@{thm typedef_pcpo} OF pcpo_thms) 1);
   135         val pcpo_thms' = map (Thm.transfer theory') pcpo_thms;
   117         val pcpo_thms' = map (Thm.transfer theory') pcpo_thms;
   136       in
   118       in
   137         theory'
   119         theory'
   138         |> Sign.add_path name
   120         |> Sign.add_path name
   139         |> PureThy.add_thms
   121         |> PureThy.add_thms
   140             ([((Rep_name ^ "_strict", Rep_strict OF pcpo_thms'), []),
   122             ([((Rep_name ^ "_strict", @{thm typedef_Rep_strict} OF pcpo_thms'), []),
   141               ((Abs_name ^ "_strict", Abs_strict OF pcpo_thms'), []),
   123               ((Abs_name ^ "_strict", @{thm typedef_Abs_strict} OF pcpo_thms'), []),
   142               ((Rep_name ^ "_strict_iff", Rep_strict_iff OF pcpo_thms'), []),
   124               ((Rep_name ^ "_strict_iff", @{thm typedef_Rep_strict_iff} OF pcpo_thms'), []),
   143               ((Abs_name ^ "_strict_iff", Abs_strict_iff OF pcpo_thms'), []),
   125               ((Abs_name ^ "_strict_iff", @{thm typedef_Abs_strict_iff} OF pcpo_thms'), []),
   144               ((Rep_name ^ "_defined", Rep_defined OF pcpo_thms'), []),
   126               ((Rep_name ^ "_defined", @{thm typedef_Rep_defined} OF pcpo_thms'), []),
   145               ((Abs_name ^ "_defined", Abs_defined OF pcpo_thms'), [])
   127               ((Abs_name ^ "_defined", @{thm typedef_Abs_defined} OF pcpo_thms'), [])
   146               ])
   128               ])
   147         |> snd
   129         |> snd
   148         |> Sign.parent_path
   130         |> Sign.parent_path
   149       end;
   131       end;
   150 
   132 
   170 
   152 
   171   in (goal, if pcpo then pcpodef_result else cpodef_result) end
   153   in (goal, if pcpo then pcpodef_result else cpodef_result) end
   172   handle ERROR msg => err_in_cpodef msg name;
   154   handle ERROR msg => err_in_cpodef msg name;
   173 
   155 
   174 
   156 
   175 (* cpodef_proof interface *)
   157 (* proof interface *)
       
   158 
       
   159 local
   176 
   160 
   177 fun gen_pcpodef_proof prep_term pcpo ((def, name), typ, set, opt_morphs) thy =
   161 fun gen_pcpodef_proof prep_term pcpo ((def, name), typ, set, opt_morphs) thy =
   178   let
   162   let
   179     val (goal, pcpodef_result) =
   163     val (goal, pcpodef_result) =
   180       prepare_pcpodef prep_term pcpo def name typ set opt_morphs thy;
   164       prepare_pcpodef prep_term pcpo def name typ set opt_morphs thy;
   181     fun after_qed [[th]] = ProofContext.theory (pcpodef_result th);
   165     fun after_qed [[th]] = ProofContext.theory (pcpodef_result th);
   182   in Proof.theorem_i NONE after_qed [[(goal, [])]] (ProofContext.init thy) end;
   166   in Proof.theorem_i NONE after_qed [[(goal, [])]] (ProofContext.init thy) end;
   183 
   167 
   184 fun pcpodef_proof x = gen_pcpodef_proof Syntax.read_term true x;
   168 in
   185 fun pcpodef_proof_i x = gen_pcpodef_proof Syntax.check_term true x;
   169 
   186 
   170 fun pcpodef_proof x = gen_pcpodef_proof Syntax.check_term true x;
   187 fun cpodef_proof x = gen_pcpodef_proof Syntax.read_term false x;
   171 fun pcpodef_proof_cmd x = gen_pcpodef_proof Syntax.read_term true x;
   188 fun cpodef_proof_i x = gen_pcpodef_proof Syntax.check_term false x;
   172 
       
   173 fun cpodef_proof x = gen_pcpodef_proof Syntax.check_term false x;
       
   174 fun cpodef_proof_cmd x = gen_pcpodef_proof Syntax.read_term false x;
       
   175 
       
   176 end;
       
   177 
   189 
   178 
   190 
   179 
   191 (** outer syntax **)
   180 (** outer syntax **)
   192 
   181 
   193 local structure P = OuterParse and K = OuterKeyword in
   182 local structure P = OuterParse and K = OuterKeyword in
   194 
   183 
   195 (* cf. HOL/Tools/typedef_package.ML *)
       
   196 val typedef_proof_decl =
   184 val typedef_proof_decl =
   197   Scan.optional (P.$$$ "(" |--
   185   Scan.optional (P.$$$ "(" |--
   198       ((P.$$$ "open" >> K false) -- Scan.option P.name || P.name >> (fn s => (true, SOME s)))
   186       ((P.$$$ "open" >> K false) -- Scan.option P.name || P.name >> (fn s => (true, SOME s)))
   199         --| P.$$$ ")") (true, NONE) --
   187         --| P.$$$ ")") (true, NONE) --
   200     (P.type_args -- P.name) -- P.opt_infix -- (P.$$$ "=" |-- P.term) --
   188     (P.type_args -- P.name) -- P.opt_infix -- (P.$$$ "=" |-- P.term) --
   201     Scan.option (P.$$$ "morphisms" |-- P.!!! (P.name -- P.name));
   189     Scan.option (P.$$$ "morphisms" |-- P.!!! (P.name -- P.name));
   202 
   190 
   203 fun mk_pcpodef_proof pcpo ((((((def, opt_name), (vs, t)), mx), A), morphs)) =
   191 fun mk_pcpodef_proof pcpo ((((((def, opt_name), (vs, t)), mx), A), morphs)) =
   204   (if pcpo then pcpodef_proof else cpodef_proof)
   192   (if pcpo then pcpodef_proof_cmd else cpodef_proof_cmd)
   205     ((def, the_default (Syntax.type_name t mx) opt_name), (t, vs, mx), A, morphs);
   193     ((def, the_default (Syntax.type_name t mx) opt_name), (t, vs, mx), A, morphs);
   206 
   194 
   207 val _ =
   195 val _ =
   208   OuterSyntax.command "pcpodef" "HOLCF type definition (requires admissibility proof)" K.thy_goal
   196   OuterSyntax.command "pcpodef" "HOLCF type definition (requires admissibility proof)" K.thy_goal
   209     (typedef_proof_decl >>
   197     (typedef_proof_decl >>