mlox/lib/lox.ml

67 lines
1.9 KiB
OCaml
Raw Normal View History

2024-08-02 00:10:48 +02:00
let ( let* ) = Result.bind
module Error = Error
2024-08-12 16:31:28 +02:00
module Expr = Expr
module Interpreter = Interpreter
2024-08-12 16:31:28 +02:00
module Lexer = Lexer
module Loxstd = Loxstd
2024-08-12 16:31:28 +02:00
module Parser = Parser
module Stmt = Stmt
2024-08-02 00:10:48 +02:00
type lox_error = Error.lox_error
let make_env_with_std () =
let env = Environment.Env.make () in
Loxstd.init_std env;
env
let run ?(env : Environment.environment option) ?(debug = false) (source : string) :
(unit, lox_error) result =
let env = Option.value env ~default:(make_env_with_std ()) in
2024-08-02 00:10:48 +02:00
let* tokens = Error.of_lexer_error (Lexer.tokenize source) in
let () =
if debug then
let print_tokens () =
prerr_endline "--- Tokens ---";
2024-08-27 20:32:05 +02:00
let f token = Printf.eprintf "%s %!" (Lexer.show_token token) in
Printf.eprintf "Got %d tokens\n%!" (List.length tokens);
List.iter f tokens;
prerr_newline ();
prerr_endline "--------------";
prerr_newline ()
in
print_tokens ()
else ()
in
2024-08-27 01:57:47 +02:00
let* stmts = Parser.parse tokens |> Error.of_parser_error in
let () =
if debug then
let print_statements () =
prerr_endline "--- Statements ---";
let f (stmt : Stmt.stmt_node) = prerr_endline (Stmt.show_stmt stmt.stmt) in
List.iter f stmts;
prerr_endline "------------------";
prerr_newline ()
in
print_statements ()
else ()
in
let rec interpret_stmts (stmts : Stmt.stmt_node list) =
match stmts with
| [] -> Ok ()
| stmt :: tail ->
2024-08-27 20:32:05 +02:00
let* () = Interpreter.interpret_stmt env stmt in
interpret_stmts tail
in
interpret_stmts stmts |> Error.of_runtimer_error
2024-08-02 00:10:48 +02:00
let runRepl ?(debug = false) () : unit =
let env = make_env_with_std () in
2024-08-02 00:10:48 +02:00
try
while true do
print_string "> ";
let line = read_line () in
let result = run ~env ~debug line in
Result.map_error Error.print_error result |> ignore
2024-08-02 00:10:48 +02:00
done
with End_of_file -> ()