summaryrefslogtreecommitdiffstats
path: root/src/3rdparty/angle/src/compiler/translator/Compiler.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/3rdparty/angle/src/compiler/translator/Compiler.cpp')
-rw-r--r--src/3rdparty/angle/src/compiler/translator/Compiler.cpp107
1 files changed, 75 insertions, 32 deletions
diff --git a/src/3rdparty/angle/src/compiler/translator/Compiler.cpp b/src/3rdparty/angle/src/compiler/translator/Compiler.cpp
index 5c62a64d10..534861ca70 100644
--- a/src/3rdparty/angle/src/compiler/translator/Compiler.cpp
+++ b/src/3rdparty/angle/src/compiler/translator/Compiler.cpp
@@ -4,7 +4,6 @@
// found in the LICENSE file.
//
-#include "compiler/translator/BuiltInFunctionEmulator.h"
#include "compiler/translator/Compiler.h"
#include "compiler/translator/DetectCallDepth.h"
#include "compiler/translator/ForLoopUnroll.h"
@@ -126,7 +125,8 @@ TCompiler::TCompiler(sh::GLenum type, ShShaderSpec spec, ShShaderOutput output)
maxCallStackDepth(0),
fragmentPrecisionHigh(false),
clampingStrategy(SH_CLAMP_WITH_CLAMP_INTRINSIC),
- builtInFunctionEmulator(type)
+ builtInFunctionEmulator(),
+ mSourcePath(NULL)
{
}
@@ -159,33 +159,41 @@ bool TCompiler::Init(const ShBuiltInResources& resources)
return true;
}
-bool TCompiler::compile(const char* const shaderStrings[],
- size_t numStrings,
- int compileOptions)
+TIntermNode *TCompiler::compileTreeForTesting(const char* const shaderStrings[],
+ size_t numStrings, int compileOptions)
+{
+ return compileTreeImpl(shaderStrings, numStrings, compileOptions);
+}
+
+TIntermNode *TCompiler::compileTreeImpl(const char* const shaderStrings[],
+ size_t numStrings, int compileOptions)
{
- TScopedPoolAllocator scopedAlloc(&allocator);
clearResults();
- if (numStrings == 0)
- return true;
+ ASSERT(numStrings > 0);
+ ASSERT(GetGlobalPoolAllocator());
+
+ // Reset the extension behavior for each compilation unit.
+ ResetExtensionBehavior(extensionBehavior);
// If compiling for WebGL, validate loop and indexing as well.
if (IsWebGLBasedSpec(shaderSpec))
compileOptions |= SH_VALIDATE_LOOP_INDEXING;
// First string is path of source file if flag is set. The actual source follows.
- const char* sourcePath = NULL;
size_t firstSource = 0;
if (compileOptions & SH_SOURCE_PATH)
{
- sourcePath = shaderStrings[0];
+ mSourcePath = shaderStrings[0];
++firstSource;
}
+ bool debugShaderPrecision = getResources().WEBGL_debug_shader_precision == 1;
TIntermediate intermediate(infoSink);
TParseContext parseContext(symbolTable, extensionBehavior, intermediate,
shaderType, shaderSpec, compileOptions, true,
- sourcePath, infoSink);
+ infoSink, debugShaderPrecision);
+
parseContext.fragmentPrecisionHigh = fragmentPrecisionHigh;
SetGlobalParseContext(&parseContext);
@@ -206,6 +214,8 @@ bool TCompiler::compile(const char* const shaderStrings[],
success = false;
}
+ TIntermNode *root = NULL;
+
if (success)
{
mPragma = parseContext.pragma();
@@ -214,7 +224,7 @@ bool TCompiler::compile(const char* const shaderStrings[],
symbolTable.setGlobalInvariant();
}
- TIntermNode* root = parseContext.treeRoot;
+ root = parseContext.treeRoot;
success = intermediate.postProcess(root);
// Disallow expressions deemed too complex.
@@ -255,8 +265,11 @@ bool TCompiler::compile(const char* const shaderStrings[],
}
// Built-in function emulation needs to happen after validateLimitations pass.
- if (success && (compileOptions & SH_EMULATE_BUILT_IN_FUNCTIONS))
+ if (success)
+ {
+ initBuiltInFunctionEmulator(&builtInFunctionEmulator, compileOptions);
builtInFunctionEmulator.MarkBuiltInFunctionsForEmulation(root);
+ }
// Clamping uniform array bounds needs to happen after validateLimitations pass.
if (success && (compileOptions & SH_CLAMP_INDIRECT_ARRAY_BOUNDS))
@@ -301,18 +314,37 @@ bool TCompiler::compile(const char* const shaderStrings[],
RegenerateStructNames gen(symbolTable, shaderVersion);
root->traverse(&gen);
}
-
- if (success && (compileOptions & SH_INTERMEDIATE_TREE))
- intermediate.outputTree(root);
-
- if (success && (compileOptions & SH_OBJECT_CODE))
- translate(root);
}
- // Cleanup memory.
- intermediate.remove(parseContext.treeRoot);
SetGlobalParseContext(NULL);
- return success;
+ if (success)
+ return root;
+
+ return NULL;
+}
+
+bool TCompiler::compile(const char* const shaderStrings[],
+ size_t numStrings, int compileOptions)
+{
+ if (numStrings == 0)
+ return true;
+
+ TScopedPoolAllocator scopedAlloc(&allocator);
+ TIntermNode *root = compileTreeImpl(shaderStrings, numStrings, compileOptions);
+
+ if (root)
+ {
+ if (compileOptions & SH_INTERMEDIATE_TREE)
+ TIntermediate::outputTree(root, infoSink.info);
+
+ if (compileOptions & SH_OBJECT_CODE)
+ translate(root, compileOptions);
+
+ // The IntermNode tree doesn't need to be deleted here, since the
+ // memory will be freed in a big chunk by the PoolAllocator.
+ return true;
+ }
+ return false;
}
bool TCompiler::InitBuiltInSymbolTable(const ShBuiltInResources &resources)
@@ -390,11 +422,15 @@ void TCompiler::setResourceString()
<< ":MaxCallStackDepth:" << compileResources.MaxCallStackDepth
<< ":EXT_frag_depth:" << compileResources.EXT_frag_depth
<< ":EXT_shader_texture_lod:" << compileResources.EXT_shader_texture_lod
+ << ":EXT_shader_framebuffer_fetch:" << compileResources.EXT_shader_framebuffer_fetch
+ << ":NV_shader_framebuffer_fetch:" << compileResources.NV_shader_framebuffer_fetch
+ << ":ARM_shader_framebuffer_fetch:" << compileResources.ARM_shader_framebuffer_fetch
<< ":MaxVertexOutputVectors:" << compileResources.MaxVertexOutputVectors
<< ":MaxFragmentInputVectors:" << compileResources.MaxFragmentInputVectors
<< ":MinProgramTexelOffset:" << compileResources.MinProgramTexelOffset
<< ":MaxProgramTexelOffset:" << compileResources.MaxProgramTexelOffset
- << ":NV_draw_buffers:" << compileResources.NV_draw_buffers;
+ << ":NV_draw_buffers:" << compileResources.NV_draw_buffers
+ << ":WEBGL_debug_shader_precision:" << compileResources.WEBGL_debug_shader_precision;
builtInResourcesString = strstream.str();
}
@@ -416,27 +452,29 @@ void TCompiler::clearResults()
builtInFunctionEmulator.Cleanup();
nameMap.clear();
+
+ mSourcePath = NULL;
}
-bool TCompiler::detectCallDepth(TIntermNode* root, TInfoSink& infoSink, bool limitCallStackDepth)
+bool TCompiler::detectCallDepth(TIntermNode* inputRoot, TInfoSink& inputInfoSink, bool limitCallStackDepth)
{
- DetectCallDepth detect(infoSink, limitCallStackDepth, maxCallStackDepth);
- root->traverse(&detect);
+ DetectCallDepth detect(inputInfoSink, limitCallStackDepth, maxCallStackDepth);
+ inputRoot->traverse(&detect);
switch (detect.detectCallDepth())
{
case DetectCallDepth::kErrorNone:
return true;
case DetectCallDepth::kErrorMissingMain:
- infoSink.info.prefix(EPrefixError);
- infoSink.info << "Missing main()";
+ inputInfoSink.info.prefix(EPrefixError);
+ inputInfoSink.info << "Missing main()";
return false;
case DetectCallDepth::kErrorRecursion:
- infoSink.info.prefix(EPrefixError);
- infoSink.info << "Function recursion detected";
+ inputInfoSink.info.prefix(EPrefixError);
+ inputInfoSink.info << "Function recursion detected";
return false;
case DetectCallDepth::kErrorMaxDepthExceeded:
- infoSink.info.prefix(EPrefixError);
- infoSink.info << "Function call stack too deep";
+ inputInfoSink.info.prefix(EPrefixError);
+ inputInfoSink.info << "Function call stack too deep";
return false;
default:
UNREACHABLE();
@@ -594,6 +632,11 @@ const TExtensionBehavior& TCompiler::getExtensionBehavior() const
return extensionBehavior;
}
+const char *TCompiler::getSourcePath() const
+{
+ return mSourcePath;
+}
+
const ShBuiltInResources& TCompiler::getResources() const
{
return compileResources;