LLVM  14.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"
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 void *Decoder);
49 
50 static DecodeStatus decodeRiMemoryValue(MCInst &Inst, unsigned Insn,
51  uint64_t Address, const void *Decoder);
52 
53 static DecodeStatus decodeRrMemoryValue(MCInst &Inst, unsigned Insn,
54  uint64_t Address, const void *Decoder);
55 
56 static DecodeStatus decodeSplsValue(MCInst &Inst, unsigned Insn,
57  uint64_t Address, const void *Decoder);
58 
59 static DecodeStatus decodeBranch(MCInst &Inst, unsigned Insn, uint64_t Address,
60  const void *Decoder);
61 
62 static DecodeStatus decodePredicateOperand(MCInst &Inst, unsigned Val,
63  uint64_t Address,
64  const void *Decoder);
65 
66 static DecodeStatus decodeShiftImm(MCInst &Inst, unsigned Insn,
67  uint64_t Address, const void *Decoder);
68 
69 #include "LanaiGenDisassemblerTables.inc"
70 
72  uint32_t &Insn) {
73  // We want to read exactly 4 bytes of data.
74  if (Bytes.size() < 4) {
75  Size = 0;
76  return MCDisassembler::Fail;
77  }
78 
79  // Encoded as big-endian 32-bit word in the stream.
80  Insn =
81  (Bytes[0] << 24) | (Bytes[1] << 16) | (Bytes[2] << 8) | (Bytes[3] << 0);
82 
84 }
85 
87  unsigned AluOp = LPAC::ADD;
88  // Fix up for pre and post operations.
89  int PqShift = -1;
90  if (isRMOpcode(Instr.getOpcode()))
91  PqShift = 16;
92  else if (isSPLSOpcode(Instr.getOpcode()))
93  PqShift = 10;
94  else if (isRRMOpcode(Instr.getOpcode())) {
95  PqShift = 16;
96  // Determine RRM ALU op.
97  AluOp = (Insn >> 8) & 0x7;
98  if (AluOp == 7)
99  // Handle JJJJJ
100  // 0b10000 or 0b11000
101  AluOp |= 0x20 | (((Insn >> 3) & 0xf) << 1);
102  }
103 
104  if (PqShift != -1) {
105  unsigned PQ = (Insn >> PqShift) & 0x3;
106  switch (PQ) {
107  case 0x0:
108  if (Instr.getOperand(2).isReg()) {
109  Instr.getOperand(2).setReg(Lanai::R0);
110  }
111  if (Instr.getOperand(2).isImm())
112  Instr.getOperand(2).setImm(0);
113  break;
114  case 0x1:
115  AluOp = LPAC::makePostOp(AluOp);
116  break;
117  case 0x2:
118  break;
119  case 0x3:
120  AluOp = LPAC::makePreOp(AluOp);
121  break;
122  }
123  Instr.addOperand(MCOperand::createImm(AluOp));
124  }
125 }
126 
129  ArrayRef<uint8_t> Bytes, uint64_t Address,
130  raw_ostream & /*CStream*/) const {
131  uint32_t Insn;
132 
133  DecodeStatus Result = readInstruction32(Bytes, Size, Insn);
134 
135  if (Result == MCDisassembler::Fail)
136  return MCDisassembler::Fail;
137 
138  // Call auto-generated decoder function
139  Result =
140  decodeInstruction(DecoderTableLanai32, Instr, Insn, Address, this, STI);
141 
142  if (Result != MCDisassembler::Fail) {
144  Size = 4;
145  return Result;
146  }
147 
148  return MCDisassembler::Fail;
149 }
150 
151 static const unsigned GPRDecoderTable[] = {
152  Lanai::R0, Lanai::R1, Lanai::PC, Lanai::R3, Lanai::SP, Lanai::FP,
153  Lanai::R6, Lanai::R7, Lanai::RV, Lanai::R9, Lanai::RR1, Lanai::RR2,
154  Lanai::R12, Lanai::R13, Lanai::R14, Lanai::RCA, Lanai::R16, Lanai::R17,
155  Lanai::R18, Lanai::R19, Lanai::R20, Lanai::R21, Lanai::R22, Lanai::R23,
156  Lanai::R24, Lanai::R25, Lanai::R26, Lanai::R27, Lanai::R28, Lanai::R29,
157  Lanai::R30, Lanai::R31};
158 
160  uint64_t /*Address*/,
161  const void * /*Decoder*/) {
162  if (RegNo > 31)
163  return MCDisassembler::Fail;
164 
165  unsigned Reg = GPRDecoderTable[RegNo];
168 }
169 
171  uint64_t Address, const void *Decoder) {
172  // RI memory values encoded using 23 bits:
173  // 5 bit register, 16 bit constant
174  unsigned Register = (Insn >> 18) & 0x1f;
176  unsigned Offset = (Insn & 0xffff);
177  Inst.addOperand(MCOperand::createImm(SignExtend32<16>(Offset)));
178 
180 }
181 
183  uint64_t Address, const void *Decoder) {
184  // RR memory values encoded using 20 bits:
185  // 5 bit register, 5 bit register, 2 bit PQ, 3 bit ALU operator, 5 bit JJJJJ
186  unsigned Register = (Insn >> 15) & 0x1f;
188  Register = (Insn >> 10) & 0x1f;
190 
192 }
193 
194 static DecodeStatus decodeSplsValue(MCInst &Inst, unsigned Insn,
195  uint64_t Address, const void *Decoder) {
196  // RI memory values encoded using 17 bits:
197  // 5 bit register, 10 bit constant
198  unsigned Register = (Insn >> 12) & 0x1f;
200  unsigned Offset = (Insn & 0x3ff);
201  Inst.addOperand(MCOperand::createImm(SignExtend32<10>(Offset)));
202 
204 }
205 
206 static bool tryAddingSymbolicOperand(int64_t Value, bool IsBranch,
207  uint64_t Address, uint64_t Offset,
209  const void *Decoder) {
210  const MCDisassembler *Dis = static_cast<const MCDisassembler *>(Decoder);
211  return Dis->tryAddingSymbolicOperand(MI, Value, Address, IsBranch, Offset,
212  Width);
213 }
214 
215 static DecodeStatus decodeBranch(MCInst &MI, unsigned Insn, uint64_t Address,
216  const void *Decoder) {
217  if (!tryAddingSymbolicOperand(Insn + Address, false, Address, 2, 23, MI,
218  Decoder))
219  MI.addOperand(MCOperand::createImm(Insn));
221 }
222 
223 static DecodeStatus decodeShiftImm(MCInst &Inst, unsigned Insn,
224  uint64_t Address, const void *Decoder) {
225  unsigned Offset = (Insn & 0xffff);
226  Inst.addOperand(MCOperand::createImm(SignExtend32<16>(Offset)));
227 
229 }
230 
231 static DecodeStatus decodePredicateOperand(MCInst &Inst, unsigned Val,
232  uint64_t Address,
233  const void *Decoder) {
234  if (Val >= LPCC::UNKNOWN)
235  return MCDisassembler::Fail;
236  Inst.addOperand(MCOperand::createImm(Val));
238 }
llvm::Check::Size
@ Size
Definition: FileCheck.h:73
MCFixedLenDisassembler.h
llvm::LPAC::ADD
@ ADD
Definition: LanaiAluCode.h:23
LanaiAluCode.h
MI
IRTranslator LLVM IR MI
Definition: IRTranslator.cpp:105
MathExtras.h
llvm
This file implements support for optimizing divisions by a constant.
Definition: AllocatorList.h:23
Reg
unsigned Reg
Definition: MachineSink.cpp:1566
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:72
llvm::Target
Target - Wrapper for Target specific information.
Definition: TargetRegistry.h:137
decodeRiMemoryValue
static DecodeStatus decodeRiMemoryValue(MCInst &Inst, unsigned Insn, uint64_t Address, const void *Decoder)
Definition: LanaiDisassembler.cpp:170
llvm::TargetRegistry::RegisterMCDisassembler
static void RegisterMCDisassembler(Target &T, Target::MCDisassemblerCtorTy Fn)
RegisterMCDisassembler - Register a MCDisassembler implementation for the given target.
Definition: TargetRegistry.h:916
Offset
uint64_t Offset
Definition: ELFObjHandler.cpp:81
llvm::MCInst
Instances of this class represent a single low-level machine instruction.
Definition: MCInst.h:184
tryAddingSymbolicOperand
static bool tryAddingSymbolicOperand(int64_t Value, bool IsBranch, uint64_t Address, uint64_t Offset, uint64_t Width, MCInst &MI, const void *Decoder)
Definition: LanaiDisassembler.cpp:206
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:86
decodeRrMemoryValue
static DecodeStatus decodeRrMemoryValue(MCInst &Inst, unsigned Insn, uint64_t Address, const void *Decoder)
Definition: LanaiDisassembler.cpp:182
llvm::MCDisassembler::Success
@ Success
Definition: MCDisassembler.h:103
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:53
llvm::MCDisassembler::DecodeStatus
DecodeStatus
Ternary decode status.
Definition: MCDisassembler.h:100
llvm::isRMOpcode
static bool isRMOpcode(unsigned Opcode)
Definition: LanaiInstrInfo.h:160
DecodeGPRRegisterClass
static DecodeStatus DecodeGPRRegisterClass(MCInst &Inst, unsigned RegNo, uint64_t Address, const void *Decoder)
Definition: LanaiDisassembler.cpp:159
llvm::MCDisassembler::STI
const MCSubtargetInfo & STI
Definition: MCDisassembler.h:170
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:128
llvm::MCOperand::isImm
bool isImm() const
Definition: MCInst.h:62
decodeBranch
static DecodeStatus decodeBranch(MCInst &Inst, unsigned Insn, uint64_t Address, const void *Decoder)
Definition: LanaiDisassembler.cpp:215
uint64_t
LanaiTargetInfo.h
LLVM_EXTERNAL_VISIBILITY
#define LLVM_EXTERNAL_VISIBILITY
Definition: Compiler.h:132
llvm::MCDisassembler
Superclass for all disassemblers.
Definition: MCDisassembler.h:76
readInstruction32
static DecodeStatus readInstruction32(ArrayRef< uint8_t > Bytes, uint64_t &Size, uint32_t &Insn)
Definition: LanaiDisassembler.cpp:71
llvm::HighlightColor::Address
@ Address
GPRDecoderTable
static const unsigned GPRDecoderTable[]
Definition: LanaiDisassembler.cpp:151
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)
llvm::MCDisassembler::tryAddingSymbolicOperand
bool tryAddingSymbolicOperand(MCInst &Inst, int64_t Value, uint64_t Address, bool IsBranch, uint64_t Offset, uint64_t InstSize) const
Definition: MCDisassembler.cpp:26
decodePredicateOperand
static DecodeStatus decodePredicateOperand(MCInst &Inst, unsigned Val, uint64_t Address, const void *Decoder)
Definition: LanaiDisassembler.cpp:231
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:101
llvm::Register
Wrapper class representing virtual and physical registers.
Definition: Register.h:19
llvm::LanaiDisassembler
Definition: LanaiDisassembler.h:22
Insn
SmallVector< AArch64_IMM::ImmInsnModel, 4 > Insn
Definition: AArch64MIPeepholeOpt.cpp:74
llvm::MCInst::getOpcode
unsigned getOpcode() const
Definition: MCInst.h:198
llvm::AMDGPU::Hwreg::Width
Width
Definition: SIDefines.h:413
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:165
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
decodeShiftImm
static DecodeStatus decodeShiftImm(MCInst &Inst, unsigned Insn, uint64_t Address, const void *Decoder)
Definition: LanaiDisassembler.cpp:223
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:75
decodeSplsValue
static DecodeStatus decodeSplsValue(MCInst &Inst, unsigned Insn, uint64_t Address, const void *Decoder)
Definition: LanaiDisassembler.cpp:194
llvm::Value
LLVM Value Representation.
Definition: Value.h:75