2011-09-27 Tristan Gingold <gingold@adacore.com>

* target.h (enum target_object): Add TARGET_OBJECT_DARWIN_DYLD_INFO.
	* solib-darwin.c (DYLD_VERSION_MAX): Update number.
	(darwin_solib_get_all_image_info_addr_at_init): New function.
	(darwin_solib_read_all_image_info_addr): Likewise.
	(darwin_solib_create_inferior_hook): Use the above two functions.
	* darwin-nat.c (darwin_execvp): Renames retval to res.
	(darwin_read_write_inferior): Update comment.
	(darwin_read_dyld_info): New function.
	(darwin_xfer_partial): Handle DYLD_INFO.
This commit is contained in:
Tristan Gingold
2011-09-27 15:30:18 +00:00
parent 6710bf39b7
commit f00c55f832
4 changed files with 109 additions and 39 deletions

View File

@ -1,3 +1,15 @@
2011-09-27 Tristan Gingold <gingold@adacore.com>
* target.h (enum target_object): Add TARGET_OBJECT_DARWIN_DYLD_INFO.
* solib-darwin.c (DYLD_VERSION_MAX): Update number.
(darwin_solib_get_all_image_info_addr_at_init): New function.
(darwin_solib_read_all_image_info_addr): Likewise.
(darwin_solib_create_inferior_hook): Use the above two functions.
* darwin-nat.c (darwin_execvp): Renames retval to res.
(darwin_read_write_inferior): Update comment.
(darwin_read_dyld_info): New function.
(darwin_xfer_partial): Handle DYLD_INFO.
2011-09-27 Stan Shebs <stan@codesourcery.com>
Add return address collection for tracepoints.

View File

@ -1512,10 +1512,10 @@ darwin_execvp (const char *file, char * const argv[], char * const env[])
{
posix_spawnattr_t attr;
short ps_flags = 0;
int retval;
int res;
retval = posix_spawnattr_init (&attr);
if (retval != 0)
res = posix_spawnattr_init (&attr);
if (res != 0)
{
fprintf_unfiltered
(gdb_stderr, "Cannot initialize attribute for posix_spawn\n");
@ -1531,11 +1531,10 @@ darwin_execvp (const char *file, char * const argv[], char * const env[])
#define _POSIX_SPAWN_DISABLE_ASLR 0x0100
#endif
ps_flags |= _POSIX_SPAWN_DISABLE_ASLR;
retval = posix_spawnattr_setflags (&attr, ps_flags);
if (retval != 0)
res = posix_spawnattr_setflags (&attr, ps_flags);
if (res != 0)
{
fprintf_unfiltered
(gdb_stderr, "Cannot set posix_spawn flags\n");
fprintf_unfiltered (gdb_stderr, "Cannot set posix_spawn flags\n");
return;
}
@ -1824,6 +1823,32 @@ out:
return length;
}
/* Read LENGTH bytes at offset ADDR of task_dyld_info for TASK, and copy them
to RDADDR.
Return 0 on failure; number of bytes read / writen otherwise. */
static int
darwin_read_dyld_info (task_t task, CORE_ADDR addr, char *rdaddr, int length)
{
struct task_dyld_info task_dyld_info;
mach_msg_type_number_t count = TASK_DYLD_INFO_COUNT;
int sz = TASK_DYLD_INFO_COUNT * sizeof (natural_t);
kern_return_t kret;
if (addr >= sz)
return 0;
kret = task_info (task, TASK_DYLD_INFO, (task_info_t) &task_dyld_info, &count);
MACH_CHECK_ERROR (kret);
if (kret != KERN_SUCCESS)
return -1;
/* Truncate. */
if (addr + length > sz)
length = sz - addr;
memcpy (rdaddr, (char *)&task_dyld_info + addr, length);
return length;
}
/* Return 0 on failure, number of bytes handled otherwise. TARGET
is ignored. */
@ -1860,11 +1885,22 @@ darwin_xfer_partial (struct target_ops *ops,
host_address_to_string (readbuf), host_address_to_string (writebuf),
inf->pid);
if (object != TARGET_OBJECT_MEMORY)
return -1;
switch (object)
{
case TARGET_OBJECT_MEMORY:
return darwin_read_write_inferior (inf->private->task, offset,
readbuf, writebuf, len);
case TARGET_OBJECT_DARWIN_DYLD_INFO:
if (writebuf != NULL || readbuf == NULL)
{
/* Support only read. */
return -1;
}
return darwin_read_dyld_info (inf->private->task, offset, readbuf, len);
default:
return -1;
}
}
static void

View File

@ -68,7 +68,7 @@ struct gdb_dyld_all_image_infos
/* Current all_image_infos version. */
#define DYLD_VERSION_MIN 1
#define DYLD_VERSION_MAX 7
#define DYLD_VERSION_MAX 12
/* Address of structure dyld_all_image_infos in inferior. */
static CORE_ADDR dyld_all_image_addr;
@ -293,22 +293,19 @@ darwin_special_symbol_handling (void)
{
}
/* Shared library startup support. See documentation in solib-svr4.c. */
/* Extract dyld_all_image_addr when the process was just created, assuming the
current PC is at the entry of the dynamic linker. */
static void
darwin_solib_create_inferior_hook (int from_tty)
darwin_solib_get_all_image_info_addr_at_init (void)
{
struct minimal_symbol *msymbol;
char **bkpt_namep;
asection *interp_sect;
gdb_byte *interp_name;
CORE_ADDR sym_addr;
CORE_ADDR load_addr = 0;
int load_addr_found = 0;
int loader_found_in_list = 0;
struct so_list *so;
bfd *dyld_bfd = NULL;
struct inferior *inf = current_inferior ();
/* This method doesn't work with an attached process. */
if (current_inferior ()->attach_flag)
return;
/* Find the program interpreter. */
interp_name = find_program_interpreter ();
@ -316,7 +313,6 @@ darwin_solib_create_inferior_hook (int from_tty)
return;
/* Create a bfd for the interpreter. */
sym_addr = 0;
dyld_bfd = bfd_openr (interp_name, gnutarget);
if (dyld_bfd)
{
@ -335,21 +331,11 @@ darwin_solib_create_inferior_hook (int from_tty)
if (!dyld_bfd)
return;
if (!inf->attach_flag)
{
/* We find the dynamic linker's base address by examining
the current pc (which should point at the entry point for the
dynamic linker) and subtracting the offset of the entry point. */
load_addr = (regcache_read_pc (get_current_regcache ())
- bfd_get_start_address (dyld_bfd));
}
else
{
/* FIXME: todo.
Get address of __DATA.__dyld in exec_bfd, read address at offset 0.
*/
return;
}
/* Now try to set a breakpoint in the dynamic linker. */
dyld_all_image_addr =
@ -361,6 +347,40 @@ darwin_solib_create_inferior_hook (int from_tty)
return;
dyld_all_image_addr += load_addr;
}
/* Extract dyld_all_image_addr reading it from
TARGET_OBJECT_DARWIN_DYLD_INFO. */
static void
darwin_solib_read_all_image_info_addr (void)
{
gdb_byte buf[8 + 8 + 4];
LONGEST len;
enum bfd_endian byte_order = gdbarch_byte_order (target_gdbarch);
len = target_read (&current_target, TARGET_OBJECT_DARWIN_DYLD_INFO, NULL,
buf, 0, sizeof (buf));
if (len != sizeof (buf))
return;
dyld_all_image_addr = extract_unsigned_integer (buf, 8, byte_order);
}
/* Shared library startup support. See documentation in solib-svr4.c. */
static void
darwin_solib_create_inferior_hook (int from_tty)
{
dyld_all_image_addr = 0;
darwin_solib_read_all_image_info_addr ();
if (dyld_all_image_addr == 0)
darwin_solib_get_all_image_info_addr_at_init ();
if (dyld_all_image_addr == 0)
return;
darwin_load_image_infos ();

View File

@ -276,6 +276,8 @@ enum target_object
TARGET_OBJECT_TRACEFRAME_INFO,
/* Load maps for FDPIC systems. */
TARGET_OBJECT_FDPIC,
/* Darwin dynamic linker info data. */
TARGET_OBJECT_DARWIN_DYLD_INFO
/* Possible future objects: TARGET_OBJECT_FILE, ... */
};