Ignore:
Timestamp:
Jul 21, 2007, 11:47:40 PM (17 years ago)
Author:
dai_9181
Message:

CodeGeneratorクラスのベースを実装

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/abdev/BasicCompiler32/op32_main.cpp

    r206 r225  
    1010    return 0;
    1111}
    12 
    13 
    14 
    15 /////////////////////////////////////////////////
    16 // ModR/Mバイト、SIBバイト、ディスプレースメント
    17 /////////////////////////////////////////////////
    18 
    19 //スケール
    20 #define SCALE_NON   (char)0x00
    21 #define SCALE_2     (char)0x40
    22 #define SCALE_4     (char)0x80
    23 #define SCALE_8     (char)0xC0
    24 
    25 //インデックスなし
    26 #define INDEX_NON   0x04
    27 
    28 void set_mod_rm_sib_disp(char mod,int reg,int scale,int index_reg,int base_reg,int disp){
    29     if(mod==MOD_DISP32){
    30         //ModR/Mバイト
    31         OpBuffer[obp++]=(char)(      REGISTER_OPERAND(reg)<<3 | REGISTER_OPERAND(0x04));
    32 
    33         base_reg=0x05;
    34         index_reg=INDEX_NON;
    35     }
    36     else{
    37         //ModR/Mバイト
    38         OpBuffer[obp++]=(char)(mod | REGISTER_OPERAND(reg)<<3 | REGISTER_OPERAND(base_reg));
    39     }
    40 
    41 
    42     //レジスタモードの場合は、ここで終了
    43     if(mod==MOD_REG) return;
    44 
    45 
    46     if(REGISTER_OPERAND(base_reg)==0x04||mod==MOD_DISP32){
    47         //////////////////////
    48         // SIBバイトを使う
    49         //////////////////////
    50 
    51         OpBuffer[obp++]=(char)(scale| REGISTER_OPERAND(index_reg)<<3 | REGISTER_OPERAND(base_reg));
    52     }
    53 
    54     //ディスプレースメントを必要としない場合は、ここで終了
    55     if(mod==MOD_BASE) return;
    56 
    57 
    58     //////////////////////////
    59     // ディスプレースメント
    60     //////////////////////////
    61 
    62     if(mod==MOD_BASE_DISP8) OpBuffer[obp++]=(char)disp;
    63     else{
    64         *((long *)(OpBuffer+obp))=disp;
    65         obp+=sizeof(long);
    66     }
    67 }
    68 
    69 
    70 
    71 void __op_format(char op_prefix,char opcode,int reg){
    72     //命令プリフィックス
    73     if(op_prefix) OpBuffer[obp++]=op_prefix;
    74 
    75     //オペコード、レジスタ
    76     OpBuffer[obp++]=(char)(opcode|REGISTER_OPERAND(reg));
    77 }
    78 void __op_format(char op_prefix,char opcode1,char opcode2,int reg,int base_reg,int offset,char mod){
    79     //命令プリフィックス
    80     if(op_prefix) OpBuffer[obp++]=op_prefix;
    81 
    82     //オペコード
    83     OpBuffer[obp++]=opcode1;
    84     if(opcode2) OpBuffer[obp++]=opcode2;
    85 
    86     //ModR/M, SIB, disp
    87     set_mod_rm_sib_disp(mod,reg,SCALE_NON,INDEX_NON,base_reg,offset);
    88 }
    89 
    90 
    91 
    92 ///////////////////
    93 // mov関連
    94 ///////////////////
    95 
    96 void op_mov_RV(int reg,int offset){
    97     //mov reg,value
    98 
    99     //オペコード、レジスタ
    100     OpBuffer[obp++]=(char)(0xB8|REGISTER_OPERAND(reg));
    101 
    102     //DISP32
    103     *((long *)(OpBuffer+obp))=offset;
    104     obp+=sizeof(long);
    105 }
    106 void op_mov_RV(int op_size,int reg,int offset){
    107     if(op_size==PTR_SIZE) op_mov_RV(reg,offset);
    108     else SetError(300,NULL,cp);
    109 }
    110 void op_mov_RR(int reg1,int reg2){
    111     //mov reg1,reg2
    112 
    113     if(reg1==reg2) return;
    114 
    115     //1000 1011 11xx xbbb
    116     OpBuffer[obp++]=(char)0x8B;
    117     OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg1)<<3 | REGISTER_OPERAND(reg2));
    118 }
    119 void op_mov_RM(int op_size,int reg,int base_reg,int offset,char mod){
    120     //mov reg32,dword ptr[base_reg+offset]
    121     //mov reg16,word ptr[base_reg+offset]
    122     //mov reg8,byte ptr[base_reg+offset]
    123 
    124     //16ビット演算の命令プリフィックス
    125     char op_prefix=0;
    126     if(op_size==sizeof(short)) op_prefix=(char)0x66;
    127 
    128     //オペコード
    129     char opcode;
    130     if(op_size==sizeof(char)) opcode=(char)0x8A;
    131     else opcode=(char)0x8B;
    132 
    133     __op_format(op_prefix,opcode,0,reg,base_reg,offset,mod);
    134 }
    135 void op_mov_RM_ex(int op_size,int reg,int base_reg1,int base_reg2,int offset,BOOL bUseOffset){
    136     //mov reg32,dword ptr[base_reg1+base_reg2+offset]
    137     //mov reg16,word ptr[base_reg1+base_reg2+offset]
    138     //mov reg8,byte ptr[base_reg1+base_reg2+offset]
    139 
    140     if(base_reg1==REG_ESP){
    141         //SIBバイトのindex部にespは指定できない
    142         base_reg1=base_reg2;
    143         base_reg2=REG_ESP;
    144     }
    145 
    146     //16ビット演算のプリフィックス
    147     if(op_size==sizeof(short)) OpBuffer[obp++]=(char)0x66;
    148 
    149     //オペコード
    150     if(op_size==sizeof(char)) OpBuffer[obp++]=(char)0x8A;
    151     else OpBuffer[obp++]=(char)0x8B;
    152 
    153     if(bUseOffset){
    154         ///////////////////////////
    155         // オフセット値を使う
    156         ///////////////////////////
    157 
    158         //レジスタ
    159         OpBuffer[obp++]=(char)(0x84| REGISTER_OPERAND(reg)<<3);
    160 
    161         //ベースレジスタ
    162         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    163 
    164         //オフセット値
    165         *((long *)(OpBuffer+obp))=offset;
    166         obp+=sizeof(long);
    167     }
    168     else{
    169         ///////////////////////////
    170         // オフセット値を使わない
    171         ///////////////////////////
    172 
    173         //レジスタ
    174         OpBuffer[obp++]=(char)(0x04| REGISTER_OPERAND(reg)<<3);
    175 
    176         //ベースレジスタ
    177         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    178     }
    179 }
    180 void op_mov_MR(int op_size,int reg,int base_reg,int offset,char mod){
    181     //mov dword ptr[base_reg+offset],reg32
    182     //mov word ptr[base_reg+offset],reg16
    183     //mov byte ptr[base_reg+offset],reg8
    184 
    185     //16ビット演算の命令プリフィックス
    186     char op_prefix=0;
    187     if(op_size==sizeof(short)) op_prefix=(char)0x66;
    188 
    189     //オペコード
    190     char opcode;
    191     if(op_size==sizeof(char)) opcode=(char)0x88;
    192     else opcode=(char)0x89;
    193 
    194     __op_format(op_prefix,opcode,0,reg,base_reg,offset,mod);
    195 }
    196 void op_mov_MR_ex(int op_size,int reg,int base_reg1,int base_reg2,int offset,BOOL bUseOffset){
    197     //mov dword ptr[base_reg1+base_reg2+offset],reg32
    198     //mov word ptr[base_reg1+base_reg2+offset],reg16
    199     //mov byte ptr[base_reg1+base_reg2+offset],reg8
    200 
    201     if(base_reg1==REG_ESP){
    202         //SIBバイトのindex部にrspは指定できない
    203         base_reg1=base_reg2;
    204         base_reg2=REG_ESP;
    205     }
    206 
    207     //16ビット演算のプリフィックス
    208     if(op_size==sizeof(short)) OpBuffer[obp++]=(char)0x66;
    209 
    210     //オペコード
    211     if(op_size==sizeof(char)) OpBuffer[obp++]=(char)0x88;
    212     else OpBuffer[obp++]=(char)0x89;
    213 
    214     if(bUseOffset==USE_OFFSET){
    215         //////////////////////////
    216         //オフセット値を使う
    217         //////////////////////////
    218 
    219         //レジスタ
    220         OpBuffer[obp++]=(char)(0x84| REGISTER_OPERAND(reg)<<3);
    221 
    222         //ベースレジスタ
    223         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    224 
    225         //オフセット値
    226         *((long *)(OpBuffer+obp))=offset;
    227         obp+=sizeof(long);
    228     }
    229     else{
    230         //////////////////////////
    231         //オフセット値を使わない
    232         //////////////////////////
    233 
    234         //レジスタ
    235         OpBuffer[obp++]=(char)(0x04| REGISTER_OPERAND(reg)<<3);
    236 
    237         //ベースレジスタ
    238         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    239     }
    240 }
    241 
    242 
    243 
    244 
    245 ////////////////////////////////
    246 // movsx関連
    247 ////////////////////////////////
    248 
    249 void op_movsx_R32R16(int reg32,int reg16){
    250     //movsx reg32,reg16
    251 
    252     //16ビット演算の命令プリフィックス
    253     char op_prefix=0;
    254 
    255     //オペコード
    256     char opcode=(char)0x0F;
    257     char opcode2=(char)0xBF;
    258 
    259     __op_format(op_prefix,opcode,opcode2,reg32,reg16,0,MOD_REG);
    260 }
    261 void op_movsx_R32R8(int reg32,int reg8){
    262     //movsx reg32,reg8
    263 
    264     //16ビット演算の命令プリフィックス
    265     char op_prefix=0;
    266 
    267     //オペコード
    268     char opcode=(char)0x0F;
    269     char opcode2=(char)0xBE;
    270 
    271     __op_format(op_prefix,opcode,opcode2,reg32,reg8,0,MOD_REG);
    272 }
    273 void op_movsx_R16R8(int reg16,int reg8){
    274     //movsx reg16,reg8
    275 
    276     //16ビット演算の命令プリフィックス
    277     char op_prefix=(char)0x66;
    278 
    279     //オペコード
    280     char opcode=(char)0x0F;
    281     char opcode2=(char)0xBE;
    282 
    283     __op_format(op_prefix,opcode,opcode2,reg16,reg8,0,MOD_REG);
    284 }
    285 
    286 
    287 
    288 //////////////////////////////////
    289 // インクリメント・デクリメント
    290 //////////////////////////////////
    291 
    292 void op_inc(int reg){
    293     //inc reg
    294 
    295     //16ビット演算の命令プリフィックス
    296     char op_prefix=0;
    297 
    298     //オペコード
    299     char opcode=(char)0xFF;
    300 
    301     __op_format(op_prefix,opcode,0,0,reg,0,MOD_REG);
    302 }
    303 void op_dec(int reg){
    304     op_inc(reg);
    305     OpBuffer[obp-1]=OpBuffer[obp-1]|0x08;
    306 }
    307 
    308 
    309 
    310 /////////////////////
    311 // add関連
    312 /////////////////////
    313 
    314 void op_add_RV8(int reg,char cValue){
    315     //add reg,value8
    316 
    317     OpBuffer[obp++]=(char)0x83;
    318     OpBuffer[obp++]=(char)(0xC0|REGISTER_OPERAND(reg));
    319     OpBuffer[obp++]=cValue;
    320 }
    321 void op_add_RM(int op_size,int reg,int base_reg,int offset,char mod){
    322     //add reg32,dword ptr[base_reg+offset]
    323     //add reg16,word ptr[base_reg+offset]
    324     //add reg8,byte ptr[base_reg+offset]
    325 
    326     //16ビット演算の命令プリフィックス
    327     char op_prefix=0;
    328     if(op_size==sizeof(short)) op_prefix=(char)0x66;
    329 
    330     //オペコード
    331     char opcode;
    332     if(op_size==sizeof(char)) opcode=(char)0x02;
    333     else opcode=(char)0x03;
    334 
    335     __op_format(op_prefix,opcode,0,reg,base_reg,offset,mod);
    336 }
    337 void op_adc_RV8(int reg,char cValue){
    338     //adc reg,value8
    339 
    340     OpBuffer[obp++]=(char)0x83;
    341     OpBuffer[obp++]=(char)(0xD0|REGISTER_OPERAND(reg));
    342     OpBuffer[obp++]=cValue;
    343 }
    344 
    345 
    346 /////////////////////
    347 // sub関連
    348 /////////////////////
    349 
    350 void op_sub_RV8(int reg,char cValue){
    351     //sub reg,value8
    352 
    353     OpBuffer[obp++]=(char)0x83;
    354     OpBuffer[obp++]=(char)(0xE8|REGISTER_OPERAND(reg));
    355     OpBuffer[obp++]=cValue;
    356 }
    357 void op_sbb_RV8(int reg,char cValue){
    358     //sbb reg,value8
    359 
    360     OpBuffer[obp++]=(char)0x83;
    361     OpBuffer[obp++]=(char)(0xD8|REGISTER_OPERAND(reg));
    362     OpBuffer[obp++]=cValue;
    363 }
    364 void op_sbb_RR( int reg1, int reg2 ){
    365     //sbb reg1,reg2
    366 
    367     //オペコード
    368     OpBuffer[obp++]=(char)0x1B;
    369 
    370     //レジスタ
    371     OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg1)<<3 | REGISTER_OPERAND(reg2));
    372 }
    373 
    374 
    375 
    376 ////////////////////////
    377 // imul関連
    378 ////////////////////////
    379 
    380 void op_imul_RR(int reg1,int reg2){
    381     //imul reg1,reg2
    382 
    383     //オペコード
    384     OpBuffer[obp++]=(char)0x0F;
    385     OpBuffer[obp++]=(char)0xAF;
    386 
    387     //レジスタ
    388     OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg1)<<3 | REGISTER_OPERAND(reg2));
    389 }
    390 
    391 void op_imul_RV(int reg,int i32data){
    392     //imul reg,i32data
    393 
    394     if(-128<=i32data&&i32data<=127){
    395         //オペコード
    396         OpBuffer[obp++]=(char)0x6B;
    397 
    398         //レジスタ
    399         OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg)<<3 | REGISTER_OPERAND(reg));
    400 
    401         //値
    402         OpBuffer[obp++]=(char)i32data;
    403     }
    404     else{
    405         //オペコード
    406         OpBuffer[obp++]=(char)0x69;
    407 
    408         //レジスタ
    409         OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg)<<3 | REGISTER_OPERAND(reg));
    410 
    411         //値
    412         *((long *)(OpBuffer+obp))=i32data;
    413         obp+=sizeof(long);
    414     }
    415 }
    416 
    417 
    418 
    419 //////////////////////
    420 // and関連
    421 //////////////////////
    422 
    423 void op_and_RV(int reg,int value){
    424     //and reg,value
    425 
    426     if(reg==REG_RAX){
    427         //eaxのみ特殊
    428 
    429         // [8bit rex] 0010 0101 [32bit offset]
    430         OpBuffer[obp++]=(char)0x25;
    431         *((long *)(OpBuffer+obp))=value;
    432         obp+=sizeof(long);
    433     }
    434     else{
    435         //16ビット演算の命令プリフィックス
    436         char op_prefix=0;
    437 
    438         //オペコード
    439         char opcode=(char)0x81;
    440 
    441         __op_format(op_prefix,opcode,0,0,reg,value,MOD_REG);
    442     }
    443 }
    444 
    445 void op_or_RR( int op_size, int reg1, int reg2 ){
    446     //16ビット演算のプリフィックス
    447     if(op_size==sizeof(short)) OpBuffer[obp++]=(char)0x66;
    448 
    449     //オペコード
    450     if(op_size==sizeof(char)) OpBuffer[obp++]=(char)0x0A;
    451     else OpBuffer[obp++]=(char)0x0B;
    452 
    453     //レジスタ
    454     OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg1)<<3 | REGISTER_OPERAND(reg2));
    455 }
    456 
    457 
    458 
    459 void op_neg( int reg ){
    460     //neg reg
    461 
    462     //オペコード
    463     OpBuffer[obp++]=(char)0xF7;
    464 
    465     //レジスタ
    466     OpBuffer[obp++]=(char)(0xD8| REGISTER_OPERAND(reg));
    467 }
    468 
    469 
    470 
    471 ///////////////////////
    472 // 64ビット関連
    473 ///////////////////////
    474 
    475 void op_cdq(){
    476     //cdq
    477     OpBuffer[obp++]=(char)0x99;
    478 }
    479 
    480 
    481 
    482 /////////////////////
    483 // ストリング関係
    484 /////////////////////
    485 
    486 void op_rep_movs(int op_size){
    487     if(op_size==sizeof(BYTE)){
    488         //rep movs byte ptr[edi],byte ptr[esi]
    489         OpBuffer[obp++]=(char)0xF3;
    490         OpBuffer[obp++]=(char)0xA4;
    491     }
    492     else if(op_size==sizeof(short)){
    493         //rep movs word ptr[edi],word ptr[esi]
    494         OpBuffer[obp++]=(char)0xF3;
    495         OpBuffer[obp++]=(char)0x66;
    496         OpBuffer[obp++]=(char)0xA5;
    497     }
    498     else if(op_size==sizeof(long)){
    499         //rep movs dword ptr[edi],dword ptr[esi]
    500         OpBuffer[obp++]=(char)0xF3;
    501         OpBuffer[obp++]=(char)0xA5;
    502     }
    503 }
    504 
    505 
    506 
    507 
    508 //////////////////////////
    509 // スタック関連
    510 //////////////////////////
    511 
    512 void op_push(int reg){
    513     //push reg
    514 
    515     if( reg == REG_NON ){
    516         op_sub_esp( PTR_SIZE );
    517         return;
    518     }
    519 
    520     //オペコード、レジスタ
    521     __op_format(0,(char)0x50,reg);
    522 }
    523 void op_push_V(long data){
    524     //スタックにリテラル値をプッシュ
    525     if(-128<=data&&data<=127){
    526         //push 8ビット値
    527         OpBuffer[obp++]=(char)0x6A;
    528         OpBuffer[obp++]=(char)data;
    529     }
    530     else{
    531         //push 32ビット値
    532         OpBuffer[obp++]=(char)0x68;
    533         *((long *)(OpBuffer+obp))=data;
    534         obp+=sizeof(long);
    535     }
    536 }
    537 void op_pop(int reg){
    538     //pop reg
    539 
    540     if( reg == REG_NON ){
    541         op_add_esp( PTR_SIZE );
    542         return;
    543     }
    544 
    545     //オペコード、レジスタ
    546     __op_format(0,(char)0x58,reg);
    547 }
    548 void op_add_esp(int num){
    549     //スタックポインタの加算(pop方向)
    550 
    551     //add esp,num
    552     if(0xFFFFFF80&num){
    553         OpBuffer[obp++]=(char)0x81;
    554         OpBuffer[obp++]=(char)0xC4;
    555         *((long *)(OpBuffer+obp))=num;
    556         obp+=sizeof(long);
    557     }
    558     else{
    559         //「128 > num > -127」の場合
    560         OpBuffer[obp++]=(char)0x83;
    561         OpBuffer[obp++]=(char)0xC4;
    562         OpBuffer[obp++]=(char)num;
    563     }
    564 }
    565 void op_sub_esp(int num){
    566     //スタックポインタの減算(push方向)
    567 
    568     //sub esp,num
    569     if(0xFFFFFF80&num){
    570         OpBuffer[obp++]=(char)0x81;
    571         OpBuffer[obp++]=(char)0xEC;
    572         *((long *)(OpBuffer+obp))=num;
    573         obp+=sizeof(long);
    574     }
    575     else{
    576         //「128 > num > -127」の場合
    577         OpBuffer[obp++]=(char)0x83;
    578         OpBuffer[obp++]=(char)0xEC;
    579         OpBuffer[obp++]=(char)num;
    580     }
    581 }
    582 
    583 
    584 
    585 /////////////////////
    586 // cmp関連
    587 /////////////////////
    588 void op_cmp_RR( int reg1, int reg2 ){
    589     //オペコード
    590     OpBuffer[obp++]=(char)0x3B;
    591 
    592     //レジスタ
    593     OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg1)<<3 | REGISTER_OPERAND(reg2));
    594 }
    595 void op_cmp_value(int op_size,int reg,char byte_data){
    596     //cmp reg,byte_data
    597 
    598     if(op_size==sizeof(char)&&reg==REG_EAX){
    599         //alレジスタの場合は特殊
    600         OpBuffer[obp++]=(char)0x3C;
    601 
    602         //8ビット値
    603         OpBuffer[obp++]=byte_data;
    604 
    605         return;
    606     }
    607 
    608     //16ビット演算のプリフィックス
    609     if(op_size==sizeof(short)) OpBuffer[obp++]=(char)0x66;
    610 
    611     //オペコード
    612     if(op_size==sizeof(char)) OpBuffer[obp++]=(char)0x80;
    613     else OpBuffer[obp++]=(char)0x83;
    614 
    615     //レジスタ
    616     OpBuffer[obp++]=(char)(0xF8| REGISTER_OPERAND(reg));
    617 
    618     //8ビット値
    619     OpBuffer[obp++]=byte_data;
    620 }
    621 void op_setne( int reg ){
    622     //オペコード
    623     OpBuffer[obp++]=(char)0x0F;
    624     OpBuffer[obp++]=(char)0x95;
    625 
    626     //レジスタ
    627     OpBuffer[obp++]=(char)( 0xC0 | REGISTER_OPERAND(reg) );
    628 }
    629 
    630 
    631 
    632 ////////////////////
    633 // test関連
    634 ////////////////////
    635 
    636 void op_test(int reg1,int reg2){
    637     //test reg1,reg2
    638 
    639     //1000 0101 11rr rbbb
    640     OpBuffer[obp++]=(char)0x85;
    641     OpBuffer[obp++]=(char)(0xC0| REGISTER_OPERAND(reg1)<<3 | REGISTER_OPERAND(reg2));
    642 }
    643 
    644 
    645 
    646 //////////////////////////////
    647 // 浮動小数点関連
    648 //////////////////////////////
    649 
    650 void op_fld_ptr_esp(int type){
    651     //スタックポインタが示すバッファのデータを浮動小数点レジスタへロード
    652 
    653     if(type==DEF_DOUBLE){
    654         //fld qword ptr[esp]
    655         OpBuffer[obp++]=(char)0xDD;
    656         OpBuffer[obp++]=(char)0x04;
    657         OpBuffer[obp++]=(char)0x24;
    658     }
    659     else if(type==DEF_SINGLE){
    660         //fld dword ptr[esp]
    661         OpBuffer[obp++]=(char)0xD9;
    662         OpBuffer[obp++]=(char)0x04;
    663         OpBuffer[obp++]=(char)0x24;
    664     }
    665     else if(type==DEF_INT64){
    666         //fild qword ptr[esp]
    667         OpBuffer[obp++]=(char)0xDF;
    668         OpBuffer[obp++]=(char)0x2C;
    669         OpBuffer[obp++]=(char)0x24;
    670     }
    671     else if(type==DEF_LONG){
    672         //fild dword ptr[esp]
    673         OpBuffer[obp++]=(char)0xDB;
    674         OpBuffer[obp++]=(char)0x04;
    675         OpBuffer[obp++]=(char)0x24;
    676     }
    677 }
    678 void op_fld_basereg(int type,int base_reg){
    679     //fld ptr[reg]
    680 
    681     //オペコード
    682     if(type==DEF_DOUBLE)        OpBuffer[obp++]=(char)0xDD;
    683     else if(type==DEF_SINGLE)   OpBuffer[obp++]=(char)0xD9;
    684     else SetError(300,NULL,cp);
    685 
    686     if(base_reg==REG_ESP){
    687         OpBuffer[obp++]=(char)0x04;
    688         OpBuffer[obp++]=(char)0x24;
    689     }
    690     else if(base_reg==REG_EBP){
    691         OpBuffer[obp++]=(char)0x45;
    692         OpBuffer[obp++]=(char)0x00;
    693     }
    694     else{
    695         OpBuffer[obp++]=(char)REGISTER_OPERAND(base_reg);
    696     }
    697 }
    698 void op_fld_base_offset(int type,int base_reg,int offset){
    699     //fld ptr[reg+offset]
    700 
    701     //オペコード
    702     if(type==DEF_DOUBLE)        OpBuffer[obp++]=(char)0xDD;
    703     else if(type==DEF_SINGLE)   OpBuffer[obp++]=(char)0xD9;
    704     else SetError(300,NULL,cp);
    705 
    706     //オペコード、レジスタ
    707     if(base_reg==REG_ESP){
    708         OpBuffer[obp++]=(char)0x84;
    709         OpBuffer[obp++]=(char)0x24;
    710     }
    711     else{
    712         OpBuffer[obp++]=(char)(0x80|REGISTER_OPERAND(base_reg));
    713     }
    714 
    715     //オフセット値
    716     *((long *)(OpBuffer+obp))=offset;
    717     obp+=sizeof(long);
    718 }
    719 void op_fld_base_offset_ex(int type,int base_reg1,int base_reg2,int offset,BOOL bUseOffset){
    720     //fld ptr[base_reg1+base_reg2+offset]
    721 
    722     if(base_reg1==REG_ESP){
    723         //SIBバイトのindex部にespは指定できない
    724         base_reg1=base_reg2;
    725         base_reg2=REG_ESP;
    726     }
    727 
    728     //オペコード
    729     if(type==DEF_DOUBLE)        OpBuffer[obp++]=(char)0xDD;
    730     else if(type==DEF_SINGLE)   OpBuffer[obp++]=(char)0xD9;
    731     else SetError(300,NULL,cp);
    732 
    733     int reg=0;
    734     if(bUseOffset){
    735         ///////////////////////////
    736         // オフセット値を使う
    737         ///////////////////////////
    738 
    739         //レジスタ
    740         OpBuffer[obp++]=(char)(0x84| REGISTER_OPERAND(reg)<<3);
    741 
    742         //ベースレジスタ
    743         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    744 
    745         //オフセット値
    746         *((long *)(OpBuffer+obp))=offset;
    747         obp+=sizeof(long);
    748     }
    749     else{
    750         ///////////////////////////
    751         // オフセット値を使わない
    752         ///////////////////////////
    753 
    754         //レジスタ
    755         OpBuffer[obp++]=(char)(0x04| REGISTER_OPERAND(reg)<<3);
    756 
    757         //ベースレジスタ
    758         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    759     }
    760 }
    761 void op_fstp_basereg(int type,int base_reg){
    762     //fstp ptr[reg]
    763 
    764     //オペコード
    765     if(type==DEF_DOUBLE)        OpBuffer[obp++]=(char)0xDD;
    766     else if(type==DEF_SINGLE)   OpBuffer[obp++]=(char)0xD9;
    767     else SetError(300,NULL,cp);
    768 
    769     if(base_reg==REG_ESP){
    770         OpBuffer[obp++]=(char)0x1C;
    771         OpBuffer[obp++]=(char)0x24;
    772     }
    773     else if(base_reg==REG_EBP){
    774         OpBuffer[obp++]=(char)0x5D;
    775         OpBuffer[obp++]=(char)0x00;
    776     }
    777     else{
    778         OpBuffer[obp++]=(char)(0x18|REGISTER_OPERAND(base_reg));
    779     }
    780 }
    781 void op_fstp_base_offset(int type,int base_reg,int offset){
    782     //fstp ptr[reg+offset]
    783 
    784     //オペコード
    785     if(type==DEF_DOUBLE)        OpBuffer[obp++]=(char)0xDD;
    786     else if(type==DEF_SINGLE)   OpBuffer[obp++]=(char)0xD9;
    787     else SetError(300,NULL,cp);
    788 
    789     //オペコード、レジスタ
    790     if(base_reg==REG_ESP){
    791         OpBuffer[obp++]=(char)0x9C;
    792         OpBuffer[obp++]=(char)0x24;
    793     }
    794     else{
    795         OpBuffer[obp++]=(char)(0x98|REGISTER_OPERAND(base_reg));
    796     }
    797 
    798     //オフセット値
    799     *((long *)(OpBuffer+obp))=offset;
    800     obp+=sizeof(long);
    801 }
    802 void op_fstp_base_offset_ex(int type,int base_reg1,int base_reg2,int offset,BOOL bUseOffset){
    803     //fstp ptr[base_reg1+base_reg2+offset]
    804 
    805     if(base_reg1==REG_ESP){
    806         //SIBバイトのindex部にespは指定できない
    807         base_reg1=base_reg2;
    808         base_reg2=REG_ESP;
    809     }
    810 
    811     //オペコード
    812     if(type==DEF_DOUBLE)        OpBuffer[obp++]=(char)0xDD;
    813     else if(type==DEF_SINGLE)   OpBuffer[obp++]=(char)0xD9;
    814     else SetError(300,NULL,cp);
    815 
    816     int reg=0;
    817     if(bUseOffset){
    818         ///////////////////////////
    819         // オフセット値を使う
    820         ///////////////////////////
    821 
    822         //レジスタ
    823         OpBuffer[obp++]=(char)(0x9C| REGISTER_OPERAND(reg)<<3);
    824 
    825         //ベースレジスタ
    826         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    827 
    828         //オフセット値
    829         *((long *)(OpBuffer+obp))=offset;
    830         obp+=sizeof(long);
    831     }
    832     else{
    833         ///////////////////////////
    834         // オフセット値を使わない
    835         ///////////////////////////
    836 
    837         //レジスタ
    838         OpBuffer[obp++]=(char)(0x1C| REGISTER_OPERAND(reg)<<3);
    839 
    840         //ベースレジスタ
    841         OpBuffer[obp++]=(char)(REGISTER_OPERAND(base_reg1)<<3 | REGISTER_OPERAND(base_reg2));
    842     }
    843 }
    844 void op_fistp_ptr_esp( int typeSize ){
    845     if( typeSize == sizeof(_int64) ){
    846         //64bit
    847 
    848         //fistp qword ptr[esp]
    849         fpu_cast();
    850         OpBuffer[obp++]=(char)0xDF;
    851         OpBuffer[obp++]=(char)0x3C;
    852         OpBuffer[obp++]=(char)0x24;
    853         fpu_cast_end();
    854     }
    855     else if( typeSize == sizeof(long) ){
    856         //32bit
    857 
    858         //fistp dword ptr[esp]
    859         fpu_cast();
    860         OpBuffer[obp++]=(char)0xDB;
    861         OpBuffer[obp++]=(char)0x1C;
    862         OpBuffer[obp++]=(char)0x24;
    863         fpu_cast_end();
    864     }
    865     else{
    866         SetError();
    867     }
    868 }
    869 void op_fstp_push( Type &type ){
    870     //sub esp,size
    871     op_sub_esp( type.GetBasicSize() );
    872 
    873     op_fstp_basereg( type.GetBasicType(), REG_ESP );
    874 }
    875 
    876 
    877 
    878 //////////////////////////////
    879 // レジスタ関連
    880 //////////////////////////////
    881 
    882 void op_zero_reg(int reg){
    883     //レジスタに0をセット
    884 
    885     switch(reg){
    886         case REG_EAX:
    887             //xor eax,eax
    888             OpBuffer[obp++]=(char)0x33;
    889             OpBuffer[obp++]=(char)0xC0;
    890             break;
    891         case REG_EBX:
    892             //xor ebx,ebx
    893             OpBuffer[obp++]=(char)0x33;
    894             OpBuffer[obp++]=(char)0xDB;
    895             break;
    896         case REG_ECX:
    897             //xor ecx,ecx
    898             OpBuffer[obp++]=(char)0x33;
    899             OpBuffer[obp++]=(char)0xC9;
    900             break;
    901         case REG_EDX:
    902             //xor edx,edx
    903             OpBuffer[obp++]=(char)0x33;
    904             OpBuffer[obp++]=(char)0xD2;
    905             break;
    906         case REG_EBP:
    907             //xor ebp,ebp
    908             OpBuffer[obp++]=(char)0x33;
    909             OpBuffer[obp++]=(char)0xED;
    910             break;
    911     }
    912 }
    913 
    914 void fpu_cast(){
    915     ///////////////////////
    916     // FPUの切り捨て設定
    917     ///////////////////////
    918 
    919     //sub esp,16
    920     op_sub_esp(16);
    921 
    922     //mov dword ptr[esp+4],eax
    923     OpBuffer[obp++]=(char)0x89;
    924     OpBuffer[obp++]=(char)0x44;
    925     OpBuffer[obp++]=(char)0x24;
    926     OpBuffer[obp++]=(char)0x04;
    927 
    928     //fnstcw word ptr[esp]
    929     OpBuffer[obp++]=(char)0xD9;
    930     OpBuffer[obp++]=(char)0x3C;
    931     OpBuffer[obp++]=(char)0x24;
    932 
    933     //mov ax,word ptr[esp]
    934     OpBuffer[obp++]=(char)0x66;
    935     OpBuffer[obp++]=(char)0x8B;
    936     OpBuffer[obp++]=(char)0x04;
    937     OpBuffer[obp++]=(char)0x24;
    938 
    939     //or ah,0Ch
    940     OpBuffer[obp++]=(char)0x80;
    941     OpBuffer[obp++]=(char)0xCC;
    942     OpBuffer[obp++]=(char)0x0C;
    943 
    944     //mov word ptr[esp+2],ax
    945     OpBuffer[obp++]=(char)0x66;
    946     OpBuffer[obp++]=(char)0x89;
    947     OpBuffer[obp++]=(char)0x44;
    948     OpBuffer[obp++]=(char)0x24;
    949     OpBuffer[obp++]=(char)0x02;
    950 
    951     //fldcw word ptr[esp+2]
    952     OpBuffer[obp++]=(char)0xD9;
    953     OpBuffer[obp++]=(char)0x6C;
    954     OpBuffer[obp++]=(char)0x24;
    955     OpBuffer[obp++]=(char)0x02;
    956 
    957     //mov eax,dword ptr[esp+4]
    958     OpBuffer[obp++]=(char)0x8B;
    959     OpBuffer[obp++]=(char)0x44;
    960     OpBuffer[obp++]=(char)0x24;
    961     OpBuffer[obp++]=(char)0x04;
    962 
    963     //add esp,16
    964     op_add_esp(16);
    965 }
    966 void fpu_cast_end(){
    967     //sub esp,16
    968     op_sub_esp(16);
    969 
    970     //fldcw word ptr[esp]
    971     OpBuffer[obp++]=(char)0xD9;
    972     OpBuffer[obp++]=(char)0x2C;
    973     OpBuffer[obp++]=(char)0x24;
    974 
    975     //add esp,16
    976     op_add_esp(16);
    977 }
    978 
    979 
    980 /////////////////////////////
    981 // 関数呼び出し
    982 /////////////////////////////
    983 
    984 void op_call(const UserProc *pUserProc){
    985     OpBuffer[obp++]=(char)0xE8;
    986     pobj_SubAddrSchedule->add(pUserProc,1);
    987     pUserProc->Using();
    988     obp+=sizeof(long);
    989 }
    990 void op_ret(){
    991     OpBuffer[obp++]=(char)0xC3;
    992 }
Note: See TracChangeset for help on using the changeset viewer.