LLVM: lib/Target/BPF/MCTargetDesc/BPFMCCodeEmitter.cpp Source File (original) (raw)
1
2
3
4
5
6
7
8
9
10
11
12
25#include
26#include
27
28using namespace llvm;
29
30#define DEBUG_TYPE "mccodeemitter"
31
32namespace {
33
36 bool IsLittleEndian;
38
39public:
41 bool IsLittleEndian, MCContext &ctx)
42 : MRI(mri), IsLittleEndian(IsLittleEndian), Ctx(ctx) {}
43 BPFMCCodeEmitter(const BPFMCCodeEmitter &) = delete;
44 void operator=(const BPFMCCodeEmitter &) = delete;
45 ~BPFMCCodeEmitter() override = default;
46
47
48
52
53
54
58
62
66};
67
68}
69
72 return new BPFMCCodeEmitter(MCII, *Ctx.getRegisterInfo(), true, Ctx);
73}
74
77 return new BPFMCCodeEmitter(MCII, *Ctx.getRegisterInfo(), false, Ctx);
78}
79
84
85unsigned BPFMCCodeEmitter::getMachineOpValue(const MCInst &MI,
90 return MRI.getEncodingValue(MO.getReg());
93 uint64_t High32Bits = Imm >> 32, High33Bits = Imm >> 31;
94 if (MI.getOpcode() != BPF::LD_imm64 && High32Bits != 0 &&
95 High33Bits != 0x1FFFFFFFFULL) {
97 "immediate out of range, shall fit in 32 bits");
98 }
99 return static_cast<unsigned>(Imm);
100 }
101
103
104 const MCExpr *Expr = MO.getExpr();
105
107
108 if (MI.getOpcode() == BPF::JAL)
109
111 else if (MI.getOpcode() == BPF::LD_imm64)
113 else if (MI.getOpcode() == BPF::JMPL)
115 else
116
118
119 return 0;
120}
121
123{
124 return (Val & 0x0F) << 4 | (Val & 0xF0) >> 4;
125}
126
127void BPFMCCodeEmitter::encodeInstruction(const MCInst &MI,
128 SmallVectorImpl &CB,
129 SmallVectorImpl &Fixups,
130 const MCSubtargetInfo &STI) const {
131 unsigned Opcode = MI.getOpcode();
132 raw_svector_ostream OS(CB);
135
136 if (Opcode == BPF::LD_imm64 || Opcode == BPF::LD_pseudo) {
137 uint64_t Value = getBinaryCodeForInstr(MI, Fixups, STI);
139 if (IsLittleEndian)
141 else
143 OSE.write<uint16_t>(0);
144 OSE.write<uint32_t>(Value & 0xffffFFFF);
145
146 const MCOperand &MO = MI.getOperand(1);
147 uint64_t Imm = MO.isImm() ? MO.getImm() : 0;
148 OSE.write<uint8_t>(0);
149 OSE.write<uint8_t>(0);
150 OSE.write<uint16_t>(0);
151 OSE.write<uint32_t>(Imm >> 32);
152 } else {
153
154 uint64_t Value = getBinaryCodeForInstr(MI, Fixups, STI);
156 if (IsLittleEndian)
158 else
160 OSE.write<uint16_t>((Value >> 32) & 0xffff);
161 OSE.write<uint32_t>(Value & 0xffffFFFF);
162 }
163}
164
165
166uint64_t BPFMCCodeEmitter::getMemoryOpValue(const MCInst &MI, unsigned Op,
167 SmallVectorImpl &Fixups,
168 const MCSubtargetInfo &STI) const {
169
170
171 int MemOpStartIndex = 1, Opcode = MI.getOpcode();
172 if (Opcode == BPF::CMPXCHGW32 || Opcode == BPF::CMPXCHGD)
173 MemOpStartIndex = 0;
174
175 uint64_t Encoding;
176 const MCOperand Op1 = MI.getOperand(MemOpStartIndex);
177 assert(Op1.isReg() && "First operand is not register.");
178 Encoding = MRI.getEncodingValue(Op1.getReg());
179 Encoding <<= 16;
180 MCOperand Op2 = MI.getOperand(MemOpStartIndex + 1);
181 assert(Op2.isImm() && "Second operand is not immediate.");
182 Encoding |= Op2.getImm() & 0xffff;
183 return Encoding;
184}
185
186#include "BPFGenMCCodeEmitter.inc"
unsigned const MachineRegisterInfo * MRI
static void addFixup(SmallVectorImpl< MCFixup > &Fixups, uint32_t Offset, const MCExpr *Value, uint16_t Kind, bool PCRel=false)
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static uint8_t SwapBits(uint8_t Val)
Definition BPFMCCodeEmitter.cpp:122
This file defines the SmallVector class.
MCCodeEmitter - Generic instruction encoding interface.
Context object for machine code objects.
LLVM_ABI void reportWarning(SMLoc L, const Twine &Msg)
Base class for the full range of assembler expressions which are needed for parsing.
@ SymbolRef
References to labels and assigned expressions.
static MCFixup create(uint32_t Offset, const MCExpr *Value, MCFixupKind Kind, bool PCRel=false)
Consider bit fields if we need more flags.
Instances of this class represent a single low-level machine instruction.
Interface to description of machine instruction set.
Instances of this class represent operands of the MCInst class.
MCRegister getReg() const
Returns the register number.
const MCExpr * getExpr() const
MCRegisterInfo base class - We assume that the target defines a static array of MCRegisterDesc object...
Generic base class for all target subtargets.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
void push_back(const T &Elt)
LLVM Value Representation.
This is an optimization pass for GlobalISel generic memory operations.
FunctionAddr VTableAddr Value
static void addFixup(SmallVectorImpl< MCFixup > &Fixups, uint32_t Offset, const MCExpr *Value, uint16_t Kind)
@ FK_Data_4
A four-byte fixup.
@ FK_SecRel_8
A eight-byte section relative fixup.
@ FK_Data_2
A two-byte fixup.
DWARFExpression::Operation Op
MCCodeEmitter * createBPFbeMCCodeEmitter(const MCInstrInfo &MCII, MCContext &Ctx)
Definition BPFMCCodeEmitter.cpp:75
MCCodeEmitter * createBPFMCCodeEmitter(const MCInstrInfo &MCII, MCContext &Ctx)
Definition BPFMCCodeEmitter.cpp:70