nand2tetris/compiler/lib/be_translate.ml

66 lines
1.5 KiB
OCaml
Raw Normal View History

2022-08-03 13:04:42 +00:00
open Base
open Be_ast
open Be_predef
let parse s =
let lexbuf = Lexing.from_string s in
let ast = Be_parser.prog Be_lexer.read lexbuf in
ast
;;
let generate_exprs lines = List.map lines ~f:parse
2022-08-04 15:29:46 +00:00
let a_command loc a =
let suffix = Int.to_string loc in
match a with
| "add" -> _add
| "sub" -> _sub
| "neg" -> _neg
| "eq" -> _eq suffix
| "gt" -> _gt suffix
| "lt" -> _lt suffix
| "and" -> _and
| "or" -> _or
| "not" -> _not
| _ -> failwith "a_command: Invalid Command"
;;
let process_push cn sp a =
match sp with
| "local" | "argument" | "this" | "that" -> push_common a sp
| "constant" -> push_constant a
| "temp" -> push_temp a
| "static" -> push_static a cn
| "pointer" -> push_pointer a
| _ -> failwith "PROCESS PUSH: Invalid Segment"
;;
let process_pop cn sp a =
match sp with
| "local" | "argument" | "this" | "that" -> pop_common a sp
| "temp" -> pop_temp a
| "static" -> pop_static a cn
| "pointer" -> pop_pointer a
| _ -> failwith "PROCESS POP: Invalid Segment"
;;
let m_command cn (c, s, a) =
match c with
| "pop" -> process_pop cn s a
| "push" -> process_push cn s a
| _ -> failwith "m_command: Invalid Command"
;;
let rec _translate expr cn loc tt =
2022-08-03 13:04:42 +00:00
match expr with
| [] -> tt
2022-08-04 15:29:46 +00:00
| Acommand a :: t -> a_command loc a @ _translate t cn (loc + 1) tt
| Mcommand (c, s, a) :: t -> m_command cn (c, s, a) @ _translate t cn loc tt
| _ :: t -> _translate t cn loc tt
2022-08-03 13:04:42 +00:00
;;
2022-08-04 15:29:46 +00:00
let translate cn lines =
2022-08-03 13:04:42 +00:00
let exprs = generate_exprs lines in
2022-08-04 15:29:46 +00:00
_translate exprs cn 0 [] @ _end
2022-08-03 13:04:42 +00:00
;;