| // Copyright (c) 2015-2016 The Khronos Group Inc. | |
| // Copyright (c) 2016 Google Inc. | |
| // | |
| // Licensed under the Apache License, Version 2.0 (the "License"); | |
| // you may not use this file except in compliance with the License. | |
| // You may obtain a copy of the License at | |
| // | |
| // http://www.apache.org/licenses/LICENSE-2.0 | |
| // | |
| // Unless required by applicable law or agreed to in writing, software | |
| // distributed under the License is distributed on an "AS IS" BASIS, | |
| // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
| // See the License for the specific language governing permissions and | |
| // limitations under the License. | |
| // Unit tests for ValidationState_t. | |
| #include <vector> | |
| #include "gtest/gtest.h" | |
| #include "source/enum_set.h" | |
| #include "source/extensions.h" | |
| #include "source/latest_version_spirv_header.h" | |
| #include "source/spirv_validator_options.h" | |
| #include "source/val/validation_state.h" | |
| namespace spvtools { | |
| namespace val { | |
| namespace { | |
| // This is all we need for these tests. | |
| static uint32_t kFakeBinary[] = {0}; | |
| // A test with a ValidationState_t member transparently. | |
| class ValidationStateTest : public testing::Test { | |
| public: | |
| ValidationStateTest() | |
| : context_(spvContextCreate(SPV_ENV_UNIVERSAL_1_0)), | |
| options_(spvValidatorOptionsCreate()), | |
| state_(context_, options_, kFakeBinary, 0, 1) {} | |
| ~ValidationStateTest() override { | |
| spvContextDestroy(context_); | |
| spvValidatorOptionsDestroy(options_); | |
| } | |
| protected: | |
| spv_context context_; | |
| spv_validator_options options_; | |
| ValidationState_t state_; | |
| }; | |
| // A test of ValidationState_t::HasAnyOfCapabilities(). | |
| using ValidationState_HasAnyOfCapabilities = ValidationStateTest; | |
| TEST_F(ValidationState_HasAnyOfCapabilities, EmptyMask) { | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({})); | |
| state_.RegisterCapability(spv::Capability::Matrix); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({})); | |
| state_.RegisterCapability(spv::Capability::ImageMipmap); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({})); | |
| state_.RegisterCapability(spv::Capability::Pipes); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({})); | |
| state_.RegisterCapability(spv::Capability::StorageImageArrayDynamicIndexing); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({})); | |
| state_.RegisterCapability(spv::Capability::ClipDistance); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({})); | |
| state_.RegisterCapability(spv::Capability::StorageImageWriteWithoutFormat); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({})); | |
| } | |
| TEST_F(ValidationState_HasAnyOfCapabilities, SingleCapMask) { | |
| EXPECT_FALSE(state_.HasAnyOfCapabilities({spv::Capability::Matrix})); | |
| EXPECT_FALSE(state_.HasAnyOfCapabilities({spv::Capability::ImageMipmap})); | |
| state_.RegisterCapability(spv::Capability::Matrix); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({spv::Capability::Matrix})); | |
| EXPECT_FALSE(state_.HasAnyOfCapabilities({spv::Capability::ImageMipmap})); | |
| state_.RegisterCapability(spv::Capability::ImageMipmap); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({spv::Capability::Matrix})); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities({spv::Capability::ImageMipmap})); | |
| } | |
| TEST_F(ValidationState_HasAnyOfCapabilities, MultiCapMask) { | |
| const auto set1 = | |
| CapabilitySet{spv::Capability::SampledRect, spv::Capability::ImageBuffer}; | |
| const auto set2 = | |
| CapabilitySet{spv::Capability::StorageImageWriteWithoutFormat, | |
| spv::Capability::StorageImageReadWithoutFormat, | |
| spv::Capability::GeometryStreams}; | |
| EXPECT_FALSE(state_.HasAnyOfCapabilities(set1)); | |
| EXPECT_FALSE(state_.HasAnyOfCapabilities(set2)); | |
| state_.RegisterCapability(spv::Capability::ImageBuffer); | |
| EXPECT_TRUE(state_.HasAnyOfCapabilities(set1)); | |
| EXPECT_FALSE(state_.HasAnyOfCapabilities(set2)); | |
| } | |
| // A test of ValidationState_t::HasAnyOfExtensions(). | |
| using ValidationState_HasAnyOfExtensions = ValidationStateTest; | |
| TEST_F(ValidationState_HasAnyOfExtensions, EmptyMask) { | |
| EXPECT_TRUE(state_.HasAnyOfExtensions({})); | |
| state_.RegisterExtension(Extension::kSPV_KHR_shader_ballot); | |
| EXPECT_TRUE(state_.HasAnyOfExtensions({})); | |
| state_.RegisterExtension(Extension::kSPV_KHR_16bit_storage); | |
| EXPECT_TRUE(state_.HasAnyOfExtensions({})); | |
| state_.RegisterExtension(Extension::kSPV_NV_viewport_array2); | |
| EXPECT_TRUE(state_.HasAnyOfExtensions({})); | |
| } | |
| TEST_F(ValidationState_HasAnyOfExtensions, SingleCapMask) { | |
| EXPECT_FALSE(state_.HasAnyOfExtensions({Extension::kSPV_KHR_shader_ballot})); | |
| EXPECT_FALSE(state_.HasAnyOfExtensions({Extension::kSPV_KHR_16bit_storage})); | |
| state_.RegisterExtension(Extension::kSPV_KHR_shader_ballot); | |
| EXPECT_TRUE(state_.HasAnyOfExtensions({Extension::kSPV_KHR_shader_ballot})); | |
| EXPECT_FALSE(state_.HasAnyOfExtensions({Extension::kSPV_KHR_16bit_storage})); | |
| state_.RegisterExtension(Extension::kSPV_KHR_16bit_storage); | |
| EXPECT_TRUE(state_.HasAnyOfExtensions({Extension::kSPV_KHR_shader_ballot})); | |
| EXPECT_TRUE(state_.HasAnyOfExtensions({Extension::kSPV_KHR_16bit_storage})); | |
| } | |
| TEST_F(ValidationState_HasAnyOfExtensions, MultiCapMask) { | |
| const auto set1 = ExtensionSet{Extension::kSPV_KHR_multiview, | |
| Extension::kSPV_KHR_16bit_storage}; | |
| const auto set2 = ExtensionSet{Extension::kSPV_KHR_shader_draw_parameters, | |
| Extension::kSPV_NV_stereo_view_rendering, | |
| Extension::kSPV_KHR_shader_ballot}; | |
| EXPECT_FALSE(state_.HasAnyOfExtensions(set1)); | |
| EXPECT_FALSE(state_.HasAnyOfExtensions(set2)); | |
| state_.RegisterExtension(Extension::kSPV_KHR_multiview); | |
| EXPECT_TRUE(state_.HasAnyOfExtensions(set1)); | |
| EXPECT_FALSE(state_.HasAnyOfExtensions(set2)); | |
| } | |
| // A test of ValidationState_t::IsOpcodeInCurrentLayoutSection(). | |
| using ValidationState_InLayoutState = ValidationStateTest; | |
| TEST_F(ValidationState_InLayoutState, Variable) { | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutTypes); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpVariable)); | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDefinitions); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpVariable)); | |
| } | |
| TEST_F(ValidationState_InLayoutState, ExtInst) { | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutTypes); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpExtInst)); | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDefinitions); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpExtInst)); | |
| } | |
| TEST_F(ValidationState_InLayoutState, Undef) { | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutTypes); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpUndef)); | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDefinitions); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpUndef)); | |
| } | |
| TEST_F(ValidationState_InLayoutState, Function) { | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDeclarations); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpFunction)); | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDefinitions); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpFunction)); | |
| } | |
| TEST_F(ValidationState_InLayoutState, FunctionParameter) { | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDeclarations); | |
| EXPECT_TRUE( | |
| state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpFunctionParameter)); | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDefinitions); | |
| EXPECT_TRUE( | |
| state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpFunctionParameter)); | |
| } | |
| TEST_F(ValidationState_InLayoutState, FunctionEnd) { | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDeclarations); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpFunctionEnd)); | |
| state_.SetCurrentLayoutSectionForTesting(kLayoutFunctionDefinitions); | |
| EXPECT_TRUE(state_.IsOpcodeInCurrentLayoutSection(spv::Op::OpFunctionEnd)); | |
| } | |
| } // namespace | |
| } // namespace val | |
| } // namespace spvtools |