/* Top-level control of tree optimizations.
- Copyright 2001, 2002, 2003, 2004, 2005, 2007, 2008, 2009
+ Copyright 2001, 2002, 2003, 2004, 2005, 2007, 2008, 2009, 2010
Free Software Foundation, Inc.
Contributed by Diego Novillo <dnovillo@redhat.com>
#include "tm_p.h"
#include "basic-block.h"
#include "output.h"
-#include "diagnostic.h"
-#include "basic-block.h"
#include "flags.h"
#include "tree-flow.h"
#include "tree-dump.h"
#include "timevar.h"
#include "function.h"
#include "langhooks.h"
+#include "diagnostic-core.h"
#include "toplev.h"
#include "flags.h"
#include "cgraph.h"
return (optimize >= 1
/* Don't bother doing anything if the program has errors.
We have to pass down the queue if we already went into SSA */
- && (!(errorcount || sorrycount) || gimple_in_ssa_p (cfun)));
+ && (!seen_error () || gimple_in_ssa_p (cfun)));
}
struct gimple_opt_pass pass_all_optimizations =
gate_all_early_local_passes (void)
{
/* Don't bother doing anything if the program has errors. */
- return (!errorcount && !sorrycount && !in_lto_p);
+ return (!seen_error () && !in_lto_p);
+}
+
+static unsigned int
+execute_all_early_local_passes (void)
+{
+ /* Once this pass (and its sub-passes) are complete, all functions
+ will be in SSA form. Technically this state change is happening
+ a tad early, since the sub-passes have not yet run, but since
+ none of the sub-passes are IPA passes and do not create new
+ functions, this is ok. We're setting this value for the benefit
+ of IPA passes that follow. */
+ if (cgraph_state < CGRAPH_STATE_IPA_SSA)
+ cgraph_state = CGRAPH_STATE_IPA_SSA;
+ return 0;
}
struct simple_ipa_opt_pass pass_early_local_passes =
SIMPLE_IPA_PASS,
"early_local_cleanups", /* name */
gate_all_early_local_passes, /* gate */
- NULL, /* execute */
+ execute_all_early_local_passes, /* execute */
NULL, /* sub */
NULL, /* next */
0, /* static_pass_number */
}
};
-static unsigned int
-execute_early_local_optimizations (void)
-{
- /* First time we start with early optimization we need to advance
- cgraph state so newly inserted functions are also early optimized.
- However we execute early local optimizations for lately inserted
- functions, in that case don't reset cgraph state back to IPA_SSA. */
- if (cgraph_state < CGRAPH_STATE_IPA_SSA)
- cgraph_state = CGRAPH_STATE_IPA_SSA;
- return 0;
-}
-
/* Gate: execute, or not, all of the non-trivial optimizations. */
static bool
{
return (optimize >= 1
/* Don't bother doing anything if the program has errors. */
- && !(errorcount || sorrycount));
+ && !seen_error ());
}
struct gimple_opt_pass pass_all_early_optimizations =
GIMPLE_PASS,
"early_optimizations", /* name */
gate_all_early_optimizations, /* gate */
- execute_early_local_optimizations, /* execute */
+ NULL, /* execute */
NULL, /* sub */
NULL, /* next */
0, /* static_pass_number */
cleanup_tree_cfg ();
cleanup_dead_labels ();
group_case_labels ();
+ if ((flag_compare_debug_opt || flag_compare_debug)
+ && flag_dump_final_insns)
+ {
+ FILE *final_output = fopen (flag_dump_final_insns, "a");
+
+ if (!final_output)
+ {
+ error ("could not open final insn dump file %qs: %m",
+ flag_dump_final_insns);
+ flag_dump_final_insns = NULL;
+ }
+ else
+ {
+ int save_unnumbered = flag_dump_unnumbered;
+ int save_noaddr = flag_dump_noaddr;
+
+ flag_dump_noaddr = flag_dump_unnumbered = 1;
+ fprintf (final_output, "\n");
+ dump_enumerated_decls (final_output, dump_flags | TDF_NOUID);
+ flag_dump_noaddr = save_noaddr;
+ flag_dump_unnumbered = save_unnumbered;
+ if (fclose (final_output))
+ {
+ error ("could not close final insn dump file %qs: %m",
+ flag_dump_final_insns);
+ flag_dump_final_insns = NULL;
+ }
+ }
+ }
return 0;
}
}
/* Pass: fixup_cfg. IPA passes, compilation of earlier functions or inlining
- might have changed some properties, such as marked functions nothrow.
+ might have changed some properties, such as marked functions nothrow,
+ pure, const or noreturn.
Remove redundant edges and basic blocks, and create new ones if necessary.
This pass can't be executed as stand alone pass from pass manager, because
tree decl = is_gimple_call (stmt)
? gimple_call_fndecl (stmt)
: NULL;
-
- if (decl
- && gimple_call_flags (stmt) & (ECF_CONST
- | ECF_PURE
- | ECF_LOOPING_CONST_OR_PURE))
+ if (decl)
{
- if (gimple_in_ssa_p (cfun))
+ int flags = gimple_call_flags (stmt);
+ if (flags & (ECF_CONST | ECF_PURE | ECF_LOOPING_CONST_OR_PURE))
{
- todo |= TODO_update_ssa | TODO_cleanup_cfg;
- mark_symbols_for_renaming (stmt);
- update_stmt (stmt);
+ if (gimple_in_ssa_p (cfun))
+ {
+ todo |= TODO_update_ssa | TODO_cleanup_cfg;
+ mark_symbols_for_renaming (stmt);
+ update_stmt (stmt);
+ }
}
- }
+
+ if (flags & ECF_NORETURN
+ && fixup_noreturn_call (stmt))
+ todo |= TODO_cleanup_cfg;
+ }
maybe_clean_eh_stmt (stmt);
}
if (count_scale != REG_BR_PROB_BASE)
compute_function_frequency ();
+ /* We just processed all calls. */
+ if (cfun->gimple_df)
+ {
+ VEC_free (gimple, gc, MODIFIED_NORETURN_CALLS (cfun));
+ MODIFIED_NORETURN_CALLS (cfun) = NULL;
+ }
+
/* Dump a textual representation of the flowgraph. */
if (dump_file)
gimple_dump_cfg (dump_file, dump_flags);