Commit b938c3ce by Alexis Hetu Committed by Alexis Hétu

Uniform blocks implementation

- Added support for uniform blocks in OutputASM::declareUniform - Added basic implementation of Program::applyUniformBuffers() to be completed later on when uniform buffers are implemented Change-Id: I919b59d4557bb10bb302e6b6bd0ada79553ca8bb Reviewed-on: https://swiftshader-review.googlesource.com/3651Tested-by: 's avatarAlexis Hétu <sugoi@google.com> Reviewed-by: 's avatarNicolas Capens <capn@google.com>
parent f2a8c37e
...@@ -75,13 +75,16 @@ namespace glsl ...@@ -75,13 +75,16 @@ namespace glsl
ConstantUnion constants[4]; ConstantUnion constants[4];
}; };
Uniform::Uniform(GLenum type, GLenum precision, const std::string &name, int arraySize, int registerIndex) Uniform::Uniform(GLenum type, GLenum precision, const std::string &name, int arraySize, int registerIndex, int blockId) :
type(type), precision(precision), name(name), arraySize(arraySize), registerIndex(registerIndex), blockId(blockId)
{
}
UniformBlock::UniformBlock(const std::string& name, const std::string& instanceName, unsigned int dataSize, unsigned int arraySize,
TLayoutBlockStorage layout, bool isRowMajorLayout, int registerIndex, int blockId) :
name(name), instanceName(instanceName), dataSize(dataSize), arraySize(arraySize), layout(layout),
isRowMajorLayout(isRowMajorLayout), registerIndex(registerIndex), blockId(blockId)
{ {
this->type = type;
this->precision = precision;
this->name = name;
this->arraySize = arraySize;
this->registerIndex = registerIndex;
} }
Attribute::Attribute() Attribute::Attribute()
...@@ -2399,55 +2402,73 @@ namespace glsl ...@@ -2399,55 +2402,73 @@ namespace glsl
} }
} }
void OutputASM::declareUniform(const TType &type, const TString &name, int index) void OutputASM::declareUniform(const TType &type, const TString &name, int offset, int blockId)
{ {
const TStructure *structure = type.getStruct(); const TStructure *structure = type.getStruct();
const TInterfaceBlock *block = (type.isInterfaceBlock() || (blockId == -1)) ? type.getInterfaceBlock() : nullptr;
ActiveUniforms &activeUniforms = shaderObject->activeUniforms; ActiveUniforms &activeUniforms = shaderObject->activeUniforms;
if(!structure) if(block)
{
ActiveUniformBlocks &activeUniformBlocks = shaderObject->activeUniformBlocks;
blockId = activeUniformBlocks.size();
unsigned int dataSize = block->objectSize() * 4; // FIXME: assuming 4 bytes per element
activeUniformBlocks.push_back(UniformBlock(block->name().c_str(), block->hasInstanceName() ? block->instanceName().c_str() : std::string(), dataSize,
block->arraySize(), block->blockStorage(), block->matrixPacking() == EmpRowMajor, offset, blockId));
}
if(!structure && !block)
{
if(blockId >= 0)
{ {
activeUniforms.push_back(Uniform(glVariableType(type), glVariablePrecision(type), name.c_str(), type.getArraySize(), index)); shaderObject->activeUniformBlocks[blockId].fields.push_back(activeUniforms.size());
}
activeUniforms.push_back(Uniform(glVariableType(type), glVariablePrecision(type), name.c_str(), type.getArraySize(), offset, blockId));
if(isSamplerRegister(type)) if(isSamplerRegister(type))
{ {
for(int i = 0; i < type.totalRegisterCount(); i++) for(int i = 0; i < type.totalRegisterCount(); i++)
{ {
shader->declareSampler(index + i); shader->declareSampler(offset + i);
} }
} }
} }
else else
{ {
const TFieldList& fields = structure->fields(); const TFieldList& fields = structure ? structure->fields() : block->fields();
const bool containerHasName = structure || block->hasInstanceName();
const TString &containerName = structure ? name : (containerHasName ? block->instanceName() : TString());
if(type.isArray()) if(type.isArray())
{ {
int elementIndex = index; int elementOffset = offset;
for(int i = 0; i < type.getArraySize(); i++) for(int i = 0; i < type.getArraySize(); i++)
{ {
int fieldOffset = (blockId == -1) ? elementOffset : 0;
for(size_t j = 0; j < fields.size(); j++) for(size_t j = 0; j < fields.size(); j++)
{ {
const TType &fieldType = *(fields[j]->type()); const TType &fieldType = *(fields[j]->type());
const TString &fieldName = fields[j]->name(); const TString &fieldName = fields[j]->name();
const TString uniformName = name + "[" + str(i) + "]." + fieldName; const TString uniformName = containerHasName ? containerName + "[" + str(i) + "]." + fieldName : fieldName;
declareUniform(fieldType, uniformName, elementIndex); declareUniform(fieldType, uniformName, fieldOffset, blockId);
elementIndex += fieldType.totalRegisterCount(); fieldOffset += fieldType.totalRegisterCount();
} }
elementOffset = fieldOffset;
} }
} }
else else
{ {
int fieldIndex = index; int fieldOffset = (blockId == -1) ? offset : 0;
for(size_t i = 0; i < fields.size(); i++) for(size_t i = 0; i < fields.size(); i++)
{ {
const TType &fieldType = *(fields[i]->type()); const TType &fieldType = *(fields[i]->type());
const TString &fieldName = fields[i]->name(); const TString &fieldName = fields[i]->name();
const TString uniformName = name + "." + fieldName; const TString uniformName = containerHasName ? containerName + "." + fieldName : fieldName;
declareUniform(fieldType, uniformName, fieldIndex); declareUniform(fieldType, uniformName, fieldOffset, blockId);
fieldIndex += fieldType.totalRegisterCount(); fieldOffset += fieldType.totalRegisterCount();
} }
} }
} }
......
...@@ -32,7 +32,7 @@ namespace glsl ...@@ -32,7 +32,7 @@ namespace glsl
{ {
struct Uniform struct Uniform
{ {
Uniform(GLenum type, GLenum precision, const std::string &name, int arraySize, int registerIndex); Uniform(GLenum type, GLenum precision, const std::string &name, int arraySize, int registerIndex, int blockId);
GLenum type; GLenum type;
GLenum precision; GLenum precision;
...@@ -40,10 +40,34 @@ namespace glsl ...@@ -40,10 +40,34 @@ namespace glsl
int arraySize; int arraySize;
int registerIndex; int registerIndex;
int blockId;
}; };
typedef std::vector<Uniform> ActiveUniforms; typedef std::vector<Uniform> ActiveUniforms;
struct UniformBlock
{
UniformBlock(const std::string& name, const std::string& instanceName, unsigned int dataSize, unsigned int arraySize,
TLayoutBlockStorage layout, bool isRowMajorLayout, int registerIndex, int blockId);
const std::string& getName() const { return (instanceName.length() > 0) ? instanceName : name; }
std::string name;
std::string instanceName;
unsigned int dataSize;
unsigned int arraySize;
TLayoutBlockStorage layout;
bool isRowMajorLayout;
std::vector<int> fields;
int registerIndex;
int blockId;
};
typedef std::vector<UniformBlock> ActiveUniformBlocks;
struct Attribute struct Attribute
{ {
Attribute(); Attribute();
...@@ -99,6 +123,7 @@ namespace glsl ...@@ -99,6 +123,7 @@ namespace glsl
VaryingList varyings; VaryingList varyings;
ActiveUniforms activeUniforms; ActiveUniforms activeUniforms;
ActiveAttributes activeAttributes; ActiveAttributes activeAttributes;
ActiveUniformBlocks activeUniformBlocks;
}; };
struct Function struct Function
...@@ -180,7 +205,7 @@ namespace glsl ...@@ -180,7 +205,7 @@ namespace glsl
int allocate(VariableArray &list, TIntermTyped *variable); int allocate(VariableArray &list, TIntermTyped *variable);
void free(VariableArray &list, TIntermTyped *variable); void free(VariableArray &list, TIntermTyped *variable);
void declareUniform(const TType &type, const TString &name, int index); void declareUniform(const TType &type, const TString &name, int offset, int blockId = -1);
GLenum glVariableType(const TType &type); GLenum glVariableType(const TType &type);
GLenum glVariablePrecision(const TType &type); GLenum glVariablePrecision(const TType &type);
......
...@@ -3031,6 +3031,7 @@ void Context::applyShaders() ...@@ -3031,6 +3031,7 @@ void Context::applyShaders()
} }
programObject->applyUniforms(); programObject->applyUniforms();
programObject->applyUniformBuffers();
} }
void Context::applyTextures() void Context::applyTextures()
......
...@@ -34,17 +34,11 @@ namespace es2 ...@@ -34,17 +34,11 @@ namespace es2
// Helper struct representing a single shader uniform // Helper struct representing a single shader uniform
struct Uniform struct Uniform
{ {
struct BlockMemberInfo struct BlockInfo
{ {
BlockMemberInfo(int offset, int arrayStride, int matrixStride, bool isRowMajorMatrix) BlockInfo(const glsl::Uniform& uniform, int blockIndex, bool rowMajorLayout);
: offset(offset), arrayStride(arrayStride), matrixStride(matrixStride), isRowMajorMatrix(isRowMajorMatrix)
{}
static BlockMemberInfo getDefaultBlockInfo()
{
return BlockMemberInfo(-1, -1, -1, false);
}
int index;
int offset; int offset;
int arrayStride; int arrayStride;
int matrixStride; int matrixStride;
...@@ -52,7 +46,7 @@ namespace es2 ...@@ -52,7 +46,7 @@ namespace es2
}; };
Uniform(GLenum type, GLenum precision, const std::string &name, unsigned int arraySize, Uniform(GLenum type, GLenum precision, const std::string &name, unsigned int arraySize,
const int blockIndex, const BlockMemberInfo &blockInfo); const BlockInfo &blockInfo);
~Uniform(); ~Uniform();
...@@ -64,8 +58,7 @@ namespace es2 ...@@ -64,8 +58,7 @@ namespace es2
const GLenum precision; const GLenum precision;
const std::string name; const std::string name;
const unsigned int arraySize; const unsigned int arraySize;
const int blockIndex; const BlockInfo blockInfo;
const BlockMemberInfo blockInfo;
unsigned char *data; unsigned char *data;
bool dirty; bool dirty;
...@@ -78,7 +71,12 @@ namespace es2 ...@@ -78,7 +71,12 @@ namespace es2
struct UniformBlock struct UniformBlock
{ {
// use GL_INVALID_INDEX for non-array elements // use GL_INVALID_INDEX for non-array elements
UniformBlock(const std::string &name, unsigned int elementIndex, unsigned int dataSize); UniformBlock(const std::string &name, unsigned int elementIndex, unsigned int dataSize, std::vector<unsigned int> memberUniformIndexes);
void setRegisterIndex(GLenum shader, unsigned int registerIndex);
// For std::find on UniformBlockArray
inline bool operator==(const UniformBlock& other) const { return name == other.name; }
bool isArrayElement() const; bool isArrayElement() const;
bool isReferencedByVertexShader() const; bool isReferencedByVertexShader() const;
...@@ -172,6 +170,7 @@ namespace es2 ...@@ -172,6 +170,7 @@ namespace es2
void dirtyAllUniforms(); void dirtyAllUniforms();
void applyUniforms(); void applyUniforms();
void applyUniformBuffers();
void link(); void link();
bool isLinked() const; bool isLinked() const;
...@@ -225,7 +224,10 @@ namespace es2 ...@@ -225,7 +224,10 @@ namespace es2
int getAttributeBinding(const glsl::Attribute &attribute); int getAttributeBinding(const glsl::Attribute &attribute);
bool linkUniforms(const Shader *shader); bool linkUniforms(const Shader *shader);
bool defineUniform(GLenum shader, GLenum type, GLenum precision, const std::string &_name, unsigned int arraySize, int registerIndex); bool linkUniformBlocks(const Shader *vertexShader, const Shader *fragmentShader);
bool areMatchingUniformBlocks(const glsl::UniformBlock &block1, const glsl::UniformBlock &block2, const Shader *shader1, const Shader *shader2);
bool defineUniform(GLenum shader, GLenum type, GLenum precision, const std::string &_name, unsigned int arraySize, int registerIndex, const Uniform::BlockInfo& blockInfo);
bool defineUniformBlock(const Shader *shader, const glsl::UniformBlock &block);
bool applyUniform1bv(GLint location, GLsizei count, const GLboolean *v); bool applyUniform1bv(GLint location, GLsizei count, const GLboolean *v);
bool applyUniform2bv(GLint location, GLsizei count, const GLboolean *v); bool applyUniform2bv(GLint location, GLsizei count, const GLboolean *v);
bool applyUniform3bv(GLint location, GLsizei count, const GLboolean *v); bool applyUniform3bv(GLint location, GLsizei count, const GLboolean *v);
...@@ -293,7 +295,7 @@ namespace es2 ...@@ -293,7 +295,7 @@ namespace es2
UniformArray uniforms; UniformArray uniforms;
typedef std::vector<UniformLocation> UniformIndex; typedef std::vector<UniformLocation> UniformIndex;
UniformIndex uniformIndex; UniformIndex uniformIndex;
typedef std::vector<UniformBlock*> UniformBlockArray; typedef std::vector<UniformBlock> UniformBlockArray;
UniformBlockArray uniformBlocks; UniformBlockArray uniformBlocks;
typedef std::vector<LinkedVarying> LinkedVaryingArray; typedef std::vector<LinkedVarying> LinkedVaryingArray;
LinkedVaryingArray transformFeedbackLinkedVaryings; LinkedVaryingArray transformFeedbackLinkedVaryings;
......
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