[PATCH] D13994: [SimplifyLibCalls] Optimization for pow(x, n) where n is some constant

Mandeep Singh Grang via llvm-commits llvm-commits at lists.llvm.org
Tue Nov 17 12:14:29 PST 2015


mgrang updated this revision to Diff 40421.

http://reviews.llvm.org/D13994

Files:
  lib/Transforms/Utils/SimplifyLibCalls.cpp

Index: lib/Transforms/Utils/SimplifyLibCalls.cpp
===================================================================
--- lib/Transforms/Utils/SimplifyLibCalls.cpp
+++ lib/Transforms/Utils/SimplifyLibCalls.cpp
@@ -1061,6 +1061,46 @@
   return Ret;
 }
 
+static Value *getPow(Value *pow1, unsigned Exp, IRBuilder<> &B) {
+  // Pre-compute Addition Chains for each exponent upto 32
+  // Refer: http://wwwhomes.uni-bielefeld.de/achim/addition_chain.html
+
+  Value *AddChain[33];
+  AddChain[1]  = pow1;
+  AddChain[2]  = B.CreateFMul(pow1, pow1);
+  AddChain[3]  = B.CreateFMul(AddChain[1],  AddChain[2]);
+  AddChain[4]  = B.CreateFMul(AddChain[2],  AddChain[2]);
+  AddChain[5]  = B.CreateFMul(AddChain[2],  AddChain[3]);
+  AddChain[6]  = B.CreateFMul(AddChain[3],  AddChain[3]);
+  AddChain[7]  = B.CreateFMul(AddChain[2],  AddChain[5]);
+  AddChain[8]  = B.CreateFMul(AddChain[4],  AddChain[4]);
+  AddChain[9]  = B.CreateFMul(AddChain[1],  AddChain[8]);
+  AddChain[10] = B.CreateFMul(AddChain[5],  AddChain[5]);
+  AddChain[11] = B.CreateFMul(AddChain[1],  AddChain[10]);
+  AddChain[12] = B.CreateFMul(AddChain[6],  AddChain[6]);
+  AddChain[13] = B.CreateFMul(AddChain[4],  AddChain[9]);
+  AddChain[14] = B.CreateFMul(AddChain[7],  AddChain[7]);
+  AddChain[15] = B.CreateFMul(AddChain[3],  AddChain[12]);
+  AddChain[16] = B.CreateFMul(AddChain[8],  AddChain[8]);
+  AddChain[17] = B.CreateFMul(AddChain[8],  AddChain[9]);
+  AddChain[18] = B.CreateFMul(AddChain[2],  AddChain[16]);
+  AddChain[19] = B.CreateFMul(AddChain[1],  AddChain[18]);
+  AddChain[20] = B.CreateFMul(AddChain[10], AddChain[10]);
+  AddChain[21] = B.CreateFMul(AddChain[6],  AddChain[15]);
+  AddChain[22] = B.CreateFMul(AddChain[11], AddChain[11]);
+  AddChain[23] = B.CreateFMul(AddChain[3],  AddChain[20]);
+  AddChain[24] = B.CreateFMul(AddChain[12], AddChain[12]);
+  AddChain[25] = B.CreateFMul(AddChain[8],  AddChain[17]);
+  AddChain[26] = B.CreateFMul(AddChain[13], AddChain[13]);
+  AddChain[27] = B.CreateFMul(AddChain[3],  AddChain[24]);
+  AddChain[28] = B.CreateFMul(AddChain[14], AddChain[14]);
+  AddChain[29] = B.CreateFMul(AddChain[4],  AddChain[25]);
+  AddChain[30] = B.CreateFMul(AddChain[15], AddChain[15]);
+  AddChain[31] = B.CreateFMul(AddChain[3],  AddChain[28]);
+  AddChain[32] = B.CreateFMul(AddChain[16], AddChain[16]);
+  return AddChain[Exp];
+}
+
 Value *LibCallSimplifier::optimizePow(CallInst *CI, IRBuilder<> &B) {
   Function *Callee = CI->getCalledFunction();
   Value *Ret = nullptr;
@@ -1154,6 +1194,27 @@
     return B.CreateFMul(Op1, Op1, "pow2");
   if (Op2C->isExactlyValue(-1.0)) // pow(x, -1.0) -> 1.0/x
     return B.CreateFDiv(ConstantFP::get(CI->getType(), 1.0), Op1, "powrecip");
+
+  // Only in fast-math mode, generate repeated fmul instead of generating
+  // pow(x, n).
+  if (canUseUnsafeFPMath(CI->getParent()->getParent())) {
+    APFloat V = abs(Op2C->getValueAPF());
+    // We limit to a max of 7 fmul(s). Thus max exponent is 32.
+    // This transformation applies to integer exponents only.
+    if (V.compare(APFloat(V.getSemantics(), 32.0)) ==
+        APFloat::cmpGreaterThan || !V.isInteger())
+      return nullptr;
+    // We cannot readily convert a non-double type (like float) to a double.
+    // So we first convert V to something which could be converted to double.
+    bool ignored;
+    V.convert(APFloat::IEEEdouble, APFloat::rmTowardZero, &ignored);
+    Value *FMul = getPow(Op1, V.convertToDouble(), B);
+    // For negative exponents simply compute the reciprocal.
+    if (Op2C->isNegative())
+      FMul = B.CreateFDiv(ConstantFP::get(CI->getType(), 1.0), FMul);
+    return FMul;
+  }
+
   return nullptr;
 }
 


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D13994.40421.patch
Type: text/x-patch
Size: 3679 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20151117/dafa4b45/attachment.bin>


More information about the llvm-commits mailing list