Mercurial > hg > CbC > CbC_gcc
comparison gcc/symtab.c @ 111:04ced10e8804
gcc 7
author | kono |
---|---|
date | Fri, 27 Oct 2017 22:46:09 +0900 |
parents | |
children | 84e7813d76e9 |
comparison
equal
deleted
inserted
replaced
68:561a7518be6b | 111:04ced10e8804 |
---|---|
1 /* Symbol table. | |
2 Copyright (C) 2012-2017 Free Software Foundation, Inc. | |
3 Contributed by Jan Hubicka | |
4 | |
5 This file is part of GCC. | |
6 | |
7 GCC is free software; you can redistribute it and/or modify it under | |
8 the terms of the GNU General Public License as published by the Free | |
9 Software Foundation; either version 3, or (at your option) any later | |
10 version. | |
11 | |
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY | |
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
15 for more details. | |
16 | |
17 You should have received a copy of the GNU General Public License | |
18 along with GCC; see the file COPYING3. If not see | |
19 <http://www.gnu.org/licenses/>. */ | |
20 | |
21 #include "config.h" | |
22 #include "system.h" | |
23 #include "coretypes.h" | |
24 #include "backend.h" | |
25 #include "target.h" | |
26 #include "rtl.h" | |
27 #include "tree.h" | |
28 #include "gimple.h" | |
29 #include "timevar.h" | |
30 #include "cgraph.h" | |
31 #include "lto-streamer.h" | |
32 #include "print-tree.h" | |
33 #include "varasm.h" | |
34 #include "langhooks.h" | |
35 #include "output.h" | |
36 #include "ipa-utils.h" | |
37 #include "calls.h" | |
38 #include "stringpool.h" | |
39 #include "attribs.h" | |
40 | |
41 static const char *ipa_ref_use_name[] = {"read","write","addr","alias","chkp"}; | |
42 | |
43 const char * const ld_plugin_symbol_resolution_names[]= | |
44 { | |
45 "", | |
46 "undef", | |
47 "prevailing_def", | |
48 "prevailing_def_ironly", | |
49 "preempted_reg", | |
50 "preempted_ir", | |
51 "resolved_ir", | |
52 "resolved_exec", | |
53 "resolved_dyn", | |
54 "prevailing_def_ironly_exp" | |
55 }; | |
56 | |
57 /* Follow the IDENTIFIER_TRANSPARENT_ALIAS chain starting at ALIAS | |
58 until we find an identifier that is not itself a transparent alias. */ | |
59 | |
60 static inline tree | |
61 ultimate_transparent_alias_target (tree alias) | |
62 { | |
63 tree target = alias; | |
64 | |
65 while (IDENTIFIER_TRANSPARENT_ALIAS (target)) | |
66 { | |
67 gcc_checking_assert (TREE_CHAIN (target)); | |
68 target = TREE_CHAIN (target); | |
69 } | |
70 gcc_checking_assert (! IDENTIFIER_TRANSPARENT_ALIAS (target) | |
71 && ! TREE_CHAIN (target)); | |
72 | |
73 return target; | |
74 } | |
75 | |
76 | |
77 /* Hash asmnames ignoring the user specified marks. */ | |
78 | |
79 hashval_t | |
80 symbol_table::decl_assembler_name_hash (const_tree asmname) | |
81 { | |
82 if (IDENTIFIER_POINTER (asmname)[0] == '*') | |
83 { | |
84 const char *decl_str = IDENTIFIER_POINTER (asmname) + 1; | |
85 size_t ulp_len = strlen (user_label_prefix); | |
86 | |
87 if (ulp_len == 0) | |
88 ; | |
89 else if (strncmp (decl_str, user_label_prefix, ulp_len) == 0) | |
90 decl_str += ulp_len; | |
91 | |
92 return htab_hash_string (decl_str); | |
93 } | |
94 | |
95 return htab_hash_string (IDENTIFIER_POINTER (asmname)); | |
96 } | |
97 | |
98 /* Return true if assembler names NAME1 and NAME2 leads to the same symbol | |
99 name. */ | |
100 | |
101 bool | |
102 symbol_table::assembler_names_equal_p (const char *name1, const char *name2) | |
103 { | |
104 if (name1 != name2) | |
105 { | |
106 if (name1[0] == '*') | |
107 { | |
108 size_t ulp_len = strlen (user_label_prefix); | |
109 | |
110 name1 ++; | |
111 | |
112 if (ulp_len == 0) | |
113 ; | |
114 else if (strncmp (name1, user_label_prefix, ulp_len) == 0) | |
115 name1 += ulp_len; | |
116 else | |
117 return false; | |
118 } | |
119 if (name2[0] == '*') | |
120 { | |
121 size_t ulp_len = strlen (user_label_prefix); | |
122 | |
123 name2 ++; | |
124 | |
125 if (ulp_len == 0) | |
126 ; | |
127 else if (strncmp (name2, user_label_prefix, ulp_len) == 0) | |
128 name2 += ulp_len; | |
129 else | |
130 return false; | |
131 } | |
132 return !strcmp (name1, name2); | |
133 } | |
134 return true; | |
135 } | |
136 | |
137 /* Compare ASMNAME with the DECL_ASSEMBLER_NAME of DECL. */ | |
138 | |
139 bool | |
140 symbol_table::decl_assembler_name_equal (tree decl, const_tree asmname) | |
141 { | |
142 tree decl_asmname = DECL_ASSEMBLER_NAME (decl); | |
143 const char *decl_str; | |
144 const char *asmname_str; | |
145 | |
146 if (decl_asmname == asmname) | |
147 return true; | |
148 | |
149 decl_str = IDENTIFIER_POINTER (decl_asmname); | |
150 asmname_str = IDENTIFIER_POINTER (asmname); | |
151 return assembler_names_equal_p (decl_str, asmname_str); | |
152 } | |
153 | |
154 | |
155 /* Returns nonzero if P1 and P2 are equal. */ | |
156 | |
157 /* Insert NODE to assembler name hash. */ | |
158 | |
159 void | |
160 symbol_table::insert_to_assembler_name_hash (symtab_node *node, | |
161 bool with_clones) | |
162 { | |
163 if (is_a <varpool_node *> (node) && DECL_HARD_REGISTER (node->decl)) | |
164 return; | |
165 gcc_checking_assert (!node->previous_sharing_asm_name | |
166 && !node->next_sharing_asm_name); | |
167 if (assembler_name_hash) | |
168 { | |
169 symtab_node **aslot; | |
170 cgraph_node *cnode; | |
171 tree decl = node->decl; | |
172 | |
173 tree name = DECL_ASSEMBLER_NAME (node->decl); | |
174 | |
175 /* C++ FE can produce decls without associated assembler name and insert | |
176 them to symtab to hold section or TLS information. */ | |
177 if (!name) | |
178 return; | |
179 | |
180 hashval_t hash = decl_assembler_name_hash (name); | |
181 aslot = assembler_name_hash->find_slot_with_hash (name, hash, INSERT); | |
182 gcc_assert (*aslot != node); | |
183 node->next_sharing_asm_name = (symtab_node *)*aslot; | |
184 if (*aslot != NULL) | |
185 (*aslot)->previous_sharing_asm_name = node; | |
186 *aslot = node; | |
187 | |
188 /* Update also possible inline clones sharing a decl. */ | |
189 cnode = dyn_cast <cgraph_node *> (node); | |
190 if (cnode && cnode->clones && with_clones) | |
191 for (cnode = cnode->clones; cnode; cnode = cnode->next_sibling_clone) | |
192 if (cnode->decl == decl) | |
193 insert_to_assembler_name_hash (cnode, true); | |
194 } | |
195 | |
196 } | |
197 | |
198 /* Remove NODE from assembler name hash. */ | |
199 | |
200 void | |
201 symbol_table::unlink_from_assembler_name_hash (symtab_node *node, | |
202 bool with_clones) | |
203 { | |
204 if (assembler_name_hash) | |
205 { | |
206 cgraph_node *cnode; | |
207 tree decl = node->decl; | |
208 | |
209 if (node->next_sharing_asm_name) | |
210 node->next_sharing_asm_name->previous_sharing_asm_name | |
211 = node->previous_sharing_asm_name; | |
212 if (node->previous_sharing_asm_name) | |
213 { | |
214 node->previous_sharing_asm_name->next_sharing_asm_name | |
215 = node->next_sharing_asm_name; | |
216 } | |
217 else | |
218 { | |
219 tree name = DECL_ASSEMBLER_NAME (node->decl); | |
220 symtab_node **slot; | |
221 | |
222 if (!name) | |
223 return; | |
224 | |
225 hashval_t hash = decl_assembler_name_hash (name); | |
226 slot = assembler_name_hash->find_slot_with_hash (name, hash, | |
227 NO_INSERT); | |
228 gcc_assert (*slot == node); | |
229 if (!node->next_sharing_asm_name) | |
230 assembler_name_hash->clear_slot (slot); | |
231 else | |
232 *slot = node->next_sharing_asm_name; | |
233 } | |
234 node->next_sharing_asm_name = NULL; | |
235 node->previous_sharing_asm_name = NULL; | |
236 | |
237 /* Update also possible inline clones sharing a decl. */ | |
238 cnode = dyn_cast <cgraph_node *> (node); | |
239 if (cnode && cnode->clones && with_clones) | |
240 for (cnode = cnode->clones; cnode; cnode = cnode->next_sibling_clone) | |
241 if (cnode->decl == decl) | |
242 unlink_from_assembler_name_hash (cnode, true); | |
243 } | |
244 } | |
245 | |
246 /* Arrange node to be first in its entry of assembler_name_hash. */ | |
247 | |
248 void | |
249 symbol_table::symtab_prevail_in_asm_name_hash (symtab_node *node) | |
250 { | |
251 unlink_from_assembler_name_hash (node, false); | |
252 insert_to_assembler_name_hash (node, false); | |
253 } | |
254 | |
255 /* Initalize asm name hash unless. */ | |
256 | |
257 void | |
258 symbol_table::symtab_initialize_asm_name_hash (void) | |
259 { | |
260 symtab_node *node; | |
261 if (!assembler_name_hash) | |
262 { | |
263 assembler_name_hash = hash_table<asmname_hasher>::create_ggc (10); | |
264 FOR_EACH_SYMBOL (node) | |
265 insert_to_assembler_name_hash (node, false); | |
266 } | |
267 } | |
268 | |
269 /* Set the DECL_ASSEMBLER_NAME and update symtab hashtables. */ | |
270 | |
271 void | |
272 symbol_table::change_decl_assembler_name (tree decl, tree name) | |
273 { | |
274 symtab_node *node = NULL; | |
275 | |
276 /* We can have user ASM names on things, like global register variables, that | |
277 are not in the symbol table. */ | |
278 if ((VAR_P (decl) && (TREE_STATIC (decl) || DECL_EXTERNAL (decl))) | |
279 || TREE_CODE (decl) == FUNCTION_DECL) | |
280 node = symtab_node::get (decl); | |
281 if (!DECL_ASSEMBLER_NAME_SET_P (decl)) | |
282 { | |
283 SET_DECL_ASSEMBLER_NAME (decl, name); | |
284 if (node) | |
285 insert_to_assembler_name_hash (node, true); | |
286 } | |
287 else | |
288 { | |
289 if (name == DECL_ASSEMBLER_NAME (decl)) | |
290 return; | |
291 | |
292 tree alias = (IDENTIFIER_TRANSPARENT_ALIAS (DECL_ASSEMBLER_NAME (decl)) | |
293 ? TREE_CHAIN (DECL_ASSEMBLER_NAME (decl)) | |
294 : NULL); | |
295 if (node) | |
296 unlink_from_assembler_name_hash (node, true); | |
297 | |
298 const char *old_name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)); | |
299 if (TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)) | |
300 && DECL_RTL_SET_P (decl)) | |
301 warning (0, "%qD renamed after being referenced in assembly", decl); | |
302 | |
303 SET_DECL_ASSEMBLER_NAME (decl, name); | |
304 if (alias) | |
305 { | |
306 IDENTIFIER_TRANSPARENT_ALIAS (name) = 1; | |
307 TREE_CHAIN (name) = alias; | |
308 } | |
309 /* If we change assembler name, also all transparent aliases must | |
310 be updated. There are three kinds - those having same assembler name, | |
311 those being renamed in varasm.c and weakref being renamed by the | |
312 assembler. */ | |
313 if (node) | |
314 { | |
315 insert_to_assembler_name_hash (node, true); | |
316 ipa_ref *ref; | |
317 for (unsigned i = 0; node->iterate_direct_aliases (i, ref); i++) | |
318 { | |
319 struct symtab_node *alias = ref->referring; | |
320 if (alias->transparent_alias && !alias->weakref | |
321 && symbol_table::assembler_names_equal_p | |
322 (old_name, IDENTIFIER_POINTER ( | |
323 DECL_ASSEMBLER_NAME (alias->decl)))) | |
324 change_decl_assembler_name (alias->decl, name); | |
325 else if (alias->transparent_alias | |
326 && IDENTIFIER_TRANSPARENT_ALIAS (alias->decl)) | |
327 { | |
328 gcc_assert (TREE_CHAIN (DECL_ASSEMBLER_NAME (alias->decl)) | |
329 && IDENTIFIER_TRANSPARENT_ALIAS | |
330 (DECL_ASSEMBLER_NAME (alias->decl))); | |
331 | |
332 TREE_CHAIN (DECL_ASSEMBLER_NAME (alias->decl)) = | |
333 ultimate_transparent_alias_target | |
334 (DECL_ASSEMBLER_NAME (node->decl)); | |
335 } | |
336 #ifdef ASM_OUTPUT_WEAKREF | |
337 else gcc_assert (!alias->transparent_alias || alias->weakref); | |
338 #else | |
339 else gcc_assert (!alias->transparent_alias); | |
340 #endif | |
341 } | |
342 gcc_assert (!node->transparent_alias || !node->definition | |
343 || node->weakref | |
344 || TREE_CHAIN (DECL_ASSEMBLER_NAME (decl)) | |
345 || symbol_table::assembler_names_equal_p | |
346 (IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)), | |
347 IDENTIFIER_POINTER | |
348 (DECL_ASSEMBLER_NAME | |
349 (node->get_alias_target ()->decl)))); | |
350 } | |
351 } | |
352 } | |
353 | |
354 /* Hash sections by their names. */ | |
355 | |
356 hashval_t | |
357 section_name_hasher::hash (section_hash_entry *n) | |
358 { | |
359 return htab_hash_string (n->name); | |
360 } | |
361 | |
362 /* Return true if section P1 name equals to P2. */ | |
363 | |
364 bool | |
365 section_name_hasher::equal (section_hash_entry *n1, const char *name) | |
366 { | |
367 return n1->name == name || !strcmp (n1->name, name); | |
368 } | |
369 | |
370 /* Add node into symbol table. This function is not used directly, but via | |
371 cgraph/varpool node creation routines. */ | |
372 | |
373 void | |
374 symtab_node::register_symbol (void) | |
375 { | |
376 symtab->register_symbol (this); | |
377 | |
378 if (!decl->decl_with_vis.symtab_node) | |
379 decl->decl_with_vis.symtab_node = this; | |
380 | |
381 ref_list.clear (); | |
382 | |
383 /* Be sure to do this last; C++ FE might create new nodes via | |
384 DECL_ASSEMBLER_NAME langhook! */ | |
385 symtab->insert_to_assembler_name_hash (this, false); | |
386 } | |
387 | |
388 /* Remove NODE from same comdat group. */ | |
389 | |
390 void | |
391 symtab_node::remove_from_same_comdat_group (void) | |
392 { | |
393 if (same_comdat_group) | |
394 { | |
395 symtab_node *prev; | |
396 for (prev = same_comdat_group; | |
397 prev->same_comdat_group != this; | |
398 prev = prev->same_comdat_group) | |
399 ; | |
400 if (same_comdat_group == prev) | |
401 prev->same_comdat_group = NULL; | |
402 else | |
403 prev->same_comdat_group = same_comdat_group; | |
404 same_comdat_group = NULL; | |
405 set_comdat_group (NULL); | |
406 } | |
407 } | |
408 | |
409 /* Remove node from symbol table. This function is not used directly, but via | |
410 cgraph/varpool node removal routines. */ | |
411 | |
412 void | |
413 symtab_node::unregister (void) | |
414 { | |
415 remove_all_references (); | |
416 remove_all_referring (); | |
417 | |
418 /* Remove reference to section. */ | |
419 set_section_for_node (NULL); | |
420 | |
421 remove_from_same_comdat_group (); | |
422 | |
423 symtab->unregister (this); | |
424 | |
425 /* During LTO symtab merging we temporarily corrupt decl to symtab node | |
426 hash. */ | |
427 gcc_assert (decl->decl_with_vis.symtab_node || in_lto_p); | |
428 if (decl->decl_with_vis.symtab_node == this) | |
429 { | |
430 symtab_node *replacement_node = NULL; | |
431 if (cgraph_node *cnode = dyn_cast <cgraph_node *> (this)) | |
432 replacement_node = cnode->find_replacement (); | |
433 decl->decl_with_vis.symtab_node = replacement_node; | |
434 } | |
435 if (!is_a <varpool_node *> (this) || !DECL_HARD_REGISTER (decl)) | |
436 symtab->unlink_from_assembler_name_hash (this, false); | |
437 if (in_init_priority_hash) | |
438 symtab->init_priority_hash->remove (this); | |
439 } | |
440 | |
441 | |
442 /* Remove symbol from symbol table. */ | |
443 | |
444 void | |
445 symtab_node::remove (void) | |
446 { | |
447 if (cgraph_node *cnode = dyn_cast <cgraph_node *> (this)) | |
448 cnode->remove (); | |
449 else if (varpool_node *vnode = dyn_cast <varpool_node *> (this)) | |
450 vnode->remove (); | |
451 } | |
452 | |
453 /* Add NEW_ to the same comdat group that OLD is in. */ | |
454 | |
455 void | |
456 symtab_node::add_to_same_comdat_group (symtab_node *old_node) | |
457 { | |
458 gcc_assert (old_node->get_comdat_group ()); | |
459 gcc_assert (!same_comdat_group); | |
460 gcc_assert (this != old_node); | |
461 | |
462 set_comdat_group (old_node->get_comdat_group ()); | |
463 same_comdat_group = old_node; | |
464 if (!old_node->same_comdat_group) | |
465 old_node->same_comdat_group = this; | |
466 else | |
467 { | |
468 symtab_node *n; | |
469 for (n = old_node->same_comdat_group; | |
470 n->same_comdat_group != old_node; | |
471 n = n->same_comdat_group) | |
472 ; | |
473 n->same_comdat_group = this; | |
474 } | |
475 } | |
476 | |
477 /* Dissolve the same_comdat_group list in which NODE resides. */ | |
478 | |
479 void | |
480 symtab_node::dissolve_same_comdat_group_list (void) | |
481 { | |
482 symtab_node *n = this; | |
483 symtab_node *next; | |
484 | |
485 if (!same_comdat_group) | |
486 return; | |
487 do | |
488 { | |
489 next = n->same_comdat_group; | |
490 n->same_comdat_group = NULL; | |
491 /* Clear comdat_group for comdat locals, since | |
492 make_decl_local doesn't. */ | |
493 if (!TREE_PUBLIC (n->decl)) | |
494 n->set_comdat_group (NULL); | |
495 n = next; | |
496 } | |
497 while (n != this); | |
498 } | |
499 | |
500 /* Return printable assembler name of NODE. | |
501 This function is used only for debugging. When assembler name | |
502 is unknown go with identifier name. */ | |
503 | |
504 const char * | |
505 symtab_node::asm_name () const | |
506 { | |
507 if (!DECL_ASSEMBLER_NAME_SET_P (decl)) | |
508 return name (); | |
509 return IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)); | |
510 } | |
511 | |
512 /* Return printable identifier name. */ | |
513 | |
514 const char * | |
515 symtab_node::name () const | |
516 { | |
517 if (!DECL_NAME (decl)) | |
518 { | |
519 if (DECL_ASSEMBLER_NAME_SET_P (decl)) | |
520 return asm_name (); | |
521 else | |
522 return "<unnamed>"; | |
523 } | |
524 return lang_hooks.decl_printable_name (decl, 2); | |
525 } | |
526 | |
527 const char * | |
528 symtab_node::get_dump_name (bool asm_name_p) const | |
529 { | |
530 #define EXTRA 16 | |
531 const char *fname = asm_name_p ? asm_name () : name (); | |
532 unsigned l = strlen (fname); | |
533 | |
534 char *s = (char *)ggc_internal_cleared_alloc (l + EXTRA); | |
535 snprintf (s, l + EXTRA, "%s/%d", fname, order); | |
536 | |
537 return s; | |
538 } | |
539 | |
540 const char * | |
541 symtab_node::dump_name () const | |
542 { | |
543 return get_dump_name (false); | |
544 } | |
545 | |
546 const char * | |
547 symtab_node::dump_asm_name () const | |
548 { | |
549 return get_dump_name (true); | |
550 } | |
551 | |
552 /* Return ipa reference from this symtab_node to | |
553 REFERED_NODE or REFERED_VARPOOL_NODE. USE_TYPE specify type | |
554 of the use. */ | |
555 | |
556 ipa_ref * | |
557 symtab_node::create_reference (symtab_node *referred_node, | |
558 enum ipa_ref_use use_type) | |
559 { | |
560 return create_reference (referred_node, use_type, NULL); | |
561 } | |
562 | |
563 | |
564 /* Return ipa reference from this symtab_node to | |
565 REFERED_NODE or REFERED_VARPOOL_NODE. USE_TYPE specify type | |
566 of the use and STMT the statement (if it exists). */ | |
567 | |
568 ipa_ref * | |
569 symtab_node::create_reference (symtab_node *referred_node, | |
570 enum ipa_ref_use use_type, gimple *stmt) | |
571 { | |
572 ipa_ref *ref = NULL, *ref2 = NULL; | |
573 ipa_ref_list *list, *list2; | |
574 ipa_ref_t *old_references; | |
575 | |
576 gcc_checking_assert (!stmt || is_a <cgraph_node *> (this)); | |
577 gcc_checking_assert (use_type != IPA_REF_ALIAS || !stmt); | |
578 | |
579 list = &ref_list; | |
580 old_references = vec_safe_address (list->references); | |
581 vec_safe_grow (list->references, vec_safe_length (list->references) + 1); | |
582 ref = &list->references->last (); | |
583 | |
584 list2 = &referred_node->ref_list; | |
585 | |
586 /* IPA_REF_ALIAS is always inserted at the beginning of the list. */ | |
587 if(use_type == IPA_REF_ALIAS) | |
588 { | |
589 list2->referring.safe_insert (0, ref); | |
590 ref->referred_index = 0; | |
591 | |
592 for (unsigned int i = 1; i < list2->referring.length (); i++) | |
593 list2->referring[i]->referred_index = i; | |
594 } | |
595 else | |
596 { | |
597 list2->referring.safe_push (ref); | |
598 ref->referred_index = list2->referring.length () - 1; | |
599 } | |
600 | |
601 ref->referring = this; | |
602 ref->referred = referred_node; | |
603 ref->stmt = stmt; | |
604 ref->lto_stmt_uid = 0; | |
605 ref->use = use_type; | |
606 ref->speculative = 0; | |
607 | |
608 /* If vector was moved in memory, update pointers. */ | |
609 if (old_references != list->references->address ()) | |
610 { | |
611 int i; | |
612 for (i = 0; iterate_reference(i, ref2); i++) | |
613 ref2->referred_ref_list ()->referring[ref2->referred_index] = ref2; | |
614 } | |
615 return ref; | |
616 } | |
617 | |
618 ipa_ref * | |
619 symtab_node::maybe_create_reference (tree val, gimple *stmt) | |
620 { | |
621 STRIP_NOPS (val); | |
622 ipa_ref_use use_type; | |
623 | |
624 switch (TREE_CODE (val)) | |
625 { | |
626 case VAR_DECL: | |
627 use_type = IPA_REF_LOAD; | |
628 break; | |
629 case ADDR_EXPR: | |
630 use_type = IPA_REF_ADDR; | |
631 break; | |
632 default: | |
633 gcc_assert (!handled_component_p (val)); | |
634 return NULL; | |
635 } | |
636 | |
637 val = get_base_var (val); | |
638 if (val && VAR_OR_FUNCTION_DECL_P (val)) | |
639 { | |
640 symtab_node *referred = symtab_node::get (val); | |
641 gcc_checking_assert (referred); | |
642 return create_reference (referred, use_type, stmt); | |
643 } | |
644 return NULL; | |
645 } | |
646 | |
647 /* Clone all references from symtab NODE to this symtab_node. */ | |
648 | |
649 void | |
650 symtab_node::clone_references (symtab_node *node) | |
651 { | |
652 ipa_ref *ref = NULL, *ref2 = NULL; | |
653 int i; | |
654 for (i = 0; node->iterate_reference (i, ref); i++) | |
655 { | |
656 bool speculative = ref->speculative; | |
657 unsigned int stmt_uid = ref->lto_stmt_uid; | |
658 | |
659 ref2 = create_reference (ref->referred, ref->use, ref->stmt); | |
660 ref2->speculative = speculative; | |
661 ref2->lto_stmt_uid = stmt_uid; | |
662 } | |
663 } | |
664 | |
665 /* Clone all referring from symtab NODE to this symtab_node. */ | |
666 | |
667 void | |
668 symtab_node::clone_referring (symtab_node *node) | |
669 { | |
670 ipa_ref *ref = NULL, *ref2 = NULL; | |
671 int i; | |
672 for (i = 0; node->iterate_referring(i, ref); i++) | |
673 { | |
674 bool speculative = ref->speculative; | |
675 unsigned int stmt_uid = ref->lto_stmt_uid; | |
676 | |
677 ref2 = ref->referring->create_reference (this, ref->use, ref->stmt); | |
678 ref2->speculative = speculative; | |
679 ref2->lto_stmt_uid = stmt_uid; | |
680 } | |
681 } | |
682 | |
683 /* Clone reference REF to this symtab_node and set its stmt to STMT. */ | |
684 | |
685 ipa_ref * | |
686 symtab_node::clone_reference (ipa_ref *ref, gimple *stmt) | |
687 { | |
688 bool speculative = ref->speculative; | |
689 unsigned int stmt_uid = ref->lto_stmt_uid; | |
690 ipa_ref *ref2; | |
691 | |
692 ref2 = create_reference (ref->referred, ref->use, stmt); | |
693 ref2->speculative = speculative; | |
694 ref2->lto_stmt_uid = stmt_uid; | |
695 return ref2; | |
696 } | |
697 | |
698 /* Find the structure describing a reference to REFERRED_NODE | |
699 and associated with statement STMT. */ | |
700 | |
701 ipa_ref * | |
702 symtab_node::find_reference (symtab_node *referred_node, | |
703 gimple *stmt, unsigned int lto_stmt_uid) | |
704 { | |
705 ipa_ref *r = NULL; | |
706 int i; | |
707 | |
708 for (i = 0; iterate_reference (i, r); i++) | |
709 if (r->referred == referred_node | |
710 && !r->speculative | |
711 && ((stmt && r->stmt == stmt) | |
712 || (lto_stmt_uid && r->lto_stmt_uid == lto_stmt_uid) | |
713 || (!stmt && !lto_stmt_uid && !r->stmt && !r->lto_stmt_uid))) | |
714 return r; | |
715 return NULL; | |
716 } | |
717 | |
718 /* Remove all references that are associated with statement STMT. */ | |
719 | |
720 void | |
721 symtab_node::remove_stmt_references (gimple *stmt) | |
722 { | |
723 ipa_ref *r = NULL; | |
724 int i = 0; | |
725 | |
726 while (iterate_reference (i, r)) | |
727 if (r->stmt == stmt) | |
728 r->remove_reference (); | |
729 else | |
730 i++; | |
731 } | |
732 | |
733 /* Remove all stmt references in non-speculative references. | |
734 Those are not maintained during inlining & clonning. | |
735 The exception are speculative references that are updated along | |
736 with callgraph edges associated with them. */ | |
737 | |
738 void | |
739 symtab_node::clear_stmts_in_references (void) | |
740 { | |
741 ipa_ref *r = NULL; | |
742 int i; | |
743 | |
744 for (i = 0; iterate_reference (i, r); i++) | |
745 if (!r->speculative) | |
746 { | |
747 r->stmt = NULL; | |
748 r->lto_stmt_uid = 0; | |
749 } | |
750 } | |
751 | |
752 /* Remove all references in ref list. */ | |
753 | |
754 void | |
755 symtab_node::remove_all_references (void) | |
756 { | |
757 while (vec_safe_length (ref_list.references)) | |
758 ref_list.references->last ().remove_reference (); | |
759 vec_free (ref_list.references); | |
760 } | |
761 | |
762 /* Remove all referring items in ref list. */ | |
763 | |
764 void | |
765 symtab_node::remove_all_referring (void) | |
766 { | |
767 while (ref_list.referring.length ()) | |
768 ref_list.referring.last ()->remove_reference (); | |
769 ref_list.referring.release (); | |
770 } | |
771 | |
772 /* Dump references in ref list to FILE. */ | |
773 | |
774 void | |
775 symtab_node::dump_references (FILE *file) | |
776 { | |
777 ipa_ref *ref = NULL; | |
778 int i; | |
779 for (i = 0; iterate_reference (i, ref); i++) | |
780 { | |
781 fprintf (file, "%s (%s)", | |
782 ref->referred->dump_asm_name (), | |
783 ipa_ref_use_name [ref->use]); | |
784 if (ref->speculative) | |
785 fprintf (file, " (speculative)"); | |
786 } | |
787 fprintf (file, "\n"); | |
788 } | |
789 | |
790 /* Dump referring in list to FILE. */ | |
791 | |
792 void | |
793 symtab_node::dump_referring (FILE *file) | |
794 { | |
795 ipa_ref *ref = NULL; | |
796 int i; | |
797 for (i = 0; iterate_referring(i, ref); i++) | |
798 { | |
799 fprintf (file, "%s (%s)", | |
800 ref->referring->dump_asm_name (), | |
801 ipa_ref_use_name [ref->use]); | |
802 if (ref->speculative) | |
803 fprintf (file, " (speculative)"); | |
804 } | |
805 fprintf (file, "\n"); | |
806 } | |
807 | |
808 static const char * const symtab_type_names[] = {"symbol", "function", "variable"}; | |
809 | |
810 /* Dump base fields of symtab nodes to F. Not to be used directly. */ | |
811 | |
812 void | |
813 symtab_node::dump_base (FILE *f) | |
814 { | |
815 static const char * const visibility_types[] = { | |
816 "default", "protected", "hidden", "internal" | |
817 }; | |
818 | |
819 fprintf (f, "%s (%s)", dump_asm_name (), name ()); | |
820 dump_addr (f, " @", (void *)this); | |
821 fprintf (f, "\n Type: %s", symtab_type_names[type]); | |
822 | |
823 if (definition) | |
824 fprintf (f, " definition"); | |
825 if (analyzed) | |
826 fprintf (f, " analyzed"); | |
827 if (alias) | |
828 fprintf (f, " alias"); | |
829 if (transparent_alias) | |
830 fprintf (f, " transparent_alias"); | |
831 if (weakref) | |
832 fprintf (f, " weakref"); | |
833 if (cpp_implicit_alias) | |
834 fprintf (f, " cpp_implicit_alias"); | |
835 if (alias_target) | |
836 fprintf (f, " target:%s", | |
837 DECL_P (alias_target) | |
838 ? IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME | |
839 (alias_target)) | |
840 : IDENTIFIER_POINTER (alias_target)); | |
841 if (body_removed) | |
842 fprintf (f, "\n Body removed by symtab_remove_unreachable_nodes"); | |
843 fprintf (f, "\n Visibility:"); | |
844 if (in_other_partition) | |
845 fprintf (f, " in_other_partition"); | |
846 if (used_from_other_partition) | |
847 fprintf (f, " used_from_other_partition"); | |
848 if (force_output) | |
849 fprintf (f, " force_output"); | |
850 if (forced_by_abi) | |
851 fprintf (f, " forced_by_abi"); | |
852 if (externally_visible) | |
853 fprintf (f, " externally_visible"); | |
854 if (no_reorder) | |
855 fprintf (f, " no_reorder"); | |
856 if (resolution != LDPR_UNKNOWN) | |
857 fprintf (f, " %s", | |
858 ld_plugin_symbol_resolution_names[(int)resolution]); | |
859 if (TREE_ASM_WRITTEN (decl)) | |
860 fprintf (f, " asm_written"); | |
861 if (DECL_EXTERNAL (decl)) | |
862 fprintf (f, " external"); | |
863 if (TREE_PUBLIC (decl)) | |
864 fprintf (f, " public"); | |
865 if (DECL_COMMON (decl)) | |
866 fprintf (f, " common"); | |
867 if (DECL_WEAK (decl)) | |
868 fprintf (f, " weak"); | |
869 if (DECL_DLLIMPORT_P (decl)) | |
870 fprintf (f, " dll_import"); | |
871 if (DECL_COMDAT (decl)) | |
872 fprintf (f, " comdat"); | |
873 if (get_comdat_group ()) | |
874 fprintf (f, " comdat_group:%s", | |
875 IDENTIFIER_POINTER (get_comdat_group_id ())); | |
876 if (DECL_ONE_ONLY (decl)) | |
877 fprintf (f, " one_only"); | |
878 if (get_section ()) | |
879 fprintf (f, " section:%s", | |
880 get_section ()); | |
881 if (implicit_section) | |
882 fprintf (f," (implicit_section)"); | |
883 if (DECL_VISIBILITY_SPECIFIED (decl)) | |
884 fprintf (f, " visibility_specified"); | |
885 if (DECL_VISIBILITY (decl)) | |
886 fprintf (f, " visibility:%s", | |
887 visibility_types [DECL_VISIBILITY (decl)]); | |
888 if (DECL_VIRTUAL_P (decl)) | |
889 fprintf (f, " virtual"); | |
890 if (DECL_ARTIFICIAL (decl)) | |
891 fprintf (f, " artificial"); | |
892 if (TREE_CODE (decl) == FUNCTION_DECL) | |
893 { | |
894 if (DECL_STATIC_CONSTRUCTOR (decl)) | |
895 fprintf (f, " constructor"); | |
896 if (DECL_STATIC_DESTRUCTOR (decl)) | |
897 fprintf (f, " destructor"); | |
898 } | |
899 fprintf (f, "\n"); | |
900 | |
901 if (same_comdat_group) | |
902 fprintf (f, " Same comdat group as: %s\n", | |
903 same_comdat_group->dump_asm_name ()); | |
904 if (next_sharing_asm_name) | |
905 fprintf (f, " next sharing asm name: %i\n", | |
906 next_sharing_asm_name->order); | |
907 if (previous_sharing_asm_name) | |
908 fprintf (f, " previous sharing asm name: %i\n", | |
909 previous_sharing_asm_name->order); | |
910 | |
911 if (address_taken) | |
912 fprintf (f, " Address is taken.\n"); | |
913 if (aux) | |
914 { | |
915 fprintf (f, " Aux:"); | |
916 dump_addr (f, " @", (void *)aux); | |
917 fprintf (f, "\n"); | |
918 } | |
919 | |
920 fprintf (f, " References: "); | |
921 dump_references (f); | |
922 fprintf (f, " Referring: "); | |
923 dump_referring (f); | |
924 if (lto_file_data) | |
925 fprintf (f, " Read from file: %s\n", | |
926 lto_file_data->file_name); | |
927 } | |
928 | |
929 /* Dump symtab node to F. */ | |
930 | |
931 void | |
932 symtab_node::dump (FILE *f) | |
933 { | |
934 if (cgraph_node *cnode = dyn_cast <cgraph_node *> (this)) | |
935 cnode->dump (f); | |
936 else if (varpool_node *vnode = dyn_cast <varpool_node *> (this)) | |
937 vnode->dump (f); | |
938 } | |
939 | |
940 void | |
941 symbol_table::dump (FILE *f) | |
942 { | |
943 symtab_node *node; | |
944 fprintf (f, "Symbol table:\n\n"); | |
945 FOR_EACH_SYMBOL (node) | |
946 node->dump (f); | |
947 } | |
948 | |
949 /* Return the cgraph node that has ASMNAME for its DECL_ASSEMBLER_NAME. | |
950 Return NULL if there's no such node. */ | |
951 | |
952 symtab_node * | |
953 symtab_node::get_for_asmname (const_tree asmname) | |
954 { | |
955 symtab_node *node; | |
956 | |
957 symtab->symtab_initialize_asm_name_hash (); | |
958 hashval_t hash = symtab->decl_assembler_name_hash (asmname); | |
959 symtab_node **slot | |
960 = symtab->assembler_name_hash->find_slot_with_hash (asmname, hash, | |
961 NO_INSERT); | |
962 | |
963 if (slot) | |
964 { | |
965 node = *slot; | |
966 return node; | |
967 } | |
968 return NULL; | |
969 } | |
970 | |
971 /* Dump symtab node NODE to stderr. */ | |
972 | |
973 DEBUG_FUNCTION void | |
974 symtab_node::debug (void) | |
975 { | |
976 dump (stderr); | |
977 } | |
978 | |
979 /* Verify common part of symtab nodes. */ | |
980 | |
981 DEBUG_FUNCTION bool | |
982 symtab_node::verify_base (void) | |
983 { | |
984 bool error_found = false; | |
985 symtab_node *hashed_node; | |
986 | |
987 if (is_a <cgraph_node *> (this)) | |
988 { | |
989 if (TREE_CODE (decl) != FUNCTION_DECL) | |
990 { | |
991 error ("function symbol is not function"); | |
992 error_found = true; | |
993 } | |
994 } | |
995 else if (is_a <varpool_node *> (this)) | |
996 { | |
997 if (!VAR_P (decl)) | |
998 { | |
999 error ("variable symbol is not variable"); | |
1000 error_found = true; | |
1001 } | |
1002 } | |
1003 else | |
1004 { | |
1005 error ("node has unknown type"); | |
1006 error_found = true; | |
1007 } | |
1008 | |
1009 if (symtab->state != LTO_STREAMING) | |
1010 { | |
1011 hashed_node = symtab_node::get (decl); | |
1012 if (!hashed_node) | |
1013 { | |
1014 error ("node not found node->decl->decl_with_vis.symtab_node"); | |
1015 error_found = true; | |
1016 } | |
1017 if (hashed_node != this | |
1018 && (!is_a <cgraph_node *> (this) | |
1019 || !dyn_cast <cgraph_node *> (this)->clone_of | |
1020 || dyn_cast <cgraph_node *> (this)->clone_of->decl != decl)) | |
1021 { | |
1022 error ("node differs from node->decl->decl_with_vis.symtab_node"); | |
1023 error_found = true; | |
1024 } | |
1025 } | |
1026 if (symtab->assembler_name_hash) | |
1027 { | |
1028 hashed_node = symtab_node::get_for_asmname (DECL_ASSEMBLER_NAME (decl)); | |
1029 if (hashed_node && hashed_node->previous_sharing_asm_name) | |
1030 { | |
1031 error ("assembler name hash list corrupted"); | |
1032 error_found = true; | |
1033 } | |
1034 while (hashed_node) | |
1035 { | |
1036 if (hashed_node == this) | |
1037 break; | |
1038 hashed_node = hashed_node->next_sharing_asm_name; | |
1039 } | |
1040 if (!hashed_node | |
1041 && !(is_a <varpool_node *> (this) | |
1042 && DECL_HARD_REGISTER (decl))) | |
1043 { | |
1044 error ("node not found in symtab assembler name hash"); | |
1045 error_found = true; | |
1046 } | |
1047 } | |
1048 if (previous_sharing_asm_name | |
1049 && previous_sharing_asm_name->next_sharing_asm_name != this) | |
1050 { | |
1051 error ("double linked list of assembler names corrupted"); | |
1052 error_found = true; | |
1053 } | |
1054 if (body_removed && definition) | |
1055 { | |
1056 error ("node has body_removed but is definition"); | |
1057 error_found = true; | |
1058 } | |
1059 if (analyzed && !definition) | |
1060 { | |
1061 error ("node is analyzed but it is not a definition"); | |
1062 error_found = true; | |
1063 } | |
1064 if (cpp_implicit_alias && !alias) | |
1065 { | |
1066 error ("node is alias but not implicit alias"); | |
1067 error_found = true; | |
1068 } | |
1069 if (alias && !definition && !weakref) | |
1070 { | |
1071 error ("node is alias but not definition"); | |
1072 error_found = true; | |
1073 } | |
1074 if (weakref && !transparent_alias) | |
1075 { | |
1076 error ("node is weakref but not an transparent_alias"); | |
1077 error_found = true; | |
1078 } | |
1079 if (transparent_alias && !alias) | |
1080 { | |
1081 error ("node is transparent_alias but not an alias"); | |
1082 error_found = true; | |
1083 } | |
1084 if (same_comdat_group) | |
1085 { | |
1086 symtab_node *n = same_comdat_group; | |
1087 | |
1088 if (!n->get_comdat_group ()) | |
1089 { | |
1090 error ("node is in same_comdat_group list but has no comdat_group"); | |
1091 error_found = true; | |
1092 } | |
1093 if (n->get_comdat_group () != get_comdat_group ()) | |
1094 { | |
1095 error ("same_comdat_group list across different groups"); | |
1096 error_found = true; | |
1097 } | |
1098 if (n->type != type) | |
1099 { | |
1100 error ("mixing different types of symbol in same comdat groups is not supported"); | |
1101 error_found = true; | |
1102 } | |
1103 if (n == this) | |
1104 { | |
1105 error ("node is alone in a comdat group"); | |
1106 error_found = true; | |
1107 } | |
1108 do | |
1109 { | |
1110 if (!n->same_comdat_group) | |
1111 { | |
1112 error ("same_comdat_group is not a circular list"); | |
1113 error_found = true; | |
1114 break; | |
1115 } | |
1116 n = n->same_comdat_group; | |
1117 } | |
1118 while (n != this); | |
1119 if (comdat_local_p ()) | |
1120 { | |
1121 ipa_ref *ref = NULL; | |
1122 | |
1123 for (int i = 0; iterate_referring (i, ref); ++i) | |
1124 { | |
1125 if (!in_same_comdat_group_p (ref->referring)) | |
1126 { | |
1127 error ("comdat-local symbol referred to by %s outside its " | |
1128 "comdat", | |
1129 identifier_to_locale (ref->referring->name())); | |
1130 error_found = true; | |
1131 } | |
1132 } | |
1133 } | |
1134 } | |
1135 if (implicit_section && !get_section ()) | |
1136 { | |
1137 error ("implicit_section flag is set but section isn't"); | |
1138 error_found = true; | |
1139 } | |
1140 if (get_section () && get_comdat_group () | |
1141 && !implicit_section | |
1142 && !lookup_attribute ("section", DECL_ATTRIBUTES (decl))) | |
1143 { | |
1144 error ("Both section and comdat group is set"); | |
1145 error_found = true; | |
1146 } | |
1147 /* TODO: Add string table for sections, so we do not keep holding duplicated | |
1148 strings. */ | |
1149 if (alias && definition | |
1150 && get_section () != get_alias_target ()->get_section () | |
1151 && (!get_section() | |
1152 || !get_alias_target ()->get_section () | |
1153 || strcmp (get_section(), | |
1154 get_alias_target ()->get_section ()))) | |
1155 { | |
1156 error ("Alias and target's section differs"); | |
1157 get_alias_target ()->dump (stderr); | |
1158 error_found = true; | |
1159 } | |
1160 if (alias && definition | |
1161 && get_comdat_group () != get_alias_target ()->get_comdat_group ()) | |
1162 { | |
1163 error ("Alias and target's comdat groups differs"); | |
1164 get_alias_target ()->dump (stderr); | |
1165 error_found = true; | |
1166 } | |
1167 if (transparent_alias && definition && !weakref) | |
1168 { | |
1169 symtab_node *to = get_alias_target (); | |
1170 const char *name1 | |
1171 = IDENTIFIER_POINTER ( | |
1172 ultimate_transparent_alias_target (DECL_ASSEMBLER_NAME (decl))); | |
1173 const char *name2 | |
1174 = IDENTIFIER_POINTER ( | |
1175 ultimate_transparent_alias_target (DECL_ASSEMBLER_NAME (to->decl))); | |
1176 if (!symbol_table::assembler_names_equal_p (name1, name2)) | |
1177 { | |
1178 error ("Transparent alias and target's assembler names differs"); | |
1179 get_alias_target ()->dump (stderr); | |
1180 error_found = true; | |
1181 } | |
1182 } | |
1183 if (transparent_alias && definition | |
1184 && get_alias_target()->transparent_alias && get_alias_target()->analyzed) | |
1185 { | |
1186 error ("Chained transparent aliases"); | |
1187 get_alias_target ()->dump (stderr); | |
1188 error_found = true; | |
1189 } | |
1190 | |
1191 return error_found; | |
1192 } | |
1193 | |
1194 /* Verify consistency of NODE. */ | |
1195 | |
1196 DEBUG_FUNCTION void | |
1197 symtab_node::verify (void) | |
1198 { | |
1199 if (seen_error ()) | |
1200 return; | |
1201 | |
1202 timevar_push (TV_CGRAPH_VERIFY); | |
1203 if (cgraph_node *node = dyn_cast <cgraph_node *> (this)) | |
1204 node->verify_node (); | |
1205 else | |
1206 if (verify_base ()) | |
1207 { | |
1208 debug (); | |
1209 internal_error ("symtab_node::verify failed"); | |
1210 } | |
1211 timevar_pop (TV_CGRAPH_VERIFY); | |
1212 } | |
1213 | |
1214 /* Verify symbol table for internal consistency. */ | |
1215 | |
1216 DEBUG_FUNCTION void | |
1217 symtab_node::verify_symtab_nodes (void) | |
1218 { | |
1219 symtab_node *node; | |
1220 hash_map<tree, symtab_node *> comdat_head_map (251); | |
1221 | |
1222 FOR_EACH_SYMBOL (node) | |
1223 { | |
1224 node->verify (); | |
1225 if (node->get_comdat_group ()) | |
1226 { | |
1227 symtab_node **entry, *s; | |
1228 bool existed; | |
1229 | |
1230 entry = &comdat_head_map.get_or_insert (node->get_comdat_group (), | |
1231 &existed); | |
1232 if (!existed) | |
1233 *entry = node; | |
1234 else if (!DECL_EXTERNAL (node->decl)) | |
1235 { | |
1236 for (s = (*entry)->same_comdat_group; | |
1237 s != NULL && s != node && s != *entry; | |
1238 s = s->same_comdat_group) | |
1239 ; | |
1240 if (!s || s == *entry) | |
1241 { | |
1242 error ("Two symbols with same comdat_group are not linked by " | |
1243 "the same_comdat_group list."); | |
1244 (*entry)->debug (); | |
1245 node->debug (); | |
1246 internal_error ("symtab_node::verify failed"); | |
1247 } | |
1248 } | |
1249 } | |
1250 } | |
1251 } | |
1252 | |
1253 /* Make DECL local. FIXME: We shouldn't need to mess with rtl this early, | |
1254 but other code such as notice_global_symbol generates rtl. */ | |
1255 | |
1256 void | |
1257 symtab_node::make_decl_local (void) | |
1258 { | |
1259 rtx rtl, symbol; | |
1260 | |
1261 if (weakref) | |
1262 { | |
1263 weakref = false; | |
1264 IDENTIFIER_TRANSPARENT_ALIAS (DECL_ASSEMBLER_NAME (decl)) = 0; | |
1265 TREE_CHAIN (DECL_ASSEMBLER_NAME (decl)) = NULL_TREE; | |
1266 symtab->change_decl_assembler_name | |
1267 (decl, DECL_ASSEMBLER_NAME (get_alias_target ()->decl)); | |
1268 DECL_ATTRIBUTES (decl) = remove_attribute ("weakref", | |
1269 DECL_ATTRIBUTES (decl)); | |
1270 } | |
1271 /* Avoid clearing comdat_groups on comdat-local decls. */ | |
1272 else if (TREE_PUBLIC (decl) == 0) | |
1273 return; | |
1274 | |
1275 /* Localizing a symbol also make all its transparent aliases local. */ | |
1276 ipa_ref *ref; | |
1277 for (unsigned i = 0; iterate_direct_aliases (i, ref); i++) | |
1278 { | |
1279 struct symtab_node *alias = ref->referring; | |
1280 if (alias->transparent_alias) | |
1281 alias->make_decl_local (); | |
1282 } | |
1283 | |
1284 if (VAR_P (decl)) | |
1285 { | |
1286 DECL_COMMON (decl) = 0; | |
1287 /* ADDRESSABLE flag is not defined for public symbols. */ | |
1288 TREE_ADDRESSABLE (decl) = 1; | |
1289 TREE_STATIC (decl) = 1; | |
1290 } | |
1291 else | |
1292 gcc_assert (TREE_CODE (decl) == FUNCTION_DECL); | |
1293 | |
1294 DECL_COMDAT (decl) = 0; | |
1295 DECL_WEAK (decl) = 0; | |
1296 DECL_EXTERNAL (decl) = 0; | |
1297 DECL_VISIBILITY_SPECIFIED (decl) = 0; | |
1298 DECL_VISIBILITY (decl) = VISIBILITY_DEFAULT; | |
1299 TREE_PUBLIC (decl) = 0; | |
1300 DECL_DLLIMPORT_P (decl) = 0; | |
1301 if (!DECL_RTL_SET_P (decl)) | |
1302 return; | |
1303 | |
1304 /* Update rtl flags. */ | |
1305 make_decl_rtl (decl); | |
1306 | |
1307 rtl = DECL_RTL (decl); | |
1308 if (!MEM_P (rtl)) | |
1309 return; | |
1310 | |
1311 symbol = XEXP (rtl, 0); | |
1312 if (GET_CODE (symbol) != SYMBOL_REF) | |
1313 return; | |
1314 | |
1315 SYMBOL_REF_WEAK (symbol) = DECL_WEAK (decl); | |
1316 } | |
1317 | |
1318 /* Copy visibility from N. | |
1319 This is useful when THIS becomes a transparent alias of N. */ | |
1320 | |
1321 void | |
1322 symtab_node::copy_visibility_from (symtab_node *n) | |
1323 { | |
1324 gcc_checking_assert (n->weakref == weakref); | |
1325 | |
1326 ipa_ref *ref; | |
1327 for (unsigned i = 0; iterate_direct_aliases (i, ref); i++) | |
1328 { | |
1329 struct symtab_node *alias = ref->referring; | |
1330 if (alias->transparent_alias) | |
1331 alias->copy_visibility_from (n); | |
1332 } | |
1333 | |
1334 if (VAR_P (decl)) | |
1335 { | |
1336 DECL_COMMON (decl) = DECL_COMMON (n->decl); | |
1337 /* ADDRESSABLE flag is not defined for public symbols. */ | |
1338 if (TREE_PUBLIC (decl) && !TREE_PUBLIC (n->decl)) | |
1339 TREE_ADDRESSABLE (decl) = 1; | |
1340 TREE_STATIC (decl) = TREE_STATIC (n->decl); | |
1341 } | |
1342 else gcc_assert (TREE_CODE (decl) == FUNCTION_DECL); | |
1343 | |
1344 DECL_COMDAT (decl) = DECL_COMDAT (n->decl); | |
1345 DECL_WEAK (decl) = DECL_WEAK (n->decl); | |
1346 DECL_EXTERNAL (decl) = DECL_EXTERNAL (n->decl); | |
1347 DECL_VISIBILITY_SPECIFIED (decl) = DECL_VISIBILITY_SPECIFIED (n->decl); | |
1348 DECL_VISIBILITY (decl) = DECL_VISIBILITY (n->decl); | |
1349 TREE_PUBLIC (decl) = TREE_PUBLIC (n->decl); | |
1350 DECL_DLLIMPORT_P (decl) = DECL_DLLIMPORT_P (n->decl); | |
1351 resolution = n->resolution; | |
1352 set_comdat_group (n->get_comdat_group ()); | |
1353 call_for_symbol_and_aliases (symtab_node::set_section, | |
1354 const_cast<char *>(n->get_section ()), true); | |
1355 externally_visible = n->externally_visible; | |
1356 if (!DECL_RTL_SET_P (decl)) | |
1357 return; | |
1358 | |
1359 /* Update rtl flags. */ | |
1360 make_decl_rtl (decl); | |
1361 | |
1362 rtx rtl = DECL_RTL (decl); | |
1363 if (!MEM_P (rtl)) | |
1364 return; | |
1365 | |
1366 rtx symbol = XEXP (rtl, 0); | |
1367 if (GET_CODE (symbol) != SYMBOL_REF) | |
1368 return; | |
1369 | |
1370 SYMBOL_REF_WEAK (symbol) = DECL_WEAK (decl); | |
1371 } | |
1372 | |
1373 /* Walk the alias chain to return the symbol NODE is alias of. | |
1374 If NODE is not an alias, return NODE. | |
1375 Assumes NODE is known to be alias. */ | |
1376 | |
1377 symtab_node * | |
1378 symtab_node::ultimate_alias_target_1 (enum availability *availability, | |
1379 symtab_node *ref) | |
1380 { | |
1381 bool transparent_p = false; | |
1382 | |
1383 /* To determine visibility of the target, we follow ELF semantic of aliases. | |
1384 Here alias is an alternative assembler name of a given definition. Its | |
1385 availability prevails the availability of its target (i.e. static alias of | |
1386 weak definition is available. | |
1387 | |
1388 Transaparent alias is just alternative anme of a given symbol used within | |
1389 one compilation unit and is translated prior hitting the object file. It | |
1390 inherits the visibility of its target. | |
1391 Weakref is a different animal (and noweak definition is weak). | |
1392 | |
1393 If we ever get into supporting targets with different semantics, a target | |
1394 hook will be needed here. */ | |
1395 | |
1396 if (availability) | |
1397 { | |
1398 transparent_p = transparent_alias; | |
1399 if (!transparent_p) | |
1400 *availability = get_availability (ref); | |
1401 else | |
1402 *availability = AVAIL_NOT_AVAILABLE; | |
1403 } | |
1404 | |
1405 symtab_node *node = this; | |
1406 while (node) | |
1407 { | |
1408 if (node->alias && node->analyzed) | |
1409 node = node->get_alias_target (); | |
1410 else | |
1411 { | |
1412 if (!availability || (!transparent_p && node->analyzed)) | |
1413 ; | |
1414 else if (node->analyzed && !node->transparent_alias) | |
1415 *availability = node->get_availability (ref); | |
1416 else | |
1417 *availability = AVAIL_NOT_AVAILABLE; | |
1418 return node; | |
1419 } | |
1420 if (node && availability && transparent_p | |
1421 && node->transparent_alias) | |
1422 { | |
1423 *availability = node->get_availability (ref); | |
1424 transparent_p = false; | |
1425 } | |
1426 } | |
1427 if (availability) | |
1428 *availability = AVAIL_NOT_AVAILABLE; | |
1429 return NULL; | |
1430 } | |
1431 | |
1432 /* C++ FE sometimes change linkage flags after producing same body aliases. | |
1433 | |
1434 FIXME: C++ produce implicit aliases for virtual functions and vtables that | |
1435 are obviously equivalent. The way it is doing so is however somewhat | |
1436 kludgy and interferes with the visibility code. As a result we need to | |
1437 copy the visibility from the target to get things right. */ | |
1438 | |
1439 void | |
1440 symtab_node::fixup_same_cpp_alias_visibility (symtab_node *target) | |
1441 { | |
1442 if (is_a <cgraph_node *> (this)) | |
1443 { | |
1444 DECL_DECLARED_INLINE_P (decl) | |
1445 = DECL_DECLARED_INLINE_P (target->decl); | |
1446 DECL_DISREGARD_INLINE_LIMITS (decl) | |
1447 = DECL_DISREGARD_INLINE_LIMITS (target->decl); | |
1448 } | |
1449 /* FIXME: It is not really clear why those flags should not be copied for | |
1450 functions, too. */ | |
1451 else | |
1452 { | |
1453 DECL_WEAK (decl) = DECL_WEAK (target->decl); | |
1454 DECL_EXTERNAL (decl) = DECL_EXTERNAL (target->decl); | |
1455 DECL_VISIBILITY (decl) = DECL_VISIBILITY (target->decl); | |
1456 } | |
1457 if (TREE_PUBLIC (decl)) | |
1458 { | |
1459 tree group; | |
1460 | |
1461 DECL_EXTERNAL (decl) = DECL_EXTERNAL (target->decl); | |
1462 DECL_COMDAT (decl) = DECL_COMDAT (target->decl); | |
1463 group = target->get_comdat_group (); | |
1464 set_comdat_group (group); | |
1465 if (group && !same_comdat_group) | |
1466 add_to_same_comdat_group (target); | |
1467 } | |
1468 externally_visible = target->externally_visible; | |
1469 } | |
1470 | |
1471 /* Set section, do not recurse into aliases. | |
1472 When one wants to change section of a symbol and its aliases, | |
1473 use set_section. */ | |
1474 | |
1475 void | |
1476 symtab_node::set_section_for_node (const char *section) | |
1477 { | |
1478 const char *current = get_section (); | |
1479 section_hash_entry **slot; | |
1480 | |
1481 if (current == section | |
1482 || (current && section | |
1483 && !strcmp (current, section))) | |
1484 return; | |
1485 | |
1486 if (current) | |
1487 { | |
1488 x_section->ref_count--; | |
1489 if (!x_section->ref_count) | |
1490 { | |
1491 hashval_t hash = htab_hash_string (x_section->name); | |
1492 slot = symtab->section_hash->find_slot_with_hash (x_section->name, | |
1493 hash, INSERT); | |
1494 ggc_free (x_section); | |
1495 symtab->section_hash->clear_slot (slot); | |
1496 } | |
1497 x_section = NULL; | |
1498 } | |
1499 if (!section) | |
1500 { | |
1501 implicit_section = false; | |
1502 return; | |
1503 } | |
1504 if (!symtab->section_hash) | |
1505 symtab->section_hash = hash_table<section_name_hasher>::create_ggc (10); | |
1506 slot = symtab->section_hash->find_slot_with_hash (section, | |
1507 htab_hash_string (section), | |
1508 INSERT); | |
1509 if (*slot) | |
1510 x_section = (section_hash_entry *)*slot; | |
1511 else | |
1512 { | |
1513 int len = strlen (section); | |
1514 *slot = x_section = ggc_cleared_alloc<section_hash_entry> (); | |
1515 x_section->name = ggc_vec_alloc<char> (len + 1); | |
1516 memcpy (x_section->name, section, len + 1); | |
1517 } | |
1518 x_section->ref_count++; | |
1519 } | |
1520 | |
1521 /* Worker for set_section. */ | |
1522 | |
1523 bool | |
1524 symtab_node::set_section (symtab_node *n, void *s) | |
1525 { | |
1526 n->set_section_for_node ((char *)s); | |
1527 return false; | |
1528 } | |
1529 | |
1530 /* Set section of symbol and its aliases. */ | |
1531 | |
1532 void | |
1533 symtab_node::set_section (const char *section) | |
1534 { | |
1535 gcc_assert (!this->alias); | |
1536 call_for_symbol_and_aliases | |
1537 (symtab_node::set_section, const_cast<char *>(section), true); | |
1538 } | |
1539 | |
1540 /* Return the initialization priority. */ | |
1541 | |
1542 priority_type | |
1543 symtab_node::get_init_priority () | |
1544 { | |
1545 if (!this->in_init_priority_hash) | |
1546 return DEFAULT_INIT_PRIORITY; | |
1547 | |
1548 symbol_priority_map *h = symtab->init_priority_hash->get (this); | |
1549 return h ? h->init : DEFAULT_INIT_PRIORITY; | |
1550 } | |
1551 | |
1552 /* Return the finalization priority. */ | |
1553 | |
1554 priority_type | |
1555 cgraph_node::get_fini_priority () | |
1556 { | |
1557 if (!this->in_init_priority_hash) | |
1558 return DEFAULT_INIT_PRIORITY; | |
1559 symbol_priority_map *h = symtab->init_priority_hash->get (this); | |
1560 return h ? h->fini : DEFAULT_INIT_PRIORITY; | |
1561 } | |
1562 | |
1563 /* Return the initialization and finalization priority information for | |
1564 DECL. If there is no previous priority information, a freshly | |
1565 allocated structure is returned. */ | |
1566 | |
1567 symbol_priority_map * | |
1568 symtab_node::priority_info (void) | |
1569 { | |
1570 if (!symtab->init_priority_hash) | |
1571 symtab->init_priority_hash = hash_map<symtab_node *, symbol_priority_map>::create_ggc (13); | |
1572 | |
1573 bool existed; | |
1574 symbol_priority_map *h | |
1575 = &symtab->init_priority_hash->get_or_insert (this, &existed); | |
1576 if (!existed) | |
1577 { | |
1578 h->init = DEFAULT_INIT_PRIORITY; | |
1579 h->fini = DEFAULT_INIT_PRIORITY; | |
1580 in_init_priority_hash = true; | |
1581 } | |
1582 | |
1583 return h; | |
1584 } | |
1585 | |
1586 /* Set initialization priority to PRIORITY. */ | |
1587 | |
1588 void | |
1589 symtab_node::set_init_priority (priority_type priority) | |
1590 { | |
1591 symbol_priority_map *h; | |
1592 | |
1593 if (is_a <cgraph_node *> (this)) | |
1594 gcc_assert (DECL_STATIC_CONSTRUCTOR (this->decl)); | |
1595 | |
1596 if (priority == DEFAULT_INIT_PRIORITY) | |
1597 { | |
1598 gcc_assert (get_init_priority() == priority); | |
1599 return; | |
1600 } | |
1601 h = priority_info (); | |
1602 h->init = priority; | |
1603 } | |
1604 | |
1605 /* Set fialization priority to PRIORITY. */ | |
1606 | |
1607 void | |
1608 cgraph_node::set_fini_priority (priority_type priority) | |
1609 { | |
1610 symbol_priority_map *h; | |
1611 | |
1612 gcc_assert (DECL_STATIC_DESTRUCTOR (this->decl)); | |
1613 | |
1614 if (priority == DEFAULT_INIT_PRIORITY) | |
1615 { | |
1616 gcc_assert (get_fini_priority() == priority); | |
1617 return; | |
1618 } | |
1619 h = priority_info (); | |
1620 h->fini = priority; | |
1621 } | |
1622 | |
1623 /* Worker for symtab_resolve_alias. */ | |
1624 | |
1625 bool | |
1626 symtab_node::set_implicit_section (symtab_node *n, | |
1627 void *data ATTRIBUTE_UNUSED) | |
1628 { | |
1629 n->implicit_section = true; | |
1630 return false; | |
1631 } | |
1632 | |
1633 /* Add reference recording that symtab node is alias of TARGET. | |
1634 The function can fail in the case of aliasing cycles; in this case | |
1635 it returns false. */ | |
1636 | |
1637 bool | |
1638 symtab_node::resolve_alias (symtab_node *target, bool transparent) | |
1639 { | |
1640 symtab_node *n; | |
1641 | |
1642 gcc_assert (!analyzed && !vec_safe_length (ref_list.references)); | |
1643 | |
1644 /* Never let cycles to creep into the symbol table alias references; | |
1645 those will make alias walkers to be infinite. */ | |
1646 for (n = target; n && n->alias; | |
1647 n = n->analyzed ? n->get_alias_target () : NULL) | |
1648 if (n == this) | |
1649 { | |
1650 if (is_a <cgraph_node *> (this)) | |
1651 error ("function %q+D part of alias cycle", decl); | |
1652 else if (is_a <varpool_node *> (this)) | |
1653 error ("variable %q+D part of alias cycle", decl); | |
1654 else | |
1655 gcc_unreachable (); | |
1656 alias = false; | |
1657 return false; | |
1658 } | |
1659 | |
1660 /* "analyze" the node - i.e. mark the reference. */ | |
1661 definition = true; | |
1662 alias = true; | |
1663 analyzed = true; | |
1664 transparent |= transparent_alias; | |
1665 transparent_alias = transparent; | |
1666 if (transparent) | |
1667 while (target->transparent_alias && target->analyzed) | |
1668 target = target->get_alias_target (); | |
1669 create_reference (target, IPA_REF_ALIAS, NULL); | |
1670 | |
1671 /* Add alias into the comdat group of its target unless it is already there. */ | |
1672 if (same_comdat_group) | |
1673 remove_from_same_comdat_group (); | |
1674 set_comdat_group (NULL); | |
1675 if (target->get_comdat_group ()) | |
1676 add_to_same_comdat_group (target); | |
1677 | |
1678 if ((get_section () != target->get_section () | |
1679 || target->get_comdat_group ()) && get_section () && !implicit_section) | |
1680 { | |
1681 error ("section of alias %q+D must match section of its target", decl); | |
1682 } | |
1683 call_for_symbol_and_aliases (symtab_node::set_section, | |
1684 const_cast<char *>(target->get_section ()), true); | |
1685 if (target->implicit_section) | |
1686 call_for_symbol_and_aliases (set_implicit_section, NULL, true); | |
1687 | |
1688 /* Alias targets become redundant after alias is resolved into an reference. | |
1689 We do not want to keep it around or we would have to mind updating them | |
1690 when renaming symbols. */ | |
1691 alias_target = NULL; | |
1692 | |
1693 if (!transparent && cpp_implicit_alias && symtab->state >= CONSTRUCTION) | |
1694 fixup_same_cpp_alias_visibility (target); | |
1695 | |
1696 /* If alias has address taken, so does the target. */ | |
1697 if (address_taken) | |
1698 target->ultimate_alias_target ()->address_taken = true; | |
1699 | |
1700 /* All non-transparent aliases of THIS are now in fact aliases of TARGET. | |
1701 If alias is transparent, also all transparent aliases of THIS are now | |
1702 aliases of TARGET. | |
1703 Also merge same comdat group lists. */ | |
1704 ipa_ref *ref; | |
1705 for (unsigned i = 0; iterate_direct_aliases (i, ref);) | |
1706 { | |
1707 struct symtab_node *alias_alias = ref->referring; | |
1708 if (alias_alias->get_comdat_group ()) | |
1709 { | |
1710 alias_alias->remove_from_same_comdat_group (); | |
1711 alias_alias->set_comdat_group (NULL); | |
1712 if (target->get_comdat_group ()) | |
1713 alias_alias->add_to_same_comdat_group (target); | |
1714 } | |
1715 if (!alias_alias->transparent_alias || transparent) | |
1716 { | |
1717 alias_alias->remove_all_references (); | |
1718 alias_alias->create_reference (target, IPA_REF_ALIAS, NULL); | |
1719 } | |
1720 else i++; | |
1721 } | |
1722 return true; | |
1723 } | |
1724 | |
1725 /* Worker searching noninterposable alias. */ | |
1726 | |
1727 bool | |
1728 symtab_node::noninterposable_alias (symtab_node *node, void *data) | |
1729 { | |
1730 if (!node->transparent_alias && decl_binds_to_current_def_p (node->decl)) | |
1731 { | |
1732 symtab_node *fn = node->ultimate_alias_target (); | |
1733 | |
1734 /* Ensure that the alias is well formed this may not be the case | |
1735 of user defined aliases and currently it is not always the case | |
1736 of C++ same body aliases (that is a bug). */ | |
1737 if (TREE_TYPE (node->decl) != TREE_TYPE (fn->decl) | |
1738 || DECL_CONTEXT (node->decl) != DECL_CONTEXT (fn->decl) | |
1739 || (TREE_CODE (node->decl) == FUNCTION_DECL | |
1740 && flags_from_decl_or_type (node->decl) | |
1741 != flags_from_decl_or_type (fn->decl)) | |
1742 || DECL_ATTRIBUTES (node->decl) != DECL_ATTRIBUTES (fn->decl)) | |
1743 return false; | |
1744 *(symtab_node **)data = node; | |
1745 return true; | |
1746 } | |
1747 return false; | |
1748 } | |
1749 | |
1750 /* If node can not be overwriten by static or dynamic linker to point to | |
1751 different definition, return NODE. Otherwise look for alias with such | |
1752 property and if none exists, introduce new one. */ | |
1753 | |
1754 symtab_node * | |
1755 symtab_node::noninterposable_alias (void) | |
1756 { | |
1757 tree new_decl; | |
1758 symtab_node *new_node = NULL; | |
1759 | |
1760 /* First try to look up existing alias or base object | |
1761 (if that is already non-overwritable). */ | |
1762 symtab_node *node = ultimate_alias_target (); | |
1763 gcc_assert (!node->alias && !node->weakref); | |
1764 node->call_for_symbol_and_aliases (symtab_node::noninterposable_alias, | |
1765 (void *)&new_node, true); | |
1766 if (new_node) | |
1767 return new_node; | |
1768 | |
1769 /* If aliases aren't supported by the assembler, fail. */ | |
1770 if (!TARGET_SUPPORTS_ALIASES) | |
1771 return NULL; | |
1772 | |
1773 /* Otherwise create a new one. */ | |
1774 new_decl = copy_node (node->decl); | |
1775 DECL_DLLIMPORT_P (new_decl) = 0; | |
1776 DECL_NAME (new_decl) = clone_function_name (node->decl, "localalias"); | |
1777 if (TREE_CODE (new_decl) == FUNCTION_DECL) | |
1778 DECL_STRUCT_FUNCTION (new_decl) = NULL; | |
1779 DECL_INITIAL (new_decl) = NULL; | |
1780 SET_DECL_ASSEMBLER_NAME (new_decl, DECL_NAME (new_decl)); | |
1781 SET_DECL_RTL (new_decl, NULL); | |
1782 | |
1783 /* Update the properties. */ | |
1784 DECL_EXTERNAL (new_decl) = 0; | |
1785 TREE_PUBLIC (new_decl) = 0; | |
1786 DECL_COMDAT (new_decl) = 0; | |
1787 DECL_WEAK (new_decl) = 0; | |
1788 | |
1789 /* Since the aliases can be added to vtables, keep DECL_VIRTUAL flag. */ | |
1790 DECL_VIRTUAL_P (new_decl) = DECL_VIRTUAL_P (node->decl); | |
1791 if (TREE_CODE (new_decl) == FUNCTION_DECL) | |
1792 { | |
1793 DECL_STATIC_CONSTRUCTOR (new_decl) = 0; | |
1794 DECL_STATIC_DESTRUCTOR (new_decl) = 0; | |
1795 new_node = cgraph_node::create_alias (new_decl, node->decl); | |
1796 } | |
1797 else | |
1798 { | |
1799 TREE_READONLY (new_decl) = TREE_READONLY (node->decl); | |
1800 DECL_INITIAL (new_decl) = error_mark_node; | |
1801 new_node = varpool_node::create_alias (new_decl, node->decl); | |
1802 } | |
1803 new_node->resolve_alias (node); | |
1804 gcc_assert (decl_binds_to_current_def_p (new_decl) | |
1805 && targetm.binds_local_p (new_decl)); | |
1806 return new_node; | |
1807 } | |
1808 | |
1809 /* Return true if symtab node and TARGET represents | |
1810 semantically equivalent symbols. */ | |
1811 | |
1812 bool | |
1813 symtab_node::semantically_equivalent_p (symtab_node *target) | |
1814 { | |
1815 enum availability avail; | |
1816 symtab_node *ba; | |
1817 symtab_node *bb; | |
1818 | |
1819 /* Equivalent functions are equivalent. */ | |
1820 if (decl == target->decl) | |
1821 return true; | |
1822 | |
1823 /* If symbol is not overwritable by different implementation, | |
1824 walk to the base object it defines. */ | |
1825 ba = ultimate_alias_target (&avail); | |
1826 if (avail >= AVAIL_AVAILABLE) | |
1827 { | |
1828 if (target == ba) | |
1829 return true; | |
1830 } | |
1831 else | |
1832 ba = this; | |
1833 bb = target->ultimate_alias_target (&avail); | |
1834 if (avail >= AVAIL_AVAILABLE) | |
1835 { | |
1836 if (this == bb) | |
1837 return true; | |
1838 } | |
1839 else | |
1840 bb = target; | |
1841 return bb == ba; | |
1842 } | |
1843 | |
1844 /* Classify symbol symtab node for partitioning. */ | |
1845 | |
1846 enum symbol_partitioning_class | |
1847 symtab_node::get_partitioning_class (void) | |
1848 { | |
1849 /* Inline clones are always duplicated. | |
1850 This include external delcarations. */ | |
1851 cgraph_node *cnode = dyn_cast <cgraph_node *> (this); | |
1852 | |
1853 if (DECL_ABSTRACT_P (decl)) | |
1854 return SYMBOL_EXTERNAL; | |
1855 | |
1856 if (cnode && cnode->global.inlined_to) | |
1857 return SYMBOL_DUPLICATE; | |
1858 | |
1859 /* Transparent aliases are always duplicated. */ | |
1860 if (transparent_alias) | |
1861 return definition ? SYMBOL_DUPLICATE : SYMBOL_EXTERNAL; | |
1862 | |
1863 /* External declarations are external. */ | |
1864 if (DECL_EXTERNAL (decl)) | |
1865 return SYMBOL_EXTERNAL; | |
1866 | |
1867 if (varpool_node *vnode = dyn_cast <varpool_node *> (this)) | |
1868 { | |
1869 if (alias && definition && !ultimate_alias_target ()->definition) | |
1870 return SYMBOL_EXTERNAL; | |
1871 /* Constant pool references use local symbol names that can not | |
1872 be promoted global. We should never put into a constant pool | |
1873 objects that can not be duplicated across partitions. */ | |
1874 if (DECL_IN_CONSTANT_POOL (decl)) | |
1875 return SYMBOL_DUPLICATE; | |
1876 if (DECL_HARD_REGISTER (decl)) | |
1877 return SYMBOL_DUPLICATE; | |
1878 gcc_checking_assert (vnode->definition); | |
1879 } | |
1880 /* Functions that are cloned may stay in callgraph even if they are unused. | |
1881 Handle them as external; compute_ltrans_boundary take care to make | |
1882 proper things to happen (i.e. to make them appear in the boundary but | |
1883 with body streamed, so clone can me materialized). */ | |
1884 else if (!dyn_cast <cgraph_node *> (this)->function_symbol ()->definition) | |
1885 return SYMBOL_EXTERNAL; | |
1886 | |
1887 /* Linker discardable symbols are duplicated to every use unless they are | |
1888 keyed. */ | |
1889 if (DECL_ONE_ONLY (decl) | |
1890 && !force_output | |
1891 && !forced_by_abi | |
1892 && !used_from_object_file_p ()) | |
1893 return SYMBOL_DUPLICATE; | |
1894 | |
1895 return SYMBOL_PARTITION; | |
1896 } | |
1897 | |
1898 /* Return true when symbol is known to be non-zero. */ | |
1899 | |
1900 bool | |
1901 symtab_node::nonzero_address () | |
1902 { | |
1903 /* Weakrefs may be NULL when their target is not defined. */ | |
1904 if (alias && weakref) | |
1905 { | |
1906 if (analyzed) | |
1907 { | |
1908 symtab_node *target = ultimate_alias_target (); | |
1909 | |
1910 if (target->alias && target->weakref) | |
1911 return false; | |
1912 /* We can not recurse to target::nonzero. It is possible that the | |
1913 target is used only via the alias. | |
1914 We may walk references and look for strong use, but we do not know | |
1915 if this strong use will survive to final binary, so be | |
1916 conservative here. | |
1917 ??? Maybe we could do the lookup during late optimization that | |
1918 could be useful to eliminate the NULL pointer checks in LTO | |
1919 programs. */ | |
1920 if (target->definition && !DECL_EXTERNAL (target->decl)) | |
1921 return true; | |
1922 if (target->resolution != LDPR_UNKNOWN | |
1923 && target->resolution != LDPR_UNDEF | |
1924 && !target->can_be_discarded_p () | |
1925 && flag_delete_null_pointer_checks) | |
1926 return true; | |
1927 return false; | |
1928 } | |
1929 else | |
1930 return false; | |
1931 } | |
1932 | |
1933 /* With !flag_delete_null_pointer_checks we assume that symbols may | |
1934 bind to NULL. This is on by default on embedded targets only. | |
1935 | |
1936 Otherwise all non-WEAK symbols must be defined and thus non-NULL or | |
1937 linking fails. Important case of WEAK we want to do well are comdats. | |
1938 Those are handled by later check for definition. | |
1939 | |
1940 When parsing, beware the cases when WEAK attribute is added later. */ | |
1941 if (!DECL_WEAK (decl) | |
1942 && flag_delete_null_pointer_checks) | |
1943 { | |
1944 refuse_visibility_changes = true; | |
1945 return true; | |
1946 } | |
1947 | |
1948 /* If target is defined and not extern, we know it will be output and thus | |
1949 it will bind to non-NULL. | |
1950 Play safe for flag_delete_null_pointer_checks where weak definition maye | |
1951 be re-defined by NULL. */ | |
1952 if (definition && !DECL_EXTERNAL (decl) | |
1953 && (flag_delete_null_pointer_checks || !DECL_WEAK (decl))) | |
1954 { | |
1955 if (!DECL_WEAK (decl)) | |
1956 refuse_visibility_changes = true; | |
1957 return true; | |
1958 } | |
1959 | |
1960 /* As the last resort, check the resolution info. */ | |
1961 if (resolution != LDPR_UNKNOWN | |
1962 && resolution != LDPR_UNDEF | |
1963 && !can_be_discarded_p () | |
1964 && flag_delete_null_pointer_checks) | |
1965 return true; | |
1966 return false; | |
1967 } | |
1968 | |
1969 /* Return 0 if symbol is known to have different address than S2, | |
1970 Return 1 if symbol is known to have same address as S2, | |
1971 return -1 otherwise. | |
1972 | |
1973 If MEMORY_ACCESSED is true, assume that both memory pointer to THIS | |
1974 and S2 is going to be accessed. This eliminates the situations when | |
1975 either THIS or S2 is NULL and is seful for comparing bases when deciding | |
1976 about memory aliasing. */ | |
1977 int | |
1978 symtab_node::equal_address_to (symtab_node *s2, bool memory_accessed) | |
1979 { | |
1980 enum availability avail1, avail2; | |
1981 | |
1982 /* A Shortcut: equivalent symbols are always equivalent. */ | |
1983 if (this == s2) | |
1984 return 1; | |
1985 | |
1986 /* Unwind transparent aliases first; those are always equal to their | |
1987 target. */ | |
1988 if (this->transparent_alias && this->analyzed) | |
1989 return this->get_alias_target ()->equal_address_to (s2); | |
1990 while (s2->transparent_alias && s2->analyzed) | |
1991 s2 = s2->get_alias_target(); | |
1992 | |
1993 if (this == s2) | |
1994 return 1; | |
1995 | |
1996 /* For non-interposable aliases, lookup and compare their actual definitions. | |
1997 Also check if the symbol needs to bind to given definition. */ | |
1998 symtab_node *rs1 = ultimate_alias_target (&avail1); | |
1999 symtab_node *rs2 = s2->ultimate_alias_target (&avail2); | |
2000 bool binds_local1 = rs1->analyzed && decl_binds_to_current_def_p (this->decl); | |
2001 bool binds_local2 = rs2->analyzed && decl_binds_to_current_def_p (s2->decl); | |
2002 bool really_binds_local1 = binds_local1; | |
2003 bool really_binds_local2 = binds_local2; | |
2004 | |
2005 /* Addresses of vtables and virtual functions can not be used by user | |
2006 code and are used only within speculation. In this case we may make | |
2007 symbol equivalent to its alias even if interposition may break this | |
2008 rule. Doing so will allow us to turn speculative inlining into | |
2009 non-speculative more agressively. */ | |
2010 if (DECL_VIRTUAL_P (this->decl) && avail1 >= AVAIL_AVAILABLE) | |
2011 binds_local1 = true; | |
2012 if (DECL_VIRTUAL_P (s2->decl) && avail2 >= AVAIL_AVAILABLE) | |
2013 binds_local2 = true; | |
2014 | |
2015 /* If both definitions are available we know that even if they are bound | |
2016 to other unit they must be defined same way and therefore we can use | |
2017 equivalence test. */ | |
2018 if (rs1 != rs2 && avail1 >= AVAIL_AVAILABLE && avail2 >= AVAIL_AVAILABLE) | |
2019 binds_local1 = binds_local2 = true; | |
2020 | |
2021 if (binds_local1 && binds_local2 && rs1 == rs2) | |
2022 { | |
2023 /* We made use of the fact that alias is not weak. */ | |
2024 if (rs1 != this) | |
2025 refuse_visibility_changes = true; | |
2026 if (rs2 != s2) | |
2027 s2->refuse_visibility_changes = true; | |
2028 return 1; | |
2029 } | |
2030 | |
2031 /* If both symbols may resolve to NULL, we can not really prove them | |
2032 different. */ | |
2033 if (!memory_accessed && !nonzero_address () && !s2->nonzero_address ()) | |
2034 return -1; | |
2035 | |
2036 /* Except for NULL, functions and variables never overlap. */ | |
2037 if (TREE_CODE (decl) != TREE_CODE (s2->decl)) | |
2038 return 0; | |
2039 | |
2040 /* If one of the symbols is unresolved alias, punt. */ | |
2041 if (rs1->alias || rs2->alias) | |
2042 return -1; | |
2043 | |
2044 /* If we have a non-interposale definition of at least one of the symbols | |
2045 and the other symbol is different, we know other unit can not interpose | |
2046 it to the first symbol; all aliases of the definition needs to be | |
2047 present in the current unit. */ | |
2048 if (((really_binds_local1 || really_binds_local2) | |
2049 /* If we have both definitions and they are different, we know they | |
2050 will be different even in units they binds to. */ | |
2051 || (binds_local1 && binds_local2)) | |
2052 && rs1 != rs2) | |
2053 { | |
2054 /* We make use of the fact that one symbol is not alias of the other | |
2055 and that the definition is non-interposable. */ | |
2056 refuse_visibility_changes = true; | |
2057 s2->refuse_visibility_changes = true; | |
2058 rs1->refuse_visibility_changes = true; | |
2059 rs2->refuse_visibility_changes = true; | |
2060 return 0; | |
2061 } | |
2062 | |
2063 /* TODO: Alias oracle basically assume that addresses of global variables | |
2064 are different unless they are declared as alias of one to another while | |
2065 the code folding comparsions doesn't. | |
2066 We probably should be consistent and use this fact here, too, but for | |
2067 the moment return false only when we are called from the alias oracle. */ | |
2068 | |
2069 return memory_accessed && rs1 != rs2 ? 0 : -1; | |
2070 } | |
2071 | |
2072 /* Worker for call_for_symbol_and_aliases. */ | |
2073 | |
2074 bool | |
2075 symtab_node::call_for_symbol_and_aliases_1 (bool (*callback) (symtab_node *, | |
2076 void *), | |
2077 void *data, | |
2078 bool include_overwritable) | |
2079 { | |
2080 ipa_ref *ref; | |
2081 FOR_EACH_ALIAS (this, ref) | |
2082 { | |
2083 symtab_node *alias = ref->referring; | |
2084 if (include_overwritable | |
2085 || alias->get_availability () > AVAIL_INTERPOSABLE) | |
2086 if (alias->call_for_symbol_and_aliases (callback, data, | |
2087 include_overwritable)) | |
2088 return true; | |
2089 } | |
2090 return false; | |
2091 } | |
2092 | |
2093 /* Return true if address of N is possibly compared. */ | |
2094 | |
2095 static bool | |
2096 address_matters_1 (symtab_node *n, void *) | |
2097 { | |
2098 struct ipa_ref *ref; | |
2099 | |
2100 if (!n->address_can_be_compared_p ()) | |
2101 return false; | |
2102 if (n->externally_visible || n->force_output) | |
2103 return true; | |
2104 | |
2105 for (unsigned int i = 0; n->iterate_referring (i, ref); i++) | |
2106 if (ref->address_matters_p ()) | |
2107 return true; | |
2108 return false; | |
2109 } | |
2110 | |
2111 /* Return true if symbol's address may possibly be compared to other | |
2112 symbol's address. */ | |
2113 | |
2114 bool | |
2115 symtab_node::address_matters_p () | |
2116 { | |
2117 gcc_assert (!alias); | |
2118 return call_for_symbol_and_aliases (address_matters_1, NULL, true); | |
2119 } | |
2120 | |
2121 /* Return true if symbol's alignment may be increased. */ | |
2122 | |
2123 bool | |
2124 symtab_node::can_increase_alignment_p (void) | |
2125 { | |
2126 symtab_node *target = ultimate_alias_target (); | |
2127 | |
2128 /* For now support only variables. */ | |
2129 if (!VAR_P (decl)) | |
2130 return false; | |
2131 | |
2132 /* With -fno-toplevel-reorder we may have already output the constant. */ | |
2133 if (TREE_ASM_WRITTEN (target->decl)) | |
2134 return false; | |
2135 | |
2136 /* If target is already placed in an anchor, we can not touch its | |
2137 alignment. */ | |
2138 if (DECL_RTL_SET_P (target->decl) | |
2139 && MEM_P (DECL_RTL (target->decl)) | |
2140 && SYMBOL_REF_HAS_BLOCK_INFO_P (XEXP (DECL_RTL (target->decl), 0))) | |
2141 return false; | |
2142 | |
2143 /* Constant pool entries may be shared. */ | |
2144 if (DECL_IN_CONSTANT_POOL (target->decl)) | |
2145 return false; | |
2146 | |
2147 /* We cannot change alignment of symbols that may bind to symbols | |
2148 in other translation unit that may contain a definition with lower | |
2149 alignment. */ | |
2150 if (!decl_binds_to_current_def_p (decl)) | |
2151 return false; | |
2152 | |
2153 /* When compiling partition, be sure the symbol is not output by other | |
2154 partition. */ | |
2155 if (flag_ltrans | |
2156 && (target->in_other_partition | |
2157 || target->get_partitioning_class () == SYMBOL_DUPLICATE)) | |
2158 return false; | |
2159 | |
2160 /* Do not override the alignment as specified by the ABI when the used | |
2161 attribute is set. */ | |
2162 if (DECL_PRESERVE_P (decl) || DECL_PRESERVE_P (target->decl)) | |
2163 return false; | |
2164 | |
2165 /* Do not override explicit alignment set by the user when an explicit | |
2166 section name is also used. This is a common idiom used by many | |
2167 software projects. */ | |
2168 if (DECL_SECTION_NAME (target->decl) != NULL && !target->implicit_section) | |
2169 return false; | |
2170 | |
2171 return true; | |
2172 } | |
2173 | |
2174 /* Worker for symtab_node::increase_alignment. */ | |
2175 | |
2176 static bool | |
2177 increase_alignment_1 (symtab_node *n, void *v) | |
2178 { | |
2179 unsigned int align = (size_t)v; | |
2180 if (DECL_ALIGN (n->decl) < align | |
2181 && n->can_increase_alignment_p ()) | |
2182 { | |
2183 SET_DECL_ALIGN (n->decl, align); | |
2184 DECL_USER_ALIGN (n->decl) = 1; | |
2185 } | |
2186 return false; | |
2187 } | |
2188 | |
2189 /* Increase alignment of THIS to ALIGN. */ | |
2190 | |
2191 void | |
2192 symtab_node::increase_alignment (unsigned int align) | |
2193 { | |
2194 gcc_assert (can_increase_alignment_p () && align < MAX_OFILE_ALIGNMENT); | |
2195 ultimate_alias_target()->call_for_symbol_and_aliases (increase_alignment_1, | |
2196 (void *)(size_t) align, | |
2197 true); | |
2198 gcc_assert (DECL_ALIGN (decl) >= align); | |
2199 } | |
2200 | |
2201 /* Helper for symtab_node::definition_alignment. */ | |
2202 | |
2203 static bool | |
2204 get_alignment_1 (symtab_node *n, void *v) | |
2205 { | |
2206 *((unsigned int *)v) = MAX (*((unsigned int *)v), DECL_ALIGN (n->decl)); | |
2207 return false; | |
2208 } | |
2209 | |
2210 /* Return desired alignment of the definition. This is NOT alignment useful | |
2211 to access THIS, because THIS may be interposable and DECL_ALIGN should | |
2212 be used instead. It however must be guaranteed when output definition | |
2213 of THIS. */ | |
2214 | |
2215 unsigned int | |
2216 symtab_node::definition_alignment () | |
2217 { | |
2218 unsigned int align = 0; | |
2219 gcc_assert (!alias); | |
2220 call_for_symbol_and_aliases (get_alignment_1, &align, true); | |
2221 return align; | |
2222 } | |
2223 | |
2224 /* Return symbol used to separate symbol name from suffix. */ | |
2225 | |
2226 char | |
2227 symbol_table::symbol_suffix_separator () | |
2228 { | |
2229 #ifndef NO_DOT_IN_LABEL | |
2230 return '.'; | |
2231 #elif !defined NO_DOLLAR_IN_LABEL | |
2232 return '$'; | |
2233 #else | |
2234 return '_'; | |
2235 #endif | |
2236 } | |
2237 | |
2238 /* Return true when references to this symbol from REF must bind to current | |
2239 definition in final executable. */ | |
2240 | |
2241 bool | |
2242 symtab_node::binds_to_current_def_p (symtab_node *ref) | |
2243 { | |
2244 if (!definition) | |
2245 return false; | |
2246 if (transparent_alias) | |
2247 return definition | |
2248 && get_alias_target()->binds_to_current_def_p (ref); | |
2249 if (lookup_attribute ("ifunc", DECL_ATTRIBUTES (decl))) | |
2250 return false; | |
2251 if (decl_binds_to_current_def_p (decl)) | |
2252 return true; | |
2253 | |
2254 /* Inline clones always binds locally. */ | |
2255 cgraph_node *cnode = dyn_cast <cgraph_node *> (this); | |
2256 if (cnode && cnode->global.inlined_to) | |
2257 return true; | |
2258 | |
2259 if (DECL_EXTERNAL (decl)) | |
2260 return false; | |
2261 | |
2262 gcc_assert (externally_visible); | |
2263 | |
2264 if (ref) | |
2265 { | |
2266 cgraph_node *cref = dyn_cast <cgraph_node *> (ref); | |
2267 if (cref) | |
2268 ref = cref->global.inlined_to; | |
2269 } | |
2270 | |
2271 /* If this is a reference from symbol itself and there are no aliases, we | |
2272 may be sure that the symbol was not interposed by something else because | |
2273 the symbol itself would be unreachable otherwise. This is important | |
2274 to optimize recursive functions well. | |
2275 | |
2276 This assumption may be broken by inlining: if symbol is interposable | |
2277 but the body is available (i.e. declared inline), inliner may make | |
2278 the body reachable even with interposition. */ | |
2279 if (this == ref && !has_aliases_p () | |
2280 && (!cnode | |
2281 || symtab->state >= IPA_SSA_AFTER_INLINING | |
2282 || get_availability () >= AVAIL_INTERPOSABLE)) | |
2283 return true; | |
2284 | |
2285 | |
2286 /* References within one comdat group are always bound in a group. */ | |
2287 if (ref | |
2288 && symtab->state >= IPA_SSA_AFTER_INLINING | |
2289 && get_comdat_group () | |
2290 && get_comdat_group () == ref->get_comdat_group ()) | |
2291 return true; | |
2292 | |
2293 return false; | |
2294 } |