/* * Beginning-of-function code: * * 'sp' is an array of indices in symtab for the arguments * 'cnt' is the number of arguments */ void bfcode(struct symtab **sp, int cnt) { union arglist *usym; int saveallargs = 0; int i, argofs = 0; /* * Detect if this function has ellipses and save all * argument registers onto stack. */ usym = cftnsp->sdf->dfun; while (usym && usym->type != TNULL) { if (usym->type == TELLIPSIS) { saveallargs = 1; break; } ++usym; } /* if returning a structure, move the hidden argument into a TEMP */ if (cftnsp->stype == STRTY+FTN || cftnsp->stype == UNIONTY+FTN) { param_retstruct(); ++argofs; } /* recalculate the arg offset and create TEMP moves */ for (i = 0; i < cnt; i++) { if (sp[i] == NULL) continue; if ((argofs >= NARGREGS) && !xtemps) break; if (argofs > NARGREGS) { putintemp(sp[i]); } else if (sp[i]->stype == STRTY || sp[i]->stype == UNIONTY) { param_struct(sp[i], &argofs); } else if (DEUNSIGN(sp[i]->stype) == LONGLONG) { param_64bit(sp[i], &argofs, xtemps && !saveallargs); } else if (sp[i]->stype == DOUBLE || sp[i]->stype == LDOUBLE) { if (features(FEATURE_HARDFLOAT)) param_double(sp[i], &argofs, xtemps && !saveallargs); else param_64bit(sp[i], &argofs, xtemps && !saveallargs); } else if (sp[i]->stype == FLOAT) { if (features(FEATURE_HARDFLOAT)) param_float(sp[i], &argofs, xtemps && !saveallargs); else param_32bit(sp[i], &argofs, xtemps && !saveallargs); } else { param_32bit(sp[i], &argofs, xtemps && !saveallargs); } } /* if saveallargs, save the rest of the args onto the stack */ while (saveallargs && argofs < NARGREGS) { NODE *p, *q; int off = ARGINIT/SZINT + argofs; q = block(REG, NIL, NIL, INT, 0, 0); regno(q) = R0 + argofs++; p = block(REG, NIL, NIL, INT, 0, 0); regno(p) = FPREG; p = block(PLUS, p, bcon(4*off), INT, 0, 0); p = block(UMUL, p, NIL, INT, 0, 0); p = buildtree(ASSIGN, p, q); ecomp(p); } }
/* * code for the beginning of a function; a is an array of * indices in symtab for the arguments; n is the number */ void bfcode(struct symtab **sp, int cnt) { union arglist *usym; int lastreg = A0 + nargregs - 1; int saveallargs = 0; int i, reg; /* * Detect if this function has ellipses and save all * argument register onto stack. */ usym = cftnsp->sdf->dfun; while (usym && usym->type != TNULL) { if (usym->type == TELLIPSIS) { saveallargs = 1; break; } ++usym; } reg = A0; /* assign hidden return structure to temporary */ if (cftnsp->stype == STRTY+FTN || cftnsp->stype == UNIONTY+FTN) { param_retptr(); ++reg; } /* recalculate the arg offset and create TEMP moves */ for (i = 0; i < cnt; i++) { if ((reg > lastreg) && !xtemps) break; else if (reg > lastreg) putintemp(sp[i]); else if (sp[i]->stype == STRTY || sp[i]->stype == UNIONTY) param_struct(sp[i], ®); else if (DEUNSIGN(sp[i]->stype) == LONGLONG) param_64bit(sp[i], ®, xtemps && !saveallargs); else if (sp[i]->stype == DOUBLE || sp[i]->stype == LDOUBLE) param_double(sp[i], ®, xtemps && !saveallargs); else if (sp[i]->stype == FLOAT) param_float(sp[i], ®, xtemps && !saveallargs); else param_32bit(sp[i], ®, xtemps && !saveallargs); } /* if saveallargs, save the rest of the args onto the stack */ if (!saveallargs) return; while (reg <= lastreg) { NODE *p, *q; int off = ARGINIT/SZINT + (reg - A0); q = block(REG, NIL, NIL, INT, 0, 0); q->n_rval = reg++; p = block(REG, NIL, NIL, INT, 0, 0); p->n_rval = FP; p = block(PLUS, p, bcon(4*off), INT, 0, 0); p = block(UMUL, p, NIL, INT, 0, 0); p = buildtree(ASSIGN, p, q); ecomp(p); } }