HLSL: cbuffer and tbuffer grammar and production.
This commit is contained in:
parent
b8d2a006d1
commit
3d157c510f
153
Test/baseResults/hlsl.buffer.frag.out
Executable file
153
Test/baseResults/hlsl.buffer.frag.out
Executable file
@ -0,0 +1,153 @@
|
|||||||
|
hlsl.buffer.frag
|
||||||
|
Shader version: 450
|
||||||
|
gl_FragCoord origin is upper left
|
||||||
|
0:? Sequence
|
||||||
|
0:23 Function Definition: PixelShaderFunction(vf4; (global 4-component vector of float)
|
||||||
|
0:20 Function Parameters:
|
||||||
|
0:20 'input' (in 4-component vector of float)
|
||||||
|
0:? Sequence
|
||||||
|
0:21 Branch: Return with expression
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 'input' (in 4-component vector of float)
|
||||||
|
0:21 v1: direct index for structure (layout(column_major std140 ) uniform 4-component vector of float)
|
||||||
|
0:21 'anon@0' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v1})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 v2: direct index for structure (layout(column_major std430 ) buffer 4-component vector of float)
|
||||||
|
0:21 'anon@1' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v2})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:21 v3: direct index for structure (layout(column_major std140 ) uniform 4-component vector of float)
|
||||||
|
0:21 'anon@2' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v3, layout(column_major std140 ) uniform int i3})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:21 v4: direct index for structure (layout(column_major std430 ) buffer 4-component vector of float)
|
||||||
|
0:21 'anon@3' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v4, layout(column_major std430 ) buffer int i4})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:? Linker Objects
|
||||||
|
0:? 'anon@0' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v1})
|
||||||
|
0:? 'anon@1' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v2})
|
||||||
|
0:? 'anon@2' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v3, layout(column_major std140 ) uniform int i3})
|
||||||
|
0:? 'anon@3' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v4, layout(column_major std430 ) buffer int i4})
|
||||||
|
|
||||||
|
|
||||||
|
Linked fragment stage:
|
||||||
|
|
||||||
|
|
||||||
|
Shader version: 450
|
||||||
|
gl_FragCoord origin is upper left
|
||||||
|
0:? Sequence
|
||||||
|
0:23 Function Definition: PixelShaderFunction(vf4; (global 4-component vector of float)
|
||||||
|
0:20 Function Parameters:
|
||||||
|
0:20 'input' (in 4-component vector of float)
|
||||||
|
0:? Sequence
|
||||||
|
0:21 Branch: Return with expression
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 'input' (in 4-component vector of float)
|
||||||
|
0:21 v1: direct index for structure (layout(column_major std140 ) uniform 4-component vector of float)
|
||||||
|
0:21 'anon@0' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v1})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:21 add (temp 4-component vector of float)
|
||||||
|
0:21 v2: direct index for structure (layout(column_major std430 ) buffer 4-component vector of float)
|
||||||
|
0:21 'anon@1' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v2})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:21 v3: direct index for structure (layout(column_major std140 ) uniform 4-component vector of float)
|
||||||
|
0:21 'anon@2' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v3, layout(column_major std140 ) uniform int i3})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:21 v4: direct index for structure (layout(column_major std430 ) buffer 4-component vector of float)
|
||||||
|
0:21 'anon@3' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v4, layout(column_major std430 ) buffer int i4})
|
||||||
|
0:21 Constant:
|
||||||
|
0:21 0 (const uint)
|
||||||
|
0:? Linker Objects
|
||||||
|
0:? 'anon@0' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v1})
|
||||||
|
0:? 'anon@1' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v2})
|
||||||
|
0:? 'anon@2' (layout(column_major std140 ) uniform block{layout(column_major std140 ) uniform 4-component vector of float v3, layout(column_major std140 ) uniform int i3})
|
||||||
|
0:? 'anon@3' (layout(column_major std430 ) buffer block{layout(column_major std430 ) buffer 4-component vector of float v4, layout(column_major std430 ) buffer int i4})
|
||||||
|
|
||||||
|
// Module Version 10000
|
||||||
|
// Generated by (magic number): 80001
|
||||||
|
// Id's are bound by 39
|
||||||
|
|
||||||
|
Capability Shader
|
||||||
|
1: ExtInstImport "GLSL.std.450"
|
||||||
|
MemoryModel Logical GLSL450
|
||||||
|
EntryPoint Fragment 4 "PixelShaderFunction" 9
|
||||||
|
ExecutionMode 4 OriginUpperLeft
|
||||||
|
Source HLSL 450
|
||||||
|
Name 4 "PixelShaderFunction"
|
||||||
|
Name 9 "input"
|
||||||
|
Name 11 ""
|
||||||
|
MemberName 11 0 "v1"
|
||||||
|
Name 13 ""
|
||||||
|
Name 20 ""
|
||||||
|
MemberName 20 0 "v2"
|
||||||
|
Name 22 ""
|
||||||
|
Name 25 ""
|
||||||
|
MemberName 25 0 "v3"
|
||||||
|
MemberName 25 1 "i3"
|
||||||
|
Name 27 ""
|
||||||
|
Name 32 ""
|
||||||
|
MemberName 32 0 "v4"
|
||||||
|
MemberName 32 1 "i4"
|
||||||
|
Name 34 ""
|
||||||
|
MemberDecorate 11 0 Offset 0
|
||||||
|
Decorate 11 Block
|
||||||
|
Decorate 13 DescriptorSet 0
|
||||||
|
MemberDecorate 20 0 Offset 0
|
||||||
|
Decorate 20 BufferBlock
|
||||||
|
Decorate 22 DescriptorSet 0
|
||||||
|
MemberDecorate 25 0 Offset 0
|
||||||
|
MemberDecorate 25 1 Offset 16
|
||||||
|
Decorate 25 Block
|
||||||
|
Decorate 27 DescriptorSet 0
|
||||||
|
MemberDecorate 32 0 Offset 0
|
||||||
|
MemberDecorate 32 1 Offset 16
|
||||||
|
Decorate 32 BufferBlock
|
||||||
|
Decorate 34 DescriptorSet 0
|
||||||
|
2: TypeVoid
|
||||||
|
3: TypeFunction 2
|
||||||
|
6: TypeFloat 32
|
||||||
|
7: TypeVector 6(float) 4
|
||||||
|
8: TypePointer Input 7(fvec4)
|
||||||
|
9(input): 8(ptr) Variable Input
|
||||||
|
11: TypeStruct 7(fvec4)
|
||||||
|
12: TypePointer Uniform 11(struct)
|
||||||
|
13: 12(ptr) Variable Uniform
|
||||||
|
14: TypeInt 32 1
|
||||||
|
15: 14(int) Constant 0
|
||||||
|
16: TypePointer Uniform 7(fvec4)
|
||||||
|
20: TypeStruct 7(fvec4)
|
||||||
|
21: TypePointer Uniform 20(struct)
|
||||||
|
22: 21(ptr) Variable Uniform
|
||||||
|
25: TypeStruct 7(fvec4) 14(int)
|
||||||
|
26: TypePointer Uniform 25(struct)
|
||||||
|
27: 26(ptr) Variable Uniform
|
||||||
|
32: TypeStruct 7(fvec4) 14(int)
|
||||||
|
33: TypePointer Uniform 32(struct)
|
||||||
|
34: 33(ptr) Variable Uniform
|
||||||
|
4(PixelShaderFunction): 2 Function None 3
|
||||||
|
5: Label
|
||||||
|
10: 7(fvec4) Load 9(input)
|
||||||
|
17: 16(ptr) AccessChain 13 15
|
||||||
|
18: 7(fvec4) Load 17
|
||||||
|
19: 7(fvec4) FAdd 10 18
|
||||||
|
23: 16(ptr) AccessChain 22 15
|
||||||
|
24: 7(fvec4) Load 23
|
||||||
|
28: 16(ptr) AccessChain 27 15
|
||||||
|
29: 7(fvec4) Load 28
|
||||||
|
30: 7(fvec4) FAdd 24 29
|
||||||
|
31: 7(fvec4) FAdd 19 30
|
||||||
|
35: 16(ptr) AccessChain 34 15
|
||||||
|
36: 7(fvec4) Load 35
|
||||||
|
37: 7(fvec4) FAdd 31 36
|
||||||
|
ReturnValue 37
|
||||||
|
FunctionEnd
|
22
Test/hlsl.buffer.frag
Normal file
22
Test/hlsl.buffer.frag
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
cbuffer {
|
||||||
|
float4 v1;
|
||||||
|
};
|
||||||
|
|
||||||
|
tbuffer {
|
||||||
|
float4 v2;
|
||||||
|
};
|
||||||
|
|
||||||
|
cbuffer cbufName : register(b2) {
|
||||||
|
float4 v3;
|
||||||
|
int i3 : packoffset(c1.y);
|
||||||
|
};
|
||||||
|
|
||||||
|
tbuffer tbufName : register(b8) {
|
||||||
|
float4 v4 : packoffset(c1);
|
||||||
|
int i4 : packoffset(c3);
|
||||||
|
};
|
||||||
|
|
||||||
|
float4 PixelShaderFunction(float4 input) : COLOR0
|
||||||
|
{
|
||||||
|
return input + v1 + v2 + v3 + v4;
|
||||||
|
}
|
@ -2,5 +2,5 @@
|
|||||||
// For the version, it uses the latest git tag followed by the number of commits.
|
// For the version, it uses the latest git tag followed by the number of commits.
|
||||||
// For the date, it uses the current date (when then script is run).
|
// For the date, it uses the current date (when then script is run).
|
||||||
|
|
||||||
#define GLSLANG_REVISION "SPIRV99.1332"
|
#define GLSLANG_REVISION "SPIRV99.1337"
|
||||||
#define GLSLANG_DATE "21-Jul-2016"
|
#define GLSLANG_DATE "25-Jul-2016"
|
||||||
|
@ -75,6 +75,7 @@ INSTANTIATE_TEST_CASE_P(
|
|||||||
{"hlsl.array.frag", "PixelShaderFunction"},
|
{"hlsl.array.frag", "PixelShaderFunction"},
|
||||||
{"hlsl.assoc.frag", "PixelShaderFunction"},
|
{"hlsl.assoc.frag", "PixelShaderFunction"},
|
||||||
{"hlsl.attribute.frag", "PixelShaderFunction"},
|
{"hlsl.attribute.frag", "PixelShaderFunction"},
|
||||||
|
{"hlsl.buffer.frag", "PixelShaderFunction"},
|
||||||
{"hlsl.cast.frag", "PixelShaderFunction"},
|
{"hlsl.cast.frag", "PixelShaderFunction"},
|
||||||
{"hlsl.discard.frag", "PixelShaderFunction"},
|
{"hlsl.discard.frag", "PixelShaderFunction"},
|
||||||
{"hlsl.doLoop.frag", "PixelShaderFunction"},
|
{"hlsl.doLoop.frag", "PixelShaderFunction"},
|
||||||
|
@ -337,6 +337,8 @@ bool HlslGrammar::acceptDeclaration(TIntermNode*& node)
|
|||||||
|
|
||||||
if (typedefDecl)
|
if (typedefDecl)
|
||||||
parseContext.declareTypedef(idToken.loc, *idToken.string, type, arraySizes);
|
parseContext.declareTypedef(idToken.loc, *idToken.string, type, arraySizes);
|
||||||
|
else if (type.getBasicType() == EbtBlock)
|
||||||
|
parseContext.declareBlock(idToken.loc, type, idToken.string);
|
||||||
else {
|
else {
|
||||||
// Declare the variable and add any initializer code to the AST.
|
// Declare the variable and add any initializer code to the AST.
|
||||||
// The top-level node is always made into an aggregate, as that's
|
// The top-level node is always made into an aggregate, as that's
|
||||||
@ -414,10 +416,18 @@ bool HlslGrammar::acceptFullySpecifiedType(TType& type)
|
|||||||
TQualifier qualifier;
|
TQualifier qualifier;
|
||||||
qualifier.clear();
|
qualifier.clear();
|
||||||
acceptQualifier(qualifier);
|
acceptQualifier(qualifier);
|
||||||
|
TSourceLoc loc = token.loc;
|
||||||
|
|
||||||
// type_specifier
|
// type_specifier
|
||||||
if (! acceptType(type))
|
if (! acceptType(type))
|
||||||
return false;
|
return false;
|
||||||
|
if (type.getBasicType() == EbtBlock) {
|
||||||
|
// the type was a block, which set some parts of the qualifier
|
||||||
|
parseContext.mergeQualifiers(loc, type.getQualifier(), qualifier, true);
|
||||||
|
// further, it can create an anonymous instance of the block
|
||||||
|
if (peekTokenClass(EHTokSemicolon))
|
||||||
|
parseContext.declareBlock(loc, type);
|
||||||
|
} else
|
||||||
type.getQualifier() = qualifier;
|
type.getQualifier() = qualifier;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
@ -825,6 +835,8 @@ bool HlslGrammar::acceptType(TType& type)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case EHTokStruct:
|
case EHTokStruct:
|
||||||
|
case EHTokCBuffer:
|
||||||
|
case EHTokTBuffer:
|
||||||
return acceptStruct(type);
|
return acceptStruct(type);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1186,13 +1198,29 @@ bool HlslGrammar::acceptType(TType& type)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// struct
|
// struct
|
||||||
// : STRUCT IDENTIFIER LEFT_BRACE struct_declaration_list RIGHT_BRACE
|
// : struct_type IDENTIFIER post_decls LEFT_BRACE struct_declaration_list RIGHT_BRACE
|
||||||
// | STRUCT LEFT_BRACE struct_declaration_list RIGHT_BRACE
|
// | struct_type post_decls LEFT_BRACE struct_declaration_list RIGHT_BRACE
|
||||||
|
//
|
||||||
|
// struct_type
|
||||||
|
// : STRUCT
|
||||||
|
// | CBUFFER
|
||||||
|
// | TBUFFER
|
||||||
//
|
//
|
||||||
bool HlslGrammar::acceptStruct(TType& type)
|
bool HlslGrammar::acceptStruct(TType& type)
|
||||||
{
|
{
|
||||||
|
// This qualifier.storage will tell us whether it's an AST block or
|
||||||
|
// just a struct.
|
||||||
|
TQualifier qualifier;
|
||||||
|
qualifier.clear();
|
||||||
|
|
||||||
|
// CBUFFER
|
||||||
|
if (acceptTokenClass(EHTokCBuffer))
|
||||||
|
qualifier.storage = EvqUniform;
|
||||||
|
// TBUFFER
|
||||||
|
else if (acceptTokenClass(EHTokTBuffer))
|
||||||
|
qualifier.storage = EvqBuffer;
|
||||||
// STRUCT
|
// STRUCT
|
||||||
if (! acceptTokenClass(EHTokStruct))
|
else if (! acceptTokenClass(EHTokStruct))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// IDENTIFIER
|
// IDENTIFIER
|
||||||
@ -1202,6 +1230,9 @@ bool HlslGrammar::acceptStruct(TType& type)
|
|||||||
advanceToken();
|
advanceToken();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// post_decls
|
||||||
|
acceptPostDecls(type);
|
||||||
|
|
||||||
// LEFT_BRACE
|
// LEFT_BRACE
|
||||||
if (! acceptTokenClass(EHTokLeftBrace)) {
|
if (! acceptTokenClass(EHTokLeftBrace)) {
|
||||||
expected("{");
|
expected("{");
|
||||||
@ -1222,11 +1253,15 @@ bool HlslGrammar::acceptStruct(TType& type)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// create the user-defined type
|
// create the user-defined type
|
||||||
|
if (qualifier.storage == EvqTemporary)
|
||||||
new(&type) TType(typeList, structName);
|
new(&type) TType(typeList, structName);
|
||||||
|
else
|
||||||
|
new(&type) TType(typeList, structName, qualifier); // sets EbtBlock
|
||||||
|
|
||||||
// If it was named, which means it can be reused later, add
|
// If it was named, which means the type can be reused later, add
|
||||||
// it to the symbol table.
|
// it to the symbol table. (Unless it's a block, in which
|
||||||
if (structName.size() > 0) {
|
// case the name is not a type.)
|
||||||
|
if (type.getBasicType() != EbtBlock && structName.size() > 0) {
|
||||||
TVariable* userTypeDef = new TVariable(&structName, type, true);
|
TVariable* userTypeDef = new TVariable(&structName, type, true);
|
||||||
if (! parseContext.symbolTable.insert(*userTypeDef))
|
if (! parseContext.symbolTable.insert(*userTypeDef))
|
||||||
parseContext.error(token.loc, "redefinition", structName.c_str(), "struct");
|
parseContext.error(token.loc, "redefinition", structName.c_str(), "struct");
|
||||||
@ -2442,6 +2477,7 @@ void HlslGrammar::acceptPostDecls(TType& type)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// TODO: process the packoffset information
|
// TODO: process the packoffset information
|
||||||
|
// c1.y means component y of location slot 1
|
||||||
} else if (! acceptIdentifier(idToken)) {
|
} else if (! acceptIdentifier(idToken)) {
|
||||||
expected("semantic or packoffset or register");
|
expected("semantic or packoffset or register");
|
||||||
return;
|
return;
|
||||||
@ -2462,6 +2498,7 @@ void HlslGrammar::acceptPostDecls(TType& type)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// TODO: process the register information
|
// TODO: process the register information
|
||||||
|
// b2 means buffer 2
|
||||||
} else {
|
} else {
|
||||||
// semantic, in idToken.string
|
// semantic, in idToken.string
|
||||||
parseContext.handleSemantic(type, *idToken.string);
|
parseContext.handleSemantic(type, *idToken.string);
|
||||||
|
@ -3898,28 +3898,31 @@ TIntermTyped* HlslParseContext::constructAggregate(TIntermNode* node, const TTyp
|
|||||||
//
|
//
|
||||||
// Do everything needed to add an interface block.
|
// Do everything needed to add an interface block.
|
||||||
//
|
//
|
||||||
void HlslParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList, const TString* instanceName, TArraySizes* arraySizes)
|
void HlslParseContext::declareBlock(const TSourceLoc& loc, TType& type, const TString* instanceName, TArraySizes* arraySizes)
|
||||||
{
|
{
|
||||||
|
assert(type.getWritableStruct() != nullptr);
|
||||||
|
|
||||||
|
TTypeList& typeList = *type.getWritableStruct();
|
||||||
// fix and check for member storage qualifiers and types that don't belong within a block
|
// fix and check for member storage qualifiers and types that don't belong within a block
|
||||||
for (unsigned int member = 0; member < typeList.size(); ++member) {
|
for (unsigned int member = 0; member < typeList.size(); ++member) {
|
||||||
TType& memberType = *typeList[member].type;
|
TType& memberType = *typeList[member].type;
|
||||||
TQualifier& memberQualifier = memberType.getQualifier();
|
TQualifier& memberQualifier = memberType.getQualifier();
|
||||||
const TSourceLoc& memberLoc = typeList[member].loc;
|
const TSourceLoc& memberLoc = typeList[member].loc;
|
||||||
globalQualifierFix(memberLoc, memberQualifier);
|
globalQualifierFix(memberLoc, memberQualifier);
|
||||||
memberQualifier.storage = currentBlockQualifier.storage;
|
memberQualifier.storage = type.getQualifier().storage;
|
||||||
}
|
}
|
||||||
|
|
||||||
// This might be a redeclaration of a built-in block. If so, redeclareBuiltinBlock() will
|
// This might be a redeclaration of a built-in block. If so, redeclareBuiltinBlock() will
|
||||||
// do all the rest.
|
// do all the rest.
|
||||||
if (! symbolTable.atBuiltInLevel() && builtInName(*blockName)) {
|
//if (! symbolTable.atBuiltInLevel() && builtInName(*blockName)) {
|
||||||
redeclareBuiltinBlock(loc, typeList, *blockName, instanceName, arraySizes);
|
// redeclareBuiltinBlock(loc, typeList, *blockName, instanceName, arraySizes);
|
||||||
return;
|
// return;
|
||||||
}
|
//}
|
||||||
|
|
||||||
// Make default block qualification, and adjust the member qualifications
|
// Make default block qualification, and adjust the member qualifications
|
||||||
|
|
||||||
TQualifier defaultQualification;
|
TQualifier defaultQualification;
|
||||||
switch (currentBlockQualifier.storage) {
|
switch (type.getQualifier().storage) {
|
||||||
case EvqUniform: defaultQualification = globalUniformDefaults; break;
|
case EvqUniform: defaultQualification = globalUniformDefaults; break;
|
||||||
case EvqBuffer: defaultQualification = globalBufferDefaults; break;
|
case EvqBuffer: defaultQualification = globalBufferDefaults; break;
|
||||||
case EvqVaryingIn: defaultQualification = globalInputDefaults; break;
|
case EvqVaryingIn: defaultQualification = globalInputDefaults; break;
|
||||||
@ -3929,12 +3932,12 @@ void HlslParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList,
|
|||||||
|
|
||||||
// Special case for "push_constant uniform", which has a default of std430,
|
// Special case for "push_constant uniform", which has a default of std430,
|
||||||
// contrary to normal uniform defaults, and can't have a default tracked for it.
|
// contrary to normal uniform defaults, and can't have a default tracked for it.
|
||||||
if (currentBlockQualifier.layoutPushConstant && ! currentBlockQualifier.hasPacking())
|
if (type.getQualifier().layoutPushConstant && ! type.getQualifier().hasPacking())
|
||||||
currentBlockQualifier.layoutPacking = ElpStd430;
|
type.getQualifier().layoutPacking = ElpStd430;
|
||||||
|
|
||||||
// fix and check for member layout qualifiers
|
// fix and check for member layout qualifiers
|
||||||
|
|
||||||
mergeObjectLayoutQualifiers(defaultQualification, currentBlockQualifier, true);
|
mergeObjectLayoutQualifiers(defaultQualification, type.getQualifier(), true);
|
||||||
|
|
||||||
bool memberWithLocation = false;
|
bool memberWithLocation = false;
|
||||||
bool memberWithoutLocation = false;
|
bool memberWithoutLocation = false;
|
||||||
@ -3958,7 +3961,7 @@ void HlslParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList,
|
|||||||
if (memberQualifier.hasPacking())
|
if (memberQualifier.hasPacking())
|
||||||
error(memberLoc, "member of block cannot have a packing layout qualifier", typeList[member].type->getFieldName().c_str(), "");
|
error(memberLoc, "member of block cannot have a packing layout qualifier", typeList[member].type->getFieldName().c_str(), "");
|
||||||
if (memberQualifier.hasLocation()) {
|
if (memberQualifier.hasLocation()) {
|
||||||
switch (currentBlockQualifier.storage) {
|
switch (type.getQualifier().storage) {
|
||||||
case EvqVaryingIn:
|
case EvqVaryingIn:
|
||||||
case EvqVaryingOut:
|
case EvqVaryingOut:
|
||||||
memberWithLocation = true;
|
memberWithLocation = true;
|
||||||
@ -3979,19 +3982,20 @@ void HlslParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList,
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Process the members
|
// Process the members
|
||||||
fixBlockLocations(loc, currentBlockQualifier, typeList, memberWithLocation, memberWithoutLocation);
|
fixBlockLocations(loc, type.getQualifier(), typeList, memberWithLocation, memberWithoutLocation);
|
||||||
fixBlockXfbOffsets(currentBlockQualifier, typeList);
|
fixBlockXfbOffsets(type.getQualifier(), typeList);
|
||||||
fixBlockUniformOffsets(currentBlockQualifier, typeList);
|
fixBlockUniformOffsets(type.getQualifier(), typeList);
|
||||||
|
|
||||||
// reverse merge, so that currentBlockQualifier now has all layout information
|
// reverse merge, so that currentBlockQualifier now has all layout information
|
||||||
// (can't use defaultQualification directly, it's missing other non-layout-default-class qualifiers)
|
// (can't use defaultQualification directly, it's missing other non-layout-default-class qualifiers)
|
||||||
mergeObjectLayoutQualifiers(currentBlockQualifier, defaultQualification, true);
|
mergeObjectLayoutQualifiers(type.getQualifier(), defaultQualification, true);
|
||||||
|
|
||||||
//
|
//
|
||||||
// Build and add the interface block as a new type named 'blockName'
|
// Build and add the interface block as a new type named 'blockName'
|
||||||
//
|
//
|
||||||
|
|
||||||
TType blockType(&typeList, *blockName, currentBlockQualifier);
|
//?? need the block name to be a typename?
|
||||||
|
TType blockType(&typeList, "" /* *blockName */, type.getQualifier());
|
||||||
if (arraySizes)
|
if (arraySizes)
|
||||||
blockType.newArraySizes(*arraySizes);
|
blockType.newArraySizes(*arraySizes);
|
||||||
|
|
||||||
@ -4008,20 +4012,20 @@ void HlslParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList,
|
|||||||
// whose type is EbtBlock, but without all the structure; that will come from the type
|
// whose type is EbtBlock, but without all the structure; that will come from the type
|
||||||
// the instances point to.
|
// the instances point to.
|
||||||
//
|
//
|
||||||
TType blockNameType(EbtBlock, blockType.getQualifier().storage);
|
//??TType blockNameType(EbtBlock, blockType.getQualifier().storage);
|
||||||
TVariable* blockNameVar = new TVariable(blockName, blockNameType);
|
//??TVariable* blockNameVar = new TVariable(blockName, blockNameType);
|
||||||
if (! symbolTable.insert(*blockNameVar)) {
|
//if (! symbolTable.insert(*blockNameVar)) {
|
||||||
TSymbol* existingName = symbolTable.find(*blockName);
|
// TSymbol* existingName = symbolTable.find(*blockName);
|
||||||
if (existingName->getType().getBasicType() == EbtBlock) {
|
// if (existingName->getType().getBasicType() == EbtBlock) {
|
||||||
if (existingName->getType().getQualifier().storage == blockType.getQualifier().storage) {
|
// if (existingName->getType().getQualifier().storage == blockType.getQualifier().storage) {
|
||||||
error(loc, "Cannot reuse block name within the same interface:", blockName->c_str(), blockType.getStorageQualifierString());
|
// error(loc, "Cannot reuse block name within the same interface:", blockName->c_str(), blockType.getStorageQualifierString());
|
||||||
return;
|
// return;
|
||||||
}
|
// }
|
||||||
} else {
|
// } else {
|
||||||
error(loc, "block name cannot redefine a non-block name", blockName->c_str(), "");
|
// error(loc, "block name cannot redefine a non-block name", blockName->c_str(), "");
|
||||||
return;
|
// return;
|
||||||
}
|
// }
|
||||||
}
|
//}
|
||||||
|
|
||||||
// Add the variable, as anonymous or named instanceName.
|
// Add the variable, as anonymous or named instanceName.
|
||||||
// Make an anonymous variable if no name was provided.
|
// Make an anonymous variable if no name was provided.
|
||||||
@ -4031,7 +4035,7 @@ void HlslParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList,
|
|||||||
TVariable& variable = *new TVariable(instanceName, blockType);
|
TVariable& variable = *new TVariable(instanceName, blockType);
|
||||||
if (! symbolTable.insert(variable)) {
|
if (! symbolTable.insert(variable)) {
|
||||||
if (*instanceName == "")
|
if (*instanceName == "")
|
||||||
error(loc, "nameless block contains a member that already has a name at global scope", blockName->c_str(), "");
|
error(loc, "nameless block contains a member that already has a name at global scope", "" /* blockName->c_str() */, "");
|
||||||
else
|
else
|
||||||
error(loc, "block instance name redefinition", variable.getName().c_str(), "");
|
error(loc, "block instance name redefinition", variable.getName().c_str(), "");
|
||||||
|
|
||||||
|
@ -133,7 +133,7 @@ public:
|
|||||||
TIntermTyped* addConstructor(const TSourceLoc&, TIntermNode*, const TType&, TOperator);
|
TIntermTyped* addConstructor(const TSourceLoc&, TIntermNode*, const TType&, TOperator);
|
||||||
TIntermTyped* constructAggregate(TIntermNode*, const TType&, int, const TSourceLoc&);
|
TIntermTyped* constructAggregate(TIntermNode*, const TType&, int, const TSourceLoc&);
|
||||||
TIntermTyped* constructBuiltIn(const TType&, TOperator, TIntermTyped*, const TSourceLoc&, bool subset);
|
TIntermTyped* constructBuiltIn(const TType&, TOperator, TIntermTyped*, const TSourceLoc&, bool subset);
|
||||||
void declareBlock(const TSourceLoc&, TTypeList& typeList, const TString* instanceName = 0, TArraySizes* arraySizes = 0);
|
void declareBlock(const TSourceLoc&, TType&, const TString* instanceName = 0, TArraySizes* arraySizes = 0);
|
||||||
void fixBlockLocations(const TSourceLoc&, TQualifier&, TTypeList&, bool memberWithLocation, bool memberWithoutLocation);
|
void fixBlockLocations(const TSourceLoc&, TQualifier&, TTypeList&, bool memberWithLocation, bool memberWithoutLocation);
|
||||||
void fixBlockXfbOffsets(TQualifier&, TTypeList&);
|
void fixBlockXfbOffsets(TQualifier&, TTypeList&);
|
||||||
void fixBlockUniformOffsets(TQualifier&, TTypeList&);
|
void fixBlockUniformOffsets(TQualifier&, TTypeList&);
|
||||||
@ -176,8 +176,6 @@ protected:
|
|||||||
bool postMainReturn; // if inside a function, true if the function is the entry point and this is after a return statement
|
bool postMainReturn; // if inside a function, true if the function is the entry point and this is after a return statement
|
||||||
const TType* currentFunctionType; // the return type of the function that's currently being parsed
|
const TType* currentFunctionType; // the return type of the function that's currently being parsed
|
||||||
bool functionReturnsValue; // true if a non-void function has a return
|
bool functionReturnsValue; // true if a non-void function has a return
|
||||||
const TString* blockName;
|
|
||||||
TQualifier currentBlockQualifier;
|
|
||||||
TBuiltInResource resources;
|
TBuiltInResource resources;
|
||||||
TLimits& limits;
|
TLimits& limits;
|
||||||
|
|
||||||
|
@ -258,6 +258,8 @@ void HlslScanContext::fillInKeywordMap()
|
|||||||
(*KeywordMap)["Texture2DMSArray"] = EHTokTexture2DMSarray;
|
(*KeywordMap)["Texture2DMSArray"] = EHTokTexture2DMSarray;
|
||||||
|
|
||||||
(*KeywordMap)["struct"] = EHTokStruct;
|
(*KeywordMap)["struct"] = EHTokStruct;
|
||||||
|
(*KeywordMap)["cbuffer"] = EHTokCBuffer;
|
||||||
|
(*KeywordMap)["tbuffer"] = EHTokTBuffer;
|
||||||
(*KeywordMap)["typedef"] = EHTokTypedef;
|
(*KeywordMap)["typedef"] = EHTokTypedef;
|
||||||
|
|
||||||
(*KeywordMap)["true"] = EHTokBoolConstant;
|
(*KeywordMap)["true"] = EHTokBoolConstant;
|
||||||
@ -574,6 +576,9 @@ EHlslTokenClass HlslScanContext::tokenizeIdentifier()
|
|||||||
// variable, user type, ...
|
// variable, user type, ...
|
||||||
case EHTokStruct:
|
case EHTokStruct:
|
||||||
case EHTokTypedef:
|
case EHTokTypedef:
|
||||||
|
case EHTokCBuffer:
|
||||||
|
case EHTokTBuffer:
|
||||||
|
return keyword;
|
||||||
|
|
||||||
case EHTokBoolConstant:
|
case EHTokBoolConstant:
|
||||||
if (strcmp("true", tokenText) == 0)
|
if (strcmp("true", tokenText) == 0)
|
||||||
|
@ -212,6 +212,8 @@ enum EHlslTokenClass {
|
|||||||
EHTokIdentifier,
|
EHTokIdentifier,
|
||||||
EHTokTypeName,
|
EHTokTypeName,
|
||||||
EHTokStruct,
|
EHTokStruct,
|
||||||
|
EHTokCBuffer,
|
||||||
|
EHTokTBuffer,
|
||||||
EHTokTypedef,
|
EHTokTypedef,
|
||||||
|
|
||||||
// constant
|
// constant
|
||||||
|
Loading…
x
Reference in New Issue
Block a user