Copyright (C) 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995,
1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
- 2008, 2009 Free Software Foundation, Inc.
+ 2008, 2009, 2010 Free Software Foundation, Inc.
This file is part of GDB.
#include "solib.h"
#include "parser-defs.h"
#include "charset.h"
+#include "arch-utils.h"
#ifdef TUI
#include "tui/tui.h" /* For tui_active et.al. */
{
/* Chain link to next auto-display item. */
struct display *next;
+
/* The expression as the user typed it. */
char *exp_string;
+
/* Expression to be evaluated and displayed. */
struct expression *exp;
+
/* Item number of this auto-display item. */
int number;
+
/* Display format specified. */
struct format_data format;
+
+ /* Program space associated with `block'. */
+ struct program_space *pspace;
+
/* Innermost block required by this expression when evaluated */
struct block *block;
+
/* Status of this display (enabled or disabled) */
int enabled_p;
};
settings of the demangle and asm_demangle variables. */
void
-print_address_symbolic (CORE_ADDR addr, struct ui_file *stream,
+print_address_symbolic (struct gdbarch *gdbarch, CORE_ADDR addr,
+ struct ui_file *stream,
int do_demangle, char *leadin)
{
char *name = NULL;
struct cleanup *cleanup_chain = make_cleanup (free_current_contents, &name);
make_cleanup (free_current_contents, &filename);
- if (build_address_symbolic (addr, do_demangle, &name, &offset,
+ if (build_address_symbolic (gdbarch, addr, do_demangle, &name, &offset,
&filename, &line, &unmapped))
{
do_cleanups (cleanup_chain);
success, when all the info in the OUT paramters is valid. Return 1
otherwise. */
int
-build_address_symbolic (CORE_ADDR addr, /* IN */
+build_address_symbolic (struct gdbarch *gdbarch,
+ CORE_ADDR addr, /* IN */
int do_demangle, /* IN */
char **name, /* OUT */
int *offset, /* OUT */
if (symbol)
{
+ /* If this is a function (i.e. a code address), strip out any
+ non-address bits. For instance, display a pointer to the
+ first instruction of a Thumb function as <function>; the
+ second instruction will be <function+2>, even though the
+ pointer is <function+3>. This matches the ISA behavior. */
+ addr = gdbarch_addr_bits_remove (gdbarch, addr);
+
name_location = BLOCK_START (SYMBOL_BLOCK_VALUE (symbol));
if (do_demangle || asm_demangle)
name_temp = SYMBOL_PRINT_NAME (symbol);
CORE_ADDR addr, struct ui_file *stream)
{
fputs_filtered (paddress (gdbarch, addr), stream);
- print_address_symbolic (addr, stream, asm_demangle, " ");
+ print_address_symbolic (gdbarch, addr, stream, asm_demangle, " ");
+}
+
+/* Return a prefix for instruction address:
+ "=> " for current instruction, else " ". */
+
+const char *
+pc_prefix (CORE_ADDR addr)
+{
+ if (has_stack_frames ())
+ {
+ struct frame_info *frame;
+ CORE_ADDR pc;
+
+ frame = get_selected_frame (NULL);
+ pc = get_frame_pc (frame);
+
+ if (pc == addr)
+ return "=> ";
+ }
+ return " ";
}
/* Print address ADDR symbolically on STREAM. Parameter DEMANGLE
else if (opts.addressprint)
{
fputs_filtered (paddress (gdbarch, addr), stream);
- print_address_symbolic (addr, stream, do_demangle, " ");
+ print_address_symbolic (gdbarch, addr, stream, do_demangle, " ");
}
else
{
- print_address_symbolic (addr, stream, do_demangle, "");
+ print_address_symbolic (gdbarch, addr, stream, do_demangle, "");
}
}
\f
while (count > 0)
{
QUIT;
+ if (format == 'i')
+ fputs_filtered (pc_prefix (next_address), gdb_stdout);
print_address (next_gdbarch, next_address, gdb_stdout);
printf_filtered (":");
for (i = maxelts;
new->exp_string = xstrdup (exp);
new->exp = expr;
new->block = innermost_block;
+ new->pspace = current_program_space;
new->next = display_chain;
new->number = ++display_number;
new->format = fmt;
if (d->enabled_p == 0)
return;
+ /* The expression carries the architecture that was used at parse time.
+ This is a problem if the expression depends on architecture features
+ (e.g. register numbers), and the current architecture is now different.
+ For example, a display statement like "display/i $pc" is expected to
+ display the PC register of the current architecture, not the arch at
+ the time the display command was given. Therefore, we re-parse the
+ expression if the current architecture has changed. */
+ if (d->exp != NULL && d->exp->gdbarch != get_current_arch ())
+ {
+ xfree (d->exp);
+ d->exp = NULL;
+ d->block = NULL;
+ }
+
if (d->exp == NULL)
{
volatile struct gdb_exception ex;
}
if (d->block)
- within_current_scope = contained_in (get_selected_block (0), d->block);
+ {
+ if (d->pspace == current_program_space)
+ within_current_scope = contained_in (get_selected_block (0), d->block);
+ else
+ within_current_scope = 0;
+ }
else
within_current_scope = 1;
if (!within_current_scope)
const union exp_element *const elts = exp->elts;
if (d->block != NULL
+ && d->pspace == solib->pspace
&& solib_contains_address_p (solib, d->block->startaddr))
return 1;
SYMBOL_OBJ_SECTION (symbol);
if (block != NULL
- && solib_contains_address_p (solib, block->startaddr))
+ && solib_contains_address_p (solib,
+ block->startaddr))
return 1;
if (section && section->objfile == solib->objfile)