|
| 1 | +(* parse_tree.ml *) |
| 2 | + |
| 3 | +open Type |
| 4 | + |
| 5 | +(* literals *) |
| 6 | +type literal = |
| 7 | + | Null |
| 8 | + | Int of int |
| 9 | + | Bool of bool |
| 10 | + | String of string |
| 11 | +;; |
| 12 | + |
| 13 | +(* unary operators *) |
| 14 | +type una_op = |
| 15 | + | Not |
| 16 | +;; |
| 17 | + |
| 18 | +(* binary operators *) |
| 19 | +type bin_op = |
| 20 | + | Add |
| 21 | + | Sub |
| 22 | + | Mul |
| 23 | + | Div |
| 24 | + | Mod |
| 25 | + | Equal |
| 26 | + | NotEqual |
| 27 | + | LT |
| 28 | + | LTE |
| 29 | + | GT |
| 30 | + | GTE |
| 31 | +;; |
| 32 | + |
| 33 | +type ident_kind = |
| 34 | + | Variable |
| 35 | +;; |
| 36 | + |
| 37 | +module type expr = sig |
| 38 | + type t = ident_kind |
| 39 | +end |
| 40 | + |
| 41 | +(* expressions *) |
| 42 | +type expression = |
| 43 | + | Binary of bin_op * expression * expression |
| 44 | + | Unary of una_op * expression |
| 45 | + | Assign of string * expression (* dst, src *) |
| 46 | + | Call of expression * expression list |
| 47 | + | Ident of string * ident_kind |
| 48 | + | Literal of literal |
| 49 | +(* statements *) |
| 50 | +and statement = |
| 51 | + | Block of statement list |
| 52 | + | For of expression * expression * expression * statement list |
| 53 | + | Break |
| 54 | + | Continue |
| 55 | + | If of expression * statement list * statement list |
| 56 | + | Expression of expression |
| 57 | + | VarDecl of string * expression |
| 58 | + (* Function(id, ret datatype, param(id, datatype) list, statements) *) |
| 59 | + | Func of string * string * ((string * string) list) * statement list |
| 60 | + | Ret of expression |
| 61 | +(* program *) |
| 62 | +and program = { program: statement list } |
| 63 | +;; |
| 64 | + |
| 65 | + |
| 66 | +(* for metainfo *) |
| 67 | +type pos = { fname: string; lnum: int; bol: int; cnum: int };; |
| 68 | +type meta = { start_p: pos; end_p: pos };; |
| 69 | +let string_of_pos { fname = fn; lnum = ln; bol = bo; cnum = cn } = |
| 70 | + "(fname:" ^ fn ^ ", lnum:" ^ string_of_int ln ^ |
| 71 | + ", bol:" ^ string_of_int bo ^ ", cnum:" ^ string_of_int cn ^ ")" |
| 72 | +;; |
| 73 | +let string_of_meta { start_p = sp; end_p = ep } = |
| 74 | + "(start_p:" ^ string_of_pos sp ^ ", end_p:" ^ string_of_pos ep ^ ")" |
| 75 | +;; |
| 76 | + |
| 77 | + |
| 78 | + |
| 79 | +(* pretty printer for AST *) |
| 80 | +let strlit s = "\"" ^ s ^ "\"";; |
| 81 | +let prop pn valstr = |
| 82 | + strlit pn ^ ":" ^ valstr |
| 83 | +let kind s = prop "kind" (strlit s) |
| 84 | + |
| 85 | +let rec string_of_program pg = |
| 86 | + "{" ^ |
| 87 | + kind "Program" ^ "," ^ |
| 88 | + prop "program" ("[" ^ string_of_statement_list pg.program ^ "]") |
| 89 | + ^ "}" |
| 90 | +and string_of_statement statement = |
| 91 | + "{" ^ |
| 92 | + match statement with |
| 93 | + | Block (stmtlist) -> |
| 94 | + kind "Block" ^ "," ^ |
| 95 | + prop "statement_list" ("[" ^ string_of_statement_list stmtlist ^ "]") |
| 96 | + | For (init, cond, update, body) -> |
| 97 | + kind "For" ^ "," ^ |
| 98 | + prop "init" (string_of_expression init) ^ "," ^ |
| 99 | + prop "cond" (string_of_expression cond) ^ "," ^ |
| 100 | + prop "update" (string_of_expression update) ^ "," ^ |
| 101 | + prop "body" ("[" ^ string_of_statement_list body ^ "]") |
| 102 | + | Break -> |
| 103 | + kind "Break" |
| 104 | + | Continue -> |
| 105 | + kind "Continue" |
| 106 | + | If (exp, conseq, alter) -> |
| 107 | + kind "If" ^ "," ^ |
| 108 | + prop "condition" (string_of_expression exp) ^ "," ^ |
| 109 | + prop "conseq" ("[" ^ string_of_statement_list conseq ^ "]") ^ "," ^ |
| 110 | + prop "alter" ("[" ^ string_of_statement_list alter ^ "]") |
| 111 | + | Expression (exp) -> |
| 112 | + kind "Expression" ^ "," ^ |
| 113 | + prop "exp" (string_of_expression exp) |
| 114 | + | VarDecl (dst_id, src_exp) -> |
| 115 | + kind "VarDecl" ^ "," ^ |
| 116 | + prop "destination" (strlit dst_id) ^ "," ^ |
| 117 | + prop "source" (string_of_expression src_exp) |
| 118 | + | Func (id, t, params, stmts) -> |
| 119 | + kind "Func" ^ "," ^ |
| 120 | + prop "id" (strlit id) ^ "," ^ |
| 121 | + prop "type" (strlit t) ^ "," ^ |
| 122 | + prop "params" ("[" ^ string_of_param_list params ^ "]") ^ "," ^ |
| 123 | + prop "stmts" ("[" ^ string_of_statement_list stmts ^ "]") |
| 124 | + | Ret (exp) -> |
| 125 | + kind "Func" ^ "," ^ |
| 126 | + prop "exp" (string_of_expression exp) |
| 127 | + ; |
| 128 | + ^ "}" |
| 129 | +and string_of_statement_list stmtlist = |
| 130 | + match stmtlist with |
| 131 | + | [] -> "" |
| 132 | + | stmt :: stmtlist_ -> |
| 133 | + string_of_statement stmt ^ |
| 134 | + string_of_statement_list_ stmtlist_ |
| 135 | + ; |
| 136 | +and string_of_statement_list_ = function |
| 137 | + | [] -> "" |
| 138 | + | stmtlist -> "," ^ string_of_statement_list stmtlist |
| 139 | + ; |
| 140 | +and string_of_expression_list exprlist = |
| 141 | + match exprlist with |
| 142 | + | [] -> "" |
| 143 | + | expr :: exprlist_ -> |
| 144 | + string_of_expression expr ^ |
| 145 | + string_of_expression_list_ exprlist_ |
| 146 | + ; |
| 147 | +and string_of_expression_list_ = function |
| 148 | + | [] -> "" |
| 149 | + | exprlist -> "," ^ string_of_expression_list exprlist |
| 150 | + ; |
| 151 | +and string_of_expression exp = |
| 152 | + "{" ^ |
| 153 | + match exp with |
| 154 | + | Binary (op, left, right) -> |
| 155 | + kind "BinaryExp" ^ "," ^ |
| 156 | + prop "operator" (strlit (string_of_binop op)) ^ "," ^ |
| 157 | + prop "left" (string_of_expression left) ^ "," ^ |
| 158 | + prop "right" (string_of_expression right) |
| 159 | + | Unary (op, e) -> |
| 160 | + kind "UnaryExp" ^ "," ^ |
| 161 | + prop "operator" (strlit (string_of_unaop op)) ^ "," ^ |
| 162 | + prop "exp" (string_of_expression e) |
| 163 | + | Assign (dst, src) -> |
| 164 | + kind "AssignExp" ^ "," ^ |
| 165 | + prop "destination" (strlit dst) ^ "," ^ |
| 166 | + prop "source" (string_of_expression src) |
| 167 | + | Call (f, args) -> |
| 168 | + kind "CallExp" ^ "," ^ |
| 169 | + prop "f" (string_of_expression f) ^ "," ^ |
| 170 | + prop "args" ("[" ^ string_of_expression_list args ^ "]") |
| 171 | + | Ident (id, _) -> |
| 172 | + kind "Ident" ^ "," ^ |
| 173 | + prop "id" (strlit id) ^ "," ^ |
| 174 | + prop "ident_kind" (strlit "Variable") |
| 175 | + | Literal (lit) -> |
| 176 | + kind "Literal" ^ "," ^ |
| 177 | + prop "literal" (string_of_literal lit) |
| 178 | + ; |
| 179 | + ^ "}" |
| 180 | +and string_of_string_list = function |
| 181 | + | [] -> "" |
| 182 | + | str :: strlist -> |
| 183 | + strlit str ^ string_of_string_list_ strlist |
| 184 | +and string_of_string_list_ = function |
| 185 | + | [] -> "" |
| 186 | + | x -> "," ^ string_of_string_list x |
| 187 | +and string_of_param id t = |
| 188 | + "{" ^ |
| 189 | + kind "Param" ^ "," ^ |
| 190 | + prop "id" (strlit id) ^ "," ^ |
| 191 | + prop "type" (strlit t) |
| 192 | + ^ "}" |
| 193 | +and string_of_param_list = function |
| 194 | + | [] -> "" |
| 195 | + | (id, t) :: paramlist -> |
| 196 | + string_of_param id t ^ string_of_param_list_ paramlist |
| 197 | +and string_of_param_list_ = function |
| 198 | + | [] -> "" |
| 199 | + | x -> "," ^ string_of_param_list x |
| 200 | +and string_of_binop = function |
| 201 | + | Add -> "add" |
| 202 | + | Sub -> "sub" |
| 203 | + | Mul -> "mul" |
| 204 | + | Div -> "div" |
| 205 | + | Mod -> "mod" |
| 206 | + | Equal -> "equal" |
| 207 | + | NotEqual -> "not equal" |
| 208 | + | LT -> "less than" |
| 209 | + | LTE -> "less than equal" |
| 210 | + | GT -> "greater than" |
| 211 | + | GTE -> "greater than equal" |
| 212 | +and string_of_unaop = function |
| 213 | + | Not -> "not" |
| 214 | +and string_of_literal lit = |
| 215 | + "{" ^ |
| 216 | + match lit with |
| 217 | + | Null -> |
| 218 | + kind "Null" |
| 219 | + | Int (num) -> |
| 220 | + kind "Int" ^ "," ^ |
| 221 | + prop "num" (string_of_int num) |
| 222 | + | Bool (b) -> |
| 223 | + kind "Bool" ^ "," ^ |
| 224 | + prop "bool" (string_of_bool b) |
| 225 | + | String (str) -> |
| 226 | + kind "String" ^ "," ^ |
| 227 | + prop "str" (strlit str) |
| 228 | + ; |
| 229 | + ^ "}" |
| 230 | +;; |
| 231 | + |
| 232 | + |
| 233 | + |
0 commit comments