1*9880d681SAndroid Build Coastguard Worker //===-- LanaiMCTargetDesc.cpp - Lanai Target Descriptions -----------------===//
2*9880d681SAndroid Build Coastguard Worker //
3*9880d681SAndroid Build Coastguard Worker // The LLVM Compiler Infrastructure
4*9880d681SAndroid Build Coastguard Worker //
5*9880d681SAndroid Build Coastguard Worker // This file is distributed under the University of Illinois Open Source
6*9880d681SAndroid Build Coastguard Worker // License. See LICENSE.TXT for details.
7*9880d681SAndroid Build Coastguard Worker //
8*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
9*9880d681SAndroid Build Coastguard Worker //
10*9880d681SAndroid Build Coastguard Worker // This file provides Lanai specific target descriptions.
11*9880d681SAndroid Build Coastguard Worker //
12*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
13*9880d681SAndroid Build Coastguard Worker
14*9880d681SAndroid Build Coastguard Worker #include "LanaiMCTargetDesc.h"
15*9880d681SAndroid Build Coastguard Worker
16*9880d681SAndroid Build Coastguard Worker #include "InstPrinter/LanaiInstPrinter.h"
17*9880d681SAndroid Build Coastguard Worker #include "LanaiMCAsmInfo.h"
18*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCInstrAnalysis.h"
19*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCInstrInfo.h"
20*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCStreamer.h"
21*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCSubtargetInfo.h"
22*9880d681SAndroid Build Coastguard Worker #include "llvm/Support/ErrorHandling.h"
23*9880d681SAndroid Build Coastguard Worker #include "llvm/Support/TargetRegistry.h"
24*9880d681SAndroid Build Coastguard Worker
25*9880d681SAndroid Build Coastguard Worker #define GET_INSTRINFO_MC_DESC
26*9880d681SAndroid Build Coastguard Worker #include "LanaiGenInstrInfo.inc"
27*9880d681SAndroid Build Coastguard Worker
28*9880d681SAndroid Build Coastguard Worker #define GET_SUBTARGETINFO_MC_DESC
29*9880d681SAndroid Build Coastguard Worker #include "LanaiGenSubtargetInfo.inc"
30*9880d681SAndroid Build Coastguard Worker
31*9880d681SAndroid Build Coastguard Worker #define GET_REGINFO_MC_DESC
32*9880d681SAndroid Build Coastguard Worker #include "LanaiGenRegisterInfo.inc"
33*9880d681SAndroid Build Coastguard Worker
34*9880d681SAndroid Build Coastguard Worker using namespace llvm;
35*9880d681SAndroid Build Coastguard Worker
createLanaiMCInstrInfo()36*9880d681SAndroid Build Coastguard Worker static MCInstrInfo *createLanaiMCInstrInfo() {
37*9880d681SAndroid Build Coastguard Worker MCInstrInfo *X = new MCInstrInfo();
38*9880d681SAndroid Build Coastguard Worker InitLanaiMCInstrInfo(X);
39*9880d681SAndroid Build Coastguard Worker return X;
40*9880d681SAndroid Build Coastguard Worker }
41*9880d681SAndroid Build Coastguard Worker
createLanaiMCRegisterInfo(const Triple & TT)42*9880d681SAndroid Build Coastguard Worker static MCRegisterInfo *createLanaiMCRegisterInfo(const Triple &TT) {
43*9880d681SAndroid Build Coastguard Worker MCRegisterInfo *X = new MCRegisterInfo();
44*9880d681SAndroid Build Coastguard Worker InitLanaiMCRegisterInfo(X, Lanai::RCA, 0, 0, Lanai::PC);
45*9880d681SAndroid Build Coastguard Worker return X;
46*9880d681SAndroid Build Coastguard Worker }
47*9880d681SAndroid Build Coastguard Worker
48*9880d681SAndroid Build Coastguard Worker static MCSubtargetInfo *
createLanaiMCSubtargetInfo(const Triple & TT,StringRef CPU,StringRef FS)49*9880d681SAndroid Build Coastguard Worker createLanaiMCSubtargetInfo(const Triple &TT, StringRef CPU, StringRef FS) {
50*9880d681SAndroid Build Coastguard Worker std::string CPUName = CPU;
51*9880d681SAndroid Build Coastguard Worker if (CPUName.empty())
52*9880d681SAndroid Build Coastguard Worker CPUName = "generic";
53*9880d681SAndroid Build Coastguard Worker
54*9880d681SAndroid Build Coastguard Worker return createLanaiMCSubtargetInfoImpl(TT, CPUName, FS);
55*9880d681SAndroid Build Coastguard Worker }
56*9880d681SAndroid Build Coastguard Worker
createMCStreamer(const Triple & T,MCContext & Context,MCAsmBackend & MAB,raw_pwrite_stream & OS,MCCodeEmitter * Emitter,bool RelaxAll)57*9880d681SAndroid Build Coastguard Worker static MCStreamer *createMCStreamer(const Triple &T, MCContext &Context,
58*9880d681SAndroid Build Coastguard Worker MCAsmBackend &MAB, raw_pwrite_stream &OS,
59*9880d681SAndroid Build Coastguard Worker MCCodeEmitter *Emitter, bool RelaxAll) {
60*9880d681SAndroid Build Coastguard Worker if (!T.isOSBinFormatELF())
61*9880d681SAndroid Build Coastguard Worker llvm_unreachable("OS not supported");
62*9880d681SAndroid Build Coastguard Worker
63*9880d681SAndroid Build Coastguard Worker return createELFStreamer(Context, MAB, OS, Emitter, RelaxAll);
64*9880d681SAndroid Build Coastguard Worker }
65*9880d681SAndroid Build Coastguard Worker
createLanaiMCInstPrinter(const Triple & T,unsigned SyntaxVariant,const MCAsmInfo & MAI,const MCInstrInfo & MII,const MCRegisterInfo & MRI)66*9880d681SAndroid Build Coastguard Worker static MCInstPrinter *createLanaiMCInstPrinter(const Triple &T,
67*9880d681SAndroid Build Coastguard Worker unsigned SyntaxVariant,
68*9880d681SAndroid Build Coastguard Worker const MCAsmInfo &MAI,
69*9880d681SAndroid Build Coastguard Worker const MCInstrInfo &MII,
70*9880d681SAndroid Build Coastguard Worker const MCRegisterInfo &MRI) {
71*9880d681SAndroid Build Coastguard Worker if (SyntaxVariant == 0)
72*9880d681SAndroid Build Coastguard Worker return new LanaiInstPrinter(MAI, MII, MRI);
73*9880d681SAndroid Build Coastguard Worker return 0;
74*9880d681SAndroid Build Coastguard Worker }
75*9880d681SAndroid Build Coastguard Worker
createLanaiElfRelocation(const Triple & TheTriple,MCContext & Ctx)76*9880d681SAndroid Build Coastguard Worker MCRelocationInfo *createLanaiElfRelocation(const Triple &TheTriple,
77*9880d681SAndroid Build Coastguard Worker MCContext &Ctx) {
78*9880d681SAndroid Build Coastguard Worker return createMCRelocationInfo(TheTriple, Ctx);
79*9880d681SAndroid Build Coastguard Worker }
80*9880d681SAndroid Build Coastguard Worker
81*9880d681SAndroid Build Coastguard Worker class LanaiMCInstrAnalysis : public MCInstrAnalysis {
82*9880d681SAndroid Build Coastguard Worker public:
LanaiMCInstrAnalysis(const MCInstrInfo * Info)83*9880d681SAndroid Build Coastguard Worker explicit LanaiMCInstrAnalysis(const MCInstrInfo *Info)
84*9880d681SAndroid Build Coastguard Worker : MCInstrAnalysis(Info) {}
85*9880d681SAndroid Build Coastguard Worker
evaluateBranch(const MCInst & Inst,uint64_t Addr,uint64_t Size,uint64_t & Target) const86*9880d681SAndroid Build Coastguard Worker bool evaluateBranch(const MCInst &Inst, uint64_t Addr, uint64_t Size,
87*9880d681SAndroid Build Coastguard Worker uint64_t &Target) const override {
88*9880d681SAndroid Build Coastguard Worker if (Inst.getNumOperands() == 0)
89*9880d681SAndroid Build Coastguard Worker return false;
90*9880d681SAndroid Build Coastguard Worker
91*9880d681SAndroid Build Coastguard Worker if (Info->get(Inst.getOpcode()).OpInfo[0].OperandType ==
92*9880d681SAndroid Build Coastguard Worker MCOI::OPERAND_PCREL) {
93*9880d681SAndroid Build Coastguard Worker int64_t Imm = Inst.getOperand(0).getImm();
94*9880d681SAndroid Build Coastguard Worker Target = Addr + Size + Imm;
95*9880d681SAndroid Build Coastguard Worker return true;
96*9880d681SAndroid Build Coastguard Worker } else {
97*9880d681SAndroid Build Coastguard Worker int64_t Imm = Inst.getOperand(0).getImm();
98*9880d681SAndroid Build Coastguard Worker
99*9880d681SAndroid Build Coastguard Worker // Skip case where immediate is 0 as that occurs in file that isn't linked
100*9880d681SAndroid Build Coastguard Worker // and the branch target inferred would be wrong.
101*9880d681SAndroid Build Coastguard Worker if (Imm == 0)
102*9880d681SAndroid Build Coastguard Worker return false;
103*9880d681SAndroid Build Coastguard Worker
104*9880d681SAndroid Build Coastguard Worker Target = Imm;
105*9880d681SAndroid Build Coastguard Worker return true;
106*9880d681SAndroid Build Coastguard Worker }
107*9880d681SAndroid Build Coastguard Worker }
108*9880d681SAndroid Build Coastguard Worker };
109*9880d681SAndroid Build Coastguard Worker
createLanaiInstrAnalysis(const MCInstrInfo * Info)110*9880d681SAndroid Build Coastguard Worker static MCInstrAnalysis *createLanaiInstrAnalysis(const MCInstrInfo *Info) {
111*9880d681SAndroid Build Coastguard Worker return new LanaiMCInstrAnalysis(Info);
112*9880d681SAndroid Build Coastguard Worker }
113*9880d681SAndroid Build Coastguard Worker
LLVMInitializeLanaiTargetMC()114*9880d681SAndroid Build Coastguard Worker extern "C" void LLVMInitializeLanaiTargetMC() {
115*9880d681SAndroid Build Coastguard Worker // Register the MC asm info.
116*9880d681SAndroid Build Coastguard Worker RegisterMCAsmInfo<LanaiMCAsmInfo> X(TheLanaiTarget);
117*9880d681SAndroid Build Coastguard Worker
118*9880d681SAndroid Build Coastguard Worker // Register the MC instruction info.
119*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCInstrInfo(TheLanaiTarget, createLanaiMCInstrInfo);
120*9880d681SAndroid Build Coastguard Worker
121*9880d681SAndroid Build Coastguard Worker // Register the MC register info.
122*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCRegInfo(TheLanaiTarget, createLanaiMCRegisterInfo);
123*9880d681SAndroid Build Coastguard Worker
124*9880d681SAndroid Build Coastguard Worker // Register the MC subtarget info.
125*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCSubtargetInfo(TheLanaiTarget,
126*9880d681SAndroid Build Coastguard Worker createLanaiMCSubtargetInfo);
127*9880d681SAndroid Build Coastguard Worker
128*9880d681SAndroid Build Coastguard Worker // Register the MC code emitter
129*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCCodeEmitter(TheLanaiTarget,
130*9880d681SAndroid Build Coastguard Worker llvm::createLanaiMCCodeEmitter);
131*9880d681SAndroid Build Coastguard Worker
132*9880d681SAndroid Build Coastguard Worker // Register the ASM Backend
133*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCAsmBackend(TheLanaiTarget, createLanaiAsmBackend);
134*9880d681SAndroid Build Coastguard Worker
135*9880d681SAndroid Build Coastguard Worker // Register the MCInstPrinter.
136*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCInstPrinter(TheLanaiTarget,
137*9880d681SAndroid Build Coastguard Worker createLanaiMCInstPrinter);
138*9880d681SAndroid Build Coastguard Worker
139*9880d681SAndroid Build Coastguard Worker // Register the ELF streamer.
140*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterELFStreamer(TheLanaiTarget, createMCStreamer);
141*9880d681SAndroid Build Coastguard Worker
142*9880d681SAndroid Build Coastguard Worker // Register the MC relocation info.
143*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCRelocationInfo(TheLanaiTarget,
144*9880d681SAndroid Build Coastguard Worker createLanaiElfRelocation);
145*9880d681SAndroid Build Coastguard Worker
146*9880d681SAndroid Build Coastguard Worker // Register the MC instruction analyzer.
147*9880d681SAndroid Build Coastguard Worker TargetRegistry::RegisterMCInstrAnalysis(TheLanaiTarget,
148*9880d681SAndroid Build Coastguard Worker createLanaiInstrAnalysis);
149*9880d681SAndroid Build Coastguard Worker }
150