LLVM  16.0.0git
LanaiDisassembler.cpp
Go to the documentation of this file.
1 //===- LanaiDisassembler.cpp - Disassembler for Lanai -----------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file is part of the Lanai Disassembler.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "LanaiDisassembler.h"
14 
15 #include "LanaiAluCode.h"
16 #include "LanaiCondCode.h"
17 #include "LanaiInstrInfo.h"
19 #include "llvm/MC/MCDecoderOps.h"
20 #include "llvm/MC/MCInst.h"
22 #include "llvm/MC/TargetRegistry.h"
24 
25 using namespace llvm;
26 
28 
30  const MCSubtargetInfo &STI,
31  MCContext &Ctx) {
32  return new LanaiDisassembler(STI, Ctx);
33 }
34 
36  // Register the disassembler
39 }
40 
42  : MCDisassembler(STI, Ctx) {}
43 
44 // Forward declare because the autogenerated code will reference this.
45 // Definition is further down.
46 static DecodeStatus DecodeGPRRegisterClass(MCInst &Inst, unsigned RegNo,
47  uint64_t Address,
48  const MCDisassembler *Decoder);
49 
50 static DecodeStatus decodeRiMemoryValue(MCInst &Inst, unsigned Insn,
51  uint64_t Address,
52  const MCDisassembler *Decoder);
53 
54 static DecodeStatus decodeRrMemoryValue(MCInst &Inst, unsigned Insn,
55  uint64_t Address,
56  const MCDisassembler *Decoder);
57 
58 static DecodeStatus decodeSplsValue(MCInst &Inst, unsigned Insn,
59  uint64_t Address,
60  const MCDisassembler *Decoder);
61 
62 static DecodeStatus decodeBranch(MCInst &Inst, unsigned Insn, uint64_t Address,
63  const MCDisassembler *Decoder);
64 
65 static DecodeStatus decodePredicateOperand(MCInst &Inst, unsigned Val,
66  uint64_t Address,
67  const MCDisassembler *Decoder);
68 
69 static DecodeStatus decodeShiftImm(MCInst &Inst, unsigned Insn,
70  uint64_t Address,
71  const MCDisassembler *Decoder);
72 
73 #include "LanaiGenDisassemblerTables.inc"
74 
76  uint32_t &Insn) {
77  // We want to read exactly 4 bytes of data.
78  if (Bytes.size() < 4) {
79  Size = 0;
80  return MCDisassembler::Fail;
81  }
82 
83  // Encoded as big-endian 32-bit word in the stream.
84  Insn =
85  (Bytes[0] << 24) | (Bytes[1] << 16) | (Bytes[2] << 8) | (Bytes[3] << 0);
86 
88 }
89 
91  unsigned AluOp = LPAC::ADD;
92  // Fix up for pre and post operations.
93  int PqShift = -1;
94  if (isRMOpcode(Instr.getOpcode()))
95  PqShift = 16;
96  else if (isSPLSOpcode(Instr.getOpcode()))
97  PqShift = 10;
98  else if (isRRMOpcode(Instr.getOpcode())) {
99  PqShift = 16;
100  // Determine RRM ALU op.
101  AluOp = (Insn >> 8) & 0x7;
102  if (AluOp == 7)
103  // Handle JJJJJ
104  // 0b10000 or 0b11000
105  AluOp |= 0x20 | (((Insn >> 3) & 0xf) << 1);
106  }
107 
108  if (PqShift != -1) {
109  unsigned PQ = (Insn >> PqShift) & 0x3;
110  switch (PQ) {
111  case 0x0:
112  if (Instr.getOperand(2).isReg()) {
113  Instr.getOperand(2).setReg(Lanai::R0);
114  }
115  if (Instr.getOperand(2).isImm())
116  Instr.getOperand(2).setImm(0);
117  break;
118  case 0x1:
119  AluOp = LPAC::makePostOp(AluOp);
120  break;
121  case 0x2:
122  break;
123  case 0x3:
124  AluOp = LPAC::makePreOp(AluOp);
125  break;
126  }
127  Instr.addOperand(MCOperand::createImm(AluOp));
128  }
129 }
130 
133  ArrayRef<uint8_t> Bytes, uint64_t Address,
134  raw_ostream & /*CStream*/) const {
135  uint32_t Insn;
136 
137  DecodeStatus Result = readInstruction32(Bytes, Size, Insn);
138 
139  if (Result == MCDisassembler::Fail)
140  return MCDisassembler::Fail;
141 
142  // Call auto-generated decoder function
143  Result =
144  decodeInstruction(DecoderTableLanai32, Instr, Insn, Address, this, STI);
145 
146  if (Result != MCDisassembler::Fail) {
148  Size = 4;
149  return Result;
150  }
151 
152  return MCDisassembler::Fail;
153 }
154 
155 static const unsigned GPRDecoderTable[] = {
156  Lanai::R0, Lanai::R1, Lanai::PC, Lanai::R3, Lanai::SP, Lanai::FP,
157  Lanai::R6, Lanai::R7, Lanai::RV, Lanai::R9, Lanai::RR1, Lanai::RR2,
158  Lanai::R12, Lanai::R13, Lanai::R14, Lanai::RCA, Lanai::R16, Lanai::R17,
159  Lanai::R18, Lanai::R19, Lanai::R20, Lanai::R21, Lanai::R22, Lanai::R23,
160  Lanai::R24, Lanai::R25, Lanai::R26, Lanai::R27, Lanai::R28, Lanai::R29,
161  Lanai::R30, Lanai::R31};
162 
164  uint64_t /*Address*/,
165  const MCDisassembler * /*Decoder*/) {
166  if (RegNo > 31)
167  return MCDisassembler::Fail;
168 
169  unsigned Reg = GPRDecoderTable[RegNo];
172 }
173 
175  uint64_t Address,
176  const MCDisassembler *Decoder) {
177  // RI memory values encoded using 23 bits:
178  // 5 bit register, 16 bit constant
179  unsigned Register = (Insn >> 18) & 0x1f;
181  unsigned Offset = (Insn & 0xffff);
182  Inst.addOperand(MCOperand::createImm(SignExtend32<16>(Offset)));
183 
185 }
186 
188  uint64_t Address,
189  const MCDisassembler *Decoder) {
190  // RR memory values encoded using 20 bits:
191  // 5 bit register, 5 bit register, 2 bit PQ, 3 bit ALU operator, 5 bit JJJJJ
192  unsigned Register = (Insn >> 15) & 0x1f;
194  Register = (Insn >> 10) & 0x1f;
196 
198 }
199 
200 static DecodeStatus decodeSplsValue(MCInst &Inst, unsigned Insn,
201  uint64_t Address,
202  const MCDisassembler *Decoder) {
203  // RI memory values encoded using 17 bits:
204  // 5 bit register, 10 bit constant
205  unsigned Register = (Insn >> 12) & 0x1f;
207  unsigned Offset = (Insn & 0x3ff);
208  Inst.addOperand(MCOperand::createImm(SignExtend32<10>(Offset)));
209 
211 }
212 
213 static bool tryAddingSymbolicOperand(int64_t Value, bool IsBranch,
214  uint64_t Address, uint64_t Offset,
216  const MCDisassembler *Decoder) {
217  return Decoder->tryAddingSymbolicOperand(MI, Value, Address, IsBranch, Offset,
218  Width, /*InstSize=*/0);
219 }
220 
221 static DecodeStatus decodeBranch(MCInst &MI, unsigned Insn, uint64_t Address,
222  const MCDisassembler *Decoder) {
223  if (!tryAddingSymbolicOperand(Insn + Address, false, Address, 2, 23, MI,
224  Decoder))
225  MI.addOperand(MCOperand::createImm(Insn));
227 }
228 
229 static DecodeStatus decodeShiftImm(MCInst &Inst, unsigned Insn,
230  uint64_t Address,
231  const MCDisassembler *Decoder) {
232  unsigned Offset = (Insn & 0xffff);
233  Inst.addOperand(MCOperand::createImm(SignExtend32<16>(Offset)));
234 
236 }
237 
238 static DecodeStatus decodePredicateOperand(MCInst &Inst, unsigned Val,
239  uint64_t Address,
240  const MCDisassembler *Decoder) {
241  if (Val >= LPCC::UNKNOWN)
242  return MCDisassembler::Fail;
243  Inst.addOperand(MCOperand::createImm(Val));
245 }
llvm::LPAC::ADD
@ ADD
Definition: LanaiAluCode.h:23
LanaiAluCode.h
MI
IRTranslator LLVM IR MI
Definition: IRTranslator.cpp:109
MathExtras.h
llvm
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
llvm::MCOperand::isReg
bool isReg() const
Definition: MCInst.h:61
llvm::MCOperand::createImm
static MCOperand createImm(int64_t Val)
Definition: MCInst.h:141
llvm::MCContext
Context object for machine code objects.
Definition: MCContext.h:77
llvm::Target
Target - Wrapper for Target specific information.
Definition: TargetRegistry.h:150
llvm::X86Disassembler::Reg
Reg
All possible values of the reg field in the ModR/M byte.
Definition: X86DisassemblerDecoder.h:462
llvm::MCDisassembler::tryAddingSymbolicOperand
bool tryAddingSymbolicOperand(MCInst &Inst, int64_t Value, uint64_t Address, bool IsBranch, uint64_t Offset, uint64_t OpSize, uint64_t InstSize) const
Definition: MCDisassembler.cpp:28
llvm::TargetRegistry::RegisterMCDisassembler
static void RegisterMCDisassembler(Target &T, Target::MCDisassemblerCtorTy Fn)
RegisterMCDisassembler - Register a MCDisassembler implementation for the given target.
Definition: TargetRegistry.h:973
Offset
uint64_t Offset
Definition: ELFObjHandler.cpp:80
llvm::MCInst
Instances of this class represent a single low-level machine instruction.
Definition: MCInst.h:184
MCDecoderOps.h
decodeRrMemoryValue
static DecodeStatus decodeRrMemoryValue(MCInst &Inst, unsigned Insn, uint64_t Address, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:187
x3
In x86 we generate this spiffy xmm0 xmm0 ret in x86 we generate this which could be xmm1 movss xmm1 xmm0 ret In sse4 we could use insertps to make both better Here s another testcase that could use x3
Definition: README-SSE.txt:547
llvm::getTheLanaiTarget
Target & getTheLanaiTarget()
Definition: LanaiTargetInfo.cpp:14
PostOperandDecodeAdjust
static void PostOperandDecodeAdjust(MCInst &Instr, uint32_t Insn)
Definition: LanaiDisassembler.cpp:90
llvm::MCDisassembler::Success
@ Success
Definition: MCDisassembler.h:107
LanaiCondCode.h
MCInst.h
llvm::LPAC::makePreOp
static unsigned makePreOp(unsigned AluOp)
Definition: LanaiAluCode.h:62
MCSubtargetInfo.h
llvm::raw_ostream
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition: raw_ostream.h:52
decodePredicateOperand
static DecodeStatus decodePredicateOperand(MCInst &Inst, unsigned Val, uint64_t Address, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:238
llvm::MCDisassembler::DecodeStatus
DecodeStatus
Ternary decode status.
Definition: MCDisassembler.h:104
llvm::isRMOpcode
static bool isRMOpcode(unsigned Opcode)
Definition: LanaiInstrInfo.h:160
llvm::MCDisassembler::STI
const MCSubtargetInfo & STI
Definition: MCDisassembler.h:197
llvm::MCInst::addOperand
void addOperand(const MCOperand Op)
Definition: MCInst.h:210
llvm::isSPLSOpcode
static bool isSPLSOpcode(unsigned Opcode)
Definition: LanaiInstrInfo.h:146
llvm::LanaiDisassembler::getInstruction
MCDisassembler::DecodeStatus getInstruction(MCInst &Instr, uint64_t &Size, ArrayRef< uint8_t > Bytes, uint64_t Address, raw_ostream &CStream) const override
Returns the disassembly of a single instruction.
Definition: LanaiDisassembler.cpp:132
llvm::MCOperand::isImm
bool isImm() const
Definition: MCInst.h:62
uint64_t
LanaiTargetInfo.h
decodeRiMemoryValue
static DecodeStatus decodeRiMemoryValue(MCInst &Inst, unsigned Insn, uint64_t Address, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:174
LLVM_EXTERNAL_VISIBILITY
#define LLVM_EXTERNAL_VISIBILITY
Definition: Compiler.h:127
llvm::MCDisassembler
Superclass for all disassemblers.
Definition: MCDisassembler.h:80
readInstruction32
static DecodeStatus readInstruction32(ArrayRef< uint8_t > Bytes, uint64_t &Size, uint32_t &Insn)
Definition: LanaiDisassembler.cpp:75
GPRDecoderTable
static const unsigned GPRDecoderTable[]
Definition: LanaiDisassembler.cpp:155
LanaiDisassembler.h
llvm::MCOperand::setImm
void setImm(int64_t Val)
Definition: MCInst.h:85
llvm::LanaiDisassembler::LanaiDisassembler
LanaiDisassembler(const MCSubtargetInfo &STI, MCContext &Ctx)
Definition: LanaiDisassembler.cpp:41
R6
#define R6(n)
DecodeGPRRegisterClass
static DecodeStatus DecodeGPRRegisterClass(MCInst &Inst, unsigned RegNo, uint64_t Address, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:163
decodeShiftImm
static DecodeStatus decodeShiftImm(MCInst &Inst, unsigned Insn, uint64_t Address, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:229
llvm::LPAC::makePostOp
static unsigned makePostOp(unsigned AluOp)
Definition: LanaiAluCode.h:67
llvm::ArrayRef< uint8_t >
llvm::MCOperand::createReg
static MCOperand createReg(unsigned Reg)
Definition: MCInst.h:134
DecodeStatus
MCDisassembler::DecodeStatus DecodeStatus
Definition: LanaiDisassembler.cpp:27
uint32_t
llvm::LPCC::UNKNOWN
@ UNKNOWN
Definition: LanaiCondCode.h:31
llvm::MCDisassembler::Fail
@ Fail
Definition: MCDisassembler.h:105
llvm::Register
Wrapper class representing virtual and physical registers.
Definition: Register.h:19
decodeBranch
static DecodeStatus decodeBranch(MCInst &Inst, unsigned Insn, uint64_t Address, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:221
llvm::LanaiDisassembler
Definition: LanaiDisassembler.h:22
Insn
SmallVector< AArch64_IMM::ImmInsnModel, 4 > Insn
Definition: AArch64MIPeepholeOpt.cpp:129
decodeSplsValue
static DecodeStatus decodeSplsValue(MCInst &Inst, unsigned Insn, uint64_t Address, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:200
llvm::MCInst::getOpcode
unsigned getOpcode() const
Definition: MCInst.h:198
llvm::AMDGPU::Hwreg::Width
Width
Definition: SIDefines.h:436
llvm::isRRMOpcode
static bool isRRMOpcode(unsigned Opcode)
Definition: LanaiInstrInfo.h:170
llvm::MCInst::getOperand
const MCOperand & getOperand(unsigned i) const
Definition: MCInst.h:206
llvm::ArrayRef::size
size_t size() const
size - Get the array size.
Definition: ArrayRef.h:164
tryAddingSymbolicOperand
static bool tryAddingSymbolicOperand(int64_t Value, bool IsBranch, uint64_t Address, uint64_t Offset, uint64_t Width, MCInst &MI, const MCDisassembler *Decoder)
Definition: LanaiDisassembler.cpp:213
llvm::MCOperand::setReg
void setReg(unsigned Reg)
Set the register number.
Definition: MCInst.h:75
LLVMInitializeLanaiDisassembler
LLVM_EXTERNAL_VISIBILITY void LLVMInitializeLanaiDisassembler()
Definition: LanaiDisassembler.cpp:35
InlinePriorityMode::Size
@ Size
LanaiInstrInfo.h
createLanaiDisassembler
static MCDisassembler * createLanaiDisassembler(const Target &, const MCSubtargetInfo &STI, MCContext &Ctx)
Definition: LanaiDisassembler.cpp:29
TargetRegistry.h
llvm::MCSubtargetInfo
Generic base class for all target subtargets.
Definition: MCSubtargetInfo.h:76
llvm::Value
LLVM Value Representation.
Definition: Value.h:74