/* Read the GIMPLE representation from a file stream.

   Copyright 2009, 2010 Free Software Foundation, Inc.
   Contributed by Kenneth Zadeck <zadeck@naturalbridge.com>
   Re-implemented by Diego Novillo <dnovillo@google.com>

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 3, 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 COPYING3.  If not see
<http://www.gnu.org/licenses/>.  */

#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "tm.h"
#include "toplev.h"
#include "tree.h"
#include "expr.h"
#include "flags.h"
#include "params.h"
#include "input.h"
#include "hashtab.h"
#include "basic-block.h"
#include "tree-flow.h"
#include "tree-pass.h"
#include "cgraph.h"
#include "function.h"
#include "ggc.h"
#include "diagnostic.h"
#include "libfuncs.h"
#include "except.h"
#include "debug.h"
#include "vec.h"
#include "timevar.h"
#include "output.h"
#include "ipa-utils.h"
#include "lto-streamer.h"
#include "tree-pass.h"

/* Data structure used to hash file names in the source_location field.  */
struct string_slot
{
  const char *s;
  unsigned int slot_num;
};

/* The table to hold the file names.  */
static htab_t file_name_hash_table;


/* Check that tag ACTUAL has one of the given values.  NUM_TAGS is the
   number of valid tag values to check.  */

static void
lto_tag_check_set (enum LTO_tags actual, int ntags, ...)
{
  va_list ap;
  int i;

  va_start (ap, ntags);
  for (i = 0; i < ntags; i++)
    if ((unsigned) actual == va_arg (ap, unsigned))
      {
	va_end (ap);
	return;
      }

  va_end (ap);
  internal_error ("bytecode stream: unexpected tag %s", lto_tag_name (actual));
}


/* Check that tag ACTUAL is in the range [TAG1, TAG2].  */

static void
lto_tag_check_range (enum LTO_tags actual, enum LTO_tags tag1,
		     enum LTO_tags tag2)
{
  if (actual < tag1 || actual > tag2)
    internal_error ("bytecode stream: tag %s is not in the expected range "
		    "[%s, %s]",
		    lto_tag_name (actual),
		    lto_tag_name (tag1),
		    lto_tag_name (tag2));
}


/* Check that tag ACTUAL == EXPECTED.  */

static void
lto_tag_check (enum LTO_tags actual, enum LTO_tags expected)
{
  if (actual != expected)
    internal_error ("bytecode stream: expected tag %s instead of %s",
		    lto_tag_name (expected), lto_tag_name (actual));
}


/* Return a hash code for P.  */

static hashval_t
hash_string_slot_node (const void *p)
{
  const struct string_slot *ds = (const struct string_slot *) p;
  return (hashval_t) htab_hash_string (ds->s);
}


/* Returns nonzero if P1 and P2 are equal.  */

static int
eq_string_slot_node (const void *p1, const void *p2)
{
  const struct string_slot *ds1 = (const struct string_slot *) p1;
  const struct string_slot *ds2 = (const struct string_slot *) p2;
  return strcmp (ds1->s, ds2->s) == 0;
}


/* Read a string from the string table in DATA_IN using input block
   IB.  Write the length to RLEN.  */

static const char *
input_string_internal (struct data_in *data_in, struct lto_input_block *ib,
		       unsigned int *rlen)
{
  struct lto_input_block str_tab;
  unsigned int len;
  unsigned int loc;
  const char *result;

  loc = lto_input_uleb128 (ib);
  LTO_INIT_INPUT_BLOCK (str_tab, data_in->strings, loc, data_in->strings_len);
  len = lto_input_uleb128 (&str_tab);
  *rlen = len;

  if (str_tab.p + len > data_in->strings_len)
    internal_error ("bytecode stream: string too long for the string table");

  result = (const char *)(data_in->strings + str_tab.p);

  return result;
}


/* Read a STRING_CST from the string table in DATA_IN using input
   block IB.  */

static tree
input_string_cst (struct data_in *data_in, struct lto_input_block *ib)
{
  unsigned int len;
  const char * ptr;
  unsigned int is_null;

  is_null = lto_input_uleb128 (ib);
  if (is_null)
    return NULL;

  ptr = input_string_internal (data_in, ib, &len);
  return build_string (len, ptr);
}


/* Read an IDENTIFIER from the string table in DATA_IN using input
   block IB.  */

static tree
input_identifier (struct data_in *data_in, struct lto_input_block *ib)
{
  unsigned int len;
  const char *ptr;
  unsigned int is_null;

  is_null = lto_input_uleb128 (ib);
  if (is_null)
    return NULL;

  ptr = input_string_internal (data_in, ib, &len);
  return get_identifier_with_length (ptr, len);
}

/* Read a NULL terminated string from the string table in DATA_IN.  */

static const char *
input_string (struct data_in *data_in, struct lto_input_block *ib)
{
  unsigned int len;
  const char *ptr;
  unsigned int is_null;

  is_null = lto_input_uleb128 (ib);
  if (is_null)
    return NULL;

  ptr = input_string_internal (data_in, ib, &len);
  if (ptr[len - 1] != '\0')
    internal_error ("bytecode stream: found non-null terminated string");

  return ptr;
}


/* Return the next tag in the input block IB.  */

static enum LTO_tags
input_record_start (struct lto_input_block *ib)
{
  enum LTO_tags tag = (enum LTO_tags) lto_input_uleb128 (ib);
  return tag;
}


/* Lookup STRING in file_name_hash_table.  If found, return the existing
   string, otherwise insert STRING as the canonical version.  */

static const char *
canon_file_name (const char *string)
{
  void **slot;
  struct string_slot s_slot;
  s_slot.s = string;

  slot = htab_find_slot (file_name_hash_table, &s_slot, INSERT);
  if (*slot == NULL)
    {
      size_t len;
      char *saved_string;
      struct string_slot *new_slot;

      len = strlen (string);
      saved_string = (char *) xmalloc (len + 1);
      new_slot = XCNEW (struct string_slot);
      strcpy (saved_string, string);
      new_slot->s = saved_string;
      *slot = new_slot;
      return saved_string;
    }
  else
    {
      struct string_slot *old_slot = (struct string_slot *) *slot;
      return old_slot->s;
    }
}


/* Clear the line info stored in DATA_IN.  */

static void
clear_line_info (struct data_in *data_in)
{
  if (data_in->current_file)
    linemap_add (line_table, LC_LEAVE, false, NULL, 0);
  data_in->current_file = NULL;
  data_in->current_line = 0;
  data_in->current_col = 0;
}


/* Read a location from input block IB.  */

static location_t
lto_input_location (struct lto_input_block *ib, struct data_in *data_in)
{
  expanded_location xloc;

  xloc.file = input_string (data_in, ib);
  if (xloc.file == NULL)
    return UNKNOWN_LOCATION;

  xloc.file = canon_file_name (xloc.file);
  xloc.line = lto_input_sleb128 (ib);
  xloc.column = lto_input_sleb128 (ib);
  xloc.sysp = lto_input_sleb128 (ib);

  if (data_in->current_file != xloc.file)
    {
      if (data_in->current_file)
	linemap_add (line_table, LC_LEAVE, false, NULL, 0);

      linemap_add (line_table, LC_ENTER, xloc.sysp, xloc.file, xloc.line);
    }
  else if (data_in->current_line != xloc.line)
    linemap_line_start (line_table, xloc.line, xloc.column);

  data_in->current_file = xloc.file;
  data_in->current_line = xloc.line;
  data_in->current_col = xloc.column;

  return linemap_position_for_column (line_table, xloc.column);
}


/* Read a reference to a tree node from DATA_IN using input block IB.
   TAG is the expected node that should be found in IB, if TAG belongs
   to one of the indexable trees, expect to read a reference index to
   be looked up in one of the symbol tables, otherwise read the pysical
   representation of the tree using lto_input_tree.  FN is the
   function scope for the read tree.  */

static tree
lto_input_tree_ref (struct lto_input_block *ib, struct data_in *data_in,
		    struct function *fn, enum LTO_tags tag)
{
  unsigned HOST_WIDE_INT ix_u;
  tree result = NULL_TREE;

  lto_tag_check_range (tag, LTO_field_decl_ref, LTO_global_decl_ref);

  switch (tag)
    {
    case LTO_type_ref:
      ix_u = lto_input_uleb128 (ib);
      result = lto_file_decl_data_get_type (data_in->file_data, ix_u);
      break;

    case LTO_ssa_name_ref:
      ix_u = lto_input_uleb128 (ib);
      result = VEC_index (tree, SSANAMES (fn), ix_u);
      break;

    case LTO_field_decl_ref:
      ix_u = lto_input_uleb128 (ib);
      result = lto_file_decl_data_get_field_decl (data_in->file_data, ix_u);
      break;

    case LTO_function_decl_ref:
      ix_u = lto_input_uleb128 (ib);
      result = lto_file_decl_data_get_fn_decl (data_in->file_data, ix_u);
      break;

    case LTO_type_decl_ref:
      ix_u = lto_input_uleb128 (ib);
      result = lto_file_decl_data_get_type_decl (data_in->file_data, ix_u);
      break;

    case LTO_namespace_decl_ref:
      ix_u = lto_input_uleb128 (ib);
      result = lto_file_decl_data_get_namespace_decl (data_in->file_data, ix_u);
      break;

    case LTO_global_decl_ref:
    case LTO_result_decl_ref:
    case LTO_const_decl_ref:
    case LTO_imported_decl_ref:
    case LTO_label_decl_ref:
    case LTO_translation_unit_decl_ref:
      ix_u = lto_input_uleb128 (ib);
      result = lto_file_decl_data_get_var_decl (data_in->file_data, ix_u);
      break;

    default:
      gcc_unreachable ();
    }

  gcc_assert (result);

  return result;
}


/* Read and return a double-linked list of catch handlers from input
   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,
			 eh_catch *last_p)
{
  eh_catch first;
  enum LTO_tags tag;

  *last_p = first = NULL;
  tag = input_record_start (ib);
  while (tag)
    {
      tree list;
      eh_catch n;

      lto_tag_check_range (tag, LTO_eh_catch, LTO_eh_catch);

      /* Read the catch node.  */
      n = ggc_alloc_cleared_eh_catch_d ();
      n->type_list = lto_input_tree (ib, data_in);
      n->filter_list = lto_input_tree (ib, data_in);
      n->label = lto_input_tree (ib, data_in);

      /* Register all the types in N->FILTER_LIST.  */
      for (list = n->filter_list; list; list = TREE_CHAIN (list))
	add_type_for_runtime (TREE_VALUE (list));

      /* Chain N to the end of the list.  */
      if (*last_p)
	(*last_p)->next_catch = n;
      n->prev_catch = *last_p;
      *last_p = n;

      /* Set the head of the list the first time through the loop.  */
      if (first == NULL)
	first = n;

      tag = input_record_start (ib);
    }

  return first;
}


/* Read and return EH region IX from input block IB, using descriptors
   in DATA_IN.  */

static eh_region
input_eh_region (struct lto_input_block *ib, struct data_in *data_in, int ix)
{
  enum LTO_tags tag;
  eh_region r;

  /* Read the region header.  */
  tag = input_record_start (ib);
  if (tag == LTO_null)
    return NULL;

  r = ggc_alloc_cleared_eh_region_d ();
  r->index = lto_input_sleb128 (ib);

  gcc_assert (r->index == ix);

  /* Read all the region pointers as region numbers.  We'll fix up
     the pointers once the whole array has been read.  */
  r->outer = (eh_region) (intptr_t) lto_input_sleb128 (ib);
  r->inner = (eh_region) (intptr_t) lto_input_sleb128 (ib);
  r->next_peer = (eh_region) (intptr_t) lto_input_sleb128 (ib);

  switch (tag)
    {
      case LTO_ert_cleanup:
	r->type = ERT_CLEANUP;
	break;

      case LTO_ert_try:
	{
	  struct eh_catch_d *last_catch;
	  r->type = ERT_TRY;
	  r->u.eh_try.first_catch = lto_input_eh_catch_list (ib, data_in,
							     &last_catch);
	  r->u.eh_try.last_catch = last_catch;
	  break;
	}

      case LTO_ert_allowed_exceptions:
	{
	  tree l;

	  r->type = ERT_ALLOWED_EXCEPTIONS;
	  r->u.allowed.type_list = lto_input_tree (ib, data_in);
	  r->u.allowed.label = lto_input_tree (ib, data_in);
	  r->u.allowed.filter = lto_input_uleb128 (ib);

	  for (l = r->u.allowed.type_list; l ; l = TREE_CHAIN (l))
	    add_type_for_runtime (TREE_VALUE (l));
	}
	break;

      case LTO_ert_must_not_throw:
	r->type = ERT_MUST_NOT_THROW;
	r->u.must_not_throw.failure_decl = lto_input_tree (ib, data_in);
	r->u.must_not_throw.failure_loc = lto_input_location (ib, data_in);
	break;

      default:
	gcc_unreachable ();
    }

  r->landing_pads = (eh_landing_pad) (intptr_t) lto_input_sleb128 (ib);

  return r;
}


/* Read and return EH landing pad IX from input block IB, using descriptors
   in DATA_IN.  */

static eh_landing_pad
input_eh_lp (struct lto_input_block *ib, struct data_in *data_in, int ix)
{
  enum LTO_tags tag;
  eh_landing_pad lp;

  /* Read the landing pad header.  */
  tag = input_record_start (ib);
  if (tag == LTO_null)
    return NULL;

  lto_tag_check_range (tag, LTO_eh_landing_pad, LTO_eh_landing_pad);

  lp = ggc_alloc_cleared_eh_landing_pad_d ();
  lp->index = lto_input_sleb128 (ib);
  gcc_assert (lp->index == ix);
  lp->next_lp = (eh_landing_pad) (intptr_t) lto_input_sleb128 (ib);
  lp->region = (eh_region) (intptr_t) lto_input_sleb128 (ib);
  lp->post_landing_pad = lto_input_tree (ib, data_in);

  return lp;
}


/* After reading the EH regions, pointers to peer and children regions
   are region numbers.  This converts all these region numbers into
   real pointers into the rematerialized regions for FN.  ROOT_REGION
   is the region number for the root EH region in FN.  */

static void
fixup_eh_region_pointers (struct function *fn, HOST_WIDE_INT root_region)
{
  unsigned i;
  VEC(eh_region,gc) *eh_array = fn->eh->region_array;
  VEC(eh_landing_pad,gc) *lp_array = fn->eh->lp_array;
  eh_region r;
  eh_landing_pad lp;

  gcc_assert (eh_array && lp_array);

  gcc_assert (root_region >= 0);
  fn->eh->region_tree = VEC_index (eh_region, eh_array, root_region);

#define FIXUP_EH_REGION(r) (r) = VEC_index (eh_region, eh_array, \
					    (HOST_WIDE_INT) (intptr_t) (r))
#define FIXUP_EH_LP(p) (p) = VEC_index (eh_landing_pad, lp_array, \
					(HOST_WIDE_INT) (intptr_t) (p))

  /* Convert all the index numbers stored in pointer fields into
     pointers to the corresponding slots in the EH region array.  */
  FOR_EACH_VEC_ELT (eh_region, eh_array, i, r)
    {
      /* The array may contain NULL regions.  */
      if (r == NULL)
	continue;

      gcc_assert (i == (unsigned) r->index);
      FIXUP_EH_REGION (r->outer);
      FIXUP_EH_REGION (r->inner);
      FIXUP_EH_REGION (r->next_peer);
      FIXUP_EH_LP (r->landing_pads);
    }

  /* Convert all the index numbers stored in pointer fields into
     pointers to the corresponding slots in the EH landing pad array.  */
  FOR_EACH_VEC_ELT (eh_landing_pad, lp_array, i, lp)
    {
      /* The array may contain NULL landing pads.  */
      if (lp == NULL)
	continue;

      gcc_assert (i == (unsigned) lp->index);
      FIXUP_EH_LP (lp->next_lp);
      FIXUP_EH_REGION (lp->region);
    }

#undef FIXUP_EH_REGION
#undef FIXUP_EH_LP
}


/* Initialize EH support.  */

static void
lto_init_eh (void)
{
  static bool eh_initialized_p = false;

  if (eh_initialized_p)
    return;

  /* Contrary to most other FEs, we only initialize EH support when at
     least one of the files in the set contains exception regions in
     it.  Since this happens much later than the call to init_eh in
     lang_dependent_init, we have to set flag_exceptions and call
     init_eh again to initialize the EH tables.  */
  flag_exceptions = 1;
  init_eh ();

  /* Initialize dwarf2 tables.  Since dwarf2out_do_frame() returns
     true only when exceptions are enabled, this initialization is
     never done during lang_dependent_init.  */
#if defined DWARF2_DEBUGGING_INFO || defined DWARF2_UNWIND_INFO
  if (dwarf2out_do_frame ())
    dwarf2out_frame_init ();
#endif

  eh_initialized_p = true;
}


/* Read the exception table for FN from IB using the data descriptors
   in DATA_IN.  */

static void
input_eh_regions (struct lto_input_block *ib, struct data_in *data_in,
		  struct function *fn)
{
  HOST_WIDE_INT i, root_region, len;
  enum LTO_tags tag;

  tag = input_record_start (ib);
  if (tag == LTO_null)
    return;

  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 = lto_input_sleb128 (ib);
  gcc_assert (root_region == (int) root_region);

  /* Read the EH region array.  */
  len = lto_input_sleb128 (ib);
  gcc_assert (len == (int) len);
  if (len > 0)
    {
      VEC_safe_grow (eh_region, gc, fn->eh->region_array, len);
      for (i = 0; i < len; i++)
	{
	  eh_region r = input_eh_region (ib, data_in, i);
	  VEC_replace (eh_region, fn->eh->region_array, i, r);
	}
    }

  /* Read the landing pads.  */
  len = lto_input_sleb128 (ib);
  gcc_assert (len == (int) len);
  if (len > 0)
    {
      VEC_safe_grow (eh_landing_pad, gc, fn->eh->lp_array, len);
      for (i = 0; i < len; i++)
	{
	  eh_landing_pad lp = input_eh_lp (ib, data_in, i);
	  VEC_replace (eh_landing_pad, fn->eh->lp_array, i, lp);
	}
    }

  /* Read the runtime type data.  */
  len = lto_input_sleb128 (ib);
  gcc_assert (len == (int) len);
  if (len > 0)
    {
      VEC_safe_grow (tree, gc, fn->eh->ttype_data, len);
      for (i = 0; i < len; i++)
	{
	  tree ttype = lto_input_tree (ib, data_in);
	  VEC_replace (tree, fn->eh->ttype_data, i, ttype);
	}
    }

  /* Read the table of action chains.  */
  len = lto_input_sleb128 (ib);
  gcc_assert (len == (int) len);
  if (len > 0)
    {
      if (targetm.arm_eabi_unwinder)
	{
	  VEC_safe_grow (tree, gc, fn->eh->ehspec_data.arm_eabi, len);
	  for (i = 0; i < len; i++)
	    {
	      tree t = lto_input_tree (ib, data_in);
	      VEC_replace (tree, fn->eh->ehspec_data.arm_eabi, i, t);
	    }
	}
      else
	{
	  VEC_safe_grow (uchar, gc, fn->eh->ehspec_data.other, len);
	  for (i = 0; i < len; i++)
	    {
	      uchar c = lto_input_1_unsigned (ib);
	      VEC_replace (uchar, fn->eh->ehspec_data.other, i, c);
	    }
	}
    }

  /* Reconstruct the EH region tree by fixing up the peer/children
     pointers.  */
  fixup_eh_region_pointers (fn, root_region);

  tag = input_record_start (ib);
  lto_tag_check_range (tag, LTO_null, LTO_null);
}


/* Make a new basic block with index INDEX in function FN.  */

static basic_block
make_new_block (struct function *fn, unsigned int index)
{
  basic_block bb = alloc_block ();
  bb->index = index;
  SET_BASIC_BLOCK_FOR_FUNCTION (fn, index, bb);
  bb->il.gimple = ggc_alloc_cleared_gimple_bb_info ();
  n_basic_blocks_for_function (fn)++;
  bb->flags = 0;
  set_bb_seq (bb, gimple_seq_alloc ());
  return bb;
}


/* Read the CFG for function FN from input block IB.  */

static void
input_cfg (struct lto_input_block *ib, struct function *fn,
	   int count_materialization_scale)
{
  unsigned int bb_count;
  basic_block p_bb;
  unsigned int i;
  int index;

  init_empty_tree_cfg_for_function (fn);
  init_ssa_operands ();

  profile_status_for_function (fn) =
    (enum profile_status_d) lto_input_uleb128 (ib);

  bb_count = lto_input_uleb128 (ib);

  last_basic_block_for_function (fn) = bb_count;
  if (bb_count > VEC_length (basic_block, basic_block_info_for_function (fn)))
    VEC_safe_grow_cleared (basic_block, gc,
			   basic_block_info_for_function (fn), bb_count);

  if (bb_count > VEC_length (basic_block, label_to_block_map_for_function (fn)))
    VEC_safe_grow_cleared (basic_block, gc,
			   label_to_block_map_for_function (fn), bb_count);

  index = lto_input_sleb128 (ib);
  while (index != -1)
    {
      basic_block bb = BASIC_BLOCK_FOR_FUNCTION (fn, index);
      unsigned int edge_count;

      if (bb == NULL)
	bb = make_new_block (fn, index);

      edge_count = lto_input_uleb128 (ib);

      /* Connect up the CFG.  */
      for (i = 0; i < edge_count; i++)
	{
	  unsigned int dest_index;
	  unsigned int edge_flags;
	  basic_block dest;
	  int probability;
	  gcov_type count;
	  edge e;

	  dest_index = lto_input_uleb128 (ib);
	  probability = (int) lto_input_sleb128 (ib);
	  count = ((gcov_type) lto_input_sleb128 (ib) * count_materialization_scale
		   + REG_BR_PROB_BASE / 2) / REG_BR_PROB_BASE;
	  edge_flags = lto_input_uleb128 (ib);

	  dest = BASIC_BLOCK_FOR_FUNCTION (fn, dest_index);

	  if (dest == NULL)
	    dest = make_new_block (fn, dest_index);

	  e = make_edge (bb, dest, edge_flags);
	  e->probability = probability;
	  e->count = count;
	}

      index = lto_input_sleb128 (ib);
    }

  p_bb = ENTRY_BLOCK_PTR_FOR_FUNCTION(fn);
  index = lto_input_sleb128 (ib);
  while (index != -1)
    {
      basic_block bb = BASIC_BLOCK_FOR_FUNCTION (fn, index);
      bb->prev_bb = p_bb;
      p_bb->next_bb = bb;
      p_bb = bb;
      index = lto_input_sleb128 (ib);
    }
}


/* Read a PHI function for basic block BB in function FN.  DATA_IN is
   the file being read.  IB is the input block to use for reading.  */

static gimple
input_phi (struct lto_input_block *ib, basic_block bb, struct data_in *data_in,
	   struct function *fn)
{
  unsigned HOST_WIDE_INT ix;
  tree phi_result;
  int i, len;
  gimple result;

  ix = lto_input_uleb128 (ib);
  phi_result = VEC_index (tree, SSANAMES (fn), ix);
  len = EDGE_COUNT (bb->preds);
  result = create_phi_node (phi_result, bb);
  SSA_NAME_DEF_STMT (phi_result) = result;

  /* We have to go through a lookup process here because the preds in the
     reconstructed graph are generally in a different order than they
     were in the original program.  */
  for (i = 0; i < len; i++)
    {
      tree def = lto_input_tree (ib, data_in);
      int src_index = lto_input_uleb128 (ib);
      location_t arg_loc = lto_input_location (ib, data_in);
      basic_block sbb = BASIC_BLOCK_FOR_FUNCTION (fn, src_index);

      edge e = NULL;
      int j;

      for (j = 0; j < len; j++)
	if (EDGE_PRED (bb, j)->src == sbb)
	  {
	    e = EDGE_PRED (bb, j);
	    break;
	  }

      add_phi_arg (result, def, e, arg_loc);
    }

  return result;
}


/* Read the SSA names array for function FN from DATA_IN using input
   block IB.  */

static void
input_ssa_names (struct lto_input_block *ib, struct data_in *data_in,
		 struct function *fn)
{
  unsigned int i, size;

  size = lto_input_uleb128 (ib);
  init_ssanames (fn, size);

  i = lto_input_uleb128 (ib);
  while (i)
    {
      tree ssa_name, name;
      bool is_default_def;

      /* Skip over the elements that had been freed.  */
      while (VEC_length (tree, SSANAMES (fn)) < i)
	VEC_quick_push (tree, SSANAMES (fn), NULL_TREE);

      is_default_def = (lto_input_1_unsigned (ib) != 0);
      name = lto_input_tree (ib, data_in);
      ssa_name = make_ssa_name_fn (fn, name, gimple_build_nop ());

      if (is_default_def)
	set_default_def (SSA_NAME_VAR (ssa_name), ssa_name);

      i = lto_input_uleb128 (ib);
    }
}

/* Read a statement with tag TAG in function FN from block IB using
   descriptors in DATA_IN.  */

static gimple
input_gimple_stmt (struct lto_input_block *ib, struct data_in *data_in,
		   struct function *fn, enum LTO_tags tag)
{
  gimple stmt;
  enum gimple_code code;
  unsigned HOST_WIDE_INT num_ops;
  size_t i;
  struct bitpack_d bp;

  code = lto_tag_to_gimple_code (tag);

  /* Read the tuple header.  */
  bp = lto_input_bitpack (ib);
  num_ops = bp_unpack_value (&bp, sizeof (unsigned) * 8);
  stmt = gimple_alloc (code, num_ops);
  stmt->gsbase.no_warning = bp_unpack_value (&bp, 1);
  if (is_gimple_assign (stmt))
    stmt->gsbase.nontemporal_move = bp_unpack_value (&bp, 1);
  stmt->gsbase.has_volatile_ops = bp_unpack_value (&bp, 1);
  stmt->gsbase.subcode = bp_unpack_value (&bp, 16);

  /* Read location information.  */
  gimple_set_location (stmt, lto_input_location (ib, data_in));

  /* Read lexical block reference.  */
  gimple_set_block (stmt, lto_input_tree (ib, data_in));

  /* Read in all the operands.  */
  switch (code)
    {
    case GIMPLE_RESX:
      gimple_resx_set_region (stmt, lto_input_sleb128 (ib));
      break;

    case GIMPLE_EH_MUST_NOT_THROW:
      gimple_eh_must_not_throw_set_fndecl (stmt, lto_input_tree (ib, data_in));
      break;

    case GIMPLE_EH_DISPATCH:
      gimple_eh_dispatch_set_region (stmt, lto_input_sleb128 (ib));
      break;

    case GIMPLE_ASM:
      {
	/* FIXME lto.  Move most of this into a new gimple_asm_set_string().  */
	tree str;
	stmt->gimple_asm.ni = lto_input_uleb128 (ib);
	stmt->gimple_asm.no = lto_input_uleb128 (ib);
	stmt->gimple_asm.nc = lto_input_uleb128 (ib);
	stmt->gimple_asm.nl = lto_input_uleb128 (ib);
	str = input_string_cst (data_in, ib);
	stmt->gimple_asm.string = TREE_STRING_POINTER (str);
      }
      /* Fallthru  */

    case GIMPLE_ASSIGN:
    case GIMPLE_CALL:
    case GIMPLE_RETURN:
    case GIMPLE_SWITCH:
    case GIMPLE_LABEL:
    case GIMPLE_COND:
    case GIMPLE_GOTO:
    case GIMPLE_DEBUG:
      for (i = 0; i < num_ops; i++)
	{
	  tree op = lto_input_tree (ib, data_in);
	  gimple_set_op (stmt, i, op);
	  if (!op)
	    continue;

	  /* Fixup FIELD_DECLs in COMPONENT_REFs, they are not handled
	     by decl merging.  */
	  if (TREE_CODE (op) == ADDR_EXPR)
	    op = TREE_OPERAND (op, 0);
	  while (handled_component_p (op))
	    {
	      if (TREE_CODE (op) == COMPONENT_REF)
		{
		  tree field, type, tem;
		  tree closest_match = NULL_TREE;
		  field = TREE_OPERAND (op, 1);
		  type = DECL_CONTEXT (field);
		  for (tem = TYPE_FIELDS (type); tem; tem = TREE_CHAIN (tem))
		    {
		      if (tem == field)
			break;
		      if (DECL_NONADDRESSABLE_P (tem)
			  == DECL_NONADDRESSABLE_P (field)
			  && gimple_compare_field_offset (tem, field))
			{
			  if (types_compatible_p (TREE_TYPE (tem),
						  TREE_TYPE (field)))
			    break;
			  else
			    closest_match = tem;
			}
		    }
		  /* In case of type mismatches across units we can fail
		     to unify some types and thus not find a proper
		     field-decl here.  */
		  if (tem == NULL_TREE)
		    {
		      /* Thus, emit a ODR violation warning.  */
		      if (warning_at (gimple_location (stmt), 0,
				      "use of type %<%E%> with two mismatching "
				      "declarations at field %<%E%>",
				      type, TREE_OPERAND (op, 1)))
			{
			  if (TYPE_FIELDS (type))
			    inform (DECL_SOURCE_LOCATION (TYPE_FIELDS (type)),
				    "original type declared here");
			  inform (DECL_SOURCE_LOCATION (TREE_OPERAND (op, 1)),
				  "field in mismatching type declared here");
			  if (TYPE_NAME (TREE_TYPE (field))
			      && (TREE_CODE (TYPE_NAME (TREE_TYPE (field)))
				  == TYPE_DECL))
			    inform (DECL_SOURCE_LOCATION
				      (TYPE_NAME (TREE_TYPE (field))),
				    "type of field declared here");
			  if (closest_match
			      && TYPE_NAME (TREE_TYPE (closest_match))
			      && (TREE_CODE (TYPE_NAME
				   (TREE_TYPE (closest_match))) == TYPE_DECL))
			    inform (DECL_SOURCE_LOCATION
				      (TYPE_NAME (TREE_TYPE (closest_match))),
				    "type of mismatching field declared here");
			}
		      /* And finally fixup the types.  */
		      TREE_OPERAND (op, 0)
			= build1 (VIEW_CONVERT_EXPR, type,
				  TREE_OPERAND (op, 0));
		    }
		  else
		    TREE_OPERAND (op, 1) = tem;
		}

	      op = TREE_OPERAND (op, 0);
	    }
	}
      break;

    case GIMPLE_NOP:
    case GIMPLE_PREDICT:
      break;

    default:
      internal_error ("bytecode stream: unknown GIMPLE statement tag %s",
		      lto_tag_name (tag));
    }

  /* Update the properties of symbols, SSA names and labels associated
     with STMT.  */
  if (code == GIMPLE_ASSIGN || code == GIMPLE_CALL)
    {
      tree lhs = gimple_get_lhs (stmt);
      if (lhs && TREE_CODE (lhs) == SSA_NAME)
	SSA_NAME_DEF_STMT (lhs) = stmt;
    }
  else if (code == GIMPLE_LABEL)
    gcc_assert (emit_label_in_global_context_p (gimple_label_label (stmt))
	        || DECL_CONTEXT (gimple_label_label (stmt)) == fn->decl);
  else if (code == GIMPLE_ASM)
    {
      unsigned i;

      for (i = 0; i < gimple_asm_noutputs (stmt); i++)
	{
	  tree op = TREE_VALUE (gimple_asm_output_op (stmt, i));
	  if (TREE_CODE (op) == SSA_NAME)
	    SSA_NAME_DEF_STMT (op) = stmt;
	}
    }

  /* Reset alias information.  */
  if (code == GIMPLE_CALL)
    gimple_call_reset_alias_info (stmt);

  /* Mark the statement modified so its operand vectors can be filled in.  */
  gimple_set_modified (stmt, true);

  return stmt;
}


/* Read a basic block with tag TAG from DATA_IN using input block IB.
   FN is the function being processed.  */

static void
input_bb (struct lto_input_block *ib, enum LTO_tags tag,
	  struct data_in *data_in, struct function *fn,
	  int count_materialization_scale)
{
  unsigned int index;
  basic_block bb;
  gimple_stmt_iterator bsi;

  /* This routine assumes that CFUN is set to FN, as it needs to call
     basic GIMPLE routines that use CFUN.  */
  gcc_assert (cfun == fn);

  index = lto_input_uleb128 (ib);
  bb = BASIC_BLOCK_FOR_FUNCTION (fn, index);

  bb->count = (lto_input_sleb128 (ib) * count_materialization_scale
	       + REG_BR_PROB_BASE / 2) / REG_BR_PROB_BASE;
  bb->loop_depth = lto_input_sleb128 (ib);
  bb->frequency = lto_input_sleb128 (ib);
  bb->flags = lto_input_sleb128 (ib);

  /* LTO_bb1 has statements.  LTO_bb0 does not.  */
  if (tag == LTO_bb0)
    return;

  bsi = gsi_start_bb (bb);
  tag = input_record_start (ib);
  while (tag)
    {
      gimple stmt = input_gimple_stmt (ib, data_in, fn, tag);
      if (!is_gimple_debug (stmt))
	find_referenced_vars_in (stmt);
      gsi_insert_after (&bsi, stmt, GSI_NEW_STMT);

      /* After the statement, expect a 0 delimiter or the EH region
	 that the previous statement belongs to.  */
      tag = input_record_start (ib);
      lto_tag_check_set (tag, 2, LTO_eh_region, LTO_null);

      if (tag == LTO_eh_region)
	{
	  HOST_WIDE_INT region = lto_input_sleb128 (ib);
	  gcc_assert (region == (int) region);
	  add_stmt_to_eh_lp (stmt, region);
	}

      tag = input_record_start (ib);
    }

  tag = input_record_start (ib);
  while (tag)
    {
      gimple phi = input_phi (ib, bb, data_in, fn);
      find_referenced_vars_in (phi);
      tag = input_record_start (ib);
    }
}

/* Go through all NODE edges and fixup call_stmt pointers
   so they point to STMTS.  */

static void
fixup_call_stmt_edges_1 (struct cgraph_node *node, gimple *stmts)
{
  struct cgraph_edge *cedge;
  for (cedge = node->callees; cedge; cedge = cedge->next_callee)
    cedge->call_stmt = stmts[cedge->lto_stmt_uid];
  for (cedge = node->indirect_calls; cedge; cedge = cedge->next_callee)
    cedge->call_stmt = stmts[cedge->lto_stmt_uid];
}

/* Fixup call_stmt pointers in NODE and all clones.  */

static void
fixup_call_stmt_edges (struct cgraph_node *orig, gimple *stmts)
{
  struct cgraph_node *node;

  while (orig->clone_of)
    orig = orig->clone_of;

  fixup_call_stmt_edges_1 (orig, stmts);
  if (orig->clones)
    for (node = orig->clones; node != orig;)
      {
	fixup_call_stmt_edges_1 (node, stmts);
	if (node->clones)
	  node = node->clones;
	else if (node->next_sibling_clone)
	  node = node->next_sibling_clone;
	else
	  {
	    while (node != orig && !node->next_sibling_clone)
	      node = node->clone_of;
	    if (node != orig)
	      node = node->next_sibling_clone;
	  }
      }
}

/* 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 function *fn;
  enum LTO_tags tag;
  gimple *stmts;
  basic_block bb;
  struct bitpack_d bp;
  struct cgraph_node *node;
  tree args, narg, oarg;
  int len;

  fn = DECL_STRUCT_FUNCTION (fn_decl);
  tag = input_record_start (ib);
  clear_line_info (data_in);

  gimple_register_cfg_hooks ();
  lto_tag_check (tag, LTO_function);

  /* Read all the attributes for FN.  */
  bp = lto_input_bitpack (ib);
  fn->is_thunk = bp_unpack_value (&bp, 1);
  fn->has_local_explicit_reg_vars = bp_unpack_value (&bp, 1);
  fn->after_tree_profile = bp_unpack_value (&bp, 1);
  fn->returns_pcc_struct = bp_unpack_value (&bp, 1);
  fn->returns_struct = bp_unpack_value (&bp, 1);
  fn->can_throw_non_call_exceptions = bp_unpack_value (&bp, 1);
  fn->always_inline_functions_inlined = bp_unpack_value (&bp, 1);
  fn->after_inlining = bp_unpack_value (&bp, 1);
  fn->dont_save_pending_sizes_p = bp_unpack_value (&bp, 1);
  fn->stdarg = bp_unpack_value (&bp, 1);
  fn->has_nonlocal_label = bp_unpack_value (&bp, 1);
  fn->calls_alloca = bp_unpack_value (&bp, 1);
  fn->calls_setjmp = bp_unpack_value (&bp, 1);
  fn->va_list_fpr_size = bp_unpack_value (&bp, 8);
  fn->va_list_gpr_size = bp_unpack_value (&bp, 8);

  /* Input the function start and end loci.  */
  fn->function_start_locus = lto_input_location (ib, data_in);
  fn->function_end_locus = lto_input_location (ib, data_in);

  /* Input the current IL state of the function.  */
  fn->curr_properties = lto_input_uleb128 (ib);

  /* Read the static chain and non-local goto save area.  */
  fn->static_chain_decl = lto_input_tree (ib, data_in);
  fn->nonlocal_goto_save_area = lto_input_tree (ib, data_in);

  /* Read all the local symbols.  */
  len = lto_input_sleb128 (ib);
  if (len > 0)
    {
      int i;
      VEC_safe_grow (tree, gc, fn->local_decls, len);
      for (i = 0; i < len; i++)
	{
	  tree t = lto_input_tree (ib, data_in);
	  VEC_replace (tree, fn->local_decls, i, t);
	}
    }

  /* Read all function arguments.  We need to re-map them here to the
     arguments of the merged function declaration.  */
  args = lto_input_tree (ib, data_in);
  for (oarg = args, narg = DECL_ARGUMENTS (fn_decl);
       oarg && narg;
       oarg = TREE_CHAIN (oarg), narg = TREE_CHAIN (narg))
    {
      int ix;
      bool res;
      res = lto_streamer_cache_lookup (data_in->reader_cache, oarg, &ix);
      gcc_assert (res);
      /* Replace the argument in the streamer cache.  */
      lto_streamer_cache_insert_at (data_in->reader_cache, narg, ix);
    }
  gcc_assert (!oarg && !narg);

  /* Read all the SSA names.  */
  input_ssa_names (ib, data_in, fn);

  /* Read the exception handling regions in the function.  */
  input_eh_regions (ib, data_in, fn);

  /* Read the tree of lexical scopes for the function.  */
  DECL_INITIAL (fn_decl) = lto_input_tree (ib, data_in);
  gcc_assert (DECL_INITIAL (fn_decl));
  DECL_SAVED_TREE (fn_decl) = NULL_TREE;
  node = cgraph_node (fn_decl);

  /* Read all the basic blocks.  */
  tag = input_record_start (ib);
  while (tag)
    {
      input_bb (ib, tag, data_in, fn,
		node->count_materialization_scale);
      tag = input_record_start (ib);
    }

  /* Fix up the call statements that are mentioned in the callgraph
     edges.  */
  renumber_gimple_stmt_uids ();
  stmts = (gimple *) xcalloc (gimple_stmt_max_uid (fn), sizeof (gimple));
  FOR_ALL_BB (bb)
    {
      gimple_stmt_iterator bsi = gsi_start_bb (bb);
      while (!gsi_end_p (bsi))
	{
	  gimple stmt = gsi_stmt (bsi);
	  /* If we're recompiling LTO objects with debug stmts but
	     we're not supposed to have debug stmts, remove them now.
	     We can't remove them earlier because this would cause uid
	     mismatches in fixups, but we can do it at this point, as
	     long as debug stmts don't require fixups.  */
	  if (!MAY_HAVE_DEBUG_STMTS && is_gimple_debug (stmt))
	    {
	      gimple_stmt_iterator gsi = bsi;
	      gsi_next (&bsi);
	      gsi_remove (&gsi, true);
	    }
	  else
	    {
	      gsi_next (&bsi);
	      stmts[gimple_uid (stmt)] = stmt;
	    }
	}
    }

  /* Set the gimple body to the statement sequence in the entry
     basic block.  FIXME lto, this is fairly hacky.  The existence
     of a gimple body is used by the cgraph routines, but we should
     really use the presence of the CFG.  */
  {
    edge_iterator ei = ei_start (ENTRY_BLOCK_PTR->succs);
    gimple_set_body (fn_decl, bb_seq (ei_edge (ei)->dest));
  }

  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);
}


/* Read initializer expressions for public statics.  DATA_IN is the
   file being read.  IB is the input block used for reading.  */

static void
input_alias_pairs (struct lto_input_block *ib, struct data_in *data_in)
{
  tree var;

  clear_line_info (data_in);

  /* Skip over all the unreferenced globals.  */
  do
    var = lto_input_tree (ib, data_in);
  while (var);

  var = lto_input_tree (ib, data_in);
  while (var)
    {
      const char *orig_name, *new_name;
      alias_pair *p;

      p = VEC_safe_push (alias_pair, gc, alias_pairs, NULL);
      p->decl = var;
      p->target = lto_input_tree (ib, data_in);

      /* If the target is a static object, we may have registered a
	 new name for it to avoid clashes between statics coming from
	 different files.  In that case, use the new name.  */
      orig_name = IDENTIFIER_POINTER (p->target);
      new_name = lto_get_decl_name_mapping (data_in->file_data, orig_name);
      if (strcmp (orig_name, new_name) != 0)
	p->target = get_identifier (new_name);

      var = lto_input_tree (ib, data_in);
    }
}


/* Read the body from DATA for function FN_DECL and fill it in.
   FILE_DATA are the global decls and types.  SECTION_TYPE is either
   LTO_section_function_body or LTO_section_static_initializer.  If
   section type is LTO_section_function_body, FN must be the decl for
   that function.  */

static void
lto_read_body (struct lto_file_decl_data *file_data, tree fn_decl,
	       const char *data, enum lto_section_type section_type)
{
  const struct lto_function_header *header;
  struct data_in *data_in;
  int32_t cfg_offset;
  int32_t main_offset;
  int32_t string_offset;
  struct lto_input_block ib_cfg;
  struct lto_input_block ib_main;

  header = (const struct lto_function_header *) data;
  cfg_offset = sizeof (struct lto_function_header);
  main_offset = cfg_offset + header->cfg_size;
  string_offset = main_offset + header->main_size;

  LTO_INIT_INPUT_BLOCK (ib_cfg,
		        data + cfg_offset,
			0,
			header->cfg_size);

  LTO_INIT_INPUT_BLOCK (ib_main,
			data + main_offset,
			0,
			header->main_size);

  data_in = lto_data_in_create (file_data, data + string_offset,
				header->string_size, NULL);

  /* Make sure the file was generated by the exact same compiler.  */
  lto_check_version (header->lto_header.major_version,
		     header->lto_header.minor_version);

  if (section_type == LTO_section_function_body)
    {
      struct function *fn = DECL_STRUCT_FUNCTION (fn_decl);
      struct lto_in_decl_state *decl_state;
      struct cgraph_node *node = cgraph_node (fn_decl);

      push_cfun (fn);
      init_tree_ssa (fn);

      /* Use the function's decl state. */
      decl_state = lto_get_function_in_decl_state (file_data, fn_decl);
      gcc_assert (decl_state);
      file_data->current_decl_state = decl_state;

      input_cfg (&ib_cfg, fn, node->count_materialization_scale);

      /* Set up the struct function.  */
      input_function (fn_decl, data_in, &ib_main);

      /* We should now be in SSA.  */
      cfun->gimple_df->in_ssa_p = true;

      /* Restore decl state */
      file_data->current_decl_state = file_data->global_decl_state;

      pop_cfun ();
    }
  else
    {
      input_alias_pairs (&ib_main, data_in);
    }

  clear_line_info (data_in);
  lto_data_in_delete (data_in);
}


/* Read the body of FN_DECL using DATA.  FILE_DATA holds the global
   decls and types.  */

void
lto_input_function_body (struct lto_file_decl_data *file_data,
			 tree fn_decl, const char *data)
{
  current_function_decl = fn_decl;
  lto_read_body (file_data, fn_decl, data, LTO_section_function_body);
}


/* Read in VAR_DECL using DATA.  FILE_DATA holds the global decls and
   types.  */

void
lto_input_constructors_and_inits (struct lto_file_decl_data *file_data,
				  const char *data)
{
  lto_read_body (file_data, NULL, data, LTO_section_static_initializer);
}


/* Return the resolution for the decl with index INDEX from DATA_IN. */

static enum ld_plugin_symbol_resolution
get_resolution (struct data_in *data_in, unsigned index)
{
  if (data_in->globals_resolution)
    {
      ld_plugin_symbol_resolution_t ret;
      /* We can have references to not emitted functions in
	 DECL_FUNCTION_PERSONALITY at least.  So we can and have
	 to indeed return LDPR_UNKNOWN in some cases.   */
      if (VEC_length (ld_plugin_symbol_resolution_t,
		      data_in->globals_resolution) <= index)
	return LDPR_UNKNOWN;
      ret = VEC_index (ld_plugin_symbol_resolution_t,
		       data_in->globals_resolution,
		       index);
      return ret;
    }
  else
    /* Delay resolution finding until decl merging.  */
    return LDPR_UNKNOWN;
}


/* Unpack all the non-pointer fields of the TS_BASE structure of
   expression EXPR from bitpack BP.  */

static void
unpack_ts_base_value_fields (struct bitpack_d *bp, tree expr)
{
  /* Note that the code for EXPR has already been unpacked to create EXPR in
     lto_materialize_tree.  */
  if (!TYPE_P (expr))
    {
      TREE_SIDE_EFFECTS (expr) = (unsigned) bp_unpack_value (bp, 1);
      TREE_CONSTANT (expr) = (unsigned) bp_unpack_value (bp, 1);
      TREE_READONLY (expr) = (unsigned) bp_unpack_value (bp, 1);

      /* TREE_PUBLIC is used on types to indicate that the type
	 has a TYPE_CACHED_VALUES vector.  This is not streamed out,
	 so we skip it here.  */
      TREE_PUBLIC (expr) = (unsigned) bp_unpack_value (bp, 1);
    }
  else
    bp_unpack_value (bp, 4);
  TREE_ADDRESSABLE (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_THIS_VOLATILE (expr) = (unsigned) bp_unpack_value (bp, 1);
  if (DECL_P (expr))
    DECL_UNSIGNED (expr) = (unsigned) bp_unpack_value (bp, 1);
  else if (TYPE_P (expr))
    TYPE_UNSIGNED (expr) = (unsigned) bp_unpack_value (bp, 1);
  else
    bp_unpack_value (bp, 1);
  TREE_ASM_WRITTEN (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_NO_WARNING (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_USED (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_NOTHROW (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_STATIC (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_PRIVATE (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_PROTECTED (expr) = (unsigned) bp_unpack_value (bp, 1);
  TREE_DEPRECATED (expr) = (unsigned) bp_unpack_value (bp, 1);
  if (TYPE_P (expr))
    TYPE_SATURATING (expr) = (unsigned) bp_unpack_value (bp, 1);
  else if (TREE_CODE (expr) == SSA_NAME)
    SSA_NAME_IS_DEFAULT_DEF (expr) = (unsigned) bp_unpack_value (bp, 1);
  else
    bp_unpack_value (bp, 1);
}


/* Unpack all the non-pointer fields of the TS_REAL_CST structure of
   expression EXPR from bitpack BP.  */

static void
unpack_ts_real_cst_value_fields (struct bitpack_d *bp, tree expr)
{
  unsigned i;
  REAL_VALUE_TYPE r;
  REAL_VALUE_TYPE *rp;

  r.cl = (unsigned) bp_unpack_value (bp, 2);
  r.decimal = (unsigned) bp_unpack_value (bp, 1);
  r.sign = (unsigned) bp_unpack_value (bp, 1);
  r.signalling = (unsigned) bp_unpack_value (bp, 1);
  r.canonical = (unsigned) bp_unpack_value (bp, 1);
  r.uexp = (unsigned) bp_unpack_value (bp, EXP_BITS);
  for (i = 0; i < SIGSZ; i++)
    r.sig[i] = (unsigned long) bp_unpack_value (bp, HOST_BITS_PER_LONG);

  rp = ggc_alloc_real_value ();
  memcpy (rp, &r, sizeof (REAL_VALUE_TYPE));
  TREE_REAL_CST_PTR (expr) = rp;
}


/* Unpack all the non-pointer fields of the TS_FIXED_CST structure of
   expression EXPR from bitpack BP.  */

static void
unpack_ts_fixed_cst_value_fields (struct bitpack_d *bp, tree expr)
{
  struct fixed_value fv;

  fv.data.low = (HOST_WIDE_INT) bp_unpack_value (bp, HOST_BITS_PER_WIDE_INT);
  fv.data.high = (HOST_WIDE_INT) bp_unpack_value (bp, HOST_BITS_PER_WIDE_INT);
  fv.mode = (enum machine_mode) bp_unpack_value (bp, HOST_BITS_PER_INT);
  TREE_FIXED_CST (expr) = fv;
}


/* Unpack all the non-pointer fields of the TS_DECL_COMMON structure
   of expression EXPR from bitpack BP.  */

static void
unpack_ts_decl_common_value_fields (struct bitpack_d *bp, tree expr)
{
  DECL_MODE (expr) = (enum machine_mode) bp_unpack_value (bp, 8);
  DECL_NONLOCAL (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_VIRTUAL_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_IGNORED_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_ABSTRACT (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_ARTIFICIAL (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_USER_ALIGN (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_PRESERVE_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_DEBUG_EXPR_IS_FROM (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_EXTERNAL (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_GIMPLE_REG_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_ALIGN (expr) = (unsigned) bp_unpack_value (bp, HOST_BITS_PER_INT);

  if (TREE_CODE (expr) == LABEL_DECL)
    {
      DECL_ERROR_ISSUED (expr) = (unsigned) bp_unpack_value (bp, 1);
      EH_LANDING_PAD_NR (expr) = (int) bp_unpack_value (bp, HOST_BITS_PER_INT);

      /* Always assume an initial value of -1 for LABEL_DECL_UID to
	 force gimple_set_bb to recreate label_to_block_map.  */
      LABEL_DECL_UID (expr) = -1;
    }

  if (TREE_CODE (expr) == FIELD_DECL)
    {
      unsigned HOST_WIDE_INT off_align;
      DECL_PACKED (expr) = (unsigned) bp_unpack_value (bp, 1);
      DECL_NONADDRESSABLE_P (expr) = (unsigned) bp_unpack_value (bp, 1);
      off_align = (unsigned HOST_WIDE_INT) bp_unpack_value (bp, 8);
      SET_DECL_OFFSET_ALIGN (expr, off_align);
    }

  if (TREE_CODE (expr) == RESULT_DECL
      || TREE_CODE (expr) == PARM_DECL
      || TREE_CODE (expr) == VAR_DECL)
    {
      DECL_BY_REFERENCE (expr) = (unsigned) bp_unpack_value (bp, 1);
      if (TREE_CODE (expr) == VAR_DECL
	  || TREE_CODE (expr) == PARM_DECL)
	DECL_HAS_VALUE_EXPR_P (expr) = (unsigned) bp_unpack_value (bp, 1);
      DECL_RESTRICTED_P (expr) = (unsigned) bp_unpack_value (bp, 1);
    }
}


/* Unpack all the non-pointer fields of the TS_DECL_WRTL structure
   of expression EXPR from bitpack BP.  */

static void
unpack_ts_decl_wrtl_value_fields (struct bitpack_d *bp, tree expr)
{
  DECL_REGISTER (expr) = (unsigned) bp_unpack_value (bp, 1);
}


/* Unpack all the non-pointer fields of the TS_DECL_WITH_VIS structure
   of expression EXPR from bitpack BP.  */

static void
unpack_ts_decl_with_vis_value_fields (struct bitpack_d *bp, tree expr)
{
  DECL_DEFER_OUTPUT (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_COMMON (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_DLLIMPORT_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_WEAK (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_SEEN_IN_BIND_EXPR_P (expr) = (unsigned) bp_unpack_value (bp,  1);
  DECL_COMDAT (expr) = (unsigned) bp_unpack_value (bp,  1);
  DECL_VISIBILITY (expr) = (enum symbol_visibility) bp_unpack_value (bp,  2);
  DECL_VISIBILITY_SPECIFIED (expr) = (unsigned) bp_unpack_value (bp,  1);

  if (TREE_CODE (expr) == VAR_DECL)
    {
      DECL_HARD_REGISTER (expr) = (unsigned) bp_unpack_value (bp, 1);
      DECL_IN_TEXT_SECTION (expr) = (unsigned) bp_unpack_value (bp, 1);
      DECL_IN_CONSTANT_POOL (expr) = (unsigned) bp_unpack_value (bp, 1);
      DECL_TLS_MODEL (expr) = (enum tls_model) bp_unpack_value (bp,  3);
    }

  if (VAR_OR_FUNCTION_DECL_P (expr))
    {
      priority_type p;
      p = (priority_type) bp_unpack_value (bp, HOST_BITS_PER_SHORT);
      SET_DECL_INIT_PRIORITY (expr, p);
    }
}


/* Unpack all the non-pointer fields of the TS_FUNCTION_DECL structure
   of expression EXPR from bitpack BP.  */

static void
unpack_ts_function_decl_value_fields (struct bitpack_d *bp, tree expr)
{
  DECL_FUNCTION_CODE (expr) = (enum built_in_function) bp_unpack_value (bp, 11);
  DECL_BUILT_IN_CLASS (expr) = (enum built_in_class) bp_unpack_value (bp, 2);
  DECL_STATIC_CONSTRUCTOR (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_STATIC_DESTRUCTOR (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_UNINLINABLE (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_POSSIBLY_INLINED (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_IS_NOVOPS (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_IS_RETURNS_TWICE (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_IS_MALLOC (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_IS_OPERATOR_NEW (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_DECLARED_INLINE_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_STATIC_CHAIN (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_NO_INLINE_WARNING_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_NO_INSTRUMENT_FUNCTION_ENTRY_EXIT (expr)
    			= (unsigned) bp_unpack_value (bp, 1);
  DECL_NO_LIMIT_STACK (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_DISREGARD_INLINE_LIMITS (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_PURE_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  DECL_LOOPING_CONST_OR_PURE_P (expr) = (unsigned) bp_unpack_value (bp, 1);
  if (DECL_STATIC_DESTRUCTOR (expr))
    {
       priority_type p = (priority_type) bp_unpack_value (bp, HOST_BITS_PER_SHORT);
       SET_DECL_FINI_PRIORITY (expr, p);
    }
}


/* Unpack all the non-pointer fields of the TS_TYPE structure
   of expression EXPR from bitpack BP.  */

static void
unpack_ts_type_value_fields (struct bitpack_d *bp, tree expr)
{
  enum machine_mode mode;

  TYPE_PRECISION (expr) = (unsigned) bp_unpack_value (bp, 10);
  mode = (enum machine_mode) bp_unpack_value (bp, 8);
  SET_TYPE_MODE (expr, mode);
  TYPE_STRING_FLAG (expr) = (unsigned) bp_unpack_value (bp, 1);
  TYPE_NO_FORCE_BLK (expr) = (unsigned) bp_unpack_value (bp, 1);
  TYPE_NEEDS_CONSTRUCTING (expr) = (unsigned) bp_unpack_value (bp, 1);
  if (RECORD_OR_UNION_TYPE_P (expr))
    TYPE_TRANSPARENT_AGGR (expr) = (unsigned) bp_unpack_value (bp, 1);
  TYPE_PACKED (expr) = (unsigned) bp_unpack_value (bp, 1);
  TYPE_RESTRICT (expr) = (unsigned) bp_unpack_value (bp, 1);
  TYPE_CONTAINS_PLACEHOLDER_INTERNAL (expr)
    	= (unsigned) bp_unpack_value (bp, 2);
  TYPE_USER_ALIGN (expr) = (unsigned) bp_unpack_value (bp, 1);
  TYPE_READONLY (expr) = (unsigned) bp_unpack_value (bp, 1);
  TYPE_ALIGN (expr) = (unsigned) bp_unpack_value (bp, HOST_BITS_PER_INT);
  TYPE_ALIAS_SET (expr) = bp_unpack_value (bp, HOST_BITS_PER_INT);
}


/* Unpack all the non-pointer fields of the TS_BLOCK structure
   of expression EXPR from bitpack BP.  */

static void
unpack_ts_block_value_fields (struct bitpack_d *bp, tree expr)
{
  BLOCK_ABSTRACT (expr) = (unsigned) bp_unpack_value (bp, 1);
  BLOCK_NUMBER (expr) = (unsigned) bp_unpack_value (bp, 31);
}

/* Unpack all the non-pointer fields of the TS_TRANSLATION_UNIT_DECL
   structure of expression EXPR from bitpack BP.  */

static void
unpack_ts_translation_unit_decl_value_fields (struct bitpack_d *bp ATTRIBUTE_UNUSED, tree expr ATTRIBUTE_UNUSED)
{
}

/* Unpack all the non-pointer fields in EXPR into a bit pack.  */

static void
unpack_value_fields (struct bitpack_d *bp, tree expr)
{
  enum tree_code code;

  code = TREE_CODE (expr);

  /* Note that all these functions are highly sensitive to changes in
     the types and sizes of each of the fields being packed.  */
  unpack_ts_base_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_REAL_CST))
    unpack_ts_real_cst_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_FIXED_CST))
    unpack_ts_fixed_cst_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_DECL_COMMON))
    unpack_ts_decl_common_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_DECL_WRTL))
    unpack_ts_decl_wrtl_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_DECL_WITH_VIS))
    unpack_ts_decl_with_vis_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_FUNCTION_DECL))
    unpack_ts_function_decl_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_TYPE))
    unpack_ts_type_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_BLOCK))
    unpack_ts_block_value_fields (bp, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_SSA_NAME))
    {
      /* We only stream the version number of SSA names.  */
      gcc_unreachable ();
    }

  if (CODE_CONTAINS_STRUCT (code, TS_STATEMENT_LIST))
    {
      /* This is only used by GENERIC.  */
      gcc_unreachable ();
    }

  if (CODE_CONTAINS_STRUCT (code, TS_OMP_CLAUSE))
    {
      /* This is only used by High GIMPLE.  */
      gcc_unreachable ();
    }

  if (CODE_CONTAINS_STRUCT (code, TS_TRANSLATION_UNIT_DECL))
    unpack_ts_translation_unit_decl_value_fields (bp, expr);
}


/* Materialize a new tree from input block IB using descriptors in
   DATA_IN.  The code for the new tree should match TAG.  Store in
   *IX_P the index into the reader cache where the new tree is stored.  */

static tree
lto_materialize_tree (struct lto_input_block *ib, struct data_in *data_in,
		      enum LTO_tags tag, int *ix_p)
{
  struct bitpack_d bp;
  enum tree_code code;
  tree result;
#ifdef LTO_STREAMER_DEBUG
  HOST_WIDEST_INT orig_address_in_writer;
#endif
  HOST_WIDE_INT ix;

  result = NULL_TREE;

  /* Read the header of the node we are about to create.  */
  ix = lto_input_sleb128 (ib);
  gcc_assert ((int) ix == ix);
  *ix_p = (int) ix;

#ifdef LTO_STREAMER_DEBUG
  /* Read the word representing the memory address for the tree
     as it was written by the writer.  This is useful when
     debugging differences between the writer and reader.  */
  orig_address_in_writer = lto_input_sleb128 (ib);
  gcc_assert ((intptr_t) orig_address_in_writer == orig_address_in_writer);
#endif

  code = lto_tag_to_tree_code (tag);

  /* We should never see an SSA_NAME tree.  Only the version numbers of
     SSA names are ever written out.  See input_ssa_names.  */
  gcc_assert (code != SSA_NAME);

  /* Instantiate a new tree using the header data.  */
  if (CODE_CONTAINS_STRUCT (code, TS_STRING))
    result = input_string_cst (data_in, ib);
  else if (CODE_CONTAINS_STRUCT (code, TS_IDENTIFIER))
    result = input_identifier (data_in, ib);
  else if (CODE_CONTAINS_STRUCT (code, TS_VEC))
    {
      HOST_WIDE_INT len = lto_input_sleb128 (ib);
      result = make_tree_vec (len);
    }
  else if (CODE_CONTAINS_STRUCT (code, TS_BINFO))
    {
      unsigned HOST_WIDE_INT len = lto_input_uleb128 (ib);
      result = make_tree_binfo (len);
    }
  else
    {
      /* All other nodes can be materialized with a raw make_node
	 call.  */
      result = make_node (code);
    }

#ifdef LTO_STREAMER_DEBUG
  /* Store the original address of the tree as seen by the writer
     in RESULT's aux field.  This is useful when debugging streaming
     problems.  This way, a debugging session can be started on
     both writer and reader with a breakpoint using this address
     value in both.  */
  lto_orig_address_map (result, (intptr_t) orig_address_in_writer);
#endif

  /* Read the bitpack of non-pointer values from IB.  */
  bp = lto_input_bitpack (ib);

  /* The first word in BP contains the code of the tree that we
     are about to read.  */
  code = (enum tree_code) bp_unpack_value (&bp, 16);
  lto_tag_check (lto_tree_code_to_tag (code), tag);

  /* Unpack all the value fields from BP.  */
  unpack_value_fields (&bp, result);

  /* Enter RESULT in the reader cache.  This will make RESULT
     available so that circular references in the rest of the tree
     structure can be resolved in subsequent calls to lto_input_tree.  */
  lto_streamer_cache_insert_at (data_in->reader_cache, result, ix);

  return result;
}


/* Read a chain of tree nodes from input block IB. DATA_IN contains
   tables and descriptors for the file being read.  */

static tree
lto_input_chain (struct lto_input_block *ib, struct data_in *data_in)
{
  int i, count;
  tree first, prev, curr;

  first = prev = NULL_TREE;
  count = lto_input_sleb128 (ib);
  for (i = 0; i < count; i++)
    {
      curr = lto_input_tree (ib, data_in);
      if (prev)
	TREE_CHAIN (prev) = curr;
      else
	first = curr;

      TREE_CHAIN (curr) = NULL_TREE;
      prev = curr;
    }

  return first;
}


/* Read all pointer fields in the TS_COMMON structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */


static void
lto_input_ts_common_tree_pointers (struct lto_input_block *ib,
				   struct data_in *data_in, tree expr)
{
  if (TREE_CODE (expr) != IDENTIFIER_NODE)
    TREE_TYPE (expr) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_VECTOR structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_vector_tree_pointers (struct lto_input_block *ib,
				   struct data_in *data_in, tree expr)
{
  TREE_VECTOR_CST_ELTS (expr) = lto_input_chain (ib, data_in);
}


/* Read all pointer fields in the TS_COMPLEX structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_complex_tree_pointers (struct lto_input_block *ib,
				    struct data_in *data_in, tree expr)
{
  TREE_REALPART (expr) = lto_input_tree (ib, data_in);
  TREE_IMAGPART (expr) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_DECL_MINIMAL structure of EXPR
   from input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_decl_minimal_tree_pointers (struct lto_input_block *ib,
					 struct data_in *data_in, tree expr)
{
  DECL_NAME (expr) = lto_input_tree (ib, data_in);
  DECL_CONTEXT (expr) = lto_input_tree (ib, data_in);
  DECL_SOURCE_LOCATION (expr) = lto_input_location (ib, data_in);
}


/* Read all pointer fields in the TS_DECL_COMMON structure of EXPR from
   input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_decl_common_tree_pointers (struct lto_input_block *ib,
					struct data_in *data_in, tree expr)
{
  DECL_SIZE (expr) = lto_input_tree (ib, data_in);
  DECL_SIZE_UNIT (expr) = lto_input_tree (ib, data_in);

  if (TREE_CODE (expr) != FUNCTION_DECL
      && TREE_CODE (expr) != TRANSLATION_UNIT_DECL)
    DECL_INITIAL (expr) = lto_input_tree (ib, data_in);

  DECL_ATTRIBUTES (expr) = lto_input_tree (ib, data_in);
  /* Do not stream DECL_ABSTRACT_ORIGIN.  We cannot handle debug information
     for early inlining so drop it on the floor instead of ICEing in
     dwarf2out.c.  */

  if (TREE_CODE (expr) == PARM_DECL)
    TREE_CHAIN (expr) = lto_input_chain (ib, data_in);

  if ((TREE_CODE (expr) == VAR_DECL
       || TREE_CODE (expr) == PARM_DECL)
      && DECL_HAS_VALUE_EXPR_P (expr))
    SET_DECL_VALUE_EXPR (expr, lto_input_tree (ib, data_in));

  if (TREE_CODE (expr) == VAR_DECL)
    {
      tree dexpr = lto_input_tree (ib, data_in);
      if (dexpr)
	SET_DECL_DEBUG_EXPR (expr, dexpr);
    }
}


/* Read all pointer fields in the TS_DECL_NON_COMMON structure of
   EXPR from input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_decl_non_common_tree_pointers (struct lto_input_block *ib,
					    struct data_in *data_in, tree expr)
{
  if (TREE_CODE (expr) == FUNCTION_DECL)
    {
      DECL_ARGUMENTS (expr) = lto_input_tree (ib, data_in);
      DECL_RESULT (expr) = lto_input_tree (ib, data_in);
    }
  DECL_VINDEX (expr) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_DECL_WITH_VIS structure of EXPR
   from input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_decl_with_vis_tree_pointers (struct lto_input_block *ib,
				          struct data_in *data_in, tree expr)
{
  tree id;

  id = lto_input_tree (ib, data_in);
  if (id)
    {
      gcc_assert (TREE_CODE (id) == IDENTIFIER_NODE);
      SET_DECL_ASSEMBLER_NAME (expr, id);
    }

  DECL_SECTION_NAME (expr) = lto_input_tree (ib, data_in);
  DECL_COMDAT_GROUP (expr) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_FIELD_DECL structure of EXPR from
   input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_field_decl_tree_pointers (struct lto_input_block *ib,
				       struct data_in *data_in, tree expr)
{
  DECL_FIELD_OFFSET (expr) = lto_input_tree (ib, data_in);
  DECL_BIT_FIELD_TYPE (expr) = lto_input_tree (ib, data_in);
  DECL_QUALIFIER (expr) = lto_input_tree (ib, data_in);
  DECL_FIELD_BIT_OFFSET (expr) = lto_input_tree (ib, data_in);
  DECL_FCONTEXT (expr) = lto_input_tree (ib, data_in);
  TREE_CHAIN (expr) = lto_input_chain (ib, data_in);
}


/* Read all pointer fields in the TS_FUNCTION_DECL structure of EXPR
   from input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_function_decl_tree_pointers (struct lto_input_block *ib,
					  struct data_in *data_in, tree expr)
{
  /* DECL_STRUCT_FUNCTION is handled by lto_input_function.  FIXME lto,
     maybe it should be handled here?  */
  DECL_FUNCTION_PERSONALITY (expr) = lto_input_tree (ib, data_in);
  DECL_FUNCTION_SPECIFIC_TARGET (expr) = lto_input_tree (ib, data_in);
  DECL_FUNCTION_SPECIFIC_OPTIMIZATION (expr) = lto_input_tree (ib, data_in);

  /* If the file contains a function with an EH personality set,
     then it was compiled with -fexceptions.  In that case, initialize
     the backend EH machinery.  */
  if (DECL_FUNCTION_PERSONALITY (expr))
    lto_init_eh ();
}


/* Read all pointer fields in the TS_TYPE structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_type_tree_pointers (struct lto_input_block *ib,
				 struct data_in *data_in, tree expr)
{
  if (TREE_CODE (expr) == ENUMERAL_TYPE)
    TYPE_VALUES (expr) = lto_input_tree (ib, data_in);
  else if (TREE_CODE (expr) == ARRAY_TYPE)
    TYPE_DOMAIN (expr) = lto_input_tree (ib, data_in);
  else if (RECORD_OR_UNION_TYPE_P (expr))
    TYPE_FIELDS (expr) = lto_input_tree (ib, data_in);
  else if (TREE_CODE (expr) == FUNCTION_TYPE
	   || TREE_CODE (expr) == METHOD_TYPE)
    TYPE_ARG_TYPES (expr) = lto_input_tree (ib, data_in);

  TYPE_SIZE (expr) = lto_input_tree (ib, data_in);
  TYPE_SIZE_UNIT (expr) = lto_input_tree (ib, data_in);
  TYPE_ATTRIBUTES (expr) = lto_input_tree (ib, data_in);
  TYPE_NAME (expr) = lto_input_tree (ib, data_in);
  /* Do not stream TYPE_POINTER_TO or TYPE_REFERENCE_TO nor
     TYPE_NEXT_PTR_TO or TYPE_NEXT_REF_TO.  */
  if (!POINTER_TYPE_P (expr))
    TYPE_MINVAL (expr) = lto_input_tree (ib, data_in);
  TYPE_MAXVAL (expr) = lto_input_tree (ib, data_in);
  TYPE_MAIN_VARIANT (expr) = lto_input_tree (ib, data_in);
  /* Do not stream TYPE_NEXT_VARIANT, we reconstruct the variant lists
     during fixup.  */
  if (RECORD_OR_UNION_TYPE_P (expr))
    TYPE_BINFO (expr) = lto_input_tree (ib, data_in);
  TYPE_CONTEXT (expr) = lto_input_tree (ib, data_in);
  /* TYPE_CANONICAL gets re-computed during type merging.  */
  TYPE_CANONICAL (expr) = NULL_TREE;
  TYPE_STUB_DECL (expr) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_LIST structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_list_tree_pointers (struct lto_input_block *ib,
				 struct data_in *data_in, tree expr)
{
  TREE_PURPOSE (expr) = lto_input_tree (ib, data_in);
  TREE_VALUE (expr) = lto_input_tree (ib, data_in);
  TREE_CHAIN (expr) = lto_input_chain (ib, data_in);
}


/* Read all pointer fields in the TS_VEC structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_vec_tree_pointers (struct lto_input_block *ib,
				struct data_in *data_in, tree expr)
{
  int i;

  /* Note that TREE_VEC_LENGTH was read by lto_materialize_tree to
     instantiate EXPR.  */
  for (i = 0; i < TREE_VEC_LENGTH (expr); i++)
    TREE_VEC_ELT (expr, i) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_EXP structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */


static void
lto_input_ts_exp_tree_pointers (struct lto_input_block *ib,
			        struct data_in *data_in, tree expr)
{
  int i, length;
  location_t loc;

  length = lto_input_sleb128 (ib);
  gcc_assert (length == TREE_OPERAND_LENGTH (expr));

  for (i = 0; i < length; i++)
    TREE_OPERAND (expr, i) = lto_input_tree (ib, data_in);

  loc = lto_input_location (ib, data_in);
  SET_EXPR_LOCATION (expr, loc);
  TREE_BLOCK (expr) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_BLOCK structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_block_tree_pointers (struct lto_input_block *ib,
				  struct data_in *data_in, tree expr)
{
  /* Do not stream BLOCK_SOURCE_LOCATION.  We cannot handle debug information
     for early inlining so drop it on the floor instead of ICEing in
     dwarf2out.c.  */
  BLOCK_VARS (expr) = lto_input_chain (ib, data_in);

  /* Do not stream BLOCK_NONLOCALIZED_VARS.  We cannot handle debug information
     for early inlining so drop it on the floor instead of ICEing in
     dwarf2out.c.  */

  BLOCK_SUPERCONTEXT (expr) = lto_input_tree (ib, data_in);
  /* Do not stream BLOCK_ABSTRACT_ORIGIN.  We cannot handle debug information
     for early inlining so drop it on the floor instead of ICEing in
     dwarf2out.c.  */
  BLOCK_FRAGMENT_ORIGIN (expr) = lto_input_tree (ib, data_in);
  BLOCK_FRAGMENT_CHAIN (expr) = lto_input_tree (ib, data_in);
  /* We re-compute BLOCK_SUBBLOCKS of our parent here instead
     of streaming it.  For non-BLOCK BLOCK_SUPERCONTEXTs we still
     stream the child relationship explicitly.  */
  if (BLOCK_SUPERCONTEXT (expr)
      && TREE_CODE (BLOCK_SUPERCONTEXT (expr)) == BLOCK)
    {
      BLOCK_CHAIN (expr) = BLOCK_SUBBLOCKS (BLOCK_SUPERCONTEXT (expr));
      BLOCK_SUBBLOCKS (BLOCK_SUPERCONTEXT (expr)) = expr;
    }
  /* The global block is rooted at the TU decl.  Hook it here to
     avoid the need to stream in this block during WPA time.  */
  else if (BLOCK_SUPERCONTEXT (expr)
	   && TREE_CODE (BLOCK_SUPERCONTEXT (expr)) == TRANSLATION_UNIT_DECL)
    DECL_INITIAL (BLOCK_SUPERCONTEXT (expr)) = expr;
  /* The function-level block is connected at the time we read in
     function bodies for the same reason.  */
}


/* Read all pointer fields in the TS_BINFO structure of EXPR from input
   block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_binfo_tree_pointers (struct lto_input_block *ib,
				  struct data_in *data_in, tree expr)
{
  unsigned i, len;
  tree t;

  /* Note that the number of slots in EXPR was read in
     lto_materialize_tree when instantiating EXPR.  However, the
     vector is empty so we cannot rely on VEC_length to know how many
     elements to read.  So, this list is emitted as a 0-terminated
     list on the writer side.  */
  do
    {
      t = lto_input_tree (ib, data_in);
      if (t)
	VEC_quick_push (tree, BINFO_BASE_BINFOS (expr), t);
    }
  while (t);

  BINFO_OFFSET (expr) = lto_input_tree (ib, data_in);
  BINFO_VTABLE (expr) = lto_input_tree (ib, data_in);
  BINFO_VIRTUALS (expr) = lto_input_tree (ib, data_in);
  BINFO_VPTR_FIELD (expr) = lto_input_tree (ib, data_in);

  len = lto_input_uleb128 (ib);
  if (len > 0)
    {
      VEC_reserve_exact (tree, gc, BINFO_BASE_ACCESSES (expr), len);
      for (i = 0; i < len; i++)
	{
	  tree a = lto_input_tree (ib, data_in);
	  VEC_quick_push (tree, BINFO_BASE_ACCESSES (expr), a);
	}
    }

  BINFO_INHERITANCE_CHAIN (expr) = lto_input_tree (ib, data_in);
  BINFO_SUBVTT_INDEX (expr) = lto_input_tree (ib, data_in);
  BINFO_VPTR_INDEX (expr) = lto_input_tree (ib, data_in);
}


/* Read all pointer fields in the TS_CONSTRUCTOR structure of EXPR from
   input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_ts_constructor_tree_pointers (struct lto_input_block *ib,
				        struct data_in *data_in, tree expr)
{
  unsigned i, len;

  len = lto_input_uleb128 (ib);
  for (i = 0; i < len; i++)
    {
      tree index, value;

      index = lto_input_tree (ib, data_in);
      value = lto_input_tree (ib, data_in);
      CONSTRUCTOR_APPEND_ELT (CONSTRUCTOR_ELTS (expr), index, value);
    }
}


/* Input a TS_TARGET_OPTION tree from IB into EXPR.  */

static void
lto_input_ts_target_option (struct lto_input_block *ib, tree expr)
{
  unsigned i, len;
  struct bitpack_d bp;
  struct cl_target_option *t = TREE_TARGET_OPTION (expr);

  bp = lto_input_bitpack (ib);
  len = sizeof (struct cl_target_option);
  for (i = 0; i < len; i++)
    ((unsigned char *)t)[i] = bp_unpack_value (&bp, 8);
  if (bp_unpack_value (&bp, 32) != 0x12345678)
    fatal_error ("cl_target_option size mismatch in LTO reader and writer");
}

/* Input a TS_TRANSLATION_UNIT_DECL tree from IB and DATA_IN into EXPR.  */

static void
lto_input_ts_translation_unit_decl_tree_pointers (struct lto_input_block *ib,
						  struct data_in *data_in,
						  tree expr)
{
  TRANSLATION_UNIT_LANGUAGE (expr) = xstrdup (input_string (data_in, ib));
  VEC_safe_push (tree, gc, all_translation_units, expr);
}

/* Helper for lto_input_tree.  Read all pointer fields in EXPR from
   input block IB.  DATA_IN contains tables and descriptors for the
   file being read.  */

static void
lto_input_tree_pointers (struct lto_input_block *ib, struct data_in *data_in,
			 tree expr)
{
  enum tree_code code;

  code = TREE_CODE (expr);

  if (CODE_CONTAINS_STRUCT (code, TS_COMMON))
    lto_input_ts_common_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_VECTOR))
    lto_input_ts_vector_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_COMPLEX))
    lto_input_ts_complex_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_DECL_MINIMAL))
    lto_input_ts_decl_minimal_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_DECL_COMMON))
    lto_input_ts_decl_common_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_DECL_NON_COMMON))
    lto_input_ts_decl_non_common_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_DECL_WITH_VIS))
    lto_input_ts_decl_with_vis_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_FIELD_DECL))
    lto_input_ts_field_decl_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_FUNCTION_DECL))
    lto_input_ts_function_decl_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_TYPE))
    lto_input_ts_type_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_LIST))
    lto_input_ts_list_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_VEC))
    lto_input_ts_vec_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_EXP))
    lto_input_ts_exp_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_SSA_NAME))
    {
      /* We only stream the version number of SSA names.  */
      gcc_unreachable ();
    }

  if (CODE_CONTAINS_STRUCT (code, TS_BLOCK))
    lto_input_ts_block_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_BINFO))
    lto_input_ts_binfo_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_STATEMENT_LIST))
    {
      /* This should only appear in GENERIC.  */
      gcc_unreachable ();
    }

  if (CODE_CONTAINS_STRUCT (code, TS_CONSTRUCTOR))
    lto_input_ts_constructor_tree_pointers (ib, data_in, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_OMP_CLAUSE))
    {
      /* This should only appear in High GIMPLE.  */
      gcc_unreachable ();
    }

  if (CODE_CONTAINS_STRUCT (code, TS_OPTIMIZATION))
    {
      sorry ("optimization options not supported yet");
    }

  if (CODE_CONTAINS_STRUCT (code, TS_TARGET_OPTION))
    lto_input_ts_target_option (ib, expr);

  if (CODE_CONTAINS_STRUCT (code, TS_TRANSLATION_UNIT_DECL))
    lto_input_ts_translation_unit_decl_tree_pointers (ib, data_in, expr);
}


/* Register DECL with the global symbol table and change its
   name if necessary to avoid name clashes for static globals across
   different files.  */

static void
lto_register_var_decl_in_symtab (struct data_in *data_in, tree decl)
{
  tree context;

  /* Variable has file scope, not local. Need to ensure static variables
     between different files don't clash unexpectedly.  */
  if (!TREE_PUBLIC (decl)
      && !((context = decl_function_context (decl))
	   && auto_var_in_fn_p (decl, context)))
    {
      /* ??? We normally pre-mangle names before we serialize them
	 out.  Here, in lto1, we do not know the language, and
	 thus cannot do the mangling again. Instead, we just
	 append a suffix to the mangled name.  The resulting name,
	 however, is not a properly-formed mangled name, and will
	 confuse any attempt to unmangle it.  */
      const char *name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
      char *label;

      ASM_FORMAT_PRIVATE_NAME (label, name, DECL_UID (decl));
      SET_DECL_ASSEMBLER_NAME (decl, get_identifier (label));
      rest_of_decl_compilation (decl, 1, 0);

      VEC_safe_push (tree, gc, lto_global_var_decls, decl);
    }

  /* If this variable has already been declared, queue the
     declaration for merging.  */
  if (TREE_PUBLIC (decl))
    {
      int ix;
      if (!lto_streamer_cache_lookup (data_in->reader_cache, decl, &ix))
	gcc_unreachable ();
      lto_symtab_register_decl (decl, get_resolution (data_in, ix),
				data_in->file_data);
    }
}



/* Register DECL with the global symbol table and change its
   name if necessary to avoid name clashes for static globals across
   different files.  DATA_IN contains descriptors and tables for the
   file being read.  */

static void
lto_register_function_decl_in_symtab (struct data_in *data_in, tree decl)
{
  /* Need to ensure static entities between different files
     don't clash unexpectedly.  */
  if (!TREE_PUBLIC (decl))
    {
      /* We must not use the DECL_ASSEMBLER_NAME macro here, as it
	 may set the assembler name where it was previously empty.  */
      tree old_assembler_name = decl->decl_with_vis.assembler_name;

      /* FIXME lto: We normally pre-mangle names before we serialize
	 them out.  Here, in lto1, we do not know the language, and
	 thus cannot do the mangling again. Instead, we just append a
	 suffix to the mangled name.  The resulting name, however, is
	 not a properly-formed mangled name, and will confuse any
	 attempt to unmangle it.  */
      const char *name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
      char *label;

      ASM_FORMAT_PRIVATE_NAME (label, name, DECL_UID (decl));
      SET_DECL_ASSEMBLER_NAME (decl, get_identifier (label));

      /* We may arrive here with the old assembler name not set
	 if the function body is not needed, e.g., it has been
	 inlined away and does not appear in the cgraph.  */
      if (old_assembler_name)
	{
	  tree new_assembler_name = DECL_ASSEMBLER_NAME (decl);

	  /* Make the original assembler name available for later use.
	     We may have used it to indicate the section within its
	     object file where the function body may be found.
	     FIXME lto: Find a better way to maintain the function decl
	     to body section mapping so we don't need this hack.  */
	  lto_record_renamed_decl (data_in->file_data,
				   IDENTIFIER_POINTER (old_assembler_name),
				   IDENTIFIER_POINTER (new_assembler_name));

	  /* Also register the reverse mapping so that we can find the
	     new name given to an existing assembler name (used when
	     restoring alias pairs in input_constructors_or_inits.  */
	  lto_record_renamed_decl (data_in->file_data,
				   IDENTIFIER_POINTER (new_assembler_name),
				   IDENTIFIER_POINTER (old_assembler_name));
	}
    }

  /* If this variable has already been declared, queue the
     declaration for merging.  */
  if (TREE_PUBLIC (decl) && !DECL_ABSTRACT (decl))
    {
      int ix;
      if (!lto_streamer_cache_lookup (data_in->reader_cache, decl, &ix))
	gcc_unreachable ();
      lto_symtab_register_decl (decl, get_resolution (data_in, ix),
				data_in->file_data);
    }
}


/* Read an index IX from input block IB and return the tree node at
   DATA_IN->FILE_DATA->GLOBALS_INDEX[IX].  */

static tree
lto_get_pickled_tree (struct lto_input_block *ib, struct data_in *data_in)
{
  HOST_WIDE_INT ix;
  tree result;
  enum LTO_tags expected_tag;
  unsigned HOST_WIDE_INT orig_offset;

  ix = lto_input_sleb128 (ib);
  expected_tag = (enum LTO_tags) lto_input_uleb128 (ib);

  orig_offset = lto_input_uleb128 (ib);
  gcc_assert (orig_offset == (unsigned) orig_offset);

  result = lto_streamer_cache_get (data_in->reader_cache, ix);
  if (result == NULL_TREE)
    {
      /* We have not yet read the cache slot IX.  Go to the offset
	 in the stream where the physical tree node is, and materialize
	 it from there.  */
      struct lto_input_block fwd_ib;

      /* If we are trying to go back in the stream, something is wrong.
	 We should've read the node at the earlier position already.  */
      if (ib->p >= orig_offset)
	internal_error ("bytecode stream: tried to jump backwards in the "
		        "stream");

      LTO_INIT_INPUT_BLOCK (fwd_ib, ib->data, orig_offset, ib->len);
      result = lto_input_tree (&fwd_ib, data_in);
    }

  gcc_assert (result
              && TREE_CODE (result) == lto_tag_to_tree_code (expected_tag));

  return result;
}


/* Read a code and class from input block IB and return the
   corresponding builtin.  DATA_IN is as in lto_input_tree.  */

static tree
lto_get_builtin_tree (struct lto_input_block *ib, struct data_in *data_in)
{
  enum built_in_class fclass;
  enum built_in_function fcode;
  const char *asmname;
  tree result;
  int ix;

  fclass = (enum built_in_class) lto_input_uleb128 (ib);
  gcc_assert (fclass == BUILT_IN_NORMAL || fclass == BUILT_IN_MD);

  fcode = (enum built_in_function) lto_input_uleb128 (ib);

  ix = lto_input_sleb128 (ib);
  gcc_assert (ix == (int) ix);

  if (fclass == BUILT_IN_NORMAL)
    {
      gcc_assert (fcode < END_BUILTINS);
      result = built_in_decls[fcode];
      gcc_assert (result);
    }
  else if (fclass == BUILT_IN_MD)
    {
      result = targetm.builtin_decl (fcode, true);
      if (!result || result == error_mark_node)
	fatal_error ("target specific builtin not available");
    }
  else
    gcc_unreachable ();

  asmname = input_string (data_in, ib);
  if (asmname)
    set_builtin_user_assembler_name (result, asmname);

  lto_streamer_cache_insert_at (data_in->reader_cache, result, ix);

  return result;
}


/* Read the physical representation of a tree node with tag TAG from
   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,
	       enum LTO_tags tag)
{
  tree result;
  int ix;

  result = lto_materialize_tree (ib, data_in, tag, &ix);

  /* Read all the pointer fields in RESULT.  */
  lto_input_tree_pointers (ib, data_in, result);

  /* We should never try to instantiate an MD or NORMAL builtin here.  */
  if (TREE_CODE (result) == FUNCTION_DECL)
    gcc_assert (!lto_stream_as_builtin_p (result));

  if (TREE_CODE (result) == VAR_DECL)
    lto_register_var_decl_in_symtab (data_in, result);
  else if (TREE_CODE (result) == FUNCTION_DECL && !DECL_BUILT_IN (result))
    lto_register_function_decl_in_symtab (data_in, result);

  /* end_marker = */ lto_input_1_unsigned (ib);

#ifdef LTO_STREAMER_DEBUG
  /* Remove the mapping to RESULT's original address set by
     lto_materialize_tree.  */
  lto_orig_address_remove (result);
#endif

  return result;
}


/* Read and INTEGER_CST node from input block IB using the per-file
   context in DATA_IN.  */

static tree
lto_input_integer_cst (struct lto_input_block *ib, struct data_in *data_in)
{
  tree result, type;
  HOST_WIDE_INT low, high;
  bool overflow_p;

  type = lto_input_tree (ib, data_in);
  overflow_p = (lto_input_1_unsigned (ib) != 0);
  low = lto_input_uleb128 (ib);
  high = lto_input_uleb128 (ib);
  result = build_int_cst_wide (type, low, high);

  /* If the original constant had overflown, build a replica of RESULT to
     avoid modifying the shared constant returned by build_int_cst_wide.  */
  if (overflow_p)
    {
      result = copy_node (result);
      TREE_OVERFLOW (result) = 1;
    }

  return result;
}


/* Read a tree from input block IB using the per-file context in
   DATA_IN.  This context is used, for example, to resolve references
   to previously read nodes.  */

tree
lto_input_tree (struct lto_input_block *ib, struct data_in *data_in)
{
  enum LTO_tags tag;
  tree result;

  tag = input_record_start (ib);
  gcc_assert ((unsigned) tag < (unsigned) LTO_NUM_TAGS);

  if (tag == LTO_null)
    result = NULL_TREE;
  else if (tag >= LTO_field_decl_ref && tag <= LTO_global_decl_ref)
    {
      /* If TAG is a reference to an indexable tree, the next value
	 in IB is the index into the table where we expect to find
	 that tree.  */
      result = lto_input_tree_ref (ib, data_in, cfun, tag);
    }
  else if (tag == LTO_tree_pickle_reference)
    {
      /* If TAG is a reference to a previously read tree, look it up in
	 the reader cache.  */
      result = lto_get_pickled_tree (ib, data_in);
    }
  else if (tag == LTO_builtin_decl)
    {
      /* If we are going to read a built-in function, all we need is
	 the code and class.  */
      result = lto_get_builtin_tree (ib, data_in);
    }
  else if (tag == lto_tree_code_to_tag (INTEGER_CST))
    {
      /* For integer constants we only need the type and its hi/low
	 words.  */
      result = lto_input_integer_cst (ib, data_in);
    }
  else
    {
      /* Otherwise, materialize a new node from IB.  */
      result = lto_read_tree (ib, data_in, tag);
    }

  return result;
}


/* Initialization for the LTO reader.  */

void
lto_init_reader (void)
{
  lto_streamer_init ();

  memset (&lto_stats, 0, sizeof (lto_stats));
  bitmap_obstack_initialize (NULL);

  file_name_hash_table = htab_create (37, hash_string_slot_node,
				      eq_string_slot_node, free);

  gimple_register_cfg_hooks ();
}


/* Create a new data_in object for FILE_DATA. STRINGS is the string
   table to use with LEN strings.  RESOLUTIONS is the vector of linker
   resolutions (NULL if not using a linker plugin).  */

struct data_in *
lto_data_in_create (struct lto_file_decl_data *file_data, const char *strings,
		    unsigned len,
		    VEC(ld_plugin_symbol_resolution_t,heap) *resolutions)
{
  struct data_in *data_in = XCNEW (struct data_in);
  data_in->file_data = file_data;
  data_in->strings = strings;
  data_in->strings_len = len;
  data_in->globals_resolution = resolutions;
  data_in->reader_cache = lto_streamer_cache_create ();

  return data_in;
}


/* Remove DATA_IN.  */

void
lto_data_in_delete (struct data_in *data_in)
{
  VEC_free (ld_plugin_symbol_resolution_t, heap, data_in->globals_resolution);
  lto_streamer_cache_delete (data_in->reader_cache);
  free (data_in->labels);
  free (data_in);
}
