107620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org// 288f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill// Copyright (c) 2002-2014 The ANGLE Project Authors. All rights reserved. 307620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org// Use of this source code is governed by a BSD-style license that can be 407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org// found in the LICENSE file. 507620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org// 607620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 717732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/BuiltInFunctionEmulator.h" 8d4a3a3171ce8b72123e4eaa85a3c5d2b3130878cJamie Madill#include "compiler/translator/Compiler.h" 917732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/DetectCallDepth.h" 1017732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/ForLoopUnroll.h" 1117732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/Initialize.h" 1217732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/InitializeParseContext.h" 134a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo#include "compiler/translator/InitializeVariables.h" 146b9cb25980022d0c792d858bc6f6500c00a6c29dJamie Madill#include "compiler/translator/ParseContext.h" 15e740addbc2ab1a7928775814115771c96848ac18Zhenyao Mo#include "compiler/translator/RegenerateStructNames.h" 1617732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/RenameFunction.h" 17cd68fe7989afb5e5a9b1ae92ae1dae1478a9d1f6Zhenyao Mo#include "compiler/translator/ScalarizeVecAndMatConstructorArgs.h" 187cab38b594213c7c80f70871b72d40d30e878035Zhenyao Mo#include "compiler/translator/UnfoldShortCircuitAST.h" 1917732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/ValidateLimitations.h" 2017732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/ValidateOutputs.h" 2117732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/VariablePacker.h" 2217732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/depgraph/DependencyGraph.h" 2317732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/depgraph/DependencyGraphOutput.h" 2417732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/timing/RestrictFragmentShaderTiming.h" 2517732823f9c21bdba9cc51ffaceb545ce3857a8cGeoff Lang#include "compiler/translator/timing/RestrictVertexShaderTiming.h" 26da1ed36a3ba807337ec1d5a2009238c00ce4caabshannon.woods@transgaming.com#include "third_party/compiler/ArrayBoundsClamper.h" 27183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill#include "angle_gl.h" 28aa72d782074e8ea2e74304ca12b372c5e36e758fJamie Madill#include "common/utilities.h" 2907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 305508f39d0cffc9a68565bbff2e6f61332a509cdfJamie Madillbool IsWebGLBasedSpec(ShShaderSpec spec) 31430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com{ 32430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com return spec == SH_WEBGL_SPEC || spec == SH_CSS_SHADERS_SPEC; 33430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com} 34430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com 357faf1a14deb3cdfc9f9137de95f9fc1552b603bdZhenyao Mosize_t GetGlobalMaxTokenSize(ShShaderSpec spec) 3688f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill{ 3788f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill // WebGL defines a max token legnth of 256, while ES2 leaves max token 3888f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill // size undefined. ES3 defines a max size of 1024 characters. 397faf1a14deb3cdfc9f9137de95f9fc1552b603bdZhenyao Mo if (IsWebGLBasedSpec(spec)) 4088f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill { 4188f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill return 256; 4288f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill } 4388f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill else 4488f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill { 4588f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill return 1024; 4688f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill } 4788f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill} 4888f6e946b97ee15fe199e3fa151174c0bfeaa895Jamie Madill 49bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.orgnamespace { 504a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Moclass TScopedPoolAllocator 514a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo{ 524a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo public: 534a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo TScopedPoolAllocator(TPoolAllocator* allocator) : mAllocator(allocator) 544a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 55bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi mAllocator->push(); 56bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org SetGlobalPoolAllocator(mAllocator); 57bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org } 584a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo ~TScopedPoolAllocator() 594a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 60bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org SetGlobalPoolAllocator(NULL); 61bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi mAllocator->pop(); 62bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org } 63bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org 644a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo private: 65bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org TPoolAllocator* mAllocator; 66bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi}; 67bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi 684a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Moclass TScopedSymbolTableLevel 694a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo{ 704a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo public: 714a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo TScopedSymbolTableLevel(TSymbolTable* table) : mTable(table) 724a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 73bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi ASSERT(mTable->atBuiltInLevel()); 74bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi mTable->push(); 75bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi } 764a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo ~TScopedSymbolTableLevel() 774a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 78bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi while (!mTable->atBuiltInLevel()) 79bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi mTable->pop(); 80bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi } 81bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi 824a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo private: 83bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi TSymbolTable* mTable; 84bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org}; 85bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org} // namespace 86bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org 874a667fe96e55df4713532e3830dd215ac7696f53Zhenyao MoTShHandleBase::TShHandleBase() 884a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo{ 89bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org allocator.push(); 90bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org SetGlobalPoolAllocator(&allocator); 91bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org} 92bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org 934a667fe96e55df4713532e3830dd215ac7696f53Zhenyao MoTShHandleBase::~TShHandleBase() 944a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo{ 95bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org SetGlobalPoolAllocator(NULL); 96bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org allocator.popAll(); 97bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org} 98bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org 99183bde5527317fa2208401e5e6b803ef51a0fdcbJamie MadillTCompiler::TCompiler(sh::GLenum type, ShShaderSpec spec, ShShaderOutput output) 1004888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org : shaderType(type), 101f420c42442136e63c8c475446e01da1f6bcf5d32zmo@google.com shaderSpec(spec), 10268fe74aabbb4d8ae08aadcf22705f0d85a16e0b5Jamie Madill outputType(output), 103eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill maxUniformVectors(0), 104eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill maxExpressionComplexity(0), 105eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill maxCallStackDepth(0), 106cbb6b6a0416552b5e3fa8589194288532558ccb8shannon.woods%transgaming.com@gtempaccount.com fragmentPrecisionHigh(false), 1071d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com clampingStrategy(SH_CLAMP_WITH_CLAMP_INTRINSIC), 1089996b8e6b16c43f8002eea64266b595f05a3a2d1zmo@google.com builtInFunctionEmulator(type) 1094888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org{ 1104888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org} 1114888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org 1124888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.orgTCompiler::~TCompiler() 1134888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org{ 1144888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org} 1154888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org 1164888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.orgbool TCompiler::Init(const ShBuiltInResources& resources) 11707620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org{ 1180bbed38f417d490604909de5928d725fb39c5e3cshannon.woods%transgaming.com@gtempaccount.com shaderVersion = 100; 119183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill maxUniformVectors = (shaderType == GL_VERTEX_SHADER) ? 1208d8047995445882c73091578b889226323f38053gman@chromium.org resources.MaxVertexUniformVectors : 1218d8047995445882c73091578b889226323f38053gman@chromium.org resources.MaxFragmentUniformVectors; 122eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill maxExpressionComplexity = resources.MaxExpressionComplexity; 123eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill maxCallStackDepth = resources.MaxCallStackDepth; 124bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi 125bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi SetGlobalPoolAllocator(&allocator); 126bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org 12707620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org // Generate built-in symbol table. 12807620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org if (!InitBuiltInSymbolTable(resources)) 12907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org return false; 13007620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org InitExtensionBehavior(resources, extensionBehavior); 131cbb6b6a0416552b5e3fa8589194288532558ccb8shannon.woods%transgaming.com@gtempaccount.com fragmentPrecisionHigh = resources.FragmentPrecisionHigh == 1; 132bafcbaa3a31cc9175b757a60d6377bce01d3be9balokp@chromium.org 1331d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com arrayBoundsClamper.SetClampingStrategy(resources.ArrayIndexClampingStrategy); 1341d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com clampingStrategy = resources.ArrayIndexClampingStrategy; 1351d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com 136c23f4611be61bccdbfe2a5c43f63c4d98537ef9fdaniel@transgaming.com hashFunction = resources.HashFunction; 137c23f4611be61bccdbfe2a5c43f63c4d98537ef9fdaniel@transgaming.com 13807620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org return true; 13907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org} 14007620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 14107620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.orgbool TCompiler::compile(const char* const shaderStrings[], 142d64b3dab06c30da1e5dd9ba12667ff86388540e2shannon.woods@transgaming.com size_t numStrings, 14307620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org int compileOptions) 14407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org{ 145bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi TScopedPoolAllocator scopedAlloc(&allocator); 14607620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org clearResults(); 14707620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 14807620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org if (numStrings == 0) 14907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org return true; 15007620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 151b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org // If compiling for WebGL, validate loop and indexing as well. 1525508f39d0cffc9a68565bbff2e6f61332a509cdfJamie Madill if (IsWebGLBasedSpec(shaderSpec)) 153b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org compileOptions |= SH_VALIDATE_LOOP_INDEXING; 1541f29954dc7d433d6a69c4ec7bd07b7153f8d4b99alokp@chromium.org 1550f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org // First string is path of source file if flag is set. The actual source follows. 1560f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org const char* sourcePath = NULL; 157d64b3dab06c30da1e5dd9ba12667ff86388540e2shannon.woods@transgaming.com size_t firstSource = 0; 1580f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org if (compileOptions & SH_SOURCE_PATH) 1590f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org { 1600f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org sourcePath = shaderStrings[0]; 1610f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org ++firstSource; 1620f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org } 1630f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org 16407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org TIntermediate intermediate(infoSink); 16507620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org TParseContext parseContext(symbolTable, extensionBehavior, intermediate, 166dc4b4f85516fec32b746d1841c1df00865d96214zmo@google.com shaderType, shaderSpec, compileOptions, true, 1670f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org sourcePath, infoSink); 168cbb6b6a0416552b5e3fa8589194288532558ccb8shannon.woods%transgaming.com@gtempaccount.com parseContext.fragmentPrecisionHigh = fragmentPrecisionHigh; 1698156b6be065905c22db8f5dc3ab0fb715b0e1b52Alok Priyadarshi SetGlobalParseContext(&parseContext); 17007620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 17107620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org // We preserve symbols at the built-in level from compile-to-compile. 17207620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org // Start pushing the user-defined symbols at global level. 173bc3f1ac66061610b80500c9b3d91321ab332be44Alok Priyadarshi TScopedSymbolTableLevel scopedSymbolLevel(&symbolTable); 17407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 17507620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org // Parse shader. 17607620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org bool success = 1770f4cefe9462e53627f02f10b34d76f8665c72521apatrick@chromium.org (PaParseStrings(numStrings - firstSource, &shaderStrings[firstSource], NULL, &parseContext) == 0) && 17807620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org (parseContext.treeRoot != NULL); 1790bbed38f417d490604909de5928d725fb39c5e3cshannon.woods%transgaming.com@gtempaccount.com 1805524db0c05c8df6002489a077b18dd6fd5746448shannon.woods%transgaming.com@gtempaccount.com shaderVersion = parseContext.getShaderVersion(); 1810bbed38f417d490604909de5928d725fb39c5e3cshannon.woods%transgaming.com@gtempaccount.com 1824a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (success) 1834a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 184b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org TIntermNode* root = parseContext.treeRoot; 185b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org success = intermediate.postProcess(root); 186b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org 1876654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill // Disallow expressions deemed too complex. 1886654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill if (success && (compileOptions & SH_LIMIT_EXPRESSION_COMPLEXITY)) 1896654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill success = limitExpressionComplexity(root); 1906654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill 191b1762df486cad22cb5b07100f6765065f9bdc546zmo@google.com if (success) 192eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill success = detectCallDepth(root, infoSink, (compileOptions & SH_LIMIT_CALL_STACK_DEPTH) != 0); 193b1762df486cad22cb5b07100f6765065f9bdc546zmo@google.com 194183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill if (success && shaderVersion == 300 && shaderType == GL_FRAGMENT_SHADER) 19505a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill success = validateOutputs(root); 19605a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill 197b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org if (success && (compileOptions & SH_VALIDATE_LOOP_INDEXING)) 198b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org success = validateLimitations(root); 19907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 20066ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com if (success && (compileOptions & SH_TIMING_RESTRICTIONS)) 20177222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.com success = enforceTimingRestrictions(root, (compileOptions & SH_DEPENDENCY_GRAPH) != 0); 20266ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com 203430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com if (success && shaderSpec == SH_CSS_SHADERS_SPEC) 204430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com rewriteCSSShader(root); 205430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com 2060c6bb7a653f52baa3dab4492a3599ddcacf076edzmo@google.com // Unroll for-loop markup needs to happen after validateLimitations pass. 2070c6bb7a653f52baa3dab4492a3599ddcacf076edzmo@google.com if (success && (compileOptions & SH_UNROLL_FOR_LOOP_WITH_INTEGER_INDEX)) 2083cdfcce86b38ef31a0afd71855887193a7924468Zhenyao Mo { 2093cdfcce86b38ef31a0afd71855887193a7924468Zhenyao Mo ForLoopUnrollMarker marker(ForLoopUnrollMarker::kIntegerIndex); 210550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo root->traverse(&marker); 211550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo } 212550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo if (success && (compileOptions & SH_UNROLL_FOR_LOOP_WITH_SAMPLER_ARRAY_INDEX)) 2133cdfcce86b38ef31a0afd71855887193a7924468Zhenyao Mo { 2143cdfcce86b38ef31a0afd71855887193a7924468Zhenyao Mo ForLoopUnrollMarker marker(ForLoopUnrollMarker::kSamplerArrayIndex); 215550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo root->traverse(&marker); 216550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo if (marker.samplerArrayIndexIsFloatLoopIndex()) 217550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo { 218550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo infoSink.info.prefix(EPrefixError); 219550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo infoSink.info << "sampler array index is float loop index"; 220550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo success = false; 221550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo } 222550c600b99d7ee2463e5878d0a9f66ea24c1414aZhenyao Mo } 2230c6bb7a653f52baa3dab4492a3599ddcacf076edzmo@google.com 22432e97315e2a55557ad7c372239e0823a81243221zmo@google.com // Built-in function emulation needs to happen after validateLimitations pass. 22532e97315e2a55557ad7c372239e0823a81243221zmo@google.com if (success && (compileOptions & SH_EMULATE_BUILT_IN_FUNCTIONS)) 22632e97315e2a55557ad7c372239e0823a81243221zmo@google.com builtInFunctionEmulator.MarkBuiltInFunctionsForEmulation(root); 22732e97315e2a55557ad7c372239e0823a81243221zmo@google.com 2284167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com // Clamping uniform array bounds needs to happen after validateLimitations pass. 2294167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com if (success && (compileOptions & SH_CLAMP_INDIRECT_ARRAY_BOUNDS)) 2304167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com arrayBoundsClamper.MarkIndirectArrayBoundsForClamping(root); 2314167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com 232183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill if (success && shaderType == GL_VERTEX_SHADER && (compileOptions & SH_INIT_GL_POSITION)) 2334a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo initializeGLPosition(root); 234ac44cd2b072916b83f079bbfda66636491279d2eZhenyao Mo 2354a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (success && (compileOptions & SH_UNFOLD_SHORT_CIRCUIT)) 2364a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 2377cab38b594213c7c80f70871b72d40d30e878035Zhenyao Mo UnfoldShortCircuitAST unfoldShortCircuit; 2387cab38b594213c7c80f70871b72d40d30e878035Zhenyao Mo root->traverse(&unfoldShortCircuit); 2397cab38b594213c7c80f70871b72d40d30e878035Zhenyao Mo unfoldShortCircuit.updateTree(); 2407cab38b594213c7c80f70871b72d40d30e878035Zhenyao Mo } 2417cab38b594213c7c80f70871b72d40d30e878035Zhenyao Mo 2424a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (success && (compileOptions & SH_VARIABLES)) 2434a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 24474da9f2f24093e828b30071cebc09f99088fc13cZhenyao Mo collectVariables(root); 2454a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (compileOptions & SH_ENFORCE_PACKING_RESTRICTIONS) 2464a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 2478d8047995445882c73091578b889226323f38053gman@chromium.org success = enforcePackingRestrictions(); 2484a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (!success) 2494a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 250075edd84dd682b91279132317d34b09e8028ae6fJamie Madill infoSink.info.prefix(EPrefixError); 251075edd84dd682b91279132317d34b09e8028ae6fJamie Madill infoSink.info << "too many uniforms"; 2528d8047995445882c73091578b889226323f38053gman@chromium.org } 2538d8047995445882c73091578b889226323f38053gman@chromium.org } 254183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill if (success && shaderType == GL_VERTEX_SHADER && 2554a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo (compileOptions & SH_INIT_VARYINGS_WITHOUT_STATIC_USE)) 2564a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo initializeVaryingsWithoutStaticUse(root); 2578d8047995445882c73091578b889226323f38053gman@chromium.org } 258fd747b861195a03df634a722a9cf3505dcd41253zmo@google.com 259cd68fe7989afb5e5a9b1ae92ae1dae1478a9d1f6Zhenyao Mo if (success && (compileOptions & SH_SCALARIZE_VEC_AND_MAT_CONSTRUCTOR_ARGS)) 260cd68fe7989afb5e5a9b1ae92ae1dae1478a9d1f6Zhenyao Mo { 261daf565720b9e26a004e8716a3f52d4a63b988217Zhenyao Mo ScalarizeVecAndMatConstructorArgs scalarizer( 262daf565720b9e26a004e8716a3f52d4a63b988217Zhenyao Mo shaderType, fragmentPrecisionHigh); 263cd68fe7989afb5e5a9b1ae92ae1dae1478a9d1f6Zhenyao Mo root->traverse(&scalarizer); 264cd68fe7989afb5e5a9b1ae92ae1dae1478a9d1f6Zhenyao Mo } 265cd68fe7989afb5e5a9b1ae92ae1dae1478a9d1f6Zhenyao Mo 266e740addbc2ab1a7928775814115771c96848ac18Zhenyao Mo if (success && (compileOptions & SH_REGENERATE_STRUCT_NAMES)) 267e740addbc2ab1a7928775814115771c96848ac18Zhenyao Mo { 268e740addbc2ab1a7928775814115771c96848ac18Zhenyao Mo RegenerateStructNames gen(symbolTable, shaderVersion); 269e740addbc2ab1a7928775814115771c96848ac18Zhenyao Mo root->traverse(&gen); 270e740addbc2ab1a7928775814115771c96848ac18Zhenyao Mo } 271e740addbc2ab1a7928775814115771c96848ac18Zhenyao Mo 2724888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org if (success && (compileOptions & SH_INTERMEDIATE_TREE)) 273b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org intermediate.outputTree(root); 27407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 2754888ceb6681c3668d3afcbdafdbe2b7efdaa3d04alokp@chromium.org if (success && (compileOptions & SH_OBJECT_CODE)) 276b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org translate(root); 27707620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org } 27807620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 27907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org // Cleanup memory. 28007620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org intermediate.remove(parseContext.treeRoot); 2817faf1a14deb3cdfc9f9137de95f9fc1552b603bdZhenyao Mo SetGlobalParseContext(NULL); 28207620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org return success; 28307620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org} 28407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 28549a8887b73345356e147702be9eeb5b40236953cNicolas Capensbool TCompiler::InitBuiltInSymbolTable(const ShBuiltInResources &resources) 28607620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org{ 28718b4c4b56a1a31e1b1c9fccf01f1ffd46504ead9shannon.woods%transgaming.com@gtempaccount.com compileResources = resources; 2882d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods setResourceString(); 2892ac0be9df9be957eb8fe504a88fa2e10c8ae9dc9shannonwoods@chromium.org 29049a8887b73345356e147702be9eeb5b40236953cNicolas Capens assert(symbolTable.isEmpty()); 29149a8887b73345356e147702be9eeb5b40236953cNicolas Capens symbolTable.push(); // COMMON_BUILTINS 29249a8887b73345356e147702be9eeb5b40236953cNicolas Capens symbolTable.push(); // ESSL1_BUILTINS 29349a8887b73345356e147702be9eeb5b40236953cNicolas Capens symbolTable.push(); // ESSL3_BUILTINS 29449a8887b73345356e147702be9eeb5b40236953cNicolas Capens 29549a8887b73345356e147702be9eeb5b40236953cNicolas Capens TPublicType integer; 29649a8887b73345356e147702be9eeb5b40236953cNicolas Capens integer.type = EbtInt; 29749a8887b73345356e147702be9eeb5b40236953cNicolas Capens integer.primarySize = 1; 29849a8887b73345356e147702be9eeb5b40236953cNicolas Capens integer.secondarySize = 1; 29949a8887b73345356e147702be9eeb5b40236953cNicolas Capens integer.array = false; 30049a8887b73345356e147702be9eeb5b40236953cNicolas Capens 30149a8887b73345356e147702be9eeb5b40236953cNicolas Capens TPublicType floatingPoint; 30249a8887b73345356e147702be9eeb5b40236953cNicolas Capens floatingPoint.type = EbtFloat; 30349a8887b73345356e147702be9eeb5b40236953cNicolas Capens floatingPoint.primarySize = 1; 30449a8887b73345356e147702be9eeb5b40236953cNicolas Capens floatingPoint.secondarySize = 1; 30549a8887b73345356e147702be9eeb5b40236953cNicolas Capens floatingPoint.array = false; 30649a8887b73345356e147702be9eeb5b40236953cNicolas Capens 307a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo TPublicType sampler; 308a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo sampler.primarySize = 1; 309a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo sampler.secondarySize = 1; 310a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo sampler.array = false; 311a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo 31249a8887b73345356e147702be9eeb5b40236953cNicolas Capens switch(shaderType) 31349a8887b73345356e147702be9eeb5b40236953cNicolas Capens { 314183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill case GL_FRAGMENT_SHADER: 31549a8887b73345356e147702be9eeb5b40236953cNicolas Capens symbolTable.setDefaultPrecision(integer, EbpMedium); 31649a8887b73345356e147702be9eeb5b40236953cNicolas Capens break; 317183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill case GL_VERTEX_SHADER: 31849a8887b73345356e147702be9eeb5b40236953cNicolas Capens symbolTable.setDefaultPrecision(integer, EbpHigh); 31949a8887b73345356e147702be9eeb5b40236953cNicolas Capens symbolTable.setDefaultPrecision(floatingPoint, EbpHigh); 32049a8887b73345356e147702be9eeb5b40236953cNicolas Capens break; 3214a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo default: 3224a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo assert(false && "Language not supported"); 32349a8887b73345356e147702be9eeb5b40236953cNicolas Capens } 324a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo // We set defaults for all the sampler types, even those that are 325a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo // only available if an extension exists. 326a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo for (int samplerType = EbtGuardSamplerBegin + 1; 3274a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo samplerType < EbtGuardSamplerEnd; ++samplerType) 3284a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 329a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo sampler.type = static_cast<TBasicType>(samplerType); 330a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo symbolTable.setDefaultPrecision(sampler, EbpLow); 331a5a1dfc6ec47c5e5aef6d871a48eef25a44dc407Zhenyao Mo } 33249a8887b73345356e147702be9eeb5b40236953cNicolas Capens 3331b45214aef6439fdeb6291e9d9fd1da61dec618cJamie Madill InsertBuiltInFunctions(shaderType, shaderSpec, resources, symbolTable); 3342ac0be9df9be957eb8fe504a88fa2e10c8ae9dc9shannonwoods@chromium.org 33549a8887b73345356e147702be9eeb5b40236953cNicolas Capens IdentifyBuiltIns(shaderType, shaderSpec, resources, symbolTable); 33649a8887b73345356e147702be9eeb5b40236953cNicolas Capens 33749a8887b73345356e147702be9eeb5b40236953cNicolas Capens return true; 33807620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org} 33907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 3402d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woodsvoid TCompiler::setResourceString() 3412d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods{ 3422d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods std::ostringstream strstream; 3432d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods strstream << ":MaxVertexAttribs:" << compileResources.MaxVertexAttribs 3442d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxVertexUniformVectors:" << compileResources.MaxVertexUniformVectors 3452d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxVaryingVectors:" << compileResources.MaxVaryingVectors 3462d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxVertexTextureImageUnits:" << compileResources.MaxVertexTextureImageUnits 3472d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxCombinedTextureImageUnits:" << compileResources.MaxCombinedTextureImageUnits 3482d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxTextureImageUnits:" << compileResources.MaxTextureImageUnits 3492d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxFragmentUniformVectors:" << compileResources.MaxFragmentUniformVectors 3502d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxDrawBuffers:" << compileResources.MaxDrawBuffers 3512d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":OES_standard_derivatives:" << compileResources.OES_standard_derivatives 3522d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":OES_EGL_image_external:" << compileResources.OES_EGL_image_external 3532d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":ARB_texture_rectangle:" << compileResources.ARB_texture_rectangle 3542d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":EXT_draw_buffers:" << compileResources.EXT_draw_buffers 3552d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":FragmentPrecisionHigh:" << compileResources.FragmentPrecisionHigh 3562d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxExpressionComplexity:" << compileResources.MaxExpressionComplexity 3572d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxCallStackDepth:" << compileResources.MaxCallStackDepth 3582d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":EXT_frag_depth:" << compileResources.EXT_frag_depth 3592d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":EXT_shader_texture_lod:" << compileResources.EXT_shader_texture_lod 3602d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxVertexOutputVectors:" << compileResources.MaxVertexOutputVectors 3612d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxFragmentInputVectors:" << compileResources.MaxFragmentInputVectors 3622d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MinProgramTexelOffset:" << compileResources.MinProgramTexelOffset 3632d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods << ":MaxProgramTexelOffset:" << compileResources.MaxProgramTexelOffset; 3642d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods 3652d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods builtInResourcesString = strstream.str(); 3662d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods} 3672d76e5f66595e1cef04f4ad678deda0d0e4643d7Shannon Woods 36807620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.orgvoid TCompiler::clearResults() 36907620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org{ 3704167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com arrayBoundsClamper.Cleanup(); 37107620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org infoSink.info.erase(); 37207620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org infoSink.obj.erase(); 37307620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org infoSink.debug.erase(); 37407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 375ed27c7296c9bc4e9d9901943a8a0147513d11fc6Jamie Madill attributes.clear(); 376ed27c7296c9bc4e9d9901943a8a0147513d11fc6Jamie Madill outputVariables.clear(); 37707620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org uniforms.clear(); 37823a8a433529d9db23882c702a29d5e594841563dJamie Madill expandedUniforms.clear(); 379d2d340b0da87296b1ec04799ef4c811966bfb7aeZhenyao Mo varyings.clear(); 38023a8a433529d9db23882c702a29d5e594841563dJamie Madill expandedVaryings.clear(); 381ed27c7296c9bc4e9d9901943a8a0147513d11fc6Jamie Madill interfaceBlocks.clear(); 382a3b4ab4c2beb1c020e474007ded4bed4a2383601zmo@google.com 383a3b4ab4c2beb1c020e474007ded4bed4a2383601zmo@google.com builtInFunctionEmulator.Cleanup(); 3840aa3b5a2b216c9033e7bb59f6dde3acf46cf2260daniel@transgaming.com 3850aa3b5a2b216c9033e7bb59f6dde3acf46cf2260daniel@transgaming.com nameMap.clear(); 38607620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org} 38707620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org 388eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madillbool TCompiler::detectCallDepth(TIntermNode* root, TInfoSink& infoSink, bool limitCallStackDepth) 389b1762df486cad22cb5b07100f6765065f9bdc546zmo@google.com{ 390eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill DetectCallDepth detect(infoSink, limitCallStackDepth, maxCallStackDepth); 391b1762df486cad22cb5b07100f6765065f9bdc546zmo@google.com root->traverse(&detect); 3924a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo switch (detect.detectCallDepth()) 3934a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 3944a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo case DetectCallDepth::kErrorNone: 3954a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo return true; 3964a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo case DetectCallDepth::kErrorMissingMain: 3974a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo infoSink.info.prefix(EPrefixError); 3984a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo infoSink.info << "Missing main()"; 3994a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo return false; 4004a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo case DetectCallDepth::kErrorRecursion: 4014a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo infoSink.info.prefix(EPrefixError); 4024a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo infoSink.info << "Function recursion detected"; 4034a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo return false; 4044a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo case DetectCallDepth::kErrorMaxDepthExceeded: 4054a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo infoSink.info.prefix(EPrefixError); 4064a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo infoSink.info << "Function call stack too deep"; 4074a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo return false; 4084a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo default: 4094a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo UNREACHABLE(); 4104a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo return false; 411b1762df486cad22cb5b07100f6765065f9bdc546zmo@google.com } 412b1762df486cad22cb5b07100f6765065f9bdc546zmo@google.com} 413b1762df486cad22cb5b07100f6765065f9bdc546zmo@google.com 41405a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madillbool TCompiler::validateOutputs(TIntermNode* root) 41505a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill{ 41605a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill ValidateOutputs validateOutputs(infoSink.info, compileResources.MaxDrawBuffers); 41705a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill root->traverse(&validateOutputs); 41805a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill return (validateOutputs.numErrors() == 0); 41905a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill} 42005a80cebc3ce8ca07ae10e2970863e3cc603c756Jamie Madill 421430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.comvoid TCompiler::rewriteCSSShader(TIntermNode* root) 422430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com{ 423430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com RenameFunction renamer("main(", "css_main("); 424430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com root->traverse(&renamer); 425430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com} 426430f5e0c75ade69935befb55d2592635f70255cemaxvujovic@gmail.com 4274a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mobool TCompiler::validateLimitations(TIntermNode* root) 4284a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo{ 429b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org ValidateLimitations validate(shaderType, infoSink.info); 430b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org root->traverse(&validate); 431b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org return validate.numErrors() == 0; 432b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org} 433b59a778cfe7e36dca41c2cc44198da511f447be8alokp@chromium.org 43477222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.combool TCompiler::enforceTimingRestrictions(TIntermNode* root, bool outputGraph) 43566ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com{ 4364a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (shaderSpec != SH_WEBGL_SPEC) 4374a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 43866ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com infoSink.info << "Timing restrictions must be enforced under the WebGL spec."; 43966ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com return false; 44066ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com } 44166ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com 442183bde5527317fa2208401e5e6b803ef51a0fdcbJamie Madill if (shaderType == GL_FRAGMENT_SHADER) 4434a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 44466ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com TDependencyGraph graph(root); 44566ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com 44666ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com // Output any errors first. 44777222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.com bool success = enforceFragmentShaderTimingRestrictions(graph); 4485508f39d0cffc9a68565bbff2e6f61332a509cdfJamie Madill 44966ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com // Then, output the dependency graph. 4504a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (outputGraph) 4514a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 45266ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com TDependencyGraphOutput output(infoSink.info); 45366ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com output.outputAllSpanningTrees(graph); 45466ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com } 4555508f39d0cffc9a68565bbff2e6f61332a509cdfJamie Madill 45666ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com return success; 45766ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com } 4584a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo else 4594a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 46077222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.com return enforceVertexShaderTimingRestrictions(root); 46166ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com } 46266ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com} 46366ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com 464eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madillbool TCompiler::limitExpressionComplexity(TIntermNode* root) 465eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill{ 4666654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill TMaxDepthTraverser traverser(maxExpressionComplexity+1); 467eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill root->traverse(&traverser); 4686654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill 4696654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill if (traverser.getMaxDepth() > maxExpressionComplexity) 4706654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill { 4716654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill infoSink.info << "Expression too complex."; 4726654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill return false; 4736654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill } 4746654bc93f1ca30c2a5d7403f56c94d668c650ca0Jamie Madill 475eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill TDependencyGraph graph(root); 476eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill 477eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill for (TFunctionCallVector::const_iterator iter = graph.beginUserDefinedFunctionCalls(); 478eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill iter != graph.endUserDefinedFunctionCalls(); 479eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill ++iter) 480eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill { 481eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill TGraphFunctionCall* samplerSymbol = *iter; 482eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill TDependencyGraphTraverser graphTraverser; 483eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill samplerSymbol->traverse(&graphTraverser); 484eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill } 485eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill 486eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill return true; 487eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill} 488eb1a010f0f996b3742fd34b92ffaf9014c943528Jamie Madill 48977222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.combool TCompiler::enforceFragmentShaderTimingRestrictions(const TDependencyGraph& graph) 49066ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com{ 49177222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.com RestrictFragmentShaderTiming restrictor(infoSink.info); 49266ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com restrictor.enforceRestrictions(graph); 49366ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com return restrictor.numErrors() == 0; 49466ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com} 49566ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com 49677222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.combool TCompiler::enforceVertexShaderTimingRestrictions(TIntermNode* root) 49766ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com{ 49877222c9715408518c21a7f359b8f0f9af8c4bfddmaxvujovic@gmail.com RestrictVertexShaderTiming restrictor(infoSink.info); 49966ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com restrictor.enforceRestrictions(root); 50066ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com return restrictor.numErrors() == 0; 50166ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com} 50266ebd0143ea40a9beb83eab5d86e24f52825b3famaxvujovic@gmail.com 50374da9f2f24093e828b30071cebc09f99088fc13cZhenyao Movoid TCompiler::collectVariables(TIntermNode* root) 50407620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org{ 505a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill sh::CollectVariables collect(&attributes, 506a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill &outputVariables, 507a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill &uniforms, 508a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill &varyings, 509a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill &interfaceBlocks, 510a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill hashFunction); 51107620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org root->traverse(&collect); 51223a8a433529d9db23882c702a29d5e594841563dJamie Madill 51323a8a433529d9db23882c702a29d5e594841563dJamie Madill // For backwards compatiblity with ShGetVariableInfo, expand struct 51423a8a433529d9db23882c702a29d5e594841563dJamie Madill // uniforms and varyings into separate variables for each field. 515a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill sh::ExpandVariables(uniforms, &expandedUniforms); 516a2fbb84095e91eec3957d0a1707dc740f0e62c50Jamie Madill sh::ExpandVariables(varyings, &expandedVaryings); 51707620a585ae04ba6a86f0c04a27b3cabd10cc6b8alokp@chromium.org} 518fd747b861195a03df634a722a9cf3505dcd41253zmo@google.com 5198d8047995445882c73091578b889226323f38053gman@chromium.orgbool TCompiler::enforcePackingRestrictions() 5208d8047995445882c73091578b889226323f38053gman@chromium.org{ 5218d8047995445882c73091578b889226323f38053gman@chromium.org VariablePacker packer; 52223a8a433529d9db23882c702a29d5e594841563dJamie Madill return packer.CheckVariablesWithinPackingLimits(maxUniformVectors, expandedUniforms); 5238d8047995445882c73091578b889226323f38053gman@chromium.org} 5248d8047995445882c73091578b889226323f38053gman@chromium.org 5254a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Movoid TCompiler::initializeGLPosition(TIntermNode* root) 5264a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo{ 5274a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo InitializeVariables::InitVariableInfoList variables; 5284a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo InitializeVariables::InitVariableInfo var( 5294a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo "gl_Position", TType(EbtFloat, EbpUndefined, EvqPosition, 4)); 5304a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo variables.push_back(var); 5314a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo InitializeVariables initializer(variables); 5324a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo root->traverse(&initializer); 5334a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo} 5344a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo 5354a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Movoid TCompiler::initializeVaryingsWithoutStaticUse(TIntermNode* root) 5364a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo{ 5374a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo InitializeVariables::InitVariableInfoList variables; 5384a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo for (size_t ii = 0; ii < varyings.size(); ++ii) 5394a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 540a718c1e00264edf434aeddf7beb14f4fae0f07a0Jamie Madill const sh::Varying& varying = varyings[ii]; 5414a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo if (varying.staticUse) 5424a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo continue; 543aa72d782074e8ea2e74304ca12b372c5e36e758fJamie Madill unsigned char primarySize = static_cast<unsigned char>(gl::VariableColumnCount(varying.type)); 544aa72d782074e8ea2e74304ca12b372c5e36e758fJamie Madill unsigned char secondarySize = static_cast<unsigned char>(gl::VariableRowCount(varying.type)); 545a718c1e00264edf434aeddf7beb14f4fae0f07a0Jamie Madill TType type(EbtFloat, EbpUndefined, EvqVaryingOut, primarySize, secondarySize, varying.isArray()); 5464a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo TString name = varying.name.c_str(); 547a718c1e00264edf434aeddf7beb14f4fae0f07a0Jamie Madill if (varying.isArray()) 5484a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo { 549a718c1e00264edf434aeddf7beb14f4fae0f07a0Jamie Madill type.setArraySize(varying.arraySize); 5504a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo name = name.substr(0, name.find_first_of('[')); 5514a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo } 5524a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo 5534a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo InitializeVariables::InitVariableInfo var(name, type); 5544a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo variables.push_back(var); 5554a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo } 5564a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo InitializeVariables initializer(variables); 5574a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo root->traverse(&initializer); 5584a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo} 5594a667fe96e55df4713532e3830dd215ac7696f53Zhenyao Mo 5605601ea0d66442518d4745bb02b7619485b9d305bzmo@google.comconst TExtensionBehavior& TCompiler::getExtensionBehavior() const 5615601ea0d66442518d4745bb02b7619485b9d305bzmo@google.com{ 5625601ea0d66442518d4745bb02b7619485b9d305bzmo@google.com return extensionBehavior; 5635601ea0d66442518d4745bb02b7619485b9d305bzmo@google.com} 56432e97315e2a55557ad7c372239e0823a81243221zmo@google.com 56518b4c4b56a1a31e1b1c9fccf01f1ffd46504ead9shannon.woods%transgaming.com@gtempaccount.comconst ShBuiltInResources& TCompiler::getResources() const 56618b4c4b56a1a31e1b1c9fccf01f1ffd46504ead9shannon.woods%transgaming.com@gtempaccount.com{ 56718b4c4b56a1a31e1b1c9fccf01f1ffd46504ead9shannon.woods%transgaming.com@gtempaccount.com return compileResources; 56818b4c4b56a1a31e1b1c9fccf01f1ffd46504ead9shannon.woods%transgaming.com@gtempaccount.com} 56918b4c4b56a1a31e1b1c9fccf01f1ffd46504ead9shannon.woods%transgaming.com@gtempaccount.com 5701d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.comconst ArrayBoundsClamper& TCompiler::getArrayBoundsClamper() const 57132e97315e2a55557ad7c372239e0823a81243221zmo@google.com{ 5721d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com return arrayBoundsClamper; 57332e97315e2a55557ad7c372239e0823a81243221zmo@google.com} 5744167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com 5751d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.comShArrayIndexClampingStrategy TCompiler::getArrayIndexClampingStrategy() const 5764167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com{ 5771d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com return clampingStrategy; 5784167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com} 5794167cc910276be723901f187dec45d04275abb7edaniel@transgaming.com 5801d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.comconst BuiltInFunctionEmulator& TCompiler::getBuiltInFunctionEmulator() const 5811d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com{ 5821d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com return builtInFunctionEmulator; 5831d432bb570bd175c3cdc51629a386e324e98b95bshannon.woods@transgaming.com} 584