Index: lib/Target/NDS32/CMakeLists.txt =================================================================== --- lib/Target/NDS32/CMakeLists.txt +++ lib/Target/NDS32/CMakeLists.txt @@ -2,6 +2,7 @@ tablegen(LLVM NDS32GenSubtargetInfo.inc -gen-subtarget) tablegen(LLVM NDS32GenRegisterInfo.inc -gen-register-info) +tablegen(LLVM NDS32GenInstrInfo.inc -gen-instr-info) add_public_tablegen_target(NDS32CommonTableGen) @@ -11,6 +12,7 @@ NDS32Subtarget.cpp NDS32FrameLowering.cpp NDS32RegisterInfo.cpp + NDS32InstrInfo.cpp ) add_subdirectory(TargetInfo) Index: lib/Target/NDS32/MCTargetDesc/NDS32MCTargetDesc.h =================================================================== --- lib/Target/NDS32/MCTargetDesc/NDS32MCTargetDesc.h +++ lib/Target/NDS32/MCTargetDesc/NDS32MCTargetDesc.h @@ -42,4 +42,8 @@ #define GET_REGINFO_ENUM #include "NDS32GenRegisterInfo.inc" +// Defines symbolic names for the NDS32 instructions. +#define GET_INSTRINFO_ENUM +#include "NDS32GenInstrInfo.inc" + #endif Index: lib/Target/NDS32/MCTargetDesc/NDS32MCTargetDesc.cpp =================================================================== --- lib/Target/NDS32/MCTargetDesc/NDS32MCTargetDesc.cpp +++ lib/Target/NDS32/MCTargetDesc/NDS32MCTargetDesc.cpp @@ -25,6 +25,9 @@ #define GET_REGINFO_MC_DESC #include "NDS32GenRegisterInfo.inc" +#define GET_INSTRINFO_MC_DESC +#include "NDS32GenInstrInfo.inc" + static MCSubtargetInfo * createNDS32MCSubtargetInfo(const Triple &TT, StringRef CPU, StringRef FS) { return createNDS32MCSubtargetInfoImpl(TT, CPU, FS); @@ -36,6 +39,12 @@ return X; } +static MCInstrInfo *createNDS32MCInstrInfo() { + MCInstrInfo *X = new MCInstrInfo(); + InitNDS32MCInstrInfo(X); + return X; +} + extern "C" void LLVMInitializeNDS32TargetMC() { // Register the MC subtarget info. TargetRegistry::RegisterMCSubtargetInfo(getTheNDS32Target(), @@ -44,4 +53,8 @@ // Register the MC register info. TargetRegistry::RegisterMCRegInfo(getTheNDS32Target(), createNDS32MCRegisterInfo); + + // Register the MC instruction info. + TargetRegistry::RegisterMCInstrInfo(getTheNDS32Target(), + createNDS32MCInstrInfo); } Index: lib/Target/NDS32/NDS32.td =================================================================== --- lib/Target/NDS32/NDS32.td +++ lib/Target/NDS32/NDS32.td @@ -22,10 +22,10 @@ def FeatureNo16Bit : SubtargetFeature<"no-16bit", "No16Bit", "true", "Disable generate 16-bit ISA">; - //===----------------------------------------------------------------------===// // NDS32 supported processors. //===----------------------------------------------------------------------===// + class Proc Features> : Processor; @@ -38,8 +38,17 @@ include "NDS32RegisterInfo.td" //===----------------------------------------------------------------------===// +// Instruction Descriptions +//===----------------------------------------------------------------------===// + +include "NDS32InstrInfo.td" + +def NDS32InstrInfo : InstrInfo; + +//===----------------------------------------------------------------------===// // Target Declaration //===----------------------------------------------------------------------===// def NDS32 : Target { + let InstructionSet = NDS32InstrInfo; } Index: lib/Target/NDS32/NDS32InstrFormats.td =================================================================== --- /dev/null +++ lib/Target/NDS32/NDS32InstrFormats.td @@ -0,0 +1,44 @@ +//===-- NDS32InstrFormats.td - NDS32 Instruction Formats -*- tablegen -*---===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +//===----------------------------------------------------------------------===// +// Describe NDS32 instructions format here +// + +// Generic NDS32 Format +class NDS32Inst : Instruction { + let Namespace = "NDS32"; + + dag OutOperandList = outs; + dag InOperandList = ins; + + let AsmString = asmstr; + + field bits<32> SoftFail = 0; +} + +class 32BitInst opcode, + dag outs, dag ins, string asmstr, list pattern> + : NDS32Inst { + field bits<32> Inst; + let Size = 4; + + let Pattern = pattern; + let Inst{31} = 0; + let Inst{30-25} = opcode; +} + +// Pseudo instructions +class Pseudo pattern> + : 32BitInst<0b110010, outs, ins, asmstr, pattern> { + let Inst{15-0} = 0; + let Pattern = pattern; + let isCodeGenOnly = 1; + let isPseudo = 1; +} Index: lib/Target/NDS32/NDS32InstrInfo.h =================================================================== --- /dev/null +++ lib/Target/NDS32/NDS32InstrInfo.h @@ -0,0 +1,84 @@ +//===-- NDS32InstrInfo.h - NDS32 Instruction Information ------*- C++ -*---===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file contains the NDS32 implementation of the TargetInstrInfo class. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_LIB_TARGET_NDS32_NDS32INSTRINFO_H +#define LLVM_LIB_TARGET_NDS32_NDS32INSTRINFO_H + +#include "NDS32RegisterInfo.h" +#include "llvm/Target/TargetInstrInfo.h" + +#define GET_INSTRINFO_HEADER +#include "NDS32GenInstrInfo.inc" + +namespace llvm { + +class NDS32Subtarget; + +class NDS32InstrInfo : public NDS32GenInstrInfo { + const NDS32Subtarget &Subtarget; + const NDS32RegisterInfo RI; + virtual void anchor(); +public: + explicit NDS32InstrInfo(NDS32Subtarget &STI); + + /// getRegisterInfo - TargetInstrInfo is a superset of MRegister info. As + /// such, whenever a client has an instance of instruction info, it should + /// always be able to get register info as well (through this method). + /// + const NDS32RegisterInfo &getRegisterInfo() const { return RI; } + + static const NDS32InstrInfo *create(NDS32Subtarget &STI); + + void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, + const DebugLoc &DL, unsigned DestReg, unsigned SrcReg, + bool KillSrc) const override; + + void storeRegToStackSlot(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MI, + unsigned SrcReg, bool isKill, + int FrameIndex, + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI) const override; + void loadRegFromStackSlot(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MI, + unsigned DestReg, int FrameIdx, + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI) const override; + + // Branch folding goodness + bool + reverseBranchCondition(SmallVectorImpl &Cond) const override; + bool analyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB, + MachineBasicBlock *&FBB, + SmallVectorImpl &Cond, + bool AllowModify) const override; + + unsigned removeBranch(MachineBasicBlock &MBB, + int *BytesRemoved = nullptr) const override; + + unsigned insertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, + MachineBasicBlock *FBB, ArrayRef Cond, + const DebugLoc &DL, + int *BytesAdded = nullptr) const override; + +protected: + MachineMemOperand *GetMemOperand(MachineBasicBlock &MBB, int FI, + MachineMemOperand::Flags Flags) const; + +private: +}; + +const NDS32InstrInfo *createNDS32InstrInfo(const NDS32Subtarget &STI); +} + +#endif Index: lib/Target/NDS32/NDS32InstrInfo.cpp =================================================================== --- /dev/null +++ lib/Target/NDS32/NDS32InstrInfo.cpp @@ -0,0 +1,96 @@ +//===-- NDS32InstrInfo.cpp - NDS32 Instruction Information ----------------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file contains the NDS32 implementation of the TargetInstrInfo class. +// +//===----------------------------------------------------------------------===// + +#include "NDS32InstrInfo.h" +#include "NDS32.h" +#include "NDS32TargetMachine.h" +#include "llvm/CodeGen/MachineFrameInfo.h" +#include "llvm/CodeGen/MachineInstrBuilder.h" +#include "llvm/CodeGen/MachineRegisterInfo.h" +#include "llvm/IR/Function.h" +#include "llvm/Support/ErrorHandling.h" +#include "llvm/Support/TargetRegistry.h" + +using namespace llvm; + +#define GET_INSTRINFO_CTOR_DTOR +#include "NDS32GenInstrInfo.inc" + +// Pin the vtable to this file. +void NDS32InstrInfo::anchor() {} + +NDS32InstrInfo::NDS32InstrInfo(NDS32Subtarget &STI) + : NDS32GenInstrInfo(NDS32::ADJCALLSTACKDOWN, NDS32::ADJCALLSTACKUP), + Subtarget(STI), + RI() {} + +const NDS32InstrInfo *NDS32InstrInfo::create(NDS32Subtarget &STI) { + return new NDS32InstrInfo(STI); +} + +void NDS32InstrInfo::storeRegToStackSlot(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MI, + unsigned SrcReg, bool isKill, int FI, + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI) const { +} + +void NDS32InstrInfo::loadRegFromStackSlot(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MI, + unsigned DestReg, int FI, + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI) const{ +} + +void NDS32InstrInfo::copyPhysReg(MachineBasicBlock &MBB, + MachineBasicBlock::iterator I, + const DebugLoc &DL, unsigned DestReg, + unsigned SrcReg, bool KillSrc) const { +} + +//===----------------------------------------------------------------------===// +// Branch Analysis +//===----------------------------------------------------------------------===// + +unsigned NDS32InstrInfo::insertBranch(MachineBasicBlock &MBB, + MachineBasicBlock *TBB, + MachineBasicBlock *FBB, + ArrayRef Cond, + const DebugLoc &DL, + int *BytesAdded) const { + // Shouldn't be a fall through. + assert(TBB && "InsertBranch must not be told to insert a fallthrough"); + return 0; +} + +// removeBranch will remove last branch or last two +// conditional and unconditional branches which let BranchFolding +// could do the right thing. +unsigned NDS32InstrInfo::removeBranch(MachineBasicBlock &MBB, + int *BytesRemoved) const { + return 0; +} + +bool NDS32InstrInfo:: +reverseBranchCondition(SmallVectorImpl &Cond) const { + + return true; +} + +bool NDS32InstrInfo::analyzeBranch(MachineBasicBlock &MBB, + MachineBasicBlock *&TBB, + MachineBasicBlock *&FBB, + SmallVectorImpl &Cond, + bool AllowModify) const { + return true; +} Index: lib/Target/NDS32/NDS32InstrInfo.td =================================================================== --- /dev/null +++ lib/Target/NDS32/NDS32InstrInfo.td @@ -0,0 +1,45 @@ +//===-- NDS32InstrInfo.td - NDS32 Instruction defs -------*- tablegen -*---===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file describes the NDS32 instructions in TableGen format. +// +//===----------------------------------------------------------------------===// + +include "NDS32InstrFormats.td" + +//===----------------------------------------------------------------------===// +// Type Profiles. +//===----------------------------------------------------------------------===// +def SDT_NDS32CallSeqStart : SDCallSeqStart<[SDTCisVT<0, i32>]>; +def SDT_NDS32CallSeqEnd : SDCallSeqEnd<[SDTCisVT<0, i32>, SDTCisVT<1, i32>]>; + +//===----------------------------------------------------------------------===// +// NDS32 Specific Node Definitions. +//===----------------------------------------------------------------------===// +def NDS32callseq_start : + SDNode<"ISD::CALLSEQ_START", SDT_NDS32CallSeqStart, + [SDNPHasChain, SDNPOutGlue]>; +def NDS32callseq_end : + SDNode<"ISD::CALLSEQ_END", SDT_NDS32CallSeqEnd, + [SDNPHasChain, SDNPOptInGlue, SDNPOutGlue]>; + +//===----------------------------------------------------------------------===// +// ADJCALLSTACKDOWN/UP implicitly use/def SP because they may be expanded into +// a stack adjustment and the codegen must know that they may modify the stack +// pointer before prolog-epilog rewriting occurs. +// Pessimistically assume ADJCALLSTACKDOWN / ADJCALLSTACKUP will become +// sub / add. +let Defs = [SP], Uses = [SP] in { +def ADJCALLSTACKDOWN : Pseudo<(outs), (ins i32imm:$amt), + "#ADJCALLSTACKDOWN", + [(NDS32callseq_start timm:$amt)]>; +def ADJCALLSTACKUP : Pseudo<(outs), (ins i32imm:$amt1, i32imm:$amt2), + "#ADJCALLSTACKUP", + [(NDS32callseq_end timm:$amt1, timm:$amt2)]>; +} Index: lib/Target/NDS32/NDS32Subtarget.h =================================================================== --- lib/Target/NDS32/NDS32Subtarget.h +++ lib/Target/NDS32/NDS32Subtarget.h @@ -15,6 +15,8 @@ #define LLVM_LIB_TARGET_NDS32_NDS32SUBTARGET_H #include "NDS32FrameLowering.h" +#include "NDS32InstrInfo.h" +#include "NDS32RegisterInfo.h" #include "llvm/IR/DataLayout.h" #include "llvm/Target/TargetSubtargetInfo.h" #include @@ -28,6 +30,7 @@ class NDS32Subtarget : public NDS32GenSubtargetInfo { virtual void anchor(); NDS32FrameLowering FrameLowering; + std::unique_ptr InstrInfo; public: /// This constructor initializes the data members to match that @@ -45,6 +48,11 @@ const TargetFrameLowering *getFrameLowering() const override { return &FrameLowering; } + const NDS32InstrInfo *getInstrInfo() const override { return InstrInfo.get(); } + const NDS32RegisterInfo *getRegisterInfo() const override { + return &InstrInfo->getRegisterInfo(); + } + protected: /// No16Bit - Not generate 16-Bit ISA bool No16Bit = false; Index: lib/Target/NDS32/NDS32Subtarget.cpp =================================================================== --- lib/Target/NDS32/NDS32Subtarget.cpp +++ lib/Target/NDS32/NDS32Subtarget.cpp @@ -33,6 +33,7 @@ NDS32Subtarget::NDS32Subtarget(const Triple &TT, const std::string &CPU, const std::string &FS, const TargetMachine &TM) - : NDS32GenSubtargetInfo(TT, CPU, FS), FrameLowering() { + : NDS32GenSubtargetInfo(TT, CPU, FS), FrameLowering(), + InstrInfo(NDS32InstrInfo::create(initializeSubtargetDependencies(CPU, FS))) { ParseSubtargetFeatures(CPU, FS); }