18bcb0991SDimitry Andric //===- lib/CodeGen/GlobalISel/GISelKnownBits.cpp --------------*- C++ *-===// 28bcb0991SDimitry Andric // 38bcb0991SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 48bcb0991SDimitry Andric // See https://llvm.org/LICENSE.txt for license information. 58bcb0991SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 68bcb0991SDimitry Andric // 78bcb0991SDimitry Andric //===----------------------------------------------------------------------===// 88bcb0991SDimitry Andric // 98bcb0991SDimitry Andric /// Provides analysis for querying information about KnownBits during GISel 108bcb0991SDimitry Andric /// passes. 118bcb0991SDimitry Andric // 128bcb0991SDimitry Andric //===------------------ 138bcb0991SDimitry Andric #include "llvm/CodeGen/GlobalISel/GISelKnownBits.h" 148bcb0991SDimitry Andric #include "llvm/Analysis/ValueTracking.h" 158bcb0991SDimitry Andric #include "llvm/CodeGen/GlobalISel/Utils.h" 168bcb0991SDimitry Andric #include "llvm/CodeGen/MachineFrameInfo.h" 178bcb0991SDimitry Andric #include "llvm/CodeGen/MachineRegisterInfo.h" 188bcb0991SDimitry Andric #include "llvm/CodeGen/TargetLowering.h" 198bcb0991SDimitry Andric #include "llvm/CodeGen/TargetOpcodes.h" 208bcb0991SDimitry Andric 218bcb0991SDimitry Andric #define DEBUG_TYPE "gisel-known-bits" 228bcb0991SDimitry Andric 238bcb0991SDimitry Andric using namespace llvm; 248bcb0991SDimitry Andric 258bcb0991SDimitry Andric char llvm::GISelKnownBitsAnalysis::ID = 0; 268bcb0991SDimitry Andric 278bcb0991SDimitry Andric INITIALIZE_PASS_BEGIN(GISelKnownBitsAnalysis, DEBUG_TYPE, 288bcb0991SDimitry Andric "Analysis for ComputingKnownBits", false, true) 298bcb0991SDimitry Andric INITIALIZE_PASS_END(GISelKnownBitsAnalysis, DEBUG_TYPE, 308bcb0991SDimitry Andric "Analysis for ComputingKnownBits", false, true) 318bcb0991SDimitry Andric 328bcb0991SDimitry Andric GISelKnownBits::GISelKnownBits(MachineFunction &MF) 338bcb0991SDimitry Andric : MF(MF), MRI(MF.getRegInfo()), TL(*MF.getSubtarget().getTargetLowering()), 348bcb0991SDimitry Andric DL(MF.getFunction().getParent()->getDataLayout()) {} 358bcb0991SDimitry Andric 368bcb0991SDimitry Andric Align GISelKnownBits::inferAlignmentForFrameIdx(int FrameIdx, int Offset, 378bcb0991SDimitry Andric const MachineFunction &MF) { 388bcb0991SDimitry Andric const MachineFrameInfo &MFI = MF.getFrameInfo(); 398bcb0991SDimitry Andric return commonAlignment(Align(MFI.getObjectAlignment(FrameIdx)), Offset); 408bcb0991SDimitry Andric // TODO: How to handle cases with Base + Offset? 418bcb0991SDimitry Andric } 428bcb0991SDimitry Andric 438bcb0991SDimitry Andric MaybeAlign GISelKnownBits::inferPtrAlignment(const MachineInstr &MI) { 448bcb0991SDimitry Andric if (MI.getOpcode() == TargetOpcode::G_FRAME_INDEX) { 458bcb0991SDimitry Andric int FrameIdx = MI.getOperand(1).getIndex(); 468bcb0991SDimitry Andric return inferAlignmentForFrameIdx(FrameIdx, 0, *MI.getMF()); 478bcb0991SDimitry Andric } 488bcb0991SDimitry Andric return None; 498bcb0991SDimitry Andric } 508bcb0991SDimitry Andric 518bcb0991SDimitry Andric void GISelKnownBits::computeKnownBitsForFrameIndex(Register R, KnownBits &Known, 528bcb0991SDimitry Andric const APInt &DemandedElts, 538bcb0991SDimitry Andric unsigned Depth) { 548bcb0991SDimitry Andric const MachineInstr &MI = *MRI.getVRegDef(R); 558bcb0991SDimitry Andric computeKnownBitsForAlignment(Known, inferPtrAlignment(MI)); 568bcb0991SDimitry Andric } 578bcb0991SDimitry Andric 588bcb0991SDimitry Andric void GISelKnownBits::computeKnownBitsForAlignment(KnownBits &Known, 598bcb0991SDimitry Andric MaybeAlign Alignment) { 608bcb0991SDimitry Andric if (Alignment) 618bcb0991SDimitry Andric // The low bits are known zero if the pointer is aligned. 628bcb0991SDimitry Andric Known.Zero.setLowBits(Log2(Alignment)); 638bcb0991SDimitry Andric } 648bcb0991SDimitry Andric 658bcb0991SDimitry Andric KnownBits GISelKnownBits::getKnownBits(MachineInstr &MI) { 668bcb0991SDimitry Andric return getKnownBits(MI.getOperand(0).getReg()); 678bcb0991SDimitry Andric } 688bcb0991SDimitry Andric 698bcb0991SDimitry Andric KnownBits GISelKnownBits::getKnownBits(Register R) { 708bcb0991SDimitry Andric KnownBits Known; 718bcb0991SDimitry Andric LLT Ty = MRI.getType(R); 728bcb0991SDimitry Andric APInt DemandedElts = 738bcb0991SDimitry Andric Ty.isVector() ? APInt::getAllOnesValue(Ty.getNumElements()) : APInt(1, 1); 748bcb0991SDimitry Andric computeKnownBitsImpl(R, Known, DemandedElts); 758bcb0991SDimitry Andric return Known; 768bcb0991SDimitry Andric } 778bcb0991SDimitry Andric 788bcb0991SDimitry Andric bool GISelKnownBits::signBitIsZero(Register R) { 798bcb0991SDimitry Andric LLT Ty = MRI.getType(R); 808bcb0991SDimitry Andric unsigned BitWidth = Ty.getScalarSizeInBits(); 818bcb0991SDimitry Andric return maskedValueIsZero(R, APInt::getSignMask(BitWidth)); 828bcb0991SDimitry Andric } 838bcb0991SDimitry Andric 848bcb0991SDimitry Andric APInt GISelKnownBits::getKnownZeroes(Register R) { 858bcb0991SDimitry Andric return getKnownBits(R).Zero; 868bcb0991SDimitry Andric } 878bcb0991SDimitry Andric 888bcb0991SDimitry Andric APInt GISelKnownBits::getKnownOnes(Register R) { return getKnownBits(R).One; } 898bcb0991SDimitry Andric 908bcb0991SDimitry Andric void GISelKnownBits::computeKnownBitsImpl(Register R, KnownBits &Known, 918bcb0991SDimitry Andric const APInt &DemandedElts, 928bcb0991SDimitry Andric unsigned Depth) { 938bcb0991SDimitry Andric MachineInstr &MI = *MRI.getVRegDef(R); 948bcb0991SDimitry Andric unsigned Opcode = MI.getOpcode(); 958bcb0991SDimitry Andric LLT DstTy = MRI.getType(R); 968bcb0991SDimitry Andric 978bcb0991SDimitry Andric // Handle the case where this is called on a register that does not have a 988bcb0991SDimitry Andric // type constraint (i.e. it has a register class constraint instead). This is 998bcb0991SDimitry Andric // unlikely to occur except by looking through copies but it is possible for 1008bcb0991SDimitry Andric // the initial register being queried to be in this state. 1018bcb0991SDimitry Andric if (!DstTy.isValid()) { 1028bcb0991SDimitry Andric Known = KnownBits(); 1038bcb0991SDimitry Andric return; 1048bcb0991SDimitry Andric } 1058bcb0991SDimitry Andric 1068bcb0991SDimitry Andric unsigned BitWidth = DstTy.getSizeInBits(); 1078bcb0991SDimitry Andric Known = KnownBits(BitWidth); // Don't know anything 1088bcb0991SDimitry Andric 1098bcb0991SDimitry Andric if (DstTy.isVector()) 1108bcb0991SDimitry Andric return; // TODO: Handle vectors. 1118bcb0991SDimitry Andric 1128bcb0991SDimitry Andric if (Depth == getMaxDepth()) 1138bcb0991SDimitry Andric return; 1148bcb0991SDimitry Andric 1158bcb0991SDimitry Andric if (!DemandedElts) 1168bcb0991SDimitry Andric return; // No demanded elts, better to assume we don't know anything. 1178bcb0991SDimitry Andric 1188bcb0991SDimitry Andric KnownBits Known2; 1198bcb0991SDimitry Andric 1208bcb0991SDimitry Andric switch (Opcode) { 1218bcb0991SDimitry Andric default: 1228bcb0991SDimitry Andric TL.computeKnownBitsForTargetInstr(*this, R, Known, DemandedElts, MRI, 1238bcb0991SDimitry Andric Depth); 1248bcb0991SDimitry Andric break; 1258bcb0991SDimitry Andric case TargetOpcode::COPY: { 1268bcb0991SDimitry Andric MachineOperand Dst = MI.getOperand(0); 1278bcb0991SDimitry Andric MachineOperand Src = MI.getOperand(1); 1288bcb0991SDimitry Andric // Look through trivial copies but don't look through trivial copies of the 1298bcb0991SDimitry Andric // form `%1:(s32) = OP %0:gpr32` known-bits analysis is currently unable to 1308bcb0991SDimitry Andric // determine the bit width of a register class. 1318bcb0991SDimitry Andric // 1328bcb0991SDimitry Andric // We can't use NoSubRegister by name as it's defined by each target but 1338bcb0991SDimitry Andric // it's always defined to be 0 by tablegen. 1348bcb0991SDimitry Andric if (Dst.getSubReg() == 0 /*NoSubRegister*/ && Src.getReg().isVirtual() && 1358bcb0991SDimitry Andric Src.getSubReg() == 0 /*NoSubRegister*/ && 1368bcb0991SDimitry Andric MRI.getType(Src.getReg()).isValid()) { 1378bcb0991SDimitry Andric // Don't increment Depth for this one since we didn't do any work. 1388bcb0991SDimitry Andric computeKnownBitsImpl(Src.getReg(), Known, DemandedElts, Depth); 1398bcb0991SDimitry Andric } 1408bcb0991SDimitry Andric break; 1418bcb0991SDimitry Andric } 1428bcb0991SDimitry Andric case TargetOpcode::G_CONSTANT: { 1438bcb0991SDimitry Andric auto CstVal = getConstantVRegVal(R, MRI); 1448bcb0991SDimitry Andric if (!CstVal) 1458bcb0991SDimitry Andric break; 1468bcb0991SDimitry Andric Known.One = *CstVal; 1478bcb0991SDimitry Andric Known.Zero = ~Known.One; 1488bcb0991SDimitry Andric break; 1498bcb0991SDimitry Andric } 1508bcb0991SDimitry Andric case TargetOpcode::G_FRAME_INDEX: { 1518bcb0991SDimitry Andric computeKnownBitsForFrameIndex(R, Known, DemandedElts); 1528bcb0991SDimitry Andric break; 1538bcb0991SDimitry Andric } 1548bcb0991SDimitry Andric case TargetOpcode::G_SUB: { 1558bcb0991SDimitry Andric // If low bits are known to be zero in both operands, then we know they are 1568bcb0991SDimitry Andric // going to be 0 in the result. Both addition and complement operations 1578bcb0991SDimitry Andric // preserve the low zero bits. 1588bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known2, DemandedElts, 1598bcb0991SDimitry Andric Depth + 1); 1608bcb0991SDimitry Andric unsigned KnownZeroLow = Known2.countMinTrailingZeros(); 1618bcb0991SDimitry Andric if (KnownZeroLow == 0) 1628bcb0991SDimitry Andric break; 1638bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), Known2, DemandedElts, 1648bcb0991SDimitry Andric Depth + 1); 1658bcb0991SDimitry Andric KnownZeroLow = std::min(KnownZeroLow, Known2.countMinTrailingZeros()); 1668bcb0991SDimitry Andric Known.Zero.setLowBits(KnownZeroLow); 1678bcb0991SDimitry Andric break; 1688bcb0991SDimitry Andric } 1698bcb0991SDimitry Andric case TargetOpcode::G_XOR: { 1708bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), Known, DemandedElts, 1718bcb0991SDimitry Andric Depth + 1); 1728bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known2, DemandedElts, 1738bcb0991SDimitry Andric Depth + 1); 1748bcb0991SDimitry Andric 1758bcb0991SDimitry Andric // Output known-0 bits are known if clear or set in both the LHS & RHS. 1768bcb0991SDimitry Andric APInt KnownZeroOut = (Known.Zero & Known2.Zero) | (Known.One & Known2.One); 1778bcb0991SDimitry Andric // Output known-1 are known to be set if set in only one of the LHS, RHS. 1788bcb0991SDimitry Andric Known.One = (Known.Zero & Known2.One) | (Known.One & Known2.Zero); 1798bcb0991SDimitry Andric Known.Zero = KnownZeroOut; 1808bcb0991SDimitry Andric break; 1818bcb0991SDimitry Andric } 182*480093f4SDimitry Andric case TargetOpcode::G_PTR_ADD: { 183*480093f4SDimitry Andric // G_PTR_ADD is like G_ADD. FIXME: Is this true for all targets? 1848bcb0991SDimitry Andric LLT Ty = MRI.getType(MI.getOperand(1).getReg()); 1858bcb0991SDimitry Andric if (DL.isNonIntegralAddressSpace(Ty.getAddressSpace())) 1868bcb0991SDimitry Andric break; 1878bcb0991SDimitry Andric LLVM_FALLTHROUGH; 1888bcb0991SDimitry Andric } 1898bcb0991SDimitry Andric case TargetOpcode::G_ADD: { 1908bcb0991SDimitry Andric // Output known-0 bits are known if clear or set in both the low clear bits 1918bcb0991SDimitry Andric // common to both LHS & RHS. For example, 8+(X<<3) is known to have the 1928bcb0991SDimitry Andric // low 3 bits clear. 1938bcb0991SDimitry Andric // Output known-0 bits are also known if the top bits of each input are 1948bcb0991SDimitry Andric // known to be clear. For example, if one input has the top 10 bits clear 1958bcb0991SDimitry Andric // and the other has the top 8 bits clear, we know the top 7 bits of the 1968bcb0991SDimitry Andric // output must be clear. 1978bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known2, DemandedElts, 1988bcb0991SDimitry Andric Depth + 1); 1998bcb0991SDimitry Andric unsigned KnownZeroHigh = Known2.countMinLeadingZeros(); 2008bcb0991SDimitry Andric unsigned KnownZeroLow = Known2.countMinTrailingZeros(); 2018bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), Known2, DemandedElts, 2028bcb0991SDimitry Andric Depth + 1); 2038bcb0991SDimitry Andric KnownZeroHigh = std::min(KnownZeroHigh, Known2.countMinLeadingZeros()); 2048bcb0991SDimitry Andric KnownZeroLow = std::min(KnownZeroLow, Known2.countMinTrailingZeros()); 2058bcb0991SDimitry Andric Known.Zero.setLowBits(KnownZeroLow); 2068bcb0991SDimitry Andric if (KnownZeroHigh > 1) 2078bcb0991SDimitry Andric Known.Zero.setHighBits(KnownZeroHigh - 1); 2088bcb0991SDimitry Andric break; 2098bcb0991SDimitry Andric } 2108bcb0991SDimitry Andric case TargetOpcode::G_AND: { 2118bcb0991SDimitry Andric // If either the LHS or the RHS are Zero, the result is zero. 2128bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), Known, DemandedElts, 2138bcb0991SDimitry Andric Depth + 1); 2148bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known2, DemandedElts, 2158bcb0991SDimitry Andric Depth + 1); 2168bcb0991SDimitry Andric 2178bcb0991SDimitry Andric // Output known-1 bits are only known if set in both the LHS & RHS. 2188bcb0991SDimitry Andric Known.One &= Known2.One; 2198bcb0991SDimitry Andric // Output known-0 are known to be clear if zero in either the LHS | RHS. 2208bcb0991SDimitry Andric Known.Zero |= Known2.Zero; 2218bcb0991SDimitry Andric break; 2228bcb0991SDimitry Andric } 2238bcb0991SDimitry Andric case TargetOpcode::G_OR: { 2248bcb0991SDimitry Andric // If either the LHS or the RHS are Zero, the result is zero. 2258bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), Known, DemandedElts, 2268bcb0991SDimitry Andric Depth + 1); 2278bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known2, DemandedElts, 2288bcb0991SDimitry Andric Depth + 1); 2298bcb0991SDimitry Andric 2308bcb0991SDimitry Andric // Output known-0 bits are only known if clear in both the LHS & RHS. 2318bcb0991SDimitry Andric Known.Zero &= Known2.Zero; 2328bcb0991SDimitry Andric // Output known-1 are known to be set if set in either the LHS | RHS. 2338bcb0991SDimitry Andric Known.One |= Known2.One; 2348bcb0991SDimitry Andric break; 2358bcb0991SDimitry Andric } 2368bcb0991SDimitry Andric case TargetOpcode::G_MUL: { 2378bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), Known, DemandedElts, 2388bcb0991SDimitry Andric Depth + 1); 2398bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known2, DemandedElts, 2408bcb0991SDimitry Andric Depth + 1); 2418bcb0991SDimitry Andric // If low bits are zero in either operand, output low known-0 bits. 2428bcb0991SDimitry Andric // Also compute a conservative estimate for high known-0 bits. 2438bcb0991SDimitry Andric // More trickiness is possible, but this is sufficient for the 2448bcb0991SDimitry Andric // interesting case of alignment computation. 2458bcb0991SDimitry Andric unsigned TrailZ = 2468bcb0991SDimitry Andric Known.countMinTrailingZeros() + Known2.countMinTrailingZeros(); 2478bcb0991SDimitry Andric unsigned LeadZ = 2488bcb0991SDimitry Andric std::max(Known.countMinLeadingZeros() + Known2.countMinLeadingZeros(), 2498bcb0991SDimitry Andric BitWidth) - 2508bcb0991SDimitry Andric BitWidth; 2518bcb0991SDimitry Andric 2528bcb0991SDimitry Andric Known.resetAll(); 2538bcb0991SDimitry Andric Known.Zero.setLowBits(std::min(TrailZ, BitWidth)); 2548bcb0991SDimitry Andric Known.Zero.setHighBits(std::min(LeadZ, BitWidth)); 2558bcb0991SDimitry Andric break; 2568bcb0991SDimitry Andric } 2578bcb0991SDimitry Andric case TargetOpcode::G_SELECT: { 2588bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(3).getReg(), Known, DemandedElts, 2598bcb0991SDimitry Andric Depth + 1); 2608bcb0991SDimitry Andric // If we don't know any bits, early out. 2618bcb0991SDimitry Andric if (Known.isUnknown()) 2628bcb0991SDimitry Andric break; 2638bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), Known2, DemandedElts, 2648bcb0991SDimitry Andric Depth + 1); 2658bcb0991SDimitry Andric // Only known if known in both the LHS and RHS. 2668bcb0991SDimitry Andric Known.One &= Known2.One; 2678bcb0991SDimitry Andric Known.Zero &= Known2.Zero; 2688bcb0991SDimitry Andric break; 2698bcb0991SDimitry Andric } 2708bcb0991SDimitry Andric case TargetOpcode::G_FCMP: 2718bcb0991SDimitry Andric case TargetOpcode::G_ICMP: { 2728bcb0991SDimitry Andric if (TL.getBooleanContents(DstTy.isVector(), 2738bcb0991SDimitry Andric Opcode == TargetOpcode::G_FCMP) == 2748bcb0991SDimitry Andric TargetLowering::ZeroOrOneBooleanContent && 2758bcb0991SDimitry Andric BitWidth > 1) 2768bcb0991SDimitry Andric Known.Zero.setBitsFrom(1); 2778bcb0991SDimitry Andric break; 2788bcb0991SDimitry Andric } 2798bcb0991SDimitry Andric case TargetOpcode::G_SEXT: { 2808bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known, DemandedElts, 2818bcb0991SDimitry Andric Depth + 1); 2828bcb0991SDimitry Andric // If the sign bit is known to be zero or one, then sext will extend 2838bcb0991SDimitry Andric // it to the top bits, else it will just zext. 2848bcb0991SDimitry Andric Known = Known.sext(BitWidth); 2858bcb0991SDimitry Andric break; 2868bcb0991SDimitry Andric } 2878bcb0991SDimitry Andric case TargetOpcode::G_ANYEXT: { 2888bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known, DemandedElts, 2898bcb0991SDimitry Andric Depth + 1); 2908bcb0991SDimitry Andric Known = Known.zext(BitWidth, true /* ExtendedBitsAreKnownZero */); 2918bcb0991SDimitry Andric break; 2928bcb0991SDimitry Andric } 2938bcb0991SDimitry Andric case TargetOpcode::G_LOAD: { 2948bcb0991SDimitry Andric if (MI.hasOneMemOperand()) { 2958bcb0991SDimitry Andric const MachineMemOperand *MMO = *MI.memoperands_begin(); 2968bcb0991SDimitry Andric if (const MDNode *Ranges = MMO->getRanges()) { 2978bcb0991SDimitry Andric computeKnownBitsFromRangeMetadata(*Ranges, Known); 2988bcb0991SDimitry Andric } 2998bcb0991SDimitry Andric } 3008bcb0991SDimitry Andric break; 3018bcb0991SDimitry Andric } 3028bcb0991SDimitry Andric case TargetOpcode::G_ZEXTLOAD: { 3038bcb0991SDimitry Andric // Everything above the retrieved bits is zero 3048bcb0991SDimitry Andric if (MI.hasOneMemOperand()) 3058bcb0991SDimitry Andric Known.Zero.setBitsFrom((*MI.memoperands_begin())->getSizeInBits()); 3068bcb0991SDimitry Andric break; 3078bcb0991SDimitry Andric } 3088bcb0991SDimitry Andric case TargetOpcode::G_ASHR: 3098bcb0991SDimitry Andric case TargetOpcode::G_LSHR: 3108bcb0991SDimitry Andric case TargetOpcode::G_SHL: { 3118bcb0991SDimitry Andric KnownBits RHSKnown; 3128bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(2).getReg(), RHSKnown, DemandedElts, 3138bcb0991SDimitry Andric Depth + 1); 3148bcb0991SDimitry Andric if (!RHSKnown.isConstant()) { 3158bcb0991SDimitry Andric LLVM_DEBUG( 3168bcb0991SDimitry Andric MachineInstr *RHSMI = MRI.getVRegDef(MI.getOperand(2).getReg()); 3178bcb0991SDimitry Andric dbgs() << '[' << Depth << "] Shift not known constant: " << *RHSMI); 3188bcb0991SDimitry Andric break; 3198bcb0991SDimitry Andric } 3208bcb0991SDimitry Andric uint64_t Shift = RHSKnown.getConstant().getZExtValue(); 3218bcb0991SDimitry Andric LLVM_DEBUG(dbgs() << '[' << Depth << "] Shift is " << Shift << '\n'); 3228bcb0991SDimitry Andric 3238bcb0991SDimitry Andric computeKnownBitsImpl(MI.getOperand(1).getReg(), Known, DemandedElts, 3248bcb0991SDimitry Andric Depth + 1); 3258bcb0991SDimitry Andric 3268bcb0991SDimitry Andric switch (Opcode) { 3278bcb0991SDimitry Andric case TargetOpcode::G_ASHR: 3288bcb0991SDimitry Andric Known.Zero = Known.Zero.ashr(Shift); 3298bcb0991SDimitry Andric Known.One = Known.One.ashr(Shift); 3308bcb0991SDimitry Andric break; 3318bcb0991SDimitry Andric case TargetOpcode::G_LSHR: 3328bcb0991SDimitry Andric Known.Zero = Known.Zero.lshr(Shift); 3338bcb0991SDimitry Andric Known.One = Known.One.lshr(Shift); 3348bcb0991SDimitry Andric Known.Zero.setBitsFrom(Known.Zero.getBitWidth() - Shift); 3358bcb0991SDimitry Andric break; 3368bcb0991SDimitry Andric case TargetOpcode::G_SHL: 3378bcb0991SDimitry Andric Known.Zero = Known.Zero.shl(Shift); 3388bcb0991SDimitry Andric Known.One = Known.One.shl(Shift); 3398bcb0991SDimitry Andric Known.Zero.setBits(0, Shift); 3408bcb0991SDimitry Andric break; 3418bcb0991SDimitry Andric } 3428bcb0991SDimitry Andric break; 3438bcb0991SDimitry Andric } 3448bcb0991SDimitry Andric case TargetOpcode::G_INTTOPTR: 3458bcb0991SDimitry Andric case TargetOpcode::G_PTRTOINT: 3468bcb0991SDimitry Andric // Fall through and handle them the same as zext/trunc. 3478bcb0991SDimitry Andric LLVM_FALLTHROUGH; 3488bcb0991SDimitry Andric case TargetOpcode::G_ZEXT: 3498bcb0991SDimitry Andric case TargetOpcode::G_TRUNC: { 3508bcb0991SDimitry Andric Register SrcReg = MI.getOperand(1).getReg(); 3518bcb0991SDimitry Andric LLT SrcTy = MRI.getType(SrcReg); 3528bcb0991SDimitry Andric unsigned SrcBitWidth = SrcTy.isPointer() 3538bcb0991SDimitry Andric ? DL.getIndexSizeInBits(SrcTy.getAddressSpace()) 3548bcb0991SDimitry Andric : SrcTy.getSizeInBits(); 3558bcb0991SDimitry Andric assert(SrcBitWidth && "SrcBitWidth can't be zero"); 3568bcb0991SDimitry Andric Known = Known.zextOrTrunc(SrcBitWidth, true); 3578bcb0991SDimitry Andric computeKnownBitsImpl(SrcReg, Known, DemandedElts, Depth + 1); 3588bcb0991SDimitry Andric Known = Known.zextOrTrunc(BitWidth, true); 3598bcb0991SDimitry Andric if (BitWidth > SrcBitWidth) 3608bcb0991SDimitry Andric Known.Zero.setBitsFrom(SrcBitWidth); 3618bcb0991SDimitry Andric break; 3628bcb0991SDimitry Andric } 3638bcb0991SDimitry Andric } 3648bcb0991SDimitry Andric 3658bcb0991SDimitry Andric assert(!Known.hasConflict() && "Bits known to be one AND zero?"); 3668bcb0991SDimitry Andric LLVM_DEBUG(dbgs() << "[" << Depth << "] Compute known bits: " << MI << "[" 3678bcb0991SDimitry Andric << Depth << "] Computed for: " << MI << "[" << Depth 3688bcb0991SDimitry Andric << "] Known: 0x" 3698bcb0991SDimitry Andric << (Known.Zero | Known.One).toString(16, false) << "\n" 3708bcb0991SDimitry Andric << "[" << Depth << "] Zero: 0x" 3718bcb0991SDimitry Andric << Known.Zero.toString(16, false) << "\n" 3728bcb0991SDimitry Andric << "[" << Depth << "] One: 0x" 3738bcb0991SDimitry Andric << Known.One.toString(16, false) << "\n"); 3748bcb0991SDimitry Andric } 3758bcb0991SDimitry Andric 376*480093f4SDimitry Andric unsigned GISelKnownBits::computeNumSignBits(Register R, 377*480093f4SDimitry Andric const APInt &DemandedElts, 378*480093f4SDimitry Andric unsigned Depth) { 379*480093f4SDimitry Andric MachineInstr &MI = *MRI.getVRegDef(R); 380*480093f4SDimitry Andric unsigned Opcode = MI.getOpcode(); 381*480093f4SDimitry Andric 382*480093f4SDimitry Andric if (Opcode == TargetOpcode::G_CONSTANT) 383*480093f4SDimitry Andric return MI.getOperand(1).getCImm()->getValue().getNumSignBits(); 384*480093f4SDimitry Andric 385*480093f4SDimitry Andric if (Depth == getMaxDepth()) 386*480093f4SDimitry Andric return 1; 387*480093f4SDimitry Andric 388*480093f4SDimitry Andric if (!DemandedElts) 389*480093f4SDimitry Andric return 1; // No demanded elts, better to assume we don't know anything. 390*480093f4SDimitry Andric 391*480093f4SDimitry Andric LLT DstTy = MRI.getType(R); 392*480093f4SDimitry Andric 393*480093f4SDimitry Andric // Handle the case where this is called on a register that does not have a 394*480093f4SDimitry Andric // type constraint. This is unlikely to occur except by looking through copies 395*480093f4SDimitry Andric // but it is possible for the initial register being queried to be in this 396*480093f4SDimitry Andric // state. 397*480093f4SDimitry Andric if (!DstTy.isValid()) 398*480093f4SDimitry Andric return 1; 399*480093f4SDimitry Andric 400*480093f4SDimitry Andric switch (Opcode) { 401*480093f4SDimitry Andric case TargetOpcode::COPY: { 402*480093f4SDimitry Andric MachineOperand &Src = MI.getOperand(1); 403*480093f4SDimitry Andric if (Src.getReg().isVirtual() && Src.getSubReg() == 0 && 404*480093f4SDimitry Andric MRI.getType(Src.getReg()).isValid()) { 405*480093f4SDimitry Andric // Don't increment Depth for this one since we didn't do any work. 406*480093f4SDimitry Andric return computeNumSignBits(Src.getReg(), DemandedElts, Depth); 407*480093f4SDimitry Andric } 408*480093f4SDimitry Andric 409*480093f4SDimitry Andric return 1; 410*480093f4SDimitry Andric } 411*480093f4SDimitry Andric case TargetOpcode::G_SEXT: { 412*480093f4SDimitry Andric Register Src = MI.getOperand(1).getReg(); 413*480093f4SDimitry Andric LLT SrcTy = MRI.getType(Src); 414*480093f4SDimitry Andric unsigned Tmp = DstTy.getScalarSizeInBits() - SrcTy.getScalarSizeInBits(); 415*480093f4SDimitry Andric return computeNumSignBits(Src, DemandedElts, Depth + 1) + Tmp; 416*480093f4SDimitry Andric } 417*480093f4SDimitry Andric case TargetOpcode::G_TRUNC: { 418*480093f4SDimitry Andric Register Src = MI.getOperand(1).getReg(); 419*480093f4SDimitry Andric LLT SrcTy = MRI.getType(Src); 420*480093f4SDimitry Andric 421*480093f4SDimitry Andric // Check if the sign bits of source go down as far as the truncated value. 422*480093f4SDimitry Andric unsigned DstTyBits = DstTy.getScalarSizeInBits(); 423*480093f4SDimitry Andric unsigned NumSrcBits = SrcTy.getScalarSizeInBits(); 424*480093f4SDimitry Andric unsigned NumSrcSignBits = computeNumSignBits(Src, DemandedElts, Depth + 1); 425*480093f4SDimitry Andric if (NumSrcSignBits > (NumSrcBits - DstTyBits)) 426*480093f4SDimitry Andric return NumSrcSignBits - (NumSrcBits - DstTyBits); 427*480093f4SDimitry Andric break; 428*480093f4SDimitry Andric } 429*480093f4SDimitry Andric default: 430*480093f4SDimitry Andric break; 431*480093f4SDimitry Andric } 432*480093f4SDimitry Andric 433*480093f4SDimitry Andric // TODO: Handle target instructions 434*480093f4SDimitry Andric // TODO: Fall back to known bits 435*480093f4SDimitry Andric return 1; 436*480093f4SDimitry Andric } 437*480093f4SDimitry Andric 438*480093f4SDimitry Andric unsigned GISelKnownBits::computeNumSignBits(Register R, unsigned Depth) { 439*480093f4SDimitry Andric LLT Ty = MRI.getType(R); 440*480093f4SDimitry Andric APInt DemandedElts = Ty.isVector() 441*480093f4SDimitry Andric ? APInt::getAllOnesValue(Ty.getNumElements()) 442*480093f4SDimitry Andric : APInt(1, 1); 443*480093f4SDimitry Andric return computeNumSignBits(R, DemandedElts, Depth); 444*480093f4SDimitry Andric } 445*480093f4SDimitry Andric 4468bcb0991SDimitry Andric void GISelKnownBitsAnalysis::getAnalysisUsage(AnalysisUsage &AU) const { 4478bcb0991SDimitry Andric AU.setPreservesAll(); 4488bcb0991SDimitry Andric MachineFunctionPass::getAnalysisUsage(AU); 4498bcb0991SDimitry Andric } 4508bcb0991SDimitry Andric 4518bcb0991SDimitry Andric bool GISelKnownBitsAnalysis::runOnMachineFunction(MachineFunction &MF) { 4528bcb0991SDimitry Andric return false; 4538bcb0991SDimitry Andric } 454