source: dev/trunk/ab5.0/abdev/compiler_x86/Compile_Var.cpp @ 745

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