1
1
let name = " wasm"
2
- let version = " 0.1 "
2
+ let version = " 0.2 "
3
3
4
- let load file =
5
- let f = open_in file in
6
- let size = in_channel_length f + 1 in
7
- let buf = Bytes. create size in
8
- let rec loop () =
9
- let len = input f buf 0 size in
10
- let source = Bytes. sub_string buf 0 len in
11
- if len == 0 then source else source ^ loop ()
12
- in
13
- let source = loop () in
14
- close_in f;
15
- source
4
+ let banner () =
5
+ print_endline (name ^ " " ^ version ^ " spec interpreter" )
16
6
17
- let parse name source =
18
- let lexbuf = Lexing. from_string source in
7
+ let parse name lexbuf start =
19
8
lexbuf.Lexing. lex_curr_p < -
20
9
{lexbuf.Lexing. lex_curr_p with Lexing. pos_fname = name};
21
- try Parser. script Lexer. token lexbuf with Script. Syntax (region , s ) ->
10
+ try start Lexer. token lexbuf with Script. Syntax (region , s ) ->
22
11
let region' = if region <> Source. no_region then region else
23
12
{Source. left = Lexer. convert_pos lexbuf.Lexing. lex_start_p;
24
13
Source. right = Lexer. convert_pos lexbuf.Lexing. lex_curr_p} in
@@ -29,10 +18,9 @@ let error at category msg =
29
18
prerr_endline (Source. string_of_region at ^ " : " ^ msg);
30
19
false
31
20
32
- let process file source =
21
+ let process file lexbuf start =
33
22
try
34
- Script. trace " Parsing..." ;
35
- let script = parse file source in
23
+ let script = parse file lexbuf start in
36
24
Script. trace " Desugaring..." ;
37
25
let script' = Script. desugar script in
38
26
Script. trace " Running..." ;
@@ -48,21 +36,44 @@ let process file source =
48
36
49
37
let process_file file =
50
38
Script. trace (" Loading (" ^ file ^ " )..." );
51
- let source = load file in
52
- if not (process file source) then exit 1
39
+ let ic = open_in file in
40
+ try
41
+ let lexbuf = Lexing. from_channel ic in
42
+ Script. trace " Parsing..." ;
43
+ let success = process file lexbuf Parser. script in
44
+ close_in ic;
45
+ if not success then exit 1
46
+ with exn -> close_in ic; raise exn
47
+
48
+ let continuing = ref false
49
+
50
+ let lexbuf_stdin buf len =
51
+ let prompt = if ! continuing then " " else " > " in
52
+ print_string prompt; flush_all () ;
53
+ continuing := true ;
54
+ let rec loop i =
55
+ if i = len then i else
56
+ let ch = input_char stdin in
57
+ Bytes. set buf i ch;
58
+ if ch = '\n' then i + 1 else loop (i + 1 )
59
+ in
60
+ let n = loop 0 in
61
+ if n = 1 then continuing := false else Script. trace " Parsing..." ;
62
+ n
53
63
54
64
let rec process_stdin () =
55
- print_string (name ^ " > " ); flush_all () ;
56
- match try Some (input_line stdin) with End_of_file -> None with
57
- | None ->
65
+ banner () ;
66
+ let lexbuf = Lexing. from_function lexbuf_stdin in
67
+ let rec loop () =
68
+ let success = process " stdin" lexbuf Parser. script1 in
69
+ if not success then Lexing. flush_input lexbuf;
70
+ if Lexing. (lexbuf.lex_curr_pos > = lexbuf.lex_buffer_len - 1 ) then
71
+ continuing := false ;
72
+ loop ()
73
+ in
74
+ try loop () with End_of_file ->
58
75
print_endline " " ;
59
76
Script. trace " Bye."
60
- | Some source ->
61
- ignore (process " stdin" source);
62
- process_stdin ()
63
-
64
- let greet () =
65
- print_endline (" Version " ^ version)
66
77
67
78
let usage = " Usage: " ^ name ^ " [option] [file ...]"
68
79
let argspec = Arg. align
@@ -72,7 +83,7 @@ let argspec = Arg.align
72
83
" -s" , Arg. Set Flags. print_sig, " show module signatures" ;
73
84
" -d" , Arg. Set Flags. dry, " dry, do not run program" ;
74
85
" -t" , Arg. Set Flags. trace, " trace execution" ;
75
- " -v" , Arg. Unit greet , " show version"
86
+ " -v" , Arg. Unit banner , " show version"
76
87
]
77
88
78
89
let () =
@@ -84,7 +95,7 @@ let () =
84
95
List. iter process_file ! files;
85
96
if ! Flags. interactive then process_stdin ()
86
97
with exn ->
87
- flush stdout ;
98
+ flush_all () ;
88
99
prerr_endline
89
100
(Sys. argv.(0 ) ^ " : uncaught exception " ^ Printexc. to_string exn );
90
101
Printexc. print_backtrace stderr;
0 commit comments