comparison Bison-Flex/BasicCompiler-MemoryBase/vm.h @ 4:805d39d28230

add Compiler-stackbase
author nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
date Tue, 17 May 2011 08:00:38 +0900
parents
children
comparison
equal deleted inserted replaced
3:3cea2e8a0e4b 4:805d39d28230
1 #ifndef __VM_H__
2 #define __VM_H__
3
4 #include <vector>
5 #include "vm_value.h"
6
7 #define VM_ENUMDEF
8 enum {
9 #include "vm_code.h"
10 VM_MAXCOMMAND,
11 } ;
12 #undef VM_ENUMDEF
13
14 namespace vm {
15
16 class data {
17 public:
18 data(): command_(0)
19 {
20 }
21 ~data()
22 {
23 delete[] command_;
24 }
25
26 public:
27 unsigned char *command_; // コマンドテーブル
28 int command_size_; // コマンドサイズ
29 int value_size_; // グローバル変数サイズ
30 } ;
31
32 // 0除算例外
33 class devide_by_zero: public std::exception {
34 public:
35 const char *what() const throw()
36 {
37 return "devide by zero";
38 }
39 } ;
40
41 // 仮想マシン
42 class vcpu {
43 public:
44 const static int STACK_SIZE = 1000;
45
46 public:
47 vcpu(data &mem)
48 : data_(mem)
49 {
50 }
51 ~vcpu()
52 {
53 }
54
55 int run();
56
57 private:
58 // 定数Push
59 void PushConst(int value)
60 {
61 push(value);
62 }
63
64 // 変数Push
65 void PushValue(int value)
66 {
67 push(global_value[value]);
68 }
69
70 // 変数にPop
71 void PopValue(int value)
72 {
73 global_value[value] = top(); pop();
74 }
75
76 // 空Pop(スタックトップを捨てる)
77 void OpPop()
78 {
79 pop();
80 }
81
82 // 代入
83 void OpMovC(int result, int arg)
84 {
85 global_value[result] = arg;
86 }
87
88 void OpMovV(int result, int arg)
89 {
90 global_value[result] = global_value[arg];
91 }
92
93 // 単項マイナス
94 void OpNegC(int result, int arg)
95 {
96 global_value[result] = -arg;
97 }
98
99 void OpNegV(int result, int arg)
100 {
101 global_value[result] = -global_value[arg];
102 }
103
104 // ==
105 void OpEqCC(int result, int arg1, int arg2)
106 {
107 global_value[result] = arg1 == arg2;
108 }
109
110 void OpEqVC(int result, int arg1, int arg2)
111 {
112 global_value[result] = global_value[arg1] == arg2;
113 }
114
115 void OpEqCV(int result, int arg1, int arg2)
116 {
117 global_value[result] = arg1 == global_value[arg2];
118 }
119
120 void OpEqVV(int result, int arg1, int arg2)
121 {
122 global_value[result] = global_value[arg1] == global_value[arg2];
123 }
124
125 // !=
126 void OpNeCC(int result, int arg1, int arg2)
127 {
128 global_value[result] = arg1 != arg2;
129 }
130
131 void OpNeVC(int result, int arg1, int arg2)
132 {
133 global_value[result] = global_value[arg1] != arg2;
134 }
135
136 void OpNeCV(int result, int arg1, int arg2)
137 {
138 global_value[result] = arg1 != global_value[arg2];
139 }
140
141 void OpNeVV(int result, int arg1, int arg2)
142 {
143 global_value[result] = global_value[arg1] != global_value[arg2];
144 }
145
146 // >
147 void OpGtCC(int result, int arg1, int arg2)
148 {
149 global_value[result] = arg1 > arg2;
150 }
151
152 void OpGtVC(int result, int arg1, int arg2)
153 {
154 global_value[result] = global_value[arg1] > arg2;
155 }
156
157 void OpGtCV(int result, int arg1, int arg2)
158 {
159 global_value[result] = arg1 > global_value[arg2];
160 }
161
162 void OpGtVV(int result, int arg1, int arg2)
163 {
164 global_value[result] = global_value[arg1] > global_value[arg2];
165 }
166
167 // >=
168 void OpGeCC(int result, int arg1, int arg2)
169 {
170 global_value[result] = arg1 >= arg2;
171 }
172
173 void OpGeVC(int result, int arg1, int arg2)
174 {
175 global_value[result] = global_value[arg1] >= arg2;
176 }
177
178 void OpGeCV(int result, int arg1, int arg2)
179 {
180 global_value[result] = arg1 >= global_value[arg2];
181 }
182
183 void OpGeVV(int result, int arg1, int arg2)
184 {
185 global_value[result] = global_value[arg1] >= global_value[arg2];
186 }
187
188 // <
189 void OpLtCC(int result, int arg1, int arg2)
190 {
191 global_value[result] = arg1 < arg2;
192 }
193
194 void OpLtVC(int result, int arg1, int arg2)
195 {
196 global_value[result] = global_value[arg1] < arg2;
197 }
198
199 void OpLtCV(int result, int arg1, int arg2)
200 {
201 global_value[result] = arg1 < global_value[arg2];
202 }
203
204 void OpLtVV(int result, int arg1, int arg2)
205 {
206 global_value[result] = global_value[arg1] < global_value[arg2];
207 }
208
209 // <=
210 void OpLeCC(int result, int arg1, int arg2)
211 {
212 global_value[result] = arg1 <= arg2;
213 }
214
215 void OpLeVC(int result, int arg1, int arg2)
216 {
217 global_value[result] = global_value[arg1] <= arg2;
218 }
219
220 void OpLeCV(int result, int arg1, int arg2)
221 {
222 global_value[result] = arg1 <= global_value[arg2];
223 }
224
225 void OpLeVV(int result, int arg1, int arg2)
226 {
227 global_value[result] = global_value[arg1] <= global_value[arg2];
228 }
229
230 // +
231 void OpAddCC(int result, int arg1, int arg2)
232 {
233 global_value[result] = arg1 + arg2;
234 }
235
236 void OpAddVC(int result, int arg1, int arg2)
237 {
238 global_value[result] = global_value[arg1] + arg2;
239 }
240
241 void OpAddCV(int result, int arg1, int arg2)
242 {
243 global_value[result] = arg1 + global_value[arg2];
244 }
245
246 void OpAddVV(int result, int arg1, int arg2)
247 {
248 global_value[result] = global_value[arg1] + global_value[arg2];
249 }
250
251 // -
252 void OpSubCC(int result, int arg1, int arg2)
253 {
254 global_value[result] = arg1 - arg2;
255 }
256
257 void OpSubVC(int result, int arg1, int arg2)
258 {
259 global_value[result] = global_value[arg1] - arg2;
260 }
261
262 void OpSubCV(int result, int arg1, int arg2)
263 {
264 global_value[result] = arg1 - global_value[arg2];
265 }
266
267 void OpSubVV(int result, int arg1, int arg2)
268 {
269 global_value[result] = global_value[arg1] - global_value[arg2];
270 }
271
272 // *
273 void OpMulCC(int result, int arg1, int arg2)
274 {
275 global_value[result] = arg1 * arg2;
276 }
277
278 void OpMulVC(int result, int arg1, int arg2)
279 {
280 global_value[result] = global_value[arg1] * arg2;
281 }
282
283 void OpMulCV(int result, int arg1, int arg2)
284 {
285 global_value[result] = arg1 * global_value[arg2];
286 }
287
288 void OpMulVV(int result, int arg1, int arg2)
289 {
290 global_value[result] = global_value[arg1] * global_value[arg2];
291 }
292
293 // /
294 void OpDivCC(int result, int arg1, int arg2)
295 {
296 if (arg2 == 0)
297 throw devide_by_zero();
298 global_value[result] = arg1 / arg2;
299 }
300
301 void OpDivVC(int result, int arg1, int arg2)
302 {
303 if (arg2 == 0)
304 throw devide_by_zero();
305 global_value[result] = global_value[arg1] / arg2;
306 }
307
308 void OpDivCV(int result, int arg1, int arg2)
309 {
310 arg2 = global_value[arg2];
311 if (arg2 == 0)
312 throw devide_by_zero();
313 global_value[result] = arg1 / arg2;
314 }
315
316 void OpDivVV(int result, int arg1, int arg2)
317 {
318 arg2 = global_value[arg2];
319 if (arg2 == 0)
320 throw devide_by_zero();
321 global_value[result] = global_value[arg1] / arg2;
322 }
323
324 // %
325 void OpModCC(int result, int arg1, int arg2)
326 {
327 if (arg2 == 0)
328 throw devide_by_zero();
329 global_value[result] = arg1 % arg2;
330 }
331
332 void OpModVC(int result, int arg1, int arg2)
333 {
334 if (arg2 == 0)
335 throw devide_by_zero();
336 global_value[result] = global_value[arg1] % arg2;
337 }
338
339 void OpModCV(int result, int arg1, int arg2)
340 {
341 arg2 = global_value[arg2];
342 if (arg2 == 0)
343 throw devide_by_zero();
344 global_value[result] = arg1 % arg2;
345 }
346
347 void OpModVV(int result, int arg1, int arg2)
348 {
349 arg2 = global_value[arg2];
350 if (arg2 == 0)
351 throw devide_by_zero();
352 global_value[result] = global_value[arg1] % arg2;
353 }
354
355 // 無条件ジャンプ
356 void OpJmp(int addr)
357 {
358 jmp(addr);
359 }
360
361 // 真の時ジャンプ
362 void OpJmpC(int addr, int arg)
363 {
364 if (global_value[arg])
365 jmp(addr);
366 }
367
368 // 偽の時ジャンプ
369 void OpJmpNC(int addr, int arg)
370 {
371 if (!global_value[arg])
372 jmp(addr);
373 }
374
375 // 仮想CPUプログラム停止
376 void OpHalt()
377 {
378 }
379
380 // 乱数
381 void OpRandC(int result, int arg)
382 {
383 global_value[result] = (arg <= 0)? 0: (rand() % arg);
384 }
385
386 void OpRandV(int result, int arg)
387 {
388 arg = global_value[arg];
389 global_value[result] = (arg <= 0)? 0: (rand() % arg);
390 }
391
392 void OpPrint(int count)
393 {
394 while (count--) {
395 std::cout << top();
396 pop();
397 if (count)
398 std::cout << ", ";
399 }
400 std::cout << std::endl;
401 }
402
403 private:
404 const int *value(int n) { const int *v = (const int *)command_ptr_; command_ptr_ += 4 * n; return v; }
405 int addr() const { return (int)(command_ptr_ - command_); }
406 void jmp(int addr) { command_ptr_ = command_ + addr; }
407 void push(int v) { stack.push(v); }
408 void pop() { stack.pop(); }
409 const int top() const { return stack.top(); }
410 int &top() { return stack.top(); }
411
412 private:
413 data &data_;
414 unsigned char *command_;
415 unsigned char *command_ptr_;
416 int command_size_;
417
418 vm::stack<int, STACK_SIZE> stack;
419 std::vector<int> global_value;
420 } ;
421
422 }
423
424 #endif