来自于《Let's Build A Compiler!》
1 // parse program
2
3 #include <iostream>
4 #include <cstdlib>
5 #include <cstdio>
6 #include <string>
7 using namespace std;
8
9 const char TAB = '\t';
10 const char CR = '\r';
11 const char NL = '\n';
12
13 char look;
14 void getChar()
15 {
16 look = getchar();
17 }
18
19 void myError(const string& s)
20 {
21 cerr << endl << "Error: " << s << '.' << endl;
22 }
23
24 void myAbort(const string& s)
25 {
26 myError(s);
27 exit(1);
28 }
29
30 void myExpected(const string& s)
31 {
32 myAbort(s + " Expected");
33 }
34
35 void skipWhite();
36
37 void myMatch(char x)
38 {
39 if (look != x)
40 {
41 myExpected(string(" ") + x + string(" "));
42 }
43 else
44 {
45 getChar();
46 skipWhite();
47 }
48 }
49
50 bool isAlpha(char c)
51 {
52 return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z');
53 }
54
55 bool isDigit(char c)
56 {
57 return c >= '0' && c <= '9';
58 }
59
60 bool isAlphaDigit(char c)
61 {
62 return isAlpha(c) || isDigit(c);
63 }
64
65 bool isAddop(char c)
66 {
67 return c == '+' || c == '-';
68 }
69
70 bool isWhite(char c)
71 {
72 return c == ' ' || c == '\t';
73 }
74
75 void skipWhite()
76 {
77 while (isWhite(look))
78 {
79 getChar();
80 }
81 }
82
83 char upCase(char x)
84 {
85 if (x >= 'a' && x <= 'z')
86 {
87 x = x - 'a' + 'A';
88 }
89 return x;
90 }
91
92 string getName()
93 {
94 string token;
95 if (!isAlpha(look))
96 {
97 myExpected("Name!");
98 }
99 while (isAlphaDigit(look))
100 {
101 token += upCase(look);
102 getChar();
103 }
104 skipWhite();
105 return token;
106 }
107
108 string getNum()
109 {
110 string value;
111 if (!isDigit(look))
112 {
113 myExpected("Interger!");
114 }
115 while (isDigit(look))
116 {
117 value += look;
118 getChar();
119 }
120 skipWhite();
121 return value;
122 }
123
124 void write(const string& s)
125 {
126 cout << s;
127 }
128
129 void emit(const string& s)
130 {
131 write('\t' + s);
132 }
133
134 void emitLine(const string& s)
135 {
136 emit(s);
137 cout << endl;
138 }
139
140 void init()
141 {
142 getChar();
143 skipWhite();
144 }
145
146 void ident()
147 {
148 string name = getName();
149 if (look == '(')
150 {
151 myMatch('(');
152 myMatch(')');
153 emitLine(string("BSR ") + name);
154 }
155 else
156 {
157 emitLine(string("MOVE ") + name + string("(PC), D0"));
158 }
159 }
160
161 void expression();
162
163 void factor()
164 {
165 if (look == '(')
166 {
167 myMatch('(');
168 expression();
169 myMatch(')');
170 }
171 else if (isAlpha(look))
172 {
173 ident();
174 }
175 else
176 {
177 emitLine(string("MOVE #") + getNum() + string(", DO"));
178 }
179 }
180
181 void multiply()
182 {
183 myMatch('*');
184 factor();
185 emitLine("MULS (SP)+, DO");
186 }
187
188 void divide()
189 {
190 myMatch('/');
191 factor();
192 emitLine("MOVE (SP)+, D1");
193 emitLine("EXS .L D0");
194 emitLine("DIVS D1, D0");
195 }
196
197 void term()
198 {
199 factor();
200 while (look == '*' || look == '/')
201 {
202 emitLine("MOVE D0, -(SP)");
203 switch (look)
204 {
205 case '*':
206 multiply();
207 break;
208 case '/':
209 divide();
210 break;
211 default:
212 myExpected("Mulop");
213 break;
214 }
215 }
216 // emitLine(string("MOVE #") + getNum() + string(", D0"));
217 }
218
219 void add()
220 {
221 myMatch('+');
222 term();
223 emitLine("ADD (SP)+, D0");
224 }
225
226 void subtract()
227 {
228 myMatch('-');
229 term();
230 emitLine("SUB (SP)+, D0");
231 emitLine("NEG D0");
232 }
233
234 void expression()
235 {
236 if (isAddop(look))
237 {
238 emitLine("CLR D0");
239 }
240 else
241 {
242 term();
243 }
244 while (isAddop(look))
245 {
246 emitLine("MOVE D0 -(SP)");
247 switch (look)
248 {
249 case '+':
250 add();
251 break;
252 case '-':
253 subtract();
254 break;
255 default:
256 myExpected("Addop");
257 break;
258 }
259 }
260 }
261
262 void assignment()
263 {
264 string name = getName();
265 myMatch('=');
266 expression();
267 emitLine(string("LEA ") + name + string("(PC), A0"));
268 emitLine("MOVE D0, (A0)");
269 }
270
271 int main()
272 {
273 init();
274 // expression();
275 assignment();
276 if (look != NL)
277 {
278 myExpected("Newline!");
279 }
280 return 0;
281 }
posted on 2011-12-27 17:36
unixfy 阅读(245)
评论(0) 编辑 收藏 引用