Skip to content

[DirectX] Add resource name argument to llvm.dx.handlefrom[implicit]binding intrinsics #139991

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 8 commits into from
May 28, 2025

Conversation

hekota
Copy link
Member

@hekota hekota commented May 15, 2025

Adds resource name argument to llvm.dx.handlefrombinding and llvm.dx.handlefromimplicitbinding intrinsics.
SPIR-V currently does not seem to need the resource names so this change only affects DirectX binding intrinsics.

Part 2/4 of #105059

Depends on #139985

@hekota hekota force-pushed the users/hekota/pr139985-resource-names-clang branch from f42d017 to 8776c02 Compare May 16, 2025 21:09
@hekota hekota force-pushed the resource-names-llvm-intr branch from 2bacb22 to 61c8945 Compare May 16, 2025 21:11
@hekota hekota changed the title [DirectX] Add resource name argument to llvm.dx.handlefrombinding intrinsic (DirectX only) [DirectX] Add resource name argument to llvm.dx.handlefrom[implicit]binding intrinsic (DirectX only) May 19, 2025
@hekota hekota changed the title [DirectX] Add resource name argument to llvm.dx.handlefrom[implicit]binding intrinsic (DirectX only) [DirectX] Add resource name argument to llvm.dx.handlefrom[implicit]binding intrinsics (DirectX only) May 19, 2025
@hekota hekota requested a review from bogner May 19, 2025 22:31
@hekota hekota marked this pull request as ready for review May 19, 2025 22:32
@llvmbot llvmbot added clang Clang issues not falling into any other category clang:codegen IR generation bugs: mangling, exceptions, etc. backend:DirectX HLSL HLSL Language Support llvm:ir llvm:analysis labels May 19, 2025
@llvmbot
Copy link
Member

llvmbot commented May 19, 2025

@llvm/pr-subscribers-backend-directx

@llvm/pr-subscribers-hlsl

Author: Helena Kotas (hekota)

Changes

Adds resource name argument to llvm.dx.handlefrombinding and llvm.dx.handlefromimplicitbinding intrinsics.
SPIR-V currently does not seem to need the resource names so this change only affects DirectX binding intrinsics.

Part 2/4 of #105059

Depends on #139985


Patch is 154.52 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/139991.diff

69 Files Affected:

  • (modified) clang/lib/CodeGen/CGHLSLBuiltins.cpp (+28-7)
  • (modified) clang/lib/CodeGen/CGHLSLRuntime.cpp (+26-12)
  • (modified) clang/lib/CodeGen/CGHLSLRuntime.h (+3)
  • (modified) clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl (+2-2)
  • (modified) clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl (+2-2)
  • (modified) clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl (+2-2)
  • (modified) clang/test/CodeGenHLSL/cbuffer.hlsl (+17-10)
  • (modified) clang/test/CodeGenHLSL/cbuffer_with_packoffset.hlsl (+2-1)
  • (modified) clang/test/CodeGenHLSL/resource-bindings.hlsl (+4-4)
  • (modified) llvm/include/llvm/IR/IntrinsicsDirectX.td (+2-2)
  • (modified) llvm/lib/Target/DirectX/DXILOpLowering.cpp (+17-11)
  • (modified) llvm/lib/Target/DirectX/DXILResourceImplicitBinding.cpp (+2-1)
  • (modified) llvm/test/Analysis/DXILResource/buffer-frombinding.ll (+10-10)
  • (modified) llvm/test/CodeGen/DirectX/BufferLoad-sm61.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/BufferLoad.ll (+8-8)
  • (modified) llvm/test/CodeGen/DirectX/BufferStore-errors.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/BufferStore-sm61.ll (+6-6)
  • (modified) llvm/test/CodeGen/DirectX/BufferStore.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/array-typedgep.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/arrays.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/scalars.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/vectors.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferLoadLegacy-errors.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/CBufferLoadLegacy.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ContainerData/PSVResources-order.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ContainerData/PSVResources.ll (+8-8)
  • (modified) llvm/test/CodeGen/DirectX/CreateHandle.ll (+13-6)
  • (modified) llvm/test/CodeGen/DirectX/CreateHandleFromBinding.ll (+14-7)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/alloca.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/ambiguous.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/buffer-O0.ll (+4-4)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/cbuffer-access.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/undominated.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/arrays.ll (+10-10)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/multiple-spaces.ll (+12-12)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/simple.ll (+6-6)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/unbounded-arrays-error.ll (+4-4)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/unbounded-arrays.ll (+8-8)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/cbuffer-only.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/cbuffer_metadata.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/resource-symbols.ll (+5-5)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/srv_metadata.ll (+9-9)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/uav_metadata.ll (+12-12)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferLoad-error64.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferLoad.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferStore-error64.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferStore.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/load_rawbuffer.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/load_typedbuffer.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/store_rawbuffer.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/store_typedbuffer.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ResourceGlobalElimination.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/max-64-uavs-array-valver1.5.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/max-64-uavs-array-valver1.6.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/max-64-uavs.ll (+9-9)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/raw-and-structured-buffers.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-alias-0.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-alias-1.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-not-alias-sm6.6.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-not-alias-sm6.7.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-not-alias-valver1.8.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/typed-uav-load-additional-formats.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/uavs-at-every-stage-lib-valver1.7.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/uavs-at-every-stage-lib-valver1.8.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/uavs-at-every-stage-vs.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/bufferUpdateCounter.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/resource_counter_error.ll (+1-1)
  • (modified) llvm/unittests/Target/DirectX/ResourceBindingAnalysisTests.cpp (+21-21)
  • (modified) llvm/unittests/Target/DirectX/UniqueResourceFromUseTests.cpp (+6-6)
diff --git a/clang/lib/CodeGen/CGHLSLBuiltins.cpp b/clang/lib/CodeGen/CGHLSLBuiltins.cpp
index d4a0714da07b3..0e0bafb0d3fd6 100644
--- a/clang/lib/CodeGen/CGHLSLBuiltins.cpp
+++ b/clang/lib/CodeGen/CGHLSLBuiltins.cpp
@@ -299,9 +299,20 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID,
     // (llvm/llvm-project#135452)
     Value *NonUniform =
         llvm::ConstantInt::get(llvm::Type::getInt1Ty(getLLVMContext()), false);
-    return Builder.CreateIntrinsic(
-        HandleTy, CGM.getHLSLRuntime().getCreateHandleFromBindingIntrinsic(),
-        ArrayRef<Value *>{SpaceOp, RegisterOp, RangeOp, IndexOp, NonUniform});
+
+    Intrinsic::ID IID =
+        CGM.getHLSLRuntime().getCreateHandleFromBindingIntrinsic();
+    // SPIR-V intrinsic does not have include the resource name
+    if (IID == Intrinsic::spv_resource_handlefrombinding)
+      return Builder.CreateIntrinsic(
+          HandleTy, IID,
+          ArrayRef<Value *>{SpaceOp, RegisterOp, RangeOp, IndexOp, NonUniform});
+
+    Value *NameOp = EmitScalarExpr(E->getArg(5));
+    return Builder.CreateIntrinsic(HandleTy, IID,
+                                   ArrayRef<Value *>{SpaceOp, RegisterOp,
+                                                     RangeOp, IndexOp,
+                                                     NonUniform, NameOp});
   }
   case Builtin::BI__builtin_hlsl_resource_handlefromimplicitbinding: {
     llvm::Type *HandleTy = CGM.getTypes().ConvertType(E->getType());
@@ -313,10 +324,20 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID,
     // (llvm/llvm-project#135452)
     Value *NonUniform =
         llvm::ConstantInt::get(llvm::Type::getInt1Ty(getLLVMContext()), false);
-    return Builder.CreateIntrinsic(
-        HandleTy,
-        CGM.getHLSLRuntime().getCreateHandleFromImplicitBindingIntrinsic(),
-        ArrayRef<Value *>{OrderID, SpaceOp, RangeOp, IndexOp, NonUniform});
+
+    Intrinsic::ID IID =
+        CGM.getHLSLRuntime().getCreateHandleFromImplicitBindingIntrinsic();
+    // SPIR-V intrinsic does not include the resource name
+    if (IID == Intrinsic::spv_resource_handlefromimplicitbinding)
+      return Builder.CreateIntrinsic(
+          HandleTy, IID,
+          ArrayRef<Value *>{OrderID, SpaceOp, RangeOp, IndexOp, NonUniform});
+
+    Value *NameOp = EmitScalarExpr(E->getArg(5));
+    return Builder.CreateIntrinsic(HandleTy, IID,
+                                   ArrayRef<Value *>{OrderID, SpaceOp, RangeOp,
+                                                     IndexOp, NonUniform,
+                                                     NameOp});
   }
   case Builtin::BI__builtin_hlsl_all: {
     Value *Op0 = EmitScalarExpr(E->getArg(0));
diff --git a/clang/lib/CodeGen/CGHLSLRuntime.cpp b/clang/lib/CodeGen/CGHLSLRuntime.cpp
index a708b3aea129d..b9577a0dc48a1 100644
--- a/clang/lib/CodeGen/CGHLSLRuntime.cpp
+++ b/clang/lib/CodeGen/CGHLSLRuntime.cpp
@@ -42,10 +42,6 @@ using namespace llvm;
 
 using llvm::hlsl::CBufferRowSizeInBytes;
 
-static void initializeBufferFromBinding(CodeGenModule &CGM,
-                                        llvm::GlobalVariable *GV,
-                                        HLSLResourceBindingAttr *RBA);
-
 namespace {
 
 void addDxilValVersion(StringRef ValVersionStr, llvm::Module &M) {
@@ -275,7 +271,7 @@ void CGHLSLRuntime::addBuffer(const HLSLBufferDecl *BufDecl) {
   HLSLResourceBindingAttr *RBA = BufDecl->getAttr<HLSLResourceBindingAttr>();
   assert(RBA &&
          "cbuffer/tbuffer should always have resource binding attribute");
-  initializeBufferFromBinding(CGM, BufGV, RBA);
+  initializeBufferFromBinding(BufDecl, BufGV, RBA);
 }
 
 llvm::TargetExtType *
@@ -557,29 +553,47 @@ static void initializeBuffer(CodeGenModule &CGM, llvm::GlobalVariable *GV,
   CGM.AddCXXGlobalInit(InitResFunc);
 }
 
-static void initializeBufferFromBinding(CodeGenModule &CGM,
-                                        llvm::GlobalVariable *GV,
-                                        HLSLResourceBindingAttr *RBA) {
+void CGHLSLRuntime::initializeBufferFromBinding(const HLSLBufferDecl *BufDecl,
+                                                llvm::GlobalVariable *GV,
+                                                HLSLResourceBindingAttr *RBA) {
   llvm::Type *Int1Ty = llvm::Type::getInt1Ty(CGM.getLLVMContext());
   auto *NonUniform = llvm::ConstantInt::get(Int1Ty, false);
   auto *Index = llvm::ConstantInt::get(CGM.IntTy, 0);
   auto *RangeSize = llvm::ConstantInt::get(CGM.IntTy, 1);
   auto *Space =
       llvm::ConstantInt::get(CGM.IntTy, RBA ? RBA->getSpaceNumber() : 0);
+  Value *Name = nullptr;
+
+  // DXIL intrinsic includes resource name
+  if (getArch() == Triple::dxil) {
+    std::string Str = std::string(BufDecl->getName());
+    std::string GlobalName = Str + ".str";
+    Name = CGM.GetAddrOfConstantCString(Str, GlobalName.c_str()).getPointer();
+  }
 
+  // buffer with explicit binding
   if (RBA->hasRegisterSlot()) {
     auto *RegSlot = llvm::ConstantInt::get(CGM.IntTy, RBA->getSlotNumber());
     Intrinsic::ID Intr =
         CGM.getHLSLRuntime().getCreateHandleFromBindingIntrinsic();
-    initializeBuffer(CGM, GV, Intr,
-                     {Space, RegSlot, RangeSize, Index, NonUniform});
+    if (Name)
+      initializeBuffer(CGM, GV, Intr,
+                       {Space, RegSlot, RangeSize, Index, NonUniform, Name});
+    else
+      initializeBuffer(CGM, GV, Intr,
+                       {Space, RegSlot, RangeSize, Index, NonUniform});
   } else {
+    // buffer with implicit binding
     auto *OrderID =
         llvm::ConstantInt::get(CGM.IntTy, RBA->getImplicitBindingOrderID());
     Intrinsic::ID Intr =
         CGM.getHLSLRuntime().getCreateHandleFromImplicitBindingIntrinsic();
-    initializeBuffer(CGM, GV, Intr,
-                     {OrderID, Space, RangeSize, Index, NonUniform});
+    if (Name)
+      initializeBuffer(CGM, GV, Intr,
+                       {OrderID, Space, RangeSize, Index, NonUniform, Name});
+    else
+      initializeBuffer(CGM, GV, Intr,
+                       {OrderID, Space, RangeSize, Index, NonUniform});
   }
 }
 
diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h
index e40864d8ed854..f86dca8c4fd26 100644
--- a/clang/lib/CodeGen/CGHLSLRuntime.h
+++ b/clang/lib/CodeGen/CGHLSLRuntime.h
@@ -164,6 +164,9 @@ class CGHLSLRuntime {
 private:
   void emitBufferGlobalsAndMetadata(const HLSLBufferDecl *BufDecl,
                                     llvm::GlobalVariable *BufGV);
+  void initializeBufferFromBinding(const HLSLBufferDecl *BufDecl,
+                                   llvm::GlobalVariable *GV,
+                                   HLSLResourceBindingAttr *RBA);
   llvm::Triple::ArchType getArch();
 
   llvm::DenseMap<const clang::RecordType *, llvm::TargetExtType *> LayoutTypes;
diff --git a/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl b/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl
index 2601a2ee4ff35..c29166e3fd749 100644
--- a/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl
@@ -70,7 +70,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl17ByteAddressBufferC2EjjijPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %registerNo, i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, ptr noundef %name)
 // CHECK-DXIL: %[[HANDLE:.*]] = call target("dx.RawBuffer", i8, 0, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_i8_0_0t(
-// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::ByteAddressBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-DXIL-NEXT: store target("dx.RawBuffer", i8, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
@@ -79,7 +79,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl19RWByteAddressBufferC2EjijjPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, i32 noundef %orderId, ptr noundef %name)
 // CHECK: %[[HANDLE:.*]] = call target("dx.RawBuffer", i8, 1, 0) @llvm.dx.resource.handlefromimplicitbinding.tdx.RawBuffer_i8_1_0t
-// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWByteAddressBuffer", ptr %this1, i32 0, i32 0
 // CHECK-NEXT: store target("dx.RawBuffer", i8, 1, 0) %[[HANDLE]], ptr %__handle, align 4
 
diff --git a/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl b/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl
index c2796fa177705..16e994457259a 100644
--- a/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl
@@ -67,7 +67,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl8RWBufferIfEC2EjjijPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %registerNo, i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, ptr noundef %name)
 // CHECK-DXIL: %[[HANDLE:.*]] = call target("dx.TypedBuffer", float, 1, 0, 0) @llvm.dx.resource.handlefrombinding.tdx.TypedBuffer_f32_1_0_0t(
-// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-DXIL-NEXT: store target("dx.TypedBuffer", float, 1, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
@@ -76,7 +76,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl8RWBufferIdEC2EjijjPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, i32 noundef %orderId, ptr noundef %name)
 // CHECK: %[[HANDLE:.*]] = call target("dx.TypedBuffer", double, 1, 0, 0) @llvm.dx.resource.handlefromimplicitbinding.tdx.TypedBuffer_f64_1_0_0t
-// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CEHCK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWBuffer.0", ptr %{{.*}}, i32 0, i32 0
 // CHECK-NEXT: store target("dx.TypedBuffer", double, 1, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
diff --git a/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl b/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl
index a85a0b0880b6b..9dd5a9b80da88 100644
--- a/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl
@@ -71,7 +71,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl16StructuredBufferIfEC2EjjijPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %registerNo, i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, ptr noundef %name)
 // CHECK-DXIL: %[[HANDLE:.*]] = call target("dx.RawBuffer", float, 0, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_0_0t(
-// CHECK-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::StructuredBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-DXIL-NEXT: store target("dx.RawBuffer", float, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
@@ -80,7 +80,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl18RWStructuredBufferIfEC2EjijjPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, i32 noundef %orderId, ptr noundef %name)
 // CHECK: %[[HANDLE:.*]] = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefromimplicitbinding.tdx.RawBuffer_f32_1_0t
-// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWStructuredBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-NEXT: store target("dx.RawBuffer", float, 1, 0) %[[HANDLE]], ptr %__handle, align 4
 
diff --git a/clang/test/CodeGenHLSL/cbuffer.hlsl b/clang/test/CodeGenHLSL/cbuffer.hlsl
index 3fb76d57341cf..e0919266dc3b7 100644
--- a/clang/test/CodeGenHLSL/cbuffer.hlsl
+++ b/clang/test/CodeGenHLSL/cbuffer.hlsl
@@ -54,6 +54,7 @@ cbuffer CBScalars : register(b1, space5) {
 // CHECK: @a6 = external addrspace(2) global i16, align 2
 // CHECK: @a7 = external addrspace(2) global i32, align 4
 // CHECK: @a8 = external addrspace(2) global i64, align 8
+// CHECK: @CBScalars.str = private unnamed_addr constant [10 x i8] c"CBScalars\00", align 1
 
 cbuffer CBVectors {
   float3 b1;
@@ -75,6 +76,7 @@ cbuffer CBVectors {
 // CHECK: @b5 = external addrspace(2) global <4 x i32>, align 16
 // CHECK: @b6 = external addrspace(2) global <3 x i16>, align 8
 // CHECK: @b7 = external addrspace(2) global <3 x i64>, align 32
+// CHECK: @CBVectors.str = private unnamed_addr constant [10 x i8] c"CBVectors\00", align 1
 
 cbuffer CBArrays : register(b2) {
   float c1[3];
@@ -97,6 +99,7 @@ cbuffer CBArrays : register(b2) {
 // CHECK: @c6 = external addrspace(2) global [1 x i16], align 2
 // CHECK: @c7 = external addrspace(2) global [2 x i64], align 8
 // CHECK: @c8 = external addrspace(2) global [4 x i32], align 4
+// CHECK: @CBArrays.str = private unnamed_addr constant [9 x i8] c"CBArrays\00", align 1
 
 typedef uint32_t4 uint32_t8[2];
 typedef uint4 T1;
@@ -111,6 +114,7 @@ cbuffer CBTypedefArray : register(space2) {
 // CHECK-SAME: 128, 0, 64))
 // CHECK: @t1 = external addrspace(2) global [2 x [2 x <4 x i32>]], align 16
 // CHECK: @t2 = external addrspace(2) global [2 x [2 x <4 x i32>]], align 16
+// CHECK: @CBTypedefArray.str = private unnamed_addr constant [15 x i8] c"CBTypedefArray\00", align 1
 struct Empty {};
 
 struct A {
@@ -140,6 +144,7 @@ struct D {
 // CHECK: @d = external addrspace(2) global target("dx.Layout", %__cblayout_D, 94, 0), align 1
 // CHECK: @e = external addrspace(2) global half, align 2
 // CHECK: @f = external addrspace(2) global <3 x i16>, align 8
+// CHECK: @CBStructs.str = private unnamed_addr constant [10 x i8] c"CBStructs\00", align 1
 
 cbuffer CBStructs {
   A a;
@@ -177,6 +182,7 @@ cbuffer CBClasses {
 // CHECK: @l = external addrspace(2) global target("dx.Layout", %L, 8, 0, 4), align 1
 // CHECK: @m = external addrspace(2) global target("dx.Layout", %M, 68, 0), align 1
 // CHECK: @ka = external addrspace(2) global [10 x target("dx.Layout", %K, 4, 0)], align 1
+// CHECK: @CBClasses.str = private unnamed_addr constant [10 x i8] c"CBClasses\00", align 1
 
 struct Test {
     float a, b;
@@ -194,6 +200,7 @@ struct Test {
 // CHECK: @f7 = external addrspace(2) global float, align 4
 // CHECK: @f8 = external addrspace(2) global <1 x double>, align 8
 // CHECK: @f9 = external addrspace(2) global i16, align 2
+// CHECK: @CBMix.str = private unnamed_addr constant [6 x i8] c"CBMix\00", align 1
 
 cbuffer CBMix {
     Test test[2];
@@ -269,61 +276,61 @@ cbuffer CB_C {
 // CHECK: define internal void @_init_buffer_CBScalars.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBScalars.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBScalars, 56, 0, 8, 16, 24, 32, 36, 40, 48))
-// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBScalarss_56_0_8_16_24_32_36_40_48tt(i32 5, i32 1, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBScalarss_56_0_8_16_24_32_36_40_48tt(i32 5, i32 1, i32 1, i32 0, i1 false, ptr @CBScalars.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBScalars, 56, 0, 8, 16, 24, 32, 36, 40, 48)) %CBScalars.cb_h, ptr @CBScalars.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBVectors.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBVectors.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBVectors, 136, 0, 16, 40, 48, 80, 96, 112))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBVectorss_136_0_16_40_48_80_96_112tt(i32 0, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBVectorss_136_0_16_40_48_80_96_112tt(i32 0, i32 0, i32 1, i32 0, i1 false, ptr @CBVectors.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBVectors, 136, 0, 16, 40, 48, 80, 96, 112)) %CBVectors.cb_h, ptr @CBVectors.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBArrays.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBArrays.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBArrays, 708, 0, 48, 112, 176, 224, 608, 624, 656))
-// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBArrayss_708_0_48_112_176_224_608_624_656tt(i32 0, i32 2, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBArrayss_708_0_48_112_176_224_608_624_656tt(i32 0, i32 2, i32 1, i32 0, i1 false, ptr @CBArrays.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBArrays, 708, 0, 48, 112, 176, 224, 608, 624, 656)) %CBArrays.cb_h, ptr @CBArrays.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBTypedefArray.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBTypedefArray.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBTypedefArray, 128, 0, 64))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBTypedefArrays_128_0_64tt(i32 1, i32 2, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBTypedefArrays_128_0_64tt(i32 1, i32 2, i32 1, i32 0, i1 false, ptr @CBTypedefArray.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBTypedefArray, 128, 0, 64)) %CBTypedefArray.cb_h, ptr @CBTypedefArray.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBStructs.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT:   %CBStructs.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBStructs, 246, 0, 16, 32, 64, 144, 238, 240))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBStructss_246_0_16_32_64_144_238_240tt(i32 2, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBStructss_246_0_16_32_64_144_238_240tt(i32 2, i32 0, i32 1, i32 0, i1 false, ptr @CBStructs.str)
 // CHECK-NEXT:   store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBStructs, 246, 0, 16, 32, 64, 144, 238, 240)) %CBStructs.cb_h, ptr @CBStructs.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBClasses.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBClasses.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBClasses, 260, 0, 16, 32, 112))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBClassess_260_0_16_32_112tt(i32 3, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBClassess_260_0_16_32_112tt(i32 3, i32 0, i32 1, i32 0, i1 false, ptr @CBClasses.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBClasses, 260, 0, 16, 32, 112)) %CBClasses.cb_h, ptr @CBClasses.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBMix.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBMix.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBMix, 170, 0, 24, 32, 120, 128, 136, 144, 152, 160, 168))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBMixs_170_0_24_32_120_128_136_144_152_160_168tt(i32 4, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefro...
[truncated]

@llvmbot
Copy link
Member

llvmbot commented May 19, 2025

@llvm/pr-subscribers-llvm-ir

Author: Helena Kotas (hekota)

Changes

Adds resource name argument to llvm.dx.handlefrombinding and llvm.dx.handlefromimplicitbinding intrinsics.
SPIR-V currently does not seem to need the resource names so this change only affects DirectX binding intrinsics.

Part 2/4 of #105059

Depends on #139985


Patch is 154.52 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/139991.diff

69 Files Affected:

  • (modified) clang/lib/CodeGen/CGHLSLBuiltins.cpp (+28-7)
  • (modified) clang/lib/CodeGen/CGHLSLRuntime.cpp (+26-12)
  • (modified) clang/lib/CodeGen/CGHLSLRuntime.h (+3)
  • (modified) clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl (+2-2)
  • (modified) clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl (+2-2)
  • (modified) clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl (+2-2)
  • (modified) clang/test/CodeGenHLSL/cbuffer.hlsl (+17-10)
  • (modified) clang/test/CodeGenHLSL/cbuffer_with_packoffset.hlsl (+2-1)
  • (modified) clang/test/CodeGenHLSL/resource-bindings.hlsl (+4-4)
  • (modified) llvm/include/llvm/IR/IntrinsicsDirectX.td (+2-2)
  • (modified) llvm/lib/Target/DirectX/DXILOpLowering.cpp (+17-11)
  • (modified) llvm/lib/Target/DirectX/DXILResourceImplicitBinding.cpp (+2-1)
  • (modified) llvm/test/Analysis/DXILResource/buffer-frombinding.ll (+10-10)
  • (modified) llvm/test/CodeGen/DirectX/BufferLoad-sm61.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/BufferLoad.ll (+8-8)
  • (modified) llvm/test/CodeGen/DirectX/BufferStore-errors.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/BufferStore-sm61.ll (+6-6)
  • (modified) llvm/test/CodeGen/DirectX/BufferStore.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/array-typedgep.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/arrays.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/scalars.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferAccess/vectors.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/CBufferLoadLegacy-errors.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/CBufferLoadLegacy.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ContainerData/PSVResources-order.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ContainerData/PSVResources.ll (+8-8)
  • (modified) llvm/test/CodeGen/DirectX/CreateHandle.ll (+13-6)
  • (modified) llvm/test/CodeGen/DirectX/CreateHandleFromBinding.ll (+14-7)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/alloca.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/ambiguous.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/buffer-O0.ll (+4-4)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/cbuffer-access.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ForwardHandleAccesses/undominated.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/arrays.ll (+10-10)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/multiple-spaces.ll (+12-12)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/simple.ll (+6-6)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/unbounded-arrays-error.ll (+4-4)
  • (modified) llvm/test/CodeGen/DirectX/ImplicitBinding/unbounded-arrays.ll (+8-8)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/cbuffer-only.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/cbuffer_metadata.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/resource-symbols.ll (+5-5)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/srv_metadata.ll (+9-9)
  • (modified) llvm/test/CodeGen/DirectX/Metadata/uav_metadata.ll (+12-12)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferLoad-error64.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferLoad.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferStore-error64.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/RawBufferStore.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/load_rawbuffer.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/load_typedbuffer.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/store_rawbuffer.ll (+7-7)
  • (modified) llvm/test/CodeGen/DirectX/ResourceAccess/store_typedbuffer.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ResourceGlobalElimination.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/max-64-uavs-array-valver1.5.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/max-64-uavs-array-valver1.6.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/max-64-uavs.ll (+9-9)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/raw-and-structured-buffers.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-alias-0.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-alias-1.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-not-alias-sm6.6.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-not-alias-sm6.7.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/res-may-not-alias-valver1.8.ll (+2-2)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/typed-uav-load-additional-formats.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/uavs-at-every-stage-lib-valver1.7.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/uavs-at-every-stage-lib-valver1.8.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/ShaderFlags/uavs-at-every-stage-vs.ll (+1-1)
  • (modified) llvm/test/CodeGen/DirectX/bufferUpdateCounter.ll (+3-3)
  • (modified) llvm/test/CodeGen/DirectX/resource_counter_error.ll (+1-1)
  • (modified) llvm/unittests/Target/DirectX/ResourceBindingAnalysisTests.cpp (+21-21)
  • (modified) llvm/unittests/Target/DirectX/UniqueResourceFromUseTests.cpp (+6-6)
diff --git a/clang/lib/CodeGen/CGHLSLBuiltins.cpp b/clang/lib/CodeGen/CGHLSLBuiltins.cpp
index d4a0714da07b3..0e0bafb0d3fd6 100644
--- a/clang/lib/CodeGen/CGHLSLBuiltins.cpp
+++ b/clang/lib/CodeGen/CGHLSLBuiltins.cpp
@@ -299,9 +299,20 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID,
     // (llvm/llvm-project#135452)
     Value *NonUniform =
         llvm::ConstantInt::get(llvm::Type::getInt1Ty(getLLVMContext()), false);
-    return Builder.CreateIntrinsic(
-        HandleTy, CGM.getHLSLRuntime().getCreateHandleFromBindingIntrinsic(),
-        ArrayRef<Value *>{SpaceOp, RegisterOp, RangeOp, IndexOp, NonUniform});
+
+    Intrinsic::ID IID =
+        CGM.getHLSLRuntime().getCreateHandleFromBindingIntrinsic();
+    // SPIR-V intrinsic does not have include the resource name
+    if (IID == Intrinsic::spv_resource_handlefrombinding)
+      return Builder.CreateIntrinsic(
+          HandleTy, IID,
+          ArrayRef<Value *>{SpaceOp, RegisterOp, RangeOp, IndexOp, NonUniform});
+
+    Value *NameOp = EmitScalarExpr(E->getArg(5));
+    return Builder.CreateIntrinsic(HandleTy, IID,
+                                   ArrayRef<Value *>{SpaceOp, RegisterOp,
+                                                     RangeOp, IndexOp,
+                                                     NonUniform, NameOp});
   }
   case Builtin::BI__builtin_hlsl_resource_handlefromimplicitbinding: {
     llvm::Type *HandleTy = CGM.getTypes().ConvertType(E->getType());
@@ -313,10 +324,20 @@ Value *CodeGenFunction::EmitHLSLBuiltinExpr(unsigned BuiltinID,
     // (llvm/llvm-project#135452)
     Value *NonUniform =
         llvm::ConstantInt::get(llvm::Type::getInt1Ty(getLLVMContext()), false);
-    return Builder.CreateIntrinsic(
-        HandleTy,
-        CGM.getHLSLRuntime().getCreateHandleFromImplicitBindingIntrinsic(),
-        ArrayRef<Value *>{OrderID, SpaceOp, RangeOp, IndexOp, NonUniform});
+
+    Intrinsic::ID IID =
+        CGM.getHLSLRuntime().getCreateHandleFromImplicitBindingIntrinsic();
+    // SPIR-V intrinsic does not include the resource name
+    if (IID == Intrinsic::spv_resource_handlefromimplicitbinding)
+      return Builder.CreateIntrinsic(
+          HandleTy, IID,
+          ArrayRef<Value *>{OrderID, SpaceOp, RangeOp, IndexOp, NonUniform});
+
+    Value *NameOp = EmitScalarExpr(E->getArg(5));
+    return Builder.CreateIntrinsic(HandleTy, IID,
+                                   ArrayRef<Value *>{OrderID, SpaceOp, RangeOp,
+                                                     IndexOp, NonUniform,
+                                                     NameOp});
   }
   case Builtin::BI__builtin_hlsl_all: {
     Value *Op0 = EmitScalarExpr(E->getArg(0));
diff --git a/clang/lib/CodeGen/CGHLSLRuntime.cpp b/clang/lib/CodeGen/CGHLSLRuntime.cpp
index a708b3aea129d..b9577a0dc48a1 100644
--- a/clang/lib/CodeGen/CGHLSLRuntime.cpp
+++ b/clang/lib/CodeGen/CGHLSLRuntime.cpp
@@ -42,10 +42,6 @@ using namespace llvm;
 
 using llvm::hlsl::CBufferRowSizeInBytes;
 
-static void initializeBufferFromBinding(CodeGenModule &CGM,
-                                        llvm::GlobalVariable *GV,
-                                        HLSLResourceBindingAttr *RBA);
-
 namespace {
 
 void addDxilValVersion(StringRef ValVersionStr, llvm::Module &M) {
@@ -275,7 +271,7 @@ void CGHLSLRuntime::addBuffer(const HLSLBufferDecl *BufDecl) {
   HLSLResourceBindingAttr *RBA = BufDecl->getAttr<HLSLResourceBindingAttr>();
   assert(RBA &&
          "cbuffer/tbuffer should always have resource binding attribute");
-  initializeBufferFromBinding(CGM, BufGV, RBA);
+  initializeBufferFromBinding(BufDecl, BufGV, RBA);
 }
 
 llvm::TargetExtType *
@@ -557,29 +553,47 @@ static void initializeBuffer(CodeGenModule &CGM, llvm::GlobalVariable *GV,
   CGM.AddCXXGlobalInit(InitResFunc);
 }
 
-static void initializeBufferFromBinding(CodeGenModule &CGM,
-                                        llvm::GlobalVariable *GV,
-                                        HLSLResourceBindingAttr *RBA) {
+void CGHLSLRuntime::initializeBufferFromBinding(const HLSLBufferDecl *BufDecl,
+                                                llvm::GlobalVariable *GV,
+                                                HLSLResourceBindingAttr *RBA) {
   llvm::Type *Int1Ty = llvm::Type::getInt1Ty(CGM.getLLVMContext());
   auto *NonUniform = llvm::ConstantInt::get(Int1Ty, false);
   auto *Index = llvm::ConstantInt::get(CGM.IntTy, 0);
   auto *RangeSize = llvm::ConstantInt::get(CGM.IntTy, 1);
   auto *Space =
       llvm::ConstantInt::get(CGM.IntTy, RBA ? RBA->getSpaceNumber() : 0);
+  Value *Name = nullptr;
+
+  // DXIL intrinsic includes resource name
+  if (getArch() == Triple::dxil) {
+    std::string Str = std::string(BufDecl->getName());
+    std::string GlobalName = Str + ".str";
+    Name = CGM.GetAddrOfConstantCString(Str, GlobalName.c_str()).getPointer();
+  }
 
+  // buffer with explicit binding
   if (RBA->hasRegisterSlot()) {
     auto *RegSlot = llvm::ConstantInt::get(CGM.IntTy, RBA->getSlotNumber());
     Intrinsic::ID Intr =
         CGM.getHLSLRuntime().getCreateHandleFromBindingIntrinsic();
-    initializeBuffer(CGM, GV, Intr,
-                     {Space, RegSlot, RangeSize, Index, NonUniform});
+    if (Name)
+      initializeBuffer(CGM, GV, Intr,
+                       {Space, RegSlot, RangeSize, Index, NonUniform, Name});
+    else
+      initializeBuffer(CGM, GV, Intr,
+                       {Space, RegSlot, RangeSize, Index, NonUniform});
   } else {
+    // buffer with implicit binding
     auto *OrderID =
         llvm::ConstantInt::get(CGM.IntTy, RBA->getImplicitBindingOrderID());
     Intrinsic::ID Intr =
         CGM.getHLSLRuntime().getCreateHandleFromImplicitBindingIntrinsic();
-    initializeBuffer(CGM, GV, Intr,
-                     {OrderID, Space, RangeSize, Index, NonUniform});
+    if (Name)
+      initializeBuffer(CGM, GV, Intr,
+                       {OrderID, Space, RangeSize, Index, NonUniform, Name});
+    else
+      initializeBuffer(CGM, GV, Intr,
+                       {OrderID, Space, RangeSize, Index, NonUniform});
   }
 }
 
diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h
index e40864d8ed854..f86dca8c4fd26 100644
--- a/clang/lib/CodeGen/CGHLSLRuntime.h
+++ b/clang/lib/CodeGen/CGHLSLRuntime.h
@@ -164,6 +164,9 @@ class CGHLSLRuntime {
 private:
   void emitBufferGlobalsAndMetadata(const HLSLBufferDecl *BufDecl,
                                     llvm::GlobalVariable *BufGV);
+  void initializeBufferFromBinding(const HLSLBufferDecl *BufDecl,
+                                   llvm::GlobalVariable *GV,
+                                   HLSLResourceBindingAttr *RBA);
   llvm::Triple::ArchType getArch();
 
   llvm::DenseMap<const clang::RecordType *, llvm::TargetExtType *> LayoutTypes;
diff --git a/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl b/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl
index 2601a2ee4ff35..c29166e3fd749 100644
--- a/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/ByteAddressBuffers-constructors.hlsl
@@ -70,7 +70,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl17ByteAddressBufferC2EjjijPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %registerNo, i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, ptr noundef %name)
 // CHECK-DXIL: %[[HANDLE:.*]] = call target("dx.RawBuffer", i8, 0, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_i8_0_0t(
-// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::ByteAddressBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-DXIL-NEXT: store target("dx.RawBuffer", i8, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
@@ -79,7 +79,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl19RWByteAddressBufferC2EjijjPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, i32 noundef %orderId, ptr noundef %name)
 // CHECK: %[[HANDLE:.*]] = call target("dx.RawBuffer", i8, 1, 0) @llvm.dx.resource.handlefromimplicitbinding.tdx.RawBuffer_i8_1_0t
-// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWByteAddressBuffer", ptr %this1, i32 0, i32 0
 // CHECK-NEXT: store target("dx.RawBuffer", i8, 1, 0) %[[HANDLE]], ptr %__handle, align 4
 
diff --git a/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl b/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl
index c2796fa177705..16e994457259a 100644
--- a/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/RWBuffer-constructor.hlsl
@@ -67,7 +67,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl8RWBufferIfEC2EjjijPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %registerNo, i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, ptr noundef %name)
 // CHECK-DXIL: %[[HANDLE:.*]] = call target("dx.TypedBuffer", float, 1, 0, 0) @llvm.dx.resource.handlefrombinding.tdx.TypedBuffer_f32_1_0_0t(
-// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-DXIL-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-DXIL-NEXT: store target("dx.TypedBuffer", float, 1, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
@@ -76,7 +76,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl8RWBufferIdEC2EjijjPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, i32 noundef %orderId, ptr noundef %name)
 // CHECK: %[[HANDLE:.*]] = call target("dx.TypedBuffer", double, 1, 0, 0) @llvm.dx.resource.handlefromimplicitbinding.tdx.TypedBuffer_f64_1_0_0t
-// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CEHCK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWBuffer.0", ptr %{{.*}}, i32 0, i32 0
 // CHECK-NEXT: store target("dx.TypedBuffer", double, 1, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
diff --git a/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl b/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl
index a85a0b0880b6b..9dd5a9b80da88 100644
--- a/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl
+++ b/clang/test/CodeGenHLSL/builtins/StructuredBuffers-constructors.hlsl
@@ -71,7 +71,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl16StructuredBufferIfEC2EjjijPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %registerNo, i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, ptr noundef %name)
 // CHECK-DXIL: %[[HANDLE:.*]] = call target("dx.RawBuffer", float, 0, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_0_0t(
-// CHECK-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-SAME: i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::StructuredBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-DXIL-NEXT: store target("dx.RawBuffer", float, 0, 0) %[[HANDLE]], ptr %__handle, align 4
 
@@ -80,7 +80,7 @@ export void foo() {
 // CHECK: define linkonce_odr void @_ZN4hlsl18RWStructuredBufferIfEC2EjijjPKc(ptr noundef nonnull align 4 dereferenceable(4) %this,
 // CHECK-SAME: i32 noundef %spaceNo, i32 noundef %range, i32 noundef %index, i32 noundef %orderId, ptr noundef %name)
 // CHECK: %[[HANDLE:.*]] = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefromimplicitbinding.tdx.RawBuffer_f32_1_0t
-// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false)
+// CHECK-SAME: (i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i32 %{{.*}}, i1 false, ptr %{{.*}})
 // CHECK-NEXT: %__handle = getelementptr inbounds nuw %"class.hlsl::RWStructuredBuffer", ptr %{{.*}}, i32 0, i32 0
 // CHECK-NEXT: store target("dx.RawBuffer", float, 1, 0) %[[HANDLE]], ptr %__handle, align 4
 
diff --git a/clang/test/CodeGenHLSL/cbuffer.hlsl b/clang/test/CodeGenHLSL/cbuffer.hlsl
index 3fb76d57341cf..e0919266dc3b7 100644
--- a/clang/test/CodeGenHLSL/cbuffer.hlsl
+++ b/clang/test/CodeGenHLSL/cbuffer.hlsl
@@ -54,6 +54,7 @@ cbuffer CBScalars : register(b1, space5) {
 // CHECK: @a6 = external addrspace(2) global i16, align 2
 // CHECK: @a7 = external addrspace(2) global i32, align 4
 // CHECK: @a8 = external addrspace(2) global i64, align 8
+// CHECK: @CBScalars.str = private unnamed_addr constant [10 x i8] c"CBScalars\00", align 1
 
 cbuffer CBVectors {
   float3 b1;
@@ -75,6 +76,7 @@ cbuffer CBVectors {
 // CHECK: @b5 = external addrspace(2) global <4 x i32>, align 16
 // CHECK: @b6 = external addrspace(2) global <3 x i16>, align 8
 // CHECK: @b7 = external addrspace(2) global <3 x i64>, align 32
+// CHECK: @CBVectors.str = private unnamed_addr constant [10 x i8] c"CBVectors\00", align 1
 
 cbuffer CBArrays : register(b2) {
   float c1[3];
@@ -97,6 +99,7 @@ cbuffer CBArrays : register(b2) {
 // CHECK: @c6 = external addrspace(2) global [1 x i16], align 2
 // CHECK: @c7 = external addrspace(2) global [2 x i64], align 8
 // CHECK: @c8 = external addrspace(2) global [4 x i32], align 4
+// CHECK: @CBArrays.str = private unnamed_addr constant [9 x i8] c"CBArrays\00", align 1
 
 typedef uint32_t4 uint32_t8[2];
 typedef uint4 T1;
@@ -111,6 +114,7 @@ cbuffer CBTypedefArray : register(space2) {
 // CHECK-SAME: 128, 0, 64))
 // CHECK: @t1 = external addrspace(2) global [2 x [2 x <4 x i32>]], align 16
 // CHECK: @t2 = external addrspace(2) global [2 x [2 x <4 x i32>]], align 16
+// CHECK: @CBTypedefArray.str = private unnamed_addr constant [15 x i8] c"CBTypedefArray\00", align 1
 struct Empty {};
 
 struct A {
@@ -140,6 +144,7 @@ struct D {
 // CHECK: @d = external addrspace(2) global target("dx.Layout", %__cblayout_D, 94, 0), align 1
 // CHECK: @e = external addrspace(2) global half, align 2
 // CHECK: @f = external addrspace(2) global <3 x i16>, align 8
+// CHECK: @CBStructs.str = private unnamed_addr constant [10 x i8] c"CBStructs\00", align 1
 
 cbuffer CBStructs {
   A a;
@@ -177,6 +182,7 @@ cbuffer CBClasses {
 // CHECK: @l = external addrspace(2) global target("dx.Layout", %L, 8, 0, 4), align 1
 // CHECK: @m = external addrspace(2) global target("dx.Layout", %M, 68, 0), align 1
 // CHECK: @ka = external addrspace(2) global [10 x target("dx.Layout", %K, 4, 0)], align 1
+// CHECK: @CBClasses.str = private unnamed_addr constant [10 x i8] c"CBClasses\00", align 1
 
 struct Test {
     float a, b;
@@ -194,6 +200,7 @@ struct Test {
 // CHECK: @f7 = external addrspace(2) global float, align 4
 // CHECK: @f8 = external addrspace(2) global <1 x double>, align 8
 // CHECK: @f9 = external addrspace(2) global i16, align 2
+// CHECK: @CBMix.str = private unnamed_addr constant [6 x i8] c"CBMix\00", align 1
 
 cbuffer CBMix {
     Test test[2];
@@ -269,61 +276,61 @@ cbuffer CB_C {
 // CHECK: define internal void @_init_buffer_CBScalars.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBScalars.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBScalars, 56, 0, 8, 16, 24, 32, 36, 40, 48))
-// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBScalarss_56_0_8_16_24_32_36_40_48tt(i32 5, i32 1, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBScalarss_56_0_8_16_24_32_36_40_48tt(i32 5, i32 1, i32 1, i32 0, i1 false, ptr @CBScalars.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBScalars, 56, 0, 8, 16, 24, 32, 36, 40, 48)) %CBScalars.cb_h, ptr @CBScalars.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBVectors.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBVectors.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBVectors, 136, 0, 16, 40, 48, 80, 96, 112))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBVectorss_136_0_16_40_48_80_96_112tt(i32 0, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBVectorss_136_0_16_40_48_80_96_112tt(i32 0, i32 0, i32 1, i32 0, i1 false, ptr @CBVectors.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBVectors, 136, 0, 16, 40, 48, 80, 96, 112)) %CBVectors.cb_h, ptr @CBVectors.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBArrays.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBArrays.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBArrays, 708, 0, 48, 112, 176, 224, 608, 624, 656))
-// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBArrayss_708_0_48_112_176_224_608_624_656tt(i32 0, i32 2, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefrombinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBArrayss_708_0_48_112_176_224_608_624_656tt(i32 0, i32 2, i32 1, i32 0, i1 false, ptr @CBArrays.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBArrays, 708, 0, 48, 112, 176, 224, 608, 624, 656)) %CBArrays.cb_h, ptr @CBArrays.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBTypedefArray.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBTypedefArray.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBTypedefArray, 128, 0, 64))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBTypedefArrays_128_0_64tt(i32 1, i32 2, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBTypedefArrays_128_0_64tt(i32 1, i32 2, i32 1, i32 0, i1 false, ptr @CBTypedefArray.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBTypedefArray, 128, 0, 64)) %CBTypedefArray.cb_h, ptr @CBTypedefArray.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBStructs.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT:   %CBStructs.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBStructs, 246, 0, 16, 32, 64, 144, 238, 240))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBStructss_246_0_16_32_64_144_238_240tt(i32 2, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBStructss_246_0_16_32_64_144_238_240tt(i32 2, i32 0, i32 1, i32 0, i1 false, ptr @CBStructs.str)
 // CHECK-NEXT:   store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBStructs, 246, 0, 16, 32, 64, 144, 238, 240)) %CBStructs.cb_h, ptr @CBStructs.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBClasses.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBClasses.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBClasses, 260, 0, 16, 32, 112))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBClassess_260_0_16_32_112tt(i32 3, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBClassess_260_0_16_32_112tt(i32 3, i32 0, i32 1, i32 0, i1 false, ptr @CBClasses.str)
 // CHECK-NEXT: store target("dx.CBuffer", target("dx.Layout", %__cblayout_CBClasses, 260, 0, 16, 32, 112)) %CBClasses.cb_h, ptr @CBClasses.cb, align 4
 
 // CHECK: define internal void @_init_buffer_CBMix.cb()
 // CHECK-NEXT: entry:
 // CHECK-NEXT: %CBMix.cb_h = call target("dx.CBuffer", target("dx.Layout", %__cblayout_CBMix, 170, 0, 24, 32, 120, 128, 136, 144, 152, 160, 168))
-// CHECK-SAME: @llvm.dx.resource.handlefromimplicitbinding.tdx.CBuffer_tdx.Layout_s___cblayout_CBMixs_170_0_24_32_120_128_136_144_152_160_168tt(i32 4, i32 0, i32 1, i32 0, i1 false)
+// CHECK-SAME: @llvm.dx.resource.handlefro...
[truncated]

@hekota hekota changed the title [DirectX] Add resource name argument to llvm.dx.handlefrom[implicit]binding intrinsics (DirectX only) [DirectX] Add resource name argument to llvm.dx.handlefrom[implicit]binding intrinsics May 22, 2025
@hekota hekota changed the base branch from users/hekota/pr139985-resource-names-clang to main May 27, 2025 18:17
@hekota hekota requested a review from V-FEXrt May 27, 2025 20:09
Copy link
Contributor

@inbelic inbelic left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM (+1 for Justin's nfc changes), the lack of any changes to SPIRV tests indicates that we have the expected behaviour on that lowering path as well

Copy link
Contributor

@V-FEXrt V-FEXrt left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Mostly philosophical question, not asking for any changes:

Is there a way to annotate the intrinsic here than tacking it on as a parameter for only one target machine? Like is possible to use IR attributes or some other kind of metadata/side channel for this info? Not sure that's actually any better but the name actually isn't used for lowering, just for diagnostics so it feels like "side info"

@hekota
Copy link
Member Author

hekota commented May 28, 2025

Mostly philosophical question, not asking for any changes:

Is there a way to annotate the intrinsic here than tacking it on as a parameter for only one target machine? Like is possible to use IR attributes or some other kind of metadata/side channel for this info? Not sure that's actually any better but the name actually isn't used for lowering, just for diagnostics so it feels like "side info"

I've considered storing it as metadata attached to the llvm.dx.resource.createhandlefrombinding call. The issue is that Clang creates the call when it is generating the body of the constructor, which is generated once per resource type and not per resource instance. It would need a metadata node that takes its value dynamically from the constructor's resource name argument.

@hekota hekota merged commit 27675cc into llvm:main May 28, 2025
12 checks passed
@llvm-ci
Copy link
Collaborator

llvm-ci commented May 28, 2025

LLVM Buildbot has detected a new failure on builder llvm-clang-aarch64-darwin running on doug-worker-4 while building clang,llvm at step 6 "test-build-unified-tree-check-all".

Full details are available at: https://lab.llvm.org/buildbot/#/builders/190/builds/20711

Here is the relevant piece of the build log for the reference
Step 6 (test-build-unified-tree-check-all) failure: test (failure)
******************** TEST 'LLVM :: ExecutionEngine/OrcLazy/multiple-compile-threads-basic.ll' FAILED ********************
Exit Code: 2

Command Output (stderr):
--
/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli -jit-kind=orc-lazy -compile-threads=2 -thread-entry hello /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/ExecutionEngine/OrcLazy/multiple-compile-threads-basic.ll | /Users/buildbot/buildbot-root/aarch64-darwin/build/bin/FileCheck /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/ExecutionEngine/OrcLazy/multiple-compile-threads-basic.ll # RUN: at line 1
+ /Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli -jit-kind=orc-lazy -compile-threads=2 -thread-entry hello /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/ExecutionEngine/OrcLazy/multiple-compile-threads-basic.ll
+ /Users/buildbot/buildbot-root/aarch64-darwin/build/bin/FileCheck /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/ExecutionEngine/OrcLazy/multiple-compile-threads-basic.ll
PLEASE submit a bug report to https://github.com/llvm/llvm-project/issues/ and include the crash backtrace.
 #0 0x0000000103729078 llvm::sys::PrintStackTrace(llvm::raw_ostream&, int) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli+0x100eed078)
 #1 0x00000001037270fc llvm::sys::RunSignalHandlers() (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli+0x100eeb0fc)
 #2 0x0000000103729770 SignalHandler(int, __siginfo*, void*) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli+0x100eed770)
 #3 0x00000001949bf584 (/usr/lib/system/libsystem_platform.dylib+0x18047b584)
 #4 0x000000019498e21c (/usr/lib/system/libsystem_pthread.dylib+0x18044a21c)
 #5 0x00000001948b4ad0 (/usr/lib/libc++.1.dylib+0x180370ad0)
 #6 0x00000001032c3b14 void llvm::detail::UniqueFunctionBase<void, llvm::Expected<llvm::DenseMap<llvm::orc::SymbolStringPtr, llvm::orc::ExecutorSymbolDef, llvm::DenseMapInfo<llvm::orc::SymbolStringPtr, void>, llvm::detail::DenseMapPair<llvm::orc::SymbolStringPtr, llvm::orc::ExecutorSymbolDef>>>>::CallImpl<llvm::orc::Platform::lookupInitSymbols(llvm::orc::ExecutionSession&, llvm::DenseMap<llvm::orc::JITDylib*, llvm::orc::SymbolLookupSet, llvm::DenseMapInfo<llvm::orc::JITDylib*, void>, llvm::detail::DenseMapPair<llvm::orc::JITDylib*, llvm::orc::SymbolLookupSet>> const&)::$_45>(void*, llvm::Expected<llvm::DenseMap<llvm::orc::SymbolStringPtr, llvm::orc::ExecutorSymbolDef, llvm::DenseMapInfo<llvm::orc::SymbolStringPtr, void>, llvm::detail::DenseMapPair<llvm::orc::SymbolStringPtr, llvm::orc::ExecutorSymbolDef>>>&) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli+0x100a87b14)
 #7 0x00000001032bf748 llvm::orc::AsynchronousSymbolQuery::handleComplete(llvm::orc::ExecutionSession&)::RunQueryCompleteTask::run() (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli+0x100a83748)
 #8 0x000000010337c1a8 void* std::__1::__thread_proxy[abi:un170006]<std::__1::tuple<std::__1::unique_ptr<std::__1::__thread_struct, std::__1::default_delete<std::__1::__thread_struct>>, llvm::orc::DynamicThreadPoolTaskDispatcher::dispatch(std::__1::unique_ptr<llvm::orc::Task, std::__1::default_delete<llvm::orc::Task>>)::$_0>>(void*) (/Users/buildbot/buildbot-root/aarch64-darwin/build/bin/lli+0x100b401a8)
 #9 0x000000019498ef94 (/usr/lib/system/libsystem_pthread.dylib+0x18044af94)
#10 0x0000000194989d34 (/usr/lib/system/libsystem_pthread.dylib+0x180445d34)
FileCheck error: '<stdin>' is empty.
FileCheck command line:  /Users/buildbot/buildbot-root/aarch64-darwin/build/bin/FileCheck /Users/buildbot/buildbot-root/aarch64-darwin/llvm-project/llvm/test/ExecutionEngine/OrcLazy/multiple-compile-threads-basic.ll

--

********************


@llvm-ci
Copy link
Collaborator

llvm-ci commented May 28, 2025

LLVM Buildbot has detected a new failure on builder clang-aarch64-sve-vla running on linaro-g3-04 while building clang,llvm at step 7 "ninja check 1".

Full details are available at: https://lab.llvm.org/buildbot/#/builders/17/builds/8382

Here is the relevant piece of the build log for the reference
Step 7 (ninja check 1) failure: stage 1 checked (failure)
******************** TEST 'LLVM :: tools/llvm-exegesis/RISCV/rvv/filter.test' FAILED ********************
Exit Code: 2

Command Output (stderr):
--
/home/tcwg-buildbot/worker/clang-aarch64-sve-vla/stage1/bin/llvm-exegesis -mtriple=riscv64 -mcpu=sifive-x280 -benchmark-phase=assemble-measured-code --mode=inverse_throughput --opcode-name=PseudoVNCLIPU_WX_M1_MASK     --riscv-filter-config='vtype = {VXRM: rod, AVL: VLMAX, SEW: e(8|16), Policy: ta/mu}' --max-configs-per-opcode=1000 --min-instructions=10 | /home/tcwg-buildbot/worker/clang-aarch64-sve-vla/stage1/bin/FileCheck /home/tcwg-buildbot/worker/clang-aarch64-sve-vla/llvm/llvm/test/tools/llvm-exegesis/RISCV/rvv/filter.test # RUN: at line 1
+ /home/tcwg-buildbot/worker/clang-aarch64-sve-vla/stage1/bin/llvm-exegesis -mtriple=riscv64 -mcpu=sifive-x280 -benchmark-phase=assemble-measured-code --mode=inverse_throughput --opcode-name=PseudoVNCLIPU_WX_M1_MASK '--riscv-filter-config=vtype = {VXRM: rod, AVL: VLMAX, SEW: e(8|16), Policy: ta/mu}' --max-configs-per-opcode=1000 --min-instructions=10
+ /home/tcwg-buildbot/worker/clang-aarch64-sve-vla/stage1/bin/FileCheck /home/tcwg-buildbot/worker/clang-aarch64-sve-vla/llvm/llvm/test/tools/llvm-exegesis/RISCV/rvv/filter.test
PseudoVNCLIPU_WX_M1_MASK: Failed to produce any snippet via: instruction has tied variables, avoiding Read-After-Write issue, picking random def and use registers not aliasing each other, for uses, one unique register for each position
FileCheck error: '<stdin>' is empty.
FileCheck command line:  /home/tcwg-buildbot/worker/clang-aarch64-sve-vla/stage1/bin/FileCheck /home/tcwg-buildbot/worker/clang-aarch64-sve-vla/llvm/llvm/test/tools/llvm-exegesis/RISCV/rvv/filter.test

--

********************


sivan-shani pushed a commit to sivan-shani/llvm-project that referenced this pull request Jun 3, 2025
…inding intrinsics (llvm#139991)

Adds resource name argument to `llvm.dx.handlefrombinding` and `llvm.dx.handlefromimplicitbinding` intrinsics.
SPIR-V currently does not seem to need the resource names so this change only affects DirectX binding intrinsics.

Part 2/4 of llvm#105059
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
backend:DirectX clang:codegen IR generation bugs: mangling, exceptions, etc. clang Clang issues not falling into any other category HLSL HLSL Language Support llvm:analysis llvm:ir
Projects
None yet
Development

Successfully merging this pull request may close these issues.

[DirectX] Capture the "name of the resource variable" in DXIL resource analysis
6 participants