Mercurial > hg > CbC > old > device
changeset 794:032dc03be02e
i64 arg_register in inline mode
author | Shinji KONO <kono@ie.u-ryukyu.ac.jp> |
---|---|
date | Tue, 23 Nov 2010 09:42:08 +0900 |
parents | aa2db7c70d42 |
children | a4fd2ab28e24 |
files | mc-code-arm.c mc-code-i64.c mc-code-ia32.c mc-code-mips.c mc-code-powerpc.c mc-code-spu.c mc-code.h mc-codegen.c mc-codegen.h mc-inline.c mc-parse.c test/tstdarg.c |
diffstat | 12 files changed, 96 insertions(+), 47 deletions(-) [+] |
line wrap: on
line diff
--- a/mc-code-arm.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-code-arm.c Tue Nov 23 09:42:08 2010 +0900 @@ -604,7 +604,7 @@ void -code_arg_register(NMTBL *fnptr) +code_arg_register(NMTBL *fnptr, int in) { int args = fnptr->dsp; NMTBL *n; @@ -616,6 +616,8 @@ int is_code0 = is_code(fnptr); int dots; + if (in) return; + function_type(fnptr->ty,&dots); while (args) { /* process in reverse order */
--- a/mc-code-i64.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-code-i64.c Tue Nov 23 09:42:08 2010 +0900 @@ -49,7 +49,6 @@ } __builtin_va_list1, *__builtin_va_list; \\\n\ \\\n\ #define __builtin_va_start(ap,v) \\\n\ -__builtin_va_list1 __my_va_list; \\\n\ { \\\n\ ap = &__my_va_list; \\\n\ ap->float_first = ap->long_last+8; \\\n\ @@ -413,9 +412,14 @@ #define REG_ESI 3 #define REG_EDX 4 #define REG_ECX 5 // for strange reason (code_assop) -#define REG_EAX 8 +#define REG_R8 6 +#define REG_R9 7 // input register +#define REG_EAX 8 // varargs count of fvar #define REG_R10 9 -#define REG_EBX 11 +#define REG_R11 10 +#define REG_EBX 11 // register var +#define REG_R12 12 +#define REG_R13 13 #define REG_R14 14 #define REG_R15 15 #define REG_XMM0 16 @@ -1231,6 +1235,9 @@ freg_var++; } int float_last = offset-SIZE_OF_LONGLONG; + + // ssetup va_list structure + // __my_va_list is defined as local in code_arg_register /* __builtin_va_list1 __my_va_list; long long_last; \n\ @@ -1238,15 +1245,7 @@ long float_last; \n\ long stack_top; \n\ */ - NMTBL *nptr =name_space_search(get_name("__builtin_va_list1",0,NONDEF),0); - if (!nptr) error(-1); - type = nptr->ty; - typedefed=glist3n(TYPEDEF,typedefed,nptr); - int smode = mode; - mode = LDECL; - stmode = 0; - NMTBL *n = def(lsearch("__my_va_list",0),0); - mode = smode; + NMTBL *n = lsearch("__my_va_list",0); // long_last g_expr_u(assign_expr0( list3n(LVAR,n->dsp,n),list2(ADDRESS,list3(LVAR,long_last,0)),LONGLONG,LONGLONG)); // float_last @@ -1259,7 +1258,7 @@ } void -code_arg_register(NMTBL *fnptr) +code_arg_register(NMTBL *fnptr, int in) { int args = fnptr->dsp; NMTBL *n; @@ -1270,8 +1269,28 @@ int is_code0 = is_code(fnptr); int dots; arg_offset_v = 0; - function_type(fnptr->ty,&dots); + + if (dots && (in || is_inline(fnptr))) { + + // special structure for variadic function + // this have to be defined before va_start + + // in parse mode, fnptr is not inline function, but we have to generated this. + + NMTBL *nptr =name_space_search(get_name("__builtin_va_list1",0,NONDEF),0); + if (!nptr) error(-1); + type = nptr->ty; + typedefed=glist3n(TYPEDEF,typedefed,nptr); + int smode = mode; + mode = LDECL; + stmode = 0; + def(lsearch("__my_va_list",0),0); + mode = smode; + // inline function is generated in pfdecl, we have to do code_arg_register also + } + if (in || !is_inline(fnptr)) return; + while (args) { // we should use increment_arg /* process in reverse order */ @@ -1568,33 +1587,33 @@ extern void code_i2c(int reg) { -// use_data_reg(reg,1); -// printf("\t%s %s,%s\n",cload(1,1), -// register_name(reg,1),register_name(reg,SIZE_OF_INT)); + use_data_reg(reg,1); + printf("\t%s %s,%s\n",cload(1,1), + register_name(reg,1),register_name(reg,0)); } extern void code_i2s(int reg) { -// use_data_reg(reg,1); -// printf("\t%s %s,%s\n",cload(1,SIZE_OF_SHORT), -// register_name(reg,2),register_name(reg,SIZE_OF_INT)); + use_data_reg(reg,1); + printf("\t%s %s,%s\n",cload(1,SIZE_OF_SHORT), + register_name(reg,2),register_name(reg,0)); } extern void code_u2uc(int reg) { -// use_data_reg(reg,1); -// printf("\t%s %s,%s\n",cload(0,1), -// register_name(reg,1),register_name(reg,SIZE_OF_INT)); + use_data_reg(reg,1); + printf("\t%s %s,%s\n",cload(0,1), + register_name(reg,1),register_name(reg,0)); } extern void code_u2us(int reg) { -// use_data_reg(reg,1); -// printf("\t%s %s,%s\n",cload(0,SIZE_OF_SHORT), -// register_name(reg,2),register_name(reg,SIZE_OF_INT)); + use_data_reg(reg,1); + printf("\t%s %s,%s\n",cload(0,SIZE_OF_SHORT), + register_name(reg,2),register_name(reg,0)); } void @@ -2222,7 +2241,7 @@ if (car(e2) == FNAME) { printf("\tcall\t_%s\n",fn->nm); } else { - printf("\tcall\t*%s\n",register_name(REG_EDX,0)); + printf("\tcall\t*%s\n",register_name(REG_R10,0)); } } @@ -2254,7 +2273,7 @@ fn=ncaddr(e2); } else { if (car(e2)==INDIRECT) e2=cadr(e2); // (*func)(i) case - jmp = list3(REGISTER,REG_EDX,0); + jmp = list3(REGISTER,REG_R10,0); if (!simple_arg(e2)) { e3=get_register_var(0);
--- a/mc-code-ia32.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-code-ia32.c Tue Nov 23 09:42:08 2010 +0900 @@ -980,7 +980,7 @@ } void -code_arg_register(NMTBL *fnptr) +code_arg_register(NMTBL *fnptr, int in) { int args = fnptr->dsp; NMTBL *n; @@ -991,6 +991,8 @@ int offset = 0; int is_code0 = is_code(fnptr); + if (in) return; + while (args) { /* process in reverse order */ n = ncadddr(args);
--- a/mc-code-mips.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-code-mips.c Tue Nov 23 09:42:08 2010 +0900 @@ -563,7 +563,7 @@ void -code_arg_register(NMTBL *fnptr) +code_arg_register(NMTBL *fnptr, int in) { int args = fnptr->dsp; NMTBL *n; @@ -574,6 +574,7 @@ int i; int is_code0 = is_code(fnptr); int dots; + if (in) return; function_type(fnptr->ty,&dots); while (args) {
--- a/mc-code-powerpc.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-code-powerpc.c Tue Nov 23 09:42:08 2010 +0900 @@ -779,7 +779,7 @@ */ void -code_arg_register(NMTBL *fnptr) +code_arg_register(NMTBL *fnptr, int in) { int args = fnptr->dsp; NMTBL *n; @@ -792,6 +792,8 @@ int dots; arg_offset_v = 0; + if (in) return; + function_type(fnptr->ty,&dots); while (args) { /* process in reverse order */
--- a/mc-code-spu.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-code-spu.c Tue Nov 23 09:42:08 2010 +0900 @@ -478,7 +478,7 @@ void -code_arg_register(NMTBL *fnptr) +code_arg_register(NMTBL *fnptr, int in) { int args = fnptr->dsp; NMTBL *n; @@ -489,6 +489,7 @@ int i; int is_code0 = is_code(fnptr); int dots; + if (in) return; function_type(fnptr->ty,&dots); while (args) {
--- a/mc-code.h Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-code.h Tue Nov 23 09:42:08 2010 +0900 @@ -286,7 +286,7 @@ extern void code_builtin_fabs(int e); extern void code_builtin_inff(); extern void code_builtin_inf(); -extern void code_arg_register(NMTBL *fnptr); +extern void code_arg_register(NMTBL *fnptr, int in); extern int get_register(); extern int get_dregister();
--- a/mc-codegen.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-codegen.c Tue Nov 23 09:42:08 2010 +0900 @@ -112,9 +112,9 @@ we should postpone code_save_argument_register */ extern void -arg_register(NMTBL *fnptr) +arg_register(NMTBL *fnptr, int in) { - code_arg_register(fnptr); + code_arg_register(fnptr, in); } extern int @@ -3396,7 +3396,7 @@ if (type0>0 && (car(type0)==STRUCT||car(type0)==UNION)) strtype=1; sz = size(type0); - if (lp64 && (sz%size_of_longlong==0)||strtype) { + if (lp64 && (sz%size_of_longlong==0)) { disp = align(disp,size_of_longlong); } else if ((sz%size_of_int==0)||strtype) { disp = align(disp,struct_align);
--- a/mc-codegen.h Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-codegen.h Tue Nov 23 09:42:08 2010 +0900 @@ -71,7 +71,7 @@ extern int rvalue_t(int e,int t); extern int search_struct_type(int type,char *name,int *dsp); extern int strop(int e,int ind); -extern void arg_register(NMTBL *fnptr); +extern void arg_register(NMTBL *fnptr, int in); extern int bexpr(int e1, char cond, int l1); extern void checkret(void); // check delayed jump, delayed last exp extern void closing();
--- a/mc-inline.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-inline.c Tue Nov 23 09:42:08 2010 +0900 @@ -700,8 +700,10 @@ if (t>0 && (car(t)==STRUCT||car(t)==UNION)) strtype=1; sz = size(t); - if (sz%size_of_int==0||strtype) { - offset = ((offset+(size_of_int-1))&~(size_of_int-1)); + if (lp64 && (sz%size_of_longlong==0||strtype)) { + offset = align(offset,size_of_longlong); + } else if (sz%size_of_int==0||strtype) { + offset = align(offset,size_of_int); } } #endif
--- a/mc-parse.c Mon Nov 22 14:31:47 2010 +0900 +++ b/mc-parse.c Tue Nov 23 09:42:08 2010 +0900 @@ -2053,7 +2053,7 @@ n->dsp = -n->dsp-caddr(t); } #endif - arg_register(fnptr); + arg_register(fnptr, inmode); } /* code sgement @@ -2201,8 +2201,7 @@ arg_disp = args; args = 0; disp=0; - if (!inmode) - arg_register(fnptr); + arg_register(fnptr,inmode); typedefed=0; conv->function_(fnptr,sd); conv->lc_(); @@ -2325,7 +2324,7 @@ tmp_struct = 0; disp=0; - arg_register(fnptr); // should fix n1->dsp + arg_register(fnptr,0); // should fix n1->dsp // make calling argments for(args=fnptr->dsp,cargs=0;args;args=cadr(args)) { @@ -2354,6 +2353,11 @@ control=0; } +/* + static inline function is not generated, but global inline fuction may + called directlry. so we have to generated this. this is also called from + parse mode. + */ extern void pcode_decl(NMTBL *n) { @@ -2397,7 +2401,7 @@ tmp_struct = 0; disp = -args; - arg_register(fnptr); // should fix n1->dsp + arg_register(fnptr, 0); // should fix n1->dsp // make calling argments for(arg=fnptr->dsp,cargs=0;arg;arg=cadr(arg)) { @@ -3812,12 +3816,16 @@ checksym(LPAR); mode = LDECL; // typespec required this if((t=typename())==0) { - error(TYERR); + mode = STAT; // too late for expression + expr(0); + t = type; } checksym(COMMA); mode = LDECL; // typespec required this if((t1=typename())==0) { - error(TYERR); + mode = STAT; // too late for expression + expr(0); + t1 = type; } set_lfree(slfree); type=stype; mode = smode;
--- a/test/tstdarg.c Mon Nov 22 14:31:47 2010 +0900 +++ b/test/tstdarg.c Tue Nov 23 09:42:08 2010 +0900 @@ -16,10 +16,22 @@ va_start(ap,numtypes); +printf("__my_va_list.long_last = %llx\n", __my_va_list.long_last); +printf("__my_va_list.float_first = %llx\n", __my_va_list.float_first); +printf("__my_va_list.float_last = %llx\n", __my_va_list.float_last); +printf("__my_va_list.stack_top = %llx\n", __my_va_list.stack_top); +printf("__my_va_list.arg = %llx\n", __my_va_list.arg); + while((t= *numtypes++)) { if (t=='i') { i = va_arg(ap,int); printf("#0021:int arg: %d\n",i); +printf("__my_va_list.long_last = %llx\n", __my_va_list.long_last); +printf("__my_va_list.float_first = %llx\n", __my_va_list.float_first); +printf("__my_va_list.float_last = %llx\n", __my_va_list.float_last); +printf("__my_va_list.stack_top = %llx\n", __my_va_list.stack_top); +printf("__my_va_list.arg = %llx\n", __my_va_list.arg); + #if 0 /* ‘float’ is promoted to ‘double’ when passed through ‘...’ */ } else if (t=='f') { f = va_arg(ap,float);