mirror of
https://github.com/KhronosGroup/OpenCL-CTS.git
synced 2026-03-19 06:09:01 +00:00
fix several compile issues with Visual Studio toolchains (#2219)
Fixes several compile issues I am seeing for my version of Visual Studio related to an ambiguous call to `fpclassify`, which is called by `isnan` and other similar functions, specifically for the `cl_half` type: ``` 19>C:\Program Files (x86)\Windows Kits\10\Include\10.0.19041.0\ucrt\corecrt_math.h(401,1): error C2668: 'fpclassify': ambiguous call to overloaded function 19>C:\Program Files (x86)\Windows Kits\10\Include\10.0.19041.0\ucrt\corecrt_math.h(298,31): message : could be 'int fpclassify(long double) throw()' 19>C:\Program Files (x86)\Windows Kits\10\Include\10.0.19041.0\ucrt\corecrt_math.h(293,31): message : or 'int fpclassify(double) throw()' 19>C:\Program Files (x86)\Windows Kits\10\Include\10.0.19041.0\ucrt\corecrt_math.h(288,31): message : or 'int fpclassify(float) throw()' 19>C:\Program Files (x86)\Windows Kits\10\Include\10.0.19041.0\ucrt\corecrt_math.h(401,1): message : while trying to match the argument list '(_Ty)' ``` Some of these issues seem like differences in compiler behavior, but at least one appears to have identified a legitimate bug. Specifically, this change: * Removes the special-case checks for finite half numbers for commonfns, since this is already handled by `UlpFn`. (test with: `test_commonfns degrees radians`) * Assigns to temporary variables to eliminate the ambiguous function call for relationals. (test with: `test_relationals relational*`) * Properly converts from half to float when checking for NaNs for select. This is the one that seems like a legitimate bug. (test with: `test_select select_half_ushort select_half_short`) * Uses `std::enable_if` to disambiguate a function call for spirv_new. (test with: `test_spirv_new decorate_saturated*`) If it's helpful, my specific Visual Studio version is: ``` Microsoft Visual Studio Professional 2019 Version 16.11.20 VisualStudio.16.Release/16.11.20+32929.386 ``` I also have the Windows Software Development Kit 10.0.19041.685 installed.
This commit is contained in:
@@ -182,27 +182,6 @@ template <typename T> inline half conv_to_half(const T &val)
|
||||
return 0;
|
||||
}
|
||||
|
||||
template <typename T> bool isfinite_fp(const T &v)
|
||||
{
|
||||
if (std::is_same<T, half>::value)
|
||||
{
|
||||
// Extract FP16 exponent and mantissa
|
||||
uint16_t h_exp = (((half)v) >> (CL_HALF_MANT_DIG - 1)) & 0x1F;
|
||||
uint16_t h_mant = ((half)v) & 0x3FF;
|
||||
|
||||
// !Inf test
|
||||
return !(h_exp == 0x1F && h_mant == 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
#if !defined(_WIN32)
|
||||
return std::isfinite(v);
|
||||
#else
|
||||
return isfinite(v);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
template <typename T> float UlpFn(const T &val, const double &r)
|
||||
{
|
||||
if (std::is_same<T, half>::value)
|
||||
|
||||
@@ -65,10 +65,6 @@ int verify_degrees(const T *const inptr, const T *const outptr, int n)
|
||||
{
|
||||
r = (180.0 / M_PI) * conv_to_dbl(inptr[i]);
|
||||
|
||||
if (std::is_same<T, half>::value)
|
||||
if (!isfinite_fp(conv_to_half(r)) && !isfinite_fp(outptr[i]))
|
||||
continue;
|
||||
|
||||
error = UlpFn(outptr[i], r);
|
||||
|
||||
if (fabsf(error) > max_error)
|
||||
@@ -115,10 +111,6 @@ int verify_radians(const T *const inptr, const T *const outptr, int n)
|
||||
{
|
||||
r = (M_PI / 180.0) * conv_to_dbl(inptr[i]);
|
||||
|
||||
if (std::is_same<T, half>::value)
|
||||
if (!isfinite_fp(conv_to_half(r)) && !isfinite_fp(outptr[i]))
|
||||
continue;
|
||||
|
||||
error = UlpFn(outptr[i], r);
|
||||
|
||||
if (fabsf(error) > max_error)
|
||||
|
||||
@@ -368,8 +368,9 @@ int RelationalsFPTest::test_equiv_kernel(unsigned int vecSize,
|
||||
{
|
||||
if (gInfNanSupport == 0)
|
||||
{
|
||||
if (isnan(inDataA[i * vecSize + j])
|
||||
|| isnan(inDataB[i * vecSize + j]))
|
||||
float a = inDataA[i * vecSize + j];
|
||||
float b = inDataB[i * vecSize + j];
|
||||
if (isnan(a) || isnan(b))
|
||||
fail = 0;
|
||||
else
|
||||
fail = 1;
|
||||
|
||||
@@ -18,6 +18,7 @@
|
||||
#include <stdio.h>
|
||||
#include <cinttypes>
|
||||
#include "test_select.h"
|
||||
#include "CL/cl_half.h"
|
||||
|
||||
|
||||
//-----------------------------------------
|
||||
@@ -830,10 +831,12 @@ size_t check_half(const void *const test, const void *const correct,
|
||||
|
||||
if (memcmp(t, c, count * sizeof(c[0])) != 0)
|
||||
{
|
||||
for (i = 0; i < count; i++) /* Allow nans to be binary different */
|
||||
if ((t[i] != c[i])
|
||||
&& !(isnan(((cl_half *)correct)[i])
|
||||
&& isnan(((cl_half *)test)[i])))
|
||||
// Allow nans to be binary different
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
float fcorrect = cl_half_to_float(c[i]);
|
||||
float ftest = cl_half_to_float(t[i]);
|
||||
if ((t[i] != c[i]) && !(isnan(fcorrect) && isnan(ftest)))
|
||||
{
|
||||
log_error("\n(check_half) Error for vector size %zu found at "
|
||||
"0x%8.8zx (of 0x%8.8zx): "
|
||||
@@ -841,6 +844,7 @@ size_t check_half(const void *const test, const void *const correct,
|
||||
vector_size, i, count, c[i], t[i]);
|
||||
return i + 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
@@ -855,9 +859,12 @@ size_t check_float(const void *const test, const void *const correct,
|
||||
|
||||
if (memcmp(t, c, count * sizeof(c[0])) != 0)
|
||||
{
|
||||
for (i = 0; i < count; i++) /* Allow nans to be binary different */
|
||||
if ((t[i] != c[i])
|
||||
&& !(isnan(((float *)correct)[i]) && isnan(((float *)test)[i])))
|
||||
// Allow nans to be binary different
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
float fcorrect = ((float *)correct)[i];
|
||||
float ftest = ((float *)test)[i];
|
||||
if ((t[i] != c[i]) && !(isnan(fcorrect) && isnan(ftest)))
|
||||
{
|
||||
log_error("\n(check_float) Error for vector size %zu found at "
|
||||
"0x%8.8zx (of 0x%8.8zx): "
|
||||
@@ -865,6 +872,7 @@ size_t check_float(const void *const test, const void *const correct,
|
||||
vector_size, i, count, c[i], t[i]);
|
||||
return i + 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
#include <algorithm>
|
||||
#include <limits>
|
||||
#include <cmath>
|
||||
#include <type_traits>
|
||||
|
||||
#include <CL/cl_half.h>
|
||||
|
||||
@@ -216,29 +217,37 @@ static inline Ti generate_saturated_rhs_input(RandomSeed &seed)
|
||||
}
|
||||
|
||||
template <typename Ti, typename Tl, typename To>
|
||||
static inline To compute_saturated_output(Ti lhs, Ti rhs,
|
||||
cl_half_rounding_mode half_rounding)
|
||||
static inline
|
||||
typename std::enable_if<std::is_same<Ti, cl_half>::value, To>::type
|
||||
compute_saturated_output(Ti lhs, Ti rhs,
|
||||
cl_half_rounding_mode half_rounding)
|
||||
{
|
||||
constexpr auto loVal = std::numeric_limits<To>::min();
|
||||
constexpr auto hiVal = std::numeric_limits<To>::max();
|
||||
|
||||
if (std::is_same<Ti, cl_half>::value)
|
||||
cl_float f = cl_half_to_float(lhs) * cl_half_to_float(rhs);
|
||||
|
||||
// Quantize to fp16:
|
||||
f = cl_half_to_float(cl_half_from_float(f, half_rounding));
|
||||
|
||||
To val = static_cast<To>(std::min<float>(std::max<float>(f, loVal), hiVal));
|
||||
if (isnan(cl_half_to_float(rhs)))
|
||||
{
|
||||
cl_float f = cl_half_to_float(lhs) * cl_half_to_float(rhs);
|
||||
|
||||
// Quantize to fp16:
|
||||
f = cl_half_to_float(cl_half_from_float(f, half_rounding));
|
||||
|
||||
To val = (To)std::min<float>(std::max<float>(f, loVal), hiVal);
|
||||
if (isnan(cl_half_to_float(rhs)))
|
||||
{
|
||||
val = 0;
|
||||
}
|
||||
return val;
|
||||
val = 0;
|
||||
}
|
||||
return val;
|
||||
}
|
||||
|
||||
Tl ival = (Tl)(lhs * rhs);
|
||||
To val = (To)std::min<Ti>(std::max<Ti>(ival, loVal), hiVal);
|
||||
template <typename Ti, typename Tl, typename To>
|
||||
static inline
|
||||
typename std::enable_if<!std::is_same<Ti, cl_half>::value, To>::type
|
||||
compute_saturated_output(Ti lhs, Ti rhs, cl_half_rounding_mode)
|
||||
{
|
||||
constexpr auto loVal = std::numeric_limits<To>::min();
|
||||
constexpr auto hiVal = std::numeric_limits<To>::max();
|
||||
|
||||
Tl ival = static_cast<Tl>(lhs * rhs);
|
||||
To val = static_cast<To>(std::min<Tl>(std::max<Tl>(ival, loVal), hiVal));
|
||||
|
||||
if (isnan(rhs))
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user