Commit d91c3793 by Luc Ferron Committed by Commit Bot

Vulkan: Implement support for structs in uniforms

- Also enables 174 additional dEQP tests. Bug: angleproject:2446 Change-Id: I07cce46815d2f7a80fd48e7fd9407f7d528b397f Reviewed-on: https://chromium-review.googlesource.com/998406Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Commit-Queue: Luc Ferron <lucferron@chromium.org>
parent 26084d0a
......@@ -76,9 +76,10 @@ class TOutputGLSLBase : public TIntermTraverser
// Used to translate function names for differences between ESSL and GLSL
virtual ImmutableString translateTextureFunction(const ImmutableString &name) { return name; }
void declareStruct(const TStructure *structure);
private:
bool structDeclared(const TStructure *structure) const;
void declareStruct(const TStructure *structure);
void declareInterfaceBlockLayout(const TInterfaceBlock *interfaceBlock);
void declareInterfaceBlock(const TInterfaceBlock *interfaceBlock);
......
......@@ -77,4 +77,10 @@ void TOutputVulkanGLSL::writeLayoutQualifier(TIntermTyped *variable)
out << ") ";
}
void TOutputVulkanGLSL::writeStructType(const TStructure *structure)
{
declareStruct(structure);
objSink() << ";\n";
}
} // namespace sh
......@@ -27,6 +27,8 @@ class TOutputVulkanGLSL : public TOutputGLSL
ShShaderOutput output,
ShCompileOptions compileOptions);
void writeStructType(const TStructure *structure);
protected:
void writeLayoutQualifier(TIntermTyped *variable) override;
};
......
......@@ -25,6 +25,59 @@ namespace sh
namespace
{
// This traverses nodes, find the struct ones and add their declarations to the sink. It also
// removes the nodes from the tree as it processes them.
class DeclareStructTypesTraverser : public TIntermTraverser
{
public:
DeclareStructTypesTraverser(TOutputVulkanGLSL *outputVulkanGLSL)
: TIntermTraverser(true, false, false), mOutputVulkanGLSL(outputVulkanGLSL)
{
}
bool visitDeclaration(Visit visit, TIntermDeclaration *node) override
{
ASSERT(visit == PreVisit);
if (!mInGlobalScope)
{
// We only want to declare the global structs in this traverser.
// TODO(lucferron): Add a test in GLSLTest for this specific case.
// http://anglebug.com/2459
return false;
}
const TIntermSequence &sequence = *(node->getSequence());
TIntermTyped *declarator = sequence.front()->getAsTyped();
const TType &type = declarator->getType();
if (type.isStructSpecifier())
{
TIntermSymbol *symbolNode = declarator->getAsSymbolNode();
if (symbolNode != nullptr && symbolNode->variable().symbolType() == SymbolType::Empty)
{
mOutputVulkanGLSL->writeStructType(type.getStruct());
// Remove the struct specifier declaration from the tree so it isn't parsed again.
TIntermSequence emptyReplacement;
mMultiReplacements.emplace_back(getParentNode()->getAsBlock(), node,
emptyReplacement);
}
else
{
// TODO(lucferron): Support structs with initializers correctly.
// http://anglebug.com/2459
UNIMPLEMENTED();
}
}
return false;
}
private:
TOutputVulkanGLSL *mOutputVulkanGLSL;
};
class DeclareDefaultUniformsTraverser : public TIntermTraverser
{
public:
......@@ -153,17 +206,36 @@ void TranslatorVulkan::translate(TIntermBlock *root,
PerformanceDiagnostics * /*perfDiagnostics*/)
{
TInfoSinkBase &sink = getInfoSink().obj;
TOutputVulkanGLSL outputGLSL(sink, getArrayIndexClampingStrategy(), getHashFunction(),
getNameMap(), &getSymbolTable(), getShaderType(),
getShaderVersion(), getOutputType(), compileOptions);
sink << "#version 450 core\n";
// Write out default uniforms into a uniform block assigned to a specific set/binding.
int defaultUniformCount = 0;
int structTypesUsedForUniforms = 0;
for (const auto &uniform : getUniforms())
{
if (!uniform.isBuiltIn() && uniform.staticUse && !gl::IsOpaqueType(uniform.type))
{
++defaultUniformCount;
}
if (uniform.isStruct())
{
++structTypesUsedForUniforms;
}
}
// TODO(lucferron): Refactor this function to do less tree traversals.
// http://anglebug.com/2461
if (structTypesUsedForUniforms > 0)
{
// We must declare the struct types before using them.
DeclareStructTypesTraverser structTypesTraverser(&outputGLSL);
root->traverse(&structTypesTraverser);
structTypesTraverser.updateTree();
}
if (defaultUniformCount > 0)
......@@ -218,9 +290,6 @@ void TranslatorVulkan::translate(TIntermBlock *root,
}
// Write translated shader.
TOutputVulkanGLSL outputGLSL(sink, getArrayIndexClampingStrategy(), getHashFunction(),
getNameMap(), &getSymbolTable(), getShaderType(),
getShaderVersion(), getOutputType(), compileOptions);
root->traverse(&outputGLSL);
}
......
......@@ -469,7 +469,8 @@ void ProgramVk::setUniformImpl(GLint location, GLsizei count, const T *v, GLenum
ASSERT(linkedUniform.typeInfo->type == gl::VariableBoolVectorType(entryPointType));
GLint initialArrayOffset = locationInfo.arrayIndex * layoutInfo.arrayStride;
GLint initialArrayOffset =
locationInfo.arrayIndex * layoutInfo.arrayStride + layoutInfo.offset;
for (GLint i = 0; i < count; i++)
{
GLint elementOffset = i * layoutInfo.arrayStride + initialArrayOffset;
......
......@@ -240,19 +240,19 @@
2161 VULKAN : dEQP-GLES2.functional.attribute_location.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.multisample.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.basic_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.struct_in_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.multiple_basic_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.multiple_nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.basic_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.struct_in_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.nested_structs_arrays.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.multiple_basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.multiple_nested_structs_arrays.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.info_query.unused_uniforms.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.basic.sampler* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.basic_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.struct_in_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.basic_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.struct_in_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.nested_structs_arrays.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.multiple_basic.vertex = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.multiple_basic.fragment = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.get_uniform.multiple_basic.both = SKIP
......@@ -268,10 +268,12 @@
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.initial.render.nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.basic.sampler* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.basic_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.struct_in_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.basic_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.basic_struct.bool_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.struct_in_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.struct_in_array.bool_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.nested_structs_arrays.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.basic_array_first_elem_without_brackets.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.multiple_basic.vertex = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.get_uniform.multiple_basic.fragment = SKIP
......@@ -282,31 +284,31 @@
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.basic.mat3_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.basic.samplerCube* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.basic_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.struct_in_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.basic_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.struct_in_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.multiple_basic.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_pointer.render.nested_structs_arrays.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.basic.sampler* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.basic_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.struct_in_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.multiple_basic_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.basic_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.struct_in_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.nested_structs_arrays.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.multiple_basic_array.vertex = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.multiple_nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.get_uniform.basic_array_first_elem_without_brackets.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.basic.samplerCube* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.basic_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.struct_in_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.nested_structs_arrays.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_full.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.basic_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.struct_in_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.by_value.render.nested_structs_arrays.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_full.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_full.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_full.multiple_basic_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_partial.basic_array.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_partial.array_in_struct.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_partial.array_in_struct.sampler2D_* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.basic_array_assign_partial.multiple_basic_array.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.value.assigned.unused_uniforms.* = SKIP
2161 VULKAN : dEQP-GLES2.functional.uniform_api.random.* = SKIP
......
......@@ -4208,7 +4208,10 @@ TEST_P(GLSLTest_ES3, VaryingStaticallyUsedButNotActiveInFragmentShader)
ANGLE_GL_PROGRAM(program, vertexShader, fragmentShader);
}
// Use this to select which configurations (e.g. which renderer, which GLES major version) these tests should be run against.
// Use this to select which configurations (e.g. which renderer, which GLES major version) these
// tests should be run against.
// TODO(lucferron): Enable tests for Vulkan and debug/open bugs for each failing ones.
// http://anglebug.com/2460
ANGLE_INSTANTIATE_TEST(GLSLTest,
ES2_D3D9(),
ES2_D3D11(),
......
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