source: dev/BasicCompiler32/NumOpe.cpp@ 104

Last change on this file since 104 was 103, checked in by dai_9181, 18 years ago

名前空間機能をグローバル変数、定数と列挙型に適用。
一部、クラスの静的メンバと名前空間の相性が悪いコードが潜んでいるため、要改修

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