coverage.c: Remove argument to rest_of_compilation.

gcc/ChangeLog:
2004-06-16  Paolo Bonzini  <bonzini@gnu.org>

	* coverage.c: Remove argument to rest_of_compilation.
	* expr.c (execute_expand, set_save_expr_context, pass_expand): New.
	* passes.c (rest_of_compilation): Remove argument.
	(pass_rest_of_compilation): New.
	(rest_of_handle_final, rest_of_handle_delay_slots,
	rest_of_handle_stack_regs, rest_of_handle_variable_tracking
	rest_of_handle_machine_reorg, rest_of_handle_regrename
	rest_of_handle_sched, rest_of_handle_sched2, rest_of_handle_gcse2
	rest_of_handle_regmove, rest_of_handle_tracer
	rest_of_handle_if_conversion, rest_of_handle_if_after_combine
	rest_of_handle_web, rest_of_handle_branch_prob
	rest_of_handle_value_profile_transformations, rest_of_handle_cfg
	rest_of_handle_addressof, rest_of_handle_jump_bypass
	rest_of_handle_life, rest_of_handle_cse, rest_of_handle_cse2):
	Check that the two arguments are actually superfluous.
	* toplev.h (rest_of_compilation): Adjust prototype.
	* tree-optimize.c (register_dump_files): Add properties argument.
	Track validity of passes.  Only initialize dump files for
	tree-based passes.  Store the full set of provided passes in
	the pass.
	(init_tree_optimization_passes): Register pass_expand and
	pass_rest_of_compilation.
	(execute_one_pass): Do not track the presence of required properties
	here.  Set in_gimple_form.  Do not update current_properties.
	(current_properties): Remove.
	(set_save_expr_context): Remove.
	(tree_rest_of_compilation): Do not set in_gimple_form.  Do not
	expand to RTL here, and do not call rest_of_compilation.  Push
	GGC context even before gimplification.
	* tree-pass.h (PROP_rtl, PROP_trees): New flags.
	(pass_expand, pass_rest_of_compilation): Declare.

gcc/java/ChangeLog:
2004-06-16  Paolo Bonzini  <bonzini@gnu.org>

	* java/class.c (emit_register_classes): Remove argument to
	rest_of_compilation.
	* java/resource.c (write_resource_constructor): Likewise.

From-SVN: r83225
This commit is contained in:
Paolo Bonzini 2004-06-16 07:25:53 +00:00
parent fd660b1bee
commit 2f8e398bf4
7 changed files with 234 additions and 98 deletions

View File

@ -955,7 +955,7 @@ create_coverage (void)
DECL_INITIAL (ctor) = make_node (BLOCK);
TREE_USED (DECL_INITIAL (ctor)) = 1;
rest_of_compilation (ctor);
rest_of_compilation ();
if (! quiet_flag)
fflush (asm_out_file);

View File

@ -48,7 +48,10 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
#include "intl.h"
#include "tm_p.h"
#include "tree-iterator.h"
#include "tree-pass.h"
#include "tree-flow.h"
#include "target.h"
#include "timevar.h"
/* Decide whether a function's arguments should be processed
from first to last or from last to first.
@ -165,6 +168,7 @@ static void emit_single_push_insn (enum machine_mode, rtx, tree);
#endif
static void do_tablejump (rtx, enum machine_mode, rtx, rtx, rtx);
static rtx const_vector_from_tree (tree);
static void execute_expand (void);
/* Record for each mode whether we can move a register directly to or
from an object of that mode in memory. If we can't, we won't try
@ -10204,5 +10208,92 @@ const_vector_from_tree (tree exp)
return gen_rtx_raw_CONST_VECTOR (mode, v);
}
/* Called to move the SAVE_EXPRs for parameter declarations in a
nested function into the nested function. DATA is really the
nested FUNCTION_DECL. */
static tree
set_save_expr_context (tree *tp,
int *walk_subtrees,
void *data)
{
if (TREE_CODE (*tp) == SAVE_EXPR && !SAVE_EXPR_CONTEXT (*tp))
SAVE_EXPR_CONTEXT (*tp) = (tree) data;
/* Do not walk back into the SAVE_EXPR_CONTEXT; that will cause
circularity. */
else if (DECL_P (*tp))
*walk_subtrees = 0;
return NULL;
}
static void
execute_expand (void)
{
/* If the function has a variably modified type, there may be
SAVE_EXPRs in the parameter types. Their context must be set to
refer to this function; they cannot be expanded in the containing
function. */
if (decl_function_context (current_function_decl) == current_function_decl
&& variably_modified_type_p (TREE_TYPE (current_function_decl)))
walk_tree (&TREE_TYPE (current_function_decl), set_save_expr_context,
current_function_decl, NULL);
/* Expand the variables recorded during gimple lowering. This must
occur before the call to expand_function_start to ensure that
all used variables are expanded before we expand anything on the
PENDING_SIZES list. */
expand_used_vars ();
/* Set up parameters and prepare for return, for the function. */
expand_function_start (current_function_decl, 0);
/* If this function is `main', emit a call to `__main'
to run global initializers, etc. */
if (DECL_NAME (current_function_decl)
&& MAIN_NAME_P (DECL_NAME (current_function_decl))
&& DECL_FILE_SCOPE_P (current_function_decl))
expand_main_function ();
/* Generate the RTL for this function. */
expand_expr_stmt_value (DECL_SAVED_TREE (current_function_decl), 0, 0);
/* We hard-wired immediate_size_expand to zero above.
expand_function_end will decrement this variable. So, we set the
variable to one here, so that after the decrement it will remain
zero. */
immediate_size_expand = 1;
/* Make sure the locus is set to the end of the function, so that
epilogue line numbers and warnings are set properly. */
if (cfun->function_end_locus.file)
input_location = cfun->function_end_locus;
/* The following insns belong to the top scope. */
record_block_change (DECL_INITIAL (current_function_decl));
/* Generate rtl for function exit. */
expand_function_end ();
}
struct tree_opt_pass pass_expand =
{
"expand", /* name */
NULL, /* gate */
execute_expand, /* execute */
NULL, /* sub */
NULL, /* next */
0, /* static_pass_number */
TV_EXPAND, /* tv_id */
/* ??? If TER is enabled, we actually receive GENERIC. */
PROP_gimple_leh, /* properties_required */
PROP_rtl, /* properties_provided */
PROP_cfg | PROP_gimple_leh, /* properties_destroyed */
0, /* todo_flags_start */
0 /* todo_flags_finish */
};
#include "gt-expr.h"

View File

@ -2316,7 +2316,7 @@ emit_register_classes (void)
input_location = DECL_SOURCE_LOCATION (init_decl);
expand_function_end ();
poplevel (1, 0, 1);
rest_of_compilation (init_decl);
rest_of_compilation ();
current_function_decl = NULL_TREE;
if (targetm.have_ctors_dtors)

View File

@ -153,7 +153,7 @@ write_resource_constructor (void)
poplevel (1, 0, 1);
/* rest_of_compilation forces generation even if -finline-functions. */
rest_of_compilation (init_decl);
rest_of_compilation ();
current_function_decl = NULL_TREE;
if (targetm.have_ctors_dtors)

View File

@ -80,6 +80,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
#include "coverage.h"
#include "value-prof.h"
#include "alloc-pool.h"
#include "tree-pass.h"
#if defined (DWARF2_UNWIND_INFO) || defined (DWARF2_DEBUGGING_INFO)
#include "dwarf2out.h"
@ -430,6 +431,9 @@ rest_of_type_compilation (tree type, int toplev)
static void
rest_of_handle_final (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_FINAL);
{
rtx x;
@ -483,6 +487,9 @@ rest_of_handle_final (tree decl, rtx insns)
static void
rest_of_handle_delay_slots (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_DBR_SCHED);
open_dump_file (DFI_dbr, decl);
@ -501,6 +508,9 @@ rest_of_handle_delay_slots (tree decl, rtx insns)
static void
rest_of_handle_stack_regs (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
#if defined (HAVE_ATTR_length)
/* If flow2 creates new instructions which need splitting
and scheduling after reload is not done, they might not be
@ -543,6 +553,9 @@ rest_of_handle_stack_regs (tree decl, rtx insns)
static void
rest_of_handle_variable_tracking (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_VAR_TRACKING);
open_dump_file (DFI_vartrack, decl);
@ -556,6 +569,9 @@ rest_of_handle_variable_tracking (tree decl, rtx insns)
static void
rest_of_handle_machine_reorg (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_MACH_DEP);
open_dump_file (DFI_mach, decl);
@ -575,6 +591,9 @@ rest_of_handle_new_regalloc (tree decl, rtx insns)
{
int failure;
if (decl != current_function_decl || insns != get_insns ())
abort ();
delete_trivially_dead_insns (insns, max_reg_num ());
reg_alloc ();
@ -622,6 +641,9 @@ rest_of_handle_old_regalloc (tree decl, rtx insns)
int failure;
int rebuild_notes;
if (decl != current_function_decl || insns != get_insns ())
abort ();
/* Allocate the reg_renumber array. */
allocate_reg_info (max_regno, FALSE, TRUE);
@ -695,6 +717,9 @@ rest_of_handle_old_regalloc (tree decl, rtx insns)
static void
rest_of_handle_regrename (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_RENAME_REGISTERS);
open_dump_file (DFI_rnreg, decl);
@ -714,6 +739,9 @@ rest_of_handle_reorder_blocks (tree decl, rtx insns)
bool changed;
open_dump_file (DFI_bbro, decl);
if (decl != current_function_decl || insns != get_insns ())
abort ();
/* Last attempt to optimize CFG, as scheduling, peepholing and insn
splitting possibly introduced more crossjumping opportunities. */
changed = cleanup_cfg (CLEANUP_EXPENSIVE
@ -744,6 +772,9 @@ rest_of_handle_reorder_blocks (tree decl, rtx insns)
static void
rest_of_handle_sched (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_SMS);
if (optimize > 0 && flag_modulo_sched)
{
@ -791,6 +822,9 @@ rest_of_handle_sched (tree decl, rtx insns)
static void
rest_of_handle_sched2 (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_SCHED2);
open_dump_file (DFI_sched2, decl);
@ -820,6 +854,9 @@ rest_of_handle_sched2 (tree decl, rtx insns)
static void
rest_of_handle_gcse2 (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_gcse2, decl);
gcse_after_reload_main (insns, dump_file);
@ -839,6 +876,9 @@ rest_of_handle_gcse2 (tree decl, rtx insns)
static void
rest_of_handle_regmove (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_REGMOVE);
open_dump_file (DFI_regmove, decl);
@ -855,6 +895,9 @@ rest_of_handle_regmove (tree decl, rtx insns)
static void
rest_of_handle_tracer (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_tracer, decl);
if (dump_file)
dump_flow_info (dump_file);
@ -868,6 +911,9 @@ rest_of_handle_tracer (tree decl, rtx insns)
static void
rest_of_handle_if_conversion (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_ce1, decl);
if (flag_if_conversion)
{
@ -891,6 +937,9 @@ rest_of_handle_if_conversion (tree decl, rtx insns)
static void
rest_of_handle_if_after_combine (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_IFCVT);
open_dump_file (DFI_ce2, decl);
@ -905,6 +954,9 @@ rest_of_handle_if_after_combine (tree decl, rtx insns)
static void
rest_of_handle_web (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_web, decl);
timevar_push (TV_WEB);
web_main ();
@ -921,6 +973,8 @@ static void
rest_of_handle_branch_prob (tree decl, rtx insns)
{
struct loops loops;
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_BRANCH_PROB);
open_dump_file (DFI_bp, decl);
@ -949,6 +1003,9 @@ rest_of_handle_branch_prob (tree decl, rtx insns)
static void
rest_of_handle_value_profile_transformations (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_vpt, decl);
timevar_push (TV_VPT);
@ -964,6 +1021,9 @@ rest_of_handle_value_profile_transformations (tree decl, rtx insns)
static void
rest_of_handle_cfg (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_cfg, decl);
if (dump_file)
dump_flow_info (dump_file);
@ -993,6 +1053,9 @@ rest_of_handle_cfg (tree decl, rtx insns)
static void
rest_of_handle_addressof (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_addressof, decl);
purge_addressof (insns);
@ -1007,6 +1070,9 @@ rest_of_handle_addressof (tree decl, rtx insns)
static void
rest_of_handle_jump_bypass (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_BYPASS);
open_dump_file (DFI_bypass, decl);
@ -1036,6 +1102,9 @@ rest_of_handle_combine (tree decl, rtx insns)
{
int rebuild_jump_labels_after_combine = 0;
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_COMBINE);
open_dump_file (DFI_combine, decl);
@ -1064,6 +1133,9 @@ rest_of_handle_combine (tree decl, rtx insns)
static void
rest_of_handle_life (tree decl, rtx insns)
{
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_life, decl);
regclass_init ();
@ -1110,6 +1182,8 @@ static void
rest_of_handle_cse (tree decl, rtx insns)
{
int tem;
if (decl != current_function_decl || insns != get_insns ())
abort ();
open_dump_file (DFI_cse, decl);
if (dump_file)
@ -1142,6 +1216,8 @@ static void
rest_of_handle_cse2 (tree decl, rtx insns)
{
int tem;
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_CSE2);
open_dump_file (DFI_cse2, decl);
@ -1178,6 +1254,8 @@ rest_of_handle_gcse (tree decl, rtx insns)
{
int save_csb, save_cfj;
int tem2 = 0, tem;
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_GCSE);
open_dump_file (DFI_gcse, decl);
@ -1241,6 +1319,9 @@ rest_of_handle_loop_optimize (tree decl, rtx insns)
{
int do_unroll, do_prefetch;
if (decl != current_function_decl || insns != get_insns ())
abort ();
timevar_push (TV_LOOP);
delete_dead_jumptables ();
cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_PRE_LOOP);
@ -1294,6 +1375,9 @@ rest_of_handle_loop2 (tree decl, rtx insns)
struct loops *loops;
basic_block bb;
if (decl != current_function_decl || insns != get_insns ())
abort ();
if (!flag_unswitch_loops
&& !flag_peel_loops
&& !flag_unroll_loops
@ -1353,11 +1437,15 @@ rest_of_handle_loop2 (tree decl, rtx insns)
After we return, the tree storage is freed. */
void
rest_of_compilation (tree decl)
rest_of_compilation (void)
{
tree decl = current_function_decl;
rtx insns;
timevar_push (TV_REST_OF_COMPILATION);
/* There's no need to defer outputting this function any more; we
know we want to output it. */
DECL_DEFER_OUTPUT (current_function_decl) = 0;
/* There's no need to defer outputting this function any more; we
know we want to output it. */
@ -1935,10 +2023,6 @@ rest_of_compilation (tree decl)
/* We're done with this function. Free up memory if we can. */
free_after_parsing (cfun);
ggc_collect ();
timevar_pop (TV_REST_OF_COMPILATION);
}
void
@ -2019,3 +2103,21 @@ enable_rtl_dump_file (int letter)
return matched;
}
struct tree_opt_pass pass_rest_of_compilation =
{
"rest of compilation", /* name */
NULL, /* gate */
rest_of_compilation, /* execute */
NULL, /* sub */
NULL, /* next */
0, /* static_pass_number */
TV_REST_OF_COMPILATION, /* tv_id */
PROP_rtl, /* properties_required */
0, /* properties_provided */
PROP_rtl, /* properties_destroyed */
0, /* todo_flags_start */
TODO_ggc_collect /* todo_flags_finish */
};

View File

@ -210,17 +210,31 @@ register_one_dump_file (struct tree_opt_pass *pass)
pass->static_pass_number = dump_register (dot_name, flag_name);
}
static void
register_dump_files (struct tree_opt_pass *pass)
static int
register_dump_files (struct tree_opt_pass *pass, int properties)
{
do
{
register_one_dump_file (pass);
/* Verify that all required properties are present. */
if (pass->properties_required & ~properties)
abort ();
if (pass->properties_destroyed & pass->properties_provided)
abort ();
pass->properties_required = properties;
pass->properties_provided = properties =
(properties | pass->properties_provided) & ~pass->properties_destroyed;
if (properties & PROP_trees)
register_one_dump_file (pass);
if (pass->sub)
register_dump_files (pass->sub);
properties = register_dump_files (pass->sub, properties);
pass = pass->next;
}
while (pass);
return properties;
}
/* Duplicate a pass that's to be run more than once. */
@ -272,6 +286,8 @@ init_tree_optimization_passes (void)
NEXT_PASS (pass_all_optimizations);
NEXT_PASS (pass_mudflap_2);
NEXT_PASS (pass_rebuild_bind);
NEXT_PASS (pass_expand);
NEXT_PASS (pass_rest_of_compilation);
*p = NULL;
p = &pass_all_optimizations.sub;
@ -326,12 +342,11 @@ init_tree_optimization_passes (void)
#undef DUP_PASS
/* Register the passes with the tree dump code. */
register_dump_files (all_passes);
register_dump_files (all_passes, 0);
}
static void execute_pass_list (struct tree_opt_pass *);
static unsigned int current_properties;
static unsigned int last_verified;
static void
@ -370,9 +385,9 @@ execute_one_pass (struct tree_opt_pass *pass)
if (pass->gate && !pass->gate ())
return false;
/* Verify that all required properties are present. */
if (pass->properties_required & ~current_properties)
abort ();
/* Note that the folders should only create gimple expressions.
This is a hack until the new folder is ready. */
in_gimple_form = (pass->properties_provided & PROP_trees) != 0;
/* Run pre-pass verification. */
todo = pass->todo_flags_start & ~last_verified;
@ -411,10 +426,6 @@ execute_one_pass (struct tree_opt_pass *pass)
if (todo)
execute_todo (todo);
/* Update properties. */
current_properties &= ~pass->properties_destroyed;
current_properties |= pass->properties_provided;
/* Close down timevar and dump file. */
if (pass->tv_id)
timevar_pop (pass->tv_id);
@ -440,25 +451,6 @@ execute_pass_list (struct tree_opt_pass *pass)
}
/* Called to move the SAVE_EXPRs for parameter declarations in a
nested function into the nested function. DATA is really the
nested FUNCTION_DECL. */
static tree
set_save_expr_context (tree *tp,
int *walk_subtrees,
void *data)
{
if (TREE_CODE (*tp) == SAVE_EXPR && !SAVE_EXPR_CONTEXT (*tp))
SAVE_EXPR_CONTEXT (*tp) = (tree) data;
/* Do not walk back into the SAVE_EXPR_CONTEXT; that will cause
circularity. */
else if (DECL_P (*tp))
*walk_subtrees = 0;
return NULL;
}
/* For functions-as-trees languages, this performs all optimization and
compilation for FNDECL. */
@ -522,68 +514,13 @@ tree_rest_of_compilation (tree fndecl, bool nested_p)
}
}
/* Note that the folders should only create gimple expressions.
This is a hack until the new folder is ready. */
in_gimple_form = true;
/* Perform all tree transforms and optimizations. */
execute_pass_list (all_passes);
/* Note that the folders can create non-gimple expressions again. */
in_gimple_form = false;
/* If the function has a variably modified type, there may be
SAVE_EXPRs in the parameter types. Their context must be set to
refer to this function; they cannot be expanded in the containing
function. */
if (decl_function_context (fndecl) == current_function_decl
&& variably_modified_type_p (TREE_TYPE (fndecl)))
walk_tree (&TREE_TYPE (fndecl), set_save_expr_context, fndecl,
NULL);
/* Expand the variables recorded during gimple lowering. This must
occur before the call to expand_function_start to ensure that
all used variables are expanded before we expand anything on the
PENDING_SIZES list. */
expand_used_vars ();
/* Set up parameters and prepare for return, for the function. */
expand_function_start (fndecl, 0);
/* If this function is `main', emit a call to `__main'
to run global initializers, etc. */
if (DECL_NAME (fndecl)
&& MAIN_NAME_P (DECL_NAME (fndecl))
&& DECL_FILE_SCOPE_P (fndecl))
expand_main_function ();
/* Generate the RTL for this function. */
expand_expr_stmt_value (DECL_SAVED_TREE (fndecl), 0, 0);
/* We hard-wired immediate_size_expand to zero above.
expand_function_end will decrement this variable. So, we set the
variable to one here, so that after the decrement it will remain
zero. */
immediate_size_expand = 1;
/* Make sure the locus is set to the end of the function, so that
epilogue line numbers and warnings are set properly. */
if (cfun->function_end_locus.file)
input_location = cfun->function_end_locus;
/* The following insns belong to the top scope. */
record_block_change (DECL_INITIAL (current_function_decl));
/* Generate rtl for function exit. */
expand_function_end ();
/* If this is a nested function, protect the local variables in the stack
above us from being collected while we're compiling this function. */
if (nested_p)
ggc_push_context ();
/* Run the optimizers and output the assembler code for this function. */
rest_of_compilation (fndecl);
/* Perform all tree transforms and optimizations. */
execute_pass_list (all_passes);
/* Restore original body if still needed. */
if (cfun->saved_tree)

View File

@ -75,6 +75,10 @@ struct tree_opt_pass
#define PROP_pta (1 << 5)
#define PROP_ssa (1 << 6)
#define PROP_no_crit_edges (1 << 7)
#define PROP_rtl (1 << 8)
#define PROP_trees \
(PROP_gimple_any | PROP_gimple_lcf | PROP_gimple_leh)
/* To-do flags. */
#define TODO_dump_func (1 << 0) /* pass doesn't dump itself */
@ -125,6 +129,8 @@ extern struct tree_opt_pass pass_dse;
extern struct tree_opt_pass pass_nrv;
extern struct tree_opt_pass pass_remove_useless_vars;
extern struct tree_opt_pass pass_rename_ssa_copies;
extern struct tree_opt_pass pass_expand;
extern struct tree_opt_pass pass_rest_of_compilation;
#endif /* GCC_TREE_PASS_H */