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 up var-tracking notes emitted in between bbs (PR middle-end/43631)


Hi!

Steven has been complaining for some years that var-tracking inserts
NOTE_INSN_VAR_LOCATION (and NOTE_INSN_CALL_ARG_LOCATION) notes sometimes
in between basic blocks, but with BLOCK_FOR_INSN set (or sometimes extends
a bb ending originally with a noreturn or throwing call by a note or more
after it).  Fixed thusly, bootstrapped/regtested on x86_64-linux and
i686-linux, ok for trunk?

2012-11-14  Jakub Jelinek  <jakub@redhat.com>

	PR middle-end/43631
	* var-tracking.c (emit_note_insn_var_location, emit_notes_in_bb):
	Clear BLOCK_FOR_INSN on notes emitted in between basic blocks,
	don't adjust BB_END when inserting note after BB_END of some bb.

--- gcc/var-tracking.c.jj	2012-11-13 10:54:06.000000000 +0100
+++ gcc/var-tracking.c	2012-11-13 11:35:31.668284140 +0100
@@ -8566,9 +8566,30 @@ emit_note_insn_var_location (void **varp
 	      || NOTE_KIND (insn) == NOTE_INSN_CALL_ARG_LOCATION))
 	note = emit_note_after (NOTE_INSN_VAR_LOCATION, insn);
       else
-	note = emit_note_before (NOTE_INSN_VAR_LOCATION, insn);
+	{
+	  note = emit_note_before (NOTE_INSN_VAR_LOCATION, insn);
+	  /* If insn is BB_HEAD of some bb, make sure the note
+	     doesn't have BLOCK_FOR_INSN set.  The notes don't
+	     extend the extents of a basic block, and e.g. notes emitted
+	     for differences in between basic blocks should live in between
+	     the basic blocks.  */
+	  if (BLOCK_FOR_INSN (note)
+	      && BB_HEAD (BLOCK_FOR_INSN (note)) == insn)
+	    set_block_for_insn (note, NULL);
+	}
     }
   NOTE_VAR_LOCATION (note) = note_vl;
+  /* If insn is BB_END of some bb, make sure the note
+     doesn't have BLOCK_FOR_INSN set.  The notes don't
+     extend the extents of a basic block, and e.g. a noreturn
+     call can still be followed by NOTE_INSN_CALL_ARG_LOCATION.  */
+  if (BLOCK_FOR_INSN (note)
+      && BB_END (BLOCK_FOR_INSN (note)) == note
+      && PREV_INSN (note) == insn)
+    {
+      BB_END (BLOCK_FOR_INSN (note)) = insn;
+      set_block_for_insn (note, NULL);
+    }
 
   set_dv_changed (var->dv, false);
   gcc_assert (var->in_changed_variables);
@@ -8936,6 +8957,16 @@ emit_notes_in_bb (basic_block bb, datafl
 		}
 	      note = emit_note_after (NOTE_INSN_CALL_ARG_LOCATION, insn);
 	      NOTE_VAR_LOCATION (note) = arguments;
+	      /* If insn is BB_END of some bb, make sure the note
+		 doesn't have BLOCK_FOR_INSN set.  The notes don't
+		 extend the extents of a basic block, and e.g. a noreturn
+		 call can still be followed by NOTE_INSN_CALL_ARG_LOCATION.  */
+	      if (BLOCK_FOR_INSN (note)
+		  && BB_END (BLOCK_FOR_INSN (note)) == note)
+		{
+		  BB_END (BLOCK_FOR_INSN (note)) = insn;
+		  set_block_for_insn (note, NULL);
+		}
 	    }
 	    break;
 

	Jakub


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