Commit bf95e88b by John David Anglin

invoke.texi: Update documentation of hppa -mjump-in-delay option.

	* doc/invoke.texi: Update documentation of hppa -mjump-in-delay option.
	* config/pa/pa-protos.h (pa_following_call): Delete declaration.
	(pa_jump_in_call_delay): Likewise.
	* config/pa/pa.c (pa_option_override): Remove jump in call delay
	override.
	(pa_output_millicode_call): Remove support for jump in call delay.
	(pa_output_call): Likewise.
	(pa_jump_in_call_delay): Delete.
	(pa_following_call): Likewise.
	* config/pa/pa.md (in_call_delay): Remove jump in delay check.
	(uncond_branch): Remove following call check from attribute length.

From-SVN: r216428
parent 22c23886
2014-10-18 John David Anglin <danglin@gcc.gnu.org>
* doc/invoke.texi: Update documentation of hppa -mjump-in-delay option.
* config/pa/pa-protos.h (pa_following_call): Delete declaration.
(pa_jump_in_call_delay): Likewise.
* config/pa/pa.c (pa_option_override): Remove jump in call delay
override.
(pa_output_millicode_call): Remove support for jump in call delay.
(pa_output_call): Likewise.
(pa_jump_in_call_delay): Delete.
(pa_following_call): Likewise.
* config/pa/pa.md (in_call_delay): Remove jump in delay check.
(uncond_branch): Remove following call check from attribute length.
2014-10-18 Oleg Endo <olegendo@gcc.gnu.org>
PR target/53513
......@@ -21,9 +21,6 @@ along with GCC; see the file COPYING3. If not see
/* Prototype function used in various macros. */
extern rtx pa_eh_return_handler_rtx (void);
/* Used in insn-*.c. */
extern int pa_following_call (rtx_insn *);
/* Define functions in pa.c and used in insn-output.c. */
extern const char *pa_output_and (rtx *);
......@@ -63,7 +60,6 @@ extern void pa_emit_bcond_fp (rtx[]);
extern int pa_emit_move_sequence (rtx *, enum machine_mode, rtx);
extern int pa_emit_hpdiv_const (rtx *, int);
extern int pa_is_function_label_plus_const (rtx);
extern int pa_jump_in_call_delay (rtx_insn *);
extern int pa_fpstore_bypass_p (rtx_insn *, rtx_insn *);
extern int pa_attr_length_millicode_call (rtx_insn *);
extern int pa_attr_length_call (rtx_insn *, int);
......
......@@ -498,15 +498,6 @@ pa_option_override (void)
}
}
/* Unconditional branches in the delay slot are not compatible with dwarf2
call frame information. There is no benefit in using this optimization
on PA8000 and later processors. */
if (pa_cpu >= PROCESSOR_8000
|| (targetm_common.except_unwind_info (&global_options) == UI_DWARF2
&& flag_exceptions)
|| flag_unwind_tables)
target_flags &= ~MASK_JUMP_IN_DELAY;
if (flag_pic && TARGET_PORTABLE_RUNTIME)
{
warning (0, "PIC code generation is not supported in the portable runtime model");
......@@ -7542,8 +7533,7 @@ pa_attr_length_millicode_call (rtx_insn *insn)
}
}
/* INSN is a function call. It may have an unconditional jump
in its delay slot.
/* INSN is a function call.
CALL_DEST is the routine we are calling. */
......@@ -7552,8 +7542,6 @@ pa_output_millicode_call (rtx_insn *insn, rtx call_dest)
{
int attr_length = get_attr_length (insn);
int seq_length = dbr_sequence_length ();
int distance;
rtx seq_insn;
rtx xoperands[3];
xoperands[0] = call_dest;
......@@ -7655,39 +7643,6 @@ pa_output_millicode_call (rtx_insn *insn, rtx call_dest)
if (seq_length == 0)
output_asm_insn ("nop", xoperands);
/* We are done if there isn't a jump in the delay slot. */
if (seq_length == 0 || ! JUMP_P (NEXT_INSN (insn)))
return "";
/* This call has an unconditional jump in its delay slot. */
xoperands[0] = XEXP (PATTERN (NEXT_INSN (insn)), 1);
/* See if the return address can be adjusted. Use the containing
sequence insn's address. */
if (INSN_ADDRESSES_SET_P ())
{
seq_insn = NEXT_INSN (PREV_INSN (final_sequence->insn (0)));
distance = (INSN_ADDRESSES (INSN_UID (JUMP_LABEL (NEXT_INSN (insn))))
- INSN_ADDRESSES (INSN_UID (seq_insn)) - 8);
if (VAL_14_BITS_P (distance))
{
xoperands[1] = gen_label_rtx ();
output_asm_insn ("ldo %0-%1(%2),%2", xoperands);
targetm.asm_out.internal_label (asm_out_file, "L",
CODE_LABEL_NUMBER (xoperands[1]));
}
else
/* ??? This branch may not reach its target. */
output_asm_insn ("nop\n\tb,n %0", xoperands);
}
else
/* ??? This branch may not reach its target. */
output_asm_insn ("nop\n\tb,n %0", xoperands);
/* Delete the jump. */
SET_INSN_DELETED (NEXT_INSN (insn));
return "";
}
......@@ -7789,16 +7744,13 @@ pa_attr_length_call (rtx_insn *insn, int sibcall)
return length;
}
/* INSN is a function call. It may have an unconditional jump
in its delay slot.
/* INSN is a function call.
CALL_DEST is the routine we are calling. */
const char *
pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
{
int delay_insn_deleted = 0;
int delay_slot_filled = 0;
int seq_length = dbr_sequence_length ();
tree call_decl = SYMBOL_REF_DECL (call_dest);
int local_call = call_decl && targetm.binds_local_p (call_decl);
......@@ -7826,17 +7778,17 @@ pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
/* If this isn't a sibcall, we put the load of %r27 into the
delay slot. We can't do this in a sibcall as we don't
have a second call-clobbered scratch register available. */
if (seq_length != 0
&& ! JUMP_P (NEXT_INSN (insn))
&& !sibcall)
have a second call-clobbered scratch register available.
We don't need to do anything when generating fast indirect
calls. */
if (seq_length != 0 && !sibcall)
{
final_scan_insn (NEXT_INSN (insn), asm_out_file,
optimize, 0, NULL);
/* Now delete the delay insn. */
SET_INSN_DELETED (NEXT_INSN (insn));
delay_insn_deleted = 1;
seq_length = 0;
}
output_asm_insn ("addil LT'%0,%%r27", xoperands);
......@@ -7854,7 +7806,7 @@ pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
output_asm_insn ("ldd 16(%%r1),%%r2", xoperands);
output_asm_insn ("bve,l (%%r2),%%r2", xoperands);
output_asm_insn ("ldd 24(%%r1),%%r27", xoperands);
delay_slot_filled = 1;
seq_length = 1;
}
}
else
......@@ -7872,7 +7824,6 @@ pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
indirect_call = 1;
if (seq_length != 0
&& ! JUMP_P (NEXT_INSN (insn))
&& !sibcall
&& (!TARGET_PA_20
|| indirect_call
......@@ -7886,7 +7837,7 @@ pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
/* Now delete the delay insn. */
SET_INSN_DELETED (NEXT_INSN (insn));
delay_insn_deleted = 1;
seq_length = 0;
}
if ((TARGET_LONG_ABS_CALL || local_call) && !flag_pic)
......@@ -7908,7 +7859,7 @@ pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
output_asm_insn ("ble R'%0(%%sr4,%%r1)", xoperands);
output_asm_insn ("copy %%r31,%%r2", xoperands);
delay_slot_filled = 1;
seq_length = 1;
}
}
else
......@@ -7995,7 +7946,7 @@ pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
{
output_asm_insn ("bve,l (%%r1),%%r2", xoperands);
output_asm_insn ("stw %%r2,-24(%%sp)", xoperands);
delay_slot_filled = 1;
seq_length = 1;
}
else
output_asm_insn ("bve,l (%%r1),%%r2", xoperands);
......@@ -8025,55 +7976,16 @@ pa_output_call (rtx_insn *insn, rtx call_dest, int sibcall)
output_asm_insn ("stw %%r31,-24(%%sp)", xoperands);
else
output_asm_insn ("copy %%r31,%%r2", xoperands);
delay_slot_filled = 1;
seq_length = 1;
}
}
}
}
}
if (!delay_slot_filled && (seq_length == 0 || delay_insn_deleted))
if (seq_length == 0)
output_asm_insn ("nop", xoperands);
/* We are done if there isn't a jump in the delay slot. */
if (seq_length == 0
|| delay_insn_deleted
|| ! JUMP_P (NEXT_INSN (insn)))
return "";
/* A sibcall should never have a branch in the delay slot. */
gcc_assert (!sibcall);
/* This call has an unconditional jump in its delay slot. */
xoperands[0] = XEXP (PATTERN (NEXT_INSN (insn)), 1);
if (!delay_slot_filled && INSN_ADDRESSES_SET_P ())
{
/* See if the return address can be adjusted. Use the containing
sequence insn's address. This would break the regular call/return@
relationship assumed by the table based eh unwinder, so only do that
if the call is not possibly throwing. */
rtx seq_insn = NEXT_INSN (PREV_INSN (final_sequence->insn (0)));
int distance = (INSN_ADDRESSES (INSN_UID (JUMP_LABEL (NEXT_INSN (insn))))
- INSN_ADDRESSES (INSN_UID (seq_insn)) - 8);
if (VAL_14_BITS_P (distance)
&& !(can_throw_internal (insn) || can_throw_external (insn)))
{
xoperands[1] = gen_label_rtx ();
output_asm_insn ("ldo %0-%1(%%r2),%%r2", xoperands);
targetm.asm_out.internal_label (asm_out_file, "L",
CODE_LABEL_NUMBER (xoperands[1]));
}
else
output_asm_insn ("nop\n\tb,n %0", xoperands);
}
else
output_asm_insn ("b,n %0", xoperands);
/* Delete the jump. */
SET_INSN_DELETED (NEXT_INSN (insn));
return "";
}
......@@ -8822,28 +8734,6 @@ forward_branch_p (rtx_insn *insn)
return false;
}
/* Return 1 if INSN is in the delay slot of a call instruction. */
int
pa_jump_in_call_delay (rtx_insn *insn)
{
if (! JUMP_P (insn))
return 0;
if (PREV_INSN (insn)
&& PREV_INSN (PREV_INSN (insn))
&& NONJUMP_INSN_P (next_real_insn (PREV_INSN (PREV_INSN (insn)))))
{
rtx test_insn = next_real_insn (PREV_INSN (PREV_INSN (insn)));
return (GET_CODE (PATTERN (test_insn)) == SEQUENCE
&& XVECEXP (PATTERN (test_insn), 0, 1) == insn);
}
else
return 0;
}
/* Output an unconditional move and branch insn. */
const char *
......@@ -8916,36 +8806,6 @@ pa_output_parallel_addb (rtx *operands, rtx_insn *insn)
return pa_output_lbranch (operands[3], insn, 1);
}
/* Return nonzero if INSN (a jump insn) immediately follows a call
to a named function. This is used to avoid filling the delay slot
of the jump since it can usually be eliminated by modifying RP in
the delay slot of the call. */
int
pa_following_call (rtx_insn *insn)
{
if (! TARGET_JUMP_IN_DELAY)
return 0;
/* Find the previous real insn, skipping NOTEs. */
insn = PREV_INSN (insn);
while (insn && NOTE_P (insn))
insn = PREV_INSN (insn);
/* Check for CALL_INSNs and millicode calls. */
if (insn
&& ((CALL_P (insn)
&& get_attr_type (insn) != TYPE_DYNCALL)
|| (NONJUMP_INSN_P (insn)
&& GET_CODE (PATTERN (insn)) != SEQUENCE
&& GET_CODE (PATTERN (insn)) != USE
&& GET_CODE (PATTERN (insn)) != CLOBBER
&& get_attr_type (insn) == TYPE_MILLI)))
return 1;
return 0;
}
/* We use this hook to perform a PA specific optimization which is difficult
to do in earlier passes. */
......
......@@ -181,19 +181,13 @@
(const_string "true")
(const_string "false")))
;; For calls and millicode calls. Allow unconditional branches in the
;; delay slot.
;; For calls and millicode calls.
(define_attr "in_call_delay" "false,true"
(cond [(and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,multi,milli,sh_func_adrs,parallel_branch")
(eq_attr "length" "4")
(not (match_test "RTX_FRAME_RELATED_P (insn)")))
(const_string "true")
(eq_attr "type" "uncond_branch")
(if_then_else (match_test "TARGET_JUMP_IN_DELAY")
(const_string "true")
(const_string "false"))]
(const_string "false")))
(if_then_else (and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,multi,milli,sh_func_adrs,parallel_branch")
(eq_attr "length" "4")
(not (match_test "RTX_FRAME_RELATED_P (insn)")))
(const_string "true")
(const_string "false")))
;; Call delay slot description.
(define_delay (eq_attr "type" "call")
......@@ -229,8 +223,7 @@
(and (eq_attr "in_nullified_branch_delay" "true")
(attr_flag "backward"))])
(define_delay (and (eq_attr "type" "uncond_branch")
(not (match_test "pa_following_call (insn)")))
(define_delay (eq_attr "type" "uncond_branch")
[(eq_attr "in_branch_delay" "true") (nil) (nil)])
;; Memory. Disregarding Cache misses, the Mustang memory times are:
......@@ -6884,13 +6877,7 @@
[(set_attr "type" "uncond_branch")
(set_attr "pa_combine_type" "uncond_branch")
(set (attr "length")
(cond [(match_test "pa_jump_in_call_delay (insn)")
(if_then_else (lt (abs (minus (match_dup 0)
(plus (pc) (const_int 8))))
(const_int MAX_12BIT_OFFSET))
(const_int 4)
(const_int 8))
(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
(cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
(const_int MAX_17BIT_OFFSET))
(const_int 4)
(match_test "TARGET_PORTABLE_RUNTIME")
......
......@@ -14862,9 +14862,7 @@ Synonyms for @option{-march=1.0}, @option{-march=1.1}, and @option{-march=2.0} r
@item -mjump-in-delay
@opindex mjump-in-delay
Fill delay slots of function calls with unconditional jump instructions
by modifying the return pointer for the function call to be the target
of the conditional jump.
This option is ignored and provided for compatibility purposes only.
@item -mdisable-fpregs
@opindex mdisable-fpregs
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment