gimple va_arg for mips
Richard Sandiford
rsandifo@redhat.com
Fri Jul 9 08:18:00 GMT 2004
Richard Henderson <rth@redhat.com> writes:
> Ouch. So, like, the mips maintainers have a choice to make.
>
> Patch 1 changes the ABI for !EABI such that variable sized types are
> passed by reference. With this, we're able to pass them through varargs.
>
> The patch that was supposed to make that work,
>
> 2003-09-25 Richard Sandiford <rsandifo@redhat.com>
>
> PR target/6222
> * config/mips/mips.c (mips_va_arg): Handle arguments that must be
> passed on the stack.
>
> only works when va_arg is called from the same function that performed
> the va_start. I'm not certain that I can replicate this hackery at the
> tree level, or if it's even desirable.
I guess I'm OK with changing the ABI. We'll probably have to do
that anyway, what with the complex arg-passing problems. ;(
But does the above mean that MUST_PASS_IN_STACK now implies
"must be passed by reference", at least in some circumstances?
E.g., the following quote seems to suggest that pass-by-value
can still be used:
-------------------------------------------------------------------
... If @code{REG_PARM_STACK_SPACE}
is not defined and @code{FUNCTION_ARG} returns nonzero for such an
argument, the compiler will abort. If @code{REG_PARM_STACK_SPACE} is
defined, the argument will be computed in the stack and then loaded into
a register.
-------------------------------------------------------------------
> In addition, there appears to have been an alignment and padding problem
> with the old code. It didn't follow the same padding as the caller side.
> See PAD_VARARGS_DOWN.
Sorry to be clueless, but I don't see what you mean. Is the mips
definition of PAD_VARARGS_DOWN wrong? Or do you mean that the old
code wasn't honouring it?
The !EABI case used std_expand_builtin_va_arg while the EABI code
handles the padding itself.
FWIW, I've done a lot of testing on 3.4-era tools, all ABIs, both big
and little endian. I haven't come across any varargs failures in the
testsuite. Not that I'm saying that makes the code right. Just a
datapoint...
I'll try to test patch 1 soon. I suspect it'll need the following
as well.
Richard
Index: config/mips/mips.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mips/mips.c,v
retrieving revision 1.426
diff -c -p -F^\([(a-zA-Z0-9_]\|#define\) -r1.426 mips.c
*** config/mips/mips.c 7 Jul 2004 19:24:28 -0000 1.426
--- config/mips/mips.c 9 Jul 2004 07:00:38 -0000
*************** mips_arg_info (const CUMULATIVE_ARGS *cu
*** 3611,3632 ****
even_reg_p = true;
}
! if (mips_abi != ABI_EABI && MUST_PASS_IN_STACK (mode, type))
! /* This argument must be passed on the stack. Eat up all the
! remaining registers. */
! info->reg_offset = MAX_ARGS_IN_REGISTERS;
! else
! {
! /* Set REG_OFFSET to the register count we're interested in.
! The EABI allocates the floating-point registers separately,
! but the other ABIs allocate them like integer registers. */
! info->reg_offset = (mips_abi == ABI_EABI && info->fpr_p
! ? cum->num_fprs
! : cum->num_gprs);
! if (even_reg_p)
! info->reg_offset += info->reg_offset & 1;
! }
/* The alignment applied to registers is also applied to stack arguments. */
info->stack_offset = cum->stack_words;
--- 3619,3633 ----
even_reg_p = true;
}
! /* Set REG_OFFSET to the register count we're interested in.
! The EABI allocates the floating-point registers separately,
! but the other ABIs allocate them like integer registers. */
! info->reg_offset = (mips_abi == ABI_EABI && info->fpr_p
! ? cum->num_fprs
! : cum->num_gprs);
! if (even_reg_p)
! info->reg_offset += info->reg_offset & 1;
/* The alignment applied to registers is also applied to stack arguments. */
info->stack_offset = cum->stack_words;
More information about the Gcc-patches
mailing list