]> gcc.gnu.org Git - gcc.git/blame - gcc/passes.c
re PR tree-optimization/15310 ([tree-ssa] Optimize an addition in a bit field)
[gcc.git] / gcc / passes.c
CommitLineData
f6db1481
RH
1/* Top level of GCC compilers (cc1, cc1plus, etc.)
2 Copyright (C) 1987, 1988, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
3 1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
4
5This file is part of GCC.
6
7GCC is free software; you can redistribute it and/or modify it under
8the terms of the GNU General Public License as published by the Free
9Software Foundation; either version 2, or (at your option) any later
10version.
11
12GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13WARRANTY; without even the implied warranty of MERCHANTABILITY or
14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15for more details.
16
17You should have received a copy of the GNU General Public License
18along with GCC; see the file COPYING. If not, write to the Free
19Software Foundation, 59 Temple Place - Suite 330, Boston, MA
2002111-1307, USA. */
21
22/* This is the top level of cc1/c++.
23 It parses command args, opens files, invokes the various passes
24 in the proper order, and counts the time used by each.
25 Error messages and low-level interface to malloc also handled here. */
26
27#include "config.h"
28#undef FLOAT /* This is for hpux. They should change hpux. */
29#undef FFS /* Some systems define this in param.h. */
30#include "system.h"
31#include "coretypes.h"
32#include "tm.h"
33#include <signal.h>
34
35#ifdef HAVE_SYS_RESOURCE_H
36# include <sys/resource.h>
37#endif
38
39#ifdef HAVE_SYS_TIMES_H
40# include <sys/times.h>
41#endif
42
43#include "line-map.h"
44#include "input.h"
45#include "tree.h"
46#include "rtl.h"
47#include "tm_p.h"
48#include "flags.h"
49#include "insn-attr.h"
50#include "insn-config.h"
51#include "insn-flags.h"
52#include "hard-reg-set.h"
53#include "recog.h"
54#include "output.h"
55#include "except.h"
56#include "function.h"
57#include "toplev.h"
58#include "expr.h"
59#include "basic-block.h"
60#include "intl.h"
61#include "ggc.h"
62#include "graph.h"
63#include "loop.h"
64#include "regs.h"
65#include "timevar.h"
66#include "diagnostic.h"
67#include "params.h"
68#include "reload.h"
69#include "dwarf2asm.h"
70#include "integrate.h"
71#include "real.h"
72#include "debug.h"
73#include "target.h"
74#include "langhooks.h"
75#include "cfglayout.h"
76#include "cfgloop.h"
77#include "hosthooks.h"
78#include "cgraph.h"
79#include "opts.h"
80#include "coverage.h"
81#include "value-prof.h"
82#include "alloc-pool.h"
2f8e398b 83#include "tree-pass.h"
f6db1481
RH
84
85#if defined (DWARF2_UNWIND_INFO) || defined (DWARF2_DEBUGGING_INFO)
86#include "dwarf2out.h"
87#endif
88
89#if defined(DBX_DEBUGGING_INFO) || defined(XCOFF_DEBUGGING_INFO)
90#include "dbxout.h"
91#endif
92
93#ifdef SDB_DEBUGGING_INFO
94#include "sdbout.h"
95#endif
96
97#ifdef XCOFF_DEBUGGING_INFO
98#include "xcoffout.h" /* Needed for external data
99 declarations for e.g. AIX 4.x. */
100#endif
101
102#ifndef HAVE_conditional_execution
103#define HAVE_conditional_execution 0
104#endif
105
106/* Format to use to print dumpfile index value */
107#ifndef DUMPFILE_FORMAT
108#define DUMPFILE_FORMAT ".%02d."
109#endif
110
111/* Describes a dump file. */
112
113struct dump_file_info
114{
115 /* The unique extension to apply, e.g. ".jump". */
116 const char *const extension;
117
118 /* The -d<c> character that enables this dump file. */
119 char const debug_switch;
120
121 /* True if there is a corresponding graph dump file. */
122 char const graph_dump_p;
123
124 /* True if the user selected this dump. */
125 char enabled;
126
127 /* True if the files have been initialized (ie truncated). */
128 char initialized;
129};
130
131/* Enumerate the extant dump files. */
132
133enum dump_file_index
134{
135 DFI_cgraph,
136 DFI_rtl,
137 DFI_sibling,
138 DFI_eh,
139 DFI_jump,
140 DFI_null,
141 DFI_cse,
142 DFI_addressof,
143 DFI_gcse,
144 DFI_loop,
145 DFI_bypass,
146 DFI_cfg,
147 DFI_bp,
148 DFI_vpt,
149 DFI_ce1,
150 DFI_tracer,
151 DFI_loop2,
152 DFI_web,
153 DFI_cse2,
154 DFI_life,
155 DFI_combine,
156 DFI_ce2,
157 DFI_regmove,
e5626198 158 DFI_sms,
f6db1481
RH
159 DFI_sched,
160 DFI_lreg,
161 DFI_greg,
162 DFI_postreload,
f9957958 163 DFI_gcse2,
f6db1481
RH
164 DFI_flow2,
165 DFI_peephole2,
166 DFI_ce3,
167 DFI_rnreg,
168 DFI_bbro,
169 DFI_branch_target_load,
170 DFI_sched2,
171 DFI_stack,
172 DFI_vartrack,
173 DFI_mach,
174 DFI_dbr,
175 DFI_MAX
176};
177
178/* Describes all the dump files. Should be kept in order of the
179 pass and in sync with dump_file_index above.
180
181 Remaining -d letters:
182
e5626198 183 " e q "
f9957958 184 " K O Q WXY "
f6db1481
RH
185*/
186
187static struct dump_file_info dump_file_tbl[DFI_MAX] =
188{
189 { "cgraph", 'U', 0, 0, 0 },
190 { "rtl", 'r', 0, 0, 0 },
191 { "sibling", 'i', 0, 0, 0 },
192 { "eh", 'h', 0, 0, 0 },
193 { "jump", 'j', 0, 0, 0 },
194 { "null", 'u', 0, 0, 0 },
195 { "cse", 's', 0, 0, 0 },
196 { "addressof", 'F', 0, 0, 0 },
197 { "gcse", 'G', 1, 0, 0 },
198 { "loop", 'L', 1, 0, 0 },
199 { "bypass", 'G', 1, 0, 0 }, /* Yes, duplicate enable switch. */
200 { "cfg", 'f', 1, 0, 0 },
201 { "bp", 'b', 1, 0, 0 },
202 { "vpt", 'V', 1, 0, 0 },
203 { "ce1", 'C', 1, 0, 0 },
204 { "tracer", 'T', 1, 0, 0 },
205 { "loop2", 'L', 1, 0, 0 },
206 { "web", 'Z', 0, 0, 0 },
207 { "cse2", 't', 1, 0, 0 },
208 { "life", 'f', 1, 0, 0 }, /* Yes, duplicate enable switch. */
209 { "combine", 'c', 1, 0, 0 },
210 { "ce2", 'C', 1, 0, 0 },
211 { "regmove", 'N', 1, 0, 0 },
e5626198 212 { "sms", 'm', 0, 0, 0 },
f6db1481
RH
213 { "sched", 'S', 1, 0, 0 },
214 { "lreg", 'l', 1, 0, 0 },
215 { "greg", 'g', 1, 0, 0 },
216 { "postreload", 'o', 1, 0, 0 },
f9957958 217 { "gcse2", 'J', 0, 0, 0 },
f6db1481
RH
218 { "flow2", 'w', 1, 0, 0 },
219 { "peephole2", 'z', 1, 0, 0 },
220 { "ce3", 'E', 1, 0, 0 },
221 { "rnreg", 'n', 1, 0, 0 },
222 { "bbro", 'B', 1, 0, 0 },
223 { "btl", 'd', 1, 0, 0 }, /* Yes, duplicate enable switch. */
224 { "sched2", 'R', 1, 0, 0 },
225 { "stack", 'k', 1, 0, 0 },
226 { "vartrack", 'V', 1, 0, 0 }, /* Yes, duplicate enable switch. */
227 { "mach", 'M', 1, 0, 0 },
228 { "dbr", 'd', 0, 0, 0 },
229};
230
231/* Routine to open a dump file. Return true if the dump file is enabled. */
232
233static int
234open_dump_file (enum dump_file_index index, tree decl)
235{
236 char *dump_name;
237 const char *open_arg;
238 char seq[16];
239
240 if (! dump_file_tbl[index].enabled)
241 return 0;
242
243 timevar_push (TV_DUMP);
244 if (dump_file != NULL)
245 fclose (dump_file);
246
247 sprintf (seq, DUMPFILE_FORMAT, index);
248
249 if (! dump_file_tbl[index].initialized)
250 {
251 /* If we've not initialized the files, do so now. */
252 if (graph_dump_format != no_graph
253 && dump_file_tbl[index].graph_dump_p)
254 {
255 dump_name = concat (seq, dump_file_tbl[index].extension, NULL);
256 clean_graph_dump_file (dump_base_name, dump_name);
257 free (dump_name);
258 }
259 dump_file_tbl[index].initialized = 1;
260 open_arg = "w";
261 }
262 else
263 open_arg = "a";
264
265 dump_name = concat (dump_base_name, seq,
266 dump_file_tbl[index].extension, NULL);
267
268 dump_file = fopen (dump_name, open_arg);
269 if (dump_file == NULL)
270 fatal_error ("can't open %s: %m", dump_name);
271
272 free (dump_name);
273
274 if (decl)
275 fprintf (dump_file, "\n;; Function %s%s\n\n",
ae2bcd98 276 lang_hooks.decl_printable_name (decl, 2),
f6db1481
RH
277 cfun->function_frequency == FUNCTION_FREQUENCY_HOT
278 ? " (hot)"
279 : cfun->function_frequency == FUNCTION_FREQUENCY_UNLIKELY_EXECUTED
280 ? " (unlikely executed)"
281 : "");
282
283 timevar_pop (TV_DUMP);
284 return 1;
285}
286
287/* Routine to close a dump file. */
288
289static void
290close_dump_file (enum dump_file_index index,
291 void (*func) (FILE *, rtx),
292 rtx insns)
293{
294 if (! dump_file)
295 return;
296
297 timevar_push (TV_DUMP);
298 if (insns
299 && graph_dump_format != no_graph
300 && dump_file_tbl[index].graph_dump_p)
301 {
302 char seq[16];
303 char *suffix;
304
305 sprintf (seq, DUMPFILE_FORMAT, index);
306 suffix = concat (seq, dump_file_tbl[index].extension, NULL);
307 print_rtl_graph_with_bb (dump_base_name, suffix, insns);
308 free (suffix);
309 }
310
311 if (func && insns)
312 func (dump_file, insns);
313
314 fflush (dump_file);
315 fclose (dump_file);
316
317 dump_file = NULL;
318 timevar_pop (TV_DUMP);
319}
320
321/* This is called from various places for FUNCTION_DECL, VAR_DECL,
322 and TYPE_DECL nodes.
323
324 This does nothing for local (non-static) variables, unless the
325 variable is a register variable with an ASMSPEC. In that case, or
326 if the variable is not an automatic, it sets up the RTL and
327 outputs any assembler code (label definition, storage allocation
328 and initialization).
329
330 DECL is the declaration. If ASMSPEC is nonzero, it specifies
331 the assembler symbol name to be used. TOP_LEVEL is nonzero
332 if this declaration is not within a function. */
333
334void
335rest_of_decl_compilation (tree decl,
336 const char *asmspec,
337 int top_level,
338 int at_end)
339{
340 /* We deferred calling assemble_alias so that we could collect
341 other attributes such as visibility. Emit the alias now. */
342 {
343 tree alias;
344 alias = lookup_attribute ("alias", DECL_ATTRIBUTES (decl));
345 if (alias)
346 {
347 alias = TREE_VALUE (TREE_VALUE (alias));
348 alias = get_identifier (TREE_STRING_POINTER (alias));
349 assemble_alias (decl, alias);
350 }
351 }
352
353 /* Forward declarations for nested functions are not "external",
354 but we need to treat them as if they were. */
355 if (TREE_STATIC (decl) || DECL_EXTERNAL (decl)
356 || TREE_CODE (decl) == FUNCTION_DECL)
357 {
358 timevar_push (TV_VARCONST);
359
360 if (asmspec)
361 make_decl_rtl (decl, asmspec);
362
363 /* Don't output anything when a tentative file-scope definition
364 is seen. But at end of compilation, do output code for them.
365
366 We do output all variables when unit-at-a-time is active and rely on
367 callgraph code to defer them except for forward declarations
368 (see gcc.c-torture/compile/920624-1.c) */
369 if ((at_end
370 || !DECL_DEFER_OUTPUT (decl)
371 || (flag_unit_at_a_time && DECL_INITIAL (decl)))
372 && !DECL_EXTERNAL (decl))
373 {
374 if (flag_unit_at_a_time && !cgraph_global_info_ready
375 && TREE_CODE (decl) != FUNCTION_DECL && top_level)
376 cgraph_varpool_finalize_decl (decl);
377 else
378 assemble_variable (decl, top_level, at_end, 0);
379 }
380
381#ifdef ASM_FINISH_DECLARE_OBJECT
382 if (decl == last_assemble_variable_decl)
383 {
384 ASM_FINISH_DECLARE_OBJECT (asm_out_file, decl,
385 top_level, at_end);
386 }
387#endif
388
389 timevar_pop (TV_VARCONST);
390 }
391 else if (DECL_REGISTER (decl) && asmspec != 0)
392 {
393 if (decode_reg_name (asmspec) >= 0)
394 {
395 SET_DECL_RTL (decl, NULL_RTX);
396 make_decl_rtl (decl, asmspec);
397 }
398 else
399 {
6de9cd9a
DN
400 error ("%Hinvalid register name `%s' for register variable",
401 &DECL_SOURCE_LOCATION (decl), asmspec);
f6db1481
RH
402 DECL_REGISTER (decl) = 0;
403 if (!top_level)
404 expand_decl (decl);
405 }
406 }
407 else if (TREE_CODE (decl) == TYPE_DECL)
408 {
409 timevar_push (TV_SYMOUT);
410 debug_hooks->type_decl (decl, !top_level);
411 timevar_pop (TV_SYMOUT);
412 }
413}
414
415/* Called after finishing a record, union or enumeral type. */
416
417void
418rest_of_type_compilation (tree type, int toplev)
419{
420 /* Avoid confusing the debug information machinery when there are
421 errors. */
422 if (errorcount != 0 || sorrycount != 0)
423 return;
424
425 timevar_push (TV_SYMOUT);
426 debug_hooks->type_decl (TYPE_STUB_DECL (type), !toplev);
427 timevar_pop (TV_SYMOUT);
428}
429
430/* Turn the RTL into assembly. */
431static void
fd743bc1 432rest_of_handle_final (void)
f6db1481
RH
433{
434 timevar_push (TV_FINAL);
435 {
436 rtx x;
437 const char *fnname;
438
439 /* Get the function's name, as described by its RTL. This may be
440 different from the DECL_NAME name used in the source file. */
441
fd743bc1 442 x = DECL_RTL (current_function_decl);
f6db1481
RH
443 if (GET_CODE (x) != MEM)
444 abort ();
445 x = XEXP (x, 0);
446 if (GET_CODE (x) != SYMBOL_REF)
447 abort ();
448 fnname = XSTR (x, 0);
449
fd743bc1
PB
450 assemble_start_function (current_function_decl, fnname);
451 final_start_function (get_insns (), asm_out_file, optimize);
452 final (get_insns (), asm_out_file, optimize, 0);
f6db1481
RH
453 final_end_function ();
454
455#ifdef IA64_UNWIND_INFO
456 /* ??? The IA-64 ".handlerdata" directive must be issued before
457 the ".endp" directive that closes the procedure descriptor. */
458 output_function_exception_table ();
459#endif
460
fd743bc1 461 assemble_end_function (current_function_decl, fnname);
f6db1481
RH
462
463#ifndef IA64_UNWIND_INFO
464 /* Otherwise, it feels unclean to switch sections in the middle. */
465 output_function_exception_table ();
466#endif
467
468 if (! quiet_flag)
469 fflush (asm_out_file);
470
471 /* Release all memory allocated by flow. */
bb8a619e 472 free_basic_block_vars ();
f6db1481
RH
473
474 /* Release all memory held by regsets now. */
475 regset_release_memory ();
476 }
477 timevar_pop (TV_FINAL);
478
479 ggc_collect ();
480}
481
482#ifdef DELAY_SLOTS
483/* Run delay slot optimization. */
484static void
fd743bc1 485rest_of_handle_delay_slots (void)
f6db1481
RH
486{
487 timevar_push (TV_DBR_SCHED);
fd743bc1 488 open_dump_file (DFI_dbr, current_function_decl);
f6db1481 489
fd743bc1 490 dbr_schedule (get_insns (), dump_file);
f6db1481 491
fd743bc1 492 close_dump_file (DFI_dbr, print_rtl, get_insns ());
f6db1481
RH
493 timevar_pop (TV_DBR_SCHED);
494
495 ggc_collect ();
496}
497#endif
498
499#ifdef STACK_REGS
500/* Convert register usage from flat register file usage to a stack
501 register file. */
502static void
fd743bc1 503rest_of_handle_stack_regs (void)
f6db1481
RH
504{
505#if defined (HAVE_ATTR_length)
506 /* If flow2 creates new instructions which need splitting
507 and scheduling after reload is not done, they might not be
508 split until final which doesn't allow splitting
509 if HAVE_ATTR_length. */
510#ifdef INSN_SCHEDULING
511 if (optimize && !flag_schedule_insns_after_reload)
512#else
513 if (optimize)
514#endif
515 {
516 timevar_push (TV_SHORTEN_BRANCH);
517 split_all_insns (1);
518 timevar_pop (TV_SHORTEN_BRANCH);
519 }
520#endif
521
522 timevar_push (TV_REG_STACK);
fd743bc1 523 open_dump_file (DFI_stack, current_function_decl);
f6db1481 524
827c06b6 525 if (reg_to_stack (dump_file) && optimize)
f6db1481
RH
526 {
527 if (cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_POST_REGSTACK
528 | (flag_crossjumping ? CLEANUP_CROSSJUMP : 0))
750054a2 529 && (flag_reorder_blocks || flag_reorder_blocks_and_partition))
f6db1481
RH
530 {
531 reorder_basic_blocks ();
532 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_POST_REGSTACK);
533 }
534 }
535
fd743bc1 536 close_dump_file (DFI_stack, print_rtl_with_bb, get_insns ());
f6db1481
RH
537 timevar_pop (TV_REG_STACK);
538
539 ggc_collect ();
540}
541#endif
542
543/* Track the variables, ie. compute where the variable is stored at each position in function. */
544static void
fd743bc1 545rest_of_handle_variable_tracking (void)
f6db1481
RH
546{
547 timevar_push (TV_VAR_TRACKING);
fd743bc1 548 open_dump_file (DFI_vartrack, current_function_decl);
f6db1481
RH
549
550 variable_tracking_main ();
551
fd743bc1 552 close_dump_file (DFI_vartrack, print_rtl_with_bb, get_insns ());
f6db1481
RH
553 timevar_pop (TV_VAR_TRACKING);
554}
555
556/* Machine independent reorg pass. */
557static void
fd743bc1 558rest_of_handle_machine_reorg (void)
f6db1481
RH
559{
560 timevar_push (TV_MACH_DEP);
fd743bc1 561 open_dump_file (DFI_mach, current_function_decl);
f6db1481 562
5fd9b178 563 targetm.machine_dependent_reorg ();
f6db1481 564
fd743bc1 565 close_dump_file (DFI_mach, print_rtl, get_insns ());
f6db1481
RH
566 timevar_pop (TV_MACH_DEP);
567
568 ggc_collect ();
569}
570
571
572/* Run new register allocator. Return TRUE if we must exit
573 rest_of_compilation upon return. */
574static bool
fd743bc1 575rest_of_handle_new_regalloc (void)
f6db1481
RH
576{
577 int failure;
578
fd743bc1 579 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
580 reg_alloc ();
581
582 timevar_pop (TV_LOCAL_ALLOC);
583 if (dump_file_tbl[DFI_lreg].enabled)
584 {
585 timevar_push (TV_DUMP);
586
587 close_dump_file (DFI_lreg, NULL, NULL);
588 timevar_pop (TV_DUMP);
589 }
590
591 /* XXX clean up the whole mess to bring live info in shape again. */
592 timevar_push (TV_GLOBAL_ALLOC);
fd743bc1 593 open_dump_file (DFI_greg, current_function_decl);
f6db1481 594
fd743bc1
PB
595 build_insn_chain (get_insns ());
596 failure = reload (get_insns (), 0);
f6db1481
RH
597
598 timevar_pop (TV_GLOBAL_ALLOC);
599
600 if (dump_file_tbl[DFI_greg].enabled)
601 {
602 timevar_push (TV_DUMP);
603
604 dump_global_regs (dump_file);
605
fd743bc1 606 close_dump_file (DFI_greg, print_rtl_with_bb, get_insns ());
f6db1481
RH
607 timevar_pop (TV_DUMP);
608 }
609
610 if (failure)
611 return true;
612
613 reload_completed = 1;
614
615 return false;
616}
617
618/* Run old register allocator. Return TRUE if we must exit
619 rest_of_compilation upon return. */
620static bool
fd743bc1 621rest_of_handle_old_regalloc (void)
f6db1481
RH
622{
623 int failure;
624 int rebuild_notes;
625
626 /* Allocate the reg_renumber array. */
627 allocate_reg_info (max_regno, FALSE, TRUE);
628
629 /* And the reg_equiv_memory_loc array. */
965ccc5a
R
630 VARRAY_GROW (reg_equiv_memory_loc_varray, max_regno);
631 reg_equiv_memory_loc = &VARRAY_RTX (reg_equiv_memory_loc_varray, 0);
f6db1481
RH
632
633 allocate_initial_values (reg_equiv_memory_loc);
634
fd743bc1 635 regclass (get_insns (), max_reg_num (), dump_file);
f6db1481
RH
636 rebuild_notes = local_alloc ();
637
638 timevar_pop (TV_LOCAL_ALLOC);
639
640 /* Local allocation may have turned an indirect jump into a direct
641 jump. If so, we must rebuild the JUMP_LABEL fields of jumping
642 instructions. */
643 if (rebuild_notes)
644 {
645 timevar_push (TV_JUMP);
646
fd743bc1 647 rebuild_jump_labels (get_insns ());
f6db1481
RH
648 purge_all_dead_edges (0);
649
650 timevar_pop (TV_JUMP);
651 }
652
653 if (dump_file_tbl[DFI_lreg].enabled)
654 {
655 timevar_push (TV_DUMP);
656
657 dump_flow_info (dump_file);
658 dump_local_alloc (dump_file);
659
fd743bc1 660 close_dump_file (DFI_lreg, print_rtl_with_bb, get_insns ());
f6db1481
RH
661 timevar_pop (TV_DUMP);
662 }
663
664 ggc_collect ();
665
666 timevar_push (TV_GLOBAL_ALLOC);
fd743bc1 667 open_dump_file (DFI_greg, current_function_decl);
f6db1481
RH
668
669 /* If optimizing, allocate remaining pseudo-regs. Do the reload
670 pass fixing up any insns that are invalid. */
671
672 if (optimize)
673 failure = global_alloc (dump_file);
674 else
675 {
fd743bc1
PB
676 build_insn_chain (get_insns ());
677 failure = reload (get_insns (), 0);
f6db1481
RH
678 }
679
680 timevar_pop (TV_GLOBAL_ALLOC);
681
682 if (dump_file_tbl[DFI_greg].enabled)
683 {
684 timevar_push (TV_DUMP);
685
686 dump_global_regs (dump_file);
687
fd743bc1 688 close_dump_file (DFI_greg, print_rtl_with_bb, get_insns ());
f6db1481
RH
689 timevar_pop (TV_DUMP);
690 }
691
692 return failure;
693}
694
695/* Run the regrename and cprop passes. */
696static void
fd743bc1 697rest_of_handle_regrename (void)
f6db1481
RH
698{
699 timevar_push (TV_RENAME_REGISTERS);
fd743bc1 700 open_dump_file (DFI_rnreg, current_function_decl);
f6db1481
RH
701
702 if (flag_rename_registers)
703 regrename_optimize ();
704 if (flag_cprop_registers)
705 copyprop_hardreg_forward ();
706
fd743bc1 707 close_dump_file (DFI_rnreg, print_rtl_with_bb, get_insns ());
f6db1481
RH
708 timevar_pop (TV_RENAME_REGISTERS);
709}
710
711/* Reorder basic blocks. */
712static void
fd743bc1 713rest_of_handle_reorder_blocks (void)
f6db1481
RH
714{
715 bool changed;
fd743bc1 716 open_dump_file (DFI_bbro, current_function_decl);
2f8e398b 717
f6db1481
RH
718 /* Last attempt to optimize CFG, as scheduling, peepholing and insn
719 splitting possibly introduced more crossjumping opportunities. */
720 changed = cleanup_cfg (CLEANUP_EXPENSIVE
721 | (!HAVE_conditional_execution
722 ? CLEANUP_UPDATE_LIFE : 0));
723
724 if (flag_sched2_use_traces && flag_schedule_insns_after_reload)
725 tracer ();
750054a2 726 if (flag_reorder_blocks || flag_reorder_blocks_and_partition)
f6db1481 727 reorder_basic_blocks ();
750054a2 728 if (flag_reorder_blocks || flag_reorder_blocks_and_partition
f6db1481
RH
729 || (flag_sched2_use_traces && flag_schedule_insns_after_reload))
730 changed |= cleanup_cfg (CLEANUP_EXPENSIVE
731 | (!HAVE_conditional_execution
732 ? CLEANUP_UPDATE_LIFE : 0));
733
734 /* On conditional execution targets we can not update the life cheaply, so
735 we deffer the updating to after both cleanups. This may lose some cases
736 but should not be terribly bad. */
737 if (changed && HAVE_conditional_execution)
738 update_life_info (NULL, UPDATE_LIFE_GLOBAL_RM_NOTES,
739 PROP_DEATH_NOTES);
fd743bc1 740 close_dump_file (DFI_bbro, print_rtl_with_bb, get_insns ());
f6db1481
RH
741}
742
743#ifdef INSN_SCHEDULING
744/* Run instruction scheduler. */
745static void
fd743bc1 746rest_of_handle_sched (void)
f6db1481 747{
e5626198
AZ
748 timevar_push (TV_SMS);
749 if (optimize > 0 && flag_modulo_sched)
750 {
751
752 /* Perform SMS module scheduling. */
fd743bc1 753 open_dump_file (DFI_sms, current_function_decl);
e5626198
AZ
754
755 /* We want to be able to create new pseudos. */
756 no_new_pseudos = 0;
757 sms_schedule (dump_file);
758 close_dump_file (DFI_sms, print_rtl, get_insns ());
759
760
61ada8ae 761 /* Update the life information, because we add pseudos. */
e5626198
AZ
762 max_regno = max_reg_num ();
763 allocate_reg_info (max_regno, FALSE, FALSE);
764 update_life_info_in_dirty_blocks (UPDATE_LIFE_GLOBAL_RM_NOTES,
765 (PROP_DEATH_NOTES
766 | PROP_KILL_DEAD_CODE
767 | PROP_SCAN_DEAD_CODE));
768 no_new_pseudos = 1;
769 }
770 timevar_pop (TV_SMS);
f6db1481
RH
771 timevar_push (TV_SCHED);
772
773 /* Print function header into sched dump now
774 because doing the sched analysis makes some of the dump. */
775 if (optimize > 0 && flag_schedule_insns)
776 {
fd743bc1 777 open_dump_file (DFI_sched, current_function_decl);
f6db1481
RH
778
779 /* Do control and data sched analysis,
780 and write some of the results to dump file. */
781
782 schedule_insns (dump_file);
783
fd743bc1 784 close_dump_file (DFI_sched, print_rtl_with_bb, get_insns ());
f6db1481
RH
785 }
786 timevar_pop (TV_SCHED);
787
788 ggc_collect ();
789}
790
791/* Run second scheduling pass after reload. */
792static void
fd743bc1 793rest_of_handle_sched2 (void)
f6db1481
RH
794{
795 timevar_push (TV_SCHED2);
fd743bc1 796 open_dump_file (DFI_sched2, current_function_decl);
f6db1481
RH
797
798 /* Do control and data sched analysis again,
799 and write some more of the results to dump file. */
800
801 split_all_insns (1);
802
803 if (flag_sched2_use_superblocks || flag_sched2_use_traces)
804 {
805 schedule_ebbs (dump_file);
806 /* No liveness updating code yet, but it should be easy to do.
4ee31f1e 807 reg-stack recomputes the liveness when needed for now. */
f6db1481
RH
808 count_or_remove_death_notes (NULL, 1);
809 cleanup_cfg (CLEANUP_EXPENSIVE);
810 }
811 else
812 schedule_insns (dump_file);
813
fd743bc1 814 close_dump_file (DFI_sched2, print_rtl_with_bb, get_insns ());
f6db1481
RH
815 timevar_pop (TV_SCHED2);
816
817 ggc_collect ();
818}
819#endif
820
f9957958 821static void
fd743bc1 822rest_of_handle_gcse2 (void)
f9957958 823{
fd743bc1 824 open_dump_file (DFI_gcse2, current_function_decl);
f9957958 825
fd743bc1
PB
826 gcse_after_reload_main (get_insns (), dump_file);
827 rebuild_jump_labels (get_insns ());
828 delete_trivially_dead_insns (get_insns (), max_reg_num ());
829 close_dump_file (DFI_gcse2, print_rtl_with_bb, get_insns ());
f9957958
MH
830
831 ggc_collect ();
832
833#ifdef ENABLE_CHECKING
834 verify_flow_info ();
835#endif
836}
837
f6db1481
RH
838/* Register allocation pre-pass, to reduce number of moves necessary
839 for two-address machines. */
840static void
fd743bc1 841rest_of_handle_regmove (void)
f6db1481
RH
842{
843 timevar_push (TV_REGMOVE);
fd743bc1 844 open_dump_file (DFI_regmove, current_function_decl);
f6db1481 845
fd743bc1 846 regmove_optimize (get_insns (), max_reg_num (), dump_file);
f6db1481
RH
847
848 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_UPDATE_LIFE);
fd743bc1 849 close_dump_file (DFI_regmove, print_rtl_with_bb, get_insns ());
f6db1481
RH
850 timevar_pop (TV_REGMOVE);
851
852 ggc_collect ();
853}
854
855/* Run tracer. */
856static void
fd743bc1 857rest_of_handle_tracer (void)
f6db1481 858{
fd743bc1 859 open_dump_file (DFI_tracer, current_function_decl);
f6db1481
RH
860 if (dump_file)
861 dump_flow_info (dump_file);
862 tracer ();
863 cleanup_cfg (CLEANUP_EXPENSIVE);
fd743bc1 864 reg_scan (get_insns (), max_reg_num (), 0);
f6db1481
RH
865 close_dump_file (DFI_tracer, print_rtl_with_bb, get_insns ());
866}
867
868/* If-conversion and CFG cleanup. */
869static void
fd743bc1 870rest_of_handle_if_conversion (void)
f6db1481 871{
fd743bc1 872 open_dump_file (DFI_ce1, current_function_decl);
f6db1481
RH
873 if (flag_if_conversion)
874 {
875 timevar_push (TV_IFCVT);
876 if (dump_file)
877 dump_flow_info (dump_file);
878 cleanup_cfg (CLEANUP_EXPENSIVE);
fd743bc1 879 reg_scan (get_insns (), max_reg_num (), 0);
f6db1481
RH
880 if_convert (0);
881 timevar_pop (TV_IFCVT);
882 }
883 timevar_push (TV_JUMP);
884 cleanup_cfg (CLEANUP_EXPENSIVE);
fd743bc1 885 reg_scan (get_insns (), max_reg_num (), 0);
f6db1481
RH
886 timevar_pop (TV_JUMP);
887 close_dump_file (DFI_ce1, print_rtl_with_bb, get_insns ());
888}
889
890/* Rerun if-conversion, as combine may have simplified things enough
891 to now meet sequence length restrictions. */
892static void
fd743bc1 893rest_of_handle_if_after_combine (void)
f6db1481
RH
894{
895 timevar_push (TV_IFCVT);
fd743bc1 896 open_dump_file (DFI_ce2, current_function_decl);
f6db1481
RH
897
898 no_new_pseudos = 0;
899 if_convert (1);
900 no_new_pseudos = 1;
901
fd743bc1 902 close_dump_file (DFI_ce2, print_rtl_with_bb, get_insns ());
f6db1481
RH
903 timevar_pop (TV_IFCVT);
904}
905
906static void
fd743bc1 907rest_of_handle_web (void)
f6db1481 908{
fd743bc1 909 open_dump_file (DFI_web, current_function_decl);
f6db1481
RH
910 timevar_push (TV_WEB);
911 web_main ();
fd743bc1 912 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
913 cleanup_cfg (CLEANUP_EXPENSIVE);
914
915 timevar_pop (TV_WEB);
fd743bc1 916 close_dump_file (DFI_web, print_rtl_with_bb, get_insns ());
f6db1481
RH
917 reg_scan (get_insns (), max_reg_num (), 0);
918}
919
920/* Do branch profiling and static profile estimation passes. */
921static void
fd743bc1 922rest_of_handle_branch_prob (void)
f6db1481
RH
923{
924 struct loops loops;
f6db1481 925 timevar_push (TV_BRANCH_PROB);
fd743bc1 926 open_dump_file (DFI_bp, current_function_decl);
f6db1481
RH
927
928 if (profile_arc_flag || flag_test_coverage || flag_branch_probabilities)
929 branch_prob ();
930
931 /* Discover and record the loop depth at the head of each basic
932 block. The loop infrastructure does the real job for us. */
933 flow_loops_find (&loops, LOOP_TREE);
934
935 if (dump_file)
936 flow_loops_dump (&loops, dump_file, NULL, 0);
937
938 /* Estimate using heuristics if no profiling info is available. */
939 if (flag_guess_branch_prob)
940 estimate_probability (&loops);
941
942 flow_loops_free (&loops);
943 free_dominance_info (CDI_DOMINATORS);
fd743bc1 944 close_dump_file (DFI_bp, print_rtl_with_bb, get_insns ());
f6db1481
RH
945 timevar_pop (TV_BRANCH_PROB);
946}
947
948/* Do optimizations based on expression value profiles. */
949static void
fd743bc1 950rest_of_handle_value_profile_transformations (void)
f6db1481 951{
fd743bc1 952 open_dump_file (DFI_vpt, current_function_decl);
f6db1481
RH
953 timevar_push (TV_VPT);
954
955 if (value_profile_transformations ())
956 cleanup_cfg (CLEANUP_EXPENSIVE);
957
958 timevar_pop (TV_VPT);
fd743bc1 959 close_dump_file (DFI_vpt, print_rtl_with_bb, get_insns ());
f6db1481
RH
960}
961
962/* Do control and data flow analysis; write some of the results to the
963 dump file. */
964static void
fd743bc1 965rest_of_handle_cfg (void)
f6db1481 966{
fd743bc1 967 open_dump_file (DFI_cfg, current_function_decl);
f6db1481
RH
968 if (dump_file)
969 dump_flow_info (dump_file);
970 if (optimize)
971 cleanup_cfg (CLEANUP_EXPENSIVE
972 | (flag_thread_jumps ? CLEANUP_THREADING : 0));
973
974 /* It may make more sense to mark constant functions after dead code is
975 eliminated by life_analysis, but we need to do it early, as -fprofile-arcs
976 may insert code making function non-constant, but we still must consider
977 it as constant, otherwise -fbranch-probabilities will not read data back.
978
979 life_analysis rarely eliminates modification of external memory.
980 */
981 if (optimize)
982 {
983 /* Alias analysis depends on this information and mark_constant_function
984 depends on alias analysis. */
fd743bc1 985 reg_scan (get_insns (), max_reg_num (), 1);
f6db1481
RH
986 mark_constant_function ();
987 }
988
fd743bc1 989 close_dump_file (DFI_cfg, print_rtl_with_bb, get_insns ());
f6db1481
RH
990}
991
992/* Purge addressofs. */
993static void
fd743bc1 994rest_of_handle_addressof (void)
f6db1481 995{
fd743bc1 996 open_dump_file (DFI_addressof, current_function_decl);
2f8e398b 997
fd743bc1 998 purge_addressof (get_insns ());
f6db1481
RH
999 if (optimize && purge_all_dead_edges (0))
1000 delete_unreachable_blocks ();
fd743bc1 1001 reg_scan (get_insns (), max_reg_num (), 1);
f6db1481 1002
fd743bc1 1003 close_dump_file (DFI_addressof, print_rtl, get_insns ());
f6db1481
RH
1004}
1005
f6db1481
RH
1006/* Perform jump bypassing and control flow optimizations. */
1007static void
fd743bc1 1008rest_of_handle_jump_bypass (void)
f6db1481
RH
1009{
1010 timevar_push (TV_BYPASS);
fd743bc1 1011 open_dump_file (DFI_bypass, current_function_decl);
f6db1481
RH
1012
1013 cleanup_cfg (CLEANUP_EXPENSIVE);
fd743bc1 1014 reg_scan (get_insns (), max_reg_num (), 1);
f6db1481
RH
1015
1016 if (bypass_jumps (dump_file))
1017 {
fd743bc1 1018 rebuild_jump_labels (get_insns ());
f6db1481 1019 cleanup_cfg (CLEANUP_EXPENSIVE);
fd743bc1 1020 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
1021 }
1022
fd743bc1 1023 close_dump_file (DFI_bypass, print_rtl_with_bb, get_insns ());
f6db1481
RH
1024 timevar_pop (TV_BYPASS);
1025
1026 ggc_collect ();
1027
1028#ifdef ENABLE_CHECKING
1029 verify_flow_info ();
1030#endif
1031}
1032
f6db1481
RH
1033/* Try combining insns through substitution. */
1034static void
fd743bc1 1035rest_of_handle_combine (void)
f6db1481
RH
1036{
1037 int rebuild_jump_labels_after_combine = 0;
1038
1039 timevar_push (TV_COMBINE);
fd743bc1 1040 open_dump_file (DFI_combine, current_function_decl);
f6db1481
RH
1041
1042 rebuild_jump_labels_after_combine
fd743bc1 1043 = combine_instructions (get_insns (), max_reg_num ());
f6db1481 1044
fd743bc1 1045 /* Combining get_insns () may have turned an indirect jump into a
f6db1481
RH
1046 direct jump. Rebuild the JUMP_LABEL fields of jumping
1047 instructions. */
1048 if (rebuild_jump_labels_after_combine)
1049 {
1050 timevar_push (TV_JUMP);
fd743bc1 1051 rebuild_jump_labels (get_insns ());
f6db1481
RH
1052 timevar_pop (TV_JUMP);
1053
1054 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_UPDATE_LIFE);
1055 }
1056
fd743bc1 1057 close_dump_file (DFI_combine, print_rtl_with_bb, get_insns ());
f6db1481
RH
1058 timevar_pop (TV_COMBINE);
1059
1060 ggc_collect ();
1061}
1062
1063/* Perform life analysis. */
1064static void
fd743bc1 1065rest_of_handle_life (void)
f6db1481 1066{
fd743bc1 1067 open_dump_file (DFI_life, current_function_decl);
f6db1481
RH
1068 regclass_init ();
1069
1070#ifdef ENABLE_CHECKING
1071 verify_flow_info ();
1072#endif
827c06b6 1073 life_analysis (dump_file, PROP_FINAL);
f6db1481
RH
1074 if (optimize)
1075 cleanup_cfg ((optimize ? CLEANUP_EXPENSIVE : 0) | CLEANUP_UPDATE_LIFE
1076 | CLEANUP_LOG_LINKS
1077 | (flag_thread_jumps ? CLEANUP_THREADING : 0));
1078 timevar_pop (TV_FLOW);
1079
6de9cd9a 1080 if (extra_warnings)
f6db1481 1081 {
fd743bc1 1082 setjmp_vars_warning (DECL_INITIAL (current_function_decl));
6de9cd9a 1083 setjmp_args_warning ();
f6db1481
RH
1084 }
1085
1086 if (optimize)
1087 {
1088 if (!flag_new_regalloc && initialize_uninitialized_subregs ())
1089 {
1090 /* Insns were inserted, and possibly pseudos created, so
1091 things might look a bit different. */
f6db1481
RH
1092 allocate_reg_life_data ();
1093 update_life_info (NULL, UPDATE_LIFE_GLOBAL_RM_NOTES,
1094 PROP_LOG_LINKS | PROP_REG_INFO | PROP_DEATH_NOTES);
1095 }
1096 }
1097
1098 no_new_pseudos = 1;
1099
fd743bc1 1100 close_dump_file (DFI_life, print_rtl_with_bb, get_insns ());
f6db1481
RH
1101
1102 ggc_collect ();
1103}
1104
1105/* Perform common subexpression elimination. Nonzero value from
1106 `cse_main' means that jumps were simplified and some code may now
1107 be unreachable, so do jump optimization again. */
1108static void
fd743bc1 1109rest_of_handle_cse (void)
f6db1481
RH
1110{
1111 int tem;
fd743bc1 1112 open_dump_file (DFI_cse, current_function_decl);
f6db1481
RH
1113 if (dump_file)
1114 dump_flow_info (dump_file);
1115 timevar_push (TV_CSE);
1116
fd743bc1 1117 reg_scan (get_insns (), max_reg_num (), 1);
f6db1481 1118
fd743bc1 1119 tem = cse_main (get_insns (), max_reg_num (), 0, dump_file);
f6db1481 1120 if (tem)
fd743bc1 1121 rebuild_jump_labels (get_insns ());
f6db1481
RH
1122 if (purge_all_dead_edges (0))
1123 delete_unreachable_blocks ();
1124
fd743bc1 1125 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
1126
1127 /* If we are not running more CSE passes, then we are no longer
1128 expecting CSE to be run. But always rerun it in a cheap mode. */
1129 cse_not_expected = !flag_rerun_cse_after_loop && !flag_gcse;
1130
1131 if (tem || optimize > 1)
1132 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_PRE_LOOP);
f6db1481
RH
1133
1134 timevar_pop (TV_CSE);
fd743bc1 1135 close_dump_file (DFI_cse, print_rtl_with_bb, get_insns ());
f6db1481
RH
1136}
1137
1138/* Run second CSE pass after loop optimizations. */
1139static void
fd743bc1 1140rest_of_handle_cse2 (void)
f6db1481
RH
1141{
1142 int tem;
f6db1481 1143 timevar_push (TV_CSE2);
fd743bc1 1144 open_dump_file (DFI_cse2, current_function_decl);
f6db1481
RH
1145 if (dump_file)
1146 dump_flow_info (dump_file);
1147 /* CFG is no longer maintained up-to-date. */
fd743bc1 1148 tem = cse_main (get_insns (), max_reg_num (), 1, dump_file);
f6db1481
RH
1149
1150 /* Run a pass to eliminate duplicated assignments to condition code
1151 registers. We have to run this after bypass_jumps, because it
1152 makes it harder for that pass to determine whether a jump can be
1153 bypassed safely. */
1154 cse_condition_code_reg ();
1155
1156 purge_all_dead_edges (0);
fd743bc1 1157 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
1158
1159 if (tem)
1160 {
1161 timevar_push (TV_JUMP);
fd743bc1 1162 rebuild_jump_labels (get_insns ());
f6db1481
RH
1163 cleanup_cfg (CLEANUP_EXPENSIVE);
1164 timevar_pop (TV_JUMP);
1165 }
fd743bc1
PB
1166 reg_scan (get_insns (), max_reg_num (), 0);
1167 close_dump_file (DFI_cse2, print_rtl_with_bb, get_insns ());
f6db1481
RH
1168 ggc_collect ();
1169 timevar_pop (TV_CSE2);
1170}
1171
1172/* Perform global cse. */
1173static void
fd743bc1 1174rest_of_handle_gcse (void)
f6db1481
RH
1175{
1176 int save_csb, save_cfj;
1177 int tem2 = 0, tem;
f6db1481 1178 timevar_push (TV_GCSE);
fd743bc1 1179 open_dump_file (DFI_gcse, current_function_decl);
f6db1481 1180
fd743bc1
PB
1181 tem = gcse_main (get_insns (), dump_file);
1182 rebuild_jump_labels (get_insns ());
1183 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
1184
1185 save_csb = flag_cse_skip_blocks;
1186 save_cfj = flag_cse_follow_jumps;
1187 flag_cse_skip_blocks = flag_cse_follow_jumps = 0;
1188
f6db1481
RH
1189 /* If -fexpensive-optimizations, re-run CSE to clean up things done
1190 by gcse. */
1191 if (flag_expensive_optimizations)
1192 {
1193 timevar_push (TV_CSE);
fd743bc1
PB
1194 reg_scan (get_insns (), max_reg_num (), 1);
1195 tem2 = cse_main (get_insns (), max_reg_num (), 0, dump_file);
f6db1481 1196 purge_all_dead_edges (0);
fd743bc1 1197 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
1198 timevar_pop (TV_CSE);
1199 cse_not_expected = !flag_rerun_cse_after_loop;
1200 }
1201
1202 /* If gcse or cse altered any jumps, rerun jump optimizations to clean
1203 things up. Then possibly re-run CSE again. */
1204 while (tem || tem2)
1205 {
1206 tem = tem2 = 0;
1207 timevar_push (TV_JUMP);
fd743bc1 1208 rebuild_jump_labels (get_insns ());
f6db1481
RH
1209 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_PRE_LOOP);
1210 timevar_pop (TV_JUMP);
1211
1212 if (flag_expensive_optimizations)
1213 {
1214 timevar_push (TV_CSE);
fd743bc1
PB
1215 reg_scan (get_insns (), max_reg_num (), 1);
1216 tem2 = cse_main (get_insns (), max_reg_num (), 0, dump_file);
f6db1481 1217 purge_all_dead_edges (0);
fd743bc1 1218 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
1219 timevar_pop (TV_CSE);
1220 }
1221 }
1222
fd743bc1 1223 close_dump_file (DFI_gcse, print_rtl_with_bb, get_insns ());
f6db1481
RH
1224 timevar_pop (TV_GCSE);
1225
1226 ggc_collect ();
1227 flag_cse_skip_blocks = save_csb;
1228 flag_cse_follow_jumps = save_cfj;
1229#ifdef ENABLE_CHECKING
1230 verify_flow_info ();
1231#endif
1232}
1233
1234/* Move constant computations out of loops. */
1235static void
fd743bc1 1236rest_of_handle_loop_optimize (void)
f6db1481
RH
1237{
1238 int do_unroll, do_prefetch;
1239
1240 timevar_push (TV_LOOP);
1241 delete_dead_jumptables ();
1242 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_PRE_LOOP);
fd743bc1 1243 open_dump_file (DFI_loop, current_function_decl);
f6db1481
RH
1244
1245 /* CFG is no longer maintained up-to-date. */
1246 free_bb_for_insn ();
1247
1248 if (flag_unroll_loops)
1249 do_unroll = LOOP_AUTO_UNROLL; /* Having two unrollers is useless. */
1250 else
1251 do_unroll = flag_old_unroll_loops ? LOOP_UNROLL : LOOP_AUTO_UNROLL;
1252 do_prefetch = flag_prefetch_loop_arrays ? LOOP_PREFETCH : 0;
1253
1254 if (flag_rerun_loop_opt)
1255 {
1256 cleanup_barriers ();
1257
1258 /* We only want to perform unrolling once. */
fd743bc1 1259 loop_optimize (get_insns (), dump_file, do_unroll);
f6db1481
RH
1260 do_unroll = 0;
1261
1262 /* The first call to loop_optimize makes some instructions
1263 trivially dead. We delete those instructions now in the
1264 hope that doing so will make the heuristics in loop work
1265 better and possibly speed up compilation. */
fd743bc1 1266 delete_trivially_dead_insns (get_insns (), max_reg_num ());
f6db1481
RH
1267
1268 /* The regscan pass is currently necessary as the alias
1269 analysis code depends on this information. */
fd743bc1 1270 reg_scan (get_insns (), max_reg_num (), 1);
f6db1481
RH
1271 }
1272 cleanup_barriers ();
fd743bc1 1273 loop_optimize (get_insns (), dump_file, do_unroll | do_prefetch);
f6db1481
RH
1274
1275 /* Loop can create trivially dead instructions. */
fd743bc1
PB
1276 delete_trivially_dead_insns (get_insns (), max_reg_num ());
1277 close_dump_file (DFI_loop, print_rtl, get_insns ());
f6db1481 1278 timevar_pop (TV_LOOP);
fd743bc1 1279 find_basic_blocks (get_insns (), max_reg_num (), dump_file);
f6db1481
RH
1280
1281 ggc_collect ();
1282}
1283
1284/* Perform loop optimizations. It might be better to do them a bit
1285 sooner, but we want the profile feedback to work more
1286 efficiently. */
1287static void
fd743bc1 1288rest_of_handle_loop2 (void)
f6db1481
RH
1289{
1290 struct loops *loops;
1291 basic_block bb;
1292
5e962776
ZD
1293 if (!flag_move_loop_invariants
1294 && !flag_unswitch_loops
689ba89d
ZD
1295 && !flag_peel_loops
1296 && !flag_unroll_loops
1297 && !flag_branch_on_count_reg)
1298 return;
1299
f6db1481 1300 timevar_push (TV_LOOP);
fd743bc1 1301 open_dump_file (DFI_loop2, current_function_decl);
f6db1481
RH
1302 if (dump_file)
1303 dump_flow_info (dump_file);
1304
1305 /* Initialize structures for layout changes. */
1306 cfg_layout_initialize ();
1307
1308 loops = loop_optimizer_init (dump_file);
1309
1310 if (loops)
1311 {
1312 /* The optimizations: */
5e962776
ZD
1313 if (flag_move_loop_invariants)
1314 move_loop_invariants (loops);
1315
f6db1481
RH
1316 if (flag_unswitch_loops)
1317 unswitch_loops (loops);
1318
1319 if (flag_peel_loops || flag_unroll_loops)
1320 unroll_and_peel_loops (loops,
1321 (flag_peel_loops ? UAP_PEEL : 0) |
1322 (flag_unroll_loops ? UAP_UNROLL : 0) |
1323 (flag_unroll_all_loops ? UAP_UNROLL_ALL : 0));
1324
689ba89d
ZD
1325#ifdef HAVE_doloop_end
1326 if (flag_branch_on_count_reg && HAVE_doloop_end)
1327 doloop_optimize_loops (loops);
1328#endif /* HAVE_doloop_end */
1329
f6db1481
RH
1330 loop_optimizer_finalize (loops, dump_file);
1331 }
1332
1333 /* Finalize layout changes. */
1334 FOR_EACH_BB (bb)
1335 if (bb->next_bb != EXIT_BLOCK_PTR)
1336 bb->rbi->next = bb->next_bb;
1337 cfg_layout_finalize ();
1338
1339 cleanup_cfg (CLEANUP_EXPENSIVE);
fd743bc1
PB
1340 delete_trivially_dead_insns (get_insns (), max_reg_num ());
1341 reg_scan (get_insns (), max_reg_num (), 0);
f6db1481
RH
1342 if (dump_file)
1343 dump_flow_info (dump_file);
1344 close_dump_file (DFI_loop2, print_rtl_with_bb, get_insns ());
1345 timevar_pop (TV_LOOP);
1346 ggc_collect ();
1347}
1348
1349/* This is called from finish_function (within langhooks.parse_file)
1350 after each top-level definition is parsed.
1351 It is supposed to compile that function or variable
1352 and output the assembler code for it.
1353 After we return, the tree storage is freed. */
1354
1355void
2f8e398b 1356rest_of_compilation (void)
f6db1481 1357{
2f8e398b
PB
1358 /* There's no need to defer outputting this function any more; we
1359 know we want to output it. */
1360 DECL_DEFER_OUTPUT (current_function_decl) = 0;
f6db1481 1361
096f22f4
PB
1362 /* There's no need to defer outputting this function any more; we
1363 know we want to output it. */
1364 DECL_DEFER_OUTPUT (current_function_decl) = 0;
1365
f6db1481
RH
1366 /* Register rtl specific functions for cfg. */
1367 rtl_register_cfg_hooks ();
1368
1369 /* Now that we're out of the frontend, we shouldn't have any more
1370 CONCATs anywhere. */
1371 generating_concat_p = 0;
1372
1373 /* When processing delayed functions, prepare_function_start() won't
1374 have been run to re-initialize it. */
1375 cse_not_expected = ! optimize;
1376
6de9cd9a
DN
1377 if (!cfun->dont_emit_block_notes)
1378 {
1379 /* First, make sure that NOTE_BLOCK is set correctly for each
1380 NOTE_INSN_BLOCK_BEG/NOTE_INSN_BLOCK_END note. */
1381 if (!cfun->x_whole_function_mode_p)
1382 identify_blocks ();
1383
1384 /* In function-at-a-time mode, we do not attempt to keep the BLOCK
1385 tree in sensible shape. So, we just recalculate it here. */
1386 if (cfun->x_whole_function_mode_p)
1387 reorder_blocks ();
1388 }
1389 else
1390 finalize_block_changes ();
f6db1481 1391
6de9cd9a 1392 /* Dump the rtl code if we are dumping rtl. */
fd743bc1 1393 if (open_dump_file (DFI_rtl, current_function_decl))
6de9cd9a
DN
1394 close_dump_file (DFI_rtl, print_rtl, get_insns ());
1395
1396 /* Convert from NOTE_INSN_EH_REGION style notes, and do other
1397 sorts of eh initialization. Delay this until after the
1398 initial rtl dump so that we can see the original nesting. */
1399 convert_from_eh_region_ranges ();
f6db1481
RH
1400
1401 /* If we're emitting a nested function, make sure its parent gets
1402 emitted as well. Doing otherwise confuses debug info. */
1403 {
1404 tree parent;
1405 for (parent = DECL_CONTEXT (current_function_decl);
1406 parent != NULL_TREE;
1407 parent = get_containing_scope (parent))
1408 if (TREE_CODE (parent) == FUNCTION_DECL)
1409 TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (parent)) = 1;
1410 }
1411
1412 /* We are now committed to emitting code for this function. Do any
1413 preparation, such as emitting abstract debug info for the inline
1414 before it gets mangled by optimization. */
fd743bc1
PB
1415 if (cgraph_function_possibly_inlined_p (current_function_decl))
1416 (*debug_hooks->outlining_inline_function) (current_function_decl);
f6db1481
RH
1417
1418 /* Remove any notes we don't need. That will make iterating
1419 over the instruction sequence faster, and allow the garbage
1420 collector to reclaim the memory used by the notes. */
1421 remove_unnecessary_notes ();
6de9cd9a
DN
1422 if (!cfun->dont_emit_block_notes)
1423 reorder_blocks ();
f6db1481
RH
1424
1425 ggc_collect ();
1426
1427 /* Initialize some variables used by the optimizers. */
1428 init_function_for_compilation ();
1429
fd743bc1 1430 TREE_ASM_WRITTEN (current_function_decl) = 1;
f6db1481
RH
1431
1432 /* Now that integrate will no longer see our rtl, we need not
1433 distinguish between the return value of this function and the
1434 return value of called functions. Also, we can remove all SETs
1435 of subregs of hard registers; they are only here because of
1436 integrate. Also, we can now initialize pseudos intended to
1437 carry magic hard reg data throughout the function. */
1438 rtx_equal_function_value_matters = 0;
1439 purge_hard_subreg_sets (get_insns ());
1440
1441 /* Early return if there were errors. We can run afoul of our
096f22f4
PB
1442 consistency checks, and there's not really much point in fixing them. */
1443 if (rtl_dump_and_exit || flag_syntax_only || errorcount || sorrycount)
f6db1481
RH
1444 goto exit_rest_of_compilation;
1445
1446 timevar_push (TV_JUMP);
fd743bc1 1447 open_dump_file (DFI_sibling, current_function_decl);
f6db1481 1448
242229bb
JH
1449 /* ??? We may get called either via tree_rest_of_compilation when the CFG
1450 is already built or directly (for instance from coverage code).
1451 The direct callers shall be updated. */
1452 if (!basic_block_info)
1453 {
1454 init_flow ();
1455 rebuild_jump_labels (get_insns ());
1456 find_exception_handler_labels ();
1457 find_basic_blocks (get_insns (), max_reg_num (), dump_file);
1458 }
f6db1481 1459 delete_unreachable_blocks ();
242229bb
JH
1460#ifdef ENABLE_CHECKING
1461 verify_flow_info();
1462#endif
f6db1481
RH
1463
1464 /* Turn NOTE_INSN_PREDICTIONs into branch predictions. */
1465 if (flag_guess_branch_prob)
1466 {
1467 timevar_push (TV_BRANCH_PROB);
1468 note_prediction_to_br_prob ();
1469 timevar_pop (TV_BRANCH_PROB);
1470 }
1471
f6db1481
RH
1472 timevar_pop (TV_JUMP);
1473
6de9cd9a
DN
1474 if (cfun->tail_call_emit)
1475 fixup_tail_calls ();
1476
f6db1481
RH
1477 insn_locators_initialize ();
1478 /* Complete generation of exception handling code. */
1479 if (doing_eh (0))
1480 {
1481 timevar_push (TV_JUMP);
fd743bc1 1482 open_dump_file (DFI_eh, current_function_decl);
f6db1481
RH
1483
1484 finish_eh_generation ();
1485
1486 close_dump_file (DFI_eh, print_rtl, get_insns ());
1487 timevar_pop (TV_JUMP);
1488 }
1489
1490 /* Delay emitting hard_reg_initial_value sets until after EH landing pad
1491 generation, which might create new sets. */
1492 emit_initial_value_sets ();
1493
1494#ifdef FINALIZE_PIC
1495 /* If we are doing position-independent code generation, now
1496 is the time to output special prologues and epilogues.
1497 We do not want to do this earlier, because it just clutters
1498 up inline functions with meaningless insns. */
1499 if (flag_pic)
1500 FINALIZE_PIC;
1501#endif
1502
f6db1481 1503 /* Copy any shared structure that should not be shared. */
fd743bc1 1504 unshare_all_rtl ();
f6db1481
RH
1505
1506#ifdef SETJMP_VIA_SAVE_AREA
1507 /* This must be performed before virtual register instantiation.
d1a6adeb 1508 Please be aware that everything in the compiler that can look
f6db1481
RH
1509 at the RTL up to this point must understand that REG_SAVE_AREA
1510 is just like a use of the REG contained inside. */
1511 if (current_function_calls_alloca)
fd743bc1 1512 optimize_save_area_alloca (get_insns ());
f6db1481
RH
1513#endif
1514
1515 /* Instantiate all virtual registers. */
fd743bc1 1516 instantiate_virtual_regs ();
f6db1481 1517
fd743bc1 1518 open_dump_file (DFI_jump, current_function_decl);
f6db1481
RH
1519
1520 /* Always do one jump optimization pass to ensure that JUMP_LABEL fields
1521 are initialized and to compute whether control can drop off the end
1522 of the function. */
1523
1524 timevar_push (TV_JUMP);
1525 /* Turn NOTE_INSN_EXPECTED_VALUE into REG_BR_PROB. Do this
1526 before jump optimization switches branch directions. */
1527 if (flag_guess_branch_prob)
1528 expected_value_to_br_prob ();
1529
fd743bc1 1530 delete_trivially_dead_insns (get_insns (), max_reg_num ());
242229bb 1531 reg_scan (get_insns(), max_reg_num (), 0);
f6db1481
RH
1532 if (dump_file)
1533 dump_flow_info (dump_file);
1534 cleanup_cfg ((optimize ? CLEANUP_EXPENSIVE : 0) | CLEANUP_PRE_LOOP
1535 | (flag_thread_jumps ? CLEANUP_THREADING : 0));
1536
6de9cd9a
DN
1537 create_loop_notes ();
1538
fd743bc1 1539 purge_line_number_notes (get_insns ());
f6db1481 1540
fd743bc1 1541 close_dump_file (DFI_jump, print_rtl, get_insns ());
f6db1481 1542
f6db1481
RH
1543 if (optimize)
1544 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_PRE_LOOP);
1545
f6db1481
RH
1546 /* Jump optimization, and the removal of NULL pointer checks, may
1547 have reduced the number of instructions substantially. CSE, and
1548 future passes, allocate arrays whose dimensions involve the
1549 maximum instruction UID, so if we can reduce the maximum UID
1550 we'll save big on memory. */
1551 renumber_insns (dump_file);
1552 timevar_pop (TV_JUMP);
1553
fd743bc1 1554 close_dump_file (DFI_jump, print_rtl_with_bb, get_insns ());
f6db1481
RH
1555
1556 ggc_collect ();
1557
1558 if (optimize > 0)
fd743bc1 1559 rest_of_handle_cse ();
f6db1481 1560
fd743bc1 1561 rest_of_handle_addressof ();
f6db1481
RH
1562
1563 ggc_collect ();
1564
1565 if (optimize > 0)
1566 {
1567 if (flag_gcse)
fd743bc1 1568 rest_of_handle_gcse ();
f6db1481
RH
1569
1570 if (flag_loop_optimize)
fd743bc1 1571 rest_of_handle_loop_optimize ();
f6db1481
RH
1572
1573 if (flag_gcse)
fd743bc1 1574 rest_of_handle_jump_bypass ();
f6db1481
RH
1575 }
1576
1577 timevar_push (TV_FLOW);
1578
fd743bc1 1579 rest_of_handle_cfg ();
f6db1481 1580
6de9cd9a
DN
1581 if (!flag_tree_based_profiling
1582 && (optimize > 0 || profile_arc_flag
1583 || flag_test_coverage || flag_branch_probabilities))
f6db1481 1584 {
6de9cd9a
DN
1585 rtl_register_profile_hooks ();
1586 rtl_register_value_prof_hooks ();
fd743bc1 1587 rest_of_handle_branch_prob ();
f6db1481
RH
1588
1589 if (flag_branch_probabilities
1590 && flag_profile_values
1591 && flag_value_profile_transformations)
fd743bc1 1592 rest_of_handle_value_profile_transformations ();
f6db1481
RH
1593
1594 /* Remove the death notes created for vpt. */
1595 if (flag_profile_values)
1596 count_or_remove_death_notes (NULL, 1);
1597 }
1598
1599 if (optimize > 0)
fd743bc1 1600 rest_of_handle_if_conversion ();
f6db1481
RH
1601
1602 if (flag_tracer)
fd743bc1 1603 rest_of_handle_tracer ();
f6db1481 1604
5e962776
ZD
1605 if (optimize > 0
1606 && flag_loop_optimize2)
fd743bc1 1607 rest_of_handle_loop2 ();
f6db1481
RH
1608
1609 if (flag_web)
fd743bc1 1610 rest_of_handle_web ();
f6db1481
RH
1611
1612 if (flag_rerun_cse_after_loop)
fd743bc1 1613 rest_of_handle_cse2 ();
f6db1481
RH
1614
1615 cse_not_expected = 1;
1616
fd743bc1 1617 rest_of_handle_life ();
f6db1481
RH
1618
1619 if (optimize > 0)
fd743bc1 1620 rest_of_handle_combine ();
f6db1481
RH
1621
1622 if (flag_if_conversion)
fd743bc1 1623 rest_of_handle_if_after_combine ();
f6db1481 1624
750054a2
CT
1625 /* The optimization to partition hot/cold basic blocks into separate
1626 sections of the .o file does not work well with exception handling.
9cf737f8 1627 Don't call it if there are exceptions. */
750054a2
CT
1628
1629 if (flag_reorder_blocks_and_partition && !flag_exceptions)
1630 {
1631 no_new_pseudos = 0;
1632 partition_hot_cold_basic_blocks ();
1633 allocate_reg_life_data ();
1634 update_life_info (NULL, UPDATE_LIFE_GLOBAL_RM_NOTES,
1635 PROP_LOG_LINKS | PROP_REG_INFO | PROP_DEATH_NOTES);
1636 no_new_pseudos = 1;
1637 }
1638
f6db1481 1639 if (optimize > 0 && (flag_regmove || flag_expensive_optimizations))
fd743bc1 1640 rest_of_handle_regmove ();
f6db1481
RH
1641
1642 /* Do unconditional splitting before register allocation to allow machine
1643 description to add extra information not needed previously. */
1644 split_all_insns (1);
1645
1646#ifdef OPTIMIZE_MODE_SWITCHING
1647 timevar_push (TV_MODE_SWITCH);
1648
1649 no_new_pseudos = 0;
1650 optimize_mode_switching (NULL);
1651 no_new_pseudos = 1;
1652
1653 timevar_pop (TV_MODE_SWITCH);
1654#endif
1655
1656 /* Any of the several passes since flow1 will have munged register
1657 lifetime data a bit. We need it to be up to date for scheduling
1658 (see handling of reg_known_equiv in init_alias_analysis). */
fd743bc1 1659 recompute_reg_usage (get_insns (), !optimize_size);
f6db1481
RH
1660
1661#ifdef INSN_SCHEDULING
fd743bc1 1662 rest_of_handle_sched ();
f6db1481
RH
1663#endif
1664
1665 /* Determine if the current function is a leaf before running reload
1666 since this can impact optimizations done by the prologue and
1667 epilogue thus changing register elimination offsets. */
1668 current_function_is_leaf = leaf_function_p ();
1669
1670 timevar_push (TV_LOCAL_ALLOC);
fd743bc1 1671 open_dump_file (DFI_lreg, current_function_decl);
f6db1481
RH
1672
1673 if (flag_new_regalloc)
1674 {
fd743bc1 1675 if (rest_of_handle_new_regalloc ())
f6db1481
RH
1676 goto exit_rest_of_compilation;
1677 }
1678 else
1679 {
fd743bc1 1680 if (rest_of_handle_old_regalloc ())
f6db1481
RH
1681 goto exit_rest_of_compilation;
1682 }
1683
1684 ggc_collect ();
1685
fd743bc1 1686 open_dump_file (DFI_postreload, current_function_decl);
f6db1481
RH
1687
1688 /* Do a very simple CSE pass over just the hard registers. */
1689 if (optimize > 0)
1690 {
1691 timevar_push (TV_RELOAD_CSE_REGS);
fd743bc1 1692 reload_cse_regs (get_insns ());
f6db1481
RH
1693 /* reload_cse_regs can eliminate potentially-trapping MEMs.
1694 Remove any EH edges associated with them. */
1695 if (flag_non_call_exceptions)
1696 purge_all_dead_edges (0);
1697 timevar_pop (TV_RELOAD_CSE_REGS);
1698 }
1699
fd743bc1 1700 close_dump_file (DFI_postreload, print_rtl_with_bb, get_insns ());
f6db1481 1701
f9957958 1702 if (optimize > 0 && flag_gcse_after_reload)
fd743bc1 1703 rest_of_handle_gcse2 ();
f9957958 1704
f6db1481
RH
1705 /* Re-create the death notes which were deleted during reload. */
1706 timevar_push (TV_FLOW2);
fd743bc1 1707 open_dump_file (DFI_flow2, current_function_decl);
f6db1481
RH
1708
1709#ifdef ENABLE_CHECKING
1710 verify_flow_info ();
1711#endif
1712
fd743bc1 1713 /* If optimizing, then go ahead and split get_insns () now. */
f6db1481
RH
1714#ifndef STACK_REGS
1715 if (optimize > 0)
1716#endif
1717 split_all_insns (0);
1718
1719 if (flag_branch_target_load_optimize)
1720 {
fd743bc1 1721 open_dump_file (DFI_branch_target_load, current_function_decl);
f6db1481 1722
827c06b6 1723 branch_target_load_optimize (/*after_prologue_epilogue_gen=*/false);
f6db1481 1724
fd743bc1 1725 close_dump_file (DFI_branch_target_load, print_rtl_with_bb, get_insns ());
f6db1481
RH
1726
1727 ggc_collect ();
1728 }
1729
1730 if (optimize)
1731 cleanup_cfg (CLEANUP_EXPENSIVE);
1732
1733 /* On some machines, the prologue and epilogue code, or parts thereof,
fd743bc1 1734 can be represented as RTL. Doing so lets us schedule get_insns () between
f6db1481
RH
1735 it and the rest of the code and also allows delayed branch
1736 scheduling to operate in the epilogue. */
fd743bc1 1737 thread_prologue_and_epilogue_insns (get_insns ());
f6db1481
RH
1738 epilogue_completed = 1;
1739
1740 if (optimize)
1741 {
827c06b6 1742 life_analysis (dump_file, PROP_POSTRELOAD);
f6db1481
RH
1743 cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_UPDATE_LIFE
1744 | (flag_crossjumping ? CLEANUP_CROSSJUMP : 0));
1745
1746 /* This is kind of a heuristic. We need to run combine_stack_adjustments
1747 even for machines with possibly nonzero RETURN_POPS_ARGS
1748 and ACCUMULATE_OUTGOING_ARGS. We expect that only ports having
1749 push instructions will have popping returns. */
1750#ifndef PUSH_ROUNDING
1751 if (!ACCUMULATE_OUTGOING_ARGS)
1752#endif
1753 combine_stack_adjustments ();
1754
1755 ggc_collect ();
1756 }
1757
1758 flow2_completed = 1;
1759
fd743bc1 1760 close_dump_file (DFI_flow2, print_rtl_with_bb, get_insns ());
f6db1481
RH
1761 timevar_pop (TV_FLOW2);
1762
1763#ifdef HAVE_peephole2
1764 if (optimize > 0 && flag_peephole2)
1765 {
1766 timevar_push (TV_PEEPHOLE2);
fd743bc1 1767 open_dump_file (DFI_peephole2, current_function_decl);
f6db1481
RH
1768
1769 peephole2_optimize (dump_file);
1770
fd743bc1 1771 close_dump_file (DFI_peephole2, print_rtl_with_bb, get_insns ());
f6db1481
RH
1772 timevar_pop (TV_PEEPHOLE2);
1773 }
1774#endif
1775
fd743bc1 1776 open_dump_file (DFI_ce3, current_function_decl);
f6db1481
RH
1777 if (optimize)
1778 /* Last attempt to optimize CFG, as scheduling, peepholing and insn
1779 splitting possibly introduced more crossjumping opportunities. */
1780 cleanup_cfg (CLEANUP_EXPENSIVE
1781 | CLEANUP_UPDATE_LIFE
1782 | (flag_crossjumping ? CLEANUP_CROSSJUMP : 0));
1783 if (flag_if_conversion2)
1784 {
1785 timevar_push (TV_IFCVT2);
1786
1787 if_convert (1);
1788
1789 timevar_pop (TV_IFCVT2);
1790 }
fd743bc1 1791 close_dump_file (DFI_ce3, print_rtl_with_bb, get_insns ());
f6db1481
RH
1792
1793 if (optimize > 0)
1794 {
1795 if (flag_rename_registers || flag_cprop_registers)
fd743bc1 1796 rest_of_handle_regrename ();
f6db1481 1797
fd743bc1 1798 rest_of_handle_reorder_blocks ();
f6db1481
RH
1799 }
1800
1801 if (flag_branch_target_load_optimize2)
1802 {
1803 /* Leave this a warning for now so that it is possible to experiment
1804 with running this pass twice. In 3.6, we should either make this
1805 an error, or use separate dump files. */
1806 if (flag_branch_target_load_optimize)
1807 warning ("branch target register load optimization is not intended "
1808 "to be run twice");
1809
fd743bc1 1810 open_dump_file (DFI_branch_target_load, current_function_decl);
f6db1481 1811
827c06b6 1812 branch_target_load_optimize (/*after_prologue_epilogue_gen=*/true);
f6db1481 1813
fd743bc1 1814 close_dump_file (DFI_branch_target_load, print_rtl_with_bb, get_insns ());
f6db1481
RH
1815
1816 ggc_collect ();
1817 }
1818
1819#ifdef INSN_SCHEDULING
1820 if (optimize > 0 && flag_schedule_insns_after_reload)
fd743bc1 1821 rest_of_handle_sched2 ();
f6db1481
RH
1822#endif
1823
1824#ifdef LEAF_REGISTERS
1825 current_function_uses_only_leaf_regs
1826 = optimize > 0 && only_leaf_regs_used () && leaf_function_p ();
1827#endif
1828
1829#ifdef STACK_REGS
fd743bc1 1830 rest_of_handle_stack_regs ();
f6db1481
RH
1831#endif
1832
1833 compute_alignments ();
1834
1835 if (flag_var_tracking)
fd743bc1 1836 rest_of_handle_variable_tracking ();
f6db1481
RH
1837
1838 /* CFG is no longer maintained up-to-date. */
1839 free_bb_for_insn ();
1840
1841 if (targetm.machine_dependent_reorg != 0)
fd743bc1 1842 rest_of_handle_machine_reorg ();
f6db1481 1843
fd743bc1 1844 purge_line_number_notes (get_insns ());
f6db1481
RH
1845 cleanup_barriers ();
1846
1847#ifdef DELAY_SLOTS
1848 if (optimize > 0 && flag_delayed_branch)
fd743bc1 1849 rest_of_handle_delay_slots ();
f6db1481
RH
1850#endif
1851
1852#if defined (HAVE_ATTR_length) && !defined (STACK_REGS)
1853 timevar_push (TV_SHORTEN_BRANCH);
1854 split_all_insns_noflow ();
1855 timevar_pop (TV_SHORTEN_BRANCH);
1856#endif
1857
1858 convert_to_eh_region_ranges ();
1859
1860 /* Shorten branches. */
1861 timevar_push (TV_SHORTEN_BRANCH);
1862 shorten_branches (get_insns ());
1863 timevar_pop (TV_SHORTEN_BRANCH);
1864
1865 set_nothrow_function_flags ();
1866 if (current_function_nothrow)
1867 /* Now we know that this can't throw; set the flag for the benefit
1868 of other functions later in this translation unit. */
1869 TREE_NOTHROW (current_function_decl) = 1;
1870
fd743bc1 1871 rest_of_handle_final ();
f6db1481
RH
1872
1873 /* Write DBX symbols if requested. */
1874
1875 /* Note that for those inline functions where we don't initially
1876 know for certain that we will be generating an out-of-line copy,
1877 the first invocation of this routine (rest_of_compilation) will
1878 skip over this code by doing a `goto exit_rest_of_compilation;'.
1879 Later on, wrapup_global_declarations will (indirectly) call
1880 rest_of_compilation again for those inline functions that need
1881 to have out-of-line copies generated. During that call, we
1882 *will* be routed past here. */
1883
1884 timevar_push (TV_SYMOUT);
fd743bc1 1885 (*debug_hooks->function_decl) (current_function_decl);
f6db1481
RH
1886 timevar_pop (TV_SYMOUT);
1887
1888 exit_rest_of_compilation:
1889
1890 coverage_end_function ();
1891
1892 /* In case the function was not output,
1893 don't leave any temporary anonymous types
1894 queued up for sdb output. */
1895#ifdef SDB_DEBUGGING_INFO
1896 if (write_symbols == SDB_DEBUG)
1897 sdbout_types (NULL_TREE);
1898#endif
1899
1900 reload_completed = 0;
1901 epilogue_completed = 0;
1902 flow2_completed = 0;
1903 no_new_pseudos = 0;
1904
1905 timevar_push (TV_FINAL);
1906
1907 /* Clear out the insn_length contents now that they are no
1908 longer valid. */
1909 init_insn_lengths ();
1910
1911 /* Show no temporary slots allocated. */
1912 init_temp_slots ();
1913
bb8a619e 1914 free_basic_block_vars ();
f6db1481
RH
1915 free_bb_for_insn ();
1916
1917 timevar_pop (TV_FINAL);
1918
5fd9b178 1919 if (targetm.binds_local_p (current_function_decl))
f6db1481
RH
1920 {
1921 int pref = cfun->preferred_stack_boundary;
1922 if (cfun->recursive_call_emit
1923 && cfun->stack_alignment_needed > cfun->preferred_stack_boundary)
1924 pref = cfun->stack_alignment_needed;
1925 cgraph_rtl_info (current_function_decl)->preferred_incoming_stack_boundary
1926 = pref;
1927 }
1928
1929 /* Make sure volatile mem refs aren't considered valid operands for
1930 arithmetic insns. We must call this here if this is a nested inline
1931 function, since the above code leaves us in the init_recog state
1932 (from final.c), and the function context push/pop code does not
1933 save/restore volatile_ok.
1934
1935 ??? Maybe it isn't necessary for expand_start_function to call this
1936 anymore if we do it here? */
1937
1938 init_recog_no_volatile ();
1939
1940 /* We're done with this function. Free up memory if we can. */
1941 free_after_parsing (cfun);
f6db1481
RH
1942}
1943
1944void
1945init_optimization_passes (void)
1946{
6868bb1c
JH
1947 open_dump_file (DFI_cgraph, NULL);
1948 cgraph_dump_file = dump_file;
1949 dump_file = NULL;
f6db1481
RH
1950}
1951
1952void
1953finish_optimization_passes (void)
1954{
1955 if (profile_arc_flag || flag_test_coverage || flag_branch_probabilities)
1956 {
1957 timevar_push (TV_DUMP);
1958 open_dump_file (DFI_bp, NULL);
1959
1960 end_branch_prob ();
1961
1962 close_dump_file (DFI_bp, NULL, NULL_RTX);
1963 timevar_pop (TV_DUMP);
1964 }
1965
1966 if (optimize > 0 && open_dump_file (DFI_combine, NULL))
1967 {
1968 timevar_push (TV_DUMP);
1969 dump_combine_total_stats (dump_file);
1970 close_dump_file (DFI_combine, NULL, NULL_RTX);
1971 timevar_pop (TV_DUMP);
1972 }
1973
6868bb1c
JH
1974 dump_file = cgraph_dump_file;
1975 cgraph_dump_file = NULL;
1976 close_dump_file (DFI_cgraph, NULL, NULL_RTX);
f6db1481
RH
1977
1978 /* Do whatever is necessary to finish printing the graphs. */
1979 if (graph_dump_format != no_graph)
1980 {
1981 int i;
1982
1983 for (i = 0; i < (int) DFI_MAX; ++i)
1984 if (dump_file_tbl[i].initialized && dump_file_tbl[i].graph_dump_p)
1985 {
1986 char seq[16];
1987 char *suffix;
1988
1989 sprintf (seq, DUMPFILE_FORMAT, i);
1990 suffix = concat (seq, dump_file_tbl[i].extension, NULL);
1991 finish_graph_dump_file (dump_base_name, suffix);
1992 free (suffix);
1993 }
1994 }
1995
1996}
1997
1998bool
1999enable_rtl_dump_file (int letter)
2000{
2001 bool matched = false;
2002 int i;
2003
2004 if (letter == 'a')
2005 {
2006 for (i = 0; i < (int) DFI_MAX; ++i)
2007 dump_file_tbl[i].enabled = 1;
2008 matched = true;
2009 }
2010 else
2011 {
2012 for (i = 0; i < (int) DFI_MAX; ++i)
2013 if (letter == dump_file_tbl[i].debug_switch)
2014 {
2015 dump_file_tbl[i].enabled = 1;
2016 matched = true;
2017 }
2018 }
2019
2020 return matched;
2021}
2f8e398b
PB
2022
2023struct tree_opt_pass pass_rest_of_compilation =
2024{
2025 "rest of compilation", /* name */
2026 NULL, /* gate */
2027 rest_of_compilation, /* execute */
2028 NULL, /* sub */
2029 NULL, /* next */
2030 0, /* static_pass_number */
2031 TV_REST_OF_COMPILATION, /* tv_id */
2032 PROP_rtl, /* properties_required */
2033 0, /* properties_provided */
2034 PROP_rtl, /* properties_destroyed */
2035 0, /* todo_flags_start */
2036 TODO_ggc_collect /* todo_flags_finish */
2037};
2038
2039
This page took 0.447895 seconds and 5 git commands to generate.