Path: blob/main_old/src/tests/compiler_tests/OVR_multiview2_test.cpp
1693 views
//1// Copyright 2016 The ANGLE Project Authors. All rights reserved.2// Use of this source code is governed by a BSD-style license that can be3// found in the LICENSE file.4//5// OVR_multiview2_test.cpp:6// Test that shaders with gl_ViewID_OVR are validated correctly.7//89#include "GLSLANG/ShaderLang.h"10#include "compiler/translator/tree_util/IntermTraverse.h"11#include "tests/test_utils/ShaderCompileTreeTest.h"12#include "tests/test_utils/compiler_test.h"1314using namespace sh;1516namespace17{1819class SymbolOccurrenceCounter : public TIntermTraverser20{21public:22SymbolOccurrenceCounter() : TIntermTraverser(true, false, false), mNumberOfOccurrences(0u) {}2324void visitSymbol(TIntermSymbol *node) override25{26if (shouldCountSymbol(node))27{28++mNumberOfOccurrences;29}30}3132virtual bool shouldCountSymbol(const TIntermSymbol *node) const = 0;3334unsigned getNumberOfOccurrences() const { return mNumberOfOccurrences; }3536private:37unsigned mNumberOfOccurrences;38};3940class SymbolOccurrenceCounterByQualifier : public SymbolOccurrenceCounter41{42public:43SymbolOccurrenceCounterByQualifier(TQualifier symbolQualifier)44: mSymbolQualifier(symbolQualifier)45{}4647bool shouldCountSymbol(const TIntermSymbol *node) const override48{49return node->getQualifier() == mSymbolQualifier;50}5152private:53TQualifier mSymbolQualifier;54};5556class SymbolOccurrenceCounterByName : public SymbolOccurrenceCounter57{58public:59SymbolOccurrenceCounterByName(const ImmutableString &symbolName) : mSymbolName(symbolName) {}6061bool shouldCountSymbol(const TIntermSymbol *node) const override62{63return node->variable().symbolType() != SymbolType::Empty && node->getName() == mSymbolName;64}6566private:67ImmutableString mSymbolName;68};6970class SymbolOccurrenceCounterByNameAndQualifier : public SymbolOccurrenceCounter71{72public:73SymbolOccurrenceCounterByNameAndQualifier(const ImmutableString &symbolName,74TQualifier qualifier)75: mSymbolName(symbolName), mSymbolQualifier(qualifier)76{}7778bool shouldCountSymbol(const TIntermSymbol *node) const override79{80return node->variable().symbolType() != SymbolType::Empty &&81node->getName() == mSymbolName && node->getQualifier() == mSymbolQualifier;82}8384private:85ImmutableString mSymbolName;86TQualifier mSymbolQualifier;87};8889class OVRMultiview2VertexShaderTest : public ShaderCompileTreeTest90{91public:92OVRMultiview2VertexShaderTest() {}9394protected:95::GLenum getShaderType() const override { return GL_VERTEX_SHADER; }96ShShaderSpec getShaderSpec() const override { return SH_WEBGL3_SPEC; }97void initResources(ShBuiltInResources *resources) override98{99resources->OVR_multiview = 1;100resources->OVR_multiview2 = 1;101resources->MaxViewsOVR = 4;102}103};104105class OVRMultiview2FragmentShaderTest : public ShaderCompileTreeTest106{107public:108OVRMultiview2FragmentShaderTest() {}109110protected:111::GLenum getShaderType() const override { return GL_FRAGMENT_SHADER; }112ShShaderSpec getShaderSpec() const override { return SH_WEBGL3_SPEC; }113void initResources(ShBuiltInResources *resources) override114{115resources->OVR_multiview = 1;116resources->OVR_multiview2 = 1;117resources->MaxViewsOVR = 4;118}119};120121class OVRMultiview2OutputCodeTest : public MatchOutputCodeTest122{123public:124OVRMultiview2OutputCodeTest(sh::GLenum shaderType)125: MatchOutputCodeTest(shaderType, 0, SH_ESSL_OUTPUT)126{127addOutputType(SH_GLSL_COMPATIBILITY_OUTPUT);128129getResources()->OVR_multiview = 1;130getResources()->OVR_multiview2 = 1;131getResources()->MaxViewsOVR = 4;132}133134void requestHLSLOutput()135{136#if defined(ANGLE_ENABLE_HLSL)137addOutputType(SH_HLSL_4_1_OUTPUT);138#endif139}140141bool foundInAllGLSLCode(const char *str)142{143return foundInGLSLCode(str) && foundInESSLCode(str);144}145146bool foundInHLSLCode(const char *stringToFind) const147{148#if defined(ANGLE_ENABLE_HLSL)149return foundInCode(SH_HLSL_4_1_OUTPUT, stringToFind);150#else151return true;152#endif153}154};155156class OVRMultiview2VertexShaderOutputCodeTest : public OVRMultiview2OutputCodeTest157{158public:159OVRMultiview2VertexShaderOutputCodeTest() : OVRMultiview2OutputCodeTest(GL_VERTEX_SHADER) {}160};161162class OVRMultiview2FragmentShaderOutputCodeTest : public OVRMultiview2OutputCodeTest163{164public:165OVRMultiview2FragmentShaderOutputCodeTest() : OVRMultiview2OutputCodeTest(GL_FRAGMENT_SHADER) {}166};167168class OVRMultiview2ComputeShaderOutputCodeTest : public OVRMultiview2OutputCodeTest169{170public:171OVRMultiview2ComputeShaderOutputCodeTest() : OVRMultiview2OutputCodeTest(GL_COMPUTE_SHADER) {}172};173174void VariableOccursNTimes(TIntermBlock *root,175const ImmutableString &varName,176const TQualifier varQualifier,177unsigned n)178{179// Check that there are n occurrences of the variable with the given name and qualifier.180SymbolOccurrenceCounterByNameAndQualifier viewIDByNameAndQualifier(varName, varQualifier);181root->traverse(&viewIDByNameAndQualifier);182EXPECT_EQ(n, viewIDByNameAndQualifier.getNumberOfOccurrences());183184// Check that there are n occurrences of the variable with the given name. By this we guarantee185// that there are no other occurrences of the variable with the same name but different186// qualifier.187SymbolOccurrenceCounterByName viewIDByName(varName);188root->traverse(&viewIDByName);189EXPECT_EQ(n, viewIDByName.getNumberOfOccurrences());190}191192// Invalid combination of non-matching num_views declarations.193TEST_F(OVRMultiview2VertexShaderTest, InvalidNumViewsMismatch)194{195const std::string &shaderString =196"#version 300 es\n"197"#extension GL_OVR_multiview2 : require\n"198"layout(num_views = 2) in;\n"199"layout(num_views = 1) in;\n"200"void main()\n"201"{\n"202" gl_Position.x = (gl_ViewID_OVR == 0u) ? 1.0 : 0.0;\n"203" gl_Position.yzw = vec3(0, 0, 1);\n"204"}\n";205if (compile(shaderString))206{207FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;208}209}210211// Invalid value zero for num_views.212TEST_F(OVRMultiview2VertexShaderTest, InvalidNumViewsZero)213{214const std::string &shaderString =215"#version 300 es\n"216"#extension GL_OVR_multiview2 : require\n"217"layout(num_views = 0) in;\n"218"void main()\n"219"{\n"220" gl_Position.x = (gl_ViewID_OVR == 0u) ? 1.0 : 0.0;\n"221" gl_Position.yzw = vec3(0, 0, 1);\n"222"}\n";223if (compile(shaderString))224{225FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;226}227}228229// Too large value for num_views.230TEST_F(OVRMultiview2VertexShaderTest, InvalidNumViewsGreaterThanMax)231{232const std::string &shaderString =233"#version 300 es\n"234"#extension GL_OVR_multiview2 : require\n"235"layout(num_views = 5) in;\n"236"void main()\n"237"{\n"238" gl_Position.x = (gl_ViewID_OVR == 0u) ? 1.0 : 0.0;\n"239" gl_Position.yzw = vec3(0, 0, 1);\n"240"}\n";241if (compile(shaderString))242{243FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;244}245}246247// Valid use of gl_ViewID_OVR.248TEST_F(OVRMultiview2VertexShaderTest, ViewIDUsed)249{250const std::string &shaderString =251"#version 300 es\n"252"#extension GL_OVR_multiview2 : require\n"253"layout(num_views = 2) in;\n"254"layout(num_views = 2) in; // Duplicated on purpose\n"255"in vec4 pos;\n"256"out float myOutput;\n"257"void main()\n"258"{\n"259" if (gl_ViewID_OVR == 0u)\n"260" {\n"261" gl_Position = pos;\n"262" myOutput = 1.0;\n"263" }\n"264" else\n"265" {\n"266" gl_Position = pos + vec4(1.0, 0.0, 0.0, 0.0);\n"267" myOutput = 2.0;\n"268" }\n"269" gl_Position += (gl_ViewID_OVR == 0u) ? 1.0 : 0.0;\n"270"}\n";271if (!compile(shaderString))272{273FAIL() << "Shader compilation failed, expecting success:\n" << mInfoLog;274}275}276277// Read gl_FragCoord in a OVR_multiview2 fragment shader.278TEST_F(OVRMultiview2FragmentShaderTest, ReadOfFragCoord)279{280const std::string &shaderString =281"#version 300 es\n"282"#extension GL_OVR_multiview2 : require\n"283"precision highp float;\n"284"out vec4 outColor;\n"285"void main()\n"286"{\n"287" outColor = vec4(gl_FragCoord.xy, 0, 1);\n"288"}\n";289if (!compile(shaderString))290{291FAIL() << "Shader compilation failed, expecting success:\n" << mInfoLog;292}293}294295// Read gl_ViewID_OVR in an OVR_multiview2 fragment shader.296TEST_F(OVRMultiview2FragmentShaderTest, ReadOfViewID)297{298const std::string &shaderString =299"#version 300 es\n"300"#extension GL_OVR_multiview2 : require\n"301"precision highp float;\n"302"out vec4 outColor;\n"303"void main()\n"304"{\n"305" outColor = vec4(gl_ViewID_OVR, 0, 0, 1);\n"306"}\n";307if (!compile(shaderString))308{309FAIL() << "Shader compilation failed, expecting success:\n" << mInfoLog;310}311}312313// Correct use of GL_OVR_multiview2 macro.314TEST_F(OVRMultiview2VertexShaderTest, UseOfExtensionMacro)315{316const std::string &shaderString =317"#version 300 es\n"318"#ifdef GL_OVR_multiview2\n"319"#if (GL_OVR_multiview2 == 1)\n"320"void main()\n"321"{\n"322" gl_Position = vec4(0.0, 0.0, 0.0, 1.0);\n"323"}\n"324"#endif\n"325"#endif\n";326if (!compile(shaderString))327{328FAIL() << "Shader compilation failed, expecting success:\n" << mInfoLog;329}330}331332// Test that gl_ViewID_OVR can't be used as an l-value.333TEST_F(OVRMultiview2VertexShaderTest, ViewIdAsLValue)334{335const std::string &shaderString =336"#version 300 es\n"337"#extension GL_OVR_multiview2 : require\n"338"layout(num_views = 2) in;\n"339"void foo(out uint u)\n"340"{\n"341" u = 3u;\n"342"}\n"343"void main()\n"344"{\n"345" foo(gl_ViewID_OVR);\n"346" gl_Position = vec4(0.0, 0.0, 0.0, 1.0);\n"347"}\n";348if (compile(shaderString))349{350FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;351}352}353354// Test that compiling an ESSL 1.00 shader with multiview support fails.355TEST_F(OVRMultiview2VertexShaderTest, ESSL1Shader)356{357const std::string &shaderString =358"#extension GL_OVR_multiview2 : require\n"359"layout(num_views = 2) in;\n"360"void main()\n"361"{\n"362" if (gl_ViewID_OVR == 0)\n"363" {\n"364" gl_Position = vec4(-1.0, 0.0, 0.0, 1.0);\n"365" }\n"366" else\n"367" {\n"368" gl_Position = vec4(1.0, 0.0, 0.0, 1.0);\n"369" }\n"370"}\n";371if (compile(shaderString))372{373FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;374}375}376377// Test that compiling an ESSL 1.00 shader with an unsupported global layout qualifier fails.378TEST_F(OVRMultiview2VertexShaderTest, ESSL1ShaderUnsupportedGlobalLayoutQualifier)379{380const std::string &shaderString =381"#extension GL_OVR_multiview2 : require\n"382"layout(num_views = 2) in;\n"383"layout(std140) uniform;\n"384"void main()\n"385"{\n"386" if (gl_ViewID_OVR == 0)\n"387" {\n"388" gl_Position = vec4(-1.0, 0.0, 0.0, 1.0);\n"389" }\n"390" else\n"391" {\n"392" gl_Position = vec4(1.0, 0.0, 0.0, 1.0);\n"393" }\n"394"}\n";395if (compile(shaderString))396{397FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;398}399}400401// Test that compiling an ESSL 1.00 vertex shader with an unsupported input storage qualifier fails.402TEST_F(OVRMultiview2VertexShaderTest, ESSL1ShaderUnsupportedInputStorageQualifier)403{404const std::string &shaderString =405"#extension GL_OVR_multiview2 : require\n"406"layout(num_views = 2) in;\n"407"in vec4 pos;\n"408"void main()\n"409"{\n"410" if (gl_ViewID_OVR == 0)\n"411" {\n"412" gl_Position = vec4(-1.0, 0.0, 0.0, 1.0);\n"413" }\n"414" else\n"415" {\n"416" gl_Position = vec4(1.0, 0.0, 0.0, 1.0);\n"417" }\n"418"}\n";419if (compile(shaderString))420{421FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;422}423}424425// Test that compiling an ESSL 1.00 fragment shader with an unsupported input storage qualifier426// fails.427TEST_F(OVRMultiview2FragmentShaderTest, ESSL1ShaderUnsupportedInStorageQualifier)428{429const std::string &shaderString =430"#extension GL_OVR_multiview2 : require\n"431"precision highp float;\n"432"in vec4 color;\n"433"void main()\n"434"{\n"435" if (gl_ViewID_OVR == 0)\n"436" {\n"437" gl_FragColor = color;\n"438" }\n"439" else\n"440" {\n"441" gl_FragColor = color + vec4(1.0, 0.0, 0.0, 1.0);\n"442" }\n"443"}\n";444if (compile(shaderString))445{446FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;447}448}449450// Test that gl_InstanceID gets correctly replaced by InstanceID. gl_InstanceID should only be used451// twice: once to initialize ViewID_OVR and once for InstanceID. The number of occurrences of452// InstanceID in the AST should be the sum of two and the number of occurrences of gl_InstanceID453// before any renaming.454TEST_F(OVRMultiview2VertexShaderTest, GLInstanceIDIsRenamed)455{456const std::string &shaderString =457"#version 300 es\n"458"#extension GL_OVR_multiview2 : require\n"459"layout(num_views = 2) in;\n"460"flat out int myInstance;\n"461"out float myInstanceF;\n"462"out float myInstanceF2;\n"463"void main()\n"464"{\n"465" gl_Position.x = gl_ViewID_OVR == 0u ? 0. : 1.;\n"466" gl_Position.yzw = vec3(0., 0., 1.);\n"467" myInstance = gl_InstanceID;\n"468" myInstanceF = float(gl_InstanceID) + .5;\n"469" myInstanceF2 = float(gl_InstanceID) + .1;\n"470"}\n";471mExtraCompileOptions |= SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW;472compileAssumeSuccess(shaderString);473474SymbolOccurrenceCounterByName glInstanceIDByName(ImmutableString("gl_InstanceID"));475mASTRoot->traverse(&glInstanceIDByName);476EXPECT_EQ(2u, glInstanceIDByName.getNumberOfOccurrences());477478SymbolOccurrenceCounterByQualifier glInstanceIDByQualifier(EvqInstanceID);479mASTRoot->traverse(&glInstanceIDByQualifier);480EXPECT_EQ(2u, glInstanceIDByQualifier.getNumberOfOccurrences());481482SymbolOccurrenceCounterByName instanceIDByName(ImmutableString("InstanceID"));483mASTRoot->traverse(&instanceIDByName);484EXPECT_EQ(5u, instanceIDByName.getNumberOfOccurrences());485}486487// Test that gl_ViewID_OVR gets correctly replaced by ViewID_OVR. gl_ViewID_OVR should not be found488// by either name or qualifier. The number of occurrences of ViewID_OVR in the AST should be the sum489// of two and the number of occurrences of gl_ViewID_OVR before any renaming.490TEST_F(OVRMultiview2VertexShaderTest, GLViewIDIsRenamed)491{492const std::string &shaderString =493"#version 300 es\n"494"#extension GL_OVR_multiview2 : require\n"495"layout(num_views = 2) in;\n"496"flat out uint a;\n"497"void main()\n"498"{\n"499" gl_Position.x = gl_ViewID_OVR == 0u ? 0. : 1.;\n"500" gl_Position.yzw = vec3(0., 0., 1.);\n"501" a = gl_ViewID_OVR == 0u ? (gl_ViewID_OVR+2u) : gl_ViewID_OVR;\n"502"}\n";503mExtraCompileOptions |= SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW;504compileAssumeSuccess(shaderString);505506SymbolOccurrenceCounterByName glViewIDOVRByName(ImmutableString("gl_ViewID_OVR"));507mASTRoot->traverse(&glViewIDOVRByName);508EXPECT_EQ(0u, glViewIDOVRByName.getNumberOfOccurrences());509510SymbolOccurrenceCounterByQualifier glViewIDOVRByQualifier(EvqViewIDOVR);511mASTRoot->traverse(&glViewIDOVRByQualifier);512EXPECT_EQ(0u, glViewIDOVRByQualifier.getNumberOfOccurrences());513514SymbolOccurrenceCounterByNameAndQualifier viewIDByNameAndQualifier(515ImmutableString("ViewID_OVR"), EvqFlatOut);516mASTRoot->traverse(&viewIDByNameAndQualifier);517EXPECT_EQ(6u, viewIDByNameAndQualifier.getNumberOfOccurrences());518}519520// The test checks that ViewID_OVR and InstanceID have the correct initializers based on the521// number of views.522TEST_F(OVRMultiview2VertexShaderOutputCodeTest, ViewIDAndInstanceIDHaveCorrectValues)523{524const std::string &shaderString =525"#version 300 es\n"526"#extension GL_OVR_multiview2 : require\n"527"layout(num_views = 3) in;\n"528"flat out int myInstance;\n"529"void main()\n"530"{\n"531" gl_Position.x = gl_ViewID_OVR == 0u ? 0. : 1.;\n"532" gl_Position.yzw = vec3(0., 0., 1.);\n"533" myInstance = gl_InstanceID;\n"534"}\n";535requestHLSLOutput();536compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW);537538EXPECT_TRUE(foundInAllGLSLCode("ViewID_OVR = (uint(gl_InstanceID) % 3u)"));539EXPECT_TRUE(foundInAllGLSLCode("InstanceID = int((uint(gl_InstanceID) / 3u))"));540541EXPECT_TRUE(foundInHLSLCode("ViewID_OVR = (uint_ctor(gl_InstanceID) % 3)"));542#if defined(ANGLE_ENABLE_HLSL)543EXPECT_FALSE(foundInHLSLCode("_ViewID_OVR = (uint_ctor(gl_InstanceID) % 3)"));544#endif545EXPECT_TRUE(foundInHLSLCode("InstanceID = int_ctor((uint_ctor(gl_InstanceID) / 3))"));546}547548// The test checks that the directive enabling GL_OVR_multiview2 is not outputted if the extension549// is emulated.550TEST_F(OVRMultiview2VertexShaderOutputCodeTest, StrippedOVRMultiviewDirective)551{552const std::string &shaderString =553"#version 300 es\n"554"#extension GL_OVR_multiview2 : require\n"555"layout(num_views = 3) in;\n"556"void main()\n"557"{\n"558"}\n";559// The directive must not be present if any of the multiview emulation options are set.560compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW);561EXPECT_FALSE(foundInESSLCode("GL_OVR_multiview2"));562EXPECT_FALSE(foundInGLSLCode("GL_OVR_multiview2"));563564// The directive should be outputted from the ESSL translator with none of the options being565// set.566compile(shaderString);567EXPECT_TRUE(foundInESSLCode("GL_OVR_multiview2"));568}569570// Test that ViewID_OVR is declared as a flat input variable in an ESSL 3.00 fragment shader.571TEST_F(OVRMultiview2FragmentShaderTest, ViewIDDeclaredAsFlatInput)572{573const std::string &shaderString =574"#version 300 es\n"575"#extension GL_OVR_multiview2 : require\n"576"void main()\n"577"{\n"578"}\n";579mExtraCompileOptions |= SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW;580compileAssumeSuccess(shaderString);581VariableOccursNTimes(mASTRoot, ImmutableString("ViewID_OVR"), EvqFlatIn, 1u);582}583584// Test that GL_OVR_multiview is not defined by the preprocessor for WebGL spec shader;585// Test that GL_OVR_multiview2 is defined by the preprocessor for WebGL spec shader.586TEST_F(OVRMultiview2FragmentShaderTest, PreprocessorOutput)587{588const std::string &shaderString =589"#version 300 es\n"590"#extension GL_OVR_multiview2 : require\n"591"#ifdef GL_OVR_multiview\n"592" #error legacy GL_OVR_multiview support must be forbidden\n"593"#endif\n"594"#ifndef GL_OVR_multiview2\n"595" #error GL_OVR_multiview2 support must be enabled\n"596"#endif\n"597"void main()\n"598"{\n"599"}\n";600compileAssumeSuccess(shaderString);601}602603// Test that ViewID_OVR is declared as a flat output variable in an ESSL 1.00 vertex shader.604TEST_F(OVRMultiview2VertexShaderTest, ViewIDDeclaredAsFlatOutput)605{606const std::string &shaderString =607"#extension GL_OVR_multiview2 : require\n"608"void main()\n"609"{\n"610"}\n";611mExtraCompileOptions |= SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW;612compileAssumeSuccess(shaderString);613VariableOccursNTimes(mASTRoot, ImmutableString("ViewID_OVR"), EvqFlatOut, 2u);614}615616// Test that GL_OVR_multiview is not defined by the preprocessor for WebGL spec shader;617// Test that GL_OVR_multiview2 is defined by the preprocessor for WebGL spec shader.618TEST_F(OVRMultiview2VertexShaderTest, PreprocessorOutput)619{620const std::string &shaderString =621"#version 300 es\n"622"#extension GL_OVR_multiview2 : require\n"623"#ifdef GL_OVR_multiview\n"624" #error legacy GL_OVR_multiview support must be forbidden\n"625"#endif\n"626"#ifndef GL_OVR_multiview2\n"627" #error GL_OVR_multiview2 support must be enabled\n"628"#endif\n"629"void main()\n"630"{\n"631"}\n";632compileAssumeSuccess(shaderString);633}634635// The test checks that the GL_NV_viewport_array2 extension is emitted in a vertex shader if the636// SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER option is set.637TEST_F(OVRMultiview2VertexShaderOutputCodeTest, ViewportArray2IsEmitted)638{639const std::string &shaderString =640"#version 300 es\n"641"#extension GL_OVR_multiview2 : require\n"642"layout(num_views = 3) in;\n"643"void main()\n"644"{\n"645"}\n";646compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW |647SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER);648EXPECT_TRUE(foundInAllGLSLCode("#extension GL_NV_viewport_array2 : require"));649}650651// The test checks that the GL_NV_viewport_array2 extension is not emitted in a vertex shader if the652// OVR_multiview2 extension is not requested in the shader source even if the653// SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER option is set.654TEST_F(OVRMultiview2VertexShaderOutputCodeTest, ViewportArray2IsNotEmitted)655{656const std::string &shaderString =657"#version 300 es\n"658"void main()\n"659"{\n"660"}\n";661compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW |662SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER);663EXPECT_FALSE(foundInGLSLCode("#extension GL_NV_viewport_array2"));664EXPECT_FALSE(foundInESSLCode("#extension GL_NV_viewport_array2"));665}666667// The test checks that the GL_NV_viewport_array2 extension is not emitted in a fragment shader if668// the SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER option is set.669TEST_F(OVRMultiview2FragmentShaderOutputCodeTest, ViewportArray2IsNotEmitted)670{671const std::string &shaderString =672"#version 300 es\n"673"#extension GL_OVR_multiview2 : require\n"674"void main()\n"675"{\n"676"}\n";677compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW |678SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER);679EXPECT_FALSE(foundInGLSLCode("#extension GL_NV_viewport_array2"));680EXPECT_FALSE(foundInESSLCode("#extension GL_NV_viewport_array2"));681}682683// The test checks if OVR_multiview2 is emitted only once and no other684// multiview extensions are emitted.685TEST_F(OVRMultiview2FragmentShaderOutputCodeTest, NativeOvrMultiview2Output)686{687const std::string &shaderString =688"#version 300 es\n"689"#extension GL_OVR_multiview2 : require\n"690"void main()\n"691"{\n"692"}\n";693compile(shaderString);694EXPECT_FALSE(foundInGLSLCode("#extension GL_NV_viewport_array2"));695EXPECT_FALSE(foundInESSLCode("#extension GL_NV_viewport_array2"));696697EXPECT_TRUE(foundInESSLCode("#extension GL_OVR_multiview2"));698EXPECT_TRUE(foundInGLSLCode("#extension GL_OVR_multiview2"));699700// no double extension701std::vector<const char *> notExpectedStrings1 = {"#extension GL_OVR_multiview",702"#extension GL_OVR_multiview"};703EXPECT_FALSE(foundInCodeInOrder(SH_ESSL_OUTPUT, notExpectedStrings1));704EXPECT_FALSE(foundInCodeInOrder(SH_GLSL_COMPATIBILITY_OUTPUT, notExpectedStrings1));705}706707// The test checks that the GL_NV_viewport_array2 extension is not emitted in a compute shader if708// the SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER option is set.709TEST_F(OVRMultiview2ComputeShaderOutputCodeTest, ViewportArray2IsNotEmitted)710{711const std::string &shaderString =712R"(#version 310 es713#extension GL_OVR_multiview2 : require714void main()715{716})";717compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW |718SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER);719EXPECT_FALSE(foundInGLSLCode("#extension GL_NV_viewport_array2"));720EXPECT_FALSE(foundInESSLCode("#extension GL_NV_viewport_array2"));721}722723// The test checks that the viewport index is selected after the initialization of ViewID_OVR for724// GLSL and ESSL ouputs.725TEST_F(OVRMultiview2VertexShaderOutputCodeTest, GlViewportIndexIsSet)726{727const std::string &shaderString =728"#version 300 es\n"729"#extension GL_OVR_multiview2 : require\n"730"layout(num_views = 3) in;\n"731"void main()\n"732"{\n"733"}\n";734compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW |735SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER);736737std::vector<const char *> expectedStrings = {"ViewID_OVR = (uint(gl_InstanceID) % 3u)",738"gl_ViewportIndex = int(ViewID_OVR)"};739EXPECT_TRUE(foundInCodeInOrder(SH_ESSL_OUTPUT, expectedStrings));740EXPECT_TRUE(foundInCodeInOrder(SH_GLSL_COMPATIBILITY_OUTPUT, expectedStrings));741}742743// The test checks that the layer is selected after the initialization of ViewID_OVR for744// GLSL and ESSL ouputs.745TEST_F(OVRMultiview2VertexShaderOutputCodeTest, GlLayerIsSet)746{747const std::string &shaderString =748"#version 300 es\n"749"#extension GL_OVR_multiview2 : require\n"750"layout(num_views = 3) in;\n"751"void main()\n"752"{\n"753"}\n";754compile(shaderString, SH_INITIALIZE_BUILTINS_FOR_INSTANCED_MULTIVIEW |755SH_SELECT_VIEW_IN_NV_GLSL_VERTEX_SHADER);756757std::vector<const char *> expectedStrings = {758"ViewID_OVR = (uint(gl_InstanceID) % 3u)",759"gl_Layer = (int(ViewID_OVR) + multiviewBaseViewLayerIndex)"};760EXPECT_TRUE(foundInCodeInOrder(SH_ESSL_OUTPUT, expectedStrings));761EXPECT_TRUE(foundInCodeInOrder(SH_GLSL_COMPATIBILITY_OUTPUT, expectedStrings));762}763764// Test that the OVR_multiview2 without emulation emits OVR_multiview2 output.765// It also tests that the GL_OVR_multiview2 is emitted only once and no other766// multiview extensions are emitted.767TEST_F(OVRMultiview2VertexShaderOutputCodeTest, NativeOvrMultiview2Output)768{769const std::string &shaderString =770"#version 300 es\n"771"#extension GL_OVR_multiview2 : require\n"772"layout(num_views = 3) in;\n"773"void main()\n"774"{\n"775"}\n";776compile(shaderString);777778std::vector<const char *> expectedStrings = {"#extension GL_OVR_multiview2",779"layout(num_views"};780EXPECT_TRUE(foundInCodeInOrder(SH_ESSL_OUTPUT, expectedStrings));781EXPECT_TRUE(foundInCodeInOrder(SH_GLSL_COMPATIBILITY_OUTPUT, expectedStrings));782783EXPECT_FALSE(foundInGLSLCode("#extension GL_NV_viewport_array2"));784EXPECT_FALSE(foundInESSLCode("#extension GL_NV_viewport_array2"));785786EXPECT_FALSE(foundInGLSLCode("gl_ViewportIndex"));787EXPECT_FALSE(foundInESSLCode("gl_ViewportIndex"));788789// no double extension790std::vector<const char *> notExpectedStrings1 = {"#extension GL_OVR_multiview",791"#extension GL_OVR_multiview"};792EXPECT_FALSE(foundInCodeInOrder(SH_ESSL_OUTPUT, notExpectedStrings1));793EXPECT_FALSE(foundInCodeInOrder(SH_GLSL_COMPATIBILITY_OUTPUT, notExpectedStrings1));794795// no double num_views796std::vector<const char *> notExpectedStrings2 = {"layout(num_views", "layout(num_views"};797EXPECT_FALSE(foundInCodeInOrder(SH_ESSL_OUTPUT, notExpectedStrings2));798EXPECT_FALSE(foundInCodeInOrder(SH_GLSL_COMPATIBILITY_OUTPUT, notExpectedStrings2));799}800801} // namespace802803804