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

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