diff mbox

patch to fix PR69461

Message ID 56B240D1.7030809@redhat.com
State New
Headers show

Commit Message

Vladimir Makarov Feb. 3, 2016, 6:02 p.m. UTC
The following patch fixes

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=69461

   The patch actually solves several issues.  Before the patch LRA has 
 >800 more failures on GCC testsuite on power8.  After the patch the LRA 
has the same number of failures as reload.

Working on the patch, I think I found some typo in 
rs6000.c::rs6000_legitimate_address_p.  The code suspicious to me:

   if (reg_offset_p && reg_addr[mode].fused_toc && 
toc_fusion_mem_wrapped (x, mode))
     return 1;

The function works with address (x) but toc_fusion_mem_wrapped requires 
memory instead of address.  Therefore the function never returns 1 for 
toc_fusion_wrapped address.

Mike and Peter, what do you think about this code?

Anyway, the patch was successfully bootstrapped and tested on power8.

Committed as rev..
diff mbox

Patch

Index: ChangeLog
===================================================================
--- ChangeLog	(revision 233106)
+++ ChangeLog	(working copy)
@@ -1,3 +1,12 @@ 
+2016-02-03  Vladimir Makarov  <vmakarov@redhat.com>
+	    Alexandre Oliva  <aoliva@redhat.com>
+
+	PR target/69461
+	* lra-constraints.c (simplify_operand_subreg): Check additionally
+	address validity after potential reloading.
+	(process_address_1): Check insns validity.  In case of failure do
+	nothing.
+
 2016-02-03  Kirill Yukhin  <kirill.yukhin@intel.com>
 
 	PR target/69118
Index: testsuite/ChangeLog
===================================================================
--- testsuite/ChangeLog	(revision 233106)
+++ testsuite/ChangeLog	(working copy)
@@ -1,3 +1,9 @@ 
+2016-02-03  Vladimir Makarov  <vmakarov@redhat.com>
+	    Alexandre Oliva  <aoliva@redhat.com>
+
+	PR target/69461
+	* gcc.target/powerpc/pr69461.c: New.
+
 2016-02-03  Uros Bizjak  <ubizjak@gmail.com>
 
 	* lib/tsan-dg.exp (tsan_init): Move check if tsan executable
Index: lra-constraints.c
===================================================================
--- lra-constraints.c	(revision 233106)
+++ lra-constraints.c	(working copy)
@@ -1411,6 +1411,21 @@  simplify_operand_subreg (int nop, machin
 	  || valid_address_p (GET_MODE (subst), XEXP (subst, 0),
 			      MEM_ADDR_SPACE (subst)))
 	return true;
+      else if ((get_constraint_type (lookup_constraint
+				     (curr_static_id->operand[nop].constraint))
+		!= CT_SPECIAL_MEMORY)
+	       /* We still can reload address and if the address is
+		  valid, we can remove subreg without reloading its
+		  inner memory.  */
+	       && valid_address_p (GET_MODE (subst),
+				   regno_reg_rtx
+				   [ira_class_hard_regs
+				    [base_reg_class (GET_MODE (subst),
+						     MEM_ADDR_SPACE (subst),
+						     ADDRESS, SCRATCH)][0]],
+				   MEM_ADDR_SPACE (subst)))
+	return true;
+
       /* If the address was valid and became invalid, prefer to reload
 	 the memory.  Typical case is when the index scale should
 	 correspond the memory.  */
@@ -2958,6 +2973,8 @@  process_address_1 (int nop, bool check_o
     {
       if (ad.index == NULL)
 	{
+	  rtx_insn *insn;
+	  rtx_insn *last = get_last_insn ();
 	  int code = -1;
 	  enum reg_class cl = base_reg_class (ad.mode, ad.as,
 					      SCRATCH, SCRATCH);
@@ -2966,9 +2983,6 @@  process_address_1 (int nop, bool check_o
 	  new_reg = lra_create_new_reg (Pmode, NULL_RTX, cl, "addr");
 	  if (HAVE_lo_sum)
 	    {
-	      rtx_insn *insn;
-	      rtx_insn *last = get_last_insn ();
-
 	      /* addr => lo_sum (new_base, addr), case (2) above.  */
 	      insn = emit_insn (gen_rtx_SET
 				(new_reg,
@@ -3004,6 +3018,20 @@  process_address_1 (int nop, bool check_o
 	    {
 	      /* addr => new_base, case (2) above.  */
 	      lra_emit_move (new_reg, addr);
+
+	      for (insn = last == NULL_RTX ? get_insns () : NEXT_INSN (last);
+		   insn != NULL_RTX;
+		   insn = NEXT_INSN (insn))
+		if (recog_memoized (insn) < 0)
+		  break;
+	      if (insn != NULL_RTX)
+		{
+		  /* Do nothing if we cannot generate right insns.
+		     This is analogous to reload pass behaviour.  */
+		  delete_insns_since (last);
+		  end_sequence ();
+		  return false;
+		}
 	      *ad.inner = new_reg;
 	    }
 	}
Index: testsuite/gcc.target/powerpc/pr69461.c
===================================================================
--- testsuite/gcc.target/powerpc/pr69461.c	(revision 0)
+++ testsuite/gcc.target/powerpc/pr69461.c	(working copy)
@@ -0,0 +1,15 @@ 
+/* { dg-do compile } */
+/* { dg-options "-O3 -mlra" } */
+
+extern void _setjmp (void);
+typedef struct {
+  double real;
+  double imag;
+} Py_complex;
+Py_complex a;
+Py_complex fn1();
+Py_complex fn2() { return fn1(); }
+void fn3() {
+  _setjmp();
+  a = fn2();
+}