diff options
author | hubicka <hubicka@138bc75d-0d04-0410-961f-82ee72b054a4> | 2010-07-15 10:01:07 +0000 |
---|---|---|
committer | hubicka <hubicka@138bc75d-0d04-0410-961f-82ee72b054a4> | 2010-07-15 10:01:07 +0000 |
commit | bfca27e379a3754ca7154f7394a19ad3b5d226ba (patch) | |
tree | 11277a792886817993fe98270d49a0e11e619778 | |
parent | cff02494c6064641537dbe3d76430c6a6d7b5c49 (diff) | |
download | gcc-bfca27e379a3754ca7154f7394a19ad3b5d226ba.tar.gz |
* cgraph.c: Include lto-streamer.h
(change_decl_assembler_name): Work when assembler name hash is at place.
(cgraph_make_decl_local): When localizing COMDAT symbol at WPA stage, be
sure to rename it to avoid name clash.
* ipa.c (cgraph_externally_visible_p, function_and_variable_visibility):
Localize hidden symbols only when locally defined.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@162211 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r-- | gcc/ChangeLog | 9 | ||||
-rw-r--r-- | gcc/cgraph.c | 78 | ||||
-rw-r--r-- | gcc/ipa.c | 10 |
3 files changed, 85 insertions, 12 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 3a2e01b82ca..5efdf1a24cd 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,12 @@ +2010-07-15 Jan Hubicka <jh@suse.cz> + + * cgraph.c: Include lto-streamer.h + (change_decl_assembler_name): Work when assembler name hash is at place. + (cgraph_make_decl_local): When localizing COMDAT symbol at WPA stage, be + sure to rename it to avoid name clash. + * ipa.c (cgraph_externally_visible_p, function_and_variable_visibility): + Localize hidden symbols only when locally defined. + 2010-07-15 Uros Bizjak <ubizjak@gmail.com> * config/i386/i386.h (SHIFT_COUNT_TRUNCATED): Expand comment. diff --git a/gcc/cgraph.c b/gcc/cgraph.c index fff437a6265..66a88db4610 100644 --- a/gcc/cgraph.c +++ b/gcc/cgraph.c @@ -97,6 +97,7 @@ The callgraph: #include "diagnostic-core.h" #include "rtl.h" #include "ipa-utils.h" +#include "lto-streamer.h" static void cgraph_node_remove_callers (struct cgraph_node *node); static inline void cgraph_edge_remove_caller (struct cgraph_edge *e); @@ -1975,20 +1976,43 @@ debug_cgraph (void) void change_decl_assembler_name (tree decl, tree name) { - gcc_assert (!assembler_name_hash); + struct cgraph_node *node; + void **slot; if (!DECL_ASSEMBLER_NAME_SET_P (decl)) + SET_DECL_ASSEMBLER_NAME (decl, name); + else { - SET_DECL_ASSEMBLER_NAME (decl, name); - return; - } - if (name == DECL_ASSEMBLER_NAME (decl)) - return; + if (name == DECL_ASSEMBLER_NAME (decl)) + return; - if (TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)) - && DECL_RTL_SET_P (decl)) - warning (0, "%D renamed after being referenced in assembly", decl); + if (assembler_name_hash + && TREE_CODE (decl) == FUNCTION_DECL + && (node = cgraph_get_node_or_alias (decl)) != NULL) + { + tree old_name = DECL_ASSEMBLER_NAME (decl); + slot = htab_find_slot_with_hash (assembler_name_hash, old_name, + decl_assembler_name_hash (old_name), + NO_INSERT); + /* Inline clones are not hashed. */ + if (slot && *slot == node) + htab_clear_slot (assembler_name_hash, slot); + } + if (TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)) + && DECL_RTL_SET_P (decl)) + warning (0, "%D renamed after being referenced in assembly", decl); - SET_DECL_ASSEMBLER_NAME (decl, name); + SET_DECL_ASSEMBLER_NAME (decl, name); + } + if (assembler_name_hash + && TREE_CODE (decl) == FUNCTION_DECL + && (node = cgraph_get_node_or_alias (decl)) != NULL) + { + slot = htab_find_slot_with_hash (assembler_name_hash, name, + decl_assembler_name_hash (name), + INSERT); + gcc_assert (!*slot); + *slot = node; + } } /* Add a top-level asm statement to the list. */ @@ -2459,6 +2483,40 @@ cgraph_make_decl_local (tree decl) if (DECL_COMDAT (decl)) { + /* It is possible that we are linking against library defining same COMDAT + function. To avoid conflict we need to rename our local name of the + function just in the case WHOPR partitioning decide to make it hidden + to avoid cross partition references. */ + if (flag_wpa) + { + const char *old_name; + + old_name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)); + if (TREE_CODE (decl) == FUNCTION_DECL) + { + struct cgraph_node *node = cgraph_get_node_or_alias (decl); + change_decl_assembler_name (decl, + clone_function_name (decl, "local")); + if (node->local.lto_file_data) + lto_record_renamed_decl (node->local.lto_file_data, + old_name, + IDENTIFIER_POINTER + (DECL_ASSEMBLER_NAME (decl))); + } + else if (TREE_CODE (decl) == VAR_DECL) + { + struct varpool_node *vnode = varpool_get_node (decl); + /* change_decl_assembler_name will warn here on vtables because + C++ frontend still sets TREE_SYMBOL_REFERENCED on them. */ + SET_DECL_ASSEMBLER_NAME (decl, + clone_function_name (decl, "local")); + if (vnode->lto_file_data) + lto_record_renamed_decl (vnode->lto_file_data, + old_name, + IDENTIFIER_POINTER + (DECL_ASSEMBLER_NAME (decl))); + } + } DECL_SECTION_NAME (decl) = 0; DECL_COMDAT (decl) = 0; } diff --git a/gcc/ipa.c b/gcc/ipa.c index 785b4bd4053..4be3fcfc959 100644 --- a/gcc/ipa.c +++ b/gcc/ipa.c @@ -582,7 +582,10 @@ cgraph_externally_visible_p (struct cgraph_node *node, bool whole_program, bool return true; /* When doing link time optimizations, hidden symbols become local. */ - if (in_lto_p && DECL_VISIBILITY (node->decl) == VISIBILITY_HIDDEN) + if (in_lto_p && DECL_VISIBILITY (node->decl) == VISIBILITY_HIDDEN + /* Be sure that node is defined in IR file, not in other object + file. In that case we don't set used_from_other_object_file. */ + && node->analyzed) ; else if (!whole_program) return true; @@ -779,7 +782,10 @@ function_and_variable_visibility (bool whole_program) /* When doing linktime optimizations, all hidden symbols will become local. */ && (!in_lto_p - || DECL_VISIBILITY (vnode->decl) != VISIBILITY_HIDDEN)) + || DECL_VISIBILITY (vnode->decl) != VISIBILITY_HIDDEN + /* We can get prevailing decision in other object file. + In this case we do not sed used_from_object_file. */ + || !vnode->finalized)) || vnode->used_from_object_file || pointer_set_contains (aliased_vnodes, vnode) || lookup_attribute ("externally_visible", |