source: dev/trunk/abdev/BasicCompiler32/NumOpe.cpp@ 302

Last change on this file since 302 was 301, checked in by dai_9181, 17 years ago
File size: 27.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
8#include "../BasicCompiler_Common/common.h"
9#include "Opcode.h"
10
11void PushReturnValue(int type){
12 //関数の戻り値をスタックへプッシュする
13 //※この処理内では、esi、ediは使用不可
14
15 if(type==DEF_OBJECT || type==DEF_STRUCT){
16 //push eax
17 compiler.codeGenerator.op_push(REG_EAX);
18 }
19 else if(type==DEF_DOUBLE){
20 //sub esp,8
21 compiler.codeGenerator.op_sub_esp(8);
22
23 //fstp qword ptr[esp]
24 compiler.codeGenerator.op_fstp_basereg( DEF_DOUBLE, REG_ESP );
25 }
26 else if(type==DEF_SINGLE){
27 //sub esp,4
28 compiler.codeGenerator.op_sub_esp(4);
29
30 //fstp dword ptr[esp]
31 compiler.codeGenerator.op_fstp_basereg( DEF_SINGLE, REG_ESP );
32 }
33 else if(type==DEF_INT64||type==DEF_QWORD){
34 //push edx
35 compiler.codeGenerator.op_push(REG_EDX);
36
37 //push eax
38 compiler.codeGenerator.op_push(REG_EAX);
39 }
40 else if(type==DEF_LONG){
41 //push eax
42 compiler.codeGenerator.op_push(REG_EAX);
43 }
44 else if(type==DEF_INTEGER || (Smoothie::IsUnicode()&&type==DEF_CHAR)){
45 //movsx ebx,ax
46 compiler.codeGenerator.op_movsx_R32R16( REG_EBX, REG_EAX );
47
48 //push ebx
49 compiler.codeGenerator.op_push(REG_EBX);
50 }
51 else if(type==DEF_SBYTE || (Smoothie::IsUnicode()==false&&type==DEF_CHAR)){
52 //movsx ebx,al
53 compiler.codeGenerator.op_movsx_R32R8( REG_EBX, REG_EAX );
54
55 //push ebx
56 compiler.codeGenerator.op_push(REG_EBX);
57 }
58 else if(type==DEF_DWORD||type==DEF_WORD||type==DEF_BYTE||type==DEF_BOOLEAN||
59 IsPtrType(type)){
60 //push eax
61 compiler.codeGenerator.op_push(REG_EAX);
62 }
63 else{
64 SetError();
65 }
66}
67
68void NewStringObject( const char *str ){
69 ///////////////////////////////////////////////////////
70 // lpszTextを元にStringオブジェクトを生成し、
71 // オブジェクトポインタをregに格納する
72 ///////////////////////////////////////////////////////
73
74 char *parameter = (char *)malloc( lstrlen( str ) + 32 );
75 sprintf( parameter, "\"%s\"%c%c*Char", str, 1, ESC_AS );
76 SetStringQuotes( parameter );
77
78 Operator_New( *compiler.GetObjectModule().meta.GetClasses().GetStringClassPtr(), "", parameter, Type( DEF_OBJECT, *compiler.GetObjectModule().meta.GetClasses().GetStringClassPtr() ) );
79
80 free( parameter );
81}
82
83void ExtendRegToBigType( int reg, int bigBasicType, int baseBasicType ){
84 if( reg != REG_EAX ){
85 SetError();
86 }
87 switch( Type::GetBasicSize( bigBasicType ) ){
88 case sizeof(_int64):
89 ExtendTypeTo64(baseBasicType);
90 break;
91 case sizeof(long):
92 ExtendTypeTo32(baseBasicType,reg);
93 break;
94 case sizeof(short):
95 ExtendTypeTo16(baseBasicType,reg);
96 break;
97 }
98}
99
100
101
102bool VarToReg( RELATIVE_VAR &relativeVar, const Type &baseType, Type &resultType ){
103 const int useReg = REG_EAX;
104
105 //大きな型への暗黙の変換
106 int bigType = AutoBigCast(baseType.GetBasicType(),resultType.GetBasicType());
107
108 if(resultType.GetBasicType()&FLAG_PTR){
109 //配列ポインタ
110 resultType.SetBasicType( GetPtrType(resultType.GetBasicType()^FLAG_PTR) );
111
112 SetVarPtrToReg(useReg, &relativeVar);
113 }
114 else if( resultType.IsStruct() ){
115 //構造体ポインタをeaxへ格納(構造体は値型)
116 SetVarPtrToReg(useReg, &relativeVar);
117 }
118 else if( resultType.IsReal() ){
119 // 実数
120 SetReg_RealVariable( resultType.GetBasicType(), &relativeVar );
121 }
122 else if( resultType.IsWhole() || resultType.IsObject()){
123 //整数型
124 SetReg_WholeVariable(resultType,&relativeVar,useReg);
125 }
126 else if( resultType.IsStruct() ){
127 //構造体ポインタをUseRegへ格納(構造体は値型)
128 SetVarPtrToReg(useReg,&relativeVar);
129 }
130 else{
131 return false;
132 }
133
134 if( resultType.GetBasicType() != bigType ){
135 // 大きな型へ変換された場合
136 // ※レジスタの値をキャストする
137 ExtendRegToBigType( useReg, bigType, resultType.GetBasicType() );
138
139 resultType.SetBasicType( bigType );
140 }
141
142 return true;
143}
144bool TermMemberOpe( const Type &leftType, const Type &baseType, Type &resultType, const char *termFull, const char *termLeft, const char *member )
145{
146 const CClass &objClass = leftType.GetClass();
147
148 const int useReg = REG_EAX;
149
150 if( GetMemberType( leftType, member, resultType, 0, false ) ){
151 // メンバが見つかったとき
152
153 //オブジェクトポインタをecxにコピー
154 compiler.codeGenerator.op_mov_RR( REG_ECX, useReg );
155
156 RELATIVE_VAR relativeVar;
157 relativeVar.dwKind=VAR_DIRECTMEM;
158
159 if( !_member_offset(
160 true, //エラー表示あり
161 false, //読み込み専用
162 leftType,
163 member,&relativeVar,resultType,0)){
164 return false;
165 }
166
167 if( !VarToReg( relativeVar, baseType, resultType ) ){
168 SetError(11,termFull,cp);
169 }
170
171 return true;
172 }
173
174
175 ///////////////////////////////////////////////////////////////////
176 // 動的メソッドを検索
177 ///////////////////////////////////////////////////////////////////
178 vector<const UserProc *> userProcs;
179
180 char methodName[VN_SIZE], lpPtrOffset[VN_SIZE], parameter[VN_SIZE], dummy[1];
181 ReferenceKind refType;
182 lstrcpy( methodName, member );
183 GetVarFormatString(methodName,parameter,lpPtrOffset,dummy,refType);
184
185 objClass.GetMethods().Enum( methodName, userProcs );
186 if(userProcs.size()){
187 //オーバーロードを解決
188 const UserProc *pUserProc = OverloadSolutionWithStrParam(termFull,userProcs,parameter,termLeft);
189
190 if( pUserProc ){
191
192 resultType = pUserProc->ReturnType();
193
194 {
195 //オブジェクトポインタをスタックに入れておく
196 //push reg
197 compiler.codeGenerator.op_push( useReg );
198
199 if( !Opcode_CallProc(parameter,pUserProc,PROCFLAG_NEW,termLeft) ){
200
201 return false;
202 }
203
204 compiler.codeGenerator.op_pop();
205
206 /////////////////////
207 // 戻り値の処理
208 /////////////////////
209
210 //大きな型への暗黙の変換
211 int bigType = AutoBigCast(baseType.GetBasicType(), resultType.GetBasicType() );
212
213 if( resultType.GetBasicType() != bigType ){
214 // 大きな型へ変換された場合
215 // ※レジスタの値をキャストする
216 ExtendRegToBigType( REG_EAX, bigType, resultType.GetBasicType() );
217
218 resultType.SetBasicType( bigType );
219 }
220
221 //SetUseRegFromRax(resultType.GetBasicType(),UseReg,XmmReg);
222
223 // 型パラメータを解決
224 ResolveFormalGenericTypeParameter( resultType, leftType, pUserProc );
225 }
226
227 return true;
228 }
229 }
230
231 return false;
232}
233bool TermOpe( const char *term, const Type &baseType, Type &resultType, bool &isLiteral, BOOL *pbUseHeap, bool isWantObject, bool *pIsClassName, bool isProcedureCallOnly ){
234 char parameter[VN_SIZE];
235
236 // Withを解決
237 char termFull[VN_SIZE];
238 if(term[0]=='.'){
239 GetWithName(termFull);
240 lstrcat(termFull,term);
241 }
242 else lstrcpy(termFull,term);
243
244 char termLeft[VN_SIZE];
245 lstrcpy(termLeft,termFull);
246
247 // パース
248 char member[VN_SIZE];
249 ReferenceKind refType;
250 if( SplitMemberName( termFull, termLeft, member, refType ) ){
251 ///////////////////////////////////////////////////////////////////
252 // オブジェクトとメンバに分解できるとき
253 // termLeft.member
254 ///////////////////////////////////////////////////////////////////
255
256 isLiteral = false;
257
258 // オブジェクト側の型を取得
259 bool isClassName = false;
260 Type leftType;
261 if( GetTermType( termLeft, leftType, isLiteral, &isClassName ) ){
262 if( isClassName == false && compiler.GetObjectModule().meta.GetBlittableTypes().IsExist( leftType ) ){
263 // 左側のオブジェクト部分がBlittable型のとき
264
265 char temporary[VN_SIZE];
266 lstrcpy( temporary, termLeft );
267 sprintf( termLeft, "%s(%s)",
268 compiler.GetObjectModule().meta.GetBlittableTypes().Find( leftType ).GetCreateStaticMethodFullName().c_str(),
269 temporary );
270 }
271 }
272
273 if( !TermOpe( termLeft, baseType, leftType, isLiteral, pbUseHeap, true, &isClassName ) ){
274 goto globalArea;
275 }
276
277 if( isClassName ){
278 // 静的メンバ/メソッドの場合
279 goto globalArea;
280 }
281
282 if( !leftType.HasMember() ){
283 // メンバを持たない型の場合
284 return false;
285 }
286
287 return TermMemberOpe( leftType, baseType, resultType, termFull, termLeft, member );
288 }
289globalArea:
290
291
292 //////////////////////////////////////////////
293 // クラス名かどうかをチェック(静的メンバ用)
294 //////////////////////////////////////////////
295
296 if( pIsClassName ){
297 if( compiler.GetObjectModule().meta.GetClasses().Find( termFull ) ){
298 *pIsClassName = true;
299 return true;
300 }
301 }
302
303
304 /////////////////////////////////////////////////////////////////
305 // グローバル属性エリア
306 /////////////////////////////////////////////////////////////////
307
308 const int useReg = REG_EAX;
309
310
311 if(lstrcmpi(termFull,"This")==0 && isProcedureCallOnly == false ){
312 //Thisオブジェクト
313 resultType.SetType( DEF_OBJECT, compiler.pCompilingClass );
314
315 SetThisPtrToReg( useReg );
316
317 isLiteral = false;
318
319 return true;
320 }
321
322
323 //////////////////////////////////////
324 // 関数(DLL、ユーザー定義、組み込み)
325 //////////////////////////////////////
326 char procName[VN_SIZE];
327 char temporary[8192];
328
329 int i2=GetCallProcName(termFull,procName);
330 if(termFull[i2]=='('){
331 int i4=GetStringInPare_RemovePare(parameter,termFull+i2+1);
332
333 void *pInfo;
334 int idProc=GetProc(procName,(void **)&pInfo);
335
336 if(idProc){
337 //閉じカッコ")"に続く文字がNULLでないとき
338 if(termFull[i2+1+i4+1]!='\0'){
339 SetError(42,NULL,cp);
340 }
341
342
343 {
344 ////////////////
345 // 呼び出し
346 ////////////////
347
348 CallProc(idProc,pInfo,procName,parameter,resultType);
349
350
351 /////////////////////
352 // 戻り値の処理
353 /////////////////////
354
355 //大きな型への暗黙の変換
356 int bigType = AutoBigCast(baseType.GetBasicType(), resultType.GetBasicType() );
357
358 /*
359 ※後でNumOpe内でプッシュする
360 //スタックへプッシュ
361 PushReturnValue( resultType.GetBasicType() );
362 */
363
364 if( resultType.GetBasicType() != bigType ){
365 // 大きな型へ変換された場合
366 // ※レジスタの値をキャストする
367 ExtendRegToBigType( useReg, bigType, resultType.GetBasicType() );
368
369 resultType.SetBasicType( bigType );
370 }
371
372 //SetUseRegFromRax(resultType.GetBasicType(),UseReg,XmmReg);
373 }
374
375
376 if(resultType.IsStruct()){
377 //構造体が戻ったときはヒープ領域にインスタンスが格納されている
378 //※後にfreeする必要あり
379 // TODO: 解放はGCに任せる
380 *pbUseHeap = 1;
381 }
382
383 isLiteral = false;
384
385 return true;
386 }
387
388 ConstMacro *pConstMacro = compiler.GetObjectModule().meta.GetGlobalConstMacros().Find( procName );
389 if( pConstMacro )
390 {
391 if( pConstMacro->GetCalcBuffer( parameter, temporary ) )
392 {
393 /////////////////////////
394 // マクロ関数
395 /////////////////////////
396
397 //閉じカッコ")"に続く文字がNULLでないときはエラーにする
398 if(termFull[i2+1+i4+1]!='\0') SetError(42,NULL,cp);
399
400 //マクロ関数の場合
401 NumOpe(useReg, temporary,Type(),resultType);
402
403 if(!IS_LITERAL(resultType.GetIndex())){
404 //リテラル値ではなかったとき
405 isLiteral = false;
406 }
407
408 return true;
409 }
410 }
411 }
412 else if( isProcedureCallOnly ){
413 // 関数呼び出し以外は受け付けない
414 return false;
415 }
416
417
418 ////////////////////////////////
419 // インデクサ(getアクセサ)
420 ////////////////////////////////
421
422 char VarName[VN_SIZE],ArrayElements[VN_SIZE];
423 GetArrayElement(termFull,VarName,ArrayElements);
424 if(ArrayElements[0]){
425 Type classType;
426 GetVarType(VarName,classType,false);
427 if( classType.IsObject() )
428 {
429 CallIndexerGetterProc(/*UseReg,*/classType,VarName, ArrayElements,resultType);
430
431 isLiteral = false;
432
433 return true;
434 }
435 }
436
437
438 ////////////////////////////////
439 // 変数
440 ////////////////////////////////
441
442 RELATIVE_VAR relativeVar;
443 if(GetVarOffset(
444 false, //エラー表示なし
445 false, //読み込み専用
446 termFull,
447 &relativeVar,resultType)){
448 //////////
449 // 変数
450 //////////
451
452 if( !VarToReg( relativeVar, baseType, resultType ) ){
453 SetError(11,termFull,cp);
454 }
455
456 isLiteral = false;
457
458 return true;
459 }
460
461
462 /////////////////////////////////
463 // プロパティ用のメソッド
464 /////////////////////////////////
465
466 //配列要素を排除
467 GetArrayElement(termFull,VarName,ArrayElements);
468
469 if(GetSubHash(VarName,0)){
470
471 {
472 CallPropertyMethod(termFull,NULL,resultType);
473
474 //大きな型への暗黙の変換
475 int bigType = AutoBigCast(baseType.GetBasicType(), resultType.GetBasicType() );
476
477 if( resultType.GetBasicType() != bigType ){
478 // 大きな型へ変換された場合
479 // ※レジスタの値をキャストする
480 ExtendRegToBigType( REG_EAX, bigType, resultType.GetBasicType() );
481
482 resultType.SetBasicType( bigType );
483 }
484
485 //SetUseRegFromRax(resultType.GetBasicType(),UseReg,XmmReg);
486 }
487
488
489 if(resultType.IsStruct()){
490 //構造体が戻ったときはヒープ領域にインスタンスが格納されている
491 //※後にfreeする必要あり
492 // TODO: 解放はGCに任せる
493 *pbUseHeap = 1;
494 }
495
496 isLiteral = false;
497
498 return true;
499 }
500
501
502 return false;
503}
504
505
506bool NumOpe( int reg,
507 const char *expression,
508 const Type &baseType,
509 Type &resultType,
510 BOOL *pbUseHeap ){
511
512 if( !NumOpe( expression, baseType, resultType, pbUseHeap ) ){
513 return false;
514 }
515
516 if( reg != REG_EAX ){
517 // TODO: 未実装
518 SetError();
519 }
520
521 if( resultType.IsReal() ){
522 //fld ptr[esp]
523 compiler.codeGenerator.op_fld_ptr_esp( resultType.GetBasicType() );
524
525 //add esp,size
526 compiler.codeGenerator.op_add_esp( resultType.GetBasicSize() );
527 }
528 else{
529 //pop eax
530 compiler.codeGenerator.op_pop(REG_EAX);
531
532 if( resultType.Is64() ){
533 //pop edx
534 compiler.codeGenerator.op_pop(REG_EDX);
535 }
536 }
537 return true;
538}
539bool NumOpe( const char *expression,
540 const Type &baseType,
541 Type &resultType,
542 BOOL *pbUseHeap )
543{
544 int i,i2,i3;
545 char temporary[1024],temp2[1024];
546
547 if(expression[0]=='\0'){
548 SetError(1,NULL,cp);
549 return false;
550 }
551
552 if( !baseType.IsNull() && expression[0] == '[' ){
553 // リテラル配列の場合
554
555 if( !baseType.IsPointer() ){
556 SetError(1,NULL,cp);
557 return false;
558 }
559 Type tempBaseType( baseType );
560 tempBaseType.PtrLevelDown();
561
562 char *buffer = (char *)malloc( lstrlen( expression ) + 1 );
563 lstrcpy( buffer, expression );
564 RemoveStringBracket( buffer );
565
566 void *binary = malloc( 1 );
567 int num = 0;
568
569 i = 0;
570 while( buffer[i] ){
571 i = GetOneParameter( buffer, i, temporary );
572 if( buffer[i] == ',' ){
573 i++;
574 }
575
576 Type resultType;
577 _int64 i64data;
578 if( !StaticCalculation( true, temporary, tempBaseType.GetBasicType(), &i64data, resultType ) ){
579 return false;
580 }
581 if( !resultType.IsWhole() ){
582 // TODO: 実数に未対応
583 SetError();
584 return false;
585 }
586
587 binary = realloc( binary, ( num + 1 ) * tempBaseType.GetSize() );
588 memcpy( (char *)binary + (num * tempBaseType.GetSize()), &i64data, tempBaseType.GetSize() );
589 num++;
590 }
591
592 i2 = compiler.GetObjectModule().dataTable.AddBinary( binary, num * tempBaseType.GetSize() );
593
594 //mov eax,i2
595 compiler.codeGenerator.op_mov_RV(REG_EAX,i2, Schedule::DataTable );
596
597 free( buffer );
598
599 resultType = baseType;
600
601 //push eax
602 compiler.codeGenerator.op_push( REG_EAX );
603
604 return true;
605 }
606
607 bool isLiteralCalculation;
608 if( !NumOpe_GetType( expression, baseType, resultType, &isLiteralCalculation ) )
609 {
610 return false;
611 }
612 if( isLiteralCalculation )
613 {
614 //右辺値が数値の定数式の場合
615 _int64 i64data;
616 StaticCalculation(true, expression,baseType.GetBasicType(),&i64data,resultType);
617
618 if( resultType.GetBasicSize() == sizeof(_int64) ){
619 //64ビット(符号有り整数/実数)
620
621 //push HILONG(i64data)
622 compiler.codeGenerator.op_push_V((long)*(long *)(((char *)(&i64data))+4));
623
624 //push LOLONG(i64data)
625 compiler.codeGenerator.op_push_V(*(long *)(&i64data));
626 }
627 else if( resultType.IsSingle() ){
628 //single実数
629
630 double dbl;
631 memcpy(&dbl,&i64data,sizeof(_int64));
632
633 float flt;
634 flt=(float)dbl;
635 long l;
636 memcpy(&l,&flt,sizeof(long));
637
638 //push flt
639 compiler.codeGenerator.op_push_V(l);
640 }
641 else{
642 //整数(符号有り/無し)
643
644 long l = (long)i64data;
645
646 if(resultType.GetBasicSize()==sizeof(char)) l = l & 0x000000FF;
647 if(resultType.GetBasicSize()==sizeof(short)) l = l & 0x0000FFFF;
648
649 //push term
650 compiler.codeGenerator.op_push_V(l);
651 }
652 return true;
653 }
654
655 if(expression[0]==1&& expression[1]==ESC_NEW ){
656 //New演算子(オブジェクト生成)
657
658 if( !Operator_New( expression+2, baseType, resultType ) ){
659 return false;
660 }
661
662 return true;
663 }
664
665
666 /////////////////////////////////
667 // 式要素を逆ポーランド式で取得
668 /////////////////////////////////
669
670 char *values[255];
671 long calc[255];
672 long stack[255];
673 int pnum;
674 if(!GetNumOpeElements(expression,&pnum,values,calc,stack)){
675 for(i=0;i<pnum;i++){
676 if(values[i]) HeapDefaultFree(values[i]);
677 }
678 return false;
679 }
680
681
682 BOOL bError;
683 bError=0;
684
685 //リテラル値のみの計算かどうかを判別するためのフラグ
686 BOOL bLiteralCalculation=1;
687
688 //リテラル演算の場合を考慮した演算前の再配置スケジュール
689 CReloc *pobj_BackReloc;
690 pobj_BackReloc=new CReloc();
691 pobj_BackReloc->copy(pobj_Reloc);
692
693 double dbl;
694 int sp;
695 int type_stack[255];
696 bool isNothing_stack[255];
697 LONG_PTR index_stack[255];
698 BOOL bUseHeap[255];
699 _int64 i64data;
700 for(i=0,sp=0;i<pnum;i++){
701 int idCalc;
702 idCalc=calc[i]%100;
703
704 if(idCalc){
705 if(type_stack[sp-2]==DEF_OBJECT){
706 if( idCalc == CALC_AS
707 && type_stack[sp-1] == ( DEF_OBJECT | FLAG_CAST )
708 && index_stack[sp-1] == index_stack[sp-2]
709 || isNothing_stack[sp-2] ){
710 // 同一の型、またはNothingに対するAsはAs演算子を呼び出さない
711 }
712 else if( idCalc == CALC_AS
713 && type_stack[sp-1] == ( DEF_OBJECT | FLAG_CAST )
714 && ( ((CClass *)index_stack[sp-1])->IsEqualsOrSubClass( (CClass *)index_stack[sp-2] ) || ((CClass *)index_stack[sp-2])->IsEqualsOrSubClass( (CClass *)index_stack[sp-1] )
715 )){
716 // ダウンキャストを許可する
717 }
718 else{
719 //オーバーロードされたオペレータを呼び出す
720 i2=CallOperatorProc(idCalc,baseType,type_stack,index_stack,bUseHeap,sp);
721 if(i2==0){
722 if(idCalc==CALC_EQUAL) lstrcpy(temp2,"==");
723 else GetCalcName(idCalc,temp2);
724 sprintf(temporary,"Operator %s",temp2);
725 SetError(27,temporary,cp);
726 goto error;
727 }
728 else if(i2==-1) goto error;
729
730 continue;
731 }
732 }
733
734 if(!CheckCalcType(idCalc,type_stack,sp)) goto error;
735 }
736
737 switch(idCalc){
738 //数値
739 case 0:
740 index_stack[sp]=-1;
741 isNothing_stack[sp] = false;
742 bUseHeap[sp]=0;
743
744 char *term;
745 term=values[i];
746
747 if( calc[i+1]%100 == CALC_AS ){
748 // As演算子の右辺値
749 //型名
750 if( compiler.StringToType( term, resultType ) ){
751 resultType.SetBasicType( resultType.GetBasicType() | FLAG_CAST );
752 }
753 else{
754 SetError(3, term, cp );
755 goto error;
756 }
757
758 type_stack[sp] = resultType.GetBasicType();
759 index_stack[sp] = resultType.GetIndex();
760 sp++;
761
762 break;
763 }
764
765 if(term[0]=='\"'){
766 //リテラル文字列
767 if(!RemoveStringQuotes(term)){
768 SetError(43,NULL,cp);
769 goto error;
770 }
771 i3=lstrlen(term);
772StrLiteral:
773
774 if( baseType.IsObject() || baseType.IsNull() ){
775 //要求タイプがオブジェクト、または未定のとき
776
777 //String型オブジェクトを生成
778 NewStringObject(term);
779
780 type_stack[sp]=DEF_OBJECT;
781 index_stack[sp]=(LONG_PTR)compiler.GetObjectModule().meta.GetClasses().GetStringClassPtr();
782 bLiteralCalculation=0;
783
784 sp++;
785 break;
786 }
787
788
789 type_stack[sp]=typeOfPtrChar;
790 bLiteralCalculation=0;
791
792 i2=compiler.GetObjectModule().dataTable.AddString(term,i3);
793
794 //push DataSize
795 compiler.codeGenerator.op_push_V( i2, Schedule::DataTable );
796 }
797 else if((term[0]=='e'||term[0]=='E')&&
798 (term[1]=='x'||term[1]=='X')&&
799 term[2]=='\"'){
800 //拡張版リテラル文字列(エスケープシーケンス可能)
801 if(!RemoveStringQuotes(term+2)){
802 SetError(43,NULL,cp);
803 goto error;
804 }
805 i3=FormatString_EscapeSequence(term+2);
806 term+=2;
807
808 goto StrLiteral;
809 }
810 else if(IsVariableTopChar(term[0])||
811 term[0]=='*'||
812 (term[0]=='.'&&IsVariableTopChar(term[1]))){
813 //////////////////
814 // 何らかの識別子
815
816 bool isLiteral;
817 if( TermOpe( term, baseType, resultType, isLiteral, &bUseHeap[sp] ) ){
818 if(resultType.IsNull()){
819 //戻り値が存在しないとき
820 for(i2=0;;i2++){
821 if(term[i2]=='('||term[i2]=='\0'){
822 term[i2]=0;
823 break;
824 }
825 }
826 SetError(38,term,cp);
827
828 goto error;
829 }
830
831 type_stack[sp] = resultType.GetBasicType();
832 index_stack[sp] = resultType.GetIndex();
833
834 if( !isLiteral ){
835 bLiteralCalculation=0;
836 }
837
838 if( resultType.GetBasicType() & FLAG_CAST ){
839 // 型名のみ
840 SetError();
841 }
842 else{
843 if( resultType.IsReal() ){
844 //sub esp,size
845 //fstp ptr[esp]
846 compiler.codeGenerator.op_fstp_push( resultType );
847 }
848 else{
849 if( resultType.Is64() ){
850 //push edx
851 compiler.codeGenerator.op_push( REG_EDX );
852 }
853 else{
854 ExtendTypeTo32( resultType.GetBasicType(), REG_EAX );
855 }
856
857 //push eax
858 compiler.codeGenerator.op_push( REG_EAX );
859 }
860 }
861
862 sp++;
863 break;
864 }
865
866
867 // Nothing
868 if( lstrcmp( term, "Nothing" ) == 0 ){
869 isNothing_stack[sp] = true;
870
871 type_stack[sp] = DEF_OBJECT;
872 if( baseType.IsObject() ){
873 index_stack[sp] = baseType.GetIndex();
874 }
875 else{
876 index_stack[sp] = (LONG_PTR)compiler.GetObjectModule().meta.GetClasses().GetObjectClassPtr();
877 }
878
879 bLiteralCalculation = 0;
880
881 //push 0
882 compiler.codeGenerator.op_push_V( 0 );
883
884 sp++;
885 break;
886 }
887
888
889 //////////////
890 // 定数の場合
891 //////////////
892
893 i3 = compiler.GetObjectModule().meta.GetGlobalConsts().GetBasicType(term);
894 if(i3){
895 if( compiler.GetObjectModule().meta.GetGlobalConsts().IsStringPtr( term ) ){
896 //リテラル文字列
897
898 double dbl = compiler.GetObjectModule().meta.GetGlobalConsts().GetDoubleData(term);
899 memcpy(&i64data,&dbl,sizeof(double));
900
901 //バイト数
902 i3=lstrlen((char *)i64data);
903
904 memcpy(term,(char *)i64data,i3);
905 term[i3]=0;
906 goto StrLiteral;
907 }
908
909 type_stack[sp]=i3;
910 if(IsRealNumberType(i3)){
911 //実数
912 double dbl = compiler.GetObjectModule().meta.GetGlobalConsts().GetDoubleData(term);
913 memcpy(&i64data,&dbl,sizeof(double));
914 goto Literal;
915 }
916 else if(IsWholeNumberType(i3)){
917 //整数
918 i64data = compiler.GetObjectModule().meta.GetGlobalConsts().GetWholeData(term);
919 goto Literal;
920 }
921 else{
922 SetError(300,NULL,cp);
923 goto error;
924 }
925 }
926
927
928 //該当する識別子が見当たらないときはエラー扱いにする
929 bError=1;
930 SetError(3,term,cp);
931 type_stack[sp]=DEF_DOUBLE;
932 }
933 else{
934 //リテラル値
935 type_stack[sp]=GetLiteralValue(term,&i64data,baseType.GetBasicType());
936Literal:
937 if(type_stack[sp]==DEF_INT64||
938 type_stack[sp]==DEF_QWORD||
939 type_stack[sp]==DEF_DOUBLE){
940 //64ビット(符号有り整数/実数)
941
942 //push HILONG(dbl)
943 compiler.codeGenerator.op_push_V((long)*(long *)(((char *)(&i64data))+4));
944
945 //push LOLONG(dbl)
946 compiler.codeGenerator.op_push_V(*(long *)(&i64data));
947 }
948 else if(type_stack[sp]==DEF_SINGLE){
949 //single実数
950
951 float flt;
952 memcpy(&dbl,&i64data,sizeof(double));
953 flt=(float)dbl;
954 memcpy(&i3,&flt,sizeof(long));
955
956 //push term
957 compiler.codeGenerator.op_push_V(i3);
958 }
959 else{
960 //その他
961
962 //push term
963 compiler.codeGenerator.op_push_V((long)i64data);
964
965 if((long)i64data==0) index_stack[sp]=LITERAL_NULL;
966 }
967
968
969 //リテラル値の種類
970 if(Is64Type(type_stack[sp])==0&&IsRealNumberType(type_stack[sp])==0){
971 //整数(符号有り/無し)
972
973 index_stack[sp]=GetLiteralIndex(i64data);
974 }
975 }
976 sp++;
977 break;
978
979 //論理演算子
980 case CALC_XOR:
981 //value[sp-2] xor= value[sp-1]
982 //xor演算
983 if(!Calc_Xor(type_stack,index_stack,&sp)) goto error;
984 break;
985 case CALC_OR:
986 //value[sp-2] or= value[sp-1]
987 //or演算
988 if(!Calc_Or(type_stack,index_stack,&sp)) goto error;
989 break;
990 case CALC_AND:
991 //value[sp-2] and= value[sp-1]
992 //and演算
993 if(!Calc_And(type_stack,index_stack,&sp)) goto error;
994 break;
995 case CALC_NOT:
996 //value[sp-1]=Not value[sp-1]
997 //NOT演算子
998 if(!Calc_Not(type_stack,sp)) goto error;
999 break;
1000
1001 //比較演算子
1002 case CALC_PE:
1003 //value[sp-2]<=value[sp-1]
1004 if(!Calc_Relation_PE(type_stack,index_stack,&sp)) goto error;
1005 break;
1006 case CALC_QE:
1007 //value[sp-2]>=value[sp-1]
1008 if(!Calc_Relation_QE(type_stack,index_stack,&sp)) goto error;
1009 break;
1010 case CALC_P:
1011 //value[sp-2]<value[sp-1]
1012 if(!Calc_Relation_P(type_stack,index_stack,&sp)) goto error;
1013 break;
1014 case CALC_Q:
1015 //value[sp-2]>value[sp-1]
1016 if(!Calc_Relation_Q(type_stack,index_stack,&sp)) goto error;
1017 break;
1018 case CALC_NOTEQUAL:
1019 //value[sp-2]<>value[sp-1]
1020 if(!Calc_Relation_NotEqual(type_stack,&sp)) goto error;
1021 break;
1022 case CALC_EQUAL:
1023 //value[sp-2]=value[sp-1]
1024 if(!Calc_Relation_Equal(type_stack,&sp)) goto error;
1025 break;
1026
1027 //ビットシフト
1028 case CALC_SHL:
1029 //value[sp-2]=value[sp-2]<<value[sp-1]
1030 if(!Calc_SHL(type_stack,&sp)) goto error;
1031 break;
1032 case CALC_SHR:
1033 //value[sp-2]=value[sp-2]>>value[sp-1]
1034 if(!Calc_SHR(type_stack,&sp)) goto error;
1035 break;
1036
1037 //算術演算
1038 case CALC_ADDITION:
1039 case CALC_SUBTRACTION:
1040 case CALC_PRODUCT:
1041 if(!CalcTwoTerm_Arithmetic(idCalc,type_stack,index_stack,&sp)) goto error;
1042 break;
1043
1044 case CALC_MOD:
1045 //value[sp-2]%=value[sp-1]
1046 //剰余演算
1047 if(!Calc_Mod(type_stack,&sp)) goto error;
1048 break;
1049 case CALC_QUOTIENT:
1050 //value[sp-2]/=value[sp-1];
1051 //除算
1052 if(!Calc_Divide(type_stack,&sp,baseType.GetBasicType())) goto error;
1053 break;
1054 case CALC_INTQUOTIENT:
1055 //value[sp-2]/=value[sp-1]
1056 //整数除算
1057 if(!Calc_IntDivide(type_stack,index_stack,&sp)) goto error;
1058 break;
1059 case CALC_MINUSMARK:
1060 //value[sp-1]=-value[sp-1]
1061 //符号反転
1062 if(!Calc_MinusMark(type_stack,sp)) goto error;
1063 index_stack[sp-1]=-1;
1064 break;
1065 case CALC_POWER:
1066 //べき乗演算(浮動小数点演算のみ)
1067 if(!Calc_Power(type_stack,&sp)) goto error;
1068 break;
1069 case CALC_AS:
1070 //キャスト
1071 if(!Calc_Cast(type_stack,index_stack,&sp)) goto error;
1072 break;
1073
1074 case CALC_BYVAL:
1075 //ポインタ型→参照型
1076 if( PTR_LEVEL( type_stack[sp-1] ) <= 0 ){
1077 //ポインタ型ではないとき
1078 SetError( 3, NULL, cp );
1079 goto error;
1080 }
1081
1082 type_stack[sp-1] = PTR_LEVEL_DOWN( type_stack[sp-1] );
1083
1084 break;
1085
1086 default:
1087 SetError(300,NULL,cp);
1088 goto error;
1089 }
1090 }
1091
1092 if(bError) goto error;
1093
1094 if(sp!=1){
1095 SetError(1,NULL,cp);
1096 goto error;
1097 }
1098
1099 if(bLiteralCalculation){
1100 //右辺値が数値の定数式の場合
1101 SetError();
1102 }
1103 else{
1104 //右辺値が数値の定数式ではないとき
1105 if(IS_LITERAL(index_stack[0])) index_stack[0]=-1;
1106 }
1107
1108 if(pbUseHeap) *pbUseHeap=bUseHeap[0];
1109
1110 resultType.SetType( type_stack[0], index_stack[0] );
1111
1112 bool isSuccessful = true;
1113 goto finish;
1114
1115
1116error:
1117 isSuccessful = false;
1118 goto finish;
1119
1120
1121finish:
1122
1123 for(i=0;i<pnum;i++){
1124 if(values[i]) HeapDefaultFree(values[i]);
1125 }
1126
1127 //再配置スケジュールバックアップ情報を解放
1128 delete pobj_BackReloc;
1129
1130 return isSuccessful;
1131}
Note: See TracBrowser for help on using the repository browser.