/* Generic symbol-table support for the BFD library.
   Copyright (C) 1990, 91, 92, 93, 94, 95, 96, 97, 98, 1999
   Free Software Foundation, Inc.
   Written by Cygnus Support.

This file is part of BFD, the Binary File Descriptor library.

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.  */

/*
SECTION
	Symbols

	BFD tries to maintain as much symbol information as it can when
	it moves information from file to file. BFD passes information
	to applications though the <<asymbol>> structure. When the
	application requests the symbol table, BFD reads the table in
	the native form and translates parts of it into the internal
	format. To maintain more than the information passed to
	applications, some targets keep some information ``behind the
	scenes'' in a structure only the particular back end knows
	about. For example, the coff back end keeps the original
	symbol table structure as well as the canonical structure when
	a BFD is read in. On output, the coff back end can reconstruct
	the output symbol table so that no information is lost, even
	information unique to coff which BFD doesn't know or
	understand. If a coff symbol table were read, but were written
	through an a.out back end, all the coff specific information
	would be lost. The symbol table of a BFD
	is not necessarily read in until a canonicalize request is
	made. Then the BFD back end fills in a table provided by the
	application with pointers to the canonical information.  To
	output symbols, the application provides BFD with a table of
	pointers to pointers to <<asymbol>>s. This allows applications
	like the linker to output a symbol as it was read, since the ``behind
	the scenes'' information will be still available.
@menu
@* Reading Symbols::
@* Writing Symbols::
@* Mini Symbols::
@* typedef asymbol::
@* symbol handling functions::
@end menu

INODE
Reading Symbols, Writing Symbols, Symbols, Symbols
SUBSECTION
	Reading symbols

	There are two stages to reading a symbol table from a BFD:
	allocating storage, and the actual reading process. This is an
	excerpt from an application which reads the symbol table:

|	  long storage_needed;
|	  asymbol **symbol_table;
|	  long number_of_symbols;
|	  long i;
|
|	  storage_needed = bfd_get_symtab_upper_bound (abfd);
|
|         if (storage_needed < 0)
|           FAIL
|
|	  if (storage_needed == 0) {
|	     return ;
|	  }
|	  symbol_table = (asymbol **) xmalloc (storage_needed);
|	    ...
|	  number_of_symbols =
|	     bfd_canonicalize_symtab (abfd, symbol_table);
|
|         if (number_of_symbols < 0)
|           FAIL
|
|	  for (i = 0; i < number_of_symbols; i++) {
|	     process_symbol (symbol_table[i]);
|	  }

	All storage for the symbols themselves is in an objalloc
	connected to the BFD; it is freed when the BFD is closed.


INODE
Writing Symbols, Mini Symbols, Reading Symbols, Symbols
SUBSECTION
	Writing symbols

	Writing of a symbol table is automatic when a BFD open for
	writing is closed. The application attaches a vector of
	pointers to pointers to symbols to the BFD being written, and
	fills in the symbol count. The close and cleanup code reads
	through the table provided and performs all the necessary
	operations. The BFD output code must always be provided with an
	``owned'' symbol: one which has come from another BFD, or one
	which has been created using <<bfd_make_empty_symbol>>.  Here is an
	example showing the creation of a symbol table with only one element:

|	#include "bfd.h"
|	main()
|	{
|	  bfd *abfd;
|	  asymbol *ptrs[2];
|	  asymbol *new;
|
|	  abfd = bfd_openw("foo","a.out-sunos-big");
|	  bfd_set_format(abfd, bfd_object);
|	  new = bfd_make_empty_symbol(abfd);
|	  new->name = "dummy_symbol";
|	  new->section = bfd_make_section_old_way(abfd, ".text");
|	  new->flags = BSF_GLOBAL;
|	  new->value = 0x12345;
|
|	  ptrs[0] = new;
|	  ptrs[1] = (asymbol *)0;
|
|	  bfd_set_symtab(abfd, ptrs, 1);
|	  bfd_close(abfd);
|	}
|
|	./makesym
|	nm foo
|	00012345 A dummy_symbol

	Many formats cannot represent arbitary symbol information; for
 	instance, the <<a.out>> object format does not allow an
	arbitary number of sections. A symbol pointing to a section
	which is not one  of <<.text>>, <<.data>> or <<.bss>> cannot
	be described.

INODE
Mini Symbols, typedef asymbol, Writing Symbols, Symbols
SUBSECTION
	Mini Symbols

	Mini symbols provide read-only access to the symbol table.
	They use less memory space, but require more time to access.
	They can be useful for tools like nm or objdump, which may
	have to handle symbol tables of extremely large executables.

	The <<bfd_read_minisymbols>> function will read the symbols
	into memory in an internal form.  It will return a <<void *>>
	pointer to a block of memory, a symbol count, and the size of
	each symbol.  The pointer is allocated using <<malloc>>, and
	should be freed by the caller when it is no longer needed.

	The function <<bfd_minisymbol_to_symbol>> will take a pointer
	to a minisymbol, and a pointer to a structure returned by
	<<bfd_make_empty_symbol>>, and return a <<asymbol>> structure.
	The return value may or may not be the same as the value from
	<<bfd_make_empty_symbol>> which was passed in.

*/



/*
DOCDD
INODE
typedef asymbol, symbol handling functions, Mini Symbols, Symbols

*/
/*
SUBSECTION
	typedef asymbol

	An <<asymbol>> has the form:

*/

/*
CODE_FRAGMENT

.
.typedef struct symbol_cache_entry
.{
.	{* A pointer to the BFD which owns the symbol. This information
.	   is necessary so that a back end can work out what additional
.   	   information (invisible to the application writer) is carried
.	   with the symbol.
.
.	   This field is *almost* redundant, since you can use section->owner
.	   instead, except that some symbols point to the global sections
.	   bfd_{abs,com,und}_section.  This could be fixed by making
.	   these globals be per-bfd (or per-target-flavor).  FIXME. *}
.
.  struct _bfd *the_bfd; {* Use bfd_asymbol_bfd(sym) to access this field. *}
.
.	{* The text of the symbol. The name is left alone, and not copied; the
.	   application may not alter it. *}
.  CONST char *name;
.
.	{* The value of the symbol.  This really should be a union of a
.          numeric value with a pointer, since some flags indicate that
.          a pointer to another symbol is stored here.  *}
.  symvalue value;
.
.	{* Attributes of a symbol: *}
.
.#define BSF_NO_FLAGS    0x00
.
.	{* The symbol has local scope; <<static>> in <<C>>. The value
. 	   is the offset into the section of the data. *}
.#define BSF_LOCAL	0x01
.
.	{* The symbol has global scope; initialized data in <<C>>. The
.	   value is the offset into the section of the data. *}
.#define BSF_GLOBAL	0x02
.
.	{* The symbol has global scope and is exported. The value is
.	   the offset into the section of the data. *}
.#define BSF_EXPORT	BSF_GLOBAL {* no real difference *}
.
.	{* A normal C symbol would be one of:
.	   <<BSF_LOCAL>>, <<BSF_FORT_COMM>>,  <<BSF_UNDEFINED>> or
.	   <<BSF_GLOBAL>> *}
.
.	{* The symbol is a debugging record. The value has an arbitary
.	   meaning, unless BSF_DEBUGGING_RELOC is also set.  *}
.#define BSF_DEBUGGING	0x08
.
.	{* The symbol denotes a function entry point.  Used in ELF,
.	   perhaps others someday.  *}
.#define BSF_FUNCTION    0x10
.
.	{* Used by the linker. *}
.#define BSF_KEEP        0x20
.#define BSF_KEEP_G      0x40
.
.	{* A weak global symbol, overridable without warnings by
.	   a regular global symbol of the same name.  *}
.#define BSF_WEAK        0x80
.
.       {* This symbol was created to point to a section, e.g. ELF's
.	   STT_SECTION symbols.  *}
.#define BSF_SECTION_SYM 0x100
.
.	{* The symbol used to be a common symbol, but now it is
.	   allocated. *}
.#define BSF_OLD_COMMON  0x200
.
.	{* The default value for common data. *}
.#define BFD_FORT_COMM_DEFAULT_VALUE 0
.
.	{* In some files the type of a symbol sometimes alters its
.	   location in an output file - ie in coff a <<ISFCN>> symbol
.	   which is also <<C_EXT>> symbol appears where it was
.	   declared and not at the end of a section.  This bit is set
.  	   by the target BFD part to convey this information. *}
.
.#define BSF_NOT_AT_END    0x400
.
.	{* Signal that the symbol is the label of constructor section. *}
.#define BSF_CONSTRUCTOR   0x800
.
.	{* Signal that the symbol is a warning symbol.  The name is a
.	   warning.  The name of the next symbol is the one to warn about;
.	   if a reference is made to a symbol with the same name as the next
.	   symbol, a warning is issued by the linker. *}
.#define BSF_WARNING       0x1000
.
.	{* Signal that the symbol is indirect.  This symbol is an indirect
.	   pointer to the symbol with the same name as the next symbol. *}
.#define BSF_INDIRECT      0x2000
.
.	{* BSF_FILE marks symbols that contain a file name.  This is used
.	   for ELF STT_FILE symbols.  *}
.#define BSF_FILE          0x4000
.
.	{* Symbol is from dynamic linking information.  *}
.#define BSF_DYNAMIC	   0x8000
.
.       {* The symbol denotes a data object.  Used in ELF, and perhaps
.          others someday.  *}
.#define BSF_OBJECT	   0x10000
.
.       {* This symbol is a debugging symbol.  The value is the offset
.          into the section of the data.  BSF_DEBUGGING should be set
.          as well.  *}
.#define BSF_DEBUGGING_RELOC 0x20000
.
.  flagword flags;
.
.	{* A pointer to the section to which this symbol is
.	   relative.  This will always be non NULL, there are special
.          sections for undefined and absolute symbols.  *}
.  struct sec *section;
.
.	{* Back end special data.  *}
.  union
.    {
.      PTR p;
.      bfd_vma i;
.    } udata;
.
.} asymbol;
*/

#include "bfd.h"
#include "sysdep.h"
#include "libbfd.h"
#include "bfdlink.h"
#include "aout/stab_gnu.h"

static char coff_section_type PARAMS ((const char *));

/*
DOCDD
INODE
symbol handling functions,  , typedef asymbol, Symbols
SUBSECTION
	Symbol handling functions
*/

/*
FUNCTION
	bfd_get_symtab_upper_bound

DESCRIPTION
	Return the number of bytes required to store a vector of pointers
	to <<asymbols>> for all the symbols in the BFD @var{abfd},
	including a terminal NULL pointer. If there are no symbols in
	the BFD, then return 0.  If an error occurs, return -1.

.#define bfd_get_symtab_upper_bound(abfd) \
.     BFD_SEND (abfd, _bfd_get_symtab_upper_bound, (abfd))

*/

/*
FUNCTION
	bfd_is_local_label

SYNOPSIS
        boolean bfd_is_local_label(bfd *abfd, asymbol *sym);

DESCRIPTION
	Return true if the given symbol @var{sym} in the BFD @var{abfd} is
	a compiler generated local label, else return false.
*/

boolean
bfd_is_local_label (abfd, sym)
     bfd *abfd;
     asymbol *sym;
{
  if ((sym->flags & (BSF_GLOBAL | BSF_WEAK)) != 0)
    return false;
  if (sym->name == NULL)
    return false;
  return bfd_is_local_label_name (abfd, sym->name);
}

/*
FUNCTION
	bfd_is_local_label_name

SYNOPSIS
        boolean bfd_is_local_label_name(bfd *abfd, const char *name);

DESCRIPTION
	Return true if a symbol with the name @var{name} in the BFD
	@var{abfd} is a compiler generated local label, else return
	false.  This just checks whether the name has the form of a
	local label.

.#define bfd_is_local_label_name(abfd, name) \
.     BFD_SEND (abfd, _bfd_is_local_label_name, (abfd, name))
*/

/*
FUNCTION
	bfd_canonicalize_symtab

DESCRIPTION
	Read the symbols from the BFD @var{abfd}, and fills in
	the vector @var{location} with pointers to the symbols and
	a trailing NULL.
	Return the actual number of symbol pointers, not
	including the NULL.


.#define bfd_canonicalize_symtab(abfd, location) \
.     BFD_SEND (abfd, _bfd_canonicalize_symtab,\
.                  (abfd, location))

*/


/*
FUNCTION
	bfd_set_symtab

SYNOPSIS
	boolean bfd_set_symtab (bfd *abfd, asymbol **location, unsigned int count);

DESCRIPTION
	Arrange that when the output BFD @var{abfd} is closed,
	the table @var{location} of @var{count} pointers to symbols
	will be written.
*/

boolean
bfd_set_symtab (abfd, location, symcount)
     bfd *abfd;
     asymbol **location;
     unsigned int symcount;
{
  if ((abfd->format != bfd_object) || (bfd_read_p (abfd)))
    {
      bfd_set_error (bfd_error_invalid_operation);
      return false;
    }

  bfd_get_outsymbols (abfd) = location;
  bfd_get_symcount (abfd) = symcount;
  return true;
}

/*
FUNCTION
	bfd_print_symbol_vandf

SYNOPSIS
	void bfd_print_symbol_vandf(PTR file, asymbol *symbol);

DESCRIPTION
	Print the value and flags of the @var{symbol} supplied to the
	stream @var{file}.
*/
void
bfd_print_symbol_vandf (arg, symbol)
     PTR arg;
     asymbol *symbol;
{
  FILE *file = (FILE *) arg;
  flagword type = symbol->flags;
  if (symbol->section != (asection *) NULL)
    {
      fprintf_vma (file, symbol->value + symbol->section->vma);
    }
  else
    {
      fprintf_vma (file, symbol->value);
    }

  /* This presumes that a symbol can not be both BSF_DEBUGGING and
     BSF_DYNAMIC, nor more than one of BSF_FUNCTION, BSF_FILE, and
     BSF_OBJECT.  */
  fprintf (file, " %c%c%c%c%c%c%c",
	   ((type & BSF_LOCAL)
	    ? (type & BSF_GLOBAL) ? '!' : 'l'
	    : (type & BSF_GLOBAL) ? 'g' : ' '),
	   (type & BSF_WEAK) ? 'w' : ' ',
	   (type & BSF_CONSTRUCTOR) ? 'C' : ' ',
	   (type & BSF_WARNING) ? 'W' : ' ',
	   (type & BSF_INDIRECT) ? 'I' : ' ',
	   (type & BSF_DEBUGGING) ? 'd' : (type & BSF_DYNAMIC) ? 'D' : ' ',
	   ((type & BSF_FUNCTION)
	    ? 'F'
	    : ((type & BSF_FILE)
	       ? 'f'
	       : ((type & BSF_OBJECT) ? 'O' : ' '))));
}


/*
FUNCTION
	bfd_make_empty_symbol

DESCRIPTION
	Create a new <<asymbol>> structure for the BFD @var{abfd}
	and return a pointer to it.

	This routine is necessary because each back end has private
	information surrounding the <<asymbol>>. Building your own
	<<asymbol>> and pointing to it will not create the private
	information, and will cause problems later on.

.#define bfd_make_empty_symbol(abfd) \
.     BFD_SEND (abfd, _bfd_make_empty_symbol, (abfd))
*/

/*
FUNCTION
	bfd_make_debug_symbol

DESCRIPTION
	Create a new <<asymbol>> structure for the BFD @var{abfd},
	to be used as a debugging symbol.  Further details of its use have
	yet to be worked out.

.#define bfd_make_debug_symbol(abfd,ptr,size) \
.        BFD_SEND (abfd, _bfd_make_debug_symbol, (abfd, ptr, size))
*/

struct section_to_type
{
  CONST char *section;
  char type;
};

/* Map section names to POSIX/BSD single-character symbol types.
   This table is probably incomplete.  It is sorted for convenience of
   adding entries.  Since it is so short, a linear search is used.  */
static CONST struct section_to_type stt[] =
{
  {"*DEBUG*", 'N'},
  {".bss", 'b'},
  {"zerovars", 'b'},		/* MRI .bss */
  {".data", 'd'},
  {"vars", 'd'},		/* MRI .data */
  {".rdata", 'r'},		/* Read only data.  */
  {".rodata", 'r'},		/* Read only data.  */
  {".sbss", 's'},		/* Small BSS (uninitialized data).  */
  {".scommon", 'c'},		/* Small common.  */
  {".sdata", 'g'},		/* Small initialized data.  */
  {".text", 't'},
  {"code", 't'},		/* MRI .text */
  {".drectve", 'i'},            /* MSVC's .drective section */
  {".idata", 'i'},              /* MSVC's .idata (import) section */
  {".edata", 'e'},              /* MSVC's .edata (export) section */
  {".pdata", 'p'},              /* MSVC's .pdata (stack unwind) section */
  {".debug", 'N'},              /* MSVC's .debug (non-standard debug syms) */
  {0, 0}
};

/* Return the single-character symbol type corresponding to
   section S, or '?' for an unknown COFF section.  

   Check for any leading string which matches, so .text5 returns
   't' as well as .text */

static char
coff_section_type (s)
     const char *s;
{
  CONST struct section_to_type *t;

  for (t = &stt[0]; t->section; t++) 
    if (!strncmp (s, t->section, strlen (t->section)))
      return t->type;

  return '?';
}

#ifndef islower
#define islower(c) ((c) >= 'a' && (c) <= 'z')
#endif
#ifndef toupper
#define toupper(c) (islower(c) ? ((c) & ~0x20) : (c))
#endif

/*
FUNCTION
	bfd_decode_symclass

DESCRIPTION
	Return a character corresponding to the symbol
	class of @var{symbol}, or '?' for an unknown class.

SYNOPSIS
	int bfd_decode_symclass(asymbol *symbol);
*/
int
bfd_decode_symclass (symbol)
     asymbol *symbol;
{
  char c;

  if (bfd_is_com_section (symbol->section))
    return 'C';
  if (bfd_is_und_section (symbol->section))
    {
      if (symbol->flags & BSF_WEAK)
	{
	  /* If weak, determine if it's specifically an object
	     or non-object weak.  */
	  if (symbol->flags & BSF_OBJECT)
	    return 'v';
	  else
	    return 'w';
	}
      else
	return 'U';
    }
  if (bfd_is_ind_section (symbol->section))
    return 'I';
  if (symbol->flags & BSF_WEAK)
    {
      /* If weak, determine if it's specifically an object
	 or non-object weak.  */
      if (symbol->flags & BSF_OBJECT)
	return 'V';
      else
	return 'W';
    }
  if (!(symbol->flags & (BSF_GLOBAL | BSF_LOCAL)))
    return '?';

  if (bfd_is_abs_section (symbol->section))
    c = 'a';
  else if (symbol->section)
    c = coff_section_type (symbol->section->name);
  else
    return '?';
  if (symbol->flags & BSF_GLOBAL)
    c = toupper (c);
  return c;

  /* We don't have to handle these cases just yet, but we will soon:
     N_SETV: 'v';
     N_SETA: 'l';
     N_SETT: 'x';
     N_SETD: 'z';
     N_SETB: 's';
     N_INDR: 'i';
     */
}

/*
FUNCTION
	bfd_is_undefined_symclass 

DESCRIPTION
	Returns non-zero if the class symbol returned by
	bfd_decode_symclass represents an undefined symbol.
	Returns zero otherwise.

SYNOPSIS
	boolean bfd_is_undefined_symclass (int symclass);
*/

boolean
bfd_is_undefined_symclass (symclass)
     int symclass;
{
  return symclass == 'U' || symclass == 'w' || symclass == 'v';
}

/*
FUNCTION
	bfd_symbol_info

DESCRIPTION
	Fill in the basic info about symbol that nm needs.
	Additional info may be added by the back-ends after
	calling this function.

SYNOPSIS
	void bfd_symbol_info(asymbol *symbol, symbol_info *ret);
*/

void
bfd_symbol_info (symbol, ret)
     asymbol *symbol;
     symbol_info *ret;
{
  ret->type = bfd_decode_symclass (symbol);
  
  if (bfd_is_undefined_symclass (ret->type))
    ret->value = 0;
  else
    ret->value = symbol->value + symbol->section->vma;
  
  ret->name = symbol->name;
}

/*
FUNCTION
	bfd_copy_private_symbol_data

SYNOPSIS
	boolean bfd_copy_private_symbol_data(bfd *ibfd, asymbol *isym, bfd *obfd, asymbol *osym);

DESCRIPTION
	Copy private symbol information from @var{isym} in the BFD
	@var{ibfd} to the symbol @var{osym} in the BFD @var{obfd}.
	Return <<true>> on success, <<false>> on error.  Possible error
	returns are:

	o <<bfd_error_no_memory>> -
	Not enough memory exists to create private data for @var{osec}.

.#define bfd_copy_private_symbol_data(ibfd, isymbol, obfd, osymbol) \
.     BFD_SEND (obfd, _bfd_copy_private_symbol_data, \
.		(ibfd, isymbol, obfd, osymbol))

*/

/* The generic version of the function which returns mini symbols.
   This is used when the backend does not provide a more efficient
   version.  It just uses BFD asymbol structures as mini symbols.  */

long
_bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep)
     bfd *abfd;
     boolean dynamic;
     PTR *minisymsp;
     unsigned int *sizep;
{
  long storage;
  asymbol **syms = NULL;
  long symcount;

  if (dynamic)
    storage = bfd_get_dynamic_symtab_upper_bound (abfd);
  else
    storage = bfd_get_symtab_upper_bound (abfd);
  if (storage < 0)
    goto error_return;

  syms = (asymbol **) bfd_malloc ((size_t) storage);
  if (syms == NULL)
    goto error_return;

  if (dynamic)
    symcount = bfd_canonicalize_dynamic_symtab (abfd, syms);
  else
    symcount = bfd_canonicalize_symtab (abfd, syms);
  if (symcount < 0)
    goto error_return;

  *minisymsp = (PTR) syms;
  *sizep = sizeof (asymbol *);
  return symcount;

 error_return:
  if (syms != NULL)
    free (syms);
  return -1;
}

/* The generic version of the function which converts a minisymbol to
   an asymbol.  We don't worry about the sym argument we are passed;
   we just return the asymbol the minisymbol points to.  */

/*ARGSUSED*/
asymbol *
_bfd_generic_minisymbol_to_symbol (abfd, dynamic, minisym, sym)
     bfd *abfd ATTRIBUTE_UNUSED;
     boolean dynamic ATTRIBUTE_UNUSED;
     const PTR minisym;
     asymbol *sym ATTRIBUTE_UNUSED;
{
  return *(asymbol **) minisym;
}

/* Look through stabs debugging information in .stab and .stabstr
   sections to find the source file and line closest to a desired
   location.  This is used by COFF and ELF targets.  It sets *pfound
   to true if it finds some information.  The *pinfo field is used to
   pass cached information in and out of this routine; this first time
   the routine is called for a BFD, *pinfo should be NULL.  The value
   placed in *pinfo should be saved with the BFD, and passed back each
   time this function is called.  */

/* We use a cache by default.  */

#define ENABLE_CACHING

/* We keep an array of indexentry structures to record where in the
   stabs section we should look to find line number information for a
   particular address.  */

struct indexentry
{
  bfd_vma val;
  bfd_byte *stab;
  bfd_byte *str;
  char *directory_name;
  char *file_name;
  char *function_name;
};

/* Compare two indexentry structures.  This is called via qsort.  */

static int
cmpindexentry (a, b)
     const PTR *a;
     const PTR *b;
{
  const struct indexentry *contestantA = (const struct indexentry *) a;
  const struct indexentry *contestantB = (const struct indexentry *) b;

  if (contestantA->val < contestantB->val)
    return -1;
  else if (contestantA->val > contestantB->val)
    return 1;
  else
    return 0;
}

/* A pointer to this structure is stored in *pinfo.  */

struct stab_find_info
{
  /* The .stab section.  */
  asection *stabsec;
  /* The .stabstr section.  */
  asection *strsec;
  /* The contents of the .stab section.  */
  bfd_byte *stabs;
  /* The contents of the .stabstr section.  */
  bfd_byte *strs;

  /* A table that indexes stabs by memory address.  */
  struct indexentry *indextable;
  /* The number of entries in indextable.  */
  int indextablesize;

#ifdef ENABLE_CACHING
  /* Cached values to restart quickly.  */
  struct indexentry *cached_indexentry;
  bfd_vma cached_offset;
  bfd_byte *cached_stab;
  char *cached_file_name;
#endif

  /* Saved ptr to malloc'ed filename.  */
  char *filename;
};

boolean
_bfd_stab_section_find_nearest_line (abfd, symbols, section, offset, pfound,
				     pfilename, pfnname, pline, pinfo)
     bfd *abfd;
     asymbol **symbols;
     asection *section;
     bfd_vma offset;
     boolean *pfound;
     const char **pfilename;
     const char **pfnname;
     unsigned int *pline;
     PTR *pinfo;
{
  struct stab_find_info *info;
  bfd_size_type stabsize, strsize;
  bfd_byte *stab, *str;
  bfd_byte *last_stab = NULL;
  bfd_size_type stroff;
  struct indexentry *indexentry;
  char *directory_name, *file_name;
  int saw_fun;

  *pfound = false;
  *pfilename = bfd_get_filename (abfd);
  *pfnname = NULL;
  *pline = 0;

  /* Stabs entries use a 12 byte format:
       4 byte string table index
       1 byte stab type
       1 byte stab other field
       2 byte stab desc field
       4 byte stab value
     FIXME: This will have to change for a 64 bit object format.

     The stabs symbols are divided into compilation units.  For the
     first entry in each unit, the type of 0, the value is the length
     of the string table for this unit, and the desc field is the
     number of stabs symbols for this unit.  */

#define STRDXOFF (0)
#define TYPEOFF (4)
#define OTHEROFF (5)
#define DESCOFF (6)
#define VALOFF (8)
#define STABSIZE (12)

  info = (struct stab_find_info *) *pinfo;
  if (info != NULL)
    {
      if (info->stabsec == NULL || info->strsec == NULL)
	{
	  /* No stabs debugging information.  */
	  return true;
	}

      stabsize = info->stabsec->_raw_size;
      strsize = info->strsec->_raw_size;
    }
  else
    {
      long reloc_size, reloc_count;
      arelent **reloc_vector;
      int i;
      char *name;
      char *file_name;
      char *directory_name;
      char *function_name;

      info = (struct stab_find_info *) bfd_zalloc (abfd, sizeof *info);
      if (info == NULL)
	return false;

      /* FIXME: When using the linker --split-by-file or
	 --split-by-reloc options, it is possible for the .stab and
	 .stabstr sections to be split.  We should handle that.  */

      info->stabsec = bfd_get_section_by_name (abfd, ".stab");
      info->strsec = bfd_get_section_by_name (abfd, ".stabstr");

      if (info->stabsec == NULL || info->strsec == NULL)
	{
	  /* No stabs debugging information.  Set *pinfo so that we
             can return quickly in the info != NULL case above.  */
	  *pinfo = (PTR) info;
	  return true;
	}

      stabsize = info->stabsec->_raw_size;
      strsize = info->strsec->_raw_size;

      info->stabs = (bfd_byte *) bfd_alloc (abfd, stabsize);
      info->strs = (bfd_byte *) bfd_alloc (abfd, strsize);
      if (info->stabs == NULL || info->strs == NULL)
	return false;

      if (! bfd_get_section_contents (abfd, info->stabsec, info->stabs, 0,
				      stabsize)
	  || ! bfd_get_section_contents (abfd, info->strsec, info->strs, 0,
					 strsize))
	return false;

      /* If this is a relocateable object file, we have to relocate
	 the entries in .stab.  This should always be simple 32 bit
	 relocations against symbols defined in this object file, so
	 this should be no big deal.  */
      reloc_size = bfd_get_reloc_upper_bound (abfd, info->stabsec);
      if (reloc_size < 0)
	return false;
      reloc_vector = (arelent **) bfd_malloc (reloc_size);
      if (reloc_vector == NULL && reloc_size != 0)
	return false;
      reloc_count = bfd_canonicalize_reloc (abfd, info->stabsec, reloc_vector,
					    symbols);
      if (reloc_count < 0)
	{
	  if (reloc_vector != NULL)
	    free (reloc_vector);
	  return false;
	}
      if (reloc_count > 0)
	{
	  arelent **pr;

	  for (pr = reloc_vector; *pr != NULL; pr++)
	    {
	      arelent *r;
	      unsigned long val;
	      asymbol *sym;

	      r = *pr;
	      if (r->howto->rightshift != 0
		  || r->howto->size != 2
		  || r->howto->bitsize != 32
		  || r->howto->pc_relative
		  || r->howto->bitpos != 0
		  || r->howto->dst_mask != 0xffffffff)
		{
		  (*_bfd_error_handler)
		    (_("Unsupported .stab relocation"));
		  bfd_set_error (bfd_error_invalid_operation);
		  if (reloc_vector != NULL)
		    free (reloc_vector);
		  return false;
		}

	      val = bfd_get_32 (abfd, info->stabs + r->address);
	      val &= r->howto->src_mask;
	      sym = *r->sym_ptr_ptr;
	      val += sym->value + sym->section->vma + r->addend;
	      bfd_put_32 (abfd, val, info->stabs + r->address);
	    }
	}

      if (reloc_vector != NULL)
	free (reloc_vector);

      /* First time through this function, build a table matching
	 function VM addresses to stabs, then sort based on starting
	 VM address.  Do this in two passes: once to count how many
	 table entries we'll need, and a second to actually build the
	 table.  */

      info->indextablesize = 0;
      saw_fun = 1;
      for (stab = info->stabs; stab < info->stabs + stabsize; stab += STABSIZE)
	{
	  if (stab[TYPEOFF] == N_SO)
	    {
	      /* N_SO with null name indicates EOF */
	      if (bfd_get_32 (abfd, stab + STRDXOFF) == 0)
		continue;

	      /* if we did not see a function def, leave space for one. */
	      if (saw_fun == 0)
		++info->indextablesize;

	      saw_fun = 0;

	      /* two N_SO's in a row is a filename and directory. Skip */
	      if (stab + STABSIZE < info->stabs + stabsize
		  && *(stab + STABSIZE + TYPEOFF) == N_SO)
		{
		  stab += STABSIZE;
		}
	    }
	  else if (stab[TYPEOFF] == N_FUN)
	    {
	      saw_fun = 1;
	      ++info->indextablesize;
	    }
	}

      if (saw_fun == 0)
	++info->indextablesize;
      
      if (info->indextablesize == 0)
	return true;
      ++info->indextablesize;

      info->indextable = ((struct indexentry *)
			  bfd_alloc (abfd,
				     (sizeof (struct indexentry)
				      * info->indextablesize)));
      if (info->indextable == NULL)
	return false;

      file_name = NULL;
      directory_name = NULL;
      saw_fun = 1;

      for (i = 0, stroff = 0, stab = info->stabs, str = info->strs;
	   i < info->indextablesize && stab < info->stabs + stabsize;
	   stab += STABSIZE)
	{
	  switch (stab[TYPEOFF])
	    {
	    case 0:
	      /* This is the first entry in a compilation unit.  */
	      if ((bfd_size_type) ((info->strs + strsize) - str) < stroff)
		break;
	      str += stroff;
	      stroff = bfd_get_32 (abfd, stab + VALOFF);
	      break;

	    case N_SO:
	      /* The main file name.  */

	      /* The following code creates a new indextable entry with
	         a NULL function name if there were no N_FUNs in a file.
	         Note that a N_SO without a file name is an EOF and
	         there could be 2 N_SO following it with the new filename 
	         and directory. */
	      if (saw_fun == 0)
		{
		  info->indextable[i].val = bfd_get_32 (abfd, last_stab + VALOFF);
		  info->indextable[i].stab = last_stab;
		  info->indextable[i].str = str;
		  info->indextable[i].directory_name = directory_name;
		  info->indextable[i].file_name = file_name;
		  info->indextable[i].function_name = NULL;
		  ++i;
		}
	      saw_fun = 0;
	      
	      file_name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF);
	      if (*file_name == '\0')
		{
		  directory_name = NULL;
		  file_name = NULL;
		  saw_fun = 1;
		}
	      else
		{
		  last_stab = stab;
		  if (stab + STABSIZE >= info->stabs + stabsize
		      || *(stab + STABSIZE + TYPEOFF) != N_SO)
		    {
		      directory_name = NULL;
		    }
		  else
		    {
		      /* Two consecutive N_SOs are a directory and a
			 file name.  */
		      stab += STABSIZE;
		      directory_name = file_name;
		      file_name = ((char *) str
				   + bfd_get_32 (abfd, stab + STRDXOFF));
		    }
		}
	      break;

	    case N_SOL:
	      /* The name of an include file.  */
	      file_name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF);
	      break;

	    case N_FUN:
	      /* A function name.  */
	      saw_fun = 1;
	      name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF);

	      if (*name == '\0')
		name = NULL;

	      function_name = name;

	      if (name == NULL)
		continue;

	      info->indextable[i].val = bfd_get_32 (abfd, stab + VALOFF);
	      info->indextable[i].stab = stab;
	      info->indextable[i].str = str;
	      info->indextable[i].directory_name = directory_name;
	      info->indextable[i].file_name = file_name;
	      info->indextable[i].function_name = function_name;
	      ++i;
	      break;
	    }
	}

      if (saw_fun == 0)
	{
	  info->indextable[i].val = bfd_get_32 (abfd, last_stab + VALOFF);
	  info->indextable[i].stab = last_stab;
	  info->indextable[i].str = str;
	  info->indextable[i].directory_name = directory_name;
	  info->indextable[i].file_name = file_name;
	  info->indextable[i].function_name = NULL;
	  ++i;
	}

      info->indextable[i].val = (bfd_vma) -1;
      info->indextable[i].stab = info->stabs + stabsize;
      info->indextable[i].str = str;
      info->indextable[i].directory_name = NULL;
      info->indextable[i].file_name = NULL;
      info->indextable[i].function_name = NULL;
      ++i;

      info->indextablesize = i;
      qsort (info->indextable, i, sizeof (struct indexentry), cmpindexentry);

      *pinfo = (PTR) info;
    }

  /* We are passed a section relative offset.  The offsets in the
     stabs information are absolute.  */
  offset += bfd_get_section_vma (abfd, section);

#ifdef ENABLE_CACHING
  if (info->cached_indexentry != NULL
      && offset >= info->cached_offset
      && offset < (info->cached_indexentry + 1)->val)
    {
      stab = info->cached_stab;
      indexentry = info->cached_indexentry;
      file_name = info->cached_file_name;
    }
  else
#endif
    {
      /* Cache non-existant or invalid.  Do binary search on
         indextable.  */

      long low, high;
      long mid = -1;

      indexentry = NULL;

      low = 0;
      high = info->indextablesize - 1;
      while (low != high)
	{
	  mid = (high + low) / 2;
	  if (offset >= info->indextable[mid].val
	      && offset < info->indextable[mid + 1].val)
	    {
	      indexentry = &info->indextable[mid];
	      break;
	    }

	  if (info->indextable[mid].val > offset)
	    high = mid;
	  else
	    low = mid + 1;
	}

      if (indexentry == NULL)
	return true;

      stab = indexentry->stab + STABSIZE;
      file_name = indexentry->file_name;
    }

  directory_name = indexentry->directory_name;
  str = indexentry->str;

  for (; stab < (indexentry+1)->stab; stab += STABSIZE)
    {
      boolean done;
      bfd_vma val;

      done = false;

      switch (stab[TYPEOFF])
	{
	case N_SOL:
	  /* The name of an include file.  */
	  val = bfd_get_32 (abfd, stab + VALOFF);
	  if (val <= offset)
	    {
	      file_name = (char *) str + bfd_get_32 (abfd, stab + STRDXOFF);
	      *pline = 0;
	    }
	  break;

	case N_SLINE:
	case N_DSLINE:
	case N_BSLINE:
	  /* A line number.  The value is relative to the start of the
             current function.  */
	  val = indexentry->val + bfd_get_32 (abfd, stab + VALOFF);
	  if (val <= offset)
	    {
	      *pline = bfd_get_16 (abfd, stab + DESCOFF);

#ifdef ENABLE_CACHING
	      info->cached_stab = stab;
	      info->cached_offset = val;
	      info->cached_file_name = file_name;
	      info->cached_indexentry = indexentry;
#endif
	    }
	  if (val > offset)
	    done = true;
	  break;

	case N_FUN:
	case N_SO:
	  done = true;
	  break;
	}

      if (done)
	break;
    }

  *pfound = true;

  if (file_name[0] == '/' || directory_name == NULL)
    *pfilename = file_name;
  else
    {
      size_t dirlen;

      dirlen = strlen (directory_name);
      if (info->filename == NULL
	  || strncmp (info->filename, directory_name, dirlen) != 0
	  || strcmp (info->filename + dirlen, file_name) != 0)
	{
	  if (info->filename != NULL)
	    free (info->filename);
	  info->filename = (char *) bfd_malloc (dirlen +
						strlen (file_name)
						+ 1);
	  if (info->filename == NULL)
	    return false;
	  strcpy (info->filename, directory_name);
	  strcpy (info->filename + dirlen, file_name);
	}

      *pfilename = info->filename;
    }

  if (indexentry->function_name != NULL)
    {
      char *s;

      /* This will typically be something like main:F(0,1), so we want
         to clobber the colon.  It's OK to change the name, since the
         string is in our own local storage anyhow.  */

      s = strchr (indexentry->function_name, ':');
      if (s != NULL)
	*s = '\0';

      *pfnname = indexentry->function_name;
    }

  return true;
}
