Skip to content

Commit 9062182

Browse files
committed
Add Diag and tests
1 parent 28e7369 commit 9062182

File tree

5 files changed

+147
-8
lines changed

5 files changed

+147
-8
lines changed

llvm/lib/Analysis/DXILResource.cpp

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
#include "llvm/Analysis/DXILResource.h"
1010
#include "llvm/ADT/APInt.h"
1111
#include "llvm/ADT/SmallString.h"
12+
#include "llvm/ADT/StringRef.h"
1213
#include "llvm/IR/Constants.h"
1314
#include "llvm/IR/DerivedTypes.h"
1415
#include "llvm/IR/DiagnosticInfo.h"
@@ -20,6 +21,7 @@
2021
#include "llvm/InitializePasses.h"
2122
#include "llvm/Support/FormatVariadic.h"
2223
#include <algorithm>
24+
#include "llvm/IR/DiagnosticInfo.h"
2325

2426
#define DEBUG_TYPE "dxil-resource"
2527

@@ -858,8 +860,8 @@ void DXILResourceCounterDirectionMap::populate(Module &M,
858860
}
859861
}
860862

861-
// An entry that is not in the map is considered unknown so its wasted
862-
// overhead and increased complexity to keep it so it should be removed.
863+
// An entry that is not in the map is considered unknown so its wasted overhead
864+
// and increased complexity to keep an entry explicitly marked unknown
863865
const auto RemoveEnd = std::remove_if(
864866
CounterDirections.begin(), CounterDirections.end(), [](const auto &Item) {
865867
return Item.second == ResourceCounterDirection::Unknown;
@@ -883,8 +885,8 @@ void DXILResourceCounterDirectionMap::populate(Module &M,
883885
if (DuplicateEntry == CounterDirections.end())
884886
return;
885887

886-
// TODO: Emit an error message
887-
assert(CounterDirections.size() == 1 && "dups found");
888+
StringRef Message = "RWStructuredBuffers may increment or decrement their counters, but not both.";
889+
M.getContext().diagnose(DiagnosticInfoGeneric(Message));
888890
}
889891

890892
bool DXILResourceCounterDirectionMap::invalidate(

llvm/lib/Passes/PassRegistry.def

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ MODULE_ANALYSIS("ctx-prof-analysis", CtxProfAnalysis())
2424
MODULE_ANALYSIS("dxil-metadata", DXILMetadataAnalysis())
2525
MODULE_ANALYSIS("dxil-resource-binding", DXILResourceBindingAnalysis())
2626
MODULE_ANALYSIS("dxil-resource-type", DXILResourceTypeAnalysis())
27+
MODULE_ANALYSIS("dxil-resource-counter-direction", DXILResourceCounterDirectionAnalysis())
2728
MODULE_ANALYSIS("inline-advisor", InlineAdvisorAnalysis())
2829
MODULE_ANALYSIS("ir-similarity", IRSimilarityAnalysis())
2930
MODULE_ANALYSIS("last-run-tracking", LastRunTrackingAnalysis())

llvm/lib/Target/DirectX/DXILOpLowering.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -816,6 +816,7 @@ class OpLowerer {
816816
PreservedAnalyses DXILOpLowering::run(Module &M, ModuleAnalysisManager &MAM) {
817817
DXILBindingMap &DBM = MAM.getResult<DXILResourceBindingAnalysis>(M);
818818
DXILResourceTypeMap &DRTM = MAM.getResult<DXILResourceTypeAnalysis>(M);
819+
DXILResourceCounterDirectionMap &DRCDM = MAM.getResult<DXILResourceCounterDirectionAnalysis>(M);
819820

820821
bool MadeChanges = OpLowerer(M, DBM, DRTM).lowerIntrinsics();
821822
if (!MadeChanges)
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
; RUN: not opt -S -passes='dxil-op-lower' -mtriple=dxil-pc-shadermodel6.3-library %s 2>&1 | FileCheck %s
2+
; CHECK: RWStructuredBuffers may increment or decrement their counters, but not both.
3+
4+
define void @inc_and_dec() {
5+
entry:
6+
%handle = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32 1, i32 2, i32 3, i32 4, i1 false)
7+
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 -1)
8+
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 1)
9+
ret void
10+
}
11+
12+
declare target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32, i32, i32, i32, i1)
13+
declare i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0), i8)

llvm/unittests/Target/DirectX/UniqueResourceFromUseTests.cpp

Lines changed: 126 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -281,17 +281,14 @@ declare target("dx.RawBuffer", float, 1, 0) @ind.func(target("dx.RawBuffer", flo
281281
}
282282
}
283283

284-
TEST_F(UniqueResourceFromUseTest, TestResourceCounter) {
284+
TEST_F(UniqueResourceFromUseTest, TestResourceCounterDecrement) {
285285
StringRef Assembly = R"(
286286
define void @main() {
287287
entry:
288288
%handle = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32 1, i32 2, i32 3, i32 4, i1 false)
289289
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 -1)
290290
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 -1)
291291
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 -1)
292-
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 -1)
293-
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 -1)
294-
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 -1)
295292
call void @a.func(target("dx.RawBuffer", float, 1, 0) %handle)
296293
ret void
297294
}
@@ -325,4 +322,129 @@ declare void @a.func(target("dx.RawBuffer", float, 1, 0) %handle)
325322
}
326323
}
327324

325+
TEST_F(UniqueResourceFromUseTest, TestResourceCounterIncrement) {
326+
StringRef Assembly = R"(
327+
define void @main() {
328+
entry:
329+
%handle = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32 1, i32 2, i32 3, i32 4, i1 false)
330+
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 1)
331+
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 1)
332+
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle, i8 1)
333+
call void @a.func(target("dx.RawBuffer", float, 1, 0) %handle)
334+
ret void
335+
}
336+
337+
declare target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32, i32, i32, i32, i1)
338+
declare i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0), i8)
339+
declare void @a.func(target("dx.RawBuffer", float, 1, 0) %handle)
340+
)";
341+
342+
LLVMContext Context;
343+
SMDiagnostic Error;
344+
auto M = parseAssemblyString(Assembly, Error, Context);
345+
ASSERT_TRUE(M) << "Bad assembly?";
346+
347+
const DXILBindingMap &DBM = MAM->getResult<DXILResourceBindingAnalysis>(*M);
348+
const DXILResourceCounterDirectionMap &DCDM =
349+
MAM->getResult<DXILResourceCounterDirectionAnalysis>(*M);
350+
351+
for (const Function &F : M->functions()) {
352+
if (F.getName() != "a.func") {
353+
continue;
354+
}
355+
356+
for (const User *U : F.users()) {
357+
const CallInst *CI = cast<CallInst>(U);
358+
const Value *Handle = CI->getArgOperand(0);
359+
const auto Bindings = DBM.findByUse(Handle);
360+
ASSERT_EQ(Bindings.size(), 1u);
361+
ASSERT_EQ(DCDM[Bindings.front()], ResourceCounterDirection::Increment);
362+
}
363+
}
364+
}
365+
366+
TEST_F(UniqueResourceFromUseTest, TestResourceCounterUnknown) {
367+
StringRef Assembly = R"(
368+
define void @main() {
369+
entry:
370+
%handle = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32 1, i32 2, i32 3, i32 4, i1 false)
371+
call void @a.func(target("dx.RawBuffer", float, 1, 0) %handle)
372+
ret void
373+
}
374+
375+
declare target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32, i32, i32, i32, i1)
376+
declare i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0), i8)
377+
declare void @a.func(target("dx.RawBuffer", float, 1, 0) %handle)
378+
)";
379+
380+
LLVMContext Context;
381+
SMDiagnostic Error;
382+
auto M = parseAssemblyString(Assembly, Error, Context);
383+
ASSERT_TRUE(M) << "Bad assembly?";
384+
385+
const DXILBindingMap &DBM = MAM->getResult<DXILResourceBindingAnalysis>(*M);
386+
const DXILResourceCounterDirectionMap &DCDM =
387+
MAM->getResult<DXILResourceCounterDirectionAnalysis>(*M);
388+
389+
for (const Function &F : M->functions()) {
390+
if (F.getName() != "a.func") {
391+
continue;
392+
}
393+
394+
for (const User *U : F.users()) {
395+
const CallInst *CI = cast<CallInst>(U);
396+
const Value *Handle = CI->getArgOperand(0);
397+
const auto Bindings = DBM.findByUse(Handle);
398+
ASSERT_EQ(Bindings.size(), 1u);
399+
ASSERT_EQ(DCDM[Bindings.front()], ResourceCounterDirection::Unknown);
400+
}
401+
}
402+
}
403+
404+
TEST_F(UniqueResourceFromUseTest, TestResourceCounterMultiple) {
405+
StringRef Assembly = R"(
406+
define void @main() {
407+
entry:
408+
%handle1 = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32 1, i32 2, i32 3, i32 4, i1 false)
409+
%handle2 = call target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32 4, i32 3, i32 2, i32 1, i1 false)
410+
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle1, i8 -1)
411+
call i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0) %handle2, i8 1)
412+
call void @a.func(target("dx.RawBuffer", float, 1, 0) %handle1)
413+
call void @b.func(target("dx.RawBuffer", float, 1, 0) %handle2)
414+
ret void
415+
}
416+
417+
declare target("dx.RawBuffer", float, 1, 0) @llvm.dx.resource.handlefrombinding.tdx.RawBuffer_f32_1_0t(i32, i32, i32, i32, i1)
418+
declare i32 @llvm.dx.resource.updatecounter.tdx.RawBuffer_f32_1_0t(target("dx.RawBuffer", float, 1, 0), i8)
419+
declare void @a.func(target("dx.RawBuffer", float, 1, 0) %handle)
420+
declare void @b.func(target("dx.RawBuffer", float, 1, 0) %handle)
421+
)";
422+
423+
LLVMContext Context;
424+
SMDiagnostic Error;
425+
auto M = parseAssemblyString(Assembly, Error, Context);
426+
ASSERT_TRUE(M) << "Bad assembly?";
427+
428+
const DXILBindingMap &DBM = MAM->getResult<DXILResourceBindingAnalysis>(*M);
429+
const DXILResourceCounterDirectionMap &DCDM =
430+
MAM->getResult<DXILResourceCounterDirectionAnalysis>(*M);
431+
432+
for (const Function &F : M->functions()) {
433+
StringRef FName = F.getName();
434+
if (FName != "a.func" && FName != "b.func") {
435+
continue;
436+
}
437+
438+
auto Dir = FName == "a.func" ? ResourceCounterDirection::Decrement : ResourceCounterDirection::Increment;
439+
440+
for (const User *U : F.users()) {
441+
const CallInst *CI = cast<CallInst>(U);
442+
const Value *Handle = CI->getArgOperand(0);
443+
const auto Bindings = DBM.findByUse(Handle);
444+
ASSERT_EQ(Bindings.size(), 1u);
445+
ASSERT_EQ(DCDM[Bindings.front()], Dir);
446+
}
447+
}
448+
}
449+
328450
} // namespace

0 commit comments

Comments
 (0)