Handwritten part of conversion of passes to C++ classes

gcc/
	* Makefile.in (PASS_MANAGER_H): Add dep on pass-instances.def.
	(toplev.o): Add dep on PASS_MANAGER_H.
	* cgraphunit.c (cgraph_process_new_functions): Rework invocation
	of early local pases to reflect this moving from a global to a
	member of gcc::pass_manager.
	(cgraph_add_new_function): Likewise.
	* lto-cgraph.c (lto_output_node): Update for conversion of
	struct ipa_opt_pass_d to a C++ subclass of opt_pass.
	* passes.c (opt_pass::clone): New.
	(opt_pass::gate): New.
	(opt_pass::execute): New.
	(opt_pass::opt_pass): New.
	(pass_manager::execute_early_local_passes): New.
	(pass_manager::execute_pass_mode_switching): new.
	(finish_optimization_passes): Convert to...
	(pass_manager::finish_optimization_passes): ...this.
	(finish_optimization_passes): Update for conversion of passes to
	C++ classes.
	(register_dump_files_1): Use has_gate since we cannot portably
	check a vtable entry against NULL.
	(dump_one_pass): Likewise.
	(ipa_write_summaries_2): Likewise.
	(ipa_write_optimization_summaries_1): Likewise.
	(ipa_read_summaries_1): Likewise.
	(ipa_read_optimization_summaries_1): Likewise.
	(execute_ipa_stmt_fixups): Likewise.
	(pass_manager::pass_manager): Rewrite pass-creation, invoking
	pass-creation functions rather than wiring up globals, and
	storing the results in fields of pass_manager generated using
	pass-instances.def.
	(pass_manager::dump_profile_report): Update for conversion of
	passes to C++ classes.
	(pass_manager::execute_ipa_summary_passes): Likewise.
	(execute_one_ipa_transform_pass): Likewise.
	(execute_one_pass): Use has_gate and has_execute since we cannot
	portably check a vtable entry against NULL.
	* pass_manager.h (pass_manager::finish_optimization_passes): New.
	(pass_manager): Use pass-instances.def to add fields for the
	various pass instances.
	* toplev.c (finalize): Update for move of
	finish_optimization_passes to a method of gcc::pass_manager.
	* toplev.h (finish_optimization_passes): Move to method of class
	pass_manager.
	* tree-pass.h (struct pass_data): New.
	(opt_pass): Convert to C++ class, make it a subclass of
	pass_data.
	(opt_pass::gate): Convert to virtual function.
	(opt_pass::~opt_pass): New.
	(opt_pass::clone): New.
	(opt_pass::execute): Convert to virtual function.
	(opt_pass::opt_pass): New.
	(opt_pass::ctxt_): new.
	(gimple_opt_pass): Convert to subclass of opt_pass.
	(gimple_opt_pass::gimple_opt_pass): New.
	(rtl_opt_pass): Convert to subclass of opt_pass.
	(rtl_opt_pass::rtl_opt_pass): New.
	(ipa_opt_pass_d): Convert to subclass of opt_pass.
	(ipa_opt_pass_d::ipa_opt_pass_d): New.
	(simple_ipa_opt_pass): Convert to subclass of opt_pass.
	(simple_ipa_opt_pass::simple_ipa_opt_pass): New.
	* config/i386/i386.c (rest_of_handle_insert_vzeroupper): Rework
	invocation of pass_mode_switching to reflect this moving from a
	global to a member of gcc::pass_manager.
	(ix86_option_override): Rework how pass_insert_vzeroupper is
	added to the pass_manager to reflect autogenerated changes.
	* config/i386/t-i386 (i386.o) Add deps on CONTEXT_H and
	PASS_MANAGER_H.

gcc/testsuite/
	* g++.dg/plugin/dumb_plugin.c (plugin_init): Rework how the pass
	is created and added to the pass_manager to reflect
	autogenerated changes.
	* g++.dg/plugin/selfassign.c (plugin_init): Likewise.
	* gcc.dg/plugin/one_time_plugin.c (plugin_init): Likewise.
	* gcc.dg/plugin/selfassign.c (plugin_init): Likewise.

From-SVN: r201505
This commit is contained in:
David Malcolm 2013-08-05 20:01:43 +00:00 committed by David Malcolm
parent d0b2f8311e
commit f7695dbf40
16 changed files with 323 additions and 65 deletions

View File

@ -1,3 +1,75 @@
2013-08-05 David Malcolm <dmalcolm@redhat.com>
Handwritten part of conversion of passes to C++ classes.
* Makefile.in (PASS_MANAGER_H): Add dep on pass-instances.def.
(toplev.o): Add dep on PASS_MANAGER_H.
* cgraphunit.c (cgraph_process_new_functions): Rework invocation
of early local pases to reflect this moving from a global to a
member of gcc::pass_manager.
(cgraph_add_new_function): Likewise.
* lto-cgraph.c (lto_output_node): Update for conversion of
struct ipa_opt_pass_d to a C++ subclass of opt_pass.
* passes.c (opt_pass::clone): New.
(opt_pass::gate): New.
(opt_pass::execute): New.
(opt_pass::opt_pass): New.
(pass_manager::execute_early_local_passes): New.
(pass_manager::execute_pass_mode_switching): new.
(finish_optimization_passes): Convert to...
(pass_manager::finish_optimization_passes): ...this.
(finish_optimization_passes): Update for conversion of passes to
C++ classes.
(register_dump_files_1): Use has_gate since we cannot portably
check a vtable entry against NULL.
(dump_one_pass): Likewise.
(ipa_write_summaries_2): Likewise.
(ipa_write_optimization_summaries_1): Likewise.
(ipa_read_summaries_1): Likewise.
(ipa_read_optimization_summaries_1): Likewise.
(execute_ipa_stmt_fixups): Likewise.
(pass_manager::pass_manager): Rewrite pass-creation, invoking
pass-creation functions rather than wiring up globals, and
storing the results in fields of pass_manager generated using
pass-instances.def.
(pass_manager::dump_profile_report): Update for conversion of
passes to C++ classes.
(pass_manager::execute_ipa_summary_passes): Likewise.
(execute_one_ipa_transform_pass): Likewise.
(execute_one_pass): Use has_gate and has_execute since we cannot
portably check a vtable entry against NULL.
* pass_manager.h (pass_manager::finish_optimization_passes): New.
(pass_manager): Use pass-instances.def to add fields for the
various pass instances.
* toplev.c (finalize): Update for move of
finish_optimization_passes to a method of gcc::pass_manager.
* toplev.h (finish_optimization_passes): Move to method of class
pass_manager.
* tree-pass.h (struct pass_data): New.
(opt_pass): Convert to C++ class, make it a subclass of
pass_data.
(opt_pass::gate): Convert to virtual function.
(opt_pass::~opt_pass): New.
(opt_pass::clone): New.
(opt_pass::execute): Convert to virtual function.
(opt_pass::opt_pass): New.
(opt_pass::ctxt_): new.
(gimple_opt_pass): Convert to subclass of opt_pass.
(gimple_opt_pass::gimple_opt_pass): New.
(rtl_opt_pass): Convert to subclass of opt_pass.
(rtl_opt_pass::rtl_opt_pass): New.
(ipa_opt_pass_d): Convert to subclass of opt_pass.
(ipa_opt_pass_d::ipa_opt_pass_d): New.
(simple_ipa_opt_pass): Convert to subclass of opt_pass.
(simple_ipa_opt_pass::simple_ipa_opt_pass): New.
* config/i386/i386.c (rest_of_handle_insert_vzeroupper): Rework
invocation of pass_mode_switching to reflect this moving from a
global to a member of gcc::pass_manager.
(ix86_option_override): Rework how pass_insert_vzeroupper is
added to the pass_manager to reflect autogenerated changes.
* config/i386/t-i386 (i386.o) Add deps on CONTEXT_H and
PASS_MANAGER_H.
2013-08-05 Richard Earnshaw <rearnsha@arm.com>
PR rtl-optimization/57708

View File

@ -987,7 +987,7 @@ PLUGIN_VERSION_H = plugin-version.h configargs.h
LIBFUNCS_H = libfuncs.h $(HASHTAB_H)
GRAPHITE_HTAB_H = graphite-htab.h graphite-clast-to-gimple.h $(HASH_TABLE_H)
CONTEXT_H = context.h
PASS_MANAGER_H = pass_manager.h
PASS_MANAGER_H = pass_manager.h pass-instances.def
#
# Now figure out from those variables how to compile and link.
@ -2733,7 +2733,7 @@ toplev.o : toplev.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) \
$(OPTS_H) params.def tree-mudflap.h $(TREE_PASS_H) $(GIMPLE_H) \
tree-ssa-alias.h $(PLUGIN_H) realmpfr.h tree-diagnostic.h \
$(TREE_PRETTY_PRINT_H) opts-diagnostic.h $(COMMON_TARGET_H) \
tsan.h diagnostic-color.h $(CONTEXT_H)
tsan.h diagnostic-color.h $(CONTEXT_H) $(PASS_MANAGER_H)
hwint.o : hwint.c $(CONFIG_H) $(SYSTEM_H) $(DIAGNOSTIC_CORE_H)

View File

@ -325,7 +325,7 @@ cgraph_process_new_functions (void)
push_cfun (DECL_STRUCT_FUNCTION (fndecl));
if (cgraph_state == CGRAPH_STATE_IPA_SSA
&& !gimple_in_ssa_p (DECL_STRUCT_FUNCTION (fndecl)))
execute_pass_list (pass_early_local_passes.pass.sub);
g->get_passes ()->execute_early_local_passes ();
else if (inline_summary_vec != NULL)
compute_inline_parameters (node, true);
free_dominance_info (CDI_POST_DOMINATORS);
@ -509,7 +509,7 @@ cgraph_add_new_function (tree fndecl, bool lowered)
gimple_register_cfg_hooks ();
bitmap_obstack_initialize (NULL);
execute_pass_list (passes->all_lowering_passes);
execute_pass_list (pass_early_local_passes.pass.sub);
passes->execute_early_local_passes ();
bitmap_obstack_release (NULL);
pop_cfun ();
@ -534,7 +534,7 @@ cgraph_add_new_function (tree fndecl, bool lowered)
gimple_register_cfg_hooks ();
bitmap_obstack_initialize (NULL);
if (!gimple_in_ssa_p (DECL_STRUCT_FUNCTION (fndecl)))
execute_pass_list (pass_early_local_passes.pass.sub);
g->get_passes ()->execute_early_local_passes ();
bitmap_obstack_release (NULL);
pop_cfun ();
expand_function (node);

View File

@ -62,6 +62,8 @@ along with GCC; see the file COPYING3. If not see
#include "dumpfile.h"
#include "tree-pass.h"
#include "tree-flow.h"
#include "context.h"
#include "pass_manager.h"
static rtx legitimize_dllimport_symbol (rtx, bool);
static rtx legitimize_pe_coff_extern_decl (rtx, bool);
@ -2596,7 +2598,7 @@ rest_of_handle_insert_vzeroupper (void)
ix86_optimize_mode_switching[AVX_U128] = 1;
/* Call optimize_mode_switching. */
pass_mode_switching.pass.execute ();
g->get_passes ()->execute_pass_mode_switching ();
return 0;
}
@ -4028,8 +4030,9 @@ ix86_option_override_internal (bool main_args_p)
static void
ix86_option_override (void)
{
opt_pass *pass_insert_vzeroupper = make_pass_insert_vzeroupper (g);
static struct register_pass_info insert_vzeroupper_info
= { &pass_insert_vzeroupper.pass, "reload",
= { pass_insert_vzeroupper, "reload",
1, PASS_POS_INSERT_AFTER
};

View File

@ -24,7 +24,7 @@ i386.o: $(CONFIG_H) $(SYSTEM_H) coretypes.h dumpfile.h $(TM_H) \
$(GGC_H) $(TARGET_H) $(TARGET_DEF_H) langhooks.h $(CGRAPH_H) \
$(TREE_GIMPLE_H) $(DWARF2_H) $(DF_H) tm-constrs.h $(PARAMS_H) \
i386-builtin-types.inc debug.h dwarf2out.h sbitmap.h $(FIBHEAP_H) \
$(OPTS_H) $(DIAGNOSTIC_H) $(COMMON_TARGET_H)
$(OPTS_H) $(DIAGNOSTIC_H) $(COMMON_TARGET_H) $(CONTEXT_H) $(PIPELINE_H)
i386-c.o: $(srcdir)/config/i386/i386-c.c \
$(srcdir)/config/i386/i386-protos.h $(CONFIG_H) $(SYSTEM_H) coretypes.h \

View File

@ -438,7 +438,7 @@ lto_output_node (struct lto_simple_output_block *ob, struct cgraph_node *node,
streamer_write_hwi_stream (ob->main_stream,
node->ipa_transforms_to_apply.length ());
FOR_EACH_VEC_ELT (node->ipa_transforms_to_apply, i, pass)
streamer_write_hwi_stream (ob->main_stream, pass->pass.static_pass_number);
streamer_write_hwi_stream (ob->main_stream, pass->static_pass_number);
if (tag == LTO_symtab_analyzed_node)
{

View File

@ -58,6 +58,12 @@ public:
void dump_profile_report () const;
void finish_optimization_passes ();
/* Access to specific passes, so that the majority can be private. */
void execute_early_local_passes ();
unsigned int execute_pass_mode_switching ();
public:
/* The root of the compilation pass tree, once constructed. */
opt_pass *all_passes;
@ -81,6 +87,37 @@ private:
private:
context *ctxt_;
/* References to all of the individual passes.
These fields are generated via macro expansion.
For example:
NEXT_PASS (pass_build_cfg, 1);
within pass-instances.def means that there is a field:
opt_pass *pass_build_cfg_1;
Similarly, the various:
NEXT_PASS (pass_copy_prop, 1);
...
NEXT_PASS (pass_copy_prop, 8);
in pass-instances.def lead to fields:
opt_pass *pass_copy_prop_1;
...
opt_pass *pass_copy_prop_8; */
#define INSERT_PASSES_AFTER(PASS)
#define PUSH_INSERT_PASSES_WITHIN(PASS)
#define POP_INSERT_PASSES()
#define NEXT_PASS(PASS, NUM) opt_pass *PASS ## _ ## NUM
#define TERMINATE_PASS_LIST()
#include "pass-instances.def"
#undef INSERT_PASSES_AFTER
#undef PUSH_INSERT_PASSES_WITHIN
#undef POP_INSERT_PASSES
#undef NEXT_PASS
#undef TERMINATE_PASS_LIST
}; // class pass_manager
} // namespace gcc

View File

@ -82,6 +82,54 @@ struct opt_pass *current_pass;
static void register_pass_name (struct opt_pass *, const char *);
/* Most passes are single-instance (within their context) and thus don't
need to implement cloning, but passes that support multiple instances
*must* provide their own implementation of the clone method.
Handle this by providing a default implemenation, but make it a fatal
error to call it. */
opt_pass *
opt_pass::clone ()
{
internal_error ("pass %s does not support cloning", name);
}
bool
opt_pass::gate ()
{
return true;
}
unsigned int
opt_pass::execute ()
{
return 0;
}
opt_pass::opt_pass(const pass_data &data, context *ctxt)
: pass_data(data),
sub(NULL),
next(NULL),
static_pass_number(0),
ctxt_(ctxt)
{
}
void
pass_manager::execute_early_local_passes ()
{
execute_pass_list (pass_early_local_passes_1->sub);
}
unsigned int
pass_manager::execute_pass_mode_switching ()
{
return pass_mode_switching_1->execute ();
}
/* Call from anywhere to find out what pass this is. Useful for
printing out debugging information deep inside an service
routine. */
@ -224,6 +272,7 @@ rest_of_type_compilation (tree type, int toplev)
void
pass_manager::
finish_optimization_passes (void)
{
int i;
@ -233,16 +282,16 @@ finish_optimization_passes (void)
timevar_push (TV_DUMP);
if (profile_arc_flag || flag_test_coverage || flag_branch_probabilities)
{
dump_start (pass_profile.pass.static_pass_number, NULL);
dump_start (pass_profile_1->static_pass_number, NULL);
end_branch_prob ();
dump_finish (pass_profile.pass.static_pass_number);
dump_finish (pass_profile_1->static_pass_number);
}
if (optimize > 0)
{
dump_start (pass_profile.pass.static_pass_number, NULL);
dump_start (pass_profile_1->static_pass_number, NULL);
print_combine_total_stats ();
dump_finish (pass_profile.pass.static_pass_number);
dump_finish (pass_profile_1->static_pass_number);
}
/* Do whatever is necessary to finish printing the graphs. */
@ -550,7 +599,7 @@ register_dump_files_1 (struct opt_pass *pass, int properties)
/* If we have a gate, combine the properties that we could have with
and without the pass being examined. */
if (pass->gate)
if (pass->has_gate)
properties &= new_properties;
else
properties = new_properties;
@ -679,7 +728,7 @@ dump_one_pass (struct opt_pass *pass, int pass_indent)
const char *pn;
bool is_on, is_really_on;
is_on = (pass->gate == NULL) ? true : pass->gate();
is_on = pass->has_gate ? pass->gate() : true;
is_really_on = override_gate_status (pass, current_function_decl, is_on);
if (pass->static_pass_number <= 0)
@ -1310,12 +1359,23 @@ pass_manager::pass_manager (context *ctxt)
#define PUSH_INSERT_PASSES_WITHIN(PASS) \
{ \
struct opt_pass **p = &(PASS).pass.sub;
struct opt_pass **p = &(PASS ## _1)->sub;
#define POP_INSERT_PASSES() \
}
#define NEXT_PASS(PASS, NUM) (p = next_pass_1 (p, &((PASS).pass)))
#define NEXT_PASS(PASS, NUM) \
do { \
gcc_assert (NULL == PASS ## _ ## NUM); \
if ((NUM) == 1) \
PASS ## _1 = make_##PASS (ctxt_); \
else \
{ \
gcc_assert (PASS ## _1); \
PASS ## _ ## NUM = PASS ## _1->clone (); \
} \
p = next_pass_1 (p, PASS ## _ ## NUM); \
} while (0)
#define TERMINATE_PASS_LIST() \
*p = NULL;
@ -1541,7 +1601,7 @@ pass_manager::dump_profile_report () const
fprintf (stderr, " ");
/* Size/time units change across gimple and RTL. */
if (i == pass_expand.pass.static_pass_number)
if (i == pass_expand_1->static_pass_number)
fprintf (stderr, "|----------");
else
{
@ -1778,11 +1838,11 @@ execute_ipa_summary_passes (struct ipa_opt_pass_d *ipa_pass)
{
while (ipa_pass)
{
struct opt_pass *pass = &ipa_pass->pass;
struct opt_pass *pass = ipa_pass;
/* Execute all of the IPA_PASSes in the list. */
if (ipa_pass->pass.type == IPA_PASS
&& (!pass->gate || pass->gate ())
if (ipa_pass->type == IPA_PASS
&& ((!pass->has_gate) || pass->gate ())
&& ipa_pass->generate_summary)
{
pass_init_dump_file (pass);
@ -1799,7 +1859,7 @@ execute_ipa_summary_passes (struct ipa_opt_pass_d *ipa_pass)
pass_fini_dump_file (pass);
}
ipa_pass = (struct ipa_opt_pass_d *)ipa_pass->pass.next;
ipa_pass = (struct ipa_opt_pass_d *)ipa_pass->next;
}
}
@ -1809,7 +1869,7 @@ static void
execute_one_ipa_transform_pass (struct cgraph_node *node,
struct ipa_opt_pass_d *ipa_pass)
{
struct opt_pass *pass = &ipa_pass->pass;
struct opt_pass *pass = ipa_pass;
unsigned int todo_after = 0;
current_pass = pass;
@ -1933,7 +1993,7 @@ execute_one_pass (struct opt_pass *pass)
/* Check whether gate check should be avoided.
User controls the value of the gate through the parameter "gate_status". */
gate_status = (pass->gate == NULL) ? true : pass->gate();
gate_status = pass->has_gate ? pass->gate() : true;
gate_status = override_gate_status (pass, current_function_decl, gate_status);
/* Override gate with plugin. */
@ -1990,7 +2050,7 @@ execute_one_pass (struct opt_pass *pass)
timevar_push (pass->tv_id);
/* Do it! */
if (pass->execute)
if (pass->has_execute)
{
todo_after = pass->execute ();
do_per_function (clear_last_verified, NULL);
@ -2066,7 +2126,7 @@ ipa_write_summaries_2 (struct opt_pass *pass, struct lto_out_decl_state *state)
gcc_assert (pass->type == SIMPLE_IPA_PASS || pass->type == IPA_PASS);
if (pass->type == IPA_PASS
&& ipa_pass->write_summary
&& (!pass->gate || pass->gate ()))
&& ((!pass->has_gate) || pass->gate ()))
{
/* If a timevar is present, start it. */
if (pass->tv_id)
@ -2182,7 +2242,7 @@ ipa_write_optimization_summaries_1 (struct opt_pass *pass, struct lto_out_decl_s
gcc_assert (pass->type == SIMPLE_IPA_PASS || pass->type == IPA_PASS);
if (pass->type == IPA_PASS
&& ipa_pass->write_optimization_summary
&& (!pass->gate || pass->gate ()))
&& ((!pass->has_gate) || pass->gate ()))
{
/* If a timevar is present, start it. */
if (pass->tv_id)
@ -2259,7 +2319,7 @@ ipa_read_summaries_1 (struct opt_pass *pass)
gcc_assert (!cfun);
gcc_assert (pass->type == SIMPLE_IPA_PASS || pass->type == IPA_PASS);
if (pass->gate == NULL || pass->gate ())
if ((!pass->has_gate) || pass->gate ())
{
if (pass->type == IPA_PASS && ipa_pass->read_summary)
{
@ -2310,7 +2370,7 @@ ipa_read_optimization_summaries_1 (struct opt_pass *pass)
gcc_assert (!cfun);
gcc_assert (pass->type == SIMPLE_IPA_PASS || pass->type == IPA_PASS);
if (pass->gate == NULL || pass->gate ())
if ((!pass->has_gate) || pass->gate ())
{
if (pass->type == IPA_PASS && ipa_pass->read_optimization_summary)
{
@ -2388,7 +2448,7 @@ execute_ipa_stmt_fixups (struct opt_pass *pass,
{
/* Execute all of the IPA_PASSes in the list. */
if (pass->type == IPA_PASS
&& (!pass->gate || pass->gate ()))
&& ((!pass->has_gate) || pass->gate ()))
{
struct ipa_opt_pass_d *ipa_pass = (struct ipa_opt_pass_d *) pass;

View File

@ -1,3 +1,12 @@
2013-08-05 David Malcolm <dmalcolm@redhat.com>
* g++.dg/plugin/dumb_plugin.c (plugin_init): Rework how the pass
is created and added to the pass_manager to reflect
autogenerated changes.
* g++.dg/plugin/selfassign.c (plugin_init): Likewise.
* gcc.dg/plugin/one_time_plugin.c (plugin_init): Likewise.
* gcc.dg/plugin/selfassign.c (plugin_init): Likewise.
2013-08-04 Ed Smith-Rowland <3dw4rd@verizon.net>
PR c++/58072

View File

@ -11,6 +11,7 @@
#include "intl.h"
#include "toplev.h"
#include "diagnostic.h"
#include "context.h"
int plugin_is_GPL_compatible;
@ -124,7 +125,7 @@ plugin_init (struct plugin_name_args *plugin_info,
return 1;
}
pass_info.pass = &pass_dumb_plugin_example.pass;
pass_info.pass = make_pass_dumb_plugin_example (g);
pass_info.reference_pass_name = ref_pass_name;
pass_info.ref_pass_instance_number = ref_instance_number;
pass_info.pos_op = PASS_POS_INSERT_AFTER;

View File

@ -15,6 +15,7 @@
#include "intl.h"
#include "plugin-version.h"
#include "diagnostic.h"
#include "context.h"
int plugin_is_GPL_compatible;
@ -309,7 +310,7 @@ plugin_init (struct plugin_name_args *plugin_info,
return 1;
/* Self-assign detection should happen after SSA is constructed. */
pass_info.pass = &pass_warn_self_assign.pass;
pass_info.pass = make_pass_warn_self_assign (g);
pass_info.reference_pass_name = "ssa";
pass_info.ref_pass_instance_number = 1;
pass_info.pos_op = PASS_POS_INSERT_AFTER;

View File

@ -8,6 +8,7 @@
#include "gimple.h"
#include "tree-pass.h"
#include "intl.h"
#include "context.h"
int plugin_is_GPL_compatible;
@ -53,7 +54,7 @@ int plugin_init (struct plugin_name_args *plugin_info,
{
struct register_pass_info p;
p.pass = &one_pass.pass;
p.pass = make_one_pass (g);
p.reference_pass_name = "cfg";
p.ref_pass_instance_number = 1;
p.pos_op = PASS_POS_INSERT_AFTER;

View File

@ -15,6 +15,7 @@
#include "intl.h"
#include "plugin-version.h"
#include "diagnostic.h"
#include "context.h"
int plugin_is_GPL_compatible;
@ -309,7 +310,7 @@ plugin_init (struct plugin_name_args *plugin_info,
return 1;
/* Self-assign detection should happen after SSA is constructed. */
pass_info.pass = &pass_warn_self_assign.pass;
pass_info.pass = make_pass_warn_self_assign (g);
pass_info.reference_pass_name = "ssa";
pass_info.ref_pass_instance_number = 1;
pass_info.pos_op = PASS_POS_INSERT_AFTER;

View File

@ -76,6 +76,7 @@ along with GCC; see the file COPYING3. If not see
#include "plugin.h"
#include "diagnostic-color.h"
#include "context.h"
#include "pass_manager.h"
#if defined(DBX_DEBUGGING_INFO) || defined(XCOFF_DEBUGGING_INFO)
#include "dbxout.h"
@ -1818,7 +1819,7 @@ finalize (bool no_backend)
{
statistics_fini ();
finish_optimization_passes ();
g->get_passes ()->finish_optimization_passes ();
ira_finish_once ();
}

View File

@ -28,7 +28,6 @@ extern int toplev_main (int, char **);
extern void rest_of_decl_compilation (tree, int, int);
extern void rest_of_type_compilation (tree, int);
extern void init_optimization_passes (void);
extern void finish_optimization_passes (void);
extern bool enable_rtl_dump_file (void);
/* In except.c. Initialize exception handling. This is used by the Ada

View File

@ -34,9 +34,8 @@ enum opt_pass_type
IPA_PASS
};
/* Describe one pass; this is the common part shared across different pass
types. */
struct opt_pass
/* Metadata for a pass, non-varying across all instances of a pass. */
struct pass_data
{
/* Optimization pass type. */
enum opt_pass_type type;
@ -48,23 +47,13 @@ struct opt_pass
/* The -fopt-info optimization group flags as defined in dumpfile.h. */
unsigned int optinfo_flags;
/* If non-null, this pass and all sub-passes are executed only if
the function returns true. */
bool (*gate) (void);
/* If true, this pass has its own implementation of the opt_pass::gate
method. */
bool has_gate;
/* This is the code to run. If null, then there should be sub-passes
otherwise this pass does nothing. The return value contains
TODOs to execute in addition to those in TODO_flags_finish. */
unsigned int (*execute) (void);
/* A list of sub-passes to run, dependent on gate predicate. */
struct opt_pass *sub;
/* Next in the list of passes to run, independent of gate predicate. */
struct opt_pass *next;
/* Static pass number, used as a fragment of the dump file name. */
int static_pass_number;
/* If true, this pass has its own implementation of the opt_pass::execute
method. */
bool has_execute;
/* The timevar id associated with this pass. */
/* ??? Ideally would be dynamically assigned. */
@ -80,16 +69,72 @@ struct opt_pass
unsigned int todo_flags_finish;
};
/* Description of GIMPLE pass. */
struct gimple_opt_pass
namespace gcc
{
struct opt_pass pass;
class context;
} // namespace gcc
/* An instance of a pass. This is also "pass_data" to minimize the
changes in existing code. */
class opt_pass : public pass_data
{
public:
virtual ~opt_pass () { }
/* Create a copy of this pass.
Passes that can have multiple instances must provide their own
implementation of this, to ensure that any sharing of state between
this instance and the copy is "wired up" correctly.
The default implementation prints an error message and aborts. */
virtual opt_pass *clone ();
/* If has_gate is set, this pass and all sub-passes are executed only if
the function returns true. */
virtual bool gate ();
/* This is the code to run. If has_execute is false, then there should
be sub-passes otherwise this pass does nothing.
The return value contains TODOs to execute in addition to those in
TODO_flags_finish. */
virtual unsigned int execute ();
protected:
opt_pass(const pass_data&, gcc::context *);
public:
/* A list of sub-passes to run, dependent on gate predicate. */
struct opt_pass *sub;
/* Next in the list of passes to run, independent of gate predicate. */
struct opt_pass *next;
/* Static pass number, used as a fragment of the dump file name. */
int static_pass_number;
protected:
gcc::context *ctxt_;
};
/* Description of GIMPLE pass. */
class gimple_opt_pass : public opt_pass
{
protected:
gimple_opt_pass(const pass_data& data, gcc::context *ctxt)
: opt_pass(data, ctxt)
{
}
};
/* Description of RTL pass. */
struct rtl_opt_pass
class rtl_opt_pass : public opt_pass
{
struct opt_pass pass;
protected:
rtl_opt_pass(const pass_data& data, gcc::context *ctxt)
: opt_pass(data, ctxt)
{
}
};
struct varpool_node;
@ -98,10 +143,9 @@ struct lto_symtab_encoder_d;
/* Description of IPA pass with generate summary, write, execute, read and
transform stages. */
struct ipa_opt_pass_d
class ipa_opt_pass_d : public opt_pass
{
struct opt_pass pass;
public:
/* IPA passes can analyze function body and variable initializers
using this hook and produce summary. */
void (*generate_summary) (void);
@ -127,13 +171,42 @@ struct ipa_opt_pass_d
unsigned int function_transform_todo_flags_start;
unsigned int (*function_transform) (struct cgraph_node *);
void (*variable_transform) (struct varpool_node *);
protected:
ipa_opt_pass_d(const pass_data& data, gcc::context *ctxt,
void (*generate_summary) (void),
void (*write_summary) (void),
void (*read_summary) (void),
void (*write_optimization_summary) (void),
void (*read_optimization_summary) (void),
void (*stmt_fixup) (struct cgraph_node *, gimple *),
unsigned int function_transform_todo_flags_start,
unsigned int (*function_transform) (struct cgraph_node *),
void (*variable_transform) (struct varpool_node *))
: opt_pass(data, ctxt),
generate_summary(generate_summary),
write_summary(write_summary),
read_summary(read_summary),
write_optimization_summary(write_optimization_summary),
read_optimization_summary(read_optimization_summary),
stmt_fixup(stmt_fixup),
function_transform_todo_flags_start(
function_transform_todo_flags_start),
function_transform(function_transform),
variable_transform(variable_transform)
{
}
};
/* Description of simple IPA pass. Simple IPA passes have just one execute
hook. */
struct simple_ipa_opt_pass
class simple_ipa_opt_pass : public opt_pass
{
struct opt_pass pass;
protected:
simple_ipa_opt_pass(const pass_data& data, gcc::context *ctxt)
: opt_pass(data, ctxt)
{
}
};
/* Pass properties. */