[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -428,6 +431,7 @@ bool SPIRVInstructionSelector::spvSelect(Register ResVReg, case TargetOpcode::G_INTRINSIC: case TargetOpcode::G_INTRINSIC_W_SIDE_EFFECTS: + case TargetOpcode::G_INTRINSIC_CONVERGENT: inbelic wrote: Afaict, not within this section of the codebase, it is used elsewhere though eg `GlobalISel`. But I think @Keenuts would be able to better elaborate. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, waveReadLaneAt) inbelic wrote: If we use `_` separated then the generated names will use `.` to separate them. So eg `wave_read_lane_at` becomes `llvm.dx.wave.read.lane.at`. Which we decided was quite confusing due to the confusion with a namespace. I will clean up the other intrinsic to cohere to this in a follow up pr. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 01/10] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===-
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -0,0 +1,26 @@ +// RUN: %clang_cc1 -finclude-default-header -triple dxil-pc-shadermodel6.6-library %s -fnative-half-type -emit-llvm-only -disable-llvm-passes -verify -verify-ignore-unexpected inbelic wrote: Good catch. There are no ignored diagnostics and it is not needed. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
inbelic wrote: I will go ahead and merge this tomorrow if there are no other comments. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111576 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
https://github.com/inbelic ready_for_review https://github.com/llvm/llvm-project/pull/111576 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111576 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex (PR #111576)
https://github.com/inbelic created https://github.com/llvm/llvm-project/pull/111576 - add additional lowering for directx backend in CGBuiltin.cpp - add directx intrinsic to IntrinscsDirectX.td - add semantic check of arguments in SemaHLSL.cpp - add mapping to DXIL op in DXIL.td - add testing of semantics in WaveGetLaneIndex-errors.hlsl - add testing of dxil lowering in WaveGetLaneIndex.ll >From 0911b563e582c621993ad908858f2ec12b0bf57e Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Tue, 8 Oct 2024 09:28:43 -0700 Subject: [PATCH] [HLSL][DXIL] Implement WaveGetLaneIndex - add additional lowering for directx backend in CGBuiltin.cpp - add directx intrinsic to IntrinscsDirectX.td - add semantic check of arguments in SemaHLSL.cpp - add mapping to DXIL op in DXIL.td - add testing of semantics in WaveGetLaneIndex-errors.hlsl - add testing of dxil lowering in WaveGetLaneIndex.ll --- clang/lib/CodeGen/CGBuiltin.cpp | 15 --- clang/lib/Sema/SemaHLSL.cpp | 5 + .../BuiltIns/WaveGetLaneIndex-errors.hlsl | 6 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 9 + llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll | 10 ++ 6 files changed, 43 insertions(+), 3 deletions(-) create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveGetLaneIndex-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..0d92e5a581cbfd 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18827,9 +18827,18 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } case Builtin::BI__builtin_hlsl_wave_get_lane_index: { -return EmitRuntimeCall(CGM.CreateRuntimeFunction( -llvm::FunctionType::get(IntTy, {}, false), "__hlsl_wave_get_lane_index", -{}, false, true)); +switch (CGM.getTarget().getTriple().getArch()) { +case llvm::Triple::dxil: + return EmitRuntimeCall(Intrinsic::getDeclaration( + &CGM.getModule(), Intrinsic::dx_waveGetLaneIndex)); +case llvm::Triple::spirv: + return EmitRuntimeCall(CGM.CreateRuntimeFunction( + llvm::FunctionType::get(IntTy, {}, false), + "__hlsl_wave_get_lane_index", {}, false, true)); +default: + llvm_unreachable( + "Intrinsic waveGetLaneIndex not supported by target architecture"); +} } case Builtin::BI__builtin_hlsl_wave_is_first_lane: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp index 43cc6c81ae5cb0..7d93f41bb2d7a0 100644 --- a/clang/lib/Sema/SemaHLSL.cpp +++ b/clang/lib/Sema/SemaHLSL.cpp @@ -1956,6 +1956,11 @@ bool SemaHLSL::CheckBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { return true; break; } + case Builtin::BI__builtin_hlsl_wave_get_lane_index: { +if (SemaRef.checkArgCount(TheCall, 0)) + return true; +break; + } case Builtin::BI__builtin_elementwise_acos: case Builtin::BI__builtin_elementwise_asin: case Builtin::BI__builtin_elementwise_atan: diff --git a/clang/test/SemaHLSL/BuiltIns/WaveGetLaneIndex-errors.hlsl b/clang/test/SemaHLSL/BuiltIns/WaveGetLaneIndex-errors.hlsl new file mode 100644 index 00..94cfd0662b5fc3 --- /dev/null +++ b/clang/test/SemaHLSL/BuiltIns/WaveGetLaneIndex-errors.hlsl @@ -0,0 +1,6 @@ +// RUN: %clang_cc1 -finclude-default-header -triple dxil-pc-shadermodel6.6-library %s -fnative-half-type -emit-llvm-only -disable-llvm-passes -verify -verify-ignore-unexpected + +int test_too_many_arg(int x) { + return __builtin_hlsl_wave_get_lane_index(x); + // expected-error@-1 {{too many arguments to function call, expected 0, have 1}} +} diff --git a/llvm/include/llvm/IR/IntrinsicsDirectX.td b/llvm/include/llvm/IR/IntrinsicsDirectX.td index 555877e7aaf0e5..585cb2b7b300df 100644 --- a/llvm/include/llvm/IR/IntrinsicsDirectX.td +++ b/llvm/include/llvm/IR/IntrinsicsDirectX.td @@ -82,6 +82,7 @@ def int_dx_imad : DefaultAttrsIntrinsic<[llvm_anyint_ty], [LLVMMatchType<0>, LLV def int_dx_umad : DefaultAttrsIntrinsic<[llvm_anyint_ty], [LLVMMatchType<0>, LLVMMatchType<0>, LLVMMatchType<0>], [IntrNoMem]>; def int_dx_normalize : DefaultAttrsIntrinsic<[LLVMMatchType<0>], [llvm_anyfloat_ty], [IntrNoMem]>; def int_dx_rsqrt : DefaultAttrsIntrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>], [IntrNoMem]>; +def int_dx_waveGetLaneIndex : DefaultAttrsIntrinsic<[llvm_i32_ty], [], [IntrConvergent, IntrNoMem]>; def int_dx_wave_is_first_lane : DefaultAttrsIntrinsic<[llvm_i1_ty], [], [IntrConvergent]>; def int_dx_sign : DefaultAttrsIntrinsic<[LLVMScalarOrSameVectorWidth<0, llvm_i32_ty>], [llvm_any_ty], [IntrNoMem]>; def int_dx_step : Defa
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic created https://github.com/llvm/llvm-project/pull/112400 - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add directx intrinsic expansion to WaveActiveOp in DXILIntrinsicExpansion.cpp - add test cases to illustrate passes >From 952271bd348f9d695a1c655a4fe3d3d37b192da4 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 11 Oct 2024 15:06:15 -0700 Subject: [PATCH] [HLSL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add directx intrinsic expansion to WaveActiveOp in DXILIntrinsicExpansion.cpp - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 32 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 3 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 21 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 34 +++ llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 78 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 13 files changed, 428 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 9ebee81fcb0d3d..2b4fb25c97504a 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4721,6 +4721,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_active_sum"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void (...)"; +} + def HLSLWaveGetLaneIndex : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_wave_get_lane_index"]; let Attributes = [NoThrow, Const]; diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index f4a2d4a3f0656a..e2f7384fb632a6 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -9232,6 +9232,9 @@ def err_typecheck_cond_incompatible_operands : Error< def err_typecheck_expect_scalar_or_vector : Error< "invalid operand of type %0 where %1 or " "a vector of such type is required">; +def err_typecheck_expect_scalar_or_vector_not_type : Error< + "invalid operand of type %0 where %1 or " + "a vector of such type is not allowed">; def err_typecheck_expect_flt_or_vector : Error< "invalid operand of type %0 where floating, complex or " "a vector of such types is required">; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 2449b90a0e7902..4da012418cf902 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18631,6 +18631,23 @@ static Intrinsic::ID getDotProductIntrinsic(CGHLSLRuntime &RT, QualType QT) { return RT.getUDotIntrinsic(); } +// Return wave active sum that corresponds to the QT scalar type +static Intrinsic::ID getWaveActiveSumIntrinsic(llvm::Triple::ArchType Arch, + CGHLSLRuntime &RT, QualType QT) { + switch (Arch) { + case llvm::Triple::spirv: +return llvm::Intrinsic::spv_wave_active_sum; + case llvm::Triple::dxil: { +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::dx_wave_active_usum; +return llvm::Intrinsic::dx_wave_active_sum; + } + default: +llvm_unreachable("Intrinsic WaveActiveSum" + " not supported by target architecture"); + } +} + Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, const CallExpr *E, ReturnValueSlot ReturnValue) { @@ -18866,6 +18883
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From c541955941a11b57efc624b87f50ce61f1b4c26a Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 11 Oct 2024 15:06:15 -0700 Subject: [PATCH] [HLSL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add directx intrinsic expansion to WaveActiveOp in DXILIntrinsicExpansion.cpp - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 32 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 21 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 34 +++ llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 78 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 13 files changed, 427 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 9ebee81fcb0d3d..2b4fb25c97504a 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4721,6 +4721,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_active_sum"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void (...)"; +} + def HLSLWaveGetLaneIndex : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_wave_get_lane_index"]; let Attributes = [NoThrow, Const]; diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index f4a2d4a3f0656a..e2f7384fb632a6 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -9232,6 +9232,9 @@ def err_typecheck_cond_incompatible_operands : Error< def err_typecheck_expect_scalar_or_vector : Error< "invalid operand of type %0 where %1 or " "a vector of such type is required">; +def err_typecheck_expect_scalar_or_vector_not_type : Error< + "invalid operand of type %0 where %1 or " + "a vector of such type is not allowed">; def err_typecheck_expect_flt_or_vector : Error< "invalid operand of type %0 where floating, complex or " "a vector of such types is required">; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 2449b90a0e7902..4da012418cf902 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18631,6 +18631,23 @@ static Intrinsic::ID getDotProductIntrinsic(CGHLSLRuntime &RT, QualType QT) { return RT.getUDotIntrinsic(); } +// Return wave active sum that corresponds to the QT scalar type +static Intrinsic::ID getWaveActiveSumIntrinsic(llvm::Triple::ArchType Arch, + CGHLSLRuntime &RT, QualType QT) { + switch (Arch) { + case llvm::Triple::spirv: +return llvm::Intrinsic::spv_wave_active_sum; + case llvm::Triple::dxil: { +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::dx_wave_active_usum; +return llvm::Intrinsic::dx_wave_active_sum; + } + default: +llvm_unreachable("Intrinsic WaveActiveSum" + " not supported by target architecture"); + } +} + Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, const CallExpr *E, ReturnValueSlot ReturnValue) { @@ -18866,6 +18883,23 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { /*ReturnType=*/Op0->getType(), CGM.getHLSLRuntime().getStepIntrinsic(), ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } + case Builtin::BI__builtin_hlsl_wave_active_sum: { +// Due to the use of variadic arguments, explicitly retreive argument +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{Op
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
inbelic wrote: Dependent on https://github.com/llvm/llvm-project/pull/112058 and https://github.com/llvm/llvm-project/pull/111010. https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][HLSL] Add GroupMemoryBarrierWithGroupSync intrinsic (PR #111883)
@@ -0,0 +1,6 @@ +// RUN: %clang_cc1 -finclude-default-header -triple dxil-pc-shadermodel6.6-library %s -emit-llvm-only -disable-llvm-passes -verify -verify-ignore-unexpected inbelic wrote: Will forward this comment here about `-verify-ignore-unexpected`: https://github.com/llvm/llvm-project/pull/111209#discussion_r1793906097 https://github.com/llvm/llvm-project/pull/111883 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][HLSL] Add GroupMemoryBarrierWithGroupSync intrinsic (PR #111883)
@@ -2018,6 +2018,11 @@ bool SemaHLSL::CheckBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { return true; break; } + case Builtin::BI__builtin_hlsl_group_memory_barrier_with_group_sync: { +if (SemaRef.checkArgCountAtMost(TheCall, 0)) inbelic wrote: Is there a reason to not use `SemaRef.checkArgCount(TheCall, 0)`? I think that would be more descriptive. https://github.com/llvm/llvm-project/pull/111883 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][HLSL] Add GroupMemoryBarrierWithGroupSync intrinsic (PR #111883)
https://github.com/inbelic approved this pull request. LGTM, just a couple nits. https://github.com/llvm/llvm-project/pull/111883 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][HLSL] Add GroupMemoryBarrierWithGroupSync intrinsic (PR #111883)
@@ -4830,6 +4830,12 @@ def HLSLRadians : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLGroupMemoryBarrierWithGroupSync: LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_group_memory_barrier_with_group_sync"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; inbelic wrote: As with `WaveIsFirstLane` I don't think we need `...` and can just do `()` https://github.com/llvm/llvm-project/pull/111883 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][HLSL] Add GroupMemoryBarrierWithGroupSync intrinsic (PR #111883)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111883 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 01/11] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===-
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, waveReadLaneAt) inbelic wrote: Updated to `wave_readlaneat`. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
@@ -18827,9 +18827,21 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } case Builtin::BI__builtin_hlsl_wave_get_lane_index: { -return EmitRuntimeCall(CGM.CreateRuntimeFunction( -llvm::FunctionType::get(IntTy, {}, false), "__hlsl_wave_get_lane_index", -{}, false, true)); +// Since we don't define a SPIR-V intrinsic for the SPIR-V built-in from +// SPIRVBuiltins.td, manually get the matching name for the DirectX +// intrinsic and the demangled builtin name inbelic wrote: The SPIR-V side has already been implemented using a builtin defined in `SPIRVBuiltins.td`. I will improve the comment to be more clear. https://github.com/llvm/llvm-project/pull/111576 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111576 >From 167718e352554e167c4690a4962234ba782bceff Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Tue, 8 Oct 2024 09:28:43 -0700 Subject: [PATCH 1/3] [HLSL][DXIL] Implement WaveGetLaneIndex - add additional lowering for directx backend in CGBuiltin.cpp - add directx intrinsic to IntrinscsDirectX.td - add semantic check of arguments in SemaHLSL.cpp - add mapping to DXIL op in DXIL.td - add testing of semantics in WaveGetLaneIndex-errors.hlsl - add testing of dxil lowering in WaveGetLaneIndex.ll --- clang/lib/CodeGen/CGBuiltin.cpp | 15 +++--- clang/lib/Sema/SemaHLSL.cpp | 5 + .../builtins/wave_get_lane_index_simple.hlsl | 20 +-- .../BuiltIns/WaveGetLaneIndex-errors.hlsl | 6 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 9 + llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll | 10 ++ 7 files changed, 57 insertions(+), 9 deletions(-) create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveGetLaneIndex-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..c83b2c5a2ca047 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18827,9 +18827,18 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } case Builtin::BI__builtin_hlsl_wave_get_lane_index: { -return EmitRuntimeCall(CGM.CreateRuntimeFunction( -llvm::FunctionType::get(IntTy, {}, false), "__hlsl_wave_get_lane_index", -{}, false, true)); +switch (CGM.getTarget().getTriple().getArch()) { +case llvm::Triple::dxil: + return EmitRuntimeCall(Intrinsic::getDeclaration( + &CGM.getModule(), Intrinsic::dx_waveGetLaneIndex)); +case llvm::Triple::spirv: + return EmitRuntimeCall(CGM.CreateRuntimeFunction( + llvm::FunctionType::get(IntTy, {}, false), + "__hlsl_wave_get_lane_index", {}, false, true)); +default: + llvm_unreachable( + "Intrinsic WaveGetLaneIndex not supported by target architecture"); +} } case Builtin::BI__builtin_hlsl_wave_is_first_lane: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp index 43cc6c81ae5cb0..7d93f41bb2d7a0 100644 --- a/clang/lib/Sema/SemaHLSL.cpp +++ b/clang/lib/Sema/SemaHLSL.cpp @@ -1956,6 +1956,11 @@ bool SemaHLSL::CheckBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { return true; break; } + case Builtin::BI__builtin_hlsl_wave_get_lane_index: { +if (SemaRef.checkArgCount(TheCall, 0)) + return true; +break; + } case Builtin::BI__builtin_elementwise_acos: case Builtin::BI__builtin_elementwise_asin: case Builtin::BI__builtin_elementwise_atan: diff --git a/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl b/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl index 8f52d81091c180..e76d35a86e512a 100644 --- a/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl +++ b/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl @@ -1,14 +1,22 @@ // RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -x hlsl -triple \ -// RUN: spirv-pc-vulkan-library %s -emit-llvm -disable-llvm-passes -o - | FileCheck %s +// RUN: spirv-pc-vulkan-library %s -emit-llvm -disable-llvm-passes -o - | FileCheck %s \ +// RUN: --check-prefixes=CHECK,CHECK-SPIRV +// RUN: %clang_cc1 -finclude-default-header \ +// RUN: -triple dxil-pc-shadermodel6.3-library %s \ +// RUN: -emit-llvm -disable-llvm-passes -o - | FileCheck %s \ +// RUN: --check-prefixes=CHECK,CHECK-DXIL -// CHECK: define spir_func noundef i32 @_Z6test_1v() [[A0:#[0-9]+]] { -// CHECK: %[[CI:[0-9]+]] = call token @llvm.experimental.convergence.entry() -// CHECK: call i32 @__hlsl_wave_get_lane_index() [ "convergencectrl"(token %[[CI]]) ] -uint test_1() { +// CHECK-SPIRV: define spir_func noundef i32 @{{.*test_1.*}}() [[A0:#[0-9]+]] { +// CHECK-DXIL: define noundef i32 @{{.*test_1.*}}() [[A0:#[0-9]+]] { +// CHECK-SPIRV: %[[CI:[0-9]+]] = call token @llvm.experimental.convergence.entry() +// CHECK-SPIRV: call i32 @__hlsl_wave_get_lane_index() [ "convergencectrl"(token %[[CI]]) ] +// CHECK-DXIL: call i32 @llvm.dx.waveGetLaneIndex() +int test_1() { return WaveGetLaneIndex(); } -// CHECK: declare i32 @__hlsl_wave_get_lane_index() [[A1:#[0-9]+]] +// CHECK-SPIRV: declare i32 @__hlsl_wave_get_lane_index() [[A1:#[0-9]+]] +// CHECK-DXIL: declare i32 @llvm.dx.waveGetLaneIndex() [[A1:#[0-9]+]] // CHECK-DAG: attributes [[A0]] = { {{.*}}convergent{{.*}} } // CHECK-DAG: attributes [[A1]] = { {{.*}}convergent{{.*}} } diff --git a/clang/test/SemaHL
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
@@ -0,0 +1,6 @@ +// RUN: %clang_cc1 -finclude-default-header -triple dxil-pc-shadermodel6.6-library %s -fnative-half-type -emit-llvm-only -disable-llvm-passes -verify -verify-ignore-unexpected inbelic wrote: The flag was not needed, so have removed it. https://github.com/llvm/llvm-project/pull/111576 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111209 >From 398dcb5c1a354c12d4d43af152f6d3e14f001274 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 2 Oct 2024 13:30:33 -0700 Subject: [PATCH 1/2] [HLSL] Implementation the `degrees` intrinsic - add degrees builtin - link degrees api in hlsl_intrinsics.h - add degrees intrinsic to IntrinsicDirectX.td - add degrees intrinsic to IntrinsicSPIRV.td - add lowering from clang builtin to dx/spv intrinsics in CGBuiltin.cpp - add semantic checks to SemaHLSL.cpp - add expansion of directx intrinsic to llvm fmul for DirectX in DXILIntrinsicExpansion.cpp - add mapping to spir-v intrinsic in SPIRVInstructionSelector.cpp - add test coverage: - degrees.hlsl -> check hlsl lowering to dx/spv degrees intrinsics - degrees-errors.hlsl/half-float-only-errors -> check semantic warnings - hlsl-intrinsics/degrees.ll -> check lowering of spir-v degrees intrinsic to SPIR-V backend - DirectX/degrees.ll -> check expansion and scalarization of directx degrees intrinsic to fmul --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 11 +++ clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 30 clang/lib/Sema/SemaHLSL.cpp | 1 + clang/test/CodeGenHLSL/builtins/degrees.hlsl | 64 + .../SemaHLSL/BuiltIns/degrees-errors.hlsl | 26 +++ .../BuiltIns/half-float-only-errors.hlsl | 1 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 12 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 2 + llvm/test/CodeGen/DirectX/degrees.ll | 54 +++ .../CodeGen/SPIRV/hlsl-intrinsics/degrees.ll | 68 +++ llvm/test/CodeGen/SPIRV/opencl/degrees.ll | 50 ++ 15 files changed, 328 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/degrees.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/degrees-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/opencl/degrees.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 5b504666365b32..44142298987f12 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4739,6 +4739,12 @@ def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDegrees : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_elementwise_degrees"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_dot"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index c864714182e019..0f824fc2c4431a 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18740,6 +18740,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, CGM.getHLSLRuntime().getNormalizeIntrinsic(), ArrayRef{X}, nullptr, "hlsl.normalize"); } + case Builtin::BI__builtin_hlsl_elementwise_degrees: { +Value *X = EmitScalarExpr(E->getArg(0)); + +assert(E->getArg(0)->getType()->hasFloatingRepresentation() && +"degree operand must have a float representation"); + +return Builder.CreateIntrinsic( +/*ReturnType=*/X->getType(), +CGM.getHLSLRuntime().getDegreesIntrinsic(), +ArrayRef{X}, nullptr, "hlsl.degrees"); + } case Builtin::BI__builtin_hlsl_elementwise_frac: { Value *Op0 = EmitScalarExpr(E->getArg(0)); if (!E->getArg(0)->getType()->hasFloatingRepresentation()) diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..966111a9600017 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -74,6 +74,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(All, all) GENERATE_HLSL_INTRINSIC_FUNCTION(Any, any) + GENERATE_HLSL_INTRINSIC_FUNCTION(Degrees, degrees) GENERATE_HLSL_INTRINSIC_FUNCTION(Frac, frac) GENERATE_HLSL_INTRINSIC_FUNCTION(Length, length) GENERATE_HLSL_INTRINSIC_FUNCTION(Lerp, lerp) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index d28f204e352de5..07004a48f96128 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -766,6 +766,36 @@ uint64_t3 countbits(uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_elementwise_popcount) uint64_t4 countbits(uint64_t4); +//===
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111576 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/9] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===---
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 01/14] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===-
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 01/14] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===-
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111209 >From 398dcb5c1a354c12d4d43af152f6d3e14f001274 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 2 Oct 2024 13:30:33 -0700 Subject: [PATCH] [HLSL] Implementation the `degrees` intrinsic - add degrees builtin - link degrees api in hlsl_intrinsics.h - add degrees intrinsic to IntrinsicDirectX.td - add degrees intrinsic to IntrinsicSPIRV.td - add lowering from clang builtin to dx/spv intrinsics in CGBuiltin.cpp - add semantic checks to SemaHLSL.cpp - add expansion of directx intrinsic to llvm fmul for DirectX in DXILIntrinsicExpansion.cpp - add mapping to spir-v intrinsic in SPIRVInstructionSelector.cpp - add test coverage: - degrees.hlsl -> check hlsl lowering to dx/spv degrees intrinsics - degrees-errors.hlsl/half-float-only-errors -> check semantic warnings - hlsl-intrinsics/degrees.ll -> check lowering of spir-v degrees intrinsic to SPIR-V backend - DirectX/degrees.ll -> check expansion and scalarization of directx degrees intrinsic to fmul --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 11 +++ clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 30 clang/lib/Sema/SemaHLSL.cpp | 1 + clang/test/CodeGenHLSL/builtins/degrees.hlsl | 64 + .../SemaHLSL/BuiltIns/degrees-errors.hlsl | 26 +++ .../BuiltIns/half-float-only-errors.hlsl | 1 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 12 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 2 + llvm/test/CodeGen/DirectX/degrees.ll | 54 +++ .../CodeGen/SPIRV/hlsl-intrinsics/degrees.ll | 68 +++ llvm/test/CodeGen/SPIRV/opencl/degrees.ll | 50 ++ 15 files changed, 328 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/degrees.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/degrees-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/opencl/degrees.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 5b504666365b32..44142298987f12 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4739,6 +4739,12 @@ def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDegrees : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_elementwise_degrees"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_dot"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index c864714182e019..0f824fc2c4431a 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18740,6 +18740,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, CGM.getHLSLRuntime().getNormalizeIntrinsic(), ArrayRef{X}, nullptr, "hlsl.normalize"); } + case Builtin::BI__builtin_hlsl_elementwise_degrees: { +Value *X = EmitScalarExpr(E->getArg(0)); + +assert(E->getArg(0)->getType()->hasFloatingRepresentation() && +"degree operand must have a float representation"); + +return Builder.CreateIntrinsic( +/*ReturnType=*/X->getType(), +CGM.getHLSLRuntime().getDegreesIntrinsic(), +ArrayRef{X}, nullptr, "hlsl.degrees"); + } case Builtin::BI__builtin_hlsl_elementwise_frac: { Value *Op0 = EmitScalarExpr(E->getArg(0)); if (!E->getArg(0)->getType()->hasFloatingRepresentation()) diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..966111a9600017 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -74,6 +74,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(All, all) GENERATE_HLSL_INTRINSIC_FUNCTION(Any, any) + GENERATE_HLSL_INTRINSIC_FUNCTION(Degrees, degrees) GENERATE_HLSL_INTRINSIC_FUNCTION(Frac, frac) GENERATE_HLSL_INTRINSIC_FUNCTION(Length, length) GENERATE_HLSL_INTRINSIC_FUNCTION(Lerp, lerp) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index d28f204e352de5..07004a48f96128 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -766,6 +766,36 @@ uint64_t3 countbits(uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_elementwise_popcount) uint64_t4 countbits(uint64_t4); +//===
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111576 >From 167718e352554e167c4690a4962234ba782bceff Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Tue, 8 Oct 2024 09:28:43 -0700 Subject: [PATCH] [HLSL][DXIL] Implement WaveGetLaneIndex - add additional lowering for directx backend in CGBuiltin.cpp - add directx intrinsic to IntrinscsDirectX.td - add semantic check of arguments in SemaHLSL.cpp - add mapping to DXIL op in DXIL.td - add testing of semantics in WaveGetLaneIndex-errors.hlsl - add testing of dxil lowering in WaveGetLaneIndex.ll --- clang/lib/CodeGen/CGBuiltin.cpp | 15 +++--- clang/lib/Sema/SemaHLSL.cpp | 5 + .../builtins/wave_get_lane_index_simple.hlsl | 20 +-- .../BuiltIns/WaveGetLaneIndex-errors.hlsl | 6 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 9 + llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll | 10 ++ 7 files changed, 57 insertions(+), 9 deletions(-) create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveGetLaneIndex-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..c83b2c5a2ca047 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18827,9 +18827,18 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } case Builtin::BI__builtin_hlsl_wave_get_lane_index: { -return EmitRuntimeCall(CGM.CreateRuntimeFunction( -llvm::FunctionType::get(IntTy, {}, false), "__hlsl_wave_get_lane_index", -{}, false, true)); +switch (CGM.getTarget().getTriple().getArch()) { +case llvm::Triple::dxil: + return EmitRuntimeCall(Intrinsic::getDeclaration( + &CGM.getModule(), Intrinsic::dx_waveGetLaneIndex)); +case llvm::Triple::spirv: + return EmitRuntimeCall(CGM.CreateRuntimeFunction( + llvm::FunctionType::get(IntTy, {}, false), + "__hlsl_wave_get_lane_index", {}, false, true)); +default: + llvm_unreachable( + "Intrinsic WaveGetLaneIndex not supported by target architecture"); +} } case Builtin::BI__builtin_hlsl_wave_is_first_lane: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp index 43cc6c81ae5cb0..7d93f41bb2d7a0 100644 --- a/clang/lib/Sema/SemaHLSL.cpp +++ b/clang/lib/Sema/SemaHLSL.cpp @@ -1956,6 +1956,11 @@ bool SemaHLSL::CheckBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { return true; break; } + case Builtin::BI__builtin_hlsl_wave_get_lane_index: { +if (SemaRef.checkArgCount(TheCall, 0)) + return true; +break; + } case Builtin::BI__builtin_elementwise_acos: case Builtin::BI__builtin_elementwise_asin: case Builtin::BI__builtin_elementwise_atan: diff --git a/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl b/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl index 8f52d81091c180..e76d35a86e512a 100644 --- a/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl +++ b/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl @@ -1,14 +1,22 @@ // RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -x hlsl -triple \ -// RUN: spirv-pc-vulkan-library %s -emit-llvm -disable-llvm-passes -o - | FileCheck %s +// RUN: spirv-pc-vulkan-library %s -emit-llvm -disable-llvm-passes -o - | FileCheck %s \ +// RUN: --check-prefixes=CHECK,CHECK-SPIRV +// RUN: %clang_cc1 -finclude-default-header \ +// RUN: -triple dxil-pc-shadermodel6.3-library %s \ +// RUN: -emit-llvm -disable-llvm-passes -o - | FileCheck %s \ +// RUN: --check-prefixes=CHECK,CHECK-DXIL -// CHECK: define spir_func noundef i32 @_Z6test_1v() [[A0:#[0-9]+]] { -// CHECK: %[[CI:[0-9]+]] = call token @llvm.experimental.convergence.entry() -// CHECK: call i32 @__hlsl_wave_get_lane_index() [ "convergencectrl"(token %[[CI]]) ] -uint test_1() { +// CHECK-SPIRV: define spir_func noundef i32 @{{.*test_1.*}}() [[A0:#[0-9]+]] { +// CHECK-DXIL: define noundef i32 @{{.*test_1.*}}() [[A0:#[0-9]+]] { +// CHECK-SPIRV: %[[CI:[0-9]+]] = call token @llvm.experimental.convergence.entry() +// CHECK-SPIRV: call i32 @__hlsl_wave_get_lane_index() [ "convergencectrl"(token %[[CI]]) ] +// CHECK-DXIL: call i32 @llvm.dx.waveGetLaneIndex() +int test_1() { return WaveGetLaneIndex(); } -// CHECK: declare i32 @__hlsl_wave_get_lane_index() [[A1:#[0-9]+]] +// CHECK-SPIRV: declare i32 @__hlsl_wave_get_lane_index() [[A1:#[0-9]+]] +// CHECK-DXIL: declare i32 @llvm.dx.waveGetLaneIndex() [[A1:#[0-9]+]] // CHECK-DAG: attributes [[A0]] = { {{.*}}convergent{{.*}} } // CHECK-DAG: attributes [[A1]] = { {{.*}}convergent{{.*}} } diff --git a/clang/test/SemaHLSL/B
[clang] [llvm] [HLSL][DXIL] Implement WaveGetLaneIndex Intrinsic (PR #111576)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111576 >From 167718e352554e167c4690a4962234ba782bceff Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Tue, 8 Oct 2024 09:28:43 -0700 Subject: [PATCH 1/2] [HLSL][DXIL] Implement WaveGetLaneIndex - add additional lowering for directx backend in CGBuiltin.cpp - add directx intrinsic to IntrinscsDirectX.td - add semantic check of arguments in SemaHLSL.cpp - add mapping to DXIL op in DXIL.td - add testing of semantics in WaveGetLaneIndex-errors.hlsl - add testing of dxil lowering in WaveGetLaneIndex.ll --- clang/lib/CodeGen/CGBuiltin.cpp | 15 +++--- clang/lib/Sema/SemaHLSL.cpp | 5 + .../builtins/wave_get_lane_index_simple.hlsl | 20 +-- .../BuiltIns/WaveGetLaneIndex-errors.hlsl | 6 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 9 + llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll | 10 ++ 7 files changed, 57 insertions(+), 9 deletions(-) create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveGetLaneIndex-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveGetLaneIndex.ll diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..c83b2c5a2ca047 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18827,9 +18827,18 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } case Builtin::BI__builtin_hlsl_wave_get_lane_index: { -return EmitRuntimeCall(CGM.CreateRuntimeFunction( -llvm::FunctionType::get(IntTy, {}, false), "__hlsl_wave_get_lane_index", -{}, false, true)); +switch (CGM.getTarget().getTriple().getArch()) { +case llvm::Triple::dxil: + return EmitRuntimeCall(Intrinsic::getDeclaration( + &CGM.getModule(), Intrinsic::dx_waveGetLaneIndex)); +case llvm::Triple::spirv: + return EmitRuntimeCall(CGM.CreateRuntimeFunction( + llvm::FunctionType::get(IntTy, {}, false), + "__hlsl_wave_get_lane_index", {}, false, true)); +default: + llvm_unreachable( + "Intrinsic WaveGetLaneIndex not supported by target architecture"); +} } case Builtin::BI__builtin_hlsl_wave_is_first_lane: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); diff --git a/clang/lib/Sema/SemaHLSL.cpp b/clang/lib/Sema/SemaHLSL.cpp index 43cc6c81ae5cb0..7d93f41bb2d7a0 100644 --- a/clang/lib/Sema/SemaHLSL.cpp +++ b/clang/lib/Sema/SemaHLSL.cpp @@ -1956,6 +1956,11 @@ bool SemaHLSL::CheckBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { return true; break; } + case Builtin::BI__builtin_hlsl_wave_get_lane_index: { +if (SemaRef.checkArgCount(TheCall, 0)) + return true; +break; + } case Builtin::BI__builtin_elementwise_acos: case Builtin::BI__builtin_elementwise_asin: case Builtin::BI__builtin_elementwise_atan: diff --git a/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl b/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl index 8f52d81091c180..e76d35a86e512a 100644 --- a/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl +++ b/clang/test/CodeGenHLSL/builtins/wave_get_lane_index_simple.hlsl @@ -1,14 +1,22 @@ // RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -x hlsl -triple \ -// RUN: spirv-pc-vulkan-library %s -emit-llvm -disable-llvm-passes -o - | FileCheck %s +// RUN: spirv-pc-vulkan-library %s -emit-llvm -disable-llvm-passes -o - | FileCheck %s \ +// RUN: --check-prefixes=CHECK,CHECK-SPIRV +// RUN: %clang_cc1 -finclude-default-header \ +// RUN: -triple dxil-pc-shadermodel6.3-library %s \ +// RUN: -emit-llvm -disable-llvm-passes -o - | FileCheck %s \ +// RUN: --check-prefixes=CHECK,CHECK-DXIL -// CHECK: define spir_func noundef i32 @_Z6test_1v() [[A0:#[0-9]+]] { -// CHECK: %[[CI:[0-9]+]] = call token @llvm.experimental.convergence.entry() -// CHECK: call i32 @__hlsl_wave_get_lane_index() [ "convergencectrl"(token %[[CI]]) ] -uint test_1() { +// CHECK-SPIRV: define spir_func noundef i32 @{{.*test_1.*}}() [[A0:#[0-9]+]] { +// CHECK-DXIL: define noundef i32 @{{.*test_1.*}}() [[A0:#[0-9]+]] { +// CHECK-SPIRV: %[[CI:[0-9]+]] = call token @llvm.experimental.convergence.entry() +// CHECK-SPIRV: call i32 @__hlsl_wave_get_lane_index() [ "convergencectrl"(token %[[CI]]) ] +// CHECK-DXIL: call i32 @llvm.dx.waveGetLaneIndex() +int test_1() { return WaveGetLaneIndex(); } -// CHECK: declare i32 @__hlsl_wave_get_lane_index() [[A1:#[0-9]+]] +// CHECK-SPIRV: declare i32 @__hlsl_wave_get_lane_index() [[A1:#[0-9]+]] +// CHECK-DXIL: declare i32 @llvm.dx.waveGetLaneIndex() [[A1:#[0-9]+]] // CHECK-DAG: attributes [[A0]] = { {{.*}}convergent{{.*}} } // CHECK-DAG: attributes [[A1]] = { {{.*}}convergent{{.*}} } diff --git a/clang/test/SemaHL
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -2653,6 +2653,21 @@ bool SPIRVInstructionSelector::selectIntrinsic(Register ResVReg, .addUse(GR.getSPIRVTypeID(ResType)) .addUse(GR.getOrCreateConstInt(3, I, IntTy, TII)); } + case Intrinsic::spv_wave_read_lane_at: { +assert(I.getNumOperands() == 4); +assert(I.getOperand(2).isReg()); +assert(I.getOperand(3).isReg()); + +// Defines the execution scope currently 2 for group, see scope table +SPIRVType *IntTy = GR.getOrCreateSPIRVIntegerType(32, I, TII); +return BuildMI(BB, I, I.getDebugLoc(), + TII.get(SPIRV::OpGroupNonUniformShuffle)) +.addDef(ResVReg) +.addUse(GR.getSPIRVTypeID(ResType)) +.addUse(I.getOperand(2).getReg()) +.addUse(I.getOperand(3).getReg()) +.addUse(GR.getOrCreateConstInt(2, I, IntTy, TII)); inbelic wrote: Right, it should facilitate communication within the wave not between waves. Thanks. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/3] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===---
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/3] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===---
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implementation the `degrees` intrinsic (PR #111209)
https://github.com/inbelic created https://github.com/llvm/llvm-project/pull/111209 - add degrees builtin - link degrees api in hlsl_intrinsics.h - add degrees intrinsic to IntrinsicDirectX.td - add degrees intrinsic to IntrinsicSPIRV.td - add lowering from clang builtin to dx/spv intrinsics in CGBuiltin.cpp - add semantic checks to SemaHLSL.cpp - add expansion of directx intrinsic to llvm fmul for DirectX in DXILIntrinsicExpansion.cpp - add mapping to spir-v intrinsic in SPIRVInstructionSelector.cpp - add test coverage: - degrees.hlsl -> check hlsl lowering to dx/spv degrees intrinsics - degrees-errors.hlsl/half-float-only-errors -> check semantic warnings - hlsl-intrinsics/degrees.ll -> check lowering of spir-v degrees intrinsic to SPIR-V backend - DirectX/degrees.ll -> check expansion and scalarization of directx degrees intrinsic to fmul >From 04fa155a8f45c2fdb30b9233f0bd7d4783045a55 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 2 Oct 2024 13:30:33 -0700 Subject: [PATCH] [HLSL] Implementation the `degrees` intrinsic - add degrees builtin - link degrees api in hlsl_intrinsics.h - add degrees intrinsic to IntrinsicDirectX.td - add degrees intrinsic to IntrinsicSPIRV.td - add lowering from clang builtin to dx/spv intrinsics in CGBuiltin.cpp - add semantic checks to SemaHLSL.cpp - add expansion of directx intrinsic to llvm fmul for DirectX in DXILIntrinsicExpansion.cpp - add mapping to spir-v intrinsic in SPIRVInstructionSelector.cpp - add test coverage: - degrees.hlsl -> check hlsl lowering to dx/spv degrees intrinsics - degrees-errors.hlsl/half-float-only-errors -> check semantic warnings - hlsl-intrinsics/degrees.ll -> check lowering of spir-v degrees intrinsic to SPIR-V backend - DirectX/degrees.ll -> check expansion and scalarization of directx degrees intrinsic to fmul --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 11 +++ clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 30 clang/lib/Sema/SemaHLSL.cpp | 1 + clang/test/CodeGenHLSL/builtins/degrees.hlsl | 64 + .../SemaHLSL/BuiltIns/degrees-errors.hlsl | 37 ++ .../BuiltIns/half-float-only-errors.hlsl | 1 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 12 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 22 ++ llvm/test/CodeGen/DirectX/degrees.ll | 54 +++ .../CodeGen/SPIRV/hlsl-intrinsics/degrees.ll | 68 +++ 14 files changed, 309 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/degrees.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/degrees-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/degrees.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..910d90cb3fbc7e 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4709,6 +4709,12 @@ def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDegrees : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_elementwise_degrees"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_dot"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..ecaff0f83b76f3 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18715,6 +18715,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, CGM.getHLSLRuntime().getNormalizeIntrinsic(), ArrayRef{X}, nullptr, "hlsl.normalize"); } + case Builtin::BI__builtin_hlsl_elementwise_degrees: { +Value *X = EmitScalarExpr(E->getArg(0)); + +assert(E->getArg(0)->getType()->hasFloatingRepresentation() && +"degree operand must have a float representation"); + +return Builder.CreateIntrinsic( +/*ReturnType=*/X->getType(), +CGM.getHLSLRuntime().getDegreesIntrinsic(), +ArrayRef{X}, nullptr, "hlsl.degrees"); + } case Builtin::BI__builtin_hlsl_elementwise_frac: { Value *Op0 = EmitScalarExpr(E->getArg(0)); if (!E->getArg(0)->getType()->hasFloatingRepresentation()) diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..966111a9600017 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -74,6 +74,7 @@ class CGHLS
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111209 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
@@ -1643,6 +1646,23 @@ bool SPIRVInstructionSelector::selectLength(Register ResVReg, .constrainAllUses(TII, TRI, RBI); } +bool SPIRVInstructionSelector::selectDegrees(Register ResVReg, + const SPIRVType *ResType, + MachineInstr &I) const { + + assert(I.getNumOperands() == 3); inbelic wrote: Correct, but I believe the first 2 operands of the spir-v instruction are usually used for the `ReturnType` and the `Result` register. https://github.com/llvm/llvm-project/pull/111209 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
@@ -2625,6 +2645,8 @@ bool SPIRVInstructionSelector::selectIntrinsic(Register ResVReg, return selectFmix(ResVReg, ResType, I); case Intrinsic::spv_length: return selectLength(ResVReg, ResType, I); + case Intrinsic::spv_degrees: +return selectDegrees(ResVReg, ResType, I); inbelic wrote: Yep, you are right and I now realize I should also support the option to use the opencl lowering path which can be done using `selectExtInst`. https://github.com/llvm/llvm-project/pull/111209 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/7] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===---
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -82,5 +82,6 @@ let TargetPrefix = "spv" in { [llvm_anyint_ty, LLVMScalarOrSameVectorWidth<0, LLVMVectorElementType<0>>], [IntrNoMem, Commutative] >; def int_spv_wave_is_first_lane : DefaultAttrsIntrinsic<[llvm_i1_ty], [], [IntrConvergent]>; + def int_spv_wave_read_lane_at : DefaultAttrsIntrinsic<[llvm_any_ty], [LLVMMatchType<0>, llvm_i32_ty], [IntrConvergent]>; inbelic wrote: Added a commit to change the name to `waveReadLaneAt` as described in below comment. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -83,6 +83,7 @@ def int_dx_umad : DefaultAttrsIntrinsic<[llvm_anyint_ty], [LLVMMatchType<0>, LLV def int_dx_normalize : DefaultAttrsIntrinsic<[LLVMMatchType<0>], [llvm_anyfloat_ty], [IntrNoMem]>; def int_dx_rsqrt : DefaultAttrsIntrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>], [IntrNoMem]>; def int_dx_wave_is_first_lane : DefaultAttrsIntrinsic<[llvm_i1_ty], [], [IntrConvergent]>; +def int_dx_wave_read_lane_at : DefaultAttrsIntrinsic<[llvm_any_ty], [LLVMMatchType<0>, llvm_i32_ty], [IntrConvergent]>; inbelic wrote: My understanding was that `IntrNoMem` denotes there are no side-effects in the operation and that cross-lane communication would be a side-effect. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/6] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===---
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); inbelic wrote: I think `__hlsl_wave_get_lane_index` is the odd one out. The other intrinsics follow the pattern of `hlsl.name`. Having changed to using one word `waveReadLaneAt` I think we can keep it consistent naming with `hlsl.waveReadLaneAt`. I can change the name to `hlsl.waveGetLaneIndex` in the clean-up pr. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111209 >From 461d5133ea1ae1fcdffd036a926243ee3dce5abb Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 2 Oct 2024 13:30:33 -0700 Subject: [PATCH] [HLSL] Implementation the `degrees` intrinsic - add degrees builtin - link degrees api in hlsl_intrinsics.h - add degrees intrinsic to IntrinsicDirectX.td - add degrees intrinsic to IntrinsicSPIRV.td - add lowering from clang builtin to dx/spv intrinsics in CGBuiltin.cpp - add semantic checks to SemaHLSL.cpp - add expansion of directx intrinsic to llvm fmul for DirectX in DXILIntrinsicExpansion.cpp - add mapping to spir-v intrinsic in SPIRVInstructionSelector.cpp - add test coverage: - degrees.hlsl -> check hlsl lowering to dx/spv degrees intrinsics - degrees-errors.hlsl/half-float-only-errors -> check semantic warnings - hlsl-intrinsics/degrees.ll -> check lowering of spir-v degrees intrinsic to SPIR-V backend - DirectX/degrees.ll -> check expansion and scalarization of directx degrees intrinsic to fmul --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 11 +++ clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 30 clang/lib/Sema/SemaHLSL.cpp | 1 + clang/test/CodeGenHLSL/builtins/degrees.hlsl | 64 + .../SemaHLSL/BuiltIns/degrees-errors.hlsl | 37 ++ .../BuiltIns/half-float-only-errors.hlsl | 1 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 12 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 2 + llvm/test/CodeGen/DirectX/degrees.ll | 54 +++ .../CodeGen/SPIRV/hlsl-intrinsics/degrees.ll | 68 +++ llvm/test/CodeGen/SPIRV/opencl/degrees.ll | 50 ++ 15 files changed, 339 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/degrees.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/degrees-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/opencl/degrees.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 5b504666365b32..44142298987f12 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4739,6 +4739,12 @@ def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDegrees : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_elementwise_degrees"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_dot"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index c864714182e019..0f824fc2c4431a 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18740,6 +18740,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, CGM.getHLSLRuntime().getNormalizeIntrinsic(), ArrayRef{X}, nullptr, "hlsl.normalize"); } + case Builtin::BI__builtin_hlsl_elementwise_degrees: { +Value *X = EmitScalarExpr(E->getArg(0)); + +assert(E->getArg(0)->getType()->hasFloatingRepresentation() && +"degree operand must have a float representation"); + +return Builder.CreateIntrinsic( +/*ReturnType=*/X->getType(), +CGM.getHLSLRuntime().getDegreesIntrinsic(), +ArrayRef{X}, nullptr, "hlsl.degrees"); + } case Builtin::BI__builtin_hlsl_elementwise_frac: { Value *Op0 = EmitScalarExpr(E->getArg(0)); if (!E->getArg(0)->getType()->hasFloatingRepresentation()) diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..966111a9600017 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -74,6 +74,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(All, all) GENERATE_HLSL_INTRINSIC_FUNCTION(Any, any) + GENERATE_HLSL_INTRINSIC_FUNCTION(Degrees, degrees) GENERATE_HLSL_INTRINSIC_FUNCTION(Frac, frac) GENERATE_HLSL_INTRINSIC_FUNCTION(Length, length) GENERATE_HLSL_INTRINSIC_FUNCTION(Lerp, lerp) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index d28f204e352de5..07004a48f96128 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -766,6 +766,36 @@ uint64_t3 countbits(uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_elementwise_popcount) uint64_t4 countbits(uint64_t4); +//===-
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
inbelic wrote: Rebasing onto commit that allows the use of `selectExtInst` with both `CL::degrees` and `GL::Degrees`. Adding additional testcase for this as well. https://github.com/llvm/llvm-project/pull/111209 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/8] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===---
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
@@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); inbelic wrote: Fwiw, this is also true for the `select` intrinsic and we use the arbitrary type template. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic ready_for_review https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From 0bdb522d97752859b0b09c3ba7c815865b87 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 18 Oct 2024 10:49:18 -0700 Subject: [PATCH 1/2] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add test cases to illustrate passes Note that this defines the dx intrinsics but does not implement the DirectX lowering to DXIL. This will be implemented in a second pr when the dependent pr merges. --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 33 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 11 files changed, 326 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..7205f10b01c2b9 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_active_sum"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void (...)"; +} + def HLSLWaveGetLaneIndex : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_wave_get_lane_index"]; let Attributes = [NoThrow, Const]; diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index c458a62d9be48c..95093723c2f495 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -9232,6 +9232,9 @@ def err_typecheck_expect_scalar_or_vector : Error< "a vector of such type is required">; def err_typecheck_expect_any_scalar_or_vector : Error< "invalid operand of type %0 where a scalar or vector is required">; +def err_typecheck_expect_scalar_or_vector_not_type : Error< + "invalid operand of type %0 where %1 or " + "a vector of such type is not allowed">; def err_typecheck_expect_flt_or_vector : Error< "invalid operand of type %0 where floating, complex or " "a vector of such types is required">; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 12f99d9f1178a9..46646492b30d31 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18638,6 +18638,23 @@ static Intrinsic::ID getDotProductIntrinsic(CGHLSLRuntime &RT, QualType QT) { return RT.getUDotIntrinsic(); } +// Return wave active sum that corresponds to the QT scalar type +static Intrinsic::ID getWaveActiveSumIntrinsic(llvm::Triple::ArchType Arch, + CGHLSLRuntime &RT, QualType QT) { + switch (Arch) { + case llvm::Triple::spirv: +return llvm::Intrinsic::spv_wave_active_sum; + case llvm::Triple::dxil: { +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::dx_wave_active_usum; +return llvm::Intrinsic::dx_wave_active_sum; + } + default: +llvm_unreachable("Intrinsic WaveActiveSum" + " not supported by target architecture"); + } +} + Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, const CallExpr *E, ReturnValueSlot ReturnValue) { @@ -18883,6 +18900,23 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { /*ReturnType=*/Op0->getType(), CGM.getHLSLRuntime().getStepIntrinsic(), ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } + case Builtin::BI__builtin_hlsl_wave_active_sum: { +// Due to the use of variadic arguments, explicitly retreive argument +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType()}, false); +Intrinsic::ID IID = getWaveActiveSumIntrinsic( +getT
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveMax` intrinsic (PR #112991)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112991 >From b18e40978cae2c0d9ba9aeb61cf7294809b75012 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 18 Oct 2024 14:41:57 -0700 Subject: [PATCH 1/2] [HLSL][SPIRV] Implement `WaveActiveMax` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add test cases to illustrate passes Note that this defines the dx intrinsics but does not implement the DirectX lowering to DXIL. This will be implemented in a second pr when the dependent pr merges. --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 36 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveMax.hlsl | 48 + .../BuiltIns/WaveActiveMax-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 2 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 34 +++ .../SPIRV/hlsl-intrinsics/WaveActiveMax.ll| 51 ++ 11 files changed, 340 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveMax.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveMax-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveMax.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..ae2068c7a153f7 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveMax : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_active_max"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLWaveGetLaneIndex : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_wave_get_lane_index"]; let Attributes = [NoThrow, Const]; diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index c458a62d9be48c..95093723c2f495 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -9232,6 +9232,9 @@ def err_typecheck_expect_scalar_or_vector : Error< "a vector of such type is required">; def err_typecheck_expect_any_scalar_or_vector : Error< "invalid operand of type %0 where a scalar or vector is required">; +def err_typecheck_expect_scalar_or_vector_not_type : Error< + "invalid operand of type %0 where %1 or " + "a vector of such type is not allowed">; def err_typecheck_expect_flt_or_vector : Error< "invalid operand of type %0 where floating, complex or " "a vector of such types is required">; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 12f99d9f1178a9..dd17b31f3d7168 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18638,6 +18638,25 @@ static Intrinsic::ID getDotProductIntrinsic(CGHLSLRuntime &RT, QualType QT) { return RT.getUDotIntrinsic(); } +// Return wave active max that corresponds to the QT scalar type +static Intrinsic::ID getWaveActiveMaxIntrinsic(llvm::Triple::ArchType Arch, + CGHLSLRuntime &RT, QualType QT) { + switch (Arch) { + case llvm::Triple::spirv: +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::spv_wave_active_umax; +return llvm::Intrinsic::spv_wave_active_max; + case llvm::Triple::dxil: { +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::dx_wave_active_umax; +return llvm::Intrinsic::dx_wave_active_max; + } + default: +llvm_unreachable("Intrinsic WaveActiveMax" + " not supported by target architecture"); + } +} + Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, const CallExpr *E, ReturnValueSlot ReturnValue) { @@ -18883,6 +18902,23 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { /*ReturnType=*/Op0->getType(), CGM.getHLSLRuntime().getStepIntrinsic(), ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } + case Builtin::BI__builtin_hlsl_wave_active_max: { +// Due to the use of variadic arguments, explicitly retreive argument +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{O
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveMax` intrinsic (PR #112991)
https://github.com/inbelic created https://github.com/llvm/llvm-project/pull/112991 - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add test cases to illustrate passes Note that this defines the dx intrinsics but does not implement the DirectX lowering to DXIL. This will be implemented in a second pr when the dependent pr merges. >From b18e40978cae2c0d9ba9aeb61cf7294809b75012 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 18 Oct 2024 14:41:57 -0700 Subject: [PATCH] [HLSL][SPIRV] Implement `WaveActiveMax` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add test cases to illustrate passes Note that this defines the dx intrinsics but does not implement the DirectX lowering to DXIL. This will be implemented in a second pr when the dependent pr merges. --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 36 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveMax.hlsl | 48 + .../BuiltIns/WaveActiveMax-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 2 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 34 +++ .../SPIRV/hlsl-intrinsics/WaveActiveMax.ll| 51 ++ 11 files changed, 340 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveMax.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveMax-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveMax.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..ae2068c7a153f7 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveMax : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_active_max"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLWaveGetLaneIndex : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_wave_get_lane_index"]; let Attributes = [NoThrow, Const]; diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index c458a62d9be48c..95093723c2f495 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -9232,6 +9232,9 @@ def err_typecheck_expect_scalar_or_vector : Error< "a vector of such type is required">; def err_typecheck_expect_any_scalar_or_vector : Error< "invalid operand of type %0 where a scalar or vector is required">; +def err_typecheck_expect_scalar_or_vector_not_type : Error< + "invalid operand of type %0 where %1 or " + "a vector of such type is not allowed">; def err_typecheck_expect_flt_or_vector : Error< "invalid operand of type %0 where floating, complex or " "a vector of such types is required">; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 12f99d9f1178a9..dd17b31f3d7168 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18638,6 +18638,25 @@ static Intrinsic::ID getDotProductIntrinsic(CGHLSLRuntime &RT, QualType QT) { return RT.getUDotIntrinsic(); } +// Return wave active max that corresponds to the QT scalar type +static Intrinsic::ID getWaveActiveMaxIntrinsic(llvm::Triple::ArchType Arch, + CGHLSLRuntime &RT, QualType QT) { + switch (Arch) { + case llvm::Triple::spirv: +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::spv_wave_active_umax; +return llvm::Intrinsic::spv_wave_active_max; + case llvm::Triple::dxil: { +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::dx_wave_active_umax; +return llvm::Intrinsic::dx_wave_active_max; + } + default: +llvm_unreachable("Intrinsic WaveActiveMax" + " not supported by target architecture"); + } +} + Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, const CallExpr *E,
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From aa2ae997f66bf6cd43fc36cbe69c6731914ce9f0 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 18 Oct 2024 10:49:18 -0700 Subject: [PATCH] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add test cases to illustrate passes Note that this defines the dx intrinsics but does not implement the DirectX lowering to DXIL. This will implemented in a secon pr when the dependent pr merges. --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 33 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 11 files changed, 326 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..7205f10b01c2b9 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_active_sum"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void (...)"; +} + def HLSLWaveGetLaneIndex : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_wave_get_lane_index"]; let Attributes = [NoThrow, Const]; diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index c458a62d9be48c..95093723c2f495 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -9232,6 +9232,9 @@ def err_typecheck_expect_scalar_or_vector : Error< "a vector of such type is required">; def err_typecheck_expect_any_scalar_or_vector : Error< "invalid operand of type %0 where a scalar or vector is required">; +def err_typecheck_expect_scalar_or_vector_not_type : Error< + "invalid operand of type %0 where %1 or " + "a vector of such type is not allowed">; def err_typecheck_expect_flt_or_vector : Error< "invalid operand of type %0 where floating, complex or " "a vector of such types is required">; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 12f99d9f1178a9..46646492b30d31 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18638,6 +18638,23 @@ static Intrinsic::ID getDotProductIntrinsic(CGHLSLRuntime &RT, QualType QT) { return RT.getUDotIntrinsic(); } +// Return wave active sum that corresponds to the QT scalar type +static Intrinsic::ID getWaveActiveSumIntrinsic(llvm::Triple::ArchType Arch, + CGHLSLRuntime &RT, QualType QT) { + switch (Arch) { + case llvm::Triple::spirv: +return llvm::Intrinsic::spv_wave_active_sum; + case llvm::Triple::dxil: { +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::dx_wave_active_usum; +return llvm::Intrinsic::dx_wave_active_sum; + } + default: +llvm_unreachable("Intrinsic WaveActiveSum" + " not supported by target architecture"); + } +} + Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, const CallExpr *E, ReturnValueSlot ReturnValue) { @@ -18883,6 +18900,23 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { /*ReturnType=*/Op0->getType(), CGM.getHLSLRuntime().getStepIntrinsic(), ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } + case Builtin::BI__builtin_hlsl_wave_active_sum: { +// Due to the use of variadic arguments, explicitly retreive argument +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType()}, false); +Intrinsic::ID IID = getWaveActiveSumIntrinsic( +getTarget().
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From 896b3adb4f2820f1ccc651cf98e2bade2f972dc4 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 14:44:09 -0700 Subject: [PATCH 1/2] [NFC][DXIL] add ability to alias to an intrinsic - allows an intrinsic to be aliased for another one and provide additional arguments when being replaced --- llvm/lib/Target/DirectX/DXIL.td| 3 +++ llvm/lib/Target/DirectX/DXILOpLowering.cpp | 29 +++- llvm/utils/TableGen/DXILEmitter.cpp| 31 ++ 3 files changed, 62 insertions(+), 1 deletion(-) diff --git a/llvm/lib/Target/DirectX/DXIL.td b/llvm/lib/Target/DirectX/DXIL.td index 147b32b1ca9903..0f8bab7656b7ec 100644 --- a/llvm/lib/Target/DirectX/DXIL.td +++ b/llvm/lib/Target/DirectX/DXIL.td @@ -321,6 +321,9 @@ class DXILOp { // Versioned attributes of operation list attributes = []; + + // List of valid aliases + list aliases = []; } // Concrete definitions of DXIL Operations diff --git a/llvm/lib/Target/DirectX/DXILOpLowering.cpp b/llvm/lib/Target/DirectX/DXILOpLowering.cpp index 99df4850872078..60123fa412208a 100644 --- a/llvm/lib/Target/DirectX/DXILOpLowering.cpp +++ b/llvm/lib/Target/DirectX/DXILOpLowering.cpp @@ -40,6 +40,19 @@ static bool isVectorArgExpansion(Function &F) { return false; } +static SmallVector getAliasArgs(Function &F, IRBuilder<> &Builder) { + switch (F.getIntrinsicID()) { + case Intrinsic::dx_wave_active_sum: +return getWaveActiveOpArgs<0, true>(F, Builder); + case Intrinsic::dx_wave_active_usum: +return getWaveActiveOpArgs<0, false>(F, Builder); + default: +break; + } + SmallVector Args; + return Args; +} + static SmallVector populateOperands(Value *Arg, IRBuilder<> &Builder) { SmallVector ExtractedElements; auto *VecArg = dyn_cast(Arg->getType()); @@ -106,7 +119,9 @@ class OpLowerer { } [[nodiscard]] - bool replaceFunctionWithOp(Function &F, dxil::OpCode DXILOp) { + bool replaceFunctionWithOp( + Function &F, dxil::OpCode DXILOp, + std::optional> AliasArgs = std::nullopt) { bool IsVectorArgExpansion = isVectorArgExpansion(F); return replaceFunction(F, [&](CallInst *CI) -> Error { SmallVector Args; @@ -117,6 +132,11 @@ class OpLowerer { } else Args.append(CI->arg_begin(), CI->arg_end()); + // Append any given alias arguments + if (AliasArgs) { +Args.append(AliasArgs->begin(), AliasArgs->end()); + } + Expected OpCall = OpBuilder.tryCreateOp(DXILOp, Args, CI->getName(), F.getReturnType()); if (Error E = OpCall.takeError()) @@ -476,6 +496,13 @@ class OpLowerer { case Intrin: \ HasErrors |= replaceFunctionWithOp(F, OpCode); \ break; +#include "DXILOperation.inc" +#define DXIL_OP_INTRINSIC_ALIAS(OpCode, Intrin) \ + case Intrin: { \ +SmallVector AliasArgs = getAliasArgs(F, OpBuilder.getIRB()); \ +HasErrors |= replaceFunctionWithOp(F, OpCode, AliasArgs); \ +break; \ + } #include "DXILOperation.inc" case Intrinsic::dx_handle_fromBinding: HasErrors |= lowerHandleFromBinding(F); diff --git a/llvm/utils/TableGen/DXILEmitter.cpp b/llvm/utils/TableGen/DXILEmitter.cpp index 06bf7a0c0a8372..6045256aff23ab 100644 --- a/llvm/utils/TableGen/DXILEmitter.cpp +++ b/llvm/utils/TableGen/DXILEmitter.cpp @@ -45,6 +45,7 @@ struct DXILOperationDesc { SmallVector AttrRecs; StringRef Intrinsic; // The llvm intrinsic map to OpName. Default is "" which // means no map exists + SmallVector IntrinsicAliases; SmallVector ShaderStages; // shader stages to which this applies, empty for all. int OverloadParamIndex; // Index of parameter with overload type. @@ -168,6 +169,15 @@ DXILOperationDesc::DXILOperationDesc(const Record *R) { Intrinsic = DefName.substr(4); } } + + Recs = R->getValueAsListOfDefs("aliases"); + + for (const Record *CR : Recs) { +auto DefName = CR->getName(); +assert(DefName.starts_with("int_") && "invalid intrinsic name"); +// Remove the int_ from intrinsic name. +IntrinsicAliases.push_back(DefName.substr(4)); + } } /// Return a string representation of OverloadKind enum that maps to @@ -388,6 +398,26 @@ static void emitDXILIntrinsicMap(ArrayRef Ops, OS << "#endif\n\n"; } +/// Emit map of DXIL operation to LLVM or DirectX intrinsic alias +/// \param A vector of DXIL Ops +/// \param Output stream +static void emitDXILIntrinsicAliasMap(ArrayRef Ops, + raw_ostream &OS) { + OS << "#ifdef DXIL_OP_INTRINSIC_ALIAS\n"; + OS << "\n"; + for (const auto &
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From 0843af11c647e839704eded62c65d87ec1b2b730 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:27:12 -0700 Subject: [PATCH 1/3] [NFC][DXIL] Allow extra args to replaceFunctionWithOp - allow passing down extra arguments when lowering a directx intrinsic to its dxil op code - this allows us to not create a custom intrinsic for the targeted intermediate intrinsic that it lowers to and does not require us to write a complete custom lowering --- llvm/lib/Target/DirectX/DXILOpLowering.cpp | 9 - 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/llvm/lib/Target/DirectX/DXILOpLowering.cpp b/llvm/lib/Target/DirectX/DXILOpLowering.cpp index 99df4850872078..9feadcb79a5e86 100644 --- a/llvm/lib/Target/DirectX/DXILOpLowering.cpp +++ b/llvm/lib/Target/DirectX/DXILOpLowering.cpp @@ -106,7 +106,9 @@ class OpLowerer { } [[nodiscard]] - bool replaceFunctionWithOp(Function &F, dxil::OpCode DXILOp) { + bool replaceFunctionWithOp( + Function &F, dxil::OpCode DXILOp, + std::optional> ExtraArgs = std::nullopt) { bool IsVectorArgExpansion = isVectorArgExpansion(F); return replaceFunction(F, [&](CallInst *CI) -> Error { SmallVector Args; @@ -117,6 +119,11 @@ class OpLowerer { } else Args.append(CI->arg_begin(), CI->arg_end()); + // Append any given alias arguments + if (ExtraArgs) { +Args.append(ExtraArgs->begin(), ExtraArgs->end()); + } + Expected OpCall = OpBuilder.tryCreateOp(DXILOp, Args, CI->getName(), F.getReturnType()); if (Error E = OpCall.takeError()) >From b68a5616c0bf23857ca1b2dba7dc3a80d6934624 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:31:37 -0700 Subject: [PATCH 2/3] [NFC][DXIL] Add `WaveActiveOp` dxil operation - lowering target for `WaveActive*` ops --- llvm/lib/Target/DirectX/DXIL.td | 9 + 1 file changed, 9 insertions(+) diff --git a/llvm/lib/Target/DirectX/DXIL.td b/llvm/lib/Target/DirectX/DXIL.td index 147b32b1ca9903..fcae23fadf9b94 100644 --- a/llvm/lib/Target/DirectX/DXIL.td +++ b/llvm/lib/Target/DirectX/DXIL.td @@ -793,6 +793,15 @@ def CreateHandleFromBinding : DXILOp<218, createHandleFromBinding> { let stages = [Stages]; } +def WaveActiveOp : DXILOp<119, waveActiveOp> { + let Doc = "returns the result of the operation across waves"; + let arguments = [OverloadTy, Int8Ty, Int8Ty]; + let result = OverloadTy; + let overloads = [Overloads]; + let stages = [Stages]; + let attributes = [Attributes]; +} + def WaveIsFirstLane : DXILOp<110, waveIsFirstLane> { let Doc = "returns 1 for the first lane in the wave"; let LLVMIntrinsic = int_dx_wave_is_first_lane; >From fc7d25fe93ce03b1e6789eb2b82d33294e1d86b8 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:30:56 -0700 Subject: [PATCH 3/3] [HLSL][SPIRV][DXIL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add directx intrinsic expansion to WaveActiveOp in DXILIntrinsicExpansion.cpp - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXILOpLowering.cpp| 22 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 33 +++ llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 78 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 13 files changed, 426 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..7205f10b01c2b9 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LANG"> {
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From 0843af11c647e839704eded62c65d87ec1b2b730 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:27:12 -0700 Subject: [PATCH 1/3] [NFC][DXIL] Allow extra args to replaceFunctionWithOp - allow passing down extra arguments when lowering a directx intrinsic to its dxil op code - this allows us to not create a custom intrinsic for the targeted intermediate intrinsic that it lowers to and does not require us to write a complete custom lowering --- llvm/lib/Target/DirectX/DXILOpLowering.cpp | 9 - 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/llvm/lib/Target/DirectX/DXILOpLowering.cpp b/llvm/lib/Target/DirectX/DXILOpLowering.cpp index 99df4850872078..9feadcb79a5e86 100644 --- a/llvm/lib/Target/DirectX/DXILOpLowering.cpp +++ b/llvm/lib/Target/DirectX/DXILOpLowering.cpp @@ -106,7 +106,9 @@ class OpLowerer { } [[nodiscard]] - bool replaceFunctionWithOp(Function &F, dxil::OpCode DXILOp) { + bool replaceFunctionWithOp( + Function &F, dxil::OpCode DXILOp, + std::optional> ExtraArgs = std::nullopt) { bool IsVectorArgExpansion = isVectorArgExpansion(F); return replaceFunction(F, [&](CallInst *CI) -> Error { SmallVector Args; @@ -117,6 +119,11 @@ class OpLowerer { } else Args.append(CI->arg_begin(), CI->arg_end()); + // Append any given alias arguments + if (ExtraArgs) { +Args.append(ExtraArgs->begin(), ExtraArgs->end()); + } + Expected OpCall = OpBuilder.tryCreateOp(DXILOp, Args, CI->getName(), F.getReturnType()); if (Error E = OpCall.takeError()) >From b68a5616c0bf23857ca1b2dba7dc3a80d6934624 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:31:37 -0700 Subject: [PATCH 2/3] [NFC][DXIL] Add `WaveActiveOp` dxil operation - lowering target for `WaveActive*` ops --- llvm/lib/Target/DirectX/DXIL.td | 9 + 1 file changed, 9 insertions(+) diff --git a/llvm/lib/Target/DirectX/DXIL.td b/llvm/lib/Target/DirectX/DXIL.td index 147b32b1ca9903..fcae23fadf9b94 100644 --- a/llvm/lib/Target/DirectX/DXIL.td +++ b/llvm/lib/Target/DirectX/DXIL.td @@ -793,6 +793,15 @@ def CreateHandleFromBinding : DXILOp<218, createHandleFromBinding> { let stages = [Stages]; } +def WaveActiveOp : DXILOp<119, waveActiveOp> { + let Doc = "returns the result of the operation across waves"; + let arguments = [OverloadTy, Int8Ty, Int8Ty]; + let result = OverloadTy; + let overloads = [Overloads]; + let stages = [Stages]; + let attributes = [Attributes]; +} + def WaveIsFirstLane : DXILOp<110, waveIsFirstLane> { let Doc = "returns 1 for the first lane in the wave"; let LLVMIntrinsic = int_dx_wave_is_first_lane; >From f298a3291cd2b62a1b15862f4e776c32e870b055 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:30:56 -0700 Subject: [PATCH 3/3] [HLSL][SPIRV][DXIL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add directx intrinsic expansion to WaveActiveOp in DXILIntrinsicExpansion.cpp - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXILOpLowering.cpp| 17 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 33 +++ llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 78 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 13 files changed, 421 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..7205f10b01c2b9 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LANG"> {
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From 0843af11c647e839704eded62c65d87ec1b2b730 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:27:12 -0700 Subject: [PATCH 1/3] [NFC][DXIL] Allow extra args to replaceFunctionWithOp - allow passing down extra arguments when lowering a directx intrinsic to its dxil op code - this allows us to not create a custom intrinsic for the targeted intermediate intrinsic that it lowers to and does not require us to write a complete custom lowering --- llvm/lib/Target/DirectX/DXILOpLowering.cpp | 9 - 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/llvm/lib/Target/DirectX/DXILOpLowering.cpp b/llvm/lib/Target/DirectX/DXILOpLowering.cpp index 99df4850872078..9feadcb79a5e86 100644 --- a/llvm/lib/Target/DirectX/DXILOpLowering.cpp +++ b/llvm/lib/Target/DirectX/DXILOpLowering.cpp @@ -106,7 +106,9 @@ class OpLowerer { } [[nodiscard]] - bool replaceFunctionWithOp(Function &F, dxil::OpCode DXILOp) { + bool replaceFunctionWithOp( + Function &F, dxil::OpCode DXILOp, + std::optional> ExtraArgs = std::nullopt) { bool IsVectorArgExpansion = isVectorArgExpansion(F); return replaceFunction(F, [&](CallInst *CI) -> Error { SmallVector Args; @@ -117,6 +119,11 @@ class OpLowerer { } else Args.append(CI->arg_begin(), CI->arg_end()); + // Append any given alias arguments + if (ExtraArgs) { +Args.append(ExtraArgs->begin(), ExtraArgs->end()); + } + Expected OpCall = OpBuilder.tryCreateOp(DXILOp, Args, CI->getName(), F.getReturnType()); if (Error E = OpCall.takeError()) >From b68a5616c0bf23857ca1b2dba7dc3a80d6934624 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:31:37 -0700 Subject: [PATCH 2/3] [NFC][DXIL] Add `WaveActiveOp` dxil operation - lowering target for `WaveActive*` ops --- llvm/lib/Target/DirectX/DXIL.td | 9 + 1 file changed, 9 insertions(+) diff --git a/llvm/lib/Target/DirectX/DXIL.td b/llvm/lib/Target/DirectX/DXIL.td index 147b32b1ca9903..fcae23fadf9b94 100644 --- a/llvm/lib/Target/DirectX/DXIL.td +++ b/llvm/lib/Target/DirectX/DXIL.td @@ -793,6 +793,15 @@ def CreateHandleFromBinding : DXILOp<218, createHandleFromBinding> { let stages = [Stages]; } +def WaveActiveOp : DXILOp<119, waveActiveOp> { + let Doc = "returns the result of the operation across waves"; + let arguments = [OverloadTy, Int8Ty, Int8Ty]; + let result = OverloadTy; + let overloads = [Overloads]; + let stages = [Stages]; + let attributes = [Attributes]; +} + def WaveIsFirstLane : DXILOp<110, waveIsFirstLane> { let Doc = "returns 1 for the first lane in the wave"; let LLVMIntrinsic = int_dx_wave_is_first_lane; >From ec4a8deb12e87d9afa61d8529d6477b38f9f5fc4 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:30:56 -0700 Subject: [PATCH 3/3] [HLSL][SPIRV][DXIL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add lowering of directx intrinsics to a WaveActiveOp dxil op in DXILOpLowering.cpp - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXILOpLowering.cpp| 22 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 33 +++ llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 78 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 13 files changed, 426 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..7205f10b01c2b9 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LAN
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From 0843af11c647e839704eded62c65d87ec1b2b730 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:27:12 -0700 Subject: [PATCH 1/5] [NFC][DXIL] Allow extra args to replaceFunctionWithOp - allow passing down extra arguments when lowering a directx intrinsic to its dxil op code - this allows us to not create a custom intrinsic for the targeted intermediate intrinsic that it lowers to and does not require us to write a complete custom lowering --- llvm/lib/Target/DirectX/DXILOpLowering.cpp | 9 - 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/llvm/lib/Target/DirectX/DXILOpLowering.cpp b/llvm/lib/Target/DirectX/DXILOpLowering.cpp index 99df4850872078..9feadcb79a5e86 100644 --- a/llvm/lib/Target/DirectX/DXILOpLowering.cpp +++ b/llvm/lib/Target/DirectX/DXILOpLowering.cpp @@ -106,7 +106,9 @@ class OpLowerer { } [[nodiscard]] - bool replaceFunctionWithOp(Function &F, dxil::OpCode DXILOp) { + bool replaceFunctionWithOp( + Function &F, dxil::OpCode DXILOp, + std::optional> ExtraArgs = std::nullopt) { bool IsVectorArgExpansion = isVectorArgExpansion(F); return replaceFunction(F, [&](CallInst *CI) -> Error { SmallVector Args; @@ -117,6 +119,11 @@ class OpLowerer { } else Args.append(CI->arg_begin(), CI->arg_end()); + // Append any given alias arguments + if (ExtraArgs) { +Args.append(ExtraArgs->begin(), ExtraArgs->end()); + } + Expected OpCall = OpBuilder.tryCreateOp(DXILOp, Args, CI->getName(), F.getReturnType()); if (Error E = OpCall.takeError()) >From b68a5616c0bf23857ca1b2dba7dc3a80d6934624 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:31:37 -0700 Subject: [PATCH 2/5] [NFC][DXIL] Add `WaveActiveOp` dxil operation - lowering target for `WaveActive*` ops --- llvm/lib/Target/DirectX/DXIL.td | 9 + 1 file changed, 9 insertions(+) diff --git a/llvm/lib/Target/DirectX/DXIL.td b/llvm/lib/Target/DirectX/DXIL.td index 147b32b1ca9903..fcae23fadf9b94 100644 --- a/llvm/lib/Target/DirectX/DXIL.td +++ b/llvm/lib/Target/DirectX/DXIL.td @@ -793,6 +793,15 @@ def CreateHandleFromBinding : DXILOp<218, createHandleFromBinding> { let stages = [Stages]; } +def WaveActiveOp : DXILOp<119, waveActiveOp> { + let Doc = "returns the result of the operation across waves"; + let arguments = [OverloadTy, Int8Ty, Int8Ty]; + let result = OverloadTy; + let overloads = [Overloads]; + let stages = [Stages]; + let attributes = [Attributes]; +} + def WaveIsFirstLane : DXILOp<110, waveIsFirstLane> { let Doc = "returns 1 for the first lane in the wave"; let LLVMIntrinsic = int_dx_wave_is_first_lane; >From ec4a8deb12e87d9afa61d8529d6477b38f9f5fc4 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:30:56 -0700 Subject: [PATCH 3/5] [HLSL][SPIRV][DXIL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add lowering of directx intrinsics to a WaveActiveOp dxil op in DXILOpLowering.cpp - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXILOpLowering.cpp| 22 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 33 +++ llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 78 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 13 files changed, 426 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..7205f10b01c2b9 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4749,6 +4749,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LAN
[clang] [llvm] [HLSL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From 0843af11c647e839704eded62c65d87ec1b2b730 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:27:12 -0700 Subject: [PATCH 1/3] [NFC][DXIL] Allow extra args to replaceFunctionWithOp - allow passing down extra arguments when lowering a directx intrinsic to its dxil op code - this allows us to not create a custom intrinsic for the targeted intermediate intrinsic that it lowers to and does not require us to write a complete custom lowering --- llvm/lib/Target/DirectX/DXILOpLowering.cpp | 9 - 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/llvm/lib/Target/DirectX/DXILOpLowering.cpp b/llvm/lib/Target/DirectX/DXILOpLowering.cpp index 99df4850872078..9feadcb79a5e86 100644 --- a/llvm/lib/Target/DirectX/DXILOpLowering.cpp +++ b/llvm/lib/Target/DirectX/DXILOpLowering.cpp @@ -106,7 +106,9 @@ class OpLowerer { } [[nodiscard]] - bool replaceFunctionWithOp(Function &F, dxil::OpCode DXILOp) { + bool replaceFunctionWithOp( + Function &F, dxil::OpCode DXILOp, + std::optional> ExtraArgs = std::nullopt) { bool IsVectorArgExpansion = isVectorArgExpansion(F); return replaceFunction(F, [&](CallInst *CI) -> Error { SmallVector Args; @@ -117,6 +119,11 @@ class OpLowerer { } else Args.append(CI->arg_begin(), CI->arg_end()); + // Append any given alias arguments + if (ExtraArgs) { +Args.append(ExtraArgs->begin(), ExtraArgs->end()); + } + Expected OpCall = OpBuilder.tryCreateOp(DXILOp, Args, CI->getName(), F.getReturnType()); if (Error E = OpCall.takeError()) >From b68a5616c0bf23857ca1b2dba7dc3a80d6934624 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:31:37 -0700 Subject: [PATCH 2/3] [NFC][DXIL] Add `WaveActiveOp` dxil operation - lowering target for `WaveActive*` ops --- llvm/lib/Target/DirectX/DXIL.td | 9 + 1 file changed, 9 insertions(+) diff --git a/llvm/lib/Target/DirectX/DXIL.td b/llvm/lib/Target/DirectX/DXIL.td index 147b32b1ca9903..fcae23fadf9b94 100644 --- a/llvm/lib/Target/DirectX/DXIL.td +++ b/llvm/lib/Target/DirectX/DXIL.td @@ -793,6 +793,15 @@ def CreateHandleFromBinding : DXILOp<218, createHandleFromBinding> { let stages = [Stages]; } +def WaveActiveOp : DXILOp<119, waveActiveOp> { + let Doc = "returns the result of the operation across waves"; + let arguments = [OverloadTy, Int8Ty, Int8Ty]; + let result = OverloadTy; + let overloads = [Overloads]; + let stages = [Stages]; + let attributes = [Attributes]; +} + def WaveIsFirstLane : DXILOp<110, waveIsFirstLane> { let Doc = "returns 1 for the first lane in the wave"; let LLVMIntrinsic = int_dx_wave_is_first_lane; >From 751f95388a7213ea96682d83fda00aca9fa5e27d Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 16 Oct 2024 15:30:56 -0700 Subject: [PATCH 3/3] [HLSL][SPIRV][DXIL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add lowering of directx intrinsics to a WaveActiveOp dxil op in DXILOpLowering.cpp - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 ++ .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 +++ clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 +++ clang/lib/Sema/SemaHLSL.cpp | 31 ++ .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 48 + .../BuiltIns/WaveActiveSum-errors.hlsl| 28 ++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXILConstants.h | 12 +++ llvm/lib/Target/DirectX/DXILOpLowering.cpp| 24 + .../DirectX/DirectXTargetTransformInfo.cpp| 2 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 33 +++ .../test/CodeGen/DirectX/WaveActiveSum-vec.ll | 34 +++ llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 78 +++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 16 files changed, 476 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum-vec.ll create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 382fb6b7a3c031..7205f10b01c2b9 100644 --- a/clang/include/cla
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111209 >From 398dcb5c1a354c12d4d43af152f6d3e14f001274 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 2 Oct 2024 13:30:33 -0700 Subject: [PATCH 1/2] [HLSL] Implementation the `degrees` intrinsic - add degrees builtin - link degrees api in hlsl_intrinsics.h - add degrees intrinsic to IntrinsicDirectX.td - add degrees intrinsic to IntrinsicSPIRV.td - add lowering from clang builtin to dx/spv intrinsics in CGBuiltin.cpp - add semantic checks to SemaHLSL.cpp - add expansion of directx intrinsic to llvm fmul for DirectX in DXILIntrinsicExpansion.cpp - add mapping to spir-v intrinsic in SPIRVInstructionSelector.cpp - add test coverage: - degrees.hlsl -> check hlsl lowering to dx/spv degrees intrinsics - degrees-errors.hlsl/half-float-only-errors -> check semantic warnings - hlsl-intrinsics/degrees.ll -> check lowering of spir-v degrees intrinsic to SPIR-V backend - DirectX/degrees.ll -> check expansion and scalarization of directx degrees intrinsic to fmul --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 11 +++ clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 30 clang/lib/Sema/SemaHLSL.cpp | 1 + clang/test/CodeGenHLSL/builtins/degrees.hlsl | 64 + .../SemaHLSL/BuiltIns/degrees-errors.hlsl | 26 +++ .../BuiltIns/half-float-only-errors.hlsl | 1 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 12 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 2 + llvm/test/CodeGen/DirectX/degrees.ll | 54 +++ .../CodeGen/SPIRV/hlsl-intrinsics/degrees.ll | 68 +++ llvm/test/CodeGen/SPIRV/opencl/degrees.ll | 50 ++ 15 files changed, 328 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/degrees.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/degrees-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/opencl/degrees.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 5b504666365b32..44142298987f12 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4739,6 +4739,12 @@ def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDegrees : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_elementwise_degrees"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_dot"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index c864714182e019..0f824fc2c4431a 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18740,6 +18740,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, CGM.getHLSLRuntime().getNormalizeIntrinsic(), ArrayRef{X}, nullptr, "hlsl.normalize"); } + case Builtin::BI__builtin_hlsl_elementwise_degrees: { +Value *X = EmitScalarExpr(E->getArg(0)); + +assert(E->getArg(0)->getType()->hasFloatingRepresentation() && +"degree operand must have a float representation"); + +return Builder.CreateIntrinsic( +/*ReturnType=*/X->getType(), +CGM.getHLSLRuntime().getDegreesIntrinsic(), +ArrayRef{X}, nullptr, "hlsl.degrees"); + } case Builtin::BI__builtin_hlsl_elementwise_frac: { Value *Op0 = EmitScalarExpr(E->getArg(0)); if (!E->getArg(0)->getType()->hasFloatingRepresentation()) diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..966111a9600017 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -74,6 +74,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(All, all) GENERATE_HLSL_INTRINSIC_FUNCTION(Any, any) + GENERATE_HLSL_INTRINSIC_FUNCTION(Degrees, degrees) GENERATE_HLSL_INTRINSIC_FUNCTION(Frac, frac) GENERATE_HLSL_INTRINSIC_FUNCTION(Length, length) GENERATE_HLSL_INTRINSIC_FUNCTION(Lerp, lerp) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index d28f204e352de5..07004a48f96128 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -766,6 +766,36 @@ uint64_t3 countbits(uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_elementwise_popcount) uint64_t4 countbits(uint64_t4); +//===
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111209 >From 398dcb5c1a354c12d4d43af152f6d3e14f001274 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 2 Oct 2024 13:30:33 -0700 Subject: [PATCH 1/3] [HLSL] Implementation the `degrees` intrinsic - add degrees builtin - link degrees api in hlsl_intrinsics.h - add degrees intrinsic to IntrinsicDirectX.td - add degrees intrinsic to IntrinsicSPIRV.td - add lowering from clang builtin to dx/spv intrinsics in CGBuiltin.cpp - add semantic checks to SemaHLSL.cpp - add expansion of directx intrinsic to llvm fmul for DirectX in DXILIntrinsicExpansion.cpp - add mapping to spir-v intrinsic in SPIRVInstructionSelector.cpp - add test coverage: - degrees.hlsl -> check hlsl lowering to dx/spv degrees intrinsics - degrees-errors.hlsl/half-float-only-errors -> check semantic warnings - hlsl-intrinsics/degrees.ll -> check lowering of spir-v degrees intrinsic to SPIR-V backend - DirectX/degrees.ll -> check expansion and scalarization of directx degrees intrinsic to fmul --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 11 +++ clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 30 clang/lib/Sema/SemaHLSL.cpp | 1 + clang/test/CodeGenHLSL/builtins/degrees.hlsl | 64 + .../SemaHLSL/BuiltIns/degrees-errors.hlsl | 26 +++ .../BuiltIns/half-float-only-errors.hlsl | 1 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/DirectX/DXILIntrinsicExpansion.cpp | 12 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 2 + llvm/test/CodeGen/DirectX/degrees.ll | 54 +++ .../CodeGen/SPIRV/hlsl-intrinsics/degrees.ll | 68 +++ llvm/test/CodeGen/SPIRV/opencl/degrees.ll | 50 ++ 15 files changed, 328 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/degrees.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/degrees-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/degrees.ll create mode 100644 llvm/test/CodeGen/SPIRV/opencl/degrees.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 5b504666365b32..44142298987f12 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4739,6 +4739,12 @@ def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDegrees : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_elementwise_degrees"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_dot"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index c864714182e019..0f824fc2c4431a 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18740,6 +18740,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, CGM.getHLSLRuntime().getNormalizeIntrinsic(), ArrayRef{X}, nullptr, "hlsl.normalize"); } + case Builtin::BI__builtin_hlsl_elementwise_degrees: { +Value *X = EmitScalarExpr(E->getArg(0)); + +assert(E->getArg(0)->getType()->hasFloatingRepresentation() && +"degree operand must have a float representation"); + +return Builder.CreateIntrinsic( +/*ReturnType=*/X->getType(), +CGM.getHLSLRuntime().getDegreesIntrinsic(), +ArrayRef{X}, nullptr, "hlsl.degrees"); + } case Builtin::BI__builtin_hlsl_elementwise_frac: { Value *Op0 = EmitScalarExpr(E->getArg(0)); if (!E->getArg(0)->getType()->hasFloatingRepresentation()) diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..966111a9600017 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -74,6 +74,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(All, all) GENERATE_HLSL_INTRINSIC_FUNCTION(Any, any) + GENERATE_HLSL_INTRINSIC_FUNCTION(Degrees, degrees) GENERATE_HLSL_INTRINSIC_FUNCTION(Frac, frac) GENERATE_HLSL_INTRINSIC_FUNCTION(Length, length) GENERATE_HLSL_INTRINSIC_FUNCTION(Lerp, lerp) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index d28f204e352de5..07004a48f96128 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -766,6 +766,36 @@ uint64_t3 countbits(uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_elementwise_popcount) uint64_t4 countbits(uint64_t4); +//===
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 01/11] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===-
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/2] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 16 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 155 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..dff56af9282e9d 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, true), + ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===---
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/111010 >From 358ea8278b4e10a094d342aa9b3b1571120a1478 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Thu, 3 Oct 2024 11:43:51 -0700 Subject: [PATCH 1/2] [HLSL] Implement `WaveReadLaneAt` intrinsic - create a clang built-in in Builtins.td - add semantic checking in SemaHLSL.cpp - link the WaveReadLaneAt api in hlsl_intrinsics.h - add lowering to spirv backend op GroupNonUniformShuffle with Scope = 2 (Group) in SPIRVInstructionSelector.cpp - add tests for HLSL intrinsic lowering to spirv intrinsic in WaveReadLaneAt.hlsl - add tests for sema checks in WaveReadLaneAt-errors.hlsl - add spir-v backend tests in WaveReadLaneAt.ll --- clang/include/clang/Basic/Builtins.td | 6 +++ clang/lib/CodeGen/CGBuiltin.cpp | 17 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 7 clang/lib/Sema/SemaHLSL.cpp | 20 ++ .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl | 40 +++ .../BuiltIns/WaveReadLaneAt-errors.hlsl | 21 ++ llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++ .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll | 28 + 10 files changed, 156 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 8090119e512fbb..eec9acd4d27d7d 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> { let Prototype = "bool()"; } +def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_read_lane_at"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void(...)"; +} + def HLSLClamp : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_clamp"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index da3eca73bfb575..2cd851475b6dd9 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18835,6 +18835,23 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic(); return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID)); } + case Builtin::BI__builtin_hlsl_wave_read_lane_at: { +// Due to the use of variadic arguments we must explicitly retreive them and +// create our function type. +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Value *OpIndex = EmitScalarExpr(E->getArg(1)); +llvm::FunctionType *FT = llvm::FunctionType::get( +OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()}, +false); + +// Get overloaded name +std::string name = +Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(), + ArrayRef{OpExpr->getType()}, &CGM.getModule()); +return EmitRuntimeCall( +CGM.CreateRuntimeFunction(FT, name, {}, false, true), +ArrayRef{OpExpr, OpIndex}, "hlsl.wave.read.lane.at"); + } case Builtin::BI__builtin_hlsl_elementwise_sign: { Value *Op0 = EmitScalarExpr(E->getArg(0)); llvm::Type *Xty = Op0->getType(); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index a8aabca7348ffb..a639ce2d784f4a 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -87,6 +87,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at) //===--===// // End of reserved area for HLSL intrinsic getters. diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 810a16d75f0228..a7bdc353ae71bf 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0) _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane) __attribute__((convergent)) bool WaveIsFirstLane(); +// \brief Returns the value of the expression for the given lane index within +// the specified wave. +template +_HLSL_AVAILABILITY(shadermodel, 6.0) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at) +__attribute__((convergent)) T WaveReadLaneAt(T, int32_t); + //===--
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic ready_for_review https://github.com/llvm/llvm-project/pull/111209 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement the `degrees` intrinsic (PR #111209)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111209 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
@@ -2653,6 +2653,21 @@ bool SPIRVInstructionSelector::selectIntrinsic(Register ResVReg, .addUse(GR.getSPIRVTypeID(ResType)) .addUse(GR.getOrCreateConstInt(3, I, IntTy, TII)); } + case Intrinsic::spv_wave_read_lane_at: { +assert(I.getNumOperands() == 4); +assert(I.getOperand(2).isReg()); +assert(I.getOperand(3).isReg()); + +// Defines the execution scope currently 2 for group, see scope table +SPIRVType *IntTy = GR.getOrCreateSPIRVIntegerType(32, I, TII); +return BuildMI(BB, I, I.getDebugLoc(), + TII.get(SPIRV::OpGroupNonUniformShuffle)) +.addDef(ResVReg) +.addUse(GR.getSPIRVTypeID(ResType)) +.addUse(I.getOperand(2).getReg()) +.addUse(I.getOperand(3).getReg()) +.addUse(GR.getOrCreateConstInt(2, I, IntTy, TII)); inbelic wrote: IIUC, an HLSL wave corresponds to the SPIR-V workgroup scope, which is denoted as 2. https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic ready_for_review https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic for spirv backend (PR #111010)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/111010 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/113382 >From 68c16dc2e21d3a78a388fdb883551f32b902db11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 18 Oct 2024 15:48:29 -0700 Subject: [PATCH 1/2] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic - add codegen for llvm builtin to spirv/directx intrinsic in CGBuiltin.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add lowering of directx intrinsic to dxil op in DXIL.td - add test cases to illustrate passes - add test case for semantic analysis --- clang/lib/CodeGen/CGBuiltin.cpp | 7 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + .../builtins/WaveActiveCountBits.hlsl | 22 +++ .../BuiltIns/WaveActiveCountBits-errors.hlsl | 18 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 9 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 37 +++ .../CodeGen/DirectX/WaveActiveCountBits.ll| 10 + .../hlsl-intrinsics/WaveActiveCountBits.ll| 19 ++ 10 files changed, 125 insertions(+) create mode 100755 clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveCountBits-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveCountBits.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveCountBits.ll diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 28f28c70b5ae52..f178499156eb1f 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18879,6 +18879,13 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { /*ReturnType=*/Op0->getType(), CGM.getHLSLRuntime().getStepIntrinsic(), ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } + case Builtin::BI__builtin_hlsl_wave_active_count_bits: { +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveActiveCountBitsIntrinsic(); +return EmitRuntimeCall( +Intrinsic::getOrInsertDeclaration(&CGM.getModule(), ID), +ArrayRef{OpExpr}); + } case Builtin::BI__builtin_hlsl_wave_get_lane_index: { // We don't define a SPIR-V intrinsic, instead it is a SPIR-V built-in // defined in SPIRVBuiltins.td. So instead we manually get the matching name diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index ff7df41b5c62e7..ada57b070783c6 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -89,6 +89,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(FDot, fdot) GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveActiveCountBits, wave_active_countbits) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_readlane) diff --git a/clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl b/clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl new file mode 100755 index 00..3e1f8fcaace9c2 --- /dev/null +++ b/clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl @@ -0,0 +1,22 @@ +// RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -triple \ +// RUN: dxil-pc-shadermodel6.3-compute %s -emit-llvm -disable-llvm-passes -o - | \ +// RUN: FileCheck %s --check-prefixes=CHECK,CHECK-DXIL +// RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -triple \ +// RUN: spirv-pc-vulkan-compute %s -emit-llvm -disable-llvm-passes -o - | \ +// RUN: FileCheck %s --check-prefixes=CHECK,CHECK-SPIRV + +// Test basic lowering to runtime function call. + +// CHECK-LABEL: test_bool +int test_bool(bool expr) { + // CHECK-SPIRV: %[[#entry_tok:]] = call token @llvm.experimental.convergence.entry() + // CHECK-SPIRV: %[[RET:.*]] = call spir_func i32 @llvm.spv.wave.active.countbits(i1 %{{.*}}) [ "convergencectrl"(token %[[#entry_tok]]) ] + // CHECK-DXIL: %[[RET:.*]] = call i32 @llvm.dx.wave.active.countbits(i1 %{{.*}}) + // CHECK: ret i32 %[[RET]] + return WaveActiveCountBits(expr); +} + +// CHECK-DXIL: declare i32 @llvm.dx.wave.active.countbits(i1) #[[#attr:]] +// CHECK-SPIRV: declare i32 @llvm.spv.wave.active.countbits(i1) #[[#attr:]] + +// CHECK: attributes #[[#attr]] = {{{.*}} convergent {{.*}}} diff --git a/clang/test/SemaHLSL/BuiltIns/WaveActiveCountBits-errors.hlsl b/clang/test/SemaHLSL/BuiltIns/WaveActiveCountBits-errors.hlsl new file mode 100644 index 00..02f45eb30b377a --- /dev/null +++ b/clang/test/SemaHLSL/BuiltIns/WaveActiveCountBits-errors.hlsl @@ -0,0 +1,18 @@ +// RUN: %clang_cc1 -finclude-default-header -triple dxil-pc-shadermodel6.6-library %s -emit-llvm-only -disable-llvm-passes -verify + +int test_too_few_arg() { + return __
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
https://github.com/inbelic created https://github.com/llvm/llvm-project/pull/113382 - add codegen for llvm builtin to spirv/directx intrinsic in CGBuiltin.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add lowering of directx intrinsic to dxil op in DXIL.td - add test cases to illustrate passes - add test case for semantic analysis >From 68c16dc2e21d3a78a388fdb883551f32b902db11 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 18 Oct 2024 15:48:29 -0700 Subject: [PATCH] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic - add codegen for llvm builtin to spirv/directx intrinsic in CGBuiltin.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add lowering of directx intrinsic to dxil op in DXIL.td - add test cases to illustrate passes - add test case for semantic analysis --- clang/lib/CodeGen/CGBuiltin.cpp | 7 clang/lib/CodeGen/CGHLSLRuntime.h | 1 + .../builtins/WaveActiveCountBits.hlsl | 22 +++ .../BuiltIns/WaveActiveCountBits-errors.hlsl | 18 + llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 9 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 37 +++ .../CodeGen/DirectX/WaveActiveCountBits.ll| 10 + .../hlsl-intrinsics/WaveActiveCountBits.ll| 19 ++ 10 files changed, 125 insertions(+) create mode 100755 clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveCountBits-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveCountBits.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveCountBits.ll diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 28f28c70b5ae52..f178499156eb1f 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18879,6 +18879,13 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { /*ReturnType=*/Op0->getType(), CGM.getHLSLRuntime().getStepIntrinsic(), ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } + case Builtin::BI__builtin_hlsl_wave_active_count_bits: { +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveActiveCountBitsIntrinsic(); +return EmitRuntimeCall( +Intrinsic::getOrInsertDeclaration(&CGM.getModule(), ID), +ArrayRef{OpExpr}); + } case Builtin::BI__builtin_hlsl_wave_get_lane_index: { // We don't define a SPIR-V intrinsic, instead it is a SPIR-V built-in // defined in SPIRVBuiltins.td. So instead we manually get the matching name diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index ff7df41b5c62e7..ada57b070783c6 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -89,6 +89,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(FDot, fdot) GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) + GENERATE_HLSL_INTRINSIC_FUNCTION(WaveActiveCountBits, wave_active_countbits) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_readlane) diff --git a/clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl b/clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl new file mode 100755 index 00..3e1f8fcaace9c2 --- /dev/null +++ b/clang/test/CodeGenHLSL/builtins/WaveActiveCountBits.hlsl @@ -0,0 +1,22 @@ +// RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -triple \ +// RUN: dxil-pc-shadermodel6.3-compute %s -emit-llvm -disable-llvm-passes -o - | \ +// RUN: FileCheck %s --check-prefixes=CHECK,CHECK-DXIL +// RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -triple \ +// RUN: spirv-pc-vulkan-compute %s -emit-llvm -disable-llvm-passes -o - | \ +// RUN: FileCheck %s --check-prefixes=CHECK,CHECK-SPIRV + +// Test basic lowering to runtime function call. + +// CHECK-LABEL: test_bool +int test_bool(bool expr) { + // CHECK-SPIRV: %[[#entry_tok:]] = call token @llvm.experimental.convergence.entry() + // CHECK-SPIRV: %[[RET:.*]] = call spir_func i32 @llvm.spv.wave.active.countbits(i1 %{{.*}}) [ "convergencectrl"(token %[[#entry_tok]]) ] + // CHECK-DXIL: %[[RET:.*]] = call i32 @llvm.dx.wave.active.countbits(i1 %{{.*}}) + // CHECK: ret i32 %[[RET]] + return WaveActiveCountBits(expr); +} + +// CHECK-DXIL: declare i32 @llvm.dx.wave.active.countbits(i1) #[[#attr:]] +// CHECK-SPIRV: declare i32 @llvm.spv.wave.active.countbits(i1) #[[#attr:]] + +// CHECK: attributes #[[#attr]] = {{{.*}} convergent {{.*}}} diff --git a/clang/test/SemaHLSL/BuiltIns/WaveActiveCountBits-errors.hlsl b/clang/test/SemaHLSL/BuiltIns/WaveActiveCountBits-errors.hlsl new file mode 100644 index 0
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
https://github.com/inbelic ready_for_review https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
inbelic wrote: Failing testcase is unrelated. Will need to rebase on review changes. https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
@@ -1762,6 +1765,36 @@ bool SPIRVInstructionSelector::selectSign(Register ResVReg, return Result; } +bool SPIRVInstructionSelector::selectWaveActiveCountBits( +Register ResVReg, const SPIRVType *ResType, MachineInstr &I) const { + assert(I.getNumOperands() == 3); + assert(I.getOperand(2).isReg()); + MachineBasicBlock &BB = *I.getParent(); + + Register BallotReg = MRI->createVirtualRegister(&SPIRV::IDRegClass); + SPIRVType *IntTy = GR.getOrCreateSPIRVIntegerType(32, I, TII); + SPIRVType *BallotType = GR.getOrCreateSPIRVVectorType(IntTy, 4, I, TII); + + bool Result = + BuildMI(BB, I, I.getDebugLoc(), TII.get(SPIRV::OpGroupNonUniformBallot)) + .addDef(BallotReg) + .addUse(GR.getSPIRVTypeID(BallotType)) + .addUse(GR.getOrCreateConstInt(SPIRV::Scope::Subgroup, I, IntTy, TII)) + .addUse(I.getOperand(2).getReg()); + + Result |= + BuildMI(BB, I, I.getDebugLoc(), + TII.get(SPIRV::OpGroupNonUniformBallotBitCount)) + .addDef(ResVReg) + .addUse(GR.getSPIRVTypeID(ResType)) + .addUse(GR.getOrCreateConstInt(SPIRV::Scope::Subgroup, I, IntTy, TII)) + .addImm(0) inbelic wrote: Will update to use the `SPIRV::OperationGroup` enum https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic (PR #113623)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/113623 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
@@ -1762,6 +1765,36 @@ bool SPIRVInstructionSelector::selectSign(Register ResVReg, return Result; } +bool SPIRVInstructionSelector::selectWaveActiveCountBits( +Register ResVReg, const SPIRVType *ResType, MachineInstr &I) const { + assert(I.getNumOperands() == 3); + assert(I.getOperand(2).isReg()); + MachineBasicBlock &BB = *I.getParent(); + + Register BallotReg = MRI->createVirtualRegister(&SPIRV::IDRegClass); + SPIRVType *IntTy = GR.getOrCreateSPIRVIntegerType(32, I, TII); + SPIRVType *BallotType = GR.getOrCreateSPIRVVectorType(IntTy, 4, I, TII); + + bool Result = + BuildMI(BB, I, I.getDebugLoc(), TII.get(SPIRV::OpGroupNonUniformBallot)) + .addDef(BallotReg) + .addUse(GR.getSPIRVTypeID(BallotType)) + .addUse(GR.getOrCreateConstInt(SPIRV::Scope::Subgroup, I, IntTy, TII)) + .addUse(I.getOperand(2).getReg()); + + Result |= + BuildMI(BB, I, I.getDebugLoc(), + TII.get(SPIRV::OpGroupNonUniformBallotBitCount)) + .addDef(ResVReg) + .addUse(GR.getSPIRVTypeID(ResType)) + .addUse(GR.getOrCreateConstInt(SPIRV::Scope::Subgroup, I, IntTy, TII)) + .addImm(0) inbelic wrote: Yep, have it added for when the other review comments are addressed. https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic (PR #113623)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/113623 >From 46822507e0b70e91cf6f4f0295d257978652bfbc Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 23 Oct 2024 22:59:15 + Subject: [PATCH 1/2] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic - create a clang built-in in Builtins.td - link dot4add_i8packed in hlsl_intrinsics.h - add lowering to spirv backend through expansion of operation as OPSDot is missing up to SPIRV 1.6 in SPIRVInstructionSelector.cpp - add dot4add_i8packed intrinsic to IntrinsicsDirectX.td and mapping to DXIL.td op Dot4AddI8Packed - add tests for HLSL intrinsic lowering to dx/spv intrinsic in dot4add_i8packed.hlsl - add tests for sema checks in dot4add_i8packed-errors.hlsl - add test of spir-v lowering in SPIRV/dot4add_i8packed.ll - add test to dxil lowering in DirectX/dot4add_i8packed.ll --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 12 ++- clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 10 +++ .../builtins/dot4add_i8packed.hlsl| 17 .../BuiltIns/dot4add_i8packed-errors.hlsl | 28 +++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 10 +++ .../Target/SPIRV/SPIRVInstructionSelector.cpp | 84 +++ llvm/test/CodeGen/DirectX/dot4add_i8packed.ll | 10 +++ .../SPIRV/hlsl-intrinsics/dot4add_i8packed.ll | 48 +++ 12 files changed, 227 insertions(+), 1 deletion(-) create mode 100644 clang/test/CodeGenHLSL/builtins/dot4add_i8packed.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/dot4add_i8packed-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/dot4add_i8packed.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/dot4add_i8packed.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 90475a361bb8f8..eb6b07e8858602 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4792,6 +4792,12 @@ def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDot4AddI8Packed : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_dot4add_i8packed"]; + let Attributes = [NoThrow, Const]; + let Prototype = "int(unsigned int, unsigned int, int)"; +} + def HLSLFrac : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_frac"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 28f28c70b5ae52..3eceafff49b776 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18722,7 +18722,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, /*ReturnType=*/T0->getScalarType(), getDotProductIntrinsic(CGM.getHLSLRuntime(), VecTy0->getElementType()), ArrayRef{Op0, Op1}, nullptr, "hlsl.dot"); - } break; + } + case Builtin::BI__builtin_hlsl_dot4add_i8packed: { +Value *A = EmitScalarExpr(E->getArg(0)); +Value *B = EmitScalarExpr(E->getArg(1)); +Value *C = EmitScalarExpr(E->getArg(2)); + +Intrinsic::ID ID = CGM.getHLSLRuntime().getDot4AddI8PackedIntrinsic(); +return Builder.CreateIntrinsic( +/*ReturnType=*/C->getType(), ID, +ArrayRef{A, B, C}, nullptr, "hlsl.dot4add.i8packed"); + } case Builtin::BI__builtin_hlsl_lerp: { Value *X = EmitScalarExpr(E->getArg(0)); Value *Y = EmitScalarExpr(E->getArg(1)); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index ff7df41b5c62e7..8b1141375106cc 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -89,6 +89,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(FDot, fdot) GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) + GENERATE_HLSL_INTRINSIC_FUNCTION(Dot4AddI8Packed, dot4add_i8packed) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_readlane) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 30dce60b3ff702..d10bfcbeed97ea 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -894,6 +894,16 @@ uint64_t dot(uint64_t3, uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) uint64_t dot(uint64_t4, uint64_t4); +//===--===// +// dot4add builtins +//===--===// + +/// \fn int dot4add_i8packed(uint A, uint B, int C) + +_HLSL_16BIT_AVAILABILITY(shadermodel, 6.4) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot4a
[clang] [llvm] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic (PR #113623)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/113623 >From 81dfa26a941f7a0926a3126fe3ebbb4d2a67cec1 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 23 Oct 2024 22:59:15 + Subject: [PATCH 1/3] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic - create a clang built-in in Builtins.td - link dot4add_i8packed in hlsl_intrinsics.h - add lowering to spirv backend through expansion of operation as OPSDot is missing up to SPIRV 1.6 in SPIRVInstructionSelector.cpp - add dot4add_i8packed intrinsic to IntrinsicsDirectX.td and mapping to DXIL.td op Dot4AddI8Packed - add tests for HLSL intrinsic lowering to dx/spv intrinsic in dot4add_i8packed.hlsl - add tests for sema checks in dot4add_i8packed-errors.hlsl - add test of spir-v lowering in SPIRV/dot4add_i8packed.ll - add test to dxil lowering in DirectX/dot4add_i8packed.ll --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 12 ++- clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 10 +++ .../builtins/dot4add_i8packed.hlsl| 17 .../BuiltIns/dot4add_i8packed-errors.hlsl | 28 +++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 10 +++ .../Target/SPIRV/SPIRVInstructionSelector.cpp | 84 +++ llvm/test/CodeGen/DirectX/dot4add_i8packed.ll | 10 +++ .../SPIRV/hlsl-intrinsics/dot4add_i8packed.ll | 48 +++ 12 files changed, 227 insertions(+), 1 deletion(-) create mode 100644 clang/test/CodeGenHLSL/builtins/dot4add_i8packed.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/dot4add_i8packed-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/dot4add_i8packed.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/dot4add_i8packed.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 90475a361bb8f8..eb6b07e8858602 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4792,6 +4792,12 @@ def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDot4AddI8Packed : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_dot4add_i8packed"]; + let Attributes = [NoThrow, Const]; + let Prototype = "int(unsigned int, unsigned int, int)"; +} + def HLSLFrac : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_frac"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 28f28c70b5ae52..13ed0f99da9815 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18722,7 +18722,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, /*ReturnType=*/T0->getScalarType(), getDotProductIntrinsic(CGM.getHLSLRuntime(), VecTy0->getElementType()), ArrayRef{Op0, Op1}, nullptr, "hlsl.dot"); - } break; + } + case Builtin::BI__builtin_hlsl_dot4add_i8packed: { +Value *A = EmitScalarExpr(E->getArg(0)); +Value *B = EmitScalarExpr(E->getArg(1)); +Value *C = EmitScalarExpr(E->getArg(2)); + +Intrinsic::ID ID = CGM.getHLSLRuntime().getDot4AddI8PackedIntrinsic(); +return Builder.CreateIntrinsic( +/*ReturnType=*/C->getType(), ID, ArrayRef{A, B, C}, nullptr, +"hlsl.dot4add.i8packed"); + } case Builtin::BI__builtin_hlsl_lerp: { Value *X = EmitScalarExpr(E->getArg(0)); Value *Y = EmitScalarExpr(E->getArg(1)); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index ff7df41b5c62e7..8b1141375106cc 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -89,6 +89,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(FDot, fdot) GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) + GENERATE_HLSL_INTRINSIC_FUNCTION(Dot4AddI8Packed, dot4add_i8packed) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_readlane) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 30dce60b3ff702..d10bfcbeed97ea 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -894,6 +894,16 @@ uint64_t dot(uint64_t3, uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) uint64_t dot(uint64_t4, uint64_t4); +//===--===// +// dot4add builtins +//===--===// + +/// \fn int dot4add_i8packed(uint A, uint B, int C) + +_HLSL_16BIT_AVAILABILITY(shadermodel, 6.4) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot4a
[clang] [llvm] [HLSL][SPIRV][DXIL] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/112400 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
@@ -820,3 +820,12 @@ def WaveGetLaneIndex : DXILOp<111, waveGetLaneIndex> { let stages = [Stages]; let attributes = [Attributes]; } + +def WaveAllBitCount : DXILOp<135, waveAllOp> { + let Doc = "returns the count of bits set to 1 across the wave"; + let LLVMIntrinsic = int_dx_wave_active_countbits; + let arguments = [Int1Ty]; + let result = Int32Ty; + let stages = [Stages]; + let attributes = [Attributes]; inbelic wrote: @pow2clk Just want to ping to double check these attributes are okay. `ReadNone` is not in `hctdb.py` but it would seem to be applicable. Should `IsWave` be added now or will we add them all at once in a separate commit? https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [HLSL][SPIRV] Implement `WaveActiveSum` intrinsic (PR #112400)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/112400 >From cb507ccb6abbd39198011f5213371bd22405fb30 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Fri, 18 Oct 2024 10:49:18 -0700 Subject: [PATCH] [HLSL][SPIRV][DXIL] Implement `WaveActiveSum` intrinsic - add clang builtin to Builtins.td - link builtin in hlsl_intrinsics - add codegen for spirv intrinsic and two directx intrinsics to retain signedness information of the operands in CGBuiltin.cpp - add semantic analysis in SemaHLSL.cpp - add lowering of spirv intrinsic to spirv backend in SPIRVInstructionSelector.cpp - add lowering of directx intrinsics to WaveActiveOp dxil op in DXIL.td - add test cases to illustrate passes --- clang/include/clang/Basic/Builtins.td | 6 + .../clang/Basic/DiagnosticSemaKinds.td| 3 + clang/lib/CodeGen/CGBuiltin.cpp | 34 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 99 clang/lib/Sema/SemaHLSL.cpp | 31 .../CodeGenHLSL/builtins/WaveActiveSum.hlsl | 45 ++ .../BuiltIns/WaveActiveSum-errors.hlsl| 28 llvm/include/llvm/IR/IntrinsicsDirectX.td | 2 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 30 .../DirectX/DirectXTargetTransformInfo.cpp| 2 + .../Target/SPIRV/SPIRVInstructionSelector.cpp | 30 llvm/test/CodeGen/DirectX/WaveActiveSum.ll| 143 ++ .../SPIRV/hlsl-intrinsics/WaveActiveSum.ll| 41 + 14 files changed, 495 insertions(+) create mode 100644 clang/test/CodeGenHLSL/builtins/WaveActiveSum.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveActiveSum-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/WaveActiveSum.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveActiveSum.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 9bd67e0cefebc3..ee97f0b2326fb8 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4750,6 +4750,12 @@ def HLSLWaveActiveCountBits : LangBuiltin<"HLSL_LANG"> { let Prototype = "unsigned int(bool)"; } +def HLSLWaveActiveSum : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_wave_active_sum"]; + let Attributes = [NoThrow, Const]; + let Prototype = "void (...)"; +} + def HLSLWaveGetLaneIndex : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_wave_get_lane_index"]; let Attributes = [NoThrow, Const]; diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index 34ff49d7238a7f..b84577a38518ff 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -9236,6 +9236,9 @@ def err_typecheck_expect_scalar_or_vector : Error< "a vector of such type is required">; def err_typecheck_expect_any_scalar_or_vector : Error< "invalid operand of type %0 where a scalar or vector is required">; +def err_typecheck_expect_scalar_or_vector_not_type : Error< + "invalid operand of type %0 where %1 or " + "a vector of such type is not allowed">; def err_typecheck_expect_flt_or_vector : Error< "invalid operand of type %0 where floating, complex or " "a vector of such types is required">; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 65d7f5c54a1913..beb4e66272d44b 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18715,6 +18715,23 @@ static Intrinsic::ID getDotProductIntrinsic(CGHLSLRuntime &RT, QualType QT) { return RT.getUDotIntrinsic(); } +// Return wave active sum that corresponds to the QT scalar type +static Intrinsic::ID getWaveActiveSumIntrinsic(llvm::Triple::ArchType Arch, + CGHLSLRuntime &RT, QualType QT) { + switch (Arch) { + case llvm::Triple::spirv: +return llvm::Intrinsic::spv_wave_active_sum; + case llvm::Triple::dxil: { +if (QT->isUnsignedIntegerType()) + return llvm::Intrinsic::dx_wave_active_usum; +return llvm::Intrinsic::dx_wave_active_sum; + } + default: +llvm_unreachable("Intrinsic WaveActiveSum" + " not supported by target architecture"); + } +} + Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, const CallExpr *E, ReturnValueSlot ReturnValue) { @@ -18960,6 +18977,23 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: { /*ReturnType=*/Op0->getType(), CGM.getHLSLRuntime().getStepIntrinsic(), ArrayRef{Op0, Op1}, nullptr, "hlsl.step"); } + case Builtin::BI__builtin_hlsl_wave_active_sum: { +// Due to the use of variadic arguments, explicitly retreive argument +Value *OpExpr = EmitScalarExpr(E->getArg(0)); +llvm::FunctionType *FT = llvm::Func
[clang] [llvm] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic (PR #113623)
https://github.com/inbelic updated https://github.com/llvm/llvm-project/pull/113623 >From 81dfa26a941f7a0926a3126fe3ebbb4d2a67cec1 Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Wed, 23 Oct 2024 22:59:15 + Subject: [PATCH 1/4] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic - create a clang built-in in Builtins.td - link dot4add_i8packed in hlsl_intrinsics.h - add lowering to spirv backend through expansion of operation as OPSDot is missing up to SPIRV 1.6 in SPIRVInstructionSelector.cpp - add dot4add_i8packed intrinsic to IntrinsicsDirectX.td and mapping to DXIL.td op Dot4AddI8Packed - add tests for HLSL intrinsic lowering to dx/spv intrinsic in dot4add_i8packed.hlsl - add tests for sema checks in dot4add_i8packed-errors.hlsl - add test of spir-v lowering in SPIRV/dot4add_i8packed.ll - add test to dxil lowering in DirectX/dot4add_i8packed.ll --- clang/include/clang/Basic/Builtins.td | 6 ++ clang/lib/CodeGen/CGBuiltin.cpp | 12 ++- clang/lib/CodeGen/CGHLSLRuntime.h | 1 + clang/lib/Headers/hlsl/hlsl_intrinsics.h | 10 +++ .../builtins/dot4add_i8packed.hlsl| 17 .../BuiltIns/dot4add_i8packed-errors.hlsl | 28 +++ llvm/include/llvm/IR/IntrinsicsDirectX.td | 1 + llvm/include/llvm/IR/IntrinsicsSPIRV.td | 1 + llvm/lib/Target/DirectX/DXIL.td | 10 +++ .../Target/SPIRV/SPIRVInstructionSelector.cpp | 84 +++ llvm/test/CodeGen/DirectX/dot4add_i8packed.ll | 10 +++ .../SPIRV/hlsl-intrinsics/dot4add_i8packed.ll | 48 +++ 12 files changed, 227 insertions(+), 1 deletion(-) create mode 100644 clang/test/CodeGenHLSL/builtins/dot4add_i8packed.hlsl create mode 100644 clang/test/SemaHLSL/BuiltIns/dot4add_i8packed-errors.hlsl create mode 100644 llvm/test/CodeGen/DirectX/dot4add_i8packed.ll create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/dot4add_i8packed.ll diff --git a/clang/include/clang/Basic/Builtins.td b/clang/include/clang/Basic/Builtins.td index 90475a361bb8f8..eb6b07e8858602 100644 --- a/clang/include/clang/Basic/Builtins.td +++ b/clang/include/clang/Basic/Builtins.td @@ -4792,6 +4792,12 @@ def HLSLDotProduct : LangBuiltin<"HLSL_LANG"> { let Prototype = "void(...)"; } +def HLSLDot4AddI8Packed : LangBuiltin<"HLSL_LANG"> { + let Spellings = ["__builtin_hlsl_dot4add_i8packed"]; + let Attributes = [NoThrow, Const]; + let Prototype = "int(unsigned int, unsigned int, int)"; +} + def HLSLFrac : LangBuiltin<"HLSL_LANG"> { let Spellings = ["__builtin_hlsl_elementwise_frac"]; let Attributes = [NoThrow, Const]; diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp index 28f28c70b5ae52..13ed0f99da9815 100644 --- a/clang/lib/CodeGen/CGBuiltin.cpp +++ b/clang/lib/CodeGen/CGBuiltin.cpp @@ -18722,7 +18722,17 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID, /*ReturnType=*/T0->getScalarType(), getDotProductIntrinsic(CGM.getHLSLRuntime(), VecTy0->getElementType()), ArrayRef{Op0, Op1}, nullptr, "hlsl.dot"); - } break; + } + case Builtin::BI__builtin_hlsl_dot4add_i8packed: { +Value *A = EmitScalarExpr(E->getArg(0)); +Value *B = EmitScalarExpr(E->getArg(1)); +Value *C = EmitScalarExpr(E->getArg(2)); + +Intrinsic::ID ID = CGM.getHLSLRuntime().getDot4AddI8PackedIntrinsic(); +return Builder.CreateIntrinsic( +/*ReturnType=*/C->getType(), ID, ArrayRef{A, B, C}, nullptr, +"hlsl.dot4add.i8packed"); + } case Builtin::BI__builtin_hlsl_lerp: { Value *X = EmitScalarExpr(E->getArg(0)); Value *Y = EmitScalarExpr(E->getArg(1)); diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h index ff7df41b5c62e7..8b1141375106cc 100644 --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -89,6 +89,7 @@ class CGHLSLRuntime { GENERATE_HLSL_INTRINSIC_FUNCTION(FDot, fdot) GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot) GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot) + GENERATE_HLSL_INTRINSIC_FUNCTION(Dot4AddI8Packed, dot4add_i8packed) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane) GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_readlane) diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h b/clang/lib/Headers/hlsl/hlsl_intrinsics.h index 30dce60b3ff702..d10bfcbeed97ea 100644 --- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h +++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h @@ -894,6 +894,16 @@ uint64_t dot(uint64_t3, uint64_t3); _HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot) uint64_t dot(uint64_t4, uint64_t4); +//===--===// +// dot4add builtins +//===--===// + +/// \fn int dot4add_i8packed(uint A, uint B, int C) + +_HLSL_16BIT_AVAILABILITY(shadermodel, 6.4) +_HLSL_BUILTIN_ALIAS(__builtin_hlsl_dot4a
[clang] [llvm] [HLSL][SPIRV][DXIL] Implement `dot4add_i8packed` intrinsic (PR #113623)
@@ -1694,6 +1698,84 @@ bool SPIRVInstructionSelector::selectIntegerDot(Register ResVReg, return Result; } +// Since pre-1.6 SPIRV has no DotProductInput4x8BitPacked implementation, +// extract the elements of the packed inputs, multiply them and add the result +// to the accumulator. inbelic wrote: Okay sounds good thanks. In terms of when the operation is not available, do you agree with the current expansion implementation? https://github.com/llvm/llvm-project/pull/113623 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
https://github.com/inbelic edited https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] [DXIL][SPIRV] Lower WaveActiveCountBits intrinsic (PR #113382)
https://github.com/inbelic deleted https://github.com/llvm/llvm-project/pull/113382 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [llvm] Inbelic/as double (PR #114847)
https://github.com/inbelic created https://github.com/llvm/llvm-project/pull/114847 None >From f340a6f0421693bd3489adc1c68983dfae9646dd Mon Sep 17 00:00:00 2001 From: Finn Plummer Date: Mon, 4 Nov 2024 17:38:36 + Subject: [PATCH 1/4] [NFC][Scalarizer][TargetTransformInfo] Add `isVectorIntrinsicWithOverloadTypeAtArg` This changes allows target intrinsic to specify overloaded types. This change will let us add scalarization for `asdouble`: --- llvm/include/llvm/Analysis/TargetTransformInfo.h | 14 ++ .../llvm/Analysis/TargetTransformInfoImpl.h| 6 ++ llvm/include/llvm/CodeGen/BasicTTIImpl.h | 6 ++ llvm/lib/Analysis/TargetTransformInfo.cpp | 6 ++ .../Target/DirectX/DirectXTargetTransformInfo.cpp | 8 .../Target/DirectX/DirectXTargetTransformInfo.h| 3 +++ llvm/lib/Transforms/Scalar/Scalarizer.cpp | 9 ++--- 7 files changed, 49 insertions(+), 3 deletions(-) diff --git a/llvm/include/llvm/Analysis/TargetTransformInfo.h b/llvm/include/llvm/Analysis/TargetTransformInfo.h index 0459941fe05cdc..796b4011d71c0c 100644 --- a/llvm/include/llvm/Analysis/TargetTransformInfo.h +++ b/llvm/include/llvm/Analysis/TargetTransformInfo.h @@ -896,6 +896,10 @@ class TargetTransformInfo { bool isTargetIntrinsicWithScalarOpAtArg(Intrinsic::ID ID, unsigned ScalarOpdIdx) const; + bool isVectorIntrinsicWithOverloadTypeAtArg(Intrinsic::ID ID, + unsigned ScalarOpdIdx, + bool Default) const; + /// Estimate the overhead of scalarizing an instruction. Insert and Extract /// are set if the demanded result elements need to be inserted and/or /// extracted from vectors. @@ -1969,6 +1973,9 @@ class TargetTransformInfo::Concept { virtual bool isTargetIntrinsicTriviallyScalarizable(Intrinsic::ID ID) = 0; virtual bool isTargetIntrinsicWithScalarOpAtArg(Intrinsic::ID ID, unsigned ScalarOpdIdx) = 0; + virtual bool isVectorIntrinsicWithOverloadTypeAtArg(Intrinsic::ID ID, + unsigned ScalarOpdIdx, + bool Default) = 0; virtual InstructionCost getScalarizationOverhead(VectorType *Ty, const APInt &DemandedElts, bool Insert, bool Extract, @@ -2530,6 +2537,13 @@ class TargetTransformInfo::Model final : public TargetTransformInfo::Concept { return Impl.isTargetIntrinsicWithScalarOpAtArg(ID, ScalarOpdIdx); } + bool isVectorIntrinsicWithOverloadTypeAtArg(Intrinsic::ID ID, + unsigned ScalarOpdIdx, + bool Default) override { +return Impl.isVectorIntrinsicWithOverloadTypeAtArg(ID, ScalarOpdIdx, + Default); + } + InstructionCost getScalarizationOverhead(VectorType *Ty, const APInt &DemandedElts, bool Insert, bool Extract, diff --git a/llvm/include/llvm/Analysis/TargetTransformInfoImpl.h b/llvm/include/llvm/Analysis/TargetTransformInfoImpl.h index dbdfb4d8cdfa32..42d1082cf4d9eb 100644 --- a/llvm/include/llvm/Analysis/TargetTransformInfoImpl.h +++ b/llvm/include/llvm/Analysis/TargetTransformInfoImpl.h @@ -392,6 +392,12 @@ class TargetTransformInfoImplBase { return false; } + bool isVectorIntrinsicWithOverloadTypeAtArg(Intrinsic::ID ID, + unsigned ScalarOpdIdx, + bool Default) const { +return Default; + } + InstructionCost getScalarizationOverhead(VectorType *Ty, const APInt &DemandedElts, bool Insert, bool Extract, diff --git a/llvm/include/llvm/CodeGen/BasicTTIImpl.h b/llvm/include/llvm/CodeGen/BasicTTIImpl.h index db3b5cddd7c1c3..b2841e778947dd 100644 --- a/llvm/include/llvm/CodeGen/BasicTTIImpl.h +++ b/llvm/include/llvm/CodeGen/BasicTTIImpl.h @@ -798,6 +798,12 @@ class BasicTTIImplBase : public TargetTransformInfoImplCRTPBase { return false; } + bool isVectorIntrinsicWithOverloadTypeAtArg(Intrinsic::ID ID, + unsigned ScalarOpdIdx, + bool Default) const { +return Default; + } + /// Helper wrapper for the DemandedElts variant of getScalarizationOverhead. InstructionCost getScalarizationOverhead(VectorType *InTy, bool Insert, bool Extract, diff --git a/llvm/lib/Analysis/TargetTransformInfo.cpp b/llvm/lib/Analysis/TargetTransformInfo.cpp index a47462b61e03b2