Commit e72fcfe8 by Jan Hubicka Committed by Jan Hubicka

Makefile.in (CRTSTUFF_CFLAGS): Add -fno-unit-at-a-time

	* Makefile.in (CRTSTUFF_CFLAGS): Add -fno-unit-at-a-time
	(OBJS): Add callgraph.o
	(callgraph.o): New.
	* c-decl.c (expand_body_1): Break out from ...
	(expand_body): This one;  change calling convention
	(finish_function): Move some of expand_body logic here.
	(c_expand_deferred_function): Update call of expand_body
	(c_expand_stmt): Use c_expand_body_1.
	* c-lang.c (LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION): Define.
	* c-objc-commin.c (c_objc_common_finish_file): Use callgraph code.
	* c-tree.h (c_expand_body): Declare.
	* callgraph.c: New file.
	* flags.h (flag_unit_at_a_time): Declare.
	* langhooks.h (LANG_HOOKS_CALLGRAPH_LOWER_FUNCTION,
	LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION,
	LANG_HOOKS_CALLGRAPH_INITIALIZER): New macros.
	* langhooks.h (struct lang_hooks_for_callgraph): New.
	(struct lang_hooks): Add callgraph field.
	* toplev.c (flag_unit_at_a_time): New.
	(lang_independent_options): Add flag_unit_at_a_time.
	(process_options): Disable unit-at-a-time mode for frontends not
	supporting callgraph.
	* tree-inline.c (typedef struct inline_data): Add "decl"
	(expand_call_inline): Update callgraph.
	(optimize_inline_calls): Set id.decl.
	* tree.h (cgraph_finalize_function, cgraph_finalize_compilation_unit,
	cgraph_create_edges, dump_cgraph, cgraph_optimize, cgraph_remove_call
	cgraph_calls_p): Declare.
	* invoke.texi (-funit-at-a-time): Document

From-SVN: r62789
parent 9037b0c7
Wed Feb 12 22:47:18 CET 2003 Jan Hubicka <jh@suse.cz>
* Makefile.in (CRTSTUFF_CFLAGS): Add -fno-unit-at-a-time
(OBJS): Add callgraph.o
(callgraph.o): New.
* c-decl.c (expand_body_1): Break out from ...
(expand_body): This one; change calling convention
(finish_function): Move some of expand_body logic here.
(c_expand_deferred_function): Update call of expand_body
(c_expand_stmt): Use c_expand_body_1.
* c-lang.c (LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION): Define.
* c-objc-commin.c (c_objc_common_finish_file): Use callgraph code.
* c-tree.h (c_expand_body): Declare.
* callgraph.c: New file.
* flags.h (flag_unit_at_a_time): Declare.
* langhooks.h (LANG_HOOKS_CALLGRAPH_LOWER_FUNCTION,
LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION,
LANG_HOOKS_CALLGRAPH_INITIALIZER): New macros.
* langhooks.h (struct lang_hooks_for_callgraph): New.
(struct lang_hooks): Add callgraph field.
* toplev.c (flag_unit_at_a_time): New.
(lang_independent_options): Add flag_unit_at_a_time.
(process_options): Disable unit-at-a-time mode for frontends not
supporting callgraph.
* tree-inline.c (typedef struct inline_data): Add "decl"
(expand_call_inline): Update callgraph.
(optimize_inline_calls): Set id.decl.
* tree.h (cgraph_finalize_function, cgraph_finalize_compilation_unit,
cgraph_create_edges, dump_cgraph, cgraph_optimize, cgraph_remove_call
cgraph_calls_p): Declare.
* invoke.texi (-funit-at-a-time): Document
2003-02-12 Aldy Hernandez <aldyh@redhat.com> 2003-02-12 Aldy Hernandez <aldyh@redhat.com>
* config/rs6000/spe.h: Fix misc formatting. * config/rs6000/spe.h: Fix misc formatting.
......
...@@ -416,7 +416,7 @@ TARGET_LIBGCC2_CFLAGS = ...@@ -416,7 +416,7 @@ TARGET_LIBGCC2_CFLAGS =
# Options to use when compiling crtbegin/end. # Options to use when compiling crtbegin/end.
CRTSTUFF_CFLAGS = -O2 $(GCC_CFLAGS) $(INCLUDES) $(MULTILIB_CFLAGS) -g0 \ CRTSTUFF_CFLAGS = -O2 $(GCC_CFLAGS) $(INCLUDES) $(MULTILIB_CFLAGS) -g0 \
-finhibit-size-directive -fno-inline-functions -fno-exceptions \ -finhibit-size-directive -fno-inline-functions -fno-exceptions \
-fno-zero-initialized-in-bss -fno-zero-initialized-in-bss -fno-unit-at-a-time
# Additional sources to handle exceptions; overridden by targets as needed. # Additional sources to handle exceptions; overridden by targets as needed.
LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde.c \ LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde.c \
...@@ -785,7 +785,7 @@ OBJS = alias.o bb-reorder.o bitmap.o builtins.o caller-save.o calls.o \ ...@@ -785,7 +785,7 @@ OBJS = alias.o bb-reorder.o bitmap.o builtins.o caller-save.o calls.o \
sibcall.o simplify-rtx.o sreal.o ssa.o ssa-ccp.o ssa-dce.o stmt.o \ sibcall.o simplify-rtx.o sreal.o ssa.o ssa-ccp.o ssa-dce.o stmt.o \
stor-layout.o stringpool.o timevar.o toplev.o tracer.o tree.o tree-dump.o \ stor-layout.o stringpool.o timevar.o toplev.o tracer.o tree.o tree-dump.o \
tree-inline.o unroll.o varasm.o varray.o version.o vmsdbgout.o xcoffout.o \ tree-inline.o unroll.o varasm.o varray.o version.o vmsdbgout.o xcoffout.o \
alloc-pool.o et-forest.o \ alloc-pool.o et-forest.o cgraph.o \
$(GGC) $(out_object_file) $(EXTRA_OBJS) $(host_hook_obj) $(GGC) $(out_object_file) $(EXTRA_OBJS) $(host_hook_obj)
BACKEND = main.o libbackend.a BACKEND = main.o libbackend.a
...@@ -1530,6 +1530,8 @@ jump.o : jump.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) flags.h \ ...@@ -1530,6 +1530,8 @@ jump.o : jump.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) flags.h \
simplify-rtx.o : simplify-rtx.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \ simplify-rtx.o : simplify-rtx.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \
$(REGS_H) hard-reg-set.h flags.h real.h insn-config.h $(RECOG_H) $(EXPR_H) toplev.h \ $(REGS_H) hard-reg-set.h flags.h real.h insn-config.h $(RECOG_H) $(EXPR_H) toplev.h \
output.h function.h $(GGC_H) $(OBSTACK_H) $(TM_P_H) $(TREE_H) $(TARGET_H) output.h function.h $(GGC_H) $(OBSTACK_H) $(TM_P_H) $(TREE_H) $(TARGET_H)
cgraph.o : cgraph.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) \
langhooks.h tree-inline.h toplev.h flags.h ggc.h $(TARGET_H)
cselib.o : cselib.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \ cselib.o : cselib.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(REGS_H) \
hard-reg-set.h flags.h real.h insn-config.h $(RECOG_H) $(EXPR_H) toplev.h \ hard-reg-set.h flags.h real.h insn-config.h $(RECOG_H) $(EXPR_H) toplev.h \
output.h function.h cselib.h $(GGC_H) $(TM_P_H) gt-cselib.h output.h function.h cselib.h $(GGC_H) $(TM_P_H) gt-cselib.h
......
...@@ -282,7 +282,7 @@ static tree grokdeclarator PARAMS ((tree, tree, enum decl_context, ...@@ -282,7 +282,7 @@ static tree grokdeclarator PARAMS ((tree, tree, enum decl_context,
static tree grokparms PARAMS ((tree, int)); static tree grokparms PARAMS ((tree, int));
static void layout_array_type PARAMS ((tree)); static void layout_array_type PARAMS ((tree));
static tree c_make_fname_decl PARAMS ((tree, int)); static tree c_make_fname_decl PARAMS ((tree, int));
static void c_expand_body PARAMS ((tree, int, int)); static void c_expand_body_1 PARAMS ((tree, int));
static void warn_if_shadowing PARAMS ((tree, tree)); static void warn_if_shadowing PARAMS ((tree, tree));
static bool flexible_array_type_p PARAMS ((tree)); static bool flexible_array_type_p PARAMS ((tree));
...@@ -6412,49 +6412,28 @@ finish_function (nested, can_defer_p) ...@@ -6412,49 +6412,28 @@ finish_function (nested, can_defer_p)
free_after_compilation (cfun); free_after_compilation (cfun);
cfun = NULL; cfun = NULL;
if (! nested) if (flag_unit_at_a_time)
{ {
/* Generate RTL for the body of this function. */ cgraph_finalize_function (fndecl, DECL_SAVED_TREE (fndecl));
c_expand_body (fndecl, nested, can_defer_p);
/* Let the error reporting routines know that we're outside a
function. For a nested function, this value is used in
c_pop_function_context and then reset via pop_function_context. */
current_function_decl = NULL; current_function_decl = NULL;
return;
} }
}
/* Generate the RTL for a deferred function FNDECL. */
void if (! nested)
c_expand_deferred_function (fndecl)
tree fndecl;
{
/* DECL_INLINE or DECL_RESULT might got cleared after the inline
function was deferred, e.g. in duplicate_decls. */
if (DECL_INLINE (fndecl) && DECL_RESULT (fndecl))
{ {
c_expand_body (fndecl, 0, 0); /* Function is parsed.
current_function_decl = NULL; Generate RTL for the body of this function or defer
} it for later expansion. */
}
/* Generate the RTL for the body of FNDECL. If NESTED_P is nonzero,
then we are already in the process of generating RTL for another
function. If can_defer_p is zero, we won't attempt to defer the
generation of RTL. */
static void
c_expand_body (fndecl, nested_p, can_defer_p)
tree fndecl;
int nested_p, can_defer_p;
{
int uninlinable = 1; int uninlinable = 1;
/* There's no reason to do any of the work here if we're only doing /* There's no reason to do any of the work here if we're only doing
semantic analysis; this code just generates RTL. */ semantic analysis; this code just generates RTL. */
if (flag_syntax_only) if (flag_syntax_only)
{
current_function_decl = NULL;
DECL_SAVED_TREE (fndecl) = NULL_TREE;
return; return;
}
if (flag_inline_trees) if (flag_inline_trees)
{ {
...@@ -6473,6 +6452,7 @@ c_expand_body (fndecl, nested_p, can_defer_p) ...@@ -6473,6 +6452,7 @@ c_expand_body (fndecl, nested_p, can_defer_p)
/* Let the back-end know that this function exists. */ /* Let the back-end know that this function exists. */
(*debug_hooks->deferred_inline_function) (fndecl); (*debug_hooks->deferred_inline_function) (fndecl);
timevar_pop (TV_INTEGRATION); timevar_pop (TV_INTEGRATION);
current_function_decl = NULL;
return; return;
} }
...@@ -6481,6 +6461,52 @@ c_expand_body (fndecl, nested_p, can_defer_p) ...@@ -6481,6 +6461,52 @@ c_expand_body (fndecl, nested_p, can_defer_p)
timevar_pop (TV_INTEGRATION); timevar_pop (TV_INTEGRATION);
} }
c_expand_body (fndecl);
if (uninlinable)
{
/* Allow the body of the function to be garbage collected. */
DECL_SAVED_TREE (fndecl) = NULL_TREE;
}
/* Let the error reporting routines know that we're outside a
function. For a nested function, this value is used in
c_pop_function_context and then reset via pop_function_context. */
current_function_decl = NULL;
}
}
/* Generate the RTL for a deferred function FNDECL. */
void
c_expand_deferred_function (fndecl)
tree fndecl;
{
/* DECL_INLINE or DECL_RESULT might got cleared after the inline
function was deferred, e.g. in duplicate_decls. */
if (DECL_INLINE (fndecl) && DECL_RESULT (fndecl))
{
if (flag_inline_trees)
{
timevar_push (TV_INTEGRATION);
optimize_inline_calls (fndecl);
timevar_pop (TV_INTEGRATION);
}
c_expand_body (fndecl);
current_function_decl = NULL;
}
}
/* Generate the RTL for the body of FNDECL. If NESTED_P is nonzero,
then we are already in the process of generating RTL for another
function. If can_defer_p is zero, we won't attempt to defer the
generation of RTL. */
static void
c_expand_body_1 (fndecl, nested_p)
tree fndecl;
int nested_p;
{
timevar_push (TV_EXPAND); timevar_push (TV_EXPAND);
if (nested_p) if (nested_p)
...@@ -6519,11 +6545,6 @@ c_expand_body (fndecl, nested_p, can_defer_p) ...@@ -6519,11 +6545,6 @@ c_expand_body (fndecl, nested_p, can_defer_p)
/* Generate the RTL for this function. */ /* Generate the RTL for this function. */
expand_stmt (DECL_SAVED_TREE (fndecl)); expand_stmt (DECL_SAVED_TREE (fndecl));
if (uninlinable)
{
/* Allow the body of the function to be garbage collected. */
DECL_SAVED_TREE (fndecl) = NULL_TREE;
}
/* We hard-wired immediate_size_expand to zero above. /* We hard-wired immediate_size_expand to zero above.
expand_function_end will decrement this variable. So, we set the expand_function_end will decrement this variable. So, we set the
...@@ -6622,6 +6643,15 @@ c_expand_body (fndecl, nested_p, can_defer_p) ...@@ -6622,6 +6643,15 @@ c_expand_body (fndecl, nested_p, can_defer_p)
timevar_pop (TV_EXPAND); timevar_pop (TV_EXPAND);
} }
/* Like c_expand_body_1 but only for unnested functions. */
void
c_expand_body (fndecl)
tree fndecl;
{
c_expand_body_1 (fndecl, 0);
}
/* Check the declarations given in a for-loop for satisfying the C99 /* Check the declarations given in a for-loop for satisfying the C99
constraints. */ constraints. */
void void
...@@ -6854,7 +6884,7 @@ c_expand_decl_stmt (t) ...@@ -6854,7 +6884,7 @@ c_expand_decl_stmt (t)
if (TREE_CODE (decl) == FUNCTION_DECL if (TREE_CODE (decl) == FUNCTION_DECL
&& DECL_CONTEXT (decl) == current_function_decl && DECL_CONTEXT (decl) == current_function_decl
&& DECL_SAVED_TREE (decl)) && DECL_SAVED_TREE (decl))
c_expand_body (decl, /*nested_p=*/1, /*can_defer_p=*/0); c_expand_body_1 (decl, 1);
} }
/* Return the IDENTIFIER_GLOBAL_VALUE of T, for use in common code, since /* Return the IDENTIFIER_GLOBAL_VALUE of T, for use in common code, since
......
...@@ -99,6 +99,9 @@ static void c_init_options PARAMS ((void)); ...@@ -99,6 +99,9 @@ static void c_init_options PARAMS ((void));
#undef LANG_HOOKS_TREE_DUMP_DUMP_TREE_FN #undef LANG_HOOKS_TREE_DUMP_DUMP_TREE_FN
#define LANG_HOOKS_TREE_DUMP_DUMP_TREE_FN c_dump_tree #define LANG_HOOKS_TREE_DUMP_DUMP_TREE_FN c_dump_tree
#undef LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION
#define LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION c_expand_body
#undef LANG_HOOKS_TYPE_FOR_MODE #undef LANG_HOOKS_TYPE_FOR_MODE
#define LANG_HOOKS_TYPE_FOR_MODE c_common_type_for_mode #define LANG_HOOKS_TYPE_FOR_MODE c_common_type_for_mode
#undef LANG_HOOKS_TYPE_FOR_SIZE #undef LANG_HOOKS_TYPE_FOR_SIZE
......
...@@ -361,6 +361,12 @@ c_objc_common_finish_file () ...@@ -361,6 +361,12 @@ c_objc_common_finish_file ()
if (pch_file) if (pch_file)
c_common_write_pch (); c_common_write_pch ();
if (flag_unit_at_a_time)
{
cgraph_finalize_compilation_unit ();
cgraph_optimize ();
}
else
expand_deferred_fns (); expand_deferred_fns ();
if (static_ctors) if (static_ctors)
......
...@@ -172,6 +172,7 @@ extern void finish_file PARAMS ((void)); ...@@ -172,6 +172,7 @@ extern void finish_file PARAMS ((void));
extern int objc_comptypes PARAMS ((tree, tree, int)); extern int objc_comptypes PARAMS ((tree, tree, int));
extern tree objc_message_selector PARAMS ((void)); extern tree objc_message_selector PARAMS ((void));
extern tree lookup_objc_ivar PARAMS ((tree)); extern tree lookup_objc_ivar PARAMS ((tree));
extern void c_expand_body PARAMS ((tree));
/* in c-parse.in */ /* in c-parse.in */
......
This diff is collapsed. Click to expand it.
...@@ -290,7 +290,7 @@ in the following sections. ...@@ -290,7 +290,7 @@ in the following sections.
-fsched-spec-load-dangerous -fsignaling-nans @gol -fsched-spec-load-dangerous -fsignaling-nans @gol
-fsingle-precision-constant -fssa -fssa-ccp -fssa-dce @gol -fsingle-precision-constant -fssa -fssa-ccp -fssa-dce @gol
-fstrength-reduce -fstrict-aliasing -ftracer -fthread-jumps @gol -fstrength-reduce -fstrict-aliasing -ftracer -fthread-jumps @gol
-funroll-all-loops -funroll-loops -funswitch-loops @gol -funit-at-a-time -funroll-all-loops -funroll-loops -funswitch-loops @gol
--param @var{name}=@var{value} --param @var{name}=@var{value}
-O -O0 -O1 -O2 -O3 -Os} -O -O0 -O1 -O2 -O3 -Os}
...@@ -4261,6 +4261,11 @@ Perform tail duplication to enlarge superblock size. This transformation ...@@ -4261,6 +4261,11 @@ Perform tail duplication to enlarge superblock size. This transformation
simplifies the control flow of the function allowing other optimizations to do simplifies the control flow of the function allowing other optimizations to do
better job. better job.
@item -funit-at-a-time
@opindex funit-at-a-time
Parse the whole compilation unit before starting to produce code. This allows some
extra optimizations to take place but consumes more memory.
@item -funroll-loops @item -funroll-loops
@opindex funroll-loops @opindex funroll-loops
Unroll loops whose number of iterations can be determined at compile Unroll loops whose number of iterations can be determined at compile
......
...@@ -652,6 +652,8 @@ extern int flag_zero_initialized_in_bss; ...@@ -652,6 +652,8 @@ extern int flag_zero_initialized_in_bss;
/* Nonzero means disable transformations observable by signaling NaNs. */ /* Nonzero means disable transformations observable by signaling NaNs. */
extern int flag_signaling_nans; extern int flag_signaling_nans;
extern int flag_unit_at_a_time;
/* True if the given mode has a NaN representation and the treatment of /* True if the given mode has a NaN representation and the treatment of
NaN operands is important. Certain optimizations, such as folding NaN operands is important. Certain optimizations, such as folding
x * 0 into x, are not correct for NaN operands, and are normally x * 0 into x, are not correct for NaN operands, and are normally
......
...@@ -164,6 +164,14 @@ tree lhd_tree_inlining_convert_parm_for_inlining PARAMS ((tree, tree, tree)); ...@@ -164,6 +164,14 @@ tree lhd_tree_inlining_convert_parm_for_inlining PARAMS ((tree, tree, tree));
LANG_HOOKS_TREE_INLINING_CONVERT_PARM_FOR_INLINING \ LANG_HOOKS_TREE_INLINING_CONVERT_PARM_FOR_INLINING \
} \ } \
#define LANG_HOOKS_CALLGRAPH_LOWER_FUNCTION NULL
#define LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION NULL
#define LANG_HOOKS_CALLGRAPH_INITIALIZER { \
LANG_HOOKS_CALLGRAPH_LOWER_FUNCTION, \
LANG_HOOKS_CALLGRAPH_EXPAND_FUNCTION, \
} \
#define LANG_HOOKS_FUNCTION_INITIALIZER { \ #define LANG_HOOKS_FUNCTION_INITIALIZER { \
LANG_HOOKS_FUNCTION_INIT, \ LANG_HOOKS_FUNCTION_INIT, \
LANG_HOOKS_FUNCTION_FINAL, \ LANG_HOOKS_FUNCTION_FINAL, \
...@@ -261,6 +269,7 @@ int lhd_tree_dump_type_quals PARAMS ((tree)); ...@@ -261,6 +269,7 @@ int lhd_tree_dump_type_quals PARAMS ((tree));
LANG_HOOKS_FORMAT_ATTRIBUTE_TABLE, \ LANG_HOOKS_FORMAT_ATTRIBUTE_TABLE, \
LANG_HOOKS_FUNCTION_INITIALIZER, \ LANG_HOOKS_FUNCTION_INITIALIZER, \
LANG_HOOKS_TREE_INLINING_INITIALIZER, \ LANG_HOOKS_TREE_INLINING_INITIALIZER, \
LANG_HOOKS_CALLGRAPH_INITIALIZER, \
LANG_HOOKS_TREE_DUMP_INITIALIZER, \ LANG_HOOKS_TREE_DUMP_INITIALIZER, \
LANG_HOOKS_DECLS, \ LANG_HOOKS_DECLS, \
LANG_HOOKS_FOR_TYPES_INITIALIZER \ LANG_HOOKS_FOR_TYPES_INITIALIZER \
......
...@@ -58,6 +58,15 @@ struct lang_hooks_for_tree_inlining ...@@ -58,6 +58,15 @@ struct lang_hooks_for_tree_inlining
union tree_node *)); union tree_node *));
}; };
struct lang_hooks_for_callgraph
{
/* Function passed as argument is needed and will be compiled.
Lower the representation so the calls are explicit. */
void (*lower_function) PARAMS ((union tree_node *));
/* Produce RTL for function passed as argument. */
void (*expand_function) PARAMS ((union tree_node *));
};
/* Lang hooks for management of language-specific data or status /* Lang hooks for management of language-specific data or status
when entering / leaving functions etc. */ when entering / leaving functions etc. */
struct lang_hooks_for_functions struct lang_hooks_for_functions
...@@ -353,6 +362,8 @@ struct lang_hooks ...@@ -353,6 +362,8 @@ struct lang_hooks
struct lang_hooks_for_tree_inlining tree_inlining; struct lang_hooks_for_tree_inlining tree_inlining;
struct lang_hooks_for_callgraph callgraph;
struct lang_hooks_for_tree_dump tree_dump; struct lang_hooks_for_tree_dump tree_dump;
struct lang_hooks_for_decls decls; struct lang_hooks_for_decls decls;
......
...@@ -883,6 +883,10 @@ int flag_new_regalloc = 0; ...@@ -883,6 +883,10 @@ int flag_new_regalloc = 0;
int flag_tracer = 0; int flag_tracer = 0;
/* Nonzero if we perform whole unit at a time compilation. */
int flag_unit_at_a_time = 0;
/* Values of the -falign-* flags: how much to align labels in code. /* Values of the -falign-* flags: how much to align labels in code.
0 means `use default', 1 means `don't align'. 0 means `use default', 1 means `don't align'.
For each variable, there is an _log variant which is the power For each variable, there is an _log variant which is the power
...@@ -989,6 +993,8 @@ static const lang_independent_options f_options[] = ...@@ -989,6 +993,8 @@ static const lang_independent_options f_options[] =
N_("Optimize sibling and tail recursive calls") }, N_("Optimize sibling and tail recursive calls") },
{"tracer", &flag_tracer, 1, {"tracer", &flag_tracer, 1,
N_("Perform superblock formation via tail duplication") }, N_("Perform superblock formation via tail duplication") },
{"unit-at-a-time", &flag_unit_at_a_time, 1,
N_("Compile whole compilation unit at a time") },
{"cse-follow-jumps", &flag_cse_follow_jumps, 1, {"cse-follow-jumps", &flag_cse_follow_jumps, 1,
N_("When running CSE, follow jumps to their targets") }, N_("When running CSE, follow jumps to their targets") },
{"cse-skip-blocks", &flag_cse_skip_blocks, 1, {"cse-skip-blocks", &flag_cse_skip_blocks, 1,
...@@ -5124,6 +5130,11 @@ process_options () ...@@ -5124,6 +5130,11 @@ process_options ()
if (flag_asynchronous_unwind_tables) if (flag_asynchronous_unwind_tables)
flag_unwind_tables = 1; flag_unwind_tables = 1;
/* Disable unit-at-a-time mode for frontends not supporting callgraph
interface. */
if (flag_unit_at_a_time && ! lang_hooks.callgraph.expand_function)
flag_unit_at_a_time = 0;
/* Warn about options that are not supported on this machine. */ /* Warn about options that are not supported on this machine. */
#ifndef INSN_SCHEDULING #ifndef INSN_SCHEDULING
if (flag_schedule_insns || flag_schedule_insns_after_reload) if (flag_schedule_insns || flag_schedule_insns_after_reload)
......
...@@ -103,6 +103,8 @@ typedef struct inline_data ...@@ -103,6 +103,8 @@ typedef struct inline_data
/* Hash table used to prevent walk_tree from visiting the same node /* Hash table used to prevent walk_tree from visiting the same node
umpteen million times. */ umpteen million times. */
htab_t tree_pruner; htab_t tree_pruner;
/* Decl of function we are inlining into. */
tree decl;
} inline_data; } inline_data;
/* Prototypes. */ /* Prototypes. */
...@@ -1368,6 +1370,13 @@ expand_call_inline (tp, walk_subtrees, data) ...@@ -1368,6 +1370,13 @@ expand_call_inline (tp, walk_subtrees, data)
/* For accounting, subtract one for the saved call/ret. */ /* For accounting, subtract one for the saved call/ret. */
id->inlined_stmts += DECL_NUM_STMTS (fn) - 1; id->inlined_stmts += DECL_NUM_STMTS (fn) - 1;
/* Update callgraph if needed. */
if (id->decl && flag_unit_at_a_time)
{
cgraph_remove_call (id->decl, fn);
cgraph_create_edges (id->decl, *inlined_body);
}
/* Recurse into the body of the just inlined function. */ /* Recurse into the body of the just inlined function. */
expand_calls_inline (inlined_body, id); expand_calls_inline (inlined_body, id);
VARRAY_POP (id->fns); VARRAY_POP (id->fns);
...@@ -1414,6 +1423,7 @@ optimize_inline_calls (fn) ...@@ -1414,6 +1423,7 @@ optimize_inline_calls (fn)
/* Clear out ID. */ /* Clear out ID. */
memset (&id, 0, sizeof (id)); memset (&id, 0, sizeof (id));
id.decl = fn;
/* Don't allow recursion into FN. */ /* Don't allow recursion into FN. */
VARRAY_TREE_INIT (id.fns, 32, "fns"); VARRAY_TREE_INIT (id.fns, 32, "fns");
VARRAY_PUSH_TREE (id.fns, fn); VARRAY_PUSH_TREE (id.fns, fn);
......
...@@ -3164,6 +3164,15 @@ extern const char *dump_flag_name PARAMS ((enum tree_dump_index)); ...@@ -3164,6 +3164,15 @@ extern const char *dump_flag_name PARAMS ((enum tree_dump_index));
extern void set_decl_rtl PARAMS ((tree, rtx)); extern void set_decl_rtl PARAMS ((tree, rtx));
/* In callgraph.c */
void cgraph_finalize_function PARAMS ((tree, tree));
void cgraph_finalize_compilation_unit PARAMS ((void));
void cgraph_create_edges PARAMS ((tree, tree));
void dump_cgraph PARAMS ((FILE *));
void cgraph_optimize PARAMS ((void));
void cgraph_remove_call PARAMS ((tree, tree));
bool cgraph_calls_p PARAMS ((tree, tree));
/* Redefine abort to report an internal error w/o coredump, and /* Redefine abort to report an internal error w/o coredump, and
reporting the location of the error in the source file. This logic reporting the location of the error in the source file. This logic
......
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