Mercurial > hg > CbC > old > device
changeset 38:d48d952da354
struct copy continue
author | kono |
---|---|
date | Tue, 11 Feb 2003 11:26:51 +0900 |
parents | 412ad2e6c2a2 |
children | c63c4fdeb9a7 |
files | .gdbinit mc-nop-386.c mc-parse.c |
diffstat | 3 files changed, 38 insertions(+), 45 deletions(-) [+] |
line wrap: on
line diff
--- a/.gdbinit Mon Feb 10 22:29:12 2003 +0900 +++ b/.gdbinit Tue Feb 11 11:26:51 2003 +0900 @@ -1,6 +1,6 @@ tb main -b error -b errmsg +# b error +# b errmsg define regs call fprintf(stderr,"eax=%08x ebx=%08x ecx=%08x edx=%08x\nesi=%08x edi=%08x ebp=%08x esp=%08x eip=%08x\n",$eax,$ebx,$ecx,$edx,$esi,$edi,$ebp,$esp,$eip) end
--- a/mc-nop-386.c Mon Feb 10 22:29:12 2003 +0900 +++ b/mc-nop-386.c Tue Feb 11 11:26:51 2003 +0900 @@ -55,7 +55,7 @@ static void tosop(int op); static void div_cleanup(char *orn); static void use_register(int virt, int real, int move); -static void emit_copy(char *from,char *to,int length,int offset); +static void emit_copy(int from,int to,int length,int offset); extern int error(int n); extern int fwdlabel(void); @@ -177,6 +177,10 @@ char * register_name(int i,int byte) { + if (i<0) { + error(REG_ERR); + return "%eax"; + } if (byte && rname[i] <= REG_EDX) { return reg_name_l[rname[i]]; } else { @@ -740,22 +744,22 @@ #define MAX_COPY_LEN 20 void -emit_copy(char *from,char *to,int length,int offset) +emit_copy(int from,int to,int length,int offset) { if (length<0) return; switch (length) { case 0: break; case 1: - printf("\tmovb %d(%s),%s\n",offset,from, reg_name_l[rname[dreg]] ); - printf("\tmovb %s,%d(%s)\n",reg_name_l[rname[dreg]] ,offset,to); + printf("\tmovb %d(%s),%s\n",offset,register_name(from,0), reg_name_l[rname[dreg]] ); + printf("\tmovb %s,%d(%s)\n",reg_name_l[rname[dreg]] ,offset,register_name(to,0)); break; case 2: - printf("\tmovw %d(%s),%s\n",offset,from, reg_name_w[rname[dreg]] ); - printf("\tmovw %s,%d(%s)\n",reg_name_w[rname[dreg]] ,offset,to); + printf("\tmovw %d(%s),%s\n",offset,register_name(from,0), reg_name_w[rname[dreg]] ); + printf("\tmovw %s,%d(%s)\n",reg_name_w[rname[dreg]] ,offset,register_name(to,0)); break; case 4: - printf("\tmovl %d(%s),%s\n",offset,from, register_name(dreg,0)); - printf("\tmovl %s,%d(%s)\n",register_name(dreg,0), offset,to); + printf("\tmovl %d(%s),%s\n",offset,register_name(from,0), register_name(dreg,0)); + printf("\tmovl %s,%d(%s)\n",register_name(dreg,0), offset,register_name(to,0)); break; default: if (length <=MAX_COPY_LEN) { @@ -767,16 +771,13 @@ emit_copy(from,to,length,offset); return; } - printf("\txchg %%edi,%s\n",from); - printf("\txchg %%esi,%s\n",to); - printf("\txchg %%ecx,%s\n",register_name(dreg,0)); + use_register(from,REG_EDI,1); + use_register(to, REG_ESI,1); + use_register(dreg,REG_ECX,1); printf("\tmovl $%d,%%ecx\n",length/4); printf("\tcld\n\trep\n\tmovsl\n"); - printf("\txchg %%ecx,%s\n",register_name(dreg,0)); - printf("\txchg %%esi,%s\n",to); - printf("\txchg %%edi,%s\n",from); if(length%4) { - emit_copy("%esi","%edi",length,offset+length/4); + emit_copy(from,to,length,offset+length/4); } } } @@ -784,28 +785,29 @@ int struct_push(int e4,int t) { - int length; + int length,xreg,save; g_expr(e4); length=size(t); if(length%size_of_int) { length += size_of_int - (length%size_of_int); } + /* I think, after g_expr, at least two registers are free */ printf("\tsubl $%d,%%esp\n",length); - if (length<=MAX_COPY_LEN) - emit_copy(register_name(creg,0),"%esp",length,0); - else { - printf("\tpushl %%edi\n"); - printf("\tpushl %%esi\n"); - printf("\tpushl %%ecx\n"); - printf("\tleal 12(%%esp),%%edi\n"); - if (rname[creg]!=REG_ESI) - printf("\tmovl %s,%%esi\n",register_name(creg,0)); - printf("\tmovl $%d,%%ecx\n",length/size_of_int); - printf("\tcld\n\trep\n\tmovsl\n"); - printf("\tpopl %%ecx\n"); - printf("\tpopl %%esi\n"); - printf("\tpopl %%edi\n"); + if (register_full()) { + /* this is wrong assumption */ + save = 1; + printf("\tpushl %s\n",register_name(lreg,0)); + xreg = lreg; + } else { + save=0; + xreg = get_register(); } + printf("\tmovl %%esp,%s\n",register_name(xreg,0)); + emit_copy(creg,xreg,length,0); + if (save) { + printf("\tpopl %s\n",register_name(lreg,0)); + } else + free_register(xreg); return length/size_of_int; } @@ -1107,8 +1109,7 @@ void sassign(int e1) { - int e2,e3,e4,sz; - char *xrn; + int e2,e3,e4,sz,xreg; /* structure assignment */ e2 = cadr(e1); /* pointer variable to the struct */ @@ -1118,8 +1119,8 @@ g_expr(e4); emit_push(); g_expr(e2); - xrn = register_name(emit_pop(0),0); - emit_copy(xrn,register_name(creg,0),sz,0); + xreg = emit_pop(0); + emit_copy(xreg,creg,sz,0); return; }
--- a/mc-parse.c Mon Feb 10 22:29:12 2003 +0900 +++ b/mc-parse.c Tue Feb 11 11:26:51 2003 +0900 @@ -1959,15 +1959,7 @@ return list2(ADDRESS,e); } else if(t==STRUCT || t==UNION) { t = cadr(type); /* size */ - switch(car(e)) { - case GVAR: - return(list3(RSTRUCT,list3(RGVAR,cadr(e),caddr(e)),t)); - case LVAR: - return(list3(RSTRUCT,list2(RLVAR,cadr(e)),t)); - case INDIRECT: - return(list3(RSTRUCT,list2(RINDIRECT,cadr(e)),t)); - default: return list3(RSTRUCT,e,t); - } + return list3(RSTRUCT,e,t); } else if(t!=POINTER) error(TYERR); } switch(car(e)) {