more autogen definiton
[official-gcc.git] / gcc / tree-optimize.c
blob3d18d20a003c36568fda6ad8df88db8cf45aa4fe
1 /* Top-level control of tree optimizations.
2 Copyright 2001, 2002, 2003, 2004, 2005, 2007, 2008, 2009, 2010
3 Free Software Foundation, Inc.
4 Contributed by Diego Novillo <dnovillo@redhat.com>
6 This file is part of GCC.
8 GCC is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3, or (at your option)
11 any later version.
13 GCC is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING3. If not see
20 <http://www.gnu.org/licenses/>. */
22 #include "config.h"
23 #include "system.h"
24 #include "coretypes.h"
25 #include "tm.h"
26 #include "tree.h"
27 #include "tm_p.h"
28 #include "basic-block.h"
29 #include "output.h"
30 #include "flags.h"
31 #include "tree-flow.h"
32 #include "tree-dump.h"
33 #include "timevar.h"
34 #include "function.h"
35 #include "langhooks.h"
36 #include "diagnostic-core.h"
37 #include "toplev.h"
38 #include "flags.h"
39 #include "cgraph.h"
40 #include "tree-inline.h"
41 #include "tree-pass.h"
42 #include "ggc.h"
43 #include "cgraph.h"
44 #include "graph.h"
45 #include "cfgloop.h"
46 #include "except.h"
47 #include "plugin.h"
48 #include "regset.h" /* FIXME: For reg_obstack. */
50 /* Gate: execute, or not, all of the non-trivial optimizations. */
52 static bool
53 gate_all_optimizations (void)
55 return (optimize >= 1
56 /* Don't bother doing anything if the program has errors.
57 We have to pass down the queue if we already went into SSA */
58 && (!seen_error () || gimple_in_ssa_p (cfun)));
61 struct gimple_opt_pass pass_all_optimizations =
64 GIMPLE_PASS,
65 "*all_optimizations", /* name */
66 gate_all_optimizations, /* gate */
67 NULL, /* execute */
68 NULL, /* sub */
69 NULL, /* next */
70 0, /* static_pass_number */
71 TV_OPTIMIZE, /* tv_id */
72 0, /* properties_required */
73 0, /* properties_provided */
74 0, /* properties_destroyed */
75 0, /* todo_flags_start */
76 0 /* todo_flags_finish */
80 /* Gate: execute, or not, all of the non-trivial optimizations. */
82 static bool
83 gate_all_early_local_passes (void)
85 /* Don't bother doing anything if the program has errors. */
86 return (!seen_error () && !in_lto_p);
89 static unsigned int
90 execute_all_early_local_passes (void)
92 /* Once this pass (and its sub-passes) are complete, all functions
93 will be in SSA form. Technically this state change is happening
94 a tad early, since the sub-passes have not yet run, but since
95 none of the sub-passes are IPA passes and do not create new
96 functions, this is ok. We're setting this value for the benefit
97 of IPA passes that follow. */
98 if (cgraph_state < CGRAPH_STATE_IPA_SSA)
99 cgraph_state = CGRAPH_STATE_IPA_SSA;
100 return 0;
103 struct simple_ipa_opt_pass pass_early_local_passes =
106 SIMPLE_IPA_PASS,
107 "early_local_cleanups", /* name */
108 gate_all_early_local_passes, /* gate */
109 execute_all_early_local_passes, /* execute */
110 NULL, /* sub */
111 NULL, /* next */
112 0, /* static_pass_number */
113 TV_EARLY_LOCAL, /* tv_id */
114 0, /* properties_required */
115 0, /* properties_provided */
116 0, /* properties_destroyed */
117 0, /* todo_flags_start */
118 TODO_remove_functions /* todo_flags_finish */
122 /* Gate: execute, or not, all of the non-trivial optimizations. */
124 static bool
125 gate_all_early_optimizations (void)
127 return (optimize >= 1
128 /* Don't bother doing anything if the program has errors. */
129 && !seen_error ());
132 struct gimple_opt_pass pass_all_early_optimizations =
135 GIMPLE_PASS,
136 "early_optimizations", /* name */
137 gate_all_early_optimizations, /* gate */
138 NULL, /* execute */
139 NULL, /* sub */
140 NULL, /* next */
141 0, /* static_pass_number */
142 TV_NONE, /* tv_id */
143 0, /* properties_required */
144 0, /* properties_provided */
145 0, /* properties_destroyed */
146 0, /* todo_flags_start */
147 0 /* todo_flags_finish */
152 /* Pass: cleanup the CFG just before expanding trees to RTL.
153 This is just a round of label cleanups and case node grouping
154 because after the tree optimizers have run such cleanups may
155 be necessary. */
157 static unsigned int
158 execute_cleanup_cfg_post_optimizing (void)
160 unsigned int todo = 0;
161 if (cleanup_tree_cfg ())
162 todo |= TODO_update_ssa;
163 maybe_remove_unreachable_handlers ();
164 cleanup_dead_labels ();
165 group_case_labels ();
166 if ((flag_compare_debug_opt || flag_compare_debug)
167 && flag_dump_final_insns)
169 FILE *final_output = fopen (flag_dump_final_insns, "a");
171 if (!final_output)
173 error ("could not open final insn dump file %qs: %m",
174 flag_dump_final_insns);
175 flag_dump_final_insns = NULL;
177 else
179 int save_unnumbered = flag_dump_unnumbered;
180 int save_noaddr = flag_dump_noaddr;
182 flag_dump_noaddr = flag_dump_unnumbered = 1;
183 fprintf (final_output, "\n");
184 dump_enumerated_decls (final_output, dump_flags | TDF_NOUID);
185 flag_dump_noaddr = save_noaddr;
186 flag_dump_unnumbered = save_unnumbered;
187 if (fclose (final_output))
189 error ("could not close final insn dump file %qs: %m",
190 flag_dump_final_insns);
191 flag_dump_final_insns = NULL;
195 return todo;
198 struct gimple_opt_pass pass_cleanup_cfg_post_optimizing =
201 GIMPLE_PASS,
202 "optimized", /* name */
203 NULL, /* gate */
204 execute_cleanup_cfg_post_optimizing, /* execute */
205 NULL, /* sub */
206 NULL, /* next */
207 0, /* static_pass_number */
208 TV_TREE_CLEANUP_CFG, /* tv_id */
209 PROP_cfg, /* properties_required */
210 0, /* properties_provided */
211 0, /* properties_destroyed */
212 0, /* todo_flags_start */
213 TODO_remove_unused_locals /* todo_flags_finish */
217 /* Pass: do the actions required to finish with tree-ssa optimization
218 passes. */
220 unsigned int
221 execute_free_datastructures (void)
223 free_dominance_info (CDI_DOMINATORS);
224 free_dominance_info (CDI_POST_DOMINATORS);
226 /* And get rid of annotations we no longer need. */
227 delete_tree_cfg_annotations ();
229 return 0;
232 /* IPA passes, compilation of earlier functions or inlining
233 might have changed some properties, such as marked functions nothrow,
234 pure, const or noreturn.
235 Remove redundant edges and basic blocks, and create new ones if necessary.
237 This pass can't be executed as stand alone pass from pass manager, because
238 in between inlining and this fixup the verify_flow_info would fail. */
240 unsigned int
241 execute_fixup_cfg (void)
243 basic_block bb;
244 gimple_stmt_iterator gsi;
245 int todo = gimple_in_ssa_p (cfun) ? TODO_verify_ssa : 0;
246 gcov_type count_scale;
247 edge e;
248 edge_iterator ei;
250 if (ENTRY_BLOCK_PTR->count)
251 count_scale = ((cgraph_get_node (current_function_decl)->count
252 * REG_BR_PROB_BASE + ENTRY_BLOCK_PTR->count / 2)
253 / ENTRY_BLOCK_PTR->count);
254 else
255 count_scale = REG_BR_PROB_BASE;
257 ENTRY_BLOCK_PTR->count = cgraph_get_node (current_function_decl)->count;
258 EXIT_BLOCK_PTR->count = (EXIT_BLOCK_PTR->count * count_scale
259 + REG_BR_PROB_BASE / 2) / REG_BR_PROB_BASE;
261 FOR_EACH_EDGE (e, ei, ENTRY_BLOCK_PTR->succs)
262 e->count = (e->count * count_scale
263 + REG_BR_PROB_BASE / 2) / REG_BR_PROB_BASE;
265 FOR_EACH_BB (bb)
267 bb->count = (bb->count * count_scale
268 + REG_BR_PROB_BASE / 2) / REG_BR_PROB_BASE;
269 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
271 gimple stmt = gsi_stmt (gsi);
272 tree decl = is_gimple_call (stmt)
273 ? gimple_call_fndecl (stmt)
274 : NULL;
275 if (decl)
277 int flags = gimple_call_flags (stmt);
278 if (flags & (ECF_CONST | ECF_PURE | ECF_LOOPING_CONST_OR_PURE))
280 if (gimple_purge_dead_abnormal_call_edges (bb))
281 todo |= TODO_cleanup_cfg;
283 if (gimple_in_ssa_p (cfun))
285 todo |= TODO_update_ssa | TODO_cleanup_cfg;
286 update_stmt (stmt);
290 if (flags & ECF_NORETURN
291 && fixup_noreturn_call (stmt))
292 todo |= TODO_cleanup_cfg;
295 if (maybe_clean_eh_stmt (stmt)
296 && gimple_purge_dead_eh_edges (bb))
297 todo |= TODO_cleanup_cfg;
300 FOR_EACH_EDGE (e, ei, bb->succs)
301 e->count = (e->count * count_scale
302 + REG_BR_PROB_BASE / 2) / REG_BR_PROB_BASE;
304 if (count_scale != REG_BR_PROB_BASE)
305 compute_function_frequency ();
307 /* We just processed all calls. */
308 if (cfun->gimple_df)
310 VEC_free (gimple, gc, MODIFIED_NORETURN_CALLS (cfun));
311 MODIFIED_NORETURN_CALLS (cfun) = NULL;
314 /* Dump a textual representation of the flowgraph. */
315 if (dump_file)
316 gimple_dump_cfg (dump_file, dump_flags);
318 return todo;
321 struct gimple_opt_pass pass_fixup_cfg =
324 GIMPLE_PASS,
325 "*free_cfg_annotations", /* name */
326 NULL, /* gate */
327 execute_fixup_cfg, /* execute */
328 NULL, /* sub */
329 NULL, /* next */
330 0, /* static_pass_number */
331 TV_NONE, /* tv_id */
332 PROP_cfg, /* properties_required */
333 0, /* properties_provided */
334 0, /* properties_destroyed */
335 0, /* todo_flags_start */
336 0 /* todo_flags_finish */
340 /* Do the actions required to initialize internal data structures used
341 in tree-ssa optimization passes. */
343 static unsigned int
344 execute_init_datastructures (void)
346 /* Allocate hash tables, arrays and other structures. */
347 init_tree_ssa (cfun);
348 return 0;
351 struct gimple_opt_pass pass_init_datastructures =
354 GIMPLE_PASS,
355 "*init_datastructures", /* name */
356 NULL, /* gate */
357 execute_init_datastructures, /* execute */
358 NULL, /* sub */
359 NULL, /* next */
360 0, /* static_pass_number */
361 TV_NONE, /* tv_id */
362 PROP_cfg, /* properties_required */
363 0, /* properties_provided */
364 0, /* properties_destroyed */
365 0, /* todo_flags_start */
366 0 /* todo_flags_finish */
370 void
371 tree_lowering_passes (tree fn)
373 tree saved_current_function_decl = current_function_decl;
375 current_function_decl = fn;
376 push_cfun (DECL_STRUCT_FUNCTION (fn));
377 gimple_register_cfg_hooks ();
378 bitmap_obstack_initialize (NULL);
379 execute_pass_list (all_lowering_passes);
380 if (optimize && cgraph_global_info_ready)
381 execute_pass_list (pass_early_local_passes.pass.sub);
382 free_dominance_info (CDI_POST_DOMINATORS);
383 free_dominance_info (CDI_DOMINATORS);
384 compact_blocks ();
385 current_function_decl = saved_current_function_decl;
386 bitmap_obstack_release (NULL);
387 pop_cfun ();
390 /* For functions-as-trees languages, this performs all optimization and
391 compilation for FNDECL. */
393 void
394 tree_rest_of_compilation (tree fndecl)
396 location_t saved_loc;
398 timevar_push (TV_REST_OF_COMPILATION);
400 gcc_assert (cgraph_global_info_ready);
402 /* Initialize the default bitmap obstack. */
403 bitmap_obstack_initialize (NULL);
405 /* Initialize the RTL code for the function. */
406 current_function_decl = fndecl;
407 saved_loc = input_location;
408 input_location = DECL_SOURCE_LOCATION (fndecl);
409 init_function_start (fndecl);
411 gimple_register_cfg_hooks ();
413 bitmap_obstack_initialize (&reg_obstack); /* FIXME, only at RTL generation*/
415 execute_all_ipa_transforms ();
417 /* Perform all tree transforms and optimizations. */
419 /* Signal the start of passes. */
420 invoke_plugin_callbacks (PLUGIN_ALL_PASSES_START, NULL);
422 execute_pass_list (all_passes);
424 /* Signal the end of passes. */
425 invoke_plugin_callbacks (PLUGIN_ALL_PASSES_END, NULL);
427 bitmap_obstack_release (&reg_obstack);
429 /* Release the default bitmap obstack. */
430 bitmap_obstack_release (NULL);
432 set_cfun (NULL);
434 /* If requested, warn about function definitions where the function will
435 return a value (usually of some struct or union type) which itself will
436 take up a lot of stack space. */
437 if (warn_larger_than && !DECL_EXTERNAL (fndecl) && TREE_TYPE (fndecl))
439 tree ret_type = TREE_TYPE (TREE_TYPE (fndecl));
441 if (ret_type && TYPE_SIZE_UNIT (ret_type)
442 && TREE_CODE (TYPE_SIZE_UNIT (ret_type)) == INTEGER_CST
443 && 0 < compare_tree_int (TYPE_SIZE_UNIT (ret_type),
444 larger_than_size))
446 unsigned int size_as_int
447 = TREE_INT_CST_LOW (TYPE_SIZE_UNIT (ret_type));
449 if (compare_tree_int (TYPE_SIZE_UNIT (ret_type), size_as_int) == 0)
450 warning (OPT_Wlarger_than_, "size of return value of %q+D is %u bytes",
451 fndecl, size_as_int);
452 else
453 warning (OPT_Wlarger_than_, "size of return value of %q+D is larger than %wd bytes",
454 fndecl, larger_than_size);
458 gimple_set_body (fndecl, NULL);
459 if (DECL_STRUCT_FUNCTION (fndecl) == 0
460 && !cgraph_get_node (fndecl)->origin)
462 /* Stop pointing to the local nodes about to be freed.
463 But DECL_INITIAL must remain nonzero so we know this
464 was an actual function definition.
465 For a nested function, this is done in c_pop_function_context.
466 If rest_of_compilation set this to 0, leave it 0. */
467 if (DECL_INITIAL (fndecl) != 0)
468 DECL_INITIAL (fndecl) = error_mark_node;
471 input_location = saved_loc;
473 ggc_collect ();
474 timevar_pop (TV_REST_OF_COMPILATION);