From: Martin Storsjo Date: Fri, 11 Jan 2019 07:31:17 +0000 (+0000) Subject: Revert "[SelectionDAGBuilder] Refactor GetRegistersForValue. NFCI." X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=4ad7a7e37f9a6d762e948d270494a7df0e91729d;p=llvm Revert "[SelectionDAGBuilder] Refactor GetRegistersForValue. NFCI." This reverts commit r350841, as it actually had functional changes and broke compilation. See PR40290. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@350921 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp b/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp index 9b8ff493771..569fb8a4e7c 100644 --- a/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp +++ b/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp @@ -7343,11 +7343,10 @@ static SDValue getAddressForMemoryInput(SDValue Chain, const SDLoc &Location, /// /// OpInfo describes the operand /// RefOpInfo describes the matching operand if any, the operand otherwise -static void GetRegistersForValue(SelectionDAG &DAG, const SDLoc &DL, - SDISelAsmOperandInfo &OpInfo, +static void GetRegistersForValue(SelectionDAG &DAG, const TargetLowering &TLI, + const SDLoc &DL, SDISelAsmOperandInfo &OpInfo, SDISelAsmOperandInfo &RefOpInfo) { LLVMContext &Context = *DAG.getContext(); - const TargetLowering &TLI = DAG.getTargetLoweringInfo(); MachineFunction &MF = DAG.getMachineFunction(); SmallVector Regs; @@ -7355,19 +7354,11 @@ static void GetRegistersForValue(SelectionDAG &DAG, const SDLoc &DL, // If this is a constraint for a single physreg, or a constraint for a // register class, find it. - unsigned AssignedReg; - const TargetRegisterClass *RC; - std::tie(AssignedReg, RC) = TLI.getRegForInlineAsmConstraint( - &TRI, RefOpInfo.ConstraintCode, RefOpInfo.ConstraintVT); - // RC is unset only on failure. Return immediately. - if (!RC) - return; - - // Get the actual register value type. This is important, because the user - // may have asked for (e.g.) the AX register in i32 type. We need to - // remember that AX is actually i16 to get the right extension. - const MVT RegVT = *TRI.legalclasstypes_begin(*RC); + std::pair PhysReg = + TLI.getRegForInlineAsmConstraint(&TRI, RefOpInfo.ConstraintCode, + RefOpInfo.ConstraintVT); + unsigned NumRegs = 1; if (OpInfo.ConstraintVT != MVT::Other) { // If this is an FP operand in an integer register (or visa versa), or more // generally if the operand value disagrees with the register class we plan @@ -7377,11 +7368,13 @@ static void GetRegistersForValue(SelectionDAG &DAG, const SDLoc &DL, // Bitcast for output value is done at the end of visitInlineAsm(). if ((OpInfo.Type == InlineAsm::isOutput || OpInfo.Type == InlineAsm::isInput) && - !TRI.isTypeLegalForClass(*RC, OpInfo.ConstraintVT)) { + PhysReg.second && + !TRI.isTypeLegalForClass(*PhysReg.second, OpInfo.ConstraintVT)) { // Try to convert to the first EVT that the reg class contains. If the // types are identical size, use a bitcast to convert (e.g. two differing // vector types). Note: output bitcast is done at the end of // visitInlineAsm(). + MVT RegVT = *TRI.legalclasstypes_begin(*PhysReg.second); if (RegVT.getSizeInBits() == OpInfo.ConstraintVT.getSizeInBits()) { // Exclude indirect inputs while they are unsupported because the code // to perform the load is missing and thus OpInfo.CallOperand still @@ -7394,13 +7387,15 @@ static void GetRegistersForValue(SelectionDAG &DAG, const SDLoc &DL, // use the corresponding integer type. This turns an f64 value into // i64, which can be passed with two i32 values on a 32-bit machine. } else if (RegVT.isInteger() && OpInfo.ConstraintVT.isFloatingPoint()) { - MVT VT = MVT::getIntegerVT(OpInfo.ConstraintVT.getSizeInBits()); + RegVT = MVT::getIntegerVT(OpInfo.ConstraintVT.getSizeInBits()); if (OpInfo.Type == InlineAsm::isInput) OpInfo.CallOperand = - DAG.getNode(ISD::BITCAST, DL, VT, OpInfo.CallOperand); - OpInfo.ConstraintVT = VT; + DAG.getNode(ISD::BITCAST, DL, RegVT, OpInfo.CallOperand); + OpInfo.ConstraintVT = RegVT; } } + + NumRegs = TLI.getNumRegisters(Context, OpInfo.ConstraintVT); } // No need to allocate a matching input constraint since the constraint it's @@ -7408,36 +7403,59 @@ static void GetRegistersForValue(SelectionDAG &DAG, const SDLoc &DL, if (OpInfo.isMatchingInputConstraint()) return; + MVT RegVT; EVT ValueVT = OpInfo.ConstraintVT; - if (OpInfo.ConstraintVT == MVT::Other) - ValueVT = RegVT; - - // Initialize NumRegs. - unsigned NumRegs = 1; - if (OpInfo.ConstraintVT != MVT::Other) - NumRegs = TLI.getNumRegisters(Context, OpInfo.ConstraintVT); // If this is a constraint for a specific physical register, like {r17}, // assign it now. + if (unsigned AssignedReg = PhysReg.first) { + const TargetRegisterClass *RC = PhysReg.second; + if (OpInfo.ConstraintVT == MVT::Other) + ValueVT = *TRI.legalclasstypes_begin(*RC); + + // Get the actual register value type. This is important, because the user + // may have asked for (e.g.) the AX register in i32 type. We need to + // remember that AX is actually i16 to get the right extension. + RegVT = *TRI.legalclasstypes_begin(*RC); + + // This is an explicit reference to a physical register. + Regs.push_back(AssignedReg); + + // If this is an expanded reference, add the rest of the regs to Regs. + if (NumRegs != 1) { + TargetRegisterClass::iterator I = RC->begin(); + for (; *I != AssignedReg; ++I) + assert(I != RC->end() && "Didn't find reg!"); + + // Already added the first reg. + --NumRegs; ++I; + for (; NumRegs; --NumRegs, ++I) { + assert(I != RC->end() && "Ran out of registers to allocate!"); + Regs.push_back(*I); + } + } - // If this associated to a specific register, initialize iterator to correct - // place. If virtual, make sure we have enough registers - - // Initialize iterator if necessary - TargetRegisterClass::iterator I = RC->begin(); - MachineRegisterInfo &RegInfo = MF.getRegInfo(); - if (AssignedReg) { - for (; *I != AssignedReg; ++I) - assert(I != RC->end() && "Didn't find reg!"); + OpInfo.AssignedRegs = RegsForValue(Regs, RegVT, ValueVT); + return; } - for (; NumRegs; --NumRegs, ++I) { - assert(I != RC->end() && "Ran out of registers to allocate!"); - auto R = (AssignedReg) ? *I : RegInfo.createVirtualRegister(RC); - Regs.push_back(R); + // Otherwise, if this was a reference to an LLVM register class, create vregs + // for this reference. + if (const TargetRegisterClass *RC = PhysReg.second) { + RegVT = *TRI.legalclasstypes_begin(*RC); + if (OpInfo.ConstraintVT == MVT::Other) + ValueVT = RegVT; + + // Create the appropriate number of virtual registers. + MachineRegisterInfo &RegInfo = MF.getRegInfo(); + for (; NumRegs; --NumRegs) + Regs.push_back(RegInfo.createVirtualRegister(RC)); + + OpInfo.AssignedRegs = RegsForValue(Regs, RegVT, ValueVT); + return; } - OpInfo.AssignedRegs = RegsForValue(Regs, RegVT, ValueVT); + // Otherwise, we couldn't allocate enough registers for this. } static unsigned @@ -7617,7 +7635,7 @@ void SelectionDAGBuilder::visitInlineAsm(ImmutableCallSite CS) { ? ConstraintOperands[OpInfo.getMatchedOperand()] : OpInfo; if (RefOpInfo.ConstraintType == TargetLowering::C_Register) - GetRegistersForValue(DAG, getCurSDLoc(), OpInfo, RefOpInfo); + GetRegistersForValue(DAG, TLI, getCurSDLoc(), OpInfo, RefOpInfo); } // Third pass - Loop over all of the operands, assigning virtual or physregs @@ -7631,7 +7649,7 @@ void SelectionDAGBuilder::visitInlineAsm(ImmutableCallSite CS) { // C_Register operands have already been allocated, Other/Memory don't need // to be. if (RefOpInfo.ConstraintType == TargetLowering::C_RegisterClass) - GetRegistersForValue(DAG, getCurSDLoc(), OpInfo, RefOpInfo); + GetRegistersForValue(DAG, TLI, getCurSDLoc(), OpInfo, RefOpInfo); } // AsmNodeOperands - The operands for the ISD::INLINEASM node.