[clang] [HLSL][LongVec] Add more intrinsic support (PR #222043)
Farzon Lotfi via cfe-commits
cfe-commits at lists.llvm.org
Tue Sep 8 11:59:31 PDT 2026
https://github.com/farzonl updated https://github.com/llvm/llvm-project/pull/222043
>From 836361fd661e00af8aa65dae9853122c22e4020f Mon Sep 17 00:00:00 2001
From: Farzon Lotfi <farzonlotfi at microsoft.com>
Date: Thu, 3 Sep 2026 16:59:07 -0400
Subject: [PATCH 1/2] [HLSL][LongVec] Add more intrinsic support
resolves #220699
resolves #220655
resolves #220639
resolves #220638
resolves #220614
---
clang/include/clang/Basic/HLSLIntrinsics.td | 5 +++++
clang/test/CodeGenHLSL/builtins/asdouble.hlsl | 12 ++++++++++++
clang/test/CodeGenHLSL/builtins/ddx.hlsl | 7 +++++++
clang/test/CodeGenHLSL/builtins/ddy.hlsl | 7 +++++++
clang/test/CodeGenHLSL/builtins/ldexp.hlsl | 6 ++++++
clang/test/CodeGenHLSL/builtins/mad.hlsl | 7 +++++++
6 files changed, 44 insertions(+)
diff --git a/clang/include/clang/Basic/HLSLIntrinsics.td b/clang/include/clang/Basic/HLSLIntrinsics.td
index ecf7c3df31fe8..21c0960b6fa23 100644
--- a/clang/include/clang/Basic/HLSLIntrinsics.td
+++ b/clang/include/clang/Basic/HLSLIntrinsics.td
@@ -427,6 +427,7 @@ def hlsl_asdouble : HLSLTwoArgBuiltin<"asdouble", "__builtin_hlsl_asdouble"> {
}];
let ReturnType = VaryingShape<DoubleTy>;
let VaryingTypes = [UIntTy];
+ let VaryingLongVector = 1;
let VaryingMatDims = [];
}
@@ -600,6 +601,7 @@ the screen-space x-coordinate.
}];
let ParamNames = ["input"];
let VaryingTypes = [HalfTy, FloatTy];
+ let VaryingLongVector = 1;
let VaryingMatDims = [];
}
@@ -649,6 +651,7 @@ the screen-space y-coordinate.
}];
let ParamNames = ["input"];
let VaryingTypes = [HalfTy, FloatTy];
+ let VaryingLongVector = 1;
let VaryingMatDims = [];
}
@@ -1141,6 +1144,7 @@ This function uses the following formula: X * 2^Exp
let VaryingTypes = [HalfTy, FloatTy];
let VaryingScalar = 1;
let VaryingVecSizes = [2, 3, 4];
+ let VaryingLongVector = 1;
let VaryingMatDims = [];
}
@@ -1264,6 +1268,7 @@ def hlsl_mad : HLSLThreeArgBuiltin<"mad", "__builtin_hlsl_mad"> {
}];
let VaryingTypes = AllNumericTypes;
let VaryingMatDims = [];
+ let VaryingLongVector = 1;
}
// Returns the greater of X and Y.
diff --git a/clang/test/CodeGenHLSL/builtins/asdouble.hlsl b/clang/test/CodeGenHLSL/builtins/asdouble.hlsl
index e73f9ad35ebe2..2753b416d7440 100644
--- a/clang/test/CodeGenHLSL/builtins/asdouble.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/asdouble.hlsl
@@ -35,3 +35,15 @@ double3 test_vuint(uint3 low, uint3 high) {
}
// CHECK-DXIL: declare <3 x double> @llvm.dx.asdouble.v3i32
+
+// CHECK-LABEL: test_vuint5
+vector<double, 5> test_vuint5(vector<uint, 5> low, vector<uint, 5> high) {
+ // CHECK-SPV: %[[SHUFFLE2:.*]] = shufflevector
+ // CHECK-SPV-SAME: {{.*}} <i32 0, i32 5, i32 1, i32 6, i32 2, i32 7, i32 3, i32 8, i32 4, i32 9>
+ // CHECK-SPV: bitcast <10 x i32> %[[SHUFFLE2]] to <5 x double>
+
+ // CHECK-DXIL: call reassoc nnan ninf nsz arcp afn <5 x double> @llvm.dx.asdouble.v5i32
+ return asdouble(low, high);
+}
+
+// CHECK-DXIL: declare <5 x double> @llvm.dx.asdouble.v5i32
diff --git a/clang/test/CodeGenHLSL/builtins/ddx.hlsl b/clang/test/CodeGenHLSL/builtins/ddx.hlsl
index e673e1985dd60..7ec896ee27851 100644
--- a/clang/test/CodeGenHLSL/builtins/ddx.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/ddx.hlsl
@@ -60,3 +60,10 @@ float3 test_f32_ddx3(float3 val) {
float4 test_f32_ddx4(float4 val) {
return ddx(val);
}
+
+// CHECK-LABEL: define {{.*}} <5 x float> @_ZN4hlsl8__detail8ddx_impl
+// CHECK: %[[VAR]] = call {{.*}} <5 x float> @llvm.[[CALL]].v5f32(<5 x float> %{{.*}})
+// CHECK: ret <5 x float> %[[VAR]]
+vector<float, 5> test_f32_ddx5(vector<float, 5> val) {
+ return ddx(val);
+}
diff --git a/clang/test/CodeGenHLSL/builtins/ddy.hlsl b/clang/test/CodeGenHLSL/builtins/ddy.hlsl
index 80d75ca7b22c3..d330d589e918b 100644
--- a/clang/test/CodeGenHLSL/builtins/ddy.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/ddy.hlsl
@@ -60,3 +60,10 @@ float3 test_f32_ddy3(float3 val) {
float4 test_f32_ddy4(float4 val) {
return ddy(val);
}
+
+// CHECK-LABEL: define {{.*}} <5 x float> @_ZN4hlsl8__detail8ddy_impl
+// CHECK: %[[VAR]] = call {{.*}} <5 x float> @llvm.[[CALL]].v5f32(<5 x float> %{{.*}})
+// CHECK: ret <5 x float> %[[VAR]]
+vector<float, 5> test_f32_ddy5(vector<float, 5> val) {
+ return ddy(val);
+}
diff --git a/clang/test/CodeGenHLSL/builtins/ldexp.hlsl b/clang/test/CodeGenHLSL/builtins/ldexp.hlsl
index 2c0458d079027..170c635e99b61 100644
--- a/clang/test/CodeGenHLSL/builtins/ldexp.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/ldexp.hlsl
@@ -47,3 +47,9 @@ float3 test_ldexp_float3(float3 X, float3 Exp) { return ldexp(X, Exp); }
// CHECK: [[MUL:%.*]] = fmul reassoc nnan ninf nsz arcp afn <4 x float> [[EXP2]], %{{.*}}
// CHECK: ret <4 x float> [[MUL]]
float4 test_ldexp_float4(float4 X, float4 Exp) { return ldexp(X, Exp); }
+
+// CHECK-LABEL: define linkonce_odr hidden noundef nofpclass(nan inf) <5 x float> @_ZN4hlsl5ldexp
+// CHECK: [[EXP2:%.*]] = call reassoc nnan ninf nsz arcp afn <5 x float> @llvm.exp2.v5f32(<5 x float> %{{.*}})
+// CHECK: [[MUL:%.*]] = fmul reassoc nnan ninf nsz arcp afn <5 x float> [[EXP2]], %{{.*}}
+// CHECK: ret <5 x float> [[MUL]]
+vector<float, 5> test_ldexp_float5(vector<float, 5> X, vector<float, 5> Exp) { return ldexp(X, Exp); }
diff --git a/clang/test/CodeGenHLSL/builtins/mad.hlsl b/clang/test/CodeGenHLSL/builtins/mad.hlsl
index d982ecba848e2..8ee6d3aac2185 100644
--- a/clang/test/CodeGenHLSL/builtins/mad.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/mad.hlsl
@@ -140,6 +140,13 @@ float3 test_mad_float3(float3 p0, float3 p1, float3 p2) { return mad(p0, p1, p2)
// CHECK: ret <4 x float> %hlsl.fmad
float4 test_mad_float4(float4 p0, float4 p1, float4 p2) { return mad(p0, p1, p2); }
+// CHECK: %[[p0:.*]] = load <5 x float>, ptr %p0.addr
+// CHECK: %[[p1:.*]] = load <5 x float>, ptr %p1.addr
+// CHECK: %[[p2:.*]] = load <5 x float>, ptr %p2.addr
+// CHECK: %hlsl.fmad = call reassoc nnan ninf nsz arcp afn <5 x float> @llvm.fmuladd.v5f32(<5 x float> %[[p0]], <5 x float> %[[p1]], <5 x float> %[[p2]])
+// CHECK: ret <5 x float> %hlsl.fmad
+vector<float, 5> test_mad_float5(vector<float, 5> p0, vector<float, 5> p1, vector<float, 5> p2) { return mad(p0, p1, p2); }
+
// CHECK: %[[p0:.*]] = load double, ptr %p0.addr
// CHECK: %[[p1:.*]] = load double, ptr %p1.addr
// CHECK: %[[p2:.*]] = load double, ptr %p2.addr
>From c5a3150a366fcdd99fb59c51c927d2afbb9bfafc Mon Sep 17 00:00:00 2001
From: Farzon Lotfi <farzonlotfi at microsoft.com>
Date: Tue, 8 Sep 2026 14:56:08 -0400
Subject: [PATCH 2/2] add missing test change
---
clang/test/SemaHLSL/BuiltIns/ldexp-errors.hlsl | 8 --------
1 file changed, 8 deletions(-)
diff --git a/clang/test/SemaHLSL/BuiltIns/ldexp-errors.hlsl b/clang/test/SemaHLSL/BuiltIns/ldexp-errors.hlsl
index ce15550d7884b..e269918d85938 100644
--- a/clang/test/SemaHLSL/BuiltIns/ldexp-errors.hlsl
+++ b/clang/test/SemaHLSL/BuiltIns/ldexp-errors.hlsl
@@ -16,11 +16,3 @@ float1 test_vec1_inputs(float1 p0, float1 p1) {
return ldexp(p0, p1);
// expected-warning at -1 2 {{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) {
- return ldexp(p0, p1);
- // expected-error at -1 {{call to 'ldexp' is ambiguous}}
- // expected-note at hlsl/hlsl_inline_intrinsics_gen.inc:* 4 {{candidate function}}
-}
More information about the cfe-commits
mailing list