Support writing initializers using HLSL literal syntax
Instead of using constructor functions to initialize variables, it is
better to use literal initializer syntax provided by HLSL when it is
possible. This way shader complexity is reduced and constant array
initialization doesn't have to go through as many AST transformations.
Before this patch, vec4 initialization would result in the following
kind of HLSL:
float4 f = float4(1.0, 2.0, 3.0, 4.0);
After this patch, it will be:
float4 f = {1.0, 2.0, 3.0, 4.0};
Before this patch, vec2 array initialization would result in the
following kind of HLSL:
float2 f[2] = {0, 0, 0, 0};
angle_construct_into_2_float2(f, float2(1.0, 2.0), float2(3.0, 4.0));
After this patch, it will be:
float2 f[2] = {1.0, 2.0, 3.0, 4.0};
BUG=angleproject:1094
BUG=541551
TEST=WebGL conformance tests
Change-Id: I9816a8d95a2cba3964922f6b561862d478da6145
Reviewed-on: https://chromium-review.googlesource.com/311160
Reviewed-by: Zhenyao Mo <zmo@chromium.org>
Tested-by: Olli Etuaho <oetuaho@nvidia.com>
diff --git a/src/compiler/translator/SeparateArrayInitialization.cpp b/src/compiler/translator/SeparateArrayInitialization.cpp
index 78aeb8d..de9050c 100644
--- a/src/compiler/translator/SeparateArrayInitialization.cpp
+++ b/src/compiler/translator/SeparateArrayInitialization.cpp
@@ -10,13 +10,15 @@
// type[n] a;
// a = initializer;
//
-// Note that if the array is declared as const, the initialization is still split, making the AST
-// technically invalid. Because of that this transformation should only be used when subsequent
-// stages don't care about const qualifiers.
+// Note that if the array is declared as const, the initialization may still be split, making the
+// AST technically invalid. Because of that this transformation should only be used when subsequent
+// stages don't care about const qualifiers. However, the initialization will not be split if the
+// initializer can be written as a HLSL literal.
#include "compiler/translator/SeparateArrayInitialization.h"
#include "compiler/translator/IntermNode.h"
+#include "compiler/translator/OutputHLSL.h"
namespace
{
@@ -51,7 +53,7 @@
if (initNode != nullptr && initNode->getOp() == EOpInitialize)
{
TIntermTyped *initializer = initNode->getRight();
- if (initializer->isArray())
+ if (initializer->isArray() && !sh::OutputHLSL::canWriteAsHLSLLiteral(initializer))
{
// We rely on that array declarations have been isolated to single declarations.
ASSERT(sequence->size() == 1);