198944Sobrien/* Handle SVR4 shared libraries for GDB, the GNU Debugger.
2130803Smarcel
3130803Smarcel   Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1998, 1999,
4130803Smarcel   2000, 2001, 2003, 2004
598944Sobrien   Free Software Foundation, Inc.
698944Sobrien
798944Sobrien   This file is part of GDB.
898944Sobrien
998944Sobrien   This program is free software; you can redistribute it and/or modify
1098944Sobrien   it under the terms of the GNU General Public License as published by
1198944Sobrien   the Free Software Foundation; either version 2 of the License, or
1298944Sobrien   (at your option) any later version.
1398944Sobrien
1498944Sobrien   This program is distributed in the hope that it will be useful,
1598944Sobrien   but WITHOUT ANY WARRANTY; without even the implied warranty of
1698944Sobrien   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
1798944Sobrien   GNU General Public License for more details.
1898944Sobrien
1998944Sobrien   You should have received a copy of the GNU General Public License
2098944Sobrien   along with this program; if not, write to the Free Software
2198944Sobrien   Foundation, Inc., 59 Temple Place - Suite 330,
2298944Sobrien   Boston, MA 02111-1307, USA.  */
2398944Sobrien
2498944Sobrien#include "defs.h"
2598944Sobrien
2698944Sobrien#include "elf/external.h"
2798944Sobrien#include "elf/common.h"
2898944Sobrien#include "elf/mips.h"
2998944Sobrien
3098944Sobrien#include "symtab.h"
3198944Sobrien#include "bfd.h"
3298944Sobrien#include "symfile.h"
3398944Sobrien#include "objfiles.h"
3498944Sobrien#include "gdbcore.h"
3598944Sobrien#include "target.h"
3698944Sobrien#include "inferior.h"
3798944Sobrien
3898944Sobrien#include "solist.h"
3998944Sobrien#include "solib-svr4.h"
4098944Sobrien
41130803Smarcel#include "bfd-target.h"
42130803Smarcel#include "exec.h"
43130803Smarcel
4498944Sobrien#ifndef SVR4_FETCH_LINK_MAP_OFFSETS
4598944Sobrien#define SVR4_FETCH_LINK_MAP_OFFSETS() svr4_fetch_link_map_offsets ()
4698944Sobrien#endif
4798944Sobrien
4898944Sobrienstatic struct link_map_offsets *svr4_fetch_link_map_offsets (void);
4998944Sobrienstatic struct link_map_offsets *legacy_fetch_link_map_offsets (void);
50130803Smarcelstatic int svr4_have_link_map_offsets (void);
5198944Sobrien
5298944Sobrien/* fetch_link_map_offsets_gdbarch_data is a handle used to obtain the
5398944Sobrien   architecture specific link map offsets fetching function.  */
5498944Sobrien
5598944Sobrienstatic struct gdbarch_data *fetch_link_map_offsets_gdbarch_data;
5698944Sobrien
5798944Sobrien/* legacy_svr4_fetch_link_map_offsets_hook is a pointer to a function
5898944Sobrien   which is used to fetch link map offsets.  It will only be set
5998944Sobrien   by solib-legacy.c, if at all. */
6098944Sobrien
6198944Sobrienstruct link_map_offsets *(*legacy_svr4_fetch_link_map_offsets_hook)(void) = 0;
6298944Sobrien
6398944Sobrien/* Link map info to include in an allocated so_list entry */
6498944Sobrien
6598944Sobrienstruct lm_info
6698944Sobrien  {
6798944Sobrien    /* Pointer to copy of link map from inferior.  The type is char *
6898944Sobrien       rather than void *, so that we may use byte offsets to find the
6998944Sobrien       various fields without the need for a cast.  */
7098944Sobrien    char *lm;
7198944Sobrien  };
7298944Sobrien
7398944Sobrien/* On SVR4 systems, a list of symbols in the dynamic linker where
7498944Sobrien   GDB can try to place a breakpoint to monitor shared library
7598944Sobrien   events.
7698944Sobrien
7798944Sobrien   If none of these symbols are found, or other errors occur, then
7898944Sobrien   SVR4 systems will fall back to using a symbol as the "startup
7998944Sobrien   mapping complete" breakpoint address.  */
8098944Sobrien
8198944Sobrienstatic char *solib_break_names[] =
8298944Sobrien{
8398944Sobrien  "r_debug_state",
8498944Sobrien  "_r_debug_state",
8598944Sobrien  "_dl_debug_state",
8698944Sobrien  "rtld_db_dlactivity",
8798944Sobrien  "_rtld_debug_state",
88130803Smarcel
89130803Smarcel  /* On the 64-bit PowerPC, the linker symbol with the same name as
90130803Smarcel     the C function points to a function descriptor, not to the entry
91130803Smarcel     point.  The linker symbol whose name is the C function name
92130803Smarcel     prefixed with a '.' points to the function's entry point.  So
93130803Smarcel     when we look through this table, we ignore symbols that point
94130803Smarcel     into the data section (thus skipping the descriptor's symbol),
95130803Smarcel     and eventually try this one, giving us the real entry point
96130803Smarcel     address.  */
97209867Snwhitehorn  ".r_debug_state",
98130803Smarcel  "._dl_debug_state",
99130803Smarcel
10098944Sobrien  NULL
10198944Sobrien};
10298944Sobrien
10398944Sobrien#define BKPT_AT_SYMBOL 1
10498944Sobrien
10598944Sobrien#if defined (BKPT_AT_SYMBOL)
10698944Sobrienstatic char *bkpt_names[] =
10798944Sobrien{
10898944Sobrien#ifdef SOLIB_BKPT_NAME
10998944Sobrien  SOLIB_BKPT_NAME,		/* Prefer configured name if it exists. */
11098944Sobrien#endif
11198944Sobrien  "_start",
112130803Smarcel  "__start",
11398944Sobrien  "main",
11498944Sobrien  NULL
11598944Sobrien};
11698944Sobrien#endif
11798944Sobrien
11898944Sobrienstatic char *main_name_list[] =
11998944Sobrien{
12098944Sobrien  "main_$main",
12198944Sobrien  NULL
12298944Sobrien};
12398944Sobrien
124130803Smarcel/* Macro to extract an address from a solib structure.  When GDB is
125130803Smarcel   configured for some 32-bit targets (e.g. Solaris 2.7 sparc), BFD is
126130803Smarcel   configured to handle 64-bit targets, so CORE_ADDR is 64 bits.  We
127130803Smarcel   have to extract only the significant bits of addresses to get the
128130803Smarcel   right address when accessing the core file BFD.
12998944Sobrien
130130803Smarcel   Assume that the address is unsigned.  */
131130803Smarcel
13298944Sobrien#define SOLIB_EXTRACT_ADDRESS(MEMBER) \
133130803Smarcel	extract_unsigned_integer (&(MEMBER), sizeof (MEMBER))
13498944Sobrien
13598944Sobrien/* local data declarations */
13698944Sobrien
13798944Sobrien/* link map access functions */
13898944Sobrien
13998944Sobrienstatic CORE_ADDR
14098944SobrienLM_ADDR (struct so_list *so)
14198944Sobrien{
14298944Sobrien  struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
14398944Sobrien
14498944Sobrien  return (CORE_ADDR) extract_signed_integer (so->lm_info->lm + lmo->l_addr_offset,
14598944Sobrien					     lmo->l_addr_size);
14698944Sobrien}
14798944Sobrien
14898944Sobrienstatic CORE_ADDR
14998944SobrienLM_NEXT (struct so_list *so)
15098944Sobrien{
15198944Sobrien  struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
15298944Sobrien
153130803Smarcel  /* Assume that the address is unsigned.  */
154130803Smarcel  return extract_unsigned_integer (so->lm_info->lm + lmo->l_next_offset,
155130803Smarcel				   lmo->l_next_size);
15698944Sobrien}
15798944Sobrien
15898944Sobrienstatic CORE_ADDR
15998944SobrienLM_NAME (struct so_list *so)
16098944Sobrien{
16198944Sobrien  struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
16298944Sobrien
163130803Smarcel  /* Assume that the address is unsigned.  */
164130803Smarcel  return extract_unsigned_integer (so->lm_info->lm + lmo->l_name_offset,
165130803Smarcel				   lmo->l_name_size);
16698944Sobrien}
16798944Sobrien
16898944Sobrienstatic int
16998944SobrienIGNORE_FIRST_LINK_MAP_ENTRY (struct so_list *so)
17098944Sobrien{
17198944Sobrien  struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
17298944Sobrien
173130803Smarcel  /* Assume that the address is unsigned.  */
174130803Smarcel  return extract_unsigned_integer (so->lm_info->lm + lmo->l_prev_offset,
175130803Smarcel				   lmo->l_prev_size) == 0;
17698944Sobrien}
17798944Sobrien
17898944Sobrienstatic CORE_ADDR debug_base;	/* Base of dynamic linker structures */
17998944Sobrienstatic CORE_ADDR breakpoint_addr;	/* Address where end bkpt is set */
18098944Sobrien
18198944Sobrien/* Local function prototypes */
18298944Sobrien
18398944Sobrienstatic int match_main (char *);
18498944Sobrien
185130803Smarcelstatic CORE_ADDR bfd_lookup_symbol (bfd *, char *, flagword);
18698944Sobrien
18798944Sobrien/*
18898944Sobrien
18998944Sobrien   LOCAL FUNCTION
19098944Sobrien
19198944Sobrien   bfd_lookup_symbol -- lookup the value for a specific symbol
19298944Sobrien
19398944Sobrien   SYNOPSIS
19498944Sobrien
195130803Smarcel   CORE_ADDR bfd_lookup_symbol (bfd *abfd, char *symname, flagword sect_flags)
19698944Sobrien
19798944Sobrien   DESCRIPTION
19898944Sobrien
19998944Sobrien   An expensive way to lookup the value of a single symbol for
20098944Sobrien   bfd's that are only temporary anyway.  This is used by the
20198944Sobrien   shared library support to find the address of the debugger
20298944Sobrien   interface structures in the shared library.
20398944Sobrien
204130803Smarcel   If SECT_FLAGS is non-zero, only match symbols in sections whose
205130803Smarcel   flags include all those in SECT_FLAGS.
206130803Smarcel
20798944Sobrien   Note that 0 is specifically allowed as an error return (no
20898944Sobrien   such symbol).
20998944Sobrien */
21098944Sobrien
21198944Sobrienstatic CORE_ADDR
212130803Smarcelbfd_lookup_symbol (bfd *abfd, char *symname, flagword sect_flags)
21398944Sobrien{
21498944Sobrien  long storage_needed;
21598944Sobrien  asymbol *sym;
21698944Sobrien  asymbol **symbol_table;
21798944Sobrien  unsigned int number_of_symbols;
21898944Sobrien  unsigned int i;
21998944Sobrien  struct cleanup *back_to;
22098944Sobrien  CORE_ADDR symaddr = 0;
22198944Sobrien
22298944Sobrien  storage_needed = bfd_get_symtab_upper_bound (abfd);
22398944Sobrien
22498944Sobrien  if (storage_needed > 0)
22598944Sobrien    {
22698944Sobrien      symbol_table = (asymbol **) xmalloc (storage_needed);
227130803Smarcel      back_to = make_cleanup (xfree, symbol_table);
22898944Sobrien      number_of_symbols = bfd_canonicalize_symtab (abfd, symbol_table);
22998944Sobrien
23098944Sobrien      for (i = 0; i < number_of_symbols; i++)
23198944Sobrien	{
23298944Sobrien	  sym = *symbol_table++;
233130803Smarcel	  if (strcmp (sym->name, symname) == 0
234130803Smarcel              && (sym->section->flags & sect_flags) == sect_flags)
23598944Sobrien	    {
23698944Sobrien	      /* Bfd symbols are section relative. */
23798944Sobrien	      symaddr = sym->value + sym->section->vma;
23898944Sobrien	      break;
23998944Sobrien	    }
24098944Sobrien	}
24198944Sobrien      do_cleanups (back_to);
24298944Sobrien    }
24398944Sobrien
24498944Sobrien  if (symaddr)
24598944Sobrien    return symaddr;
24698944Sobrien
24798944Sobrien  /* On FreeBSD, the dynamic linker is stripped by default.  So we'll
24898944Sobrien     have to check the dynamic string table too.  */
24998944Sobrien
25098944Sobrien  storage_needed = bfd_get_dynamic_symtab_upper_bound (abfd);
25198944Sobrien
25298944Sobrien  if (storage_needed > 0)
25398944Sobrien    {
25498944Sobrien      symbol_table = (asymbol **) xmalloc (storage_needed);
255130803Smarcel      back_to = make_cleanup (xfree, symbol_table);
25698944Sobrien      number_of_symbols = bfd_canonicalize_dynamic_symtab (abfd, symbol_table);
25798944Sobrien
25898944Sobrien      for (i = 0; i < number_of_symbols; i++)
25998944Sobrien	{
26098944Sobrien	  sym = *symbol_table++;
261130803Smarcel
262130803Smarcel	  if (strcmp (sym->name, symname) == 0
263130803Smarcel              && (sym->section->flags & sect_flags) == sect_flags)
26498944Sobrien	    {
26598944Sobrien	      /* Bfd symbols are section relative. */
26698944Sobrien	      symaddr = sym->value + sym->section->vma;
26798944Sobrien	      break;
26898944Sobrien	    }
26998944Sobrien	}
27098944Sobrien      do_cleanups (back_to);
27198944Sobrien    }
27298944Sobrien
27398944Sobrien  return symaddr;
27498944Sobrien}
27598944Sobrien
27698944Sobrien#ifdef HANDLE_SVR4_EXEC_EMULATORS
27798944Sobrien
27898944Sobrien/*
27998944Sobrien   Solaris BCP (the part of Solaris which allows it to run SunOS4
28098944Sobrien   a.out files) throws in another wrinkle. Solaris does not fill
28198944Sobrien   in the usual a.out link map structures when running BCP programs,
28298944Sobrien   the only way to get at them is via groping around in the dynamic
28398944Sobrien   linker.
28498944Sobrien   The dynamic linker and it's structures are located in the shared
28598944Sobrien   C library, which gets run as the executable's "interpreter" by
28698944Sobrien   the kernel.
28798944Sobrien
28898944Sobrien   Note that we can assume nothing about the process state at the time
28998944Sobrien   we need to find these structures.  We may be stopped on the first
29098944Sobrien   instruction of the interpreter (C shared library), the first
29198944Sobrien   instruction of the executable itself, or somewhere else entirely
29298944Sobrien   (if we attached to the process for example).
29398944Sobrien */
29498944Sobrien
29598944Sobrienstatic char *debug_base_symbols[] =
29698944Sobrien{
29798944Sobrien  "r_debug",			/* Solaris 2.3 */
29898944Sobrien  "_r_debug",			/* Solaris 2.1, 2.2 */
29998944Sobrien  NULL
30098944Sobrien};
30198944Sobrien
30298944Sobrienstatic int look_for_base (int, CORE_ADDR);
30398944Sobrien
30498944Sobrien/*
30598944Sobrien
30698944Sobrien   LOCAL FUNCTION
30798944Sobrien
30898944Sobrien   look_for_base -- examine file for each mapped address segment
30998944Sobrien
31098944Sobrien   SYNOPSYS
31198944Sobrien
31298944Sobrien   static int look_for_base (int fd, CORE_ADDR baseaddr)
31398944Sobrien
31498944Sobrien   DESCRIPTION
31598944Sobrien
31698944Sobrien   This function is passed to proc_iterate_over_mappings, which
31798944Sobrien   causes it to get called once for each mapped address space, with
31898944Sobrien   an open file descriptor for the file mapped to that space, and the
31998944Sobrien   base address of that mapped space.
32098944Sobrien
32198944Sobrien   Our job is to find the debug base symbol in the file that this
32298944Sobrien   fd is open on, if it exists, and if so, initialize the dynamic
32398944Sobrien   linker structure base address debug_base.
32498944Sobrien
32598944Sobrien   Note that this is a computationally expensive proposition, since
32698944Sobrien   we basically have to open a bfd on every call, so we specifically
32798944Sobrien   avoid opening the exec file.
32898944Sobrien */
32998944Sobrien
33098944Sobrienstatic int
33198944Sobrienlook_for_base (int fd, CORE_ADDR baseaddr)
33298944Sobrien{
33398944Sobrien  bfd *interp_bfd;
33498944Sobrien  CORE_ADDR address = 0;
33598944Sobrien  char **symbolp;
33698944Sobrien
33798944Sobrien  /* If the fd is -1, then there is no file that corresponds to this
33898944Sobrien     mapped memory segment, so skip it.  Also, if the fd corresponds
33998944Sobrien     to the exec file, skip it as well. */
34098944Sobrien
34198944Sobrien  if (fd == -1
34298944Sobrien      || (exec_bfd != NULL
34398944Sobrien	  && fdmatch (fileno ((FILE *) (exec_bfd->iostream)), fd)))
34498944Sobrien    {
34598944Sobrien      return (0);
34698944Sobrien    }
34798944Sobrien
34898944Sobrien  /* Try to open whatever random file this fd corresponds to.  Note that
34998944Sobrien     we have no way currently to find the filename.  Don't gripe about
35098944Sobrien     any problems we might have, just fail. */
35198944Sobrien
35298944Sobrien  if ((interp_bfd = bfd_fdopenr ("unnamed", gnutarget, fd)) == NULL)
35398944Sobrien    {
35498944Sobrien      return (0);
35598944Sobrien    }
35698944Sobrien  if (!bfd_check_format (interp_bfd, bfd_object))
35798944Sobrien    {
35898944Sobrien      /* FIXME-leak: on failure, might not free all memory associated with
35998944Sobrien         interp_bfd.  */
36098944Sobrien      bfd_close (interp_bfd);
36198944Sobrien      return (0);
36298944Sobrien    }
36398944Sobrien
36498944Sobrien  /* Now try to find our debug base symbol in this file, which we at
36598944Sobrien     least know to be a valid ELF executable or shared library. */
36698944Sobrien
36798944Sobrien  for (symbolp = debug_base_symbols; *symbolp != NULL; symbolp++)
36898944Sobrien    {
369130803Smarcel      address = bfd_lookup_symbol (interp_bfd, *symbolp, 0);
37098944Sobrien      if (address != 0)
37198944Sobrien	{
37298944Sobrien	  break;
37398944Sobrien	}
37498944Sobrien    }
37598944Sobrien  if (address == 0)
37698944Sobrien    {
37798944Sobrien      /* FIXME-leak: on failure, might not free all memory associated with
37898944Sobrien         interp_bfd.  */
37998944Sobrien      bfd_close (interp_bfd);
38098944Sobrien      return (0);
38198944Sobrien    }
38298944Sobrien
38398944Sobrien  /* Eureka!  We found the symbol.  But now we may need to relocate it
38498944Sobrien     by the base address.  If the symbol's value is less than the base
38598944Sobrien     address of the shared library, then it hasn't yet been relocated
38698944Sobrien     by the dynamic linker, and we have to do it ourself.  FIXME: Note
38798944Sobrien     that we make the assumption that the first segment that corresponds
38898944Sobrien     to the shared library has the base address to which the library
38998944Sobrien     was relocated. */
39098944Sobrien
39198944Sobrien  if (address < baseaddr)
39298944Sobrien    {
39398944Sobrien      address += baseaddr;
39498944Sobrien    }
39598944Sobrien  debug_base = address;
39698944Sobrien  /* FIXME-leak: on failure, might not free all memory associated with
39798944Sobrien     interp_bfd.  */
39898944Sobrien  bfd_close (interp_bfd);
39998944Sobrien  return (1);
40098944Sobrien}
40198944Sobrien#endif /* HANDLE_SVR4_EXEC_EMULATORS */
40298944Sobrien
40398944Sobrien/*
40498944Sobrien
40598944Sobrien   LOCAL FUNCTION
40698944Sobrien
40798944Sobrien   elf_locate_base -- locate the base address of dynamic linker structs
40898944Sobrien   for SVR4 elf targets.
40998944Sobrien
41098944Sobrien   SYNOPSIS
41198944Sobrien
41298944Sobrien   CORE_ADDR elf_locate_base (void)
41398944Sobrien
41498944Sobrien   DESCRIPTION
41598944Sobrien
41698944Sobrien   For SVR4 elf targets the address of the dynamic linker's runtime
41798944Sobrien   structure is contained within the dynamic info section in the
41898944Sobrien   executable file.  The dynamic section is also mapped into the
41998944Sobrien   inferior address space.  Because the runtime loader fills in the
42098944Sobrien   real address before starting the inferior, we have to read in the
42198944Sobrien   dynamic info section from the inferior address space.
42298944Sobrien   If there are any errors while trying to find the address, we
42398944Sobrien   silently return 0, otherwise the found address is returned.
42498944Sobrien
42598944Sobrien */
42698944Sobrien
42798944Sobrienstatic CORE_ADDR
42898944Sobrienelf_locate_base (void)
42998944Sobrien{
430130803Smarcel  struct bfd_section *dyninfo_sect;
43198944Sobrien  int dyninfo_sect_size;
43298944Sobrien  CORE_ADDR dyninfo_addr;
43398944Sobrien  char *buf;
43498944Sobrien  char *bufend;
43598944Sobrien  int arch_size;
43698944Sobrien
43798944Sobrien  /* Find the start address of the .dynamic section.  */
43898944Sobrien  dyninfo_sect = bfd_get_section_by_name (exec_bfd, ".dynamic");
43998944Sobrien  if (dyninfo_sect == NULL)
44098944Sobrien    return 0;
44198944Sobrien  dyninfo_addr = bfd_section_vma (exec_bfd, dyninfo_sect);
44298944Sobrien
44398944Sobrien  /* Read in .dynamic section, silently ignore errors.  */
44498944Sobrien  dyninfo_sect_size = bfd_section_size (exec_bfd, dyninfo_sect);
44598944Sobrien  buf = alloca (dyninfo_sect_size);
44698944Sobrien  if (target_read_memory (dyninfo_addr, buf, dyninfo_sect_size))
44798944Sobrien    return 0;
44898944Sobrien
44998944Sobrien  /* Find the DT_DEBUG entry in the the .dynamic section.
45098944Sobrien     For mips elf we look for DT_MIPS_RLD_MAP, mips elf apparently has
45198944Sobrien     no DT_DEBUG entries.  */
45298944Sobrien
45398944Sobrien  arch_size = bfd_get_arch_size (exec_bfd);
45498944Sobrien  if (arch_size == -1)	/* failure */
45598944Sobrien    return 0;
45698944Sobrien
45798944Sobrien  if (arch_size == 32)
45898944Sobrien    { /* 32-bit elf */
45998944Sobrien      for (bufend = buf + dyninfo_sect_size;
46098944Sobrien	   buf < bufend;
46198944Sobrien	   buf += sizeof (Elf32_External_Dyn))
46298944Sobrien	{
46398944Sobrien	  Elf32_External_Dyn *x_dynp = (Elf32_External_Dyn *) buf;
46498944Sobrien	  long dyn_tag;
46598944Sobrien	  CORE_ADDR dyn_ptr;
46698944Sobrien
46798944Sobrien	  dyn_tag = bfd_h_get_32 (exec_bfd, (bfd_byte *) x_dynp->d_tag);
46898944Sobrien	  if (dyn_tag == DT_NULL)
46998944Sobrien	    break;
47098944Sobrien	  else if (dyn_tag == DT_DEBUG)
47198944Sobrien	    {
47298944Sobrien	      dyn_ptr = bfd_h_get_32 (exec_bfd,
47398944Sobrien				      (bfd_byte *) x_dynp->d_un.d_ptr);
47498944Sobrien	      return dyn_ptr;
47598944Sobrien	    }
47698944Sobrien	  else if (dyn_tag == DT_MIPS_RLD_MAP)
47798944Sobrien	    {
47898944Sobrien	      char *pbuf;
479130803Smarcel	      int pbuf_size = TARGET_PTR_BIT / HOST_CHAR_BIT;
48098944Sobrien
481130803Smarcel	      pbuf = alloca (pbuf_size);
48298944Sobrien	      /* DT_MIPS_RLD_MAP contains a pointer to the address
48398944Sobrien		 of the dynamic link structure.  */
48498944Sobrien	      dyn_ptr = bfd_h_get_32 (exec_bfd,
48598944Sobrien				      (bfd_byte *) x_dynp->d_un.d_ptr);
486130803Smarcel	      if (target_read_memory (dyn_ptr, pbuf, pbuf_size))
48798944Sobrien		return 0;
488130803Smarcel	      return extract_unsigned_integer (pbuf, pbuf_size);
48998944Sobrien	    }
49098944Sobrien	}
49198944Sobrien    }
49298944Sobrien  else /* 64-bit elf */
49398944Sobrien    {
49498944Sobrien      for (bufend = buf + dyninfo_sect_size;
49598944Sobrien	   buf < bufend;
49698944Sobrien	   buf += sizeof (Elf64_External_Dyn))
49798944Sobrien	{
49898944Sobrien	  Elf64_External_Dyn *x_dynp = (Elf64_External_Dyn *) buf;
49998944Sobrien	  long dyn_tag;
50098944Sobrien	  CORE_ADDR dyn_ptr;
50198944Sobrien
50298944Sobrien	  dyn_tag = bfd_h_get_64 (exec_bfd, (bfd_byte *) x_dynp->d_tag);
50398944Sobrien	  if (dyn_tag == DT_NULL)
50498944Sobrien	    break;
50598944Sobrien	  else if (dyn_tag == DT_DEBUG)
50698944Sobrien	    {
50798944Sobrien	      dyn_ptr = bfd_h_get_64 (exec_bfd,
50898944Sobrien				      (bfd_byte *) x_dynp->d_un.d_ptr);
50998944Sobrien	      return dyn_ptr;
51098944Sobrien	    }
511130803Smarcel	  else if (dyn_tag == DT_MIPS_RLD_MAP)
512130803Smarcel	    {
513130803Smarcel	      char *pbuf;
514130803Smarcel	      int pbuf_size = TARGET_PTR_BIT / HOST_CHAR_BIT;
515130803Smarcel
516130803Smarcel	      pbuf = alloca (pbuf_size);
517130803Smarcel	      /* DT_MIPS_RLD_MAP contains a pointer to the address
518130803Smarcel		 of the dynamic link structure.  */
519130803Smarcel	      dyn_ptr = bfd_h_get_64 (exec_bfd,
520130803Smarcel				      (bfd_byte *) x_dynp->d_un.d_ptr);
521130803Smarcel	      if (target_read_memory (dyn_ptr, pbuf, pbuf_size))
522130803Smarcel		return 0;
523130803Smarcel	      return extract_unsigned_integer (pbuf, pbuf_size);
524130803Smarcel	    }
52598944Sobrien	}
52698944Sobrien    }
52798944Sobrien
52898944Sobrien  /* DT_DEBUG entry not found.  */
52998944Sobrien  return 0;
53098944Sobrien}
53198944Sobrien
53298944Sobrien/*
53398944Sobrien
53498944Sobrien   LOCAL FUNCTION
53598944Sobrien
53698944Sobrien   locate_base -- locate the base address of dynamic linker structs
53798944Sobrien
53898944Sobrien   SYNOPSIS
53998944Sobrien
54098944Sobrien   CORE_ADDR locate_base (void)
54198944Sobrien
54298944Sobrien   DESCRIPTION
54398944Sobrien
54498944Sobrien   For both the SunOS and SVR4 shared library implementations, if the
54598944Sobrien   inferior executable has been linked dynamically, there is a single
54698944Sobrien   address somewhere in the inferior's data space which is the key to
54798944Sobrien   locating all of the dynamic linker's runtime structures.  This
54898944Sobrien   address is the value of the debug base symbol.  The job of this
54998944Sobrien   function is to find and return that address, or to return 0 if there
55098944Sobrien   is no such address (the executable is statically linked for example).
55198944Sobrien
55298944Sobrien   For SunOS, the job is almost trivial, since the dynamic linker and
55398944Sobrien   all of it's structures are statically linked to the executable at
55498944Sobrien   link time.  Thus the symbol for the address we are looking for has
55598944Sobrien   already been added to the minimal symbol table for the executable's
55698944Sobrien   objfile at the time the symbol file's symbols were read, and all we
55798944Sobrien   have to do is look it up there.  Note that we explicitly do NOT want
55898944Sobrien   to find the copies in the shared library.
55998944Sobrien
56098944Sobrien   The SVR4 version is a bit more complicated because the address
56198944Sobrien   is contained somewhere in the dynamic info section.  We have to go
56298944Sobrien   to a lot more work to discover the address of the debug base symbol.
56398944Sobrien   Because of this complexity, we cache the value we find and return that
56498944Sobrien   value on subsequent invocations.  Note there is no copy in the
56598944Sobrien   executable symbol tables.
56698944Sobrien
56798944Sobrien */
56898944Sobrien
56998944Sobrienstatic CORE_ADDR
57098944Sobrienlocate_base (void)
57198944Sobrien{
57298944Sobrien  /* Check to see if we have a currently valid address, and if so, avoid
57398944Sobrien     doing all this work again and just return the cached address.  If
57498944Sobrien     we have no cached address, try to locate it in the dynamic info
575130803Smarcel     section for ELF executables.  There's no point in doing any of this
576130803Smarcel     though if we don't have some link map offsets to work with.  */
57798944Sobrien
578130803Smarcel  if (debug_base == 0 && svr4_have_link_map_offsets ())
57998944Sobrien    {
58098944Sobrien      if (exec_bfd != NULL
58198944Sobrien	  && bfd_get_flavour (exec_bfd) == bfd_target_elf_flavour)
58298944Sobrien	debug_base = elf_locate_base ();
58398944Sobrien#ifdef HANDLE_SVR4_EXEC_EMULATORS
58498944Sobrien      /* Try it the hard way for emulated executables.  */
58598944Sobrien      else if (!ptid_equal (inferior_ptid, null_ptid) && target_has_execution)
58698944Sobrien	proc_iterate_over_mappings (look_for_base);
58798944Sobrien#endif
58898944Sobrien    }
58998944Sobrien  return (debug_base);
59098944Sobrien}
59198944Sobrien
59298944Sobrien/*
59398944Sobrien
59498944Sobrien   LOCAL FUNCTION
59598944Sobrien
59698944Sobrien   first_link_map_member -- locate first member in dynamic linker's map
59798944Sobrien
59898944Sobrien   SYNOPSIS
59998944Sobrien
60098944Sobrien   static CORE_ADDR first_link_map_member (void)
60198944Sobrien
60298944Sobrien   DESCRIPTION
60398944Sobrien
60498944Sobrien   Find the first element in the inferior's dynamic link map, and
60598944Sobrien   return its address in the inferior.  This function doesn't copy the
60698944Sobrien   link map entry itself into our address space; current_sos actually
60798944Sobrien   does the reading.  */
60898944Sobrien
60998944Sobrienstatic CORE_ADDR
61098944Sobrienfirst_link_map_member (void)
61198944Sobrien{
61298944Sobrien  CORE_ADDR lm = 0;
61398944Sobrien  struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
61498944Sobrien  char *r_map_buf = xmalloc (lmo->r_map_size);
61598944Sobrien  struct cleanup *cleanups = make_cleanup (xfree, r_map_buf);
61698944Sobrien
61798944Sobrien  read_memory (debug_base + lmo->r_map_offset, r_map_buf, lmo->r_map_size);
61898944Sobrien
619130803Smarcel  /* Assume that the address is unsigned.  */
620130803Smarcel  lm = extract_unsigned_integer (r_map_buf, lmo->r_map_size);
62198944Sobrien
62298944Sobrien  /* FIXME:  Perhaps we should validate the info somehow, perhaps by
62398944Sobrien     checking r_version for a known version number, or r_state for
62498944Sobrien     RT_CONSISTENT. */
62598944Sobrien
62698944Sobrien  do_cleanups (cleanups);
62798944Sobrien
62898944Sobrien  return (lm);
62998944Sobrien}
63098944Sobrien
63198944Sobrien/*
63298944Sobrien
63398944Sobrien  LOCAL FUNCTION
63498944Sobrien
63598944Sobrien  open_symbol_file_object
63698944Sobrien
63798944Sobrien  SYNOPSIS
63898944Sobrien
63998944Sobrien  void open_symbol_file_object (void *from_tty)
64098944Sobrien
64198944Sobrien  DESCRIPTION
64298944Sobrien
64398944Sobrien  If no open symbol file, attempt to locate and open the main symbol
64498944Sobrien  file.  On SVR4 systems, this is the first link map entry.  If its
64598944Sobrien  name is here, we can open it.  Useful when attaching to a process
64698944Sobrien  without first loading its symbol file.
64798944Sobrien
64898944Sobrien  If FROM_TTYP dereferences to a non-zero integer, allow messages to
64998944Sobrien  be printed.  This parameter is a pointer rather than an int because
65098944Sobrien  open_symbol_file_object() is called via catch_errors() and
65198944Sobrien  catch_errors() requires a pointer argument. */
65298944Sobrien
65398944Sobrienstatic int
65498944Sobrienopen_symbol_file_object (void *from_ttyp)
65598944Sobrien{
65698944Sobrien  CORE_ADDR lm, l_name;
65798944Sobrien  char *filename;
65898944Sobrien  int errcode;
65998944Sobrien  int from_tty = *(int *)from_ttyp;
66098944Sobrien  struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
66198944Sobrien  char *l_name_buf = xmalloc (lmo->l_name_size);
66298944Sobrien  struct cleanup *cleanups = make_cleanup (xfree, l_name_buf);
66398944Sobrien
66498944Sobrien  if (symfile_objfile)
66598944Sobrien    if (!query ("Attempt to reload symbols from process? "))
66698944Sobrien      return 0;
66798944Sobrien
66898944Sobrien  if ((debug_base = locate_base ()) == 0)
66998944Sobrien    return 0;	/* failed somehow... */
67098944Sobrien
67198944Sobrien  /* First link map member should be the executable.  */
67298944Sobrien  if ((lm = first_link_map_member ()) == 0)
67398944Sobrien    return 0;	/* failed somehow... */
67498944Sobrien
67598944Sobrien  /* Read address of name from target memory to GDB.  */
67698944Sobrien  read_memory (lm + lmo->l_name_offset, l_name_buf, lmo->l_name_size);
67798944Sobrien
678130803Smarcel  /* Convert the address to host format.  Assume that the address is
679130803Smarcel     unsigned.  */
680130803Smarcel  l_name = extract_unsigned_integer (l_name_buf, lmo->l_name_size);
68198944Sobrien
68298944Sobrien  /* Free l_name_buf.  */
68398944Sobrien  do_cleanups (cleanups);
68498944Sobrien
68598944Sobrien  if (l_name == 0)
68698944Sobrien    return 0;		/* No filename.  */
68798944Sobrien
68898944Sobrien  /* Now fetch the filename from target memory.  */
68998944Sobrien  target_read_string (l_name, &filename, SO_NAME_MAX_PATH_SIZE - 1, &errcode);
69098944Sobrien
69198944Sobrien  if (errcode)
69298944Sobrien    {
69398944Sobrien      warning ("failed to read exec filename from attached file: %s",
69498944Sobrien	       safe_strerror (errcode));
69598944Sobrien      return 0;
69698944Sobrien    }
69798944Sobrien
69898944Sobrien  make_cleanup (xfree, filename);
69998944Sobrien  /* Have a pathname: read the symbol file.  */
70098944Sobrien  symbol_file_add_main (filename, from_tty);
70198944Sobrien
70298944Sobrien  return 1;
70398944Sobrien}
70498944Sobrien
70598944Sobrien/* LOCAL FUNCTION
70698944Sobrien
70798944Sobrien   current_sos -- build a list of currently loaded shared objects
70898944Sobrien
70998944Sobrien   SYNOPSIS
71098944Sobrien
71198944Sobrien   struct so_list *current_sos ()
71298944Sobrien
71398944Sobrien   DESCRIPTION
71498944Sobrien
71598944Sobrien   Build a list of `struct so_list' objects describing the shared
71698944Sobrien   objects currently loaded in the inferior.  This list does not
71798944Sobrien   include an entry for the main executable file.
71898944Sobrien
71998944Sobrien   Note that we only gather information directly available from the
72098944Sobrien   inferior --- we don't examine any of the shared library files
72198944Sobrien   themselves.  The declaration of `struct so_list' says which fields
72298944Sobrien   we provide values for.  */
72398944Sobrien
72498944Sobrienstatic struct so_list *
72598944Sobriensvr4_current_sos (void)
72698944Sobrien{
72798944Sobrien  CORE_ADDR lm;
72898944Sobrien  struct so_list *head = 0;
72998944Sobrien  struct so_list **link_ptr = &head;
73098944Sobrien
73198944Sobrien  /* Make sure we've looked up the inferior's dynamic linker's base
73298944Sobrien     structure.  */
73398944Sobrien  if (! debug_base)
73498944Sobrien    {
73598944Sobrien      debug_base = locate_base ();
73698944Sobrien
73798944Sobrien      /* If we can't find the dynamic linker's base structure, this
73898944Sobrien	 must not be a dynamically linked executable.  Hmm.  */
73998944Sobrien      if (! debug_base)
74098944Sobrien	return 0;
74198944Sobrien    }
74298944Sobrien
74398944Sobrien  /* Walk the inferior's link map list, and build our list of
74498944Sobrien     `struct so_list' nodes.  */
74598944Sobrien  lm = first_link_map_member ();
74698944Sobrien  while (lm)
74798944Sobrien    {
74898944Sobrien      struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
74998944Sobrien      struct so_list *new
75098944Sobrien	= (struct so_list *) xmalloc (sizeof (struct so_list));
75198944Sobrien      struct cleanup *old_chain = make_cleanup (xfree, new);
75298944Sobrien
75398944Sobrien      memset (new, 0, sizeof (*new));
75498944Sobrien
75598944Sobrien      new->lm_info = xmalloc (sizeof (struct lm_info));
75698944Sobrien      make_cleanup (xfree, new->lm_info);
75798944Sobrien
75898944Sobrien      new->lm_info->lm = xmalloc (lmo->link_map_size);
75998944Sobrien      make_cleanup (xfree, new->lm_info->lm);
76098944Sobrien      memset (new->lm_info->lm, 0, lmo->link_map_size);
76198944Sobrien
76298944Sobrien      read_memory (lm, new->lm_info->lm, lmo->link_map_size);
76398944Sobrien
76498944Sobrien      lm = LM_NEXT (new);
76598944Sobrien
76698944Sobrien      /* For SVR4 versions, the first entry in the link map is for the
76798944Sobrien         inferior executable, so we must ignore it.  For some versions of
76898944Sobrien         SVR4, it has no name.  For others (Solaris 2.3 for example), it
76998944Sobrien         does have a name, so we can no longer use a missing name to
77098944Sobrien         decide when to ignore it. */
77198944Sobrien      if (IGNORE_FIRST_LINK_MAP_ENTRY (new))
77298944Sobrien	free_so (new);
77398944Sobrien      else
77498944Sobrien	{
77598944Sobrien	  int errcode;
77698944Sobrien	  char *buffer;
77798944Sobrien
77898944Sobrien	  /* Extract this shared object's name.  */
77998944Sobrien	  target_read_string (LM_NAME (new), &buffer,
78098944Sobrien			      SO_NAME_MAX_PATH_SIZE - 1, &errcode);
78198944Sobrien	  if (errcode != 0)
78298944Sobrien	    {
78398944Sobrien	      warning ("current_sos: Can't read pathname for load map: %s\n",
78498944Sobrien		       safe_strerror (errcode));
78598944Sobrien	    }
78698944Sobrien	  else
78798944Sobrien	    {
78898944Sobrien	      strncpy (new->so_name, buffer, SO_NAME_MAX_PATH_SIZE - 1);
78998944Sobrien	      new->so_name[SO_NAME_MAX_PATH_SIZE - 1] = '\0';
79098944Sobrien	      xfree (buffer);
79198944Sobrien	      strcpy (new->so_original_name, new->so_name);
79298944Sobrien	    }
79398944Sobrien
79498944Sobrien	  /* If this entry has no name, or its name matches the name
79598944Sobrien	     for the main executable, don't include it in the list.  */
79698944Sobrien	  if (! new->so_name[0]
79798944Sobrien	      || match_main (new->so_name))
79898944Sobrien	    free_so (new);
79998944Sobrien	  else
80098944Sobrien	    {
80198944Sobrien	      new->next = 0;
80298944Sobrien	      *link_ptr = new;
80398944Sobrien	      link_ptr = &new->next;
80498944Sobrien	    }
80598944Sobrien	}
80698944Sobrien
80798944Sobrien      discard_cleanups (old_chain);
80898944Sobrien    }
80998944Sobrien
81098944Sobrien  return head;
81198944Sobrien}
81298944Sobrien
813130803Smarcel/* Get the address of the link_map for a given OBJFILE.  Loop through
814130803Smarcel   the link maps, and return the address of the one corresponding to
815130803Smarcel   the given objfile.  Note that this function takes into account that
816130803Smarcel   objfile can be the main executable, not just a shared library.  The
817130803Smarcel   main executable has always an empty name field in the linkmap.  */
81898944Sobrien
819130803SmarcelCORE_ADDR
820130803Smarcelsvr4_fetch_objfile_link_map (struct objfile *objfile)
821130803Smarcel{
822130803Smarcel  CORE_ADDR lm;
823130803Smarcel
824130803Smarcel  if ((debug_base = locate_base ()) == 0)
825130803Smarcel    return 0;   /* failed somehow... */
826130803Smarcel
827130803Smarcel  /* Position ourselves on the first link map.  */
828130803Smarcel  lm = first_link_map_member ();
829130803Smarcel  while (lm)
830130803Smarcel    {
831130803Smarcel      /* Get info on the layout of the r_debug and link_map structures. */
832130803Smarcel      struct link_map_offsets *lmo = SVR4_FETCH_LINK_MAP_OFFSETS ();
833130803Smarcel      int errcode;
834130803Smarcel      char *buffer;
835130803Smarcel      struct lm_info objfile_lm_info;
836130803Smarcel      struct cleanup *old_chain;
837130803Smarcel      CORE_ADDR name_address;
838130803Smarcel      char *l_name_buf = xmalloc (lmo->l_name_size);
839130803Smarcel      old_chain = make_cleanup (xfree, l_name_buf);
840130803Smarcel
841130803Smarcel      /* Set up the buffer to contain the portion of the link_map
842130803Smarcel         structure that gdb cares about.  Note that this is not the
843130803Smarcel         whole link_map structure.  */
844130803Smarcel      objfile_lm_info.lm = xmalloc (lmo->link_map_size);
845130803Smarcel      make_cleanup (xfree, objfile_lm_info.lm);
846130803Smarcel      memset (objfile_lm_info.lm, 0, lmo->link_map_size);
847130803Smarcel
848130803Smarcel      /* Read the link map into our internal structure.  */
849130803Smarcel      read_memory (lm, objfile_lm_info.lm, lmo->link_map_size);
850130803Smarcel
851130803Smarcel      /* Read address of name from target memory to GDB.  */
852130803Smarcel      read_memory (lm + lmo->l_name_offset, l_name_buf, lmo->l_name_size);
853130803Smarcel
854130803Smarcel      /* Extract this object's name.  Assume that the address is
855130803Smarcel         unsigned.  */
856130803Smarcel      name_address = extract_unsigned_integer (l_name_buf, lmo->l_name_size);
857130803Smarcel      target_read_string (name_address, &buffer,
858130803Smarcel      			  SO_NAME_MAX_PATH_SIZE - 1, &errcode);
859130803Smarcel      make_cleanup (xfree, buffer);
860130803Smarcel      if (errcode != 0)
861130803Smarcel    	{
862130803Smarcel	  warning ("svr4_fetch_objfile_link_map: Can't read pathname for load map: %s\n",
863130803Smarcel  		   safe_strerror (errcode));
864130803Smarcel  	}
865130803Smarcel      else
866130803Smarcel  	{
867130803Smarcel	  /* Is this the linkmap for the file we want?  */
868130803Smarcel	  /* If the file is not a shared library and has no name,
869130803Smarcel	     we are sure it is the main executable, so we return that.  */
870130803Smarcel	  if ((buffer && strcmp (buffer, objfile->name) == 0)
871130803Smarcel              || (!(objfile->flags & OBJF_SHARED) && (strcmp (buffer, "") == 0)))
872130803Smarcel  	    {
873130803Smarcel    	      do_cleanups (old_chain);
874130803Smarcel    	      return lm;
875130803Smarcel      	    }
876130803Smarcel  	}
877130803Smarcel      /* Not the file we wanted, continue checking.  Assume that the
878130803Smarcel         address is unsigned.  */
879130803Smarcel      lm = extract_unsigned_integer (objfile_lm_info.lm + lmo->l_next_offset,
880130803Smarcel				     lmo->l_next_size);
881130803Smarcel      do_cleanups (old_chain);
882130803Smarcel    }
883130803Smarcel  return 0;
884130803Smarcel}
885130803Smarcel
88698944Sobrien/* On some systems, the only way to recognize the link map entry for
88798944Sobrien   the main executable file is by looking at its name.  Return
88898944Sobrien   non-zero iff SONAME matches one of the known main executable names.  */
88998944Sobrien
89098944Sobrienstatic int
89198944Sobrienmatch_main (char *soname)
89298944Sobrien{
89398944Sobrien  char **mainp;
89498944Sobrien
89598944Sobrien  for (mainp = main_name_list; *mainp != NULL; mainp++)
89698944Sobrien    {
89798944Sobrien      if (strcmp (soname, *mainp) == 0)
89898944Sobrien	return (1);
89998944Sobrien    }
90098944Sobrien
90198944Sobrien  return (0);
90298944Sobrien}
90398944Sobrien
90498944Sobrien/* Return 1 if PC lies in the dynamic symbol resolution code of the
90598944Sobrien   SVR4 run time loader.  */
90698944Sobrienstatic CORE_ADDR interp_text_sect_low;
90798944Sobrienstatic CORE_ADDR interp_text_sect_high;
90898944Sobrienstatic CORE_ADDR interp_plt_sect_low;
90998944Sobrienstatic CORE_ADDR interp_plt_sect_high;
91098944Sobrien
91198944Sobrienstatic int
91298944Sobriensvr4_in_dynsym_resolve_code (CORE_ADDR pc)
91398944Sobrien{
91498944Sobrien  return ((pc >= interp_text_sect_low && pc < interp_text_sect_high)
91598944Sobrien	  || (pc >= interp_plt_sect_low && pc < interp_plt_sect_high)
91698944Sobrien	  || in_plt_section (pc, NULL));
91798944Sobrien}
91898944Sobrien
919130803Smarcel/* Given an executable's ABFD and target, compute the entry-point
920130803Smarcel   address.  */
92198944Sobrien
922130803Smarcelstatic CORE_ADDR
923130803Smarcelexec_entry_point (struct bfd *abfd, struct target_ops *targ)
924130803Smarcel{
925130803Smarcel  /* KevinB wrote ... for most targets, the address returned by
926130803Smarcel     bfd_get_start_address() is the entry point for the start
927130803Smarcel     function.  But, for some targets, bfd_get_start_address() returns
928130803Smarcel     the address of a function descriptor from which the entry point
929130803Smarcel     address may be extracted.  This address is extracted by
930130803Smarcel     gdbarch_convert_from_func_ptr_addr().  The method
931130803Smarcel     gdbarch_convert_from_func_ptr_addr() is the merely the identify
932130803Smarcel     function for targets which don't use function descriptors.  */
933130803Smarcel  return gdbarch_convert_from_func_ptr_addr (current_gdbarch,
934130803Smarcel					     bfd_get_start_address (abfd),
935130803Smarcel					     targ);
936130803Smarcel}
937130803Smarcel
93898944Sobrien/*
93998944Sobrien
94098944Sobrien   LOCAL FUNCTION
94198944Sobrien
94298944Sobrien   enable_break -- arrange for dynamic linker to hit breakpoint
94398944Sobrien
94498944Sobrien   SYNOPSIS
94598944Sobrien
94698944Sobrien   int enable_break (void)
94798944Sobrien
94898944Sobrien   DESCRIPTION
94998944Sobrien
95098944Sobrien   Both the SunOS and the SVR4 dynamic linkers have, as part of their
95198944Sobrien   debugger interface, support for arranging for the inferior to hit
95298944Sobrien   a breakpoint after mapping in the shared libraries.  This function
95398944Sobrien   enables that breakpoint.
95498944Sobrien
95598944Sobrien   For SunOS, there is a special flag location (in_debugger) which we
95698944Sobrien   set to 1.  When the dynamic linker sees this flag set, it will set
95798944Sobrien   a breakpoint at a location known only to itself, after saving the
95898944Sobrien   original contents of that place and the breakpoint address itself,
95998944Sobrien   in it's own internal structures.  When we resume the inferior, it
96098944Sobrien   will eventually take a SIGTRAP when it runs into the breakpoint.
96198944Sobrien   We handle this (in a different place) by restoring the contents of
96298944Sobrien   the breakpointed location (which is only known after it stops),
96398944Sobrien   chasing around to locate the shared libraries that have been
96498944Sobrien   loaded, then resuming.
96598944Sobrien
96698944Sobrien   For SVR4, the debugger interface structure contains a member (r_brk)
96798944Sobrien   which is statically initialized at the time the shared library is
96898944Sobrien   built, to the offset of a function (_r_debug_state) which is guaran-
96998944Sobrien   teed to be called once before mapping in a library, and again when
97098944Sobrien   the mapping is complete.  At the time we are examining this member,
97198944Sobrien   it contains only the unrelocated offset of the function, so we have
97298944Sobrien   to do our own relocation.  Later, when the dynamic linker actually
97398944Sobrien   runs, it relocates r_brk to be the actual address of _r_debug_state().
97498944Sobrien
97598944Sobrien   The debugger interface structure also contains an enumeration which
97698944Sobrien   is set to either RT_ADD or RT_DELETE prior to changing the mapping,
97798944Sobrien   depending upon whether or not the library is being mapped or unmapped,
97898944Sobrien   and then set to RT_CONSISTENT after the library is mapped/unmapped.
97998944Sobrien */
98098944Sobrien
98198944Sobrienstatic int
98298944Sobrienenable_break (void)
98398944Sobrien{
98498944Sobrien  int success = 0;
98598944Sobrien
98698944Sobrien#ifdef BKPT_AT_SYMBOL
98798944Sobrien
98898944Sobrien  struct minimal_symbol *msymbol;
98998944Sobrien  char **bkpt_namep;
99098944Sobrien  asection *interp_sect;
99198944Sobrien
99298944Sobrien  /* First, remove all the solib event breakpoints.  Their addresses
99398944Sobrien     may have changed since the last time we ran the program.  */
99498944Sobrien  remove_solib_event_breakpoints ();
99598944Sobrien
99698944Sobrien  interp_text_sect_low = interp_text_sect_high = 0;
99798944Sobrien  interp_plt_sect_low = interp_plt_sect_high = 0;
99898944Sobrien
99998944Sobrien  /* Find the .interp section; if not found, warn the user and drop
100098944Sobrien     into the old breakpoint at symbol code.  */
100198944Sobrien  interp_sect = bfd_get_section_by_name (exec_bfd, ".interp");
100298944Sobrien  if (interp_sect)
100398944Sobrien    {
100498944Sobrien      unsigned int interp_sect_size;
100598944Sobrien      char *buf;
100698944Sobrien      CORE_ADDR load_addr = 0;
100798944Sobrien      int load_addr_found = 0;
100898944Sobrien      struct so_list *inferior_sos;
100998944Sobrien      bfd *tmp_bfd = NULL;
1010130803Smarcel      struct target_ops *tmp_bfd_target;
101198944Sobrien      int tmp_fd = -1;
101298944Sobrien      char *tmp_pathname = NULL;
101398944Sobrien      CORE_ADDR sym_addr = 0;
101498944Sobrien
101598944Sobrien      /* Read the contents of the .interp section into a local buffer;
101698944Sobrien         the contents specify the dynamic linker this program uses.  */
101798944Sobrien      interp_sect_size = bfd_section_size (exec_bfd, interp_sect);
101898944Sobrien      buf = alloca (interp_sect_size);
101998944Sobrien      bfd_get_section_contents (exec_bfd, interp_sect,
102098944Sobrien				buf, 0, interp_sect_size);
102198944Sobrien
102298944Sobrien      /* Now we need to figure out where the dynamic linker was
102398944Sobrien         loaded so that we can load its symbols and place a breakpoint
102498944Sobrien         in the dynamic linker itself.
102598944Sobrien
102698944Sobrien         This address is stored on the stack.  However, I've been unable
102798944Sobrien         to find any magic formula to find it for Solaris (appears to
102898944Sobrien         be trivial on GNU/Linux).  Therefore, we have to try an alternate
102998944Sobrien         mechanism to find the dynamic linker's base address.  */
103098944Sobrien
103198944Sobrien      tmp_fd  = solib_open (buf, &tmp_pathname);
103298944Sobrien      if (tmp_fd >= 0)
103398944Sobrien	tmp_bfd = bfd_fdopenr (tmp_pathname, gnutarget, tmp_fd);
103498944Sobrien
103598944Sobrien      if (tmp_bfd == NULL)
103698944Sobrien	goto bkpt_at_symbol;
103798944Sobrien
103898944Sobrien      /* Make sure the dynamic linker's really a useful object.  */
103998944Sobrien      if (!bfd_check_format (tmp_bfd, bfd_object))
104098944Sobrien	{
104198944Sobrien	  warning ("Unable to grok dynamic linker %s as an object file", buf);
104298944Sobrien	  bfd_close (tmp_bfd);
104398944Sobrien	  goto bkpt_at_symbol;
104498944Sobrien	}
104598944Sobrien
1046130803Smarcel      /* Now convert the TMP_BFD into a target.  That way target, as
1047130803Smarcel         well as BFD operations can be used.  Note that closing the
1048130803Smarcel         target will also close the underlying bfd.  */
1049130803Smarcel      tmp_bfd_target = target_bfd_reopen (tmp_bfd);
1050130803Smarcel
105198944Sobrien      /* If the entry in _DYNAMIC for the dynamic linker has already
105298944Sobrien         been filled in, we can read its base address from there. */
105398944Sobrien      inferior_sos = svr4_current_sos ();
105498944Sobrien      if (inferior_sos)
105598944Sobrien	{
105698944Sobrien	  /* Connected to a running target.  Update our shared library table. */
105798944Sobrien	  solib_add (NULL, 0, NULL, auto_solib_add);
105898944Sobrien	}
105998944Sobrien      while (inferior_sos)
106098944Sobrien	{
106198944Sobrien	  if (strcmp (buf, inferior_sos->so_original_name) == 0)
106298944Sobrien	    {
106398944Sobrien	      load_addr_found = 1;
106498944Sobrien	      load_addr = LM_ADDR (inferior_sos);
106598944Sobrien	      break;
106698944Sobrien	    }
106798944Sobrien	  inferior_sos = inferior_sos->next;
106898944Sobrien	}
106998944Sobrien
107098944Sobrien      /* Otherwise we find the dynamic linker's base address by examining
107198944Sobrien	 the current pc (which should point at the entry point for the
107298944Sobrien	 dynamic linker) and subtracting the offset of the entry point.  */
107398944Sobrien      if (!load_addr_found)
1074130803Smarcel	load_addr = (read_pc ()
1075130803Smarcel		     - exec_entry_point (tmp_bfd, tmp_bfd_target));
107698944Sobrien
107798944Sobrien      /* Record the relocated start and end address of the dynamic linker
107898944Sobrien         text and plt section for svr4_in_dynsym_resolve_code.  */
107998944Sobrien      interp_sect = bfd_get_section_by_name (tmp_bfd, ".text");
108098944Sobrien      if (interp_sect)
108198944Sobrien	{
108298944Sobrien	  interp_text_sect_low =
108398944Sobrien	    bfd_section_vma (tmp_bfd, interp_sect) + load_addr;
108498944Sobrien	  interp_text_sect_high =
108598944Sobrien	    interp_text_sect_low + bfd_section_size (tmp_bfd, interp_sect);
108698944Sobrien	}
108798944Sobrien      interp_sect = bfd_get_section_by_name (tmp_bfd, ".plt");
108898944Sobrien      if (interp_sect)
108998944Sobrien	{
109098944Sobrien	  interp_plt_sect_low =
109198944Sobrien	    bfd_section_vma (tmp_bfd, interp_sect) + load_addr;
109298944Sobrien	  interp_plt_sect_high =
109398944Sobrien	    interp_plt_sect_low + bfd_section_size (tmp_bfd, interp_sect);
109498944Sobrien	}
109598944Sobrien
109698944Sobrien      /* Now try to set a breakpoint in the dynamic linker.  */
109798944Sobrien      for (bkpt_namep = solib_break_names; *bkpt_namep != NULL; bkpt_namep++)
109898944Sobrien	{
1099130803Smarcel          /* On ABI's that use function descriptors, there are usually
1100130803Smarcel             two linker symbols associated with each C function: one
1101130803Smarcel             pointing at the actual entry point of the machine code,
1102130803Smarcel             and one pointing at the function's descriptor.  The
1103130803Smarcel             latter symbol has the same name as the C function.
1104130803Smarcel
1105130803Smarcel             What we're looking for here is the machine code entry
1106130803Smarcel             point, so we are only interested in symbols in code
1107130803Smarcel             sections.  */
1108130803Smarcel	  sym_addr = bfd_lookup_symbol (tmp_bfd, *bkpt_namep, SEC_CODE);
110998944Sobrien	  if (sym_addr != 0)
111098944Sobrien	    break;
111198944Sobrien	}
111298944Sobrien
1113130803Smarcel      /* We're done with both the temporary bfd and target.  Remember,
1114130803Smarcel         closing the target closes the underlying bfd.  */
1115130803Smarcel      target_close (tmp_bfd_target, 0);
111698944Sobrien
111798944Sobrien      if (sym_addr != 0)
111898944Sobrien	{
111998944Sobrien	  create_solib_event_breakpoint (load_addr + sym_addr);
112098944Sobrien	  return 1;
112198944Sobrien	}
112298944Sobrien
112398944Sobrien      /* For whatever reason we couldn't set a breakpoint in the dynamic
112498944Sobrien         linker.  Warn and drop into the old code.  */
112598944Sobrien    bkpt_at_symbol:
112698944Sobrien      warning ("Unable to find dynamic linker breakpoint function.\nGDB will be unable to debug shared library initializers\nand track explicitly loaded dynamic code.");
112798944Sobrien    }
112898944Sobrien
112998944Sobrien  /* Scan through the list of symbols, trying to look up the symbol and
113098944Sobrien     set a breakpoint there.  Terminate loop when we/if we succeed. */
113198944Sobrien
113298944Sobrien  breakpoint_addr = 0;
113398944Sobrien  for (bkpt_namep = bkpt_names; *bkpt_namep != NULL; bkpt_namep++)
113498944Sobrien    {
113598944Sobrien      msymbol = lookup_minimal_symbol (*bkpt_namep, NULL, symfile_objfile);
113698944Sobrien      if ((msymbol != NULL) && (SYMBOL_VALUE_ADDRESS (msymbol) != 0))
113798944Sobrien	{
113898944Sobrien	  create_solib_event_breakpoint (SYMBOL_VALUE_ADDRESS (msymbol));
113998944Sobrien	  return 1;
114098944Sobrien	}
114198944Sobrien    }
114298944Sobrien
114398944Sobrien  /* Nothing good happened.  */
114498944Sobrien  success = 0;
114598944Sobrien
114698944Sobrien#endif /* BKPT_AT_SYMBOL */
114798944Sobrien
114898944Sobrien  return (success);
114998944Sobrien}
115098944Sobrien
115198944Sobrien/*
115298944Sobrien
115398944Sobrien   LOCAL FUNCTION
115498944Sobrien
115598944Sobrien   special_symbol_handling -- additional shared library symbol handling
115698944Sobrien
115798944Sobrien   SYNOPSIS
115898944Sobrien
115998944Sobrien   void special_symbol_handling ()
116098944Sobrien
116198944Sobrien   DESCRIPTION
116298944Sobrien
116398944Sobrien   Once the symbols from a shared object have been loaded in the usual
116498944Sobrien   way, we are called to do any system specific symbol handling that
116598944Sobrien   is needed.
116698944Sobrien
116798944Sobrien   For SunOS4, this consisted of grunging around in the dynamic
116898944Sobrien   linkers structures to find symbol definitions for "common" symbols
116998944Sobrien   and adding them to the minimal symbol table for the runtime common
117098944Sobrien   objfile.
117198944Sobrien
117298944Sobrien   However, for SVR4, there's nothing to do.
117398944Sobrien
117498944Sobrien */
117598944Sobrien
117698944Sobrienstatic void
117798944Sobriensvr4_special_symbol_handling (void)
117898944Sobrien{
117998944Sobrien}
118098944Sobrien
118198944Sobrien/* Relocate the main executable.  This function should be called upon
118298944Sobrien   stopping the inferior process at the entry point to the program.
118398944Sobrien   The entry point from BFD is compared to the PC and if they are
118498944Sobrien   different, the main executable is relocated by the proper amount.
118598944Sobrien
118698944Sobrien   As written it will only attempt to relocate executables which
118798944Sobrien   lack interpreter sections.  It seems likely that only dynamic
118898944Sobrien   linker executables will get relocated, though it should work
118998944Sobrien   properly for a position-independent static executable as well.  */
119098944Sobrien
119198944Sobrienstatic void
119298944Sobriensvr4_relocate_main_executable (void)
119398944Sobrien{
119498944Sobrien  asection *interp_sect;
119598944Sobrien  CORE_ADDR pc = read_pc ();
119698944Sobrien
119798944Sobrien  /* Decide if the objfile needs to be relocated.  As indicated above,
119898944Sobrien     we will only be here when execution is stopped at the beginning
119998944Sobrien     of the program.  Relocation is necessary if the address at which
120098944Sobrien     we are presently stopped differs from the start address stored in
120198944Sobrien     the executable AND there's no interpreter section.  The condition
120298944Sobrien     regarding the interpreter section is very important because if
120398944Sobrien     there *is* an interpreter section, execution will begin there
120498944Sobrien     instead.  When there is an interpreter section, the start address
120598944Sobrien     is (presumably) used by the interpreter at some point to start
120698944Sobrien     execution of the program.
120798944Sobrien
120898944Sobrien     If there is an interpreter, it is normal for it to be set to an
120998944Sobrien     arbitrary address at the outset.  The job of finding it is
121098944Sobrien     handled in enable_break().
121198944Sobrien
121298944Sobrien     So, to summarize, relocations are necessary when there is no
121398944Sobrien     interpreter section and the start address obtained from the
121498944Sobrien     executable is different from the address at which GDB is
121598944Sobrien     currently stopped.
121698944Sobrien
121798944Sobrien     [ The astute reader will note that we also test to make sure that
121898944Sobrien       the executable in question has the DYNAMIC flag set.  It is my
121998944Sobrien       opinion that this test is unnecessary (undesirable even).  It
122098944Sobrien       was added to avoid inadvertent relocation of an executable
122198944Sobrien       whose e_type member in the ELF header is not ET_DYN.  There may
122298944Sobrien       be a time in the future when it is desirable to do relocations
122398944Sobrien       on other types of files as well in which case this condition
122498944Sobrien       should either be removed or modified to accomodate the new file
122598944Sobrien       type.  (E.g, an ET_EXEC executable which has been built to be
122698944Sobrien       position-independent could safely be relocated by the OS if
122798944Sobrien       desired.  It is true that this violates the ABI, but the ABI
122898944Sobrien       has been known to be bent from time to time.)  - Kevin, Nov 2000. ]
122998944Sobrien     */
123098944Sobrien
123198944Sobrien  interp_sect = bfd_get_section_by_name (exec_bfd, ".interp");
123298944Sobrien  if (interp_sect == NULL
123398944Sobrien      && (bfd_get_file_flags (exec_bfd) & DYNAMIC) != 0
1234130803Smarcel      && (exec_entry_point (exec_bfd, &exec_ops) != pc))
123598944Sobrien    {
123698944Sobrien      struct cleanup *old_chain;
123798944Sobrien      struct section_offsets *new_offsets;
123898944Sobrien      int i, changed;
123998944Sobrien      CORE_ADDR displacement;
124098944Sobrien
124198944Sobrien      /* It is necessary to relocate the objfile.  The amount to
124298944Sobrien	 relocate by is simply the address at which we are stopped
124398944Sobrien	 minus the starting address from the executable.
124498944Sobrien
124598944Sobrien	 We relocate all of the sections by the same amount.  This
124698944Sobrien	 behavior is mandated by recent editions of the System V ABI.
124798944Sobrien	 According to the System V Application Binary Interface,
124898944Sobrien	 Edition 4.1, page 5-5:
124998944Sobrien
125098944Sobrien	   ...  Though the system chooses virtual addresses for
125198944Sobrien	   individual processes, it maintains the segments' relative
125298944Sobrien	   positions.  Because position-independent code uses relative
125398944Sobrien	   addressesing between segments, the difference between
125498944Sobrien	   virtual addresses in memory must match the difference
125598944Sobrien	   between virtual addresses in the file.  The difference
125698944Sobrien	   between the virtual address of any segment in memory and
125798944Sobrien	   the corresponding virtual address in the file is thus a
125898944Sobrien	   single constant value for any one executable or shared
125998944Sobrien	   object in a given process.  This difference is the base
126098944Sobrien	   address.  One use of the base address is to relocate the
126198944Sobrien	   memory image of the program during dynamic linking.
126298944Sobrien
126398944Sobrien	 The same language also appears in Edition 4.0 of the System V
126498944Sobrien	 ABI and is left unspecified in some of the earlier editions.  */
126598944Sobrien
1266130803Smarcel      displacement = pc - exec_entry_point (exec_bfd, &exec_ops);
126798944Sobrien      changed = 0;
126898944Sobrien
126998944Sobrien      new_offsets = xcalloc (symfile_objfile->num_sections,
127098944Sobrien			     sizeof (struct section_offsets));
127198944Sobrien      old_chain = make_cleanup (xfree, new_offsets);
127298944Sobrien
127398944Sobrien      for (i = 0; i < symfile_objfile->num_sections; i++)
127498944Sobrien	{
127598944Sobrien	  if (displacement != ANOFFSET (symfile_objfile->section_offsets, i))
127698944Sobrien	    changed = 1;
127798944Sobrien	  new_offsets->offsets[i] = displacement;
127898944Sobrien	}
127998944Sobrien
128098944Sobrien      if (changed)
128198944Sobrien	objfile_relocate (symfile_objfile, new_offsets);
128298944Sobrien
128398944Sobrien      do_cleanups (old_chain);
128498944Sobrien    }
128598944Sobrien}
128698944Sobrien
128798944Sobrien/*
128898944Sobrien
128998944Sobrien   GLOBAL FUNCTION
129098944Sobrien
129198944Sobrien   svr4_solib_create_inferior_hook -- shared library startup support
129298944Sobrien
129398944Sobrien   SYNOPSIS
129498944Sobrien
129598944Sobrien   void svr4_solib_create_inferior_hook()
129698944Sobrien
129798944Sobrien   DESCRIPTION
129898944Sobrien
129998944Sobrien   When gdb starts up the inferior, it nurses it along (through the
130098944Sobrien   shell) until it is ready to execute it's first instruction.  At this
130198944Sobrien   point, this function gets called via expansion of the macro
130298944Sobrien   SOLIB_CREATE_INFERIOR_HOOK.
130398944Sobrien
130498944Sobrien   For SunOS executables, this first instruction is typically the
130598944Sobrien   one at "_start", or a similar text label, regardless of whether
130698944Sobrien   the executable is statically or dynamically linked.  The runtime
130798944Sobrien   startup code takes care of dynamically linking in any shared
130898944Sobrien   libraries, once gdb allows the inferior to continue.
130998944Sobrien
131098944Sobrien   For SVR4 executables, this first instruction is either the first
131198944Sobrien   instruction in the dynamic linker (for dynamically linked
131298944Sobrien   executables) or the instruction at "start" for statically linked
131398944Sobrien   executables.  For dynamically linked executables, the system
131498944Sobrien   first exec's /lib/libc.so.N, which contains the dynamic linker,
131598944Sobrien   and starts it running.  The dynamic linker maps in any needed
131698944Sobrien   shared libraries, maps in the actual user executable, and then
131798944Sobrien   jumps to "start" in the user executable.
131898944Sobrien
131998944Sobrien   For both SunOS shared libraries, and SVR4 shared libraries, we
132098944Sobrien   can arrange to cooperate with the dynamic linker to discover the
132198944Sobrien   names of shared libraries that are dynamically linked, and the
132298944Sobrien   base addresses to which they are linked.
132398944Sobrien
132498944Sobrien   This function is responsible for discovering those names and
132598944Sobrien   addresses, and saving sufficient information about them to allow
132698944Sobrien   their symbols to be read at a later time.
132798944Sobrien
132898944Sobrien   FIXME
132998944Sobrien
133098944Sobrien   Between enable_break() and disable_break(), this code does not
133198944Sobrien   properly handle hitting breakpoints which the user might have
133298944Sobrien   set in the startup code or in the dynamic linker itself.  Proper
133398944Sobrien   handling will probably have to wait until the implementation is
133498944Sobrien   changed to use the "breakpoint handler function" method.
133598944Sobrien
133698944Sobrien   Also, what if child has exit()ed?  Must exit loop somehow.
133798944Sobrien */
133898944Sobrien
133998944Sobrienstatic void
134098944Sobriensvr4_solib_create_inferior_hook (void)
134198944Sobrien{
134298944Sobrien  /* Relocate the main executable if necessary.  */
134398944Sobrien  svr4_relocate_main_executable ();
134498944Sobrien
1345130803Smarcel  if (!svr4_have_link_map_offsets ())
1346130803Smarcel    {
1347130803Smarcel      warning ("no shared library support for this OS / ABI");
1348130803Smarcel      return;
1349130803Smarcel
1350130803Smarcel    }
1351130803Smarcel
135298944Sobrien  if (!enable_break ())
135398944Sobrien    {
135498944Sobrien      warning ("shared library handler failed to enable breakpoint");
135598944Sobrien      return;
135698944Sobrien    }
135798944Sobrien
135898944Sobrien#if defined(_SCO_DS)
135998944Sobrien  /* SCO needs the loop below, other systems should be using the
136098944Sobrien     special shared library breakpoints and the shared library breakpoint
136198944Sobrien     service routine.
136298944Sobrien
136398944Sobrien     Now run the target.  It will eventually hit the breakpoint, at
136498944Sobrien     which point all of the libraries will have been mapped in and we
136598944Sobrien     can go groveling around in the dynamic linker structures to find
136698944Sobrien     out what we need to know about them. */
136798944Sobrien
136898944Sobrien  clear_proceed_status ();
1369130803Smarcel  stop_soon = STOP_QUIETLY;
137098944Sobrien  stop_signal = TARGET_SIGNAL_0;
137198944Sobrien  do
137298944Sobrien    {
137398944Sobrien      target_resume (pid_to_ptid (-1), 0, stop_signal);
137498944Sobrien      wait_for_inferior ();
137598944Sobrien    }
137698944Sobrien  while (stop_signal != TARGET_SIGNAL_TRAP);
1377130803Smarcel  stop_soon = NO_STOP_QUIETLY;
137898944Sobrien#endif /* defined(_SCO_DS) */
137998944Sobrien}
138098944Sobrien
138198944Sobrienstatic void
138298944Sobriensvr4_clear_solib (void)
138398944Sobrien{
138498944Sobrien  debug_base = 0;
138598944Sobrien}
138698944Sobrien
138798944Sobrienstatic void
138898944Sobriensvr4_free_so (struct so_list *so)
138998944Sobrien{
139098944Sobrien  xfree (so->lm_info->lm);
139198944Sobrien  xfree (so->lm_info);
139298944Sobrien}
139398944Sobrien
139498944Sobrien
139598944Sobrien/* Clear any bits of ADDR that wouldn't fit in a target-format
139698944Sobrien   data pointer.  "Data pointer" here refers to whatever sort of
139798944Sobrien   address the dynamic linker uses to manage its sections.  At the
139898944Sobrien   moment, we don't support shared libraries on any processors where
139998944Sobrien   code and data pointers are different sizes.
140098944Sobrien
140198944Sobrien   This isn't really the right solution.  What we really need here is
140298944Sobrien   a way to do arithmetic on CORE_ADDR values that respects the
140398944Sobrien   natural pointer/address correspondence.  (For example, on the MIPS,
140498944Sobrien   converting a 32-bit pointer to a 64-bit CORE_ADDR requires you to
140598944Sobrien   sign-extend the value.  There, simply truncating the bits above
140698944Sobrien   TARGET_PTR_BIT, as we do below, is no good.)  This should probably
140798944Sobrien   be a new gdbarch method or something.  */
140898944Sobrienstatic CORE_ADDR
140998944Sobriensvr4_truncate_ptr (CORE_ADDR addr)
141098944Sobrien{
141198944Sobrien  if (TARGET_PTR_BIT == sizeof (CORE_ADDR) * 8)
141298944Sobrien    /* We don't need to truncate anything, and the bit twiddling below
141398944Sobrien       will fail due to overflow problems.  */
141498944Sobrien    return addr;
141598944Sobrien  else
141698944Sobrien    return addr & (((CORE_ADDR) 1 << TARGET_PTR_BIT) - 1);
141798944Sobrien}
141898944Sobrien
141998944Sobrien
142098944Sobrienstatic void
142198944Sobriensvr4_relocate_section_addresses (struct so_list *so,
142298944Sobrien                                 struct section_table *sec)
142398944Sobrien{
142498944Sobrien  sec->addr    = svr4_truncate_ptr (sec->addr    + LM_ADDR (so));
142598944Sobrien  sec->endaddr = svr4_truncate_ptr (sec->endaddr + LM_ADDR (so));
142698944Sobrien}
142798944Sobrien
142898944Sobrien
142998944Sobrien/* Fetch a link_map_offsets structure for native targets using struct
143098944Sobrien   definitions from link.h.  See solib-legacy.c for the function
143198944Sobrien   which does the actual work.
143298944Sobrien
143398944Sobrien   Note: For non-native targets (i.e. cross-debugging situations),
143498944Sobrien   a target specific fetch_link_map_offsets() function should be
143598944Sobrien   defined and registered via set_solib_svr4_fetch_link_map_offsets().  */
143698944Sobrien
143798944Sobrienstatic struct link_map_offsets *
143898944Sobrienlegacy_fetch_link_map_offsets (void)
143998944Sobrien{
144098944Sobrien  if (legacy_svr4_fetch_link_map_offsets_hook)
144198944Sobrien    return legacy_svr4_fetch_link_map_offsets_hook ();
144298944Sobrien  else
144398944Sobrien    {
144498944Sobrien      internal_error (__FILE__, __LINE__,
144598944Sobrien                      "legacy_fetch_link_map_offsets called without legacy "
144698944Sobrien		      "link_map support enabled.");
144798944Sobrien      return 0;
144898944Sobrien    }
144998944Sobrien}
145098944Sobrien
145198944Sobrien/* Fetch a link_map_offsets structure using the method registered in the
145298944Sobrien   architecture vector.  */
145398944Sobrien
145498944Sobrienstatic struct link_map_offsets *
145598944Sobriensvr4_fetch_link_map_offsets (void)
145698944Sobrien{
145798944Sobrien  struct link_map_offsets *(*flmo)(void) =
1458130803Smarcel    gdbarch_data (current_gdbarch, fetch_link_map_offsets_gdbarch_data);
145998944Sobrien
146098944Sobrien  if (flmo == NULL)
146198944Sobrien    {
146298944Sobrien      internal_error (__FILE__, __LINE__,
146398944Sobrien                      "svr4_fetch_link_map_offsets: fetch_link_map_offsets "
146498944Sobrien		      "method not defined for this architecture.");
146598944Sobrien      return 0;
146698944Sobrien    }
146798944Sobrien  else
146898944Sobrien    return (flmo ());
146998944Sobrien}
147098944Sobrien
1471130803Smarcel/* Return 1 if a link map offset fetcher has been defined, 0 otherwise.  */
1472130803Smarcelstatic int
1473130803Smarcelsvr4_have_link_map_offsets (void)
1474130803Smarcel{
1475130803Smarcel  struct link_map_offsets *(*flmo)(void) =
1476130803Smarcel    gdbarch_data (current_gdbarch, fetch_link_map_offsets_gdbarch_data);
1477130803Smarcel  if (flmo == NULL
1478130803Smarcel      || (flmo == legacy_fetch_link_map_offsets
1479130803Smarcel          && legacy_svr4_fetch_link_map_offsets_hook == NULL))
1480130803Smarcel    return 0;
1481130803Smarcel  else
1482130803Smarcel    return 1;
1483130803Smarcel}
1484130803Smarcel
148598944Sobrien/* set_solib_svr4_fetch_link_map_offsets() is intended to be called by
148698944Sobrien   a <arch>_gdbarch_init() function.  It is used to establish an
148798944Sobrien   architecture specific link_map_offsets fetcher for the architecture
148898944Sobrien   being defined.  */
148998944Sobrien
149098944Sobrienvoid
149198944Sobrienset_solib_svr4_fetch_link_map_offsets (struct gdbarch *gdbarch,
149298944Sobrien                                       struct link_map_offsets *(*flmo) (void))
149398944Sobrien{
149498944Sobrien  set_gdbarch_data (gdbarch, fetch_link_map_offsets_gdbarch_data, flmo);
149598944Sobrien}
149698944Sobrien
1497130803Smarcel/* Initialize the architecture-specific link_map_offsets fetcher.
1498130803Smarcel   This is called after <arch>_gdbarch_init() has set up its `struct
1499130803Smarcel   gdbarch' for the new architecture, and is only called if the
1500130803Smarcel   link_map_offsets fetcher isn't already initialized (which is
1501130803Smarcel   usually done by calling set_solib_svr4_fetch_link_map_offsets()
1502130803Smarcel   above in <arch>_gdbarch_init()).  Therefore we attempt to provide a
1503130803Smarcel   reasonable alternative (for native targets anyway) if the
1504130803Smarcel   <arch>_gdbarch_init() fails to call
150598944Sobrien   set_solib_svr4_fetch_link_map_offsets().  */
150698944Sobrien
150798944Sobrienstatic void *
150898944Sobrieninit_fetch_link_map_offsets (struct gdbarch *gdbarch)
150998944Sobrien{
1510130803Smarcel  return legacy_fetch_link_map_offsets;
1511130803Smarcel}
151298944Sobrien
1513130803Smarcel/* Most OS'es that have SVR4-style ELF dynamic libraries define a
1514130803Smarcel   `struct r_debug' and a `struct link_map' that are binary compatible
1515130803Smarcel   with the origional SVR4 implementation.  */
1516130803Smarcel
1517130803Smarcel/* Fetch (and possibly build) an appropriate `struct link_map_offsets'
1518130803Smarcel   for an ILP32 SVR4 system.  */
1519130803Smarcel
1520130803Smarcelstruct link_map_offsets *
1521130803Smarcelsvr4_ilp32_fetch_link_map_offsets (void)
1522130803Smarcel{
1523130803Smarcel  static struct link_map_offsets lmo;
1524130803Smarcel  static struct link_map_offsets *lmp = NULL;
1525130803Smarcel
1526130803Smarcel  if (lmp == NULL)
1527130803Smarcel    {
1528130803Smarcel      lmp = &lmo;
1529130803Smarcel
1530130803Smarcel      /* Everything we need is in the first 8 bytes.  */
1531130803Smarcel      lmo.r_debug_size = 8;
1532130803Smarcel      lmo.r_map_offset = 4;
1533130803Smarcel      lmo.r_map_size   = 4;
1534130803Smarcel
1535130803Smarcel      /* Everything we need is in the first 20 bytes.  */
1536130803Smarcel      lmo.link_map_size = 20;
1537130803Smarcel      lmo.l_addr_offset = 0;
1538130803Smarcel      lmo.l_addr_size   = 4;
1539130803Smarcel      lmo.l_name_offset = 4;
1540130803Smarcel      lmo.l_name_size   = 4;
1541130803Smarcel      lmo.l_next_offset = 12;
1542130803Smarcel      lmo.l_next_size   = 4;
1543130803Smarcel      lmo.l_prev_offset = 16;
1544130803Smarcel      lmo.l_prev_size   = 4;
1545130803Smarcel    }
1546130803Smarcel
1547130803Smarcel  return lmp;
154898944Sobrien}
154998944Sobrien
1550130803Smarcel/* Fetch (and possibly build) an appropriate `struct link_map_offsets'
1551130803Smarcel   for an LP64 SVR4 system.  */
1552130803Smarcel
1553130803Smarcelstruct link_map_offsets *
1554130803Smarcelsvr4_lp64_fetch_link_map_offsets (void)
1555130803Smarcel{
1556130803Smarcel  static struct link_map_offsets lmo;
1557130803Smarcel  static struct link_map_offsets *lmp = NULL;
1558130803Smarcel
1559130803Smarcel  if (lmp == NULL)
1560130803Smarcel    {
1561130803Smarcel      lmp = &lmo;
1562130803Smarcel
1563130803Smarcel      /* Everything we need is in the first 16 bytes.  */
1564130803Smarcel      lmo.r_debug_size = 16;
1565130803Smarcel      lmo.r_map_offset = 8;
1566130803Smarcel      lmo.r_map_size   = 8;
1567130803Smarcel
1568130803Smarcel      /* Everything we need is in the first 40 bytes.  */
1569130803Smarcel      lmo.link_map_size = 40;
1570130803Smarcel      lmo.l_addr_offset = 0;
1571130803Smarcel      lmo.l_addr_size   = 8;
1572130803Smarcel      lmo.l_name_offset = 8;
1573130803Smarcel      lmo.l_name_size   = 8;
1574130803Smarcel      lmo.l_next_offset = 24;
1575130803Smarcel      lmo.l_next_size   = 8;
1576130803Smarcel      lmo.l_prev_offset = 32;
1577130803Smarcel      lmo.l_prev_size   = 8;
1578130803Smarcel    }
1579130803Smarcel
1580130803Smarcel  return lmp;
1581130803Smarcel}
1582130803Smarcel
1583130803Smarcel
158498944Sobrienstatic struct target_so_ops svr4_so_ops;
158598944Sobrien
1586130803Smarcelextern initialize_file_ftype _initialize_svr4_solib; /* -Wmissing-prototypes */
1587130803Smarcel
158898944Sobrienvoid
158998944Sobrien_initialize_svr4_solib (void)
159098944Sobrien{
159198944Sobrien  fetch_link_map_offsets_gdbarch_data =
1592130803Smarcel    register_gdbarch_data (init_fetch_link_map_offsets);
159398944Sobrien
159498944Sobrien  svr4_so_ops.relocate_section_addresses = svr4_relocate_section_addresses;
159598944Sobrien  svr4_so_ops.free_so = svr4_free_so;
159698944Sobrien  svr4_so_ops.clear_solib = svr4_clear_solib;
159798944Sobrien  svr4_so_ops.solib_create_inferior_hook = svr4_solib_create_inferior_hook;
159898944Sobrien  svr4_so_ops.special_symbol_handling = svr4_special_symbol_handling;
159998944Sobrien  svr4_so_ops.current_sos = svr4_current_sos;
160098944Sobrien  svr4_so_ops.open_symbol_file_object = open_symbol_file_object;
160198944Sobrien  svr4_so_ops.in_dynsym_resolve_code = svr4_in_dynsym_resolve_code;
160298944Sobrien
160398944Sobrien  /* FIXME: Don't do this here.  *_gdbarch_init() should set so_ops. */
160498944Sobrien  current_target_so_ops = &svr4_so_ops;
160598944Sobrien}
1606