aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHelena Kotas <hekotas@microsoft.com>2025-07-24 16:26:26 -0700
committerJustin Bogner <mail@justinbogner.com>2025-07-25 08:28:01 -0700
commitc6d931a04a18aba49a37b59301957d06367b1119 (patch)
treee0e675a3090082f5eb642ed17918a82f8fd4232a
parent1bd7ccd4a5dc403aa822f0d45242e287889c4b3b (diff)
downloadllvm-users/bogner/pr150547.zip
llvm-users/bogner/pr150547.tar.gz
llvm-users/bogner/pr150547.tar.bz2
Cherry-pick #150547: [HLSL] Fix detection of overlapping binding with unbounded arrayusers/bogner/pr150547
Fixes #150534
-rw-r--r--llvm/include/llvm/Analysis/DXILResource.h2
-rw-r--r--llvm/lib/Analysis/DXILResource.cpp7
-rw-r--r--llvm/test/CodeGen/DirectX/Binding/binding-overlap-6.ll24
3 files changed, 30 insertions, 3 deletions
diff --git a/llvm/include/llvm/Analysis/DXILResource.h b/llvm/include/llvm/Analysis/DXILResource.h
index 9e2dc1a..956dcbc 100644
--- a/llvm/include/llvm/Analysis/DXILResource.h
+++ b/llvm/include/llvm/Analysis/DXILResource.h
@@ -359,6 +359,8 @@ public:
std::tie(RHS.RecordID, RHS.Space, RHS.LowerBound, RHS.Size);
}
bool overlapsWith(const ResourceBinding &RHS) const {
+ if (Size == UINT32_MAX)
+ return LowerBound < RHS.LowerBound;
return Space == RHS.Space && LowerBound + Size - 1 >= RHS.LowerBound;
}
};
diff --git a/llvm/lib/Analysis/DXILResource.cpp b/llvm/lib/Analysis/DXILResource.cpp
index 2da6468..179b7b4 100644
--- a/llvm/lib/Analysis/DXILResource.cpp
+++ b/llvm/lib/Analysis/DXILResource.cpp
@@ -1079,15 +1079,16 @@ void DXILResourceBindingInfo::populate(Module &M, DXILResourceTypeMap &DRTM) {
// add new space
S = &BS->Spaces.emplace_back(B.Space);
- // the space is full - set flag to report overlapping binding later
- if (S->FreeRanges.empty()) {
+ // The space is full - there are no free slots left, or the rest of the
+ // slots are taken by an unbouded array. Set flag to report overlapping
+ // binding later.
+ if (S->FreeRanges.empty() || S->FreeRanges.back().UpperBound < UINT32_MAX) {
OverlappingBinding = true;
continue;
}
// adjust the last free range lower bound, split it in two, or remove it
BindingRange &LastFreeRange = S->FreeRanges.back();
- assert(LastFreeRange.UpperBound == UINT32_MAX);
if (LastFreeRange.LowerBound == B.LowerBound) {
if (B.UpperBound < UINT32_MAX)
LastFreeRange.LowerBound = B.UpperBound + 1;
diff --git a/llvm/test/CodeGen/DirectX/Binding/binding-overlap-6.ll b/llvm/test/CodeGen/DirectX/Binding/binding-overlap-6.ll
new file mode 100644
index 0000000..3c37e63
--- /dev/null
+++ b/llvm/test/CodeGen/DirectX/Binding/binding-overlap-6.ll
@@ -0,0 +1,24 @@
+; RUN: not opt -S -passes='dxil-post-optimization-validation' -mtriple=dxil-pc-shadermodel6.3-library %s 2>&1 | FileCheck %s
+
+; Check overlap with unbounded array
+
+; A overlaps with B
+; RWBuffer<float> A[3] : register(u0);
+; RWBuffer<float> B[] : register(u4);
+; RWBuffer<float> C : register(u17);
+
+; CHECK: error: resource B at register 4 overlaps with resource C at register 17 in space 0
+
+target triple = "dxil-pc-shadermodel6.3-library"
+
+@A.str = private unnamed_addr constant [2 x i8] c"A\00", align 1
+@B.str = private unnamed_addr constant [2 x i8] c"B\00", align 1
+@C.str = private unnamed_addr constant [2 x i8] c"C\00", align 1
+
+define void @test_overlapping() {
+entry:
+ %h1 = call target("dx.TypedBuffer", float, 1, 0, 0) @llvm.dx.resource.handlefrombinding(i32 0, i32 0, i32 3, i32 0, i1 false, ptr @A.str)
+ %h2 = call target("dx.TypedBuffer", float, 1, 0, 0) @llvm.dx.resource.handlefrombinding(i32 0, i32 4, i32 -1, i32 0, i1 false, ptr @B.str)
+ %h3 = call target("dx.TypedBuffer", float, 1, 0, 0) @llvm.dx.resource.handlefrombinding(i32 0, i32 17, i32 1, i32 0, i1 false, ptr @C.str)
+ ret void
+}