diff mbox

[SH,committed] Fix PR 67260

Message ID 1455353674.2124.260.camel@t-online.de
State New
Headers show

Commit Message

Oleg Endo Feb. 13, 2016, 8:54 a.m. UTC
Hi,

The attached patch(es) fix PR 67260.  For details please see the
discussion in the PR log.

Tested on trunk and sh-elf with
make -k check RUNTESTFLAGS="--target_board=sh-sim\{-m2/-ml,-m2/-mb,
-m2a/-mb,-m4/-ml,-m4/-mb,-m4a/-ml,-m4a/-mb}"

and on GCC 5 and GCC 4.9 branch with make all-gcc and compiling the
testcase.

Committed to trunk as r233399 + r233400, to GCC 5 branch as r233401 and
to GCC 4.9 branch as r233402.

Cheers,
Oleg
diff mbox

Patch

Index: gcc/config/sh/sh.md
===================================================================
--- gcc/config/sh/sh.md	(revision 233397)
+++ gcc/config/sh/sh.md	(working copy)
@@ -10476,12 +10476,16 @@ 
 		      (const_string "single") (const_string "double")))
    (set_attr "type" "jump_ind")])
 
+;; sibcall_value_pcrel used to have a =&k clobber for the scratch register
+;; that it needs for the branch address.  This causes troubles when there
+;; is a big overlap of argument and return value registers.  Hence, use a
+;; fixed call clobbered register for the address.  See also PR 67260.
 (define_insn_and_split "sibcall_value_pcrel"
   [(set (match_operand 0 "" "=rf")
 	(call (mem:SI (match_operand:SI 1 "symbol_ref_operand" ""))
 	      (match_operand 2 "" "")))
    (use (reg:SI FPSCR_MODES_REG))
-   (clobber (match_scratch:SI 3 "=&k"))
+   (clobber (reg:SI R1_REG))
    (return)]
   "TARGET_SH2 && !TARGET_FDPIC"
   "#"
@@ -10491,6 +10495,8 @@ 
   rtx lab = PATTERN (gen_call_site ());
   rtx call_insn;
 
+  operands[3] =  gen_rtx_REG (SImode, R1_REG);
+
   sh_expand_sym_label2reg (operands[3], operands[1], lab, true);
   call_insn = emit_call_insn (gen_sibcall_valuei_pcrel (operands[0],
 							operands[3],
@@ -10505,6 +10511,8 @@ 
 		      (const_string "single") (const_string "double")))
    (set_attr "type" "jump_ind")])
 
+;; Like for sibcall_value_pcrel, use a fixed call clobbered register for
+;; the branch address.
 (define_insn_and_split "sibcall_value_pcrel_fdpic"
   [(set (match_operand 0 "" "=rf")
 	(call (mem:SI (match_operand:SI 1 "symbol_ref_operand"))
@@ -10511,7 +10519,7 @@ 
 	      (match_operand 2)))
    (use (reg:SI FPSCR_MODES_REG))
    (use (reg:SI PIC_REG))
-   (clobber (match_scratch:SI 3 "=k"))
+   (clobber (reg:SI R1_REG))
    (return)]
   "TARGET_SH2 && TARGET_FDPIC"
   "#"
@@ -10520,6 +10528,8 @@ 
 {
   rtx lab = PATTERN (gen_call_site ());
 
+  operands[3] =  gen_rtx_REG (SImode, R1_REG);
+
   sh_expand_sym_label2reg (operands[3], operands[1], lab, true);
   rtx i = emit_call_insn (gen_sibcall_valuei_pcrel_fdpic (operands[0],
 							  operands[3],
Index: gcc/testsuite/gcc.target/sh/torture/pr67260.c
===================================================================
--- gcc/testsuite/gcc.target/sh/torture/pr67260.c	(revision 0)
+++ gcc/testsuite/gcc.target/sh/torture/pr67260.c	(working copy)
@@ -0,0 +1,12 @@ 
+/* { dg-additional-options "-std=gnu99 -fPIC" }  */
+/* { dg-do compile }  */
+
+#pragma GCC visibility push(hidden)
+
+double _Complex foo (double _Complex arg);
+
+double _Complex
+bar (double _Complex arg)
+{
+  return foo (arg);
+}