4 Prover command execution: read -- eval -- print. |
4 Prover command execution: read -- eval -- print. |
5 *) |
5 *) |
6 |
6 |
7 signature COMMAND = |
7 signature COMMAND = |
8 sig |
8 sig |
9 val read: (unit -> theory) -> Token.T list -> Toplevel.transition |
9 type blob = (string * string option) Exn.result |
|
10 val read_file: Path.T -> Position.T -> Path.T -> Token.file |
|
11 val read: (unit -> theory) -> Path.T -> blob list -> Token.T list -> Toplevel.transition |
10 type eval |
12 type eval |
11 val eval_eq: eval * eval -> bool |
13 val eval_eq: eval * eval -> bool |
12 val eval_running: eval -> bool |
14 val eval_running: eval -> bool |
13 val eval_finished: eval -> bool |
15 val eval_finished: eval -> bool |
14 val eval_result_state: eval -> Toplevel.state |
16 val eval_result_state: eval -> Toplevel.state |
15 val eval: (unit -> theory) -> Token.T list -> eval -> eval |
17 val eval: (unit -> theory) -> Path.T -> blob list -> Token.T list -> eval -> eval |
16 type print |
18 type print |
17 val print: bool -> (string * string list) list -> string -> |
19 val print: bool -> (string * string list) list -> string -> |
18 eval -> print list -> print list option |
20 eval -> print list -> print list option |
19 type print_fn = Toplevel.transition -> Toplevel.state -> unit |
21 type print_fn = Toplevel.transition -> Toplevel.state -> unit |
20 type print_function = |
22 type print_function = |
82 |
84 |
83 (** main phases of execution **) |
85 (** main phases of execution **) |
84 |
86 |
85 (* read *) |
87 (* read *) |
86 |
88 |
87 fun read init span = |
89 type blob = (string * string option) Exn.result; (*file node name, digest or text*) |
|
90 |
|
91 fun read_file master_dir pos src_path = |
|
92 let |
|
93 val full_path = File.check_file (File.full_path master_dir src_path); |
|
94 val _ = Position.report pos (Markup.path (Path.implode full_path)); |
|
95 in {src_path = src_path, text = File.read full_path, pos = Path.position full_path} end; |
|
96 |
|
97 fun resolve_files master_dir blobs toks = |
|
98 (case Thy_Syntax.parse_spans toks of |
|
99 [span] => span |
|
100 |> Thy_Syntax.resolve_files (fn cmd => fn (path, pos) => |
|
101 let |
|
102 fun make_file src_path (Exn.Res (_, NONE)) = |
|
103 Exn.interruptible_capture (fn () => read_file master_dir pos src_path) () |
|
104 | make_file src_path (Exn.Res (file, SOME text)) = |
|
105 let val _ = Position.report pos (Markup.path file) |
|
106 in Exn.Res {src_path = src_path, text = text, pos = Position.file file} end |
|
107 | make_file _ (Exn.Exn e) = Exn.Exn e; |
|
108 |
|
109 val src_paths = Keyword.command_files cmd path; |
|
110 in |
|
111 if null blobs then |
|
112 map2 make_file src_paths (map (K (Exn.Res ("", NONE))) src_paths) |
|
113 else if length src_paths = length blobs then |
|
114 map2 make_file src_paths blobs |
|
115 else error ("Misalignment of inlined files" ^ Position.here pos) |
|
116 end) |
|
117 |> Thy_Syntax.span_content |
|
118 | _ => toks); |
|
119 |
|
120 fun read init master_dir blobs span = |
88 let |
121 let |
89 val outer_syntax = #2 (Outer_Syntax.get_syntax ()); |
122 val outer_syntax = #2 (Outer_Syntax.get_syntax ()); |
90 val command_reports = Outer_Syntax.command_reports outer_syntax; |
123 val command_reports = Outer_Syntax.command_reports outer_syntax; |
91 |
124 |
92 val proper_range = |
125 val proper_range = |
99 val (is_malformed, token_reports) = Thy_Syntax.reports_of_tokens span; |
132 val (is_malformed, token_reports) = Thy_Syntax.reports_of_tokens span; |
100 val _ = Position.reports_text (token_reports @ maps command_reports span); |
133 val _ = Position.reports_text (token_reports @ maps command_reports span); |
101 in |
134 in |
102 if is_malformed then Toplevel.malformed pos "Malformed command syntax" |
135 if is_malformed then Toplevel.malformed pos "Malformed command syntax" |
103 else |
136 else |
104 (case Outer_Syntax.read_spans outer_syntax span of |
137 (case Outer_Syntax.read_spans outer_syntax (resolve_files master_dir blobs span) of |
105 [tr] => |
138 [tr] => |
106 if Keyword.is_control (Toplevel.name_of tr) then |
139 if Keyword.is_control (Toplevel.name_of tr) then |
107 Toplevel.malformed pos "Illegal control command" |
140 Toplevel.malformed pos "Illegal control command" |
108 else Toplevel.modify_init init tr |
141 else Toplevel.modify_init init tr |
109 | [] => Toplevel.ignored (Position.set_range (Token.position_range_of span)) |
142 | [] => Toplevel.ignored (Position.set_range (Token.position_range_of span)) |
181 in {failed = false, malformed = malformed', command = tr, state = st'} end) |
214 in {failed = false, malformed = malformed', command = tr, state = st'} end) |
182 end; |
215 end; |
183 |
216 |
184 in |
217 in |
185 |
218 |
186 fun eval init span eval0 = |
219 fun eval init master_dir blobs span eval0 = |
187 let |
220 let |
188 val exec_id = Document_ID.make (); |
221 val exec_id = Document_ID.make (); |
189 fun process () = |
222 fun process () = |
190 let |
223 let |
191 val tr = |
224 val tr = |
192 Position.setmp_thread_data (Position.id_only (Document_ID.print exec_id)) |
225 Position.setmp_thread_data (Position.id_only (Document_ID.print exec_id)) |
193 (fn () => read init span |> Toplevel.exec_id exec_id) (); |
226 (fn () => read init master_dir blobs span |> Toplevel.exec_id exec_id) (); |
194 in eval_state span tr (eval_result eval0) end; |
227 in eval_state span tr (eval_result eval0) end; |
195 in Eval {exec_id = exec_id, eval_process = memo exec_id process} end; |
228 in Eval {exec_id = exec_id, eval_process = memo exec_id process} end; |
196 |
229 |
197 end; |
230 end; |
198 |
231 |