]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
Move all varpool routines out of cgraph/cgraphunit to varpool.c
authorJan Hubicka <jh@suse.cz>
Mon, 11 Dec 2006 08:07:52 +0000 (09:07 +0100)
committerJan Hubicka <hubicka@gcc.gnu.org>
Mon, 11 Dec 2006 08:07:52 +0000 (08:07 +0000)
Move all varpool routines out of cgraph/cgraphunit to varpool.c
* cgraph.c: Update comments.
(cgraph_varpool_hash,
cgraph_varpool_nodes, cgraph_varpool_last_needed_node
cgraph_varpool_node_name, cgraph_varpool_node,
cgraph_varpol_mode_for_asm, cgraph_varpool_mark_needed_node,
cgraph_variable_initializer_availability): Move to
varpool.c and drop cgraph_ prefixes.
(cgraph_varpool_enqueue_needed_node, cgraph_varpool_reset_queue,
cgraph_varpool_first_unanalyzed_node, cgraph_varpool_finalize_decl):
move to varpool.c; drop cgraph_ prefix; make static.
(dump_cgraph_varpool_node): Move to varpool.c under name
dump_varpool_node.
(dump_varpool, hash_varpool_node, eq_varpool_node,
decide_is_variable_needed): Move to varpool.c
(decl_assembler_name_equal): Move to tree.c.
(availability_names): Rename to ...
(cgraph_availability_names): ... this one.
(dump_cgraph_node): Update.
* cgraph.h: Reorder declarations now in varpool.c
(cgraph_vailablity_names): Declare.
(struct cgraph_varpool_node): Rename to ...
(struct varpool_node): ... this one.
(cgraph_varpool_first_unanalyzed_node, cgraph_varpool_nodes_queue,
cgraph_varpool_first_unanalyzed_node, cgraph_varpool_node,
cgraph_varpool_node_for_asm, cgraph_varpool_mark_needed_node,
cgraph_varpool_finalize_decl, cgraph_varpool_enqueue_needed_node,
cgraph_varpool_reset_queue, cgraph_varpool_assemble_pending_decls,
cgraph_variable_initializer_availability): Rename to ...
(varpool_first_unanalyzed_node, varpool_nodes_queue,
varpool_first_unanalyzed_node, varpool_node,
varpool_node_for_asm, varpool_mark_needed_node,
varpool_finalize_decl, varpool_enqueue_needed_node,
varpool_assemble_pending_decls, variable_initializer_availability):
Rename to ...
* tree.c (decl_assembler_name_equal): Move here from cgraph.c.
* tree.h (decl_assembler_name_equal): Declare.
* omp-low.c (lower_omp_critical): Update.
* ipa-reference (analyze_variable, static_execute): Likewise.
* toplev.c (wrapup_global_declaration_2, compile_file): Update.
* cgraphunit.c: Update comments.
(cgraph_varpool_assembled_nodes_queue): Move to varpool.c under name
varpool_assembled_nodes_queue.
(cgraph_varpool_analyze_pending_decls): Move to varpool.c under name
varpool_analyze_pending_decls.
(cgraph_varpool_remove_unreferenced_decls): Move to varpool.c under name
varpool_remove_unreferenced_decls.
(record_reference): Update.
(cgraph_create_edges): Update.
(record_referneces_in_initializer): New function.
(cgraph_varpool_assemble_decl): Move to varpool.c under name
varpool_assemble_decl; make global.
(cgraph_varpool_assemble_pending_decls): Move to varpool.c under name
varpool_assemble_pending_decls.
(process_function_and_variable_attributes, cgraph_finalize_compilation_unit,
struct cgraph_order_sort, cgraph_output_in_order,
cgraph_function_and_variable_invisibility, cgraph_optimize,
cgraph_increase_alignment): Update.
* dwarf2out.c (decls_for_scope): Likewise.
* ipa-type-escape.c (analyze_variable, type_escape_execute): Likewise.
* except.c (output_ttype): Likewise.
* varasm.c (mark_decl_referenced): Likewise.
(find_decl_and_mark_referenced, assemble_alias): update.
* Makefile.in: Add varpool.c, gt-varpool.c and remove gt-cgraphunit.c
* passes.c (rest_of_decl_compilation): Update.

* cp/decl2.c (var_finalized_p): Update for renamed varpool functions.
* fortran/f59-lang.c (gfc_expand_function): Update for renamed varpool functions.

From-SVN: r119731

23 files changed:
gcc/ChangeLog
gcc/Makefile.in
gcc/cgraph.c
gcc/cgraph.h
gcc/cgraphunit.c
gcc/cp/ChangeLog
gcc/cp/decl2.c
gcc/dwarf2out.c
gcc/except.c
gcc/fortran/ChangeLog
gcc/fortran/f95-lang.c
gcc/ipa-reference.c
gcc/ipa-type-escape.c
gcc/java/ChangeLog
gcc/java/class.c
gcc/java/resource.c
gcc/omp-low.c
gcc/passes.c
gcc/toplev.c
gcc/tree.c
gcc/tree.h
gcc/varasm.c
gcc/varpool.c [new file with mode: 0644]

index b4c1f1397e0a91479748090bb53b8687d1ad80ac..7d7cf2828c2554275dcfed5ae7a754226d1f646c 100644 (file)
@@ -1,3 +1,71 @@
+2006-12-11  Jan Hubicka  <jh@suse.cz>
+
+       Move all varpool routines out of cgraph/cgraphunit to varpool.c
+       * cgraph.c: Update comments.
+       (cgraph_varpool_hash,
+       cgraph_varpool_nodes, cgraph_varpool_last_needed_node
+       cgraph_varpool_node_name, cgraph_varpool_node,
+       cgraph_varpol_mode_for_asm, cgraph_varpool_mark_needed_node,
+       cgraph_variable_initializer_availability): Move to
+       varpool.c and drop cgraph_ prefixes.
+       (cgraph_varpool_enqueue_needed_node, cgraph_varpool_reset_queue,
+       cgraph_varpool_first_unanalyzed_node, cgraph_varpool_finalize_decl):
+       move to varpool.c; drop cgraph_ prefix; make static.
+       (dump_cgraph_varpool_node): Move to varpool.c under name
+       dump_varpool_node.
+       (dump_varpool, hash_varpool_node, eq_varpool_node,
+       decide_is_variable_needed): Move to varpool.c
+       (decl_assembler_name_equal): Move to tree.c.
+       (availability_names): Rename to ...
+       (cgraph_availability_names): ... this one.
+       (dump_cgraph_node): Update.
+       * cgraph.h: Reorder declarations now in varpool.c
+       (cgraph_vailablity_names): Declare.
+       (struct cgraph_varpool_node): Rename to ...
+       (struct varpool_node): ... this one.
+       (cgraph_varpool_first_unanalyzed_node, cgraph_varpool_nodes_queue,
+       cgraph_varpool_first_unanalyzed_node, cgraph_varpool_node,
+       cgraph_varpool_node_for_asm, cgraph_varpool_mark_needed_node,
+       cgraph_varpool_finalize_decl, cgraph_varpool_enqueue_needed_node,
+       cgraph_varpool_reset_queue, cgraph_varpool_assemble_pending_decls,
+       cgraph_variable_initializer_availability): Rename to ...
+       (varpool_first_unanalyzed_node, varpool_nodes_queue,
+       varpool_first_unanalyzed_node, varpool_node,
+       varpool_node_for_asm, varpool_mark_needed_node,
+       varpool_finalize_decl, varpool_enqueue_needed_node,
+       varpool_assemble_pending_decls, variable_initializer_availability):
+       Rename to ...
+       * tree.c (decl_assembler_name_equal): Move here from cgraph.c.
+       * tree.h (decl_assembler_name_equal): Declare.
+       * omp-low.c (lower_omp_critical): Update.
+       * ipa-reference (analyze_variable, static_execute): Likewise.
+       * toplev.c (wrapup_global_declaration_2, compile_file): Update.
+       * cgraphunit.c: Update comments.
+       (cgraph_varpool_assembled_nodes_queue): Move to varpool.c under name
+       varpool_assembled_nodes_queue.
+       (cgraph_varpool_analyze_pending_decls): Move to varpool.c under name
+       varpool_analyze_pending_decls.
+       (cgraph_varpool_remove_unreferenced_decls): Move to varpool.c under name
+       varpool_remove_unreferenced_decls.
+       (record_reference): Update.
+       (cgraph_create_edges): Update.
+       (record_referneces_in_initializer): New function.
+       (cgraph_varpool_assemble_decl): Move to varpool.c under name
+       varpool_assemble_decl; make global.
+       (cgraph_varpool_assemble_pending_decls): Move to varpool.c under name
+       varpool_assemble_pending_decls.
+       (process_function_and_variable_attributes, cgraph_finalize_compilation_unit,
+       struct cgraph_order_sort, cgraph_output_in_order,
+       cgraph_function_and_variable_invisibility, cgraph_optimize,
+       cgraph_increase_alignment): Update.
+       * dwarf2out.c (decls_for_scope): Likewise.
+       * ipa-type-escape.c (analyze_variable, type_escape_execute): Likewise.
+       * except.c (output_ttype): Likewise.
+       * varasm.c (mark_decl_referenced): Likewise.
+       (find_decl_and_mark_referenced, assemble_alias): update.
+       * Makefile.in: Add varpool.c, gt-varpool.c and remove gt-cgraphunit.c
+       * passes.c (rest_of_decl_compilation): Update.
+
 2006-12-11  Ira Rosen  <irar@il.ibm.com>
 
        * tree-vect-patterns.c (vect_recog_dot_prod_pattern): Use 
index 8da131d5ee0c6d3ce07db317f4de23872e0d1101..8613e6c40a05d207b8e87e68352d0486ee0df9ba 100644 (file)
@@ -1024,7 +1024,7 @@ OBJS-md = $(out_object_file)
 OBJS-archive = $(EXTRA_OBJS) $(host_hook_obj) tree-inline.o               \
   cgraph.o cgraphunit.o tree-nomudflap.o ipa.o ipa-inline.o                \
   ipa-utils.o ipa-reference.o ipa-pure-const.o ipa-type-escape.o           \
-  ipa-prop.o ipa-cp.o
+  ipa-prop.o ipa-cp.o varpool.o
 
 OBJS = $(OBJS-common) $(out_object_file) $(OBJS-archive)
 
@@ -2290,11 +2290,16 @@ cgraph.o : cgraph.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) \
    gt-cgraph.h output.h intl.h $(BASIC_BLOCK_H) debug.h $(HASHTAB_H) \
    $(TREE_INLINE_H) $(VARRAY_H) $(TREE_DUMP_H)
 cgraphunit.o : cgraphunit.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) \
+   $(TREE_H) langhooks.h $(TREE_INLINE_H) toplev.h $(FLAGS_H) $(GGC_H) \
+   $(TARGET_H) $(CGRAPH_H) intl.h pointer-set.h $(FUNCTION_H) $(TREE_GIMPLE_H) \
+   $(TREE_FLOW_H) tree-pass.h $(C_COMMON_H) debug.h $(DIAGNOSTIC_H) \
+   $(FIBHEAP_H) output.h $(PARAMS_H) $(RTL_H) $(TIMEVAR_H) ipa-prop.h 
+varpool.o : varpool.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) \
    $(TREE_H) langhooks.h $(TREE_INLINE_H) toplev.h $(FLAGS_H) $(GGC_H) \
    $(TARGET_H) $(CGRAPH_H) intl.h pointer-set.h $(FUNCTION_H) $(TREE_GIMPLE_H) \
    $(TREE_FLOW_H) tree-pass.h $(C_COMMON_H) debug.h $(DIAGNOSTIC_H) \
    $(FIBHEAP_H) output.h $(PARAMS_H) $(RTL_H) $(TIMEVAR_H) ipa-prop.h \
-   gt-cgraphunit.h
+   gt-varpool.h
 ipa.o : ipa.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(CGRAPH_H) 
 ipa-prop.o : ipa-prop.c $(CONFIG_H) $(SYSTEM_H) coretypes.h  \
    langhooks.h $(GGC_H) $(TARGET_H) $(CGRAPH_H) ipa-prop.h \
@@ -2873,8 +2878,8 @@ GTFILES = $(srcdir)/input.h $(srcdir)/coretypes.h \
   $(srcdir)/tree-profile.c $(srcdir)/tree-nested.c \
   $(srcdir)/ipa-reference.c $(srcdir)/tree-ssa-structalias.h \
   $(srcdir)/tree-ssa-structalias.c \
-  $(srcdir)/c-pragma.h $(srcdir)/omp-low.c \
-  $(srcdir)/targhooks.c $(srcdir)/cgraphunit.c $(out_file) \
+  $(srcdir)/c-pragma.h $(srcdir)/omp-low.c $(srcdir)/varpool.c \
+  $(srcdir)/targhooks.c $(out_file) \
   @all_gtfiles@
 
 GTFILES_FILES_LANGS = @all_gtfiles_files_langs@
@@ -2904,8 +2909,8 @@ gt-tree-mudflap.h gt-tree-vect-generic.h \
 gt-tree-profile.h gt-tree-ssa-address.h \
 gt-tree-iterator.h gt-gimplify.h \
 gt-tree-phinodes.h gt-tree-nested.h \
-gt-tree-ssa-propagate.h \
-gt-tree-ssa-structalias.h gt-ipa-inline.h gt-cgraphunit.h \
+gt-tree-ssa-propagate.h gt-varpool.h \
+gt-tree-ssa-structalias.h gt-ipa-inline.h \
 gt-stringpool.h gt-targhooks.h gt-omp-low.h : s-gtype ; @true
 
 define echo_quoted_to_gtyp
index 23429feb8e787b4996e802cd0503f766b12574b6..7706098ab3c96ab091a280abc31e88d88668140f 100644 (file)
@@ -19,7 +19,7 @@ along with GCC; see the file COPYING.  If not, write to the Free
 Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
 02110-1301, USA.  */
 
-/*  This file contains basic routines manipulating call graph and variable pool
+/*  This file contains basic routines manipulating call graph
 
 The callgraph:
 
@@ -69,15 +69,7 @@ The callgraph:
 
       Each edge has "inline_failed" field.  When the field is set to NULL,
       the call will be inlined.  When it is non-NULL it contains a reason
-      why inlining wasn't performed.
-
-
-The varpool data structure:
-
-    Varpool is used to maintain variables in similar manner as call-graph
-    is used for functions.  Most of the API is symmetric replacing cgraph
-    function prefix by cgraph_varpool  */
-
+      why inlining wasn't performed.  */
 
 #include "config.h"
 #include "system.h"
@@ -130,18 +122,6 @@ bool cgraph_global_info_ready = false;
 /* Set when the cgraph is fully build and the basic flags are computed.  */
 bool cgraph_function_flags_ready = false;
 
-/* Hash table used to convert declarations into nodes.  */
-static GTY((param_is (struct cgraph_varpool_node))) htab_t cgraph_varpool_hash;
-
-/* Queue of cgraph nodes scheduled to be lowered and output.  */
-struct cgraph_varpool_node *cgraph_varpool_nodes_queue, *cgraph_varpool_first_unanalyzed_node;
-
-/* The linked list of cgraph varpool nodes.  */
-struct cgraph_varpool_node *cgraph_varpool_nodes;
-
-/* End of the varpool queue.  Needs to be QTYed to work with PCH.  */
-static GTY(()) struct cgraph_varpool_node *cgraph_varpool_last_needed_node;
-
 /* Linked list of cgraph asm nodes.  */
 struct cgraph_asm_node *cgraph_asm_nodes;
 
@@ -243,40 +223,6 @@ cgraph_insert_node_to_hashtable (struct cgraph_node *node)
   *slot = node;
 }
 
-/* Compare ASMNAME with the DECL_ASSEMBLER_NAME of DECL.  */
-
-static bool
-decl_assembler_name_equal (tree decl, tree asmname)
-{
-  tree decl_asmname = DECL_ASSEMBLER_NAME (decl);
-
-  if (decl_asmname == asmname)
-    return true;
-
-  /* If the target assembler name was set by the user, things are trickier.
-     We have a leading '*' to begin with.  After that, it's arguable what
-     is the correct thing to do with -fleading-underscore.  Arguably, we've
-     historically been doing the wrong thing in assemble_alias by always
-     printing the leading underscore.  Since we're not changing that, make
-     sure user_label_prefix follows the '*' before matching.  */
-  if (IDENTIFIER_POINTER (decl_asmname)[0] == '*')
-    {
-      const char *decl_str = IDENTIFIER_POINTER (decl_asmname) + 1;
-      size_t ulp_len = strlen (user_label_prefix);
-
-      if (ulp_len == 0)
-       ;
-      else if (strncmp (decl_str, user_label_prefix, ulp_len) == 0)
-       decl_str += ulp_len;
-      else
-       return false;
-
-      return strcmp (decl_str, IDENTIFIER_POINTER (asmname)) == 0;
-    }
-
-  return false;
-}
-
 
 /* Return the cgraph node that has ASMNAME for its DECL_ASSEMBLER_NAME.
    Return NULL if there's no such node.  */
@@ -683,15 +629,8 @@ cgraph_node_name (struct cgraph_node *node)
   return lang_hooks.decl_printable_name (node->decl, 2);
 }
 
-/* Return name of the node used in debug output.  */
-static const char *
-cgraph_varpool_node_name (struct cgraph_varpool_node *node)
-{
-  return lang_hooks.decl_printable_name (node->decl, 2);
-}
-
 /* Names used to print out the availability enum.  */
-static const char * const availability_names[] =
+const char * const cgraph_availability_names[] =
   {"unset", "not_available", "overwrittable", "available", "local"};
 
 /* Dump given cgraph node.  */
@@ -706,7 +645,7 @@ dump_cgraph_node (FILE *f, struct cgraph_node *node)
             node->global.inlined_to->uid);
   if (cgraph_function_flags_ready)
     fprintf (f, " availability:%s",
-            availability_names [cgraph_function_body_availability (node)]);
+            cgraph_availability_names [cgraph_function_body_availability (node)]);
   if (node->master_clone && node->master_clone->uid != node->uid)
     fprintf (f, "(%i)", node->master_clone->uid);
   if (node->count)
@@ -785,100 +724,6 @@ dump_cgraph (FILE *f)
     dump_cgraph_node (f, node);
 }
 
-/* Dump given cgraph node.  */
-void
-dump_cgraph_varpool_node (FILE *f, struct cgraph_varpool_node *node)
-{
-  fprintf (f, "%s:", cgraph_varpool_node_name (node));
-  fprintf (f, " availability:%s",
-          cgraph_function_flags_ready
-          ? availability_names[cgraph_variable_initializer_availability (node)]
-          : "not-ready");
-  if (DECL_INITIAL (node->decl))
-    fprintf (f, " initialized");
-  if (node->needed)
-    fprintf (f, " needed");
-  if (node->analyzed)
-    fprintf (f, " analyzed");
-  if (node->finalized)
-    fprintf (f, " finalized");
-  if (node->output)
-    fprintf (f, " output");
-  if (node->externally_visible)
-    fprintf (f, " externally_visible");
-  fprintf (f, "\n");
-}
-
-/* Dump the callgraph.  */
-
-void
-dump_varpool (FILE *f)
-{
-  struct cgraph_varpool_node *node;
-
-  fprintf (f, "variable pool:\n\n");
-  for (node = cgraph_varpool_nodes; node; node = node->next_needed)
-    dump_cgraph_varpool_node (f, node);
-}
-
-/* Returns a hash code for P.  */
-
-static hashval_t
-hash_varpool_node (const void *p)
-{
-  const struct cgraph_varpool_node *n = (const struct cgraph_varpool_node *) p;
-  return (hashval_t) DECL_UID (n->decl);
-}
-
-/* Returns nonzero if P1 and P2 are equal.  */
-
-static int
-eq_varpool_node (const void *p1, const void *p2)
-{
-  const struct cgraph_varpool_node *n1 =
-    (const struct cgraph_varpool_node *) p1;
-  const struct cgraph_varpool_node *n2 =
-    (const struct cgraph_varpool_node *) p2;
-  return DECL_UID (n1->decl) == DECL_UID (n2->decl);
-}
-
-/* Return cgraph_varpool node assigned to DECL.  Create new one when needed.  */
-struct cgraph_varpool_node *
-cgraph_varpool_node (tree decl)
-{
-  struct cgraph_varpool_node key, *node, **slot;
-
-  gcc_assert (DECL_P (decl) && TREE_CODE (decl) != FUNCTION_DECL);
-
-  if (!cgraph_varpool_hash)
-    cgraph_varpool_hash = htab_create_ggc (10, hash_varpool_node,
-                                          eq_varpool_node, NULL);
-  key.decl = decl;
-  slot = (struct cgraph_varpool_node **)
-    htab_find_slot (cgraph_varpool_hash, &key, INSERT);
-  if (*slot)
-    return *slot;
-  node = GGC_CNEW (struct cgraph_varpool_node);
-  node->decl = decl;
-  node->order = cgraph_order++;
-  node->next = cgraph_varpool_nodes;
-  cgraph_varpool_nodes = node;
-  *slot = node;
-  return node;
-}
-
-struct cgraph_varpool_node *
-cgraph_varpool_node_for_asm (tree asmname)
-{
-  struct cgraph_varpool_node *node;
-
-  for (node = cgraph_varpool_nodes; node ; node = node->next)
-    if (decl_assembler_name_equal (node->decl, asmname))
-      return node;
-
-  return NULL;
-}
-
 /* Set the DECL_ASSEMBLER_NAME and update cgraph hashtables.  */
 void
 change_decl_assembler_name (tree decl, tree name)
@@ -898,116 +743,6 @@ change_decl_assembler_name (tree decl, tree name)
   SET_DECL_ASSEMBLER_NAME (decl, name);
 }
 
-/* Helper function for finalization code - add node into lists so it will
-   be analyzed and compiled.  */
-void
-cgraph_varpool_enqueue_needed_node (struct cgraph_varpool_node *node)
-{
-  if (cgraph_varpool_last_needed_node)
-    cgraph_varpool_last_needed_node->next_needed = node;
-  cgraph_varpool_last_needed_node = node;
-  node->next_needed = NULL;
-  if (!cgraph_varpool_nodes_queue)
-    cgraph_varpool_nodes_queue = node;
-  if (!cgraph_varpool_first_unanalyzed_node)
-    cgraph_varpool_first_unanalyzed_node = node;
-  notice_global_symbol (node->decl);
-}
-
-/* Reset the queue of needed nodes.  */
-void
-cgraph_varpool_reset_queue (void)
-{
-  cgraph_varpool_last_needed_node = NULL;
-  cgraph_varpool_nodes_queue = NULL;
-  cgraph_varpool_first_unanalyzed_node = NULL;
-}
-
-/* Notify finalize_compilation_unit that given node is reachable
-   or needed.  */
-void
-cgraph_varpool_mark_needed_node (struct cgraph_varpool_node *node)
-{
-  if (!node->needed && node->finalized
-      && !TREE_ASM_WRITTEN (node->decl))
-    cgraph_varpool_enqueue_needed_node (node);
-  node->needed = 1;
-}
-
-/* Determine if variable DECL is needed.  That is, visible to something
-   either outside this translation unit, something magic in the system
-   configury, or (if not doing unit-at-a-time) to something we haven't
-   seen yet.  */
-
-bool
-decide_is_variable_needed (struct cgraph_varpool_node *node, tree decl)
-{
-  /* If the user told us it is used, then it must be so.  */
-  if (node->externally_visible)
-    return true;
-  if (!flag_unit_at_a_time
-      && lookup_attribute ("used", DECL_ATTRIBUTES (decl)))
-    return true;
-
-  /* ??? If the assembler name is set by hand, it is possible to assemble
-     the name later after finalizing the function and the fact is noticed
-     in assemble_name then.  This is arguably a bug.  */
-  if (DECL_ASSEMBLER_NAME_SET_P (decl)
-      && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)))
-    return true;
-
-  /* If we decided it was needed before, but at the time we didn't have
-     the definition available, then it's still needed.  */
-  if (node->needed)
-    return true;
-
-  /* Externally visible variables must be output.  The exception is
-     COMDAT variables that must be output only when they are needed.  */
-  if (TREE_PUBLIC (decl) && !flag_whole_program && !DECL_COMDAT (decl)
-      && !DECL_EXTERNAL (decl))
-    return true;
-
-  /* When not reordering top level variables, we have to assume that
-     we are going to keep everything.  */
-  if (flag_unit_at_a_time && flag_toplevel_reorder)
-    return false;
-
-  /* We want to emit COMDAT variables only when absolutely necessary.  */
-  if (DECL_COMDAT (decl))
-    return false;
-  return true;
-}
-
-void
-cgraph_varpool_finalize_decl (tree decl)
-{
-  struct cgraph_varpool_node *node = cgraph_varpool_node (decl);
-
-  /* The first declaration of a variable that comes through this function
-     decides whether it is global (in C, has external linkage)
-     or local (in C, has internal linkage).  So do nothing more
-     if this function has already run.  */
-  if (node->finalized)
-    {
-      if (cgraph_global_info_ready || (!flag_unit_at_a_time && !flag_openmp))
-       cgraph_varpool_assemble_pending_decls ();
-      return;
-    }
-  if (node->needed)
-    cgraph_varpool_enqueue_needed_node (node);
-  node->finalized = true;
-
-  if (decide_is_variable_needed (node, decl))
-    cgraph_varpool_mark_needed_node (node);
-  /* Since we reclaim unreachable nodes at the end of every language
-     level unit, we need to be conservative about possible entry points
-     there.  */
-  else if (TREE_PUBLIC (decl) && !DECL_COMDAT (decl) && !DECL_EXTERNAL (decl))
-    cgraph_varpool_mark_needed_node (node);
-  if (cgraph_global_info_ready || (!flag_unit_at_a_time && !flag_openmp))
-    cgraph_varpool_assemble_pending_decls ();
-}
-
 /* Add a top-level asm statement to the list.  */
 
 struct cgraph_asm_node *
@@ -1181,25 +916,6 @@ cgraph_function_body_availability (struct cgraph_node *node)
   return avail;
 }
 
-/* Return variable availability.  See cgraph.h for description of individual
-   return values.  */
-enum availability
-cgraph_variable_initializer_availability (struct cgraph_varpool_node *node)
-{
-  gcc_assert (cgraph_function_flags_ready);
-  if (!node->finalized)
-    return AVAIL_NOT_AVAILABLE;
-  if (!TREE_PUBLIC (node->decl))
-    return AVAIL_AVAILABLE;
-  /* If the variable can be overwritten, return OVERWRITABLE.  Takes
-     care of at least two notable extensions - the COMDAT variables
-     used to share template instantiations in C++.  */
-  if (!(*targetm.binds_local_p) (node->decl) && !DECL_COMDAT (node->decl))
-    return AVAIL_OVERWRITABLE;
-  return AVAIL_AVAILABLE;
-}
-
-
 /* Add the function FNDECL to the call graph.  FNDECL is assumed to be
    in low GIMPLE form and ready to be processed by cgraph_finalize_function.
 
index 89655633d9c97ae464f42e6fd910a53e40b6e592..b60239c36629171199467c6e8568d8aa55586704 100644 (file)
@@ -46,6 +46,8 @@ enum availability
   AVAIL_LOCAL
 };
 
+extern const char * const cgraph_availability_names[];
+
 /* Information about the function collected locally.
    Available after function is analyzed.  */
 
@@ -204,16 +206,16 @@ typedef struct cgraph_edge *cgraph_edge_p;
 DEF_VEC_P(cgraph_edge_p);
 DEF_VEC_ALLOC_P(cgraph_edge_p,heap);
 
-/* The cgraph_varpool data structure.
-   Each static variable decl has assigned cgraph_varpool_node.  */
+/* The varpool data structure.
+   Each static variable decl has assigned varpool_node.  */
 
-struct cgraph_varpool_node GTY(())
+struct varpool_node GTY(())
 {
   tree decl;
-  /* Pointer to the next function in cgraph_varpool_nodes.  */
-  struct cgraph_varpool_node *next;
-  /* Pointer to the next function in cgraph_varpool_nodes_queue.  */
-  struct cgraph_varpool_node *next_needed;
+  /* Pointer to the next function in varpool_nodes.  */
+  struct varpool_node *next;
+  /* Pointer to the next function in varpool_nodes_queue.  */
+  struct varpool_node *next_needed;
   /* Ordering of all cgraph nodes.  */
   int order;
 
@@ -256,9 +258,6 @@ extern bool cgraph_function_flags_ready;
 extern GTY(()) struct cgraph_node *cgraph_nodes_queue;
 extern GTY(()) struct cgraph_node *cgraph_expand_queue;
 
-extern GTY(()) struct cgraph_varpool_node *cgraph_varpool_first_unanalyzed_node;
-extern GTY(()) struct cgraph_varpool_node *cgraph_varpool_nodes_queue;
-extern GTY(()) struct cgraph_varpool_node *cgraph_varpool_nodes;
 extern GTY(()) struct cgraph_asm_node *cgraph_asm_nodes;
 extern GTY(()) int cgraph_order;
 
@@ -266,8 +265,6 @@ extern GTY(()) int cgraph_order;
 void dump_cgraph (FILE *);
 void dump_cgraph_node (FILE *, struct cgraph_node *);
 void cgraph_insert_node_to_hashtable (struct cgraph_node *node);
-void dump_varpool (FILE *);
-void dump_cgraph_varpool_node (FILE *, struct cgraph_varpool_node *);
 void cgraph_remove_edge (struct cgraph_edge *);
 void cgraph_remove_node (struct cgraph_node *);
 void cgraph_node_remove_callees (struct cgraph_node *node);
@@ -288,28 +285,19 @@ struct cgraph_edge * cgraph_clone_edge (struct cgraph_edge *,
 struct cgraph_node * cgraph_clone_node (struct cgraph_node *, gcov_type,
                                        int, bool);
 
-struct cgraph_varpool_node *cgraph_varpool_node (tree);
-struct cgraph_varpool_node *cgraph_varpool_node_for_asm (tree asmname);
-void cgraph_varpool_mark_needed_node (struct cgraph_varpool_node *);
-void cgraph_varpool_finalize_decl (tree);
 void cgraph_redirect_edge_callee (struct cgraph_edge *, struct cgraph_node *);
 
 struct cgraph_asm_node *cgraph_add_asm_node (tree);
 
 bool cgraph_function_possibly_inlined_p (tree);
 void cgraph_unnest_node (struct cgraph_node *);
-void cgraph_varpool_enqueue_needed_node (struct cgraph_varpool_node *);
-void cgraph_varpool_reset_queue (void);
-bool decide_is_variable_needed (struct cgraph_varpool_node *, tree);
 
 enum availability cgraph_function_body_availability (struct cgraph_node *);
-enum availability cgraph_variable_initializer_availability (struct cgraph_varpool_node *);
 bool cgraph_is_master_clone (struct cgraph_node *);
 struct cgraph_node *cgraph_master_clone (struct cgraph_node *);
 void cgraph_add_new_function (tree);
 
 /* In cgraphunit.c  */
-bool cgraph_varpool_assemble_pending_decls (void);
 void cgraph_finalize_function (tree, bool);
 void cgraph_finalize_compilation_unit (void);
 void cgraph_optimize (void);
@@ -327,11 +315,33 @@ struct cgraph_node *cgraph_function_versioning (struct cgraph_node *,
                                                varray_type);
 void cgraph_analyze_function (struct cgraph_node *);
 struct cgraph_node *save_inline_function_body (struct cgraph_node *);
+void record_references_in_initializer (tree);
 
 /* In ipa.c  */
 bool cgraph_remove_unreachable_nodes (bool, FILE *);
 int cgraph_postorder (struct cgraph_node **);
 
+/* In varpool.c  */
+
+extern GTY(()) struct varpool_node *varpool_nodes_queue;
+extern GTY(()) struct varpool_node *varpool_nodes;
+
+struct varpool_node *varpool_node (tree);
+struct varpool_node *varpool_node_for_asm (tree asmname);
+void varpool_mark_needed_node (struct varpool_node *);
+void dump_varpool (FILE *);
+void dump_varpool_node (FILE *, struct varpool_node *);
+
+void varpool_finalize_decl (tree);
+bool decide_is_variable_needed (struct varpool_node *, tree);
+enum availability cgraph_variable_initializer_availability (struct varpool_node *);
+
+bool varpool_assemble_pending_decls (void);
+bool varpool_assemble_decl (struct varpool_node *node);
+bool varpool_analyze_pending_decls (void);
+void varpool_output_debug_info (void);
+void varpool_remove_unreferenced_decls (void);
+
 /* In ipa-inline.c  */
 bool cgraph_decide_inlining_incrementally (struct cgraph_node *, bool);
 void cgraph_clone_inlined_nodes (struct cgraph_edge *, bool, bool);
index 26399d368c95b61468d306223c0055549f2ef897..73015b6f29b68f50880d8df37150dfc58ca21c55 100644 (file)
@@ -35,7 +35,7 @@ Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
       (There is one exception needed for implementing GCC extern inline
        function.)
 
-    - cgraph_varpool_finalize_variable
+    - varpool_finalize_variable
 
       This function has same behavior as the above but is used for static
       variables.
@@ -60,7 +60,7 @@ Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
       modify calling conventions, do better inlining or similar optimizations.
 
     - cgraph_mark_needed_node
-    - cgraph_varpool_mark_needed_node
+    - varpool_mark_needed_node
 
       When function or variable is referenced by some hidden way the call-graph
       data structure must be updated accordingly by this function.
@@ -82,8 +82,8 @@ Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
       This function is used to expand function and pass it into RTL back-end.
       Front-end should not make any assumptions about when this function can be
       called.  In particular cgraph_assemble_pending_functions,
-      cgraph_varpool_assemble_pending_variables, cgraph_finalize_function,
-      cgraph_varpool_finalize_function, cgraph_optimize can cause arbitrarily
+      varpool_assemble_pending_variables, cgraph_finalize_function,
+      varpool_finalize_function, cgraph_optimize can cause arbitrarily
       previously finalized functions to be expanded.
 
     We implement two compilation modes.
@@ -168,9 +168,6 @@ static tree record_reference (tree *, int *, void *);
 static void cgraph_output_pending_asms (void);
 static void cgraph_increase_alignment (void);
 
-/* Lists all assembled variables to be sent to debugger output later on.  */
-static GTY(()) struct cgraph_varpool_node *cgraph_varpool_assembled_nodes_queue;
-
 /* Records tree nodes seen in record_reference.  Simply using
    walk_tree_without_duplicates doesn't guarantee each node is visited
    once because it gets a new htab upon each recursive call from
@@ -265,83 +262,6 @@ decide_is_function_needed (struct cgraph_node *node, tree decl)
   return false;
 }
 
-/* Walk the decls we marked as necessary and see if they reference new
-   variables or functions and add them into the worklists.  */
-static bool
-cgraph_varpool_analyze_pending_decls (void)
-{
-  bool changed = false;
-  timevar_push (TV_CGRAPH);
-
-  while (cgraph_varpool_first_unanalyzed_node)
-    {
-      tree decl = cgraph_varpool_first_unanalyzed_node->decl;
-
-      cgraph_varpool_first_unanalyzed_node->analyzed = true;
-
-      cgraph_varpool_first_unanalyzed_node = cgraph_varpool_first_unanalyzed_node->next_needed;
-
-      /* Compute the alignment early so function body expanders are
-        already informed about increased alignment.  */
-      align_variable (decl, 0);
-
-      if (DECL_INITIAL (decl))
-       {
-         visited_nodes = pointer_set_create ();
-         walk_tree (&DECL_INITIAL (decl), record_reference, NULL, visited_nodes);
-         pointer_set_destroy (visited_nodes);
-         visited_nodes = NULL;
-       }
-      changed = true;
-    }
-  timevar_pop (TV_CGRAPH);
-  return changed;
-}
-
-/* Optimization of function bodies might've rendered some variables as
-   unnecessary so we want to avoid these from being compiled.
-
-   This is done by pruning the queue and keeping only the variables that
-   really appear needed (ie they are either externally visible or referenced
-   by compiled function). Re-doing the reachability analysis on variables
-   brings back the remaining variables referenced by these.  */
-static void
-cgraph_varpool_remove_unreferenced_decls (void)
-{
-  struct cgraph_varpool_node *next, *node = cgraph_varpool_nodes_queue;
-
-  cgraph_varpool_reset_queue ();
-
-  if (errorcount || sorrycount)
-    return;
-
-  while (node)
-    {
-      tree decl = node->decl;
-      next = node->next_needed;
-      node->needed = 0;
-
-      if (node->finalized
-         && ((DECL_ASSEMBLER_NAME_SET_P (decl)
-              && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)))
-             || node->force_output
-             || decide_is_variable_needed (node, decl)
-             /* ??? Cgraph does not yet rule the world with an iron hand,
-                and does not control the emission of debug information.
-                After a variable has its DECL_RTL set, we must assume that
-                it may be referenced by the debug information, and we can
-                no longer elide it.  */
-             || DECL_RTL_SET_P (decl)))
-       cgraph_varpool_mark_needed_node (node);
-
-      node = next;
-    }
-  /* Make sure we mark alias targets as used targets.  */
-  finish_aliases_1 ();
-  cgraph_varpool_analyze_pending_decls ();
-}
-
-
 /* When not doing unit-at-a-time, output all functions enqueued.
    Return true when such a functions were found.  */
 
@@ -521,7 +441,7 @@ record_reference (tree *tp, int *walk_subtrees, void *data)
         after rtl has been generated.  */
       if (TREE_STATIC (t) || DECL_EXTERNAL (t))
        {
-         cgraph_varpool_mark_needed_node (cgraph_varpool_node (t));
+         varpool_mark_needed_node (varpool_node (t));
          if (lang_hooks.callgraph.analyze_expr)
            return lang_hooks.callgraph.analyze_expr (tp, walk_subtrees,
                                                      data);
@@ -602,7 +522,7 @@ cgraph_create_edges (struct cgraph_node *node, tree body)
       if (TREE_CODE (decl) == VAR_DECL
          && (TREE_STATIC (decl) && !DECL_EXTERNAL (decl))
          && flag_unit_at_a_time)
-       cgraph_varpool_finalize_decl (decl);
+       varpool_finalize_decl (decl);
       else if (TREE_CODE (decl) == VAR_DECL && DECL_INITIAL (decl))
        walk_tree (&DECL_INITIAL (decl), record_reference, node, visited_nodes);
     }
@@ -611,6 +531,16 @@ cgraph_create_edges (struct cgraph_node *node, tree body)
   visited_nodes = NULL;
 }
 
+void
+record_references_in_initializer (tree decl)
+{
+  visited_nodes = pointer_set_create ();
+  walk_tree (&DECL_INITIAL (decl), record_reference, NULL, visited_nodes);
+  pointer_set_destroy (visited_nodes);
+  visited_nodes = NULL;
+}
+
+
 /* Give initial reasons why inlining would fail.  Those gets
    either NULLified or usually overwritten by more precise reason
    later.  */
@@ -844,78 +774,6 @@ verify_cgraph (void)
     verify_cgraph_node (node);
 }
 
-/* Output one variable, if necessary.  Return whether we output it.  */
-static bool
-cgraph_varpool_assemble_decl (struct cgraph_varpool_node *node)
-{
-  tree decl = node->decl;
-
-  if (!TREE_ASM_WRITTEN (decl)
-      && !node->alias
-      && !DECL_EXTERNAL (decl)
-      && (TREE_CODE (decl) != VAR_DECL || !DECL_HAS_VALUE_EXPR_P (decl)))
-    {
-      assemble_variable (decl, 0, 1, 0);
-      return TREE_ASM_WRITTEN (decl);
-    }
-
-  return false;
-}
-
-/* Output all variables enqueued to be assembled.  */
-bool
-cgraph_varpool_assemble_pending_decls (void)
-{
-  bool changed = false;
-
-  if (errorcount || sorrycount)
-    return false;
-
-  /* EH might mark decls as needed during expansion.  This should be safe since
-     we don't create references to new function, but it should not be used
-     elsewhere.  */
-  cgraph_varpool_analyze_pending_decls ();
-
-  while (cgraph_varpool_nodes_queue)
-    {
-      struct cgraph_varpool_node *node = cgraph_varpool_nodes_queue;
-
-      cgraph_varpool_nodes_queue = cgraph_varpool_nodes_queue->next_needed;
-      if (cgraph_varpool_assemble_decl (node))
-       {
-         changed = true;
-         node->next_needed = cgraph_varpool_assembled_nodes_queue;
-         cgraph_varpool_assembled_nodes_queue = node;
-         node->finalized = 1;
-       }
-      else
-        node->next_needed = NULL;
-    }
-  return changed;
-}
-/* Output all variables enqueued to be assembled.  */
-static void
-cgraph_varpool_output_debug_info (void)
-{
-  timevar_push (TV_SYMOUT);
-  if (errorcount == 0 && sorrycount == 0)
-    while (cgraph_varpool_assembled_nodes_queue)
-      {
-       struct cgraph_varpool_node *node = cgraph_varpool_assembled_nodes_queue;
-
-       /* Local static variables are never seen by check_global_declarations
-          so we need to output debug info by hand.  */
-       if (DECL_CONTEXT (node->decl)
-           && (TREE_CODE (DECL_CONTEXT (node->decl)) == BLOCK
-               || TREE_CODE (DECL_CONTEXT (node->decl)) == FUNCTION_DECL)
-           && errorcount == 0 && sorrycount == 0)
-            (*debug_hooks->global_decl) (node->decl);
-       cgraph_varpool_assembled_nodes_queue = node->next_needed;
-       node->next_needed = 0;
-      }
-  timevar_pop (TV_SYMOUT);
-}
-
 /* Output all asm statements we have stored up to be output.  */
 
 static void
@@ -990,10 +848,10 @@ cgraph_analyze_function (struct cgraph_node *node)
 
 static void
 process_function_and_variable_attributes (struct cgraph_node *first,
-                                          struct cgraph_varpool_node *first_var)
+                                          struct varpool_node *first_var)
 {
   struct cgraph_node *node;
-  struct cgraph_varpool_node *vnode;
+  struct varpool_node *vnode;
 
   for (node = cgraph_nodes; node != first; node = node->next)
     {
@@ -1018,14 +876,14 @@ process_function_and_variable_attributes (struct cgraph_node *first,
            }
        }
     }
-  for (vnode = cgraph_varpool_nodes; vnode != first_var; vnode = vnode->next)
+  for (vnode = varpool_nodes; vnode != first_var; vnode = vnode->next)
     {
       tree decl = vnode->decl;
       if (lookup_attribute ("used", DECL_ATTRIBUTES (decl)))
        {
          mark_decl_referenced (decl);
          if (vnode->finalized)
-           cgraph_varpool_mark_needed_node (vnode);
+           varpool_mark_needed_node (vnode);
        }
       if (lookup_attribute ("externally_visible", DECL_ATTRIBUTES (decl)))
        {
@@ -1036,7 +894,7 @@ process_function_and_variable_attributes (struct cgraph_node *first,
          else
            {
              if (vnode->finalized)
-               cgraph_varpool_mark_needed_node (vnode);
+               varpool_mark_needed_node (vnode);
              vnode->externally_visible = true;
            }
        }
@@ -1053,7 +911,7 @@ cgraph_finalize_compilation_unit (void)
      intermodule optimization.  */
   static struct cgraph_node *first_analyzed;
   struct cgraph_node *first_processed = first_analyzed;
-  static struct cgraph_varpool_node *first_analyzed_var;
+  static struct varpool_node *first_analyzed_var;
 
   if (errorcount || sorrycount)
     return;
@@ -1064,7 +922,7 @@ cgraph_finalize_compilation_unit (void)
     {
       cgraph_output_pending_asms ();
       cgraph_assemble_pending_functions ();
-      cgraph_varpool_output_debug_info ();
+      varpool_output_debug_info ();
       return;
     }
 
@@ -1078,8 +936,8 @@ cgraph_finalize_compilation_unit (void)
   process_function_and_variable_attributes (first_processed,
                                            first_analyzed_var);
   first_processed = cgraph_nodes;
-  first_analyzed_var = cgraph_varpool_nodes;
-  cgraph_varpool_analyze_pending_decls ();
+  first_analyzed_var = varpool_nodes;
+  varpool_analyze_pending_decls ();
   if (cgraph_dump_file)
     {
       fprintf (cgraph_dump_file, "Initial entry points:");
@@ -1125,8 +983,8 @@ cgraph_finalize_compilation_unit (void)
       process_function_and_variable_attributes (first_processed,
                                                first_analyzed_var);
       first_processed = cgraph_nodes;
-      first_analyzed_var = cgraph_varpool_nodes;
-      cgraph_varpool_analyze_pending_decls ();
+      first_analyzed_var = varpool_nodes;
+      varpool_analyze_pending_decls ();
     }
 
   /* Collect entry points to the unit.  */
@@ -1328,7 +1186,7 @@ struct cgraph_order_sort
   union
   {
     struct cgraph_node *f;
-    struct cgraph_varpool_node *v;
+    struct varpool_node *v;
     struct cgraph_asm_node *a;
   } u;
 };
@@ -1347,7 +1205,7 @@ cgraph_output_in_order (void)
   struct cgraph_order_sort *nodes;
   int i;
   struct cgraph_node *pf;
-  struct cgraph_varpool_node *pv;
+  struct varpool_node *pv;
   struct cgraph_asm_node *pa;
 
   max = cgraph_order;
@@ -1355,7 +1213,7 @@ cgraph_output_in_order (void)
   nodes = (struct cgraph_order_sort *) alloca (size);
   memset (nodes, 0, size);
 
-  cgraph_varpool_analyze_pending_decls ();
+  varpool_analyze_pending_decls ();
 
   for (pf = cgraph_nodes; pf; pf = pf->next)
     {
@@ -1368,7 +1226,7 @@ cgraph_output_in_order (void)
        }
     }
 
-  for (pv = cgraph_varpool_nodes_queue; pv; pv = pv->next_needed)
+  for (pv = varpool_nodes_queue; pv; pv = pv->next_needed)
     {
       i = pv->order;
       gcc_assert (nodes[i].kind == ORDER_UNDEFINED);
@@ -1394,7 +1252,7 @@ cgraph_output_in_order (void)
          break;
 
        case ORDER_VAR:
-         cgraph_varpool_assemble_decl (nodes[i].u.v);
+         varpool_assemble_decl (nodes[i].u.v);
          break;
 
        case ORDER_ASM:
@@ -1427,7 +1285,7 @@ static void
 cgraph_function_and_variable_visibility (void)
 {
   struct cgraph_node *node;
-  struct cgraph_varpool_node *vnode;
+  struct varpool_node *vnode;
 
   for (node = cgraph_nodes; node; node = node->next)
     {
@@ -1447,7 +1305,7 @@ cgraph_function_and_variable_visibility (void)
                           && !DECL_EXTERNAL (node->decl)
                           && !node->local.externally_visible);
     }
-  for (vnode = cgraph_varpool_nodes_queue; vnode; vnode = vnode->next_needed)
+  for (vnode = varpool_nodes_queue; vnode; vnode = vnode->next_needed)
     {
       if (vnode->needed
          && !flag_whole_program
@@ -1525,8 +1383,8 @@ cgraph_optimize (void)
   if (!flag_unit_at_a_time)
     {
       cgraph_output_pending_asms ();
-      cgraph_varpool_assemble_pending_decls ();
-      cgraph_varpool_output_debug_info ();
+      varpool_assemble_pending_decls ();
+      varpool_output_debug_info ();
       return;
     }
 
@@ -1534,7 +1392,7 @@ cgraph_optimize (void)
 
   /* Frontend may output common variables after the unit has been finalized.
      It is safe to deal with them here as they are always zero initialized.  */
-  cgraph_varpool_analyze_pending_decls ();
+  varpool_analyze_pending_decls ();
 
   timevar_push (TV_CGRAPHOPT);
   if (!quiet_flag)
@@ -1580,10 +1438,10 @@ cgraph_optimize (void)
       cgraph_output_pending_asms ();
 
       cgraph_expand_all_functions ();
-      cgraph_varpool_remove_unreferenced_decls ();
+      varpool_remove_unreferenced_decls ();
 
-      cgraph_varpool_assemble_pending_decls ();
-      cgraph_varpool_output_debug_info ();
+      varpool_assemble_pending_decls ();
+      varpool_output_debug_info ();
     }
 
   if (cgraph_dump_file)
@@ -1627,10 +1485,10 @@ cgraph_increase_alignment (void)
 {
   if (flag_section_anchors && flag_tree_vectorize)
     {
-      struct cgraph_varpool_node *vnode;
+      struct varpool_node *vnode;
 
       /* Increase the alignment of all global arrays for vectorization.  */
-      for (vnode = cgraph_varpool_nodes_queue;
+      for (vnode = varpool_nodes_queue;
            vnode;
            vnode = vnode->next_needed)
         {
@@ -1923,5 +1781,3 @@ save_inline_function_body (struct cgraph_node *node)
 #endif
   return first_clone;
 }
-
-#include "gt-cgraphunit.h"
index e72ffeb51679dfdbef2eba9b359451836c9feaea..54b244ce1f7e9665a76413a7404c0e797771d890 100644 (file)
@@ -1,3 +1,7 @@
+2006-12-11  Jan Hubicka  <jh@suse.cz>
+
+       * decl2.c (var_finalized_p): Update for renamed varpool functions.
+
 2006-12-09  Zack Weinberg  <zackw@panix.com>
 
        * parser.c (yydebug, enum pragma_omp_clause): Delete.
index b2a97ff9dc2c213372ba6ee93f85bb9b943d7c13..0c0695e8b7f9dadd773119ebe6f17ee9f1b0a19a 100644 (file)
@@ -1410,7 +1410,7 @@ import_export_class (tree ctype)
 static bool
 var_finalized_p (tree var)
 {
-  return cgraph_varpool_node (var)->finalized;
+  return varpool_node (var)->finalized;
 }
 
 /* DECL is a VAR_DECL or FUNCTION_DECL which, for whatever reason,
index 9a4903bdb48e8c4ef3f3ab145ef72d6f9a04390e..a9f6308a934031507b04948ec5e7506ac971b585 100644 (file)
@@ -12926,7 +12926,7 @@ decls_for_scope (tree stmt, dw_die_ref context_die, int depth)
            add_child_die (context_die, die);
          /* Do not produce debug information for static variables since
             these might be optimized out.  We are called for these later
-            in cgraph_varpool_analyze_pending_decls. */
+            in varpool_analyze_pending_decls. */
          if (TREE_CODE (decl) == VAR_DECL && TREE_STATIC (decl))
            ;
          else
index c51307ba3353b5bb3df4915db9c1a5bb77746d76..9f40dc47694419622f270c4a80252c05dfbea928 100644 (file)
@@ -3581,7 +3581,7 @@ output_ttype (tree type, int tt_format, int tt_format_size)
     value = const0_rtx;
   else
     {
-      struct cgraph_varpool_node *node;
+      struct varpool_node *node;
 
       type = lookup_type_for_runtime (type);
       value = expand_expr (type, NULL_RTX, VOIDmode, EXPAND_INITIALIZER);
@@ -3595,9 +3595,9 @@ output_ttype (tree type, int tt_format, int tt_format_size)
          type = TREE_OPERAND (type, 0);
          if (TREE_CODE (type) == VAR_DECL)
            {
-             node = cgraph_varpool_node (type);
+             node = varpool_node (type);
              if (node)
-               cgraph_varpool_mark_needed_node (node);
+               varpool_mark_needed_node (node);
              public = TREE_PUBLIC (type);
            }
        }
index 16845eef8f50c22f694380c19766e26f3f9e03f4..e3b685206ebed59e4c43ee2d7c9394c4e211011d 100644 (file)
@@ -1,3 +1,7 @@
+2006-12-11  Jan Hubicka  <jh@suse.cz>
+
+       * f59-lang.c (gfc_expand_function): Update for renamed varpool functions.
+
 2006-12-10  Tobias Burnus  <burnus@net-b.de>
 
        * gfortran.texi: Update Fortran 2003 section.
index 11513186c046869c0ad37ff213475c7c55243a72..4caaa1a63c315e724b3f77c8b216df8abb6481d8 100644 (file)
@@ -226,7 +226,7 @@ gfc_expand_function (tree fndecl)
                && TREE_CODE (TREE_OPERAND (expr, 0)) == VAR_DECL
                && TREE_CODE (TREE_TYPE (TREE_OPERAND (expr, 0)))
                   == UNION_TYPE
-               && cgraph_varpool_node (TREE_OPERAND (expr, 0))->needed
+               && varpool_node (TREE_OPERAND (expr, 0))->needed
                && errorcount == 0 && sorrycount == 0)
              {
                timevar_push (TV_SYMOUT);
index 9780acf74700cc0cef3b43f2ecee562397509e6d..9427fd5db8c6a3ea65e5119531e66151120cf453 100644 (file)
@@ -770,7 +770,7 @@ ipa_init (void)
    to variables defined within this unit.  */
 
 static void 
-analyze_variable (struct cgraph_varpool_node *vnode)
+analyze_variable (struct varpool_node *vnode)
 {
   tree global = vnode->decl;
   if (TREE_CODE (global) == VAR_DECL)
@@ -892,7 +892,7 @@ static unsigned int
 static_execute (void)
 {
   struct cgraph_node *node;
-  struct cgraph_varpool_node *vnode;
+  struct varpool_node *vnode;
   struct cgraph_node *w;
   struct cgraph_node **order =
     xcalloc (cgraph_n_nodes, sizeof (struct cgraph_node *));
@@ -902,7 +902,7 @@ static_execute (void)
   ipa_init ();
 
   /* Process all of the variables first.  */
-  for (vnode = cgraph_varpool_nodes_queue; vnode; vnode = vnode->next_needed)
+  for (vnode = varpool_nodes_queue; vnode; vnode = vnode->next_needed)
     analyze_variable (vnode);
 
   /* Process all of the functions next. 
index 0b0c19a7e91de8adbdc264667430936b47f48eab..faddb7754cda47252238e2f4a66a07d63dfd3000 100644 (file)
@@ -1337,7 +1337,7 @@ ipa_init (void)
    to variables defined within this unit.  */
 
 static void 
-analyze_variable (struct cgraph_varpool_node *vnode)
+analyze_variable (struct varpool_node *vnode)
 {
   tree global = vnode->decl;
   tree type = get_canon_type (TREE_TYPE (global), false, false);
@@ -1674,7 +1674,7 @@ static unsigned int
 type_escape_execute (void)
 {
   struct cgraph_node *node;
-  struct cgraph_varpool_node *vnode;
+  struct varpool_node *vnode;
   unsigned int i;
   bitmap_iterator bi;
   splay_tree_node result;
@@ -1682,7 +1682,7 @@ type_escape_execute (void)
   ipa_init ();
 
   /* Process all of the variables first.  */
-  for (vnode = cgraph_varpool_nodes_queue; vnode; vnode = vnode->next_needed)
+  for (vnode = varpool_nodes_queue; vnode; vnode = vnode->next_needed)
     analyze_variable (vnode);
 
   /* Process all of the functions. next
index 46d7d1de1de84c269100b515212b5502c809d1f4..edd58d47e2d4ffa97dc309327e28a9f036d676d8 100644 (file)
@@ -1,3 +1,8 @@
+2006-11-12  Jan Hubicka  <jh@suse.cz>
+
+       * resource.c (compile_resource_data): Update for new varpool names.
+       * java/class.c (build_utf8_ref): Likewise.
+
 2006-11-12  David Daney  <ddaney@avtrex.com>
 
        PR java/29805
index cdb298e77a1e0f494f7478c27827cf322b7fd3a0..b1faafc616c30dc460463677901f0cee4725df60 100644 (file)
@@ -937,7 +937,7 @@ build_utf8_ref (tree name)
   layout_decl (decl, 0);
   pushdecl (decl);
   rest_of_decl_compilation (decl, global_bindings_p (), 0);
-  cgraph_varpool_mark_needed_node (cgraph_varpool_node (decl));
+  varpool_mark_needed_node (varpool_node (decl));
   utf8_decl_list = decl;
   ref = build1 (ADDR_EXPR, utf8const_ptr_type, decl);
   IDENTIFIER_UTF8_REF (name) = ref;
index fd3d4946c4eab562d1b31813cb82319dcfb64f5b..b0b941cc8dcafb7ec4022481fcbb5d1b7be89783 100644 (file)
@@ -93,7 +93,7 @@ compile_resource_data (const char *name, const char *buffer, int length)
   layout_decl (decl, 0);
   pushdecl (decl);
   rest_of_decl_compilation (decl, global_bindings_p (), 0);
-  cgraph_varpool_finalize_decl (decl);
+  varpool_finalize_decl (decl);
 
   resources = tree_cons (NULL_TREE, decl, resources);
 }
index 625ac37496784a82138952381b02d22eeca79cbe..141efa04b7e1e33a15158a8f7cbb0e69ce9cecb4 100644 (file)
@@ -3929,7 +3929,7 @@ lower_omp_critical (tree *stmt_p, omp_context *ctx)
          DECL_COMMON (decl) = 1;
          DECL_ARTIFICIAL (decl) = 1;
          DECL_IGNORED_P (decl) = 1;
-         cgraph_varpool_finalize_decl (decl);
+         varpool_finalize_decl (decl);
 
          splay_tree_insert (critical_name_mutexes, (splay_tree_key) name,
                             (splay_tree_value) decl);
index 13b3b33e972fdbefd0ef54a80edc53c7d9bbeaac..e5faaa464f39c36271deb80f8ac860c46d885946 100644 (file)
@@ -159,7 +159,7 @@ rest_of_decl_compilation (tree decl,
          && !DECL_EXTERNAL (decl))
        {
          if (TREE_CODE (decl) != FUNCTION_DECL)
-           cgraph_varpool_finalize_decl (decl);
+           varpool_finalize_decl (decl);
          else
            assemble_variable (decl, top_level, at_end, 0);
        }
@@ -186,7 +186,7 @@ rest_of_decl_compilation (tree decl,
 
   /* Let cgraph know about the existence of variables.  */
   if (TREE_CODE (decl) == VAR_DECL && !DECL_EXTERNAL (decl))
-    cgraph_varpool_node (decl);
+    varpool_node (decl);
 }
 
 /* Called after finishing a record, union or enumeral type.  */
index 5fd8c4d3b4c7c76cdb1eeffd7d59423d0f868723..0aa6f6cf3ead55e67048cf74749401cfec73112b 100644 (file)
@@ -751,9 +751,9 @@ wrapup_global_declaration_2 (tree decl)
 
   if (TREE_CODE (decl) == VAR_DECL && TREE_STATIC (decl))
     {
-      struct cgraph_varpool_node *node;
+      struct varpool_node *node;
       bool needed = true;
-      node = cgraph_varpool_node (decl);
+      node = varpool_node (decl);
 
       if (node->finalized)
        needed = false;
@@ -1042,7 +1042,7 @@ compile_file (void)
   if (errorcount || sorrycount)
     return;
 
-  cgraph_varpool_assemble_pending_decls ();
+  varpool_assemble_pending_decls ();
   finish_aliases_2 ();
 
   /* This must occur after the loop to output deferred functions.
index 68aa58f9619e4533eb7468093feac4c8c51faf3c..2c6f3b855b0919f56af610bcf7c559e5bd74bc1f 100644 (file)
@@ -307,6 +307,40 @@ decl_assembler_name (tree decl)
   return DECL_WITH_VIS_CHECK (decl)->decl_with_vis.assembler_name;
 }
 
+/* Compare ASMNAME with the DECL_ASSEMBLER_NAME of DECL.  */
+
+bool
+decl_assembler_name_equal (tree decl, tree asmname)
+{
+  tree decl_asmname = DECL_ASSEMBLER_NAME (decl);
+
+  if (decl_asmname == asmname)
+    return true;
+
+  /* If the target assembler name was set by the user, things are trickier.
+     We have a leading '*' to begin with.  After that, it's arguable what
+     is the correct thing to do with -fleading-underscore.  Arguably, we've
+     historically been doing the wrong thing in assemble_alias by always
+     printing the leading underscore.  Since we're not changing that, make
+     sure user_label_prefix follows the '*' before matching.  */
+  if (IDENTIFIER_POINTER (decl_asmname)[0] == '*')
+    {
+      const char *decl_str = IDENTIFIER_POINTER (decl_asmname) + 1;
+      size_t ulp_len = strlen (user_label_prefix);
+
+      if (ulp_len == 0)
+       ;
+      else if (strncmp (decl_str, user_label_prefix, ulp_len) == 0)
+       decl_str += ulp_len;
+      else
+       return false;
+
+      return strcmp (decl_str, IDENTIFIER_POINTER (asmname)) == 0;
+    }
+
+  return false;
+}
+
 /* Compute the number of bytes occupied by a tree with code CODE.
    This function cannot be used for TREE_VEC, PHI_NODE, or STRING_CST
    codes, which are of variable length.  */
index 4e42c9b1e20c364d3699097e0670ae87521578d3..389ea16f75a7a5a6b0afbcb8a67c783ef3ab5a48 100644 (file)
@@ -3496,6 +3496,7 @@ enum ptrmemfunc_vbit_where_t
 #define NULL_TREE (tree) NULL
 
 extern tree decl_assembler_name (tree);
+extern bool decl_assembler_name_equal (tree decl, tree asmname);
 
 /* Compute the number of bytes occupied by 'node'.  This routine only
    looks at TREE_CODE and, if the code is TREE_VEC, TREE_VEC_LENGTH.  */
index 1e7af0e5b5d70391651a904fa21bdd2b72c80ff6..50487d283ffcf9d92a3b50342887db082a15f98f 100644 (file)
@@ -2018,8 +2018,8 @@ mark_decl_referenced (tree decl)
     }
   else if (TREE_CODE (decl) == VAR_DECL)
     {
-      struct cgraph_varpool_node *node = cgraph_varpool_node (decl);
-      cgraph_varpool_mark_needed_node (node);
+      struct varpool_node *node = varpool_node (decl);
+      varpool_mark_needed_node (node);
       /* C++ frontend use mark_decl_references to force COMDAT variables
          to be output that might appear dead otherwise.  */
       node->force_output = true;
@@ -4808,17 +4808,17 @@ static tree
 find_decl_and_mark_needed (tree decl, tree target)
 {
   struct cgraph_node *fnode = NULL;
-  struct cgraph_varpool_node *vnode = NULL;
+  struct varpool_node *vnode = NULL;
 
   if (TREE_CODE (decl) == FUNCTION_DECL)
     {
       fnode = cgraph_node_for_asm (target);
       if (fnode == NULL)
-       vnode = cgraph_varpool_node_for_asm (target);
+       vnode = varpool_node_for_asm (target);
     }
   else
     {
-      vnode = cgraph_varpool_node_for_asm (target);
+      vnode = varpool_node_for_asm (target);
       if (vnode == NULL)
        fnode = cgraph_node_for_asm (target);
     }
@@ -4836,7 +4836,7 @@ find_decl_and_mark_needed (tree decl, tree target)
     }
   else if (vnode)
     {
-      cgraph_varpool_mark_needed_node (vnode);
+      varpool_mark_needed_node (vnode);
       return vnode->decl;
     }
   else
@@ -5029,7 +5029,7 @@ assemble_alias (tree decl, tree target)
   if (TREE_CODE (decl) == FUNCTION_DECL)
     cgraph_node (decl)->alias = true;
   else
-    cgraph_varpool_node (decl)->alias = true;
+    varpool_node (decl)->alias = true;
 
   /* If the target has already been emitted, we don't have to queue the
      alias.  This saves a tad o memory.  */
diff --git a/gcc/varpool.c b/gcc/varpool.c
new file mode 100644 (file)
index 0000000..2c3a43e
--- /dev/null
@@ -0,0 +1,451 @@
+/* Callgraph handling code.
+   Copyright (C) 2003, 2004, 2005, 2006 Free Software Foundation, Inc.
+   Contributed by Jan Hubicka
+
+This file is part of GCC.
+
+GCC is free software; you can redistribute it and/or modify it under
+the terms of the GNU General Public License as published by the Free
+Software Foundation; either version 2, or (at your option) any later
+version.
+
+GCC is distributed in the hope that it will be useful, but WITHOUT ANY
+WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You should have received a copy of the GNU General Public License
+along with GCC; see the file COPYING.  If not, write to the Free
+Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301, USA.  */
+
+#include "config.h"
+#include "system.h"
+#include "coretypes.h"
+#include "tm.h"
+#include "tree.h"
+#include "cgraph.h"
+#include "langhooks.h"
+#include "diagnostic.h"
+#include "hashtab.h"
+#include "ggc.h"
+#include "timevar.h"
+#include "debug.h" 
+#include "target.h"
+#include "output.h"
+
+/*  This file contains basic routines manipulating variable pool.
+
+    Varpool acts as interface in between the front-end and middle-end
+    and drives the decision process on what variables and when are
+    going to be compiled.
+
+    The varpool nodes are alocated lazilly for declarations
+    either by frontend or at callgraph construction time.
+    All variables supposed to be output into final file needs to be
+    explicitely marked by frontend via VARPOOL_FINALIZE_DECL function.  */
+
+/* Hash table used to convert declarations into nodes.  */
+static GTY((param_is (struct varpool_node))) htab_t varpool_hash;
+
+/* The linked list of cgraph varpool nodes.
+   Linked via node->next pointer.  */
+struct varpool_node *varpool_nodes;
+
+/* Queue of cgraph nodes scheduled to be lowered and output.
+   The queue is maintained via mark_needed_node, linked via node->next_needed
+   pointer. 
+
+   LAST_NNEDED_NODE points to the end of queue, so it can be maintained in forward
+   order.  QTY is needed to make it friendly to PCH.
+   During unit-at-a-time compilation we construct the queue of needed variables
+   twice: first time it is during cgraph construction, second time it is at the
+   end of compilation in VARPOOL_REMOVE_UNREFERENCED_DECLS so we can avoid
+   optimized out variables being output.
+   
+   Each variable is thus first analyzed and then later possibly output.  
+   FIRST_UNANALYZED_NODE points to first node in queue that was not analyzed
+   yet and is moved via VARPOOL_ANALYZE_PENDING_DECLS.  */
+   
+struct varpool_node *varpool_nodes_queue;
+static GTY(()) struct varpool_node *varpool_last_needed_node;
+static GTY(()) struct varpool_node *varpool_first_unanalyzed_node;
+
+/* Lists all assembled variables to be sent to debugger output later on.  */
+static GTY(()) struct varpool_node *varpool_assembled_nodes_queue;
+
+/* Return name of the node used in debug output.  */
+static const char *
+varpool_node_name (struct varpool_node *node)
+{
+  return lang_hooks.decl_printable_name (node->decl, 2);
+}
+
+/* Returns a hash code for P.  */
+static hashval_t
+hash_varpool_node (const void *p)
+{
+  const struct varpool_node *n = (const struct varpool_node *) p;
+  return (hashval_t) DECL_UID (n->decl);
+}
+
+/* Returns nonzero if P1 and P2 are equal.  */
+static int
+eq_varpool_node (const void *p1, const void *p2)
+{
+  const struct varpool_node *n1 =
+    (const struct varpool_node *) p1;
+  const struct varpool_node *n2 =
+    (const struct varpool_node *) p2;
+  return DECL_UID (n1->decl) == DECL_UID (n2->decl);
+}
+
+/* Return varpool node assigned to DECL.  Create new one when needed.  */
+struct varpool_node *
+varpool_node (tree decl)
+{
+  struct varpool_node key, *node, **slot;
+
+  gcc_assert (DECL_P (decl) && TREE_CODE (decl) != FUNCTION_DECL);
+
+  if (!varpool_hash)
+    varpool_hash = htab_create_ggc (10, hash_varpool_node,
+                                          eq_varpool_node, NULL);
+  key.decl = decl;
+  slot = (struct varpool_node **)
+    htab_find_slot (varpool_hash, &key, INSERT);
+  if (*slot)
+    return *slot;
+  node = GGC_CNEW (struct varpool_node);
+  node->decl = decl;
+  node->order = cgraph_order++;
+  node->next = varpool_nodes;
+  varpool_nodes = node;
+  *slot = node;
+  return node;
+}
+
+/* Dump given cgraph node.  */
+void
+dump_varpool_node (FILE *f, struct varpool_node *node)
+{
+  fprintf (f, "%s:", varpool_node_name (node));
+  fprintf (f, " availability:%s",
+          cgraph_function_flags_ready
+          ? cgraph_availability_names[cgraph_variable_initializer_availability (node)]
+          : "not-ready");
+  if (DECL_INITIAL (node->decl))
+    fprintf (f, " initialized");
+  if (node->needed)
+    fprintf (f, " needed");
+  if (node->analyzed)
+    fprintf (f, " analyzed");
+  if (node->finalized)
+    fprintf (f, " finalized");
+  if (node->output)
+    fprintf (f, " output");
+  if (node->externally_visible)
+    fprintf (f, " externally_visible");
+  fprintf (f, "\n");
+}
+
+/* Dump the variable pool.  */
+void
+dump_varpool (FILE *f)
+{
+  struct varpool_node *node;
+
+  fprintf (f, "variable pool:\n\n");
+  for (node = varpool_nodes; node; node = node->next_needed)
+    dump_varpool_node (f, node);
+}
+
+/* Given an assembler name, lookup node.  */
+struct varpool_node *
+varpool_node_for_asm (tree asmname)
+{
+  struct varpool_node *node;
+
+  for (node = varpool_nodes; node ; node = node->next)
+    if (decl_assembler_name_equal (node->decl, asmname))
+      return node;
+
+  return NULL;
+}
+
+/* Helper function for finalization code - add node into lists so it will
+   be analyzed and compiled.  */
+static void
+varpool_enqueue_needed_node (struct varpool_node *node)
+{
+  if (varpool_last_needed_node)
+    varpool_last_needed_node->next_needed = node;
+  varpool_last_needed_node = node;
+  node->next_needed = NULL;
+  if (!varpool_nodes_queue)
+    varpool_nodes_queue = node;
+  if (!varpool_first_unanalyzed_node)
+    varpool_first_unanalyzed_node = node;
+  notice_global_symbol (node->decl);
+}
+
+/* Notify finalize_compilation_unit that given node is reachable
+   or needed.  */
+void
+varpool_mark_needed_node (struct varpool_node *node)
+{
+  if (!node->needed && node->finalized
+      && !TREE_ASM_WRITTEN (node->decl))
+    varpool_enqueue_needed_node (node);
+  node->needed = 1;
+}
+
+/* Reset the queue of needed nodes.  */
+static void
+varpool_reset_queue (void)
+{
+  varpool_last_needed_node = NULL;
+  varpool_nodes_queue = NULL;
+  varpool_first_unanalyzed_node = NULL;
+}
+
+/* Determine if variable DECL is needed.  That is, visible to something
+   either outside this translation unit, something magic in the system
+   configury, or (if not doing unit-at-a-time) to something we haven't
+   seen yet.  */
+bool
+decide_is_variable_needed (struct varpool_node *node, tree decl)
+{
+  /* If the user told us it is used, then it must be so.  */
+  if (node->externally_visible)
+    return true;
+  if (!flag_unit_at_a_time
+      && lookup_attribute ("used", DECL_ATTRIBUTES (decl)))
+    return true;
+
+  /* ??? If the assembler name is set by hand, it is possible to assemble
+     the name later after finalizing the function and the fact is noticed
+     in assemble_name then.  This is arguably a bug.  */
+  if (DECL_ASSEMBLER_NAME_SET_P (decl)
+      && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)))
+    return true;
+
+  /* If we decided it was needed before, but at the time we didn't have
+     the definition available, then it's still needed.  */
+  if (node->needed)
+    return true;
+
+  /* Externally visible variables must be output.  The exception is
+     COMDAT variables that must be output only when they are needed.  */
+  if (TREE_PUBLIC (decl) && !flag_whole_program && !DECL_COMDAT (decl)
+      && !DECL_EXTERNAL (decl))
+    return true;
+
+  /* When not reordering top level variables, we have to assume that
+     we are going to keep everything.  */
+  if (flag_unit_at_a_time && flag_toplevel_reorder)
+    return false;
+
+  /* We want to emit COMDAT variables only when absolutely necessary.  */
+  if (DECL_COMDAT (decl))
+    return false;
+  return true;
+}
+
+/* Mark DECL as finalized.  By finalizing the declaration, frontend instruct the
+   middle end to output the variable to asm file, if needed or externally
+   visible.  */
+void
+varpool_finalize_decl (tree decl)
+{
+  struct varpool_node *node = varpool_node (decl);
+
+  /* The first declaration of a variable that comes through this function
+     decides whether it is global (in C, has external linkage)
+     or local (in C, has internal linkage).  So do nothing more
+     if this function has already run.  */
+  if (node->finalized)
+    {
+      if (cgraph_global_info_ready || (!flag_unit_at_a_time && !flag_openmp))
+       varpool_assemble_pending_decls ();
+      return;
+    }
+  if (node->needed)
+    varpool_enqueue_needed_node (node);
+  node->finalized = true;
+
+  if (decide_is_variable_needed (node, decl))
+    varpool_mark_needed_node (node);
+  /* Since we reclaim unreachable nodes at the end of every language
+     level unit, we need to be conservative about possible entry points
+     there.  */
+  else if (TREE_PUBLIC (decl) && !DECL_COMDAT (decl) && !DECL_EXTERNAL (decl))
+    varpool_mark_needed_node (node);
+  if (cgraph_global_info_ready || (!flag_unit_at_a_time && !flag_openmp))
+    varpool_assemble_pending_decls ();
+}
+
+/* Return variable availability.  See cgraph.h for description of individual
+   return values.  */
+enum availability
+cgraph_variable_initializer_availability (struct varpool_node *node)
+{
+  gcc_assert (cgraph_function_flags_ready);
+  if (!node->finalized)
+    return AVAIL_NOT_AVAILABLE;
+  if (!TREE_PUBLIC (node->decl))
+    return AVAIL_AVAILABLE;
+  /* If the variable can be overwritten, return OVERWRITABLE.  Takes
+     care of at least two notable extensions - the COMDAT variables
+     used to share template instantiations in C++.  */
+  if (!(*targetm.binds_local_p) (node->decl) && !DECL_COMDAT (node->decl))
+    return AVAIL_OVERWRITABLE;
+  return AVAIL_AVAILABLE;
+}
+
+/* Walk the decls we marked as necessary and see if they reference new
+   variables or functions and add them into the worklists.  */
+bool
+varpool_analyze_pending_decls (void)
+{
+  bool changed = false;
+  timevar_push (TV_CGRAPH);
+
+  while (varpool_first_unanalyzed_node)
+    {
+      tree decl = varpool_first_unanalyzed_node->decl;
+
+      varpool_first_unanalyzed_node->analyzed = true;
+
+      varpool_first_unanalyzed_node = varpool_first_unanalyzed_node->next_needed;
+
+      /* Compute the alignment early so function body expanders are
+        already informed about increased alignment.  */
+      align_variable (decl, 0);
+
+      if (DECL_INITIAL (decl))
+       record_references_in_initializer (decl);
+      changed = true;
+    }
+  timevar_pop (TV_CGRAPH);
+  return changed;
+}
+
+/* Output one variable, if necessary.  Return whether we output it.  */
+bool
+varpool_assemble_decl (struct varpool_node *node)
+{
+  tree decl = node->decl;
+
+  if (!TREE_ASM_WRITTEN (decl)
+      && !node->alias
+      && !DECL_EXTERNAL (decl)
+      && (TREE_CODE (decl) != VAR_DECL || !DECL_HAS_VALUE_EXPR_P (decl)))
+    {
+      assemble_variable (decl, 0, 1, 0);
+      return TREE_ASM_WRITTEN (decl);
+    }
+
+  return false;
+}
+
+/* Optimization of function bodies might've rendered some variables as
+   unnecessary so we want to avoid these from being compiled.
+
+   This is done by pruning the queue and keeping only the variables that
+   really appear needed (ie they are either externally visible or referenced
+   by compiled function). Re-doing the reachability analysis on variables
+   brings back the remaining variables referenced by these.  */
+void
+varpool_remove_unreferenced_decls (void)
+{
+  struct varpool_node *next, *node = varpool_nodes_queue;
+
+  varpool_reset_queue ();
+
+  if (errorcount || sorrycount)
+    return;
+
+  while (node)
+    {
+      tree decl = node->decl;
+      next = node->next_needed;
+      node->needed = 0;
+
+      if (node->finalized
+         && ((DECL_ASSEMBLER_NAME_SET_P (decl)
+              && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)))
+             || node->force_output
+             || decide_is_variable_needed (node, decl)
+             /* ??? Cgraph does not yet rule the world with an iron hand,
+                and does not control the emission of debug information.
+                After a variable has its DECL_RTL set, we must assume that
+                it may be referenced by the debug information, and we can
+                no longer elide it.  */
+             || DECL_RTL_SET_P (decl)))
+       varpool_mark_needed_node (node);
+
+      node = next;
+    }
+  /* Make sure we mark alias targets as used targets.  */
+  finish_aliases_1 ();
+  varpool_analyze_pending_decls ();
+}
+
+/* Output all variables enqueued to be assembled.  */
+bool
+varpool_assemble_pending_decls (void)
+{
+  bool changed = false;
+
+  if (errorcount || sorrycount)
+    return false;
+
+  /* EH might mark decls as needed during expansion.  This should be safe since
+     we don't create references to new function, but it should not be used
+     elsewhere.  */
+  varpool_analyze_pending_decls ();
+
+  while (varpool_nodes_queue)
+    {
+      struct varpool_node *node = varpool_nodes_queue;
+
+      varpool_nodes_queue = varpool_nodes_queue->next_needed;
+      if (varpool_assemble_decl (node))
+       {
+         changed = true;
+         node->next_needed = varpool_assembled_nodes_queue;
+         varpool_assembled_nodes_queue = node;
+         node->finalized = 1;
+       }
+      else
+        node->next_needed = NULL;
+    }
+  return changed;
+}
+
+/* Output all variables enqueued to be assembled.  */
+void
+varpool_output_debug_info (void)
+{
+  timevar_push (TV_SYMOUT);
+  if (errorcount == 0 && sorrycount == 0)
+    while (varpool_assembled_nodes_queue)
+      {
+       struct varpool_node *node = varpool_assembled_nodes_queue;
+
+       /* Local static variables are never seen by check_global_declarations
+          so we need to output debug info by hand.  */
+       if (DECL_CONTEXT (node->decl)
+           && (TREE_CODE (DECL_CONTEXT (node->decl)) == BLOCK
+               || TREE_CODE (DECL_CONTEXT (node->decl)) == FUNCTION_DECL)
+           && errorcount == 0 && sorrycount == 0)
+            (*debug_hooks->global_decl) (node->decl);
+       varpool_assembled_nodes_queue = node->next_needed;
+       node->next_needed = 0;
+      }
+  timevar_pop (TV_SYMOUT);
+}
+
+#include "gt-varpool.h"