GLSL: Fix #1359: don't allow unsized arrays as initializers.

This commit is contained in:
John Kessenich 2018-04-23 15:18:42 -06:00
parent d8462c6f49
commit b4cb70fcd9
6 changed files with 45 additions and 17 deletions

View File

@ -109,4 +109,5 @@ uniform sampler2D s2d[];
void foo4() void foo4()
{ {
s2d[a]; // ERROR, can't variably index unsized array s2d[a]; // ERROR, can't variably index unsized array
float local[] = gUnusedUnsized; // ERROR, can initialize with runtime-sized array
} }

View File

@ -27,7 +27,8 @@ ERROR: 0:104: '=' : cannot convert from ' const float' to ' global unsized 1-el
ERROR: 0:106: 'constructor' : array argument must be sized ERROR: 0:106: 'constructor' : array argument must be sized
ERROR: 0:111: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier ERROR: 0:111: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier
ERROR: 0:111: 'variable indexing sampler array' : not supported with this profile: none ERROR: 0:111: 'variable indexing sampler array' : not supported with this profile: none
ERROR: 28 compilation errors. No code generated. ERROR: 0:112: '[]' : array initializer must be sized
ERROR: 29 compilation errors. No code generated.
Shader version: 130 Shader version: 130
@ -272,6 +273,10 @@ ERROR: node is still EOpNull!
0:111 indirect index ( temp sampler2D) 0:111 indirect index ( temp sampler2D)
0:111 's2d' ( uniform runtime-sized array of sampler2D) 0:111 's2d' ( uniform runtime-sized array of sampler2D)
0:111 'a' ( uniform int) 0:111 'a' ( uniform int)
0:112 Sequence
0:112 move second child to first child ( temp unsized 1-element array of float)
0:112 'local' ( temp unsized 1-element array of float)
0:112 'gUnusedUnsized' ( global unsized 1-element array of float)
0:? Linker Objects 0:? Linker Objects
0:? 'gu' ( global runtime-sized array of float) 0:? 'gu' ( global runtime-sized array of float)
0:? 'g4' ( global 4-element array of float) 0:? 'g4' ( global 4-element array of float)

View File

@ -31,7 +31,8 @@ ERROR: 0:104: 'variable index' : required extension not requested: GL_EXT_nonuni
ERROR: 0:105: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier ERROR: 0:105: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier
ERROR: 0:106: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier ERROR: 0:106: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier
ERROR: 0:107: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier ERROR: 0:107: 'variable index' : required extension not requested: GL_EXT_nonuniform_qualifier
ERROR: 26 compilation errors. No code generated. ERROR: 0:109: '[]' : array initializer must be sized
ERROR: 27 compilation errors. No code generated.
Shader version: 450 Shader version: 450
@ -311,6 +312,13 @@ ERROR: node is still EOpNull!
0:107 indirect index (layout( binding=9 r32f) temp imageBuffer) 0:107 indirect index (layout( binding=9 r32f) temp imageBuffer)
0:107 'storageTexelBuffer' (layout( binding=9 r32f) uniform runtime-sized array of imageBuffer) 0:107 'storageTexelBuffer' (layout( binding=9 r32f) uniform runtime-sized array of imageBuffer)
0:107 'i' ( global int) 0:107 'i' ( global int)
0:109 Sequence
0:109 move second child to first child ( temp unsized 1-element array of float)
0:109 'local' ( temp unsized 1-element array of float)
0:109 b: direct index for structure (layout( column_major shared) uniform runtime-sized array of float)
0:109 'ubuf' (layout( column_major shared) uniform block{layout( column_major shared) uniform runtime-sized array of int a, layout( column_major shared) uniform runtime-sized array of float b})
0:109 Constant:
0:109 1 (const int)
0:? Linker Objects 0:? Linker Objects
0:? 'buf' (layout( column_major shared) buffer block{layout( column_major shared) buffer runtime-sized array of int a, layout( column_major shared) buffer runtime-sized array of float b}) 0:? 'buf' (layout( column_major shared) buffer block{layout( column_major shared) buffer runtime-sized array of int a, layout( column_major shared) buffer runtime-sized array of float b})
0:? 'ubuf' (layout( column_major shared) uniform block{layout( column_major shared) uniform runtime-sized array of int a, layout( column_major shared) uniform runtime-sized array of float b}) 0:? 'ubuf' (layout( column_major shared) uniform block{layout( column_major shared) uniform runtime-sized array of int a, layout( column_major shared) uniform runtime-sized array of float b})
@ -611,6 +619,13 @@ ERROR: node is still EOpNull!
0:107 indirect index (layout( binding=9 r32f) temp imageBuffer) 0:107 indirect index (layout( binding=9 r32f) temp imageBuffer)
0:107 'storageTexelBuffer' (layout( binding=9 r32f) uniform runtime-sized array of imageBuffer) 0:107 'storageTexelBuffer' (layout( binding=9 r32f) uniform runtime-sized array of imageBuffer)
0:107 'i' ( global int) 0:107 'i' ( global int)
0:109 Sequence
0:109 move second child to first child ( temp 1-element array of float)
0:109 'local' ( temp 1-element array of float)
0:109 b: direct index for structure (layout( column_major shared) uniform runtime-sized array of float)
0:109 'ubuf' (layout( column_major shared) uniform block{layout( column_major shared) uniform runtime-sized array of int a, layout( column_major shared) uniform runtime-sized array of float b})
0:109 Constant:
0:109 1 (const int)
0:? Linker Objects 0:? Linker Objects
0:? 'buf' (layout( column_major shared) buffer block{layout( column_major shared) buffer runtime-sized array of int a, layout( column_major shared) buffer runtime-sized array of float b}) 0:? 'buf' (layout( column_major shared) buffer block{layout( column_major shared) buffer runtime-sized array of int a, layout( column_major shared) buffer runtime-sized array of float b})
0:? 'ubuf' (layout( column_major shared) uniform block{layout( column_major shared) uniform runtime-sized array of int a, layout( column_major shared) uniform runtime-sized array of float b}) 0:? 'ubuf' (layout( column_major shared) uniform block{layout( column_major shared) uniform runtime-sized array of int a, layout( column_major shared) uniform runtime-sized array of float b})

View File

@ -105,4 +105,6 @@ void main()
storageImage[i]; // ERROR, need extension storageImage[i]; // ERROR, need extension
uniformTexelBuffer[i]; // ERROR, need extension uniformTexelBuffer[i]; // ERROR, need extension
storageTexelBuffer[i]; // ERROR, need extension storageTexelBuffer[i]; // ERROR, need extension
float local[] = ubuf.b; // ERROR, can initialize with runtime-sized array
} }

View File

@ -3135,7 +3135,8 @@ void TParseContext::structArrayCheck(const TSourceLoc& /*loc*/, const TType& typ
} }
} }
void TParseContext::arraySizesCheck(const TSourceLoc& loc, const TQualifier& qualifier, TArraySizes* arraySizes, bool initializer, bool lastMember) void TParseContext::arraySizesCheck(const TSourceLoc& loc, const TQualifier& qualifier, TArraySizes* arraySizes,
const TIntermTyped* initializer, bool lastMember)
{ {
assert(arraySizes); assert(arraySizes);
@ -3143,9 +3144,13 @@ void TParseContext::arraySizesCheck(const TSourceLoc& loc, const TQualifier& qua
if (parsingBuiltins) if (parsingBuiltins)
return; return;
// always allow an initializer to set any unknown array sizes // initializer must be a sized array, in which case
if (initializer) // allow the initializer to set any unknown array sizes
if (initializer != nullptr) {
if (initializer->getType().isUnsizedArray())
error(loc, "array initializer must be sized", "[]", "");
return; return;
}
// No environment allows any non-outer-dimension to be implicitly sized // No environment allows any non-outer-dimension to be implicitly sized
if (arraySizes->isInnerUnsized()) { if (arraySizes->isInnerUnsized()) {
@ -5390,7 +5395,7 @@ TIntermNode* TParseContext::declareVariable(const TSourceLoc& loc, TString& iden
// Declare the variable // Declare the variable
if (type.isArray()) { if (type.isArray()) {
// Check that implicit sizing is only where allowed. // Check that implicit sizing is only where allowed.
arraySizesCheck(loc, type.getQualifier(), type.getArraySizes(), initializer != nullptr, false); arraySizesCheck(loc, type.getQualifier(), type.getArraySizes(), initializer, false);
if (! arrayQualifierError(loc, type.getQualifier()) && ! arrayError(loc, type)) if (! arrayQualifierError(loc, type.getQualifier()) && ! arrayError(loc, type))
declareArray(loc, identifier, type, symbol); declareArray(loc, identifier, type, symbol);
@ -5992,7 +5997,7 @@ void TParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList, con
blockStageIoCheck(loc, currentBlockQualifier); blockStageIoCheck(loc, currentBlockQualifier);
blockQualifierCheck(loc, currentBlockQualifier, instanceName != nullptr); blockQualifierCheck(loc, currentBlockQualifier, instanceName != nullptr);
if (arraySizes != nullptr) { if (arraySizes != nullptr) {
arraySizesCheck(loc, currentBlockQualifier, arraySizes, false, false); arraySizesCheck(loc, currentBlockQualifier, arraySizes, nullptr, false);
arrayOfArrayVersionCheck(loc, arraySizes); arrayOfArrayVersionCheck(loc, arraySizes);
if (arraySizes->getNumDims() > 1) if (arraySizes->getNumDims() > 1)
requireProfile(loc, ~EEsProfile, "array-of-array of block"); requireProfile(loc, ~EEsProfile, "array-of-array of block");
@ -6010,7 +6015,7 @@ void TParseContext::declareBlock(const TSourceLoc& loc, TTypeList& typeList, con
if ((currentBlockQualifier.storage == EvqUniform || currentBlockQualifier.storage == EvqBuffer) && (memberQualifier.isInterpolation() || memberQualifier.isAuxiliary())) if ((currentBlockQualifier.storage == EvqUniform || currentBlockQualifier.storage == EvqBuffer) && (memberQualifier.isInterpolation() || memberQualifier.isAuxiliary()))
error(memberLoc, "member of uniform or buffer block cannot have an auxiliary or interpolation qualifier", memberType.getFieldName().c_str(), ""); error(memberLoc, "member of uniform or buffer block cannot have an auxiliary or interpolation qualifier", memberType.getFieldName().c_str(), "");
if (memberType.isArray()) if (memberType.isArray())
arraySizesCheck(memberLoc, currentBlockQualifier, memberType.getArraySizes(), false, member == typeList.size() - 1); arraySizesCheck(memberLoc, currentBlockQualifier, memberType.getArraySizes(), nullptr, member == typeList.size() - 1);
if (memberQualifier.hasOffset()) { if (memberQualifier.hasOffset()) {
if (spvVersion.spv == 0) { if (spvVersion.spv == 0) {
requireProfile(memberLoc, ~EEsProfile, "offset on block member"); requireProfile(memberLoc, ~EEsProfile, "offset on block member");

View File

@ -340,7 +340,7 @@ public:
bool arrayError(const TSourceLoc&, const TType&); bool arrayError(const TSourceLoc&, const TType&);
void arraySizeRequiredCheck(const TSourceLoc&, const TArraySizes&); void arraySizeRequiredCheck(const TSourceLoc&, const TArraySizes&);
void structArrayCheck(const TSourceLoc&, const TType& structure); void structArrayCheck(const TSourceLoc&, const TType& structure);
void arraySizesCheck(const TSourceLoc&, const TQualifier&, TArraySizes*, bool initializer, bool lastMember); void arraySizesCheck(const TSourceLoc&, const TQualifier&, TArraySizes*, const TIntermTyped* initializer, bool lastMember);
void arrayOfArrayVersionCheck(const TSourceLoc&, const TArraySizes*); void arrayOfArrayVersionCheck(const TSourceLoc&, const TArraySizes*);
bool voidErrorCheck(const TSourceLoc&, const TString&, TBasicType); bool voidErrorCheck(const TSourceLoc&, const TString&, TBasicType);
void boolCheck(const TSourceLoc&, const TIntermTyped*); void boolCheck(const TSourceLoc&, const TIntermTyped*);