diff --git a/clang/lib/CIR/CodeGen/CIRGenBuilder.h b/clang/lib/CIR/CodeGen/CIRGenBuilder.h index 8e25c4ac7acb..d451c40ae901 100644 --- a/clang/lib/CIR/CodeGen/CIRGenBuilder.h +++ b/clang/lib/CIR/CodeGen/CIRGenBuilder.h @@ -557,7 +557,9 @@ class CIRGenBuilderTy : public mlir::OpBuilder { llvm_unreachable("negation for the given type is NYI"); } - mlir::Value createFPExt(mlir::Value v, mlir::Type destType) { + // TODO: split this to createFPExt/createFPTrunc when we have dedicated cast + // operations. + mlir::Value createFloatingCast(mlir::Value v, mlir::Type destType) { if (getIsFPConstrained()) llvm_unreachable("constrainedfp NYI"); diff --git a/clang/lib/CIR/CodeGen/CIRGenExprScalar.cpp b/clang/lib/CIR/CodeGen/CIRGenExprScalar.cpp index 9f467aae7f5b..f756ff1e0224 100644 --- a/clang/lib/CIR/CodeGen/CIRGenExprScalar.cpp +++ b/clang/lib/CIR/CodeGen/CIRGenExprScalar.cpp @@ -1670,11 +1670,10 @@ mlir::Value ScalarExprEmitter::buildScalarCast( return Builder.create( Src.getLoc(), DstTy, mlir::cir::CastKind::float_to_int, Src); } else if (DstElementTy.isa()) { + // TODO: split this to createFPExt/createFPTrunc auto FloatDstTy = DstTy.cast(); auto FloatSrcTy = SrcTy.cast(); - if (FloatDstTy.getWidth() < FloatSrcTy.getWidth()) - llvm_unreachable("NYI: narrowing floating-point cast"); - return Builder.createFPExt(Src, DstTy); + return Builder.createFloatingCast(Src, DstTy); } else { llvm_unreachable("Unexpected destination type for scalar cast"); } diff --git a/clang/test/CIR/CodeGen/cast.cpp b/clang/test/CIR/CodeGen/cast.cpp index 0ebd680322cb..f01de927f6ff 100644 --- a/clang/test/CIR/CodeGen/cast.cpp +++ b/clang/test/CIR/CodeGen/cast.cpp @@ -17,7 +17,7 @@ unsigned char cxxstaticcast_0(unsigned int x) { // CHECK: } -int cStyleCasts_0(unsigned x1, int x2, float x3, short x4) { +int cStyleCasts_0(unsigned x1, int x2, float x3, short x4, double x5) { // CHECK: cir.func @_{{.*}}cStyleCasts_0{{.*}} char a = (char)x1; // truncate @@ -68,11 +68,14 @@ int cStyleCasts_0(unsigned x1, int x2, float x3, short x4) { unsigned fptoui = (unsigned)x3; // Floating point to unsigned integer // CHECK: %{{.+}} = cir.cast(float_to_int, %{{[0-9]+}} : f32), !u32i - bool x5 = (bool)x1; // No checking, because this isn't a cast. + bool ib = (bool)x1; // No checking, because this isn't a cast. - int bi = (int)x5; // bool to int + int bi = (int)ib; // bool to int // CHECK: %{{[0-9]+}} = cir.cast(bool_to_int, %{{[0-9]+}} : !cir.bool), !s32i + float dptofp = (float)x5; + // CHECK: %{{.+}} = cir.cast(floating, %{{[0-9]+}} : f64), f32 + return 0; } diff --git a/clang/test/CIR/Lowering/cast.cir b/clang/test/CIR/Lowering/cast.cir index 74e176a29f10..70420c63d8f8 100644 --- a/clang/test/CIR/Lowering/cast.cir +++ b/clang/test/CIR/Lowering/cast.cir @@ -10,7 +10,7 @@ !u64i = !cir.int module { - cir.func @cStyleCasts(%arg0: !u32i, %arg1: !s32i, %arg2: f32) -> !s32i { + cir.func @cStyleCasts(%arg0: !u32i, %arg1: !s32i, %arg2: f32, %arg3: f64) -> !s32i { // CHECK: llvm.func @cStyleCasts %0 = cir.alloca !u32i, cir.ptr , ["x1", init] {alignment = 4 : i64} %1 = cir.alloca !s32i, cir.ptr , ["x2", init] {alignment = 4 : i64} @@ -74,6 +74,8 @@ module { %28 = cir.cast(float_to_int, %arg2 : f32), !u32i // CHECK: %{{.+}} = llvm.fptoui %{{.+}} : f32 to i32 %18 = cir.const(#cir.int<0> : !s32i) : !s32i + // CHECK: %{{.+}} = llvm.fptrunc %{{.+}} : f64 to f32 + %34 = cir.cast(floating, %arg3 : f64), f32 cir.store %18, %2 : !s32i, cir.ptr %19 = cir.load %2 : cir.ptr , !s32i