1 /*------------------------------------------------------------------------
2  * Vulkan Conformance Tests
3  * ------------------------
4  *
5  * Copyright (c) 2014 The Android Open Source Project
6  * Copyright (c) 2016 The Khronos Group Inc.
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *      http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  *
20  *//*!
21  * \file
22  * \brief Tessellation Limits Tests
23  *//*--------------------------------------------------------------------*/
24 
25 #include "vktTessellationLimitsTests.hpp"
26 #include "vktTestCaseUtil.hpp"
27 
28 #include "tcuTestLog.hpp"
29 
30 #include "vkDefs.hpp"
31 #include "vkQueryUtil.hpp"
32 
33 #include "deUniquePtr.hpp"
34 
35 namespace vkt
36 {
37 namespace tessellation
38 {
39 
40 using namespace vk;
41 
42 namespace
43 {
44 
45 enum TessellationLimits
46 {
47     LIMIT_MAX_TESSELLATION_GENERATION_LEVEL,
48     LIMIT_MAX_TESSELLATION_PATCH_SIZE,
49     LIMIT_MAX_TESSELLATION_CONTROL_PER_VERTEX_INPUT_COMPONENTS,
50     LIMIT_MAX_TESSELLATION_CONTROL_PER_VERTEX_OUTPUT_COMPONENTS,
51     LIMIT_MAX_TESSELLATION_CONTROL_PER_PATCH_OUTPUT_COMPONENTS,
52     LIMIT_MAX_TESSELLATION_CONTROL_TOTAL_OUTPUT_COMPONENTS,
53     LIMIT_MAX_TESSELLATION_EVALUATION_INPUT_COMPONENTS,
54     LIMIT_MAX_TESSELLATION_EVALUATION_OUTPUT_COMPONENTS,
55 };
56 
57 struct LimitsCaseDefinition
58 {
59     TessellationLimits limitType;
60     uint32_t minimum; //!< Implementation must provide at least this value
61 };
62 
expectGreaterOrEqual(tcu::TestLog & log,const uint32_t expected,const uint32_t actual)63 tcu::TestStatus expectGreaterOrEqual(tcu::TestLog &log, const uint32_t expected, const uint32_t actual)
64 {
65     log << tcu::TestLog::Message << "Expected: " << expected << ", got: " << actual << tcu::TestLog::EndMessage;
66 
67     if (actual >= expected)
68         return tcu::TestStatus::pass("OK");
69     else
70         return tcu::TestStatus::fail("Value doesn't meet minimal spec requirements");
71 }
72 
deviceLimitsTestCase(Context & context,const LimitsCaseDefinition caseDef)73 tcu::TestStatus deviceLimitsTestCase(Context &context, const LimitsCaseDefinition caseDef)
74 {
75     const InstanceInterface &vki            = context.getInstanceInterface();
76     const VkPhysicalDevice physDevice       = context.getPhysicalDevice();
77     const VkPhysicalDeviceFeatures features = getPhysicalDeviceFeatures(vki, physDevice);
78 
79     if (!features.tessellationShader)
80         throw tcu::NotSupportedError("Tessellation shader not supported");
81 
82     const VkPhysicalDeviceProperties properties = getPhysicalDeviceProperties(vki, physDevice);
83     tcu::TestLog &log                           = context.getTestContext().getLog();
84 
85     switch (caseDef.limitType)
86     {
87     case LIMIT_MAX_TESSELLATION_GENERATION_LEVEL:
88         return expectGreaterOrEqual(log, caseDef.minimum, properties.limits.maxTessellationGenerationLevel);
89     case LIMIT_MAX_TESSELLATION_PATCH_SIZE:
90         return expectGreaterOrEqual(log, caseDef.minimum, properties.limits.maxTessellationPatchSize);
91     case LIMIT_MAX_TESSELLATION_CONTROL_PER_VERTEX_INPUT_COMPONENTS:
92         return expectGreaterOrEqual(log, caseDef.minimum,
93                                     properties.limits.maxTessellationControlPerVertexInputComponents);
94     case LIMIT_MAX_TESSELLATION_CONTROL_PER_VERTEX_OUTPUT_COMPONENTS:
95         return expectGreaterOrEqual(log, caseDef.minimum,
96                                     properties.limits.maxTessellationControlPerVertexOutputComponents);
97     case LIMIT_MAX_TESSELLATION_CONTROL_PER_PATCH_OUTPUT_COMPONENTS:
98         return expectGreaterOrEqual(log, caseDef.minimum,
99                                     properties.limits.maxTessellationControlPerPatchOutputComponents);
100     case LIMIT_MAX_TESSELLATION_CONTROL_TOTAL_OUTPUT_COMPONENTS:
101         return expectGreaterOrEqual(log, caseDef.minimum,
102                                     properties.limits.maxTessellationControlTotalOutputComponents);
103     case LIMIT_MAX_TESSELLATION_EVALUATION_INPUT_COMPONENTS:
104         return expectGreaterOrEqual(log, caseDef.minimum, properties.limits.maxTessellationEvaluationInputComponents);
105     case LIMIT_MAX_TESSELLATION_EVALUATION_OUTPUT_COMPONENTS:
106         return expectGreaterOrEqual(log, caseDef.minimum, properties.limits.maxTessellationEvaluationOutputComponents);
107     }
108 
109     // Control should never get here.
110     DE_FATAL("Internal test error");
111     return tcu::TestStatus::fail("Test error");
112 }
113 
114 } // namespace
115 
116 //! These tests correspond roughly to dEQP-GLES31.functional.tessellation.state_query.*
createLimitsTests(tcu::TestContext & testCtx)117 tcu::TestCaseGroup *createLimitsTests(tcu::TestContext &testCtx)
118 {
119     de::MovePtr<tcu::TestCaseGroup> group(new tcu::TestCaseGroup(testCtx, "limits"));
120 
121     static const struct
122     {
123         std::string caseName;
124         LimitsCaseDefinition caseDef;
125     } cases[] = {
126         {"max_tessellation_generation_level", {LIMIT_MAX_TESSELLATION_GENERATION_LEVEL, 64}},
127         {"max_tessellation_patch_size", {LIMIT_MAX_TESSELLATION_PATCH_SIZE, 32}},
128         {"max_tessellation_control_per_vertex_input_components",
129          {LIMIT_MAX_TESSELLATION_CONTROL_PER_VERTEX_INPUT_COMPONENTS, 64}},
130         {"max_tessellation_control_per_vertex_output_components",
131          {LIMIT_MAX_TESSELLATION_CONTROL_PER_VERTEX_OUTPUT_COMPONENTS, 64}},
132         {"max_tessellation_control_per_patch_output_components",
133          {LIMIT_MAX_TESSELLATION_CONTROL_PER_PATCH_OUTPUT_COMPONENTS, 120}},
134         {"max_tessellation_control_total_output_components",
135          {LIMIT_MAX_TESSELLATION_CONTROL_TOTAL_OUTPUT_COMPONENTS, 2048}},
136         {"max_tessellation_evaluation_input_components", {LIMIT_MAX_TESSELLATION_EVALUATION_INPUT_COMPONENTS, 64}},
137         {"max_tessellation_evaluation_output_components", {LIMIT_MAX_TESSELLATION_EVALUATION_OUTPUT_COMPONENTS, 64}},
138     };
139 
140     for (int i = 0; i < DE_LENGTH_OF_ARRAY(cases); ++i)
141         addFunctionCase<LimitsCaseDefinition>(group.get(), cases[i].caseName, deviceLimitsTestCase, cases[i].caseDef);
142 
143     return group.release();
144 }
145 
146 } // namespace tessellation
147 } // namespace vkt
148