source: dev/trunk/abdev/BasicCompiler_Common/VariableOpe.cpp@ 275

Last change on this file since 275 was 275, checked in by dai_9181, 17 years ago
File size: 26.1 KB
Line 
1#include "stdafx.h"
2
3#include <jenga/include/smoothie/Smoothie.h>
4#include <jenga/include/smoothie/LexicalAnalysis.h>
5
6#include <Compiler.h>
7#include <LexicalScope.h>
8#include <Variable.h>
9#include <NamespaceSupporter.h>
10
11#include "../BasicCompiler_Common/common.h"
12
13#ifdef _AMD64_
14#include "../BasicCompiler64/opcode.h"
15#else
16#include "../BasicCompiler32/opcode.h"
17#endif
18
19BOOL IsPtrType(int type){
20 if(type==-1) return 0;
21
22 if(PTR_LEVEL(type)||type==DEF_PTR_VOID||type==DEF_PTR_PROC||
23 (type&FLAG_PTR) ) return 1;
24
25 return 0;
26}
27BOOL IsSignedType(int type){
28 switch(type){
29 case DEF_SBYTE:
30 case DEF_INTEGER:
31 case DEF_LONG:
32 case DEF_INT64:
33 case DEF_SINGLE:
34 case DEF_DOUBLE:
35 case DEF_CHAR:
36 return 1;
37 default:
38 break;
39 }
40 return 0;
41}
42BOOL IsNaturalWholeNumberType(int type){
43 switch(type){
44 case DEF_SBYTE:
45 case DEF_BYTE:
46 case DEF_INTEGER:
47 case DEF_WORD:
48 case DEF_LONG:
49 case DEF_DWORD:
50 case DEF_INT64:
51 case DEF_QWORD:
52 case DEF_CHAR:
53 return 1;
54 default:
55 break;
56 }
57 return 0;
58}
59BOOL IsWholeNumberType(int type){
60 return (
61 IsNaturalWholeNumberType(type)
62 || IsPtrType(type)
63 || type == DEF_BOOLEAN
64 );
65}
66BOOL IsRealNumberType(int type){
67 switch(type){
68 case DEF_DOUBLE:
69 case DEF_SINGLE:
70 return 1;
71 default:
72 break;
73 }
74 return 0;
75}
76BOOL Is64Type(int type){
77 switch(type){
78 case DEF_INT64:
79 case DEF_QWORD:
80 return 1;
81 default:
82 break;
83 }
84#ifdef _AMD64_
85 return IsPtrType(type);
86#else
87 return 0;
88#endif
89}
90int GetSignedType(int type){
91 switch(type){
92 case DEF_BYTE:
93 return DEF_SBYTE;
94 case DEF_WORD:
95 return DEF_INTEGER;
96 case DEF_DWORD:
97 return DEF_LONG;
98 case DEF_QWORD:
99 return DEF_INT64;
100 default:
101 break;
102 }
103#ifdef _AMD64_
104 if(IsPtrType(type)) return DEF_INT64;
105#else
106 if(IsPtrType(type)) return DEF_LONG;
107#endif
108 return type;
109}
110int GetUnsignedType(int type){
111 switch(type){
112 case DEF_SBYTE:
113 return DEF_BYTE;
114 case DEF_INTEGER:
115 return DEF_WORD;
116 case DEF_LONG:
117 return DEF_DWORD;
118 case DEF_INT64:
119 return DEF_QWORD;
120 case DEF_CHAR:
121 if( Smoothie::IsUnicode() ) return DEF_WORD;
122 return DEF_BYTE;
123 }
124 return type;
125}
126int GetTypeSize(int type,LONG_PTR lpIndex){
127 if(type==DEF_LONG){
128 if(lpIndex==LITERAL_NULL||lpIndex==LITERAL_M128_0||lpIndex==LITERAL_0_255)
129 return sizeof(BYTE);
130 else if(lpIndex==LITERAL_M32768_0||lpIndex==LITERAL_0_65535)
131 return sizeof(WORD);
132
133 return sizeof(DWORD);
134 }
135
136 //整数型
137 if(type==DEF_INT64||type==DEF_QWORD)
138 return sizeof(_int64);
139 else if(type==DEF_LONG||type==DEF_DWORD)
140 return sizeof(DWORD);
141 else if(type==DEF_INTEGER||type==DEF_WORD)
142 return sizeof(WORD);
143 else if(type==DEF_SBYTE||type==DEF_BYTE || type == DEF_BOOLEAN)
144 return sizeof(BYTE);
145
146 //実数型
147 else if(type==DEF_DOUBLE) return sizeof(double);
148 else if(type==DEF_SINGLE) return sizeof(float);
149
150 //文字型
151 else if( type == DEF_CHAR ){
152 if( Smoothie::IsUnicode() ) return sizeof( WORD );
153 return sizeof( BYTE );
154 }
155
156 //ポインタ型
157 else if(IsPtrType(type)) return PTR_SIZE;
158
159 else if( type == DEF_STRUCT ){
160 if(lpIndex == 0 || lpIndex == -1){
161 SetError(300,NULL,cp);
162 return 0;
163 }
164
165 const CClass *pobj_c=(CClass *)lpIndex;
166
167 return pobj_c->GetSize();
168 }
169
170 else if(type==DEF_OBJECT){
171 return PTR_SIZE;
172 }
173 else{
174 SetError(300,NULL,cp);
175 }
176 return 0;
177}
178int GetPtrType(int type){
179 return MAKE_PTR_TYPE(NATURAL_TYPE(type),PTR_LEVEL(type)+1);
180}
181BOOL GetTypeName(int type,LONG_PTR lpIndex,char *name){
182 if(PTR_LEVEL(type)){
183 //ポインタ型
184 name[0]='*';
185 return GetTypeName(MAKE_PTR_TYPE(NATURAL_TYPE(type),PTR_LEVEL(type)-1),lpIndex,name+1);
186 }
187
188 //整数型
189 if(type==DEF_SBYTE) lstrcpy(name,"SByte");
190 else if(type==DEF_BYTE) lstrcpy(name,"Byte");
191 else if(type==DEF_INTEGER) lstrcpy(name,"Integer");
192 else if(type==DEF_WORD) lstrcpy(name,"Word");
193 else if(type==DEF_LONG) lstrcpy(name,"Long");
194 else if(type==DEF_DWORD) lstrcpy(name,"DWord");
195 else if(type==DEF_INT64) lstrcpy(name,"Int64");
196 else if(type==DEF_QWORD) lstrcpy(name,"QWord");
197
198 //実数型
199 else if(type==DEF_SINGLE) lstrcpy(name,"Single");
200 else if(type==DEF_DOUBLE) lstrcpy(name,"Double");
201
202 //文字型
203 //else if(type==DEF_CHAR) lstrcpy(name,"Char");
204
205 //bool型
206 else if(type==DEF_BOOLEAN) lstrcpy(name,"Boolean");
207
208 //オブジェクト
209 else if(type==DEF_OBJECT || type==DEF_STRUCT){
210 if(lpIndex==0) lstrcpy(name,"non");
211 else{
212 lstrcpy(name,((CClass *)lpIndex)->GetName().c_str());
213 }
214 }
215
216 //ポインタ型
217 else if(type==DEF_PTR_VOID) lstrcpy(name,"VoidPtr");
218
219 else if(type==DEF_PTR_PROC){
220 if(lpIndex==-1) lstrcpy(name,"VoidPtr");
221 else{
222 if( compiler.GetObjectModule().meta.GetProcPointers()[lpIndex]->ReturnType().IsNull() )
223 lstrcpy(name,"*Sub");
224 else lstrcpy(name,"*Function");
225 }
226 }
227
228 else{
229 extern int cp;
230 SetError(1,NULL,cp);
231 return 0;
232 }
233 return 1;
234}
235
236Type GetStringTypeInfo(){
237 Type type( DEF_OBJECT, *compiler.GetObjectModule().meta.GetClasses().GetStringClassPtr() );
238 return type;
239}
240
241void GetWithName(char *buffer){
242 extern WITHINFO WithInfo;
243 int i;
244
245 buffer[0]=0;
246 for(i=0;i<WithInfo.num;i++)
247 lstrcat(buffer,WithInfo.ppName[i]);
248}
249
250
251void GetArrange(char *variable,char *variAnswer, Subscripts &subscripts ){
252 extern int cp;
253 int i,i2,i4;
254 double dbl;
255 _int64 i64data;
256 BOOL bBracket;
257 char temporary[VN_SIZE];
258
259 for(i=0;;i++){
260 if(variable[i]=='('||variable[i]=='['){
261 if(variable[i]=='[') bBracket=1;
262 else bBracket=0;
263
264 variAnswer[i]=0;
265 for(i++,i2=0;;i++,i2++){
266 if(variable[i]==','){
267 temporary[i2]=0;
268
269 Type resultType;
270 if( !StaticCalculation(true, temporary,0,&i64data,resultType) ){
271 return;
272 }
273 if(resultType.IsReal()){
274 memcpy(&dbl,&i64data,sizeof(double));
275 i64data=(_int64)dbl;
276 }
277
278 if(i64data<0)
279 {
280 //error
281 subscripts.push_back( 0 );
282 }
283 else
284 {
285 subscripts.push_back( (int)i64data );
286 }
287 i2=-1;
288 continue;
289 }
290 if(variable[i]=='('){
291 i4=GetStringInPare(temporary+i2,variable+i);
292 i2+=i4-1;
293 i+=i4-1;
294 continue;
295 }
296 if(variable[i]=='['){
297 i4=GetStringInBracket(temporary+i2,variable+i);
298 i2+=i4-1;
299 i+=i4-1;
300 continue;
301 }
302 if(variable[i]==')'&&bBracket==0||
303 variable[i]==']'&&bBracket){
304 temporary[i2]=0;
305 if(i2==0){
306 subscripts.push_back( -2 );
307 break;
308 }
309
310 Type resultType;
311 if( !StaticCalculation(true, temporary,0,&i64data,resultType) ){
312 return;
313 }
314 if(resultType.IsReal()){
315 memcpy(&dbl,&i64data,sizeof(double));
316 i64data=(_int64)dbl;
317 }
318
319 if(i64data<0){
320 //error
321 subscripts.push_back( 0 );
322 }
323 else
324 {
325 subscripts.push_back( (int)i64data );
326 }
327 break;
328 }
329 if(variable[i]=='\"'){
330 SetError(1,NULL,cp);
331 return;
332 }
333 temporary[i2]=variable[i];
334 }
335 break;
336 }
337 variAnswer[i]=variable[i];
338 if(variable[i]=='\0'){
339 break;
340 }
341 }
342}
343
344
345BOOL GetVarFormatString(char *buffer,char *array,char *array2,char *NestMember,ReferenceKind &refType){
346 extern int cp;
347 int i,i2,i3;
348 char cPare_Open,cPare_Close;
349
350 array[0]=0;
351 array2[0]=0;
352 NestMember[0]=0;
353 for(i=0;;i++){
354 if(buffer[i]=='\"'){
355 for(i++;;i++){
356 if(IsDBCSLeadByte(buffer[i])){
357 i++;
358 continue;
359 }
360 if(buffer[i]=='\"') break;
361 }
362 }
363 if(buffer[i]=='['||buffer[i]=='('){
364 if(buffer[i]=='['){
365 cPare_Open='[';
366 cPare_Close=']';
367 }
368 else{
369 cPare_Open='(';
370 cPare_Close=')';
371 }
372 buffer[i]=0;
373 for(i++,i2=0;;i++,i2++){
374 if(buffer[i]==cPare_Open){
375 if(cPare_Open=='[') i3=GetStringInBracket(array+i2,buffer+i);
376 else i3=GetStringInPare(array+i2,buffer+i);
377 i+=i3-1;
378 i2+=i3-1;
379 continue;
380 }
381 if(buffer[i]==cPare_Close){
382 array[i2]=0;
383 break;
384 }
385 array[i2]=buffer[i];
386 }
387 if(buffer[i+1]==cPare_Open){
388 for(i+=2,i2=0;;i++,i2++){
389 if(buffer[i]==cPare_Open){
390 if(cPare_Open=='[') i3=GetStringInBracket(array2+i2,buffer+i);
391 else i3=GetStringInPare(array2+i2,buffer+i);
392 i+=i3-1;
393 i2+=i3-1;
394 continue;
395 }
396 if(buffer[i]==cPare_Close){
397 array2[i2]=0;
398 break;
399 }
400 array2[i2]=buffer[i];
401 }
402 if(buffer[i+1]==cPare_Open){
403 SetError(14,buffer,cp);
404 return 0;
405 }
406 }
407 continue;
408 }
409 if(buffer[i]=='.'){
410 lstrcpy(NestMember,buffer+i+1);
411 refType = RefDot;
412 buffer[i]=0;
413 break;
414 }
415 if(buffer[i]==1&&buffer[i+1]==ESC_PSMEM){
416 lstrcpy(NestMember,buffer+i+2);
417 refType = RefPointer;
418 buffer[i]=0;
419 break;
420 }
421 if(buffer[i]=='\0') break;
422 }
423 return 1;
424}
425
426void GetArrayElement( const char *buffer,char *variable,char *array_element){
427 array_element[0]=0;
428
429 if(buffer[lstrlen(buffer)-1]!=']'){
430 lstrcpy(variable,buffer);
431 return;
432 }
433
434 int i,i2;
435 for(i=0;;i++){
436 if(buffer[i]=='\0') break;
437 if(buffer[i]=='['){
438 i2=GetStringInBracket(array_element,buffer+i);
439 i+=i2-1;
440 continue;
441 }
442 }
443
444 lstrcpy(variable,buffer);
445 variable[lstrlen(variable)-lstrlen(array_element)]=0;
446
447 RemoveStringBracket(array_element);
448}
449
450BOOL CheckVarNameError(char *name,int nowLine){
451 int i2;
452
453 if(!IsVariableTopChar(name[0])){
454 SetError(1,NULL,nowLine);
455 return 0;
456 }
457 for(i2=1;;i2++){
458 if(name[i2]=='\0') break;
459 if(!IsVariableChar(name[i2])){
460 SetError(1,NULL,nowLine);
461 return 0;
462 }
463 }
464 return 1;
465}
466
467int JumpSubScripts( const Subscripts &subscripts ){
468 //DIMで定義された並んだ配列の数だけアドレスを進める
469 int i, i2;
470 for( i=0,i2=1; i<(int)subscripts.size(); i++ ){
471 i2 *= subscripts[i] + 1;
472 }
473 return i2;
474}
475
476
477bool GetMemberType( const CClass &objClass, const char *lpszMember, Type &resultType, BOOL bPrivateAccess, bool isErrorEnabled){
478 extern int cp;
479
480 //クラス、配列の構成要素を解析する
481 char VarName[VN_SIZE]; //変数名
482 char array[VN_SIZE]; //第1次配列
483 char lpPtrOffset[VN_SIZE]; //第2次配列
484 char NestMember[VN_SIZE]; //入れ子メンバ
485 ReferenceKind refType = RefNon;
486 lstrcpy(VarName,lpszMember);
487 if(!GetVarFormatString(VarName,array,lpPtrOffset,NestMember,refType)) return false;
488
489 bool isFound = false;
490 CMember *pMember = NULL;
491 BOOST_FOREACH( pMember, objClass.GetDynamicMembers() ){
492 if( pMember->GetName() == VarName ){
493 isFound = true;
494 break;
495 }
496 }
497 if( !isFound ){
498 if(isErrorEnabled) SetError(103,VarName,cp);
499 return false;
500 }
501
502 //アクセシビリティをチェック
503 if( &objClass == compiler.pCompilingClass ){
504 //同一クラスオブジェクトの場合はプライベートアクセスを容認する
505 if( pMember->IsNoneAccess() ){
506 if(isErrorEnabled) SetError(107,VarName,cp);
507 return false;
508 }
509 }
510 else{
511 if(( bPrivateAccess==0 && pMember->IsPrivate() )||
512 pMember->IsNoneAccess() ){
513 if(isErrorEnabled) SetError(107,VarName,cp);
514 return false;
515 }
516 else if( bPrivateAccess==0 && pMember->IsProtected() ){
517 if(isErrorEnabled) SetError(108,VarName,cp);
518 return false;
519 }
520 }
521
522 resultType = pMember->GetType();
523
524 //ポインタ変数の場合
525 if( resultType.IsPointer() ){
526 if( pMember->GetSubscripts().size() == 0 ){
527 lstrcpy(lpPtrOffset,array);
528 array[0]=0;
529 }
530 }
531 else{
532 if(lpPtrOffset[0]){
533 if(isErrorEnabled) SetError(16,lpszMember,cp);
534 return false;
535 }
536 }
537
538 if( refType != RefNon ){
539 //入れ子構造の場合
540
541 return GetMemberType( pMember->GetType().GetClass(),
542 NestMember,
543 resultType,
544 0,
545 isErrorEnabled);
546 }
547
548 if( array[0] == 0 && pMember->GetSubscripts().size() > 0 ){
549 resultType.SetBasicType( resultType.GetBasicType() | FLAG_PTR );
550 return true;
551 }
552
553 if(lpPtrOffset[0]){
554 if( resultType.PtrLevel() ){
555 resultType.PtrLevelDown();
556 }
557 else{
558 //エラー
559 if(isErrorEnabled) SetError(1,NULL,cp);
560 return false;
561 }
562 }
563
564 return true;
565}
566bool GetVarType( const char *nameBuffer, Type &resultType, bool isErrorEnabled){
567 char variable[VN_SIZE];
568
569 if(nameBuffer[0]=='.'){
570 GetWithName(variable);
571 lstrcat(variable,nameBuffer);
572 }
573 else lstrcpy(variable,nameBuffer);
574
575 // 名前空間を分離
576 char namespaceStr[VN_SIZE]="", simpleName[VN_SIZE];
577 compiler.GetObjectModule().meta.GetNamespaces().SplitNamespace( variable, namespaceStr, simpleName );
578
579 // 先頭オブジェクトまたはクラス名と入れ子メンバに分割
580 ReferenceKind refType;
581 char member[VN_SIZE],array[VN_SIZE],lpPtrOffset[VN_SIZE];
582 GetVarFormatString(simpleName,array,lpPtrOffset,member,refType);
583
584 // 名前空間を分離していた場合は結合
585 char VarName[VN_SIZE];
586 if( namespaceStr[0] ){
587 sprintf( VarName, "%s.%s", namespaceStr, simpleName );
588 }
589 else{
590 lstrcpy( VarName, simpleName );
591 }
592
593 const Variable *pVar = NULL;
594
595 if( UserProc::IsLocalAreaCompiling() ){
596 /////////////////
597 // ローカル変数
598 /////////////////
599
600 pVar = UserProc::CompilingUserProc().GetLocalVars().BackSearch( Symbol( VarName ) );
601 if( pVar ){
602 goto ok;
603 }
604 }
605
606 if(compiler.pCompilingClass){
607 ///////////////////////
608 // クラスメンバの参照
609 ///////////////////////
610
611 if(lstrcmpi(variable,"This")==0){
612 //Thisオブジェクト
613 resultType.SetType( DEF_OBJECT, compiler.pCompilingClass );
614 return true;
615 }
616
617 if(memicmp(variable,"This.",5)==0){
618 //Thisオブジェクトのメンバを参照するとき
619 SlideString(variable+5,-5);
620 lstrcpy(VarName,variable);
621 }
622 else{
623 //クラス内メンバを参照するとき(通常)
624
625 bool isFound = false;
626 BOOST_FOREACH( CMember *pMember, compiler.pCompilingClass->GetDynamicMembers() ){
627 if( pMember->GetName() == VarName ){
628 isFound = true;
629 break;
630 }
631 }
632 if( !isFound ) goto NonClassMember;
633 }
634
635 return GetMemberType(*compiler.pCompilingClass,variable,resultType,1,isErrorEnabled);
636 }
637
638NonClassMember:
639
640 //////////////////////////
641 // 静的ローカル変数
642 // ※"Static.Object.Method.Variable"
643 //////////////////////////
644
645 char temporary[VN_SIZE];
646 if( UserProc::IsLocalAreaCompiling() ){
647 GetNowStaticVarFullName(VarName,temporary);
648
649 pVar = compiler.GetObjectModule().meta.GetGlobalVars().Find( Symbol( temporary ) );
650 if( pVar ){
651 goto ok;
652 }
653 }
654
655
656 //////////////////////////
657 // クラスの静的メンバ
658 //////////////////////////
659
660 if(member[0]){
661 lstrcpy(temporary,member);
662 char tempMember[VN_SIZE];
663 char tempArray[VN_SIZE];
664 {
665 ReferenceKind refType;
666 GetVarFormatString(temporary,tempArray,lpPtrOffset,tempMember,refType);
667 }
668
669 int typeDefIndex = compiler.GetObjectModule().meta.GetTypeDefs().GetIndex( VarName );
670 if( typeDefIndex != -1 ){
671 // TypeDef後の型名だったとき
672 lstrcpy( VarName, compiler.GetObjectModule().meta.GetTypeDefs()[typeDefIndex].GetBaseName().c_str() );
673 }
674
675 char temp2[VN_SIZE];
676 sprintf(temp2,"%s.%s",VarName,temporary);
677
678 pVar = compiler.GetObjectModule().meta.GetGlobalVars().Find( Symbol( temp2 ) );
679 if( pVar ){
680 lstrcpy(member,tempMember);
681 lstrcpy(array,tempArray);
682 goto ok;
683 }
684 }
685
686 if(compiler.pCompilingClass){
687 //自身のクラスから静的メンバを参照する場合
688 char temp2[VN_SIZE];
689 sprintf(temp2,"%s.%s",compiler.pCompilingClass->GetName().c_str(),VarName);
690
691 pVar = compiler.GetObjectModule().meta.GetGlobalVars().Find( Symbol( temp2 ) );
692 if( pVar ){
693 goto ok;
694 }
695 }
696
697
698 ////////////////////
699 // グローバル変数
700 ////////////////////
701
702 pVar = compiler.GetObjectModule().meta.GetGlobalVars().BackSearch( Symbol( VarName ) );
703 if( pVar ){
704 goto ok;
705 }
706
707 //変数として見つからなかったとき
708 if(isErrorEnabled) SetError(3,variable,cp);
709 return false;
710
711ok:
712
713 //ポインタ変数の場合
714 if( pVar->GetType().IsPointer() ){
715 if( !pVar->IsArray() ){
716 lstrcpy(lpPtrOffset,array);
717 array[0]=0;
718 }
719 }
720 else{
721 if(lpPtrOffset[0]){
722 if(isErrorEnabled) SetError(16,variable,cp);
723 return false;
724 }
725 }
726
727 resultType = pVar->GetType();
728
729 if(member[0]){
730 if( NATURAL_TYPE( resultType.GetBasicType() )==DEF_OBJECT
731 || NATURAL_TYPE( resultType.GetBasicType() )==DEF_STRUCT){
732 return GetMemberType(resultType.GetClass(),member,resultType,0,isErrorEnabled);
733 }
734 }
735
736 if( array[0] == 0 && pVar->GetSubscripts().size() > 0 ){
737 //配列の先頭ポインタを示す場合
738 resultType.SetBasicType( resultType.GetBasicType() | FLAG_PTR );
739 }
740
741 if(lpPtrOffset[0]){
742 if( resultType.PtrLevel() ){
743 resultType.PtrLevelDown();
744 }
745 else{
746 //エラー
747 if(isErrorEnabled) SetError(1,NULL,cp);
748 return false;
749 }
750 }
751
752 return true;
753}
754
755bool GetVarOffsetReadOnly(const char *NameBuffer,RELATIVE_VAR *pRelativeVar,Type &resultType, Subscripts *pResultSubscripts ){
756 //読み取り専用で変数へアクセス
757 return GetVarOffset(
758 true, //エラー表示有効
759 false, //書き込みアクセスは無し
760 NameBuffer,
761 pRelativeVar,
762 resultType,
763 pResultSubscripts
764 );
765}
766bool GetVarOffsetReadWrite(const char *NameBuffer,RELATIVE_VAR *pRelativeVar,Type &resultType, Subscripts *pResultSubscripts ){
767 //読み書き両用で変数へアクセス
768 return GetVarOffset(
769 true, //エラー表示有効
770 true, //書き込みアクセス
771 NameBuffer,
772 pRelativeVar,
773 resultType,
774 pResultSubscripts
775 );
776}
777
778
779
780bool GetDimentionFormat( const char *buffer,
781 char *VarName,
782 Subscripts &subscripts,
783 Type &type,
784 char *InitBuf,
785 char *ConstractParameter ){
786 int i,i2,i3,IsStr;
787 char variable[VN_SIZE],temporary[8192];
788
789 for(i=0;;i++){
790 if((buffer[i]==1&&buffer[i+1]==ESC_AS)||
791 buffer[i]=='='||
792 buffer[i]=='\0'){
793 variable[i]=0;
794 break;
795 }
796 variable[i]=buffer[i];
797 }
798
799 if(buffer[i]=='='){
800 ////////////////////////////////////
801 // 初期化データが指定されいるとき
802 ////////////////////////////////////
803 i++;
804
805 if( buffer[i]=='[' ){
806 // 構造初期データの場合
807
808 i3=GetStringInBracket(InitBuf,buffer+i);
809 i+=i3;
810 }
811 else{
812 // 代入初期データの場合
813
814 for(i2=0,IsStr=0;;i++,i2++){
815 if(buffer[i]=='\"') IsStr^=1;
816 if(buffer[i]=='('&&IsStr==0){
817 i3=GetStringInPare(InitBuf+i2,buffer+i);
818 i+=i3-1;
819 i2+=i3-1;
820 continue;
821 }
822 if(buffer[i]=='['&&IsStr==0){
823 i3=GetStringInBracket(InitBuf+i2,buffer+i);
824 i+=i3-1;
825 i2+=i3-1;
826 continue;
827 }
828 if((buffer[i]==','&&IsStr==0)||
829 buffer[i]=='\0'){
830 InitBuf[i2]=0;
831 break;
832 }
833 InitBuf[i2]=buffer[i];
834 }
835 }
836 }
837 else{
838 //初期化データなし
839 InitBuf[0]=0;
840 }
841
842 ConstractParameter[0]=0;
843 if(buffer[i]==1&&buffer[i+1]==ESC_AS){
844 /////////////////////////////
845 // "As ~" による型指定あり
846 /////////////////////////////
847
848 for(i+=2,i2=0;;i++,i2++){
849 if(buffer[i]==','||buffer[i]=='('||buffer[i]=='\0'){
850 temporary[i2]=0;
851 break;
852 }
853 temporary[i2]=buffer[i];
854 }
855 if(temporary[0]=='*'&&
856 temporary[1]==1&&
857 (temporary[2]==ESC_FUNCTION||temporary[2]==ESC_SUB)){
858 if(buffer[i]!='('){
859 SetError(10,temporary,cp);
860 return false;
861 }
862 i3=GetStringInPare(temporary+3,buffer+i);
863 i+=i3;
864 i2+=i3;
865
866 if(temporary[2]==ESC_FUNCTION&&buffer[i]==1&&buffer[i+1]==ESC_AS){
867 temporary[i2++]=buffer[i++];
868 temporary[i2++]=buffer[i++];
869 for(;;i++,i2++){
870 if(!IsVariableChar(buffer[i])){
871 temporary[i2]=0;
872 break;
873 }
874 temporary[i2]=buffer[i];
875 }
876 }
877 }
878
879 if( !compiler.StringToType( temporary, type ) ){
880 SetError(3,temporary,cp);
881 type.SetBasicType( DEF_LONG );
882 }
883
884 if(buffer[i]=='('){
885 //コンストラクタに渡すパラメータを取得
886 i2=GetStringInPare(ConstractParameter,buffer+i);
887 i+=i2;
888 RemoveStringPare(ConstractParameter);
889
890 if( !type.IsObject() ){
891 SetError(112,variable,cp);
892 return false;
893 }
894 }
895 }
896 else{
897 /////////////////
898 // As指定なし
899 /////////////////
900
901 if( InitBuf[0] == '\0' ){
902 //As指定も、初期値指定もない場合
903 type.SetBasicType( Type::GetBasicTypeFromSimpleName(variable) );
904
905 i2=lstrlen(variable)-1;
906 if(i2>=0){
907 if(!(variable[i2]=='#'||variable[i2]=='!'||variable[i2]=='%'||variable[i2]=='$'))
908 SetError(-103,variable,cp);
909 }
910 }
911 else{
912 //初期値の型を判別して自動的に型情報を付加する
913 if( !NumOpe_GetType( InitBuf, GetStringTypeInfo(), type ) ){
914 // エラーの場合
915 return false;
916 }
917
918 if( IS_LITERAL( type.GetIndex() ) ){
919 type.SetIndex( -1 );
920 }
921 }
922
923 }
924
925 if( InitBuf[0] != '\0' && ConstractParameter[0] != '\0' ){
926 //初期値とコンストラクタパラメータが同時に呼び出されているとき
927 SetError(132, NULL, cp);
928 }
929
930 GetArrange(variable,VarName,subscripts);
931 return true;
932}
933
934BOOL GetNowStaticVarFullName(char *VarName,char *FullName){
935 if( UserProc::IsGlobalAreaCompiling() ){
936 // グローバル領域をコンパイル中のとき
937 return 0;
938 }
939
940 const UserProc &proc = UserProc::CompilingUserProc();
941
942 //Static識別
943 lstrcpy(FullName,"Static%");
944
945 //クラス名
946 if(compiler.pCompilingClass){
947 lstrcat(FullName,compiler.pCompilingClass->GetName().c_str());
948 lstrcat(FullName,"%");
949 }
950
951 //関数(またはメソッド)名
952 lstrcat(FullName,proc.GetName().c_str());
953 lstrcat(FullName,"%");
954
955 //ID
956 char temp[255];
957 sprintf(temp,"%x",proc.GetId());
958 lstrcat(FullName,temp);
959 lstrcat(FullName,"%");
960
961 //変数名
962 lstrcat(FullName,VarName);
963
964 return 1;
965}
966
967
968void AddGlobalVariable( const char *name, const Subscripts &subscripts, const Type &type,const char *InitBuf,const char *ConstractParameter,DWORD dwFlag){
969 /////////////////////////
970 // グローバル変数を追加
971 /////////////////////////
972
973 if( compiler.GetObjectModule().meta.GetGlobalVars().DuplicateCheck( Symbol( name ) ) ){
974 //2重定義のエラー
975 SetError(15,name,cp);
976 return;
977 }
978
979 bool isConst = ( dwFlag & DIMFLAG_CONST ) ? true:false;
980
981 Variable *pVar = new Variable(
982 compiler.GetNamespaceSupporter().GetLivingNamespaceScopes(),
983 name,
984 type,
985 isConst,
986 false,
987 ConstractParameter,
988 ( InitBuf[0] != 0 || dwFlag == DIMFLAG_INITDEBUGVAR )
989 );
990
991 if( subscripts.size() > 0 ){
992 //配列あり
993 pVar->SetArray( subscripts );
994 }
995
996 //レキシカルスコープ
997 pVar->SetScopeLevel( compiler.codeGenerator.lexicalScopes.GetNowLevel() );
998 pVar->SetScopeStartAddress( compiler.codeGenerator.lexicalScopes.GetStartAddress() );
999 pVar->bLiving=TRUE;
1000
1001 //エラー用
1002 pVar->source_code_address=cp;
1003
1004 // 変数を追加
1005 compiler.GetObjectModule().meta.GetGlobalVars().Add( pVar );
1006
1007 if(InitBuf[0]){
1008 int result = 0;
1009 if( !pVar->GetType().IsObject() ){
1010 //初期バッファにデータをセット
1011 extern BYTE *initGlobalBuf;
1012 initGlobalBuf = (BYTE *)HeapReAlloc(
1013 hHeap,
1014 HEAP_ZERO_MEMORY,
1015 initGlobalBuf,
1016 compiler.GetObjectModule().meta.GetGlobalVars().GetAllInitSize()
1017 );
1018
1019 result = SetInitGlobalData(pVar->GetOffsetAddress(),
1020 pVar->GetType(),
1021 pVar->GetSubscripts(),
1022 InitBuf);
1023 }
1024
1025 if(!result){
1026 //動的な式だった場合は代入演算を行う
1027
1028 //初期代入時のみ、書き込みアクセスを許可する
1029 if( isConst ){
1030 pVar->ConstOff();
1031 }
1032
1033 //代入
1034 char temporary[8192];
1035 sprintf(temporary,"%s=%s",name,InitBuf);
1036 OpcodeCalc(temporary);
1037
1038 //アクセス制限を元に戻す
1039 if( isConst ){
1040 pVar->ConstOn();
1041 }
1042 }
1043 }
1044
1045
1046 if( type.IsObject() ){
1047 //デストラクタの利用フラグをオンにする
1048 const CMethod *method = type.GetClass().GetDestructorMethod();
1049 if( method ){
1050 method->GetUserProc().Using();
1051 }
1052 }
1053}
1054
1055void dim(char *Parameter,DWORD dwFlags){
1056 extern HANDLE hHeap;
1057 int i2;
1058 char VarName[VN_SIZE];
1059
1060 i2 = 0;
1061
1062 if( Parameter[i2] == 1 && Parameter[i2+1] == ESC_BYREF ){
1063 //参照型
1064 SetError();
1065 Parameter += 2;
1066 }
1067
1068 if(dwFlags & DIMFLAG_CONST){
1069
1070 //////////////////////////////////
1071 // 定数変数の場合を考慮
1072 //////////////////////////////////
1073 for(;;i2++){
1074 if(Parameter[i2] == '=' ||
1075 Parameter[i2] == 1 && Parameter[i2] == ESC_AS ||
1076 Parameter[i2] =='('){
1077 VarName[i2] = 0;
1078 break;
1079 }
1080 VarName[i2] = Parameter[i2];
1081 }
1082
1083 //定数と2重定義されていないる場合は抜け出す
1084 if(compiler.GetObjectModule().meta.GetGlobalConsts().GetBasicType(VarName)){
1085 return;
1086 }
1087
1088 //定数マクロとして定義されている場合は抜け出す
1089 if( compiler.GetObjectModule().meta.GetGlobalConstMacros().IsExist( VarName ) )
1090 {
1091 return;
1092 }
1093 }
1094
1095 //構文を解析
1096 Type type;
1097 char InitBuf[8192];
1098 char ConstractParameter[VN_SIZE];
1099 Subscripts subscripts;
1100 if(!GetDimentionFormat(Parameter, VarName,subscripts,type,InitBuf,ConstractParameter))
1101 return;
1102
1103
1104 //定数と2重定義されていないかを調べる
1105 if(compiler.GetObjectModule().meta.GetGlobalConsts().GetBasicType(VarName)){
1106 SetError(15,VarName,cp);
1107 return;
1108 }
1109
1110 //定数マクロとして定義されている場合
1111 if( compiler.GetObjectModule().meta.GetGlobalConstMacros().IsExist( VarName ) ){
1112 SetError(15,VarName,cp);
1113 return;
1114 }
1115
1116 if( type.IsObject() ){
1117 if( type.GetClass().IsBlittableType() ){
1118 // Blittable型のときは基本型として扱う
1119 // ※ただし、コンパイル中のメソッドがBlittable型クラスに属していないこと
1120 if( UserProc::IsLocalAreaCompiling()
1121 && UserProc::CompilingUserProc().HasParentClass()
1122 && UserProc::CompilingUserProc().GetParentClass().IsBlittableType() )
1123 {
1124 // コンパイル中のメソッドがBlittable型クラスに属している
1125 }
1126 else{
1127 type = type.GetClass().GetBlittableType();
1128 }
1129 }
1130 }
1131
1132 if(dwFlags&DIMFLAG_STATIC){
1133 if( UserProc::IsGlobalAreaCompiling() ){
1134 SetError(60,NULL,cp);
1135 return;
1136 }
1137
1138 /////////////////////
1139 // Static変数
1140 // ※"Static.Object.Method.Variable"
1141 /////////////////////
1142
1143 char temporary[VN_SIZE];
1144 GetNowStaticVarFullName(VarName,temporary);
1145
1146 dim( temporary,subscripts,type,InitBuf,ConstractParameter,dwFlags );
1147
1148 /*
1149 Note: 静的変数のコンストラクタ呼び出しは
1150 _System_InitStaticLocalVariables関数内で一括して行う
1151 */
1152 }
1153 else{
1154 dim( VarName,subscripts,type,InitBuf,ConstractParameter,dwFlags );
1155 }
1156}
1157void OpcodeDim(char *Parameter,DWORD dwFlags){
1158 int i,i2,i3,IsStr=0;
1159 char temporary[8192];
1160
1161 for(i=0,i2=0;;i++,i2++){
1162 if(Parameter[i]=='\"') IsStr^=1;
1163 if(Parameter[i]=='('&&IsStr==0){
1164 i3=GetStringInPare(temporary+i2,Parameter+i);
1165 i+=i3-1;
1166 i2+=i3-1;
1167 continue;
1168 }
1169 if(Parameter[i]=='['&&IsStr==0){
1170 i3=GetStringInBracket(temporary+i2,Parameter+i);
1171 i+=i3-1;
1172 i2+=i3-1;
1173 continue;
1174 }
1175 if((Parameter[i]==','&&IsStr==0)||
1176 Parameter[i]=='\0'){
1177 temporary[i2]=0;
1178
1179 dim(temporary,dwFlags);
1180
1181 if(Parameter[i]=='\0') break;
1182 i2=-1;
1183 continue;
1184 }
1185 temporary[i2]=Parameter[i];
1186 }
1187}
Note: See TracBrowser for help on using the repository browser.