Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
G
glslang
Project
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Chen Yisong
glslang
Commits
e0b6cad4
Commit
e0b6cad4
authored
Dec 24, 2015
by
John Kessenich
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
SPV: Generalize multiple struct-type instances for interpolation/invariant qualifiers.
parent
69d01ead
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
108 additions
and
50 deletions
+108
-50
GlslangToSpv.cpp
SPIRV/GlslangToSpv.cpp
+70
-38
spv.layoutNested.vert.out
Test/baseResults/spv.layoutNested.vert.out
+32
-9
spv.layoutNested.vert
Test/spv.layoutNested.vert
+4
-1
revision.h
glslang/Include/revision.h
+2
-2
No files found.
SPIRV/GlslangToSpv.cpp
View file @
e0b6cad4
...
...
@@ -91,7 +91,7 @@ protected:
spv
::
Id
createSpvVariable
(
const
glslang
::
TIntermSymbol
*
);
spv
::
Id
getSampledType
(
const
glslang
::
TSampler
&
);
spv
::
Id
convertGlslangToSpvType
(
const
glslang
::
TType
&
type
);
spv
::
Id
convertGlslangToSpvType
(
const
glslang
::
TType
&
type
,
glslang
::
TLayoutPacking
,
glslang
::
TLayoutMatrix
);
spv
::
Id
convertGlslangToSpvType
(
const
glslang
::
TType
&
type
,
glslang
::
TLayoutPacking
,
const
glslang
::
TQualifier
&
);
glslang
::
TLayoutPacking
getExplicitLayout
(
const
glslang
::
TType
&
type
)
const
;
int
getArrayStride
(
const
glslang
::
TType
&
arrayType
,
glslang
::
TLayoutPacking
,
glslang
::
TLayoutMatrix
);
int
getMatrixStride
(
const
glslang
::
TType
&
matrixType
,
glslang
::
TLayoutPacking
,
glslang
::
TLayoutMatrix
);
...
...
@@ -299,30 +299,30 @@ spv::Decoration TranslateLayoutDecoration(const glslang::TType& type, glslang::T
// Translate glslang type to SPIR-V interpolation decorations.
// Returns spv::Decoration(spv::BadValue) when no decoration
// should be applied.
spv
::
Decoration
TranslateInterpolationDecoration
(
const
glslang
::
T
Type
&
type
)
spv
::
Decoration
TranslateInterpolationDecoration
(
const
glslang
::
T
Qualifier
&
qualifier
)
{
if
(
type
.
getQualifier
()
.
smooth
)
{
if
(
qualifier
.
smooth
)
{
// Smooth decoration doesn't exist in SPIR-V 1.0
return
(
spv
::
Decoration
)
spv
::
BadValue
;
}
if
(
type
.
getQualifier
()
.
nopersp
)
if
(
qualifier
.
nopersp
)
return
spv
::
DecorationNoPerspective
;
else
if
(
type
.
getQualifier
()
.
patch
)
else
if
(
qualifier
.
patch
)
return
spv
::
DecorationPatch
;
else
if
(
type
.
getQualifier
()
.
flat
)
else
if
(
qualifier
.
flat
)
return
spv
::
DecorationFlat
;
else
if
(
type
.
getQualifier
()
.
centroid
)
else
if
(
qualifier
.
centroid
)
return
spv
::
DecorationCentroid
;
else
if
(
type
.
getQualifier
()
.
sample
)
else
if
(
qualifier
.
sample
)
return
spv
::
DecorationSample
;
else
return
(
spv
::
Decoration
)
spv
::
BadValue
;
}
// If glslang type is invaraiant, return SPIR-V invariant decoration.
spv
::
Decoration
TranslateInvariantDecoration
(
const
glslang
::
T
Type
&
type
)
spv
::
Decoration
TranslateInvariantDecoration
(
const
glslang
::
T
Qualifier
&
qualifier
)
{
if
(
type
.
getQualifier
()
.
invariant
)
if
(
qualifier
.
invariant
)
return
spv
::
DecorationInvariant
;
else
return
(
spv
::
Decoration
)
spv
::
BadValue
;
...
...
@@ -420,6 +420,34 @@ spv::ImageFormat TranslateImageFormat(const glslang::TType& type)
}
}
void
InheritQualifiers
(
glslang
::
TQualifier
&
child
,
const
glslang
::
TQualifier
&
parent
)
{
if
(
child
.
layoutMatrix
==
glslang
::
ElmNone
)
child
.
layoutMatrix
=
parent
.
layoutMatrix
;
if
(
parent
.
invariant
)
child
.
invariant
=
true
;
if
(
parent
.
nopersp
)
child
.
nopersp
=
true
;
if
(
parent
.
flat
)
child
.
flat
=
true
;
if
(
parent
.
centroid
)
child
.
centroid
=
true
;
if
(
parent
.
patch
)
child
.
patch
=
true
;
if
(
parent
.
sample
)
child
.
sample
=
true
;
}
bool
HasNonLayoutQualifiers
(
const
glslang
::
TQualifier
&
qualifier
)
{
// This should list qualifiers that simultaneous satisify:
// - struct members can inherit from a struct declaration
// - effect decorations on the struct members (note smooth does not, and expecting something like volatile to effect the whole object)
// - are not part of the offset/st430/etc or row/column-major layout
return
qualifier
.
invariant
||
qualifier
.
nopersp
||
qualifier
.
flat
||
qualifier
.
centroid
||
qualifier
.
patch
||
qualifier
.
sample
;
}
//
// Implement the TGlslangToSpvTraverser class.
//
...
...
@@ -1467,14 +1495,14 @@ spv::Id TGlslangToSpvTraverser::getSampledType(const glslang::TSampler& sampler)
// layout state rooted from the top-level type.
spv
::
Id
TGlslangToSpvTraverser
::
convertGlslangToSpvType
(
const
glslang
::
TType
&
type
)
{
return
convertGlslangToSpvType
(
type
,
getExplicitLayout
(
type
),
type
.
getQualifier
()
.
layoutMatrix
);
return
convertGlslangToSpvType
(
type
,
getExplicitLayout
(
type
),
type
.
getQualifier
());
}
// Do full recursive conversion of an arbitrary glslang type to a SPIR-V Id.
// explicitLayout can be kept the same throughout the heirarchical recursive walk.
spv
::
Id
TGlslangToSpvTraverser
::
convertGlslangToSpvType
(
const
glslang
::
TType
&
type
,
glslang
::
TLayoutPacking
explicitLayout
,
glslang
::
TLayoutMatrix
matrixLayout
)
spv
::
Id
TGlslangToSpvTraverser
::
convertGlslangToSpvType
(
const
glslang
::
TType
&
type
,
glslang
::
TLayoutPacking
explicitLayout
,
const
glslang
::
TQualifier
&
qualifier
)
{
spv
::
Id
spvType
=
0
;
spv
::
Id
spvType
=
spv
::
NoResult
;
switch
(
type
.
getBasicType
())
{
case
glslang
:
:
EbtVoid
:
...
...
@@ -1503,13 +1531,13 @@ spv::Id TGlslangToSpvTraverser::convertGlslangToSpvType(const glslang::TType& ty
case
glslang
:
:
EbtSampler
:
{
const
glslang
::
TSampler
&
sampler
=
type
.
getSampler
();
// an image is present, make its type
spvType
=
builder
.
makeImageType
(
getSampledType
(
sampler
),
TranslateDimensionality
(
sampler
),
sampler
.
shadow
,
sampler
.
arrayed
,
sampler
.
ms
,
sampler
.
image
?
2
:
1
,
TranslateImageFormat
(
type
));
// an image is present, make its type
spvType
=
builder
.
makeImageType
(
getSampledType
(
sampler
),
TranslateDimensionality
(
sampler
),
sampler
.
shadow
,
sampler
.
arrayed
,
sampler
.
ms
,
sampler
.
image
?
2
:
1
,
TranslateImageFormat
(
type
));
if
(
!
sampler
.
image
)
{
spvType
=
builder
.
makeSampledImageType
(
spvType
);
}
spvType
=
builder
.
makeSampledImageType
(
spvType
);
}
}
break
;
case
glslang
:
:
EbtStruct
:
case
glslang
:
:
EbtBlock
:
...
...
@@ -1517,8 +1545,12 @@ spv::Id TGlslangToSpvTraverser::convertGlslangToSpvType(const glslang::TType& ty
// If we've seen this struct type, return it
const
glslang
::
TTypeList
*
glslangStruct
=
type
.
getStruct
();
std
::
vector
<
spv
::
Id
>
structFields
;
spvType
=
structMap
[
explicitLayout
][
matrixLayout
][
glslangStruct
];
if
(
spvType
)
// Try to share structs for different layouts, but not yet for other
// kinds of qualification (primarily not yet including interpolant qualification).
if
(
!
HasNonLayoutQualifiers
(
qualifier
))
spvType
=
structMap
[
explicitLayout
][
qualifier
.
layoutMatrix
][
glslangStruct
];
if
(
spvType
!=
spv
::
NoResult
)
break
;
// else, we haven't seen it...
...
...
@@ -1536,16 +1568,17 @@ spv::Id TGlslangToSpvTraverser::convertGlslangToSpvType(const glslang::TType& ty
}
else
{
if
(
type
.
getBasicType
()
==
glslang
::
EbtBlock
)
memberRemapper
[
glslangStruct
][
i
]
=
i
-
memberDelta
;
// modify just th
e children's view of matrix layout, if there is one for this memb
er
glslang
::
T
LayoutMatrix
subMatrixLayout
=
glslangType
.
getQualifier
().
layoutMatrix
;
structFields
.
push_back
(
convertGlslangToSpvType
(
glslangType
,
explicitLayout
,
subMatrixLayout
!=
glslang
::
ElmNone
?
subMatrixLayout
:
matrixLayout
));
// modify just th
is child's view of the qualifi
er
glslang
::
T
Qualifier
subQualifier
=
glslangType
.
getQualifier
()
;
InheritQualifiers
(
subQualifier
,
qualifier
);
structFields
.
push_back
(
convertGlslangToSpvType
(
glslangType
,
explicitLayout
,
subQualifier
));
}
}
// Make the SPIR-V type
spvType
=
builder
.
makeStructType
(
structFields
,
type
.
getTypeName
().
c_str
());
structMap
[
explicitLayout
][
matrixLayout
][
glslangStruct
]
=
spvType
;
if
(
!
HasNonLayoutQualifiers
(
qualifier
))
structMap
[
explicitLayout
][
qualifier
.
layoutMatrix
][
glslangStruct
]
=
spvType
;
// Name and decorate the non-hidden members
int
offset
=
-
1
;
...
...
@@ -1555,18 +1588,17 @@ spv::Id TGlslangToSpvTraverser::convertGlslangToSpvType(const glslang::TType& ty
if
(
type
.
getBasicType
()
==
glslang
::
EbtBlock
)
member
=
memberRemapper
[
glslangStruct
][
i
];
// modify just the children's view of matrix layout, if there is one for this member
glslang
::
TLayoutMatrix
subMatrixLayout
=
glslangType
.
getQualifier
().
layoutMatrix
;
if
(
subMatrixLayout
==
glslang
::
ElmNone
)
subMatrixLayout
=
matrixLayout
;
// modify just this child's view of the qualifier
glslang
::
TQualifier
subQualifier
=
glslangType
.
getQualifier
();
InheritQualifiers
(
subQualifier
,
qualifier
);
// using -1 above to indicate a hidden member
if
(
member
>=
0
)
{
builder
.
addMemberName
(
spvType
,
member
,
glslangType
.
getFieldName
().
c_str
());
addMemberDecoration
(
spvType
,
member
,
TranslateLayoutDecoration
(
glslangType
,
sub
MatrixLayout
));
addMemberDecoration
(
spvType
,
member
,
TranslateLayoutDecoration
(
glslangType
,
sub
Qualifier
.
layoutMatrix
));
addMemberDecoration
(
spvType
,
member
,
TranslatePrecisionDecoration
(
glslangType
));
addMemberDecoration
(
spvType
,
member
,
TranslateInterpolationDecoration
(
glslangType
));
addMemberDecoration
(
spvType
,
member
,
TranslateInvariantDecoration
(
glslangType
));
addMemberDecoration
(
spvType
,
member
,
TranslateInterpolationDecoration
(
subQualifier
));
addMemberDecoration
(
spvType
,
member
,
TranslateInvariantDecoration
(
subQualifier
));
if
(
glslangType
.
getQualifier
().
hasLocation
())
builder
.
addMemberDecoration
(
spvType
,
member
,
spv
::
DecorationLocation
,
glslangType
.
getQualifier
().
layoutLocation
);
if
(
glslangType
.
getQualifier
().
hasComponent
())
...
...
@@ -1576,14 +1608,14 @@ spv::Id TGlslangToSpvTraverser::convertGlslangToSpvType(const glslang::TType& ty
else
if
(
explicitLayout
!=
glslang
::
ElpNone
)
{
// figure out what to do with offset, which is accumulating
int
nextOffset
;
updateMemberOffset
(
type
,
glslangType
,
offset
,
nextOffset
,
explicitLayout
,
sub
MatrixLayout
);
updateMemberOffset
(
type
,
glslangType
,
offset
,
nextOffset
,
explicitLayout
,
sub
Qualifier
.
layoutMatrix
);
if
(
offset
>=
0
)
builder
.
addMemberDecoration
(
spvType
,
member
,
spv
::
DecorationOffset
,
offset
);
offset
=
nextOffset
;
}
if
(
glslangType
.
isMatrix
()
&&
explicitLayout
!=
glslang
::
ElpNone
)
builder
.
addMemberDecoration
(
spvType
,
member
,
spv
::
DecorationMatrixStride
,
getMatrixStride
(
glslangType
,
explicitLayout
,
sub
MatrixLayout
));
builder
.
addMemberDecoration
(
spvType
,
member
,
spv
::
DecorationMatrixStride
,
getMatrixStride
(
glslangType
,
explicitLayout
,
sub
Qualifier
.
layoutMatrix
));
// built-in variable decorations
spv
::
BuiltIn
builtIn
=
TranslateBuiltInDecoration
(
glslangType
.
getQualifier
().
builtIn
);
...
...
@@ -1593,7 +1625,7 @@ spv::Id TGlslangToSpvTraverser::convertGlslangToSpvType(const glslang::TType& ty
}
// Decorate the structure
addDecoration
(
spvType
,
TranslateLayoutDecoration
(
type
,
matrixLayout
));
addDecoration
(
spvType
,
TranslateLayoutDecoration
(
type
,
qualifier
.
layoutMatrix
));
addDecoration
(
spvType
,
TranslateBlockDecoration
(
type
));
if
(
type
.
getQualifier
().
hasStream
())
builder
.
addDecoration
(
spvType
,
spv
::
DecorationStream
,
type
.
getQualifier
().
layoutStream
);
...
...
@@ -1641,7 +1673,7 @@ spv::Id TGlslangToSpvTraverser::convertGlslangToSpvType(const glslang::TType& ty
// except for the very top if it is an array of blocks; that array is
// not laid out in memory in a way needing a stride.
if
(
explicitLayout
&&
type
.
getBasicType
()
!=
glslang
::
EbtBlock
)
builder
.
addDecoration
(
spvType
,
spv
::
DecorationArrayStride
,
getArrayStride
(
type
,
explicitLayout
,
matrixLayout
));
builder
.
addDecoration
(
spvType
,
spv
::
DecorationArrayStride
,
getArrayStride
(
type
,
explicitLayout
,
qualifier
.
layoutMatrix
));
}
return
spvType
;
...
...
@@ -3146,7 +3178,7 @@ spv::Id TGlslangToSpvTraverser::getSymbolId(const glslang::TIntermSymbol* symbol
if
(
!
symbol
->
getType
().
isStruct
())
{
addDecoration
(
id
,
TranslatePrecisionDecoration
(
symbol
->
getType
()));
addDecoration
(
id
,
TranslateInterpolationDecoration
(
symbol
->
getType
()));
addDecoration
(
id
,
TranslateInterpolationDecoration
(
symbol
->
getType
()
.
getQualifier
()
));
if
(
symbol
->
getQualifier
().
hasLocation
())
builder
.
addDecoration
(
id
,
spv
::
DecorationLocation
,
symbol
->
getQualifier
().
layoutLocation
);
if
(
symbol
->
getQualifier
().
hasIndex
())
...
...
@@ -3163,7 +3195,7 @@ spv::Id TGlslangToSpvTraverser::getSymbolId(const glslang::TIntermSymbol* symbol
}
}
addDecoration
(
id
,
TranslateInvariantDecoration
(
symbol
->
getType
()));
addDecoration
(
id
,
TranslateInvariantDecoration
(
symbol
->
getType
()
.
getQualifier
()
));
if
(
symbol
->
getQualifier
().
hasStream
())
builder
.
addDecoration
(
id
,
spv
::
DecorationStream
,
symbol
->
getQualifier
().
layoutStream
);
if
(
symbol
->
getQualifier
().
hasSet
())
...
...
Test/baseResults/spv.layoutNested.vert.out
View file @
e0b6cad4
...
...
@@ -7,12 +7,12 @@ Linked vertex stage:
// Module Version 10000
// Generated by (magic number): 80001
// Id's are bound by 6
3
// Id's are bound by 6
9
Capability Shader
1: ExtInstImport "GLSL.std.450"
MemoryModel Logical GLSL450
EntryPoint Vertex 4 "main" 6
1 62
EntryPoint Vertex 4 "main" 6
2 65 67 68
Source GLSL 450
Name 4 "main"
Name 14 "S"
...
...
@@ -82,8 +82,18 @@ Linked vertex stage:
MemberName 57(bBt3) 0 "ntcol"
MemberName 57(bBt3) 1 "ntrow"
Name 59 "bBtn3"
Name 61 "gl_VertexID"
Name 62 "gl_InstanceID"
Name 60 "S"
MemberName 60(S) 0 "a"
MemberName 60(S) 1 "b"
MemberName 60(S) 2 "c"
Name 62 "sout"
Name 63 "S"
MemberName 63(S) 0 "a"
MemberName 63(S) 1 "b"
MemberName 63(S) 2 "c"
Name 65 "soutinv"
Name 67 "gl_VertexID"
Name 68 "gl_InstanceID"
Decorate 13 ArrayStride 32
MemberDecorate 14(S) 0 Offset 0
MemberDecorate 14(S) 1 ColMajor
...
...
@@ -156,8 +166,15 @@ Linked vertex stage:
Decorate 57(bBt3) BufferBlock
Decorate 59(bBtn3) DescriptorSet 1
Decorate 59(bBtn3) Binding 0
Decorate 61(gl_VertexID) BuiltIn VertexId
Decorate 62(gl_InstanceID) BuiltIn InstanceId
MemberDecorate 60(S) 0 Flat
MemberDecorate 60(S) 1 Flat
MemberDecorate 60(S) 2 Flat
MemberDecorate 63(S) 0 Invariant
MemberDecorate 63(S) 1 Invariant
MemberDecorate 63(S) 2 Invariant
Decorate 65(soutinv) Invariant
Decorate 67(gl_VertexID) BuiltIn VertexId
Decorate 68(gl_InstanceID) BuiltIn InstanceId
2: TypeVoid
3: TypeFunction 2
6: TypeInt 32 1
...
...
@@ -214,9 +231,15 @@ Linked vertex stage:
57(bBt3): TypeStruct 48(Nestor) 53(Nestor)
58: TypePointer Uniform 57(bBt3)
59(bBtn3): 58(ptr) Variable Uniform
60: TypePointer Input 6(int)
61(gl_VertexID): 60(ptr) Variable Input
62(gl_InstanceID): 60(ptr) Variable Input
60(S): TypeStruct 8(ivec3) 13 7(int)
61: TypePointer Output 60(S)
62(sout): 61(ptr) Variable Output
63(S): TypeStruct 8(ivec3) 13 7(int)
64: TypePointer Output 63(S)
65(soutinv): 64(ptr) Variable Output
66: TypePointer Input 6(int)
67(gl_VertexID): 66(ptr) Variable Input
68(gl_InstanceID): 66(ptr) Variable Input
4(main): 2 Function None 3
5: Label
Return
...
...
Test/spv.layoutNested.vert
View file @
e0b6cad4
#version 450
// should get 3 SPV types for S: no layout, 140, and 430
// should get 3 SPV types for S: no layout, 140, and 430
, plus extras for interpolation or invariant differences
struct
S
{
highp
uvec3
a
;
...
...
@@ -71,3 +71,6 @@ layout(set = 1, binding = 0, std430) buffer bBt3
void
main
()
{
}
flat
out
S
sout
;
invariant
out
S
soutinv
;
glslang/Include/revision.h
View file @
e0b6cad4
...
...
@@ -2,5 +2,5 @@
// 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).
#define GLSLANG_REVISION "SPIRV99.86
5
"
#define GLSLANG_DATE "2
2
-Dec-2015"
#define GLSLANG_REVISION "SPIRV99.86
6
"
#define GLSLANG_DATE "2
4
-Dec-2015"
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment