xref: /dflybsd-src/contrib/gdb-7/gdb/solib-svr4.c (revision de8e141f24382815c10a4012d209bbbf7abf1112)
15796c8dcSSimon Schubert /* Handle SVR4 shared libraries for GDB, the GNU Debugger.
25796c8dcSSimon Schubert 
3*ef5ccd6cSJohn Marino    Copyright (C) 1990-2013 Free Software Foundation, Inc.
45796c8dcSSimon Schubert 
55796c8dcSSimon Schubert    This file is part of GDB.
65796c8dcSSimon Schubert 
75796c8dcSSimon Schubert    This program is free software; you can redistribute it and/or modify
85796c8dcSSimon Schubert    it under the terms of the GNU General Public License as published by
95796c8dcSSimon Schubert    the Free Software Foundation; either version 3 of the License, or
105796c8dcSSimon Schubert    (at your option) any later version.
115796c8dcSSimon Schubert 
125796c8dcSSimon Schubert    This program is distributed in the hope that it will be useful,
135796c8dcSSimon Schubert    but WITHOUT ANY WARRANTY; without even the implied warranty of
145796c8dcSSimon Schubert    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
155796c8dcSSimon Schubert    GNU General Public License for more details.
165796c8dcSSimon Schubert 
175796c8dcSSimon Schubert    You should have received a copy of the GNU General Public License
185796c8dcSSimon Schubert    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
195796c8dcSSimon Schubert 
205796c8dcSSimon Schubert #include "defs.h"
215796c8dcSSimon Schubert 
225796c8dcSSimon Schubert #include "elf/external.h"
235796c8dcSSimon Schubert #include "elf/common.h"
245796c8dcSSimon Schubert #include "elf/mips.h"
255796c8dcSSimon Schubert 
265796c8dcSSimon Schubert #include "symtab.h"
275796c8dcSSimon Schubert #include "bfd.h"
285796c8dcSSimon Schubert #include "symfile.h"
295796c8dcSSimon Schubert #include "objfiles.h"
305796c8dcSSimon Schubert #include "gdbcore.h"
315796c8dcSSimon Schubert #include "target.h"
325796c8dcSSimon Schubert #include "inferior.h"
335796c8dcSSimon Schubert #include "regcache.h"
345796c8dcSSimon Schubert #include "gdbthread.h"
355796c8dcSSimon Schubert #include "observer.h"
365796c8dcSSimon Schubert 
375796c8dcSSimon Schubert #include "gdb_assert.h"
385796c8dcSSimon Schubert 
395796c8dcSSimon Schubert #include "solist.h"
405796c8dcSSimon Schubert #include "solib.h"
415796c8dcSSimon Schubert #include "solib-svr4.h"
425796c8dcSSimon Schubert 
435796c8dcSSimon Schubert #include "bfd-target.h"
445796c8dcSSimon Schubert #include "elf-bfd.h"
455796c8dcSSimon Schubert #include "exec.h"
465796c8dcSSimon Schubert #include "auxv.h"
475796c8dcSSimon Schubert #include "exceptions.h"
48*ef5ccd6cSJohn Marino #include "gdb_bfd.h"
495796c8dcSSimon Schubert 
505796c8dcSSimon Schubert static struct link_map_offsets *svr4_fetch_link_map_offsets (void);
515796c8dcSSimon Schubert static int svr4_have_link_map_offsets (void);
52cf7f2e2dSJohn Marino static void svr4_relocate_main_executable (void);
535796c8dcSSimon Schubert 
54c50c785cSJohn Marino /* Link map info to include in an allocated so_list entry.  */
555796c8dcSSimon Schubert 
565796c8dcSSimon Schubert struct lm_info
575796c8dcSSimon Schubert   {
585796c8dcSSimon Schubert     /* Amount by which addresses in the binary should be relocated to
59a45ae5f8SJohn Marino        match the inferior.  The direct inferior value is L_ADDR_INFERIOR.
60a45ae5f8SJohn Marino        When prelinking is involved and the prelink base address changes,
61a45ae5f8SJohn Marino        we may need a different offset - the recomputed offset is in L_ADDR.
62a45ae5f8SJohn Marino        It is commonly the same value.  It is cached as we want to warn about
63a45ae5f8SJohn Marino        the difference and compute it only once.  L_ADDR is valid
64a45ae5f8SJohn Marino        iff L_ADDR_P.  */
65a45ae5f8SJohn Marino     CORE_ADDR l_addr, l_addr_inferior;
66a45ae5f8SJohn Marino     unsigned int l_addr_p : 1;
675796c8dcSSimon Schubert 
685796c8dcSSimon Schubert     /* The target location of lm.  */
695796c8dcSSimon Schubert     CORE_ADDR lm_addr;
70a45ae5f8SJohn Marino 
71a45ae5f8SJohn Marino     /* Values read in from inferior's fields of the same name.  */
72a45ae5f8SJohn Marino     CORE_ADDR l_ld, l_next, l_prev, l_name;
735796c8dcSSimon Schubert   };
745796c8dcSSimon Schubert 
755796c8dcSSimon Schubert /* On SVR4 systems, a list of symbols in the dynamic linker where
765796c8dcSSimon Schubert    GDB can try to place a breakpoint to monitor shared library
775796c8dcSSimon Schubert    events.
785796c8dcSSimon Schubert 
795796c8dcSSimon Schubert    If none of these symbols are found, or other errors occur, then
805796c8dcSSimon Schubert    SVR4 systems will fall back to using a symbol as the "startup
815796c8dcSSimon Schubert    mapping complete" breakpoint address.  */
825796c8dcSSimon Schubert 
83c50c785cSJohn Marino static const char * const solib_break_names[] =
845796c8dcSSimon Schubert {
855796c8dcSSimon Schubert   "r_debug_state",
865796c8dcSSimon Schubert   "_r_debug_state",
875796c8dcSSimon Schubert   "_dl_debug_state",
885796c8dcSSimon Schubert   "rtld_db_dlactivity",
89cf7f2e2dSJohn Marino   "__dl_rtld_db_dlactivity",
905796c8dcSSimon Schubert   "_rtld_debug_state",
915796c8dcSSimon Schubert 
925796c8dcSSimon Schubert   NULL
935796c8dcSSimon Schubert };
945796c8dcSSimon Schubert 
95c50c785cSJohn Marino static const char * const bkpt_names[] =
965796c8dcSSimon Schubert {
975796c8dcSSimon Schubert   "_start",
985796c8dcSSimon Schubert   "__start",
995796c8dcSSimon Schubert   "main",
1005796c8dcSSimon Schubert   NULL
1015796c8dcSSimon Schubert };
1025796c8dcSSimon Schubert 
103c50c785cSJohn Marino static const  char * const main_name_list[] =
1045796c8dcSSimon Schubert {
1055796c8dcSSimon Schubert   "main_$main",
1065796c8dcSSimon Schubert   NULL
1075796c8dcSSimon Schubert };
1085796c8dcSSimon Schubert 
1095796c8dcSSimon Schubert /* Return non-zero if GDB_SO_NAME and INFERIOR_SO_NAME represent
1105796c8dcSSimon Schubert    the same shared library.  */
1115796c8dcSSimon Schubert 
1125796c8dcSSimon Schubert static int
svr4_same_1(const char * gdb_so_name,const char * inferior_so_name)1135796c8dcSSimon Schubert svr4_same_1 (const char *gdb_so_name, const char *inferior_so_name)
1145796c8dcSSimon Schubert {
1155796c8dcSSimon Schubert   if (strcmp (gdb_so_name, inferior_so_name) == 0)
1165796c8dcSSimon Schubert     return 1;
1175796c8dcSSimon Schubert 
1185796c8dcSSimon Schubert   /* On Solaris, when starting inferior we think that dynamic linker is
1195796c8dcSSimon Schubert      /usr/lib/ld.so.1, but later on, the table of loaded shared libraries
1205796c8dcSSimon Schubert      contains /lib/ld.so.1.  Sometimes one file is a link to another, but
1215796c8dcSSimon Schubert      sometimes they have identical content, but are not linked to each
1225796c8dcSSimon Schubert      other.  We don't restrict this check for Solaris, but the chances
1235796c8dcSSimon Schubert      of running into this situation elsewhere are very low.  */
1245796c8dcSSimon Schubert   if (strcmp (gdb_so_name, "/usr/lib/ld.so.1") == 0
1255796c8dcSSimon Schubert       && strcmp (inferior_so_name, "/lib/ld.so.1") == 0)
1265796c8dcSSimon Schubert     return 1;
1275796c8dcSSimon Schubert 
1285796c8dcSSimon Schubert   /* Similarly, we observed the same issue with sparc64, but with
1295796c8dcSSimon Schubert      different locations.  */
1305796c8dcSSimon Schubert   if (strcmp (gdb_so_name, "/usr/lib/sparcv9/ld.so.1") == 0
1315796c8dcSSimon Schubert       && strcmp (inferior_so_name, "/lib/sparcv9/ld.so.1") == 0)
1325796c8dcSSimon Schubert     return 1;
1335796c8dcSSimon Schubert 
1345796c8dcSSimon Schubert   return 0;
1355796c8dcSSimon Schubert }
1365796c8dcSSimon Schubert 
1375796c8dcSSimon Schubert static int
svr4_same(struct so_list * gdb,struct so_list * inferior)1385796c8dcSSimon Schubert svr4_same (struct so_list *gdb, struct so_list *inferior)
1395796c8dcSSimon Schubert {
1405796c8dcSSimon Schubert   return (svr4_same_1 (gdb->so_original_name, inferior->so_original_name));
1415796c8dcSSimon Schubert }
1425796c8dcSSimon Schubert 
143a45ae5f8SJohn Marino static struct lm_info *
lm_info_read(CORE_ADDR lm_addr)144a45ae5f8SJohn Marino lm_info_read (CORE_ADDR lm_addr)
1455796c8dcSSimon Schubert {
1465796c8dcSSimon Schubert   struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
147a45ae5f8SJohn Marino   gdb_byte *lm;
148a45ae5f8SJohn Marino   struct lm_info *lm_info;
149a45ae5f8SJohn Marino   struct cleanup *back_to;
150a45ae5f8SJohn Marino 
151a45ae5f8SJohn Marino   lm = xmalloc (lmo->link_map_size);
152a45ae5f8SJohn Marino   back_to = make_cleanup (xfree, lm);
153a45ae5f8SJohn Marino 
154a45ae5f8SJohn Marino   if (target_read_memory (lm_addr, lm, lmo->link_map_size) != 0)
155a45ae5f8SJohn Marino     {
156a45ae5f8SJohn Marino       warning (_("Error reading shared library list entry at %s"),
157*ef5ccd6cSJohn Marino 	       paddress (target_gdbarch (), lm_addr)),
158a45ae5f8SJohn Marino       lm_info = NULL;
159a45ae5f8SJohn Marino     }
160a45ae5f8SJohn Marino   else
161a45ae5f8SJohn Marino     {
162*ef5ccd6cSJohn Marino       struct type *ptr_type = builtin_type (target_gdbarch ())->builtin_data_ptr;
1635796c8dcSSimon Schubert 
164a45ae5f8SJohn Marino       lm_info = xzalloc (sizeof (*lm_info));
165a45ae5f8SJohn Marino       lm_info->lm_addr = lm_addr;
166a45ae5f8SJohn Marino 
167a45ae5f8SJohn Marino       lm_info->l_addr_inferior = extract_typed_address (&lm[lmo->l_addr_offset],
168a45ae5f8SJohn Marino 							ptr_type);
169a45ae5f8SJohn Marino       lm_info->l_ld = extract_typed_address (&lm[lmo->l_ld_offset], ptr_type);
170a45ae5f8SJohn Marino       lm_info->l_next = extract_typed_address (&lm[lmo->l_next_offset],
171a45ae5f8SJohn Marino 					       ptr_type);
172a45ae5f8SJohn Marino       lm_info->l_prev = extract_typed_address (&lm[lmo->l_prev_offset],
173a45ae5f8SJohn Marino 					       ptr_type);
174a45ae5f8SJohn Marino       lm_info->l_name = extract_typed_address (&lm[lmo->l_name_offset],
1755796c8dcSSimon Schubert 					       ptr_type);
1765796c8dcSSimon Schubert     }
1775796c8dcSSimon Schubert 
178a45ae5f8SJohn Marino   do_cleanups (back_to);
179a45ae5f8SJohn Marino 
180a45ae5f8SJohn Marino   return lm_info;
181a45ae5f8SJohn Marino }
182a45ae5f8SJohn Marino 
1835796c8dcSSimon Schubert static int
has_lm_dynamic_from_link_map(void)184a45ae5f8SJohn Marino has_lm_dynamic_from_link_map (void)
1855796c8dcSSimon Schubert {
1865796c8dcSSimon Schubert   struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
1875796c8dcSSimon Schubert 
1885796c8dcSSimon Schubert   return lmo->l_ld_offset >= 0;
1895796c8dcSSimon Schubert }
1905796c8dcSSimon Schubert 
1915796c8dcSSimon Schubert static CORE_ADDR
lm_addr_check(struct so_list * so,bfd * abfd)192a45ae5f8SJohn Marino lm_addr_check (struct so_list *so, bfd *abfd)
1935796c8dcSSimon Schubert {
194a45ae5f8SJohn Marino   if (!so->lm_info->l_addr_p)
1955796c8dcSSimon Schubert     {
1965796c8dcSSimon Schubert       struct bfd_section *dyninfo_sect;
197cf7f2e2dSJohn Marino       CORE_ADDR l_addr, l_dynaddr, dynaddr;
1985796c8dcSSimon Schubert 
199a45ae5f8SJohn Marino       l_addr = so->lm_info->l_addr_inferior;
2005796c8dcSSimon Schubert 
201a45ae5f8SJohn Marino       if (! abfd || ! has_lm_dynamic_from_link_map ())
2025796c8dcSSimon Schubert 	goto set_addr;
2035796c8dcSSimon Schubert 
204a45ae5f8SJohn Marino       l_dynaddr = so->lm_info->l_ld;
2055796c8dcSSimon Schubert 
2065796c8dcSSimon Schubert       dyninfo_sect = bfd_get_section_by_name (abfd, ".dynamic");
2075796c8dcSSimon Schubert       if (dyninfo_sect == NULL)
2085796c8dcSSimon Schubert 	goto set_addr;
2095796c8dcSSimon Schubert 
2105796c8dcSSimon Schubert       dynaddr = bfd_section_vma (abfd, dyninfo_sect);
2115796c8dcSSimon Schubert 
2125796c8dcSSimon Schubert       if (dynaddr + l_addr != l_dynaddr)
2135796c8dcSSimon Schubert 	{
214cf7f2e2dSJohn Marino 	  CORE_ADDR align = 0x1000;
215cf7f2e2dSJohn Marino 	  CORE_ADDR minpagesize = align;
216cf7f2e2dSJohn Marino 
2175796c8dcSSimon Schubert 	  if (bfd_get_flavour (abfd) == bfd_target_elf_flavour)
2185796c8dcSSimon Schubert 	    {
2195796c8dcSSimon Schubert 	      Elf_Internal_Ehdr *ehdr = elf_tdata (abfd)->elf_header;
2205796c8dcSSimon Schubert 	      Elf_Internal_Phdr *phdr = elf_tdata (abfd)->phdr;
2215796c8dcSSimon Schubert 	      int i;
2225796c8dcSSimon Schubert 
2235796c8dcSSimon Schubert 	      align = 1;
2245796c8dcSSimon Schubert 
2255796c8dcSSimon Schubert 	      for (i = 0; i < ehdr->e_phnum; i++)
2265796c8dcSSimon Schubert 		if (phdr[i].p_type == PT_LOAD && phdr[i].p_align > align)
2275796c8dcSSimon Schubert 		  align = phdr[i].p_align;
228cf7f2e2dSJohn Marino 
229cf7f2e2dSJohn Marino 	      minpagesize = get_elf_backend_data (abfd)->minpagesize;
2305796c8dcSSimon Schubert 	    }
2315796c8dcSSimon Schubert 
2325796c8dcSSimon Schubert 	  /* Turn it into a mask.  */
2335796c8dcSSimon Schubert 	  align--;
2345796c8dcSSimon Schubert 
2355796c8dcSSimon Schubert 	  /* If the changes match the alignment requirements, we
2365796c8dcSSimon Schubert 	     assume we're using a core file that was generated by the
2375796c8dcSSimon Schubert 	     same binary, just prelinked with a different base offset.
2385796c8dcSSimon Schubert 	     If it doesn't match, we may have a different binary, the
2395796c8dcSSimon Schubert 	     same binary with the dynamic table loaded at an unrelated
2405796c8dcSSimon Schubert 	     location, or anything, really.  To avoid regressions,
2415796c8dcSSimon Schubert 	     don't adjust the base offset in the latter case, although
2425796c8dcSSimon Schubert 	     odds are that, if things really changed, debugging won't
243cf7f2e2dSJohn Marino 	     quite work.
244cf7f2e2dSJohn Marino 
245cf7f2e2dSJohn Marino 	     One could expect more the condition
246cf7f2e2dSJohn Marino 	       ((l_addr & align) == 0 && ((l_dynaddr - dynaddr) & align) == 0)
247cf7f2e2dSJohn Marino 	     but the one below is relaxed for PPC.  The PPC kernel supports
248cf7f2e2dSJohn Marino 	     either 4k or 64k page sizes.  To be prepared for 64k pages,
249cf7f2e2dSJohn Marino 	     PPC ELF files are built using an alignment requirement of 64k.
250cf7f2e2dSJohn Marino 	     However, when running on a kernel supporting 4k pages, the memory
251cf7f2e2dSJohn Marino 	     mapping of the library may not actually happen on a 64k boundary!
252cf7f2e2dSJohn Marino 
253cf7f2e2dSJohn Marino 	     (In the usual case where (l_addr & align) == 0, this check is
254cf7f2e2dSJohn Marino 	     equivalent to the possibly expected check above.)
255cf7f2e2dSJohn Marino 
256cf7f2e2dSJohn Marino 	     Even on PPC it must be zero-aligned at least for MINPAGESIZE.  */
257cf7f2e2dSJohn Marino 
258a45ae5f8SJohn Marino 	  l_addr = l_dynaddr - dynaddr;
259a45ae5f8SJohn Marino 
260cf7f2e2dSJohn Marino 	  if ((l_addr & (minpagesize - 1)) == 0
261cf7f2e2dSJohn Marino 	      && (l_addr & align) == ((l_dynaddr - dynaddr) & align))
2625796c8dcSSimon Schubert 	    {
263cf7f2e2dSJohn Marino 	      if (info_verbose)
264cf7f2e2dSJohn Marino 		printf_unfiltered (_("Using PIC (Position Independent Code) "
265cf7f2e2dSJohn Marino 				     "prelink displacement %s for \"%s\".\n"),
266*ef5ccd6cSJohn Marino 				   paddress (target_gdbarch (), l_addr),
267cf7f2e2dSJohn Marino 				   so->so_name);
2685796c8dcSSimon Schubert 	    }
2695796c8dcSSimon Schubert 	  else
270a45ae5f8SJohn Marino 	    {
271a45ae5f8SJohn Marino 	      /* There is no way to verify the library file matches.  prelink
272a45ae5f8SJohn Marino 		 can during prelinking of an unprelinked file (or unprelinking
273a45ae5f8SJohn Marino 		 of a prelinked file) shift the DYNAMIC segment by arbitrary
274a45ae5f8SJohn Marino 		 offset without any page size alignment.  There is no way to
275a45ae5f8SJohn Marino 		 find out the ELF header and/or Program Headers for a limited
276a45ae5f8SJohn Marino 		 verification if it they match.  One could do a verification
277a45ae5f8SJohn Marino 		 of the DYNAMIC segment.  Still the found address is the best
278a45ae5f8SJohn Marino 		 one GDB could find.  */
279a45ae5f8SJohn Marino 
2805796c8dcSSimon Schubert 	      warning (_(".dynamic section for \"%s\" "
2815796c8dcSSimon Schubert 			 "is not at the expected address "
2825796c8dcSSimon Schubert 			 "(wrong library or version mismatch?)"), so->so_name);
2835796c8dcSSimon Schubert 	    }
284a45ae5f8SJohn Marino 	}
2855796c8dcSSimon Schubert 
2865796c8dcSSimon Schubert     set_addr:
2875796c8dcSSimon Schubert       so->lm_info->l_addr = l_addr;
288a45ae5f8SJohn Marino       so->lm_info->l_addr_p = 1;
2895796c8dcSSimon Schubert     }
2905796c8dcSSimon Schubert 
2915796c8dcSSimon Schubert   return so->lm_info->l_addr;
2925796c8dcSSimon Schubert }
2935796c8dcSSimon Schubert 
294cf7f2e2dSJohn Marino /* Per pspace SVR4 specific data.  */
2955796c8dcSSimon Schubert 
2965796c8dcSSimon Schubert struct svr4_info
2975796c8dcSSimon Schubert {
298c50c785cSJohn Marino   CORE_ADDR debug_base;	/* Base of dynamic linker structures.  */
2995796c8dcSSimon Schubert 
3005796c8dcSSimon Schubert   /* Validity flag for debug_loader_offset.  */
3015796c8dcSSimon Schubert   int debug_loader_offset_p;
3025796c8dcSSimon Schubert 
3035796c8dcSSimon Schubert   /* Load address for the dynamic linker, inferred.  */
3045796c8dcSSimon Schubert   CORE_ADDR debug_loader_offset;
3055796c8dcSSimon Schubert 
3065796c8dcSSimon Schubert   /* Name of the dynamic linker, valid if debug_loader_offset_p.  */
3075796c8dcSSimon Schubert   char *debug_loader_name;
3085796c8dcSSimon Schubert 
3095796c8dcSSimon Schubert   /* Load map address for the main executable.  */
3105796c8dcSSimon Schubert   CORE_ADDR main_lm_addr;
311cf7f2e2dSJohn Marino 
312cf7f2e2dSJohn Marino   CORE_ADDR interp_text_sect_low;
313cf7f2e2dSJohn Marino   CORE_ADDR interp_text_sect_high;
314cf7f2e2dSJohn Marino   CORE_ADDR interp_plt_sect_low;
315cf7f2e2dSJohn Marino   CORE_ADDR interp_plt_sect_high;
3165796c8dcSSimon Schubert };
3175796c8dcSSimon Schubert 
318cf7f2e2dSJohn Marino /* Per-program-space data key.  */
319cf7f2e2dSJohn Marino static const struct program_space_data *solib_svr4_pspace_data;
3205796c8dcSSimon Schubert 
3215796c8dcSSimon Schubert static void
svr4_pspace_data_cleanup(struct program_space * pspace,void * arg)322cf7f2e2dSJohn Marino svr4_pspace_data_cleanup (struct program_space *pspace, void *arg)
3235796c8dcSSimon Schubert {
324cf7f2e2dSJohn Marino   struct svr4_info *info;
3255796c8dcSSimon Schubert 
326cf7f2e2dSJohn Marino   info = program_space_data (pspace, solib_svr4_pspace_data);
327cf7f2e2dSJohn Marino   xfree (info);
3285796c8dcSSimon Schubert }
3295796c8dcSSimon Schubert 
330cf7f2e2dSJohn Marino /* Get the current svr4 data.  If none is found yet, add it now.  This
331cf7f2e2dSJohn Marino    function always returns a valid object.  */
3325796c8dcSSimon Schubert 
333cf7f2e2dSJohn Marino static struct svr4_info *
get_svr4_info(void)334cf7f2e2dSJohn Marino get_svr4_info (void)
3355796c8dcSSimon Schubert {
336cf7f2e2dSJohn Marino   struct svr4_info *info;
337cf7f2e2dSJohn Marino 
338cf7f2e2dSJohn Marino   info = program_space_data (current_program_space, solib_svr4_pspace_data);
339cf7f2e2dSJohn Marino   if (info != NULL)
340cf7f2e2dSJohn Marino     return info;
341cf7f2e2dSJohn Marino 
342cf7f2e2dSJohn Marino   info = XZALLOC (struct svr4_info);
343cf7f2e2dSJohn Marino   set_program_space_data (current_program_space, solib_svr4_pspace_data, info);
344cf7f2e2dSJohn Marino   return info;
3455796c8dcSSimon Schubert }
3465796c8dcSSimon Schubert 
3475796c8dcSSimon Schubert /* Local function prototypes */
3485796c8dcSSimon Schubert 
349c50c785cSJohn Marino static int match_main (const char *);
3505796c8dcSSimon Schubert 
3515796c8dcSSimon Schubert /* Read program header TYPE from inferior memory.  The header is found
3525796c8dcSSimon Schubert    by scanning the OS auxillary vector.
3535796c8dcSSimon Schubert 
354cf7f2e2dSJohn Marino    If TYPE == -1, return the program headers instead of the contents of
355cf7f2e2dSJohn Marino    one program header.
356cf7f2e2dSJohn Marino 
3575796c8dcSSimon Schubert    Return a pointer to allocated memory holding the program header contents,
3585796c8dcSSimon Schubert    or NULL on failure.  If sucessful, and unless P_SECT_SIZE is NULL, the
3595796c8dcSSimon Schubert    size of those contents is returned to P_SECT_SIZE.  Likewise, the target
3605796c8dcSSimon Schubert    architecture size (32-bit or 64-bit) is returned to P_ARCH_SIZE.  */
3615796c8dcSSimon Schubert 
3625796c8dcSSimon Schubert static gdb_byte *
read_program_header(int type,int * p_sect_size,int * p_arch_size)3635796c8dcSSimon Schubert read_program_header (int type, int *p_sect_size, int *p_arch_size)
3645796c8dcSSimon Schubert {
365*ef5ccd6cSJohn Marino   enum bfd_endian byte_order = gdbarch_byte_order (target_gdbarch ());
366a45ae5f8SJohn Marino   CORE_ADDR at_phdr, at_phent, at_phnum, pt_phdr = 0;
3675796c8dcSSimon Schubert   int arch_size, sect_size;
3685796c8dcSSimon Schubert   CORE_ADDR sect_addr;
3695796c8dcSSimon Schubert   gdb_byte *buf;
370a45ae5f8SJohn Marino   int pt_phdr_p = 0;
3715796c8dcSSimon Schubert 
3725796c8dcSSimon Schubert   /* Get required auxv elements from target.  */
3735796c8dcSSimon Schubert   if (target_auxv_search (&current_target, AT_PHDR, &at_phdr) <= 0)
3745796c8dcSSimon Schubert     return 0;
3755796c8dcSSimon Schubert   if (target_auxv_search (&current_target, AT_PHENT, &at_phent) <= 0)
3765796c8dcSSimon Schubert     return 0;
3775796c8dcSSimon Schubert   if (target_auxv_search (&current_target, AT_PHNUM, &at_phnum) <= 0)
3785796c8dcSSimon Schubert     return 0;
3795796c8dcSSimon Schubert   if (!at_phdr || !at_phnum)
3805796c8dcSSimon Schubert     return 0;
3815796c8dcSSimon Schubert 
3825796c8dcSSimon Schubert   /* Determine ELF architecture type.  */
3835796c8dcSSimon Schubert   if (at_phent == sizeof (Elf32_External_Phdr))
3845796c8dcSSimon Schubert     arch_size = 32;
3855796c8dcSSimon Schubert   else if (at_phent == sizeof (Elf64_External_Phdr))
3865796c8dcSSimon Schubert     arch_size = 64;
3875796c8dcSSimon Schubert   else
3885796c8dcSSimon Schubert     return 0;
3895796c8dcSSimon Schubert 
390cf7f2e2dSJohn Marino   /* Find the requested segment.  */
391cf7f2e2dSJohn Marino   if (type == -1)
392cf7f2e2dSJohn Marino     {
393cf7f2e2dSJohn Marino       sect_addr = at_phdr;
394cf7f2e2dSJohn Marino       sect_size = at_phent * at_phnum;
395cf7f2e2dSJohn Marino     }
396cf7f2e2dSJohn Marino   else if (arch_size == 32)
3975796c8dcSSimon Schubert     {
3985796c8dcSSimon Schubert       Elf32_External_Phdr phdr;
3995796c8dcSSimon Schubert       int i;
4005796c8dcSSimon Schubert 
4015796c8dcSSimon Schubert       /* Search for requested PHDR.  */
4025796c8dcSSimon Schubert       for (i = 0; i < at_phnum; i++)
4035796c8dcSSimon Schubert 	{
404a45ae5f8SJohn Marino 	  int p_type;
405a45ae5f8SJohn Marino 
4065796c8dcSSimon Schubert 	  if (target_read_memory (at_phdr + i * sizeof (phdr),
4075796c8dcSSimon Schubert 				  (gdb_byte *)&phdr, sizeof (phdr)))
4085796c8dcSSimon Schubert 	    return 0;
4095796c8dcSSimon Schubert 
410a45ae5f8SJohn Marino 	  p_type = extract_unsigned_integer ((gdb_byte *) phdr.p_type,
411a45ae5f8SJohn Marino 					     4, byte_order);
412a45ae5f8SJohn Marino 
413a45ae5f8SJohn Marino 	  if (p_type == PT_PHDR)
414a45ae5f8SJohn Marino 	    {
415a45ae5f8SJohn Marino 	      pt_phdr_p = 1;
416a45ae5f8SJohn Marino 	      pt_phdr = extract_unsigned_integer ((gdb_byte *) phdr.p_vaddr,
417a45ae5f8SJohn Marino 						  4, byte_order);
418a45ae5f8SJohn Marino 	    }
419a45ae5f8SJohn Marino 
420a45ae5f8SJohn Marino 	  if (p_type == type)
4215796c8dcSSimon Schubert 	    break;
4225796c8dcSSimon Schubert 	}
4235796c8dcSSimon Schubert 
4245796c8dcSSimon Schubert       if (i == at_phnum)
4255796c8dcSSimon Schubert 	return 0;
4265796c8dcSSimon Schubert 
4275796c8dcSSimon Schubert       /* Retrieve address and size.  */
4285796c8dcSSimon Schubert       sect_addr = extract_unsigned_integer ((gdb_byte *)phdr.p_vaddr,
4295796c8dcSSimon Schubert 					    4, byte_order);
4305796c8dcSSimon Schubert       sect_size = extract_unsigned_integer ((gdb_byte *)phdr.p_memsz,
4315796c8dcSSimon Schubert 					    4, byte_order);
4325796c8dcSSimon Schubert     }
4335796c8dcSSimon Schubert   else
4345796c8dcSSimon Schubert     {
4355796c8dcSSimon Schubert       Elf64_External_Phdr phdr;
4365796c8dcSSimon Schubert       int i;
4375796c8dcSSimon Schubert 
4385796c8dcSSimon Schubert       /* Search for requested PHDR.  */
4395796c8dcSSimon Schubert       for (i = 0; i < at_phnum; i++)
4405796c8dcSSimon Schubert 	{
441a45ae5f8SJohn Marino 	  int p_type;
442a45ae5f8SJohn Marino 
4435796c8dcSSimon Schubert 	  if (target_read_memory (at_phdr + i * sizeof (phdr),
4445796c8dcSSimon Schubert 				  (gdb_byte *)&phdr, sizeof (phdr)))
4455796c8dcSSimon Schubert 	    return 0;
4465796c8dcSSimon Schubert 
447a45ae5f8SJohn Marino 	  p_type = extract_unsigned_integer ((gdb_byte *) phdr.p_type,
448a45ae5f8SJohn Marino 					     4, byte_order);
449a45ae5f8SJohn Marino 
450a45ae5f8SJohn Marino 	  if (p_type == PT_PHDR)
451a45ae5f8SJohn Marino 	    {
452a45ae5f8SJohn Marino 	      pt_phdr_p = 1;
453a45ae5f8SJohn Marino 	      pt_phdr = extract_unsigned_integer ((gdb_byte *) phdr.p_vaddr,
454a45ae5f8SJohn Marino 						  8, byte_order);
455a45ae5f8SJohn Marino 	    }
456a45ae5f8SJohn Marino 
457a45ae5f8SJohn Marino 	  if (p_type == type)
4585796c8dcSSimon Schubert 	    break;
4595796c8dcSSimon Schubert 	}
4605796c8dcSSimon Schubert 
4615796c8dcSSimon Schubert       if (i == at_phnum)
4625796c8dcSSimon Schubert 	return 0;
4635796c8dcSSimon Schubert 
4645796c8dcSSimon Schubert       /* Retrieve address and size.  */
4655796c8dcSSimon Schubert       sect_addr = extract_unsigned_integer ((gdb_byte *)phdr.p_vaddr,
4665796c8dcSSimon Schubert 					    8, byte_order);
4675796c8dcSSimon Schubert       sect_size = extract_unsigned_integer ((gdb_byte *)phdr.p_memsz,
4685796c8dcSSimon Schubert 					    8, byte_order);
4695796c8dcSSimon Schubert     }
4705796c8dcSSimon Schubert 
471a45ae5f8SJohn Marino   /* PT_PHDR is optional, but we really need it
472a45ae5f8SJohn Marino      for PIE to make this work in general.  */
473a45ae5f8SJohn Marino 
474a45ae5f8SJohn Marino   if (pt_phdr_p)
475a45ae5f8SJohn Marino     {
476a45ae5f8SJohn Marino       /* at_phdr is real address in memory. pt_phdr is what pheader says it is.
477a45ae5f8SJohn Marino 	 Relocation offset is the difference between the two. */
478a45ae5f8SJohn Marino       sect_addr = sect_addr + (at_phdr - pt_phdr);
479a45ae5f8SJohn Marino     }
480a45ae5f8SJohn Marino 
4815796c8dcSSimon Schubert   /* Read in requested program header.  */
4825796c8dcSSimon Schubert   buf = xmalloc (sect_size);
4835796c8dcSSimon Schubert   if (target_read_memory (sect_addr, buf, sect_size))
4845796c8dcSSimon Schubert     {
4855796c8dcSSimon Schubert       xfree (buf);
4865796c8dcSSimon Schubert       return NULL;
4875796c8dcSSimon Schubert     }
4885796c8dcSSimon Schubert 
4895796c8dcSSimon Schubert   if (p_arch_size)
4905796c8dcSSimon Schubert     *p_arch_size = arch_size;
4915796c8dcSSimon Schubert   if (p_sect_size)
4925796c8dcSSimon Schubert     *p_sect_size = sect_size;
4935796c8dcSSimon Schubert 
4945796c8dcSSimon Schubert   return buf;
4955796c8dcSSimon Schubert }
4965796c8dcSSimon Schubert 
4975796c8dcSSimon Schubert 
4985796c8dcSSimon Schubert /* Return program interpreter string.  */
4995796c8dcSSimon Schubert static gdb_byte *
find_program_interpreter(void)5005796c8dcSSimon Schubert find_program_interpreter (void)
5015796c8dcSSimon Schubert {
5025796c8dcSSimon Schubert   gdb_byte *buf = NULL;
5035796c8dcSSimon Schubert 
5045796c8dcSSimon Schubert   /* If we have an exec_bfd, use its section table.  */
5055796c8dcSSimon Schubert   if (exec_bfd
5065796c8dcSSimon Schubert       && bfd_get_flavour (exec_bfd) == bfd_target_elf_flavour)
5075796c8dcSSimon Schubert    {
5085796c8dcSSimon Schubert      struct bfd_section *interp_sect;
5095796c8dcSSimon Schubert 
5105796c8dcSSimon Schubert      interp_sect = bfd_get_section_by_name (exec_bfd, ".interp");
5115796c8dcSSimon Schubert      if (interp_sect != NULL)
5125796c8dcSSimon Schubert       {
5135796c8dcSSimon Schubert 	int sect_size = bfd_section_size (exec_bfd, interp_sect);
5145796c8dcSSimon Schubert 
5155796c8dcSSimon Schubert 	buf = xmalloc (sect_size);
5165796c8dcSSimon Schubert 	bfd_get_section_contents (exec_bfd, interp_sect, buf, 0, sect_size);
5175796c8dcSSimon Schubert       }
5185796c8dcSSimon Schubert    }
5195796c8dcSSimon Schubert 
5205796c8dcSSimon Schubert   /* If we didn't find it, use the target auxillary vector.  */
5215796c8dcSSimon Schubert   if (!buf)
5225796c8dcSSimon Schubert     buf = read_program_header (PT_INTERP, NULL, NULL);
5235796c8dcSSimon Schubert 
5245796c8dcSSimon Schubert   return buf;
5255796c8dcSSimon Schubert }
5265796c8dcSSimon Schubert 
5275796c8dcSSimon Schubert 
5285796c8dcSSimon Schubert /* Scan for DYNTAG in .dynamic section of ABFD.  If DYNTAG is found 1 is
5295796c8dcSSimon Schubert    returned and the corresponding PTR is set.  */
5305796c8dcSSimon Schubert 
5315796c8dcSSimon Schubert static int
scan_dyntag(int dyntag,bfd * abfd,CORE_ADDR * ptr)5325796c8dcSSimon Schubert scan_dyntag (int dyntag, bfd *abfd, CORE_ADDR *ptr)
5335796c8dcSSimon Schubert {
5345796c8dcSSimon Schubert   int arch_size, step, sect_size;
5355796c8dcSSimon Schubert   long dyn_tag;
5365796c8dcSSimon Schubert   CORE_ADDR dyn_ptr, dyn_addr;
5375796c8dcSSimon Schubert   gdb_byte *bufend, *bufstart, *buf;
5385796c8dcSSimon Schubert   Elf32_External_Dyn *x_dynp_32;
5395796c8dcSSimon Schubert   Elf64_External_Dyn *x_dynp_64;
5405796c8dcSSimon Schubert   struct bfd_section *sect;
541cf7f2e2dSJohn Marino   struct target_section *target_section;
5425796c8dcSSimon Schubert 
5435796c8dcSSimon Schubert   if (abfd == NULL)
5445796c8dcSSimon Schubert     return 0;
5455796c8dcSSimon Schubert 
5465796c8dcSSimon Schubert   if (bfd_get_flavour (abfd) != bfd_target_elf_flavour)
5475796c8dcSSimon Schubert     return 0;
5485796c8dcSSimon Schubert 
5495796c8dcSSimon Schubert   arch_size = bfd_get_arch_size (abfd);
5505796c8dcSSimon Schubert   if (arch_size == -1)
5515796c8dcSSimon Schubert     return 0;
5525796c8dcSSimon Schubert 
5535796c8dcSSimon Schubert   /* Find the start address of the .dynamic section.  */
5545796c8dcSSimon Schubert   sect = bfd_get_section_by_name (abfd, ".dynamic");
5555796c8dcSSimon Schubert   if (sect == NULL)
5565796c8dcSSimon Schubert     return 0;
557cf7f2e2dSJohn Marino 
558cf7f2e2dSJohn Marino   for (target_section = current_target_sections->sections;
559cf7f2e2dSJohn Marino        target_section < current_target_sections->sections_end;
560cf7f2e2dSJohn Marino        target_section++)
561cf7f2e2dSJohn Marino     if (sect == target_section->the_bfd_section)
562cf7f2e2dSJohn Marino       break;
563cf7f2e2dSJohn Marino   if (target_section < current_target_sections->sections_end)
564cf7f2e2dSJohn Marino     dyn_addr = target_section->addr;
565cf7f2e2dSJohn Marino   else
566cf7f2e2dSJohn Marino     {
567cf7f2e2dSJohn Marino       /* ABFD may come from OBJFILE acting only as a symbol file without being
568cf7f2e2dSJohn Marino 	 loaded into the target (see add_symbol_file_command).  This case is
569cf7f2e2dSJohn Marino 	 such fallback to the file VMA address without the possibility of
570cf7f2e2dSJohn Marino 	 having the section relocated to its actual in-memory address.  */
571cf7f2e2dSJohn Marino 
5725796c8dcSSimon Schubert       dyn_addr = bfd_section_vma (abfd, sect);
573cf7f2e2dSJohn Marino     }
5745796c8dcSSimon Schubert 
5755796c8dcSSimon Schubert   /* Read in .dynamic from the BFD.  We will get the actual value
5765796c8dcSSimon Schubert      from memory later.  */
5775796c8dcSSimon Schubert   sect_size = bfd_section_size (abfd, sect);
5785796c8dcSSimon Schubert   buf = bufstart = alloca (sect_size);
5795796c8dcSSimon Schubert   if (!bfd_get_section_contents (abfd, sect,
5805796c8dcSSimon Schubert 				 buf, 0, sect_size))
5815796c8dcSSimon Schubert     return 0;
5825796c8dcSSimon Schubert 
5835796c8dcSSimon Schubert   /* Iterate over BUF and scan for DYNTAG.  If found, set PTR and return.  */
5845796c8dcSSimon Schubert   step = (arch_size == 32) ? sizeof (Elf32_External_Dyn)
5855796c8dcSSimon Schubert 			   : sizeof (Elf64_External_Dyn);
5865796c8dcSSimon Schubert   for (bufend = buf + sect_size;
5875796c8dcSSimon Schubert        buf < bufend;
5885796c8dcSSimon Schubert        buf += step)
5895796c8dcSSimon Schubert   {
5905796c8dcSSimon Schubert     if (arch_size == 32)
5915796c8dcSSimon Schubert       {
5925796c8dcSSimon Schubert 	x_dynp_32 = (Elf32_External_Dyn *) buf;
5935796c8dcSSimon Schubert 	dyn_tag = bfd_h_get_32 (abfd, (bfd_byte *) x_dynp_32->d_tag);
5945796c8dcSSimon Schubert 	dyn_ptr = bfd_h_get_32 (abfd, (bfd_byte *) x_dynp_32->d_un.d_ptr);
5955796c8dcSSimon Schubert       }
5965796c8dcSSimon Schubert     else
5975796c8dcSSimon Schubert       {
5985796c8dcSSimon Schubert 	x_dynp_64 = (Elf64_External_Dyn *) buf;
5995796c8dcSSimon Schubert 	dyn_tag = bfd_h_get_64 (abfd, (bfd_byte *) x_dynp_64->d_tag);
6005796c8dcSSimon Schubert 	dyn_ptr = bfd_h_get_64 (abfd, (bfd_byte *) x_dynp_64->d_un.d_ptr);
6015796c8dcSSimon Schubert       }
6025796c8dcSSimon Schubert      if (dyn_tag == DT_NULL)
6035796c8dcSSimon Schubert        return 0;
6045796c8dcSSimon Schubert      if (dyn_tag == dyntag)
6055796c8dcSSimon Schubert        {
6065796c8dcSSimon Schubert 	 /* If requested, try to read the runtime value of this .dynamic
6075796c8dcSSimon Schubert 	    entry.  */
6085796c8dcSSimon Schubert 	 if (ptr)
6095796c8dcSSimon Schubert 	   {
6105796c8dcSSimon Schubert 	     struct type *ptr_type;
6115796c8dcSSimon Schubert 	     gdb_byte ptr_buf[8];
6125796c8dcSSimon Schubert 	     CORE_ADDR ptr_addr;
6135796c8dcSSimon Schubert 
614*ef5ccd6cSJohn Marino 	     ptr_type = builtin_type (target_gdbarch ())->builtin_data_ptr;
6155796c8dcSSimon Schubert 	     ptr_addr = dyn_addr + (buf - bufstart) + arch_size / 8;
6165796c8dcSSimon Schubert 	     if (target_read_memory (ptr_addr, ptr_buf, arch_size / 8) == 0)
6175796c8dcSSimon Schubert 	       dyn_ptr = extract_typed_address (ptr_buf, ptr_type);
6185796c8dcSSimon Schubert 	     *ptr = dyn_ptr;
6195796c8dcSSimon Schubert 	   }
6205796c8dcSSimon Schubert 	 return 1;
6215796c8dcSSimon Schubert        }
6225796c8dcSSimon Schubert   }
6235796c8dcSSimon Schubert 
6245796c8dcSSimon Schubert   return 0;
6255796c8dcSSimon Schubert }
6265796c8dcSSimon Schubert 
6275796c8dcSSimon Schubert /* Scan for DYNTAG in .dynamic section of the target's main executable,
6285796c8dcSSimon Schubert    found by consulting the OS auxillary vector.  If DYNTAG is found 1 is
6295796c8dcSSimon Schubert    returned and the corresponding PTR is set.  */
6305796c8dcSSimon Schubert 
6315796c8dcSSimon Schubert static int
scan_dyntag_auxv(int dyntag,CORE_ADDR * ptr)6325796c8dcSSimon Schubert scan_dyntag_auxv (int dyntag, CORE_ADDR *ptr)
6335796c8dcSSimon Schubert {
634*ef5ccd6cSJohn Marino   enum bfd_endian byte_order = gdbarch_byte_order (target_gdbarch ());
6355796c8dcSSimon Schubert   int sect_size, arch_size, step;
6365796c8dcSSimon Schubert   long dyn_tag;
6375796c8dcSSimon Schubert   CORE_ADDR dyn_ptr;
6385796c8dcSSimon Schubert   gdb_byte *bufend, *bufstart, *buf;
6395796c8dcSSimon Schubert 
6405796c8dcSSimon Schubert   /* Read in .dynamic section.  */
6415796c8dcSSimon Schubert   buf = bufstart = read_program_header (PT_DYNAMIC, &sect_size, &arch_size);
6425796c8dcSSimon Schubert   if (!buf)
6435796c8dcSSimon Schubert     return 0;
6445796c8dcSSimon Schubert 
6455796c8dcSSimon Schubert   /* Iterate over BUF and scan for DYNTAG.  If found, set PTR and return.  */
6465796c8dcSSimon Schubert   step = (arch_size == 32) ? sizeof (Elf32_External_Dyn)
6475796c8dcSSimon Schubert 			   : sizeof (Elf64_External_Dyn);
6485796c8dcSSimon Schubert   for (bufend = buf + sect_size;
6495796c8dcSSimon Schubert        buf < bufend;
6505796c8dcSSimon Schubert        buf += step)
6515796c8dcSSimon Schubert   {
6525796c8dcSSimon Schubert     if (arch_size == 32)
6535796c8dcSSimon Schubert       {
6545796c8dcSSimon Schubert 	Elf32_External_Dyn *dynp = (Elf32_External_Dyn *) buf;
655cf7f2e2dSJohn Marino 
6565796c8dcSSimon Schubert 	dyn_tag = extract_unsigned_integer ((gdb_byte *) dynp->d_tag,
6575796c8dcSSimon Schubert 					    4, byte_order);
6585796c8dcSSimon Schubert 	dyn_ptr = extract_unsigned_integer ((gdb_byte *) dynp->d_un.d_ptr,
6595796c8dcSSimon Schubert 					    4, byte_order);
6605796c8dcSSimon Schubert       }
6615796c8dcSSimon Schubert     else
6625796c8dcSSimon Schubert       {
6635796c8dcSSimon Schubert 	Elf64_External_Dyn *dynp = (Elf64_External_Dyn *) buf;
664cf7f2e2dSJohn Marino 
6655796c8dcSSimon Schubert 	dyn_tag = extract_unsigned_integer ((gdb_byte *) dynp->d_tag,
6665796c8dcSSimon Schubert 					    8, byte_order);
6675796c8dcSSimon Schubert 	dyn_ptr = extract_unsigned_integer ((gdb_byte *) dynp->d_un.d_ptr,
6685796c8dcSSimon Schubert 					    8, byte_order);
6695796c8dcSSimon Schubert       }
6705796c8dcSSimon Schubert     if (dyn_tag == DT_NULL)
6715796c8dcSSimon Schubert       break;
6725796c8dcSSimon Schubert 
6735796c8dcSSimon Schubert     if (dyn_tag == dyntag)
6745796c8dcSSimon Schubert       {
6755796c8dcSSimon Schubert 	if (ptr)
6765796c8dcSSimon Schubert 	  *ptr = dyn_ptr;
6775796c8dcSSimon Schubert 
6785796c8dcSSimon Schubert 	xfree (bufstart);
6795796c8dcSSimon Schubert 	return 1;
6805796c8dcSSimon Schubert       }
6815796c8dcSSimon Schubert   }
6825796c8dcSSimon Schubert 
6835796c8dcSSimon Schubert   xfree (bufstart);
6845796c8dcSSimon Schubert   return 0;
6855796c8dcSSimon Schubert }
6865796c8dcSSimon Schubert 
687a45ae5f8SJohn Marino /* Locate the base address of dynamic linker structs for SVR4 elf
688a45ae5f8SJohn Marino    targets.
6895796c8dcSSimon Schubert 
6905796c8dcSSimon Schubert    For SVR4 elf targets the address of the dynamic linker's runtime
6915796c8dcSSimon Schubert    structure is contained within the dynamic info section in the
6925796c8dcSSimon Schubert    executable file.  The dynamic section is also mapped into the
6935796c8dcSSimon Schubert    inferior address space.  Because the runtime loader fills in the
6945796c8dcSSimon Schubert    real address before starting the inferior, we have to read in the
6955796c8dcSSimon Schubert    dynamic info section from the inferior address space.
6965796c8dcSSimon Schubert    If there are any errors while trying to find the address, we
697a45ae5f8SJohn Marino    silently return 0, otherwise the found address is returned.  */
6985796c8dcSSimon Schubert 
6995796c8dcSSimon Schubert static CORE_ADDR
elf_locate_base(void)7005796c8dcSSimon Schubert elf_locate_base (void)
7015796c8dcSSimon Schubert {
7025796c8dcSSimon Schubert   struct minimal_symbol *msymbol;
7035796c8dcSSimon Schubert   CORE_ADDR dyn_ptr;
7045796c8dcSSimon Schubert 
7055796c8dcSSimon Schubert   /* Look for DT_MIPS_RLD_MAP first.  MIPS executables use this
7065796c8dcSSimon Schubert      instead of DT_DEBUG, although they sometimes contain an unused
7075796c8dcSSimon Schubert      DT_DEBUG.  */
7085796c8dcSSimon Schubert   if (scan_dyntag (DT_MIPS_RLD_MAP, exec_bfd, &dyn_ptr)
7095796c8dcSSimon Schubert       || scan_dyntag_auxv (DT_MIPS_RLD_MAP, &dyn_ptr))
7105796c8dcSSimon Schubert     {
711*ef5ccd6cSJohn Marino       struct type *ptr_type = builtin_type (target_gdbarch ())->builtin_data_ptr;
7125796c8dcSSimon Schubert       gdb_byte *pbuf;
7135796c8dcSSimon Schubert       int pbuf_size = TYPE_LENGTH (ptr_type);
714cf7f2e2dSJohn Marino 
7155796c8dcSSimon Schubert       pbuf = alloca (pbuf_size);
7165796c8dcSSimon Schubert       /* DT_MIPS_RLD_MAP contains a pointer to the address
7175796c8dcSSimon Schubert 	 of the dynamic link structure.  */
7185796c8dcSSimon Schubert       if (target_read_memory (dyn_ptr, pbuf, pbuf_size))
7195796c8dcSSimon Schubert 	return 0;
7205796c8dcSSimon Schubert       return extract_typed_address (pbuf, ptr_type);
7215796c8dcSSimon Schubert     }
7225796c8dcSSimon Schubert 
7235796c8dcSSimon Schubert   /* Find DT_DEBUG.  */
7245796c8dcSSimon Schubert   if (scan_dyntag (DT_DEBUG, exec_bfd, &dyn_ptr)
7255796c8dcSSimon Schubert       || scan_dyntag_auxv (DT_DEBUG, &dyn_ptr))
7265796c8dcSSimon Schubert     return dyn_ptr;
7275796c8dcSSimon Schubert 
7285796c8dcSSimon Schubert   /* This may be a static executable.  Look for the symbol
7295796c8dcSSimon Schubert      conventionally named _r_debug, as a last resort.  */
7305796c8dcSSimon Schubert   msymbol = lookup_minimal_symbol ("_r_debug", NULL, symfile_objfile);
7315796c8dcSSimon Schubert   if (msymbol != NULL)
7325796c8dcSSimon Schubert     return SYMBOL_VALUE_ADDRESS (msymbol);
7335796c8dcSSimon Schubert 
7345796c8dcSSimon Schubert   /* DT_DEBUG entry not found.  */
7355796c8dcSSimon Schubert   return 0;
7365796c8dcSSimon Schubert }
7375796c8dcSSimon Schubert 
738a45ae5f8SJohn Marino /* Locate the base address of dynamic linker structs.
7395796c8dcSSimon Schubert 
7405796c8dcSSimon Schubert    For both the SunOS and SVR4 shared library implementations, if the
7415796c8dcSSimon Schubert    inferior executable has been linked dynamically, there is a single
7425796c8dcSSimon Schubert    address somewhere in the inferior's data space which is the key to
7435796c8dcSSimon Schubert    locating all of the dynamic linker's runtime structures.  This
7445796c8dcSSimon Schubert    address is the value of the debug base symbol.  The job of this
7455796c8dcSSimon Schubert    function is to find and return that address, or to return 0 if there
7465796c8dcSSimon Schubert    is no such address (the executable is statically linked for example).
7475796c8dcSSimon Schubert 
7485796c8dcSSimon Schubert    For SunOS, the job is almost trivial, since the dynamic linker and
7495796c8dcSSimon Schubert    all of it's structures are statically linked to the executable at
7505796c8dcSSimon Schubert    link time.  Thus the symbol for the address we are looking for has
7515796c8dcSSimon Schubert    already been added to the minimal symbol table for the executable's
7525796c8dcSSimon Schubert    objfile at the time the symbol file's symbols were read, and all we
7535796c8dcSSimon Schubert    have to do is look it up there.  Note that we explicitly do NOT want
7545796c8dcSSimon Schubert    to find the copies in the shared library.
7555796c8dcSSimon Schubert 
7565796c8dcSSimon Schubert    The SVR4 version is a bit more complicated because the address
7575796c8dcSSimon Schubert    is contained somewhere in the dynamic info section.  We have to go
7585796c8dcSSimon Schubert    to a lot more work to discover the address of the debug base symbol.
7595796c8dcSSimon Schubert    Because of this complexity, we cache the value we find and return that
7605796c8dcSSimon Schubert    value on subsequent invocations.  Note there is no copy in the
761a45ae5f8SJohn Marino    executable symbol tables.  */
7625796c8dcSSimon Schubert 
7635796c8dcSSimon Schubert static CORE_ADDR
locate_base(struct svr4_info * info)7645796c8dcSSimon Schubert locate_base (struct svr4_info *info)
7655796c8dcSSimon Schubert {
7665796c8dcSSimon Schubert   /* Check to see if we have a currently valid address, and if so, avoid
7675796c8dcSSimon Schubert      doing all this work again and just return the cached address.  If
7685796c8dcSSimon Schubert      we have no cached address, try to locate it in the dynamic info
7695796c8dcSSimon Schubert      section for ELF executables.  There's no point in doing any of this
7705796c8dcSSimon Schubert      though if we don't have some link map offsets to work with.  */
7715796c8dcSSimon Schubert 
7725796c8dcSSimon Schubert   if (info->debug_base == 0 && svr4_have_link_map_offsets ())
7735796c8dcSSimon Schubert     info->debug_base = elf_locate_base ();
7745796c8dcSSimon Schubert   return info->debug_base;
7755796c8dcSSimon Schubert }
7765796c8dcSSimon Schubert 
7775796c8dcSSimon Schubert /* Find the first element in the inferior's dynamic link map, and
778cf7f2e2dSJohn Marino    return its address in the inferior.  Return zero if the address
779cf7f2e2dSJohn Marino    could not be determined.
7805796c8dcSSimon Schubert 
7815796c8dcSSimon Schubert    FIXME: Perhaps we should validate the info somehow, perhaps by
7825796c8dcSSimon Schubert    checking r_version for a known version number, or r_state for
7835796c8dcSSimon Schubert    RT_CONSISTENT.  */
7845796c8dcSSimon Schubert 
7855796c8dcSSimon Schubert static CORE_ADDR
solib_svr4_r_map(struct svr4_info * info)7865796c8dcSSimon Schubert solib_svr4_r_map (struct svr4_info *info)
7875796c8dcSSimon Schubert {
7885796c8dcSSimon Schubert   struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
789*ef5ccd6cSJohn Marino   struct type *ptr_type = builtin_type (target_gdbarch ())->builtin_data_ptr;
790cf7f2e2dSJohn Marino   CORE_ADDR addr = 0;
791cf7f2e2dSJohn Marino   volatile struct gdb_exception ex;
7925796c8dcSSimon Schubert 
793cf7f2e2dSJohn Marino   TRY_CATCH (ex, RETURN_MASK_ERROR)
794cf7f2e2dSJohn Marino     {
795cf7f2e2dSJohn Marino       addr = read_memory_typed_address (info->debug_base + lmo->r_map_offset,
7965796c8dcSSimon Schubert                                         ptr_type);
7975796c8dcSSimon Schubert     }
798cf7f2e2dSJohn Marino   exception_print (gdb_stderr, ex);
799cf7f2e2dSJohn Marino   return addr;
800cf7f2e2dSJohn Marino }
8015796c8dcSSimon Schubert 
8025796c8dcSSimon Schubert /* Find r_brk from the inferior's debug base.  */
8035796c8dcSSimon Schubert 
8045796c8dcSSimon Schubert static CORE_ADDR
solib_svr4_r_brk(struct svr4_info * info)8055796c8dcSSimon Schubert solib_svr4_r_brk (struct svr4_info *info)
8065796c8dcSSimon Schubert {
8075796c8dcSSimon Schubert   struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
808*ef5ccd6cSJohn Marino   struct type *ptr_type = builtin_type (target_gdbarch ())->builtin_data_ptr;
8095796c8dcSSimon Schubert 
8105796c8dcSSimon Schubert   return read_memory_typed_address (info->debug_base + lmo->r_brk_offset,
8115796c8dcSSimon Schubert 				    ptr_type);
8125796c8dcSSimon Schubert }
8135796c8dcSSimon Schubert 
8145796c8dcSSimon Schubert /* Find the link map for the dynamic linker (if it is not in the
8155796c8dcSSimon Schubert    normal list of loaded shared objects).  */
8165796c8dcSSimon Schubert 
8175796c8dcSSimon Schubert static CORE_ADDR
solib_svr4_r_ldsomap(struct svr4_info * info)8185796c8dcSSimon Schubert solib_svr4_r_ldsomap (struct svr4_info *info)
8195796c8dcSSimon Schubert {
8205796c8dcSSimon Schubert   struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
821*ef5ccd6cSJohn Marino   struct type *ptr_type = builtin_type (target_gdbarch ())->builtin_data_ptr;
822*ef5ccd6cSJohn Marino   enum bfd_endian byte_order = gdbarch_byte_order (target_gdbarch ());
8235796c8dcSSimon Schubert   ULONGEST version;
8245796c8dcSSimon Schubert 
8255796c8dcSSimon Schubert   /* Check version, and return zero if `struct r_debug' doesn't have
8265796c8dcSSimon Schubert      the r_ldsomap member.  */
8275796c8dcSSimon Schubert   version
8285796c8dcSSimon Schubert     = read_memory_unsigned_integer (info->debug_base + lmo->r_version_offset,
8295796c8dcSSimon Schubert 				    lmo->r_version_size, byte_order);
8305796c8dcSSimon Schubert   if (version < 2 || lmo->r_ldsomap_offset == -1)
8315796c8dcSSimon Schubert     return 0;
8325796c8dcSSimon Schubert 
8335796c8dcSSimon Schubert   return read_memory_typed_address (info->debug_base + lmo->r_ldsomap_offset,
8345796c8dcSSimon Schubert 				    ptr_type);
8355796c8dcSSimon Schubert }
8365796c8dcSSimon Schubert 
837cf7f2e2dSJohn Marino /* On Solaris systems with some versions of the dynamic linker,
838cf7f2e2dSJohn Marino    ld.so's l_name pointer points to the SONAME in the string table
839cf7f2e2dSJohn Marino    rather than into writable memory.  So that GDB can find shared
840cf7f2e2dSJohn Marino    libraries when loading a core file generated by gcore, ensure that
841cf7f2e2dSJohn Marino    memory areas containing the l_name string are saved in the core
842cf7f2e2dSJohn Marino    file.  */
843cf7f2e2dSJohn Marino 
844cf7f2e2dSJohn Marino static int
svr4_keep_data_in_core(CORE_ADDR vaddr,unsigned long size)845cf7f2e2dSJohn Marino svr4_keep_data_in_core (CORE_ADDR vaddr, unsigned long size)
846cf7f2e2dSJohn Marino {
847cf7f2e2dSJohn Marino   struct svr4_info *info;
848cf7f2e2dSJohn Marino   CORE_ADDR ldsomap;
849cf7f2e2dSJohn Marino   struct so_list *new;
850cf7f2e2dSJohn Marino   struct cleanup *old_chain;
851a45ae5f8SJohn Marino   CORE_ADDR name_lm;
852cf7f2e2dSJohn Marino 
853cf7f2e2dSJohn Marino   info = get_svr4_info ();
854cf7f2e2dSJohn Marino 
855cf7f2e2dSJohn Marino   info->debug_base = 0;
856cf7f2e2dSJohn Marino   locate_base (info);
857cf7f2e2dSJohn Marino   if (!info->debug_base)
858cf7f2e2dSJohn Marino     return 0;
859cf7f2e2dSJohn Marino 
860cf7f2e2dSJohn Marino   ldsomap = solib_svr4_r_ldsomap (info);
861cf7f2e2dSJohn Marino   if (!ldsomap)
862cf7f2e2dSJohn Marino     return 0;
863cf7f2e2dSJohn Marino 
864cf7f2e2dSJohn Marino   new = XZALLOC (struct so_list);
865cf7f2e2dSJohn Marino   old_chain = make_cleanup (xfree, new);
866a45ae5f8SJohn Marino   new->lm_info = lm_info_read (ldsomap);
867cf7f2e2dSJohn Marino   make_cleanup (xfree, new->lm_info);
868a45ae5f8SJohn Marino   name_lm = new->lm_info ? new->lm_info->l_name : 0;
869cf7f2e2dSJohn Marino   do_cleanups (old_chain);
870cf7f2e2dSJohn Marino 
871a45ae5f8SJohn Marino   return (name_lm >= vaddr && name_lm < vaddr + size);
872cf7f2e2dSJohn Marino }
873cf7f2e2dSJohn Marino 
874a45ae5f8SJohn Marino /* Implement the "open_symbol_file_object" target_so_ops method.
8755796c8dcSSimon Schubert 
8765796c8dcSSimon Schubert    If no open symbol file, attempt to locate and open the main symbol
8775796c8dcSSimon Schubert    file.  On SVR4 systems, this is the first link map entry.  If its
8785796c8dcSSimon Schubert    name is here, we can open it.  Useful when attaching to a process
879a45ae5f8SJohn Marino    without first loading its symbol file.  */
8805796c8dcSSimon Schubert 
8815796c8dcSSimon Schubert static int
open_symbol_file_object(void * from_ttyp)8825796c8dcSSimon Schubert open_symbol_file_object (void *from_ttyp)
8835796c8dcSSimon Schubert {
8845796c8dcSSimon Schubert   CORE_ADDR lm, l_name;
8855796c8dcSSimon Schubert   char *filename;
8865796c8dcSSimon Schubert   int errcode;
8875796c8dcSSimon Schubert   int from_tty = *(int *)from_ttyp;
8885796c8dcSSimon Schubert   struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
889*ef5ccd6cSJohn Marino   struct type *ptr_type = builtin_type (target_gdbarch ())->builtin_data_ptr;
8905796c8dcSSimon Schubert   int l_name_size = TYPE_LENGTH (ptr_type);
8915796c8dcSSimon Schubert   gdb_byte *l_name_buf = xmalloc (l_name_size);
8925796c8dcSSimon Schubert   struct cleanup *cleanups = make_cleanup (xfree, l_name_buf);
893cf7f2e2dSJohn Marino   struct svr4_info *info = get_svr4_info ();
8945796c8dcSSimon Schubert 
8955796c8dcSSimon Schubert   if (symfile_objfile)
8965796c8dcSSimon Schubert     if (!query (_("Attempt to reload symbols from process? ")))
897a45ae5f8SJohn Marino       {
898a45ae5f8SJohn Marino 	do_cleanups (cleanups);
8995796c8dcSSimon Schubert 	return 0;
900a45ae5f8SJohn Marino       }
9015796c8dcSSimon Schubert 
9025796c8dcSSimon Schubert   /* Always locate the debug struct, in case it has moved.  */
9035796c8dcSSimon Schubert   info->debug_base = 0;
9045796c8dcSSimon Schubert   if (locate_base (info) == 0)
905a45ae5f8SJohn Marino     {
906a45ae5f8SJohn Marino       do_cleanups (cleanups);
9075796c8dcSSimon Schubert       return 0;	/* failed somehow...  */
908a45ae5f8SJohn Marino     }
9095796c8dcSSimon Schubert 
9105796c8dcSSimon Schubert   /* First link map member should be the executable.  */
9115796c8dcSSimon Schubert   lm = solib_svr4_r_map (info);
9125796c8dcSSimon Schubert   if (lm == 0)
913a45ae5f8SJohn Marino     {
914a45ae5f8SJohn Marino       do_cleanups (cleanups);
9155796c8dcSSimon Schubert       return 0;	/* failed somehow...  */
916a45ae5f8SJohn Marino     }
9175796c8dcSSimon Schubert 
9185796c8dcSSimon Schubert   /* Read address of name from target memory to GDB.  */
9195796c8dcSSimon Schubert   read_memory (lm + lmo->l_name_offset, l_name_buf, l_name_size);
9205796c8dcSSimon Schubert 
9215796c8dcSSimon Schubert   /* Convert the address to host format.  */
9225796c8dcSSimon Schubert   l_name = extract_typed_address (l_name_buf, ptr_type);
9235796c8dcSSimon Schubert 
9245796c8dcSSimon Schubert   if (l_name == 0)
925a45ae5f8SJohn Marino     {
926a45ae5f8SJohn Marino       do_cleanups (cleanups);
9275796c8dcSSimon Schubert       return 0;		/* No filename.  */
928a45ae5f8SJohn Marino     }
9295796c8dcSSimon Schubert 
9305796c8dcSSimon Schubert   /* Now fetch the filename from target memory.  */
9315796c8dcSSimon Schubert   target_read_string (l_name, &filename, SO_NAME_MAX_PATH_SIZE - 1, &errcode);
9325796c8dcSSimon Schubert   make_cleanup (xfree, filename);
9335796c8dcSSimon Schubert 
9345796c8dcSSimon Schubert   if (errcode)
9355796c8dcSSimon Schubert     {
9365796c8dcSSimon Schubert       warning (_("failed to read exec filename from attached file: %s"),
9375796c8dcSSimon Schubert 	       safe_strerror (errcode));
938a45ae5f8SJohn Marino       do_cleanups (cleanups);
9395796c8dcSSimon Schubert       return 0;
9405796c8dcSSimon Schubert     }
9415796c8dcSSimon Schubert 
9425796c8dcSSimon Schubert   /* Have a pathname: read the symbol file.  */
9435796c8dcSSimon Schubert   symbol_file_add_main (filename, from_tty);
9445796c8dcSSimon Schubert 
945a45ae5f8SJohn Marino   do_cleanups (cleanups);
9465796c8dcSSimon Schubert   return 1;
9475796c8dcSSimon Schubert }
9485796c8dcSSimon Schubert 
949a45ae5f8SJohn Marino /* Data exchange structure for the XML parser as returned by
950a45ae5f8SJohn Marino    svr4_current_sos_via_xfer_libraries.  */
951a45ae5f8SJohn Marino 
952a45ae5f8SJohn Marino struct svr4_library_list
953a45ae5f8SJohn Marino {
954a45ae5f8SJohn Marino   struct so_list *head, **tailp;
955a45ae5f8SJohn Marino 
956a45ae5f8SJohn Marino   /* Inferior address of struct link_map used for the main executable.  It is
957a45ae5f8SJohn Marino      NULL if not known.  */
958a45ae5f8SJohn Marino   CORE_ADDR main_lm;
959a45ae5f8SJohn Marino };
960a45ae5f8SJohn Marino 
961a45ae5f8SJohn Marino /* Implementation for target_so_ops.free_so.  */
962a45ae5f8SJohn Marino 
963a45ae5f8SJohn Marino static void
svr4_free_so(struct so_list * so)964a45ae5f8SJohn Marino svr4_free_so (struct so_list *so)
965a45ae5f8SJohn Marino {
966a45ae5f8SJohn Marino   xfree (so->lm_info);
967a45ae5f8SJohn Marino }
968a45ae5f8SJohn Marino 
969a45ae5f8SJohn Marino /* Free so_list built so far (called via cleanup).  */
970a45ae5f8SJohn Marino 
971a45ae5f8SJohn Marino static void
svr4_free_library_list(void * p_list)972a45ae5f8SJohn Marino svr4_free_library_list (void *p_list)
973a45ae5f8SJohn Marino {
974a45ae5f8SJohn Marino   struct so_list *list = *(struct so_list **) p_list;
975a45ae5f8SJohn Marino 
976a45ae5f8SJohn Marino   while (list != NULL)
977a45ae5f8SJohn Marino     {
978a45ae5f8SJohn Marino       struct so_list *next = list->next;
979a45ae5f8SJohn Marino 
980*ef5ccd6cSJohn Marino       free_so (list);
981a45ae5f8SJohn Marino       list = next;
982a45ae5f8SJohn Marino     }
983a45ae5f8SJohn Marino }
984a45ae5f8SJohn Marino 
985a45ae5f8SJohn Marino #ifdef HAVE_LIBEXPAT
986a45ae5f8SJohn Marino 
987a45ae5f8SJohn Marino #include "xml-support.h"
988a45ae5f8SJohn Marino 
989a45ae5f8SJohn Marino /* Handle the start of a <library> element.  Note: new elements are added
990a45ae5f8SJohn Marino    at the tail of the list, keeping the list in order.  */
991a45ae5f8SJohn Marino 
992a45ae5f8SJohn Marino static void
library_list_start_library(struct gdb_xml_parser * parser,const struct gdb_xml_element * element,void * user_data,VEC (gdb_xml_value_s)* attributes)993a45ae5f8SJohn Marino library_list_start_library (struct gdb_xml_parser *parser,
994a45ae5f8SJohn Marino 			    const struct gdb_xml_element *element,
995a45ae5f8SJohn Marino 			    void *user_data, VEC(gdb_xml_value_s) *attributes)
996a45ae5f8SJohn Marino {
997a45ae5f8SJohn Marino   struct svr4_library_list *list = user_data;
998a45ae5f8SJohn Marino   const char *name = xml_find_attribute (attributes, "name")->value;
999a45ae5f8SJohn Marino   ULONGEST *lmp = xml_find_attribute (attributes, "lm")->value;
1000a45ae5f8SJohn Marino   ULONGEST *l_addrp = xml_find_attribute (attributes, "l_addr")->value;
1001a45ae5f8SJohn Marino   ULONGEST *l_ldp = xml_find_attribute (attributes, "l_ld")->value;
1002a45ae5f8SJohn Marino   struct so_list *new_elem;
1003a45ae5f8SJohn Marino 
1004a45ae5f8SJohn Marino   new_elem = XZALLOC (struct so_list);
1005a45ae5f8SJohn Marino   new_elem->lm_info = XZALLOC (struct lm_info);
1006a45ae5f8SJohn Marino   new_elem->lm_info->lm_addr = *lmp;
1007a45ae5f8SJohn Marino   new_elem->lm_info->l_addr_inferior = *l_addrp;
1008a45ae5f8SJohn Marino   new_elem->lm_info->l_ld = *l_ldp;
1009a45ae5f8SJohn Marino 
1010a45ae5f8SJohn Marino   strncpy (new_elem->so_name, name, sizeof (new_elem->so_name) - 1);
1011a45ae5f8SJohn Marino   new_elem->so_name[sizeof (new_elem->so_name) - 1] = 0;
1012a45ae5f8SJohn Marino   strcpy (new_elem->so_original_name, new_elem->so_name);
1013a45ae5f8SJohn Marino 
1014a45ae5f8SJohn Marino   *list->tailp = new_elem;
1015a45ae5f8SJohn Marino   list->tailp = &new_elem->next;
1016a45ae5f8SJohn Marino }
1017a45ae5f8SJohn Marino 
1018a45ae5f8SJohn Marino /* Handle the start of a <library-list-svr4> element.  */
1019a45ae5f8SJohn Marino 
1020a45ae5f8SJohn Marino static void
svr4_library_list_start_list(struct gdb_xml_parser * parser,const struct gdb_xml_element * element,void * user_data,VEC (gdb_xml_value_s)* attributes)1021a45ae5f8SJohn Marino svr4_library_list_start_list (struct gdb_xml_parser *parser,
1022a45ae5f8SJohn Marino 			      const struct gdb_xml_element *element,
1023a45ae5f8SJohn Marino 			      void *user_data, VEC(gdb_xml_value_s) *attributes)
1024a45ae5f8SJohn Marino {
1025a45ae5f8SJohn Marino   struct svr4_library_list *list = user_data;
1026a45ae5f8SJohn Marino   const char *version = xml_find_attribute (attributes, "version")->value;
1027a45ae5f8SJohn Marino   struct gdb_xml_value *main_lm = xml_find_attribute (attributes, "main-lm");
1028a45ae5f8SJohn Marino 
1029a45ae5f8SJohn Marino   if (strcmp (version, "1.0") != 0)
1030a45ae5f8SJohn Marino     gdb_xml_error (parser,
1031a45ae5f8SJohn Marino 		   _("SVR4 Library list has unsupported version \"%s\""),
1032a45ae5f8SJohn Marino 		   version);
1033a45ae5f8SJohn Marino 
1034a45ae5f8SJohn Marino   if (main_lm)
1035a45ae5f8SJohn Marino     list->main_lm = *(ULONGEST *) main_lm->value;
1036a45ae5f8SJohn Marino }
1037a45ae5f8SJohn Marino 
1038a45ae5f8SJohn Marino /* The allowed elements and attributes for an XML library list.
1039a45ae5f8SJohn Marino    The root element is a <library-list>.  */
1040a45ae5f8SJohn Marino 
1041a45ae5f8SJohn Marino static const struct gdb_xml_attribute svr4_library_attributes[] =
1042a45ae5f8SJohn Marino {
1043a45ae5f8SJohn Marino   { "name", GDB_XML_AF_NONE, NULL, NULL },
1044a45ae5f8SJohn Marino   { "lm", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
1045a45ae5f8SJohn Marino   { "l_addr", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
1046a45ae5f8SJohn Marino   { "l_ld", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
1047a45ae5f8SJohn Marino   { NULL, GDB_XML_AF_NONE, NULL, NULL }
1048a45ae5f8SJohn Marino };
1049a45ae5f8SJohn Marino 
1050a45ae5f8SJohn Marino static const struct gdb_xml_element svr4_library_list_children[] =
1051a45ae5f8SJohn Marino {
1052a45ae5f8SJohn Marino   {
1053a45ae5f8SJohn Marino     "library", svr4_library_attributes, NULL,
1054a45ae5f8SJohn Marino     GDB_XML_EF_REPEATABLE | GDB_XML_EF_OPTIONAL,
1055a45ae5f8SJohn Marino     library_list_start_library, NULL
1056a45ae5f8SJohn Marino   },
1057a45ae5f8SJohn Marino   { NULL, NULL, NULL, GDB_XML_EF_NONE, NULL, NULL }
1058a45ae5f8SJohn Marino };
1059a45ae5f8SJohn Marino 
1060a45ae5f8SJohn Marino static const struct gdb_xml_attribute svr4_library_list_attributes[] =
1061a45ae5f8SJohn Marino {
1062a45ae5f8SJohn Marino   { "version", GDB_XML_AF_NONE, NULL, NULL },
1063a45ae5f8SJohn Marino   { "main-lm", GDB_XML_AF_OPTIONAL, gdb_xml_parse_attr_ulongest, NULL },
1064a45ae5f8SJohn Marino   { NULL, GDB_XML_AF_NONE, NULL, NULL }
1065a45ae5f8SJohn Marino };
1066a45ae5f8SJohn Marino 
1067a45ae5f8SJohn Marino static const struct gdb_xml_element svr4_library_list_elements[] =
1068a45ae5f8SJohn Marino {
1069a45ae5f8SJohn Marino   { "library-list-svr4", svr4_library_list_attributes, svr4_library_list_children,
1070a45ae5f8SJohn Marino     GDB_XML_EF_NONE, svr4_library_list_start_list, NULL },
1071a45ae5f8SJohn Marino   { NULL, NULL, NULL, GDB_XML_EF_NONE, NULL, NULL }
1072a45ae5f8SJohn Marino };
1073a45ae5f8SJohn Marino 
1074a45ae5f8SJohn Marino /* Parse qXfer:libraries:read packet into *SO_LIST_RETURN.  Return 1 if
1075a45ae5f8SJohn Marino 
1076a45ae5f8SJohn Marino    Return 0 if packet not supported, *SO_LIST_RETURN is not modified in such
1077a45ae5f8SJohn Marino    case.  Return 1 if *SO_LIST_RETURN contains the library list, it may be
1078a45ae5f8SJohn Marino    empty, caller is responsible for freeing all its entries.  */
1079a45ae5f8SJohn Marino 
1080a45ae5f8SJohn Marino static int
svr4_parse_libraries(const char * document,struct svr4_library_list * list)1081a45ae5f8SJohn Marino svr4_parse_libraries (const char *document, struct svr4_library_list *list)
1082a45ae5f8SJohn Marino {
1083a45ae5f8SJohn Marino   struct cleanup *back_to = make_cleanup (svr4_free_library_list,
1084a45ae5f8SJohn Marino 					  &list->head);
1085a45ae5f8SJohn Marino 
1086a45ae5f8SJohn Marino   memset (list, 0, sizeof (*list));
1087a45ae5f8SJohn Marino   list->tailp = &list->head;
1088a45ae5f8SJohn Marino   if (gdb_xml_parse_quick (_("target library list"), "library-list.dtd",
1089a45ae5f8SJohn Marino 			   svr4_library_list_elements, document, list) == 0)
1090a45ae5f8SJohn Marino     {
1091a45ae5f8SJohn Marino       /* Parsed successfully, keep the result.  */
1092a45ae5f8SJohn Marino       discard_cleanups (back_to);
1093a45ae5f8SJohn Marino       return 1;
1094a45ae5f8SJohn Marino     }
1095a45ae5f8SJohn Marino 
1096a45ae5f8SJohn Marino   do_cleanups (back_to);
1097a45ae5f8SJohn Marino   return 0;
1098a45ae5f8SJohn Marino }
1099a45ae5f8SJohn Marino 
1100a45ae5f8SJohn Marino /* Attempt to get so_list from target via qXfer:libraries:read packet.
1101a45ae5f8SJohn Marino 
1102a45ae5f8SJohn Marino    Return 0 if packet not supported, *SO_LIST_RETURN is not modified in such
1103a45ae5f8SJohn Marino    case.  Return 1 if *SO_LIST_RETURN contains the library list, it may be
1104a45ae5f8SJohn Marino    empty, caller is responsible for freeing all its entries.  */
1105a45ae5f8SJohn Marino 
1106a45ae5f8SJohn Marino static int
svr4_current_sos_via_xfer_libraries(struct svr4_library_list * list)1107a45ae5f8SJohn Marino svr4_current_sos_via_xfer_libraries (struct svr4_library_list *list)
1108a45ae5f8SJohn Marino {
1109a45ae5f8SJohn Marino   char *svr4_library_document;
1110a45ae5f8SJohn Marino   int result;
1111a45ae5f8SJohn Marino   struct cleanup *back_to;
1112a45ae5f8SJohn Marino 
1113a45ae5f8SJohn Marino   /* Fetch the list of shared libraries.  */
1114a45ae5f8SJohn Marino   svr4_library_document = target_read_stralloc (&current_target,
1115a45ae5f8SJohn Marino 						TARGET_OBJECT_LIBRARIES_SVR4,
1116a45ae5f8SJohn Marino 						NULL);
1117a45ae5f8SJohn Marino   if (svr4_library_document == NULL)
1118a45ae5f8SJohn Marino     return 0;
1119a45ae5f8SJohn Marino 
1120a45ae5f8SJohn Marino   back_to = make_cleanup (xfree, svr4_library_document);
1121a45ae5f8SJohn Marino   result = svr4_parse_libraries (svr4_library_document, list);
1122a45ae5f8SJohn Marino   do_cleanups (back_to);
1123a45ae5f8SJohn Marino 
1124a45ae5f8SJohn Marino   return result;
1125a45ae5f8SJohn Marino }
1126a45ae5f8SJohn Marino 
1127a45ae5f8SJohn Marino #else
1128a45ae5f8SJohn Marino 
1129a45ae5f8SJohn Marino static int
svr4_current_sos_via_xfer_libraries(struct svr4_library_list * list)1130a45ae5f8SJohn Marino svr4_current_sos_via_xfer_libraries (struct svr4_library_list *list)
1131a45ae5f8SJohn Marino {
1132a45ae5f8SJohn Marino   return 0;
1133a45ae5f8SJohn Marino }
1134a45ae5f8SJohn Marino 
1135a45ae5f8SJohn Marino #endif
1136a45ae5f8SJohn Marino 
11375796c8dcSSimon Schubert /* If no shared library information is available from the dynamic
11385796c8dcSSimon Schubert    linker, build a fallback list from other sources.  */
11395796c8dcSSimon Schubert 
11405796c8dcSSimon Schubert static struct so_list *
svr4_default_sos(void)11415796c8dcSSimon Schubert svr4_default_sos (void)
11425796c8dcSSimon Schubert {
1143cf7f2e2dSJohn Marino   struct svr4_info *info = get_svr4_info ();
1144a45ae5f8SJohn Marino   struct so_list *new;
11455796c8dcSSimon Schubert 
1146a45ae5f8SJohn Marino   if (!info->debug_loader_offset_p)
1147a45ae5f8SJohn Marino     return NULL;
11485796c8dcSSimon Schubert 
1149a45ae5f8SJohn Marino   new = XZALLOC (struct so_list);
11505796c8dcSSimon Schubert 
1151a45ae5f8SJohn Marino   new->lm_info = xzalloc (sizeof (struct lm_info));
11525796c8dcSSimon Schubert 
1153a45ae5f8SJohn Marino   /* Nothing will ever check the other fields if we set l_addr_p.  */
11545796c8dcSSimon Schubert   new->lm_info->l_addr = info->debug_loader_offset;
1155a45ae5f8SJohn Marino   new->lm_info->l_addr_p = 1;
11565796c8dcSSimon Schubert 
1157a45ae5f8SJohn Marino   strncpy (new->so_name, info->debug_loader_name, SO_NAME_MAX_PATH_SIZE - 1);
11585796c8dcSSimon Schubert   new->so_name[SO_NAME_MAX_PATH_SIZE - 1] = '\0';
11595796c8dcSSimon Schubert   strcpy (new->so_original_name, new->so_name);
11605796c8dcSSimon Schubert 
1161a45ae5f8SJohn Marino   return new;
11625796c8dcSSimon Schubert }
11635796c8dcSSimon Schubert 
1164a45ae5f8SJohn Marino /* Read the whole inferior libraries chain starting at address LM.  Add the
1165a45ae5f8SJohn Marino    entries to the tail referenced by LINK_PTR_PTR.  Ignore the first entry if
1166a45ae5f8SJohn Marino    IGNORE_FIRST and set global MAIN_LM_ADDR according to it.  */
1167a45ae5f8SJohn Marino 
1168a45ae5f8SJohn Marino static void
svr4_read_so_list(CORE_ADDR lm,struct so_list *** link_ptr_ptr,int ignore_first)1169a45ae5f8SJohn Marino svr4_read_so_list (CORE_ADDR lm, struct so_list ***link_ptr_ptr,
1170a45ae5f8SJohn Marino 		   int ignore_first)
1171a45ae5f8SJohn Marino {
1172a45ae5f8SJohn Marino   CORE_ADDR prev_lm = 0, next_lm;
1173a45ae5f8SJohn Marino 
1174a45ae5f8SJohn Marino   for (; lm != 0; prev_lm = lm, lm = next_lm)
1175a45ae5f8SJohn Marino     {
1176a45ae5f8SJohn Marino       struct so_list *new;
1177a45ae5f8SJohn Marino       struct cleanup *old_chain;
1178a45ae5f8SJohn Marino       int errcode;
1179a45ae5f8SJohn Marino       char *buffer;
1180a45ae5f8SJohn Marino 
1181a45ae5f8SJohn Marino       new = XZALLOC (struct so_list);
1182a45ae5f8SJohn Marino       old_chain = make_cleanup_free_so (new);
1183a45ae5f8SJohn Marino 
1184a45ae5f8SJohn Marino       new->lm_info = lm_info_read (lm);
1185a45ae5f8SJohn Marino       if (new->lm_info == NULL)
1186a45ae5f8SJohn Marino 	{
1187a45ae5f8SJohn Marino 	  do_cleanups (old_chain);
1188a45ae5f8SJohn Marino 	  break;
11895796c8dcSSimon Schubert 	}
11905796c8dcSSimon Schubert 
1191a45ae5f8SJohn Marino       next_lm = new->lm_info->l_next;
11925796c8dcSSimon Schubert 
1193a45ae5f8SJohn Marino       if (new->lm_info->l_prev != prev_lm)
1194a45ae5f8SJohn Marino 	{
1195a45ae5f8SJohn Marino 	  warning (_("Corrupted shared library list: %s != %s"),
1196*ef5ccd6cSJohn Marino 		   paddress (target_gdbarch (), prev_lm),
1197*ef5ccd6cSJohn Marino 		   paddress (target_gdbarch (), new->lm_info->l_prev));
1198a45ae5f8SJohn Marino 	  do_cleanups (old_chain);
1199a45ae5f8SJohn Marino 	  break;
1200a45ae5f8SJohn Marino 	}
12015796c8dcSSimon Schubert 
1202a45ae5f8SJohn Marino       /* For SVR4 versions, the first entry in the link map is for the
1203a45ae5f8SJohn Marino          inferior executable, so we must ignore it.  For some versions of
1204a45ae5f8SJohn Marino          SVR4, it has no name.  For others (Solaris 2.3 for example), it
1205a45ae5f8SJohn Marino          does have a name, so we can no longer use a missing name to
1206a45ae5f8SJohn Marino          decide when to ignore it.  */
1207a45ae5f8SJohn Marino       if (ignore_first && new->lm_info->l_prev == 0)
1208a45ae5f8SJohn Marino 	{
1209a45ae5f8SJohn Marino 	  struct svr4_info *info = get_svr4_info ();
12105796c8dcSSimon Schubert 
1211a45ae5f8SJohn Marino 	  info->main_lm_addr = new->lm_info->lm_addr;
1212a45ae5f8SJohn Marino 	  do_cleanups (old_chain);
1213a45ae5f8SJohn Marino 	  continue;
1214a45ae5f8SJohn Marino 	}
12155796c8dcSSimon Schubert 
1216a45ae5f8SJohn Marino       /* Extract this shared object's name.  */
1217a45ae5f8SJohn Marino       target_read_string (new->lm_info->l_name, &buffer,
1218a45ae5f8SJohn Marino 			  SO_NAME_MAX_PATH_SIZE - 1, &errcode);
1219a45ae5f8SJohn Marino       if (errcode != 0)
1220a45ae5f8SJohn Marino 	{
1221a45ae5f8SJohn Marino 	  warning (_("Can't read pathname for load map: %s."),
1222a45ae5f8SJohn Marino 		   safe_strerror (errcode));
1223a45ae5f8SJohn Marino 	  do_cleanups (old_chain);
1224a45ae5f8SJohn Marino 	  continue;
1225a45ae5f8SJohn Marino 	}
12265796c8dcSSimon Schubert 
1227a45ae5f8SJohn Marino       strncpy (new->so_name, buffer, SO_NAME_MAX_PATH_SIZE - 1);
1228a45ae5f8SJohn Marino       new->so_name[SO_NAME_MAX_PATH_SIZE - 1] = '\0';
1229a45ae5f8SJohn Marino       strcpy (new->so_original_name, new->so_name);
1230a45ae5f8SJohn Marino       xfree (buffer);
12315796c8dcSSimon Schubert 
1232a45ae5f8SJohn Marino       /* If this entry has no name, or its name matches the name
1233a45ae5f8SJohn Marino 	 for the main executable, don't include it in the list.  */
1234a45ae5f8SJohn Marino       if (! new->so_name[0] || match_main (new->so_name))
1235a45ae5f8SJohn Marino 	{
1236a45ae5f8SJohn Marino 	  do_cleanups (old_chain);
1237a45ae5f8SJohn Marino 	  continue;
1238a45ae5f8SJohn Marino 	}
1239a45ae5f8SJohn Marino 
1240a45ae5f8SJohn Marino       discard_cleanups (old_chain);
1241a45ae5f8SJohn Marino       new->next = 0;
1242a45ae5f8SJohn Marino       **link_ptr_ptr = new;
1243a45ae5f8SJohn Marino       *link_ptr_ptr = &new->next;
1244a45ae5f8SJohn Marino     }
1245a45ae5f8SJohn Marino }
1246a45ae5f8SJohn Marino 
1247a45ae5f8SJohn Marino /* Implement the "current_sos" target_so_ops method.  */
12485796c8dcSSimon Schubert 
12495796c8dcSSimon Schubert static struct so_list *
svr4_current_sos(void)12505796c8dcSSimon Schubert svr4_current_sos (void)
12515796c8dcSSimon Schubert {
1252a45ae5f8SJohn Marino   CORE_ADDR lm;
1253a45ae5f8SJohn Marino   struct so_list *head = NULL;
12545796c8dcSSimon Schubert   struct so_list **link_ptr = &head;
12555796c8dcSSimon Schubert   struct svr4_info *info;
1256a45ae5f8SJohn Marino   struct cleanup *back_to;
1257a45ae5f8SJohn Marino   int ignore_first;
1258a45ae5f8SJohn Marino   struct svr4_library_list library_list;
1259a45ae5f8SJohn Marino 
1260*ef5ccd6cSJohn Marino   /* Fall back to manual examination of the target if the packet is not
1261*ef5ccd6cSJohn Marino      supported or gdbserver failed to find DT_DEBUG.  gdb.server/solib-list.exp
1262*ef5ccd6cSJohn Marino      tests a case where gdbserver cannot find the shared libraries list while
1263*ef5ccd6cSJohn Marino      GDB itself is able to find it via SYMFILE_OBJFILE.
1264*ef5ccd6cSJohn Marino 
1265*ef5ccd6cSJohn Marino      Unfortunately statically linked inferiors will also fall back through this
1266*ef5ccd6cSJohn Marino      suboptimal code path.  */
1267*ef5ccd6cSJohn Marino 
1268a45ae5f8SJohn Marino   if (svr4_current_sos_via_xfer_libraries (&library_list))
1269a45ae5f8SJohn Marino     {
1270a45ae5f8SJohn Marino       if (library_list.main_lm)
1271a45ae5f8SJohn Marino 	{
1272a45ae5f8SJohn Marino 	  info = get_svr4_info ();
1273a45ae5f8SJohn Marino 	  info->main_lm_addr = library_list.main_lm;
1274a45ae5f8SJohn Marino 	}
1275a45ae5f8SJohn Marino 
1276a45ae5f8SJohn Marino       return library_list.head ? library_list.head : svr4_default_sos ();
1277a45ae5f8SJohn Marino     }
12785796c8dcSSimon Schubert 
1279cf7f2e2dSJohn Marino   info = get_svr4_info ();
12805796c8dcSSimon Schubert 
12815796c8dcSSimon Schubert   /* Always locate the debug struct, in case it has moved.  */
12825796c8dcSSimon Schubert   info->debug_base = 0;
12835796c8dcSSimon Schubert   locate_base (info);
12845796c8dcSSimon Schubert 
12855796c8dcSSimon Schubert   /* If we can't find the dynamic linker's base structure, this
12865796c8dcSSimon Schubert      must not be a dynamically linked executable.  Hmm.  */
12875796c8dcSSimon Schubert   if (! info->debug_base)
12885796c8dcSSimon Schubert     return svr4_default_sos ();
12895796c8dcSSimon Schubert 
1290a45ae5f8SJohn Marino   /* Assume that everything is a library if the dynamic loader was loaded
1291a45ae5f8SJohn Marino      late by a static executable.  */
1292a45ae5f8SJohn Marino   if (exec_bfd && bfd_get_section_by_name (exec_bfd, ".dynamic") == NULL)
1293a45ae5f8SJohn Marino     ignore_first = 0;
1294a45ae5f8SJohn Marino   else
1295a45ae5f8SJohn Marino     ignore_first = 1;
1296a45ae5f8SJohn Marino 
1297a45ae5f8SJohn Marino   back_to = make_cleanup (svr4_free_library_list, &head);
1298a45ae5f8SJohn Marino 
12995796c8dcSSimon Schubert   /* Walk the inferior's link map list, and build our list of
13005796c8dcSSimon Schubert      `struct so_list' nodes.  */
13015796c8dcSSimon Schubert   lm = solib_svr4_r_map (info);
1302a45ae5f8SJohn Marino   if (lm)
1303a45ae5f8SJohn Marino     svr4_read_so_list (lm, &link_ptr, ignore_first);
1304cf7f2e2dSJohn Marino 
13055796c8dcSSimon Schubert   /* On Solaris, the dynamic linker is not in the normal list of
13065796c8dcSSimon Schubert      shared objects, so make sure we pick it up too.  Having
13075796c8dcSSimon Schubert      symbol information for the dynamic linker is quite crucial
13085796c8dcSSimon Schubert      for skipping dynamic linker resolver code.  */
1309a45ae5f8SJohn Marino   lm = solib_svr4_r_ldsomap (info);
1310a45ae5f8SJohn Marino   if (lm)
1311a45ae5f8SJohn Marino     svr4_read_so_list (lm, &link_ptr, 0);
13125796c8dcSSimon Schubert 
1313a45ae5f8SJohn Marino   discard_cleanups (back_to);
13145796c8dcSSimon Schubert 
13155796c8dcSSimon Schubert   if (head == NULL)
13165796c8dcSSimon Schubert     return svr4_default_sos ();
13175796c8dcSSimon Schubert 
13185796c8dcSSimon Schubert   return head;
13195796c8dcSSimon Schubert }
13205796c8dcSSimon Schubert 
13215796c8dcSSimon Schubert /* Get the address of the link_map for a given OBJFILE.  */
13225796c8dcSSimon Schubert 
13235796c8dcSSimon Schubert CORE_ADDR
svr4_fetch_objfile_link_map(struct objfile * objfile)13245796c8dcSSimon Schubert svr4_fetch_objfile_link_map (struct objfile *objfile)
13255796c8dcSSimon Schubert {
13265796c8dcSSimon Schubert   struct so_list *so;
1327cf7f2e2dSJohn Marino   struct svr4_info *info = get_svr4_info ();
13285796c8dcSSimon Schubert 
13295796c8dcSSimon Schubert   /* Cause svr4_current_sos() to be run if it hasn't been already.  */
13305796c8dcSSimon Schubert   if (info->main_lm_addr == 0)
13315796c8dcSSimon Schubert     solib_add (NULL, 0, &current_target, auto_solib_add);
13325796c8dcSSimon Schubert 
13335796c8dcSSimon Schubert   /* svr4_current_sos() will set main_lm_addr for the main executable.  */
13345796c8dcSSimon Schubert   if (objfile == symfile_objfile)
13355796c8dcSSimon Schubert     return info->main_lm_addr;
13365796c8dcSSimon Schubert 
13375796c8dcSSimon Schubert   /* The other link map addresses may be found by examining the list
13385796c8dcSSimon Schubert      of shared libraries.  */
13395796c8dcSSimon Schubert   for (so = master_so_list (); so; so = so->next)
13405796c8dcSSimon Schubert     if (so->objfile == objfile)
13415796c8dcSSimon Schubert       return so->lm_info->lm_addr;
13425796c8dcSSimon Schubert 
13435796c8dcSSimon Schubert   /* Not found!  */
13445796c8dcSSimon Schubert   return 0;
13455796c8dcSSimon Schubert }
13465796c8dcSSimon Schubert 
13475796c8dcSSimon Schubert /* On some systems, the only way to recognize the link map entry for
13485796c8dcSSimon Schubert    the main executable file is by looking at its name.  Return
13495796c8dcSSimon Schubert    non-zero iff SONAME matches one of the known main executable names.  */
13505796c8dcSSimon Schubert 
13515796c8dcSSimon Schubert static int
match_main(const char * soname)1352c50c785cSJohn Marino match_main (const char *soname)
13535796c8dcSSimon Schubert {
1354c50c785cSJohn Marino   const char * const *mainp;
13555796c8dcSSimon Schubert 
13565796c8dcSSimon Schubert   for (mainp = main_name_list; *mainp != NULL; mainp++)
13575796c8dcSSimon Schubert     {
13585796c8dcSSimon Schubert       if (strcmp (soname, *mainp) == 0)
13595796c8dcSSimon Schubert 	return (1);
13605796c8dcSSimon Schubert     }
13615796c8dcSSimon Schubert 
13625796c8dcSSimon Schubert   return (0);
13635796c8dcSSimon Schubert }
13645796c8dcSSimon Schubert 
13655796c8dcSSimon Schubert /* Return 1 if PC lies in the dynamic symbol resolution code of the
13665796c8dcSSimon Schubert    SVR4 run time loader.  */
13675796c8dcSSimon Schubert 
13685796c8dcSSimon Schubert int
svr4_in_dynsym_resolve_code(CORE_ADDR pc)13695796c8dcSSimon Schubert svr4_in_dynsym_resolve_code (CORE_ADDR pc)
13705796c8dcSSimon Schubert {
1371cf7f2e2dSJohn Marino   struct svr4_info *info = get_svr4_info ();
1372cf7f2e2dSJohn Marino 
1373cf7f2e2dSJohn Marino   return ((pc >= info->interp_text_sect_low
1374cf7f2e2dSJohn Marino 	   && pc < info->interp_text_sect_high)
1375cf7f2e2dSJohn Marino 	  || (pc >= info->interp_plt_sect_low
1376cf7f2e2dSJohn Marino 	      && pc < info->interp_plt_sect_high)
1377c50c785cSJohn Marino 	  || in_plt_section (pc, NULL)
1378c50c785cSJohn Marino 	  || in_gnu_ifunc_stub (pc));
13795796c8dcSSimon Schubert }
13805796c8dcSSimon Schubert 
13815796c8dcSSimon Schubert /* Given an executable's ABFD and target, compute the entry-point
13825796c8dcSSimon Schubert    address.  */
13835796c8dcSSimon Schubert 
13845796c8dcSSimon Schubert static CORE_ADDR
exec_entry_point(struct bfd * abfd,struct target_ops * targ)13855796c8dcSSimon Schubert exec_entry_point (struct bfd *abfd, struct target_ops *targ)
13865796c8dcSSimon Schubert {
1387*ef5ccd6cSJohn Marino   CORE_ADDR addr;
1388*ef5ccd6cSJohn Marino 
13895796c8dcSSimon Schubert   /* KevinB wrote ... for most targets, the address returned by
13905796c8dcSSimon Schubert      bfd_get_start_address() is the entry point for the start
13915796c8dcSSimon Schubert      function.  But, for some targets, bfd_get_start_address() returns
13925796c8dcSSimon Schubert      the address of a function descriptor from which the entry point
13935796c8dcSSimon Schubert      address may be extracted.  This address is extracted by
13945796c8dcSSimon Schubert      gdbarch_convert_from_func_ptr_addr().  The method
13955796c8dcSSimon Schubert      gdbarch_convert_from_func_ptr_addr() is the merely the identify
13965796c8dcSSimon Schubert      function for targets which don't use function descriptors.  */
1397*ef5ccd6cSJohn Marino   addr = gdbarch_convert_from_func_ptr_addr (target_gdbarch (),
13985796c8dcSSimon Schubert 					     bfd_get_start_address (abfd),
13995796c8dcSSimon Schubert 					     targ);
1400*ef5ccd6cSJohn Marino   return gdbarch_addr_bits_remove (target_gdbarch (), addr);
14015796c8dcSSimon Schubert }
14025796c8dcSSimon Schubert 
1403a45ae5f8SJohn Marino /* Helper function for gdb_bfd_lookup_symbol.  */
14045796c8dcSSimon Schubert 
1405a45ae5f8SJohn Marino static int
cmp_name_and_sec_flags(asymbol * sym,void * data)1406a45ae5f8SJohn Marino cmp_name_and_sec_flags (asymbol *sym, void *data)
1407a45ae5f8SJohn Marino {
1408a45ae5f8SJohn Marino   return (strcmp (sym->name, (const char *) data) == 0
1409a45ae5f8SJohn Marino 	  && (sym->section->flags & (SEC_CODE | SEC_DATA)) != 0);
1410a45ae5f8SJohn Marino }
1411a45ae5f8SJohn Marino /* Arrange for dynamic linker to hit breakpoint.
14125796c8dcSSimon Schubert 
14135796c8dcSSimon Schubert    Both the SunOS and the SVR4 dynamic linkers have, as part of their
14145796c8dcSSimon Schubert    debugger interface, support for arranging for the inferior to hit
14155796c8dcSSimon Schubert    a breakpoint after mapping in the shared libraries.  This function
14165796c8dcSSimon Schubert    enables that breakpoint.
14175796c8dcSSimon Schubert 
14185796c8dcSSimon Schubert    For SunOS, there is a special flag location (in_debugger) which we
14195796c8dcSSimon Schubert    set to 1.  When the dynamic linker sees this flag set, it will set
14205796c8dcSSimon Schubert    a breakpoint at a location known only to itself, after saving the
14215796c8dcSSimon Schubert    original contents of that place and the breakpoint address itself,
14225796c8dcSSimon Schubert    in it's own internal structures.  When we resume the inferior, it
14235796c8dcSSimon Schubert    will eventually take a SIGTRAP when it runs into the breakpoint.
14245796c8dcSSimon Schubert    We handle this (in a different place) by restoring the contents of
14255796c8dcSSimon Schubert    the breakpointed location (which is only known after it stops),
14265796c8dcSSimon Schubert    chasing around to locate the shared libraries that have been
14275796c8dcSSimon Schubert    loaded, then resuming.
14285796c8dcSSimon Schubert 
14295796c8dcSSimon Schubert    For SVR4, the debugger interface structure contains a member (r_brk)
14305796c8dcSSimon Schubert    which is statically initialized at the time the shared library is
14315796c8dcSSimon Schubert    built, to the offset of a function (_r_debug_state) which is guaran-
14325796c8dcSSimon Schubert    teed to be called once before mapping in a library, and again when
14335796c8dcSSimon Schubert    the mapping is complete.  At the time we are examining this member,
14345796c8dcSSimon Schubert    it contains only the unrelocated offset of the function, so we have
14355796c8dcSSimon Schubert    to do our own relocation.  Later, when the dynamic linker actually
14365796c8dcSSimon Schubert    runs, it relocates r_brk to be the actual address of _r_debug_state().
14375796c8dcSSimon Schubert 
14385796c8dcSSimon Schubert    The debugger interface structure also contains an enumeration which
14395796c8dcSSimon Schubert    is set to either RT_ADD or RT_DELETE prior to changing the mapping,
14405796c8dcSSimon Schubert    depending upon whether or not the library is being mapped or unmapped,
1441a45ae5f8SJohn Marino    and then set to RT_CONSISTENT after the library is mapped/unmapped.  */
14425796c8dcSSimon Schubert 
14435796c8dcSSimon Schubert static int
enable_break(struct svr4_info * info,int from_tty)1444cf7f2e2dSJohn Marino enable_break (struct svr4_info *info, int from_tty)
14455796c8dcSSimon Schubert {
14465796c8dcSSimon Schubert   struct minimal_symbol *msymbol;
1447c50c785cSJohn Marino   const char * const *bkpt_namep;
14485796c8dcSSimon Schubert   asection *interp_sect;
14495796c8dcSSimon Schubert   gdb_byte *interp_name;
14505796c8dcSSimon Schubert   CORE_ADDR sym_addr;
14515796c8dcSSimon Schubert 
1452cf7f2e2dSJohn Marino   info->interp_text_sect_low = info->interp_text_sect_high = 0;
1453cf7f2e2dSJohn Marino   info->interp_plt_sect_low = info->interp_plt_sect_high = 0;
14545796c8dcSSimon Schubert 
14555796c8dcSSimon Schubert   /* If we already have a shared library list in the target, and
14565796c8dcSSimon Schubert      r_debug contains r_brk, set the breakpoint there - this should
14575796c8dcSSimon Schubert      mean r_brk has already been relocated.  Assume the dynamic linker
14585796c8dcSSimon Schubert      is the object containing r_brk.  */
14595796c8dcSSimon Schubert 
1460cf7f2e2dSJohn Marino   solib_add (NULL, from_tty, &current_target, auto_solib_add);
14615796c8dcSSimon Schubert   sym_addr = 0;
14625796c8dcSSimon Schubert   if (info->debug_base && solib_svr4_r_map (info) != 0)
14635796c8dcSSimon Schubert     sym_addr = solib_svr4_r_brk (info);
14645796c8dcSSimon Schubert 
14655796c8dcSSimon Schubert   if (sym_addr != 0)
14665796c8dcSSimon Schubert     {
14675796c8dcSSimon Schubert       struct obj_section *os;
14685796c8dcSSimon Schubert 
14695796c8dcSSimon Schubert       sym_addr = gdbarch_addr_bits_remove
1470*ef5ccd6cSJohn Marino 	(target_gdbarch (), gdbarch_convert_from_func_ptr_addr (target_gdbarch (),
14715796c8dcSSimon Schubert 							     sym_addr,
14725796c8dcSSimon Schubert 							     &current_target));
14735796c8dcSSimon Schubert 
1474cf7f2e2dSJohn Marino       /* On at least some versions of Solaris there's a dynamic relocation
1475cf7f2e2dSJohn Marino 	 on _r_debug.r_brk and SYM_ADDR may not be relocated yet, e.g., if
1476cf7f2e2dSJohn Marino 	 we get control before the dynamic linker has self-relocated.
1477cf7f2e2dSJohn Marino 	 Check if SYM_ADDR is in a known section, if it is assume we can
1478cf7f2e2dSJohn Marino 	 trust its value.  This is just a heuristic though, it could go away
1479cf7f2e2dSJohn Marino 	 or be replaced if it's getting in the way.
1480cf7f2e2dSJohn Marino 
1481cf7f2e2dSJohn Marino 	 On ARM we need to know whether the ISA of rtld_db_dlactivity (or
1482cf7f2e2dSJohn Marino 	 however it's spelled in your particular system) is ARM or Thumb.
1483cf7f2e2dSJohn Marino 	 That knowledge is encoded in the address, if it's Thumb the low bit
1484cf7f2e2dSJohn Marino 	 is 1.  However, we've stripped that info above and it's not clear
1485cf7f2e2dSJohn Marino 	 what all the consequences are of passing a non-addr_bits_remove'd
1486cf7f2e2dSJohn Marino 	 address to create_solib_event_breakpoint.  The call to
1487cf7f2e2dSJohn Marino 	 find_pc_section verifies we know about the address and have some
1488cf7f2e2dSJohn Marino 	 hope of computing the right kind of breakpoint to use (via
1489cf7f2e2dSJohn Marino 	 symbol info).  It does mean that GDB needs to be pointed at a
1490cf7f2e2dSJohn Marino 	 non-stripped version of the dynamic linker in order to obtain
1491cf7f2e2dSJohn Marino 	 information it already knows about.  Sigh.  */
1492cf7f2e2dSJohn Marino 
14935796c8dcSSimon Schubert       os = find_pc_section (sym_addr);
14945796c8dcSSimon Schubert       if (os != NULL)
14955796c8dcSSimon Schubert 	{
14965796c8dcSSimon Schubert 	  /* Record the relocated start and end address of the dynamic linker
14975796c8dcSSimon Schubert 	     text and plt section for svr4_in_dynsym_resolve_code.  */
14985796c8dcSSimon Schubert 	  bfd *tmp_bfd;
14995796c8dcSSimon Schubert 	  CORE_ADDR load_addr;
15005796c8dcSSimon Schubert 
15015796c8dcSSimon Schubert 	  tmp_bfd = os->objfile->obfd;
15025796c8dcSSimon Schubert 	  load_addr = ANOFFSET (os->objfile->section_offsets,
1503*ef5ccd6cSJohn Marino 				SECT_OFF_TEXT (os->objfile));
15045796c8dcSSimon Schubert 
15055796c8dcSSimon Schubert 	  interp_sect = bfd_get_section_by_name (tmp_bfd, ".text");
15065796c8dcSSimon Schubert 	  if (interp_sect)
15075796c8dcSSimon Schubert 	    {
1508cf7f2e2dSJohn Marino 	      info->interp_text_sect_low =
15095796c8dcSSimon Schubert 		bfd_section_vma (tmp_bfd, interp_sect) + load_addr;
1510cf7f2e2dSJohn Marino 	      info->interp_text_sect_high =
1511cf7f2e2dSJohn Marino 		info->interp_text_sect_low
1512cf7f2e2dSJohn Marino 		+ bfd_section_size (tmp_bfd, interp_sect);
15135796c8dcSSimon Schubert 	    }
15145796c8dcSSimon Schubert 	  interp_sect = bfd_get_section_by_name (tmp_bfd, ".plt");
15155796c8dcSSimon Schubert 	  if (interp_sect)
15165796c8dcSSimon Schubert 	    {
1517cf7f2e2dSJohn Marino 	      info->interp_plt_sect_low =
15185796c8dcSSimon Schubert 		bfd_section_vma (tmp_bfd, interp_sect) + load_addr;
1519cf7f2e2dSJohn Marino 	      info->interp_plt_sect_high =
1520cf7f2e2dSJohn Marino 		info->interp_plt_sect_low
1521cf7f2e2dSJohn Marino 		+ bfd_section_size (tmp_bfd, interp_sect);
15225796c8dcSSimon Schubert 	    }
15235796c8dcSSimon Schubert 
1524*ef5ccd6cSJohn Marino 	  create_solib_event_breakpoint (target_gdbarch (), sym_addr);
15255796c8dcSSimon Schubert 	  return 1;
15265796c8dcSSimon Schubert 	}
15275796c8dcSSimon Schubert     }
15285796c8dcSSimon Schubert 
15295796c8dcSSimon Schubert   /* Find the program interpreter; if not found, warn the user and drop
15305796c8dcSSimon Schubert      into the old breakpoint at symbol code.  */
15315796c8dcSSimon Schubert   interp_name = find_program_interpreter ();
15325796c8dcSSimon Schubert   if (interp_name)
15335796c8dcSSimon Schubert     {
15345796c8dcSSimon Schubert       CORE_ADDR load_addr = 0;
15355796c8dcSSimon Schubert       int load_addr_found = 0;
15365796c8dcSSimon Schubert       int loader_found_in_list = 0;
15375796c8dcSSimon Schubert       struct so_list *so;
15385796c8dcSSimon Schubert       bfd *tmp_bfd = NULL;
15395796c8dcSSimon Schubert       struct target_ops *tmp_bfd_target;
15405796c8dcSSimon Schubert       volatile struct gdb_exception ex;
15415796c8dcSSimon Schubert 
15425796c8dcSSimon Schubert       sym_addr = 0;
15435796c8dcSSimon Schubert 
15445796c8dcSSimon Schubert       /* Now we need to figure out where the dynamic linker was
15455796c8dcSSimon Schubert          loaded so that we can load its symbols and place a breakpoint
15465796c8dcSSimon Schubert          in the dynamic linker itself.
15475796c8dcSSimon Schubert 
15485796c8dcSSimon Schubert          This address is stored on the stack.  However, I've been unable
15495796c8dcSSimon Schubert          to find any magic formula to find it for Solaris (appears to
15505796c8dcSSimon Schubert          be trivial on GNU/Linux).  Therefore, we have to try an alternate
15515796c8dcSSimon Schubert          mechanism to find the dynamic linker's base address.  */
15525796c8dcSSimon Schubert 
15535796c8dcSSimon Schubert       TRY_CATCH (ex, RETURN_MASK_ALL)
15545796c8dcSSimon Schubert         {
15555796c8dcSSimon Schubert 	  tmp_bfd = solib_bfd_open (interp_name);
15565796c8dcSSimon Schubert 	}
15575796c8dcSSimon Schubert       if (tmp_bfd == NULL)
15585796c8dcSSimon Schubert 	goto bkpt_at_symbol;
15595796c8dcSSimon Schubert 
15605796c8dcSSimon Schubert       /* Now convert the TMP_BFD into a target.  That way target, as
1561*ef5ccd6cSJohn Marino          well as BFD operations can be used.  */
15625796c8dcSSimon Schubert       tmp_bfd_target = target_bfd_reopen (tmp_bfd);
1563*ef5ccd6cSJohn Marino       /* target_bfd_reopen acquired its own reference, so we can
1564*ef5ccd6cSJohn Marino          release ours now.  */
1565*ef5ccd6cSJohn Marino       gdb_bfd_unref (tmp_bfd);
15665796c8dcSSimon Schubert 
15675796c8dcSSimon Schubert       /* On a running target, we can get the dynamic linker's base
15685796c8dcSSimon Schubert          address from the shared library table.  */
15695796c8dcSSimon Schubert       so = master_so_list ();
15705796c8dcSSimon Schubert       while (so)
15715796c8dcSSimon Schubert 	{
15725796c8dcSSimon Schubert 	  if (svr4_same_1 (interp_name, so->so_original_name))
15735796c8dcSSimon Schubert 	    {
15745796c8dcSSimon Schubert 	      load_addr_found = 1;
15755796c8dcSSimon Schubert 	      loader_found_in_list = 1;
1576a45ae5f8SJohn Marino 	      load_addr = lm_addr_check (so, tmp_bfd);
15775796c8dcSSimon Schubert 	      break;
15785796c8dcSSimon Schubert 	    }
15795796c8dcSSimon Schubert 	  so = so->next;
15805796c8dcSSimon Schubert 	}
15815796c8dcSSimon Schubert 
15825796c8dcSSimon Schubert       /* If we were not able to find the base address of the loader
15835796c8dcSSimon Schubert          from our so_list, then try using the AT_BASE auxilliary entry.  */
15845796c8dcSSimon Schubert       if (!load_addr_found)
15855796c8dcSSimon Schubert         if (target_auxv_search (&current_target, AT_BASE, &load_addr) > 0)
1586cf7f2e2dSJohn Marino 	  {
1587*ef5ccd6cSJohn Marino 	    int addr_bit = gdbarch_addr_bit (target_gdbarch ());
1588cf7f2e2dSJohn Marino 
1589cf7f2e2dSJohn Marino 	    /* Ensure LOAD_ADDR has proper sign in its possible upper bits so
1590cf7f2e2dSJohn Marino 	       that `+ load_addr' will overflow CORE_ADDR width not creating
1591cf7f2e2dSJohn Marino 	       invalid addresses like 0x101234567 for 32bit inferiors on 64bit
1592cf7f2e2dSJohn Marino 	       GDB.  */
1593cf7f2e2dSJohn Marino 
1594cf7f2e2dSJohn Marino 	    if (addr_bit < (sizeof (CORE_ADDR) * HOST_CHAR_BIT))
1595cf7f2e2dSJohn Marino 	      {
1596cf7f2e2dSJohn Marino 		CORE_ADDR space_size = (CORE_ADDR) 1 << addr_bit;
1597cf7f2e2dSJohn Marino 		CORE_ADDR tmp_entry_point = exec_entry_point (tmp_bfd,
1598cf7f2e2dSJohn Marino 							      tmp_bfd_target);
1599cf7f2e2dSJohn Marino 
1600cf7f2e2dSJohn Marino 		gdb_assert (load_addr < space_size);
1601cf7f2e2dSJohn Marino 
1602cf7f2e2dSJohn Marino 		/* TMP_ENTRY_POINT exceeding SPACE_SIZE would be for prelinked
1603cf7f2e2dSJohn Marino 		   64bit ld.so with 32bit executable, it should not happen.  */
1604cf7f2e2dSJohn Marino 
1605cf7f2e2dSJohn Marino 		if (tmp_entry_point < space_size
1606cf7f2e2dSJohn Marino 		    && tmp_entry_point + load_addr >= space_size)
1607cf7f2e2dSJohn Marino 		  load_addr -= space_size;
1608cf7f2e2dSJohn Marino 	      }
1609cf7f2e2dSJohn Marino 
16105796c8dcSSimon Schubert 	    load_addr_found = 1;
1611cf7f2e2dSJohn Marino 	  }
16125796c8dcSSimon Schubert 
16135796c8dcSSimon Schubert       /* Otherwise we find the dynamic linker's base address by examining
16145796c8dcSSimon Schubert 	 the current pc (which should point at the entry point for the
16155796c8dcSSimon Schubert 	 dynamic linker) and subtracting the offset of the entry point.
16165796c8dcSSimon Schubert 
16175796c8dcSSimon Schubert          This is more fragile than the previous approaches, but is a good
16185796c8dcSSimon Schubert          fallback method because it has actually been working well in
16195796c8dcSSimon Schubert          most cases.  */
16205796c8dcSSimon Schubert       if (!load_addr_found)
16215796c8dcSSimon Schubert 	{
16225796c8dcSSimon Schubert 	  struct regcache *regcache
1623*ef5ccd6cSJohn Marino 	    = get_thread_arch_regcache (inferior_ptid, target_gdbarch ());
1624cf7f2e2dSJohn Marino 
16255796c8dcSSimon Schubert 	  load_addr = (regcache_read_pc (regcache)
16265796c8dcSSimon Schubert 		       - exec_entry_point (tmp_bfd, tmp_bfd_target));
16275796c8dcSSimon Schubert 	}
16285796c8dcSSimon Schubert 
16295796c8dcSSimon Schubert       if (!loader_found_in_list)
16305796c8dcSSimon Schubert 	{
16315796c8dcSSimon Schubert 	  info->debug_loader_name = xstrdup (interp_name);
16325796c8dcSSimon Schubert 	  info->debug_loader_offset_p = 1;
16335796c8dcSSimon Schubert 	  info->debug_loader_offset = load_addr;
1634cf7f2e2dSJohn Marino 	  solib_add (NULL, from_tty, &current_target, auto_solib_add);
16355796c8dcSSimon Schubert 	}
16365796c8dcSSimon Schubert 
16375796c8dcSSimon Schubert       /* Record the relocated start and end address of the dynamic linker
16385796c8dcSSimon Schubert          text and plt section for svr4_in_dynsym_resolve_code.  */
16395796c8dcSSimon Schubert       interp_sect = bfd_get_section_by_name (tmp_bfd, ".text");
16405796c8dcSSimon Schubert       if (interp_sect)
16415796c8dcSSimon Schubert 	{
1642cf7f2e2dSJohn Marino 	  info->interp_text_sect_low =
16435796c8dcSSimon Schubert 	    bfd_section_vma (tmp_bfd, interp_sect) + load_addr;
1644cf7f2e2dSJohn Marino 	  info->interp_text_sect_high =
1645cf7f2e2dSJohn Marino 	    info->interp_text_sect_low
1646cf7f2e2dSJohn Marino 	    + bfd_section_size (tmp_bfd, interp_sect);
16475796c8dcSSimon Schubert 	}
16485796c8dcSSimon Schubert       interp_sect = bfd_get_section_by_name (tmp_bfd, ".plt");
16495796c8dcSSimon Schubert       if (interp_sect)
16505796c8dcSSimon Schubert 	{
1651cf7f2e2dSJohn Marino 	  info->interp_plt_sect_low =
16525796c8dcSSimon Schubert 	    bfd_section_vma (tmp_bfd, interp_sect) + load_addr;
1653cf7f2e2dSJohn Marino 	  info->interp_plt_sect_high =
1654cf7f2e2dSJohn Marino 	    info->interp_plt_sect_low
1655cf7f2e2dSJohn Marino 	    + bfd_section_size (tmp_bfd, interp_sect);
16565796c8dcSSimon Schubert 	}
16575796c8dcSSimon Schubert 
16585796c8dcSSimon Schubert       /* Now try to set a breakpoint in the dynamic linker.  */
16595796c8dcSSimon Schubert       for (bkpt_namep = solib_break_names; *bkpt_namep != NULL; bkpt_namep++)
16605796c8dcSSimon Schubert 	{
1661a45ae5f8SJohn Marino 	  sym_addr = gdb_bfd_lookup_symbol (tmp_bfd, cmp_name_and_sec_flags,
1662a45ae5f8SJohn Marino 					    (void *) *bkpt_namep);
16635796c8dcSSimon Schubert 	  if (sym_addr != 0)
16645796c8dcSSimon Schubert 	    break;
16655796c8dcSSimon Schubert 	}
16665796c8dcSSimon Schubert 
16675796c8dcSSimon Schubert       if (sym_addr != 0)
16685796c8dcSSimon Schubert 	/* Convert 'sym_addr' from a function pointer to an address.
16695796c8dcSSimon Schubert 	   Because we pass tmp_bfd_target instead of the current
16705796c8dcSSimon Schubert 	   target, this will always produce an unrelocated value.  */
1671*ef5ccd6cSJohn Marino 	sym_addr = gdbarch_convert_from_func_ptr_addr (target_gdbarch (),
16725796c8dcSSimon Schubert 						       sym_addr,
16735796c8dcSSimon Schubert 						       tmp_bfd_target);
16745796c8dcSSimon Schubert 
1675*ef5ccd6cSJohn Marino       /* We're done with both the temporary bfd and target.  Closing
1676*ef5ccd6cSJohn Marino          the target closes the underlying bfd, because it holds the
1677*ef5ccd6cSJohn Marino          only remaining reference.  */
16785796c8dcSSimon Schubert       target_close (tmp_bfd_target, 0);
16795796c8dcSSimon Schubert 
16805796c8dcSSimon Schubert       if (sym_addr != 0)
16815796c8dcSSimon Schubert 	{
1682*ef5ccd6cSJohn Marino 	  create_solib_event_breakpoint (target_gdbarch (), load_addr + sym_addr);
16835796c8dcSSimon Schubert 	  xfree (interp_name);
16845796c8dcSSimon Schubert 	  return 1;
16855796c8dcSSimon Schubert 	}
16865796c8dcSSimon Schubert 
16875796c8dcSSimon Schubert       /* For whatever reason we couldn't set a breakpoint in the dynamic
16885796c8dcSSimon Schubert          linker.  Warn and drop into the old code.  */
16895796c8dcSSimon Schubert     bkpt_at_symbol:
16905796c8dcSSimon Schubert       xfree (interp_name);
16915796c8dcSSimon Schubert       warning (_("Unable to find dynamic linker breakpoint function.\n"
16925796c8dcSSimon Schubert                "GDB will be unable to debug shared library initializers\n"
16935796c8dcSSimon Schubert                "and track explicitly loaded dynamic code."));
16945796c8dcSSimon Schubert     }
16955796c8dcSSimon Schubert 
16965796c8dcSSimon Schubert   /* Scan through the lists of symbols, trying to look up the symbol and
16975796c8dcSSimon Schubert      set a breakpoint there.  Terminate loop when we/if we succeed.  */
16985796c8dcSSimon Schubert 
16995796c8dcSSimon Schubert   for (bkpt_namep = solib_break_names; *bkpt_namep != NULL; bkpt_namep++)
17005796c8dcSSimon Schubert     {
17015796c8dcSSimon Schubert       msymbol = lookup_minimal_symbol (*bkpt_namep, NULL, symfile_objfile);
17025796c8dcSSimon Schubert       if ((msymbol != NULL) && (SYMBOL_VALUE_ADDRESS (msymbol) != 0))
17035796c8dcSSimon Schubert 	{
1704cf7f2e2dSJohn Marino 	  sym_addr = SYMBOL_VALUE_ADDRESS (msymbol);
1705*ef5ccd6cSJohn Marino 	  sym_addr = gdbarch_convert_from_func_ptr_addr (target_gdbarch (),
1706cf7f2e2dSJohn Marino 							 sym_addr,
1707cf7f2e2dSJohn Marino 							 &current_target);
1708*ef5ccd6cSJohn Marino 	  create_solib_event_breakpoint (target_gdbarch (), sym_addr);
17095796c8dcSSimon Schubert 	  return 1;
17105796c8dcSSimon Schubert 	}
17115796c8dcSSimon Schubert     }
17125796c8dcSSimon Schubert 
1713*ef5ccd6cSJohn Marino   if (interp_name != NULL && !current_inferior ()->attach_flag)
1714c50c785cSJohn Marino     {
17155796c8dcSSimon Schubert       for (bkpt_namep = bkpt_names; *bkpt_namep != NULL; bkpt_namep++)
17165796c8dcSSimon Schubert 	{
17175796c8dcSSimon Schubert 	  msymbol = lookup_minimal_symbol (*bkpt_namep, NULL, symfile_objfile);
17185796c8dcSSimon Schubert 	  if ((msymbol != NULL) && (SYMBOL_VALUE_ADDRESS (msymbol) != 0))
17195796c8dcSSimon Schubert 	    {
1720cf7f2e2dSJohn Marino 	      sym_addr = SYMBOL_VALUE_ADDRESS (msymbol);
1721*ef5ccd6cSJohn Marino 	      sym_addr = gdbarch_convert_from_func_ptr_addr (target_gdbarch (),
1722cf7f2e2dSJohn Marino 							     sym_addr,
1723cf7f2e2dSJohn Marino 							     &current_target);
1724*ef5ccd6cSJohn Marino 	      create_solib_event_breakpoint (target_gdbarch (), sym_addr);
17255796c8dcSSimon Schubert 	      return 1;
17265796c8dcSSimon Schubert 	    }
17275796c8dcSSimon Schubert 	}
1728c50c785cSJohn Marino     }
17295796c8dcSSimon Schubert   return 0;
17305796c8dcSSimon Schubert }
17315796c8dcSSimon Schubert 
1732a45ae5f8SJohn Marino /* Implement the "special_symbol_handling" target_so_ops method.  */
17335796c8dcSSimon Schubert 
17345796c8dcSSimon Schubert static void
svr4_special_symbol_handling(void)17355796c8dcSSimon Schubert svr4_special_symbol_handling (void)
17365796c8dcSSimon Schubert {
1737a45ae5f8SJohn Marino   /* Nothing to do.  */
17385796c8dcSSimon Schubert }
17395796c8dcSSimon Schubert 
1740cf7f2e2dSJohn Marino /* Read the ELF program headers from ABFD.  Return the contents and
1741cf7f2e2dSJohn Marino    set *PHDRS_SIZE to the size of the program headers.  */
17425796c8dcSSimon Schubert 
1743cf7f2e2dSJohn Marino static gdb_byte *
read_program_headers_from_bfd(bfd * abfd,int * phdrs_size)1744cf7f2e2dSJohn Marino read_program_headers_from_bfd (bfd *abfd, int *phdrs_size)
17455796c8dcSSimon Schubert {
1746cf7f2e2dSJohn Marino   Elf_Internal_Ehdr *ehdr;
1747cf7f2e2dSJohn Marino   gdb_byte *buf;
17485796c8dcSSimon Schubert 
1749cf7f2e2dSJohn Marino   ehdr = elf_elfheader (abfd);
17505796c8dcSSimon Schubert 
1751cf7f2e2dSJohn Marino   *phdrs_size = ehdr->e_phnum * ehdr->e_phentsize;
1752cf7f2e2dSJohn Marino   if (*phdrs_size == 0)
1753cf7f2e2dSJohn Marino     return NULL;
17545796c8dcSSimon Schubert 
1755cf7f2e2dSJohn Marino   buf = xmalloc (*phdrs_size);
1756cf7f2e2dSJohn Marino   if (bfd_seek (abfd, ehdr->e_phoff, SEEK_SET) != 0
1757cf7f2e2dSJohn Marino       || bfd_bread (buf, *phdrs_size, abfd) != *phdrs_size)
17585796c8dcSSimon Schubert     {
1759cf7f2e2dSJohn Marino       xfree (buf);
1760cf7f2e2dSJohn Marino       return NULL;
1761cf7f2e2dSJohn Marino     }
17625796c8dcSSimon Schubert 
1763cf7f2e2dSJohn Marino   return buf;
1764cf7f2e2dSJohn Marino }
1765cf7f2e2dSJohn Marino 
1766cf7f2e2dSJohn Marino /* Return 1 and fill *DISPLACEMENTP with detected PIE offset of inferior
1767cf7f2e2dSJohn Marino    exec_bfd.  Otherwise return 0.
17685796c8dcSSimon Schubert 
17695796c8dcSSimon Schubert    We relocate all of the sections by the same amount.  This
17705796c8dcSSimon Schubert    behavior is mandated by recent editions of the System V ABI.
17715796c8dcSSimon Schubert    According to the System V Application Binary Interface,
17725796c8dcSSimon Schubert    Edition 4.1, page 5-5:
17735796c8dcSSimon Schubert 
17745796c8dcSSimon Schubert      ...  Though the system chooses virtual addresses for
17755796c8dcSSimon Schubert      individual processes, it maintains the segments' relative
17765796c8dcSSimon Schubert      positions.  Because position-independent code uses relative
17775796c8dcSSimon Schubert      addressesing between segments, the difference between
17785796c8dcSSimon Schubert      virtual addresses in memory must match the difference
17795796c8dcSSimon Schubert      between virtual addresses in the file.  The difference
17805796c8dcSSimon Schubert      between the virtual address of any segment in memory and
17815796c8dcSSimon Schubert      the corresponding virtual address in the file is thus a
17825796c8dcSSimon Schubert      single constant value for any one executable or shared
17835796c8dcSSimon Schubert      object in a given process.  This difference is the base
17845796c8dcSSimon Schubert      address.  One use of the base address is to relocate the
17855796c8dcSSimon Schubert      memory image of the program during dynamic linking.
17865796c8dcSSimon Schubert 
17875796c8dcSSimon Schubert    The same language also appears in Edition 4.0 of the System V
1788cf7f2e2dSJohn Marino    ABI and is left unspecified in some of the earlier editions.
17895796c8dcSSimon Schubert 
1790cf7f2e2dSJohn Marino    Decide if the objfile needs to be relocated.  As indicated above, we will
1791cf7f2e2dSJohn Marino    only be here when execution is stopped.  But during attachment PC can be at
1792cf7f2e2dSJohn Marino    arbitrary address therefore regcache_read_pc can be misleading (contrary to
1793cf7f2e2dSJohn Marino    the auxv AT_ENTRY value).  Moreover for executable with interpreter section
1794cf7f2e2dSJohn Marino    regcache_read_pc would point to the interpreter and not the main executable.
17955796c8dcSSimon Schubert 
1796cf7f2e2dSJohn Marino    So, to summarize, relocations are necessary when the start address obtained
1797cf7f2e2dSJohn Marino    from the executable is different from the address in auxv AT_ENTRY entry.
17985796c8dcSSimon Schubert 
1799cf7f2e2dSJohn Marino    [ The astute reader will note that we also test to make sure that
1800cf7f2e2dSJohn Marino      the executable in question has the DYNAMIC flag set.  It is my
1801cf7f2e2dSJohn Marino      opinion that this test is unnecessary (undesirable even).  It
1802cf7f2e2dSJohn Marino      was added to avoid inadvertent relocation of an executable
1803cf7f2e2dSJohn Marino      whose e_type member in the ELF header is not ET_DYN.  There may
1804cf7f2e2dSJohn Marino      be a time in the future when it is desirable to do relocations
1805cf7f2e2dSJohn Marino      on other types of files as well in which case this condition
1806cf7f2e2dSJohn Marino      should either be removed or modified to accomodate the new file
1807cf7f2e2dSJohn Marino      type.  - Kevin, Nov 2000. ]  */
1808cf7f2e2dSJohn Marino 
1809cf7f2e2dSJohn Marino static int
svr4_exec_displacement(CORE_ADDR * displacementp)1810cf7f2e2dSJohn Marino svr4_exec_displacement (CORE_ADDR *displacementp)
18115796c8dcSSimon Schubert {
1812cf7f2e2dSJohn Marino   /* ENTRY_POINT is a possible function descriptor - before
1813cf7f2e2dSJohn Marino      a call to gdbarch_convert_from_func_ptr_addr.  */
1814cf7f2e2dSJohn Marino   CORE_ADDR entry_point, displacement;
1815cf7f2e2dSJohn Marino 
1816cf7f2e2dSJohn Marino   if (exec_bfd == NULL)
1817cf7f2e2dSJohn Marino     return 0;
1818cf7f2e2dSJohn Marino 
1819cf7f2e2dSJohn Marino   /* Therefore for ELF it is ET_EXEC and not ET_DYN.  Both shared libraries
1820cf7f2e2dSJohn Marino      being executed themselves and PIE (Position Independent Executable)
1821cf7f2e2dSJohn Marino      executables are ET_DYN.  */
1822cf7f2e2dSJohn Marino 
1823cf7f2e2dSJohn Marino   if ((bfd_get_file_flags (exec_bfd) & DYNAMIC) == 0)
1824cf7f2e2dSJohn Marino     return 0;
1825cf7f2e2dSJohn Marino 
1826cf7f2e2dSJohn Marino   if (target_auxv_search (&current_target, AT_ENTRY, &entry_point) <= 0)
1827cf7f2e2dSJohn Marino     return 0;
1828cf7f2e2dSJohn Marino 
1829cf7f2e2dSJohn Marino   displacement = entry_point - bfd_get_start_address (exec_bfd);
1830cf7f2e2dSJohn Marino 
1831cf7f2e2dSJohn Marino   /* Verify the DISPLACEMENT candidate complies with the required page
1832cf7f2e2dSJohn Marino      alignment.  It is cheaper than the program headers comparison below.  */
1833cf7f2e2dSJohn Marino 
1834cf7f2e2dSJohn Marino   if (bfd_get_flavour (exec_bfd) == bfd_target_elf_flavour)
1835cf7f2e2dSJohn Marino     {
1836cf7f2e2dSJohn Marino       const struct elf_backend_data *elf = get_elf_backend_data (exec_bfd);
1837cf7f2e2dSJohn Marino 
1838cf7f2e2dSJohn Marino       /* p_align of PT_LOAD segments does not specify any alignment but
1839cf7f2e2dSJohn Marino 	 only congruency of addresses:
1840cf7f2e2dSJohn Marino 	   p_offset % p_align == p_vaddr % p_align
1841cf7f2e2dSJohn Marino 	 Kernel is free to load the executable with lower alignment.  */
1842cf7f2e2dSJohn Marino 
1843cf7f2e2dSJohn Marino       if ((displacement & (elf->minpagesize - 1)) != 0)
1844cf7f2e2dSJohn Marino 	return 0;
18455796c8dcSSimon Schubert     }
18465796c8dcSSimon Schubert 
1847cf7f2e2dSJohn Marino   /* Verify that the auxilliary vector describes the same file as exec_bfd, by
1848cf7f2e2dSJohn Marino      comparing their program headers.  If the program headers in the auxilliary
1849cf7f2e2dSJohn Marino      vector do not match the program headers in the executable, then we are
1850cf7f2e2dSJohn Marino      looking at a different file than the one used by the kernel - for
1851cf7f2e2dSJohn Marino      instance, "gdb program" connected to "gdbserver :PORT ld.so program".  */
18525796c8dcSSimon Schubert 
1853cf7f2e2dSJohn Marino   if (bfd_get_flavour (exec_bfd) == bfd_target_elf_flavour)
1854cf7f2e2dSJohn Marino     {
1855cf7f2e2dSJohn Marino       /* Be optimistic and clear OK only if GDB was able to verify the headers
1856cf7f2e2dSJohn Marino 	 really do not match.  */
1857cf7f2e2dSJohn Marino       int phdrs_size, phdrs2_size, ok = 1;
1858cf7f2e2dSJohn Marino       gdb_byte *buf, *buf2;
1859cf7f2e2dSJohn Marino       int arch_size;
1860cf7f2e2dSJohn Marino 
1861cf7f2e2dSJohn Marino       buf = read_program_header (-1, &phdrs_size, &arch_size);
1862cf7f2e2dSJohn Marino       buf2 = read_program_headers_from_bfd (exec_bfd, &phdrs2_size);
1863cf7f2e2dSJohn Marino       if (buf != NULL && buf2 != NULL)
1864cf7f2e2dSJohn Marino 	{
1865*ef5ccd6cSJohn Marino 	  enum bfd_endian byte_order = gdbarch_byte_order (target_gdbarch ());
1866cf7f2e2dSJohn Marino 
1867cf7f2e2dSJohn Marino 	  /* We are dealing with three different addresses.  EXEC_BFD
1868cf7f2e2dSJohn Marino 	     represents current address in on-disk file.  target memory content
1869cf7f2e2dSJohn Marino 	     may be different from EXEC_BFD as the file may have been prelinked
1870cf7f2e2dSJohn Marino 	     to a different address after the executable has been loaded.
1871cf7f2e2dSJohn Marino 	     Moreover the address of placement in target memory can be
1872c50c785cSJohn Marino 	     different from what the program headers in target memory say -
1873c50c785cSJohn Marino 	     this is the goal of PIE.
1874cf7f2e2dSJohn Marino 
1875cf7f2e2dSJohn Marino 	     Detected DISPLACEMENT covers both the offsets of PIE placement and
1876cf7f2e2dSJohn Marino 	     possible new prelink performed after start of the program.  Here
1877cf7f2e2dSJohn Marino 	     relocate BUF and BUF2 just by the EXEC_BFD vs. target memory
1878cf7f2e2dSJohn Marino 	     content offset for the verification purpose.  */
1879cf7f2e2dSJohn Marino 
1880cf7f2e2dSJohn Marino 	  if (phdrs_size != phdrs2_size
1881cf7f2e2dSJohn Marino 	      || bfd_get_arch_size (exec_bfd) != arch_size)
1882cf7f2e2dSJohn Marino 	    ok = 0;
1883c50c785cSJohn Marino 	  else if (arch_size == 32
1884c50c785cSJohn Marino 		   && phdrs_size >= sizeof (Elf32_External_Phdr)
1885cf7f2e2dSJohn Marino 	           && phdrs_size % sizeof (Elf32_External_Phdr) == 0)
1886cf7f2e2dSJohn Marino 	    {
1887cf7f2e2dSJohn Marino 	      Elf_Internal_Ehdr *ehdr2 = elf_tdata (exec_bfd)->elf_header;
1888cf7f2e2dSJohn Marino 	      Elf_Internal_Phdr *phdr2 = elf_tdata (exec_bfd)->phdr;
1889cf7f2e2dSJohn Marino 	      CORE_ADDR displacement = 0;
1890cf7f2e2dSJohn Marino 	      int i;
1891cf7f2e2dSJohn Marino 
1892cf7f2e2dSJohn Marino 	      /* DISPLACEMENT could be found more easily by the difference of
1893cf7f2e2dSJohn Marino 		 ehdr2->e_entry.  But we haven't read the ehdr yet, and we
1894cf7f2e2dSJohn Marino 		 already have enough information to compute that displacement
1895cf7f2e2dSJohn Marino 		 with what we've read.  */
1896cf7f2e2dSJohn Marino 
1897cf7f2e2dSJohn Marino 	      for (i = 0; i < ehdr2->e_phnum; i++)
1898cf7f2e2dSJohn Marino 		if (phdr2[i].p_type == PT_LOAD)
1899cf7f2e2dSJohn Marino 		  {
1900cf7f2e2dSJohn Marino 		    Elf32_External_Phdr *phdrp;
1901cf7f2e2dSJohn Marino 		    gdb_byte *buf_vaddr_p, *buf_paddr_p;
1902cf7f2e2dSJohn Marino 		    CORE_ADDR vaddr, paddr;
1903cf7f2e2dSJohn Marino 		    CORE_ADDR displacement_vaddr = 0;
1904cf7f2e2dSJohn Marino 		    CORE_ADDR displacement_paddr = 0;
1905cf7f2e2dSJohn Marino 
1906cf7f2e2dSJohn Marino 		    phdrp = &((Elf32_External_Phdr *) buf)[i];
1907cf7f2e2dSJohn Marino 		    buf_vaddr_p = (gdb_byte *) &phdrp->p_vaddr;
1908cf7f2e2dSJohn Marino 		    buf_paddr_p = (gdb_byte *) &phdrp->p_paddr;
1909cf7f2e2dSJohn Marino 
1910cf7f2e2dSJohn Marino 		    vaddr = extract_unsigned_integer (buf_vaddr_p, 4,
1911cf7f2e2dSJohn Marino 						      byte_order);
1912cf7f2e2dSJohn Marino 		    displacement_vaddr = vaddr - phdr2[i].p_vaddr;
1913cf7f2e2dSJohn Marino 
1914cf7f2e2dSJohn Marino 		    paddr = extract_unsigned_integer (buf_paddr_p, 4,
1915cf7f2e2dSJohn Marino 						      byte_order);
1916cf7f2e2dSJohn Marino 		    displacement_paddr = paddr - phdr2[i].p_paddr;
1917cf7f2e2dSJohn Marino 
1918cf7f2e2dSJohn Marino 		    if (displacement_vaddr == displacement_paddr)
1919cf7f2e2dSJohn Marino 		      displacement = displacement_vaddr;
1920cf7f2e2dSJohn Marino 
1921cf7f2e2dSJohn Marino 		    break;
1922cf7f2e2dSJohn Marino 		  }
1923cf7f2e2dSJohn Marino 
1924cf7f2e2dSJohn Marino 	      /* Now compare BUF and BUF2 with optional DISPLACEMENT.  */
1925cf7f2e2dSJohn Marino 
1926cf7f2e2dSJohn Marino 	      for (i = 0; i < phdrs_size / sizeof (Elf32_External_Phdr); i++)
1927cf7f2e2dSJohn Marino 		{
1928cf7f2e2dSJohn Marino 		  Elf32_External_Phdr *phdrp;
1929cf7f2e2dSJohn Marino 		  Elf32_External_Phdr *phdr2p;
1930cf7f2e2dSJohn Marino 		  gdb_byte *buf_vaddr_p, *buf_paddr_p;
1931cf7f2e2dSJohn Marino 		  CORE_ADDR vaddr, paddr;
1932c50c785cSJohn Marino 		  asection *plt2_asect;
1933cf7f2e2dSJohn Marino 
1934cf7f2e2dSJohn Marino 		  phdrp = &((Elf32_External_Phdr *) buf)[i];
1935cf7f2e2dSJohn Marino 		  buf_vaddr_p = (gdb_byte *) &phdrp->p_vaddr;
1936cf7f2e2dSJohn Marino 		  buf_paddr_p = (gdb_byte *) &phdrp->p_paddr;
1937cf7f2e2dSJohn Marino 		  phdr2p = &((Elf32_External_Phdr *) buf2)[i];
1938cf7f2e2dSJohn Marino 
1939cf7f2e2dSJohn Marino 		  /* PT_GNU_STACK is an exception by being never relocated by
1940cf7f2e2dSJohn Marino 		     prelink as its addresses are always zero.  */
1941cf7f2e2dSJohn Marino 
1942cf7f2e2dSJohn Marino 		  if (memcmp (phdrp, phdr2p, sizeof (*phdrp)) == 0)
1943cf7f2e2dSJohn Marino 		    continue;
1944cf7f2e2dSJohn Marino 
1945cf7f2e2dSJohn Marino 		  /* Check also other adjustment combinations - PR 11786.  */
1946cf7f2e2dSJohn Marino 
1947c50c785cSJohn Marino 		  vaddr = extract_unsigned_integer (buf_vaddr_p, 4,
1948c50c785cSJohn Marino 						    byte_order);
1949cf7f2e2dSJohn Marino 		  vaddr -= displacement;
1950cf7f2e2dSJohn Marino 		  store_unsigned_integer (buf_vaddr_p, 4, byte_order, vaddr);
1951cf7f2e2dSJohn Marino 
1952c50c785cSJohn Marino 		  paddr = extract_unsigned_integer (buf_paddr_p, 4,
1953c50c785cSJohn Marino 						    byte_order);
1954cf7f2e2dSJohn Marino 		  paddr -= displacement;
1955cf7f2e2dSJohn Marino 		  store_unsigned_integer (buf_paddr_p, 4, byte_order, paddr);
1956cf7f2e2dSJohn Marino 
1957cf7f2e2dSJohn Marino 		  if (memcmp (phdrp, phdr2p, sizeof (*phdrp)) == 0)
1958cf7f2e2dSJohn Marino 		    continue;
1959cf7f2e2dSJohn Marino 
1960c50c785cSJohn Marino 		  /* prelink can convert .plt SHT_NOBITS to SHT_PROGBITS.  */
1961c50c785cSJohn Marino 		  plt2_asect = bfd_get_section_by_name (exec_bfd, ".plt");
1962c50c785cSJohn Marino 		  if (plt2_asect)
1963c50c785cSJohn Marino 		    {
1964c50c785cSJohn Marino 		      int content2;
1965c50c785cSJohn Marino 		      gdb_byte *buf_filesz_p = (gdb_byte *) &phdrp->p_filesz;
1966c50c785cSJohn Marino 		      CORE_ADDR filesz;
1967c50c785cSJohn Marino 
1968c50c785cSJohn Marino 		      content2 = (bfd_get_section_flags (exec_bfd, plt2_asect)
1969c50c785cSJohn Marino 				  & SEC_HAS_CONTENTS) != 0;
1970c50c785cSJohn Marino 
1971c50c785cSJohn Marino 		      filesz = extract_unsigned_integer (buf_filesz_p, 4,
1972c50c785cSJohn Marino 							 byte_order);
1973c50c785cSJohn Marino 
1974c50c785cSJohn Marino 		      /* PLT2_ASECT is from on-disk file (exec_bfd) while
1975c50c785cSJohn Marino 			 FILESZ is from the in-memory image.  */
1976c50c785cSJohn Marino 		      if (content2)
1977c50c785cSJohn Marino 			filesz += bfd_get_section_size (plt2_asect);
1978c50c785cSJohn Marino 		      else
1979c50c785cSJohn Marino 			filesz -= bfd_get_section_size (plt2_asect);
1980c50c785cSJohn Marino 
1981c50c785cSJohn Marino 		      store_unsigned_integer (buf_filesz_p, 4, byte_order,
1982c50c785cSJohn Marino 					      filesz);
1983c50c785cSJohn Marino 
1984c50c785cSJohn Marino 		      if (memcmp (phdrp, phdr2p, sizeof (*phdrp)) == 0)
1985c50c785cSJohn Marino 			continue;
1986c50c785cSJohn Marino 		    }
1987c50c785cSJohn Marino 
1988cf7f2e2dSJohn Marino 		  ok = 0;
1989cf7f2e2dSJohn Marino 		  break;
1990cf7f2e2dSJohn Marino 		}
1991cf7f2e2dSJohn Marino 	    }
1992c50c785cSJohn Marino 	  else if (arch_size == 64
1993c50c785cSJohn Marino 		   && phdrs_size >= sizeof (Elf64_External_Phdr)
1994cf7f2e2dSJohn Marino 	           && phdrs_size % sizeof (Elf64_External_Phdr) == 0)
1995cf7f2e2dSJohn Marino 	    {
1996cf7f2e2dSJohn Marino 	      Elf_Internal_Ehdr *ehdr2 = elf_tdata (exec_bfd)->elf_header;
1997cf7f2e2dSJohn Marino 	      Elf_Internal_Phdr *phdr2 = elf_tdata (exec_bfd)->phdr;
1998cf7f2e2dSJohn Marino 	      CORE_ADDR displacement = 0;
1999cf7f2e2dSJohn Marino 	      int i;
2000cf7f2e2dSJohn Marino 
2001cf7f2e2dSJohn Marino 	      /* DISPLACEMENT could be found more easily by the difference of
2002cf7f2e2dSJohn Marino 		 ehdr2->e_entry.  But we haven't read the ehdr yet, and we
2003cf7f2e2dSJohn Marino 		 already have enough information to compute that displacement
2004cf7f2e2dSJohn Marino 		 with what we've read.  */
2005cf7f2e2dSJohn Marino 
2006cf7f2e2dSJohn Marino 	      for (i = 0; i < ehdr2->e_phnum; i++)
2007cf7f2e2dSJohn Marino 		if (phdr2[i].p_type == PT_LOAD)
2008cf7f2e2dSJohn Marino 		  {
2009cf7f2e2dSJohn Marino 		    Elf64_External_Phdr *phdrp;
2010cf7f2e2dSJohn Marino 		    gdb_byte *buf_vaddr_p, *buf_paddr_p;
2011cf7f2e2dSJohn Marino 		    CORE_ADDR vaddr, paddr;
2012cf7f2e2dSJohn Marino 		    CORE_ADDR displacement_vaddr = 0;
2013cf7f2e2dSJohn Marino 		    CORE_ADDR displacement_paddr = 0;
2014cf7f2e2dSJohn Marino 
2015cf7f2e2dSJohn Marino 		    phdrp = &((Elf64_External_Phdr *) buf)[i];
2016cf7f2e2dSJohn Marino 		    buf_vaddr_p = (gdb_byte *) &phdrp->p_vaddr;
2017cf7f2e2dSJohn Marino 		    buf_paddr_p = (gdb_byte *) &phdrp->p_paddr;
2018cf7f2e2dSJohn Marino 
2019cf7f2e2dSJohn Marino 		    vaddr = extract_unsigned_integer (buf_vaddr_p, 8,
2020cf7f2e2dSJohn Marino 						      byte_order);
2021cf7f2e2dSJohn Marino 		    displacement_vaddr = vaddr - phdr2[i].p_vaddr;
2022cf7f2e2dSJohn Marino 
2023cf7f2e2dSJohn Marino 		    paddr = extract_unsigned_integer (buf_paddr_p, 8,
2024cf7f2e2dSJohn Marino 						      byte_order);
2025cf7f2e2dSJohn Marino 		    displacement_paddr = paddr - phdr2[i].p_paddr;
2026cf7f2e2dSJohn Marino 
2027cf7f2e2dSJohn Marino 		    if (displacement_vaddr == displacement_paddr)
2028cf7f2e2dSJohn Marino 		      displacement = displacement_vaddr;
2029cf7f2e2dSJohn Marino 
2030cf7f2e2dSJohn Marino 		    break;
2031cf7f2e2dSJohn Marino 		  }
2032cf7f2e2dSJohn Marino 
2033cf7f2e2dSJohn Marino 	      /* Now compare BUF and BUF2 with optional DISPLACEMENT.  */
2034cf7f2e2dSJohn Marino 
2035cf7f2e2dSJohn Marino 	      for (i = 0; i < phdrs_size / sizeof (Elf64_External_Phdr); i++)
2036cf7f2e2dSJohn Marino 		{
2037cf7f2e2dSJohn Marino 		  Elf64_External_Phdr *phdrp;
2038cf7f2e2dSJohn Marino 		  Elf64_External_Phdr *phdr2p;
2039cf7f2e2dSJohn Marino 		  gdb_byte *buf_vaddr_p, *buf_paddr_p;
2040cf7f2e2dSJohn Marino 		  CORE_ADDR vaddr, paddr;
2041c50c785cSJohn Marino 		  asection *plt2_asect;
2042cf7f2e2dSJohn Marino 
2043cf7f2e2dSJohn Marino 		  phdrp = &((Elf64_External_Phdr *) buf)[i];
2044cf7f2e2dSJohn Marino 		  buf_vaddr_p = (gdb_byte *) &phdrp->p_vaddr;
2045cf7f2e2dSJohn Marino 		  buf_paddr_p = (gdb_byte *) &phdrp->p_paddr;
2046cf7f2e2dSJohn Marino 		  phdr2p = &((Elf64_External_Phdr *) buf2)[i];
2047cf7f2e2dSJohn Marino 
2048cf7f2e2dSJohn Marino 		  /* PT_GNU_STACK is an exception by being never relocated by
2049cf7f2e2dSJohn Marino 		     prelink as its addresses are always zero.  */
2050cf7f2e2dSJohn Marino 
2051cf7f2e2dSJohn Marino 		  if (memcmp (phdrp, phdr2p, sizeof (*phdrp)) == 0)
2052cf7f2e2dSJohn Marino 		    continue;
2053cf7f2e2dSJohn Marino 
2054cf7f2e2dSJohn Marino 		  /* Check also other adjustment combinations - PR 11786.  */
2055cf7f2e2dSJohn Marino 
2056c50c785cSJohn Marino 		  vaddr = extract_unsigned_integer (buf_vaddr_p, 8,
2057c50c785cSJohn Marino 						    byte_order);
2058cf7f2e2dSJohn Marino 		  vaddr -= displacement;
2059cf7f2e2dSJohn Marino 		  store_unsigned_integer (buf_vaddr_p, 8, byte_order, vaddr);
2060cf7f2e2dSJohn Marino 
2061c50c785cSJohn Marino 		  paddr = extract_unsigned_integer (buf_paddr_p, 8,
2062c50c785cSJohn Marino 						    byte_order);
2063cf7f2e2dSJohn Marino 		  paddr -= displacement;
2064cf7f2e2dSJohn Marino 		  store_unsigned_integer (buf_paddr_p, 8, byte_order, paddr);
2065cf7f2e2dSJohn Marino 
2066cf7f2e2dSJohn Marino 		  if (memcmp (phdrp, phdr2p, sizeof (*phdrp)) == 0)
2067cf7f2e2dSJohn Marino 		    continue;
2068cf7f2e2dSJohn Marino 
2069c50c785cSJohn Marino 		  /* prelink can convert .plt SHT_NOBITS to SHT_PROGBITS.  */
2070c50c785cSJohn Marino 		  plt2_asect = bfd_get_section_by_name (exec_bfd, ".plt");
2071c50c785cSJohn Marino 		  if (plt2_asect)
2072c50c785cSJohn Marino 		    {
2073c50c785cSJohn Marino 		      int content2;
2074c50c785cSJohn Marino 		      gdb_byte *buf_filesz_p = (gdb_byte *) &phdrp->p_filesz;
2075c50c785cSJohn Marino 		      CORE_ADDR filesz;
2076c50c785cSJohn Marino 
2077c50c785cSJohn Marino 		      content2 = (bfd_get_section_flags (exec_bfd, plt2_asect)
2078c50c785cSJohn Marino 				  & SEC_HAS_CONTENTS) != 0;
2079c50c785cSJohn Marino 
2080c50c785cSJohn Marino 		      filesz = extract_unsigned_integer (buf_filesz_p, 8,
2081c50c785cSJohn Marino 							 byte_order);
2082c50c785cSJohn Marino 
2083c50c785cSJohn Marino 		      /* PLT2_ASECT is from on-disk file (exec_bfd) while
2084c50c785cSJohn Marino 			 FILESZ is from the in-memory image.  */
2085c50c785cSJohn Marino 		      if (content2)
2086c50c785cSJohn Marino 			filesz += bfd_get_section_size (plt2_asect);
2087c50c785cSJohn Marino 		      else
2088c50c785cSJohn Marino 			filesz -= bfd_get_section_size (plt2_asect);
2089c50c785cSJohn Marino 
2090c50c785cSJohn Marino 		      store_unsigned_integer (buf_filesz_p, 8, byte_order,
2091c50c785cSJohn Marino 					      filesz);
2092c50c785cSJohn Marino 
2093c50c785cSJohn Marino 		      if (memcmp (phdrp, phdr2p, sizeof (*phdrp)) == 0)
2094c50c785cSJohn Marino 			continue;
2095c50c785cSJohn Marino 		    }
2096c50c785cSJohn Marino 
2097cf7f2e2dSJohn Marino 		  ok = 0;
2098cf7f2e2dSJohn Marino 		  break;
2099cf7f2e2dSJohn Marino 		}
2100cf7f2e2dSJohn Marino 	    }
2101cf7f2e2dSJohn Marino 	  else
2102cf7f2e2dSJohn Marino 	    ok = 0;
2103cf7f2e2dSJohn Marino 	}
2104cf7f2e2dSJohn Marino 
2105cf7f2e2dSJohn Marino       xfree (buf);
2106cf7f2e2dSJohn Marino       xfree (buf2);
2107cf7f2e2dSJohn Marino 
2108cf7f2e2dSJohn Marino       if (!ok)
2109cf7f2e2dSJohn Marino 	return 0;
2110cf7f2e2dSJohn Marino     }
2111cf7f2e2dSJohn Marino 
2112cf7f2e2dSJohn Marino   if (info_verbose)
2113cf7f2e2dSJohn Marino     {
2114cf7f2e2dSJohn Marino       /* It can be printed repeatedly as there is no easy way to check
2115cf7f2e2dSJohn Marino 	 the executable symbols/file has been already relocated to
2116cf7f2e2dSJohn Marino 	 displacement.  */
2117cf7f2e2dSJohn Marino 
2118cf7f2e2dSJohn Marino       printf_unfiltered (_("Using PIE (Position Independent Executable) "
2119cf7f2e2dSJohn Marino 			   "displacement %s for \"%s\".\n"),
2120*ef5ccd6cSJohn Marino 			 paddress (target_gdbarch (), displacement),
2121cf7f2e2dSJohn Marino 			 bfd_get_filename (exec_bfd));
2122cf7f2e2dSJohn Marino     }
2123cf7f2e2dSJohn Marino 
2124cf7f2e2dSJohn Marino   *displacementp = displacement;
2125cf7f2e2dSJohn Marino   return 1;
2126cf7f2e2dSJohn Marino }
2127cf7f2e2dSJohn Marino 
2128cf7f2e2dSJohn Marino /* Relocate the main executable.  This function should be called upon
2129cf7f2e2dSJohn Marino    stopping the inferior process at the entry point to the program.
2130cf7f2e2dSJohn Marino    The entry point from BFD is compared to the AT_ENTRY of AUXV and if they are
2131cf7f2e2dSJohn Marino    different, the main executable is relocated by the proper amount.  */
2132cf7f2e2dSJohn Marino 
2133cf7f2e2dSJohn Marino static void
svr4_relocate_main_executable(void)2134cf7f2e2dSJohn Marino svr4_relocate_main_executable (void)
2135cf7f2e2dSJohn Marino {
2136cf7f2e2dSJohn Marino   CORE_ADDR displacement;
2137cf7f2e2dSJohn Marino 
2138cf7f2e2dSJohn Marino   /* If we are re-running this executable, SYMFILE_OBJFILE->SECTION_OFFSETS
2139cf7f2e2dSJohn Marino      probably contains the offsets computed using the PIE displacement
2140cf7f2e2dSJohn Marino      from the previous run, which of course are irrelevant for this run.
2141cf7f2e2dSJohn Marino      So we need to determine the new PIE displacement and recompute the
2142cf7f2e2dSJohn Marino      section offsets accordingly, even if SYMFILE_OBJFILE->SECTION_OFFSETS
2143cf7f2e2dSJohn Marino      already contains pre-computed offsets.
2144cf7f2e2dSJohn Marino 
2145cf7f2e2dSJohn Marino      If we cannot compute the PIE displacement, either:
2146cf7f2e2dSJohn Marino 
2147cf7f2e2dSJohn Marino        - The executable is not PIE.
2148cf7f2e2dSJohn Marino 
2149cf7f2e2dSJohn Marino        - SYMFILE_OBJFILE does not match the executable started in the target.
2150cf7f2e2dSJohn Marino 	 This can happen for main executable symbols loaded at the host while
2151cf7f2e2dSJohn Marino 	 `ld.so --ld-args main-executable' is loaded in the target.
2152cf7f2e2dSJohn Marino 
2153cf7f2e2dSJohn Marino      Then we leave the section offsets untouched and use them as is for
2154cf7f2e2dSJohn Marino      this run.  Either:
2155cf7f2e2dSJohn Marino 
2156cf7f2e2dSJohn Marino        - These section offsets were properly reset earlier, and thus
2157cf7f2e2dSJohn Marino 	 already contain the correct values.  This can happen for instance
2158cf7f2e2dSJohn Marino 	 when reconnecting via the remote protocol to a target that supports
2159cf7f2e2dSJohn Marino 	 the `qOffsets' packet.
2160cf7f2e2dSJohn Marino 
2161cf7f2e2dSJohn Marino        - The section offsets were not reset earlier, and the best we can
2162c50c785cSJohn Marino 	 hope is that the old offsets are still applicable to the new run.  */
2163cf7f2e2dSJohn Marino 
2164cf7f2e2dSJohn Marino   if (! svr4_exec_displacement (&displacement))
2165cf7f2e2dSJohn Marino     return;
2166cf7f2e2dSJohn Marino 
2167cf7f2e2dSJohn Marino   /* Even DISPLACEMENT 0 is a valid new difference of in-memory vs. in-file
2168cf7f2e2dSJohn Marino      addresses.  */
2169cf7f2e2dSJohn Marino 
2170cf7f2e2dSJohn Marino   if (symfile_objfile)
2171cf7f2e2dSJohn Marino     {
2172cf7f2e2dSJohn Marino       struct section_offsets *new_offsets;
2173cf7f2e2dSJohn Marino       int i;
2174cf7f2e2dSJohn Marino 
2175cf7f2e2dSJohn Marino       new_offsets = alloca (symfile_objfile->num_sections
2176cf7f2e2dSJohn Marino 			    * sizeof (*new_offsets));
2177cf7f2e2dSJohn Marino 
2178cf7f2e2dSJohn Marino       for (i = 0; i < symfile_objfile->num_sections; i++)
2179cf7f2e2dSJohn Marino 	new_offsets->offsets[i] = displacement;
2180cf7f2e2dSJohn Marino 
2181cf7f2e2dSJohn Marino       objfile_relocate (symfile_objfile, new_offsets);
2182cf7f2e2dSJohn Marino     }
2183cf7f2e2dSJohn Marino   else if (exec_bfd)
2184cf7f2e2dSJohn Marino     {
2185cf7f2e2dSJohn Marino       asection *asect;
2186cf7f2e2dSJohn Marino 
2187cf7f2e2dSJohn Marino       for (asect = exec_bfd->sections; asect != NULL; asect = asect->next)
2188cf7f2e2dSJohn Marino 	exec_set_section_address (bfd_get_filename (exec_bfd), asect->index,
2189cf7f2e2dSJohn Marino 				  (bfd_section_vma (exec_bfd, asect)
2190cf7f2e2dSJohn Marino 				   + displacement));
21915796c8dcSSimon Schubert     }
21925796c8dcSSimon Schubert }
21935796c8dcSSimon Schubert 
2194a45ae5f8SJohn Marino /* Implement the "create_inferior_hook" target_solib_ops method.
21955796c8dcSSimon Schubert 
21965796c8dcSSimon Schubert    For SVR4 executables, this first instruction is either the first
21975796c8dcSSimon Schubert    instruction in the dynamic linker (for dynamically linked
21985796c8dcSSimon Schubert    executables) or the instruction at "start" for statically linked
21995796c8dcSSimon Schubert    executables.  For dynamically linked executables, the system
22005796c8dcSSimon Schubert    first exec's /lib/libc.so.N, which contains the dynamic linker,
22015796c8dcSSimon Schubert    and starts it running.  The dynamic linker maps in any needed
22025796c8dcSSimon Schubert    shared libraries, maps in the actual user executable, and then
22035796c8dcSSimon Schubert    jumps to "start" in the user executable.
22045796c8dcSSimon Schubert 
2205a45ae5f8SJohn Marino    We can arrange to cooperate with the dynamic linker to discover the
2206a45ae5f8SJohn Marino    names of shared libraries that are dynamically linked, and the base
2207a45ae5f8SJohn Marino    addresses to which they are linked.
22085796c8dcSSimon Schubert 
22095796c8dcSSimon Schubert    This function is responsible for discovering those names and
22105796c8dcSSimon Schubert    addresses, and saving sufficient information about them to allow
2211*ef5ccd6cSJohn Marino    their symbols to be read at a later time.  */
22125796c8dcSSimon Schubert 
22135796c8dcSSimon Schubert static void
svr4_solib_create_inferior_hook(int from_tty)2214cf7f2e2dSJohn Marino svr4_solib_create_inferior_hook (int from_tty)
22155796c8dcSSimon Schubert {
22165796c8dcSSimon Schubert   struct svr4_info *info;
22175796c8dcSSimon Schubert 
2218cf7f2e2dSJohn Marino   info = get_svr4_info ();
22195796c8dcSSimon Schubert 
22205796c8dcSSimon Schubert   /* Relocate the main executable if necessary.  */
22215796c8dcSSimon Schubert   svr4_relocate_main_executable ();
22225796c8dcSSimon Schubert 
2223c50c785cSJohn Marino   /* No point setting a breakpoint in the dynamic linker if we can't
2224c50c785cSJohn Marino      hit it (e.g., a core file, or a trace file).  */
2225c50c785cSJohn Marino   if (!target_has_execution)
2226c50c785cSJohn Marino     return;
2227c50c785cSJohn Marino 
22285796c8dcSSimon Schubert   if (!svr4_have_link_map_offsets ())
22295796c8dcSSimon Schubert     return;
22305796c8dcSSimon Schubert 
2231cf7f2e2dSJohn Marino   if (!enable_break (info, from_tty))
22325796c8dcSSimon Schubert     return;
22335796c8dcSSimon Schubert }
22345796c8dcSSimon Schubert 
22355796c8dcSSimon Schubert static void
svr4_clear_solib(void)22365796c8dcSSimon Schubert svr4_clear_solib (void)
22375796c8dcSSimon Schubert {
2238cf7f2e2dSJohn Marino   struct svr4_info *info;
2239cf7f2e2dSJohn Marino 
2240cf7f2e2dSJohn Marino   info = get_svr4_info ();
2241cf7f2e2dSJohn Marino   info->debug_base = 0;
2242cf7f2e2dSJohn Marino   info->debug_loader_offset_p = 0;
2243cf7f2e2dSJohn Marino   info->debug_loader_offset = 0;
2244cf7f2e2dSJohn Marino   xfree (info->debug_loader_name);
2245cf7f2e2dSJohn Marino   info->debug_loader_name = NULL;
22465796c8dcSSimon Schubert }
22475796c8dcSSimon Schubert 
22485796c8dcSSimon Schubert /* Clear any bits of ADDR that wouldn't fit in a target-format
22495796c8dcSSimon Schubert    data pointer.  "Data pointer" here refers to whatever sort of
22505796c8dcSSimon Schubert    address the dynamic linker uses to manage its sections.  At the
22515796c8dcSSimon Schubert    moment, we don't support shared libraries on any processors where
22525796c8dcSSimon Schubert    code and data pointers are different sizes.
22535796c8dcSSimon Schubert 
22545796c8dcSSimon Schubert    This isn't really the right solution.  What we really need here is
22555796c8dcSSimon Schubert    a way to do arithmetic on CORE_ADDR values that respects the
22565796c8dcSSimon Schubert    natural pointer/address correspondence.  (For example, on the MIPS,
22575796c8dcSSimon Schubert    converting a 32-bit pointer to a 64-bit CORE_ADDR requires you to
22585796c8dcSSimon Schubert    sign-extend the value.  There, simply truncating the bits above
22595796c8dcSSimon Schubert    gdbarch_ptr_bit, as we do below, is no good.)  This should probably
22605796c8dcSSimon Schubert    be a new gdbarch method or something.  */
22615796c8dcSSimon Schubert static CORE_ADDR
svr4_truncate_ptr(CORE_ADDR addr)22625796c8dcSSimon Schubert svr4_truncate_ptr (CORE_ADDR addr)
22635796c8dcSSimon Schubert {
2264*ef5ccd6cSJohn Marino   if (gdbarch_ptr_bit (target_gdbarch ()) == sizeof (CORE_ADDR) * 8)
22655796c8dcSSimon Schubert     /* We don't need to truncate anything, and the bit twiddling below
22665796c8dcSSimon Schubert        will fail due to overflow problems.  */
22675796c8dcSSimon Schubert     return addr;
22685796c8dcSSimon Schubert   else
2269*ef5ccd6cSJohn Marino     return addr & (((CORE_ADDR) 1 << gdbarch_ptr_bit (target_gdbarch ())) - 1);
22705796c8dcSSimon Schubert }
22715796c8dcSSimon Schubert 
22725796c8dcSSimon Schubert 
22735796c8dcSSimon Schubert static void
svr4_relocate_section_addresses(struct so_list * so,struct target_section * sec)22745796c8dcSSimon Schubert svr4_relocate_section_addresses (struct so_list *so,
22755796c8dcSSimon Schubert                                  struct target_section *sec)
22765796c8dcSSimon Schubert {
2277a45ae5f8SJohn Marino   sec->addr    = svr4_truncate_ptr (sec->addr    + lm_addr_check (so,
22785796c8dcSSimon Schubert 								  sec->bfd));
2279a45ae5f8SJohn Marino   sec->endaddr = svr4_truncate_ptr (sec->endaddr + lm_addr_check (so,
22805796c8dcSSimon Schubert 								  sec->bfd));
22815796c8dcSSimon Schubert }
22825796c8dcSSimon Schubert 
22835796c8dcSSimon Schubert 
22845796c8dcSSimon Schubert /* Architecture-specific operations.  */
22855796c8dcSSimon Schubert 
22865796c8dcSSimon Schubert /* Per-architecture data key.  */
22875796c8dcSSimon Schubert static struct gdbarch_data *solib_svr4_data;
22885796c8dcSSimon Schubert 
22895796c8dcSSimon Schubert struct solib_svr4_ops
22905796c8dcSSimon Schubert {
22915796c8dcSSimon Schubert   /* Return a description of the layout of `struct link_map'.  */
22925796c8dcSSimon Schubert   struct link_map_offsets *(*fetch_link_map_offsets)(void);
22935796c8dcSSimon Schubert };
22945796c8dcSSimon Schubert 
22955796c8dcSSimon Schubert /* Return a default for the architecture-specific operations.  */
22965796c8dcSSimon Schubert 
22975796c8dcSSimon Schubert static void *
solib_svr4_init(struct obstack * obstack)22985796c8dcSSimon Schubert solib_svr4_init (struct obstack *obstack)
22995796c8dcSSimon Schubert {
23005796c8dcSSimon Schubert   struct solib_svr4_ops *ops;
23015796c8dcSSimon Schubert 
23025796c8dcSSimon Schubert   ops = OBSTACK_ZALLOC (obstack, struct solib_svr4_ops);
23035796c8dcSSimon Schubert   ops->fetch_link_map_offsets = NULL;
23045796c8dcSSimon Schubert   return ops;
23055796c8dcSSimon Schubert }
23065796c8dcSSimon Schubert 
23075796c8dcSSimon Schubert /* Set the architecture-specific `struct link_map_offsets' fetcher for
23085796c8dcSSimon Schubert    GDBARCH to FLMO.  Also, install SVR4 solib_ops into GDBARCH.  */
23095796c8dcSSimon Schubert 
23105796c8dcSSimon Schubert void
set_solib_svr4_fetch_link_map_offsets(struct gdbarch * gdbarch,struct link_map_offsets * (* flmo)(void))23115796c8dcSSimon Schubert set_solib_svr4_fetch_link_map_offsets (struct gdbarch *gdbarch,
23125796c8dcSSimon Schubert                                        struct link_map_offsets *(*flmo) (void))
23135796c8dcSSimon Schubert {
23145796c8dcSSimon Schubert   struct solib_svr4_ops *ops = gdbarch_data (gdbarch, solib_svr4_data);
23155796c8dcSSimon Schubert 
23165796c8dcSSimon Schubert   ops->fetch_link_map_offsets = flmo;
23175796c8dcSSimon Schubert 
23185796c8dcSSimon Schubert   set_solib_ops (gdbarch, &svr4_so_ops);
23195796c8dcSSimon Schubert }
23205796c8dcSSimon Schubert 
23215796c8dcSSimon Schubert /* Fetch a link_map_offsets structure using the architecture-specific
23225796c8dcSSimon Schubert    `struct link_map_offsets' fetcher.  */
23235796c8dcSSimon Schubert 
23245796c8dcSSimon Schubert static struct link_map_offsets *
svr4_fetch_link_map_offsets(void)23255796c8dcSSimon Schubert svr4_fetch_link_map_offsets (void)
23265796c8dcSSimon Schubert {
2327*ef5ccd6cSJohn Marino   struct solib_svr4_ops *ops = gdbarch_data (target_gdbarch (), solib_svr4_data);
23285796c8dcSSimon Schubert 
23295796c8dcSSimon Schubert   gdb_assert (ops->fetch_link_map_offsets);
23305796c8dcSSimon Schubert   return ops->fetch_link_map_offsets ();
23315796c8dcSSimon Schubert }
23325796c8dcSSimon Schubert 
23335796c8dcSSimon Schubert /* Return 1 if a link map offset fetcher has been defined, 0 otherwise.  */
23345796c8dcSSimon Schubert 
23355796c8dcSSimon Schubert static int
svr4_have_link_map_offsets(void)23365796c8dcSSimon Schubert svr4_have_link_map_offsets (void)
23375796c8dcSSimon Schubert {
2338*ef5ccd6cSJohn Marino   struct solib_svr4_ops *ops = gdbarch_data (target_gdbarch (), solib_svr4_data);
2339cf7f2e2dSJohn Marino 
23405796c8dcSSimon Schubert   return (ops->fetch_link_map_offsets != NULL);
23415796c8dcSSimon Schubert }
23425796c8dcSSimon Schubert 
23435796c8dcSSimon Schubert 
23445796c8dcSSimon Schubert /* Most OS'es that have SVR4-style ELF dynamic libraries define a
23455796c8dcSSimon Schubert    `struct r_debug' and a `struct link_map' that are binary compatible
23465796c8dcSSimon Schubert    with the origional SVR4 implementation.  */
23475796c8dcSSimon Schubert 
23485796c8dcSSimon Schubert /* Fetch (and possibly build) an appropriate `struct link_map_offsets'
23495796c8dcSSimon Schubert    for an ILP32 SVR4 system.  */
23505796c8dcSSimon Schubert 
23515796c8dcSSimon Schubert struct link_map_offsets *
svr4_ilp32_fetch_link_map_offsets(void)23525796c8dcSSimon Schubert svr4_ilp32_fetch_link_map_offsets (void)
23535796c8dcSSimon Schubert {
23545796c8dcSSimon Schubert   static struct link_map_offsets lmo;
23555796c8dcSSimon Schubert   static struct link_map_offsets *lmp = NULL;
23565796c8dcSSimon Schubert 
23575796c8dcSSimon Schubert   if (lmp == NULL)
23585796c8dcSSimon Schubert     {
23595796c8dcSSimon Schubert       lmp = &lmo;
23605796c8dcSSimon Schubert 
23615796c8dcSSimon Schubert       lmo.r_version_offset = 0;
23625796c8dcSSimon Schubert       lmo.r_version_size = 4;
23635796c8dcSSimon Schubert       lmo.r_map_offset = 4;
23645796c8dcSSimon Schubert       lmo.r_brk_offset = 8;
23655796c8dcSSimon Schubert       lmo.r_ldsomap_offset = 20;
23665796c8dcSSimon Schubert 
23675796c8dcSSimon Schubert       /* Everything we need is in the first 20 bytes.  */
23685796c8dcSSimon Schubert       lmo.link_map_size = 20;
23695796c8dcSSimon Schubert       lmo.l_addr_offset = 0;
23705796c8dcSSimon Schubert       lmo.l_name_offset = 4;
23715796c8dcSSimon Schubert       lmo.l_ld_offset = 8;
23725796c8dcSSimon Schubert       lmo.l_next_offset = 12;
23735796c8dcSSimon Schubert       lmo.l_prev_offset = 16;
23745796c8dcSSimon Schubert     }
23755796c8dcSSimon Schubert 
23765796c8dcSSimon Schubert   return lmp;
23775796c8dcSSimon Schubert }
23785796c8dcSSimon Schubert 
23795796c8dcSSimon Schubert /* Fetch (and possibly build) an appropriate `struct link_map_offsets'
23805796c8dcSSimon Schubert    for an LP64 SVR4 system.  */
23815796c8dcSSimon Schubert 
23825796c8dcSSimon Schubert struct link_map_offsets *
svr4_lp64_fetch_link_map_offsets(void)23835796c8dcSSimon Schubert svr4_lp64_fetch_link_map_offsets (void)
23845796c8dcSSimon Schubert {
23855796c8dcSSimon Schubert   static struct link_map_offsets lmo;
23865796c8dcSSimon Schubert   static struct link_map_offsets *lmp = NULL;
23875796c8dcSSimon Schubert 
23885796c8dcSSimon Schubert   if (lmp == NULL)
23895796c8dcSSimon Schubert     {
23905796c8dcSSimon Schubert       lmp = &lmo;
23915796c8dcSSimon Schubert 
23925796c8dcSSimon Schubert       lmo.r_version_offset = 0;
23935796c8dcSSimon Schubert       lmo.r_version_size = 4;
23945796c8dcSSimon Schubert       lmo.r_map_offset = 8;
23955796c8dcSSimon Schubert       lmo.r_brk_offset = 16;
23965796c8dcSSimon Schubert       lmo.r_ldsomap_offset = 40;
23975796c8dcSSimon Schubert 
23985796c8dcSSimon Schubert       /* Everything we need is in the first 40 bytes.  */
23995796c8dcSSimon Schubert       lmo.link_map_size = 40;
24005796c8dcSSimon Schubert       lmo.l_addr_offset = 0;
24015796c8dcSSimon Schubert       lmo.l_name_offset = 8;
24025796c8dcSSimon Schubert       lmo.l_ld_offset = 16;
24035796c8dcSSimon Schubert       lmo.l_next_offset = 24;
24045796c8dcSSimon Schubert       lmo.l_prev_offset = 32;
24055796c8dcSSimon Schubert     }
24065796c8dcSSimon Schubert 
24075796c8dcSSimon Schubert   return lmp;
24085796c8dcSSimon Schubert }
24095796c8dcSSimon Schubert 
24105796c8dcSSimon Schubert 
24115796c8dcSSimon Schubert struct target_so_ops svr4_so_ops;
24125796c8dcSSimon Schubert 
24135796c8dcSSimon Schubert /* Lookup global symbol for ELF DSOs linked with -Bsymbolic.  Those DSOs have a
24145796c8dcSSimon Schubert    different rule for symbol lookup.  The lookup begins here in the DSO, not in
24155796c8dcSSimon Schubert    the main executable.  */
24165796c8dcSSimon Schubert 
24175796c8dcSSimon Schubert static struct symbol *
elf_lookup_lib_symbol(const struct objfile * objfile,const char * name,const domain_enum domain)24185796c8dcSSimon Schubert elf_lookup_lib_symbol (const struct objfile *objfile,
24195796c8dcSSimon Schubert 		       const char *name,
24205796c8dcSSimon Schubert 		       const domain_enum domain)
24215796c8dcSSimon Schubert {
2422cf7f2e2dSJohn Marino   bfd *abfd;
2423cf7f2e2dSJohn Marino 
2424cf7f2e2dSJohn Marino   if (objfile == symfile_objfile)
2425cf7f2e2dSJohn Marino     abfd = exec_bfd;
2426cf7f2e2dSJohn Marino   else
2427cf7f2e2dSJohn Marino     {
2428cf7f2e2dSJohn Marino       /* OBJFILE should have been passed as the non-debug one.  */
2429cf7f2e2dSJohn Marino       gdb_assert (objfile->separate_debug_objfile_backlink == NULL);
2430cf7f2e2dSJohn Marino 
2431cf7f2e2dSJohn Marino       abfd = objfile->obfd;
2432cf7f2e2dSJohn Marino     }
2433cf7f2e2dSJohn Marino 
2434cf7f2e2dSJohn Marino   if (abfd == NULL || scan_dyntag (DT_SYMBOLIC, abfd, NULL) != 1)
24355796c8dcSSimon Schubert     return NULL;
24365796c8dcSSimon Schubert 
2437cf7f2e2dSJohn Marino   return lookup_global_symbol_from_objfile (objfile, name, domain);
24385796c8dcSSimon Schubert }
24395796c8dcSSimon Schubert 
24405796c8dcSSimon Schubert extern initialize_file_ftype _initialize_svr4_solib; /* -Wmissing-prototypes */
24415796c8dcSSimon Schubert 
24425796c8dcSSimon Schubert void
_initialize_svr4_solib(void)24435796c8dcSSimon Schubert _initialize_svr4_solib (void)
24445796c8dcSSimon Schubert {
24455796c8dcSSimon Schubert   solib_svr4_data = gdbarch_data_register_pre_init (solib_svr4_init);
2446cf7f2e2dSJohn Marino   solib_svr4_pspace_data
2447*ef5ccd6cSJohn Marino     = register_program_space_data_with_cleanup (NULL, svr4_pspace_data_cleanup);
24485796c8dcSSimon Schubert 
24495796c8dcSSimon Schubert   svr4_so_ops.relocate_section_addresses = svr4_relocate_section_addresses;
24505796c8dcSSimon Schubert   svr4_so_ops.free_so = svr4_free_so;
24515796c8dcSSimon Schubert   svr4_so_ops.clear_solib = svr4_clear_solib;
24525796c8dcSSimon Schubert   svr4_so_ops.solib_create_inferior_hook = svr4_solib_create_inferior_hook;
24535796c8dcSSimon Schubert   svr4_so_ops.special_symbol_handling = svr4_special_symbol_handling;
24545796c8dcSSimon Schubert   svr4_so_ops.current_sos = svr4_current_sos;
24555796c8dcSSimon Schubert   svr4_so_ops.open_symbol_file_object = open_symbol_file_object;
24565796c8dcSSimon Schubert   svr4_so_ops.in_dynsym_resolve_code = svr4_in_dynsym_resolve_code;
24575796c8dcSSimon Schubert   svr4_so_ops.bfd_open = solib_bfd_open;
24585796c8dcSSimon Schubert   svr4_so_ops.lookup_lib_global_symbol = elf_lookup_lib_symbol;
24595796c8dcSSimon Schubert   svr4_so_ops.same = svr4_same;
2460cf7f2e2dSJohn Marino   svr4_so_ops.keep_data_in_core = svr4_keep_data_in_core;
24615796c8dcSSimon Schubert }
2462