source: dev/BasicCompiler_Common/hash.cpp@ 23

Last change on this file since 23 was 5, checked in by dai_9181, 18 years ago
File size: 6.4 KB
Line 
1#include "../BasicCompiler_Common/common.h"
2
3#ifdef _AMD64_
4#include "../BasicCompiler64/opcode.h"
5#else
6#include "../BasicCompiler32/opcode.h"
7#endif
8
9int hash_default(char *name){
10 int key;
11
12 for(key=0;*name!='\0';name++){
13 key=((key<<8)+ *name )%MAX_HASH;
14 }
15
16 return key;
17}
18
19CONSTINFO *GetConstHash(char *name){
20 //ハッシュ値を取得
21 int key;
22 key=hash_default(name);
23
24 //格納位置を取得
25 extern CONSTINFO **ppConstHash;
26 CONSTINFO *pci;
27 pci=ppConstHash[key];
28 while(pci){
29 if(lstrcmp(pci->name,name)==0) break;
30
31 pci=pci->pNextData;
32 }
33
34 return pci;
35}
36
37DECLAREINFO *GetDeclareHash(char *name){
38 //ハッシュ値を取得
39 int key;
40 key=hash_default(name);
41
42 //格納位置を取得
43 extern DECLAREINFO **ppDeclareHash;
44 DECLAREINFO *pdi;
45 pdi=ppDeclareHash[key];
46 while(pdi){
47 if(lstrcmp(pdi->name,name)==0) break;
48
49 pdi=pdi->pNextData;
50 }
51
52 return pdi;
53}
54
55SUBINFO **GetOverloadObjectSubHash(char *name,CClass *pobj_c, int *pNum){
56 int i;
57
58
59 //格納のための構造体配列を用意
60 extern HANDLE hHeap;
61 SUBINFO **ppArray_si;
62 int num=0;
63 ppArray_si=(SUBINFO **)HeapAlloc(hHeap,0,sizeof(SUBINFO *)*1024);
64
65
66 //オブジェクトのメンバ関数の場合
67 //※オーバーライドされた関数を先にサーチする必要があるため、バックサーチを行う
68 for(i=pobj_c->iMethodNum-1;i>=0;i--){
69 if(lstrcmp(name,pobj_c->ppobj_Method[i]->psi->name)==0){
70 ppArray_si[num]=pobj_c->ppobj_Method[i]->psi;
71 num++;
72 }
73 }
74
75 *pNum=num;
76 return ppArray_si;
77}
78
79SUBINFO **GetOverloadSubHash(char *lpszName,int *pNum){
80 extern SUBINFO *pSubInfo;
81 extern int SubInfoNum;
82 extern int cp;
83 int i;
84
85
86 char name[VN_SIZE];
87
88 if(lpszName[0]=='.'){
89 GetWithName(name);
90 lstrcat(name,lpszName);
91 }
92 else lstrcpy(name,lpszName);
93
94
95 //格納のための構造体配列を用意
96 extern HANDLE hHeap;
97 SUBINFO **ppArray_si;
98 int num=0;
99 ppArray_si=(SUBINFO **)HeapAlloc(hHeap,0,sizeof(SUBINFO *)*1024);
100
101
102 char ObjName[VN_SIZE]; //オブジェクト変数
103 char NestMember[VN_SIZE]; //入れ子メンバ
104 BOOL bObjectMember;
105 lstrcpy(ObjName,name);
106 for(i=lstrlen(ObjName)-1;i>=0;i--){
107 if(ObjName[i]=='.'||(ObjName[i]==1&&ObjName[i+1]==ESC_PSMEM))
108 break;
109 }
110 if(i==-1) bObjectMember=0;
111 else{
112 if(ObjName[i]=='.')
113 lstrcpy(NestMember,ObjName+i+1);
114 else
115 lstrcpy(NestMember,ObjName+i+2);
116 ObjName[i]=0;
117 bObjectMember=1;
118 }
119
120 if(bObjectMember){
121 //オブジェクトのメンバ関数の場合
122
123 if(lstrcmpi(ObjName,"Super")==0){
124 //スーパークラス参照の場合
125
126 if(pobj_CompilingClass==0){
127 SetError(118,NULL,cp);
128 goto finish;
129 }
130
131 //クラス内のメンバ関数をコンパイルしているとき
132 //※オーバーライドされた関数をサーチする
133 for(i=0;i<pobj_CompilingClass->iMethodNum;i++){
134 if(pobj_CompilingClass->ppobj_Method[i]->pobj_InheritsClass==0) continue;
135
136 if(lstrcmp(NestMember,pobj_CompilingClass->ppobj_Method[i]->psi->name)==0){
137 ppArray_si[num]=pobj_CompilingClass->ppobj_Method[i]->psi;
138 num++;
139 }
140 }
141
142 if(num==0) SetError(119,NestMember,cp);
143
144 goto finish;
145 }
146
147
148
149 //////////////////////////////////////////////
150 // 静的メソッド(クラス名が指定される場合)
151 //////////////////////////////////////////////
152
153 CClass *pobj_c;
154 pobj_c=pobj_DBClass->check(ObjName);
155 if(pobj_c){
156 for(i=0;i<pobj_c->iStaticMethodNum;i++){
157 if(lstrcmp(NestMember,pobj_c->ppobj_StaticMethod[i]->psi->name)==0){
158 ppArray_si[num]=pobj_c->ppobj_StaticMethod[i]->psi;
159 num++;
160 }
161 }
162
163 goto finish;
164 }
165
166
167 i=GetVarType(ObjName,(LONG_PTR *)&pobj_c,1);
168 if(i==-1) goto finish; //エラーの場合
169 if(!(NATURAL_TYPE(i)==DEF_OBJECT)) goto finish;
170
171 //※オーバーライドされた関数を先にサーチする必要があるため、バックサーチを行う
172 for(i=pobj_c->iMethodNum-1;i>=0;i--){
173 if(lstrcmp(NestMember,pobj_c->ppobj_Method[i]->psi->name)==0){
174 ppArray_si[num]=pobj_c->ppobj_Method[i]->psi;
175 num++;
176 }
177 }
178 goto finish;
179 }
180
181 if(pobj_CompilingClass){
182 //自身のオブジェクトのメンバ関数を検索
183
184
185 //////////////////////////////////////////////
186 // 静的メソッド
187 //////////////////////////////////////////////
188
189 CClass *pobj_c = pobj_CompilingClass;
190
191 for(i=0;i<pobj_c->iStaticMethodNum;i++){
192 if(lstrcmp(name,pobj_c->ppobj_StaticMethod[i]->psi->name)==0){
193 ppArray_si[num]=pobj_c->ppobj_StaticMethod[i]->psi;
194 num++;
195 }
196 }
197
198
199 ///////////////////////
200 // 動的メソッド(一般)
201 ///////////////////////
202 for(i=0;i<pobj_CompilingClass->iMethodNum;i++){
203 //オーバーライドされた関数を飛び越す
204 if(pobj_CompilingClass->ppobj_Method[i]->pobj_InheritsClass==0) break;
205 }
206 for(;i<pobj_CompilingClass->iMethodNum;i++){
207 if(lstrcmp(name,pobj_CompilingClass->ppobj_Method[i]->psi->name)==0){
208 ppArray_si[num]=pobj_CompilingClass->ppobj_Method[i]->psi;
209 num++;
210 }
211 }
212
213 //オーバーライドされたメンバ関数
214 for(i=0;i<pobj_CompilingClass->iMethodNum;i++){
215 //オーバーライドされた関数を飛び越す
216 if(pobj_CompilingClass->ppobj_Method[i]->pobj_InheritsClass){
217 if(lstrcmp(name,pobj_CompilingClass->ppobj_Method[i]->psi->name)==0){
218 ppArray_si[num]=pobj_CompilingClass->ppobj_Method[i]->psi;
219 num++;
220 }
221 }
222 }
223
224 if(num) goto finish;
225 }
226
227 //ハッシュ値を取得
228 int key;
229 key=hash_default(name);
230
231 //格納位置を取得
232 extern SUBINFO **ppSubHash;
233 SUBINFO *psi;
234 psi=ppSubHash[key];
235 while(psi){
236 if(!psi->pobj_ParentClass){
237 if(lstrcmp(psi->name,name)==0){
238 ppArray_si[num]=psi;
239 num++;
240 }
241 }
242
243 psi=psi->pNextData;
244 }
245
246finish:
247
248 *pNum=num;
249 return ppArray_si;
250}
251
252//オーバーロードされていない関数を取得(昔のコンパイラソースコードとの互換性保持)
253SUBINFO *GetSubHash(char *lpszName,BOOL bError){
254 int num;
255 SUBINFO **ppsi,*psi;
256 ppsi = GetOverloadSubHash(lpszName,&num);
257
258 //関数が存在しないとき
259 if(num == 0){
260 HeapDefaultFree(ppsi);
261 return 0;
262 }
263
264 //一つ以上の関数が存在するときは内部エラー(デバッグ用)
265 if(num > 1){
266 if(bError) SetError(300,NULL,cp);
267 }
268
269 psi = ppsi[0];
270
271 HeapDefaultFree(ppsi);
272
273 return psi;
274}
275SUBINFO *GetMethodHash(char *ObjectName,char *MethodName,char *Parameter,BOOL bError){
276 char temporary[VN_SIZE];
277 sprintf(temporary,"%s.%s",ObjectName,MethodName);
278
279 int num;
280 SUBINFO **ppsi,*psi;
281 ppsi = GetOverloadSubHash(temporary,&num);
282
283 //関数が存在しないとき
284 if(num == 0){
285 HeapDefaultFree(ppsi);
286 return 0;
287 }
288
289 //オーバーロードを解決
290 psi=OverloadSolutionWithStrParam(temporary,ppsi,num,Parameter,ObjectName,NULL);
291 HeapDefaultFree(ppsi);
292
293 return psi;
294}
Note: See TracBrowser for help on using the repository browser.