2003-01-18 Andrew Cagney <ac131313@redhat.com>
[deliverable/binutils-gdb.git] / gdb / xcoffread.c
index 00b99d51bb33f78df0c96d8bfd298ead428ece6e..34c506f56e42499f513c9037c432935c52eb0cfa 100644 (file)
@@ -1,5 +1,6 @@
 /* Read AIX xcoff symbol tables and convert to internal format, for GDB.
-   Copyright 1986, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 1997
+   Copyright 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995,
+   1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003
    Free Software Foundation, Inc.
    Derived from coffread.c, dbxread.c, and a lot of hacking.
    Contributed by IBM Corporation.
@@ -37,6 +38,8 @@
 
 #include "coff/internal.h"
 #include "libcoff.h"           /* FIXME, internal data from BFD */
+#include "coff/xcoff.h"
+#include "libxcoff.h"
 #include "coff/rs6000.h"
 
 #include "symtab.h"
@@ -46,7 +49,6 @@
 #include "buildsym.h"
 #include "stabsread.h"
 #include "expression.h"
-#include "language.h"          /* Needed inside partial-stab.h */
 #include "complaints.h"
 
 #include "gdb-stabs.h"
 /* For interface with stabsread.c.  */
 #include "aout/stab_gnu.h"
 
-/* For interface with partial-stab.h.  */
-#define N_UNDF 0               /* Undefined symbol */
-#undef N_ABS
-#define N_ABS 2
-#define N_TEXT         4               /* Text sym -- defined at offset in text seg */
-#define N_DATA         6               /* Data sym -- defined at offset in data seg */
-#define N_BSS  8               /* BSS  sym -- defined at offset in zero'd seg */
-#define        N_COMM  0x12            /* Common symbol (visible after shared lib dynlink) */
-#define N_FN   0x1f            /* File name of .o file */
-#define        N_FN_SEQ 0x0C           /* N_FN from Sequent compilers (sigh) */
-/* Note: N_EXT can only be usefully OR-ed with N_UNDF, N_ABS, N_TEXT,
-   N_DATA, or N_BSS.  When the low-order bit of other types is set,
-   (e.g. N_WARNING versus N_FN), they are two different types.  */
-#define N_EXT  1               /* External symbol (as opposed to local-to-this-file) */
-#define N_INDR 0x0a
-
-/* The following symbols refer to set elements.
-   All the N_SET[ATDB] symbols with the same name form one set.
-   Space is allocated for the set in the text section, and each set
-   elements value is stored into one word of the space.
-   The first word of the space is the length of the set (number of elements).
-
-   The address of the set is made into an N_SETV symbol
-   whose name is the same as the name of the set.
-   This symbol acts like a N_DATA global symbol
-   in that it can satisfy undefined external references.  */
-
-/* These appear as input to LD, in a .o file.  */
-#define        N_SETA  0x14            /* Absolute set element symbol */
-#define        N_SETT  0x16            /* Text set element symbol */
-#define        N_SETD  0x18            /* Data set element symbol */
-#define        N_SETB  0x1A            /* Bss set element symbol */
-
-/* This is output from LD.  */
-#define N_SETV 0x1C            /* Pointer to set vector in data area.  */
 \f
 /* We put a pointer to this structure in the read_symtab_private field
    of the psymtab.  */
@@ -183,17 +150,25 @@ struct coff_symfile_info
     CORE_ADDR toc_offset;
   };
 
-static struct complaint storclass_complaint =
-{"Unexpected storage class: %d", 0, 0};
-
-static struct complaint bf_notfound_complaint =
-{"line numbers off, `.bf' symbol not found", 0, 0};
+static void
+bf_notfound_complaint (void)
+{
+  complaint (&symfile_complaints, "line numbers off, `.bf' symbol not found");
+}
 
-static struct complaint ef_complaint =
-{"Mismatched .ef symbol ignored starting at symnum %d", 0, 0};
+static void
+ef_complaint (int arg1)
+{
+  complaint (&symfile_complaints,
+            "Mismatched .ef symbol ignored starting at symnum %d", arg1);
+}
 
-static struct complaint eb_complaint =
-{"Mismatched .eb symbol ignored starting at symnum %d", 0, 0};
+static void
+eb_complaint (int arg1)
+{
+  complaint (&symfile_complaints,
+            "Mismatched .eb symbol ignored starting at symnum %d", arg1);
+}
 
 static void xcoff_initial_scan (struct objfile *, int);
 
@@ -218,7 +193,7 @@ static void xcoff_symfile_finish (struct objfile *);
 static void
 xcoff_symfile_offsets (struct objfile *, struct section_addr_info *addrs);
 
-static void find_linenos (bfd *, sec_ptr, PTR);
+static void find_linenos (bfd *, sec_ptr, void *);
 
 static char *coff_getfilename (union internal_auxent *, struct objfile *);
 
@@ -262,10 +237,7 @@ struct find_targ_sec_arg
 static void find_targ_sec (bfd *, asection *, void *);
 
 static void
-find_targ_sec (abfd, sect, obj)
-     bfd *abfd;
-     asection *sect;
-     PTR obj;
+find_targ_sec (bfd *abfd, asection *sect, void *obj)
 {
   struct find_targ_sec_arg *args = (struct find_targ_sec_arg *) obj;
   struct objfile *objfile = args->objfile;
@@ -277,16 +249,14 @@ find_targ_sec (abfd, sect, obj)
       else if (bfd_get_section_flags (abfd, sect) & SEC_LOAD)
        *args->resultp = SECT_OFF_DATA (objfile);
       else
-       *args->resultp = SECT_OFF_BSS (objfile);
+       *args->resultp = sect->index;
       *args->bfd_sect = sect;
     }
 }
 
 /* Return the section number (SECT_OFF_*) that CS points to.  */
 static int
-secnum_to_section (secnum, objfile)
-     int secnum;
-     struct objfile *objfile;
+secnum_to_section (int secnum, struct objfile *objfile)
 {
   int off = SECT_OFF_TEXT (objfile);
   asection *sect = NULL;
@@ -301,9 +271,7 @@ secnum_to_section (secnum, objfile)
 
 /* Return the BFD section that CS points to.  */
 static asection *
-secnum_to_bfd_section (secnum, objfile)
-     int secnum;
-     struct objfile *objfile;
+secnum_to_bfd_section (int secnum, struct objfile *objfile)
 {
   int off = SECT_OFF_TEXT (objfile);
   asection *sect = NULL;
@@ -321,9 +289,7 @@ secnum_to_bfd_section (secnum, objfile)
 #if 0
 
 static void
-add_stab_to_list (stabname, stabvector)
-     char *stabname;
-     struct pending_stabs **stabvector;
+add_stab_to_list (char *stabname, struct pending_stabs **stabvector)
 {
   if (*stabvector == NULL)
     {
@@ -403,9 +369,7 @@ add_stab_to_list (stabname, stabvector)
 /* compare line table entry addresses. */
 
 static int
-compare_lte (lte1p, lte2p)
-     const void *lte1p;
-     const void *lte2p;
+compare_lte (const void *lte1p, const void *lte2p)
 {
   struct linetable_entry *lte1 = (struct linetable_entry *) lte1p;
   struct linetable_entry *lte2 = (struct linetable_entry *) lte2p;
@@ -419,8 +383,7 @@ compare_lte (lte1p, lte2p)
    sort_linevec = 1 to end_symtab.  */
 
 static struct linetable *
-arrange_linetable (oldLineTb)
-     struct linetable *oldLineTb;      /* old linetable */
+arrange_linetable (struct linetable *oldLineTb)
 {
   int ii, jj, newline,         /* new line count */
     function_count;            /* # of functions */
@@ -455,7 +418,7 @@ arrange_linetable (oldLineTb)
 
   if (function_count == 0)
     {
-      free (fentry);
+      xfree (fentry);
       return oldLineTb;
     }
   else if (function_count > 1)
@@ -485,7 +448,7 @@ arrange_linetable (oldLineTb)
           ++jj, ++newline)
        newLineTb->item[newline] = oldLineTb->item[jj];
     }
-  free (fentry);
+  xfree (fentry);
   newLineTb->nitems = oldLineTb->nitems - function_count;
   return newLineTb;
 }
@@ -518,8 +481,7 @@ static int inclDepth;               /* nested include depth */
 static void allocate_include_entry (void);
 
 static void
-record_include_begin (cs)
-     struct coff_symbol *cs;
+record_include_begin (struct coff_symbol *cs)
 {
   if (inclDepth)
     {
@@ -529,9 +491,7 @@ record_include_begin (cs)
       /* This can happen with old versions of GCC.
          GCC 2.3.3-930426 does not exhibit this on a test case which
          a user said produced the message for him.  */
-      static struct complaint msg =
-      {"Nested C_BINCL symbols", 0, 0};
-      complain (&msg);
+      complaint (&symfile_complaints, "Nested C_BINCL symbols");
     }
   ++inclDepth;
 
@@ -542,16 +502,13 @@ record_include_begin (cs)
 }
 
 static void
-record_include_end (cs)
-     struct coff_symbol *cs;
+record_include_end (struct coff_symbol *cs)
 {
   InclTable *pTbl;
 
   if (inclDepth == 0)
     {
-      static struct complaint msg =
-      {"Mismatched C_BINCL/C_EINCL pair", 0, 0};
-      complain (&msg);
+      complaint (&symfile_complaints, "Mismatched C_BINCL/C_EINCL pair");
     }
 
   allocate_include_entry ();
@@ -564,7 +521,7 @@ record_include_end (cs)
 }
 
 static void
-allocate_include_entry ()
+allocate_include_entry (void)
 {
   if (inclTable == NULL)
     {
@@ -593,8 +550,7 @@ static struct partial_symtab *this_symtab_psymtab;
    at times) process its lines and create appropriate line vectors. */
 
 static void
-process_linenos (start, end)
-     CORE_ADDR start, end;
+process_linenos (CORE_ADDR start, CORE_ADDR end)
 {
   int offset, ii;
   file_ptr max_offset =
@@ -690,7 +646,7 @@ process_linenos (start, end)
        }
       else
        {
-         free (lv);
+         xfree (lv);
          current_subfile->line_vector = lineTb;
        }
 
@@ -740,7 +696,7 @@ process_linenos (start, end)
            if (fakename == NULL)
              fakename = " ?";
            start_subfile (fakename, (char *) 0);
-           free (current_subfile->name);
+           xfree (current_subfile->name);
          }
          current_subfile->name = xstrdup (inclTable[ii].name);
 #endif
@@ -755,7 +711,7 @@ process_linenos (start, end)
            }
          else
            {
-             free (lv);
+             xfree (lv);
              current_subfile->line_vector = lineTb;
            }
 
@@ -775,7 +731,7 @@ return_after_cleanup:
 }
 
 void
-aix_process_linenos ()
+aix_process_linenos (void)
 {
   /* process line numbers and enter them into line vector */
   process_linenos (last_source_start_addr, cur_src_end_addr);
@@ -791,12 +747,9 @@ aix_process_linenos ()
    attention to.  */
 
 static void
-enter_line_range (subfile, beginoffset, endoffset, startaddr, endaddr,
-                 firstLine)
-     struct subfile *subfile;
-     unsigned beginoffset, endoffset;  /* offsets to line table */
-     CORE_ADDR startaddr, endaddr;
-     unsigned *firstLine;
+enter_line_range (struct subfile *subfile, unsigned beginoffset, unsigned endoffset,   /* offsets to line table */
+                 CORE_ADDR startaddr,  /* offsets to line table */
+                 CORE_ADDR endaddr, unsigned *firstLine)
 {
   unsigned int curoffset;
   CORE_ADDR addr;
@@ -817,9 +770,8 @@ enter_line_range (subfile, beginoffset, endoffset, startaddr, endaddr,
     {
       if (endoffset >= limit_offset)
        {
-         static struct complaint msg =
-         {"Bad line table offset in C_EINCL directive", 0, 0};
-         complain (&msg);
+         complaint (&symfile_complaints,
+                    "Bad line table offset in C_EINCL directive");
          return;
        }
       limit_offset = endoffset;
@@ -834,7 +786,7 @@ enter_line_range (subfile, beginoffset, endoffset, startaddr, endaddr,
   while (curoffset <= limit_offset)
     {
       bfd_seek (abfd, curoffset, SEEK_SET);
-      bfd_read (ext_lnno, linesz, 1, abfd);
+      bfd_bread (ext_lnno, linesz, abfd);
       bfd_coff_swap_lineno_in (abfd, ext_lnno, &int_lnno);
 
       /* Find the address this line represents.  */
@@ -912,12 +864,9 @@ static char *raw_symbol;
    continuations.  */
 
 static char *
-xcoff_next_symbol_text (objfile)
-     struct objfile *objfile;
+xcoff_next_symbol_text (struct objfile *objfile)
 {
   struct internal_syment symbol;
-  static struct complaint msg =
-  {"Unexpected symbol continuation", 0, 0};
   char *retval;
   /* FIXME: is this the same as the passed arg? */
   objfile = this_symtab_psymtab->objfile;
@@ -925,7 +874,7 @@ xcoff_next_symbol_text (objfile)
   bfd_coff_swap_sym_in (objfile->obfd, raw_symbol, &symbol);
   if (symbol.n_zeroes)
     {
-      complain (&msg);
+      complaint (&symfile_complaints, "Unexpected symbol continuation");
 
       /* Return something which points to '\0' and hope the symbol reading
          code does something reasonable.  */
@@ -942,7 +891,7 @@ xcoff_next_symbol_text (objfile)
     }
   else
     {
-      complain (&msg);
+      complaint (&symfile_complaints, "Unexpected symbol continuation");
 
       /* Return something which points to '\0' and hope the symbol reading
          code does something reasonable.  */
@@ -954,8 +903,7 @@ xcoff_next_symbol_text (objfile)
 /* Read symbols for a given partial symbol table.  */
 
 static void
-read_xcoff_symtab (pst)
-     struct partial_symtab *pst;
+read_xcoff_symtab (struct partial_symtab *pst)
 {
   struct objfile *objfile = pst->objfile;
   bfd *abfd = objfile->obfd;
@@ -963,7 +911,7 @@ read_xcoff_symtab (pst)
   char *strtbl = ((struct coff_symfile_info *) objfile->sym_private)->strtbl;
   char *debugsec =
   ((struct coff_symfile_info *) objfile->sym_private)->debugsec;
-  char *debugfmt = xcoff_data (abfd)->xcoff64 ? "XCOFF64" : "XCOFF";
+  char *debugfmt = bfd_xcoff_is_xcoff64 (abfd) ? "XCOFF64" : "XCOFF";
 
   struct internal_syment symbol[1];
   union internal_auxent main_aux;
@@ -1100,14 +1048,6 @@ read_xcoff_symtab (pst)
          /* done with all files, everything from here on is globals */
        }
 
-      /* if explicitly specified as a function, treat is as one. */
-      if (ISFCN (cs->c_type) && cs->c_sclass != C_TPDEF)
-       {
-         bfd_coff_swap_aux_in (abfd, raw_auxptr, cs->c_type, cs->c_sclass,
-                               0, cs->c_naux, &main_aux);
-         goto function_entry_point;
-       }
-
       if ((cs->c_sclass == C_EXT || cs->c_sclass == C_HIDEXT)
          && cs->c_naux == 1)
        {
@@ -1177,7 +1117,8 @@ read_xcoff_symtab (pst)
                                                SECT_OFF_TEXT (objfile));
                      file_end_addr = file_start_addr + CSECT_LEN (&main_aux);
 
-                     if (cs->c_name && cs->c_name[0] == '.')
+                     if (cs->c_name && (cs->c_name[0] == '.'
+                                        || cs->c_name[0] == '@'))
                        {
                          last_csect_name = cs->c_name;
                          last_csect_val = cs->c_value;
@@ -1251,6 +1192,16 @@ read_xcoff_symtab (pst)
            }
        }
 
+      /* If explicitly specified as a function, treat is as one.  This check
+        evaluates to true for @FIX* bigtoc CSECT symbols, so it must occur
+        after the above CSECT check.  */
+      if (ISFCN (cs->c_type) && cs->c_sclass != C_TPDEF)
+       {
+         bfd_coff_swap_aux_in (abfd, raw_auxptr, cs->c_type, cs->c_sclass,
+                               0, cs->c_naux, &main_aux);
+         goto function_entry_point;
+       }
+
       switch (cs->c_sclass)
        {
 
@@ -1332,7 +1283,7 @@ read_xcoff_symtab (pst)
 
              if (context_stack_depth <= 0)
                {               /* We attempted to pop an empty context stack */
-                 complain (&ef_complaint, cs->c_symnum);
+                 ef_complaint (cs->c_symnum);
                  within_function = 0;
                  break;
                }
@@ -1340,7 +1291,7 @@ read_xcoff_symtab (pst)
              /* Stack must be empty now.  */
              if (context_stack_depth > 0 || new == NULL)
                {
-                 complain (&ef_complaint, cs->c_symnum);
+                 ef_complaint (cs->c_symnum);
                  within_function = 0;
                  break;
                }
@@ -1382,9 +1333,8 @@ read_xcoff_symtab (pst)
        case C_UNTAG:
        case C_ENTAG:
          {
-           static struct complaint msg =
-           {"Unrecognized storage class %d.", 0, 0};
-           complain (&msg, cs->c_sclass);
+           complaint (&symfile_complaints, "Unrecognized storage class %d.",
+                      cs->c_sclass);
          }
          break;
 
@@ -1426,13 +1376,13 @@ read_xcoff_symtab (pst)
            {
              if (context_stack_depth <= 0)
                {               /* We attempted to pop an empty context stack */
-                 complain (&eb_complaint, cs->c_symnum);
+                 eb_complaint (cs->c_symnum);
                  break;
                }
              new = pop_context ();
              if (depth-- != new->depth)
                {
-                 complain (&eb_complaint, cs->c_symnum);
+                 eb_complaint (cs->c_symnum);
                  break;
                }
              if (local_symbols && context_stack_depth > 0)
@@ -1488,9 +1438,7 @@ static struct type *var_symbol_type;
 /* process one xcoff symbol. */
 
 static struct symbol *
-process_xcoff_symbol (cs, objfile)
-     register struct coff_symbol *cs;
-     struct objfile *objfile;
+process_xcoff_symbol (register struct coff_symbol *cs, struct objfile *objfile)
 {
   struct symbol onesymbol;
   register struct symbol *sym = &onesymbol;
@@ -1572,7 +1520,8 @@ process_xcoff_symbol (cs, objfile)
          break;
 
        default:
-         complain (&storclass_complaint, cs->c_sclass);
+         complaint (&symfile_complaints, "Unexpected storage class: %d",
+                    cs->c_sclass);
          /* FALLTHROUGH */
 
        case C_DECL:
@@ -1627,9 +1576,7 @@ process_xcoff_symbol (cs, objfile)
    Result is in static storage and is only good for temporary use.  */
 
 static char *
-coff_getfilename (aux_entry, objfile)
-     union internal_auxent *aux_entry;
-     struct objfile *objfile;
+coff_getfilename (union internal_auxent *aux_entry, struct objfile *objfile)
 {
   static char buffer[BUFSIZ];
 
@@ -1647,9 +1594,7 @@ coff_getfilename (aux_entry, objfile)
 
 /* Set *SYMBOL to symbol number symno in symtbl.  */
 static void
-read_symbol (symbol, symno)
-     struct internal_syment *symbol;
-     int symno;
+read_symbol (struct internal_syment *symbol, int symno)
 {
   int nsyms =
   ((struct coff_symfile_info *) this_symtab_psymtab->objfile->sym_private)
@@ -1659,9 +1604,7 @@ read_symbol (symbol, symno)
   ->symtbl;
   if (symno < 0 || symno >= nsyms)
     {
-      static struct complaint msg =
-      {"Invalid symbol offset", 0, 0};
-      complain (&msg);
+      complaint (&symfile_complaints, "Invalid symbol offset");
       symbol->n_value = 0;
       symbol->n_scnum = -1;
       return;
@@ -1674,8 +1617,7 @@ read_symbol (symbol, symno)
 /* Get value corresponding to symbol number symno in symtbl.  */
 
 static CORE_ADDR
-read_symbol_nvalue (symno)
-     int symno;
+read_symbol_nvalue (int symno)
 {
   struct internal_syment symbol[1];
 
@@ -1688,11 +1630,10 @@ read_symbol_nvalue (symno)
    symno is the symbol pointed to by the linetable.  */
 
 static int
-read_symbol_lineno (symno)
-     int symno;
+read_symbol_lineno (int symno)
 {
   struct objfile *objfile = this_symtab_psymtab->objfile;
-  boolean xcoff64 = xcoff_data (objfile->obfd)->xcoff64;
+  int xcoff64 = bfd_xcoff_is_xcoff64 (objfile->obfd);
 
   struct coff_symfile_info *info =
     (struct coff_symfile_info *)objfile->sym_private;
@@ -1705,7 +1646,7 @@ read_symbol_lineno (symno)
 
   if (symno < 0)
     {
-      complain (&bf_notfound_complaint);
+      bf_notfound_complaint ();
       return 0;
     }
 
@@ -1738,7 +1679,7 @@ read_symbol_lineno (symno)
       symno += symbol->n_numaux + 1;
     }
 
-  complain (&bf_notfound_complaint);
+  bf_notfound_complaint ();
   return 0;
 
 gotit:
@@ -1758,10 +1699,7 @@ gotit:
  * mainline code can read the whole thing for efficiency.
  */
 static void
-find_linenos (abfd, asect, vpinfo)
-     bfd *abfd;
-     sec_ptr asect;
-     PTR vpinfo;
+find_linenos (bfd *abfd, sec_ptr asect, void *vpinfo)
 {
   struct coff_symfile_info *info;
   int size, count;
@@ -1787,8 +1725,7 @@ find_linenos (abfd, asect, vpinfo)
 static void xcoff_psymtab_to_symtab_1 (struct partial_symtab *);
 
 static void
-xcoff_psymtab_to_symtab_1 (pst)
-     struct partial_symtab *pst;
+xcoff_psymtab_to_symtab_1 (struct partial_symtab *pst)
 {
   struct cleanup *old_chain;
   int i;
@@ -1844,8 +1781,7 @@ static void xcoff_psymtab_to_symtab (struct partial_symtab *);
    Be verbose about it if the user wants that.  */
 
 static void
-xcoff_psymtab_to_symtab (pst)
-     struct partial_symtab *pst;
+xcoff_psymtab_to_symtab (struct partial_symtab *pst)
 {
   bfd *sym_bfd;
 
@@ -1888,8 +1824,7 @@ xcoff_psymtab_to_symtab (pst)
 }
 \f
 static void
-xcoff_new_init (objfile)
-     struct objfile *objfile;
+xcoff_new_init (struct objfile *objfile)
 {
   stabsread_new_init ();
   buildsym_new_init ();
@@ -1902,8 +1837,7 @@ xcoff_new_init (objfile)
    uses BFD's determination to vector to us.  */
 
 static void
-xcoff_symfile_init (objfile)
-     struct objfile *objfile;
+xcoff_symfile_init (struct objfile *objfile)
 {
   /* Allocate struct to keep track of the symfile */
   objfile->sym_private = xmmalloc (objfile->md,
@@ -1923,18 +1857,17 @@ xcoff_symfile_init (objfile)
    objfile struct from the global list of known objfiles. */
 
 static void
-xcoff_symfile_finish (objfile)
-     struct objfile *objfile;
+xcoff_symfile_finish (struct objfile *objfile)
 {
   if (objfile->sym_private != NULL)
     {
-      mfree (objfile->md, objfile->sym_private);
+      xmfree (objfile->md, objfile->sym_private);
     }
 
   /* Start with a fresh include table for the next objfile.  */
   if (inclTable)
     {
-      free (inclTable);
+      xfree (inclTable);
       inclTable = NULL;
     }
   inclIndx = inclLength = inclDepth = 0;
@@ -1942,10 +1875,7 @@ xcoff_symfile_finish (objfile)
 
 
 static void
-init_stringtab (abfd, offset, objfile)
-     bfd *abfd;
-     file_ptr offset;
-     struct objfile *objfile;
+init_stringtab (bfd *abfd, file_ptr offset, struct objfile *objfile)
 {
   long length;
   int val;
@@ -1958,7 +1888,7 @@ init_stringtab (abfd, offset, objfile)
     error ("cannot seek to string table in %s: %s",
           bfd_get_filename (abfd), bfd_errmsg (bfd_get_error ()));
 
-  val = bfd_read ((char *) lengthbuf, 1, sizeof lengthbuf, abfd);
+  val = bfd_bread ((char *) lengthbuf, sizeof lengthbuf, abfd);
   length = bfd_h_get_32 (abfd, lengthbuf);
 
   /* If no string table is needed, then the file may end immediately
@@ -1979,8 +1909,7 @@ init_stringtab (abfd, offset, objfile)
   if (length == sizeof lengthbuf)
     return;
 
-  val = bfd_read (strtbl + sizeof lengthbuf, 1, length - sizeof lengthbuf,
-                 abfd);
+  val = bfd_bread (strtbl + sizeof lengthbuf, length - sizeof lengthbuf, abfd);
 
   if (val != length - sizeof lengthbuf)
     error ("cannot read string table from %s: %s",
@@ -2008,13 +1937,9 @@ static struct partial_symtab *xcoff_start_psymtab
    (normal). */
 
 static struct partial_symtab *
-xcoff_start_psymtab (objfile, filename, first_symnum, global_syms,
-                    static_syms)
-     struct objfile *objfile;
-     char *filename;
-     int first_symnum;
-     struct partial_symbol **global_syms;
-     struct partial_symbol **static_syms;
+xcoff_start_psymtab (struct objfile *objfile, char *filename, int first_symnum,
+                    struct partial_symbol **global_syms,
+                    struct partial_symbol **static_syms)
 {
   struct partial_symtab *result =
   start_psymtab_common (objfile, objfile->section_offsets,
@@ -2047,15 +1972,10 @@ static struct partial_symtab *xcoff_end_psymtab
    are the information for includes and dependencies.  */
 
 static struct partial_symtab *
-xcoff_end_psymtab (pst, include_list, num_includes, capping_symbol_number,
-                  dependency_list, number_dependencies, textlow_not_set)
-     struct partial_symtab *pst;
-     char **include_list;
-     int num_includes;
-     int capping_symbol_number;
-     struct partial_symtab **dependency_list;
-     int number_dependencies;
-     int textlow_not_set;
+xcoff_end_psymtab (struct partial_symtab *pst, char **include_list,
+                  int num_includes, int capping_symbol_number,
+                  struct partial_symtab **dependency_list,
+                  int number_dependencies, int textlow_not_set)
 {
   int i;
   struct objfile *objfile = pst->objfile;
@@ -2150,13 +2070,9 @@ static void swap_sym (struct internal_syment *,
    the symbol and its auxents.  */
 
 static void
-swap_sym (symbol, aux, name, raw, symnump, objfile)
-     struct internal_syment *symbol;
-     union internal_auxent *aux;
-     char **name;
-     char **raw;
-     unsigned int *symnump;
-     struct objfile *objfile;
+swap_sym (struct internal_syment *symbol, union internal_auxent *aux,
+         char **name, char **raw, unsigned int *symnump,
+         struct objfile *objfile)
 {
   bfd_coff_swap_sym_in (objfile->obfd, *raw, symbol);
   if (symbol->n_zeroes)
@@ -2201,8 +2117,15 @@ swap_sym (symbol, aux, name, raw, symnump, objfile)
 }
 
 static void
-scan_xcoff_symtab (objfile)
-     struct objfile *objfile;
+function_outside_compilation_unit_complaint (const char *arg1)
+{
+  complaint (&symfile_complaints,
+            "function `%s' appears to be defined outside of all compilation units",
+            arg1);
+}
+
+static void
+scan_xcoff_symtab (struct objfile *objfile)
 {
   CORE_ADDR toc_offset = 0;    /* toc offset value in data section. */
   char *filestring = NULL;
@@ -2259,11 +2182,6 @@ scan_xcoff_symtab (objfile)
   while (ssymnum < nsyms)
     {
       int sclass;
-      /* This is the type we pass to partial-stab.h.  A less kludgy solution
-         would be to break out partial-stab.h into its various parts--shuffle
-         off the DBXREAD_ONLY stuff to dbxread.c, and make separate
-         pstab-norm.h (for most types), pstab-sol.h (for N_SOL), etc.  */
-      int stype;
 
       QUIT;
 
@@ -2342,7 +2260,11 @@ scan_xcoff_symtab (objfile)
                               objfile->static_psymbols.next);
                          }
                      }
-                   if (namestring && namestring[0] == '.')
+                   /* Activate the misc_func_recorded mechanism for
+                      compiler- and linker-generated CSECTs like ".strcmp"
+                      and "@FIX1".  */ 
+                   if (namestring && (namestring[0] == '.'
+                                      || namestring[0] == '@'))
                      {
                        last_csect_name = namestring;
                        last_csect_val = symbol.n_value;
@@ -2362,6 +2284,7 @@ scan_xcoff_symtab (objfile)
                    break;
 
                  case XMC_RW:
+                 case XMC_TD:
                    /* Data variables are recorded in the minimal symbol
                       table, except for section symbols.  */
                    if (*namestring != '.')
@@ -2526,9 +2449,8 @@ scan_xcoff_symtab (objfile)
 
        default:
          {
-           static struct complaint msg =
-           {"Storage class %d not recognized during scan", 0, 0};
-           complain (&msg, sclass);
+           complaint (&symfile_complaints,
+                      "Storage class %d not recognized during scan", sclass);
          }
          /* FALLTHROUGH */
 
@@ -2584,9 +2506,59 @@ scan_xcoff_symtab (objfile)
          break;
 
        case C_BINCL:
-         stype = N_SOL;
-         goto pstab;
+         {
+           /* Mark down an include file in the current psymtab */
+           enum language tmp_language;
+           swap_sym (&symbol, &main_aux[0], &namestring, &sraw_symbol,
+                     &ssymnum, objfile);
+
+           tmp_language = deduce_language_from_filename (namestring);
+
+           /* Only change the psymtab's language if we've learned
+              something useful (eg. tmp_language is not language_unknown).
+              In addition, to match what start_subfile does, never change
+              from C++ to C.  */
+           if (tmp_language != language_unknown
+               && (tmp_language != language_c
+                   || psymtab_language != language_cplus))
+             psymtab_language = tmp_language;
+
+           /* In C++, one may expect the same filename to come round many
+              times, when code is coming alternately from the main file
+              and from inline functions in other files. So I check to see
+              if this is a file we've seen before -- either the main
+              source file, or a previously included file.
+
+              This seems to be a lot of time to be spending on N_SOL, but
+              things like "break c-exp.y:435" need to work (I
+              suppose the psymtab_include_list could be hashed or put
+              in a binary tree, if profiling shows this is a major hog).  */
+           if (pst && STREQ (namestring, pst->filename))
+             continue;
+           {
+             register int i;
+             for (i = 0; i < includes_used; i++)
+               if (STREQ (namestring, psymtab_include_list[i]))
+                 {
+                   i = -1;
+                   break;
+                 }
+             if (i == -1)
+               continue;
+           }
+           psymtab_include_list[includes_used++] = namestring;
+           if (includes_used >= includes_allocated)
+             {
+               char **orig = psymtab_include_list;
 
+               psymtab_include_list = (char **)
+                 alloca ((includes_allocated *= 2) *
+                         sizeof (char *));
+               memcpy (psymtab_include_list, orig,
+                       includes_used * sizeof (char *));
+             }
+           continue;
+         }
        case C_FUN:
          /* The value of the C_FUN is not the address of the function (it
             appears to be the address before linking), but as long as it
@@ -2597,23 +2569,270 @@ scan_xcoff_symtab (objfile)
        case C_ECOML:
        case C_DECL:
        case C_STSYM:
-         stype = N_LSYM;
-       pstab:
-         swap_sym (&symbol, &main_aux[0], &namestring, &sraw_symbol,
-                   &ssymnum, objfile);
-#define CUR_SYMBOL_TYPE stype
-#define CUR_SYMBOL_VALUE symbol.n_value
-
-/* START_PSYMTAB and END_PSYMTAB are never used, because they are only
-   called from DBXREAD_ONLY or N_SO code.  Likewise for the symnum
-   variable.  */
-#define START_PSYMTAB(ofile,fname,low,symoff,global_syms,static_syms) 0
-#define END_PSYMTAB(pst,ilist,ninc,c_off,c_text,dep_list,n_deps,textlow_not_set)\
-  do {} while (0)
-/* We have already set the namestring.  */
-#define SET_NAMESTRING()       /* */
-
-#include "partial-stab.h"
+         {
+           char *p;
+           swap_sym (&symbol, &main_aux[0], &namestring, &sraw_symbol,
+                     &ssymnum, objfile);
+
+           p = (char *) strchr (namestring, ':');
+           if (!p)
+             continue;                 /* Not a debugging symbol.   */
+
+           /* Main processing section for debugging symbols which
+              the initial read through the symbol tables needs to worry
+              about.  If we reach this point, the symbol which we are
+              considering is definitely one we are interested in.
+              p must also contain the (valid) index into the namestring
+              which indicates the debugging type symbol.  */
+
+           switch (p[1])
+             {
+             case 'S':
+               symbol.n_value += ANOFFSET (objfile->section_offsets, SECT_OFF_DATA (objfile));
+#ifdef STATIC_TRANSFORM_NAME
+               namestring = STATIC_TRANSFORM_NAME (namestring);
+#endif
+               add_psymbol_to_list (namestring, p - namestring,
+                                    VAR_NAMESPACE, LOC_STATIC,
+                                    &objfile->static_psymbols,
+                                    0, symbol.n_value,
+                                    psymtab_language, objfile);
+               continue;
+
+             case 'G':
+               symbol.n_value += ANOFFSET (objfile->section_offsets, SECT_OFF_DATA (objfile));
+               /* The addresses in these entries are reported to be
+                  wrong.  See the code that reads 'G's for symtabs. */
+               add_psymbol_to_list (namestring, p - namestring,
+                                    VAR_NAMESPACE, LOC_STATIC,
+                                    &objfile->global_psymbols,
+                                    0, symbol.n_value,
+                                    psymtab_language, objfile);
+               continue;
+
+             case 'T':
+               /* When a 'T' entry is defining an anonymous enum, it
+                  may have a name which is the empty string, or a
+                  single space.  Since they're not really defining a
+                  symbol, those shouldn't go in the partial symbol
+                  table.  We do pick up the elements of such enums at
+                  'check_enum:', below.  */
+               if (p >= namestring + 2
+                   || (p == namestring + 1
+                       && namestring[0] != ' '))
+                 {
+                   add_psymbol_to_list (namestring, p - namestring,
+                                        STRUCT_NAMESPACE, LOC_TYPEDEF,
+                                        &objfile->static_psymbols,
+                                        symbol.n_value, 0,
+                                        psymtab_language, objfile);
+                   if (p[2] == 't')
+                     {
+                       /* Also a typedef with the same name.  */
+                       add_psymbol_to_list (namestring, p - namestring,
+                                            VAR_NAMESPACE, LOC_TYPEDEF,
+                                            &objfile->static_psymbols,
+                                            symbol.n_value, 0,
+                                            psymtab_language, objfile);
+                       p += 1;
+                     }
+#if 0 /* OBSOLETE CFront */
+// OBSOLETE                /* The semantics of C++ state that "struct foo { ... }"
+// OBSOLETE                   also defines a typedef for "foo".  Unfortuantely, cfront
+// OBSOLETE                   never makes the typedef when translating from C++ to C.
+// OBSOLETE                   We make the typedef here so that "ptype foo" works as
+// OBSOLETE                   expected for cfront translated code.  */
+// OBSOLETE                else if (psymtab_language == language_cplus)
+// OBSOLETE                  {
+// OBSOLETE                    /* Also a typedef with the same name.  */
+// OBSOLETE                    add_psymbol_to_list (namestring, p - namestring,
+// OBSOLETE                                         VAR_NAMESPACE, LOC_TYPEDEF,
+// OBSOLETE                                         &objfile->static_psymbols,
+// OBSOLETE                                         symbol.n_value, 0,
+// OBSOLETE                                         psymtab_language, objfile);
+// OBSOLETE                  }
+#endif /* OBSOLETE CFront */
+                 }
+               goto check_enum;
+
+             case 't':
+               if (p != namestring)    /* a name is there, not just :T... */
+                 {
+                   add_psymbol_to_list (namestring, p - namestring,
+                                        VAR_NAMESPACE, LOC_TYPEDEF,
+                                        &objfile->static_psymbols,
+                                        symbol.n_value, 0,
+                                        psymtab_language, objfile);
+                 }
+             check_enum:
+               /* If this is an enumerated type, we need to
+                  add all the enum constants to the partial symbol
+                  table.  This does not cover enums without names, e.g.
+                  "enum {a, b} c;" in C, but fortunately those are
+                  rare.  There is no way for GDB to find those from the
+                  enum type without spending too much time on it.  Thus
+                  to solve this problem, the compiler needs to put out the
+                  enum in a nameless type.  GCC2 does this.  */
+
+               /* We are looking for something of the form
+                  <name> ":" ("t" | "T") [<number> "="] "e"
+                  {<constant> ":" <value> ","} ";".  */
+
+               /* Skip over the colon and the 't' or 'T'.  */
+               p += 2;
+               /* This type may be given a number.  Also, numbers can come
+                  in pairs like (0,26).  Skip over it.  */
+               while ((*p >= '0' && *p <= '9')
+                      || *p == '(' || *p == ',' || *p == ')'
+                      || *p == '=')
+                 p++;
+
+               if (*p++ == 'e')
+                 {
+                   /* The aix4 compiler emits extra crud before the members.  */
+                   if (*p == '-')
+                     {
+                       /* Skip over the type (?).  */
+                       while (*p != ':')
+                         p++;
+
+                       /* Skip over the colon.  */
+                       p++;
+                     }
+
+                   /* We have found an enumerated type.  */
+                   /* According to comments in read_enum_type
+                      a comma could end it instead of a semicolon.
+                      I don't know where that happens.
+                      Accept either.  */
+                   while (*p && *p != ';' && *p != ',')
+                     {
+                       char *q;
+
+                       /* Check for and handle cretinous dbx symbol name
+                          continuation!  */
+                       if (*p == '\\' || (*p == '?' && p[1] == '\0'))
+                         p = next_symbol_text (objfile);
+
+                       /* Point to the character after the name
+                          of the enum constant.  */
+                       for (q = p; *q && *q != ':'; q++)
+                         ;
+                       /* Note that the value doesn't matter for
+                          enum constants in psymtabs, just in symtabs.  */
+                       add_psymbol_to_list (p, q - p,
+                                            VAR_NAMESPACE, LOC_CONST,
+                                            &objfile->static_psymbols, 0,
+                                            0, psymtab_language, objfile);
+                       /* Point past the name.  */
+                       p = q;
+                       /* Skip over the value.  */
+                       while (*p && *p != ',')
+                         p++;
+                       /* Advance past the comma.  */
+                       if (*p)
+                         p++;
+                     }
+                 }
+               continue;
+
+             case 'c':
+               /* Constant, e.g. from "const" in Pascal.  */
+               add_psymbol_to_list (namestring, p - namestring,
+                                    VAR_NAMESPACE, LOC_CONST,
+                                    &objfile->static_psymbols, symbol.n_value,
+                                    0, psymtab_language, objfile);
+               continue;
+
+             case 'f':
+               if (! pst)
+                 {
+                   int name_len = p - namestring;
+                   char *name = xmalloc (name_len + 1);
+                   memcpy (name, namestring, name_len);
+                   name[name_len] = '\0';
+                   function_outside_compilation_unit_complaint (name);
+                   xfree (name);
+                 }
+               symbol.n_value += ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+               add_psymbol_to_list (namestring, p - namestring,
+                                    VAR_NAMESPACE, LOC_BLOCK,
+                                    &objfile->static_psymbols,
+                                    0, symbol.n_value,
+                                    psymtab_language, objfile);
+               continue;
+
+               /* Global functions were ignored here, but now they
+                  are put into the global psymtab like one would expect.
+                  They're also in the minimal symbol table.  */
+             case 'F':
+               if (! pst)
+                 {
+                   int name_len = p - namestring;
+                   char *name = xmalloc (name_len + 1);
+                   memcpy (name, namestring, name_len);
+                   name[name_len] = '\0';
+                   function_outside_compilation_unit_complaint (name);
+                   xfree (name);
+                 }
+               symbol.n_value += ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+               add_psymbol_to_list (namestring, p - namestring,
+                                    VAR_NAMESPACE, LOC_BLOCK,
+                                    &objfile->global_psymbols,
+                                    0, symbol.n_value,
+                                    psymtab_language, objfile);
+               continue;
+
+               /* Two things show up here (hopefully); static symbols of
+                  local scope (static used inside braces) or extensions
+                  of structure symbols.  We can ignore both.  */
+             case 'V':
+             case '(':
+             case '0':
+             case '1':
+             case '2':
+             case '3':
+             case '4':
+             case '5':
+             case '6':
+             case '7':
+             case '8':
+             case '9':
+             case '-':
+             case '#':         /* for symbol identification (used in live ranges) */
+#if 0 /* OBSOLETE CFront */
+// OBSOLETE            /* added to support cfront stabs strings */
+// OBSOLETE          case 'Z':         /* for definition continuations */
+// OBSOLETE          case 'P':         /* for prototypes */
+#endif /* OBSOLETE CFront */
+               continue;
+
+             case ':':
+               /* It is a C++ nested symbol.  We don't need to record it
+                  (I don't think); if we try to look up foo::bar::baz,
+                  then symbols for the symtab containing foo should get
+                  read in, I think.  */
+               /* Someone says sun cc puts out symbols like
+                  /foo/baz/maclib::/usr/local/bin/maclib,
+                  which would get here with a symbol type of ':'.  */
+               continue;
+
+             default:
+               /* Unexpected symbol descriptor.  The second and subsequent stabs
+                  of a continued stab can show up here.  The question is
+                  whether they ever can mimic a normal stab--it would be
+                  nice if not, since we certainly don't want to spend the
+                  time searching to the end of every string looking for
+                  a backslash.  */
+
+               complaint (&symfile_complaints,
+                          "unknown symbol descriptor `%c'", p[1]);
+
+               /* Ignore it; perhaps it is an extension that we don't
+                  know about.  */
+               continue;
+             }
+         }
        }
     }
 
@@ -2634,8 +2853,7 @@ scan_xcoff_symtab (objfile)
 /* Return the toc offset value for a given objfile.  */
 
 CORE_ADDR
-get_toc_offset (objfile)
-     struct objfile *objfile;
+get_toc_offset (struct objfile *objfile)
 {
   if (objfile)
     return ((struct coff_symfile_info *) objfile->sym_private)->toc_offset;
@@ -2653,9 +2871,7 @@ get_toc_offset (objfile)
    table (as opposed to a shared lib or dynamically loaded file).  */
 
 static void
-xcoff_initial_scan (objfile, mainline)
-     struct objfile *objfile;
-     int mainline;             /* FIXME comments above */
+xcoff_initial_scan (struct objfile *objfile, int mainline)
 {
   bfd *abfd;
   int val;
@@ -2725,15 +2941,15 @@ xcoff_initial_scan (objfile, mainline)
   ((struct coff_symfile_info *) objfile->sym_private)->symtbl_num_syms =
     num_symbols;
 
-  val = bfd_read (((struct coff_symfile_info *) objfile->sym_private)->symtbl,
-                 size, 1, abfd);
+  val = bfd_bread (((struct coff_symfile_info *) objfile->sym_private)->symtbl,
+                  size, abfd);
   if (val != size)
     perror_with_name ("reading symbol table");
 
   /* If we are reinitializing, or if we have never loaded syms yet, init */
   if (mainline
-      || objfile->global_psymbols.size == 0
-      || objfile->static_psymbols.size == 0)
+      || (objfile->global_psymbols.size == 0
+         && objfile->static_psymbols.size == 0))
     /* I'm not sure how how good num_symbols is; the rule of thumb in
        init_psymbol_list was developed for a.out.  On the one hand,
        num_symbols includes auxents.  On the other hand, it doesn't
@@ -2760,9 +2976,7 @@ xcoff_initial_scan (objfile, mainline)
 }
 \f
 static void
-xcoff_symfile_offsets (objfile, addrs)
-     struct objfile *objfile;
-     struct section_addr_info *addrs;
+xcoff_symfile_offsets (struct objfile *objfile, struct section_addr_info *addrs)
 {
   asection *sect = NULL;
   int i;
@@ -2799,7 +3013,7 @@ xcoff_symfile_offsets (objfile, addrs)
         sensibly), so just ignore the addr parameter and use 0.
         rs6000-nat.c will set the correct section offsets via
         objfile_relocate.  */
-       ANOFFSET (objfile->section_offsets, i) = 0;
+       (objfile->section_offsets)->offsets[i] = 0;
     }
 }
 
@@ -2828,7 +3042,7 @@ static struct sym_fns xcoff_sym_fns =
 };
 
 void
-_initialize_xcoffread ()
+_initialize_xcoffread (void)
 {
   add_symtab_fns (&xcoff_sym_fns);
 
This page took 0.038808 seconds and 4 git commands to generate.