This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH] Fix https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83396#c28 on ia64 (PR bootstrap/83396)


Hi!

I think there are 2 issues.  One is that the ia64 backend emits
the group barrier insns before BB_HEAD label, so it isn't part of a bb,
but has BLOCK_FOR_INSN of the following block, that looks invalid to me
and the ia64.c hunk ought to fix that, except that I don't have access to
ia64 anymore and so can't test it.  Andreas, could you try that?

Another thing is that if we because of this end up with insns outside of
basic blocks, the vt_initialize asserts will fire again.  Here, first of
all, IMNSHO we should assert that debug bind insns aren't outside of basic
blocks, the other patches and checking should ensure that (and if any slips
in, we want to fix that too rather than work-around).
Another is that while walking from get_first_insn to one before BB_HEAD (bb->next_bb),
we can encounter insns outside of bb not just before BB_HEAD (bb), but also
after BB_END (bb), both cases are outside of a bb and thus we can
expect BLOCK_FOR_INSN being NULL.

Bootstrapped/regtested on x86_64-linux, i686-linux, powerpc64le-linux,
regtest on powerpc64-linux pending.  Ok for trunk perhaps without the
ia64.c bits until that gets tested?

Or, in the PR there is a variant patch which just doesn't do the asserts and
doesn't have to track outside_bb.

2017-12-13  Jakub Jelinek  <jakub@redhat.com>

	PR bootstrap/83396
	* config/ia64/ia64.c (emit_insn_group_barriers): If emitting a group
	barrier before BB_HEAD, clear BLOCK_FOR_INSN on the group barrier.
	* var-tracking.c (vt_initialize): Don't assert blocks without
	BLOCK_FOR_INSN are only debug insns, instead assert they are outside of
	basic blocks.  Don't reset debug bind stmts outside of basic blocks,
	instead assert they aren't present outside of basic blocks.  Simplify.

	* gcc.dg/pr83396.c: New test.

--- gcc/config/ia64/ia64.c.jj	2017-12-07 18:05:02.000000000 +0100
+++ gcc/config/ia64/ia64.c	2017-12-13 12:29:07.598684661 +0100
@@ -7098,7 +7098,13 @@ emit_insn_group_barriers (FILE *dump)
 		  if (dump)
 		    fprintf (dump, "Emitting stop before label %d\n",
 			     INSN_UID (last_label));
-		  emit_insn_before (gen_insn_group_barrier (GEN_INT (3)), last_label);
+		  insn
+		    = emit_insn_before (gen_insn_group_barrier (GEN_INT (3)),
+					last_label);
+		  /* If we emit the group barrier before BB_HEAD, it should
+		     be outside of any bb.  */
+		  if (BB_HEAD (BLOCK_FOR_INSN (last_label)) == last_label)
+		    BLOCK_FOR_INSN (insn) = NULL;
 		  insn = last_label;
 
 		  init_insn_group_barriers ();
--- gcc/var-tracking.c.jj	2017-12-12 09:48:26.000000000 +0100
+++ gcc/var-tracking.c	2017-12-13 12:38:51.856261497 +0100
@@ -10157,28 +10157,28 @@ vt_initialize (void)
 	     insns that might be before it too.  Unfortunately,
 	     BB_HEADER and BB_FOOTER are not set while we run this
 	     pass.  */
-	  insn = get_first_insn (bb);
-	  for (rtx_insn *next;
-	       insn != BB_HEAD (bb->next_bb)
-		 ? next = NEXT_INSN (insn), true : false;
+	  rtx_insn *next;
+	  bool outside_bb = true;
+	  for (insn = get_first_insn (bb); insn != BB_HEAD (bb->next_bb);
 	       insn = next)
 	    {
+	      next = NEXT_INSN (insn);
+	      if (insn == BB_HEAD (bb))
+		outside_bb = false;
 	      if (INSN_P (insn))
 		{
 		  basic_block save_bb = BLOCK_FOR_INSN (insn);
 		  if (!BLOCK_FOR_INSN (insn))
 		    {
+		      gcc_assert (outside_bb);
 		      BLOCK_FOR_INSN (insn) = bb;
-		      gcc_assert (DEBUG_INSN_P (insn));
-		      /* Reset debug insns between basic blocks.
-			 Their location is not reliable, because they
-			 were probably not maintained up to date.  */
-		      if (DEBUG_BIND_INSN_P (insn))
-			INSN_VAR_LOCATION_LOC (insn)
-			  = gen_rtx_UNKNOWN_VAR_LOC ();
 		    }
 		  else
 		    gcc_assert (BLOCK_FOR_INSN (insn) == bb);
+		  /* Verify debug bind insns don't occur outside of bbs.  */
+		  gcc_assert (!DEBUG_BIND_INSN_P (insn) || !outside_bb);
+		  if (insn == BB_END (bb))
+		    outside_bb = true;
 
 		  if (!frame_pointer_needed)
 		    {
@@ -10255,6 +10255,8 @@ vt_initialize (void)
 		    }
 		  BLOCK_FOR_INSN (insn) = save_bb;
 		}
+	      else if (insn == BB_END (bb))
+		outside_bb = true;
 	    }
 	  gcc_assert (offset == VTI (bb)->out.stack_adjust);
 	}
--- gcc/testsuite/gcc.dg/pr83396.c.jj	2017-12-13 12:41:05.127570666 +0100
+++ gcc/testsuite/gcc.dg/pr83396.c	2017-12-13 12:40:30.020014539 +0100
@@ -0,0 +1,12 @@
+/* PR bootstrap/83396 */
+/* { dg-do compile } */
+/* { dg-options "-O2 -g" } */
+
+int bar (int);
+int baz (int);
+
+int
+foo (int x)
+{
+  return bar (x) || baz (x) != 0;
+}

	Jakub


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]