Mercurial > hg > CbC > old > device
changeset 219:6190d24e178c use_xxx_fix_before
long long code generation level 4
author | kono |
---|---|
date | Sun, 25 Apr 2004 18:32:30 +0900 |
parents | 2d64e82437d2 |
children | 97246ddfe8ab |
files | Changes mc-code-ia32.c mc-code-mips.c mc-code-powerpc.c mc-code.h mc-codegen.c mc-parse.c mc.h |
diffstat | 8 files changed, 150 insertions(+), 72 deletions(-) [+] |
line wrap: on
line diff
--- a/Changes Sat Apr 24 21:56:53 2004 +0900 +++ b/Changes Sun Apr 25 18:32:30 2004 +0900 @@ -3973,3 +3973,17 @@ long long op int, unsigned long long op int/unsigned ってのがあるのか.... うーん... + +Sun Apr 25 17:20:40 JST 2004 + +実装しないのにテストルーチン入れるなよ。。。 register lassop + +compiler を書くには... + (1) parser を書く + (2) code 生成部を書く + (3) compiler のcompile エラーを取る + (4) compiler のコード生成をデバッグする + (5) 生成したコードがアセンブラを通るかどうかを直す + (6) 生成したコードが正しいかどうかを調べる +で、(4) までできました。 +
--- a/mc-code-ia32.c Sat Apr 24 21:56:53 2004 +0900 +++ b/mc-code-ia32.c Sun Apr 25 18:32:30 2004 +0900 @@ -1940,6 +1940,11 @@ } void +code_register_dassop(int reg,int op,int d) { + error(-1); +} + +void code_dpreinc(int e1,int e2,int d,int freg) { g_expr(e2); printf("\t%s (%s)\n",fload(d),register_name(creg,0)); @@ -2295,6 +2300,10 @@ } +void +code_register_lassop(int reg,int op) { +} + #endif
--- a/mc-code-mips.c Sat Apr 24 21:56:53 2004 +0900 +++ b/mc-code-mips.c Sun Apr 25 18:32:30 2004 +0900 @@ -2555,6 +2555,11 @@ } } +void +code_register_dassop(int reg,int op,int d) { + error(-1); +} + void code_dpreinc(int e1,int e2,int d,int reg) { @@ -2964,6 +2969,11 @@ } +void +code_register_lassop(int reg,int op) { +} + + #endif
--- a/mc-code-powerpc.c Sat Apr 24 21:56:53 2004 +0900 +++ b/mc-code-powerpc.c Sun Apr 25 18:32:30 2004 +0900 @@ -449,7 +449,7 @@ int get_register(void) { /* 使われていないレジスタを調べる */ - int i,reg; + int i,j,reg; for(i=MAX_TMP_REG;i>MIN_TMP_REG;i--) { if (regs[i]) continue; /* 使われている */ regs[i]=USING_REG; /* そのレジスタを使うことを宣言し */ @@ -468,8 +468,8 @@ for(i=0;i<reg_sp;i++) { if ((reg=reg_stack[i])>=0) { code_assign_lvar( - (reg_stack[i]=new_lvar(size_of_int)),reg,0); - reg_stack[i]= reg_stack[i]-REG_LVAR_OFFSET; + (j=new_lvar(size_of_int)),reg,0); + reg_stack[i]= j-REG_LVAR_OFFSET; return reg; } } @@ -477,9 +477,9 @@ /* search register stack */ for(i=0;i<lreg_sp;i++) { if ((reg=lreg_stack[i])>=0) { - code_assign_lvar( - (lreg_stack[i]=new_lvar(size_of_longlong)),reg,0); - lreg_stack[i]= lreg_stack[i]-REG_LVAR_OFFSET; + code_lassign_lvar( + (j=new_lvar(size_of_longlong)),reg); + lreg_stack[i]= j-REG_LVAR_OFFSET; free_register(reg); return get_register(); } @@ -1446,7 +1446,7 @@ if (creg!=ireg) free_register(creg); free_register(creg); } - creg = freg = reg; + creg = lreg = reg; } void @@ -1608,7 +1608,7 @@ nargs ++ ; reg_arg++; continue; } else if (t==LONGLONG||t==ULONGLONG) { - if (reg_arg>=MAX_INPUT_REGISTER_VAR) { + if (reg_arg+1>=MAX_INPUT_REGISTER_VAR) { arg = list2(LVAR,caller_arg_offset_v(nargs)); } else if (!simple_args(e3) && cadr(e3)) { arg = get_register_var(0); @@ -2966,6 +2966,20 @@ emit_dpop_free(xreg,d); } +void +code_register_dassop(int reg,int op,int d) { + int xreg=emit_dpop(d); + set_freg(reg,0); + dtosop(op,xreg); + if (creg==reg) { + printf("\tfmr %s,%s\n",fregister_name(xreg),fregister_name(freg)); + free_register(freg); + freg = creg = xreg; + } else { + printf("\tfmr %s,%s\n",fregister_name(reg),fregister_name(freg)); + emit_dpop_free(xreg,d); + } +} void code_dpreinc(int e1,int e2,int d,int reg) { @@ -3097,6 +3111,12 @@ /* 64bit int part */ +static void +lmove(int to,int from) +{ + printf("\tmr %s,%s\n",lregister_name_high(to),lregister_name_high(from)); + printf("\tmr %s,%s\n",lregister_name_low(to),lregister_name_low(from)); +} static void cond(char *s,int l1) @@ -3185,10 +3205,7 @@ code_lregister(int e2,int reg) { if (creg!=e2) { - printf("\tmr %s,%s\n",lregister_name_low(creg), - lregister_name_low(e2)); - printf("\tmr %s,%s\n",lregister_name_high(creg), - lregister_name_high(e2)); + lmove(creg,e2); } } @@ -3249,9 +3266,8 @@ void code_lassign_lregister(int e2,int reg) { - if (e2!=creg) { - printf("\tmr %s,%s\n",lregister_name_high(e2),lregister_name_high(creg)); - printf("\tmr %s,%s\n",lregister_name_low(e2),lregister_name_low(creg)); + if (e2!=reg) { + lmove(e2,reg); } } @@ -3354,6 +3370,7 @@ " lwz r3,-48(r1)", " lwz r4,-44(r1)", " blr", +0 }; static int asld_lib_used=0; @@ -3385,6 +3402,7 @@ " lwz r3,-48(r1)", " lwz r4,-44(r1)", " blr", +0 }; static int asrd_lib_used=0; @@ -3415,6 +3433,7 @@ " lwz r3,-48(r1)", " lwz r4,-44(r1)", " blr", +0 }; static void @@ -3552,31 +3571,31 @@ crn_h = lregister_name_high(creg); crn_l = lregister_name_low(creg); switch(op) { - case ADD: + case LADD: printf("\taddc %s,%s,%s\n",crn_l,crn_l,orn_l); printf("\tadde %s,%s,%s\n",crn_h,crn_h,orn_h); break; - case SUB: + case LSUB: printf("\tsubfc %s,%s,%s\n",crn_l,crn_l,orn_l); printf("\tsubfe %s,%s,%s\n",crn_h,crn_h,orn_h); break; case LCMP: error(-1); break; - case BAND: + case LBAND: printf("\tand %s,%s,%s\n",crn_l,crn_l,orn_l); printf("\tand %s,%s,%s\n",crn_h,crn_h,orn_h); break; - case EOR: + case LEOR: printf("\txor %s,%s,%s\n",crn_l,crn_l,orn_l); printf("\txor %s,%s,%s\n",crn_h,crn_h,orn_h); break; - case BOR: + case LBOR: printf("\tor %s,%s,%s\n",crn_l,crn_l,orn_l); printf("\tor %s,%s,%s\n",crn_h,crn_h,orn_h); break; - case MUL: - case UMUL: + case LMUL: + case LUMUL: dx=get_lregister(); drn_l = lregister_name_low(dx); drn_h = lregister_name_high(dx); @@ -3597,16 +3616,16 @@ printf("\tadd %s,%s,%s\n",crn_l,drn_h,crn_h); printf("\tmr %s,%s\n",crn_l,drn_l); break; - case DIV: + case LDIV: code_ldiv_lib(oreg); // ___divdi3$stub break; - case UDIV: + case LUDIV: code_ludiv_lib(oreg); // ___udivdi3$stub break; - case MOD: + case LMOD: code_lmod_lib(oreg); // ___moddi3$stub break; - case UMOD: + case LUMOD: code_lumod_lib(oreg); // ___umoddi3$stub break; default: @@ -3633,10 +3652,10 @@ case RSHIFT: case URSHIFT: return (0<v&&v<31); - case ADD: - case SUB: + case LADD: + case LSUB: return 1; - case BOR: + case LBOR: return (v>0); default: return 0; @@ -3656,8 +3675,8 @@ else if (car(e)==CONST) v = caddr(e); switch(op) { - case LSHIFT: - case ULSHIFT: + case LLSHIFT: + case LULSHIFT: greg = get_register(); grn = register_name(greg); printf("\tsrwi %s,%s,%d\n",grn,crn_h,32-v); @@ -3666,7 +3685,7 @@ printf("\tslwi %s,%s,%d\n",crn_h,crn_h,v); free_register(greg); return; - case RSHIFT: + case LRSHIFT: greg = get_register(); grn = register_name(greg); printf("\tsrwi %s,%s,%d\n",grn,crn_l,v); @@ -3675,7 +3694,7 @@ printf("\tmr %s,%s\n",crn_l,grn); free_register(greg); return; - case URSHIFT: + case LURSHIFT: greg = get_register(); grn = register_name(greg); printf("\tslwi %s,%s,%d\n",grn,crn_l,32-v); @@ -3685,15 +3704,15 @@ free_register(greg); return; return; - case ADD: + case LADD: printf("\taddi %s,%s,lo16(%d)\n",crn_l,crn_l,v); printf("\taddze %s,%s\n",crn_h,crn_h); break; - case SUB: + case LSUB: printf("\tsubi %s,%s,lo16(%d)\n",crn_l,crn_l,v); printf("\taddme %s,%s\n",crn_h,crn_h); break; - case BOR: + case LBOR: printf("\tori %s,%s,lo16(%d)\n",crn_l,crn_l,v); break; default: @@ -3721,15 +3740,15 @@ } void -code_i2ll(int creg) +code_i2ll(int reg) { char *crn,*crn_h,*crn_l; int creg0; - crn = register_name(creg); + crn = register_name(reg); creg = use_longlong(creg0=creg); crn_h = lregister_name_high(creg); crn_l = lregister_name_low(creg); - if (creg0!=regv_l(creg)) + if (creg0!=regv_l(reg)) printf("\tmr %s,%s\n",crn_l,crn); printf("\tsrawi %s,%s,31\n",crn_h,crn_l); } @@ -3741,15 +3760,15 @@ } void -code_u2ll(int creg) +code_u2ll(int reg) { int creg0; char *crn,*crn_h,*crn_l; - crn = register_name(creg); + crn = register_name(reg); creg = use_longlong(creg0=creg); crn_h = lregister_name_high(creg); crn_l = lregister_name_low(creg); - if (creg0!=regv_l(creg)) + if (creg0!=regv_l(reg)) printf("\tmr %s,%s\n",crn_l,crn); printf("\tli %s,0\n",crn_h); } @@ -3761,12 +3780,13 @@ } void -code_ll2i(int creg) +code_ll2i(int reg) { - int creg0; - char *crn_l = lregister_name_low(creg); - creg = use_int(creg0=creg); - if (creg!=regv_l(creg0)) + char *crn_l; + if (!is_longlong_reg(reg)) { error(-1); return; } + crn_l = lregister_name_low(reg); + creg = use_int(creg); + if (creg!=regv_l(reg)) printf("\tmr %s,%s\n",register_name(creg),crn_l); } @@ -3867,10 +3887,7 @@ printf("\taddei %s,%s,0\n", lregister_name_high(cadr(e2)),lregister_name_high(cadr(e2))); if (cadr(reg)!=cadr(e2)) { - printf("\tmr %s,%s\n",lregister_name_low(cadr(reg)), - lregister_name_low(cadr(e2))); - printf("\tmr %s,%s\n",lregister_name_high(cadr(reg)), - lregister_name_high(cadr(e2))); + lmove(cadr(reg),cadr(e2)); } return; } @@ -3896,10 +3913,7 @@ int dreg,nreg; int dir=caddr(e1); if (car(e2)==LREGISTER) { - printf("\tmr %s,%s\n",lregister_name_low(cadr(reg)), - lregister_name_low(cadr(e2))); - printf("\tmr %s,%s\n",lregister_name_high(cadr(reg)), - lregister_name_high(cadr(e2))); + lmove(cadr(reg),cadr(e2)); printf("\taddci %s,%s,%d\n", lregister_name_low(cadr(e2)),lregister_name_low(cadr(e2)), dir); printf("\taddei %s,%s,0\n", @@ -3952,6 +3966,21 @@ emit_lpop_free(xreg); } +void +code_register_lassop(int reg,int op) { + int xreg=emit_lpop(); + set_lreg(reg,0); + ltosop(op,xreg); + if (creg==reg) { + free_register(lreg); + lmove(xreg,lreg); + lreg = creg = xreg; + } else { + lmove(reg,lreg); + emit_lpop_free(xreg); + } +} + #endif
--- a/mc-code.h Sat Apr 24 21:56:53 2004 +0900 +++ b/mc-code.h Sun Apr 25 18:32:30 2004 +0900 @@ -145,6 +145,7 @@ extern void code_dpreinc(int e1,int e2,int d,int reg); extern void code_dpostinc(int e1,int e2,int d,int reg); extern void code_dassop(int op,int d); +extern void code_register_dassop(int reg,int op,int d); #endif @@ -196,6 +197,7 @@ extern void code_lpreinc(int e1,int e2,int reg); extern void code_lpostinc(int e1,int e2,int reg); extern void code_lassop(int op); +extern void code_register_lassop(int reg,int op); #endif
--- a/mc-codegen.c Sat Apr 24 21:56:53 2004 +0900 +++ b/mc-codegen.c Sun Apr 25 18:32:30 2004 +0900 @@ -143,6 +143,12 @@ code_dregister(e2,creg,0); return FLOAT; #endif +#if LONGLONG_CODE + case LREGISTER: + creg=use_longlong(creg); + code_lregister(e2,creg); + return LONGLONG; +#endif case RLVAR: creg=use_int(creg); code_rlvar(e2,creg); @@ -363,11 +369,19 @@ case LPREINC: /* ++d */ creg=use_longlong(creg); code_lpreinc(e1,e2,creg); - return DOUBLE; + return LONGLONG; case LPOSTINC: /* d++ */ creg=use_longlong(creg); code_lpostinc(e1,e2,creg); - return DOUBLE; + return LONGLONG; + case LUPREINC: /* ++d */ + creg=use_longlong(creg); + code_lpreinc(e1,e2,creg); + return ULONGLONG; + case LUPOSTINC: /* d++ */ + creg=use_longlong(creg); + code_lpostinc(e1,e2,creg); + return ULONGLONG; #endif case MUL: case UMUL: case DIV: case UDIV: @@ -999,7 +1013,8 @@ ce1==GVAR ||ce1==RGVAR||ce1==CRGVAR || ce1==DRGVAR || ce1==LRGVAR || ce1==FRLVAR || ce1==FRGVAR || ce1==CURGVAR ||ce1==SURGVAR||ce1==SRGVAR || - ce1==REGISTER|| ce1==DREGISTER || ce1==FREGISTER + ce1==REGISTER|| ce1==DREGISTER || ce1==FREGISTER || + ce1==LREGISTER ); } @@ -1475,11 +1490,11 @@ return; } g_expr(e2); - emit_lpush(); + emit_push(); g_expr(e4); - e2 = emit_lpop(); + e2 = emit_pop(0); code_lassign(e2,creg); - emit_lpop_free(e2); + emit_pop_free(e2); return; } @@ -1538,8 +1553,7 @@ emit_dpush(d); g_expr(e2); if (car(e2)==DREGISTER||car(e2)==FREGISTER) { - /* code_register_dassop(cadr(e2),op,d); */ - error(-1); /* unsupported now */ + code_register_dassop(cadr(e2),op,d); return; } code_dassop(op,d); @@ -1566,8 +1580,7 @@ emit_lpush(); g_expr(e2); if (car(e2)==LREGISTER) { - /* code_register_lassop(cadr(e2),op); */ - error(-1); /* unsupported now */ + code_register_lassop(cadr(e2),op); return; } code_lassop(op);
--- a/mc-parse.c Sat Apr 24 21:56:53 2004 +0900 +++ b/mc-parse.c Sun Apr 25 18:32:30 2004 +0900 @@ -809,6 +809,7 @@ if(t==REGISTER) return size_of_int; if(t==DREGISTER) return size_of_double; if(t==FREGISTER) return size_of_float; + if(t==LREGISTER) return size_of_longlong; if(scalar(t)) return size_of_int; if(t==FLOAT) return size_of_float; if(t==DOUBLE) return size_of_double; @@ -2237,7 +2238,7 @@ return(list4(LASSOP,e1,e2,op+LOP)); } else if (t==ULONGLONG) { e2=ulonglong_value(e2,type); type=t; - return(list4(LASSOP,e1,e2,op+LOP+US)); + return(list4(LASSOP,e1,e2,op+LOP+((op==MUL+AS||op==DIV+AS)?US:0))); } #endif if(!integral(type)) error(TYERR); @@ -2744,6 +2745,7 @@ type=nptr->ty; getsym(0); break; + case LREGISTER: case DREGISTER: case FREGISTER: case REGISTER: @@ -3257,6 +3259,7 @@ } if((op==MUL||op==DIV)&&car(e2)==LCONST&&lcadr(e2)==1) return e1; if(op==BOR||op==EOR||op==BAND) return(list3(op+LOP,e1,e2)); + /* there is no UADD, USUB (should be? */ if(op==LSHIFT||op==RSHIFT) return(list3(op+(t1==ULONGLONG?US:0)+LOP,e1,e2)); return(list3(type==ULONGLONG?op+US+LOP:op,e1,e2)); } @@ -3272,16 +3275,14 @@ if(t1>0&&car(t1)==POINTER) { e2= int_value(e2,t2); t2=INT; } else if(t2>0&&car(t2)==POINTER) { e1= int_value(e1,t1); t1=INT; } #if FLOAT_CODE - if(t1==DOUBLE||t2==DOUBLE) + else if(t1==DOUBLE||t2==DOUBLE) return dbinop(op,e1,e2,t1,t2); - if(t1==FLOAT||t2==FLOAT) + else if(t1==FLOAT||t2==FLOAT) return fbinop(op,e1,e2,t1,t2); #endif #if LONGLONG_CODE - if(t1==LONGLONG||t2==LONGLONG) + else if((t1==LONGLONG||t2==LONGLONG)||(t1==ULONGLONG||t2==ULONGLONG)) return lbinop(op,e1,e2,t1,t2); - if(t1==ULONGLONG||t2==ULONGLONG) - return lbinop(op+((op==BOR||op==EOR||op==BAND||op==EQ||op==NEQ)?0:US),e1,e2,t1,t2); #endif if(car(e1)==CONST&&car(e2)==CONST) { e1=cadr(e1);
--- a/mc.h Sat Apr 24 21:56:53 2004 +0900 +++ b/mc.h Sun Apr 25 18:32:30 2004 +0900 @@ -144,7 +144,7 @@ #define STRING 8 #define FNAME 9 -#define NULLARY_ARGS(i) (i==REGISTER||i==DREGISTER||i==FREGISTER||(GVAR<=(i%SOP)&&(i%SOP)<=FNAME)) +#define NULLARY_ARGS(i) (i==REGISTER||i==DREGISTER||i==FREGISTER||i==LREGISTER||(GVAR<=(i%SOP)&&(i%SOP)<=FNAME)) /* unary argments */