summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMark Kettenis <kettenis@gnu.org>2006-02-02 22:15:01 +0000
committerMark Kettenis <kettenis@gnu.org>2006-02-02 22:15:01 +0000
commite4cd0d6a2669159e399359ff2cb59dd93668f056 (patch)
tree6954ecef430a59241e88db40ab413e0f99f95f1e
parentde205c03b963123f4f7fecd0520861b161b3795e (diff)
downloadbinutils-gdb-e4cd0d6a2669159e399359ff2cb59dd93668f056.tar.gz
* solib-svr4.h (struct link_map_offsets): Remove r_debug_size and
r_map_size members. Add r_version_offset, r_version_size and r_ldsomap_offset members. * solib-svr4.c (solib_svr4_r_map): Renamed from fetch_link_map_member. Simplify using read_memory_typed_address. (solib_svr4_r_ldsomap): New function. (open_symbol_file_object): Use solib_svr_r_map. (svr4_current_sos): Use solib_svr4_r_map and look for the dynamic linker by using solib_svr4_r_ldsomap. (svr4_ilp32_fetch_link_map_offsets) (svr4_lp64_fetch_link_map_offsets): Adjust for changes to `struct link_map_offsets'. * solib-legacy.c (legacy_svr4_fetch_link_map_offsets): Adjust for changes to `struct link_map_offsets'. * mipsnbsd-tdep.c (mipsnbsd_ilp32_fetch_link_map_offsets) (mipsnbsd_lp64_fetch_link_map_offsets): Adjust for changes to `struct link_map_offsets'.
-rw-r--r--gdb/ChangeLog20
-rw-r--r--gdb/mipsnbsd-tdep.c33
-rw-r--r--gdb/solib-legacy.c15
-rw-r--r--gdb/solib-svr4.c98
-rw-r--r--gdb/solib-svr4.h13
5 files changed, 103 insertions, 76 deletions
diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index 468e8bb88b1..a419107acf1 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,23 @@
+2006-02-02 Mark Kettenis <kettenis@gnu.org>
+
+ * solib-svr4.h (struct link_map_offsets): Remove r_debug_size and
+ r_map_size members. Add r_version_offset, r_version_size and
+ r_ldsomap_offset members.
+ * solib-svr4.c (solib_svr4_r_map): Renamed from
+ fetch_link_map_member. Simplify using read_memory_typed_address.
+ (solib_svr4_r_ldsomap): New function.
+ (open_symbol_file_object): Use solib_svr_r_map.
+ (svr4_current_sos): Use solib_svr4_r_map and look for the dynamic
+ linker by using solib_svr4_r_ldsomap.
+ (svr4_ilp32_fetch_link_map_offsets)
+ (svr4_lp64_fetch_link_map_offsets): Adjust for changes to `struct
+ link_map_offsets'.
+ * solib-legacy.c (legacy_svr4_fetch_link_map_offsets): Adjust for
+ changes to `struct link_map_offsets'.
+ * mipsnbsd-tdep.c (mipsnbsd_ilp32_fetch_link_map_offsets)
+ (mipsnbsd_lp64_fetch_link_map_offsets): Adjust for changes to
+ `struct link_map_offsets'.
+
2006-02-01 Daniel Jacobowitz <dan@codesourcery.com>
* linux-nat.c (struct saved_ptids, threads_to_delete)
diff --git a/gdb/mipsnbsd-tdep.c b/gdb/mipsnbsd-tdep.c
index d878bcec072..dfdc01d8b98 100644
--- a/gdb/mipsnbsd-tdep.c
+++ b/gdb/mipsnbsd-tdep.c
@@ -1,6 +1,7 @@
/* Target-dependent code for NetBSD/mips.
- Copyright (C) 2002, 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2003, 2004, 2006 Free Software Foundation, Inc.
+
Contributed by Wasabi Systems, Inc.
This file is part of GDB.
@@ -327,21 +328,21 @@ mipsnbsd_ilp32_fetch_link_map_offsets (void)
{
lmp = &lmo;
- /* Everything we need is in the first 8 bytes. */
- lmo.r_debug_size = 8;
+ lmo.r_version_offset = 0;
+ lmo.r_version_size = 4;
lmo.r_map_offset = 4;
- lmo.r_map_size = 4;
+ lmo.r_ldsomap_offset = -1;
/* Everything we need is in the first 24 bytes. */
lmo.link_map_size = 24;
lmo.l_addr_offset = 4;
- lmo.l_addr_size = 4;
+ lmo.l_addr_size = 4;
lmo.l_name_offset = 8;
- lmo.l_name_size = 4;
+ lmo.l_name_size = 4;
lmo.l_next_offset = 16;
- lmo.l_next_size = 4;
+ lmo.l_next_size = 4;
lmo.l_prev_offset = 20;
- lmo.l_prev_size = 4;
+ lmo.l_prev_size = 4;
}
return lmp;
@@ -357,21 +358,21 @@ mipsnbsd_lp64_fetch_link_map_offsets (void)
{
lmp = &lmo;
- /* Everything we need is in the first 16 bytes. */
- lmo.r_debug_size = 16;
- lmo.r_map_offset = 8;
- lmo.r_map_size = 8;
+ lmo.r_version_offset = 0;
+ lmo.r_version_size = 4;
+ lmo.r_map_offset = 8;
+ lmo.r_ldsomap_offset = -1;
/* Everything we need is in the first 40 bytes. */
lmo.link_map_size = 48;
lmo.l_addr_offset = 0;
- lmo.l_addr_size = 8;
+ lmo.l_addr_size = 8;
lmo.l_name_offset = 16;
- lmo.l_name_size = 8;
+ lmo.l_name_size = 8;
lmo.l_next_offset = 32;
- lmo.l_next_size = 8;
+ lmo.l_next_size = 8;
lmo.l_prev_offset = 40;
- lmo.l_prev_size = 8;
+ lmo.l_prev_size = 8;
}
return lmp;
diff --git a/gdb/solib-legacy.c b/gdb/solib-legacy.c
index 237df349d02..67899933268 100644
--- a/gdb/solib-legacy.c
+++ b/gdb/solib-legacy.c
@@ -1,5 +1,6 @@
/* Provide legacy r_debug and link_map support for SVR4-like native targets.
- Copyright (C) 2000, 2001
+
+ Copyright (C) 2000, 2001, 2006
Free Software Foundation, Inc.
This file is part of GDB.
@@ -55,10 +56,10 @@ legacy_svr4_fetch_link_map_offsets (void)
lmp = &lmo;
#ifdef HAVE_STRUCT_LINK_MAP_WITH_L_MEMBERS
- lmo.r_debug_size = sizeof (struct r_debug);
-
+ lmo.r_version_offset = offsetof (struct r_debug, r_version);
+ lmo.r_version_size = fieldsize (struct r_debug, r_version);
lmo.r_map_offset = offsetof (struct r_debug, r_map);
- lmo.r_map_size = fieldsize (struct r_debug, r_map);
+ lmo.r_ldsomap_offset = -1;
lmo.link_map_size = sizeof (struct link_map);
@@ -107,10 +108,10 @@ legacy_svr4_fetch_link_map_offsets (void)
{
lmp32 = &lmo32;
- lmo32.r_debug_size = sizeof (struct r_debug32);
-
+ lmo32.r_version_offset = offsetof (struct r_debug32, r_version);
+ lmo32.r_version_size = fieldsize (struct r_debug32, r_version);
lmo32.r_map_offset = offsetof (struct r_debug32, r_map);
- lmo32.r_map_size = fieldsize (struct r_debug32, r_map);
+ lmo32.r_ldsomap_offset = -1;
lmo32.link_map_size = sizeof (struct link_map32);
diff --git a/gdb/solib-svr4.c b/gdb/solib-svr4.c
index 0a19b4a78fe..caadb4a26d6 100644
--- a/gdb/solib-svr4.c
+++ b/gdb/solib-svr4.c
@@ -1,7 +1,7 @@
/* Handle SVR4 shared libraries for GDB, the GNU Debugger.
Copyright (C) 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1998, 1999,
- 2000, 2001, 2003, 2004, 2005
+ 2000, 2001, 2003, 2004, 2005, 2006
Free Software Foundation, Inc.
This file is part of GDB.
@@ -447,43 +447,40 @@ locate_base (void)
return (debug_base);
}
-/*
-
- LOCAL FUNCTION
-
- first_link_map_member -- locate first member in dynamic linker's map
-
- SYNOPSIS
-
- static CORE_ADDR first_link_map_member (void)
-
- DESCRIPTION
+/* Find the first element in the inferior's dynamic link map, and
+ return its address in the inferior.
- Find the first element in the inferior's dynamic link map, and
- return its address in the inferior. This function doesn't copy the
- link map entry itself into our address space; current_sos actually
- does the reading. */
+ FIXME: Perhaps we should validate the info somehow, perhaps by
+ checking r_version for a known version number, or r_state for
+ RT_CONSISTENT. */
static CORE_ADDR
-first_link_map_member (void)
+solib_svr4_r_map (void)
{
- CORE_ADDR lm = 0;
struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
- gdb_byte *r_map_buf = xmalloc (lmo->r_map_size);
- struct cleanup *cleanups = make_cleanup (xfree, r_map_buf);
- read_memory (debug_base + lmo->r_map_offset, r_map_buf, lmo->r_map_size);
+ return read_memory_typed_address (debug_base + lmo->r_map_offset,
+ builtin_type_void_data_ptr);
+}
- /* Assume that the address is unsigned. */
- lm = extract_unsigned_integer (r_map_buf, lmo->r_map_size);
+/* Find the link map for the dynamic linker (if it is not in the
+ normal list of loaded shared objects). */
- /* FIXME: Perhaps we should validate the info somehow, perhaps by
- checking r_version for a known version number, or r_state for
- RT_CONSISTENT. */
+static CORE_ADDR
+solib_svr4_r_ldsomap (void)
+{
+ struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
+ ULONGEST version;
- do_cleanups (cleanups);
+ /* Check version, and return zero if `struct r_debug' doesn't have
+ the r_ldsomap member. */
+ version = read_memory_unsigned_integer (debug_base + lmo->r_version_offset,
+ lmo->r_version_size);
+ if (version < 2 || lmo->r_ldsomap_offset == -1)
+ return 0;
- return (lm);
+ return read_memory_typed_address (debug_base + lmo->r_ldsomap_offset,
+ builtin_type_void_data_ptr);
}
/*
@@ -527,7 +524,8 @@ open_symbol_file_object (void *from_ttyp)
return 0; /* failed somehow... */
/* First link map member should be the executable. */
- if ((lm = first_link_map_member ()) == 0)
+ lm = solib_svr4_r_map ();
+ if (lm == 0)
return 0; /* failed somehow... */
/* Read address of name from target memory to GDB. */
@@ -585,6 +583,7 @@ svr4_current_sos (void)
CORE_ADDR lm;
struct so_list *head = 0;
struct so_list **link_ptr = &head;
+ CORE_ADDR ldsomap = 0;
/* Make sure we've looked up the inferior's dynamic linker's base
structure. */
@@ -600,7 +599,7 @@ svr4_current_sos (void)
/* Walk the inferior's link map list, and build our list of
`struct so_list' nodes. */
- lm = first_link_map_member ();
+ lm = solib_svr4_r_map ();
while (lm)
{
struct link_map_offsets *lmo = svr4_fetch_link_map_offsets ();
@@ -622,7 +621,7 @@ svr4_current_sos (void)
SVR4, it has no name. For others (Solaris 2.3 for example), it
does have a name, so we can no longer use a missing name to
decide when to ignore it. */
- if (IGNORE_FIRST_LINK_MAP_ENTRY (new))
+ if (IGNORE_FIRST_LINK_MAP_ENTRY (new) && ldsomap == 0)
free_so (new);
else
{
@@ -656,6 +655,13 @@ svr4_current_sos (void)
}
}
+ /* On Solaris, the dynamic linker is not in the normal list of
+ shared objects, so make sure we pick it up too. Having
+ symbol information for the dynamic linker is quite crucial
+ for skipping dynamic linker resolver code. */
+ if (lm == 0 && ldsomap == 0)
+ lm = ldsomap = solib_svr4_r_ldsomap ();
+
discard_cleanups (old_chain);
}
@@ -677,7 +683,7 @@ svr4_fetch_objfile_link_map (struct objfile *objfile)
return 0; /* failed somehow... */
/* Position ourselves on the first link map. */
- lm = first_link_map_member ();
+ lm = solib_svr4_r_map ();
while (lm)
{
/* Get info on the layout of the r_debug and link_map structures. */
@@ -1345,21 +1351,21 @@ svr4_ilp32_fetch_link_map_offsets (void)
{
lmp = &lmo;
- /* Everything we need is in the first 8 bytes. */
- lmo.r_debug_size = 8;
+ lmo.r_version_offset = 0;
+ lmo.r_version_size = 4;
lmo.r_map_offset = 4;
- lmo.r_map_size = 4;
+ lmo.r_ldsomap_offset = 20;
/* Everything we need is in the first 20 bytes. */
lmo.link_map_size = 20;
lmo.l_addr_offset = 0;
- lmo.l_addr_size = 4;
+ lmo.l_addr_size = 4;
lmo.l_name_offset = 4;
- lmo.l_name_size = 4;
+ lmo.l_name_size = 4;
lmo.l_next_offset = 12;
- lmo.l_next_size = 4;
+ lmo.l_next_size = 4;
lmo.l_prev_offset = 16;
- lmo.l_prev_size = 4;
+ lmo.l_prev_size = 4;
}
return lmp;
@@ -1378,21 +1384,21 @@ svr4_lp64_fetch_link_map_offsets (void)
{
lmp = &lmo;
- /* Everything we need is in the first 16 bytes. */
- lmo.r_debug_size = 16;
+ lmo.r_version_offset = 0;
+ lmo.r_version_size = 4;
lmo.r_map_offset = 8;
- lmo.r_map_size = 8;
+ lmo.r_ldsomap_offset = 40;
/* Everything we need is in the first 40 bytes. */
lmo.link_map_size = 40;
lmo.l_addr_offset = 0;
- lmo.l_addr_size = 8;
+ lmo.l_addr_size = 8;
lmo.l_name_offset = 8;
- lmo.l_name_size = 8;
+ lmo.l_name_size = 8;
lmo.l_next_offset = 24;
- lmo.l_next_size = 8;
+ lmo.l_next_size = 8;
lmo.l_prev_offset = 32;
- lmo.l_prev_size = 8;
+ lmo.l_prev_size = 8;
}
return lmp;
diff --git a/gdb/solib-svr4.h b/gdb/solib-svr4.h
index 082b3e25fe5..ae2740e0de7 100644
--- a/gdb/solib-svr4.h
+++ b/gdb/solib-svr4.h
@@ -1,6 +1,6 @@
/* Handle shared libraries for GDB, the GNU Debugger.
- Copyright (C) 2000, 2004
+ Copyright (C) 2000, 2004, 2006
Free Software Foundation, Inc.
This file is part of GDB.
@@ -31,15 +31,14 @@ struct objfile;
struct link_map_offsets
{
- /* Size of struct r_debug (or equivalent), or at least enough of it to
- be able to obtain the r_map field. */
- int r_debug_size;
+ /* Offset and size of r_debug.r_version. */
+ int r_version_offset, r_version_size;
- /* Offset to the r_map field in struct r_debug. */
+ /* Offset of r_debug.r_map. */
int r_map_offset;
- /* Size of the r_map field in struct r_debug. */
- int r_map_size;
+ /* Offset of r_debug.r_ldsomap. */
+ int r_ldsomap_offset;
/* Size of struct link_map (or equivalent), or at least enough of it
to be able to obtain the fields below. */