xref: /NextBSD/contrib/llvm/tools/lldb/include/lldb/Core/Disassembler.h (revision 84d351007654069f9643c8e4b4802a7f5f08ee42)
1 //===-- Disassembler.h ------------------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #ifndef liblldb_Disassembler_h_
11 #define liblldb_Disassembler_h_
12 
13 // C Includes
14 // C++ Includes
15 #include <vector>
16 #include <string>
17 
18 // Other libraries and framework includes
19 // Project includes
20 #include "lldb/lldb-private.h"
21 #include "lldb/Core/Address.h"
22 #include "lldb/Core/ArchSpec.h"
23 #include "lldb/Core/EmulateInstruction.h"
24 #include "lldb/Core/Opcode.h"
25 #include "lldb/Core/PluginInterface.h"
26 #include "lldb/Interpreter/OptionValue.h"
27 
28 namespace lldb_private {
29 
30 class Instruction
31 {
32 public:
33     Instruction (const Address &address,
34                  lldb::AddressClass addr_class = lldb::eAddressClassInvalid);
35 
36     virtual
37    ~Instruction();
38 
39     const Address &
GetAddress()40     GetAddress () const
41     {
42         return m_address;
43     }
44 
45     const char *
GetMnemonic(const ExecutionContext * exe_ctx)46     GetMnemonic (const ExecutionContext* exe_ctx)
47     {
48         CalculateMnemonicOperandsAndCommentIfNeeded (exe_ctx);
49         return m_opcode_name.c_str();
50     }
51     const char *
GetOperands(const ExecutionContext * exe_ctx)52     GetOperands (const ExecutionContext* exe_ctx)
53     {
54         CalculateMnemonicOperandsAndCommentIfNeeded (exe_ctx);
55         return m_mnemonics.c_str();
56     }
57 
58     const char *
GetComment(const ExecutionContext * exe_ctx)59     GetComment (const ExecutionContext* exe_ctx)
60     {
61         CalculateMnemonicOperandsAndCommentIfNeeded (exe_ctx);
62         return m_comment.c_str();
63     }
64 
65     virtual void
66     CalculateMnemonicOperandsAndComment (const ExecutionContext* exe_ctx) = 0;
67 
68     lldb::AddressClass
69     GetAddressClass ();
70 
71     void
SetAddress(const Address & addr)72     SetAddress (const Address &addr)
73     {
74         // Invalidate the address class to lazily discover
75         // it if we need to.
76         m_address_class = lldb::eAddressClassInvalid;
77         m_address = addr;
78     }
79 
80     //------------------------------------------------------------------
81     /// Dump the text representation of this Instruction to a Stream
82     ///
83     /// Print the (optional) address, (optional) bytes, opcode,
84     /// operands, and instruction comments to a stream.
85     ///
86     /// @param[in] s
87     ///     The Stream to add the text to.
88     ///
89     /// @param[in] show_address
90     ///     Whether the address (using disassembly_addr_format_spec formatting)
91     ///     should be printed.
92     ///
93     /// @param[in] show_bytes
94     ///     Whether the bytes of the assembly instruction should be printed.
95     ///
96     /// @param[in] max_opcode_byte_size
97     ///     The size (in bytes) of the largest instruction in the list that
98     ///     we are printing (for text justification/alignment purposes)
99     ///     Only needed if show_bytes is true.
100     ///
101     /// @param[in] exe_ctx
102     ///     The current execution context, if available.  May be used in
103     ///     the assembling of the operands+comments for this instruction.
104     ///     Pass NULL if not applicable.
105     ///
106     /// @param[in] sym_ctx
107     ///     The SymbolContext for this instruction.
108     ///     Pass NULL if not available/computed.
109     ///     Only needed if show_address is true.
110     ///
111     /// @param[in] prev_sym_ctx
112     ///     The SymbolContext for the previous instruction.  Depending on
113     ///     the disassembly address format specification, a change in
114     ///     Symbol / Function may mean that a line is printed with the new
115     ///     symbol/function name.
116     ///     Pass NULL if unavailable, or if this is the first instruction of
117     ///     the InstructionList.
118     ///     Only needed if show_address is true.
119     ///
120     /// @param[in] disassembly_addr_format
121     ///     The format specification for how addresses are printed.
122     ///     Only needed if show_address is true.
123     ///
124     /// @param[in] max_address_text_size
125     ///     The length of the longest address string at the start of the
126     ///     disassembly line that will be printed (the Debugger::FormatDisassemblerAddress() string)
127     ///     so this method can properly align the instruction opcodes.
128     ///     May be 0 to indicate no indentation/alignment of the opcodes.
129     //------------------------------------------------------------------
130 
131     virtual void
132     Dump (Stream *s,
133           uint32_t max_opcode_byte_size,
134           bool show_address,
135           bool show_bytes,
136           const ExecutionContext* exe_ctx,
137           const SymbolContext *sym_ctx,
138           const SymbolContext *prev_sym_ctx,
139           const FormatEntity::Entry *disassembly_addr_format,
140           size_t max_address_text_size);
141 
142     virtual bool
143     DoesBranch () = 0;
144 
145     virtual size_t
146     Decode (const Disassembler &disassembler,
147             const DataExtractor& data,
148             lldb::offset_t data_offset) = 0;
149 
150     virtual void
SetDescription(const char *)151     SetDescription (const char *) {}  // May be overridden in sub-classes that have descriptions.
152 
153     lldb::OptionValueSP
154     ReadArray (FILE *in_file, Stream *out_stream, OptionValue::Type data_type);
155 
156     lldb::OptionValueSP
157     ReadDictionary (FILE *in_file, Stream *out_stream);
158 
159     bool
160     DumpEmulation (const ArchSpec &arch);
161 
162     virtual bool
163     TestEmulation (Stream *stream, const char *test_file_name);
164 
165     bool
166     Emulate (const ArchSpec &arch,
167              uint32_t evaluate_options,
168              void *baton,
169              EmulateInstruction::ReadMemoryCallback read_mem_callback,
170              EmulateInstruction::WriteMemoryCallback write_mem_calback,
171              EmulateInstruction::ReadRegisterCallback read_reg_callback,
172              EmulateInstruction::WriteRegisterCallback write_reg_callback);
173 
174     const Opcode &
GetOpcode()175     GetOpcode () const
176     {
177         return m_opcode;
178     }
179 
180     uint32_t
181     GetData (DataExtractor &data);
182 
183 protected:
184     Address m_address; // The section offset address of this instruction
185     // We include an address class in the Instruction class to
186     // allow the instruction specify the eAddressClassCodeAlternateISA
187     // (currently used for thumb), and also to specify data (eAddressClassData).
188     // The usual value will be eAddressClassCode, but often when
189     // disassembling memory, you might run into data. This can
190     // help us to disassemble appropriately.
191 private:
192     lldb::AddressClass m_address_class; // Use GetAddressClass () accessor function!
193 protected:
194     Opcode m_opcode; // The opcode for this instruction
195     std::string m_opcode_name;
196     std::string m_mnemonics;
197     std::string m_comment;
198     bool m_calculated_strings;
199 
200     void
CalculateMnemonicOperandsAndCommentIfNeeded(const ExecutionContext * exe_ctx)201     CalculateMnemonicOperandsAndCommentIfNeeded (const ExecutionContext* exe_ctx)
202     {
203         if (!m_calculated_strings)
204         {
205             m_calculated_strings = true;
206             CalculateMnemonicOperandsAndComment(exe_ctx);
207         }
208     }
209 };
210 
211 
212 class InstructionList
213 {
214 public:
215     InstructionList();
216     ~InstructionList();
217 
218     size_t
219     GetSize() const;
220 
221     uint32_t
222     GetMaxOpcocdeByteSize () const;
223 
224     lldb::InstructionSP
225     GetInstructionAtIndex (size_t idx) const;
226 
227     uint32_t
228     GetIndexOfNextBranchInstruction(uint32_t start, Target &target) const;
229 
230     uint32_t
231     GetIndexOfInstructionAtLoadAddress (lldb::addr_t load_addr, Target &target);
232 
233     uint32_t
234     GetIndexOfInstructionAtAddress (const Address &addr);
235 
236     void
237     Clear();
238 
239     void
240     Append (lldb::InstructionSP &inst_sp);
241 
242     void
243     Dump (Stream *s,
244           bool show_address,
245           bool show_bytes,
246           const ExecutionContext* exe_ctx);
247 
248 private:
249     typedef std::vector<lldb::InstructionSP> collection;
250     typedef collection::iterator iterator;
251     typedef collection::const_iterator const_iterator;
252 
253     collection m_instructions;
254 };
255 
256 class PseudoInstruction :
257     public Instruction
258 {
259 public:
260 
261     PseudoInstruction ();
262 
263      virtual
264      ~PseudoInstruction ();
265 
266     virtual bool
267     DoesBranch ();
268 
269     virtual void
CalculateMnemonicOperandsAndComment(const ExecutionContext * exe_ctx)270     CalculateMnemonicOperandsAndComment (const ExecutionContext* exe_ctx)
271     {
272         // TODO: fill this in and put opcode name into Instruction::m_opcode_name,
273         // mnemonic into Instruction::m_mnemonics, and any comment into
274         // Instruction::m_comment
275     }
276 
277     virtual size_t
278     Decode (const Disassembler &disassembler,
279             const DataExtractor &data,
280             lldb::offset_t data_offset);
281 
282     void
283     SetOpcode (size_t opcode_size, void *opcode_data);
284 
285     virtual void
286     SetDescription (const char *description);
287 
288 protected:
289     std::string m_description;
290 
291     DISALLOW_COPY_AND_ASSIGN (PseudoInstruction);
292 };
293 
294 class Disassembler :
295     public std::enable_shared_from_this<Disassembler>,
296     public PluginInterface
297 {
298 public:
299 
300     enum
301     {
302         eOptionNone             = 0u,
303         eOptionShowBytes        = (1u << 0),
304         eOptionRawOuput         = (1u << 1),
305         eOptionMarkPCSourceLine = (1u << 2), // Mark the source line that contains the current PC (mixed mode only)
306         eOptionMarkPCAddress    = (1u << 3)  // Mark the disassembly line the contains the PC
307     };
308 
309     enum HexImmediateStyle
310     {
311         eHexStyleC,
312         eHexStyleAsm,
313     };
314 
315     // FindPlugin should be lax about the flavor string (it is too annoying to have various internal uses of the
316     // disassembler fail because the global flavor string gets set wrong.  Instead, if you get a flavor string you
317     // don't understand, use the default.  Folks who care to check can use the FlavorValidForArchSpec method on the
318     // disassembler they got back.
319     static lldb::DisassemblerSP
320     FindPlugin (const ArchSpec &arch, const char *flavor, const char *plugin_name);
321 
322     // This version will use the value in the Target settings if flavor is NULL;
323     static lldb::DisassemblerSP
324     FindPluginForTarget(const lldb::TargetSP target_sp, const ArchSpec &arch, const char *flavor, const char *plugin_name);
325 
326     static lldb::DisassemblerSP
327     DisassembleRange (const ArchSpec &arch,
328                       const char *plugin_name,
329                       const char *flavor,
330                       const ExecutionContext &exe_ctx,
331                       const AddressRange &disasm_range,
332                       bool prefer_file_cache);
333 
334     static lldb::DisassemblerSP
335     DisassembleBytes (const ArchSpec &arch,
336                       const char *plugin_name,
337                       const char *flavor,
338                       const Address &start,
339                       const void *bytes,
340                       size_t length,
341                       uint32_t max_num_instructions,
342                       bool data_from_file);
343 
344     static bool
345     Disassemble (Debugger &debugger,
346                  const ArchSpec &arch,
347                  const char *plugin_name,
348                  const char *flavor,
349                  const ExecutionContext &exe_ctx,
350                  const AddressRange &range,
351                  uint32_t num_instructions,
352                  uint32_t num_mixed_context_lines,
353                  uint32_t options,
354                  Stream &strm);
355 
356     static bool
357     Disassemble (Debugger &debugger,
358                  const ArchSpec &arch,
359                  const char *plugin_name,
360                  const char *flavor,
361                  const ExecutionContext &exe_ctx,
362                  const Address &start,
363                  uint32_t num_instructions,
364                  uint32_t num_mixed_context_lines,
365                  uint32_t options,
366                  Stream &strm);
367 
368     static size_t
369     Disassemble (Debugger &debugger,
370                  const ArchSpec &arch,
371                  const char *plugin_name,
372                  const char *flavor,
373                  const ExecutionContext &exe_ctx,
374                  SymbolContextList &sc_list,
375                  uint32_t num_instructions,
376                  uint32_t num_mixed_context_lines,
377                  uint32_t options,
378                  Stream &strm);
379 
380     static bool
381     Disassemble (Debugger &debugger,
382                  const ArchSpec &arch,
383                  const char *plugin_name,
384                  const char *flavor,
385                  const ExecutionContext &exe_ctx,
386                  const ConstString &name,
387                  Module *module,
388                  uint32_t num_instructions,
389                  uint32_t num_mixed_context_lines,
390                  uint32_t options,
391                  Stream &strm);
392 
393     static bool
394     Disassemble (Debugger &debugger,
395                  const ArchSpec &arch,
396                  const char *plugin_name,
397                  const char *flavor,
398                  const ExecutionContext &exe_ctx,
399                  uint32_t num_instructions,
400                  uint32_t num_mixed_context_lines,
401                  uint32_t options,
402                  Stream &strm);
403 
404     //------------------------------------------------------------------
405     // Constructors and Destructors
406     //------------------------------------------------------------------
407     Disassembler(const ArchSpec &arch, const char *flavor);
408     virtual ~Disassembler();
409 
410     typedef const char * (*SummaryCallback)(const Instruction& inst, ExecutionContext *exe_context, void *user_data);
411 
412     static bool
413     PrintInstructions (Disassembler *disasm_ptr,
414                        Debugger &debugger,
415                        const ArchSpec &arch,
416                        const ExecutionContext &exe_ctx,
417                        uint32_t num_instructions,
418                        uint32_t num_mixed_context_lines,
419                        uint32_t options,
420                        Stream &strm);
421 
422     size_t
423     ParseInstructions (const ExecutionContext *exe_ctx,
424                        const AddressRange &range,
425                        Stream *error_strm_ptr,
426                        bool prefer_file_cache);
427 
428     size_t
429     ParseInstructions (const ExecutionContext *exe_ctx,
430                        const Address &range,
431                        uint32_t num_instructions,
432                        bool prefer_file_cache);
433 
434     virtual size_t
435     DecodeInstructions (const Address &base_addr,
436                         const DataExtractor& data,
437                         lldb::offset_t data_offset,
438                         size_t num_instructions,
439                         bool append,
440                         bool data_from_file) = 0;
441 
442     InstructionList &
443     GetInstructionList ();
444 
445     const InstructionList &
446     GetInstructionList () const;
447 
448     const ArchSpec &
GetArchitecture()449     GetArchitecture () const
450     {
451         return m_arch;
452     }
453 
454     const char *
GetFlavor()455     GetFlavor () const
456     {
457         return m_flavor.c_str();
458     }
459 
460     virtual bool
461     FlavorValidForArchSpec (const lldb_private::ArchSpec &arch, const char *flavor) = 0;
462 
463 protected:
464     //------------------------------------------------------------------
465     // Classes that inherit from Disassembler can see and modify these
466     //------------------------------------------------------------------
467     ArchSpec m_arch;
468     InstructionList m_instruction_list;
469     lldb::addr_t m_base_addr;
470     std::string m_flavor;
471 
472 private:
473     //------------------------------------------------------------------
474     // For Disassembler only
475     //------------------------------------------------------------------
476     DISALLOW_COPY_AND_ASSIGN (Disassembler);
477 };
478 
479 } // namespace lldb_private
480 
481 #endif  // liblldb_Disassembler_h_
482