Commit 18bd4100 by Brandon Jones

Removed the last references to Renderer from ProgramBinary.

BUG=angle:731 Change-Id: I8829a434e59279b1b9c37e9a1922ae05d467b376 Reviewed-on: https://chromium-review.googlesource.com/219421Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Reviewed-by: 's avatarShannon Woods <shannonwoods@chromium.org> Tested-by: 's avatarBrandon Jones <bajones@chromium.org>
parent 10ac4043
...@@ -23,9 +23,7 @@ ...@@ -23,9 +23,7 @@
#include "libGLESv2/Shader.h" #include "libGLESv2/Shader.h"
#include "libGLESv2/Program.h" #include "libGLESv2/Program.h"
#include "libGLESv2/renderer/ProgramImpl.h" #include "libGLESv2/renderer/ProgramImpl.h"
#include "libGLESv2/renderer/Renderer.h"
#include "libGLESv2/renderer/d3d/ShaderD3D.h" #include "libGLESv2/renderer/d3d/ShaderD3D.h"
#include "libGLESv2/renderer/d3d/VertexDataManager.h"
#include "libGLESv2/Context.h" #include "libGLESv2/Context.h"
#include "libGLESv2/Buffer.h" #include "libGLESv2/Buffer.h"
#include "common/blocklayout.h" #include "common/blocklayout.h"
...@@ -956,7 +954,7 @@ Error ProgramBinary::applyUniforms() ...@@ -956,7 +954,7 @@ Error ProgramBinary::applyUniforms()
{ {
updateSamplerMapping(); updateSamplerMapping();
Error error = mProgram->getRenderer()->applyUniforms(*this); Error error = mProgram->applyUniforms(mUniforms);
if (error.isError()) if (error.isError())
{ {
return error; return error;
...@@ -972,51 +970,8 @@ Error ProgramBinary::applyUniforms() ...@@ -972,51 +970,8 @@ Error ProgramBinary::applyUniforms()
Error ProgramBinary::applyUniformBuffers(const std::vector<gl::Buffer*> boundBuffers, const Caps &caps) Error ProgramBinary::applyUniformBuffers(const std::vector<gl::Buffer*> boundBuffers, const Caps &caps)
{ {
const gl::Buffer *vertexUniformBuffers[gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS] = {NULL};
const gl::Buffer *fragmentUniformBuffers[gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS] = {NULL};
const unsigned int reservedBuffersInVS = mProgram->getRenderer()->getReservedVertexUniformBuffers();
const unsigned int reservedBuffersInFS = mProgram->getRenderer()->getReservedFragmentUniformBuffers();
ASSERT(boundBuffers.size() == mUniformBlocks.size()); ASSERT(boundBuffers.size() == mUniformBlocks.size());
return mProgram->applyUniformBuffers(mUniformBlocks, boundBuffers, caps);
for (unsigned int uniformBlockIndex = 0; uniformBlockIndex < mUniformBlocks.size(); uniformBlockIndex++)
{
UniformBlock *uniformBlock = getUniformBlockByIndex(uniformBlockIndex);
gl::Buffer *uniformBuffer = boundBuffers[uniformBlockIndex];
ASSERT(uniformBlock && uniformBuffer);
if (uniformBuffer->getSize() < uniformBlock->dataSize)
{
// undefined behaviour
return gl::Error(GL_INVALID_OPERATION, "It is undefined behaviour to use a uniform buffer that is too small.");
}
// Unnecessary to apply an unreferenced standard or shared UBO
if (!uniformBlock->isReferencedByVertexShader() && !uniformBlock->isReferencedByFragmentShader())
{
continue;
}
if (uniformBlock->isReferencedByVertexShader())
{
unsigned int registerIndex = uniformBlock->vsRegisterIndex - reservedBuffersInVS;
ASSERT(vertexUniformBuffers[registerIndex] == NULL);
ASSERT(registerIndex < caps.maxVertexUniformBlocks);
vertexUniformBuffers[registerIndex] = uniformBuffer;
}
if (uniformBlock->isReferencedByFragmentShader())
{
unsigned int registerIndex = uniformBlock->psRegisterIndex - reservedBuffersInFS;
ASSERT(fragmentUniformBuffers[registerIndex] == NULL);
ASSERT(registerIndex < caps.maxFragmentUniformBlocks);
fragmentUniformBuffers[registerIndex] = uniformBuffer;
}
}
return mProgram->getRenderer()->setUniformBuffers(vertexUniformBuffers, fragmentUniformBuffers);
} }
bool ProgramBinary::linkVaryings(InfoLog &infoLog, Shader *fragmentShader, Shader *vertexShader) bool ProgramBinary::linkVaryings(InfoLog &infoLog, Shader *fragmentShader, Shader *vertexShader)
...@@ -1246,10 +1201,10 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina ...@@ -1246,10 +1201,10 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina
unsigned int vertexShaderSize = stream.readInt<unsigned int>(); unsigned int vertexShaderSize = stream.readInt<unsigned int>();
const unsigned char *vertexShaderFunction = reinterpret_cast<const unsigned char*>(binary) + stream.offset(); const unsigned char *vertexShaderFunction = reinterpret_cast<const unsigned char*>(binary) + stream.offset();
rx::ShaderExecutable *shaderExecutable = mProgram->getRenderer()->loadExecutable(reinterpret_cast<const DWORD*>(vertexShaderFunction), rx::ShaderExecutable *shaderExecutable = mProgram->loadExecutable(reinterpret_cast<const DWORD*>(vertexShaderFunction),
vertexShaderSize, rx::SHADER_VERTEX, vertexShaderSize, rx::SHADER_VERTEX,
mTransformFeedbackLinkedVaryings, mTransformFeedbackLinkedVaryings,
(mTransformFeedbackBufferMode == GL_SEPARATE_ATTRIBS)); (mTransformFeedbackBufferMode == GL_SEPARATE_ATTRIBS));
if (!shaderExecutable) if (!shaderExecutable)
{ {
infoLog.append("Could not create vertex shader."); infoLog.append("Could not create vertex shader.");
...@@ -1278,8 +1233,7 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina ...@@ -1278,8 +1233,7 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina
const size_t pixelShaderSize = stream.readInt<unsigned int>(); const size_t pixelShaderSize = stream.readInt<unsigned int>();
const unsigned char *pixelShaderFunction = reinterpret_cast<const unsigned char*>(binary) + stream.offset(); const unsigned char *pixelShaderFunction = reinterpret_cast<const unsigned char*>(binary) + stream.offset();
rx::Renderer *renderer = mProgram->getRenderer(); rx::ShaderExecutable *shaderExecutable = mProgram->loadExecutable(pixelShaderFunction, pixelShaderSize,
rx::ShaderExecutable *shaderExecutable = renderer->loadExecutable(pixelShaderFunction, pixelShaderSize,
rx::SHADER_PIXEL, mTransformFeedbackLinkedVaryings, rx::SHADER_PIXEL, mTransformFeedbackLinkedVaryings,
(mTransformFeedbackBufferMode == GL_SEPARATE_ATTRIBS)); (mTransformFeedbackBufferMode == GL_SEPARATE_ATTRIBS));
...@@ -1300,8 +1254,7 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina ...@@ -1300,8 +1254,7 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina
if (geometryShaderSize > 0) if (geometryShaderSize > 0)
{ {
const char *geometryShaderFunction = (const char*) binary + stream.offset(); const char *geometryShaderFunction = (const char*) binary + stream.offset();
rx::Renderer *renderer = mProgram->getRenderer(); mGeometryExecutable = mProgram->loadExecutable(reinterpret_cast<const DWORD*>(geometryShaderFunction),
mGeometryExecutable = renderer->loadExecutable(reinterpret_cast<const DWORD*>(geometryShaderFunction),
geometryShaderSize, rx::SHADER_GEOMETRY, mTransformFeedbackLinkedVaryings, geometryShaderSize, rx::SHADER_GEOMETRY, mTransformFeedbackLinkedVaryings,
(mTransformFeedbackBufferMode == GL_SEPARATE_ATTRIBS)); (mTransformFeedbackBufferMode == GL_SEPARATE_ATTRIBS));
...@@ -1318,18 +1271,6 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina ...@@ -1318,18 +1271,6 @@ bool ProgramBinary::load(InfoLog &infoLog, GLenum binaryFormat, const void *bina
return false; return false;
} }
const char *ptr = (const char*) binary + stream.offset();
const GUID *binaryIdentifier = (const GUID *) ptr;
ptr += sizeof(GUID);
GUID identifier = mProgram->getRenderer()->getAdapterIdentifier();
if (memcmp(&identifier, binaryIdentifier, sizeof(GUID)) != 0)
{
infoLog.append("Invalid program binary.");
return false;
}
mProgram->initializeUniformStorage(mUniforms); mProgram->initializeUniformStorage(mUniforms);
return true; return true;
...@@ -1501,13 +1442,10 @@ bool ProgramBinary::save(GLenum *binaryFormat, void *binary, GLsizei bufSize, GL ...@@ -1501,13 +1442,10 @@ bool ProgramBinary::save(GLenum *binaryFormat, void *binary, GLsizei bufSize, GL
return false; return false;
} }
GUID identifier = mProgram->getRenderer()->getAdapterIdentifier();
GLsizei streamLength = stream.length(); GLsizei streamLength = stream.length();
const void *streamData = stream.data(); const void *streamData = stream.data();
GLsizei totalLength = streamLength + sizeof(GUID); if (streamLength > bufSize)
if (totalLength > bufSize)
{ {
if (length) if (length)
{ {
...@@ -1524,15 +1462,12 @@ bool ProgramBinary::save(GLenum *binaryFormat, void *binary, GLsizei bufSize, GL ...@@ -1524,15 +1462,12 @@ bool ProgramBinary::save(GLenum *binaryFormat, void *binary, GLsizei bufSize, GL
memcpy(ptr, streamData, streamLength); memcpy(ptr, streamData, streamLength);
ptr += streamLength; ptr += streamLength;
memcpy(ptr, &identifier, sizeof(GUID)); ASSERT(ptr - streamLength == binary);
ptr += sizeof(GUID);
ASSERT(ptr - totalLength == binary);
} }
if (length) if (length)
{ {
*length = totalLength; *length = streamLength;
} }
return true; return true;
...@@ -1980,7 +1915,7 @@ bool ProgramBinary::indexSamplerUniform(const LinkedUniform &uniform, InfoLog &i ...@@ -1980,7 +1915,7 @@ bool ProgramBinary::indexSamplerUniform(const LinkedUniform &uniform, InfoLog &i
return false; return false;
} }
unsigned int maxVertexVectors = mProgram->getRenderer()->getReservedVertexUniformVectors() + caps.maxVertexUniformVectors; unsigned int maxVertexVectors = mProgram->getReservedUniformVectors(GL_VERTEX_SHADER) + caps.maxVertexUniformVectors;
if (uniform.vsRegisterIndex + uniform.registerCount > maxVertexVectors) if (uniform.vsRegisterIndex + uniform.registerCount > maxVertexVectors)
{ {
infoLog.append("Vertex shader active uniforms exceed GL_MAX_VERTEX_UNIFORM_VECTORS (%u)", infoLog.append("Vertex shader active uniforms exceed GL_MAX_VERTEX_UNIFORM_VECTORS (%u)",
...@@ -1999,7 +1934,7 @@ bool ProgramBinary::indexSamplerUniform(const LinkedUniform &uniform, InfoLog &i ...@@ -1999,7 +1934,7 @@ bool ProgramBinary::indexSamplerUniform(const LinkedUniform &uniform, InfoLog &i
return false; return false;
} }
unsigned int maxFragmentVectors = mProgram->getRenderer()->getReservedFragmentUniformVectors() + caps.maxFragmentUniformVectors; unsigned int maxFragmentVectors = mProgram->getReservedUniformVectors(GL_FRAGMENT_SHADER) + caps.maxFragmentUniformVectors;
if (uniform.psRegisterIndex + uniform.registerCount > maxFragmentVectors) if (uniform.psRegisterIndex + uniform.registerCount > maxFragmentVectors)
{ {
infoLog.append("Fragment shader active uniforms exceed GL_MAX_FRAGMENT_UNIFORM_VECTORS (%u)", infoLog.append("Fragment shader active uniforms exceed GL_MAX_FRAGMENT_UNIFORM_VECTORS (%u)",
...@@ -2326,8 +2261,8 @@ bool ProgramBinary::defineUniformBlock(InfoLog &infoLog, const Shader &shader, c ...@@ -2326,8 +2261,8 @@ bool ProgramBinary::defineUniformBlock(InfoLog &infoLog, const Shader &shader, c
UniformBlock *uniformBlock = mUniformBlocks[blockIndex + uniformBlockElement]; UniformBlock *uniformBlock = mUniformBlocks[blockIndex + uniformBlockElement];
ASSERT(uniformBlock->name == interfaceBlock.name); ASSERT(uniformBlock->name == interfaceBlock.name);
if (!assignUniformBlockRegister(infoLog, uniformBlock, shader.getType(), if (!mProgram->assignUniformBlockRegister(infoLog, uniformBlock, shader.getType(),
interfaceBlockRegister + uniformBlockElement, caps)) interfaceBlockRegister + uniformBlockElement, caps))
{ {
return false; return false;
} }
...@@ -2337,31 +2272,6 @@ bool ProgramBinary::defineUniformBlock(InfoLog &infoLog, const Shader &shader, c ...@@ -2337,31 +2272,6 @@ bool ProgramBinary::defineUniformBlock(InfoLog &infoLog, const Shader &shader, c
return true; return true;
} }
bool ProgramBinary::assignUniformBlockRegister(InfoLog &infoLog, UniformBlock *uniformBlock, GLenum shader, unsigned int registerIndex, const Caps &caps)
{
if (shader == GL_VERTEX_SHADER)
{
uniformBlock->vsRegisterIndex = registerIndex;
if (registerIndex - mProgram->getRenderer()->getReservedVertexUniformBuffers() >= caps.maxVertexUniformBlocks)
{
infoLog.append("Vertex shader uniform block count exceed GL_MAX_VERTEX_UNIFORM_BLOCKS (%u)", caps.maxVertexUniformBlocks);
return false;
}
}
else if (shader == GL_FRAGMENT_SHADER)
{
uniformBlock->psRegisterIndex = registerIndex;
if (registerIndex - mProgram->getRenderer()->getReservedFragmentUniformBuffers() >= caps.maxFragmentUniformBlocks)
{
infoLog.append("Fragment shader uniform block count exceed GL_MAX_FRAGMENT_UNIFORM_BLOCKS (%u)", caps.maxFragmentUniformBlocks);
return false;
}
}
else UNREACHABLE();
return true;
}
bool ProgramBinary::isValidated() const bool ProgramBinary::isValidated() const
{ {
return mValidated; return mValidated;
......
...@@ -13,6 +13,7 @@ ...@@ -13,6 +13,7 @@
#include "libGLESv2/BinaryStream.h" #include "libGLESv2/BinaryStream.h"
#include "libGLESv2/Constants.h" #include "libGLESv2/Constants.h"
#include "libGLESv2/ProgramBinary.h" #include "libGLESv2/ProgramBinary.h"
#include "libGLESv2/renderer/Renderer.h"
namespace rx namespace rx
{ {
...@@ -24,8 +25,6 @@ class ProgramImpl ...@@ -24,8 +25,6 @@ class ProgramImpl
public: public:
virtual ~ProgramImpl() { } virtual ~ProgramImpl() { }
// TODO: Temporary interfaces to ease migration. Remove soon!
virtual Renderer *getRenderer() = 0;
virtual const std::vector<rx::PixelShaderOutputVariable> &getPixelShaderKey() = 0; virtual const std::vector<rx::PixelShaderOutputVariable> &getPixelShaderKey() = 0;
virtual bool usesPointSize() const = 0; virtual bool usesPointSize() const = 0;
...@@ -47,6 +46,9 @@ public: ...@@ -47,6 +46,9 @@ public:
virtual rx::ShaderExecutable *getGeometryExecutable(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader, virtual rx::ShaderExecutable *getGeometryExecutable(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader,
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings, const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers, int registers) = 0; bool separatedOutputBuffers, int registers) = 0;
virtual rx::ShaderExecutable *loadExecutable(const void *function, size_t length, rx::ShaderType type,
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers) = 0;
virtual bool link(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader, virtual bool link(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader,
const std::vector<std::string> &transformFeedbackVaryings, int *registers, const std::vector<std::string> &transformFeedbackVaryings, int *registers,
...@@ -57,6 +59,13 @@ public: ...@@ -57,6 +59,13 @@ public:
virtual void initializeUniformStorage(const std::vector<gl::LinkedUniform*> &uniforms) = 0; virtual void initializeUniformStorage(const std::vector<gl::LinkedUniform*> &uniforms) = 0;
virtual gl::Error applyUniforms(const std::vector<gl::LinkedUniform*> &uniforms) = 0;
virtual gl::Error applyUniformBuffers(const std::vector<gl::UniformBlock*> uniformBlocks, const std::vector<gl::Buffer*> boundBuffers,
const gl::Caps &caps) = 0;
virtual bool assignUniformBlockRegister(gl::InfoLog &infoLog, gl::UniformBlock *uniformBlock, GLenum shader,
unsigned int registerIndex, const gl::Caps &caps) = 0;
virtual unsigned int getReservedUniformVectors(GLenum shader) = 0;
virtual void reset() = 0; virtual void reset() = 0;
}; };
......
...@@ -128,7 +128,7 @@ class Renderer ...@@ -128,7 +128,7 @@ class Renderer
virtual gl::Error applyRenderTarget(gl::Framebuffer *frameBuffer) = 0; virtual gl::Error applyRenderTarget(gl::Framebuffer *frameBuffer) = 0;
virtual gl::Error applyShaders(gl::ProgramBinary *programBinary, const gl::VertexFormat inputLayout[], const gl::Framebuffer *framebuffer, virtual gl::Error applyShaders(gl::ProgramBinary *programBinary, const gl::VertexFormat inputLayout[], const gl::Framebuffer *framebuffer,
bool rasterizerDiscard, bool transformFeedbackActive) = 0; bool rasterizerDiscard, bool transformFeedbackActive) = 0;
virtual gl::Error applyUniforms(const gl::ProgramBinary &programBinary) = 0; virtual gl::Error applyUniforms(const ProgramImpl &program, const std::vector<gl::LinkedUniform*> &uniformArray) = 0;
virtual bool applyPrimitiveType(GLenum primitiveType, GLsizei elementCount) = 0; virtual bool applyPrimitiveType(GLenum primitiveType, GLsizei elementCount) = 0;
virtual gl::Error applyVertexBuffer(gl::ProgramBinary *programBinary, const gl::VertexAttribute vertexAttributes[], const gl::VertexAttribCurrentValueData currentValues[], virtual gl::Error applyVertexBuffer(gl::ProgramBinary *programBinary, const gl::VertexAttribute vertexAttributes[], const gl::VertexAttribCurrentValueData currentValues[],
GLint first, GLsizei count, GLsizei instances) = 0; GLint first, GLsizei count, GLsizei instances) = 0;
......
...@@ -9,6 +9,7 @@ ...@@ -9,6 +9,7 @@
#include "libGLESv2/renderer/d3d/ProgramD3D.h" #include "libGLESv2/renderer/d3d/ProgramD3D.h"
#include "common/utilities.h" #include "common/utilities.h"
#include "libGLESv2/Program.h"
#include "libGLESv2/ProgramBinary.h" #include "libGLESv2/ProgramBinary.h"
#include "libGLESv2/renderer/Renderer.h" #include "libGLESv2/renderer/Renderer.h"
#include "libGLESv2/renderer/ShaderExecutable.h" #include "libGLESv2/renderer/ShaderExecutable.h"
...@@ -87,6 +88,16 @@ bool ProgramD3D::load(gl::InfoLog &infoLog, gl::BinaryInputStream *stream) ...@@ -87,6 +88,16 @@ bool ProgramD3D::load(gl::InfoLog &infoLog, gl::BinaryInputStream *stream)
stream->readInt(&mPixelShaderKey[pixelShaderKeyIndex].outputIndex); stream->readInt(&mPixelShaderKey[pixelShaderKeyIndex].outputIndex);
} }
GUID binaryIdentifier = {0};
stream->readBytes(reinterpret_cast<unsigned char*>(&binaryIdentifier), sizeof(GUID));
GUID identifier = mRenderer->getAdapterIdentifier();
if (memcmp(&identifier, &binaryIdentifier, sizeof(GUID)) != 0)
{
infoLog.append("Invalid program binary.");
return false;
}
return true; return true;
} }
...@@ -112,58 +123,68 @@ bool ProgramD3D::save(gl::BinaryOutputStream *stream) ...@@ -112,58 +123,68 @@ bool ProgramD3D::save(gl::BinaryOutputStream *stream)
stream->writeInt(variable.outputIndex); stream->writeInt(variable.outputIndex);
} }
GUID binaryIdentifier = mRenderer->getAdapterIdentifier();
stream->writeBytes(reinterpret_cast<unsigned char*>(&binaryIdentifier), sizeof(GUID));
return true; return true;
} }
rx::ShaderExecutable *ProgramD3D::getPixelExecutableForOutputLayout(gl::InfoLog &infoLog, const std::vector<GLenum> &outputSignature, ShaderExecutable *ProgramD3D::getPixelExecutableForOutputLayout(gl::InfoLog &infoLog, const std::vector<GLenum> &outputSignature,
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings, const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers) bool separatedOutputBuffers)
{ {
std::string finalPixelHLSL = mDynamicHLSL->generatePixelShaderForOutputSignature(mPixelHLSL, mPixelShaderKey, mUsesFragDepth, std::string finalPixelHLSL = mDynamicHLSL->generatePixelShaderForOutputSignature(mPixelHLSL, mPixelShaderKey, mUsesFragDepth,
outputSignature); outputSignature);
// Generate new pixel executable // Generate new pixel executable
rx::ShaderExecutable *pixelExecutable = mRenderer->compileToExecutable(infoLog, finalPixelHLSL.c_str(), rx::SHADER_PIXEL, ShaderExecutable *pixelExecutable = mRenderer->compileToExecutable(infoLog, finalPixelHLSL.c_str(), rx::SHADER_PIXEL,
transformFeedbackLinkedVaryings, separatedOutputBuffers, transformFeedbackLinkedVaryings, separatedOutputBuffers,
mPixelWorkarounds); mPixelWorkarounds);
return pixelExecutable; return pixelExecutable;
} }
rx::ShaderExecutable *ProgramD3D::getVertexExecutableForInputLayout(gl::InfoLog &infoLog, ShaderExecutable *ProgramD3D::getVertexExecutableForInputLayout(gl::InfoLog &infoLog,
const gl::VertexFormat inputLayout[gl::MAX_VERTEX_ATTRIBS], const gl::VertexFormat inputLayout[gl::MAX_VERTEX_ATTRIBS],
const sh::Attribute shaderAttributes[], const sh::Attribute shaderAttributes[],
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings, const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers) bool separatedOutputBuffers)
{ {
// Generate new dynamic layout with attribute conversions // Generate new dynamic layout with attribute conversions
std::string finalVertexHLSL = mDynamicHLSL->generateVertexShaderForInputLayout(mVertexHLSL, inputLayout, shaderAttributes); std::string finalVertexHLSL = mDynamicHLSL->generateVertexShaderForInputLayout(mVertexHLSL, inputLayout, shaderAttributes);
// Generate new vertex executable // Generate new vertex executable
rx::ShaderExecutable *vertexExecutable = mRenderer->compileToExecutable(infoLog, finalVertexHLSL.c_str(), ShaderExecutable *vertexExecutable = mRenderer->compileToExecutable(infoLog, finalVertexHLSL.c_str(),
rx::SHADER_VERTEX, rx::SHADER_VERTEX,
transformFeedbackLinkedVaryings, separatedOutputBuffers, transformFeedbackLinkedVaryings, separatedOutputBuffers,
mVertexWorkarounds); mVertexWorkarounds);
return vertexExecutable; return vertexExecutable;
} }
rx::ShaderExecutable *ProgramD3D::getGeometryExecutable(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader, ShaderExecutable *ProgramD3D::getGeometryExecutable(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader,
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings, const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers, int registers) bool separatedOutputBuffers, int registers)
{ {
rx::ShaderD3D *vertexShaderD3D = rx::ShaderD3D::makeShaderD3D(vertexShader->getImplementation()); ShaderD3D *vertexShaderD3D = ShaderD3D::makeShaderD3D(vertexShader->getImplementation());
rx::ShaderD3D *fragmentShaderD3D = rx::ShaderD3D::makeShaderD3D(fragmentShader->getImplementation()); ShaderD3D *fragmentShaderD3D = ShaderD3D::makeShaderD3D(fragmentShader->getImplementation());
std::string geometryHLSL = mDynamicHLSL->generateGeometryShaderHLSL(registers, fragmentShaderD3D, vertexShaderD3D); std::string geometryHLSL = mDynamicHLSL->generateGeometryShaderHLSL(registers, fragmentShaderD3D, vertexShaderD3D);
rx::ShaderExecutable *geometryExecutable = mRenderer->compileToExecutable(infoLog, geometryHLSL.c_str(), ShaderExecutable *geometryExecutable = mRenderer->compileToExecutable(infoLog, geometryHLSL.c_str(),
rx::SHADER_GEOMETRY, transformFeedbackLinkedVaryings, rx::SHADER_GEOMETRY, transformFeedbackLinkedVaryings,
separatedOutputBuffers, rx::ANGLE_D3D_WORKAROUND_NONE); separatedOutputBuffers, rx::ANGLE_D3D_WORKAROUND_NONE);
return geometryExecutable; return geometryExecutable;
} }
ShaderExecutable *ProgramD3D::loadExecutable(const void *function, size_t length, rx::ShaderType type,
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers)
{
return mRenderer->loadExecutable(function, length, type, transformFeedbackLinkedVaryings, separatedOutputBuffers);
}
bool ProgramD3D::link(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader, bool ProgramD3D::link(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader,
const std::vector<std::string> &transformFeedbackVaryings, int *registers, const std::vector<std::string> &transformFeedbackVaryings, int *registers,
std::vector<gl::LinkedVarying> *linkedVaryings, std::map<int, gl::VariableLocation> *outputVariables) std::vector<gl::LinkedVarying> *linkedVaryings, std::map<int, gl::VariableLocation> *outputVariables)
...@@ -235,6 +256,100 @@ void ProgramD3D::initializeUniformStorage(const std::vector<gl::LinkedUniform*> ...@@ -235,6 +256,100 @@ void ProgramD3D::initializeUniformStorage(const std::vector<gl::LinkedUniform*>
mFragmentUniformStorage = mRenderer->createUniformStorage(fragmentRegisters * 16u); mFragmentUniformStorage = mRenderer->createUniformStorage(fragmentRegisters * 16u);
} }
gl::Error ProgramD3D::applyUniforms(const std::vector<gl::LinkedUniform*> &uniforms)
{
return mRenderer->applyUniforms(*this, uniforms);
}
gl::Error ProgramD3D::applyUniformBuffers(const std::vector<gl::UniformBlock*> uniformBlocks, const std::vector<gl::Buffer*> boundBuffers,
const gl::Caps &caps)
{
const gl::Buffer *vertexUniformBuffers[gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS] = {NULL};
const gl::Buffer *fragmentUniformBuffers[gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS] = {NULL};
const unsigned int reservedBuffersInVS = mRenderer->getReservedVertexUniformBuffers();
const unsigned int reservedBuffersInFS = mRenderer->getReservedFragmentUniformBuffers();
for (unsigned int uniformBlockIndex = 0; uniformBlockIndex < uniformBlocks.size(); uniformBlockIndex++)
{
gl::UniformBlock *uniformBlock = uniformBlocks[uniformBlockIndex];
gl::Buffer *uniformBuffer = boundBuffers[uniformBlockIndex];
ASSERT(uniformBlock && uniformBuffer);
if (uniformBuffer->getSize() < uniformBlock->dataSize)
{
// undefined behaviour
return gl::Error(GL_INVALID_OPERATION, "It is undefined behaviour to use a uniform buffer that is too small.");
}
// Unnecessary to apply an unreferenced standard or shared UBO
if (!uniformBlock->isReferencedByVertexShader() && !uniformBlock->isReferencedByFragmentShader())
{
continue;
}
if (uniformBlock->isReferencedByVertexShader())
{
unsigned int registerIndex = uniformBlock->vsRegisterIndex - reservedBuffersInVS;
ASSERT(vertexUniformBuffers[registerIndex] == NULL);
ASSERT(registerIndex < caps.maxVertexUniformBlocks);
vertexUniformBuffers[registerIndex] = uniformBuffer;
}
if (uniformBlock->isReferencedByFragmentShader())
{
unsigned int registerIndex = uniformBlock->psRegisterIndex - reservedBuffersInFS;
ASSERT(fragmentUniformBuffers[registerIndex] == NULL);
ASSERT(registerIndex < caps.maxFragmentUniformBlocks);
fragmentUniformBuffers[registerIndex] = uniformBuffer;
}
}
return mRenderer->setUniformBuffers(vertexUniformBuffers, fragmentUniformBuffers);
}
bool ProgramD3D::assignUniformBlockRegister(gl::InfoLog &infoLog, gl::UniformBlock *uniformBlock, GLenum shader,
unsigned int registerIndex, const gl::Caps &caps)
{
if (shader == GL_VERTEX_SHADER)
{
uniformBlock->vsRegisterIndex = registerIndex;
if (registerIndex - mRenderer->getReservedVertexUniformBuffers() >= caps.maxVertexUniformBlocks)
{
infoLog.append("Vertex shader uniform block count exceed GL_MAX_VERTEX_UNIFORM_BLOCKS (%u)", caps.maxVertexUniformBlocks);
return false;
}
}
else if (shader == GL_FRAGMENT_SHADER)
{
uniformBlock->psRegisterIndex = registerIndex;
if (registerIndex - mRenderer->getReservedFragmentUniformBuffers() >= caps.maxFragmentUniformBlocks)
{
infoLog.append("Fragment shader uniform block count exceed GL_MAX_FRAGMENT_UNIFORM_BLOCKS (%u)", caps.maxFragmentUniformBlocks);
return false;
}
}
else UNREACHABLE();
return true;
}
unsigned int ProgramD3D::getReservedUniformVectors(GLenum shader)
{
if (shader == GL_VERTEX_SHADER)
{
return mRenderer->getReservedVertexUniformVectors();
}
else if (shader == GL_FRAGMENT_SHADER)
{
return mRenderer->getReservedFragmentUniformVectors();
}
else UNREACHABLE();
return 0;
}
void ProgramD3D::reset() void ProgramD3D::reset()
{ {
mVertexHLSL.clear(); mVertexHLSL.clear();
......
...@@ -35,7 +35,6 @@ class ProgramD3D : public ProgramImpl ...@@ -35,7 +35,6 @@ class ProgramD3D : public ProgramImpl
static ProgramD3D *makeProgramD3D(ProgramImpl *impl); static ProgramD3D *makeProgramD3D(ProgramImpl *impl);
static const ProgramD3D *makeProgramD3D(const ProgramImpl *impl); static const ProgramD3D *makeProgramD3D(const ProgramImpl *impl);
Renderer *getRenderer() { return mRenderer; }
const std::vector<rx::PixelShaderOutputVariable> &getPixelShaderKey() { return mPixelShaderKey; } const std::vector<rx::PixelShaderOutputVariable> &getPixelShaderKey() { return mPixelShaderKey; }
int getShaderVersion() const { return mShaderVersion; } int getShaderVersion() const { return mShaderVersion; }
...@@ -58,6 +57,9 @@ class ProgramD3D : public ProgramImpl ...@@ -58,6 +57,9 @@ class ProgramD3D : public ProgramImpl
ShaderExecutable *getGeometryExecutable(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader, ShaderExecutable *getGeometryExecutable(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader,
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings, const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers, int registers); bool separatedOutputBuffers, int registers);
ShaderExecutable *loadExecutable(const void *function, size_t length, rx::ShaderType type,
const std::vector<gl::LinkedVarying> &transformFeedbackLinkedVaryings,
bool separatedOutputBuffers);
bool link(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader, bool link(gl::InfoLog &infoLog, gl::Shader *fragmentShader, gl::Shader *vertexShader,
const std::vector<std::string> &transformFeedbackVaryings, int *registers, const std::vector<std::string> &transformFeedbackVaryings, int *registers,
...@@ -65,8 +67,13 @@ class ProgramD3D : public ProgramImpl ...@@ -65,8 +67,13 @@ class ProgramD3D : public ProgramImpl
void getInputLayoutSignature(const gl::VertexFormat inputLayout[], GLenum signature[]) const; void getInputLayoutSignature(const gl::VertexFormat inputLayout[], GLenum signature[]) const;
// D3D only
void initializeUniformStorage(const std::vector<gl::LinkedUniform*> &uniforms); void initializeUniformStorage(const std::vector<gl::LinkedUniform*> &uniforms);
gl::Error applyUniforms(const std::vector<gl::LinkedUniform*> &uniforms);
gl::Error applyUniformBuffers(const std::vector<gl::UniformBlock*> uniformBlocks, const std::vector<gl::Buffer*> boundBuffers,
const gl::Caps &caps);
bool assignUniformBlockRegister(gl::InfoLog &infoLog, gl::UniformBlock *uniformBlock, GLenum shader,
unsigned int registerIndex, const gl::Caps &caps);
unsigned int getReservedUniformVectors(GLenum shader);
const UniformStorage &getVertexUniformStorage() const { return *mVertexUniformStorage; } const UniformStorage &getVertexUniformStorage() const { return *mVertexUniformStorage; }
const UniformStorage &getFragmentUniformStorage() const { return *mFragmentUniformStorage; } const UniformStorage &getFragmentUniformStorage() const { return *mFragmentUniformStorage; }
......
...@@ -1392,10 +1392,8 @@ gl::Error Renderer11::applyShaders(gl::ProgramBinary *programBinary, const gl::V ...@@ -1392,10 +1392,8 @@ gl::Error Renderer11::applyShaders(gl::ProgramBinary *programBinary, const gl::V
return gl::Error(GL_NO_ERROR); return gl::Error(GL_NO_ERROR);
} }
gl::Error Renderer11::applyUniforms(const gl::ProgramBinary &programBinary) gl::Error Renderer11::applyUniforms(const ProgramImpl &program, const std::vector<gl::LinkedUniform*> &uniformArray)
{ {
const std::vector<gl::LinkedUniform*> &uniformArray = programBinary.getUniforms();
unsigned int totalRegisterCountVS = 0; unsigned int totalRegisterCountVS = 0;
unsigned int totalRegisterCountPS = 0; unsigned int totalRegisterCountPS = 0;
...@@ -1419,7 +1417,7 @@ gl::Error Renderer11::applyUniforms(const gl::ProgramBinary &programBinary) ...@@ -1419,7 +1417,7 @@ gl::Error Renderer11::applyUniforms(const gl::ProgramBinary &programBinary)
} }
} }
const ProgramD3D *programD3D = ProgramD3D::makeProgramD3D(programBinary.getImplementation()); const ProgramD3D *programD3D = ProgramD3D::makeProgramD3D(&program);
const UniformStorage11 *vertexUniformStorage = UniformStorage11::makeUniformStorage11(&programD3D->getVertexUniformStorage()); const UniformStorage11 *vertexUniformStorage = UniformStorage11::makeUniformStorage11(&programD3D->getVertexUniformStorage());
const UniformStorage11 *fragmentUniformStorage = UniformStorage11::makeUniformStorage11(&programD3D->getFragmentUniformStorage()); const UniformStorage11 *fragmentUniformStorage = UniformStorage11::makeUniformStorage11(&programD3D->getFragmentUniformStorage());
ASSERT(vertexUniformStorage); ASSERT(vertexUniformStorage);
......
...@@ -79,7 +79,7 @@ class Renderer11 : public Renderer ...@@ -79,7 +79,7 @@ class Renderer11 : public Renderer
virtual gl::Error applyRenderTarget(gl::Framebuffer *frameBuffer); virtual gl::Error applyRenderTarget(gl::Framebuffer *frameBuffer);
virtual gl::Error applyShaders(gl::ProgramBinary *programBinary, const gl::VertexFormat inputLayout[], const gl::Framebuffer *framebuffer, virtual gl::Error applyShaders(gl::ProgramBinary *programBinary, const gl::VertexFormat inputLayout[], const gl::Framebuffer *framebuffer,
bool rasterizerDiscard, bool transformFeedbackActive); bool rasterizerDiscard, bool transformFeedbackActive);
virtual gl::Error applyUniforms(const gl::ProgramBinary &programBinary); virtual gl::Error applyUniforms(const ProgramImpl &program, const std::vector<gl::LinkedUniform*> &uniformArray);
virtual gl::Error applyVertexBuffer(gl::ProgramBinary *programBinary, const gl::VertexAttribute vertexAttributes[], const gl::VertexAttribCurrentValueData currentValues[], virtual gl::Error applyVertexBuffer(gl::ProgramBinary *programBinary, const gl::VertexAttribute vertexAttributes[], const gl::VertexAttribCurrentValueData currentValues[],
GLint first, GLsizei count, GLsizei instances); GLint first, GLsizei count, GLsizei instances);
virtual gl::Error applyIndexBuffer(const GLvoid *indices, gl::Buffer *elementArrayBuffer, GLsizei count, GLenum mode, GLenum type, TranslatedIndexData *indexInfo); virtual gl::Error applyIndexBuffer(const GLvoid *indices, gl::Buffer *elementArrayBuffer, GLsizei count, GLenum mode, GLenum type, TranslatedIndexData *indexInfo);
......
...@@ -1704,10 +1704,8 @@ gl::Error Renderer9::applyShaders(gl::ProgramBinary *programBinary, const gl::Ve ...@@ -1704,10 +1704,8 @@ gl::Error Renderer9::applyShaders(gl::ProgramBinary *programBinary, const gl::Ve
return gl::Error(GL_NO_ERROR); return gl::Error(GL_NO_ERROR);
} }
gl::Error Renderer9::applyUniforms(const gl::ProgramBinary &programBinary) gl::Error Renderer9::applyUniforms(const ProgramImpl &program, const std::vector<gl::LinkedUniform*> &uniformArray)
{ {
const std::vector<gl::LinkedUniform*> &uniformArray = programBinary.getUniforms();
for (size_t uniformIndex = 0; uniformIndex < uniformArray.size(); uniformIndex++) for (size_t uniformIndex = 0; uniformIndex < uniformArray.size(); uniformIndex++)
{ {
gl::LinkedUniform *targetUniform = uniformArray[uniformIndex]; gl::LinkedUniform *targetUniform = uniformArray[uniformIndex];
......
...@@ -79,7 +79,7 @@ class Renderer9 : public Renderer ...@@ -79,7 +79,7 @@ class Renderer9 : public Renderer
virtual gl::Error applyRenderTarget(gl::Framebuffer *frameBuffer); virtual gl::Error applyRenderTarget(gl::Framebuffer *frameBuffer);
virtual gl::Error applyShaders(gl::ProgramBinary *programBinary, const gl::VertexFormat inputLayout[], const gl::Framebuffer *framebuffer, virtual gl::Error applyShaders(gl::ProgramBinary *programBinary, const gl::VertexFormat inputLayout[], const gl::Framebuffer *framebuffer,
bool rasterizerDiscard, bool transformFeedbackActive); bool rasterizerDiscard, bool transformFeedbackActive);
virtual gl::Error applyUniforms(const gl::ProgramBinary &programBinary); virtual gl::Error applyUniforms(const ProgramImpl &program, const std::vector<gl::LinkedUniform*> &uniformArray);
virtual bool applyPrimitiveType(GLenum primitiveType, GLsizei elementCount); virtual bool applyPrimitiveType(GLenum primitiveType, GLsizei elementCount);
virtual gl::Error applyVertexBuffer(gl::ProgramBinary *programBinary, const gl::VertexAttribute vertexAttributes[], const gl::VertexAttribCurrentValueData currentValues[], virtual gl::Error applyVertexBuffer(gl::ProgramBinary *programBinary, const gl::VertexAttribute vertexAttributes[], const gl::VertexAttribCurrentValueData currentValues[],
GLint first, GLsizei count, GLsizei instances); GLint first, GLsizei count, GLsizei instances);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment