5 Syntax translations for Hoare logic. |
5 Syntax translations for Hoare logic. |
6 *) |
6 *) |
7 |
7 |
8 signature HOARE_SYNTAX = |
8 signature HOARE_SYNTAX = |
9 sig |
9 sig |
10 val hoare_vars_tr: term list -> term |
10 val hoare_vars_tr: Proof.context -> term list -> term |
11 val hoare_tc_vars_tr: term list -> term |
11 val hoare_tc_vars_tr: Proof.context -> term list -> term |
12 val spec_tr': string -> term list -> term |
12 val spec_tr': string -> Proof.context -> term list -> term |
|
13 val setup: |
|
14 {Basic: string, Skip: string, Seq: string, Cond: string, While: string, |
|
15 Valid: string, ValidTC: string} -> theory -> theory |
13 end; |
16 end; |
14 |
17 |
15 structure Hoare_Syntax: HOARE_SYNTAX = |
18 structure Hoare_Syntax: HOARE_SYNTAX = |
16 struct |
19 struct |
|
20 |
|
21 (** theory data **) |
|
22 |
|
23 structure Data = Theory_Data |
|
24 ( |
|
25 type T = |
|
26 {Basic: string, Skip: string, Seq: string, Cond: string, While: string, |
|
27 Valid: string, ValidTC: string} option; |
|
28 val empty: T = NONE; |
|
29 val extend = I; |
|
30 fun merge (data1, data2) = |
|
31 if is_some data1 andalso is_some data2 andalso data1 <> data2 then |
|
32 error "Cannot merge syntax from different Hoare Logics" |
|
33 else merge_options (data1, data2); |
|
34 ); |
|
35 |
|
36 fun const_syntax ctxt which = |
|
37 (case Data.get (Proof_Context.theory_of ctxt) of |
|
38 SOME consts => which consts |
|
39 | NONE => error "Undefined Hoare syntax consts"); |
|
40 |
|
41 val syntax_const = Syntax.const oo const_syntax; |
|
42 |
|
43 |
17 |
44 |
18 (** parse translation **) |
45 (** parse translation **) |
19 |
46 |
20 local |
47 local |
21 |
48 |
52 fun var_tr v xs = mk_abstuple xs v; |
79 fun var_tr v xs = mk_abstuple xs v; |
53 |
80 |
54 |
81 |
55 (* com_tr *) |
82 (* com_tr *) |
56 |
83 |
57 fun com_tr (Const (\<^syntax_const>\<open>_assign\<close>, _) $ x $ e) xs = |
84 fun com_tr ctxt = |
58 Syntax.const \<^const_syntax>\<open>Basic\<close> $ mk_fexp x e xs |
85 let |
59 | com_tr (Const (\<^const_syntax>\<open>Basic\<close>,_) $ f) _ = Syntax.const \<^const_syntax>\<open>Basic\<close> $ f |
86 fun tr (Const (\<^syntax_const>\<open>_assign\<close>, _) $ x $ e) xs = |
60 | com_tr (Const (\<^const_syntax>\<open>Seq\<close>,_) $ c1 $ c2) xs = |
87 syntax_const ctxt #Basic $ mk_fexp x e xs |
61 Syntax.const \<^const_syntax>\<open>Seq\<close> $ com_tr c1 xs $ com_tr c2 xs |
88 | tr (Const (\<^syntax_const>\<open>_Seq\<close>,_) $ c1 $ c2) xs = |
62 | com_tr (Const (\<^const_syntax>\<open>Cond\<close>,_) $ b $ c1 $ c2) xs = |
89 syntax_const ctxt #Seq $ tr c1 xs $ tr c2 xs |
63 Syntax.const \<^const_syntax>\<open>Cond\<close> $ bexp_tr b xs $ com_tr c1 xs $ com_tr c2 xs |
90 | tr (Const (\<^syntax_const>\<open>_Cond\<close>,_) $ b $ c1 $ c2) xs = |
64 | com_tr (Const (\<^const_syntax>\<open>While\<close>,_) $ b $ I $ V $ c) xs = |
91 syntax_const ctxt #Cond $ bexp_tr b xs $ tr c1 xs $ tr c2 xs |
65 Syntax.const \<^const_syntax>\<open>While\<close> $ bexp_tr b xs $ assn_tr I xs $ var_tr V xs $ com_tr c xs |
92 | tr (Const (\<^syntax_const>\<open>_While\<close>,_) $ b $ I $ V $ c) xs = |
66 | com_tr t _ = t; |
93 syntax_const ctxt #While $ bexp_tr b xs $ assn_tr I xs $ var_tr V xs $ tr c xs |
|
94 | tr t _ = t; |
|
95 in tr end; |
67 |
96 |
68 fun vars_tr (Const (\<^syntax_const>\<open>_idts\<close>, _) $ idt $ vars) = idt :: vars_tr vars |
97 fun vars_tr (Const (\<^syntax_const>\<open>_idts\<close>, _) $ idt $ vars) = idt :: vars_tr vars |
69 | vars_tr t = [t]; |
98 | vars_tr t = [t]; |
70 |
99 |
71 in |
100 in |
72 |
101 |
73 fun hoare_vars_tr [vars, pre, prg, post] = |
102 fun hoare_vars_tr ctxt [vars, pre, prg, post] = |
74 let val xs = vars_tr vars |
103 let val xs = vars_tr vars |
75 in Syntax.const \<^const_syntax>\<open>Valid\<close> $ |
104 in syntax_const ctxt #Valid $ assn_tr pre xs $ com_tr ctxt prg xs $ assn_tr post xs end |
76 assn_tr pre xs $ com_tr prg xs $ assn_tr post xs |
105 | hoare_vars_tr _ ts = raise TERM ("hoare_vars_tr", ts); |
77 end |
106 |
78 | hoare_vars_tr ts = raise TERM ("hoare_vars_tr", ts); |
107 fun hoare_tc_vars_tr ctxt [vars, pre, prg, post] = |
79 |
|
80 fun hoare_tc_vars_tr [vars, pre, prg, post] = |
|
81 let val xs = vars_tr vars |
108 let val xs = vars_tr vars |
82 in Syntax.const \<^const_syntax>\<open>ValidTC\<close> $ |
109 in syntax_const ctxt #ValidTC $ assn_tr pre xs $ com_tr ctxt prg xs $ assn_tr post xs end |
83 assn_tr pre xs $ com_tr prg xs $ assn_tr post xs |
110 | hoare_tc_vars_tr _ ts = raise TERM ("hoare_tc_vars_tr", ts); |
84 end |
|
85 | hoare_tc_vars_tr ts = raise TERM ("hoare_tc_vars_tr", ts); |
|
86 |
111 |
87 end; |
112 end; |
88 |
113 |
89 |
114 |
90 |
115 |
137 | var_tr' t = t; |
162 | var_tr' t = t; |
138 |
163 |
139 |
164 |
140 (* com_tr' *) |
165 (* com_tr' *) |
141 |
166 |
142 fun mk_assign f = |
167 fun mk_assign ctxt f = |
143 let |
168 let |
144 val (vs, ts) = mk_vts f; |
169 val (vs, ts) = mk_vts f; |
145 val (ch, which) = find_ch (vs ~~ ts) (length vs - 1) (rev vs); |
170 val (ch, (a, b)) = find_ch (vs ~~ ts) (length vs - 1) (rev vs); |
146 in |
171 in |
147 if ch |
172 if ch |
148 then Syntax.const \<^syntax_const>\<open>_assign\<close> $ fst which $ snd which |
173 then Syntax.const \<^syntax_const>\<open>_assign\<close> $ a $ b |
149 else Syntax.const \<^const_syntax>\<open>annskip\<close> |
174 else syntax_const ctxt #Skip |
150 end; |
175 end; |
151 |
176 |
152 fun com_tr' (Const (\<^const_syntax>\<open>Basic\<close>, _) $ f) = |
177 fun com_tr' ctxt t = |
153 if is_f f then mk_assign f |
178 let |
154 else Syntax.const \<^const_syntax>\<open>Basic\<close> $ f |
179 val (head, args) = apfst (try (#1 o Term.dest_Const)) (Term.strip_comb t); |
155 | com_tr' (Const (\<^const_syntax>\<open>Seq\<close>,_) $ c1 $ c2) = |
180 fun arg k = nth args (k - 1); |
156 Syntax.const \<^const_syntax>\<open>Seq\<close> $ com_tr' c1 $ com_tr' c2 |
181 val n = length args; |
157 | com_tr' (Const (\<^const_syntax>\<open>Cond\<close>, _) $ b $ c1 $ c2) = |
182 in |
158 Syntax.const \<^const_syntax>\<open>Cond\<close> $ bexp_tr' b $ com_tr' c1 $ com_tr' c2 |
183 (case head of |
159 | com_tr' (Const (\<^const_syntax>\<open>While\<close>, _) $ b $ I $ V $ c) = |
184 NONE => t |
160 Syntax.const \<^const_syntax>\<open>While\<close> $ bexp_tr' b $ assn_tr' I $ var_tr' V $ com_tr' c |
185 | SOME c => |
161 | com_tr' t = t; |
186 if c = const_syntax ctxt #Basic andalso n = 1 andalso is_f (arg 1) then |
|
187 mk_assign ctxt (arg 1) |
|
188 else if c = const_syntax ctxt #Seq andalso n = 2 then |
|
189 Syntax.const \<^syntax_const>\<open>_Seq\<close> $ com_tr' ctxt (arg 1) $ com_tr' ctxt (arg 2) |
|
190 else if c = const_syntax ctxt #Cond andalso n = 3 then |
|
191 Syntax.const \<^syntax_const>\<open>_Cond\<close> $ |
|
192 bexp_tr' (arg 1) $ com_tr' ctxt (arg 2) $ com_tr' ctxt (arg 3) |
|
193 else if c = const_syntax ctxt #While andalso n = 4 then |
|
194 Syntax.const \<^syntax_const>\<open>_While\<close> $ |
|
195 bexp_tr' (arg 1) $ assn_tr' (arg 2) $ var_tr' (arg 3) $ com_tr' ctxt (arg 4) |
|
196 else t) |
|
197 end; |
162 |
198 |
163 in |
199 in |
164 |
200 |
165 fun spec_tr' syn [p, c, q] = Syntax.const syn $ assn_tr' p $ com_tr' c $ assn_tr' q; |
201 fun spec_tr' syn ctxt [p, c, q] = |
166 |
202 Syntax.const syn $ assn_tr' p $ com_tr' ctxt c $ assn_tr' q; |
167 end; |
203 |
168 |
204 end; |
169 end; |
205 |
170 |
206 |
|
207 (** setup **) |
|
208 |
|
209 fun setup consts = |
|
210 Data.put (SOME consts) #> |
|
211 Sign.parse_translation |
|
212 [(\<^syntax_const>\<open>_hoare_vars\<close>, hoare_vars_tr), |
|
213 (\<^syntax_const>\<open>_hoare_vars_tc\<close>, hoare_tc_vars_tr)] #> |
|
214 Sign.print_translation |
|
215 [(#Valid consts, spec_tr' \<^syntax_const>\<open>_hoare\<close>), |
|
216 (#ValidTC consts, spec_tr' \<^syntax_const>\<open>_hoare_tc\<close>)]; |
|
217 |
|
218 end; |