1 //===-- VEISelLowering.cpp - VE DAG Lowering Implementation ---------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file implements the interfaces that VE uses to lower LLVM code into a 10 // selection DAG. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "VEISelLowering.h" 15 #include "VERegisterInfo.h" 16 #include "VETargetMachine.h" 17 #include "llvm/ADT/StringSwitch.h" 18 #include "llvm/CodeGen/CallingConvLower.h" 19 #include "llvm/CodeGen/MachineFrameInfo.h" 20 #include "llvm/CodeGen/MachineFunction.h" 21 #include "llvm/CodeGen/MachineInstrBuilder.h" 22 #include "llvm/CodeGen/MachineModuleInfo.h" 23 #include "llvm/CodeGen/MachineRegisterInfo.h" 24 #include "llvm/CodeGen/SelectionDAG.h" 25 #include "llvm/CodeGen/TargetLoweringObjectFileImpl.h" 26 #include "llvm/IR/DerivedTypes.h" 27 #include "llvm/IR/Function.h" 28 #include "llvm/IR/Module.h" 29 #include "llvm/Support/ErrorHandling.h" 30 #include "llvm/Support/KnownBits.h" 31 using namespace llvm; 32 33 #define DEBUG_TYPE "ve-lower" 34 35 //===----------------------------------------------------------------------===// 36 // Calling Convention Implementation 37 //===----------------------------------------------------------------------===// 38 39 #include "VEGenCallingConv.inc" 40 41 bool VETargetLowering::CanLowerReturn( 42 CallingConv::ID CallConv, MachineFunction &MF, bool IsVarArg, 43 const SmallVectorImpl<ISD::OutputArg> &Outs, LLVMContext &Context) const { 44 assert(!IsVarArg && "TODO implement var args"); 45 assert(Outs.empty() && "TODO implement return values"); 46 return true; // TODO support more than 'ret void' 47 } 48 49 SDValue 50 VETargetLowering::LowerReturn(SDValue Chain, CallingConv::ID CallConv, 51 bool IsVarArg, 52 const SmallVectorImpl<ISD::OutputArg> &Outs, 53 const SmallVectorImpl<SDValue> &OutVals, 54 const SDLoc &DL, SelectionDAG &DAG) const { 55 assert(!IsVarArg && "TODO implement var args"); 56 assert(Outs.empty() && "TODO implement return values"); 57 assert(OutVals.empty() && "TODO implement return values"); 58 59 SmallVector<SDValue, 4> RetOps(1, Chain); 60 RetOps[0] = Chain; // Update chain. 61 return DAG.getNode(VEISD::RET_FLAG, DL, MVT::Other, RetOps); 62 } 63 64 SDValue VETargetLowering::LowerFormalArguments( 65 SDValue Chain, CallingConv::ID CallConv, bool IsVarArg, 66 const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &DL, 67 SelectionDAG &DAG, SmallVectorImpl<SDValue> &InVals) const { 68 assert(!IsVarArg && "TODO implement var args"); 69 assert(Ins.empty() && "TODO implement input arguments"); 70 return Chain; 71 } 72 73 // FIXME? Maybe this could be a TableGen attribute on some registers and 74 // this table could be generated automatically from RegInfo. 75 Register VETargetLowering::getRegisterByName(const char *RegName, LLT VT, 76 const MachineFunction &MF) const { 77 Register Reg = StringSwitch<Register>(RegName) 78 .Case("sp", VE::SX11) // Stack pointer 79 .Case("fp", VE::SX9) // Frame pointer 80 .Case("sl", VE::SX8) // Stack limit 81 .Case("lr", VE::SX10) // Link regsiter 82 .Case("tp", VE::SX14) // Thread pointer 83 .Case("outer", VE::SX12) // Outer regiser 84 .Case("info", VE::SX17) // Info area register 85 .Case("got", VE::SX15) // Global offset table register 86 .Case("plt", VE::SX16) // Procedure linkage table register 87 .Default(0); 88 89 if (Reg) 90 return Reg; 91 92 report_fatal_error("Invalid register name global variable"); 93 } 94 95 //===----------------------------------------------------------------------===// 96 // TargetLowering Implementation 97 //===----------------------------------------------------------------------===// 98 99 VETargetLowering::VETargetLowering(const TargetMachine &TM, 100 const VESubtarget &STI) 101 : TargetLowering(TM), Subtarget(&STI) { 102 // Instructions which use registers as conditionals examine all the 103 // bits (as does the pseudo SELECT_CC expansion). I don't think it 104 // matters much whether it's ZeroOrOneBooleanContent, or 105 // ZeroOrNegativeOneBooleanContent, so, arbitrarily choose the 106 // former. 107 setBooleanContents(ZeroOrOneBooleanContent); 108 setBooleanVectorContents(ZeroOrOneBooleanContent); 109 110 // Set up the register classes. 111 addRegisterClass(MVT::i64, &VE::I64RegClass); 112 113 setStackPointerRegisterToSaveRestore(VE::SX11); 114 115 // Set function alignment to 16 bytes 116 setMinFunctionAlignment(Align(16)); 117 118 // VE stores all argument by 8 bytes alignment 119 setMinStackArgumentAlignment(Align(8)); 120 121 computeRegisterProperties(Subtarget->getRegisterInfo()); 122 } 123 124 const char *VETargetLowering::getTargetNodeName(unsigned Opcode) const { 125 switch ((VEISD::NodeType)Opcode) { 126 case VEISD::FIRST_NUMBER: 127 break; 128 case VEISD::RET_FLAG: 129 return "VEISD::RET_FLAG"; 130 } 131 return nullptr; 132 } 133 134 EVT VETargetLowering::getSetCCResultType(const DataLayout &, LLVMContext &, 135 EVT VT) const { 136 return MVT::i64; 137 } 138