-Wwrite-strings: The Rest
[deliverable/binutils-gdb.git] / gdb / dwarf2read.c
index 91c6a8feeee4c70c7fbad920aa79f2926c389216..966e1ee81ba99a17f96b095c19a5d14485f84af9 100644 (file)
@@ -1,6 +1,6 @@
 /* DWARF 2 debugging format support for GDB.
 
-   Copyright (C) 1994-2015 Free Software Foundation, Inc.
+   Copyright (C) 1994-2017 Free Software Foundation, Inc.
 
    Adapted by Gary Funck (gary@intrepid.com), Intrepid Technology,
    Inc.  with support from Florida State University (under contract
@@ -53,7 +53,6 @@
 #include "block.h"
 #include "addrmap.h"
 #include "typeprint.h"
-#include "jv-lang.h"
 #include "psympriv.h"
 #include <sys/stat.h>
 #include "completer.h"
 #include "source.h"
 #include "filestuff.h"
 #include "build-id.h"
+#include "namespace.h"
+#include "common/gdb_unlinker.h"
+#include "common/function-view.h"
+#include "common/gdb_optional.h"
+#include "common/underlying.h"
 
 #include <fcntl.h>
 #include <sys/types.h>
+#include <algorithm>
 
 typedef struct symbol *symbolp;
 DEF_VEC_P (symbolp);
@@ -123,7 +128,7 @@ struct dwarf2_section_info
   union
   {
     /* If this is a real section, the bfd section.  */
-    asection *asection;
+    asection *section;
     /* If this is a virtual section, pointer to the containing ("real")
        section.  */
     struct dwarf2_section_info *containing_section;
@@ -138,7 +143,7 @@ struct dwarf2_section_info
   /* True if we have tried to read this section.  */
   char readin;
   /* True if this is a virtual section, False otherwise.
-     This specifies which of s.asection and s.containing_section to use.  */
+     This specifies which of s.section and s.containing_section to use.  */
   char is_virtual;
 };
 
@@ -220,10 +225,13 @@ struct dwarf2_per_objfile
   struct dwarf2_section_info abbrev;
   struct dwarf2_section_info line;
   struct dwarf2_section_info loc;
+  struct dwarf2_section_info loclists;
   struct dwarf2_section_info macinfo;
   struct dwarf2_section_info macro;
   struct dwarf2_section_info str;
+  struct dwarf2_section_info line_str;
   struct dwarf2_section_info ranges;
+  struct dwarf2_section_info rnglists;
   struct dwarf2_section_info addr;
   struct dwarf2_section_info frame;
   struct dwarf2_section_info eh_frame;
@@ -331,10 +339,13 @@ static const struct dwarf2_debug_sections dwarf2_elf_names =
   { ".debug_abbrev", ".zdebug_abbrev" },
   { ".debug_line", ".zdebug_line" },
   { ".debug_loc", ".zdebug_loc" },
+  { ".debug_loclists", ".zdebug_loclists" },
   { ".debug_macinfo", ".zdebug_macinfo" },
   { ".debug_macro", ".zdebug_macro" },
   { ".debug_str", ".zdebug_str" },
+  { ".debug_line_str", ".zdebug_line_str" },
   { ".debug_ranges", ".zdebug_ranges" },
+  { ".debug_rnglists", ".zdebug_rnglists" },
   { ".debug_types", ".zdebug_types" },
   { ".debug_addr", ".zdebug_addr" },
   { ".debug_frame", ".zdebug_frame" },
@@ -351,6 +362,7 @@ static const struct dwop_section_names
   struct dwarf2_section_names info_dwo;
   struct dwarf2_section_names line_dwo;
   struct dwarf2_section_names loc_dwo;
+  struct dwarf2_section_names loclists_dwo;
   struct dwarf2_section_names macinfo_dwo;
   struct dwarf2_section_names macro_dwo;
   struct dwarf2_section_names str_dwo;
@@ -365,6 +377,7 @@ dwop_section_names =
   { ".debug_info.dwo", ".zdebug_info.dwo" },
   { ".debug_line.dwo", ".zdebug_line.dwo" },
   { ".debug_loc.dwo", ".zdebug_loc.dwo" },
+  { ".debug_loclists.dwo", ".zdebug_loclists.dwo" },
   { ".debug_macinfo.dwo", ".zdebug_macinfo.dwo" },
   { ".debug_macro.dwo", ".zdebug_macro.dwo" },
   { ".debug_str.dwo", ".zdebug_str.dwo" },
@@ -384,7 +397,7 @@ struct comp_unit_head
   short version;
   unsigned char addr_size;
   unsigned char signed_addr_p;
-  sect_offset abbrev_offset;
+  sect_offset abbrev_sect_off;
 
   /* Size of file offsets; either 4 or 8.  */
   unsigned int offset_size;
@@ -392,13 +405,22 @@ struct comp_unit_head
   /* Size of the length field; either 4 or 12.  */
   unsigned int initial_length_size;
 
+  enum dwarf_unit_type unit_type;
+
   /* Offset to the first byte of this compilation unit header in the
      .debug_info section, for resolving relative reference dies.  */
-  sect_offset offset;
+  sect_offset sect_off;
 
   /* Offset to first die in this cu from the start of the cu.
      This will be the first byte following the compilation unit header.  */
-  cu_offset first_die_offset;
+  cu_offset first_die_cu_offset;
+
+  /* 64-bit signature of this type unit - it is valid only for
+     UNIT_TYPE DW_UT_type.  */
+  ULONGEST signature;
+
+  /* For types, offset in the type's DIE of the type defined by this TU.  */
+  cu_offset type_cu_offset_in_tu;
 };
 
 /* Type used for delaying computation of method physnames.
@@ -567,9 +589,12 @@ struct dwarf2_per_cu_data
      initial_length_size.
      If the DIE refers to a DWO file, this is always of the original die,
      not the DWO file.  */
-  sect_offset offset;
+  sect_offset sect_off;
   unsigned int length;
 
+  /* DWARF standard version this data has been read from (such as 4 or 5).  */
+  short dwarf_version;
+
   /* Flag indicating this compilation unit will be read in before
      any of the current compilation units are processed.  */
   unsigned int queued : 1;
@@ -610,7 +635,8 @@ struct dwarf2_per_cu_data
   struct dwarf2_section_info *section;
 
   /* Set to non-NULL iff this CU is currently loaded.  When it gets freed out
-     of the CU cache it gets reset to NULL again.  */
+     of the CU cache it gets reset to NULL again.  This is left as NULL for
+     dummy CUs (a CU header, but nothing else).  */
   struct dwarf2_cu *cu;
 
   /* The corresponding objfile.
@@ -702,7 +728,7 @@ struct stmt_list_hash
   struct dwo_unit *dwo_unit;
 
   /* Offset in .debug_line or .debug_line.dwo.  */
-  sect_offset line_offset;
+  sect_offset line_sect_off;
 };
 
 /* Each element of dwarf2_per_objfile->type_unit_groups is a pointer to
@@ -753,6 +779,7 @@ struct dwo_sections
   struct dwarf2_section_info abbrev;
   struct dwarf2_section_info line;
   struct dwarf2_section_info loc;
+  struct dwarf2_section_info loclists;
   struct dwarf2_section_info macinfo;
   struct dwarf2_section_info macro;
   struct dwarf2_section_info str;
@@ -777,8 +804,8 @@ struct dwo_unit
   /* The section this CU/TU lives in, in the DWO file.  */
   struct dwarf2_section_info *section;
 
-  /* Same as dwarf2_per_cu_data:{offset,length} but in the DWO section.  */
-  sect_offset offset;
+  /* Same as dwarf2_per_cu_data:{sect_off,length} but in the DWO section.  */
+  sect_offset sect_off;
   unsigned int length;
 
   /* For types, offset in the type's DIE of the type defined by this TU.  */
@@ -1027,16 +1054,46 @@ typedef void (die_reader_func_ftype) (const struct die_reader_specs *reader,
                                      int has_children,
                                      void *data);
 
+/* A 1-based directory index.  This is a strong typedef to prevent
+   accidentally using a directory index as a 0-based index into an
+   array/vector.  */
+enum class dir_index : unsigned int {};
+
+/* Likewise, a 1-based file name index.  */
+enum class file_name_index : unsigned int {};
+
 struct file_entry
 {
-  const char *name;
-  unsigned int dir_index;
-  unsigned int mod_time;
-  unsigned int length;
-  /* Non-zero if referenced by the Line Number Program.  */
-  int included_p;
+  file_entry () = default;
+
+  file_entry (const char *name_, dir_index d_index_,
+             unsigned int mod_time_, unsigned int length_)
+    : name (name_),
+      d_index (d_index_),
+      mod_time (mod_time_),
+      length (length_)
+  {}
+
+  /* Return the include directory at D_INDEX stored in LH.  Returns
+     NULL if D_INDEX is out of bounds.  */
+  const char *include_dir (const line_header *lh) const;
+
+  /* The file name.  Note this is an observing pointer.  The memory is
+     owned by debug_line_buffer.  */
+  const char *name {};
+
+  /* The directory index (1-based).  */
+  dir_index d_index {};
+
+  unsigned int mod_time {};
+
+  unsigned int length {};
+
+  /* True if referenced by the Line Number Program.  */
+  bool included_p {};
+
   /* The associated symbol table, if any.  */
-  struct symtab *symtab;
+  struct symtab *symtab {};
 };
 
 /* The line number information for a compilation unit (found in the
@@ -1044,52 +1101,99 @@ struct file_entry
    which contains the following information.  */
 struct line_header
 {
+  line_header ()
+    : offset_in_dwz {}
+  {}
+
+  /* Add an entry to the include directory table.  */
+  void add_include_dir (const char *include_dir);
+
+  /* Add an entry to the file name table.  */
+  void add_file_name (const char *name, dir_index d_index,
+                     unsigned int mod_time, unsigned int length);
+
+  /* Return the include dir at INDEX (1-based).  Returns NULL if INDEX
+     is out of bounds.  */
+  const char *include_dir_at (dir_index index) const
+  {
+    /* Convert directory index number (1-based) to vector index
+       (0-based).  */
+    size_t vec_index = to_underlying (index) - 1;
+
+    if (vec_index >= include_dirs.size ())
+      return NULL;
+    return include_dirs[vec_index];
+  }
+
+  /* Return the file name at INDEX (1-based).  Returns NULL if INDEX
+     is out of bounds.  */
+  file_entry *file_name_at (file_name_index index)
+  {
+    /* Convert file name index number (1-based) to vector index
+       (0-based).  */
+    size_t vec_index = to_underlying (index) - 1;
+
+    if (vec_index >= file_names.size ())
+      return NULL;
+    return &file_names[vec_index];
+  }
+
+  /* Const version of the above.  */
+  const file_entry *file_name_at (unsigned int index) const
+  {
+    if (index >= file_names.size ())
+      return NULL;
+    return &file_names[index];
+  }
+
   /* Offset of line number information in .debug_line section.  */
-  sect_offset offset;
+  sect_offset sect_off {};
 
   /* OFFSET is for struct dwz_file associated with dwarf2_per_objfile.  */
-  unsigned offset_in_dwz : 1;
-
-  unsigned int total_length;
-  unsigned short version;
-  unsigned int header_length;
-  unsigned char minimum_instruction_length;
-  unsigned char maximum_ops_per_instruction;
-  unsigned char default_is_stmt;
-  int line_base;
-  unsigned char line_range;
-  unsigned char opcode_base;
+  unsigned offset_in_dwz : 1; /* Can't initialize bitfields in-class.  */
+
+  unsigned int total_length {};
+  unsigned short version {};
+  unsigned int header_length {};
+  unsigned char minimum_instruction_length {};
+  unsigned char maximum_ops_per_instruction {};
+  unsigned char default_is_stmt {};
+  int line_base {};
+  unsigned char line_range {};
+  unsigned char opcode_base {};
 
   /* standard_opcode_lengths[i] is the number of operands for the
      standard opcode whose value is i.  This means that
      standard_opcode_lengths[0] is unused, and the last meaningful
      element is standard_opcode_lengths[opcode_base - 1].  */
-  unsigned char *standard_opcode_lengths;
+  std::unique_ptr<unsigned char[]> standard_opcode_lengths;
 
-  /* The include_directories table.  NOTE!  These strings are not
-     allocated with xmalloc; instead, they are pointers into
-     debug_line_buffer.  If you try to free them, `free' will get
-     indigestion.  */
-  unsigned int num_include_dirs, include_dirs_size;
-  const char **include_dirs;
+  /* The include_directories table.  Note these are observing
+     pointers.  The memory is owned by debug_line_buffer.  */
+  std::vector<const char *> include_dirs;
 
-  /* The file_names table.  NOTE!  These strings are not allocated
-     with xmalloc; instead, they are pointers into debug_line_buffer.
-     Don't try to free them directly.  */
-  unsigned int num_file_names, file_names_size;
-  struct file_entry *file_names;
+  /* The file_names table.  */
+  std::vector<file_entry> file_names;
 
   /* The start and end of the statement program following this
      header.  These point into dwarf2_per_objfile->line_buffer.  */
-  const gdb_byte *statement_program_start, *statement_program_end;
+  const gdb_byte *statement_program_start {}, *statement_program_end {};
 };
 
+typedef std::unique_ptr<line_header> line_header_up;
+
+const char *
+file_entry::include_dir (const line_header *lh) const
+{
+  return lh->include_dir_at (d_index);
+}
+
 /* When we construct a partial symbol table entry we only
    need this much information.  */
 struct partial_die_info
   {
     /* Offset of this DIE.  */
-    sect_offset offset;
+    sect_offset sect_off;
 
     /* DWARF-2 tag for this DIE.  */
     ENUM_BITFIELD(dwarf_tag) tag : 16;
@@ -1103,6 +1207,9 @@ struct partial_die_info
     unsigned int has_pc_info : 1;
     unsigned int may_be_inlined : 1;
 
+    /* This DIE has been marked DW_AT_main_subprogram.  */
+    unsigned int main_subprogram : 1;
+
     /* Flag set if the SCOPE field of this structure has been
        computed.  */
     unsigned int scope_set : 1;
@@ -1144,7 +1251,7 @@ struct partial_die_info
       /* The location description associated with this DIE, if any.  */
       struct dwarf_block *locdesc;
       /* The offset of an import, for DW_TAG_imported_unit.  */
-      sect_offset offset;
+      sect_offset sect_off;
     } d;
 
     /* If HAS_PC_INFO, the PC range associated with this DIE.  */
@@ -1182,6 +1289,9 @@ struct attr_abbrev
   {
     ENUM_BITFIELD(dwarf_attribute) name : 16;
     ENUM_BITFIELD(dwarf_form) form : 16;
+
+    /* It is valid only if FORM is DW_FORM_implicit_const.  */
+    LONGEST implicit_const;
   };
 
 /* Size of abbrev_table.abbrev_hash_table.  */
@@ -1193,7 +1303,7 @@ struct abbrev_table
 {
   /* Where the abbrev table came from.
      This is used as a sanity check when the table is used.  */
-  sect_offset offset;
+  sect_offset sect_off;
 
   /* Storage for the abbrev table.  */
   struct obstack abbrev_obstack;
@@ -1248,7 +1358,7 @@ struct die_info
     unsigned int abbrev;
 
     /* Offset in .debug_info or .debug_types section.  */
-    sect_offset offset;
+    sect_offset sect_off;
 
     /* The dies in a compilation unit form an n-ary tree.  PARENT
        points to this die's parent; CHILD points to the first child of
@@ -1501,9 +1611,11 @@ static const char *read_indirect_string (bfd *, const gdb_byte *,
                                         const struct comp_unit_head *,
                                         unsigned int *);
 
-static const char *read_indirect_string_from_dwz (struct dwz_file *, LONGEST);
+static const char *read_indirect_line_string (bfd *, const gdb_byte *,
+                                             const struct comp_unit_head *,
+                                             unsigned int *);
 
-static ULONGEST read_unsigned_leb128 (bfd *, const gdb_byte *, unsigned int *);
+static const char *read_indirect_string_from_dwz (struct dwz_file *, LONGEST);
 
 static LONGEST read_signed_leb128 (bfd *, const gdb_byte *, unsigned int *);
 
@@ -1522,6 +1634,9 @@ static struct attribute *dwarf2_attr (struct die_info *, unsigned int,
 static struct attribute *dwarf2_attr_no_follow (struct die_info *,
                                                unsigned int);
 
+static const char *dwarf2_string_attr (struct die_info *die, unsigned int name,
+                                       struct dwarf2_cu *cu);
+
 static int dwarf2_flag_true_p (struct die_info *die, unsigned name,
                                struct dwarf2_cu *cu);
 
@@ -1530,10 +1645,8 @@ static int die_is_declaration (struct die_info *, struct dwarf2_cu *cu);
 static struct die_info *die_specification (struct die_info *die,
                                           struct dwarf2_cu **);
 
-static void free_line_header (struct line_header *lh);
-
-static struct line_header *dwarf_decode_line_header (unsigned int offset,
-                                                    struct dwarf2_cu *cu);
+static line_header_up dwarf_decode_line_header (sect_offset sect_off,
+                                               struct dwarf2_cu *cu);
 
 static void dwarf_decode_lines (struct line_header *, const char *,
                                struct dwarf2_cu *, struct partial_symtab *,
@@ -1601,9 +1714,28 @@ static void read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu);
 static int dwarf2_ranges_read (unsigned, CORE_ADDR *, CORE_ADDR *,
                               struct dwarf2_cu *, struct partial_symtab *);
 
-static int dwarf2_get_pc_bounds (struct die_info *,
-                                CORE_ADDR *, CORE_ADDR *, struct dwarf2_cu *,
-                                struct partial_symtab *);
+/* How dwarf2_get_pc_bounds constructed its *LOWPC and *HIGHPC return
+   values.  Keep the items ordered with increasing constraints compliance.  */
+enum pc_bounds_kind
+{
+  /* No attribute DW_AT_low_pc, DW_AT_high_pc or DW_AT_ranges was found.  */
+  PC_BOUNDS_NOT_PRESENT,
+
+  /* Some of the attributes DW_AT_low_pc, DW_AT_high_pc or DW_AT_ranges
+     were present but they do not form a valid range of PC addresses.  */
+  PC_BOUNDS_INVALID,
+
+  /* Discontiguous range was found - that is DW_AT_ranges was found.  */
+  PC_BOUNDS_RANGES,
+
+  /* Contiguous range was found - DW_AT_low_pc and DW_AT_high_pc were found.  */
+  PC_BOUNDS_HIGH_LOW,
+};
+
+static enum pc_bounds_kind dwarf2_get_pc_bounds (struct die_info *,
+                                                CORE_ADDR *, CORE_ADDR *,
+                                                struct dwarf2_cu *,
+                                                struct partial_symtab *);
 
 static void get_scope_pc_bounds (struct die_info *,
                                 CORE_ADDR *, CORE_ADDR *,
@@ -1634,6 +1766,8 @@ static void read_namespace (struct die_info *die, struct dwarf2_cu *);
 
 static void read_module (struct die_info *die, struct dwarf2_cu *cu);
 
+static struct using_direct **using_directives (enum language);
+
 static void read_import_statement (struct die_info *die, struct dwarf2_cu *);
 
 static int read_namespace_alias (struct die_info *die, struct dwarf2_cu *cu);
@@ -1691,7 +1825,7 @@ static const char *dwarf_attr_name (unsigned int);
 
 static const char *dwarf_form_name (unsigned int);
 
-static char *dwarf_bool_name (unsigned int);
+static const char *dwarf_bool_name (unsigned int);
 
 static const char *dwarf_type_encoding_name (unsigned int);
 
@@ -1736,6 +1870,10 @@ static void load_full_type_unit (struct dwarf2_per_cu_data *per_cu);
 
 static void read_signatured_type (struct signatured_type *);
 
+static int attr_to_dynamic_prop (const struct attribute *attr,
+                                struct die_info *die, struct dwarf2_cu *cu,
+                                struct dynamic_prop *prop);
+
 /* memory allocation interface */
 
 static struct dwarf_block *dwarf_alloc_block (struct dwarf2_cu *);
@@ -1772,7 +1910,7 @@ static hashval_t partial_die_hash (const void *item);
 static int partial_die_eq (const void *item_lhs, const void *item_rhs);
 
 static struct dwarf2_per_cu_data *dwarf2_find_containing_comp_unit
-  (sect_offset offset, unsigned int offset_in_dwz, struct objfile *objfile);
+  (sect_offset sect_off, unsigned int offset_in_dwz, struct objfile *objfile);
 
 static void init_one_comp_unit (struct dwarf2_cu *cu,
                                struct dwarf2_per_cu_data *per_cu);
@@ -1824,18 +1962,39 @@ static void queue_comp_unit (struct dwarf2_per_cu_data *per_cu,
 
 static void process_queue (void);
 
-static void find_file_and_directory (struct die_info *die,
-                                    struct dwarf2_cu *cu,
-                                    const char **name, const char **comp_dir);
+/* The return type of find_file_and_directory.  Note, the enclosed
+   string pointers are only valid while this object is valid.  */
+
+struct file_and_directory
+{
+  /* The filename.  This is never NULL.  */
+  const char *name;
+
+  /* The compilation directory.  NULL if not known.  If we needed to
+     compute a new string, this points to COMP_DIR_STORAGE, otherwise,
+     points directly to the DW_AT_comp_dir string attribute owned by
+     the obstack that owns the DIE.  */
+  const char *comp_dir;
+
+  /* If we needed to build a new string for comp_dir, this is what
+     owns the storage.  */
+  std::string comp_dir_storage;
+};
+
+static file_and_directory find_file_and_directory (struct die_info *die,
+                                                  struct dwarf2_cu *cu);
 
 static char *file_full_name (int file, struct line_header *lh,
                             const char *comp_dir);
 
+/* Expected enum dwarf_unit_type for read_comp_unit_head.  */
+enum class rcuh_kind { COMPILE, TYPE };
+
 static const gdb_byte *read_and_check_comp_unit_head
   (struct comp_unit_head *header,
    struct dwarf2_section_info *section,
    struct dwarf2_section_info *abbrev_section, const gdb_byte *info_ptr,
-   int is_debug_types_section);
+   rcuh_kind section_kind);
 
 static void init_cutu_and_read_dies
   (struct dwarf2_per_cu_data *this_cu, struct abbrev_table *abbrev_table,
@@ -1943,7 +2102,7 @@ dwarf2_invalid_attrib_class_complaint (const char *arg1, const char *arg2)
 static hashval_t
 line_header_hash (const struct line_header *ofs)
 {
-  return ofs->offset.sect_off ^ ofs->offset_in_dwz;
+  return to_underlying (ofs->sect_off) ^ ofs->offset_in_dwz;
 }
 
 /* Hash function for htab_create_alloc_ex for line_header_hash.  */
@@ -1951,7 +2110,7 @@ line_header_hash (const struct line_header *ofs)
 static hashval_t
 line_header_hash_voidp (const void *item)
 {
-  const struct line_header *ofs = item;
+  const struct line_header *ofs = (const struct line_header *) item;
 
   return line_header_hash (ofs);
 }
@@ -1961,10 +2120,10 @@ line_header_hash_voidp (const void *item)
 static int
 line_header_eq_voidp (const void *item_lhs, const void *item_rhs)
 {
-  const struct line_header *ofs_lhs = item_lhs;
-  const struct line_header *ofs_rhs = item_rhs;
+  const struct line_header *ofs_lhs = (const struct line_header *) item_lhs;
+  const struct line_header *ofs_rhs = (const struct line_header *) item_rhs;
 
-  return (ofs_lhs->offset.sect_off == ofs_rhs->offset.sect_off
+  return (ofs_lhs->sect_off == ofs_rhs->sect_off
          && ofs_lhs->offset_in_dwz == ofs_rhs->offset_in_dwz);
 }
 
@@ -2032,12 +2191,13 @@ int
 dwarf2_has_info (struct objfile *objfile,
                  const struct dwarf2_debug_sections *names)
 {
-  dwarf2_per_objfile = objfile_data (objfile, dwarf2_objfile_data_key);
+  dwarf2_per_objfile = ((struct dwarf2_per_objfile *)
+                       objfile_data (objfile, dwarf2_objfile_data_key));
   if (!dwarf2_per_objfile)
     {
       /* Initialize per-objfile state.  */
       struct dwarf2_per_objfile *data
-       = obstack_alloc (&objfile->objfile_obstack, sizeof (*data));
+       = XOBNEW (&objfile->objfile_obstack, struct dwarf2_per_objfile);
 
       memset (data, 0, sizeof (*data));
       set_objfile_data (objfile, dwarf2_objfile_data_key, data);
@@ -2048,9 +2208,9 @@ dwarf2_has_info (struct objfile *objfile,
       dwarf2_per_objfile->objfile = objfile;
     }
   return (!dwarf2_per_objfile->info.is_virtual
-         && dwarf2_per_objfile->info.s.asection != NULL
+         && dwarf2_per_objfile->info.s.section != NULL
          && !dwarf2_per_objfile->abbrev.is_virtual
-         && dwarf2_per_objfile->abbrev.s.asection != NULL);
+         && dwarf2_per_objfile->abbrev.s.section != NULL);
 }
 
 /* Return the containing section of virtual section SECTION.  */
@@ -2072,7 +2232,7 @@ get_section_bfd_owner (const struct dwarf2_section_info *section)
       section = get_containing_section (section);
       gdb_assert (!section->is_virtual);
     }
-  return section->s.asection->owner;
+  return section->s.section->owner;
 }
 
 /* Return the bfd section of SECTION.
@@ -2086,7 +2246,7 @@ get_section_bfd_section (const struct dwarf2_section_info *section)
       section = get_containing_section (section);
       gdb_assert (!section->is_virtual);
     }
-  return section->s.asection;
+  return section->s.section;
 }
 
 /* Return the name of SECTION.  */
@@ -2171,65 +2331,80 @@ dwarf2_locate_sections (bfd *abfd, asection *sectp, void *vnames)
     }
   else if (section_is_p (sectp->name, &names->info))
     {
-      dwarf2_per_objfile->info.s.asection = sectp;
+      dwarf2_per_objfile->info.s.section = sectp;
       dwarf2_per_objfile->info.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->abbrev))
     {
-      dwarf2_per_objfile->abbrev.s.asection = sectp;
+      dwarf2_per_objfile->abbrev.s.section = sectp;
       dwarf2_per_objfile->abbrev.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->line))
     {
-      dwarf2_per_objfile->line.s.asection = sectp;
+      dwarf2_per_objfile->line.s.section = sectp;
       dwarf2_per_objfile->line.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->loc))
     {
-      dwarf2_per_objfile->loc.s.asection = sectp;
+      dwarf2_per_objfile->loc.s.section = sectp;
       dwarf2_per_objfile->loc.size = bfd_get_section_size (sectp);
     }
+  else if (section_is_p (sectp->name, &names->loclists))
+    {
+      dwarf2_per_objfile->loclists.s.section = sectp;
+      dwarf2_per_objfile->loclists.size = bfd_get_section_size (sectp);
+    }
   else if (section_is_p (sectp->name, &names->macinfo))
     {
-      dwarf2_per_objfile->macinfo.s.asection = sectp;
+      dwarf2_per_objfile->macinfo.s.section = sectp;
       dwarf2_per_objfile->macinfo.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->macro))
     {
-      dwarf2_per_objfile->macro.s.asection = sectp;
+      dwarf2_per_objfile->macro.s.section = sectp;
       dwarf2_per_objfile->macro.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->str))
     {
-      dwarf2_per_objfile->str.s.asection = sectp;
+      dwarf2_per_objfile->str.s.section = sectp;
       dwarf2_per_objfile->str.size = bfd_get_section_size (sectp);
     }
+  else if (section_is_p (sectp->name, &names->line_str))
+    {
+      dwarf2_per_objfile->line_str.s.section = sectp;
+      dwarf2_per_objfile->line_str.size = bfd_get_section_size (sectp);
+    }
   else if (section_is_p (sectp->name, &names->addr))
     {
-      dwarf2_per_objfile->addr.s.asection = sectp;
+      dwarf2_per_objfile->addr.s.section = sectp;
       dwarf2_per_objfile->addr.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->frame))
     {
-      dwarf2_per_objfile->frame.s.asection = sectp;
+      dwarf2_per_objfile->frame.s.section = sectp;
       dwarf2_per_objfile->frame.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->eh_frame))
     {
-      dwarf2_per_objfile->eh_frame.s.asection = sectp;
+      dwarf2_per_objfile->eh_frame.s.section = sectp;
       dwarf2_per_objfile->eh_frame.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->ranges))
     {
-      dwarf2_per_objfile->ranges.s.asection = sectp;
+      dwarf2_per_objfile->ranges.s.section = sectp;
       dwarf2_per_objfile->ranges.size = bfd_get_section_size (sectp);
     }
+  else if (section_is_p (sectp->name, &names->rnglists))
+    {
+      dwarf2_per_objfile->rnglists.s.section = sectp;
+      dwarf2_per_objfile->rnglists.size = bfd_get_section_size (sectp);
+    }
   else if (section_is_p (sectp->name, &names->types))
     {
       struct dwarf2_section_info type_section;
 
       memset (&type_section, 0, sizeof (type_section));
-      type_section.s.asection = sectp;
+      type_section.s.section = sectp;
       type_section.size = bfd_get_section_size (sectp);
 
       VEC_safe_push (dwarf2_section_info_def, dwarf2_per_objfile->types,
@@ -2237,11 +2412,11 @@ dwarf2_locate_sections (bfd *abfd, asection *sectp, void *vnames)
     }
   else if (section_is_p (sectp->name, &names->gdb_index))
     {
-      dwarf2_per_objfile->gdb_index.s.asection = sectp;
+      dwarf2_per_objfile->gdb_index.s.section = sectp;
       dwarf2_per_objfile->gdb_index.size = bfd_get_section_size (sectp);
     }
 
-  if ((bfd_get_section_flags (abfd, sectp) & SEC_LOAD)
+  if ((bfd_get_section_flags (abfd, sectp) & (SEC_LOAD | SEC_ALLOC))
       && bfd_section_vma (abfd, sectp) == 0)
     dwarf2_per_objfile->has_section_at_zero = 1;
 }
@@ -2254,7 +2429,7 @@ dwarf2_section_empty_p (const struct dwarf2_section_info *section)
 {
   if (section->is_virtual)
     return section->size == 0;
-  return section->s.asection == NULL || section->size == 0;
+  return section->s.section == NULL || section->size == 0;
 }
 
 /* Read the contents of the section INFO.
@@ -2313,7 +2488,7 @@ dwarf2_read_section (struct objfile *objfile, struct dwarf2_section_info *info)
       return;
     }
 
-  buf = obstack_alloc (&objfile->objfile_obstack, info->size);
+  buf = (gdb_byte *) obstack_alloc (&objfile->objfile_obstack, info->size);
   info->buffer = buf;
 
   /* When debugging .o files, we may need to apply relocations; see
@@ -2365,7 +2540,8 @@ dwarf2_get_section_info (struct objfile *objfile,
                          bfd_size_type *sizep)
 {
   struct dwarf2_per_objfile *data
-    = objfile_data (objfile, dwarf2_objfile_data_key);
+    = (struct dwarf2_per_objfile *) objfile_data (objfile,
+                                                 dwarf2_objfile_data_key);
   struct dwarf2_section_info *info;
 
   /* We may see an objfile without any DWARF, in which case we just
@@ -2401,38 +2577,38 @@ dwarf2_get_section_info (struct objfile *objfile,
 static void
 locate_dwz_sections (bfd *abfd, asection *sectp, void *arg)
 {
-  struct dwz_file *dwz_file = arg;
+  struct dwz_file *dwz_file = (struct dwz_file *) arg;
 
   /* Note that we only support the standard ELF names, because .dwz
      is ELF-only (at the time of writing).  */
   if (section_is_p (sectp->name, &dwarf2_elf_names.abbrev))
     {
-      dwz_file->abbrev.s.asection = sectp;
+      dwz_file->abbrev.s.section = sectp;
       dwz_file->abbrev.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &dwarf2_elf_names.info))
     {
-      dwz_file->info.s.asection = sectp;
+      dwz_file->info.s.section = sectp;
       dwz_file->info.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &dwarf2_elf_names.str))
     {
-      dwz_file->str.s.asection = sectp;
+      dwz_file->str.s.section = sectp;
       dwz_file->str.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &dwarf2_elf_names.line))
     {
-      dwz_file->line.s.asection = sectp;
+      dwz_file->line.s.section = sectp;
       dwz_file->line.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &dwarf2_elf_names.macro))
     {
-      dwz_file->macro.s.asection = sectp;
+      dwz_file->macro.s.section = sectp;
       dwz_file->macro.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &dwarf2_elf_names.gdb_index))
     {
-      dwz_file->gdb_index.s.asection = sectp;
+      dwz_file->gdb_index.s.section = sectp;
       dwz_file->gdb_index.size = bfd_get_section_size (sectp);
     }
 }
@@ -2444,7 +2620,6 @@ locate_dwz_sections (bfd *abfd, asection *sectp, void *arg)
 static struct dwz_file *
 dwarf2_get_dwz_file (void)
 {
-  bfd *dwz_bfd;
   char *data;
   struct cleanup *cleanup;
   const char *filename;
@@ -2472,30 +2647,24 @@ dwarf2_get_dwz_file (void)
   buildid_len = (size_t) buildid_len_arg;
 
   filename = (const char *) data;
+
+  std::string abs_storage;
   if (!IS_ABSOLUTE_PATH (filename))
     {
       char *abs = gdb_realpath (objfile_name (dwarf2_per_objfile->objfile));
-      char *rel;
 
       make_cleanup (xfree, abs);
-      abs = ldirname (abs);
-      make_cleanup (xfree, abs);
-
-      rel = concat (abs, SLASH_STRING, filename, (char *) NULL);
-      make_cleanup (xfree, rel);
-      filename = rel;
+      abs_storage = ldirname (abs) + SLASH_STRING + filename;
+      filename = abs_storage.c_str ();
     }
 
   /* First try the file name given in the section.  If that doesn't
      work, try to use the build-id instead.  */
-  dwz_bfd = gdb_bfd_open (filename, gnutarget, -1);
+  gdb_bfd_ref_ptr dwz_bfd (gdb_bfd_open (filename, gnutarget, -1));
   if (dwz_bfd != NULL)
     {
-      if (!build_id_verify (dwz_bfd, buildid_len, buildid))
-       {
-         gdb_bfd_unref (dwz_bfd);
-         dwz_bfd = NULL;
-       }
+      if (!build_id_verify (dwz_bfd.get (), buildid_len, buildid))
+       dwz_bfd.release ();
     }
 
   if (dwz_bfd == NULL)
@@ -2507,13 +2676,13 @@ dwarf2_get_dwz_file (void)
 
   result = OBSTACK_ZALLOC (&dwarf2_per_objfile->objfile->objfile_obstack,
                           struct dwz_file);
-  result->dwz_bfd = dwz_bfd;
+  result->dwz_bfd = dwz_bfd.release ();
 
-  bfd_map_over_sections (dwz_bfd, locate_dwz_sections, result);
+  bfd_map_over_sections (result->dwz_bfd, locate_dwz_sections, result);
 
   do_cleanups (cleanup);
 
-  gdb_bfd_record_inclusion (dwarf2_per_objfile->objfile->obfd, dwz_bfd);
+  gdb_bfd_record_inclusion (dwarf2_per_objfile->objfile->obfd, result->dwz_bfd);
   dwarf2_per_objfile->dwz_file = result;
   return result;
 }
@@ -2574,7 +2743,7 @@ hash_stmt_list_entry (const struct stmt_list_hash *stmt_list_hash)
 
   if (stmt_list_hash->dwo_unit != NULL)
     v += (uintptr_t) stmt_list_hash->dwo_unit->dwo_file;
-  v += stmt_list_hash->line_offset.sect_off;
+  v += to_underlying (stmt_list_hash->line_sect_off);
   return v;
 }
 
@@ -2590,7 +2759,7 @@ eq_stmt_list_entry (const struct stmt_list_hash *lhs,
       && lhs->dwo_unit->dwo_file != rhs->dwo_unit->dwo_file)
     return 0;
 
-  return lhs->line_offset.sect_off == rhs->line_offset.sect_off;
+  return lhs->line_sect_off == rhs->line_sect_off;
 }
 
 /* Hash function for a quick_file_names.  */
@@ -2598,7 +2767,8 @@ eq_stmt_list_entry (const struct stmt_list_hash *lhs,
 static hashval_t
 hash_file_name_entry (const void *e)
 {
-  const struct quick_file_names *file_data = e;
+  const struct quick_file_names *file_data
+    = (const struct quick_file_names *) e;
 
   return hash_stmt_list_entry (&file_data->hash);
 }
@@ -2608,8 +2778,8 @@ hash_file_name_entry (const void *e)
 static int
 eq_file_name_entry (const void *a, const void *b)
 {
-  const struct quick_file_names *ea = a;
-  const struct quick_file_names *eb = b;
+  const struct quick_file_names *ea = (const struct quick_file_names *) a;
+  const struct quick_file_names *eb = (const struct quick_file_names *) b;
 
   return eq_stmt_list_entry (&ea->hash, &eb->hash);
 }
@@ -2619,7 +2789,7 @@ eq_file_name_entry (const void *a, const void *b)
 static void
 delete_file_name_entry (void *e)
 {
-  struct quick_file_names *file_data = e;
+  struct quick_file_names *file_data = (struct quick_file_names *) e;
   int i;
 
   for (i = 0; i < file_data->num_file_names; ++i)
@@ -2655,7 +2825,8 @@ load_cu (struct dwarf2_per_cu_data *per_cu)
   else
     load_full_comp_unit (per_cu, language_minimal);
 
-  gdb_assert (per_cu->cu != NULL);
+  if (per_cu->cu == NULL)
+    return;  /* Dummy CU.  */
 
   dwarf2_find_base_address (per_cu->cu->dies, per_cu->cu);
 }
@@ -2685,6 +2856,7 @@ dw2_do_instantiate_symtab (struct dwarf2_per_cu_data *per_cu)
         that may badly handle TUs, load all the TUs in that DWO as well.
         http://sourceware.org/bugzilla/show_bug.cgi?id=15021  */
       if (!per_cu->is_debug_types
+         && per_cu->cu != NULL
          && per_cu->cu->dwo_unit != NULL
          && dwarf2_per_objfile->index_table != NULL
          && dwarf2_per_objfile->index_table->version <= 7
@@ -2774,17 +2946,17 @@ create_cus_from_index_list (struct objfile *objfile,
 
   for (i = 0; i < n_elements; i += 2)
     {
-      struct dwarf2_per_cu_data *the_cu;
-      ULONGEST offset, length;
-
       gdb_static_assert (sizeof (ULONGEST) >= 8);
-      offset = extract_unsigned_integer (cu_list, 8, BFD_ENDIAN_LITTLE);
-      length = extract_unsigned_integer (cu_list + 8, 8, BFD_ENDIAN_LITTLE);
+
+      sect_offset sect_off
+       = (sect_offset) extract_unsigned_integer (cu_list, 8, BFD_ENDIAN_LITTLE);
+      ULONGEST length = extract_unsigned_integer (cu_list + 8, 8, BFD_ENDIAN_LITTLE);
       cu_list += 2 * 8;
 
-      the_cu = OBSTACK_ZALLOC (&objfile->objfile_obstack,
-                              struct dwarf2_per_cu_data);
-      the_cu->offset.sect_off = offset;
+      dwarf2_per_cu_data *the_cu
+       = OBSTACK_ZALLOC (&objfile->objfile_obstack,
+                         struct dwarf2_per_cu_data);
+      the_cu->sect_off = sect_off;
       the_cu->length = length;
       the_cu->objfile = objfile;
       the_cu->section = section;
@@ -2806,10 +2978,9 @@ create_cus_from_index (struct objfile *objfile,
   struct dwz_file *dwz;
 
   dwarf2_per_objfile->n_comp_units = (cu_list_elements + dwz_elements) / 2;
-  dwarf2_per_objfile->all_comp_units
-    = obstack_alloc (&objfile->objfile_obstack,
-                    dwarf2_per_objfile->n_comp_units
-                    * sizeof (struct dwarf2_per_cu_data *));
+  dwarf2_per_objfile->all_comp_units =
+    XOBNEWVEC (&objfile->objfile_obstack, struct dwarf2_per_cu_data *,
+              dwarf2_per_objfile->n_comp_units);
 
   create_cus_from_index_list (objfile, cu_list, cu_list_elements,
                              &dwarf2_per_objfile->info, 0, 0);
@@ -2836,32 +3007,34 @@ create_signatured_type_table_from_index (struct objfile *objfile,
   dwarf2_per_objfile->n_type_units
     = dwarf2_per_objfile->n_allocated_type_units
     = elements / 3;
-  dwarf2_per_objfile->all_type_units
-    = xmalloc (dwarf2_per_objfile->n_type_units
-              * sizeof (struct signatured_type *));
+  dwarf2_per_objfile->all_type_units =
+    XNEWVEC (struct signatured_type *, dwarf2_per_objfile->n_type_units);
 
   sig_types_hash = allocate_signatured_type_table (objfile);
 
   for (i = 0; i < elements; i += 3)
     {
       struct signatured_type *sig_type;
-      ULONGEST offset, type_offset_in_tu, signature;
+      ULONGEST signature;
       void **slot;
+      cu_offset type_offset_in_tu;
 
       gdb_static_assert (sizeof (ULONGEST) >= 8);
-      offset = extract_unsigned_integer (bytes, 8, BFD_ENDIAN_LITTLE);
-      type_offset_in_tu = extract_unsigned_integer (bytes + 8, 8,
-                                                   BFD_ENDIAN_LITTLE);
+      sect_offset sect_off
+       = (sect_offset) extract_unsigned_integer (bytes, 8, BFD_ENDIAN_LITTLE);
+      type_offset_in_tu
+       = (cu_offset) extract_unsigned_integer (bytes + 8, 8,
+                                               BFD_ENDIAN_LITTLE);
       signature = extract_unsigned_integer (bytes + 16, 8, BFD_ENDIAN_LITTLE);
       bytes += 3 * 8;
 
       sig_type = OBSTACK_ZALLOC (&objfile->objfile_obstack,
                                 struct signatured_type);
       sig_type->signature = signature;
-      sig_type->type_offset_in_tu.cu_off = type_offset_in_tu;
+      sig_type->type_offset_in_tu = type_offset_in_tu;
       sig_type->per_cu.is_debug_types = 1;
       sig_type->per_cu.section = section;
-      sig_type->per_cu.offset.sect_off = offset;
+      sig_type->per_cu.sect_off = sect_off;
       sig_type->per_cu.objfile = objfile;
       sig_type->per_cu.v.quick
        = OBSTACK_ZALLOC (&objfile->objfile_obstack,
@@ -2973,7 +3146,6 @@ find_slot_in_mapped_hash (struct mapped_index *index, const char *name,
   int (*cmp) (const char *, const char *);
 
   if (current_language->la_language == language_cplus
-      || current_language->la_language == language_java
       || current_language->la_language == language_fortran
       || current_language->la_language == language_d)
     {
@@ -3217,7 +3389,7 @@ dwarf2_read_index (struct objfile *objfile)
 
   create_addrmap_from_index (objfile, &local_map);
 
-  map = obstack_alloc (&objfile->objfile_obstack, sizeof (struct mapped_index));
+  map = XOBNEW (&objfile->objfile_obstack, struct mapped_index);
   *map = local_map;
 
   dwarf2_per_objfile->index_table = map;
@@ -3234,7 +3406,8 @@ dwarf2_read_index (struct objfile *objfile)
 static void
 dw2_setup (struct objfile *objfile)
 {
-  dwarf2_per_objfile = objfile_data (objfile, dwarf2_objfile_data_key);
+  dwarf2_per_objfile = ((struct dwarf2_per_objfile *)
+                       objfile_data (objfile, dwarf2_objfile_data_key));
   gdb_assert (dwarf2_per_objfile);
 }
 
@@ -3251,13 +3424,10 @@ dw2_get_file_names_reader (const struct die_reader_specs *reader,
   struct dwarf2_per_cu_data *this_cu = cu->per_cu;  
   struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct dwarf2_per_cu_data *lh_cu;
-  struct line_header *lh;
   struct attribute *attr;
   int i;
-  const char *name, *comp_dir;
   void **slot;
   struct quick_file_names *qfn;
-  unsigned int line_offset;
 
   gdb_assert (! this_cu->is_debug_types);
 
@@ -3270,26 +3440,27 @@ dw2_get_file_names_reader (const struct die_reader_specs *reader,
     }
 
   lh_cu = this_cu;
-  lh = NULL;
   slot = NULL;
-  line_offset = 0;
+
+  line_header_up lh;
+  sect_offset line_offset {};
 
   attr = dwarf2_attr (comp_unit_die, DW_AT_stmt_list, cu);
   if (attr)
     {
       struct quick_file_names find_entry;
 
-      line_offset = DW_UNSND (attr);
+      line_offset = (sect_offset) DW_UNSND (attr);
 
       /* We may have already read in this line header (TU line header sharing).
         If we have we're done.  */
       find_entry.hash.dwo_unit = cu->dwo_unit;
-      find_entry.hash.line_offset.sect_off = line_offset;
+      find_entry.hash.line_sect_off = line_offset;
       slot = htab_find_slot (dwarf2_per_objfile->quick_file_names_table,
                             &find_entry, INSERT);
       if (*slot != NULL)
        {
-         lh_cu->v.quick->file_names = *slot;
+         lh_cu->v.quick->file_names = (struct quick_file_names *) *slot;
          return;
        }
 
@@ -3301,23 +3472,21 @@ dw2_get_file_names_reader (const struct die_reader_specs *reader,
       return;
     }
 
-  qfn = obstack_alloc (&objfile->objfile_obstack, sizeof (*qfn));
+  qfn = XOBNEW (&objfile->objfile_obstack, struct quick_file_names);
   qfn->hash.dwo_unit = cu->dwo_unit;
-  qfn->hash.line_offset.sect_off = line_offset;
+  qfn->hash.line_sect_off = line_offset;
   gdb_assert (slot != NULL);
   *slot = qfn;
 
-  find_file_and_directory (comp_unit_die, cu, &name, &comp_dir);
+  file_and_directory fnd = find_file_and_directory (comp_unit_die, cu);
 
-  qfn->num_file_names = lh->num_file_names;
-  qfn->file_names = obstack_alloc (&objfile->objfile_obstack,
-                                  lh->num_file_names * sizeof (char *));
-  for (i = 0; i < lh->num_file_names; ++i)
-    qfn->file_names[i] = file_full_name (i + 1, lhcomp_dir);
+  qfn->num_file_names = lh->file_names.size ();
+  qfn->file_names =
+    XOBNEWVEC (&objfile->objfile_obstack, const char *, lh->file_names.size ());
+  for (i = 0; i < lh->file_names.size (); ++i)
+    qfn->file_names[i] = file_full_name (i + 1, lh.get (), fnd.comp_dir);
   qfn->real_names = NULL;
 
-  free_line_header (lh);
-
   lh_cu->v.quick->file_names = qfn;
 }
 
@@ -3413,8 +3582,7 @@ static int
 dw2_map_expand_apply (struct objfile *objfile,
                      struct dwarf2_per_cu_data *per_cu,
                      const char *name, const char *real_path,
-                     int (*callback) (struct symtab *, void *),
-                     void *data)
+                     gdb::function_view<bool (symtab *)> callback)
 {
   struct compunit_symtab *last_made = objfile->compunit_symtabs;
 
@@ -3426,17 +3594,16 @@ dw2_map_expand_apply (struct objfile *objfile,
      all of them.  */
   dw2_instantiate_symtab (per_cu);
 
-  return iterate_over_some_symtabs (name, real_path, callback, data,
-                                   objfile->compunit_symtabs, last_made);
+  return iterate_over_some_symtabs (name, real_path, objfile->compunit_symtabs,
+                                   last_made, callback);
 }
 
 /* Implementation of the map_symtabs_matching_filename method.  */
 
-static int
-dw2_map_symtabs_matching_filename (struct objfile *objfile, const char *name,
-                                  const char *real_path,
-                                  int (*callback) (struct symtab *, void *),
-                                  void *data)
+static bool
+dw2_map_symtabs_matching_filename
+  (struct objfile *objfile, const char *name, const char *real_path,
+   gdb::function_view<bool (symtab *)> callback)
 {
   int i;
   const char *name_basename = lbasename (name);
@@ -3468,8 +3635,8 @@ dw2_map_symtabs_matching_filename (struct objfile *objfile, const char *name,
          if (compare_filenames_for_search (this_name, name))
            {
              if (dw2_map_expand_apply (objfile, per_cu, name, real_path,
-                                       callback, data))
-               return 1;
+                                       callback))
+               return true;
              continue;
            }
 
@@ -3483,8 +3650,8 @@ dw2_map_symtabs_matching_filename (struct objfile *objfile, const char *name,
          if (compare_filenames_for_search (this_real_name, name))
            {
              if (dw2_map_expand_apply (objfile, per_cu, name, real_path,
-                                       callback, data))
-               return 1;
+                                       callback))
+               return true;
              continue;
            }
 
@@ -3496,15 +3663,15 @@ dw2_map_symtabs_matching_filename (struct objfile *objfile, const char *name,
                  && FILENAME_CMP (real_path, this_real_name) == 0)
                {
                  if (dw2_map_expand_apply (objfile, per_cu, name, real_path,
-                                           callback, data))
-                   return 1;
+                                           callback))
+                   return true;
                  continue;
                }
            }
        }
     }
 
-  return 0;
+  return false;
 }
 
 /* Struct used to manage iterating over all CUs looking for a symbol.  */
@@ -3842,11 +4009,10 @@ dw2_map_matching_symbols (struct objfile *objfile,
 static void
 dw2_expand_symtabs_matching
   (struct objfile *objfile,
-   expand_symtabs_file_matcher_ftype *file_matcher,
-   expand_symtabs_symbol_matcher_ftype *symbol_matcher,
-   expand_symtabs_exp_notify_ftype *expansion_notify,
-   enum search_domain kind,
-   void *data)
+   gdb::function_view<expand_symtabs_file_matcher_ftype> file_matcher,
+   gdb::function_view<expand_symtabs_symbol_matcher_ftype> symbol_matcher,
+   gdb::function_view<expand_symtabs_exp_notify_ftype> expansion_notify,
+   enum search_domain kind)
 {
   int i;
   offset_type iter;
@@ -3861,17 +4027,12 @@ dw2_expand_symtabs_matching
 
   if (file_matcher != NULL)
     {
-      struct cleanup *cleanup;
-      htab_t visited_found, visited_not_found;
-
-      visited_found = htab_create_alloc (10,
-                                        htab_hash_pointer, htab_eq_pointer,
-                                        NULL, xcalloc, xfree);
-      cleanup = make_cleanup_htab_delete (visited_found);
-      visited_not_found = htab_create_alloc (10,
-                                            htab_hash_pointer, htab_eq_pointer,
-                                            NULL, xcalloc, xfree);
-      make_cleanup_htab_delete (visited_not_found);
+      htab_up visited_found (htab_create_alloc (10, htab_hash_pointer,
+                                               htab_eq_pointer,
+                                               NULL, xcalloc, xfree));
+      htab_up visited_not_found (htab_create_alloc (10, htab_hash_pointer,
+                                                   htab_eq_pointer,
+                                                   NULL, xcalloc, xfree));
 
       /* The rule is CUs specify all the files, including those used by
         any TU, so there's no need to scan TUs here.  */
@@ -3895,9 +4056,9 @@ dw2_expand_symtabs_matching
          if (file_data == NULL)
            continue;
 
-         if (htab_find (visited_not_found, file_data) != NULL)
+         if (htab_find (visited_not_found.get (), file_data) != NULL)
            continue;
-         else if (htab_find (visited_found, file_data) != NULL)
+         else if (htab_find (visited_found.get (), file_data) != NULL)
            {
              per_cu->v.quick->mark = 1;
              continue;
@@ -3907,7 +4068,7 @@ dw2_expand_symtabs_matching
            {
              const char *this_real_name;
 
-             if (file_matcher (file_data->file_names[j], data, 0))
+             if (file_matcher (file_data->file_names[j], false))
                {
                  per_cu->v.quick->mark = 1;
                  break;
@@ -3917,11 +4078,11 @@ dw2_expand_symtabs_matching
                 files are involved, do a quick comparison of the basenames.  */
              if (!basenames_may_differ
                  && !file_matcher (lbasename (file_data->file_names[j]),
-                                   data, 1))
+                                   true))
                continue;
 
              this_real_name = dw2_get_real_path (objfile, file_data, j);
-             if (file_matcher (this_real_name, data, 0))
+             if (file_matcher (this_real_name, false))
                {
                  per_cu->v.quick->mark = 1;
                  break;
@@ -3929,13 +4090,11 @@ dw2_expand_symtabs_matching
            }
 
          slot = htab_find_slot (per_cu->v.quick->mark
-                                ? visited_found
-                                : visited_not_found,
+                                ? visited_found.get ()
+                                : visited_not_found.get (),
                                 file_data, INSERT);
          *slot = file_data;
        }
-
-      do_cleanups (cleanup);
     }
 
   for (iter = 0; iter < index->symbol_table_slots; ++iter)
@@ -3952,7 +4111,7 @@ dw2_expand_symtabs_matching
 
       name = index->constant_pool + MAYBE_SWAP (index->symbol_table[idx]);
 
-      if (! (*symbol_matcher) (name, data))
+      if (!symbol_matcher (name))
        continue;
 
       /* The name was matched, now expand corresponding CUs that were
@@ -4030,8 +4189,7 @@ dw2_expand_symtabs_matching
                  && symtab_was_null
                  && per_cu->v.quick->compunit_symtab != NULL)
                {
-                 expansion_notify (per_cu->v.quick->compunit_symtab,
-                                   data);
+                 expansion_notify (per_cu->v.quick->compunit_symtab);
                }
            }
        }
@@ -4081,7 +4239,8 @@ dw2_find_pc_sect_compunit_symtab (struct objfile *objfile,
   if (!objfile->psymtabs_addrmap)
     return NULL;
 
-  data = addrmap_find (objfile->psymtabs_addrmap, pc);
+  data = (struct dwarf2_per_cu_data *) addrmap_find (objfile->psymtabs_addrmap,
+                                                    pc);
   if (!data)
     return NULL;
 
@@ -4101,11 +4260,9 @@ dw2_map_symbol_filenames (struct objfile *objfile, symbol_filename_ftype *fun,
                          void *data, int need_fullname)
 {
   int i;
-  struct cleanup *cleanup;
-  htab_t visited = htab_create_alloc (10, htab_hash_pointer, htab_eq_pointer,
-                                     NULL, xcalloc, xfree);
+  htab_up visited (htab_create_alloc (10, htab_hash_pointer, htab_eq_pointer,
+                                     NULL, xcalloc, xfree));
 
-  cleanup = make_cleanup_htab_delete (visited);
   dw2_setup (objfile);
 
   /* The rule is CUs specify all the files, including those used by
@@ -4118,7 +4275,8 @@ dw2_map_symbol_filenames (struct objfile *objfile, symbol_filename_ftype *fun,
 
       if (per_cu->v.quick->compunit_symtab)
        {
-         void **slot = htab_find_slot (visited, per_cu->v.quick->file_names,
+         void **slot = htab_find_slot (visited.get (),
+                                       per_cu->v.quick->file_names,
                                        INSERT);
 
          *slot = per_cu->v.quick->file_names;
@@ -4140,7 +4298,7 @@ dw2_map_symbol_filenames (struct objfile *objfile, symbol_filename_ftype *fun,
       if (file_data == NULL)
        continue;
 
-      slot = htab_find_slot (visited, file_data, INSERT);
+      slot = htab_find_slot (visited.get (), file_data, INSERT);
       if (*slot)
        {
          /* Already visited.  */
@@ -4159,8 +4317,6 @@ dw2_map_symbol_filenames (struct objfile *objfile, symbol_filename_ftype *fun,
          (*fun) (file_data->file_names[j], this_real_name, data);
        }
     }
-
-  do_cleanups (cleanup);
 }
 
 static int
@@ -4247,10 +4403,9 @@ dwarf2_build_psymtabs (struct objfile *objfile)
       /* This isn't really ideal: all the data we allocate on the
         objfile's obstack is still uselessly kept around.  However,
         freeing it seems unsafe.  */
-      struct cleanup *cleanups = make_cleanup_discard_psymtabs (objfile);
-
+      psymtab_discarder psymtabs (objfile);
       dwarf2_build_psymtabs_hard (objfile);
-      discard_cleanups (cleanups);
+      psymtabs.keep ();
     }
   CATCH (except, RETURN_MASK_ERROR)
     {
@@ -4267,15 +4422,15 @@ get_cu_length (const struct comp_unit_head *header)
   return header->initial_length_size + header->length;
 }
 
-/* Return TRUE if OFFSET is within CU_HEADER.  */
+/* Return TRUE if SECT_OFF is within CU_HEADER.  */
 
-static inline int
-offset_in_cu_p (const struct comp_unit_head *cu_header, sect_offset offset)
+static inline bool
+offset_in_cu_p (const comp_unit_head *cu_header, sect_offset sect_off)
 {
-  sect_offset bottom = { cu_header->offset.sect_off };
-  sect_offset top = { cu_header->offset.sect_off + get_cu_length (cu_header) };
+  sect_offset bottom = cu_header->sect_off;
+  sect_offset top = cu_header->sect_off + get_cu_length (cu_header);
 
-  return (offset.sect_off >= bottom.sect_off && offset.sect_off < top.sect_off);
+  return sect_off >= bottom && sect_off < top;
 }
 
 /* Find the base address of the compilation unit for range lists and
@@ -4310,15 +4465,20 @@ dwarf2_find_base_address (struct die_info *die, struct dwarf2_cu *cu)
 }
 
 /* Read in the comp unit header information from the debug_info at info_ptr.
+   Use rcuh_kind::COMPILE as the default type if not known by the caller.
    NOTE: This leaves members offset, first_die_offset to be filled in
    by the caller.  */
 
 static const gdb_byte *
 read_comp_unit_head (struct comp_unit_head *cu_header,
-                    const gdb_byte *info_ptr, bfd *abfd)
+                    const gdb_byte *info_ptr,
+                    struct dwarf2_section_info *section,
+                    rcuh_kind section_kind)
 {
   int signed_addr;
   unsigned int bytes_read;
+  const char *filename = get_section_file_name (section);
+  bfd *abfd = get_section_bfd_owner (section);
 
   cu_header->length = read_initial_length (abfd, info_ptr, &bytes_read);
   cu_header->initial_length_size = bytes_read;
@@ -4326,17 +4486,75 @@ read_comp_unit_head (struct comp_unit_head *cu_header,
   info_ptr += bytes_read;
   cu_header->version = read_2_bytes (abfd, info_ptr);
   info_ptr += 2;
-  cu_header->abbrev_offset.sect_off = read_offset (abfd, info_ptr, cu_header,
-                                            &bytes_read);
+  if (cu_header->version < 5)
+    switch (section_kind)
+      {
+      case rcuh_kind::COMPILE:
+       cu_header->unit_type = DW_UT_compile;
+       break;
+      case rcuh_kind::TYPE:
+       cu_header->unit_type = DW_UT_type;
+       break;
+      default:
+       internal_error (__FILE__, __LINE__,
+                       _("read_comp_unit_head: invalid section_kind"));
+      }
+  else
+    {
+      cu_header->unit_type = static_cast<enum dwarf_unit_type>
+                                                (read_1_byte (abfd, info_ptr));
+      info_ptr += 1;
+      switch (cu_header->unit_type)
+       {
+       case DW_UT_compile:
+         if (section_kind != rcuh_kind::COMPILE)
+           error (_("Dwarf Error: wrong unit_type in compilation unit header "
+                  "(is DW_UT_compile, should be DW_UT_type) [in module %s]"),
+                  filename);
+         break;
+       case DW_UT_type:
+         section_kind = rcuh_kind::TYPE;
+         break;
+       default:
+         error (_("Dwarf Error: wrong unit_type in compilation unit header "
+                "(is %d, should be %d or %d) [in module %s]"),
+                cu_header->unit_type, DW_UT_compile, DW_UT_type, filename);
+       }
+
+      cu_header->addr_size = read_1_byte (abfd, info_ptr);
+      info_ptr += 1;
+    }
+  cu_header->abbrev_sect_off = (sect_offset) read_offset (abfd, info_ptr,
+                                                         cu_header,
+                                                         &bytes_read);
   info_ptr += bytes_read;
-  cu_header->addr_size = read_1_byte (abfd, info_ptr);
-  info_ptr += 1;
+  if (cu_header->version < 5)
+    {
+      cu_header->addr_size = read_1_byte (abfd, info_ptr);
+      info_ptr += 1;
+    }
   signed_addr = bfd_get_sign_extend_vma (abfd);
   if (signed_addr < 0)
     internal_error (__FILE__, __LINE__,
                    _("read_comp_unit_head: dwarf from non elf file"));
   cu_header->signed_addr_p = signed_addr;
 
+  if (section_kind == rcuh_kind::TYPE)
+    {
+      LONGEST type_offset;
+
+      cu_header->signature = read_8_bytes (abfd, info_ptr);
+      info_ptr += 8;
+
+      type_offset = read_offset (abfd, info_ptr, cu_header, &bytes_read);
+      info_ptr += bytes_read;
+      cu_header->type_cu_offset_in_tu = (cu_offset) type_offset;
+      if (to_underlying (cu_header->type_cu_offset_in_tu) != type_offset)
+       error (_("Dwarf Error: Too big type_offset in compilation unit "
+              "header (is %s) [in module %s]"), plongest (type_offset),
+              filename);
+    }
+
   return info_ptr;
 }
 
@@ -4365,28 +4583,28 @@ error_check_comp_unit_head (struct comp_unit_head *header,
                            struct dwarf2_section_info *section,
                            struct dwarf2_section_info *abbrev_section)
 {
-  bfd *abfd = get_section_bfd_owner (section);
   const char *filename = get_section_file_name (section);
 
-  if (header->version != 2 && header->version != 3 && header->version != 4)
+  if (header->version < 2 || header->version > 5)
     error (_("Dwarf Error: wrong version in compilation unit header "
-          "(is %d, should be 2, 3, or 4) [in module %s]"), header->version,
+          "(is %d, should be 2, 3, 4 or 5) [in module %s]"), header->version,
           filename);
 
-  if (header->abbrev_offset.sect_off
+  if (to_underlying (header->abbrev_sect_off)
       >= dwarf2_section_size (dwarf2_per_objfile->objfile, abbrev_section))
-    error (_("Dwarf Error: bad offset (0x%lx) in compilation unit header "
-          "(offset 0x%lx + 6) [in module %s]"),
-          (long) header->abbrev_offset.sect_off, (long) header->offset.sect_off,
+    error (_("Dwarf Error: bad offset (0x%x) in compilation unit header "
+          "(offset 0x%x + 6) [in module %s]"),
+          to_underlying (header->abbrev_sect_off),
+          to_underlying (header->sect_off),
           filename);
 
-  /* Cast to unsigned long to use 64-bit arithmetic when possible to
+  /* Cast to ULONGEST to use 64-bit arithmetic when possible to
      avoid potential 32-bit overflow.  */
-  if (((unsigned long) header->offset.sect_off + get_cu_length (header))
+  if (((ULONGEST) header->sect_off + get_cu_length (header))
       > section->size)
-    error (_("Dwarf Error: bad length (0x%lx) in compilation unit header "
-          "(offset 0x%lx + 0) [in module %s]"),
-          (long) header->length, (long) header->offset.sect_off,
+    error (_("Dwarf Error: bad length (0x%x) in compilation unit header "
+          "(offset 0x%x + 0) [in module %s]"),
+          header->length, to_underlying (header->sect_off),
           filename);
 }
 
@@ -4399,56 +4617,16 @@ read_and_check_comp_unit_head (struct comp_unit_head *header,
                               struct dwarf2_section_info *section,
                               struct dwarf2_section_info *abbrev_section,
                               const gdb_byte *info_ptr,
-                              int is_debug_types_section)
-{
-  const gdb_byte *beg_of_comp_unit = info_ptr;
-  bfd *abfd = get_section_bfd_owner (section);
-
-  header->offset.sect_off = beg_of_comp_unit - section->buffer;
-
-  info_ptr = read_comp_unit_head (header, info_ptr, abfd);
-
-  /* If we're reading a type unit, skip over the signature and
-     type_offset fields.  */
-  if (is_debug_types_section)
-    info_ptr += 8 /*signature*/ + header->offset_size;
-
-  header->first_die_offset.cu_off = info_ptr - beg_of_comp_unit;
-
-  error_check_comp_unit_head (header, section, abbrev_section);
-
-  return info_ptr;
-}
-
-/* Read in the types comp unit header information from .debug_types entry at
-   types_ptr.  The result is a pointer to one past the end of the header.  */
-
-static const gdb_byte *
-read_and_check_type_unit_head (struct comp_unit_head *header,
-                              struct dwarf2_section_info *section,
-                              struct dwarf2_section_info *abbrev_section,
-                              const gdb_byte *info_ptr,
-                              ULONGEST *signature,
-                              cu_offset *type_offset_in_tu)
+                              rcuh_kind section_kind)
 {
   const gdb_byte *beg_of_comp_unit = info_ptr;
   bfd *abfd = get_section_bfd_owner (section);
 
-  header->offset.sect_off = beg_of_comp_unit - section->buffer;
+  header->sect_off = (sect_offset) (beg_of_comp_unit - section->buffer);
 
-  info_ptr = read_comp_unit_head (header, info_ptr, abfd);
+  info_ptr = read_comp_unit_head (header, info_ptr, section, section_kind);
 
-  /* If we're reading a type unit, skip over the signature and
-     type_offset fields.  */
-  if (signature != NULL)
-    *signature = read_8_bytes (abfd, info_ptr);
-  info_ptr += 8;
-  if (type_offset_in_tu != NULL)
-    type_offset_in_tu->cu_off = read_offset_1 (abfd, info_ptr,
-                                              header->offset_size);
-  info_ptr += header->offset_size;
-
-  header->first_die_offset.cu_off = info_ptr - beg_of_comp_unit;
+  header->first_die_cu_offset = (cu_offset) (info_ptr - beg_of_comp_unit);
 
   error_check_comp_unit_head (header, section, abbrev_section);
 
@@ -4459,20 +4637,28 @@ read_and_check_type_unit_head (struct comp_unit_head *header,
 
 static sect_offset
 read_abbrev_offset (struct dwarf2_section_info *section,
-                   sect_offset offset)
+                   sect_offset sect_off)
 {
   bfd *abfd = get_section_bfd_owner (section);
   const gdb_byte *info_ptr;
-  unsigned int length, initial_length_size, offset_size;
-  sect_offset abbrev_offset;
+  unsigned int initial_length_size, offset_size;
+  uint16_t version;
 
   dwarf2_read_section (dwarf2_per_objfile->objfile, section);
-  info_ptr = section->buffer + offset.sect_off;
-  length = read_initial_length (abfd, info_ptr, &initial_length_size);
+  info_ptr = section->buffer + to_underlying (sect_off);
+  read_initial_length (abfd, info_ptr, &initial_length_size);
   offset_size = initial_length_size == 4 ? 4 : 8;
-  info_ptr += initial_length_size + 2 /*version*/;
-  abbrev_offset.sect_off = read_offset_1 (abfd, info_ptr, offset_size);
-  return abbrev_offset;
+  info_ptr += initial_length_size;
+
+  version = read_2_bytes (abfd, info_ptr);
+  info_ptr += 2;
+  if (version >= 5)
+    {
+      /* Skip unit type and address size.  */
+      info_ptr += 2;
+    }
+
+  return (sect_offset) read_offset_1 (abfd, info_ptr, offset_size);
 }
 
 /* Allocate a new partial symtab for file named NAME and mark this new
@@ -4493,9 +4679,8 @@ dwarf2_create_include_psymtab (const char *name, struct partial_symtab *pst,
   subpst->textlow = 0;
   subpst->texthigh = 0;
 
-  subpst->dependencies = (struct partial_symtab **)
-    obstack_alloc (&objfile->objfile_obstack,
-                   sizeof (struct partial_symtab *));
+  subpst->dependencies
+    = XOBNEW (&objfile->objfile_obstack, struct partial_symtab *);
   subpst->dependencies[0] = pst;
   subpst->number_of_dependencies = 1;
 
@@ -4522,25 +4707,24 @@ dwarf2_build_include_psymtabs (struct dwarf2_cu *cu,
                               struct die_info *die,
                               struct partial_symtab *pst)
 {
-  struct line_header *lh = NULL;
+  line_header_up lh;
   struct attribute *attr;
 
   attr = dwarf2_attr (die, DW_AT_stmt_list, cu);
   if (attr)
-    lh = dwarf_decode_line_header (DW_UNSND (attr), cu);
+    lh = dwarf_decode_line_header ((sect_offset) DW_UNSND (attr), cu);
   if (lh == NULL)
     return;  /* No linetable, so no includes.  */
 
   /* NOTE: pst->dirname is DW_AT_comp_dir (if present).  */
-  dwarf_decode_lines (lh, pst->dirname, cu, pst, pst->textlow, 1);
-
-  free_line_header (lh);
+  dwarf_decode_lines (lh.get (), pst->dirname, cu, pst, pst->textlow, 1);
 }
 
 static hashval_t
 hash_signatured_type (const void *item)
 {
-  const struct signatured_type *sig_type = item;
+  const struct signatured_type *sig_type
+    = (const struct signatured_type *) item;
 
   /* This drops the top 32 bits of the signature, but is ok for a hash.  */
   return sig_type->signature;
@@ -4549,8 +4733,8 @@ hash_signatured_type (const void *item)
 static int
 eq_signatured_type (const void *item_lhs, const void *item_rhs)
 {
-  const struct signatured_type *lhs = item_lhs;
-  const struct signatured_type *rhs = item_rhs;
+  const struct signatured_type *lhs = (const struct signatured_type *) item_lhs;
+  const struct signatured_type *rhs = (const struct signatured_type *) item_rhs;
 
   return lhs->signature == rhs->signature;
 }
@@ -4574,8 +4758,8 @@ allocate_signatured_type_table (struct objfile *objfile)
 static int
 add_signatured_type_cu_to_table (void **slot, void *datum)
 {
-  struct signatured_type *sigt = *slot;
-  struct signatured_type ***datap = datum;
+  struct signatured_type *sigt = (struct signatured_type *) *slot;
+  struct signatured_type ***datap = (struct signatured_type ***) datum;
 
   **datap = sigt;
   ++*datap;
@@ -4583,165 +4767,177 @@ add_signatured_type_cu_to_table (void **slot, void *datum)
   return 1;
 }
 
-/* Create the hash table of all entries in the .debug_types
-   (or .debug_types.dwo) section(s).
-   If reading a DWO file, then DWO_FILE is a pointer to the DWO file object,
-   otherwise it is NULL.
-
-   The result is a pointer to the hash table or NULL if there are no types.
-
-   Note: This function processes DWO files only, not DWP files.  */
+/* A helper for create_debug_types_hash_table.  Read types from SECTION
+   and fill them into TYPES_HTAB.  It will process only type units,
+   therefore DW_UT_type.  */
 
-static htab_t
-create_debug_types_hash_table (struct dwo_file *dwo_file,
-                              VEC (dwarf2_section_info_def) *types)
+static void
+create_debug_type_hash_table (struct dwo_file *dwo_file,
+                             dwarf2_section_info *section, htab_t &types_htab,
+                             rcuh_kind section_kind)
 {
   struct objfile *objfile = dwarf2_per_objfile->objfile;
-  htab_t types_htab = NULL;
-  int ix;
-  struct dwarf2_section_info *section;
   struct dwarf2_section_info *abbrev_section;
-
-  if (VEC_empty (dwarf2_section_info_def, types))
-    return NULL;
+  bfd *abfd;
+  const gdb_byte *info_ptr, *end_ptr;
 
   abbrev_section = (dwo_file != NULL
                    ? &dwo_file->sections.abbrev
                    : &dwarf2_per_objfile->abbrev);
 
   if (dwarf_read_debug)
-    fprintf_unfiltered (gdb_stdlog, "Reading .debug_types%s for %s:\n",
-                       dwo_file ? ".dwo" : "",
+    fprintf_unfiltered (gdb_stdlog, "Reading %s for %s:\n",
+                       get_section_name (section),
                        get_section_file_name (abbrev_section));
 
-  for (ix = 0;
-       VEC_iterate (dwarf2_section_info_def, types, ix, section);
-       ++ix)
-    {
-      bfd *abfd;
-      const gdb_byte *info_ptr, *end_ptr;
+  dwarf2_read_section (objfile, section);
+  info_ptr = section->buffer;
 
-      dwarf2_read_section (objfile, section);
-      info_ptr = section->buffer;
+  if (info_ptr == NULL)
+    return;
 
-      if (info_ptr == NULL)
-       continue;
+  /* We can't set abfd until now because the section may be empty or
+     not present, in which case the bfd is unknown.  */
+  abfd = get_section_bfd_owner (section);
 
-      /* We can't set abfd until now because the section may be empty or
-        not present, in which case the bfd is unknown.  */
-      abfd = get_section_bfd_owner (section);
+  /* We don't use init_cutu_and_read_dies_simple, or some such, here
+     because we don't need to read any dies: the signature is in the
+     header.  */
 
-      /* We don't use init_cutu_and_read_dies_simple, or some such, here
-        because we don't need to read any dies: the signature is in the
-        header.  */
+  end_ptr = info_ptr + section->size;
+  while (info_ptr < end_ptr)
+    {
+      struct signatured_type *sig_type;
+      struct dwo_unit *dwo_tu;
+      void **slot;
+      const gdb_byte *ptr = info_ptr;
+      struct comp_unit_head header;
+      unsigned int length;
 
-      end_ptr = info_ptr + section->size;
-      while (info_ptr < end_ptr)
-       {
-         sect_offset offset;
-         cu_offset type_offset_in_tu;
-         ULONGEST signature;
-         struct signatured_type *sig_type;
-         struct dwo_unit *dwo_tu;
-         void **slot;
-         const gdb_byte *ptr = info_ptr;
-         struct comp_unit_head header;
-         unsigned int length;
+      sect_offset sect_off = (sect_offset) (ptr - section->buffer);
 
-         offset.sect_off = ptr - section->buffer;
+      /* Initialize it due to a false compiler warning.  */
+      header.signature = -1;
+      header.type_cu_offset_in_tu = (cu_offset) -1;
 
-         /* We need to read the type's signature in order to build the hash
-            table, but we don't need anything else just yet.  */
+      /* We need to read the type's signature in order to build the hash
+        table, but we don't need anything else just yet.  */
 
-         ptr = read_and_check_type_unit_head (&header, section,
-                                              abbrev_section, ptr,
-                                              &signature, &type_offset_in_tu);
+      ptr = read_and_check_comp_unit_head (&header, section,
+                                          abbrev_section, ptr, section_kind);
 
-         length = get_cu_length (&header);
+      length = get_cu_length (&header);
 
-         /* Skip dummy type units.  */
-         if (ptr >= info_ptr + length
-             || peek_abbrev_code (abfd, ptr) == 0)
-           {
-             info_ptr += length;
-             continue;
-           }
+      /* Skip dummy type units.  */
+      if (ptr >= info_ptr + length
+         || peek_abbrev_code (abfd, ptr) == 0
+         || header.unit_type != DW_UT_type)
+       {
+         info_ptr += length;
+         continue;
+       }
 
-         if (types_htab == NULL)
-           {
-             if (dwo_file)
-               types_htab = allocate_dwo_unit_table (objfile);
-             else
-               types_htab = allocate_signatured_type_table (objfile);
-           }
+      if (types_htab == NULL)
+       {
+         if (dwo_file)
+           types_htab = allocate_dwo_unit_table (objfile);
+         else
+           types_htab = allocate_signatured_type_table (objfile);
+       }
+
+      if (dwo_file)
+       {
+         sig_type = NULL;
+         dwo_tu = OBSTACK_ZALLOC (&objfile->objfile_obstack,
+                                  struct dwo_unit);
+         dwo_tu->dwo_file = dwo_file;
+         dwo_tu->signature = header.signature;
+         dwo_tu->type_offset_in_tu = header.type_cu_offset_in_tu;
+         dwo_tu->section = section;
+         dwo_tu->sect_off = sect_off;
+         dwo_tu->length = length;
+       }
+      else
+       {
+         /* N.B.: type_offset is not usable if this type uses a DWO file.
+            The real type_offset is in the DWO file.  */
+         dwo_tu = NULL;
+         sig_type = OBSTACK_ZALLOC (&objfile->objfile_obstack,
+                                    struct signatured_type);
+         sig_type->signature = header.signature;
+         sig_type->type_offset_in_tu = header.type_cu_offset_in_tu;
+         sig_type->per_cu.objfile = objfile;
+         sig_type->per_cu.is_debug_types = 1;
+         sig_type->per_cu.section = section;
+         sig_type->per_cu.sect_off = sect_off;
+         sig_type->per_cu.length = length;
+       }
+
+      slot = htab_find_slot (types_htab,
+                            dwo_file ? (void*) dwo_tu : (void *) sig_type,
+                            INSERT);
+      gdb_assert (slot != NULL);
+      if (*slot != NULL)
+       {
+         sect_offset dup_sect_off;
 
          if (dwo_file)
            {
-             sig_type = NULL;
-             dwo_tu = OBSTACK_ZALLOC (&objfile->objfile_obstack,
-                                      struct dwo_unit);
-             dwo_tu->dwo_file = dwo_file;
-             dwo_tu->signature = signature;
-             dwo_tu->type_offset_in_tu = type_offset_in_tu;
-             dwo_tu->section = section;
-             dwo_tu->offset = offset;
-             dwo_tu->length = length;
+             const struct dwo_unit *dup_tu
+               = (const struct dwo_unit *) *slot;
+
+             dup_sect_off = dup_tu->sect_off;
            }
          else
            {
-             /* N.B.: type_offset is not usable if this type uses a DWO file.
-                The real type_offset is in the DWO file.  */
-             dwo_tu = NULL;
-             sig_type = OBSTACK_ZALLOC (&objfile->objfile_obstack,
-                                        struct signatured_type);
-             sig_type->signature = signature;
-             sig_type->type_offset_in_tu = type_offset_in_tu;
-             sig_type->per_cu.objfile = objfile;
-             sig_type->per_cu.is_debug_types = 1;
-             sig_type->per_cu.section = section;
-             sig_type->per_cu.offset = offset;
-             sig_type->per_cu.length = length;
+             const struct signatured_type *dup_tu
+               = (const struct signatured_type *) *slot;
+
+             dup_sect_off = dup_tu->per_cu.sect_off;
            }
 
-         slot = htab_find_slot (types_htab,
-                                dwo_file ? (void*) dwo_tu : (void *) sig_type,
-                                INSERT);
-         gdb_assert (slot != NULL);
-         if (*slot != NULL)
-           {
-             sect_offset dup_offset;
+         complaint (&symfile_complaints,
+                    _("debug type entry at offset 0x%x is duplicate to"
+                      " the entry at offset 0x%x, signature %s"),
+                    to_underlying (sect_off), to_underlying (dup_sect_off),
+                    hex_string (header.signature));
+       }
+      *slot = dwo_file ? (void *) dwo_tu : (void *) sig_type;
 
-             if (dwo_file)
-               {
-                 const struct dwo_unit *dup_tu = *slot;
+      if (dwarf_read_debug > 1)
+       fprintf_unfiltered (gdb_stdlog, "  offset 0x%x, signature %s\n",
+                           to_underlying (sect_off),
+                           hex_string (header.signature));
 
-                 dup_offset = dup_tu->offset;
-               }
-             else
-               {
-                 const struct signatured_type *dup_tu = *slot;
+      info_ptr += length;
+    }
+}
 
-                 dup_offset = dup_tu->per_cu.offset;
-               }
+/* Create the hash table of all entries in the .debug_types
+   (or .debug_types.dwo) section(s).
+   If reading a DWO file, then DWO_FILE is a pointer to the DWO file object,
+   otherwise it is NULL.
 
-             complaint (&symfile_complaints,
-                        _("debug type entry at offset 0x%x is duplicate to"
-                          " the entry at offset 0x%x, signature %s"),
-                        offset.sect_off, dup_offset.sect_off,
-                        hex_string (signature));
-           }
-         *slot = dwo_file ? (void *) dwo_tu : (void *) sig_type;
+   The result is a pointer to the hash table or NULL if there are no types.
 
-         if (dwarf_read_debug > 1)
-           fprintf_unfiltered (gdb_stdlog, "  offset 0x%x, signature %s\n",
-                               offset.sect_off,
-                               hex_string (signature));
+   Note: This function processes DWO files only, not DWP files.  */
 
-         info_ptr += length;
-       }
-    }
+static void
+create_debug_types_hash_table (struct dwo_file *dwo_file,
+                              VEC (dwarf2_section_info_def) *types,
+                              htab_t &types_htab)
+{
+  int ix;
+  struct dwarf2_section_info *section;
+
+  if (VEC_empty (dwarf2_section_info_def, types))
+    return;
 
-  return types_htab;
+  for (ix = 0;
+       VEC_iterate (dwarf2_section_info_def, types, ix, section);
+       ++ix)
+    create_debug_type_hash_table (dwo_file, section, types_htab,
+                                 rcuh_kind::TYPE);
 }
 
 /* Create the hash table of all entries in the .debug_types section,
@@ -4752,10 +4948,12 @@ create_debug_types_hash_table (struct dwo_file *dwo_file,
 static int
 create_all_type_units (struct objfile *objfile)
 {
-  htab_t types_htab;
+  htab_t types_htab = NULL;
   struct signatured_type **iter;
 
-  types_htab = create_debug_types_hash_table (NULL, dwarf2_per_objfile->types);
+  create_debug_type_hash_table (NULL, &dwarf2_per_objfile->info, types_htab,
+                               rcuh_kind::COMPILE);
+  create_debug_types_hash_table (NULL, dwarf2_per_objfile->types, types_htab);
   if (types_htab == NULL)
     {
       dwarf2_per_objfile->signatured_types = NULL;
@@ -4767,9 +4965,8 @@ create_all_type_units (struct objfile *objfile)
   dwarf2_per_objfile->n_type_units
     = dwarf2_per_objfile->n_allocated_type_units
     = htab_elements (types_htab);
-  dwarf2_per_objfile->all_type_units
-    = xmalloc (dwarf2_per_objfile->n_type_units
-              * sizeof (struct signatured_type *));
+  dwarf2_per_objfile->all_type_units =
+    XNEWVEC (struct signatured_type *, dwarf2_per_objfile->n_type_units);
   iter = &dwarf2_per_objfile->all_type_units[0];
   htab_traverse_noresize (types_htab, add_signatured_type_cu_to_table, &iter);
   gdb_assert (iter - &dwarf2_per_objfile->all_type_units[0]
@@ -4797,9 +4994,9 @@ add_type_unit (ULONGEST sig, void **slot)
        dwarf2_per_objfile->n_allocated_type_units = 1;
       dwarf2_per_objfile->n_allocated_type_units *= 2;
       dwarf2_per_objfile->all_type_units
-       = xrealloc (dwarf2_per_objfile->all_type_units,
-                   dwarf2_per_objfile->n_allocated_type_units
-                   * sizeof (struct signatured_type *));
+       = XRESIZEVEC (struct signatured_type *,
+                     dwarf2_per_objfile->all_type_units,
+                     dwarf2_per_objfile->n_allocated_type_units);
       ++dwarf2_per_objfile->tu_stats.nr_all_type_units_reallocs;
     }
   dwarf2_per_objfile->n_type_units = n_type_units;
@@ -4846,12 +5043,12 @@ fill_in_sig_entry_from_dwo_entry (struct objfile *objfile,
   else
       gdb_assert (sig_entry->per_cu.v.psymtab == NULL);
   gdb_assert (sig_entry->signature == dwo_entry->signature);
-  gdb_assert (sig_entry->type_offset_in_section.sect_off == 0);
+  gdb_assert (to_underlying (sig_entry->type_offset_in_section) == 0);
   gdb_assert (sig_entry->type_unit_group == NULL);
   gdb_assert (sig_entry->dwo_unit == NULL);
 
   sig_entry->per_cu.section = dwo_entry->section;
-  sig_entry->per_cu.offset = dwo_entry->offset;
+  sig_entry->per_cu.sect_off = dwo_entry->sect_off;
   sig_entry->per_cu.length = dwo_entry->length;
   sig_entry->per_cu.reading_dwo_directly = 1;
   sig_entry->per_cu.objfile = objfile;
@@ -4899,7 +5096,7 @@ lookup_dwo_signatured_type (struct dwarf2_cu *cu, ULONGEST sig)
   find_sig_entry.signature = sig;
   slot = htab_find_slot (dwarf2_per_objfile->signatured_types,
                         &find_sig_entry, INSERT);
-  sig_entry = *slot;
+  sig_entry = (struct signatured_type *) *slot;
 
   /* We can get here with the TU already read, *or* in the process of being
      read.  Don't reassign the global entry to point to this DWO if that's
@@ -4921,7 +5118,7 @@ lookup_dwo_signatured_type (struct dwarf2_cu *cu, ULONGEST sig)
   if (dwo_file->tus == NULL)
     return NULL;
   find_dwo_entry.signature = sig;
-  dwo_entry = htab_find (dwo_file->tus, &find_dwo_entry);
+  dwo_entry = (struct dwo_unit *) htab_find (dwo_file->tus, &find_dwo_entry);
   if (dwo_entry == NULL)
     return NULL;
 
@@ -4962,7 +5159,7 @@ lookup_dwp_signatured_type (struct dwarf2_cu *cu, ULONGEST sig)
   find_sig_entry.signature = sig;
   slot = htab_find_slot (dwarf2_per_objfile->signatured_types,
                         &find_sig_entry, INSERT);
-  sig_entry = *slot;
+  sig_entry = (struct signatured_type *) *slot;
 
   /* Have we already tried to read this TU?
      Note: sig_entry can be NULL if the skeleton TU was removed (thus it
@@ -5007,7 +5204,8 @@ lookup_signatured_type (struct dwarf2_cu *cu, ULONGEST sig)
       if (dwarf2_per_objfile->signatured_types == NULL)
        return NULL;
       find_entry.signature = sig;
-      entry = htab_find (dwarf2_per_objfile->signatured_types, &find_entry);
+      entry = ((struct signatured_type *)
+              htab_find (dwarf2_per_objfile->signatured_types, &find_entry));
       return entry;
     }
 }
@@ -5117,8 +5315,7 @@ read_cutu_die_from_dwo (struct dwarf2_per_cu_data *this_cu,
   else if (stub_comp_dir != NULL)
     {
       /* Reconstruct the comp_dir attribute to simplify the code below.  */
-      comp_dir = (struct attribute *)
-       obstack_alloc (&cu->comp_unit_obstack, sizeof (*comp_dir));
+      comp_dir = XOBNEW (&cu->comp_unit_obstack, struct attribute);
       comp_dir->name = DW_AT_comp_dir;
       comp_dir->form = DW_FORM_string;
       DW_STRING_IS_CANONICAL (comp_dir) = 0;
@@ -5130,48 +5327,45 @@ read_cutu_die_from_dwo (struct dwarf2_per_cu_data *this_cu,
   section = dwo_unit->section;
   dwarf2_read_section (objfile, section);
   abfd = get_section_bfd_owner (section);
-  begin_info_ptr = info_ptr = section->buffer + dwo_unit->offset.sect_off;
+  begin_info_ptr = info_ptr = (section->buffer
+                              + to_underlying (dwo_unit->sect_off));
   dwo_abbrev_section = &dwo_unit->dwo_file->sections.abbrev;
   init_cu_die_reader (result_reader, cu, section, dwo_unit->dwo_file);
 
   if (this_cu->is_debug_types)
     {
-      ULONGEST header_signature;
-      cu_offset type_offset_in_tu;
       struct signatured_type *sig_type = (struct signatured_type *) this_cu;
 
-      info_ptr = read_and_check_type_unit_head (&cu->header, section,
+      info_ptr = read_and_check_comp_unit_head (&cu->header, section,
                                                dwo_abbrev_section,
-                                               info_ptr,
-                                               &header_signature,
-                                               &type_offset_in_tu);
+                                               info_ptr, rcuh_kind::TYPE);
       /* This is not an assert because it can be caused by bad debug info.  */
-      if (sig_type->signature != header_signature)
+      if (sig_type->signature != cu->header.signature)
        {
          error (_("Dwarf Error: signature mismatch %s vs %s while reading"
                   " TU at offset 0x%x [in module %s]"),
                 hex_string (sig_type->signature),
-                hex_string (header_signature),
-                dwo_unit->offset.sect_off,
+                hex_string (cu->header.signature),
+                to_underlying (dwo_unit->sect_off),
                 bfd_get_filename (abfd));
        }
-      gdb_assert (dwo_unit->offset.sect_off == cu->header.offset.sect_off);
+      gdb_assert (dwo_unit->sect_off == cu->header.sect_off);
       /* For DWOs coming from DWP files, we don't know the CU length
         nor the type's offset in the TU until now.  */
       dwo_unit->length = get_cu_length (&cu->header);
-      dwo_unit->type_offset_in_tu = type_offset_in_tu;
+      dwo_unit->type_offset_in_tu = cu->header.type_cu_offset_in_tu;
 
       /* Establish the type offset that can be used to lookup the type.
         For DWO files, we don't know it until now.  */
-      sig_type->type_offset_in_section.sect_off =
-       dwo_unit->offset.sect_off + dwo_unit->type_offset_in_tu.cu_off;
+      sig_type->type_offset_in_section
+       = dwo_unit->sect_off + to_underlying (dwo_unit->type_offset_in_tu);
     }
   else
     {
       info_ptr = read_and_check_comp_unit_head (&cu->header, section,
                                                dwo_abbrev_section,
-                                               info_ptr, 0);
-      gdb_assert (dwo_unit->offset.sect_off == cu->header.offset.sect_off);
+                                               info_ptr, rcuh_kind::COMPILE);
+      gdb_assert (dwo_unit->sect_off == cu->header.sect_off);
       /* For DWOs coming from DWP files, we don't know the CU length
         until now.  */
       dwo_unit->length = get_cu_length (&cu->header);
@@ -5264,13 +5458,8 @@ lookup_dwo_unit (struct dwarf2_per_cu_data *this_cu,
   gdb_assert (cu != NULL);
 
   /* Yeah, we look dwo_name up again, but it simplifies the code.  */
-  attr = dwarf2_attr (comp_unit_die, DW_AT_GNU_dwo_name, cu);
-  gdb_assert (attr != NULL);
-  dwo_name = DW_STRING (attr);
-  comp_dir = NULL;
-  attr = dwarf2_attr (comp_unit_die, DW_AT_comp_dir, cu);
-  if (attr)
-    comp_dir = DW_STRING (attr);
+  dwo_name = dwarf2_string_attr (comp_unit_die, DW_AT_GNU_dwo_name, cu);
+  comp_dir = dwarf2_string_attr (comp_unit_die, DW_AT_comp_dir, cu);
 
   if (this_cu->is_debug_types)
     {
@@ -5341,7 +5530,7 @@ init_tu_and_read_dwo_dies (struct dwarf2_per_cu_data *this_cu,
     {
       /* If !use_existing_cu, this_cu->cu must be NULL.  */
       gdb_assert (this_cu->cu == NULL);
-      cu = xmalloc (sizeof (*cu));
+      cu = XNEW (struct dwarf2_cu);
       init_one_comp_unit (cu, this_cu);
       /* If an error occurs while loading, release our storage.  */
       free_cu_cleanup = make_cleanup (free_heap_comp_unit, cu);
@@ -5436,7 +5625,7 @@ init_cutu_and_read_dies (struct dwarf2_per_cu_data *this_cu,
   if (dwarf_die_debug)
     fprintf_unfiltered (gdb_stdlog, "Reading %s unit at offset 0x%x\n",
                        this_cu->is_debug_types ? "type" : "comp",
-                       this_cu->offset.sect_off);
+                       to_underlying (this_cu->sect_off));
 
   if (use_existing_cu)
     gdb_assert (keep);
@@ -5458,7 +5647,7 @@ init_cutu_and_read_dies (struct dwarf2_per_cu_data *this_cu,
   /* This is cheap if the section is already read in.  */
   dwarf2_read_section (objfile, section);
 
-  begin_info_ptr = info_ptr = section->buffer + this_cu->offset.sect_off;
+  begin_info_ptr = info_ptr = section->buffer + to_underlying (this_cu->sect_off);
 
   abbrev_section = get_abbrev_section_for_cu (this_cu);
 
@@ -5478,54 +5667,54 @@ init_cutu_and_read_dies (struct dwarf2_per_cu_data *this_cu,
     {
       /* If !use_existing_cu, this_cu->cu must be NULL.  */
       gdb_assert (this_cu->cu == NULL);
-      cu = xmalloc (sizeof (*cu));
+      cu = XNEW (struct dwarf2_cu);
       init_one_comp_unit (cu, this_cu);
       /* If an error occurs while loading, release our storage.  */
       free_cu_cleanup = make_cleanup (free_heap_comp_unit, cu);
     }
 
   /* Get the header.  */
-  if (cu->header.first_die_offset.cu_off != 0 && ! rereading_dwo_cu)
+  if (to_underlying (cu->header.first_die_cu_offset) != 0 && !rereading_dwo_cu)
     {
       /* We already have the header, there's no need to read it in again.  */
-      info_ptr += cu->header.first_die_offset.cu_off;
+      info_ptr += to_underlying (cu->header.first_die_cu_offset);
     }
   else
     {
       if (this_cu->is_debug_types)
        {
-         ULONGEST signature;
-         cu_offset type_offset_in_tu;
-
-         info_ptr = read_and_check_type_unit_head (&cu->header, section,
+         info_ptr = read_and_check_comp_unit_head (&cu->header, section,
                                                    abbrev_section, info_ptr,
-                                                   &signature,
-                                                   &type_offset_in_tu);
+                                                   rcuh_kind::TYPE);
 
          /* Since per_cu is the first member of struct signatured_type,
             we can go from a pointer to one to a pointer to the other.  */
          sig_type = (struct signatured_type *) this_cu;
-         gdb_assert (sig_type->signature == signature);
-         gdb_assert (sig_type->type_offset_in_tu.cu_off
-                     == type_offset_in_tu.cu_off);
-         gdb_assert (this_cu->offset.sect_off == cu->header.offset.sect_off);
+         gdb_assert (sig_type->signature == cu->header.signature);
+         gdb_assert (sig_type->type_offset_in_tu
+                     == cu->header.type_cu_offset_in_tu);
+         gdb_assert (this_cu->sect_off == cu->header.sect_off);
 
          /* LENGTH has not been set yet for type units if we're
             using .gdb_index.  */
          this_cu->length = get_cu_length (&cu->header);
 
          /* Establish the type offset that can be used to lookup the type.  */
-         sig_type->type_offset_in_section.sect_off =
-           this_cu->offset.sect_off + sig_type->type_offset_in_tu.cu_off;
+         sig_type->type_offset_in_section =
+           this_cu->sect_off + to_underlying (sig_type->type_offset_in_tu);
+
+         this_cu->dwarf_version = cu->header.version;
        }
       else
        {
          info_ptr = read_and_check_comp_unit_head (&cu->header, section,
                                                    abbrev_section,
-                                                   info_ptr, 0);
+                                                   info_ptr,
+                                                   rcuh_kind::COMPILE);
 
-         gdb_assert (this_cu->offset.sect_off == cu->header.offset.sect_off);
+         gdb_assert (this_cu->sect_off == cu->header.sect_off);
          gdb_assert (this_cu->length == get_cu_length (&cu->header));
+         this_cu->dwarf_version = cu->header.version;
        }
     }
 
@@ -5545,8 +5734,7 @@ init_cutu_and_read_dies (struct dwarf2_per_cu_data *this_cu,
   if (abbrev_table != NULL)
     {
       gdb_assert (cu->abbrev_table == NULL);
-      gdb_assert (cu->header.abbrev_offset.sect_off
-                 == abbrev_table->offset.sect_off);
+      gdb_assert (cu->header.abbrev_sect_off == abbrev_table->sect_off);
       cu->abbrev_table = abbrev_table;
     }
   else if (cu->abbrev_table == NULL)
@@ -5579,7 +5767,7 @@ init_cutu_and_read_dies (struct dwarf2_per_cu_data *this_cu,
          complaint (&symfile_complaints,
                     _("compilation unit with DW_AT_GNU_dwo_name"
                       " has children (offset 0x%x) [in module %s]"),
-                    this_cu->offset.sect_off, bfd_get_filename (abfd));
+                    to_underlying (this_cu->sect_off), bfd_get_filename (abfd));
        }
       dwo_unit = lookup_dwo_unit (this_cu, comp_unit_die);
       if (dwo_unit != NULL)
@@ -5669,7 +5857,7 @@ init_cutu_and_read_dies_no_follow (struct dwarf2_per_cu_data *this_cu,
   if (dwarf_die_debug)
     fprintf_unfiltered (gdb_stdlog, "Reading %s unit at offset 0x%x\n",
                        this_cu->is_debug_types ? "type" : "comp",
-                       this_cu->offset.sect_off);
+                       to_underlying (this_cu->sect_off));
 
   gdb_assert (this_cu->cu == NULL);
 
@@ -5684,10 +5872,12 @@ init_cutu_and_read_dies_no_follow (struct dwarf2_per_cu_data *this_cu,
 
   cleanups = make_cleanup (free_stack_comp_unit, &cu);
 
-  begin_info_ptr = info_ptr = section->buffer + this_cu->offset.sect_off;
+  begin_info_ptr = info_ptr = section->buffer + to_underlying (this_cu->sect_off);
   info_ptr = read_and_check_comp_unit_head (&cu.header, section,
                                            abbrev_section, info_ptr,
-                                           this_cu->is_debug_types);
+                                           (this_cu->is_debug_types
+                                            ? rcuh_kind::TYPE
+                                            : rcuh_kind::COMPILE));
 
   this_cu->length = get_cu_length (&cu.header);
 
@@ -5738,7 +5928,8 @@ init_cutu_and_read_dies_simple (struct dwarf2_per_cu_data *this_cu,
 static hashval_t
 hash_type_unit_group (const void *item)
 {
-  const struct type_unit_group *tu_group = item;
+  const struct type_unit_group *tu_group
+    = (const struct type_unit_group *) item;
 
   return hash_stmt_list_entry (&tu_group->hash);
 }
@@ -5746,8 +5937,8 @@ hash_type_unit_group (const void *item)
 static int
 eq_type_unit_group (const void *item_lhs, const void *item_rhs)
 {
-  const struct type_unit_group *lhs = item_lhs;
-  const struct type_unit_group *rhs = item_rhs;
+  const struct type_unit_group *lhs = (const struct type_unit_group *) item_lhs;
+  const struct type_unit_group *rhs = (const struct type_unit_group *) item_rhs;
 
   return eq_stmt_list_entry (&lhs->hash, &rhs->hash);
 }
@@ -5794,7 +5985,7 @@ create_type_unit_group (struct dwarf2_cu *cu, sect_offset line_offset_struct)
     }
   else
     {
-      unsigned int line_offset = line_offset_struct.sect_off;
+      unsigned int line_offset = to_underlying (line_offset_struct);
       struct partial_symtab *pst;
       char *name;
 
@@ -5812,7 +6003,7 @@ create_type_unit_group (struct dwarf2_cu *cu, sect_offset line_offset_struct)
     }
 
   tu_group->hash.dwo_unit = cu->dwo_unit;
-  tu_group->hash.line_offset = line_offset_struct;
+  tu_group->hash.line_sect_off = line_offset_struct;
 
   return tu_group;
 }
@@ -5856,19 +6047,17 @@ get_type_unit_group (struct dwarf2_cu *cu, const struct attribute *stmt_list)
     }
 
   type_unit_group_for_lookup.hash.dwo_unit = cu->dwo_unit;
-  type_unit_group_for_lookup.hash.line_offset.sect_off = line_offset;
+  type_unit_group_for_lookup.hash.line_sect_off = (sect_offset) line_offset;
   slot = htab_find_slot (dwarf2_per_objfile->type_unit_groups,
                         &type_unit_group_for_lookup, INSERT);
   if (*slot != NULL)
     {
-      tu_group = *slot;
+      tu_group = (struct type_unit_group *) *slot;
       gdb_assert (tu_group != NULL);
     }
   else
     {
-      sect_offset line_offset_struct;
-
-      line_offset_struct.sect_off = line_offset;
+      sect_offset line_offset_struct = (sect_offset) line_offset;
       tu_group = create_type_unit_group (cu, line_offset_struct);
       *slot = tu_group;
       ++tu_stats->nr_symtabs;
@@ -5932,13 +6121,13 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
   struct objfile *objfile = cu->objfile;
   struct gdbarch *gdbarch = get_objfile_arch (objfile);
   struct dwarf2_per_cu_data *per_cu = cu->per_cu;
-  struct attribute *attr;
   CORE_ADDR baseaddr;
   CORE_ADDR best_lowpc = 0, best_highpc = 0;
   struct partial_symtab *pst;
-  int has_pc_info;
+  enum pc_bounds_kind cu_bounds_kind;
   const char *filename;
-  struct process_psymtab_comp_unit_data *info = data;
+  struct process_psymtab_comp_unit_data *info
+    = (struct process_psymtab_comp_unit_data *) data;
 
   if (comp_unit_die->tag == DW_TAG_partial_unit && !info->want_partial_unit)
     return;
@@ -5950,18 +6139,14 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
   cu->list_in_scope = &file_symbols;
 
   /* Allocate a new partial symbol table structure.  */
-  attr = dwarf2_attr (comp_unit_die, DW_AT_name, cu);
-  if (attr == NULL || !DW_STRING (attr))
+  filename = dwarf2_string_attr (comp_unit_die, DW_AT_name, cu);
+  if (filename == NULL)
     filename = "";
-  else
-    filename = DW_STRING (attr);
 
   pst = create_partial_symtab (per_cu, filename);
 
   /* This must be done before calling dwarf2_build_include_psymtabs.  */
-  attr = dwarf2_attr (comp_unit_die, DW_AT_comp_dir, cu);
-  if (attr != NULL)
-    pst->dirname = DW_STRING (attr);
+  pst->dirname = dwarf2_string_attr (comp_unit_die, DW_AT_comp_dir, cu);
 
   baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
 
@@ -5969,9 +6154,9 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
 
   /* Possibly set the default values of LOWPC and HIGHPC from
      `DW_AT_ranges'.  */
-  has_pc_info = dwarf2_get_pc_bounds (comp_unit_die, &best_lowpc,
-                                     &best_highpc, cu, pst);
-  if (has_pc_info == 1 && best_lowpc < best_highpc)
+  cu_bounds_kind = dwarf2_get_pc_bounds (comp_unit_die, &best_lowpc,
+                                        &best_highpc, cu, pst);
+  if (cu_bounds_kind == PC_BOUNDS_HIGH_LOW && best_lowpc < best_highpc)
     /* Store the contiguous range if it is not empty; it can be empty for
        CUs with no code.  */
     addrmap_set_empty (objfile->psymtabs_addrmap,
@@ -5995,7 +6180,7 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
       first_die = load_partial_dies (reader, info_ptr, 1);
 
       scan_partial_symbols (first_die, &lowpc, &highpc,
-                           ! has_pc_info, cu);
+                           cu_bounds_kind <= PC_BOUNDS_INVALID, cu);
 
       /* If we didn't find a lowpc, set it to highpc to avoid
         complaints from `maint check'.  */
@@ -6004,7 +6189,7 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
 
       /* If the compilation unit didn't have an explicit address range,
         then use the information extracted from its child dies.  */
-      if (! has_pc_info)
+      if (cu_bounds_kind <= PC_BOUNDS_INVALID)
        {
          best_lowpc = lowpc;
          best_highpc = highpc;
@@ -6013,11 +6198,7 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
   pst->textlow = gdbarch_adjust_dwarf2_addr (gdbarch, best_lowpc + baseaddr);
   pst->texthigh = gdbarch_adjust_dwarf2_addr (gdbarch, best_highpc + baseaddr);
 
-  pst->n_global_syms = objfile->global_psymbols.next -
-    (objfile->global_psymbols.list + pst->globals_offset);
-  pst->n_static_syms = objfile->static_psymbols.next -
-    (objfile->static_psymbols.list + pst->statics_offset);
-  sort_pst_symbols (objfile, pst);
+  end_psymtab_common (objfile, pst);
 
   if (!VEC_empty (dwarf2_per_cu_ptr, cu->per_cu->imported_symtabs))
     {
@@ -6028,8 +6209,8 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
       /* Fill in 'dependencies' here; we fill in 'users' in a
         post-pass.  */
       pst->number_of_dependencies = len;
-      pst->dependencies = obstack_alloc (&objfile->objfile_obstack,
-                                        len * sizeof (struct symtab *));
+      pst->dependencies =
+       XOBNEWVEC (&objfile->objfile_obstack, struct partial_symtab *, len);
       for (i = 0;
           VEC_iterate (dwarf2_per_cu_ptr, cu->per_cu->imported_symtabs,
                        i, iter);
@@ -6051,7 +6232,7 @@ process_psymtab_comp_unit_reader (const struct die_reader_specs *reader,
                          "Psymtab for %s unit @0x%x: %s - %s"
                          ", %d global, %d static syms\n",
                          per_cu->is_debug_types ? "type" : "comp",
-                         per_cu->offset.sect_off,
+                         to_underlying (per_cu->sect_off),
                          paddress (gdbarch, pst->textlow),
                          paddress (gdbarch, pst->texthigh),
                          pst->n_global_syms, pst->n_static_syms);
@@ -6129,11 +6310,7 @@ build_type_psymtabs_reader (const struct die_reader_specs *reader,
   highpc = (CORE_ADDR) 0;
   scan_partial_symbols (first_die, &lowpc, &highpc, 0, cu);
 
-  pst->n_global_syms = objfile->global_psymbols.next -
-    (objfile->global_psymbols.list + pst->globals_offset);
-  pst->n_static_syms = objfile->static_psymbols.next -
-    (objfile->static_psymbols.list + pst->statics_offset);
-  sort_pst_symbols (objfile, pst);
+  end_psymtab_common (objfile, pst);
 }
 
 /* Struct used to sort TUs by their abbreviation table offset.  */
@@ -6149,10 +6326,12 @@ struct tu_abbrev_offset
 static int
 sort_tu_by_abbrev_offset (const void *ap, const void *bp)
 {
-  const struct tu_abbrev_offset * const *a = ap;
-  const struct tu_abbrev_offset * const *b = bp;
-  unsigned int aoff = (*a)->abbrev_offset.sect_off;
-  unsigned int boff = (*b)->abbrev_offset.sect_off;
+  const struct tu_abbrev_offset * const *a
+    = (const struct tu_abbrev_offset * const*) ap;
+  const struct tu_abbrev_offset * const *b
+    = (const struct tu_abbrev_offset * const*) bp;
+  sect_offset aoff = (*a)->abbrev_offset;
+  sect_offset boff = (*b)->abbrev_offset;
 
   return (aoff > boff) - (aoff < boff);
 }
@@ -6178,13 +6357,11 @@ sort_tu_by_abbrev_offset (const void *ap, const void *bp)
 static void
 build_type_psymtabs_1 (void)
 {
-  struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct tu_stats *tu_stats = &dwarf2_per_objfile->tu_stats;
   struct cleanup *cleanups;
   struct abbrev_table *abbrev_table;
   sect_offset abbrev_offset;
   struct tu_abbrev_offset *sorted_by_abbrev;
-  struct type_unit_group **iter;
   int i;
 
   /* It's up to the caller to not call us multiple times.  */
@@ -6226,13 +6403,13 @@ build_type_psymtabs_1 (void)
       sorted_by_abbrev[i].sig_type = sig_type;
       sorted_by_abbrev[i].abbrev_offset =
        read_abbrev_offset (sig_type->per_cu.section,
-                           sig_type->per_cu.offset);
+                           sig_type->per_cu.sect_off);
     }
   cleanups = make_cleanup (xfree, sorted_by_abbrev);
   qsort (sorted_by_abbrev, dwarf2_per_objfile->n_type_units,
         sizeof (struct tu_abbrev_offset), sort_tu_by_abbrev_offset);
 
-  abbrev_offset.sect_off = ~(unsigned) 0;
+  abbrev_offset = (sect_offset) ~(unsigned) 0;
   abbrev_table = NULL;
   make_cleanup (abbrev_table_free_cleanup, &abbrev_table);
 
@@ -6242,7 +6419,7 @@ build_type_psymtabs_1 (void)
 
       /* Switch to the next abbrev table if necessary.  */
       if (abbrev_table == NULL
-         || tu->abbrev_offset.sect_off != abbrev_offset.sect_off)
+         || tu->abbrev_offset != abbrev_offset)
        {
          if (abbrev_table != NULL)
            {
@@ -6304,8 +6481,8 @@ build_type_psymtab_dependencies (void **slot, void *info)
   gdb_assert (IS_TYPE_UNIT_GROUP (per_cu));
 
   pst->number_of_dependencies = len;
-  pst->dependencies = obstack_alloc (&objfile->objfile_obstack,
-                                    len * sizeof (struct psymtab *));
+  pst->dependencies =
+    XOBNEWVEC (&objfile->objfile_obstack, struct partial_symtab *, len);
   for (i = 0;
        VEC_iterate (sig_type_ptr, tu_group->tus, i, iter);
        ++i)
@@ -6339,7 +6516,7 @@ static int
 process_skeletonless_type_unit (void **slot, void *info)
 {
   struct dwo_unit *dwo_unit = (struct dwo_unit *) *slot;
-  struct objfile *objfile = info;
+  struct objfile *objfile = (struct objfile *) info;
   struct signatured_type find_entry, *entry;
 
   /* If this TU doesn't exist in the global table, add it and read it in.  */
@@ -6409,7 +6586,7 @@ process_skeletonless_type_units (struct objfile *objfile)
 static void
 psymtabs_addrmap_cleanup (void *o)
 {
-  struct objfile *objfile = o;
+  struct objfile *objfile = (struct objfile *) o;
 
   objfile->psymtabs_addrmap = NULL;
 }
@@ -6561,19 +6738,17 @@ read_comp_units_from_section (struct objfile *objfile,
     {
       unsigned int length, initial_length_size;
       struct dwarf2_per_cu_data *this_cu;
-      sect_offset offset;
 
-      offset.sect_off = info_ptr - section->buffer;
+      sect_offset sect_off = (sect_offset) (info_ptr - section->buffer);
 
       /* Read just enough information to find out where the next
         compilation unit is.  */
       length = read_initial_length (abfd, info_ptr, &initial_length_size);
 
       /* Save the compilation unit for later lookup.  */
-      this_cu = obstack_alloc (&objfile->objfile_obstack,
-                              sizeof (struct dwarf2_per_cu_data));
+      this_cu = XOBNEW (&objfile->objfile_obstack, struct dwarf2_per_cu_data);
       memset (this_cu, 0, sizeof (*this_cu));
-      this_cu->offset = offset;
+      this_cu->sect_off = sect_off;
       this_cu->length = length + initial_length_size;
       this_cu->is_dwz = is_dwz;
       this_cu->objfile = objfile;
@@ -6582,9 +6757,8 @@ read_comp_units_from_section (struct objfile *objfile,
       if (*n_comp_units == *n_allocated)
        {
          *n_allocated *= 2;
-         *all_comp_units = xrealloc (*all_comp_units,
-                                     *n_allocated
-                                     * sizeof (struct dwarf2_per_cu_data *));
+         *all_comp_units = XRESIZEVEC (struct dwarf2_per_cu_data *,
+                                       *all_comp_units, *n_allocated);
        }
       (*all_comp_units)[*n_comp_units] = this_cu;
       ++*n_comp_units;
@@ -6606,8 +6780,7 @@ create_all_comp_units (struct objfile *objfile)
 
   n_comp_units = 0;
   n_allocated = 10;
-  all_comp_units = xmalloc (n_allocated
-                           * sizeof (struct dwarf2_per_cu_data *));
+  all_comp_units = XNEWVEC (struct dwarf2_per_cu_data *, n_allocated);
 
   read_comp_units_from_section (objfile, &dwarf2_per_objfile->info, 0,
                                &n_allocated, &n_comp_units, &all_comp_units);
@@ -6618,9 +6791,9 @@ create_all_comp_units (struct objfile *objfile)
                                  &n_allocated, &n_comp_units,
                                  &all_comp_units);
 
-  dwarf2_per_objfile->all_comp_units
-    = obstack_alloc (&objfile->objfile_obstack,
-                    n_comp_units * sizeof (struct dwarf2_per_cu_data *));
+  dwarf2_per_objfile->all_comp_units = XOBNEWVEC (&objfile->objfile_obstack,
+                                                 struct dwarf2_per_cu_data *,
+                                                 n_comp_units);
   memcpy (dwarf2_per_objfile->all_comp_units, all_comp_units,
          n_comp_units * sizeof (struct dwarf2_per_cu_data *));
   xfree (all_comp_units);
@@ -6679,6 +6852,9 @@ scan_partial_symbols (struct partial_die_info *first_die, CORE_ADDR *lowpc,
                {
                  add_partial_symbol (pdi, cu);
                }
+             if (cu->language == language_rust && pdi->has_children)
+               scan_partial_symbols (pdi->die_child, lowpc, highpc,
+                                     set_addrmap, cu);
              break;
            case DW_TAG_enumeration_type:
              if (!pdi->is_declaration)
@@ -6708,7 +6884,7 @@ scan_partial_symbols (struct partial_die_info *first_die, CORE_ADDR *lowpc,
                           objfile_name (cu->objfile));
                  }
 
-               per_cu = dwarf2_find_containing_comp_unit (pdi->d.offset,
+               per_cu = dwarf2_find_containing_comp_unit (pdi->d.sect_off,
                                                           pdi->is_dwz,
                                                           cu->objfile);
 
@@ -6737,8 +6913,7 @@ scan_partial_symbols (struct partial_die_info *first_die, CORE_ADDR *lowpc,
 /* Functions used to compute the fully scoped name of a partial DIE.
 
    Normally, this is simple.  For C++, the parent DIE's fully scoped
-   name is concatenated with "::" and the partial DIE's name.  For
-   Java, the same thing occurs except that "." is used instead of "::".
+   name is concatenated with "::" and the partial DIE's name.
    Enumerators are an exception; they use the scope of their parent
    enumeration type, i.e. the name of the enumeration type is not
    prepended to the enumerator.
@@ -6822,7 +6997,7 @@ partial_die_parent_scope (struct partial_die_info *pdi,
         ignoring them.  */
       complaint (&symfile_complaints,
                 _("unhandled containing DIE tag %d for DIE at %d"),
-                parent->tag, pdi->offset.sect_off);
+                parent->tag, to_underlying (pdi->sect_off));
       parent->scope = grandparent_scope;
     }
 
@@ -6854,9 +7029,9 @@ partial_die_full_name (struct partial_die_info *pdi,
          struct dwarf2_cu *ref_cu = cu;
 
          /* DW_FORM_ref_addr is using section offset.  */
-         attr.name = 0;
+         attr.name = (enum dwarf_attribute) 0;
          attr.form = DW_FORM_ref_addr;
-         attr.u.unsnd = pdi->offset.sect_off;
+         attr.u.unsnd = to_underlying (pdi->sect_off);
          die = follow_die_ref (NULL, &attr, &ref_cu);
 
          return xstrdup (dwarf2_full_name (NULL, die, ref_cu));
@@ -6899,24 +7074,23 @@ add_partial_symbol (struct partial_die_info *pdi, struct dwarf2_cu *cu)
              of the global scope.  But in Ada, we want to be able to access
              nested procedures globally.  So all Ada subprograms are stored
              in the global scope.  */
-         /* prim_record_minimal_symbol (actual_name, addr, mst_text,
-            objfile); */
          add_psymbol_to_list (actual_name, strlen (actual_name),
                               built_actual_name != NULL,
                               VAR_DOMAIN, LOC_BLOCK,
                               &objfile->global_psymbols,
-                              0, addr, cu->language, objfile);
+                              addr, cu->language, objfile);
        }
       else
        {
-         /* prim_record_minimal_symbol (actual_name, addr, mst_file_text,
-            objfile); */
          add_psymbol_to_list (actual_name, strlen (actual_name),
                               built_actual_name != NULL,
                               VAR_DOMAIN, LOC_BLOCK,
                               &objfile->static_psymbols,
-                              0, addr, cu->language, objfile);
+                              addr, cu->language, objfile);
        }
+
+      if (pdi->main_subprogram && actual_name != NULL)
+       set_objfile_main_name (objfile, actual_name, cu->language);
       break;
     case DW_TAG_constant:
       {
@@ -6928,7 +7102,7 @@ add_partial_symbol (struct partial_die_info *pdi, struct dwarf2_cu *cu)
          list = &objfile->static_psymbols;
        add_psymbol_to_list (actual_name, strlen (actual_name),
                             built_actual_name != NULL, VAR_DOMAIN, LOC_STATIC,
-                            list, 0, 0, cu->language, objfile);
+                            list, 0, cu->language, objfile);
       }
       break;
     case DW_TAG_variable:
@@ -6964,7 +7138,7 @@ add_partial_symbol (struct partial_die_info *pdi, struct dwarf2_cu *cu)
                                 built_actual_name != NULL,
                                 VAR_DOMAIN, LOC_STATIC,
                                 &objfile->global_psymbols,
-                                0, addr + baseaddr,
+                                addr + baseaddr,
                                 cu->language, objfile);
        }
       else
@@ -6979,13 +7153,10 @@ add_partial_symbol (struct partial_die_info *pdi, struct dwarf2_cu *cu)
              return;
            }
 
-         /* prim_record_minimal_symbol (actual_name, addr + baseaddr,
-            mst_file_data, objfile); */
          add_psymbol_to_list (actual_name, strlen (actual_name),
                               built_actual_name != NULL,
                               VAR_DOMAIN, LOC_STATIC,
                               &objfile->static_psymbols,
-                              0,
                               has_loc ? addr + baseaddr : (CORE_ADDR) 0,
                               cu->language, objfile);
        }
@@ -6997,7 +7168,7 @@ add_partial_symbol (struct partial_die_info *pdi, struct dwarf2_cu *cu)
                           built_actual_name != NULL,
                           VAR_DOMAIN, LOC_TYPEDEF,
                           &objfile->static_psymbols,
-                          0, (CORE_ADDR) 0, cu->language, objfile);
+                          0, cu->language, objfile);
       break;
     case DW_TAG_imported_declaration:
     case DW_TAG_namespace:
@@ -7005,14 +7176,14 @@ add_partial_symbol (struct partial_die_info *pdi, struct dwarf2_cu *cu)
                           built_actual_name != NULL,
                           VAR_DOMAIN, LOC_TYPEDEF,
                           &objfile->global_psymbols,
-                          0, (CORE_ADDR) 0, cu->language, objfile);
+                          0, cu->language, objfile);
       break;
     case DW_TAG_module:
       add_psymbol_to_list (actual_name, strlen (actual_name),
                           built_actual_name != NULL,
                           MODULE_DOMAIN, LOC_TYPEDEF,
                           &objfile->global_psymbols,
-                          0, (CORE_ADDR) 0, cu->language, objfile);
+                          0, cu->language, objfile);
       break;
     case DW_TAG_class_type:
     case DW_TAG_interface_type:
@@ -7035,22 +7206,20 @@ add_partial_symbol (struct partial_die_info *pdi, struct dwarf2_cu *cu)
       add_psymbol_to_list (actual_name, strlen (actual_name),
                           built_actual_name != NULL,
                           STRUCT_DOMAIN, LOC_TYPEDEF,
-                          (cu->language == language_cplus
-                           || cu->language == language_java)
+                          cu->language == language_cplus
                           ? &objfile->global_psymbols
                           : &objfile->static_psymbols,
-                          0, (CORE_ADDR) 0, cu->language, objfile);
+                          0, cu->language, objfile);
 
       break;
     case DW_TAG_enumerator:
       add_psymbol_to_list (actual_name, strlen (actual_name),
                           built_actual_name != NULL,
                           VAR_DOMAIN, LOC_CONST,
-                          (cu->language == language_cplus
-                           || cu->language == language_java)
+                          cu->language == language_cplus
                           ? &objfile->global_psymbols
                           : &objfile->static_psymbols,
-                          0, (CORE_ADDR) 0, cu->language, objfile);
+                          0, cu->language, objfile);
       break;
     default:
       break;
@@ -7222,7 +7391,7 @@ peek_die_abbrev (const gdb_byte *info_ptr, unsigned int *bytes_read,
       error (_("Dwarf Error: Could not find abbrev number %d in %s"
               " at offset 0x%x [in module %s]"),
             abbrev_number, cu->per_cu->is_debug_types ? "TU" : "CU",
-            cu->header.offset.sect_off, bfd_get_filename (abfd));
+            to_underlying (cu->header.sect_off), bfd_get_filename (abfd));
     }
 
   return abbrev;
@@ -7265,7 +7434,6 @@ skip_one_die (const struct die_reader_specs *reader, const gdb_byte *info_ptr,
   struct dwarf2_cu *cu = reader->cu;
   const gdb_byte *buffer = reader->buffer;
   const gdb_byte *buffer_end = reader->buffer_end;
-  const gdb_byte *start_info_ptr = info_ptr;
   unsigned int form, i;
 
   for (i = 0; i < abbrev->num_attrs; i++)
@@ -7279,8 +7447,8 @@ skip_one_die (const struct die_reader_specs *reader, const gdb_byte *info_ptr,
                       _("ignoring absolute DW_AT_sibling"));
          else
            {
-             unsigned int off = dwarf2_get_ref_die_offset (&attr).sect_off;
-             const gdb_byte *sibling_ptr = buffer + off;
+             sect_offset off = dwarf2_get_ref_die_offset (&attr);
+             const gdb_byte *sibling_ptr = buffer + to_underlying (off);
 
              if (sibling_ptr < info_ptr)
                complaint (&symfile_complaints,
@@ -7317,6 +7485,7 @@ skip_one_die (const struct die_reader_specs *reader, const gdb_byte *info_ptr,
          info_ptr += 1;
          break;
        case DW_FORM_flag_present:
+       case DW_FORM_implicit_const:
          break;
        case DW_FORM_data2:
        case DW_FORM_ref2:
@@ -7331,6 +7500,9 @@ skip_one_die (const struct die_reader_specs *reader, const gdb_byte *info_ptr,
        case DW_FORM_ref_sig8:
          info_ptr += 8;
          break;
+       case DW_FORM_data16:
+         info_ptr += 16;
+         break;
        case DW_FORM_string:
          read_direct_string (abfd, info_ptr, &bytes_read);
          info_ptr += bytes_read;
@@ -7427,7 +7599,9 @@ dwarf2_read_symtab (struct partial_symtab *self,
        }
 
       /* Restore our global data.  */
-      dwarf2_per_objfile = objfile_data (objfile, dwarf2_objfile_data_key);
+      dwarf2_per_objfile
+       = (struct dwarf2_per_objfile *) objfile_data (objfile,
+                                                     dwarf2_objfile_data_key);
 
       /* If this psymtab is constructed from a debug-only objfile, the
         has_section_at_zero flag will not necessarily be correct.  We
@@ -7436,8 +7610,9 @@ dwarf2_read_symtab (struct partial_symtab *self,
       if (objfile->separate_debug_objfile_backlink)
        {
          struct dwarf2_per_objfile *dpo_backlink
-           = objfile_data (objfile->separate_debug_objfile_backlink,
-                           dwarf2_objfile_data_key);
+           = ((struct dwarf2_per_objfile *)
+              objfile_data (objfile->separate_debug_objfile_backlink,
+                            dwarf2_objfile_data_key));
 
          dwarf2_per_objfile->has_section_at_zero
            = dpo_backlink->has_section_at_zero;
@@ -7466,7 +7641,7 @@ queue_comp_unit (struct dwarf2_per_cu_data *per_cu,
   struct dwarf2_queue_item *item;
 
   per_cu->queued = 1;
-  item = xmalloc (sizeof (*item));
+  item = XNEW (struct dwarf2_queue_item);
   item->per_cu = per_cu;
   item->pretend_language = pretend_language;
   item->next = NULL;
@@ -7544,9 +7719,11 @@ process_queue (void)
      may load a new CU, adding it to the end of the queue.  */
   for (item = dwarf2_queue; item != NULL; dwarf2_queue = item = next_item)
     {
-      if (dwarf2_per_objfile->using_index
-         ? !item->per_cu->v.quick->compunit_symtab
-         : (item->per_cu->v.psymtab && !item->per_cu->v.psymtab->readin))
+      if ((dwarf2_per_objfile->using_index
+          ? !item->per_cu->v.quick->compunit_symtab
+          : (item->per_cu->v.psymtab && !item->per_cu->v.psymtab->readin))
+         /* Skip dummy CUs.  */
+         && item->per_cu->cu != NULL)
        {
          struct dwarf2_per_cu_data *per_cu = item->per_cu;
          unsigned int debug_print_threshold;
@@ -7559,14 +7736,15 @@ process_queue (void)
 
              sprintf (buf, "TU %s at offset 0x%x",
                       hex_string (sig_type->signature),
-                      per_cu->offset.sect_off);
+                      to_underlying (per_cu->sect_off));
              /* There can be 100s of TUs.
                 Only print them in verbose mode.  */
              debug_print_threshold = 2;
            }
          else
            {
-             sprintf (buf, "CU at offset 0x%x", per_cu->offset.sect_off);
+             sprintf (buf, "CU at offset 0x%x",
+                      to_underlying (per_cu->sect_off));
              debug_print_threshold = 1;
            }
 
@@ -7655,7 +7833,7 @@ psymtab_to_symtab_1 (struct partial_symtab *pst)
         psymtab_to_symtab_1 (pst->dependencies[i]);
       }
 
-  per_cu = pst->read_symtab_private;
+  per_cu = (struct dwarf2_per_cu_data *) pst->read_symtab_private;
 
   if (per_cu == NULL)
     {
@@ -7674,9 +7852,9 @@ psymtab_to_symtab_1 (struct partial_symtab *pst)
 static hashval_t
 die_hash (const void *item)
 {
-  const struct die_info *die = item;
+  const struct die_info *die = (const struct die_info *) item;
 
-  return die->offset.sect_off;
+  return to_underlying (die->sect_off);
 }
 
 /* Trivial comparison function for die_info structures: two DIEs
@@ -7685,10 +7863,10 @@ die_hash (const void *item)
 static int
 die_eq (const void *item_lhs, const void *item_rhs)
 {
-  const struct die_info *die_lhs = item_lhs;
-  const struct die_info *die_rhs = item_rhs;
+  const struct die_info *die_lhs = (const struct die_info *) item_lhs;
+  const struct die_info *die_rhs = (const struct die_info *) item_rhs;
 
-  return die_lhs->offset.sect_off == die_rhs->offset.sect_off;
+  return die_lhs->sect_off == die_rhs->sect_off;
 }
 
 /* die_reader_func for load_full_comp_unit.
@@ -7703,7 +7881,7 @@ load_full_comp_unit_reader (const struct die_reader_specs *reader,
                            void *data)
 {
   struct dwarf2_cu *cu = reader->cu;
-  enum language *language_ptr = data;
+  enum language *language_ptr = (enum language *) data;
 
   gdb_assert (cu->die_hash == NULL);
   cu->die_hash =
@@ -7846,11 +8024,11 @@ fixup_go_packaging (struct dwarf2_cu *cu)
     {
       struct objfile *objfile = cu->objfile;
       const char *saved_package_name
-       = obstack_copy0 (&objfile->per_bfd->storage_obstack,
-                        package_name,
-                        strlen (package_name));
-      struct type *type = init_type (TYPE_CODE_MODULE, 0, 0,
-                                    saved_package_name, objfile);
+       = (const char *) obstack_copy0 (&objfile->per_bfd->storage_obstack,
+                                       package_name,
+                                       strlen (package_name));
+      struct type *type = init_type (objfile, TYPE_CODE_MODULE, 0,
+                                    saved_package_name);
       struct symbol *sym;
 
       TYPE_TAG_NAME (type) = TYPE_NAME (type);
@@ -7977,8 +8155,8 @@ compute_compunit_symtab_includes (struct dwarf2_per_cu_data *per_cu)
       /* Now we have a transitive closure of all the included symtabs.  */
       len = VEC_length (compunit_symtab_ptr, result_symtabs);
       cust->includes
-       = obstack_alloc (&dwarf2_per_objfile->objfile->objfile_obstack,
-                        (len + 1) * sizeof (struct symtab *));
+       = XOBNEWVEC (&dwarf2_per_objfile->objfile->objfile_obstack,
+                    struct compunit_symtab *, len + 1);
       for (ix = 0;
           VEC_iterate (compunit_symtab_ptr, result_symtabs, ix,
                        compunit_symtab_iter);
@@ -8080,7 +8258,7 @@ process_full_comp_unit (struct dwarf2_per_cu_data *per_cu,
         compilation is from a C file generated by language preprocessors, do
         not set the language if it was already deduced by start_subfile.  */
       if (!(cu->language == language_c
-           && COMPUNIT_FILETABS (cust)->language != language_c))
+           && COMPUNIT_FILETABS (cust)->language != language_unknown))
        COMPUNIT_FILETABS (cust)->language = cu->language;
 
       /* GCC-4.0 has started to support -fvar-tracking.  GCC-3.x still can
@@ -8213,14 +8391,10 @@ process_imported_unit_die (struct die_info *die, struct dwarf2_cu *cu)
   attr = dwarf2_attr (die, DW_AT_import, cu);
   if (attr != NULL)
     {
-      struct dwarf2_per_cu_data *per_cu;
-      struct symtab *imported_symtab;
-      sect_offset offset;
-      int is_dwz;
-
-      offset = dwarf2_get_ref_die_offset (attr);
-      is_dwz = (attr->form == DW_FORM_GNU_ref_alt || cu->per_cu->is_dwz);
-      per_cu = dwarf2_find_containing_comp_unit (offset, is_dwz, cu->objfile);
+      sect_offset sect_off = dwarf2_get_ref_die_offset (attr);
+      bool is_dwz = (attr->form == DW_FORM_GNU_ref_alt || cu->per_cu->is_dwz);
+      dwarf2_per_cu_data *per_cu
+       = dwarf2_find_containing_comp_unit (sect_off, is_dwz, cu->objfile);
 
       /* If necessary, add it to the queue and load its DIEs.  */
       if (maybe_queue_comp_unit (cu, per_cu, cu->language))
@@ -8236,7 +8410,7 @@ process_imported_unit_die (struct die_info *die, struct dwarf2_cu *cu)
 static void
 reset_die_in_process (void *arg)
 {
-  struct die_info *die = arg;
+  struct die_info *die = (struct die_info *) arg;
 
   die->in_process = 0;
 }
@@ -8274,6 +8448,7 @@ process_die (struct die_info *die, struct dwarf2_cu *cu)
     case DW_TAG_catch_block:
       read_lexical_block_scope (die, cu);
       break;
+    case DW_TAG_call_site:
     case DW_TAG_GNU_call_site:
       read_call_site_scope (die, cu);
       break;
@@ -8296,6 +8471,7 @@ process_die (struct die_info *die, struct dwarf2_cu *cu)
     case DW_TAG_pointer_type:
     case DW_TAG_ptr_to_member_type:
     case DW_TAG_reference_type:
+    case DW_TAG_rvalue_reference_type:
     case DW_TAG_string_type:
       break;
 
@@ -8406,22 +8582,10 @@ die_needs_namespace (struct die_info *die, struct dwarf2_cu *cu)
     }
 }
 
-/* Retrieve the last character from a mem_file.  */
-
-static void
-do_ui_file_peek_last (void *object, const char *buffer, long length)
-{
-  char *last_char_p = (char *) object;
-
-  if (length > 0)
-    *last_char_p = buffer[length - 1];
-}
-
 /* Compute the fully qualified name of DIE in CU.  If PHYSNAME is nonzero,
    compute the physname for the object, which include a method's:
-   - formal parameters (C++/Java),
+   - formal parameters (C++),
    - receiver type (Go),
-   - return type (Java).
 
    The term "physname" is a bit confusing.
    For C++, for example, it is the demangled name.
@@ -8442,8 +8606,13 @@ dwarf2_compute_name (const char *name,
   if (name == NULL)
     name = dwarf2_name (die, cu);
 
-  /* For Fortran GDB prefers DW_AT_*linkage_name if present but otherwise
-     compute it by typename_concat inside GDB.  */
+  /* For Fortran GDB prefers DW_AT_*linkage_name for the physname if present
+     but otherwise compute it by typename_concat inside GDB.
+     FIXME: Actually this is not really true, or at least not always true.
+     It's all very confusing.  SYMBOL_SET_NAMES doesn't try to demangle
+     Fortran names because there is no mangling standard.  So new_symbol_full
+     will set the demangled name to the result of dwarf2_full_name, and it is
+     the demangled name that GDB uses if it exists.  */
   if (cu->language == language_ada
       || (cu->language == language_fortran && physname))
     {
@@ -8452,40 +8621,40 @@ dwarf2_compute_name (const char *name,
         to be able to reference.  Ideally, we want the user to be able
         to reference this entity using either natural or linkage name,
         but we haven't started looking at this enhancement yet.  */
-      struct attribute *attr;
+      const char *linkage_name;
 
-      attr = dwarf2_attr (die, DW_AT_linkage_name, cu);
-      if (attr == NULL)
-       attr = dwarf2_attr (die, DW_AT_MIPS_linkage_name, cu);
-      if (attr && DW_STRING (attr))
-       return DW_STRING (attr);
+      linkage_name = dwarf2_string_attr (die, DW_AT_linkage_name, cu);
+      if (linkage_name == NULL)
+       linkage_name = dwarf2_string_attr (die, DW_AT_MIPS_linkage_name, cu);
+      if (linkage_name != NULL)
+       return linkage_name;
     }
 
   /* These are the only languages we know how to qualify names in.  */
   if (name != NULL
-      && (cu->language == language_cplus || cu->language == language_java
-         || cu->language == language_fortran || cu->language == language_d))
+      && (cu->language == language_cplus
+         || cu->language == language_fortran || cu->language == language_d
+         || cu->language == language_rust))
     {
       if (die_needs_namespace (die, cu))
        {
          long length;
          const char *prefix;
-         struct ui_file *buf;
-         char *intermediate_name;
          const char *canonical_name = NULL;
 
+         string_file buf;
+
          prefix = determine_prefix (die, cu);
-         buf = mem_fileopen ();
          if (*prefix != '\0')
            {
              char *prefixed_name = typename_concat (NULL, prefix, name,
                                                     physname, cu);
 
-             fputs_unfiltered (prefixed_name, buf);
+             buf.puts (prefixed_name);
              xfree (prefixed_name);
            }
          else
-           fputs_unfiltered (name, buf);
+           buf.puts (name);
 
          /* Template parameters may be specified in the DIE's DW_AT_name, or
             as children with DW_TAG_template_type_param or
@@ -8530,25 +8699,25 @@ dwarf2_compute_name (const char *name,
 
                  if (first)
                    {
-                     fputs_unfiltered ("<", buf);
+                     buf.puts ("<");
                      first = 0;
                    }
                  else
-                   fputs_unfiltered (", ", buf);
+                   buf.puts (", ");
 
                  attr = dwarf2_attr (child, DW_AT_type, cu);
                  if (attr == NULL)
                    {
                      complaint (&symfile_complaints,
                                 _("template parameter missing DW_AT_type"));
-                     fputs_unfiltered ("UNKNOWN_TYPE", buf);
+                     buf.puts ("UNKNOWN_TYPE");
                      continue;
                    }
                  type = die_type (child, cu);
 
                  if (child->tag == DW_TAG_template_type_param)
                    {
-                     c_print_type (type, "", buf, -1, 0, &type_print_raw_options);
+                     c_print_type (type, "", &buf, -1, 0, &type_print_raw_options);
                      continue;
                    }
 
@@ -8558,7 +8727,7 @@ dwarf2_compute_name (const char *name,
                      complaint (&symfile_complaints,
                                 _("template parameter missing "
                                   "DW_AT_const_value"));
-                     fputs_unfiltered ("UNKNOWN_VALUE", buf);
+                     buf.puts ("UNKNOWN_VALUE");
                      continue;
                    }
 
@@ -8569,7 +8738,7 @@ dwarf2_compute_name (const char *name,
                  if (TYPE_NOSIGN (type))
                    /* GDB prints characters as NUMBER 'CHAR'.  If that's
                       changed, this can use value_print instead.  */
-                   c_printchar (value, type, buf);
+                   c_printchar (value, type, &buf);
                  else
                    {
                      struct value_print_options opts;
@@ -8592,7 +8761,7 @@ dwarf2_compute_name (const char *name,
                         the radix.  */
                      get_formatted_print_options (&opts, 'd');
                      opts.raw = 1;
-                     value_print (v, buf, &opts);
+                     value_print (v, &buf, &opts);
                      release_value (v);
                      value_free (v);
                    }
@@ -8604,36 +8773,25 @@ dwarf2_compute_name (const char *name,
                {
                  /* Close the argument list, with a space if necessary
                     (nested templates).  */
-                 char last_char = '\0';
-                 ui_file_put (buf, do_ui_file_peek_last, &last_char);
-                 if (last_char == '>')
-                   fputs_unfiltered (" >", buf);
+                 if (!buf.empty () && buf.string ().back () == '>')
+                   buf.puts (" >");
                  else
-                   fputs_unfiltered (">", buf);
+                   buf.puts (">");
                }
            }
 
-         /* For Java and C++ methods, append formal parameter type
+         /* For C++ methods, append formal parameter type
             information, if PHYSNAME.  */
 
          if (physname && die->tag == DW_TAG_subprogram
-             && (cu->language == language_cplus
-                 || cu->language == language_java))
+             && cu->language == language_cplus)
            {
              struct type *type = read_type_die (die, cu);
 
-             c_type_print_args (type, buf, 1, cu->language,
+             c_type_print_args (type, &buf, 1, cu->language,
                                 &type_print_raw_options);
 
-             if (cu->language == language_java)
-               {
-                 /* For java, we must append the return type to method
-                    names.  */
-                 if (die->tag == DW_TAG_subprogram)
-                   java_print_type (TYPE_TARGET_TYPE (type), "", buf,
-                                    0, 0, &type_print_raw_options);
-               }
-             else if (cu->language == language_cplus)
+             if (cu->language == language_cplus)
                {
                  /* Assume that an artificial first parameter is
                     "this", but do not crash if it is not.  RealView
@@ -8645,29 +8803,27 @@ dwarf2_compute_name (const char *name,
                      && TYPE_CODE (TYPE_FIELD_TYPE (type, 0)) == TYPE_CODE_PTR
                      && TYPE_CONST (TYPE_TARGET_TYPE (TYPE_FIELD_TYPE (type,
                                                                        0))))
-                   fputs_unfiltered (" const", buf);
+                   buf.puts (" const");
                }
            }
 
-         intermediate_name = ui_file_xstrdup (buf, &length);
-         ui_file_delete (buf);
+         const std::string &intermediate_name = buf.string ();
 
          if (cu->language == language_cplus)
            canonical_name
-             = dwarf2_canonicalize_name (intermediate_name, cu,
+             = dwarf2_canonicalize_name (intermediate_name.c_str (), cu,
                                          &objfile->per_bfd->storage_obstack);
 
          /* If we only computed INTERMEDIATE_NAME, or if
             INTERMEDIATE_NAME is already canonical, then we need to
             copy it to the appropriate obstack.  */
-         if (canonical_name == NULL || canonical_name == intermediate_name)
-           name = obstack_copy0 (&objfile->per_bfd->storage_obstack,
-                                 intermediate_name,
-                                 strlen (intermediate_name));
+         if (canonical_name == NULL || canonical_name == intermediate_name.c_str ())
+           name = ((const char *)
+                   obstack_copy0 (&objfile->per_bfd->storage_obstack,
+                                  intermediate_name.c_str (),
+                                  intermediate_name.length ()));
          else
            name = canonical_name;
-
-         xfree (intermediate_name);
        }
     }
 
@@ -8680,7 +8836,7 @@ dwarf2_compute_name (const char *name,
    not have a name.  NAME may either be from a previous call to
    dwarf2_name or NULL.
 
-   The output string will be canonicalized (if C++/Java).  */
+   The output string will be canonicalized (if C++).  */
 
 static const char *
 dwarf2_full_name (const char *name, struct die_info *die, struct dwarf2_cu *cu)
@@ -8693,13 +8849,12 @@ dwarf2_full_name (const char *name, struct die_info *die, struct dwarf2_cu *cu)
    allocated on the objfile_objstack or NULL if the DIE does not have a
    name.
 
-   The output string will be canonicalized (if C++/Java).  */
+   The output string will be canonicalized (if C++).  */
 
 static const char *
 dwarf2_physname (const char *name, struct die_info *die, struct dwarf2_cu *cu)
 {
   struct objfile *objfile = cu->objfile;
-  struct attribute *attr;
   const char *retval, *mangled = NULL, *canon = NULL;
   struct cleanup *back_to;
   int need_copy = 1;
@@ -8711,18 +8866,22 @@ dwarf2_physname (const char *name, struct die_info *die, struct dwarf2_cu *cu)
 
   back_to = make_cleanup (null_cleanup, NULL);
 
-  attr = dwarf2_attr (die, DW_AT_linkage_name, cu);
-  if (!attr)
-    attr = dwarf2_attr (die, DW_AT_MIPS_linkage_name, cu);
+  mangled = dwarf2_string_attr (die, DW_AT_linkage_name, cu);
+  if (mangled == NULL)
+    mangled = dwarf2_string_attr (die, DW_AT_MIPS_linkage_name, cu);
+
+  /* rustc emits invalid values for DW_AT_linkage_name.  Ignore these.
+     See https://github.com/rust-lang/rust/issues/32925.  */
+  if (cu->language == language_rust && mangled != NULL
+      && strchr (mangled, '{') != NULL)
+    mangled = NULL;
 
   /* DW_AT_linkage_name is missing in some cases - depend on what GDB
      has computed.  */
-  if (attr && DW_STRING (attr))
+  if (mangled != NULL)
     {
       char *demangled;
 
-      mangled = DW_STRING (attr);
-
       /* Use DMGL_RET_DROP for C++ template functions to suppress their return
         type.  It is easier for GDB users to search for such functions as
         `name(params)' than `long name(params)'.  In such case the minimal
@@ -8742,10 +8901,7 @@ dwarf2_physname (const char *name, struct die_info *die, struct dwarf2_cu *cu)
       else
        {
          demangled = gdb_demangle (mangled,
-                                   (DMGL_PARAMS | DMGL_ANSI
-                                    | (cu->language == language_java
-                                       ? DMGL_JAVA | DMGL_RET_POSTFIX
-                                       : DMGL_RET_DROP)));
+                                   (DMGL_PARAMS | DMGL_ANSI | DMGL_RET_DROP));
        }
       if (demangled)
        {
@@ -8772,7 +8928,7 @@ dwarf2_physname (const char *name, struct die_info *die, struct dwarf2_cu *cu)
          complaint (&symfile_complaints,
                     _("Computed physname <%s> does not match demangled <%s> "
                       "(from linkage <%s>) - DIE at 0x%x [in module %s]"),
-                    physname, canon, mangled, die->offset.sect_off,
+                    physname, canon, mangled, to_underlying (die->sect_off),
                     objfile_name (objfile));
 
          /* Prefer DW_AT_linkage_name (in the CANON form) - when it
@@ -8791,8 +8947,9 @@ dwarf2_physname (const char *name, struct die_info *die, struct dwarf2_cu *cu)
     retval = canon;
 
   if (need_copy)
-    retval = obstack_copy0 (&objfile->per_bfd->storage_obstack,
-                           retval, strlen (retval));
+    retval = ((const char *)
+             obstack_copy0 (&objfile->per_bfd->storage_obstack,
+                            retval, strlen (retval)));
 
   do_cleanups (back_to);
   return retval;
@@ -8835,16 +8992,16 @@ read_namespace_alias (struct die_info *die, struct dwarf2_cu *cu)
        {
          complaint (&symfile_complaints,
                     _("DIE at 0x%x has too many recursively imported "
-                      "declarations"), d->offset.sect_off);
+                      "declarations"), to_underlying (d->sect_off));
          return 0;
        }
 
       if (attr != NULL)
        {
          struct type *type;
-         sect_offset offset = dwarf2_get_ref_die_offset (attr);
+         sect_offset sect_off = dwarf2_get_ref_die_offset (attr);
 
-         type = get_die_type_at_offset (offset, cu->per_cu);
+         type = get_die_type_at_offset (sect_off, cu->per_cu);
          if (type != NULL && TYPE_CODE (type) == TYPE_CODE_NAMESPACE)
            {
              /* This declaration is a global namespace alias.  Add
@@ -8858,6 +9015,24 @@ read_namespace_alias (struct die_info *die, struct dwarf2_cu *cu)
   return 0;
 }
 
+/* Return the using directives repository (global or local?) to use in the
+   current context for LANGUAGE.
+
+   For Ada, imported declarations can materialize renamings, which *may* be
+   global.  However it is impossible (for now?) in DWARF to distinguish
+   "external" imported declarations and "static" ones.  As all imported
+   declarations seem to be static in all other languages, make them all CU-wide
+   global only in Ada.  */
+
+static struct using_direct **
+using_directives (enum language language)
+{
+  if (language == language_ada && context_stack_depth == 0)
+    return &global_using_directives;
+  else
+    return &local_using_directives;
+}
+
 /* Read the import statement specified by the given die and record it.  */
 
 static void
@@ -8964,7 +9139,7 @@ read_import_statement (struct die_info *die, struct dwarf2_cu *cu)
            complaint (&symfile_complaints,
                       _("child DW_TAG_imported_declaration expected "
                         "- DIE at 0x%x [in module %s]"),
-                      child_die->offset.sect_off, objfile_name (objfile));
+                      to_underlying (child_die->sect_off), objfile_name (objfile));
            continue;
          }
 
@@ -8985,7 +9160,7 @@ read_import_statement (struct die_info *die, struct dwarf2_cu *cu)
            complaint (&symfile_complaints,
                       _("child DW_TAG_imported_declaration has unknown "
                         "imported name - DIE at 0x%x [in module %s]"),
-                      child_die->offset.sect_off, objfile_name (objfile));
+                      to_underlying (child_die->sect_off), objfile_name (objfile));
            continue;
          }
 
@@ -8994,28 +9169,18 @@ read_import_statement (struct die_info *die, struct dwarf2_cu *cu)
        process_die (child_die, cu);
       }
 
-  cp_add_using_directive (import_prefix,
-                          canonical_name,
-                          import_alias,
-                          imported_declaration,
-                         excludes,
-                         0,
-                          &objfile->objfile_obstack);
+  add_using_directive (using_directives (cu->language),
+                      import_prefix,
+                      canonical_name,
+                      import_alias,
+                      imported_declaration,
+                      excludes,
+                      0,
+                      &objfile->objfile_obstack);
 
   do_cleanups (cleanups);
 }
 
-/* Cleanup function for handle_DW_AT_stmt_list.  */
-
-static void
-free_cu_line_header (void *arg)
-{
-  struct dwarf2_cu *cu = arg;
-
-  free_line_header (cu->line_header);
-  cu->line_header = NULL;
-}
-
 /* Check for possibly missing DW_AT_comp_dir with relative .debug_line
    directory paths.  GCC SVN r127613 (new option -fdebug-prefix-map) fixed
    this, it was first present in GCC release 4.3.0.  */
@@ -9029,47 +9194,38 @@ producer_is_gcc_lt_4_3 (struct dwarf2_cu *cu)
   return cu->producer_is_gcc_lt_4_3;
 }
 
-static void
-find_file_and_directory (struct die_info *die, struct dwarf2_cu *cu,
-                        const char **name, const char **comp_dir)
+static file_and_directory
+find_file_and_directory (struct die_info *die, struct dwarf2_cu *cu)
 {
-  struct attribute *attr;
-
-  *name = NULL;
-  *comp_dir = NULL;
+  file_and_directory res;
 
   /* Find the filename.  Do not use dwarf2_name here, since the filename
      is not a source language identifier.  */
-  attr = dwarf2_attr (die, DW_AT_name, cu);
-  if (attr)
-    {
-      *name = DW_STRING (attr);
-    }
+  res.name = dwarf2_string_attr (die, DW_AT_name, cu);
+  res.comp_dir = dwarf2_string_attr (die, DW_AT_comp_dir, cu);
 
-  attr = dwarf2_attr (die, DW_AT_comp_dir, cu);
-  if (attr)
-    *comp_dir = DW_STRING (attr);
-  else if (producer_is_gcc_lt_4_3 (cu) && *name != NULL
-          && IS_ABSOLUTE_PATH (*name))
+  if (res.comp_dir == NULL
+      && producer_is_gcc_lt_4_3 (cu) && res.name != NULL
+      && IS_ABSOLUTE_PATH (res.name))
     {
-      char *d = ldirname (*name);
-
-      *comp_dir = d;
-      if (d != NULL)
-       make_cleanup (xfree, d);
+      res.comp_dir_storage = ldirname (res.name);
+      if (!res.comp_dir_storage.empty ())
+       res.comp_dir = res.comp_dir_storage.c_str ();
     }
-  if (*comp_dir != NULL)
+  if (res.comp_dir != NULL)
     {
       /* Irix 6.2 native cc prepends <machine>.: to the compilation
         directory, get rid of it.  */
-      char *cp = strchr (*comp_dir, ':');
+      const char *cp = strchr (res.comp_dir, ':');
 
-      if (cp && cp != *comp_dir && cp[-1] == '.' && cp[1] == '/')
-       *comp_dir = cp + 1;
+      if (cp && cp != res.comp_dir && cp[-1] == '.' && cp[1] == '/')
+       res.comp_dir = cp + 1;
     }
 
-  if (*name == NULL)
-    *name = "<unknown>";
+  if (res.name == NULL)
+    res.name = "<unknown>";
+
+  return res;
 }
 
 /* Handle DW_AT_stmt_list for a compilation unit.
@@ -9083,7 +9239,6 @@ handle_DW_AT_stmt_list (struct die_info *die, struct dwarf2_cu *cu,
 {
   struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct attribute *attr;
-  unsigned int line_offset;
   struct line_header line_header_local;
   hashval_t line_header_local_hash;
   unsigned u;
@@ -9096,7 +9251,7 @@ handle_DW_AT_stmt_list (struct die_info *die, struct dwarf2_cu *cu,
   if (attr == NULL)
     return;
 
-  line_offset = DW_UNSND (attr);
+  sect_offset line_offset = (sect_offset) DW_UNSND (attr);
 
   /* The line header hash table is only created if needed (it exists to
      prevent redundant reading of the line table for partial_units).
@@ -9116,7 +9271,7 @@ handle_DW_AT_stmt_list (struct die_info *die, struct dwarf2_cu *cu,
                                dummy_obstack_deallocate);
     }
 
-  line_header_local.offset.sect_off = line_offset;
+  line_header_local.sect_off = line_offset;
   line_header_local.offset_in_dwz = cu->per_cu->is_dwz;
   line_header_local_hash = line_header_hash (&line_header_local);
   if (dwarf2_per_objfile->line_header_hash != NULL)
@@ -9131,16 +9286,17 @@ handle_DW_AT_stmt_list (struct die_info *die, struct dwarf2_cu *cu,
       if (die->tag == DW_TAG_partial_unit && slot != NULL)
        {
          gdb_assert (*slot != NULL);
-         cu->line_header = *slot;
+         cu->line_header = (struct line_header *) *slot;
          return;
        }
     }
 
   /* dwarf_decode_line_header does not yet provide sufficient information.
      We always have to call also dwarf_decode_lines for it.  */
-  cu->line_header = dwarf_decode_line_header (line_offset, cu);
-  if (cu->line_header == NULL)
+  line_header_up lh = dwarf_decode_line_header (line_offset, cu);
+  if (lh == NULL)
     return;
+  cu->line_header = lh.get ();
 
   if (dwarf2_per_objfile->line_header_hash == NULL)
     slot = NULL;
@@ -9165,11 +9321,12 @@ handle_DW_AT_stmt_list (struct die_info *die, struct dwarf2_cu *cu,
         number information unit.  And if we're not using line_header_hash
         then this is what we want as well.  */
       gdb_assert (die->tag != DW_TAG_partial_unit);
-      make_cleanup (free_cu_line_header, cu);
     }
   decode_mapping = (die->tag != DW_TAG_partial_unit);
   dwarf_decode_lines (cu->line_header, comp_dir, cu, NULL, lowpc,
                      decode_mapping);
+
+  lh.release ();
 }
 
 /* Process DW_TAG_compile_unit or DW_TAG_partial_unit.  */
@@ -9179,14 +9336,10 @@ read_file_scope (struct die_info *die, struct dwarf2_cu *cu)
 {
   struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct gdbarch *gdbarch = get_objfile_arch (objfile);
-  struct cleanup *back_to = make_cleanup (null_cleanup, 0);
   CORE_ADDR lowpc = ((CORE_ADDR) -1);
   CORE_ADDR highpc = ((CORE_ADDR) 0);
   struct attribute *attr;
-  const char *name = NULL;
-  const char *comp_dir = NULL;
   struct die_info *child_die;
-  bfd *abfd = objfile->obfd;
   CORE_ADDR baseaddr;
 
   baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
@@ -9199,7 +9352,7 @@ read_file_scope (struct die_info *die, struct dwarf2_cu *cu)
     lowpc = highpc;
   lowpc = gdbarch_adjust_dwarf2_addr (gdbarch, lowpc + baseaddr);
 
-  find_file_and_directory (die, cu, &name, &comp_dir);
+  file_and_directory fnd = find_file_and_directory (die, cu);
 
   prepare_one_comp_unit (cu, die, cu->language);
 
@@ -9213,12 +9366,12 @@ read_file_scope (struct die_info *die, struct dwarf2_cu *cu)
   if (cu->producer && strstr (cu->producer, "GNU Go ") != NULL)
     set_cu_language (DW_LANG_Go, cu);
 
-  dwarf2_start_symtab (cu, name, comp_dir, lowpc);
+  dwarf2_start_symtab (cu, fnd.name, fnd.comp_dir, lowpc);
 
   /* Decode line number information if present.  We do this before
      processing child DIEs, so that the line header table is available
      for DW_AT_decl_file.  */
-  handle_DW_AT_stmt_list (die, cu, comp_dir, lowpc);
+  handle_DW_AT_stmt_list (die, cu, fnd.comp_dir, lowpc);
 
   /* Process all dies in compilation unit.  */
   if (die->child != NULL)
@@ -9235,12 +9388,14 @@ read_file_scope (struct die_info *die, struct dwarf2_cu *cu)
      refers to information in the line number info statement program
      header, so we can only read it if we've read the header
      successfully.  */
-  attr = dwarf2_attr (die, DW_AT_GNU_macros, cu);
+  attr = dwarf2_attr (die, DW_AT_macros, cu);
+  if (attr == NULL)
+    attr = dwarf2_attr (die, DW_AT_GNU_macros, cu);
   if (attr && cu->line_header)
     {
       if (dwarf2_attr (die, DW_AT_macro_info, cu))
        complaint (&symfile_complaints,
-                  _("CU refers to both DW_AT_GNU_macros and DW_AT_macro_info"));
+                  _("CU refers to both DW_AT_macros and DW_AT_macro_info"));
 
       dwarf_decode_macros (cu, DW_UNSND (attr), 1);
     }
@@ -9254,8 +9409,6 @@ read_file_scope (struct die_info *die, struct dwarf2_cu *cu)
          dwarf_decode_macros (cu, macro_offset, 0);
        }
     }
-
-  do_cleanups (back_to);
 }
 
 /* TU version of handle_DW_AT_stmt_list for read_type_unit_scope.
@@ -9267,13 +9420,11 @@ read_file_scope (struct die_info *die, struct dwarf2_cu *cu)
 static void
 setup_type_unit_groups (struct die_info *die, struct dwarf2_cu *cu)
 {
-  struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct dwarf2_per_cu_data *per_cu = cu->per_cu;
   struct type_unit_group *tu_group;
   int first_time;
-  struct line_header *lh;
   struct attribute *attr;
-  unsigned int i, line_offset;
+  unsigned int i;
   struct signatured_type *sig_type;
 
   gdb_assert (per_cu->is_debug_types);
@@ -9295,10 +9446,10 @@ setup_type_unit_groups (struct die_info *die, struct dwarf2_cu *cu)
 
   /* We have to handle the case of both a missing DW_AT_stmt_list or bad
      debug info.  */
-  lh = NULL;
+  line_header_up lh;
   if (attr != NULL)
     {
-      line_offset = DW_UNSND (attr);
+      sect_offset line_offset = (sect_offset) DW_UNSND (attr);
       lh = dwarf_decode_line_header (line_offset, cu);
     }
   if (lh == NULL)
@@ -9313,24 +9464,25 @@ setup_type_unit_groups (struct die_info *die, struct dwarf2_cu *cu)
       return;
     }
 
-  cu->line_header = lh;
-  make_cleanup (free_cu_line_header, cu);
+  cu->line_header = lh.get ();
 
   if (first_time)
     {
       struct compunit_symtab *cust = dwarf2_start_symtab (cu, "", NULL, 0);
 
-      tu_group->num_symtabs = lh->num_file_names;
-      tu_group->symtabs = XNEWVEC (struct symtab *, lh->num_file_names);
+      /* Note: We don't assign tu_group->compunit_symtab yet because we're
+        still initializing it, and our caller (a few levels up)
+        process_full_type_unit still needs to know if this is the first
+        time.  */
 
-      for (i = 0; i < lh->num_file_names; ++i)
+      tu_group->num_symtabs = lh->file_names.size ();
+      tu_group->symtabs = XNEWVEC (struct symtab *, lh->file_names.size ());
+
+      for (i = 0; i < lh->file_names.size (); ++i)
        {
-         const char *dir = NULL;
-         struct file_entry *fe = &lh->file_names[i];
+         file_entry &fe = lh->file_names[i];
 
-         if (fe->dir_index && lh->include_dirs != NULL)
-           dir = lh->include_dirs[fe->dir_index - 1];
-         dwarf2_start_subfile (fe->name, dir);
+         dwarf2_start_subfile (fe.name, fe.include_dir (lh.get ()));
 
          if (current_subfile->symtab == NULL)
            {
@@ -9342,15 +9494,15 @@ setup_type_unit_groups (struct die_info *die, struct dwarf2_cu *cu)
                = allocate_symtab (cust, current_subfile->name);
            }
 
-         fe->symtab = current_subfile->symtab;
-         tu_group->symtabs[i] = fe->symtab;
+         fe.symtab = current_subfile->symtab;
+         tu_group->symtabs[i] = fe.symtab;
        }
     }
   else
     {
       restart_symtab (tu_group->compunit_symtab, "", 0);
 
-      for (i = 0; i < lh->num_file_names; ++i)
+      for (i = 0; i < lh->file_names.size (); ++i)
        {
          struct file_entry *fe = &lh->file_names[i];
 
@@ -9358,6 +9510,8 @@ setup_type_unit_groups (struct die_info *die, struct dwarf2_cu *cu)
        }
     }
 
+  lh.release ();
+
   /* The main symtab is allocated last.  Type units don't have DW_AT_name
      so they don't have a "real" (so to speak) symtab anyway.
      There is later code that will assign the main symtab to all symbols
@@ -9405,7 +9559,7 @@ read_type_unit_scope (struct die_info *die, struct dwarf2_cu *cu)
 static hashval_t
 hash_dwo_file (const void *item)
 {
-  const struct dwo_file *dwo_file = item;
+  const struct dwo_file *dwo_file = (const struct dwo_file *) item;
   hashval_t hash;
 
   hash = htab_hash_string (dwo_file->dwo_name);
@@ -9417,8 +9571,8 @@ hash_dwo_file (const void *item)
 static int
 eq_dwo_file (const void *item_lhs, const void *item_rhs)
 {
-  const struct dwo_file *lhs = item_lhs;
-  const struct dwo_file *rhs = item_rhs;
+  const struct dwo_file *lhs = (const struct dwo_file *) item_lhs;
+  const struct dwo_file *rhs = (const struct dwo_file *) item_rhs;
 
   if (strcmp (lhs->dwo_name, rhs->dwo_name) != 0)
     return 0;
@@ -9465,7 +9619,7 @@ lookup_dwo_file_slot (const char *dwo_name, const char *comp_dir)
 static hashval_t
 hash_dwo_unit (const void *item)
 {
-  const struct dwo_unit *dwo_unit = item;
+  const struct dwo_unit *dwo_unit = (const struct dwo_unit *) item;
 
   /* This drops the top 32 bits of the id, but is ok for a hash.  */
   return dwo_unit->signature;
@@ -9474,8 +9628,8 @@ hash_dwo_unit (const void *item)
 static int
 eq_dwo_unit (const void *item_lhs, const void *item_rhs)
 {
-  const struct dwo_unit *lhs = item_lhs;
-  const struct dwo_unit *rhs = item_rhs;
+  const struct dwo_unit *lhs = (const struct dwo_unit *) item_lhs;
+  const struct dwo_unit *rhs = (const struct dwo_unit *) item_rhs;
 
   /* The signature is assumed to be unique within the DWO file.
      So while object file CU dwo_id's always have the value zero,
@@ -9519,10 +9673,9 @@ create_dwo_cu_reader (const struct die_reader_specs *reader,
                      void *datap)
 {
   struct dwarf2_cu *cu = reader->cu;
-  struct objfile *objfile = dwarf2_per_objfile->objfile;
-  sect_offset offset = cu->per_cu->offset;
+  sect_offset sect_off = cu->per_cu->sect_off;
   struct dwarf2_section_info *section = cu->per_cu->section;
-  struct create_dwo_cu_data *data = datap;
+  struct create_dwo_cu_data *data = (struct create_dwo_cu_data *) datap;
   struct dwo_file *dwo_file = data->dwo_file;
   struct dwo_unit *dwo_unit = &data->dwo_unit;
   struct attribute *attr;
@@ -9533,19 +9686,20 @@ create_dwo_cu_reader (const struct die_reader_specs *reader,
       complaint (&symfile_complaints,
                 _("Dwarf Error: debug entry at offset 0x%x is missing"
                   " its dwo_id [in module %s]"),
-                offset.sect_off, dwo_file->dwo_name);
+                to_underlying (sect_off), dwo_file->dwo_name);
       return;
     }
 
   dwo_unit->dwo_file = dwo_file;
   dwo_unit->signature = DW_UNSND (attr);
   dwo_unit->section = section;
-  dwo_unit->offset = offset;
+  dwo_unit->sect_off = sect_off;
   dwo_unit->length = cu->per_cu->length;
 
   if (dwarf_read_debug)
     fprintf_unfiltered (gdb_stdlog, "  offset 0x%x, dwo_id %s\n",
-                       offset.sect_off, hex_string (dwo_unit->signature));
+                       to_underlying (sect_off),
+                       hex_string (dwo_unit->signature));
 }
 
 /* Create the dwo_unit for the lone CU in DWO_FILE.
@@ -9556,8 +9710,6 @@ create_dwo_cu (struct dwo_file *dwo_file)
 {
   struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct dwarf2_section_info *section = &dwo_file->sections.info;
-  bfd *abfd;
-  htab_t cu_htab;
   const gdb_byte *info_ptr, *end_ptr;
   struct create_dwo_cu_data create_dwo_cu_data;
   struct dwo_unit *dwo_unit;
@@ -9568,10 +9720,6 @@ create_dwo_cu (struct dwo_file *dwo_file)
   if (info_ptr == NULL)
     return NULL;
 
-  /* We can't set abfd until now because the section may be empty or
-     not present, in which case section->asection will be NULL.  */
-  abfd = get_section_bfd_owner (section);
-
   if (dwarf_read_debug)
     {
       fprintf_unfiltered (gdb_stdlog, "Reading %s for %s:\n",
@@ -9592,7 +9740,7 @@ create_dwo_cu (struct dwo_file *dwo_file)
       memset (&per_cu, 0, sizeof (per_cu));
       per_cu.objfile = objfile;
       per_cu.is_debug_types = 0;
-      per_cu.offset.sect_off = info_ptr - section->buffer;
+      per_cu.sect_off = sect_offset (info_ptr - section->buffer);
       per_cu.section = section;
 
       init_cutu_and_read_dies_no_follow (&per_cu, dwo_file,
@@ -9928,58 +10076,58 @@ locate_v1_virtual_dwo_sections (asection *sectp,
   if (section_is_p (sectp->name, &names->abbrev_dwo))
     {
       /* There can be only one.  */
-      if (sections->abbrev.s.asection != NULL)
+      if (sections->abbrev.s.section != NULL)
        return 0;
-      sections->abbrev.s.asection = sectp;
+      sections->abbrev.s.section = sectp;
       sections->abbrev.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->info_dwo)
           || section_is_p (sectp->name, &names->types_dwo))
     {
       /* There can be only one.  */
-      if (sections->info_or_types.s.asection != NULL)
+      if (sections->info_or_types.s.section != NULL)
        return 0;
-      sections->info_or_types.s.asection = sectp;
+      sections->info_or_types.s.section = sectp;
       sections->info_or_types.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->line_dwo))
     {
       /* There can be only one.  */
-      if (sections->line.s.asection != NULL)
+      if (sections->line.s.section != NULL)
        return 0;
-      sections->line.s.asection = sectp;
+      sections->line.s.section = sectp;
       sections->line.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->loc_dwo))
     {
       /* There can be only one.  */
-      if (sections->loc.s.asection != NULL)
+      if (sections->loc.s.section != NULL)
        return 0;
-      sections->loc.s.asection = sectp;
+      sections->loc.s.section = sectp;
       sections->loc.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->macinfo_dwo))
     {
       /* There can be only one.  */
-      if (sections->macinfo.s.asection != NULL)
+      if (sections->macinfo.s.section != NULL)
        return 0;
-      sections->macinfo.s.asection = sectp;
+      sections->macinfo.s.section = sectp;
       sections->macinfo.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->macro_dwo))
     {
       /* There can be only one.  */
-      if (sections->macro.s.asection != NULL)
+      if (sections->macro.s.section != NULL)
        return 0;
-      sections->macro.s.asection = sectp;
+      sections->macro.s.section = sectp;
       sections->macro.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->str_offsets_dwo))
     {
       /* There can be only one.  */
-      if (sections->str_offsets.s.asection != NULL)
+      if (sections->str_offsets.s.section != NULL)
        return 0;
-      sections->str_offsets.s.asection = sectp;
+      sections->str_offsets.s.section = sectp;
       sections->str_offsets.size = bfd_get_section_size (sectp);
     }
   else
@@ -10012,7 +10160,6 @@ create_dwo_unit_in_dwp_v1 (struct dwp_file *dwp_file,
   struct virtual_v1_dwo_sections sections;
   void **dwo_file_slot;
   char *virtual_dwo_name;
-  struct dwarf2_section_info *cutu;
   struct cleanup *cleanups;
   int i;
 
@@ -10110,9 +10257,10 @@ create_dwo_unit_in_dwp_v1 (struct dwp_file *dwp_file,
                              virtual_dwo_name);
        }
       dwo_file = OBSTACK_ZALLOC (&objfile->objfile_obstack, struct dwo_file);
-      dwo_file->dwo_name = obstack_copy0 (&objfile->objfile_obstack,
-                                         virtual_dwo_name,
-                                         strlen (virtual_dwo_name));
+      dwo_file->dwo_name
+       = (const char *) obstack_copy0 (&objfile->objfile_obstack,
+                                       virtual_dwo_name,
+                                       strlen (virtual_dwo_name));
       dwo_file->comp_dir = comp_dir;
       dwo_file->sections.abbrev = sections.abbrev;
       dwo_file->sections.line = sections.line;
@@ -10138,15 +10286,15 @@ create_dwo_unit_in_dwp_v1 (struct dwp_file *dwp_file,
          fprintf_unfiltered (gdb_stdlog, "Using existing virtual DWO: %s\n",
                              virtual_dwo_name);
        }
-      dwo_file = *dwo_file_slot;
+      dwo_file = (struct dwo_file *) *dwo_file_slot;
     }
   do_cleanups (cleanups);
 
   dwo_unit = OBSTACK_ZALLOC (&objfile->objfile_obstack, struct dwo_unit);
   dwo_unit->dwo_file = dwo_file;
   dwo_unit->signature = signature;
-  dwo_unit->section = obstack_alloc (&objfile->objfile_obstack,
-                                    sizeof (struct dwarf2_section_info));
+  dwo_unit->section =
+    XOBNEW (&objfile->objfile_obstack, struct dwarf2_section_info);
   *dwo_unit->section = sections.info_or_types;
   /* dwo_unit->{offset,length,type_offset_in_tu} are set later.  */
 
@@ -10217,7 +10365,6 @@ create_dwo_unit_in_dwp_v2 (struct dwp_file *dwp_file,
   struct virtual_v2_dwo_sections sections;
   void **dwo_file_slot;
   char *virtual_dwo_name;
-  struct dwarf2_section_info *cutu;
   struct cleanup *cleanups;
   int i;
 
@@ -10311,9 +10458,10 @@ create_dwo_unit_in_dwp_v2 (struct dwp_file *dwp_file,
                              virtual_dwo_name);
        }
       dwo_file = OBSTACK_ZALLOC (&objfile->objfile_obstack, struct dwo_file);
-      dwo_file->dwo_name = obstack_copy0 (&objfile->objfile_obstack,
-                                         virtual_dwo_name,
-                                         strlen (virtual_dwo_name));
+      dwo_file->dwo_name
+       = (const char *) obstack_copy0 (&objfile->objfile_obstack,
+                                       virtual_dwo_name,
+                                       strlen (virtual_dwo_name));
       dwo_file->comp_dir = comp_dir;
       dwo_file->sections.abbrev =
        create_dwp_v2_section (&dwp_file->sections.abbrev,
@@ -10352,15 +10500,15 @@ create_dwo_unit_in_dwp_v2 (struct dwp_file *dwp_file,
          fprintf_unfiltered (gdb_stdlog, "Using existing virtual DWO: %s\n",
                              virtual_dwo_name);
        }
-      dwo_file = *dwo_file_slot;
+      dwo_file = (struct dwo_file *) *dwo_file_slot;
     }
   do_cleanups (cleanups);
 
   dwo_unit = OBSTACK_ZALLOC (&objfile->objfile_obstack, struct dwo_unit);
   dwo_unit->dwo_file = dwo_file;
   dwo_unit->signature = signature;
-  dwo_unit->section = obstack_alloc (&objfile->objfile_obstack,
-                                    sizeof (struct dwarf2_section_info));
+  dwo_unit->section =
+    XOBNEW (&objfile->objfile_obstack, struct dwarf2_section_info);
   *dwo_unit->section = create_dwp_v2_section (is_debug_types
                                              ? &dwp_file->sections.types
                                              : &dwp_file->sections.info,
@@ -10386,7 +10534,7 @@ lookup_dwo_unit_in_dwp (struct dwp_file *dwp_file, const char *comp_dir,
   uint32_t hash2 = ((signature >> 32) & mask) | 1;
   unsigned int i;
   void **slot;
-  struct dwo_unit find_dwo_cu, *dwo_cu;
+  struct dwo_unit find_dwo_cu;
 
   memset (&find_dwo_cu, 0, sizeof (find_dwo_cu));
   find_dwo_cu.signature = signature;
@@ -10396,7 +10544,7 @@ lookup_dwo_unit_in_dwp (struct dwp_file *dwp_file, const char *comp_dir,
                         &find_dwo_cu, INSERT);
 
   if (*slot != NULL)
-    return *slot;
+    return (struct dwo_unit *) *slot;
 
   /* Use a for loop so that we don't loop forever on bad debug info.  */
   for (i = 0; i < dwp_htab->nr_slots; ++i)
@@ -10423,7 +10571,7 @@ lookup_dwo_unit_in_dwp (struct dwp_file *dwp_file, const char *comp_dir,
                                                 comp_dir, signature,
                                                 is_debug_types);
            }
-         return *slot;
+         return (struct dwo_unit *) *slot;
        }
       if (signature_in_table == 0)
        return NULL;
@@ -10447,10 +10595,9 @@ lookup_dwo_unit_in_dwp (struct dwp_file *dwp_file, const char *comp_dir,
    If unable to find/open the file, return NULL.
    NOTE: This function is derived from symfile_bfd_open.  */
 
-static bfd *
+static gdb_bfd_ref_ptr
 try_open_dwop_file (const char *file_name, int is_dwp, int search_cwd)
 {
-  bfd *sym_bfd;
   int desc, flags;
   char *absolute_name;
   /* Blech.  OPF_TRY_CWD_FIRST also disables searching the path list if
@@ -10463,7 +10610,7 @@ try_open_dwop_file (const char *file_name, int is_dwp, int search_cwd)
     {
       if (*debug_file_directory != '\0')
        search_path = concat (".", dirname_separator_string,
-                             debug_file_directory, NULL);
+                             debug_file_directory, (char *) NULL);
       else
        search_path = xstrdup (".");
     }
@@ -10479,23 +10626,20 @@ try_open_dwop_file (const char *file_name, int is_dwp, int search_cwd)
   if (desc < 0)
     return NULL;
 
-  sym_bfd = gdb_bfd_open (absolute_name, gnutarget, desc);
+  gdb_bfd_ref_ptr sym_bfd (gdb_bfd_open (absolute_name, gnutarget, desc));
   xfree (absolute_name);
   if (sym_bfd == NULL)
     return NULL;
-  bfd_set_cacheable (sym_bfd, 1);
+  bfd_set_cacheable (sym_bfd.get (), 1);
 
-  if (!bfd_check_format (sym_bfd, bfd_object))
-    {
-      gdb_bfd_unref (sym_bfd); /* This also closes desc.  */
-      return NULL;
-    }
+  if (!bfd_check_format (sym_bfd.get (), bfd_object))
+    return NULL;
 
   /* Success.  Record the bfd as having been included by the objfile's bfd.
      This is important because things like demangled_names_hash lives in the
      objfile's per_bfd space and may have references to things like symbol
      names that live in the DWO/DWP file's per_bfd space.  PR 16426.  */
-  gdb_bfd_record_inclusion (dwarf2_per_objfile->objfile->obfd, sym_bfd);
+  gdb_bfd_record_inclusion (dwarf2_per_objfile->objfile->obfd, sym_bfd.get ());
 
   return sym_bfd;
 }
@@ -10507,11 +10651,9 @@ try_open_dwop_file (const char *file_name, int is_dwp, int search_cwd)
    Upon success, the canonicalized path of the file is stored in the bfd,
    same as symfile_bfd_open.  */
 
-static bfd *
+static gdb_bfd_ref_ptr
 open_dwo_file (const char *file_name, const char *comp_dir)
 {
-  bfd *abfd;
-
   if (IS_ABSOLUTE_PATH (file_name))
     return try_open_dwop_file (file_name, 0 /*is_dwp*/, 0 /*search_cwd*/);
 
@@ -10519,11 +10661,13 @@ open_dwo_file (const char *file_name, const char *comp_dir)
 
   if (comp_dir != NULL)
     {
-      char *path_to_try = concat (comp_dir, SLASH_STRING, file_name, NULL);
+      char *path_to_try = concat (comp_dir, SLASH_STRING,
+                                 file_name, (char *) NULL);
 
       /* NOTE: If comp_dir is a relative path, this will also try the
         search path, which seems useful.  */
-      abfd = try_open_dwop_file (path_to_try, 0 /*is_dwp*/, 1 /*search_cwd*/);
+      gdb_bfd_ref_ptr abfd (try_open_dwop_file (path_to_try, 0 /*is_dwp*/,
+                                               1 /*search_cwd*/));
       xfree (path_to_try);
       if (abfd != NULL)
        return abfd;
@@ -10544,47 +10688,47 @@ open_dwo_file (const char *file_name, const char *comp_dir)
 static void
 dwarf2_locate_dwo_sections (bfd *abfd, asection *sectp, void *dwo_sections_ptr)
 {
-  struct dwo_sections *dwo_sections = dwo_sections_ptr;
+  struct dwo_sections *dwo_sections = (struct dwo_sections *) dwo_sections_ptr;
   const struct dwop_section_names *names = &dwop_section_names;
 
   if (section_is_p (sectp->name, &names->abbrev_dwo))
     {
-      dwo_sections->abbrev.s.asection = sectp;
+      dwo_sections->abbrev.s.section = sectp;
       dwo_sections->abbrev.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->info_dwo))
     {
-      dwo_sections->info.s.asection = sectp;
+      dwo_sections->info.s.section = sectp;
       dwo_sections->info.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->line_dwo))
     {
-      dwo_sections->line.s.asection = sectp;
+      dwo_sections->line.s.section = sectp;
       dwo_sections->line.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->loc_dwo))
     {
-      dwo_sections->loc.s.asection = sectp;
+      dwo_sections->loc.s.section = sectp;
       dwo_sections->loc.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->macinfo_dwo))
     {
-      dwo_sections->macinfo.s.asection = sectp;
+      dwo_sections->macinfo.s.section = sectp;
       dwo_sections->macinfo.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->macro_dwo))
     {
-      dwo_sections->macro.s.asection = sectp;
+      dwo_sections->macro.s.section = sectp;
       dwo_sections->macro.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->str_dwo))
     {
-      dwo_sections->str.s.asection = sectp;
+      dwo_sections->str.s.section = sectp;
       dwo_sections->str.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->str_offsets_dwo))
     {
-      dwo_sections->str_offsets.s.asection = sectp;
+      dwo_sections->str_offsets.s.section = sectp;
       dwo_sections->str_offsets.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->types_dwo))
@@ -10592,7 +10736,7 @@ dwarf2_locate_dwo_sections (bfd *abfd, asection *sectp, void *dwo_sections_ptr)
       struct dwarf2_section_info type_section;
 
       memset (&type_section, 0, sizeof (type_section));
-      type_section.s.asection = sectp;
+      type_section.s.section = sectp;
       type_section.size = bfd_get_section_size (sectp);
       VEC_safe_push (dwarf2_section_info_def, dwo_sections->types,
                     &type_section);
@@ -10609,10 +10753,9 @@ open_and_init_dwo_file (struct dwarf2_per_cu_data *per_cu,
 {
   struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct dwo_file *dwo_file;
-  bfd *dbfd;
   struct cleanup *cleanups;
 
-  dbfd = open_dwo_file (dwo_name, comp_dir);
+  gdb_bfd_ref_ptr dbfd (open_dwo_file (dwo_name, comp_dir));
   if (dbfd == NULL)
     {
       if (dwarf_read_debug)
@@ -10622,16 +10765,17 @@ open_and_init_dwo_file (struct dwarf2_per_cu_data *per_cu,
   dwo_file = OBSTACK_ZALLOC (&objfile->objfile_obstack, struct dwo_file);
   dwo_file->dwo_name = dwo_name;
   dwo_file->comp_dir = comp_dir;
-  dwo_file->dbfd = dbfd;
+  dwo_file->dbfd = dbfd.release ();
 
   cleanups = make_cleanup (free_dwo_file_cleanup, dwo_file);
 
-  bfd_map_over_sections (dbfd, dwarf2_locate_dwo_sections, &dwo_file->sections);
+  bfd_map_over_sections (dwo_file->dbfd, dwarf2_locate_dwo_sections,
+                        &dwo_file->sections);
 
   dwo_file->cu = create_dwo_cu (dwo_file);
 
-  dwo_file->tus = create_debug_types_hash_table (dwo_file,
-                                                dwo_file->sections.types);
+  create_debug_types_hash_table (dwo_file, dwo_file->sections.types,
+                                dwo_file->tus);
 
   discard_cleanups (cleanups);
 
@@ -10649,7 +10793,7 @@ static void
 dwarf2_locate_common_dwp_sections (bfd *abfd, asection *sectp,
                                   void *dwp_file_ptr)
 {
-  struct dwp_file *dwp_file = dwp_file_ptr;
+  struct dwp_file *dwp_file = (struct dwp_file *) dwp_file_ptr;
   const struct dwop_section_names *names = &dwop_section_names;
   unsigned int elf_section_nr = elf_section_data (sectp)->this_idx;
 
@@ -10661,17 +10805,17 @@ dwarf2_locate_common_dwp_sections (bfd *abfd, asection *sectp,
   /* Look for specific sections that we need.  */
   if (section_is_p (sectp->name, &names->str_dwo))
     {
-      dwp_file->sections.str.s.asection = sectp;
+      dwp_file->sections.str.s.section = sectp;
       dwp_file->sections.str.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->cu_index))
     {
-      dwp_file->sections.cu_index.s.asection = sectp;
+      dwp_file->sections.cu_index.s.section = sectp;
       dwp_file->sections.cu_index.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->tu_index))
     {
-      dwp_file->sections.tu_index.s.asection = sectp;
+      dwp_file->sections.tu_index.s.section = sectp;
       dwp_file->sections.tu_index.size = bfd_get_section_size (sectp);
     }
 }
@@ -10684,7 +10828,7 @@ dwarf2_locate_common_dwp_sections (bfd *abfd, asection *sectp,
 static void
 dwarf2_locate_v2_dwp_sections (bfd *abfd, asection *sectp, void *dwp_file_ptr)
 {
-  struct dwp_file *dwp_file = dwp_file_ptr;
+  struct dwp_file *dwp_file = (struct dwp_file *) dwp_file_ptr;
   const struct dwop_section_names *names = &dwop_section_names;
   unsigned int elf_section_nr = elf_section_data (sectp)->this_idx;
 
@@ -10696,42 +10840,42 @@ dwarf2_locate_v2_dwp_sections (bfd *abfd, asection *sectp, void *dwp_file_ptr)
   /* Look for specific sections that we need.  */
   if (section_is_p (sectp->name, &names->abbrev_dwo))
     {
-      dwp_file->sections.abbrev.s.asection = sectp;
+      dwp_file->sections.abbrev.s.section = sectp;
       dwp_file->sections.abbrev.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->info_dwo))
     {
-      dwp_file->sections.info.s.asection = sectp;
+      dwp_file->sections.info.s.section = sectp;
       dwp_file->sections.info.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->line_dwo))
     {
-      dwp_file->sections.line.s.asection = sectp;
+      dwp_file->sections.line.s.section = sectp;
       dwp_file->sections.line.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->loc_dwo))
     {
-      dwp_file->sections.loc.s.asection = sectp;
+      dwp_file->sections.loc.s.section = sectp;
       dwp_file->sections.loc.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->macinfo_dwo))
     {
-      dwp_file->sections.macinfo.s.asection = sectp;
+      dwp_file->sections.macinfo.s.section = sectp;
       dwp_file->sections.macinfo.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->macro_dwo))
     {
-      dwp_file->sections.macro.s.asection = sectp;
+      dwp_file->sections.macro.s.section = sectp;
       dwp_file->sections.macro.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->str_offsets_dwo))
     {
-      dwp_file->sections.str_offsets.s.asection = sectp;
+      dwp_file->sections.str_offsets.s.section = sectp;
       dwp_file->sections.str_offsets.size = bfd_get_section_size (sectp);
     }
   else if (section_is_p (sectp->name, &names->types_dwo))
     {
-      dwp_file->sections.types.s.asection = sectp;
+      dwp_file->sections.types.s.section = sectp;
       dwp_file->sections.types.size = bfd_get_section_size (sectp);
     }
 }
@@ -10741,7 +10885,7 @@ dwarf2_locate_v2_dwp_sections (bfd *abfd, asection *sectp, void *dwp_file_ptr)
 static hashval_t
 hash_dwp_loaded_cutus (const void *item)
 {
-  const struct dwo_unit *dwo_unit = item;
+  const struct dwo_unit *dwo_unit = (const struct dwo_unit *) item;
 
   /* This drops the top 32 bits of the signature, but is ok for a hash.  */
   return dwo_unit->signature;
@@ -10752,8 +10896,8 @@ hash_dwp_loaded_cutus (const void *item)
 static int
 eq_dwp_loaded_cutus (const void *a, const void *b)
 {
-  const struct dwo_unit *dua = a;
-  const struct dwo_unit *dub = b;
+  const struct dwo_unit *dua = (const struct dwo_unit *) a;
+  const struct dwo_unit *dub = (const struct dwo_unit *) b;
 
   return dua->signature == dub->signature;
 }
@@ -10778,12 +10922,11 @@ allocate_dwp_loaded_cutus_table (struct objfile *objfile)
    Upon success, the canonicalized path of the file is stored in the bfd,
    same as symfile_bfd_open.  */
 
-static bfd *
+static gdb_bfd_ref_ptr
 open_dwp_file (const char *file_name)
 {
-  bfd *abfd;
-
-  abfd = try_open_dwop_file (file_name, 1 /*is_dwp*/, 1 /*search_cwd*/);
+  gdb_bfd_ref_ptr abfd (try_open_dwop_file (file_name, 1 /*is_dwp*/,
+                                           1 /*search_cwd*/));
   if (abfd != NULL)
     return abfd;
 
@@ -10816,44 +10959,53 @@ open_and_init_dwp_file (void)
 {
   struct objfile *objfile = dwarf2_per_objfile->objfile;
   struct dwp_file *dwp_file;
-  char *dwp_name;
-  bfd *dbfd;
-  struct cleanup *cleanups;
 
   /* Try to find first .dwp for the binary file before any symbolic links
      resolving.  */
-  dwp_name = xstrprintf ("%s.dwp", objfile->original_name);
-  cleanups = make_cleanup (xfree, dwp_name);
 
-  dbfd = open_dwp_file (dwp_name);
+  /* If the objfile is a debug file, find the name of the real binary
+     file and get the name of dwp file from there.  */
+  std::string dwp_name;
+  if (objfile->separate_debug_objfile_backlink != NULL)
+    {
+      struct objfile *backlink = objfile->separate_debug_objfile_backlink;
+      const char *backlink_basename = lbasename (backlink->original_name);
+
+      dwp_name = ldirname (objfile->original_name) + SLASH_STRING + backlink_basename;
+    }
+  else
+    dwp_name = objfile->original_name;
+
+  dwp_name += ".dwp";
+
+  gdb_bfd_ref_ptr dbfd (open_dwp_file (dwp_name.c_str ()));
   if (dbfd == NULL
       && strcmp (objfile->original_name, objfile_name (objfile)) != 0)
     {
       /* Try to find .dwp for the binary file after gdb_realpath resolving.  */
-      dwp_name = xstrprintf ("%s.dwp", objfile_name (objfile));
-      make_cleanup (xfree, dwp_name);
-      dbfd = open_dwp_file (dwp_name);
+      dwp_name = objfile_name (objfile);
+      dwp_name += ".dwp";
+      dbfd = open_dwp_file (dwp_name.c_str ());
     }
 
   if (dbfd == NULL)
     {
       if (dwarf_read_debug)
-       fprintf_unfiltered (gdb_stdlog, "DWP file not found: %s\n", dwp_name);
-      do_cleanups (cleanups);
+       fprintf_unfiltered (gdb_stdlog, "DWP file not found: %s\n", dwp_name.c_str ());
       return NULL;
     }
   dwp_file = OBSTACK_ZALLOC (&objfile->objfile_obstack, struct dwp_file);
-  dwp_file->name = bfd_get_filename (dbfd);
-  dwp_file->dbfd = dbfd;
-  do_cleanups (cleanups);
+  dwp_file->name = bfd_get_filename (dbfd.get ());
+  dwp_file->dbfd = dbfd.release ();
 
   /* +1: section 0 is unused */
-  dwp_file->num_sections = bfd_count_sections (dbfd) + 1;
+  dwp_file->num_sections = bfd_count_sections (dwp_file->dbfd) + 1;
   dwp_file->elf_sections =
     OBSTACK_CALLOC (&objfile->objfile_obstack,
                    dwp_file->num_sections, asection *);
 
-  bfd_map_over_sections (dbfd, dwarf2_locate_common_dwp_sections, dwp_file);
+  bfd_map_over_sections (dwp_file->dbfd, dwarf2_locate_common_dwp_sections,
+                        dwp_file);
 
   dwp_file->cus = create_dwp_hash_table (dwp_file, 0);
 
@@ -10868,12 +11020,13 @@ open_and_init_dwp_file (void)
       error (_("Dwarf Error: DWP file CU version %s doesn't match"
               " TU version %s [in DWP file %s]"),
             pulongest (dwp_file->cus->version),
-            pulongest (dwp_file->tus->version), dwp_name);
+            pulongest (dwp_file->tus->version), dwp_name.c_str ());
     }
   dwp_file->version = dwp_file->cus->version;
 
   if (dwp_file->version == 2)
-    bfd_map_over_sections (dbfd, dwarf2_locate_v2_dwp_sections, dwp_file);
+    bfd_map_over_sections (dwp_file->dbfd, dwarf2_locate_v2_dwp_sections,
+                          dwp_file);
 
   dwp_file->loaded_cus = allocate_dwp_loaded_cutus_table (objfile);
   dwp_file->loaded_tus = allocate_dwp_loaded_cutus_table (objfile);
@@ -10971,7 +11124,7 @@ lookup_dwo_cutu (struct dwarf2_per_cu_data *this_unit,
          *dwo_file_slot = open_and_init_dwo_file (this_unit, dwo_name, comp_dir);
        }
       /* NOTE: This will be NULL if unable to open the file.  */
-      dwo_file = *dwo_file_slot;
+      dwo_file = (struct dwo_file *) *dwo_file_slot;
 
       if (dwo_file != NULL)
        {
@@ -10983,7 +11136,8 @@ lookup_dwo_cutu (struct dwarf2_per_cu_data *this_unit,
 
              memset (&find_dwo_cutu, 0, sizeof (find_dwo_cutu));
              find_dwo_cutu.signature = signature;
-             dwo_cutu = htab_find (dwo_file->tus, &find_dwo_cutu);
+             dwo_cutu
+               = (struct dwo_unit *) htab_find (dwo_file->tus, &find_dwo_cutu);
            }
          else if (!is_debug_types && dwo_file->cu)
            {
@@ -11031,7 +11185,7 @@ lookup_dwo_cutu (struct dwarf2_per_cu_data *this_unit,
             kind, dwo_name, hex_string (signature),
             dwp_text != NULL ? dwp_text : "",
             this_unit->is_debug_types ? "TU" : "CU",
-            this_unit->offset.sect_off, objfile_name (objfile));
+            to_underlying (this_unit->sect_off), objfile_name (objfile));
 
     do_cleanups (cleanups);
   }
@@ -11115,8 +11269,6 @@ queue_and_load_all_dwo_tus (struct dwarf2_per_cu_data *per_cu)
 static void
 free_dwo_file (struct dwo_file *dwo_file, struct objfile *objfile)
 {
-  int ix;
-  struct dwarf2_section_info *section;
 
   /* Note: dbfd is NULL for virtual DWO files.  */
   gdb_bfd_unref (dwo_file->dbfd);
@@ -11211,7 +11363,8 @@ inherit_abstract_dies (struct die_info *die, struct dwarf2_cu *cu)
           && origin_die->tag == DW_TAG_subprogram))
     complaint (&symfile_complaints,
               _("DIE 0x%x and its abstract origin 0x%x have different tags"),
-              die->offset.sect_off, origin_die->offset.sect_off);
+              to_underlying (die->sect_off),
+              to_underlying (origin_die->sect_off));
 
   child_die = die->child;
   die_children_count = 0;
@@ -11220,7 +11373,7 @@ inherit_abstract_dies (struct die_info *die, struct dwarf2_cu *cu)
       child_die = sibling_die (child_die);
       die_children_count++;
     }
-  offsets = xmalloc (sizeof (*offsets) * die_children_count);
+  offsets = XNEWVEC (sect_offset, die_children_count);
   cleanups = make_cleanup (xfree, offsets);
 
   offsets_end = offsets;
@@ -11232,11 +11385,12 @@ inherit_abstract_dies (struct die_info *die, struct dwarf2_cu *cu)
       struct dwarf2_cu *child_origin_cu;
 
       /* We are trying to process concrete instance entries:
-        DW_TAG_GNU_call_site DIEs indeed have a DW_AT_abstract_origin tag, but
+        DW_TAG_call_site DIEs indeed have a DW_AT_abstract_origin tag, but
         it's not relevant to our analysis here. i.e. detecting DIEs that are
         present in the abstract instance but not referenced in the concrete
         one.  */
-      if (child_die->tag == DW_TAG_GNU_call_site)
+      if (child_die->tag == DW_TAG_call_site
+          || child_die->tag == DW_TAG_GNU_call_site)
        continue;
 
       /* For each CHILD_DIE, find the corresponding child of
@@ -11265,25 +11419,27 @@ inherit_abstract_dies (struct die_info *die, struct dwarf2_cu *cu)
                   && child_origin_die->tag == DW_TAG_subprogram))
            complaint (&symfile_complaints,
                       _("Child DIE 0x%x and its abstract origin 0x%x have "
-                        "different tags"), child_die->offset.sect_off,
-                      child_origin_die->offset.sect_off);
+                        "different tags"),
+                      to_underlying (child_die->sect_off),
+                      to_underlying (child_origin_die->sect_off));
          if (child_origin_die->parent != origin_die)
            complaint (&symfile_complaints,
                       _("Child DIE 0x%x and its abstract origin 0x%x have "
-                        "different parents"), child_die->offset.sect_off,
-                      child_origin_die->offset.sect_off);
+                        "different parents"),
+                      to_underlying (child_die->sect_off),
+                      to_underlying (child_origin_die->sect_off));
          else
-           *offsets_end++ = child_origin_die->offset;
+           *offsets_end++ = child_origin_die->sect_off;
        }
     }
   qsort (offsets, offsets_end - offsets, sizeof (*offsets),
         unsigned_int_compar);
   for (offsetp = offsets + 1; offsetp < offsets_end; offsetp++)
-    if (offsetp[-1].sect_off == offsetp->sect_off)
+    if (offsetp[-1] == *offsetp)
       complaint (&symfile_complaints,
                 _("Multiple children of DIE 0x%x refer "
                   "to DIE 0x%x as their abstract origin"),
-                die->offset.sect_off, offsetp->sect_off);
+                to_underlying (die->sect_off), to_underlying (*offsetp));
 
   offsetp = offsets;
   origin_child_die = origin_die->child;
@@ -11291,10 +11447,10 @@ inherit_abstract_dies (struct die_info *die, struct dwarf2_cu *cu)
     {
       /* Is ORIGIN_CHILD_DIE referenced by any of the DIE children?  */
       while (offsetp < offsets_end
-            && offsetp->sect_off < origin_child_die->offset.sect_off)
+            && *offsetp < origin_child_die->sect_off)
        offsetp++;
       if (offsetp >= offsets_end
-         || offsetp->sect_off > origin_child_die->offset.sect_off)
+         || *offsetp > origin_child_die->sect_off)
        {
          /* Found that ORIGIN_CHILD_DIE is really not referenced.
             Check whether we're already processing ORIGIN_CHILD_DIE.
@@ -11351,19 +11507,20 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
     {
       complaint (&symfile_complaints,
                 _("missing name for subprogram DIE at %d"),
-                die->offset.sect_off);
+                to_underlying (die->sect_off));
       return;
     }
 
   /* Ignore functions with missing or invalid low and high pc attributes.  */
-  if (!dwarf2_get_pc_bounds (die, &lowpc, &highpc, cu, NULL))
+  if (dwarf2_get_pc_bounds (die, &lowpc, &highpc, cu, NULL)
+      <= PC_BOUNDS_INVALID)
     {
       attr = dwarf2_attr (die, DW_AT_external, cu);
       if (!attr || !DW_UNSND (attr))
        complaint (&symfile_complaints,
                   _("cannot get low and high bounds "
                     "for subprogram DIE at %d"),
-                  die->offset.sect_off);
+                  to_underlying (die->sect_off));
       return;
     }
 
@@ -11393,6 +11550,16 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
   if (attr)
     dwarf2_symbol_mark_computed (attr, newobj->name, cu, 1);
 
+  /* If there is a location for the static link, record it.  */
+  newobj->static_link = NULL;
+  attr = dwarf2_attr (die, DW_AT_static_link, cu);
+  if (attr)
+    {
+      newobj->static_link
+       = XOBNEW (&objfile->objfile_obstack, struct dynamic_prop);
+      attr_to_dynamic_prop (attr, die, cu, newobj->static_link);
+    }
+
   cu->list_in_scope = &local_symbols;
 
   if (die->child != NULL)
@@ -11444,12 +11611,13 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
   newobj = pop_context ();
   /* Make a block for the local symbols within.  */
   block = finish_block (newobj->name, &local_symbols, newobj->old_blocks,
-                        lowpc, highpc);
+                       newobj->static_link, lowpc, highpc);
 
   /* For C++, set the block's scope.  */
   if ((cu->language == language_cplus
        || cu->language == language_fortran
-       || cu->language == language_d)
+       || cu->language == language_d
+       || cu->language == language_rust)
       && cu->processing_has_namespace_info)
     block_set_scope (block, determine_prefix (die, cu),
                     &objfile->objfile_obstack);
@@ -11466,9 +11634,8 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
 
       templ_func->n_template_arguments = VEC_length (symbolp, template_args);
       templ_func->template_arguments
-       = obstack_alloc (&objfile->objfile_obstack,
-                        (templ_func->n_template_arguments
-                         * sizeof (struct symbol *)));
+        = XOBNEWVEC (&objfile->objfile_obstack, struct symbol *,
+                    templ_func->n_template_arguments);
       memcpy (templ_func->template_arguments,
              VEC_address (symbolp, template_args),
              (templ_func->n_template_arguments * sizeof (struct symbol *)));
@@ -11480,7 +11647,7 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
      when we finish processing a function scope, we may need to go
      back to building a containing block's symbol lists.  */
   local_symbols = newobj->locals;
-  using_directives = newobj->using_directives;
+  local_using_directives = newobj->local_using_directives;
 
   /* If we've finished processing a top-level function, subsequent
      symbols go in the file symbol list.  */
@@ -11508,8 +11675,20 @@ read_lexical_block_scope (struct die_info *die, struct dwarf2_cu *cu)
      as multiple lexical blocks?  Handling children in a sane way would
      be nasty.  Might be easier to properly extend generic blocks to
      describe ranges.  */
-  if (!dwarf2_get_pc_bounds (die, &lowpc, &highpc, cu, NULL))
-    return;
+  switch (dwarf2_get_pc_bounds (die, &lowpc, &highpc, cu, NULL))
+    {
+    case PC_BOUNDS_NOT_PRESENT:
+      /* DW_TAG_lexical_block has no attributes, process its children as if
+        there was no wrapping by that DW_TAG_lexical_block.
+        GCC does no longer produces such DWARF since GCC r224161.  */
+      for (child_die = die->child;
+          child_die != NULL && child_die->tag;
+          child_die = sibling_die (child_die))
+       process_die (child_die, cu);
+      return;
+    case PC_BOUNDS_INVALID:
+      return;
+    }
   lowpc = gdbarch_adjust_dwarf2_addr (gdbarch, lowpc + baseaddr);
   highpc = gdbarch_adjust_dwarf2_addr (gdbarch, highpc + baseaddr);
 
@@ -11526,10 +11705,10 @@ read_lexical_block_scope (struct die_info *die, struct dwarf2_cu *cu)
   inherit_abstract_dies (die, cu);
   newobj = pop_context ();
 
-  if (local_symbols != NULL || using_directives != NULL)
+  if (local_symbols != NULL || local_using_directives != NULL)
     {
       struct block *block
-        = finish_block (0, &local_symbols, newobj->old_blocks,
+        = finish_block (0, &local_symbols, newobj->old_blocks, NULL,
                        newobj->start_addr, highpc);
 
       /* Note that recording ranges after traversing children, as we
@@ -11545,10 +11724,10 @@ read_lexical_block_scope (struct die_info *die, struct dwarf2_cu *cu)
       dwarf2_record_block_ranges (die, block, baseaddr, cu);
     }
   local_symbols = newobj->locals;
-  using_directives = newobj->using_directives;
+  local_using_directives = newobj->local_using_directives;
 }
 
-/* Read in DW_TAG_GNU_call_site and insert it to CU->call_site_htab.  */
+/* Read in DW_TAG_call_site and insert it to CU->call_site_htab.  */
 
 static void
 read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
@@ -11564,13 +11743,19 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
 
   baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
 
-  attr = dwarf2_attr (die, DW_AT_low_pc, cu);
+  attr = dwarf2_attr (die, DW_AT_call_return_pc, cu);
+  if (attr == NULL)
+    {
+      /* This was a pre-DWARF-5 GNU extension alias
+        for DW_AT_call_return_pc.  */
+      attr = dwarf2_attr (die, DW_AT_low_pc, cu);
+    }
   if (!attr)
     {
       complaint (&symfile_complaints,
-                _("missing DW_AT_low_pc for DW_TAG_GNU_call_site "
+                _("missing DW_AT_call_return_pc for DW_TAG_call_site "
                   "DIE 0x%x [in module %s]"),
-                die->offset.sect_off, objfile_name (objfile));
+                to_underlying (die->sect_off), objfile_name (objfile));
       return;
     }
   pc = attr_value_as_address (attr) + baseaddr;
@@ -11585,9 +11770,9 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
   if (*slot != NULL)
     {
       complaint (&symfile_complaints,
-                _("Duplicate PC %s for DW_TAG_GNU_call_site "
+                _("Duplicate PC %s for DW_TAG_call_site "
                   "DIE 0x%x [in module %s]"),
-                paddress (gdbarch, pc), die->offset.sect_off,
+                paddress (gdbarch, pc), to_underlying (die->sect_off),
                 objfile_name (objfile));
       return;
     }
@@ -11598,12 +11783,13 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
   for (child_die = die->child; child_die && child_die->tag;
        child_die = sibling_die (child_die))
     {
-      if (child_die->tag != DW_TAG_GNU_call_site_parameter)
+      if (child_die->tag != DW_TAG_call_site_parameter
+          && child_die->tag != DW_TAG_GNU_call_site_parameter)
        {
          complaint (&symfile_complaints,
-                    _("Tag %d is not DW_TAG_GNU_call_site_parameter in "
-                      "DW_TAG_GNU_call_site child DIE 0x%x [in module %s]"),
-                    child_die->tag, child_die->offset.sect_off,
+                    _("Tag %d is not DW_TAG_call_site_parameter in "
+                      "DW_TAG_call_site child DIE 0x%x [in module %s]"),
+                    child_die->tag, to_underlying (child_die->sect_off),
                     objfile_name (objfile));
          continue;
        }
@@ -11611,15 +11797,17 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
       nparams++;
     }
 
-  call_site = obstack_alloc (&objfile->objfile_obstack,
-                            (sizeof (*call_site)
-                             + (sizeof (*call_site->parameter)
-                                * (nparams - 1))));
+  call_site
+    = ((struct call_site *)
+       obstack_alloc (&objfile->objfile_obstack,
+                     sizeof (*call_site)
+                     + (sizeof (*call_site->parameter) * (nparams - 1))));
   *slot = call_site;
   memset (call_site, 0, sizeof (*call_site) - sizeof (*call_site->parameter));
   call_site->pc = pc;
 
-  if (dwarf2_flag_true_p (die, DW_AT_GNU_tail_call, cu))
+  if (dwarf2_flag_true_p (die, DW_AT_call_tail_call, cu)
+      || dwarf2_flag_true_p (die, DW_AT_GNU_tail_call, cu))
     {
       struct die_info *func_die;
 
@@ -11629,10 +11817,12 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
           && func_die->tag != DW_TAG_subroutine_type;
           func_die = func_die->parent);
 
-      /* DW_AT_GNU_all_call_sites is a superset
-        of DW_AT_GNU_all_tail_call_sites.  */
+      /* DW_AT_call_all_calls is a superset
+        of DW_AT_call_all_tail_calls.  */
       if (func_die
+          && !dwarf2_flag_true_p (func_die, DW_AT_call_all_calls, cu)
           && !dwarf2_flag_true_p (func_die, DW_AT_GNU_all_call_sites, cu)
+         && !dwarf2_flag_true_p (func_die, DW_AT_call_all_tail_calls, cu)
          && !dwarf2_flag_true_p (func_die, DW_AT_GNU_all_tail_call_sites, cu))
        {
          /* TYPE_TAIL_CALL_LIST is not interesting in functions where it is
@@ -11660,15 +11850,22 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
            }
          else
            complaint (&symfile_complaints,
-                      _("Cannot find function owning DW_TAG_GNU_call_site "
+                      _("Cannot find function owning DW_TAG_call_site "
                         "DIE 0x%x [in module %s]"),
-                      die->offset.sect_off, objfile_name (objfile));
+                      to_underlying (die->sect_off), objfile_name (objfile));
        }
     }
 
-  attr = dwarf2_attr (die, DW_AT_GNU_call_site_target, cu);
+  attr = dwarf2_attr (die, DW_AT_call_target, cu);
+  if (attr == NULL)
+    attr = dwarf2_attr (die, DW_AT_GNU_call_site_target, cu);
+  if (attr == NULL)
+    attr = dwarf2_attr (die, DW_AT_call_origin, cu);
   if (attr == NULL)
-    attr = dwarf2_attr (die, DW_AT_abstract_origin, cu);
+    {
+      /* This was a pre-DWARF-5 GNU extension alias for DW_AT_call_origin.  */
+      attr = dwarf2_attr (die, DW_AT_abstract_origin, cu);
+    }
   SET_FIELD_DWARF_BLOCK (call_site->target, NULL);
   if (!attr || (attr_form_is_block (attr) && DW_BLOCK (attr)->size == 0))
     /* Keep NULL DWARF_BLOCK.  */;
@@ -11676,7 +11873,7 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
     {
       struct dwarf2_locexpr_baton *dlbaton;
 
-      dlbaton = obstack_alloc (&objfile->objfile_obstack, sizeof (*dlbaton));
+      dlbaton = XOBNEW (&objfile->objfile_obstack, struct dwarf2_locexpr_baton);
       dlbaton->data = DW_BLOCK (attr)->data;
       dlbaton->size = DW_BLOCK (attr)->size;
       dlbaton->per_cu = cu->per_cu;
@@ -11692,23 +11889,23 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
       gdb_assert (target_cu->objfile == objfile);
       if (die_is_declaration (target_die, target_cu))
        {
-         const char *target_physname = NULL;
-         struct attribute *target_attr;
+         const char *target_physname;
 
          /* Prefer the mangled name; otherwise compute the demangled one.  */
-         target_attr = dwarf2_attr (target_die, DW_AT_linkage_name, target_cu);
-         if (target_attr == NULL)
-           target_attr = dwarf2_attr (target_die, DW_AT_MIPS_linkage_name,
-                                      target_cu);
-         if (target_attr != NULL && DW_STRING (target_attr) != NULL)
-           target_physname = DW_STRING (target_attr);
-         else
+         target_physname = dwarf2_string_attr (target_die,
+                                               DW_AT_linkage_name,
+                                               target_cu);
+         if (target_physname == NULL)
+           target_physname = dwarf2_string_attr (target_die,
+                                                DW_AT_MIPS_linkage_name,
+                                                target_cu);
+         if (target_physname == NULL)
            target_physname = dwarf2_physname (NULL, target_die, target_cu);
          if (target_physname == NULL)
            complaint (&symfile_complaints,
-                      _("DW_AT_GNU_call_site_target target DIE has invalid "
+                      _("DW_AT_call_target target DIE has invalid "
                         "physname, for referencing DIE 0x%x [in module %s]"),
-                      die->offset.sect_off, objfile_name (objfile));
+                      to_underlying (die->sect_off), objfile_name (objfile));
          else
            SET_FIELD_PHYSNAME (call_site->target, target_physname);
        }
@@ -11717,11 +11914,12 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
          CORE_ADDR lowpc;
 
          /* DW_AT_entry_pc should be preferred.  */
-         if (!dwarf2_get_pc_bounds (target_die, &lowpc, NULL, target_cu, NULL))
+         if (dwarf2_get_pc_bounds (target_die, &lowpc, NULL, target_cu, NULL)
+             <= PC_BOUNDS_INVALID)
            complaint (&symfile_complaints,
-                      _("DW_AT_GNU_call_site_target target DIE has invalid "
+                      _("DW_AT_call_target target DIE has invalid "
                         "low pc, for referencing DIE 0x%x [in module %s]"),
-                      die->offset.sect_off, objfile_name (objfile));
+                      to_underlying (die->sect_off), objfile_name (objfile));
          else
            {
              lowpc = gdbarch_adjust_dwarf2_addr (gdbarch, lowpc + baseaddr);
@@ -11731,9 +11929,9 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
     }
   else
     complaint (&symfile_complaints,
-              _("DW_TAG_GNU_call_site DW_AT_GNU_call_site_target is neither "
+              _("DW_TAG_call_site DW_AT_call_target is neither "
                 "block nor reference, for DIE 0x%x [in module %s]"),
-              die->offset.sect_off, objfile_name (objfile));
+              to_underlying (die->sect_off), objfile_name (objfile));
 
   call_site->per_cu = cu->per_cu;
 
@@ -11744,7 +11942,8 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
       struct call_site_parameter *parameter;
       struct attribute *loc, *origin;
 
-      if (child_die->tag != DW_TAG_GNU_call_site_parameter)
+      if (child_die->tag != DW_TAG_call_site_parameter
+          && child_die->tag != DW_TAG_GNU_call_site_parameter)
        {
          /* Already printed the complaint above.  */
          continue;
@@ -11755,37 +11954,43 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
 
       /* DW_AT_location specifies the register number or DW_AT_abstract_origin
         specifies DW_TAG_formal_parameter.  Value of the data assumed for the
-        register is contained in DW_AT_GNU_call_site_value.  */
+        register is contained in DW_AT_call_value.  */
 
       loc = dwarf2_attr (child_die, DW_AT_location, cu);
-      origin = dwarf2_attr (child_die, DW_AT_abstract_origin, cu);
+      origin = dwarf2_attr (child_die, DW_AT_call_parameter, cu);
+      if (origin == NULL)
+       {
+         /* This was a pre-DWARF-5 GNU extension alias
+            for DW_AT_call_parameter.  */
+         origin = dwarf2_attr (child_die, DW_AT_abstract_origin, cu);
+       }
       if (loc == NULL && origin != NULL && attr_form_is_ref (origin))
        {
-         sect_offset offset;
-
          parameter->kind = CALL_SITE_PARAMETER_PARAM_OFFSET;
-         offset = dwarf2_get_ref_die_offset (origin);
-         if (!offset_in_cu_p (&cu->header, offset))
+
+         sect_offset sect_off
+           = (sect_offset) dwarf2_get_ref_die_offset (origin);
+         if (!offset_in_cu_p (&cu->header, sect_off))
            {
              /* As DW_OP_GNU_parameter_ref uses CU-relative offset this
                 binding can be done only inside one CU.  Such referenced DIE
                 therefore cannot be even moved to DW_TAG_partial_unit.  */
              complaint (&symfile_complaints,
-                        _("DW_AT_abstract_origin offset is not in CU for "
-                          "DW_TAG_GNU_call_site child DIE 0x%x "
-                          "[in module %s]"),
-                        child_die->offset.sect_off, objfile_name (objfile));
+                        _("DW_AT_call_parameter offset is not in CU for "
+                          "DW_TAG_call_site child DIE 0x%x [in module %s]"),
+                        to_underlying (child_die->sect_off),
+                        objfile_name (objfile));
              continue;
            }
-         parameter->u.param_offset.cu_off = (offset.sect_off
-                                             - cu->header.offset.sect_off);
+         parameter->u.param_cu_off
+           = (cu_offset) (sect_off - cu->header.sect_off);
        }
       else if (loc == NULL || origin != NULL || !attr_form_is_block (loc))
        {
          complaint (&symfile_complaints,
                     _("No DW_FORM_block* DW_AT_location for "
-                      "DW_TAG_GNU_call_site child DIE 0x%x [in module %s]"),
-                    child_die->offset.sect_off, objfile_name (objfile));
+                      "DW_TAG_call_site child DIE 0x%x [in module %s]"),
+                    to_underlying (child_die->sect_off), objfile_name (objfile));
          continue;
        }
       else
@@ -11803,20 +12008,24 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
              complaint (&symfile_complaints,
                         _("Only single DW_OP_reg or DW_OP_fbreg is supported "
                           "for DW_FORM_block* DW_AT_location is supported for "
-                          "DW_TAG_GNU_call_site child DIE 0x%x "
+                          "DW_TAG_call_site child DIE 0x%x "
                           "[in module %s]"),
-                        child_die->offset.sect_off, objfile_name (objfile));
+                        to_underlying (child_die->sect_off),
+                        objfile_name (objfile));
              continue;
            }
        }
 
-      attr = dwarf2_attr (child_die, DW_AT_GNU_call_site_value, cu);
+      attr = dwarf2_attr (child_die, DW_AT_call_value, cu);
+      if (attr == NULL)
+       attr = dwarf2_attr (child_die, DW_AT_GNU_call_site_value, cu);
       if (!attr_form_is_block (attr))
        {
          complaint (&symfile_complaints,
-                    _("No DW_FORM_block* DW_AT_GNU_call_site_value for "
-                      "DW_TAG_GNU_call_site child DIE 0x%x [in module %s]"),
-                    child_die->offset.sect_off, objfile_name (objfile));
+                    _("No DW_FORM_block* DW_AT_call_value for "
+                      "DW_TAG_call_site child DIE 0x%x [in module %s]"),
+                    to_underlying (child_die->sect_off),
+                    objfile_name (objfile));
          continue;
        }
       parameter->value = DW_BLOCK (attr)->data;
@@ -11827,14 +12036,17 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
       parameter->data_value_size = 0;
       call_site->parameter_count++;
 
-      attr = dwarf2_attr (child_die, DW_AT_GNU_call_site_data_value, cu);
+      attr = dwarf2_attr (child_die, DW_AT_call_data_value, cu);
+      if (attr == NULL)
+       attr = dwarf2_attr (child_die, DW_AT_GNU_call_site_data_value, cu);
       if (attr)
        {
          if (!attr_form_is_block (attr))
            complaint (&symfile_complaints,
-                      _("No DW_FORM_block* DW_AT_GNU_call_site_data_value for "
-                        "DW_TAG_GNU_call_site child DIE 0x%x [in module %s]"),
-                      child_die->offset.sect_off, objfile_name (objfile));
+                      _("No DW_FORM_block* DW_AT_call_data_value for "
+                        "DW_TAG_call_site child DIE 0x%x [in module %s]"),
+                      to_underlying (child_die->sect_off),
+                      objfile_name (objfile));
          else
            {
              parameter->data_value = DW_BLOCK (attr)->data;
@@ -11844,14 +12056,17 @@ read_call_site_scope (struct die_info *die, struct dwarf2_cu *cu)
     }
 }
 
-/* Get low and high pc attributes from DW_AT_ranges attribute value OFFSET.
-   Return 1 if the attributes are present and valid, otherwise, return 0.
-   If RANGES_PST is not NULL we should setup `objfile->psymtabs_addrmap'.  */
+/* Call CALLBACK from DW_AT_ranges attribute value OFFSET
+   reading .debug_rnglists.
+   Callback's type should be:
+    void (CORE_ADDR range_beginning, CORE_ADDR range_end)
+   Return true if the attributes are present and valid, otherwise,
+   return false.  */
 
-static int
-dwarf2_ranges_read (unsigned offset, CORE_ADDR *low_return,
-                   CORE_ADDR *high_return, struct dwarf2_cu *cu,
-                   struct partial_symtab *ranges_pst)
+template <typename Callback>
+static bool
+dwarf2_rnglists_process (unsigned offset, struct dwarf2_cu *cu,
+                        Callback &&callback)
 {
   struct objfile *objfile = cu->objfile;
   struct gdbarch *gdbarch = get_objfile_arch (objfile);
@@ -11864,38 +12079,196 @@ dwarf2_ranges_read (unsigned offset, CORE_ADDR *low_return,
   int found_base;
   unsigned int dummy;
   const gdb_byte *buffer;
-  CORE_ADDR marker;
-  int low_set;
   CORE_ADDR low = 0;
   CORE_ADDR high = 0;
   CORE_ADDR baseaddr;
+  bool overflow = false;
 
   found_base = cu->base_known;
   base = cu->base_address;
 
-  dwarf2_read_section (objfile, &dwarf2_per_objfile->ranges);
-  if (offset >= dwarf2_per_objfile->ranges.size)
+  dwarf2_read_section (objfile, &dwarf2_per_objfile->rnglists);
+  if (offset >= dwarf2_per_objfile->rnglists.size)
     {
       complaint (&symfile_complaints,
                 _("Offset %d out of bounds for DW_AT_ranges attribute"),
                 offset);
-      return 0;
+      return false;
     }
-  buffer = dwarf2_per_objfile->ranges.buffer + offset;
+  buffer = dwarf2_per_objfile->rnglists.buffer + offset;
+
+  baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
 
-  /* Read in the largest possible address.  */
-  marker = read_address (obfd, buffer, cu, &dummy);
-  if ((marker & mask) == mask)
+  while (1)
     {
-      /* If we found the largest possible address, then
-        read the base address.  */
-      base = read_address (obfd, buffer + addr_size, cu, &dummy);
-      buffer += 2 * addr_size;
-      offset += 2 * addr_size;
-      found_base = 1;
+      /* Initialize it due to a false compiler warning.  */
+      CORE_ADDR range_beginning = 0, range_end = 0;
+      const gdb_byte *buf_end = (dwarf2_per_objfile->rnglists.buffer
+                                + dwarf2_per_objfile->rnglists.size);
+      unsigned int bytes_read;
+
+      if (buffer == buf_end)
+       {
+         overflow = true;
+         break;
+       }
+      const auto rlet = static_cast<enum dwarf_range_list_entry>(*buffer++);
+      switch (rlet)
+       {
+       case DW_RLE_end_of_list:
+         break;
+       case DW_RLE_base_address:
+         if (buffer + cu->header.addr_size > buf_end)
+           {
+             overflow = true;
+             break;
+           }
+         base = read_address (obfd, buffer, cu, &bytes_read);
+         found_base = 1;
+         buffer += bytes_read;
+         break;
+       case DW_RLE_start_length:
+         if (buffer + cu->header.addr_size > buf_end)
+           {
+             overflow = true;
+             break;
+           }
+         range_beginning = read_address (obfd, buffer, cu, &bytes_read);
+         buffer += bytes_read;
+         range_end = (range_beginning
+                      + read_unsigned_leb128 (obfd, buffer, &bytes_read));
+         buffer += bytes_read;
+         if (buffer > buf_end)
+           {
+             overflow = true;
+             break;
+           }
+         break;
+       case DW_RLE_offset_pair:
+         range_beginning = read_unsigned_leb128 (obfd, buffer, &bytes_read);
+         buffer += bytes_read;
+         if (buffer > buf_end)
+           {
+             overflow = true;
+             break;
+           }
+         range_end = read_unsigned_leb128 (obfd, buffer, &bytes_read);
+         buffer += bytes_read;
+         if (buffer > buf_end)
+           {
+             overflow = true;
+             break;
+           }
+         break;
+       case DW_RLE_start_end:
+         if (buffer + 2 * cu->header.addr_size > buf_end)
+           {
+             overflow = true;
+             break;
+           }
+         range_beginning = read_address (obfd, buffer, cu, &bytes_read);
+         buffer += bytes_read;
+         range_end = read_address (obfd, buffer, cu, &bytes_read);
+         buffer += bytes_read;
+         break;
+       default:
+         complaint (&symfile_complaints,
+                    _("Invalid .debug_rnglists data (no base address)"));
+         return false;
+       }
+      if (rlet == DW_RLE_end_of_list || overflow)
+       break;
+      if (rlet == DW_RLE_base_address)
+       continue;
+
+      if (!found_base)
+       {
+         /* We have no valid base address for the ranges
+            data.  */
+         complaint (&symfile_complaints,
+                    _("Invalid .debug_rnglists data (no base address)"));
+         return false;
+       }
+
+      if (range_beginning > range_end)
+       {
+         /* Inverted range entries are invalid.  */
+         complaint (&symfile_complaints,
+                    _("Invalid .debug_rnglists data (inverted range)"));
+         return false;
+       }
+
+      /* Empty range entries have no effect.  */
+      if (range_beginning == range_end)
+       continue;
+
+      range_beginning += base;
+      range_end += base;
+
+      /* A not-uncommon case of bad debug info.
+        Don't pollute the addrmap with bad data.  */
+      if (range_beginning + baseaddr == 0
+         && !dwarf2_per_objfile->has_section_at_zero)
+       {
+         complaint (&symfile_complaints,
+                    _(".debug_rnglists entry has start address of zero"
+                      " [in module %s]"), objfile_name (objfile));
+         continue;
+       }
+
+      callback (range_beginning, range_end);
     }
 
-  low_set = 0;
+  if (overflow)
+    {
+      complaint (&symfile_complaints,
+                _("Offset %d is not terminated "
+                  "for DW_AT_ranges attribute"),
+                offset);
+      return false;
+    }
+
+  return true;
+}
+
+/* Call CALLBACK from DW_AT_ranges attribute value OFFSET reading .debug_ranges.
+   Callback's type should be:
+    void (CORE_ADDR range_beginning, CORE_ADDR range_end)
+   Return 1 if the attributes are present and valid, otherwise, return 0.  */
+
+template <typename Callback>
+static int
+dwarf2_ranges_process (unsigned offset, struct dwarf2_cu *cu,
+                      Callback &&callback)
+{
+  struct objfile *objfile = cu->objfile;
+  struct gdbarch *gdbarch = get_objfile_arch (objfile);
+  struct comp_unit_head *cu_header = &cu->header;
+  bfd *obfd = objfile->obfd;
+  unsigned int addr_size = cu_header->addr_size;
+  CORE_ADDR mask = ~(~(CORE_ADDR)1 << (addr_size * 8 - 1));
+  /* Base address selection entry.  */
+  CORE_ADDR base;
+  int found_base;
+  unsigned int dummy;
+  const gdb_byte *buffer;
+  CORE_ADDR baseaddr;
+
+  if (cu_header->version >= 5)
+    return dwarf2_rnglists_process (offset, cu, callback);
+
+  found_base = cu->base_known;
+  base = cu->base_address;
+
+  dwarf2_read_section (objfile, &dwarf2_per_objfile->ranges);
+  if (offset >= dwarf2_per_objfile->ranges.size)
+    {
+      complaint (&symfile_complaints,
+                _("Offset %d out of bounds for DW_AT_ranges attribute"),
+                offset);
+      return 0;
+    }
+  buffer = dwarf2_per_objfile->ranges.buffer + offset;
 
   baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
 
@@ -11919,9 +12292,9 @@ dwarf2_ranges_read (unsigned offset, CORE_ADDR *low_return,
         the base address.  Check for a base address here.  */
       if ((range_beginning & mask) == mask)
        {
-         /* If we found the largest possible address, then
-            read the base address.  */
-         base = read_address (obfd, buffer + addr_size, cu, &dummy);
+         /* If we found the largest possible address, then we already
+            have the base address in range_end.  */
+         base = range_end;
          found_base = 1;
          continue;
        }
@@ -11961,6 +12334,33 @@ dwarf2_ranges_read (unsigned offset, CORE_ADDR *low_return,
          continue;
        }
 
+      callback (range_beginning, range_end);
+    }
+
+  return 1;
+}
+
+/* Get low and high pc attributes from DW_AT_ranges attribute value OFFSET.
+   Return 1 if the attributes are present and valid, otherwise, return 0.
+   If RANGES_PST is not NULL we should setup `objfile->psymtabs_addrmap'.  */
+
+static int
+dwarf2_ranges_read (unsigned offset, CORE_ADDR *low_return,
+                   CORE_ADDR *high_return, struct dwarf2_cu *cu,
+                   struct partial_symtab *ranges_pst)
+{
+  struct objfile *objfile = cu->objfile;
+  struct gdbarch *gdbarch = get_objfile_arch (objfile);
+  const CORE_ADDR baseaddr = ANOFFSET (objfile->section_offsets,
+                                      SECT_OFF_TEXT (objfile));
+  int low_set = 0;
+  CORE_ADDR low = 0;
+  CORE_ADDR high = 0;
+  int retval;
+
+  retval = dwarf2_ranges_process (offset, cu,
+    [&] (CORE_ADDR range_beginning, CORE_ADDR range_end)
+    {
       if (ranges_pst != NULL)
        {
          CORE_ADDR lowpc;
@@ -11991,7 +12391,9 @@ dwarf2_ranges_read (unsigned offset, CORE_ADDR *low_return,
          if (range_end > high)
            high = range_end;
        }
-    }
+    });
+  if (!retval)
+    return 0;
 
   if (! low_set)
     /* If the first entry is an end-of-list marker, the range
@@ -12005,11 +12407,11 @@ dwarf2_ranges_read (unsigned offset, CORE_ADDR *low_return,
   return 1;
 }
 
-/* Get low and high pc attributes from a die.  Return 1 if the attributes
-   are present and valid, otherwise, return 0.  Return -1 if the range is
-   discontinuous, i.e. derived from DW_AT_ranges information.  */
+/* Get low and high pc attributes from a die.  See enum pc_bounds_kind
+   definition for the return value.  *LOWPC and *HIGHPC are set iff
+   neither PC_BOUNDS_NOT_PRESENT nor PC_BOUNDS_INVALID are returned.  */
 
-static int
+static enum pc_bounds_kind
 dwarf2_get_pc_bounds (struct die_info *die, CORE_ADDR *lowpc,
                      CORE_ADDR *highpc, struct dwarf2_cu *cu,
                      struct partial_symtab *pst)
@@ -12018,7 +12420,7 @@ dwarf2_get_pc_bounds (struct die_info *die, CORE_ADDR *lowpc,
   struct attribute *attr_high;
   CORE_ADDR low = 0;
   CORE_ADDR high = 0;
-  int ret = 0;
+  enum pc_bounds_kind ret;
 
   attr_high = dwarf2_attr (die, DW_AT_high_pc, cu);
   if (attr_high)
@@ -12033,10 +12435,10 @@ dwarf2_get_pc_bounds (struct die_info *die, CORE_ADDR *lowpc,
        }
       else
        /* Found high w/o low attribute.  */
-       return 0;
+       return PC_BOUNDS_INVALID;
 
       /* Found consecutive range of addresses.  */
-      ret = 1;
+      ret = PC_BOUNDS_HIGH_LOW;
     }
   else
     {
@@ -12055,15 +12457,17 @@ dwarf2_get_pc_bounds (struct die_info *die, CORE_ADDR *lowpc,
          /* Value of the DW_AT_ranges attribute is the offset in the
             .debug_ranges section.  */
          if (!dwarf2_ranges_read (ranges_offset, &low, &high, cu, pst))
-           return 0;
+           return PC_BOUNDS_INVALID;
          /* Found discontinuous range of addresses.  */
-         ret = -1;
+         ret = PC_BOUNDS_RANGES;
        }
+      else
+       return PC_BOUNDS_NOT_PRESENT;
     }
 
   /* read_partial_die has also the strict LOW < HIGH requirement.  */
   if (high <= low)
-    return 0;
+    return PC_BOUNDS_INVALID;
 
   /* When using the GNU linker, .gnu.linkonce. sections are used to
      eliminate duplicate copies of functions and vtables and such.
@@ -12074,7 +12478,7 @@ dwarf2_get_pc_bounds (struct die_info *die, CORE_ADDR *lowpc,
      If this is a discarded function, mark the pc bounds as invalid,
      so that GDB will ignore it.  */
   if (low == 0 && !dwarf2_per_objfile->has_section_at_zero)
-    return 0;
+    return PC_BOUNDS_INVALID;
 
   *lowpc = low;
   if (highpc)
@@ -12095,10 +12499,10 @@ dwarf2_get_subprogram_pc_bounds (struct die_info *die,
   CORE_ADDR low, high;
   struct die_info *child = die->child;
 
-  if (dwarf2_get_pc_bounds (die, &low, &high, cu, NULL))
+  if (dwarf2_get_pc_bounds (die, &low, &high, cu, NULL) >= PC_BOUNDS_RANGES)
     {
-      *lowpc = min (*lowpc, low);
-      *highpc = max (*highpc, high);
+      *lowpc = std::min (*lowpc, low);
+      *highpc = std::max (*highpc, high);
     }
 
   /* If the language does not allow nested subprograms (either inside
@@ -12132,7 +12536,8 @@ get_scope_pc_bounds (struct die_info *die,
   CORE_ADDR best_high = (CORE_ADDR) 0;
   CORE_ADDR current_low, current_high;
 
-  if (dwarf2_get_pc_bounds (die, &current_low, &current_high, cu, NULL))
+  if (dwarf2_get_pc_bounds (die, &current_low, &current_high, cu, NULL)
+      >= PC_BOUNDS_RANGES)
     {
       best_low = current_low;
       best_high = current_high;
@@ -12161,8 +12566,8 @@ get_scope_pc_bounds (struct die_info *die,
 
            if (current_low != ((CORE_ADDR) -1))
              {
-               best_low = min (best_low, current_low);
-               best_high = max (best_high, current_high);
+               best_low = std::min (best_low, current_low);
+               best_high = std::max (best_high, current_high);
              }
            break;
          default:
@@ -12240,79 +12645,15 @@ dwarf2_record_block_ranges (struct die_info *die, struct block *block,
       CORE_ADDR base = cu->base_address;
       int base_known = cu->base_known;
 
-      dwarf2_read_section (objfile, &dwarf2_per_objfile->ranges);
-      if (offset >= dwarf2_per_objfile->ranges.size)
-        {
-          complaint (&symfile_complaints,
-                     _("Offset %lu out of bounds for DW_AT_ranges attribute"),
-                     offset);
-          return;
-        }
-      buffer = dwarf2_per_objfile->ranges.buffer + offset;
-
-      for (;;)
-        {
-          unsigned int bytes_read;
-          CORE_ADDR start, end;
-
-          start = read_address (obfd, buffer, cu, &bytes_read);
-          buffer += bytes_read;
-          end = read_address (obfd, buffer, cu, &bytes_read);
-          buffer += bytes_read;
-
-          /* Did we find the end of the range list?  */
-          if (start == 0 && end == 0)
-            break;
-
-          /* Did we find a base address selection entry?  */
-          else if ((start & base_select_mask) == base_select_mask)
-            {
-              base = end;
-              base_known = 1;
-            }
-
-          /* We found an ordinary address range.  */
-          else
-            {
-              if (!base_known)
-                {
-                  complaint (&symfile_complaints,
-                            _("Invalid .debug_ranges data "
-                              "(no base address)"));
-                  return;
-                }
-
-             if (start > end)
-               {
-                 /* Inverted range entries are invalid.  */
-                 complaint (&symfile_complaints,
-                            _("Invalid .debug_ranges data "
-                              "(inverted range)"));
-                 return;
-               }
-
-             /* Empty range entries have no effect.  */
-             if (start == end)
-               continue;
-
-             start += base + baseaddr;
-             end += base + baseaddr;
-
-             /* A not-uncommon case of bad debug info.
-                Don't pollute the addrmap with bad data.  */
-             if (start == 0 && !dwarf2_per_objfile->has_section_at_zero)
-               {
-                 complaint (&symfile_complaints,
-                            _(".debug_ranges entry has start address of zero"
-                              " [in module %s]"), objfile_name (objfile));
-                 continue;
-               }
-
-             start = gdbarch_adjust_dwarf2_addr (gdbarch, start);
-             end = gdbarch_adjust_dwarf2_addr (gdbarch, end);
-              record_block_range (block, start, end - 1);
-            }
-        }
+      dwarf2_ranges_process (offset, cu,
+       [&] (CORE_ADDR start, CORE_ADDR end)
+       {
+         start += baseaddr;
+         end += baseaddr;
+         start = gdbarch_adjust_dwarf2_addr (gdbarch, start);
+         end = gdbarch_adjust_dwarf2_addr (gdbarch, end);
+         record_block_range (block, start, end - 1);
+       });
     }
 }
 
@@ -12322,7 +12663,6 @@ dwarf2_record_block_ranges (struct die_info *die, struct block *block,
 static void
 check_producer (struct dwarf2_cu *cu)
 {
-  const char *cs;
   int major, minor;
 
   if (cu->producer == NULL)
@@ -12443,7 +12783,7 @@ dwarf2_add_field (struct field_info *fip, struct die_info *die,
   const char *fieldname = "";
 
   /* Allocate a new field list entry and link it in.  */
-  new_field = (struct nextfield *) xmalloc (sizeof (struct nextfield));
+  new_field = XNEW (struct nextfield);
   make_cleanup (xfree, new_field);
   memset (new_field, 0, sizeof (struct nextfield));
 
@@ -12545,6 +12885,10 @@ dwarf2_add_field (struct field_info *fip, struct die_info *die,
                                 - bit_offset - FIELD_BITSIZE (*fp)));
            }
        }
+      attr = dwarf2_attr (die, DW_AT_data_bit_offset, cu);
+      if (attr != NULL)
+       SET_FIELD_BITPOS (*fp, (FIELD_BITPOS (*fp)
+                               + dwarf2_get_attr_constant_value (attr, 0)));
 
       /* Get name of field.  */
       fieldname = dwarf2_name (die, cu);
@@ -12622,14 +12966,11 @@ static void
 dwarf2_add_typedef (struct field_info *fip, struct die_info *die,
                    struct dwarf2_cu *cu)
 {
-  struct objfile *objfile = cu->objfile;
   struct typedef_field_list *new_field;
-  struct attribute *attr;
   struct typedef_field *fp;
-  char *fieldname = "";
 
   /* Allocate a new field list entry and link it in.  */
-  new_field = xzalloc (sizeof (*new_field));
+  new_field = XCNEW (struct typedef_field_list);
   make_cleanup (xfree, new_field);
 
   gdb_assert (die->tag == DW_TAG_typedef);
@@ -12688,7 +13029,7 @@ dwarf2_attach_fields_to_type (struct field_info *fip, struct type *type,
       unsigned char *pointer;
 
       ALLOCATE_CPLUS_STRUCT_TYPE (type);
-      pointer = TYPE_ALLOC (type, num_bytes);
+      pointer = (unsigned char *) TYPE_ALLOC (type, num_bytes);
       TYPE_FIELD_VIRTUAL_BITS (type) = pointer;
       B_CLRALL (TYPE_FIELD_VIRTUAL_BITS (type), fip->nbaseclasses);
       TYPE_N_BASECLASSES (type) = fip->nbaseclasses;
@@ -12833,7 +13174,7 @@ dwarf2_add_member_fn (struct field_info *fip, struct die_info *die,
 
   /* Create a new member function field and chain it to the field list
      entry.  */
-  new_fnfield = (struct nextfnfield *) xmalloc (sizeof (struct nextfnfield));
+  new_fnfield = XNEW (struct nextfnfield);
   make_cleanup (xfree, new_fnfield);
   memset (new_fnfield, 0, sizeof (struct nextfnfield));
   new_fnfield->next = flp->head;
@@ -12844,7 +13185,7 @@ dwarf2_add_member_fn (struct field_info *fip, struct die_info *die,
   fnp = &new_fnfield->fnfield;
 
   /* Delay processing of the physname until later.  */
-  if (cu->language == language_cplus || cu->language == language_java)
+  if (cu->language == language_cplus)
     {
       add_to_method_list (type, i, flp->length - 1, fieldname,
                          die, cu);
@@ -12892,7 +13233,7 @@ dwarf2_add_member_fn (struct field_info *fip, struct die_info *die,
   /* Get accessibility.  */
   attr = dwarf2_attr (die, DW_AT_accessibility, cu);
   if (attr)
-    accessibility = DW_UNSND (attr);
+    accessibility = (enum dwarf_access_attribute) DW_UNSND (attr);
   else
     accessibility = dwarf2_default_access_attribute (die, cu);
   switch (accessibility)
@@ -12933,13 +13274,6 @@ dwarf2_add_member_fn (struct field_info *fip, struct die_info *die,
                       && DW_BLOCK (attr)->data[0] == DW_OP_deref_size
                       && DW_BLOCK (attr)->data[1] == cu->header.addr_size))
            {
-             struct dwarf_block blk;
-             int offset;
-
-             offset = (DW_BLOCK (attr)->data[0] == DW_OP_deref
-                       ? 1 : 2);
-             blk.size = DW_BLOCK (attr)->size - offset;
-             blk.data = DW_BLOCK (attr)->data + offset;
              fnp->voffset = decode_locdesc (DW_BLOCK (attr), cu);
              if ((fnp->voffset % cu->header.addr_size) != 0)
                dwarf2_complex_location_expr_complaint ();
@@ -12961,7 +13295,7 @@ dwarf2_add_member_fn (struct field_info *fip, struct die_info *die,
                  complaint (&symfile_complaints,
                             _("cannot determine context for virtual member "
                               "function \"%s\" (offset %d)"),
-                            fieldname, die->offset.sect_off);
+                            fieldname, to_underlying (die->sect_off));
                }
              else
                {
@@ -12989,7 +13323,7 @@ dwarf2_add_member_fn (struct field_info *fip, struct die_info *die,
          complaint (&symfile_complaints,
                     _("Member function \"%s\" (offset %d) is virtual "
                       "but the vtable offset is not specified"),
-                    fieldname, die->offset.sect_off);
+                    fieldname, to_underlying (die->sect_off));
          ALLOCATE_CPLUS_STRUCT_TYPE (type);
          TYPE_CPLUS_DYNAMIC (type) = 1;
        }
@@ -13037,11 +13371,8 @@ is_vtable_name (const char *name, struct dwarf2_cu *cu)
   static const char vptr[] = "_vptr";
   static const char vtable[] = "vtable";
 
-  /* Look for the C++ and Java forms of the vtable.  */
-  if ((cu->language == language_java
-       && startswith (name, vtable))
-       || (startswith (name, vptr)
-       && is_cplus_marker (name[sizeof (vptr) - 1])))
+  /* Look for the C++ form of the vtable.  */
+  if (startswith (name, vptr) && is_cplus_marker (name[sizeof (vptr) - 1]))
     return 1;
 
   return 0;
@@ -13144,8 +13475,8 @@ read_structure_type (struct die_info *die, struct dwarf2_cu *cu)
   if (name != NULL)
     {
       if (cu->language == language_cplus
-         || cu->language == language_java
-         || cu->language == language_d)
+         || cu->language == language_d
+         || cu->language == language_rust)
        {
          const char *full_name = dwarf2_full_name (name, die, cu);
 
@@ -13188,7 +13519,20 @@ read_structure_type (struct die_info *die, struct dwarf2_cu *cu)
   attr = dwarf2_attr (die, DW_AT_byte_size, cu);
   if (attr)
     {
-      TYPE_LENGTH (type) = DW_UNSND (attr);
+      if (attr_form_is_constant (attr))
+        TYPE_LENGTH (type) = DW_UNSND (attr);
+      else
+       {
+         /* For the moment, dynamic type sizes are not supported
+            by GDB's struct type.  The actual size is determined
+            on-demand when resolving the type of a given object,
+            so set the type's length to zero for now.  Otherwise,
+            we record an expression as the length, and that expression
+            could lead to a very large value, which could eventually
+            lead to us trying to allocate that much memory when creating
+            a value of that type.  */
+          TYPE_LENGTH (type) = 0;
+       }
     }
   else
     {
@@ -13261,8 +13605,16 @@ process_structure_scope (struct die_info *die, struct dwarf2_cu *cu)
            }
          else if (child_die->tag == DW_TAG_subprogram)
            {
-             /* C++ member function.  */
-             dwarf2_add_member_fn (&fi, child_die, type, cu);
+             /* Rust doesn't have member functions in the C++ sense.
+                However, it does emit ordinary functions as children
+                of a struct DIE.  */
+             if (cu->language == language_rust)
+               read_func_scope (child_die, cu);
+             else
+               {
+                 /* C++ member function.  */
+                 dwarf2_add_member_fn (&fi, child_die, type, cu);
+               }
            }
          else if (child_die->tag == DW_TAG_inheritance)
            {
@@ -13290,9 +13642,9 @@ process_structure_scope (struct die_info *die, struct dwarf2_cu *cu)
          TYPE_N_TEMPLATE_ARGUMENTS (type)
            = VEC_length (symbolp, template_args);
          TYPE_TEMPLATE_ARGUMENTS (type)
-           = obstack_alloc (&objfile->objfile_obstack,
-                            (TYPE_N_TEMPLATE_ARGUMENTS (type)
-                             * sizeof (struct symbol *)));
+           = XOBNEWVEC (&objfile->objfile_obstack,
+                        struct symbol *,
+                        TYPE_N_TEMPLATE_ARGUMENTS (type));
          memcpy (TYPE_TEMPLATE_ARGUMENTS (type),
                  VEC_address (symbolp, template_args),
                  (TYPE_N_TEMPLATE_ARGUMENTS (type)
@@ -13379,7 +13731,8 @@ process_structure_scope (struct die_info *die, struct dwarf2_cu *cu)
 
          ALLOCATE_CPLUS_STRUCT_TYPE (type);
          TYPE_TYPEDEF_FIELD_ARRAY (type)
-           = TYPE_ALLOC (type, sizeof (TYPE_TYPEDEF_FIELD (type, 0)) * i);
+           = ((struct typedef_field *)
+              TYPE_ALLOC (type, sizeof (TYPE_TYPEDEF_FIELD (type, 0)) * i));
          TYPE_TYPEDEF_FIELD_COUNT (type) = i;
 
          /* Reverse the list order to keep the debug info elements order.  */
@@ -13395,9 +13748,6 @@ process_structure_scope (struct die_info *die, struct dwarf2_cu *cu)
        }
 
       do_cleanups (back_to);
-
-      if (HAVE_CPLUS_STRUCT (type))
-       TYPE_CPLUS_REALLY_JAVA (type) = cu->language == language_java;
     }
 
   quirk_gcc_member_function_pointer (type, objfile);
@@ -13663,8 +14013,8 @@ process_enumeration_scope (struct die_info *die, struct dwarf2_cu *cu)
       struct signatured_type *sig_type;
 
       sig_type = (struct signatured_type *) cu->per_cu;
-      gdb_assert (sig_type->type_offset_in_section.sect_off != 0);
-      if (sig_type->type_offset_in_section.sect_off != die->offset.sect_off)
+      gdb_assert (to_underlying (sig_type->type_offset_in_section) != 0);
+      if (sig_type->type_offset_in_section != die->sect_off)
        return;
     }
 
@@ -13807,7 +14157,8 @@ read_array_order (struct die_info *die, struct dwarf2_cu *cu)
 
   attr = dwarf2_attr (die, DW_AT_ordering, cu);
 
-  if (attr) return DW_SND (attr);
+  if (attr)
+    return (enum dwarf_array_dim_ordering) DW_SND (attr);
 
   /* GNU F77 is a special case, as at 08/2004 array type info is the
      opposite order to the dwarf2 specification, but data is still
@@ -13885,8 +14236,7 @@ mark_common_block_symbol_computed (struct symbol *sym,
   gdb_assert (attr_form_is_block (member_loc)
              || attr_form_is_constant (member_loc));
 
-  baton = obstack_alloc (&objfile->objfile_obstack,
-                        sizeof (struct dwarf2_locexpr_baton));
+  baton = XOBNEW (&objfile->objfile_obstack, struct dwarf2_locexpr_baton);
   baton->per_cu = cu->per_cu;
   gdb_assert (baton->per_cu);
 
@@ -13900,11 +14250,11 @@ mark_common_block_symbol_computed (struct symbol *sym,
   else
     baton->size += DW_BLOCK (member_loc)->size;
 
-  ptr = obstack_alloc (&objfile->objfile_obstack, baton->size);
+  ptr = (gdb_byte *) obstack_alloc (&objfile->objfile_obstack, baton->size);
   baton->data = ptr;
 
   *ptr++ = DW_OP_call4;
-  cu_off = common_die->offset.sect_off - cu->per_cu->offset.sect_off;
+  cu_off = common_die->sect_off - cu->per_cu->sect_off;
   store_unsigned_integer (ptr, 4, byte_order, cu_off);
   ptr += 4;
 
@@ -13976,7 +14326,9 @@ read_common_block (struct die_info *die, struct dwarf2_cu *cu)
 
       size = (sizeof (struct common_block)
              + (n_entries - 1) * sizeof (struct symbol *));
-      common_block = obstack_alloc (&objfile->objfile_obstack, size);
+      common_block
+       = (struct common_block *) obstack_alloc (&objfile->objfile_obstack,
+                                                size);
       memset (common_block->contents, 0, n_entries * sizeof (struct symbol *));
       common_block->n_entries = 0;
 
@@ -14005,7 +14357,7 @@ read_common_block (struct die_info *die, struct dwarf2_cu *cu)
                             _("Variable in common block has "
                               "DW_AT_data_member_location "
                               "- DIE at 0x%x [in module %s]"),
-                            child_die->offset.sect_off,
+                            to_underlying (child_die->sect_off),
                             objfile_name (cu->objfile));
 
                  if (attr_form_is_section_offset (member_loc))
@@ -14062,15 +14414,13 @@ read_namespace_type (struct die_info *die, struct dwarf2_cu *cu)
                            previous_prefix, name, 0, cu);
 
   /* Create the type.  */
-  type = init_type (TYPE_CODE_NAMESPACE, 0, 0, NULL,
-                   objfile);
-  TYPE_NAME (type) = name;
+  type = init_type (objfile, TYPE_CODE_NAMESPACE, 0, name);
   TYPE_TAG_NAME (type) = TYPE_NAME (type);
 
   return set_die_type (die, type, cu);
 }
 
-/* Read a C++ namespace.  */
+/* Read a namespace scope.  */
 
 static void
 read_namespace (struct die_info *die, struct dwarf2_cu *cu)
@@ -14094,8 +14444,9 @@ read_namespace (struct die_info *die, struct dwarf2_cu *cu)
        {
          const char *previous_prefix = determine_prefix (die, cu);
 
-         cp_add_using_directive (previous_prefix, TYPE_NAME (type), NULL,
-                                 NULL, NULL, 0, &objfile->objfile_obstack);
+         add_using_directive (using_directives (cu->language),
+                              previous_prefix, TYPE_NAME (type), NULL,
+                              NULL, NULL, 0, &objfile->objfile_obstack);
        }
     }
 
@@ -14126,8 +14477,8 @@ read_module_type (struct die_info *die, struct dwarf2_cu *cu)
   if (!module_name)
     complaint (&symfile_complaints,
               _("DW_TAG_module has no name, offset 0x%x"),
-               die->offset.sect_off);
-  type = init_type (TYPE_CODE_MODULE, 0, 0, module_name, objfile);
+               to_underlying (die->sect_off));
+  type = init_type (objfile, TYPE_CODE_MODULE, 0, module_name);
 
   /* determine_prefix uses TYPE_TAG_NAME.  */
   TYPE_TAG_NAME (type) = TYPE_NAME (type);
@@ -14171,10 +14522,8 @@ namespace_name (struct die_info *die, int *is_anonymous, struct dwarf2_cu *cu)
     {
       /* We don't use dwarf2_name here so that we can detect the absence
         of a name -> anonymous namespace.  */
-      struct attribute *attr = dwarf2_attr (die, DW_AT_name, cu);
+      name = dwarf2_string_attr (die, DW_AT_name, cu);
 
-      if (attr != NULL)
-       name = DW_STRING (attr);
       if (name != NULL)
        break;
     }
@@ -14288,16 +14637,19 @@ read_tag_ptr_to_member_type (struct die_info *die, struct dwarf2_cu *cu)
   return set_die_type (die, type, cu);
 }
 
-/* Extract all information from a DW_TAG_reference_type DIE and add to
+/* Extract all information from a DW_TAG_{rvalue_,}reference_type DIE and add to
    the user defined type vector.  */
 
 static struct type *
-read_tag_reference_type (struct die_info *die, struct dwarf2_cu *cu)
+read_tag_reference_type (struct die_info *die, struct dwarf2_cu *cu,
+                          enum type_code refcode)
 {
   struct comp_unit_head *cu_header = &cu->header;
   struct type *type, *target_type;
   struct attribute *attr;
 
+  gdb_assert (refcode == TYPE_CODE_REF || refcode == TYPE_CODE_RVALUE_REF);
+
   target_type = die_type (die, cu);
 
   /* The die_type call above may have already set the type for this DIE.  */
@@ -14305,7 +14657,7 @@ read_tag_reference_type (struct die_info *die, struct dwarf2_cu *cu)
   if (type)
     return type;
 
-  type = lookup_reference_type (target_type);
+  type = lookup_reference_type (target_type, refcode);
   attr = dwarf2_attr (die, DW_AT_byte_size, cu);
   if (attr)
     {
@@ -14603,19 +14955,7 @@ read_subroutine_type (struct die_info *die, struct dwarf2_cu *cu)
              if (attr)
                TYPE_FIELD_ARTIFICIAL (ftype, iparams) = DW_UNSND (attr);
              else
-               {
-                 TYPE_FIELD_ARTIFICIAL (ftype, iparams) = 0;
-
-                 /* GCC/43521: In java, the formal parameter
-                    "this" is sometimes not marked with DW_AT_artificial.  */
-                 if (cu->language == language_java)
-                   {
-                     const char *name = dwarf2_name (child_die, cu);
-
-                     if (name && !strcmp (name, "this"))
-                       TYPE_FIELD_ARTIFICIAL (ftype, iparams) = 1;
-                   }
-               }
+               TYPE_FIELD_ARTIFICIAL (ftype, iparams) = 0;
              arg_type = die_type (child_die, cu);
 
              /* RealView does not mark THIS as const, which the testsuite
@@ -14667,9 +15007,8 @@ read_typedef (struct die_info *die, struct dwarf2_cu *cu)
   struct type *this_type, *target_type;
 
   name = dwarf2_full_name (NULL, die, cu);
-  this_type = init_type (TYPE_CODE_TYPEDEF, 0,
-                        TYPE_FLAG_TARGET_STUB, NULL, objfile);
-  TYPE_NAME (this_type) = name;
+  this_type = init_type (objfile, TYPE_CODE_TYPEDEF, 0, name);
+  TYPE_TARGET_STUB (this_type) = 1;
   set_die_type (die, this_type, cu);
   target_type = die_type (die, cu);
   if (target_type != this_type)
@@ -14681,12 +15020,33 @@ read_typedef (struct die_info *die, struct dwarf2_cu *cu)
       complaint (&symfile_complaints,
                 _("Self-referential DW_TAG_typedef "
                   "- DIE at 0x%x [in module %s]"),
-                die->offset.sect_off, objfile_name (objfile));
+                to_underlying (die->sect_off), objfile_name (objfile));
       TYPE_TARGET_TYPE (this_type) = NULL;
     }
   return this_type;
 }
 
+/* Allocate a floating-point type of size BITS and name NAME.  Pass NAME_HINT
+   (which may be different from NAME) to the architecture back-end to allow
+   it to guess the correct format if necessary.  */
+
+static struct type *
+dwarf2_init_float_type (struct objfile *objfile, int bits, const char *name,
+                       const char *name_hint)
+{
+  struct gdbarch *gdbarch = get_objfile_arch (objfile);
+  const struct floatformat **format;
+  struct type *type;
+
+  format = gdbarch_floatformat_for_type (gdbarch, name_hint, bits);
+  if (format)
+    type = init_float_type (objfile, bits, name, format);
+  else
+    type = init_type (objfile, TYPE_CODE_ERROR, bits / TARGET_CHAR_BIT, name);
+
+  return type;
+}
+
 /* Find a representation of a given base type and install
    it in the TYPE field of the die.  */
 
@@ -14696,11 +15056,8 @@ read_base_type (struct die_info *die, struct dwarf2_cu *cu)
   struct objfile *objfile = cu->objfile;
   struct type *type;
   struct attribute *attr;
-  int encoding = 0, size = 0;
+  int encoding = 0, bits = 0;
   const char *name;
-  enum type_code code = TYPE_CODE_INT;
-  int type_flags = 0;
-  struct type *target_type = NULL;
 
   attr = dwarf2_attr (die, DW_AT_encoding, cu);
   if (attr)
@@ -14710,7 +15067,7 @@ read_base_type (struct die_info *die, struct dwarf2_cu *cu)
   attr = dwarf2_attr (die, DW_AT_byte_size, cu);
   if (attr)
     {
-      size = DW_UNSND (attr);
+      bits = DW_UNSND (attr) * TARGET_CHAR_BIT;
     }
   name = dwarf2_name (die, cu);
   if (!name)
@@ -14723,61 +15080,64 @@ read_base_type (struct die_info *die, struct dwarf2_cu *cu)
     {
       case DW_ATE_address:
        /* Turn DW_ATE_address into a void * pointer.  */
-       code = TYPE_CODE_PTR;
-       type_flags |= TYPE_FLAG_UNSIGNED;
-       target_type = init_type (TYPE_CODE_VOID, 1, 0, NULL, objfile);
+       type = init_type (objfile, TYPE_CODE_VOID, 1, NULL);
+       type = init_pointer_type (objfile, bits, name, type);
        break;
       case DW_ATE_boolean:
-       code = TYPE_CODE_BOOL;
-       type_flags |= TYPE_FLAG_UNSIGNED;
+       type = init_boolean_type (objfile, bits, 1, name);
        break;
       case DW_ATE_complex_float:
-       code = TYPE_CODE_COMPLEX;
-       target_type = init_type (TYPE_CODE_FLT, size / 2, 0, NULL, objfile);
+       type = dwarf2_init_float_type (objfile, bits / 2, NULL, name);
+       type = init_complex_type (objfile, name, type);
        break;
       case DW_ATE_decimal_float:
-       code = TYPE_CODE_DECFLOAT;
+       type = init_decfloat_type (objfile, bits, name);
        break;
       case DW_ATE_float:
-       code = TYPE_CODE_FLT;
+       type = dwarf2_init_float_type (objfile, bits, name, name);
        break;
       case DW_ATE_signed:
+       type = init_integer_type (objfile, bits, 0, name);
        break;
       case DW_ATE_unsigned:
-       type_flags |= TYPE_FLAG_UNSIGNED;
        if (cu->language == language_fortran
            && name
            && startswith (name, "character("))
-         code = TYPE_CODE_CHAR;
+         type = init_character_type (objfile, bits, 1, name);
+       else
+         type = init_integer_type (objfile, bits, 1, name);
        break;
       case DW_ATE_signed_char:
        if (cu->language == language_ada || cu->language == language_m2
            || cu->language == language_pascal
            || cu->language == language_fortran)
-         code = TYPE_CODE_CHAR;
+         type = init_character_type (objfile, bits, 0, name);
+       else
+         type = init_integer_type (objfile, bits, 0, name);
        break;
       case DW_ATE_unsigned_char:
        if (cu->language == language_ada || cu->language == language_m2
            || cu->language == language_pascal
-           || cu->language == language_fortran)
-         code = TYPE_CODE_CHAR;
-       type_flags |= TYPE_FLAG_UNSIGNED;
+           || cu->language == language_fortran
+           || cu->language == language_rust)
+         type = init_character_type (objfile, bits, 1, name);
+       else
+         type = init_integer_type (objfile, bits, 1, name);
        break;
       case DW_ATE_UTF:
        /* We just treat this as an integer and then recognize the
           type by name elsewhere.  */
+       type = init_integer_type (objfile, bits, 0, name);
        break;
 
       default:
        complaint (&symfile_complaints, _("unsupported DW_AT_encoding: '%s'"),
                   dwarf_type_encoding_name (encoding));
+       type = init_type (objfile, TYPE_CODE_ERROR,
+                         bits / TARGET_CHAR_BIT, name);
        break;
     }
 
-  type = init_type (code, size, type_flags, NULL, objfile);
-  TYPE_NAME (type) = name;
-  TYPE_TARGET_TYPE (type) = target_type;
-
   if (name && strcmp (name, "char") == 0)
     TYPE_NOSIGN (type) = 1;
 
@@ -14800,7 +15160,7 @@ attr_to_dynamic_prop (const struct attribute *attr, struct die_info *die,
 
   if (attr_form_is_block (attr))
     {
-      baton = obstack_alloc (obstack, sizeof (*baton));
+      baton = XOBNEW (obstack, struct dwarf2_property_baton);
       baton->referenced_type = NULL;
       baton->locexpr.per_cu = cu->per_cu;
       baton->locexpr.size = DW_BLOCK (attr)->size;
@@ -14828,7 +15188,7 @@ attr_to_dynamic_prop (const struct attribute *attr, struct die_info *die,
          case DW_AT_location:
            if (attr_form_is_section_offset (target_attr))
              {
-               baton = obstack_alloc (obstack, sizeof (*baton));
+               baton = XOBNEW (obstack, struct dwarf2_property_baton);
                baton->referenced_type = die_type (target_die, target_cu);
                fill_in_loclist_baton (cu, &baton->loclist, target_attr);
                prop->data.baton = baton;
@@ -14837,7 +15197,7 @@ attr_to_dynamic_prop (const struct attribute *attr, struct die_info *die,
              }
            else if (attr_form_is_block (target_attr))
              {
-               baton = obstack_alloc (obstack, sizeof (*baton));
+               baton = XOBNEW (obstack, struct dwarf2_property_baton);
                baton->referenced_type = die_type (target_die, target_cu);
                baton->locexpr.per_cu = cu->per_cu;
                baton->locexpr.size = DW_BLOCK (target_attr)->size;
@@ -14861,7 +15221,7 @@ attr_to_dynamic_prop (const struct attribute *attr, struct die_info *die,
                                                &offset))
                return 0;
 
-             baton = obstack_alloc (obstack, sizeof (*baton));
+             baton = XOBNEW (obstack, struct dwarf2_property_baton);
              baton->referenced_type = read_type_die (target_die->parent,
                                                      target_cu);
              baton->offset_info.offset = offset;
@@ -14931,8 +15291,8 @@ read_subrange_type (struct die_info *die, struct dwarf2_cu *cu)
       low_default_is_valid = 1;
       break;
     case language_d:
-    case language_java:
     case language_objc:
+    case language_rust:
       low.data.const_val = 0;
       low_default_is_valid = (cu->header.version >= 4);
       break;
@@ -14954,7 +15314,7 @@ read_subrange_type (struct die_info *die, struct dwarf2_cu *cu)
   else if (!low_default_is_valid)
     complaint (&symfile_complaints, _("Missing DW_AT_lower_bound "
                                      "- DIE at 0x%x [in module %s]"),
-              die->offset.sect_off, objfile_name (cu->objfile));
+              to_underlying (die->sect_off), objfile_name (cu->objfile));
 
   attr = dwarf2_attr (die, DW_AT_upper_bound, cu);
   if (!attr_to_dynamic_prop (attr, die, cu, &high))
@@ -15016,7 +15376,7 @@ read_subrange_type (struct die_info *die, struct dwarf2_cu *cu)
      the bounds as signed, and thus sign-extend their values, when
      the base type is signed.  */
   negative_mask =
-    (LONGEST) -1 << (TYPE_LENGTH (base_type) * TARGET_CHAR_BIT - 1);
+    -((LONGEST) 1 << (TYPE_LENGTH (base_type) * TARGET_CHAR_BIT - 1));
   if (low.kind == PROP_CONST
       && !TYPE_UNSIGNED (base_type) && (low.data.const_val & negative_mask))
     low.data.const_val |= negative_mask;
@@ -15056,7 +15416,7 @@ read_unspecified_type (struct die_info *die, struct dwarf2_cu *cu)
 
   /* For now, we only support the C meaning of an unspecified type: void.  */
 
-  type = init_type (TYPE_CODE_VOID, 0, 0, NULL, cu->objfile);
+  type = init_type (cu->objfile, TYPE_CODE_VOID, 0, NULL);
   TYPE_NAME (type) = dwarf2_name (die, cu);
 
   return set_die_type (die, type, cu);
@@ -15176,13 +15536,12 @@ read_full_die_1 (const struct die_reader_specs *reader,
                 int *has_children, int num_extra_attrs)
 {
   unsigned int abbrev_number, bytes_read, i;
-  sect_offset offset;
   struct abbrev_info *abbrev;
   struct die_info *die;
   struct dwarf2_cu *cu = reader->cu;
   bfd *abfd = reader->abfd;
 
-  offset.sect_off = info_ptr - reader->buffer;
+  sect_offset sect_off = (sect_offset) (info_ptr - reader->buffer);
   abbrev_number = read_unsigned_leb128 (abfd, info_ptr, &bytes_read);
   info_ptr += bytes_read;
   if (!abbrev_number)
@@ -15199,7 +15558,7 @@ read_full_die_1 (const struct die_reader_specs *reader,
           bfd_get_filename (abfd));
 
   die = dwarf_alloc_die (cu, abbrev->num_attrs + num_extra_attrs);
-  die->offset = offset;
+  die->sect_off = sect_off;
   die->tag = abbrev->tag;
   die->abbrev = abbrev_number;
 
@@ -15258,9 +15617,9 @@ abbrev_table_alloc_abbrev (struct abbrev_table *abbrev_table)
 {
   struct abbrev_info *abbrev;
 
-  abbrev = (struct abbrev_info *)
-    obstack_alloc (&abbrev_table->abbrev_obstack, sizeof (struct abbrev_info));
+  abbrev = XOBNEW (&abbrev_table->abbrev_obstack, struct abbrev_info);
   memset (abbrev, 0, sizeof (struct abbrev_info));
+
   return abbrev;
 }
 
@@ -15304,7 +15663,7 @@ abbrev_table_lookup_abbrev (const struct abbrev_table *abbrev_table,
 
 static struct abbrev_table *
 abbrev_table_read_table (struct dwarf2_section_info *section,
-                        sect_offset offset)
+                        sect_offset sect_off)
 {
   struct objfile *objfile = dwarf2_per_objfile->objfile;
   bfd *abfd = get_section_bfd_owner (section);
@@ -15317,21 +15676,21 @@ abbrev_table_read_table (struct dwarf2_section_info *section,
   unsigned int allocated_attrs;
 
   abbrev_table = XNEW (struct abbrev_table);
-  abbrev_table->offset = offset;
+  abbrev_table->sect_off = sect_off;
   obstack_init (&abbrev_table->abbrev_obstack);
-  abbrev_table->abbrevs = obstack_alloc (&abbrev_table->abbrev_obstack,
-                                        (ABBREV_HASH_SIZE
-                                         * sizeof (struct abbrev_info *)));
+  abbrev_table->abbrevs =
+    XOBNEWVEC (&abbrev_table->abbrev_obstack, struct abbrev_info *,
+              ABBREV_HASH_SIZE);
   memset (abbrev_table->abbrevs, 0,
          ABBREV_HASH_SIZE * sizeof (struct abbrev_info *));
 
   dwarf2_read_section (objfile, section);
-  abbrev_ptr = section->buffer + offset.sect_off;
+  abbrev_ptr = section->buffer + to_underlying (sect_off);
   abbrev_number = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
   abbrev_ptr += bytes_read;
 
   allocated_attrs = ATTR_ALLOC_CHUNK;
-  cur_attrs = xmalloc (allocated_attrs * sizeof (struct attr_abbrev));
+  cur_attrs = XNEWVEC (struct attr_abbrev, allocated_attrs);
 
   /* Loop until we reach an abbrev number of 0.  */
   while (abbrev_number)
@@ -15340,37 +15699,54 @@ abbrev_table_read_table (struct dwarf2_section_info *section,
 
       /* read in abbrev header */
       cur_abbrev->number = abbrev_number;
-      cur_abbrev->tag = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
+      cur_abbrev->tag
+       = (enum dwarf_tag) read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
       abbrev_ptr += bytes_read;
       cur_abbrev->has_children = read_1_byte (abfd, abbrev_ptr);
       abbrev_ptr += 1;
 
       /* now read in declarations */
-      abbrev_name = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
-      abbrev_ptr += bytes_read;
-      abbrev_form = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
-      abbrev_ptr += bytes_read;
-      while (abbrev_name)
+      for (;;)
        {
+         LONGEST implicit_const;
+
+         abbrev_name = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
+         abbrev_ptr += bytes_read;
+         abbrev_form = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
+         abbrev_ptr += bytes_read;
+         if (abbrev_form == DW_FORM_implicit_const)
+           {
+             implicit_const = read_signed_leb128 (abfd, abbrev_ptr,
+                                                  &bytes_read);
+             abbrev_ptr += bytes_read;
+           }
+         else
+           {
+             /* Initialize it due to a false compiler warning.  */
+             implicit_const = -1;
+           }
+
+         if (abbrev_name == 0)
+           break;
+
          if (cur_abbrev->num_attrs == allocated_attrs)
            {
              allocated_attrs += ATTR_ALLOC_CHUNK;
              cur_attrs
-               = xrealloc (cur_attrs, (allocated_attrs
-                                       * sizeof (struct attr_abbrev)));
+               = XRESIZEVEC (struct attr_abbrev, cur_attrs, allocated_attrs);
            }
 
-         cur_attrs[cur_abbrev->num_attrs].name = abbrev_name;
-         cur_attrs[cur_abbrev->num_attrs++].form = abbrev_form;
-         abbrev_name = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
-         abbrev_ptr += bytes_read;
-         abbrev_form = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
-         abbrev_ptr += bytes_read;
+         cur_attrs[cur_abbrev->num_attrs].name
+           = (enum dwarf_attribute) abbrev_name;
+         cur_attrs[cur_abbrev->num_attrs].form
+           = (enum dwarf_form) abbrev_form;
+         cur_attrs[cur_abbrev->num_attrs].implicit_const = implicit_const;
+         ++cur_abbrev->num_attrs;
        }
 
-      cur_abbrev->attrs = obstack_alloc (&abbrev_table->abbrev_obstack,
-                                        (cur_abbrev->num_attrs
-                                         * sizeof (struct attr_abbrev)));
+      cur_abbrev->attrs =
+       XOBNEWVEC (&abbrev_table->abbrev_obstack, struct attr_abbrev,
+                  cur_abbrev->num_attrs);
       memcpy (cur_abbrev->attrs, cur_attrs,
              cur_abbrev->num_attrs * sizeof (struct attr_abbrev));
 
@@ -15412,7 +15788,7 @@ abbrev_table_free (struct abbrev_table *abbrev_table)
 static void
 abbrev_table_free_cleanup (void *table_ptr)
 {
-  struct abbrev_table **abbrev_table_ptr = table_ptr;
+  struct abbrev_table **abbrev_table_ptr = (struct abbrev_table **) table_ptr;
 
   if (*abbrev_table_ptr != NULL)
     abbrev_table_free (*abbrev_table_ptr);
@@ -15426,7 +15802,7 @@ dwarf2_read_abbrevs (struct dwarf2_cu *cu,
                     struct dwarf2_section_info *abbrev_section)
 {
   cu->abbrev_table =
-    abbrev_table_read_table (abbrev_section, cu->header.abbrev_offset);
+    abbrev_table_read_table (abbrev_section, cu->header.abbrev_sect_off);
 }
 
 /* Release the memory used by the abbrev table for a compilation unit.  */
@@ -15434,7 +15810,7 @@ dwarf2_read_abbrevs (struct dwarf2_cu *cu,
 static void
 dwarf2_free_abbrev_table (void *ptr_to_cu)
 {
-  struct dwarf2_cu *cu = ptr_to_cu;
+  struct dwarf2_cu *cu = (struct dwarf2_cu *) ptr_to_cu;
 
   if (cu->abbrev_table != NULL)
     abbrev_table_free (cu->abbrev_table);
@@ -15506,8 +15882,7 @@ load_partial_dies (const struct die_reader_specs *reader,
                            hashtab_obstack_allocate,
                            dummy_obstack_deallocate);
 
-  part_die = obstack_alloc (&cu->comp_unit_obstack,
-                           sizeof (struct partial_die_info));
+  part_die = XOBNEW (&cu->comp_unit_obstack, struct partial_die_info);
 
   while (1)
     {
@@ -15612,7 +15987,7 @@ load_partial_dies (const struct die_reader_specs *reader,
            add_psymbol_to_list (part_die->name, strlen (part_die->name), 0,
                                 VAR_DOMAIN, LOC_TYPEDEF,
                                 &objfile->static_psymbols,
-                                0, (CORE_ADDR) 0, cu->language, objfile);
+                                0, cu->language, objfile);
          info_ptr = locate_pdi_sibling (reader, part_die, info_ptr);
          continue;
        }
@@ -15629,7 +16004,7 @@ load_partial_dies (const struct die_reader_specs *reader,
        complaint (&symfile_complaints,
                   _("DW_TAG_typedef has childen - GCC PR debug/47510 bug "
                     "- DIE at 0x%x [in module %s]"),
-                  part_die->offset.sect_off, objfile_name (objfile));
+                  to_underlying (part_die->sect_off), objfile_name (objfile));
 
       /* If we're at the second level, and we're an enumerator, and
         our parent has no specification (meaning possibly lives in a
@@ -15647,11 +16022,10 @@ load_partial_dies (const struct die_reader_specs *reader,
          else if (building_psymtab)
            add_psymbol_to_list (part_die->name, strlen (part_die->name), 0,
                                 VAR_DOMAIN, LOC_CONST,
-                                (cu->language == language_cplus
-                                 || cu->language == language_java)
+                                cu->language == language_cplus
                                 ? &objfile->global_psymbols
                                 : &objfile->static_psymbols,
-                                0, (CORE_ADDR) 0, cu->language, objfile);
+                                0, cu->language, objfile);
 
          info_ptr = locate_pdi_sibling (reader, part_die, info_ptr);
          continue;
@@ -15703,12 +16077,12 @@ load_partial_dies (const struct die_reader_specs *reader,
          void **slot;
 
          slot = htab_find_slot_with_hash (cu->partial_dies, part_die,
-                                          part_die->offset.sect_off, INSERT);
+                                          to_underlying (part_die->sect_off),
+                                          INSERT);
          *slot = part_die;
        }
 
-      part_die = obstack_alloc (&cu->comp_unit_obstack,
-                               sizeof (struct partial_die_info));
+      part_die = XOBNEW (&cu->comp_unit_obstack, struct partial_die_info);
 
       /* For some DIEs we want to follow their children (if any).  For C
         we have no reason to follow the children of structures; for other
@@ -15771,7 +16145,7 @@ read_partial_die (const struct die_reader_specs *reader,
 
   memset (part_die, 0, sizeof (struct partial_die_info));
 
-  part_die->offset.sect_off = info_ptr - buffer;
+  part_die->sect_off = (sect_offset) (info_ptr - buffer);
 
   info_ptr += abbrev_len;
 
@@ -15870,8 +16244,8 @@ read_partial_die (const struct die_reader_specs *reader,
                       _("ignoring absolute DW_AT_sibling"));
          else
            {
-             unsigned int off = dwarf2_get_ref_die_offset (&attr).sect_off;
-             const gdb_byte *sibling_ptr = buffer + off;
+             sect_offset off = dwarf2_get_ref_die_offset (&attr);
+             const gdb_byte *sibling_ptr = buffer + to_underlying (off);
 
              if (sibling_ptr < info_ptr)
                complaint (&symfile_complaints,
@@ -15894,18 +16268,18 @@ read_partial_die (const struct die_reader_specs *reader,
             to describe functions' calling conventions.
 
             However, because it's a necessary piece of information in
-            Fortran, and because DW_CC_program is the only piece of debugging
-            information whose definition refers to a 'main program' at all,
-            several compilers have begun marking Fortran main programs with
-            DW_CC_program --- even when those functions use the standard
-            calling conventions.
-
-            So until DWARF specifies a way to provide this information and
-            compilers pick up the new representation, we'll support this
-            practice.  */
+            Fortran, and before DWARF 4 DW_CC_program was the only
+            piece of debugging information whose definition refers to
+            a 'main program' at all, several compilers marked Fortran
+            main programs with DW_CC_program --- even when those
+            functions use the standard calling conventions.
+
+            Although DWARF now specifies a way to provide this
+            information, we support this practice for backward
+            compatibility.  */
          if (DW_UNSND (&attr) == DW_CC_program
              && cu->language == language_fortran)
-           set_objfile_main_name (objfile, part_die->name, language_fortran);
+           part_die->main_subprogram = 1;
          break;
        case DW_AT_inline:
          if (DW_UNSND (&attr) == DW_INL_inlined
@@ -15916,12 +16290,16 @@ read_partial_die (const struct die_reader_specs *reader,
        case DW_AT_import:
          if (part_die->tag == DW_TAG_imported_unit)
            {
-             part_die->d.offset = dwarf2_get_ref_die_offset (&attr);
+             part_die->d.sect_off = dwarf2_get_ref_die_offset (&attr);
              part_die->is_dwz = (attr.form == DW_FORM_GNU_ref_alt
                                  || cu->per_cu->is_dwz);
            }
          break;
 
+       case DW_AT_main_subprogram:
+         part_die->main_subprogram = DW_UNSND (&attr);
+         break;
+
        default:
          break;
        }
@@ -15948,7 +16326,7 @@ read_partial_die (const struct die_reader_specs *reader,
                     _("DW_AT_low_pc %s is zero "
                       "for DIE at 0x%x [in module %s]"),
                     paddress (gdbarch, part_die->lowpc),
-                    part_die->offset.sect_off, objfile_name (objfile));
+                    to_underlying (part_die->sect_off), objfile_name (objfile));
        }
       /* dwarf2_get_pc_bounds has also the strict low < high requirement.  */
       else if (part_die->lowpc >= part_die->highpc)
@@ -15960,7 +16338,8 @@ read_partial_die (const struct die_reader_specs *reader,
                       "for DIE at 0x%x [in module %s]"),
                     paddress (gdbarch, part_die->lowpc),
                     paddress (gdbarch, part_die->highpc),
-                    part_die->offset.sect_off, objfile_name (objfile));
+                    to_underlying (part_die->sect_off),
+                    objfile_name (objfile));
        }
       else
        part_die->has_pc_info = 1;
@@ -15972,14 +16351,15 @@ read_partial_die (const struct die_reader_specs *reader,
 /* Find a cached partial DIE at OFFSET in CU.  */
 
 static struct partial_die_info *
-find_partial_die_in_comp_unit (sect_offset offset, struct dwarf2_cu *cu)
+find_partial_die_in_comp_unit (sect_offset sect_off, struct dwarf2_cu *cu)
 {
   struct partial_die_info *lookup_die = NULL;
   struct partial_die_info part_die;
 
-  part_die.offset = offset;
-  lookup_die = htab_find_with_hash (cu->partial_dies, &part_die,
-                                   offset.sect_off);
+  part_die.sect_off = sect_off;
+  lookup_die = ((struct partial_die_info *)
+               htab_find_with_hash (cu->partial_dies, &part_die,
+                                    to_underlying (sect_off)));
 
   return lookup_die;
 }
@@ -15990,16 +16370,16 @@ find_partial_die_in_comp_unit (sect_offset offset, struct dwarf2_cu *cu)
    DW_FORM_ref_sig8).  */
 
 static struct partial_die_info *
-find_partial_die (sect_offset offset, int offset_in_dwz, struct dwarf2_cu *cu)
+find_partial_die (sect_offset sect_off, int offset_in_dwz, struct dwarf2_cu *cu)
 {
   struct objfile *objfile = cu->objfile;
   struct dwarf2_per_cu_data *per_cu = NULL;
   struct partial_die_info *pd = NULL;
 
   if (offset_in_dwz == cu->per_cu->is_dwz
-      && offset_in_cu_p (&cu->header, offset))
+      && offset_in_cu_p (&cu->header, sect_off))
     {
-      pd = find_partial_die_in_comp_unit (offset, cu);
+      pd = find_partial_die_in_comp_unit (sect_off, cu);
       if (pd != NULL)
        return pd;
       /* We missed recording what we needed.
@@ -16011,19 +16391,19 @@ find_partial_die (sect_offset offset, int offset_in_dwz, struct dwarf2_cu *cu)
       /* TUs don't reference other CUs/TUs (except via type signatures).  */
       if (cu->per_cu->is_debug_types)
        {
-         error (_("Dwarf Error: Type Unit at offset 0x%lx contains"
-                  " external reference to offset 0x%lx [in module %s].\n"),
-                (long) cu->header.offset.sect_off, (long) offset.sect_off,
+         error (_("Dwarf Error: Type Unit at offset 0x%x contains"
+                  " external reference to offset 0x%x [in module %s].\n"),
+                to_underlying (cu->header.sect_off), to_underlying (sect_off),
                 bfd_get_filename (objfile->obfd));
        }
-      per_cu = dwarf2_find_containing_comp_unit (offset, offset_in_dwz,
+      per_cu = dwarf2_find_containing_comp_unit (sect_off, offset_in_dwz,
                                                 objfile);
 
       if (per_cu->cu == NULL || per_cu->cu->partial_dies == NULL)
        load_partial_comp_unit (per_cu);
 
       per_cu->cu->last_used = 0;
-      pd = find_partial_die_in_comp_unit (offset, per_cu->cu);
+      pd = find_partial_die_in_comp_unit (sect_off, per_cu->cu);
     }
 
   /* If we didn't find it, and not all dies have been loaded,
@@ -16041,14 +16421,14 @@ find_partial_die (sect_offset offset, int offset_in_dwz, struct dwarf2_cu *cu)
         set.  */
       load_partial_comp_unit (per_cu);
 
-      pd = find_partial_die_in_comp_unit (offset, per_cu->cu);
+      pd = find_partial_die_in_comp_unit (sect_off, per_cu->cu);
     }
 
   if (pd == NULL)
     internal_error (__FILE__, __LINE__,
                    _("could not find partial DIE 0x%x "
                      "in cache [from module %s]\n"),
-                   offset.sect_off, bfd_get_filename (objfile->obfd));
+                   to_underlying (sect_off), bfd_get_filename (objfile->obfd));
   return pd;
 }
 
@@ -16094,9 +16474,10 @@ guess_partial_die_structure_name (struct partial_die_info *struct_pdi,
          if (actual_class_name != NULL)
            {
              struct_pdi->name
-               = obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
-                                actual_class_name,
-                                strlen (actual_class_name));
+               = ((const char *)
+                  obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
+                                 actual_class_name,
+                                 strlen (actual_class_name)));
              xfree (actual_class_name);
            }
          break;
@@ -16181,8 +16562,9 @@ fixup_partial_die (struct partial_die_info *part_die,
            base = demangled;
 
          part_die->name
-           = obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
-                            base, strlen (base));
+           = ((const char *)
+              obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
+                             base, strlen (base)));
          xfree (demangled);
        }
     }
@@ -16195,7 +16577,7 @@ fixup_partial_die (struct partial_die_info *part_die,
 static const gdb_byte *
 read_attribute_value (const struct die_reader_specs *reader,
                      struct attribute *attr, unsigned form,
-                     const gdb_byte *info_ptr)
+                     LONGEST implicit_const, const gdb_byte *info_ptr)
 {
   struct dwarf2_cu *cu = reader->cu;
   struct objfile *objfile = cu->objfile;
@@ -16205,7 +16587,7 @@ read_attribute_value (const struct die_reader_specs *reader,
   unsigned int bytes_read;
   struct dwarf_block *blk;
 
-  attr->form = form;
+  attr->form = (enum dwarf_form) form;
   switch (form)
     {
     case DW_FORM_ref_addr:
@@ -16253,6 +16635,13 @@ read_attribute_value (const struct die_reader_specs *reader,
       DW_UNSND (attr) = read_8_bytes (abfd, info_ptr);
       info_ptr += 8;
       break;
+    case DW_FORM_data16:
+      blk = dwarf_alloc_block (cu);
+      blk->size = 16;
+      blk->data = read_n_bytes (abfd, info_ptr, 16);
+      info_ptr += 16;
+      DW_BLOCK (attr) = blk;
+      break;
     case DW_FORM_sec_offset:
       DW_UNSND (attr) = read_offset (abfd, info_ptr, &cu->header, &bytes_read);
       info_ptr += bytes_read;
@@ -16272,6 +16661,16 @@ read_attribute_value (const struct die_reader_specs *reader,
          break;
        }
       /* FALLTHROUGH */
+    case DW_FORM_line_strp:
+      if (!cu->per_cu->is_dwz)
+       {
+         DW_STRING (attr) = read_indirect_line_string (abfd, info_ptr,
+                                                       cu_header, &bytes_read);
+         DW_STRING_IS_CANONICAL (attr) = 0;
+         info_ptr += bytes_read;
+         break;
+       }
+      /* FALLTHROUGH */
     case DW_FORM_GNU_strp_alt:
       {
        struct dwz_file *dwz = dwarf2_get_dwz_file ();
@@ -16320,22 +16719,22 @@ read_attribute_value (const struct die_reader_specs *reader,
       info_ptr += bytes_read;
       break;
     case DW_FORM_ref1:
-      DW_UNSND (attr) = (cu->header.offset.sect_off
+      DW_UNSND (attr) = (to_underlying (cu->header.sect_off)
                         + read_1_byte (abfd, info_ptr));
       info_ptr += 1;
       break;
     case DW_FORM_ref2:
-      DW_UNSND (attr) = (cu->header.offset.sect_off
+      DW_UNSND (attr) = (to_underlying (cu->header.sect_off)
                         + read_2_bytes (abfd, info_ptr));
       info_ptr += 2;
       break;
     case DW_FORM_ref4:
-      DW_UNSND (attr) = (cu->header.offset.sect_off
+      DW_UNSND (attr) = (to_underlying (cu->header.sect_off)
                         + read_4_bytes (abfd, info_ptr));
       info_ptr += 4;
       break;
     case DW_FORM_ref8:
-      DW_UNSND (attr) = (cu->header.offset.sect_off
+      DW_UNSND (attr) = (to_underlying (cu->header.sect_off)
                         + read_8_bytes (abfd, info_ptr));
       info_ptr += 8;
       break;
@@ -16344,14 +16743,23 @@ read_attribute_value (const struct die_reader_specs *reader,
       info_ptr += 8;
       break;
     case DW_FORM_ref_udata:
-      DW_UNSND (attr) = (cu->header.offset.sect_off
+      DW_UNSND (attr) = (to_underlying (cu->header.sect_off)
                         + read_unsigned_leb128 (abfd, info_ptr, &bytes_read));
       info_ptr += bytes_read;
       break;
     case DW_FORM_indirect:
       form = read_unsigned_leb128 (abfd, info_ptr, &bytes_read);
       info_ptr += bytes_read;
-      info_ptr = read_attribute_value (reader, attr, form, info_ptr);
+      if (form == DW_FORM_implicit_const)
+       {
+         implicit_const = read_signed_leb128 (abfd, info_ptr, &bytes_read);
+         info_ptr += bytes_read;
+       }
+      info_ptr = read_attribute_value (reader, attr, form, implicit_const,
+                                      info_ptr);
+      break;
+    case DW_FORM_implicit_const:
+      DW_SND (attr) = implicit_const;
       break;
     case DW_FORM_GNU_addr_index:
       if (reader->dwo_file == NULL)
@@ -16421,7 +16829,8 @@ read_attribute (const struct die_reader_specs *reader,
                const gdb_byte *info_ptr)
 {
   attr->name = abbrev->name;
-  return read_attribute_value (reader, attr, abbrev->form, info_ptr);
+  return read_attribute_value (reader, attr, abbrev->form,
+                              abbrev->implicit_const, info_ptr);
 }
 
 /* Read dwarf information from a buffer.  */
@@ -16674,21 +17083,47 @@ read_direct_string (bfd *abfd, const gdb_byte *buf,
   return (const char *) buf;
 }
 
+/* Return pointer to string at section SECT offset STR_OFFSET with error
+   reporting strings FORM_NAME and SECT_NAME.  */
+
 static const char *
-read_indirect_string_at_offset (bfd *abfd, LONGEST str_offset)
-{
-  dwarf2_read_section (dwarf2_per_objfile->objfile, &dwarf2_per_objfile->str);
-  if (dwarf2_per_objfile->str.buffer == NULL)
-    error (_("DW_FORM_strp used without .debug_str section [in module %s]"),
-          bfd_get_filename (abfd));
-  if (str_offset >= dwarf2_per_objfile->str.size)
-    error (_("DW_FORM_strp pointing outside of "
-            ".debug_str section [in module %s]"),
-          bfd_get_filename (abfd));
+read_indirect_string_at_offset_from (bfd *abfd, LONGEST str_offset,
+                                    struct dwarf2_section_info *sect,
+                                    const char *form_name,
+                                    const char *sect_name)
+{
+  dwarf2_read_section (dwarf2_per_objfile->objfile, sect);
+  if (sect->buffer == NULL)
+    error (_("%s used without %s section [in module %s]"),
+          form_name, sect_name, bfd_get_filename (abfd));
+  if (str_offset >= sect->size)
+    error (_("%s pointing outside of %s section [in module %s]"),
+          form_name, sect_name, bfd_get_filename (abfd));
   gdb_assert (HOST_CHAR_BIT == 8);
-  if (dwarf2_per_objfile->str.buffer[str_offset] == '\0')
+  if (sect->buffer[str_offset] == '\0')
     return NULL;
-  return (const char *) (dwarf2_per_objfile->str.buffer + str_offset);
+  return (const char *) (sect->buffer + str_offset);
+}
+
+/* Return pointer to string at .debug_str offset STR_OFFSET.  */
+
+static const char *
+read_indirect_string_at_offset (bfd *abfd, LONGEST str_offset)
+{
+  return read_indirect_string_at_offset_from (abfd, str_offset,
+                                             &dwarf2_per_objfile->str,
+                                             "DW_FORM_strp", ".debug_str");
+}
+
+/* Return pointer to string at .debug_line_str offset STR_OFFSET.  */
+
+static const char *
+read_indirect_line_string_at_offset (bfd *abfd, LONGEST str_offset)
+{
+  return read_indirect_string_at_offset_from (abfd, str_offset,
+                                             &dwarf2_per_objfile->line_str,
+                                             "DW_FORM_line_strp",
+                                             ".debug_line_str");
 }
 
 /* Read a string at offset STR_OFFSET in the .debug_str section from
@@ -16715,6 +17150,10 @@ read_indirect_string_from_dwz (struct dwz_file *dwz, LONGEST str_offset)
   return (const char *) (dwz->str.buffer + str_offset);
 }
 
+/* Return pointer to string at .debug_str offset as read from BUF.
+   BUF is assumed to be in a compilation unit described by CU_HEADER.
+   Return *BYTES_READ_PTR count of bytes read from BUF.  */
+
 static const char *
 read_indirect_string (bfd *abfd, const gdb_byte *buf,
                      const struct comp_unit_head *cu_header,
@@ -16725,19 +17164,32 @@ read_indirect_string (bfd *abfd, const gdb_byte *buf,
   return read_indirect_string_at_offset (abfd, str_offset);
 }
 
-static ULONGEST
+/* Return pointer to string at .debug_line_str offset as read from BUF.
+   BUF is assumed to be in a compilation unit described by CU_HEADER.
+   Return *BYTES_READ_PTR count of bytes read from BUF.  */
+
+static const char *
+read_indirect_line_string (bfd *abfd, const gdb_byte *buf,
+                          const struct comp_unit_head *cu_header,
+                          unsigned int *bytes_read_ptr)
+{
+  LONGEST str_offset = read_offset (abfd, buf, cu_header, bytes_read_ptr);
+
+  return read_indirect_line_string_at_offset (abfd, str_offset);
+}
+
+ULONGEST
 read_unsigned_leb128 (bfd *abfd, const gdb_byte *buf,
-                     unsigned int *bytes_read_ptr)
+                         unsigned int *bytes_read_ptr)
 {
   ULONGEST result;
   unsigned int num_read;
-  int i, shift;
+  int shift;
   unsigned char byte;
 
   result = 0;
   shift = 0;
   num_read = 0;
-  i = 0;
   while (1)
     {
       byte = bfd_get_8 (abfd, buf);
@@ -16759,13 +17211,12 @@ read_signed_leb128 (bfd *abfd, const gdb_byte *buf,
                    unsigned int *bytes_read_ptr)
 {
   LONGEST result;
-  int i, shift, num_read;
+  int shift, num_read;
   unsigned char byte;
 
   result = 0;
   shift = 0;
   num_read = 0;
-  i = 0;
   while (1)
     {
       byte = bfd_get_8 (abfd, buf);
@@ -16931,16 +17382,16 @@ read_str_index (const struct die_reader_specs *reader, ULONGEST str_index)
   dwarf2_read_section (objfile, str_offsets_section);
   if (str_section->buffer == NULL)
     error (_("%s used without .debug_str.dwo section"
-            " in CU at offset 0x%lx [in module %s]"),
-          form_name, (long) cu->header.offset.sect_off, objf_name);
+            " in CU at offset 0x%x [in module %s]"),
+          form_name, to_underlying (cu->header.sect_off), objf_name);
   if (str_offsets_section->buffer == NULL)
     error (_("%s used without .debug_str_offsets.dwo section"
-            " in CU at offset 0x%lx [in module %s]"),
-          form_name, (long) cu->header.offset.sect_off, objf_name);
+            " in CU at offset 0x%x [in module %s]"),
+          form_name, to_underlying (cu->header.sect_off), objf_name);
   if (str_index * cu->header.offset_size >= str_offsets_section->size)
     error (_("%s pointing outside of .debug_str_offsets.dwo"
-            " section in CU at offset 0x%lx [in module %s]"),
-          form_name, (long) cu->header.offset.sect_off, objf_name);
+            " section in CU at offset 0x%x [in module %s]"),
+          form_name, to_underlying (cu->header.sect_off), objf_name);
   info_ptr = (str_offsets_section->buffer
              + str_index * cu->header.offset_size);
   if (cu->header.offset_size == 4)
@@ -16949,8 +17400,8 @@ read_str_index (const struct die_reader_specs *reader, ULONGEST str_index)
     str_offset = bfd_get_64 (abfd, info_ptr);
   if (str_offset >= str_section->size)
     error (_("Offset from %s pointing outside of"
-            " .debug_str.dwo section in CU at offset 0x%lx [in module %s]"),
-          form_name, (long) cu->header.offset.sect_off, objf_name);
+            " .debug_str.dwo section in CU at offset 0x%x [in module %s]"),
+          form_name, to_underlying (cu->header.sect_off), objf_name);
   return (const char *) (str_section->buffer + str_offset);
 }
 
@@ -16982,6 +17433,7 @@ set_cu_language (unsigned int lang, struct dwarf2_cu *cu)
     case DW_LANG_UPC:
       cu->language = language_c;
       break;
+    case DW_LANG_Java:
     case DW_LANG_C_plus_plus:
     case DW_LANG_C_plus_plus_11:
     case DW_LANG_C_plus_plus_14:
@@ -17003,9 +17455,6 @@ set_cu_language (unsigned int lang, struct dwarf2_cu *cu)
     case DW_LANG_Mips_Assembler:
       cu->language = language_asm;
       break;
-    case DW_LANG_Java:
-      cu->language = language_java;
-      break;
     case DW_LANG_Ada83:
     case DW_LANG_Ada95:
       cu->language = language_ada;
@@ -17019,6 +17468,10 @@ set_cu_language (unsigned int lang, struct dwarf2_cu *cu)
     case DW_LANG_ObjC:
       cu->language = language_objc;
       break;
+    case DW_LANG_Rust:
+    case DW_LANG_Rust_old:
+      cu->language = language_rust;
+      break;
     case DW_LANG_Cobol74:
     case DW_LANG_Cobol85:
     default:
@@ -17074,6 +17527,33 @@ dwarf2_attr_no_follow (struct die_info *die, unsigned int name)
   return NULL;
 }
 
+/* Return the string associated with a string-typed attribute, or NULL if it
+   is either not found or is of an incorrect type.  */
+
+static const char *
+dwarf2_string_attr (struct die_info *die, unsigned int name, struct dwarf2_cu *cu)
+{
+  struct attribute *attr;
+  const char *str = NULL;
+
+  attr = dwarf2_attr (die, name, cu);
+
+  if (attr != NULL)
+    {
+      if (attr->form == DW_FORM_strp || attr->form == DW_FORM_line_strp
+         || attr->form == DW_FORM_string || attr->form == DW_FORM_GNU_strp_alt)
+       str = DW_STRING (attr);
+      else
+        complaint (&symfile_complaints,
+                  _("string type expected for attribute %s for "
+                    "DIE at 0x%x in module %s"),
+                  dwarf_attr_name (name), to_underlying (die->sect_off),
+                  objfile_name (cu->objfile));
+    }
+
+  return str;
+}
+
 /* Return non-zero iff the attribute NAME is defined for the given DIE,
    and holds a non-zero value.  This function should only be used for
    DW_FORM_flag or DW_FORM_flag_present attributes.  */
@@ -17121,125 +17601,189 @@ die_specification (struct die_info *die, struct dwarf2_cu **spec_cu)
     return follow_die_ref (die, spec_attr, spec_cu);
 }
 
-/* Free the line_header structure *LH, and any arrays and strings it
-   refers to.
-   NOTE: This is also used as a "cleanup" function.  */
+/* Stub for free_line_header to match void * callback types.  */
 
 static void
-free_line_header (struct line_header *lh)
+free_line_header_voidp (void *arg)
 {
-  if (lh->standard_opcode_lengths)
-    xfree (lh->standard_opcode_lengths);
+  struct line_header *lh = (struct line_header *) arg;
 
-  /* Remember that all the lh->file_names[i].name pointers are
-     pointers into debug_line_buffer, and don't need to be freed.  */
-  if (lh->file_names)
-    xfree (lh->file_names);
+  delete lh;
+}
 
-  /* Similarly for the include directory names.  */
-  if (lh->include_dirs)
-    xfree (lh->include_dirs);
+void
+line_header::add_include_dir (const char *include_dir)
+{
+  if (dwarf_line_debug >= 2)
+    fprintf_unfiltered (gdb_stdlog, "Adding dir %zu: %s\n",
+                       include_dirs.size () + 1, include_dir);
 
-  xfree (lh);
+  include_dirs.push_back (include_dir);
 }
 
-/* Stub for free_line_header to match void * callback types.  */
-
-static void
-free_line_header_voidp (void *arg)
+void
+line_header::add_file_name (const char *name,
+                           dir_index d_index,
+                           unsigned int mod_time,
+                           unsigned int length)
 {
-  struct line_header *lh = arg;
+  if (dwarf_line_debug >= 2)
+    fprintf_unfiltered (gdb_stdlog, "Adding file %u: %s\n",
+                       (unsigned) file_names.size () + 1, name);
 
-  free_line_header (lh);
+  file_names.emplace_back (name, d_index, mod_time, length);
 }
 
-/* Add an entry to LH's include directory table.  */
+/* A convenience function to find the proper .debug_line section for a CU.  */
 
-static void
-add_include_dir (struct line_header *lh, const char *include_dir)
+static struct dwarf2_section_info *
+get_debug_line_section (struct dwarf2_cu *cu)
 {
-  if (dwarf_line_debug >= 2)
-    fprintf_unfiltered (gdb_stdlog, "Adding dir %u: %s\n",
-                       lh->num_include_dirs + 1, include_dir);
+  struct dwarf2_section_info *section;
 
-  /* Grow the array if necessary.  */
-  if (lh->include_dirs_size == 0)
-    {
-      lh->include_dirs_size = 1; /* for testing */
-      lh->include_dirs = xmalloc (lh->include_dirs_size
-                                  * sizeof (*lh->include_dirs));
-    }
-  else if (lh->num_include_dirs >= lh->include_dirs_size)
+  /* For TUs in DWO files, the DW_AT_stmt_list attribute lives in the
+     DWO file.  */
+  if (cu->dwo_unit && cu->per_cu->is_debug_types)
+    section = &cu->dwo_unit->dwo_file->sections.line;
+  else if (cu->per_cu->is_dwz)
     {
-      lh->include_dirs_size *= 2;
-      lh->include_dirs = xrealloc (lh->include_dirs,
-                                   (lh->include_dirs_size
-                                    * sizeof (*lh->include_dirs)));
+      struct dwz_file *dwz = dwarf2_get_dwz_file ();
+
+      section = &dwz->line;
     }
+  else
+    section = &dwarf2_per_objfile->line;
 
-  lh->include_dirs[lh->num_include_dirs++] = include_dir;
+  return section;
 }
 
-/* Add an entry to LH's file name table.  */
+/* Read directory or file name entry format, starting with byte of
+   format count entries, ULEB128 pairs of entry formats, ULEB128 of
+   entries count and the entries themselves in the described entry
+   format.  */
 
 static void
-add_file_name (struct line_header *lh,
-               const char *name,
-               unsigned int dir_index,
-               unsigned int mod_time,
-               unsigned int length)
-{
-  struct file_entry *fe;
+read_formatted_entries (bfd *abfd, const gdb_byte **bufp,
+                       struct line_header *lh,
+                       const struct comp_unit_head *cu_header,
+                       void (*callback) (struct line_header *lh,
+                                         const char *name,
+                                         dir_index d_index,
+                                         unsigned int mod_time,
+                                         unsigned int length))
+{
+  gdb_byte format_count, formati;
+  ULONGEST data_count, datai;
+  const gdb_byte *buf = *bufp;
+  const gdb_byte *format_header_data;
+  int i;
+  unsigned int bytes_read;
 
-  if (dwarf_line_debug >= 2)
-    fprintf_unfiltered (gdb_stdlog, "Adding file %u: %s\n",
-                       lh->num_file_names + 1, name);
+  format_count = read_1_byte (abfd, buf);
+  buf += 1;
+  format_header_data = buf;
+  for (formati = 0; formati < format_count; formati++)
+    {
+      read_unsigned_leb128 (abfd, buf, &bytes_read);
+      buf += bytes_read;
+      read_unsigned_leb128 (abfd, buf, &bytes_read);
+      buf += bytes_read;
+    }
+
+  data_count = read_unsigned_leb128 (abfd, buf, &bytes_read);
+  buf += bytes_read;
+  for (datai = 0; datai < data_count; datai++)
+    {
+      const gdb_byte *format = format_header_data;
+      struct file_entry fe;
+
+      for (formati = 0; formati < format_count; formati++)
+       {
+         ULONGEST content_type = read_unsigned_leb128 (abfd, format, &bytes_read);
+         format += bytes_read;
+
+         ULONGEST form  = read_unsigned_leb128 (abfd, format, &bytes_read);
+         format += bytes_read;
+
+         gdb::optional<const char *> string;
+         gdb::optional<unsigned int> uint;
+
+         switch (form)
+           {
+           case DW_FORM_string:
+             string.emplace (read_direct_string (abfd, buf, &bytes_read));
+             buf += bytes_read;
+             break;
+
+           case DW_FORM_line_strp:
+             string.emplace (read_indirect_line_string (abfd, buf,
+                                                        cu_header,
+                                                        &bytes_read));
+             buf += bytes_read;
+             break;
+
+           case DW_FORM_data1:
+             uint.emplace (read_1_byte (abfd, buf));
+             buf += 1;
+             break;
+
+           case DW_FORM_data2:
+             uint.emplace (read_2_bytes (abfd, buf));
+             buf += 2;
+             break;
 
-  /* Grow the array if necessary.  */
-  if (lh->file_names_size == 0)
-    {
-      lh->file_names_size = 1; /* for testing */
-      lh->file_names = xmalloc (lh->file_names_size
-                                * sizeof (*lh->file_names));
-    }
-  else if (lh->num_file_names >= lh->file_names_size)
-    {
-      lh->file_names_size *= 2;
-      lh->file_names = xrealloc (lh->file_names,
-                                 (lh->file_names_size
-                                  * sizeof (*lh->file_names)));
-    }
+           case DW_FORM_data4:
+             uint.emplace (read_4_bytes (abfd, buf));
+             buf += 4;
+             break;
 
-  fe = &lh->file_names[lh->num_file_names++];
-  fe->name = name;
-  fe->dir_index = dir_index;
-  fe->mod_time = mod_time;
-  fe->length = length;
-  fe->included_p = 0;
-  fe->symtab = NULL;
-}
+           case DW_FORM_data8:
+             uint.emplace (read_8_bytes (abfd, buf));
+             buf += 8;
+             break;
 
-/* A convenience function to find the proper .debug_line section for a CU.  */
+           case DW_FORM_udata:
+             uint.emplace (read_unsigned_leb128 (abfd, buf, &bytes_read));
+             buf += bytes_read;
+             break;
 
-static struct dwarf2_section_info *
-get_debug_line_section (struct dwarf2_cu *cu)
-{
-  struct dwarf2_section_info *section;
+           case DW_FORM_block:
+             /* It is valid only for DW_LNCT_timestamp which is ignored by
+                current GDB.  */
+             break;
+           }
 
-  /* For TUs in DWO files, the DW_AT_stmt_list attribute lives in the
-     DWO file.  */
-  if (cu->dwo_unit && cu->per_cu->is_debug_types)
-    section = &cu->dwo_unit->dwo_file->sections.line;
-  else if (cu->per_cu->is_dwz)
-    {
-      struct dwz_file *dwz = dwarf2_get_dwz_file ();
+         switch (content_type)
+           {
+           case DW_LNCT_path:
+             if (string.has_value ())
+               fe.name = *string;
+             break;
+           case DW_LNCT_directory_index:
+             if (uint.has_value ())
+               fe.d_index = (dir_index) *uint;
+             break;
+           case DW_LNCT_timestamp:
+             if (uint.has_value ())
+               fe.mod_time = *uint;
+             break;
+           case DW_LNCT_size:
+             if (uint.has_value ())
+               fe.length = *uint;
+             break;
+           case DW_LNCT_MD5:
+             break;
+           default:
+             complaint (&symfile_complaints,
+                        _("Unknown format content type %s"),
+                        pulongest (content_type));
+           }
+       }
 
-      section = &dwz->line;
+      callback (lh, fe.name, fe.d_index, fe.mod_time, fe.length);
     }
-  else
-    section = &dwarf2_per_objfile->line;
 
-  return section;
+  *bufp = buf;
 }
 
 /* Read the statement program header starting at OFFSET in
@@ -17252,11 +17796,9 @@ get_debug_line_section (struct dwarf2_cu *cu)
    the returned object point into the dwarf line section buffer,
    and must not be freed.  */
 
-static struct line_header *
-dwarf_decode_line_header (unsigned int offset, struct dwarf2_cu *cu)
+static line_header_up
+dwarf_decode_line_header (sect_offset sect_off, struct dwarf2_cu *cu)
 {
-  struct cleanup *back_to;
-  struct line_header *lh;
   const gdb_byte *line_ptr;
   unsigned int bytes_read, offset_size;
   int i;
@@ -17281,21 +17823,18 @@ dwarf_decode_line_header (unsigned int offset, struct dwarf2_cu *cu)
 
   /* Make sure that at least there's room for the total_length field.
      That could be 12 bytes long, but we're just going to fudge that.  */
-  if (offset + 4 >= section->size)
+  if (to_underlying (sect_off) + 4 >= section->size)
     {
       dwarf2_statement_list_fits_in_line_number_section_complaint ();
       return 0;
     }
 
-  lh = xmalloc (sizeof (*lh));
-  memset (lh, 0, sizeof (*lh));
-  back_to = make_cleanup ((make_cleanup_ftype *) free_line_header,
-                          (void *) lh);
+  line_header_up lh (new line_header ());
 
-  lh->offset.sect_off = offset;
+  lh->sect_off = sect_off;
   lh->offset_in_dwz = cu->per_cu->is_dwz;
 
-  line_ptr = section->buffer + offset;
+  line_ptr = section->buffer + to_underlying (sect_off);
 
   /* Read in the header.  */
   lh->total_length =
@@ -17305,13 +17844,12 @@ dwarf_decode_line_header (unsigned int offset, struct dwarf2_cu *cu)
   if (line_ptr + lh->total_length > (section->buffer + section->size))
     {
       dwarf2_statement_list_fits_in_line_number_section_complaint ();
-      do_cleanups (back_to);
       return 0;
     }
   lh->statement_program_end = line_ptr + lh->total_length;
   lh->version = read_2_bytes (abfd, line_ptr);
   line_ptr += 2;
-  if (lh->version > 4)
+  if (lh->version > 5)
     {
       /* This is a version we don't understand.  The format could have
         changed in ways we don't handle properly so just punt.  */
@@ -17319,6 +17857,25 @@ dwarf_decode_line_header (unsigned int offset, struct dwarf2_cu *cu)
                 _("unsupported version in .debug_line section"));
       return NULL;
     }
+  if (lh->version >= 5)
+    {
+      gdb_byte segment_selector_size;
+
+      /* Skip address size.  */
+      read_1_byte (abfd, line_ptr);
+      line_ptr += 1;
+
+      segment_selector_size = read_1_byte (abfd, line_ptr);
+      line_ptr += 1;
+      if (segment_selector_size != 0)
+       {
+         complaint (&symfile_complaints,
+                    _("unsupported segment selector size %u "
+                      "in .debug_line section"),
+                    segment_selector_size);
+         return NULL;
+       }
+    }
   lh->header_length = read_offset_1 (abfd, line_ptr, offset_size);
   line_ptr += offset_size;
   lh->minimum_instruction_length = read_1_byte (abfd, line_ptr);
@@ -17347,8 +17904,7 @@ dwarf_decode_line_header (unsigned int offset, struct dwarf2_cu *cu)
   line_ptr += 1;
   lh->opcode_base = read_1_byte (abfd, line_ptr);
   line_ptr += 1;
-  lh->standard_opcode_lengths
-    = xmalloc (lh->opcode_base * sizeof (lh->standard_opcode_lengths[0]));
+  lh->standard_opcode_lengths.reset (new unsigned char[lh->opcode_base]);
 
   lh->standard_opcode_lengths[0] = 1;  /* This should never be used anyway.  */
   for (i = 1; i < lh->opcode_base; ++i)
@@ -17357,30 +17913,54 @@ dwarf_decode_line_header (unsigned int offset, struct dwarf2_cu *cu)
       line_ptr += 1;
     }
 
-  /* Read directory table.  */
-  while ((cur_dir = read_direct_string (abfd, line_ptr, &bytes_read)) != NULL)
+  if (lh->version >= 5)
     {
-      line_ptr += bytes_read;
-      add_include_dir (lh, cur_dir);
+      /* Read directory table.  */
+      read_formatted_entries (abfd, &line_ptr, lh.get (), &cu->header,
+                             [] (struct line_header *lh, const char *name,
+                                 dir_index d_index, unsigned int mod_time,
+                                 unsigned int length)
+       {
+         lh->add_include_dir (name);
+       });
+
+      /* Read file name table.  */
+      read_formatted_entries (abfd, &line_ptr, lh.get (), &cu->header,
+                             [] (struct line_header *lh, const char *name,
+                                 dir_index d_index, unsigned int mod_time,
+                                 unsigned int length)
+       {
+         lh->add_file_name (name, d_index, mod_time, length);
+       });
     }
-  line_ptr += bytes_read;
-
-  /* Read file name table.  */
-  while ((cur_file = read_direct_string (abfd, line_ptr, &bytes_read)) != NULL)
+  else
     {
-      unsigned int dir_index, mod_time, length;
-
-      line_ptr += bytes_read;
-      dir_index = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
-      line_ptr += bytes_read;
-      mod_time = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
-      line_ptr += bytes_read;
-      length = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
+      /* Read directory table.  */
+      while ((cur_dir = read_direct_string (abfd, line_ptr, &bytes_read)) != NULL)
+       {
+         line_ptr += bytes_read;
+         lh->add_include_dir (cur_dir);
+       }
       line_ptr += bytes_read;
 
-      add_file_name (lh, cur_file, dir_index, mod_time, length);
+      /* Read file name table.  */
+      while ((cur_file = read_direct_string (abfd, line_ptr, &bytes_read)) != NULL)
+       {
+         unsigned int mod_time, length;
+         dir_index d_index;
+
+         line_ptr += bytes_read;
+         d_index = (dir_index) read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
+         line_ptr += bytes_read;
+         mod_time = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
+         line_ptr += bytes_read;
+         length = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
+         line_ptr += bytes_read;
+
+         lh->add_file_name (cur_file, d_index, mod_time, length);
+       }
+      line_ptr += bytes_read;
     }
-  line_ptr += bytes_read;
   lh->statement_program_start = line_ptr;
 
   if (line_ptr > (section->buffer + section->size))
@@ -17388,7 +17968,6 @@ dwarf_decode_line_header (unsigned int offset, struct dwarf2_cu *cu)
               _("line number info header doesn't "
                 "fit in `.debug_line' section"));
 
-  discard_cleanups (back_to);
   return lh;
 }
 
@@ -17406,16 +17985,14 @@ psymtab_include_file_name (const struct line_header *lh, int file_index,
                           const struct partial_symtab *pst,
                           const char *comp_dir)
 {
-  const struct file_entry fe = lh->file_names [file_index];
+  const file_entry &fe = lh->file_names[file_index];
   const char *include_name = fe.name;
   const char *include_name_to_compare = include_name;
-  const char *dir_name = NULL;
   const char *pst_filename;
   char *copied_name = NULL;
   int file_is_pst;
 
-  if (fe.dir_index && lh->include_dirs != NULL)
-    dir_name = lh->include_dirs[fe.dir_index - 1];
+  const char *dir_name = fe.include_dir (lh);
 
   if (!IS_ABSOLUTE_PATH (include_name)
       && (dir_name != NULL || comp_dir != NULL))
@@ -17480,51 +18057,203 @@ psymtab_include_file_name (const struct line_header *lh, int file_index,
 
 /* State machine to track the state of the line number program.  */
 
-typedef struct
+class lnp_state_machine
 {
-  /* These are part of the standard DWARF line number state machine.  */
+public:
+  /* Initialize a machine state for the start of a line number
+     program.  */
+  lnp_state_machine (gdbarch *arch, line_header *lh, bool record_lines_p);
+
+  file_entry *current_file ()
+  {
+    /* lh->file_names is 0-based, but the file name numbers in the
+       statement program are 1-based.  */
+    return m_line_header->file_name_at (m_file);
+  }
+
+  /* Record the line in the state machine.  END_SEQUENCE is true if
+     we're processing the end of a sequence.  */
+  void record_line (bool end_sequence);
+
+  /* Check address and if invalid nop-out the rest of the lines in this
+     sequence.  */
+  void check_line_address (struct dwarf2_cu *cu,
+                          const gdb_byte *line_ptr,
+                          CORE_ADDR lowpc, CORE_ADDR address);
+
+  void handle_set_discriminator (unsigned int discriminator)
+  {
+    m_discriminator = discriminator;
+    m_line_has_non_zero_discriminator |= discriminator != 0;
+  }
+
+  /* Handle DW_LNE_set_address.  */
+  void handle_set_address (CORE_ADDR baseaddr, CORE_ADDR address)
+  {
+    m_op_index = 0;
+    address += baseaddr;
+    m_address = gdbarch_adjust_dwarf2_line (m_gdbarch, address, false);
+  }
+
+  /* Handle DW_LNS_advance_pc.  */
+  void handle_advance_pc (CORE_ADDR adjust);
+
+  /* Handle a special opcode.  */
+  void handle_special_opcode (unsigned char op_code);
+
+  /* Handle DW_LNS_advance_line.  */
+  void handle_advance_line (int line_delta)
+  {
+    advance_line (line_delta);
+  }
+
+  /* Handle DW_LNS_set_file.  */
+  void handle_set_file (file_name_index file);
+
+  /* Handle DW_LNS_negate_stmt.  */
+  void handle_negate_stmt ()
+  {
+    m_is_stmt = !m_is_stmt;
+  }
+
+  /* Handle DW_LNS_const_add_pc.  */
+  void handle_const_add_pc ();
+
+  /* Handle DW_LNS_fixed_advance_pc.  */
+  void handle_fixed_advance_pc (CORE_ADDR addr_adj)
+  {
+    m_address += gdbarch_adjust_dwarf2_line (m_gdbarch, addr_adj, true);
+    m_op_index = 0;
+  }
+
+  /* Handle DW_LNS_copy.  */
+  void handle_copy ()
+  {
+    record_line (false);
+    m_discriminator = 0;
+  }
+
+  /* Handle DW_LNE_end_sequence.  */
+  void handle_end_sequence ()
+  {
+    m_record_line_callback = ::record_line;
+  }
+
+private:
+  /* Advance the line by LINE_DELTA.  */
+  void advance_line (int line_delta)
+  {
+    m_line += line_delta;
+
+    if (line_delta != 0)
+      m_line_has_non_zero_discriminator = m_discriminator != 0;
+  }
+
+  gdbarch *m_gdbarch;
+
+  /* True if we're recording lines.
+     Otherwise we're building partial symtabs and are just interested in
+     finding include files mentioned by the line number program.  */
+  bool m_record_lines_p;
+
+  /* The line number header.  */
+  line_header *m_line_header;
+
+  /* These are part of the standard DWARF line number state machine,
+     and initialized according to the DWARF spec.  */
+
+  unsigned char m_op_index = 0;
+  /* The line table index (1-based) of the current file.  */
+  file_name_index m_file = (file_name_index) 1;
+  unsigned int m_line = 1;
+
+  /* These are initialized in the constructor.  */
 
-  unsigned char op_index;
-  unsigned int file;
-  unsigned int line;
-  CORE_ADDR address;
-  int is_stmt;
-  unsigned int discriminator;
+  CORE_ADDR m_address;
+  bool m_is_stmt;
+  unsigned int m_discriminator;
 
   /* Additional bits of state we need to track.  */
 
   /* The last file that we called dwarf2_start_subfile for.
      This is only used for TLLs.  */
-  unsigned int last_file;
+  unsigned int m_last_file = 0;
   /* The last file a line number was recorded for.  */
-  struct subfile *last_subfile;
+  struct subfile *m_last_subfile = NULL;
 
   /* The function to call to record a line.  */
-  record_line_ftype *record_line;
+  record_line_ftype *m_record_line_callback = NULL;
 
   /* The last line number that was recorded, used to coalesce
      consecutive entries for the same line.  This can happen, for
      example, when discriminators are present.  PR 17276.  */
-  unsigned int last_line;
-  int line_has_non_zero_discriminator;
-} lnp_state_machine;
+  unsigned int m_last_line = 0;
+  bool m_line_has_non_zero_discriminator = false;
+};
+
+void
+lnp_state_machine::handle_advance_pc (CORE_ADDR adjust)
+{
+  CORE_ADDR addr_adj = (((m_op_index + adjust)
+                        / m_line_header->maximum_ops_per_instruction)
+                       * m_line_header->minimum_instruction_length);
+  m_address += gdbarch_adjust_dwarf2_line (m_gdbarch, addr_adj, true);
+  m_op_index = ((m_op_index + adjust)
+               % m_line_header->maximum_ops_per_instruction);
+}
+
+void
+lnp_state_machine::handle_special_opcode (unsigned char op_code)
+{
+  unsigned char adj_opcode = op_code - m_line_header->opcode_base;
+  CORE_ADDR addr_adj = (((m_op_index
+                         + (adj_opcode / m_line_header->line_range))
+                        / m_line_header->maximum_ops_per_instruction)
+                       * m_line_header->minimum_instruction_length);
+  m_address += gdbarch_adjust_dwarf2_line (m_gdbarch, addr_adj, true);
+  m_op_index = ((m_op_index + (adj_opcode / m_line_header->line_range))
+               % m_line_header->maximum_ops_per_instruction);
 
-/* There's a lot of static state to pass to dwarf_record_line.
-   This keeps it all together.  */
+  int line_delta = (m_line_header->line_base
+                   + (adj_opcode % m_line_header->line_range));
+  advance_line (line_delta);
+  record_line (false);
+  m_discriminator = 0;
+}
 
-typedef struct
+void
+lnp_state_machine::handle_set_file (file_name_index file)
 {
-  /* The gdbarch.  */
-  struct gdbarch *gdbarch;
+  m_file = file;
 
-  /* The line number header.  */
-  struct line_header *line_header;
+  const file_entry *fe = current_file ();
+  if (fe == NULL)
+    dwarf2_debug_line_missing_file_complaint ();
+  else if (m_record_lines_p)
+    {
+      const char *dir = fe->include_dir (m_line_header);
 
-  /* Non-zero if we're recording lines.
-     Otherwise we're building partial symtabs and are just interested in
-     finding include files mentioned by the line number program.  */
-  int record_lines_p;
-} lnp_reader_state;
+      m_last_subfile = current_subfile;
+      m_line_has_non_zero_discriminator = m_discriminator != 0;
+      dwarf2_start_subfile (fe->name, dir);
+    }
+}
+
+void
+lnp_state_machine::handle_const_add_pc ()
+{
+  CORE_ADDR adjust
+    = (255 - m_line_header->opcode_base) / m_line_header->line_range;
+
+  CORE_ADDR addr_adj
+    = (((m_op_index + adjust)
+       / m_line_header->maximum_ops_per_instruction)
+       * m_line_header->minimum_instruction_length);
+
+  m_address += gdbarch_adjust_dwarf2_line (m_gdbarch, addr_adj, true);
+  m_op_index = ((m_op_index + adjust)
+               % m_line_header->maximum_ops_per_instruction);
+}
 
 /* Ignore this record_line request.  */
 
@@ -17625,102 +18354,76 @@ dwarf_finish_line (struct gdbarch *gdbarch, struct subfile *subfile,
   dwarf_record_line_1 (gdbarch, subfile, 0, address, p_record_line);
 }
 
-/* Record the line in STATE.
-   END_SEQUENCE is non-zero if we're processing the end of a sequence.  */
-
-static void
-dwarf_record_line (lnp_reader_state *reader, lnp_state_machine *state,
-                  int end_sequence)
+void
+lnp_state_machine::record_line (bool end_sequence)
 {
-  const struct line_header *lh = reader->line_header;
-  unsigned int file, line, discriminator;
-  int is_stmt;
-
-  file = state->file;
-  line = state->line;
-  is_stmt = state->is_stmt;
-  discriminator = state->discriminator;
-
   if (dwarf_line_debug)
     {
       fprintf_unfiltered (gdb_stdlog,
                          "Processing actual line %u: file %u,"
                          " address %s, is_stmt %u, discrim %u\n",
-                         line, file,
-                         paddress (reader->gdbarch, state->address),
-                         is_stmt, discriminator);
+                         m_line, to_underlying (m_file),
+                         paddress (m_gdbarch, m_address),
+                         m_is_stmt, m_discriminator);
     }
 
-  if (file == 0 || file - 1 >= lh->num_file_names)
+  file_entry *fe = current_file ();
+
+  if (fe == NULL)
     dwarf2_debug_line_missing_file_complaint ();
   /* For now we ignore lines not starting on an instruction boundary.
      But not when processing end_sequence for compatibility with the
      previous version of the code.  */
-  else if (state->op_index == 0 || end_sequence)
+  else if (m_op_index == 0 || end_sequence)
     {
-      lh->file_names[file - 1].included_p = 1;
-      if (reader->record_lines_p && is_stmt)
+      fe->included_p = 1;
+      if (m_record_lines_p && m_is_stmt)
        {
-         if (state->last_subfile != current_subfile || end_sequence)
+         if (m_last_subfile != current_subfile || end_sequence)
            {
-             dwarf_finish_line (reader->gdbarch, state->last_subfile,
-                                state->address, state->record_line);
+             dwarf_finish_line (m_gdbarch, m_last_subfile,
+                                m_address, m_record_line_callback);
            }
 
          if (!end_sequence)
            {
-             if (dwarf_record_line_p (line, state->last_line,
-                                      state->line_has_non_zero_discriminator,
-                                      state->last_subfile))
+             if (dwarf_record_line_p (m_line, m_last_line,
+                                      m_line_has_non_zero_discriminator,
+                                      m_last_subfile))
                {
-                 dwarf_record_line_1 (reader->gdbarch, current_subfile,
-                                      line, state->address,
-                                      state->record_line);
+                 dwarf_record_line_1 (m_gdbarch, current_subfile,
+                                      m_line, m_address,
+                                      m_record_line_callback);
                }
-             state->last_subfile = current_subfile;
-             state->last_line = line;
+             m_last_subfile = current_subfile;
+             m_last_line = m_line;
            }
        }
     }
 }
 
-/* Initialize STATE for the start of a line number program.  */
-
-static void
-init_lnp_state_machine (lnp_state_machine *state,
-                       const lnp_reader_state *reader)
+lnp_state_machine::lnp_state_machine (gdbarch *arch, line_header *lh,
+                                     bool record_lines_p)
 {
-  memset (state, 0, sizeof (*state));
+  m_gdbarch = arch;
+  m_record_lines_p = record_lines_p;
+  m_line_header = lh;
 
-  /* Just starting, there is no "last file".  */
-  state->last_file = 0;
-  state->last_subfile = NULL;
+  m_record_line_callback = ::record_line;
 
-  state->record_line = record_line;
-
-  state->last_line = 0;
-  state->line_has_non_zero_discriminator = 0;
-
-  /* Initialize these according to the DWARF spec.  */
-  state->op_index = 0;
-  state->file = 1;
-  state->line = 1;
   /* Call `gdbarch_adjust_dwarf2_line' on the initial 0 address as if there
      was a line entry for it so that the backend has a chance to adjust it
      and also record it in case it needs it.  This is currently used by MIPS
      code, cf. `mips_adjust_dwarf2_line'.  */
-  state->address = gdbarch_adjust_dwarf2_line (reader->gdbarch, 0, 0);
-  state->is_stmt = reader->line_header->default_is_stmt;
-  state->discriminator = 0;
+  m_address = gdbarch_adjust_dwarf2_line (arch, 0, 0);
+  m_is_stmt = lh->default_is_stmt;
+  m_discriminator = 0;
 }
 
-/* Check address and if invalid nop-out the rest of the lines in this
-   sequence.  */
-
-static void
-check_line_address (struct dwarf2_cu *cu, lnp_state_machine *state,
-                   const gdb_byte *line_ptr,
-                   CORE_ADDR lowpc, CORE_ADDR address)
+void
+lnp_state_machine::check_line_address (struct dwarf2_cu *cu,
+                                      const gdb_byte *line_ptr,
+                                      CORE_ADDR lowpc, CORE_ADDR address)
 {
   /* If address < lowpc then it's not a usable value, it's outside the
      pc range of the CU.  However, we restrict the test to only address
@@ -17738,9 +18441,9 @@ check_line_address (struct dwarf2_cu *cu, lnp_state_machine *state,
       complaint (&symfile_complaints,
                 _(".debug_line address at offset 0x%lx is 0 [in module %s]"),
                 line_offset, objfile_name (objfile));
-      state->record_line = noop_record_line;
-      /* Note: sm.record_line is left as noop_record_line
-        until we see DW_LNE_end_sequence.  */
+      m_record_line_callback = noop_record_line;
+      /* Note: record_line_callback is left as noop_record_line until
+        we see DW_LNE_end_sequence.  */
     }
 }
 
@@ -17761,44 +18464,32 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
   struct objfile *objfile = cu->objfile;
   bfd *abfd = objfile->obfd;
   struct gdbarch *gdbarch = get_objfile_arch (objfile);
-  /* Non-zero if we're recording line info (as opposed to building partial
-     symtabs).  */
-  int record_lines_p = !decode_for_pst_p;
-  /* A collection of things we need to pass to dwarf_record_line.  */
-  lnp_reader_state reader_state;
+  /* True if we're recording line info (as opposed to building partial
+     symtabs and just interested in finding include files mentioned by
+     the line number program).  */
+  bool record_lines_p = !decode_for_pst_p;
 
   baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
 
   line_ptr = lh->statement_program_start;
   line_end = lh->statement_program_end;
 
-  reader_state.gdbarch = gdbarch;
-  reader_state.line_header = lh;
-  reader_state.record_lines_p = record_lines_p;
-
   /* Read the statement sequences until there's nothing left.  */
   while (line_ptr < line_end)
     {
-      /* The DWARF line number program state machine.  */
-      lnp_state_machine state_machine;
-      int end_sequence = 0;
+      /* The DWARF line number program state machine.  Reset the state
+        machine at the start of each sequence.  */
+      lnp_state_machine state_machine (gdbarch, lh, record_lines_p);
+      bool end_sequence = false;
 
-      /* Reset the state machine at the start of each sequence.  */
-      init_lnp_state_machine (&state_machine, &reader_state);
-
-      if (record_lines_p && lh->num_file_names >= state_machine.file)
+      if (record_lines_p)
        {
-          /* Start a subfile for the current file of the state machine.  */
-         /* lh->include_dirs and lh->file_names are 0-based, but the
-            directory and file name numbers in the statement program
-            are 1-based.  */
-          struct file_entry *fe = &lh->file_names[state_machine.file - 1];
-          const char *dir = NULL;
-
-          if (fe->dir_index && lh->include_dirs != NULL)
-            dir = lh->include_dirs[fe->dir_index - 1];
+         /* Start a subfile for the current file of the state
+            machine.  */
+         const file_entry *fe = state_machine.current_file ();
 
-         dwarf2_start_subfile (fe->name, dir);
+         if (fe != NULL)
+           dwarf2_start_subfile (fe->name, fe->include_dir (lh));
        }
 
       /* Decode the table.  */
@@ -17810,28 +18501,7 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
          if (op_code >= lh->opcode_base)
            {
              /* Special opcode.  */
-             unsigned char adj_opcode;
-             CORE_ADDR addr_adj;
-             int line_delta;
-
-             adj_opcode = op_code - lh->opcode_base;
-             addr_adj = (((state_machine.op_index
-                           + (adj_opcode / lh->line_range))
-                          / lh->maximum_ops_per_instruction)
-                         * lh->minimum_instruction_length);
-             state_machine.address
-               += gdbarch_adjust_dwarf2_line (gdbarch, addr_adj, 1);
-             state_machine.op_index = ((state_machine.op_index
-                                        + (adj_opcode / lh->line_range))
-                                       % lh->maximum_ops_per_instruction);
-             line_delta = lh->line_base + (adj_opcode % lh->line_range);
-             state_machine.line += line_delta;
-             if (line_delta != 0)
-               state_machine.line_has_non_zero_discriminator
-                 = state_machine.discriminator != 0;
-
-             dwarf_record_line (&reader_state, &state_machine, 0);
-             state_machine.discriminator = 0;
+             state_machine.handle_special_opcode (op_code);
            }
          else switch (op_code)
            {
@@ -17845,32 +18515,30 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
              switch (extended_op)
                {
                case DW_LNE_end_sequence:
-                 state_machine.record_line = record_line;
-                 end_sequence = 1;
+                 state_machine.handle_end_sequence ();
+                 end_sequence = true;
                  break;
                case DW_LNE_set_address:
                  {
                    CORE_ADDR address
                      = read_address (abfd, line_ptr, cu, &bytes_read);
-
                    line_ptr += bytes_read;
-                   check_line_address (cu, &state_machine, line_ptr,
-                                       lowpc, address);
-                   state_machine.op_index = 0;
-                   address += baseaddr;
-                   state_machine.address
-                     = gdbarch_adjust_dwarf2_line (gdbarch, address, 0);
+
+                   state_machine.check_line_address (cu, line_ptr,
+                                                     lowpc, address);
+                   state_machine.handle_set_address (baseaddr, address);
                  }
                  break;
                case DW_LNE_define_file:
                   {
                     const char *cur_file;
-                    unsigned int dir_index, mod_time, length;
+                   unsigned int mod_time, length;
+                   dir_index dindex;
 
                     cur_file = read_direct_string (abfd, line_ptr,
                                                   &bytes_read);
                     line_ptr += bytes_read;
-                    dir_index =
+                    dindex = (dir_index)
                       read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
                     line_ptr += bytes_read;
                     mod_time =
@@ -17879,20 +18547,23 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
                     length =
                       read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
                     line_ptr += bytes_read;
-                    add_file_name (lh, cur_file, dir_index, mod_time, length);
+                    lh->add_file_name (cur_file, dindex, mod_time, length);
                   }
                  break;
                case DW_LNE_set_discriminator:
-                 /* The discriminator is not interesting to the debugger;
-                    just ignore it.  We still need to check its value though:
-                    if there are consecutive entries for the same
-                    (non-prologue) line we want to coalesce them.
-                    PR 17276.  */
-                 state_machine.discriminator
-                   = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
-                 state_machine.line_has_non_zero_discriminator
-                   |= state_machine.discriminator != 0;
-                 line_ptr += bytes_read;
+                 {
+                   /* The discriminator is not interesting to the
+                      debugger; just ignore it.  We still need to
+                      check its value though:
+                      if there are consecutive entries for the same
+                      (non-prologue) line we want to coalesce them.
+                      PR 17276.  */
+                   unsigned int discr
+                     = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
+                   line_ptr += bytes_read;
+
+                   state_machine.handle_set_discriminator (discr);
+                 }
                  break;
                default:
                  complaint (&symfile_complaints,
@@ -17910,64 +18581,34 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
                }
              break;
            case DW_LNS_copy:
-             dwarf_record_line (&reader_state, &state_machine, 0);
-             state_machine.discriminator = 0;
+             state_machine.handle_copy ();
              break;
            case DW_LNS_advance_pc:
              {
                CORE_ADDR adjust
                  = read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
-               CORE_ADDR addr_adj;
-
-               addr_adj = (((state_machine.op_index + adjust)
-                            / lh->maximum_ops_per_instruction)
-                           * lh->minimum_instruction_length);
-               state_machine.address
-                 += gdbarch_adjust_dwarf2_line (gdbarch, addr_adj, 1);
-               state_machine.op_index = ((state_machine.op_index + adjust)
-                                         % lh->maximum_ops_per_instruction);
                line_ptr += bytes_read;
+
+               state_machine.handle_advance_pc (adjust);
              }
              break;
            case DW_LNS_advance_line:
              {
                int line_delta
                  = read_signed_leb128 (abfd, line_ptr, &bytes_read);
-
-               state_machine.line += line_delta;
-               if (line_delta != 0)
-                 state_machine.line_has_non_zero_discriminator
-                   = state_machine.discriminator != 0;
                line_ptr += bytes_read;
+
+               state_machine.handle_advance_line (line_delta);
              }
              break;
            case DW_LNS_set_file:
              {
-               /* The arrays lh->include_dirs and lh->file_names are
-                  0-based, but the directory and file name numbers in
-                  the statement program are 1-based.  */
-               struct file_entry *fe;
-               const char *dir = NULL;
-
-               state_machine.file = read_unsigned_leb128 (abfd, line_ptr,
-                                                          &bytes_read);
+               file_name_index file
+                 = (file_name_index) read_unsigned_leb128 (abfd, line_ptr,
+                                                           &bytes_read);
                line_ptr += bytes_read;
-               if (state_machine.file == 0
-                   || state_machine.file - 1 >= lh->num_file_names)
-                 dwarf2_debug_line_missing_file_complaint ();
-               else
-                 {
-                   fe = &lh->file_names[state_machine.file - 1];
-                   if (fe->dir_index && lh->include_dirs != NULL)
-                     dir = lh->include_dirs[fe->dir_index - 1];
-                   if (record_lines_p)
-                     {
-                       state_machine.last_subfile = current_subfile;
-                       state_machine.line_has_non_zero_discriminator
-                         = state_machine.discriminator != 0;
-                       dwarf2_start_subfile (fe->name, dir);
-                     }
-                 }
+
+               state_machine.handle_set_file (file);
              }
              break;
            case DW_LNS_set_column:
@@ -17975,7 +18616,7 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
              line_ptr += bytes_read;
              break;
            case DW_LNS_negate_stmt:
-             state_machine.is_stmt = (!state_machine.is_stmt);
+             state_machine.handle_negate_stmt ();
              break;
            case DW_LNS_set_basic_block:
              break;
@@ -17985,28 +18626,14 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
               instruction length since special opcode 255 would have
               scaled the increment.  */
            case DW_LNS_const_add_pc:
-             {
-               CORE_ADDR adjust = (255 - lh->opcode_base) / lh->line_range;
-               CORE_ADDR addr_adj;
-
-               addr_adj = (((state_machine.op_index + adjust)
-                            / lh->maximum_ops_per_instruction)
-                           * lh->minimum_instruction_length);
-               state_machine.address
-                 += gdbarch_adjust_dwarf2_line (gdbarch, addr_adj, 1);
-               state_machine.op_index = ((state_machine.op_index + adjust)
-                                         % lh->maximum_ops_per_instruction);
-             }
+             state_machine.handle_const_add_pc ();
              break;
            case DW_LNS_fixed_advance_pc:
              {
-               CORE_ADDR addr_adj;
-
-               addr_adj = read_2_bytes (abfd, line_ptr);
-               state_machine.address
-                 += gdbarch_adjust_dwarf2_line (gdbarch, addr_adj, 1);
-               state_machine.op_index = 0;
+               CORE_ADDR addr_adj = read_2_bytes (abfd, line_ptr);
                line_ptr += 2;
+
+               state_machine.handle_fixed_advance_pc (addr_adj);
              }
              break;
            default:
@@ -18028,7 +18655,7 @@ dwarf_decode_lines_1 (struct line_header *lh, struct dwarf2_cu *cu,
 
       /* We got a DW_LNE_end_sequence (or we ran off the end of the buffer,
         in which case we still finish recording the last line).  */
-      dwarf_record_line (&reader_state, &state_machine, 1);
+      state_machine.record_line (true);
     }
 }
 
@@ -18077,7 +18704,7 @@ dwarf_decode_lines (struct line_header *lh, const char *comp_dir,
 
       /* Now that we're done scanning the Line Header Program, we can
          create the psymtab of each included file.  */
-      for (file_index = 0; file_index < lh->num_file_names; file_index++)
+      for (file_index = 0; file_index < lh->file_names.size (); file_index++)
         if (lh->file_names[file_index].included_p == 1)
           {
            const char *include_name =
@@ -18094,22 +18721,18 @@ dwarf_decode_lines (struct line_header *lh, const char *comp_dir,
       struct compunit_symtab *cust = buildsym_compunit_symtab ();
       int i;
 
-      for (i = 0; i < lh->num_file_names; i++)
+      for (i = 0; i < lh->file_names.size (); i++)
        {
-         const char *dir = NULL;
-         struct file_entry *fe;
+         file_entry &fe = lh->file_names[i];
 
-         fe = &lh->file_names[i];
-         if (fe->dir_index && lh->include_dirs != NULL)
-           dir = lh->include_dirs[fe->dir_index - 1];
-         dwarf2_start_subfile (fe->name, dir);
+         dwarf2_start_subfile (fe.name, fe.include_dir (lh));
 
          if (current_subfile->symtab == NULL)
            {
              current_subfile->symtab
                = allocate_symtab (cust, current_subfile->name);
            }
-         fe->symtab = current_subfile->symtab;
+         fe.symtab = current_subfile->symtab;
        }
     }
 }
@@ -18318,19 +18941,19 @@ new_symbol_full (struct die_info *die, struct type *type, struct dwarf2_cu *cu,
                          cu);
       if (attr)
        {
-         int file_index = DW_UNSND (attr);
+         file_name_index file_index = (file_name_index) DW_UNSND (attr);
+         struct file_entry *fe;
+
+         if (cu->line_header != NULL)
+           fe = cu->line_header->file_name_at (file_index);
+         else
+           fe = NULL;
 
-         if (cu->line_header == NULL
-             || file_index > cu->line_header->num_file_names)
+         if (fe == NULL)
            complaint (&symfile_complaints,
                       _("file index out of range"));
-         else if (file_index > 0)
-           {
-             struct file_entry *fe;
-
-             fe = &cu->line_header->file_names[file_index - 1];
-             symbol_set_symtab (sym, fe->symtab);
-           }
+         else
+           symbol_set_symtab (sym, fe->symtab);
        }
 
       switch (die->tag)
@@ -18448,7 +19071,7 @@ new_symbol_full (struct die_info *die, struct type *type, struct dwarf2_cu *cu,
                  if (cu->language == language_fortran && die->parent
                      && die->parent->tag == DW_TAG_module
                      && cu->producer
-                     && startswith (cu->producer, "GNU Fortran "))
+                     && startswith (cu->producer, "GNU Fortran"))
                    SYMBOL_ACLASS_INDEX (sym) = LOC_UNRESOLVED;
 
                  /* A variable with DW_AT_external is never static,
@@ -18538,7 +19161,7 @@ new_symbol_full (struct die_info *die, struct type *type, struct dwarf2_cu *cu,
          SYMBOL_DOMAIN (sym) = STRUCT_DOMAIN;
 
          {
-           /* NOTE: carlton/2003-11-10: C++ and Java class symbols shouldn't
+           /* NOTE: carlton/2003-11-10: C++ class symbols shouldn't
               really ever be static objects: otherwise, if you try
               to, say, break of a class's method and you're in a file
               which doesn't mention that class, it won't work unless
@@ -18549,18 +19172,15 @@ new_symbol_full (struct die_info *die, struct type *type, struct dwarf2_cu *cu,
            if (!suppress_add)
              {
                list_to_add = (cu->list_in_scope == &file_symbols
-                              && (cu->language == language_cplus
-                                  || cu->language == language_java)
+                              && cu->language == language_cplus
                               ? &global_symbols : cu->list_in_scope);
 
                /* The semantics of C++ state that "struct foo {
-                  ... }" also defines a typedef for "foo".  A Java
-                  class declaration also defines a typedef for the
-                  class.  */
+                  ... }" also defines a typedef for "foo".  */
                if (cu->language == language_cplus
-                   || cu->language == language_java
                    || cu->language == language_ada
-                   || cu->language == language_d)
+                   || cu->language == language_d
+                   || cu->language == language_rust)
                  {
                    /* The symbol's name is already allocated along
                       with this objfile, so we don't need to
@@ -18593,8 +19213,7 @@ new_symbol_full (struct die_info *die, struct type *type, struct dwarf2_cu *cu,
               DW_TAG_class_type, etc. block.  */
 
            list_to_add = (cu->list_in_scope == &file_symbols
-                          && (cu->language == language_cplus
-                              || cu->language == language_java)
+                          && cu->language == language_cplus
                           ? &global_symbols : cu->list_in_scope);
          }
          break;
@@ -18676,7 +19295,7 @@ dwarf2_const_value_data (const struct attribute *attr, struct obstack *obstack,
     *value = l;
   else
     {
-      gdb_byte *bytes = obstack_alloc (obstack, bits / 8);
+      gdb_byte *bytes = (gdb_byte *) obstack_alloc (obstack, bits / 8);
       store_unsigned_integer (bytes, bits / 8, byte_order, l);
       return bytes;
     }
@@ -18721,12 +19340,12 @@ dwarf2_const_value_attr (const struct attribute *attr, struct type *type,
        /* Symbols of this form are reasonably rare, so we just
           piggyback on the existing location code rather than writing
           a new implementation of symbol_computed_ops.  */
-       *baton = obstack_alloc (obstack, sizeof (struct dwarf2_locexpr_baton));
+       *baton = XOBNEW (obstack, struct dwarf2_locexpr_baton);
        (*baton)->per_cu = cu->per_cu;
        gdb_assert ((*baton)->per_cu);
 
        (*baton)->size = 2 + cu_header->addr_size;
-       data = obstack_alloc (obstack, (*baton)->size);
+       data = (gdb_byte *) obstack_alloc (obstack, (*baton)->size);
        (*baton)->data = data;
 
        data[0] = DW_OP_addr;
@@ -18748,6 +19367,7 @@ dwarf2_const_value_attr (const struct attribute *attr, struct type *type,
     case DW_FORM_block4:
     case DW_FORM_block:
     case DW_FORM_exprloc:
+    case DW_FORM_data16:
       blk = DW_BLOCK (attr);
       if (TYPE_LENGTH (type) != blk->size)
        dwarf2_const_value_length_mismatch_complaint (name, blk->size,
@@ -18798,7 +19418,6 @@ dwarf2_const_value (const struct attribute *attr, struct symbol *sym,
                    struct dwarf2_cu *cu)
 {
   struct objfile *objfile = cu->objfile;
-  struct comp_unit_head *cu_header = &cu->header;
   LONGEST value;
   const gdb_byte *bytes;
   struct dwarf2_locexpr_baton *baton;
@@ -18918,13 +19537,13 @@ build_error_marker_type (struct dwarf2_cu *cu, struct die_info *die)
 
   message = xstrprintf (_("<unknown type in %s, CU 0x%x, DIE 0x%x>"),
                        objfile_name (objfile),
-                       cu->header.offset.sect_off,
-                       die->offset.sect_off);
-  saved = obstack_copy0 (&objfile->objfile_obstack,
-                        message, strlen (message));
+                       to_underlying (cu->header.sect_off),
+                       to_underlying (die->sect_off));
+  saved = (char *) obstack_copy0 (&objfile->objfile_obstack,
+                                 message, strlen (message));
   xfree (message);
 
-  return init_type (TYPE_CODE_ERROR, 0, 0, saved, objfile);
+  return init_type (objfile, TYPE_CODE_ERROR, 0, saved);
 }
 
 /* Look up the type of DIE in CU using its type attribute ATTR.
@@ -18948,16 +19567,16 @@ lookup_die_type (struct die_info *die, const struct attribute *attr,
   if (attr->form == DW_FORM_GNU_ref_alt)
     {
       struct dwarf2_per_cu_data *per_cu;
-      sect_offset offset = dwarf2_get_ref_die_offset (attr);
+      sect_offset sect_off = dwarf2_get_ref_die_offset (attr);
 
-      per_cu = dwarf2_find_containing_comp_unit (offset, 1, cu->objfile);
-      this_type = get_die_type_at_offset (offset, per_cu);
+      per_cu = dwarf2_find_containing_comp_unit (sect_off, 1, cu->objfile);
+      this_type = get_die_type_at_offset (sect_off, per_cu);
     }
   else if (attr_form_is_ref (attr))
     {
-      sect_offset offset = dwarf2_get_ref_die_offset (attr);
+      sect_offset sect_off = dwarf2_get_ref_die_offset (attr);
 
-      this_type = get_die_type_at_offset (offset, cu->per_cu);
+      this_type = get_die_type_at_offset (sect_off, cu->per_cu);
     }
   else if (attr->form == DW_FORM_ref_sig8)
     {
@@ -18970,7 +19589,7 @@ lookup_die_type (struct die_info *die, const struct attribute *attr,
       complaint (&symfile_complaints,
                 _("Dwarf Error: Bad type attribute %s in DIE"
                   " at 0x%x [in module %s]"),
-                dwarf_attr_name (attr->name), die->offset.sect_off,
+                dwarf_attr_name (attr->name), to_underlying (die->sect_off),
                 objfile_name (objfile));
       return build_error_marker_type (cu, die);
     }
@@ -19057,7 +19676,10 @@ read_type_die_1 (struct die_info *die, struct dwarf2_cu *cu)
       this_type = read_tag_ptr_to_member_type (die, cu);
       break;
     case DW_TAG_reference_type:
-      this_type = read_tag_reference_type (die, cu);
+      this_type = read_tag_reference_type (die, cu, TYPE_CODE_REF);
+      break;
+    case DW_TAG_rvalue_reference_type:
+      this_type = read_tag_reference_type (die, cu, TYPE_CODE_RVALUE_REF);
       break;
     case DW_TAG_const_type:
       this_type = read_tag_const_type (die, cu);
@@ -19131,16 +19753,17 @@ guess_full_die_structure_name (struct die_info *die, struct dwarf2_cu *cu)
     {
       if (child->tag == DW_TAG_subprogram)
        {
-         struct attribute *attr;
+         const char *linkage_name;
 
-         attr = dwarf2_attr (child, DW_AT_linkage_name, cu);
-         if (attr == NULL)
-           attr = dwarf2_attr (child, DW_AT_MIPS_linkage_name, cu);
-         if (attr != NULL)
+         linkage_name = dwarf2_string_attr (child, DW_AT_linkage_name, cu);
+         if (linkage_name == NULL)
+           linkage_name = dwarf2_string_attr (child, DW_AT_MIPS_linkage_name,
+                                              cu);
+         if (linkage_name != NULL)
            {
              char *actual_name
                = language_class_name_from_physname (cu->language_defn,
-                                                    DW_STRING (attr));
+                                                    linkage_name);
              char *name = NULL;
 
              if (actual_name != NULL)
@@ -19159,10 +19782,9 @@ guess_full_die_structure_name (struct die_info *die, struct dwarf2_cu *cu)
                      if (actual_name_len > die_name_len + 2
                          && actual_name[actual_name_len
                                         - die_name_len - 1] == ':')
-                       name =
-                         obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
-                                        actual_name,
-                                        actual_name_len - die_name_len - 2);
+                       name = (char *) obstack_copy0 (
+                         &cu->objfile->per_bfd->storage_obstack,
+                         actual_name, actual_name_len - die_name_len - 2);
                    }
                }
              xfree (actual_name);
@@ -19178,18 +19800,17 @@ guess_full_die_structure_name (struct die_info *die, struct dwarf2_cu *cu)
    prefix part in such case.  See
    http://gcc.gnu.org/bugzilla/show_bug.cgi?id=47510.  */
 
-static char *
+static const char *
 anonymous_struct_prefix (struct die_info *die, struct dwarf2_cu *cu)
 {
   struct attribute *attr;
-  char *base;
+  const char *base;
 
   if (die->tag != DW_TAG_class_type && die->tag != DW_TAG_interface_type
       && die->tag != DW_TAG_structure_type && die->tag != DW_TAG_union_type)
     return NULL;
 
-  attr = dwarf2_attr (die, DW_AT_name, cu);
-  if (attr != NULL && DW_STRING (attr) != NULL)
+  if (dwarf2_string_attr (die, DW_AT_name, cu) != NULL)
     return NULL;
 
   attr = dwarf2_attr (die, DW_AT_linkage_name, cu);
@@ -19206,8 +19827,9 @@ anonymous_struct_prefix (struct die_info *die, struct dwarf2_cu *cu)
   if (base == NULL || base == DW_STRING (attr) || base[-1] != ':')
     return "";
 
-  return obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
-                       DW_STRING (attr), &base[-1] - DW_STRING (attr));
+  return (char *) obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
+                                DW_STRING (attr),
+                                &base[-1] - DW_STRING (attr));
 }
 
 /* Return the name of the namespace/class that DIE is defined within,
@@ -19231,10 +19853,11 @@ determine_prefix (struct die_info *die, struct dwarf2_cu *cu)
   struct die_info *parent, *spec_die;
   struct dwarf2_cu *spec_cu;
   struct type *parent_type;
-  char *retval;
+  const char *retval;
 
-  if (cu->language != language_cplus && cu->language != language_java
-      && cu->language != language_fortran && cu->language != language_d)
+  if (cu->language != language_cplus
+      && cu->language != language_fortran && cu->language != language_d
+      && cu->language != language_rust)
     return "";
 
   retval = anonymous_struct_prefix (die, cu);
@@ -19388,8 +20011,6 @@ typename_concat (struct obstack *obs, const char *prefix, const char *suffix,
   if (suffix == NULL || suffix[0] == '\0'
       || prefix == NULL || prefix[0] == '\0')
     sep = "";
-  else if (cu->language == language_java)
-    sep = ".";
   else if (cu->language == language_d)
     {
       /* For D, the 'main' function could be defined in any module, but it
@@ -19421,7 +20042,8 @@ typename_concat (struct obstack *obs, const char *prefix, const char *suffix,
   if (obs == NULL)
     {
       char *retval
-       = xmalloc (strlen (prefix) + MAX_SEP_LEN + strlen (suffix) + 1);
+       = ((char *)
+          xmalloc (strlen (prefix) + MAX_SEP_LEN + strlen (suffix) + 1));
 
       strcpy (retval, lead);
       strcat (retval, prefix);
@@ -19452,13 +20074,14 @@ dwarf2_canonicalize_name (const char *name, struct dwarf2_cu *cu,
 {
   if (name && cu->language == language_cplus)
     {
-      char *canon_name = cp_canonicalize_string (name);
+      std::string canon_name = cp_canonicalize_string (name);
 
-      if (canon_name != NULL)
+      if (!canon_name.empty ())
        {
-         if (strcmp (canon_name, name) != 0)
-           name = obstack_copy0 (obstack, canon_name, strlen (canon_name));
-         xfree (canon_name);
+         if (canon_name != name)
+           name = (const char *) obstack_copy0 (obstack,
+                                                canon_name.c_str (),
+                                                canon_name.length ());
        }
     }
 
@@ -19499,36 +20122,6 @@ dwarf2_name (struct die_info *die, struct dwarf2_cu *cu)
        return DW_STRING (attr);
       return CP_ANONYMOUS_NAMESPACE_STR;
 
-    case DW_TAG_subprogram:
-      /* Java constructors will all be named "<init>", so return
-        the class name when we see this special case.  */
-      if (cu->language == language_java
-         && DW_STRING (attr) != NULL
-         && strcmp (DW_STRING (attr), "<init>") == 0)
-       {
-         struct dwarf2_cu *spec_cu = cu;
-         struct die_info *spec_die;
-
-         /* GCJ will output '<init>' for Java constructor names.
-            For this special case, return the name of the parent class.  */
-
-         /* GCJ may output subprogram DIEs with AT_specification set.
-            If so, use the name of the specified DIE.  */
-         spec_die = die_specification (die, &spec_cu);
-         if (spec_die != NULL)
-           return dwarf2_name (spec_die, spec_cu);
-
-         do
-           {
-             die = die->parent;
-             if (die->tag == DW_TAG_class_type)
-               return dwarf2_name (die, cu);
-           }
-         while (die->tag != DW_TAG_compile_unit
-                && die->tag != DW_TAG_partial_unit);
-       }
-      break;
-
     case DW_TAG_class_type:
     case DW_TAG_interface_type:
     case DW_TAG_structure_type:
@@ -19562,12 +20155,13 @@ dwarf2_name (struct die_info *die, struct dwarf2_cu *cu)
 
          if (demangled)
            {
-             char *base;
+             const char *base;
 
              /* FIXME: we already did this for the partial symbol... */
              DW_STRING (attr)
-               = obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
-                                demangled, strlen (demangled));
+               = ((const char *)
+                  obstack_copy0 (&cu->objfile->per_bfd->storage_obstack,
+                                 demangled, strlen (demangled)));
              DW_STRING_IS_CANONICAL (attr) = 1;
              xfree (demangled);
 
@@ -19661,7 +20255,7 @@ dwarf_form_name (unsigned form)
   return name;
 }
 
-static char *
+static const char *
 dwarf_bool_name (unsigned mybool)
 {
   if (mybool)
@@ -19690,13 +20284,14 @@ dump_die_shallow (struct ui_file *f, int indent, struct die_info *die)
 
   print_spaces (indent, f);
   fprintf_unfiltered (f, "Die: %s (abbrev %d, offset 0x%x)\n",
-          dwarf_tag_name (die->tag), die->abbrev, die->offset.sect_off);
+                     dwarf_tag_name (die->tag), die->abbrev,
+                     to_underlying (die->sect_off));
 
   if (die->parent != NULL)
     {
       print_spaces (indent, f);
       fprintf_unfiltered (f, "  parent at offset: 0x%x\n",
-                         die->parent->offset.sect_off);
+                         to_underlying (die->parent->sect_off));
     }
 
   print_spaces (indent, f);
@@ -19731,6 +20326,9 @@ dump_die_shallow (struct ui_file *f, int indent, struct die_info *die)
          fprintf_unfiltered (f, "expression: size %s",
                              pulongest (DW_BLOCK (&die->attrs[i])->size));
          break;
+       case DW_FORM_data16:
+         fprintf_unfiltered (f, "constant of 16 bytes");
+         break;
        case DW_FORM_ref_addr:
          fprintf_unfiltered (f, "ref address: ");
          fputs_filtered (hex_string (DW_UNSND (&die->attrs[i])), f);
@@ -19766,6 +20364,7 @@ dump_die_shallow (struct ui_file *f, int indent, struct die_info *die)
          break;
        case DW_FORM_string:
        case DW_FORM_strp:
+       case DW_FORM_line_strp:
        case DW_FORM_GNU_str_index:
        case DW_FORM_GNU_strp_alt:
          fprintf_unfiltered (f, "string: \"%s\" (%s canonicalized)",
@@ -19851,7 +20450,8 @@ store_in_ref_table (struct die_info *die, struct dwarf2_cu *cu)
 {
   void **slot;
 
-  slot = htab_find_slot_with_hash (cu->die_hash, die, die->offset.sect_off,
+  slot = htab_find_slot_with_hash (cu->die_hash, die,
+                                  to_underlying (die->sect_off),
                                   INSERT);
 
   *slot = die;
@@ -19863,16 +20463,13 @@ store_in_ref_table (struct die_info *die, struct dwarf2_cu *cu)
 static sect_offset
 dwarf2_get_ref_die_offset (const struct attribute *attr)
 {
-  sect_offset retval = { DW_UNSND (attr) };
-
   if (attr_form_is_ref (attr))
-    return retval;
+    return (sect_offset) DW_UNSND (attr);
 
-  retval.sect_off = 0;
   complaint (&symfile_complaints,
             _("unsupported die ref attribute form: '%s'"),
             dwarf_form_name (attr->form));
-  return retval;
+  return {};
 }
 
 /* Return the constant value held by ATTR.  Return DEFAULT_VALUE if
@@ -19891,6 +20488,7 @@ dwarf2_get_attr_constant_value (const struct attribute *attr, int default_value)
     return DW_UNSND (attr);
   else
     {
+      /* For DW_FORM_data16 see attr_form_is_constant.  */
       complaint (&symfile_complaints,
                 _("Attribute value is not a constant (%s)"),
                  dwarf_form_name (attr->form));
@@ -19928,7 +20526,7 @@ follow_die_ref_or_sig (struct die_info *src_die, const struct attribute *attr,
    Returns NULL if OFFSET is invalid.  */
 
 static struct die_info *
-follow_die_offset (sect_offset offset, int offset_in_dwz,
+follow_die_offset (sect_offset sect_off, int offset_in_dwz,
                   struct dwarf2_cu **ref_cu)
 {
   struct die_info temp_die;
@@ -19943,15 +20541,15 @@ follow_die_offset (sect_offset offset, int offset_in_dwz,
       /* .debug_types CUs cannot reference anything outside their CU.
         If they need to, they have to reference a signatured type via
         DW_FORM_ref_sig8.  */
-      if (! offset_in_cu_p (&cu->header, offset))
+      if (!offset_in_cu_p (&cu->header, sect_off))
        return NULL;
     }
   else if (offset_in_dwz != cu->per_cu->is_dwz
-          || ! offset_in_cu_p (&cu->header, offset))
+          || !offset_in_cu_p (&cu->header, sect_off))
     {
       struct dwarf2_per_cu_data *per_cu;
 
-      per_cu = dwarf2_find_containing_comp_unit (offset, offset_in_dwz,
+      per_cu = dwarf2_find_containing_comp_unit (sect_off, offset_in_dwz,
                                                 cu->objfile);
 
       /* If necessary, add it to the queue and load its DIEs.  */
@@ -19968,8 +20566,10 @@ follow_die_offset (sect_offset offset, int offset_in_dwz,
     }
 
   *ref_cu = target_cu;
-  temp_die.offset = offset;
-  return htab_find_with_hash (target_cu->die_hash, &temp_die, offset.sect_off);
+  temp_die.sect_off = sect_off;
+  return (struct die_info *) htab_find_with_hash (target_cu->die_hash,
+                                                 &temp_die,
+                                                 to_underlying (sect_off));
 }
 
 /* Follow reference attribute ATTR of SRC_DIE.
@@ -19980,29 +20580,29 @@ static struct die_info *
 follow_die_ref (struct die_info *src_die, const struct attribute *attr,
                struct dwarf2_cu **ref_cu)
 {
-  sect_offset offset = dwarf2_get_ref_die_offset (attr);
+  sect_offset sect_off = dwarf2_get_ref_die_offset (attr);
   struct dwarf2_cu *cu = *ref_cu;
   struct die_info *die;
 
-  die = follow_die_offset (offset,
+  die = follow_die_offset (sect_off,
                           (attr->form == DW_FORM_GNU_ref_alt
                            || cu->per_cu->is_dwz),
                           ref_cu);
   if (!die)
     error (_("Dwarf Error: Cannot find DIE at 0x%x referenced from DIE "
           "at 0x%x [in module %s]"),
-          offset.sect_off, src_die->offset.sect_off,
+          to_underlying (sect_off), to_underlying (src_die->sect_off),
           objfile_name (cu->objfile));
 
   return die;
 }
 
-/* Return DWARF block referenced by DW_AT_location of DIE at OFFSET at PER_CU.
+/* Return DWARF block referenced by DW_AT_location of DIE at SECT_OFF at PER_CU.
    Returned value is intended for DW_OP_call*.  Returned
    dwarf2_locexpr_baton->data has lifetime of PER_CU->OBJFILE.  */
 
 struct dwarf2_locexpr_baton
-dwarf2_fetch_die_loc_sect_off (sect_offset offset,
+dwarf2_fetch_die_loc_sect_off (sect_offset sect_off,
                               struct dwarf2_per_cu_data *per_cu,
                               CORE_ADDR (*get_frame_pc) (void *baton),
                               void *baton)
@@ -20017,11 +20617,18 @@ dwarf2_fetch_die_loc_sect_off (sect_offset offset,
   if (per_cu->cu == NULL)
     load_cu (per_cu);
   cu = per_cu->cu;
+  if (cu == NULL)
+    {
+      /* We shouldn't get here for a dummy CU, but don't crash on the user.
+        Instead just throw an error, not much else we can do.  */
+      error (_("Dwarf Error: Dummy CU at 0x%x referenced in module %s"),
+            to_underlying (sect_off), objfile_name (per_cu->objfile));
+    }
 
-  die = follow_die_offset (offset, per_cu->is_dwz, &cu);
+  die = follow_die_offset (sect_off, per_cu->is_dwz, &cu);
   if (!die)
     error (_("Dwarf Error: Cannot find DIE at 0x%x referenced in module %s"),
-          offset.sect_off, objfile_name (per_cu->objfile));
+          to_underlying (sect_off), objfile_name (per_cu->objfile));
 
   attr = dwarf2_attr (die, DW_AT_location, cu);
   if (!attr)
@@ -20049,7 +20656,7 @@ dwarf2_fetch_die_loc_sect_off (sect_offset offset,
       if (!attr_form_is_block (attr))
        error (_("Dwarf Error: DIE at 0x%x referenced in module %s "
                 "is neither DW_FORM_block* nor DW_FORM_exprloc"),
-              offset.sect_off, objfile_name (per_cu->objfile));
+              to_underlying (sect_off), objfile_name (per_cu->objfile));
 
       retval.data = DW_BLOCK (attr)->data;
       retval.size = DW_BLOCK (attr)->size;
@@ -20070,9 +20677,9 @@ dwarf2_fetch_die_loc_cu_off (cu_offset offset_in_cu,
                             CORE_ADDR (*get_frame_pc) (void *baton),
                             void *baton)
 {
-  sect_offset offset = { per_cu->offset.sect_off + offset_in_cu.cu_off };
+  sect_offset sect_off = per_cu->sect_off + to_underlying (offset_in_cu);
 
-  return dwarf2_fetch_die_loc_sect_off (offset, per_cu, get_frame_pc, baton);
+  return dwarf2_fetch_die_loc_sect_off (sect_off, per_cu, get_frame_pc, baton);
 }
 
 /* Write a constant of a given type as target-ordered bytes into
@@ -20088,7 +20695,7 @@ write_constant_as_bytes (struct obstack *obstack,
   gdb_byte *result;
 
   *len = TYPE_LENGTH (type);
-  result = obstack_alloc (obstack, *len);
+  result = (gdb_byte *) obstack_alloc (obstack, *len);
   store_unsigned_integer (result, *len, byte_order, value);
 
   return result;
@@ -20100,7 +20707,7 @@ write_constant_as_bytes (struct obstack *obstack,
    does not have a DW_AT_const_value, return NULL.  */
 
 const gdb_byte *
-dwarf2_fetch_constant_bytes (sect_offset offset,
+dwarf2_fetch_constant_bytes (sect_offset sect_off,
                             struct dwarf2_per_cu_data *per_cu,
                             struct obstack *obstack,
                             LONGEST *len)
@@ -20118,11 +20725,18 @@ dwarf2_fetch_constant_bytes (sect_offset offset,
   if (per_cu->cu == NULL)
     load_cu (per_cu);
   cu = per_cu->cu;
+  if (cu == NULL)
+    {
+      /* We shouldn't get here for a dummy CU, but don't crash on the user.
+        Instead just throw an error, not much else we can do.  */
+      error (_("Dwarf Error: Dummy CU at 0x%x referenced in module %s"),
+            to_underlying (sect_off), objfile_name (per_cu->objfile));
+    }
 
-  die = follow_die_offset (offset, per_cu->is_dwz, &cu);
+  die = follow_die_offset (sect_off, per_cu->is_dwz, &cu);
   if (!die)
     error (_("Dwarf Error: Cannot find DIE at 0x%x referenced in module %s"),
-          offset.sect_off, objfile_name (per_cu->objfile));
+          to_underlying (sect_off), objfile_name (per_cu->objfile));
 
 
   attr = dwarf2_attr (die, DW_AT_const_value, cu);
@@ -20140,7 +20754,7 @@ dwarf2_fetch_constant_bytes (sect_offset offset,
        gdb_byte *tem;
 
        *len = cu->header.addr_size;
-       tem = obstack_alloc (obstack, *len);
+       tem = (gdb_byte *) obstack_alloc (obstack, *len);
        store_unsigned_integer (tem, *len, byte_order, DW_ADDR (attr));
        result = tem;
       }
@@ -20159,6 +20773,7 @@ dwarf2_fetch_constant_bytes (sect_offset offset,
     case DW_FORM_block4:
     case DW_FORM_block:
     case DW_FORM_exprloc:
+    case DW_FORM_data16:
       result = DW_BLOCK (attr)->data;
       *len = DW_BLOCK (attr)->size;
       break;
@@ -20219,6 +20834,31 @@ dwarf2_fetch_constant_bytes (sect_offset offset,
   return result;
 }
 
+/* Return the type of the die at OFFSET in PER_CU.  Return NULL if no
+   valid type for this die is found.  */
+
+struct type *
+dwarf2_fetch_die_type_sect_off (sect_offset sect_off,
+                               struct dwarf2_per_cu_data *per_cu)
+{
+  struct dwarf2_cu *cu;
+  struct die_info *die;
+
+  dw2_setup (per_cu->objfile);
+
+  if (per_cu->cu == NULL)
+    load_cu (per_cu);
+  cu = per_cu->cu;
+  if (!cu)
+    return NULL;
+
+  die = follow_die_offset (sect_off, per_cu->is_dwz, &cu);
+  if (!die)
+    return NULL;
+
+  return die_type (die, cu);
+}
+
 /* Return the type of the DIE at DIE_OFFSET in the CU named by
    PER_CU.  */
 
@@ -20226,11 +20866,9 @@ struct type *
 dwarf2_get_die_type (cu_offset die_offset,
                     struct dwarf2_per_cu_data *per_cu)
 {
-  sect_offset die_offset_sect;
-
   dw2_setup (per_cu->objfile);
 
-  die_offset_sect.sect_off = per_cu->offset.sect_off + die_offset.cu_off;
+  sect_offset die_offset_sect = per_cu->sect_off + to_underlying (die_offset);
   return get_die_type_at_offset (die_offset_sect, per_cu);
 }
 
@@ -20243,7 +20881,6 @@ static struct die_info *
 follow_die_sig_1 (struct die_info *src_die, struct signatured_type *sig_type,
                  struct dwarf2_cu **ref_cu)
 {
-  struct objfile *objfile = (*ref_cu)->objfile;
   struct die_info temp_die;
   struct dwarf2_cu *sig_cu;
   struct die_info *die;
@@ -20259,10 +20896,10 @@ follow_die_sig_1 (struct die_info *src_die, struct signatured_type *sig_type,
 
   sig_cu = sig_type->per_cu.cu;
   gdb_assert (sig_cu != NULL);
-  gdb_assert (sig_type->type_offset_in_section.sect_off != 0);
-  temp_die.offset = sig_type->type_offset_in_section;
-  die = htab_find_with_hash (sig_cu->die_hash, &temp_die,
-                            temp_die.offset.sect_off);
+  gdb_assert (to_underlying (sig_type->type_offset_in_section) != 0);
+  temp_die.sect_off = sig_type->type_offset_in_section;
+  die = (struct die_info *) htab_find_with_hash (sig_cu->die_hash, &temp_die,
+                                                to_underlying (temp_die.sect_off));
   if (die)
     {
       /* For .gdb_index version 7 keep track of included TUs.
@@ -20305,7 +20942,7 @@ follow_die_sig (struct die_info *src_die, const struct attribute *attr,
     {
       error (_("Dwarf Error: Cannot find signatured DIE %s referenced"
                " from DIE at 0x%x [in module %s]"),
-             hex_string (signature), src_die->offset.sect_off,
+             hex_string (signature), to_underlying (src_die->sect_off),
             objfile_name ((*ref_cu)->objfile));
     }
 
@@ -20315,7 +20952,7 @@ follow_die_sig (struct die_info *src_die, const struct attribute *attr,
       dump_die_for_error (src_die);
       error (_("Dwarf Error: Problem reading signatured DIE %s referenced"
               " from DIE at 0x%x [in module %s]"),
-            hex_string (signature), src_die->offset.sect_off,
+            hex_string (signature), to_underlying (src_die->sect_off),
             objfile_name ((*ref_cu)->objfile));
     }
 
@@ -20342,7 +20979,7 @@ get_signatured_type (struct die_info *die, ULONGEST signature,
       complaint (&symfile_complaints,
                 _("Dwarf Error: Cannot find signatured DIE %s referenced"
                   " from DIE at 0x%x [in module %s]"),
-                hex_string (signature), die->offset.sect_off,
+                hex_string (signature), to_underlying (die->sect_off),
                 objfile_name (dwarf2_per_objfile->objfile));
       return build_error_marker_type (cu, die);
     }
@@ -20364,7 +21001,7 @@ get_signatured_type (struct die_info *die, ULONGEST signature,
          complaint (&symfile_complaints,
                     _("Dwarf Error: Cannot build signatured type %s"
                       " referenced from DIE at 0x%x [in module %s]"),
-                    hex_string (signature), die->offset.sect_off,
+                    hex_string (signature), to_underlying (die->sect_off),
                     objfile_name (dwarf2_per_objfile->objfile));
          type = build_error_marker_type (cu, die);
        }
@@ -20374,7 +21011,7 @@ get_signatured_type (struct die_info *die, ULONGEST signature,
       complaint (&symfile_complaints,
                 _("Dwarf Error: Problem reading signatured DIE %s referenced"
                   " from DIE at 0x%x [in module %s]"),
-                hex_string (signature), die->offset.sect_off,
+                hex_string (signature), to_underlying (die->sect_off),
                 objfile_name (dwarf2_per_objfile->objfile));
       type = build_error_marker_type (cu, die);
     }
@@ -20407,7 +21044,7 @@ get_DW_AT_signature_type (struct die_info *die, const struct attribute *attr,
       complaint (&symfile_complaints,
                 _("Dwarf Error: DW_AT_signature has bad form %s in DIE"
                   " at 0x%x [in module %s]"),
-                dwarf_form_name (attr->form), die->offset.sect_off,
+                dwarf_form_name (attr->form), to_underlying (die->sect_off),
                 objfile_name (dwarf2_per_objfile->objfile));
       return build_error_marker_type (cu, die);
     }
@@ -20696,6 +21333,7 @@ decode_locdesc (struct dwarf_block *blk, struct dwarf2_cu *cu)
          break;
 
         case DW_OP_GNU_push_tls_address:
+       case DW_OP_form_tls_address:
          /* The top of the stack has the offset from the beginning
             of the thread control block at which the variable is located.  */
          /* Nothing should follow this operator, so the top of stack would
@@ -20758,11 +21396,7 @@ decode_locdesc (struct dwarf_block *blk, struct dwarf2_cu *cu)
 static struct dwarf_block *
 dwarf_alloc_block (struct dwarf2_cu *cu)
 {
-  struct dwarf_block *blk;
-
-  blk = (struct dwarf_block *)
-    obstack_alloc (&cu->comp_unit_obstack, sizeof (struct dwarf_block));
-  return (blk);
+  return XOBNEW (&cu->comp_unit_obstack, struct dwarf_block);
 }
 
 static struct die_info *
@@ -20791,15 +21425,17 @@ file_file_name (int file, struct line_header *lh)
 {
   /* Is the file number a valid index into the line header's file name
      table?  Remember that file numbers start with one, not zero.  */
-  if (1 <= file && file <= lh->num_file_names)
+  if (1 <= file && file <= lh->file_names.size ())
     {
-      struct file_entry *fe = &lh->file_names[file - 1];
+      const file_entry &fe = lh->file_names[file - 1];
 
-      if (IS_ABSOLUTE_PATH (fe->name) || fe->dir_index == 0
-         || lh->include_dirs == NULL)
-        return xstrdup (fe->name);
-      return concat (lh->include_dirs[fe->dir_index - 1], SLASH_STRING,
-                    fe->name, NULL);
+      if (!IS_ABSOLUTE_PATH (fe.name))
+       {
+         const char *dir = fe.include_dir (lh);
+         if (dir != NULL)
+           return concat (dir, SLASH_STRING, fe.name, (char *) NULL);
+       }
+      return xstrdup (fe.name);
     }
   else
     {
@@ -20828,13 +21464,14 @@ file_full_name (int file, struct line_header *lh, const char *comp_dir)
 {
   /* Is the file number a valid index into the line header's file name
      table?  Remember that file numbers start with one, not zero.  */
-  if (1 <= file && file <= lh->num_file_names)
+  if (1 <= file && file <= lh->file_names.size ())
     {
       char *relative = file_file_name (file, lh);
 
       if (IS_ABSOLUTE_PATH (relative) || comp_dir == NULL)
        return relative;
-      return reconcat (relative, comp_dir, SLASH_STRING, relative, NULL);
+      return reconcat (relative, comp_dir, SLASH_STRING,
+                      relative, (char *) NULL);
     }
   else
     return file_file_name (file, lh);
@@ -20874,7 +21511,7 @@ macro_start_file (int file, int line,
 static char *
 copy_string (const char *buf, int len)
 {
-  char *s = xmalloc (len + 1);
+  char *s = (char *) xmalloc (len + 1);
 
   memcpy (s, buf, len);
   s[len] = '\0';
@@ -20962,7 +21599,7 @@ parse_macro_definition (struct macro_source_file *file, int line,
       char *name = copy_string (body, p - body);
       int argc = 0;
       int argv_size = 1;
-      char **argv = xmalloc (argv_size * sizeof (*argv));
+      char **argv = XNEWVEC (char *, argv_size);
 
       p++;
 
@@ -20985,7 +21622,7 @@ parse_macro_definition (struct macro_source_file *file, int line,
               if (argc >= argv_size)
                 {
                   argv_size *= 2;
-                  argv = xrealloc (argv, argv_size * sizeof (*argv));
+                  argv = XRESIZEVEC (char *, argv, argv_size);
                 }
 
               argv[argc++] = copy_string (arg_start, p - arg_start);
@@ -21070,6 +21707,10 @@ skip_form_bytes (bfd *abfd, const gdb_byte *bytes, const gdb_byte *buffer_end,
       bytes += 8;
       break;
 
+    case DW_FORM_data16:
+      bytes += 16;
+      break;
+
     case DW_FORM_string:
       read_direct_string (abfd, bytes, &bytes_read);
       bytes += bytes_read;
@@ -21151,7 +21792,8 @@ skip_unknown_opcode (unsigned int opcode,
 
   for (i = 0; i < arg; ++i)
     {
-      mac_ptr = skip_form_bytes (abfd, mac_ptr, mac_end, defn[i], offset_size,
+      mac_ptr = skip_form_bytes (abfd, mac_ptr, mac_end,
+                                (enum dwarf_form) defn[i], offset_size,
                                 section);
       if (mac_ptr == NULL)
        {
@@ -21182,7 +21824,7 @@ dwarf_parse_macro_header (const gdb_byte **opcode_definitions,
       unsigned int version, flags;
 
       version = read_2_bytes (abfd, mac_ptr);
-      if (version != 4)
+      if (version != 4 && version != 5)
        {
          complaint (&symfile_complaints,
                     _("unrecognized version `%d' in .debug_macro section"),
@@ -21225,7 +21867,7 @@ dwarf_parse_macro_header (const gdb_byte **opcode_definitions,
 }
 
 /* A helper for dwarf_decode_macros that handles the GNU extensions,
-   including DW_MACRO_GNU_transparent_include.  */
+   including DW_MACRO_import.  */
 
 static void
 dwarf_decode_macro_bytes (bfd *abfd,
@@ -21268,7 +21910,7 @@ dwarf_decode_macro_bytes (bfd *abfd,
          break;
        }
 
-      macinfo_type = read_1_byte (abfd, mac_ptr);
+      macinfo_type = (enum dwarf_macro_record_type) read_1_byte (abfd, mac_ptr);
       mac_ptr++;
 
       /* Note that we rely on the fact that the corresponding GNU and
@@ -21280,12 +21922,12 @@ dwarf_decode_macro_bytes (bfd *abfd,
        case 0:
          break;
 
-        case DW_MACRO_GNU_define:
-        case DW_MACRO_GNU_undef:
-       case DW_MACRO_GNU_define_indirect:
-       case DW_MACRO_GNU_undef_indirect:
-       case DW_MACRO_GNU_define_indirect_alt:
-       case DW_MACRO_GNU_undef_indirect_alt:
+        case DW_MACRO_define:
+        case DW_MACRO_undef:
+       case DW_MACRO_define_strp:
+       case DW_MACRO_undef_strp:
+       case DW_MACRO_define_sup:
+       case DW_MACRO_undef_sup:
           {
             unsigned int bytes_read;
             int line;
@@ -21295,8 +21937,8 @@ dwarf_decode_macro_bytes (bfd *abfd,
            line = read_unsigned_leb128 (abfd, mac_ptr, &bytes_read);
            mac_ptr += bytes_read;
 
-           if (macinfo_type == DW_MACRO_GNU_define
-               || macinfo_type == DW_MACRO_GNU_undef)
+           if (macinfo_type == DW_MACRO_define
+               || macinfo_type == DW_MACRO_undef)
              {
                body = read_direct_string (abfd, mac_ptr, &bytes_read);
                mac_ptr += bytes_read;
@@ -21308,8 +21950,8 @@ dwarf_decode_macro_bytes (bfd *abfd,
                str_offset = read_offset_1 (abfd, mac_ptr, offset_size);
                mac_ptr += offset_size;
 
-               if (macinfo_type == DW_MACRO_GNU_define_indirect_alt
-                   || macinfo_type == DW_MACRO_GNU_undef_indirect_alt
+               if (macinfo_type == DW_MACRO_define_sup
+                   || macinfo_type == DW_MACRO_undef_sup
                    || section_is_dwz)
                  {
                    struct dwz_file *dwz = dwarf2_get_dwz_file ();
@@ -21320,9 +21962,9 @@ dwarf_decode_macro_bytes (bfd *abfd,
                  body = read_indirect_string_at_offset (abfd, str_offset);
              }
 
-           is_define = (macinfo_type == DW_MACRO_GNU_define
-                        || macinfo_type == DW_MACRO_GNU_define_indirect
-                        || macinfo_type == DW_MACRO_GNU_define_indirect_alt);
+           is_define = (macinfo_type == DW_MACRO_define
+                        || macinfo_type == DW_MACRO_define_strp
+                        || macinfo_type == DW_MACRO_define_sup);
             if (! current_file)
              {
                /* DWARF violation as no main source is present.  */
@@ -21345,15 +21987,15 @@ dwarf_decode_macro_bytes (bfd *abfd,
              parse_macro_definition (current_file, line, body);
            else
              {
-               gdb_assert (macinfo_type == DW_MACRO_GNU_undef
-                           || macinfo_type == DW_MACRO_GNU_undef_indirect
-                           || macinfo_type == DW_MACRO_GNU_undef_indirect_alt);
+               gdb_assert (macinfo_type == DW_MACRO_undef
+                           || macinfo_type == DW_MACRO_undef_strp
+                           || macinfo_type == DW_MACRO_undef_sup);
                macro_undef (current_file, line, body);
              }
           }
           break;
 
-        case DW_MACRO_GNU_start_file:
+        case DW_MACRO_start_file:
           {
             unsigned int bytes_read;
             int line, file;
@@ -21373,7 +22015,7 @@ dwarf_decode_macro_bytes (bfd *abfd,
 
            if (at_commandline)
              {
-               /* This DW_MACRO_GNU_start_file was executed in the
+               /* This DW_MACRO_start_file was executed in the
                   pass one.  */
                at_commandline = 0;
              }
@@ -21382,7 +22024,7 @@ dwarf_decode_macro_bytes (bfd *abfd,
           }
           break;
 
-        case DW_MACRO_GNU_end_file:
+        case DW_MACRO_end_file:
           if (! current_file)
            complaint (&symfile_complaints,
                       _("macro debug info has an unmatched "
@@ -21408,7 +22050,9 @@ dwarf_decode_macro_bytes (bfd *abfd,
 
                   /* We don't increment mac_ptr here, so this is just
                      a look-ahead.  */
-                  next_type = read_1_byte (abfd, mac_ptr);
+                  next_type
+                   = (enum dwarf_macro_record_type) read_1_byte (abfd,
+                                                                 mac_ptr);
                   if (next_type != 0)
                    complaint (&symfile_complaints,
                               _("no terminating 0-type entry for "
@@ -21419,14 +22063,13 @@ dwarf_decode_macro_bytes (bfd *abfd,
             }
           break;
 
-       case DW_MACRO_GNU_transparent_include:
-       case DW_MACRO_GNU_transparent_include_alt:
+       case DW_MACRO_import:
+       case DW_MACRO_import_sup:
          {
            LONGEST offset;
            void **slot;
            bfd *include_bfd = abfd;
            struct dwarf2_section_info *include_section = section;
-           struct dwarf2_section_info alt_section;
            const gdb_byte *include_mac_end = mac_end;
            int is_dwz = section_is_dwz;
            const gdb_byte *new_mac_ptr;
@@ -21434,7 +22077,7 @@ dwarf_decode_macro_bytes (bfd *abfd,
            offset = read_offset_1 (abfd, mac_ptr, offset_size);
            mac_ptr += offset_size;
 
-           if (macinfo_type == DW_MACRO_GNU_transparent_include_alt)
+           if (macinfo_type == DW_MACRO_import_sup)
              {
                struct dwz_file *dwz = dwarf2_get_dwz_file ();
 
@@ -21454,7 +22097,7 @@ dwarf_decode_macro_bytes (bfd *abfd,
                /* This has actually happened; see
                   http://sourceware.org/bugzilla/show_bug.cgi?id=13568.  */
                complaint (&symfile_complaints,
-                          _("recursive DW_MACRO_GNU_transparent_include in "
+                          _("recursive DW_MACRO_import in "
                             ".debug_macro section"));
              }
            else
@@ -21475,9 +22118,10 @@ dwarf_decode_macro_bytes (bfd *abfd,
          if (!section_is_gnu)
            {
              unsigned int bytes_read;
-             int constant;
 
-             constant = read_unsigned_leb128 (abfd, mac_ptr, &bytes_read);
+             /* This reads the constant, but since we don't recognize
+                any vendor extensions, we ignore it.  */
+             read_unsigned_leb128 (abfd, mac_ptr, &bytes_read);
              mac_ptr += bytes_read;
              read_direct_string (abfd, mac_ptr, &bytes_read);
              mac_ptr += bytes_read;
@@ -21511,7 +22155,6 @@ dwarf_decode_macros (struct dwarf2_cu *cu, unsigned int offset,
   unsigned int offset_size = cu->header.offset_size;
   const gdb_byte *opcode_definitions[256];
   struct cleanup *cleanup;
-  htab_t include_hash;
   void **slot;
   struct dwarf2_section_info *section;
   const char *section_name;
@@ -21584,7 +22227,7 @@ dwarf_decode_macros (struct dwarf2_cu *cu, unsigned int offset,
          break;
         }
 
-      macinfo_type = read_1_byte (abfd, mac_ptr);
+      macinfo_type = (enum dwarf_macro_record_type) read_1_byte (abfd, mac_ptr);
       mac_ptr++;
 
       /* Note that we rely on the fact that the corresponding GNU and
@@ -21596,8 +22239,8 @@ dwarf_decode_macros (struct dwarf2_cu *cu, unsigned int offset,
         case 0:
          break;
 
-       case DW_MACRO_GNU_define:
-       case DW_MACRO_GNU_undef:
+       case DW_MACRO_define:
+       case DW_MACRO_undef:
          /* Only skip the data by MAC_PTR.  */
          {
            unsigned int bytes_read;
@@ -21609,7 +22252,7 @@ dwarf_decode_macros (struct dwarf2_cu *cu, unsigned int offset,
          }
          break;
 
-       case DW_MACRO_GNU_start_file:
+       case DW_MACRO_start_file:
          {
            unsigned int bytes_read;
            int line, file;
@@ -21623,14 +22266,14 @@ dwarf_decode_macros (struct dwarf2_cu *cu, unsigned int offset,
          }
          break;
 
-       case DW_MACRO_GNU_end_file:
+       case DW_MACRO_end_file:
          /* No data to skip by MAC_PTR.  */
          break;
 
-       case DW_MACRO_GNU_define_indirect:
-       case DW_MACRO_GNU_undef_indirect:
-       case DW_MACRO_GNU_define_indirect_alt:
-       case DW_MACRO_GNU_undef_indirect_alt:
+       case DW_MACRO_define_strp:
+       case DW_MACRO_undef_strp:
+       case DW_MACRO_define_sup:
+       case DW_MACRO_undef_sup:
          {
            unsigned int bytes_read;
 
@@ -21640,10 +22283,10 @@ dwarf_decode_macros (struct dwarf2_cu *cu, unsigned int offset,
          }
          break;
 
-       case DW_MACRO_GNU_transparent_include:
-       case DW_MACRO_GNU_transparent_include_alt:
+       case DW_MACRO_import:
+       case DW_MACRO_import_sup:
          /* Note that, according to the spec, a transparent include
-            chain cannot call DW_MACRO_GNU_start_file.  So, we can just
+            chain cannot call DW_MACRO_start_file.  So, we can just
             skip this opcode.  */
          mac_ptr += offset_size;
          break;
@@ -21677,16 +22320,16 @@ dwarf_decode_macros (struct dwarf2_cu *cu, unsigned int offset,
      command-line macro definitions/undefinitions.  This flag is unset when we
      reach the first DW_MACINFO_start_file entry.  */
 
-  include_hash = htab_create_alloc (1, htab_hash_pointer, htab_eq_pointer,
-                                   NULL, xcalloc, xfree);
-  cleanup = make_cleanup_htab_delete (include_hash);
+  htab_up include_hash (htab_create_alloc (1, htab_hash_pointer,
+                                          htab_eq_pointer,
+                                          NULL, xcalloc, xfree));
   mac_ptr = section->buffer + offset;
-  slot = htab_find_slot (include_hash, mac_ptr, INSERT);
+  slot = htab_find_slot (include_hash.get (), mac_ptr, INSERT);
   *slot = (void *) mac_ptr;
   dwarf_decode_macro_bytes (abfd, mac_ptr, mac_end,
                            current_file, lh, section,
-                           section_is_gnu, 0, offset_size, include_hash);
-  do_cleanups (cleanup);
+                           section_is_gnu, 0, offset_size,
+                           include_hash.get ());
 }
 
 /* Check if the attribute's form is a DW_FORM_block*
@@ -21731,7 +22374,10 @@ attr_form_is_section_offset (const struct attribute *attr)
    (lineptr, loclistptr, macptr or rangelistptr).  The DWARF spec says
    that, if an attribute's can be either a constant or one of the
    section offset classes, DW_FORM_data4 and DW_FORM_data8 should be
-   taken as section offsets, not constants.  */
+   taken as section offsets, not constants.
+
+   DW_FORM_data16 is not considered as dwarf2_get_attr_constant_value
+   cannot handle that.  */
 
 static int
 attr_form_is_constant (const struct attribute *attr)
@@ -21779,8 +22425,13 @@ static struct dwarf2_section_info *
 cu_debug_loc_section (struct dwarf2_cu *cu)
 {
   if (cu->dwo_unit)
-    return &cu->dwo_unit->dwo_file->sections.loc;
-  return &dwarf2_per_objfile->loc;
+    {
+      struct dwo_sections *sections = &cu->dwo_unit->dwo_file->sections;
+      
+      return cu->header.version >= 5 ? &sections->loclists : &sections->loc;
+    }
+  return (cu->header.version >= 5 ? &dwarf2_per_objfile->loclists
+                                 : &dwarf2_per_objfile->loc);
 }
 
 /* A helper function that fills in a dwarf2_loclist_baton.  */
@@ -21819,8 +22470,7 @@ dwarf2_symbol_mark_computed (const struct attribute *attr, struct symbol *sym,
     {
       struct dwarf2_loclist_baton *baton;
 
-      baton = obstack_alloc (&objfile->objfile_obstack,
-                            sizeof (struct dwarf2_loclist_baton));
+      baton = XOBNEW (&objfile->objfile_obstack, struct dwarf2_loclist_baton);
 
       fill_in_loclist_baton (cu, baton, attr);
 
@@ -21838,8 +22488,7 @@ dwarf2_symbol_mark_computed (const struct attribute *attr, struct symbol *sym,
     {
       struct dwarf2_locexpr_baton *baton;
 
-      baton = obstack_alloc (&objfile->objfile_obstack,
-                            sizeof (struct dwarf2_locexpr_baton));
+      baton = XOBNEW (&objfile->objfile_obstack, struct dwarf2_locexpr_baton);
       baton->per_cu = cu->per_cu;
       gdb_assert (baton->per_cu);
 
@@ -21897,10 +22546,11 @@ per_cu_header_read_in (struct comp_unit_head *cu_headerp,
   if (per_cu->cu)
     return &per_cu->cu->header;
 
-  info_ptr = per_cu->section->buffer + per_cu->offset.sect_off;
+  info_ptr = per_cu->section->buffer + to_underlying (per_cu->sect_off);
 
   memset (cu_headerp, 0, sizeof (*cu_headerp));
-  read_comp_unit_head (cu_headerp, info_ptr, per_cu->objfile->obfd);
+  read_comp_unit_head (cu_headerp, info_ptr, per_cu->section,
+                      rcuh_kind::COMPILE);
 
   return cu_headerp;
 }
@@ -21960,11 +22610,19 @@ dwarf2_per_cu_text_offset (struct dwarf2_per_cu_data *per_cu)
   return ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
 }
 
+/* Return DWARF version number of PER_CU.  */
+
+short
+dwarf2_version (struct dwarf2_per_cu_data *per_cu)
+{
+  return per_cu->dwarf_version;
+}
+
 /* Locate the .debug_info compilation unit from CU's objfile which contains
    the DIE at OFFSET.  Raises an error on failure.  */
 
 static struct dwarf2_per_cu_data *
-dwarf2_find_containing_comp_unit (sect_offset offset,
+dwarf2_find_containing_comp_unit (sect_offset sect_off,
                                  unsigned int offset_in_dwz,
                                  struct objfile *objfile)
 {
@@ -21980,35 +22638,34 @@ dwarf2_find_containing_comp_unit (sect_offset offset,
       int mid = low + (high - low) / 2;
 
       mid_cu = dwarf2_per_objfile->all_comp_units[mid];
-      cu_off = &mid_cu->offset;
+      cu_off = &mid_cu->sect_off;
       if (mid_cu->is_dwz > offset_in_dwz
-         || (mid_cu->is_dwz == offset_in_dwz
-             && cu_off->sect_off >= offset.sect_off))
+         || (mid_cu->is_dwz == offset_in_dwz && *cu_off >= sect_off))
        high = mid;
       else
        low = mid + 1;
     }
   gdb_assert (low == high);
   this_cu = dwarf2_per_objfile->all_comp_units[low];
-  cu_off = &this_cu->offset;
-  if (this_cu->is_dwz != offset_in_dwz || cu_off->sect_off > offset.sect_off)
+  cu_off = &this_cu->sect_off;
+  if (this_cu->is_dwz != offset_in_dwz || *cu_off > sect_off)
     {
       if (low == 0 || this_cu->is_dwz != offset_in_dwz)
        error (_("Dwarf Error: could not find partial DIE containing "
-              "offset 0x%lx [in module %s]"),
-              (long) offset.sect_off, bfd_get_filename (objfile->obfd));
+              "offset 0x%x [in module %s]"),
+              to_underlying (sect_off), bfd_get_filename (objfile->obfd));
 
-      gdb_assert (dwarf2_per_objfile->all_comp_units[low-1]->offset.sect_off
-                 <= offset.sect_off);
+      gdb_assert (dwarf2_per_objfile->all_comp_units[low-1]->sect_off
+                 <= sect_off);
       return dwarf2_per_objfile->all_comp_units[low-1];
     }
   else
     {
       this_cu = dwarf2_per_objfile->all_comp_units[low];
       if (low == dwarf2_per_objfile->n_comp_units - 1
-         && offset.sect_off >= this_cu->offset.sect_off + this_cu->length)
-       error (_("invalid dwarf2 offset %u"), offset.sect_off);
-      gdb_assert (offset.sect_off < this_cu->offset.sect_off + this_cu->length);
+         && sect_off >= this_cu->sect_off + this_cu->length)
+       error (_("invalid dwarf2 offset %u"), to_underlying (sect_off));
+      gdb_assert (sect_off < this_cu->sect_off + this_cu->length);
       return this_cu;
     }
 }
@@ -22043,9 +22700,7 @@ prepare_one_comp_unit (struct dwarf2_cu *cu, struct die_info *comp_unit_die,
       cu->language_defn = language_def (cu->language);
     }
 
-  attr = dwarf2_attr (comp_unit_die, DW_AT_producer, cu);
-  if (attr)
-    cu->producer = DW_STRING (attr);
+  cu->producer = dwarf2_string_attr (comp_unit_die, DW_AT_producer, cu);
 }
 
 /* Release one cached compilation unit, CU.  We unlink it from the tree
@@ -22057,7 +22712,7 @@ prepare_one_comp_unit (struct dwarf2_cu *cu, struct die_info *comp_unit_die,
 static void
 free_heap_comp_unit (void *data)
 {
-  struct dwarf2_cu *cu = data;
+  struct dwarf2_cu *cu = (struct dwarf2_cu *) data;
 
   gdb_assert (cu->per_cu != NULL);
   cu->per_cu->cu = NULL;
@@ -22075,7 +22730,7 @@ free_heap_comp_unit (void *data)
 static void
 free_stack_comp_unit (void *data)
 {
-  struct dwarf2_cu *cu = data;
+  struct dwarf2_cu *cu = (struct dwarf2_cu *) data;
 
   gdb_assert (cu->per_cu != NULL);
   cu->per_cu->cu = NULL;
@@ -22179,7 +22834,9 @@ free_one_cached_comp_unit (struct dwarf2_per_cu_data *target_per_cu)
 void
 dwarf2_free_objfile (struct objfile *objfile)
 {
-  dwarf2_per_objfile = objfile_data (objfile, dwarf2_objfile_data_key);
+  dwarf2_per_objfile
+    = (struct dwarf2_per_objfile *) objfile_data (objfile,
+                                                 dwarf2_objfile_data_key);
 
   if (dwarf2_per_objfile == NULL)
     return;
@@ -22213,7 +22870,7 @@ dwarf2_free_objfile (struct objfile *objfile)
 struct dwarf2_per_cu_offset_and_type
 {
   const struct dwarf2_per_cu_data *per_cu;
-  sect_offset offset;
+  sect_offset sect_off;
   struct type *type;
 };
 
@@ -22222,9 +22879,10 @@ struct dwarf2_per_cu_offset_and_type
 static hashval_t
 per_cu_offset_and_type_hash (const void *item)
 {
-  const struct dwarf2_per_cu_offset_and_type *ofs = item;
+  const struct dwarf2_per_cu_offset_and_type *ofs
+    = (const struct dwarf2_per_cu_offset_and_type *) item;
 
-  return (uintptr_t) ofs->per_cu + ofs->offset.sect_off;
+  return (uintptr_t) ofs->per_cu + to_underlying (ofs->sect_off);
 }
 
 /* Equality function for a dwarf2_per_cu_offset_and_type.  */
@@ -22232,11 +22890,13 @@ per_cu_offset_and_type_hash (const void *item)
 static int
 per_cu_offset_and_type_eq (const void *item_lhs, const void *item_rhs)
 {
-  const struct dwarf2_per_cu_offset_and_type *ofs_lhs = item_lhs;
-  const struct dwarf2_per_cu_offset_and_type *ofs_rhs = item_rhs;
+  const struct dwarf2_per_cu_offset_and_type *ofs_lhs
+    = (const struct dwarf2_per_cu_offset_and_type *) item_lhs;
+  const struct dwarf2_per_cu_offset_and_type *ofs_rhs
+    = (const struct dwarf2_per_cu_offset_and_type *) item_rhs;
 
   return (ofs_lhs->per_cu == ofs_rhs->per_cu
-         && ofs_lhs->offset.sect_off == ofs_rhs->offset.sect_off);
+         && ofs_lhs->sect_off == ofs_rhs->sect_off);
 }
 
 /* Set the type associated with DIE to TYPE.  Save it in CU's hash
@@ -22281,6 +22941,36 @@ set_die_type (struct die_info *die, struct type *type, struct dwarf2_cu *cu)
       && !HAVE_GNAT_AUX_INFO (type))
     INIT_GNAT_SPECIFIC (type);
 
+  /* Read DW_AT_allocated and set in type.  */
+  attr = dwarf2_attr (die, DW_AT_allocated, cu);
+  if (attr_form_is_block (attr))
+    {
+      if (attr_to_dynamic_prop (attr, die, cu, &prop))
+        add_dyn_prop (DYN_PROP_ALLOCATED, prop, type, objfile);
+    }
+  else if (attr != NULL)
+    {
+      complaint (&symfile_complaints,
+                _("DW_AT_allocated has the wrong form (%s) at DIE 0x%x"),
+                (attr != NULL ? dwarf_form_name (attr->form) : "n/a"),
+                to_underlying (die->sect_off));
+    }
+
+  /* Read DW_AT_associated and set in type.  */
+  attr = dwarf2_attr (die, DW_AT_associated, cu);
+  if (attr_form_is_block (attr))
+    {
+      if (attr_to_dynamic_prop (attr, die, cu, &prop))
+        add_dyn_prop (DYN_PROP_ASSOCIATED, prop, type, objfile);
+    }
+  else if (attr != NULL)
+    {
+      complaint (&symfile_complaints,
+                _("DW_AT_associated has the wrong form (%s) at DIE 0x%x"),
+                (attr != NULL ? dwarf_form_name (attr->form) : "n/a"),
+                to_underlying (die->sect_off));
+    }
+
   /* Read DW_AT_data_location and set in type.  */
   attr = dwarf2_attr (die, DW_AT_data_location, cu);
   if (attr_to_dynamic_prop (attr, die, cu, &prop))
@@ -22299,24 +22989,25 @@ set_die_type (struct die_info *die, struct type *type, struct dwarf2_cu *cu)
     }
 
   ofs.per_cu = cu->per_cu;
-  ofs.offset = die->offset;
+  ofs.sect_off = die->sect_off;
   ofs.type = type;
   slot = (struct dwarf2_per_cu_offset_and_type **)
     htab_find_slot (dwarf2_per_objfile->die_type_hash, &ofs, INSERT);
   if (*slot)
     complaint (&symfile_complaints,
               _("A problem internal to GDB: DIE 0x%x has type already set"),
-              die->offset.sect_off);
-  *slot = obstack_alloc (&objfile->objfile_obstack, sizeof (**slot));
+              to_underlying (die->sect_off));
+  *slot = XOBNEW (&objfile->objfile_obstack,
+                 struct dwarf2_per_cu_offset_and_type);
   **slot = ofs;
   return type;
 }
 
-/* Look up the type for the die at OFFSET in PER_CU in die_type_hash,
+/* Look up the type for the die at SECT_OFF in PER_CU in die_type_hash,
    or return NULL if the die does not have a saved type.  */
 
 static struct type *
-get_die_type_at_offset (sect_offset offset,
+get_die_type_at_offset (sect_offset sect_off,
                        struct dwarf2_per_cu_data *per_cu)
 {
   struct dwarf2_per_cu_offset_and_type *slot, ofs;
@@ -22325,8 +23016,9 @@ get_die_type_at_offset (sect_offset offset,
     return NULL;
 
   ofs.per_cu = per_cu;
-  ofs.offset = offset;
-  slot = htab_find (dwarf2_per_objfile->die_type_hash, &ofs);
+  ofs.sect_off = sect_off;
+  slot = ((struct dwarf2_per_cu_offset_and_type *)
+         htab_find (dwarf2_per_objfile->die_type_hash, &ofs));
   if (slot)
     return slot->type;
   else
@@ -22339,7 +23031,7 @@ get_die_type_at_offset (sect_offset offset,
 static struct type *
 get_die_type (struct die_info *die, struct dwarf2_cu *cu)
 {
-  return get_die_type_at_offset (die->offset, cu->per_cu);
+  return get_die_type_at_offset (die->sect_off, cu->per_cu);
 }
 
 /* Add a dependence relationship from CU to REF_PER_CU.  */
@@ -22418,9 +23110,10 @@ dwarf2_clear_marks (struct dwarf2_per_cu_data *per_cu)
 static hashval_t
 partial_die_hash (const void *item)
 {
-  const struct partial_die_info *part_die = item;
+  const struct partial_die_info *part_die
+    = (const struct partial_die_info *) item;
 
-  return part_die->offset.sect_off;
+  return to_underlying (part_die->sect_off);
 }
 
 /* Trivial comparison function for partial_die_info structures: two DIEs
@@ -22429,10 +23122,12 @@ partial_die_hash (const void *item)
 static int
 partial_die_eq (const void *item_lhs, const void *item_rhs)
 {
-  const struct partial_die_info *part_die_lhs = item_lhs;
-  const struct partial_die_info *part_die_rhs = item_rhs;
+  const struct partial_die_info *part_die_lhs
+    = (const struct partial_die_info *) item_lhs;
+  const struct partial_die_info *part_die_rhs
+    = (const struct partial_die_info *) item_rhs;
 
-  return part_die_lhs->offset.sect_off == part_die_rhs->offset.sect_off;
+  return part_die_lhs->sect_off == part_die_rhs->sect_off;
 }
 
 static struct cmd_list_element *set_dwarf_cmdlist;
@@ -22456,7 +23151,7 @@ show_dwarf_cmd (char *args, int from_tty)
 static void
 dwarf2_per_objfile_free (struct objfile *objfile, void *d)
 {
-  struct dwarf2_per_objfile *data = d;
+  struct dwarf2_per_objfile *data = (struct dwarf2_per_objfile *) d;
   int ix;
 
   /* Make sure we don't accidentally use dwarf2_per_objfile while
@@ -22501,7 +23196,7 @@ struct strtab_entry
 static hashval_t
 hash_strtab_entry (const void *e)
 {
-  const struct strtab_entry *entry = e;
+  const struct strtab_entry *entry = (const struct strtab_entry *) e;
   return mapped_index_string_hash (INT_MAX, entry->str);
 }
 
@@ -22510,8 +23205,8 @@ hash_strtab_entry (const void *e)
 static int
 eq_strtab_entry (const void *a, const void *b)
 {
-  const struct strtab_entry *ea = a;
-  const struct strtab_entry *eb = b;
+  const struct strtab_entry *ea = (const struct strtab_entry *) a;
+  const struct strtab_entry *eb = (const struct strtab_entry *) b;
   return !strcmp (ea->str, eb->str);
 }
 
@@ -22537,7 +23232,7 @@ add_string (htab_t table, struct obstack *cpool, const char *str)
   entry.str = str;
   slot = htab_find_slot (table, &entry, INSERT);
   if (*slot)
-    result = *slot;
+    result = (struct strtab_entry *) *slot;
   else
     {
       result = XNEW (struct strtab_entry);
@@ -22574,7 +23269,8 @@ struct mapped_symtab
 static hashval_t
 hash_symtab_entry (const void *e)
 {
-  const struct symtab_index_entry *entry = e;
+  const struct symtab_index_entry *entry
+    = (const struct symtab_index_entry *) e;
   return iterative_hash (VEC_address (offset_type, entry->cu_indices),
                         sizeof (offset_type) * VEC_length (offset_type,
                                                            entry->cu_indices),
@@ -22586,8 +23282,8 @@ hash_symtab_entry (const void *e)
 static int
 eq_symtab_entry (const void *a, const void *b)
 {
-  const struct symtab_index_entry *ea = a;
-  const struct symtab_index_entry *eb = b;
+  const struct symtab_index_entry *ea = (const struct symtab_index_entry *) a;
+  const struct symtab_index_entry *eb = (const struct symtab_index_entry *) b;
   int len = VEC_length (offset_type, ea->cu_indices);
   if (len != VEC_length (offset_type, eb->cu_indices))
     return 0;
@@ -22601,7 +23297,7 @@ eq_symtab_entry (const void *a, const void *b)
 static void
 delete_symtab_entry (void *p)
 {
-  struct symtab_index_entry *entry = p;
+  struct symtab_index_entry *entry = (struct symtab_index_entry *) p;
   VEC_free (offset_type, entry->cu_indices);
   xfree (entry);
 }
@@ -22632,7 +23328,7 @@ create_mapped_symtab (void)
 static void
 cleanup_mapped_symtab (void *p)
 {
-  struct mapped_symtab *symtab = p;
+  struct mapped_symtab *symtab = (struct mapped_symtab *) p;
   /* The contents of the array are freed when the other hash table is
      destroyed.  */
   xfree (symtab->data);
@@ -22809,7 +23505,8 @@ add_indices_to_cpool (htab_t symbol_hash_table, struct obstack *cpool,
     }
   else
     {
-      struct symtab_index_entry *old_entry = *slot;
+      struct symtab_index_entry *old_entry
+       = (struct symtab_index_entry *) *slot;
       entry->index_offset = old_entry->index_offset;
       entry = old_entry;
     }
@@ -22877,7 +23574,8 @@ struct psymtab_cu_index_map
 static hashval_t
 hash_psymtab_cu_index (const void *item)
 {
-  const struct psymtab_cu_index_map *map = item;
+  const struct psymtab_cu_index_map *map
+    = (const struct psymtab_cu_index_map *) item;
 
   return htab_hash_pointer (map->psymtab);
 }
@@ -22885,8 +23583,10 @@ hash_psymtab_cu_index (const void *item)
 static int
 eq_psymtab_cu_index (const void *item_lhs, const void *item_rhs)
 {
-  const struct psymtab_cu_index_map *lhs = item_lhs;
-  const struct psymtab_cu_index_map *rhs = item_rhs;
+  const struct psymtab_cu_index_map *lhs
+    = (const struct psymtab_cu_index_map *) item_lhs;
+  const struct psymtab_cu_index_map *rhs
+    = (const struct psymtab_cu_index_map *) item_rhs;
 
   return lhs->psymtab == rhs->psymtab;
 }
@@ -22933,8 +23633,8 @@ add_address_entry (struct objfile *objfile, struct obstack *obstack,
 static int
 add_address_entry_worker (void *datap, CORE_ADDR start_addr, void *obj)
 {
-  struct addrmap_index_data *data = datap;
-  struct partial_symtab *pst = obj;
+  struct addrmap_index_data *data = (struct addrmap_index_data *) datap;
+  struct partial_symtab *pst = (struct partial_symtab *) obj;
 
   if (data->previous_valid)
     add_address_entry (data->objfile, data->addr_obstack,
@@ -22946,7 +23646,8 @@ add_address_entry_worker (void *datap, CORE_ADDR start_addr, void *obj)
     {
       struct psymtab_cu_index_map find_map, *map;
       find_map.psymtab = pst;
-      map = htab_find (data->cu_index_htab, &find_map);
+      map = ((struct psymtab_cu_index_map *)
+            htab_find (data->cu_index_htab, &find_map));
       gdb_assert (map != NULL);
       data->previous_cu_index = map->cu_index;
       data->previous_valid = 1;
@@ -23071,16 +23772,6 @@ write_obstack (FILE *file, struct obstack *obstack)
     error (_("couldn't data write to file"));
 }
 
-/* Unlink a file if the argument is not NULL.  */
-
-static void
-unlink_if_set (void *p)
-{
-  char **filename = p;
-  if (*filename)
-    unlink (*filename);
-}
-
 /* A helper struct used when iterating over debug_types.  */
 struct signatured_type_index_data
 {
@@ -23097,7 +23788,8 @@ struct signatured_type_index_data
 static int
 write_one_signatured_type (void **slot, void *d)
 {
-  struct signatured_type_index_data *info = d;
+  struct signatured_type_index_data *info
+    = (struct signatured_type_index_data *) d;
   struct signatured_type *entry = (struct signatured_type *) *slot;
   struct partial_symtab *psymtab = entry->per_cu.v.psymtab;
   gdb_byte val[8];
@@ -23116,10 +23808,10 @@ write_one_signatured_type (void **slot, void *d)
                  1);
 
   store_unsigned_integer (val, 8, BFD_ENDIAN_LITTLE,
-                         entry->per_cu.offset.sect_off);
+                         to_underlying (entry->per_cu.sect_off));
   obstack_grow (info->types_list, val, 8);
   store_unsigned_integer (val, 8, BFD_ENDIAN_LITTLE,
-                         entry->type_offset_in_tu.cu_off);
+                         to_underlying (entry->type_offset_in_tu));
   obstack_grow (info->types_list, val, 8);
   store_unsigned_integer (val, 8, BFD_ENDIAN_LITTLE, entry->signature);
   obstack_grow (info->types_list, val, 8);
@@ -23164,7 +23856,7 @@ static void
 write_psymtabs_to_index (struct objfile *objfile, const char *dir)
 {
   struct cleanup *cleanup;
-  char *filename, *cleanup_filename;
+  char *filename;
   struct obstack contents, addr_obstack, constant_pool, symtab_obstack;
   struct obstack cu_list, types_cu_list;
   int i;
@@ -23172,8 +23864,6 @@ write_psymtabs_to_index (struct objfile *objfile, const char *dir)
   struct mapped_symtab *symtab;
   offset_type val, size_of_contents, total_len;
   struct stat st;
-  htab_t psyms_seen;
-  htab_t cu_index_htab;
   struct psymtab_cu_index_map *psymtab_cu_index_map;
 
   if (dwarf2_per_objfile->using_index)
@@ -23196,8 +23886,7 @@ write_psymtabs_to_index (struct objfile *objfile, const char *dir)
   if (!out_file)
     error (_("Can't open `%s' for writing"), filename);
 
-  cleanup_filename = filename;
-  make_cleanup (unlink_if_set, &cleanup_filename);
+  gdb::unlinker unlink_file (filename);
 
   symtab = create_mapped_symtab ();
   make_cleanup (cleanup_mapped_symtab, symtab);
@@ -23211,22 +23900,20 @@ write_psymtabs_to_index (struct objfile *objfile, const char *dir)
   obstack_init (&types_cu_list);
   make_cleanup_obstack_free (&types_cu_list);
 
-  psyms_seen = htab_create_alloc (100, htab_hash_pointer, htab_eq_pointer,
-                                 NULL, xcalloc, xfree);
-  make_cleanup_htab_delete (psyms_seen);
+  htab_up psyms_seen (htab_create_alloc (100, htab_hash_pointer,
+                                        htab_eq_pointer,
+                                        NULL, xcalloc, xfree));
 
   /* While we're scanning CU's create a table that maps a psymtab pointer
      (which is what addrmap records) to its index (which is what is recorded
      in the index file).  This will later be needed to write the address
      table.  */
-  cu_index_htab = htab_create_alloc (100,
-                                    hash_psymtab_cu_index,
-                                    eq_psymtab_cu_index,
-                                    NULL, xcalloc, xfree);
-  make_cleanup_htab_delete (cu_index_htab);
-  psymtab_cu_index_map = (struct psymtab_cu_index_map *)
-    xmalloc (sizeof (struct psymtab_cu_index_map)
-            * dwarf2_per_objfile->n_comp_units);
+  htab_up cu_index_htab (htab_create_alloc (100,
+                                           hash_psymtab_cu_index,
+                                           eq_psymtab_cu_index,
+                                           NULL, xcalloc, xfree));
+  psymtab_cu_index_map = XNEWVEC (struct psymtab_cu_index_map,
+                                 dwarf2_per_objfile->n_comp_units);
   make_cleanup (xfree, psymtab_cu_index_map);
 
   /* The CU list is already sorted, so we don't need to do additional
@@ -23248,25 +23935,26 @@ write_psymtabs_to_index (struct objfile *objfile, const char *dir)
        continue;
 
       if (psymtab->user == NULL)
-       recursively_write_psymbols (objfile, psymtab, symtab, psyms_seen, i);
+       recursively_write_psymbols (objfile, psymtab, symtab,
+                                   psyms_seen.get (), i);
 
       map = &psymtab_cu_index_map[i];
       map->psymtab = psymtab;
       map->cu_index = i;
-      slot = htab_find_slot (cu_index_htab, map, INSERT);
+      slot = htab_find_slot (cu_index_htab.get (), map, INSERT);
       gdb_assert (slot != NULL);
       gdb_assert (*slot == NULL);
       *slot = map;
 
       store_unsigned_integer (val, 8, BFD_ENDIAN_LITTLE,
-                             per_cu->offset.sect_off);
+                             to_underlying (per_cu->sect_off));
       obstack_grow (&cu_list, val, 8);
       store_unsigned_integer (val, 8, BFD_ENDIAN_LITTLE, per_cu->length);
       obstack_grow (&cu_list, val, 8);
     }
 
   /* Dump the address map.  */
-  write_address_map (objfile, &addr_obstack, cu_index_htab);
+  write_address_map (objfile, &addr_obstack, cu_index_htab.get ());
 
   /* Write out the .debug_type entries, if any.  */
   if (dwarf2_per_objfile->signatured_types)
@@ -23276,7 +23964,7 @@ write_psymtabs_to_index (struct objfile *objfile, const char *dir)
       sig_data.objfile = objfile;
       sig_data.symtab = symtab;
       sig_data.types_list = &types_cu_list;
-      sig_data.psyms_seen = psyms_seen;
+      sig_data.psyms_seen = psyms_seen.get ();
       sig_data.cu_index = dwarf2_per_objfile->n_comp_units;
       htab_traverse_noresize (dwarf2_per_objfile->signatured_types,
                              write_one_signatured_type, &sig_data);
@@ -23337,9 +24025,8 @@ write_psymtabs_to_index (struct objfile *objfile, const char *dir)
 
   fclose (out_file);
 
-  /* We want to keep the file, so we set cleanup_filename to NULL
-     here.  See unlink_if_set.  */
-  cleanup_filename = NULL;
+  /* We want to keep the file.  */
+  unlink_file.keep ();
 
   do_cleanups (cleanup);
 }
@@ -23365,7 +24052,9 @@ save_gdb_index_command (char *arg, int from_tty)
     if (stat (objfile_name (objfile), &st) < 0)
       continue;
 
-    dwarf2_per_objfile = objfile_data (objfile, dwarf2_objfile_data_key);
+    dwarf2_per_objfile
+      = (struct dwarf2_per_objfile *) objfile_data (objfile,
+                                                   dwarf2_objfile_data_key);
     if (dwarf2_per_objfile)
       {
 
This page took 0.199223 seconds and 4 git commands to generate.