blob: 2e5a435fece9755f6bb7514312a3b3007a52e31e (
plain)
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
|
fast parsing
------------
Some things are problably easy to implement efficiently:
typedef Date = ....
Here, typedef is read, then the parser learns that Date is a type, check
that the next symbol is a "=" and expects a type.
If the first symbol of a line is not a keyword, and not an paranthesis,
then it must be an identifier (valid or not). If we encounter one of those:
int age;
int make_timestamp(string iso_date);
then we assume that "int" must be a either a type of a value or a return
type of a function. Then second identifier must be a newly defined
identifier. In the second case, the identifier make_timestamp by "(" which
means it must be a function.
This logic can also be used in argument lists and in struct types.
Parsing code blocks:
These are variable declarations statements:
Type a; i i;
Type a = 0; i i = ...;
Type[T] a; i [ i ] i;
Pkg.Type a; i . i i;
or:
const type identifier
var type identifier
These are control statements:
if (...) ...
else ...
for (vardecl : ...) ...
for (...; ...; ...) ... // should we really have this one?
while (...) ...
do ... while (...);
switch (...) { case ...: ... case ...: ... }
switch (...) { case ...: ... case ...: ... default: ... }
break;
return;
return ...;
Everything else is an expression:
i
e[e]
e.i
e.i[e]
e +
+ e
e + e
(e)
e ? e : e
|