summaryrefslogtreecommitdiffstats
path: root/gfx/angle/src/libANGLE/Compiler.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'gfx/angle/src/libANGLE/Compiler.cpp')
-rwxr-xr-xgfx/angle/src/libANGLE/Compiler.cpp194
1 files changed, 194 insertions, 0 deletions
diff --git a/gfx/angle/src/libANGLE/Compiler.cpp b/gfx/angle/src/libANGLE/Compiler.cpp
new file mode 100755
index 000000000..078491284
--- /dev/null
+++ b/gfx/angle/src/libANGLE/Compiler.cpp
@@ -0,0 +1,194 @@
+//
+// Copyright (c) 2014 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// Compiler.cpp: implements the gl::Compiler class.
+
+#include "libANGLE/Compiler.h"
+
+#include "common/debug.h"
+#include "libANGLE/ContextState.h"
+#include "libANGLE/renderer/CompilerImpl.h"
+#include "libANGLE/renderer/GLImplFactory.h"
+
+namespace gl
+{
+
+namespace
+{
+
+// Global count of active shader compiler handles. Needed to know when to call sh::Initialize and
+// sh::Finalize.
+size_t activeCompilerHandles = 0;
+
+ShShaderSpec SelectShaderSpec(GLint majorVersion, GLint minorVersion, bool isWebGL)
+{
+ if (majorVersion >= 3)
+ {
+ if (minorVersion == 1)
+ {
+ return isWebGL ? SH_WEBGL3_SPEC : SH_GLES3_1_SPEC;
+ }
+ else
+ {
+ return isWebGL ? SH_WEBGL2_SPEC : SH_GLES3_SPEC;
+ }
+ }
+ return isWebGL ? SH_WEBGL_SPEC : SH_GLES2_SPEC;
+}
+
+} // anonymous namespace
+
+Compiler::Compiler(rx::GLImplFactory *implFactory, const ContextState &state)
+ : mImplementation(implFactory->createCompiler()),
+ mSpec(SelectShaderSpec(state.getClientMajorVersion(),
+ state.getClientMinorVersion(),
+ state.getExtensions().webglCompatibility)),
+ mOutputType(mImplementation->getTranslatorOutputType()),
+ mResources(),
+ mFragmentCompiler(nullptr),
+ mVertexCompiler(nullptr),
+ mComputeCompiler(nullptr)
+{
+ ASSERT(state.getClientMajorVersion() == 2 || state.getClientMajorVersion() == 3);
+
+ const gl::Caps &caps = state.getCaps();
+ const gl::Extensions &extensions = state.getExtensions();
+
+ sh::InitBuiltInResources(&mResources);
+ mResources.MaxVertexAttribs = caps.maxVertexAttributes;
+ mResources.MaxVertexUniformVectors = caps.maxVertexUniformVectors;
+ mResources.MaxVaryingVectors = caps.maxVaryingVectors;
+ mResources.MaxVertexTextureImageUnits = caps.maxVertexTextureImageUnits;
+ mResources.MaxCombinedTextureImageUnits = caps.maxCombinedTextureImageUnits;
+ mResources.MaxTextureImageUnits = caps.maxTextureImageUnits;
+ mResources.MaxFragmentUniformVectors = caps.maxFragmentUniformVectors;
+ mResources.MaxDrawBuffers = caps.maxDrawBuffers;
+ mResources.OES_standard_derivatives = extensions.standardDerivatives;
+ mResources.EXT_draw_buffers = extensions.drawBuffers;
+ mResources.EXT_shader_texture_lod = extensions.shaderTextureLOD;
+ mResources.OES_EGL_image_external = extensions.eglImageExternal;
+ mResources.OES_EGL_image_external_essl3 = extensions.eglImageExternalEssl3;
+ mResources.NV_EGL_stream_consumer_external = extensions.eglStreamConsumerExternal;
+ // TODO: use shader precision caps to determine if high precision is supported?
+ mResources.FragmentPrecisionHigh = 1;
+ mResources.EXT_frag_depth = extensions.fragDepth;
+
+ // GLSL ES 3.0 constants
+ mResources.MaxVertexOutputVectors = caps.maxVertexOutputComponents / 4;
+ mResources.MaxFragmentInputVectors = caps.maxFragmentInputComponents / 4;
+ mResources.MinProgramTexelOffset = caps.minProgramTexelOffset;
+ mResources.MaxProgramTexelOffset = caps.maxProgramTexelOffset;
+
+ // GLSL ES 3.1 compute shader constants
+ mResources.MaxImageUnits = caps.maxImageUnits;
+ mResources.MaxVertexImageUniforms = caps.maxVertexImageUniforms;
+ mResources.MaxFragmentImageUniforms = caps.maxFragmentImageUniforms;
+ mResources.MaxComputeImageUniforms = caps.maxComputeImageUniforms;
+ mResources.MaxCombinedImageUniforms = caps.maxCombinedImageUniforms;
+ mResources.MaxCombinedShaderOutputResources = caps.maxCombinedShaderOutputResources;
+
+ for (size_t index = 0u; index < 3u; ++index)
+ {
+ mResources.MaxComputeWorkGroupCount[index] = caps.maxComputeWorkGroupCount[index];
+ mResources.MaxComputeWorkGroupSize[index] = caps.maxComputeWorkGroupSize[index];
+ }
+
+ mResources.MaxComputeUniformComponents = caps.maxComputeUniformComponents;
+ mResources.MaxComputeTextureImageUnits = caps.maxComputeTextureImageUnits;
+
+ mResources.MaxComputeAtomicCounters = caps.maxComputeAtomicCounters;
+ mResources.MaxComputeAtomicCounterBuffers = caps.maxComputeAtomicCounterBuffers;
+
+ mResources.MaxVertexAtomicCounters = caps.maxVertexAtomicCounters;
+ mResources.MaxFragmentAtomicCounters = caps.maxFragmentAtomicCounters;
+ mResources.MaxCombinedAtomicCounters = caps.maxCombinedAtomicCounters;
+ mResources.MaxAtomicCounterBindings = caps.maxAtomicCounterBufferBindings;
+ mResources.MaxVertexAtomicCounterBuffers = caps.maxVertexAtomicCounterBuffers;
+ mResources.MaxFragmentAtomicCounterBuffers = caps.maxFragmentAtomicCounterBuffers;
+ mResources.MaxCombinedAtomicCounterBuffers = caps.maxCombinedAtomicCounterBuffers;
+ mResources.MaxAtomicCounterBufferSize = caps.maxAtomicCounterBufferSize;
+}
+
+Compiler::~Compiler()
+{
+ release();
+ SafeDelete(mImplementation);
+}
+
+Error Compiler::release()
+{
+ if (mFragmentCompiler)
+ {
+ sh::Destruct(mFragmentCompiler);
+ mFragmentCompiler = nullptr;
+
+ ASSERT(activeCompilerHandles > 0);
+ activeCompilerHandles--;
+ }
+
+ if (mVertexCompiler)
+ {
+ sh::Destruct(mVertexCompiler);
+ mVertexCompiler = nullptr;
+
+ ASSERT(activeCompilerHandles > 0);
+ activeCompilerHandles--;
+ }
+
+ if (mComputeCompiler)
+ {
+ sh::Destruct(mComputeCompiler);
+ mComputeCompiler = nullptr;
+
+ ASSERT(activeCompilerHandles > 0);
+ activeCompilerHandles--;
+ }
+
+ if (activeCompilerHandles == 0)
+ {
+ sh::Finalize();
+ }
+
+ mImplementation->release();
+
+ return gl::Error(GL_NO_ERROR);
+}
+
+ShHandle Compiler::getCompilerHandle(GLenum type)
+{
+ ShHandle *compiler = nullptr;
+ switch (type)
+ {
+ case GL_VERTEX_SHADER:
+ compiler = &mVertexCompiler;
+ break;
+
+ case GL_FRAGMENT_SHADER:
+ compiler = &mFragmentCompiler;
+ break;
+ case GL_COMPUTE_SHADER:
+ compiler = &mComputeCompiler;
+ break;
+ default:
+ UNREACHABLE();
+ return nullptr;
+ }
+
+ if (!(*compiler))
+ {
+ if (activeCompilerHandles == 0)
+ {
+ sh::Initialize();
+ }
+
+ *compiler = sh::ConstructCompiler(type, mSpec, mOutputType, &mResources);
+ activeCompilerHandles++;
+ }
+
+ return *compiler;
+}
+
+} // namespace gl