#define FBO1_NOT_CONST 0 #define FBO1_INT 1 #define FBO1_DOUBLE 2 BoolU8 FixupBinaryOp1(IntermediateCode *tempi, IntermediateCode *tempi1,IntermediateCode *tempi2, BoolU4 *is_unsigned) { ClassStruct *tempc=tempi->ic_class,*tempc1,*tempc2; tempc1=tempi1->ic_class; while (tempc1->return_class) tempc1=tempc1->return_class; tempc2=tempi2->ic_class; while (tempc2->return_class) tempc2=tempc2->return_class; if (tempc1->sub_type>tempc2->sub_type) tempi->ic_class=tempc1; else tempi->ic_class=tempc2; tempc=tempi->ic_class; if (tempc->sub_type==IT_DOUBLE) { if (!(tempi->ic_flags&ICF_USE_INT)) { if (tempi1->ic_opcode==EC_IMM) { tempi1->ic_data><(double)=tempi1->ic_data; tempi1->ic_class=sys_internal_types[IT_DOUBLE]; tempi1->ic_opcode=EC_DOUBLE; } else if (tempc1->sub_type!=IT_DOUBLE) tempi1->ic_flags|=ICF_R_TO_DOUBLE; if (tempi2->ic_opcode==EC_IMM) { tempi2->ic_data><(double)=tempi2->ic_data; tempi2->ic_class=sys_internal_types[IT_DOUBLE]; tempi2->ic_opcode=EC_DOUBLE; } else if (tempc2->sub_type!=IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_DOUBLE; } if (tempi1->ic_opcode==EC_DOUBLE && tempi2->ic_opcode==EC_DOUBLE && !(tempi->ic_flags&(ICF_PUSH_CMP|ICF_POP_CMP))) { tempi->ic_flags|=tempi1->ic_flags|tempi2->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; return FBO1_DOUBLE; } else return FBO1_NOT_CONST; } tempi->ic_flags&=~ICF_USE_INT; *is_unsigned=tempc1->sub_type&1 || tempc2->sub_type&1; if (tempi1->ic_opcode==EC_IMM && tempi2->ic_opcode==EC_IMM && !(tempi->ic_flags&(ICF_PUSH_CMP|ICF_POP_CMP))) { tempi->ic_flags|=tempi1->ic_flags|tempi2->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; return FBO1_INT; } else return FBO1_NOT_CONST; } BoolU8 FixupBinaryOp2(IntermediateCode **tempi1,IntermediateCode **tempi2) { IntermediateCode *tempii1=*tempi1, *tempii2=*tempi2; if (tempii1->ic_opcode==EC_IMM && !(tempii1->ic_flags & ICF_R_TO_DOUBLE)) return TRUE; if (tempii2->ic_opcode==EC_IMM && !(tempii2->ic_flags & ICF_R_TO_DOUBLE)) { *tempi1=tempii2; *tempi2=tempii1; return TRUE; } return FALSE; } BoolU8 FixupUnaryOp(IntermediateCode *tempi, IntermediateCode *tempi1, BoolU4 *is_unsigned) { ClassStruct *tempc,*tempc1; tempc1=tempi1->ic_class; while (tempc1->return_class) tempc1=tempc1->return_class; tempi->ic_class=tempc1; tempc=tempi->ic_class; if (tempc->sub_type==IT_DOUBLE) { if (!(tempi->ic_flags&ICF_USE_INT)) { if (tempi1->ic_opcode==EC_IMM) { tempi1->ic_data><(double)=tempi1->ic_data; tempi1->ic_class=sys_internal_types[IT_DOUBLE]; tempi1->ic_opcode=EC_DOUBLE; } else if (tempc1->sub_type!=IT_DOUBLE) tempi1->ic_flags|=ICF_R_TO_DOUBLE; } if (tempi1->ic_opcode==EC_DOUBLE) { tempi->ic_flags|=tempi1->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; return FBO1_DOUBLE; } else return FBO1_NOT_CONST; } tempi->ic_flags&=~ICF_USE_INT; *is_unsigned=tempc1->sub_type&1; if (tempi1->ic_opcode==EC_IMM) { tempi->ic_flags|=tempi1->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; return FBO1_INT; } else return FBO1_NOT_CONST; } I8 CmpOffsetToReg(I8 offset,I8 *register_offsets) { I8 i; for (i=0;icb); ps->ptr=0; for (i=0;i<4;i++) temp_lag[i]=&opt_nop; return ps; } LTextern CP_OPTNEXT BoolU4 OptNext(IntermediateCode *tempi, IntermediateCode **temp_lag); LTextern CP_OPTNEXT2 BoolU4 OptNext2(IntermediateCode *tempi, IntermediateCode **temp_lag); LTextern CP_OPTNEXT3 BoolU4 OptNext3(IntermediateCode *tempi, IntermediateCode **temp_lag); void OptEnd(LexStruct *lx,I8 pass,ParseStack *ps) { if (ps->ptr>2) { PrintF("Pass:%d Stack:%08X\r\n",pass,ps->ptr); PrsExcept(lx,"ST_OPT_INTERNAL_ERROR"); } Free(ps); } IntermediateCode *OptLag(LexStruct *lx,IntermediateCode *tempi) { do { if (tempi==lx->cb.cb_in_ptr) return NULL; else tempi-=sizeof(IntermediateCode); } while (tempi->ic_opcode<=EC_END_EXP); return tempi; } IntermediateCode *OptLag1(LexStruct *lx,IntermediateCode *tempi) { do { if (tempi==lx->cb.cb_in_ptr) return NULL; else tempi-=sizeof(IntermediateCode); } while (tempi->ic_opcode==EC_NOP||tempi->ic_opcode==EC_NOP1); return tempi; } IntermediateCode *OptLead1(LexStruct *lx,IntermediateCode *tempi) { nounusedwarn lx; do { tempi+=sizeof(IntermediateCode); if (tempi->ic_opcode==EC_NULL) return NULL; } while (tempi->ic_opcode==EC_NOP||tempi->ic_opcode==EC_NOP1); return tempi; } extern void OptBrNotZero(LexStruct *lx,IntermediateCode *tempi); IntermediateCode *OptBrZero(LexStruct *lx,IntermediateCode *tempi) { CbMiscStruct *templ_true,*templ_false; IntermediateCode *tempii=OptLag(lx,tempi),*tempii2; switch (tempii->ic_opcode) { case EC_NOT: tempi->ic_opcode=EC_BR_NOT_ZERO; tempi->ic_class=tempii->ic_class; tempi->ic_flags|=tempii->ic_flags; tempi->p1c=tempii->p1c; tempi->p1t=tempii->p1t; tempii->ic_opcode=EC_NOP; tempii->ic_flags=0; return OptBrNotZero(lx,tempi); case EC_EQUAL_EQUAL: tempi->ic_opcode=EC_BR_NOT_EQUAL; break; case EC_NOT_EQUAL: tempi->ic_opcode=EC_BR_EQUAL_EQUAL; break; case EC_LESS: tempi->ic_opcode=EC_BR_GREATER_EQUAL; break; case EC_GREATER: tempi->ic_opcode=EC_BR_LESS_EQUAL; break; case EC_LESS_EQUAL: tempi->ic_opcode=EC_BR_GREATER; break; case EC_GREATER_EQUAL: tempi->ic_opcode=EC_BR_LESS; break; case EC_OR_OR: tempi->ic_opcode=EC_BR_OR_OR_ZERO; break; case EC_AND_AND: tempi->ic_opcode=EC_BR_AND_AND_ZERO; break; case EC_AND: tempi->ic_opcode=EC_BR_AND_ZERO; break; case EC_CALL_END: tempii2=OptLag(lx,tempii); switch (tempii2->ic_opcode) { case EC_BT: tempii2->ic_opcode=EC_BR_NOT_BT; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_BTS: tempii2->ic_opcode=EC_BR_NOT_BTS; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_BTR: tempii2->ic_opcode=EC_BR_NOT_BTR; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_BTC: tempii2->ic_opcode=EC_BR_NOT_BTC; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_LBTS: tempii2->ic_opcode=EC_BR_NOT_LBTS; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_LBTR: tempii2->ic_opcode=EC_BR_NOT_LBTR; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_LBTC: tempii2->ic_opcode=EC_BR_NOT_LBTC; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; } break; } if (tempi->ic_opcode!=EC_BR_ZERO) { tempi->ic_class=tempii->ic_class; tempi->ic_flags|=tempii->ic_flags; tempi->p1c=tempii->p1c; tempi->p2c=tempii->p2c; tempi->p1t=tempii->p1t; tempi->p2t=tempii->p2t; tempii->ic_opcode=EC_NOP; tempii->ic_flags=0; templ_true=tempi->ic_data; if (tempi->ic_opcode==EC_BR_AND_AND_ZERO) { tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempii=tempi->p1t+sizeof(IntermediateCode); tempii->ic_data=templ_true; tempii->p1t=tempi->p1t; tempii->p1c=tempi->p1c; tempii->ic_opcode=EC_BR_ZERO; OptBrZero(lx,tempii); tempii=tempi->p2t+sizeof(IntermediateCode); tempii->p1t=tempi->p2t; tempii->p1c=tempi->p2c; tempii->ic_data=templ_true; tempii->ic_opcode=EC_BR_ZERO; return OptBrZero(lx,tempii); } else if (tempi->ic_opcode==EC_BR_OR_OR_ZERO) { templ_false=CbMiscNew(lx,CBMT_LABEL); tempi->ic_opcode=EC_LABEL; tempi->ic_flags=0; tempi->ic_data=templ_false; tempii=tempi->p1t+sizeof(IntermediateCode); tempii->p1t=tempi->p1t; tempii->p1c=tempi->p1c; tempii->ic_data=templ_false; tempii->ic_opcode=EC_BR_NOT_ZERO; OptBrNotZero(lx,tempii); tempii=tempi->p2t+sizeof(IntermediateCode); tempii->p1t=tempi->p2t; tempii->p1c=tempi->p2c; tempii->ic_data=templ_true; tempii->ic_opcode=EC_BR_ZERO; return OptBrZero(lx,tempii); } } return tempi; } IntermediateCode *OptBrNotZero(LexStruct *lx,IntermediateCode *tempi) { CbMiscStruct *templ_true,*templ_false; IntermediateCode *tempii=OptLag(lx,tempi),*tempii2; switch (tempii->ic_opcode) { case EC_NOT: tempi->ic_opcode=EC_BR_ZERO; tempi->ic_class=tempii->ic_class; tempi->ic_flags|=tempii->ic_flags; tempi->p1c=tempii->p1c; tempi->p1t=tempii->p1t; tempii->ic_opcode=EC_NOP; tempii->ic_flags=0; return OptBrZero(lx,tempi); case EC_EQUAL_EQUAL: tempi->ic_opcode=EC_BR_EQUAL_EQUAL; break; case EC_NOT_EQUAL: tempi->ic_opcode=EC_BR_NOT_EQUAL; break; case EC_LESS: tempi->ic_opcode=EC_BR_LESS; break; case EC_GREATER: tempi->ic_opcode=EC_BR_GREATER; break; case EC_LESS_EQUAL: tempi->ic_opcode=EC_BR_LESS_EQUAL; break; case EC_GREATER_EQUAL: tempi->ic_opcode=EC_BR_GREATER_EQUAL; break; case EC_OR_OR: tempi->ic_opcode=EC_BR_OR_OR_NOT_ZERO; break; case EC_AND_AND: tempi->ic_opcode=EC_BR_AND_AND_NOT_ZERO; break; case EC_AND: tempi->ic_opcode=EC_BR_AND_NOT_ZERO; break; case EC_CALL_END: tempii2=OptLag(lx,tempii); switch (tempii2->ic_opcode) { case EC_BT: tempii2->ic_opcode=EC_BR_BT; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_BTS: tempii2->ic_opcode=EC_BR_BTS; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_BTR: tempii2->ic_opcode=EC_BR_BTR; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_BTC: tempii2->ic_opcode=EC_BR_BTC; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_LBTS: tempii2->ic_opcode=EC_BR_LBTS; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_LBTR: tempii2->ic_opcode=EC_BR_LBTR; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; case EC_LBTC: tempii2->ic_opcode=EC_BR_LBTC; tempii2->ic_data=tempi->ic_data; tempii->ic_opcode=EC_CALL_END2; tempi->ic_opcode=EC_NOP; return tempii; } break; } if (tempi->ic_opcode!=EC_BR_NOT_ZERO) { tempi->ic_class=tempii->ic_class; tempi->ic_flags|=tempii->ic_flags; tempi->p1c=tempii->p1c; tempi->p2c=tempii->p2c; tempi->p1t=tempii->p1t; tempi->p2t=tempii->p2t; tempii->ic_opcode=EC_NOP; tempii->ic_flags=0; templ_true=tempi->ic_data; if (tempi->ic_opcode==EC_BR_OR_OR_NOT_ZERO) { tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempii=tempi->p1t+sizeof(IntermediateCode); tempii->p1t=tempi->p1t; tempii->p1c=tempi->p1c; tempii->ic_data=templ_true; tempii->ic_opcode=EC_BR_NOT_ZERO; OptBrNotZero(lx,tempii); tempii=tempi->p2t+sizeof(IntermediateCode); tempii->p1t=tempi->p2t; tempii->p1c=tempi->p2c; tempii->ic_data=templ_true; tempii->ic_opcode=EC_BR_NOT_ZERO; return OptBrNotZero(lx,tempii); } else if (tempi->ic_opcode==EC_BR_AND_AND_NOT_ZERO) { templ_false=CbMiscNew(lx,CBMT_LABEL); tempi->ic_opcode=EC_LABEL; tempi->ic_flags=0; tempi->ic_data=templ_false; tempii=tempi->p1t+sizeof(IntermediateCode); tempii->p1t=tempi->p1t; tempii->p1c=tempi->p1c; tempii->ic_data=templ_false; tempii->ic_opcode=EC_BR_ZERO; OptBrZero(lx,tempii); tempii=tempi->p2t+sizeof(IntermediateCode); tempii->p1t=tempi->p2t; tempii->p1c=tempi->p2c; tempii->ic_data=templ_true; tempii->ic_opcode=EC_BR_NOT_ZERO; return OptBrNotZero(lx,tempii); } } return tempi; } IntermediateCode *CmpOptPass1(LexStruct *lx,ClassStruct *fun_class,BoolU4 combined) { /* Simplify CONST arithmetic. Sets the class throughout Expression trees. Returns the type of an Expression for use in int<-->double conversions of function parameters. */ I8 code,i; BoolU4 is_unsigned; ClassStruct *tempc,*tempc1,*tempc2,*tempc3,*tempcc; IntermediateCode *tempi,*tempi1,*tempi2,*tempi3,*tempi_push, *temp_lag[4],*last_with_class=NULL,*tempii; ParseStack *ps=OptStart(lx,temp_lag); if (combined) tempi=lx->cb.cb_in_ptr; else tempi=CbGetIc1(&lx->cb); while (code=tempi->ic_opcode) { OptNext(tempi,temp_lag); tempc=tempi->ic_class; tempi->original_class=tempc; tempi_push=tempi; switch (cmp_param_cnt[code]) { case 9: ps->ptr-=tempi->ic_data>>2; break; case 3: tempi3=PrsPop(ps); tempc3=tempi3->ic_class; tempi->p3t=tempi3; tempi->p3c=PrsPop(ps); case 2: tempi2=PrsPop(ps); tempc2=tempi2->ic_class; tempi->p2t=tempi2; tempi->p2c=PrsPop(ps); case 1: tempi1=PrsPop(ps); tempc1=tempi1->ic_class; tempi->p1t=tempi1; tempi->p1c=PrsPop(ps); break; } if (Bt(not_constant_bitmap,code)) lx->flags|=LF_NOT_CONSTANT; switch (code) { case EC_IMM: case EC_DOUBLE: case EC_STR_CONST: case EC_RBP: case EC_FS: case EC_GS: break; case EC_PUSH_CMP: tempi1=temp_lag[1]; if (tempi1->ic_opcode==EC_AND_AND) tempi1=temp_lag[2]; tempi->ic_class=tempi1->ic_class; tempi->original_class=tempi->ic_class; tempi->ic_data=0; if (tempi->ic_class->sub_type==IT_DOUBLE) tempi->ic_flags|=ICF_USE_DOUBLE; break; case EC_COM: if (tempc->sub_type==IT_DOUBLE) { if (tempi1->ic_opcode==EC_DOUBLE) { tempi->ic_data><(double)=~tempi1->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; tempi->ic_flags|=tempi1->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; } break; } if (tempi1->ic_opcode==EC_IMM) { tempi->ic_data=~tempi1->ic_data; tempi->ic_opcode=EC_IMM; tempi->ic_flags|=tempi1->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_NOT: if (tempc->sub_type==IT_DOUBLE) { if (tempi1->ic_opcode==EC_DOUBLE) { tempi->ic_data><(double)=!tempi1->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; tempi->ic_flags|=tempi1->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; } break; } if (tempi1->ic_opcode==EC_IMM) { tempi->ic_data=!tempi1->ic_data; tempi->ic_opcode=EC_IMM; tempi->ic_flags|=tempi1->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_UNARY_MINUS: if (i=FixupUnaryOp(tempi,tempi1,&is_unsigned)) { if (i==FBO1_INT) { tempi->ic_data=-tempi1->ic_data><(I8); tempi->ic_opcode=EC_IMM; } else { if (tempi->ic_flags&ICF_USE_INT) { tempi->ic_data=-tempi1->ic_data><(double); tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=-tempi1->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } } if (tempc1->type&HTT_INTERNAL_TYPE && tempc1->sub_type& 1) tempi->ic_class=sys_internal_types[tempc1->sub_type-1]; if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_DEREF: case EC__PP: case EC__MM: case EC_PP_: case EC_MM_: break; case EC_SHL_CONST: case EC_SHR_CONST: if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_POWER: if (tempc1->sub_type>tempc2->sub_type) tempi->ic_class=tempc1; else tempi->ic_class=tempc2; tempc=tempi->ic_class; if (tempc1->sub_type!=IT_DOUBLE) tempi1->ic_flags|=ICF_R_TO_DOUBLE; if (tempc2->sub_type!=IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_DOUBLE; if (tempc->sub_type!=IT_DOUBLE) tempi->ic_flags|=ICF_R_TO_INT|ICF_USE_DOUBLE; if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_SHL: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)<ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)<ic_data><(I8); tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=tempi1->ic_data><(double) << tempi2->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } else if (tempi2->ic_opcode==EC_IMM) { tempi->ic_flags|=tempi2->ic_flags; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_data=tempi2->ic_data; tempi->ic_opcode=EC_SHL_CONST; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_SHR: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)>>tempi2->ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)>>tempi2->ic_data><(I8); tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=tempi1->ic_data><(double) >> tempi2->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } else if (tempi2->ic_opcode==EC_IMM) { tempi->ic_flags|=tempi2->ic_flags; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_data=tempi2->ic_data; tempi->ic_opcode=EC_SHR_CONST; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_MUL: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)*tempi2->ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)*tempi2->ic_data><(I8); tempi->ic_opcode=EC_IMM; } else { if (tempi->ic_flags&ICF_USE_INT) { tempi->ic_data=tempi1->ic_data><(double)* tempi2->ic_data><(double); tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=tempi1->ic_data><(double)* tempi2->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } } else { if (tempi2->ic_opcode==EC_IMM) { tempcc=tempi->p1c; tempii=tempi2; tempi2=tempi1; tempi1=tempii; } else tempcc=tempi->p2c; if (tempi1->ic_opcode==EC_IMM) { i=tempi1->ic_data; switch (i) { case 0: break; case 1: tempi2->ic_flags|=tempi->ic_flags|tempi1->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi2->p1c=tempi->p1c; tempi2->p1t=tempi->p1t; tempi2->original_class=tempi->original_class; tempi_push=tempi2; break; default: if (Bsf(i)==Bsr(i)) { tempi->ic_flags|=tempi1->ic_flags; tempi->p1c=tempcc; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; tempi->ic_data=Bsf(i); tempi->ic_opcode=EC_SHL_CONST; } break; } } } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_DIV: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (!tempi2->ic_data) PrsExcept(lx,"ST_DIVIDE_BY_ZERO"); if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)/tempi2->ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)/tempi2->ic_data><(I8); tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=tempi1->ic_data><(double)/ tempi2->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } else { if (tempi2->ic_opcode==EC_IMM) { i=tempi2->ic_data; switch (i) { case 0: PrsExcept(lx,"ST_DIVIDE_BY_ZERO"); break; case 1: tempi1->ic_flags|=tempi2->ic_flags|tempi->ic_flags; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi1->p1c=tempi->p1c; tempi1->p1t=tempi->p1t; tempi1->original_class=tempi->original_class; tempi_push=tempi1; break; default: if (Bsf(i)==Bsr(i)) { tempi->ic_flags|=tempi2->ic_flags; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_data=Bsf(i); tempi->ic_opcode=EC_SHR_CONST; } break; } } } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_MOD: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (!tempi2->ic_data) PrsExcept(lx,"ST_DIVIDE_BY_ZERO"); if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)%tempi2->ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)%tempi2->ic_data><(I8); tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=tempi1->ic_data><(double)% tempi2->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } else { if (tempi2->ic_opcode==EC_IMM) { i=tempi2->ic_data; switch (i) { case 0: PrsExcept(lx,"ST_DIVIDE_BY_ZERO"); break; default: if (i>0 && Bsf(i)==Bsr(i)) { tempi2->ic_data=i-1; tempi->ic_opcode=EC_AND; } break; } } } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_AND: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data&tempi2->ic_data; if (i==FBO1_INT) tempi->ic_opcode=EC_IMM; else tempi->ic_opcode=EC_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_OR: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data|tempi2->ic_data; if (i==FBO1_INT) tempi->ic_opcode=EC_IMM; else tempi->ic_opcode=EC_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_XOR: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data^tempi2->ic_data; if (i==FBO1_INT) tempi->ic_opcode=EC_IMM; else tempi->ic_opcode=EC_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_ADD: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { tempi->ic_data=tempi1->ic_data+tempi2->ic_data; tempi->ic_opcode=EC_IMM; } else { if (tempi->ic_flags&ICF_USE_INT) { tempi->ic_data=tempi1->ic_data><(double)* tempi2->ic_data><(double); tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=tempi1->ic_data><(double)+ tempi2->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } } else { if (tempi1->ic_opcode==EC_IMM) { /******* we got problems--class needs to propigate back if (!tempi1->ic_data) { tempi2->ic_flags|=tempi1->ic_flags|tempi->ic_flags; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi2->p1c=tempi->p1c; tempi2->p1t=tempi->p1t; tempi2->original_class=tempi->original_class; tempi_push=tempi2; } else *******/ // we got problems--class needs to propigate back if (tempi2->ic_opcode==EC_ADD|| tempi2->ic_opcode==EC_SUB) { if (tempi2->p1t->ic_opcode==EC_IMM) { tempi2->ic_flags|=tempi->ic_flags; if (tempi2->ic_opcode==EC_ADD) tempi2->p1t->ic_data+=tempi1->ic_data; else tempi2->p1t->ic_data-=tempi1->ic_data; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi2->p1c=tempi->p1c; tempi2->p1t=tempi->p1t; tempi2->original_class=tempi->original_class; tempi_push=tempi2; } else if (tempi2->p2t->ic_opcode==EC_IMM) { tempi2->ic_flags|=tempi->ic_flags; if (tempi2->ic_opcode==EC_ADD) tempi2->p2t->ic_data+=tempi1->ic_data; else tempi2->p2t->ic_data-=tempi1->ic_data; tempi1->ic_opcode=EC_NOP; tempi1->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi2->p1c=tempi->p1c; tempi2->p1t=tempi->p1t; tempi2->original_class=tempi->original_class; tempi_push=tempi2; } } } else if (tempi2->ic_opcode==EC_IMM) { /******* we got problems--class needs to propigate back if (!tempi2->ic_data) { tempi1->ic_flags|=tempi2->ic_flags|tempi->ic_flags; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi1->p1c=tempi->p1c; tempi1->p1t=tempi->p1t; tempi1->original_class=tempi->original_class; tempi_push=tempi1; } else *******/ // we got problems--class needs to propigate back if (tempi1->ic_opcode==EC_ADD || tempi1->ic_opcode==EC_SUB) { if (tempi1->p1t->ic_opcode==EC_IMM) { tempi1->ic_flags|=tempi->ic_flags; if (tempi1->ic_opcode==EC_ADD) tempi1->p1t->ic_data+=tempi2->ic_data; else tempi1->p1t->ic_data-=tempi2->ic_data; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi1->p1c=tempi->p1c; tempi1->p1t=tempi->p1t; tempi1->original_class=tempi->original_class; tempi_push=tempi1; } else if (tempi1->p2t->ic_opcode==EC_IMM) { tempi1->ic_flags|=tempi->ic_flags; if (tempi1->ic_opcode==EC_ADD) tempi1->p2t->ic_data+=tempi2->ic_data; else tempi1->p2t->ic_data-=tempi2->ic_data; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi1->p1c=tempi->p1c; tempi1->p1t=tempi->p1t; tempi1->original_class=tempi->original_class; tempi_push=tempi1; } } } } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_SUB: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { tempi->ic_data=tempi1->ic_data-tempi2->ic_data; tempi->ic_opcode=EC_IMM; } else { tempi->ic_data><(double)=tempi1->ic_data><(double)- tempi2->ic_data><(double); tempi->ic_opcode=EC_DOUBLE; } } else { if (tempi2->ic_opcode==EC_IMM && !tempi2->ic_data) { tempi1->ic_flags|=tempi2->ic_flags|tempi->ic_flags; tempi2->ic_opcode=EC_NOP; tempi2->ic_flags=0; tempi->ic_opcode=EC_NOP; tempi->ic_flags=0; tempi1->p1c=tempi->p1c; tempi1->p1t=tempi->p1t; tempi1->original_class=tempi->original_class; tempi_push=tempi1; } } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_EQUAL_EQUAL: if (FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data==tempi2->ic_data; tempi->ic_opcode=EC_IMM; } else if (tempi->ic_class->sub_type==IT_DOUBLE) tempi->ic_flags|=ICF_USE_DOUBLE; if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } if (tempi_push->ic_flags & ICF_PUSH_CMP) tempi->ic_class=tempi->original_class; else tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_NOT_EQUAL: if (FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data!=tempi2->ic_data; tempi->ic_opcode=EC_IMM; } else if (tempi->ic_class->sub_type==IT_DOUBLE) tempi->ic_flags|=ICF_USE_DOUBLE; if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } if (tempi_push->ic_flags & ICF_PUSH_CMP) tempi->ic_class=tempi->original_class; else tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_LESS: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)ic_data><(I8); } else { tempi->ic_data=tempi1->ic_data><(double)< tempi2->ic_data><(double); } tempi->ic_opcode=EC_IMM; } else { if (is_unsigned) tempi->ic_flags|=ICF_USE_UNSIGNED; if (tempi->ic_class->sub_type==IT_DOUBLE) tempi->ic_flags|=ICF_USE_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } if (tempi_push->ic_flags & ICF_PUSH_CMP) tempi->ic_class=tempi->original_class; else tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_GREATER: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)>tempi2->ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)>tempi2->ic_data><(I8); } else { tempi->ic_data=tempi1->ic_data><(double)> tempi2->ic_data><(double); } tempi->ic_opcode=EC_IMM; } else { if (is_unsigned) tempi->ic_flags|=ICF_USE_UNSIGNED; if (tempi->ic_class->sub_type==IT_DOUBLE) tempi->ic_flags|=ICF_USE_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } if (tempi_push->ic_flags & ICF_PUSH_CMP) tempi->ic_class=tempi->original_class; else tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_LESS_EQUAL: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)<=tempi2->ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)<=tempi2->ic_data><(I8); } else { tempi->ic_data=tempi1->ic_data><(double)<= tempi2->ic_data><(double); } tempi->ic_opcode=EC_IMM; } else { if (is_unsigned) tempi->ic_flags|=ICF_USE_UNSIGNED; if (tempi->ic_class->sub_type==IT_DOUBLE) tempi->ic_flags|=ICF_USE_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } if (tempi_push->ic_flags & ICF_PUSH_CMP) tempi->ic_class=tempi->original_class; else tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_GREATER_EQUAL: if (i=FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { if (i==FBO1_INT) { if (is_unsigned) tempi->ic_data=tempi1->ic_data><(U8)>=tempi2->ic_data><(U8); else tempi->ic_data=tempi1->ic_data><(I8)>=tempi2->ic_data><(I8); } else { tempi->ic_data=tempi1->ic_data><(double)>= tempi2->ic_data><(double); } tempi->ic_opcode=EC_IMM; } else { if (is_unsigned) tempi->ic_flags|=ICF_USE_UNSIGNED; if (tempi->ic_class->sub_type==IT_DOUBLE) tempi->ic_flags|=ICF_USE_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } if (tempi_push->ic_flags & ICF_PUSH_CMP) tempi->ic_class=tempi->original_class; else tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_AND_AND: if (FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data&&tempi2->ic_data; tempi->ic_opcode=EC_IMM; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_OR_OR: if (FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data||tempi2->ic_data; tempi->ic_opcode=EC_IMM; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_XOR_XOR: if (FixupBinaryOp1(tempi,tempi1,tempi2,&is_unsigned)) { tempi->ic_data=tempi1->ic_data^^tempi2->ic_data; tempi->ic_opcode=EC_IMM; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else if (is_unsigned) tempi_push->original_class=sys_internal_types[IT_U8]; else tempi_push->original_class=sys_internal_types[IT_I8]; } tempi->ic_class=sys_internal_types[IT_I8]; break; case EC_COLON: if (tempc2->sub_type>tempc3->sub_type) tempi->ic_class=tempc2; else tempi->ic_class=tempc3; tempc=tempi->ic_class; if (tempc->sub_type==IT_DOUBLE) { if (tempc2->sub_type!=IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_DOUBLE; if (tempc3->sub_type!=IT_DOUBLE) tempi3->ic_flags|=ICF_R_TO_DOUBLE; } if (!tempi_push->ic_class->ptr_cnt) { if (tempi_push->ic_class->sub_type==IT_DOUBLE) tempi_push->original_class=sys_internal_types[IT_DOUBLE]; else tempi_push->original_class=sys_internal_types[IT_I8]; } break; case EC_MUL_EQUAL: if (tempi2->ic_opcode==EC_IMM && tempc->sub_type!=IT_DOUBLE && tempc2->sub_type!=IT_DOUBLE) { if (i=tempi2->ic_data) { if (Bsf(i)==Bsr(i)) { tempi2->ic_data=Bsf(i); tempi->ic_opcode=EC_SHL_EQUAL; } } } if (tempc->sub_type==IT_DOUBLE) { if (tempc2->sub_type!=IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_DOUBLE; } else { if (tempc2->sub_type==IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_INT; } break; case EC_DIV_EQUAL: if (tempi2->ic_opcode==EC_IMM && tempc->sub_type!=IT_DOUBLE && tempc2->sub_type!=IT_DOUBLE) { if (i=tempi2->ic_data) { if (Bsf(i)==Bsr(i)) { tempi2->ic_data=Bsf(i); tempi->ic_opcode=EC_SHR_EQUAL; } } else PrsExcept(lx,"ST_DIVIDE_BY_ZERO"); } if (tempc->sub_type==IT_DOUBLE) { if (tempc2->sub_type!=IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_DOUBLE; } else { if (tempc2->sub_type==IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_INT; } break; case EC_MOD_EQUAL: if (tempi2->ic_opcode==EC_IMM && tempc->sub_type!=IT_DOUBLE && tempc2->sub_type!=IT_DOUBLE) { if (i=tempi2->ic_data) { if (i>0 && Bsf(i)==Bsr(i)) { tempi2->ic_data=i-1; tempi->ic_opcode=EC_AND_EQUAL; } } else PrsExcept(lx,"ST_DIVIDE_BY_ZERO"); } if (tempc->sub_type==IT_DOUBLE) { if (tempc2->sub_type!=IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_DOUBLE; } else { if (tempc2->sub_type==IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_INT; } break; case EC_ADD_EQUAL: case EC_SUB_EQUAL: case EC_ASSIGN: if (tempc->sub_type==IT_DOUBLE) { if (tempc2->sub_type!=IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_DOUBLE; } else { if (tempc2->sub_type==IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_INT; } break; case EC_SHL_EQUAL: case EC_SHR_EQUAL: case EC_AND_EQUAL: case EC_OR_EQUAL: case EC_XOR_EQUAL: if (tempc2->sub_type==IT_DOUBLE) tempi2->ic_flags|=ICF_R_TO_INT; break; case EC_ENTER: case EC_LEAVE: tempi->ic_data=-fun_class->size; break; case EC_ADD_RSP: if (temp_lag[1]->ic_opcode==EC_ADD_RSP) { tempi->ic_data+=temp_lag[1]->ic_data; tempi->ic_flags|=temp_lag[1]->ic_flags; temp_lag[1]->ic_opcode=EC_NOP; temp_lag[1]->ic_flags=0; } break; case EC_CALL: case EC_CALL_INDIRECT: case EC_CALL_INDIRECT2: case EC_CALL_EXTERN: case EC_CLI: case EC_STI: case EC_WBINVD: case EC_INVD: case EC_ENABLE_CACHE: case EC_DISABLE_CACHE: case EC_GET_FLAGS: case EC_GET_BASE_PTR: case EC_GET_STACK_PTR: case EC_RETURN_START: case EC_RETURN_END: case EC_ABSOLUTE_ADDRESS: case EC_GET_LABEL: case EC_TYPE: case EC_RDTSC: case EC_SET_FLAGS: case EC_SET_BASE_PTR: case EC_SET_STACK_PTR: case EC_SET_RAX: case EC_BSF: case EC_BSR: case EC_PREEMPT: case EC_ABSI8: case EC_REMQUE: case EC_INPD: case EC_INPW: case EC_INP: case EC_STRLEN: case EC_BT: case EC_BTS: case EC_BTR: case EC_BTC: case EC_LBTS: case EC_LBTR: case EC_LBTC: case EC_INSQUE: case EC_INSQUE_REV: case EC_OUTPD: case EC_OUTPW: case EC_OUTP: case EC_SWITCH: case EC_MEMCPY: case EC_MEMSET: break; case EC_BR_ZERO: if (combined) tempi_push=OptBrZero(lx,tempi); break; case EC_BR_NOT_ZERO: if (combined) tempi_push=OptBrNotZero(lx,tempi); break; case EC_BR_NOT_EQUAL: case EC_BR_EQUAL_EQUAL: case EC_BR_GREATER_EQUAL: case EC_BR_LESS_EQUAL: case EC_BR_GREATER: case EC_BR_LESS: case EC_BR_OR_OR_NOT_ZERO: case EC_BR_OR_OR_ZERO: case EC_BR_AND_AND_NOT_ZERO: case EC_BR_AND_AND_ZERO: case EC_BR_AND_NOT_ZERO: case EC_BR_AND_ZERO: case EC_BR_BT: case EC_BR_BTS: case EC_BR_BTR: case EC_BR_BTC: case EC_BR_NOT_BT: case EC_BR_NOT_BTS: case EC_BR_NOT_BTR: case EC_BR_NOT_BTC: case EC_BR_LBTS: case EC_BR_LBTR: case EC_BR_LBTC: case EC_BR_NOT_LBTS: case EC_BR_NOT_LBTR: case EC_BR_NOT_LBTC: break; case EC_NOP: if (combined && tempi->ic_flags&ICF_PUSH_RESULT) { tempii=tempi; do tempii-=sizeof(IntermediateCode); while (tempii->ic_opcode==EC_NOP); tempii->ic_flags|=ICF_PUSH_RESULT; tempi->ic_flags&=~ICF_PUSH_RESULT; } break; case EC_NOP1: ps->ptr+=tempi->ic_data<<1; break; case EC_LABEL: tempii=temp_lag[1]; if (tempii->ic_opcode==EC_JMP) { if (tempii->ic_data==tempi->ic_data) { tempii->ic_opcode=EC_NOP; tempi->ic_flags|=tempii->ic_flags; } } else if (tempii->ic_opcode==EC_LABEL) { tempii=temp_lag[2]; if (tempii->ic_opcode==EC_JMP) { if (tempii->ic_data==tempi->ic_data) { tempii->ic_opcode=EC_NOP; tempi->ic_flags|=tempii->ic_flags; } } } break; case EC_NULL: case EC_ADDRESS: case EC_QUESTION: case EC_RET: case EC_END_EXP: case EC_CALL_START: case EC_CALL_END: case EC_CALL_END2: case EC_PUSH_REGS: case EC_POP_REGS: case EC_IRQ: case EC_JMP: break; default: OptMissing(lx,1,tempi); } if (cmp_result_cnt[tempi_push->ic_opcode]) { PrsPush(ps,tempi->original_class); PrsPush(ps,tempi_push); } if (tempi->ic_class) { if (code!=EC_RETURN_END && code>EC_END_EXP) last_with_class=tempi; } if (combined) tempi+=sizeof(IntermediateCode); else tempi=CbGetIc1(&lx->cb); } OptEnd(lx,1,ps); /* This is for determining type conversions for passing parameters to functions. */ return last_with_class; }