llvmbot wrote:

<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-clang

Author: Yeongu Choe (YeonguChoe)

<details>
<summary>Changes</summary>

BI__builtin_fpclassify function is not implemented in ClangIR, so fpclassify 
cannot be used at the moment with ClangIR. I implemented BI__builtin_fpclassify 
so that fpclassify can use builtin_fpclassify.

---
Full diff: https://github.com/llvm/llvm-project/pull/183893.diff


2 Files Affected:

- (modified) clang/lib/CIR/CodeGen/CIRGenBuiltin.cpp (+64-2) 
- (modified) clang/test/CIR/CodeGenBuiltins/builtins-floating-point.c (+7) 


``````````diff
diff --git a/clang/lib/CIR/CodeGen/CIRGenBuiltin.cpp 
b/clang/lib/CIR/CodeGen/CIRGenBuiltin.cpp
index 86d34be0a311c..5eee7a522331c 100644
--- a/clang/lib/CIR/CodeGen/CIRGenBuiltin.cpp
+++ b/clang/lib/CIR/CodeGen/CIRGenBuiltin.cpp
@@ -1544,8 +1544,70 @@ RValue CIRGenFunction::emitBuiltinExpr(const GlobalDecl 
&gd, unsigned builtinID,
   case Builtin::BI__builtin_isinf_sign:
   case Builtin::BI__builtin_flt_rounds:
   case Builtin::BI__builtin_set_flt_rounds:
-  case Builtin::BI__builtin_fpclassify:
-    return errorBuiltinNYI(*this, e, builtinID);
+  case Builtin::BI__builtin_fpclassify: {
+    CIRGenFunction::CIRGenFPOptionsRAII FPOptsRAII(*this, e);
+    mlir::Location Loc = getLoc(e->getBeginLoc());
+
+    mlir::Value NanLiteral = emitScalarExpr(e->getArg(0));
+    mlir::Value InfinityLiteral = emitScalarExpr(e->getArg(1));
+    mlir::Value NormalLiteral = emitScalarExpr(e->getArg(2));
+    mlir::Value SubnormalLiteral = emitScalarExpr(e->getArg(3));
+    mlir::Value ZeroLiteral = emitScalarExpr(e->getArg(4));
+    mlir::Value V = emitScalarExpr(e->getArg(5));
+
+    mlir::Type ResultTy = convertType(e->getType());
+    mlir::Block *EntryBlock = builder.getInsertionBlock();
+    mlir::Region *Region = EntryBlock->getParent();
+
+    // Create Blocks
+    mlir::Block *InfinityBlock = builder.createBlock(Region, Region->end());
+    mlir::Block *NormalBlock = builder.createBlock(Region, Region->end());
+    mlir::Block *SubnormalBlock = builder.createBlock(Region, Region->end());
+    mlir::Block *ZeroBlock = builder.createBlock(Region, Region->end());
+    mlir::Block *EndBlock = builder.createBlock(Region, Region->end());
+    EndBlock->addArgument(ResultTy, Loc);
+
+    // ^EntryBlock
+    builder.setInsertionPointToEnd(EntryBlock);
+    mlir::Value IsNan = builder.createIsFPClass(Loc, V, cir::FPClassTest::Nan);
+    cir::BrCondOp::create(builder, Loc, IsNan, EndBlock,
+                          InfinityBlock, // destTrue, destFalse
+                          mlir::ValueRange{NanLiteral},
+                          mlir::ValueRange{}); // operandsTrue, operandsFalse
+
+    // ^InfinityBlock
+    builder.setInsertionPointToEnd(InfinityBlock);
+    mlir::Value IsInfinity =
+        builder.createIsFPClass(Loc, V, cir::FPClassTest::Infinity);
+    cir::BrCondOp::create(builder, Loc, IsInfinity, EndBlock, NormalBlock,
+                          mlir::ValueRange{InfinityLiteral},
+                          mlir::ValueRange{});
+
+    // ^NormalBlock
+    builder.setInsertionPointToEnd(NormalBlock);
+    mlir::Value IsNormal =
+        builder.createIsFPClass(Loc, V, cir::FPClassTest::Normal);
+    cir::BrCondOp::create(builder, Loc, IsNormal, EndBlock, SubnormalBlock,
+                          mlir::ValueRange{NormalLiteral}, mlir::ValueRange{});
+
+    // ^SubnormalBlock
+    builder.setInsertionPointToEnd(SubnormalBlock);
+    mlir::Value IsSubnormal =
+        builder.createIsFPClass(Loc, V, cir::FPClassTest::Subnormal);
+    cir::BrCondOp::create(builder, Loc, IsSubnormal, EndBlock, ZeroBlock,
+                          mlir::ValueRange{SubnormalLiteral},
+                          mlir::ValueRange{});
+
+    // ^ZeroBlock
+    builder.setInsertionPointToEnd(ZeroBlock);
+    cir::BrOp::create(builder, Loc, EndBlock, mlir::ValueRange{ZeroLiteral});
+
+    // ^EndBlock(x)
+    builder.setInsertionPointToEnd(EndBlock);
+    mlir::Value Result = EndBlock->getArgument(0);
+
+    return RValue::get(Result);
+  }
   case Builtin::BIalloca:
   case Builtin::BI_alloca:
   case Builtin::BI__builtin_alloca_uninitialized:
diff --git a/clang/test/CIR/CodeGenBuiltins/builtins-floating-point.c 
b/clang/test/CIR/CodeGenBuiltins/builtins-floating-point.c
index be82137427ea2..f63ec9b4c76e9 100644
--- a/clang/test/CIR/CodeGenBuiltins/builtins-floating-point.c
+++ b/clang/test/CIR/CodeGenBuiltins/builtins-floating-point.c
@@ -2210,3 +2210,10 @@ double my_roundeven(double x) {
   // OGCG: define{{.*}}@my_roundeven(
   // OGCG: call double @llvm.roundeven.f64(
 }
+
+int fpclassify(float f) {
+  return __builtin_fpclassify(0, 1, 2, 3, 4, f);
+  // CIR: %{{.*}} = cir.is_fp_class %{{.*}}, fcNan : (!cir.float) -> !cir.bool
+  // LLVM: %{{.*}} = call i1 @llvm.is.fpclass.f32(float %{{.*}}, i32 {{.*}})
+  // OGCG: %{{.*}} = fcmp uno float %{{.*}}, %{{.*}}
+}
\ No newline at end of file

``````````

</details>


https://github.com/llvm/llvm-project/pull/183893
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to