Mercurial > hg > CbC > old > device
diff mc-code-mips.c @ 276:ebaec1ae566e
MIPS double/longlong lib operand register conflict
author | kono |
---|---|
date | Fri, 21 May 2004 18:59:56 +0900 |
parents | 8f09f8bbc494 |
children | d5467cf30f58 |
line wrap: on
line diff
--- a/mc-code-mips.c Fri May 21 14:00:02 2004 +0900 +++ b/mc-code-mips.c Fri May 21 18:59:56 2004 +0900 @@ -258,6 +258,9 @@ static int code_d1(double d); static int code_d2(double d); +static void code_double_lib(char *lib,int to,int reg,int oreg); +static void code_double_lib_c(char *lib,int from,int to,double value); + #endif #if LONGLONG_CODE static int code_l1(long long ll); @@ -1666,14 +1669,7 @@ // save_stack,clear_ptr_cache is assumed if (!is_longlong_reg(reg)) { error(-1); return; } if (mode) { - if (regv_h(reg)!=DREGISTER_OPERAND_H) { - printf("\tmove %s,%s\n", - lregister_name_high(DREGISTER_OPERAND),lregister_name_high(reg)); - } - if (regv_l(reg)!=DREGISTER_OPERAND_L) { - printf("\tmove %s,%s\n", - lregister_name_low(DREGISTER_OPERAND),lregister_name_low(reg)); - } + lmove(LREGISTER_OPERAND,reg); } } @@ -1683,14 +1679,7 @@ // save_stack,clear_ptr_cache is assumed if (!is_longlong_reg(reg)) { error(-1); return; } if (mode) { - if (regv_h(reg)!=DREGISTER_OPERAND_1_H) { - printf("\tmove %s,%s\n", - lregister_name_high(DREGISTER_OPERAND_1),lregister_name_high(reg)); - } - if (regv_l(reg)!=DREGISTER_OPERAND_1_L) { - printf("\tmove %s,%s\n", - lregister_name_low(DREGISTER_OPERAND_1),lregister_name_low(reg)); - } + lmove(LREGISTER_OPERAND_1,reg); } } @@ -1749,7 +1738,6 @@ n->dsp = offset; offset+=SIZE_OF_INT; t = INT; - reg += reg_offset; /* for duplicated floating point argument */ } else if (tag==FREGISTER) { /* regs[reg]==INPUT_REG case should be considered */ n->dsp = offset; @@ -1760,7 +1748,7 @@ tag = REGISTER; t = INT; } } - else if(t==DOUBLE) { offset+=SIZE_OF_DOUBLE; reg_offset+=2; } + // else if(t==DOUBLE) { offset+=SIZE_OF_DOUBLE; reg_offset+=2; } else error(-1); } else if (tag==DREGISTER) { /* regs[reg]==INPUT_REG case should be considered */ @@ -2298,20 +2286,24 @@ lmove(int to,int from) { int tmp; - if (regv_h(to)==regv_h(from)&&(regv_l(to)==regv_l(from))) + if (regv_h(to)==regv_h(from)&&(regv_l(to)==regv_l(from))) { return; - if (regv_h(to)==regv_l(from)&&(regv_l(to)==regv_h(from))) { + } else if (regv_h(to)!=regv_l(from)) { + if (regv_h(to)!=regv_h(from)) + printf("\tmove %s,%s\n",lregister_name_high(to),lregister_name_high(from)); + if (regv_l(to)!=regv_l(from)) + printf("\tmove %s,%s\n",lregister_name_low(to),lregister_name_low(from)); + } else if (regv_l(to)!=regv_h(from)) { + if (regv_l(to)!=regv_l(from)) + printf("\tmove %s,%s\n",lregister_name_low(to),lregister_name_low(from)); + if (regv_h(to)!=regv_h(from)) + printf("\tmove %s,%s\n",lregister_name_high(to),lregister_name_high(from)); + } else { tmp = get_register(); printf("\tmove %s,%s\n",register_name(tmp),lregister_name_low(from)); printf("\tmove %s,%s\n",lregister_name_high(to),lregister_name_high(from)); printf("\tmove %s,%s\n",lregister_name_low(to),register_name(tmp)); free_register(tmp); - } else if (regv_h(to)==regv_l(from)) { - printf("\tmove %s,%s\n",lregister_name_low(to),lregister_name_low(from)); - printf("\tmove %s,%s\n",lregister_name_high(to),lregister_name_high(from)); - } else { - printf("\tmove %s,%s\n",lregister_name_low(to),lregister_name_low(from)); - printf("\tmove %s,%s\n",lregister_name_high(to),lregister_name_high(from)); } } @@ -3201,7 +3193,7 @@ code_save_stacks(); clear_ptr_cache(); set_dreg(RET_DREGISTER,1); - printf("\tli.d $6,%g\n",0.0); + printf("\tli.d $6,%10.10g\n",0.0); extern_conv("dpcmp"); cmpreg = 2; return; @@ -3328,7 +3320,7 @@ if (d) { code_save_stacks(); clear_ptr_cache(); - set_lreg(LREGISTER_OPERAND_1,1); + set_dreg(DREGISTER_OPERAND_1,1); printf("\tmove $4,$0\n"); printf("\tmove $5,$0\n"); /// set_dreg_operand(oreg,1); @@ -3346,7 +3338,7 @@ use_float(1,reg); code_save_stacks(); clear_ptr_cache(); - set_dreg(RET_DREGISTER,1); + set_dreg(DREGISTER_OPERAND,1); extern_conv("dptoli"); set_ireg(RET_REGISTER,0); return; @@ -3370,7 +3362,7 @@ use_float(1,reg); code_save_stacks(); clear_ptr_cache(); - set_dreg(RET_DREGISTER,1); + set_dreg(DREGISTER_OPERAND,1); extern_conv("dptoul"); set_ireg(RET_REGISTER,0); return; @@ -3379,18 +3371,30 @@ void code_u2d(int reg) { + int tmp=new_lvar(SIZE_OF_INT); set_ireg(REGISTER_OPERAND,1); + code_assign_lvar(tmp,REGISTER_OPERAND,0); code_save_stacks(); clear_ptr_cache(); extern_conv("litodp"); + code_rlvar(tmp,REGISTER_OPERAND); + printf("\tbgez\t%s,1f\n",register_name(REGISTER_OPERAND)); + code_double_lib_c("dpadd",RET_DREGISTER,RET_DREGISTER,4.294967296e9); + printf("1:\n"); set_dreg(RET_DREGISTER,0); - use_float(1,reg); + if (reg!=USE_CREG) { + use_float(1,reg); + if (reg!=RET_DREGISTER) { + lmove(reg,RET_DREGISTER); + } + } + free_lvar(tmp); return; } void code_d2f(int reg) { - set_dreg(RET_DREGISTER,1); + set_dreg(DREGISTER_OPERAND,1); code_save_stacks(); clear_ptr_cache(); extern_conv("dptofp"); @@ -3412,9 +3416,20 @@ void code_f2i(int reg) { +#if 0 + int tmp=new_lvar(SIZE_OF_INT); use_int(reg); printf("\ttrunc.w.s %s,%s,%s\n",register_name(freg), register_name(freg),register_name(ireg)); + code_dassign_lvar(tmp,freg,1); + code_rlvar(tmp,reg); + free_lvar(tmp); +#else + use_int(reg); + printf("\ttrunc.w.s %s,%s,%s\n",fregister_name(freg), + fregister_name(freg),register_name(ireg)); + printf("\tmfc1 %s,%s\n",register_name(reg),fregister_name(freg)); +#endif } void @@ -3461,6 +3476,7 @@ use_float(0,reg); code_drlvar(n,0,reg); printf("\tcvt.s.w %s,%s\n",register_name(freg),register_name(freg)); + free_lvar(n); } void @@ -3579,10 +3595,24 @@ static void code_double_lib(char *lib,int to,int reg,int oreg) { + int tmp; code_save_stacks(); clear_ptr_cache(); - set_dreg_operand(reg,1); - set_dreg_operand1(oreg,1); + if (regs[DREGISTER_OPERAND_L]||regs[DREGISTER_OPERAND_H]) { + if (regs[DREGISTER_OPERAND_1_L]||regs[DREGISTER_OPERAND_1_H]) { + tmp = new_lvar(SIZE_OF_DOUBLE); + code_lassign_lvar(tmp,reg); + set_dreg_operand1(oreg,1); + code_lrlvar(tmp,DREGISTER_OPERAND); + free_lvar(tmp); + } else { + set_dreg_operand1(oreg,1); + set_dreg_operand(reg,1); + } + } else { + set_dreg_operand(reg,1); + set_dreg_operand1(oreg,1); + } extern_conv(lib); set_dreg(RET_DREGISTER,0); if (to!=RET_DREGISTER) { @@ -3596,7 +3626,7 @@ code_save_stacks(); clear_ptr_cache(); set_dreg_operand(from,1); - printf("\tli.d $6,%g\n",value); + printf("\tli.d $6,%10.10g\n",value); extern_conv(lib); set_dreg(RET_DREGISTER,0); if (to!=RET_DREGISTER) { @@ -3764,6 +3794,7 @@ } else { if (car(e2)==DREGISTER) { use_float(d,reg); + code_save_stacks(); code_double_lib_c("dpadd",cadr(e2),cadr(e2),dir); if (reg!=cadr(e2)) lmove(reg,cadr(e2)); return; @@ -3903,8 +3934,8 @@ } g_expr(list3(op1,e2,e1)); switch(op) { - case DOP+GT: printf("\tblez\t$2,$L_%d\n",l1);break; - case DOP+GE: printf("\tbltz\t$2,$L_%d\n",l1);break; + case DOP+GT: printf("\tbltz\t$2,$L_%d\n",l1);break; + case DOP+GE: printf("\tblez\t$2,$L_%d\n",l1);break; case DOP+EQ: printf("\tbeq\t$2,$0,$L_%d\n",l1);break; case DOP+NEQ: printf("\tbne\t$2,$0,$L_%d\n",l1);break; case FOP+GT: printf("\tbc1t\t$L_%d\n",l1);break; @@ -4369,10 +4400,24 @@ static void code_longlong_lib(char *lib,int reg,int oreg) { + int tmp; code_save_stacks(); clear_ptr_cache(); - set_lreg_operand(reg,1); - set_lreg_operand1(oreg,1); + if (regs[LREGISTER_OPERAND_L]||regs[LREGISTER_OPERAND_H]) { + if (regs[LREGISTER_OPERAND_1_L]||regs[LREGISTER_OPERAND_1_H]) { + tmp = new_lvar(SIZE_OF_LONGLONG); + code_lassign_lvar(tmp,reg); + set_lreg_operand1(oreg,1); + code_lrlvar(tmp,LREGISTER_OPERAND); + free_lvar(tmp); + } else { + set_lreg_operand1(oreg,1); + set_lreg_operand(reg,1); + } + } else { + set_lreg_operand(reg,1); + set_lreg_operand1(oreg,1); + } extern_conv(lib); set_lreg(RET_LREGISTER,0); }