diff --git a/llvm/lib/Target/CSKY/CSKYAsmPrinter.cpp b/llvm/lib/Target/CSKY/CSKYAsmPrinter.cpp index ea5b4555757e..24a4212de27a 100644 --- a/llvm/lib/Target/CSKY/CSKYAsmPrinter.cpp +++ b/llvm/lib/Target/CSKY/CSKYAsmPrinter.cpp @@ -208,6 +208,9 @@ void CSKYAsmPrinter::emitMachineConstantPoolValue( } else if (CCPV->isJT()) { signed JTI = cast(CCPV)->getJTI(); MCSym = GetJTISymbol(JTI); + } else if (CCPV->isConstPool()) { + const Constant *C = cast(CCPV)->getConstantPool(); + MCSym = GetCPISymbol(MCP->getConstantPoolIndex(C, Align(4))); } else { assert(CCPV->isExtSymbol() && "unrecognized constant pool value"); StringRef Sym = cast(CCPV)->getSymbol(); diff --git a/llvm/lib/Target/CSKY/CSKYConstantIslandPass.cpp b/llvm/lib/Target/CSKY/CSKYConstantIslandPass.cpp index 5d7241258543..4acdd571f6c9 100644 --- a/llvm/lib/Target/CSKY/CSKYConstantIslandPass.cpp +++ b/llvm/lib/Target/CSKY/CSKYConstantIslandPass.cpp @@ -573,10 +573,6 @@ void CSKYConstantIslands::initializeFunctionInfo( CPEntry *CPE = findConstPoolEntry(CPI, CPEMI); assert(CPE && "Cannot find a corresponding CPEntry!"); CPE->RefCount++; - - // Instructions can only use one CP entry, don't bother scanning the - // rest of the operands. - break; } } } diff --git a/llvm/lib/Target/CSKY/CSKYConstantPoolValue.cpp b/llvm/lib/Target/CSKY/CSKYConstantPoolValue.cpp index d4c4bb847237..7998f4c6de9c 100644 --- a/llvm/lib/Target/CSKY/CSKYConstantPoolValue.cpp +++ b/llvm/lib/Target/CSKY/CSKYConstantPoolValue.cpp @@ -77,16 +77,23 @@ void CSKYConstantPoolValue::print(raw_ostream &O) const { //===----------------------------------------------------------------------===// CSKYConstantPoolConstant::CSKYConstantPoolConstant( - const Constant *C, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust, + const Constant *C, Type *Ty, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust, CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress, unsigned ID) - : CSKYConstantPoolValue(C->getType(), Kind, PCAdjust, Modifier, - AddCurrentAddress, ID), + : CSKYConstantPoolValue(Ty, Kind, PCAdjust, Modifier, AddCurrentAddress, + ID), CVal(C) {} CSKYConstantPoolConstant *CSKYConstantPoolConstant::Create( const Constant *C, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust, CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress, unsigned ID) { - return new CSKYConstantPoolConstant(C, Kind, PCAdjust, Modifier, + return new CSKYConstantPoolConstant(C, C->getType(), Kind, PCAdjust, Modifier, + AddCurrentAddress, ID); +} + +CSKYConstantPoolConstant *CSKYConstantPoolConstant::Create( + const Constant *C, Type *Ty, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust, + CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress, unsigned ID) { + return new CSKYConstantPoolConstant(C, Ty, Kind, PCAdjust, Modifier, AddCurrentAddress, ID); } @@ -100,6 +107,10 @@ const BlockAddress *CSKYConstantPoolConstant::getBlockAddress() const { return cast(CVal); } +const Constant *CSKYConstantPoolConstant::getConstantPool() const { + return CVal; +} + int CSKYConstantPoolConstant::getExistingMachineCPValue(MachineConstantPool *CP, Align Alignment) { return getExistingMachineCPValueImpl(CP, Alignment); diff --git a/llvm/lib/Target/CSKY/CSKYConstantPoolValue.h b/llvm/lib/Target/CSKY/CSKYConstantPoolValue.h index 2eff9404a34c..e36454139d43 100644 --- a/llvm/lib/Target/CSKY/CSKYConstantPoolValue.h +++ b/llvm/lib/Target/CSKY/CSKYConstantPoolValue.h @@ -33,7 +33,8 @@ enum CSKYCPKind { CPExtSymbol, CPBlockAddress, CPMachineBasicBlock, - CPJT + CPJT, + CPConstPool }; enum CSKYCPModifier { NO_MOD, ADDR, GOT, GOTOFF, PLT, TLSLE, TLSIE, TLSGD }; @@ -69,6 +70,7 @@ public: return Kind == CSKYCP::CPMachineBasicBlock; } bool isJT() const { return Kind == CSKYCP::CPJT; } + bool isConstPool() const { return Kind == CSKYCP::CPConstPool; } int getExistingMachineCPValue(MachineConstantPool *CP, Align Alignment) override; @@ -105,7 +107,7 @@ public: class CSKYConstantPoolConstant : public CSKYConstantPoolValue { const Constant *CVal; // Constant being loaded. - CSKYConstantPoolConstant(const Constant *C, CSKYCP::CSKYCPKind Kind, + CSKYConstantPoolConstant(const Constant *C, Type *Ty, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust, CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress, unsigned ID); @@ -114,8 +116,13 @@ public: Create(const Constant *C, CSKYCP::CSKYCPKind Kind, unsigned PCAdjust, CSKYCP::CSKYCPModifier Modifier, bool AddCurrentAddress, unsigned ID = 0); + static CSKYConstantPoolConstant * + Create(const Constant *C, Type *Ty, CSKYCP::CSKYCPKind Kind, + unsigned PCAdjust, CSKYCP::CSKYCPModifier Modifier, + bool AddCurrentAddress, unsigned ID = 0); const GlobalValue *getGV() const; const BlockAddress *getBlockAddress() const; + const Constant *getConstantPool() const; int getExistingMachineCPValue(MachineConstantPool *CP, Align Alignment) override; @@ -127,7 +134,7 @@ public: } static bool classof(const CSKYConstantPoolValue *APV) { - return APV->isGlobalValue() || APV->isBlockAddress(); + return APV->isGlobalValue() || APV->isBlockAddress() || APV->isConstPool(); } }; diff --git a/llvm/lib/Target/CSKY/CSKYISelLowering.cpp b/llvm/lib/Target/CSKY/CSKYISelLowering.cpp index eaf64c563178..e83b90e46e84 100644 --- a/llvm/lib/Target/CSKY/CSKYISelLowering.cpp +++ b/llvm/lib/Target/CSKY/CSKYISelLowering.cpp @@ -87,6 +87,9 @@ CSKYTargetLowering::CSKYTargetLowering(const TargetMachine &TM, setOperationAction(ISD::ExternalSymbol, MVT::i32, Custom); setOperationAction(ISD::GlobalTLSAddress, MVT::i32, Custom); setOperationAction(ISD::BlockAddress, MVT::i32, Custom); + if (!Subtarget.hasE2()) { + setOperationAction(ISD::ConstantPool, MVT::i32, Custom); + } setOperationAction(ISD::JumpTable, MVT::i32, Custom); setOperationAction(ISD::VASTART, MVT::Other, Custom); @@ -170,6 +173,8 @@ SDValue CSKYTargetLowering::LowerOperation(SDValue Op, return LowerJumpTable(Op, DAG); case ISD::BlockAddress: return LowerBlockAddress(Op, DAG); + case ISD::ConstantPool: + return LowerConstantPool(Op, DAG); case ISD::VASTART: return LowerVASTART(Op, DAG); case ISD::FRAMEADDR: @@ -1058,12 +1063,24 @@ SDValue CSKYTargetLowering::getTargetConstantPoolValue(BlockAddressSDNode *N, EVT Ty, SelectionDAG &DAG, unsigned Flags) const { + assert(N->getOffset() == 0); CSKYConstantPoolValue *CPV = CSKYConstantPoolConstant::Create( N->getBlockAddress(), CSKYCP::CPBlockAddress, 0, getModifier(Flags), false); return DAG.getTargetConstantPool(CPV, Ty); } +SDValue CSKYTargetLowering::getTargetConstantPoolValue(ConstantPoolSDNode *N, + EVT Ty, + SelectionDAG &DAG, + unsigned Flags) const { + assert(N->getOffset() == 0); + CSKYConstantPoolValue *CPV = CSKYConstantPoolConstant::Create( + N->getConstVal(), Type::getInt32Ty(*DAG.getContext()), + CSKYCP::CPConstPool, 0, getModifier(Flags), false); + return DAG.getTargetConstantPool(CPV, Ty); +} + SDValue CSKYTargetLowering::getTargetNode(GlobalAddressSDNode *N, SDLoc DL, EVT Ty, SelectionDAG &DAG, unsigned Flags) const { @@ -1089,6 +1106,14 @@ SDValue CSKYTargetLowering::getTargetNode(BlockAddressSDNode *N, SDLoc DL, Flags); } +SDValue CSKYTargetLowering::getTargetNode(ConstantPoolSDNode *N, SDLoc DL, + EVT Ty, SelectionDAG &DAG, + unsigned Flags) const { + + return DAG.getTargetConstantPool(N->getConstVal(), Ty, N->getAlign(), + N->getOffset(), Flags); +} + const char *CSKYTargetLowering::getTargetNodeName(unsigned Opcode) const { switch (Opcode) { default: @@ -1158,6 +1183,14 @@ SDValue CSKYTargetLowering::LowerBlockAddress(SDValue Op, return getAddr(N, DAG); } +SDValue CSKYTargetLowering::LowerConstantPool(SDValue Op, + SelectionDAG &DAG) const { + assert(!Subtarget.hasE2()); + ConstantPoolSDNode *N = cast(Op); + + return getAddr(N, DAG); +} + SDValue CSKYTargetLowering::LowerVASTART(SDValue Op, SelectionDAG &DAG) const { MachineFunction &MF = DAG.getMachineFunction(); CSKYMachineFunctionInfo *FuncInfo = MF.getInfo(); diff --git a/llvm/lib/Target/CSKY/CSKYISelLowering.h b/llvm/lib/Target/CSKY/CSKYISelLowering.h index 1cd0f99b17bc..d0abc7e9a7e4 100644 --- a/llvm/lib/Target/CSKY/CSKYISelLowering.h +++ b/llvm/lib/Target/CSKY/CSKYISelLowering.h @@ -110,6 +110,9 @@ private: SDValue getTargetNode(BlockAddressSDNode *N, SDLoc DL, EVT Ty, SelectionDAG &DAG, unsigned Flags) const; + SDValue getTargetNode(ConstantPoolSDNode *N, SDLoc DL, EVT Ty, + SelectionDAG &DAG, unsigned Flags) const; + SDValue getTargetConstantPoolValue(GlobalAddressSDNode *N, EVT Ty, SelectionDAG &DAG, unsigned Flags) const; @@ -122,6 +125,9 @@ private: SDValue getTargetConstantPoolValue(BlockAddressSDNode *N, EVT Ty, SelectionDAG &DAG, unsigned Flags) const; + SDValue getTargetConstantPoolValue(ConstantPoolSDNode *N, EVT Ty, + SelectionDAG &DAG, unsigned Flags) const; + template SDValue getAddr(NodeTy *N, SelectionDAG &DAG, bool IsLocal = true) const { SDLoc DL(N); @@ -155,6 +161,7 @@ private: SDValue LowerExternalSymbol(SDValue Op, SelectionDAG &DAG) const; SDValue LowerGlobalTLSAddress(SDValue Op, SelectionDAG &DAG) const; SDValue LowerBlockAddress(SDValue Op, SelectionDAG &DAG) const; + SDValue LowerConstantPool(SDValue Op, SelectionDAG &DAG) const; SDValue LowerJumpTable(SDValue Op, SelectionDAG &DAG) const; SDValue LowerVASTART(SDValue Op, SelectionDAG &DAG) const; SDValue LowerFRAMEADDR(SDValue Op, SelectionDAG &DAG) const; diff --git a/llvm/lib/Target/CSKY/CSKYInstrInfo.td b/llvm/lib/Target/CSKY/CSKYInstrInfo.td index b5720cde79ad..b99dbf08f112 100644 --- a/llvm/lib/Target/CSKY/CSKYInstrInfo.td +++ b/llvm/lib/Target/CSKY/CSKYInstrInfo.td @@ -1117,6 +1117,7 @@ def : Pat<(CSKY_LOAD_ADDR tglobaladdr, tconstpool:$src2), (LRW32 tconstpool:$src def : Pat<(CSKY_LOAD_ADDR tblockaddress, tconstpool:$src2), (LRW32 tconstpool:$src2)>; def : Pat<(CSKY_LOAD_ADDR tjumptable:$src1, tconstpool:$src2), (LRW32_Gen tjumptable:$src1, tconstpool:$src2)>; def : Pat<(CSKY_LOAD_ADDR texternalsym, tconstpool:$src2), (LRW32 tconstpool:$src2)>; +def : Pat<(CSKY_LOAD_ADDR tconstpool:$src1, tconstpool:$src2), (LRW32_Gen tconstpool:$src1, tconstpool:$src2)>; let Predicates = [iHas2E3] in def : Pat<(i32 constpool:$src), (GRS32 (to_tconstpool tconstpool:$src))>; diff --git a/llvm/lib/Target/CSKY/CSKYInstrInfo16Instr.td b/llvm/lib/Target/CSKY/CSKYInstrInfo16Instr.td index 2d7fb85e89fa..86719d36d23e 100644 --- a/llvm/lib/Target/CSKY/CSKYInstrInfo16Instr.td +++ b/llvm/lib/Target/CSKY/CSKYInstrInfo16Instr.td @@ -472,6 +472,7 @@ def : Pat<(CSKY_LOAD_ADDR tglobaladdr, tconstpool:$src2), (LRW16 tconstpool:$src def : Pat<(CSKY_LOAD_ADDR tblockaddress, tconstpool:$src2), (LRW16 tconstpool:$src2)>; def : Pat<(CSKY_LOAD_ADDR tjumptable:$src1, tconstpool:$src2), (LRW16_Gen tjumptable:$src1, tconstpool:$src2)>; def : Pat<(CSKY_LOAD_ADDR texternalsym, tconstpool:$src2), (LRW16 tconstpool:$src2)>; +def : Pat<(CSKY_LOAD_ADDR tconstpool:$src1, tconstpool:$src2), (LRW16_Gen tconstpool:$src1, tconstpool:$src2)>; def : Pat<(i32 (load constpool:$src)), (LRW16 (to_tconstpool tconstpool:$src))>; diff --git a/llvm/test/CodeGen/CSKY/constantpool.ll b/llvm/test/CodeGen/CSKY/constantpool.ll new file mode 100644 index 000000000000..d7741f2e1a1b --- /dev/null +++ b/llvm/test/CodeGen/CSKY/constantpool.ll @@ -0,0 +1,44 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; Test get the address of constant pool without grs instruction +; RUN: llc -verify-machineinstrs -csky-no-aliases < %s -mtriple=csky | FileCheck %s --check-prefix=GENERIC + +declare i32 @llvm.cttz.i32(i32, i1) + +define void @cttztest(i32 %C, i32* %CP) { +; GENERIC-LABEL: cttztest: +; GENERIC: # %bb.0: +; GENERIC-NEXT: .cfi_def_cfa_offset 0 +; GENERIC-NEXT: subi16 sp, sp, 4 +; GENERIC-NEXT: .cfi_def_cfa_offset 4 +; GENERIC-NEXT: movi16 a2, 0 +; GENERIC-NEXT: subu16 a2, a2, a0 +; GENERIC-NEXT: and16 a2, a0 +; GENERIC-NEXT: movi16 a0, 7 +; GENERIC-NEXT: lsli16 a0, a0, 24 +; GENERIC-NEXT: movi16 a3, 124 +; GENERIC-NEXT: lsli16 a3, a3, 16 +; GENERIC-NEXT: or16 a3, a0 +; GENERIC-NEXT: movi16 a0, 181 +; GENERIC-NEXT: lsli16 a0, a0, 8 +; GENERIC-NEXT: or16 a0, a3 +; GENERIC-NEXT: movi16 a3, 49 +; GENERIC-NEXT: or16 a3, a0 +; GENERIC-NEXT: mult16 a3, a2 +; GENERIC-NEXT: lsri16 a0, a3, 27 +; GENERIC-NEXT: lrw32 a2, [.LCPI0_1] +; GENERIC-NEXT: addu16 a0, a2, a0 +; GENERIC-NEXT: ld16.b a0, (a0, 0) +; GENERIC-NEXT: st16.w a0, (a1, 0) +; GENERIC-NEXT: addi16 sp, sp, 4 +; GENERIC-NEXT: rts16 +; GENERIC-NEXT: .p2align 1 +; GENERIC-NEXT: # %bb.1: +; GENERIC-NEXT: .p2align 2, 0x0 +; GENERIC-NEXT: .LCPI0_1: +; GENERIC-NEXT: .long .LCPI0_0 +; GENERIC-NEXT: .LCPI0_0: +; GENERIC-NEXT: .ascii "\000\001\034\002\035\016\030\003\036\026\024\017\031\021\004\b\037\033\r\027\025\023\020\007\032\f\022\006\013\005\n\t" + %c = call i32 @llvm.cttz.i32( i32 %C, i1 true ) + store i32 %c, i32* %CP + ret void +}