Browse Source

Implement tests for compile/link/flat

pull/576/head
Vladislav Oleshko 4 years ago
parent
commit
6fe87cc7bf
  1. 109
      src/Magnum/GL/Test/AbstractShaderProgramGLTest.cpp
  2. 68
      src/Magnum/GL/Test/ShaderGLTest.cpp
  3. 2
      src/Magnum/Shaders/FlatGL.cpp
  4. 91
      src/Magnum/Shaders/Test/FlatGLTest.cpp

109
src/Magnum/GL/Test/AbstractShaderProgramGLTest.cpp

@ -27,6 +27,7 @@
#include <Corrade/Containers/Reference.h>
#include <Corrade/Containers/StringStl.h> /** @todo remove when Shader is <string>-free */
#include <Corrade/TestSuite/Compare/Container.h>
#include <Corrade/TestSuite/Compare/String.h>
#include <Corrade/Utility/DebugStl.h>
#include <Corrade/Utility/Resource.h>
@ -68,8 +69,11 @@ struct AbstractShaderProgramGLTest: OpenGLTester {
#ifndef MAGNUM_TARGET_GLES
void createMultipleOutputsIndexed();
#endif
void createAsync();
void linkFailure();
void linkFailureAsync();
void uniformNotFound();
void uniform();
@ -103,12 +107,14 @@ AbstractShaderProgramGLTest::AbstractShaderProgramGLTest() {
#endif
&AbstractShaderProgramGLTest::create,
&AbstractShaderProgramGLTest::createAsync,
&AbstractShaderProgramGLTest::createMultipleOutputs,
#ifndef MAGNUM_TARGET_GLES
&AbstractShaderProgramGLTest::createMultipleOutputsIndexed,
#endif
&AbstractShaderProgramGLTest::linkFailure,
&AbstractShaderProgramGLTest::linkFailureAsync,
&AbstractShaderProgramGLTest::uniformNotFound,
&AbstractShaderProgramGLTest::uniform,
@ -205,6 +211,8 @@ struct MyPublicShader: AbstractShaderProgram {
using AbstractShaderProgram::bindFragmentDataLocation;
#endif
using AbstractShaderProgram::link;
using AbstractShaderProgram::submitLink;
using AbstractShaderProgram::checkLink;
using AbstractShaderProgram::uniformLocation;
#ifndef MAGNUM_TARGET_GLES2
using AbstractShaderProgram::uniformBlockIndex;
@ -257,6 +265,74 @@ void AbstractShaderProgramGLTest::create() {
MAGNUM_VERIFY_NO_GL_ERROR();
CORRADE_VERIFY(linked);
// TODO: decide on this.
//CORRADE_VERIFY(program.isLinkFinished());
{
#if defined(CORRADE_TARGET_APPLE) && !defined(MAGNUM_TARGET_GLES)
CORRADE_EXPECT_FAIL("macOS drivers need insane amount of state to validate properly.");
#endif
CORRADE_VERIFY(valid);
}
const Int matrixUniform = program.uniformLocation("matrix");
const Int multiplierUniform = program.uniformLocation("multiplier");
const Int colorUniform = program.uniformLocation("color");
const Int additionsUniform = program.uniformLocation("additions");
MAGNUM_VERIFY_NO_GL_ERROR();
CORRADE_VERIFY(matrixUniform >= 0);
CORRADE_VERIFY(multiplierUniform >= 0);
CORRADE_VERIFY(colorUniform >= 0);
CORRADE_VERIFY(additionsUniform >= 0);
}
void AbstractShaderProgramGLTest::createAsync() {
Utility::Resource rs("AbstractShaderProgramGLTest");
Shader vert(
#ifndef MAGNUM_TARGET_GLES
#ifndef CORRADE_TARGET_APPLE
Version::GL210
#else
Version::GL310
#endif
#else
Version::GLES200
#endif
, Shader::Type::Vertex);
vert.addSource(rs.getString("MyShader.vert"));
const bool vertCompiled = vert.compile();
Shader frag(
#ifndef MAGNUM_TARGET_GLES
#ifndef CORRADE_TARGET_APPLE
Version::GL210
#else
Version::GL310
#endif
#else
Version::GLES200
#endif
, Shader::Type::Fragment);
frag.addSource(rs.getString("MyShader.frag"));
const bool fragCompiled = frag.compile();
MAGNUM_VERIFY_NO_GL_ERROR();
CORRADE_VERIFY(vertCompiled);
CORRADE_VERIFY(fragCompiled);
MyPublicShader program;
program.attachShaders({vert, frag});
MAGNUM_VERIFY_NO_GL_ERROR();
program.bindAttributeLocation(0, "position");
program.submitLink();
CORRADE_VERIFY(program.checkLink());
const bool valid = program.validate().first;
MAGNUM_VERIFY_NO_GL_ERROR();
{
#if defined(CORRADE_TARGET_APPLE) && !defined(MAGNUM_TARGET_GLES)
CORRADE_EXPECT_FAIL("macOS drivers need insane amount of state to validate properly.");
@ -412,6 +488,39 @@ void AbstractShaderProgramGLTest::linkFailure() {
CORRADE_VERIFY(!program.link());
}
void AbstractShaderProgramGLTest::linkFailureAsync() {
Shader shader(
#ifndef MAGNUM_TARGET_GLES
#ifndef CORRADE_TARGET_APPLE
Version::GL210
#else
Version::GL310
#endif
#else
Version::GLES200
#endif
, Shader::Type::Fragment);
shader.addSource("[fu] bleh error #:! stuff\n");
{
Error redirectError{nullptr};
CORRADE_VERIFY(!shader.compile());
}
MyPublicShader program;
program.attachShaders({shader});
std::ostringstream out;
Error redirectError{&out};
program.submitLink();
CORRADE_VERIFY(out.str().empty());
CORRADE_VERIFY(!program.checkLink());
CORRADE_COMPARE_AS(out.str(), "GL::AbstractShaderProgram::link(): linking failed with the following message:",
TestSuite::Compare::StringHasPrefix);
}
void AbstractShaderProgramGLTest::uniformNotFound() {
MyPublicShader program;

68
src/Magnum/GL/Test/ShaderGLTest.cpp

@ -23,7 +23,9 @@
DEALINGS IN THE SOFTWARE.
*/
#include <sstream>
#include <Corrade/Containers/StringStl.h> /** @todo remove once Shader is <string>-free */
#include <Corrade/TestSuite/Compare/String.h>
#include <Corrade/Utility/DebugStl.h>
#include <Corrade/Utility/Path.h>
@ -40,6 +42,18 @@
namespace Magnum { namespace GL { namespace Test { namespace {
constexpr GL::Version shaderCompileGLVersion =
#ifndef MAGNUM_TARGET_GLES
#ifndef CORRADE_TARGET_APPLE
Version::GL210
#else
Version::GL310
#endif
;
#else
Version::GLES200;
#endif
struct ShaderGLTest: OpenGLTester {
explicit ShaderGLTest();
@ -55,6 +69,9 @@ struct ShaderGLTest: OpenGLTester {
void addSourceNoVersion();
void addFile();
void compile();
void compileFailure();
void compileAsync();
void compileAsyncFailure();
void compileUtf8();
void compileNoVersion();
};
@ -72,6 +89,9 @@ ShaderGLTest::ShaderGLTest() {
&ShaderGLTest::addSourceNoVersion,
&ShaderGLTest::addFile,
&ShaderGLTest::compile,
&ShaderGLTest::compileFailure,
&ShaderGLTest::compileAsync,
&ShaderGLTest::compileAsyncFailure,
&ShaderGLTest::compileUtf8,
&ShaderGLTest::compileNoVersion});
}
@ -262,25 +282,41 @@ void ShaderGLTest::addFile() {
}
void ShaderGLTest::compile() {
#ifndef MAGNUM_TARGET_GLES
constexpr Version v =
#ifndef CORRADE_TARGET_APPLE
Version::GL210
#else
Version::GL310
#endif
;
#else
constexpr Version v = Version::GLES200;
#endif
Shader shader(v, Shader::Type::Fragment);
Shader shader(shaderCompileGLVersion, Shader::Type::Fragment);
shader.addSource("void main() {}\n");
CORRADE_VERIFY(shader.compile());
CORRADE_VERIFY(shader.isCompileFinished());
}
void ShaderGLTest::compileFailure() {
Shader shader(shaderCompileGLVersion, Shader::Type::Fragment);
shader.addSource("[fu] bleh error #:! stuff\n");
CORRADE_VERIFY(!shader.compile());
CORRADE_VERIFY(shader.isCompileFinished());
}
void ShaderGLTest::compileAsync() {
Shader shader(shaderCompileGLVersion, Shader::Type::Fragment);
shader.addSource("void main() {}\n");
shader.submitCompile();
CORRADE_VERIFY(shader.checkCompile());
}
void ShaderGLTest::compileAsyncFailure() {
Shader shader(shaderCompileGLVersion, Shader::Type::Fragment);
shader.addSource("[fu] bleh error #:! stuff\n");
shader.submitCompile();
std::ostringstream out;
Error redirectError{&out};
CORRADE_VERIFY(out.str().empty());
Shader shader2(v, Shader::Type::Fragment);
shader2.addSource("[fu] bleh error #:! stuff\n");
CORRADE_VERIFY(!shader2.compile());
CORRADE_VERIFY(!shader.checkCompile());
CORRADE_COMPARE_AS(out.str(), "GL::Shader::compile(): compilation of fragment shader failed with the following message:",
TestSuite::Compare::StringHasPrefix);
}
void ShaderGLTest::compileUtf8() {

2
src/Magnum/Shaders/FlatGL.cpp

@ -241,9 +241,9 @@ template<UnsignedInt dimensions> FlatGL<dimensions>::FlatGL(CompileState&& cs)
: FlatGL{static_cast<FlatGL&&>(std::move(cs))} {
if (id() == 0) return;
CORRADE_INTERNAL_ASSERT_OUTPUT(checkLink());
CORRADE_INTERNAL_ASSERT_OUTPUT(cs._vert.checkCompile());
CORRADE_INTERNAL_ASSERT_OUTPUT(cs._frag.checkCompile());
CORRADE_INTERNAL_ASSERT_OUTPUT(checkLink());
const GL::Context& context = GL::Context::current();
const GL::Version version = cs._version;

91
src/Magnum/Shaders/Test/FlatGLTest.cpp

@ -83,8 +83,10 @@ struct FlatGLTest: GL::OpenGLTester {
explicit FlatGLTest();
template<UnsignedInt dimensions> void construct();
template<UnsignedInt dimensions> void constructAsync();
#ifndef MAGNUM_TARGET_GLES2
template<UnsignedInt dimensions> void constructUniformBuffers();
template<UnsignedInt dimensions> void constructUniformBuffersAsync();
#endif
template<UnsignedInt dimensions> void constructMove();
@ -597,13 +599,18 @@ constexpr struct {
FlatGLTest::FlatGLTest() {
addInstancedTests<FlatGLTest>({
&FlatGLTest::construct<2>,
&FlatGLTest::construct<3>},
&FlatGLTest::construct<3>,
&FlatGLTest::constructAsync<2>,
&FlatGLTest::constructAsync<3>},
Containers::arraySize(ConstructData));
#ifndef MAGNUM_TARGET_GLES2
addInstancedTests<FlatGLTest>({
&FlatGLTest::constructUniformBuffers<2>,
&FlatGLTest::constructUniformBuffers<3>},
&FlatGLTest::constructUniformBuffers<3>,
&FlatGLTest::constructUniformBuffersAsync<2>,
&FlatGLTest::constructUniformBuffersAsync<3>},
Containers::arraySize(ConstructUniformBuffersData));
#endif
@ -853,6 +860,37 @@ template<UnsignedInt dimensions> void FlatGLTest::construct() {
MAGNUM_VERIFY_NO_GL_ERROR();
}
template<UnsignedInt dimensions> void FlatGLTest::constructAsync() {
setTestCaseTemplateName(Utility::format("{}", dimensions));
auto&& data = ConstructData[testCaseInstanceId()];
setTestCaseDescription(data.name);
#ifndef MAGNUM_TARGET_GLES
if((data.flags & FlatGL2D::Flag::ObjectId) && !GL::Context::current().isExtensionSupported<GL::Extensions::EXT::gpu_shader4>())
CORRADE_SKIP(GL::Extensions::EXT::gpu_shader4::string() << "is not supported.");
if((data.flags & FlatGL2D::Flag::TextureArrays) && !GL::Context::current().isExtensionSupported<GL::Extensions::EXT::texture_array>())
CORRADE_SKIP(GL::Extensions::EXT::texture_array::string() << "is not supported.");
#endif
auto compileState = FlatGL<dimensions>::compile(data.flags);
CORRADE_COMPARE(compileState.flags(), data.flags);
FlatGL<dimensions> shader{std::move(compileState)};
CORRADE_COMPARE(shader.flags(), data.flags);
// TODO: decide on this.
// CORRADE_VERIFY(shader.isLinkFinished());
CORRADE_VERIFY(shader.id());
{
#if defined(CORRADE_TARGET_APPLE) && !defined(MAGNUM_TARGET_GLES)
CORRADE_EXPECT_FAIL("macOS drivers need insane amount of state to validate properly.");
#endif
CORRADE_VERIFY(shader.validate().first);
}
MAGNUM_VERIFY_NO_GL_ERROR();
}
#ifndef MAGNUM_TARGET_GLES2
template<UnsignedInt dimensions> void FlatGLTest::constructUniformBuffers() {
setTestCaseTemplateName(Utility::format("{}", dimensions));
@ -896,6 +934,55 @@ template<UnsignedInt dimensions> void FlatGLTest::constructUniformBuffers() {
MAGNUM_VERIFY_NO_GL_ERROR();
}
template<UnsignedInt dimensions> void FlatGLTest::constructUniformBuffersAsync() {
setTestCaseTemplateName(Utility::format("{}", dimensions));
auto&& data = ConstructUniformBuffersData[testCaseInstanceId()];
setTestCaseDescription(data.name);
#ifndef MAGNUM_TARGET_GLES
if((data.flags & FlatGL2D::Flag::UniformBuffers) && !GL::Context::current().isExtensionSupported<GL::Extensions::ARB::uniform_buffer_object>())
CORRADE_SKIP(GL::Extensions::ARB::uniform_buffer_object::string() << "is not supported.");
if((data.flags & FlatGL2D::Flag::ObjectId) && !GL::Context::current().isExtensionSupported<GL::Extensions::EXT::gpu_shader4>())
CORRADE_SKIP(GL::Extensions::EXT::gpu_shader4::string() << "is not supported.");
if((data.flags & FlatGL2D::Flag::TextureArrays) && !GL::Context::current().isExtensionSupported<GL::Extensions::EXT::texture_array>())
CORRADE_SKIP(GL::Extensions::EXT::texture_array::string() << "is not supported.");
#endif
if(data.flags >= FlatGL2D::Flag::MultiDraw) {
#ifndef MAGNUM_TARGET_GLES
if(!GL::Context::current().isExtensionSupported<GL::Extensions::ARB::shader_draw_parameters>())
CORRADE_SKIP(GL::Extensions::ARB::shader_draw_parameters::string() << "is not supported.");
#elif !defined(MAGNUM_TARGET_WEBGL)
if(!GL::Context::current().isExtensionSupported<GL::Extensions::ANGLE::multi_draw>())
CORRADE_SKIP(GL::Extensions::ANGLE::multi_draw::string() << "is not supported.");
#else
if(!GL::Context::current().isExtensionSupported<GL::Extensions::WEBGL::multi_draw>())
CORRADE_SKIP(GL::Extensions::WEBGL::multi_draw::string() << "is not supported.");
#endif
}
auto compileState = FlatGL<dimensions>::compile(data.flags, data.materialCount, data.drawCount);
CORRADE_COMPARE(compileState.flags(), data.flags);
CORRADE_COMPARE(compileState.materialCount(), data.materialCount);
CORRADE_COMPARE(compileState.drawCount(), data.drawCount);
FlatGL<dimensions> shader{std::move(compileState)};
CORRADE_COMPARE(shader.flags(), data.flags);
CORRADE_COMPARE(shader.materialCount(), data.materialCount);
CORRADE_COMPARE(shader.drawCount(), data.drawCount);
CORRADE_VERIFY(shader.id());
{
#if defined(CORRADE_TARGET_APPLE) && !defined(MAGNUM_TARGET_GLES)
CORRADE_EXPECT_FAIL("macOS drivers need insane amount of state to validate properly.");
#endif
CORRADE_VERIFY(shader.validate().first);
}
MAGNUM_VERIFY_NO_GL_ERROR();
}
#endif
template<UnsignedInt dimensions> void FlatGLTest::constructMove() {

Loading…
Cancel
Save