[Mlir-commits] [mlir] [MLIR][Math][GPU] Add lowering of absi and fpowi to libdevice (PR #123422)

William Moses llvmlistbot at llvm.org
Sun Jan 19 12:16:46 PST 2025


================
@@ -132,23 +159,84 @@ struct OpToFuncCallLowering : public ConvertOpToLLVMPattern<SourceOp> {
     return "";
   }
 
-  LLVM::LLVMFuncOp appendOrGetFuncOp(StringRef funcName, Type funcType,
-                                     Operation *op) const {
-    using LLVM::LLVMFuncOp;
+  const std::string f32Func;
+  const std::string f64Func;
+  const std::string f32ApproxFunc;
+  const std::string f16Func;
+};
 
-    auto funcAttr = StringAttr::get(op->getContext(), funcName);
-    Operation *funcOp = SymbolTable::lookupNearestSymbolFrom(op, funcAttr);
-    if (funcOp)
-      return cast<LLVMFuncOp>(*funcOp);
+/// Rewriting that replace SourceOp with a CallOp to `i32Func`
+/// The function declaration is added in case it was not added before.
+/// This assumes that all types integral.
+///
+/// Example with NVVM:
+///   %abs_i32 = math.iabs %arg_i32 : i32
+///
+/// will be transformed into
+///   llvm.call @__nv_abs(%arg_i32) : (i32) -> i32
+///
+template <typename SourceOp>
+struct IntOpToFuncCallLowering
+    : public OpToFuncCallLoweringBase<SourceOp,
+                                      IntOpToFuncCallLowering<SourceOp>> {
+public:
+  explicit IntOpToFuncCallLowering(const LLVMTypeConverter &lowering,
+                                   StringRef i32Func)
+      : OpToFuncCallLoweringBase<SourceOp, IntOpToFuncCallLowering<SourceOp>>(
+            lowering),
+        i32Func(i32Func) {}
 
-    mlir::OpBuilder b(op->getParentOfType<FunctionOpInterface>());
-    return b.create<LLVMFuncOp>(op->getLoc(), funcName, funcType);
+  Value maybeCast(Value operand, PatternRewriter &rewriter) const {
+    return operand;
+  }
+
+  StringRef getFunctionName(Type type, SourceOp op) const {
+    IntegerType itype = dyn_cast<IntegerType>(type);
+    if (!itype || itype.getWidth() != 32)
+      return "";
+    return i32Func;
+  }
+
+  const std::string i32Func;
+};
+
+/// Rewriting that replaces SourceOp with a CallOp to `f32Func` or `f64Func`,
+/// depending on the type of the result. This assumes that the first argument is
+/// a floating type and the second argument is an integer type.
+///
+/// Example with NVVM:
+///   %result32 = math.fpowi %arg_f32, %arg_i32 : f32, i32
+///
+/// will be transformed into
+///   llvm.call @__nv_powf(%arg_f32, %arg_i32) : (f32, i32) -> f32
+///
+template <typename SourceOp>
+struct FloatIntOpToFuncCallLowering
----------------
wsmoses wrote:

yeah the optofunccalllowering checks if input types are valid floats (saying it doesnt apply otherwise) whereas here we check if it's a 32bit integer (the only supported input)

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


More information about the Mlir-commits mailing list