OSDN Git Service

Daily bump.
[pf3gnuchains/gcc-fork.git] / gcc / cfgrtl.c
index 78df3ff..4c4b3b7 100644 (file)
@@ -531,7 +531,26 @@ rtl_split_block (basic_block bb, void *insnp)
       insn = first_insn_after_basic_block_note (bb);
 
       if (insn)
-       insn = PREV_INSN (insn);
+       {
+         rtx next = insn;
+
+         insn = PREV_INSN (insn);
+
+         /* If the block contains only debug insns, insn would have
+            been NULL in a non-debug compilation, and then we'd end
+            up emitting a DELETED note.  For -fcompare-debug
+            stability, emit the note too.  */
+         if (insn != BB_END (bb)
+             && DEBUG_INSN_P (next)
+             && DEBUG_INSN_P (BB_END (bb)))
+           {
+             while (next != BB_END (bb) && DEBUG_INSN_P (next))
+               next = NEXT_INSN (next);
+
+             if (next == BB_END (bb))
+               emit_note_after (NOTE_INSN_DELETED, next);
+           }
+       }
       else
        insn = get_last_insn ();
     }
@@ -566,11 +585,15 @@ rtl_merge_blocks (basic_block a, basic_block b)
 {
   rtx b_head = BB_HEAD (b), b_end = BB_END (b), a_end = BB_END (a);
   rtx del_first = NULL_RTX, del_last = NULL_RTX;
+  rtx b_debug_start = b_end, b_debug_end = b_end;
   int b_empty = 0;
 
   if (dump_file)
     fprintf (dump_file, "merging block %d into block %d\n", b->index, a->index);
 
+  while (DEBUG_INSN_P (b_end))
+    b_end = PREV_INSN (b_debug_start = b_end);
+
   /* If there was a CODE_LABEL beginning B, delete it.  */
   if (LABEL_P (b_head))
     {
@@ -636,9 +659,21 @@ rtl_merge_blocks (basic_block a, basic_block b)
   /* Reassociate the insns of B with A.  */
   if (!b_empty)
     {
-      update_bb_for_insn_chain (a_end, b_end, a);
+      update_bb_for_insn_chain (a_end, b_debug_end, a);
 
-      a_end = b_end;
+      a_end = b_debug_end;
+    }
+  else if (b_end != b_debug_end)
+    {
+      /* Move any deleted labels and other notes between the end of A
+        and the debug insns that make up B after the debug insns,
+        bringing the debug insns into A while keeping the notes after
+        the end of A.  */
+      if (NEXT_INSN (a_end) != b_debug_start)
+       reorder_insns_nobb (NEXT_INSN (a_end), PREV_INSN (b_debug_start),
+                           b_debug_end);
+      update_bb_for_insn_chain (b_debug_start, b_debug_end, a);
+      a_end = b_debug_end;
     }
 
   df_bb_delete (b->index);
@@ -1712,11 +1747,11 @@ get_last_bb_insn (basic_block bb)
     end = tmp;
 
   /* Include any barriers that may follow the basic block.  */
-  tmp = next_nonnote_insn (end);
+  tmp = next_nonnote_insn_bb (end);
   while (tmp && BARRIER_P (tmp))
     {
       end = tmp;
-      tmp = next_nonnote_insn (end);
+      tmp = next_nonnote_insn_bb (end);
     }
 
   return end;
@@ -2162,6 +2197,11 @@ purge_dead_edges (basic_block bb)
   bool found;
   edge_iterator ei;
 
+  if (DEBUG_INSN_P (insn) && insn != BB_HEAD (bb))
+    do
+      insn = PREV_INSN (insn);
+    while ((DEBUG_INSN_P (insn) || NOTE_P (insn)) && insn != BB_HEAD (bb));
+
   /* If this instruction cannot trap, remove REG_EH_REGION notes.  */
   if (NONJUMP_INSN_P (insn)
       && (note = find_reg_note (insn, REG_EH_REGION, NULL)))
@@ -2182,10 +2222,10 @@ purge_dead_edges (basic_block bb)
         latter can appear when nonlocal gotos are used.  */
       if (e->flags & EDGE_EH)
        {
-         if (can_throw_internal (BB_END (bb))
+         if (can_throw_internal (insn)
              /* If this is a call edge, verify that this is a call insn.  */
              && (! (e->flags & EDGE_ABNORMAL_CALL)
-                 || CALL_P (BB_END (bb))))
+                 || CALL_P (insn)))
            {
              ei_next (&ei);
              continue;
@@ -2193,7 +2233,7 @@ purge_dead_edges (basic_block bb)
        }
       else if (e->flags & EDGE_ABNORMAL_CALL)
        {
-         if (CALL_P (BB_END (bb))
+         if (CALL_P (insn)
              && (! (note = find_reg_note (insn, REG_EH_REGION, NULL))
                  || INTVAL (XEXP (note, 0)) >= 0))
            {
@@ -2771,7 +2811,8 @@ rtl_block_ends_with_call_p (basic_block bb)
   while (!CALL_P (insn)
         && insn != BB_HEAD (bb)
         && (keep_with_call_p (insn)
-            || NOTE_P (insn)))
+            || NOTE_P (insn)
+            || DEBUG_INSN_P (insn)))
     insn = PREV_INSN (insn);
   return (CALL_P (insn));
 }