From 071ea11e85eb9d529cc5eb3d35f6247466a21b99 Mon Sep 17 00:00:00 2001 From: Stan Shebs Date: Fri, 16 Apr 1999 01:34:07 +0000 Subject: Initial creation of sourceware repository --- gdb/hpread.c | 2050 ---------------------------------------------------------- 1 file changed, 2050 deletions(-) delete mode 100644 gdb/hpread.c (limited to 'gdb/hpread.c') diff --git a/gdb/hpread.c b/gdb/hpread.c deleted file mode 100644 index 0b464ec..0000000 --- a/gdb/hpread.c +++ /dev/null @@ -1,2050 +0,0 @@ -/* Read hp debug symbols and convert to internal format, for GDB. - Copyright 1993, 1996 Free Software Foundation, Inc. - - This file is part of GDB. - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - - Written by the Center for Software Science at the University of Utah - and by Cygnus Support. */ - -#include "defs.h" -#include "bfd.h" -#include "gdb_string.h" -#include "hp-symtab.h" -#include "syms.h" -#include "symtab.h" -#include "symfile.h" -#include "objfiles.h" -#include "buildsym.h" -#include "complaints.h" -#include "gdb-stabs.h" -#include "gdbtypes.h" -#include "demangle.h" - -/* Private information attached to an objfile which we use to find - and internalize the HP C debug symbols within that objfile. */ - -struct hpread_symfile_info -{ - /* The contents of each of the debug sections (there are 4 of them). */ - char *gntt; - char *lntt; - char *slt; - char *vt; - - /* We keep the size of the $VT$ section for range checking. */ - unsigned int vt_size; - - /* Some routines still need to know the number of symbols in the - main debug sections ($LNTT$ and $GNTT$). */ - unsigned int lntt_symcount; - unsigned int gntt_symcount; - - /* To keep track of all the types we've processed. */ - struct type **type_vector; - int type_vector_length; - - /* Keeps track of the beginning of a range of source lines. */ - sltpointer sl_index; - - /* Some state variables we'll need. */ - int within_function; - - /* Keep track of the current function's address. We may need to look - up something based on this address. */ - unsigned int current_function_value; -}; - -/* Accessor macros to get at the fields. */ -#define HPUX_SYMFILE_INFO(o) \ - ((struct hpread_symfile_info *)((o)->sym_private)) -#define GNTT(o) (HPUX_SYMFILE_INFO(o)->gntt) -#define LNTT(o) (HPUX_SYMFILE_INFO(o)->lntt) -#define SLT(o) (HPUX_SYMFILE_INFO(o)->slt) -#define VT(o) (HPUX_SYMFILE_INFO(o)->vt) -#define VT_SIZE(o) (HPUX_SYMFILE_INFO(o)->vt_size) -#define LNTT_SYMCOUNT(o) (HPUX_SYMFILE_INFO(o)->lntt_symcount) -#define GNTT_SYMCOUNT(o) (HPUX_SYMFILE_INFO(o)->gntt_symcount) -#define TYPE_VECTOR(o) (HPUX_SYMFILE_INFO(o)->type_vector) -#define TYPE_VECTOR_LENGTH(o) (HPUX_SYMFILE_INFO(o)->type_vector_length) -#define SL_INDEX(o) (HPUX_SYMFILE_INFO(o)->sl_index) -#define WITHIN_FUNCTION(o) (HPUX_SYMFILE_INFO(o)->within_function) -#define CURRENT_FUNCTION_VALUE(o) (HPUX_SYMFILE_INFO(o)->current_function_value) - -/* Given the native debug symbol SYM, set NAMEP to the name associated - with the debug symbol. Note we may be called with a debug symbol which - has no associated name, in that case we return an empty string. - - Also note we "know" that the name for any symbol is always in the - same place. Hence we don't have to conditionalize on the symbol type. */ -#define SET_NAMESTRING(SYM, NAMEP, OBJFILE) \ - if (! hpread_has_name ((SYM)->dblock.kind)) \ - *NAMEP = ""; \ - else if (((unsigned)(SYM)->dsfile.name) >= VT_SIZE (OBJFILE)) \ - { \ - complain (&string_table_offset_complaint, (char *) symnum); \ - *NAMEP = ""; \ - } \ - else \ - *NAMEP = (SYM)->dsfile.name + VT (OBJFILE) - -/* We put a pointer to this structure in the read_symtab_private field - of the psymtab. */ - -struct symloc -{ - /* The offset within the file symbol table of first local symbol for - this file. */ - - int ldsymoff; - - /* Length (in bytes) of the section of the symbol table devoted to - this file's symbols (actually, the section bracketed may contain - more than just this file's symbols). If ldsymlen is 0, the only - reason for this thing's existence is the dependency list. - Nothing else will happen when it is read in. */ - - int ldsymlen; -}; - -#define LDSYMOFF(p) (((struct symloc *)((p)->read_symtab_private))->ldsymoff) -#define LDSYMLEN(p) (((struct symloc *)((p)->read_symtab_private))->ldsymlen) -#define SYMLOC(p) ((struct symloc *)((p)->read_symtab_private)) - -/* FIXME: Shouldn't this stuff be in a .h file somewhere? */ -/* Nonzero means give verbose info on gdb action. */ -extern int info_verbose; - -/* Complaints about the symbols we have encountered. */ -extern struct complaint string_table_offset_complaint; -extern struct complaint lbrac_unmatched_complaint; -extern struct complaint lbrac_mismatch_complaint; - - -void hpread_symfile_init PARAMS ((struct objfile *)); - -static struct type * -hpread_read_array_type PARAMS ((dnttpointer, union dnttentry *, struct objfile *)); - -static struct type *hpread_alloc_type - PARAMS ((dnttpointer, struct objfile *)); - -static struct type **hpread_lookup_type - PARAMS ((dnttpointer, struct objfile *)); - -static struct type *hpread_read_enum_type - PARAMS ((dnttpointer, union dnttentry *, struct objfile *)); - -static struct type *hpread_read_set_type - PARAMS ((dnttpointer, union dnttentry *, struct objfile *)); - -static struct type *hpread_read_subrange_type - PARAMS ((dnttpointer, union dnttentry *, struct objfile *)); - -static struct type *hpread_read_struct_type - PARAMS ((dnttpointer, union dnttentry *, struct objfile *)); - -void hpread_build_psymtabs - PARAMS ((struct objfile *, struct section_offsets *, int)); - -void hpread_symfile_finish PARAMS ((struct objfile *)); - -static struct partial_symtab *hpread_start_psymtab - PARAMS ((struct objfile *, struct section_offsets *, char *, CORE_ADDR, int, - struct partial_symbol **, struct partial_symbol **)); - -static struct partial_symtab *hpread_end_psymtab - PARAMS ((struct partial_symtab *, char **, int, int, CORE_ADDR, - struct partial_symtab **, int)); - -static struct symtab *hpread_expand_symtab - PARAMS ((struct objfile *, int, int, CORE_ADDR, int, - struct section_offsets *, char *)); - -static void hpread_process_one_debug_symbol - PARAMS ((union dnttentry *, char *, struct section_offsets *, - struct objfile *, CORE_ADDR, int, char *, int)); - -static sltpointer hpread_record_lines - PARAMS ((struct subfile *, sltpointer, sltpointer, - struct objfile *, CORE_ADDR)); - -static struct type *hpread_read_function_type - PARAMS ((dnttpointer, union dnttentry *, struct objfile *)); - -static struct type * hpread_type_lookup - PARAMS ((dnttpointer, struct objfile *)); - -static unsigned long hpread_get_depth - PARAMS ((sltpointer, struct objfile *)); - -static unsigned long hpread_get_line - PARAMS ((sltpointer, struct objfile *)); - -static CORE_ADDR hpread_get_location - PARAMS ((sltpointer, struct objfile *)); - -static int hpread_type_translate PARAMS ((dnttpointer)); -static unsigned long hpread_get_textlow PARAMS ((int, int, struct objfile *)); -static union dnttentry *hpread_get_gntt PARAMS ((int, struct objfile *)); -static union dnttentry *hpread_get_lntt PARAMS ((int, struct objfile *)); -static union sltentry *hpread_get_slt PARAMS ((int, struct objfile *)); -static void hpread_psymtab_to_symtab PARAMS ((struct partial_symtab *)); -static void hpread_psymtab_to_symtab_1 PARAMS ((struct partial_symtab *)); -static int hpread_has_name PARAMS ((enum dntt_entry_type)); - - -/* Initialization for reading native HP C debug symbols from OBJFILE. - - It's only purpose in life is to set up the symbol reader's private - per-objfile data structures, and read in the raw contents of the debug - sections (attaching pointers to the debug info into the private data - structures). - - Since BFD doesn't know how to read debug symbols in a format-independent - way (and may never do so...), we have to do it ourselves. Note we may - be called on a file without native HP C debugging symbols. - FIXME, there should be a cleaner peephole into the BFD environment here. */ - -void -hpread_symfile_init (objfile) - struct objfile *objfile; -{ - asection *vt_section, *slt_section, *lntt_section, *gntt_section; - - /* Allocate struct to keep track of the symfile */ - objfile->sym_private = (PTR) - xmmalloc (objfile->md, sizeof (struct hpread_symfile_info)); - memset (objfile->sym_private, 0, sizeof (struct hpread_symfile_info)); - - /* We haven't read in any types yet. */ - TYPE_VECTOR (objfile) = 0; - - /* Read in data from the $GNTT$ subspace. */ - gntt_section = bfd_get_section_by_name (objfile->obfd, "$GNTT$"); - if (!gntt_section) - return; - - GNTT (objfile) - = obstack_alloc (&objfile->symbol_obstack, - bfd_section_size (objfile->obfd, gntt_section)); - - bfd_get_section_contents (objfile->obfd, gntt_section, GNTT (objfile), - 0, bfd_section_size (objfile->obfd, gntt_section)); - - GNTT_SYMCOUNT (objfile) - = bfd_section_size (objfile->obfd, gntt_section) - / sizeof (struct dntt_type_block); - - /* Read in data from the $LNTT$ subspace. Also keep track of the number - of LNTT symbols. */ - lntt_section = bfd_get_section_by_name (objfile->obfd, "$LNTT$"); - if (!lntt_section) - return; - - LNTT (objfile) - = obstack_alloc (&objfile->symbol_obstack, - bfd_section_size (objfile->obfd, lntt_section)); - - bfd_get_section_contents (objfile->obfd, lntt_section, LNTT (objfile), - 0, bfd_section_size (objfile->obfd, lntt_section)); - - LNTT_SYMCOUNT (objfile) - = bfd_section_size (objfile->obfd, lntt_section) - / sizeof (struct dntt_type_block); - - /* Read in data from the $SLT$ subspace. $SLT$ contains information - on source line numbers. */ - slt_section = bfd_get_section_by_name (objfile->obfd, "$SLT$"); - if (!slt_section) - return; - - SLT (objfile) = - obstack_alloc (&objfile->symbol_obstack, - bfd_section_size (objfile->obfd, slt_section)); - - bfd_get_section_contents (objfile->obfd, slt_section, SLT (objfile), - 0, bfd_section_size (objfile->obfd, slt_section)); - - /* Read in data from the $VT$ subspace. $VT$ contains things like - names and constants. Keep track of the number of symbols in the VT. */ - vt_section = bfd_get_section_by_name (objfile->obfd, "$VT$"); - if (!vt_section) - return; - - VT_SIZE (objfile) = bfd_section_size (objfile->obfd, vt_section); - - VT (objfile) = - (char *) obstack_alloc (&objfile->symbol_obstack, - VT_SIZE (objfile)); - - bfd_get_section_contents (objfile->obfd, vt_section, VT (objfile), - 0, VT_SIZE (objfile)); -} - -/* Scan and build partial symbols for a symbol file. - - The minimal symbol table (either SOM or HP a.out) has already been - read in; all we need to do is setup partial symbols based on the - native debugging information. - - We assume hpread_symfile_init has been called to initialize the - symbol reader's private data structures. - - SECTION_OFFSETS contains offsets relative to which the symbols in the - various sections are (depending where the sections were actually loaded). - MAINLINE is true if we are reading the main symbol - table (as opposed to a shared lib or dynamically loaded file). */ - -void -hpread_build_psymtabs (objfile, section_offsets, mainline) - struct objfile *objfile; - struct section_offsets *section_offsets; - int mainline; -{ - char *namestring; - int past_first_source_file = 0; - struct cleanup *old_chain; - - int hp_symnum, symcount, i; - - union dnttentry *dn_bufp; - unsigned long valu; - char *p; - int texthigh = 0; - int have_name = 0; - - /* Current partial symtab */ - struct partial_symtab *pst; - - /* List of current psymtab's include files */ - char **psymtab_include_list; - int includes_allocated; - int includes_used; - - /* Index within current psymtab dependency list */ - struct partial_symtab **dependency_list; - int dependencies_used, dependencies_allocated; - - /* Just in case the stabs reader left turds lying around. */ - free_pending_blocks (); - make_cleanup (really_free_pendings, 0); - - pst = (struct partial_symtab *) 0; - - /* We shouldn't use alloca, instead use malloc/free. Doing so avoids - a number of problems with cross compilation and creating useless holes - in the stack when we have to allocate new entries. FIXME. */ - - includes_allocated = 30; - includes_used = 0; - psymtab_include_list = (char **) alloca (includes_allocated * - sizeof (char *)); - - dependencies_allocated = 30; - dependencies_used = 0; - dependency_list = - (struct partial_symtab **) alloca (dependencies_allocated * - sizeof (struct partial_symtab *)); - - old_chain = make_cleanup (free_objfile, objfile); - - last_source_file = 0; - - /* Make two passes, one ofr the GNTT symbols, the other for the - LNTT symbols. */ - for (i = 0; i < 1; i++) - { - int within_function = 0; - - if (i) - symcount = GNTT_SYMCOUNT (objfile); - else - symcount = LNTT_SYMCOUNT (objfile); - - for (hp_symnum = 0; hp_symnum < symcount; hp_symnum++) - { - QUIT; - if (i) - dn_bufp = hpread_get_gntt (hp_symnum, objfile); - else - dn_bufp = hpread_get_lntt (hp_symnum, objfile); - - if (dn_bufp->dblock.extension) - continue; - - /* Only handle things which are necessary for minimal symbols. - everything else is ignored. */ - switch (dn_bufp->dblock.kind) - { - case DNTT_TYPE_SRCFILE: - { - /* A source file of some kind. Note this may simply - be an included file. */ - SET_NAMESTRING (dn_bufp, &namestring, objfile); - - /* Check if this is the source file we are already working - with. */ - if (pst && !strcmp (namestring, pst->filename)) - continue; - - /* Check if this is an include file, if so check if we have - already seen it. Add it to the include list */ - p = strrchr (namestring, '.'); - if (!strcmp (p, ".h")) - { - int j, found; - - found = 0; - for (j = 0; j < includes_used; j++) - if (!strcmp (namestring, psymtab_include_list[j])) - { - found = 1; - break; - } - if (found) - continue; - - /* Add it to the list of includes seen so far and - allocate more include space if necessary. */ - 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 ((PTR) psymtab_include_list, (PTR) orig, - includes_used * sizeof (char *)); - } - continue; - } - - - if (pst) - { - if (!have_name) - { - pst->filename = (char *) - obstack_alloc (&pst->objfile->psymbol_obstack, - strlen (namestring) + 1); - strcpy (pst->filename, namestring); - have_name = 1; - continue; - } - continue; - } - - /* This is a bonafide new source file. - End the current partial symtab and start a new one. */ - - if (pst && past_first_source_file) - { - hpread_end_psymtab (pst, psymtab_include_list, - includes_used, - (hp_symnum - * sizeof (struct dntt_type_block)), - texthigh, - dependency_list, dependencies_used); - pst = (struct partial_symtab *) 0; - includes_used = 0; - dependencies_used = 0; - } - else - past_first_source_file = 1; - - valu = hpread_get_textlow (i, hp_symnum, objfile); - valu += ANOFFSET (section_offsets, SECT_OFF_TEXT); - pst = hpread_start_psymtab (objfile, section_offsets, - namestring, valu, - (hp_symnum - * sizeof (struct dntt_type_block)), - objfile->global_psymbols.next, - objfile->static_psymbols.next); - texthigh = valu; - have_name = 1; - continue; - } - - case DNTT_TYPE_MODULE: - /* A source file. It's still unclear to me what the - real difference between a DNTT_TYPE_SRCFILE and DNTT_TYPE_MODULE - is supposed to be. */ - SET_NAMESTRING (dn_bufp, &namestring, objfile); - valu = hpread_get_textlow (i, hp_symnum, objfile); - valu += ANOFFSET (section_offsets, SECT_OFF_TEXT); - if (!pst) - { - pst = hpread_start_psymtab (objfile, section_offsets, - namestring, valu, - (hp_symnum - * sizeof (struct dntt_type_block)), - objfile->global_psymbols.next, - objfile->static_psymbols.next); - texthigh = valu; - have_name = 0; - } - continue; - case DNTT_TYPE_FUNCTION: - case DNTT_TYPE_ENTRY: - /* The beginning of a function. DNTT_TYPE_ENTRY may also denote - a secondary entry point. */ - valu = dn_bufp->dfunc.hiaddr + ANOFFSET (section_offsets, - SECT_OFF_TEXT); - if (valu > texthigh) - texthigh = valu; - valu = dn_bufp->dfunc.lowaddr + - ANOFFSET (section_offsets, SECT_OFF_TEXT); - SET_NAMESTRING (dn_bufp, &namestring, objfile); - add_psymbol_to_list (namestring, strlen (namestring), - VAR_NAMESPACE, LOC_BLOCK, - &objfile->static_psymbols, valu, - 0, language_unknown, objfile); - within_function = 1; - continue; - case DNTT_TYPE_BEGIN: - case DNTT_TYPE_END: - /* Scope block begin/end. We only care about function - and file blocks right now. */ - if (dn_bufp->dend.endkind == DNTT_TYPE_MODULE) - { - hpread_end_psymtab (pst, psymtab_include_list, includes_used, - (hp_symnum - * sizeof (struct dntt_type_block)), - texthigh, - dependency_list, dependencies_used); - pst = (struct partial_symtab *) 0; - includes_used = 0; - dependencies_used = 0; - have_name = 0; - } - if (dn_bufp->dend.endkind == DNTT_TYPE_FUNCTION) - within_function = 0; - continue; - case DNTT_TYPE_SVAR: - case DNTT_TYPE_DVAR: - case DNTT_TYPE_TYPEDEF: - case DNTT_TYPE_TAGDEF: - { - /* Variables, typedefs an the like. */ - enum address_class storage; - namespace_enum namespace; - - /* Don't add locals to the partial symbol table. */ - if (within_function - && (dn_bufp->dblock.kind == DNTT_TYPE_SVAR - || dn_bufp->dblock.kind == DNTT_TYPE_DVAR)) - continue; - - /* TAGDEFs go into the structure namespace. */ - if (dn_bufp->dblock.kind == DNTT_TYPE_TAGDEF) - namespace = STRUCT_NAMESPACE; - else - namespace = VAR_NAMESPACE; - - /* What kind of "storage" does this use? */ - if (dn_bufp->dblock.kind == DNTT_TYPE_SVAR) - storage = LOC_STATIC; - else if (dn_bufp->dblock.kind == DNTT_TYPE_DVAR - && dn_bufp->ddvar.regvar) - storage = LOC_REGISTER; - else if (dn_bufp->dblock.kind == DNTT_TYPE_DVAR) - storage = LOC_LOCAL; - else - storage = LOC_UNDEF; - - SET_NAMESTRING (dn_bufp, &namestring, objfile); - if (!pst) - { - pst = hpread_start_psymtab (objfile, section_offsets, - "globals", 0, - (hp_symnum - * sizeof (struct dntt_type_block)), - objfile->global_psymbols.next, - objfile->static_psymbols.next); - } - if (dn_bufp->dsvar.global) - { - add_psymbol_to_list (namestring, strlen (namestring), - namespace, storage, - &objfile->global_psymbols, - dn_bufp->dsvar.location, - 0, language_unknown, objfile); - } - else - { - add_psymbol_to_list (namestring, strlen (namestring), - namespace, storage, - &objfile->static_psymbols, - dn_bufp->dsvar.location, - 0, language_unknown, objfile); - } - continue; - } - case DNTT_TYPE_MEMENUM: - case DNTT_TYPE_CONST: - /* Constants and members of enumerated types. */ - SET_NAMESTRING (dn_bufp, &namestring, objfile); - if (!pst) - { - pst = hpread_start_psymtab (objfile, section_offsets, - "globals", 0, - (hp_symnum - * sizeof (struct dntt_type_block)), - objfile->global_psymbols.next, - objfile->static_psymbols.next); - } - add_psymbol_to_list (namestring, strlen (namestring), - VAR_NAMESPACE, LOC_CONST, - &objfile->static_psymbols, 0, - 0, language_unknown, objfile); - continue; - default: - continue; - } - } - } - - /* End any pending partial symbol table. */ - if (pst) - { - hpread_end_psymtab (pst, psymtab_include_list, includes_used, - hp_symnum * sizeof (struct dntt_type_block), - 0, dependency_list, dependencies_used); - } - - discard_cleanups (old_chain); -} - -/* Perform any local cleanups required when we are done with a particular - objfile. I.E, we are in the process of discarding all symbol information - for an objfile, freeing up all memory held for it, and unlinking the - objfile struct from the global list of known objfiles. */ - -void -hpread_symfile_finish (objfile) - struct objfile *objfile; -{ - if (objfile->sym_private != NULL) - { - mfree (objfile->md, objfile->sym_private); - } -} - - -/* The remaining functions are all for internal use only. */ - -/* Various small functions to get entries in the debug symbol sections. */ - -static union dnttentry * -hpread_get_lntt (index, objfile) - int index; - struct objfile *objfile; -{ - return (union dnttentry *) - &(LNTT (objfile)[(index * sizeof (struct dntt_type_block))]); -} - -static union dnttentry * -hpread_get_gntt (index, objfile) - int index; - struct objfile *objfile; -{ - return (union dnttentry *) - &(GNTT (objfile)[(index * sizeof (struct dntt_type_block))]); -} - -static union sltentry * -hpread_get_slt (index, objfile) - int index; - struct objfile *objfile; -{ - return (union sltentry *)&(SLT (objfile)[index * sizeof (union sltentry)]); -} - -/* Get the low address associated with some symbol (typically the start - of a particular source file or module). Since that information is not - stored as part of the DNTT_TYPE_MODULE or DNTT_TYPE_SRCFILE symbol we must infer it from - the existance of DNTT_TYPE_FUNCTION symbols. */ - -static unsigned long -hpread_get_textlow (global, index, objfile) - int global; - int index; - struct objfile *objfile; -{ - union dnttentry *dn_bufp; - struct minimal_symbol *msymbol; - - /* Look for a DNTT_TYPE_FUNCTION symbol. */ - do - { - if (global) - dn_bufp = hpread_get_gntt (index++, objfile); - else - dn_bufp = hpread_get_lntt (index++, objfile); - } while (dn_bufp->dblock.kind != DNTT_TYPE_FUNCTION - && dn_bufp->dblock.kind != DNTT_TYPE_END); - - /* Avoid going past a DNTT_TYPE_END when looking for a DNTT_TYPE_FUNCTION. This - might happen when a sourcefile has no functions. */ - if (dn_bufp->dblock.kind == DNTT_TYPE_END) - return 0; - - /* The minimal symbols are typically more accurate for some reason. */ - msymbol = lookup_minimal_symbol (dn_bufp->dfunc.name + VT (objfile), NULL, - objfile); - if (msymbol) - return SYMBOL_VALUE_ADDRESS (msymbol); - else - return dn_bufp->dfunc.lowaddr; -} - -/* Get the nesting depth for the source line identified by INDEX. */ - -static unsigned long -hpread_get_depth (index, objfile) - sltpointer index; - struct objfile *objfile; -{ - union sltentry *sl_bufp; - - sl_bufp = hpread_get_slt (index, objfile); - return sl_bufp->sspec.backptr.dnttp.index; -} - -/* Get the source line number the the line identified by INDEX. */ - -static unsigned long -hpread_get_line (index, objfile) - sltpointer index; - struct objfile *objfile; -{ - union sltentry *sl_bufp; - - sl_bufp = hpread_get_slt (index, objfile); - return sl_bufp->snorm.line; -} - -static CORE_ADDR -hpread_get_location (index, objfile) - sltpointer index; - struct objfile *objfile; -{ - union sltentry *sl_bufp; - int i; - - /* code location of special sltentrys is determined from context */ - sl_bufp = hpread_get_slt (index, objfile); - - if (sl_bufp->snorm.sltdesc == SLT_END) - { - /* find previous normal sltentry and get address */ - for (i = 0; ((sl_bufp->snorm.sltdesc != SLT_NORMAL) && - (sl_bufp->snorm.sltdesc != SLT_EXIT)); i++) - sl_bufp = hpread_get_slt (index - i, objfile); - return sl_bufp->snorm.address; - } - - /* find next normal sltentry and get address */ - for (i = 0; ((sl_bufp->snorm.sltdesc != SLT_NORMAL) && - (sl_bufp->snorm.sltdesc != SLT_EXIT)); i++) - sl_bufp = hpread_get_slt (index + i, objfile); - return sl_bufp->snorm.address; -} - - -/* Return 1 if an HP debug symbol of type KIND has a name associated with - it, else return 0. */ - -static int -hpread_has_name (kind) - enum dntt_entry_type kind; -{ - switch (kind) - { - case DNTT_TYPE_SRCFILE: - case DNTT_TYPE_MODULE: - case DNTT_TYPE_FUNCTION: - case DNTT_TYPE_ENTRY: - case DNTT_TYPE_IMPORT: - case DNTT_TYPE_LABEL: - case DNTT_TYPE_FPARAM: - case DNTT_TYPE_SVAR: - case DNTT_TYPE_DVAR: - case DNTT_TYPE_CONST: - case DNTT_TYPE_TYPEDEF: - case DNTT_TYPE_TAGDEF: - case DNTT_TYPE_MEMENUM: - case DNTT_TYPE_FIELD: - case DNTT_TYPE_SA: - return 1; - - case DNTT_TYPE_BEGIN: - case DNTT_TYPE_END: - case DNTT_TYPE_WITH: - case DNTT_TYPE_COMMON: - case DNTT_TYPE_POINTER: - case DNTT_TYPE_ENUM: - case DNTT_TYPE_SET: - case DNTT_TYPE_SUBRANGE: - case DNTT_TYPE_ARRAY: - case DNTT_TYPE_STRUCT: - case DNTT_TYPE_UNION: - case DNTT_TYPE_VARIANT: - case DNTT_TYPE_FILE: - case DNTT_TYPE_FUNCTYPE: - case DNTT_TYPE_COBSTRUCT: - case DNTT_TYPE_XREF: - case DNTT_TYPE_MACRO: - default: - return 0; - } -} - -/* Allocate and partially fill a partial symtab. It will be - completely filled at the end of the symbol list. - - SYMFILE_NAME is the name of the symbol-file we are reading from, and ADDR - is the address relative to which its symbols are (incremental) or 0 - (normal). */ - -static struct partial_symtab * -hpread_start_psymtab (objfile, section_offsets, - filename, textlow, ldsymoff, global_syms, static_syms) - struct objfile *objfile; - struct section_offsets *section_offsets; - char *filename; - CORE_ADDR textlow; - int ldsymoff; - struct partial_symbol **global_syms; - struct partial_symbol **static_syms; -{ - struct partial_symtab *result = - start_psymtab_common (objfile, section_offsets, - filename, textlow, global_syms, static_syms); - - result->read_symtab_private = (char *) - obstack_alloc (&objfile->psymbol_obstack, sizeof (struct symloc)); - LDSYMOFF (result) = ldsymoff; - result->read_symtab = hpread_psymtab_to_symtab; - - return result; -} - - -/* Close off the current usage of PST. - Returns PST or NULL if the partial symtab was empty and thrown away. - - FIXME: List variables and peculiarities of same. */ - -static struct partial_symtab * -hpread_end_psymtab (pst, include_list, num_includes, capping_symbol_offset, - capping_text, dependency_list, number_dependencies) - struct partial_symtab *pst; - char **include_list; - int num_includes; - int capping_symbol_offset; - CORE_ADDR capping_text; - struct partial_symtab **dependency_list; - int number_dependencies; -{ - int i; - struct objfile *objfile = pst -> objfile; - - if (capping_symbol_offset != -1) - LDSYMLEN(pst) = capping_symbol_offset - LDSYMOFF(pst); - pst->texthigh = capping_text; - - 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); - - pst->number_of_dependencies = number_dependencies; - if (number_dependencies) - { - pst->dependencies = (struct partial_symtab **) - obstack_alloc (&objfile->psymbol_obstack, - number_dependencies * sizeof (struct partial_symtab *)); - memcpy (pst->dependencies, dependency_list, - number_dependencies * sizeof (struct partial_symtab *)); - } - else - pst->dependencies = 0; - - for (i = 0; i < num_includes; i++) - { - struct partial_symtab *subpst = - allocate_psymtab (include_list[i], objfile); - - subpst->section_offsets = pst->section_offsets; - subpst->read_symtab_private = - (char *) obstack_alloc (&objfile->psymbol_obstack, - sizeof (struct symloc)); - LDSYMOFF(subpst) = - LDSYMLEN(subpst) = - subpst->textlow = - subpst->texthigh = 0; - - /* We could save slight bits of space by only making one of these, - shared by the entire set of include files. FIXME-someday. */ - subpst->dependencies = (struct partial_symtab **) - obstack_alloc (&objfile->psymbol_obstack, - sizeof (struct partial_symtab *)); - subpst->dependencies[0] = pst; - subpst->number_of_dependencies = 1; - - subpst->globals_offset = - subpst->n_global_syms = - subpst->statics_offset = - subpst->n_static_syms = 0; - - subpst->readin = 0; - subpst->symtab = 0; - subpst->read_symtab = pst->read_symtab; - } - - sort_pst_symbols (pst); - - /* If there is already a psymtab or symtab for a file of this name, remove it. - (If there is a symtab, more drastic things also happen.) - This happens in VxWorks. */ - free_named_symtabs (pst->filename); - - if (num_includes == 0 - && number_dependencies == 0 - && pst->n_global_syms == 0 - && pst->n_static_syms == 0) - { - /* Throw away this psymtab, it's empty. We can't deallocate it, since - it is on the obstack, but we can forget to chain it on the list. */ - /* Empty psymtabs happen as a result of header files which don't have - any symbols in them. There can be a lot of them. But this check - is wrong, in that a psymtab with N_SLINE entries but nothing else - is not empty, but we don't realize that. Fixing that without slowing - things down might be tricky. */ - - discard_psymtab (pst); - - /* Indicate that psymtab was thrown away. */ - pst = (struct partial_symtab *)NULL; - } - return pst; -} - -/* Do the dirty work of reading in the full symbol from a partial symbol - table. */ - -static void -hpread_psymtab_to_symtab_1 (pst) - struct partial_symtab *pst; -{ - struct cleanup *old_chain; - int i; - - /* Get out quick if passed junk. */ - if (!pst) - return; - - /* Complain if we've already read in this symbol table. */ - if (pst->readin) - { - fprintf (stderr, "Psymtab for %s already read in. Shouldn't happen.\n", - pst->filename); - return; - } - - /* Read in all partial symtabs on which this one is dependent */ - for (i = 0; i < pst->number_of_dependencies; i++) - if (!pst->dependencies[i]->readin) - { - /* Inform about additional files that need to be read in. */ - if (info_verbose) - { - fputs_filtered (" ", gdb_stdout); - wrap_here (""); - fputs_filtered ("and ", gdb_stdout); - wrap_here (""); - printf_filtered ("%s...", pst->dependencies[i]->filename); - wrap_here (""); /* Flush output */ - gdb_flush (gdb_stdout); - } - hpread_psymtab_to_symtab_1 (pst->dependencies[i]); - } - - /* If it's real... */ - if (LDSYMLEN (pst)) - { - /* Init stuff necessary for reading in symbols */ - buildsym_init (); - old_chain = make_cleanup (really_free_pendings, 0); - - pst->symtab = - hpread_expand_symtab (pst->objfile, LDSYMOFF (pst), LDSYMLEN (pst), - pst->textlow, pst->texthigh - pst->textlow, - pst->section_offsets, pst->filename); - sort_symtab_syms (pst->symtab); - - do_cleanups (old_chain); - } - - pst->readin = 1; -} - -/* Read in all of the symbols for a given psymtab for real. - Be verbose about it if the user wants that. */ - -static void -hpread_psymtab_to_symtab (pst) - struct partial_symtab *pst; -{ - /* Get out quick if given junk. */ - if (!pst) - return; - - /* Sanity check. */ - if (pst->readin) - { - fprintf (stderr, "Psymtab for %s already read in. Shouldn't happen.\n", - pst->filename); - return; - } - - if (LDSYMLEN (pst) || pst->number_of_dependencies) - { - /* Print the message now, before reading the string table, - to avoid disconcerting pauses. */ - if (info_verbose) - { - printf_filtered ("Reading in symbols for %s...", pst->filename); - gdb_flush (gdb_stdout); - } - - hpread_psymtab_to_symtab_1 (pst); - - /* Match with global symbols. This only needs to be done once, - after all of the symtabs and dependencies have been read in. */ - scan_file_globals (pst->objfile); - - /* Finish up the debug error message. */ - if (info_verbose) - printf_filtered ("done.\n"); - } -} -/* Read in a defined section of a specific object file's symbols. - - DESC is the file descriptor for the file, positioned at the - beginning of the symtab - SYM_OFFSET is the offset within the file of - the beginning of the symbols we want to read - SYM_SIZE is the size of the symbol info to read in. - TEXT_OFFSET is the beginning of the text segment we are reading symbols for - TEXT_SIZE is the size of the text segment read in. - SECTION_OFFSETS are the relocation offsets which get added to each symbol. */ - -static struct symtab * -hpread_expand_symtab (objfile, sym_offset, sym_size, text_offset, text_size, - section_offsets, filename) - struct objfile *objfile; - int sym_offset; - int sym_size; - CORE_ADDR text_offset; - int text_size; - struct section_offsets *section_offsets; - char *filename; -{ - char *namestring; - union dnttentry *dn_bufp; - unsigned max_symnum; - - int sym_index = sym_offset / sizeof (struct dntt_type_block); - - current_objfile = objfile; - subfile_stack = 0; - - last_source_file = 0; - - dn_bufp = hpread_get_lntt (sym_index, objfile); - if (!((dn_bufp->dblock.kind == (unsigned char) DNTT_TYPE_SRCFILE) || - (dn_bufp->dblock.kind == (unsigned char) DNTT_TYPE_MODULE))) - { - start_symtab ("globals", NULL, 0); - record_debugformat ("HP"); - } - - max_symnum = sym_size / sizeof (struct dntt_type_block); - - /* Read in and process each debug symbol within the specified range. */ - for (symnum = 0; - symnum < max_symnum; - symnum++) - { - QUIT; /* Allow this to be interruptable */ - dn_bufp = hpread_get_lntt (sym_index + symnum, objfile); - - if (dn_bufp->dblock.extension) - continue; - - /* Yow! We call SET_NAMESTRING on things without names! */ - SET_NAMESTRING (dn_bufp, &namestring, objfile); - - hpread_process_one_debug_symbol (dn_bufp, namestring, section_offsets, - objfile, text_offset, text_size, - filename, symnum + sym_index); - } - - current_objfile = NULL; - - return end_symtab (text_offset + text_size, objfile, 0); -} - - -/* Convert basic types from HP debug format into GDB internal format. */ - -static int -hpread_type_translate (typep) - dnttpointer typep; -{ - if (!typep.dntti.immediate) - abort (); - - switch (typep.dntti.type) - { - case HP_TYPE_BOOLEAN: - case HP_TYPE_BOOLEAN_S300_COMPAT: - case HP_TYPE_BOOLEAN_VAX_COMPAT: - return FT_BOOLEAN; - /* Ugh. No way to distinguish between signed and unsigned chars. */ - case HP_TYPE_CHAR: - case HP_TYPE_WIDE_CHAR: - return FT_CHAR; - case HP_TYPE_INT: - if (typep.dntti.bitlength <= 8) - return FT_CHAR; - if (typep.dntti.bitlength <= 16) - return FT_SHORT; - if (typep.dntti.bitlength <= 32) - return FT_INTEGER; - return FT_LONG_LONG; - case HP_TYPE_LONG: - return FT_LONG; - case HP_TYPE_UNSIGNED_LONG: - if (typep.dntti.bitlength <= 8) - return FT_UNSIGNED_CHAR; - if (typep.dntti.bitlength <= 16) - return FT_UNSIGNED_SHORT; - if (typep.dntti.bitlength <= 32) - return FT_UNSIGNED_LONG; - return FT_UNSIGNED_LONG_LONG; - case HP_TYPE_UNSIGNED_INT: - if (typep.dntti.bitlength <= 8) - return FT_UNSIGNED_CHAR; - if (typep.dntti.bitlength <= 16) - return FT_UNSIGNED_SHORT; - if (typep.dntti.bitlength <= 32) - return FT_UNSIGNED_INTEGER; - return FT_UNSIGNED_LONG_LONG; - case HP_TYPE_REAL: - case HP_TYPE_REAL_3000: - case HP_TYPE_DOUBLE: - if (typep.dntti.bitlength == 64) - return FT_DBL_PREC_FLOAT; - if (typep.dntti.bitlength == 128) - return FT_EXT_PREC_FLOAT; - return FT_FLOAT; - case HP_TYPE_COMPLEX: - case HP_TYPE_COMPLEXS3000: - if (typep.dntti.bitlength == 128) - return FT_DBL_PREC_COMPLEX; - if (typep.dntti.bitlength == 192) - return FT_EXT_PREC_COMPLEX; - return FT_COMPLEX; - case HP_TYPE_STRING200: - case HP_TYPE_LONGSTRING200: - case HP_TYPE_FTN_STRING_SPEC: - case HP_TYPE_MOD_STRING_SPEC: - case HP_TYPE_MOD_STRING_3000: - case HP_TYPE_FTN_STRING_S300_COMPAT: - case HP_TYPE_FTN_STRING_VAX_COMPAT: - return FT_STRING; - default: - abort (); - } -} - -/* Return the type associated with the index found in HP_TYPE. */ - -static struct type ** -hpread_lookup_type (hp_type, objfile) - dnttpointer hp_type; - struct objfile *objfile; -{ - unsigned old_len; - int index = hp_type.dnttp.index; - - if (hp_type.dntti.immediate) - return NULL; - - if (index < LNTT_SYMCOUNT (objfile)) - { - if (index >= TYPE_VECTOR_LENGTH (objfile)) - { - old_len = TYPE_VECTOR_LENGTH (objfile); - if (old_len == 0) - { - TYPE_VECTOR_LENGTH (objfile) = 100; - TYPE_VECTOR (objfile) = (struct type **) - xmmalloc (objfile -> md, - TYPE_VECTOR_LENGTH (objfile) * sizeof (struct type *)); - } - while (index >= TYPE_VECTOR_LENGTH (objfile)) - TYPE_VECTOR_LENGTH (objfile) *= 2; - TYPE_VECTOR (objfile) = (struct type **) - xmrealloc (objfile -> md, - (char *) TYPE_VECTOR (objfile), - (TYPE_VECTOR_LENGTH (objfile) * sizeof (struct type *))); - memset (&TYPE_VECTOR (objfile)[old_len], 0, - (TYPE_VECTOR_LENGTH (objfile) - old_len) * - sizeof (struct type *)); - } - return &TYPE_VECTOR (objfile)[index]; - } - else - return NULL; -} - -/* Possibly allocate a GDB internal type so we can internalize HP_TYPE. - Note we'll just return the address of a GDB internal type if we already - have it lying around. */ - -static struct type * -hpread_alloc_type (hp_type, objfile) - dnttpointer hp_type; - struct objfile *objfile; -{ - struct type **type_addr; - - type_addr = hpread_lookup_type (hp_type, objfile); - if (*type_addr == 0) - *type_addr = alloc_type (objfile); - - TYPE_CPLUS_SPECIFIC (*type_addr) - = (struct cplus_struct_type *) &cplus_struct_default; - return *type_addr; -} - -/* Read a native enumerated type and return it in GDB internal form. */ - -static struct type * -hpread_read_enum_type (hp_type, dn_bufp, objfile) - dnttpointer hp_type; - union dnttentry *dn_bufp; - struct objfile *objfile; -{ - struct type *type; - struct pending **symlist, *osyms, *syms; - int o_nsyms, nsyms = 0; - dnttpointer mem; - union dnttentry *memp; - char *name; - long n; - struct symbol *sym; - - type = hpread_alloc_type (hp_type, objfile); - TYPE_LENGTH (type) = 4; - - symlist = &file_symbols; - osyms = *symlist; - o_nsyms = osyms ? osyms->nsyms : 0; - - /* Get a name for each member and add it to our list of members. */ - mem = dn_bufp->denum.firstmem; - while (mem.dnttp.extension && mem.word != DNTTNIL) - { - memp = hpread_get_lntt (mem.dnttp.index, objfile); - - name = VT (objfile) + memp->dmember.name; - sym = (struct symbol *) obstack_alloc (&objfile->symbol_obstack, - sizeof (struct symbol)); - memset (sym, 0, sizeof (struct symbol)); - SYMBOL_NAME (sym) = obsavestring (name, strlen (name), - &objfile->symbol_obstack); - SYMBOL_CLASS (sym) = LOC_CONST; - SYMBOL_NAMESPACE (sym) = VAR_NAMESPACE; - SYMBOL_VALUE (sym) = memp->dmember.value; - add_symbol_to_list (sym, symlist); - nsyms++; - mem = memp->dmember.nextmem; - } - - /* Now that we know more about the enum, fill in more info. */ - TYPE_CODE (type) = TYPE_CODE_ENUM; - TYPE_FLAGS (type) &= ~TYPE_FLAG_STUB; - TYPE_NFIELDS (type) = nsyms; - TYPE_FIELDS (type) = (struct field *) - obstack_alloc (&objfile->type_obstack, sizeof (struct field) * nsyms); - - /* Find the symbols for the members and put them into the type. - The symbols can be found in the symlist that we put them on - to cause them to be defined. osyms contains the old value - of that symlist; everything up to there was defined by us. - - Note that we preserve the order of the enum constants, so - that in something like "enum {FOO, LAST_THING=FOO}" we print - FOO, not LAST_THING. */ - for (syms = *symlist, n = 0; syms; syms = syms->next) - { - int j = 0; - if (syms == osyms) - j = o_nsyms; - for (; j < syms->nsyms; j++, n++) - { - struct symbol *xsym = syms->symbol[j]; - SYMBOL_TYPE (xsym) = type; - TYPE_FIELD_NAME (type, n) = SYMBOL_NAME (xsym); - TYPE_FIELD_BITPOS (type, n) = SYMBOL_VALUE (xsym); - TYPE_FIELD_BITSIZE (type, n) = 0; - } - if (syms == osyms) - break; - } - - return type; -} - -/* Read and internalize a native function debug symbol. */ - -static struct type * -hpread_read_function_type (hp_type, dn_bufp, objfile) - dnttpointer hp_type; - union dnttentry *dn_bufp; - struct objfile *objfile; -{ - struct type *type, *type1; - struct pending **symlist, *osyms, *syms; - int o_nsyms, nsyms = 0; - dnttpointer param; - union dnttentry *paramp; - char *name; - long n; - struct symbol *sym; - - param = dn_bufp->dfunc.firstparam; - - /* See if we've already read in this type. */ - type = hpread_alloc_type (hp_type, objfile); - if (TYPE_CODE (type) == TYPE_CODE_FUNC) - return type; - - /* Nope, so read it in and store it away. */ - type1 = lookup_function_type (hpread_type_lookup (dn_bufp->dfunc.retval, - objfile)); - memcpy ((char *) type, (char *) type1, sizeof (struct type)); - - symlist = &local_symbols; - osyms = *symlist; - o_nsyms = osyms ? osyms->nsyms : 0; - - /* Now examine each parameter noting its type, location, and a - wealth of other information. */ - while (param.word && param.word != DNTTNIL) - { - paramp = hpread_get_lntt (param.dnttp.index, objfile); - nsyms++; - param = paramp->dfparam.nextparam; - - /* Get the name. */ - name = VT (objfile) + paramp->dfparam.name; - sym = (struct symbol *) obstack_alloc (&objfile->symbol_obstack, - sizeof (struct symbol)); - (void) memset (sym, 0, sizeof (struct symbol)); - SYMBOL_NAME (sym) = obsavestring (name, strlen (name), - &objfile->symbol_obstack); - - /* Figure out where it lives. */ - if (paramp->dfparam.regparam) - SYMBOL_CLASS (sym) = LOC_REGPARM; - else if (paramp->dfparam.indirect) - SYMBOL_CLASS (sym) = LOC_REF_ARG; - else - SYMBOL_CLASS (sym) = LOC_ARG; - SYMBOL_NAMESPACE (sym) = VAR_NAMESPACE; - if (paramp->dfparam.copyparam) - { - SYMBOL_VALUE (sym) = paramp->dfparam.location ; -#ifdef HPREAD_ADJUST_STACK_ADDRESS - SYMBOL_VALUE (sym) - += HPREAD_ADJUST_STACK_ADDRESS (CURRENT_FUNCTION_VALUE (objfile)); -#endif - /* This is likely a pass-by-invisible reference parameter, - Hack on the symbol class to make GDB happy. */ - SYMBOL_CLASS (sym) = LOC_REGPARM_ADDR; - } - else - SYMBOL_VALUE (sym) = paramp->dfparam.location; - - /* Get its type. */ - SYMBOL_TYPE (sym) = hpread_type_lookup (paramp->dfparam.type, objfile); - - /* Add it to the list. */ - add_symbol_to_list (sym, symlist); - } - - /* Note how many parameters we found. */ - TYPE_NFIELDS (type) = nsyms; - TYPE_FIELDS (type) = (struct field *) - obstack_alloc (&objfile->type_obstack, - sizeof (struct field) * nsyms); - - /* Find the symbols for the values and put them into the type. - The symbols can be found in the symlist that we put them on - to cause them to be defined. osyms contains the old value - of that symlist; everything up to there was defined by us. */ - /* Note that we preserve the order of the parameters, so - that in something like "enum {FOO, LAST_THING=FOO}" we print - FOO, not LAST_THING. */ - for (syms = *symlist, n = 0; syms; syms = syms->next) - { - int j = 0; - if (syms == osyms) - j = o_nsyms; - for (; j < syms->nsyms; j++, n++) - { - struct symbol *xsym = syms->symbol[j]; - TYPE_FIELD_NAME (type, n) = SYMBOL_NAME (xsym); - TYPE_FIELD_TYPE (type, n) = SYMBOL_TYPE (xsym); - TYPE_FIELD_BITPOS (type, n) = n; - TYPE_FIELD_BITSIZE (type, n) = 0; - } - if (syms == osyms) - break; - } - return type; -} - -/* Read in and internalize a structure definition. */ - -static struct type * -hpread_read_struct_type (hp_type, dn_bufp, objfile) - dnttpointer hp_type; - union dnttentry *dn_bufp; - struct objfile *objfile; -{ - struct nextfield - { - struct nextfield *next; - struct field field; - }; - - struct type *type; - struct nextfield *list = 0; - struct nextfield *new; - int n, nfields = 0; - dnttpointer field; - union dnttentry *fieldp; - - /* Is it something we've already dealt with? */ - type = hpread_alloc_type (hp_type, objfile); - if ((TYPE_CODE (type) == TYPE_CODE_STRUCT) || - (TYPE_CODE (type) == TYPE_CODE_UNION)) - return type; - - /* Get the basic type correct. */ - if (dn_bufp->dblock.kind == DNTT_TYPE_STRUCT) - { - TYPE_CODE (type) = TYPE_CODE_STRUCT; - TYPE_LENGTH (type) = dn_bufp->dstruct.bitlength / 8; - } - else if (dn_bufp->dblock.kind == DNTT_TYPE_UNION) - { - TYPE_CODE (type) = TYPE_CODE_UNION; - TYPE_LENGTH (type) = dn_bufp->dunion.bitlength / 8; - } - else - return type; - - - TYPE_FLAGS (type) &= ~TYPE_FLAG_STUB; - - /* Read in and internalize all the fields. */ - field = dn_bufp->dstruct.firstfield; - while (field.word != DNTTNIL && field.dnttp.extension) - { - fieldp = hpread_get_lntt (field.dnttp.index, objfile); - - /* Get space to record the next field's data. */ - new = (struct nextfield *) alloca (sizeof (struct nextfield)); - new->next = list; - list = new; - - list->field.name = VT (objfile) + fieldp->dfield.name; - FIELD_BITPOS (list->field) = fieldp->dfield.bitoffset; - if (fieldp->dfield.bitlength % 8) - FIELD_BITSIZE (list->field) = fieldp->dfield.bitlength; - else - FIELD_BITSIZE (list->field) = 0; - nfields++; - field = fieldp->dfield.nextfield; - FIELD_TYPE (list->field) = hpread_type_lookup (fieldp->dfield.type, - objfile); - } - - TYPE_NFIELDS (type) = nfields; - TYPE_FIELDS (type) = (struct field *) - obstack_alloc (&objfile->type_obstack, sizeof (struct field) * nfields); - - /* Copy the saved-up fields into the field vector. */ - for (n = nfields; list; list = list->next) - { - n -= 1; - TYPE_FIELD (type, n) = list->field; - } - return type; -} - -/* Read in and internalize a set debug symbol. */ - -static struct type * -hpread_read_set_type (hp_type, dn_bufp, objfile) - dnttpointer hp_type; - union dnttentry *dn_bufp; - struct objfile *objfile; -{ - struct type *type; - - /* See if it's something we've already deal with. */ - type = hpread_alloc_type (hp_type, objfile); - if (TYPE_CODE (type) == TYPE_CODE_SET) - return type; - - /* Nope. Fill in the appropriate fields. */ - TYPE_CODE (type) = TYPE_CODE_SET; - TYPE_LENGTH (type) = dn_bufp->dset.bitlength / 8; - TYPE_NFIELDS (type) = 0; - TYPE_TARGET_TYPE (type) = hpread_type_lookup (dn_bufp->dset.subtype, - objfile); - return type; -} - -/* Read in and internalize an array debug symbol. */ - -static struct type * -hpread_read_array_type (hp_type, dn_bufp, objfile) - dnttpointer hp_type; - union dnttentry *dn_bufp; - struct objfile *objfile; -{ - struct type *type; - union dnttentry save; - save = *dn_bufp; - - /* Why no check here? Because it kept us from properly determining - the size of the array! */ - type = hpread_alloc_type (hp_type, objfile); - - TYPE_CODE (type) = TYPE_CODE_ARRAY; - - /* values are not normalized. */ - if (!((dn_bufp->darray.arrayisbytes && dn_bufp->darray.elemisbytes) - || (!dn_bufp->darray.arrayisbytes && !dn_bufp->darray.elemisbytes))) - abort (); - else if (dn_bufp->darray.arraylength == 0x7fffffff) - { - /* The HP debug format represents char foo[]; as an array with - length 0x7fffffff. Internally GDB wants to represent this - as an array of length zero. */ - TYPE_LENGTH (type) = 0; - } - else - TYPE_LENGTH (type) = dn_bufp->darray.arraylength / 8; - - TYPE_NFIELDS (type) = 1; - TYPE_TARGET_TYPE (type) = hpread_type_lookup (dn_bufp->darray.elemtype, - objfile); - dn_bufp = &save; - TYPE_FIELDS (type) = (struct field *) - obstack_alloc (&objfile->type_obstack, sizeof (struct field)); - TYPE_FIELD_TYPE (type, 0) = hpread_type_lookup (dn_bufp->darray.indextype, - objfile); - return type; -} - -/* Read in and internalize a subrange debug symbol. */ -static struct type * -hpread_read_subrange_type (hp_type, dn_bufp, objfile) - dnttpointer hp_type; - union dnttentry *dn_bufp; - struct objfile *objfile; -{ - struct type *type; - - /* Is it something we've already dealt with. */ - type = hpread_alloc_type (hp_type, objfile); - if (TYPE_CODE (type) == TYPE_CODE_RANGE) - return type; - - /* Nope, internalize it. */ - TYPE_CODE (type) = TYPE_CODE_RANGE; - TYPE_LENGTH (type) = dn_bufp->dsubr.bitlength / 8; - TYPE_NFIELDS (type) = 2; - TYPE_FIELDS (type) - = (struct field *) obstack_alloc (&objfile->type_obstack, - 2 * sizeof (struct field)); - - if (dn_bufp->dsubr.dyn_low) - TYPE_FIELD_BITPOS (type, 0) = 0; - else - TYPE_FIELD_BITPOS (type, 0) = dn_bufp->dsubr.lowbound; - - if (dn_bufp->dsubr.dyn_high) - TYPE_FIELD_BITPOS (type, 1) = -1; - else - TYPE_FIELD_BITPOS (type, 1) = dn_bufp->dsubr.highbound; - TYPE_TARGET_TYPE (type) = hpread_type_lookup (dn_bufp->dsubr.subtype, - objfile); - return type; -} - -static struct type * -hpread_type_lookup (hp_type, objfile) - dnttpointer hp_type; - struct objfile *objfile; -{ - union dnttentry *dn_bufp; - - /* First see if it's a simple builtin type. */ - if (hp_type.dntti.immediate) - return lookup_fundamental_type (objfile, hpread_type_translate (hp_type)); - - /* Not a builtin type. We'll have to read it in. */ - if (hp_type.dnttp.index < LNTT_SYMCOUNT (objfile)) - dn_bufp = hpread_get_lntt (hp_type.dnttp.index, objfile); - else - return lookup_fundamental_type (objfile, FT_VOID); - - switch (dn_bufp->dblock.kind) - { - case DNTT_TYPE_SRCFILE: - case DNTT_TYPE_MODULE: - case DNTT_TYPE_FUNCTION: - case DNTT_TYPE_ENTRY: - case DNTT_TYPE_BEGIN: - case DNTT_TYPE_END: - case DNTT_TYPE_IMPORT: - case DNTT_TYPE_LABEL: - case DNTT_TYPE_WITH: - case DNTT_TYPE_COMMON: - case DNTT_TYPE_FPARAM: - case DNTT_TYPE_SVAR: - case DNTT_TYPE_DVAR: - case DNTT_TYPE_CONST: - /* Opps. Something went very wrong. */ - return lookup_fundamental_type (objfile, FT_VOID); - - case DNTT_TYPE_TYPEDEF: - { - struct type *structtype = hpread_type_lookup (dn_bufp->dtype.type, - objfile); - char *suffix; - suffix = VT (objfile) + dn_bufp->dtype.name; - - TYPE_CPLUS_SPECIFIC (structtype) - = (struct cplus_struct_type *) &cplus_struct_default; - TYPE_NAME (structtype) = suffix; - return structtype; - } - - case DNTT_TYPE_TAGDEF: - { - /* Just a little different from above. We have to tack on - an identifier of some kind (struct, union, enum, etc). */ - struct type *structtype = hpread_type_lookup (dn_bufp->dtype.type, - objfile); - char *prefix, *suffix; - suffix = VT (objfile) + dn_bufp->dtype.name; - - /* Lookup the next type in the list. It should be a structure, - union, or enum type. We will need to attach that to our name. */ - if (dn_bufp->dtype.type.dnttp.index < LNTT_SYMCOUNT (objfile)) - dn_bufp = hpread_get_lntt (dn_bufp->dtype.type.dnttp.index, objfile); - else - abort (); - - if (dn_bufp->dblock.kind == DNTT_TYPE_STRUCT) - prefix = "struct "; - else if (dn_bufp->dblock.kind == DNTT_TYPE_UNION) - prefix = "union "; - else - prefix = "enum "; - - /* Build the correct name. */ - structtype->name - = (char *) obstack_alloc (&objfile->type_obstack, - strlen (prefix) + strlen (suffix) + 1); - TYPE_NAME (structtype) = strcpy (TYPE_NAME (structtype), prefix); - TYPE_NAME (structtype) = strcat (TYPE_NAME (structtype), suffix); - TYPE_TAG_NAME (structtype) = suffix; - - TYPE_CPLUS_SPECIFIC (structtype) - = (struct cplus_struct_type *) &cplus_struct_default; - - return structtype; - } - case DNTT_TYPE_POINTER: - return lookup_pointer_type (hpread_type_lookup (dn_bufp->dptr.pointsto, - objfile)); - case DNTT_TYPE_ENUM: - return hpread_read_enum_type (hp_type, dn_bufp, objfile); - case DNTT_TYPE_MEMENUM: - return lookup_fundamental_type (objfile, FT_VOID); - case DNTT_TYPE_SET: - return hpread_read_set_type (hp_type, dn_bufp, objfile); - case DNTT_TYPE_SUBRANGE: - return hpread_read_subrange_type (hp_type, dn_bufp, objfile); - case DNTT_TYPE_ARRAY: - return hpread_read_array_type (hp_type, dn_bufp, objfile); - case DNTT_TYPE_STRUCT: - case DNTT_TYPE_UNION: - return hpread_read_struct_type (hp_type, dn_bufp, objfile); - case DNTT_TYPE_FIELD: - return hpread_type_lookup (dn_bufp->dfield.type, objfile); - case DNTT_TYPE_VARIANT: - case DNTT_TYPE_FILE: - return lookup_fundamental_type (objfile, FT_VOID); - case DNTT_TYPE_FUNCTYPE: - return lookup_function_type (hpread_type_lookup (dn_bufp->dfunctype.retval, - objfile)); - case DNTT_TYPE_COBSTRUCT: - case DNTT_TYPE_XREF: - case DNTT_TYPE_SA: - case DNTT_TYPE_MACRO: - default: - return lookup_fundamental_type (objfile, FT_VOID); - } -} - -static sltpointer -hpread_record_lines (subfile, s_idx, e_idx, objfile, offset) - struct subfile *subfile; - sltpointer s_idx, e_idx; - struct objfile *objfile; - CORE_ADDR offset; -{ - union sltentry *sl_bufp; - - while (s_idx <= e_idx) - { - sl_bufp = hpread_get_slt (s_idx, objfile); - /* Only record "normal" entries in the SLT. */ - if (sl_bufp->snorm.sltdesc == SLT_NORMAL - || sl_bufp->snorm.sltdesc == SLT_EXIT) - record_line (subfile, sl_bufp->snorm.line, - sl_bufp->snorm.address + offset); - s_idx++; - } - return e_idx; -} - -/* Internalize one native debug symbol. */ - -static void -hpread_process_one_debug_symbol (dn_bufp, name, section_offsets, objfile, - text_offset, text_size, filename, index) - union dnttentry *dn_bufp; - char *name; - struct section_offsets *section_offsets; - struct objfile *objfile; - CORE_ADDR text_offset; - int text_size; - char *filename; - int index; -{ - unsigned long desc; - int type; - CORE_ADDR valu; - int offset = ANOFFSET (section_offsets, SECT_OFF_TEXT); - union dnttentry *dn_temp; - dnttpointer hp_type; - struct symbol *sym; - struct context_stack *new; - - /* Allocate one GDB debug symbol and fill in some default values. */ - sym = (struct symbol *) obstack_alloc (&objfile->symbol_obstack, - sizeof (struct symbol)); - memset (sym, 0, sizeof (struct symbol)); - SYMBOL_NAME (sym) = obsavestring (name, strlen (name), &objfile->symbol_obstack); - SYMBOL_LANGUAGE (sym) = language_auto; - SYMBOL_INIT_DEMANGLED_NAME (sym, &objfile->symbol_obstack); - SYMBOL_NAMESPACE (sym) = VAR_NAMESPACE; - SYMBOL_LINE (sym) = 0; - SYMBOL_VALUE (sym) = 0; - SYMBOL_CLASS (sym) = LOC_TYPEDEF; - - hp_type.dnttp.extension = 1; - hp_type.dnttp.immediate = 0; - hp_type.dnttp.global = 0; - hp_type.dnttp.index = index; - - type = dn_bufp->dblock.kind; - - switch (type) - { - case DNTT_TYPE_SRCFILE: - /* This type of symbol indicates from which source file or include file - the following data comes. If there are no modules it also may - indicate the start of a new source file, in which case we must - finish the symbol table of the previous source file - (if any) and start accumulating a new symbol table. */ - - valu = text_offset; - if (!last_source_file) - { - start_symtab (name, NULL, valu); - record_debugformat ("HP"); - SL_INDEX (objfile) = dn_bufp->dsfile.address; - } - else - { - SL_INDEX (objfile) = hpread_record_lines (current_subfile, - SL_INDEX (objfile), - dn_bufp->dsfile.address, - objfile, offset); - } - start_subfile (name, NULL); - break; - - case DNTT_TYPE_MODULE: - /* No need to do anything with these DNTT_TYPE_MODULE symbols anymore. */ - break; - - case DNTT_TYPE_FUNCTION: - case DNTT_TYPE_ENTRY: - /* A function or secondary entry point. */ - valu = dn_bufp->dfunc.lowaddr + offset; - SL_INDEX (objfile) = hpread_record_lines (current_subfile, - SL_INDEX (objfile), - dn_bufp->dfunc.address, - objfile, offset); - - WITHIN_FUNCTION (objfile) = 1; - CURRENT_FUNCTION_VALUE (objfile) = valu; - - /* Stack must be empty now. */ - if (context_stack_depth != 0) - complain (&lbrac_unmatched_complaint, (char *) symnum); - new = push_context (0, valu); - - SYMBOL_CLASS (sym) = LOC_BLOCK; - SYMBOL_TYPE (sym) = hpread_read_function_type (hp_type, dn_bufp, objfile); - if (dn_bufp->dfunc.global) - add_symbol_to_list (sym, &global_symbols); - else - add_symbol_to_list (sym, &file_symbols); - new->name = sym; - - /* Search forward to the next scope beginning. */ - while (dn_bufp->dblock.kind != DNTT_TYPE_BEGIN) - { - dn_bufp = hpread_get_lntt (++index, objfile); - if (dn_bufp->dblock.extension) - continue; - } - SL_INDEX (objfile) = hpread_record_lines (current_subfile, - SL_INDEX (objfile), - dn_bufp->dbegin.address, - objfile, offset); - SYMBOL_LINE (sym) = hpread_get_line (dn_bufp->dbegin.address, objfile); - record_line (current_subfile, SYMBOL_LINE (sym), valu); - break; - - case DNTT_TYPE_BEGIN: - /* Begin a new scope. */ - SL_INDEX (objfile) = hpread_record_lines (current_subfile, - SL_INDEX (objfile), - dn_bufp->dbegin.address, - objfile, offset); - valu = hpread_get_location (dn_bufp->dbegin.address, objfile); - valu += offset; /* Relocate for dynamic loading */ - desc = hpread_get_depth (dn_bufp->dbegin.address, objfile); - new = push_context (desc, valu); - break; - - case DNTT_TYPE_END: - /* End a scope. */ - SL_INDEX (objfile) = hpread_record_lines (current_subfile, - SL_INDEX (objfile), - dn_bufp->dend.address + 1, - objfile, offset); - switch (dn_bufp->dend.endkind) - { - case DNTT_TYPE_MODULE: - /* Ending a module ends the symbol table for that module. */ - valu = text_offset + text_size + offset; - (void) end_symtab (valu, objfile, 0); - break; - - case DNTT_TYPE_FUNCTION: - /* Ending a function, well, ends the function's scope. */ - dn_temp = hpread_get_lntt (dn_bufp->dend.beginscope.dnttp.index, - objfile); - valu = dn_temp->dfunc.hiaddr + offset; - new = pop_context (); - /* Make a block for the local symbols within. */ - finish_block (new->name, &local_symbols, new->old_blocks, - new->start_addr, valu, objfile); - WITHIN_FUNCTION (objfile) = 0; - break; - case DNTT_TYPE_BEGIN: - /* Just ending a local scope. */ - valu = hpread_get_location (dn_bufp->dend.address, objfile); - /* Why in the hell is this needed? */ - valu += offset + 9; /* Relocate for dynamic loading */ - new = pop_context (); - desc = dn_bufp->dend.beginscope.dnttp.index; - if (desc != new->depth) - complain (&lbrac_mismatch_complaint, (char *) symnum); - /* Make a block for the local symbols within. */ - finish_block (new->name, &local_symbols, new->old_blocks, - new->start_addr, valu, objfile); - local_symbols = new->locals; - break; - } - break; - case DNTT_TYPE_LABEL: - SYMBOL_NAMESPACE (sym) = LABEL_NAMESPACE; - break; - case DNTT_TYPE_FPARAM: - /* Function parameters. */ - if (dn_bufp->dfparam.regparam) - SYMBOL_CLASS (sym) = LOC_REGISTER; - else - SYMBOL_CLASS (sym) = LOC_LOCAL; - if (dn_bufp->dfparam.copyparam) - { - SYMBOL_VALUE (sym) = dn_bufp->dfparam.location; -#ifdef HPREAD_ADJUST_STACK_ADDRESS - SYMBOL_VALUE (sym) - += HPREAD_ADJUST_STACK_ADDRESS (CURRENT_FUNCTION_VALUE (objfile)); -#endif - } - else - SYMBOL_VALUE (sym) = dn_bufp->dfparam.location; - SYMBOL_TYPE (sym) = hpread_type_lookup (dn_bufp->dfparam.type, objfile); - add_symbol_to_list (sym, &local_symbols); - break; - case DNTT_TYPE_SVAR: - /* Static variables. */ - SYMBOL_CLASS (sym) = LOC_STATIC; - SYMBOL_VALUE_ADDRESS (sym) = dn_bufp->dsvar.location; - SYMBOL_TYPE (sym) = hpread_type_lookup (dn_bufp->dsvar.type, objfile); - if (dn_bufp->dsvar.global) - add_symbol_to_list (sym, &global_symbols); - else if (WITHIN_FUNCTION (objfile)) - add_symbol_to_list (sym, &local_symbols); - else - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_DVAR: - /* Dynamic variables. */ - if (dn_bufp->ddvar.regvar) - SYMBOL_CLASS (sym) = LOC_REGISTER; - else - SYMBOL_CLASS (sym) = LOC_LOCAL; - SYMBOL_VALUE (sym) = dn_bufp->ddvar.location; -#ifdef HPREAD_ADJUST_STACK_ADDRESS - SYMBOL_VALUE (sym) - += HPREAD_ADJUST_STACK_ADDRESS (CURRENT_FUNCTION_VALUE (objfile)); -#endif - SYMBOL_TYPE (sym) = hpread_type_lookup (dn_bufp->ddvar.type, objfile); - if (dn_bufp->ddvar.global) - add_symbol_to_list (sym, &global_symbols); - else if (WITHIN_FUNCTION (objfile)) - add_symbol_to_list (sym, &local_symbols); - else - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_CONST: - /* A constant (pascal?). */ - SYMBOL_CLASS (sym) = LOC_CONST; - SYMBOL_VALUE (sym) = dn_bufp->dconst.location; - SYMBOL_TYPE (sym) = hpread_type_lookup (dn_bufp->dconst.type, objfile); - if (dn_bufp->dconst.global) - add_symbol_to_list (sym, &global_symbols); - else if (WITHIN_FUNCTION (objfile)) - add_symbol_to_list (sym, &local_symbols); - else - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_TYPEDEF: - SYMBOL_NAMESPACE (sym) = VAR_NAMESPACE; - SYMBOL_TYPE (sym) = hpread_type_lookup (dn_bufp->dtype.type, objfile); - if (dn_bufp->dtype.global) - add_symbol_to_list (sym, &global_symbols); - else if (WITHIN_FUNCTION (objfile)) - add_symbol_to_list (sym, &local_symbols); - else - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_TAGDEF: - SYMBOL_NAMESPACE (sym) = STRUCT_NAMESPACE; - SYMBOL_TYPE (sym) = hpread_type_lookup (dn_bufp->dtype.type, objfile); - TYPE_NAME (sym->type) = SYMBOL_NAME (sym); - TYPE_TAG_NAME (sym->type) = SYMBOL_NAME (sym); - if (dn_bufp->dtype.global) - add_symbol_to_list (sym, &global_symbols); - else if (WITHIN_FUNCTION (objfile)) - add_symbol_to_list (sym, &local_symbols); - else - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_POINTER: - SYMBOL_TYPE (sym) = lookup_pointer_type (hpread_type_lookup - (dn_bufp->dptr.pointsto, - objfile)); - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_ENUM: - SYMBOL_NAMESPACE (sym) = STRUCT_NAMESPACE; - SYMBOL_TYPE (sym) = hpread_read_enum_type (hp_type, dn_bufp, objfile); - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_MEMENUM: - break; - case DNTT_TYPE_SET: - SYMBOL_TYPE (sym) = hpread_read_set_type (hp_type, dn_bufp, objfile); - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_SUBRANGE: - SYMBOL_TYPE (sym) = hpread_read_subrange_type (hp_type, dn_bufp, - objfile); - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_ARRAY: - SYMBOL_TYPE (sym) = hpread_read_array_type (hp_type, dn_bufp, objfile); - add_symbol_to_list (sym, &file_symbols); - break; - case DNTT_TYPE_STRUCT: - case DNTT_TYPE_UNION: - SYMBOL_NAMESPACE (sym) = STRUCT_NAMESPACE; - SYMBOL_TYPE (sym) = hpread_read_struct_type (hp_type, dn_bufp, objfile); - add_symbol_to_list (sym, &file_symbols); - break; - default: - break; - } -} -- cgit v1.1