From baa8dec7fd2c771ddce19df5bc222614e0d02351 Mon Sep 17 00:00:00 2001 From: rth Date: Thu, 27 Dec 2001 22:19:59 +0000 Subject: [PATCH] * haifa-sched.c (reemit_other_notes): New. (schedule_block): Use it. * sched-ebb.c (schedule_ebbs): Call remove_unnecessary_notes. * sched-rgn.c (schedule_insns): Likewise. * cfglayout.c (remove_scope_notes): Handle removing note at the end of the insn chain. * function.c (debug_find_var_in_block_tree): New. * gcc.dg/debug-1.c, gcc.dg/debug-2.c: New. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@48333 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/ChangeLog | 10 ++++++ gcc/cfglayout.c | 3 +- gcc/function.c | 24 ++++++++++++++ gcc/haifa-sched.c | 74 ++++++++++++++++++++++++++++++++---------- gcc/sched-ebb.c | 4 +++ gcc/sched-rgn.c | 4 +++ gcc/testsuite/ChangeLog | 4 +++ gcc/testsuite/gcc.dg/debug-1.c | 14 ++++++++ gcc/testsuite/gcc.dg/debug-2.c | 20 ++++++++++++ 9 files changed, 138 insertions(+), 19 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/debug-1.c create mode 100644 gcc/testsuite/gcc.dg/debug-2.c diff --git a/gcc/ChangeLog b/gcc/ChangeLog index e42d64be1ff..c6c6b921e2a 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,13 @@ +2001-12-27 Richard Henderson + + * haifa-sched.c (reemit_other_notes): New. + (schedule_block): Use it. + * sched-ebb.c (schedule_ebbs): Call remove_unnecessary_notes. + * sched-rgn.c (schedule_insns): Likewise. + * cfglayout.c (remove_scope_notes): Handle removing note at + the end of the insn chain. + * function.c (debug_find_var_in_block_tree): New. + 2001-12-27 Alan Modra David Edelsohn diff --git a/gcc/cfglayout.c b/gcc/cfglayout.c index 14f08eb39ef..e0adb53c71a 100644 --- a/gcc/cfglayout.c +++ b/gcc/cfglayout.c @@ -540,7 +540,8 @@ remove_scope_notes () if (PREV_INSN (x)) { NEXT_INSN (PREV_INSN (x)) = next; - PREV_INSN (next) = PREV_INSN (x); + if (next) + PREV_INSN (next) = PREV_INSN (x); NEXT_INSN (x) = NULL; PREV_INSN (x) = NULL; diff --git a/gcc/function.c b/gcc/function.c index f5a3102bf4d..097aea44684 100644 --- a/gcc/function.c +++ b/gcc/function.c @@ -277,6 +277,7 @@ static void reorder_fix_fragments PARAMS ((tree)); static tree blocks_nreverse PARAMS ((tree)); static int all_blocks PARAMS ((tree, tree *)); static tree *get_block_vector PARAMS ((tree, int *)); +extern tree debug_find_var_in_block_tree PARAMS ((tree, tree)); /* We always define `record_insns' even if its not used so that we can always export `prologue_epilogue_contains'. */ static void record_insns PARAMS ((rtx, varray_type *)) ATTRIBUTE_UNUSED; @@ -6051,6 +6052,29 @@ number_blocks (fn) return; } + +/* If VAR is present in a subblock of BLOCK, return the subblock. */ + +tree +debug_find_var_in_block_tree (var, block) + tree var; + tree block; +{ + tree t; + + for (t = BLOCK_VARS (block); t; t = TREE_CHAIN (t)) + if (t == var) + return block; + + for (t = BLOCK_SUBBLOCKS (block); t; t = TREE_CHAIN (t)) + { + tree ret = debug_find_var_in_block_tree (var, t); + if (ret) + return ret; + } + + return NULL_TREE; +} /* Allocate a function structure and reset its contents to the defaults. */ diff --git a/gcc/haifa-sched.c b/gcc/haifa-sched.c index 7b9a2e82126..ca6cfbb1d4f 100644 --- a/gcc/haifa-sched.c +++ b/gcc/haifa-sched.c @@ -319,6 +319,7 @@ static void adjust_priority PARAMS ((rtx)); static rtx unlink_other_notes PARAMS ((rtx, rtx)); static rtx unlink_line_notes PARAMS ((rtx, rtx)); static rtx reemit_notes PARAMS ((rtx, rtx)); +static rtx reemit_other_notes PARAMS ((rtx, rtx)); static rtx *ready_lastpos PARAMS ((struct ready_list *)); static void ready_sort PARAMS ((struct ready_list *)); @@ -1575,6 +1576,60 @@ reemit_notes (insn, last) return retval; } + +/* NOTE_LIST is the end of a chain of notes previously found among the + insns. Insert them at the beginning of the insns. Actually, insert + NOTE_INSN_BLOCK_END notes at the end of the insns. Doing otherwise + tends to collapse lexical blocks into empty regions, which is somewhat + less than useful. */ +/* ??? Ideally we'd mark each insn with the block it originated from, + and preserve that information. This requires some moderately + sophisticated block reconstruction code, since block nestings must + be preserved. */ + +static rtx +reemit_other_notes (head, tail) + rtx head, tail; +{ + bool saw_block_beg = false; + + while (note_list) + { + rtx note_tail = note_list; + note_list = PREV_INSN (note_tail); + + if (NOTE_LINE_NUMBER (note_tail) == NOTE_INSN_BLOCK_END + /* We can only extend the lexical block while we havn't + seen a BLOCK_BEG note. Otherwise we risk mis-nesting + the notes. */ + && ! saw_block_beg) + { + rtx insert_after = tail; + if (GET_CODE (NEXT_INSN (tail)) == BARRIER) + insert_after = NEXT_INSN (tail); + + PREV_INSN (note_tail) = insert_after; + NEXT_INSN (note_tail) = NEXT_INSN (insert_after); + if (NEXT_INSN (insert_after)) + PREV_INSN (NEXT_INSN (insert_after)) = note_tail; + NEXT_INSN (insert_after) = note_tail; + } + else + { + if (NOTE_LINE_NUMBER (note_tail) == NOTE_INSN_BLOCK_BEG) + saw_block_beg = true; + + PREV_INSN (note_tail) = PREV_INSN (head); + NEXT_INSN (PREV_INSN (head)) = note_tail; + NEXT_INSN (note_tail) = head; + PREV_INSN (head) = note_tail; + head = note_tail; + } + } + + return head; +} + /* Move INSN, and all insns which should be issued before it, due to SCHED_GROUP_P flag. Reemit notes if needed. @@ -1800,24 +1855,7 @@ schedule_block (b, rgn_n_insns) head = NEXT_INSN (prev_head); tail = last; - /* Restore-other-notes: NOTE_LIST is the end of a chain of notes - previously found among the insns. Insert them at the beginning - of the insns. */ - if (note_list != 0) - { - rtx note_head = note_list; - - while (PREV_INSN (note_head)) - { - note_head = PREV_INSN (note_head); - } - - PREV_INSN (note_head) = PREV_INSN (head); - NEXT_INSN (PREV_INSN (head)) = note_head; - PREV_INSN (head) = note_list; - NEXT_INSN (note_list) = head; - head = note_head; - } + head = reemit_other_notes (head, tail); /* Debugging. */ if (sched_verbose) diff --git a/gcc/sched-ebb.c b/gcc/sched-ebb.c index d4a9f777653..13b9fe6602d 100644 --- a/gcc/sched-ebb.c +++ b/gcc/sched-ebb.c @@ -285,6 +285,10 @@ schedule_ebbs (dump_file) if (n_basic_blocks == 0) return; + /* Remove lexical block notes for empty regions. These get shuffled + about during scheduling and confuse the debugging issue. */ + remove_unnecessary_notes (); + sched_init (dump_file); current_sched_info = &ebb_sched_info; diff --git a/gcc/sched-rgn.c b/gcc/sched-rgn.c index ab5adee8159..68242046221 100644 --- a/gcc/sched-rgn.c +++ b/gcc/sched-rgn.c @@ -2896,6 +2896,10 @@ schedule_insns (dump_file) if (n_basic_blocks == 0) return; + /* Remove lexical block notes for empty regions. These get shuffled + about during scheduling and confuse the debugging issue. */ + remove_unnecessary_notes (); + nr_inter = 0; nr_spec = 0; diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 698296b87a0..915a148a432 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,7 @@ +2001-12-27 Richard Henderson + + * gcc.dg/debug-1.c, gcc.dg/debug-2.c: New. + 2001-12-26 Nathan Sidwell * g++.dg/eh/ctor1.C: New test. diff --git a/gcc/testsuite/gcc.dg/debug-1.c b/gcc/testsuite/gcc.dg/debug-1.c new file mode 100644 index 00000000000..1e53b14eb5c --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug-1.c @@ -0,0 +1,14 @@ +/* Verify that the scheduler does not discard the lexical block. */ +/* { dg-do compile } */ +/* { dg-options "-O2 -g -dA" } */ +/* { dg-final { scan-assembler "xyzzy" } } */ + +long foo(long p) +{ + { + long xyzzy = 0; + if (p) + xyzzy = 2; + return xyzzy; + } +} diff --git a/gcc/testsuite/gcc.dg/debug-2.c b/gcc/testsuite/gcc.dg/debug-2.c new file mode 100644 index 00000000000..4305059ba7b --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug-2.c @@ -0,0 +1,20 @@ +/* Verify that the scheduler does not discard the lexical block. */ +/* { dg-do compile } */ +/* { dg-options "-O2 -g -dA" } */ +/* { dg-final { scan-assembler "xyzzy" } } */ + +long foo(long p) +{ + if (1) + { + long xyzzy = 0; + if (p) + xyzzy = 2; + return xyzzy; + } + else + { + int x = 0; + return x; + } +} -- 2.11.4.GIT