diff options
Diffstat (limited to 'contrib/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp')
-rw-r--r-- | contrib/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp | 91 |
1 files changed, 91 insertions, 0 deletions
diff --git a/contrib/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp b/contrib/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp new file mode 100644 index 0000000..b2ed137 --- /dev/null +++ b/contrib/llvm/lib/Target/RISCV/MCTargetDesc/RISCVMCCodeEmitter.cpp @@ -0,0 +1,91 @@ +//===-- RISCVMCCodeEmitter.cpp - Convert RISCV code to machine code -------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file implements the RISCVMCCodeEmitter class. +// +//===----------------------------------------------------------------------===// + +#include "MCTargetDesc/RISCVMCTargetDesc.h" +#include "llvm/ADT/Statistic.h" +#include "llvm/MC/MCCodeEmitter.h" +#include "llvm/MC/MCContext.h" +#include "llvm/MC/MCExpr.h" +#include "llvm/MC/MCInst.h" +#include "llvm/MC/MCRegisterInfo.h" +#include "llvm/MC/MCSymbol.h" +#include "llvm/MC/MCAsmInfo.h" +#include "llvm/Support/EndianStream.h" +#include "llvm/Support/raw_ostream.h" + +using namespace llvm; + +#define DEBUG_TYPE "mccodeemitter" + +STATISTIC(MCNumEmitted, "Number of MC instructions emitted"); + +namespace { +class RISCVMCCodeEmitter : public MCCodeEmitter { + RISCVMCCodeEmitter(const RISCVMCCodeEmitter &) = delete; + void operator=(const RISCVMCCodeEmitter &) = delete; + MCContext &Ctx; + +public: + RISCVMCCodeEmitter(MCContext &ctx) : Ctx(ctx) {} + + ~RISCVMCCodeEmitter() override {} + + void encodeInstruction(const MCInst &MI, raw_ostream &OS, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const override; + + /// TableGen'erated function for getting the binary encoding for an + /// instruction. + uint64_t getBinaryCodeForInstr(const MCInst &MI, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const; + + /// Return binary encoding of operand. If the machine operand requires + /// relocation, record the relocation and return zero. + unsigned getMachineOpValue(const MCInst &MI, const MCOperand &MO, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const; +}; +} // end anonymous namespace + +MCCodeEmitter *llvm::createRISCVMCCodeEmitter(const MCInstrInfo &MCII, + const MCRegisterInfo &MRI, + MCContext &Ctx) { + return new RISCVMCCodeEmitter(Ctx); +} + +void RISCVMCCodeEmitter::encodeInstruction(const MCInst &MI, raw_ostream &OS, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const { + // For now, we only support RISC-V instructions with 32-bit length + uint32_t Bits = getBinaryCodeForInstr(MI, Fixups, STI); + support::endian::Writer<support::little>(OS).write(Bits); + ++MCNumEmitted; // Keep track of the # of mi's emitted. +} + +unsigned +RISCVMCCodeEmitter::getMachineOpValue(const MCInst &MI, const MCOperand &MO, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const { + + if (MO.isReg()) + return Ctx.getRegisterInfo()->getEncodingValue(MO.getReg()); + + if (MO.isImm()) + return static_cast<unsigned>(MO.getImm()); + + llvm_unreachable("Unhandled expression!"); + return 0; +} + +#include "RISCVGenMCCodeEmitter.inc" |