Hash :
0461d8d4
Author :
Date :
2021-06-23T23:20:33
Vulkan: SPIR-V Gen: texture and image built-ins GLSL contains a large number of built-in texture* and image* functions, but these map to only a handful of SPIR-V instructions. The bulk of the work to map these is to extract the arguments from the built-ins based on their ordinal position. Bug: angleproject:4889 Change-Id: I760d986bd9171ddde35f9f046c549ca53252df17 Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/2992980 Reviewed-by: Shahbaz Youssefi <syoussefi@chromium.org> Reviewed-by: Jamie Madill <jmadill@chromium.org> Commit-Queue: Shahbaz Youssefi <syoussefi@chromium.org>
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182
//
// Copyright 2017 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.
//
// SamplerTest.cpp : Tests for samplers.
#include "test_utils/ANGLETest.h"
#include "test_utils/gl_raii.h"
namespace angle
{
class SamplersTest : public ANGLETest
{
protected:
SamplersTest() {}
// Sets a value for GL_TEXTURE_MAX_ANISOTROPY_EXT and expects it to fail.
void validateInvalidAnisotropy(GLSampler &sampler, float invalidValue)
{
glSamplerParameterf(sampler, GL_TEXTURE_MAX_ANISOTROPY_EXT, invalidValue);
EXPECT_GL_ERROR(GL_INVALID_VALUE);
}
// Sets a value for GL_TEXTURE_MAX_ANISOTROPY_EXT and expects it to work.
void validateValidAnisotropy(GLSampler &sampler, float validValue)
{
glSamplerParameterf(sampler, GL_TEXTURE_MAX_ANISOTROPY_EXT, validValue);
EXPECT_GL_NO_ERROR();
GLfloat valueToVerify = 0.0f;
glGetSamplerParameterfv(sampler, GL_TEXTURE_MAX_ANISOTROPY_EXT, &valueToVerify);
ASSERT_EQ(valueToVerify, validValue);
}
};
class SamplersTest31 : public SamplersTest
{};
// Verify that samplerParameterf supports TEXTURE_MAX_ANISOTROPY_EXT valid values.
TEST_P(SamplersTest, ValidTextureSamplerMaxAnisotropyExt)
{
// http://anglebug.com/4092
ANGLE_SKIP_TEST_IF(isSwiftshader());
GLSampler sampler;
// Exact min
validateValidAnisotropy(sampler, 1.0f);
GLfloat maxValue = 0.0f;
glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &maxValue);
// Max value
validateValidAnisotropy(sampler, maxValue - 1);
// In-between
GLfloat between = (1.0f + maxValue) / 2;
validateValidAnisotropy(sampler, between);
}
// Verify an error is thrown if we try to go under the minimum value for
// GL_TEXTURE_MAX_ANISOTROPY_EXT
TEST_P(SamplersTest, InvalidUnderTextureSamplerMaxAnisotropyExt)
{
// http://anglebug.com/4092
ANGLE_SKIP_TEST_IF(isSwiftshader());
GLSampler sampler;
// Under min
validateInvalidAnisotropy(sampler, 0.0f);
}
// Verify an error is thrown if we try to go over the max value for
// GL_TEXTURE_MAX_ANISOTROPY_EXT
TEST_P(SamplersTest, InvalidOverTextureSamplerMaxAnisotropyExt)
{
// http://anglebug.com/4092
ANGLE_SKIP_TEST_IF(isSwiftshader());
GLSampler sampler;
GLfloat maxValue = 0.0f;
glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &maxValue);
maxValue += 1;
validateInvalidAnisotropy(sampler, maxValue);
}
// Test that updating a sampler uniform in a program behaves correctly.
TEST_P(SamplersTest31, SampleTextureAThenTextureB)
{
ANGLE_SKIP_TEST_IF(!IsVulkan());
constexpr int kWidth = 2;
constexpr int kHeight = 2;
const GLchar *vertString = R"(#version 310 es
precision highp float;
in vec2 a_position;
out vec2 texCoord;
void main()
{
gl_Position = vec4(a_position, 0, 1);
texCoord = a_position * 0.5 + vec2(0.5);
})";
const GLchar *fragString = R"(#version 310 es
precision highp float;
in vec2 texCoord;
uniform sampler2D tex;
out vec4 my_FragColor;
void main()
{
my_FragColor = texture(tex, texCoord);
})";
std::array<GLColor, kWidth *kHeight> redColor = {
{GLColor::red, GLColor::red, GLColor::red, GLColor::red}};
std::array<GLColor, kWidth *kHeight> greenColor = {
{GLColor::green, GLColor::green, GLColor::green, GLColor::green}};
// Create a red texture and bind to texture unit 0
GLTexture redTex;
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, redTex);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, kWidth, kHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE,
redColor.data());
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
ASSERT_GL_NO_ERROR();
// Create a green texture and bind to texture unit 1
GLTexture greenTex;
glActiveTexture(GL_TEXTURE1);
glBindTexture(GL_TEXTURE_2D, greenTex);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, kWidth, kHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE,
greenColor.data());
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glActiveTexture(GL_TEXTURE0);
ASSERT_GL_NO_ERROR();
GLProgram program;
program.makeRaster(vertString, fragString);
ASSERT_NE(0u, program.get());
glUseProgram(program);
GLint location = glGetUniformLocation(program, "tex");
ASSERT_NE(location, -1);
ASSERT_GL_NO_ERROR();
// Draw red
glUniform1i(location, 0);
ASSERT_GL_NO_ERROR();
drawQuad(program, "a_position", 0.5f);
ASSERT_GL_NO_ERROR();
glEnable(GL_BLEND);
glBlendEquation(GL_FUNC_ADD);
glBlendFunc(GL_ONE, GL_ONE);
// Draw green
glUniform1i(location, 1);
ASSERT_GL_NO_ERROR();
drawQuad(program, "a_position", 0.5f);
ASSERT_GL_NO_ERROR();
// Draw red
glUniform1i(location, 0);
ASSERT_GL_NO_ERROR();
drawQuad(program, "a_position", 0.5f);
ASSERT_GL_NO_ERROR();
EXPECT_PIXEL_RECT_EQ(0, 0, kWidth, kHeight, GLColor::yellow);
}
// Samplers are only supported on ES3.
GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(SamplersTest);
ANGLE_INSTANTIATE_TEST_ES3(SamplersTest);
ANGLE_INSTANTIATE_TEST_ES31_AND(SamplersTest31, WithDirectSPIRVGeneration(ES31_VULKAN()));
} // namespace angle