[Lldb-commits] [lldb] 35e60f5 - [NFC][trace] simplify the instruction dumper
Walter Erquinigo via lldb-commits
lldb-commits at lists.llvm.org
Mon Apr 25 20:02:55 PDT 2022
Author: Walter Erquinigo
Date: 2022-04-25T20:02:48-07:00
New Revision: 35e60f5de180aea55ed478298f4b40f04dcc57d1
URL: https://github.com/llvm/llvm-project/commit/35e60f5de180aea55ed478298f4b40f04dcc57d1
DIFF: https://github.com/llvm/llvm-project/commit/35e60f5de180aea55ed478298f4b40f04dcc57d1.diff
LOG: [NFC][trace] simplify the instruction dumper
TraceInstructionDumper::DumpInstructions was becoming too big, so I'm
refactoring it into smaller functions. I also made some static methods proper
instance methods to simplify calls. Other minor improvements are also done.
Differential Revision: https://reviews.llvm.org/D124064
Added:
Modified:
lldb/include/lldb/Target/TraceInstructionDumper.h
lldb/source/Target/TraceInstructionDumper.cpp
Removed:
################################################################################
diff --git a/lldb/include/lldb/Target/TraceInstructionDumper.h b/lldb/include/lldb/Target/TraceInstructionDumper.h
index 9dc8e4c50f428..53a1a03ee1ce2 100644
--- a/lldb/include/lldb/Target/TraceInstructionDumper.h
+++ b/lldb/include/lldb/Target/TraceInstructionDumper.h
@@ -8,11 +8,24 @@
#include "lldb/Target/TraceCursor.h"
+#include "lldb/Symbol/SymbolContext.h"
+
#ifndef LLDB_TARGET_TRACE_INSTRUCTION_DUMPER_H
#define LLDB_TARGET_TRACE_INSTRUCTION_DUMPER_H
namespace lldb_private {
+/// Helper struct that holds symbol, disassembly and address information of an
+/// instruction.
+struct InstructionSymbolInfo {
+ SymbolContext sc;
+ Address address;
+ lldb::addr_t load_address;
+ lldb::DisassemblerSP disassembler;
+ lldb::InstructionSP instruction;
+ lldb_private::ExecutionContext exe_ctx;
+};
+
/// Class that holds the configuration used by \a TraceInstructionDumper for
/// traversing and dumping instructions.
struct TraceInstructionDumperOptions {
@@ -83,6 +96,28 @@ class TraceInstructionDumper {
void PrintEvents();
+ void PrintMissingInstructionsMessage();
+
+ void PrintInstructionHeader();
+
+ void DumpInstructionDisassembly(const InstructionSymbolInfo &insn);
+
+ /// Dump the symbol context of the given instruction address if it's
diff erent
+ /// from the symbol context of the previous instruction in the trace.
+ ///
+ /// \param[in] prev_sc
+ /// The symbol context of the previous instruction in the trace.
+ ///
+ /// \param[in] address
+ /// The address whose symbol information will be dumped.
+ ///
+ /// \return
+ /// The symbol context of the current address, which might
diff er from the
+ /// previous one.
+ void DumpInstructionSymbolContext(
+ const llvm::Optional<InstructionSymbolInfo> &prev_insn,
+ const InstructionSymbolInfo &insn);
+
lldb::TraceCursorUP m_cursor_up;
TraceInstructionDumperOptions m_options;
Stream &m_s;
diff --git a/lldb/source/Target/TraceInstructionDumper.cpp b/lldb/source/Target/TraceInstructionDumper.cpp
index 7473e84e356f1..fd809f263ea25 100644
--- a/lldb/source/Target/TraceInstructionDumper.cpp
+++ b/lldb/source/Target/TraceInstructionDumper.cpp
@@ -47,8 +47,6 @@ TraceInstructionDumper::TraceInstructionDumper(
}
}
-/// \return
-/// Return \b true if the cursor could move one step.
bool TraceInstructionDumper::TryMoveOneStep() {
if (!m_cursor_up->Next()) {
SetNoMoreData();
@@ -57,17 +55,6 @@ bool TraceInstructionDumper::TryMoveOneStep() {
return true;
}
-/// Helper struct that holds symbol, disassembly and address information of an
-/// instruction.
-struct InstructionSymbolInfo {
- SymbolContext sc;
- Address address;
- lldb::addr_t load_address;
- lldb::DisassemblerSP disassembler;
- lldb::InstructionSP instruction;
- lldb_private::ExecutionContext exe_ctx;
-};
-
// This custom LineEntry validator is neded because some line_entries have
// 0 as line, which is meaningless. Notice that LineEntry::IsValid only
// checks that line is not LLDB_INVALID_LINE_NUMBER, i.e. UINT32_MAX.
@@ -122,46 +109,35 @@ IsSameInstructionSymbolContext(const InstructionSymbolInfo &prev_insn,
return curr_line_valid == prev_line_valid;
}
-/// Dump the symbol context of the given instruction address if it's
diff erent
-/// from the symbol context of the previous instruction in the trace.
-///
-/// \param[in] prev_sc
-/// The symbol context of the previous instruction in the trace.
-///
-/// \param[in] address
-/// The address whose symbol information will be dumped.
-///
-/// \return
-/// The symbol context of the current address, which might
diff er from the
-/// previous one.
-static void
-DumpInstructionSymbolContext(Stream &s,
- Optional<InstructionSymbolInfo> prev_insn,
- InstructionSymbolInfo &insn) {
+void TraceInstructionDumper::DumpInstructionSymbolContext(
+ const Optional<InstructionSymbolInfo> &prev_insn,
+ const InstructionSymbolInfo &insn) {
if (prev_insn && IsSameInstructionSymbolContext(*prev_insn, insn))
return;
- s.Printf(" ");
+ m_s << " ";
if (!insn.sc.module_sp)
- s.Printf("(none)");
+ m_s << "(none)";
else if (!insn.sc.function && !insn.sc.symbol)
- s.Printf("%s`(none)",
- insn.sc.module_sp->GetFileSpec().GetFilename().AsCString());
+ m_s.Format("{0}`(none)",
+ insn.sc.module_sp->GetFileSpec().GetFilename().AsCString());
else
- insn.sc.DumpStopContext(&s, insn.exe_ctx.GetTargetPtr(), insn.address,
+ insn.sc.DumpStopContext(&m_s, insn.exe_ctx.GetTargetPtr(), insn.address,
/*show_fullpaths=*/false,
/*show_module=*/true, /*show_inlined_frames=*/false,
/*show_function_arguments=*/true,
/*show_function_name=*/true);
- s.Printf("\n");
+ m_s << "\n";
}
-static void DumpInstructionDisassembly(Stream &s, InstructionSymbolInfo &insn) {
+void TraceInstructionDumper::DumpInstructionDisassembly(
+ const InstructionSymbolInfo &insn) {
if (!insn.instruction)
return;
- s.Printf(" ");
- insn.instruction->Dump(&s, /*max_opcode_byte_size=*/0, /*show_address=*/false,
+ m_s << " ";
+ insn.instruction->Dump(&m_s, /*max_opcode_byte_size=*/0,
+ /*show_address=*/false,
/*show_bytes=*/false, &insn.exe_ctx, &insn.sc,
/*prev_sym_ctx=*/nullptr,
/*disassembly_addr_format=*/nullptr,
@@ -172,6 +148,26 @@ void TraceInstructionDumper::SetNoMoreData() { m_no_more_data = true; }
bool TraceInstructionDumper::HasMoreData() { return !m_no_more_data; }
+void TraceInstructionDumper::PrintMissingInstructionsMessage() {
+ m_s << " ...missing instructions\n";
+}
+
+void TraceInstructionDumper::PrintInstructionHeader() {
+ m_s.Format(" {0}: ", m_cursor_up->GetId());
+
+ if (m_options.show_tsc) {
+ m_s << "[tsc=";
+
+ if (Optional<uint64_t> timestamp =
+ m_cursor_up->GetCounter(lldb::eTraceCounterTSC))
+ m_s.Format("{0:x+16}", *timestamp);
+ else
+ m_s << "unavailable";
+
+ m_s << "] ";
+ }
+}
+
void TraceInstructionDumper::PrintEvents() {
if (!m_options.show_events)
return;
@@ -182,90 +178,76 @@ void TraceInstructionDumper::PrintEvents() {
});
}
-Optional<lldb::tid_t> TraceInstructionDumper::DumpInstructions(size_t count) {
+/// Find the symbol context for the given address reusing the previous
+/// instruction's symbol context when possible.
+static SymbolContext
+CalculateSymbolContext(const Address &address,
+ const InstructionSymbolInfo &prev_insn_info) {
+ AddressRange range;
+ if (prev_insn_info.sc.GetAddressRange(eSymbolContextEverything, 0,
+ /*inline_block_range*/ false, range) &&
+ range.Contains(address))
+ return prev_insn_info.sc;
+
+ SymbolContext sc;
+ address.CalculateSymbolContext(&sc, eSymbolContextEverything);
+ return sc;
+}
+
+/// Find the disassembler for the given address reusing the previous
+/// instruction's disassembler when possible.
+static std::tuple<DisassemblerSP, InstructionSP>
+CalculateDisass(const InstructionSymbolInfo &insn_info,
+ const InstructionSymbolInfo &prev_insn_info,
+ const ExecutionContext &exe_ctx) {
+ if (prev_insn_info.disassembler) {
+ if (InstructionSP instruction =
+ prev_insn_info.disassembler->GetInstructionList()
+ .GetInstructionAtAddress(insn_info.address))
+ return std::make_tuple(prev_insn_info.disassembler, instruction);
+ }
+
+ if (insn_info.sc.function) {
+ if (DisassemblerSP disassembler =
+ insn_info.sc.function->GetInstructions(exe_ctx, nullptr)) {
+ if (InstructionSP instruction =
+ disassembler->GetInstructionList().GetInstructionAtAddress(
+ insn_info.address))
+ return std::make_tuple(disassembler, instruction);
+ }
+ }
+ // We fallback to a single instruction disassembler
+ Target &target = exe_ctx.GetTargetRef();
+ const ArchSpec arch = target.GetArchitecture();
+ AddressRange range(insn_info.address, arch.GetMaximumOpcodeByteSize());
+ DisassemblerSP disassembler =
+ Disassembler::DisassembleRange(arch, /*plugin_name*/ nullptr,
+ /*flavor*/ nullptr, target, range);
+ return std::make_tuple(
+ disassembler,
+ disassembler ? disassembler->GetInstructionList().GetInstructionAtAddress(
+ insn_info.address)
+ : InstructionSP());
+}
+
+Optional<lldb::user_id_t>
+TraceInstructionDumper::DumpInstructions(size_t count) {
ThreadSP thread_sp = m_cursor_up->GetExecutionContextRef().GetThreadSP();
if (!thread_sp) {
- m_s.Printf("invalid thread");
+ m_s << "invalid thread";
return None;
}
bool was_prev_instruction_an_error = false;
-
- auto printMissingInstructionsMessage = [&]() {
- m_s.Printf(" ...missing instructions\n");
- };
-
- auto printInstructionHeader = [&](uint64_t id) {
- m_s.Printf(" %" PRIu64 ": ", id);
-
- if (m_options.show_tsc) {
- m_s.Printf("[tsc=");
-
- if (Optional<uint64_t> timestamp = m_cursor_up->GetCounter(lldb::eTraceCounterTSC))
- m_s.Printf("0x%016" PRIx64, *timestamp);
- else
- m_s.Printf("unavailable");
-
- m_s.Printf("] ");
- }
- };
-
InstructionSymbolInfo prev_insn_info;
+ Optional<lldb::user_id_t> last_id;
- Target &target = thread_sp->GetProcess()->GetTarget();
ExecutionContext exe_ctx;
- target.CalculateExecutionContext(exe_ctx);
- const ArchSpec &arch = target.GetArchitecture();
-
- // Find the symbol context for the given address reusing the previous
- // instruction's symbol context when possible.
- auto calculateSymbolContext = [&](const Address &address) {
- AddressRange range;
- if (prev_insn_info.sc.GetAddressRange(eSymbolContextEverything, 0,
- /*inline_block_range*/ false,
- range) &&
- range.Contains(address))
- return prev_insn_info.sc;
-
- SymbolContext sc;
- address.CalculateSymbolContext(&sc, eSymbolContextEverything);
- return sc;
- };
-
- // Find the disassembler for the given address reusing the previous
- // instruction's disassembler when possible.
- auto calculateDisass = [&](const Address &address, const SymbolContext &sc) {
- if (prev_insn_info.disassembler) {
- if (InstructionSP instruction =
- prev_insn_info.disassembler->GetInstructionList()
- .GetInstructionAtAddress(address))
- return std::make_tuple(prev_insn_info.disassembler, instruction);
- }
+ thread_sp->GetProcess()->GetTarget().CalculateExecutionContext(exe_ctx);
- if (sc.function) {
- if (DisassemblerSP disassembler =
- sc.function->GetInstructions(exe_ctx, nullptr)) {
- if (InstructionSP instruction =
- disassembler->GetInstructionList().GetInstructionAtAddress(
- address))
- return std::make_tuple(disassembler, instruction);
- }
- }
- // We fallback to a single instruction disassembler
- AddressRange range(address, arch.GetMaximumOpcodeByteSize());
- DisassemblerSP disassembler =
- Disassembler::DisassembleRange(arch, /*plugin_name*/ nullptr,
- /*flavor*/ nullptr, target, range);
- return std::make_tuple(disassembler,
- disassembler ? disassembler->GetInstructionList()
- .GetInstructionAtAddress(address)
- : InstructionSP());
- };
-
- Optional<lldb::user_id_t> last_id;
for (size_t i = 0; i < count; i++) {
if (!HasMoreData()) {
- m_s.Printf(" no more data\n");
+ m_s << " no more data\n";
break;
}
last_id = m_cursor_up->GetId();
@@ -277,15 +259,15 @@ Optional<lldb::tid_t> TraceInstructionDumper::DumpInstructions(size_t count) {
if (const char *err = m_cursor_up->GetError()) {
if (!m_cursor_up->IsForwards() && !was_prev_instruction_an_error)
- printMissingInstructionsMessage();
+ PrintMissingInstructionsMessage();
was_prev_instruction_an_error = true;
- printInstructionHeader(m_cursor_up->GetId());
+ PrintInstructionHeader();
m_s << err;
} else {
if (m_cursor_up->IsForwards() && was_prev_instruction_an_error)
- printMissingInstructionsMessage();
+ PrintMissingInstructionsMessage();
was_prev_instruction_an_error = false;
@@ -294,24 +276,26 @@ Optional<lldb::tid_t> TraceInstructionDumper::DumpInstructions(size_t count) {
if (!m_options.raw) {
insn_info.load_address = m_cursor_up->GetLoadAddress();
insn_info.exe_ctx = exe_ctx;
- insn_info.address.SetLoadAddress(insn_info.load_address, &target);
- insn_info.sc = calculateSymbolContext(insn_info.address);
+ insn_info.address.SetLoadAddress(insn_info.load_address,
+ exe_ctx.GetTargetPtr());
+ insn_info.sc =
+ CalculateSymbolContext(insn_info.address, prev_insn_info);
std::tie(insn_info.disassembler, insn_info.instruction) =
- calculateDisass(insn_info.address, insn_info.sc);
+ CalculateDisass(insn_info, prev_insn_info, exe_ctx);
- DumpInstructionSymbolContext(m_s, prev_insn_info, insn_info);
+ DumpInstructionSymbolContext(prev_insn_info, insn_info);
}
- printInstructionHeader(m_cursor_up->GetId());
- m_s.Printf("0x%016" PRIx64, m_cursor_up->GetLoadAddress());
+ PrintInstructionHeader();
+ m_s.Format("{0:x+16}", m_cursor_up->GetLoadAddress());
if (!m_options.raw)
- DumpInstructionDisassembly(m_s, insn_info);
+ DumpInstructionDisassembly(insn_info);
prev_insn_info = insn_info;
}
- m_s.Printf("\n");
+ m_s << "\n";
if (!m_options.forwards) {
// If we move backwards, we print the events after printing
More information about the lldb-commits
mailing list