7 signature THY_LOAD = |
7 signature THY_LOAD = |
8 sig |
8 sig |
9 val master_directory: theory -> Path.T |
9 val master_directory: theory -> Path.T |
10 val imports_of: theory -> (string * Position.T) list |
10 val imports_of: theory -> (string * Position.T) list |
11 val thy_path: Path.T -> Path.T |
11 val thy_path: Path.T -> Path.T |
|
12 val read_files: Path.T -> string -> Path.T * Position.T -> Token.file list |
12 val parse_files: string -> (theory -> Token.file list) parser |
13 val parse_files: string -> (theory -> Token.file list) parser |
13 val check_thy: Path.T -> string -> |
14 val check_thy: Path.T -> string -> |
14 {master: Path.T * SHA1.digest, text: string, theory_pos: Position.T, |
15 {master: Path.T * SHA1.digest, text: string, theory_pos: Position.T, |
15 imports: (string * Position.T) list, keywords: Thy_Header.keywords} |
16 imports: (string * Position.T) list, keywords: Thy_Header.keywords} |
16 val provide: Path.T * SHA1.digest -> theory -> theory |
17 val provide: Path.T * SHA1.digest -> theory -> theory |
53 val imports_of = #imports o Files.get; |
54 val imports_of = #imports o Files.get; |
54 |
55 |
55 fun put_deps master_dir imports = map_files (fn _ => (master_dir, imports, [])); |
56 fun put_deps master_dir imports = map_files (fn _ => (master_dir, imports, [])); |
56 |
57 |
57 |
58 |
58 (* inlined files *) |
59 (* auxiliary files *) |
59 |
60 |
60 fun check_file dir file = File.check_file (File.full_path dir file); |
61 fun check_file dir file = File.check_file (File.full_path dir file); |
61 |
62 |
62 fun read_files cmd dir (path, pos) = |
63 fun read_files dir cmd (path, pos) = |
63 let |
64 let |
64 fun make_file file = |
65 fun make_file file = |
65 let |
66 let |
66 val _ = Position.report pos (Markup.path (Path.implode file)); |
67 val _ = Position.report pos (Markup.path (Path.implode file)); |
67 val full_path = check_file dir file; |
68 val full_path = check_file dir file; |
74 |
75 |
75 fun parse_files cmd = |
76 fun parse_files cmd = |
76 Scan.ahead Parse.not_eof -- Parse.path >> (fn (tok, name) => fn thy => |
77 Scan.ahead Parse.not_eof -- Parse.path >> (fn (tok, name) => fn thy => |
77 (case Token.get_files tok of |
78 (case Token.get_files tok of |
78 SOME files => files |
79 SOME files => files |
79 | NONE => read_files cmd (master_directory thy) (Path.explode name, Token.position_of tok))); |
80 | NONE => read_files (master_directory thy) cmd (Path.explode name, Token.position_of tok))); |
80 |
81 |
81 local |
82 |
82 |
83 (* theory files *) |
83 fun clean ((i1, t1) :: (i2, t2) :: toks) = |
|
84 if Token.keyword_with (fn s => s = "%" orelse s = "--") t1 then clean toks |
|
85 else (i1, t1) :: clean ((i2, t2) :: toks) |
|
86 | clean toks = toks; |
|
87 |
|
88 fun clean_tokens toks = |
|
89 ((0 upto length toks - 1) ~~ toks) |
|
90 |> filter (fn (_, tok) => Token.is_proper tok) |
|
91 |> clean; |
|
92 |
|
93 fun find_file toks = |
|
94 rev (clean_tokens toks) |> get_first (fn (i, tok) => |
|
95 if Token.is_name tok then |
|
96 SOME (i, (Path.explode (Token.content_of tok), Token.position_of tok)) |
|
97 handle ERROR msg => error (msg ^ Token.pos_of tok) |
|
98 else NONE); |
|
99 |
|
100 in |
|
101 |
|
102 fun resolve_files master_dir span = |
|
103 (case span of |
|
104 Thy_Syntax.Span (Thy_Syntax.Command (cmd, pos), toks) => |
|
105 if Keyword.is_theory_load cmd then |
|
106 (case find_file toks of |
|
107 NONE => error ("Bad file argument of command " ^ quote cmd ^ Position.here pos) |
|
108 | SOME (i, path) => |
|
109 let |
|
110 val toks' = toks |> map_index (fn (j, tok) => |
|
111 if i = j then Token.put_files (read_files cmd master_dir path) tok |
|
112 else tok); |
|
113 in Thy_Syntax.Span (Thy_Syntax.Command (cmd, pos), toks') end) |
|
114 else span |
|
115 | span => span); |
|
116 |
|
117 end; |
|
118 |
|
119 |
|
120 (* check files *) |
|
121 |
84 |
122 val thy_path = Path.ext "thy"; |
85 val thy_path = Path.ext "thy"; |
123 |
86 |
124 fun check_thy dir thy_name = |
87 fun check_thy dir thy_name = |
125 let |
88 let |
211 |> Present.begin_theory update_time master_dir; |
174 |> Present.begin_theory update_time master_dir; |
212 |
175 |
213 val lexs = Keyword.get_lexicons (); |
176 val lexs = Keyword.get_lexicons (); |
214 |
177 |
215 val toks = Thy_Syntax.parse_tokens lexs text_pos text; |
178 val toks = Thy_Syntax.parse_tokens lexs text_pos text; |
216 val spans = map (resolve_files master_dir) (Thy_Syntax.parse_spans toks); |
179 val spans = map (Thy_Syntax.resolve_files (read_files master_dir)) (Thy_Syntax.parse_spans toks); |
217 val elements = Thy_Syntax.parse_elements spans; |
180 val elements = Thy_Syntax.parse_elements spans; |
218 |
181 |
219 val _ = Present.theory_source name |
182 val _ = Present.theory_source name |
220 (fn () => HTML.html_mode (implode o map Thy_Syntax.present_span) spans); |
183 (fn () => HTML.html_mode (implode o map Thy_Syntax.present_span) spans); |
221 |
184 |