This repository was archived by the owner on Oct 4, 2020. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathlexer.mll
103 lines (89 loc) · 2.95 KB
/
lexer.mll
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
(* Analizador léxico *)
{
open Lexing
open Ast
open Parser
exception Lexing_error of string
let id_or_kwd =
let h = Hashtbl.create 32 in
List.iter (fun (s, tok) -> Hashtbl.add h s tok)
[
"type", TYPE;
"var", VAR;
"array", ARRAY;
"of", OF;
"filled", FILLED;
"by", BY;
"if", IF;
"then", THEN;
"else", ELSE;
"foreach", FOREACH;
"in", IN;
"do", DO;
"print", PRINT;
"size", SIZE;
"int", TINT
];
fun s -> try Hashtbl.find h s with Not_found -> IDENT s
let string_buffer = Buffer.create 1024
}
let letter = ['a'-'z' 'A'-'Z']
let digit = ['0'-'9']
let ident = letter (letter | digit | '_')*
let integer = ['0'-'9']+
let space = ' ' | '\t'
let comment = "//" [^'\n']*
rule next_tokens = parse
| (space | comment)+ { next_tokens lexbuf }
| '\n' { new_line lexbuf; next_tokens lexbuf }
| ident as id { [id_or_kwd id] }
| '.' { [DOT] }
| '+' { [PLUS] }
| '-' { [MINUS] }
| '*' { [TIMES] }
| '/' { [DIV] }
| "==" { [BINOP Bequal] }
| "!=" { [BINOP Bnotequal] }
| '=' { [EQUAL] }
| ':' { [COLON] }
| '(' { [LPARENT] }
| ')' { [RPARENT] }
| '[' { [LBRACKET] }
| ']' { [RBRACKET] }
| '{' { [LKEY] }
| '}' { [RKEY] }
| "<=" { [BINOP Bsmallerequal] }
| '<' { [BINOP Bsmaller] }
| ">=" { [BINOP Bbiggerequal] }
| '>' { [BINOP Bbigger] }
| ';' { [SEMICOLON] }
| integer as s { try [CONSTANT (Cint (Int64.of_string s))] with _ -> raise (Lexing_error ("constant too large: " ^ s)) }
| '"' { [CONSTANT (Cstring (string lexbuf))] }
| eof { [EOF] }
| _ as c { raise (Lexing_error ("illegal character: " ^ String.make 1 c)) }
and string = parse
| '"'
{ let s = Buffer.contents string_buffer in
Buffer.reset string_buffer;
s }
| "\\n"
{ Buffer.add_char string_buffer '\n';
string lexbuf }
| "\\\""
{ Buffer.add_char string_buffer '"';
string lexbuf }
| _ as c
{ Buffer.add_char string_buffer c;
string lexbuf }
| eof
{ raise (Lexing_error "unterminated string") }
{
let next_token =
let tokens = Queue.create () in (* próximos tokens por retornar *)
fun lb ->
if Queue.is_empty tokens then begin
let l = next_tokens lb in
List.iter (fun t -> Queue.add t tokens) l
end;
Queue.pop tokens
}