source: dev/BasicCompiler64/Compile_Func.cpp@ 64

Last change on this file since 64 was 64, checked in by dai_9181, 17 years ago

すべてのオブジェクトを参照型に切り替えた。

File size: 7.2 KB
Line 
1#include "../BasicCompiler_Common/common.h"
2#include "Opcode.h"
3
4int GetFunctionType(int FuncNum){
5 switch(FuncNum){
6 case FUNC_LEN:
7 return DEF_LONG;
8 case FUNC_SIZEOF:
9 return DEF_LONG;
10 case FUNC_ADDRESSOF:
11 case FUNC_VARPTR:
12 return DEF_PTR_VOID;
13 case FUNC_GETDOUBLE:
14 return DEF_DOUBLE;
15 case FUNC_GETSINGLE:
16 return DEF_SINGLE;
17 case FUNC_GETQWORD:
18 return DEF_QWORD;
19 case FUNC_GETDWORD:
20 return DEF_DWORD;
21 case FUNC_GETWORD:
22 return DEF_WORD;
23 case FUNC_GETBYTE:
24 return DEF_BYTE;
25 }
26 return 0;
27}
28int GetFunctionFromName(char *FuncName){
29 if(lstrcmpi(FuncName,"Len")==0) return FUNC_LEN;
30 if(lstrcmpi(FuncName,"AddressOf")==0) return FUNC_ADDRESSOF;
31 if(lstrcmpi(FuncName,"SizeOf")==0) return FUNC_SIZEOF;
32 if(lstrcmpi(FuncName,"VarPtr")==0) return FUNC_VARPTR;
33 if(lstrcmpi(FuncName,"GetDouble")==0) return FUNC_GETDOUBLE;
34 if(lstrcmpi(FuncName,"GetSingle")==0) return FUNC_GETSINGLE;
35 if(lstrcmpi(FuncName,"GetQWord")==0) return FUNC_GETQWORD;
36 if(lstrcmpi(FuncName,"GetDWord")==0) return FUNC_GETDWORD;
37 if(lstrcmpi(FuncName,"GetWord")==0) return FUNC_GETWORD;
38 if(lstrcmpi(FuncName,"GetByte")==0) return FUNC_GETBYTE;
39 return 0;
40}
41void Opcode_Func_Len( const char *Parameter ){
42 int type,TypeSize;
43 LONG_PTR lpIndex;
44 BOOL bArrayHead;
45
46 type=GetVarType(Parameter,&lpIndex,0);
47
48 const char *tempParm=Parameter;
49 char temporary[VN_SIZE];
50 char temp2[32];
51 if(type==-1){
52 sprintf(temporary,"_System_DummyStr2=%s",Parameter);
53 OpcodeCalc(temporary);
54
55 lstrcpy(temp2,"_System_DummyStr2");
56 tempParm=temp2;
57
58 extern CClass *pobj_StringClass;
59 type=DEF_OBJECT;
60 lpIndex=(LONG_PTR)pobj_StringClass;
61 }
62
63 TYPEINFO TypeInfo={type,lpIndex};
64 if(IsStringObjectType(TypeInfo)){
65 //Stringオブジェクトの場合
66 sprintf(temporary,"%s.Length",tempParm);
67
68 int reg=REG_RAX;
69 NumOpe(&reg,temporary,0,0,NULL,NULL);
70 return;
71 }
72
73
74 int SubScripts[MAX_ARRAYDIM];
75 RELATIVE_VAR RelativeVar;
76 if(!GetVarOffsetReadOnly(tempParm,&type,&RelativeVar,&lpIndex,SubScripts)) return;
77
78
79 if(type&FLAG_PTR){
80 type&=~FLAG_PTR;
81
82 bArrayHead=1;
83 }
84 else bArrayHead=0;
85
86 TypeSize=GetTypeSize(type,lpIndex);
87
88 if(bArrayHead) TypeSize*=JumpSubScripts(SubScripts);
89
90 //mov rax,TypeSize
91 op_mov_RV(sizeof(_int64),REG_RAX,TypeSize);
92
93 return;
94}
95void Opcode_Func_AddressOf( const char *name ){
96 extern int cp;
97 SUBINFO *psi;
98
99 extern LONG_PTR ProcPtr_BaseIndex;
100 if(ProcPtr_BaseIndex!=-1){
101 //左辺の型にのっとり、オーバーロードを解決
102
103 std::vector<SUBINFO *> subs;
104 GetOverloadSubHash( name, subs );
105 if( subs.size() == 0 ){
106 SetError(27,name,cp);
107 return;
108 }
109
110 //オーバーロードを解決
111 extern PROCPTRINFO *pProcPtrInfo;
112 psi=OverloadSolution(name,subs,pProcPtrInfo[ProcPtr_BaseIndex].pParmInfo,pProcPtrInfo[ProcPtr_BaseIndex].ParmNum,NULL);
113
114 if(!psi){
115 SetError(27,name,cp);
116 return;
117 }
118 }
119 else{
120 psi=GetSubHash(name);
121 if(!psi){
122 SetError(27,name,cp);
123 return;
124 }
125 }
126
127
128 if(psi->bVirtual){
129 ///////////////////////////////
130 // 仮想関数の場合
131 // thisポインタをrcxにコピー
132 ///////////////////////////////
133
134 CClass *pobj_c;
135
136 char ObjectName[VN_SIZE];
137 int RefType;
138 SplitObjectName(name,ObjectName,&RefType);
139
140 if(ObjectName[0]){
141 if(lstrcmpi(ObjectName,"Super")==0) goto InClassMember;
142 else{
143 RELATIVE_VAR RelativeVar;
144 int type;
145 if(!GetVarOffsetReadOnly(ObjectName,&type,&RelativeVar,(LONG_PTR *)&pobj_c)) return;
146 SetVarPtrToReg(REG_RCX,&RelativeVar);
147
148 //参照タイプが整合しているかをチェック
149 if(type!=RefType) SetError(104,ObjectName,cp);
150
151 if(type==DEF_PTR_OBJECT){
152 //mov rcx,qword ptr[rcx]
153 op_mov_RM(sizeof(_int64),REG_RCX,REG_RCX,0,MOD_BASE);
154 }
155 }
156 }
157 else{
158InClassMember:
159 //自身のオブジェクトのThisポインタをrcxにコピー
160 SetThisPtrToReg(REG_RCX);
161
162 pobj_c=pobj_CompilingClass;
163 }
164
165
166 //仮想関数(オブジェクトメソッド)
167 //pObj->func_table->func1
168 // ->func2
169 // ->func3
170
171 //mov r11,qword ptr[rcx]
172 op_mov_RM(sizeof(_int64),REG_R11,REG_RCX,0,MOD_BASE);
173
174 int i2 = pobj_c->GetFuncNumInVtbl( psi );
175
176 //mov rax,qword ptr[r11+func_index]
177 if(i2*PTR_SIZE<=0x7F){
178 op_mov_RM(sizeof(_int64),REG_RAX,REG_R11,i2*PTR_SIZE,MOD_BASE_DISP8);
179 }
180 else{
181 op_mov_RM(sizeof(_int64),REG_RAX,REG_R11,i2*PTR_SIZE,MOD_BASE_DISP32);
182 }
183 }
184 else{
185 //一般の関数
186
187 //mov rax,ProcAddr
188 op_mov_RV(sizeof(_int64),REG_RAX,0);
189 obp-=sizeof(long);
190 pobj_SubAddrSchedule->add(psi,0);
191 obp+=sizeof(long);
192 }
193
194 psi->bUse=1;
195}
196void Opcode_Func_SizeOf( const char *Parameter ){
197 LONG_PTR lpIndex;
198 int type = GetTypeFixed(Parameter,&lpIndex);
199
200 int size;
201 if( type == DEF_OBJECT ){
202 CClass *pClass = (CClass *)lpIndex;
203 size = pClass->GetSize();
204 }
205 else{
206 size=GetTypeSize(type,lpIndex);
207 }
208
209 //mov rax,size
210 op_mov_RV(sizeof(_int64),REG_RAX,size);
211}
212void Opcode_Func_VarPtr( const char *Parameter, TYPEINFO &ReturnTypeInfo ){
213 RELATIVE_VAR RelativeVar;
214
215 //変数のアドレスを取得
216 if(!GetVarOffsetReadOnly( Parameter, &ReturnTypeInfo.type, &RelativeVar, &ReturnTypeInfo.u.lpIndex )) return;
217
218 int beforeType = ReturnTypeInfo.type;
219
220 PTR_LEVEL_UP( ReturnTypeInfo.type );
221
222 SetVarPtrToReg(REG_RAX,&RelativeVar);
223
224 if( beforeType == DEF_OBJECT && lstrcmpi( Parameter, "This" ) != 0 ){
225 //参照をオブジェクトポインタに変更
226
227 //mov rax,qword ptr[rax]
228 op_mov_RM( sizeof(_int64), REG_RAX, REG_RAX, 0, MOD_BASE );
229 }
230}
231void Opcode_Func_GetPtrData( const char *Parameter, const int type ){
232 int i2;
233
234 int reg=REG_RAX;
235 i2=NumOpe(&reg,Parameter,0,0,0);
236 if(!IsWholeNumberType(i2)){
237 extern int cp;
238 SetError(11,Parameter,cp);
239 return;
240 }
241
242 if(type==DEF_DOUBLE){
243 //movlpd xmm0,qword ptr[rax]
244 op_movlpd_RM(REG_XMM0,REG_RAX,0,MOD_BASE);
245 }
246 else if(type==DEF_SINGLE){
247 //movss xmm0,dword ptr[rax]
248 op_movss_RM(REG_XMM0,REG_RAX,0,MOD_BASE);
249 }
250 else{
251 //mov rax,ptr[rax]
252 op_mov_RM(GetTypeSize(type,-1),REG_RAX,REG_RAX,0,MOD_BASE);
253 }
254}
255
256void Opcode_CallFunc( const char *Parameter, const int FuncNum, TYPEINFO &ReturnTypeInfo ){
257 switch(FuncNum){
258 case FUNC_LEN:
259 Opcode_Func_Len(Parameter);
260 ReturnTypeInfo.type = DEF_LONG;
261 break;
262 case FUNC_ADDRESSOF:
263 Opcode_Func_AddressOf(Parameter);
264 ReturnTypeInfo.type = DEF_PTR_VOID;
265 break;
266 case FUNC_SIZEOF:
267 Opcode_Func_SizeOf(Parameter);
268 ReturnTypeInfo.type = DEF_LONG;
269 break;
270 case FUNC_VARPTR:
271 Opcode_Func_VarPtr( Parameter, ReturnTypeInfo );
272 break;
273
274 case FUNC_GETDOUBLE:
275 Opcode_Func_GetPtrData(Parameter,DEF_DOUBLE);
276 ReturnTypeInfo.type = DEF_DOUBLE;
277 break;
278 case FUNC_GETSINGLE:
279 Opcode_Func_GetPtrData(Parameter,DEF_SINGLE);
280 ReturnTypeInfo.type = DEF_SINGLE;
281 break;
282 case FUNC_GETQWORD:
283 Opcode_Func_GetPtrData(Parameter,DEF_QWORD);
284 ReturnTypeInfo.type = DEF_QWORD;
285 break;
286 case FUNC_GETDWORD:
287 Opcode_Func_GetPtrData(Parameter,DEF_DWORD);
288 ReturnTypeInfo.type = DEF_DWORD;
289 break;
290 case FUNC_GETWORD:
291 Opcode_Func_GetPtrData(Parameter,DEF_WORD);
292 ReturnTypeInfo.type = DEF_WORD;
293 break;
294 case FUNC_GETBYTE:
295 Opcode_Func_GetPtrData(Parameter,DEF_BYTE);
296 ReturnTypeInfo.type = DEF_BYTE;
297 break;
298 }
299}
Note: See TracBrowser for help on using the repository browser.