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>

	* config/m68k/m68k-protos.h (m68k_interrupt_function_p): Declare.
	(m68k_movem_pattern_p, m68k_output_movem): Likewise.
	(m68k_expand_prologue, m68k_expand_epilogue): Likewise.
	* config/m68k/m68k.h (EPILOGUE_USES): Define.  Treat all registers
	as being live on exit from an interrupt function.
	(PRINT_OPERAND_PUNCT_VALID_P): Return true for '?'.
	* config/m68k/m68k.c (MIN_MOVEM_REGS, MIN_FMOVEM_REGS): New macros.
	(m68k_frame): Remove reg_rev_mask and fpu_rev_mask.
	(TARGET_ASM_FUNCTION_PROLOGUE, TARGET_ASM_FUNCTION_EPILOGUE): Delete.
	(m68k_interrupt_function_p): Globalize.
	(m68k_compute_frame_layout): Remove reverse mask code.
	(m68k_emit_movem, m68k_set_frame_related): New functions.
	(m68k_output_function_prologue): Delete in favor of...
	(m68k_expand_prologue): ...this new function.
	(m68k_output_function_epilogue): Delete in favor of...
	(m68k_expand_epilogue): ...this new function.
	(m68k_split_offset, m68k_movem_pattern_p, m68k_output_movem): New
	functions.
	(print_operand): Handle %?.
	* config/m68k/m68k.md (UNSPEC_SIN, UNSPEC_COS): Remove excess space.
	(UNSPEC_GOT, A1_REG, PIC_REG, FP0_REG): New constants.
	(prologue, epilogue): New patterns.
	(return): Turn into a define_expand.
	(*return): New pattern, derived from old "return" pattern.  Use rte
	rather than rts for interrupt functions.  Only use rtd if the pop
	count is nonzero.
	(*m68k_store_multiple, *m68k_store_multiple_automod): New patterns.
	(*m68k_load_multiple, *m68k_load_multiple_automod): Likewise.
	(link, *link, unlink, *unlink, load_got): Likewise.

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

From-SVN: r122605
This commit is contained in:
Kazu Hirata 2007-03-06 08:58:40 +00:00 committed by Richard Sandiford
parent fc2241eb94
commit a40ed0f310
5 changed files with 678 additions and 455 deletions

View File

@ -1,3 +1,36 @@
2007-03-06 Kazu Hirata <kazu@codesourcery.com>
Richard Sandiford <richard@codesourcery.com>
* config/m68k/m68k-protos.h (m68k_interrupt_function_p): Declare.
(m68k_movem_pattern_p, m68k_output_movem): Likewise.
(m68k_expand_prologue, m68k_expand_epilogue): Likewise.
* config/m68k/m68k.h (EPILOGUE_USES): Define. Treat all registers
as being live on exit from an interrupt function.
(PRINT_OPERAND_PUNCT_VALID_P): Return true for '?'.
* config/m68k/m68k.c (MIN_MOVEM_REGS, MIN_FMOVEM_REGS): New macros.
(m68k_frame): Remove reg_rev_mask and fpu_rev_mask.
(TARGET_ASM_FUNCTION_PROLOGUE, TARGET_ASM_FUNCTION_EPILOGUE): Delete.
(m68k_interrupt_function_p): Globalize.
(m68k_compute_frame_layout): Remove reverse mask code.
(m68k_emit_movem, m68k_set_frame_related): New functions.
(m68k_output_function_prologue): Delete in favor of...
(m68k_expand_prologue): ...this new function.
(m68k_output_function_epilogue): Delete in favor of...
(m68k_expand_epilogue): ...this new function.
(m68k_split_offset, m68k_movem_pattern_p, m68k_output_movem): New
functions.
(print_operand): Handle %?.
* config/m68k/m68k.md (UNSPEC_SIN, UNSPEC_COS): Remove excess space.
(UNSPEC_GOT, A1_REG, PIC_REG, FP0_REG): New constants.
(prologue, epilogue): New patterns.
(return): Turn into a define_expand.
(*return): New pattern, derived from old "return" pattern. Use rte
rather than rts for interrupt functions. Only use rtd if the pop
count is nonzero.
(*m68k_store_multiple, *m68k_store_multiple_automod): New patterns.
(*m68k_load_multiple, *m68k_load_multiple_automod): Likewise.
(link, *link, unlink, *unlink, load_got): Likewise.
2007-03-06 Richard Sandiford <richard@codesourcery.com>
PR target/23482

View File

@ -21,6 +21,7 @@ Boston, MA 02110-1301, USA. */
/* Define functions defined in aux-output.c and used in templates. */
#ifdef RTX_CODE
extern bool m68k_interrupt_function_p (tree);
extern HOST_WIDE_INT m68k_initial_elimination_offset (int from, int to);
extern void split_di (rtx[], int, rtx[], rtx[]);
@ -61,12 +62,16 @@ extern int valid_dbcc_comparison_p_2 (rtx, enum machine_mode);
extern rtx m68k_libcall_value (enum machine_mode);
extern rtx m68k_function_value (tree, tree);
extern int emit_move_sequence (rtx *, enum machine_mode, rtx);
extern bool m68k_movem_pattern_p (rtx, rtx, HOST_WIDE_INT, bool);
extern const char *m68k_output_movem (rtx *, rtx, HOST_WIDE_INT, bool);
#endif /* RTX_CODE */
extern bool m68k_regno_mode_ok (int, enum machine_mode);
extern int flags_in_68881 (void);
extern void m68k_expand_prologue (void);
extern bool m68k_use_return_insn (void);
extern void m68k_expand_epilogue (void);
extern void override_options (void);
extern const char *m68k_cpp_cpu_ident (const char *);
extern const char *m68k_cpp_cpu_family (const char *);

File diff suppressed because it is too large Load Diff

View File

@ -987,6 +987,10 @@ do { if (cc_prev_status.flags & CC_IN_68881) \
/* Before the prologue, the top of the frame is at 4(%sp). */
#define INCOMING_FRAME_SP_OFFSET 4
/* All registers are live on exit from an interrupt routine. */
#define EPILOGUE_USES(REGNO) \
(reload_completed && m68k_interrupt_function_p (current_function_decl))
/* Describe how we implement __builtin_eh_return. */
#define EH_RETURN_DATA_REGNO(N) \
((N) < 2 ? (N) : INVALID_REGNUM)
@ -1123,6 +1127,7 @@ do { if (cc_prev_status.flags & CC_IN_68881) \
'$' for the letter `s' in an op code, but only on the 68040.
'&' for the letter `d' in an op code, but only on the 68040.
'/' for register prefix needed by longlong.h.
'?' for m68k_library_id_string
'b' for byte insn (no effect, on the Sun; this is for the ISI).
'd' to force memory addressing to be absolute, not relative.
@ -1133,7 +1138,7 @@ do { if (cc_prev_status.flags & CC_IN_68881) \
#define PRINT_OPERAND_PUNCT_VALID_P(CODE) \
((CODE) == '.' || (CODE) == '#' || (CODE) == '-' \
|| (CODE) == '+' || (CODE) == '@' || (CODE) == '!' \
|| (CODE) == '$' || (CODE) == '&' || (CODE) == '/')
|| (CODE) == '$' || (CODE) == '&' || (CODE) == '/' || (CODE) == '?')
/* See m68k.c for the m68k specific codes. */

View File

@ -112,8 +112,9 @@
;; UNSPEC usage:
(define_constants
[(UNSPEC_SIN 1)
(UNSPEC_COS 2)
[(UNSPEC_SIN 1)
(UNSPEC_COS 2)
(UNSPEC_GOT 3)
])
;; UNSPEC_VOLATILE usage:
@ -126,7 +127,10 @@
(define_constants
[(D0_REG 0)
(A0_REG 8)
(A1_REG 9)
(PIC_REG 13)
(SP_REG 15)
(FP0_REG 16)
])
(include "predicates.md")
@ -6756,15 +6760,158 @@
""
"nop")
(define_expand "prologue"
[(const_int 0)]
""
{
m68k_expand_prologue ();
DONE;
})
(define_expand "epilogue"
[(return)]
""
{
m68k_expand_epilogue ();
DONE;
})
;; Used for frameless functions which save no regs and allocate no locals.
(define_insn "return"
(define_expand "return"
[(return)]
"m68k_use_return_insn ()"
"")
(define_insn "*return"
[(return)]
""
{
if (current_function_pops_args == 0)
if (m68k_interrupt_function_p (current_function_decl))
return "rte";
else if (current_function_pops_args)
{
operands[0] = GEN_INT (current_function_pops_args);
return "rtd %0";
}
else
return "rts";
operands[0] = GEN_INT (current_function_pops_args);
return "rtd %0";
})
(define_insn "*m68k_store_multiple"
[(match_parallel 0 "" [(match_operand 1 "")])]
"m68k_movem_pattern_p (operands[0], NULL, 0, true)"
{
return m68k_output_movem (operands, operands[0], 0, true);
})
(define_insn "*m68k_store_multiple_automod"
[(match_parallel 0 ""
[(set (match_operand:SI 1 "register_operand" "=a")
(plus:SI (match_operand:SI 2 "register_operand" "1")
(match_operand:SI 3 "const_int_operand")))])]
"m68k_movem_pattern_p (operands[0], operands[1], INTVAL (operands[3]), true)"
{
return m68k_output_movem (operands, operands[0], INTVAL (operands[3]), true);
})
(define_insn "*m68k_load_multiple"
[(match_parallel 0 "" [(match_operand 1 "")])]
"m68k_movem_pattern_p (operands[0], NULL, 0, false)"
{
return m68k_output_movem (operands, operands[0], 0, false);
})
(define_insn "*m68k_load_multiple_automod"
[(match_parallel 0 ""
[(set (match_operand:SI 1 "register_operand" "=a")
(plus:SI (match_operand:SI 2 "register_operand" "1")
(match_operand:SI 3 "const_int_operand")))])]
"m68k_movem_pattern_p (operands[0], operands[1],
INTVAL (operands[3]), false)"
{
return m68k_output_movem (operands, operands[0],
INTVAL (operands[3]), false);
})
(define_expand "link"
[(parallel
[(set (match_operand:SI 0 "register_operand")
(plus:SI (reg:SI SP_REG) (const_int -4)))
(set (match_dup 2)
(match_dup 0))
(set (reg:SI SP_REG)
(plus:SI (reg:SI SP_REG)
(match_operand:SI 1 "const_int_operand")))])]
"TARGET_68020 || INTVAL (operands[1]) >= -0x8004"
{
operands[2] = gen_frame_mem (SImode, plus_constant (stack_pointer_rtx, -4));
})
(define_insn "*link"
[(set (match_operand:SI 0 "register_operand" "+r")
(plus:SI (reg:SI SP_REG) (const_int -4)))
(set (mem:SI (plus:SI (reg:SI SP_REG) (const_int -4)))
(match_dup 0))
(set (reg:SI SP_REG)
(plus:SI (reg:SI SP_REG)
(match_operand:SI 1 "const_int_operand")))]
"TARGET_68020 || INTVAL (operands[1]) >= -0x8004"
{
operands[1] = GEN_INT (INTVAL (operands[1]) + 4);
if (!MOTOROLA)
return "link %0,%1";
else if (INTVAL (operands[1]) >= -0x8000)
return "link.w %0,%1";
else
return "link.l %0,%1";
})
(define_expand "unlink"
[(parallel
[(set (match_operand:SI 0 "register_operand")
(match_dup 1))
(set (reg:SI SP_REG)
(plus:SI (match_dup 0)
(const_int 4)))])]
""
{
operands[1] = gen_frame_mem (SImode, copy_rtx (operands[0]));
})
(define_insn "*unlink"
[(set (match_operand:SI 0 "register_operand" "+r")
(mem:SI (match_dup 0)))
(set (reg:SI SP_REG)
(plus:SI (match_dup 0)
(const_int 4)))]
""
"unlk %0")
(define_insn "load_got"
[(set (match_operand:SI 0 "register_operand" "=a")
(unspec:SI [(const_int 0)] UNSPEC_GOT))]
""
{
if (TARGET_ID_SHARED_LIBRARY)
{
operands[1] = gen_rtx_REG (Pmode, PIC_REG);
return MOTOROLA ? "move.l %?(%1),%0" : "movel %1@(%?), %0";
}
else if (MOTOROLA)
{
if (TARGET_COLDFIRE)
/* Load the full 32-bit PC-relative offset of
_GLOBAL_OFFSET_TABLE_ into the PIC register, then use it to
calculate the absolute value. The offset and "lea"
operation word together occupy 6 bytes. */
return ("move.l #_GLOBAL_OFFSET_TABLE_@GOTPC, %0\n\t"
"lea (-6, %%pc, %0), %0");
else
return "lea (%%pc, _GLOBAL_OFFSET_TABLE_@GOTPC), %0";
}
else
return ("movel #_GLOBAL_OFFSET_TABLE_, %0\n\t"
"lea %%pc@(0,%0:l),%0");
})
(define_insn "indirect_jump"