OSDN Git Service

Imported a few ES3 fixes from Angle
[android-x86/external-swiftshader.git] / src / OpenGL / compiler / ParseHelper.cpp
1 // Copyright 2016 The SwiftShader Authors. All Rights Reserved.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //    http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #include "ParseHelper.h"
16
17 #include <stdarg.h>
18 #include <stdio.h>
19
20 #include "glslang.h"
21 #include "preprocessor/SourceLocation.h"
22 #include "ValidateGlobalInitializer.h"
23 #include "ValidateSwitch.h"
24
25 ///////////////////////////////////////////////////////////////////////
26 //
27 // Sub- vector and matrix fields
28 //
29 ////////////////////////////////////////////////////////////////////////
30
31 namespace
32 {
33         bool IsVaryingOut(TQualifier qualifier)
34         {
35                 switch(qualifier)
36                 {
37                 case EvqVaryingOut:
38                 case EvqSmoothOut:
39                 case EvqFlatOut:
40                 case EvqCentroidOut:
41                 case EvqVertexOut:
42                         return true;
43
44                 default: break;
45                 }
46
47                 return false;
48         }
49
50         bool IsVaryingIn(TQualifier qualifier)
51         {
52                 switch(qualifier)
53                 {
54                 case EvqVaryingIn:
55                 case EvqSmoothIn:
56                 case EvqFlatIn:
57                 case EvqCentroidIn:
58                 case EvqFragmentIn:
59                         return true;
60
61                 default: break;
62                 }
63
64                 return false;
65         }
66
67         bool IsVarying(TQualifier qualifier)
68         {
69                 return IsVaryingIn(qualifier) || IsVaryingOut(qualifier);
70         }
71
72         bool IsAssignment(TOperator op)
73         {
74                 switch(op)
75                 {
76                 case EOpPostIncrement:
77                 case EOpPostDecrement:
78                 case EOpPreIncrement:
79                 case EOpPreDecrement:
80                 case EOpAssign:
81                 case EOpAddAssign:
82                 case EOpSubAssign:
83                 case EOpMulAssign:
84                 case EOpVectorTimesMatrixAssign:
85                 case EOpVectorTimesScalarAssign:
86                 case EOpMatrixTimesScalarAssign:
87                 case EOpMatrixTimesMatrixAssign:
88                 case EOpDivAssign:
89                 case EOpIModAssign:
90                 case EOpBitShiftLeftAssign:
91                 case EOpBitShiftRightAssign:
92                 case EOpBitwiseAndAssign:
93                 case EOpBitwiseXorAssign:
94                 case EOpBitwiseOrAssign:
95                         return true;
96                 default:
97                         return false;
98                 }
99         }
100 }
101
102 //
103 // Look at a '.' field selector string and change it into offsets
104 // for a vector.
105 //
106 bool TParseContext::parseVectorFields(const TString& compString, int vecSize, TVectorFields& fields, const TSourceLoc &line)
107 {
108         fields.num = (int) compString.size();
109         if (fields.num > 4) {
110                 error(line, "illegal vector field selection", compString.c_str());
111                 return false;
112         }
113
114         enum {
115                 exyzw,
116                 ergba,
117                 estpq
118         } fieldSet[4];
119
120         for (int i = 0; i < fields.num; ++i) {
121                 switch (compString[i])  {
122                 case 'x':
123                         fields.offsets[i] = 0;
124                         fieldSet[i] = exyzw;
125                         break;
126                 case 'r':
127                         fields.offsets[i] = 0;
128                         fieldSet[i] = ergba;
129                         break;
130                 case 's':
131                         fields.offsets[i] = 0;
132                         fieldSet[i] = estpq;
133                         break;
134                 case 'y':
135                         fields.offsets[i] = 1;
136                         fieldSet[i] = exyzw;
137                         break;
138                 case 'g':
139                         fields.offsets[i] = 1;
140                         fieldSet[i] = ergba;
141                         break;
142                 case 't':
143                         fields.offsets[i] = 1;
144                         fieldSet[i] = estpq;
145                         break;
146                 case 'z':
147                         fields.offsets[i] = 2;
148                         fieldSet[i] = exyzw;
149                         break;
150                 case 'b':
151                         fields.offsets[i] = 2;
152                         fieldSet[i] = ergba;
153                         break;
154                 case 'p':
155                         fields.offsets[i] = 2;
156                         fieldSet[i] = estpq;
157                         break;
158                 case 'w':
159                         fields.offsets[i] = 3;
160                         fieldSet[i] = exyzw;
161                         break;
162                 case 'a':
163                         fields.offsets[i] = 3;
164                         fieldSet[i] = ergba;
165                         break;
166                 case 'q':
167                         fields.offsets[i] = 3;
168                         fieldSet[i] = estpq;
169                         break;
170                 default:
171                         error(line, "illegal vector field selection", compString.c_str());
172                         return false;
173                 }
174         }
175
176         for (int i = 0; i < fields.num; ++i) {
177                 if (fields.offsets[i] >= vecSize) {
178                         error(line, "vector field selection out of range",  compString.c_str());
179                         return false;
180                 }
181
182                 if (i > 0) {
183                         if (fieldSet[i] != fieldSet[i-1]) {
184                                 error(line, "illegal - vector component fields not from the same set", compString.c_str());
185                                 return false;
186                         }
187                 }
188         }
189
190         return true;
191 }
192
193
194 //
195 // Look at a '.' field selector string and change it into offsets
196 // for a matrix.
197 //
198 bool TParseContext::parseMatrixFields(const TString& compString, int matCols, int matRows, TMatrixFields& fields, const TSourceLoc &line)
199 {
200         fields.wholeRow = false;
201         fields.wholeCol = false;
202         fields.row = -1;
203         fields.col = -1;
204
205         if (compString.size() != 2) {
206                 error(line, "illegal length of matrix field selection", compString.c_str());
207                 return false;
208         }
209
210         if (compString[0] == '_') {
211                 if (compString[1] < '0' || compString[1] > '3') {
212                         error(line, "illegal matrix field selection", compString.c_str());
213                         return false;
214                 }
215                 fields.wholeCol = true;
216                 fields.col = compString[1] - '0';
217         } else if (compString[1] == '_') {
218                 if (compString[0] < '0' || compString[0] > '3') {
219                         error(line, "illegal matrix field selection", compString.c_str());
220                         return false;
221                 }
222                 fields.wholeRow = true;
223                 fields.row = compString[0] - '0';
224         } else {
225                 if (compString[0] < '0' || compString[0] > '3' ||
226                         compString[1] < '0' || compString[1] > '3') {
227                         error(line, "illegal matrix field selection", compString.c_str());
228                         return false;
229                 }
230                 fields.row = compString[0] - '0';
231                 fields.col = compString[1] - '0';
232         }
233
234         if (fields.row >= matRows || fields.col >= matCols) {
235                 error(line, "matrix field selection out of range", compString.c_str());
236                 return false;
237         }
238
239         return true;
240 }
241
242 ///////////////////////////////////////////////////////////////////////
243 //
244 // Errors
245 //
246 ////////////////////////////////////////////////////////////////////////
247
248 //
249 // Track whether errors have occurred.
250 //
251 void TParseContext::recover()
252 {
253 }
254
255 //
256 // Used by flex/bison to output all syntax and parsing errors.
257 //
258 void TParseContext::error(const TSourceLoc& loc,
259                                                   const char* reason, const char* token,
260                                                   const char* extraInfo)
261 {
262         pp::SourceLocation srcLoc(loc.first_file, loc.first_line);
263         mDiagnostics.writeInfo(pp::Diagnostics::PP_ERROR,
264                                                    srcLoc, reason, token, extraInfo);
265
266 }
267
268 void TParseContext::warning(const TSourceLoc& loc,
269                                                         const char* reason, const char* token,
270                                                         const char* extraInfo) {
271         pp::SourceLocation srcLoc(loc.first_file, loc.first_line);
272         mDiagnostics.writeInfo(pp::Diagnostics::PP_WARNING,
273                                                    srcLoc, reason, token, extraInfo);
274 }
275
276 void TParseContext::trace(const char* str)
277 {
278         mDiagnostics.writeDebug(str);
279 }
280
281 //
282 // Same error message for all places assignments don't work.
283 //
284 void TParseContext::assignError(const TSourceLoc &line, const char* op, TString left, TString right)
285 {
286         std::stringstream extraInfoStream;
287         extraInfoStream << "cannot convert from '" << right << "' to '" << left << "'";
288         std::string extraInfo = extraInfoStream.str();
289         error(line, "", op, extraInfo.c_str());
290 }
291
292 //
293 // Same error message for all places unary operations don't work.
294 //
295 void TParseContext::unaryOpError(const TSourceLoc &line, const char* op, TString operand)
296 {
297         std::stringstream extraInfoStream;
298         extraInfoStream << "no operation '" << op << "' exists that takes an operand of type " << operand
299                                         << " (or there is no acceptable conversion)";
300         std::string extraInfo = extraInfoStream.str();
301         error(line, " wrong operand type", op, extraInfo.c_str());
302 }
303
304 //
305 // Same error message for all binary operations don't work.
306 //
307 void TParseContext::binaryOpError(const TSourceLoc &line, const char* op, TString left, TString right)
308 {
309         std::stringstream extraInfoStream;
310         extraInfoStream << "no operation '" << op << "' exists that takes a left-hand operand of type '" << left
311                                         << "' and a right operand of type '" << right << "' (or there is no acceptable conversion)";
312         std::string extraInfo = extraInfoStream.str();
313         error(line, " wrong operand types ", op, extraInfo.c_str());
314 }
315
316 bool TParseContext::precisionErrorCheck(const TSourceLoc &line, TPrecision precision, TBasicType type){
317         if (!mChecksPrecisionErrors)
318                 return false;
319         switch( type ){
320         case EbtFloat:
321                 if( precision == EbpUndefined ){
322                         error( line, "No precision specified for (float)", "" );
323                         return true;
324                 }
325                 break;
326         case EbtInt:
327                 if( precision == EbpUndefined ){
328                         error( line, "No precision specified (int)", "" );
329                         return true;
330                 }
331                 break;
332         default:
333                 return false;
334         }
335         return false;
336 }
337
338 //
339 // Both test and if necessary, spit out an error, to see if the node is really
340 // an l-value that can be operated on this way.
341 //
342 // Returns true if the was an error.
343 //
344 bool TParseContext::lValueErrorCheck(const TSourceLoc &line, const char* op, TIntermTyped* node)
345 {
346         TIntermSymbol* symNode = node->getAsSymbolNode();
347         TIntermBinary* binaryNode = node->getAsBinaryNode();
348
349         if (binaryNode) {
350                 bool errorReturn;
351
352                 switch(binaryNode->getOp()) {
353                 case EOpIndexDirect:
354                 case EOpIndexIndirect:
355                 case EOpIndexDirectStruct:
356                 case EOpIndexDirectInterfaceBlock:
357                         return lValueErrorCheck(line, op, binaryNode->getLeft());
358                 case EOpVectorSwizzle:
359                         errorReturn = lValueErrorCheck(line, op, binaryNode->getLeft());
360                         if (!errorReturn) {
361                                 int offset[4] = {0,0,0,0};
362
363                                 TIntermTyped* rightNode = binaryNode->getRight();
364                                 TIntermAggregate *aggrNode = rightNode->getAsAggregate();
365
366                                 for (TIntermSequence::iterator p = aggrNode->getSequence().begin();
367                                                                                            p != aggrNode->getSequence().end(); p++) {
368                                         int value = (*p)->getAsTyped()->getAsConstantUnion()->getIConst(0);
369                                         offset[value]++;
370                                         if (offset[value] > 1) {
371                                                 error(line, " l-value of swizzle cannot have duplicate components", op);
372
373                                                 return true;
374                                         }
375                                 }
376                         }
377
378                         return errorReturn;
379                 default:
380                         break;
381                 }
382                 error(line, " l-value required", op);
383
384                 return true;
385         }
386
387
388         const char* symbol = 0;
389         if (symNode != 0)
390                 symbol = symNode->getSymbol().c_str();
391
392         const char* message = 0;
393         switch (node->getQualifier()) {
394         case EvqConstExpr:      message = "can't modify a const";        break;
395         case EvqConstReadOnly:  message = "can't modify a const";        break;
396         case EvqAttribute:      message = "can't modify an attribute";   break;
397         case EvqFragmentIn:     message = "can't modify an input";       break;
398         case EvqVertexIn:       message = "can't modify an input";       break;
399         case EvqUniform:        message = "can't modify a uniform";      break;
400         case EvqSmoothIn:
401         case EvqFlatIn:
402         case EvqCentroidIn:
403         case EvqVaryingIn:      message = "can't modify a varying";      break;
404         case EvqInput:          message = "can't modify an input";       break;
405         case EvqFragCoord:      message = "can't modify gl_FragCoord";   break;
406         case EvqFrontFacing:    message = "can't modify gl_FrontFacing"; break;
407         case EvqPointCoord:     message = "can't modify gl_PointCoord";  break;
408         case EvqInstanceID:     message = "can't modify gl_InstanceID";  break;
409         default:
410
411                 //
412                 // Type that can't be written to?
413                 //
414                 if(IsSampler(node->getBasicType()))
415                 {
416                         message = "can't modify a sampler";
417                 }
418                 else if(node->getBasicType() == EbtVoid)
419                 {
420                         message = "can't modify void";
421                 }
422         }
423
424         if (message == 0 && binaryNode == 0 && symNode == 0) {
425                 error(line, " l-value required", op);
426
427                 return true;
428         }
429
430
431         //
432         // Everything else is okay, no error.
433         //
434         if (message == 0)
435                 return false;
436
437         //
438         // If we get here, we have an error and a message.
439         //
440         if (symNode) {
441                 std::stringstream extraInfoStream;
442                 extraInfoStream << "\"" << symbol << "\" (" << message << ")";
443                 std::string extraInfo = extraInfoStream.str();
444                 error(line, " l-value required", op, extraInfo.c_str());
445         }
446         else {
447                 std::stringstream extraInfoStream;
448                 extraInfoStream << "(" << message << ")";
449                 std::string extraInfo = extraInfoStream.str();
450                 error(line, " l-value required", op, extraInfo.c_str());
451         }
452
453         return true;
454 }
455
456 //
457 // Both test, and if necessary spit out an error, to see if the node is really
458 // a constant.
459 //
460 // Returns true if the was an error.
461 //
462 bool TParseContext::constErrorCheck(TIntermTyped* node)
463 {
464         if (node->getQualifier() == EvqConstExpr)
465                 return false;
466
467         error(node->getLine(), "constant expression required", "");
468
469         return true;
470 }
471
472 //
473 // Both test, and if necessary spit out an error, to see if the node is really
474 // an integer.
475 //
476 // Returns true if the was an error.
477 //
478 bool TParseContext::integerErrorCheck(TIntermTyped* node, const char* token)
479 {
480         if (node->isScalarInt())
481                 return false;
482
483         error(node->getLine(), "integer expression required", token);
484
485         return true;
486 }
487
488 //
489 // Both test, and if necessary spit out an error, to see if we are currently
490 // globally scoped.
491 //
492 // Returns true if the was an error.
493 //
494 bool TParseContext::globalErrorCheck(const TSourceLoc &line, bool global, const char* token)
495 {
496         if (global)
497                 return false;
498
499         error(line, "only allowed at global scope", token);
500
501         return true;
502 }
503
504 //
505 // For now, keep it simple:  if it starts "gl_", it's reserved, independent
506 // of scope.  Except, if the symbol table is at the built-in push-level,
507 // which is when we are parsing built-ins.
508 // Also checks for "webgl_" and "_webgl_" reserved identifiers if parsing a
509 // webgl shader.
510 //
511 // Returns true if there was an error.
512 //
513 bool TParseContext::reservedErrorCheck(const TSourceLoc &line, const TString& identifier)
514 {
515         static const char* reservedErrMsg = "reserved built-in name";
516         if (!symbolTable.atBuiltInLevel()) {
517                 if (identifier.compare(0, 3, "gl_") == 0) {
518                         error(line, reservedErrMsg, "gl_");
519                         return true;
520                 }
521                 if (identifier.find("__") != TString::npos) {
522                         error(line, "identifiers containing two consecutive underscores (__) are reserved as possible future keywords", identifier.c_str());
523                         return true;
524                 }
525         }
526
527         return false;
528 }
529
530 //
531 // Make sure there is enough data provided to the constructor to build
532 // something of the type of the constructor.  Also returns the type of
533 // the constructor.
534 //
535 // Returns true if there was an error in construction.
536 //
537 bool TParseContext::constructorErrorCheck(const TSourceLoc &line, TIntermNode* node, TFunction& function, TOperator op, TType* type)
538 {
539         *type = function.getReturnType();
540
541         bool constructingMatrix = false;
542         switch(op) {
543         case EOpConstructMat2:
544         case EOpConstructMat2x3:
545         case EOpConstructMat2x4:
546         case EOpConstructMat3x2:
547         case EOpConstructMat3:
548         case EOpConstructMat3x4:
549         case EOpConstructMat4x2:
550         case EOpConstructMat4x3:
551         case EOpConstructMat4:
552                 constructingMatrix = true;
553                 break;
554         default:
555                 break;
556         }
557
558         //
559         // Note: It's okay to have too many components available, but not okay to have unused
560         // arguments.  'full' will go to true when enough args have been seen.  If we loop
561         // again, there is an extra argument, so 'overfull' will become true.
562         //
563
564         size_t size = 0;
565         bool full = false;
566         bool overFull = false;
567         bool matrixInMatrix = false;
568         bool arrayArg = false;
569         for (size_t i = 0; i < function.getParamCount(); ++i) {
570                 const TParameter& param = function.getParam(i);
571                 size += param.type->getObjectSize();
572
573                 if (constructingMatrix && param.type->isMatrix())
574                         matrixInMatrix = true;
575                 if (full)
576                         overFull = true;
577                 if (op != EOpConstructStruct && !type->isArray() && size >= type->getObjectSize())
578                         full = true;
579                 if (param.type->isArray())
580                         arrayArg = true;
581         }
582
583         if(type->isArray()) {
584                 if(type->getArraySize() == 0) {
585                         type->setArraySize(function.getParamCount());
586                 } else if(type->getArraySize() != (int)function.getParamCount()) {
587                         error(line, "array constructor needs one argument per array element", "constructor");
588                         return true;
589                 }
590         }
591
592         if (arrayArg && op != EOpConstructStruct) {
593                 error(line, "constructing from a non-dereferenced array", "constructor");
594                 return true;
595         }
596
597         if (matrixInMatrix && !type->isArray()) {
598                 if (function.getParamCount() != 1) {
599                   error(line, "constructing matrix from matrix can only take one argument", "constructor");
600                   return true;
601                 }
602         }
603
604         if (overFull) {
605                 error(line, "too many arguments", "constructor");
606                 return true;
607         }
608
609         if (op == EOpConstructStruct && !type->isArray() && type->getStruct()->fields().size() != function.getParamCount()) {
610                 error(line, "Number of constructor parameters does not match the number of structure fields", "constructor");
611                 return true;
612         }
613
614         if (!type->isMatrix() || !matrixInMatrix) {
615                 if ((op != EOpConstructStruct && size != 1 && size < type->getObjectSize()) ||
616                         (op == EOpConstructStruct && size < type->getObjectSize())) {
617                         error(line, "not enough data provided for construction", "constructor");
618                         return true;
619                 }
620         }
621
622         TIntermTyped *typed = node ? node->getAsTyped() : 0;
623         if (typed == 0) {
624                 error(line, "constructor argument does not have a type", "constructor");
625                 return true;
626         }
627         if (op != EOpConstructStruct && IsSampler(typed->getBasicType())) {
628                 error(line, "cannot convert a sampler", "constructor");
629                 return true;
630         }
631         if (typed->getBasicType() == EbtVoid) {
632                 error(line, "cannot convert a void", "constructor");
633                 return true;
634         }
635
636         return false;
637 }
638
639 // This function checks to see if a void variable has been declared and raise an error message for such a case
640 //
641 // returns true in case of an error
642 //
643 bool TParseContext::voidErrorCheck(const TSourceLoc &line, const TString& identifier, const TBasicType& type)
644 {
645         if(type == EbtVoid) {
646                 error(line, "illegal use of type 'void'", identifier.c_str());
647                 return true;
648         }
649
650         return false;
651 }
652
653 // This function checks to see if the node (for the expression) contains a scalar boolean expression or not
654 //
655 // returns true in case of an error
656 //
657 bool TParseContext::boolErrorCheck(const TSourceLoc &line, const TIntermTyped* type)
658 {
659         if (type->getBasicType() != EbtBool || type->isArray() || type->isMatrix() || type->isVector()) {
660                 error(line, "boolean expression expected", "");
661                 return true;
662         }
663
664         return false;
665 }
666
667 // This function checks to see if the node (for the expression) contains a scalar boolean expression or not
668 //
669 // returns true in case of an error
670 //
671 bool TParseContext::boolErrorCheck(const TSourceLoc &line, const TPublicType& pType)
672 {
673         if (pType.type != EbtBool || pType.array || (pType.primarySize > 1) || (pType.secondarySize > 1)) {
674                 error(line, "boolean expression expected", "");
675                 return true;
676         }
677
678         return false;
679 }
680
681 bool TParseContext::samplerErrorCheck(const TSourceLoc &line, const TPublicType& pType, const char* reason)
682 {
683         if (pType.type == EbtStruct) {
684                 if (containsSampler(*pType.userDef)) {
685                         error(line, reason, getBasicString(pType.type), "(structure contains a sampler)");
686
687                         return true;
688                 }
689
690                 return false;
691         } else if (IsSampler(pType.type)) {
692                 error(line, reason, getBasicString(pType.type));
693
694                 return true;
695         }
696
697         return false;
698 }
699
700 bool TParseContext::structQualifierErrorCheck(const TSourceLoc &line, const TPublicType& pType)
701 {
702         switch(pType.qualifier)
703         {
704         case EvqVaryingOut:
705         case EvqSmooth:
706         case EvqFlat:
707         case EvqCentroidOut:
708         case EvqVaryingIn:
709         case EvqSmoothIn:
710         case EvqFlatIn:
711         case EvqCentroidIn:
712         case EvqAttribute:
713         case EvqVertexIn:
714         case EvqFragmentOut:
715                 if(pType.type == EbtStruct)
716                 {
717                         error(line, "cannot be used with a structure", getQualifierString(pType.qualifier));
718
719                         return true;
720                 }
721                 break;
722         default:
723                 break;
724         }
725
726         if (pType.qualifier != EvqUniform && samplerErrorCheck(line, pType, "samplers must be uniform"))
727                 return true;
728
729         // check for layout qualifier issues
730         if (pType.qualifier != EvqVertexIn && pType.qualifier != EvqFragmentOut &&
731                 layoutLocationErrorCheck(line, pType.layoutQualifier))
732         {
733                 return true;
734         }
735
736         return false;
737 }
738
739 // These checks are common for all declarations starting a declarator list, and declarators that follow an empty
740 // declaration.
741 //
742 bool TParseContext::singleDeclarationErrorCheck(const TPublicType &publicType, const TSourceLoc &identifierLocation)
743 {
744         switch(publicType.qualifier)
745         {
746         case EvqVaryingIn:
747         case EvqVaryingOut:
748         case EvqAttribute:
749         case EvqVertexIn:
750         case EvqFragmentOut:
751                 if(publicType.type == EbtStruct)
752                 {
753                         error(identifierLocation, "cannot be used with a structure",
754                                 getQualifierString(publicType.qualifier));
755                         return true;
756                 }
757
758         default: break;
759         }
760
761         if(publicType.qualifier != EvqUniform && samplerErrorCheck(identifierLocation, publicType,
762                 "samplers must be uniform"))
763         {
764                 return true;
765         }
766
767         // check for layout qualifier issues
768         const TLayoutQualifier layoutQualifier = publicType.layoutQualifier;
769
770         if(layoutQualifier.matrixPacking != EmpUnspecified)
771         {
772                 error(identifierLocation, "layout qualifier", getMatrixPackingString(layoutQualifier.matrixPacking),
773                         "only valid for interface blocks");
774                 return true;
775         }
776
777         if(layoutQualifier.blockStorage != EbsUnspecified)
778         {
779                 error(identifierLocation, "layout qualifier", getBlockStorageString(layoutQualifier.blockStorage),
780                         "only valid for interface blocks");
781                 return true;
782         }
783
784         if(publicType.qualifier != EvqVertexIn && publicType.qualifier != EvqFragmentOut &&
785                 layoutLocationErrorCheck(identifierLocation, publicType.layoutQualifier))
786         {
787                 return true;
788         }
789
790         return false;
791 }
792
793 bool TParseContext::layoutLocationErrorCheck(const TSourceLoc &location, const TLayoutQualifier &layoutQualifier)
794 {
795         if(layoutQualifier.location != -1)
796         {
797                 error(location, "invalid layout qualifier:", "location", "only valid on program inputs and outputs");
798                 return true;
799         }
800
801         return false;
802 }
803
804 bool TParseContext::locationDeclaratorListCheck(const TSourceLoc& line, const TPublicType &pType)
805 {
806         if(pType.layoutQualifier.location != -1)
807         {
808                 error(line, "location must only be specified for a single input or output variable", "location");
809                 return true;
810         }
811
812         return false;
813 }
814
815 bool TParseContext::parameterSamplerErrorCheck(const TSourceLoc &line, TQualifier qualifier, const TType& type)
816 {
817         if ((qualifier == EvqOut || qualifier == EvqInOut) &&
818                          type.getBasicType() != EbtStruct && IsSampler(type.getBasicType())) {
819                 error(line, "samplers cannot be output parameters", type.getBasicString());
820                 return true;
821         }
822
823         return false;
824 }
825
826 bool TParseContext::containsSampler(TType& type)
827 {
828         if (IsSampler(type.getBasicType()))
829                 return true;
830
831         if (type.getBasicType() == EbtStruct || type.isInterfaceBlock()) {
832                 const TFieldList& fields = type.getStruct()->fields();
833                 for(unsigned int i = 0; i < fields.size(); ++i) {
834                         if (containsSampler(*fields[i]->type()))
835                                 return true;
836                 }
837         }
838
839         return false;
840 }
841
842 //
843 // Do size checking for an array type's size.
844 //
845 // Returns true if there was an error.
846 //
847 bool TParseContext::arraySizeErrorCheck(const TSourceLoc &line, TIntermTyped* expr, int& size)
848 {
849         TIntermConstantUnion* constant = expr->getAsConstantUnion();
850
851         if (expr->getQualifier() != EvqConstExpr || constant == 0 || !constant->isScalarInt())
852         {
853                 error(line, "array size must be a constant integer expression", "");
854                 return true;
855         }
856
857         if (constant->getBasicType() == EbtUInt)
858         {
859                 unsigned int uintSize = constant->getUConst(0);
860                 if (uintSize > static_cast<unsigned int>(std::numeric_limits<int>::max()))
861                 {
862                         error(line, "array size too large", "");
863                         size = 1;
864                         return true;
865                 }
866
867                 size = static_cast<int>(uintSize);
868         }
869         else
870         {
871                 size = constant->getIConst(0);
872
873                 if (size < 0)
874                 {
875                         error(line, "array size must be non-negative", "");
876                         size = 1;
877                         return true;
878                 }
879         }
880
881         if(size == 0)
882         {
883                 error(line, "array size must be greater than zero", "");
884                 return true;
885         }
886
887         return false;
888 }
889
890 //
891 // See if this qualifier can be an array.
892 //
893 // Returns true if there is an error.
894 //
895 bool TParseContext::arrayQualifierErrorCheck(const TSourceLoc &line, TPublicType type)
896 {
897         if ((type.qualifier == EvqAttribute) || (type.qualifier == EvqVertexIn) || (type.qualifier == EvqConstExpr && mShaderVersion < 300)) {
898                 error(line, "cannot declare arrays of this qualifier", TType(type).getCompleteString().c_str());
899                 return true;
900         }
901
902         return false;
903 }
904
905 //
906 // See if this type can be an array.
907 //
908 // Returns true if there is an error.
909 //
910 bool TParseContext::arrayTypeErrorCheck(const TSourceLoc &line, TPublicType type)
911 {
912         //
913         // Can the type be an array?
914         //
915         if (type.array) {
916                 error(line, "cannot declare arrays of arrays", TType(type).getCompleteString().c_str());
917                 return true;
918         }
919
920         // In ESSL1.00 shaders, structs cannot be varying (section 4.3.5). This is checked elsewhere.
921         // In ESSL3.00 shaders, struct inputs/outputs are allowed but not arrays of structs (section 4.3.4).
922         if(mShaderVersion >= 300 && type.type == EbtStruct && IsVarying(type.qualifier))
923         {
924                 error(line, "cannot declare arrays of structs of this qualifier",
925                       TType(type).getCompleteString().c_str());
926                 return true;
927         }
928
929         return false;
930 }
931
932 bool TParseContext::arraySetMaxSize(TIntermSymbol *node, TType* type, int size, bool updateFlag, const TSourceLoc &line)
933 {
934         bool builtIn = false;
935         TSymbol* symbol = symbolTable.find(node->getSymbol(), mShaderVersion, &builtIn);
936         if (symbol == 0) {
937                 error(line, " undeclared identifier", node->getSymbol().c_str());
938                 return true;
939         }
940         TVariable* variable = static_cast<TVariable*>(symbol);
941
942         type->setArrayInformationType(variable->getArrayInformationType());
943         variable->updateArrayInformationType(type);
944
945         // special casing to test index value of gl_FragData. If the accessed index is >= gl_MaxDrawBuffers
946         // its an error
947         if (node->getSymbol() == "gl_FragData") {
948                 TSymbol* fragData = symbolTable.find("gl_MaxDrawBuffers", mShaderVersion, &builtIn);
949                 ASSERT(fragData);
950
951                 int fragDataValue = static_cast<TVariable*>(fragData)->getConstPointer()[0].getIConst();
952                 if (fragDataValue <= size) {
953                         error(line, "", "[", "gl_FragData can only have a max array size of up to gl_MaxDrawBuffers");
954                         return true;
955                 }
956         }
957
958         // we dont want to update the maxArraySize when this flag is not set, we just want to include this
959         // node type in the chain of node types so that its updated when a higher maxArraySize comes in.
960         if (!updateFlag)
961                 return false;
962
963         size++;
964         variable->getType().setMaxArraySize(size);
965         type->setMaxArraySize(size);
966         TType* tt = type;
967
968         while(tt->getArrayInformationType() != 0) {
969                 tt = tt->getArrayInformationType();
970                 tt->setMaxArraySize(size);
971         }
972
973         return false;
974 }
975
976 //
977 // Enforce non-initializer type/qualifier rules.
978 //
979 // Returns true if there was an error.
980 //
981 bool TParseContext::nonInitConstErrorCheck(const TSourceLoc &line, TString& identifier, TPublicType& type, bool array)
982 {
983         if (type.qualifier == EvqConstExpr)
984         {
985                 // Make the qualifier make sense.
986                 type.qualifier = EvqTemporary;
987
988                 if (array)
989                 {
990                         error(line, "arrays may not be declared constant since they cannot be initialized", identifier.c_str());
991                 }
992                 else if (type.isStructureContainingArrays())
993                 {
994                         error(line, "structures containing arrays may not be declared constant since they cannot be initialized", identifier.c_str());
995                 }
996                 else
997                 {
998                         error(line, "variables with qualifier 'const' must be initialized", identifier.c_str());
999                 }
1000
1001                 return true;
1002         }
1003
1004         return false;
1005 }
1006
1007 //
1008 // Do semantic checking for a variable declaration that has no initializer,
1009 // and update the symbol table.
1010 //
1011 // Returns true if there was an error.
1012 //
1013 bool TParseContext::nonInitErrorCheck(const TSourceLoc &line, const TString& identifier, TPublicType& type)
1014 {
1015         if(type.qualifier == EvqConstExpr)
1016         {
1017                 // Make the qualifier make sense.
1018                 type.qualifier = EvqTemporary;
1019
1020                 // Generate informative error messages for ESSL1.
1021                 // In ESSL3 arrays and structures containing arrays can be constant.
1022                 if(mShaderVersion < 300 && type.isStructureContainingArrays())
1023                 {
1024                         error(line,
1025                                 "structures containing arrays may not be declared constant since they cannot be initialized",
1026                                 identifier.c_str());
1027                 }
1028                 else
1029                 {
1030                         error(line, "variables with qualifier 'const' must be initialized", identifier.c_str());
1031                 }
1032
1033                 return true;
1034         }
1035         if(type.isUnsizedArray())
1036         {
1037                 error(line, "implicitly sized arrays need to be initialized", identifier.c_str());
1038                 return true;
1039         }
1040         return false;
1041 }
1042
1043 // Do some simple checks that are shared between all variable declarations,
1044 // and update the symbol table.
1045 //
1046 // Returns true if declaring the variable succeeded.
1047 //
1048 bool TParseContext::declareVariable(const TSourceLoc &line, const TString &identifier, const TType &type,
1049         TVariable **variable)
1050 {
1051         ASSERT((*variable) == nullptr);
1052
1053         // gl_LastFragData may be redeclared with a new precision qualifier
1054         if(type.isArray() && identifier.compare(0, 15, "gl_LastFragData") == 0)
1055         {
1056                 const TVariable *maxDrawBuffers =
1057                         static_cast<const TVariable *>(symbolTable.findBuiltIn("gl_MaxDrawBuffers", mShaderVersion));
1058                 if(type.getArraySize() != maxDrawBuffers->getConstPointer()->getIConst())
1059                 {
1060                         error(line, "redeclaration of gl_LastFragData with size != gl_MaxDrawBuffers", identifier.c_str());
1061                         return false;
1062                 }
1063         }
1064
1065         if(reservedErrorCheck(line, identifier))
1066                 return false;
1067
1068         (*variable) = new TVariable(&identifier, type);
1069         if(!symbolTable.declare(**variable))
1070         {
1071                 error(line, "redefinition", identifier.c_str());
1072                 delete (*variable);
1073                 (*variable) = nullptr;
1074                 return false;
1075         }
1076
1077         if(voidErrorCheck(line, identifier, type.getBasicType()))
1078                 return false;
1079
1080         return true;
1081 }
1082
1083 bool TParseContext::paramErrorCheck(const TSourceLoc &line, TQualifier qualifier, TQualifier paramQualifier, TType* type)
1084 {
1085         if (qualifier != EvqConstReadOnly && qualifier != EvqTemporary) {
1086                 error(line, "qualifier not allowed on function parameter", getQualifierString(qualifier));
1087                 return true;
1088         }
1089         if (qualifier == EvqConstReadOnly && paramQualifier != EvqIn) {
1090                 error(line, "qualifier not allowed with ", getQualifierString(qualifier), getQualifierString(paramQualifier));
1091                 return true;
1092         }
1093
1094         if (qualifier == EvqConstReadOnly)
1095                 type->setQualifier(EvqConstReadOnly);
1096         else
1097                 type->setQualifier(paramQualifier);
1098
1099         return false;
1100 }
1101
1102 bool TParseContext::extensionErrorCheck(const TSourceLoc &line, const TString& extension)
1103 {
1104         const TExtensionBehavior& extBehavior = extensionBehavior();
1105         TExtensionBehavior::const_iterator iter = extBehavior.find(extension.c_str());
1106         if (iter == extBehavior.end()) {
1107                 error(line, "extension", extension.c_str(), "is not supported");
1108                 return true;
1109         }
1110         // In GLSL ES, an extension's default behavior is "disable".
1111         if (iter->second == EBhDisable || iter->second == EBhUndefined) {
1112                 error(line, "extension", extension.c_str(), "is disabled");
1113                 return true;
1114         }
1115         if (iter->second == EBhWarn) {
1116                 warning(line, "extension", extension.c_str(), "is being used");
1117                 return false;
1118         }
1119
1120         return false;
1121 }
1122
1123 bool TParseContext::functionCallLValueErrorCheck(const TFunction *fnCandidate, TIntermAggregate *aggregate)
1124 {
1125         for(size_t i = 0; i < fnCandidate->getParamCount(); ++i)
1126         {
1127                 TQualifier qual = fnCandidate->getParam(i).type->getQualifier();
1128                 if(qual == EvqOut || qual == EvqInOut)
1129                 {
1130                         TIntermTyped *node = (aggregate->getSequence())[i]->getAsTyped();
1131                         if(lValueErrorCheck(node->getLine(), "assign", node))
1132                         {
1133                                 error(node->getLine(),
1134                                         "Constant value cannot be passed for 'out' or 'inout' parameters.", "Error");
1135                                 recover();
1136                                 return true;
1137                         }
1138                 }
1139         }
1140         return false;
1141 }
1142
1143 void TParseContext::es3InvariantErrorCheck(const TQualifier qualifier, const TSourceLoc &invariantLocation)
1144 {
1145         switch(qualifier)
1146         {
1147         case EvqVaryingOut:
1148         case EvqSmoothOut:
1149         case EvqFlatOut:
1150         case EvqCentroidOut:
1151         case EvqVertexOut:
1152         case EvqFragmentOut:
1153                 break;
1154         default:
1155                 error(invariantLocation, "Only out variables can be invariant.", "invariant");
1156                 recover();
1157                 break;
1158         }
1159 }
1160
1161 bool TParseContext::supportsExtension(const char* extension)
1162 {
1163         const TExtensionBehavior& extbehavior = extensionBehavior();
1164         TExtensionBehavior::const_iterator iter = extbehavior.find(extension);
1165         return (iter != extbehavior.end());
1166 }
1167
1168 void TParseContext::handleExtensionDirective(const TSourceLoc &line, const char* extName, const char* behavior)
1169 {
1170         pp::SourceLocation loc(line.first_file, line.first_line);
1171         mDirectiveHandler.handleExtension(loc, extName, behavior);
1172 }
1173
1174 void TParseContext::handlePragmaDirective(const TSourceLoc &line, const char* name, const char* value)
1175 {
1176         pp::SourceLocation loc(line.first_file, line.first_line);
1177         mDirectiveHandler.handlePragma(loc, name, value);
1178 }
1179
1180 /////////////////////////////////////////////////////////////////////////////////
1181 //
1182 // Non-Errors.
1183 //
1184 /////////////////////////////////////////////////////////////////////////////////
1185
1186 const TVariable *TParseContext::getNamedVariable(const TSourceLoc &location,
1187         const TString *name,
1188         const TSymbol *symbol)
1189 {
1190         const TVariable *variable = nullptr;
1191
1192         if(!symbol)
1193         {
1194                 error(location, "undeclared identifier", name->c_str());
1195                 recover();
1196         }
1197         else if(!symbol->isVariable())
1198         {
1199                 error(location, "variable expected", name->c_str());
1200                 recover();
1201         }
1202         else
1203         {
1204                 variable = static_cast<const TVariable*>(symbol);
1205
1206                 if(symbolTable.findBuiltIn(variable->getName(), mShaderVersion))
1207                 {
1208                         recover();
1209                 }
1210
1211                 // Reject shaders using both gl_FragData and gl_FragColor
1212                 TQualifier qualifier = variable->getType().getQualifier();
1213                 if(qualifier == EvqFragData)
1214                 {
1215                         mUsesFragData = true;
1216                 }
1217                 else if(qualifier == EvqFragColor)
1218                 {
1219                         mUsesFragColor = true;
1220                 }
1221
1222                 // This validation is not quite correct - it's only an error to write to
1223                 // both FragData and FragColor. For simplicity, and because users shouldn't
1224                 // be rewarded for reading from undefined variables, return an error
1225                 // if they are both referenced, rather than assigned.
1226                 if(mUsesFragData && mUsesFragColor)
1227                 {
1228                         error(location, "cannot use both gl_FragData and gl_FragColor", name->c_str());
1229                         recover();
1230                 }
1231         }
1232
1233         if(!variable)
1234         {
1235                 TType type(EbtFloat, EbpUndefined);
1236                 TVariable *fakeVariable = new TVariable(name, type);
1237                 symbolTable.declare(*fakeVariable);
1238                 variable = fakeVariable;
1239         }
1240
1241         return variable;
1242 }
1243
1244 //
1245 // Look up a function name in the symbol table, and make sure it is a function.
1246 //
1247 // Return the function symbol if found, otherwise 0.
1248 //
1249 const TFunction* TParseContext::findFunction(const TSourceLoc &line, TFunction* call, bool *builtIn)
1250 {
1251         // First find by unmangled name to check whether the function name has been
1252         // hidden by a variable name or struct typename.
1253         const TSymbol* symbol = symbolTable.find(call->getName(), mShaderVersion, builtIn);
1254         if (symbol == 0) {
1255                 symbol = symbolTable.find(call->getMangledName(), mShaderVersion, builtIn);
1256         }
1257
1258         if (symbol == 0) {
1259                 error(line, "no matching overloaded function found", call->getName().c_str());
1260                 return nullptr;
1261         }
1262
1263         if (!symbol->isFunction()) {
1264                 error(line, "function name expected", call->getName().c_str());
1265                 return nullptr;
1266         }
1267
1268         return static_cast<const TFunction*>(symbol);
1269 }
1270
1271 //
1272 // Initializers show up in several places in the grammar.  Have one set of
1273 // code to handle them here.
1274 //
1275 bool TParseContext::executeInitializer(const TSourceLoc& line, const TString& identifier, const TPublicType& pType,
1276                                                                            TIntermTyped *initializer, TIntermNode **intermNode)
1277 {
1278         ASSERT(intermNode != nullptr);
1279         TType type = TType(pType);
1280
1281         if(type.isUnsizedArray())
1282         {
1283                 // We have not checked yet whether the initializer actually is an array or not.
1284                 if(initializer->isArray())
1285                 {
1286                         type.setArraySize(initializer->getArraySize());
1287                 }
1288                 else
1289                 {
1290                         // Having a non-array initializer for an unsized array will result in an error later,
1291                         // so we don't generate an error message here.
1292                         type.setArraySize(1u);
1293                 }
1294         }
1295
1296         TVariable *variable = nullptr;
1297         if(!declareVariable(line, identifier, type, &variable))
1298         {
1299                 return true;
1300         }
1301
1302         bool globalInitWarning = false;
1303         if(symbolTable.atGlobalLevel() && !ValidateGlobalInitializer(initializer, this, &globalInitWarning))
1304         {
1305                 // Error message does not completely match behavior with ESSL 1.00, but
1306                 // we want to steer developers towards only using constant expressions.
1307                 error(line, "global variable initializers must be constant expressions", "=");
1308                 return true;
1309         }
1310         if(globalInitWarning)
1311         {
1312                 warning(line, "global variable initializers should be constant expressions "
1313                         "(uniforms and globals are allowed in global initializers for legacy compatibility)", "=");
1314         }
1315
1316         //
1317         // identifier must be of type constant, a global, or a temporary
1318         //
1319         TQualifier qualifier = type.getQualifier();
1320         if ((qualifier != EvqTemporary) && (qualifier != EvqGlobal) && (qualifier != EvqConstExpr)) {
1321                 error(line, " cannot initialize this type of qualifier ", variable->getType().getQualifierString());
1322                 return true;
1323         }
1324         //
1325         // test for and propagate constant
1326         //
1327
1328         if (qualifier == EvqConstExpr) {
1329                 if (qualifier != initializer->getQualifier()) {
1330                         std::stringstream extraInfoStream;
1331                         extraInfoStream << "'" << variable->getType().getCompleteString() << "'";
1332                         std::string extraInfo = extraInfoStream.str();
1333                         error(line, " assigning non-constant to", "=", extraInfo.c_str());
1334                         variable->getType().setQualifier(EvqTemporary);
1335                         return true;
1336                 }
1337
1338                 if (type != initializer->getType()) {
1339                         error(line, " non-matching types for const initializer ",
1340                                 variable->getType().getQualifierString());
1341                         variable->getType().setQualifier(EvqTemporary);
1342                         return true;
1343                 }
1344
1345                 if (initializer->getAsConstantUnion()) {
1346                         variable->shareConstPointer(initializer->getAsConstantUnion()->getUnionArrayPointer());
1347                 } else if (initializer->getAsSymbolNode()) {
1348                         const TSymbol* symbol = symbolTable.find(initializer->getAsSymbolNode()->getSymbol(), 0);
1349                         const TVariable* tVar = static_cast<const TVariable*>(symbol);
1350
1351                         ConstantUnion* constArray = tVar->getConstPointer();
1352                         variable->shareConstPointer(constArray);
1353                 }
1354         }
1355
1356         if (!variable->isConstant()) {
1357                 TIntermSymbol* intermSymbol = intermediate.addSymbol(variable->getUniqueId(), variable->getName(), variable->getType(), line);
1358                 *intermNode = createAssign(EOpInitialize, intermSymbol, initializer, line);
1359                 if(*intermNode == nullptr) {
1360                         assignError(line, "=", intermSymbol->getCompleteString(), initializer->getCompleteString());
1361                         return true;
1362                 }
1363         } else
1364                 *intermNode = nullptr;
1365
1366         return false;
1367 }
1368
1369 TPublicType TParseContext::addFullySpecifiedType(TQualifier qualifier, bool invariant, TLayoutQualifier layoutQualifier, const TPublicType &typeSpecifier)
1370 {
1371         TPublicType returnType = typeSpecifier;
1372         returnType.qualifier = qualifier;
1373         returnType.invariant = invariant;
1374         returnType.layoutQualifier = layoutQualifier;
1375
1376         if(typeSpecifier.array)
1377         {
1378                 error(typeSpecifier.line, "not supported", "first-class array");
1379                 recover();
1380                 returnType.clearArrayness();
1381         }
1382
1383         if(mShaderVersion < 300)
1384         {
1385                 if(typeSpecifier.array)
1386                 {
1387                         error(typeSpecifier.line, "not supported", "first-class array");
1388                         returnType.clearArrayness();
1389                 }
1390
1391                 if(qualifier == EvqAttribute && (typeSpecifier.type == EbtBool || typeSpecifier.type == EbtInt))
1392                 {
1393                         error(typeSpecifier.line, "cannot be bool or int", getQualifierString(qualifier));
1394                         recover();
1395                 }
1396
1397                 if((qualifier == EvqVaryingIn || qualifier == EvqVaryingOut) &&
1398                         (typeSpecifier.type == EbtBool || typeSpecifier.type == EbtInt))
1399                 {
1400                         error(typeSpecifier.line, "cannot be bool or int", getQualifierString(qualifier));
1401                         recover();
1402                 }
1403         }
1404         else
1405         {
1406                 if(!returnType.layoutQualifier.isEmpty())
1407                 {
1408                         globalErrorCheck(typeSpecifier.line, symbolTable.atGlobalLevel(), "layout");
1409                 }
1410
1411                 if(IsVarying(returnType.qualifier) || returnType.qualifier == EvqVertexIn || returnType.qualifier == EvqFragmentOut)
1412                 {
1413                         checkInputOutputTypeIsValidES3(returnType.qualifier, typeSpecifier, typeSpecifier.line);
1414                 }
1415         }
1416
1417         return returnType;
1418 }
1419
1420 void TParseContext::checkInputOutputTypeIsValidES3(const TQualifier qualifier,
1421                                                    const TPublicType &type,
1422                                                    const TSourceLoc &qualifierLocation)
1423 {
1424         // An input/output variable can never be bool or a sampler. Samplers are checked elsewhere.
1425         if(type.type == EbtBool)
1426         {
1427                 error(qualifierLocation, "cannot be bool", getQualifierString(qualifier));
1428         }
1429
1430         // Specific restrictions apply for vertex shader inputs and fragment shader outputs.
1431         switch(qualifier)
1432         {
1433         case EvqVertexIn:
1434                 // ESSL 3.00 section 4.3.4
1435                 if(type.array)
1436                 {
1437                         error(qualifierLocation, "cannot be array", getQualifierString(qualifier));
1438                 }
1439                 // Vertex inputs with a struct type are disallowed in singleDeclarationErrorCheck
1440                 return;
1441         case EvqFragmentOut:
1442                 // ESSL 3.00 section 4.3.6
1443                 if(type.isMatrix())
1444                 {
1445                         error(qualifierLocation, "cannot be matrix", getQualifierString(qualifier));
1446                 }
1447                 // Fragment outputs with a struct type are disallowed in singleDeclarationErrorCheck
1448                 return;
1449         default:
1450                 break;
1451         }
1452
1453         // Vertex shader outputs / fragment shader inputs have a different, slightly more lenient set of
1454         // restrictions.
1455         bool typeContainsIntegers = (type.type == EbtInt || type.type == EbtUInt ||
1456                                     type.isStructureContainingType(EbtInt) ||
1457                                     type.isStructureContainingType(EbtUInt));
1458         if(typeContainsIntegers && qualifier != EvqFlatIn && qualifier != EvqFlatOut)
1459         {
1460                 error(qualifierLocation, "must use 'flat' interpolation here", getQualifierString(qualifier));
1461         }
1462
1463         if(type.type == EbtStruct)
1464         {
1465                 // ESSL 3.00 sections 4.3.4 and 4.3.6.
1466                 // These restrictions are only implied by the ESSL 3.00 spec, but
1467                 // the ESSL 3.10 spec lists these restrictions explicitly.
1468                 if(type.array)
1469                 {
1470                         error(qualifierLocation, "cannot be an array of structures", getQualifierString(qualifier));
1471                 }
1472                 if(type.isStructureContainingArrays())
1473                 {
1474                         error(qualifierLocation, "cannot be a structure containing an array", getQualifierString(qualifier));
1475                 }
1476                 if(type.isStructureContainingType(EbtStruct))
1477                 {
1478                         error(qualifierLocation, "cannot be a structure containing a structure", getQualifierString(qualifier));
1479                 }
1480                 if(type.isStructureContainingType(EbtBool))
1481                 {
1482                         error(qualifierLocation, "cannot be a structure containing a bool", getQualifierString(qualifier));
1483                 }
1484         }
1485 }
1486
1487 TIntermAggregate *TParseContext::parseSingleDeclaration(TPublicType &publicType,
1488         const TSourceLoc &identifierOrTypeLocation,
1489         const TString &identifier)
1490 {
1491         TIntermSymbol *symbol = intermediate.addSymbol(0, identifier, TType(publicType), identifierOrTypeLocation);
1492
1493         bool emptyDeclaration = (identifier == "");
1494
1495         mDeferredSingleDeclarationErrorCheck = emptyDeclaration;
1496
1497         if(emptyDeclaration)
1498         {
1499                 if(publicType.isUnsizedArray())
1500                 {
1501                         // ESSL3 spec section 4.1.9: Array declaration which leaves the size unspecified is an error.
1502                         // It is assumed that this applies to empty declarations as well.
1503                         error(identifierOrTypeLocation, "empty array declaration needs to specify a size", identifier.c_str());
1504                 }
1505         }
1506         else
1507         {
1508                 if(singleDeclarationErrorCheck(publicType, identifierOrTypeLocation))
1509                         recover();
1510
1511                 if(nonInitErrorCheck(identifierOrTypeLocation, identifier, publicType))
1512                         recover();
1513
1514                 TVariable *variable = nullptr;
1515                 if(!declareVariable(identifierOrTypeLocation, identifier, TType(publicType), &variable))
1516                         recover();
1517
1518                 if(variable && symbol)
1519                         symbol->setId(variable->getUniqueId());
1520         }
1521
1522         return intermediate.makeAggregate(symbol, identifierOrTypeLocation);
1523 }
1524
1525 TIntermAggregate *TParseContext::parseSingleArrayDeclaration(TPublicType &publicType,
1526         const TSourceLoc &identifierLocation,
1527         const TString &identifier,
1528         const TSourceLoc &indexLocation,
1529         TIntermTyped *indexExpression)
1530 {
1531         mDeferredSingleDeclarationErrorCheck = false;
1532
1533         if(singleDeclarationErrorCheck(publicType, identifierLocation))
1534                 recover();
1535
1536         if(nonInitErrorCheck(identifierLocation, identifier, publicType))
1537                 recover();
1538
1539         if(arrayTypeErrorCheck(indexLocation, publicType) || arrayQualifierErrorCheck(indexLocation, publicType))
1540         {
1541                 recover();
1542         }
1543
1544         TType arrayType(publicType);
1545
1546         int size;
1547         if(arraySizeErrorCheck(identifierLocation, indexExpression, size))
1548         {
1549                 recover();
1550         }
1551         // Make the type an array even if size check failed.
1552         // This ensures useless error messages regarding the variable's non-arrayness won't follow.
1553         arrayType.setArraySize(size);
1554
1555         TVariable *variable = nullptr;
1556         if(!declareVariable(identifierLocation, identifier, arrayType, &variable))
1557                 recover();
1558
1559         TIntermSymbol *symbol = intermediate.addSymbol(0, identifier, arrayType, identifierLocation);
1560         if(variable && symbol)
1561                 symbol->setId(variable->getUniqueId());
1562
1563         return intermediate.makeAggregate(symbol, identifierLocation);
1564 }
1565
1566 TIntermAggregate *TParseContext::parseSingleInitDeclaration(const TPublicType &publicType,
1567         const TSourceLoc &identifierLocation,
1568         const TString &identifier,
1569         const TSourceLoc &initLocation,
1570         TIntermTyped *initializer)
1571 {
1572         mDeferredSingleDeclarationErrorCheck = false;
1573
1574         if(singleDeclarationErrorCheck(publicType, identifierLocation))
1575                 recover();
1576
1577         TIntermNode *intermNode = nullptr;
1578         if(!executeInitializer(identifierLocation, identifier, publicType, initializer, &intermNode))
1579         {
1580                 //
1581                 // Build intermediate representation
1582                 //
1583                 return intermNode ? intermediate.makeAggregate(intermNode, initLocation) : nullptr;
1584         }
1585         else
1586         {
1587                 recover();
1588                 return nullptr;
1589         }
1590 }
1591
1592 TIntermAggregate *TParseContext::parseSingleArrayInitDeclaration(TPublicType &publicType,
1593         const TSourceLoc &identifierLocation,
1594         const TString &identifier,
1595         const TSourceLoc &indexLocation,
1596         TIntermTyped *indexExpression,
1597         const TSourceLoc &initLocation,
1598         TIntermTyped *initializer)
1599 {
1600         mDeferredSingleDeclarationErrorCheck = false;
1601
1602         if(singleDeclarationErrorCheck(publicType, identifierLocation))
1603                 recover();
1604
1605         if(arrayTypeErrorCheck(indexLocation, publicType) || arrayQualifierErrorCheck(indexLocation, publicType))
1606         {
1607                 recover();
1608         }
1609
1610         TPublicType arrayType(publicType);
1611
1612         int size = 0;
1613         // If indexExpression is nullptr, then the array will eventually get its size implicitly from the initializer.
1614         if(indexExpression != nullptr && arraySizeErrorCheck(identifierLocation, indexExpression, size))
1615         {
1616                 recover();
1617         }
1618         // Make the type an array even if size check failed.
1619         // This ensures useless error messages regarding the variable's non-arrayness won't follow.
1620         arrayType.setArray(true, size);
1621
1622         // initNode will correspond to the whole of "type b[n] = initializer".
1623         TIntermNode *initNode = nullptr;
1624         if(!executeInitializer(identifierLocation, identifier, arrayType, initializer, &initNode))
1625         {
1626                 return initNode ? intermediate.makeAggregate(initNode, initLocation) : nullptr;
1627         }
1628         else
1629         {
1630                 recover();
1631                 return nullptr;
1632         }
1633 }
1634
1635 TIntermAggregate *TParseContext::parseInvariantDeclaration(const TSourceLoc &invariantLoc,
1636         const TSourceLoc &identifierLoc,
1637         const TString *identifier,
1638         const TSymbol *symbol)
1639 {
1640         // invariant declaration
1641         if(globalErrorCheck(invariantLoc, symbolTable.atGlobalLevel(), "invariant varying"))
1642         {
1643                 recover();
1644         }
1645
1646         if(!symbol)
1647         {
1648                 error(identifierLoc, "undeclared identifier declared as invariant", identifier->c_str());
1649                 recover();
1650                 return nullptr;
1651         }
1652         else
1653         {
1654                 const TString kGlFrontFacing("gl_FrontFacing");
1655                 if(*identifier == kGlFrontFacing)
1656                 {
1657                         error(identifierLoc, "identifier should not be declared as invariant", identifier->c_str());
1658                         recover();
1659                         return nullptr;
1660                 }
1661                 symbolTable.addInvariantVarying(std::string(identifier->c_str()));
1662                 const TVariable *variable = getNamedVariable(identifierLoc, identifier, symbol);
1663                 ASSERT(variable);
1664                 const TType &type = variable->getType();
1665                 TIntermSymbol *intermSymbol = intermediate.addSymbol(variable->getUniqueId(),
1666                         *identifier, type, identifierLoc);
1667
1668                 TIntermAggregate *aggregate = intermediate.makeAggregate(intermSymbol, identifierLoc);
1669                 aggregate->setOp(EOpInvariantDeclaration);
1670                 return aggregate;
1671         }
1672 }
1673
1674 TIntermAggregate *TParseContext::parseDeclarator(TPublicType &publicType, TIntermAggregate *aggregateDeclaration,
1675         const TSourceLoc &identifierLocation, const TString &identifier)
1676 {
1677         // If the declaration starting this declarator list was empty (example: int,), some checks were not performed.
1678         if(mDeferredSingleDeclarationErrorCheck)
1679         {
1680                 if(singleDeclarationErrorCheck(publicType, identifierLocation))
1681                         recover();
1682                 mDeferredSingleDeclarationErrorCheck = false;
1683         }
1684
1685         if(locationDeclaratorListCheck(identifierLocation, publicType))
1686                 recover();
1687
1688         if(nonInitErrorCheck(identifierLocation, identifier, publicType))
1689                 recover();
1690
1691         TVariable *variable = nullptr;
1692         if(!declareVariable(identifierLocation, identifier, TType(publicType), &variable))
1693                 recover();
1694
1695         TIntermSymbol *symbol = intermediate.addSymbol(0, identifier, TType(publicType), identifierLocation);
1696         if(variable && symbol)
1697                 symbol->setId(variable->getUniqueId());
1698
1699         return intermediate.growAggregate(aggregateDeclaration, symbol, identifierLocation);
1700 }
1701
1702 TIntermAggregate *TParseContext::parseArrayDeclarator(TPublicType &publicType, TIntermAggregate *aggregateDeclaration,
1703         const TSourceLoc &identifierLocation, const TString &identifier,
1704         const TSourceLoc &arrayLocation, TIntermTyped *indexExpression)
1705 {
1706         // If the declaration starting this declarator list was empty (example: int,), some checks were not performed.
1707         if(mDeferredSingleDeclarationErrorCheck)
1708         {
1709                 if(singleDeclarationErrorCheck(publicType, identifierLocation))
1710                         recover();
1711                 mDeferredSingleDeclarationErrorCheck = false;
1712         }
1713
1714         if(locationDeclaratorListCheck(identifierLocation, publicType))
1715                 recover();
1716
1717         if(nonInitErrorCheck(identifierLocation, identifier, publicType))
1718                 recover();
1719
1720         if(arrayTypeErrorCheck(arrayLocation, publicType) || arrayQualifierErrorCheck(arrayLocation, publicType))
1721         {
1722                 recover();
1723         }
1724         else
1725         {
1726                 TType arrayType = TType(publicType);
1727                 int size;
1728                 if(arraySizeErrorCheck(arrayLocation, indexExpression, size))
1729                 {
1730                         recover();
1731                 }
1732                 arrayType.setArraySize(size);
1733
1734                 TVariable *variable = nullptr;
1735                 if(!declareVariable(identifierLocation, identifier, arrayType, &variable))
1736                         recover();
1737
1738                 TIntermSymbol *symbol = intermediate.addSymbol(0, identifier, arrayType, identifierLocation);
1739                 if(variable && symbol)
1740                         symbol->setId(variable->getUniqueId());
1741
1742                 return intermediate.growAggregate(aggregateDeclaration, symbol, identifierLocation);
1743         }
1744
1745         return nullptr;
1746 }
1747
1748 TIntermAggregate *TParseContext::parseInitDeclarator(const TPublicType &publicType, TIntermAggregate *aggregateDeclaration,
1749         const TSourceLoc &identifierLocation, const TString &identifier,
1750         const TSourceLoc &initLocation, TIntermTyped *initializer)
1751 {
1752         // If the declaration starting this declarator list was empty (example: int,), some checks were not performed.
1753         if(mDeferredSingleDeclarationErrorCheck)
1754         {
1755                 if(singleDeclarationErrorCheck(publicType, identifierLocation))
1756                         recover();
1757                 mDeferredSingleDeclarationErrorCheck = false;
1758         }
1759
1760         if(locationDeclaratorListCheck(identifierLocation, publicType))
1761                 recover();
1762
1763         TIntermNode *intermNode = nullptr;
1764         if(!executeInitializer(identifierLocation, identifier, publicType, initializer, &intermNode))
1765         {
1766                 //
1767                 // build the intermediate representation
1768                 //
1769                 if(intermNode)
1770                 {
1771                         return intermediate.growAggregate(aggregateDeclaration, intermNode, initLocation);
1772                 }
1773                 else
1774                 {
1775                         return aggregateDeclaration;
1776                 }
1777         }
1778         else
1779         {
1780                 recover();
1781                 return nullptr;
1782         }
1783 }
1784
1785 TIntermAggregate *TParseContext::parseArrayInitDeclarator(const TPublicType &publicType,
1786         TIntermAggregate *aggregateDeclaration,
1787         const TSourceLoc &identifierLocation,
1788         const TString &identifier,
1789         const TSourceLoc &indexLocation,
1790         TIntermTyped *indexExpression,
1791         const TSourceLoc &initLocation, TIntermTyped *initializer)
1792 {
1793         // If the declaration starting this declarator list was empty (example: int,), some checks were not performed.
1794         if(mDeferredSingleDeclarationErrorCheck)
1795         {
1796                 if(singleDeclarationErrorCheck(publicType, identifierLocation))
1797                         recover();
1798                 mDeferredSingleDeclarationErrorCheck = false;
1799         }
1800
1801         if(locationDeclaratorListCheck(identifierLocation, publicType))
1802                 recover();
1803
1804         if(arrayTypeErrorCheck(indexLocation, publicType) || arrayQualifierErrorCheck(indexLocation, publicType))
1805         {
1806                 recover();
1807         }
1808
1809         TPublicType arrayType(publicType);
1810
1811         int size = 0;
1812         // If indexExpression is nullptr, then the array will eventually get its size implicitly from the initializer.
1813         if(indexExpression != nullptr && arraySizeErrorCheck(identifierLocation, indexExpression, size))
1814         {
1815                 recover();
1816         }
1817         // Make the type an array even if size check failed.
1818         // This ensures useless error messages regarding the variable's non-arrayness won't follow.
1819         arrayType.setArray(true, size);
1820
1821         // initNode will correspond to the whole of "b[n] = initializer".
1822         TIntermNode *initNode = nullptr;
1823         if(!executeInitializer(identifierLocation, identifier, arrayType, initializer, &initNode))
1824         {
1825                 if(initNode)
1826                 {
1827                         return intermediate.growAggregate(aggregateDeclaration, initNode, initLocation);
1828                 }
1829                 else
1830                 {
1831                         return aggregateDeclaration;
1832                 }
1833         }
1834         else
1835         {
1836                 recover();
1837                 return nullptr;
1838         }
1839 }
1840
1841 void TParseContext::parseGlobalLayoutQualifier(const TPublicType &typeQualifier)
1842 {
1843         if(mShaderVersion < 300)
1844         {
1845                 error(typeQualifier.line, "layout qualifiers supported in GLSL ES 3.00 only", "layout");
1846                 recover();
1847                 return;
1848         }
1849
1850         if(typeQualifier.qualifier != EvqUniform)
1851         {
1852                 error(typeQualifier.line, "invalid qualifier:", getQualifierString(typeQualifier.qualifier), "global layout must be uniform");
1853                 recover();
1854                 return;
1855         }
1856
1857         const TLayoutQualifier layoutQualifier = typeQualifier.layoutQualifier;
1858         ASSERT(!layoutQualifier.isEmpty());
1859
1860         if(layoutLocationErrorCheck(typeQualifier.line, typeQualifier.layoutQualifier))
1861         {
1862                 recover();
1863                 return;
1864         }
1865
1866         if(layoutQualifier.matrixPacking != EmpUnspecified)
1867         {
1868                 mDefaultMatrixPacking = layoutQualifier.matrixPacking;
1869         }
1870
1871         if(layoutQualifier.blockStorage != EbsUnspecified)
1872         {
1873                 mDefaultBlockStorage = layoutQualifier.blockStorage;
1874         }
1875 }
1876
1877 TIntermAggregate *TParseContext::addFunctionPrototypeDeclaration(const TFunction &function, const TSourceLoc &location)
1878 {
1879         // Note: symbolTableFunction could be the same as function if this is the first declaration.
1880         // Either way the instance in the symbol table is used to track whether the function is declared
1881         // multiple times.
1882         TFunction *symbolTableFunction =
1883                 static_cast<TFunction *>(symbolTable.find(function.getMangledName(), getShaderVersion()));
1884         if(symbolTableFunction->hasPrototypeDeclaration() && mShaderVersion == 100)
1885         {
1886                 // ESSL 1.00.17 section 4.2.7.
1887                 // Doesn't apply to ESSL 3.00.4: see section 4.2.3.
1888                 error(location, "duplicate function prototype declarations are not allowed", "function");
1889                 recover();
1890         }
1891         symbolTableFunction->setHasPrototypeDeclaration();
1892
1893         TIntermAggregate *prototype = new TIntermAggregate;
1894         prototype->setType(function.getReturnType());
1895         prototype->setName(function.getMangledName());
1896
1897         for(size_t i = 0; i < function.getParamCount(); i++)
1898         {
1899                 const TParameter &param = function.getParam(i);
1900                 if(param.name != 0)
1901                 {
1902                         TVariable variable(param.name, *param.type);
1903
1904                         TIntermSymbol *paramSymbol = intermediate.addSymbol(
1905                                 variable.getUniqueId(), variable.getName(), variable.getType(), location);
1906                         prototype = intermediate.growAggregate(prototype, paramSymbol, location);
1907                 }
1908                 else
1909                 {
1910                         TIntermSymbol *paramSymbol = intermediate.addSymbol(0, "", *param.type, location);
1911                         prototype = intermediate.growAggregate(prototype, paramSymbol, location);
1912                 }
1913         }
1914
1915         prototype->setOp(EOpPrototype);
1916
1917         symbolTable.pop();
1918
1919         if(!symbolTable.atGlobalLevel())
1920         {
1921                 // ESSL 3.00.4 section 4.2.4.
1922                 error(location, "local function prototype declarations are not allowed", "function");
1923                 recover();
1924         }
1925
1926         return prototype;
1927 }
1928
1929 TIntermAggregate *TParseContext::addFunctionDefinition(const TFunction &function, TIntermAggregate *functionPrototype, TIntermAggregate *functionBody, const TSourceLoc &location)
1930 {
1931         //?? Check that all paths return a value if return type != void ?
1932         //   May be best done as post process phase on intermediate code
1933         if(mCurrentFunctionType->getBasicType() != EbtVoid && !mFunctionReturnsValue)
1934         {
1935                 error(location, "function does not return a value:", "", function.getName().c_str());
1936                 recover();
1937         }
1938
1939         TIntermAggregate *aggregate = intermediate.growAggregate(functionPrototype, functionBody, location);
1940         intermediate.setAggregateOperator(aggregate, EOpFunction, location);
1941         aggregate->setName(function.getMangledName().c_str());
1942         aggregate->setType(function.getReturnType());
1943
1944         // store the pragma information for debug and optimize and other vendor specific
1945         // information. This information can be queried from the parse tree
1946         aggregate->setOptimize(pragma().optimize);
1947         aggregate->setDebug(pragma().debug);
1948
1949         if(functionBody && functionBody->getAsAggregate())
1950                 aggregate->setEndLine(functionBody->getAsAggregate()->getEndLine());
1951
1952         symbolTable.pop();
1953         return aggregate;
1954 }
1955
1956 void TParseContext::parseFunctionPrototype(const TSourceLoc &location, TFunction *function, TIntermAggregate **aggregateOut)
1957 {
1958         const TSymbol *builtIn = symbolTable.findBuiltIn(function->getMangledName(), getShaderVersion());
1959
1960         if(builtIn)
1961         {
1962                 error(location, "built-in functions cannot be redefined", function->getName().c_str());
1963                 recover();
1964         }
1965
1966         TFunction *prevDec = static_cast<TFunction *>(symbolTable.find(function->getMangledName(), getShaderVersion()));
1967         //
1968         // Note:  'prevDec' could be 'function' if this is the first time we've seen function
1969         // as it would have just been put in the symbol table.  Otherwise, we're looking up
1970         // an earlier occurance.
1971         //
1972         if(prevDec->isDefined())
1973         {
1974                 // Then this function already has a body.
1975                 error(location, "function already has a body", function->getName().c_str());
1976                 recover();
1977         }
1978         prevDec->setDefined();
1979         //
1980         // Overload the unique ID of the definition to be the same unique ID as the declaration.
1981         // Eventually we will probably want to have only a single definition and just swap the
1982         // arguments to be the definition's arguments.
1983         //
1984         function->setUniqueId(prevDec->getUniqueId());
1985
1986         // Raise error message if main function takes any parameters or return anything other than void
1987         if(function->getName() == "main")
1988         {
1989                 if(function->getParamCount() > 0)
1990                 {
1991                         error(location, "function cannot take any parameter(s)", function->getName().c_str());
1992                         recover();
1993                 }
1994                 if(function->getReturnType().getBasicType() != EbtVoid)
1995                 {
1996                         error(location, "", function->getReturnType().getBasicString(), "main function cannot return a value");
1997                         recover();
1998                 }
1999         }
2000
2001         //
2002         // Remember the return type for later checking for RETURN statements.
2003         //
2004         mCurrentFunctionType = &(prevDec->getReturnType());
2005         mFunctionReturnsValue = false;
2006
2007         //
2008         // Insert parameters into the symbol table.
2009         // If the parameter has no name, it's not an error, just don't insert it
2010         // (could be used for unused args).
2011         //
2012         // Also, accumulate the list of parameters into the HIL, so lower level code
2013         // knows where to find parameters.
2014         //
2015         TIntermAggregate *paramNodes = new TIntermAggregate;
2016         for(size_t i = 0; i < function->getParamCount(); i++)
2017         {
2018                 const TParameter &param = function->getParam(i);
2019                 if(param.name != 0)
2020                 {
2021                         TVariable *variable = new TVariable(param.name, *param.type);
2022                         //
2023                         // Insert the parameters with name in the symbol table.
2024                         //
2025                         if(!symbolTable.declare(*variable))
2026                         {
2027                                 error(location, "redefinition", variable->getName().c_str());
2028                                 recover();
2029                                 paramNodes = intermediate.growAggregate(
2030                                         paramNodes, intermediate.addSymbol(0, "", *param.type, location), location);
2031                                 continue;
2032                         }
2033
2034                         //
2035                         // Add the parameter to the HIL
2036                         //
2037                         TIntermSymbol *symbol = intermediate.addSymbol(
2038                                 variable->getUniqueId(), variable->getName(), variable->getType(), location);
2039
2040                         paramNodes = intermediate.growAggregate(paramNodes, symbol, location);
2041                 }
2042                 else
2043                 {
2044                         paramNodes = intermediate.growAggregate(
2045                                 paramNodes, intermediate.addSymbol(0, "", *param.type, location), location);
2046                 }
2047         }
2048         intermediate.setAggregateOperator(paramNodes, EOpParameters, location);
2049         *aggregateOut = paramNodes;
2050         setLoopNestingLevel(0);
2051 }
2052
2053 TFunction *TParseContext::parseFunctionDeclarator(const TSourceLoc &location, TFunction *function)
2054 {
2055         //
2056         // We don't know at this point whether this is a function definition or a prototype.
2057         // The definition production code will check for redefinitions.
2058         // In the case of ESSL 1.00 the prototype production code will also check for redeclarations.
2059         //
2060         // Return types and parameter qualifiers must match in all redeclarations, so those are checked
2061         // here.
2062         //
2063         TFunction *prevDec = static_cast<TFunction *>(symbolTable.find(function->getMangledName(), getShaderVersion()));
2064         if(getShaderVersion() >= 300 && symbolTable.hasUnmangledBuiltIn(function->getName().c_str()))
2065         {
2066                 // With ESSL 3.00, names of built-in functions cannot be redeclared as functions.
2067                 // Therefore overloading or redefining builtin functions is an error.
2068                 error(location, "Name of a built-in function cannot be redeclared as function", function->getName().c_str());
2069         }
2070         else if(prevDec)
2071         {
2072                 if(prevDec->getReturnType() != function->getReturnType())
2073                 {
2074                         error(location, "overloaded functions must have the same return type",
2075                                 function->getReturnType().getBasicString());
2076                         recover();
2077                 }
2078                 for(size_t i = 0; i < prevDec->getParamCount(); ++i)
2079                 {
2080                         if(prevDec->getParam(i).type->getQualifier() != function->getParam(i).type->getQualifier())
2081                         {
2082                                 error(location, "overloaded functions must have the same parameter qualifiers",
2083                                         function->getParam(i).type->getQualifierString());
2084                                 recover();
2085                         }
2086                 }
2087         }
2088
2089         //
2090         // Check for previously declared variables using the same name.
2091         //
2092         TSymbol *prevSym = symbolTable.find(function->getName(), getShaderVersion());
2093         if(prevSym)
2094         {
2095                 if(!prevSym->isFunction())
2096                 {
2097                         error(location, "redefinition", function->getName().c_str(), "function");
2098                         recover();
2099                 }
2100         }
2101
2102         // We're at the inner scope level of the function's arguments and body statement.
2103         // Add the function prototype to the surrounding scope instead.
2104         symbolTable.getOuterLevel()->insert(*function);
2105
2106         //
2107         // If this is a redeclaration, it could also be a definition, in which case, we want to use the
2108         // variable names from this one, and not the one that's
2109         // being redeclared.  So, pass back up this declaration, not the one in the symbol table.
2110         //
2111         return function;
2112 }
2113
2114 TFunction *TParseContext::addConstructorFunc(const TPublicType &publicTypeIn)
2115 {
2116         TPublicType publicType = publicTypeIn;
2117         TOperator op = EOpNull;
2118         if(publicType.userDef)
2119         {
2120                 op = EOpConstructStruct;
2121         }
2122         else
2123         {
2124                 op = TypeToConstructorOperator(TType(publicType));
2125                 if(op == EOpNull)
2126                 {
2127                         error(publicType.line, "cannot construct this type", getBasicString(publicType.type));
2128                         recover();
2129                         publicType.type = EbtFloat;
2130                         op = EOpConstructFloat;
2131                 }
2132         }
2133
2134         TString tempString;
2135         TType type(publicType);
2136         return new TFunction(&tempString, type, op);
2137 }
2138
2139 // This function is used to test for the correctness of the parameters passed to various constructor functions
2140 // and also convert them to the right datatype if it is allowed and required.
2141 //
2142 // Returns 0 for an error or the constructed node (aggregate or typed) for no error.
2143 //
2144 TIntermTyped* TParseContext::addConstructor(TIntermNode* arguments, const TType* type, TOperator op, TFunction* fnCall, const TSourceLoc &line)
2145 {
2146         TIntermAggregate *aggregateArguments = arguments->getAsAggregate();
2147
2148         if(!aggregateArguments)
2149         {
2150                 aggregateArguments = new TIntermAggregate;
2151                 aggregateArguments->getSequence().push_back(arguments);
2152         }
2153
2154         if(type->isArray())
2155         {
2156                 // GLSL ES 3.00 section 5.4.4: Each argument must be the same type as the element type of
2157                 // the array.
2158                 for(TIntermNode *&argNode : aggregateArguments->getSequence())
2159                 {
2160                         const TType &argType = argNode->getAsTyped()->getType();
2161                         // It has already been checked that the argument is not an array.
2162                         ASSERT(!argType.isArray());
2163                         if(!argType.sameElementType(*type))
2164                         {
2165                                 error(line, "Array constructor argument has an incorrect type", "Error");
2166                                 return nullptr;
2167                         }
2168                 }
2169         }
2170         else if(op == EOpConstructStruct)
2171         {
2172                 const TFieldList &fields = type->getStruct()->fields();
2173                 TIntermSequence &args = aggregateArguments->getSequence();
2174
2175                 for(size_t i = 0; i < fields.size(); i++)
2176                 {
2177                         if(args[i]->getAsTyped()->getType() != *fields[i]->type())
2178                         {
2179                                 error(line, "Structure constructor arguments do not match structure fields", "Error");
2180                                 recover();
2181
2182                                 return nullptr;
2183                         }
2184                 }
2185         }
2186
2187         // Turn the argument list itself into a constructor
2188         TIntermAggregate *constructor = intermediate.setAggregateOperator(aggregateArguments, op, line);
2189         TIntermTyped *constConstructor = foldConstConstructor(constructor, *type);
2190         if(constConstructor)
2191         {
2192                 return constConstructor;
2193         }
2194
2195         return constructor;
2196 }
2197
2198 TIntermTyped* TParseContext::foldConstConstructor(TIntermAggregate* aggrNode, const TType& type)
2199 {
2200         aggrNode->setType(type);
2201         if (aggrNode->isConstantFoldable()) {
2202                 bool returnVal = false;
2203                 ConstantUnion* unionArray = new ConstantUnion[type.getObjectSize()];
2204                 if (aggrNode->getSequence().size() == 1)  {
2205                         returnVal = intermediate.parseConstTree(aggrNode->getLine(), aggrNode, unionArray, aggrNode->getOp(), type, true);
2206                 }
2207                 else {
2208                         returnVal = intermediate.parseConstTree(aggrNode->getLine(), aggrNode, unionArray, aggrNode->getOp(), type);
2209                 }
2210                 if (returnVal)
2211                         return nullptr;
2212
2213                 return intermediate.addConstantUnion(unionArray, type, aggrNode->getLine());
2214         }
2215
2216         return nullptr;
2217 }
2218
2219 //
2220 // This function returns the tree representation for the vector field(s) being accessed from contant vector.
2221 // If only one component of vector is accessed (v.x or v[0] where v is a contant vector), then a contant node is
2222 // returned, else an aggregate node is returned (for v.xy). The input to this function could either be the symbol
2223 // node or it could be the intermediate tree representation of accessing fields in a constant structure or column of
2224 // a constant matrix.
2225 //
2226 TIntermTyped* TParseContext::addConstVectorNode(TVectorFields& fields, TIntermTyped* node, const TSourceLoc &line)
2227 {
2228         TIntermTyped* typedNode;
2229         TIntermConstantUnion* tempConstantNode = node->getAsConstantUnion();
2230
2231         ConstantUnion *unionArray;
2232         if (tempConstantNode) {
2233                 unionArray = tempConstantNode->getUnionArrayPointer();
2234
2235                 if (!unionArray) {
2236                         return node;
2237                 }
2238         } else { // The node has to be either a symbol node or an aggregate node or a tempConstant node, else, its an error
2239                 error(line, "Cannot offset into the vector", "Error");
2240                 recover();
2241
2242                 return nullptr;
2243         }
2244
2245         ConstantUnion* constArray = new ConstantUnion[fields.num];
2246
2247         int objSize = static_cast<int>(node->getType().getObjectSize());
2248         for (int i = 0; i < fields.num; i++) {
2249                 if (fields.offsets[i] >= objSize) {
2250                         std::stringstream extraInfoStream;
2251                         extraInfoStream << "vector field selection out of range '" << fields.offsets[i] << "'";
2252                         std::string extraInfo = extraInfoStream.str();
2253                         error(line, "", "[", extraInfo.c_str());
2254                         recover();
2255                         fields.offsets[i] = 0;
2256                 }
2257
2258                 constArray[i] = unionArray[fields.offsets[i]];
2259
2260         }
2261         typedNode = intermediate.addConstantUnion(constArray, node->getType(), line);
2262         return typedNode;
2263 }
2264
2265 //
2266 // This function returns the column being accessed from a constant matrix. The values are retrieved from
2267 // the symbol table and parse-tree is built for a vector (each column of a matrix is a vector). The input
2268 // to the function could either be a symbol node (m[0] where m is a constant matrix)that represents a
2269 // constant matrix or it could be the tree representation of the constant matrix (s.m1[0] where s is a constant structure)
2270 //
2271 TIntermTyped* TParseContext::addConstMatrixNode(int index, TIntermTyped* node, const TSourceLoc &line)
2272 {
2273         TIntermTyped* typedNode;
2274         TIntermConstantUnion* tempConstantNode = node->getAsConstantUnion();
2275
2276         if (index >= node->getType().getNominalSize()) {
2277                 std::stringstream extraInfoStream;
2278                 extraInfoStream << "matrix field selection out of range '" << index << "'";
2279                 std::string extraInfo = extraInfoStream.str();
2280                 error(line, "", "[", extraInfo.c_str());
2281                 recover();
2282                 index = 0;
2283         }
2284
2285         if (tempConstantNode) {
2286                  ConstantUnion* unionArray = tempConstantNode->getUnionArrayPointer();
2287                  int size = tempConstantNode->getType().getNominalSize();
2288                  typedNode = intermediate.addConstantUnion(&unionArray[size*index], tempConstantNode->getType(), line);
2289         } else {
2290                 error(line, "Cannot offset into the matrix", "Error");
2291                 recover();
2292
2293                 return nullptr;
2294         }
2295
2296         return typedNode;
2297 }
2298
2299
2300 //
2301 // This function returns an element of an array accessed from a constant array. The values are retrieved from
2302 // the symbol table and parse-tree is built for the type of the element. The input
2303 // to the function could either be a symbol node (a[0] where a is a constant array)that represents a
2304 // constant array or it could be the tree representation of the constant array (s.a1[0] where s is a constant structure)
2305 //
2306 TIntermTyped* TParseContext::addConstArrayNode(int index, TIntermTyped* node, const TSourceLoc &line)
2307 {
2308         TIntermTyped* typedNode;
2309         TIntermConstantUnion* tempConstantNode = node->getAsConstantUnion();
2310         TType arrayElementType = node->getType();
2311         arrayElementType.clearArrayness();
2312
2313         if (index >= node->getType().getArraySize()) {
2314                 std::stringstream extraInfoStream;
2315                 extraInfoStream << "array field selection out of range '" << index << "'";
2316                 std::string extraInfo = extraInfoStream.str();
2317                 error(line, "", "[", extraInfo.c_str());
2318                 recover();
2319                 index = 0;
2320         }
2321
2322         size_t arrayElementSize = arrayElementType.getObjectSize();
2323
2324         if (tempConstantNode) {
2325                  ConstantUnion* unionArray = tempConstantNode->getUnionArrayPointer();
2326                  typedNode = intermediate.addConstantUnion(&unionArray[arrayElementSize * index], tempConstantNode->getType(), line);
2327         } else {
2328                 error(line, "Cannot offset into the array", "Error");
2329                 recover();
2330
2331                 return nullptr;
2332         }
2333
2334         return typedNode;
2335 }
2336
2337
2338 //
2339 // This function returns the value of a particular field inside a constant structure from the symbol table.
2340 // If there is an embedded/nested struct, it appropriately calls addConstStructNested or addConstStructFromAggr
2341 // function and returns the parse-tree with the values of the embedded/nested struct.
2342 //
2343 TIntermTyped* TParseContext::addConstStruct(const TString& identifier, TIntermTyped* node, const TSourceLoc &line)
2344 {
2345         const TFieldList &fields = node->getType().getStruct()->fields();
2346         TIntermTyped *typedNode;
2347         size_t instanceSize = 0;
2348         TIntermConstantUnion *tempConstantNode = node->getAsConstantUnion();
2349
2350         for(size_t index = 0; index < fields.size(); ++index) {
2351                 if (fields[index]->name() == identifier) {
2352                         break;
2353                 } else {
2354                         instanceSize += fields[index]->type()->getObjectSize();
2355                 }
2356         }
2357
2358         if (tempConstantNode) {
2359                  ConstantUnion* constArray = tempConstantNode->getUnionArrayPointer();
2360
2361                  typedNode = intermediate.addConstantUnion(constArray+instanceSize, tempConstantNode->getType(), line); // type will be changed in the calling function
2362         } else {
2363                 error(line, "Cannot offset into the structure", "Error");
2364                 recover();
2365
2366                 return nullptr;
2367         }
2368
2369         return typedNode;
2370 }
2371
2372 //
2373 // Interface/uniform blocks
2374 //
2375 TIntermAggregate* TParseContext::addInterfaceBlock(const TPublicType& typeQualifier, const TSourceLoc& nameLine, const TString& blockName, TFieldList* fieldList,
2376                                                                                                    const TString* instanceName, const TSourceLoc& instanceLine, TIntermTyped* arrayIndex, const TSourceLoc& arrayIndexLine)
2377 {
2378         if(reservedErrorCheck(nameLine, blockName))
2379                 recover();
2380
2381         if(typeQualifier.qualifier != EvqUniform)
2382         {
2383                 error(typeQualifier.line, "invalid qualifier:", getQualifierString(typeQualifier.qualifier), "interface blocks must be uniform");
2384                 recover();
2385         }
2386
2387         TLayoutQualifier blockLayoutQualifier = typeQualifier.layoutQualifier;
2388         if(layoutLocationErrorCheck(typeQualifier.line, blockLayoutQualifier))
2389         {
2390                 recover();
2391         }
2392
2393         if(blockLayoutQualifier.matrixPacking == EmpUnspecified)
2394         {
2395                 blockLayoutQualifier.matrixPacking = mDefaultMatrixPacking;
2396         }
2397
2398         if(blockLayoutQualifier.blockStorage == EbsUnspecified)
2399         {
2400                 blockLayoutQualifier.blockStorage = mDefaultBlockStorage;
2401         }
2402
2403         TSymbol* blockNameSymbol = new TSymbol(&blockName);
2404         if(!symbolTable.declare(*blockNameSymbol)) {
2405                 error(nameLine, "redefinition", blockName.c_str(), "interface block name");
2406                 recover();
2407         }
2408
2409         // check for sampler types and apply layout qualifiers
2410         for(size_t memberIndex = 0; memberIndex < fieldList->size(); ++memberIndex) {
2411                 TField* field = (*fieldList)[memberIndex];
2412                 TType* fieldType = field->type();
2413                 if(IsSampler(fieldType->getBasicType())) {
2414                         error(field->line(), "unsupported type", fieldType->getBasicString(), "sampler types are not allowed in interface blocks");
2415                         recover();
2416                 }
2417
2418                 const TQualifier qualifier = fieldType->getQualifier();
2419                 switch(qualifier)
2420                 {
2421                 case EvqGlobal:
2422                 case EvqUniform:
2423                         break;
2424                 default:
2425                         error(field->line(), "invalid qualifier on interface block member", getQualifierString(qualifier));
2426                         recover();
2427                         break;
2428                 }
2429
2430                 // check layout qualifiers
2431                 TLayoutQualifier fieldLayoutQualifier = fieldType->getLayoutQualifier();
2432                 if(layoutLocationErrorCheck(field->line(), fieldLayoutQualifier))
2433                 {
2434                         recover();
2435                 }
2436
2437                 if(fieldLayoutQualifier.blockStorage != EbsUnspecified)
2438                 {
2439                         error(field->line(), "invalid layout qualifier:", getBlockStorageString(fieldLayoutQualifier.blockStorage), "cannot be used here");
2440                         recover();
2441                 }
2442
2443                 if(fieldLayoutQualifier.matrixPacking == EmpUnspecified)
2444                 {
2445                         fieldLayoutQualifier.matrixPacking = blockLayoutQualifier.matrixPacking;
2446                 }
2447                 else if(!fieldType->isMatrix())
2448                 {
2449                         error(field->line(), "invalid layout qualifier:", getMatrixPackingString(fieldLayoutQualifier.matrixPacking), "can only be used on matrix types");
2450                         recover();
2451                 }
2452
2453                 fieldType->setLayoutQualifier(fieldLayoutQualifier);
2454         }
2455
2456         // add array index
2457         int arraySize = 0;
2458         if(arrayIndex)
2459         {
2460                 if(arraySizeErrorCheck(arrayIndexLine, arrayIndex, arraySize))
2461                         recover();
2462         }
2463
2464         TInterfaceBlock* interfaceBlock = new TInterfaceBlock(&blockName, fieldList, instanceName, arraySize, blockLayoutQualifier);
2465         TType interfaceBlockType(interfaceBlock, typeQualifier.qualifier, blockLayoutQualifier, arraySize);
2466
2467         TString symbolName = "";
2468         int symbolId = 0;
2469
2470         if(!instanceName)
2471         {
2472                 // define symbols for the members of the interface block
2473                 for(size_t memberIndex = 0; memberIndex < fieldList->size(); ++memberIndex)
2474                 {
2475                         TField* field = (*fieldList)[memberIndex];
2476                         TType* fieldType = field->type();
2477
2478                         // set parent pointer of the field variable
2479                         fieldType->setInterfaceBlock(interfaceBlock);
2480
2481                         TVariable* fieldVariable = new TVariable(&field->name(), *fieldType);
2482                         fieldVariable->setQualifier(typeQualifier.qualifier);
2483
2484                         if(!symbolTable.declare(*fieldVariable)) {
2485                                 error(field->line(), "redefinition", field->name().c_str(), "interface block member name");
2486                                 recover();
2487                         }
2488                 }
2489         }
2490         else
2491         {
2492                 // add a symbol for this interface block
2493                 TVariable* instanceTypeDef = new TVariable(instanceName, interfaceBlockType, false);
2494                 instanceTypeDef->setQualifier(typeQualifier.qualifier);
2495
2496                 if(!symbolTable.declare(*instanceTypeDef)) {
2497                         error(instanceLine, "redefinition", instanceName->c_str(), "interface block instance name");
2498                         recover();
2499                 }
2500
2501                 symbolId = instanceTypeDef->getUniqueId();
2502                 symbolName = instanceTypeDef->getName();
2503         }
2504
2505         TIntermAggregate *aggregate = intermediate.makeAggregate(intermediate.addSymbol(symbolId, symbolName, interfaceBlockType, typeQualifier.line), nameLine);
2506         aggregate->setOp(EOpDeclaration);
2507
2508         exitStructDeclaration();
2509         return aggregate;
2510 }
2511
2512 //
2513 // Parse an array index expression
2514 //
2515 TIntermTyped *TParseContext::addIndexExpression(TIntermTyped *baseExpression, const TSourceLoc &location, TIntermTyped *indexExpression)
2516 {
2517         TIntermTyped *indexedExpression = nullptr;
2518
2519         if(!baseExpression->isArray() && !baseExpression->isMatrix() && !baseExpression->isVector())
2520         {
2521                 if(baseExpression->getAsSymbolNode())
2522                 {
2523                         error(location, " left of '[' is not of type array, matrix, or vector ",
2524                                 baseExpression->getAsSymbolNode()->getSymbol().c_str());
2525                 }
2526                 else
2527                 {
2528                         error(location, " left of '[' is not of type array, matrix, or vector ", "expression");
2529                 }
2530                 recover();
2531         }
2532
2533         TIntermConstantUnion *indexConstantUnion = indexExpression->getAsConstantUnion();
2534
2535         if(indexExpression->getQualifier() == EvqConstExpr && indexConstantUnion)
2536         {
2537                 int index = indexConstantUnion->getIConst(0);
2538                 if(index < 0)
2539                 {
2540                         std::stringstream infoStream;
2541                         infoStream << index;
2542                         std::string info = infoStream.str();
2543                         error(location, "negative index", info.c_str());
2544                         recover();
2545                         index = 0;
2546                 }
2547                 if(baseExpression->getType().getQualifier() == EvqConstExpr)
2548                 {
2549                         if(baseExpression->isArray())
2550                         {
2551                                 // constant folding for arrays
2552                                 indexedExpression = addConstArrayNode(index, baseExpression, location);
2553                         }
2554                         else if(baseExpression->isVector())
2555                         {
2556                                 // constant folding for vectors
2557                                 TVectorFields fields;
2558                                 fields.num = 1;
2559                                 fields.offsets[0] = index; // need to do it this way because v.xy sends fields integer array
2560                                 indexedExpression = addConstVectorNode(fields, baseExpression, location);
2561                         }
2562                         else if(baseExpression->isMatrix())
2563                         {
2564                                 // constant folding for matrices
2565                                 indexedExpression = addConstMatrixNode(index, baseExpression, location);
2566                         }
2567                 }
2568                 else
2569                 {
2570                         int safeIndex = -1;
2571
2572                         if(baseExpression->isArray())
2573                         {
2574                                 if(index >= baseExpression->getType().getArraySize())
2575                                 {
2576                                         std::stringstream extraInfoStream;
2577                                         extraInfoStream << "array index out of range '" << index << "'";
2578                                         std::string extraInfo = extraInfoStream.str();
2579                                         error(location, "", "[", extraInfo.c_str());
2580                                         recover();
2581                                         safeIndex = baseExpression->getType().getArraySize() - 1;
2582                                 }
2583                         }
2584                         else if((baseExpression->isVector() || baseExpression->isMatrix()) &&
2585                                 baseExpression->getType().getNominalSize() <= index)
2586                         {
2587                                 std::stringstream extraInfoStream;
2588                                 extraInfoStream << "field selection out of range '" << index << "'";
2589                                 std::string extraInfo = extraInfoStream.str();
2590                                 error(location, "", "[", extraInfo.c_str());
2591                                 recover();
2592                                 safeIndex = baseExpression->getType().getNominalSize() - 1;
2593                         }
2594
2595                         // Don't modify the data of the previous constant union, because it can point
2596                         // to builtins, like gl_MaxDrawBuffers. Instead use a new sanitized object.
2597                         if(safeIndex != -1)
2598                         {
2599                                 ConstantUnion *safeConstantUnion = new ConstantUnion();
2600                                 safeConstantUnion->setIConst(safeIndex);
2601                                 indexConstantUnion->replaceConstantUnion(safeConstantUnion);
2602                         }
2603
2604                         indexedExpression = intermediate.addIndex(EOpIndexDirect, baseExpression, indexExpression, location);
2605                 }
2606         }
2607         else
2608         {
2609                 if(baseExpression->isInterfaceBlock())
2610                 {
2611                         error(location, "",
2612                                 "[", "array indexes for interface blocks arrays must be constant integral expressions");
2613                         recover();
2614                 }
2615                 else if(baseExpression->getQualifier() == EvqFragmentOut)
2616                 {
2617                         error(location, "", "[", "array indexes for fragment outputs must be constant integral expressions");
2618                         recover();
2619                 }
2620
2621                 indexedExpression = intermediate.addIndex(EOpIndexIndirect, baseExpression, indexExpression, location);
2622         }
2623
2624         if(indexedExpression == 0)
2625         {
2626                 ConstantUnion *unionArray = new ConstantUnion[1];
2627                 unionArray->setFConst(0.0f);
2628                 indexedExpression = intermediate.addConstantUnion(unionArray, TType(EbtFloat, EbpHigh, EvqConstExpr), location);
2629         }
2630         else if(baseExpression->isArray())
2631         {
2632                 const TType &baseType = baseExpression->getType();
2633                 if(baseType.getStruct())
2634                 {
2635                         TType copyOfType(baseType.getStruct());
2636                         indexedExpression->setType(copyOfType);
2637                 }
2638                 else if(baseType.isInterfaceBlock())
2639                 {
2640                         TType copyOfType(baseType.getInterfaceBlock(), EvqTemporary, baseType.getLayoutQualifier(), 0);
2641                         indexedExpression->setType(copyOfType);
2642                 }
2643                 else
2644                 {
2645                         indexedExpression->setType(TType(baseExpression->getBasicType(), baseExpression->getPrecision(),
2646                                 EvqTemporary, static_cast<unsigned char>(baseExpression->getNominalSize()),
2647                                 static_cast<unsigned char>(baseExpression->getSecondarySize())));
2648                 }
2649
2650                 if(baseExpression->getType().getQualifier() == EvqConstExpr)
2651                 {
2652                         indexedExpression->getTypePointer()->setQualifier(EvqConstExpr);
2653                 }
2654         }
2655         else if(baseExpression->isMatrix())
2656         {
2657                 TQualifier qualifier = baseExpression->getType().getQualifier() == EvqConstExpr ? EvqConstExpr : EvqTemporary;
2658                 indexedExpression->setType(TType(baseExpression->getBasicType(), baseExpression->getPrecision(),
2659                         qualifier, static_cast<unsigned char>(baseExpression->getSecondarySize())));
2660         }
2661         else if(baseExpression->isVector())
2662         {
2663                 TQualifier qualifier = baseExpression->getType().getQualifier() == EvqConstExpr ? EvqConstExpr : EvqTemporary;
2664                 indexedExpression->setType(TType(baseExpression->getBasicType(), baseExpression->getPrecision(), qualifier));
2665         }
2666         else
2667         {
2668                 indexedExpression->setType(baseExpression->getType());
2669         }
2670
2671         return indexedExpression;
2672 }
2673
2674 TIntermTyped *TParseContext::addFieldSelectionExpression(TIntermTyped *baseExpression, const TSourceLoc &dotLocation,
2675         const TString &fieldString, const TSourceLoc &fieldLocation)
2676 {
2677         TIntermTyped *indexedExpression = nullptr;
2678
2679         if(baseExpression->isArray())
2680         {
2681                 error(fieldLocation, "cannot apply dot operator to an array", ".");
2682                 recover();
2683         }
2684
2685         if(baseExpression->isVector())
2686         {
2687                 TVectorFields fields;
2688                 if(!parseVectorFields(fieldString, baseExpression->getNominalSize(), fields, fieldLocation))
2689                 {
2690                         fields.num = 1;
2691                         fields.offsets[0] = 0;
2692                         recover();
2693                 }
2694
2695                 if(baseExpression->getAsConstantUnion())
2696                 {
2697                         // constant folding for vector fields
2698                         indexedExpression = addConstVectorNode(fields, baseExpression, fieldLocation);
2699                         if(indexedExpression == 0)
2700                         {
2701                                 recover();
2702                                 indexedExpression = baseExpression;
2703                         }
2704                         else
2705                         {
2706                                 indexedExpression->setType(TType(baseExpression->getBasicType(), baseExpression->getPrecision(),
2707                                         EvqConstExpr, (unsigned char)(fieldString).size()));
2708                         }
2709                 }
2710                 else
2711                 {
2712                         TString vectorString = fieldString;
2713                         TIntermTyped *index = intermediate.addSwizzle(fields, fieldLocation);
2714                         indexedExpression = intermediate.addIndex(EOpVectorSwizzle, baseExpression, index, dotLocation);
2715                         indexedExpression->setType(TType(baseExpression->getBasicType(), baseExpression->getPrecision(),
2716                                 baseExpression->getQualifier() == EvqConstExpr ? EvqConstExpr : EvqTemporary, (unsigned char)vectorString.size()));
2717                 }
2718         }
2719         else if(baseExpression->isMatrix())
2720         {
2721                 TMatrixFields fields;
2722                 if(!parseMatrixFields(fieldString, baseExpression->getNominalSize(), baseExpression->getSecondarySize(), fields, fieldLocation))
2723                 {
2724                         fields.wholeRow = false;
2725                         fields.wholeCol = false;
2726                         fields.row = 0;
2727                         fields.col = 0;
2728                         recover();
2729                 }
2730
2731                 if(fields.wholeRow || fields.wholeCol)
2732                 {
2733                         error(dotLocation, " non-scalar fields not implemented yet", ".");
2734                         recover();
2735                         ConstantUnion *unionArray = new ConstantUnion[1];
2736                         unionArray->setIConst(0);
2737                         TIntermTyped *index = intermediate.addConstantUnion(unionArray, TType(EbtInt, EbpUndefined, EvqConstExpr),
2738                                 fieldLocation);
2739                         indexedExpression = intermediate.addIndex(EOpIndexDirect, baseExpression, index, dotLocation);
2740                         indexedExpression->setType(TType(baseExpression->getBasicType(), baseExpression->getPrecision(),
2741                                 EvqTemporary, static_cast<unsigned char>(baseExpression->getNominalSize()),
2742                                 static_cast<unsigned char>(baseExpression->getSecondarySize())));
2743                 }
2744                 else
2745                 {
2746                         ConstantUnion *unionArray = new ConstantUnion[1];
2747                         unionArray->setIConst(fields.col * baseExpression->getSecondarySize() + fields.row);
2748                         TIntermTyped *index = intermediate.addConstantUnion(unionArray, TType(EbtInt, EbpUndefined, EvqConstExpr),
2749                                 fieldLocation);
2750                         indexedExpression = intermediate.addIndex(EOpIndexDirect, baseExpression, index, dotLocation);
2751                         indexedExpression->setType(TType(baseExpression->getBasicType(), baseExpression->getPrecision()));
2752                 }
2753         }
2754         else if(baseExpression->getBasicType() == EbtStruct)
2755         {
2756                 bool fieldFound = false;
2757                 const TFieldList &fields = baseExpression->getType().getStruct()->fields();
2758                 if(fields.empty())
2759                 {
2760                         error(dotLocation, "structure has no fields", "Internal Error");
2761                         recover();
2762                         indexedExpression = baseExpression;
2763                 }
2764                 else
2765                 {
2766                         unsigned int i;
2767                         for(i = 0; i < fields.size(); ++i)
2768                         {
2769                                 if(fields[i]->name() == fieldString)
2770                                 {
2771                                         fieldFound = true;
2772                                         break;
2773                                 }
2774                         }
2775                         if(fieldFound)
2776                         {
2777                                 if(baseExpression->getType().getQualifier() == EvqConstExpr)
2778                                 {
2779                                         indexedExpression = addConstStruct(fieldString, baseExpression, dotLocation);
2780                                         if(indexedExpression == 0)
2781                                         {
2782                                                 recover();
2783                                                 indexedExpression = baseExpression;
2784                                         }
2785                                         else
2786                                         {
2787                                                 indexedExpression->setType(*fields[i]->type());
2788                                                 // change the qualifier of the return type, not of the structure field
2789                                                 // as the structure definition is shared between various structures.
2790                                                 indexedExpression->getTypePointer()->setQualifier(EvqConstExpr);
2791                                         }
2792                                 }
2793                                 else
2794                                 {
2795                                         TIntermTyped *index = TIntermTyped::CreateIndexNode(i);
2796                                         index->setLine(fieldLocation);
2797                                         indexedExpression = intermediate.addIndex(EOpIndexDirectStruct, baseExpression, index, dotLocation);
2798                                         indexedExpression->setType(*fields[i]->type());
2799                                 }
2800                         }
2801                         else
2802                         {
2803                                 error(dotLocation, " no such field in structure", fieldString.c_str());
2804                                 recover();
2805                                 indexedExpression = baseExpression;
2806                         }
2807                 }
2808         }
2809         else if(baseExpression->isInterfaceBlock())
2810         {
2811                 bool fieldFound = false;
2812                 const TFieldList &fields = baseExpression->getType().getInterfaceBlock()->fields();
2813                 if(fields.empty())
2814                 {
2815                         error(dotLocation, "interface block has no fields", "Internal Error");
2816                         recover();
2817                         indexedExpression = baseExpression;
2818                 }
2819                 else
2820                 {
2821                         unsigned int i;
2822                         for(i = 0; i < fields.size(); ++i)
2823                         {
2824                                 if(fields[i]->name() == fieldString)
2825                                 {
2826                                         fieldFound = true;
2827                                         break;
2828                                 }
2829                         }
2830                         if(fieldFound)
2831                         {
2832                                 ConstantUnion *unionArray = new ConstantUnion[1];
2833                                 unionArray->setIConst(i);
2834                                 TIntermTyped *index = intermediate.addConstantUnion(unionArray, *fields[i]->type(), fieldLocation);
2835                                 indexedExpression = intermediate.addIndex(EOpIndexDirectInterfaceBlock, baseExpression, index,
2836                                         dotLocation);
2837                                 indexedExpression->setType(*fields[i]->type());
2838                         }
2839                         else
2840                         {
2841                                 error(dotLocation, " no such field in interface block", fieldString.c_str());
2842                                 recover();
2843                                 indexedExpression = baseExpression;
2844                         }
2845                 }
2846         }
2847         else
2848         {
2849                 if(mShaderVersion < 300)
2850                 {
2851                         error(dotLocation, " field selection requires structure, vector, or matrix on left hand side",
2852                                 fieldString.c_str());
2853                 }
2854                 else
2855                 {
2856                         error(dotLocation,
2857                                 " field selection requires structure, vector, matrix, or interface block on left hand side",
2858                                 fieldString.c_str());
2859                 }
2860                 recover();
2861                 indexedExpression = baseExpression;
2862         }
2863
2864         return indexedExpression;
2865 }
2866
2867 TLayoutQualifier TParseContext::parseLayoutQualifier(const TString &qualifierType, const TSourceLoc& qualifierTypeLine)
2868 {
2869         TLayoutQualifier qualifier;
2870
2871         qualifier.location = -1;
2872         qualifier.matrixPacking = EmpUnspecified;
2873         qualifier.blockStorage = EbsUnspecified;
2874
2875         if(qualifierType == "shared")
2876         {
2877                 qualifier.blockStorage = EbsShared;
2878         }
2879         else if(qualifierType == "packed")
2880         {
2881                 qualifier.blockStorage = EbsPacked;
2882         }
2883         else if(qualifierType == "std140")
2884         {
2885                 qualifier.blockStorage = EbsStd140;
2886         }
2887         else if(qualifierType == "row_major")
2888         {
2889                 qualifier.matrixPacking = EmpRowMajor;
2890         }
2891         else if(qualifierType == "column_major")
2892         {
2893                 qualifier.matrixPacking = EmpColumnMajor;
2894         }
2895         else if(qualifierType == "location")
2896         {
2897                 error(qualifierTypeLine, "invalid layout qualifier", qualifierType.c_str(), "location requires an argument");
2898                 recover();
2899         }
2900         else
2901         {
2902                 error(qualifierTypeLine, "invalid layout qualifier", qualifierType.c_str());
2903                 recover();
2904         }
2905
2906         return qualifier;
2907 }
2908
2909 TLayoutQualifier TParseContext::parseLayoutQualifier(const TString &qualifierType, const TSourceLoc& qualifierTypeLine, const TString &intValueString, int intValue, const TSourceLoc& intValueLine)
2910 {
2911         TLayoutQualifier qualifier;
2912
2913         qualifier.location = -1;
2914         qualifier.matrixPacking = EmpUnspecified;
2915         qualifier.blockStorage = EbsUnspecified;
2916
2917         if (qualifierType != "location")
2918         {
2919                 error(qualifierTypeLine, "invalid layout qualifier", qualifierType.c_str(), "only location may have arguments");
2920                 recover();
2921         }
2922         else
2923         {
2924                 // must check that location is non-negative
2925                 if (intValue < 0)
2926                 {
2927                         error(intValueLine, "out of range:", intValueString.c_str(), "location must be non-negative");
2928                         recover();
2929                 }
2930                 else
2931                 {
2932                         qualifier.location = intValue;
2933                 }
2934         }
2935
2936         return qualifier;
2937 }
2938
2939 TLayoutQualifier TParseContext::joinLayoutQualifiers(TLayoutQualifier leftQualifier, TLayoutQualifier rightQualifier)
2940 {
2941         TLayoutQualifier joinedQualifier = leftQualifier;
2942
2943         if (rightQualifier.location != -1)
2944         {
2945                 joinedQualifier.location = rightQualifier.location;
2946         }
2947         if(rightQualifier.matrixPacking != EmpUnspecified)
2948         {
2949                 joinedQualifier.matrixPacking = rightQualifier.matrixPacking;
2950         }
2951         if(rightQualifier.blockStorage != EbsUnspecified)
2952         {
2953                 joinedQualifier.blockStorage = rightQualifier.blockStorage;
2954         }
2955
2956         return joinedQualifier;
2957 }
2958
2959
2960 TPublicType TParseContext::joinInterpolationQualifiers(const TSourceLoc &interpolationLoc, TQualifier interpolationQualifier,
2961         const TSourceLoc &storageLoc, TQualifier storageQualifier)
2962 {
2963         TQualifier mergedQualifier = EvqSmoothIn;
2964
2965         if(storageQualifier == EvqFragmentIn) {
2966                 if(interpolationQualifier == EvqSmooth)
2967                         mergedQualifier = EvqSmoothIn;
2968                 else if(interpolationQualifier == EvqFlat)
2969                         mergedQualifier = EvqFlatIn;
2970                 else UNREACHABLE(interpolationQualifier);
2971         }
2972         else if(storageQualifier == EvqCentroidIn) {
2973                 if(interpolationQualifier == EvqSmooth)
2974                         mergedQualifier = EvqCentroidIn;
2975                 else if(interpolationQualifier == EvqFlat)
2976                         mergedQualifier = EvqFlatIn;
2977                 else UNREACHABLE(interpolationQualifier);
2978         }
2979         else if(storageQualifier == EvqVertexOut) {
2980                 if(interpolationQualifier == EvqSmooth)
2981                         mergedQualifier = EvqSmoothOut;
2982                 else if(interpolationQualifier == EvqFlat)
2983                         mergedQualifier = EvqFlatOut;
2984                 else UNREACHABLE(interpolationQualifier);
2985         }
2986         else if(storageQualifier == EvqCentroidOut) {
2987                 if(interpolationQualifier == EvqSmooth)
2988                         mergedQualifier = EvqCentroidOut;
2989                 else if(interpolationQualifier == EvqFlat)
2990                         mergedQualifier = EvqFlatOut;
2991                 else UNREACHABLE(interpolationQualifier);
2992         }
2993         else {
2994                 error(interpolationLoc, "interpolation qualifier requires a fragment 'in' or vertex 'out' storage qualifier", getQualifierString(interpolationQualifier));
2995                 recover();
2996
2997                 mergedQualifier = storageQualifier;
2998         }
2999
3000         TPublicType type;
3001         type.setBasic(EbtVoid, mergedQualifier, storageLoc);
3002         return type;
3003 }
3004
3005 TFieldList *TParseContext::addStructDeclaratorList(const TPublicType &typeSpecifier, TFieldList *fieldList)
3006 {
3007         if(voidErrorCheck(typeSpecifier.line, (*fieldList)[0]->name(), typeSpecifier.type))
3008         {
3009                 recover();
3010         }
3011
3012         for(unsigned int i = 0; i < fieldList->size(); ++i)
3013         {
3014                 //
3015                 // Careful not to replace already known aspects of type, like array-ness
3016                 //
3017                 TType *type = (*fieldList)[i]->type();
3018                 type->setBasicType(typeSpecifier.type);
3019                 type->setNominalSize(typeSpecifier.primarySize);
3020                 type->setSecondarySize(typeSpecifier.secondarySize);
3021                 type->setPrecision(typeSpecifier.precision);
3022                 type->setQualifier(typeSpecifier.qualifier);
3023                 type->setLayoutQualifier(typeSpecifier.layoutQualifier);
3024
3025                 // don't allow arrays of arrays
3026                 if(type->isArray())
3027                 {
3028                         if(arrayTypeErrorCheck(typeSpecifier.line, typeSpecifier))
3029                                 recover();
3030                 }
3031                 if(typeSpecifier.array)
3032                         type->setArraySize(typeSpecifier.arraySize);
3033                 if(typeSpecifier.userDef)
3034                 {
3035                         type->setStruct(typeSpecifier.userDef->getStruct());
3036                 }
3037
3038                 if(structNestingErrorCheck(typeSpecifier.line, *(*fieldList)[i]))
3039                 {
3040                         recover();
3041                 }
3042         }
3043
3044         return fieldList;
3045 }
3046
3047 TPublicType TParseContext::addStructure(const TSourceLoc &structLine, const TSourceLoc &nameLine,
3048         const TString *structName, TFieldList *fieldList)
3049 {
3050         TStructure *structure = new TStructure(structName, fieldList);
3051         TType *structureType = new TType(structure);
3052
3053         // Store a bool in the struct if we're at global scope, to allow us to
3054         // skip the local struct scoping workaround in HLSL.
3055         structure->setUniqueId(TSymbolTableLevel::nextUniqueId());
3056         structure->setAtGlobalScope(symbolTable.atGlobalLevel());
3057
3058         if(!structName->empty())
3059         {
3060                 if(reservedErrorCheck(nameLine, *structName))
3061                 {
3062                         recover();
3063                 }
3064                 TVariable *userTypeDef = new TVariable(structName, *structureType, true);
3065                 if(!symbolTable.declare(*userTypeDef))
3066                 {
3067                         error(nameLine, "redefinition", structName->c_str(), "struct");
3068                         recover();
3069                 }
3070         }
3071
3072         // ensure we do not specify any storage qualifiers on the struct members
3073         for(unsigned int typeListIndex = 0; typeListIndex < fieldList->size(); typeListIndex++)
3074         {
3075                 const TField &field = *(*fieldList)[typeListIndex];
3076                 const TQualifier qualifier = field.type()->getQualifier();
3077                 switch(qualifier)
3078                 {
3079                 case EvqGlobal:
3080                 case EvqTemporary:
3081                         break;
3082                 default:
3083                         error(field.line(), "invalid qualifier on struct member", getQualifierString(qualifier));
3084                         recover();
3085                         break;
3086                 }
3087         }
3088
3089         TPublicType publicType;
3090         publicType.setBasic(EbtStruct, EvqTemporary, structLine);
3091         publicType.userDef = structureType;
3092         exitStructDeclaration();
3093
3094         return publicType;
3095 }
3096
3097 bool TParseContext::enterStructDeclaration(const TSourceLoc &line, const TString& identifier)
3098 {
3099         ++mStructNestingLevel;
3100
3101         // Embedded structure definitions are not supported per GLSL ES spec.
3102         // They aren't allowed in GLSL either, but we need to detect this here
3103         // so we don't rely on the GLSL compiler to catch it.
3104         if (mStructNestingLevel > 1) {
3105                 error(line, "", "Embedded struct definitions are not allowed");
3106                 return true;
3107         }
3108
3109         return false;
3110 }
3111
3112 void TParseContext::exitStructDeclaration()
3113 {
3114         --mStructNestingLevel;
3115 }
3116
3117 bool TParseContext::structNestingErrorCheck(const TSourceLoc &line, const TField &field)
3118 {
3119         static const int kWebGLMaxStructNesting = 4;
3120
3121         if(field.type()->getBasicType() != EbtStruct)
3122         {
3123                 return false;
3124         }
3125
3126         // We're already inside a structure definition at this point, so add
3127         // one to the field's struct nesting.
3128         if(1 + field.type()->getDeepestStructNesting() > kWebGLMaxStructNesting)
3129         {
3130                 std::stringstream reasonStream;
3131                 reasonStream << "Reference of struct type "
3132                         << field.type()->getStruct()->name().c_str()
3133                         << " exceeds maximum allowed nesting level of "
3134                         << kWebGLMaxStructNesting;
3135                 std::string reason = reasonStream.str();
3136                 error(line, reason.c_str(), field.name().c_str(), "");
3137                 return true;
3138         }
3139
3140         return false;
3141 }
3142
3143 TIntermTyped *TParseContext::createUnaryMath(TOperator op, TIntermTyped *child, const TSourceLoc &loc, const TType *funcReturnType)
3144 {
3145         if(child == nullptr)
3146         {
3147                 return nullptr;
3148         }
3149
3150         switch(op)
3151         {
3152         case EOpLogicalNot:
3153                 if(child->getBasicType() != EbtBool ||
3154                         child->isMatrix() ||
3155                         child->isArray() ||
3156                         child->isVector())
3157                 {
3158                         return nullptr;
3159                 }
3160                 break;
3161         case EOpBitwiseNot:
3162                 if((child->getBasicType() != EbtInt && child->getBasicType() != EbtUInt) ||
3163                         child->isMatrix() ||
3164                         child->isArray())
3165                 {
3166                         return nullptr;
3167                 }
3168                 break;
3169         case EOpPostIncrement:
3170         case EOpPreIncrement:
3171         case EOpPostDecrement:
3172         case EOpPreDecrement:
3173         case EOpNegative:
3174                 if(child->getBasicType() == EbtStruct ||
3175                         child->getBasicType() == EbtBool ||
3176                         child->isArray())
3177                 {
3178                         return nullptr;
3179                 }
3180                 // Operators for built-ins are already type checked against their prototype.
3181         default:
3182                 break;
3183         }
3184
3185         return intermediate.addUnaryMath(op, child, loc, funcReturnType);
3186 }
3187
3188 TIntermTyped *TParseContext::addUnaryMath(TOperator op, TIntermTyped *child, const TSourceLoc &loc)
3189 {
3190         TIntermTyped *node = createUnaryMath(op, child, loc, nullptr);
3191         if(node == nullptr)
3192         {
3193                 unaryOpError(loc, getOperatorString(op), child->getCompleteString());
3194                 recover();
3195                 return child;
3196         }
3197         return node;
3198 }
3199
3200 TIntermTyped *TParseContext::addUnaryMathLValue(TOperator op, TIntermTyped *child, const TSourceLoc &loc)
3201 {
3202         if(lValueErrorCheck(loc, getOperatorString(op), child))
3203                 recover();
3204         return addUnaryMath(op, child, loc);
3205 }
3206
3207 bool TParseContext::binaryOpCommonCheck(TOperator op, TIntermTyped *left, TIntermTyped *right, const TSourceLoc &loc)
3208 {
3209         if(left->isArray() || right->isArray())
3210         {
3211                 if(mShaderVersion < 300)
3212                 {
3213                         error(loc, "Invalid operation for arrays", getOperatorString(op));
3214                         return false;
3215                 }
3216
3217                 if(left->isArray() != right->isArray())
3218                 {
3219                         error(loc, "array / non-array mismatch", getOperatorString(op));
3220                         return false;
3221                 }
3222
3223                 switch(op)
3224                 {
3225                 case EOpEqual:
3226                 case EOpNotEqual:
3227                 case EOpAssign:
3228                 case EOpInitialize:
3229                         break;
3230                 default:
3231                         error(loc, "Invalid operation for arrays", getOperatorString(op));
3232                         return false;
3233                 }
3234                 // At this point, size of implicitly sized arrays should be resolved.
3235                 if(left->getArraySize() != right->getArraySize())
3236                 {
3237                         error(loc, "array size mismatch", getOperatorString(op));
3238                         return false;
3239                 }
3240         }
3241
3242         // Check ops which require integer / ivec parameters
3243         bool isBitShift = false;
3244         switch(op)
3245         {
3246         case EOpBitShiftLeft:
3247         case EOpBitShiftRight:
3248         case EOpBitShiftLeftAssign:
3249         case EOpBitShiftRightAssign:
3250                 // Unsigned can be bit-shifted by signed and vice versa, but we need to
3251                 // check that the basic type is an integer type.
3252                 isBitShift = true;
3253                 if(!IsInteger(left->getBasicType()) || !IsInteger(right->getBasicType()))
3254                 {
3255                         return false;
3256                 }
3257                 break;
3258         case EOpBitwiseAnd:
3259         case EOpBitwiseXor:
3260         case EOpBitwiseOr:
3261         case EOpBitwiseAndAssign:
3262         case EOpBitwiseXorAssign:
3263         case EOpBitwiseOrAssign:
3264                 // It is enough to check the type of only one operand, since later it
3265                 // is checked that the operand types match.
3266                 if(!IsInteger(left->getBasicType()))
3267                 {
3268                         return false;
3269                 }
3270                 break;
3271         default:
3272                 break;
3273         }
3274
3275         // GLSL ES 1.00 and 3.00 do not support implicit type casting.
3276         // So the basic type should usually match.
3277         if(!isBitShift && left->getBasicType() != right->getBasicType())
3278         {
3279                 return false;
3280         }
3281
3282         // Check that type sizes match exactly on ops that require that.
3283         // Also check restrictions for structs that contain arrays or samplers.
3284         switch(op)
3285         {
3286         case EOpAssign:
3287         case EOpInitialize:
3288         case EOpEqual:
3289         case EOpNotEqual:
3290                 // ESSL 1.00 sections 5.7, 5.8, 5.9
3291                 if(mShaderVersion < 300 && left->getType().isStructureContainingArrays())
3292                 {
3293                         error(loc, "undefined operation for structs containing arrays", getOperatorString(op));
3294                         return false;
3295                 }
3296                 // Samplers as l-values are disallowed also in ESSL 3.00, see section 4.1.7,
3297                 // we interpret the spec so that this extends to structs containing samplers,
3298                 // similarly to ESSL 1.00 spec.
3299                 if((mShaderVersion < 300 || op == EOpAssign || op == EOpInitialize) &&
3300                         left->getType().isStructureContainingSamplers())
3301                 {
3302                         error(loc, "undefined operation for structs containing samplers", getOperatorString(op));
3303                         return false;
3304                 }
3305         case EOpLessThan:
3306         case EOpGreaterThan:
3307         case EOpLessThanEqual:
3308         case EOpGreaterThanEqual:
3309                 if((left->getNominalSize() != right->getNominalSize()) ||
3310                         (left->getSecondarySize() != right->getSecondarySize()))
3311                 {
3312                         return false;
3313                 }
3314                 break;
3315         case EOpAdd:
3316         case EOpSub:
3317         case EOpDiv:
3318         case EOpIMod:
3319         case EOpBitShiftLeft:
3320         case EOpBitShiftRight:
3321         case EOpBitwiseAnd:
3322         case EOpBitwiseXor:
3323         case EOpBitwiseOr:
3324         case EOpAddAssign:
3325         case EOpSubAssign:
3326         case EOpDivAssign:
3327         case EOpIModAssign:
3328         case EOpBitShiftLeftAssign:
3329         case EOpBitShiftRightAssign:
3330         case EOpBitwiseAndAssign:
3331         case EOpBitwiseXorAssign:
3332         case EOpBitwiseOrAssign:
3333                 if((left->isMatrix() && right->isVector()) || (left->isVector() && right->isMatrix()))
3334                 {
3335                         return false;
3336                 }
3337
3338                 // Are the sizes compatible?
3339                 if(left->getNominalSize() != right->getNominalSize() || left->getSecondarySize() != right->getSecondarySize())
3340                 {
3341                         // If the nominal sizes of operands do not match:
3342                         // One of them must be a scalar.
3343                         if(!left->isScalar() && !right->isScalar())
3344                                 return false;
3345
3346                         // In the case of compound assignment other than multiply-assign,
3347                         // the right side needs to be a scalar. Otherwise a vector/matrix
3348                         // would be assigned to a scalar. A scalar can't be shifted by a
3349                         // vector either.
3350                         if(!right->isScalar() && (IsAssignment(op) || op == EOpBitShiftLeft || op == EOpBitShiftRight))
3351                                 return false;
3352                 }
3353                 break;
3354         default:
3355                 break;
3356         }
3357
3358         return true;
3359 }
3360
3361 TIntermSwitch *TParseContext::addSwitch(TIntermTyped *init, TIntermAggregate *statementList, const TSourceLoc &loc)
3362 {
3363         TBasicType switchType = init->getBasicType();
3364         if((switchType != EbtInt && switchType != EbtUInt) ||
3365            init->isMatrix() ||
3366            init->isArray() ||
3367            init->isVector())
3368         {
3369                 error(init->getLine(), "init-expression in a switch statement must be a scalar integer", "switch");
3370                 recover();
3371                 return nullptr;
3372         }
3373
3374         if(statementList)
3375         {
3376                 if(!ValidateSwitch::validate(switchType, this, statementList, loc))
3377                 {
3378                         recover();
3379                         return nullptr;
3380                 }
3381         }
3382
3383         TIntermSwitch *node = intermediate.addSwitch(init, statementList, loc);
3384         if(node == nullptr)
3385         {
3386                 error(loc, "erroneous switch statement", "switch");
3387                 recover();
3388                 return nullptr;
3389         }
3390         return node;
3391 }
3392
3393 TIntermCase *TParseContext::addCase(TIntermTyped *condition, const TSourceLoc &loc)
3394 {
3395         if(mSwitchNestingLevel == 0)
3396         {
3397                 error(loc, "case labels need to be inside switch statements", "case");
3398                 recover();
3399                 return nullptr;
3400         }
3401         if(condition == nullptr)
3402         {
3403                 error(loc, "case label must have a condition", "case");
3404                 recover();
3405                 return nullptr;
3406         }
3407         if((condition->getBasicType() != EbtInt && condition->getBasicType() != EbtUInt) ||
3408            condition->isMatrix() ||
3409            condition->isArray() ||
3410            condition->isVector())
3411         {
3412                 error(condition->getLine(), "case label must be a scalar integer", "case");
3413                 recover();
3414         }
3415         TIntermConstantUnion *conditionConst = condition->getAsConstantUnion();
3416         if(conditionConst == nullptr)
3417         {
3418                 error(condition->getLine(), "case label must be constant", "case");
3419                 recover();
3420         }
3421         TIntermCase *node = intermediate.addCase(condition, loc);
3422         if(node == nullptr)
3423         {
3424                 error(loc, "erroneous case statement", "case");
3425                 recover();
3426                 return nullptr;
3427         }
3428         return node;
3429 }
3430
3431 TIntermCase *TParseContext::addDefault(const TSourceLoc &loc)
3432 {
3433         if(mSwitchNestingLevel == 0)
3434         {
3435                 error(loc, "default labels need to be inside switch statements", "default");
3436                 recover();
3437                 return nullptr;
3438         }
3439         TIntermCase *node = intermediate.addCase(nullptr, loc);
3440         if(node == nullptr)
3441         {
3442                 error(loc, "erroneous default statement", "default");
3443                 recover();
3444                 return nullptr;
3445         }
3446         return node;
3447 }
3448 TIntermTyped *TParseContext::createAssign(TOperator op, TIntermTyped *left, TIntermTyped *right, const TSourceLoc &loc)
3449 {
3450         if(binaryOpCommonCheck(op, left, right, loc))
3451         {
3452                 return intermediate.addAssign(op, left, right, loc);
3453         }
3454         return nullptr;
3455 }
3456
3457 TIntermTyped *TParseContext::addAssign(TOperator op, TIntermTyped *left, TIntermTyped *right, const TSourceLoc &loc)
3458 {
3459         TIntermTyped *node = createAssign(op, left, right, loc);
3460         if(node == nullptr)
3461         {
3462                 assignError(loc, "assign", left->getCompleteString(), right->getCompleteString());
3463                 recover();
3464                 return left;
3465         }
3466         return node;
3467 }
3468
3469 TIntermTyped *TParseContext::addBinaryMathInternal(TOperator op, TIntermTyped *left, TIntermTyped *right,
3470         const TSourceLoc &loc)
3471 {
3472         if(!binaryOpCommonCheck(op, left, right, loc))
3473                 return nullptr;
3474
3475         switch(op)
3476         {
3477         case EOpEqual:
3478         case EOpNotEqual:
3479                 break;
3480         case EOpLessThan:
3481         case EOpGreaterThan:
3482         case EOpLessThanEqual:
3483         case EOpGreaterThanEqual:
3484                 ASSERT(!left->isArray() && !right->isArray());
3485                 if(left->isMatrix() || left->isVector() ||
3486                         left->getBasicType() == EbtStruct)
3487                 {
3488                         return nullptr;
3489                 }
3490                 break;
3491         case EOpLogicalOr:
3492         case EOpLogicalXor:
3493         case EOpLogicalAnd:
3494                 ASSERT(!left->isArray() && !right->isArray());
3495                 if(left->getBasicType() != EbtBool ||
3496                         left->isMatrix() || left->isVector())
3497                 {
3498                         return nullptr;
3499                 }
3500                 break;
3501         case EOpAdd:
3502         case EOpSub:
3503         case EOpDiv:
3504         case EOpMul:
3505                 ASSERT(!left->isArray() && !right->isArray());
3506                 if(left->getBasicType() == EbtStruct || left->getBasicType() == EbtBool)
3507                 {
3508                         return nullptr;
3509                 }
3510                 break;
3511         case EOpIMod:
3512                 ASSERT(!left->isArray() && !right->isArray());
3513                 // Note that this is only for the % operator, not for mod()
3514                 if(left->getBasicType() == EbtStruct || left->getBasicType() == EbtBool || left->getBasicType() == EbtFloat)
3515                 {
3516                         return nullptr;
3517                 }
3518                 break;
3519                 // Note that for bitwise ops, type checking is done in promote() to
3520                 // share code between ops and compound assignment
3521         default:
3522                 break;
3523         }
3524
3525         return intermediate.addBinaryMath(op, left, right, loc);
3526 }
3527
3528 TIntermTyped *TParseContext::addBinaryMath(TOperator op, TIntermTyped *left, TIntermTyped *right, const TSourceLoc &loc)
3529 {
3530         TIntermTyped *node = addBinaryMathInternal(op, left, right, loc);
3531         if(node == 0)
3532         {
3533                 binaryOpError(loc, getOperatorString(op), left->getCompleteString(), right->getCompleteString());
3534                 recover();
3535                 return left;
3536         }
3537         return node;
3538 }
3539
3540 TIntermTyped *TParseContext::addBinaryMathBooleanResult(TOperator op, TIntermTyped *left, TIntermTyped *right, const TSourceLoc &loc)
3541 {
3542         TIntermTyped *node = addBinaryMathInternal(op, left, right, loc);
3543         if(node == 0)
3544         {
3545                 binaryOpError(loc, getOperatorString(op), left->getCompleteString(), right->getCompleteString());
3546                 recover();
3547                 ConstantUnion *unionArray = new ConstantUnion[1];
3548                 unionArray->setBConst(false);
3549                 return intermediate.addConstantUnion(unionArray, TType(EbtBool, EbpUndefined, EvqConstExpr), loc);
3550         }
3551         return node;
3552 }
3553
3554 TIntermBranch *TParseContext::addBranch(TOperator op, const TSourceLoc &loc)
3555 {
3556         switch(op)
3557         {
3558         case EOpContinue:
3559                 if(mLoopNestingLevel <= 0)
3560                 {
3561                         error(loc, "continue statement only allowed in loops", "");
3562                         recover();
3563                 }
3564                 break;
3565         case EOpBreak:
3566                 if(mLoopNestingLevel <= 0 && mSwitchNestingLevel <= 0)
3567                 {
3568                         error(loc, "break statement only allowed in loops and switch statements", "");
3569                         recover();
3570                 }
3571                 break;
3572         case EOpReturn:
3573                 if(mCurrentFunctionType->getBasicType() != EbtVoid)
3574                 {
3575                         error(loc, "non-void function must return a value", "return");
3576                         recover();
3577                 }
3578                 break;
3579         default:
3580                 // No checks for discard
3581                 break;
3582         }
3583         return intermediate.addBranch(op, loc);
3584 }
3585
3586 TIntermBranch *TParseContext::addBranch(TOperator op, TIntermTyped *returnValue, const TSourceLoc &loc)
3587 {
3588         ASSERT(op == EOpReturn);
3589         mFunctionReturnsValue = true;
3590         if(mCurrentFunctionType->getBasicType() == EbtVoid)
3591         {
3592                 error(loc, "void function cannot return a value", "return");
3593                 recover();
3594         }
3595         else if(*mCurrentFunctionType != returnValue->getType())
3596         {
3597                 error(loc, "function return is not matching type:", "return");
3598                 recover();
3599         }
3600         return intermediate.addBranch(op, returnValue, loc);
3601 }
3602
3603 TIntermTyped *TParseContext::addFunctionCallOrMethod(TFunction *fnCall, TIntermNode *paramNode, TIntermNode *thisNode, const TSourceLoc &loc, bool *fatalError)
3604 {
3605         *fatalError = false;
3606         TOperator op = fnCall->getBuiltInOp();
3607         TIntermTyped *callNode = nullptr;
3608
3609         if(thisNode != nullptr)
3610         {
3611                 ConstantUnion *unionArray = new ConstantUnion[1];
3612                 int arraySize = 0;
3613                 TIntermTyped *typedThis = thisNode->getAsTyped();
3614                 if(fnCall->getName() != "length")
3615                 {
3616                         error(loc, "invalid method", fnCall->getName().c_str());
3617                         recover();
3618                 }
3619                 else if(paramNode != nullptr)
3620                 {
3621                         error(loc, "method takes no parameters", "length");
3622                         recover();
3623                 }
3624                 else if(typedThis == nullptr || !typedThis->isArray())
3625                 {
3626                         error(loc, "length can only be called on arrays", "length");
3627                         recover();
3628                 }
3629                 else
3630                 {
3631                         arraySize = typedThis->getArraySize();
3632                         if(typedThis->getAsSymbolNode() == nullptr)
3633                         {
3634                                 // This code path can be hit with expressions like these:
3635                                 // (a = b).length()
3636                                 // (func()).length()
3637                                 // (int[3](0, 1, 2)).length()
3638                                 // ESSL 3.00 section 5.9 defines expressions so that this is not actually a valid expression.
3639                                 // It allows "An array name with the length method applied" in contrast to GLSL 4.4 spec section 5.9
3640                                 // which allows "An array, vector or matrix expression with the length method applied".
3641                                 error(loc, "length can only be called on array names, not on array expressions", "length");
3642                                 recover();
3643                         }
3644                 }
3645                 unionArray->setIConst(arraySize);
3646                 callNode = intermediate.addConstantUnion(unionArray, TType(EbtInt, EbpUndefined, EvqConstExpr), loc);
3647         }
3648         else if(op != EOpNull)
3649         {
3650                 //
3651                 // Then this should be a constructor.
3652                 // Don't go through the symbol table for constructors.
3653                 // Their parameters will be verified algorithmically.
3654                 //
3655                 TType type(EbtVoid, EbpUndefined);  // use this to get the type back
3656                 if(!constructorErrorCheck(loc, paramNode, *fnCall, op, &type))
3657                 {
3658                         //
3659                         // It's a constructor, of type 'type'.
3660                         //
3661                         callNode = addConstructor(paramNode, &type, op, fnCall, loc);
3662                 }
3663
3664                 if(callNode == nullptr)
3665                 {
3666                         recover();
3667                         callNode = intermediate.setAggregateOperator(nullptr, op, loc);
3668                 }
3669         }
3670         else
3671         {
3672                 //
3673                 // Not a constructor.  Find it in the symbol table.
3674                 //
3675                 const TFunction *fnCandidate;
3676                 bool builtIn;
3677                 fnCandidate = findFunction(loc, fnCall, &builtIn);
3678                 if(fnCandidate)
3679                 {
3680                         //
3681                         // A declared function.
3682                         //
3683                         if(builtIn && !fnCandidate->getExtension().empty() &&
3684                                 extensionErrorCheck(loc, fnCandidate->getExtension()))
3685                         {
3686                                 recover();
3687                         }
3688                         op = fnCandidate->getBuiltInOp();
3689                         if(builtIn && op != EOpNull)
3690                         {
3691                                 //
3692                                 // A function call mapped to a built-in operation.
3693                                 //
3694                                 if(fnCandidate->getParamCount() == 1)
3695                                 {
3696                                         //
3697                                         // Treat it like a built-in unary operator.
3698                                         //
3699                                         callNode = createUnaryMath(op, paramNode->getAsTyped(), loc, &fnCandidate->getReturnType());
3700                                         if(callNode == nullptr)
3701                                         {
3702                                                 std::stringstream extraInfoStream;
3703                                                 extraInfoStream << "built in unary operator function.  Type: "
3704                                                         << static_cast<TIntermTyped*>(paramNode)->getCompleteString();
3705                                                 std::string extraInfo = extraInfoStream.str();
3706                                                 error(paramNode->getLine(), " wrong operand type", "Internal Error", extraInfo.c_str());
3707                                                 *fatalError = true;
3708                                                 return nullptr;
3709                                         }
3710                                 }
3711                                 else
3712                                 {
3713                                         TIntermAggregate *aggregate = intermediate.setAggregateOperator(paramNode, op, loc);
3714                                         aggregate->setType(fnCandidate->getReturnType());
3715
3716                                         // Some built-in functions have out parameters too.
3717                                         functionCallLValueErrorCheck(fnCandidate, aggregate);
3718
3719                                         callNode = aggregate;
3720
3721                                         if(fnCandidate->getParamCount() == 2)
3722                                         {
3723                                                 TIntermSequence &parameters = paramNode->getAsAggregate()->getSequence();
3724                                                 TIntermTyped *left = parameters[0]->getAsTyped();
3725                                                 TIntermTyped *right = parameters[1]->getAsTyped();
3726
3727                                                 TIntermConstantUnion *leftTempConstant = left->getAsConstantUnion();
3728                                                 TIntermConstantUnion *rightTempConstant = right->getAsConstantUnion();
3729                                                 if (leftTempConstant && rightTempConstant)
3730                                                 {
3731                                                         TIntermTyped *typedReturnNode = leftTempConstant->fold(op, rightTempConstant, infoSink());
3732
3733                                                         if(typedReturnNode)
3734                                                         {
3735                                                                 callNode = typedReturnNode;
3736                                                         }
3737                                                 }
3738                                         }
3739                                 }
3740                         }
3741                         else
3742                         {
3743                                 // This is a real function call
3744
3745                                 TIntermAggregate *aggregate = intermediate.setAggregateOperator(paramNode, EOpFunctionCall, loc);
3746                                 aggregate->setType(fnCandidate->getReturnType());
3747
3748                                 // this is how we know whether the given function is a builtIn function or a user defined function
3749                                 // if builtIn == false, it's a userDefined -> could be an overloaded builtIn function also
3750                                 // if builtIn == true, it's definitely a builtIn function with EOpNull
3751                                 if(!builtIn)
3752                                         aggregate->setUserDefined();
3753                                 aggregate->setName(fnCandidate->getMangledName());
3754
3755                                 callNode = aggregate;
3756
3757                                 functionCallLValueErrorCheck(fnCandidate, aggregate);
3758                         }
3759                 }
3760                 else
3761                 {
3762                         // error message was put out by findFunction()
3763                         // Put on a dummy node for error recovery
3764                         ConstantUnion *unionArray = new ConstantUnion[1];
3765                         unionArray->setFConst(0.0f);
3766                         callNode = intermediate.addConstantUnion(unionArray, TType(EbtFloat, EbpUndefined, EvqConstExpr), loc);
3767                         recover();
3768                 }
3769         }
3770         delete fnCall;
3771         return callNode;
3772 }
3773
3774 TIntermTyped *TParseContext::addTernarySelection(TIntermTyped *cond, TIntermTyped *trueBlock, TIntermTyped *falseBlock, const TSourceLoc &loc)
3775 {
3776         if(boolErrorCheck(loc, cond))
3777                 recover();
3778
3779         if(trueBlock->getType() != falseBlock->getType())
3780         {
3781                 binaryOpError(loc, ":", trueBlock->getCompleteString(), falseBlock->getCompleteString());
3782                 recover();
3783                 return falseBlock;
3784         }
3785         // ESSL1 sections 5.2 and 5.7:
3786         // ESSL3 section 5.7:
3787         // Ternary operator is not among the operators allowed for structures/arrays.
3788         if(trueBlock->isArray() || trueBlock->getBasicType() == EbtStruct)
3789         {
3790                 error(loc, "ternary operator is not allowed for structures or arrays", ":");
3791                 recover();
3792                 return falseBlock;
3793         }
3794         return intermediate.addSelection(cond, trueBlock, falseBlock, loc);
3795 }
3796
3797 //
3798 // Parse an array of strings using yyparse.
3799 //
3800 // Returns 0 for success.
3801 //
3802 int PaParseStrings(int count, const char* const string[], const int length[],
3803                                    TParseContext* context) {
3804         if ((count == 0) || !string)
3805                 return 1;
3806
3807         if (glslang_initialize(context))
3808                 return 1;
3809
3810         int error = glslang_scan(count, string, length, context);
3811         if (!error)
3812                 error = glslang_parse(context);
3813
3814         glslang_finalize(context);
3815
3816         return (error == 0) && (context->numErrors() == 0) ? 0 : 1;
3817 }
3818
3819
3820