source: dev/BasicCompiler32/Compile_Var.cpp@ 18

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

オブジェクト定数に対応。

File size: 31.0 KB
Line 
1#include "../BasicCompiler_Common/common.h"
2#include "Opcode.h"
3
4//変数
5VARIABLE *GlobalVar;
6int MaxGlobalVarNum;
7int AllGlobalVarSize;
8int AllInitGlobalVarSize;
9VARIABLE *LocalVar;
10int MaxLocalVarNum;
11int AllLocalVarSize;
12
13void SetRelativeOffset(int *pType,LONG_PTR lpIndex,RELATIVE_VAR *pRelativeVar,char *lpPtrOffset){
14 int i2;
15
16 PushLongVariable(pRelativeVar);
17
18 i2=NumOpe(lpPtrOffset,0,0,0);
19 ChangeTypeToLong(i2);
20
21 //pop ebx
22 op_pop(REG_EBX);
23
24 if(PTR_LEVEL(*pType)){
25 *pType=MAKE_PTR_TYPE(NATURAL_TYPE(*pType),PTR_LEVEL(*pType)-1);
26 if((*pType)==DEF_OBJECT){
27 //imul ebx,objsize
28 OpBuffer[obp++]=(char)0x69;
29 OpBuffer[obp++]=(char)0xDB;
30 *((long *)(OpBuffer+obp))=GetSizeOfClassMember((CClass *)lpIndex,NULL,NULL);
31 obp+=sizeof(long);
32 }
33 else{
34 i2=GetTypeSize(*pType,-1);
35 if(i2>=2){
36 //imul ebx,i2
37 OpBuffer[obp++]=(char)0x6B;
38 OpBuffer[obp++]=(char)0xDB;
39 OpBuffer[obp++]=(char)i2;
40 }
41 }
42 }
43 else{
44 //エラー
45 SetError(1,NULL,cp);
46 return;
47 }
48
49 //pop ecx
50 op_pop(REG_ECX);
51
52 //add ecx,ebx
53 OpBuffer[obp++]=(char)0x03;
54 OpBuffer[obp++]=(char)0xCB;
55}
56BOOL GetArrayOffset(int *SubScripts,char *array,int type,LONG_PTR lpIndex){
57 extern HANDLE hHeap;
58 int i,i2,i3,i4,TypeSize;
59 char temporary[VN_SIZE],*pParm[MAX_PARMS];
60
61 for(i=0,i2=0,i3=0;;i++,i2++){
62 if(array[i]=='('){
63 i4=GetStringInPare(temporary+i2,array+i);
64 i+=i4-1;
65 i2+=i4-1;
66 continue;
67 }
68 if(array[i]=='['){
69 i4=GetStringInBracket(temporary+i2,array+i);
70 i+=i4-1;
71 i2+=i4-1;
72 continue;
73 }
74 if(array[i]==','||array[i]=='\0'){
75 if(SubScripts[i3]==-1){
76 for(i3--;i3>=0;i3--) HeapDefaultFree(pParm[i3]);
77 return 0;
78 }
79
80 temporary[i2]=0;
81
82 pParm[i3]=(char *)HeapAlloc(hHeap,0,lstrlen(temporary)+1);
83 lstrcpy(pParm[i3],temporary);
84
85 i3++;
86
87 if(array[i]=='\0'){
88 if(SubScripts[i3]!=-1){
89 for(i3--;i3>=0;i3--) HeapDefaultFree(pParm[i3]);
90 return 0;
91 }
92 break;
93 }
94
95 i2=-1;
96 continue;
97 }
98 temporary[i2]=array[i];
99 }
100
101 //push ecx
102 op_push(REG_ECX);
103
104 //push 0
105 op_push_value(0);
106
107 for(i=i3-1;i>=0;i--){
108 TYPEINFO TypeInfo;
109 BOOL bUseHeap;
110 TypeInfo.type=NumOpe(pParm[i],DEF_LONG,-1,&TypeInfo.u.lpIndex,&bUseHeap);
111 if(TypeInfo.type==DEF_OBJECT){
112 //キャスト演算子のオーバーロードに対応する
113 CallCastOperatorProc(
114 TypeInfo.type,TypeInfo.u.lpIndex,
115 bUseHeap,DEF_LONG,-1);
116 TypeInfo.type=DEF_LONG;
117 }
118 ChangeTypeToLong(TypeInfo.type);
119
120 //pop eax
121 op_pop(REG_EAX);
122
123 for(i2=i+1,i4=1;i2<i3;i2++) i4*=SubScripts[i2]+1;
124
125 //imul eax,i4
126 OpBuffer[obp++]=(char)0x69;
127 OpBuffer[obp++]=(char)0xC0;
128 *((long *)(OpBuffer+obp))=i4;
129 obp+=sizeof(long);
130
131 //add dword ptr[esp],eax
132 OpBuffer[obp++]=(char)0x01;
133 OpBuffer[obp++]=(char)0x04;
134 OpBuffer[obp++]=(char)0x24;
135
136 HeapDefaultFree(pParm[i]);
137 }
138
139 //pop eax
140 op_pop(REG_EAX);
141
142 TypeSize=GetTypeSize(type,lpIndex);
143
144 //imul eax,TypeSize
145 OpBuffer[obp++]=(char)0x69;
146 OpBuffer[obp++]=(char)0xC0;
147 *((long *)(OpBuffer+obp))=TypeSize;
148 obp+=sizeof(long);
149
150 //pop ecx
151 op_pop(REG_ECX);
152
153 //add ecx,eax
154 OpBuffer[obp++]=(char)0x03;
155 OpBuffer[obp++]=(char)0xC8;
156
157 return 1;
158}
159BOOL GetMemberOffset(bool isErrorEnabled, bool isWriteAccess, CClass *pobj_c, char *member, int *pType, RELATIVE_VAR *pRelativeVar, LONG_PTR *plpNestIndex, BOOL bPrivateAccess){
160 int i,offset;
161
162 //クラス、配列の構成要素を解析する
163 char VarName[VN_SIZE]; //変数名
164 char array[VN_SIZE]; //第1次配列
165 char lpPtrOffset[VN_SIZE]; //第2次配列
166 char NestMember[VN_SIZE]; //入れ子メンバ
167 int RefType; //"."参照のときは0、"->"参照のときは1
168 lstrcpy(VarName,member);
169 if(!GetVarFormatString(VarName,array,lpPtrOffset,NestMember,&RefType)) return 0;
170
171 ////////////////////////////
172 // メンバオフセットを取得
173 ////////////////////////////
174
175 offset=GetSizeOfClassMember(pobj_c,VarName,&i);
176 if(i==pobj_c->iMemberNum){
177 if(isErrorEnabled) SetError(103,VarName,cp);
178 return 0;
179 }
180
181 //アクセシビリティをチェック
182 if(pobj_c==pobj_CompilingClass){
183 //同一クラスオブジェクトの場合はプライベートアクセスを容認する
184 if(pobj_c->ppobj_Member[i]->dwAccess==ACCESS_NON){
185 if(isErrorEnabled) SetError(107,VarName,cp);
186 return 0;
187 }
188 }
189 else{
190 if((bPrivateAccess==0&&pobj_c->ppobj_Member[i]->dwAccess==ACCESS_PRIVATE)||
191 pobj_c->ppobj_Member[i]->dwAccess==ACCESS_NON){
192 if(isErrorEnabled) SetError(107,VarName,cp);
193 return 0;
194 }
195 else if(bPrivateAccess==0&&pobj_c->ppobj_Member[i]->dwAccess==ACCESS_PROTECTED){
196 if(isErrorEnabled) SetError(108,VarName,cp);
197 return 0;
198 }
199 }
200
201 //Const定義の場合は書き込みアクセスを制限する
202 //※コンストラクタをコンパイル中の場合は例外的に許可する
203 if( pobj_c->ppobj_Member[i]->IsConst() && //定数メンバである
204 isWriteAccess && //書き込みアクセスを要求されている
205 pobj_c->IsCompilingConstructor() == false //コンストラクタ コンパイル中を除く
206 ){
207 //Const定義の変数に書き込みアクセスをしようとした場合
208 SetError(61,VarName,cp);
209 }
210
211 *pType=pobj_c->ppobj_Member[i]->TypeInfo.type;
212 *plpNestIndex=pobj_c->ppobj_Member[i]->TypeInfo.u.lpIndex;
213
214 //ポインタ変数の場合
215 if(IsPtrType(*pType)){
216 if(pobj_c->ppobj_Member[i]->SubScripts[0]==-1){
217 lstrcpy(lpPtrOffset,array);
218 array[0]=0;
219 }
220 }
221 else{
222 if(lpPtrOffset[0]){
223 if(isErrorEnabled) SetError(16,member,cp);
224 return 0;
225 }
226 }
227
228 if(offset){
229 //add ecx,offset
230 OpBuffer[obp++]=(char)0x81;
231 OpBuffer[obp++]=(char)0xC1;
232 *((long *)(OpBuffer+obp))=offset;
233 obp+=sizeof(long);
234 }
235
236 if(array[0]){
237 //配列オフセット
238 if(!GetArrayOffset(pobj_c->ppobj_Member[i]->SubScripts,array,*pType,pobj_c->ppobj_Member[i]->TypeInfo.u.lpIndex))
239 if(isErrorEnabled) SetError(14,member,cp);
240 }
241 else if(pobj_c->ppobj_Member[i]->SubScripts[0]!=-1){
242 *pType|=FLAG_PTR;
243 }
244
245 if(NestMember[0]){
246 //入れ子構造の場合
247
248 if(*pType==DEF_OBJECT){
249 if(RefType!=DEF_OBJECT){
250 if(isErrorEnabled) SetError(104,member,cp);
251 return 0;
252 }
253 }
254 else if(*pType==DEF_PTR_OBJECT){
255 //構造体ポインタ型メンバ変数
256
257 if(lpPtrOffset[0]){
258 //pObj[n].member
259 if(RefType!=DEF_OBJECT){
260 if(isErrorEnabled) SetError(104,member,cp);
261 return 0;
262 }
263
264 //直接参照に切り替え
265 SetRelativeOffset(pType,*plpNestIndex,pRelativeVar,lpPtrOffset);
266 pRelativeVar->dwKind=VAR_DIRECTMEM;
267
268 lpPtrOffset[0]=0;
269 }
270 else{
271 //pObj->member
272 if(RefType!=DEF_PTR_OBJECT){
273 if(isErrorEnabled) SetError(104,member,cp);
274 return 0;
275 }
276
277 if(pRelativeVar->dwKind==VAR_DIRECTMEM){
278 //mov ecx,dword ptr[ecx]
279 OpBuffer[obp++]=(char)0x8B;
280 OpBuffer[obp++]=(char)0x09;
281 }
282 else{
283 //直接参照に切り替え
284 SetVarPtrToEax(pRelativeVar);
285 pRelativeVar->dwKind=VAR_DIRECTMEM;
286
287 //mov ecx,dword ptr[eax]
288 OpBuffer[obp++]=(char)0x8B;
289 OpBuffer[obp++]=(char)0x08;
290 }
291 }
292 }
293 else if(*pType==MAKE_PTR_TYPE(DEF_OBJECT,2)){
294 //構造体ポインタのポインタ型メンバ変数
295
296 if(lpPtrOffset[0]){
297 //ppObj[n]->member
298 if(RefType!=DEF_PTR_OBJECT){
299 if(isErrorEnabled) SetError(104,member,cp);
300 return 0;
301 }
302
303 //直接参照に切り替え
304 SetRelativeOffset(pType,*plpNestIndex,pRelativeVar,lpPtrOffset);
305 pRelativeVar->dwKind=VAR_DIRECTMEM;
306
307 lpPtrOffset[0]=0;
308
309 //mov ecx,dword ptr[ecx]
310 OpBuffer[obp++]=(char)0x8B;
311 OpBuffer[obp++]=(char)0x09;
312 }
313 else{
314 if(isErrorEnabled) SetError(104,member,cp);
315 return 0;
316 }
317 }
318
319 if(!GetMemberOffset(
320 isErrorEnabled,
321 isWriteAccess,
322 pobj_c->ppobj_Member[i]->TypeInfo.u.pobj_Class,
323 NestMember,
324 pType,
325 pRelativeVar,
326 plpNestIndex,
327 0)) return 0;
328 }
329
330 if(lpPtrOffset[0]){
331 SetRelativeOffset(pType,*plpNestIndex,pRelativeVar,lpPtrOffset);
332 pRelativeVar->dwKind=VAR_DIRECTMEM;
333 }
334
335 return 1;
336}
337void GetWithName(char *buffer){
338 extern WITHINFO WithInfo;
339 int i;
340
341 buffer[0]=0;
342 for(i=0;i<WithInfo.num;i++)
343 lstrcat(buffer,WithInfo.ppName[i]);
344}
345
346int LocalVar_ThisPtrOffset;
347void SetThisPtrToReg(int reg){
348 //自身のオブジェクトのThisポインタをregにコピー
349
350 extern VARIABLE *LocalVar;
351 RELATIVE_VAR RelativeVar;
352 RelativeVar.dwKind=VAR_LOCAL;
353 RelativeVar.bOffsetOffset=0;
354 RelativeVar.offset=-LocalVar_ThisPtrOffset;
355
356 SetReg_WholeVariable(DEF_PTR_VOID,&RelativeVar,reg);
357}
358
359BOOL GetVarOffset(bool isErrorEnabled, bool isWriteAccess, char *NameBuffer, int *pType, RELATIVE_VAR *pRelativeVar, LONG_PTR *plpIndex, int *pss){
360 extern BOOL bCompilingGlobal;
361 int i,RefType;
362 char variable[VN_SIZE],member[VN_SIZE],VarName[VN_SIZE],array[VN_SIZE],lpPtrOffset[VN_SIZE];
363
364 if(NameBuffer[0]=='.'){
365 GetWithName(variable);
366 lstrcat(variable,NameBuffer);
367 }
368 else lstrcpy(variable,NameBuffer);
369
370 lstrcpy(VarName,variable);
371 GetVarFormatString(VarName,array,lpPtrOffset,member,&RefType);
372
373 LONG_PTR lpIndex;
374 int *pSubScripts;
375 bool bConst;
376
377 if(bCompilingGlobal==0){
378 ////////////////////
379 // ローカル変数
380 ////////////////////
381
382 for(i=MaxLocalVarNum-1;i>=0;i--){ //レキシカルスコープを考慮してバックサーチ
383 if(LocalVar[i].bLiving){
384 if(lstrcmp(VarName,LocalVar[i].name)==0) break;
385 }
386 }
387 if(i>=0){
388 //ポインタ変数の場合
389 if(IsPtrType(LocalVar[i].type)){
390 if(LocalVar[i].SubScripts[0]==-1){
391 lstrcpy(lpPtrOffset,array);
392 array[0]=0;
393 }
394 }
395 else{
396 if(lpPtrOffset[0]){
397 SetError(16,variable,cp);
398 pRelativeVar->dwKind=NON_VAR;
399 return 0;
400 }
401 }
402
403 pRelativeVar->offset=-LocalVar[i].offset;
404 pRelativeVar->bOffsetOffset=0;
405 if(LocalVar[i].fRef) pRelativeVar->dwKind=VAR_REFLOCAL;
406 else pRelativeVar->dwKind=VAR_LOCAL;
407 *pType=LocalVar[i].type;
408 lpIndex=LocalVar[i].u.index;
409 if(plpIndex) *plpIndex=lpIndex;
410 pSubScripts=LocalVar[i].SubScripts;
411 bConst = LocalVar[i].bConst;
412
413 goto ok;
414 }
415 }
416
417 if(pobj_CompilingClass){
418 //////////////////////
419 // クラスメンバの参照
420 //////////////////////
421
422 if(lstrcmpi(variable,"This")==0){
423 //Thisオブジェクト
424
425 //Thisポインタをecxにコピー
426 SetThisPtrToReg(REG_ECX);
427
428 *pType=DEF_OBJECT;
429 pRelativeVar->dwKind=VAR_DIRECTMEM;
430
431 if(plpIndex) *plpIndex=(LONG_PTR)pobj_CompilingClass;
432 return 1;
433 }
434
435 if(_memicmp(variable,"This.",5)==0){
436 //Thisオブジェクトのメンバを参照するとき
437 SlideString(variable+5,-5);
438 lstrcpy(VarName,variable);
439 }
440 else{
441 //クラス内メンバを参照するとき(通常)
442
443 for(i=0;i<pobj_CompilingClass->iMemberNum;i++){
444 if(lstrcmp(VarName,pobj_CompilingClass->ppobj_Member[i]->name)==0) break;
445 }
446 if(i==pobj_CompilingClass->iMemberNum) goto NonClassMember;
447 }
448
449 //Const修飾子のメソッド内でメンバ書き込みアクセスが発生したとき
450 //(コンストラクタ、デストラクタ内を除く)
451 CMethod *pMethod = pobj_DBClass->GetNowCompilingMethodInfo();
452 if( isWriteAccess &&
453 pMethod->isConst &&
454 pobj_CompilingClass->IsCompilingConstructor() == false &&
455 pobj_CompilingClass->IsCompilingDestructor() == false
456 ){
457 SetError(131, NULL, cp );
458 }
459
460 /////////////////////////////
461 // thisポインタをecxにセット
462
463 //Thisポインタをecxにコピー
464 SetThisPtrToReg(REG_ECX);
465
466 pRelativeVar->dwKind=VAR_DIRECTMEM;
467 if(!GetMemberOffset(
468 isErrorEnabled,
469 isWriteAccess,
470 pobj_CompilingClass,
471 variable,
472 pType,
473 pRelativeVar,
474 &lpIndex,1)) return 0;
475 if(plpIndex) *plpIndex=lpIndex;
476 return 1;
477 }
478
479NonClassMember:
480
481 //////////////////////////
482 // 静的ローカル変数
483 // ※"Static.Object.Method.Variable"
484 //////////////////////////
485
486 char temporary[VN_SIZE];
487 extern SUBINFO *pCompilingSubInfo;
488 if(pCompilingSubInfo){
489 GetNowStaticVarFullName(VarName,temporary);
490
491 for(i=0;i<MaxGlobalVarNum;i++){
492 if(lstrcmp(temporary,GlobalVar[i].name)==0) break;
493 }
494 if(i!=MaxGlobalVarNum){
495 goto GlobalOk;
496 }
497 }
498
499
500 ////////////////////
501 // グローバル変数
502 ////////////////////
503
504 for(i=MaxGlobalVarNum-1;i>=0;i--){ //レキシカルスコープを考慮してバックサーチ
505 if(GlobalVar[i].bLiving){
506 if(lstrcmp(VarName,GlobalVar[i].name)==0) break;
507 }
508 }
509 if(i>=0){
510 goto GlobalOk;
511 }
512
513
514 //////////////////////////
515 // クラスの静的メンバ
516 //////////////////////////
517
518 if(member[0]){
519 lstrcpy(temporary,member);
520 GetVarFormatString(temporary,array,lpPtrOffset,member,&i);
521
522 char temp2[VN_SIZE];
523 sprintf(temp2,"%s.%s",VarName,temporary);
524 for(i=0;i<MaxGlobalVarNum;i++){
525 if(lstrcmp(temp2,GlobalVar[i].name)==0) break;
526 }
527
528 if(i!=MaxGlobalVarNum){
529 goto GlobalOk;
530 }
531 }
532
533 if(pobj_CompilingClass){
534 //自身のクラスから静的メンバを参照する場合
535 char temp2[VN_SIZE];
536 sprintf(temp2,"%s.%s",pobj_CompilingClass->name,VarName);
537 for(i=0;i<MaxGlobalVarNum;i++){
538 if(lstrcmp(temp2,GlobalVar[i].name)==0) break;
539 }
540
541 if(i!=MaxGlobalVarNum){
542 goto GlobalOk;
543 }
544 }
545
546 if(isErrorEnabled) SetError(3,variable,cp);
547 pRelativeVar->dwKind=NON_VAR;
548 return 0;
549
550
551GlobalOk:
552
553 //ポインタ変数の場合
554 if(IsPtrType(GlobalVar[i].type)){
555 if(GlobalVar[i].SubScripts[0]==-1){
556 lstrcpy(lpPtrOffset,array);
557 array[0]=0;
558 }
559 }
560 else{
561 if(lpPtrOffset[0]){
562 SetError(16,variable,cp);
563 pRelativeVar->dwKind=NON_VAR;
564 return 0;
565 }
566 }
567
568 pRelativeVar->offset=GlobalVar[i].offset;
569 pRelativeVar->bOffsetOffset=0;
570 pRelativeVar->dwKind=VAR_GLOBAL;
571 *pType=GlobalVar[i].type;
572 lpIndex=GlobalVar[i].u.index;
573 if(plpIndex) *plpIndex=lpIndex;
574 pSubScripts=GlobalVar[i].SubScripts;
575 bConst = GlobalVar[i].bConst;
576
577
578ok:
579
580 if( bConst && isWriteAccess ){
581 //Const定義の変数に書き込みアクセスをしようとした場合
582 if( *pType == DEF_OBJECT ){
583 //オブジェクト定数
584 SetError(130, VarName, cp );
585 }
586 else{
587 //一般のConst変数
588 SetError(61,VarName,cp);
589 }
590 }
591
592 if(array[0]==0&&pSubScripts[0]!=-1){
593 //配列の先頭ポインタを示す場合
594 *pType|=FLAG_PTR;
595 if(pss) memcpy(pss,pSubScripts,MAX_ARRAYDIM);
596 return 1;
597 }
598
599 if(array[0]||member[0]){
600 //xor ecx,ecx(ecxを0に初期化する)
601 //※ecxは変数ベースアドレスからの相対オフセットを示す
602 op_zero_reg(REG_ECX);
603
604 pRelativeVar->bOffsetOffset=1;
605 }
606 if(array[0]){
607 if(!GetArrayOffset(pSubScripts,array,*pType,lpIndex)){
608 SetError(14,variable,cp);
609 pRelativeVar->dwKind=NON_VAR;
610 return 0;
611 }
612 }
613 if(member[0]){
614 if(*pType==DEF_OBJECT){
615 //実態オブジェクトのメンバを参照(obj.member)
616 if(RefType!=DEF_OBJECT){
617 SetError(104,VarName,cp);
618 pRelativeVar->dwKind=NON_VAR;
619 return 0;
620 }
621 }
622 else if(*pType==DEF_PTR_OBJECT){
623 //ポインタオブジェクトが示すメンバを参照
624 if(lpPtrOffset[0]){
625 //pObj[n].member
626 if(RefType!=DEF_OBJECT){
627 SetError(104,VarName,cp);
628 pRelativeVar->dwKind=NON_VAR;
629 return 0;
630 }
631 SetRelativeOffset(pType,lpIndex,pRelativeVar,lpPtrOffset);
632 pRelativeVar->dwKind=VAR_DIRECTMEM;
633 }
634 else{
635 //pObj->member
636 if(RefType!=DEF_PTR_OBJECT){
637 SetError(104,VarName,cp);
638 pRelativeVar->dwKind=NON_VAR;
639 return 0;
640 }
641
642 SetVarPtrToEax(pRelativeVar);
643 pRelativeVar->dwKind=VAR_DIRECTMEM;
644
645 //mov ecx,dword ptr[eax]
646 OpBuffer[obp++]=(char)0x8B;
647 OpBuffer[obp++]=(char)0x08;
648 }
649 }
650 else if(*pType==MAKE_PTR_TYPE(DEF_OBJECT,2)){
651 //ポインタオブジェクトが示すメンバを参照
652 if(lpPtrOffset[0]){
653 //ppObj[n]->member
654 if(RefType!=DEF_PTR_OBJECT){
655 SetError(104,VarName,cp);
656 pRelativeVar->dwKind=NON_VAR;
657 return 0;
658 }
659
660 SetRelativeOffset(pType,lpIndex,pRelativeVar,lpPtrOffset);
661 pRelativeVar->dwKind=VAR_DIRECTMEM;
662
663
664 SetVarPtrToEax(pRelativeVar);
665
666 //mov ecx,dword ptr[eax]
667 OpBuffer[obp++]=(char)0x8B;
668 OpBuffer[obp++]=(char)0x08;
669 }
670 else{
671 SetError(104,VarName,cp);
672 pRelativeVar->dwKind=NON_VAR;
673 return 0;
674 }
675 }
676 else{
677 SetError(102,VarName,cp);
678 pRelativeVar->dwKind=NON_VAR;
679 return 0;
680 }
681
682 LONG_PTR lp2;
683 if(!GetMemberOffset(
684 isErrorEnabled,
685 isWriteAccess,
686 (CClass *)lpIndex,
687 member,pType,pRelativeVar,&lp2,0)) return 0;
688 if(plpIndex) *plpIndex=lp2;
689
690 return 1;
691 }
692
693 if(lpPtrOffset[0]){
694 SetRelativeOffset(pType,lpIndex,pRelativeVar,lpPtrOffset);
695 pRelativeVar->dwKind=VAR_DIRECTMEM;
696 }
697
698 return 1;
699}
700
701BOOL SetInitGlobalData(int offset,int type,LONG_PTR lpIndex,int *SubScripts,char *InitBuf){
702 extern BYTE *initGlobalBuf;
703 int i,i2,i3,TypeSize;
704 char temporary[VN_SIZE];
705
706 if(InitBuf[0]=='['){
707 SlideString(InitBuf+1,-1);
708 InitBuf[lstrlen(InitBuf)-1]=0;
709
710 TypeSize=GetTypeSize(type,lpIndex);
711
712 if(SubScripts[0]!=-1){
713 TypeSize*=JumpSubScripts(SubScripts+1);
714 i=0;
715 i2=0;
716 while(1){
717 if(SubScripts[0]<i2){
718 SetError(41,0,cp);
719 return 0;
720 }
721 i=GetOneParameter(InitBuf,i,temporary);
722 if(!SetInitGlobalData(
723 offset+i2*TypeSize,
724 type,
725 lpIndex,
726 SubScripts+1,
727 temporary)) return 0;
728 i2++;
729 if(InitBuf[i]=='\0') break;
730 }
731 return -1;
732 }
733
734 if(type==DEF_OBJECT){
735 CClass *pobj_c;
736 pobj_c=(CClass *)lpIndex;
737
738 for(i=0,i2=0;i2<pobj_c->iMemberNum;i2++){
739 i=GetOneParameter(InitBuf,i,temporary);
740
741 i3=GetSizeOfClassMember(pobj_c,pobj_c->ppobj_Member[i2]->name,NULL);
742
743 if(!SetInitGlobalData(offset+i3,
744 pobj_c->ppobj_Member[i2]->TypeInfo.type,
745 pobj_c->ppobj_Member[i2]->TypeInfo.u.lpIndex,
746 pobj_c->ppobj_Member[i2]->SubScripts,
747 temporary)) return 0;
748
749 if(InitBuf[i]=='\0') break;
750 }
751 if(i2+1!=pobj_c->iMemberNum){
752 SetError(41,0,cp);
753 return 0;
754 }
755 return 1;
756 }
757
758 SetError(41,0,cp);
759 return 0;
760 }
761
762 if(SubScripts[0]!=-1){
763 SetError(41,0,cp);
764 return 0;
765 }
766
767 double dbl;
768 _int64 i64data;
769 int CalcType;
770 LONG_PTR lpCalcIndex;
771 CalcType=StaticCalculation(true, InitBuf,type,&i64data,&lpCalcIndex);
772 if(IsRealNumberType(CalcType)){
773 memcpy(&dbl,&i64data,sizeof(double));
774 i64data=(_int64)dbl;
775 }
776 else dbl=(double)i64data;
777
778 //型チェック
779 CheckDifferentType(
780 type,
781 lpIndex,
782 CalcType,
783 lpCalcIndex,
784 0,0);
785
786 if(type==DEF_DOUBLE)
787 *(double *)(initGlobalBuf+offset)=(double)dbl;
788 else if(type==DEF_SINGLE)
789 *(float *)(initGlobalBuf+offset)=(float)dbl;
790 else if(type==DEF_INT64||type==DEF_QWORD)
791 *(_int64 *)(initGlobalBuf+offset)=i64data;
792 else if(type==DEF_LONG||type==DEF_DWORD||IsPtrType(type)){
793 if(type==DEF_PTR_BYTE&&lpCalcIndex==LITERAL_STRING){
794 //文字列定数のとき
795
796 char *temp;
797 temp=(char *)i64data;
798 i2=AddDataTable(temp,lstrlen(temp));
799 HeapDefaultFree(temp);
800
801 //mov eax,DataPos
802 OpBuffer[obp++]=(char)0xB8;
803 *((long *)(OpBuffer+obp))=(long)i2;
804 pobj_DataTableSchedule->add();
805 obp+=sizeof(long);
806
807 //mov dword ptr[offset],eax
808 OpBuffer[obp++]=(char)0xA3;
809 *((long *)(OpBuffer+obp))=offset;
810 pobj_GlobalVarSchedule->add();
811 obp+=sizeof(long);
812 }
813 else{
814 *(DWORD *)(initGlobalBuf+offset)=(DWORD)i64data;
815 }
816 }
817 else if(type==DEF_INTEGER||type==DEF_WORD)
818 *(WORD *)(initGlobalBuf+offset)=(WORD)i64data;
819 else if(type==DEF_CHAR||type==DEF_BYTE)
820 *(BYTE *)(initGlobalBuf+offset)=(BYTE)i64data;
821 //String型が未完成
822 return 1;
823}
824BOOL InitLocalVar(int offset,int type,LONG_PTR lpIndex,int *SubScripts,char *InitBuf){
825 int i,i2,i3,TypeSize;
826 char temporary[VN_SIZE];
827
828 if(InitBuf[0]=='['){
829 SlideString(InitBuf+1,-1);
830 InitBuf[lstrlen(InitBuf)-1]=0;
831
832 TypeSize=GetTypeSize(type,lpIndex);
833
834 if(SubScripts[0]!=-1){
835 TypeSize*=JumpSubScripts(SubScripts+1);
836 i=0;
837 i2=0;
838 while(1){
839 if(SubScripts[0]<i2){
840 SetError(41,0,cp);
841 return 0;
842 }
843 i=GetOneParameter(InitBuf,i,temporary);
844 if(!InitLocalVar(
845 offset+i2*TypeSize,
846 type,
847 lpIndex,
848 SubScripts+1,
849 temporary)) return 0;
850 i2++;
851 if(InitBuf[i]=='\0') break;
852 }
853 return -1;
854 }
855
856 if(type==DEF_OBJECT){
857 CClass *pobj_c;
858 pobj_c=(CClass *)lpIndex;
859
860 for(i=0,i2=0;i2<pobj_c->iMemberNum;i2++){
861 i=GetOneParameter(InitBuf,i,temporary);
862
863 i3=GetSizeOfClassMember(pobj_c,pobj_c->ppobj_Member[i2]->name,NULL);
864
865 if(!InitLocalVar(offset+i3,
866 pobj_c->ppobj_Member[i2]->TypeInfo.type,
867 pobj_c->ppobj_Member[i2]->TypeInfo.u.lpIndex,
868 pobj_c->ppobj_Member[i2]->SubScripts,
869 temporary)) return 0;
870
871 if(InitBuf[i]=='\0') break;
872 }
873 if(i2+1!=pobj_c->iMemberNum){
874 SetError(41,0,cp);
875 return 0;
876 }
877 return 1;
878 }
879
880 SetError(41,0,cp);
881 return 0;
882 }
883
884 if(SubScripts[0]!=-1){
885 SetError(41,0,cp);
886 return 0;
887 }
888
889 double dbl;
890 _int64 i64data;
891 int CalcType;
892 LONG_PTR lpCalcIndex;
893 CalcType=StaticCalculation(false, InitBuf,type,&i64data,&lpCalcIndex);
894 if(!CalcType){
895 //動的データだった場合
896 return 0;
897 }
898 if(IsRealNumberType(CalcType)){
899 memcpy(&dbl,&i64data,sizeof(double));
900 i64data=(_int64)dbl;
901 }
902 else dbl=(double)i64data;
903
904 //型チェック
905 CheckDifferentType(
906 type,
907 lpIndex,
908 CalcType,
909 lpCalcIndex,
910 0,0);
911
912 if(type==DEF_DOUBLE){
913 //mov eax,HILONG(dbl)
914 OpBuffer[obp++]=(char)0xB8;
915 *((long *)(OpBuffer+obp))=(long)*(long *)(((char *)(&dbl))+4);
916 obp+=sizeof(long);
917
918 //mov dword ptr[ebp+offset+sizeof(long)],eax
919 OpBuffer[obp++]=(char)0x89;
920 OpBuffer[obp++]=(char)0x85;
921 *((long *)(OpBuffer+obp))=offset+sizeof(long);
922 AddLocalVarAddrSchedule();
923 obp+=sizeof(long);
924
925 //mov eax,LOLONG(dbl)
926 OpBuffer[obp++]=(char)0xB8;
927 *((long *)(OpBuffer+obp))=*(long *)(&dbl);
928 obp+=sizeof(long);
929
930 //mov dword ptr[ebp+offset],eax
931 OpBuffer[obp++]=(char)0x89;
932 OpBuffer[obp++]=(char)0x85;
933 *((long *)(OpBuffer+obp))=offset;
934 AddLocalVarAddrSchedule();
935 obp+=sizeof(long);
936 }
937 else if(type==DEF_SINGLE){
938 float flt;
939 flt=(float)dbl;
940 //mov eax,InitValue
941 OpBuffer[obp++]=(char)0xB8;
942 *((long *)(OpBuffer+obp))=*(long *)&flt;
943 obp+=sizeof(long);
944
945 //mov dword ptr[ebp+offset],eax
946 OpBuffer[obp++]=(char)0x89;
947 OpBuffer[obp++]=(char)0x85;
948 *((long *)(OpBuffer+obp))=offset;
949 AddLocalVarAddrSchedule();
950 obp+=sizeof(long);
951 }
952 else if(type==DEF_INT64||type==DEF_QWORD){
953 //mov eax,HILONG(i64data)
954 OpBuffer[obp++]=(char)0xB8;
955 *((long *)(OpBuffer+obp))=(long)*(long *)(((char *)(&i64data))+4);
956 obp+=sizeof(long);
957
958 //mov dword ptr[ebp+offset+sizeof(long)],eax
959 OpBuffer[obp++]=(char)0x89;
960 OpBuffer[obp++]=(char)0x85;
961 *((long *)(OpBuffer+obp))=offset+sizeof(long);
962 AddLocalVarAddrSchedule();
963 obp+=sizeof(long);
964
965 //mov eax,LOLONG(i64data)
966 OpBuffer[obp++]=(char)0xB8;
967 *((long *)(OpBuffer+obp))=*(long *)(&i64data);
968 obp+=sizeof(long);
969
970 //mov dword ptr[ebp+offset],eax
971 OpBuffer[obp++]=(char)0x89;
972 OpBuffer[obp++]=(char)0x85;
973 *((long *)(OpBuffer+obp))=offset;
974 AddLocalVarAddrSchedule();
975 obp+=sizeof(long);
976 }
977 else if(type==DEF_LONG||type==DEF_DWORD||IsPtrType(type)){
978 if(type==DEF_PTR_BYTE&&lpCalcIndex==LITERAL_STRING){
979 //文字列定数のとき
980
981 char *temp;
982 temp=(char *)i64data;
983 i2=AddDataTable(temp,lstrlen(temp));
984 HeapDefaultFree(temp);
985
986 //mov eax,DataPos
987 OpBuffer[obp++]=(char)0xB8;
988 *((long *)(OpBuffer+obp))=(long)i2;
989 pobj_DataTableSchedule->add();
990 obp+=sizeof(long);
991 }
992 else{
993 //mov eax,InitValue
994 OpBuffer[obp++]=(char)0xB8;
995 *((long *)(OpBuffer+obp))=(long)i64data;
996 obp+=sizeof(long);
997 }
998
999 //mov dword ptr[ebp+offset],eax
1000 OpBuffer[obp++]=(char)0x89;
1001 OpBuffer[obp++]=(char)0x85;
1002 *((long *)(OpBuffer+obp))=offset;
1003 AddLocalVarAddrSchedule();
1004 obp+=sizeof(long);
1005 }
1006 else if(type==DEF_INTEGER||type==DEF_WORD){
1007 //mov ax,InitValue
1008 OpBuffer[obp++]=(char)0x66;
1009 OpBuffer[obp++]=(char)0xB8;
1010 *((WORD *)(OpBuffer+obp))=(WORD)i64data;
1011 obp+=sizeof(WORD);
1012
1013 //mov word ptr[ebp+offset],ax
1014 OpBuffer[obp++]=(char)0x66;
1015 OpBuffer[obp++]=(char)0x89;
1016 OpBuffer[obp++]=(char)0x85;
1017 *((long *)(OpBuffer+obp))=offset;
1018 AddLocalVarAddrSchedule();
1019 obp+=sizeof(long);
1020 }
1021 else if(type==DEF_CHAR||type==DEF_BYTE){
1022 //mov byte ptr[ebp+offset],InitValue
1023 OpBuffer[obp++]=(char)0xC6;
1024 OpBuffer[obp++]=(char)0x85;
1025 *((long *)(OpBuffer+obp))=offset;
1026 AddLocalVarAddrSchedule();
1027 obp+=sizeof(long);
1028 *((BYTE *)(OpBuffer+obp))=(BYTE)i64data;
1029 obp+=sizeof(BYTE);
1030 }
1031 //String型が未完成
1032 return 1;
1033}
1034
1035void dim(char *Parameter,DWORD dwFlag){
1036 extern BOOL bCompilingGlobal;
1037 extern HANDLE hHeap;
1038 int i2,i3,VarSize;
1039 char VarName[VN_SIZE];
1040
1041
1042 if(dwFlag & DIMFLAG_CONST){
1043 //////////////////////////////////
1044 // 定数変数の場合を考慮
1045 //////////////////////////////////
1046 for(i2=0;;i2++){
1047 if(Parameter[i2] == '=' ||
1048 Parameter[i2] == 1 && Parameter[i2] == ESC_AS ||
1049 Parameter[i2] =='('){
1050 VarName[i2] = 0;
1051 break;
1052 }
1053 VarName[i2] = Parameter[i2];
1054 }
1055
1056 //定数と2重定義されていないる場合は抜け出す
1057 if(CDBConst::obj.GetType(VarName)){
1058 return;
1059 }
1060
1061 //定数マクロとして定義されている場合は抜け出す
1062 if(GetConstHash(VarName)){
1063 return;
1064 }
1065 }
1066
1067
1068 //構文を解析
1069 int SubScripts[MAX_ARRAYDIM];
1070 TYPEINFO TypeInfo;
1071 char InitBuf[8192];
1072 char ConstractParameter[VN_SIZE];
1073 if(!GetDimentionFormat(Parameter,VarName,SubScripts,&TypeInfo,InitBuf,ConstractParameter))
1074 return;
1075
1076
1077 //定数と2重定義されていないかを調べる
1078 if(CDBConst::obj.GetType(VarName)){
1079 SetError(15,VarName,cp);
1080 return;
1081 }
1082
1083 //定数マクロとして定義されている場合
1084 if(GetConstHash(VarName)){
1085 SetError(15,VarName,cp);
1086 return;
1087 }
1088
1089
1090 //タイプサイズを取得
1091 int TypeSize;
1092 TypeSize=GetTypeSize(TypeInfo.type,TypeInfo.u.lpIndex);
1093
1094 if(dwFlag&DIMFLAG_STATIC){
1095 if(bCompilingGlobal){
1096 SetError(60,NULL,cp);
1097 return;
1098 }
1099
1100 /////////////////////
1101 // Static変数
1102 // ※"Static.Object.Method.Variable"
1103 /////////////////////
1104
1105 char temporary[VN_SIZE];
1106 GetNowStaticVarFullName(VarName,temporary);
1107
1108 AddGlobalVariable(temporary,SubScripts,&TypeInfo,TypeSize,InitBuf,ConstractParameter,dwFlag);
1109
1110 /*
1111 Note: 静的変数のコンストラクタ呼び出しは
1112 _System_InitStaticLocalVariables関数内で一括して行う
1113 */
1114 }
1115 else{
1116 if(bCompilingGlobal){
1117 /////////////////////////
1118 // グローバル変数
1119 /////////////////////////
1120
1121 AddGlobalVariable(VarName,SubScripts,&TypeInfo,TypeSize,InitBuf,ConstractParameter,dwFlag);
1122 }
1123 else{
1124 /////////////////
1125 // ローカル変数
1126 /////////////////
1127
1128 for(i2=0;i2<MaxLocalVarNum;i2++){
1129 if(LocalVar[i2].bLiving&&obj_LexScopes.GetNowLevel()==LocalVar[i2].ScopeLevel){
1130 if(lstrcmp(LocalVar[i2].name,VarName)==0){
1131 //2重定義のエラー
1132 SetError(15,VarName,cp);
1133 return;
1134 }
1135 }
1136 }
1137
1138 LocalVar=(VARIABLE *)HeapReAlloc(hHeap,0,LocalVar,(MaxLocalVarNum+1)*sizeof(VARIABLE));
1139
1140 for(i2=1,i3=0;i3<255;i3++){
1141 //配列要素数
1142 LocalVar[MaxLocalVarNum].SubScripts[i3]=SubScripts[i3];
1143
1144 if(SubScripts[i3]==-1) break;
1145 i2*=SubScripts[i3]+1;
1146 }
1147 VarSize=TypeSize*i2;
1148 if(VarSize%4) VarSize+=4-(VarSize%4);
1149
1150 VARIABLE *pVar = &LocalVar[MaxLocalVarNum];
1151
1152 MaxLocalVarNum++;
1153
1154 //変数データを追加
1155 lstrcpy(pVar->name,VarName);
1156 pVar->fRef=0;
1157 if(dwFlag & DIMFLAG_CONST) pVar->bConst = true;
1158 else pVar->bConst = false;
1159 if(SubScripts[0]==-1) pVar->bArray=0;
1160 else pVar->bArray=1;
1161 pVar->type=TypeInfo.type;
1162 pVar->u.index=TypeInfo.u.lpIndex;
1163 AllLocalVarSize+=VarSize;
1164 pVar->offset=AllLocalVarSize;
1165
1166 //レキシカルスコープ
1167 pVar->ScopeLevel=obj_LexScopes.GetNowLevel();
1168 pVar->ScopeStartAddress=obj_LexScopes.GetStartAddress();
1169 pVar->bLiving=TRUE;
1170
1171 if(InitBuf[0]){
1172 //初期代入時のみ、書き込みアクセスを許可する
1173 bool bConstBack = pVar->bConst;
1174 pVar->bConst = false;
1175
1176 int result = InitLocalVar(-pVar->offset,
1177 pVar->type,
1178 pVar->u.index,
1179 pVar->SubScripts,
1180 InitBuf);
1181
1182 if(!result){
1183 //動的な式だった場合は代入演算を行う
1184 char temporary[8192];
1185 sprintf(temporary,"%s=%s",VarName,InitBuf);
1186 OpcodeCalc(temporary);
1187 }
1188
1189 pVar->bConst = bConstBack;
1190 }
1191 else{
1192 //push 0
1193 op_push_value(0);
1194
1195 //push VarSize
1196 op_push_value(VarSize);
1197
1198 //mov eax,ebp
1199 OpBuffer[obp++]=(char)0x8B;
1200 OpBuffer[obp++]=(char)0xC5;
1201
1202 //add eax,offset
1203 OpBuffer[obp++]=(char)0x05;
1204 *((long *)(OpBuffer+obp))=-pVar->offset;
1205 AddLocalVarAddrSchedule();
1206 obp+=sizeof(long);
1207
1208 //push eax
1209 op_push(REG_EAX);
1210
1211 //call FillMemory
1212 OpBuffer[obp++]=(char)0xFF;
1213 OpBuffer[obp++]=(char)0x15;
1214 DECLAREINFO *pdi;
1215 pdi=GetDeclareHash("FillMemory");
1216 pdi->bUse=1;
1217 pobj_ImportAddrSchedule->add(pdi);
1218 obp+=sizeof(long);
1219 }
1220 }
1221
1222 //コンストラクタ呼び出し
1223 if(TypeInfo.type==DEF_OBJECT&&(dwFlag&DIMFLAG_NONCALL_CONSTRACTOR)==0){
1224 CallConstractor(VarName,SubScripts,TypeInfo,ConstractParameter);
1225 }
1226 }
1227
1228 if(TypeInfo.type==DEF_OBJECT){
1229 if(TypeInfo.u.pobj_Class->IsHoldAbstractFunction()){
1230 //抽象クラスだったとき
1231 SetError(125,TypeInfo.u.pobj_Class->name,cp);
1232 }
1233 }
1234}
1235void OpcodeDim(char *Parameter,DWORD dwFlag){
1236 int i,i2,i3,IsStr=0;
1237 char temporary[8192];
1238
1239 for(i=0,i2=0;;i++,i2++){
1240 if(Parameter[i]=='\"') IsStr^=1;
1241 if(Parameter[i]=='('&&IsStr==0){
1242 i3=GetStringInPare(temporary+i2,Parameter+i);
1243 i+=i3-1;
1244 i2+=i3-1;
1245 continue;
1246 }
1247 if(Parameter[i]=='['&&IsStr==0){
1248 i3=GetStringInBracket(temporary+i2,Parameter+i);
1249 i+=i3-1;
1250 i2+=i3-1;
1251 continue;
1252 }
1253 if((Parameter[i]==','&&IsStr==0)||
1254 Parameter[i]=='\0'){
1255 temporary[i2]=0;
1256
1257 dim(temporary,dwFlag);
1258
1259 if(Parameter[i]=='\0') break;
1260 i2=-1;
1261 continue;
1262 }
1263 temporary[i2]=Parameter[i];
1264 }
1265}
1266
1267void SetVarPtrToEax(RELATIVE_VAR *pRelativeVar){
1268 if(pRelativeVar->dwKind==VAR_GLOBAL){
1269 if(pRelativeVar->bOffsetOffset){
1270 //lea eax,dword ptr[ecx+offset]
1271 OpBuffer[obp++]=(char)0x8D;
1272 OpBuffer[obp++]=(char)0x81;
1273 *((long *)(OpBuffer+obp))=pRelativeVar->offset;
1274 pobj_GlobalVarSchedule->add();
1275 obp+=sizeof(long);
1276 }
1277 else{
1278 //mov eax,offset
1279 OpBuffer[obp++]=(char)0xB8;
1280 *((long *)(OpBuffer+obp))=pRelativeVar->offset;
1281 pobj_GlobalVarSchedule->add();
1282 obp+=sizeof(long);
1283 }
1284 }
1285 else if(pRelativeVar->dwKind==VAR_LOCAL){
1286 if(pRelativeVar->bOffsetOffset){
1287 //add ecx,offset
1288 OpBuffer[obp++]=(char)0x81;
1289 OpBuffer[obp++]=(char)0xC1;
1290 *((long *)(OpBuffer+obp))=pRelativeVar->offset;
1291 AddLocalVarAddrSchedule();
1292 obp+=sizeof(long);
1293
1294 //lea eax,dword ptr[ebp+ecx]
1295 OpBuffer[obp++]=(char)0x8D;
1296 OpBuffer[obp++]=(char)0x44;
1297 OpBuffer[obp++]=(char)0x0D;
1298 OpBuffer[obp++]=(char)0x00;
1299 }
1300 else{
1301 //lea eax,dword ptr[ebp+offset]
1302 OpBuffer[obp++]=(char)0x8D;
1303 OpBuffer[obp++]=(char)0x85;
1304 *((long *)(OpBuffer+obp))=pRelativeVar->offset;
1305 AddLocalVarAddrSchedule();
1306 obp+=sizeof(long);
1307 }
1308 }
1309 else if(pRelativeVar->dwKind==VAR_REFLOCAL){
1310 if(pRelativeVar->bOffsetOffset){
1311 //mov eax,ecx
1312 OpBuffer[obp++]=(char)0x8B;
1313 OpBuffer[obp++]=(char)0xC1;
1314
1315 //add eax,dword ptr[ebp+offset]
1316 OpBuffer[obp++]=(char)0x03;
1317 OpBuffer[obp++]=(char)0x85;
1318 *((long *)(OpBuffer+obp))=pRelativeVar->offset;
1319 AddLocalVarAddrSchedule();
1320 obp+=sizeof(long);
1321 }
1322 else{
1323 //mov eax,dword ptr[ebp+offset]
1324 OpBuffer[obp++]=(char)0x8B;
1325 OpBuffer[obp++]=(char)0x85;
1326 *((long *)(OpBuffer+obp))=pRelativeVar->offset;
1327 AddLocalVarAddrSchedule();
1328 obp+=sizeof(long);
1329 }
1330 }
1331 else if(pRelativeVar->dwKind==VAR_DIRECTMEM){
1332 //mov eax,ecx
1333 OpBuffer[obp++]=(char)0x8B;
1334 OpBuffer[obp++]=(char)0xC1;
1335 }
1336}
Note: See TracBrowser for help on using the repository browser.