31#define LLDB_OPTIONS_disassemble
32#include "CommandOptions.inc"
41 uint32_t option_idx, llvm::StringRef option_arg,
45 const int short_option = m_getopt_table[option_idx].val;
47 switch (short_option) {
53 if (option_arg.getAsInteger(0, num_lines_context))
54 error.SetErrorStringWithFormat(
"invalid num context lines string: \"%s\"",
55 option_arg.str().c_str());
59 if (option_arg.getAsInteger(0, num_instructions))
60 error.SetErrorStringWithFormat(
61 "invalid num of instructions string: \"%s\"",
62 option_arg.str().c_str());
70 show_control_flow_kind =
true;
77 some_location_specified =
true;
83 some_location_specified =
true;
87 func_name.assign(std::string(option_arg));
88 some_location_specified =
true;
93 some_location_specified =
true;
101 some_location_specified =
true;
105 plugin_name.assign(std::string(option_arg));
111 if (target_sp && (target_sp->GetArchitecture().GetTriple().getArch() ==
113 target_sp->GetArchitecture().GetTriple().getArch() ==
114 llvm::Triple::x86_64)) {
115 flavor_string.assign(std::string(option_arg));
117 error.SetErrorStringWithFormat(
"Disassembler flavors are currently only "
118 "supported for x86 and x86_64 targets.");
127 current_function =
true;
128 some_location_specified =
true;
132 if (execution_context) {
133 const auto &target_sp = execution_context->
GetTargetSP();
134 auto platform_ptr = target_sp ? target_sp->GetPlatform().get() :
nullptr;
143 some_location_specified =
true;
152 llvm_unreachable(
"Unimplemented option");
162 show_control_flow_kind =
false;
163 num_lines_context = 0;
164 num_instructions = 0;
166 current_function =
false;
176 execution_context ? execution_context->
GetTargetPtr() :
nullptr;
185 llvm::Triple::x86_64) {
188 flavor_string.assign(
"default");
191 flavor_string.assign(
"default");
194 some_location_specified =
false;
200 if (!some_location_specified)
201 current_function =
true;
205llvm::ArrayRef<OptionDefinition>
207 return llvm::ArrayRef(g_disassemble_options);
215 interpreter,
"disassemble",
216 "Disassemble specified instructions in the current target. "
217 "Defaults to the current function for the current thread and "
219 "disassemble [<cmd-options>]", eCommandRequiresTarget) {}
224 llvm::StringRef what) {
227 return llvm::Error::success();
229 msg <<
"Not disassembling " << what <<
" because it is very large ";
232 msg <<
". To disassemble specify an instruction count limit, start/stop "
233 "addresses or use the --force option.";
234 return llvm::createStringError(llvm::inconvertibleErrorCode(),
238llvm::Expected<std::vector<AddressRange>>
240 std::vector<AddressRange> ranges;
241 const auto &get_range = [&](
Address addr) {
242 ModuleSP module_sp(addr.GetModule());
244 bool resolve_tail_call_address =
true;
245 addr.GetModule()->ResolveSymbolContextForAddress(
246 addr, eSymbolContextEverything, sc, resolve_tail_call_address);
251 ranges.push_back(range);
257 Address symbol_containing_address;
260 get_range(symbol_containing_address);
267 get_range(file_address);
272 if (ranges.empty()) {
273 return llvm::createStringError(
274 llvm::inconvertibleErrorCode(),
275 "Could not find function bounds for address 0x%" PRIx64,
280 return std::move(err);
284llvm::Expected<std::vector<AddressRange>>
290 return llvm::createStringError(
291 llvm::inconvertibleErrorCode(),
292 "Cannot disassemble around the current "
293 "function without the process being stopped.\n");
295 return llvm::createStringError(llvm::inconvertibleErrorCode(),
296 "Cannot disassemble around the current "
297 "function without a selected frame: "
298 "no currently running process.\n");
311 if (llvm::Error err =
CheckRangeSize(range,
"the current function"))
312 return std::move(err);
313 return std::vector<AddressRange>{range};
316llvm::Expected<std::vector<AddressRange>>
322 return llvm::createStringError(
323 llvm::inconvertibleErrorCode(),
324 "Cannot disassemble around the current "
325 "function without the process being stopped.\n");
327 return llvm::createStringError(llvm::inconvertibleErrorCode(),
328 "Cannot disassemble around the current "
329 "line without a selected frame: "
330 "no currently running process.\n");
337 return std::vector<AddressRange>{pc_line_entry.
range};
344llvm::Expected<std::vector<AddressRange>>
355 function_options, sc_list);
357 std::vector<AddressRange> ranges;
358 llvm::Error range_errs = llvm::Error::success();
360 const uint32_t scope =
361 eSymbolContextBlock | eSymbolContextFunction | eSymbolContextSymbol;
362 const bool use_inline_block_range =
true;
364 for (uint32_t range_idx = 0;
365 sc.GetAddressRange(scope, range_idx, use_inline_block_range, range);
368 range_errs = joinErrors(std::move(range_errs), std::move(err));
370 ranges.push_back(range);
373 if (ranges.empty()) {
375 return std::move(range_errs);
376 return llvm::createStringError(llvm::inconvertibleErrorCode(),
377 "Unable to find symbol with name '%s'.\n",
385llvm::Expected<std::vector<AddressRange>>
391 return llvm::createStringError(
392 llvm::inconvertibleErrorCode(),
393 "Cannot disassemble around the current "
394 "function without the process being stopped.\n");
396 return llvm::createStringError(llvm::inconvertibleErrorCode(),
397 "Cannot disassemble around the current "
398 "PC without a selected frame: "
399 "no currently running process.\n");
411llvm::Expected<std::vector<AddressRange>>
416 return llvm::createStringError(llvm::inconvertibleErrorCode(),
417 "End address before start address.");
424llvm::Expected<std::vector<AddressRange>>
449 "use the --arch option or set the target architecture to disassemble");
462 "Unable to find Disassembler plug-in named '%s' that supports the "
463 "'%s' architecture.\n",
467 "Unable to find Disassembler plug-in for the '%s' architecture.\n",
470 }
else if (flavor_string !=
nullptr && !disassembler->FlavorValidForArchSpec(
473 "invalid disassembler flavor \"%s\", using default.\n", flavor_string);
477 if (!command.
empty()) {
479 "\"disassemble\" arguments are specified as options.\n");
480 const int terminal_width =
507 llvm::Expected<std::vector<AddressRange>> ranges =
514 bool print_sc_header = ranges->size() > 1;
519 if (limit.
value == 0)
533 "Failed to disassemble memory in function at 0x%8.8" PRIx64
".\n",
537 "Failed to disassemble memory at 0x%8.8" PRIx64
".\n",
538 cur_range.GetBaseAddress().GetLoadAddress(&target));
static constexpr unsigned default_disasm_num_ins
static constexpr unsigned default_disasm_byte_size
static llvm::raw_ostream & error(Stream &strm)
A section + offset based address range class.
bool Dump(Stream *s, Target *target, Address::DumpStyle style, Address::DumpStyle fallback_style=Address::DumpStyleInvalid) const
Dump a description of this object to a Stream.
lldb::addr_t GetByteSize() const
Get accessor for the byte size of this range.
A section + offset based address class.
@ DumpStyleFileAddress
Display as the file address (if any).
@ DumpStyleLoadAddress
Display as the load address (if resolved).
bool IsValid() const
Tests if this ArchSpec is valid.
llvm::Triple & GetTriple()
Architecture triple accessor.
const char * GetArchitectureName() const
Returns a static string representing the current architecture.
A command line argument class.
bool show_control_flow_kind
Status SetOptionValue(uint32_t option_idx, llvm::StringRef option_arg, ExecutionContext *execution_context) override
Set the value of an option.
uint32_t num_lines_context
void OptionParsingStarting(ExecutionContext *execution_context) override
Status OptionParsingFinished(ExecutionContext *execution_context) override
lldb::addr_t symbol_containing_addr
llvm::ArrayRef< OptionDefinition > GetDefinitions() override
~CommandOptions() override
const char * GetFlavorString()
const char * GetPluginName()
uint32_t num_instructions
llvm::Expected< std::vector< AddressRange > > GetCurrentFunctionRanges()
void DoExecute(Args &command, CommandReturnObject &result) override
~CommandObjectDisassemble() override
llvm::Expected< std::vector< AddressRange > > GetStartEndAddressRanges()
llvm::Error CheckRangeSize(const AddressRange &range, llvm::StringRef what)
CommandObjectDisassemble(CommandInterpreter &interpreter)
llvm::Expected< std::vector< AddressRange > > GetNameRanges(CommandReturnObject &result)
llvm::Expected< std::vector< AddressRange > > GetPCRanges()
llvm::Expected< std::vector< AddressRange > > GetCurrentLineRanges()
Options * GetOptions() override
llvm::Expected< std::vector< AddressRange > > GetContainingAddressRanges()
llvm::Expected< std::vector< AddressRange > > GetRangesForSelectedMode(CommandReturnObject &result)
ExecutionContext m_exe_ctx
CommandInterpreter & GetCommandInterpreter()
void void AppendError(llvm::StringRef in_string)
void AppendWarningWithFormat(const char *format,...) __attribute__((format(printf
Stream & GetErrorStream()
void SetStatus(lldb::ReturnStatus status)
void AppendErrorWithFormat(const char *format,...) __attribute__((format(printf
void void AppendWarning(llvm::StringRef in_string)
Stream & GetOutputStream()
A uniqued constant string class.
const char * GetCString() const
Get the string value as a C string.
uint64_t GetTerminalWidth() const
static lldb::DisassemblerSP FindPlugin(const ArchSpec &arch, const char *flavor, const char *plugin_name)
@ eOptionMarkPCSourceLine
@ eOptionShowControlFlowKind
static bool Disassemble(Debugger &debugger, const ArchSpec &arch, const char *plugin_name, const char *flavor, const ExecutionContext &exe_ctx, const Address &start, Limit limit, bool mixed_source_and_assembly, uint32_t num_mixed_context_lines, uint32_t options, Stream &strm)
"lldb/Target/ExecutionContext.h" A class that contains an execution context.
const lldb::TargetSP & GetTargetSP() const
Get accessor to get the target shared pointer.
StackFrame * GetFramePtr() const
Returns a pointer to the frame object.
Target * GetTargetPtr() const
Returns a pointer to the target object.
Process * GetProcessPtr() const
Returns a pointer to the process object.
const AddressRange & GetAddressRange()
void FindFunctions(ConstString name, lldb::FunctionNameType name_type_mask, const ModuleFunctionSearchOptions &options, SymbolContextList &sc_list) const
ModuleIterable Modules() const
void GenerateOptionUsage(Stream &strm, CommandObject &cmd, uint32_t screen_width)
A plug-in interface definition class for debugging a process.
bool ResolveLoadAddress(lldb::addr_t load_addr, Address &so_addr, bool allow_section_end=false) const
This base class provides an interface to stack frames.
const SymbolContext & GetSymbolContext(lldb::SymbolContextItem resolve_scope)
Provide a SymbolContext for this StackFrame's current pc value.
const Address & GetFrameCodeAddress()
Get an Address for the current pc value in this StackFrame.
llvm::StringRef GetString() const
Defines a list of symbol context objects.
SymbolContextIterable SymbolContexts()
Defines a symbol context baton that can be handed other debug core functions.
Function * function
The Function for a given query.
bool GetAddressRange(uint32_t scope, uint32_t range_idx, bool use_inline_block_range, AddressRange &range) const
Get the address range contained within a symbol context.
Symbol * symbol
The Symbol for a given query.
LineEntry line_entry
The LineEntry for a given query.
bool ValueIsAddress() const
lldb::addr_t GetByteSize() const
Address GetAddress() const
const char * GetDisassemblyFlavor() const
SectionLoadList & GetSectionLoadList()
const ModuleList & GetImages() const
Get accessor for the images for this process.
const ArchSpec & GetArchitecture() const
#define LLDB_INVALID_ADDRESS
A class that represents a running process on the host machine.
const char * toString(AppleArm64ExceptionClass EC)
std::shared_ptr< lldb_private::Disassembler > DisassemblerSP
@ eReturnStatusSuccessFinishResult
std::shared_ptr< lldb_private::Target > TargetSP
std::shared_ptr< lldb_private::Module > ModuleSP
A line table entry class.
bool IsValid() const
Check if a line entry object is valid.
AddressRange range
The section offset address range for this line entry.
Options used by Module::FindFunctions.
bool include_inlines
Include inlined functions.
bool include_symbols
Include the symbol table.
static lldb::addr_t ToAddress(const ExecutionContext *exe_ctx, llvm::StringRef s, lldb::addr_t fail_value, Status *error_ptr)
Try to parse an address.