From 5011159d3b21a80a3db632c1ef8ff543bbcdc0a7 Mon Sep 17 00:00:00 2001 From: Rex Xu Date: Mon, 20 Nov 2023 14:55:06 +0800 Subject: [PATCH] Revert the PR#2804 handling specials input of fract(x) This change reverts the PR https://github.com/GPUOpen-Drivers/llpc/pull/2804. After SPIR-V workgroup discussed the issues of fract(x), they decide to align fract(-0.0), fract(-INF), and fract(INF) with DXIL's definitions. Our original implementation is fine enough to meet the spec requirements. --- llpc/translator/lib/SPIRV/SPIRVReader.cpp | 37 ++--------------------- 1 file changed, 2 insertions(+), 35 deletions(-) diff --git a/llpc/translator/lib/SPIRV/SPIRVReader.cpp b/llpc/translator/lib/SPIRV/SPIRVReader.cpp index dd9f405d31..388684f6a0 100644 --- a/llpc/translator/lib/SPIRV/SPIRVReader.cpp +++ b/llpc/translator/lib/SPIRV/SPIRVReader.cpp @@ -9311,42 +9311,9 @@ Value *SPIRVToLLVM::transGLSLExtInst(SPIRVExtInst *extInst, BasicBlock *bb) { // Round up to whole number return getBuilder()->CreateUnaryIntrinsic(Intrinsic::ceil, args[0]); - case GLSLstd450Fract: { + case GLSLstd450Fract: // Get fractional part - auto fract = getBuilder()->CreateFract(args[0]); - - // NOTE: Although SPIR-V spec says nothing about such cases: fract(-0.0), fract(+INF), fract(-INF), OpenCL spec does - // have following definitions: - // - // fract(-0.0) = -0.0 - // fract(+INF) = +0.0 - // fract(-INF) = -0.0 - // - // When we follow it, we have two issues that are similar to modf(x): - // - // 1. When we input x=+INF/-INF to above formula, we finally get the computation of (-INF) + INF or INF - INF. - // The result is NaN returned by HW. - // 2. When we input x=-0.0 to above formula, we finally get the addition of (-0.0) + 0.0. The result is +0.0 - // returned by HW. - // - // Hence, we have to manually check those special cases: - // - // y = fract(x) - // y = x == -0.0 || x == INF ? copysign(0.0, x) : y, when either NSZ or NoInfs is not present - unsigned checkFlags = 0; - if (!getBuilder()->getFastMathFlags().noSignedZeros()) - checkFlags |= lgc::Builder::CmpClass::NegativeZero; - if (!getBuilder()->getFastMathFlags().noInfs()) - checkFlags |= (lgc::Builder::CmpClass::NegativeZero | lgc::Builder::CmpClass::NegativeZero); - - if (checkFlags) { - Value *isNegZeroOrInf = getBuilder()->createIsFPClass(args[0], checkFlags); - Value *signedZero = getBuilder()->CreateCopySign(ConstantFP::getNullValue(args[0]->getType()), args[0]); - fract = getBuilder()->CreateSelect(isNegZeroOrInf, signedZero, fract); - } - - return fract; - } + return getBuilder()->CreateFract(args[0]); case GLSLstd450Radians: // Convert from degrees to radians