1 /* Basic IPA optimizations and utilities.
2 Copyright (C) 2003-2015 Free Software Foundation, Inc.
4 This file is part of GCC.
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 3, or (at your option) any later
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING3. If not see
18 <http://www.gnu.org/licenses/>. */
22 #include "coretypes.h"
27 #include "double-int.h"
35 #include "fold-const.h"
37 #include "stringpool.h"
39 #include "basic-block.h"
42 #include "plugin-api.h"
43 #include "hard-reg-set.h"
48 #include "tree-pass.h"
49 #include "gimple-expr.h"
53 #include "tree-iterator.h"
54 #include "ipa-utils.h"
55 #include "alloc-pool.h"
56 #include "symbol-summary.h"
58 #include "ipa-inline.h"
59 #include "tree-inline.h"
62 #include "internal-fn.h"
63 #include "tree-ssa-alias.h"
68 /* Return true when NODE has ADDR reference. */
71 has_addr_references_p (struct cgraph_node
*node
,
72 void *data ATTRIBUTE_UNUSED
)
75 struct ipa_ref
*ref
= NULL
;
77 for (i
= 0; node
->iterate_referring (i
, ref
); i
++)
78 if (ref
->use
== IPA_REF_ADDR
)
83 /* Look for all functions inlined to NODE and update their inlined_to pointers
87 update_inlined_to_pointer (struct cgraph_node
*node
, struct cgraph_node
*inlined_to
)
89 struct cgraph_edge
*e
;
90 for (e
= node
->callees
; e
; e
= e
->next_callee
)
91 if (e
->callee
->global
.inlined_to
)
93 e
->callee
->global
.inlined_to
= inlined_to
;
94 update_inlined_to_pointer (e
->callee
, inlined_to
);
98 /* Add symtab NODE to queue starting at FIRST.
100 The queue is linked via AUX pointers and terminated by pointer to 1.
101 We enqueue nodes at two occasions: when we find them reachable or when we find
102 their bodies needed for further clonning. In the second case we mark them
103 by pointer to 2 after processing so they are re-queue when they become
107 enqueue_node (symtab_node
*node
, symtab_node
**first
,
108 hash_set
<symtab_node
*> *reachable
)
110 /* Node is still in queue; do nothing. */
111 if (node
->aux
&& node
->aux
!= (void *) 2)
113 /* Node was already processed as unreachable, re-enqueue
114 only if it became reachable now. */
115 if (node
->aux
== (void *)2 && !reachable
->contains (node
))
121 /* Process references. */
124 process_references (symtab_node
*snode
,
126 bool before_inlining_p
,
127 hash_set
<symtab_node
*> *reachable
)
130 struct ipa_ref
*ref
= NULL
;
131 for (i
= 0; snode
->iterate_reference (i
, ref
); i
++)
133 symtab_node
*node
= ref
->referred
;
134 symtab_node
*body
= node
->ultimate_alias_target ();
136 if (node
->definition
&& !node
->in_other_partition
137 && ((!DECL_EXTERNAL (node
->decl
) || node
->alias
)
138 || (((before_inlining_p
139 && ((TREE_CODE (node
->decl
) != FUNCTION_DECL
141 || (TREE_CODE (node
->decl
) == FUNCTION_DECL
142 && opt_for_fn (body
->decl
, optimize
))
143 || (symtab
->state
< IPA_SSA
146 DECL_ATTRIBUTES (body
->decl
))))))
147 /* We use variable constructors during late compilation for
148 constant folding. Keep references alive so partitioning
149 knows about potential references. */
150 || (TREE_CODE (node
->decl
) == VAR_DECL
152 && ctor_for_folding (node
->decl
)
153 != error_mark_node
))))
155 /* Be sure that we will not optimize out alias target
157 if (DECL_EXTERNAL (node
->decl
)
159 && before_inlining_p
)
160 reachable
->add (body
);
161 reachable
->add (node
);
163 enqueue_node (node
, first
, reachable
);
167 /* EDGE is an polymorphic call. If BEFORE_INLINING_P is set, mark
168 all its potential targets as reachable to permit later inlining if
169 devirtualization happens. After inlining still keep their declarations
170 around, so we can devirtualize to a direct call.
172 Also try to make trivial devirutalization when no or only one target is
176 walk_polymorphic_call_targets (hash_set
<void *> *reachable_call_targets
,
177 struct cgraph_edge
*edge
,
179 hash_set
<symtab_node
*> *reachable
,
180 bool before_inlining_p
)
185 vec
<cgraph_node
*>targets
186 = possible_polymorphic_call_targets
187 (edge
, &final
, &cache_token
);
189 if (!reachable_call_targets
->add (cache_token
))
191 for (i
= 0; i
< targets
.length (); i
++)
193 struct cgraph_node
*n
= targets
[i
];
195 /* Do not bother to mark virtual methods in anonymous namespace;
196 either we will find use of virtual table defining it, or it is
198 if (TREE_CODE (TREE_TYPE (n
->decl
)) == METHOD_TYPE
199 && type_in_anonymous_namespace_p
200 (method_class_type (TREE_TYPE (n
->decl
))))
203 symtab_node
*body
= n
->function_symbol ();
205 /* Prior inlining, keep alive bodies of possible targets for
208 && (before_inlining_p
209 && opt_for_fn (body
->decl
, optimize
)
210 && opt_for_fn (body
->decl
, flag_devirtualize
)))
212 /* Be sure that we will not optimize out alias target
214 if (DECL_EXTERNAL (n
->decl
)
216 && before_inlining_p
)
217 reachable
->add (body
);
220 /* Even after inlining we want to keep the possible targets in the
221 boundary, so late passes can still produce direct call even if
222 the chance for inlining is lost. */
223 enqueue_node (n
, first
, reachable
);
227 /* Very trivial devirtualization; when the type is
228 final or anonymous (so we know all its derivation)
229 and there is only one possible virtual call target,
230 make the edge direct. */
233 if (targets
.length () <= 1 && dbg_cnt (devirt
))
235 cgraph_node
*target
, *node
= edge
->caller
;
236 if (targets
.length () == 1)
239 target
= cgraph_node::get_create
240 (builtin_decl_implicit (BUILT_IN_UNREACHABLE
));
242 if (dump_enabled_p ())
246 locus
= gimple_location (edge
->call_stmt
);
248 locus
= UNKNOWN_LOCATION
;
249 dump_printf_loc (MSG_OPTIMIZED_LOCATIONS
, locus
,
250 "devirtualizing call in %s/%i to %s/%i\n",
251 edge
->caller
->name (), edge
->caller
->order
,
255 edge
= edge
->make_direct (target
);
256 if (inline_summaries
)
257 inline_update_overall_summary (node
);
258 else if (edge
->call_stmt
)
260 edge
->redirect_call_stmt_to_callee ();
262 /* Call to __builtin_unreachable shouldn't be instrumented. */
263 if (!targets
.length ())
264 gimple_call_set_with_bounds (edge
->call_stmt
, false);
270 /* Perform reachability analysis and reclaim all unreachable nodes.
272 The algorithm is basically mark&sweep but with some extra refinements:
274 - reachable extern inline functions needs special handling; the bodies needs
275 to stay in memory until inlining in hope that they will be inlined.
276 After inlining we release their bodies and turn them into unanalyzed
277 nodes even when they are reachable.
279 - virtual functions are kept in callgraph even if they seem unreachable in
280 hope calls to them will be devirtualized.
282 Again we remove them after inlining. In late optimization some
283 devirtualization may happen, but it is not important since we won't inline
284 the call. In theory early opts and IPA should work out all important cases.
286 - virtual clones needs bodies of their origins for later materialization;
287 this means that we want to keep the body even if the origin is unreachable
288 otherwise. To avoid origin from sitting in the callgraph and being
289 walked by IPA passes, we turn them into unanalyzed nodes with body
292 We maintain set of function declaration where body needs to stay in
293 body_needed_for_clonning
295 Inline clones represent special case: their declaration match the
296 declaration of origin and cgraph_remove_node already knows how to
297 reshape callgraph and preserve body when offline copy of function or
298 inline clone is being removed.
300 - C++ virtual tables keyed to other unit are represented as DECL_EXTERNAL
301 variables with DECL_INITIAL set. We finalize these and keep reachable
302 ones around for constant folding purposes. After inlining we however
303 stop walking their references to let everything static referneced by them
304 to be removed when it is otherwise unreachable.
306 We maintain queue of both reachable symbols (i.e. defined symbols that needs
307 to stay) and symbols that are in boundary (i.e. external symbols referenced
308 by reachable symbols or origins of clones). The queue is represented
309 as linked list by AUX pointer terminated by 1.
311 At the end we keep all reachable symbols. For symbols in boundary we always
312 turn definition into a declaration, but we may keep function body around
313 based on body_needed_for_clonning
315 All symbols that enter the queue have AUX pointer non-zero and are in the
316 boundary. Pointer set REACHABLE is used to track reachable symbols.
318 Every symbol can be visited twice - once as part of boundary and once
319 as real reachable symbol. enqueue_node needs to decide whether the
320 node needs to be re-queued for second processing. For this purpose
321 we set AUX pointer of processed symbols in the boundary to constant 2. */
324 symbol_table::remove_unreachable_nodes (FILE *file
)
326 symtab_node
*first
= (symtab_node
*) (void *) 1;
327 struct cgraph_node
*node
, *next
;
328 varpool_node
*vnode
, *vnext
;
329 bool changed
= false;
330 hash_set
<symtab_node
*> reachable
;
331 hash_set
<tree
> body_needed_for_clonning
;
332 hash_set
<void *> reachable_call_targets
;
333 bool before_inlining_p
= symtab
->state
< (!optimize
? IPA_SSA
334 : IPA_SSA_AFTER_INLINING
);
336 timevar_push (TV_IPA_UNREACHABLE
);
337 build_type_inheritance_graph ();
339 fprintf (file
, "\nReclaiming functions:");
340 #ifdef ENABLE_CHECKING
341 FOR_EACH_FUNCTION (node
)
342 gcc_assert (!node
->aux
);
343 FOR_EACH_VARIABLE (vnode
)
344 gcc_assert (!vnode
->aux
);
346 /* Mark functions whose bodies are obviously needed.
347 This is mostly when they can be referenced externally. Inline clones
348 are special since their declarations are shared with master clone and thus
349 cgraph_can_remove_if_no_direct_calls_and_refs_p should not be called on them. */
350 FOR_EACH_FUNCTION (node
)
352 node
->used_as_abstract_origin
= false;
354 && !node
->global
.inlined_to
355 && !node
->in_other_partition
356 && !node
->can_remove_if_no_direct_calls_and_refs_p ())
358 gcc_assert (!node
->global
.inlined_to
);
359 reachable
.add (node
);
360 enqueue_node (node
, &first
, &reachable
);
363 gcc_assert (!node
->aux
);
366 /* Mark variables that are obviously needed. */
367 FOR_EACH_DEFINED_VARIABLE (vnode
)
368 if (!vnode
->can_remove_if_no_refs_p()
369 && !vnode
->in_other_partition
)
371 reachable
.add (vnode
);
372 enqueue_node (vnode
, &first
, &reachable
);
375 /* Perform reachability analysis. */
376 while (first
!= (symtab_node
*) (void *) 1)
378 bool in_boundary_p
= !reachable
.contains (first
);
379 symtab_node
*node
= first
;
381 first
= (symtab_node
*)first
->aux
;
383 /* If we are processing symbol in boundary, mark its AUX pointer for
384 possible later re-processing in enqueue_node. */
386 node
->aux
= (void *)2;
389 if (TREE_CODE (node
->decl
) == FUNCTION_DECL
390 && DECL_ABSTRACT_ORIGIN (node
->decl
))
392 struct cgraph_node
*origin_node
393 = cgraph_node::get (DECL_ABSTRACT_ORIGIN (node
->decl
));
394 if (origin_node
&& !origin_node
->used_as_abstract_origin
)
396 origin_node
->used_as_abstract_origin
= true;
397 gcc_assert (!origin_node
->prev_sibling_clone
);
398 gcc_assert (!origin_node
->next_sibling_clone
);
399 for (cgraph_node
*n
= origin_node
->clones
; n
;
400 n
= n
->next_sibling_clone
)
401 if (n
->decl
== DECL_ABSTRACT_ORIGIN (node
->decl
))
402 n
->used_as_abstract_origin
= true;
405 /* If any symbol in a comdat group is reachable, force
406 all externally visible symbols in the same comdat
407 group to be reachable as well. Comdat-local symbols
408 can be discarded if all uses were inlined. */
409 if (node
->same_comdat_group
)
412 for (next
= node
->same_comdat_group
;
414 next
= next
->same_comdat_group
)
415 if (!next
->comdat_local_p ()
416 && !reachable
.add (next
))
417 enqueue_node (next
, &first
, &reachable
);
419 /* Mark references as reachable. */
420 process_references (node
, &first
, before_inlining_p
, &reachable
);
423 if (cgraph_node
*cnode
= dyn_cast
<cgraph_node
*> (node
))
425 /* Mark the callees reachable unless they are direct calls to extern
426 inline functions we decided to not inline. */
429 struct cgraph_edge
*e
;
430 /* Keep alive possible targets for devirtualization. */
431 if (opt_for_fn (cnode
->decl
, optimize
)
432 && opt_for_fn (cnode
->decl
, flag_devirtualize
))
434 struct cgraph_edge
*next
;
435 for (e
= cnode
->indirect_calls
; e
; e
= next
)
437 next
= e
->next_callee
;
438 if (e
->indirect_info
->polymorphic
)
439 walk_polymorphic_call_targets (&reachable_call_targets
,
440 e
, &first
, &reachable
,
444 for (e
= cnode
->callees
; e
; e
= e
->next_callee
)
446 symtab_node
*body
= e
->callee
->function_symbol ();
447 if (e
->callee
->definition
448 && !e
->callee
->in_other_partition
449 && (!e
->inline_failed
450 || !DECL_EXTERNAL (e
->callee
->decl
)
452 || (before_inlining_p
453 && (opt_for_fn (body
->decl
, optimize
)
454 || (symtab
->state
< IPA_SSA
457 DECL_ATTRIBUTES (body
->decl
)))))))
459 /* Be sure that we will not optimize out alias target
461 if (DECL_EXTERNAL (e
->callee
->decl
)
463 && before_inlining_p
)
464 reachable
.add (body
);
465 reachable
.add (e
->callee
);
467 enqueue_node (e
->callee
, &first
, &reachable
);
470 /* When inline clone exists, mark body to be preserved so when removing
471 offline copy of the function we don't kill it. */
472 if (cnode
->global
.inlined_to
)
473 body_needed_for_clonning
.add (cnode
->decl
);
475 /* For non-inline clones, force their origins to the boundary and ensure
476 that body is not removed. */
477 while (cnode
->clone_of
)
479 bool noninline
= cnode
->clone_of
->decl
!= cnode
->decl
;
480 cnode
= cnode
->clone_of
;
483 body_needed_for_clonning
.add (cnode
->decl
);
484 enqueue_node (cnode
, &first
, &reachable
);
489 /* If any reachable function has simd clones, mark them as
490 reachable as well. */
491 if (cnode
->simd_clones
)
494 for (next
= cnode
->simd_clones
;
496 next
= next
->simdclone
->next_clone
)
498 || !reachable
.add (next
))
499 enqueue_node (next
, &first
, &reachable
);
502 /* When we see constructor of external variable, keep referred nodes in the
503 boundary. This will also hold initializers of the external vars NODE
505 varpool_node
*vnode
= dyn_cast
<varpool_node
*> (node
);
507 && DECL_EXTERNAL (node
->decl
)
511 struct ipa_ref
*ref
= NULL
;
512 for (int i
= 0; node
->iterate_reference (i
, ref
); i
++)
513 enqueue_node (ref
->referred
, &first
, &reachable
);
517 /* Remove unreachable functions. */
518 for (node
= first_function (); node
; node
= next
)
520 next
= next_function (node
);
522 /* If node is not needed at all, remove it. */
526 fprintf (file
, " %s/%i", node
->name (), node
->order
);
530 /* If node is unreachable, remove its body. */
531 else if (!reachable
.contains (node
))
533 if (!body_needed_for_clonning
.contains (node
->decl
))
534 node
->release_body ();
535 else if (!node
->clone_of
)
536 gcc_assert (in_lto_p
|| DECL_RESULT (node
->decl
));
537 if (node
->definition
)
540 fprintf (file
, " %s/%i", node
->name (), node
->order
);
541 node
->body_removed
= true;
542 node
->analyzed
= false;
543 node
->definition
= false;
544 node
->cpp_implicit_alias
= false;
546 node
->thunk
.thunk_p
= false;
547 node
->weakref
= false;
548 /* After early inlining we drop always_inline attributes on
549 bodies of functions that are still referenced (have their
551 DECL_ATTRIBUTES (node
->decl
)
552 = remove_attribute ("always_inline",
553 DECL_ATTRIBUTES (node
->decl
));
554 if (!node
->in_other_partition
)
555 node
->local
.local
= false;
556 node
->remove_callees ();
557 node
->remove_from_same_comdat_group ();
558 node
->remove_all_references ();
560 if (node
->thunk
.thunk_p
561 && node
->thunk
.add_pointer_bounds_args
)
563 node
->thunk
.thunk_p
= false;
564 node
->thunk
.add_pointer_bounds_args
= false;
569 gcc_assert (node
->clone_of
|| !node
->has_gimple_body_p ()
570 || in_lto_p
|| DECL_RESULT (node
->decl
));
573 /* Inline clones might be kept around so their materializing allows further
574 cloning. If the function the clone is inlined into is removed, we need
575 to turn it into normal cone. */
576 FOR_EACH_FUNCTION (node
)
578 if (node
->global
.inlined_to
581 gcc_assert (node
->clones
);
582 node
->global
.inlined_to
= NULL
;
583 update_inlined_to_pointer (node
, node
);
588 /* Remove unreachable variables. */
590 fprintf (file
, "\nReclaiming variables:");
591 for (vnode
= first_variable (); vnode
; vnode
= vnext
)
593 vnext
= next_variable (vnode
);
595 /* For can_refer_decl_in_current_unit_p we want to track for
596 all external variables if they are defined in other partition
598 && (!flag_ltrans
|| !DECL_EXTERNAL (vnode
->decl
)))
601 fprintf (file
, " %s/%i", vnode
->name (), vnode
->order
);
605 else if (!reachable
.contains (vnode
))
608 if (vnode
->definition
)
611 fprintf (file
, " %s", vnode
->name ());
614 /* Keep body if it may be useful for constant folding. */
615 if ((init
= ctor_for_folding (vnode
->decl
)) == error_mark_node
616 && !POINTER_BOUNDS_P (vnode
->decl
))
617 vnode
->remove_initializer ();
619 DECL_INITIAL (vnode
->decl
) = init
;
620 vnode
->body_removed
= true;
621 vnode
->definition
= false;
622 vnode
->analyzed
= false;
625 vnode
->remove_from_same_comdat_group ();
627 vnode
->remove_all_references ();
633 /* Now update address_taken flags and try to promote functions to be local. */
635 fprintf (file
, "\nClearing address taken flags:");
636 FOR_EACH_DEFINED_FUNCTION (node
)
637 if (node
->address_taken
638 && !node
->used_from_other_partition
)
640 if (!node
->call_for_symbol_thunks_and_aliases
641 (has_addr_references_p
, NULL
, true)
642 && (!node
->instrumentation_clone
643 || !node
->instrumented_version
644 || !node
->instrumented_version
->address_taken
))
647 fprintf (file
, " %s", node
->name ());
648 node
->address_taken
= false;
650 if (node
->local_p ())
652 node
->local
.local
= true;
654 fprintf (file
, " (local)");
659 fprintf (file
, "\n");
661 #ifdef ENABLE_CHECKING
662 symtab_node::verify_symtab_nodes ();
665 /* If we removed something, perhaps profile could be improved. */
666 if (changed
&& optimize
&& inline_edge_summary_vec
.exists ())
667 FOR_EACH_DEFINED_FUNCTION (node
)
668 ipa_propagate_frequency (node
);
670 timevar_pop (TV_IPA_UNREACHABLE
);
674 /* Process references to VNODE and set flags WRITTEN, ADDRESS_TAKEN, READ
675 as needed, also clear EXPLICIT_REFS if the references to given variable
676 do not need to be explicit. */
679 process_references (varpool_node
*vnode
,
680 bool *written
, bool *address_taken
,
681 bool *read
, bool *explicit_refs
)
686 if (!vnode
->all_refs_explicit_p ()
687 || TREE_THIS_VOLATILE (vnode
->decl
))
688 *explicit_refs
= false;
690 for (i
= 0; vnode
->iterate_referring (i
, ref
)
691 && *explicit_refs
&& (!*written
|| !*address_taken
|| !*read
); i
++)
695 *address_taken
= true;
704 process_references (dyn_cast
<varpool_node
*> (ref
->referring
), written
,
705 address_taken
, read
, explicit_refs
);
712 /* Set TREE_READONLY bit. */
715 set_readonly_bit (varpool_node
*vnode
, void *data ATTRIBUTE_UNUSED
)
717 TREE_READONLY (vnode
->decl
) = true;
721 /* Set writeonly bit and clear the initalizer, since it will not be needed. */
724 set_writeonly_bit (varpool_node
*vnode
, void *data
)
726 vnode
->writeonly
= true;
729 DECL_INITIAL (vnode
->decl
) = NULL
;
732 if (vnode
->num_references ())
733 *(bool *)data
= true;
734 vnode
->remove_all_references ();
740 /* Clear addressale bit of VNODE. */
743 clear_addressable_bit (varpool_node
*vnode
, void *data ATTRIBUTE_UNUSED
)
745 vnode
->address_taken
= false;
746 TREE_ADDRESSABLE (vnode
->decl
) = 0;
750 /* Discover variables that have no longer address taken or that are read only
751 and update their flags.
753 Return true when unreachable symbol removan should be done.
755 FIXME: This can not be done in between gimplify and omp_expand since
756 readonly flag plays role on what is shared and what is not. Currently we do
757 this transformation as part of whole program visibility and re-do at
758 ipa-reference pass (to take into account clonning), but it would
759 make sense to do it before early optimizations. */
762 ipa_discover_readonly_nonaddressable_vars (void)
764 bool remove_p
= false;
767 fprintf (dump_file
, "Clearing variable flags:");
768 FOR_EACH_VARIABLE (vnode
)
770 && (TREE_ADDRESSABLE (vnode
->decl
)
772 || !TREE_READONLY (vnode
->decl
)))
774 bool written
= false;
775 bool address_taken
= false;
777 bool explicit_refs
= true;
779 process_references (vnode
, &written
, &address_taken
, &read
,
785 if (TREE_ADDRESSABLE (vnode
->decl
) && dump_file
)
786 fprintf (dump_file
, " %s (non-addressable)", vnode
->name ());
787 vnode
->call_for_node_and_aliases (clear_addressable_bit
, NULL
,
790 if (!address_taken
&& !written
791 /* Making variable in explicit section readonly can cause section
793 See e.g. gcc.c-torture/compile/pr23237.c */
794 && vnode
->get_section () == NULL
)
796 if (!TREE_READONLY (vnode
->decl
) && dump_file
)
797 fprintf (dump_file
, " %s (read-only)", vnode
->name ());
798 vnode
->call_for_node_and_aliases (set_readonly_bit
, NULL
, true);
800 if (!vnode
->writeonly
&& !read
&& !address_taken
&& written
)
803 fprintf (dump_file
, " %s (write-only)", vnode
->name ());
804 vnode
->call_for_node_and_aliases (set_writeonly_bit
, &remove_p
,
809 fprintf (dump_file
, "\n");
813 /* Free inline summary. */
817 const pass_data pass_data_ipa_free_inline_summary
=
819 SIMPLE_IPA_PASS
, /* type */
820 "free-inline-summary", /* name */
821 OPTGROUP_NONE
, /* optinfo_flags */
822 TV_IPA_FREE_INLINE_SUMMARY
, /* tv_id */
823 0, /* properties_required */
824 0, /* properties_provided */
825 0, /* properties_destroyed */
826 0, /* todo_flags_start */
827 /* Early optimizations may make function unreachable. We can not
828 remove unreachable functions as part of the ealry opts pass because
829 TODOs are run before subpasses. Do it here. */
830 ( TODO_remove_functions
| TODO_dump_symtab
), /* todo_flags_finish */
833 class pass_ipa_free_inline_summary
: public simple_ipa_opt_pass
836 pass_ipa_free_inline_summary (gcc::context
*ctxt
)
837 : simple_ipa_opt_pass (pass_data_ipa_free_inline_summary
, ctxt
)
840 /* opt_pass methods: */
841 virtual unsigned int execute (function
*)
843 inline_free_summary ();
847 }; // class pass_ipa_free_inline_summary
851 simple_ipa_opt_pass
*
852 make_pass_ipa_free_inline_summary (gcc::context
*ctxt
)
854 return new pass_ipa_free_inline_summary (ctxt
);
857 /* Generate and emit a static constructor or destructor. WHICH must
858 be one of 'I' (for a constructor), 'D' (for a destructor), 'P'
859 (for chp static vars constructor) or 'B' (for chkp static bounds
860 constructor). BODY is a STATEMENT_LIST containing GENERIC
861 statements. PRIORITY is the initialization priority for this
862 constructor or destructor.
864 FINAL specify whether the externally visible name for collect2 should
868 cgraph_build_static_cdtor_1 (char which
, tree body
, int priority
, bool final
)
870 static int counter
= 0;
872 tree decl
, name
, resdecl
;
874 /* The priority is encoded in the constructor or destructor name.
875 collect2 will sort the names and arrange that they are called at
878 sprintf (which_buf
, "%c_%.5d_%d", which
, priority
, counter
++);
880 /* Proudce sane name but one not recognizable by collect2, just for the
881 case we fail to inline the function. */
882 sprintf (which_buf
, "sub_%c_%.5d_%d", which
, priority
, counter
++);
883 name
= get_file_function_name (which_buf
);
885 decl
= build_decl (input_location
, FUNCTION_DECL
, name
,
886 build_function_type_list (void_type_node
, NULL_TREE
));
887 current_function_decl
= decl
;
889 resdecl
= build_decl (input_location
,
890 RESULT_DECL
, NULL_TREE
, void_type_node
);
891 DECL_ARTIFICIAL (resdecl
) = 1;
892 DECL_RESULT (decl
) = resdecl
;
893 DECL_CONTEXT (resdecl
) = decl
;
895 allocate_struct_function (decl
, false);
897 TREE_STATIC (decl
) = 1;
898 TREE_USED (decl
) = 1;
899 DECL_ARTIFICIAL (decl
) = 1;
900 DECL_NO_INSTRUMENT_FUNCTION_ENTRY_EXIT (decl
) = 1;
901 DECL_SAVED_TREE (decl
) = body
;
902 if (!targetm
.have_ctors_dtors
&& final
)
904 TREE_PUBLIC (decl
) = 1;
905 DECL_PRESERVE_P (decl
) = 1;
907 DECL_UNINLINABLE (decl
) = 1;
909 DECL_INITIAL (decl
) = make_node (BLOCK
);
910 TREE_USED (DECL_INITIAL (decl
)) = 1;
912 DECL_SOURCE_LOCATION (decl
) = input_location
;
913 cfun
->function_end_locus
= input_location
;
918 DECL_STATIC_CONSTRUCTOR (decl
) = 1;
919 decl_init_priority_insert (decl
, priority
);
922 DECL_STATIC_CONSTRUCTOR (decl
) = 1;
923 DECL_ATTRIBUTES (decl
) = tree_cons (get_identifier ("chkp ctor"),
926 decl_init_priority_insert (decl
, priority
);
929 DECL_STATIC_CONSTRUCTOR (decl
) = 1;
930 DECL_ATTRIBUTES (decl
) = tree_cons (get_identifier ("bnd_legacy"),
933 decl_init_priority_insert (decl
, priority
);
936 DECL_STATIC_DESTRUCTOR (decl
) = 1;
937 decl_fini_priority_insert (decl
, priority
);
943 gimplify_function_tree (decl
);
945 cgraph_node::add_new_function (decl
, false);
948 current_function_decl
= NULL
;
951 /* Generate and emit a static constructor or destructor. WHICH must
952 be one of 'I' (for a constructor), 'D' (for a destructor), 'P'
953 (for chkp static vars constructor) or 'B' (for chkp static bounds
954 constructor). BODY is a STATEMENT_LIST containing GENERIC
955 statements. PRIORITY is the initialization priority for this
956 constructor or destructor. */
959 cgraph_build_static_cdtor (char which
, tree body
, int priority
)
961 cgraph_build_static_cdtor_1 (which
, body
, priority
, false);
964 /* A vector of FUNCTION_DECLs declared as static constructors. */
965 static vec
<tree
> static_ctors
;
966 /* A vector of FUNCTION_DECLs declared as static destructors. */
967 static vec
<tree
> static_dtors
;
969 /* When target does not have ctors and dtors, we call all constructor
970 and destructor by special initialization/destruction function
971 recognized by collect2.
973 When we are going to build this function, collect all constructors and
974 destructors and turn them into normal functions. */
977 record_cdtor_fn (struct cgraph_node
*node
)
979 if (DECL_STATIC_CONSTRUCTOR (node
->decl
))
980 static_ctors
.safe_push (node
->decl
);
981 if (DECL_STATIC_DESTRUCTOR (node
->decl
))
982 static_dtors
.safe_push (node
->decl
);
983 node
= cgraph_node::get (node
->decl
);
984 DECL_DISREGARD_INLINE_LIMITS (node
->decl
) = 1;
987 /* Define global constructors/destructor functions for the CDTORS, of
988 which they are LEN. The CDTORS are sorted by initialization
989 priority. If CTOR_P is true, these are constructors; otherwise,
990 they are destructors. */
993 build_cdtor (bool ctor_p
, vec
<tree
> cdtors
)
996 size_t len
= cdtors
.length ();
1003 priority_type priority
;
1012 p
= ctor_p
? DECL_INIT_PRIORITY (fn
) : DECL_FINI_PRIORITY (fn
);
1015 else if (p
!= priority
)
1021 /* When there is only one cdtor and target supports them, do nothing. */
1023 && targetm
.have_ctors_dtors
)
1028 /* Find the next batch of constructors/destructors with the same
1029 initialization priority. */
1034 call
= build_call_expr (fn
, 0);
1036 DECL_STATIC_CONSTRUCTOR (fn
) = 0;
1038 DECL_STATIC_DESTRUCTOR (fn
) = 0;
1039 /* We do not want to optimize away pure/const calls here.
1040 When optimizing, these should be already removed, when not
1041 optimizing, we want user to be able to breakpoint in them. */
1042 TREE_SIDE_EFFECTS (call
) = 1;
1043 append_to_statement_list (call
, &body
);
1045 gcc_assert (body
!= NULL_TREE
);
1046 /* Generate a function to call all the function of like
1048 cgraph_build_static_cdtor_1 (ctor_p
? 'I' : 'D', body
, priority
, true);
1052 /* Comparison function for qsort. P1 and P2 are actually of type
1053 "tree *" and point to static constructors. DECL_INIT_PRIORITY is
1054 used to determine the sort order. */
1057 compare_ctor (const void *p1
, const void *p2
)
1064 f1
= *(const tree
*)p1
;
1065 f2
= *(const tree
*)p2
;
1066 priority1
= DECL_INIT_PRIORITY (f1
);
1067 priority2
= DECL_INIT_PRIORITY (f2
);
1069 if (priority1
< priority2
)
1071 else if (priority1
> priority2
)
1074 /* Ensure a stable sort. Constructors are executed in backwarding
1075 order to make LTO initialize braries first. */
1076 return DECL_UID (f2
) - DECL_UID (f1
);
1079 /* Comparison function for qsort. P1 and P2 are actually of type
1080 "tree *" and point to static destructors. DECL_FINI_PRIORITY is
1081 used to determine the sort order. */
1084 compare_dtor (const void *p1
, const void *p2
)
1091 f1
= *(const tree
*)p1
;
1092 f2
= *(const tree
*)p2
;
1093 priority1
= DECL_FINI_PRIORITY (f1
);
1094 priority2
= DECL_FINI_PRIORITY (f2
);
1096 if (priority1
< priority2
)
1098 else if (priority1
> priority2
)
1101 /* Ensure a stable sort. */
1102 return DECL_UID (f1
) - DECL_UID (f2
);
1105 /* Generate functions to call static constructors and destructors
1106 for targets that do not support .ctors/.dtors sections. These
1107 functions have magic names which are detected by collect2. */
1110 build_cdtor_fns (void)
1112 if (!static_ctors
.is_empty ())
1114 gcc_assert (!targetm
.have_ctors_dtors
|| in_lto_p
);
1115 static_ctors
.qsort (compare_ctor
);
1116 build_cdtor (/*ctor_p=*/true, static_ctors
);
1119 if (!static_dtors
.is_empty ())
1121 gcc_assert (!targetm
.have_ctors_dtors
|| in_lto_p
);
1122 static_dtors
.qsort (compare_dtor
);
1123 build_cdtor (/*ctor_p=*/false, static_dtors
);
1127 /* Look for constructors and destructors and produce function calling them.
1128 This is needed for targets not supporting ctors or dtors, but we perform the
1129 transformation also at linktime to merge possibly numerous
1130 constructors/destructors into single function to improve code locality and
1134 ipa_cdtor_merge (void)
1136 struct cgraph_node
*node
;
1137 FOR_EACH_DEFINED_FUNCTION (node
)
1138 if (DECL_STATIC_CONSTRUCTOR (node
->decl
)
1139 || DECL_STATIC_DESTRUCTOR (node
->decl
))
1140 record_cdtor_fn (node
);
1142 static_ctors
.release ();
1143 static_dtors
.release ();
1149 const pass_data pass_data_ipa_cdtor_merge
=
1151 IPA_PASS
, /* type */
1153 OPTGROUP_NONE
, /* optinfo_flags */
1154 TV_CGRAPHOPT
, /* tv_id */
1155 0, /* properties_required */
1156 0, /* properties_provided */
1157 0, /* properties_destroyed */
1158 0, /* todo_flags_start */
1159 0, /* todo_flags_finish */
1162 class pass_ipa_cdtor_merge
: public ipa_opt_pass_d
1165 pass_ipa_cdtor_merge (gcc::context
*ctxt
)
1166 : ipa_opt_pass_d (pass_data_ipa_cdtor_merge
, ctxt
,
1167 NULL
, /* generate_summary */
1168 NULL
, /* write_summary */
1169 NULL
, /* read_summary */
1170 NULL
, /* write_optimization_summary */
1171 NULL
, /* read_optimization_summary */
1172 NULL
, /* stmt_fixup */
1173 0, /* function_transform_todo_flags_start */
1174 NULL
, /* function_transform */
1175 NULL
) /* variable_transform */
1178 /* opt_pass methods: */
1179 virtual bool gate (function
*);
1180 virtual unsigned int execute (function
*) { return ipa_cdtor_merge (); }
1182 }; // class pass_ipa_cdtor_merge
1185 pass_ipa_cdtor_merge::gate (function
*)
1187 /* Perform the pass when we have no ctors/dtors support
1188 or at LTO time to merge multiple constructors into single
1190 return !targetm
.have_ctors_dtors
|| (optimize
&& in_lto_p
);
1196 make_pass_ipa_cdtor_merge (gcc::context
*ctxt
)
1198 return new pass_ipa_cdtor_merge (ctxt
);
1201 /* Invalid pointer representing BOTTOM for single user dataflow. */
1202 #define BOTTOM ((cgraph_node *)(size_t) 2)
1204 /* Meet operation for single user dataflow.
1205 Here we want to associate variables with sigle function that may access it.
1207 FUNCTION is current single user of a variable, VAR is variable that uses it.
1208 Latttice is stored in SINGLE_USER_MAP.
1211 - TOP by no entry in SIGNLE_USER_MAP
1212 - BOTTOM by BOTTOM in AUX pointer (to save lookups)
1213 - known single user by cgraph pointer in SINGLE_USER_MAP. */
1216 meet (cgraph_node
*function
, varpool_node
*var
,
1217 hash_map
<varpool_node
*, cgraph_node
*> &single_user_map
)
1219 struct cgraph_node
*user
, **f
;
1221 if (var
->aux
== BOTTOM
)
1224 f
= single_user_map
.get (var
);
1230 else if (function
!= user
)
1236 /* Propagation step of single-use dataflow.
1238 Check all uses of VNODE and see if they are used by single function FUNCTION.
1239 SINGLE_USER_MAP represents the dataflow lattice. */
1242 propagate_single_user (varpool_node
*vnode
, cgraph_node
*function
,
1243 hash_map
<varpool_node
*, cgraph_node
*> &single_user_map
)
1246 struct ipa_ref
*ref
;
1248 gcc_assert (!vnode
->externally_visible
);
1250 /* If node is an alias, first meet with its target. */
1252 function
= meet (function
, vnode
->get_alias_target (), single_user_map
);
1254 /* Check all users and see if they correspond to a single function. */
1255 for (i
= 0; vnode
->iterate_referring (i
, ref
) && function
!= BOTTOM
; i
++)
1257 struct cgraph_node
*cnode
= dyn_cast
<cgraph_node
*> (ref
->referring
);
1260 if (cnode
->global
.inlined_to
)
1261 cnode
= cnode
->global
.inlined_to
;
1264 else if (function
!= cnode
)
1268 function
= meet (function
, dyn_cast
<varpool_node
*> (ref
->referring
),
1274 /* Pass setting used_by_single_function flag.
1275 This flag is set on variable when there is only one function that may
1276 possibly referr to it. */
1279 ipa_single_use (void)
1281 varpool_node
*first
= (varpool_node
*) (void *) 1;
1283 hash_map
<varpool_node
*, cgraph_node
*> single_user_map
;
1285 FOR_EACH_DEFINED_VARIABLE (var
)
1286 if (!var
->all_refs_explicit_p ())
1290 /* Enqueue symbol for dataflow. */
1295 /* The actual dataflow. */
1297 while (first
!= (void *) 1)
1299 cgraph_node
*user
, *orig_user
, **f
;
1302 first
= (varpool_node
*)first
->aux
;
1304 f
= single_user_map
.get (var
);
1309 user
= propagate_single_user (var
, orig_user
, single_user_map
);
1311 gcc_checking_assert (var
->aux
!= BOTTOM
);
1313 /* If user differs, enqueue all references. */
1314 if (user
!= orig_user
)
1319 single_user_map
.put (var
, user
);
1321 /* Enqueue all aliases for re-processing. */
1322 for (i
= 0; var
->iterate_referring (i
, ref
); i
++)
1323 if (ref
->use
== IPA_REF_ALIAS
1324 && !ref
->referring
->aux
)
1326 ref
->referring
->aux
= first
;
1327 first
= dyn_cast
<varpool_node
*> (ref
->referring
);
1329 /* Enqueue all users for re-processing. */
1330 for (i
= 0; var
->iterate_reference (i
, ref
); i
++)
1331 if (!ref
->referred
->aux
1332 && ref
->referred
->definition
1333 && is_a
<varpool_node
*> (ref
->referred
))
1335 ref
->referred
->aux
= first
;
1336 first
= dyn_cast
<varpool_node
*> (ref
->referred
);
1339 /* If user is BOTTOM, just punt on this var. */
1349 FOR_EACH_DEFINED_VARIABLE (var
)
1351 if (var
->aux
!= BOTTOM
)
1353 #ifdef ENABLE_CHECKING
1354 /* Not having the single user known means that the VAR is
1355 unreachable. Either someone forgot to remove unreachable
1356 variables or the reachability here is wrong. */
1358 gcc_assert (single_user_map
.get (var
));
1362 fprintf (dump_file
, "Variable %s/%i is used by single function\n",
1363 var
->name (), var
->order
);
1365 var
->used_by_single_function
= true;
1374 const pass_data pass_data_ipa_single_use
=
1376 IPA_PASS
, /* type */
1377 "single-use", /* name */
1378 OPTGROUP_NONE
, /* optinfo_flags */
1379 TV_CGRAPHOPT
, /* tv_id */
1380 0, /* properties_required */
1381 0, /* properties_provided */
1382 0, /* properties_destroyed */
1383 0, /* todo_flags_start */
1384 0, /* todo_flags_finish */
1387 class pass_ipa_single_use
: public ipa_opt_pass_d
1390 pass_ipa_single_use (gcc::context
*ctxt
)
1391 : ipa_opt_pass_d (pass_data_ipa_single_use
, ctxt
,
1392 NULL
, /* generate_summary */
1393 NULL
, /* write_summary */
1394 NULL
, /* read_summary */
1395 NULL
, /* write_optimization_summary */
1396 NULL
, /* read_optimization_summary */
1397 NULL
, /* stmt_fixup */
1398 0, /* function_transform_todo_flags_start */
1399 NULL
, /* function_transform */
1400 NULL
) /* variable_transform */
1403 /* opt_pass methods: */
1404 virtual bool gate (function
*);
1405 virtual unsigned int execute (function
*) { return ipa_single_use (); }
1407 }; // class pass_ipa_single_use
1410 pass_ipa_single_use::gate (function
*)
1418 make_pass_ipa_single_use (gcc::context
*ctxt
)
1420 return new pass_ipa_single_use (ctxt
);