along with this program. If not, see <http://www.gnu.org/licenses/>. */
#include "defs.h"
-#include "gdb_string.h"
+#include <string.h>
#include "frame.h"
#include "symtab.h"
#include "gdbtypes.h"
past the specification and past all whitespace following it. */
static struct format_data
-decode_format (char **string_ptr, int oformat, int osize)
+decode_format (const char **string_ptr, int oformat, int osize)
{
struct format_data val;
- char *p = *string_ptr;
+ const char *p = *string_ptr;
val.format = '?';
val.size = '?';
}
break;
+ case 'z':
+ print_hex_chars (stream, valaddr, len, byte_order);
+ break;
+
default:
error (_("Undefined output format \"%c\"."), options->format);
}
save some memory, but for many debug format--ELF/DWARF or
anything/stabs--it would be inconvenient to eliminate those minimal
symbols anyway). */
- msymbol = lookup_minimal_symbol_by_pc_section (addr, section);
+ msymbol = lookup_minimal_symbol_by_pc_section (addr, section).minsym;
symbol = find_pc_sect_function (addr, section);
if (symbol)
{
if (SYMBOL_VALUE_ADDRESS (msymbol) > name_location || symbol == NULL)
{
+ /* 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. */
+ if (MSYMBOL_TYPE (msymbol) == mst_text
+ || MSYMBOL_TYPE (msymbol) == mst_text_gnu_ifunc
+ || MSYMBOL_TYPE (msymbol) == mst_file_text
+ || MSYMBOL_TYPE (msymbol) == mst_solib_trampoline)
+ addr = gdbarch_addr_bits_remove (gdbarch, addr);
+
/* The msymbol is closer to the address than the symbol;
use the msymbol instead. */
symbol = 0;
first argument ("/x myvar" for example, to print myvar in hex). */
static void
-print_command_1 (char *exp, int voidprint)
+print_command_1 (const char *exp, int voidprint)
{
struct expression *expr;
- struct cleanup *old_chain = 0;
+ struct cleanup *old_chain = make_cleanup (null_cleanup, NULL);
char format = 0;
struct value *val;
struct format_data fmt;
- int cleanup = 0;
if (exp && *exp == '/')
{
if (exp && *exp)
{
expr = parse_expression (exp);
- old_chain = make_cleanup (free_current_contents, &expr);
- cleanup = 1;
+ make_cleanup (free_current_contents, &expr);
val = evaluate_expression (expr);
}
else
annotate_value_end ();
}
- if (cleanup)
- do_cleanups (old_chain);
+ do_cleanups (old_chain);
}
static void
print_command_1 (exp, 0);
}
-void
+/* Implementation of the "output" command. */
+
+static void
output_command (char *exp, int from_tty)
+{
+ output_command_const (exp, from_tty);
+}
+
+/* Like output_command, but takes a const string as argument. */
+
+void
+output_command_const (const char *exp, int from_tty)
{
struct expression *expr;
struct cleanup *old_chain;
if (obj_section_addr (osect) <= sect_addr
&& sect_addr < obj_section_endaddr (osect)
- && (msymbol = lookup_minimal_symbol_by_pc_section (sect_addr, osect)))
+ && (msymbol
+ = lookup_minimal_symbol_by_pc_section (sect_addr, osect).minsym))
{
const char *obj_name, *mapped, *sec_name, *msym_name;
char *loc_string;
a pagination request inside printf_filtered. */
old_chain = make_cleanup (xfree, loc_string);
- gdb_assert (osect->objfile && osect->objfile->name);
- obj_name = osect->objfile->name;
+ gdb_assert (osect->objfile && objfile_name (osect->objfile));
+ obj_name = objfile_name (osect->objfile);
if (MULTI_OBJFILE_P ())
if (pc_in_unmapped_range (addr, osect))
struct gdbarch *gdbarch;
int regno;
struct symbol *sym;
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
long val;
struct obj_section *section;
CORE_ADDR load_addr, context_pc = 0;
return;
}
- msymbol = lookup_minimal_symbol (exp, NULL, NULL);
+ msymbol = lookup_bound_minimal_symbol (exp);
- if (msymbol != NULL)
+ if (msymbol.minsym != NULL)
{
- gdbarch = get_objfile_arch (msymbol_objfile (msymbol));
- load_addr = SYMBOL_VALUE_ADDRESS (msymbol);
+ struct objfile *objfile = msymbol.objfile;
+
+ gdbarch = get_objfile_arch (objfile);
+ load_addr = SYMBOL_VALUE_ADDRESS (msymbol.minsym);
printf_filtered ("Symbol \"");
fprintf_symbol_filtered (gdb_stdout, exp,
printf_filtered ("\" is at ");
fputs_filtered (paddress (gdbarch, load_addr), gdb_stdout);
printf_filtered (" in a file compiled without debugging");
- section = SYMBOL_OBJ_SECTION (msymbol);
+ section = SYMBOL_OBJ_SECTION (objfile, msymbol.minsym);
if (section_is_overlay (section))
{
load_addr = overlay_unmapped_address (load_addr, section);
current_language->la_language, DMGL_ANSI);
printf_filtered ("\" is ");
val = SYMBOL_VALUE (sym);
- section = SYMBOL_OBJ_SECTION (sym);
+ section = SYMBOL_OBJ_SECTION (SYMBOL_OBJFILE (sym), sym);
gdbarch = get_objfile_arch (SYMBOL_SYMTAB (sym)->objfile);
+ if (SYMBOL_COMPUTED_OPS (sym) != NULL)
+ {
+ SYMBOL_COMPUTED_OPS (sym)->describe_location (sym, context_pc,
+ gdb_stdout);
+ printf_filtered (".\n");
+ return;
+ }
+
switch (SYMBOL_CLASS (sym))
{
case LOC_CONST:
break;
case LOC_COMPUTED:
- /* FIXME: cagney/2004-01-26: It should be possible to
- unconditionally call the SYMBOL_COMPUTED_OPS method when available.
- Unfortunately DWARF 2 stores the frame-base (instead of the
- function) location in a function's symbol. Oops! For the
- moment enable this when/where applicable. */
- SYMBOL_COMPUTED_OPS (sym)->describe_location (sym, context_pc,
- gdb_stdout);
- break;
+ gdb_assert_not_reached (_("LOC_COMPUTED variable missing a method"));
case LOC_REGISTER:
/* GDBARCH is the architecture associated with the objfile the symbol
case LOC_UNRESOLVED:
{
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
- msym = lookup_minimal_symbol (SYMBOL_LINKAGE_NAME (sym), NULL, NULL);
- if (msym == NULL)
+ msym = lookup_minimal_symbol_and_objfile (SYMBOL_LINKAGE_NAME (sym));
+ if (msym.minsym == NULL)
printf_filtered ("unresolved");
else
{
- section = SYMBOL_OBJ_SECTION (msym);
- load_addr = SYMBOL_VALUE_ADDRESS (msym);
+ section = SYMBOL_OBJ_SECTION (msym.objfile, msym.minsym);
+ load_addr = SYMBOL_VALUE_ADDRESS (msym.minsym);
if (section
&& (section->the_bfd_section->flags & SEC_THREAD_LOCAL) != 0)
printf_filtered (_("a thread-local variable at offset %s "
"in the thread-local storage for `%s'"),
paddress (gdbarch, load_addr),
- section->objfile->name);
+ objfile_name (section->objfile));
else
{
printf_filtered (_("static storage at address "));
if (exp && *exp == '/')
{
- exp++;
- fmt = decode_format (&exp, last_format, last_size);
+ const char *tmp = exp + 1;
+
+ fmt = decode_format (&tmp, last_format, last_size);
+ exp = (char *) tmp;
}
/* If we have an expression, evaluate it and use it as the address. */
Specify the expression. */
static void
-display_command (char *exp, int from_tty)
+display_command (char *arg, int from_tty)
{
struct format_data fmt;
struct expression *expr;
struct display *new;
int display_it = 1;
+ const char *exp = arg;
#if defined(TUI)
/* NOTE: cagney/2003-02-13 The `tui_active' was previously
an item by re-parsing .exp_string field in the new execution context. */
static void
-clear_dangling_display_expressions (struct so_list *solib)
+clear_dangling_display_expressions (struct objfile *objfile)
{
- struct objfile *objfile = solib->objfile;
struct display *d;
+ struct program_space *pspace;
/* With no symbol file we cannot have a block or expression from it. */
if (objfile == NULL)
return;
+ pspace = objfile->pspace;
if (objfile->separate_debug_objfile_backlink)
- objfile = objfile->separate_debug_objfile_backlink;
- gdb_assert (objfile->pspace == solib->pspace);
+ {
+ objfile = objfile->separate_debug_objfile_backlink;
+ gdb_assert (objfile->pspace == pspace);
+ }
for (d = display_chain; d != NULL; d = d->next)
{
- if (d->pspace != solib->pspace)
+ if (d->pspace != pspace)
continue;
if (lookup_objfile_from_block (d->block) == objfile
printf_command (char *arg, int from_tty)
{
ui_printf (arg, gdb_stdout);
+ gdb_flush (gdb_stdout);
}
/* Implement the "eval" command. */
current_display_number = -1;
- observer_attach_solib_unloaded (clear_dangling_display_expressions);
+ observer_attach_free_objfile (clear_dangling_display_expressions);
add_info ("address", address_info,
_("Describe where symbol SYM is stored."));
ADDRESS is an expression for the memory address to examine.\n\
FMT is a repeat count followed by a format letter and a size letter.\n\
Format letters are o(octal), x(hex), d(decimal), u(unsigned decimal),\n\
- t(binary), f(float), a(address), i(instruction), c(char) and s(string).\n\
+ t(binary), f(float), a(address), i(instruction), c(char), s(string)\n\
+ and z(hex, zero padded on the left).\n\
Size letters are b(byte), h(halfword), w(word), g(giant, 8 bytes).\n\
The specified number of objects of the specified size are printed\n\
according to the format.\n\n\
add_setshow_uinteger_cmd ("max-symbolic-offset", no_class,
&max_symbolic_offset, _("\
Set the largest offset that will be printed in <symbol+1234> form."), _("\
-Show the largest offset that will be printed in <symbol+1234> form."), NULL,
+Show the largest offset that will be printed in <symbol+1234> form."), _("\
+Tell GDB to only display the symbolic form of an address if the\n\
+offset between the closest earlier symbol and the address is less than\n\
+the specified maximum offset. The default is \"unlimited\", which tells GDB\n\
+to always print the symbolic form of an address if any symbol precedes\n\
+it. Zero is equivalent to \"unlimited\"."),
NULL,
show_max_symbolic_offset,
&setprintlist, &showprintlist);