Theory Isabelle_code_target
chapter‹Part ...›
theory Isabelle_code_target
imports Main
keywords "attach"
and "lazy_code_printing" "apply_code_printing" "apply_code_printing_reflect"
:: thy_decl
begin
subsection‹beginning (lazy code printing)›
ML‹
structure Isabelle_Code_Target =
struct
open Basic_Code_Symbol;
open Basic_Code_Thingol;
val parse_classrel_ident = Parse.class --| @{keyword "<"} -- Parse.class;
val parse_inst_ident = Parse.name --| @{keyword "::"} -- Parse.class;
fun prep_destination s = ({physical = true}, (Path.explode s, Position.none));
fun export_code_cmd all_public raw_cs seris thy =
let
val ctxt = Proof_Context.init_global thy;
val cs = Code_Thingol.read_const_exprs ctxt raw_cs;
in
thy |> Named_Target.theory_map
(Code_Target.export_code all_public cs
((map o apfst o apsnd o Option.map) prep_destination seris))
end;
fun parse_single_symbol_pragma parse_keyword parse_isa parse_target =
parse_keyword |-- Parse.!!! (parse_isa --| (@{keyword "⇀"} || @{keyword "=>"})
-- Parse.and_list1 (@{keyword "("} |-- (Parse.name --| @{keyword ")"} -- Scan.option parse_target)));
fun parse_symbol_pragma parse_const parse_tyco parse_class parse_classrel parse_inst parse_module =
parse_single_symbol_pragma @{keyword "constant"} Parse.term parse_const
>> Constant
|| parse_single_symbol_pragma @{keyword "type_constructor"} Parse.type_const parse_tyco
>> Type_Constructor
|| parse_single_symbol_pragma @{keyword "type_class"} Parse.class parse_class
>> Type_Class
|| parse_single_symbol_pragma @{keyword "class_relation"} parse_classrel_ident parse_classrel
>> Class_Relation
|| parse_single_symbol_pragma @{keyword "class_instance"} parse_inst_ident parse_inst
>> Class_Instance
|| parse_single_symbol_pragma @{keyword "code_module"} Parse.name parse_module
>> Code_Symbol.Module;
fun parse_symbol_pragmas parse_const parse_tyco parse_class parse_classrel parse_inst parse_module =
Parse.enum1 "|" (Parse.group (fn () => "code symbol pragma")
(parse_symbol_pragma parse_const parse_tyco parse_class parse_classrel parse_inst parse_module));
end
›
ML‹
structure Code_printing = struct
datatype code_printing = Code_printing of
(string * (bstring * Code_Printer.raw_const_syntax option) list,
string * (bstring * Code_Printer.tyco_syntax option) list,
string * (bstring * string option) list,
(string * string) * (bstring * unit option) list,
(xstring * string) * (bstring * unit option) list,
bstring * (bstring * (string * Code_Symbol.T list) option) list)
Code_Symbol.attr
list
structure Data_code = Theory_Data
(
type T = code_printing list Symtab.table
val empty = Symtab.empty
val merge = Symtab.merge (K true)
)
val code_empty = ""
val () =
Outer_Syntax.command @{command_keyword lazy_code_printing} "declare dedicated printing for code symbols"
(Isabelle_Code_Target.parse_symbol_pragmas (Code_Printer.parse_const_syntax) (Code_Printer.parse_tyco_syntax)
Parse.string (Parse.minus >> K ()) (Parse.minus >> K ())
(Parse.embedded -- Scan.optional (@{keyword "attach"} |-- Scan.repeat1 Parse.term >> map Code_Symbol.Constant) [])
>> (fn code =>
Toplevel.theory (Data_code.map (Symtab.map_default (code_empty, []) (fn l => Code_printing code :: l)))))
fun apply_code_printing thy =
(case Symtab.lookup (Data_code.get thy) code_empty of SOME l => rev l | _ => [])
|> (fn l => fold (fn Code_printing l => fold Code_Target.set_printings l) l thy)
val () =
Outer_Syntax.command @{command_keyword apply_code_printing} "apply dedicated printing for code symbols"
(Parse.$$$ "(" -- Parse.$$$ ")" >> K (Toplevel.theory apply_code_printing))
fun reflect_ml source thy =
case ML_Context.exec (fn () =>
ML_Context.eval_source (ML_Compiler.verbose false ML_Compiler.flags) source) (Context.Theory thy) of
Context.Theory thy => thy
fun apply_code_printing_reflect thy =
(case Symtab.lookup (Data_code.get thy) code_empty of SOME l => rev l | _ => [])
|> (fn l => fold (fn Code_printing l =>
fold (fn Code_Symbol.Module (_, l) =>
fold (fn ("SML", SOME (txt, _)) => reflect_ml (Input.source false txt (Position.none, Position.none))
| _ => I) l
| _ => I) l) l thy)
val () =
Outer_Syntax.command @{command_keyword apply_code_printing_reflect} "apply dedicated printing for code symbols"
(Parse.ML_source >> (fn src => Toplevel.theory (apply_code_printing_reflect o reflect_ml src)))
end
›
end