Commit 3ed2db58 by John Kessenich

Put in correct rules for multiple versions of qualification and typing of inputs…

Put in correct rules for multiple versions of qualification and typing of inputs and outputs. Also, removed EvqAttribute, merging it with EvqVaryingIn. git-svn-id: https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/tools/glslang@21064 e7fa87d3-cd2b-0410-9028-fcbf551c1848
parent ad3663be
...@@ -23,10 +23,19 @@ in vec2 c2D; ...@@ -23,10 +23,19 @@ in vec2 c2D;
in vec3 c3D; in vec3 c3D;
in vec4 c4D; in vec4 c4D;
in int ic1D; flat in int ic1D;
in ivec2 ic2D; flat in ivec2 ic2D;
in ivec3 ic3D; flat in ivec3 ic3D;
in ivec4 ic4D; flat in ivec4 ic4D;
in sampler2D bads; // ERROR
struct s {
int i;
sampler2D s; // ERROR
};
out s badout; // ERROR
void main() void main()
{ {
......
...@@ -7,6 +7,8 @@ uniform mat4x4 m44; ...@@ -7,6 +7,8 @@ uniform mat4x4 m44;
in vec3 v3; in vec3 v3;
in vec2 v2; in vec2 v2;
in vec4 bad[10];
void main() void main()
{ {
int id = gl_VertexID + gl_InstanceID; int id = gl_VertexID + gl_InstanceID;
......
#version 300 es #version 300 es
in uvec2 badu; // ERROR
in uvec2 t; flat in uvec2 t;
in float f; in float f;
in vec2 tc; in vec2 tc;
in bool bad; // ERROR
uniform uvec4 v; uniform uvec4 v;
uniform int i; uniform int i;
uniform bool b; uniform bool b;
......
...@@ -62,9 +62,8 @@ enum TStorageQualifier { ...@@ -62,9 +62,8 @@ enum TStorageQualifier {
EvqTemporary, // For temporaries (within a function), read/write EvqTemporary, // For temporaries (within a function), read/write
EvqGlobal, // For globals read/write EvqGlobal, // For globals read/write
EvqConst, // User defined constants and non-output parameters in functions EvqConst, // User defined constants and non-output parameters in functions
EvqAttribute, // Readonly EvqVaryingIn, // pipeline input, read only
EvqVaryingIn, // readonly, fragment shaders only EvqVaryingOut, // pipeline ouput, read/write
EvqVaryingOut, // vertex shaders only read/write
EvqUniform, // Readonly, vertex and fragment EvqUniform, // Readonly, vertex and fragment
// parameters // parameters
...@@ -103,9 +102,8 @@ __inline const char* getStorageQualifierString(TStorageQualifier q) ...@@ -103,9 +102,8 @@ __inline const char* getStorageQualifierString(TStorageQualifier q)
case EvqGlobal: return "global"; break; case EvqGlobal: return "global"; break;
case EvqConst: return "const"; break; case EvqConst: return "const"; break;
case EvqConstReadOnly: return "const (read only)"; break; case EvqConstReadOnly: return "const (read only)"; break;
case EvqAttribute: return "attribute"; break; case EvqVaryingIn: return "shader in"; break;
case EvqVaryingIn: return "varying in"; break; case EvqVaryingOut: return "shader out"; break;
case EvqVaryingOut: return "varying out"; break;
case EvqUniform: return "uniform"; break; case EvqUniform: return "uniform"; break;
case EvqIn: return "in"; break; case EvqIn: return "in"; break;
case EvqOut: return "out"; break; case EvqOut: return "out"; break;
......
...@@ -217,6 +217,18 @@ public: ...@@ -217,6 +217,18 @@ public:
bool restrict : 1; bool restrict : 1;
bool readonly : 1; bool readonly : 1;
bool writeonly : 1; bool writeonly : 1;
bool isMemory()
{
return coherent || volatil || restrict || readonly || writeonly;
}
bool isInterpolation()
{
return flat || smooth || nopersp;
}
bool isAuxillary()
{
return centroid || patch || sample;
}
}; };
class TPublicType { class TPublicType {
......
...@@ -328,9 +328,8 @@ bool TParseContext::lValueErrorCheck(int line, const char* op, TIntermTyped* nod ...@@ -328,9 +328,8 @@ bool TParseContext::lValueErrorCheck(int line, const char* op, TIntermTyped* nod
switch (node->getQualifier().storage) { switch (node->getQualifier().storage) {
case EvqConst: message = "can't modify a const"; break; case EvqConst: message = "can't modify a const"; break;
case EvqConstReadOnly: message = "can't modify a const"; break; case EvqConstReadOnly: message = "can't modify a const"; break;
case EvqAttribute: message = "can't modify an attribute"; break; case EvqVaryingIn: message = "can't modify shader input"; break;
case EvqUniform: message = "can't modify a uniform"; break; case EvqUniform: message = "can't modify a uniform"; break;
case EvqVaryingIn: message = "can't modify a varying"; break;
case EvqInstanceId: message = "can't modify gl_InstanceID"; break; case EvqInstanceId: message = "can't modify gl_InstanceID"; break;
case EvqVertexId: message = "can't modify gl_VertexID"; break; case EvqVertexId: message = "can't modify gl_VertexID"; break;
case EvqFace: message = "can't modify gl_FrontFace"; break; case EvqFace: message = "can't modify gl_FrontFace"; break;
...@@ -617,7 +616,7 @@ bool TParseContext::samplerErrorCheck(int line, const TPublicType& pType, const ...@@ -617,7 +616,7 @@ bool TParseContext::samplerErrorCheck(int line, const TPublicType& pType, const
{ {
if (pType.type == EbtStruct) { if (pType.type == EbtStruct) {
if (containsSampler(*pType.userDef)) { if (containsSampler(*pType.userDef)) {
error(line, reason, TType::getBasicString(pType.type), "(structure contains a sampler/image)"); error(line, reason, TType::getBasicString(pType.type), "(structure cannot contain a sampler or image)");
return true; return true;
} }
...@@ -632,8 +631,13 @@ bool TParseContext::samplerErrorCheck(int line, const TPublicType& pType, const ...@@ -632,8 +631,13 @@ bool TParseContext::samplerErrorCheck(int line, const TPublicType& pType, const
return false; return false;
} }
bool TParseContext::globalQualifierFixAndErrorCheck(int line, TQualifier& qualifier) bool TParseContext::globalQualifierFixAndErrorCheck(int line, TQualifier& qualifier, const TPublicType& publicType)
{ {
if (! symbolTable.atGlobalLevel())
return false;
// First, move from parameter qualifiers to shader in/out qualifiers
switch (qualifier.storage) { switch (qualifier.storage) {
case EvqIn: case EvqIn:
profileRequires(line, ENoProfile, 130, 0, "in for stage inputs"); profileRequires(line, ENoProfile, 130, 0, "in for stage inputs");
...@@ -645,31 +649,68 @@ bool TParseContext::globalQualifierFixAndErrorCheck(int line, TQualifier& qualif ...@@ -645,31 +649,68 @@ bool TParseContext::globalQualifierFixAndErrorCheck(int line, TQualifier& qualif
profileRequires(line, EEsProfile, 300, 0, "out for stage outputs"); profileRequires(line, EEsProfile, 300, 0, "out for stage outputs");
qualifier.storage = EvqVaryingOut; qualifier.storage = EvqVaryingOut;
break; break;
case EvqVaryingIn:
case EvqVaryingOut:
break;
case EvqInOut: case EvqInOut:
qualifier.storage = EvqVaryingIn; qualifier.storage = EvqVaryingIn;
error(line, "cannot use 'inout' at global scope", "", ""); error(line, "cannot use 'inout' at global scope", "", "");
return true; return true;
default: break; // some compilers want this default:
break;
} }
// Do non in/out error checks
if (qualifier.storage != EvqUniform && samplerErrorCheck(line, publicType, "samplers and images must be uniform"))
return true;
if (qualifier.storage != EvqVaryingIn && qualifier.storage != EvqVaryingOut)
return false; return false;
}
bool TParseContext::structQualifierErrorCheck(int line, const TPublicType& pType) // now, knowing it is a shader in/out, do all the in/out semantic checks
{
if ((pType.qualifier.storage == EvqVaryingIn || if (publicType.type == EbtBool) {
pType.qualifier.storage == EvqVaryingOut || error(line, "cannot be bool", getStorageQualifierString(qualifier.storage), "");
pType.qualifier.storage == EvqAttribute) && return true;
pType.type == EbtStruct) { }
error(line, "cannot be used with a structure", getStorageQualifierString(pType.qualifier.storage), ""); if (language == EShLangVertex && qualifier.storage == EvqVaryingIn) {
if (publicType.type == EbtStruct) {
error(line, "cannot be a structure or array", getStorageQualifierString(qualifier.storage), "");
return true;
}
if (publicType.arraySizes) {
requireProfile(line, (EProfileMask)~EEsProfileMask, "vertex input arrays");
profileRequires(line, ENoProfile, 150, 0, "vertex input arrays");
}
}
if (language == EShLangFragment && qualifier.storage == EvqVaryingOut) {
profileRequires(line, EEsProfile, 300, 0, "fragment shader output");
if (publicType.type == EbtStruct) {
error(line, "cannot be a structure", getStorageQualifierString(qualifier.storage), "");
return true; return true;
} }
}
if (publicType.type == EbtInt || publicType.type == EbtUint || publicType.type == EbtDouble) {
profileRequires(line, EEsProfile, 300, 0, "shader input/output");
if (language != EShLangVertex && qualifier.storage == EvqVaryingIn && ! qualifier.flat ||
language != EShLangFragment && qualifier.storage == EvqVaryingOut && ! qualifier.flat) {
error(line, "must be qualified as 'flat'", getStorageQualifierString(qualifier.storage), TType::getBasicString(publicType.type));
if (pType.qualifier.storage != EvqUniform && samplerErrorCheck(line, pType, "samplers and images must be uniform"))
return true; return true;
}
}
if (language == EShLangVertex && qualifier.storage == EvqVaryingIn &&
(qualifier.isAuxillary() || qualifier.isInterpolation() || qualifier.isMemory() || qualifier.buffer || qualifier.invariant)) {
error(line, "vertex input cannot be further qualified", "", "");
return true;
}
return false; return false;
} }
...@@ -832,13 +873,8 @@ bool TParseContext::arraySizeErrorCheck(int line, TIntermTyped* expr, int& size) ...@@ -832,13 +873,8 @@ bool TParseContext::arraySizeErrorCheck(int line, TIntermTyped* expr, int& size)
// //
// Returns true if there is an error. // Returns true if there is an error.
// //
bool TParseContext::arrayQualifierErrorCheck(int line, TPublicType type) bool TParseContext::arrayQualifierErrorCheck(int line, const TPublicType& type)
{ {
if (type.qualifier.storage == EvqAttribute) {
error(line, "cannot declare arrays of this qualifier", TType(type).getCompleteString().c_str(), "");
return true;
}
if (type.qualifier.storage == EvqConst) if (type.qualifier.storage == EvqConst)
profileRequires(line, ENoProfile, 120, "GL_3DL_array_objects", "const array"); profileRequires(line, ENoProfile, 120, "GL_3DL_array_objects", "const array");
...@@ -870,7 +906,7 @@ bool TParseContext::arraySizeRequiredErrorCheck(int line, int& size) ...@@ -870,7 +906,7 @@ bool TParseContext::arraySizeRequiredErrorCheck(int line, int& size)
// //
// Returns true if there was an error. // Returns true if there was an error.
// //
bool TParseContext::arrayErrorCheck(int line, TString& identifier, TPublicType type, TVariable*& variable) bool TParseContext::arrayErrorCheck(int line, TString& identifier, const TPublicType& type, TVariable*& variable)
{ {
// //
// Don't check for reserved word use until after we know it's not in the symbol table, // Don't check for reserved word use until after we know it's not in the symbol table,
......
...@@ -112,15 +112,15 @@ struct TParseContext { ...@@ -112,15 +112,15 @@ struct TParseContext {
bool globalErrorCheck(int line, bool global, const char* token); bool globalErrorCheck(int line, bool global, const char* token);
bool constructorErrorCheck(int line, TIntermNode*, TFunction&, TOperator, TType*); bool constructorErrorCheck(int line, TIntermNode*, TFunction&, TOperator, TType*);
bool arraySizeErrorCheck(int line, TIntermTyped* expr, int& size); bool arraySizeErrorCheck(int line, TIntermTyped* expr, int& size);
bool arrayQualifierErrorCheck(int line, TPublicType type); bool arrayQualifierErrorCheck(int line, const TPublicType&);
bool arraySizeRequiredErrorCheck(int line, int& size); bool arraySizeRequiredErrorCheck(int line, int& size);
bool arrayErrorCheck(int line, TString& identifier, TPublicType type, TVariable*& variable); bool arrayErrorCheck(int line, TString& identifier, const TPublicType&, TVariable*& variable);
bool insertBuiltInArrayAtGlobalLevel(); bool insertBuiltInArrayAtGlobalLevel();
bool voidErrorCheck(int, const TString&, const TPublicType&); bool voidErrorCheck(int, const TString&, const TPublicType&);
bool boolErrorCheck(int, const TIntermTyped*); bool boolErrorCheck(int, const TIntermTyped*);
bool boolErrorCheck(int, const TPublicType&); bool boolErrorCheck(int, const TPublicType&);
bool samplerErrorCheck(int line, const TPublicType& pType, const char* reason); bool samplerErrorCheck(int line, const TPublicType& pType, const char* reason);
bool globalQualifierFixAndErrorCheck(int line, TQualifier&); bool globalQualifierFixAndErrorCheck(int line, TQualifier&, const TPublicType&);
bool structQualifierErrorCheck(int line, const TPublicType& pType); bool structQualifierErrorCheck(int line, const TPublicType& pType);
bool mergeQualifiersErrorCheck(int line, TPublicType& left, const TPublicType& right); bool mergeQualifiersErrorCheck(int line, TPublicType& left, const TPublicType& right);
void setDefaultPrecision(int line, TPublicType&, TPrecisionQualifier); void setDefaultPrecision(int line, TPublicType&, TPrecisionQualifier);
......
...@@ -1302,9 +1302,6 @@ function_header ...@@ -1302,9 +1302,6 @@ function_header
getStorageQualifierString($1.qualifier.storage), ""); getStorageQualifierString($1.qualifier.storage), "");
parseContext.recover(); parseContext.recover();
} }
// make sure a sampler is not involved as well...
if (parseContext.structQualifierErrorCheck($2.line, $1))
parseContext.recover();
// Add the function as a prototype after parsing it (we do not support recursion) // Add the function as a prototype after parsing it (we do not support recursion)
TFunction *function; TFunction *function;
...@@ -1410,9 +1407,6 @@ init_declarator_list ...@@ -1410,9 +1407,6 @@ init_declarator_list
} }
| init_declarator_list COMMA IDENTIFIER { | init_declarator_list COMMA IDENTIFIER {
$$ = $1; $$ = $1;
if (parseContext.structQualifierErrorCheck($3.line, $$.type))
parseContext.recover();
if (parseContext.nonInitConstErrorCheck($3.line, *$3.string, $$.type)) if (parseContext.nonInitConstErrorCheck($3.line, *$3.string, $$.type))
parseContext.recover(); parseContext.recover();
...@@ -1420,9 +1414,6 @@ init_declarator_list ...@@ -1420,9 +1414,6 @@ init_declarator_list
parseContext.recover(); parseContext.recover();
} }
| init_declarator_list COMMA IDENTIFIER array_specifier { | init_declarator_list COMMA IDENTIFIER array_specifier {
if (parseContext.structQualifierErrorCheck($3.line, $1.type))
parseContext.recover();
if (parseContext.nonInitConstErrorCheck($3.line, *$3.string, $1.type)) if (parseContext.nonInitConstErrorCheck($3.line, *$3.string, $1.type))
parseContext.recover(); parseContext.recover();
...@@ -1438,9 +1429,6 @@ init_declarator_list ...@@ -1438,9 +1429,6 @@ init_declarator_list
} }
} }
| init_declarator_list COMMA IDENTIFIER array_specifier EQUAL initializer { | init_declarator_list COMMA IDENTIFIER array_specifier EQUAL initializer {
if (parseContext.structQualifierErrorCheck($3.line, $1.type))
parseContext.recover();
$$ = $1; $$ = $1;
TVariable* variable = 0; TVariable* variable = 0;
...@@ -1469,9 +1457,6 @@ init_declarator_list ...@@ -1469,9 +1457,6 @@ init_declarator_list
} }
} }
| init_declarator_list COMMA IDENTIFIER EQUAL initializer { | init_declarator_list COMMA IDENTIFIER EQUAL initializer {
if (parseContext.structQualifierErrorCheck($3.line, $1.type))
parseContext.recover();
$$ = $1; $$ = $1;
TIntermNode* intermNode; TIntermNode* intermNode;
...@@ -1494,21 +1479,11 @@ single_declaration ...@@ -1494,21 +1479,11 @@ single_declaration
: fully_specified_type { : fully_specified_type {
$$.type = $1; $$.type = $1;
$$.intermAggregate = 0; $$.intermAggregate = 0;
if (parseContext.globalQualifierFixAndErrorCheck($1.line, $1.qualifier))
parseContext.recover();
} }
| fully_specified_type IDENTIFIER { | fully_specified_type IDENTIFIER {
$$.intermAggregate = 0; $$.intermAggregate = 0;
if (parseContext.globalQualifierFixAndErrorCheck($1.line, $1.qualifier))
parseContext.recover();
$$.type = $1; $$.type = $1;
if (parseContext.structQualifierErrorCheck($2.line, $$.type))
parseContext.recover();
if (parseContext.nonInitConstErrorCheck($2.line, *$2.string, $$.type)) if (parseContext.nonInitConstErrorCheck($2.line, *$2.string, $$.type))
parseContext.recover(); parseContext.recover();
...@@ -1517,13 +1492,6 @@ single_declaration ...@@ -1517,13 +1492,6 @@ single_declaration
} }
| fully_specified_type IDENTIFIER array_specifier { | fully_specified_type IDENTIFIER array_specifier {
$$.intermAggregate = 0; $$.intermAggregate = 0;
if (parseContext.globalQualifierFixAndErrorCheck($1.line, $1.qualifier))
parseContext.recover();
if (parseContext.structQualifierErrorCheck($2.line, $1))
parseContext.recover();
if (parseContext.nonInitConstErrorCheck($2.line, *$2.string, $1)) if (parseContext.nonInitConstErrorCheck($2.line, *$2.string, $1))
parseContext.recover(); parseContext.recover();
...@@ -1540,10 +1508,6 @@ single_declaration ...@@ -1540,10 +1508,6 @@ single_declaration
} }
| fully_specified_type IDENTIFIER array_specifier EQUAL initializer { | fully_specified_type IDENTIFIER array_specifier EQUAL initializer {
$$.intermAggregate = 0; $$.intermAggregate = 0;
if (parseContext.structQualifierErrorCheck($2.line, $1))
parseContext.recover();
$$.type = $1; $$.type = $1;
TVariable* variable = 0; TVariable* variable = 0;
...@@ -1572,9 +1536,6 @@ single_declaration ...@@ -1572,9 +1536,6 @@ single_declaration
} }
} }
| fully_specified_type IDENTIFIER EQUAL initializer { | fully_specified_type IDENTIFIER EQUAL initializer {
if (parseContext.structQualifierErrorCheck($2.line, $1))
parseContext.recover();
$$.type = $1; $$.type = $1;
TIntermNode* intermNode; TIntermNode* intermNode;
...@@ -1604,6 +1565,9 @@ fully_specified_type ...@@ -1604,6 +1565,9 @@ fully_specified_type
} }
} }
| type_qualifier type_specifier { | type_qualifier type_specifier {
if (parseContext.globalQualifierFixAndErrorCheck($1.line, $1.qualifier, $2))
parseContext.recover();
if ($2.arraySizes) { if ($2.arraySizes) {
parseContext.profileRequires($2.line, ENoProfile, 120, "GL_3DL_array_objects", "arrayed type"); parseContext.profileRequires($2.line, ENoProfile, 120, "GL_3DL_array_objects", "arrayed type");
parseContext.profileRequires($2.line, EEsProfile, 300, 0, "arrayed type"); parseContext.profileRequires($2.line, EEsProfile, 300, 0, "arrayed type");
...@@ -1614,16 +1578,6 @@ fully_specified_type ...@@ -1614,16 +1578,6 @@ fully_specified_type
$2.arraySizes = 0; $2.arraySizes = 0;
} }
if ($1.qualifier.storage == EvqAttribute &&
($2.type == EbtBool || $2.type == EbtInt || $2.type == EbtUint)) {
parseContext.error($2.line, "cannot be bool or int", getStorageQualifierString($1.qualifier.storage), "");
parseContext.recover();
}
if (($1.qualifier.storage == EvqVaryingIn || $1.qualifier.storage == EvqVaryingOut) &&
($2.type == EbtBool || $2.type == EbtInt || $2.type == EbtUint)) {
parseContext.error($2.line, "cannot be bool or int", getStorageQualifierString($1.qualifier.storage), "");
parseContext.recover();
}
$$ = $2; $$ = $2;
$$.qualifier = $1.qualifier; $$.qualifier = $1.qualifier;
if ($$.qualifier.precision == EpqNone) if ($$.qualifier.precision == EpqNone)
...@@ -1747,7 +1701,7 @@ storage_qualifier ...@@ -1747,7 +1701,7 @@ storage_qualifier
parseContext.recover(); parseContext.recover();
$$.init($1.line); $$.init($1.line);
$$.qualifier.storage = EvqAttribute; $$.qualifier.storage = EvqVaryingIn;
} }
| VARYING { | VARYING {
parseContext.checkDeprecated($1.line, ENoProfile, 140, "varying"); parseContext.checkDeprecated($1.line, ENoProfile, 140, "varying");
...@@ -2790,8 +2744,6 @@ condition ...@@ -2790,8 +2744,6 @@ condition
} }
| fully_specified_type IDENTIFIER EQUAL initializer { | fully_specified_type IDENTIFIER EQUAL initializer {
TIntermNode* intermNode; TIntermNode* intermNode;
if (parseContext.structQualifierErrorCheck($2.line, $1))
parseContext.recover();
if (parseContext.boolErrorCheck($2.line, $1)) if (parseContext.boolErrorCheck($2.line, $1))
parseContext.recover(); parseContext.recover();
......
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