https://github.com/Icohedron created https://github.com/llvm/llvm-project/pull/188362
Partially addresses https://github.com/llvm/llvm-project/issues/188345. This PR rewrites a small subset of the HLSL intrinsics into TableGen as a reference or example for later intrinsic rewrites. The subset of intrinsics were chosen for the following reasons: - `abs` has two sets of overloads split between aliasing the clang `builtin __builtin_elementwise_abs` and inline identity functions on unsigned integer types. It also operates on 16-bit types and the half type to demonstrate the automatic inclusion of `#ifdef __HLSL_ENABLE_16_BIT` guards and `_HLSL_AVAILABILITY(shadermodel, 6.2)` for 16-bit integer types, and `_HLSL_16BIT_AVAILABILITY(shadermodel, 6.2)` for half types. - `and` demonstrates creating overloads with matrix types, and the ability to restrict the `Varying` type to only booleans. - `cross` aliases two different clang builtins (`__builtin_hlsl_crossf32` and `__builtin_hlsl_crossf16`) and demonstrates the use of fixed vector-type arguments. - `dot` has overloads for all vector types except for double-typed vectors, so the double-typed variant is split into its own scalar-only overload. It also demonstrates the use of `VaryingElemType` to always return the element type for the current overload. - `dot2add` demonstrates the use of `DetailFunc` to create an inline function that calls `__detail::dot2add_impl(A, B, C)`. It also demonstrates the use of fixed-type arguments and return type (both scalar and vector), and the use of the `Availability` field to set the minimum shader model requirement. - `GroupMemoryBarrierWithGroupSync` demonstrates creating an overload with void return type and no arguments, as well as being a wave function that needs to be annotated with `__attribute__((convergent))` by setting the `IsConvergent` field to 1. - `isinf` demonstrates the use of `VaryingShape<T>` to specify a return type that is of the same shape as the Varying type for the current overload but with a fixed element type (`BoolTy` in this case). - The defining of `refract` in TableGen instead of templates introduces some significant changes to error messages and also introduces a new offload test suite failure in the fp16 test because a call to `refract(x, y, 0.5)` where x and y are half-typed vectors is ambiguous due to 0.5 being a 32-bit float literal. The generated `hlsl_alias_intrinsic_gen.inc` and `hlsl_inline_intrinsic_gen.inc` files for this PR can be viewed with this GitHub gist: https://gist.github.com/Icohedron/5ca4e1cc7e811ae72b091472478e9222 They can also be found in the build folder after building Clang, under the paths `lib/clang/23/include/hlsl/hlsl_alias_intrinsics_gen.inc` and `lib/clang/23/include/hlsl/hlsl_inline_intrinsics_gen.inc`. Assisted-by: GitHub Copilot >From d5af8c0c51310bc79957d5858a7ee461392aa1bd Mon Sep 17 00:00:00 2001 From: Deric Cheung <[email protected]> Date: Tue, 24 Mar 2026 14:40:08 -0700 Subject: [PATCH] Rewrite a subset of HLSL intrinsics into TableGen Assisted-by: GitHub Copilot --- clang/include/clang/Basic/HLSLIntrinsics.td | 163 ++++++++- .../lib/Headers/hlsl/hlsl_alias_intrinsics.h | 310 ------------------ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 74 ----- .../test/SemaHLSL/BuiltIns/cross-errors.hlsl | 12 +- .../SemaHLSL/BuiltIns/dot2add-errors.hlsl | 4 +- .../SemaHLSL/BuiltIns/refract-errors.hlsl | 58 ++-- 6 files changed, 192 insertions(+), 429 deletions(-) diff --git a/clang/include/clang/Basic/HLSLIntrinsics.td b/clang/include/clang/Basic/HLSLIntrinsics.td index b205491e6ca78..8811f747f3452 100644 --- a/clang/include/clang/Basic/HLSLIntrinsics.td +++ b/clang/include/clang/Basic/HLSLIntrinsics.td @@ -313,8 +313,163 @@ class HLSLOneArgInlineBuiltin<string name> : HLSLBuiltin<name> { // Intrinsic definitions (sorted alphabetically by function name) //===----------------------------------------------------------------------===// -// TODO: Convert hand-written overloads from hlsl_intrinsics.h and -// hlsl_alias_intrinsics.h into TableGen below. -// Include "hlsl_alias_intrinsics_gen.inc" in hlsl_alias_intrinsics.h -// Include "hlsl_inline_intrinsics_gen.inc" in hlsl_intrinsics.h +// Returns the absolute value of the input value, Val. +def hlsl_abs : HLSLOneArgBuiltin<"abs", "__builtin_elementwise_abs"> { + let Doc = [{ +\fn T abs(T Val) +\brief Returns the absolute value of the input value, \a Val. +\param Val The input value. +}]; + let VaryingTypes = SignedTypes; + let VaryingMatDims = []; +} + +// Unsigned abs is a constexpr identity — unsigned values are already non-negative. +def hlsl_abs_unsigned : HLSLOneArgInlineBuiltin<"abs"> { + let ParamNames = ["V"]; + let Body = "return V;"; + let IsConstexpr = 1; + let VaryingTypes = UnsignedIntTypes; + let VaryingMatDims = []; +} + +// Returns the boolean AND of two bool values or vectors. +def hlsl_and : HLSLTwoArgBuiltin<"and", "__builtin_hlsl_and"> { + let Doc = [{ +\fn bool and(bool x, bool y) +\brief Logically ands two boolean vectors or matrices elementwise and +produces a bool vector or matrix output. +}]; + let VaryingTypes = [BoolTy]; +} + +// Returns the cross product of two floating-point, 3D vectors. +// Two separate defs are needed because the float and half variants alias +// different builtins (__builtin_hlsl_crossf32 vs __builtin_hlsl_crossf16). +def hlsl_cross_float : HLSLBuiltin<"cross", "__builtin_hlsl_crossf32"> { + let Doc = [{ +\fn T cross(T x, T y) +\brief Returns the cross product of two floating-point, 3D vectors. +\param x [in] The first floating-point, 3D vector. +\param y [in] The second floating-point, 3D vector. + +Result is the cross product of x and y, i.e., the resulting +components are, in order : +x[1] * y[2] - y[1] * x[2] +x[2] * y[0] - y[2] * x[0] +x[0] * y[1] - y[0] * x[1] +}]; + let Args = [VectorType<FloatTy, 3>, VectorType<FloatTy, 3>]; + let ReturnType = VectorType<FloatTy, 3>; +} + +def hlsl_cross_half : HLSLBuiltin<"cross", "__builtin_hlsl_crossf16"> { + let Args = [VectorType<HalfTy, 3>, VectorType<HalfTy, 3>]; + let ReturnType = VectorType<HalfTy, 3>; +} + +// Returns the dot product (a scalar value) of X and Y. +def hlsl_dot : HLSLTwoArgBuiltin<"dot", "__builtin_hlsl_dot"> { + let Doc = [{ +\fn K dot(T X, T Y) +\brief Return the dot product (a scalar value) of \a X and \a Y. +\param X The X input value. +\param Y The Y input value. +}]; + let ReturnType = VaryingElemType; + let VaryingTypes = NumericTypesNoDbl; + let VaryingMatDims = []; +} + +// double dot only has scalar overload (no vectors). +def hlsl_dot_double : HLSLBuiltin<"dot", "__builtin_hlsl_dot"> { + let Args = [Varying, Varying]; + let ReturnType = VaryingElemType; + let VaryingTypes = [DoubleTy]; + let VaryingScalar = 1; +} + +// Dot product of 2 half vectors plus a float scalar. +def hlsl_dot2add : HLSLBuiltin<"dot2add"> { + let Doc = [{ +\fn float dot2add(half2 A, half2 B, float C) +\brief Dot product of 2 vector of type half and add a float scalar value. +\param A The first input value to dot product. +\param B The second input value to dot product. +\param C The input value added to the dot product. +}]; + let DetailFunc = "dot2add_impl"; + let ParamNames = ["A", "B", "C"]; + let Args = [VectorType<HalfTy, 2>, VectorType<HalfTy, 2>, FloatTy]; + let ReturnType = FloatTy; + let Availability = SM6_4; +} + +// Blocks execution of all threads in a group until all group shared accesses +// have been completed and all threads in the group have reached this call. +def hlsl_group_memory_barrier_with_group_sync : + HLSLBuiltin<"GroupMemoryBarrierWithGroupSync", + "__builtin_hlsl_group_memory_barrier_with_group_sync"> { + let Doc = [{ +\fn void GroupMemoryBarrierWithGroupSync(void) +\brief Blocks execution of all threads in a group until all group shared +accesses have been completed and all threads in the group have reached this +call. +}]; + let IsConvergent = 1; +} + +// Determines if the specified value x is infinite. +def hlsl_isinf : HLSLOneArgBuiltin<"isinf", "__builtin_hlsl_elementwise_isinf"> { + let Doc = [{ +\fn T isinf(T x) +\brief Determines if the specified value \a x is infinite. +\param x The specified input value. + +Returns a value of the same size as the input, with a value set +to True if the x parameter is +INF or -INF. Otherwise, False. +}]; + let ReturnType = VaryingShape<BoolTy>; + let VaryingTypes = [HalfTy, FloatTy]; + let VaryingMatDims = []; +} + +// Returns a refraction vector using an entering ray, a surface normal, and +// a refraction index. +def hlsl_refract : HLSLBuiltin<"refract"> { + let Doc = [{ +\fn T refract(T I, T N, T eta) +\brief Returns a refraction using an entering ray, \a I, a surface +normal, \a N and refraction index \a eta +\param I The entering ray. +\param N The surface normal. +\param eta The refraction index. + +The return value is a floating-point vector that represents the refraction +using the refraction index, \a eta, for the direction of the entering ray, +\a I, off a surface with the normal \a N. + +This function calculates the refraction vector using the following formulas: +k = 1.0 - eta * eta * (1.0 - dot(N, I) * dot(N, I)) +if k < 0.0 the result is 0.0 +otherwise, the result is eta * I - (eta * dot(N, I) + sqrt(k)) * N + +I and N must already be normalized in order to achieve the desired result. + +I and N must be a scalar or vector whose component type is +floating-point. + +eta must be a 16-bit or 32-bit floating-point scalar. + +Result type, the type of I, and the type of N must all be the same type. +}]; + let DetailFunc = "refract_impl"; + let ParamNames = ["I", "N", "eta"]; + let Args = [Varying, Varying, VaryingElemType]; + let ReturnType = Varying; + let VaryingTypes = [HalfTy, FloatTy]; + let VaryingScalar = 1; + let VaryingVecSizes = [2, 3, 4]; + let VaryingMatDims = []; +} diff --git a/clang/lib/Headers/hlsl/hlsl_alias_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_alias_intrinsics.h index 76fca33ae0c13..90e681b55fa12 100644 --- a/clang/lib/Headers/hlsl/hlsl_alias_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_alias_intrinsics.h @@ -41,97 +41,6 @@ namespace hlsl { // Generated by clang-tblgen from HLSLIntrinsics.td (alias intrinsics). #include "hlsl_alias_intrinsics_gen.inc" -//===----------------------------------------------------------------------===// -// abs builtins -//===----------------------------------------------------------------------===// - -/// \fn T abs(T Val) -/// \brief Returns the absolute value of the input value, \a Val. -/// \param Val The input value. - -#ifdef __HLSL_ENABLE_16_BIT -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int16_t abs(int16_t); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int16_t2 abs(int16_t2); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int16_t3 abs(int16_t3); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int16_t4 abs(int16_t4); - -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -constexpr uint16_t abs(uint16_t V) { return V; } -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -constexpr uint16_t2 abs(uint16_t2 V) { return V; } -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -constexpr uint16_t3 abs(uint16_t3 V) { return V; } -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -constexpr uint16_t4 abs(uint16_t4 V) { return V; } -#endif - -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -half abs(half); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -half2 abs(half2); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -half3 abs(half3); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -half4 abs(half4); - -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int abs(int); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int2 abs(int2); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int3 abs(int3); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int4 abs(int4); - -constexpr uint abs(uint V) { return V; } -constexpr uint2 abs(uint2 V) { return V; } -constexpr uint3 abs(uint3 V) { return V; } -constexpr uint4 abs(uint4 V) { return V; } - -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -float abs(float); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -float2 abs(float2); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -float3 abs(float3); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -float4 abs(float4); - -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int64_t abs(int64_t); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int64_t2 abs(int64_t2); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int64_t3 abs(int64_t3); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -int64_t4 abs(int64_t4); - -constexpr uint64_t abs(uint64_t V) { return V; } -constexpr uint64_t2 abs(uint64_t2 V) { return V; } -constexpr uint64_t3 abs(uint64_t3 V) { return V; } -constexpr uint64_t4 abs(uint64_t4 V) { return V; } - -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -double abs(double); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -double2 abs(double2); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -double3 abs(double3); -_HLSL_BUILTIN_ALIAS(__builtin_elementwise_abs) -double4 abs(double4); - //===----------------------------------------------------------------------===// // acos builtins //===----------------------------------------------------------------------===// @@ -295,60 +204,6 @@ bool all(double3); _HLSL_BUILTIN_ALIAS(__builtin_hlsl_all) bool all(double4); -//===----------------------------------------------------------------------===// -// and builtins -//===----------------------------------------------------------------------===// - -/// \fn bool and(bool x, bool y) -/// \brief Logically ands two boolean vectors or matrices elementwise and -/// produces a bool vector or matrix output. - -// TODO: Clean up clang-format marker once we've resolved -// https://github.com/llvm/llvm-project/issues/127851 -// -// clang-format off -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool and(bool x, bool y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool2 and(bool2 x, bool2 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool3 and(bool3 x, bool3 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool4 and(bool4 x, bool4 y); - - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool1x2 and(bool1x2 x, bool1x2 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool1x3 and(bool1x3 x, bool1x3 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool1x4 and(bool1x4 x, bool1x4 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool2x1 and(bool2x1 x, bool2x1 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool2x2 and(bool2x2 x, bool2x2 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool2x3 and(bool2x3 x, bool2x3 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool2x4 and(bool2x4 x, bool2x4 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool3x1 and(bool3x1 x, bool3x1 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool3x2 and(bool3x2 x, bool3x2 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool3x3 and(bool3x3 x, bool3x3 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool3x4 and(bool3x4 x, bool3x4 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool4x1 and(bool4x1 x, bool4x1 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool4x2 and(bool4x2 x, bool4x2 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool4x3 and(bool4x3 x, bool4x3 y); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_and) -bool4x4 and(bool4x4 x, bool4x4 y); -// clang-format on - //===----------------------------------------------------------------------===// // any builtins //===----------------------------------------------------------------------===// @@ -912,104 +767,6 @@ float3 degrees(float3); _HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_degrees) float4 degrees(float4); -//===----------------------------------------------------------------------===// -// dot product builtins -//===----------------------------------------------------------------------===// - -/// \fn K dot(T X, T Y) -/// \brief Return the dot product (a scalar value) of \a X and \a Y. -/// \param X The X input value. -/// \param Y The Y input value. - -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -half dot(half, half); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -half dot(half2, half2); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -half dot(half3, half3); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -half dot(half4, half4); - -#ifdef __HLSL_ENABLE_16_BIT -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int16_t dot(int16_t, int16_t); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int16_t dot(int16_t2, int16_t2); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int16_t dot(int16_t3, int16_t3); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int16_t dot(int16_t4, int16_t4); - -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint16_t dot(uint16_t, uint16_t); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint16_t dot(uint16_t2, uint16_t2); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint16_t dot(uint16_t3, uint16_t3); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint16_t dot(uint16_t4, uint16_t4); -#endif - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -float dot(float, float); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -float dot(float2, float2); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -float dot(float3, float3); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -float dot(float4, float4); - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -double dot(double, double); - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int dot(int, int); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int dot(int2, int2); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int dot(int3, int3); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int dot(int4, int4); - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint dot(uint, uint); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint dot(uint2, uint2); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint dot(uint3, uint3); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint dot(uint4, uint4); - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int64_t dot(int64_t, int64_t); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int64_t dot(int64_t2, int64_t2); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int64_t dot(int64_t3, int64_t3); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -int64_t dot(int64_t4, int64_t4); - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint64_t dot(uint64_t, uint64_t); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint64_t dot(uint64_t2, uint64_t2); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint64_t dot(uint64_t3, uint64_t3); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) -uint64_t dot(uint64_t4, uint64_t4); - //===----------------------------------------------------------------------===// // dot4add builtins //===----------------------------------------------------------------------===// @@ -1267,39 +1024,6 @@ float3 frac(float3); _HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_frac) float4 frac(float4); -//===----------------------------------------------------------------------===// -// isinf builtins -//===----------------------------------------------------------------------===// - -/// \fn T isinf(T x) -/// \brief Determines if the specified value \a x is infinite. -/// \param x The specified input value. -/// -/// Returns a value of the same size as the input, with a value set -/// to True if the x parameter is +INF or -INF. Otherwise, False. - -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool isinf(half); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool2 isinf(half2); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool3 isinf(half3); -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool4 isinf(half4); - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool isinf(float); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool2 isinf(float2); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool3 isinf(float3); -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_isinf) -bool4 isinf(float4); - //===----------------------------------------------------------------------===// // isnan builtins //===----------------------------------------------------------------------===// @@ -2019,28 +1743,6 @@ uint64_t3 reversebits(uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_elementwise_bitreverse) uint64_t4 reversebits(uint64_t4); -//===----------------------------------------------------------------------===// -// cross builtins -//===----------------------------------------------------------------------===// - -/// \fn T cross(T x, T y) -/// \brief Returns the cross product of two floating-point, 3D vectors. -/// \param x [in] The first floating-point, 3D vector. -/// \param y [in] The second floating-point, 3D vector. -/// -/// Result is the cross product of x and y, i.e., the resulting -/// components are, in order : -/// x[1] * y[2] - y[1] * x[2] -/// x[2] * y[0] - y[2] * x[0] -/// x[0] * y[1] - y[0] * x[1] - -_HLSL_16BIT_AVAILABILITY_SHADERMODEL_DEFAULT() -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_crossf16) -half3 cross(half3, half3); - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_crossf32) -float3 cross(float3, float3); - //===----------------------------------------------------------------------===// // rcp builtins //===----------------------------------------------------------------------===// @@ -3773,18 +3475,6 @@ float3 radians(float3); _HLSL_BUILTIN_ALIAS(__builtin_hlsl_elementwise_radians) float4 radians(float4); -//===----------------------------------------------------------------------===// -// GroupMemoryBarrierWithGroupSync builtins -//===----------------------------------------------------------------------===// - -/// \fn void GroupMemoryBarrierWithGroupSync(void) -/// \brief Blocks execution of all threads in a group until all group shared -/// accesses have been completed and all threads in the group have reached this -/// call. - -_HLSL_BUILTIN_ALIAS(__builtin_hlsl_group_memory_barrier_with_group_sync) -__attribute__((convergent)) void GroupMemoryBarrierWithGroupSync(void); - //===----------------------------------------------------------------------===// // ddx_coarse builtin //===----------------------------------------------------------------------===// diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 6a37a50064411..95d77eed41853 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -178,21 +178,6 @@ const inline float distance(__detail::HLSL_FIXED_VECTOR<float, N> X, return __detail::distance_vec_impl(X, Y); } -//===----------------------------------------------------------------------===// -// dot2add builtins -//===----------------------------------------------------------------------===// - -/// \fn float dot2add(half2 A, half2 B, float C) -/// \brief Dot product of 2 vector of type half and add a float scalar value. -/// \param A The first input value to dot product. -/// \param B The second input value to dot product. -/// \param C The input value added to the dot product. - -_HLSL_AVAILABILITY(shadermodel, 6.4) -const inline float dot2add(half2 A, half2 B, float C) { - return __detail::dot2add_impl(A, B, C); -} - //===----------------------------------------------------------------------===// // dst builtins //===----------------------------------------------------------------------===// @@ -563,65 +548,6 @@ reflect(__detail::HLSL_FIXED_VECTOR<float, L> I, return __detail::reflect_vec_impl(I, N); } -//===----------------------------------------------------------------------===// -// refract builtin -//===----------------------------------------------------------------------===// - -/// \fn T refract(T I, T N, T eta) -/// \brief Returns a refraction using an entering ray, \a I, a surface -/// normal, \a N and refraction index \a eta -/// \param I The entering ray. -/// \param N The surface normal. -/// \param eta The refraction index. -/// -/// The return value is a floating-point vector that represents the refraction -/// using the refraction index, \a eta, for the direction of the entering ray, -/// \a I, off a surface with the normal \a N. -/// -/// This function calculates the refraction vector using the following formulas: -/// k = 1.0 - eta * eta * (1.0 - dot(N, I) * dot(N, I)) -/// if k < 0.0 the result is 0.0 -/// otherwise, the result is eta * I - (eta * dot(N, I) + sqrt(k)) * N -/// -/// I and N must already be normalized in order to achieve the desired result. -/// -/// I and N must be a scalar or vector whose component type is -/// floating-point. -/// -/// eta must be a 16-bit or 32-bit floating-point scalar. -/// -/// Result type, the type of I, and the type of N must all be the same type. - -template <typename T> -_HLSL_16BIT_AVAILABILITY(shadermodel, 6.2) -const inline __detail::enable_if_t<__detail::is_arithmetic<T>::Value && - __detail::is_same<half, T>::value, - T> refract(T I, T N, T eta) { - return __detail::refract_impl(I, N, eta); -} - -template <typename T> -const inline __detail::enable_if_t< - __detail::is_arithmetic<T>::Value && __detail::is_same<float, T>::value, T> -refract(T I, T N, T eta) { - return __detail::refract_impl(I, N, eta); -} - -template <int L> -_HLSL_16BIT_AVAILABILITY(shadermodel, 6.2) -const inline __detail::HLSL_FIXED_VECTOR<half, L> refract( - __detail::HLSL_FIXED_VECTOR<half, L> I, - __detail::HLSL_FIXED_VECTOR<half, L> N, half eta) { - return __detail::refract_impl(I, N, eta); -} - -template <int L> -const inline __detail::HLSL_FIXED_VECTOR<float, L> -refract(__detail::HLSL_FIXED_VECTOR<float, L> I, - __detail::HLSL_FIXED_VECTOR<float, L> N, float eta) { - return __detail::refract_impl(I, N, eta); -} - //===----------------------------------------------------------------------===// // smoothstep builtin //===----------------------------------------------------------------------===// diff --git a/clang/test/SemaHLSL/BuiltIns/cross-errors.hlsl b/clang/test/SemaHLSL/BuiltIns/cross-errors.hlsl index 2c3e8d1560c87..c9bd1bdd3cb8e 100644 --- a/clang/test/SemaHLSL/BuiltIns/cross-errors.hlsl +++ b/clang/test/SemaHLSL/BuiltIns/cross-errors.hlsl @@ -4,8 +4,8 @@ void test_too_few_arg() { return cross(); // expected-error@-1 {{no matching function for call to 'cross'}} - // expected-note@hlsl/hlsl_alias_intrinsics.h:* {{candidate function not viable: requires 2 arguments, but 0 were provided}} - // expected-note@hlsl/hlsl_alias_intrinsics.h:* {{candidate function not viable: requires 2 arguments, but 0 were provided}} + // expected-note@hlsl/hlsl_alias_intrinsics_gen.inc:* {{candidate function not viable: requires 2 arguments, but 0 were provided}} + // expected-note@hlsl/hlsl_alias_intrinsics_gen.inc:* {{candidate function not viable: requires 2 arguments, but 0 were provided}} } void test_too_few_arg_f32() @@ -24,8 +24,8 @@ void test_too_many_arg(float3 p0) { return cross(p0, p0, p0); // expected-error@-1 {{no matching function for call to 'cross'}} - // expected-note@hlsl/hlsl_alias_intrinsics.h:* {{candidate function not viable: requires 2 arguments, but 3 were provided}} - // expected-note@hlsl/hlsl_alias_intrinsics.h:* {{candidate function not viable: requires 2 arguments, but 3 were provided}} + // expected-note@hlsl/hlsl_alias_intrinsics_gen.inc:* {{candidate function not viable: requires 2 arguments, but 3 were provided}} + // expected-note@hlsl/hlsl_alias_intrinsics_gen.inc:* {{candidate function not viable: requires 2 arguments, but 3 were provided}} } void test_too_many_arg_f32(float3 p0) @@ -56,6 +56,6 @@ void test_ambiguous(int p0) { return cross(p0,p0); // expected-error@-1 {{call to 'cross' is ambiguous}} - // expected-note@hlsl/hlsl_alias_intrinsics.h:* {{candidate function}} - // expected-note@hlsl/hlsl_alias_intrinsics.h:* {{candidate function}} + // expected-note@hlsl/hlsl_alias_intrinsics_gen.inc:* {{candidate function}} + // expected-note@hlsl/hlsl_alias_intrinsics_gen.inc:* {{candidate function}} } diff --git a/clang/test/SemaHLSL/BuiltIns/dot2add-errors.hlsl b/clang/test/SemaHLSL/BuiltIns/dot2add-errors.hlsl index 84333ba08b9b8..e576f73669002 100644 --- a/clang/test/SemaHLSL/BuiltIns/dot2add-errors.hlsl +++ b/clang/test/SemaHLSL/BuiltIns/dot2add-errors.hlsl @@ -3,11 +3,11 @@ float test_too_few_arg() { return dot2add(); // expected-error@-1 {{no matching function for call to 'dot2add'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function not viable: requires 3 arguments, but 0 were provided}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* {{candidate function not viable: requires 3 arguments, but 0 were provided}} } float test_too_many_arg(half2 p1, half2 p2, float p3) { return dot2add(p1, p2, p3, p1); // expected-error@-1 {{no matching function for call to 'dot2add'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function not viable: requires 3 arguments, but 4 were provided}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* {{candidate function not viable: requires 3 arguments, but 4 were provided}} } diff --git a/clang/test/SemaHLSL/BuiltIns/refract-errors.hlsl b/clang/test/SemaHLSL/BuiltIns/refract-errors.hlsl index fce41a4a46d38..8d9949f52aeb0 100644 --- a/clang/test/SemaHLSL/BuiltIns/refract-errors.hlsl +++ b/clang/test/SemaHLSL/BuiltIns/refract-errors.hlsl @@ -3,64 +3,56 @@ float test_no_second_arg(float3 p0) { return refract(p0); // expected-error@-1 {{no matching function for call to 'refract'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 1 was provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 1 was provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 1 was provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 1 was provided}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 8 {{candidate function not viable: requires 3 arguments, but 1 was provided}} } float test_no_third_arg(float3 p0) { return refract(p0, p0); // expected-error@-1 {{no matching function for call to 'refract'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 2 were provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 2 were provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 2 were provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 2 were provided}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 8 {{candidate function not viable: requires 3 arguments, but 2 were provided}} } float test_too_many_arg(float2 p0) { return refract(p0, p0, p0, p0); // expected-error@-1 {{no matching function for call to 'refract'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 4 were provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 4 were provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 4 were provided}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate function template not viable: requires 3 arguments, but 4 were provided}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 8 {{candidate function not viable: requires 3 arguments, but 4 were provided}} } float test_double_inputs(double p0, double p1, double p2) { return refract(p0, p1, p2); - // expected-error@-1 {{no matching function for call to 'refract'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} + // expected-error@-1 {{call to 'refract' is ambiguous}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 2 {{candidate function}} } float test_int_inputs(int p0, int p1, int p2) { return refract(p0, p1, p2); - // expected-error@-1 {{no matching function for call to 'refract'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored}} + // expected-error@-1 {{call to 'refract' is ambiguous}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 2 {{candidate function}} } float1 test_vec1_inputs(float1 p0, float1 p1, float1 p2) { return refract(p0, p1, p2); - // expected-error@-1 {{no matching function for call to 'refract'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: substitution failure [with T = float1]: no type named 'Type' in 'hlsl::__detail::enable_if<false, vector<float, 1>>'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: substitution failure [with T = float1]: no type named 'Type' in 'hlsl::__detail::enable_if<false, vector<float, 1>>'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: substitution failure [with L = 1]: no type named 'Type' in 'hlsl::__detail::enable_if<false, half>'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: substitution failure [with L = 1]: no type named 'Type' in 'hlsl::__detail::enable_if<false, float>'}} + // expected-warning@-1 {{implicit conversion turns vector to scalar: 'float1' (aka 'vector<float, 1>') to 'float'}} + // expected-warning@-2 {{implicit conversion turns vector to scalar: 'float1' (aka 'vector<float, 1>') to 'float'}} + // expected-warning@-3 {{implicit conversion turns vector to scalar: 'float1' (aka 'vector<float, 1>') to 'float'}} } typedef float float5 __attribute__((ext_vector_type(5))); -float5 test_vec5_inputs(float5 p0, float5 p1, float p2) { +float5 test_vec5_inputs(float5 p0, float5 p1, float p2) { return refract(p0, p1, p2); - // expected-error@-1 {{no matching function for call to 'refract'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: deduced conflicting types for parameter 'T' ('float5' (vector of 5 'float' values) vs. 'float')}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: deduced conflicting types for parameter 'T' ('float5' (vector of 5 'float' values) vs. 'float')}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: substitution failure [with L = 5]: no type named 'Type' in 'hlsl::__detail::enable_if<false, half>'}} - // expected-note@hlsl/hlsl_intrinsics.h:* {{candidate template ignored: substitution failure [with L = 5]: no type named 'Type' in 'hlsl::__detail::enable_if<false, float>'}} + // expected-error@-1 {{call to 'refract' is ambiguous}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 4 {{candidate function}} +} + +half3 test_half_inputs_with_float(half3 p0, half3 p1, float p3) { + return refract(p0, p1, p3); + // expected-error@-1 {{call to 'refract' is ambiguous}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 6 {{candidate function}} +} + +half3 test_half_inputs_with_float_literal(half3 p0, half3 p1) { + return refract(p0, p1, 0.5); + // expected-error@-1 {{call to 'refract' is ambiguous}} + // expected-note@hlsl/hlsl_inline_intrinsics_gen.inc:* 6 {{candidate function}} } _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
