]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/ipa-reference.c
re PR tree-optimization/52975 (Ofast produces not optimized code for vectorized ...
[thirdparty/gcc.git] / gcc / ipa-reference.c
CommitLineData
ea900239 1/* Callgraph based analysis of static variables.
c75c517d
SB
2 Copyright (C) 2004, 2005, 2007, 2008, 2009, 2010
3 Free Software Foundation, Inc.
ea900239
DB
4 Contributed by Kenneth Zadeck <zadeck@naturalbridge.com>
5
6This file is part of GCC.
7
8GCC is free software; you can redistribute it and/or modify it under
9the terms of the GNU General Public License as published by the Free
9dcd6f09 10Software Foundation; either version 3, or (at your option) any later
ea900239
DB
11version.
12
13GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14WARRANTY; without even the implied warranty of MERCHANTABILITY or
15FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16for more details.
17
18You should have received a copy of the GNU General Public License
9dcd6f09
NC
19along with GCC; see the file COPYING3. If not see
20<http://www.gnu.org/licenses/>. */
ea900239
DB
21
22/* This file gathers information about how variables whose scope is
b8698a0f 23 confined to the compilation unit are used.
ea900239 24
4a444e58 25 The transitive call site specific clobber effects are computed
ea900239
DB
26 for the variables whose scope is contained within this compilation
27 unit.
28
29 First each function and static variable initialization is analyzed
30 to determine which local static variables are either read, written,
31 or have their address taken. Any local static that has its address
32 taken is removed from consideration. Once the local read and
33 writes are determined, a transitive closure of this information is
34 performed over the call graph to determine the worst case set of
35 side effects of each call. In later parts of the compiler, these
36 local and global sets are examined to make the call clobbering less
37 traumatic, promote some statics to registers, and improve aliasing
4a444e58 38 information. */
ea900239
DB
39
40#include "config.h"
41#include "system.h"
42#include "coretypes.h"
43#include "tm.h"
44#include "tree.h"
45#include "tree-flow.h"
46#include "tree-inline.h"
47#include "tree-pass.h"
48#include "langhooks.h"
49#include "pointer-set.h"
ea264ca5 50#include "splay-tree.h"
ea900239
DB
51#include "ggc.h"
52#include "ipa-utils.h"
53#include "ipa-reference.h"
726a989a 54#include "gimple.h"
ea900239
DB
55#include "cgraph.h"
56#include "output.h"
57#include "flags.h"
58#include "timevar.h"
59#include "diagnostic.h"
60#include "langhooks.h"
412288f1 61#include "data-streamer.h"
d7f09764
DN
62#include "lto-streamer.h"
63
d7f09764
DN
64static void remove_node_data (struct cgraph_node *node,
65 void *data ATTRIBUTE_UNUSED);
66static void duplicate_node_data (struct cgraph_node *src,
67 struct cgraph_node *dst,
68 void *data ATTRIBUTE_UNUSED);
ea900239 69
e2c9111c 70/* The static variables defined within the compilation unit that are
b8698a0f 71 loaded or stored directly by function that owns this structure. */
e2c9111c 72
b8698a0f 73struct ipa_reference_local_vars_info_d
e2c9111c
JH
74{
75 bitmap statics_read;
76 bitmap statics_written;
e2c9111c
JH
77};
78
79/* Statics that are read and written by some set of functions. The
80 local ones are based on the loads and stores local to the function.
81 The global ones are based on the local info as well as the
46c30019 82 transitive closure of the functions that are called. */
e2c9111c
JH
83
84struct ipa_reference_global_vars_info_d
85{
86 bitmap statics_read;
87 bitmap statics_written;
46c30019
JH
88};
89
61502ca8 90/* Information we save about every function after ipa-reference is completed. */
46c30019
JH
91
92struct ipa_reference_optimization_summary_d
93{
e2c9111c
JH
94 bitmap statics_not_read;
95 bitmap statics_not_written;
96};
97
98typedef struct ipa_reference_local_vars_info_d *ipa_reference_local_vars_info_t;
99typedef struct ipa_reference_global_vars_info_d *ipa_reference_global_vars_info_t;
46c30019
JH
100typedef struct ipa_reference_optimization_summary_d *ipa_reference_optimization_summary_t;
101
b8698a0f 102struct ipa_reference_vars_info_d
e2c9111c 103{
46c30019
JH
104 struct ipa_reference_local_vars_info_d local;
105 struct ipa_reference_global_vars_info_d global;
e2c9111c
JH
106};
107
108typedef struct ipa_reference_vars_info_d *ipa_reference_vars_info_t;
109
ea900239 110/* This splay tree contains all of the static variables that are
46c30019
JH
111 being considered by the compilation level alias analysis. */
112static splay_tree reference_vars_to_consider;
ea900239 113
ea900239
DB
114/* A bit is set for every module static we are considering. This is
115 ored into the local info when asm code is found that clobbers all
116 memory. */
117static bitmap all_module_statics;
118
ebcf9dc8
JH
119/* Obstack holding bitmaps of local analysis (live from analysis to
120 propagation) */
121static bitmap_obstack local_info_obstack;
122/* Obstack holding global analysis live forever. */
46c30019 123static bitmap_obstack optimization_summary_obstack;
ea900239 124
129a37fc 125/* Holders of ipa cgraph hooks: */
e2c9111c
JH
126static struct cgraph_2node_hook_list *node_duplication_hook_holder;
127static struct cgraph_node_hook_list *node_removal_hook_holder;
129a37fc 128
e2c9111c
JH
129/* Vector where the reference var infos are actually stored. */
130DEF_VEC_P (ipa_reference_vars_info_t);
131DEF_VEC_ALLOC_P (ipa_reference_vars_info_t, heap);
132static VEC (ipa_reference_vars_info_t, heap) *ipa_reference_vars_vector;
46c30019
JH
133DEF_VEC_P (ipa_reference_optimization_summary_t);
134DEF_VEC_ALLOC_P (ipa_reference_optimization_summary_t, heap);
135static VEC (ipa_reference_optimization_summary_t, heap) *ipa_reference_opt_sum_vector;
e2c9111c 136
ea900239
DB
137/* Return the ipa_reference_vars structure starting from the cgraph NODE. */
138static inline ipa_reference_vars_info_t
e2c9111c
JH
139get_reference_vars_info (struct cgraph_node *node)
140{
141 if (!ipa_reference_vars_vector
46c30019
JH
142 || VEC_length (ipa_reference_vars_info_t,
143 ipa_reference_vars_vector) <= (unsigned int) node->uid)
e2c9111c 144 return NULL;
46c30019
JH
145 return VEC_index (ipa_reference_vars_info_t, ipa_reference_vars_vector,
146 node->uid);
e2c9111c
JH
147}
148
149/* Return the ipa_reference_vars structure starting from the cgraph NODE. */
46c30019
JH
150static inline ipa_reference_optimization_summary_t
151get_reference_optimization_summary (struct cgraph_node *node)
ea900239 152{
46c30019
JH
153 if (!ipa_reference_opt_sum_vector
154 || (VEC_length (ipa_reference_optimization_summary_t,
22a8d1e6 155 ipa_reference_opt_sum_vector)
46c30019 156 <= (unsigned int) node->uid))
ea900239 157 return NULL;
46c30019
JH
158 return VEC_index (ipa_reference_optimization_summary_t, ipa_reference_opt_sum_vector,
159 node->uid);
ea900239
DB
160}
161
46c30019
JH
162/* Return the ipa_reference_vars structure starting from the cgraph NODE. */
163static inline void
164set_reference_vars_info (struct cgraph_node *node,
165 ipa_reference_vars_info_t info)
ea900239 166{
46c30019
JH
167 if (!ipa_reference_vars_vector
168 || VEC_length (ipa_reference_vars_info_t,
169 ipa_reference_vars_vector) <= (unsigned int) node->uid)
170 VEC_safe_grow_cleared (ipa_reference_vars_info_t, heap,
171 ipa_reference_vars_vector, node->uid + 1);
172 VEC_replace (ipa_reference_vars_info_t, ipa_reference_vars_vector,
173 node->uid, info);
ea900239
DB
174}
175
46c30019
JH
176/* Return the ipa_reference_vars structure starting from the cgraph NODE. */
177static inline void
178set_reference_optimization_summary (struct cgraph_node *node,
179 ipa_reference_optimization_summary_t info)
ea900239 180{
46c30019
JH
181 if (!ipa_reference_opt_sum_vector
182 || (VEC_length (ipa_reference_optimization_summary_t,
183 ipa_reference_opt_sum_vector)
184 <= (unsigned int) node->uid))
185 VEC_safe_grow_cleared (ipa_reference_optimization_summary_t,
186 heap, ipa_reference_opt_sum_vector, node->uid + 1);
187 VEC_replace (ipa_reference_optimization_summary_t,
188 ipa_reference_opt_sum_vector, node->uid, info);
ea900239
DB
189}
190
191/* Return a bitmap indexed by_DECL_UID uid for the static variables
192 that are not read during the execution of the function FN. Returns
193 NULL if no data is available. */
194
b8698a0f
L
195bitmap
196ipa_reference_get_not_read_global (struct cgraph_node *fn)
ea900239 197{
46c30019
JH
198 ipa_reference_optimization_summary_t info;
199
fede8efa 200 info = get_reference_optimization_summary (cgraph_function_node (fn, NULL));
46c30019
JH
201 if (info)
202 return info->statics_not_read;
960bfb69 203 else if (flags_from_decl_or_type (fn->symbol.decl) & ECF_LEAF)
46a4da10 204 return all_module_statics;
ea900239
DB
205 else
206 return NULL;
207}
208
209/* Return a bitmap indexed by DECL_UID uid for the static variables
210 that are not written during the execution of the function FN. Note
211 that variables written may or may not be read during the function
212 call. Returns NULL if no data is available. */
213
b8698a0f
L
214bitmap
215ipa_reference_get_not_written_global (struct cgraph_node *fn)
ea900239 216{
46c30019
JH
217 ipa_reference_optimization_summary_t info;
218
219 info = get_reference_optimization_summary (fn);
220 if (info)
221 return info->statics_not_written;
960bfb69 222 else if (flags_from_decl_or_type (fn->symbol.decl) & ECF_LEAF)
46a4da10 223 return all_module_statics;
ea900239
DB
224 else
225 return NULL;
226}
227
228\f
229
230/* Add VAR to all_module_statics and the two
231 reference_vars_to_consider* sets. */
232
b8698a0f
L
233static inline void
234add_static_var (tree var)
ea900239
DB
235{
236 int uid = DECL_UID (var);
ebcf9dc8 237 gcc_assert (TREE_CODE (var) == VAR_DECL);
df24c2b8
JH
238 if (dump_file)
239 splay_tree_insert (reference_vars_to_consider,
240 uid, (splay_tree_value)var);
241 bitmap_set_bit (all_module_statics, uid);
ea900239
DB
242}
243
244/* Return true if the variable T is the right kind of static variable to
245 perform compilation unit scope escape analysis. */
246
b8698a0f 247static inline bool
5f902d76 248is_proper_for_analysis (tree t)
ea900239 249{
46c30019
JH
250 /* We handle only variables whose address is never taken. */
251 if (TREE_ADDRESSABLE (t))
252 return false;
22a8d1e6 253
ea900239
DB
254 /* If the variable has the "used" attribute, treat it as if it had a
255 been touched by the devil. */
b42186f1 256 if (DECL_PRESERVE_P (t))
ea900239
DB
257 return false;
258
259 /* Do not want to do anything with volatile except mark any
260 function that uses one to be not const or pure. */
b8698a0f 261 if (TREE_THIS_VOLATILE (t))
ea900239
DB
262 return false;
263
22a8d1e6
JH
264 /* We do not need to analyze readonly vars, we already know they do not
265 alias. */
266 if (TREE_READONLY (t))
267 return false;
268
2276d5ed
AP
269 /* We cannot touch decls where the type needs constructing. */
270 if (TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (t)))
271 return false;
272
ea900239
DB
273 /* This is a variable we care about. Check if we have seen it
274 before, and if not add it the set of variables we care about. */
f3380641
JH
275 if (all_module_statics
276 && !bitmap_bit_p (all_module_statics, DECL_UID (t)))
ea900239
DB
277 add_static_var (t);
278
279 return true;
280}
281
ea900239 282/* Lookup the tree node for the static variable that has UID and
a4174ebf 283 convert the name to a string for debugging. */
ea900239
DB
284
285static const char *
286get_static_name (int index)
287{
b8698a0f 288 splay_tree_node stn =
ea900239
DB
289 splay_tree_lookup (reference_vars_to_consider, index);
290 if (stn)
291 return lang_hooks.decl_printable_name ((tree)(stn->value), 2);
292 return NULL;
293}
294
e2c9111c
JH
295/* Or in all of the bits from every callee of X into X_GLOBAL, the caller's cycle,
296 bit vector. There are several cases to check to avoid the sparse
ea900239
DB
297 bitmap oring. */
298
299static void
e2c9111c 300propagate_bits (ipa_reference_global_vars_info_t x_global, struct cgraph_node *x)
ea900239 301{
ea900239 302 struct cgraph_edge *e;
b8698a0f 303 for (e = x->callees; e; e = e->next_callee)
ea900239 304 {
46a4da10 305 enum availability avail;
fede8efa 306 struct cgraph_node *y = cgraph_function_node (e->callee, &avail);
ea900239 307
fede8efa
JH
308 if (!y)
309 continue;
c59f5d1b 310 /* Only look into nodes we can propagate something. */
46a4da10
JH
311 if (avail > AVAIL_OVERWRITABLE
312 || (avail == AVAIL_OVERWRITABLE
960bfb69 313 && (flags_from_decl_or_type (y->symbol.decl) & ECF_LEAF)))
ea900239 314 {
960bfb69 315 int flags = flags_from_decl_or_type (y->symbol.decl);
e2c9111c 316 if (get_reference_vars_info (y))
ea900239 317 {
b8698a0f 318 ipa_reference_vars_info_t y_info
e2c9111c 319 = get_reference_vars_info (y);
46c30019 320 ipa_reference_global_vars_info_t y_global = &y_info->global;
e2c9111c
JH
321
322 /* Calls in current cycle do not have global computed yet. */
46c30019 323 if (!y_global->statics_read)
e2c9111c 324 continue;
b8698a0f 325
22a8d1e6
JH
326 /* If function is declared const, it reads no memory even if it
327 seems so to local analysis. */
328 if (flags & ECF_CONST)
329 continue;
330
ea900239
DB
331 if (x_global->statics_read
332 != all_module_statics)
333 {
b8698a0f 334 if (y_global->statics_read
ea900239
DB
335 == all_module_statics)
336 {
337 BITMAP_FREE (x_global->statics_read);
b8698a0f 338 x_global->statics_read
ea900239
DB
339 = all_module_statics;
340 }
341 /* Skip bitmaps that are pointer equal to node's bitmap
342 (no reason to spin within the cycle). */
b8698a0f 343 else if (x_global->statics_read
ea900239
DB
344 != y_global->statics_read)
345 bitmap_ior_into (x_global->statics_read,
346 y_global->statics_read);
347 }
b8698a0f 348
22a8d1e6
JH
349 /* If function is declared pure, it has no stores even if it
350 seems so to local analysis; If we can not return from here,
351 we can safely ignore the call. */
352 if ((flags & ECF_PURE)
353 || cgraph_edge_cannot_lead_to_return (e))
354 continue;
355
b8698a0f 356 if (x_global->statics_written
ea900239
DB
357 != all_module_statics)
358 {
b8698a0f 359 if (y_global->statics_written
ea900239
DB
360 == all_module_statics)
361 {
362 BITMAP_FREE (x_global->statics_written);
b8698a0f 363 x_global->statics_written
ea900239
DB
364 = all_module_statics;
365 }
366 /* Skip bitmaps that are pointer equal to node's bitmap
367 (no reason to spin within the cycle). */
b8698a0f 368 else if (x_global->statics_written
ea900239
DB
369 != y_global->statics_written)
370 bitmap_ior_into (x_global->statics_written,
371 y_global->statics_written);
372 }
373 }
b8698a0f 374 else
ebcf9dc8 375 gcc_unreachable ();
ea900239
DB
376 }
377 }
378}
379
ea900239
DB
380/* The init routine for analyzing global static variable usage. See
381 comments at top for description. */
b8698a0f
L
382static void
383ipa_init (void)
ea900239 384{
d7f09764
DN
385 static bool init_p = false;
386
387 if (init_p)
388 return;
389
390 init_p = true;
391
46c30019
JH
392 if (dump_file)
393 reference_vars_to_consider = splay_tree_new (splay_tree_compare_ints, 0, 0);
ea900239 394
ebcf9dc8 395 bitmap_obstack_initialize (&local_info_obstack);
46c30019 396 bitmap_obstack_initialize (&optimization_summary_obstack);
22a8d1e6 397 all_module_statics = BITMAP_ALLOC (&optimization_summary_obstack);
7dbca013 398
d7f09764
DN
399 node_removal_hook_holder =
400 cgraph_add_node_removal_hook (&remove_node_data, NULL);
401 node_duplication_hook_holder =
402 cgraph_add_node_duplication_hook (&duplicate_node_data, NULL);
ea900239
DB
403}
404
d7f09764 405
812dbce5 406/* Set up the persistent info for FN. */
ea900239 407
812dbce5
JH
408static ipa_reference_local_vars_info_t
409init_function_info (struct cgraph_node *fn)
ea900239 410{
b8698a0f 411 ipa_reference_vars_info_t info
c5274326 412 = XCNEW (struct ipa_reference_vars_info_d);
ea900239
DB
413
414 /* Add the info to the tree's annotation. */
e2c9111c 415 set_reference_vars_info (fn, info);
ea900239 416
46c30019
JH
417 info->local.statics_read = BITMAP_ALLOC (&local_info_obstack);
418 info->local.statics_written = BITMAP_ALLOC (&local_info_obstack);
ea900239 419
46c30019 420 return &info->local;
812dbce5
JH
421}
422
d7f09764 423
812dbce5
JH
424/* This is the main routine for finding the reference patterns for
425 global variables within a function FN. */
d7f09764 426
812dbce5
JH
427static void
428analyze_function (struct cgraph_node *fn)
429{
8b583a06 430 ipa_reference_local_vars_info_t local;
5f902d76
JH
431 struct ipa_ref *ref;
432 int i;
433 tree var;
812dbce5 434
5f902d76 435 local = init_function_info (fn);
960bfb69 436 for (i = 0; ipa_ref_list_reference_iterate (&fn->symbol.ref_list, i, ref); i++)
812dbce5 437 {
5f902d76
JH
438 if (ref->refered_type != IPA_REF_VARPOOL)
439 continue;
960bfb69
JH
440 var = ipa_ref_varpool_node (ref)->symbol.decl;
441 if (ipa_ref_varpool_node (ref)->symbol.externally_visible
5f902d76
JH
442 || !ipa_ref_varpool_node (ref)->analyzed
443 || !is_proper_for_analysis (var))
444 continue;
445 switch (ref->use)
812dbce5 446 {
5f902d76
JH
447 case IPA_REF_LOAD:
448 bitmap_set_bit (local->statics_read, DECL_UID (var));
449 break;
450 case IPA_REF_STORE:
f10ea640
JH
451 if (ipa_ref_cannot_lead_to_return (ref))
452 break;
5f902d76 453 bitmap_set_bit (local->statics_written, DECL_UID (var));
5f902d76
JH
454 break;
455 case IPA_REF_ADDR:
22a8d1e6 456 gcc_unreachable ();
5f902d76 457 break;
812dbce5 458 }
812dbce5 459 }
ea900239 460
22a8d1e6
JH
461 if (cgraph_node_cannot_return (fn))
462 bitmap_clear (local->statics_written);
ea900239
DB
463}
464
e2c9111c
JH
465static bitmap
466copy_global_bitmap (bitmap src)
467{
468 bitmap dst;
469 if (!src)
470 return NULL;
22a8d1e6
JH
471 if (src == all_module_statics)
472 return all_module_statics;
46c30019 473 dst = BITMAP_ALLOC (&optimization_summary_obstack);
e2c9111c
JH
474 bitmap_copy (dst, src);
475 return dst;
476}
477
5f902d76 478
e2c9111c
JH
479/* Called when new clone is inserted to callgraph late. */
480
481static void
482duplicate_node_data (struct cgraph_node *src, struct cgraph_node *dst,
483 void *data ATTRIBUTE_UNUSED)
484{
46c30019
JH
485 ipa_reference_optimization_summary_t ginfo;
486 ipa_reference_optimization_summary_t dst_ginfo;
e2c9111c 487
46c30019 488 ginfo = get_reference_optimization_summary (src);
5f902d76 489 if (!ginfo)
e2c9111c 490 return;
46c30019
JH
491 dst_ginfo = XCNEW (struct ipa_reference_optimization_summary_d);
492 set_reference_optimization_summary (dst, dst_ginfo);
493 dst_ginfo->statics_not_read = copy_global_bitmap (ginfo->statics_not_read);
494 dst_ginfo->statics_not_written = copy_global_bitmap (ginfo->statics_not_written);
e2c9111c
JH
495}
496
497/* Called when node is removed. */
498
499static void
500remove_node_data (struct cgraph_node *node, void *data ATTRIBUTE_UNUSED)
501{
46c30019
JH
502 ipa_reference_optimization_summary_t ginfo;
503 ginfo = get_reference_optimization_summary (node);
504 if (ginfo)
505 {
506 if (ginfo->statics_not_read
507 && ginfo->statics_not_read != all_module_statics)
508 BITMAP_FREE (ginfo->statics_not_read);
509
510 if (ginfo->statics_not_written
511 && ginfo->statics_not_written != all_module_statics)
512 BITMAP_FREE (ginfo->statics_not_written);
513 free (ginfo);
514 set_reference_optimization_summary (node, NULL);
515 }
e2c9111c
JH
516}
517
812dbce5
JH
518/* Analyze each function in the cgraph to see which global or statics
519 are read or written. */
520
b8698a0f 521static void
812dbce5 522generate_summary (void)
ea900239
DB
523{
524 struct cgraph_node *node;
812dbce5
JH
525 unsigned int index;
526 bitmap_iterator bi;
812dbce5 527 bitmap bm_temp;
b8698a0f 528
ea900239 529 ipa_init ();
ebcf9dc8 530 bm_temp = BITMAP_ALLOC (&local_info_obstack);
ea900239 531
5f902d76 532 /* Process all of the functions next. */
ea900239 533 for (node = cgraph_nodes; node; node = node->next)
5f902d76 534 if (node->analyzed)
ea900239
DB
535 analyze_function (node);
536
812dbce5 537 if (dump_file)
ea900239
DB
538 EXECUTE_IF_SET_IN_BITMAP (all_module_statics, 0, index, bi)
539 {
812dbce5
JH
540 fprintf (dump_file, "\nPromotable global:%s",
541 get_static_name (index));
ea900239 542 }
b8698a0f 543
812dbce5 544 BITMAP_FREE(bm_temp);
b8698a0f 545
ea900239 546 if (dump_file)
812dbce5 547 for (node = cgraph_nodes; node; node = node->next)
e2c9111c 548 if (cgraph_function_body_availability (node) >= AVAIL_OVERWRITABLE)
ea900239 549 {
ea900239 550 ipa_reference_local_vars_info_t l;
812dbce5 551 unsigned int index;
ea900239 552 bitmap_iterator bi;
b8698a0f 553
46c30019 554 l = &get_reference_vars_info (node)->local;
b8698a0f
L
555 fprintf (dump_file,
556 "\nFunction name:%s/%i:",
ea900239
DB
557 cgraph_node_name (node), node->uid);
558 fprintf (dump_file, "\n locals read: ");
8b583a06
JH
559 if (l->statics_read)
560 EXECUTE_IF_SET_IN_BITMAP (l->statics_read,
561 0, index, bi)
562 {
563 fprintf (dump_file, "%s ",
564 get_static_name (index));
565 }
ea900239 566 fprintf (dump_file, "\n locals written: ");
8b583a06
JH
567 if (l->statics_written)
568 EXECUTE_IF_SET_IN_BITMAP (l->statics_written,
569 0, index, bi)
570 {
571 fprintf(dump_file, "%s ",
572 get_static_name (index));
573 }
ea900239 574 }
812dbce5
JH
575}
576\f
22a8d1e6 577/* Set READ_ALL/WRITE_ALL based on decl flags of NODE. */
46c30019 578
c59f5d1b 579static void
22a8d1e6
JH
580read_write_all_from_decl (struct cgraph_node *node, bool * read_all,
581 bool * write_all)
c59f5d1b 582{
960bfb69 583 tree decl = node->symbol.decl;
c59f5d1b 584 int flags = flags_from_decl_or_type (decl);
46a4da10
JH
585 if ((flags & ECF_LEAF)
586 && cgraph_function_body_availability (node) <= AVAIL_OVERWRITABLE)
587 ;
588 else if (flags & ECF_CONST)
c59f5d1b 589 ;
22a8d1e6
JH
590 else if ((flags & ECF_PURE)
591 || cgraph_node_cannot_return (node))
46a4da10
JH
592 {
593 *read_all = true;
594 if (dump_file && (dump_flags & TDF_DETAILS))
595 fprintf (dump_file, " %s/%i -> read all\n",
596 cgraph_node_name (node), node->uid);
597 }
c59f5d1b
JH
598 else
599 {
600 /* TODO: To be able to produce sane results, we should also handle
46c30019 601 common builtins, in particular throw. */
c59f5d1b 602 *read_all = true;
22a8d1e6 603 *write_all = true;
46a4da10
JH
604 if (dump_file && (dump_flags & TDF_DETAILS))
605 fprintf (dump_file, " %s/%i -> read all, write all\n",
606 cgraph_node_name (node), node->uid);
c59f5d1b
JH
607 }
608}
609
812dbce5 610/* Produce the global information by preforming a transitive closure
46c30019 611 on the local information that was produced by ipa_analyze_function */
812dbce5
JH
612
613static unsigned int
614propagate (void)
615{
616 struct cgraph_node *node;
617 struct cgraph_node *w;
618 struct cgraph_node **order =
619 XCNEWVEC (struct cgraph_node *, cgraph_n_nodes);
af8bca3c 620 int order_pos;
812dbce5
JH
621 int i;
622
b8698a0f 623 if (dump_file)
812dbce5 624 dump_cgraph (dump_file);
ea900239 625
46c30019 626 ipa_discover_readonly_nonaddressable_vars ();
5f902d76
JH
627 generate_summary ();
628
ea900239
DB
629 /* Propagate the local information thru the call graph to produce
630 the global information. All the nodes within a cycle will have
631 the same info so we collapse cycles first. Then we can do the
632 propagation in one pass from the leaves to the roots. */
af8bca3c 633 order_pos = ipa_reduced_postorder (order, true, true, NULL);
ea900239 634 if (dump_file)
af8bca3c 635 ipa_print_order (dump_file, "reduced", order, order_pos);
ea900239
DB
636
637 for (i = 0; i < order_pos; i++ )
638 {
639 ipa_reference_vars_info_t node_info;
46c30019 640 ipa_reference_global_vars_info_t node_g;
ea900239 641 ipa_reference_local_vars_info_t node_l;
22a8d1e6 642 struct cgraph_edge *e, *ie;
b8698a0f 643
ea900239
DB
644 bool read_all;
645 bool write_all;
646 struct ipa_dfs_info * w_info;
647
648 node = order[i];
71fb4f92
JH
649 if (node->alias)
650 continue;
e2c9111c 651 node_info = get_reference_vars_info (node);
22a8d1e6 652 gcc_assert (node_info);
ea900239 653
46a4da10
JH
654
655 if (dump_file && (dump_flags & TDF_DETAILS))
656 fprintf (dump_file, "Starting cycle with %s/%i\n",
657 cgraph_node_name (node), node->uid);
658
46c30019
JH
659 node_l = &node_info->local;
660 node_g = &node_info->global;
ea900239 661
22a8d1e6
JH
662 read_all = false;
663 write_all = false;
ea900239 664
61502ca8 665 /* When function is overwritable, we can not assume anything. */
c59f5d1b 666 if (cgraph_function_body_availability (node) <= AVAIL_OVERWRITABLE)
22a8d1e6 667 read_write_all_from_decl (node, &read_all, &write_all);
c59f5d1b 668
b8698a0f 669 for (e = node->callees; e; e = e->next_callee)
fede8efa
JH
670 {
671 enum availability avail;
672 struct cgraph_node *callee = cgraph_function_node (e->callee, &avail);
673 if (!callee || avail <= AVAIL_OVERWRITABLE)
674 read_write_all_from_decl (callee, &read_all, &write_all);
675 }
22a8d1e6
JH
676
677 for (ie = node->indirect_calls; ie; ie = ie->next_callee)
678 if (!(ie->indirect_info->ecf_flags & ECF_CONST))
679 {
680 read_all = true;
46a4da10
JH
681 if (dump_file && (dump_flags & TDF_DETAILS))
682 fprintf (dump_file, " indirect call -> read all\n");
22a8d1e6
JH
683 if (!cgraph_edge_cannot_lead_to_return (ie)
684 && !(ie->indirect_info->ecf_flags & ECF_PURE))
46a4da10
JH
685 {
686 if (dump_file && (dump_flags & TDF_DETAILS))
687 fprintf (dump_file, " indirect call -> write all\n");
688 write_all = true;
689 }
22a8d1e6 690 }
c59f5d1b
JH
691
692
22a8d1e6 693 /* If any node in a cycle is read_all or write_all
ea900239 694 they all are. */
960bfb69 695 w_info = (struct ipa_dfs_info *) node->symbol.aux;
ea900239 696 w = w_info->next_cycle;
22a8d1e6 697 while (w && (!read_all || !write_all))
ea900239 698 {
46a4da10
JH
699 if (dump_file && (dump_flags & TDF_DETAILS))
700 fprintf (dump_file, " Visiting %s/%i\n",
701 cgraph_node_name (w), w->uid);
61502ca8 702 /* When function is overwritable, we can not assume anything. */
c59f5d1b 703 if (cgraph_function_body_availability (w) <= AVAIL_OVERWRITABLE)
22a8d1e6 704 read_write_all_from_decl (w, &read_all, &write_all);
c59f5d1b 705
b8698a0f 706 for (e = w->callees; e; e = e->next_callee)
fede8efa
JH
707 {
708 enum availability avail;
709 struct cgraph_node *callee = cgraph_function_node (e->callee, &avail);
710
711 if (avail <= AVAIL_OVERWRITABLE)
712 read_write_all_from_decl (callee, &read_all, &write_all);
713 }
c59f5d1b 714
22a8d1e6
JH
715 for (ie = w->indirect_calls; ie; ie = ie->next_callee)
716 if (!(ie->indirect_info->ecf_flags & ECF_CONST))
717 {
718 read_all = true;
46a4da10
JH
719 if (dump_file && (dump_flags & TDF_DETAILS))
720 fprintf (dump_file, " indirect call -> read all\n");
22a8d1e6
JH
721 if (!cgraph_edge_cannot_lead_to_return (ie)
722 && !(ie->indirect_info->ecf_flags & ECF_PURE))
46a4da10
JH
723 {
724 write_all = true;
725 if (dump_file && (dump_flags & TDF_DETAILS))
726 fprintf (dump_file, " indirect call -> write all\n");
727 }
22a8d1e6 728 }
ea900239 729
960bfb69 730 w_info = (struct ipa_dfs_info *) w->symbol.aux;
ea900239
DB
731 w = w_info->next_cycle;
732 }
733
c59f5d1b 734
ea900239 735 /* Initialized the bitmaps for the reduced nodes */
b8698a0f 736 if (read_all)
ea900239 737 node_g->statics_read = all_module_statics;
b8698a0f 738 else
ea900239 739 {
46c30019 740 node_g->statics_read = BITMAP_ALLOC (&local_info_obstack);
b8698a0f 741 bitmap_copy (node_g->statics_read,
ea900239
DB
742 node_l->statics_read);
743 }
b8698a0f 744 if (write_all)
ea900239
DB
745 node_g->statics_written = all_module_statics;
746 else
747 {
46c30019 748 node_g->statics_written = BITMAP_ALLOC (&local_info_obstack);
b8698a0f 749 bitmap_copy (node_g->statics_written,
ea900239
DB
750 node_l->statics_written);
751 }
752
e2c9111c 753 propagate_bits (node_g, node);
960bfb69 754 w_info = (struct ipa_dfs_info *) node->symbol.aux;
ea900239 755 w = w_info->next_cycle;
22a8d1e6 756 while (w && (!read_all || !write_all))
ea900239 757 {
b8698a0f 758 ipa_reference_vars_info_t w_ri =
e2c9111c 759 get_reference_vars_info (w);
46c30019 760 ipa_reference_local_vars_info_t w_l = &w_ri->local;
960bfb69 761 int flags = flags_from_decl_or_type (w->symbol.decl);
b8698a0f 762
ea900239
DB
763 /* These global bitmaps are initialized from the local info
764 of all of the nodes in the region. However there is no
765 need to do any work if the bitmaps were set to
766 all_module_statics. */
22a8d1e6 767 if (!read_all && !(flags & ECF_CONST))
ea900239
DB
768 bitmap_ior_into (node_g->statics_read,
769 w_l->statics_read);
22a8d1e6
JH
770 if (!write_all
771 && !(flags & ECF_PURE)
772 && !cgraph_node_cannot_return (w))
ea900239
DB
773 bitmap_ior_into (node_g->statics_written,
774 w_l->statics_written);
e2c9111c 775 propagate_bits (node_g, w);
960bfb69 776 w_info = (struct ipa_dfs_info *) w->symbol.aux;
ea900239
DB
777 w = w_info->next_cycle;
778 }
779
e2c9111c 780 /* All nodes within a cycle have the same global info bitmaps. */
46c30019 781 node_info->global = *node_g;
960bfb69 782 w_info = (struct ipa_dfs_info *) node->symbol.aux;
ea900239
DB
783 w = w_info->next_cycle;
784 while (w)
785 {
b8698a0f 786 ipa_reference_vars_info_t w_ri =
e2c9111c
JH
787 get_reference_vars_info (w);
788
46c30019 789 w_ri->global = *node_g;
e2c9111c 790
960bfb69 791 w_info = (struct ipa_dfs_info *) w->symbol.aux;
ea900239
DB
792 w = w_info->next_cycle;
793 }
794 }
795
796 if (dump_file)
797 {
798 for (i = 0; i < order_pos; i++ )
799 {
800 ipa_reference_vars_info_t node_info;
801 ipa_reference_global_vars_info_t node_g;
802 ipa_reference_local_vars_info_t node_l;
803 unsigned int index;
804 bitmap_iterator bi;
805 struct ipa_dfs_info * w_info;
806
807 node = order[i];
71fb4f92
JH
808 if (node->alias)
809 continue;
e2c9111c 810 node_info = get_reference_vars_info (node);
46c30019
JH
811 node_g = &node_info->global;
812 node_l = &node_info->local;
b8698a0f
L
813 fprintf (dump_file,
814 "\nFunction name:%s/%i:",
ea900239
DB
815 cgraph_node_name (node), node->uid);
816 fprintf (dump_file, "\n locals read: ");
8b583a06
JH
817 if (node_l->statics_read)
818 EXECUTE_IF_SET_IN_BITMAP (node_l->statics_read,
819 0, index, bi)
820 {
821 fprintf (dump_file, "%s ",
822 get_static_name (index));
823 }
ea900239 824 fprintf (dump_file, "\n locals written: ");
8b583a06
JH
825 if (node_l->statics_written)
826 EXECUTE_IF_SET_IN_BITMAP (node_l->statics_written,
827 0, index, bi)
828 {
829 fprintf(dump_file, "%s ",
830 get_static_name (index));
831 }
ea900239 832
960bfb69 833 w_info = (struct ipa_dfs_info *) node->symbol.aux;
ea900239 834 w = w_info->next_cycle;
b8698a0f 835 while (w)
ea900239 836 {
b8698a0f 837 ipa_reference_vars_info_t w_ri =
e2c9111c 838 get_reference_vars_info (w);
46c30019 839 ipa_reference_local_vars_info_t w_l = &w_ri->local;
ea900239
DB
840 fprintf (dump_file, "\n next cycle: %s/%i ",
841 cgraph_node_name (w), w->uid);
40513dd3
JJ
842 fprintf (dump_file, "\n locals read: ");
843 if (w_l->statics_read)
844 EXECUTE_IF_SET_IN_BITMAP (w_l->statics_read,
845 0, index, bi)
846 {
847 fprintf (dump_file, "%s ",
848 get_static_name (index));
849 }
ea900239
DB
850
851 fprintf (dump_file, "\n locals written: ");
40513dd3
JJ
852 if (w_l->statics_written)
853 EXECUTE_IF_SET_IN_BITMAP (w_l->statics_written,
854 0, index, bi)
855 {
856 fprintf (dump_file, "%s ",
857 get_static_name (index));
858 }
ea900239 859
960bfb69 860 w_info = (struct ipa_dfs_info *) w->symbol.aux;
ea900239
DB
861 w = w_info->next_cycle;
862 }
863 fprintf (dump_file, "\n globals read: ");
8b583a06
JH
864 if (node_g->statics_read == all_module_statics)
865 fprintf (dump_file, "ALL");
866 else
867 EXECUTE_IF_SET_IN_BITMAP (node_g->statics_read,
868 0, index, bi)
869 {
870 fprintf (dump_file, "%s ",
871 get_static_name (index));
872 }
ea900239 873 fprintf (dump_file, "\n globals written: ");
8b583a06
JH
874 if (node_g->statics_written == all_module_statics)
875 fprintf (dump_file, "ALL");
876 else
877 EXECUTE_IF_SET_IN_BITMAP (node_g->statics_written,
878 0, index, bi)
879 {
880 fprintf (dump_file, "%s ",
881 get_static_name (index));
882 }
ea900239
DB
883 }
884 }
885
886 /* Cleanup. */
58efc3ac 887 for (node = cgraph_nodes; node; node = node->next)
ea900239
DB
888 {
889 ipa_reference_vars_info_t node_info;
890 ipa_reference_global_vars_info_t node_g;
46c30019
JH
891 ipa_reference_optimization_summary_t opt;
892
71fb4f92 893 if (!node->analyzed || node->alias)
58efc3ac
JH
894 continue;
895
e2c9111c 896 node_info = get_reference_vars_info (node);
46a4da10 897 if (cgraph_function_body_availability (node) > AVAIL_OVERWRITABLE
960bfb69 898 || (flags_from_decl_or_type (node->symbol.decl) & ECF_LEAF))
46c30019
JH
899 {
900 node_g = &node_info->global;
ea900239 901
46c30019
JH
902 opt = XCNEW (struct ipa_reference_optimization_summary_d);
903 set_reference_optimization_summary (node, opt);
ea900239 904
46c30019 905 /* Create the complimentary sets. */
22a8d1e6
JH
906
907 if (bitmap_empty_p (node_g->statics_read))
908 opt->statics_not_read = all_module_statics;
909 else
910 {
911 opt->statics_not_read
912 = BITMAP_ALLOC (&optimization_summary_obstack);
913 if (node_g->statics_read != all_module_statics)
914 bitmap_and_compl (opt->statics_not_read,
915 all_module_statics,
916 node_g->statics_read);
917 }
918
919 if (bitmap_empty_p (node_g->statics_written))
920 opt->statics_not_written = all_module_statics;
921 else
922 {
923 opt->statics_not_written
924 = BITMAP_ALLOC (&optimization_summary_obstack);
925 if (node_g->statics_written != all_module_statics)
926 bitmap_and_compl (opt->statics_not_written,
927 all_module_statics,
928 node_g->statics_written);
929 }
46c30019 930 }
04695783 931 free (node_info);
46c30019
JH
932 }
933
af8bca3c 934 ipa_free_postorder_info ();
46c30019 935 free (order);
b8698a0f 936
ebcf9dc8 937 bitmap_obstack_release (&local_info_obstack);
46c30019
JH
938 VEC_free (ipa_reference_vars_info_t, heap, ipa_reference_vars_vector);
939 ipa_reference_vars_vector = NULL;
940 if (dump_file)
941 splay_tree_delete (reference_vars_to_consider);
942 reference_vars_to_consider = NULL;
c2924966 943 return 0;
ea900239
DB
944}
945
f3380641
JH
946/* Return true if we need to write summary of NODE. */
947
948static bool
949write_node_summary_p (struct cgraph_node *node,
950 cgraph_node_set set,
951 varpool_node_set vset,
952 bitmap ltrans_statics)
953{
954 ipa_reference_optimization_summary_t info;
955
956 /* See if we have (non-empty) info. */
957 if (!node->analyzed || node->global.inlined_to)
958 return false;
959 info = get_reference_optimization_summary (node);
960 if (!info || (bitmap_empty_p (info->statics_not_read)
961 && bitmap_empty_p (info->statics_not_written)))
962 return false;
963
964 /* See if we want to encode it.
965 Encode also referenced functions since constant folding might turn it into
966 a direct call.
967
968 In future we might also want to include summaries of functions references
969 by initializers of constant variables references in current unit. */
970 if (!reachable_from_this_partition_p (node, set)
960bfb69 971 && !referenced_from_this_partition_p (&node->symbol.ref_list, set, vset))
f3380641
JH
972 return false;
973
974 /* See if the info has non-empty intersections with vars we want to encode. */
975 if (!bitmap_intersect_p (info->statics_not_read, ltrans_statics)
976 && !bitmap_intersect_p (info->statics_not_written, ltrans_statics))
977 return false;
978 return true;
979}
980
22a8d1e6
JH
981/* Stream out BITS&LTRANS_STATICS as list of decls to OB.
982 LTRANS_STATICS_BITCOUNT specify number of bits in LTRANS_STATICS
983 or -1. When it is positive, just output -1 when
984 BITS&LTRANS_STATICS == BITS&LTRANS_STATICS. */
f3380641
JH
985
986static void
987stream_out_bitmap (struct lto_simple_output_block *ob,
22a8d1e6
JH
988 bitmap bits, bitmap ltrans_statics,
989 int ltrans_statics_bitcount)
f3380641 990{
22a8d1e6 991 int count = 0;
f3380641
JH
992 unsigned int index;
993 bitmap_iterator bi;
22a8d1e6
JH
994 if (bits == all_module_statics)
995 {
412288f1 996 streamer_write_hwi_stream (ob->main_stream, -1);
22a8d1e6
JH
997 return;
998 }
f3380641
JH
999 EXECUTE_IF_AND_IN_BITMAP (bits, ltrans_statics, 0, index, bi)
1000 count ++;
22a8d1e6
JH
1001 if (count == ltrans_statics_bitcount)
1002 {
412288f1 1003 streamer_write_hwi_stream (ob->main_stream, -1);
22a8d1e6
JH
1004 return;
1005 }
412288f1 1006 streamer_write_hwi_stream (ob->main_stream, count);
f3380641
JH
1007 if (!count)
1008 return;
1009 EXECUTE_IF_AND_IN_BITMAP (bits, ltrans_statics, 0, index, bi)
1010 {
1011 tree decl = (tree)splay_tree_lookup (reference_vars_to_consider, index)->value;
1012 lto_output_var_decl_index(ob->decl_state, ob->main_stream, decl);
1013 }
1014}
1015
1016/* Serialize the ipa info for lto. */
1017
1018static void
1019ipa_reference_write_optimization_summary (cgraph_node_set set,
1020 varpool_node_set vset)
1021{
1022 struct cgraph_node *node;
f3380641
JH
1023 struct lto_simple_output_block *ob
1024 = lto_create_simple_output_block (LTO_section_ipa_reference);
1025 unsigned int count = 0;
22a8d1e6 1026 int ltrans_statics_bitcount = 0;
f3380641 1027 lto_cgraph_encoder_t encoder = ob->decl_state->cgraph_node_encoder;
22a8d1e6 1028 lto_varpool_encoder_t varpool_encoder = ob->decl_state->varpool_node_encoder;
f3380641 1029 bitmap ltrans_statics = BITMAP_ALLOC (NULL);
22a8d1e6 1030 int i;
f3380641
JH
1031
1032 reference_vars_to_consider = splay_tree_new (splay_tree_compare_ints, 0, 0);
1033
1034 /* See what variables we are interested in. */
22a8d1e6
JH
1035 for (i = 0; i < lto_varpool_encoder_size (varpool_encoder); i++)
1036 {
1037 struct varpool_node *vnode = lto_varpool_encoder_deref (varpool_encoder, i);
960bfb69 1038 if (!vnode->symbol.externally_visible
22a8d1e6 1039 && vnode->analyzed
960bfb69
JH
1040 && bitmap_bit_p (all_module_statics, DECL_UID (vnode->symbol.decl))
1041 && referenced_from_this_partition_p (&vnode->symbol.ref_list, set, vset))
22a8d1e6 1042 {
960bfb69 1043 tree decl = vnode->symbol.decl;
22a8d1e6
JH
1044 bitmap_set_bit (ltrans_statics, DECL_UID (decl));
1045 splay_tree_insert (reference_vars_to_consider,
1046 DECL_UID (decl), (splay_tree_value)decl);
1047 ltrans_statics_bitcount ++;
1048 }
1049 }
f3380641 1050
22a8d1e6
JH
1051
1052 if (ltrans_statics_bitcount)
1053 for (i = 0; i < lto_cgraph_encoder_size (encoder); i++)
1054 if (write_node_summary_p (lto_cgraph_encoder_deref (encoder, i),
1055 set, vset, ltrans_statics))
1056 count++;
f3380641 1057
412288f1 1058 streamer_write_uhwi_stream (ob->main_stream, count);
22a8d1e6
JH
1059 if (count)
1060 stream_out_bitmap (ob, ltrans_statics, ltrans_statics,
1061 -1);
f3380641
JH
1062
1063 /* Process all of the functions. */
22a8d1e6
JH
1064 if (ltrans_statics_bitcount)
1065 for (i = 0; i < lto_cgraph_encoder_size (encoder); i++)
f3380641 1066 {
22a8d1e6
JH
1067 node = lto_cgraph_encoder_deref (encoder, i);
1068 if (write_node_summary_p (node, set, vset, ltrans_statics))
1069 {
1070 ipa_reference_optimization_summary_t info;
1071 int node_ref;
1072
1073 info = get_reference_optimization_summary (node);
1074 node_ref = lto_cgraph_encoder_encode (encoder, node);
412288f1 1075 streamer_write_uhwi_stream (ob->main_stream, node_ref);
22a8d1e6
JH
1076
1077 stream_out_bitmap (ob, info->statics_not_read, ltrans_statics,
1078 ltrans_statics_bitcount);
1079 stream_out_bitmap (ob, info->statics_not_written, ltrans_statics,
1080 ltrans_statics_bitcount);
1081 }
f3380641
JH
1082 }
1083 BITMAP_FREE (ltrans_statics);
1084 lto_destroy_simple_output_block (ob);
1085 splay_tree_delete (reference_vars_to_consider);
1086}
1087
1088/* Deserialize the ipa info for lto. */
1089
1090static void
1091ipa_reference_read_optimization_summary (void)
1092{
1093 struct lto_file_decl_data ** file_data_vec
1094 = lto_get_file_decl_data ();
1095 struct lto_file_decl_data * file_data;
1096 unsigned int j = 0;
1097 bitmap_obstack_initialize (&optimization_summary_obstack);
1098
1099 node_removal_hook_holder =
1100 cgraph_add_node_removal_hook (&remove_node_data, NULL);
1101 node_duplication_hook_holder =
1102 cgraph_add_node_duplication_hook (&duplicate_node_data, NULL);
22a8d1e6 1103 all_module_statics = BITMAP_ALLOC (&optimization_summary_obstack);
f3380641
JH
1104
1105 while ((file_data = file_data_vec[j++]))
1106 {
1107 const char *data;
1108 size_t len;
1109 struct lto_input_block *ib
1110 = lto_create_simple_input_block (file_data,
1111 LTO_section_ipa_reference,
1112 &data, &len);
1113 if (ib)
1114 {
1115 unsigned int i;
412288f1 1116 unsigned int f_count = streamer_read_uhwi (ib);
22a8d1e6
JH
1117 int b_count;
1118 if (!f_count)
1119 continue;
412288f1 1120 b_count = streamer_read_hwi (ib);
22a8d1e6
JH
1121 if (dump_file)
1122 fprintf (dump_file, "all module statics:");
1123 for (i = 0; i < (unsigned int)b_count; i++)
1124 {
412288f1 1125 unsigned int var_index = streamer_read_uhwi (ib);
22a8d1e6
JH
1126 tree v_decl = lto_file_decl_data_get_var_decl (file_data,
1127 var_index);
1128 bitmap_set_bit (all_module_statics, DECL_UID (v_decl));
1129 if (dump_file)
1130 fprintf (dump_file, " %s",
1131 lang_hooks.decl_printable_name (v_decl, 2));
1132 }
f3380641
JH
1133
1134 for (i = 0; i < f_count; i++)
1135 {
1136 unsigned int j, index;
1137 struct cgraph_node *node;
1138 ipa_reference_optimization_summary_t info;
1139 int v_count;
1140 lto_cgraph_encoder_t encoder;
1141
412288f1 1142 index = streamer_read_uhwi (ib);
f3380641
JH
1143 encoder = file_data->cgraph_node_encoder;
1144 node = lto_cgraph_encoder_deref (encoder, index);
1145 info = XCNEW (struct ipa_reference_optimization_summary_d);
1146 set_reference_optimization_summary (node, info);
1147 info->statics_not_read = BITMAP_ALLOC (&optimization_summary_obstack);
1148 info->statics_not_written = BITMAP_ALLOC (&optimization_summary_obstack);
1149 if (dump_file)
1150 fprintf (dump_file,
1151 "\nFunction name:%s/%i:\n static not read:",
1152 cgraph_node_name (node), node->uid);
1153
1154 /* Set the statics not read. */
412288f1 1155 v_count = streamer_read_hwi (ib);
22a8d1e6 1156 if (v_count == -1)
f3380641 1157 {
22a8d1e6 1158 info->statics_not_read = all_module_statics;
f3380641 1159 if (dump_file)
22a8d1e6 1160 fprintf (dump_file, " all module statics");
f3380641 1161 }
22a8d1e6
JH
1162 else
1163 for (j = 0; j < (unsigned int)v_count; j++)
1164 {
412288f1 1165 unsigned int var_index = streamer_read_uhwi (ib);
22a8d1e6
JH
1166 tree v_decl = lto_file_decl_data_get_var_decl (file_data,
1167 var_index);
1168 bitmap_set_bit (info->statics_not_read, DECL_UID (v_decl));
1169 if (dump_file)
1170 fprintf (dump_file, " %s",
1171 lang_hooks.decl_printable_name (v_decl, 2));
1172 }
f3380641
JH
1173
1174 if (dump_file)
1175 fprintf (dump_file,
1176 "\n static not written:");
1177 /* Set the statics not written. */
412288f1 1178 v_count = streamer_read_hwi (ib);
22a8d1e6 1179 if (v_count == -1)
f3380641 1180 {
22a8d1e6 1181 info->statics_not_written = all_module_statics;
f3380641 1182 if (dump_file)
22a8d1e6 1183 fprintf (dump_file, " all module statics");
f3380641 1184 }
22a8d1e6
JH
1185 else
1186 for (j = 0; j < (unsigned int)v_count; j++)
1187 {
412288f1 1188 unsigned int var_index = streamer_read_uhwi (ib);
22a8d1e6
JH
1189 tree v_decl = lto_file_decl_data_get_var_decl (file_data,
1190 var_index);
1191 bitmap_set_bit (info->statics_not_written, DECL_UID (v_decl));
1192 if (dump_file)
1193 fprintf (dump_file, " %s",
1194 lang_hooks.decl_printable_name (v_decl, 2));
1195 }
f3380641
JH
1196 if (dump_file)
1197 fprintf (dump_file, "\n");
1198 }
1199
1200 lto_destroy_simple_input_block (file_data,
1201 LTO_section_ipa_reference,
1202 ib, data, len);
1203 }
1204 else
1205 /* Fatal error here. We do not want to support compiling ltrans units with
1206 different version of compiler or different flags than the WPA unit, so
1207 this should never happen. */
1208 fatal_error ("ipa reference summary is missing in ltrans unit");
1209 }
1210}
ea900239
DB
1211
1212static bool
1213gate_reference (void)
1214{
7e8b322a 1215 return (flag_ipa_reference
ea900239 1216 /* Don't bother doing anything if the program has errors. */
1da2ed5f 1217 && !seen_error ());
ea900239
DB
1218}
1219
7e5487a2 1220struct ipa_opt_pass_d pass_ipa_reference =
ea900239 1221{
8ddbbcae 1222 {
812dbce5 1223 IPA_PASS,
ea900239
DB
1224 "static-var", /* name */
1225 gate_reference, /* gate */
812dbce5 1226 propagate, /* execute */
ea900239
DB
1227 NULL, /* sub */
1228 NULL, /* next */
1229 0, /* static_pass_number */
1230 TV_IPA_REFERENCE, /* tv_id */
1231 0, /* properties_required */
1232 0, /* properties_provided */
1233 0, /* properties_destroyed */
1234 0, /* todo_flags_start */
8ddbbcae 1235 0 /* todo_flags_finish */
812dbce5 1236 },
5f902d76
JH
1237 NULL, /* generate_summary */
1238 NULL, /* write_summary */
1239 NULL, /* read_summary */
f3380641
JH
1240 ipa_reference_write_optimization_summary,/* write_optimization_summary */
1241 ipa_reference_read_optimization_summary,/* read_optimization_summary */
2c5721d9 1242 NULL, /* stmt_fixup */
812dbce5
JH
1243 0, /* TODOs */
1244 NULL, /* function_transform */
1245 NULL /* variable_transform */
ea900239 1246};