Commit 34cbc544 by Jonah Ryan-Davis Committed by Commit Bot

Use ANGLE's gpu_info_util libraries for test expectations

3. Remove gpu_info.h and gpu_info.cc and use ANGLE's own gpu_info_util to to gather device info instead. - Support collecting info for and parsing expectations of specific Android devices such as Nexus 5X and Pixel 2. - Change parser behavior to more closely follow: bit.ly/chromium-test-list-format Bug: angleproject:2677 Change-Id: I4c0b9342142b718e884484a6bcaac2dff3ac575a Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/1553822 Commit-Queue: Jonah Ryan-Davis <jonahr@google.com> Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org>
parent 893ccb48
......@@ -37,6 +37,8 @@ std::string VendorName(VendorID vendor)
return "Vivante";
case kVendorID_VeriSilicon:
return "VeriSilicon";
case kVendorID_VMWare:
return "VMWare";
case kVendorID_Kazan:
return "Kazan";
default:
......@@ -132,6 +134,11 @@ bool IsVeriSilicon(VendorID vendorId)
return vendorId == kVendorID_VeriSilicon;
}
bool IsVMWare(VendorID vendorId)
{
return vendorId == kVendorID_VMWare;
}
bool IsVivante(VendorID vendorId)
{
return vendorId == kVendorID_Vivante;
......
......@@ -93,6 +93,7 @@ constexpr VendorID kVendorID_ImgTec = 0x1010;
constexpr VendorID kVendorID_Intel = 0x8086;
constexpr VendorID kVendorID_NVIDIA = 0x10DE;
constexpr VendorID kVendorID_Qualcomm = 0x5143;
constexpr VendorID kVendorID_VMWare = 0x15ad;
// Known non-PCI (i.e. Khronos-registered) vendor IDs
constexpr VendorID kVendorID_Vivante = 0x10001;
......@@ -108,6 +109,7 @@ bool IsKazan(VendorID vendorId);
bool IsNVIDIA(VendorID vendorId);
bool IsQualcomm(VendorID vendorId);
bool IsVeriSilicon(VendorID vendorId);
bool IsVMWare(VendorID vendorId);
bool IsVivante(VendorID vendorId);
// Dumps the system info to stdout.
......
......@@ -98,6 +98,37 @@ angle_test("angle_unittests_helper") {
]
}
test_expectations_sources = [
"test_expectations/GPUTestConfig.cpp",
"test_expectations/GPUTestConfig.h",
"test_expectations/GPUTestExpectationsParser.cpp",
"test_expectations/GPUTestExpectationsParser.h",
]
if (is_mac) {
test_expectations_sources_mac = [
"test_expectations/GPUTestConfig_mac.mm",
"test_expectations/GPUTestConfig_mac.h",
]
}
config("angle_test_expectations_config") {
include_dirs = [ "${angle_root}:angle_common" ]
}
angle_static_library("angle_test_expectations") {
public_configs += [ ":angle_test_expectations_config" ]
public_deps = [
"${angle_root}:angle_common",
"${angle_root}:angle_gpu_info_util",
"${angle_root}:angle_util",
]
sources = test_expectations_sources
if (is_mac) {
sources += test_expectations_sources_mac
libs = [ "Cocoa.framework" ]
}
}
angle_test("angle_unittests") {
sources = angle_unittests_sources
......@@ -108,6 +139,7 @@ angle_test("angle_unittests") {
deps = googletest_deps + [
"${angle_root}:libANGLE",
":angle_test_expectations",
"${angle_root}:preprocessor",
"${angle_root}:translator",
"${angle_root}:libfeature_support${angle_libs_suffix}",
......@@ -152,6 +184,7 @@ if (is_win || is_linux || is_mac || is_android || is_fuchsia) {
deps = [
":angle_end2end_tests_main",
":angle_test_expectations",
"${angle_root}:angle_gpu_info_util",
"${angle_root}:angle_image_util",
"${angle_root}:angle_util",
......@@ -659,38 +692,17 @@ if (build_angle_deqp_tests && !is_fuchsia) {
}
}
config("angle_deqp_test_expectations_config") {
include_dirs = [ "${angle_root}:angle_common" ]
}
angle_static_library("angle_deqp_test_expectations") {
public_configs += [ ":angle_deqp_test_expectations_config" ]
public_deps = [
"${angle_root}:angle_common",
"${angle_root}:angle_util",
]
sources = deqp_test_expectations_sources
if (is_mac) {
sources += deqp_test_expectations_sources_mac
libs = [ "Cocoa.framework" ]
}
}
angle_source_set("angle_deqp_gtest_support") {
testonly = true
public_deps = [
":angle_deqp_test_expectations",
":angle_deqp_tests_main",
":angle_test_expectations",
"${angle_root}:angle_common",
"${angle_root}:angle_util",
]
libs = []
if (!is_android) {
public_deps += [ "${angle_root}:angle_gpu_info_util" ]
}
}
api_names = [
......
......@@ -139,6 +139,7 @@ angle_end2end_tests_sources = [
"egl_tests/EGLSurfacelessContextTest.cpp",
"egl_tests/EGLSurfaceTest.cpp",
"egl_tests/EGLSyncTest.cpp",
"test_expectations/GPUTestExpectationsTest.cpp",
"test_utils/ANGLETest.cpp",
"test_utils/ANGLETest.h",
"test_utils/MultiviewTest.cpp",
......
......@@ -102,6 +102,7 @@ angle_unittests_sources = [
"../tests/compiler_tests/VectorizeVectorScalarArithmetic_test.cpp",
"../tests/compiler_tests/WEBGL_multiview_test.cpp",
"../tests/compiler_tests/WorkGroupSize_test.cpp",
"../tests/test_expectations/GPUTestExpectationsParser_unittest.cpp",
"../tests/preprocessor_tests/char_test.cpp",
"../tests/preprocessor_tests/comment_test.cpp",
"../tests/preprocessor_tests/define_test.cpp",
......
......@@ -1143,15 +1143,3 @@ deqp_libtester_sources_android = [
"$_deqp_path/framework/platform/android/tcuAndroidInternals.cpp",
"$_deqp_path/framework/platform/android/tcuAndroidInternals.hpp",
]
deqp_test_expectations_sources = [
"test_expectations/GPUInfo.cpp",
"test_expectations/GPUInfo.h",
"test_expectations/GPUTestConfig.cpp",
"test_expectations/GPUTestConfig.h",
"test_expectations/GPUTestExpectationsParser.cpp",
"test_expectations/GPUTestExpectationsParser.h",
]
deqp_test_expectations_sources_mac = [
"test_expectations/GPUTestConfig_mac.mm",
"test_expectations/GPUTestConfig_mac.h",
]
......@@ -20,6 +20,7 @@
#include "common/platform.h"
#include "common/string_utils.h"
#include "platform/Platform.h"
#include "tests/test_expectations/GPUTestConfig.h"
#include "tests/test_expectations/GPUTestExpectationsParser.h"
#include "util/system_utils.h"
......@@ -218,7 +219,6 @@ class dEQPCaseList
private:
std::vector<CaseInfo> mCaseInfoList;
angle::GPUTestExpectationsParser mTestExpectationsParser;
angle::GPUTestBotConfig mTestConfig;
size_t mTestModuleIndex;
bool mInitialized;
};
......@@ -252,10 +252,20 @@ void dEQPCaseList::initialize()
Die();
}
if (!mTestExpectationsParser.LoadTestExpectationsFromFile(testExpectationsPath.value()))
angle::GPUTestConfig::API api = GetDefaultAPIInfo()->second;
// Set the API from the command line, or using the default platform API.
if (gInitAPI)
{
api = gInitAPI->second;
}
angle::GPUTestConfig testConfig = angle::GPUTestConfig(api);
if (!mTestExpectationsParser.loadTestExpectationsFromFile(testConfig,
testExpectationsPath.value()))
{
std::stringstream errorMsgStream;
for (const auto &message : mTestExpectationsParser.GetErrorMessages())
for (const auto &message : mTestExpectationsParser.getErrorMessages())
{
errorMsgStream << std::endl << " " << message;
}
......@@ -264,22 +274,6 @@ void dEQPCaseList::initialize()
Die();
}
if (!mTestConfig.LoadCurrentConfig(nullptr))
{
std::cerr << "Failed to load test configuration." << std::endl;
Die();
}
// Set the API from the command line, or using the default platform API.
if (gInitAPI)
{
mTestConfig.set_api(gInitAPI->second);
}
else
{
mTestConfig.set_api(GetDefaultAPIInfo()->second);
}
std::ifstream caseListStream(caseListPath.value());
if (caseListStream.fail())
{
......@@ -299,7 +293,7 @@ void dEQPCaseList::initialize()
if (gTestName.empty())
continue;
int expectation = mTestExpectationsParser.GetTestExpectation(dEQPName, mTestConfig);
int expectation = mTestExpectationsParser.getTestExpectation(dEQPName);
if (expectation != angle::GPUTestExpectationsParser::kGpuTestSkip)
{
mCaseInfoList.push_back(CaseInfo(dEQPName, gTestName, expectation));
......
......@@ -6,27 +6,33 @@
// format is:
// {BUG#} {MODIFIERS} : {TEST_NAME} = {PASS,FAIL,FLAKY,TIMEOUT,SKIP}
//
// MODIFIERS can be a combination of the below list:
// WIN XP VISTA WIN7 MAC LEOPARD SNOWLEOPARD LION LINUX CHROMEOS MOUNTAINLION
// MAVERICKS
// MODIFIERS can be a combination of the below list, combined with a logical AND:
// WIN XP VISTA WIN7 WIN8 WIN10
// MAC LEOPARD SNOWLEOPARD LION MOUNTAINLION MAVERICKS YOSEMITE ELCAPITAN SIERRA HIGHSIERRA MOJAVE
// LINUX CHROMEOS ANDROID
// NVIDIA AMD INTEL
// 0xabcd - GPU PCI device ID. Specifying a PCI id requires a vendor.
// DEBUG RELEASE
// TODO(jmadill): Add ANGLE Renderer selection modifiers
// D3D9 D3D11 OPENGL GLES VULKAN
// NEXUS5X PIXEL2
// QUADROP400
//
//
// TEST_NAME can be a specific test name, or have a '*' in the end, which
// indicates a prefix matching.
//
// Examples:
// 91530 MAC WIN LINUX : context_lost_restored = TIMEOUT
// 91533 WIN : gl_min_uniforms = FAIL
// 91531 MAC WIN LINUX : conformance_more_* = SKIP
// 91532 MAC NVIDIA 0x0640 : tex_image_and_sub_image_2d_with_video = PASS FAIL
// fails on both windows and mac (crash)
// 91530 WIN : context_lost_restored = SKIP
// 91530 MAC : context_lost_restored = SKIP
// fails on windows using NVIDIA GPUs
// 91533 WIN NVIDIA : gl_min_uniforms = FAIL
// fails on Nexus5X with GLES backend (hangs)
// 91531 NEXUS5X GLES : conformance_more_* = SKIP
// ANGLE does not yet support multithreading
1340 WIN MAC LINUX : dEQP-EGL.functional.sharing.gles2.multithread.* = SKIP
1340 WIN MAC LINUX : dEQP-EGL.functional.multithread.* = SKIP
1340 WIN MAC LINUX : dEQP-EGL.functional.render.multi_thread.* = SKIP
1340 : dEQP-EGL.functional.sharing.gles2.multithread.* = SKIP
1340 : dEQP-EGL.functional.multithread.* = SKIP
1340 : dEQP-EGL.functional.render.multi_thread.* = SKIP
// dEQP doesn't handle configs created for extensions
1662 WIN : dEQP-EGL.functional.color_clears.single_context.gles2.other = FAIL
......@@ -52,7 +58,7 @@
1662 WIN : dEQP-EGL.functional.native_color_mapping.native_window.other_render = SKIP
// Intentionally causes TDRs that eventually blacklist the application
2319 DEBUG RELEASE : dEQP-EGL.functional.robustness.reset_context.shaders.infinite_loop.* = SKIP
2319 : dEQP-EGL.functional.robustness.reset_context.shaders.infinite_loop.* = SKIP
////////////////////////////////////////////////////////////////////////////////
//
......@@ -169,9 +175,6 @@
2567 ANDROID GLES : dEQP-EGL.functional.image.api.create_image_gles2_tex2d_rg = FAIL
2716 ANDROID GLES : dEQP-EGL.functional.preserve_swap.preserve.* = FAIL
// Seems to crash on the 5x. Possibly other Android devices.
3113 ANDROID GLES : dEQP-EGL.functional.reusable_sync.* = SKIP
// Android failures
2546 ANDROID : dEQP-EGL.functional.buffer_age.* = FAIL
3270 ANDROID : dEQP-EGL.functional.choose_config.simple.selection_only.transparent_red_value = FAIL
......@@ -183,7 +186,6 @@
2546 ANDROID : dEQP-EGL.functional.color_clears.multi_context.* = SKIP
2546 ANDROID : dEQP-EGL.functional.color_clears.multi_thread.* = SKIP
2546 ANDROID : dEQP-EGL.functional.color_clears.single_context.* = SKIP
2546 ANDROID : dEQP-EGL.functional.multithread.* = SKIP
2546 ANDROID : dEQP-EGL.functional.native_color_mapping.native_window.* = SKIP
2546 ANDROID : dEQP-EGL.functional.native_coord_mapping.native_window.* = SKIP
2546 ANDROID : dEQP-EGL.functional.negative_api.copy_buffers = FAIL
......@@ -195,9 +197,7 @@
2546 ANDROID : dEQP-EGL.functional.query_context.get_current_surface.r* = FAIL
2546 ANDROID : dEQP-EGL.functional.query_context.query_context.* = SKIP
2546 ANDROID : dEQP-EGL.functional.render.multi_context.* = SKIP
2546 ANDROID : dEQP-EGL.functional.render.multi_thread.* = SKIP
2546 ANDROID : dEQP-EGL.functional.render.single_context.* = FAIL
2546 ANDROID : dEQP-EGL.functional.sharing.gles2.multithread.* = SKIP
2546 ANDROID : dEQP-EGL.functional.thread_cleanup.multi_context_* = SKIP
2546 ANDROID : dEQP-EGL.functional.thread_cleanup.single_context_* = FAIL
......@@ -218,17 +218,23 @@
2546 ANDROID VULKAN : dEQP-EGL.functional.wide_color.window* = SKIP
// ES 1 tests
2306 WIN MAC LINUX : dEQP-EGL.functional.color_clears.single_context.gles1* = FAIL
2306 WIN MAC LINUX : dEQP-EGL.functional.color_clears.multi_context.gles1* = FAIL
2306 WIN MAC LINUX : dEQP-EGL.functional.color_clears.multi_thread.gles1* = FAIL
2306 WIN : dEQP-EGL.functional.color_clears.single_context.gles1* = FAIL
2306 WIN : dEQP-EGL.functional.color_clears.multi_context.gles1* = FAIL
2306 WIN : dEQP-EGL.functional.color_clears.multi_thread.gles1* = FAIL
2306 MAC : dEQP-EGL.functional.color_clears.single_context.gles1* = FAIL
2306 MAC : dEQP-EGL.functional.color_clears.multi_context.gles1* = FAIL
2306 MAC : dEQP-EGL.functional.color_clears.multi_thread.gles1* = FAIL
2306 LINUX : dEQP-EGL.functional.color_clears.single_context.gles1* = FAIL
2306 LINUX : dEQP-EGL.functional.color_clears.multi_context.gles1* = FAIL
2306 LINUX : dEQP-EGL.functional.color_clears.multi_thread.gles1* = FAIL
// Tests failing since the Jan 2018 roll of dEQP
2341 DEBUG RELEASE : dEQP-EGL.functional.swap_buffers.* = SKIP
2330 DEBUG RELEASE : dEQP-EGL.functional.robustness.create_context.no_reset_notification = SKIP
2330 DEBUG RELEASE : dEQP-EGL.functional.robustness.create_context.lose_context_on_reset = SKIP
2330 DEBUG RELEASE : dEQP-EGL.functional.robustness.reset_context.fixed_function_pipeline.reset_status.index_buffer_out_of_bounds = SKIP
2330 DEBUG RELEASE : dEQP-EGL.functional.robustness.reset_context.fixed_function_pipeline.reset_status.vertex_buffer_out_of_bounds = SKIP
2341 : dEQP-EGL.functional.swap_buffers.* = SKIP
2330 : dEQP-EGL.functional.robustness.create_context.no_reset_notification = SKIP
2330 : dEQP-EGL.functional.robustness.create_context.lose_context_on_reset = SKIP
2330 : dEQP-EGL.functional.robustness.reset_context.fixed_function_pipeline.reset_status.index_buffer_out_of_bounds = SKIP
2330 : dEQP-EGL.functional.robustness.reset_context.fixed_function_pipeline.reset_status.vertex_buffer_out_of_bounds = SKIP
// Tests were being hidden by flakiness (anglebug.com/3271)
3325 WIN MAC LINUX : dEQP-EGL.functional.fence_sync.* = SKIP
3325 WIN MAC LINUX : dEQP-EGL.functional.reusable_sync.* = SKIP
3325 : dEQP-EGL.functional.fence_sync.* = SKIP
3325 : dEQP-EGL.functional.reusable_sync.* = SKIP
......@@ -6,29 +6,35 @@
// format is:
// {BUG#} {MODIFIERS} : {TEST_NAME} = {PASS,FAIL,FLAKY,TIMEOUT,SKIP}
//
// MODIFIERS can be a combination of the below list:
// WIN XP VISTA WIN7 MAC LEOPARD SNOWLEOPARD LION LINUX CHROMEOS MOUNTAINLION
// MAVERICKS
// MODIFIERS can be a combination of the below list, combined with a logical AND:
// WIN XP VISTA WIN7 WIN8 WIN10
// MAC LEOPARD SNOWLEOPARD LION MOUNTAINLION MAVERICKS YOSEMITE ELCAPITAN SIERRA HIGHSIERRA MOJAVE
// LINUX CHROMEOS ANDROID
// NVIDIA AMD INTEL
// 0xabcd - GPU PCI device ID. Specifying a PCI id requires a vendor.
// DEBUG RELEASE
// TODO(jmadill): Add ANGLE Renderer selection modifiers
// D3D9 D3D11 OPENGL GLES VULKAN
// NEXUS5X PIXEL2
// QUADROP400
//
//
// TEST_NAME can be a specific test name, or have a '*' in the end, which
// indicates a prefix matching.
//
// Examples:
// 91530 MAC WIN LINUX : context_lost_restored = TIMEOUT
// 91533 WIN : gl_min_uniforms = FAIL
// 91531 MAC WIN LINUX : conformance_more_* = SKIP
// 91532 MAC NVIDIA 0x0640 : tex_image_and_sub_image_2d_with_video = PASS FAIL
// fails on both windows and mac (crash)
// 91530 WIN : context_lost_restored = SKIP
// 91530 MAC : context_lost_restored = SKIP
// fails on windows using NVIDIA GPUs
// 91533 WIN NVIDIA : gl_min_uniforms = FAIL
// fails on Nexus5X with GLES backend (hangs)
// 91531 NEXUS5X GLES : conformance_more_* = SKIP
// Skip these tests due to timeouts
1034 DEBUG RELEASE : dEQP-GLES2.functional.flush_finish.* = SKIP
1034 : dEQP-GLES2.functional.flush_finish.* = SKIP
// Don't run these tests for faster turnover
998 DEBUG RELEASE : dEQP-GLES2.performance.* = SKIP
998 DEBUG RELEASE : dEQP-GLES2.stress.* = SKIP
998 : dEQP-GLES2.performance.* = SKIP
998 : dEQP-GLES2.stress.* = SKIP
// Failures related to not supporting separate depth/stencil masks on D3D11.
1655 D3D11 : dEQP-GLES2.functional.fragment_ops.depth_stencil.stencil_depth_funcs.stencil_* = FAIL
......@@ -68,23 +74,23 @@
////////////////////////////////////////////////////////////////////////////////
// dEQP bugs
1028 DEBUG RELEASE : dEQP-GLES2.functional.fbo.completeness.renderable.texture.color0.srgb8 = FAIL
1028 DEBUG RELEASE : dEQP-GLES2.functional.fbo.completeness.renderable.texture.stencil.srgb8 = FAIL
1028 DEBUG RELEASE : dEQP-GLES2.functional.fbo.completeness.renderable.texture.depth.srgb8 = FAIL
1028 : dEQP-GLES2.functional.fbo.completeness.renderable.texture.color0.srgb8 = FAIL
1028 : dEQP-GLES2.functional.fbo.completeness.renderable.texture.stencil.srgb8 = FAIL
1028 : dEQP-GLES2.functional.fbo.completeness.renderable.texture.depth.srgb8 = FAIL
// Bind aliasing is not working currently
3252 DEBUG RELEASE : dEQP-GLES2.functional.attribute_location.bind_aliasing.cond* = FAIL
3252 DEBUG RELEASE : dEQP-GLES2.functional.attribute_location.bind_aliasing.max_cond* = FAIL
3252 : dEQP-GLES2.functional.attribute_location.bind_aliasing.cond* = FAIL
3252 : dEQP-GLES2.functional.attribute_location.bind_aliasing.max_cond* = FAIL
// Half float OES either has an implementation bug or a dEQP bug.
3283 DEBUG RELEASE : dEQP-GLES2.functional.fbo.completeness.renderable.texture.color0.rgba_half_float_oes = FAIL
3283 : dEQP-GLES2.functional.fbo.completeness.renderable.texture.color0.rgba_half_float_oes = FAIL
// Shader failures.
3285 DEBUG RELEASE : dEQP-GLES2.functional.shaders.preprocessor.pragmas.pragma_fragment = FAIL
3285 DEBUG RELEASE : dEQP-GLES2.functional.shaders.preprocessor.extensions.after_non_preprocessing_tokens_vertex = FAIL
3285 DEBUG RELEASE : dEQP-GLES2.functional.shaders.preprocessor.extensions.after_non_preprocessing_tokens_fragment = FAIL
3287 DEBUG RELEASE : dEQP-GLES2.functional.shaders.scoping.valid.local_variable_hides_function_parameter_vertex = FAIL
3287 DEBUG RELEASE : dEQP-GLES2.functional.shaders.scoping.valid.local_variable_hides_function_parameter_fragment = FAIL
3285 : dEQP-GLES2.functional.shaders.preprocessor.pragmas.pragma_fragment = FAIL
3285 : dEQP-GLES2.functional.shaders.preprocessor.extensions.after_non_preprocessing_tokens_vertex = FAIL
3285 : dEQP-GLES2.functional.shaders.preprocessor.extensions.after_non_preprocessing_tokens_fragment = FAIL
3287 : dEQP-GLES2.functional.shaders.scoping.valid.local_variable_hides_function_parameter_vertex = FAIL
3287 : dEQP-GLES2.functional.shaders.scoping.valid.local_variable_hides_function_parameter_fragment = FAIL
// The fragment_ops.depth_stencil.random tests all seem to fail on D3D11.
3282 D3D11 : dEQP-GLES2.functional.fragment_ops.depth_stencil.random.* = FAIL
......@@ -251,17 +257,17 @@
2630 GLES ANDROID : dEQP-GLES2.functional.shaders.struct.uniform.sampler_in_function_arg_* = FAIL
// Nexus 5x failures
3309 GLES ANDROID : dEQP-GLES2.functional.fbo.render.texsubimage.after_render_tex2d_rgb = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.polygon_offset.default_result_depth_clamp = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.shaders.return.output_write_in_func_always_vertex = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.shaders.return.output_write_in_func_always_fragment = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.shaders.texture_functions.vertex.texturecubelod = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.texture.mipmap.cube.* = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_* = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_* = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_* = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.uniform_api.random.3 = FAIL
3309 GLES ANDROID : dEQP-GLES2.functional.uniform_api.random.54 = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.fbo.render.texsubimage.after_render_tex2d_rgb = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.polygon_offset.default_result_depth_clamp = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.shaders.return.output_write_in_func_always_vertex = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.shaders.return.output_write_in_func_always_fragment = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.shaders.texture_functions.vertex.texturecubelod = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.texture.mipmap.cube.* = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_* = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_* = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_* = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.uniform_api.random.3 = FAIL
3309 NEXUS5X GLES : dEQP-GLES2.functional.uniform_api.random.54 = FAIL
// General Vulkan failures
3300 VULKAN : dEQP-GLES2.functional.shaders.texture_functions.vertex.texturecubelod = FAIL
......@@ -288,24 +294,40 @@
3239 VULKAN : dEQP-GLES2.functional.texture.completeness.cube.npot_size_level_1_neg_x = FAIL
// These seem to fail on both D3D11 and Vulkan
3243 D3D11 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.basic.linear_nearest = FAIL
3243 D3D11 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.basic.linear_linear = FAIL
3243 D3D11 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.projected.linear_nearest = FAIL
3243 D3D11 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.projected.linear_linear = FAIL
3243 D3D11 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.bias.linear_nearest = FAIL
3243 D3D11 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.bias.linear_linear = FAIL
3243 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.basic.linear_nearest = FAIL
3243 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.basic.linear_linear = FAIL
3243 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.projected.linear_nearest = FAIL
3243 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.projected.linear_linear = FAIL
3243 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.bias.linear_nearest = FAIL
3243 VULKAN : dEQP-GLES2.functional.texture.mipmap.cube.bias.linear_linear = FAIL
3243 D3D11 : dEQP-GLES2.functional.texture.mipmap.cube.basic.linear_nearest = FAIL
3243 D3D11 : dEQP-GLES2.functional.texture.mipmap.cube.basic.linear_linear = FAIL
3243 D3D11 : dEQP-GLES2.functional.texture.mipmap.cube.projected.linear_nearest = FAIL
3243 D3D11 : dEQP-GLES2.functional.texture.mipmap.cube.projected.linear_linear = FAIL
3243 D3D11 : dEQP-GLES2.functional.texture.mipmap.cube.bias.linear_nearest = FAIL
3243 D3D11 : dEQP-GLES2.functional.texture.mipmap.cube.bias.linear_linear = FAIL
// Fail with very tiny pixel differences
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_nearest_clamp = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_nearest_mirror = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_linear_clamp = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_linear_mirror = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_clamp = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_repeat = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_mirror = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_clamp = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_repeat = FAIL
3240 D3D11 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_mirror = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_nearest_clamp = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_nearest_mirror = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_linear_clamp = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_linear_mirror = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_clamp = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_repeat = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_mirror = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_clamp = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_repeat = FAIL
3240 VULKAN : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_mirror = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_nearest_clamp = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_nearest_mirror = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_linear_clamp = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.filtering.linear_mipmap_linear_linear_mirror = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_clamp = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_repeat = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.wrap.clamp_mirror = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_clamp = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_repeat = FAIL
3240 D3D11 : dEQP-GLES2.functional.texture.vertex.cube.wrap.mirror_mirror = FAIL
// Android Vulkan backend only failures
2549 VULKAN ANDROID : dEQP-GLES2.functional.fragment_ops.depth_stencil.stencil* = SKIP
......
......@@ -6,26 +6,33 @@
// format is:
// {BUG#} {MODIFIERS} : {TEST_NAME} = {PASS,FAIL,FLAKY,TIMEOUT,SKIP}
//
// MODIFIERS can be a combination of the below list:
// WIN XP VISTA WIN7 MAC LEOPARD SNOWLEOPARD LION LINUX CHROMEOS MOUNTAINLION
// MAVERICKS
// MODIFIERS can be a combination of the below list, combined with a logical AND:
// WIN XP VISTA WIN7 WIN8 WIN10
// MAC LEOPARD SNOWLEOPARD LION MOUNTAINLION MAVERICKS YOSEMITE ELCAPITAN SIERRA HIGHSIERRA MOJAVE
// LINUX CHROMEOS ANDROID
// NVIDIA AMD INTEL
// 0xabcd - GPU PCI device ID. Specifying a PCI id requires a vendor.
// DEBUG RELEASE
// TODO(jmadill): Add ANGLE Renderer selection modifiers
// D3D9 D3D11 OPENGL GLES VULKAN
// NEXUS5X PIXEL2
// QUADROP400
//
//
// TEST_NAME can be a specific test name, or have a '*' in the end, which
// indicates a prefix matching.
//
// Examples:
// 91530 MAC WIN LINUX : context_lost_restored = TIMEOUT
// 91533 WIN : gl_min_uniforms = FAIL
// 91531 MAC WIN LINUX : conformance_more_* = SKIP
// 91532 MAC NVIDIA 0x0640 : tex_image_and_sub_image_2d_with_video = PASS FAIL
// fails on both windows and mac (crash)
// 91530 WIN : context_lost_restored = SKIP
// 91530 MAC : context_lost_restored = SKIP
// fails on windows using NVIDIA GPUs
// 91533 WIN NVIDIA : gl_min_uniforms = FAIL
// fails on Nexus5X with GLES backend (hangs)
// 91531 NEXUS5X GLES : conformance_more_* = SKIP
// Crashing Tests
1920 NVIDIA D3D11 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP
1442 OPENGL D3D11 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.resource_list.vertex_fragment.builtin_gl_position = SKIP
1442 D3D11 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.resource_list.vertex_fragment.builtin_gl_position = SKIP
1442 OPENGL : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.resource_list.vertex_fragment.builtin_gl_position = SKIP
// Crashing Tests on Linux on Intel HD 630.
2349 LINUX INTEL : dEQP-GLES31.functional.synchronization.in_invocation.image_* = SKIP
......@@ -37,14 +44,16 @@
// Failing Tests on Linux on Intel HD 630.
2349 LINUX INTEL : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader.program_binary = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.resource_list.vertex_fragment.default_block_struct_member = SKIP
1442 OPENGL D3D11 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.array_size.vertex_fragment.default_block_struct_member = SKIP
1442 OPENGL D3D11 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.name_length.vertex_fragment.default_block_struct_member = SKIP
1442 OPENGL D3D11 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.type.vertex_fragment.struct.* = SKIP
1442 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.resource_list.vertex_fragment.default_block_struct_member = SKIP
1442 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.array_size.vertex_fragment.default_block_struct_member = SKIP
1442 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.name_length.vertex_fragment.default_block_struct_member = SKIP
1442 : dEQP-GLES31.functional.program_interface_query.transform_feedback_varying.type.vertex_fragment.struct.* = SKIP
1442 : dEQP-GLES31.functional.image_load_store.* = SKIP
1442 D3D11 : dEQP-GLES31.functional.stencil_texturing.* = SKIP
// TODO(xinghua.cao@intel.com): FAIL expectation instead of SKIP should be sufficient for OpenGL, but the
// test expectations parser doesn't support having FAIL for GL and SKIP for D3D with the same test filter.
1442 OPENGL D3D11 : dEQP-GLES31.functional.image_load_store.* = SKIP
1729 D3D11 : dEQP-GLES31.functional.atomic_counter.* = SKIP
1951 D3D11 : dEQP-GLES31.functional.layout_binding.ssbo.* = SKIP
......@@ -544,52 +553,52 @@
2432 NVIDIA OPENGL : dEQP-GLES31.functional.vertex_attribute_binding.usage.mixed_usage.mixed_api_change_binding_point = SKIP
// OpenGL and D3D11 Failing Tests
1442 OPENGL D3D11 : dEQP-GLES31.functional.compute.basic.copy_image_to_ssbo_large = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.compute.basic.copy_ssbo_to_image_large = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.shaders.opaque_type_indexing.* = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.shaders.helper_invocation.* = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.state_query.integer.program_pipeline_binding_* = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.state_query.program.program_separable_get_programiv = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.state_query.program_pipeline.* = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.synchronization.inter_call.without_memory_barrier.atomic_counter_dispatch_100_calls_1k_invocations = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.separate_shader.* = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.error_filters.case_11 = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.error_groups.case_11 = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.buffer.bind_buffer_range = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader.compile_compute_shader = SKIP
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader_directive.primitive_bounding_box = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader_directive.tessellation_shader = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.log.buffer.bind_buffer_range = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.log.shader.compile_compute_shader = SKIP
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.log.shader_directive.primitive_bounding_box = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.log.shader_directive.tessellation_shader = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.buffer.bind_buffer_range = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.buffer.read_pixels_format_mismatch = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.buffer.framebuffer_texture2d = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copyteximage2d_invalid_format = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copyteximage2d_inequal_width_height_cube = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copyteximage2d_max_width_height = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copytexsubimage2d_invalid_offset = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage2d = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage2d_invalid_size = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.texsubimage3d_neg_level = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.texsubimage3d_neg_offset = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copytexsubimage3d_invalid_offset = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage3d = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage3d_invalid_buffer_target = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader.compile_compute_shader = SKIP
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.vertex_array.draw_range_elements = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.vertex_array.draw_range_elements_incomplete_primitive = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader_directive.primitive_bounding_box = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader_directive.tessellation_shader = FAIL
1442 OPENGL D3D11 : dEQP-GLES31.functional.debug.object_labels.program_pipeline = FAIL
1442 : dEQP-GLES31.functional.compute.basic.copy_image_to_ssbo_large = FAIL
1442 : dEQP-GLES31.functional.compute.basic.copy_ssbo_to_image_large = FAIL
1442 : dEQP-GLES31.functional.shaders.opaque_type_indexing.* = FAIL
1442 : dEQP-GLES31.functional.shaders.helper_invocation.* = FAIL
1442 : dEQP-GLES31.functional.state_query.integer.program_pipeline_binding_* = FAIL
1442 : dEQP-GLES31.functional.state_query.program.program_separable_get_programiv = FAIL
1442 : dEQP-GLES31.functional.state_query.program_pipeline.* = FAIL
1442 : dEQP-GLES31.functional.synchronization.inter_call.without_memory_barrier.atomic_counter_dispatch_100_calls_1k_invocations = FAIL
1442 : dEQP-GLES31.functional.separate_shader.* = FAIL
1442 : dEQP-GLES31.functional.debug.error_filters.case_11 = FAIL
1442 : dEQP-GLES31.functional.debug.error_groups.case_11 = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.buffer.bind_buffer_range = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader.compile_compute_shader = SKIP
1442 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader_directive.primitive_bounding_box = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader_directive.tessellation_shader = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.log.buffer.bind_buffer_range = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.log.shader.compile_compute_shader = SKIP
1442 : dEQP-GLES31.functional.debug.negative_coverage.log.shader_directive.primitive_bounding_box = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.log.shader_directive.tessellation_shader = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.buffer.bind_buffer_range = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.buffer.read_pixels_format_mismatch = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.buffer.framebuffer_texture2d = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copyteximage2d_invalid_format = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copyteximage2d_inequal_width_height_cube = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copyteximage2d_max_width_height = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copytexsubimage2d_invalid_offset = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage2d = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage2d_invalid_size = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.texsubimage3d_neg_level = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.texsubimage3d_neg_offset = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.copytexsubimage3d_invalid_offset = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage3d = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.texture.compressedtexsubimage3d_invalid_buffer_target = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader.compile_compute_shader = SKIP
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.vertex_array.draw_range_elements = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.vertex_array.draw_range_elements_incomplete_primitive = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader_directive.primitive_bounding_box = FAIL
1442 : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader_directive.tessellation_shader = FAIL
1442 : dEQP-GLES31.functional.debug.object_labels.program_pipeline = FAIL
2324 DEBUG RELEASE : dEQP-GLES31.functional.debug.negative_coverage.callbacks.compute.program_not_active = FAIL
2324 DEBUG RELEASE : dEQP-GLES31.functional.debug.negative_coverage.log.compute.program_not_active = FAIL
2324 DEBUG RELEASE : dEQP-GLES31.functional.debug.negative_coverage.get_error.compute.program_not_active = FAIL
2324 DEBUG RELEASE : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader_storage.block_number_limits = FAIL
2324 DEBUG RELEASE : dEQP-GLES31.functional.debug.negative_coverage.log.shader_storage.block_number_limits = FAIL
2324 DEBUG RELEASE : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader_storage.block_number_limits = FAIL
2324 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.compute.program_not_active = FAIL
2324 : dEQP-GLES31.functional.debug.negative_coverage.log.compute.program_not_active = FAIL
2324 : dEQP-GLES31.functional.debug.negative_coverage.get_error.compute.program_not_active = FAIL
2324 : dEQP-GLES31.functional.debug.negative_coverage.get_error.shader_storage.block_number_limits = FAIL
2324 : dEQP-GLES31.functional.debug.negative_coverage.log.shader_storage.block_number_limits = FAIL
2324 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.shader_storage.block_number_limits = FAIL
// These tests are failing because of compile errors with SSBOs in compute shaders.
1951 D3D11 : dEQP-GLES31.functional.debug.negative_coverage.callbacks.compute.exceed_shared_memory_size_limit = FAIL
......
......@@ -6,31 +6,37 @@
// format is:
// {BUG#} {MODIFIERS} : {TEST_NAME} = {PASS,FAIL,FLAKY,TIMEOUT,SKIP}
//
// MODIFIERS can be a combination of the below list:
// WIN XP VISTA WIN7 MAC LEOPARD SNOWLEOPARD LION LINUX CHROMEOS MOUNTAINLION
// MAVERICKS
// MODIFIERS can be a combination of the below list, combined with a logical AND:
// WIN XP VISTA WIN7 WIN8 WIN10
// MAC LEOPARD SNOWLEOPARD LION MOUNTAINLION MAVERICKS YOSEMITE ELCAPITAN SIERRA HIGHSIERRA MOJAVE
// LINUX CHROMEOS ANDROID
// NVIDIA AMD INTEL
// 0xabcd - GPU PCI device ID. Specifying a PCI id requires a vendor.
// DEBUG RELEASE
// TODO(jmadill): Add ANGLE Renderer selection modifiers
// D3D9 D3D11 OPENGL GLES VULKAN
// NEXUS5X PIXEL2
// QUADROP400
//
//
// TEST_NAME can be a specific test name, or have a '*' in the end, which
// indicates a prefix matching.
//
// Examples:
// 91530 MAC WIN LINUX : context_lost_restored = TIMEOUT
// 91533 WIN : gl_min_uniforms = FAIL
// 91531 MAC WIN LINUX : conformance_more_* = SKIP
// 91532 MAC NVIDIA 0x0640 : tex_image_and_sub_image_2d_with_video = PASS FAIL
// fails on both windows and mac (crash)
// 91530 WIN : context_lost_restored = SKIP
// 91530 MAC : context_lost_restored = SKIP
// fails on windows using NVIDIA GPUs
// 91533 WIN NVIDIA : gl_min_uniforms = FAIL
// fails on Nexus5X with GLES backend (hangs)
// 91531 NEXUS5X GLES : conformance_more_* = SKIP
// Don't run these tests for faster turnover
998 DEBUG RELEASE : dEQP-GLES3.performance.* = SKIP
998 DEBUG RELEASE : dEQP-GLES3.stress.* = SKIP
1101 DEBUG RELEASE : dEQP-GLES3.functional.flush_finish.* = SKIP
998 : dEQP-GLES3.performance.* = SKIP
998 : dEQP-GLES3.stress.* = SKIP
1101 : dEQP-GLES3.functional.flush_finish.* = SKIP
// Figure out why this caused this regression in Chrome:
// https://bugs.chromium.org/p/chromium/issues/detail?id=833809#
2321 DEBUG RELEASE : dEQP-GLES3.functional.state_query.fbo.framebuffer_unspecified_attachment_x_size_rbo = FAIL
2321 : dEQP-GLES3.functional.state_query.fbo.framebuffer_unspecified_attachment_x_size_rbo = FAIL
// TODO(jmadill): Figure out why these fail on the bots, but not locally.
1108 WIN D3D11 : dEQP-GLES3.functional.shaders.struct.local.dynamic_loop_struct_array_fragment = FAIL
......@@ -104,14 +110,15 @@
2222 D3D11 NVIDIA : dEQP-GLES3.functional.texture.mipmap.cube.min_lod.nearest_nearest = FAIL
// Failing everywhere
2322 DEBUG RELEASE : dEQP-GLES3.functional.shaders.metamorphic.* = FAIL
2322 : dEQP-GLES3.functional.shaders.metamorphic.* = FAIL
// Bind aliasing is not working currently
3252 DEBUG RELEASE : dEQP-GLES3.functional.attribute_location.bind_aliasing.cond* = FAIL
3252 DEBUG RELEASE : dEQP-GLES3.functional.attribute_location.bind_aliasing.max_cond* = FAIL
3252 : dEQP-GLES3.functional.attribute_location.bind_aliasing.cond* = FAIL
3252 : dEQP-GLES3.functional.attribute_location.bind_aliasing.max_cond* = FAIL
// Windows and Linux failures
1095 WIN LINUX : dEQP-GLES3.functional.texture.mipmap.2d.projected.* = FAIL
1095 WIN : dEQP-GLES3.functional.texture.mipmap.2d.projected.* = FAIL
1095 LINUX : dEQP-GLES3.functional.texture.mipmap.2d.projected.* = FAIL
// Windows only failure
1092 WIN D3D11 : dEQP-GLES3.functional.shaders.texture_functions.textureoffset.sampler3d_fixed_fragment = FAIL
......@@ -254,7 +261,8 @@
2349 D3D11 INTEL : dEQP-GLES3.functional.rasterization.fbo.rbo_multisample_max.interpolation.lines = FAIL
// Failing Tests on Windows and Mac on Intel HD 630
2137 WIN MAC INTEL : dEQP-GLES3.functional.fbo.color.repeated_clear.sample.tex2d.* = FAIL
2137 WIN INTEL : dEQP-GLES3.functional.fbo.color.repeated_clear.sample.tex2d.* = FAIL
2137 MAC INTEL : dEQP-GLES3.functional.fbo.color.repeated_clear.sample.tex2d.* = FAIL
// Linux only failures
......@@ -507,11 +515,11 @@
2567 ANDROID GLES : dEQP-GLES3.functional.fbo.completeness.renderable.texture.stencil.rg_unsigned_byte = FAIL
// Nexus 5x failures
3308 ANDROID GLES : dEQP-GLES3.functional.polygon_offset.default_result_depth_clamp = FAIL
3308 ANDROID GLES : dEQP-GLES3.functional.polygon_offset.fixed24_result_depth_clamp = FAIL
3308 ANDROID GLES : dEQP-GLES3.functional.transform_feedback.random.interleaved.lines.3 = FAIL
3308 ANDROID GLES : dEQP-GLES3.functional.transform_feedback.random.interleaved.triangles.8 = FAIL
3308 ANDROID GLES : dEQP-GLES3.functional.transform_feedback.random.interleaved.triangles.10 = FAIL
3308 NEXUS5X GLES : dEQP-GLES3.functional.polygon_offset.default_result_depth_clamp = FAIL
3308 NEXUS5X GLES : dEQP-GLES3.functional.polygon_offset.fixed24_result_depth_clamp = FAIL
3308 NEXUS5X GLES : dEQP-GLES3.functional.transform_feedback.random.interleaved.lines.3 = FAIL
3308 NEXUS5X GLES : dEQP-GLES3.functional.transform_feedback.random.interleaved.triangles.8 = FAIL
3308 NEXUS5X GLES : dEQP-GLES3.functional.transform_feedback.random.interleaved.triangles.10 = FAIL
// Seems to fail on all desktop GL
2960 OPENGL : dEQP-GLES3.functional.fbo.blit.default_framebuffer.srgb8_alpha8 = FAIL
......
//
// 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.
//
#include <stdint.h>
#include "GPUInfo.h"
namespace
{
void EnumerateGPUDevice(const angle::GPUInfo::GPUDevice &device,
angle::GPUInfo::Enumerator *enumerator)
{
enumerator->BeginGPUDevice();
enumerator->AddInt("vendorId", device.vendor_id);
enumerator->AddInt("deviceId", device.device_id);
enumerator->AddBool("active", device.active);
enumerator->AddString("vendorString", device.vendor_string);
enumerator->AddString("deviceString", device.device_string);
enumerator->AddString("driverVendor", device.driver_vendor);
enumerator->AddString("driverVersion", device.driver_version);
enumerator->AddString("driverDate", device.driver_date);
enumerator->AddInt("cudaComputeCapabilityMajor", device.cuda_compute_capability_major);
enumerator->EndGPUDevice();
}
void EnumerateVideoDecodeAcceleratorSupportedProfile(
const angle::VideoDecodeAcceleratorSupportedProfile &profile,
angle::GPUInfo::Enumerator *enumerator)
{
enumerator->BeginVideoDecodeAcceleratorSupportedProfile();
enumerator->AddInt("profile", profile.profile);
enumerator->AddInt("maxResolutionWidth", profile.max_resolution.width());
enumerator->AddInt("maxResolutionHeight", profile.max_resolution.height());
enumerator->AddInt("minResolutionWidth", profile.min_resolution.width());
enumerator->AddInt("minResolutionHeight", profile.min_resolution.height());
enumerator->AddBool("encrypted_only", profile.encrypted_only);
enumerator->EndVideoDecodeAcceleratorSupportedProfile();
}
void EnumerateVideoEncodeAcceleratorSupportedProfile(
const angle::VideoEncodeAcceleratorSupportedProfile &profile,
angle::GPUInfo::Enumerator *enumerator)
{
enumerator->BeginVideoEncodeAcceleratorSupportedProfile();
enumerator->AddInt("profile", profile.profile);
enumerator->AddInt("maxResolutionWidth", profile.max_resolution.width());
enumerator->AddInt("maxResolutionHeight", profile.max_resolution.height());
enumerator->AddInt("maxFramerateNumerator", profile.max_framerate_numerator);
enumerator->AddInt("maxFramerateDenominator", profile.max_framerate_denominator);
enumerator->EndVideoEncodeAcceleratorSupportedProfile();
}
const char *ImageDecodeAcceleratorTypeToString(angle::ImageDecodeAcceleratorType type)
{
switch (type)
{
case angle::ImageDecodeAcceleratorType::kJpeg:
return "JPEG";
case angle::ImageDecodeAcceleratorType::kUnknown:
return "Unknown";
}
}
const char *ImageDecodeAcceleratorSubsamplingToString(
angle::ImageDecodeAcceleratorSubsampling subsampling)
{
switch (subsampling)
{
case angle::ImageDecodeAcceleratorSubsampling::k420:
return "4:2:0";
case angle::ImageDecodeAcceleratorSubsampling::k422:
return "4:2:2";
}
}
void EnumerateImageDecodeAcceleratorSupportedProfile(
const angle::ImageDecodeAcceleratorSupportedProfile &profile,
angle::GPUInfo::Enumerator *enumerator)
{
enumerator->BeginImageDecodeAcceleratorSupportedProfile();
enumerator->AddString("imageType", ImageDecodeAcceleratorTypeToString(profile.image_type));
enumerator->AddString("minEncodedDimensions", profile.min_encoded_dimensions.ToString());
enumerator->AddString("maxEncodedDimensions", profile.max_encoded_dimensions.ToString());
std::string subsamplings;
for (size_t i = 0; i < profile.subsamplings.size(); i++)
{
if (i > 0)
subsamplings += ", ";
subsamplings += ImageDecodeAcceleratorSubsamplingToString(profile.subsamplings[i]);
}
enumerator->AddString("subsamplings", subsamplings);
enumerator->EndImageDecodeAcceleratorSupportedProfile();
}
#if defined(ANGLE_PLATFORM_WINDOWS)
void EnumerateOverlayCapability(const angle::OverlayCapability &cap,
angle::GPUInfo::Enumerator *enumerator)
{
std::string key_string = "overlayCap";
key_string += OverlayFormatToString(cap.format);
enumerator->BeginOverlayCapability();
enumerator->AddString(key_string.c_str(), cap.is_scaling_supported ? "SCALING" : "DIRECT");
enumerator->EndOverlayCapability();
}
void EnumerateDx12VulkanVersionInfo(const angle::Dx12VulkanVersionInfo &info,
angle::GPUInfo::Enumerator *enumerator)
{
enumerator->BeginDx12VulkanVersionInfo();
enumerator->AddBool("supportsDx12", info.supports_dx12);
enumerator->AddBool("supportsVulkan", info.supports_vulkan);
enumerator->AddInt("dx12FeatureLevel", static_cast<int>(info.d3d12_feature_level));
enumerator->AddInt("vulkanVersion", static_cast<int>(info.vulkan_version));
enumerator->EndDx12VulkanVersionInfo();
}
#endif
} // namespace
namespace angle
{
#if defined(ANGLE_PLATFORM_WINDOWS)
const char *OverlayFormatToString(OverlayFormat format)
{
switch (format)
{
case OverlayFormat::kBGRA:
return "BGRA";
case OverlayFormat::kYUY2:
return "YUY2";
case OverlayFormat::kNV12:
return "NV12";
}
}
bool OverlayCapability::operator==(const OverlayCapability &other) const
{
return format == other.format && is_scaling_supported == other.is_scaling_supported;
}
#endif
VideoDecodeAcceleratorCapabilities::VideoDecodeAcceleratorCapabilities() : flags(0) {}
VideoDecodeAcceleratorCapabilities::VideoDecodeAcceleratorCapabilities(
const VideoDecodeAcceleratorCapabilities &other) = default;
VideoDecodeAcceleratorCapabilities::~VideoDecodeAcceleratorCapabilities() = default;
ImageDecodeAcceleratorSupportedProfile::ImageDecodeAcceleratorSupportedProfile()
: image_type(ImageDecodeAcceleratorType::kUnknown)
{}
ImageDecodeAcceleratorSupportedProfile::ImageDecodeAcceleratorSupportedProfile(
const ImageDecodeAcceleratorSupportedProfile &other) = default;
ImageDecodeAcceleratorSupportedProfile::ImageDecodeAcceleratorSupportedProfile(
ImageDecodeAcceleratorSupportedProfile &&other) = default;
ImageDecodeAcceleratorSupportedProfile::~ImageDecodeAcceleratorSupportedProfile() = default;
ImageDecodeAcceleratorSupportedProfile &ImageDecodeAcceleratorSupportedProfile::operator=(
const ImageDecodeAcceleratorSupportedProfile &other) = default;
ImageDecodeAcceleratorSupportedProfile &ImageDecodeAcceleratorSupportedProfile::operator=(
ImageDecodeAcceleratorSupportedProfile &&other) = default;
GPUInfo::GPUDevice::GPUDevice()
: vendor_id(0), device_id(0), active(false), cuda_compute_capability_major(0)
{}
GPUInfo::GPUDevice::GPUDevice(const GPUInfo::GPUDevice &other) = default;
GPUInfo::GPUDevice::GPUDevice(GPUInfo::GPUDevice &&other) noexcept = default;
GPUInfo::GPUDevice::~GPUDevice() noexcept = default;
GPUInfo::GPUDevice &GPUInfo::GPUDevice::operator=(const GPUInfo::GPUDevice &other) = default;
GPUInfo::GPUDevice &GPUInfo::GPUDevice::operator=(GPUInfo::GPUDevice &&other) noexcept = default;
GPUInfo::GPUInfo()
: optimus(false),
amd_switchable(false),
gl_reset_notification_strategy(0),
software_rendering(false),
direct_rendering(true),
sandboxed(false),
in_process_gpu(true),
passthrough_cmd_decoder(false),
jpeg_decode_accelerator_supported(false),
#if defined(USE_X11)
system_visual(0),
rgba_visual(0),
#endif
oop_rasterization_supported(false)
{}
GPUInfo::GPUInfo(const GPUInfo &other) = default;
GPUInfo::~GPUInfo() = default;
GPUInfo::GPUDevice &GPUInfo::active_gpu()
{
return const_cast<GPUInfo::GPUDevice &>(const_cast<const GPUInfo &>(*this).active_gpu());
}
const GPUInfo::GPUDevice &GPUInfo::active_gpu() const
{
if (gpu.active || secondary_gpus.empty())
return gpu;
for (const auto &secondary_gpu : secondary_gpus)
{
if (secondary_gpu.active)
return secondary_gpu;
}
std::cerr << "No active GPU found, returning primary GPU.\n";
return gpu;
}
bool GPUInfo::IsInitialized() const
{
return gpu.vendor_id != 0 || !gl_vendor.empty();
}
void GPUInfo::EnumerateFields(Enumerator *enumerator) const
{
struct GPUInfoKnownFields
{
int64_t initialization_time;
bool optimus;
bool amd_switchable;
GPUDevice gpu;
std::vector<GPUDevice> secondary_gpus;
std::string pixel_shader_version;
std::string vertex_shader_version;
std::string max_msaa_samples;
std::string machine_model_name;
std::string machine_model_version;
std::string gl_version_string;
std::string gl_vendor;
std::string gl_renderer;
std::string gl_extensions;
std::string gl_ws_vendor;
std::string gl_ws_version;
std::string gl_ws_extensions;
uint32_t gl_reset_notification_strategy;
bool software_rendering;
bool direct_rendering;
bool sandboxed;
bool in_process_gpu;
bool passthrough_cmd_decoder;
bool can_support_threaded_texture_mailbox;
#if defined(ANGLE_PLATFORM_WINDOWS)
bool direct_composition;
bool supports_overlays;
OverlayCapabilities overlay_capabilities;
DxDiagNode dx_diagnostics;
Dx12VulkanVersionInfo dx12_vulkan_version_info;
#endif
VideoDecodeAcceleratorCapabilities video_decode_accelerator_capabilities;
VideoEncodeAcceleratorSupportedProfiles video_encode_accelerator_supported_profiles;
bool jpeg_decode_accelerator_supported;
ImageDecodeAcceleratorSupportedProfiles image_decode_accelerator_supported_profiles;
#if defined(USE_X11)
VisualID system_visual;
VisualID rgba_visual;
#endif
bool oop_rasterization_supported;
};
// If this assert fails then most likely something below needs to be updated.
// Note that this assert is only approximate. If a new field is added to
// GPUInfo which fits within the current padding then it will not be caught.
static_assert(sizeof(GPUInfo) == sizeof(GPUInfoKnownFields),
"fields have changed in GPUInfo, GPUInfoKnownFields must be updated");
// Required fields (according to DevTools protocol) first.
enumerator->AddString("machineModelName", machine_model_name);
enumerator->AddString("machineModelVersion", machine_model_version);
EnumerateGPUDevice(gpu, enumerator);
for (const auto &secondary_gpu : secondary_gpus)
EnumerateGPUDevice(secondary_gpu, enumerator);
enumerator->BeginAuxAttributes();
enumerator->AddTimeDeltaInSeconds("initializationTime", initialization_time);
enumerator->AddBool("optimus", optimus);
enumerator->AddBool("amdSwitchable", amd_switchable);
enumerator->AddString("pixelShaderVersion", pixel_shader_version);
enumerator->AddString("vertexShaderVersion", vertex_shader_version);
enumerator->AddString("maxMsaaSamples", max_msaa_samples);
enumerator->AddString("glVersion", gl_version);
enumerator->AddString("glVendor", gl_vendor);
enumerator->AddString("glRenderer", gl_renderer);
enumerator->AddString("glExtensions", gl_extensions);
enumerator->AddString("glWsVendor", gl_ws_vendor);
enumerator->AddString("glWsVersion", gl_ws_version);
enumerator->AddString("glWsExtensions", gl_ws_extensions);
enumerator->AddInt("glResetNotificationStrategy",
static_cast<int>(gl_reset_notification_strategy));
// TODO(kbr): add performance_stats.
enumerator->AddBool("softwareRendering", software_rendering);
enumerator->AddBool("directRendering", direct_rendering);
enumerator->AddBool("sandboxed", sandboxed);
enumerator->AddBool("inProcessGpu", in_process_gpu);
enumerator->AddBool("passthroughCmdDecoder", passthrough_cmd_decoder);
enumerator->AddBool("canSupportThreadedTextureMailbox", can_support_threaded_texture_mailbox);
// TODO(kbr): add dx_diagnostics on Windows.
#if defined(ANGLE_PLATFORM_WINDOWS)
enumerator->AddBool("directComposition", direct_composition);
enumerator->AddBool("supportsOverlays", supports_overlays);
for (const auto &cap : overlay_capabilities)
EnumerateOverlayCapability(cap, enumerator);
EnumerateDx12VulkanVersionInfo(dx12_vulkan_version_info, enumerator);
#endif
enumerator->AddInt("videoDecodeAcceleratorFlags", video_decode_accelerator_capabilities.flags);
for (const auto &profile : video_decode_accelerator_capabilities.supported_profiles)
EnumerateVideoDecodeAcceleratorSupportedProfile(profile, enumerator);
for (const auto &profile : video_encode_accelerator_supported_profiles)
EnumerateVideoEncodeAcceleratorSupportedProfile(profile, enumerator);
enumerator->AddBool("jpegDecodeAcceleratorSupported", jpeg_decode_accelerator_supported);
for (const auto &profile : image_decode_accelerator_supported_profiles)
EnumerateImageDecodeAcceleratorSupportedProfile(profile, enumerator);
#if defined(USE_X11)
enumerator->AddInt64("systemVisual", system_visual);
enumerator->AddInt64("rgbaVisual", rgba_visual);
#endif
enumerator->AddBool("oopRasterizationSupported", oop_rasterization_supported);
enumerator->EndAuxAttributes();
}
} // namespace angle
//
// 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.
//
#ifndef TEST_EXPECTATIONS_GPU_INFO_H_
#define TEST_EXPECTATIONS_GPU_INFO_H_
// Provides access to the GPU information for the system
// on which chrome is currently running.
#include <stdint.h>
#include <string>
#include <vector>
#include "GPUTestConfig.h"
#include "common/platform.h"
#if defined(USE_X11)
typedef unsigned long VisualID;
#endif
namespace angle
{
// These values are persisted to logs. Entries should not be renumbered and
// numeric values should never be reused.
enum class GpuSeriesType
{
kUnknown = 0,
// Intel 6th gen
kIntelSandyBridge = 1,
// Intel 7th gen
kIntelValleyView = 2, // BayTrail
kIntelIvyBridge = 3,
kIntelHaswell = 4,
// Intel 8th gen
kIntelCherryView = 5, // Braswell
kIntelBroadwell = 6,
// Intel 9th gen
kIntelApolloLake = 7,
kIntelSkyLake = 8,
kIntelGeminiLake = 9,
kIntelKabyLake = 10,
kIntelCoffeeLake = 11,
// Please also update |gpu_series_map| in process_json.py.
kMaxValue = kIntelCoffeeLake,
};
// Video profile. This *must* match media::VideoCodecProfile.
enum VideoCodecProfile
{
VIDEO_CODEC_PROFILE_UNKNOWN = -1,
VIDEO_CODEC_PROFILE_MIN = VIDEO_CODEC_PROFILE_UNKNOWN,
H264PROFILE_BASELINE = 0,
H264PROFILE_MAIN,
H264PROFILE_EXTENDED,
H264PROFILE_HIGH,
H264PROFILE_HIGH10PROFILE,
H264PROFILE_HIGH422PROFILE,
H264PROFILE_HIGH444PREDICTIVEPROFILE,
H264PROFILE_SCALABLEBASELINE,
H264PROFILE_SCALABLEHIGH,
H264PROFILE_STEREOHIGH,
H264PROFILE_MULTIVIEWHIGH,
VP8PROFILE_ANY,
VP9PROFILE_PROFILE0,
VP9PROFILE_PROFILE1,
VP9PROFILE_PROFILE2,
VP9PROFILE_PROFILE3,
HEVCPROFILE_MAIN,
HEVCPROFILE_MAIN10,
HEVCPROFILE_MAIN_STILL_PICTURE,
DOLBYVISION_PROFILE0,
DOLBYVISION_PROFILE4,
DOLBYVISION_PROFILE5,
DOLBYVISION_PROFILE7,
THEORAPROFILE_ANY,
AV1PROFILE_PROFILE_MAIN,
AV1PROFILE_PROFILE_HIGH,
AV1PROFILE_PROFILE_PRO,
VIDEO_CODEC_PROFILE_MAX = AV1PROFILE_PROFILE_PRO,
};
// Specification of a decoding profile supported by a hardware decoder.
struct VideoDecodeAcceleratorSupportedProfile
{
VideoCodecProfile profile;
gfx::Size max_resolution;
gfx::Size min_resolution;
bool encrypted_only;
};
using VideoDecodeAcceleratorSupportedProfiles = std::vector<VideoDecodeAcceleratorSupportedProfile>;
struct VideoDecodeAcceleratorCapabilities
{
VideoDecodeAcceleratorCapabilities();
VideoDecodeAcceleratorCapabilities(const VideoDecodeAcceleratorCapabilities &other);
~VideoDecodeAcceleratorCapabilities();
VideoDecodeAcceleratorSupportedProfiles supported_profiles;
uint32_t flags;
};
// Specification of an encoding profile supported by a hardware encoder.
struct VideoEncodeAcceleratorSupportedProfile
{
VideoCodecProfile profile;
gfx::Size max_resolution;
uint32_t max_framerate_numerator;
uint32_t max_framerate_denominator;
};
using VideoEncodeAcceleratorSupportedProfiles = std::vector<VideoEncodeAcceleratorSupportedProfile>;
enum class ImageDecodeAcceleratorType
{
kJpeg = 0,
kUnknown = 1,
kMaxValue = kUnknown,
};
enum class ImageDecodeAcceleratorSubsampling
{
k420 = 0,
k422 = 1,
kMaxValue = k422,
};
// Specification of an image decoding profile supported by a hardware decoder.
struct ImageDecodeAcceleratorSupportedProfile
{
ImageDecodeAcceleratorSupportedProfile();
ImageDecodeAcceleratorSupportedProfile(const ImageDecodeAcceleratorSupportedProfile &other);
ImageDecodeAcceleratorSupportedProfile(ImageDecodeAcceleratorSupportedProfile &&other);
~ImageDecodeAcceleratorSupportedProfile();
ImageDecodeAcceleratorSupportedProfile &operator=(
const ImageDecodeAcceleratorSupportedProfile &other);
ImageDecodeAcceleratorSupportedProfile &operator=(
ImageDecodeAcceleratorSupportedProfile &&other);
// Fields common to all image types.
// Type of image to which this profile applies, e.g., JPEG.
ImageDecodeAcceleratorType image_type;
// Minimum and maximum supported pixel dimensions of the encoded image.
gfx::Size min_encoded_dimensions;
gfx::Size max_encoded_dimensions;
// Fields specific to |image_type| == kJpeg.
// The supported chroma subsampling formats, e.g. 4:2:0.
std::vector<ImageDecodeAcceleratorSubsampling> subsamplings;
};
using ImageDecodeAcceleratorSupportedProfiles = std::vector<ImageDecodeAcceleratorSupportedProfile>;
#if defined(ANGLE_PLATFORM_WINDOWS)
// Common overlay formats that we're interested in. Must match the OverlayFormat
// enum in //tools/metrics/histograms/enums.xml. Mapped to corresponding DXGI
// formats in DirectCompositionSurfaceWin.
enum class OverlayFormat
{
kBGRA = 0,
kYUY2 = 1,
kNV12 = 2,
kMaxValue = kNV12
};
const char *OverlayFormatToString(OverlayFormat format);
struct OverlayCapability
{
OverlayFormat format;
bool is_scaling_supported;
bool operator==(const OverlayCapability &other) const;
};
using OverlayCapabilities = std::vector<OverlayCapability>;
struct Dx12VulkanVersionInfo
{
bool IsEmpty() const { return !d3d12_feature_level && !vulkan_version; }
// True if the GPU driver supports DX12.
bool supports_dx12 = false;
// True if the GPU driver supports Vulkan.
bool supports_vulkan = false;
// The supported d3d feature level in the gpu driver;
uint32_t d3d12_feature_level = 0;
// The support Vulkan API version in the gpu driver;
uint32_t vulkan_version = 0;
};
#endif
struct GPUInfo
{
struct GPUDevice
{
GPUDevice();
GPUDevice(const GPUDevice &other);
GPUDevice(GPUDevice &&other) noexcept;
~GPUDevice() noexcept;
GPUDevice &operator=(const GPUDevice &other);
GPUDevice &operator=(GPUDevice &&other) noexcept;
// The DWORD (uint32_t) representing the graphics card vendor id.
uint32_t vendor_id;
// The DWORD (uint32_t) representing the graphics card device id.
// Device ids are unique to vendor, not to one another.
uint32_t device_id;
// Whether this GPU is the currently used one.
// Currently this field is only supported and meaningful on OS X.
bool active;
// The strings that describe the GPU.
// In Linux these strings are obtained through libpci.
// In Win/MacOSX, these two strings are not filled at the moment.
// In Android, these are respectively GL_VENDOR and GL_RENDERER.
std::string vendor_string;
std::string device_string;
std::string driver_vendor;
std::string driver_version;
std::string driver_date;
// NVIDIA CUDA compute capability, major version. 0 if undetermined. Can be
// used to determine the hardware generation that the GPU belongs to.
int cuda_compute_capability_major;
};
GPUInfo();
GPUInfo(const GPUInfo &other);
~GPUInfo();
// The currently active gpu.
GPUDevice &active_gpu();
const GPUDevice &active_gpu() const;
bool IsInitialized() const;
// The amount of time taken to get from the process starting to the message
// loop being pumped.
int64_t initialization_time;
// Computer has NVIDIA Optimus
bool optimus;
// Computer has AMD Dynamic Switchable Graphics
bool amd_switchable;
// Primary GPU, for exmaple, the discrete GPU in a dual GPU machine.
GPUDevice gpu;
// Secondary GPUs, for example, the integrated GPU in a dual GPU machine.
std::vector<GPUDevice> secondary_gpus;
// The version of the pixel/fragment shader used by the gpu.
std::string pixel_shader_version;
// The version of the vertex shader used by the gpu.
std::string vertex_shader_version;
// The maximum multisapling sample count, either through ES3 or
// EXT_multisampled_render_to_texture MSAA.
std::string max_msaa_samples;
// The machine model identifier. They can contain any character, including
// whitespaces. Currently it is supported on MacOSX and Android.
// Android examples: "Naxus 5", "XT1032".
// On MacOSX, the version is stripped out of the model identifier, for
// example, the original identifier is "MacBookPro7,2", and we put
// "MacBookPro" as machine_model_name, and "7.2" as machine_model_version.
std::string machine_model_name;
// The version of the machine model. Currently it is supported on MacOSX.
// See machine_model_name's comment.
std::string machine_model_version;
// The GL_VERSION string.
std::string gl_version;
// The GL_VENDOR string.
std::string gl_vendor;
// The GL_RENDERER string.
std::string gl_renderer;
// The GL_EXTENSIONS string.
std::string gl_extensions;
// GL window system binding vendor. "" if not available.
std::string gl_ws_vendor;
// GL window system binding version. "" if not available.
std::string gl_ws_version;
// GL window system binding extensions. "" if not available.
std::string gl_ws_extensions;
// GL reset notification strategy as defined by GL_ARB_robustness. 0 if GPU
// reset detection or notification not available.
uint32_t gl_reset_notification_strategy;
bool software_rendering;
// Whether the driver uses direct rendering. True on most platforms, false on
// X11 when using remote X.
bool direct_rendering;
// Whether the gpu process is running in a sandbox.
bool sandboxed;
// True if the GPU is running in the browser process instead of its own.
bool in_process_gpu;
// True if the GPU process is using the passthrough command decoder.
bool passthrough_cmd_decoder;
// True only on android when extensions for threaded mailbox sharing are
// present. Threaded mailbox sharing is used on Android only, so this check
// is only implemented on Android.
bool can_support_threaded_texture_mailbox = false;
#if defined(ANGLE_PLATFORM_WINDOWS)
// True if we use direct composition surface on Windows.
bool direct_composition = false;
// True if we use direct composition surface overlays on Windows.
bool supports_overlays = false;
OverlayCapabilities overlay_capabilities;
// The information returned by the DirectX Diagnostics Tool.
DxDiagNode dx_diagnostics;
Dx12VulkanVersionInfo dx12_vulkan_version_info;
#endif
VideoDecodeAcceleratorCapabilities video_decode_accelerator_capabilities;
VideoEncodeAcceleratorSupportedProfiles video_encode_accelerator_supported_profiles;
bool jpeg_decode_accelerator_supported;
ImageDecodeAcceleratorSupportedProfiles image_decode_accelerator_supported_profiles;
#if defined(USE_X11)
VisualID system_visual;
VisualID rgba_visual;
#endif
bool oop_rasterization_supported;
// Note: when adding new members, please remember to update EnumerateFields
// in gpu_info.cc.
// In conjunction with EnumerateFields, this allows the embedder to
// enumerate the values in this structure without having to embed
// references to its specific member variables. This simplifies the
// addition of new fields to this type.
class Enumerator
{
public:
// The following methods apply to the "current" object. Initially this
// is the root object, but calls to BeginGPUDevice/EndGPUDevice and
// BeginAuxAttributes/EndAuxAttributes change the object to which these
// calls should apply.
virtual void AddInt64(const char *name, int64_t value) = 0;
virtual void AddInt(const char *name, int value) = 0;
virtual void AddString(const char *name, const std::string &value) = 0;
virtual void AddBool(const char *name, bool value) = 0;
virtual void AddTimeDeltaInSeconds(const char *name, const int64_t &value) = 0;
// Markers indicating that a GPUDevice is being described.
virtual void BeginGPUDevice() = 0;
virtual void EndGPUDevice() = 0;
// Markers indicating that a VideoDecodeAcceleratorSupportedProfile is
// being described.
virtual void BeginVideoDecodeAcceleratorSupportedProfile() = 0;
virtual void EndVideoDecodeAcceleratorSupportedProfile() = 0;
// Markers indicating that a VideoEncodeAcceleratorSupportedProfile is
// being described.
virtual void BeginVideoEncodeAcceleratorSupportedProfile() = 0;
virtual void EndVideoEncodeAcceleratorSupportedProfile() = 0;
// Markers indicating that an ImageDecodeAcceleratorSupportedProfile is
// being described.
virtual void BeginImageDecodeAcceleratorSupportedProfile() = 0;
virtual void EndImageDecodeAcceleratorSupportedProfile() = 0;
// Markers indicating that "auxiliary" attributes of the GPUInfo
// (according to the DevTools protocol) are being described.
virtual void BeginAuxAttributes() = 0;
virtual void EndAuxAttributes() = 0;
virtual void BeginOverlayCapability() = 0;
virtual void EndOverlayCapability() = 0;
virtual void BeginDx12VulkanVersionInfo() = 0;
virtual void EndDx12VulkanVersionInfo() = 0;
protected:
virtual ~Enumerator() = default;
};
// Outputs the fields in this structure to the provided enumerator.
void EnumerateFields(Enumerator *enumerator) const;
};
} // namespace angle
#endif // TEST_EXPECTATIONS_GPU_INFO_H_
//#if
// Copyright 2019 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
......@@ -7,404 +6,564 @@
#include "GPUTestConfig.h"
#include <stddef.h>
#include <stdint.h>
#include <iostream>
#include "GPUInfo.h"
#include "GPUTestExpectationsParser.h"
#include "common/angleutils.h"
#include "common/debug.h"
#include "common/platform.h"
#include "common/string_utils.h"
#include "gpu_info_util/SystemInfo.h"
#if defined(ANGLE_PLATFORM_APPLE)
# include "GPUTestConfig_mac.h"
#endif
#if !defined(ANGLE_PLATFORM_ANDROID)
# include "gpu_info_util/SystemInfo.h"
#endif
#if defined(ANGLE_PLATFORM_WINDOWS)
namespace base
{
namespace
namespace angle
{
// Disable the deprecated function warning for GetVersionEx
# pragma warning(disable : 4996)
class SysInfo
namespace
{
public:
static void OperatingSystemVersionNumbers(int32_t *major_version,
int32_t *minor_version,
int32_t *bugfix_version);
};
// static
void SysInfo::OperatingSystemVersionNumbers(int32_t *major_version,
int32_t *minor_version,
int32_t *bugfix_version)
// Generic function call to get the OS version information from any platform
// defined below. This function will also cache the OS version info in static
// variables.
inline bool OperatingSystemVersionNumbers(int32_t *majorVersion, int32_t *minorVersion)
{
OSVERSIONINFOEX version_info = {sizeof version_info};
::GetVersionEx(reinterpret_cast<OSVERSIONINFO *>(&version_info));
*major_version = version_info.dwMajorVersion;
*minor_version = version_info.dwMinorVersion;
*bugfix_version = version_info.dwBuildNumber;
}
static int32_t sSavedMajorVersion = -1;
static int32_t sSavedMinorVersion = -1;
bool ret = false;
if (sSavedMajorVersion == -1 || sSavedMinorVersion == -1)
{
#if defined(ANGLE_PLATFORM_WINDOWS)
OSVERSIONINFOEX version_info = {sizeof version_info};
::GetVersionEx(reinterpret_cast<OSVERSIONINFO *>(&version_info));
sSavedMajorVersion = version_info.dwMajorVersion;
*majorVersion = sSavedMajorVersion;
sSavedMinorVersion = version_info.dwMinorVersion;
*minorVersion = sSavedMinorVersion;
ret = true;
} // anonymous namespace
} // namespace base
#elif defined(ANGLE_PLATFORM_APPLE)
GetOperatingSystemVersionNumbers(&sSavedMajorVersion, &sSavedMinorVersion);
*majorVersion = sSavedMajorVersion;
*minorVersion = sSavedMinorVersion;
ret = true;
#endif // defined(ANGLE_PLATFORM_WINDOWS)
#else
ret = false;
#endif
}
else
{
ret = true;
}
*majorVersion = sSavedMajorVersion;
*minorVersion = sSavedMinorVersion;
return ret;
}
namespace angle
// Check if the OS is any version of Windows
inline bool IsWin()
{
#if defined(ANGLE_PLATFORM_WINDOWS)
return true;
#else
return false;
#endif
}
namespace
// Check if the OS is a specific major version of windows.
inline bool IsWinVersion(const int32_t majorVersion)
{
if (IsWin())
{
int32_t currentMajorVersion = 0;
int32_t currentMinorVersion = 0;
if (OperatingSystemVersionNumbers(&currentMajorVersion, &currentMinorVersion))
{
if (currentMajorVersion == majorVersion)
{
return true;
}
}
}
return false;
}
GPUTestConfig::OS GetCurrentOS()
// Check if the OS is a specific major and minor version of windows.
inline bool IsWinVersion(const int32_t majorVersion, const int32_t minorVersion)
{
#if defined(ANGLE_PLATFORM_LINUX)
return GPUTestConfig::kOsLinux;
#elif defined(ANGLE_PLATFORM_WINDOWS)
int32_t major_version = 0;
int32_t minor_version = 0;
int32_t bugfix_version = 0;
base::SysInfo::OperatingSystemVersionNumbers(&major_version, &minor_version, &bugfix_version);
if (major_version == 5)
return GPUTestConfig::kOsWinXP;
if (major_version == 6 && minor_version == 0)
return GPUTestConfig::kOsWinVista;
if (major_version == 6 && minor_version == 1)
return GPUTestConfig::kOsWin7;
if (major_version == 6 && (minor_version == 2 || minor_version == 3))
return GPUTestConfig::kOsWin8;
if (major_version == 10)
return GPUTestConfig::kOsWin10;
#elif defined(ANGLE_PLATFORM_APPLE)
int32_t major_version = 0;
int32_t minor_version = 0;
int32_t bugfix_version = 0;
angle::GetOperatingSystemVersionNumbers(&major_version, &minor_version, &bugfix_version);
if (major_version == 10)
if (IsWin())
{
switch (minor_version)
int32_t currentMajorVersion = 0;
int32_t currentMinorVersion = 0;
if (OperatingSystemVersionNumbers(&currentMajorVersion, &currentMinorVersion))
{
case 5:
return GPUTestConfig::kOsMacLeopard;
case 6:
return GPUTestConfig::kOsMacSnowLeopard;
case 7:
return GPUTestConfig::kOsMacLion;
case 8:
return GPUTestConfig::kOsMacMountainLion;
case 9:
return GPUTestConfig::kOsMacMavericks;
case 10:
return GPUTestConfig::kOsMacYosemite;
case 11:
return GPUTestConfig::kOsMacElCapitan;
case 12:
return GPUTestConfig::kOsMacSierra;
case 13:
return GPUTestConfig::kOsMacHighSierra;
case 14:
return GPUTestConfig::kOsMacMojave;
if (currentMajorVersion == majorVersion && currentMinorVersion == minorVersion)
{
return true;
}
}
}
#elif defined(ANGLE_PLATFORM_ANDROID)
return GPUTestConfig::kOsAndroid;
#elif defined(ANGLE_PLATFORM_FUCHSIA)
return GPUTestConfig::kOsFuchsia;
#endif
return GPUTestConfig::kOsUnknown;
return false;
}
#if !defined(ANGLE_PLATFORM_ANDROID)
bool CollectBasicGraphicsInfo(GPUInfo *gpu_info)
// Check if the OS is Windows XP
inline bool IsWinXP()
{
angle::SystemInfo info;
if (!angle::GetSystemInfo(&info))
if (IsWinVersion(5))
{
return false;
return true;
}
const angle::GPUDeviceInfo &gpu = info.gpus[info.primaryGPUIndex];
gpu_info->gpu.vendor_id = gpu.vendorId;
gpu_info->gpu.device_id = gpu.deviceId;
gpu_info->gpu.active = true;
return true;
return false;
}
#else
bool CollectBasicGraphicsInfo(GPUInfo *gpu_info)
// Check if the OS is Windows Vista
inline bool IsWinVista()
{
gpu_info->gpu.vendor_id = 0;
gpu_info->gpu.device_id = 0;
gpu_info->gpu.active = true;
if (IsWinVersion(6, 0))
{
return true;
}
return false;
}
#endif // defined(ANGLE_PLATFORM_ANDROID)
} // namespace
GPUTestConfig::GPUTestConfig()
: validate_gpu_info_(true),
os_(kOsUnknown),
gpu_device_id_(0),
build_type_(kBuildTypeUnknown),
api_(kAPIUnknown)
{}
GPUTestConfig::GPUTestConfig(const GPUTestConfig &other) = default;
GPUTestConfig::~GPUTestConfig() = default;
// Check if the OS is Windows 7
inline bool IsWin7()
{
if (IsWinVersion(6, 1))
{
return true;
}
return false;
}
void GPUTestConfig::set_os(int32_t os)
// Check if the OS is Windows 8
inline bool IsWin8()
{
ASSERT((0) == (os & ~(kOsAndroid | kOsWin | kOsMac | kOsLinux | kOsFuchsia)));
os_ = os;
if (IsWinVersion(6, 2) || IsWinVersion(6, 3))
{
return true;
}
return false;
}
void GPUTestConfig::AddGPUVendor(uint32_t gpu_vendor)
// Check if the OS is Windows 10
inline bool IsWin10()
{
ASSERT((0u) != (gpu_vendor));
for (size_t i = 0; i < gpu_vendor_.size(); ++i)
ASSERT((gpu_vendor_[i]) != (gpu_vendor));
gpu_vendor_.push_back(gpu_vendor);
if (IsWinVersion(10))
{
return true;
}
return false;
}
void GPUTestConfig::set_gpu_device_id(uint32_t id)
// Check if the OS is any version of OSX
inline bool IsMac()
{
gpu_device_id_ = id;
#if defined(ANGLE_PLATFORM_APPLE)
return true;
#else
return false;
#endif
}
void GPUTestConfig::set_build_type(int32_t build_type)
// Check if the OS is a specific major and minor version of OSX
inline bool IsMacVersion(const int32_t majorVersion, const int32_t minorVersion)
{
ASSERT((0) == (build_type & ~(kBuildTypeRelease | kBuildTypeDebug)));
build_type_ = build_type;
if (IsMac())
{
int32_t currentMajorVersion = 0;
int32_t currentMinorVersion = 0;
if (OperatingSystemVersionNumbers(&currentMajorVersion, &currentMinorVersion))
{
if (currentMajorVersion == majorVersion && currentMinorVersion == minorVersion)
{
return true;
}
}
}
return false;
}
void GPUTestConfig::set_api(int32_t api)
// Check if the OS is OSX Leopard
inline bool IsMacLeopard()
{
ASSERT((0) == (api & ~(kAPID3D9 | kAPID3D11 | kAPIGLDesktop | kAPIGLES | kAPIVulkan)));
api_ = api;
if (IsMacVersion(10, 5))
{
return true;
}
return false;
}
bool GPUTestConfig::IsValid() const
// Check if the OS is OSX Snow Leopard
inline bool IsMacSnowLeopard()
{
if (!validate_gpu_info_)
if (IsMacVersion(10, 6))
{
return true;
if (gpu_device_id_ != 0 && (gpu_vendor_.size() != 1 || gpu_vendor_[0] == 0))
return false;
return true;
}
return false;
}
bool GPUTestConfig::OverlapsWith(const GPUTestConfig &config) const
// Check if the OS is OSX Lion
inline bool IsMacLion()
{
ASSERT(IsValid());
ASSERT(config.IsValid());
if (config.os_ != kOsUnknown && os_ != kOsUnknown && (os_ & config.os_) == 0)
return false;
if (config.gpu_vendor_.size() > 0 && gpu_vendor_.size() > 0)
if (IsMacVersion(10, 7))
{
bool shared = false;
for (size_t i = 0; i < config.gpu_vendor_.size() && !shared; ++i)
{
for (size_t j = 0; j < gpu_vendor_.size(); ++j)
{
if (config.gpu_vendor_[i] == gpu_vendor_[j])
{
shared = true;
break;
}
}
}
if (!shared)
return false;
return true;
}
if (config.gpu_device_id_ != 0 && gpu_device_id_ != 0 &&
gpu_device_id_ != config.gpu_device_id_)
return false;
if (config.build_type_ != kBuildTypeUnknown && build_type_ != kBuildTypeUnknown &&
(build_type_ & config.build_type_) == 0)
return false;
if (config.api() != kAPIUnknown && api_ != kAPIUnknown && api_ != config.api_)
return false;
return true;
return false;
}
void GPUTestConfig::DisableGPUInfoValidation()
// Check if the OS is OSX Mountain Lion
inline bool IsMacMountainLion()
{
validate_gpu_info_ = false;
if (IsMacVersion(10, 8))
{
return true;
}
return false;
}
void GPUTestConfig::ClearGPUVendor()
// Check if the OS is OSX Mavericks
inline bool IsMacMavericks()
{
gpu_vendor_.clear();
if (IsMacVersion(10, 9))
{
return true;
}
return false;
}
GPUTestBotConfig::~GPUTestBotConfig() = default;
// Check if the OS is OSX Yosemite
inline bool IsMacYosemite()
{
if (IsMacVersion(10, 10))
{
return true;
}
return false;
}
void GPUTestBotConfig::AddGPUVendor(uint32_t gpu_vendor)
// Check if the OS is OSX El Capitan
inline bool IsMacElCapitan()
{
ASSERT((0u) == (GPUTestConfig::gpu_vendor().size()));
GPUTestConfig::AddGPUVendor(gpu_vendor);
if (IsMacVersion(10, 11))
{
return true;
}
return false;
}
bool GPUTestBotConfig::SetGPUInfo(const GPUInfo &gpu_info)
// Check if the OS is OSX Sierra
inline bool IsMacSierra()
{
ASSERT(validate_gpu_info_);
if (gpu_info.gpu.device_id == 0 || gpu_info.gpu.vendor_id == 0)
return false;
ClearGPUVendor();
AddGPUVendor(gpu_info.gpu.vendor_id);
set_gpu_device_id(gpu_info.gpu.device_id);
return true;
if (IsMacVersion(10, 12))
{
return true;
}
return false;
}
bool GPUTestBotConfig::IsValid() const
{
switch (os())
{
case kOsWinXP:
case kOsWinVista:
case kOsWin7:
case kOsWin8:
case kOsWin10:
case kOsMacLeopard:
case kOsMacSnowLeopard:
case kOsMacLion:
case kOsMacMountainLion:
case kOsMacMavericks:
case kOsMacYosemite:
case kOsMacElCapitan:
case kOsMacSierra:
case kOsMacHighSierra:
case kOsMacMojave:
case kOsLinux:
case kOsAndroid:
case kOsFuchsia:
break;
default:
return false;
}
if (validate_gpu_info_)
{
if (gpu_vendor().size() != 1 || gpu_vendor()[0] == 0)
return false;
if (gpu_device_id() == 0)
return false;
}
switch (build_type())
{
case kBuildTypeRelease:
case kBuildTypeDebug:
break;
default:
return false;
// Check if the OS is OSX High Sierra
inline bool IsMacHighSierra()
{
if (IsMacVersion(10, 13))
{
return true;
}
return true;
return false;
}
bool GPUTestBotConfig::Matches(const GPUTestConfig &config) const
// Check if the OS is OSX Mojave
inline bool IsMacMojave()
{
ASSERT(IsValid());
ASSERT(config.IsValid());
if (config.os() != kOsUnknown && (os() & config.os()) == 0)
return false;
if (config.gpu_vendor().size() > 0)
if (IsMacVersion(10, 14))
{
bool contained = false;
for (size_t i = 0; i < config.gpu_vendor().size(); ++i)
{
if (!gpu_vendor().empty() && config.gpu_vendor()[i] == gpu_vendor()[0])
{
contained = true;
break;
}
}
if (!contained)
return false;
return true;
}
if (config.gpu_device_id() != 0 && gpu_device_id() != config.gpu_device_id())
return false;
if (config.build_type() != kBuildTypeUnknown && (build_type() & config.build_type()) == 0)
return false;
if (config.api() != 0 && (api() & config.api()) == 0)
return false;
return true;
return false;
}
bool GPUTestBotConfig::Matches(const std::string &config_data) const
// Check if the OS is any version of Linux
inline bool IsLinux()
{
GPUTestExpectationsParser parser;
GPUTestConfig config;
#if defined(ANGLE_PLATFORM_LINUX)
return true;
#else
return false;
#endif
}
if (!parser.ParseConfig(config_data, &config))
return false;
return Matches(config);
// Check if the OS is any version of Android
inline bool IsAndroid()
{
#if defined(ANGLE_PLATFORM_ANDROID)
return true;
#else
return false;
#endif
}
bool GPUTestBotConfig::LoadCurrentConfig(const GPUInfo *gpu_info)
// Generic function call to populate the SystemInfo struct. This function will
// also cache the SystemInfo struct for future calls. Returns false if the
// struct was not fully populated. Guaranteed to set sysInfo to a valid pointer
inline bool GetGPUTestSystemInfo(SystemInfo **sysInfo)
{
bool rt;
if (!gpu_info)
static SystemInfo *sSystemInfo = nullptr;
static bool sPopulated = false;
if (sSystemInfo == nullptr)
{
GPUInfo my_gpu_info;
if (!CollectBasicGraphicsInfo(&my_gpu_info))
sSystemInfo = new SystemInfo;
if (!GetSystemInfo(sSystemInfo))
{
std::cerr << "Fail to identify GPU\n";
DisableGPUInfoValidation();
rt = true;
std::cout << "Error populating SystemInfo for dEQP tests." << std::endl;
}
else
{
rt = SetGPUInfo(my_gpu_info);
sPopulated = true;
}
}
*sysInfo = sSystemInfo;
ASSERT(*sysInfo != nullptr);
return sPopulated;
}
// Get the active GPUDeviceInfo from the SystemInfo struct.
// Returns false if devInfo is not guaranteed to be set to the active device.
inline bool GetActiveGPU(GPUDeviceInfo **devInfo)
{
SystemInfo *systemInfo = nullptr;
GetGPUTestSystemInfo(&systemInfo);
if (systemInfo->gpus.size() <= 0)
{
return false;
}
uint32_t index = 0;
// See if the activeGPUIndex was set first
if (systemInfo->activeGPUIndex != -1)
{
index = systemInfo->activeGPUIndex;
}
// Else fallback to the primaryGPUIndex
else if (systemInfo->primaryGPUIndex != -1)
{
index = systemInfo->primaryGPUIndex;
}
ASSERT(index < systemInfo->gpus.size());
*devInfo = &(systemInfo->gpus[index]);
return true;
}
// Get the vendor ID of the active GPU from the SystemInfo struct.
// Returns 0 if there is an error.
inline VendorID GetActiveGPUVendorID()
{
GPUDeviceInfo *activeGPU = nullptr;
if (GetActiveGPU(&activeGPU))
{
return activeGPU->vendorId;
}
else
{
rt = SetGPUInfo(*gpu_info);
return static_cast<VendorID>(0);
}
set_os(GetCurrentOS());
if (os() == kOsUnknown)
}
// Get the device ID of the active GPU from the SystemInfo struct.
// Returns 0 if there is an error.
inline DeviceID GetActiveGPUDeviceID()
{
GPUDeviceInfo *activeGPU = nullptr;
if (GetActiveGPU(&activeGPU))
{
std::cerr << "Unknown OS\n";
rt = false;
return activeGPU->deviceId;
}
#if defined(NDEBUG)
set_build_type(kBuildTypeRelease);
else
{
return static_cast<DeviceID>(0);
}
}
// Check whether the active GPU is NVIDIA.
inline bool IsNVIDIA()
{
return angle::IsNVIDIA(GetActiveGPUVendorID());
}
// Check whether the active GPU is AMD.
inline bool IsAMD()
{
return angle::IsAMD(GetActiveGPUVendorID());
}
// Check whether the active GPU is Intel.
inline bool IsIntel()
{
return angle::IsIntel(GetActiveGPUVendorID());
}
// Check whether the active GPU is VMWare.
inline bool IsVMWare()
{
return angle::IsVMWare(GetActiveGPUVendorID());
}
// Check whether this is a debug build.
inline bool IsDebug()
{
#if !defined(NDEBUG)
return true;
#else
set_build_type(kBuildTypeDebug);
return false;
#endif
return rt;
}
// static
bool GPUTestBotConfig::CurrentConfigMatches(const std::string &config_data)
// Check whether this is a release build.
inline bool IsRelease()
{
GPUTestBotConfig my_config;
if (!my_config.LoadCurrentConfig(nullptr))
return false;
return my_config.Matches(config_data);
return !IsDebug();
}
// static
bool GPUTestBotConfig::CurrentConfigMatches(const std::vector<std::string> &configs)
// Check whether the system is a specific Android device based on the name.
inline bool IsAndroidDevice(const std::string &deviceName)
{
GPUTestBotConfig my_config;
if (!my_config.LoadCurrentConfig(nullptr))
if (!IsAndroid())
{
return false;
for (size_t i = 0; i < configs.size(); ++i)
}
SystemInfo *systemInfo = nullptr;
GetGPUTestSystemInfo(&systemInfo);
if (systemInfo->machineModelName == deviceName)
{
if (my_config.Matches(configs[i]))
return true;
return true;
}
return false;
}
// static
bool GPUTestBotConfig::GpuBlacklistedOnBot()
// Check whether the system is a Nexus 5X device.
inline bool IsNexus5X()
{
return false;
return IsAndroidDevice("Nexus 5X");
}
// Check whether the system is a Pixel 2 device.
inline bool IsPixel2()
{
return IsAndroidDevice("Pixel 2");
}
// Check whether the active GPU is a specific device based on the string device ID.
inline bool IsDeviceIdGPU(const std::string &gpuDeviceId)
{
uint32_t deviceId = 0;
if (!HexStringToUInt(gpuDeviceId, &deviceId) || deviceId == 0)
{
// PushErrorMessage(kErrorMessage[kErrorEntryWithGpuDeviceIdConflicts], line_number);
return false;
}
return (deviceId == GetActiveGPUDeviceID());
}
// Check whether the active GPU is a NVIDIA Quadro P400
inline bool IsNVIDIAQuadroP400()
{
if (!IsNVIDIA())
{
return false;
}
return IsDeviceIdGPU("0x1CB3");
}
// Check whether the backend API has been set to D3D9 in the constructor
inline bool IsD3D9(const GPUTestConfig::API &api)
{
return (api == GPUTestConfig::kAPID3D9);
}
// Check whether the backend API has been set to D3D11 in the constructor
inline bool IsD3D11(const GPUTestConfig::API &api)
{
return (api == GPUTestConfig::kAPID3D11);
}
// Check whether the backend API has been set to OpenGL in the constructor
inline bool IsGLDesktop(const GPUTestConfig::API &api)
{
return (api == GPUTestConfig::kAPIGLDesktop);
}
// Check whether the backend API has been set to OpenGLES in the constructor
inline bool IsGLES(const GPUTestConfig::API &api)
{
return (api == GPUTestConfig::kAPIGLES);
}
// Check whether the backend API has been set to Vulkan in the constructor
inline bool IsVulkan(const GPUTestConfig::API &api)
{
return (api == GPUTestConfig::kAPIVulkan);
}
} // anonymous namespace
// Load all conditions in the constructor since this data will not change during a test set.
GPUTestConfig::GPUTestConfig()
{
mConditions[kConditionNone] = false;
mConditions[kConditionWinXP] = IsWinXP();
mConditions[kConditionWinVista] = IsWinVista();
mConditions[kConditionWin7] = IsWin7();
mConditions[kConditionWin8] = IsWin8();
mConditions[kConditionWin10] = IsWin10();
mConditions[kConditionWin] = IsWin();
mConditions[kConditionMacLeopard] = IsMacLeopard();
mConditions[kConditionMacSnowLeopard] = IsMacSnowLeopard();
mConditions[kConditionMacLion] = IsMacLion();
mConditions[kConditionMacMountainLion] = IsMacMountainLion();
mConditions[kConditionMacMavericks] = IsMacMavericks();
mConditions[kConditionMacYosemite] = IsMacYosemite();
mConditions[kConditionMacElCapitan] = IsMacElCapitan();
mConditions[kConditionMacSierra] = IsMacSierra();
mConditions[kConditionMacHighSierra] = IsMacHighSierra();
mConditions[kConditionMacMojave] = IsMacMojave();
mConditions[kConditionMac] = IsMac();
mConditions[kConditionLinux] = IsLinux();
mConditions[kConditionAndroid] = IsAndroid();
mConditions[kConditionNVIDIA] = IsNVIDIA();
mConditions[kConditionAMD] = IsAMD();
mConditions[kConditionIntel] = IsIntel();
mConditions[kConditionVMWare] = IsVMWare();
mConditions[kConditionRelease] = IsRelease();
mConditions[kConditionDebug] = IsDebug();
// If no API provided, pass these conditions by default
mConditions[kConditionD3D9] = true;
mConditions[kConditionD3D11] = true;
mConditions[kConditionGLDesktop] = true;
mConditions[kConditionGLES] = true;
mConditions[kConditionVulkan] = true;
mConditions[kConditionNexus5X] = IsNexus5X();
mConditions[kConditionPixel2] = IsPixel2();
mConditions[kConditionNVIDIAQuadroP400] = IsNVIDIAQuadroP400();
}
// If the constructor is passed an API, load those conditions as well
GPUTestConfig::GPUTestConfig(const API &api) : GPUTestConfig()
{
mConditions[kConditionD3D9] = IsD3D9(api);
mConditions[kConditionD3D11] = IsD3D11(api);
mConditions[kConditionGLDesktop] = IsGLDesktop(api);
mConditions[kConditionGLES] = IsGLES(api);
mConditions[kConditionVulkan] = IsVulkan(api);
}
// Return a const reference to the list of all pre-calculated conditions.
const GPUTestConfig::ConditionArray &GPUTestConfig::getConditions() const
{
return mConditions;
}
} // namespace angle
......@@ -7,166 +7,73 @@
#ifndef TEST_EXPECTATIONS_GPU_TEST_CONFIG_H_
#define TEST_EXPECTATIONS_GPU_TEST_CONFIG_H_
#include <stdint.h>
#include <iostream>
#include <string>
#include <vector>
#include "common/debug.h"
#include "common/platform.h"
#include "common/string_utils.h"
namespace gfx
{
class Size
{
public:
int width() const { return 0; }
int height() const { return 0; }
std::string ToString() const { return "0x0"; }
};
} // namespace gfx
struct DxDiagNode
{};
#include <array>
namespace angle
{
struct GPUInfo;
class GPUTestConfig
struct GPUTestConfig
{
public:
enum OS
enum API
{
kOsUnknown = 0,
kOsWinXP = 1 << 0,
kOsWinVista = 1 << 1,
kOsWin7 = 1 << 2,
kOsWin8 = 1 << 3,
kOsMacLeopard = 1 << 4,
kOsMacSnowLeopard = 1 << 5,
kOsMacLion = 1 << 6,
kOsMacMountainLion = 1 << 7,
kOsMacMavericks = 1 << 8,
kOsMacYosemite = 1 << 9,
kOsMacElCapitan = 1 << 10,
kOsMacSierra = 1 << 11,
kOsMacHighSierra = 1 << 12,
kOsMacMojave = 1 << 13,
kOsMac = kOsMacLeopard | kOsMacSnowLeopard | kOsMacLion | kOsMacMountainLion |
kOsMacMavericks | kOsMacYosemite | kOsMacElCapitan | kOsMacSierra |
kOsMacHighSierra | kOsMacMojave,
kOsLinux = 1 << 14,
kOsChromeOS = 1 << 15,
kOsAndroid = 1 << 16,
kOsWin10 = 1 << 17,
kOsWin = kOsWinXP | kOsWinVista | kOsWin7 | kOsWin8 | kOsWin10,
kOsFuchsia = 1 << 18,
kAPIUnknown = 0,
kAPID3D9,
kAPID3D11,
kAPIGLDesktop,
kAPIGLES,
kAPIVulkan,
};
enum BuildType
enum Condition
{
kBuildTypeUnknown = 0,
kBuildTypeRelease = 1 << 0,
kBuildTypeDebug = 1 << 1,
kConditionNone = 0,
kConditionWinXP,
kConditionWinVista,
kConditionWin7,
kConditionWin8,
kConditionWin10,
kConditionWin,
kConditionMacLeopard,
kConditionMacSnowLeopard,
kConditionMacLion,
kConditionMacMountainLion,
kConditionMacMavericks,
kConditionMacYosemite,
kConditionMacElCapitan,
kConditionMacSierra,
kConditionMacHighSierra,
kConditionMacMojave,
kConditionMac,
kConditionLinux,
kConditionAndroid,
kConditionNVIDIA,
kConditionAMD,
kConditionIntel,
kConditionVMWare,
kConditionRelease,
kConditionDebug,
kConditionD3D9,
kConditionD3D11,
kConditionGLDesktop,
kConditionGLES,
kConditionVulkan,
kConditionNexus5X,
kConditionPixel2,
kConditionNVIDIAQuadroP400,
kNumberOfConditions,
};
enum API
{
kAPIUnknown = 0,
kAPID3D9 = 1 << 0,
kAPID3D11 = 1 << 1,
kAPIGLDesktop = 1 << 2,
kAPIGLES = 1 << 3,
kAPIVulkan = 1 << 4,
};
typedef std::array<bool, GPUTestConfig::kNumberOfConditions> ConditionArray;
GPUTestConfig();
GPUTestConfig(const GPUTestConfig &other);
virtual ~GPUTestConfig();
void set_os(int32_t os);
void set_gpu_device_id(uint32_t id);
void set_build_type(int32_t build_type);
void set_api(int32_t api);
virtual void AddGPUVendor(uint32_t gpu_vendor);
int32_t os() const { return os_; }
const std::vector<uint32_t> &gpu_vendor() const { return gpu_vendor_; }
uint32_t gpu_device_id() const { return gpu_device_id_; }
int32_t build_type() const { return build_type_; }
int32_t api() const { return api_; }
// Check if the config is valid. For example, if gpu_device_id_ is set, but
// gpu_vendor_ is unknown, then it's invalid.
virtual bool IsValid() const;
// Check if two configs overlap, i.e., if there exists a config that matches
// both configs.
bool OverlapsWith(const GPUTestConfig &config) const;
GPUTestConfig(const API &api);
// Disable validation of GPU vendor and device ids.
void DisableGPUInfoValidation();
const GPUTestConfig::ConditionArray &getConditions() const;
protected:
void ClearGPUVendor();
// Indicates that the OS has the notion of a numeric GPU vendor and device id
// and this data should be validated.
bool validate_gpu_info_;
private:
// operating system.
int32_t os_;
// GPU vendor.
std::vector<uint32_t> gpu_vendor_;
// GPU device id (unique to each vendor).
uint32_t gpu_device_id_;
// Release or Debug.
int32_t build_type_;
// Back-end rendering APIs.
int32_t api_;
};
class GPUTestBotConfig : public GPUTestConfig
{
public:
GPUTestBotConfig() = default;
~GPUTestBotConfig() override;
// This should only be called when no gpu_vendor is added.
void AddGPUVendor(uint32_t gpu_vendor) override;
// Return false if gpu_info does not have valid vendor_id and device_id.
bool SetGPUInfo(const GPUInfo &gpu_info);
// Check if the bot config is valid, i.e., if it is one valid test-bot
// environment. For example, if a field is unknown, or if OS is not one
// fully defined OS, then it's valid.
bool IsValid() const override;
// Check if a bot config matches a test config, i.e., the test config is a
// superset of the bot config.
bool Matches(const GPUTestConfig &config) const;
bool Matches(const std::string &config_data) const;
// Setup the config with the current gpu testing environment.
// If gpu_info is nullptr, collect GPUInfo first.
bool LoadCurrentConfig(const GPUInfo *gpu_info);
// Check if this bot's config matches |config_data| or any of the |configs|.
static bool CurrentConfigMatches(const std::string &config_data);
static bool CurrentConfigMatches(const std::vector<std::string> &configs);
// Check if the bot has blacklisted all GPU features.
static bool GpuBlacklistedOnBot();
GPUTestConfig::ConditionArray mConditions;
};
} // namespace angle
......
......@@ -10,14 +10,12 @@
#ifndef TEST_EXPECTATIONS_GPU_TEST_CONFIG_MAC_H_
#define TEST_EXPECTATIONS_GPU_TEST_CONFIG_MAC_H_
#include "GPUInfo.h"
#include <stdint.h>
namespace angle
{
void GetOperatingSystemVersionNumbers(int32_t *major_version,
int32_t *minor_version,
int32_t *bugfix_version);
void GetOperatingSystemVersionNumbers(int32_t *majorVersion, int32_t *minorVersion);
} // namespace angle
......
......@@ -4,7 +4,7 @@
// found in the LICENSE file.
//
// GPUTestConfig_mac.mm:
// Helper functions for gpu_test_config that have to be compiled in ObjectiveC++
// Helper functions for GPUTestConfig that have to be compiled in ObjectiveC++
#include "GPUTestConfig_mac.h"
......@@ -21,28 +21,23 @@
namespace angle
{
void GetOperatingSystemVersionNumbers(int32_t *major_version,
int32_t *minor_version,
int32_t *bugfix_version)
void GetOperatingSystemVersionNumbers(int32_t *majorVersion, int32_t *minorVersion)
{
#if MAC_OS_X_VERSION_MIN_REQUIRED < MAC_OS_X_VERSION_10_8
Gestalt(gestaltSystemVersionMajor, reinterpret_cast<SInt32 *>(major_version));
Gestalt(gestaltSystemVersionMinor, reinterpret_cast<SInt32 *>(minor_version));
Gestalt(gestaltSystemVersionBugFix, reinterpret_cast<SInt32 *>(bugfix_version));
Gestalt(gestaltSystemVersionMajor, reinterpret_cast<SInt32 *>(majorVersion));
Gestalt(gestaltSystemVersionMinor, reinterpret_cast<SInt32 *>(minorVersion));
#else
if (@available(macOS 10.10, *))
{
NSOperatingSystemVersion version = [[NSProcessInfo processInfo] operatingSystemVersion];
*major_version = version.majorVersion;
*minor_version = version.minorVersion;
*bugfix_version = version.patchVersion;
*majorVersion = version.majorVersion;
*minorVersion = version.minorVersion;
}
else
{
// This can only happen on 10.9
*major_version = 10;
*minor_version = 9;
*bugfix_version = 0;
*majorVersion = 10;
*minorVersion = 9;
}
#endif
}
......
......@@ -10,44 +10,10 @@
#include <stdint.h>
#include "common/angleutils.h"
#include "common/debug.h"
#include "common/string_utils.h"
namespace base
{
namespace
{
bool StartsWithASCII(const std::string &str, const std::string &search, bool case_sensitive)
{
ASSERT(!case_sensitive);
return str.compare(0, search.length(), search) == 0;
}
template <class Char>
inline Char ToLowerASCII(Char c)
{
return (c >= 'A' && c <= 'Z') ? (c + ('a' - 'A')) : c;
}
template <typename Iter>
static inline bool DoLowerCaseEqualsASCII(Iter a_begin, Iter a_end, const char *b)
{
for (Iter it = a_begin; it != a_end; ++it, ++b)
{
if (!*b || base::ToLowerASCII(*it) != *b)
return false;
}
return *b == 0;
}
bool LowerCaseEqualsASCII(const std::string &a, const char *b)
{
return DoLowerCaseEqualsASCII(a.begin(), a.end(), b);
}
} // anonymous namespace
} // namespace base
#include "GPUTestConfig.h"
namespace angle
{
......@@ -90,7 +56,7 @@ enum Token
kConfigChromeOS,
kConfigAndroid,
// gpu vendor
kConfigNVidia,
kConfigNVIDIA,
kConfigAMD,
kConfigIntel,
kConfigVMWare,
......@@ -103,6 +69,11 @@ enum Token
kConfigGLDesktop,
kConfigGLES,
kConfigVulkan,
// Android devices
kConfigNexus5X,
kConfigPixel2,
// GPU devices
kConfigNVIDIAQuadroP400,
// expectation
kExpectationPass,
kExpectationFail,
......@@ -116,56 +87,10 @@ enum Token
kNumberOfExactMatchTokens,
// others
kConfigGPUDeviceID,
kTokenComment,
kTokenWord,
};
struct TokenInfo
{
const char *name;
int32_t flag;
};
const TokenInfo kTokenData[] = {
{"xp", GPUTestConfig::kOsWinXP},
{"vista", GPUTestConfig::kOsWinVista},
{"win7", GPUTestConfig::kOsWin7},
{"win8", GPUTestConfig::kOsWin8},
{"win10", GPUTestConfig::kOsWin10},
{"win", GPUTestConfig::kOsWin},
{"leopard", GPUTestConfig::kOsMacLeopard},
{"snowleopard", GPUTestConfig::kOsMacSnowLeopard},
{"lion", GPUTestConfig::kOsMacLion},
{"mountainlion", GPUTestConfig::kOsMacMountainLion},
{"mavericks", GPUTestConfig::kOsMacMavericks},
{"yosemite", GPUTestConfig::kOsMacYosemite},
{"elcapitan", GPUTestConfig::kOsMacElCapitan},
{"sierra", GPUTestConfig::kOsMacSierra},
{"highsierra", GPUTestConfig::kOsMacHighSierra},
{"mojave", GPUTestConfig::kOsMacMojave},
{"mac", GPUTestConfig::kOsMac},
{"linux", GPUTestConfig::kOsLinux},
{"chromeos", GPUTestConfig::kOsChromeOS},
{"android", GPUTestConfig::kOsAndroid},
{"nvidia", 0x10DE},
{"amd", 0x1002},
{"intel", 0x8086},
{"vmware", 0x15ad},
{"release", GPUTestConfig::kBuildTypeRelease},
{"debug", GPUTestConfig::kBuildTypeDebug},
{"d3d9", GPUTestConfig::kAPID3D9},
{"d3d11", GPUTestConfig::kAPID3D11},
{"opengl", GPUTestConfig::kAPIGLDesktop},
{"gles", GPUTestConfig::kAPIGLES},
{"vulkan", GPUTestConfig::kAPIVulkan},
{"pass", GPUTestExpectationsParser::kGpuTestPass},
{"fail", GPUTestExpectationsParser::kGpuTestFail},
{"flaky", GPUTestExpectationsParser::kGpuTestFlaky},
{"timeout", GPUTestExpectationsParser::kGpuTestTimeout},
{"skip", GPUTestExpectationsParser::kGpuTestSkip},
{":", 0},
{"=", 0},
kNumberOfTokens,
};
enum ErrorType
......@@ -173,66 +98,136 @@ enum ErrorType
kErrorFileIO = 0,
kErrorIllegalEntry,
kErrorInvalidEntry,
kErrorEntryWithOsConflicts,
kErrorEntryWithGpuVendorConflicts,
kErrorEntryWithBuildTypeConflicts,
kErrorEntryWithAPIConflicts,
kErrorEntryWithGpuDeviceIdConflicts,
kErrorEntryWithExpectationConflicts,
kErrorEntriesOverlap,
kNumberOfErrors,
};
const char *kErrorMessage[] = {
struct TokenInfo
{
const char *name;
GPUTestConfig::Condition condition;
GPUTestExpectationsParser::GPUTestExpectation expectation;
};
const TokenInfo kTokenData[kNumberOfTokens] = {
{"xp", GPUTestConfig::kConditionWinXP},
{"vista", GPUTestConfig::kConditionWinVista},
{"win7", GPUTestConfig::kConditionWin7},
{"win8", GPUTestConfig::kConditionWin8},
{"win10", GPUTestConfig::kConditionWin10},
{"win", GPUTestConfig::kConditionWin},
{"leopard", GPUTestConfig::kConditionMacLeopard},
{"snowleopard", GPUTestConfig::kConditionMacSnowLeopard},
{"lion", GPUTestConfig::kConditionMacLion},
{"mountainlion", GPUTestConfig::kConditionMacMountainLion},
{"mavericks", GPUTestConfig::kConditionMacMavericks},
{"yosemite", GPUTestConfig::kConditionMacYosemite},
{"elcapitan", GPUTestConfig::kConditionMacElCapitan},
{"sierra", GPUTestConfig::kConditionMacSierra},
{"highsierra", GPUTestConfig::kConditionMacHighSierra},
{"mojave", GPUTestConfig::kConditionMacMojave},
{"mac", GPUTestConfig::kConditionMac},
{"linux", GPUTestConfig::kConditionLinux},
{"chromeos"}, // (https://anglebug.com/3363) ChromeOS not supported yet
{"android", GPUTestConfig::kConditionAndroid},
{"nvidia", GPUTestConfig::kConditionNVIDIA},
{"amd", GPUTestConfig::kConditionAMD},
{"intel", GPUTestConfig::kConditionIntel},
{"vmware", GPUTestConfig::kConditionVMWare},
{"release", GPUTestConfig::kConditionRelease},
{"debug", GPUTestConfig::kConditionDebug},
{"d3d9", GPUTestConfig::kConditionD3D9},
{"d3d11", GPUTestConfig::kConditionD3D11},
{"opengl", GPUTestConfig::kConditionGLDesktop},
{"gles", GPUTestConfig::kConditionGLES},
{"vulkan", GPUTestConfig::kConditionVulkan},
{"nexus5x", GPUTestConfig::kConditionNexus5X},
{"pixel2", GPUTestConfig::kConditionPixel2},
{"quadrop400", GPUTestConfig::kConditionNVIDIAQuadroP400},
{"pass", GPUTestConfig::kConditionNone, GPUTestExpectationsParser::kGpuTestPass},
{"fail", GPUTestConfig::kConditionNone, GPUTestExpectationsParser::kGpuTestFail},
{"flaky", GPUTestConfig::kConditionNone, GPUTestExpectationsParser::kGpuTestFlaky},
{"timeout", GPUTestConfig::kConditionNone, GPUTestExpectationsParser::kGpuTestTimeout},
{"skip", GPUTestConfig::kConditionNone, GPUTestExpectationsParser::kGpuTestSkip},
{":"}, // kSeparatorColon
{"="}, // kSeparatorEqual
{}, // kNumberOfExactMatchTokens
{}, // kTokenComment
{}, // kTokenWord
};
const char *kErrorMessage[kNumberOfErrors] = {
"file IO failed",
"entry with wrong format",
"entry invalid, likely wrong modifiers combination",
"entry with OS modifier conflicts",
"entry with GPU vendor modifier conflicts",
"entry with GPU build type conflicts",
"entry with GPU API conflicts",
"entry with GPU device id conflicts or malformat",
"entry invalid, likely unimplemented modifiers",
"entry with expectation modifier conflicts",
"two entries' configs overlap",
};
Token ParseToken(const std::string &word)
inline bool StartsWithASCII(const std::string &str, const std::string &search, bool caseSensitive)
{
ASSERT(!caseSensitive);
return str.compare(0, search.length(), search) == 0;
}
template <class Char>
inline Char ToLowerASCII(Char c)
{
return (c >= 'A' && c <= 'Z') ? (c + ('a' - 'A')) : c;
}
template <typename Iter>
inline bool DoLowerCaseEqualsASCII(Iter a_begin, Iter a_end, const char *b)
{
for (Iter it = a_begin; it != a_end; ++it, ++b)
{
if (!*b || ToLowerASCII(*it) != *b)
return false;
}
return *b == 0;
}
inline bool LowerCaseEqualsASCII(const std::string &a, const char *b)
{
return DoLowerCaseEqualsASCII(a.begin(), a.end(), b);
}
inline Token ParseToken(const std::string &word)
{
if (base::StartsWithASCII(word, "//", false))
if (StartsWithASCII(word, "//", false))
return kTokenComment;
if (base::StartsWithASCII(word, "0x", false))
return kConfigGPUDeviceID;
for (int32_t i = 0; i < kNumberOfExactMatchTokens; ++i)
{
if (base::LowerCaseEqualsASCII(word, kTokenData[i].name))
if (LowerCaseEqualsASCII(word, kTokenData[i].name))
return static_cast<Token>(i);
}
return kTokenWord;
}
// reference name can have the last character as *.
bool NamesMatching(const std::string &ref, const std::string &test_name)
inline bool NamesMatching(const std::string &ref, const std::string &testName)
{
size_t len = ref.length();
if (len == 0)
return false;
if (ref[len - 1] == '*')
{
if (test_name.length() > len - 1 && ref.compare(0, len - 1, test_name, 0, len - 1) == 0)
if (testName.length() > len - 1 && ref.compare(0, len - 1, testName, 0, len - 1) == 0)
return true;
return false;
}
return (ref == test_name);
return (ref == testName);
}
} // namespace
} // anonymous namespace
GPUTestExpectationsParser::GPUTestExpectationsParser()
{
// Some sanity check.
ASSERT((static_cast<unsigned int>(kNumberOfExactMatchTokens)) ==
ASSERT((static_cast<unsigned int>(kNumberOfTokens)) ==
(sizeof(kTokenData) / sizeof(kTokenData[0])));
ASSERT((static_cast<unsigned int>(kNumberOfErrors)) ==
(sizeof(kErrorMessage) / sizeof(kErrorMessage[0])));
......@@ -240,135 +235,75 @@ GPUTestExpectationsParser::GPUTestExpectationsParser()
GPUTestExpectationsParser::~GPUTestExpectationsParser() = default;
bool GPUTestExpectationsParser::LoadTestExpectations(const std::string &data)
bool GPUTestExpectationsParser::loadTestExpectations(const GPUTestConfig &config,
const std::string &data)
{
entries_.clear();
error_messages_.clear();
mEntries.clear();
mErrorMessages.clear();
std::vector<std::string> lines = SplitString(data, "\n", TRIM_WHITESPACE, SPLIT_WANT_ALL);
bool rt = true;
for (size_t i = 0; i < lines.size(); ++i)
{
if (!ParseLine(lines[i], i + 1))
if (!parseLine(config, lines[i], i + 1))
rt = false;
}
if (DetectConflictsBetweenEntries())
if (detectConflictsBetweenEntries())
{
entries_.clear();
mEntries.clear();
rt = false;
}
return rt;
}
bool GPUTestExpectationsParser::LoadTestExpectationsFromFile(const std::string &path)
bool GPUTestExpectationsParser::loadTestExpectationsFromFile(const GPUTestConfig &config,
const std::string &path)
{
entries_.clear();
error_messages_.clear();
mEntries.clear();
mErrorMessages.clear();
std::string data;
if (!ReadFileToString(path, &data))
{
error_messages_.push_back(kErrorMessage[kErrorFileIO]);
mErrorMessages.push_back(kErrorMessage[kErrorFileIO]);
return false;
}
return LoadTestExpectations(data);
return loadTestExpectations(config, data);
}
int32_t GPUTestExpectationsParser::GetTestExpectation(const std::string &test_name,
const GPUTestBotConfig &bot_config) const
int32_t GPUTestExpectationsParser::getTestExpectation(const std::string &testName) const
{
for (size_t i = 0; i < entries_.size(); ++i)
for (size_t i = 0; i < mEntries.size(); ++i)
{
if (NamesMatching(entries_[i].test_name, test_name) &&
bot_config.Matches(entries_[i].test_config))
return entries_[i].test_expectation;
if (NamesMatching(mEntries[i].mTestName, testName))
return mEntries[i].mTestExpectation;
}
return kGpuTestPass;
}
const std::vector<std::string> &GPUTestExpectationsParser::GetErrorMessages() const
const std::vector<std::string> &GPUTestExpectationsParser::getErrorMessages() const
{
return error_messages_;
}
bool GPUTestExpectationsParser::ParseConfig(const std::string &config_data, GPUTestConfig *config)
{
ASSERT(config);
std::vector<std::string> tokens =
SplitString(config_data, kWhitespaceASCII, KEEP_WHITESPACE, SPLIT_WANT_NONEMPTY);
for (size_t i = 0; i < tokens.size(); ++i)
{
Token token = ParseToken(tokens[i]);
switch (token)
{
case kConfigWinXP:
case kConfigWinVista:
case kConfigWin7:
case kConfigWin8:
case kConfigWin10:
case kConfigWin:
case kConfigMacLeopard:
case kConfigMacSnowLeopard:
case kConfigMacLion:
case kConfigMacMountainLion:
case kConfigMacMavericks:
case kConfigMacYosemite:
case kConfigMacElCapitan:
case kConfigMacSierra:
case kConfigMacHighSierra:
case kConfigMacMojave:
case kConfigMac:
case kConfigLinux:
case kConfigChromeOS:
case kConfigAndroid:
case kConfigNVidia:
case kConfigAMD:
case kConfigIntel:
case kConfigVMWare:
case kConfigRelease:
case kConfigDebug:
case kConfigD3D9:
case kConfigD3D11:
case kConfigGLDesktop:
case kConfigGLES:
case kConfigVulkan:
case kConfigGPUDeviceID:
if (token == kConfigGPUDeviceID)
{
if (!UpdateTestConfig(config, tokens[i], 0))
return false;
}
else
{
if (!UpdateTestConfig(config, token, 0))
return false;
}
break;
default:
return false;
}
}
return true;
return mErrorMessages;
}
bool GPUTestExpectationsParser::ParseLine(const std::string &line_data, size_t line_number)
bool GPUTestExpectationsParser::parseLine(const GPUTestConfig &config,
const std::string &lineData,
size_t lineNumber)
{
std::vector<std::string> tokens =
SplitString(line_data, kWhitespaceASCII, KEEP_WHITESPACE, SPLIT_WANT_NONEMPTY);
SplitString(lineData, kWhitespaceASCII, KEEP_WHITESPACE, SPLIT_WANT_NONEMPTY);
int32_t stage = kLineParserBegin;
GPUTestExpectationEntry entry;
entry.line_number = line_number;
GPUTestConfig &config = entry.test_config;
bool comments_encountered = false;
for (size_t i = 0; i < tokens.size() && !comments_encountered; ++i)
entry.mLineNumber = lineNumber;
bool skipLine = false;
for (size_t i = 0; i < tokens.size() && !skipLine; ++i)
{
Token token = ParseToken(tokens[i]);
switch (token)
{
case kTokenComment:
comments_encountered = true;
skipLine = true;
break;
case kConfigWinXP:
case kConfigWinVista:
......@@ -390,7 +325,7 @@ bool GPUTestExpectationsParser::ParseLine(const std::string &line_data, size_t l
case kConfigLinux:
case kConfigChromeOS:
case kConfigAndroid:
case kConfigNVidia:
case kConfigNVIDIA:
case kConfigAMD:
case kConfigIntel:
case kConfigVMWare:
......@@ -401,31 +336,41 @@ bool GPUTestExpectationsParser::ParseLine(const std::string &line_data, size_t l
case kConfigGLDesktop:
case kConfigGLES:
case kConfigVulkan:
case kConfigGPUDeviceID:
// MODIFIERS, could be in any order, need at least one.
case kConfigNexus5X:
case kConfigPixel2:
case kConfigNVIDIAQuadroP400:
// MODIFIERS, check each condition and add accordingly.
if (stage != kLineParserConfigs && stage != kLineParserBugID)
{
PushErrorMessage(kErrorMessage[kErrorIllegalEntry], line_number);
pushErrorMessage(kErrorMessage[kErrorIllegalEntry], lineNumber);
return false;
}
if (token == kConfigGPUDeviceID)
{
if (!UpdateTestConfig(&config, tokens[i], line_number))
return false;
}
else
{
if (!UpdateTestConfig(&config, token, line_number))
bool err = false;
if (!checkTokenCondition(config, err, token, lineNumber))
{
skipLine = true; // Move to the next line without adding this one.
}
if (err)
{
return false;
}
}
if (stage == kLineParserBugID)
{
stage++;
}
break;
case kSeparatorColon:
// :
// If there are no modifiers, move straight to separator colon
if (stage == kLineParserBugID)
{
stage++;
}
if (stage != kLineParserConfigs)
{
PushErrorMessage(kErrorMessage[kErrorIllegalEntry], line_number);
pushErrorMessage(kErrorMessage[kErrorIllegalEntry], lineNumber);
return false;
}
stage++;
......@@ -434,7 +379,7 @@ bool GPUTestExpectationsParser::ParseLine(const std::string &line_data, size_t l
// =
if (stage != kLineParserTestName)
{
PushErrorMessage(kErrorMessage[kErrorIllegalEntry], line_number);
pushErrorMessage(kErrorMessage[kErrorIllegalEntry], lineNumber);
return false;
}
stage++;
......@@ -447,11 +392,11 @@ bool GPUTestExpectationsParser::ParseLine(const std::string &line_data, size_t l
}
else if (stage == kLineParserColon)
{
entry.test_name = tokens[i];
entry.mTestName = tokens[i];
}
else
{
PushErrorMessage(kErrorMessage[kErrorIllegalEntry], line_number);
pushErrorMessage(kErrorMessage[kErrorIllegalEntry], lineNumber);
return false;
}
stage++;
......@@ -464,16 +409,16 @@ bool GPUTestExpectationsParser::ParseLine(const std::string &line_data, size_t l
// TEST_EXPECTATIONS
if (stage != kLineParserEqual && stage != kLineParserExpectations)
{
PushErrorMessage(kErrorMessage[kErrorIllegalEntry], line_number);
pushErrorMessage(kErrorMessage[kErrorIllegalEntry], lineNumber);
return false;
}
if ((kTokenData[token].flag & entry.test_expectation) != 0)
if (entry.mTestExpectation != 0)
{
PushErrorMessage(kErrorMessage[kErrorEntryWithExpectationConflicts],
line_number);
pushErrorMessage(kErrorMessage[kErrorEntryWithExpectationConflicts],
lineNumber);
return false;
}
entry.test_expectation = (kTokenData[token].flag | entry.test_expectation);
entry.mTestExpectation = kTokenData[token].expectation;
if (stage == kLineParserEqual)
stage++;
break;
......@@ -482,132 +427,55 @@ bool GPUTestExpectationsParser::ParseLine(const std::string &line_data, size_t l
break;
}
}
if (stage == kLineParserBegin)
if (stage == kLineParserBegin || skipLine)
{
// The whole line is empty or all comments
// The whole line is empty or all comments, or has been skipped to to a condition token.
return true;
}
if (stage == kLineParserExpectations)
{
if (!config.IsValid())
{
PushErrorMessage(kErrorMessage[kErrorInvalidEntry], line_number);
return false;
}
entries_.push_back(entry);
mEntries.push_back(entry);
return true;
}
PushErrorMessage(kErrorMessage[kErrorIllegalEntry], line_number);
pushErrorMessage(kErrorMessage[kErrorIllegalEntry], lineNumber);
return false;
}
bool GPUTestExpectationsParser::UpdateTestConfig(GPUTestConfig *config,
int32_t token,
size_t line_number)
bool GPUTestExpectationsParser::checkTokenCondition(const GPUTestConfig &config,
bool &err,
int32_t token,
size_t lineNumber)
{
ASSERT(config);
switch (token)
if (token >= kNumberOfTokens)
{
case kConfigWinXP:
case kConfigWinVista:
case kConfigWin7:
case kConfigWin8:
case kConfigWin10:
case kConfigWin:
case kConfigMacLeopard:
case kConfigMacSnowLeopard:
case kConfigMacLion:
case kConfigMacMountainLion:
case kConfigMacMavericks:
case kConfigMacYosemite:
case kConfigMacElCapitan:
case kConfigMacSierra:
case kConfigMacHighSierra:
case kConfigMacMojave:
case kConfigMac:
case kConfigLinux:
case kConfigChromeOS:
case kConfigAndroid:
if ((config->os() & kTokenData[token].flag) != 0)
{
PushErrorMessage(kErrorMessage[kErrorEntryWithOsConflicts], line_number);
return false;
}
config->set_os(config->os() | kTokenData[token].flag);
break;
case kConfigNVidia:
case kConfigAMD:
case kConfigIntel:
case kConfigVMWare:
{
uint32_t gpu_vendor = static_cast<uint32_t>(kTokenData[token].flag);
for (size_t i = 0; i < config->gpu_vendor().size(); ++i)
{
if (config->gpu_vendor()[i] == gpu_vendor)
{
PushErrorMessage(kErrorMessage[kErrorEntryWithGpuVendorConflicts], line_number);
return false;
}
}
config->AddGPUVendor(gpu_vendor);
}
break;
case kConfigRelease:
case kConfigDebug:
if ((config->build_type() & kTokenData[token].flag) != 0)
{
PushErrorMessage(kErrorMessage[kErrorEntryWithBuildTypeConflicts], line_number);
return false;
}
config->set_build_type(config->build_type() | kTokenData[token].flag);
break;
case kConfigD3D9:
case kConfigD3D11:
case kConfigGLDesktop:
case kConfigGLES:
case kConfigVulkan:
if ((config->api() & kTokenData[token].flag) != 0)
{
PushErrorMessage(kErrorMessage[kErrorEntryWithAPIConflicts], line_number);
return false;
}
config->set_api(config->api() | kTokenData[token].flag);
break;
default:
ASSERT(false);
break;
pushErrorMessage(kErrorMessage[kErrorIllegalEntry], lineNumber);
err = true;
return false;
}
return true;
}
bool GPUTestExpectationsParser::UpdateTestConfig(GPUTestConfig *config,
const std::string &gpu_device_id,
size_t line_number)
{
ASSERT(config);
uint32_t device_id = 0;
if (config->gpu_device_id() != 0 || !HexStringToUInt(gpu_device_id, &device_id) ||
device_id == 0)
if (kTokenData[token].condition == GPUTestConfig::kConditionNone ||
kTokenData[token].condition >= GPUTestConfig::kNumberOfConditions)
{
PushErrorMessage(kErrorMessage[kErrorEntryWithGpuDeviceIdConflicts], line_number);
pushErrorMessage(kErrorMessage[kErrorInvalidEntry], lineNumber);
// error on any unsupported conditions
err = true;
return false;
}
config->set_gpu_device_id(device_id);
return true;
err = false;
return config.getConditions()[kTokenData[token].condition];
}
bool GPUTestExpectationsParser::DetectConflictsBetweenEntries()
bool GPUTestExpectationsParser::detectConflictsBetweenEntries()
{
bool rt = false;
for (size_t i = 0; i < entries_.size(); ++i)
for (size_t i = 0; i < mEntries.size(); ++i)
{
for (size_t j = i + 1; j < entries_.size(); ++j)
for (size_t j = i + 1; j < mEntries.size(); ++j)
{
if (entries_[i].test_name == entries_[j].test_name &&
entries_[i].test_config.OverlapsWith(entries_[j].test_config))
if (mEntries[i].mTestName == mEntries[j].mTestName)
{
PushErrorMessage(kErrorMessage[kErrorEntriesOverlap], entries_[i].line_number,
entries_[j].line_number);
pushErrorMessage(kErrorMessage[kErrorEntriesOverlap], mEntries[i].mLineNumber,
mEntries[j].mLineNumber);
rt = true;
}
}
......@@ -615,21 +483,21 @@ bool GPUTestExpectationsParser::DetectConflictsBetweenEntries()
return rt;
}
void GPUTestExpectationsParser::PushErrorMessage(const std::string &message, size_t line_number)
void GPUTestExpectationsParser::pushErrorMessage(const std::string &message, size_t lineNumber)
{
error_messages_.push_back("Line " + ToString(line_number) + " : " + message.c_str());
mErrorMessages.push_back("Line " + ToString(lineNumber) + " : " + message.c_str());
}
void GPUTestExpectationsParser::PushErrorMessage(const std::string &message,
size_t entry1_line_number,
size_t entry2_line_number)
void GPUTestExpectationsParser::pushErrorMessage(const std::string &message,
size_t entry1LineNumber,
size_t entry2LineNumber)
{
error_messages_.push_back("Line " + ToString(entry1_line_number) + " and " +
ToString(entry2_line_number) + " : " + message.c_str());
mErrorMessages.push_back("Line " + ToString(entry1LineNumber) + " and " +
ToString(entry2LineNumber) + " : " + message.c_str());
}
GPUTestExpectationsParser::GPUTestExpectationEntry::GPUTestExpectationEntry()
: test_expectation(0), line_number(0)
: mTestExpectation(0), mLineNumber(0)
{}
} // namespace angle
......@@ -13,11 +13,11 @@
#include <string>
#include <vector>
#include "GPUTestConfig.h"
namespace angle
{
struct GPUTestConfig;
class GPUTestExpectationsParser
{
public:
......@@ -36,55 +36,47 @@ class GPUTestExpectationsParser
// Parse the text expectations, and if no error is encountered,
// save all the entries. Otherwise, generate error messages.
// Return true if parsing succeeds.
bool LoadTestExpectations(const std::string &data);
bool LoadTestExpectationsFromFile(const std::string &path);
bool loadTestExpectations(const GPUTestConfig &config, const std::string &data);
bool loadTestExpectationsFromFile(const GPUTestConfig &config, const std::string &path);
// Query error messages from the last LoadTestExpectations() call.
const std::vector<std::string> &GetErrorMessages() const;
const std::vector<std::string> &getErrorMessages() const;
// Get the test expectation of a given test on a given bot.
int32_t GetTestExpectation(const std::string &test_name,
const GPUTestBotConfig &bot_config) const;
// Parse a list of config modifiers. If we have a valid entry with no
// conflicts, | config | stores it, and the function returns true.
bool ParseConfig(const std::string &config_data, GPUTestConfig *config);
int32_t getTestExpectation(const std::string &testName) const;
private:
struct GPUTestExpectationEntry
{
GPUTestExpectationEntry();
std::string test_name;
GPUTestConfig test_config;
int32_t test_expectation;
size_t line_number;
std::string mTestName;
int32_t mTestExpectation;
size_t mLineNumber;
};
// Parse a line of text. If we have a valid entry, save it; otherwise,
// generate error messages.
bool ParseLine(const std::string &line_data, size_t line_number);
// Update OS/GPUVendor/BuildType modifiers. May generate an error message.
bool UpdateTestConfig(GPUTestConfig *config, int32_t token, size_t line_number);
bool parseLine(const GPUTestConfig &config, const std::string &lineData, size_t lineNumber);
// Update GPUDeviceID modifier. May generate an error message.
bool UpdateTestConfig(GPUTestConfig *config,
const std::string &gpu_device_id,
size_t line_number);
// Check a the condition assigned to a particular token.
bool checkTokenCondition(const GPUTestConfig &config,
bool &err,
int32_t token,
size_t lineNumber);
// Check if two entries' config overlap with each other. May generate an
// error message.
bool DetectConflictsBetweenEntries();
bool detectConflictsBetweenEntries();
// Save an error message, which can be queried later.
void PushErrorMessage(const std::string &message, size_t line_number);
void PushErrorMessage(const std::string &message,
size_t entry1_line_number,
size_t entry2_line_number);
void pushErrorMessage(const std::string &message, size_t lineNumber);
void pushErrorMessage(const std::string &message,
size_t entry1LineNumber,
size_t entry2LineNumber);
std::vector<GPUTestExpectationEntry> entries_;
std::vector<std::string> error_messages_;
std::vector<GPUTestExpectationEntry> mEntries;
std::vector<std::string> mErrorMessages;
};
} // namespace angle
......
//
// 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.
//
// GPUTestExpectationsParser_unittest.cpp: Unit tests for GPUTestExpectationsParser*
//
#include "tests/test_expectations/GPUTestExpectationsParser.h"
#include <gtest/gtest.h>
#include "tests/test_expectations/GPUTestConfig.h"
using namespace angle;
namespace
{
class GPUTestConfigTester : public GPUTestConfig
{
public:
GPUTestConfigTester()
{
for (bool &condition : mConditions)
{
condition = false;
}
mConditions[GPUTestConfig::kConditionWin] = true;
mConditions[GPUTestConfig::kConditionNVIDIA] = true;
mConditions[GPUTestConfig::kConditionD3D11] = true;
}
};
// A correct entry with a test that's skipped on all platforms should not lead
// to any errors, and should properly return the expectation SKIP.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserSkip)
{
GPUTestConfigTester config;
std::string line =
R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestSkip);
}
// A correct entry with a test that's failed on all platforms should not lead
// to any errors, and should properly return the expectation FAIL.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserFail)
{
GPUTestConfigTester config;
std::string line =
R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = FAIL)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestFail);
}
// A correct entry with a test that's passed on all platforms should not lead
// to any errors, and should properly return the expectation PASS.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserPass)
{
GPUTestConfigTester config;
std::string line =
R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = PASS)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A correct entry with a test that's timed out on all platforms should not lead
// to any errors, and should properly return the expectation TIMEOUT.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserTimeout)
{
GPUTestConfigTester config;
std::string line =
R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = TIMEOUT)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestTimeout);
}
// A correct entry with a test that's flaky on all platforms should not lead
// to any errors, and should properly return the expectation FLAKY.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserFlaky)
{
GPUTestConfigTester config;
std::string line =
R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = FLAKY)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestFlaky);
}
// A correct entry with a test that's skipped on windows should not lead
// to any errors, and should properly return the expectation SKIP on this
// tester.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserSingleLineWin)
{
GPUTestConfigTester config;
std::string line =
R"(100 WIN : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestSkip);
}
// A correct entry with a test that's skipped on windows/NVIDIA should not lead
// to any errors, and should properly return the expectation SKIP on this
// tester.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserSingleLineWinNVIDIA)
{
GPUTestConfigTester config;
std::string line =
R"(100 WIN NVIDIA : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestSkip);
}
// A correct entry with a test that's skipped on windows/NVIDIA/D3D11 should not
// lead to any errors, and should properly return the expectation SKIP on this
// tester.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserSingleLineWinNVIDIAD3D11)
{
GPUTestConfigTester config;
std::string line =
R"(100 WIN NVIDIA D3D11 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestSkip);
}
// Same as GPUTestExpectationsParserSingleLineWinNVIDIAD3D11, but verifying that the order
// of these conditions doesn't matter
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserSingleLineWinNVIDIAD3D11OtherOrder)
{
GPUTestConfigTester config;
std::string line =
R"(100 D3D11 NVIDIA WIN : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestSkip);
}
// A correct entry with a test that's skipped on mac should not lead
// to any errors, and should default to PASS on this tester (windows).
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserSingleLineMac)
{
GPUTestConfigTester config;
std::string line =
R"(100 MAC : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A correct entry with a test that has conflicting entries should not lead
// to any errors, and should default to PASS.
// (https:anglebug.com/3368) In the future, this condition should cause an
// error
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserSingleLineConflict)
{
GPUTestConfigTester config;
std::string line =
R"(100 WIN MAC : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A line without a bug ID should return an error and not add the expectation.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserMissingBugId)
{
GPUTestConfigTester config;
std::string line = R"( : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_FALSE(parser.loadTestExpectations(config, line));
EXPECT_EQ(parser.getErrorMessages().size(), 1u);
if (parser.getErrorMessages().size() >= 1)
EXPECT_EQ(parser.getErrorMessages()[0], "Line 1 : entry with wrong format");
// Default behavior is to let missing tests pass
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A line without a bug ID should return an error and not add the expectation, (even if
// the line contains conditions that might be mistaken for a bug id)
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserMissingBugIdWithConditions)
{
GPUTestConfigTester config;
std::string line =
R"(WIN D3D11 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_FALSE(parser.loadTestExpectations(config, line));
EXPECT_EQ(parser.getErrorMessages().size(), 1u);
if (parser.getErrorMessages().size() >= 1)
EXPECT_EQ(parser.getErrorMessages()[0], "Line 1 : entry with wrong format");
// Default behavior is to let missing tests pass
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A line without a colon should return an error and not add the expectation.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserMissingColon)
{
GPUTestConfigTester config;
std::string line = R"(100 dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_FALSE(parser.loadTestExpectations(config, line));
EXPECT_EQ(parser.getErrorMessages().size(), 1u);
if (parser.getErrorMessages().size() >= 1)
EXPECT_EQ(parser.getErrorMessages()[0], "Line 1 : entry with wrong format");
// Default behavior is to let missing tests pass
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A wild character (*) at the end of a line should match any expectations that are a subset of that
// line. It should not greedily match to omany expectations that aren't in that subset.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserWildChar)
{
GPUTestConfigTester config;
std::string line = R"(100 : dEQP-GLES31.functional.layout_binding.ubo.* = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestSkip);
// Also ensure the wild char is not too wild, only covers tests that are more specific
EXPECT_EQ(parser.getTestExpectation(
"dEQP-GLES31.functional.program_interface_query.transform_feedback_varying."
"resource_list.vertex_fragment.builtin_gl_position"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A line without an equals should return an error and not add the expectation.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserMissingEquals)
{
GPUTestConfigTester config;
std::string line = R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max SKIP)";
GPUTestExpectationsParser parser;
EXPECT_FALSE(parser.loadTestExpectations(config, line));
EXPECT_EQ(parser.getErrorMessages().size(), 1u);
if (parser.getErrorMessages().size() >= 1)
EXPECT_EQ(parser.getErrorMessages()[0], "Line 1 : entry with wrong format");
// Default behavior is to let missing tests pass
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A line without an expectation should return an error and not add the expectation.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserMissingExpectation)
{
GPUTestConfigTester config;
std::string line = R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max =)";
GPUTestExpectationsParser parser;
EXPECT_FALSE(parser.loadTestExpectations(config, line));
EXPECT_EQ(parser.getErrorMessages().size(), 1u);
if (parser.getErrorMessages().size() >= 1)
EXPECT_EQ(parser.getErrorMessages()[0], "Line 1 : entry with wrong format");
// Default behavior is to let missing tests pass
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// A line with an expectation that doesn't exist should return an error and not add the expectation.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserInvalidExpectation)
{
GPUTestConfigTester config;
std::string line =
R"(100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = WRONG)";
GPUTestExpectationsParser parser;
EXPECT_FALSE(parser.loadTestExpectations(config, line));
EXPECT_EQ(parser.getErrorMessages().size(), 1u);
if (parser.getErrorMessages().size() >= 1)
EXPECT_EQ(parser.getErrorMessages()[0], "Line 1 : entry with wrong format");
// Default behavior is to let missing tests pass
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// ChromeOS is reserved as a token, but doesn't actually check any conditions. Any tokens that
// do not check conditions should return an error and not add the expectation
// (https://anglebug.com/3363) Remove/update this test when ChromeOS is supported
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserUnimplementedCondition)
{
GPUTestConfigTester config;
std::string line =
R"(100 CHROMEOS : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_FALSE(parser.loadTestExpectations(config, line));
EXPECT_EQ(parser.getErrorMessages().size(), 1u);
if (parser.getErrorMessages().size() >= 1)
EXPECT_EQ(parser.getErrorMessages()[0],
"Line 1 : entry invalid, likely unimplemented modifiers");
// Default behavior is to let missing tests pass
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
// If a line starts with a comment, it's ignored and should not be added to the list.
TEST(GPUTestExpectationsParserTest, GPUTestExpectationsParserComment)
{
GPUTestConfigTester config;
std::string line =
R"(//100 : dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max = SKIP)";
GPUTestExpectationsParser parser;
EXPECT_TRUE(parser.loadTestExpectations(config, line));
EXPECT_TRUE(parser.getErrorMessages().empty());
EXPECT_EQ(
parser.getTestExpectation("dEQP-GLES31.functional.layout_binding.ubo.vertex_binding_max"),
GPUTestExpectationsParser::kGpuTestPass);
}
} // anonymous namespace
//
// 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.
//
// GPUTestExpectationsTest.cpp : Tests of the test_expectations library.
#include "test_expectations/GPUTestConfig.h"
#include "test_expectations/GPUTestExpectationsParser.h"
#include "test_utils/ANGLETest.h"
namespace angle
{
class GPUTestConfigTest : public ANGLETest
{
protected:
GPUTestConfigTest() {}
// todo(jonahr): Eventually could add support for all conditions/operating
// systems, but these are the ones in use for now
void validateConfigBase(const GPUTestConfig &config)
{
EXPECT_EQ(IsWindows(), config.getConditions()[GPUTestConfig::kConditionWin]);
EXPECT_EQ(IsOSX(), config.getConditions()[GPUTestConfig::kConditionMac]);
EXPECT_EQ(IsLinux(), config.getConditions()[GPUTestConfig::kConditionLinux]);
EXPECT_EQ(IsAndroid(), config.getConditions()[GPUTestConfig::kConditionAndroid]);
EXPECT_EQ(IsNexus5X(), config.getConditions()[GPUTestConfig::kConditionNexus5X]);
EXPECT_EQ(IsPixel2(), config.getConditions()[GPUTestConfig::kConditionPixel2]);
EXPECT_EQ(IsIntel(), config.getConditions()[GPUTestConfig::kConditionIntel]);
EXPECT_EQ(IsAMD(), config.getConditions()[GPUTestConfig::kConditionAMD]);
EXPECT_EQ(IsNVIDIA(), config.getConditions()[GPUTestConfig::kConditionNVIDIA]);
EXPECT_EQ(IsDebug(), config.getConditions()[GPUTestConfig::kConditionDebug]);
EXPECT_EQ(IsRelease(), config.getConditions()[GPUTestConfig::kConditionRelease]);
}
void validateConfigAPI(const GPUTestConfig &config, const GPUTestConfig::API &api)
{
bool D3D9 = false;
bool D3D11 = false;
bool GLDesktop = false;
bool GLES = false;
bool Vulkan = false;
switch (api)
{
case GPUTestConfig::kAPID3D9:
D3D9 = true;
break;
case GPUTestConfig::kAPID3D11:
D3D11 = true;
break;
case GPUTestConfig::kAPIGLDesktop:
GLDesktop = true;
break;
case GPUTestConfig::kAPIGLES:
GLES = true;
break;
case GPUTestConfig::kAPIVulkan:
Vulkan = true;
break;
case GPUTestConfig::kAPIUnknown:
default:
break;
}
EXPECT_EQ(D3D9, config.getConditions()[GPUTestConfig::kConditionD3D9]);
EXPECT_EQ(D3D11, config.getConditions()[GPUTestConfig::kConditionD3D11]);
EXPECT_EQ(GLDesktop, config.getConditions()[GPUTestConfig::kConditionGLDesktop]);
EXPECT_EQ(GLES, config.getConditions()[GPUTestConfig::kConditionGLES]);
EXPECT_EQ(Vulkan, config.getConditions()[GPUTestConfig::kConditionVulkan]);
}
};
// Create a new GPUTestConfig and make sure all the condition flags were set
// correctly based on the hardware.
TEST_P(GPUTestConfigTest, GPUTestConfigConditions)
{
GPUTestConfig config;
validateConfigBase(config);
}
// Create a new GPUTestConfig with each backend specified and validate the
// condition flags are set correctly.
TEST_P(GPUTestConfigTest, GPUTestConfigConditions_D3D9)
{
GPUTestConfig config(GPUTestConfig::kAPID3D9);
validateConfigAPI(config, GPUTestConfig::kAPID3D9);
}
TEST_P(GPUTestConfigTest, GPUTestConfigConditions_D3D11)
{
GPUTestConfig config(GPUTestConfig::kAPID3D11);
validateConfigAPI(config, GPUTestConfig::kAPID3D11);
}
TEST_P(GPUTestConfigTest, GPUTestConfigConditions_GLDesktop)
{
GPUTestConfig config(GPUTestConfig::kAPIGLDesktop);
validateConfigAPI(config, GPUTestConfig::kAPIGLDesktop);
}
TEST_P(GPUTestConfigTest, GPUTestConfigConditions_GLES)
{
GPUTestConfig config(GPUTestConfig::kAPIGLES);
validateConfigAPI(config, GPUTestConfig::kAPIGLES);
}
TEST_P(GPUTestConfigTest, GPUTestConfigConditions_Vulkan)
{
GPUTestConfig config(GPUTestConfig::kAPIVulkan);
validateConfigAPI(config, GPUTestConfig::kAPIVulkan);
}
// Use this to select which configurations (e.g. which renderer, which GLES major version) these
// tests should be run against.
ANGLE_INSTANTIATE_TEST(GPUTestConfigTest,
ES2_D3D9(),
ES2_D3D11(),
ES3_D3D11(),
ES2_D3D11_FL9_3(),
ES2_OPENGL(),
ES3_OPENGL(),
ES2_OPENGLES(),
ES3_OPENGLES(),
ES2_VULKAN());
} // namespace angle
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment