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

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