source: dev/trunk/abdev/BasicCompiler32/Compile_Statement.cpp@ 424

Last change on this file since 424 was 424, checked in by dai_9181, 16 years ago

・ジェネリックな型をパラメータに持つメソッドのオーバーロード解決に対応した。
・型パラメータの制約クラス指定に対応した。

File size: 32.9 KB
RevLine 
[206]1#include "stdafx.h"
2
[248]3#include <LexicalScope.h>
[183]4#include <Compiler.h>
5
[3]6#include "../BasicCompiler_Common/common.h"
7#include "Opcode.h"
8
[129]9void OpcodeOthers( const char *Command ){
[3]10 int i,i2;
11
[122]12 char leftTerm[8192];
13 int lastParePos = 0;
[3]14 for(i=0;;i++){
[122]15 if(Command[i]=='\"'){
16 //ダブルクォートは不正なのでエラー扱い
17 leftTerm[i]=0;
18 SetError(3,leftTerm,cp);
19 return;
20 }
21
22 if(Command[i]=='('){
23 lastParePos = i;
24 i2=GetStringInPare(leftTerm+i,Command+i);
[3]25 i+=i2-1;
26 continue;
27 }
[122]28 if(Command[i]=='['){
29 i2=GetStringInBracket(leftTerm+i,Command+i);
30 i+=i2-1;
[3]31 continue;
32 }
[122]33 if(Command[i]=='\0'){
34 leftTerm[i] = 0;
[3]35 break;
36 }
[122]37
38 if( IsNumCalcMark( Command, i ) ){
39 leftTerm[i] = 0;
40 break;
41 }
42
43 leftTerm[i]=Command[i];
[3]44 }
45 if(!(
[122]46 IsVariableTopChar(leftTerm[0])||
47 leftTerm[0]=='.'||
48 (leftTerm[0]==1&&leftTerm[1]==ESC_PSMEM)
[3]49 )){
50 SetError(1,NULL,cp);
51 return;
52 }
53
54
[122]55 if(Command[i]=='\0' && lastParePos == 0){
[3]56 //////////////////////////////
57 // パラメータ無しのマクロ検索
58 //////////////////////////////
59
[206]60 const UserProc *pUserProc = GetSubHash(Command);
[3]61
62 //GetSubHash内でエラー提示が行われた場合
[75]63 if(pUserProc==(UserProc *)-1) return;
[3]64
[75]65 if(pUserProc==0){
[3]66 char temporary[VN_SIZE];
67 lstrcpy(temporary,Command);
68
69 CharUpper(temporary);
[75]70 pUserProc=GetSubHash(temporary);
[3]71
72 //GetSubHash内でエラー提示が行われた場合
[75]73 if(pUserProc==(UserProc *)-1) return;
[3]74 }
75
[75]76 if(pUserProc){
[122]77 if( !pUserProc->IsMacro() ){
78 SetError(10,Command,cp);
79 }
[3]80
[290]81 Opcode_CallProc("",pUserProc,0,"");
[3]82
83 return;
84 }
85 }
86 else if(IsNumCalcMark(Command,i)){
87 //代入演算
88 OpcodeCalc(Command);
89 return;
90 }
91
[122]92 Type resultType;
93 bool isLiteral;
94 BOOL bUseHeap;
[415]95 bool result = TermOpe( leftTerm, Type(), resultType, isLiteral, &bUseHeap, NULL, true );
[122]96 if( result ){
[3]97
98 /////////////////////
99 // 戻り値の処理
100 /////////////////////
101
[76]102 if( resultType.IsReal() ){
[3]103 //fstp st(0)
[236]104 compiler.codeGenerator.PutOld(
105 (char)0xDD,
106 (char)0xD8
107 );
[3]108 }
[76]109 else if( resultType.IsStruct() ){
[51]110 //mov ebx,eax
[225]111 compiler.codeGenerator.op_mov_RR(REG_EBX,REG_EAX);
[3]112
[76]113 FreeTempObject(REG_EBX,&resultType.GetClass());
[3]114 }
[386]115
116 return;
[3]117 }
[386]118
119 // どこにも当てはまらなかったため、失敗
120 SetError(1,NULL,cp);
[3]121}
122
123void OpcodeIf(char *Parameter){
[241]124 int i,i2;
[76]125 Type tempType;
[3]126
127 for(i=0;;i++){
128 if(Parameter[i]=='\0'){
129 SetError(21,NULL,cp);
130 return;
131 }
132 if(Parameter[i]==1&&Parameter[i+1]==ESC_THEN){
133 Parameter[i]=0;
134 break;
135 }
136 }
137
[248]138 const PertialSchedule *pIfPertialSchedule = NULL;
[326]139 if( !NumOpe(Parameter,Type(DEF_BOOLEAN),tempType) ){
[3]140 //NumOpe内でエラー
141 }
[76]142 else if( tempType.IsDouble() ){
[3]143 //fld qword ptr[esp]
[225]144 compiler.codeGenerator.op_fld_ptr_esp(DEF_DOUBLE);
[3]145
146 //push 0
[225]147 compiler.codeGenerator.op_push_V(0);
[3]148
149 //fild dword ptr[esp]
[225]150 compiler.codeGenerator.op_fld_ptr_esp(DEF_LONG);
[3]151
152 //add esp,sizeof(double)+sizeof(long)
[225]153 compiler.codeGenerator.op_add_esp(sizeof(double)+sizeof(long));
[3]154
155 //fcompp
[225]156 compiler.codeGenerator.op_fcompp();
[3]157
158 //fnstsw ax
[225]159 compiler.codeGenerator.op_fnstsw_ax();
[3]160
161 //test ah,40
[225]162 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]163
164 //jne (endif、または else まで)
[241]165 pIfPertialSchedule = compiler.codeGenerator.op_jne( 0, sizeof(long), true );
[3]166 }
[76]167 else if( tempType.IsSingle() ){
[3]168 //fld dword ptr[esp]
[225]169 compiler.codeGenerator.op_fld_ptr_esp(DEF_SINGLE);
[3]170
171 //push 0
[225]172 compiler.codeGenerator.op_push_V(0);
[3]173
174 //fild dword ptr[esp]
[225]175 compiler.codeGenerator.op_fld_ptr_esp(DEF_LONG);
[3]176
177 //add esp,sizeof(float)+sizeof(long)
[225]178 compiler.codeGenerator.op_add_esp(sizeof(float)+sizeof(long));
[3]179
180 //fcompp
[225]181 compiler.codeGenerator.op_fcompp();
[3]182
183 //fnstsw ax
[225]184 compiler.codeGenerator.op_fnstsw_ax();
[3]185
186 //test ah,40
[225]187 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]188
189 //jne (endif、または else まで)
[241]190 pIfPertialSchedule = compiler.codeGenerator.op_jne( 0, sizeof(long), true );
[3]191 }
[76]192 else if( tempType.Is64() ){
[3]193 //64ビット型
194
195 //pop eax
[225]196 compiler.codeGenerator.op_pop(REG_EAX);
[3]197
198 //pop ebx
[225]199 compiler.codeGenerator.op_pop(REG_EBX);
[3]200
201 //cmp eax,0
[236]202 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]203
204 //jne
[248]205 const PertialSchedule *pTempPertialSchedule1 = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]206
207 //cmp ebx,0
[236]208 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EBX, 0 );
[3]209
210 //jne
[248]211 const PertialSchedule *pTempPertialSchedule2 = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]212
213 //jmp (endif、または else までジャンプ)
[241]214 pIfPertialSchedule = compiler.codeGenerator.op_jmp( 0, sizeof(long), true );
[3]215
[241]216 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule1 );
217 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule2 );
[3]218 }
219 else{
220 //32ビット型
221
222 //pop eax
[225]223 compiler.codeGenerator.op_pop(REG_EAX);
[3]224
225 //cmp eax,0
[236]226 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]227
228 //je (endif、または else まで条件ジャンプ)
[241]229 pIfPertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(long), true );
[3]230 }
231
232
233 /////////////////////////
234 // If内をコード化
235 /////////////////////////
236
237 //レキシカルスコープをレベルアップ
[276]238 compiler.codeGenerator.lexicalScopes.Start(
239 compiler.codeGenerator.GetNativeCodeSize(),
240 LexicalScope::SCOPE_TYPE_IF
241 );
[3]242
243 i2=CompileBuffer(ESC_ENDIF,0);
244
245 //レキシカルスコープをレベルダウン
[248]246 compiler.codeGenerator.lexicalScopes.End();
[3]247
248
[241]249 if( pIfPertialSchedule == NULL ) return;
[3]250
251 if(i2==ESC_ELSE){
252 //jmp (endifまで)
[248]253 const PertialSchedule *pTempPertialSchedule = compiler.codeGenerator.op_jmp( 0, sizeof(long), true );
[3]254
[241]255 compiler.codeGenerator.opfix_JmpPertialSchedule( pIfPertialSchedule );
[3]256
257
258 /////////////////////////
259 // Else内をコード化
260 /////////////////////////
261
262 //レキシカルスコープをレベルアップ
[276]263 compiler.codeGenerator.lexicalScopes.Start(
264 compiler.codeGenerator.GetNativeCodeSize(),
265 LexicalScope::SCOPE_TYPE_IF
266 );
[3]267
268 CompileBuffer(ESC_ENDIF,0);
269
270 //レキシカルスコープをレベルダウン
[248]271 compiler.codeGenerator.lexicalScopes.End();
[3]272
273
[241]274 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule );
[3]275 }
276 else{
[241]277 compiler.codeGenerator.opfix_JmpPertialSchedule( pIfPertialSchedule );
[3]278 }
279}
280
281int GetLabelAddress(char *LabelName,int LineNum){
282 if(LabelName){
[261]283 BOOST_FOREACH( const GotoLabel &label, compiler.codeGenerator.gotoLabels )
[260]284 {
285 if( label.name.size() > 0 )
286 {
287 if( label.name == LabelName )
288 {
289 return label.address;
290 }
[3]291 }
292 }
293 }
294 else{
[261]295 BOOST_FOREACH( const GotoLabel &label, compiler.codeGenerator.gotoLabels )
[260]296 {
297 if( label.name.size() == 0 )
298 {
299 if( label.line == LineNum )
300 {
301 return label.address;
302 }
[3]303 }
304 }
305 }
306 return -1;
307}
308void OpcodeGoto(char *Parameter){
309 extern HANDLE hHeap;
310 int i,LineNum;
311
312 if(Parameter[0]=='*'){
313 i=GetLabelAddress(Parameter+1,0);
314
[246]315 if( i == -1 )
316 {
317 //jmp ...(schedule)
[253]318 compiler.codeGenerator.op_jmp_goto_schedule( (const std::string)(Parameter + 1), 0, cp );
[3]319 }
[246]320 else
321 {
322 //jmp ...
[276]323 compiler.codeGenerator.op_jmp(
324 i-compiler.codeGenerator.GetNativeCodeSize(),
325 sizeof(long),
326 false,
327 true
328 );
[246]329 }
[3]330 }
331 else{
332 LineNum=atoi(Parameter);
333 i=GetLabelAddress(0,LineNum);
334
[246]335 if( i == -1 )
336 {
337 //jmp ...(schedule)
[253]338 compiler.codeGenerator.op_jmp_goto_schedule( "", LineNum, cp );
[3]339 }
[246]340 else
341 {
342 //jmp ...
[276]343 compiler.codeGenerator.op_jmp(
344 i-compiler.codeGenerator.GetNativeCodeSize(),
345 sizeof(long),
346 false,
347 true
348 );
[246]349 }
[3]350 }
351}
352void OpcodeWhile(char *Parameter){
353 extern HANDLE hHeap;
354
355 //Continueアドレスのバックアップとセット
[241]356 compiler.codeGenerator.ContinueAreaBegin();
[3]357
358 if(!Parameter[0]) SetError(10,"While",cp);
359
[248]360 const PertialSchedule *pWhilePertialSchedule = NULL;
[76]361 Type tempType;
362 if( !NumOpe(Parameter,Type(),tempType) ){
363 //ダミー
364 }
365 else if( tempType.IsDouble() ){
[3]366 //fld qword ptr[esp]
[225]367 compiler.codeGenerator.op_fld_ptr_esp(DEF_DOUBLE);
[3]368
369 //push 0
[225]370 compiler.codeGenerator.op_push_V(0);
[3]371
372 //fild dword ptr[esp]
[225]373 compiler.codeGenerator.op_fld_ptr_esp(DEF_LONG);
[3]374
375 //add esp,sizeof(double)+sizeof(long)
[225]376 compiler.codeGenerator.op_add_esp(sizeof(double)+sizeof(long));
[3]377
378 //fcompp
[225]379 compiler.codeGenerator.op_fcompp();
[3]380
381 //fnstsw ax
[225]382 compiler.codeGenerator.op_fnstsw_ax();
[3]383
384 //test ah,40
[225]385 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]386
387 //jne (Wend まで)
[241]388 pWhilePertialSchedule = compiler.codeGenerator.op_jne( 0, sizeof(long), true );
[3]389 }
[76]390 else if( tempType.IsSingle() ){
[3]391 //fld dword ptr[esp]
[225]392 compiler.codeGenerator.op_fld_ptr_esp(DEF_SINGLE);
[3]393
394 //push 0
[225]395 compiler.codeGenerator.op_push_V(0);
[3]396
397 //fild dword ptr[esp]
[225]398 compiler.codeGenerator.op_fld_ptr_esp(DEF_LONG);
[3]399
400 //add esp,sizeof(float)+sizeof(long)
[225]401 compiler.codeGenerator.op_add_esp(sizeof(float)+sizeof(long));
[3]402
403 //fcompp
[225]404 compiler.codeGenerator.op_fcompp();
[3]405
406 //fnstsw ax
[225]407 compiler.codeGenerator.op_fnstsw_ax();
[3]408
[241]409 //test ah,40h
[225]410 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]411
412 //jne (Wend まで)
[241]413 pWhilePertialSchedule = compiler.codeGenerator.op_jne( 0, sizeof(long), true );
[3]414 }
[76]415 else if( tempType.Is64() ){
[3]416 //64ビット型
417
418 //pop eax
[225]419 compiler.codeGenerator.op_pop(REG_EAX);
[3]420
421 //pop ebx
[225]422 compiler.codeGenerator.op_pop(REG_EBX);
[3]423
424 //cmp eax,0
[236]425 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]426
427 //jne
[248]428 const PertialSchedule *pTempPertialSchedule1 = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]429
430 //cmp ebx,0
[236]431 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EBX, 0 );
[3]432
433 //jne
[248]434 const PertialSchedule *pTempPertialSchedule2 = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]435
[241]436 //jmp (Wendまでジャンプ)
437 pWhilePertialSchedule = compiler.codeGenerator.op_jmp( 0, sizeof(long), true );
[3]438
[241]439 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule1 );
440 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule2 );
[3]441 }
442 else{
443 //その他整数型
444
445 //pop eax
[225]446 compiler.codeGenerator.op_pop(REG_EAX);
[3]447
448 //cmp eax,0
[236]449 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]450
451 //je (Wend まで)
[241]452 pWhilePertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(long), true );
[3]453 }
454
455 //レキシカルスコープをレベルアップ
[276]456 compiler.codeGenerator.lexicalScopes.Start( compiler.codeGenerator.GetNativeCodeSize(), LexicalScope::SCOPE_TYPE_WHILE );
[3]457
458 //While内をコンパイル
459 CompileBuffer(0,COM_WEND);
460
[248]461 compiler.codeGenerator.lexicalScopes.CallDestructorsOfScopeEnd();
[3]462
463 //jmp ...
[241]464 compiler.codeGenerator.op_jmp_continue();
[3]465
466 //レキシカルスコープをレベルダウン
[248]467 compiler.codeGenerator.lexicalScopes.End();
[3]468
[241]469 if( pWhilePertialSchedule )
470 {
471 compiler.codeGenerator.opfix_JmpPertialSchedule( pWhilePertialSchedule );
472 }
[3]473
[241]474 compiler.codeGenerator.ContinueAreaEnd();
[3]475}
476
477char szNextVariable[VN_SIZE];
478void OpcodeFor(char *Parameter){
479 extern HANDLE hHeap;
[241]480 int i,i2;
[3]481 char temporary[VN_SIZE],variable[VN_SIZE],JudgeNum[VN_SIZE],StepNum[VN_SIZE];
482
483 //第1パラメータを取得
484 i=GetOneParameter(Parameter,0,temporary);
485 if(!Parameter[i]){
486 SetError(12,"For",cp);
487 goto ErrorStep;
488 }
489
490 for(i2=0;;i2++){
491 if(temporary[i2]=='='){
492 variable[i2]=0;
493
494 //カウンタ初期化
495 OpcodeCalc(temporary);
496 break;
497 }
498 if(temporary[i2]=='\0'){
499 SetError(12,"For",cp);
500 goto ErrorStep;
501 }
502 variable[i2]=temporary[i2];
503 }
504
505 //jmp ...
[248]506 const PertialSchedule *pTempPertialSchedule = compiler.codeGenerator.op_jmp( 0, sizeof(long), true );
[3]507
508 //Continueアドレスのバックアップとセット
[241]509 compiler.codeGenerator.ContinueAreaBegin();
[3]510
511 //第2パラメータを取得(to~)
512 i=GetOneParameter(Parameter,i,JudgeNum);
513
514 //第3パラメータを取得(step~)
515 if(Parameter[i]){
516 i=GetOneParameter(Parameter,i,StepNum);
517 if(Parameter[i]) SetError(12,"For",cp);
518 }
519 else lstrcpy(StepNum,"1");
520
521 //カウンタを増加させる
522 sprintf(temporary,"%s=(%s)+(%s)",variable,variable,StepNum);
523 OpcodeCalc(temporary);
524
[241]525 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule );
[3]526
527 //増加か減少かを区別する
528 sprintf(temporary,"(%s)>=0",StepNum);
[76]529 NumOpe(temporary,Type(),Type());
[3]530
531 //pop eax
[225]532 compiler.codeGenerator.op_pop(REG_EAX);
[3]533
534 //cmp eax,0
[236]535 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]536
537 //je [カウンタ減少の場合の判定]
[241]538 pTempPertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(long), true );
[3]539
540 //判定(カウンタ増加の場合)
541 sprintf(temporary,"%s<=(%s)",variable,JudgeNum);
[76]542 NumOpe(temporary,Type(),Type());
[3]543
544 //pop eax
[225]545 compiler.codeGenerator.op_pop(REG_EAX);
[3]546
547 //jmp [カウンタ減少の場合の判定を飛び越す]
[248]548 const PertialSchedule *pTempPertialSchedule2 = compiler.codeGenerator.op_jmp( 0, sizeof(long), true );
[3]549
[241]550 //jeジャンプ先のオフセット値
551 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule );
[3]552
553 //判定(カウンタ減少の場合)
554 sprintf(temporary,"%s>=(%s)",variable,JudgeNum);
[76]555 NumOpe(temporary,Type(),Type());
[3]556
557 //pop eax
[225]558 compiler.codeGenerator.op_pop(REG_EAX);
[3]559
[241]560 //jmpジャンプ先のオフセット値
561 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule2 );
[3]562
563 //cmp eax,0
[236]564 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]565
566ErrorStep:
567
568 //je ...
[241]569 pTempPertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(long), true );
[3]570
571 //レキシカルスコープをレベルアップ
[276]572 compiler.codeGenerator.lexicalScopes.Start( compiler.codeGenerator.GetNativeCodeSize(), LexicalScope::SCOPE_TYPE_FOR );
[3]573
574 //For内をコンパイル
575 CompileBuffer(0,COM_NEXT);
576
[248]577 compiler.codeGenerator.lexicalScopes.CallDestructorsOfScopeEnd();
[3]578
579 if(szNextVariable[0]){
580 if(lstrcmp(szNextVariable,variable)!=0){
581 SetError(55,szNextVariable,cp);
582 }
583 }
584
585 //jmp ...
[241]586 compiler.codeGenerator.op_jmp_continue();
[3]587
588 //レキシカルスコープをレベルダウン
[248]589 compiler.codeGenerator.lexicalScopes.End();
[3]590
[241]591 //jeジャンプ先のオフセット値
592 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule );
[3]593
594 //Continueアドレスを復元
[241]595 compiler.codeGenerator.ContinueAreaEnd();
[3]596}
597
[372]598void OpcodeForeach( const char *Parameter )
599{
600 Type resultType;
[381]601 char temporary[VN_SIZE],variable[VN_SIZE],collectionVar[VN_SIZE];
[372]602 bool isError = false;
603
[381]604 //レキシカルスコープをレベルアップ
605 compiler.codeGenerator.lexicalScopes.Start( compiler.codeGenerator.GetNativeCodeSize(), LexicalScope::SCOPE_TYPE_FOR );
606
[372]607 //第1パラメータを取得
[381]608 int i = 0;
609 GetCustomToken( variable, Parameter, i, ESC_IN, true );
[372]610 if(!Parameter[i]){
611 SetError(12,"Foreach",cp);
612 isError = true;
613 goto ErrorStep;
614 }
[381]615 i++;
[372]616
617 //第2パラメータを取得(in~)
[381]618 lstrcpy( collectionVar, Parameter + i );
[374]619
[373]620 if( !GetVarType( variable, resultType, false ) )
621 {
622 Type collectionType;
[374]623 if( !NumOpe_GetType( collectionVar, Type(), collectionType ) )
[373]624 {
625 isError = true;
626 goto ErrorStep;
627 }
[372]628
[373]629 // 未定義の場合は自動的に定義する
[390]630 sprintf(temporary,"%s=Nothing%c%c%s", variable, 1, ESC_AS, collectionType.GetActualGenericType(0).GetClass().GetFullName().c_str() );
[373]631 OpcodeDim(temporary,DIMFLAG_INITDEBUGVAR);
632 }
633
[372]634 // Resetメソッドを呼び出す
635 sprintf( temporary, "%s.Reset()", collectionVar );
636 Compile( temporary );
637
638 //Continueアドレスのバックアップとセット
639 compiler.codeGenerator.ContinueAreaBegin();
640
641 // MoveNextメソッドを呼び出す
642 sprintf( temporary, "%s.MoveNext()", collectionVar );
643 NumOpe(temporary,Type(),Type());
644
645 //pop eax
646 compiler.codeGenerator.op_pop(REG_EAX);
647
648 //cmp eax,0
649 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
650
651ErrorStep:
652
653 //je ...
654 const PertialSchedule *pTempPertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(long), true );
655
[381]656 if( !isError )
657 {
658 // Currentプロパティから現在の値を取得
659 sprintf( temporary, "%s=%s.Current", variable, collectionVar );
660 Compile( temporary );
661 }
[372]662
663 //For内をコンパイル
664 CompileBuffer(0,COM_NEXT);
665
666 compiler.codeGenerator.lexicalScopes.CallDestructorsOfScopeEnd();
667
668 if(szNextVariable[0]){
669 if(lstrcmp(szNextVariable,variable)!=0){
670 SetError(55,szNextVariable,cp);
671 }
672 }
673
[381]674 if( !isError )
675 {
676 //jmp ...
677 compiler.codeGenerator.op_jmp_continue();
678 }
[372]679
680 //レキシカルスコープをレベルダウン
681 compiler.codeGenerator.lexicalScopes.End();
682
683 //jeジャンプ先のオフセット値
684 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule );
685
686 //Continueアドレスを復元
687 compiler.codeGenerator.ContinueAreaEnd();
688}
689
[3]690void OpcodeDo(char *Parameter){
691 extern HANDLE hHeap;
[247]692 int i,i2,i3;
[3]693
694 if(Parameter[0]) SetError(10,"Do",cp);
695
696 //Continueアドレスのバックアップとセット
[241]697 compiler.codeGenerator.ContinueAreaBegin();
[3]698
699 //レキシカルスコープをレベルアップ
[276]700 compiler.codeGenerator.lexicalScopes.Start( compiler.codeGenerator.GetNativeCodeSize(), LexicalScope::SCOPE_TYPE_DO );
[3]701
702 //Do内をコンパイル
703 CompileBuffer(0,COM_LOOP);
704
[248]705 compiler.codeGenerator.lexicalScopes.CallDestructorsOfScopeEnd();
[3]706
[248]707 const PertialSchedule *pDoPertialSchedule = NULL;
[241]708
[3]709 extern char *basbuf;
710 char temporary[VN_SIZE];
711 for(i=cp-1;;i--){
712 if(IsCommandDelimitation(basbuf[i])){
713 i+=3;
714 if(!(basbuf[i]=='0'||basbuf[i]=='1')){
715 //無条件ループ
716 break;
717 }
718 i3=i;
719
720 for(i+=2,i2=0;;i++,i2++){
721 if(IsCommandDelimitation(basbuf[i])){
722 temporary[i2]=0;
723 break;
724 }
725 temporary[i2]=basbuf[i];
726 }
727
[76]728 Type tempType;
729 NumOpe(temporary,Type(),tempType);
[3]730
[76]731 if( tempType.IsDouble() ){
[3]732 //fld qword ptr[esp]
[225]733 compiler.codeGenerator.op_fld_ptr_esp(DEF_DOUBLE);
[3]734
735 //push 0
[225]736 compiler.codeGenerator.op_push_V(0);
[3]737
738 //fild dword ptr[esp]
[225]739 compiler.codeGenerator.op_fld_ptr_esp(DEF_LONG);
[3]740
741 //add esp,sizeof(double)+sizeof(long)
[225]742 compiler.codeGenerator.op_add_esp(sizeof(double)+sizeof(long));
[3]743
744 //fcompp
[225]745 compiler.codeGenerator.op_fcompp();
[3]746
747 //fnstsw ax
[225]748 compiler.codeGenerator.op_fnstsw_ax();
[3]749
750 //test ah,40
[225]751 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]752
753 if(basbuf[i3]=='0'){
754 //While
755
756 //jne 5(ループ終了)
[241]757 pDoPertialSchedule = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]758 }
759 else if(basbuf[i3]=='1'){
760 //Until
761
762 //je 5(ループ終了)
[241]763 pDoPertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(char), true );
[3]764 }
765 }
[76]766 else if( tempType.IsSingle() ){
[3]767 //fld dword ptr[esp]
[225]768 compiler.codeGenerator.op_fld_ptr_esp(DEF_SINGLE);
[3]769
770 //push 0
[225]771 compiler.codeGenerator.op_push_V(0);
[3]772
773 //fild dword ptr[esp]
[225]774 compiler.codeGenerator.op_fld_ptr_esp(DEF_LONG);
[3]775
776 //add esp,sizeof(float)+sizeof(long)
[225]777 compiler.codeGenerator.op_add_esp(sizeof(float)+sizeof(long));
[3]778
779 //fcompp
[225]780 compiler.codeGenerator.op_fcompp();
[3]781
782 //fnstsw ax
[225]783 compiler.codeGenerator.op_fnstsw_ax();
[3]784
785 //test ah,40
[225]786 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]787
788 if(basbuf[i3]=='0'){
789 //While
790
791 //jne 5(ループ終了)
[241]792 pDoPertialSchedule = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]793 }
794 else if(basbuf[i3]=='1'){
795 //Until
796
797 //je 5(ループ終了)
[241]798 pDoPertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(char), true );
[3]799 }
800 }
[76]801 else if( tempType.Is64() ){
[3]802 //64ビット型
803
804 //pop eax
[225]805 compiler.codeGenerator.op_pop(REG_EAX);
[3]806
807 //pop ebx
[225]808 compiler.codeGenerator.op_pop(REG_EBX);
[3]809
810 //cmp eax,0
[236]811 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]812
813 //jne
[248]814 const PertialSchedule *pTempPertialSchedule1 = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]815
816 //cmp ebx,0
[236]817 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EBX, 0 );
[3]818
819 //jne
[248]820 const PertialSchedule *pTempPertialSchedule2 = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]821
822 if(basbuf[i3]=='0'){
823 //While
824
825 //jmp 5(ループ終了)
[241]826 pDoPertialSchedule = compiler.codeGenerator.op_jmp( 0, sizeof(char), true );
[3]827
[247]828 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule1 );
829 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule2 );
[3]830 }
831 else if(basbuf[i3]=='1'){
832 //Until
833
834 //jmp 2(ループを続ける)
[248]835 const PertialSchedule *pTempPertialSchedule3 = compiler.codeGenerator.op_jmp( 0, sizeof(char), true );
[3]836
[247]837 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule1 );
838 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule2 );
[3]839
840 //jmp 5(ループ終了)
[241]841 pDoPertialSchedule = compiler.codeGenerator.op_jmp( 0, sizeof(char), true );
[247]842
843 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule3 );
[3]844 }
845 }
846 else{
847 //pop eax
[225]848 compiler.codeGenerator.op_pop(REG_EAX);
[3]849
850 //cmp eax,0
[236]851 compiler.codeGenerator.op_cmp_value( sizeof(long), REG_EAX, 0 );
[3]852
853 if(basbuf[i3]=='0'){
854 //While
855
856 //je 5(ループ終了)
[241]857 pDoPertialSchedule = compiler.codeGenerator.op_je( 0, sizeof(char), true );
[3]858 }
859 else if(basbuf[i3]=='1'){
860 //Until
861
862 //jne 5(ループ終了)
[241]863 pDoPertialSchedule = compiler.codeGenerator.op_jne( 0, sizeof(char), true );
[3]864 }
865 }
866 break;
867 }
868 }
869
870 //jmp ...
[241]871 compiler.codeGenerator.op_jmp_continue();
[3]872
[241]873 if( pDoPertialSchedule )
874 {
875 compiler.codeGenerator.opfix_JmpPertialSchedule( pDoPertialSchedule );
876 }
877
[3]878 //jmp ...
[248]879 const PertialSchedule *pTempPertialSchedule = compiler.codeGenerator.op_jmp( 0, sizeof(long), true );
[3]880
881 //レキシカルスコープをレベルダウン
[248]882 compiler.codeGenerator.lexicalScopes.End();
[3]883
[243]884 //jmpジャンプ先のオフセット値
885 compiler.codeGenerator.opfix_JmpPertialSchedule( pTempPertialSchedule );
[3]886
887 //Continueアドレスを復元
[241]888 compiler.codeGenerator.ContinueAreaEnd();
[3]889}
890void OpcodeContinue(void){
891 //jmp ...(Continue addr)
[241]892 compiler.codeGenerator.op_jmp_continue();
[3]893}
894
895void OpcodeExitSub(void){
[76]896 if( UserProc::IsGlobalAreaCompiling() ){
[3]897 SetError(12,"Exit Sub/Function",cp);
898 return;
899 }
900
[34]901 //未解放のローカルオブジェクトのデストラクタを呼び出す
[248]902 compiler.codeGenerator.lexicalScopes.CallDestructorsOfReturn();
[34]903
[3]904 //jmp ...(End Sub/Function)
[247]905 compiler.codeGenerator.op_jmp_exitsub();
[3]906}
907
[250]908//Caseスケジュール
909class SelectSchedule
910{
911public:
912 SelectSchedule( int typeSize )
913 : typeSize( typeSize )
914 , nowCaseSchedule( 0 )
915 {
916 }
[3]917
[250]918 PertialSchedules casePertialSchedules;
919 int typeSize;
920 int nowCaseSchedule;
921};
922std::vector<SelectSchedule> selectSchedules;
[3]923
[408]924void OpcodeSelect(const char *lpszParms)
925{
[3]926 extern HANDLE hHeap;
927 extern char *basbuf;
[76]928 int i,i2,i3,sw,NowCaseCp;
[3]929 char temporary[VN_SIZE];
[250]930
[76]931 Type type1;
[408]932 bool result = NumOpe(lpszParms,Type(), type1 );
[3]933
[250]934 selectSchedules.push_back( SelectSchedule( type1.GetSize() ) );
935
[408]936 if( result )
937 {
938 if( selectSchedules.back().typeSize < sizeof(long) ){
939 selectSchedules.back().typeSize = sizeof(long);
940 }
[76]941
[408]942 for(i=cp,sw=0;;i++){
943 if(basbuf[i]=='\0'){
944 selectSchedules.pop_back();
945 SetError(22,"Select",cp);
946 return;
947 }
948 if(basbuf[i]==1&&basbuf[i+1]==ESC_SELECTCASE){
949 for(i2=0;;i++){
950 if(basbuf[i]==1&&basbuf[i+1]==ESC_SELECTCASE) i2++;
951 if(basbuf[i]==1&&basbuf[i+1]==ESC_ENDSELECT){
952 i2--;
953 if(i2==0) break;
954 }
[3]955 }
[408]956 continue;
[3]957 }
[408]958 if(basbuf[i]==1&&basbuf[i+1]==ESC_ENDSELECT){
959 if(sw==0){
960 //add esp,CaseTypeSize
961 compiler.codeGenerator.op_add_esp( selectSchedules.back().typeSize );
962 }
963 break;
[3]964 }
[408]965 if(basbuf[i]==1&&basbuf[i+1]==ESC_CASE){
966 NowCaseCp=i;
[3]967
[408]968 i++;
969 while(1){
970 for(i++,i2=0;;i++,i2++){
971 if(basbuf[i]=='\"'){
972 i3=GetStringInQuotation(temporary+i2,basbuf+i);
973 i+=i3-1;
974 i2+=i3-1;
975 continue;
976 }
977 if(basbuf[i]=='('){
978 i3=GetStringInPare(temporary+i2,basbuf+i);
979 i+=i3-1;
980 i2+=i3-1;
981 continue;
982 }
983 if(basbuf[i]=='['){
984 i3=GetStringInBracket(temporary+i2,basbuf+i);
985 i+=i3-1;
986 i2+=i3-1;
987 continue;
988 }
[3]989
[408]990 if(IsCommandDelimitation(basbuf[i])){
991 temporary[i2]=0;
992 break;
993 }
994 if(basbuf[i]==','){
995 temporary[i2]=0;
996 break;
997 }
998
999 temporary[i2]=basbuf[i];
[3]1000 }
1001
[408]1002 //エラー用
1003 i2=cp;
1004 cp=NowCaseCp;
[3]1005
[408]1006 Type type2;
1007 if( !NumOpe(temporary,type1,type2) ){
1008 return;
1009 }
[3]1010
[408]1011 cp=i2;
[3]1012
[408]1013 if(type1.IsObject()){
1014 std::vector<const UserProc *> subs;
1015 type1.GetClass().GetDynamicMethods().Enum( CALC_EQUAL, subs );
1016 if( subs.size() == 0 ){
1017 return;
1018 }
[3]1019
[408]1020 Parameters params;
1021 params.push_back( new Parameter( "", Type( type2 ) ) );
[3]1022
[408]1023 //オーバーロードを解決
[424]1024 const UserProc *pUserProc = OverloadSolution( "==", subs, params, Type( DEF_BOOLEAN ), type1 );
[3]1025
[408]1026 delete params[0];
[3]1027
[408]1028 if(!pUserProc){
1029 //エラー
1030 return;
1031 }
[75]1032
[3]1033
[408]1034 //pop edx
1035 compiler.codeGenerator.op_pop(REG_EDX);
[3]1036
[408]1037 //mov ecx,dword ptr[esp]
1038 compiler.codeGenerator.op_mov_RM(sizeof(long),REG_ECX,REG_ESP,0,MOD_BASE);
[3]1039
[408]1040 //push edx
1041 compiler.codeGenerator.op_push(REG_EDX);
[3]1042
[408]1043 //push ecx
1044 compiler.codeGenerator.op_push(REG_ECX);
[3]1045
[408]1046 //call operator_proc ※ ==演算子
1047 compiler.codeGenerator.op_call(pUserProc);
[3]1048
[408]1049 //test eax,eax
1050 compiler.codeGenerator.op_test(REG_EAX,REG_EAX);
[3]1051
[408]1052 //jne ...
1053 selectSchedules.back().casePertialSchedules.push_back(
1054 compiler.codeGenerator.op_jne( 0, sizeof(long), true )
1055 );
1056 }
1057 else if(type1.IsDouble()){
1058 ChangeTypeToDouble(type2.GetBasicType());
[3]1059
[408]1060 //fld qword ptr[esp]
1061 compiler.codeGenerator.op_fld_ptr_esp(DEF_DOUBLE);
[3]1062
[408]1063 //add esp,CaseTypeSize
1064 compiler.codeGenerator.op_add_esp(selectSchedules.back().typeSize);
[3]1065
[408]1066 //fld qword ptr[esp]
1067 compiler.codeGenerator.op_fld_ptr_esp(DEF_DOUBLE);
[3]1068
[408]1069 //fcompp
1070 compiler.codeGenerator.op_fcompp();
[3]1071
[408]1072 //fnstsw ax
1073 compiler.codeGenerator.op_fnstsw_ax();
[3]1074
[408]1075 //test ah,40
1076 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]1077
[408]1078 //jne ...
1079 selectSchedules.back().casePertialSchedules.push_back(
1080 compiler.codeGenerator.op_jne( 0, sizeof(long), true )
1081 );
1082 }
1083 else if(type1.IsSingle()){
1084 ChangeTypeToSingle(type2.GetBasicType());
[3]1085
[408]1086 //fld dword ptr[esp]
1087 compiler.codeGenerator.op_fld_ptr_esp(DEF_SINGLE);
[3]1088
[408]1089 //add esp,CaseTypeSize
1090 compiler.codeGenerator.op_add_esp(selectSchedules.back().typeSize);
[3]1091
[408]1092 //fld dword ptr[esp]
1093 compiler.codeGenerator.op_fld_ptr_esp(DEF_SINGLE);
[3]1094
[408]1095 //fcompp
1096 compiler.codeGenerator.op_fcompp();
[3]1097
[408]1098 //fnstsw ax
1099 compiler.codeGenerator.op_fnstsw_ax();
[3]1100
[408]1101 //test ah,40
1102 compiler.codeGenerator.op_test_ah( (char)0x40 );
[3]1103
[408]1104 //jne ...
1105 selectSchedules.back().casePertialSchedules.push_back(
1106 compiler.codeGenerator.op_jne( 0, sizeof(long), true )
1107 );
1108 }
1109 else{
1110 //その他整数型
[3]1111
[408]1112 //pop ebx
1113 compiler.codeGenerator.op_pop(REG_EBX);
[3]1114
[408]1115 //mov eax,dword ptr[esp]
1116 compiler.codeGenerator.op_mov_RM( sizeof(long), REG_EAX, REG_ESP, 0, MOD_BASE );
[3]1117
[408]1118 //cmp eax,ebx
1119 compiler.codeGenerator.op_cmp_RR( REG_EAX, REG_EBX );
[3]1120
[408]1121 //je ...
1122 selectSchedules.back().casePertialSchedules.push_back(
1123 compiler.codeGenerator.op_je( 0, sizeof(long), true )
1124 );
1125 }
[3]1126
[408]1127 if(basbuf[i]!=',') break;
[3]1128 }
[408]1129 }
1130 if(basbuf[i]==1&&basbuf[i+1]==ESC_CASEELSE){
1131 sw=1;
[3]1132
[408]1133 //jmp ...
1134 selectSchedules.back().casePertialSchedules.push_back(
1135 compiler.codeGenerator.op_jmp( 0, sizeof(long), true )
1136 );
[3]1137 }
1138 }
1139 }
1140
1141 //レキシカルスコープをレベルアップ
[276]1142 compiler.codeGenerator.lexicalScopes.Start( compiler.codeGenerator.GetNativeCodeSize(), LexicalScope::SCOPE_TYPE_SELECT );
[3]1143
1144 //Select Case内をコンパイル
1145 CompileBuffer(ESC_ENDSELECT,0);
1146
1147 //jmp EndSelect
[250]1148 selectSchedules.back().casePertialSchedules.push_back(
1149 compiler.codeGenerator.op_jmp( 0, sizeof(long), true )
1150 );
[3]1151
1152 //最終スケジュール
[250]1153 for(i=selectSchedules.back().nowCaseSchedule;i<(int)selectSchedules.back().casePertialSchedules.size();i++){
1154 compiler.codeGenerator.opfix_JmpPertialSchedule( selectSchedules.back().casePertialSchedules[i] );
[3]1155 }
1156
1157 //レキシカルスコープをレベルダウン
[248]1158 compiler.codeGenerator.lexicalScopes.End();
[3]1159
[250]1160 selectSchedules.pop_back();
[3]1161}
1162void OpcodeCase(char *Parameter){
1163 int i;
1164
[250]1165 if(selectSchedules.back().typeSize==-1){
[3]1166 SetError(30,"Case",cp);
1167 return;
1168 }
1169
1170 //jmp EndSelect
[250]1171 selectSchedules.back().casePertialSchedules.push_back(
1172 compiler.codeGenerator.op_jmp( 0, sizeof(long), true )
1173 );
[3]1174
1175 i=0;
1176 while(1){
1177 //Caseスケジュール
[250]1178 compiler.codeGenerator.opfix_JmpPertialSchedule( selectSchedules.back().casePertialSchedules[selectSchedules.back().nowCaseSchedule] );
1179 selectSchedules.back().nowCaseSchedule++;
[3]1180
1181 i=JumpOneParameter(Parameter,i);
1182 if(Parameter[i]=='\0') break;
1183 }
1184
1185 //add esp,CaseTypeSize
[250]1186 compiler.codeGenerator.op_add_esp(selectSchedules.back().typeSize);
[3]1187}
1188
1189void OpcodeGosub(char *Parameter){
1190 extern HANDLE hHeap;
1191 int i,LineNum;
1192
1193 if(Parameter[0]=='*'){
1194 i=GetLabelAddress(Parameter+1,0);
1195
[246]1196 if( i == -1 )
1197 {
1198 //jmp ...(schedule)
[253]1199 compiler.codeGenerator.op_jmp_goto_schedule( (const std::string)(Parameter + 1), 0, cp );
[3]1200 }
[246]1201 else
1202 {
1203 //jmp ...
[276]1204 compiler.codeGenerator.op_jmp(
1205 i-compiler.codeGenerator.GetNativeCodeSize(),
1206 sizeof(long),
1207 false,
1208 true
1209 );
[246]1210 }
[3]1211 }
1212 else{
1213 LineNum=atoi(Parameter);
1214 i=GetLabelAddress(0,LineNum);
1215
[246]1216 if( i == -1 )
1217 {
1218 //jmp ...(schedule)
[253]1219 compiler.codeGenerator.op_jmp_goto_schedule( "", LineNum, cp );
[3]1220 }
[246]1221 else
1222 {
1223 //jmp ...
[276]1224 compiler.codeGenerator.op_jmp(
1225 i-compiler.codeGenerator.GetNativeCodeSize(),
1226 sizeof(long),
1227 false,
1228 true
1229 );
[246]1230 }
[3]1231 }
1232}
1233void OpcodeReturn(char *Parameter){
[76]1234 if( UserProc::IsGlobalAreaCompiling() ){
[3]1235 //Gosub~Returnとして扱う
1236
1237 //ret
[225]1238 compiler.codeGenerator.op_ret();
[3]1239 }
1240 else{
1241 //戻り値をセット
1242 if(Parameter[0]){
[206]1243 const UserProc &proc = UserProc::CompilingUserProc();
[76]1244
[75]1245 const char *temp = "_System_ReturnValue";
[76]1246 if(proc.GetName()[0]==1&&proc.GetName()[1]==ESC_OPERATOR)
[75]1247 {
1248 }
[76]1249 else{
1250 temp=proc.GetName().c_str();
1251 }
[3]1252
[75]1253 char temporary[VN_SIZE];
1254 sprintf(temporary,"%s=%s",temp,Parameter);
1255 OpcodeCalc(temporary);
[3]1256 }
1257
1258 //プロシージャを抜け出す(C言語のreturnと同様の処理を行う)
1259 OpcodeExitSub();
1260 }
1261}
1262
1263
1264////////////
1265// ポインタ
1266
1267void OpcodeSetPtrData(char *Parameter,int type){
[76]1268 int i;
[3]1269 char temporary[VN_SIZE];
1270
1271 if(Parameter[0]=='('){
1272 i=JumpStringInPare(Parameter,1);
1273 if(Parameter[i+1]=='\0'){
1274 for(i=0;;i++){
1275 Parameter[i]=Parameter[i+1];
1276 if(Parameter[i]=='\0') break;
1277 }
1278 Parameter[i-1]=0;
1279 }
1280 }
1281
1282 //第1パラメータを取得
1283 i=GetOneParameter(Parameter,0,temporary);
1284 if(!Parameter[i]){
1285 SetError(1,NULL,cp);
1286 return;
1287 }
1288
[76]1289 Type resultType;
1290 if( !NumOpe(temporary,Type(),resultType) ){
1291 return;
1292 }
1293 if(!resultType.IsWhole()){
1294 SetError(11,Parameter,cp);
1295 return;
1296 }
[3]1297
[76]1298 ChangeTypeToLong( resultType.GetBasicType() );
1299
[3]1300 //第2パラメータを取得
1301 i=GetOneParameter(Parameter,i,temporary);
1302 if(Parameter[i]){
1303 SetError(1,NULL,cp);
1304 return;
1305 }
1306
[76]1307 if( !NumOpe(temporary,Type(),resultType) ){
1308 return;
1309 }
1310
[3]1311 if(type==DEF_DOUBLE){
[76]1312 ChangeTypeToDouble_ToFpuReg( resultType.GetBasicType() );
[3]1313
1314 //pop eax
[225]1315 compiler.codeGenerator.op_pop(REG_EAX);
[3]1316
1317 //fstp qword ptr[eax]
[236]1318 compiler.codeGenerator.PutOld(
1319 (char)0xDD,
1320 (char)0x18
1321 );
[3]1322 }
1323 else if(type==DEF_SINGLE){
[76]1324 ChangeTypeToSingle( resultType.GetBasicType() );
[3]1325
1326 //pop ebx
[225]1327 compiler.codeGenerator.op_pop(REG_EBX);
[3]1328
1329 //pop eax
[225]1330 compiler.codeGenerator.op_pop(REG_EAX);
[3]1331
1332 //mov dword ptr[eax],ebx
[225]1333 compiler.codeGenerator.op_mov_MR( sizeof(long), REG_EBX, REG_EAX, 0, MOD_BASE );
[3]1334 }
1335 else if(type==DEF_QWORD){
[76]1336 ChangeTypeToInt64( resultType.GetBasicType() );
[3]1337
1338 //pop ecx
[225]1339 compiler.codeGenerator.op_pop(REG_ECX);
[3]1340
1341 //pop ebx
[225]1342 compiler.codeGenerator.op_pop(REG_EBX);
[3]1343
1344 //pop eax
[225]1345 compiler.codeGenerator.op_pop(REG_EAX);
[3]1346
1347 //mov dword ptr[eax],ecx
[225]1348 compiler.codeGenerator.op_mov_MR( sizeof(long), REG_ECX, REG_EAX, 0, MOD_BASE );
[3]1349
1350 //mov dword ptr[eax+sizeof(long)],ebx
[225]1351 compiler.codeGenerator.op_mov_MR( sizeof(long), REG_EBX, REG_EAX, 0x04, MOD_BASE_DISP8 );
[3]1352 }
1353 else if(type==DEF_DWORD){
[76]1354 ChangeTypeToLong( resultType.GetBasicType() );
[3]1355
1356 //pop ebx
[225]1357 compiler.codeGenerator.op_pop(REG_EBX);
[3]1358
1359 //pop eax
[225]1360 compiler.codeGenerator.op_pop(REG_EAX);
[3]1361
1362 //mov dword ptr[eax],ebx
[225]1363 compiler.codeGenerator.op_mov_MR( sizeof(long), REG_EBX, REG_EAX, 0, MOD_BASE );
[3]1364 }
1365 else if(type==DEF_WORD){
[76]1366 ChangeTypeToLong( resultType.GetBasicType() );
[3]1367
1368 //pop ebx
[225]1369 compiler.codeGenerator.op_pop(REG_EBX);
[3]1370
1371 //pop eax
[225]1372 compiler.codeGenerator.op_pop(REG_EAX);
[3]1373
1374 //mov word ptr[eax],bx
[236]1375 compiler.codeGenerator.op_mov_MR( sizeof(short), REG_EBX, REG_EAX, 0, MOD_BASE );
[3]1376 }
1377 else if(type==DEF_BYTE){
[76]1378 ChangeTypeToLong( resultType.GetBasicType() );
[3]1379
1380 //pop ebx
[225]1381 compiler.codeGenerator.op_pop(REG_EBX);
[3]1382
1383 //pop eax
[225]1384 compiler.codeGenerator.op_pop(REG_EAX);
[3]1385
1386 //mov byte ptr[eax],bl
[236]1387 compiler.codeGenerator.op_mov_MR( sizeof(char), REG_EBX, REG_EAX, 0, MOD_BASE );
[3]1388 }
1389}
Note: See TracBrowser for help on using the repository browser.