Skip to content

Commit f2c8c42

Browse files
joaosaffranjoaosaffran
andauthored
[HLSL] Update Frontend to support version 1.2 of root signature (#160616)
This patch updates the frontend to support version 1.2 of root signatures, it adds parsing, metadata generation and a few tests. --------- Co-authored-by: joaosaffran <[email protected]>
1 parent f1986d9 commit f2c8c42

20 files changed

+194
-28
lines changed

clang/include/clang/Basic/LangOptions.h

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -549,8 +549,7 @@ class LangOptions : public LangOptionsBase {
549549
bool CheckNew = false;
550550

551551
/// The HLSL root signature version for dxil.
552-
llvm::dxbc::RootSignatureVersion HLSLRootSigVer =
553-
llvm::dxbc::RootSignatureVersion::V1_1;
552+
llvm::dxbc::RootSignatureVersion HLSLRootSigVer;
554553

555554
/// The HLSL root signature that will be used to overide the root signature
556555
/// used for the shader entry point.

clang/include/clang/Driver/Options.td

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9473,7 +9473,7 @@ def target_profile : DXCJoinedOrSeparate<"T">, MetaVarName<"<profile>">,
94739473
"lib_6_3, lib_6_4, lib_6_5, lib_6_6, lib_6_7, lib_6_x,"
94749474
"ms_6_5, ms_6_6, ms_6_7,"
94759475
"as_6_5, as_6_6, as_6_7,"
9476-
"rootsig_1_0, rootsig_1_1">;
9476+
"rootsig_1_0, rootsig_1_1, rootsig_1_2">;
94779477
def emit_pristine_llvm : DXCFlag<"emit-pristine-llvm">,
94789478
HelpText<"Emit pristine LLVM IR from the frontend by not running any LLVM passes at all."
94799479
"Same as -S + -emit-llvm + -disable-llvm-passes.">;
@@ -9486,9 +9486,9 @@ def fdx_rootsignature_version :
94869486
Group<dxc_Group>,
94879487
Visibility<[ClangOption, CC1Option]>,
94889488
HelpText<"Root Signature Version">,
9489-
Values<"rootsig_1_0,rootsig_1_1">,
9489+
Values<"rootsig_1_0,rootsig_1_1,rootsig_1_2">,
94909490
NormalizedValuesScope<"llvm::dxbc::RootSignatureVersion">,
9491-
NormalizedValues<["V1_0", "V1_1"]>,
9491+
NormalizedValues<["V1_0", "V1_1", "V1_2"]>,
94929492
MarshallingInfoEnum<LangOpts<"HLSLRootSigVer">, "V1_1">;
94939493
def dxc_rootsig_ver :
94949494
Separate<["/", "-"], "force-rootsig-ver">,

clang/include/clang/Lex/HLSLRootSignatureTokenKinds.def

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,9 @@
6565
#ifndef STATIC_BORDER_COLOR_ENUM
6666
#define STATIC_BORDER_COLOR_ENUM(NAME, LIT) ENUM(NAME, LIT)
6767
#endif
68+
#ifndef STATIC_SAMPLER_FLAG_ENUM
69+
#define STATIC_SAMPLER_FLAG_ENUM(NAME, LIT) ENUM(NAME, LIT)
70+
#endif
6871

6972
// General Tokens:
7073
TOK(invalid, "invalid identifier")
@@ -228,6 +231,10 @@ STATIC_BORDER_COLOR_ENUM(OpaqueWhite, "STATIC_BORDER_COLOR_OPAQUE_WHITE")
228231
STATIC_BORDER_COLOR_ENUM(OpaqueBlackUint, "STATIC_BORDER_COLOR_OPAQUE_BLACK_UINT")
229232
STATIC_BORDER_COLOR_ENUM(OpaqueWhiteUint, "STATIC_BORDER_COLOR_OPAQUE_WHITE_UINT")
230233

234+
// Root Descriptor Flag Enums:
235+
STATIC_SAMPLER_FLAG_ENUM(UintBorderColor, "UINT_BORDER_COLOR")
236+
STATIC_SAMPLER_FLAG_ENUM(NonNormalizedCoordinates, "NON_NORMALIZED_COORDINATES")
237+
231238
#undef STATIC_BORDER_COLOR_ENUM
232239
#undef COMPARISON_FUNC_ENUM
233240
#undef TEXTURE_ADDRESS_MODE_ENUM
@@ -237,6 +244,7 @@ STATIC_BORDER_COLOR_ENUM(OpaqueWhiteUint, "STATIC_BORDER_COLOR_OPAQUE_WHITE_UINT
237244
#undef DESCRIPTOR_RANGE_FLAG_ENUM_OFF
238245
#undef DESCRIPTOR_RANGE_FLAG_ENUM_ON
239246
#undef ROOT_DESCRIPTOR_FLAG_ENUM
247+
#undef STATIC_SAMPLER_FLAG_ENUM
240248
#undef ROOT_FLAG_ENUM
241249
#undef DESCRIPTOR_RANGE_OFFSET_ENUM
242250
#undef UNBOUNDED_ENUM

clang/include/clang/Parse/ParseHLSLRootSignature.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,7 @@ class RootSignatureParser {
130130
std::optional<float> MaxLOD;
131131
std::optional<uint32_t> Space;
132132
std::optional<llvm::dxbc::ShaderVisibility> Visibility;
133+
std::optional<llvm::dxbc::StaticSamplerFlags> Flags;
133134
};
134135
std::optional<ParsedStaticSamplerParams> parseStaticSamplerParams();
135136

@@ -153,6 +154,8 @@ class RootSignatureParser {
153154
parseRootDescriptorFlags(RootSignatureToken::Kind Context);
154155
std::optional<llvm::dxbc::DescriptorRangeFlags>
155156
parseDescriptorRangeFlags(RootSignatureToken::Kind Context);
157+
std::optional<llvm::dxbc::StaticSamplerFlags>
158+
parseStaticSamplerFlags(RootSignatureToken::Kind Context);
156159

157160
/// Use NumericLiteralParser to convert CurToken.NumSpelling into a unsigned
158161
/// 32-bit integer

clang/lib/AST/TextNodeDumper.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3095,6 +3095,9 @@ void TextNodeDumper::VisitHLSLRootSignatureDecl(
30953095
case llvm::dxbc::RootSignatureVersion::V1_1:
30963096
OS << "1.1";
30973097
break;
3098+
case llvm::dxbc::RootSignatureVersion::V1_2:
3099+
OS << "1.2";
3100+
break;
30983101
}
30993102
OS << ", ";
31003103
llvm::hlsl::rootsig::dumpRootElements(OS, D->getRootElements());

clang/lib/Driver/ToolChains/HLSL.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ bool isLegalShaderModel(Triple &T) {
6464
} break;
6565
case Triple::EnvironmentType::RootSignature:
6666
VersionTuple MinVer(1, 0);
67-
VersionTuple MaxVer(1, 1);
67+
VersionTuple MaxVer(1, 2);
6868
return MinVer <= Version && Version <= MaxVer;
6969
}
7070
return false;

clang/lib/Parse/ParseHLSLRootSignature.cpp

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -485,6 +485,9 @@ std::optional<StaticSampler> RootSignatureParser::parseStaticSampler() {
485485
if (Params->Visibility.has_value())
486486
Sampler.Visibility = Params->Visibility.value();
487487

488+
if (Params->Flags.has_value())
489+
Sampler.Flags = Params->Flags.value();
490+
488491
return Sampler;
489492
}
490493

@@ -926,6 +929,20 @@ RootSignatureParser::parseStaticSamplerParams() {
926929
if (!Visibility.has_value())
927930
return std::nullopt;
928931
Params.Visibility = Visibility;
932+
} else if (tryConsumeExpectedToken(TokenKind::kw_flags)) {
933+
// `flags` `=` STATIC_SAMPLE_FLAGS
934+
if (Params.Flags.has_value()) {
935+
reportDiag(diag::err_hlsl_rootsig_repeat_param) << CurToken.TokKind;
936+
return std::nullopt;
937+
}
938+
939+
if (consumeExpectedToken(TokenKind::pu_equal))
940+
return std::nullopt;
941+
942+
auto Flags = parseStaticSamplerFlags(TokenKind::kw_flags);
943+
if (!Flags.has_value())
944+
return std::nullopt;
945+
Params.Flags = Flags;
929946
} else {
930947
consumeNextToken(); // let diagnostic be at the start of invalid token
931948
reportDiag(diag::err_hlsl_invalid_token)
@@ -1255,6 +1272,50 @@ RootSignatureParser::parseDescriptorRangeFlags(TokenKind Context) {
12551272
return Flags;
12561273
}
12571274

1275+
std::optional<llvm::dxbc::StaticSamplerFlags>
1276+
RootSignatureParser::parseStaticSamplerFlags(TokenKind Context) {
1277+
assert(CurToken.TokKind == TokenKind::pu_equal &&
1278+
"Expects to only be invoked starting at given keyword");
1279+
1280+
// Handle the edge-case of '0' to specify no flags set
1281+
if (tryConsumeExpectedToken(TokenKind::int_literal)) {
1282+
if (!verifyZeroFlag()) {
1283+
reportDiag(diag::err_hlsl_rootsig_non_zero_flag);
1284+
return std::nullopt;
1285+
}
1286+
return llvm::dxbc::StaticSamplerFlags::None;
1287+
}
1288+
1289+
TokenKind Expected[] = {
1290+
#define STATIC_SAMPLER_FLAG_ENUM(NAME, LIT) TokenKind::en_##NAME,
1291+
#include "clang/Lex/HLSLRootSignatureTokenKinds.def"
1292+
};
1293+
1294+
std::optional<llvm::dxbc::StaticSamplerFlags> Flags;
1295+
1296+
do {
1297+
if (tryConsumeExpectedToken(Expected)) {
1298+
switch (CurToken.TokKind) {
1299+
#define STATIC_SAMPLER_FLAG_ENUM(NAME, LIT) \
1300+
case TokenKind::en_##NAME: \
1301+
Flags = maybeOrFlag<llvm::dxbc::StaticSamplerFlags>( \
1302+
Flags, llvm::dxbc::StaticSamplerFlags::NAME); \
1303+
break;
1304+
#include "clang/Lex/HLSLRootSignatureTokenKinds.def"
1305+
default:
1306+
llvm_unreachable("Switch for consumed enum token was not provided");
1307+
}
1308+
} else {
1309+
consumeNextToken(); // consume token to point at invalid token
1310+
reportDiag(diag::err_hlsl_invalid_token)
1311+
<< /*value=*/1 << /*value of*/ Context;
1312+
return std::nullopt;
1313+
}
1314+
} while (tryConsumeExpectedToken(TokenKind::pu_or));
1315+
1316+
return Flags;
1317+
}
1318+
12581319
std::optional<uint32_t> RootSignatureParser::handleUIntLiteral() {
12591320
// Parse the numeric value and do semantic checks on its specification
12601321
clang::NumericLiteralParser Literal(

clang/test/AST/HLSL/RootSignature-Target-AST.hlsl

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,15 @@
11
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-rootsignature -ast-dump \
2+
// RUN: -fdx-rootsignature-version=rootsig_1_0 \
3+
// RUN: -hlsl-entry EntryRootSig -disable-llvm-passes -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-V1_0
4+
5+
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-rootsignature -ast-dump \
6+
// RUN: -fdx-rootsignature-version=rootsig_1_1 \
27
// RUN: -hlsl-entry EntryRootSig -disable-llvm-passes -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-V1_1
38

49
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-rootsignature -ast-dump \
5-
// RUN: -fdx-rootsignature-version=rootsig_1_0 \
6-
// RUN: -hlsl-entry EntryRootSig -disable-llvm-passes -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-V1_0
10+
// RUN: -fdx-rootsignature-version=rootsig_1_2 \
11+
// RUN: -hlsl-entry EntryRootSig -disable-llvm-passes -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-V1_2
12+
713

814
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-rootsignature -ast-dump \
915
// RUN: -D CmdRS='"UAV(u0)"'\
@@ -12,11 +18,13 @@
1218
// CHECK: -HLSLRootSignatureDecl 0x{{.*}} {{.*}} implicit [[ENTRY_RS_DECL:__hlsl_rootsig_decl_\d*]]
1319
// CHECK-V1_0-SAME: version: 1.0,
1420
// CHECK-V1_1-SAME: version: 1.1,
21+
// CHECK-V1_2-SAME: version: 1.2,
1522
// CHECK-SAME: RootElements{
1623
// CHECK-SAME: RootCBV(b0,
1724
// CHECK-SAME: space = 0, visibility = All,
1825
// CHECK-V1_0-SAME: flags = DataVolatile
1926
// CHECK-V1_1-SAME: flags = DataStaticWhileSetAtExecute
27+
// CHECK-V1_2-SAME: flags = DataStaticWhileSetAtExecute
2028
// CHECK-SAME: )
2129
// CHECK-SAME: }
2230
#define EntryRootSig "CBV(b0)"

clang/test/AST/HLSL/RootSignatures-AST.hlsl

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@
66
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-library -ast-dump \
77
// RUN: -fdx-rootsignature-version=rootsig_1_1 \
88
// RUN: -disable-llvm-passes -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-V1_1
9+
// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-library -ast-dump \
10+
// RUN: -fdx-rootsignature-version=rootsig_1_2 \
11+
// RUN: -disable-llvm-passes -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-V1_2
912

1013
// This test ensures that the sample root signature is parsed without error and
1114
// the Attr AST Node is created succesfully. If an invalid root signature was
@@ -31,6 +34,7 @@
3134
// CHECK: -HLSLRootSignatureDecl 0x{{.*}} {{.*}} implicit [[SAMPLE_RS_DECL:__hlsl_rootsig_decl_\d*]]
3235
// CHECK-V1_0: version: 1.0,
3336
// CHECK-V1_1: version: 1.1,
37+
// CHECK-V1_2: version: 1.2,
3438
// CHECK-SAME: RootElements{
3539
// CHECK-SAME: RootFlags(AllowInputAssemblerInputLayout | DenyVertexShaderRootAccess),
3640
// CHECK-SAME: RootCBV(b0,
@@ -62,6 +66,7 @@
6266
// CHECK-SAME: s0, numDescriptors = 4, space = 1, offset = DescriptorTableOffsetAppend,
6367
// CHECK-V1_0-SAME: flags = DescriptorsVolatile
6468
// CHECK-V1_1-SAME: flags = None
69+
// CHECK-V1_2-SAME: flags = None
6570
// CHECK-SAME: ),
6671
// CHECK-SAME: DescriptorTable(
6772
// CHECK-SAME: numClauses = 1, visibility = All
@@ -73,6 +78,7 @@
7378
// CHECK-SAME: s1, filter = Anisotropic, addressU = Wrap, addressV = Wrap, addressW = Wrap,
7479
// CHECK-SAME: mipLODBias = 0.000000e+00, maxAnisotropy = 16, comparisonFunc = LessEqual,
7580
// CHECK-SAME: borderColor = OpaqueWhite, minLOD = 0.000000e+00, maxLOD = 3.402823e+38, space = 0, visibility = All
81+
// CHECK-SAME: flags = None
7682
// CHECK-SAME: )}
7783

7884
// CHECK: -RootSignatureAttr 0x{{.*}} {{.*}} [[SAMPLE_RS_DECL]]
@@ -131,3 +137,24 @@ void same_rs_string_main() {}
131137
// CHECK: -RootSignatureAttr 0x{{.*}} {{.*}} [[DIFF_RS_DECL]]
132138
[RootSignature(SampleDifferentRS)]
133139
void different_rs_string_main() {}
140+
141+
#define SampleStaticSamplerRS \
142+
"StaticSampler(s0, flags = NON_NORMALIZED_COORDINATES)"
143+
144+
// Ensure that static samplers flags are correctly parsed in different versions
145+
146+
// CHECK: -HLSLRootSignatureDecl 0x{{.*}} {{.*}} implicit [[DIFF_RS_DECL:__hlsl_rootsig_decl_\d*]]
147+
// CHECK-V1_0: version: 1.0,
148+
// CHECK-V1_1: version: 1.1,
149+
// CHECK-V1_2: version: 1.2,
150+
// CHECK-SAME: RootElements{
151+
// CHECK-SAME: StaticSampler(
152+
// CHECK-SAME: s0, filter = Anisotropic, addressU = Wrap, addressV = Wrap, addressW = Wrap,
153+
// CHECK-SAME: mipLODBias = 0.000000e+00, maxAnisotropy = 16, comparisonFunc = LessEqual,
154+
// CHECK-SAME: borderColor = OpaqueWhite, minLOD = 0.000000e+00, maxLOD = 3.402823e+38, space = 0, visibility = All
155+
// CHECK-SAME: flags = NonNormalizedCoordinates
156+
// CHECK-SAME: )}
157+
158+
// CHECK: -RootSignatureAttr 0x{{.*}} {{.*}} [[DIFF_RS_DECL]]
159+
[RootSignature(SampleStaticSamplerRS)]
160+
void statoc_sampler_v12_main() {}

clang/test/CodeGenHLSL/RootSignature.hlsl

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -82,8 +82,8 @@ void RootDescriptorsEntry() {}
8282
// checking minLOD, maxLOD
8383
// CHECK-SAME: float -1.280000e+02, float 1.280000e+02,
8484

85-
// checking register, space, visibility and flags
86-
// CHECK-SAME: i32 42, i32 0, i32 0, i32 0}
85+
// checking register, space, visibility and flag
86+
// CHECK-SAME: i32 42, i32 0, i32 0, i32 1}
8787

8888
#define SampleStaticSampler \
8989
"StaticSampler(s42, " \
@@ -96,6 +96,7 @@ void RootDescriptorsEntry() {}
9696
" borderColor = STATIC_BORDER_COLOR_OPAQUE_WHITE, " \
9797
" minLOD = -128.f, maxLOD = 128.f, " \
9898
" space = 0, visibility = SHADER_VISIBILITY_ALL, " \
99+
" flags = UINT_BORDER_COLOR" \
99100
")"
100101
[shader("compute"), RootSignature(SampleStaticSampler)]
101102
[numthreads(1,1,1)]

0 commit comments

Comments
 (0)