Skip to content

Commit 65fa57b

Browse files
inbelicFinn Plummer
andauthored
[HLSL][RootSignature] Define and integrate HLSLRootSignatureAttr (#134124)
- Defines HLSLRootSignature Attr in `Attr.td` - Define and implement handleHLSLRootSignature in `SemaHLSL` - Adds sample test case to show AST Node is generated in `RootSignatures-AST.hlsl` This commit will "hook-up" the seperately defined RootSignature parser and invoke it to create the RootElements, then store them on the ASTContext and finally store the reference to the Elements in RootSignatureAttr Resolves #119011 --------- Co-authored-by: Finn Plummer <[email protected]>
1 parent bf388f8 commit 65fa57b

File tree

8 files changed

+103
-0
lines changed

8 files changed

+103
-0
lines changed

clang/include/clang/AST/Attr.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
#include "clang/Basic/SourceLocation.h"
2727
#include "clang/Support/Compiler.h"
2828
#include "llvm/Frontend/HLSL/HLSLResource.h"
29+
#include "llvm/Frontend/HLSL/HLSLRootSignature.h"
2930
#include "llvm/Support/CodeGen.h"
3031
#include "llvm/Support/ErrorHandling.h"
3132
#include "llvm/Support/VersionTuple.h"

clang/include/clang/Basic/Attr.td

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4710,6 +4710,25 @@ def Error : InheritableAttr {
47104710
let Documentation = [ErrorAttrDocs];
47114711
}
47124712

4713+
def HLSLRootSignature : Attr {
4714+
/// [RootSignature(Signature)]
4715+
let Spellings = [Microsoft<"RootSignature">];
4716+
let Args = [StringArgument<"Signature">];
4717+
let Subjects = SubjectList<[Function],
4718+
ErrorDiag, "'function'">;
4719+
let LangOpts = [HLSL];
4720+
let Documentation = [HLSLRootSignatureDocs];
4721+
let AdditionalMembers = [{
4722+
private:
4723+
ArrayRef<llvm::hlsl::rootsig::RootElement> RootElements;
4724+
public:
4725+
void setElements(ArrayRef<llvm::hlsl::rootsig::RootElement> Elements) {
4726+
RootElements = Elements;
4727+
}
4728+
auto getElements() const { return RootElements; }
4729+
}];
4730+
}
4731+
47134732
def HLSLNumThreads: InheritableAttr {
47144733
let Spellings = [Microsoft<"numthreads">];
47154734
let Args = [IntArgument<"X">, IntArgument<"Y">, IntArgument<"Z">];

clang/include/clang/Basic/AttrDocs.td

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8145,6 +8145,17 @@ and https://microsoft.github.io/hlsl-specs/proposals/0013-wave-size-range.html
81458145
}];
81468146
}
81478147

8148+
def HLSLRootSignatureDocs : Documentation {
8149+
let Category = DocCatFunction;
8150+
let Content = [{
8151+
The ``RootSignature`` attribute applies to HLSL entry functions to define what
8152+
types of resources are bound to the graphics pipeline.
8153+
8154+
For details about the use and specification of Root Signatures please see here:
8155+
https://learn.microsoft.com/en-us/windows/win32/direct3d12/root-signatures
8156+
}];
8157+
}
8158+
81488159
def NumThreadsDocs : Documentation {
81498160
let Category = DocCatFunction;
81508161
let Content = [{

clang/include/clang/Sema/SemaHLSL.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,7 @@ class SemaHLSL : public SemaBase {
118118
bool IsCompAssign);
119119
void emitLogicalOperatorFixIt(Expr *LHS, Expr *RHS, BinaryOperatorKind Opc);
120120

121+
void handleRootSignatureAttr(Decl *D, const ParsedAttr &AL);
121122
void handleNumThreadsAttr(Decl *D, const ParsedAttr &AL);
122123
void handleWaveSizeAttr(Decl *D, const ParsedAttr &AL);
123124
void handleSV_DispatchThreadIDAttr(Decl *D, const ParsedAttr &AL);

clang/lib/Sema/SemaDeclAttr.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7498,6 +7498,9 @@ ProcessDeclAttribute(Sema &S, Scope *scope, Decl *D, const ParsedAttr &AL,
74987498
break;
74997499

75007500
// HLSL attributes:
7501+
case ParsedAttr::AT_HLSLRootSignature:
7502+
S.HLSL().handleRootSignatureAttr(D, AL);
7503+
break;
75017504
case ParsedAttr::AT_HLSLNumThreads:
75027505
S.HLSL().handleNumThreadsAttr(D, AL);
75037506
break;

clang/lib/Sema/SemaHLSL.cpp

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
#include "clang/Basic/SourceLocation.h"
2929
#include "clang/Basic/Specifiers.h"
3030
#include "clang/Basic/TargetInfo.h"
31+
#include "clang/Parse/ParseHLSLRootSignature.h"
3132
#include "clang/Sema/Initialization.h"
3233
#include "clang/Sema/ParsedAttr.h"
3334
#include "clang/Sema/Sema.h"
@@ -941,6 +942,40 @@ void SemaHLSL::emitLogicalOperatorFixIt(Expr *LHS, Expr *RHS,
941942
<< NewFnName << FixItHint::CreateReplacement(FullRange, OS.str());
942943
}
943944

945+
void SemaHLSL::handleRootSignatureAttr(Decl *D, const ParsedAttr &AL) {
946+
if (AL.getNumArgs() != 1) {
947+
Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << AL << 1;
948+
return;
949+
}
950+
951+
StringRef Signature;
952+
if (!SemaRef.checkStringLiteralArgumentAttr(AL, 0, Signature))
953+
return;
954+
955+
SourceLocation Loc = AL.getArgAsExpr(0)->getExprLoc();
956+
// TODO(#126565): pass down below to lexer when fp is supported
957+
// llvm::RoundingMode RM = SemaRef.CurFPFeatures.getRoundingMode();
958+
hlsl::RootSignatureLexer Lexer(Signature, Loc);
959+
SmallVector<llvm::hlsl::rootsig::RootElement> Elements;
960+
hlsl::RootSignatureParser Parser(Elements, Lexer, SemaRef.getPreprocessor());
961+
962+
if (Parser.parse())
963+
return;
964+
965+
// Allocate elements onto AST context
966+
unsigned N = Elements.size();
967+
auto RootElements = MutableArrayRef<llvm::hlsl::rootsig::RootElement>(
968+
::new (getASTContext()) llvm::hlsl::rootsig::RootElement[N], N);
969+
for (unsigned I = 0; I < N; ++I)
970+
RootElements[I] = Elements[I];
971+
972+
// Set elements
973+
auto *Result = ::new (getASTContext())
974+
HLSLRootSignatureAttr(getASTContext(), AL, Signature);
975+
Result->setElements(ArrayRef<llvm::hlsl::rootsig::RootElement>(RootElements));
976+
D->addAttr(Result);
977+
}
978+
944979
void SemaHLSL::handleNumThreadsAttr(Decl *D, const ParsedAttr &AL) {
945980
llvm::VersionTuple SMVersion =
946981
getASTContext().getTargetInfo().getTriple().getOSVersion();
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-library -ast-dump \
2+
// RUN: -disable-llvm-passes -o - %s | FileCheck %s
3+
4+
// This test ensures that the sample root signature is parsed without error and
5+
// the Attr AST Node is created succesfully. If an invalid root signature was
6+
// passed in then we would exit out of Sema before the Attr is created.
7+
8+
#define SampleRS \
9+
"DescriptorTable( " \
10+
" CBV(), " \
11+
" SRV(), " \
12+
" UAV()" \
13+
"), " \
14+
"DescriptorTable(Sampler())"
15+
16+
// CHECK: HLSLRootSignatureAttr
17+
// CHECK-SAME: "DescriptorTable(
18+
// CHECK-SAME: CBV(),
19+
// CHECK-SAME: SRV(),
20+
// CHECK-SAME: UAV()
21+
// CHECK-SAME: ),
22+
// CHECK-SAME: DescriptorTable(Sampler())"
23+
[RootSignature(SampleRS)]
24+
void main() {}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.3-library -x hlsl -o - %s -verify
2+
3+
// Attr test
4+
5+
[RootSignature()] // expected-error {{'RootSignature' attribute takes one argument}}
6+
void bad_root_signature_0() {}
7+
8+
[RootSignature("Arg1", "Arg2")] // expected-error {{'RootSignature' attribute takes one argument}}
9+
void bad_root_signature_1() {}

0 commit comments

Comments
 (0)