This is the mail archive of the
gdb-patches@sourceware.org
mailing list for the GDB project.
Re: mips-tdep.c: Fix new-ABI handling of composite return values
- From: "Maciej W. Rozycki" <macro at mips dot com>
- To: Daniel Jacobowitz <drow at false dot org>
- Cc: gdb-patches at sourceware dot org, David Ung <davidu at mips dot com>, "Maciej W. Rozycki" <macro at linux-mips dot org>
- Date: Tue, 25 Sep 2007 16:48:06 +0100 (BST)
- Subject: Re: mips-tdep.c: Fix new-ABI handling of composite return values
- References: <Pine.LNX.4.61.0709251522080.6904@perivale.mips.com> <20070925151022.GA8482@caradoc.them.org>
On Tue, 25 Sep 2007, Daniel Jacobowitz wrote:
> 128-bit long double is also handled in this patch - that's not a
> composite type. I think that's a merge error, though. If you look
> above the float / double block you'll find another copy of
> 128-bit long double support in HEAD.
Oops! -- I have missed this bit indeed.
> > else if (TYPE_CODE (type) == TYPE_CODE_STRUCT
> > && TYPE_NFIELDS (type) <= 2
> > && TYPE_NFIELDS (type) >= 1
> > && ((TYPE_NFIELDS (type) == 1
> > - && (TYPE_CODE (TYPE_FIELD_TYPE (type, 0))
> > + && (TYPE_CODE (check_typedef (TYPE_FIELD_TYPE (type, 0)))
>
> Funny indentation. Is the only substantive change in this patch the
Fixed.
> new calls to check_typedef?
Of course not. This bit matters much too:
- if (TYPE_CODE (type) == TYPE_CODE_STRUCT
- || TYPE_CODE (type) == TYPE_CODE_UNION
- || TYPE_CODE (type) == TYPE_CODE_ARRAY
+ if (TYPE_CODE (type) == TYPE_CODE_ARRAY
Here's an updated version.
2007-09-25 David Ung <davidu@mips.com>
Maciej W. Rozycki <macro@mips.com>
* mips-tdep.c (mips_n32n64_return_value): Per N32/N64 ABI
rules return composite types in registers as appropriate.
OK to apply?
Maciej
12438.diff
Index: binutils-quilt/src/gdb/mips-tdep.c
===================================================================
--- binutils-quilt.orig/src/gdb/mips-tdep.c 2007-09-25 16:42:08.000000000 +0100
+++ binutils-quilt/src/gdb/mips-tdep.c 2007-09-25 16:43:43.000000000 +0100
@@ -3076,9 +3076,30 @@
gdb_byte *readbuf, const gdb_byte *writebuf)
{
struct gdbarch_tdep *tdep = gdbarch_tdep (current_gdbarch);
- if (TYPE_CODE (type) == TYPE_CODE_STRUCT
- || TYPE_CODE (type) == TYPE_CODE_UNION
- || TYPE_CODE (type) == TYPE_CODE_ARRAY
+
+ /* From MIPSpro N32 ABI Handbook, Document Number: 007-2816-004
+
+ Function results are returned in $2 (and $3 if needed), or $f0 (and $f2
+ if needed), as appropriate for the type. Composite results (struct,
+ union, or array) are returned in $2/$f0 and $3/$f2 according to the
+ following rules:
+
+ * A struct with only one or two floating point fields is returned in $f0
+ (and $f2 if necessary). This is a generalization of the Fortran COMPLEX
+ case.
+
+ * Any other struct or union results of at most 128 bits are returned in
+ $2 (first 64 bits) and $3 (remainder, if necessary).
+
+ * Larger composite results are handled by converting the function to a
+ procedure with an implicit first parameter, which is a pointer to an area
+ reserved by the caller to receive the result. [The o32-bit ABI requires
+ that all composite results be handled by conversion to implicit first
+ parameters. The MIPS/SGI Fortran implementation has always made a
+ specific exception to return COMPLEX results in the floating point
+ registers.] */
+
+ if (TYPE_CODE (type) == TYPE_CODE_ARRAY
|| TYPE_LENGTH (type) > 2 * MIPS64_REGSIZE)
return RETURN_VALUE_STRUCT_CONVENTION;
else if (TYPE_CODE (type) == TYPE_CODE_FLT
@@ -3122,12 +3143,12 @@
&& TYPE_NFIELDS (type) <= 2
&& TYPE_NFIELDS (type) >= 1
&& ((TYPE_NFIELDS (type) == 1
- && (TYPE_CODE (TYPE_FIELD_TYPE (type, 0))
+ && (TYPE_CODE (check_typedef (TYPE_FIELD_TYPE (type, 0)))
== TYPE_CODE_FLT))
|| (TYPE_NFIELDS (type) == 2
- && (TYPE_CODE (TYPE_FIELD_TYPE (type, 0))
+ && (TYPE_CODE (check_typedef (TYPE_FIELD_TYPE (type, 0)))
== TYPE_CODE_FLT)
- && (TYPE_CODE (TYPE_FIELD_TYPE (type, 1))
+ && (TYPE_CODE (check_typedef (TYPE_FIELD_TYPE (type, 1)))
== TYPE_CODE_FLT)))
&& tdep->mips_fpu_type != MIPS_FPU_NONE)
{