src/Pure/Tools/generated_files.ML
author wenzelm
Sat, 17 Dec 2022 19:06:40 +0100
changeset 76668 dd03c91cda43
parent 75691 041d7d633977
child 76802 ad01b550e74b
permissions -rw-r--r--
clarified signature;
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
69383
747f8b052e59 clarified modules;
wenzelm
parents: 69381
diff changeset
     1
(*  Title:      Pure/Tools/generated_files.ML
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
     2
    Author:     Makarius
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
     3
69383
747f8b052e59 clarified modules;
wenzelm
parents: 69381
diff changeset
     4
Generated source files for other languages: with antiquotations, without Isabelle symbols.
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
     5
*)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
     6
69383
747f8b052e59 clarified modules;
wenzelm
parents: 69381
diff changeset
     7
signature GENERATED_FILES =
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
     8
sig
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
     9
  val add_files: Path.binding * Bytes.T -> theory -> theory
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
    10
  type file = {path: Path.T, pos: Position.T, content: Bytes.T}
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    11
  val file_binding: file -> Path.binding
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
    12
  val file_markup: file -> Markup.T
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    13
  val print_file: file -> string
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
    14
  val report_file: Proof.context -> Position.T -> file -> unit
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    15
  val get_files: theory -> file list
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    16
  val get_file: theory -> Path.binding -> file
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
    17
  val get_files_in: Path.binding list * theory -> (file * Position.T) list
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    18
  val check_files_in: Proof.context ->
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    19
    (string * Position.T) list * (string * Position.T) option -> Path.binding list * theory
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    20
  val write_file: Path.T -> file -> unit
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    21
  val export_file: theory -> file -> unit
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    22
  type file_type =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    23
    {name: string, ext: string, make_comment: string -> string, make_string: string -> string}
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    24
  val file_type:
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    25
    binding -> {ext: string, make_comment: string -> string, make_string: string -> string} ->
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    26
    theory -> theory
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    27
  val antiquotation: binding -> 'a Token.context_parser ->
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    28
    ({context: Proof.context, source: Token.src, file_type: file_type, argument: 'a} -> string) ->
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    29
    theory -> theory
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    30
  val set_string: string -> Proof.context -> Proof.context
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    31
  val generate_file: Path.binding * Input.source -> Proof.context -> local_theory
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    32
  val generate_file_cmd: (string * Position.T) * Input.source -> local_theory -> local_theory
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    33
  val export_generated_files: Proof.context -> (Path.binding list * theory) list -> unit
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    34
  val export_generated_files_cmd: Proof.context ->
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
    35
    ((string * Position.T) list * (string * Position.T) option) list -> unit
75685
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
    36
  val check_external_files: Proof.context ->
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
    37
    Input.source list * Input.source -> Path.T list * Path.T
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
    38
  val get_external_files: Path.T -> Path.T list * Path.T -> unit
75686
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
    39
  val scala_build_generated_files: Proof.context -> (Path.binding list * theory) list ->
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
    40
    (Path.T list * Path.T) list -> unit
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
    41
  val scala_build_generated_files_cmd: Proof.context ->
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
    42
    ((string * Position.T) list * (string * Position.T) option) list ->
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
    43
    (Input.source list * Input.source) list -> unit
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
    44
  val with_compile_dir: (Path.T -> unit) -> unit
70054
a884b2967dd7 clarified export_files: Isabelle_System.copy_file_base preserves given directory sub-structure;
wenzelm
parents: 70053
diff changeset
    45
  val compile_generated_files: Proof.context ->
a884b2967dd7 clarified export_files: Isabelle_System.copy_file_base preserves given directory sub-structure;
wenzelm
parents: 70053
diff changeset
    46
    (Path.binding list * theory) list ->
a884b2967dd7 clarified export_files: Isabelle_System.copy_file_base preserves given directory sub-structure;
wenzelm
parents: 70053
diff changeset
    47
    (Path.T list * Path.T) list ->
a884b2967dd7 clarified export_files: Isabelle_System.copy_file_base preserves given directory sub-structure;
wenzelm
parents: 70053
diff changeset
    48
    (Path.binding list * bool option) list ->
a884b2967dd7 clarified export_files: Isabelle_System.copy_file_base preserves given directory sub-structure;
wenzelm
parents: 70053
diff changeset
    49
    Path.binding -> Input.source -> unit
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
    50
  val compile_generated_files_cmd: Proof.context ->
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
    51
    ((string * Position.T) list * (string * Position.T) option) list ->
72841
fd8d82c4433b more accurate markup (refining 1c59b555ac4a);
wenzelm
parents: 72511
diff changeset
    52
    (Input.source list * Input.source) list ->
70054
a884b2967dd7 clarified export_files: Isabelle_System.copy_file_base preserves given directory sub-structure;
wenzelm
parents: 70053
diff changeset
    53
    ((string * Position.T) list * bool option) list ->
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
    54
    string * Position.T -> Input.source -> unit
70067
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
    55
  val execute: Path.T -> Input.source -> string -> string
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    56
end;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    57
69383
747f8b052e59 clarified modules;
wenzelm
parents: 69381
diff changeset
    58
structure Generated_Files: GENERATED_FILES =
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    59
struct
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    60
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    61
(** context data **)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    62
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
    63
type file = Path.T * (Position.T * Bytes.T);
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    64
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    65
type file_type =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    66
  {name: string, ext: string, make_comment: string -> string, make_string: string -> string};
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    67
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    68
type antiquotation = Token.src -> Proof.context -> file_type -> string;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    69
72046
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    70
fun err_dup_files path pos pos' =
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    71
  error ("Duplicate generated file: " ^ Path.print path ^ Position.here_list [pos, pos']);
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    72
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    73
structure Data = Theory_Data
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    74
(
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    75
  type T =
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    76
    file list Symtab.table *  (*files for named theory*)
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    77
    file_type Name_Space.table *  (*file types*)
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
    78
    antiquotation Name_Space.table;  (*antiquotations*)
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    79
  val empty =
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    80
    (Symtab.empty,
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
    81
     Name_Space.empty_table Markup.file_typeN,
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
    82
     Name_Space.empty_table Markup.antiquotationN);
72046
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    83
  fun merge ((files1, types1, antiqs1), (files2, types2, antiqs2)) =
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    84
    let
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    85
      val files' =
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
    86
        (files1, files2) |> Symtab.join (fn _ =>
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
    87
          Library.merge (fn ((path1, (pos1, bytes1)), (path2, (pos2, bytes2))) =>
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
    88
            if path1 <> path2 then false
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
    89
            else if pos1 = pos2 andalso Bytes.eq (bytes1, bytes2) then true
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
    90
            else err_dup_files path1 pos1 pos2));
72046
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    91
      val types' = Name_Space.merge_tables (types1, types2);
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    92
      val antiqs' = Name_Space.merge_tables (antiqs1, antiqs2);
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
    93
    in (files', types', antiqs') end;
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    94
);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
    95
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    96
fun lookup_files thy =
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    97
  Symtab.lookup_list (#1 (Data.get thy)) (Context.theory_long_name thy);
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    98
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
    99
fun update_files thy_files' thy =
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   100
  (Data.map o @{apply 3(1)}) (Symtab.update (Context.theory_long_name thy, thy_files')) thy;
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   101
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   102
fun add_files (binding, content) thy =
70055
36fb663145e5 type Path.binding may be empty: check later via proper_binding;
wenzelm
parents: 70054
diff changeset
   103
  let
36fb663145e5 type Path.binding may be empty: check later via proper_binding;
wenzelm
parents: 70054
diff changeset
   104
    val _ = Path.proper_binding binding;
36fb663145e5 type Path.binding may be empty: check later via proper_binding;
wenzelm
parents: 70054
diff changeset
   105
    val (path, pos) = Path.dest_binding binding;
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   106
    val thy_files = lookup_files thy;
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   107
    val thy_files' =
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   108
      (case AList.lookup (op =) thy_files path of
72046
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
   109
        SOME (pos', _) => err_dup_files path pos pos'
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   110
      | NONE => (path, (pos, content)) :: thy_files);
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   111
  in update_files thy_files' thy end;
72046
c386d1b77762 more thorough extend/merge (for Theory.join_theory);
wenzelm
parents: 70991
diff changeset
   112
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   113
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   114
(* get files *)
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   115
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   116
type file = {path: Path.T, pos: Position.T, content: Bytes.T};
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   117
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   118
fun file_binding (file: file) = Path.binding (#path file, #pos file);
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   119
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   120
fun file_markup (file: file) = (Markup.entityN, Position.def_properties_of (#pos file));
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   121
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   122
fun print_file (file: file) = Markup.markup (file_markup file) (quote (Path.implode (#path file)));
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   123
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   124
fun report_file ctxt pos file = Context_Position.report ctxt pos (file_markup file);
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   125
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
   126
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   127
fun get_files thy =
72050
d4de7e4754d2 clarified theory data: more robust merge;
wenzelm
parents: 72046
diff changeset
   128
  lookup_files thy |> rev |> map (fn (path, (pos, content)) =>
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   129
    {path = path, pos = pos, content = content}: file);
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   130
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   131
fun get_file thy binding =
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   132
  let val (path, pos) = Path.dest_binding binding in
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   133
    (case find_first (fn file => #path file = path) (get_files thy) of
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   134
      SOME file => file
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   135
    | NONE =>
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   136
        error ("Missing generated file " ^ Path.print path ^
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   137
          " in theory " ^ quote (Context.theory_long_name thy) ^ Position.here pos))
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   138
  end;
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   139
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   140
fun get_files_in ([], thy) = map (rpair Position.none) (get_files thy)
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   141
  | get_files_in (files, thy) =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   142
      map (fn binding => (get_file thy binding, Path.pos_of_binding binding)) files;
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   143
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   144
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   145
(* check and output files *)
69628
a2fbfdc5e62d export generated files;
wenzelm
parents: 69385
diff changeset
   146
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   147
fun check_files_in ctxt (files, opt_thy) =
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   148
  let
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   149
    val thy =
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   150
      (case opt_thy of
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   151
        SOME name => Theory.check {long = false} ctxt name
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   152
      | NONE => Proof_Context.theory_of ctxt);
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   153
  in (map Path.explode_binding files, thy) end;
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   154
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   155
fun write_file dir (file: file) =
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   156
  let
72511
460d743010bc clarified signature: overloaded "+" for Path.append;
wenzelm
parents: 72375
diff changeset
   157
    val path = Path.expand (dir + #path file);
72375
e48d93811ed7 clarified signature;
wenzelm
parents: 72050
diff changeset
   158
    val _ = Isabelle_System.make_directory (Path.dir path);
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   159
    val content = #content file;
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   160
    val write_content =
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   161
      (case try Bytes.read path of
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   162
        SOME old_content => not (Bytes.eq (content, old_content))
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   163
      | NONE => true)
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   164
  in if write_content then Bytes.write path content else () end;
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   165
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   166
fun export_file thy (file: file) =
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   167
  Export.export thy (file_binding file) (Bytes.contents_blob (#content file));
70013
6de8b7a5cd44 tuned signature -- more operations;
wenzelm
parents: 70012
diff changeset
   168
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   169
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   170
(* file types *)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   171
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   172
fun get_file_type thy ext =
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   173
  if ext = "" then error "Bad file extension"
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   174
  else
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
   175
    (#2 (Data.get thy), NONE) |-> Name_Space.fold_table
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   176
      (fn (_, file_type) => fn res =>
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   177
        if #ext file_type = ext then SOME file_type else res)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   178
    |> (fn SOME file_type => file_type
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   179
         | NONE => error ("Unknown file type for extension " ^ quote ext));
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   180
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   181
fun file_type binding {ext, make_comment, make_string} thy =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   182
  let
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   183
    val name = Binding.name_of binding;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   184
    val pos = Binding.pos_of binding;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   185
    val file_type = {name = name, ext = ext, make_comment = make_comment, make_string = make_string};
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   186
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
   187
    val table = #2 (Data.get thy);
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   188
    val space = Name_Space.space_of_table table;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   189
    val context = Context.Theory thy |> Name_Space.map_naming (K Name_Space.global_naming);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   190
    val (_, data') = table |> Name_Space.define context true (Binding.make (name, pos), file_type);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   191
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   192
    val _ =
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   193
      (case try (#name o get_file_type thy) ext of
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   194
        NONE => ()
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   195
      | SOME name' =>
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   196
          error ("Extension " ^ quote ext ^ " already registered for file type " ^
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   197
            quote (Markup.markup (Name_Space.markup space name') name') ^ Position.here pos));
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
   198
  in thy |> (Data.map o @{apply 3(2)}) (K data') end;
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   199
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   200
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   201
(* antiquotations *)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   202
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
   203
val get_antiquotations = #3 o Data.get o Proof_Context.theory_of;
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   204
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   205
fun antiquotation name scan body thy =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   206
  let
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   207
    fun ant src ctxt file_type : string =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   208
      let val (x, ctxt') = Token.syntax scan src ctxt
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   209
      in body {context = ctxt', source = src, file_type = file_type, argument = x} end;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   210
  in
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   211
    thy
69385
be9f187dcd50 clarified signature: allow to add_files/get_files by other tools;
wenzelm
parents: 69383
diff changeset
   212
    |> (Data.map o @{apply 3(3)}) (Name_Space.define (Context.Theory thy) true (name, ant) #> #2)
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   213
  end;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   214
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   215
val scan_antiq =
74373
6e4093927dbb outer syntax: support for control-cartouche tokens;
wenzelm
parents: 74147
diff changeset
   216
  Antiquote.scan_control Antiquote.err_prefix >> Antiquote.Control ||
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   217
  Scan.one (Symbol.not_eof o Symbol_Pos.symbol) >> (Antiquote.Text o Symbol_Pos.symbol);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   218
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   219
fun read_source ctxt (file_type: file_type) source =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   220
  let
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   221
    val _ =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   222
      Context_Position.report ctxt (Input.pos_of source)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   223
        (Markup.language
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   224
          {name = #name file_type, symbols = false, antiquotes = true,
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   225
            delimited = Input.is_delimited source});
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   226
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   227
    val (input, _) =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   228
      Input.source_explode source
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   229
      |> Scan.error (Scan.finite Symbol_Pos.stopper (Scan.repeat scan_antiq));
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   230
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   231
    val _ = Context_Position.reports ctxt (Antiquote.antiq_reports input);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   232
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   233
    fun expand antiq =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   234
      (case antiq of
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   235
        Antiquote.Text s => s
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   236
      | Antiquote.Control {name, body, ...} =>
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   237
          let
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   238
            val src = Token.make_src name (if null body then [] else [Token.read_cartouche body]);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   239
            val (src', ant) = Token.check_src ctxt get_antiquotations src;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   240
          in ant src' ctxt file_type end
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   241
      | Antiquote.Antiq antiq => error ("Bad antiquotation " ^ Position.here (#1 (#range antiq))));
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   242
  in implode (map expand input) end;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   243
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   244
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   245
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   246
(** Isar commands **)
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   247
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   248
(* generate_file *)
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   249
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   250
fun generate_file (binding, source) lthy =
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   251
  let
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   252
    val thy = Proof_Context.theory_of lthy;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   253
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   254
    val (path, pos) = Path.dest_binding binding;
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   255
    val file_type =
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   256
      get_file_type thy (#2 (Path.split_ext path))
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   257
        handle ERROR msg => error (msg ^ Position.here pos);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   258
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   259
    val header = #make_comment file_type " generated by Isabelle ";
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   260
    val content = Bytes.string (header ^ "\n" ^ read_source lthy file_type source);
70015
c8e08d8ffb93 clarified signature: more explicit type Path.binding;
wenzelm
parents: 70013
diff changeset
   261
  in lthy |> (Local_Theory.background_theory o add_files) (binding, content) end;
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   262
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   263
fun generate_file_cmd (file, source) lthy =
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   264
  generate_file (Path.explode_binding file, source) lthy;
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   265
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   266
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   267
(* export_generated_files *)
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   268
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   269
fun export_generated_files ctxt args =
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   270
  let val thy = Proof_Context.theory_of ctxt in
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   271
    (case map #1 (maps get_files_in args) of
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   272
      [] => ()
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   273
    | files =>
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   274
       (List.app (export_file thy) files;
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   275
        writeln (Export.message thy Path.current);
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   276
        writeln (cat_lines (map (prefix "  " o print_file) files))))
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   277
  end;
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   278
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   279
fun export_generated_files_cmd ctxt args =
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   280
  export_generated_files ctxt (map (check_files_in ctxt) args);
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   281
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   282
75685
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   283
(* external files *)
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   284
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   285
fun check_external_files ctxt (raw_files, raw_base_dir) =
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   286
  let
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   287
    val base_dir = Resources.check_dir ctxt NONE raw_base_dir;
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   288
    fun check source =
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   289
     (Resources.check_file ctxt (SOME base_dir) source;
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   290
      Path.explode (Input.string_of source));
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   291
    val files = map check raw_files;
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   292
  in (files, base_dir) end;
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   293
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   294
fun get_external_files dir (files, base_dir) =
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   295
  files |> List.app (fn file => Isabelle_System.copy_file_base (base_dir, file) dir);
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   296
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   297
75686
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   298
(* scala_build_generated_files *)
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   299
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   300
fun scala_build_generated_files ctxt args external =
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   301
  Isabelle_System.with_tmp_dir "scala_build" (fn dir =>
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   302
    let
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   303
      val files = maps get_files_in args;
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   304
      val _ = List.app (fn (file, pos) => report_file ctxt pos file) files;
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   305
      val _ = List.app (write_file dir o #1) files;
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   306
      val _ = List.app (get_external_files dir) external;
75691
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   307
      val [jar_name, jar_bytes, output] =
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   308
        \<^scala>\<open>scala_build\<close> [Bytes.string (Isabelle_System.absolute_path dir)];
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   309
      val _ = writeln (Bytes.content output);
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   310
    in
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   311
      Export.export (Proof_Context.theory_of ctxt)
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   312
        (Path.explode_binding0 (Bytes.content jar_name))
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   313
        (Bytes.contents_blob jar_bytes)
041d7d633977 clarified modules;
wenzelm
parents: 75687
diff changeset
   314
    end);
75686
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   315
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   316
fun scala_build_generated_files_cmd ctxt args external =
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   317
  scala_build_generated_files ctxt
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   318
    (map (check_files_in ctxt) args)
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   319
    (map (check_external_files ctxt) external)
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   320
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   321
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   322
(* compile_generated_files *)
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   323
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   324
val compile_dir = Config.declare_string ("compile_dir", \<^here>) (K "");
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   325
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   326
fun with_compile_dir body : unit =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   327
  body (Path.explode (Config.get (Context.the_local_context ()) compile_dir));
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   328
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   329
fun compile_generated_files ctxt args external export export_prefix source =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   330
  Isabelle_System.with_tmp_dir "compile" (fn dir =>
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   331
    let
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   332
      val thy = Proof_Context.theory_of ctxt;
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   333
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   334
      val files = maps get_files_in args;
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   335
      val _ = List.app (fn (file, pos) => report_file ctxt pos file) files;
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   336
      val _ = List.app (write_file dir o #1) files;
75685
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   337
      val _ = List.app (get_external_files dir) external;
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   338
      val _ =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   339
        ML_Context.eval_in (SOME (Config.put compile_dir (Path.implode dir) ctxt))
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   340
          ML_Compiler.flags (Input.pos_of source)
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   341
          (ML_Lex.read "Generated_Files.with_compile_dir (" @
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   342
            ML_Lex.read_source source @ ML_Lex.read ")");
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   343
      val _ =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   344
        export |> List.app (fn (bindings, executable) =>
70053
997f256c98e3 proper .exe path for export;
wenzelm
parents: 70051
diff changeset
   345
          bindings |> List.app (fn binding0 =>
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   346
            let
70053
997f256c98e3 proper .exe path for export;
wenzelm
parents: 70051
diff changeset
   347
              val binding = binding0 |> Path.map_binding (executable = SOME true ? Path.exe);
997f256c98e3 proper .exe path for export;
wenzelm
parents: 70051
diff changeset
   348
              val (path, pos) = Path.dest_binding binding;
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   349
              val content =
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   350
                (case try Bytes.read (dir + path) of
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   351
                  SOME bytes => Bytes.contents_blob bytes
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   352
                | NONE => error ("Missing result file " ^ Path.print path ^ Position.here pos));
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   353
              val _ = Export.report_export thy export_prefix;
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   354
              val binding' =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   355
                Path.map_binding (Path.append (Path.path_of_binding export_prefix)) binding;
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   356
            in
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   357
              (if is_some executable then Export.export_executable else Export.export)
75604
39df30349778 more scalable generated files and code export, using Bytes.T;
wenzelm
parents: 74561
diff changeset
   358
                thy binding' content
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   359
            end));
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   360
      val _ =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   361
        if null export then ()
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   362
        else writeln (Export.message thy (Path.path_of_binding export_prefix));
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   363
    in () end);
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   364
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   365
fun compile_generated_files_cmd ctxt args external export export_prefix source =
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   366
  compile_generated_files ctxt
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   367
    (map (check_files_in ctxt) args)
75685
07cd3b243c69 clarified signature;
wenzelm
parents: 75683
diff changeset
   368
    (map (check_external_files ctxt) external)
70051
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   369
    ((map o apfst o map) Path.explode_binding export)
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   370
    (Path.explode_binding export_prefix)
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   371
    source;
7a4dc1e60dc8 added command 'compile_generated_files';
wenzelm
parents: 70049
diff changeset
   372
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   373
70067
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   374
(* execute compiler -- auxiliary *)
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   375
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   376
fun execute dir title compile =
74147
d030b988d470 provide bash_process server for Isabelle/ML and other external programs;
wenzelm
parents: 74142
diff changeset
   377
  Isabelle_System.bash_process (Bash.script compile |> Bash.cwd dir)
73279
37aff2142295 clarified signature;
wenzelm
parents: 72841
diff changeset
   378
  |> Process_Result.check
37aff2142295 clarified signature;
wenzelm
parents: 72841
diff changeset
   379
  |> Process_Result.out
70067
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   380
    handle ERROR msg =>
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   381
      let val (s, pos) = Input.source_content title
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   382
      in error (s ^ " failed" ^ Position.here pos ^ ":\n" ^ msg) end;
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   383
9b34dbeb1103 auxiliary operation for common uses of 'compile_generated_files';
wenzelm
parents: 70055
diff changeset
   384
70047
96fe857a7a6f clarified signature: more explicit operations for corresponding Isar commands;
wenzelm
parents: 70015
diff changeset
   385
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   386
(** concrete file types **)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   387
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   388
val _ =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   389
  Theory.setup
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   390
    (file_type \<^binding>\<open>Haskell\<close>
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   391
      {ext = "hs",
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   392
       make_comment = enclose "{-" "-}",
75683
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   393
       make_string = GHC.print_string} #>
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   394
     file_type \<^binding>\<open>Java\<close>
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   395
      {ext = "java",
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   396
       make_comment = enclose "/*" "*/",
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   397
       make_string = Java.print_string} #>
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   398
     file_type \<^binding>\<open>Scala\<close>
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   399
      {ext = "scala",
7ca63aea3c6c support more file types;
wenzelm
parents: 75604
diff changeset
   400
       make_comment = enclose "/*" "*/",
75686
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   401
       make_string = Java.print_string} #>
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   402
     file_type \<^binding>\<open>Properties\<close>
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   403
      {ext = "props",
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   404
       make_comment = enclose "#" "",
42f19e398ee4 command 'scala_build_generated_files' with proper management of source dependencies;
wenzelm
parents: 75685
diff changeset
   405
       make_string = I});
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   406
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   407
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   408
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   409
(** concrete antiquotations **)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   410
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   411
(* ML expression as string literal *)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   412
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   413
structure Local_Data = Proof_Data
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   414
(
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   415
  type T = string option;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   416
  fun init _ = NONE;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   417
);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   418
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   419
val set_string = Local_Data.put o SOME;
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   420
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   421
fun the_string ctxt =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   422
  (case Local_Data.get ctxt of
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   423
    SOME s => s
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   424
  | NONE => raise Fail "No result string");
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   425
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   426
val _ =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   427
  Theory.setup
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   428
    (antiquotation \<^binding>\<open>cartouche\<close> (Scan.lift Args.cartouche_input)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   429
      (fn {context = ctxt, file_type, argument, ...} =>
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   430
        ctxt |> Context.proof_map
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   431
          (ML_Context.expression (Input.pos_of argument)
69383
747f8b052e59 clarified modules;
wenzelm
parents: 69381
diff changeset
   432
            (ML_Lex.read "Theory.local_setup (Generated_Files.set_string (" @
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   433
             ML_Lex.read_source argument @ ML_Lex.read "))"))
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   434
        |> the_string |> #make_string file_type));
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   435
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   436
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   437
(* file-system paths *)
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   438
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   439
fun path_antiquotation binding check =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   440
  antiquotation binding
72841
fd8d82c4433b more accurate markup (refining 1c59b555ac4a);
wenzelm
parents: 72511
diff changeset
   441
    (Args.context -- Scan.lift Parse.path_input >>
fd8d82c4433b more accurate markup (refining 1c59b555ac4a);
wenzelm
parents: 72511
diff changeset
   442
      (fn (ctxt, source) => (check ctxt (SOME Path.current) source |> Path.implode)))
69381
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   443
    (fn {file_type, argument, ...} => #make_string file_type argument);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   444
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   445
val _ =
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   446
  Theory.setup
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   447
   (path_antiquotation \<^binding>\<open>path\<close> Resources.check_path #>
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   448
    path_antiquotation \<^binding>\<open>file\<close> Resources.check_file #>
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   449
    path_antiquotation \<^binding>\<open>dir\<close> Resources.check_dir);
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   450
4c9b4e2c5460 more general command 'generate_file' for registered file types, notably Haskell;
wenzelm
parents:
diff changeset
   451
end;