source: dev/trunk/ab5.0/abdev/BasicCompiler_Common/src/LexicalAnalyzer_Class.cpp@ 553

Last change on this file since 553 was 546, checked in by dai_9181, 16 years ago

LexicalAnalyzerのソースコードの記述位置を整理。

File size: 29.3 KB
Line 
1#include "stdafx.h"
2
3#include <Source.h>
4#include <Class.h>
5#include <Compiler.h>
6
7#include "../common.h"
8#ifdef _AMD64_
9#include "../../compiler_x64/opcode.h"
10#else
11#include "../../compiler_x86/opcode.h"
12#endif
13
14using namespace ActiveBasic::Compiler;
15
16
17void LexicalAnalyzer::CollectClassesForNameOnly( const char *source, Classes &classes )
18{
19 int i, i2;
20 char temporary[VN_SIZE];
21
22 // 名前空間管理
23 NamespaceScopes &namespaceScopes = compiler.GetNamespaceSupporter().GetLivingNamespaceScopes();
24 namespaceScopes.clear();
25
26 // Importsされた名前空間の管理
27 NamespaceScopesCollection &importedNamespaces = compiler.GetNamespaceSupporter().GetImportedNamespaces();
28 importedNamespaces.clear();
29
30 for(i=0;;i++){
31 if(source[i]=='\0') break;
32
33 if( source[i] == 1 && source[i+1] == ESC_NAMESPACE ){
34 for(i+=2,i2=0;;i2++,i++){
35 if( IsCommandDelimitation( source[i] ) ){
36 temporary[i2]=0;
37 break;
38 }
39 temporary[i2]=source[i];
40 }
41 namespaceScopes.push_back( temporary );
42
43 continue;
44 }
45 else if( source[i] == 1 && source[i+1] == ESC_ENDNAMESPACE ){
46 if( namespaceScopes.size() <= 0 ){
47 compiler.errorMessenger.Output(12, "End Namespace", i );
48 }
49 else{
50 namespaceScopes.pop_back();
51 }
52
53 i += 2;
54 continue;
55 }
56 else if( source[i] == 1 && source[i+1] == ESC_IMPORTS ){
57 for(i+=2,i2=0;;i2++,i++){
58 if( IsCommandDelimitation( source[i] ) ){
59 temporary[i2]=0;
60 break;
61 }
62 temporary[i2]=source[i];
63 }
64 if( !compiler.GetNamespaceSupporter().ImportsNamespace( temporary ) )
65 {
66 compiler.errorMessenger.Output(64,temporary,i );
67 }
68
69 continue;
70 }
71 else if( source[i] == 1 && source[i+1] == ESC_CLEARNAMESPACEIMPORTED ){
72 importedNamespaces.clear();
73 continue;
74 }
75
76 if(source[i]==1&&(
77 source[i+1]==ESC_CLASS||
78 source[i+1]==ESC_TYPE||
79 source[i+1]==ESC_INTERFACE
80 ))
81 {
82 int nowLine = i;
83 i += 2;
84
85 Type blittableType;
86 if(memicmp(source+i,"Align(",6)==0){
87 //アラインメント修飾子
88 i+=6;
89 i=JumpStringInPare(source,i)+1;
90 }
91 else if( memicmp( source + i, "Blittable(", 10 ) == 0 ){
92 // Blittable修飾子
93 i+=10;
94 i+=GetStringInPare_RemovePare(temporary,source+i)+1;
95 compiler.StringToType( temporary, blittableType );
96 }
97
98 bool isEnum = false;
99 bool isDelegate = false;
100 if( source[i] == 1 && source[i+1] == ESC_ENUM ){
101 // 列挙型の場合
102 isEnum = true;
103
104 i += 2;
105 }
106 else if( source[i] == 1 && source[i+1] == ESC_DELEGATE )
107 {
108 // デリゲートの場合
109 isDelegate = true;
110
111 i += 2;
112 }
113
114 for(i2=0;;i++,i2++){
115 if(!IsVariableChar(source[i])){
116 temporary[i2]=0;
117 break;
118 }
119 temporary[i2]=source[i];
120 }
121
122 //クラスを追加
123 CClass *pClass = classes.Add(namespaceScopes, importedNamespaces, temporary,nowLine);
124 if( pClass ){
125 if( source[nowLine+1] == ESC_CLASS ){
126 if( isEnum )
127 {
128 pClass->SetClassType( CClass::Enum );
129 }
130 else if( isDelegate )
131 {
132 pClass->SetClassType( CClass::Delegate );
133 }
134 else{
135 pClass->SetClassType( CClass::Class );
136 }
137 }
138 else if( source[nowLine+1] == ESC_INTERFACE ){
139 pClass->SetClassType( CClass::Interface );
140 }
141 else{
142 pClass->SetClassType( CClass::Structure );
143 }
144 }
145
146 // Blittable型の場合
147 if( !blittableType.IsNull() ){
148 pClass->SetBlittableType( blittableType );
149
150 // Blittable型として登録
151 compiler.GetObjectModule().meta.GetBlittableTypes().push_back( BlittableType( blittableType, pClass ) );
152 }
153 }
154 }
155}
156
157
158class CLoopRefCheck{
159 char **names;
160 int num;
161 void init(){
162 int i;
163 for(i=0;i<num;i++){
164 free(names[i]);
165 }
166 free(names);
167 }
168public:
169 CLoopRefCheck()
170 {
171 names=(char **)malloc(1);
172 num=0;
173 }
174 ~CLoopRefCheck()
175 {
176 init();
177 }
178 void add(const char *lpszInheritsClass)
179 {
180 names=(char **)realloc(names,(num+1)*sizeof(char *));
181 names[num]=(char *)malloc(lstrlen(lpszInheritsClass)+1);
182 lstrcpy(names[num],lpszInheritsClass);
183 num++;
184 }
185 void del(const char *lpszInheritsClass)
186 {
187 int i;
188 for(i=0;i<num;i++){
189 if(lstrcmp(names[i],lpszInheritsClass)==0){
190 free(names[i]);
191 break;
192 }
193 }
194 if(i!=num){
195 num--;
196 for(;i<num;i++){
197 names[i]=names[i+1];
198 }
199 }
200 }
201 BOOL check(const CClass &inheritsClass) const
202 {
203 //ループ継承チェック
204 int i;
205 for(i=0;i<num;i++){
206 if( inheritsClass.GetName() == names[i] ){
207 return 1;
208 }
209 }
210 return 0;
211 }
212};
213CLoopRefCheck *pobj_LoopRefCheck;
214
215bool MemberVar_LoopRefCheck(const CClass &objClass){
216 if( objClass.HasSuperClass() )
217 {
218 // 基底クラスをチェック
219 if( MemberVar_LoopRefCheck( objClass.GetSuperClass() ) == false )
220 {
221 return false;
222 }
223 }
224
225 bool result = true;
226 BOOST_FOREACH( CMember *pMember, objClass.GetDynamicMembers() ){
227 if(pMember->GetType().IsStruct()){
228 //循環参照でないかをチェック
229 if(pobj_LoopRefCheck->check(pMember->GetType().GetClass())){
230 extern int cp;
231 compiler.errorMessenger.Output(124,pMember->GetType().GetClass().GetName(),cp);
232 return false;
233 }
234
235 pobj_LoopRefCheck->add(objClass.GetName().c_str());
236
237 bool tempResult = MemberVar_LoopRefCheck(pMember->GetType().GetClass());
238 if( result )
239 {
240 result = tempResult;
241 }
242
243 pobj_LoopRefCheck->del(objClass.GetName().c_str());
244 }
245 }
246
247 return result;
248}
249
250void LexicalAnalyzer::AddMethod(CClass *pobj_c, UserProc *pUserProc, Prototype::Accessibility accessibility, BOOL bStatic, bool isConst, bool isAbstract,
251 bool isVirtual, bool isOverride, const char *interfaceName, bool isAutoGeneration, int nowLine)
252{
253 if( isAutoGeneration )
254 {
255 // コード自動生成
256 pUserProc->ThisIsAutoGenerationProc();
257 }
258
259
260 ////////////////////////////////////////////////////////////
261 // コンストラクタ、デストラクタの場合の処理
262 ////////////////////////////////////////////////////////////
263 BOOL fConstructor=0,bDestructor=0;
264
265 if( pUserProc->GetName() == pobj_c->GetName() ){
266 //コンストラクタの場合
267
268 //標準コンストラクタ(引数なし)
269 if(pUserProc->Params().size()==0) fConstructor=1;
270
271 //強制的にConst修飾子をつける
272 isConst = true;
273 }
274 else if(pUserProc->GetName()[0]=='~'){
275 //デストラクタの場合はその名前が正しいかチェックを行う
276 if(lstrcmp(pUserProc->GetName().c_str()+1,pobj_c->GetName().c_str())!=0)
277 compiler.errorMessenger.Output(117,NULL,nowLine);
278 else
279 bDestructor=1;
280 }
281 if(fConstructor||bDestructor){
282 // コンストラクタ、デストラクタのアクセシビリティをチェック
283
284 //強制的にConst修飾子をつける
285 isConst = true;
286 }
287
288 if( fConstructor == 1 )
289 pobj_c->SetConstructorMemberSubIndex( (int)pobj_c->GetDynamicMethods().size() );
290 else if( bDestructor )
291 pobj_c->SetDestructorMemberSubIndex( (int)pobj_c->GetDynamicMethods().size() );
292
293
294
295 //////////////////
296 // 重複チェック
297 //////////////////
298
299 if(pobj_c->DupliCheckMember( pUserProc->GetName().c_str() )){
300 compiler.errorMessenger.Output(15,pUserProc->GetName(),nowLine);
301 return;
302 }
303
304 //メソッド
305 BOOST_FOREACH( const CMethod *pMethod, pobj_c->GetDynamicMethods() )
306 {
307 //基底クラスと重複する場合はオーバーライドを行う
308 if( pMethod->GetInheritsClassPtr() ) continue;
309
310 if( pMethod->GetUserProc().IsEqualForOverride( pobj_c->GetSuperClassActualTypeParameters(), pUserProc ) )
311 {
312 //関数名、パラメータ、戻り値が合致したとき
313 compiler.errorMessenger.Output(15,pUserProc->GetName().c_str(),nowLine);
314 return;
315 }
316 }
317
318 //仮想関数の場合
319 if( isAbstract ) pUserProc->CompleteCompile();
320
321 // メソッドのオーバーライド
322 CMethod *pMethodForOverride = pobj_c->GetDynamicMethods().FindForOverride( pobj_c->GetSuperClassActualTypeParameters(), pUserProc );
323 if( pMethodForOverride )
324 {
325 pMethodForOverride->Override( pUserProc, accessibility, isOverride );
326 pUserProc->SetMethod( pMethodForOverride );
327 return;
328 }
329 else
330 {
331 // インターフェイス メソッドのオーバーライド
332 BOOST_FOREACH( ::Interface *pInterface, pobj_c->GetInterfaces() )
333 {
334 if( interfaceName[0] )
335 {
336 if( pInterface->GetClass().GetName() != interfaceName )
337 {
338 // 指定されたインターフェイス名と整合しないとき
339 continue;
340 }
341 }
342
343 if( !pInterface->GetClass().IsReady() ){
344 // インターフェイスが未解析のとき
345 LexicalAnalyzer::LookaheadClass(
346 pInterface->GetClass().GetName().c_str(),
347 compiler.GetObjectModule().meta.GetClasses()
348 );
349 }
350
351 CMethod *pMethodForOverride = pInterface->GetDynamicMethods().FindForOverride( pInterface->GetActualTypeParameters(), pUserProc );
352 if( pMethodForOverride )
353 {
354 pMethodForOverride->Override( pUserProc, accessibility, isOverride );
355 pUserProc->SetMethod( pMethodForOverride );
356 return;
357 }
358 }
359 }
360
361 if( interfaceName[0] )
362 {
363 compiler.errorMessenger.Output(139,interfaceName,nowLine);
364 }
365
366 if( isVirtual ){
367 pobj_c->AddVtblNum( 1 );
368 }
369
370 if( isOverride ){
371 compiler.errorMessenger.Output(12,"Override",nowLine);
372 }
373
374 if(bStatic){
375 pobj_c->GetStaticMethods().AddStatic( pUserProc, accessibility );
376 }
377 else{
378 pobj_c->GetDynamicMethods().Add(pUserProc, accessibility, isConst, isAbstract, isVirtual);
379 }
380}
381
382bool LexicalAnalyzer::Inherits( CClass &currentClass, const char *inheritNames, int nowLine ){
383 int i = 0;
384 bool isInheritsClass = false;
385 while( true ){
386
387 char temporary[VN_SIZE];
388 for( int i2=0;; i++, i2++ ){
389 if( inheritNames[i] == '\0' || inheritNames[i] == ',' ){
390 temporary[i2] = 0;
391 break;
392 }
393 temporary[i2] = inheritNames[i];
394 }
395
396 // ジェネリクス構文を分解
397 char className[VN_SIZE];
398 Jenga::Common::Strings typeParameterStrings;
399 SplitGenericClassInstance( temporary, className, typeParameterStrings );
400
401 // 型パラメータ文字列から型データを取得
402 Types actualTypeParameters;
403 BOOST_FOREACH( const std::string &typeParameterStr, typeParameterStrings )
404 {
405 Type type;
406 compiler.StringToType( typeParameterStr, type );
407 actualTypeParameters.push_back( type );
408 }
409
410 //継承元クラスを取得
411 const CClass *pInheritsClass = compiler.GetObjectModule().meta.GetClasses().Find(className);
412 if( !pInheritsClass ){
413 compiler.errorMessenger.Output(106,className,nowLine);
414 return false;
415 }
416
417 if( pInheritsClass->IsClass() ){
418 // クラスを継承する
419 isInheritsClass = true;
420
421 //ループ継承でないかをチェック
422 if( !LexicalAnalyzer::LoopRefCheck(*pInheritsClass) )
423 {
424 compiler.errorMessenger.Output(123,pInheritsClass->GetName(),nowLine);
425 return false;
426 }
427
428 if( !pInheritsClass->IsReady() ){
429 //継承先が読み取られていないとき
430 LexicalAnalyzer::LookaheadClass(
431 pInheritsClass->GetName().c_str(),
432 compiler.GetObjectModule().meta.GetClasses()
433 );
434 }
435
436 if( !currentClass.InheritsClass( *pInheritsClass, actualTypeParameters, nowLine ) ){
437 return false;
438 }
439 }
440 else{
441 compiler.errorMessenger.Output(135,pInheritsClass->GetFullName().c_str(),nowLine);
442 return false;
443 }
444
445 if( inheritNames[i] == '\0' ){
446 break;
447 }
448 i++;
449 }
450
451 if( !isInheritsClass ){
452 const CClass *pObjectClass = compiler.GetObjectModule().meta.GetClasses().GetObjectClassPtr();
453 //ループ継承でないかをチェック
454 if( !LexicalAnalyzer::LoopRefCheck( *pObjectClass ) )
455 {
456 compiler.errorMessenger.Output(123,pObjectClass->GetName(),nowLine);
457 return false;
458 }
459
460 if( !pObjectClass->IsReady() ){
461 //継承先が読み取られていないとき
462 LexicalAnalyzer::LookaheadClass(
463 pObjectClass->GetName().c_str(),
464 compiler.GetObjectModule().meta.GetClasses()
465 );
466 }
467
468 // クラスを一つも継承していないとき
469 if( !currentClass.InheritsClass( *pObjectClass, Types(), nowLine ) ){
470 return false;
471 }
472 }
473
474 return true;
475}
476
477bool LexicalAnalyzer::Implements( CClass &currentClass, const char *interfaceNames, int nowLine )
478{
479 Jenga::Common::Strings paramStrs;
480 SplitParameter( interfaceNames, paramStrs );
481
482 BOOST_FOREACH( const std::string &paramStr, paramStrs )
483 {
484 char className[VN_SIZE];
485 Jenga::Common::Strings typeParameterStrings;
486 SplitGenericClassInstance( paramStr.c_str(), className, typeParameterStrings );
487
488 Types actualTypeParameters;
489 BOOST_FOREACH( const std::string &typeParameterStr, typeParameterStrings )
490 {
491 Type type;
492 compiler.StringToType( typeParameterStr, type );
493 actualTypeParameters.push_back( type );
494 }
495
496 //継承元クラスを取得
497 const CClass *pInterfaceClass = compiler.GetObjectModule().meta.GetClasses().Find( className );
498 if( !pInterfaceClass ){
499 compiler.errorMessenger.Output(106,paramStr.c_str(),nowLine);
500 continue;
501 }
502
503 if( !pInterfaceClass->IsReady() ){
504 // インターフェイスが未解析のとき
505 LexicalAnalyzer::LookaheadClass(
506 pInterfaceClass->GetName().c_str(),
507 compiler.GetObjectModule().meta.GetClasses()
508 );
509 }
510
511 // インターフェイスを継承する
512 currentClass.Implements( *pInterfaceClass, actualTypeParameters, nowLine );
513 }
514
515 return true;
516}
517
518void GetClass_recur( const char *lpszInheritsClass, Classes &classes )
519{
520 extern char *basbuf;
521 int i,i2,i3,sub_address,top_pos;
522 char temporary[8192];
523
524 // 名前空間管理
525 NamespaceScopes backupNamespaceScopes = compiler.GetNamespaceSupporter().GetLivingNamespaceScopes();
526 NamespaceScopes &namespaceScopes = compiler.GetNamespaceSupporter().GetLivingNamespaceScopes();
527 namespaceScopes.clear();
528
529 // Importsされた名前空間の管理
530 NamespaceScopesCollection backupImportedNamespaces = compiler.GetNamespaceSupporter().GetImportedNamespaces();
531 compiler.GetNamespaceSupporter().GetImportedNamespaces().clear();
532
533 // 呼び出し元でコンパイル中のクラスポインタをバックアップ
534 const CClass *pBackCompilingClass = compiler.IsCompilingClass()
535 ? &compiler.GetCompilingClass()
536 : NULL;
537
538 for(i=0;;i++){
539 if(basbuf[i]=='\0') break;
540
541
542 // 名前空間
543 if( basbuf[i] == 1 && basbuf[i+1] == ESC_NAMESPACE ){
544 for(i+=2,i2=0;;i2++,i++){
545 if( IsCommandDelimitation( basbuf[i] ) ){
546 temporary[i2]=0;
547 break;
548 }
549 temporary[i2]=basbuf[i];
550 }
551 namespaceScopes.push_back( temporary );
552
553 continue;
554 }
555 else if( basbuf[i] == 1 && basbuf[i+1] == ESC_ENDNAMESPACE ){
556 if( namespaceScopes.size() <= 0 ){
557 compiler.errorMessenger.Output(12, "End Namespace", i );
558 }
559 else{
560 namespaceScopes.pop_back();
561 }
562
563 i += 2;
564 continue;
565 }
566
567 else if( basbuf[i] == 1 && basbuf[i+1] == ESC_IMPORTS ){
568 for(i+=2,i2=0;;i2++,i++){
569 if( IsCommandDelimitation( basbuf[i] ) ){
570 temporary[i2]=0;
571 break;
572 }
573 temporary[i2]=basbuf[i];
574 }
575 if( !compiler.GetNamespaceSupporter().ImportsNamespace( temporary ) )
576 {
577 compiler.errorMessenger.Output(64,temporary,i );
578 }
579
580 continue;
581 }
582 else if( basbuf[i] == 1 && basbuf[i+1] == ESC_CLEARNAMESPACEIMPORTED ){
583 compiler.GetNamespaceSupporter().GetImportedNamespaces().clear();
584 continue;
585 }
586
587
588
589 if(basbuf[i]==1&&basbuf[i+1]==ESC_INTERFACE){
590 //////////////////////////
591 // インターフェイス
592 //////////////////////////
593
594 top_pos=i;
595
596 i+=2;
597
598 //インターフェイス名を取得
599 GetCommandToken( temporary, basbuf, i );
600
601 char className[VN_SIZE];
602 Jenga::Common::Strings typeParameters;
603 Jenga::Common::Strings typeParameterBaseClassNames;
604 SplitGenericClassInstance( temporary, className, typeParameters, true, &typeParameterBaseClassNames );
605
606 CClass *pobj_c = const_cast<CClass *>( classes.Find(namespaceScopes, className) );
607 if(!pobj_c) continue;
608
609 compiler.SetCompilingClass( pobj_c );
610
611 if(lpszInheritsClass){
612 if(lstrcmp(lpszInheritsClass,pobj_c->GetName().c_str())!=0){
613 //継承先先読み用
614 continue;
615 }
616 }
617
618 if(pobj_c->IsReady()){
619 //既に先読みされているとき
620 continue;
621 }
622
623 /////////////////////////////////////////////////////////
624 // ☆★☆ ジェネリクスサポート ☆★☆
625 for( i2=0; i2<static_cast<int>(typeParameters.size()); i2++ )
626 {
627 Type baseType( DEF_OBJECT, *classes.GetObjectClassPtr() );
628 if( typeParameterBaseClassNames[i2].size() )
629 {
630 if( !compiler.StringToType( typeParameterBaseClassNames[i2], baseType ) )
631 {
632 compiler.errorMessenger.Output(106,typeParameterBaseClassNames[i2],i);
633 }
634 else if( !baseType.IsObject() )
635 {
636 compiler.errorMessenger.Output(106,typeParameterBaseClassNames[i2],i);
637 }
638 }
639
640 pobj_c->AddFormalGenericType( GenericType( typeParameters[i2], baseType ) );
641 }
642 /////////////////////////////////////////////////////////
643
644 pobj_c->Readed();
645
646 pobj_c->SetConstructorMemberSubIndex( -1 );
647 pobj_c->SetDestructorMemberSubIndex( -1 );
648
649 if( memcmp( basbuf+i+1, "__COM", 5 ) == 0 && IsCommandDelimitation( basbuf[i+1+5] ) )
650 {
651 // COMインターフェイス
652 pobj_c->SetClassType( CClass::ComInterface );
653
654 i += 6;
655 }
656
657 if(basbuf[i+1]==1&&basbuf[i+2]==ESC_INHERITS){
658 //継承を行う場合
659 for(i+=3,i2=0;;i++,i2++){
660 if(IsCommandDelimitation(basbuf[i])){
661 temporary[i2]=0;
662 break;
663 }
664 temporary[i2]=basbuf[i];
665 }
666
667 if(lstrcmpi(temporary,pobj_c->GetName().c_str())==0){
668 compiler.errorMessenger.Output(105,temporary,i);
669 goto Interface_InheritsError;
670 }
671
672 //継承元クラスを取得
673 const CClass *pInheritsClass = classes.Find(temporary);
674 if( !pInheritsClass ){
675 compiler.errorMessenger.Output(106,temporary,i);
676 goto Interface_InheritsError;
677 }
678
679 //ループ継承でないかをチェック
680 if( !LexicalAnalyzer::LoopRefCheck( *pInheritsClass ) )
681 {
682 compiler.errorMessenger.Output(123,pInheritsClass->GetName(),i);
683 goto Interface_InheritsError;
684 }
685
686 //継承させる
687 if( !pobj_c->InheritsClass( *pInheritsClass, Types(), i ) ){
688 goto Interface_InheritsError;
689 }
690 }
691 else{
692 //継承無し
693 if( &pobj_c->GetSuperClass() || pobj_c->GetVtblNum() )
694 {
695 // TODO: ここに来ないことが実証できたらこの分岐は消す
696 Jenga::Throw( "GetClass_recur内の例外" );
697 }
698 }
699Interface_InheritsError:
700
701 //メンバ変数、関数を取得
702 while(1){
703 i++;
704
705 //エラー
706 if(basbuf[i]==1&&(basbuf[i+1]==ESC_CLASS||basbuf[i+1]==ESC_TYPE||basbuf[i+1]==ESC_INTERFACE)){
707 compiler.errorMessenger.Output(22,"Interface",i);
708 i--;
709 break;
710 }
711
712 if(basbuf[i]==1&&basbuf[i+1]==ESC_INHERITS){
713 compiler.errorMessenger.Output(111,NULL,i);
714 break;
715 }
716 else if( basbuf[i] == 1 && basbuf[i+1] == ESC_IMPLEMENTS )
717 {
718 compiler.errorMessenger.Output(137, NULL, i );
719 break;
720 }
721
722 sub_address=i;
723
724 for(i2=0;;i++,i2++){
725 if(IsCommandDelimitation(basbuf[i])){
726 temporary[i2]=0;
727 break;
728 }
729 temporary[i2]=basbuf[i];
730 }
731 if(temporary[0]=='\0'){
732 if(basbuf[i]=='\0'){
733 i--;
734 compiler.errorMessenger.Output(22,"Interface",top_pos);
735 break;
736 }
737 continue;
738 }
739
740 //End Interface記述の場合
741 if(temporary[0]==1&&temporary[1]==ESC_ENDINTERFACE) break;
742
743 if(!(temporary[0]==1&&(
744 temporary[1]==ESC_SUB||temporary[1]==ESC_FUNCTION
745 ))){
746 compiler.errorMessenger.Output(1,NULL,i);
747 break;
748 }
749
750 //関数ハッシュへ登録
751 char interfaceName[VN_SIZE] = "";
752 UserProc *pUserProc = LexicalAnalyzer::ParseUserProc( NamespaceScopes(), NamespaceScopesCollection(), temporary,sub_address,true,pobj_c, false, interfaceName );
753 if( pUserProc )
754 {
755 compiler.GetObjectModule().meta.GetUserProcs().Insert( pUserProc, i );
756
757 //メンバ関数を追加
758 LexicalAnalyzer::AddMethod(pobj_c,
759 pUserProc,
760 Prototype::Public, //Publicアクセス権
761 0, // bStatic
762 false, // isConst
763 true, // isAbstract
764 true, // isVirtual
765 false, // isOverride
766 interfaceName,
767 false, // isAutoGeneration
768 sub_address
769 );
770 }
771 }
772 }
773
774 if(basbuf[i]==1&&(basbuf[i+1]==ESC_CLASS||basbuf[i+1]==ESC_TYPE)){
775 //////////////////////////
776 // クラス
777 //////////////////////////
778
779 top_pos=i;
780
781 const DWORD dwClassType=basbuf[i+1];
782
783 i+=2;
784
785 int iAlign=0;
786 if(memicmp(basbuf+i,"Align(",6)==0){
787 //アラインメント修飾子
788 i+=6;
789 i+=GetStringInPare_RemovePare(temporary,basbuf+i)+1;
790 iAlign=atoi(temporary);
791
792 if( dwClassType != ESC_TYPE )
793 {
794 compiler.errorMessenger.Output(140,NULL,i);
795 }
796
797 if(!(iAlign==1||iAlign==2||iAlign==4||iAlign==8||iAlign==16))
798 compiler.errorMessenger.Output(51,NULL,i);
799 }
800 else if( memicmp( basbuf + i, "Blittable(", 10 ) == 0 ){
801 // Blittable修飾子
802 i+=10;
803 i=JumpStringInPare(basbuf,i)+1;
804
805 if( dwClassType != ESC_CLASS )
806 {
807 compiler.errorMessenger.Output(141,NULL,i);
808 }
809 }
810
811 if( basbuf[i] == 1 && basbuf[i+1] == ESC_ENUM )
812 {
813 // 列挙型の場合
814 i += 2;
815 }
816 else if( basbuf[i] == 1 && basbuf[i+1] == ESC_DELEGATE )
817 {
818 // デリゲートの場合
819 i += 2;
820 }
821
822 //クラス名を取得
823 GetCommandToken( temporary, basbuf, i );
824
825 char className[VN_SIZE];
826 Jenga::Common::Strings typeParameters;
827 Jenga::Common::Strings typeParameterBaseClassNames;
828 SplitGenericClassInstance( temporary, className, typeParameters, true, &typeParameterBaseClassNames );
829
830 CClass *pobj_c = const_cast<CClass *>( classes.Find(namespaceScopes, className) );
831 if(!pobj_c) continue;
832
833 compiler.SetCompilingClass( pobj_c );
834
835 if(lpszInheritsClass){
836 if( pobj_c->GetName() != lpszInheritsClass ){
837 //継承先先読み用
838 continue;
839 }
840 }
841
842 if( lstrcmp(className,"Control")==0)
843 {
844 int test=0;
845 }
846
847 if(pobj_c->IsReady()){
848 //既に先読みされているとき
849 continue;
850 }
851
852
853 /////////////////////////////////////////////////////////
854 // ☆★☆ ジェネリクスサポート ☆★☆
855 for( i2=0; i2<static_cast<int>(typeParameters.size()); i2++ )
856 {
857 Type baseType( DEF_OBJECT, *classes.GetObjectClassPtr() );
858 if( typeParameterBaseClassNames[i2].size() )
859 {
860 if( !compiler.StringToType( typeParameterBaseClassNames[i2], baseType ) )
861 {
862 compiler.errorMessenger.Output(106,typeParameterBaseClassNames[i2],i);
863 }
864 else if( !baseType.IsObject() )
865 {
866 compiler.errorMessenger.Output(106,typeParameterBaseClassNames[i2],i);
867 }
868 }
869
870 pobj_c->AddFormalGenericType( GenericType( typeParameters[i2], baseType ) );
871 }
872 /////////////////////////////////////////////////////////
873
874
875 pobj_c->SetFixedAlignment( iAlign );
876
877 pobj_c->Readed();
878
879 pobj_c->SetConstructorMemberSubIndex( -1 );
880 pobj_c->SetDestructorMemberSubIndex( -1 );
881
882 //アクセス制限の初期値をセット
883 Prototype::Accessibility accessibility;
884 if(dwClassType==ESC_CLASS){
885 accessibility = Prototype::Private;
886 }
887 else{
888 accessibility = Prototype::Public;
889 }
890
891 if( pobj_c->GetName() == "Object"
892 || dwClassType == ESC_TYPE )
893 {
894 // 何も継承しない
895
896 if( &pobj_c->GetSuperClass() || pobj_c->GetVtblNum() )
897 {
898 // TODO: ここに来ないことが実証できたらこの分岐は消す
899 Jenga::Throw( "GetClass_recur内の例外" );
900 }
901 }
902 else{
903 if(basbuf[i+1]==1&&basbuf[i+2]==ESC_INHERITS)
904 {
905 // クラス継承先が指定されているとき
906 i += 3;
907 GetCommandToken( temporary, basbuf, i );
908
909 if(lstrcmpi(temporary,pobj_c->GetName().c_str())==0){
910 compiler.errorMessenger.Output(105,temporary,i);
911 goto InheritsError;
912 }
913 }
914 else
915 {
916 // 何の指定もないときはObjectクラスを継承する
917 lstrcpy( temporary, "Object" );
918 }
919 LexicalAnalyzer::Inherits( *pobj_c, temporary, i );
920
921 if( basbuf[i+1] == 1 && basbuf[i+2] == ESC_IMPLEMENTS )
922 {
923 // インターフェイス実装を行う場合
924 i += 3;
925 GetCommandToken( temporary, basbuf, i );
926
927 LexicalAnalyzer::Implements( *pobj_c, temporary, i );
928 }
929 }
930InheritsError:
931
932 //メンバとメソッドを取得
933 while(1){
934 i++;
935
936 //エラー
937 if(basbuf[i]==1&&(basbuf[i+1]==ESC_CLASS||basbuf[i+1]==ESC_TYPE)){
938 compiler.errorMessenger.Output(22,"Class",i);
939 i--;
940 break;
941 }
942
943 if(basbuf[i]==1&&basbuf[i+1]==ESC_INHERITS){
944 compiler.errorMessenger.Output(111,NULL,i);
945 break;
946 }
947 else if( basbuf[i] == 1 && basbuf[i+1] == ESC_IMPLEMENTS )
948 {
949 compiler.errorMessenger.Output(137, NULL, i );
950 break;
951 }
952
953 //Static修飾子
954 BOOL bStatic;
955 if(basbuf[i]==1&&basbuf[i+1]==ESC_STATIC){
956 bStatic=1;
957 i+=2;
958 }
959 else bStatic=0;
960
961 //Const修飾子
962 bool isConst = false;
963 if( basbuf[i] == 1 && basbuf[i + 1] == ESC_CONST ){
964 isConst = true;
965 i += 2;
966 }
967
968 if(basbuf[i]==1&&(
969 basbuf[i+1]==ESC_ABSTRACT||basbuf[i+1]==ESC_VIRTUAL||basbuf[i+1]==ESC_OVERRIDE||
970 basbuf[i+1]==ESC_SUB||basbuf[i+1]==ESC_FUNCTION
971 )){
972 i3=basbuf[i+1];
973 sub_address=i;
974 }
975 else i3=0;
976
977 bool isVirtual = false, isAbstract = false, isOverride = false;
978 if(i3==ESC_ABSTRACT){
979 isAbstract=1;
980 isVirtual=1;
981 i+=2;
982
983 i3=basbuf[i+1];
984 }
985 else if(i3==ESC_VIRTUAL){
986 isAbstract=0;
987 isVirtual=1;
988 i+=2;
989
990 i3=basbuf[i+1];
991 }
992 else if(i3==ESC_OVERRIDE){
993 isOverride=1;
994 isVirtual=1;
995
996 i+=2;
997
998 i3=basbuf[i+1];
999 }
1000
1001 for(i2=0;;i++,i2++){
1002 if(IsCommandDelimitation(basbuf[i])){
1003 temporary[i2]=0;
1004 break;
1005 }
1006 temporary[i2]=basbuf[i];
1007 }
1008 if(temporary[0]=='\0'){
1009 if(basbuf[i]=='\0'){
1010
1011 if(dwClassType==ESC_CLASS)
1012 compiler.errorMessenger.Output(22,"Class",top_pos);
1013 else
1014 compiler.errorMessenger.Output(22,"Type",top_pos);
1015
1016 i--;
1017 break;
1018 }
1019 continue;
1020 }
1021
1022 //End Class記述の場合
1023 if(temporary[0]==1&&temporary[1]==ESC_ENDCLASS&&dwClassType==ESC_CLASS) break;
1024 if(temporary[0]==1&&temporary[1]==ESC_ENDTYPE&&dwClassType==ESC_TYPE) break;
1025
1026 //アクセスを変更
1027 if(lstrcmpi(temporary,"Private")==0){
1028 accessibility = Prototype::Private;
1029 continue;
1030 }
1031 if(lstrcmpi(temporary,"Public")==0){
1032 accessibility = Prototype::Public;
1033 continue;
1034 }
1035 if(lstrcmpi(temporary,"Protected")==0){
1036 accessibility = Prototype::Protected;
1037 continue;
1038 }
1039
1040 extern int cp;
1041 if(i3==0){
1042 if(bStatic){
1043 //静的メンバを追加
1044 cp=i; //エラー用
1045 pobj_c->AddStaticMember( accessibility, isConst, false, temporary, i);
1046 }
1047 else{
1048 //メンバを追加
1049 cp=i; //エラー用
1050 pobj_c->AddMember( accessibility, isConst, false, temporary, i );
1051
1052
1053 if(pobj_c->GetDynamicMembers().back()->GetType().IsStruct()){
1054 if( !pobj_c->GetDynamicMembers().back()->GetType().GetClass().IsReady() ){
1055 //参照先が読み取られていないとき
1056 GetClass_recur( pobj_c->GetDynamicMembers().back()->GetType().GetClass().GetName().c_str(), classes );
1057 }
1058 }
1059
1060
1061 if(pobj_c->GetDynamicMembers().back()->GetType().IsStruct()){
1062 //循環参照のチェック
1063 pobj_LoopRefCheck->add(pobj_c->GetName().c_str());
1064 if(!MemberVar_LoopRefCheck(pobj_c->GetDynamicMembers().back()->GetType().GetClass())){
1065 //エラー回避
1066 Type &type = const_cast<Type &>(pobj_c->GetDynamicMembers().back()->GetType());
1067 type.SetBasicType( DEF_PTR_VOID );
1068 }
1069 pobj_LoopRefCheck->del(pobj_c->GetName().c_str());
1070 }
1071 }
1072 }
1073 else{
1074 //関数ハッシュへ登録
1075 char interfaceName[VN_SIZE] = "";
1076 UserProc *pUserProc = LexicalAnalyzer::ParseUserProc( NamespaceScopes(), NamespaceScopesCollection(), temporary,sub_address,isVirtual,pobj_c, (bStatic!=0), interfaceName );
1077 if( pUserProc )
1078 {
1079 compiler.GetObjectModule().meta.GetUserProcs().Insert( pUserProc, i );
1080
1081 //メソッドを追加
1082 cp=i; //エラー用
1083 LexicalAnalyzer::AddMethod(pobj_c,
1084 pUserProc,
1085 accessibility,
1086 bStatic,
1087 isConst,
1088 isAbstract,
1089 isVirtual,
1090 isOverride,
1091 interfaceName,
1092 false,
1093 sub_address);
1094 }
1095
1096 if( isAbstract ) continue;
1097
1098 for(;;i++){
1099 if(basbuf[i]=='\0'){
1100 i--;
1101 break;
1102 }
1103 if(basbuf[i-1]!='*'&&
1104 basbuf[i]==1&&(
1105 basbuf[i+1]==ESC_SUB||
1106 basbuf[i+1]==ESC_FUNCTION||
1107 basbuf[i+1]==ESC_MACRO||
1108 basbuf[i+1]==ESC_TYPE||
1109 basbuf[i+1]==ESC_CLASS||
1110 basbuf[i+1]==ESC_INTERFACE||
1111 basbuf[i+1]==ESC_ENUM)){
1112 GetDefaultNameFromES(i3,temporary);
1113 compiler.errorMessenger.Output(22,temporary,i);
1114 }
1115 if(basbuf[i]==1&&basbuf[i+1]==GetEndXXXCommand((char)i3)){
1116 i+=2;
1117 break;
1118 }
1119 }
1120 }
1121 }
1122 }
1123 }
1124
1125 // 呼び出し元でコンパイル中のクラスポインタを元に戻す
1126 compiler.SetCompilingClass( pBackCompilingClass );
1127
1128 // 名前空間を元に戻す
1129 compiler.GetNamespaceSupporter().GetLivingNamespaceScopes() = backupNamespaceScopes;
1130
1131 // インポートされた名前空間を元に戻す
1132 compiler.GetNamespaceSupporter().GetImportedNamespaces() = backupImportedNamespaces;
1133}
1134
1135void LexicalAnalyzer::LookaheadClass( const char *className, Classes &classes )
1136{
1137 pobj_LoopRefCheck->add( className );
1138 GetClass_recur( className, classes );
1139 pobj_LoopRefCheck->del( className );
1140}
1141
1142bool LexicalAnalyzer::LoopRefCheck( const CClass &objClass )
1143{
1144 if( pobj_LoopRefCheck->check( objClass ) )
1145 {
1146 return false;
1147 }
1148
1149 return true;
1150}
1151
1152void LexicalAnalyzer::CollectClasses( const char *source, Classes &classes ){
1153 //ループ継承チェック用のクラス
1154 pobj_LoopRefCheck=new CLoopRefCheck();
1155
1156 //クラスを取得
1157 GetClass_recur( 0, classes );
1158
1159 delete pobj_LoopRefCheck;
1160 pobj_LoopRefCheck=0;
1161
1162 // イテレータの準備
1163 classes.Iterator_Init();
1164}
Note: See TracBrowser for help on using the repository browser.