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

Last change on this file since 206 was 206, 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 ConstMacro *pConstMacro = compiler.GetMeta().GetGlobalConstMacros().Find( procName );
390 if( pConstMacro )
391 {
392 if( pConstMacro->GetCalcBuffer( parameter, temporary ) )
393 {
394 /////////////////////////
395 // マクロ関数
396 /////////////////////////
397
398 //閉じカッコ")"に続く文字がNULLでないときはエラーにする
399 if(termFull[i2+1+i4+1]!='\0') SetError(42,NULL,cp);
400
401 //マクロ関数の場合
402 NumOpe(useReg, temporary,Type(),resultType);
403
404 if(!IS_LITERAL(resultType.GetIndex())){
405 //リテラル値ではなかったとき
406 isLiteral = false;
407 }
408
409 return true;
410 }
411 }
412 }
413 else if( isProcedureCallOnly ){
414 // 関数呼び出し以外は受け付けない
415 return false;
416 }
417
418
419 ////////////////////////////////
420 // インデクサ(getアクセサ)
421 ////////////////////////////////
422
423 char VarName[VN_SIZE],ArrayElements[VN_SIZE];
424 GetArrayElement(termFull,VarName,ArrayElements);
425 if(ArrayElements[0]){
426 GetVarType(VarName,resultType,false);
427 if( resultType.IsObject() ){
428 CallIndexerGetterProc(/*UseReg,*/&resultType.GetClass(),VarName,ArrayElements,resultType);
429
430 isLiteral = false;
431
432 return true;
433 }
434 }
435
436
437 ////////////////////////////////
438 // 変数
439 ////////////////////////////////
440
441 RELATIVE_VAR relativeVar;
442 if(GetVarOffset(
443 false, //エラー表示なし
444 false, //読み込み専用
445 termFull,
446 &relativeVar,resultType)){
447 //////////
448 // 変数
449 //////////
450
451 if( !VarToReg( relativeVar, baseType, resultType ) ){
452 SetError(11,termFull,cp);
453 }
454
455 isLiteral = false;
456
457 return true;
458 }
459
460
461 /////////////////////////////////
462 // プロパティ用のメソッド
463 /////////////////////////////////
464
465 //配列要素を排除
466 GetArrayElement(termFull,VarName,ArrayElements);
467
468 if(GetSubHash(VarName,0)){
469
470 {
471 CallPropertyMethod(termFull,NULL,resultType);
472
473 //大きな型への暗黙の変換
474 int bigType = AutoBigCast(baseType.GetBasicType(), resultType.GetBasicType() );
475
476 if( resultType.GetBasicType() != bigType ){
477 // 大きな型へ変換された場合
478 // ※レジスタの値をキャストする
479 ExtendRegToBigType( REG_EAX, bigType, resultType.GetBasicType() );
480
481 resultType.SetBasicType( bigType );
482 }
483
484 //SetUseRegFromRax(resultType.GetBasicType(),UseReg,XmmReg);
485 }
486
487
488 if(resultType.IsStruct()){
489 //構造体が戻ったときはヒープ領域にインスタンスが格納されている
490 //※後にfreeする必要あり
491 // TODO: 解放はGCに任せる
492 *pbUseHeap = 1;
493 }
494
495 isLiteral = false;
496
497 return true;
498 }
499
500
501 return false;
502}
503
504
505bool NumOpe( int reg,
506 const char *expression,
507 const Type &baseType,
508 Type &resultType,
509 BOOL *pbUseHeap ){
510
511 if( !NumOpe( expression, baseType, resultType, pbUseHeap ) ){
512 return false;
513 }
514
515 if( reg != REG_EAX ){
516 // TODO: 未実装
517 SetError();
518 }
519
520 if( resultType.IsReal() ){
521 //fld ptr[esp]
522 op_fld_ptr_esp( resultType.GetBasicType() );
523
524 //add esp,size
525 op_add_esp( resultType.GetBasicSize() );
526 }
527 else{
528 //pop eax
529 op_pop(REG_EAX);
530
531 if( resultType.Is64() ){
532 //pop edx
533 op_pop(REG_EDX);
534 }
535 }
536 return true;
537}
538bool NumOpe( const char *expression,
539 const Type &baseType,
540 Type &resultType,
541 BOOL *pbUseHeap ){
542
543 int i,i2,i3;
544 char temporary[1024],temp2[1024];
545
546 if(expression[0]=='\0'){
547 SetError(1,NULL,cp);
548 return false;
549 }
550
551 if(expression[0]==1&& expression[1]==ESC_NEW ){
552 //New演算子(オブジェクト生成)
553
554 if( !Operator_New( expression+2, baseType, resultType ) ){
555 return false;
556 }
557
558 return true;
559 }
560
561 if( !baseType.IsNull() && expression[0] == '[' ){
562 // リテラル配列の場合
563
564 if( !baseType.IsPointer() ){
565 SetError(1,NULL,cp);
566 return false;
567 }
568 Type tempBaseType( baseType );
569 tempBaseType.PtrLevelDown();
570
571 char *buffer = (char *)malloc( lstrlen( expression ) + 1 );
572 lstrcpy( buffer, expression );
573 RemoveStringBracket( buffer );
574
575 void *binary = malloc( 1 );
576 int num = 0;
577
578 i = 0;
579 while( buffer[i] ){
580 i = GetOneParameter( buffer, i, temporary );
581 if( buffer[i] == ',' ){
582 i++;
583 }
584
585 Type resultType;
586 _int64 i64data;
587 if( !StaticCalculation( true, temporary, tempBaseType.GetBasicType(), &i64data, resultType ) ){
588 return false;
589 }
590 if( !resultType.IsWhole() ){
591 // TODO: 実数に未対応
592 SetError();
593 return false;
594 }
595
596 binary = realloc( binary, ( num + 1 ) * tempBaseType.GetSize() );
597 memcpy( (char *)binary + (num * tempBaseType.GetSize()), &i64data, tempBaseType.GetSize() );
598 num++;
599 }
600
601 i2 = compiler.GetNativeCode().GetDataTable().AddBinary( binary, num * tempBaseType.GetSize() );
602
603 //mov eax,i2
604 op_mov_RV(REG_EAX,i2);
605 obp-=sizeof(long);
606 pobj_DataTableSchedule->add();
607 obp+=sizeof(long);
608
609 free( buffer );
610
611 resultType = baseType;
612
613 //push eax
614 op_push( REG_EAX );
615
616 return true;
617 }
618
619
620 /////////////////////////////////
621 // 式要素を逆ポーランド式で取得
622 /////////////////////////////////
623
624 char *values[255];
625 long calc[255];
626 long stack[255];
627 int pnum;
628 if(!GetNumOpeElements(expression,&pnum,values,calc,stack)){
629 for(i=0;i<pnum;i++){
630 if(values[i]) HeapDefaultFree(values[i]);
631 }
632 return false;
633 }
634
635
636 BOOL bError;
637 bError=0;
638
639 //リテラル値のみの計算かどうかを判別するためのフラグ
640 BOOL bLiteralCalculation=1;
641
642 //リテラル演算の場合を考慮した演算前のバッファ位置
643 int BeforeObp;
644 BeforeObp=obp;
645
646 //リテラル演算の場合を考慮した演算前のプロシージャスケジュール位置
647 //※64ビットの掛け算、除算などで特殊関数が呼ばれるため
648 int Before_ProcAddrScheduleNum;
649 Before_ProcAddrScheduleNum=pobj_SubAddrSchedule->num;
650
651 //リテラル演算の場合を考慮した演算前のデータテーブルスケジュール位置
652 int Before_DataTableScheduleNum;
653 Before_DataTableScheduleNum=pobj_DataTableSchedule->num;
654
655 //リテラル演算の場合を考慮した演算前の再配置スケジュール
656 CReloc *pobj_BackReloc;
657 pobj_BackReloc=new CReloc();
658 pobj_BackReloc->copy(pobj_Reloc);
659
660 double dbl;
661 int sp;
662 int type_stack[255];
663 bool isNothing_stack[255];
664 LONG_PTR index_stack[255];
665 BOOL bUseHeap[255];
666 _int64 i64data;
667 for(i=0,sp=0;i<pnum;i++){
668 int idCalc;
669 idCalc=calc[i]%100;
670
671 if(idCalc){
672 if(type_stack[sp-2]==DEF_OBJECT){
673 if( idCalc == CALC_AS
674 && type_stack[sp-1] == ( DEF_OBJECT | FLAG_CAST )
675 && index_stack[sp-1] == index_stack[sp-2]
676 || isNothing_stack[sp-2] ){
677 // 同一の型、またはNothingに対するAsはAs演算子を呼び出さない
678 }
679 else if( idCalc == CALC_AS
680 && type_stack[sp-1] == ( DEF_OBJECT | FLAG_CAST )
681 && ( ((CClass *)index_stack[sp-1])->IsEqualsOrSubClass( (CClass *)index_stack[sp-2] ) || ((CClass *)index_stack[sp-2])->IsEqualsOrSubClass( (CClass *)index_stack[sp-1] )
682 )){
683 // ダウンキャストを許可する
684 }
685 else{
686 //オーバーロードされたオペレータを呼び出す
687 i2=CallOperatorProc(idCalc,baseType,type_stack,index_stack,bUseHeap,sp);
688 if(i2==0){
689 if(idCalc==CALC_EQUAL) lstrcpy(temp2,"==");
690 else GetCalcName(idCalc,temp2);
691 sprintf(temporary,"Operator %s",temp2);
692 SetError(27,temporary,cp);
693 goto error;
694 }
695 else if(i2==-1) goto error;
696
697 continue;
698 }
699 }
700
701 if(!CheckCalcType(idCalc,type_stack,sp)) goto error;
702 }
703
704 switch(idCalc){
705 //数値
706 case 0:
707 index_stack[sp]=-1;
708 isNothing_stack[sp] = false;
709 bUseHeap[sp]=0;
710
711 char *term;
712 term=values[i];
713
714 if( calc[i+1]%100 == CALC_AS ){
715 // As演算子の右辺値
716 //型名
717 if( Compiler::StringToType( term, resultType ) ){
718 resultType.SetBasicType( resultType.GetBasicType() | FLAG_CAST );
719 }
720 else{
721 SetError(3, term, cp );
722 goto error;
723 }
724
725 type_stack[sp] = resultType.GetBasicType();
726 index_stack[sp] = resultType.GetIndex();
727 sp++;
728
729 break;
730 }
731
732 if(term[0]=='\"'){
733 //リテラル文字列
734 if(!RemoveStringQuotes(term)){
735 SetError(43,NULL,cp);
736 goto error;
737 }
738 i3=lstrlen(term);
739StrLiteral:
740
741 if( baseType.IsObject() || baseType.IsNull() ){
742 //要求タイプがオブジェクト、または未定のとき
743
744 //String型オブジェクトを生成
745 NewStringObject(term);
746
747 type_stack[sp]=DEF_OBJECT;
748 index_stack[sp]=(LONG_PTR)compiler.GetMeta().GetClasses().GetStringClassPtr();
749 bLiteralCalculation=0;
750
751 sp++;
752 break;
753 }
754
755
756 type_stack[sp]=typeOfPtrChar;
757 bLiteralCalculation=0;
758
759 i2=compiler.GetNativeCode().GetDataTable().AddString(term,i3);
760
761 //push DataSize
762 OpBuffer[obp++]=(char)0x68;
763 *((long *)(OpBuffer+obp))=i2;
764 pobj_DataTableSchedule->add();
765 obp+=sizeof(long);
766 }
767 else if((term[0]=='e'||term[0]=='E')&&
768 (term[1]=='x'||term[1]=='X')&&
769 term[2]=='\"'){
770 //拡張版リテラル文字列(エスケープシーケンス可能)
771 if(!RemoveStringQuotes(term+2)){
772 SetError(43,NULL,cp);
773 goto error;
774 }
775 i3=FormatString_EscapeSequence(term+2);
776 term+=2;
777
778 goto StrLiteral;
779 }
780 else if(IsVariableTopChar(term[0])||
781 term[0]=='*'||
782 (term[0]=='.'&&IsVariableTopChar(term[1]))){
783 //////////////////
784 // 何らかの識別子
785
786 bool isLiteral;
787 if( TermOpe( term, baseType, resultType, isLiteral, &bUseHeap[sp] ) ){
788 if(resultType.IsNull()){
789 //戻り値が存在しないとき
790 for(i2=0;;i2++){
791 if(term[i2]=='('||term[i2]=='\0'){
792 term[i2]=0;
793 break;
794 }
795 }
796 SetError(38,term,cp);
797
798 goto error;
799 }
800
801 type_stack[sp] = resultType.GetBasicType();
802 index_stack[sp] = resultType.GetIndex();
803
804 if( !isLiteral ){
805 bLiteralCalculation=0;
806 }
807
808 if( resultType.GetBasicType() & FLAG_CAST ){
809 // 型名のみ
810 SetError();
811 }
812 else{
813 if( resultType.IsReal() ){
814 //sub esp,size
815 //fstp ptr[esp]
816 op_fstp_push( resultType );
817 }
818 else{
819 if( resultType.Is64() ){
820 //push edx
821 op_push( REG_EDX );
822 }
823 else{
824 ExtendTypeTo32( resultType.GetBasicType(), REG_EAX );
825 }
826
827 //push eax
828 op_push( REG_EAX );
829 }
830 }
831
832 sp++;
833 break;
834 }
835
836
837 // Nothing
838 if( lstrcmp( term, "Nothing" ) == 0 ){
839 isNothing_stack[sp] = true;
840
841 type_stack[sp] = DEF_OBJECT;
842 if( baseType.IsObject() ){
843 index_stack[sp] = baseType.GetIndex();
844 }
845 else{
846 index_stack[sp] = (LONG_PTR)compiler.GetMeta().GetClasses().GetObjectClassPtr();
847 }
848
849 bLiteralCalculation = 0;
850
851 //push 0
852 op_push_V( 0 );
853
854 sp++;
855 break;
856 }
857
858
859 //////////////
860 // 定数の場合
861 //////////////
862
863 i3 = compiler.GetMeta().GetGlobalConsts().GetBasicType(term);
864 if(i3){
865 if( compiler.GetMeta().GetGlobalConsts().IsStringPtr( term ) ){
866 //リテラル文字列
867
868 double dbl = compiler.GetMeta().GetGlobalConsts().GetDoubleData(term);
869 memcpy(&i64data,&dbl,sizeof(double));
870
871 //バイト数
872 i3=lstrlen((char *)i64data);
873
874 memcpy(term,(char *)i64data,i3);
875 term[i3]=0;
876 goto StrLiteral;
877 }
878
879 type_stack[sp]=i3;
880 if(IsRealNumberType(i3)){
881 //実数
882 double dbl = compiler.GetMeta().GetGlobalConsts().GetDoubleData(term);
883 memcpy(&i64data,&dbl,sizeof(double));
884 goto Literal;
885 }
886 else if(IsWholeNumberType(i3)){
887 //整数
888 i64data = compiler.GetMeta().GetGlobalConsts().GetWholeData(term);
889 goto Literal;
890 }
891 else{
892 SetError(300,NULL,cp);
893 goto error;
894 }
895 }
896
897
898 //該当する識別子が見当たらないときはエラー扱いにする
899 bError=1;
900 SetError(3,term,cp);
901 type_stack[sp]=DEF_DOUBLE;
902 }
903 else{
904 //リテラル値
905 type_stack[sp]=GetLiteralValue(term,&i64data,baseType.GetBasicType());
906Literal:
907 if(type_stack[sp]==DEF_INT64||
908 type_stack[sp]==DEF_QWORD||
909 type_stack[sp]==DEF_DOUBLE){
910 //64ビット(符号有り整数/実数)
911
912 //push HILONG(dbl)
913 op_push_V((long)*(long *)(((char *)(&i64data))+4));
914
915 //push LOLONG(dbl)
916 op_push_V(*(long *)(&i64data));
917 }
918 else if(type_stack[sp]==DEF_SINGLE){
919 //single実数
920
921 float flt;
922 memcpy(&dbl,&i64data,sizeof(double));
923 flt=(float)dbl;
924 memcpy(&i3,&flt,sizeof(long));
925
926 //push term
927 op_push_V(i3);
928 }
929 else{
930 //その他
931
932 //push term
933 op_push_V((long)i64data);
934
935 if((long)i64data==0) index_stack[sp]=LITERAL_NULL;
936 }
937
938
939 //リテラル値の種類
940 if(Is64Type(type_stack[sp])==0&&IsRealNumberType(type_stack[sp])==0){
941 //整数(符号有り/無し)
942
943 index_stack[sp]=GetLiteralIndex(i64data);
944 }
945 }
946 sp++;
947 break;
948
949 //論理演算子
950 case CALC_XOR:
951 //value[sp-2] xor= value[sp-1]
952 //xor演算
953 if(!Calc_Xor(type_stack,index_stack,&sp)) goto error;
954 break;
955 case CALC_OR:
956 //value[sp-2] or= value[sp-1]
957 //or演算
958 if(!Calc_Or(type_stack,index_stack,&sp)) goto error;
959 break;
960 case CALC_AND:
961 //value[sp-2] and= value[sp-1]
962 //and演算
963 if(!Calc_And(type_stack,index_stack,&sp)) goto error;
964 break;
965 case CALC_NOT:
966 //value[sp-1]=Not value[sp-1]
967 //NOT演算子
968 if(!Calc_Not(type_stack,sp)) goto error;
969 break;
970
971 //比較演算子
972 case CALC_PE:
973 //value[sp-2]<=value[sp-1]
974 if(!Calc_Relation_PE(type_stack,index_stack,&sp)) goto error;
975 break;
976 case CALC_QE:
977 //value[sp-2]>=value[sp-1]
978 if(!Calc_Relation_QE(type_stack,index_stack,&sp)) goto error;
979 break;
980 case CALC_P:
981 //value[sp-2]<value[sp-1]
982 if(!Calc_Relation_P(type_stack,index_stack,&sp)) goto error;
983 break;
984 case CALC_Q:
985 //value[sp-2]>value[sp-1]
986 if(!Calc_Relation_Q(type_stack,index_stack,&sp)) goto error;
987 break;
988 case CALC_NOTEQUAL:
989 //value[sp-2]<>value[sp-1]
990 if(!Calc_Relation_NotEqual(type_stack,&sp)) goto error;
991 break;
992 case CALC_EQUAL:
993 //value[sp-2]=value[sp-1]
994 if(!Calc_Relation_Equal(type_stack,&sp)) goto error;
995 break;
996
997 //ビットシフト
998 case CALC_SHL:
999 //value[sp-2]=value[sp-2]<<value[sp-1]
1000 if(!Calc_SHL(type_stack,&sp)) goto error;
1001 break;
1002 case CALC_SHR:
1003 //value[sp-2]=value[sp-2]>>value[sp-1]
1004 if(!Calc_SHR(type_stack,&sp)) goto error;
1005 break;
1006
1007 //算術演算
1008 case CALC_ADDITION:
1009 case CALC_SUBTRACTION:
1010 case CALC_PRODUCT:
1011 if(!CalcTwoTerm_Arithmetic(idCalc,type_stack,index_stack,&sp)) goto error;
1012 break;
1013
1014 case CALC_MOD:
1015 //value[sp-2]%=value[sp-1]
1016 //剰余演算
1017 if(!Calc_Mod(type_stack,&sp)) goto error;
1018 break;
1019 case CALC_QUOTIENT:
1020 //value[sp-2]/=value[sp-1];
1021 //除算
1022 if(!Calc_Divide(type_stack,&sp,baseType.GetBasicType())) goto error;
1023 break;
1024 case CALC_INTQUOTIENT:
1025 //value[sp-2]/=value[sp-1]
1026 //整数除算
1027 if(!Calc_IntDivide(type_stack,index_stack,&sp)) goto error;
1028 break;
1029 case CALC_MINUSMARK:
1030 //value[sp-1]=-value[sp-1]
1031 //符号反転
1032 if(!Calc_MinusMark(type_stack,sp)) goto error;
1033 index_stack[sp-1]=-1;
1034 break;
1035 case CALC_POWER:
1036 //べき乗演算(浮動小数点演算のみ)
1037 if(!Calc_Power(type_stack,&sp)) goto error;
1038 break;
1039 case CALC_AS:
1040 //キャスト
1041 if(!Calc_Cast(type_stack,index_stack,&sp)) goto error;
1042 break;
1043
1044 case CALC_BYVAL:
1045 //ポインタ型→参照型
1046 if( PTR_LEVEL( type_stack[sp-1] ) <= 0 ){
1047 //ポインタ型ではないとき
1048 SetError( 3, NULL, cp );
1049 goto error;
1050 }
1051
1052 type_stack[sp-1] = PTR_LEVEL_DOWN( type_stack[sp-1] );
1053
1054 break;
1055
1056 default:
1057 SetError(300,NULL,cp);
1058 goto error;
1059 }
1060 }
1061
1062 if(bError) goto error;
1063
1064 if(sp!=1){
1065 SetError(1,NULL,cp);
1066 goto error;
1067 }
1068
1069 if(bLiteralCalculation){
1070 //右辺値が数値の定数式の場合
1071 Type resultType;
1072 StaticCalculation(true, expression,baseType.GetBasicType(),&i64data,resultType);
1073
1074 obp=BeforeObp;
1075 pobj_SubAddrSchedule->num=Before_ProcAddrScheduleNum;
1076 pobj_DataTableSchedule->num=Before_DataTableScheduleNum;
1077 pobj_Reloc->copy(pobj_BackReloc);
1078
1079 if( resultType.GetBasicSize() == sizeof(_int64) ){
1080 //64ビット(符号有り整数/実数)
1081
1082 //push HILONG(i64data)
1083 op_push_V((long)*(long *)(((char *)(&i64data))+4));
1084
1085 //push LOLONG(i64data)
1086 op_push_V(*(long *)(&i64data));
1087 }
1088 else if( resultType.IsSingle() ){
1089 //single実数
1090
1091 memcpy(&dbl,&i64data,sizeof(_int64));
1092
1093 float flt;
1094 flt=(float)dbl;
1095 memcpy(&i3,&flt,sizeof(long));
1096
1097 //push flt
1098 op_push_V(i3);
1099 }
1100 else{
1101 //整数(符号有り/無し)
1102
1103 i3=(long)i64data;
1104
1105 if(resultType.GetBasicSize()==sizeof(char)) i3=i3&0x000000FF;
1106 if(resultType.GetBasicSize()==sizeof(short)) i3=i3&0x0000FFFF;
1107
1108 //push term
1109 op_push_V(i3);
1110 }
1111
1112 type_stack[0]=resultType.GetBasicType();
1113 index_stack[0]=resultType.GetIndex();
1114 }
1115 else{
1116 //右辺値が数値の定数式ではないとき
1117 if(IS_LITERAL(index_stack[0])) index_stack[0]=-1;
1118 }
1119
1120 if(pbUseHeap) *pbUseHeap=bUseHeap[0];
1121
1122 resultType.SetType( type_stack[0], index_stack[0] );
1123
1124 bool isSuccessful = true;
1125 goto finish;
1126
1127
1128error:
1129 isSuccessful = false;
1130 goto finish;
1131
1132
1133finish:
1134
1135 for(i=0;i<pnum;i++){
1136 if(values[i]) HeapDefaultFree(values[i]);
1137 }
1138
1139 //再配置スケジュールバックアップ情報を解放
1140 delete pobj_BackReloc;
1141
1142 return isSuccessful;
1143}
Note: See TracBrowser for help on using the repository browser.