[llvm] Fdim constant fold (PR #109235)

Matt Arsenault via llvm-commits llvm-commits at lists.llvm.org
Thu Sep 19 21:53:16 PDT 2024


================
@@ -3080,6 +3080,41 @@ Value *LibCallSimplifier::optimizeRemquo(CallInst *CI, IRBuilderBase &B) {
   return ConstantFP::get(CI->getType(), Rem);
 }
 
+/// Constant folds fdim
+Value *LibCallSimplifier::optimizeFdim(CallInst *CI, IRBuilderBase &B) {
+  const APFloat *X, *Y;
+  // Check if both values are constants
+  if (!match(CI->getArgOperand(0), m_APFloat(X)) ||
+      !match(CI->getArgOperand(1), m_APFloat(Y)))
+    return nullptr;
+  // If either argument is NaN, NaN is returned
+  if (X->isNaN() || Y->isNaN())
+    return ConstantFP::getQNaN(CI->getType());
+
+  // If the difference if negative, return +0.0
+  if (*X <= *Y)
+    return ConstantFP::get(CI->getType(), 0.0);
+
+  APFloat ReturnVal = *X;
+  APFloat::opStatus Status =
+      ReturnVal.subtract(*Y, RoundingMode::NearestTiesToEven);
+  switch (Status) {
+  case APFloat::opStatus::opOK:
+    break;
+  case APFloat::opStatus::opOverflow:
+    return ConstantFP::get(
+        CI->getType(),
+        APFloat::getLargest(X->getSemantics(), /*Negative=*/false));
----------------
arsenm wrote:

The special cases also set errno, in which case we cannot perform the fold unless the call is memory(none) 

https://github.com/llvm/llvm-project/pull/109235


More information about the llvm-commits mailing list