From: Craig Topper Date: Sun, 12 Jun 2016 03:10:47 +0000 (+0000) Subject: [X86] Greatly simplify the llvm.x86.avx.vpermil.* auto-upgrade code. We can fully... X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=44d1e38210c9d22d045023f7f8f02d7aeead8dad;p=llvm [X86] Greatly simplify the llvm.x86.avx.vpermil.* auto-upgrade code. We can fully derive everything using types of the intrinsic arguments rather than writing separate loops for each intrinsic. NFC git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@272496 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/IR/AutoUpgrade.cpp b/lib/IR/AutoUpgrade.cpp index 31f665baf86..bb3dc081fd6 100644 --- a/lib/IR/AutoUpgrade.cpp +++ b/lib/IR/AutoUpgrade.cpp @@ -888,43 +888,25 @@ void llvm::UpgradeIntrinsicCall(CallInst *CI, Function *NewFn) { Rep = Builder.CreateShuffleVector(Op0, UndefV, Idxs); } else if (Name == "llvm.stackprotectorcheck") { Rep = nullptr; + } else if (Name.startswith("llvm.x86.avx.vpermil.")) { + Value *Op0 = CI->getArgOperand(0); + unsigned Imm = cast(CI->getArgOperand(1))->getZExtValue(); + VectorType *VecTy = cast(CI->getType()); + unsigned NumElts = VecTy->getNumElements(); + // Calcuate the size of each index in the immediate. + unsigned IdxSize = 64 / VecTy->getScalarSizeInBits(); + unsigned IdxMask = ((1 << IdxSize) - 1); + + SmallVector Idxs(NumElts); + // Lookup the bits for this element, wrapping around the immediate every + // 8-bits. Elements are grouped into sets of 2 or 4 elements so we need + // to offset by the first index of each group. + for (unsigned i = 0; i != NumElts; ++i) + Idxs[i] = ((Imm >> ((i * IdxSize) % 8)) & IdxMask) | (i & ~IdxMask); + + Rep = Builder.CreateShuffleVector(Op0, Op0, Idxs); } else { - bool PD128 = false, PD256 = false, PS128 = false, PS256 = false; - if (Name == "llvm.x86.avx.vpermil.pd.256") - PD256 = true; - else if (Name == "llvm.x86.avx.vpermil.pd") - PD128 = true; - else if (Name == "llvm.x86.avx.vpermil.ps.256") - PS256 = true; - else if (Name == "llvm.x86.avx.vpermil.ps") - PS128 = true; - - if (PD256 || PD128 || PS256 || PS128) { - Value *Op0 = CI->getArgOperand(0); - unsigned Imm = cast(CI->getArgOperand(1))->getZExtValue(); - SmallVector Idxs; - - if (PD128) - for (unsigned i = 0; i != 2; ++i) - Idxs.push_back((Imm >> i) & 0x1); - else if (PD256) - for (unsigned l = 0; l != 4; l+=2) - for (unsigned i = 0; i != 2; ++i) - Idxs.push_back(((Imm >> (l+i)) & 0x1) + l); - else if (PS128) - for (unsigned i = 0; i != 4; ++i) - Idxs.push_back((Imm >> (2 * i)) & 0x3); - else if (PS256) - for (unsigned l = 0; l != 8; l+=4) - for (unsigned i = 0; i != 4; ++i) - Idxs.push_back(((Imm >> (2 * i)) & 0x3) + l); - else - llvm_unreachable("Unexpected function"); - - Rep = Builder.CreateShuffleVector(Op0, Op0, Idxs); - } else { - llvm_unreachable("Unknown function for CallInst upgrade."); - } + llvm_unreachable("Unknown function for CallInst upgrade."); } if (Rep)