1064859bdSKazushi (Jam) Marukawa //===-- VEInstrInfo.cpp - VE Instruction Information ----------------------===// 2064859bdSKazushi (Jam) Marukawa // 3064859bdSKazushi (Jam) Marukawa // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4064859bdSKazushi (Jam) Marukawa // See https://llvm.org/LICENSE.txt for license information. 5064859bdSKazushi (Jam) Marukawa // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6064859bdSKazushi (Jam) Marukawa // 7064859bdSKazushi (Jam) Marukawa //===----------------------------------------------------------------------===// 8064859bdSKazushi (Jam) Marukawa // 9064859bdSKazushi (Jam) Marukawa // This file contains the VE implementation of the TargetInstrInfo class. 10064859bdSKazushi (Jam) Marukawa // 11064859bdSKazushi (Jam) Marukawa //===----------------------------------------------------------------------===// 12064859bdSKazushi (Jam) Marukawa 13064859bdSKazushi (Jam) Marukawa #include "VEInstrInfo.h" 14064859bdSKazushi (Jam) Marukawa #include "VE.h" 1560431bd7SKazushi (Jam) Marukawa #include "VEMachineFunctionInfo.h" 16064859bdSKazushi (Jam) Marukawa #include "VESubtarget.h" 17064859bdSKazushi (Jam) Marukawa #include "llvm/ADT/STLExtras.h" 18064859bdSKazushi (Jam) Marukawa #include "llvm/ADT/SmallVector.h" 19064859bdSKazushi (Jam) Marukawa #include "llvm/CodeGen/MachineFrameInfo.h" 20064859bdSKazushi (Jam) Marukawa #include "llvm/CodeGen/MachineInstrBuilder.h" 21064859bdSKazushi (Jam) Marukawa #include "llvm/CodeGen/MachineMemOperand.h" 22064859bdSKazushi (Jam) Marukawa #include "llvm/CodeGen/MachineRegisterInfo.h" 23064859bdSKazushi (Jam) Marukawa #include "llvm/Support/CommandLine.h" 24064859bdSKazushi (Jam) Marukawa #include "llvm/Support/Debug.h" 25064859bdSKazushi (Jam) Marukawa #include "llvm/Support/ErrorHandling.h" 26064859bdSKazushi (Jam) Marukawa #include "llvm/Support/TargetRegistry.h" 27064859bdSKazushi (Jam) Marukawa 28dedaf3a2SKazushi (Jam) Marukawa #define DEBUG_TYPE "ve-instr-info" 29064859bdSKazushi (Jam) Marukawa 30064859bdSKazushi (Jam) Marukawa using namespace llvm; 31064859bdSKazushi (Jam) Marukawa 32064859bdSKazushi (Jam) Marukawa #define GET_INSTRINFO_CTOR_DTOR 33064859bdSKazushi (Jam) Marukawa #include "VEGenInstrInfo.inc" 34064859bdSKazushi (Jam) Marukawa 35064859bdSKazushi (Jam) Marukawa // Pin the vtable to this file. 36064859bdSKazushi (Jam) Marukawa void VEInstrInfo::anchor() {} 37064859bdSKazushi (Jam) Marukawa 38064859bdSKazushi (Jam) Marukawa VEInstrInfo::VEInstrInfo(VESubtarget &ST) 39df4cc35eSFangrui Song : VEGenInstrInfo(VE::ADJCALLSTACKDOWN, VE::ADJCALLSTACKUP), RI() {} 40064859bdSKazushi (Jam) Marukawa 41fef80a29SKazushi (Jam) Marukawa static bool IsIntegerCC(unsigned CC) { return (CC < VECC::CC_AF); } 42fef80a29SKazushi (Jam) Marukawa 4328a42dd1SKazushi (Jam) Marukawa static VECC::CondCode GetOppositeBranchCondition(VECC::CondCode CC) { 44fef80a29SKazushi (Jam) Marukawa switch (CC) { 45117c0d7cSKazushi (Jam) Marukawa case VECC::CC_IG: 46117c0d7cSKazushi (Jam) Marukawa return VECC::CC_ILE; 47117c0d7cSKazushi (Jam) Marukawa case VECC::CC_IL: 48117c0d7cSKazushi (Jam) Marukawa return VECC::CC_IGE; 49117c0d7cSKazushi (Jam) Marukawa case VECC::CC_INE: 50117c0d7cSKazushi (Jam) Marukawa return VECC::CC_IEQ; 51117c0d7cSKazushi (Jam) Marukawa case VECC::CC_IEQ: 52117c0d7cSKazushi (Jam) Marukawa return VECC::CC_INE; 53117c0d7cSKazushi (Jam) Marukawa case VECC::CC_IGE: 54117c0d7cSKazushi (Jam) Marukawa return VECC::CC_IL; 55117c0d7cSKazushi (Jam) Marukawa case VECC::CC_ILE: 56117c0d7cSKazushi (Jam) Marukawa return VECC::CC_IG; 57117c0d7cSKazushi (Jam) Marukawa case VECC::CC_AF: 58117c0d7cSKazushi (Jam) Marukawa return VECC::CC_AT; 59117c0d7cSKazushi (Jam) Marukawa case VECC::CC_G: 60117c0d7cSKazushi (Jam) Marukawa return VECC::CC_LENAN; 61117c0d7cSKazushi (Jam) Marukawa case VECC::CC_L: 62117c0d7cSKazushi (Jam) Marukawa return VECC::CC_GENAN; 63117c0d7cSKazushi (Jam) Marukawa case VECC::CC_NE: 64117c0d7cSKazushi (Jam) Marukawa return VECC::CC_EQNAN; 65117c0d7cSKazushi (Jam) Marukawa case VECC::CC_EQ: 66117c0d7cSKazushi (Jam) Marukawa return VECC::CC_NENAN; 67117c0d7cSKazushi (Jam) Marukawa case VECC::CC_GE: 68117c0d7cSKazushi (Jam) Marukawa return VECC::CC_LNAN; 69117c0d7cSKazushi (Jam) Marukawa case VECC::CC_LE: 70117c0d7cSKazushi (Jam) Marukawa return VECC::CC_GNAN; 71117c0d7cSKazushi (Jam) Marukawa case VECC::CC_NUM: 72117c0d7cSKazushi (Jam) Marukawa return VECC::CC_NAN; 73117c0d7cSKazushi (Jam) Marukawa case VECC::CC_NAN: 74117c0d7cSKazushi (Jam) Marukawa return VECC::CC_NUM; 75117c0d7cSKazushi (Jam) Marukawa case VECC::CC_GNAN: 76117c0d7cSKazushi (Jam) Marukawa return VECC::CC_LE; 77117c0d7cSKazushi (Jam) Marukawa case VECC::CC_LNAN: 78117c0d7cSKazushi (Jam) Marukawa return VECC::CC_GE; 79117c0d7cSKazushi (Jam) Marukawa case VECC::CC_NENAN: 80117c0d7cSKazushi (Jam) Marukawa return VECC::CC_EQ; 81117c0d7cSKazushi (Jam) Marukawa case VECC::CC_EQNAN: 82117c0d7cSKazushi (Jam) Marukawa return VECC::CC_NE; 83117c0d7cSKazushi (Jam) Marukawa case VECC::CC_GENAN: 84117c0d7cSKazushi (Jam) Marukawa return VECC::CC_L; 85117c0d7cSKazushi (Jam) Marukawa case VECC::CC_LENAN: 86117c0d7cSKazushi (Jam) Marukawa return VECC::CC_G; 87117c0d7cSKazushi (Jam) Marukawa case VECC::CC_AT: 88117c0d7cSKazushi (Jam) Marukawa return VECC::CC_AF; 89117c0d7cSKazushi (Jam) Marukawa case VECC::UNKNOWN: 90117c0d7cSKazushi (Jam) Marukawa return VECC::UNKNOWN; 91fef80a29SKazushi (Jam) Marukawa } 92fef80a29SKazushi (Jam) Marukawa llvm_unreachable("Invalid cond code"); 93fef80a29SKazushi (Jam) Marukawa } 94fef80a29SKazushi (Jam) Marukawa 953c80478dSKazushi (Jam) Marukawa // Treat br.l [BRCF AT] as unconditional branch 96fef80a29SKazushi (Jam) Marukawa static bool isUncondBranchOpcode(int Opc) { 973c80478dSKazushi (Jam) Marukawa return Opc == VE::BRCFLa || Opc == VE::BRCFWa || 983c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFLa_nt || Opc == VE::BRCFWa_nt || 993c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFLa_t || Opc == VE::BRCFWa_t || 1003c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFDa || Opc == VE::BRCFSa || 1013c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFDa_nt || Opc == VE::BRCFSa_nt || 1023c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFDa_t || Opc == VE::BRCFSa_t; 103fef80a29SKazushi (Jam) Marukawa } 104fef80a29SKazushi (Jam) Marukawa 105fef80a29SKazushi (Jam) Marukawa static bool isCondBranchOpcode(int Opc) { 1063c80478dSKazushi (Jam) Marukawa return Opc == VE::BRCFLrr || Opc == VE::BRCFLir || 1073c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFLrr_nt || Opc == VE::BRCFLir_nt || 1083c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFLrr_t || Opc == VE::BRCFLir_t || 1093c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFWrr || Opc == VE::BRCFWir || 1103c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFWrr_nt || Opc == VE::BRCFWir_nt || 1113c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFWrr_t || Opc == VE::BRCFWir_t || 1123c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFDrr || Opc == VE::BRCFDir || 1133c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFDrr_nt || Opc == VE::BRCFDir_nt || 1143c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFDrr_t || Opc == VE::BRCFDir_t || 1153c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFSrr || Opc == VE::BRCFSir || 1163c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFSrr_nt || Opc == VE::BRCFSir_nt || 1173c80478dSKazushi (Jam) Marukawa Opc == VE::BRCFSrr_t || Opc == VE::BRCFSir_t; 1183c80478dSKazushi (Jam) Marukawa } 1193c80478dSKazushi (Jam) Marukawa 1203c80478dSKazushi (Jam) Marukawa static bool isIndirectBranchOpcode(int Opc) { 1213c80478dSKazushi (Jam) Marukawa return Opc == VE::BCFLari || Opc == VE::BCFLari || 1223c80478dSKazushi (Jam) Marukawa Opc == VE::BCFLari_nt || Opc == VE::BCFLari_nt || 1233c80478dSKazushi (Jam) Marukawa Opc == VE::BCFLari_t || Opc == VE::BCFLari_t || 1243c80478dSKazushi (Jam) Marukawa Opc == VE::BCFLari || Opc == VE::BCFLari || 1253c80478dSKazushi (Jam) Marukawa Opc == VE::BCFLari_nt || Opc == VE::BCFLari_nt || 1263c80478dSKazushi (Jam) Marukawa Opc == VE::BCFLari_t || Opc == VE::BCFLari_t; 127fef80a29SKazushi (Jam) Marukawa } 128fef80a29SKazushi (Jam) Marukawa 129fef80a29SKazushi (Jam) Marukawa static void parseCondBranch(MachineInstr *LastInst, MachineBasicBlock *&Target, 130fef80a29SKazushi (Jam) Marukawa SmallVectorImpl<MachineOperand> &Cond) { 131fef80a29SKazushi (Jam) Marukawa Cond.push_back(MachineOperand::CreateImm(LastInst->getOperand(0).getImm())); 132fef80a29SKazushi (Jam) Marukawa Cond.push_back(LastInst->getOperand(1)); 133fef80a29SKazushi (Jam) Marukawa Cond.push_back(LastInst->getOperand(2)); 134fef80a29SKazushi (Jam) Marukawa Target = LastInst->getOperand(3).getMBB(); 135fef80a29SKazushi (Jam) Marukawa } 136fef80a29SKazushi (Jam) Marukawa 13724215fecSSimon Moll bool VEInstrInfo::analyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB, 138fef80a29SKazushi (Jam) Marukawa MachineBasicBlock *&FBB, 139fef80a29SKazushi (Jam) Marukawa SmallVectorImpl<MachineOperand> &Cond, 140fef80a29SKazushi (Jam) Marukawa bool AllowModify) const { 141fef80a29SKazushi (Jam) Marukawa MachineBasicBlock::iterator I = MBB.getLastNonDebugInstr(); 142fef80a29SKazushi (Jam) Marukawa if (I == MBB.end()) 143fef80a29SKazushi (Jam) Marukawa return false; 144fef80a29SKazushi (Jam) Marukawa 145fef80a29SKazushi (Jam) Marukawa if (!isUnpredicatedTerminator(*I)) 146fef80a29SKazushi (Jam) Marukawa return false; 147fef80a29SKazushi (Jam) Marukawa 148fef80a29SKazushi (Jam) Marukawa // Get the last instruction in the block. 149fef80a29SKazushi (Jam) Marukawa MachineInstr *LastInst = &*I; 150fef80a29SKazushi (Jam) Marukawa unsigned LastOpc = LastInst->getOpcode(); 151fef80a29SKazushi (Jam) Marukawa 152fef80a29SKazushi (Jam) Marukawa // If there is only one terminator instruction, process it. 153fef80a29SKazushi (Jam) Marukawa if (I == MBB.begin() || !isUnpredicatedTerminator(*--I)) { 154fef80a29SKazushi (Jam) Marukawa if (isUncondBranchOpcode(LastOpc)) { 155fef80a29SKazushi (Jam) Marukawa TBB = LastInst->getOperand(0).getMBB(); 156fef80a29SKazushi (Jam) Marukawa return false; 157fef80a29SKazushi (Jam) Marukawa } 158fef80a29SKazushi (Jam) Marukawa if (isCondBranchOpcode(LastOpc)) { 159fef80a29SKazushi (Jam) Marukawa // Block ends with fall-through condbranch. 160fef80a29SKazushi (Jam) Marukawa parseCondBranch(LastInst, TBB, Cond); 161fef80a29SKazushi (Jam) Marukawa return false; 162fef80a29SKazushi (Jam) Marukawa } 163fef80a29SKazushi (Jam) Marukawa return true; // Can't handle indirect branch. 164fef80a29SKazushi (Jam) Marukawa } 165fef80a29SKazushi (Jam) Marukawa 166fef80a29SKazushi (Jam) Marukawa // Get the instruction before it if it is a terminator. 167fef80a29SKazushi (Jam) Marukawa MachineInstr *SecondLastInst = &*I; 168fef80a29SKazushi (Jam) Marukawa unsigned SecondLastOpc = SecondLastInst->getOpcode(); 169fef80a29SKazushi (Jam) Marukawa 170fef80a29SKazushi (Jam) Marukawa // If AllowModify is true and the block ends with two or more unconditional 171fef80a29SKazushi (Jam) Marukawa // branches, delete all but the first unconditional branch. 172fef80a29SKazushi (Jam) Marukawa if (AllowModify && isUncondBranchOpcode(LastOpc)) { 173fef80a29SKazushi (Jam) Marukawa while (isUncondBranchOpcode(SecondLastOpc)) { 174fef80a29SKazushi (Jam) Marukawa LastInst->eraseFromParent(); 175fef80a29SKazushi (Jam) Marukawa LastInst = SecondLastInst; 176fef80a29SKazushi (Jam) Marukawa LastOpc = LastInst->getOpcode(); 177fef80a29SKazushi (Jam) Marukawa if (I == MBB.begin() || !isUnpredicatedTerminator(*--I)) { 178fef80a29SKazushi (Jam) Marukawa // Return now the only terminator is an unconditional branch. 179fef80a29SKazushi (Jam) Marukawa TBB = LastInst->getOperand(0).getMBB(); 180fef80a29SKazushi (Jam) Marukawa return false; 181fef80a29SKazushi (Jam) Marukawa } 182fef80a29SKazushi (Jam) Marukawa SecondLastInst = &*I; 183fef80a29SKazushi (Jam) Marukawa SecondLastOpc = SecondLastInst->getOpcode(); 184fef80a29SKazushi (Jam) Marukawa } 185fef80a29SKazushi (Jam) Marukawa } 186fef80a29SKazushi (Jam) Marukawa 187fef80a29SKazushi (Jam) Marukawa // If there are three terminators, we don't know what sort of block this is. 188fef80a29SKazushi (Jam) Marukawa if (SecondLastInst && I != MBB.begin() && isUnpredicatedTerminator(*--I)) 189fef80a29SKazushi (Jam) Marukawa return true; 190fef80a29SKazushi (Jam) Marukawa 191fef80a29SKazushi (Jam) Marukawa // If the block ends with a B and a Bcc, handle it. 192fef80a29SKazushi (Jam) Marukawa if (isCondBranchOpcode(SecondLastOpc) && isUncondBranchOpcode(LastOpc)) { 193fef80a29SKazushi (Jam) Marukawa parseCondBranch(SecondLastInst, TBB, Cond); 194fef80a29SKazushi (Jam) Marukawa FBB = LastInst->getOperand(0).getMBB(); 195fef80a29SKazushi (Jam) Marukawa return false; 196fef80a29SKazushi (Jam) Marukawa } 197fef80a29SKazushi (Jam) Marukawa 198fef80a29SKazushi (Jam) Marukawa // If the block ends with two unconditional branches, handle it. The second 199fef80a29SKazushi (Jam) Marukawa // one is not executed. 200fef80a29SKazushi (Jam) Marukawa if (isUncondBranchOpcode(SecondLastOpc) && isUncondBranchOpcode(LastOpc)) { 201fef80a29SKazushi (Jam) Marukawa TBB = SecondLastInst->getOperand(0).getMBB(); 202fef80a29SKazushi (Jam) Marukawa return false; 203fef80a29SKazushi (Jam) Marukawa } 204fef80a29SKazushi (Jam) Marukawa 2053c80478dSKazushi (Jam) Marukawa // ...likewise if it ends with an indirect branch followed by an unconditional 206fef80a29SKazushi (Jam) Marukawa // branch. 2073c80478dSKazushi (Jam) Marukawa if (isIndirectBranchOpcode(SecondLastOpc) && isUncondBranchOpcode(LastOpc)) { 2083c80478dSKazushi (Jam) Marukawa I = LastInst; 2093c80478dSKazushi (Jam) Marukawa if (AllowModify) 2103c80478dSKazushi (Jam) Marukawa I->eraseFromParent(); 2113c80478dSKazushi (Jam) Marukawa return true; 2123c80478dSKazushi (Jam) Marukawa } 213fef80a29SKazushi (Jam) Marukawa 214fef80a29SKazushi (Jam) Marukawa // Otherwise, can't handle this. 215fef80a29SKazushi (Jam) Marukawa return true; 216fef80a29SKazushi (Jam) Marukawa } 217fef80a29SKazushi (Jam) Marukawa 218fef80a29SKazushi (Jam) Marukawa unsigned VEInstrInfo::insertBranch(MachineBasicBlock &MBB, 219fef80a29SKazushi (Jam) Marukawa MachineBasicBlock *TBB, 220fef80a29SKazushi (Jam) Marukawa MachineBasicBlock *FBB, 221fef80a29SKazushi (Jam) Marukawa ArrayRef<MachineOperand> Cond, 22224215fecSSimon Moll const DebugLoc &DL, int *BytesAdded) const { 223fef80a29SKazushi (Jam) Marukawa assert(TBB && "insertBranch must not be told to insert a fallthrough"); 224fef80a29SKazushi (Jam) Marukawa assert((Cond.size() == 3 || Cond.size() == 0) && 225fef80a29SKazushi (Jam) Marukawa "VE branch conditions should have three component!"); 226fef80a29SKazushi (Jam) Marukawa assert(!BytesAdded && "code size not handled"); 227fef80a29SKazushi (Jam) Marukawa if (Cond.empty()) { 228fef80a29SKazushi (Jam) Marukawa // Uncondition branch 229fef80a29SKazushi (Jam) Marukawa assert(!FBB && "Unconditional branch with multiple successors!"); 2303c80478dSKazushi (Jam) Marukawa BuildMI(&MBB, DL, get(VE::BRCFLa_t)) 231fef80a29SKazushi (Jam) Marukawa .addMBB(TBB); 232fef80a29SKazushi (Jam) Marukawa return 1; 233fef80a29SKazushi (Jam) Marukawa } 234fef80a29SKazushi (Jam) Marukawa 235fef80a29SKazushi (Jam) Marukawa // Conditional branch 2363c80478dSKazushi (Jam) Marukawa // (BRCFir CC sy sz addr) 237fef80a29SKazushi (Jam) Marukawa assert(Cond[0].isImm() && Cond[2].isReg() && "not implemented"); 238fef80a29SKazushi (Jam) Marukawa 239fef80a29SKazushi (Jam) Marukawa unsigned opc[2]; 240fef80a29SKazushi (Jam) Marukawa const TargetRegisterInfo *TRI = &getRegisterInfo(); 241fef80a29SKazushi (Jam) Marukawa MachineFunction *MF = MBB.getParent(); 242fef80a29SKazushi (Jam) Marukawa const MachineRegisterInfo &MRI = MF->getRegInfo(); 243fef80a29SKazushi (Jam) Marukawa unsigned Reg = Cond[2].getReg(); 244fef80a29SKazushi (Jam) Marukawa if (IsIntegerCC(Cond[0].getImm())) { 245fef80a29SKazushi (Jam) Marukawa if (TRI->getRegSizeInBits(Reg, MRI) == 32) { 2463c80478dSKazushi (Jam) Marukawa opc[0] = VE::BRCFWir; 2473c80478dSKazushi (Jam) Marukawa opc[1] = VE::BRCFWrr; 248fef80a29SKazushi (Jam) Marukawa } else { 2493c80478dSKazushi (Jam) Marukawa opc[0] = VE::BRCFLir; 2503c80478dSKazushi (Jam) Marukawa opc[1] = VE::BRCFLrr; 251fef80a29SKazushi (Jam) Marukawa } 252fef80a29SKazushi (Jam) Marukawa } else { 253fef80a29SKazushi (Jam) Marukawa if (TRI->getRegSizeInBits(Reg, MRI) == 32) { 2543c80478dSKazushi (Jam) Marukawa opc[0] = VE::BRCFSir; 2553c80478dSKazushi (Jam) Marukawa opc[1] = VE::BRCFSrr; 256fef80a29SKazushi (Jam) Marukawa } else { 2573c80478dSKazushi (Jam) Marukawa opc[0] = VE::BRCFDir; 2583c80478dSKazushi (Jam) Marukawa opc[1] = VE::BRCFDrr; 259fef80a29SKazushi (Jam) Marukawa } 260fef80a29SKazushi (Jam) Marukawa } 261fef80a29SKazushi (Jam) Marukawa if (Cond[1].isImm()) { 262fef80a29SKazushi (Jam) Marukawa BuildMI(&MBB, DL, get(opc[0])) 263fef80a29SKazushi (Jam) Marukawa .add(Cond[0]) // condition code 264fef80a29SKazushi (Jam) Marukawa .add(Cond[1]) // lhs 265fef80a29SKazushi (Jam) Marukawa .add(Cond[2]) // rhs 266fef80a29SKazushi (Jam) Marukawa .addMBB(TBB); 267fef80a29SKazushi (Jam) Marukawa } else { 268fef80a29SKazushi (Jam) Marukawa BuildMI(&MBB, DL, get(opc[1])) 269fef80a29SKazushi (Jam) Marukawa .add(Cond[0]) 270fef80a29SKazushi (Jam) Marukawa .add(Cond[1]) 271fef80a29SKazushi (Jam) Marukawa .add(Cond[2]) 272fef80a29SKazushi (Jam) Marukawa .addMBB(TBB); 273fef80a29SKazushi (Jam) Marukawa } 274fef80a29SKazushi (Jam) Marukawa 275fef80a29SKazushi (Jam) Marukawa if (!FBB) 276fef80a29SKazushi (Jam) Marukawa return 1; 277fef80a29SKazushi (Jam) Marukawa 2783c80478dSKazushi (Jam) Marukawa BuildMI(&MBB, DL, get(VE::BRCFLa_t)) 279fef80a29SKazushi (Jam) Marukawa .addMBB(FBB); 280fef80a29SKazushi (Jam) Marukawa return 2; 281fef80a29SKazushi (Jam) Marukawa } 282fef80a29SKazushi (Jam) Marukawa 283fef80a29SKazushi (Jam) Marukawa unsigned VEInstrInfo::removeBranch(MachineBasicBlock &MBB, 284fef80a29SKazushi (Jam) Marukawa int *BytesRemoved) const { 285fef80a29SKazushi (Jam) Marukawa assert(!BytesRemoved && "code size not handled"); 286fef80a29SKazushi (Jam) Marukawa 287fef80a29SKazushi (Jam) Marukawa MachineBasicBlock::iterator I = MBB.end(); 288fef80a29SKazushi (Jam) Marukawa unsigned Count = 0; 289fef80a29SKazushi (Jam) Marukawa while (I != MBB.begin()) { 290fef80a29SKazushi (Jam) Marukawa --I; 291fef80a29SKazushi (Jam) Marukawa 292fef80a29SKazushi (Jam) Marukawa if (I->isDebugValue()) 293fef80a29SKazushi (Jam) Marukawa continue; 294fef80a29SKazushi (Jam) Marukawa 295fef80a29SKazushi (Jam) Marukawa if (!isUncondBranchOpcode(I->getOpcode()) && 296fef80a29SKazushi (Jam) Marukawa !isCondBranchOpcode(I->getOpcode())) 297fef80a29SKazushi (Jam) Marukawa break; // Not a branch 298fef80a29SKazushi (Jam) Marukawa 299fef80a29SKazushi (Jam) Marukawa I->eraseFromParent(); 300fef80a29SKazushi (Jam) Marukawa I = MBB.end(); 301fef80a29SKazushi (Jam) Marukawa ++Count; 302fef80a29SKazushi (Jam) Marukawa } 303fef80a29SKazushi (Jam) Marukawa return Count; 304fef80a29SKazushi (Jam) Marukawa } 305fef80a29SKazushi (Jam) Marukawa 306fef80a29SKazushi (Jam) Marukawa bool VEInstrInfo::reverseBranchCondition( 307fef80a29SKazushi (Jam) Marukawa SmallVectorImpl<MachineOperand> &Cond) const { 30828a42dd1SKazushi (Jam) Marukawa VECC::CondCode CC = static_cast<VECC::CondCode>(Cond[0].getImm()); 309fef80a29SKazushi (Jam) Marukawa Cond[0].setImm(GetOppositeBranchCondition(CC)); 310fef80a29SKazushi (Jam) Marukawa return false; 311fef80a29SKazushi (Jam) Marukawa } 312fef80a29SKazushi (Jam) Marukawa 3133a906a9fSKazushi (Jam) Marukawa static bool IsAliasOfSX(Register Reg) { 3142f01af76SKazushi (Jam) Marukawa return VE::I32RegClass.contains(Reg) || VE::I64RegClass.contains(Reg) || 3153a906a9fSKazushi (Jam) Marukawa VE::F32RegClass.contains(Reg); 3163a906a9fSKazushi (Jam) Marukawa } 3173a906a9fSKazushi (Jam) Marukawa 31840f1e7e8SKazushi (Jam) Marukawa static void copyPhysSubRegs(MachineBasicBlock &MBB, 31940f1e7e8SKazushi (Jam) Marukawa MachineBasicBlock::iterator I, const DebugLoc &DL, 32040f1e7e8SKazushi (Jam) Marukawa MCRegister DestReg, MCRegister SrcReg, bool KillSrc, 32140f1e7e8SKazushi (Jam) Marukawa const MCInstrDesc &MCID, unsigned int NumSubRegs, 32240f1e7e8SKazushi (Jam) Marukawa const unsigned *SubRegIdx, 32340f1e7e8SKazushi (Jam) Marukawa const TargetRegisterInfo *TRI) { 32440f1e7e8SKazushi (Jam) Marukawa MachineInstr *MovMI = nullptr; 32540f1e7e8SKazushi (Jam) Marukawa 32640f1e7e8SKazushi (Jam) Marukawa for (unsigned Idx = 0; Idx != NumSubRegs; ++Idx) { 32740f1e7e8SKazushi (Jam) Marukawa Register SubDest = TRI->getSubReg(DestReg, SubRegIdx[Idx]); 32840f1e7e8SKazushi (Jam) Marukawa Register SubSrc = TRI->getSubReg(SrcReg, SubRegIdx[Idx]); 32940f1e7e8SKazushi (Jam) Marukawa assert(SubDest && SubSrc && "Bad sub-register"); 33040f1e7e8SKazushi (Jam) Marukawa 33140f1e7e8SKazushi (Jam) Marukawa if (MCID.getOpcode() == VE::ORri) { 33240f1e7e8SKazushi (Jam) Marukawa // generate "ORri, dest, src, 0" instruction. 33340f1e7e8SKazushi (Jam) Marukawa MachineInstrBuilder MIB = 33440f1e7e8SKazushi (Jam) Marukawa BuildMI(MBB, I, DL, MCID, SubDest).addReg(SubSrc).addImm(0); 33540f1e7e8SKazushi (Jam) Marukawa MovMI = MIB.getInstr(); 33640f1e7e8SKazushi (Jam) Marukawa } else { 33740f1e7e8SKazushi (Jam) Marukawa llvm_unreachable("Unexpected reg-to-reg copy instruction"); 33840f1e7e8SKazushi (Jam) Marukawa } 33940f1e7e8SKazushi (Jam) Marukawa } 34040f1e7e8SKazushi (Jam) Marukawa // Add implicit super-register defs and kills to the last MovMI. 34140f1e7e8SKazushi (Jam) Marukawa MovMI->addRegisterDefined(DestReg, TRI); 34240f1e7e8SKazushi (Jam) Marukawa if (KillSrc) 34340f1e7e8SKazushi (Jam) Marukawa MovMI->addRegisterKilled(SrcReg, TRI, true); 34440f1e7e8SKazushi (Jam) Marukawa } 34540f1e7e8SKazushi (Jam) Marukawa 346773ae62fSKazushi (Jam) Marukawa void VEInstrInfo::copyPhysReg(MachineBasicBlock &MBB, 347773ae62fSKazushi (Jam) Marukawa MachineBasicBlock::iterator I, const DebugLoc &DL, 348773ae62fSKazushi (Jam) Marukawa MCRegister DestReg, MCRegister SrcReg, 349773ae62fSKazushi (Jam) Marukawa bool KillSrc) const { 350773ae62fSKazushi (Jam) Marukawa 3513a906a9fSKazushi (Jam) Marukawa if (IsAliasOfSX(SrcReg) && IsAliasOfSX(DestReg)) { 352773ae62fSKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::ORri), DestReg) 353773ae62fSKazushi (Jam) Marukawa .addReg(SrcReg, getKillRegState(KillSrc)) 354773ae62fSKazushi (Jam) Marukawa .addImm(0); 35540f1e7e8SKazushi (Jam) Marukawa } else if (VE::F128RegClass.contains(DestReg, SrcReg)) { 35640f1e7e8SKazushi (Jam) Marukawa // Use two instructions. 35740f1e7e8SKazushi (Jam) Marukawa const unsigned SubRegIdx[] = {VE::sub_even, VE::sub_odd}; 35840f1e7e8SKazushi (Jam) Marukawa unsigned int NumSubRegs = 2; 35940f1e7e8SKazushi (Jam) Marukawa copyPhysSubRegs(MBB, I, DL, DestReg, SrcReg, KillSrc, get(VE::ORri), 36040f1e7e8SKazushi (Jam) Marukawa NumSubRegs, SubRegIdx, &getRegisterInfo()); 361773ae62fSKazushi (Jam) Marukawa } else { 362773ae62fSKazushi (Jam) Marukawa const TargetRegisterInfo *TRI = &getRegisterInfo(); 363773ae62fSKazushi (Jam) Marukawa dbgs() << "Impossible reg-to-reg copy from " << printReg(SrcReg, TRI) 364773ae62fSKazushi (Jam) Marukawa << " to " << printReg(DestReg, TRI) << "\n"; 365773ae62fSKazushi (Jam) Marukawa llvm_unreachable("Impossible reg-to-reg copy"); 366773ae62fSKazushi (Jam) Marukawa } 367773ae62fSKazushi (Jam) Marukawa } 368773ae62fSKazushi (Jam) Marukawa 36907c9f757SKazushi (Jam) Marukawa /// isLoadFromStackSlot - If the specified machine instruction is a direct 37007c9f757SKazushi (Jam) Marukawa /// load from a stack slot, return the virtual or physical register number of 37107c9f757SKazushi (Jam) Marukawa /// the destination along with the FrameIndex of the loaded stack slot. If 37207c9f757SKazushi (Jam) Marukawa /// not, return 0. This predicate must return 0 if the instruction has 37307c9f757SKazushi (Jam) Marukawa /// any side effects other than loading from the stack slot. 37407c9f757SKazushi (Jam) Marukawa unsigned VEInstrInfo::isLoadFromStackSlot(const MachineInstr &MI, 37507c9f757SKazushi (Jam) Marukawa int &FrameIndex) const { 376e981a46aSKazushi (Jam) Marukawa if (MI.getOpcode() == VE::LDrii || // I64 377e981a46aSKazushi (Jam) Marukawa MI.getOpcode() == VE::LDLSXrii || // I32 37840f1e7e8SKazushi (Jam) Marukawa MI.getOpcode() == VE::LDUrii || // F32 37940f1e7e8SKazushi (Jam) Marukawa MI.getOpcode() == VE::LDQrii // F128 (pseudo) 380e981a46aSKazushi (Jam) Marukawa ) { 38107c9f757SKazushi (Jam) Marukawa if (MI.getOperand(1).isFI() && MI.getOperand(2).isImm() && 382e981a46aSKazushi (Jam) Marukawa MI.getOperand(2).getImm() == 0 && MI.getOperand(3).isImm() && 383e981a46aSKazushi (Jam) Marukawa MI.getOperand(3).getImm() == 0) { 38407c9f757SKazushi (Jam) Marukawa FrameIndex = MI.getOperand(1).getIndex(); 38507c9f757SKazushi (Jam) Marukawa return MI.getOperand(0).getReg(); 38607c9f757SKazushi (Jam) Marukawa } 38707c9f757SKazushi (Jam) Marukawa } 38807c9f757SKazushi (Jam) Marukawa return 0; 38907c9f757SKazushi (Jam) Marukawa } 39007c9f757SKazushi (Jam) Marukawa 39107c9f757SKazushi (Jam) Marukawa /// isStoreToStackSlot - If the specified machine instruction is a direct 39207c9f757SKazushi (Jam) Marukawa /// store to a stack slot, return the virtual or physical register number of 39307c9f757SKazushi (Jam) Marukawa /// the source reg along with the FrameIndex of the loaded stack slot. If 39407c9f757SKazushi (Jam) Marukawa /// not, return 0. This predicate must return 0 if the instruction has 39507c9f757SKazushi (Jam) Marukawa /// any side effects other than storing to the stack slot. 39607c9f757SKazushi (Jam) Marukawa unsigned VEInstrInfo::isStoreToStackSlot(const MachineInstr &MI, 39707c9f757SKazushi (Jam) Marukawa int &FrameIndex) const { 398e981a46aSKazushi (Jam) Marukawa if (MI.getOpcode() == VE::STrii || // I64 399e981a46aSKazushi (Jam) Marukawa MI.getOpcode() == VE::STLrii || // I32 40040f1e7e8SKazushi (Jam) Marukawa MI.getOpcode() == VE::STUrii || // F32 40140f1e7e8SKazushi (Jam) Marukawa MI.getOpcode() == VE::STQrii // F128 (pseudo) 402e981a46aSKazushi (Jam) Marukawa ) { 40307c9f757SKazushi (Jam) Marukawa if (MI.getOperand(0).isFI() && MI.getOperand(1).isImm() && 404e981a46aSKazushi (Jam) Marukawa MI.getOperand(1).getImm() == 0 && MI.getOperand(2).isImm() && 405e981a46aSKazushi (Jam) Marukawa MI.getOperand(2).getImm() == 0) { 40607c9f757SKazushi (Jam) Marukawa FrameIndex = MI.getOperand(0).getIndex(); 407e981a46aSKazushi (Jam) Marukawa return MI.getOperand(3).getReg(); 40807c9f757SKazushi (Jam) Marukawa } 40907c9f757SKazushi (Jam) Marukawa } 41007c9f757SKazushi (Jam) Marukawa return 0; 41107c9f757SKazushi (Jam) Marukawa } 41207c9f757SKazushi (Jam) Marukawa 41307c9f757SKazushi (Jam) Marukawa void VEInstrInfo::storeRegToStackSlot(MachineBasicBlock &MBB, 41407c9f757SKazushi (Jam) Marukawa MachineBasicBlock::iterator I, 41507c9f757SKazushi (Jam) Marukawa Register SrcReg, bool isKill, int FI, 41607c9f757SKazushi (Jam) Marukawa const TargetRegisterClass *RC, 41707c9f757SKazushi (Jam) Marukawa const TargetRegisterInfo *TRI) const { 41807c9f757SKazushi (Jam) Marukawa DebugLoc DL; 41907c9f757SKazushi (Jam) Marukawa if (I != MBB.end()) 42007c9f757SKazushi (Jam) Marukawa DL = I->getDebugLoc(); 42107c9f757SKazushi (Jam) Marukawa 42207c9f757SKazushi (Jam) Marukawa MachineFunction *MF = MBB.getParent(); 42307c9f757SKazushi (Jam) Marukawa const MachineFrameInfo &MFI = MF->getFrameInfo(); 42407c9f757SKazushi (Jam) Marukawa MachineMemOperand *MMO = MF->getMachineMemOperand( 42507c9f757SKazushi (Jam) Marukawa MachinePointerInfo::getFixedStack(*MF, FI), MachineMemOperand::MOStore, 426624654fdSFangrui Song MFI.getObjectSize(FI), MFI.getObjectAlign(FI)); 42707c9f757SKazushi (Jam) Marukawa 42807c9f757SKazushi (Jam) Marukawa // On the order of operands here: think "[FrameIdx + 0] = SrcReg". 42907c9f757SKazushi (Jam) Marukawa if (RC == &VE::I64RegClass) { 430e981a46aSKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::STrii)) 43107c9f757SKazushi (Jam) Marukawa .addFrameIndex(FI) 43207c9f757SKazushi (Jam) Marukawa .addImm(0) 433e981a46aSKazushi (Jam) Marukawa .addImm(0) 43407c9f757SKazushi (Jam) Marukawa .addReg(SrcReg, getKillRegState(isKill)) 43507c9f757SKazushi (Jam) Marukawa .addMemOperand(MMO); 43607c9f757SKazushi (Jam) Marukawa } else if (RC == &VE::I32RegClass) { 437e981a46aSKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::STLrii)) 43807c9f757SKazushi (Jam) Marukawa .addFrameIndex(FI) 43907c9f757SKazushi (Jam) Marukawa .addImm(0) 440e981a46aSKazushi (Jam) Marukawa .addImm(0) 44107c9f757SKazushi (Jam) Marukawa .addReg(SrcReg, getKillRegState(isKill)) 44207c9f757SKazushi (Jam) Marukawa .addMemOperand(MMO); 44307c9f757SKazushi (Jam) Marukawa } else if (RC == &VE::F32RegClass) { 444e981a46aSKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::STUrii)) 44507c9f757SKazushi (Jam) Marukawa .addFrameIndex(FI) 44607c9f757SKazushi (Jam) Marukawa .addImm(0) 447e981a46aSKazushi (Jam) Marukawa .addImm(0) 44807c9f757SKazushi (Jam) Marukawa .addReg(SrcReg, getKillRegState(isKill)) 44907c9f757SKazushi (Jam) Marukawa .addMemOperand(MMO); 45040f1e7e8SKazushi (Jam) Marukawa } else if (VE::F128RegClass.hasSubClassEq(RC)) { 45140f1e7e8SKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::STQrii)) 45240f1e7e8SKazushi (Jam) Marukawa .addFrameIndex(FI) 45340f1e7e8SKazushi (Jam) Marukawa .addImm(0) 45440f1e7e8SKazushi (Jam) Marukawa .addImm(0) 45540f1e7e8SKazushi (Jam) Marukawa .addReg(SrcReg, getKillRegState(isKill)) 45640f1e7e8SKazushi (Jam) Marukawa .addMemOperand(MMO); 45707c9f757SKazushi (Jam) Marukawa } else 45807c9f757SKazushi (Jam) Marukawa report_fatal_error("Can't store this register to stack slot"); 45907c9f757SKazushi (Jam) Marukawa } 46007c9f757SKazushi (Jam) Marukawa 46107c9f757SKazushi (Jam) Marukawa void VEInstrInfo::loadRegFromStackSlot(MachineBasicBlock &MBB, 46207c9f757SKazushi (Jam) Marukawa MachineBasicBlock::iterator I, 46307c9f757SKazushi (Jam) Marukawa Register DestReg, int FI, 46407c9f757SKazushi (Jam) Marukawa const TargetRegisterClass *RC, 46507c9f757SKazushi (Jam) Marukawa const TargetRegisterInfo *TRI) const { 46607c9f757SKazushi (Jam) Marukawa DebugLoc DL; 46707c9f757SKazushi (Jam) Marukawa if (I != MBB.end()) 46807c9f757SKazushi (Jam) Marukawa DL = I->getDebugLoc(); 46907c9f757SKazushi (Jam) Marukawa 47007c9f757SKazushi (Jam) Marukawa MachineFunction *MF = MBB.getParent(); 47107c9f757SKazushi (Jam) Marukawa const MachineFrameInfo &MFI = MF->getFrameInfo(); 47207c9f757SKazushi (Jam) Marukawa MachineMemOperand *MMO = MF->getMachineMemOperand( 47307c9f757SKazushi (Jam) Marukawa MachinePointerInfo::getFixedStack(*MF, FI), MachineMemOperand::MOLoad, 474624654fdSFangrui Song MFI.getObjectSize(FI), MFI.getObjectAlign(FI)); 47507c9f757SKazushi (Jam) Marukawa 47607c9f757SKazushi (Jam) Marukawa if (RC == &VE::I64RegClass) { 477e981a46aSKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::LDrii), DestReg) 47807c9f757SKazushi (Jam) Marukawa .addFrameIndex(FI) 47907c9f757SKazushi (Jam) Marukawa .addImm(0) 480e981a46aSKazushi (Jam) Marukawa .addImm(0) 48107c9f757SKazushi (Jam) Marukawa .addMemOperand(MMO); 48207c9f757SKazushi (Jam) Marukawa } else if (RC == &VE::I32RegClass) { 483e981a46aSKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::LDLSXrii), DestReg) 48407c9f757SKazushi (Jam) Marukawa .addFrameIndex(FI) 48507c9f757SKazushi (Jam) Marukawa .addImm(0) 486e981a46aSKazushi (Jam) Marukawa .addImm(0) 48707c9f757SKazushi (Jam) Marukawa .addMemOperand(MMO); 48807c9f757SKazushi (Jam) Marukawa } else if (RC == &VE::F32RegClass) { 489e981a46aSKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::LDUrii), DestReg) 49007c9f757SKazushi (Jam) Marukawa .addFrameIndex(FI) 49107c9f757SKazushi (Jam) Marukawa .addImm(0) 492e981a46aSKazushi (Jam) Marukawa .addImm(0) 49307c9f757SKazushi (Jam) Marukawa .addMemOperand(MMO); 49440f1e7e8SKazushi (Jam) Marukawa } else if (VE::F128RegClass.hasSubClassEq(RC)) { 49540f1e7e8SKazushi (Jam) Marukawa BuildMI(MBB, I, DL, get(VE::LDQrii), DestReg) 49640f1e7e8SKazushi (Jam) Marukawa .addFrameIndex(FI) 49740f1e7e8SKazushi (Jam) Marukawa .addImm(0) 49840f1e7e8SKazushi (Jam) Marukawa .addImm(0) 49940f1e7e8SKazushi (Jam) Marukawa .addMemOperand(MMO); 50007c9f757SKazushi (Jam) Marukawa } else 50107c9f757SKazushi (Jam) Marukawa report_fatal_error("Can't load this register from stack slot"); 50207c9f757SKazushi (Jam) Marukawa } 50307c9f757SKazushi (Jam) Marukawa 504*dd6f607eSKazushi (Jam) Marukawa bool VEInstrInfo::FoldImmediate(MachineInstr &UseMI, MachineInstr &DefMI, 505*dd6f607eSKazushi (Jam) Marukawa Register Reg, MachineRegisterInfo *MRI) const { 506*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "FoldImmediate\n"); 507*dd6f607eSKazushi (Jam) Marukawa 508*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "checking DefMI\n"); 509*dd6f607eSKazushi (Jam) Marukawa int64_t ImmVal; 510*dd6f607eSKazushi (Jam) Marukawa switch (DefMI.getOpcode()) { 511*dd6f607eSKazushi (Jam) Marukawa default: 512*dd6f607eSKazushi (Jam) Marukawa return false; 513*dd6f607eSKazushi (Jam) Marukawa case VE::ORim: 514*dd6f607eSKazushi (Jam) Marukawa // General move small immediate instruction on VE. 515*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "checking ORim\n"); 516*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(DefMI.dump()); 517*dd6f607eSKazushi (Jam) Marukawa // FIXME: We may need to support FPImm too. 518*dd6f607eSKazushi (Jam) Marukawa assert(DefMI.getOperand(1).isImm()); 519*dd6f607eSKazushi (Jam) Marukawa assert(DefMI.getOperand(2).isImm()); 520*dd6f607eSKazushi (Jam) Marukawa ImmVal = 521*dd6f607eSKazushi (Jam) Marukawa DefMI.getOperand(1).getImm() + mimm2Val(DefMI.getOperand(2).getImm()); 522*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "ImmVal is " << ImmVal << "\n"); 523*dd6f607eSKazushi (Jam) Marukawa break; 524*dd6f607eSKazushi (Jam) Marukawa case VE::LEAzii: 525*dd6f607eSKazushi (Jam) Marukawa // General move immediate instruction on VE. 526*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "checking LEAzii\n"); 527*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(DefMI.dump()); 528*dd6f607eSKazushi (Jam) Marukawa // FIXME: We may need to support FPImm too. 529*dd6f607eSKazushi (Jam) Marukawa assert(DefMI.getOperand(2).isImm()); 530*dd6f607eSKazushi (Jam) Marukawa if (!DefMI.getOperand(3).isImm()) 531*dd6f607eSKazushi (Jam) Marukawa // LEAzii may refer label 532*dd6f607eSKazushi (Jam) Marukawa return false; 533*dd6f607eSKazushi (Jam) Marukawa ImmVal = DefMI.getOperand(2).getImm() + DefMI.getOperand(3).getImm(); 534*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "ImmVal is " << ImmVal << "\n"); 535*dd6f607eSKazushi (Jam) Marukawa break; 536*dd6f607eSKazushi (Jam) Marukawa } 537*dd6f607eSKazushi (Jam) Marukawa 538*dd6f607eSKazushi (Jam) Marukawa // Try to fold like below: 539*dd6f607eSKazushi (Jam) Marukawa // %1:i64 = ORim 0, 0(1) 540*dd6f607eSKazushi (Jam) Marukawa // %2:i64 = CMPSLrr %0, %1 541*dd6f607eSKazushi (Jam) Marukawa // To 542*dd6f607eSKazushi (Jam) Marukawa // %2:i64 = CMPSLrm %0, 0(1) 543*dd6f607eSKazushi (Jam) Marukawa // 544*dd6f607eSKazushi (Jam) Marukawa // Another example: 545*dd6f607eSKazushi (Jam) Marukawa // %1:i64 = ORim 6, 0(1) 546*dd6f607eSKazushi (Jam) Marukawa // %2:i64 = CMPSLrr %1, %0 547*dd6f607eSKazushi (Jam) Marukawa // To 548*dd6f607eSKazushi (Jam) Marukawa // %2:i64 = CMPSLir 6, %0 549*dd6f607eSKazushi (Jam) Marukawa // 550*dd6f607eSKazushi (Jam) Marukawa // Support commutable instructions like below: 551*dd6f607eSKazushi (Jam) Marukawa // %1:i64 = ORim 6, 0(1) 552*dd6f607eSKazushi (Jam) Marukawa // %2:i64 = ADDSLrr %1, %0 553*dd6f607eSKazushi (Jam) Marukawa // To 554*dd6f607eSKazushi (Jam) Marukawa // %2:i64 = ADDSLri %0, 6 555*dd6f607eSKazushi (Jam) Marukawa // 556*dd6f607eSKazushi (Jam) Marukawa // FIXME: Need to support i32. Current implementtation requires 557*dd6f607eSKazushi (Jam) Marukawa // EXTRACT_SUBREG, so input has following COPY and it avoids folding: 558*dd6f607eSKazushi (Jam) Marukawa // %1:i64 = ORim 6, 0(1) 559*dd6f607eSKazushi (Jam) Marukawa // %2:i32 = COPY %1.sub_i32 560*dd6f607eSKazushi (Jam) Marukawa // %3:i32 = ADDSWSXrr %0, %2 561*dd6f607eSKazushi (Jam) Marukawa // FIXME: Need to support shift, cmov, and more instructions. 562*dd6f607eSKazushi (Jam) Marukawa // FIXME: Need to support lvl too, but LVLGen runs after peephole-opt. 563*dd6f607eSKazushi (Jam) Marukawa 564*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "checking UseMI\n"); 565*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(UseMI.dump()); 566*dd6f607eSKazushi (Jam) Marukawa unsigned NewUseOpcSImm7; 567*dd6f607eSKazushi (Jam) Marukawa unsigned NewUseOpcMImm; 568*dd6f607eSKazushi (Jam) Marukawa enum InstType { 569*dd6f607eSKazushi (Jam) Marukawa rr2ri_rm, // rr -> ri or rm, commutable 570*dd6f607eSKazushi (Jam) Marukawa rr2ir_rm, // rr -> ir or rm 571*dd6f607eSKazushi (Jam) Marukawa } InstType; 572*dd6f607eSKazushi (Jam) Marukawa 573*dd6f607eSKazushi (Jam) Marukawa using namespace llvm::VE; 574*dd6f607eSKazushi (Jam) Marukawa #define INSTRKIND(NAME) \ 575*dd6f607eSKazushi (Jam) Marukawa case NAME##rr: \ 576*dd6f607eSKazushi (Jam) Marukawa NewUseOpcSImm7 = NAME##ri; \ 577*dd6f607eSKazushi (Jam) Marukawa NewUseOpcMImm = NAME##rm; \ 578*dd6f607eSKazushi (Jam) Marukawa InstType = rr2ri_rm; \ 579*dd6f607eSKazushi (Jam) Marukawa break 580*dd6f607eSKazushi (Jam) Marukawa #define NCINSTRKIND(NAME) \ 581*dd6f607eSKazushi (Jam) Marukawa case NAME##rr: \ 582*dd6f607eSKazushi (Jam) Marukawa NewUseOpcSImm7 = NAME##ir; \ 583*dd6f607eSKazushi (Jam) Marukawa NewUseOpcMImm = NAME##rm; \ 584*dd6f607eSKazushi (Jam) Marukawa InstType = rr2ir_rm; \ 585*dd6f607eSKazushi (Jam) Marukawa break 586*dd6f607eSKazushi (Jam) Marukawa 587*dd6f607eSKazushi (Jam) Marukawa switch (UseMI.getOpcode()) { 588*dd6f607eSKazushi (Jam) Marukawa default: 589*dd6f607eSKazushi (Jam) Marukawa return false; 590*dd6f607eSKazushi (Jam) Marukawa 591*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(ADDUL); 592*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(ADDSWSX); 593*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(ADDSWZX); 594*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(ADDSL); 595*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(SUBUL); 596*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(SUBSWSX); 597*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(SUBSWZX); 598*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(SUBSL); 599*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MULUL); 600*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MULSWSX); 601*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MULSWZX); 602*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MULSL); 603*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(DIVUL); 604*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(DIVSWSX); 605*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(DIVSWZX); 606*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(DIVSL); 607*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(CMPUL); 608*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(CMPSWSX); 609*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(CMPSWZX); 610*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(CMPSL); 611*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MAXSWSX); 612*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MAXSWZX); 613*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MAXSL); 614*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MINSWSX); 615*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MINSWZX); 616*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(MINSL); 617*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(AND); 618*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(OR); 619*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(XOR); 620*dd6f607eSKazushi (Jam) Marukawa INSTRKIND(EQV); 621*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(NND); 622*dd6f607eSKazushi (Jam) Marukawa NCINSTRKIND(MRG); 623*dd6f607eSKazushi (Jam) Marukawa } 624*dd6f607eSKazushi (Jam) Marukawa 625*dd6f607eSKazushi (Jam) Marukawa #undef INSTRKIND 626*dd6f607eSKazushi (Jam) Marukawa 627*dd6f607eSKazushi (Jam) Marukawa unsigned NewUseOpc; 628*dd6f607eSKazushi (Jam) Marukawa unsigned UseIdx; 629*dd6f607eSKazushi (Jam) Marukawa bool Commute = false; 630*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "checking UseMI operands\n"); 631*dd6f607eSKazushi (Jam) Marukawa switch (InstType) { 632*dd6f607eSKazushi (Jam) Marukawa case rr2ri_rm: 633*dd6f607eSKazushi (Jam) Marukawa UseIdx = 2; 634*dd6f607eSKazushi (Jam) Marukawa if (UseMI.getOperand(1).getReg() == Reg) { 635*dd6f607eSKazushi (Jam) Marukawa Commute = true; 636*dd6f607eSKazushi (Jam) Marukawa } else { 637*dd6f607eSKazushi (Jam) Marukawa assert(UseMI.getOperand(2).getReg() == Reg); 638*dd6f607eSKazushi (Jam) Marukawa } 639*dd6f607eSKazushi (Jam) Marukawa if (isInt<7>(ImmVal)) { 640*dd6f607eSKazushi (Jam) Marukawa // This ImmVal matches to SImm7 slot, so change UseOpc to an instruction 641*dd6f607eSKazushi (Jam) Marukawa // holds a simm7 slot. 642*dd6f607eSKazushi (Jam) Marukawa NewUseOpc = NewUseOpcSImm7; 643*dd6f607eSKazushi (Jam) Marukawa } else if (isMImmVal(ImmVal)) { 644*dd6f607eSKazushi (Jam) Marukawa // Similarly, change UseOpc to an instruction holds a mimm slot. 645*dd6f607eSKazushi (Jam) Marukawa NewUseOpc = NewUseOpcMImm; 646*dd6f607eSKazushi (Jam) Marukawa ImmVal = val2MImm(ImmVal); 647*dd6f607eSKazushi (Jam) Marukawa } else 648*dd6f607eSKazushi (Jam) Marukawa return false; 649*dd6f607eSKazushi (Jam) Marukawa break; 650*dd6f607eSKazushi (Jam) Marukawa case rr2ir_rm: 651*dd6f607eSKazushi (Jam) Marukawa if (UseMI.getOperand(1).getReg() == Reg) { 652*dd6f607eSKazushi (Jam) Marukawa // Check immediate value whether it matchs to the UseMI instruction. 653*dd6f607eSKazushi (Jam) Marukawa if (!isInt<7>(ImmVal)) 654*dd6f607eSKazushi (Jam) Marukawa return false; 655*dd6f607eSKazushi (Jam) Marukawa NewUseOpc = NewUseOpcSImm7; 656*dd6f607eSKazushi (Jam) Marukawa UseIdx = 1; 657*dd6f607eSKazushi (Jam) Marukawa } else { 658*dd6f607eSKazushi (Jam) Marukawa assert(UseMI.getOperand(2).getReg() == Reg); 659*dd6f607eSKazushi (Jam) Marukawa // Check immediate value whether it matchs to the UseMI instruction. 660*dd6f607eSKazushi (Jam) Marukawa if (!isMImmVal(ImmVal)) 661*dd6f607eSKazushi (Jam) Marukawa return false; 662*dd6f607eSKazushi (Jam) Marukawa NewUseOpc = NewUseOpcMImm; 663*dd6f607eSKazushi (Jam) Marukawa ImmVal = val2MImm(ImmVal); 664*dd6f607eSKazushi (Jam) Marukawa UseIdx = 2; 665*dd6f607eSKazushi (Jam) Marukawa } 666*dd6f607eSKazushi (Jam) Marukawa break; 667*dd6f607eSKazushi (Jam) Marukawa } 668*dd6f607eSKazushi (Jam) Marukawa 669*dd6f607eSKazushi (Jam) Marukawa LLVM_DEBUG(dbgs() << "modifying UseMI\n"); 670*dd6f607eSKazushi (Jam) Marukawa bool DeleteDef = MRI->hasOneNonDBGUse(Reg); 671*dd6f607eSKazushi (Jam) Marukawa UseMI.setDesc(get(NewUseOpc)); 672*dd6f607eSKazushi (Jam) Marukawa if (Commute) { 673*dd6f607eSKazushi (Jam) Marukawa UseMI.getOperand(1).setReg(UseMI.getOperand(UseIdx).getReg()); 674*dd6f607eSKazushi (Jam) Marukawa } 675*dd6f607eSKazushi (Jam) Marukawa UseMI.getOperand(UseIdx).ChangeToImmediate(ImmVal); 676*dd6f607eSKazushi (Jam) Marukawa if (DeleteDef) 677*dd6f607eSKazushi (Jam) Marukawa DefMI.eraseFromParent(); 678*dd6f607eSKazushi (Jam) Marukawa 679*dd6f607eSKazushi (Jam) Marukawa return true; 680*dd6f607eSKazushi (Jam) Marukawa } 681*dd6f607eSKazushi (Jam) Marukawa 68260431bd7SKazushi (Jam) Marukawa Register VEInstrInfo::getGlobalBaseReg(MachineFunction *MF) const { 68360431bd7SKazushi (Jam) Marukawa VEMachineFunctionInfo *VEFI = MF->getInfo<VEMachineFunctionInfo>(); 68460431bd7SKazushi (Jam) Marukawa Register GlobalBaseReg = VEFI->getGlobalBaseReg(); 68560431bd7SKazushi (Jam) Marukawa if (GlobalBaseReg != 0) 68660431bd7SKazushi (Jam) Marukawa return GlobalBaseReg; 68760431bd7SKazushi (Jam) Marukawa 68860431bd7SKazushi (Jam) Marukawa // We use %s15 (%got) as a global base register 68960431bd7SKazushi (Jam) Marukawa GlobalBaseReg = VE::SX15; 69060431bd7SKazushi (Jam) Marukawa 69160431bd7SKazushi (Jam) Marukawa // Insert a pseudo instruction to set the GlobalBaseReg into the first 69260431bd7SKazushi (Jam) Marukawa // MBB of the function 69360431bd7SKazushi (Jam) Marukawa MachineBasicBlock &FirstMBB = MF->front(); 69460431bd7SKazushi (Jam) Marukawa MachineBasicBlock::iterator MBBI = FirstMBB.begin(); 69560431bd7SKazushi (Jam) Marukawa DebugLoc dl; 69660431bd7SKazushi (Jam) Marukawa BuildMI(FirstMBB, MBBI, dl, get(VE::GETGOT), GlobalBaseReg); 69760431bd7SKazushi (Jam) Marukawa VEFI->setGlobalBaseReg(GlobalBaseReg); 69860431bd7SKazushi (Jam) Marukawa return GlobalBaseReg; 69960431bd7SKazushi (Jam) Marukawa } 70060431bd7SKazushi (Jam) Marukawa 701064859bdSKazushi (Jam) Marukawa bool VEInstrInfo::expandPostRAPseudo(MachineInstr &MI) const { 702064859bdSKazushi (Jam) Marukawa switch (MI.getOpcode()) { 703064859bdSKazushi (Jam) Marukawa case VE::EXTEND_STACK: { 704064859bdSKazushi (Jam) Marukawa return expandExtendStackPseudo(MI); 705064859bdSKazushi (Jam) Marukawa } 706064859bdSKazushi (Jam) Marukawa case VE::EXTEND_STACK_GUARD: { 707064859bdSKazushi (Jam) Marukawa MI.eraseFromParent(); // The pseudo instruction is gone now. 708064859bdSKazushi (Jam) Marukawa return true; 709064859bdSKazushi (Jam) Marukawa } 710dedaf3a2SKazushi (Jam) Marukawa case VE::GETSTACKTOP: { 711dedaf3a2SKazushi (Jam) Marukawa return expandGetStackTopPseudo(MI); 712dedaf3a2SKazushi (Jam) Marukawa } 713064859bdSKazushi (Jam) Marukawa } 714064859bdSKazushi (Jam) Marukawa return false; 715064859bdSKazushi (Jam) Marukawa } 716064859bdSKazushi (Jam) Marukawa 717064859bdSKazushi (Jam) Marukawa bool VEInstrInfo::expandExtendStackPseudo(MachineInstr &MI) const { 718064859bdSKazushi (Jam) Marukawa MachineBasicBlock &MBB = *MI.getParent(); 719064859bdSKazushi (Jam) Marukawa MachineFunction &MF = *MBB.getParent(); 720dedaf3a2SKazushi (Jam) Marukawa const VESubtarget &STI = MF.getSubtarget<VESubtarget>(); 721dedaf3a2SKazushi (Jam) Marukawa const VEInstrInfo &TII = *STI.getInstrInfo(); 722064859bdSKazushi (Jam) Marukawa DebugLoc dl = MBB.findDebugLoc(MI); 723064859bdSKazushi (Jam) Marukawa 724064859bdSKazushi (Jam) Marukawa // Create following instructions and multiple basic blocks. 725064859bdSKazushi (Jam) Marukawa // 726064859bdSKazushi (Jam) Marukawa // thisBB: 727064859bdSKazushi (Jam) Marukawa // brge.l.t %sp, %sl, sinkBB 728064859bdSKazushi (Jam) Marukawa // syscallBB: 729064859bdSKazushi (Jam) Marukawa // ld %s61, 0x18(, %tp) // load param area 730064859bdSKazushi (Jam) Marukawa // or %s62, 0, %s0 // spill the value of %s0 731064859bdSKazushi (Jam) Marukawa // lea %s63, 0x13b // syscall # of grow 732064859bdSKazushi (Jam) Marukawa // shm.l %s63, 0x0(%s61) // store syscall # at addr:0 733064859bdSKazushi (Jam) Marukawa // shm.l %sl, 0x8(%s61) // store old limit at addr:8 734064859bdSKazushi (Jam) Marukawa // shm.l %sp, 0x10(%s61) // store new limit at addr:16 735064859bdSKazushi (Jam) Marukawa // monc // call monitor 736064859bdSKazushi (Jam) Marukawa // or %s0, 0, %s62 // restore the value of %s0 737064859bdSKazushi (Jam) Marukawa // sinkBB: 738064859bdSKazushi (Jam) Marukawa 739064859bdSKazushi (Jam) Marukawa // Create new MBB 740064859bdSKazushi (Jam) Marukawa MachineBasicBlock *BB = &MBB; 741064859bdSKazushi (Jam) Marukawa const BasicBlock *LLVM_BB = BB->getBasicBlock(); 742064859bdSKazushi (Jam) Marukawa MachineBasicBlock *syscallMBB = MF.CreateMachineBasicBlock(LLVM_BB); 743064859bdSKazushi (Jam) Marukawa MachineBasicBlock *sinkMBB = MF.CreateMachineBasicBlock(LLVM_BB); 744064859bdSKazushi (Jam) Marukawa MachineFunction::iterator It = ++(BB->getIterator()); 745064859bdSKazushi (Jam) Marukawa MF.insert(It, syscallMBB); 746064859bdSKazushi (Jam) Marukawa MF.insert(It, sinkMBB); 747064859bdSKazushi (Jam) Marukawa 748064859bdSKazushi (Jam) Marukawa // Transfer the remainder of BB and its successor edges to sinkMBB. 749064859bdSKazushi (Jam) Marukawa sinkMBB->splice(sinkMBB->begin(), BB, 750064859bdSKazushi (Jam) Marukawa std::next(std::next(MachineBasicBlock::iterator(MI))), 751064859bdSKazushi (Jam) Marukawa BB->end()); 752064859bdSKazushi (Jam) Marukawa sinkMBB->transferSuccessorsAndUpdatePHIs(BB); 753064859bdSKazushi (Jam) Marukawa 754064859bdSKazushi (Jam) Marukawa // Next, add the true and fallthrough blocks as its successors. 755064859bdSKazushi (Jam) Marukawa BB->addSuccessor(syscallMBB); 756064859bdSKazushi (Jam) Marukawa BB->addSuccessor(sinkMBB); 7573c80478dSKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::BRCFLrr_t)) 758064859bdSKazushi (Jam) Marukawa .addImm(VECC::CC_IGE) 759064859bdSKazushi (Jam) Marukawa .addReg(VE::SX11) // %sp 760064859bdSKazushi (Jam) Marukawa .addReg(VE::SX8) // %sl 761064859bdSKazushi (Jam) Marukawa .addMBB(sinkMBB); 762064859bdSKazushi (Jam) Marukawa 763064859bdSKazushi (Jam) Marukawa BB = syscallMBB; 764064859bdSKazushi (Jam) Marukawa 765064859bdSKazushi (Jam) Marukawa // Update machine-CFG edges 766064859bdSKazushi (Jam) Marukawa BB->addSuccessor(sinkMBB); 767064859bdSKazushi (Jam) Marukawa 768e981a46aSKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::LDrii), VE::SX61) 769064859bdSKazushi (Jam) Marukawa .addReg(VE::SX14) 770e981a46aSKazushi (Jam) Marukawa .addImm(0) 771064859bdSKazushi (Jam) Marukawa .addImm(0x18); 772064859bdSKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::ORri), VE::SX62) 773064859bdSKazushi (Jam) Marukawa .addReg(VE::SX0) 774064859bdSKazushi (Jam) Marukawa .addImm(0); 775e981a46aSKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::LEAzii), VE::SX63) 776e981a46aSKazushi (Jam) Marukawa .addImm(0) 777e981a46aSKazushi (Jam) Marukawa .addImm(0) 778064859bdSKazushi (Jam) Marukawa .addImm(0x13b); 77949e4faa0SKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::SHMLri)) 780064859bdSKazushi (Jam) Marukawa .addReg(VE::SX61) 781064859bdSKazushi (Jam) Marukawa .addImm(0) 782064859bdSKazushi (Jam) Marukawa .addReg(VE::SX63); 78349e4faa0SKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::SHMLri)) 784064859bdSKazushi (Jam) Marukawa .addReg(VE::SX61) 785064859bdSKazushi (Jam) Marukawa .addImm(8) 786064859bdSKazushi (Jam) Marukawa .addReg(VE::SX8); 78749e4faa0SKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::SHMLri)) 788064859bdSKazushi (Jam) Marukawa .addReg(VE::SX61) 789064859bdSKazushi (Jam) Marukawa .addImm(16) 790064859bdSKazushi (Jam) Marukawa .addReg(VE::SX11); 791064859bdSKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::MONC)); 792064859bdSKazushi (Jam) Marukawa 793064859bdSKazushi (Jam) Marukawa BuildMI(BB, dl, TII.get(VE::ORri), VE::SX0) 794064859bdSKazushi (Jam) Marukawa .addReg(VE::SX62) 795064859bdSKazushi (Jam) Marukawa .addImm(0); 796064859bdSKazushi (Jam) Marukawa 797064859bdSKazushi (Jam) Marukawa MI.eraseFromParent(); // The pseudo instruction is gone now. 798064859bdSKazushi (Jam) Marukawa return true; 799064859bdSKazushi (Jam) Marukawa } 800dedaf3a2SKazushi (Jam) Marukawa 801dedaf3a2SKazushi (Jam) Marukawa bool VEInstrInfo::expandGetStackTopPseudo(MachineInstr &MI) const { 802dedaf3a2SKazushi (Jam) Marukawa MachineBasicBlock *MBB = MI.getParent(); 803dedaf3a2SKazushi (Jam) Marukawa MachineFunction &MF = *MBB->getParent(); 804dedaf3a2SKazushi (Jam) Marukawa const VESubtarget &STI = MF.getSubtarget<VESubtarget>(); 805dedaf3a2SKazushi (Jam) Marukawa const VEInstrInfo &TII = *STI.getInstrInfo(); 806dedaf3a2SKazushi (Jam) Marukawa DebugLoc DL = MBB->findDebugLoc(MI); 807dedaf3a2SKazushi (Jam) Marukawa 808dedaf3a2SKazushi (Jam) Marukawa // Create following instruction 809dedaf3a2SKazushi (Jam) Marukawa // 810dedaf3a2SKazushi (Jam) Marukawa // dst = %sp + target specific frame + the size of parameter area 811dedaf3a2SKazushi (Jam) Marukawa 812dedaf3a2SKazushi (Jam) Marukawa const MachineFrameInfo &MFI = MF.getFrameInfo(); 813dedaf3a2SKazushi (Jam) Marukawa const VEFrameLowering &TFL = *STI.getFrameLowering(); 814dedaf3a2SKazushi (Jam) Marukawa 815dedaf3a2SKazushi (Jam) Marukawa // The VE ABI requires a reserved 176 bytes area at the top 816dedaf3a2SKazushi (Jam) Marukawa // of stack as described in VESubtarget.cpp. So, we adjust it here. 817dedaf3a2SKazushi (Jam) Marukawa unsigned NumBytes = STI.getAdjustedFrameSize(0); 818dedaf3a2SKazushi (Jam) Marukawa 819dedaf3a2SKazushi (Jam) Marukawa // Also adds the size of parameter area. 820dedaf3a2SKazushi (Jam) Marukawa if (MFI.adjustsStack() && TFL.hasReservedCallFrame(MF)) 821dedaf3a2SKazushi (Jam) Marukawa NumBytes += MFI.getMaxCallFrameSize(); 822dedaf3a2SKazushi (Jam) Marukawa 823dedaf3a2SKazushi (Jam) Marukawa BuildMI(*MBB, MI, DL, TII.get(VE::LEArii)) 824dedaf3a2SKazushi (Jam) Marukawa .addDef(MI.getOperand(0).getReg()) 825dedaf3a2SKazushi (Jam) Marukawa .addReg(VE::SX11) 826dedaf3a2SKazushi (Jam) Marukawa .addImm(0) 827dedaf3a2SKazushi (Jam) Marukawa .addImm(NumBytes); 828dedaf3a2SKazushi (Jam) Marukawa 829dedaf3a2SKazushi (Jam) Marukawa MI.eraseFromParent(); // The pseudo instruction is gone now. 830dedaf3a2SKazushi (Jam) Marukawa return true; 831dedaf3a2SKazushi (Jam) Marukawa } 832