Commit 44b807e1 by John Kessenich

GL_ARB_enhanced_layouts, part 3: Semantics for xfb_*: where they can go,…

GL_ARB_enhanced_layouts, part 3: Semantics for xfb_*: where they can go, inheritance, etc., but not yet the backing arithmetic for offsets and strides. git-svn-id: https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/tools/glslang@24916 e7fa87d3-cd2b-0410-9028-fcbf551c1848
parent 281958c2
...@@ -62,3 +62,37 @@ layout(location = 1, component = 1) out; // ERROR, no global set ...@@ -62,3 +62,37 @@ layout(location = 1, component = 1) out; // ERROR, no global set
layout(location = 50, component = 3) out int be; layout(location = 50, component = 3) out int be;
layout(location = 50, component = 0) out vec3 bf; layout(location = 50, component = 0) out vec3 bf;
out bblck1 {
vec4 bbv;
} bbinst1;
out bblck2 {
layout(xfb_offset=16) vec4 bbv;
} bbinst2;
layout(xfb_buffer = 3, xfb_stride = 16) out;
out bblck3 {
layout(xfb_offset=16) vec4 bbv;
} bbinst3;
uniform ubblck3 {
layout(xfb_offset=16) vec4 bbv; // ERROR
} ubbinst3;
layout(xfb_buffer=2, xfb_offset=32, xfb_stride=64) out vec4 bg;
layout( xfb_offset=32, xfb_stride=64) out vec4 bh;
layout(xfb_offset=48) out; // ERROR
layout(xfb_stride=32, xfb_buffer=2, xfb_offset=16) out bblck4 {
vec4 bbv1;
vec4 bbv2;
} bbinst4;
out bblck5 {
layout(xfb_offset=0) vec4 bbv1;
layout(xfb_stride=32, xfb_buffer=3, xfb_offset=16) vec4 bbv2;
layout(xfb_buffer=2) vec4 bbv3; // ERROR, wrong buffer
} bbinst5;
...@@ -19,9 +19,13 @@ ERROR: 0:55: 'component' : type overflows the available 4 components ...@@ -19,9 +19,13 @@ ERROR: 0:55: 'component' : type overflows the available 4 components
ERROR: 0:57: 'component' : cannot apply to a matrix, structure, or block ERROR: 0:57: 'component' : cannot apply to a matrix, structure, or block
ERROR: 0:58: 'component' : cannot apply to a matrix, structure, or block ERROR: 0:58: 'component' : cannot apply to a matrix, structure, or block
ERROR: 0:61: 'location' : cannot declare a default, use a full declaration ERROR: 0:61: 'location' : cannot declare a default, use a full declaration
ERROR: 19 compilation errors. No code generated. ERROR: 0:81: 'xfb layout qualifier' : can only be used on an output
ERROR: 0:87: 'xfb_offset' : cannot declare a default, use a full declaration
ERROR: 0:97: 'xfb_buffer' : member cannot contradict block (or what block inherited from global)
ERROR: 22 compilation errors. No code generated.
in xfb mode
ERROR: node is still EOpNull! ERROR: node is still EOpNull!
0:? Linker Objects 0:? Linker Objects
0:? 'a' (layout(location=2 component=2 ) in 2-component vector of float) 0:? 'a' (layout(location=2 component=2 ) in 2-component vector of float)
...@@ -55,6 +59,14 @@ ERROR: node is still EOpNull! ...@@ -55,6 +59,14 @@ ERROR: node is still EOpNull!
0:? 'bd' (out block{layout(location=40 component=2 ) out float u, layout(location=40 component=0 ) out float v, layout(location=40 component=3 ) out float w, layout(location=40 component=1 ) out 2-component vector of float x, layout(location=41 component=3 ) out 2-component vector of float y, layout(location=42 component=1 ) out 4-component vector of float z, layout(location=42 component=1 ) out 4X4 matrix of float ba, layout(location=43 component=1 ) out structure{int a} Ss}) 0:? 'bd' (out block{layout(location=40 component=2 ) out float u, layout(location=40 component=0 ) out float v, layout(location=40 component=3 ) out float w, layout(location=40 component=1 ) out 2-component vector of float x, layout(location=41 component=3 ) out 2-component vector of float y, layout(location=42 component=1 ) out 4-component vector of float z, layout(location=42 component=1 ) out 4X4 matrix of float ba, layout(location=43 component=1 ) out structure{int a} Ss})
0:? 'be' (layout(location=50 component=3 ) smooth out int) 0:? 'be' (layout(location=50 component=3 ) smooth out int)
0:? 'bf' (layout(location=50 component=0 ) smooth out 3-component vector of float) 0:? 'bf' (layout(location=50 component=0 ) smooth out 3-component vector of float)
0:? 'bbinst1' (out block{out 4-component vector of float bbv})
0:? 'bbinst2' (out block{layout(xfb_buffer=0 xfb_offset=16 ) out 4-component vector of float bbv})
0:? 'bbinst3' (out block{layout(xfb_buffer=3 xfb_offset=16 ) out 4-component vector of float bbv})
0:? 'ubbinst3' (layout(column_major shared ) uniform block{layout(column_major shared xfb_offset=16 ) uniform 4-component vector of float bbv})
0:? 'bg' (layout(xfb_buffer=2 xfb_offset=32 xfb_stride=64 ) smooth out 4-component vector of float)
0:? 'bh' (layout(xfb_buffer=3 xfb_offset=32 xfb_stride=64 ) smooth out 4-component vector of float)
0:? 'bbinst4' (layout(xfb_buffer=2 xfb_offset=16 xfb_stride=32 ) out block{layout(xfb_buffer=2 xfb_offset=16 ) out 4-component vector of float bbv1, layout(xfb_buffer=2 xfb_offset=16 ) out 4-component vector of float bbv2})
0:? 'bbinst5' (out block{layout(xfb_buffer=3 xfb_offset=0 ) out 4-component vector of float bbv1, layout(xfb_buffer=3 xfb_offset=16 xfb_stride=32 ) out 4-component vector of float bbv2, out 4-component vector of float bbv3})
0:? 'gl_VertexID' (gl_VertexId int) 0:? 'gl_VertexID' (gl_VertexId int)
0:? 'gl_InstanceID' (gl_InstanceId int) 0:? 'gl_InstanceID' (gl_InstanceId int)
...@@ -63,4 +75,5 @@ Linked vertex stage: ...@@ -63,4 +75,5 @@ Linked vertex stage:
ERROR: Linking vertex stage: Missing entry point: Each stage requires one "void main()" entry point ERROR: Linking vertex stage: Missing entry point: Each stage requires one "void main()" entry point
in xfb mode
...@@ -9,5 +9,5 @@ ...@@ -9,5 +9,5 @@
// source have to figure out how to create revision.h just to get a build // source have to figure out how to create revision.h just to get a build
// going. However, if it is not updated, it can be a version behind. // going. However, if it is not updated, it can be a version behind.
#define GLSLANG_REVISION "24740" #define GLSLANG_REVISION "24741"
#define GLSLANG_DATE "2014/01/11 12:29:55" #define GLSLANG_DATE "2014/01/11 13:35:26"
...@@ -101,11 +101,14 @@ TParseContext::TParseContext(TSymbolTable& symt, TIntermediate& interm, bool pb, ...@@ -101,11 +101,14 @@ TParseContext::TParseContext(TSymbolTable& symt, TIntermediate& interm, bool pb,
globalBufferDefaults.layoutMatrix = ElmColumnMajor; globalBufferDefaults.layoutMatrix = ElmColumnMajor;
globalBufferDefaults.layoutPacking = ElpShared; globalBufferDefaults.layoutPacking = ElpShared;
// TODO: 4.4 enhanced layouts: defaults for xfb?
globalInputDefaults.clear(); globalInputDefaults.clear();
globalOutputDefaults.clear(); globalOutputDefaults.clear();
if (language == EShLangVertex ||
language == EShLangTessControl ||
language == EShLangTessEvaluation ||
language == EShLangGeometry)
globalOutputDefaults.layoutXfbBuffer = 0;
if (language == EShLangGeometry) if (language == EShLangGeometry)
globalOutputDefaults.layoutStream = 0; globalOutputDefaults.layoutStream = 0;
} }
...@@ -1791,7 +1794,7 @@ void TParseContext::globalQualifierCheck(TSourceLoc loc, const TQualifier& quali ...@@ -1791,7 +1794,7 @@ void TParseContext::globalQualifierCheck(TSourceLoc loc, const TQualifier& quali
case EShLangCompute: case EShLangCompute:
break; break;
default: default:
break; break;
} }
} else { } else {
...@@ -1827,7 +1830,7 @@ void TParseContext::globalQualifierCheck(TSourceLoc loc, const TQualifier& quali ...@@ -1827,7 +1830,7 @@ void TParseContext::globalQualifierCheck(TSourceLoc loc, const TQualifier& quali
case EShLangCompute: case EShLangCompute:
break; break;
default: default:
break; break;
} }
} }
...@@ -2869,6 +2872,7 @@ void TParseContext::setLayoutQualifier(TSourceLoc loc, TPublicType& publicType, ...@@ -2869,6 +2872,7 @@ void TParseContext::setLayoutQualifier(TSourceLoc loc, TPublicType& publicType,
publicType.qualifier.layoutComponent = value; publicType.qualifier.layoutComponent = value;
return; return;
} else if (id.compare(0, 4, "xfb_") == 0) { } else if (id.compare(0, 4, "xfb_") == 0) {
intermediate.setXfbMode();
const char* feature = "transform feedback qualifier"; const char* feature = "transform feedback qualifier";
requireStage(loc, (EShLanguageMask)(EShLangVertexMask | EShLangGeometryMask | EShLangTessControlMask | EShLangTessEvaluationMask), feature); requireStage(loc, (EShLanguageMask)(EShLangVertexMask | EShLangGeometryMask | EShLangTessControlMask | EShLangTessEvaluationMask), feature);
requireProfile(loc, ECoreProfile | ECompatibilityProfile, feature); requireProfile(loc, ECoreProfile | ECompatibilityProfile, feature);
...@@ -2878,16 +2882,19 @@ void TParseContext::setLayoutQualifier(TSourceLoc loc, TPublicType& publicType, ...@@ -2878,16 +2882,19 @@ void TParseContext::setLayoutQualifier(TSourceLoc loc, TPublicType& publicType,
error(loc, "buffer is too large", id.c_str(), ""); error(loc, "buffer is too large", id.c_str(), "");
else else
publicType.qualifier.layoutXfbBuffer = value; publicType.qualifier.layoutXfbBuffer = value;
return;
} else if (id == "xfb_offset") { } else if (id == "xfb_offset") {
if (value >= TQualifier::layoutXfbOffsetEnd) // TODO: 4.4 enhanced layouts: also check against gl_MaxTransformFeedbackInterleavedComponents if (value >= TQualifier::layoutXfbOffsetEnd) // TODO: 4.4 enhanced layouts: also check against gl_MaxTransformFeedbackInterleavedComponents
error(loc, "offset is too large", id.c_str(), ""); error(loc, "offset is too large", id.c_str(), "");
else else
publicType.qualifier.layoutXfbOffset = value; publicType.qualifier.layoutXfbOffset = value;
return;
} else if (id == "xfb_stride") { } else if (id == "xfb_stride") {
if (value >= TQualifier::layoutXfbStrideEnd) // TODO: 4.4 enhanced layouts: also check against gl_MaxTransformFeedbackInterleavedComponents if (value >= TQualifier::layoutXfbStrideEnd) // TODO: 4.4 enhanced layouts: also check against 4*gl_MaxTransformFeedbackInterleavedComponents
error(loc, "stride is too large", id.c_str(), ""); error(loc, "stride is too large", id.c_str(), "");
else else
publicType.qualifier.layoutXfbStride = value; publicType.qualifier.layoutXfbStride = value;
return;
} }
} }
...@@ -2929,7 +2936,7 @@ void TParseContext::setLayoutQualifier(TSourceLoc loc, TPublicType& publicType, ...@@ -2929,7 +2936,7 @@ void TParseContext::setLayoutQualifier(TSourceLoc loc, TPublicType& publicType,
case EShLangCompute: case EShLangCompute:
break; break;
default: default:
break; break;
} }
...@@ -2947,8 +2954,10 @@ void TParseContext::mergeObjectLayoutQualifiers(TSourceLoc loc, TQualifier& dst, ...@@ -2947,8 +2954,10 @@ void TParseContext::mergeObjectLayoutQualifiers(TSourceLoc loc, TQualifier& dst,
if (src.hasStream()) if (src.hasStream())
dst.layoutStream = src.layoutStream; dst.layoutStream = src.layoutStream;
if (src.layoutXfbBuffer != TQualifier::layoutXfbBufferEnd) if (src.hasXfbBuffer())
dst.layoutXfbBuffer = src.layoutXfbBuffer; dst.layoutXfbBuffer = src.layoutXfbBuffer;
if (src.hasXfbOffset())
dst.layoutXfbOffset = src.layoutXfbOffset;
if (! inheritOnly) { if (! inheritOnly) {
if (src.layoutLocation != TQualifier::layoutLocationEnd) if (src.layoutLocation != TQualifier::layoutLocationEnd)
...@@ -2964,10 +2973,8 @@ void TParseContext::mergeObjectLayoutQualifiers(TSourceLoc loc, TQualifier& dst, ...@@ -2964,10 +2973,8 @@ void TParseContext::mergeObjectLayoutQualifiers(TSourceLoc loc, TQualifier& dst,
if (src.layoutBinding != TQualifier::layoutBindingEnd) if (src.layoutBinding != TQualifier::layoutBindingEnd)
dst.layoutBinding = src.layoutBinding; dst.layoutBinding = src.layoutBinding;
if (src.layoutXfbStride != TQualifier::layoutXfbStrideEnd) if (src.hasXfbStride())
dst.layoutXfbStride = src.layoutXfbStride; dst.layoutXfbStride = src.layoutXfbStride;
if (src.layoutXfbOffset != TQualifier::layoutXfbOffsetEnd)
dst.layoutXfbOffset = src.layoutXfbOffset;
} }
} }
...@@ -3145,6 +3152,10 @@ void TParseContext::layoutQualifierCheck(TSourceLoc loc, const TQualifier& quali ...@@ -3145,6 +3152,10 @@ void TParseContext::layoutQualifierCheck(TSourceLoc loc, const TQualifier& quali
if (qualifier.storage != EvqVaryingOut) if (qualifier.storage != EvqVaryingOut)
error(loc, "can only be used on an output", "stream", ""); error(loc, "can only be used on an output", "stream", "");
} }
if (qualifier.hasXfb()) {
if (qualifier.storage != EvqVaryingOut)
error(loc, "can only be used on an output", "xfb layout qualifier", "");
}
} }
// For places that can't have shader-level layout qualifiers // For places that can't have shader-level layout qualifiers
...@@ -3303,10 +3314,6 @@ TIntermNode* TParseContext::declareVariable(TSourceLoc loc, TString& identifier, ...@@ -3303,10 +3314,6 @@ TIntermNode* TParseContext::declareVariable(TSourceLoc loc, TString& identifier,
invariantCheck(loc, type, identifier); invariantCheck(loc, type, identifier);
samplerCheck(loc, type, identifier); samplerCheck(loc, type, identifier);
// Pick up defaults
if (! type.getQualifier().hasStream() && language == EShLangGeometry && type.getQualifier().storage == EvqVaryingOut)
type.getQualifier().layoutStream = globalOutputDefaults.layoutStream;
if (identifier != "gl_FragCoord" && (publicType.shaderQualifiers.originUpperLeft || publicType.shaderQualifiers.pixelCenterInteger)) if (identifier != "gl_FragCoord" && (publicType.shaderQualifiers.originUpperLeft || publicType.shaderQualifiers.pixelCenterInteger))
error(loc, "can only apply origin_upper_left and pixel_center_origin to gl_FragCoord", "layout qualifier", ""); error(loc, "can only apply origin_upper_left and pixel_center_origin to gl_FragCoord", "layout qualifier", "");
...@@ -3316,6 +3323,8 @@ TIntermNode* TParseContext::declareVariable(TSourceLoc loc, TString& identifier, ...@@ -3316,6 +3323,8 @@ TIntermNode* TParseContext::declareVariable(TSourceLoc loc, TString& identifier,
if (! symbol) if (! symbol)
reservedErrorCheck(loc, identifier); reservedErrorCheck(loc, identifier);
inheritGlobalDefaults(type.getQualifier());
// Declare the variable // Declare the variable
if (arraySizes || type.isArray()) { if (arraySizes || type.isArray()) {
// Arrayness is potentially coming both from the type and from the // Arrayness is potentially coming both from the type and from the
...@@ -3369,6 +3378,17 @@ TIntermNode* TParseContext::declareVariable(TSourceLoc loc, TString& identifier, ...@@ -3369,6 +3378,17 @@ TIntermNode* TParseContext::declareVariable(TSourceLoc loc, TString& identifier,
return initNode; return initNode;
} }
// Pick up global defaults from the provide global defaults into dst.
void TParseContext::inheritGlobalDefaults(TQualifier& dst) const
{
if (dst.storage == EvqVaryingOut) {
if (! dst.hasStream() && language == EShLangGeometry)
dst.layoutStream = globalOutputDefaults.layoutStream;
if (! dst.hasXfbBuffer())
dst.layoutXfbBuffer = globalOutputDefaults.layoutXfbBuffer;
}
}
// //
// Declare a non-array variable, the main point being there is no redeclaration // Declare a non-array variable, the main point being there is no redeclaration
// for resizing allowed. // for resizing allowed.
...@@ -3824,6 +3844,10 @@ void TParseContext::declareBlock(TSourceLoc loc, TTypeList& typeList, const TStr ...@@ -3824,6 +3844,10 @@ void TParseContext::declareBlock(TSourceLoc loc, TTypeList& typeList, const TStr
if (defaultQualification.layoutStream != memberQualifier.layoutStream) if (defaultQualification.layoutStream != memberQualifier.layoutStream)
error(memberLoc, "member cannot contradict block", "stream", ""); error(memberLoc, "member cannot contradict block", "stream", "");
} }
if (memberQualifier.hasXfbBuffer()) {
if (defaultQualification.layoutXfbBuffer != memberQualifier.layoutXfbBuffer)
error(memberLoc, "member cannot contradict block (or what block inherited from global)", "xfb_buffer", "");
}
if (memberQualifier.layoutPacking != ElpNone) if (memberQualifier.layoutPacking != ElpNone)
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()) {
...@@ -4124,6 +4148,8 @@ void TParseContext::updateStandaloneQualifierDefaults(TSourceLoc loc, const TPub ...@@ -4124,6 +4148,8 @@ void TParseContext::updateStandaloneQualifierDefaults(TSourceLoc loc, const TPub
case EvqVaryingOut: case EvqVaryingOut:
if (qualifier.hasStream()) if (qualifier.hasStream())
globalOutputDefaults.layoutStream = qualifier.layoutStream; globalOutputDefaults.layoutStream = qualifier.layoutStream;
if (qualifier.hasXfbBuffer())
globalOutputDefaults.layoutXfbBuffer = qualifier.layoutXfbBuffer;
break; break;
default: default:
error(loc, "default qualifier requires 'uniform', 'buffer', 'in', or 'out' storage qualification", "", ""); error(loc, "default qualifier requires 'uniform', 'buffer', 'in', or 'out' storage qualification", "", "");
...@@ -4134,6 +4160,8 @@ void TParseContext::updateStandaloneQualifierDefaults(TSourceLoc loc, const TPub ...@@ -4134,6 +4160,8 @@ void TParseContext::updateStandaloneQualifierDefaults(TSourceLoc loc, const TPub
error(loc, "cannot declare a default, include a type or full declaration", "binding", ""); error(loc, "cannot declare a default, include a type or full declaration", "binding", "");
if (qualifier.hasLocation()) if (qualifier.hasLocation())
error(loc, "cannot declare a default, use a full declaration", "location", ""); error(loc, "cannot declare a default, use a full declaration", "location", "");
if (qualifier.hasXfbOffset())
error(loc, "cannot declare a default, use a full declaration", "xfb_offset", "");
} }
// //
......
...@@ -202,6 +202,7 @@ public: ...@@ -202,6 +202,7 @@ public:
protected: protected:
void nonInitConstCheck(TSourceLoc, TString& identifier, TType& type); void nonInitConstCheck(TSourceLoc, TString& identifier, TType& type);
void inheritGlobalDefaults(TQualifier& dst) const;
TVariable* declareNonArray(TSourceLoc, TString& identifier, TType&, bool& newDeclaration); TVariable* declareNonArray(TSourceLoc, TString& identifier, TType&, bool& newDeclaration);
void declareArray(TSourceLoc, TString& identifier, const TType&, TSymbol*&, bool& newDeclaration); void declareArray(TSourceLoc, TString& identifier, const TType&, TSymbol*&, bool& newDeclaration);
TIntermNode* executeInitializer(TSourceLoc, TString& identifier, TIntermTyped* initializer, TVariable* variable); TIntermNode* executeInitializer(TSourceLoc, TString& identifier, TIntermTyped* initializer, TVariable* variable);
......
...@@ -579,6 +579,9 @@ bool TOutputTraverser::visitSwitch(TVisit /* visit */, TIntermSwitch* node) ...@@ -579,6 +579,9 @@ bool TOutputTraverser::visitSwitch(TVisit /* visit */, TIntermSwitch* node)
// //
void TIntermediate::output(TInfoSink& infoSink, bool tree) void TIntermediate::output(TInfoSink& infoSink, bool tree)
{ {
if (xfbMode)
infoSink.debug << "in xfb mode\n";
switch (language) { switch (language) {
case EShLangVertex: case EShLangVertex:
break; break;
......
...@@ -110,6 +110,9 @@ void TIntermediate::merge(TInfoSink& infoSink, TIntermediate& unit) ...@@ -110,6 +110,9 @@ void TIntermediate::merge(TInfoSink& infoSink, TIntermediate& unit)
if (unit.pointMode) if (unit.pointMode)
pointMode = true; pointMode = true;
if (unit.xfbMode)
xfbMode = true;
if (unit.treeRoot == 0) if (unit.treeRoot == 0)
return; return;
......
...@@ -62,7 +62,7 @@ public: ...@@ -62,7 +62,7 @@ public:
explicit TIntermediate(EShLanguage l, int v = 0, EProfile p = ENoProfile) : language(l), treeRoot(0), profile(p), version(v), explicit TIntermediate(EShLanguage l, int v = 0, EProfile p = ENoProfile) : language(l), treeRoot(0), profile(p), version(v),
numMains(0), numErrors(0), recursive(false), numMains(0), numErrors(0), recursive(false),
invocations(0), vertices(0), inputPrimitive(ElgNone), outputPrimitive(ElgNone), pixelCenterInteger(false), originUpperLeft(false), invocations(0), vertices(0), inputPrimitive(ElgNone), outputPrimitive(ElgNone), pixelCenterInteger(false), originUpperLeft(false),
vertexSpacing(EvsNone), vertexOrder(EvoNone), pointMode(false) { } vertexSpacing(EvsNone), vertexOrder(EvoNone), pointMode(false), xfbMode(false) { }
bool postProcess(TIntermNode*, EShLanguage); bool postProcess(TIntermNode*, EShLanguage);
void output(TInfoSink&, bool tree); void output(TInfoSink&, bool tree);
void removeTree(); void removeTree();
...@@ -153,6 +153,7 @@ public: ...@@ -153,6 +153,7 @@ public:
return true; return true;
} }
void setPointMode() { pointMode = true; } void setPointMode() { pointMode = true; }
void setXfbMode() { xfbMode = true; }
bool setOutputPrimitive(TLayoutGeometry p) bool setOutputPrimitive(TLayoutGeometry p)
{ {
if (outputPrimitive != ElgNone) if (outputPrimitive != ElgNone)
...@@ -202,6 +203,7 @@ protected: ...@@ -202,6 +203,7 @@ protected:
TVertexSpacing vertexSpacing; TVertexSpacing vertexSpacing;
TVertexOrder vertexOrder; TVertexOrder vertexOrder;
bool pointMode; bool pointMode;
bool xfbMode;
// for detecting recursion: pair is <caller, callee> // for detecting recursion: pair is <caller, callee>
struct TCall { struct TCall {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment