зеркало из https://github.com/AvaloniaUI/angle.git
Vulkan: dFdy is incorrect when the framebuffer is flipped
To account for framebuffer flipping, `dFdy()` expressions must be changed to: dFdy() * ANGLEUniforms.viewportYScale Bug: angleproject:3487 Test: dEQP-GLES3.functional.shaders.derivate.dfdy.* Change-Id: I38f25ba37fb8c5ae61cee5ac911df88ec4a93fef Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/1678404 Commit-Queue: Tim Van Patten <timvp@google.com> Reviewed-by: Jamie Madill <jmadill@chromium.org> Reviewed-by: Shahbaz Youssefi <syoussefi@chromium.org>
This commit is contained in:
Родитель
b7418a177f
Коммит
6d37651a23
|
@ -154,6 +154,8 @@ angle_translator_sources = [
|
||||||
"src/compiler/translator/tree_ops/RemoveUnreferencedVariables.h",
|
"src/compiler/translator/tree_ops/RemoveUnreferencedVariables.h",
|
||||||
"src/compiler/translator/tree_ops/RewriteAtomicFunctionExpressions.cpp",
|
"src/compiler/translator/tree_ops/RewriteAtomicFunctionExpressions.cpp",
|
||||||
"src/compiler/translator/tree_ops/RewriteAtomicFunctionExpressions.h",
|
"src/compiler/translator/tree_ops/RewriteAtomicFunctionExpressions.h",
|
||||||
|
"src/compiler/translator/tree_ops/RewriteDfdy.cpp",
|
||||||
|
"src/compiler/translator/tree_ops/RewriteDfdy.h",
|
||||||
"src/compiler/translator/tree_ops/RewriteDoWhile.cpp",
|
"src/compiler/translator/tree_ops/RewriteDoWhile.cpp",
|
||||||
"src/compiler/translator/tree_ops/RewriteDoWhile.h",
|
"src/compiler/translator/tree_ops/RewriteDoWhile.h",
|
||||||
"src/compiler/translator/tree_ops/RewriteExpressionsWithShaderStorageBlock.cpp",
|
"src/compiler/translator/tree_ops/RewriteExpressionsWithShaderStorageBlock.cpp",
|
||||||
|
@ -183,6 +185,8 @@ angle_translator_sources = [
|
||||||
"src/compiler/translator/tree_ops/VectorizeVectorScalarArithmetic.cpp",
|
"src/compiler/translator/tree_ops/VectorizeVectorScalarArithmetic.cpp",
|
||||||
"src/compiler/translator/tree_ops/VectorizeVectorScalarArithmetic.h",
|
"src/compiler/translator/tree_ops/VectorizeVectorScalarArithmetic.h",
|
||||||
"src/compiler/translator/tree_util/BuiltIn_autogen.h",
|
"src/compiler/translator/tree_util/BuiltIn_autogen.h",
|
||||||
|
"src/compiler/translator/tree_util/FindFunction.cpp",
|
||||||
|
"src/compiler/translator/tree_util/FindFunction.h",
|
||||||
"src/compiler/translator/tree_util/FindMain.cpp",
|
"src/compiler/translator/tree_util/FindMain.cpp",
|
||||||
"src/compiler/translator/tree_util/FindMain.h",
|
"src/compiler/translator/tree_util/FindMain.h",
|
||||||
"src/compiler/translator/tree_util/FindSymbolNode.cpp",
|
"src/compiler/translator/tree_util/FindSymbolNode.cpp",
|
||||||
|
|
|
@ -17,8 +17,10 @@
|
||||||
#include "compiler/translator/OutputVulkanGLSL.h"
|
#include "compiler/translator/OutputVulkanGLSL.h"
|
||||||
#include "compiler/translator/StaticType.h"
|
#include "compiler/translator/StaticType.h"
|
||||||
#include "compiler/translator/tree_ops/NameEmbeddedUniformStructs.h"
|
#include "compiler/translator/tree_ops/NameEmbeddedUniformStructs.h"
|
||||||
|
#include "compiler/translator/tree_ops/RewriteDfdy.h"
|
||||||
#include "compiler/translator/tree_ops/RewriteStructSamplers.h"
|
#include "compiler/translator/tree_ops/RewriteStructSamplers.h"
|
||||||
#include "compiler/translator/tree_util/BuiltIn_autogen.h"
|
#include "compiler/translator/tree_util/BuiltIn_autogen.h"
|
||||||
|
#include "compiler/translator/tree_util/FindFunction.h"
|
||||||
#include "compiler/translator/tree_util/FindMain.h"
|
#include "compiler/translator/tree_util/FindMain.h"
|
||||||
#include "compiler/translator/tree_util/IntermNode_util.h"
|
#include "compiler/translator/tree_util/IntermNode_util.h"
|
||||||
#include "compiler/translator/tree_util/ReplaceVariable.h"
|
#include "compiler/translator/tree_util/ReplaceVariable.h"
|
||||||
|
@ -388,12 +390,13 @@ const TVariable *AddDriverUniformsToShader(TIntermBlock *root, TSymbolTable *sym
|
||||||
TIntermSymbol *driverUniformsDeclarator = new TIntermSymbol(driverUniformsVar);
|
TIntermSymbol *driverUniformsDeclarator = new TIntermSymbol(driverUniformsVar);
|
||||||
driverUniformsDecl->appendDeclarator(driverUniformsDeclarator);
|
driverUniformsDecl->appendDeclarator(driverUniformsDeclarator);
|
||||||
|
|
||||||
// Insert the declarations before Main.
|
// Insert the declarations before first function, since functions before main() may refer to
|
||||||
|
// these values.
|
||||||
TIntermSequence *insertSequence = new TIntermSequence;
|
TIntermSequence *insertSequence = new TIntermSequence;
|
||||||
insertSequence->push_back(driverUniformsDecl);
|
insertSequence->push_back(driverUniformsDecl);
|
||||||
|
|
||||||
size_t mainIndex = FindMainIndex(root);
|
size_t firstFunctionIndex = FindFirstFunctionDefinitionIndex(root);
|
||||||
root->insertChildNodes(mainIndex, *insertSequence);
|
root->insertChildNodes(firstFunctionIndex, *insertSequence);
|
||||||
|
|
||||||
return driverUniformsVar;
|
return driverUniformsVar;
|
||||||
}
|
}
|
||||||
|
@ -766,6 +769,11 @@ void TranslatorVulkan::translate(TIntermBlock *root,
|
||||||
InsertFragCoordCorrection(root, GetMainSequence(root), &getSymbolTable(),
|
InsertFragCoordCorrection(root, GetMainSequence(root), &getSymbolTable(),
|
||||||
driverUniforms);
|
driverUniforms);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
TIntermBinary *viewportYScale = CreateDriverUniformRef(driverUniforms, kViewportYScale);
|
||||||
|
RewriteDfdy(root, getSymbolTable(), getShaderVersion(), viewportYScale);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
@ -0,0 +1,89 @@
|
||||||
|
//
|
||||||
|
// Copyright 2019 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.
|
||||||
|
//
|
||||||
|
// Implementation of dFdy viewport transformation.
|
||||||
|
// See header for more info.
|
||||||
|
|
||||||
|
#include "compiler/translator/tree_ops/RewriteDfdy.h"
|
||||||
|
|
||||||
|
#include "common/angleutils.h"
|
||||||
|
#include "compiler/translator/SymbolTable.h"
|
||||||
|
#include "compiler/translator/tree_util/IntermNode_util.h"
|
||||||
|
#include "compiler/translator/tree_util/IntermTraverse.h"
|
||||||
|
|
||||||
|
namespace sh
|
||||||
|
{
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
|
|
||||||
|
class Traverser : public TIntermTraverser
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
static void Apply(TIntermNode *root,
|
||||||
|
const TSymbolTable &symbolTable,
|
||||||
|
TIntermBinary *viewportYScale);
|
||||||
|
|
||||||
|
private:
|
||||||
|
Traverser(TIntermBinary *viewportYScale, TSymbolTable *symbolTable);
|
||||||
|
bool visitUnary(Visit visit, TIntermUnary *node) override;
|
||||||
|
|
||||||
|
TIntermBinary *mViewportYScale = nullptr;
|
||||||
|
};
|
||||||
|
|
||||||
|
Traverser::Traverser(TIntermBinary *viewportYScale, TSymbolTable *symbolTable)
|
||||||
|
: TIntermTraverser(true, false, false, symbolTable), mViewportYScale(viewportYScale)
|
||||||
|
{}
|
||||||
|
|
||||||
|
// static
|
||||||
|
void Traverser::Apply(TIntermNode *root,
|
||||||
|
const TSymbolTable &symbolTable,
|
||||||
|
TIntermBinary *viewportYScale)
|
||||||
|
{
|
||||||
|
TSymbolTable *pSymbolTable = const_cast<TSymbolTable *>(&symbolTable);
|
||||||
|
Traverser traverser(viewportYScale, pSymbolTable);
|
||||||
|
root->traverse(&traverser);
|
||||||
|
traverser.updateTree();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Traverser::visitUnary(Visit visit, TIntermUnary *node)
|
||||||
|
{
|
||||||
|
// Decide if the node represents a call to dFdy()
|
||||||
|
if (node->getOp() != EOpDFdy)
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Copy the dFdy node so we can replace it with the corrected value
|
||||||
|
TIntermUnary *newDfdy = node->deepCopy()->getAsUnaryNode();
|
||||||
|
|
||||||
|
size_t objectSize = node->getType().getObjectSize();
|
||||||
|
TOperator multiplyOp = (objectSize == 1) ? EOpMul : EOpVectorTimesScalar;
|
||||||
|
|
||||||
|
// Correct dFdy()'s value:
|
||||||
|
// (dFdy() * ANGLEUniforms.viewportYScale)
|
||||||
|
TIntermBinary *correctedDfdy = new TIntermBinary(multiplyOp, newDfdy, mViewportYScale);
|
||||||
|
|
||||||
|
// Replace the old dFdy node with the new node that contains the corrected value
|
||||||
|
queueReplacement(correctedDfdy, OriginalNode::IS_DROPPED);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
} // anonymous namespace
|
||||||
|
|
||||||
|
void RewriteDfdy(TIntermNode *root,
|
||||||
|
const TSymbolTable &symbolTable,
|
||||||
|
int shaderVersion,
|
||||||
|
TIntermBinary *viewportYScale)
|
||||||
|
{
|
||||||
|
// dFdy is only valid in GLSL 3.0 and later.
|
||||||
|
if (shaderVersion < 300)
|
||||||
|
return;
|
||||||
|
|
||||||
|
Traverser::Apply(root, symbolTable, viewportYScale);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace sh
|
|
@ -0,0 +1,30 @@
|
||||||
|
//
|
||||||
|
// Copyright 2019 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.
|
||||||
|
//
|
||||||
|
// This mutating tree traversal flips the output of dFdy() to account for framebuffer flipping.
|
||||||
|
//
|
||||||
|
// From: dFdy(p)
|
||||||
|
// To: (dFdy(p) * viewportYScale)
|
||||||
|
//
|
||||||
|
// See http://anglebug.com/3487
|
||||||
|
|
||||||
|
#ifndef COMPILER_TRANSLATOR_TREEOPS_FLIP_DFDY_H_
|
||||||
|
#define COMPILER_TRANSLATOR_TREEOPS_FLIP_DFDY_H_
|
||||||
|
|
||||||
|
class TIntermNode;
|
||||||
|
class TIntermBinary;
|
||||||
|
class TSymbolTable;
|
||||||
|
|
||||||
|
namespace sh
|
||||||
|
{
|
||||||
|
|
||||||
|
void RewriteDfdy(TIntermNode *root,
|
||||||
|
const TSymbolTable &symbolTable,
|
||||||
|
int shaderVersion,
|
||||||
|
TIntermBinary *viewportYScale);
|
||||||
|
|
||||||
|
} // namespace sh
|
||||||
|
|
||||||
|
#endif // COMPILER_TRANSLATOR_TREEOPS_FLIP_DFDY_H_
|
|
@ -0,0 +1,32 @@
|
||||||
|
//
|
||||||
|
// Copyright 2019 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.
|
||||||
|
//
|
||||||
|
|
||||||
|
// FindFunction.cpp: Find functions.
|
||||||
|
|
||||||
|
#include "compiler/translator/tree_util/FindFunction.h"
|
||||||
|
|
||||||
|
#include "compiler/translator/IntermNode.h"
|
||||||
|
#include "compiler/translator/Symbol.h"
|
||||||
|
|
||||||
|
namespace sh
|
||||||
|
{
|
||||||
|
|
||||||
|
size_t FindFirstFunctionDefinitionIndex(TIntermBlock *root)
|
||||||
|
{
|
||||||
|
const TIntermSequence &sequence = *root->getSequence();
|
||||||
|
for (size_t index = 0; index < sequence.size(); ++index)
|
||||||
|
{
|
||||||
|
TIntermNode *node = sequence[index];
|
||||||
|
TIntermFunctionDefinition *nodeFunction = node->getAsFunctionDefinition();
|
||||||
|
if (nodeFunction != nullptr)
|
||||||
|
{
|
||||||
|
return index;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return std::numeric_limits<size_t>::max();
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace sh
|
|
@ -0,0 +1,21 @@
|
||||||
|
//
|
||||||
|
// Copyright 2019 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.
|
||||||
|
//
|
||||||
|
|
||||||
|
// FindFunction.h: Adds functions to find functions
|
||||||
|
|
||||||
|
#ifndef COMPILER_TRANSLATOR_TREEUTIL_FINDFUNCTION_H_
|
||||||
|
#define COMPILER_TRANSLATOR_TREEUTIL_FINDFUNCTION_H_
|
||||||
|
|
||||||
|
#include <cstddef>
|
||||||
|
|
||||||
|
namespace sh
|
||||||
|
{
|
||||||
|
class TIntermBlock;
|
||||||
|
|
||||||
|
size_t FindFirstFunctionDefinitionIndex(TIntermBlock *root);
|
||||||
|
} // namespace sh
|
||||||
|
|
||||||
|
#endif // COMPILER_TRANSLATOR_TREEUTIL_FINDFUNCTION_H_
|
|
@ -660,7 +660,6 @@
|
||||||
3219 VULKAN : dEQP-GLES3.functional.negative_api.shader.link_program = FAIL
|
3219 VULKAN : dEQP-GLES3.functional.negative_api.shader.link_program = FAIL
|
||||||
3219 VULKAN : dEQP-GLES3.functional.negative_api.shader.use_program = FAIL
|
3219 VULKAN : dEQP-GLES3.functional.negative_api.shader.use_program = FAIL
|
||||||
3443 VULKAN : dEQP-GLES3.functional.ubo.random.basic_arrays.10 = FAIL
|
3443 VULKAN : dEQP-GLES3.functional.ubo.random.basic_arrays.10 = FAIL
|
||||||
3487 VULKAN : dEQP-GLES3.functional.shaders.derivate.dfdy.* = FAIL
|
|
||||||
|
|
||||||
// New vertex attribute formats:
|
// New vertex attribute formats:
|
||||||
3193 VULKAN : dEQP-GLES3.functional.vertex_arrays.single_attribute.*.int2_10_10_10.* = SKIP
|
3193 VULKAN : dEQP-GLES3.functional.vertex_arrays.single_attribute.*.int2_10_10_10.* = SKIP
|
||||||
|
|
Загрузка…
Ссылка в новой задаче