diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h b/clang/lib/CodeGen/CGHLSLRuntime.h --- a/clang/lib/CodeGen/CGHLSLRuntime.h +++ b/clang/lib/CodeGen/CGHLSLRuntime.h @@ -22,6 +22,7 @@ #include "llvm/ADT/Optional.h" #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/StringRef.h" +#include "llvm/Frontend/HLSL/HLSLResource.h" #include @@ -35,6 +36,7 @@ class VarDecl; class ParmVarDecl; class HLSLBufferDecl; +class HLSLResourceBindingAttr; class CallExpr; class Type; class DeclContext; @@ -47,13 +49,20 @@ class CGHLSLRuntime { public: + struct BufferResBinding { + // The ID like 2 in register(b2, space1). + llvm::Optional Reg; + // The Space like 1 is register(b2, space1). + // Default value is 0. + unsigned Space; + BufferResBinding(HLSLResourceBindingAttr *Attr); + }; struct Buffer { Buffer(const HLSLBufferDecl *D); llvm::StringRef Name; // IsCBuffer - Whether the buffer is a cbuffer (and not a tbuffer). bool IsCBuffer; - llvm::Optional Reg; - unsigned Space; + BufferResBinding Binding; // Global variable and offset for each constant. std::vector> Constants; llvm::StructType *LayoutStruct = nullptr; @@ -82,6 +91,11 @@ void setHLSLFunctionAttributes(llvm::Function *, const FunctionDecl *); private: + void addBufferResourceAnnotation(llvm::GlobalVariable *GV, + llvm::StringRef TyName, + hlsl::ResourceClass RC, + llvm::hlsl::ResourceKind RK, + BufferResBinding &Binding); void addConstant(VarDecl *D, Buffer &CB); void addBufferDecls(const DeclContext *DC, Buffer &CB); llvm::SmallVector Buffers; diff --git a/clang/lib/CodeGen/CGHLSLRuntime.cpp b/clang/lib/CodeGen/CGHLSLRuntime.cpp --- a/clang/lib/CodeGen/CGHLSLRuntime.cpp +++ b/clang/lib/CodeGen/CGHLSLRuntime.cpp @@ -17,7 +17,6 @@ #include "CodeGenModule.h" #include "clang/AST/Decl.h" #include "clang/Basic/TargetOptions.h" -#include "llvm/Frontend/HLSL/HLSLResource.h" #include "llvm/IR/IntrinsicsDirectX.h" #include "llvm/IR/Metadata.h" #include "llvm/IR/Module.h" @@ -90,16 +89,16 @@ GlobalVariable *replaceBuffer(CGHLSLRuntime::Buffer &Buf) { // Create global variable for CB. - GlobalVariable *CBGV = - new GlobalVariable(Buf.LayoutStruct, /*isConstant*/ true, - GlobalValue::LinkageTypes::ExternalLinkage, nullptr, - Buf.Name + (Buf.IsCBuffer ? ".cb." : ".tb."), - GlobalValue::NotThreadLocal); + GlobalVariable *CBGV = new GlobalVariable( + Buf.LayoutStruct, /*isConstant*/ true, + GlobalValue::LinkageTypes::ExternalLinkage, nullptr, + llvm::formatv("{0}{1}", Buf.Name, Buf.IsCBuffer ? ".cb." : ".tb."), + GlobalValue::NotThreadLocal); IRBuilder<> B(CBGV->getContext()); Value *ZeroIdx = B.getInt32(0); // Replace Const use with CB use. - for (auto &[GV, Offset]: Buf.Constants) { + for (auto &[GV, Offset] : Buf.Constants) { Value *GEP = B.CreateGEP(Buf.LayoutStruct, CBGV, {ZeroIdx, B.getInt32(Offset)}); @@ -177,25 +176,100 @@ layoutBuffer(Buf, DL); GlobalVariable *GV = replaceBuffer(Buf); M.getGlobalList().push_back(GV); - // FIXME: generate resource binding. - // See https://github.com/llvm/llvm-project/issues/57915. + hlsl::ResourceClass RC = + Buf.IsCBuffer ? hlsl::ResourceClass::CBuffer : hlsl::ResourceClass::SRV; + llvm::hlsl::ResourceKind RK = Buf.IsCBuffer + ? llvm::hlsl::ResourceKind::CBuffer + : llvm::hlsl::ResourceKind::TBuffer; + std::string TyName = + Buf.Name.str() + (Buf.IsCBuffer ? ".cb." : ".tb.") + "ty"; + addBufferResourceAnnotation(GV, TyName, RC, RK, Buf.Binding); } } -CGHLSLRuntime::Buffer::Buffer(const HLSLBufferDecl *D) { - Name = D->getName(); - IsCBuffer = D->isCBuffer(); - if (auto *Binding = D->getAttr()) { - llvm::APInt RegInt(64, 0); - Binding->getSlot().substr(1).getAsInteger(10, RegInt); - Reg = RegInt.getLimitedValue(); +CGHLSLRuntime::Buffer::Buffer(const HLSLBufferDecl *D) + : Name(D->getName()), IsCBuffer(D->isCBuffer()), + Binding(D->getAttr()) {} - llvm::APInt SpaceInt(64, 0); - Binding->getSpace().substr(5).getAsInteger(10, RegInt); - Space = SpaceInt.getLimitedValue(); - } else { - Space = 0; +void CGHLSLRuntime::addBufferResourceAnnotation(llvm::GlobalVariable *GV, + llvm::StringRef TyName, + hlsl::ResourceClass RC, + llvm::hlsl::ResourceKind RK, + BufferResBinding &Binding) { + uint32_t Counter = ResourceCounters[static_cast(RC)]++; + llvm::Module &M = CGM.getModule(); + + NamedMDNode *ResourceMD = nullptr; + switch (RC) { + case hlsl::ResourceClass::UAV: + ResourceMD = M.getOrInsertNamedMetadata("hlsl.uavs"); + break; + case hlsl::ResourceClass::SRV: + ResourceMD = M.getOrInsertNamedMetadata("hlsl.srvs"); + break; + case hlsl::ResourceClass::CBuffer: + ResourceMD = M.getOrInsertNamedMetadata("hlsl.cbufs"); + break; + default: + assert(false && "Unsupported buffer type!"); + return; } + + assert(ResourceMD != nullptr && + "ResourceMD must have been set by the switch above."); + + llvm::hlsl::FrontendResource Res( + GV, TyName, Counter, RK, Binding.Reg.value_or(UINT_MAX), Binding.Space); + ResourceMD->addOperand(Res.getMetadata()); +} + +static llvm::hlsl::ResourceKind +castResourceShapeToResourceKind(HLSLResourceAttr::ResourceKind RK) { + switch (RK) { + case HLSLResourceAttr::ResourceKind::Texture1D: + return llvm::hlsl::ResourceKind::Texture1D; + case HLSLResourceAttr::ResourceKind::Texture2D: + return llvm::hlsl::ResourceKind::Texture2D; + case HLSLResourceAttr::ResourceKind::Texture2DMS: + return llvm::hlsl::ResourceKind::Texture2DMS; + case HLSLResourceAttr::ResourceKind::Texture3D: + return llvm::hlsl::ResourceKind::Texture3D; + case HLSLResourceAttr::ResourceKind::TextureCube: + return llvm::hlsl::ResourceKind::TextureCube; + case HLSLResourceAttr::ResourceKind::Texture1DArray: + return llvm::hlsl::ResourceKind::Texture1DArray; + case HLSLResourceAttr::ResourceKind::Texture2DArray: + return llvm::hlsl::ResourceKind::Texture2DArray; + case HLSLResourceAttr::ResourceKind::Texture2DMSArray: + return llvm::hlsl::ResourceKind::Texture2DMSArray; + case HLSLResourceAttr::ResourceKind::TextureCubeArray: + return llvm::hlsl::ResourceKind::TextureCubeArray; + case HLSLResourceAttr::ResourceKind::TypedBuffer: + return llvm::hlsl::ResourceKind::TypedBuffer; + case HLSLResourceAttr::ResourceKind::RawBuffer: + return llvm::hlsl::ResourceKind::RawBuffer; + case HLSLResourceAttr::ResourceKind::StructuredBuffer: + return llvm::hlsl::ResourceKind::StructuredBuffer; + case HLSLResourceAttr::ResourceKind::CBufferKind: + return llvm::hlsl::ResourceKind::CBuffer; + case HLSLResourceAttr::ResourceKind::SamplerKind: + return llvm::hlsl::ResourceKind::Sampler; + case HLSLResourceAttr::ResourceKind::TBuffer: + return llvm::hlsl::ResourceKind::TBuffer; + case HLSLResourceAttr::ResourceKind::RTAccelerationStructure: + return llvm::hlsl::ResourceKind::RTAccelerationStructure; + case HLSLResourceAttr::ResourceKind::FeedbackTexture2D: + return llvm::hlsl::ResourceKind::FeedbackTexture2D; + case HLSLResourceAttr::ResourceKind::FeedbackTexture2DArray: + return llvm::hlsl::ResourceKind::FeedbackTexture2DArray; + } + // Make sure to update HLSLResourceAttr::ResourceKind when add new Kind to + // hlsl::ResourceKind. Assume FeedbackTexture2DArray is the last enum for + // HLSLResourceAttr::ResourceKind. + static_assert( + static_cast( + HLSLResourceAttr::ResourceKind::FeedbackTexture2DArray) == + (static_cast(llvm::hlsl::ResourceKind::NumEntries) - 2)); } void CGHLSLRuntime::annotateHLSLResource(const VarDecl *D, GlobalVariable *GV) { @@ -210,26 +284,27 @@ return; HLSLResourceAttr::ResourceClass RC = Attr->getResourceType(); - uint32_t Counter = ResourceCounters[static_cast(RC)]++; - - NamedMDNode *ResourceMD = nullptr; - switch (RC) { - case HLSLResourceAttr::ResourceClass::UAV: - ResourceMD = CGM.getModule().getOrInsertNamedMetadata("hlsl.uavs"); - break; - default: - assert(false && "Unsupported buffer type!"); - return; - } - - assert(ResourceMD != nullptr && - "ResourceMD must have been set by the switch above."); + llvm::hlsl::ResourceKind RK = + castResourceShapeToResourceKind(Attr->getResourceShape()); - auto &Ctx = CGM.getModule().getContext(); - IRBuilder<> B(Ctx); QualType QT(Ty, 0); - llvm::hlsl::FrontendResource Res(GV, QT.getAsString(), Counter); - ResourceMD->addOperand(Res.getMetadata()); + BufferResBinding Binding(D->getAttr()); + addBufferResourceAnnotation( + GV, QT.getAsString(), static_cast(RC), RK, Binding); +} + +CGHLSLRuntime::BufferResBinding::BufferResBinding( + HLSLResourceBindingAttr *Binding) { + if (Binding) { + llvm::APInt RegInt(64, 0); + Binding->getSlot().substr(1).getAsInteger(10, RegInt); + Reg = RegInt.getLimitedValue(); + llvm::APInt SpaceInt(64, 0); + Binding->getSpace().substr(5).getAsInteger(10, SpaceInt); + Space = SpaceInt.getLimitedValue(); + } else { + Space = 0; + } } void clang::CodeGen::CGHLSLRuntime::setHLSLEntryAttributes( diff --git a/clang/test/CodeGenHLSL/builtins/RWBuffer-annotations.hlsl b/clang/test/CodeGenHLSL/builtins/RWBuffer-annotations.hlsl --- a/clang/test/CodeGenHLSL/builtins/RWBuffer-annotations.hlsl +++ b/clang/test/CodeGenHLSL/builtins/RWBuffer-annotations.hlsl @@ -3,10 +3,22 @@ RWBuffer Buffer1; RWBuffer > BufferArray[4]; +RWBuffer Buffer2 : register(u3); +RWBuffer > BufferArray2[4] : register(u4); + +RWBuffer Buffer3 : register(u3, space1); +RWBuffer > BufferArray3[4] : register(u4, space1); + + + [numthreads(1,1,1)] void main() { } -// CHECK: !hlsl.uavs = !{![[Single:[0-9]+]], ![[Array:[0-9]+]]} -// CHECK-DAG: ![[Single]] = !{ptr @"?Buffer1@@3V?$RWBuffer@M@hlsl@@A", !"RWBuffer", i32 0} -// CHECK-DAG: ![[Array]] = !{ptr @"?BufferArray@@3PAV?$RWBuffer@T?$__vector@M$03@__clang@@@hlsl@@A", !"RWBuffer >", i32 1} +// CHECK: !hlsl.uavs = !{![[Single:[0-9]+]], ![[Array:[0-9]+]], ![[SingleAllocated:[0-9]+]], ![[ArrayAllocated:[0-9]+]], ![[SingleSpace:[0-9]+]], ![[ArraySpace:[0-9]+]]} +// CHECK-DAG: ![[Single]] = !{ptr @"?Buffer1@@3V?$RWBuffer@M@hlsl@@A", !"RWBuffer", i32 0, i32 10, i32 -1, i32 0} +// CHECK-DAG: ![[Array]] = !{ptr @"?BufferArray@@3PAV?$RWBuffer@T?$__vector@M$03@__clang@@@hlsl@@A", !"RWBuffer >", i32 1, i32 10, i32 -1, i32 0} +// CHECK-DAG: ![[SingleAllocated]] = !{ptr @"?Buffer2@@3V?$RWBuffer@M@hlsl@@A", !"RWBuffer", i32 2, i32 10, i32 3, i32 0} +// CHECK-DAG: ![[ArrayAllocated]] = !{ptr @"?BufferArray2@@3PAV?$RWBuffer@T?$__vector@M$03@__clang@@@hlsl@@A", !"RWBuffer >", i32 3, i32 10, i32 4, i32 0} +// CHECK-DAG: ![[SingleSpace]] = !{ptr @"?Buffer3@@3V?$RWBuffer@M@hlsl@@A", !"RWBuffer", i32 4, i32 10, i32 3, i32 1} +// CHECK-DAG: ![[ArraySpace]] = !{ptr @"?BufferArray3@@3PAV?$RWBuffer@T?$__vector@M$03@__clang@@@hlsl@@A", !"RWBuffer >", i32 5, i32 10, i32 4, i32 1} diff --git a/clang/test/CodeGenHLSL/cbuf.hlsl b/clang/test/CodeGenHLSL/cbuf.hlsl --- a/clang/test/CodeGenHLSL/cbuf.hlsl +++ b/clang/test/CodeGenHLSL/cbuf.hlsl @@ -3,7 +3,7 @@ // RUN: -emit-llvm -disable-llvm-passes -o - | FileCheck %s // CHECK: @[[CB:.+]] = external constant { float, double } -cbuffer A : register(b0, space1) { +cbuffer A : register(b0, space2) { float a; double b; } @@ -21,3 +21,8 @@ // CHECK: load double, ptr getelementptr inbounds ({ float, double }, ptr @[[TB]], i32 0, i32 1), align 8 return a + b + c*d; } + +// CHECK: !hlsl.cbufs = !{![[CBMD:[0-9]+]]} +// CHECK: !hlsl.srvs = !{![[TBMD:[0-9]+]]} +// CHECK: ![[CBMD]] = !{ptr @[[CB]], !"A.cb.ty", i32 0, i32 13, i32 0, i32 2} +// CHECK: ![[TBMD]] = !{ptr @[[TB]], !"A.tb.ty", i32 0, i32 15, i32 2, i32 1} diff --git a/llvm/include/llvm/Frontend/HLSL/HLSLResource.h b/llvm/include/llvm/Frontend/HLSL/HLSLResource.h --- a/llvm/include/llvm/Frontend/HLSL/HLSLResource.h +++ b/llvm/include/llvm/Frontend/HLSL/HLSLResource.h @@ -21,20 +21,48 @@ namespace hlsl { +// The value ordering of this enumeration is part of the DXIL ABI. Elements +// can only be added to the end, and not removed. +enum class ResourceKind : uint32_t { + Invalid = 0, + Texture1D, + Texture2D, + Texture2DMS, + Texture3D, + TextureCube, + Texture1DArray, + Texture2DArray, + Texture2DMSArray, + TextureCubeArray, + TypedBuffer, + RawBuffer, + StructuredBuffer, + CBuffer, + Sampler, + TBuffer, + RTAccelerationStructure, + FeedbackTexture2D, + FeedbackTexture2DArray, + NumEntries, +}; + class FrontendResource { MDNode *Entry; public: FrontendResource(MDNode *E) : Entry(E) { - assert(Entry->getNumOperands() == 3 && "Unexpected metadata shape"); + assert(Entry->getNumOperands() == 6 && "Unexpected metadata shape"); } - FrontendResource(GlobalVariable *GV, StringRef TypeStr, uint32_t Counter); + FrontendResource(GlobalVariable *GV, StringRef TypeStr, uint32_t Counter, + ResourceKind RK, uint32_t ResIndex, uint32_t Space); GlobalVariable *getGlobalVariable(); StringRef getSourceType(); Constant *getID(); - + uint32_t getResourceKind(); + uint32_t getResourceIndex(); + uint32_t getSpace(); MDNode *getMetadata() { return Entry; } }; } // namespace hlsl diff --git a/llvm/lib/Frontend/HLSL/HLSLResource.cpp b/llvm/lib/Frontend/HLSL/HLSLResource.cpp --- a/llvm/lib/Frontend/HLSL/HLSLResource.cpp +++ b/llvm/lib/Frontend/HLSL/HLSLResource.cpp @@ -31,11 +31,31 @@ return cast(Entry->getOperand(2))->getValue(); } +uint32_t FrontendResource::FrontendResource::getResourceKind() { + return cast( + cast(Entry->getOperand(3))->getValue()) + ->getLimitedValue(); +} +uint32_t FrontendResource::getResourceIndex() { + return cast( + cast(Entry->getOperand(4))->getValue()) + ->getLimitedValue(); +} +uint32_t FrontendResource::getSpace() { + return cast( + cast(Entry->getOperand(5))->getValue()) + ->getLimitedValue(); +} + FrontendResource::FrontendResource(GlobalVariable *GV, StringRef TypeStr, - uint32_t Counter) { + uint32_t Counter, ResourceKind RK, + uint32_t ResIndex, uint32_t Space) { auto &Ctx = GV->getContext(); IRBuilder<> B(Ctx); - Entry = - MDNode::get(Ctx, {ValueAsMetadata::get(GV), MDString::get(Ctx, TypeStr), - ConstantAsMetadata::get(B.getInt32(Counter))}); + Entry = MDNode::get( + Ctx, {ValueAsMetadata::get(GV), MDString::get(Ctx, TypeStr), + ConstantAsMetadata::get(B.getInt32(Counter)), + ConstantAsMetadata::get(B.getInt32(static_cast(RK))), + ConstantAsMetadata::get(B.getInt32(ResIndex)), + ConstantAsMetadata::get(B.getInt32(Space))}); } diff --git a/llvm/lib/Target/DirectX/DXILResource.h b/llvm/lib/Target/DirectX/DXILResource.h --- a/llvm/lib/Target/DirectX/DXILResource.h +++ b/llvm/lib/Target/DirectX/DXILResource.h @@ -40,32 +40,7 @@ void write(LLVMContext &Ctx, MutableArrayRef Entries) const; void print(raw_ostream &O, StringRef IDPrefix, StringRef BindingPrefix) const; - - // The value ordering of this enumeration is part of the DXIL ABI. Elements - // can only be added to the end, and not removed. - enum class Kinds : uint32_t { - Invalid = 0, - Texture1D, - Texture2D, - Texture2DMS, - Texture3D, - TextureCube, - Texture1DArray, - Texture2DArray, - Texture2DMSArray, - TextureCubeArray, - TypedBuffer, - RawBuffer, - StructuredBuffer, - CBuffer, - Sampler, - TBuffer, - RTAccelerationStructure, - FeedbackTexture2D, - FeedbackTexture2DArray, - NumEntries, - }; - + using Kinds = hlsl::ResourceKind; static StringRef getKindName(Kinds Kind); static void printKind(Kinds Kind, unsigned Alignment, raw_ostream &OS, bool SRV = false, bool HasCounter = false, diff --git a/llvm/lib/Target/DirectX/DXILResource.cpp b/llvm/lib/Target/DirectX/DXILResource.cpp --- a/llvm/lib/Target/DirectX/DXILResource.cpp +++ b/llvm/lib/Target/DirectX/DXILResource.cpp @@ -36,8 +36,8 @@ void Resources::collect(Module &M) { collectUAVs(M); } ResourceBase::ResourceBase(uint32_t I, FrontendResource R) - : ID(I), GV(R.getGlobalVariable()), Name(""), Space(0), LowerBound(0), - RangeSize(1) { + : ID(I), GV(R.getGlobalVariable()), Name(""), Space(R.getSpace()), + LowerBound(R.getResourceIndex()), RangeSize(1) { if (auto *ArrTy = dyn_cast(GV->getInitializer()->getType())) RangeSize = ArrTy->getNumElements(); } @@ -210,8 +210,9 @@ } UAVResource::UAVResource(uint32_t I, FrontendResource R) - : ResourceBase(I, R), Shape(Kinds::Invalid), GloballyCoherent(false), - HasCounter(false), IsROV(false), ExtProps() { + : ResourceBase(I, R), + Shape(static_cast(R.getResourceKind())), + GloballyCoherent(false), HasCounter(false), IsROV(false), ExtProps() { parseSourceType(R.getSourceType()); } diff --git a/llvm/test/CodeGen/DirectX/UAVMetadata.ll b/llvm/test/CodeGen/DirectX/UAVMetadata.ll --- a/llvm/test/CodeGen/DirectX/UAVMetadata.ll +++ b/llvm/test/CodeGen/DirectX/UAVMetadata.ll @@ -13,15 +13,15 @@ ; PRINT-NEXT:; Name Type Format Dim ID HLSL Bind Count ; PRINT-NEXT:; ------------------------------ ---------- ------- ----------- ------- -------------- ------ ; PRINT-NEXT:; UAV f16 buf U0 u0 1 -; PRINT-NEXT:; UAV f32 buf U1 u0 1 -; PRINT-NEXT:; UAV f64 buf U2 u0 1 -; PRINT-NEXT:; UAV i1 buf U3 u0 2 -; PRINT-NEXT:; UAV byte r/w U4 u0 1 -; PRINT-NEXT:; UAV struct r/w U5 u0 1 -; PRINT-NEXT:; UAV i32 buf U6 u0 1 -; PRINT-NEXT:; UAV struct r/w U7 u0 1 -; PRINT-NEXT:; UAV byte r/w U8 u0 1 -; PRINT-NEXT:; UAV u64 buf U9 u0 1 +; PRINT-NEXT:; UAV f32 buf U1 u1 1 +; PRINT-NEXT:; UAV f64 buf U2 u2 1 +; PRINT-NEXT:; UAV i1 buf U3 u3 2 +; PRINT-NEXT:; UAV byte r/w U4 u5 1 +; PRINT-NEXT:; UAV struct r/w U5 u6 1 +; PRINT-NEXT:; UAV i32 buf U6 u7 1 +; PRINT-NEXT:; UAV struct r/w U7 u8 1 +; PRINT-NEXT:; UAV byte r/w U8 u9 1 +; PRINT-NEXT:; UAV u64 buf U9 u10,space2 1 @Zero = local_unnamed_addr global %"class.hlsl::RWBuffer" zeroinitializer, align 4 @One = local_unnamed_addr global %"class.hlsl::RWBuffer" zeroinitializer, align 4 @@ -37,16 +37,16 @@ !hlsl.uavs = !{!0, !1, !2, !3, !4, !5, !6, !7, !8, !9} -!0 = !{ptr @Zero, !"RWBuffer", i32 0} -!1 = !{ptr @One, !"Buffer>", i32 1} -!2 = !{ptr @Two, !"Buffer", i32 2} -!3 = !{ptr @Three, !"Buffer", i32 3} -!4 = !{ptr @Four, !"ByteAddressBuffer", i32 4} -!5 = !{ptr @Five, !"StructuredBuffer", i32 5} -!6 = !{ptr @Six, !"RasterizerOrderedBuffer", i32 6} -!7 = !{ptr @Seven, !"RasterizerOrderedStructuredBuffer", i32 7} -!8 = !{ptr @Eight, !"RasterizerOrderedByteAddressBuffer", i32 8} -!9 = !{ptr @Nine, !"RWBuffer", i32 9} +!0 = !{ptr @Zero, !"RWBuffer", i32 0, i32 10, i32 0, i32 0} +!1 = !{ptr @One, !"Buffer>", i32 1, i32 10, i32 1, i32 0} +!2 = !{ptr @Two, !"Buffer", i32 2, i32 10, i32 2, i32 0} +!3 = !{ptr @Three, !"Buffer", i32 3, i32 10, i32 3, i32 0} +!4 = !{ptr @Four, !"ByteAddressBuffer", i32 4, i32 11, i32 5, i32 0} +!5 = !{ptr @Five, !"StructuredBuffer", i32 5, i32 12, i32 6, i32 0} +!6 = !{ptr @Six, !"RasterizerOrderedBuffer", i32 6, i32 10, i32 7, i32 0} +!7 = !{ptr @Seven, !"RasterizerOrderedStructuredBuffer", i32 7, i32 12, i32 8, i32 0} +!8 = !{ptr @Eight, !"RasterizerOrderedByteAddressBuffer", i32 8, i32 11, i32 9, i32 0} +!9 = !{ptr @Nine, !"RWBuffer", i32 9, i32 10, i32 10, i32 2} ; CHECK: !dx.resources = !{[[ResList:[!][0-9]+]]} @@ -57,21 +57,21 @@ ; CHECK-SAME: [[Eight:[!][0-9]+]], [[Nine:[!][0-9]+]]} ; CHECK: [[Zero]] = !{i32 0, ptr @Zero, !"", i32 0, i32 0, i32 1, i32 10, i1 false, i1 false, i1 false, [[Half:[!][0-9]+]]} ; CHECK: [[Half]] = !{i32 0, i32 8} -; CHECK: [[One]] = !{i32 1, ptr @One, !"", i32 0, i32 0, i32 1, i32 10, i1 false, i1 false, i1 false, [[Float:[!][0-9]+]]} +; CHECK: [[One]] = !{i32 1, ptr @One, !"", i32 0, i32 1, i32 1, i32 10, i1 false, i1 false, i1 false, [[Float:[!][0-9]+]]} ; CHECK: [[Float]] = !{i32 0, i32 9} -; CHECK: [[Two]] = !{i32 2, ptr @Two, !"", i32 0, i32 0, i32 1, i32 10, i1 false, i1 false, i1 false, [[Double:[!][0-9]+]]} +; CHECK: [[Two]] = !{i32 2, ptr @Two, !"", i32 0, i32 2, i32 1, i32 10, i1 false, i1 false, i1 false, [[Double:[!][0-9]+]]} ; CHECK: [[Double]] = !{i32 0, i32 10} -; CHECK: [[Three]] = !{i32 3, ptr @Three, !"", i32 0, i32 0, i32 2, i32 10, i1 false, i1 false, i1 false, [[Bool:[!][0-9]+]]} +; CHECK: [[Three]] = !{i32 3, ptr @Three, !"", i32 0, i32 3, i32 2, i32 10, i1 false, i1 false, i1 false, [[Bool:[!][0-9]+]]} ; CHECK: [[Bool]] = !{i32 0, i32 1} -; CHECK: [[Four]] = !{i32 4, ptr @Four, !"", i32 0, i32 0, i32 1, i32 11, i1 false, i1 false, i1 false, [[I16:[!][0-9]+]]} +; CHECK: [[Four]] = !{i32 4, ptr @Four, !"", i32 0, i32 5, i32 1, i32 11, i1 false, i1 false, i1 false, [[I16:[!][0-9]+]]} ; CHECK: [[I16]] = !{i32 0, i32 2} -; CHECK: [[Five]] = !{i32 5, ptr @Five, !"", i32 0, i32 0, i32 1, i32 12, i1 false, i1 false, i1 false, [[U16:[!][0-9]+]]} +; CHECK: [[Five]] = !{i32 5, ptr @Five, !"", i32 0, i32 6, i32 1, i32 12, i1 false, i1 false, i1 false, [[U16:[!][0-9]+]]} ; CHECK: [[U16]] = !{i32 0, i32 3} -; CHECK: [[Six]] = !{i32 6, ptr @Six, !"", i32 0, i32 0, i32 1, i32 10, i1 false, i1 false, i1 true, [[I32:[!][0-9]+]]} +; CHECK: [[Six]] = !{i32 6, ptr @Six, !"", i32 0, i32 7, i32 1, i32 10, i1 false, i1 false, i1 true, [[I32:[!][0-9]+]]} ; CHECK: [[I32]] = !{i32 0, i32 4} -; CHECK: [[Seven]] = !{i32 7, ptr @Seven, !"", i32 0, i32 0, i32 1, i32 12, i1 false, i1 false, i1 true, [[U32:[!][0-9]+]]} +; CHECK: [[Seven]] = !{i32 7, ptr @Seven, !"", i32 0, i32 8, i32 1, i32 12, i1 false, i1 false, i1 true, [[U32:[!][0-9]+]]} ; CHECK: [[U32]] = !{i32 0, i32 5} -; CHECK: [[Eight]] = !{i32 8, ptr @Eight, !"", i32 0, i32 0, i32 1, i32 11, i1 false, i1 false, i1 true, [[I64:[!][0-9]+]]} +; CHECK: [[Eight]] = !{i32 8, ptr @Eight, !"", i32 0, i32 9, i32 1, i32 11, i1 false, i1 false, i1 true, [[I64:[!][0-9]+]]} ; CHECK: [[I64]] = !{i32 0, i32 6} -; CHECK: [[Nine]] = !{i32 9, ptr @Nine, !"", i32 0, i32 0, i32 1, i32 10, i1 false, i1 false, i1 false, [[U64:[!][0-9]+]]} +; CHECK: [[Nine]] = !{i32 9, ptr @Nine, !"", i32 2, i32 10, i32 1, i32 10, i1 false, i1 false, i1 false, [[U64:[!][0-9]+]]} ; CHECK: [[U64]] = !{i32 0, i32 7}