+2019-08-06 Tom Tromey <tom@tromey.com>
+
+ * utils.c (set_output_style): Sometimes pass stream to
+ emit_style_escape.
+ * ui-out.h (class ui_out) <can_emit_style_escape>: Declare.
+ * record-btrace.c (btrace_insn_history): Update.
+ * mi/mi-out.h (class mi_ui_out) <can_emit_style_escape>: New
+ method.
+ * disasm.h (gdb_pretty_print_disassembler): Add uiout parameter.
+ Update initializers.
+ <m_uiout>: New field.
+ <m_di>: Move lower.
+ * disasm.c (gdb_pretty_print_disassembler::pretty_print_insn):
+ Remove "uiout" parameter.
+ (dump_insns): Update.
+ * cli-out.h (class cli_ui_out) <can_emit_style_escape>: Declare.
+ * cli-out.c (cli_ui_out::can_emit_style_escape): New method.
+
2019-08-06 Christian Biesinger <cbiesinger@google.com>
* symtab.c (symbol_cache_lookup): Change int to enum block_enum.
return old;
}
+bool
+cli_ui_out::can_emit_style_escape () const
+{
+ return m_streams.back ()->can_emit_style_escape ();
+}
+
/* CLI interface to display tab-completion matches. */
/* CLI version of displayer.crlf. */
ui_file *set_stream (ui_file *stream);
+ bool can_emit_style_escape () const override;
+
protected:
virtual void do_table_begin (int nbrofcols, int nr_rows,
/* See disasm.h. */
int
-gdb_pretty_print_disassembler::pretty_print_insn (struct ui_out *uiout,
- const struct disasm_insn *insn,
+gdb_pretty_print_disassembler::pretty_print_insn (const struct disasm_insn *insn,
gdb_disassembly_flags flags)
{
/* parts of the symbolic representation of the address */
struct gdbarch *gdbarch = arch ();
{
- ui_out_emit_tuple tuple_emitter (uiout, NULL);
+ ui_out_emit_tuple tuple_emitter (m_uiout, NULL);
pc = insn->addr;
if (insn->number != 0)
{
- uiout->field_unsigned ("insn-number", insn->number);
- uiout->text ("\t");
+ m_uiout->field_unsigned ("insn-number", insn->number);
+ m_uiout->text ("\t");
}
if ((flags & DISASSEMBLY_SPECULATIVE) != 0)
{
if (insn->is_speculative)
{
- uiout->field_string ("is-speculative", "?");
+ m_uiout->field_string ("is-speculative", "?");
/* The speculative execution indication overwrites the first
character of the PC prefix.
We assume a PC prefix length of 3 characters. */
if ((flags & DISASSEMBLY_OMIT_PC) == 0)
- uiout->text (pc_prefix (pc) + 1);
+ m_uiout->text (pc_prefix (pc) + 1);
else
- uiout->text (" ");
+ m_uiout->text (" ");
}
else if ((flags & DISASSEMBLY_OMIT_PC) == 0)
- uiout->text (pc_prefix (pc));
+ m_uiout->text (pc_prefix (pc));
else
- uiout->text (" ");
+ m_uiout->text (" ");
}
else if ((flags & DISASSEMBLY_OMIT_PC) == 0)
- uiout->text (pc_prefix (pc));
- uiout->field_core_addr ("address", gdbarch, pc);
+ m_uiout->text (pc_prefix (pc));
+ m_uiout->field_core_addr ("address", gdbarch, pc);
std::string name, filename;
bool omit_fname = ((flags & DISASSEMBLY_OMIT_FNAME) != 0);
{
/* We don't care now about line, filename and unmapped. But we might in
the future. */
- uiout->text (" <");
+ m_uiout->text (" <");
if (!omit_fname)
- uiout->field_string ("func-name", name.c_str (),
- ui_out_style_kind::FUNCTION);
+ m_uiout->field_string ("func-name", name.c_str (),
+ ui_out_style_kind::FUNCTION);
/* For negative offsets, avoid displaying them as +-N; the sign of
the offset takes the place of the "+" here. */
if (offset >= 0)
- uiout->text ("+");
- uiout->field_signed ("offset", offset);
- uiout->text (">:\t");
+ m_uiout->text ("+");
+ m_uiout->field_signed ("offset", offset);
+ m_uiout->text (">:\t");
}
else
- uiout->text (":\t");
+ m_uiout->text (":\t");
m_insn_stb.clear ();
spacer = " ";
}
- uiout->field_stream ("opcodes", m_opcode_stb);
- uiout->text ("\t");
+ m_uiout->field_stream ("opcodes", m_opcode_stb);
+ m_uiout->text ("\t");
}
else
size = m_di.print_insn (pc);
- uiout->field_stream ("inst", m_insn_stb);
+ m_uiout->field_stream ("inst", m_insn_stb);
}
- uiout->text ("\n");
+ m_uiout->text ("\n");
return size;
}
memset (&insn, 0, sizeof (insn));
insn.addr = low;
- gdb_pretty_print_disassembler disasm (gdbarch);
+ gdb_pretty_print_disassembler disasm (gdbarch, uiout);
while (insn.addr < high && (how_many < 0 || num_displayed < how_many))
{
int size;
- size = disasm.pretty_print_insn (uiout, &insn, flags);
+ size = disasm.pretty_print_insn (&insn, flags);
if (size <= 0)
break;
class gdb_pretty_print_disassembler
{
public:
- explicit gdb_pretty_print_disassembler (struct gdbarch *gdbarch)
- : m_di (gdbarch, &m_insn_stb)
+ explicit gdb_pretty_print_disassembler (struct gdbarch *gdbarch,
+ struct ui_out *uiout)
+ : m_uiout (uiout),
+ m_insn_stb (uiout->can_emit_style_escape ()),
+ m_di (gdbarch, &m_insn_stb)
{}
- /* Prints the instruction INSN into UIOUT and returns the length of
- the printed instruction in bytes. */
- int pretty_print_insn (struct ui_out *uiout, const struct disasm_insn *insn,
+ /* Prints the instruction INSN into the saved ui_out and returns the
+ length of the printed instruction in bytes. */
+ int pretty_print_insn (const struct disasm_insn *insn,
gdb_disassembly_flags flags);
private:
/* Returns the architecture used for disassembling. */
struct gdbarch *arch () { return m_di.arch (); }
- /* The disassembler used for instruction printing. */
- gdb_disassembler m_di;
+ /* The ui_out that is used by pretty_print_insn. */
+ struct ui_out *m_uiout;
/* The buffer used to build the instruction string. The
disassembler is initialized with this stream. */
string_file m_insn_stb;
+ /* The disassembler used for instruction printing. */
+ gdb_disassembler m_di;
+
/* The buffer used to build the raw opcodes string. */
string_file m_opcode_stb;
};
/* Return the version number of the current MI. */
int version ();
+ bool can_emit_style_escape () const override
+ {
+ return false;
+ }
+
protected:
virtual void do_table_begin (int nbrofcols, int nr_rows, const char *tblid)
gdb::optional<ui_out_emit_tuple> src_and_asm_tuple;
gdb::optional<ui_out_emit_list> asm_list;
- gdb_pretty_print_disassembler disasm (gdbarch);
+ gdb_pretty_print_disassembler disasm (gdbarch, uiout);
for (btrace_insn_iterator it = *begin; btrace_insn_cmp (&it, end) != 0;
btrace_insn_next (&it, 1))
if ((insn->flags & BTRACE_INSN_FLAG_SPECULATIVE) != 0)
dinsn.is_speculative = 1;
- disasm.pretty_print_insn (uiout, &dinsn, flags);
+ disasm.pretty_print_insn (&dinsn, flags);
}
}
}
+2019-08-06 Tom Tromey <tom@tromey.com>
+
+ * gdb.base/style.exp: Add disassemble test.
+ * gdb.base/style.c (some_called_function): New function.
+ (main): Use it.
+
2019-08-05 Christian Biesinger <cbiesinger@google.com>
* gdb.python/py-block.exp: Test dictionary access on blocks.
#define SOME_MACRO 23
+int some_called_function (void)
+{
+ return 0;
+}
+
int
main (int argc, char **argv)
{
- return 0; /* break here */
+ return some_called_function (); /* break here */
}
"Defined at $base_file_expr:16\r\n#define SOME_MACRO 23"
}
+ set func [style some_called_function function]
+ # Somewhere should see the call to the function.
+ gdb_test "disassemble main" "[style $hex address].*$func.*"
+
gdb_exit
gdb_spawn
bool query_table_field (int colno, int *width, int *alignment,
const char **col_name);
+ /* Return true if this stream is prepared to handle style
+ escapes. */
+ virtual bool can_emit_style_escape () const = 0;
+
protected:
virtual void do_table_begin (int nbrofcols, int nr_rows, const char *tblid)
if (!stream->can_emit_style_escape ())
return;
- /* Note that we don't pass STREAM here, because we want to emit to
+ /* Note that we may not pass STREAM here, when we want to emit to
the wrap buffer, not directly to STREAM. */
- emit_style_escape (style);
+ if (stream == gdb_stdout)
+ stream = nullptr;
+ emit_style_escape (style, stream);
}
/* See utils.h. */