Commit ec9ac2bc by Jan Hubicka Committed by Jan Hubicka

Revert:

	2007-04-23  Jan Hubicka  <jh@suse.cz>
	* function.c (init_function_start): Don't init line number info.
	(expand_function_end): Update.
	(reset_block_changes, record_block_change, finalize_block_changes,
	check_block_change, free_block_changes): Kill.
	* function.h (reset_block_changes, record_block_change,
	finalize_block_changes, check_block_change, free_block_changes): Remove
	prototypes.
	(struct function): Remove ib_boundaries_block.
	* emit-rtl.c (make_insn_raw, make_jump_insn_raw, make_call_insn_raw):
	Use curr_insn_locator to initialize locator.
	(emit_line_note): Remove.
	* cfgexpand.c (expand_gimple_cond_expr): Update.
	(construct_exit_block): Likewise.
	(tree_expand_cfg): Initialize/finalize locators.
	* expr.c (expand_expr_real): Update.
	* cfglayout.c (line_locators_locs, line_locators_lines,
	file_locators_locs, file_locators_files): Remove.
	(set_block_levels): Move to cfgexpand.c.
	(insn_locators_initialize): Remove.
	(pass_insn_locators_initialize): Remove.
	(locations_locators_locs, locations_locators_vals): New static vars.
	(curr_location, last_location, curr_block, last_block, curr_rtl_loc):
	Likewise.
	(insn_locators_alloc, insn_locators_finalize,
	set_curr_insn_source_location, set_curr_insn_block, curr_insn_locator):
	New functions.
	(locator_location): New.
	(locator_line, locator_file): Rewrite.
	* rtl.h (emit_line_note): Kill.
	(insn_locators_alloc, insn_locators_finalize,
	set_curr_insn_source_location, set_curr_insn_block, curr_insn_locator):
	Declare.
	* tree-inline.c (initialize_cfun): Do not initialize
	ib_boundaries_block.
	* passes.c (pass_insn_locators_initialize): Remove.

From-SVN: r124094
parent edc5f63b
2007-04-24 Jan Hubicka <j@suse.cz>
Revert:
2007-04-23 Jan Hubicka <jh@suse.cz>
* function.c (init_function_start): Don't init line number info.
(expand_function_end): Update.
(reset_block_changes, record_block_change, finalize_block_changes,
check_block_change, free_block_changes): Kill.
* function.h (reset_block_changes, record_block_change,
finalize_block_changes, check_block_change, free_block_changes): Remove
prototypes.
(struct function): Remove ib_boundaries_block.
* emit-rtl.c (make_insn_raw, make_jump_insn_raw, make_call_insn_raw):
Use curr_insn_locator to initialize locator.
(emit_line_note): Remove.
* cfgexpand.c (expand_gimple_cond_expr): Update.
(construct_exit_block): Likewise.
(tree_expand_cfg): Initialize/finalize locators.
* expr.c (expand_expr_real): Update.
* cfglayout.c (line_locators_locs, line_locators_lines,
file_locators_locs, file_locators_files): Remove.
(set_block_levels): Move to cfgexpand.c.
(insn_locators_initialize): Remove.
(pass_insn_locators_initialize): Remove.
(locations_locators_locs, locations_locators_vals): New static vars.
(curr_location, last_location, curr_block, last_block, curr_rtl_loc):
Likewise.
(insn_locators_alloc, insn_locators_finalize,
set_curr_insn_source_location, set_curr_insn_block, curr_insn_locator):
New functions.
(locator_location): New.
(locator_line, locator_file): Rewrite.
* rtl.h (emit_line_note): Kill.
(insn_locators_alloc, insn_locators_finalize,
set_curr_insn_source_location, set_curr_insn_block, curr_insn_locator):
Declare.
* tree-inline.c (initialize_cfun): Do not initialize
ib_boundaries_block.
* passes.c (pass_insn_locators_initialize): Remove.
2007-04-24 Daniel Franke <franke.daniel@gmail.com> 2007-04-24 Daniel Franke <franke.daniel@gmail.com>
* doc/invoke.texi: Removed leading '-' from option index entries. * doc/invoke.texi: Removed leading '-' from option index entries.
......
...@@ -1265,8 +1265,8 @@ expand_gimple_cond_expr (basic_block bb, tree stmt) ...@@ -1265,8 +1265,8 @@ expand_gimple_cond_expr (basic_block bb, tree stmt)
extract_true_false_edges_from_block (bb, &true_edge, &false_edge); extract_true_false_edges_from_block (bb, &true_edge, &false_edge);
if (EXPR_LOCUS (stmt)) if (EXPR_LOCUS (stmt))
{ {
set_curr_insn_source_location (*(EXPR_LOCUS (stmt))); emit_line_note (*(EXPR_LOCUS (stmt)));
set_curr_insn_block (TREE_BLOCK (stmt)); record_block_change (TREE_BLOCK (stmt));
} }
/* These flags have no purpose in RTL land. */ /* These flags have no purpose in RTL land. */
...@@ -1281,7 +1281,7 @@ expand_gimple_cond_expr (basic_block bb, tree stmt) ...@@ -1281,7 +1281,7 @@ expand_gimple_cond_expr (basic_block bb, tree stmt)
add_reg_br_prob_note (last, true_edge->probability); add_reg_br_prob_note (last, true_edge->probability);
maybe_dump_rtl_for_tree_stmt (stmt, last); maybe_dump_rtl_for_tree_stmt (stmt, last);
if (EXPR_LOCUS (then_exp)) if (EXPR_LOCUS (then_exp))
set_curr_insn_source_location (*(EXPR_LOCUS (then_exp))); emit_line_note (*(EXPR_LOCUS (then_exp)));
return NULL; return NULL;
} }
if (TREE_CODE (else_exp) == GOTO_EXPR && IS_EMPTY_STMT (then_exp)) if (TREE_CODE (else_exp) == GOTO_EXPR && IS_EMPTY_STMT (then_exp))
...@@ -1290,7 +1290,7 @@ expand_gimple_cond_expr (basic_block bb, tree stmt) ...@@ -1290,7 +1290,7 @@ expand_gimple_cond_expr (basic_block bb, tree stmt)
add_reg_br_prob_note (last, false_edge->probability); add_reg_br_prob_note (last, false_edge->probability);
maybe_dump_rtl_for_tree_stmt (stmt, last); maybe_dump_rtl_for_tree_stmt (stmt, last);
if (EXPR_LOCUS (else_exp)) if (EXPR_LOCUS (else_exp))
set_curr_insn_source_location (*(EXPR_LOCUS (else_exp))); emit_line_note (*(EXPR_LOCUS (else_exp)));
return NULL; return NULL;
} }
gcc_assert (TREE_CODE (then_exp) == GOTO_EXPR gcc_assert (TREE_CODE (then_exp) == GOTO_EXPR
...@@ -1322,7 +1322,7 @@ expand_gimple_cond_expr (basic_block bb, tree stmt) ...@@ -1322,7 +1322,7 @@ expand_gimple_cond_expr (basic_block bb, tree stmt)
maybe_dump_rtl_for_tree_stmt (stmt, last2); maybe_dump_rtl_for_tree_stmt (stmt, last2);
if (EXPR_LOCUS (else_exp)) if (EXPR_LOCUS (else_exp))
set_curr_insn_source_location (*(EXPR_LOCUS (else_exp))); emit_line_note (*(EXPR_LOCUS (else_exp)));
return new_bb; return new_bb;
} }
...@@ -1613,19 +1613,6 @@ construct_init_block (void) ...@@ -1613,19 +1613,6 @@ construct_init_block (void)
return init_block; return init_block;
} }
/* For each lexical block, set BLOCK_NUMBER to the depth at which it is
found in the block tree. */
static void
set_block_levels (tree block, int level)
{
while (block)
{
BLOCK_NUMBER (block) = level;
set_block_levels (BLOCK_SUBBLOCKS (block), level + 1);
block = BLOCK_CHAIN (block);
}
}
/* Create a block containing landing pads and similar stuff. */ /* Create a block containing landing pads and similar stuff. */
...@@ -1650,7 +1637,7 @@ construct_exit_block (void) ...@@ -1650,7 +1637,7 @@ construct_exit_block (void)
input_location = cfun->function_end_locus; input_location = cfun->function_end_locus;
/* The following insns belong to the top scope. */ /* The following insns belong to the top scope. */
set_curr_insn_block (DECL_INITIAL (current_function_decl)); record_block_change (DECL_INITIAL (current_function_decl));
/* Generate rtl for function exit. */ /* Generate rtl for function exit. */
expand_function_end (); expand_function_end ();
...@@ -1778,16 +1765,8 @@ tree_expand_cfg (void) ...@@ -1778,16 +1765,8 @@ tree_expand_cfg (void)
/* Some backends want to know that we are expanding to RTL. */ /* Some backends want to know that we are expanding to RTL. */
currently_expanding_to_rtl = 1; currently_expanding_to_rtl = 1;
insn_locators_alloc (); /* Prepare the rtl middle end to start recording block changes. */
if (!DECL_BUILT_IN (current_function_decl)) reset_block_changes ();
set_curr_insn_source_location (DECL_SOURCE_LOCATION (current_function_decl));
set_curr_insn_block (DECL_INITIAL (current_function_decl));
prologue_locator = curr_insn_locator ();
/* Make sure first insn is a note even if we don't want linenums.
This makes sure the first insn will never be deleted.
Also, final expects a note to appear there. */
emit_note (NOTE_INSN_DELETED);
/* Mark arrays indexed with non-constant indices with TREE_ADDRESSABLE. */ /* Mark arrays indexed with non-constant indices with TREE_ADDRESSABLE. */
discover_nonconstant_array_refs (); discover_nonconstant_array_refs ();
...@@ -1834,8 +1813,6 @@ tree_expand_cfg (void) ...@@ -1834,8 +1813,6 @@ tree_expand_cfg (void)
bb = expand_gimple_basic_block (bb); bb = expand_gimple_basic_block (bb);
construct_exit_block (); construct_exit_block ();
set_curr_insn_block (DECL_INITIAL (current_function_decl));
insn_locators_finalize ();
/* We're done expanding trees to RTL. */ /* We're done expanding trees to RTL. */
currently_expanding_to_rtl = 0; currently_expanding_to_rtl = 0;
...@@ -1866,6 +1843,8 @@ tree_expand_cfg (void) ...@@ -1866,6 +1843,8 @@ tree_expand_cfg (void)
more CONCATs anywhere. */ more CONCATs anywhere. */
generating_concat_p = 0; generating_concat_p = 0;
finalize_block_changes ();
if (dump_file) if (dump_file)
{ {
fprintf (dump_file, fprintf (dump_file,
...@@ -1896,9 +1875,6 @@ tree_expand_cfg (void) ...@@ -1896,9 +1875,6 @@ tree_expand_cfg (void)
return_label = NULL; return_label = NULL;
naked_return_label = NULL; naked_return_label = NULL;
free_histograms (); free_histograms ();
/* Tag the blocks with a depth number so that change_scope can find
the common parent easily. */
set_block_levels (DECL_INITIAL (cfun->decl), 0);
return 0; return 0;
} }
......
...@@ -48,6 +48,7 @@ static void record_effective_endpoints (void); ...@@ -48,6 +48,7 @@ static void record_effective_endpoints (void);
static rtx label_for_bb (basic_block); static rtx label_for_bb (basic_block);
static void fixup_reorder_chain (void); static void fixup_reorder_chain (void);
static void set_block_levels (tree, int);
static void change_scope (rtx, tree, tree); static void change_scope (rtx, tree, tree);
void verify_insn_chain (void); void verify_insn_chain (void);
...@@ -231,106 +232,121 @@ record_effective_endpoints (void) ...@@ -231,106 +232,121 @@ record_effective_endpoints (void)
than the following one. Similarly for the other properties. */ than the following one. Similarly for the other properties. */
static VEC(int,heap) *block_locators_locs; static VEC(int,heap) *block_locators_locs;
static GTY(()) VEC(tree,gc) *block_locators_blocks; static GTY(()) VEC(tree,gc) *block_locators_blocks;
static VEC(int,heap) *locations_locators_locs; static VEC(int,heap) *line_locators_locs;
DEF_VEC_O(location_t); static VEC(int,heap) *line_locators_lines;
DEF_VEC_ALLOC_O(location_t,heap); static VEC(int,heap) *file_locators_locs;
static VEC(location_t,heap) *locations_locators_vals; static GTY(()) varray_type file_locators_files;
int prologue_locator; int prologue_locator;
int epilogue_locator; int epilogue_locator;
/* Hold current location information and last location information, so the /* During the RTL expansion the lexical blocks and line numbers are
datastructures are built lazilly only when some instructions in given represented via INSN_NOTEs. Replace them by representation using
place are needed. */ INSN_LOCATORs. */
location_t curr_location, last_location;
static tree curr_block, last_block;
static int curr_rtl_loc = -1;
/* Allocate insn locator datastructure. */ unsigned int
void insn_locators_initialize (void)
insn_locators_alloc (void)
{ {
tree block = NULL;
tree last_block = NULL;
rtx insn, next;
int loc = 0;
int line_number = 0, last_line_number = 0;
const char *file_name = NULL, *last_file_name = NULL;
prologue_locator = epilogue_locator = 0; prologue_locator = epilogue_locator = 0;
block_locators_locs = VEC_alloc (int, heap, 32); block_locators_locs = VEC_alloc (int, heap, 32);
block_locators_blocks = VEC_alloc (tree, gc, 32); block_locators_blocks = VEC_alloc (tree, gc, 32);
locations_locators_locs = VEC_alloc (int, heap, 32); line_locators_locs = VEC_alloc (int, heap, 32);
locations_locators_vals = VEC_alloc (location_t, heap, 32); line_locators_lines = VEC_alloc (int, heap, 32);
file_locators_locs = VEC_alloc (int, heap, 32);
#ifdef USE_MAPPED_LOCATION VARRAY_CHAR_PTR_INIT (file_locators_files, 32, "file_locators_files");
last_location = -1;
curr_location = -1;
#else
last_location.line = -1;
curr_location.line = -1;
#endif
curr_block = NULL;
last_block = NULL;
curr_rtl_loc = 0;
}
/* At the end of emit stage, clear current location. */ for (insn = get_insns (); insn; insn = next)
void {
insn_locators_finalize (void) int active = 0;
{
if (curr_rtl_loc >= 0)
epilogue_locator = curr_insn_locator ();
curr_rtl_loc = -1;
}
/* Set current location. */ next = NEXT_INSN (insn);
void
set_curr_insn_source_location (location_t location)
{
gcc_assert (curr_rtl_loc >= 0);
#ifdef USE_MAPPED_LOCATION
if (location == last_location)
return;
#else
if (location.file && last_location.file
&& !strcmp (location.file, last_location.file)
&& location.line == last_location.line)
return;
#endif
curr_location = location;
}
/* Set current scope block. */ if (NOTE_P (insn))
void {
set_curr_insn_block (tree b) gcc_assert (NOTE_LINE_NUMBER (insn) != NOTE_INSN_BLOCK_BEG
{ && NOTE_LINE_NUMBER (insn) != NOTE_INSN_BLOCK_END);
gcc_assert (curr_rtl_loc >= 0); if (NOTE_LINE_NUMBER (insn) > 0)
if (b) {
curr_block = b; expanded_location xloc;
} NOTE_EXPANDED_LOCATION (xloc, insn);
line_number = xloc.line;
file_name = xloc.file;
delete_insn (insn);
}
}
else
active = (active_insn_p (insn)
&& GET_CODE (PATTERN (insn)) != ADDR_VEC
&& GET_CODE (PATTERN (insn)) != ADDR_DIFF_VEC);
/* Return current insn locator. */ check_block_change (insn, &block);
int
curr_insn_locator (void) if (active
{ || !next
if (curr_rtl_loc == -1) || (!prologue_locator && file_name))
return 0; {
if (last_block != curr_block) if (last_block != block)
{ {
curr_rtl_loc++; loc++;
VEC_safe_push (int, heap, block_locators_locs, curr_rtl_loc); VEC_safe_push (int, heap, block_locators_locs, loc);
VEC_safe_push (tree, gc, block_locators_blocks, curr_block); VEC_safe_push (tree, gc, block_locators_blocks, block);
last_block = curr_block; last_block = block;
} }
#ifdef USE_MAPPED_LOCATION if (last_line_number != line_number)
if (last_location != curr_location) {
#else loc++;
if (last_location.file != curr_location.file VEC_safe_push (int, heap, line_locators_locs, loc);
|| last_location.line != curr_location.line) VEC_safe_push (int, heap, line_locators_lines, line_number);
#endif last_line_number = line_number;
{ }
curr_rtl_loc++; if (last_file_name != file_name)
VEC_safe_push (int, heap, locations_locators_locs, curr_rtl_loc); {
VEC_safe_push (location_t, heap, locations_locators_vals, &curr_location); loc++;
last_location = curr_location; VEC_safe_push (int, heap, file_locators_locs, loc);
VARRAY_PUSH_CHAR_PTR (file_locators_files, (char *) file_name);
last_file_name = file_name;
}
if (!prologue_locator && file_name)
prologue_locator = loc;
if (!next)
epilogue_locator = loc;
if (active)
INSN_LOCATOR (insn) = loc;
}
} }
return curr_rtl_loc;
/* Tag the blocks with a depth number so that change_scope can find
the common parent easily. */
set_block_levels (DECL_INITIAL (cfun->decl), 0);
free_block_changes ();
return 0;
} }
struct tree_opt_pass pass_insn_locators_initialize =
{
"locators", /* name */
NULL, /* gate */
insn_locators_initialize, /* execute */
NULL, /* sub */
NULL, /* next */
0, /* static_pass_number */
0, /* tv_id */
0, /* properties_required */
0, /* properties_provided */
0, /* properties_destroyed */
0, /* todo_flags_start */
TODO_dump_func, /* todo_flags_finish */
0 /* letter */
};
static unsigned int static unsigned int
into_cfg_layout_mode (void) into_cfg_layout_mode (void)
{ {
...@@ -385,6 +401,20 @@ struct tree_opt_pass pass_outof_cfg_layout_mode = ...@@ -385,6 +401,20 @@ struct tree_opt_pass pass_outof_cfg_layout_mode =
TODO_dump_func, /* todo_flags_finish */ TODO_dump_func, /* todo_flags_finish */
0 /* letter */ 0 /* letter */
}; };
/* For each lexical block, set BLOCK_NUMBER to the depth at which it is
found in the block tree. */
static void
set_block_levels (tree block, int level)
{
while (block)
{
BLOCK_NUMBER (block) = level;
set_block_levels (BLOCK_SUBBLOCKS (block), level + 1);
block = BLOCK_CHAIN (block);
}
}
/* Return sope resulting from combination of S1 and S2. */ /* Return sope resulting from combination of S1 and S2. */
static tree static tree
...@@ -484,16 +514,18 @@ insn_scope (rtx insn) ...@@ -484,16 +514,18 @@ insn_scope (rtx insn)
} }
/* Return line number of the statement specified by the locator. */ /* Return line number of the statement specified by the locator. */
static location_t int
locator_location (int loc) locator_line (int loc)
{ {
int max = VEC_length (int, locations_locators_locs); int max = VEC_length (int, line_locators_locs);
int min = 0; int min = 0;
if (!max || !loc)
return 0;
while (1) while (1)
{ {
int pos = (min + max) / 2; int pos = (min + max) / 2;
int tmp = VEC_index (int, locations_locators_locs, pos); int tmp = VEC_index (int, line_locators_locs, pos);
if (tmp <= loc && min != pos) if (tmp <= loc && min != pos)
min = pos; min = pos;
...@@ -505,19 +537,7 @@ locator_location (int loc) ...@@ -505,19 +537,7 @@ locator_location (int loc)
break; break;
} }
} }
return *VEC_index (location_t, locations_locators_vals, min); return VEC_index (int, line_locators_lines, min);
}
/* Return source line of the statement that produced this insn. */
int
locator_line (int loc)
{
expanded_location xloc;
if (!loc)
return 0;
else
xloc = expand_location (locator_location (loc));
return xloc.line;
} }
/* Return line number of the statement that produced this insn. */ /* Return line number of the statement that produced this insn. */
...@@ -531,12 +551,27 @@ insn_line (rtx insn) ...@@ -531,12 +551,27 @@ insn_line (rtx insn)
const char * const char *
locator_file (int loc) locator_file (int loc)
{ {
expanded_location xloc; int max = VEC_length (int, file_locators_locs);
if (!loc) int min = 0;
return 0;
else if (!max || !loc)
xloc = expand_location (locator_location (loc)); return NULL;
return xloc.file; while (1)
{
int pos = (min + max) / 2;
int tmp = VEC_index (int, file_locators_locs, pos);
if (tmp <= loc && min != pos)
min = pos;
else if (tmp > loc && max != pos)
max = pos;
else
{
min = pos;
break;
}
}
return VARRAY_CHAR_PTR (file_locators_files, min);
} }
/* Return source file of the statement that produced this insn. */ /* Return source file of the statement that produced this insn. */
......
...@@ -3336,7 +3336,7 @@ make_insn_raw (rtx pattern) ...@@ -3336,7 +3336,7 @@ make_insn_raw (rtx pattern)
INSN_CODE (insn) = -1; INSN_CODE (insn) = -1;
LOG_LINKS (insn) = NULL; LOG_LINKS (insn) = NULL;
REG_NOTES (insn) = NULL; REG_NOTES (insn) = NULL;
INSN_LOCATOR (insn) = curr_insn_locator (); INSN_LOCATOR (insn) = 0;
BLOCK_FOR_INSN (insn) = NULL; BLOCK_FOR_INSN (insn) = NULL;
#ifdef ENABLE_RTL_CHECKING #ifdef ENABLE_RTL_CHECKING
...@@ -3369,7 +3369,7 @@ make_jump_insn_raw (rtx pattern) ...@@ -3369,7 +3369,7 @@ make_jump_insn_raw (rtx pattern)
LOG_LINKS (insn) = NULL; LOG_LINKS (insn) = NULL;
REG_NOTES (insn) = NULL; REG_NOTES (insn) = NULL;
JUMP_LABEL (insn) = NULL; JUMP_LABEL (insn) = NULL;
INSN_LOCATOR (insn) = curr_insn_locator (); INSN_LOCATOR (insn) = 0;
BLOCK_FOR_INSN (insn) = NULL; BLOCK_FOR_INSN (insn) = NULL;
return insn; return insn;
...@@ -3390,7 +3390,7 @@ make_call_insn_raw (rtx pattern) ...@@ -3390,7 +3390,7 @@ make_call_insn_raw (rtx pattern)
LOG_LINKS (insn) = NULL; LOG_LINKS (insn) = NULL;
REG_NOTES (insn) = NULL; REG_NOTES (insn) = NULL;
CALL_INSN_FUNCTION_USAGE (insn) = NULL; CALL_INSN_FUNCTION_USAGE (insn) = NULL;
INSN_LOCATOR (insn) = curr_insn_locator (); INSN_LOCATOR (insn) = 0;
BLOCK_FOR_INSN (insn) = NULL; BLOCK_FOR_INSN (insn) = NULL;
return insn; return insn;
...@@ -4460,6 +4460,42 @@ emit_barrier (void) ...@@ -4460,6 +4460,42 @@ emit_barrier (void)
return barrier; return barrier;
} }
/* Make line numbering NOTE insn for LOCATION add it to the end
of the doubly-linked list, but only if line-numbers are desired for
debugging info and it doesn't match the previous one. */
rtx
emit_line_note (location_t location)
{
rtx note;
#ifdef USE_MAPPED_LOCATION
if (location == last_location)
return NULL_RTX;
#else
if (location.file && last_location.file
&& !strcmp (location.file, last_location.file)
&& location.line == last_location.line)
return NULL_RTX;
#endif
last_location = location;
if (no_line_numbers)
{
cur_insn_uid++;
return NULL_RTX;
}
#ifdef USE_MAPPED_LOCATION
note = emit_note ((int) location);
#else
note = emit_note (location.line);
NOTE_SOURCE_FILE (note) = location.file;
#endif
return note;
}
/* Emit a copy of note ORIG. */ /* Emit a copy of note ORIG. */
rtx rtx
......
...@@ -6777,14 +6777,14 @@ expand_expr_real (tree exp, rtx target, enum machine_mode tmode, ...@@ -6777,14 +6777,14 @@ expand_expr_real (tree exp, rtx target, enum machine_mode tmode,
information. It would be better of the diagnostic routines information. It would be better of the diagnostic routines
used the file/line information embedded in the tree nodes rather used the file/line information embedded in the tree nodes rather
than globals. */ than globals. */
if (cfun && EXPR_HAS_LOCATION (exp)) if (cfun && cfun->ib_boundaries_block && EXPR_HAS_LOCATION (exp))
{ {
location_t saved_location = input_location; location_t saved_location = input_location;
input_location = EXPR_LOCATION (exp); input_location = EXPR_LOCATION (exp);
set_curr_insn_source_location (input_location); emit_line_note (input_location);
/* Record where the insns produced belong. */ /* Record where the insns produced belong. */
set_curr_insn_block (TREE_BLOCK (exp)); record_block_change (TREE_BLOCK (exp));
ret = expand_expr_real_1 (exp, target, tmode, modifier, alt_rtl); ret = expand_expr_real_1 (exp, target, tmode, modifier, alt_rtl);
......
...@@ -3843,6 +3843,18 @@ init_function_start (tree subr) ...@@ -3843,6 +3843,18 @@ init_function_start (tree subr)
{ {
prepare_function_start (subr); prepare_function_start (subr);
/* Prevent ever trying to delete the first instruction of a
function. Also tell final how to output a linenum before the
function prologue. Note linenums could be missing, e.g. when
compiling a Java .class file. */
if (! DECL_IS_BUILTIN (subr))
emit_line_note (DECL_SOURCE_LOCATION (subr));
/* Make sure first insn is a note even if we don't want linenums.
This makes sure the first insn will never be deleted.
Also, final expects a note to appear there. */
emit_note (NOTE_INSN_DELETED);
/* Warn if this value is an aggregate type, /* Warn if this value is an aggregate type,
regardless of which calling convention we are using for it. */ regardless of which calling convention we are using for it. */
if (AGGREGATE_TYPE_P (TREE_TYPE (DECL_RESULT (subr)))) if (AGGREGATE_TYPE_P (TREE_TYPE (DECL_RESULT (subr))))
...@@ -4293,7 +4305,7 @@ expand_function_end (void) ...@@ -4293,7 +4305,7 @@ expand_function_end (void)
/* Output a linenumber for the end of the function. /* Output a linenumber for the end of the function.
SDB depends on this. */ SDB depends on this. */
force_next_line_note (); force_next_line_note ();
set_curr_insn_source_location (input_location); emit_line_note (input_location);
/* Before the return label (if any), clobber the return /* Before the return label (if any), clobber the return
registers so that they are not propagated live to the rest of registers so that they are not propagated live to the rest of
...@@ -5336,6 +5348,62 @@ reposition_prologue_and_epilogue_notes (rtx f ATTRIBUTE_UNUSED) ...@@ -5336,6 +5348,62 @@ reposition_prologue_and_epilogue_notes (rtx f ATTRIBUTE_UNUSED)
#endif /* HAVE_prologue or HAVE_epilogue */ #endif /* HAVE_prologue or HAVE_epilogue */
} }
/* Resets insn_block_boundaries array. */
void
reset_block_changes (void)
{
cfun->ib_boundaries_block = VEC_alloc (tree, gc, 100);
VEC_quick_push (tree, cfun->ib_boundaries_block, NULL_TREE);
}
/* Record the boundary for BLOCK. */
void
record_block_change (tree block)
{
int i, n;
tree last_block;
if (!block)
return;
if(!cfun->ib_boundaries_block)
return;
last_block = VEC_pop (tree, cfun->ib_boundaries_block);
n = get_max_uid ();
for (i = VEC_length (tree, cfun->ib_boundaries_block); i < n; i++)
VEC_safe_push (tree, gc, cfun->ib_boundaries_block, last_block);
VEC_safe_push (tree, gc, cfun->ib_boundaries_block, block);
}
/* Finishes record of boundaries. */
void
finalize_block_changes (void)
{
record_block_change (DECL_INITIAL (current_function_decl));
}
/* For INSN return the BLOCK it belongs to. */
void
check_block_change (rtx insn, tree *block)
{
unsigned uid = INSN_UID (insn);
if (uid >= VEC_length (tree, cfun->ib_boundaries_block))
return;
*block = VEC_index (tree, cfun->ib_boundaries_block, uid);
}
/* Releases the ib_boundaries_block records. */
void
free_block_changes (void)
{
VEC_free (tree, gc, cfun->ib_boundaries_block);
}
/* Returns the name of the current function. */ /* Returns the name of the current function. */
const char * const char *
current_function_name (void) current_function_name (void)
......
...@@ -347,6 +347,9 @@ struct function GTY(()) ...@@ -347,6 +347,9 @@ struct function GTY(())
/* Line number of the end of the function. */ /* Line number of the end of the function. */
location_t function_end_locus; location_t function_end_locus;
/* Array mapping insn uids to blocks. */
VEC(tree,gc) *ib_boundaries_block;
/* The variables unexpanded so far. */ /* The variables unexpanded so far. */
tree unexpanded_var_list; tree unexpanded_var_list;
...@@ -549,6 +552,11 @@ extern void number_blocks (tree); ...@@ -549,6 +552,11 @@ extern void number_blocks (tree);
extern void clear_block_marks (tree); extern void clear_block_marks (tree);
extern tree blocks_nreverse (tree); extern tree blocks_nreverse (tree);
extern void reset_block_changes (void);
extern void record_block_change (tree);
extern void finalize_block_changes (void);
extern void check_block_change (rtx, tree *);
extern void free_block_changes (void);
/* Return size needed for stack frame based on slots so far allocated. /* Return size needed for stack frame based on slots so far allocated.
This size counts from zero. It is not rounded to STACK_BOUNDARY; This size counts from zero. It is not rounded to STACK_BOUNDARY;
......
...@@ -654,6 +654,7 @@ init_optimization_passes (void) ...@@ -654,6 +654,7 @@ init_optimization_passes (void)
struct tree_opt_pass **p = &pass_rest_of_compilation.sub; struct tree_opt_pass **p = &pass_rest_of_compilation.sub;
NEXT_PASS (pass_init_function); NEXT_PASS (pass_init_function);
NEXT_PASS (pass_jump); NEXT_PASS (pass_jump);
NEXT_PASS (pass_insn_locators_initialize);
NEXT_PASS (pass_rtl_eh); NEXT_PASS (pass_rtl_eh);
NEXT_PASS (pass_initial_value_sets); NEXT_PASS (pass_initial_value_sets);
NEXT_PASS (pass_unshare_all_rtl); NEXT_PASS (pass_unshare_all_rtl);
......
...@@ -1562,6 +1562,7 @@ extern rtx emit_label (rtx); ...@@ -1562,6 +1562,7 @@ extern rtx emit_label (rtx);
extern rtx emit_barrier (void); extern rtx emit_barrier (void);
extern rtx emit_note (int); extern rtx emit_note (int);
extern rtx emit_note_copy (rtx); extern rtx emit_note_copy (rtx);
extern rtx emit_line_note (location_t);
extern rtx make_insn_raw (rtx); extern rtx make_insn_raw (rtx);
extern rtx make_jump_insn_raw (rtx); extern rtx make_jump_insn_raw (rtx);
extern void add_function_usage_to (rtx, rtx); extern void add_function_usage_to (rtx, rtx);
...@@ -2297,10 +2298,4 @@ extern const struct rtl_hooks general_rtl_hooks; ...@@ -2297,10 +2298,4 @@ extern const struct rtl_hooks general_rtl_hooks;
/* Keep this for the nonce. */ /* Keep this for the nonce. */
#define gen_lowpart rtl_hooks.gen_lowpart #define gen_lowpart rtl_hooks.gen_lowpart
extern void insn_locators_alloc (void);
extern void insn_locators_finalize (void);
extern void set_curr_insn_source_location (location_t);
extern void set_curr_insn_block (tree);
extern int curr_insn_locator (void);
#endif /* ! GCC_RTL_H */ #endif /* ! GCC_RTL_H */
...@@ -1117,6 +1117,7 @@ initialize_cfun (tree new_fndecl, tree callee_fndecl, gcov_type count, ...@@ -1117,6 +1117,7 @@ initialize_cfun (tree new_fndecl, tree callee_fndecl, gcov_type count,
new_cfun->unexpanded_var_list = NULL; new_cfun->unexpanded_var_list = NULL;
new_cfun->cfg = NULL; new_cfun->cfg = NULL;
new_cfun->decl = new_fndecl /*= copy_node (callee_fndecl)*/; new_cfun->decl = new_fndecl /*= copy_node (callee_fndecl)*/;
new_cfun->ib_boundaries_block = NULL;
DECL_STRUCT_FUNCTION (new_fndecl) = new_cfun; DECL_STRUCT_FUNCTION (new_fndecl) = new_cfun;
push_cfun (new_cfun); push_cfun (new_cfun);
init_empty_tree_cfg (); init_empty_tree_cfg ();
......
...@@ -329,6 +329,7 @@ extern struct tree_opt_pass pass_fixup_cfg; ...@@ -329,6 +329,7 @@ extern struct tree_opt_pass pass_fixup_cfg;
extern struct tree_opt_pass pass_init_function; extern struct tree_opt_pass pass_init_function;
extern struct tree_opt_pass pass_jump; extern struct tree_opt_pass pass_jump;
extern struct tree_opt_pass pass_insn_locators_initialize;
extern struct tree_opt_pass pass_rtl_eh; extern struct tree_opt_pass pass_rtl_eh;
extern struct tree_opt_pass pass_initial_value_sets; extern struct tree_opt_pass pass_initial_value_sets;
extern struct tree_opt_pass pass_unshare_all_rtl; extern struct tree_opt_pass pass_unshare_all_rtl;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment