19 |
19 |
20 structure FixrecPackage: FIXREC_PACKAGE = |
20 structure FixrecPackage: FIXREC_PACKAGE = |
21 struct |
21 struct |
22 |
22 |
23 fun fixrec_err s = error ("fixrec definition error:\n" ^ s); |
23 fun fixrec_err s = error ("fixrec definition error:\n" ^ s); |
24 fun fixrec_eq_err sign s eq = |
24 fun fixrec_eq_err thy s eq = |
25 fixrec_err (s ^ "\nin\n" ^ quote (Sign.string_of_term sign eq)); |
25 fixrec_err (s ^ "\nin\n" ^ quote (Sign.string_of_term thy eq)); |
26 |
26 |
27 (* ->> is taken from holcf_logic.ML *) |
27 (* ->> is taken from holcf_logic.ML *) |
28 (* TODO: fix dependencies so we can import HOLCFLogic here *) |
28 (* TODO: fix dependencies so we can import HOLCFLogic here *) |
29 infixr 6 ->>; |
29 infixr 6 ->>; |
30 fun S ->> T = Type ("Cfun.->",[S,T]); |
30 fun S ->> T = Type ("Cfun.->",[S,T]); |
98 fun defs [] _ = [] |
98 fun defs [] _ = [] |
99 | defs (l::[]) r = [one_def l r] |
99 | defs (l::[]) r = [one_def l r] |
100 | defs (l::ls) r = one_def l (%%:"Cprod.cfst"`r) :: defs ls (%%:"Cprod.csnd"`r); |
100 | defs (l::ls) r = one_def l (%%:"Cprod.cfst"`r) :: defs ls (%%:"Cprod.csnd"`r); |
101 val (names, pre_fixdefs) = ListPair.unzip (defs lhss fixpoint); |
101 val (names, pre_fixdefs) = ListPair.unzip (defs lhss fixpoint); |
102 |
102 |
103 val fixdefs = map (inferT_axm (sign_of thy)) pre_fixdefs; |
103 val fixdefs = map (inferT_axm thy) pre_fixdefs; |
104 val (thy', fixdef_thms) = |
104 val (thy', fixdef_thms) = |
105 PureThy.add_defs_i false (map Thm.no_attributes fixdefs) thy; |
105 PureThy.add_defs_i false (map Thm.no_attributes fixdefs) thy; |
106 val ctuple_fixdef_thm = foldr1 (fn (x,y) => cpair_equalI OF [x,y]) fixdef_thms; |
106 val ctuple_fixdef_thm = foldr1 (fn (x,y) => cpair_equalI OF [x,y]) fixdef_thms; |
107 |
107 |
108 fun mk_cterm t = let val sg' = sign_of thy' in cterm_of sg' (infer sg' t) end; |
108 fun mk_cterm t = cterm_of thy' (infer thy' t); |
109 val ctuple_unfold_ct = mk_cterm (mk_trp (mk_ctuple lhss === mk_ctuple rhss)); |
109 val ctuple_unfold_ct = mk_cterm (mk_trp (mk_ctuple lhss === mk_ctuple rhss)); |
110 val ctuple_unfold_thm = prove_goalw_cterm [] ctuple_unfold_ct |
110 val ctuple_unfold_thm = prove_goalw_cterm [] ctuple_unfold_ct |
111 (fn _ => [rtac (ctuple_fixdef_thm RS fix_eq2 RS trans) 1, |
111 (fn _ => [rtac (ctuple_fixdef_thm RS fix_eq2 RS trans) 1, |
112 simp_tac (simpset_of thy') 1]); |
112 simp_tac (simpset_of thy') 1]); |
113 val ctuple_induct_thm = |
113 val ctuple_induct_thm = |
231 fun gen_add_fixrec prep_prop prep_attrib strict blocks thy = |
231 fun gen_add_fixrec prep_prop prep_attrib strict blocks thy = |
232 let |
232 let |
233 val eqns = List.concat blocks; |
233 val eqns = List.concat blocks; |
234 val lengths = map length blocks; |
234 val lengths = map length blocks; |
235 |
235 |
236 val sign = sign_of thy; |
|
237 val ((names, srcss), strings) = apfst split_list (split_list eqns); |
236 val ((names, srcss), strings) = apfst split_list (split_list eqns); |
238 val atts = map (map (prep_attrib thy)) srcss; |
237 val atts = map (map (prep_attrib thy)) srcss; |
239 val eqn_ts = map (prep_prop thy) strings; |
238 val eqn_ts = map (prep_prop thy) strings; |
240 val rec_ts = map (fn eq => chead_of (fst (dest_eqs (Logic.strip_imp_concl eq))) |
239 val rec_ts = map (fn eq => chead_of (fst (dest_eqs (Logic.strip_imp_concl eq))) |
241 handle TERM _ => fixrec_eq_err sign "not a proper equation" eq) eqn_ts; |
240 handle TERM _ => fixrec_eq_err thy "not a proper equation" eq) eqn_ts; |
242 val (_, eqn_ts') = InductivePackage.unify_consts sign rec_ts eqn_ts; |
241 val (_, eqn_ts') = InductivePackage.unify_consts thy rec_ts eqn_ts; |
243 |
242 |
244 fun unconcat [] _ = [] |
243 fun unconcat [] _ = [] |
245 | unconcat (n::ns) xs = List.take (xs,n) :: unconcat ns (List.drop (xs,n)); |
244 | unconcat (n::ns) xs = List.take (xs,n) :: unconcat ns (List.drop (xs,n)); |
246 val pattern_blocks = unconcat lengths (map Logic.strip_imp_concl eqn_ts'); |
245 val pattern_blocks = unconcat lengths (map Logic.strip_imp_concl eqn_ts'); |
247 val compiled_ts = map (infer sign o compile_pats) pattern_blocks; |
246 val compiled_ts = map (infer thy o compile_pats) pattern_blocks; |
248 val (thy', cnames, fixdef_thms, unfold_thms) = add_fixdefs compiled_ts thy; |
247 val (thy', cnames, fixdef_thms, unfold_thms) = add_fixdefs compiled_ts thy; |
249 in |
248 in |
250 if strict then let (* only prove simp rules if strict = true *) |
249 if strict then let (* only prove simp rules if strict = true *) |
251 val eqn_blocks = unconcat lengths ((names ~~ eqn_ts') ~~ atts); |
250 val eqn_blocks = unconcat lengths ((names ~~ eqn_ts') ~~ atts); |
252 val simps = List.concat (map (make_simps thy') (unfold_thms ~~ eqn_blocks)); |
251 val simps = List.concat (map (make_simps thy') (unfold_thms ~~ eqn_blocks)); |
299 |
298 |
300 local structure P = OuterParse and K = OuterSyntax.Keyword in |
299 local structure P = OuterParse and K = OuterSyntax.Keyword in |
301 |
300 |
302 val fixrec_eqn = P.opt_thm_name ":" -- P.prop; |
301 val fixrec_eqn = P.opt_thm_name ":" -- P.prop; |
303 |
302 |
304 val fixrec_strict = |
303 val fixrec_strict = P.opt_keyword "permissive" >> not; |
305 Scan.optional (P.$$$ "(" -- P.!!! (P.$$$ "permissive" -- P.$$$ ")") >> K false) true; |
|
306 |
304 |
307 val fixrec_decl = fixrec_strict -- P.and_list1 (Scan.repeat1 fixrec_eqn); |
305 val fixrec_decl = fixrec_strict -- P.and_list1 (Scan.repeat1 fixrec_eqn); |
308 |
306 |
309 (* this builds a parser for a new keyword, fixrec, whose functionality |
307 (* this builds a parser for a new keyword, fixrec, whose functionality |
310 is defined by add_fixrec *) |
308 is defined by add_fixrec *) |