diff --git a/sql-plugin/src/main/scala/com/nvidia/spark/rapids/literals.scala b/sql-plugin/src/main/scala/com/nvidia/spark/rapids/literals.scala index fc6566dc222..cb2e2101f41 100644 --- a/sql-plugin/src/main/scala/com/nvidia/spark/rapids/literals.scala +++ b/sql-plugin/src/main/scala/com/nvidia/spark/rapids/literals.scala @@ -280,10 +280,26 @@ object GpuScalar extends Logging { s" for LongType, expecting Long, or Int.") } case DoubleType => v match { - case d: Double => Scalar.fromDouble(d) - case f: Float => Scalar.fromDouble(f.toDouble) - case _ => throw new IllegalArgumentException(s"'$v: ${v.getClass}' is not supported" + - s" for DoubleType, expecting Double or Float.") + case d: Double => + // cuDF Scalar.fromDouble normalizes -0.0 to 0.0 (see #14116). + if (JDouble.doubleToRawLongBits(d) == JDouble.doubleToRawLongBits(-0.0d)) { + withResource(ColumnVector.fromDoubles(d)) { cv => + cv.getScalarElement(0) + } + } else { + Scalar.fromDouble(d) + } + case f: Float => + val d = f.toDouble + if (JDouble.doubleToRawLongBits(d) == JDouble.doubleToRawLongBits(-0.0d)) { + withResource(ColumnVector.fromDoubles(d)) { cv => + cv.getScalarElement(0) + } + } else { + Scalar.fromDouble(d) + } + case _ => throw new IllegalArgumentException(s"'$v: ${v.getClass}' is not supported" + + s" for DoubleType, expecting Double or Float.") } case TimestampType => v match { // Usually the timestamp will be used by the `add/sub` operators for date/time related @@ -314,7 +330,15 @@ object GpuScalar extends Logging { s" for DateType, expecting Int or LocalDate") } case FloatType => v match { - case f: Float => Scalar.fromFloat(f) + case f: Float => + // cuDF Scalar.fromFloat normalizes -0.0f to 0.0f (see #14116). + if (JFloat.floatToRawIntBits(f) == JFloat.floatToRawIntBits(-0.0f)) { + withResource(ColumnVector.fromFloats(f)) { cv => + cv.getScalarElement(0) + } + } else { + Scalar.fromFloat(f) + } case _ => throw new IllegalArgumentException(s"'$v: ${v.getClass}' is not supported" + s" for FloatType, expecting Float.") } diff --git a/tests/src/test/spark330/scala/org/apache/spark/sql/rapids/utils/RapidsTestSettings.scala b/tests/src/test/spark330/scala/org/apache/spark/sql/rapids/utils/RapidsTestSettings.scala index 085d823d383..2cf300092bf 100644 --- a/tests/src/test/spark330/scala/org/apache/spark/sql/rapids/utils/RapidsTestSettings.scala +++ b/tests/src/test/spark330/scala/org/apache/spark/sql/rapids/utils/RapidsTestSettings.scala @@ -226,7 +226,6 @@ class RapidsTestSettings extends BackendTestSettings { .exclude("SPARK-17515: CollectLimit.execute() should perform per-partition limits", KNOWN_ISSUE("https://github.com/NVIDIA/spark-rapids/issues/14109")) .exclude("SPARK-19650: An action on a Command should not trigger a Spark job", KNOWN_ISSUE("https://github.com/NVIDIA/spark-rapids/issues/14110")) .exclude("SPARK-31594: Do not display the seed of rand/randn with no argument in output schema", ADJUST_UT("Replaced by testRapids version with a correct regex expression to match the projectExplainOutput, randn isn't supported now. See https://github.com/NVIDIA/spark-rapids/issues/11613")) - .exclude("normalize special floating numbers in subquery", KNOWN_ISSUE("https://github.com/NVIDIA/spark-rapids/issues/14116")) .exclude("SPARK-33677: LikeSimplification should be skipped if pattern contains any escapeChar", KNOWN_ISSUE("https://github.com/NVIDIA/spark-rapids/issues/14117")) .exclude("SPARK-33593: Vector reader got incorrect data with binary partition value", KNOWN_ISSUE("https://github.com/NVIDIA/spark-rapids/issues/14118")) .exclude("SPARK-33084: Add jar support Ivy URI in SQL -- jar contains udf class", ADJUST_UT("Replaced by testRapids version that uses testFile() to access Spark test resources instead of getContextClassLoader"))