ROSE  0.11.21.0
DisassemblerM68k.h
1 /* Disassembly specific to Motorola architectures */
2 #ifndef ROSE_DisassemblerM68k_H
3 #define ROSE_DisassemblerM68k_H
4 
5 #include <featureTests.h>
6 #ifdef ROSE_ENABLE_BINARY_ANALYSIS
7 #include "Disassembler.h"
8 
9 #include "InstructionEnumsM68k.h"
10 #include "BitPattern.h"
11 
12 #include <boost/serialization/access.hpp>
13 #include <boost/serialization/base_object.hpp>
14 #include <boost/serialization/export.hpp>
15 #include <boost/serialization/split_member.hpp>
16 
17 namespace Rose {
18 namespace BinaryAnalysis {
19 
22 public:
23  // State mutated during the call to disassembleOne. Used internally.
24  struct State: boost::noncopyable { // noncopyable is so we don't accidentally pass it by value
26  rose_addr_t insn_va;
27  uint16_t iwords[11];
28  size_t niwords;
29  size_t niwords_used;
31  State()
32  : insn_va(0), niwords(0), niwords_used(0) {}
33  };
34 
35 public:
44  class M68k {
45  public:
46  M68k(const std::string &name, unsigned family, const BitPattern<uint16_t> &pattern)
47  : name(name), family(family), pattern(pattern) {}
48  virtual ~M68k() {}
49  std::string name; // for debugging; same as class name but without the "M68k_" prefix
50  unsigned family; // bitmask of M68kFamily bits
51  BitPattern<uint16_t> pattern; // bits that match
52  typedef DisassemblerM68k D;
53  virtual SgAsmM68kInstruction *operator()(State&, const D *d, unsigned w0) = 0;
54  };
55 
56 private:
57  M68kFamily family;
59  // The instruction disassembly table is an array indexed by the high-order nybble of the first 16-bit word of the
60  // instruction's pattern, the so-called "operator" bits. Since most instruction disassembler have invariant operator
61  // bits, we can divide the table into 16 entries for these invariant bits, and another entry (index 16) for the cases
62  // with a variable operator byte. Each of these 17 buckets is an unordered list of instruction disassemblers whose
63  // patterns we attempt to match one at a time (the insertion function checks that there are no ambiguities).
64  typedef std::list<M68k*> IdisList;
65  typedef std::vector<IdisList> IdisTable;
66  IdisTable idis_table;
67 
68 #ifdef ROSE_HAVE_BOOST_SERIALIZATION_LIB
69 private:
70  friend class boost::serialization::access;
71 
72  template<class S>
73  void serialize_common(S &s, const unsigned /*version*/) {
74  s & BOOST_SERIALIZATION_BASE_OBJECT_NVP(Disassembler);
75  s & BOOST_SERIALIZATION_NVP(family);
76  //s & idis_table; -- not saved
77  }
78 
79  template<class S>
80  void save(S &s, const unsigned version) const {
81  serialize_common(s, version);
82  }
83 
84  template<class S>
85  void load(S &s, const unsigned version) {
86  serialize_common(s, version);
87  init();
88  }
89 
90  BOOST_SERIALIZATION_SPLIT_MEMBER();
91 #endif
92 
93 protected:
94  // undocumented constructor for serialization. The init() will be called by the serialization.
95  DisassemblerM68k()
96  : family(m68k_freescale_cpu32) {}
97 
98 public:
107  explicit DisassemblerM68k(M68kFamily family)
108  : family(family) {
109  init();
110  }
111  virtual DisassemblerM68k *clone() const ROSE_OVERRIDE { return new DisassemblerM68k(*this); }
112  virtual bool canDisassemble(SgAsmGenericHeader*) const ROSE_OVERRIDE;
113  virtual SgAsmInstruction *disassembleOne(const MemoryMap::Ptr&, rose_addr_t start_va,
114  AddressSet *successors=NULL) ROSE_OVERRIDE;
115  virtual SgAsmInstruction *makeUnknownInstruction(const Disassembler::Exception&) ROSE_OVERRIDE;
116  virtual Unparser::BasePtr unparser() const ROSE_OVERRIDE;
117 
118  typedef std::pair<SgAsmExpression*, SgAsmExpression*> ExpressionPair;
119 
123  M68k *find_idis(uint16_t *insn_bytes, size_t nbytes) const;
124 
127  void insert_idis(M68k*);
128 
130  void start_instruction(State &state, const MemoryMap::Ptr &map, rose_addr_t start_va) const{
131  state.map = map;
132  state.insn_va = start_va;
133  state.niwords = 0;
134  memset(state.iwords, 0, sizeof state.iwords);
135  state.niwords_used = 0;
136  }
137 
139  uint16_t instructionWord(State&, size_t n) const;
140 
142  size_t extensionWordsUsed(State&) const;
143 
145  SgAsmType *makeType(State&, M68kDataFormat) const;
146 
148  SgAsmRegisterReferenceExpression *makeDataRegister(State&, unsigned regnum, M68kDataFormat, size_t bit_offset=0) const;
149 
151  SgAsmRegisterReferenceExpression *makeAddressRegister(State&, unsigned regnum, M68kDataFormat, size_t bit_offset=0) const;
152 
156 
160 
164  size_t bit_offset=0) const;
165 
171  SgAsmRegisterNames *makeRegistersFromMask(State&, unsigned mask, M68kDataFormat fmt, bool reverse=false) const;
172 
178  SgAsmRegisterNames *makeFPRegistersFromMask(State&, unsigned mask, M68kDataFormat fmt, bool reverse=false) const;
179 
182 
185 
187  SgAsmRegisterReferenceExpression* makeColdFireControlRegister(State&, unsigned regnum) const;
188 
191 
194 
196  SgAsmRegisterReferenceExpression *makeMacAccumulatorRegister(State&, unsigned accumIndex) const;
197 
201  SgAsmRegisterReferenceExpression *makeFPRegister(State&, unsigned regnum) const;
202 
205 
207  SgAsmIntegerValueExpression *makeImmediateValue(State&, M68kDataFormat fmt, unsigned value) const;
208 
210  SgAsmIntegerValueExpression *makeImmediateExtension(State&, M68kDataFormat fmt, size_t ext_word_idx) const;
211 
218  SgAsmExpression *makeEffectiveAddress(State&, unsigned modreg, M68kDataFormat fmt, size_t ext_offset) const;
219  SgAsmExpression *makeEffectiveAddress(State&, unsigned mode, unsigned reg, M68kDataFormat fmt, size_t ext_offset) const;
225  SgAsmExpression *makeAddress(State&, SgAsmExpression *expr) const;
226 
229  ExpressionPair makeOffsetWidthPair(State&, unsigned extension_word) const;
230 
232  SgAsmM68kInstruction *makeInstruction(State&, M68kInstructionKind, const std::string &mnemonic,
233  SgAsmExpression *arg0=NULL, SgAsmExpression *arg1=NULL, SgAsmExpression *arg2=NULL,
234  SgAsmExpression *arg3=NULL, SgAsmExpression *arg4=NULL, SgAsmExpression *arg5=NULL,
235  SgAsmExpression *arg6=NULL) const;
236 
238  M68kFamily get_family() const { return family; }
239 
240 private:
241  void init();
242 };
243 
244 } // namespace
245 } // namespace
246 
247 #ifdef ROSE_HAVE_BOOST_SERIALIZATION_LIB
248 BOOST_CLASS_EXPORT_KEY(Rose::BinaryAnalysis::DisassemblerM68k);
249 #endif
250 
251 #endif
252 #endif
Freescale CPU32 (similar to MC68020 w/out bitfield insns.
virtual Unparser::BasePtr unparser() const ROSE_OVERRIDE
Unparser.
rose_addr_t insn_va
Address of instruction.
size_t niwords_used
High water number of instruction words used by instructionWord().
Base class for references to a machine register.
SgAsmRegisterReferenceExpression * makeRegister(RegisterDescriptor) const
Generic ways to make a register.
M68kInstructionKind
M68k instruction types.
SgAsmRegisterNames * makeRegistersFromMask(State &, unsigned mask, M68kDataFormat fmt, bool reverse=false) const
Create a list of data and/or address registers.
Base class for machine instructions.
virtual SgAsmInstruction * disassembleOne(const MemoryMap::Ptr &, rose_addr_t start_va, AddressSet *successors=NULL) ROSE_OVERRIDE
This is the lowest level disassembly function and is implemented in the architecture-specific subclas...
SgAsmRegisterNames * makeFPRegistersFromMask(State &, unsigned mask, M68kDataFormat fmt, bool reverse=false) const
Create a list of floating-point data registers.
STL namespace.
void start_instruction(State &state, const MemoryMap::Ptr &map, rose_addr_t start_va) const
Called by disassembleOne() to initialize the disassembler state for the next instruction.
Main namespace for the ROSE library.
virtual bool canDisassemble(SgAsmGenericHeader *) const ROSE_OVERRIDE
Predicate determining the suitability of a disassembler for a specific file header.
SgAsmRegisterReferenceExpression * makeFPRegister(State &, unsigned regnum) const
Create a floating point register.
SgAsmMemoryReferenceExpression * makeAddressRegisterPostIncrement(State &, unsigned regnum, M68kDataFormat fmt) const
Make a memory reference expression using an address register in post-increment mode.
SgAsmRegisterReferenceExpression * makeStatusRegister(State &) const
Create a reference to the status register.
M68kDataFormat
M68k data formats for floating-point operations.
SgAsmRegisterReferenceExpression * makeConditionCodeRegister(State &) const
Create a reference to the condition code register.
void insert_idis(M68k *)
Insert an instruction-specific disassembler.
SgAsmRegisterReferenceExpression * makeColdFireControlRegister(State &, unsigned regnum) const
Create control register for ColdFire cpu.
SgAsmRegisterReferenceExpression * makeProgramCounter(State &) const
Create a reference to the program counter register.
Disassembler for Motorola M68k-based instruction set architectures.
SgAsmRegisterReferenceExpression * makeMacRegister(State &, M68kMacRegister) const
Create a MAC register reference expression.
SgAsmIntegerValueExpression * makeImmediateValue(State &, M68kDataFormat fmt, unsigned value) const
Create an integer expression from a specified value.
Interface for disassembling a single instruction.
Reference to memory locations.
M68kFamily
Members of the Motorola Coldfire family of m68k processors.
SgAsmExpression * makeAddress(State &, SgAsmExpression *expr) const
Converts a memory-reference expression to an address.
An ordered list of registers.
Base class for container file headers.
SgAsmType * makeType(State &, M68kDataFormat) const
Create a ROSE data type for m68k data format.
Base class for integer values.
Describes (part of) a physical CPU register.
size_t extensionWordsUsed(State &) const
Returns number of instruction words referenced so far in the current instruction. ...
SgAsmExpression * makeEffectiveAddress(State &, unsigned modreg, M68kDataFormat fmt, size_t ext_offset) const
Create an expression for m68k "x" or "y".
ExpressionPair makeOffsetWidthPair(State &, unsigned extension_word) const
Create an offset width pair from an extension word.
An efficient mapping from an address space to stored data.
Definition: MemoryMap.h:112
M68kMacRegister
M68k MAC registers.
MemoryMap::Ptr map
Map from which to read instruction words.
SgAsmMemoryReferenceExpression * makeAddressRegisterPreDecrement(State &, unsigned regnum, M68kDataFormat fmt) const
Make a memory reference expression using an address register in pre-decrement mode.
size_t niwords
Number of instruction words read.
Base class for expressions.
SgAsmRegisterReferenceExpression * makeDataAddressRegister(State &, unsigned regnum, M68kDataFormat fmt, size_t bit_offset=0) const
Create either a data or address register reference expression.
Base class for binary types.
SgAsmRegisterReferenceExpression * makeMacAccumulatorRegister(State &, unsigned accumIndex) const
Create a MAC accumulator register.
SgAsmRegisterReferenceExpression * makeAddressRegister(State &, unsigned regnum, M68kDataFormat, size_t bit_offset=0) const
Create an address register reference expression.
DisassemblerM68k(M68kFamily family)
Constructor for a specific family.
SgAsmM68kInstruction * makeInstruction(State &, M68kInstructionKind, const std::string &mnemonic, SgAsmExpression *arg0=NULL, SgAsmExpression *arg1=NULL, SgAsmExpression *arg2=NULL, SgAsmExpression *arg3=NULL, SgAsmExpression *arg4=NULL, SgAsmExpression *arg5=NULL, SgAsmExpression *arg6=NULL) const
Build an instruction.
uint16_t instructionWord(State &, size_t n) const
Return the Nth instruction word.
M68kFamily get_family() const
Returns ISA family specified in constructor.
virtual SgAsmInstruction * makeUnknownInstruction(const Disassembler::Exception &) ROSE_OVERRIDE
Makes an unknown instruction from an exception.
SgAsmRegisterReferenceExpression * makeDataRegister(State &, unsigned regnum, M68kDataFormat, size_t bit_offset=0) const
Create a data register reference expression.
virtual DisassemblerM68k * clone() const ROSE_OVERRIDE
Creates a new copy of a disassembler.
Base class for all ROSE exceptions.
Definition: RoseException.h:9
M68k * find_idis(uint16_t *insn_bytes, size_t nbytes) const
Find an instruction-specific disassembler.
Virtual base class for instruction disassemblers.
Definition: Disassembler.h:50
SgAsmIntegerValueExpression * makeImmediateExtension(State &, M68kDataFormat fmt, size_t ext_word_idx) const
Create an integer expression from extension words.
uint16_t iwords[11]
Instruction words.