diff gcc/lto-streamer-in.c @ 145:1830386684a0

gcc-9.2.0
author anatofuz
date Thu, 13 Feb 2020 11:34:05 +0900
parents 84e7813d76e9
children
line wrap: on
line diff
--- a/gcc/lto-streamer-in.c	Thu Oct 25 07:37:49 2018 +0900
+++ b/gcc/lto-streamer-in.c	Thu Feb 13 11:34:05 2020 +0900
@@ -1,6 +1,6 @@
 /* Read the GIMPLE representation from a file stream.
 
-   Copyright (C) 2009-2018 Free Software Foundation, Inc.
+   Copyright (C) 2009-2020 Free Software Foundation, Inc.
    Contributed by Kenneth Zadeck <zadeck@naturalbridge.com>
    Re-implemented by Diego Novillo <dnovillo@google.com>
 
@@ -42,21 +42,18 @@
 #include "cgraph.h"
 #include "cfgloop.h"
 #include "debug.h"
-
+#include "alloc-pool.h"
 
-struct freeing_string_slot_hasher : string_slot_hasher
-{
-  static inline void remove (value_type *);
-};
-
-inline void
-freeing_string_slot_hasher::remove (value_type *v)
-{
-  free (v);
-}
+/* Allocator used to hold string slot entries for line map streaming.  */
+static struct object_allocator<struct string_slot> *string_slot_allocator;
 
 /* The table to hold the file names.  */
-static hash_table<freeing_string_slot_hasher> *file_name_hash_table;
+static hash_table<string_slot_hasher> *file_name_hash_table;
+
+/* This obstack holds file names used in locators. Line map datastructures
+   points here and thus it needs to be kept allocated as long as linemaps
+   exists.  */
+static struct obstack file_name_obstack;
 
 
 /* Check that tag ACTUAL has one of the given values.  NUM_TAGS is the
@@ -84,7 +81,7 @@
 /* Read LENGTH bytes from STREAM to ADDR.  */
 
 void
-lto_input_data_block (struct lto_input_block *ib, void *addr, size_t length)
+lto_input_data_block (class lto_input_block *ib, void *addr, size_t length)
 {
   size_t i;
   unsigned char *const buffer = (unsigned char *) addr;
@@ -113,8 +110,8 @@
       char *saved_string;
       struct string_slot *new_slot;
 
-      saved_string = (char *) xmalloc (len + 1);
-      new_slot = XCNEW (struct string_slot);
+      saved_string = XOBNEWVEC (&file_name_obstack, char, len + 1);
+      new_slot = string_slot_allocator->allocate ();
       memcpy (saved_string, string, len + 1);
       new_slot->s = saved_string;
       new_slot->len = len;
@@ -232,7 +229,7 @@
 
 void
 lto_location_cache::input_location (location_t *loc, struct bitpack_d *bp,
-				    struct data_in *data_in)
+				    class data_in *data_in)
 {
   static const char *stream_file;
   static int stream_line;
@@ -287,7 +284,7 @@
 
 void
 lto_input_location (location_t *loc, struct bitpack_d *bp,
-		    struct data_in *data_in)
+		    class data_in *data_in)
 {
   data_in->location_cache.input_location (loc, bp, data_in);
 }
@@ -297,7 +294,7 @@
    discarded.  */
 
 location_t
-stream_input_location_now (struct bitpack_d *bp, struct data_in *data_in)
+stream_input_location_now (struct bitpack_d *bp, class data_in *data_in)
 {
   location_t loc;
   stream_input_location (&loc, bp, data_in);
@@ -313,7 +310,7 @@
    function scope for the read tree.  */
 
 tree
-lto_input_tree_ref (struct lto_input_block *ib, struct data_in *data_in,
+lto_input_tree_ref (class lto_input_block *ib, class data_in *data_in,
 		    struct function *fn, enum LTO_tags tag)
 {
   unsigned HOST_WIDE_INT ix_u;
@@ -378,7 +375,7 @@
    block IB, using descriptors in DATA_IN.  */
 
 static struct eh_catch_d *
-lto_input_eh_catch_list (struct lto_input_block *ib, struct data_in *data_in,
+lto_input_eh_catch_list (class lto_input_block *ib, class data_in *data_in,
 			 eh_catch *last_p)
 {
   eh_catch first;
@@ -424,7 +421,7 @@
    in DATA_IN.  */
 
 static eh_region
-input_eh_region (struct lto_input_block *ib, struct data_in *data_in, int ix)
+input_eh_region (class lto_input_block *ib, class data_in *data_in, int ix)
 {
   enum LTO_tags tag;
   eh_region r;
@@ -499,7 +496,7 @@
    in DATA_IN.  */
 
 static eh_landing_pad
-input_eh_lp (struct lto_input_block *ib, struct data_in *data_in, int ix)
+input_eh_lp (class lto_input_block *ib, class data_in *data_in, int ix)
 {
   enum LTO_tags tag;
   eh_landing_pad lp;
@@ -603,7 +600,7 @@
    in DATA_IN.  */
 
 static void
-input_eh_regions (struct lto_input_block *ib, struct data_in *data_in,
+input_eh_regions (class lto_input_block *ib, class data_in *data_in,
 		  struct function *fn)
 {
   HOST_WIDE_INT i, root_region, len;
@@ -615,11 +612,6 @@
 
   lto_tag_check_range (tag, LTO_eh_table, LTO_eh_table);
 
-  /* If the file contains EH regions, then it was compiled with
-     -fexceptions.  In that case, initialize the backend EH
-     machinery.  */
-  lto_init_eh ();
-
   gcc_assert (fn->eh);
 
   root_region = streamer_read_hwi (ib);
@@ -714,7 +706,7 @@
 /* Read the CFG for function FN from input block IB.  */
 
 static void
-input_cfg (struct lto_input_block *ib, struct data_in *data_in,
+input_cfg (class lto_input_block *ib, class data_in *data_in,
 	   struct function *fn)
 {
   unsigned int bb_count;
@@ -807,7 +799,7 @@
 	  continue;
 	}
 
-      struct loop *loop = alloc_loop ();
+      class loop *loop = alloc_loop ();
       loop->header = BASIC_BLOCK_FOR_FN (fn, header_index);
       loop->header->loop_father = loop;
 
@@ -826,6 +818,7 @@
       /* Read OMP SIMD related info.  */
       loop->safelen = streamer_read_hwi (ib);
       loop->unroll = streamer_read_hwi (ib);
+      loop->owned_clique = streamer_read_hwi (ib);
       loop->dont_vectorize = streamer_read_hwi (ib);
       loop->force_vectorize = streamer_read_hwi (ib);
       loop->simduid = stream_read_tree (ib, data_in);
@@ -846,7 +839,7 @@
    block IB.  */
 
 static void
-input_ssa_names (struct lto_input_block *ib, struct data_in *data_in,
+input_ssa_names (class lto_input_block *ib, class data_in *data_in,
 		 struct function *fn)
 {
   unsigned int i, size;
@@ -899,6 +892,7 @@
         fatal_error (input_location,
 		     "Cgraph edge statement index out of range");
       cedge->call_stmt = as_a <gcall *> (stmts[cedge->lto_stmt_uid - 1]);
+      cedge->lto_stmt_uid = 0;
       if (!cedge->call_stmt)
         fatal_error (input_location,
 		     "Cgraph edge statement index not found");
@@ -909,6 +903,7 @@
         fatal_error (input_location,
 		     "Cgraph edge statement index out of range");
       cedge->call_stmt = as_a <gcall *> (stmts[cedge->lto_stmt_uid - 1]);
+      cedge->lto_stmt_uid = 0;
       if (!cedge->call_stmt)
         fatal_error (input_location, "Cgraph edge statement index not found");
     }
@@ -919,6 +914,7 @@
 	  fatal_error (input_location,
 		       "Reference statement index out of range");
 	ref->stmt = stmts[ref->lto_stmt_uid - 1];
+	ref->lto_stmt_uid = 0;
 	if (!ref->stmt)
 	  fatal_error (input_location, "Reference statement index not found");
       }
@@ -963,8 +959,8 @@
    using input block IB.  */
 
 static void
-input_struct_function_base (struct function *fn, struct data_in *data_in,
-                            struct lto_input_block *ib)
+input_struct_function_base (struct function *fn, class data_in *data_in,
+	                    class lto_input_block *ib)
 {
   struct bitpack_d bp;
   int len;
@@ -1004,6 +1000,7 @@
   fn->has_forced_label_in_static = bp_unpack_value (&bp, 1);
   fn->calls_alloca = bp_unpack_value (&bp, 1);
   fn->calls_setjmp = bp_unpack_value (&bp, 1);
+  fn->calls_eh_return = bp_unpack_value (&bp, 1);
   fn->has_force_vectorize_loops = bp_unpack_value (&bp, 1);
   fn->has_simduid_loops = bp_unpack_value (&bp, 1);
   fn->va_list_fpr_size = bp_unpack_value (&bp, 8);
@@ -1027,14 +1024,14 @@
 /* Read the body of function FN_DECL from DATA_IN using input block IB.  */
 
 static void
-input_function (tree fn_decl, struct data_in *data_in,
-		struct lto_input_block *ib, struct lto_input_block *ib_cfg)
+input_function (tree fn_decl, class data_in *data_in,
+		class lto_input_block *ib, class lto_input_block *ib_cfg,
+		cgraph_node *node)
 {
   struct function *fn;
   enum LTO_tags tag;
   gimple **stmts;
   basic_block bb;
-  struct cgraph_node *node;
 
   tag = streamer_read_record_start (ib);
   lto_tag_check (tag, LTO_function);
@@ -1070,9 +1067,6 @@
 
   gimple_register_cfg_hooks ();
 
-  node = cgraph_node::get (fn_decl);
-  if (!node)
-    node = cgraph_node::create (fn_decl);
   input_struct_function_base (fn, data_in, ib);
   input_cfg (ib_cfg, data_in, fn);
 
@@ -1139,6 +1133,15 @@
 		      ? !MAY_HAVE_DEBUG_MARKER_STMTS
 		      : !MAY_HAVE_DEBUG_BIND_STMTS))
 		remove = true;
+	      /* In case the linemap overflows locations can be dropped
+		 to zero.  Thus do not keep nonsensical inline entry markers
+		 we'd later ICE on.  */
+	      tree block;
+	      if (gimple_debug_inline_entry_p (stmt)
+		  && (((block = gimple_block (stmt))
+		       && !inlined_function_outer_scope_p (block))
+		      || !debug_inline_points))
+		remove = true;
 	      if (is_gimple_call (stmt)
 		  && gimple_call_internal_p (stmt))
 		{
@@ -1221,7 +1224,6 @@
   fixup_call_stmt_edges (node, stmts);
   execute_all_ipa_stmt_fixups (node, stmts);
 
-  update_ssa (TODO_update_ssa_only_virtuals);
   free_dominance_info (CDI_DOMINATORS);
   free_dominance_info (CDI_POST_DOMINATORS);
   free (stmts);
@@ -1231,8 +1233,8 @@
 /* Read the body of function FN_DECL from DATA_IN using input block IB.  */
 
 static void
-input_constructor (tree var, struct data_in *data_in,
-		   struct lto_input_block *ib)
+input_constructor (tree var, class data_in *data_in,
+		   class lto_input_block *ib)
 {
   DECL_INITIAL (var) = stream_read_tree (ib, data_in);
 }
@@ -1249,7 +1251,7 @@
 			      const char *data, enum lto_section_type section_type)
 {
   const struct lto_function_header *header;
-  struct data_in *data_in;
+  class data_in *data_in;
   int cfg_offset;
   int main_offset;
   int string_offset;
@@ -1292,7 +1294,8 @@
 	{
 	  lto_input_block ib_cfg (data + cfg_offset, header->cfg_size,
 				  file_data->mode_table);
-	  input_function (fn_decl, data_in, &ib_main, &ib_cfg);
+	  input_function (fn_decl, data_in, &ib_main, &ib_cfg,
+			  dyn_cast <cgraph_node *>(node));
 	}
       else
         input_constructor (fn_decl, data_in, &ib_main);
@@ -1362,7 +1365,7 @@
    input block IB using the per-file context in DATA_IN.  */
 
 static void
-lto_read_tree_1 (struct lto_input_block *ib, struct data_in *data_in, tree expr)
+lto_read_tree_1 (class lto_input_block *ib, class data_in *data_in, tree expr)
 {
   /* Read all the bitfield values in EXPR.  Note that for LTO, we
      only write language-independent bitfields, so no more unpacking is
@@ -1400,7 +1403,7 @@
    input block IB using the per-file context in DATA_IN.  */
 
 static tree
-lto_read_tree (struct lto_input_block *ib, struct data_in *data_in,
+lto_read_tree (class lto_input_block *ib, class data_in *data_in,
 	       enum LTO_tags tag, hashval_t hash)
 {
   /* Instantiate a new tree node.  */
@@ -1423,7 +1426,7 @@
    following in the IB, DATA_IN stream.  */
 
 hashval_t
-lto_input_scc (struct lto_input_block *ib, struct data_in *data_in,
+lto_input_scc (class lto_input_block *ib, class data_in *data_in,
 	       unsigned *len, unsigned *entry_len)
 {
   /* A blob of unnamed tree nodes, fill the cache from it and
@@ -1480,7 +1483,7 @@
    to previously read nodes.  */
 
 tree
-lto_input_tree_1 (struct lto_input_block *ib, struct data_in *data_in,
+lto_input_tree_1 (class lto_input_block *ib, class data_in *data_in,
 		  enum LTO_tags tag, hashval_t hash)
 {
   tree result;
@@ -1530,7 +1533,7 @@
 }
 
 tree
-lto_input_tree (struct lto_input_block *ib, struct data_in *data_in)
+lto_input_tree (class lto_input_block *ib, class data_in *data_in)
 {
   enum LTO_tags tag;
 
@@ -1557,12 +1560,12 @@
 lto_input_toplevel_asms (struct lto_file_decl_data *file_data, int order_base)
 {
   size_t len;
-  const char *data = lto_get_section_data (file_data, LTO_section_asm,
-					   NULL, &len);
+  const char *data
+    = lto_get_summary_section_data (file_data, LTO_section_asm, &len);
   const struct lto_simple_header_with_strings *header
     = (const struct lto_simple_header_with_strings *) data;
   int string_offset;
-  struct data_in *data_in;
+  class data_in *data_in;
   tree str;
 
   if (! data)
@@ -1596,8 +1599,8 @@
 lto_input_mode_table (struct lto_file_decl_data *file_data)
 {
   size_t len;
-  const char *data = lto_get_section_data (file_data, LTO_section_mode_table,
-					   NULL, &len);
+  const char *data
+    = lto_get_summary_section_data (file_data, LTO_section_mode_table, &len);
   if (! data)
     {
       internal_error ("cannot read LTO mode table from %s",
@@ -1610,7 +1613,7 @@
   const struct lto_simple_header_with_strings *header
     = (const struct lto_simple_header_with_strings *) data;
   int string_offset;
-  struct data_in *data_in;
+  class data_in *data_in;
   string_offset = sizeof (*header) + header->main_size;
 
   lto_input_block ib (data + sizeof (*header), header->main_size, NULL);
@@ -1699,7 +1702,31 @@
 		}
 	      /* FALLTHRU */
 	    default:
-	      fatal_error (UNKNOWN_LOCATION, "unsupported mode %s\n", mname);
+	      /* This is only used for offloading-target compilations and
+		 is a user-facing error.  Give a better error message for
+		 the common modes; see also mode-classes.def.   */
+	      if (mclass == MODE_FLOAT)
+		fatal_error (UNKNOWN_LOCATION,
+			     "%s - %u-bit-precision floating-point numbers "
+			     "unsupported (mode %qs)", TARGET_MACHINE,
+			     prec.to_constant (), mname);
+	      else if (mclass == MODE_DECIMAL_FLOAT)
+		fatal_error (UNKNOWN_LOCATION,
+			     "%s - %u-bit-precision decimal floating-point "
+			     "numbers unsupported (mode %qs)", TARGET_MACHINE,
+			     prec.to_constant (), mname);
+	      else if (mclass == MODE_COMPLEX_FLOAT)
+		fatal_error (UNKNOWN_LOCATION,
+			     "%s - %u-bit-precision complex floating-point "
+			     "numbers unsupported (mode %qs)", TARGET_MACHINE,
+			     prec.to_constant (), mname);
+	      else if (mclass == MODE_INT)
+		fatal_error (UNKNOWN_LOCATION,
+			     "%s - %u-bit integer numbers unsupported (mode "
+			     "%qs)", TARGET_MACHINE, prec.to_constant (), mname);
+	      else
+		fatal_error (UNKNOWN_LOCATION, "%s - unsupported mode %qs",
+			     TARGET_MACHINE, mname);
 	      break;
 	    }
 	}
@@ -1717,7 +1744,23 @@
 {
   lto_streamer_init ();
   file_name_hash_table
-    = new hash_table<freeing_string_slot_hasher> (37);
+    = new hash_table<string_slot_hasher> (37);
+  string_slot_allocator = new object_allocator <struct string_slot>
+				("line map file name hash");
+  gcc_obstack_init (&file_name_obstack);
+}
+
+/* Free hash table used to stream in location file names.  */
+
+void
+lto_free_file_name_hash (void)
+{
+  delete file_name_hash_table;
+  file_name_hash_table = NULL;
+  delete string_slot_allocator;
+  string_slot_allocator = NULL;
+  /* file_name_obstack must stay allocated since it is referred to by
+     line map table.  */
 }
 
 
@@ -1725,12 +1768,12 @@
    table to use with LEN strings.  RESOLUTIONS is the vector of linker
    resolutions (NULL if not using a linker plugin).  */
 
-struct data_in *
+class data_in *
 lto_data_in_create (struct lto_file_decl_data *file_data, const char *strings,
 		    unsigned len,
 		    vec<ld_plugin_symbol_resolution_t> resolutions)
 {
-  struct data_in *data_in = new (struct data_in);
+  class data_in *data_in = new (class data_in);
   data_in->file_data = file_data;
   data_in->strings = strings;
   data_in->strings_len = len;
@@ -1743,7 +1786,7 @@
 /* Remove DATA_IN.  */
 
 void
-lto_data_in_delete (struct data_in *data_in)
+lto_data_in_delete (class data_in *data_in)
 {
   data_in->globals_resolution.release ();
   streamer_tree_cache_delete (data_in->reader_cache);