20427
|
1 |
(* ID: $Id$
|
|
2 |
Author: Florian Haftmann, TU Muenchen
|
|
3 |
*)
|
|
4 |
|
|
5 |
header {* Operational equality for code generation *}
|
|
6 |
|
|
7 |
theory CodeOperationalEquality
|
|
8 |
imports Main
|
|
9 |
begin
|
|
10 |
|
|
11 |
section {* Operational equality for code generation *}
|
|
12 |
|
|
13 |
subsection {* eq class *}
|
|
14 |
|
|
15 |
class eq =
|
|
16 |
fixes eq :: "'a \<Rightarrow> 'a \<Rightarrow> bool"
|
|
17 |
|
|
18 |
defs
|
|
19 |
eq_def: "eq x y == (x = y)"
|
|
20 |
|
|
21 |
ML {*
|
|
22 |
local
|
|
23 |
val thy = the_context ();
|
|
24 |
val const_eq = Sign.intern_const thy "eq";
|
|
25 |
val type_bool = Type (Sign.intern_type thy "bool", []);
|
|
26 |
in
|
|
27 |
val eq_def_sym = Thm.symmetric (thm "eq_def");
|
|
28 |
val class_eq = Sign.intern_class thy "eq";
|
|
29 |
end
|
|
30 |
*}
|
|
31 |
|
|
32 |
|
|
33 |
subsection {* preprocessor *}
|
|
34 |
|
|
35 |
ML {*
|
|
36 |
fun constrain_op_eq thy thms =
|
|
37 |
let
|
|
38 |
fun dest_eq (Const ("op =", ty)) =
|
|
39 |
(SOME o hd o fst o strip_type) ty
|
|
40 |
| dest_eq _ = NONE
|
|
41 |
fun eqs_of t =
|
|
42 |
fold_aterms (fn t => case dest_eq t
|
|
43 |
of SOME (TVar v_sort) => cons v_sort
|
|
44 |
| _ => I) t [];
|
|
45 |
val eqs = maps (eqs_of o Thm.prop_of) thms;
|
|
46 |
val instT = map (fn (v_i, sort) =>
|
|
47 |
(Thm.ctyp_of thy (TVar (v_i, sort)),
|
|
48 |
Thm.ctyp_of thy (TVar (v_i, Sorts.inter_sort (Sign.classes_of thy) (sort, [class_eq]))))) eqs;
|
|
49 |
in
|
|
50 |
thms
|
|
51 |
|> map (Thm.instantiate (instT, []))
|
|
52 |
end;
|
|
53 |
*}
|
|
54 |
|
|
55 |
|
|
56 |
subsection {* codetypes hook *}
|
|
57 |
|
|
58 |
setup {*
|
|
59 |
let
|
|
60 |
fun add_eq_instance specs =
|
|
61 |
DatatypeCodegen.prove_codetypes_arities
|
|
62 |
(K (ClassPackage.intro_classes_tac []))
|
|
63 |
(map (fn (tyco, (is_dt, _)) => (tyco, is_dt)) specs)
|
|
64 |
[class_eq] ((K o K o K) []);
|
|
65 |
(* fun add_eq_thms dtco thy =
|
|
66 |
let
|
|
67 |
val thms =
|
|
68 |
DatatypeCodegen.get_eq thy dtco
|
|
69 |
|> maps ((#mk o #mk_rews o snd o MetaSimplifier.rep_ss o Simplifier.simpset_of) thy)
|
|
70 |
|> constrain_op_eq thy
|
|
71 |
|> map (Tactic.rewrite_rule [eq_def_sym])
|
|
72 |
in fold CodegenTheorems.add_fun thms thy end; *)
|
|
73 |
fun hook dtcos =
|
|
74 |
add_eq_instance dtcos (* #> fold add_eq_thms dtcos *);
|
|
75 |
in
|
|
76 |
DatatypeCodegen.add_codetypes_hook_bootstrap hook
|
|
77 |
end
|
|
78 |
*}
|
|
79 |
|
|
80 |
|
|
81 |
subsection {* extractor *}
|
|
82 |
|
|
83 |
setup {*
|
|
84 |
let
|
|
85 |
fun get_eq_thms thy tyco = case DatatypePackage.get_datatype thy tyco
|
|
86 |
of SOME _ => DatatypeCodegen.get_eq thy tyco
|
|
87 |
| NONE => case TypedefCodegen.get_triv_typedef thy tyco
|
|
88 |
of SOME (_ ,(_, thm)) => [thm]
|
|
89 |
| NONE => [];
|
|
90 |
fun get_eq_thms_eq thy ("OperationalEquality.eq", ty) = (case strip_type ty
|
|
91 |
of (Type (tyco, _) :: _, _) =>
|
|
92 |
get_eq_thms thy tyco
|
|
93 |
| _ => [])
|
|
94 |
| get_eq_thms_eq _ _ = [];
|
|
95 |
in
|
|
96 |
CodegenTheorems.add_fun_extr get_eq_thms_eq
|
|
97 |
end
|
|
98 |
*}
|
|
99 |
|
|
100 |
|
|
101 |
subsection {* integers *}
|
|
102 |
|
|
103 |
definition
|
|
104 |
"eq_integer (k\<Colon>int) l = (k = l)"
|
|
105 |
|
|
106 |
instance int :: eq ..
|
|
107 |
|
|
108 |
lemma [code fun]:
|
|
109 |
"eq k l = eq_integer k l"
|
|
110 |
unfolding eq_integer_def eq_def ..
|
|
111 |
|
|
112 |
code_constapp eq_integer
|
|
113 |
ml (infixl 6 "=")
|
|
114 |
haskell (infixl 4 "==")
|
|
115 |
|
|
116 |
|
|
117 |
subsection {* codegenerator setup *}
|
|
118 |
|
|
119 |
setup {*
|
|
120 |
CodegenTheorems.add_preproc constrain_op_eq
|
|
121 |
*}
|
|
122 |
|
|
123 |
declare eq_def [symmetric, code inline]
|
|
124 |
|
|
125 |
|
|
126 |
subsection {* haskell setup *}
|
|
127 |
|
|
128 |
code_class eq
|
|
129 |
haskell "Eq" (eq "(==)")
|
|
130 |
|
|
131 |
code_instance
|
|
132 |
(eq :: bool) haskell
|
|
133 |
(eq :: unit) haskell
|
|
134 |
(eq :: *) haskell
|
|
135 |
(eq :: option) haskell
|
|
136 |
(eq :: list) haskell
|
|
137 |
(eq :: char) haskell
|
|
138 |
(eq :: int) haskell
|
|
139 |
|
|
140 |
code_constapp
|
|
141 |
"eq"
|
|
142 |
haskell (infixl 4 "==")
|
|
143 |
"eq \<Colon> bool \<Rightarrow> bool \<Rightarrow> bool"
|
|
144 |
haskell (infixl 4 "==")
|
|
145 |
"eq \<Colon> unit \<Rightarrow> unit \<Rightarrow> bool"
|
|
146 |
haskell (infixl 4 "==")
|
|
147 |
"eq \<Colon> 'a\<Colon>eq \<times> 'b\<Colon>eq \<Rightarrow> 'a \<times> 'b \<Rightarrow> bool"
|
|
148 |
haskell (infixl 4 "==")
|
|
149 |
"eq \<Colon> 'a\<Colon>eq option \<Rightarrow> 'a option \<Rightarrow> bool"
|
|
150 |
haskell (infixl 4 "==")
|
|
151 |
"eq \<Colon> 'a\<Colon>eq list \<Rightarrow> 'a list \<Rightarrow> bool"
|
|
152 |
haskell (infixl 4 "==")
|
|
153 |
"eq \<Colon> char \<Rightarrow> char \<Rightarrow> bool"
|
|
154 |
haskell (infixl 4 "==")
|
|
155 |
"eq \<Colon> int \<Rightarrow> int \<Rightarrow> bool"
|
|
156 |
haskell (infixl 4 "==")
|
|
157 |
|
|
158 |
end |