]> granicus.if.org Git - clang/commitdiff
[Intrinsics] Merge lround.i32 and lround.i64 into a single intrinsic with overloaded...
authorCraig Topper <craig.topper@intel.com>
Mon, 20 May 2019 16:27:09 +0000 (16:27 +0000)
committerCraig Topper <craig.topper@intel.com>
Mon, 20 May 2019 16:27:09 +0000 (16:27 +0000)
We shouldn't really make assumptions about possible sizes for long and long long. And longer term we should probably support vectorizing these intrinsics. By making the result types not fixed we can support vectors as well.

Differential Revision: https://reviews.llvm.org/D62026

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@361169 91177308-0d34-0410-b5e6-96231b3b80d8

lib/CodeGen/CGBuiltin.cpp
test/CodeGen/math-builtins.c
test/CodeGen/math-libcalls.c

index 43963576dacf1d0743391d9f70f5e82c498a1f56..6a18312907359f486a74204826e1ac61261badc5 100644 (file)
@@ -391,6 +391,18 @@ static Value *emitFPIntBuiltin(CodeGenFunction &CGF,
   return CGF.Builder.CreateCall(F, {Src0, Src1});
 }
 
+// Emit an intrinsic that has overloaded integer result and fp operand.
+static Value *emitFPToIntRoundBuiltin(CodeGenFunction &CGF,
+                                      const CallExpr *E,
+                                      unsigned IntrinsicID) {
+   llvm::Type *ResultType = CGF.ConvertType(E->getType());
+   llvm::Value *Src0 = CGF.EmitScalarExpr(E->getArg(0));
+
+   Function *F = CGF.CGM.getIntrinsic(IntrinsicID,
+                                      {ResultType, Src0->getType()});
+   return CGF.Builder.CreateCall(F, Src0);
+}
+
 /// EmitFAbs - Emit a call to @llvm.fabs().
 static Value *EmitFAbs(CodeGenFunction &CGF, Value *V) {
   Function *F = CGF.CGM.getIntrinsic(Intrinsic::fabs, V->getType());
@@ -1726,13 +1738,8 @@ RValue CodeGenFunction::EmitBuiltinExpr(const GlobalDecl GD, unsigned BuiltinID,
     case Builtin::BIlroundl:
     case Builtin::BI__builtin_lround:
     case Builtin::BI__builtin_lroundf:
-    case Builtin::BI__builtin_lroundl: {
-      llvm::Type *ResultType = ConvertType(E->getType());
-      int Width = ResultType->getPrimitiveSizeInBits();
-      return RValue::get(emitUnaryBuiltin(*this, E,
-                                          Width == 32 ? Intrinsic::lround_i32
-                                                      : Intrinsic::lround_i64));
-    }
+    case Builtin::BI__builtin_lroundl:
+      return RValue::get(emitFPToIntRoundBuiltin(*this, E, Intrinsic::lround));
 
     case Builtin::BIllround:
     case Builtin::BIllroundf:
@@ -1740,7 +1747,7 @@ RValue CodeGenFunction::EmitBuiltinExpr(const GlobalDecl GD, unsigned BuiltinID,
     case Builtin::BI__builtin_llround:
     case Builtin::BI__builtin_llroundf:
     case Builtin::BI__builtin_llroundl:
-      return RValue::get(emitUnaryBuiltin(*this, E, Intrinsic::llround));
+      return RValue::get(emitFPToIntRoundBuiltin(*this, E, Intrinsic::llround));
 
     default:
       break;
index 83e3d4a2929a3de2fd86b6365eaf9dc7f2884b2d..cb31288496a730aef3a0dd9f2e04c59b903466af 100644 (file)
@@ -362,9 +362,9 @@ void foo(double *d, float f, float *fp, long double *l, int *i, const char *c) {
 
   __builtin_llround(f);    __builtin_llroundf(f);   __builtin_llroundl(f);
 
-// NO__ERRNO: declare i64 @llvm.llround.f64(double) [[READNONE_INTRINSIC]]
-// NO__ERRNO: declare i64 @llvm.llround.f32(float) [[READNONE_INTRINSIC]]
-// NO__ERRNO: declare i64 @llvm.llround.f80(x86_fp80) [[READNONE_INTRINSIC]]
+// NO__ERRNO: declare i64 @llvm.llround.i64.f64(double) [[READNONE_INTRINSIC]]
+// NO__ERRNO: declare i64 @llvm.llround.i64.f32(float) [[READNONE_INTRINSIC]]
+// NO__ERRNO: declare i64 @llvm.llround.i64.f80(x86_fp80) [[READNONE_INTRINSIC]]
 // HAS_ERRNO: declare i64 @llround(double) [[NOT_READNONE]]
 // HAS_ERRNO: declare i64 @llroundf(float) [[NOT_READNONE]]
 // HAS_ERRNO: declare i64 @llroundl(x86_fp80) [[NOT_READNONE]]
index 176ff38972ddd33834132fe0c8b1e3842aa13372..405597e1f03192f9eef3847da7d06983b102aec4 100644 (file)
@@ -317,9 +317,9 @@ void foo(double *d, float f, float *fp, long double *l, int *i, const char *c) {
 
   llround(f);    llroundf(f);   llroundl(f);
 
-// NO__ERRNO: declare i64 @llvm.llround.f64(double) [[READNONE_INTRINSIC]]
-// NO__ERRNO: declare i64 @llvm.llround.f32(float) [[READNONE_INTRINSIC]]
-// NO__ERRNO: declare i64 @llvm.llround.f80(x86_fp80) [[READNONE_INTRINSIC]]
+// NO__ERRNO: declare i64 @llvm.llround.i64.f64(double) [[READNONE_INTRINSIC]]
+// NO__ERRNO: declare i64 @llvm.llround.i64.f32(float) [[READNONE_INTRINSIC]]
+// NO__ERRNO: declare i64 @llvm.llround.i64.f80(x86_fp80) [[READNONE_INTRINSIC]]
 // HAS_ERRNO: declare i64 @llround(double) [[NOT_READNONE]]
 // HAS_ERRNO: declare i64 @llroundf(float) [[NOT_READNONE]]
 // HAS_ERRNO: declare i64 @llroundl(x86_fp80) [[NOT_READNONE]]