gdb: add target_ops::supports_displaced_step
[deliverable/binutils-gdb.git] / gdb / mipsread.c
index 6f7cad899702237e3a3d24aecbed8b0354d0228c..6e39538e952d1ce53123f3d6e077b6d53f361227 100644 (file)
@@ -1,7 +1,6 @@
 /* Read a symbol table in MIPS' format (Third-Eye).
 
-   Copyright (C) 1986, 1987, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996,
-   1998, 1999, 2000, 2001, 2003, 2004, 2007 Free Software Foundation, Inc.
+   Copyright (C) 1986-2020 Free Software Foundation, Inc.
 
    Contributed by Alessandro Forin (af@cs.cmu.edu) at CMU.  Major work
    by Per Bothner, John Gilmore and Ian Lance Taylor at Cygnus Support.
    mdebugread.c.  */
 
 #include "defs.h"
-#include "gdb_string.h"
 #include "bfd.h"
 #include "symtab.h"
 #include "objfiles.h"
-#include "buildsym.h"
 #include "stabsread.h"
+#include "mdebugread.h"
 
 #include "coff/sym.h"
 #include "coff/internal.h"
 #include "libcoff.h"           /* Private BFD COFF information.  */
 #include "libecoff.h"          /* Private BFD ECOFF information.  */
 #include "elf/common.h"
+#include "elf/internal.h"
 #include "elf/mips.h"
 
+#include "psymtab.h"
+
 static void
-read_alphacoff_dynamic_symtab (struct section_offsets *,
+read_alphacoff_dynamic_symtab (minimal_symbol_reader &,
                               struct objfile *objfile);
 
 /* Initialize anything that needs initializing when a completely new
@@ -52,7 +53,6 @@ static void
 mipscoff_new_init (struct objfile *ignore)
 {
   stabsread_new_init ();
-  buildsym_new_init ();
 }
 
 /* Initialize to read a symbol file (nothing to do).  */
@@ -65,33 +65,30 @@ mipscoff_symfile_init (struct objfile *objfile)
 /* Read a symbol file from a file.  */
 
 static void
-mipscoff_symfile_read (struct objfile *objfile, int mainline)
+mipscoff_symfile_read (struct objfile *objfile, symfile_add_flags symfile_flags)
 {
   bfd *abfd = objfile->obfd;
-  struct cleanup *back_to;
 
-  init_minimal_symbol_collection ();
-  back_to = make_cleanup_discard_minimal_symbols ();
+  minimal_symbol_reader reader (objfile);
 
   /* Now that the executable file is positioned at symbol table,
      process it and define symbols accordingly.  */
 
   if (!((*ecoff_backend (abfd)->debug_swap.read_debug_info)
-       (abfd, (asection *) NULL, &ecoff_data (abfd)->debug_info)))
+       (abfd, NULL, &ecoff_data (abfd)->debug_info)))
     error (_("Error reading symbol table: %s"), bfd_errmsg (bfd_get_error ()));
 
-  mdebug_build_psymtabs (objfile, &ecoff_backend (abfd)->debug_swap,
+  mdebug_build_psymtabs (reader, objfile, &ecoff_backend (abfd)->debug_swap,
                         &ecoff_data (abfd)->debug_info);
 
   /* Add alpha coff dynamic symbols.  */
 
-  read_alphacoff_dynamic_symtab (objfile->section_offsets, objfile);
+  read_alphacoff_dynamic_symtab (reader, objfile);
 
   /* Install any minimal symbols that have been collected as the current
-     minimal symbols for this objfile. */
+     minimal symbols for this objfile.  */
 
-  install_minimal_symbols (objfile);
-  do_cleanups (back_to);
+  reader.install ();
 }
 
 /* Perform any local cleanups required when we are done with a
@@ -106,7 +103,7 @@ mipscoff_symfile_finish (struct objfile *objfile)
    standard COFF section.  The ELF format for the symbols differs from
    the format defined in elf/external.h.  It seems that a normal ELF
    32-bit format is used, and the representation only changes because
-   longs are 64-bit on the alpha. In addition, the handling of
+   longs are 64-bit on the alpha.  In addition, the handling of
    text/data section indices for symbols is different from the ELF
    ABI.  As the BFD linker currently does not support dynamic linking
    on the alpha, there seems to be no reason to pollute BFD with
@@ -175,29 +172,20 @@ alphacoff_locate_sections (bfd *ignore_abfd, asection *sectp, void *sip)
    them to the minimal symbol table.  */
 
 static void
-read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
+read_alphacoff_dynamic_symtab (minimal_symbol_reader &reader,
                               struct objfile *objfile)
 {
   bfd *abfd = objfile->obfd;
   struct alphacoff_dynsecinfo si;
-  char *sym_secptr;
-  char *str_secptr;
-  char *dyninfo_secptr;
-  char *got_secptr;
-  bfd_size_type sym_secsize;
-  bfd_size_type str_secsize;
-  bfd_size_type dyninfo_secsize;
-  bfd_size_type got_secsize;
   int sym_count;
   int i;
   int stripped;
   Elfalpha_External_Sym *x_symp;
-  char *dyninfo_p;
-  char *dyninfo_end;
+  gdb_byte *dyninfo_p;
+  gdb_byte *dyninfo_end;
   int got_entry_size = 8;
   int dt_mips_local_gotno = -1;
   int dt_mips_gotsym = -1;
-  struct cleanup *cleanups;
 
   /* We currently only know how to handle alpha dynamic symbols.  */
   if (bfd_get_arch (abfd) != bfd_arch_alpha)
@@ -210,35 +198,28 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
       || si.dyninfo_sect == NULL || si.got_sect == NULL)
     return;
 
-  sym_secsize = bfd_get_section_size (si.sym_sect);
-  str_secsize = bfd_get_section_size (si.str_sect);
-  dyninfo_secsize = bfd_get_section_size (si.dyninfo_sect);
-  got_secsize = bfd_get_section_size (si.got_sect);
-  sym_secptr = xmalloc (sym_secsize);
-  cleanups = make_cleanup (free, sym_secptr);
-  str_secptr = xmalloc (str_secsize);
-  make_cleanup (free, str_secptr);
-  dyninfo_secptr = xmalloc (dyninfo_secsize);
-  make_cleanup (free, dyninfo_secptr);
-  got_secptr = xmalloc (got_secsize);
-  make_cleanup (free, got_secptr);
-
-  if (!bfd_get_section_contents (abfd, si.sym_sect, sym_secptr,
-                                (file_ptr) 0, sym_secsize))
+  gdb::byte_vector sym_sec (bfd_section_size (si.sym_sect));
+  gdb::byte_vector str_sec (bfd_section_size (si.str_sect));
+  gdb::byte_vector dyninfo_sec (bfd_section_size (si.dyninfo_sect));
+  gdb::byte_vector got_sec (bfd_section_size (si.got_sect));
+
+  if (!bfd_get_section_contents (abfd, si.sym_sect, sym_sec.data (),
+                                (file_ptr) 0, sym_sec.size ()))
     return;
-  if (!bfd_get_section_contents (abfd, si.str_sect, str_secptr,
-                                (file_ptr) 0, str_secsize))
+  if (!bfd_get_section_contents (abfd, si.str_sect, str_sec.data (),
+                                (file_ptr) 0, str_sec.size ()))
     return;
-  if (!bfd_get_section_contents (abfd, si.dyninfo_sect, dyninfo_secptr,
-                                (file_ptr) 0, dyninfo_secsize))
+  if (!bfd_get_section_contents (abfd, si.dyninfo_sect, dyninfo_sec.data (),
+                                (file_ptr) 0, dyninfo_sec.size ()))
     return;
-  if (!bfd_get_section_contents (abfd, si.got_sect, got_secptr,
-                                (file_ptr) 0, got_secsize))
+  if (!bfd_get_section_contents (abfd, si.got_sect, got_sec.data (),
+                                (file_ptr) 0, got_sec.size ()))
     return;
 
-  /* Find the number of local GOT entries and the index for the the
+  /* Find the number of local GOT entries and the index for the
      first dynamic symbol in the GOT.  */
-  for (dyninfo_p = dyninfo_secptr, dyninfo_end = dyninfo_p + dyninfo_secsize;
+  for ((dyninfo_p = dyninfo_sec.data (),
+       dyninfo_end = dyninfo_p + dyninfo_sec.size ());
        dyninfo_p < dyninfo_end;
        dyninfo_p += sizeof (Elfalpha_External_Dyn))
     {
@@ -266,11 +247,11 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
 
   /* Scan all dynamic symbols and enter them into the minimal symbol
      table if appropriate.  */
-  sym_count = sym_secsize / sizeof (Elfalpha_External_Sym);
+  sym_count = sym_sec.size () / sizeof (Elfalpha_External_Sym);
   stripped = (bfd_get_symcount (abfd) == 0);
 
   /* Skip first symbol, which is a null dummy.  */
-  for (i = 1, x_symp = (Elfalpha_External_Sym *) sym_secptr + 1;
+  for (i = 1, x_symp = (Elfalpha_External_Sym *) sym_sec.data () + 1;
        i < sym_count;
        i++, x_symp++)
     {
@@ -283,15 +264,17 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
       enum minimal_symbol_type ms_type;
 
       strx = bfd_h_get_32 (abfd, (bfd_byte *) x_symp->st_name);
-      if (strx >= str_secsize)
+      if (strx >= str_sec.size ())
        continue;
-      name = str_secptr + strx;
+      name = (char *) (str_sec.data () + strx);
       if (*name == '\0' || *name == '.')
        continue;
 
       sym_value = bfd_h_get_64 (abfd, (bfd_byte *) x_symp->st_value);
       sym_info = bfd_h_get_8 (abfd, (bfd_byte *) x_symp->st_info);
       sym_shndx = bfd_h_get_16 (abfd, (bfd_byte *) x_symp->st_shndx);
+      if (sym_shndx >= (SHN_LORESERVE & 0xffff))
+       sym_shndx += SHN_LORESERVE - (SHN_LORESERVE & 0xffff);
       isglobal = (ELF_ST_BIND (sym_info) == STB_GLOBAL);
 
       if (sym_shndx == SHN_UNDEF)
@@ -324,18 +307,20 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
              int got_entry_offset =
                (i - dt_mips_gotsym + dt_mips_local_gotno) * got_entry_size;
 
-             if (got_entry_offset < 0 || got_entry_offset >= got_secsize)
+             if (got_entry_offset < 0
+                 || got_entry_offset >= got_sec.size ())
                continue;
              sym_value =
                bfd_h_get_64 (abfd,
-                             (bfd_byte *) (got_secptr + got_entry_offset));
+                             (bfd_byte *) (got_sec.data ()
+                                           + got_entry_offset));
              if (sym_value == 0)
                continue;
            }
        }
       else
        {
-         /* Symbols defined in the executable itself. We only care
+         /* Symbols defined in the executable itself.  We only care
             about them if this is a stripped executable, otherwise
             they have been retrieved from the normal symbol table
             already.  */
@@ -348,7 +333,6 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
                ms_type = mst_text;
              else
                ms_type = mst_file_text;
-             sym_value += ANOFFSET (section_offsets, SECT_OFF_TEXT (objfile));
            }
          else if (sym_shndx == SHN_MIPS_DATA)
            {
@@ -356,7 +340,6 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
                ms_type = mst_data;
              else
                ms_type = mst_file_data;
-             sym_value += ANOFFSET (section_offsets, SECT_OFF_DATA (objfile));
            }
          else if (sym_shndx == SHN_MIPS_ACOMMON)
            {
@@ -364,7 +347,6 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
                ms_type = mst_bss;
              else
                ms_type = mst_file_bss;
-             sym_value += ANOFFSET (section_offsets, SECT_OFF_BSS (objfile));
            }
          else if (sym_shndx == SHN_ABS)
            {
@@ -376,33 +358,30 @@ read_alphacoff_dynamic_symtab (struct section_offsets *section_offsets,
            }
        }
 
-      prim_record_minimal_symbol (name, sym_value, ms_type, objfile);
+      reader.record (name, sym_value, ms_type);
     }
-
-  do_cleanups (cleanups);
 }
 
 /* Initialization.  */
 
-static struct sym_fns ecoff_sym_fns =
+static const struct sym_fns ecoff_sym_fns =
 {
-  bfd_target_ecoff_flavour,
-  mipscoff_new_init,           /* sym_new_init: init anything gbl to entire symtab */
-  mipscoff_symfile_init,       /* sym_init: read initial info, setup for sym_read() */
-  mipscoff_symfile_read,       /* sym_read: read a symbol file into symtab */
-  mipscoff_symfile_finish,     /* sym_finish: finished with file, cleanup */
-  default_symfile_offsets,     /* sym_offsets: dummy FIXME til implem sym reloc */
-  default_symfile_segments,    /* sym_segments: Get segment information from
-                                  a file.  */
-  NULL,                         /* sym_read_linetable */
-  NULL                         /* next: pointer to next struct sym_fns */
+  mipscoff_new_init,           /* init anything gbl to entire symtab */
+  mipscoff_symfile_init,       /* read initial info, setup for sym_read() */
+  mipscoff_symfile_read,       /* read a symbol file into symtab */
+  NULL,                                /* sym_read_psymbols */
+  mipscoff_symfile_finish,     /* finished with file, cleanup */
+  default_symfile_offsets,     /* dummy FIXME til implem sym reloc */
+  default_symfile_segments,    /* Get segment information from a file.  */
+  NULL,
+  default_symfile_relocate,    /* Relocate a debug section.  */
+  NULL,                                /* sym_probe_fns */
+  &psym_functions
 };
 
-/* Provide a prototype to silence -Wmissing-prototypes.  */
-void _initialize_mipsread (void);
-
+void _initialize_mipsread ();
 void
-_initialize_mipsread (void)
+_initialize_mipsread ()
 {
-  add_symtab_fns (&ecoff_sym_fns);
+  add_symtab_fns (bfd_target_ecoff_flavour, &ecoff_sym_fns);
 }
This page took 0.028447 seconds and 4 git commands to generate.