200x-xx-xx Kazu Hirata <kazu@codesourcery.com> Richard Sandiford <richard@codesourcery.com>

gcc/
200x-xx-xx  Kazu Hirata  <kazu@codesourcery.com>
	    Richard Sandiford  <richard@codesourcery.com>

	* doc/tm.texi (TARGET_FUNCTION_VALUE): Expand documentation of
	parallels.
	* calls.c (expand_call): If the return value is a PARALLEL,
	extract its first member.
	* config/m68k/linux.h (FUNCTION_EXTRA_EPILOGUE): Remove.
	* config/m68k/m68k.c (m68k_output_function_epilogue): Don't
	use FUNCTION_EXTRA_EPILOGUE.
	(m68k_function_value): Return a PARALLEL if the return value
	is of a pointer type.
	* config/m68k/netbsd-elf.h (current_function_returns_pointer)
	(FUNCTION_EXTRA_EPILOGUE): Remove.
	* config/m68k/m68k.md (D0_REG): New constant.

Co-Authored-By: Richard Sandiford <richard@codesourcery.com>

From-SVN: r120929
This commit is contained in:
Kazu Hirata 2007-01-18 19:54:44 +00:00 committed by Richard Sandiford
parent dfd050746b
commit 576c9028f0
7 changed files with 58 additions and 42 deletions

View File

@ -1,3 +1,19 @@
2007-01-18 Kazu Hirata <kazu@codesourcery.com>
Richard Sandiford <richard@codesourcery.com>
* doc/tm.texi (TARGET_FUNCTION_VALUE): Expand documentation of
parallels.
* calls.c (expand_call): If the return value is a PARALLEL,
extract its first member.
* config/m68k/linux.h (FUNCTION_EXTRA_EPILOGUE): Remove.
* config/m68k/m68k.c (m68k_output_function_epilogue): Don't
use FUNCTION_EXTRA_EPILOGUE.
(m68k_function_value): Return a PARALLEL if the return value
is of a pointer type.
* config/m68k/netbsd-elf.h (current_function_returns_pointer)
(FUNCTION_EXTRA_EPILOGUE): Remove.
* config/m68k/m68k.md (D0_REG): New constant.
2007-01-18 Kazu Hirata <kazu@codesourcery.com>
* config/m68k/m68k.c (m68k_output_function_epilogue): Don't

View File

@ -2566,6 +2566,19 @@ expand_call (tree exp, rtx target, int ignore)
else
valreg = hard_function_value (TREE_TYPE (exp), fndecl, fntype,
(pass == 0));
/* If VALREG is a PARALLEL whose first member has a zero
offset, use that. This is for targets such as m68k that
return the same value in multiple places. */
if (GET_CODE (valreg) == PARALLEL)
{
rtx elem = XVECEXP (valreg, 0, 0);
rtx where = XEXP (elem, 0);
rtx offset = XEXP (elem, 1);
if (offset == const0_rtx
&& GET_MODE (where) == GET_MODE (valreg))
valreg = where;
}
}
/* Precompute all register parameters. It isn't safe to compute anything

View File

@ -179,20 +179,6 @@ Boston, MA 02110-1301, USA. */
#define FUNCTION_VALUE(VALTYPE, FUNC) \
m68k_function_value (VALTYPE, FUNC)
/* For compatibility with the large body of existing code which does
not always properly declare external functions returning pointer
types, the m68k/SVR4 convention is to copy the value returned for
pointer functions from a0 to d0 in the function epilogue, so that
callers that have neglected to properly declare the callee can
still find the correct return value. */
#define FUNCTION_EXTRA_EPILOGUE(FILE, SIZE) \
do { \
if (current_function_returns_pointer \
&& ! find_equiv_reg (0, get_last_insn (), 0, 0, 0, 8, Pmode)) \
asm_fprintf (FILE, "\tmove.l %Ra0,%Rd0\n"); \
} while (0);
/* Define how to find the value returned by a library function
assuming the value has mode MODE.
For m68k/SVR4 look for integer values in d0, pointer values in d0

View File

@ -1057,10 +1057,6 @@ m68k_output_function_epilogue (FILE *stream,
if (insn && GET_CODE (insn) == BARRIER)
return;
#ifdef FUNCTION_EXTRA_EPILOGUE
FUNCTION_EXTRA_EPILOGUE (stream, size);
#endif
fsize = current_frame.size;
/* FIXME: leaf_function_p below is too strong.
@ -3894,9 +3890,26 @@ m68k_function_value (tree valtype, tree func ATTRIBUTE_UNUSED)
break;
}
/* If the function returns a pointer, push that into %a0 */
if (POINTER_TYPE_P (valtype))
return gen_rtx_REG (mode, 8);
/* If the function returns a pointer, push that into %a0. */
if (func && POINTER_TYPE_P (TREE_TYPE (TREE_TYPE (func))))
/* For compatibility with the large body of existing code which
does not always properly declare external functions returning
pointer types, the m68k/SVR4 convention is to copy the value
returned for pointer functions from a0 to d0 in the function
epilogue, so that callers that have neglected to properly
declare the callee can still find the correct return value in
d0. */
return gen_rtx_PARALLEL
(mode,
gen_rtvec (2,
gen_rtx_EXPR_LIST (VOIDmode,
gen_rtx_REG (mode, A0_REG),
const0_rtx),
gen_rtx_EXPR_LIST (VOIDmode,
gen_rtx_REG (mode, D0_REG),
const0_rtx)));
else if (POINTER_TYPE_P (valtype))
return gen_rtx_REG (mode, A0_REG);
else
return gen_rtx_REG (mode, 0);
return gen_rtx_REG (mode, D0_REG);
}

View File

@ -124,7 +124,8 @@
;; Registers by name.
(define_constants
[(A0_REG 8)
[(D0_REG 0)
(A0_REG 8)
(SP_REG 15)
])

View File

@ -273,24 +273,6 @@ while (0)
m68k_function_value (VALTYPE, FUNC)
/* For compatibility with the large body of existing code which does
not always properly declare external functions returning pointer
types, the m68k/SVR4 convention is to copy the value returned for
pointer functions from a0 to d0 in the function epilogue, so that
callers that have neglected to properly declare the callee can
still find the correct return value. */
extern int current_function_returns_pointer;
#define FUNCTION_EXTRA_EPILOGUE(FILE, SIZE) \
do \
{ \
if (current_function_returns_pointer \
&& ! find_equiv_reg (0, get_last_insn (), 0, 0, 0, 8, Pmode)) \
asm_fprintf (FILE, "\tmove.l %Ra0,%Rd0\n"); \
} \
while (0)
/* Define how to find the value returned by a library function
assuming the value has mode MODE.
For m68k/SVR4 look for integer values in d0, pointer values in d0

View File

@ -4107,7 +4107,12 @@ place regardless of mode.) The value of the expression is usually a
@code{reg} RTX for the hard register where the return value is stored.
The value can also be a @code{parallel} RTX, if the return value is in
multiple places. See @code{FUNCTION_ARG} for an explanation of the
@code{parallel} form.
@code{parallel} form. Note that the callee will populate every
location specified in the @code{parallel}, but if the first element of
the @code{parallel} contains the whole return value, callers will use
that element as the canonical location and ignore the others. The m68k
port uses this type of @code{parallel} to return pointers in both
@samp{%a0} (the canonical location) and @samp{%d0}.
If @code{TARGET_PROMOTE_FUNCTION_RETURN} returns true, you must apply
the same promotion rules specified in @code{PROMOTE_MODE} if