annotate Bison-Flex/Compiler-StackBase/EUC/node.cpp @ 0:db40c85cad7a default tip

upload sample source
author nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
date Mon, 09 May 2011 03:11:59 +0900
parents
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
2 // ノード
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
3 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
4 // (c)2008 Chihiro.SAKAMOTO HyperWorks
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
5 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
6 #include <functional>
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
7 #include <iostream>
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
8 #include <iomanip>
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
9 #include "node.h"
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
10 #include "compiler.h"
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
11 #include "script-parser.hh"
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
12
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
13 // ノード生成
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
14 // ただし、定数同士の計算は、leftノードに結果を代入し、それを返す
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
15
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
16 CNode *CNode::MakeNode(compiler &c, const yy::location& l, int op, CNode *left, CNode *right)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
17 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
18 if (right == 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
19 switch (op) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
20 case OP_NEG:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
21 if (left->op_ == OP_CONST) { // 定数演算を計算する
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
22 left->value_ = -left->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
23 return left;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
24 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
25 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
26 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
27 return new CNode(l, op, left);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
28 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
29
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
30 // 定数演算を計算する
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
31 if (left->op_ == OP_CONST && right->op_ == OP_CONST) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
32 switch (op) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
33 case OP_LOGAND:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
34 left->value_ = (left->value_ && right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
35 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
36
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
37 case OP_LOGOR:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
38 left->value_ = (left->value_ || right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
39 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
40
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
41 case OP_EQ:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
42 left->value_ = (left->value_ == right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
43 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
44
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
45 case OP_NE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
46 left->value_ = (left->value_ != right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
47 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
48
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
49 case OP_GT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
50 left->value_ = (left->value_ > right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
51 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
52
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
53 case OP_GE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
54 left->value_ = (left->value_ >= right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
55 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
56
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
57 case OP_LT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
58 left->value_ = (left->value_ < right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
59 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
60
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
61 case OP_LE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
62 left->value_ = (left->value_ <= right->value_)? 1: 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
63 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
64
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
65 case OP_AND:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
66 left->value_ &= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
67 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
68
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
69 case OP_OR:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
70 left->value_ |= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
71 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
72
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
73 case OP_LSHIFT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
74 left->value_ <<= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
75 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
76
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
77 case OP_RSHIFT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
78 left->value_ >>= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
79 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
80
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
81 case OP_MINUS:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
82 left->value_ -= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
83 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
84
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
85 case OP_PLUS:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
86 left->value_ += right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
87 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
88
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
89 case OP_TIMES:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
90 left->value_ *= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
91 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
92
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
93 case OP_DIVIDE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
94 if (right->value_ == 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
95 c.error(l, "定数計算を0で除算しました。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
96 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
97 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
98 left->value_ /= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
99 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
100 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
101
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
102 case OP_MOD:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
103 if (right->value_ == 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
104 c.error(l, "定数計算を0で除算しました。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
105 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
106 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
107 left->value_ %= right->value_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
108 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
109 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
110
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
111 default:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
112 return new CNode(l, op, left, right);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
113 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
114 delete right;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
115 return left;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
116 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
117
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
118 // 文字列同士の定数計算
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
119 if (left->op_ == OP_STRING && right->op_ == OP_STRING) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
120 if (op == OP_PLUS) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
121 *left->string_ += *right->string_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
122 delete right;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
123 return left;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
124 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
125
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
126 int value = 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
127 switch (op) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
128 case OP_EQ:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
129 if (*left->string_ == *right->string_)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
130 value = 1;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
131 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
132
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
133 case OP_NE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
134 if (*left->string_ != *right->string_)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
135 value = 1;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
136 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
137
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
138 case OP_GT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
139 if (*left->string_ > *right->string_)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
140 value = 1;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
141 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
142
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
143 case OP_GE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
144 if (*left->string_ >= *right->string_)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
145 value = 1;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
146 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
147
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
148 case OP_LT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
149 if (*left->string_ < *right->string_)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
150 value = 1;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
151 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
152
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
153 case OP_LE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
154 if (*left->string_ <= *right->string_)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
155 value = 1;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
156 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
157
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
158 default:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
159 c.error(l, "文字列同士ではできない計算です");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
160 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
161 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
162 delete left;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
163 delete right;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
164 return new CNode(l, OP_CONST, value);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
165 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
166 return new CNode(l, op, left, right);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
167 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
168
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
169 // ノードのpush処理
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
170 int CNode::push(compiler *c) const
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
171 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
172 switch (op_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
173 case OP_NEG:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
174 if (left_->push(c) == TYPE_STRING)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
175 c->error(l_, "文字列には許されない計算です。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
176 c->OpNeg();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
177 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
178
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
179 case OP_CONST:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
180 c->PushConst(value_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
181 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
182
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
183 case OP_STRING:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
184 c->PushString(*string_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
185 return TYPE_STRING;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
186 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
187
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
188 int left_type = left_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
189 int right_type = right_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
190
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
191 if (left_type != right_type)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
192 c->error(l_, "文字列と整数間で計算できません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
193
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
194 // 整数計算ノードの処理
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
195 if (left_type == TYPE_INTEGER) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
196 switch (op_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
197 case OP_LOGAND:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
198 c->OpLogAnd();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
199 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
200
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
201 case OP_LOGOR:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
202 c->OpLogOr();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
203 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
204
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
205 case OP_EQ:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
206 c->OpEq();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
207 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
208
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
209 case OP_NE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
210 c->OpNe();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
211 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
212
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
213 case OP_GT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
214 c->OpGt();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
215 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
216
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
217 case OP_GE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
218 c->OpGe();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
219 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
220
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
221 case OP_LT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
222 c->OpLt();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
223 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
224
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
225 case OP_LE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
226 c->OpLe();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
227 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
228
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
229 case OP_AND:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
230 c->OpAnd();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
231 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
232
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
233 case OP_OR:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
234 c->OpOr();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
235 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
236
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
237 case OP_LSHIFT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
238 c->OpLeftShift();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
239 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
240
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
241 case OP_RSHIFT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
242 c->OpRightShift();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
243 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
244
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
245 case OP_MINUS:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
246 c->OpSub();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
247 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
248
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
249 case OP_PLUS:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
250 c->OpAdd();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
251 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
252
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
253 case OP_TIMES:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
254 c->OpMul();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
255 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
256
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
257 case OP_DIVIDE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
258 c->OpDiv();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
259 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
260
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
261 case OP_MOD:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
262 c->OpMod();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
263 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
264
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
265 default:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
266 c->error(l_, "内部エラー:処理できない計算ノードがありました。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
267 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
268 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
269 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
270 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
271
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
272 // 文字列計算ノードの処理
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
273 switch (op_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
274 case OP_EQ:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
275 c->OpStrEq();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
276 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
277
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
278 case OP_NE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
279 c->OpStrNe();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
280 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
281
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
282 case OP_GT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
283 c->OpStrGt();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
284 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
285
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
286 case OP_GE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
287 c->OpStrGe();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
288 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
289
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
290 case OP_LT:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
291 c->OpStrLt();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
292 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
293
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
294 case OP_LE:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
295 c->OpStrLe();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
296 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
297
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
298 case OP_PLUS:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
299 c->OpStrAdd();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
300 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
301
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
302 default:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
303 c->error(l_, "文字列では計算できない式です。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
304 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
305 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
306 return TYPE_STRING;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
307 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
308
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
309 // ノードのpop
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
310 // 計算ノードはpopできない
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
311
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
312 int CNode::pop(compiler *c) const
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
313 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
314 c->error(l_, "内部エラー:計算ノードをpopしています。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
315 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
316 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
317
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
318 // 変数ノードのpush
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
319 int CValueNode::push(compiler *c) const
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
320 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
321 if (op_ != OP_VALUE) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
322 c->error(l_, "内部エラー:変数ノードに変数以外が登録されています。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
323 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
324 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
325 const CValueTag *tag = c->GetValueTag(*string_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
326 if (tag == 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
327 c->error(l_, "変数 " + *string_ + " は定義されていません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
328 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
329 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
330 // 参照型変数は、引数にしか存在しない
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
331 if (tag->type_ >= TYPE_INTEGER_REF) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
332 if (left_) { // 配列
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
333 left_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
334 c->PushLocalArrayRef(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
335 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
336 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
337 c->PushLocalRef(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
338 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
339 return tag->type_ - TYPE_INTEGER_REF;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
340 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
341 if (tag->global_) { // 外部変数
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
342 if (left_) { // 配列
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
343 left_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
344 c->PushArray(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
345 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
346 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
347 c->PushValue(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
348 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
349 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
350 else { // ローカル変数
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
351 if (left_) { // 配列
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
352 left_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
353 c->PushLocalArray(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
354 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
355 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
356 c->PushLocal(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
357 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
358 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
359 return tag->type_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
360 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
361 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
362 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
363 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
364
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
365 // 変数ノードのpop
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
366 int CValueNode::pop(compiler *c) const
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
367 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
368 if (op_ != OP_VALUE) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
369 c->error(l_, "内部エラー:変数ノードに変数以外が登録されています。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
370 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
371 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
372 const CValueTag *tag = c->GetValueTag(*string_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
373 if (tag == 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
374 c->error(l_, "変数 " + *string_ + " は定義されていません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
375 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
376 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
377 // 参照型変数は、引数にしか存在しない
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
378 if (tag->type_ >= TYPE_INTEGER_REF) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
379 if (left_) { // 配列
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
380 left_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
381 c->PopLocalArrayRef(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
382 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
383 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
384 c->PopLocalRef(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
385 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
386 return tag->type_ - TYPE_INTEGER_REF;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
387 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
388 if (tag->global_) { // 外部変数
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
389 if (left_) { // 配列
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
390 left_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
391 c->PopArray(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
392 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
393 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
394 c->PopValue(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
395 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
396 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
397 else { // ローカル変数
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
398 if (left_) { // 配列
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
399 left_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
400 c->PopLocalArray(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
401 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
402 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
403 c->PopLocal(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
404 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
405 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
406 return tag->type_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
407 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
408 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
409 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
410 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
411
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
412 // 関数呼び出し
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
413
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
414 struct set_arg {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
415 compiler *comp_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
416 const CFunctionTag *func_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
417 mutable int index_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
418 set_arg(compiler *comp, const CFunctionTag *func): comp_(comp), func_(func), index_(0)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
419 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
420 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
421
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
422 void operator()(CNode *node) const
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
423 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
424 int type = func_->GetArg(index_++);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
425 if (type >= TYPE_INTEGER_REF) { // 参照
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
426 if (node->op() != OP_VALUE) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
427 comp_->error(node->location(), "参照型引数に、変数以外は指定できません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
428 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
429 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
430 const CValueTag *tag = comp_->GetValueTag(node->string());
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
431 if (tag == 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
432 comp_->error(node->location(), "変数 " + node->string() + " は定義されていません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
433 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
434 else if (tag->type_ >= TYPE_INTEGER_REF) { // 参照
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
435 // 参照型変数は、ローカルしかない
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
436 if (node->left()) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
437 node->left()->push(comp_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
438 comp_->PushLocal(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
439 comp_->OpAdd();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
440 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
441 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
442 comp_->PushLocal(tag->addr_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
443 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
444 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
445 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
446 if (TypeToRef(tag->type_) != type) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
447 comp_->error(node->location(), "引数の型が合いません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
448 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
449 int addr = tag->addr_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
450 if (tag->global_) // 外部変数
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
451 addr |= vm::vcpu::global_flag;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
452 // アドレスをpush
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
453 if (node->left()) { // 配列
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
454 if (node->left()->op() == OP_CONST) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
455 comp_->PushAddr(addr + node->left()->value());
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
456 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
457 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
458 node->left()->push(comp_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
459 comp_->PushArrayAddr(addr);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
460 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
461 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
462 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
463 comp_->PushAddr(addr);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
464 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
465 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
466 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
467 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
468 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
469 if (node->push(comp_) != type) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
470 comp_->error(node->location(), "引数の型が合いません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
471 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
472 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
473 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
474 } ;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
475
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
476 int CFunctionNode::push(compiler *c) const
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
477 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
478 const CFunctionTag *tag = c->GetFunctionTag(*string_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
479 if (tag == NULL) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
480 c->error(l_, "関数 " + *string_ + "は、定義されていません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
481 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
482 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
483
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
484 int arg_size = (args_)? args_->size(): 0;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
485 if (tag->ArgSize() != arg_size) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
486 c->error(l_, "引数の数が合いません。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
487 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
488
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
489 // 引数をpush
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
490 if (args_ && tag->ArgSize() == arg_size) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
491 args_->for_each(set_arg(c, tag));
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
492 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
493
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
494 // 引数の数をpush
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
495 c->PushConst(arg_size);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
496
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
497 if (tag->IsSystem()) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
498 c->OpSysCall(tag->GetIndex()); // システムコール
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
499 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
500 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
501 c->OpCall(tag->GetIndex()); // スクリプト上の関数
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
502 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
503
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
504 return tag->type_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
505 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
506
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
507 // 関数にpopはできないのでエラーメッセージを出す
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
508 int CFunctionNode::pop(compiler *c) const
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
509 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
510 c->error(l_, "内部エラー:関数ノードをpopした");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
511 return TYPE_INTEGER;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
512 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
513
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
514 // 変数定義
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
515
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
516 struct add_value {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
517 compiler *comp_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
518 int type_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
519 add_value(compiler *comp, int type): comp_(comp), type_(type)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
520 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
521 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
522
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
523 void operator()(CValueNode *node)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
524 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
525 comp_->AddValue(node->location(), type_, node->string(), node->left());
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
526 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
527 } ;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
528
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
529 void CDecl::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
530 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
531 list_->for_each(add_value(c, type_));
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
532 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
533
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
534 // 代入命令を生成
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
535 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
536 // a = b
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
537 // > push b
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
538 // > pop a
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
539 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
540 // a += b
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
541 // > push a
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
542 // > push b
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
543 // > add
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
544 // > pop a
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
545 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
546 void CAssign::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
547 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
548 if (op_ != '=')
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
549 value_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
550
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
551 if (expr_->push(c) == TYPE_INTEGER) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
552 switch (op_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
553 case '+':
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
554 c->OpAdd();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
555 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
556
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
557 case '-':
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
558 c->OpSub();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
559 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
560
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
561 case '*':
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
562 c->OpMul();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
563 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
564
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
565 case '/':
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
566 c->OpDiv();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
567 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
568
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
569 case '%':
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
570 c->OpMod();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
571 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
572 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
573 if (value_->pop(c) != TYPE_INTEGER)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
574 c->error(l_, "文字列型に整数を代入しています。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
575 return;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
576 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
577
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
578 switch (op_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
579 case '+':
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
580 c->OpStrAdd();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
581 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
582
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
583 case '=':
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
584 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
585
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
586 default:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
587 c->error(l_, "文字列では許されない計算です。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
588 break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
589 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
590 if (value_->pop(c) != TYPE_STRING)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
591 c->error(l_, "整数型に文字列を代入しています。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
592 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
593
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
594 // '{' '}' で囲まれた文の生成
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
595
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
596 void CStateBlock::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
597 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
598 // ローカル変数の定義
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
599 if (decls_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
600 decls_->for_each(std::bind2nd(std::mem_fun(&CDecl::analyze), c));
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
601 c->AllocStack();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
602 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
603
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
604 // 文のコード生成
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
605 if (states_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
606 states_->for_each(std::bind2nd(std::mem_fun(&CStatement::analyze), c));
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
607 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
608 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
609
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
610 // NOP
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
611
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
612 void CNopStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
613 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
614 // 何もしない
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
615 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
616
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
617 // 代入
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
618
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
619 void CAssignStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
620 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
621 assign_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
622 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
623
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
624 // 関数呼び出し
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
625
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
626 void CFunctionStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
627 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
628 int type = node_.push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
629 if (type != TYPE_VOID)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
630 c->OpPop(); // 戻り値を捨てるためのpop
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
631 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
632
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
633 // IF文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
634 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
635 // if (expr) A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
636 // > push expr
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
637 // > jmp_nc L1
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
638 // > A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
639 // > L1:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
640 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
641 // if (expr) A else B
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
642 // > push expr
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
643 // > jmp_nc L1
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
644 // > A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
645 // > jmp L2
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
646 // > L1:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
647 // > B
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
648 // > L2:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
649 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
650 void CIfStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
651 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
652 expr_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
653 int label1 = c->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
654 c->OpJmpNC(label1);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
655 then_statement_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
656
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
657 if (else_statement_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
658 int label2 = c->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
659 c->OpJmp(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
660 c->SetLabel(label1);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
661 else_statement_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
662 c->SetLabel(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
663 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
664 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
665 c->SetLabel(label1);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
666 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
667 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
668
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
669 // FOR文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
670 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
671 // for (init; expr; next) A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
672 // > init
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
673 // > L1:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
674 // > push expr
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
675 // > jmp_nc L2
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
676 // > A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
677 // > next
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
678 // > jmp L1
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
679 // > L2:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
680 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
681 void CForStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
682 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
683 int label1 = c->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
684 int label2 = c->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
685
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
686 int break_label = c->SetBreakLabel(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
687
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
688 init_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
689 c->SetLabel(label1);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
690 expr_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
691 c->OpJmpNC(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
692 statement_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
693 next_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
694 c->OpJmp(label1);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
695 c->SetLabel(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
696
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
697 c->SetBreakLabel(break_label);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
698 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
699
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
700 // WHILE文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
701 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
702 // while (expr) A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
703 // > L1:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
704 // > push expr
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
705 // > jmp_nc L2
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
706 // > A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
707 // > jmp L1
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
708 // > L2:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
709 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
710 void CWhileStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
711 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
712 int label1 = c->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
713 int label2 = c->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
714
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
715 int break_label = c->SetBreakLabel(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
716
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
717 c->SetLabel(label1);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
718 expr_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
719 c->OpJmpNC(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
720 statement_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
721 c->OpJmp(label1);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
722 c->SetLabel(label2);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
723
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
724 c->SetBreakLabel(break_label);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
725 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
726
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
727 // SWITCH文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
728 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
729 // switch (expr) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
730 // case A:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
731 // STATE_A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
732 // break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
733 // case B:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
734 // STATE_B
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
735 // break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
736 // default:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
737 // STATE_C
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
738 // break;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
739 // }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
740 // > push expr
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
741 // > push A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
742 // > test L1 ; stack上の2値を比較し、等しければpopしてJmp
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
743 // > push B
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
744 // > test L2
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
745 // > pop
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
746 // > jmp L3
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
747 // > L1:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
748 // > STATE_A
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
749 // > jmp L0 ; break
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
750 // > L2:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
751 // > STATE_B
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
752 // > jmp L0 ; break
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
753 // > L3:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
754 // > STATE_C
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
755 // > jmp L0 ; break
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
756 // > L0:
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
757 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
758 void CSwitchStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
759 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
760 expr_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
761
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
762 if (list_) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
763 int label = c->MakeLabel(); // L0ラベル作成
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
764 int break_label = c->SetBreakLabel(label);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
765 int default_label = label;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
766
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
767 case_action_param param(c, default_label);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
768
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
769 list_->for_each(std::bind2nd(std::mem_fun(&CStatement::case_analyze), &param));
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
770 c->OpPop();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
771 c->OpJmp(default_label);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
772
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
773 list_->for_each(std::bind2nd(std::mem_fun(&CStatement::analyze), c));
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
774 c->SetLabel(label);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
775
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
776 c->SetBreakLabel(break_label);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
777 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
778 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
779
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
780 // CASE文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
781 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
782 // switch文の特殊処理
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
783 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
784 void CCaseStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
785 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
786 c->SetLabel(label_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
787 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
788
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
789 void CCaseStatement::case_analyze(case_action_param *param)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
790 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
791 compiler *c = param->comp_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
792
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
793 label_ = c->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
794 if (expr_->op() != OP_CONST)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
795 c->error(l_, "case 文には定数のみ指定できます。");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
796 expr_->push(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
797 c->OpTest(label_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
798 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
799
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
800 // DEFAULT文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
801 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
802 // switch文の特殊処理
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
803 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
804 void CDefaultStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
805 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
806 c->SetLabel(label_);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
807 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
808
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
809 void CDefaultStatement::case_analyze(case_action_param *param)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
810 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
811 label_ = param->comp_->MakeLabel();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
812 param->default_label = label_;
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
813 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
814
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
815 // BREAK文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
816 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
817 // 登録されているJump先へのJmp命令を生成
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
818 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
819 void CBreakStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
820 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
821 if (!c->JmpBreakLabel()) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
822 c->error(l_, "breakがswitch/for/while外に有ります");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
823 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
824 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
825
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
826 // RETURN文
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
827 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
828 // RETURNコマンドを生成
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
829 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
830 void CReturnStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
831 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
832 if (c->GetFunctionType() == TYPE_VOID) { // 戻り値無し
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
833 if (expr_ != 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
834 c->error(l_, "void関数に戻り値が設定されています");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
835 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
836 c->OpReturn();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
837 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
838 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
839 if (expr_ == 0) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
840 c->error(l_, "関数の戻り値がありません");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
841 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
842 else {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
843 int expr_type = expr_->push(c); // 戻り値をpush
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
844 if (expr_type != c->GetFunctionType()) {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
845 c->error(l_, "戻り値の型が合いません");
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
846 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
847 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
848 c->OpReturnV();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
849 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
850 }
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
851
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
852 // 文ブロック
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
853 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
854 // 再帰的にすべての文を解析
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
855 //
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
856 void CBlockStatement::analyze(compiler *c)
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
857 {
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
858 c->BlockIn();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
859 block_->analyze(c);
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
860 c->BlockOut();
db40c85cad7a upload sample source
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
861 }