1 /*------------------------------------------------------------------------
2 * Vulkan Conformance Tests
3 * ------------------------
5 * Copyright (c) 2016 The Khronos Group Inc.
6 * Copyright (c) 2016 Samsung Electronics Co., Ltd.
7 * Copyright (c) 2014 The Android Open Source Project
9 * Licensed under the Apache License, Version 2.0 (the "License");
10 * you may not use this file except in compliance with the License.
11 * You may obtain a copy of the License at
13 * http://www.apache.org/licenses/LICENSE-2.0
15 * Unless required by applicable law or agreed to in writing, software
16 * distributed under the License is distributed on an "AS IS" BASIS,
17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18 * See the License for the specific language governing permissions and
19 * limitations under the License.
23 * \brief Texture test utilities.
24 *//*--------------------------------------------------------------------*/
26 #include "vktTextureTestUtil.hpp"
28 #include "deFilePath.hpp"
30 #include "tcuCompressedTexture.hpp"
31 #include "tcuImageIO.hpp"
32 #include "tcuStringTemplate.hpp"
33 #include "tcuTestLog.hpp"
34 #include "vkBuilderUtil.hpp"
35 #include "vkImageUtil.hpp"
36 #include "vkPrograms.hpp"
37 #include "vkQueryUtil.hpp"
38 #include "vkRefUtil.hpp"
39 #include "vkTypeUtil.hpp"
47 using namespace glu::TextureTestUtil;
56 struct ShaderParameters {
57 float bias; //!< User-supplied bias.
58 float ref; //!< Reference value for shadow lookups.
59 tcu::Vec2 padding; //!< Shader uniform padding.
60 tcu::Vec4 colorScale; //!< Scale for texture color values.
61 tcu::Vec4 colorBias; //!< Bias for texture color values.
64 const char* getProgramName(Program program)
68 case PROGRAM_2D_FLOAT: return "2D_FLOAT";
69 case PROGRAM_2D_INT: return "2D_INT";
70 case PROGRAM_2D_UINT: return "2D_UINT";
71 case PROGRAM_2D_SHADOW: return "2D_SHADOW";
72 case PROGRAM_2D_FLOAT_BIAS: return "2D_FLOAT_BIAS";
73 case PROGRAM_2D_INT_BIAS: return "2D_INT_BIAS";
74 case PROGRAM_2D_UINT_BIAS: return "2D_UINT_BIAS";
75 case PROGRAM_2D_SHADOW_BIAS: return "2D_SHADOW_BIAS";
76 case PROGRAM_1D_FLOAT: return "1D_FLOAT";
77 case PROGRAM_1D_INT: return "1D_INT";
78 case PROGRAM_1D_UINT: return "1D_UINT";
79 case PROGRAM_1D_SHADOW: return "1D_SHADOW";
80 case PROGRAM_1D_FLOAT_BIAS: return "1D_FLOAT_BIAS";
81 case PROGRAM_1D_INT_BIAS: return "1D_INT_BIAS";
82 case PROGRAM_1D_UINT_BIAS: return "1D_UINT_BIAS";
83 case PROGRAM_1D_SHADOW_BIAS: return "1D_SHADOW_BIAS";
84 case PROGRAM_CUBE_FLOAT: return "CUBE_FLOAT";
85 case PROGRAM_CUBE_INT: return "CUBE_INT";
86 case PROGRAM_CUBE_UINT: return "CUBE_UINT";
87 case PROGRAM_CUBE_SHADOW: return "CUBE_SHADOW";
88 case PROGRAM_CUBE_FLOAT_BIAS: return "CUBE_FLOAT_BIAS";
89 case PROGRAM_CUBE_INT_BIAS: return "CUBE_INT_BIAS";
90 case PROGRAM_CUBE_UINT_BIAS: return "CUBE_UINT_BIAS";
91 case PROGRAM_CUBE_SHADOW_BIAS: return "CUBE_SHADOW_BIAS";
92 case PROGRAM_2D_ARRAY_FLOAT: return "2D_ARRAY_FLOAT";
93 case PROGRAM_2D_ARRAY_INT: return "2D_ARRAY_INT";
94 case PROGRAM_2D_ARRAY_UINT: return "2D_ARRAY_UINT";
95 case PROGRAM_2D_ARRAY_SHADOW: return "2D_ARRAY_SHADOW";
96 case PROGRAM_3D_FLOAT: return "3D_FLOAT";
97 case PROGRAM_3D_INT: return "3D_INT";
98 case PROGRAM_3D_UINT: return "3D_UINT";
99 case PROGRAM_3D_FLOAT_BIAS: return "3D_FLOAT_BIAS";
100 case PROGRAM_3D_INT_BIAS: return "3D_INT_BIAS";
101 case PROGRAM_3D_UINT_BIAS: return "3D_UINT_BIAS";
102 case PROGRAM_CUBE_ARRAY_FLOAT: return "CUBE_ARRAY_FLOAT";
103 case PROGRAM_CUBE_ARRAY_INT: return "CUBE_ARRAY_INT";
104 case PROGRAM_CUBE_ARRAY_UINT: return "CUBE_ARRAY_UINT";
105 case PROGRAM_CUBE_ARRAY_SHADOW: return "CUBE_ARRAY_SHADOW";
106 case PROGRAM_1D_ARRAY_FLOAT: return "1D_ARRAY_FLOAT";
107 case PROGRAM_1D_ARRAY_INT: return "1D_ARRAY_INT";
108 case PROGRAM_1D_ARRAY_UINT: return "1D_ARRAY_UINT";
109 case PROGRAM_1D_ARRAY_SHADOW: return "1D_ARRAY_SHADOW";
110 case PROGRAM_BUFFER_FLOAT: return "BUFFER_FLOAT";
111 case PROGRAM_BUFFER_INT: return "BUFFER_INT";
112 case PROGRAM_BUFFER_UINT: return "BUFFER_UINT";
119 VkImageViewType textureTypeToImageViewType (TextureBinding::Type type)
123 case TextureBinding::TYPE_2D: return VK_IMAGE_VIEW_TYPE_2D;
124 case TextureBinding::TYPE_2D_ARRAY: return VK_IMAGE_VIEW_TYPE_2D_ARRAY;
125 case TextureBinding::TYPE_CUBE_MAP: return VK_IMAGE_VIEW_TYPE_CUBE;
126 case TextureBinding::TYPE_3D: return VK_IMAGE_VIEW_TYPE_3D;
131 return VK_IMAGE_VIEW_TYPE_2D;
134 VkImageType imageViewTypeToImageType (VkImageViewType type)
138 case VK_IMAGE_VIEW_TYPE_2D:
139 case VK_IMAGE_VIEW_TYPE_2D_ARRAY:
140 case VK_IMAGE_VIEW_TYPE_CUBE: return VK_IMAGE_TYPE_2D;
141 case VK_IMAGE_VIEW_TYPE_3D: return VK_IMAGE_TYPE_3D;
146 return VK_IMAGE_TYPE_2D;
149 void initializePrograms(vk::SourceCollections& programCollection, glu::Precision texCoordPrecision, const std::vector<Program>& programs)
151 static const char* vertShaderTemplate =
153 "layout(location = 0) ${VTX_IN} highp vec4 a_position;\n"
154 "layout(location = 1) ${VTX_IN} ${PRECISION} ${TEXCOORD_TYPE} a_texCoord;\n"
155 "layout(location = 0) ${VTX_OUT} ${PRECISION} ${TEXCOORD_TYPE} v_texCoord;\n"
156 "${VTX_OUT} gl_PerVertex { vec4 gl_Position; };\n"
160 " gl_Position = a_position;\n"
161 " v_texCoord = a_texCoord;\n"
164 static const char* fragShaderTemplate =
166 "layout(location = 0) ${FRAG_IN} ${PRECISION} ${TEXCOORD_TYPE} v_texCoord;\n"
167 "layout(location = 0) out mediump vec4 ${FRAG_COLOR};\n"
168 "layout (set=0, binding=0, std140) uniform Block \n"
170 " ${PRECISION} float u_bias;\n"
171 " ${PRECISION} float u_ref;\n"
172 " ${PRECISION} vec4 u_colorScale;\n"
173 " ${PRECISION} vec4 u_colorBias;\n"
175 "layout (set=1, binding=0) uniform ${PRECISION} ${SAMPLER_TYPE} u_sampler;\n"
178 " ${FRAG_COLOR} = ${LOOKUP} * u_colorScale + u_colorBias;\n"
181 tcu::StringTemplate vertexSource (vertShaderTemplate);
182 tcu::StringTemplate fragmentSource (fragShaderTemplate);
184 for (std::vector<Program>::const_iterator programIt = programs.begin(); programIt != programs.end(); ++programIt)
186 Program program = *programIt;
187 std::map<std::string, std::string> params;
189 bool isCube = de::inRange<int>(program, PROGRAM_CUBE_FLOAT, PROGRAM_CUBE_SHADOW_BIAS);
190 bool isArray = de::inRange<int>(program, PROGRAM_2D_ARRAY_FLOAT, PROGRAM_2D_ARRAY_SHADOW)
191 || de::inRange<int>(program, PROGRAM_1D_ARRAY_FLOAT, PROGRAM_1D_ARRAY_SHADOW);
193 bool is1D = de::inRange<int>(program, PROGRAM_1D_FLOAT, PROGRAM_1D_SHADOW_BIAS)
194 || de::inRange<int>(program, PROGRAM_1D_ARRAY_FLOAT, PROGRAM_1D_ARRAY_SHADOW)
195 || de::inRange<int>(program, PROGRAM_BUFFER_FLOAT, PROGRAM_BUFFER_UINT);
197 bool is2D = de::inRange<int>(program, PROGRAM_2D_FLOAT, PROGRAM_2D_SHADOW_BIAS)
198 || de::inRange<int>(program, PROGRAM_2D_ARRAY_FLOAT, PROGRAM_2D_ARRAY_SHADOW);
200 bool is3D = de::inRange<int>(program, PROGRAM_3D_FLOAT, PROGRAM_3D_UINT_BIAS);
201 bool isCubeArray = de::inRange<int>(program, PROGRAM_CUBE_ARRAY_FLOAT, PROGRAM_CUBE_ARRAY_SHADOW);
203 const std::string version = glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_450);
205 params["FRAG_HEADER"] = version + "\n";
206 params["VTX_HEADER"] = version + "\n";
207 params["VTX_IN"] = "in";
208 params["VTX_OUT"] = "out";
209 params["FRAG_IN"] = "in";
210 params["FRAG_COLOR"] = "dEQP_FragColor";
212 params["PRECISION"] = glu::getPrecisionName(texCoordPrecision);
215 params["TEXCOORD_TYPE"] = "vec4";
216 else if (isCube || (is2D && isArray) || is3D)
217 params["TEXCOORD_TYPE"] = "vec3";
218 else if ((is1D && isArray) || is2D)
219 params["TEXCOORD_TYPE"] = "vec2";
221 params["TEXCOORD_TYPE"] = "float";
225 const char* sampler = DE_NULL;
226 const char* lookup = DE_NULL;
230 case PROGRAM_2D_FLOAT: sampler = "sampler2D"; lookup = "texture(u_sampler, v_texCoord)"; break;
231 case PROGRAM_2D_INT: sampler = "isampler2D"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
232 case PROGRAM_2D_UINT: sampler = "usampler2D"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
233 case PROGRAM_2D_SHADOW: sampler = "sampler2DShadow"; lookup = "vec4(texture(u_sampler, vec3(v_texCoord, u_ref)), 0.0, 0.0, 1.0)"; break;
234 case PROGRAM_2D_FLOAT_BIAS: sampler = "sampler2D"; lookup = "texture(u_sampler, v_texCoord, u_bias)"; break;
235 case PROGRAM_2D_INT_BIAS: sampler = "isampler2D"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
236 case PROGRAM_2D_UINT_BIAS: sampler = "usampler2D"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
237 case PROGRAM_2D_SHADOW_BIAS: sampler = "sampler2DShadow"; lookup = "vec4(texture(u_sampler, vec3(v_texCoord, u_ref), u_bias), 0.0, 0.0, 1.0)"; break;
238 case PROGRAM_1D_FLOAT: sampler = "sampler1D"; lookup = "texture(u_sampler, v_texCoord)"; break;
239 case PROGRAM_1D_INT: sampler = "isampler1D"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
240 case PROGRAM_1D_UINT: sampler = "usampler1D"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
241 case PROGRAM_1D_SHADOW: sampler = "sampler1DShadow"; lookup = "vec4(texture(u_sampler, vec3(v_texCoord, 0.0, u_ref)), 0.0, 0.0, 1.0)"; break;
242 case PROGRAM_1D_FLOAT_BIAS: sampler = "sampler1D"; lookup = "texture(u_sampler, v_texCoord, u_bias)"; break;
243 case PROGRAM_1D_INT_BIAS: sampler = "isampler1D"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
244 case PROGRAM_1D_UINT_BIAS: sampler = "usampler1D"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
245 case PROGRAM_1D_SHADOW_BIAS: sampler = "sampler1DShadow"; lookup = "vec4(texture(u_sampler, vec3(v_texCoord, 0.0, u_ref), u_bias), 0.0, 0.0, 1.0)"; break;
246 case PROGRAM_CUBE_FLOAT: sampler = "samplerCube"; lookup = "texture(u_sampler, v_texCoord)"; break;
247 case PROGRAM_CUBE_INT: sampler = "isamplerCube"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
248 case PROGRAM_CUBE_UINT: sampler = "usamplerCube"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
249 case PROGRAM_CUBE_SHADOW: sampler = "samplerCubeShadow"; lookup = "vec4(texture(u_sampler, vec4(v_texCoord, u_ref)), 0.0, 0.0, 1.0)"; break;
250 case PROGRAM_CUBE_FLOAT_BIAS: sampler = "samplerCube"; lookup = "texture(u_sampler, v_texCoord, u_bias)"; break;
251 case PROGRAM_CUBE_INT_BIAS: sampler = "isamplerCube"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
252 case PROGRAM_CUBE_UINT_BIAS: sampler = "usamplerCube"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
253 case PROGRAM_CUBE_SHADOW_BIAS: sampler = "samplerCubeShadow"; lookup = "vec4(texture(u_sampler, vec4(v_texCoord, u_ref), u_bias), 0.0, 0.0, 1.0)"; break;
254 case PROGRAM_2D_ARRAY_FLOAT: sampler = "sampler2DArray"; lookup = "texture(u_sampler, v_texCoord)"; break;
255 case PROGRAM_2D_ARRAY_INT: sampler = "isampler2DArray"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
256 case PROGRAM_2D_ARRAY_UINT: sampler = "usampler2DArray"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
257 case PROGRAM_2D_ARRAY_SHADOW: sampler = "sampler2DArrayShadow"; lookup = "vec4(texture(u_sampler, vec4(v_texCoord, u_ref)), 0.0, 0.0, 1.0)"; break;
258 case PROGRAM_3D_FLOAT: sampler = "sampler3D"; lookup = "texture(u_sampler, v_texCoord)"; break;
259 case PROGRAM_3D_INT: sampler = "isampler3D"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
260 case PROGRAM_3D_UINT: sampler = "usampler3D"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
261 case PROGRAM_3D_FLOAT_BIAS: sampler = "sampler3D"; lookup = "texture(u_sampler, v_texCoord, u_bias)"; break;
262 case PROGRAM_3D_INT_BIAS: sampler = "isampler3D"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
263 case PROGRAM_3D_UINT_BIAS: sampler = "usampler3D"; lookup = "vec4(texture(u_sampler, v_texCoord, u_bias))"; break;
264 case PROGRAM_CUBE_ARRAY_FLOAT: sampler = "samplerCubeArray"; lookup = "texture(u_sampler, v_texCoord)"; break;
265 case PROGRAM_CUBE_ARRAY_INT: sampler = "isamplerCubeArray"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
266 case PROGRAM_CUBE_ARRAY_UINT: sampler = "usamplerCubeArray"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
267 case PROGRAM_CUBE_ARRAY_SHADOW: sampler = "samplerCubeArrayShadow"; lookup = "vec4(texture(u_sampler, v_texCoord, u_ref), 0.0, 0.0, 1.0)"; break;
268 case PROGRAM_1D_ARRAY_FLOAT: sampler = "sampler1DArray"; lookup = "texture(u_sampler, v_texCoord)"; break;
269 case PROGRAM_1D_ARRAY_INT: sampler = "isampler1DArray"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
270 case PROGRAM_1D_ARRAY_UINT: sampler = "usampler1DArray"; lookup = "vec4(texture(u_sampler, v_texCoord))"; break;
271 case PROGRAM_1D_ARRAY_SHADOW: sampler = "sampler1DArrayShadow"; lookup = "vec4(texture(u_sampler, vec3(v_texCoord, u_ref)), 0.0, 0.0, 1.0)"; break;
272 case PROGRAM_BUFFER_FLOAT: sampler = "samplerBuffer"; lookup = "texelFetch(u_sampler, int(v_texCoord))"; break;
273 case PROGRAM_BUFFER_INT: sampler = "isamplerBuffer"; lookup = "vec4(texelFetch(u_sampler, int(v_texCoord)))"; break;
274 case PROGRAM_BUFFER_UINT: sampler = "usamplerBuffer"; lookup = "vec4(texelFetch(u_sampler, int(v_texCoord)))"; break;
279 params["SAMPLER_TYPE"] = sampler;
280 params["LOOKUP"] = lookup;
282 programCollection.glslSources.add("vertext_" + std::string(getProgramName(program))) << glu::VertexSource(vertexSource.specialize(params));
283 programCollection.glslSources.add("fragment_" + std::string(getProgramName(program))) << glu::FragmentSource(fragmentSource.specialize(params));
287 TextureBinding::TextureBinding (Context& context)
288 : m_context (context)
292 TextureBinding::TextureBinding (Context& context, const TestTextureSp& textureData, const TextureBinding::Type type)
293 : m_context (context)
295 , m_textureData (textureData)
297 updateTextureData(m_textureData, m_type);
300 void TextureBinding::updateTextureData (const TestTextureSp& textureData, const TextureBinding::Type textureType)
302 const DeviceInterface& vkd = m_context.getDeviceInterface();
303 const VkDevice vkDevice = m_context.getDevice();
304 const VkQueue queue = m_context.getUniversalQueue();
305 const deUint32 queueFamilyIndex = m_context.getUniversalQueueFamilyIndex();
306 Allocator& allocator = m_context.getDefaultAllocator();
308 m_type = textureType;
309 m_textureData = textureData;
311 const bool isCube = m_type == TYPE_CUBE_MAP;
312 const VkImageCreateFlags imageCreateFlags = isCube ? VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT : 0;
313 const VkImageViewType imageViewType = textureTypeToImageViewType(textureType);
314 const VkImageType imageType = imageViewTypeToImageType(imageViewType);
315 const VkImageTiling imageTiling = VK_IMAGE_TILING_OPTIMAL;
316 const VkImageUsageFlags imageUsageFlags = VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT;
317 const VkFormat format = textureData->isCompressed() ? mapCompressedTextureFormat(textureData->getCompressedLevel(0, 0).getFormat()) : mapTextureFormat(textureData->getTextureFormat());
318 const tcu::UVec3 textureDimension = textureData->getTextureDimension();
319 const deUint32 mipLevels = textureData->getNumLevels();
320 const deUint32 arraySize = textureData->getArraySize();
321 vk::VkImageFormatProperties imageFormatProperties;
322 const VkResult imageFormatQueryResult = m_context.getInstanceInterface().getPhysicalDeviceImageFormatProperties(m_context.getPhysicalDevice(), format, imageType, imageTiling, imageUsageFlags, imageCreateFlags, &imageFormatProperties);
324 if (imageFormatQueryResult == VK_ERROR_FORMAT_NOT_SUPPORTED)
326 TCU_THROW(NotSupportedError, (std::string("Format not supported: ") + vk::getFormatName(format)).c_str());
329 VK_CHECK(imageFormatQueryResult);
331 if (imageFormatProperties.maxArrayLayers < arraySize)
332 TCU_THROW(NotSupportedError, ("Maximum array layers number for this format is not enough for this test."));
334 if (imageFormatProperties.maxMipLevels < mipLevels)
335 TCU_THROW(NotSupportedError, ("Maximum mimap level number for this format is not enough for this test."));
337 if (imageFormatProperties.maxExtent.width < textureDimension.x() ||
338 imageFormatProperties.maxExtent.height < textureDimension.y() ||
339 imageFormatProperties.maxExtent.depth < textureDimension.z())
341 TCU_THROW(NotSupportedError, ("Maximum image dimension for this format is not enough for this test."));
345 const VkImageCreateInfo imageParams =
347 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType;
348 DE_NULL, // const void* pNext;
349 imageCreateFlags, // VkImageCreateFlags flags;
350 imageType, // VkImageType imageType;
351 format, // VkFormat format;
352 { // VkExtent3D extent;
353 (deUint32)textureDimension.x(),
354 (deUint32)textureDimension.y(),
355 (deUint32)textureDimension.z()
357 mipLevels, // deUint32 mipLevels;
358 arraySize, // deUint32 arrayLayers;
359 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples;
360 imageTiling, // VkImageTiling tiling;
361 imageUsageFlags, // VkImageUsageFlags usage;
362 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
363 1u, // deUint32 queueFamilyIndexCount;
364 &queueFamilyIndex, // const deUint32* pQueueFamilyIndices;
365 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout;
368 m_textureImage = createImage(vkd, vkDevice, &imageParams);
369 m_textureImageMemory = allocator.allocate(getImageMemoryRequirements(vkd, vkDevice, *m_textureImage), MemoryRequirement::Any);
370 VK_CHECK(vkd.bindImageMemory(vkDevice, *m_textureImage, m_textureImageMemory->getMemory(), m_textureImageMemory->getOffset()));
372 updateTextureViewMipLevels(0, mipLevels - 1);
374 pipeline::uploadTestTexture(vkd, vkDevice, queue, queueFamilyIndex, allocator, *m_textureData, *m_textureImage);
377 void TextureBinding::updateTextureViewMipLevels (deUint32 baseLevel, deUint32 maxLevel)
379 const DeviceInterface& vkd = m_context.getDeviceInterface();
380 const VkDevice vkDevice = m_context.getDevice();
381 const vk::VkImageViewType imageViewType = textureTypeToImageViewType(m_type);
382 const vk::VkFormat format = m_textureData->isCompressed() ? mapCompressedTextureFormat(m_textureData->getCompressedLevel(0, 0).getFormat()) : mapTextureFormat(m_textureData->getTextureFormat());
383 const bool isShadowTexture = tcu::hasDepthComponent(m_textureData->getTextureFormat().order);
384 const VkImageAspectFlags aspectMask = isShadowTexture ? VK_IMAGE_ASPECT_DEPTH_BIT : VK_IMAGE_ASPECT_COLOR_BIT;
385 const deUint32 layerCount = m_textureData->getArraySize();
386 const vk::VkImageViewCreateInfo viewParams =
388 vk::VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType;
389 NULL, // const voide* pNext;
390 0u, // VkImageViewCreateFlags flags;
391 *m_textureImage, // VkImage image;
392 imageViewType, // VkImageViewType viewType;
393 format, // VkFormat format;
394 makeComponentMappingRGBA(), // VkComponentMapping components;
396 aspectMask, // VkImageAspectFlags aspectMask;
397 baseLevel, // deUint32 baseMipLevel;
398 maxLevel-baseLevel+1, // deUint32 levelCount;
399 0, // deUint32 baseArrayLayer;
400 layerCount // deUint32 layerCount;
401 }, // VkImageSubresourceRange subresourceRange;
404 m_textureImageView = createImageView(vkd, vkDevice, &viewParams);
407 const deUint16 TextureRenderer::s_vertexIndices[6] = { 0, 1, 2, 2, 1, 3 };
408 const VkDeviceSize TextureRenderer::s_vertexIndexBufferSize = sizeof(TextureRenderer::s_vertexIndices);
410 TextureRenderer::TextureRenderer (Context& context, VkSampleCountFlagBits sampleCount, deUint32 renderWidth, deUint32 renderHeight)
411 : m_context (context)
412 , m_log (context.getTestContext().getLog())
413 , m_renderWidth (renderWidth)
414 , m_renderHeight (renderHeight)
415 , m_sampleCount (sampleCount)
416 , m_multisampling (m_sampleCount != VK_SAMPLE_COUNT_1_BIT)
417 , m_imageFormat (VK_FORMAT_R8G8B8A8_UNORM)
418 , m_textureFormat (vk::mapVkFormat(m_imageFormat))
419 , m_uniformBufferSize (sizeof(ShaderParameters))
420 , m_resultBufferSize (renderWidth * renderHeight * m_textureFormat.getPixelSize())
421 , m_viewportOffsetX (0.0f)
422 , m_viewportOffsetY (0.0f)
423 , m_viewportWidth ((float)renderWidth)
424 , m_viewportHeight ((float)renderHeight)
426 const DeviceInterface& vkd = m_context.getDeviceInterface();
427 const VkDevice vkDevice = m_context.getDevice();
428 const deUint32 queueFamilyIndex = m_context.getUniversalQueueFamilyIndex();
429 Allocator& allocator = m_context.getDefaultAllocator();
432 m_commandPool = createCommandPool(vkd, vkDevice, VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT, queueFamilyIndex);
436 const VkImageUsageFlags imageUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT;
437 VkImageFormatProperties properties;
439 if ((m_context.getInstanceInterface().getPhysicalDeviceImageFormatProperties(m_context.getPhysicalDevice(),
442 VK_IMAGE_TILING_OPTIMAL,
445 &properties) == VK_ERROR_FORMAT_NOT_SUPPORTED))
447 TCU_THROW(NotSupportedError, "Format not supported");
450 if ((properties.sampleCounts & m_sampleCount) != m_sampleCount)
452 TCU_THROW(NotSupportedError, "Format not supported");
455 const VkImageCreateInfo imageCreateInfo =
457 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType;
458 DE_NULL, // const void* pNext;
459 0u, // VkImageCreateFlags flags;
460 VK_IMAGE_TYPE_2D, // VkImageType imageType;
461 m_imageFormat, // VkFormat format;
462 { m_renderWidth, m_renderHeight, 1u }, // VkExtent3D extent;
463 1u, // deUint32 mipLevels;
464 1u, // deUint32 arrayLayers;
465 m_sampleCount, // VkSampleCountFlagBits samples;
466 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling;
467 imageUsage, // VkImageUsageFlags usage;
468 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
469 1u, // deUint32 queueFamilyIndexCount;
470 &queueFamilyIndex, // const deUint32* pQueueFamilyIndices;
471 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout;
474 m_image = vk::createImage(vkd, vkDevice, &imageCreateInfo, DE_NULL);
476 m_imageMemory = allocator.allocate(getImageMemoryRequirements(vkd, vkDevice, *m_image), MemoryRequirement::Any);
477 VK_CHECK(vkd.bindImageMemory(vkDevice, *m_image, m_imageMemory->getMemory(), m_imageMemory->getOffset()));
482 const VkImageViewCreateInfo imageViewCreateInfo =
484 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType;
485 DE_NULL, // const void* pNext;
486 0u, // VkImageViewCreateFlags flags;
487 *m_image, // VkImage image;
488 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType;
489 m_imageFormat, // VkFormat format;
490 makeComponentMappingRGBA(), // VkComponentMapping components;
492 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask;
493 0u, // deUint32 baseMipLevel;
494 1u, // deUint32 mipLevels;
495 0u, // deUint32 baseArrayLayer;
496 1u, // deUint32 arraySize;
497 }, // VkImageSubresourceRange subresourceRange;
500 m_imageView = vk::createImageView(vkd, vkDevice, &imageViewCreateInfo, DE_NULL);
507 const VkImageUsageFlags imageUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT;
508 VkImageFormatProperties properties;
510 if ((m_context.getInstanceInterface().getPhysicalDeviceImageFormatProperties(m_context.getPhysicalDevice(),
513 VK_IMAGE_TILING_OPTIMAL,
516 &properties) == VK_ERROR_FORMAT_NOT_SUPPORTED))
518 TCU_THROW(NotSupportedError, "Format not supported");
521 const VkImageCreateInfo imageCreateInfo =
523 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType;
524 DE_NULL, // const void* pNext;
525 0u, // VkImageCreateFlags flags;
526 VK_IMAGE_TYPE_2D, // VkImageType imageType;
527 m_imageFormat, // VkFormat format;
528 { m_renderWidth, m_renderHeight, 1u }, // VkExtent3D extent;
529 1u, // deUint32 mipLevels;
530 1u, // deUint32 arrayLayers;
531 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples;
532 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling;
533 imageUsage, // VkImageUsageFlags usage;
534 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
535 1u, // deUint32 queueFamilyIndexCount;
536 &queueFamilyIndex, // const deUint32* pQueueFamilyIndices;
537 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout;
540 m_resolvedImage = vk::createImage(vkd, vkDevice, &imageCreateInfo, DE_NULL);
541 m_resolvedImageMemory = allocator.allocate(getImageMemoryRequirements(vkd, vkDevice, *m_resolvedImage), MemoryRequirement::Any);
542 VK_CHECK(vkd.bindImageMemory(vkDevice, *m_resolvedImage, m_resolvedImageMemory->getMemory(), m_resolvedImageMemory->getOffset()));
545 // Resolved Image View
547 const VkImageViewCreateInfo imageViewCreateInfo =
549 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType;
550 DE_NULL, // const void* pNext;
551 0u, // VkImageViewCreateFlags flags;
552 *m_resolvedImage, // VkImage image;
553 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType;
554 m_imageFormat, // VkFormat format;
555 makeComponentMappingRGBA(), // VkComponentMapping components;
557 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask;
558 0u, // deUint32 baseMipLevel;
559 1u, // deUint32 mipLevels;
560 0u, // deUint32 baseArrayLayer;
561 1u, // deUint32 arraySize;
562 }, // VkImageSubresourceRange subresourceRange;
565 m_resolvedImageView = vk::createImageView(vkd, vkDevice, &imageViewCreateInfo, DE_NULL);
571 const VkImageLayout imageLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
572 const VkAttachmentDescription attachmentDesc[] =
575 0u, // VkAttachmentDescriptionFlags flags;
576 m_imageFormat, // VkFormat format;
577 m_sampleCount, // VkSampleCountFlagBits samples;
578 VK_ATTACHMENT_LOAD_OP_LOAD, // VkAttachmentLoadOp loadOp;
579 VK_ATTACHMENT_STORE_OP_STORE, // VkAttachmentStoreOp storeOp;
580 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp stencilLoadOp;
581 VK_ATTACHMENT_STORE_OP_DONT_CARE, // VkAttachmentStoreOp stencilStoreOp;
582 imageLayout, // VkImageLayout initialLayout;
583 imageLayout, // VkImageLayout finalLayout;
586 0u, // VkAttachmentDescriptionFlags flags;
587 m_imageFormat, // VkFormat format;
588 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples;
589 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp loadOp;
590 VK_ATTACHMENT_STORE_OP_STORE, // VkAttachmentStoreOp storeOp;
591 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp stencilLoadOp;
592 VK_ATTACHMENT_STORE_OP_DONT_CARE, // VkAttachmentStoreOp stencilStoreOp;
593 imageLayout, // VkImageLayout initialLayout;
594 imageLayout, // VkImageLayout finalLayout;
598 const VkAttachmentReference attachmentRef =
600 0u, // deUint32 attachment;
601 imageLayout, // VkImageLayout layout;
604 const VkAttachmentReference resolveAttachmentRef =
606 1u, // deUint32 attachment;
607 imageLayout, // VkImageLayout layout;
610 const VkSubpassDescription subpassDesc =
612 0u, // VkSubpassDescriptionFlags flags;
613 VK_PIPELINE_BIND_POINT_GRAPHICS, // VkPipelineBindPoint pipelineBindPoint;
614 0u, // deUint32 inputAttachmentCount;
615 DE_NULL, // const VkAttachmentReference* pInputAttachments;
616 1u, // deUint32 colorAttachmentCount;
617 &attachmentRef, // const VkAttachmentReference* pColorAttachments;
618 m_multisampling ? &resolveAttachmentRef : DE_NULL, // const VkAttachmentReference* pResolveAttachments;
619 DE_NULL, // const VkAttachmentReference* pDepthStencilAttachment;
620 0u, // deUint32 preserveAttachmentCount;
621 DE_NULL, // const VkAttachmentReference* pPreserveAttachments;
624 const VkRenderPassCreateInfo renderPassCreateInfo =
626 VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO, // VkStructureType sType;
627 DE_NULL, // const void* pNext;
628 0u, // VkRenderPassCreateFlags flags;
629 m_multisampling ? 2u : 1u, // deUint32 attachmentCount;
630 attachmentDesc, // const VkAttachmentDescription* pAttachments;
631 1u, // deUint32 subpassCount;
632 &subpassDesc, // const VkSubpassDescription* pSubpasses;
633 0u, // deUint32 dependencyCount;
634 DE_NULL, // const VkSubpassDependency* pDependencies;
637 m_renderPass = createRenderPass(vkd, vkDevice, &renderPassCreateInfo, DE_NULL);
640 // Vertex index buffer
642 const VkBufferCreateInfo indexBufferParams =
644 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType;
645 DE_NULL, // const void* pNext;
646 0u, // VkBufferCreateFlags flags;
647 s_vertexIndexBufferSize, // VkDeviceSize size;
648 VK_BUFFER_USAGE_INDEX_BUFFER_BIT, // VkBufferUsageFlags usage;
649 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
650 1u, // deUint32 queueFamilyCount;
651 &queueFamilyIndex // const deUint32* pQueueFamilyIndices;
654 m_vertexIndexBuffer = createBuffer(vkd, vkDevice, &indexBufferParams);
655 m_vertexIndexBufferMemory = allocator.allocate(getBufferMemoryRequirements(vkd, vkDevice, *m_vertexIndexBuffer), MemoryRequirement::HostVisible);
657 VK_CHECK(vkd.bindBufferMemory(vkDevice, *m_vertexIndexBuffer, m_vertexIndexBufferMemory->getMemory(), m_vertexIndexBufferMemory->getOffset()));
659 // Load vertices into vertex buffer
660 deMemcpy(m_vertexIndexBufferMemory->getHostPtr(), s_vertexIndices, s_vertexIndexBufferSize);
661 flushMappedMemoryRange(vkd, vkDevice, m_vertexIndexBufferMemory->getMemory(), m_vertexIndexBufferMemory->getOffset(), VK_WHOLE_SIZE);
666 const VkImageView attachments[] =
669 *m_resolvedImageView,
672 const VkFramebufferCreateInfo framebufferCreateInfo =
674 VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO, // VkStructureType sType;
675 DE_NULL, // const void* pNext;
676 0u, // VkFramebufferCreateFlags flags;
677 *m_renderPass, // VkRenderPass renderPass;
678 m_multisampling ? 2u : 1u, // deUint32 attachmentCount;
679 attachments, // const VkImageView* pAttachments;
680 m_renderWidth, // deUint32 width;
681 m_renderHeight, // deUint32 height;
682 1u, // deUint32 layers;
685 m_frameBuffer = createFramebuffer(vkd, vkDevice, &framebufferCreateInfo, DE_NULL);
690 const VkBufferCreateInfo bufferCreateInfo =
692 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType;
693 DE_NULL, // const void* pNext;
694 0u, // VkBufferCreateFlags flags;
695 m_uniformBufferSize, // VkDeviceSize size;
696 VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT, // VkBufferUsageFlags usage;
697 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
698 1u, // deUint32 queueFamilyIndexCount;
699 &queueFamilyIndex // const deUint32* pQueueFamilyIndices;
702 m_uniformBuffer = createBuffer(vkd, vkDevice, &bufferCreateInfo);
703 m_uniformBufferMemory = allocator.allocate(getBufferMemoryRequirements(vkd, vkDevice, *m_uniformBuffer), MemoryRequirement::HostVisible);
705 VK_CHECK(vkd.bindBufferMemory(vkDevice, *m_uniformBuffer, m_uniformBufferMemory->getMemory(), m_uniformBufferMemory->getOffset()));
710 DescriptorPoolBuilder descriptorPoolBuilder;
712 descriptorPoolBuilder.addType(VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER);
713 descriptorPoolBuilder.addType(VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER);
714 m_descriptorPool = descriptorPoolBuilder.build(vkd, vkDevice, VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT, 2u);
718 m_fence = createFence(vkd, vkDevice);
722 const VkBufferCreateInfo bufferCreateInfo =
724 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType;
725 DE_NULL, // const void* pNext;
726 0u, // VkBufferCreateFlags flags;
727 m_resultBufferSize, // VkDeviceSize size;
728 VK_BUFFER_USAGE_TRANSFER_DST_BIT, // VkBufferUsageFlags usage;
729 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
730 1u, // deUint32 queueFamilyIndexCount;
731 &queueFamilyIndex // const deUint32* pQueueFamilyIndices;
734 m_resultBuffer = createBuffer(vkd, vkDevice, &bufferCreateInfo);
735 m_resultBufferMemory = allocator.allocate(getBufferMemoryRequirements(vkd, vkDevice, *m_resultBuffer), MemoryRequirement::HostVisible);
737 VK_CHECK(vkd.bindBufferMemory(vkDevice, *m_resultBuffer, m_resultBufferMemory->getMemory(), m_resultBufferMemory->getOffset()));
740 clearImage(*m_image);
742 clearImage(*m_resolvedImage);
745 TextureRenderer::~TextureRenderer (void)
749 void TextureRenderer::clearImage(VkImage image)
751 const DeviceInterface& vkd = m_context.getDeviceInterface();
752 const VkDevice vkDevice = m_context.getDevice();
753 Move<VkCommandBuffer> commandBuffer;
754 const VkQueue queue = m_context.getUniversalQueue();
756 const VkImageSubresourceRange subResourcerange =
758 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask;
759 0, // deUint32 baseMipLevel;
760 1, // deUint32 levelCount;
761 0, // deUint32 baseArrayLayer;
762 1 // deUint32 layerCount;
765 commandBuffer = allocateCommandBuffer(vkd, vkDevice, *m_commandPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
767 const VkCommandBufferBeginInfo cmdBufferBeginInfo =
769 VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO, // VkStructureType sType;
770 DE_NULL, // const void* pNext;
771 0u, // VkCmdBufferOptimizeFlags flags;
772 DE_NULL // const VkCommandBufferInheritanceInfo* pInheritanceInfo;
775 VK_CHECK(vkd.beginCommandBuffer(*commandBuffer, &cmdBufferBeginInfo));
777 addImageTransitionBarrier(*commandBuffer, image,
778 VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, // VkPipelineStageFlags srcStageMask
779 VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, // VkPipelineStageFlags dstStageMask
780 0, // VkAccessFlags srcAccessMask
781 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags dstAccessMask
782 VK_IMAGE_LAYOUT_UNDEFINED, // VkImageLayout oldLayout;
783 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL); // VkImageLayout newLayout;
785 VkClearColorValue color = makeClearValueColorF32(0.0f, 0.0f, 0.0f, 1.0f).color;
786 vkd.cmdClearColorImage(*commandBuffer, image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &color, 1, &subResourcerange);
788 addImageTransitionBarrier(*commandBuffer, image,
789 VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, // VkPipelineStageFlags srcStageMask
790 VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, // VkPipelineStageFlags dstStageMask
791 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags srcAccessMask
792 VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, // VkAccessFlags dstAccessMask
793 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, // VkImageLayout oldLayout;
794 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL); // VkImageLayout newLayout;
796 VK_CHECK(vkd.endCommandBuffer(*commandBuffer));
798 const VkSubmitInfo submitInfo =
800 VK_STRUCTURE_TYPE_SUBMIT_INFO, // VkStructureType sType;
801 DE_NULL, // const void* pNext;
802 0u, // deUint32 waitSemaphoreCount;
803 DE_NULL, // const VkSemaphore* pWaitSemaphores;
804 DE_NULL, // const VkPipelineStageFlags* pWaitDstStageMask;
805 1u, // deUint32 commandBufferCount;
806 &commandBuffer.get(), // const VkCommandBuffer* pCommandBuffers;
807 0u, // deUint32 signalSemaphoreCount;
808 DE_NULL, // const VkSemaphore* pSignalSemaphores;
811 VK_CHECK(vkd.resetFences(vkDevice, 1, &m_fence.get()));
812 VK_CHECK(vkd.queueSubmit(queue, 1, &submitInfo, *m_fence));
813 VK_CHECK(vkd.waitForFences(vkDevice, 1, &m_fence.get(), true, ~(0ull) /* infinity */));
816 void TextureRenderer::add2DTexture (const TestTexture2DSp& texture)
818 m_textureBindings.push_back(TextureBindingSp(new TextureBinding(m_context, texture, TextureBinding::TYPE_2D)));
821 void TextureRenderer::addCubeTexture (const TestTextureCubeSp& texture)
823 m_textureBindings.push_back(TextureBindingSp(new TextureBinding(m_context, texture, TextureBinding::TYPE_CUBE_MAP)));
826 void TextureRenderer::add2DArrayTexture (const TestTexture2DArraySp& texture)
828 m_textureBindings.push_back(TextureBindingSp(new TextureBinding(m_context, texture, TextureBinding::TYPE_2D_ARRAY)));
831 void TextureRenderer::add3DTexture (const TestTexture3DSp& texture)
833 m_textureBindings.push_back(TextureBindingSp(new TextureBinding(m_context, texture, TextureBinding::TYPE_3D)));
836 const pipeline::TestTexture2D& TextureRenderer::get2DTexture (int textureIndex) const
838 DE_ASSERT(m_textureBindings.size() > (size_t)textureIndex);
839 DE_ASSERT(m_textureBindings[textureIndex]->getType() == TextureBinding::TYPE_2D);
841 return dynamic_cast<const pipeline::TestTexture2D&>(m_textureBindings[textureIndex]->getTestTexture());
844 const pipeline::TestTextureCube& TextureRenderer::getCubeTexture (int textureIndex) const
846 DE_ASSERT(m_textureBindings.size() > (size_t)textureIndex);
847 DE_ASSERT(m_textureBindings[textureIndex]->getType() == TextureBinding::TYPE_CUBE_MAP);
849 return dynamic_cast<const pipeline::TestTextureCube&>(m_textureBindings[textureIndex]->getTestTexture());
852 const pipeline::TestTexture2DArray& TextureRenderer::get2DArrayTexture (int textureIndex) const
854 DE_ASSERT(m_textureBindings.size() > (size_t)textureIndex);
855 DE_ASSERT(m_textureBindings[textureIndex]->getType() == TextureBinding::TYPE_2D_ARRAY);
857 return dynamic_cast<const pipeline::TestTexture2DArray&>(m_textureBindings[textureIndex]->getTestTexture());
860 const pipeline::TestTexture3D& TextureRenderer::get3DTexture (int textureIndex) const
862 DE_ASSERT(m_textureBindings.size() > (size_t)textureIndex);
863 DE_ASSERT(m_textureBindings[textureIndex]->getType() == TextureBinding::TYPE_3D);
865 return dynamic_cast<const pipeline::TestTexture3D&>(m_textureBindings[textureIndex]->getTestTexture());
868 void TextureRenderer::setViewport (float viewportX, float viewportY, float viewportW, float viewportH)
870 m_viewportHeight = viewportH;
871 m_viewportWidth = viewportW;
872 m_viewportOffsetX = viewportX;
873 m_viewportOffsetY = viewportY;
876 TextureBinding* TextureRenderer::getTextureBinding (int textureIndex) const
878 DE_ASSERT(m_textureBindings.size() > (size_t)textureIndex);
879 return m_textureBindings[textureIndex].get();
882 deUint32 TextureRenderer::getRenderWidth (void) const
884 return m_renderWidth;
887 deUint32 TextureRenderer::getRenderHeight (void) const
889 return m_renderHeight;
892 Move<VkDescriptorSet> TextureRenderer::makeDescriptorSet (const VkDescriptorPool descriptorPool, const VkDescriptorSetLayout setLayout) const
894 const DeviceInterface& vkd = m_context.getDeviceInterface();
895 const VkDevice vkDevice = m_context.getDevice();
897 const VkDescriptorSetAllocateInfo allocateParams =
899 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO, // VkStructureType sType
900 DE_NULL, // const void* pNext
901 descriptorPool, // VkDescriptorPool descriptorPool
902 1u, // deUint32 descriptorSetCount
903 &setLayout, // const VkDescriptorSetLayout* pSetLayouts
905 return allocateDescriptorSet(vkd, vkDevice, &allocateParams);
908 void TextureRenderer::addImageTransitionBarrier(VkCommandBuffer commandBuffer, VkImage image, VkPipelineStageFlags srcStageMask, VkPipelineStageFlags dstStageMask, VkAccessFlags srcAccessMask, VkAccessFlags dstAccessMask, VkImageLayout oldLayout, VkImageLayout newLayout) const
910 const DeviceInterface& vkd = m_context.getDeviceInterface();
912 const VkImageSubresourceRange subResourcerange =
914 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask;
915 0, // deUint32 baseMipLevel;
916 1, // deUint32 levelCount;
917 0, // deUint32 baseArrayLayer;
918 1 // deUint32 layerCount;
921 const VkImageMemoryBarrier imageBarrier =
923 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType;
924 DE_NULL, // const void* pNext;
925 srcAccessMask, // VkAccessFlags srcAccessMask;
926 dstAccessMask, // VkAccessFlags dstAccessMask;
927 oldLayout, // VkImageLayout oldLayout;
928 newLayout, // VkImageLayout newLayout;
929 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex;
930 VK_QUEUE_FAMILY_IGNORED, // deUint32 destQueueFamilyIndex;
931 image, // VkImage image;
932 subResourcerange // VkImageSubresourceRange subresourceRange;
935 vkd.cmdPipelineBarrier(commandBuffer, srcStageMask, dstStageMask, 0, 0, DE_NULL, 0, DE_NULL, 1, &imageBarrier);
939 void TextureRenderer::renderQuad (tcu::Surface& result, int texUnit, const float* texCoord, TextureType texType)
941 renderQuad(result, texUnit, texCoord, ReferenceParams(texType));
944 void TextureRenderer::renderQuad (tcu::Surface& result, int texUnit, const float* texCoord, const ReferenceParams& params)
946 const float maxAnisotropy = 1.0f;
949 -1.0, -1.0f, 0.0f, 1.0f,
950 -1.0f, +1.0f, 0.0f, 1.0f,
951 +1.0f, -1.0f, 0.0f, 1.0f,
952 +1.0f, +1.0f, 0.0f, 1.0f
954 renderQuad(result, positions, texUnit, texCoord, params, maxAnisotropy);
957 void TextureRenderer::renderQuad (tcu::Surface& result,
958 const float* positions,
960 const float* texCoord,
961 const glu::TextureTestUtil::ReferenceParams& params,
962 const float maxAnisotropy)
964 const DeviceInterface& vkd = m_context.getDeviceInterface();
965 const VkDevice vkDevice = m_context.getDevice();
966 const VkQueue queue = m_context.getUniversalQueue();
967 const deUint32 queueFamilyIndex = m_context.getUniversalQueueFamilyIndex();
968 Allocator& allocator = m_context.getDefaultAllocator();
970 tcu::Vec4 wCoord = params.flags & RenderParams::PROJECTED ? params.w : tcu::Vec4(1.0f);
971 bool useBias = !!(params.flags & RenderParams::USE_BIAS);
972 bool logUniforms = !!(params.flags & RenderParams::LOG_UNIFORMS);
974 // Render quad with texture.
977 positions[0]*wCoord.x(), positions[1]*wCoord.x(), positions[2], positions[3]*wCoord.x(),
978 positions[4]*wCoord.y(), positions[5]*wCoord.y(), positions[6], positions[7]*wCoord.y(),
979 positions[8]*wCoord.z(), positions[9]*wCoord.z(), positions[10], positions[11]*wCoord.z(),
980 positions[12]*wCoord.w(), positions[13]*wCoord.w(), positions[14], positions[15]*wCoord.w()
983 Program progSpec = PROGRAM_LAST;
986 if (params.texType == TEXTURETYPE_2D)
990 switch (params.samplerType)
992 case SAMPLERTYPE_FLOAT: progSpec = useBias ? PROGRAM_2D_FLOAT_BIAS : PROGRAM_2D_FLOAT; break;
993 case SAMPLERTYPE_INT: progSpec = useBias ? PROGRAM_2D_INT_BIAS : PROGRAM_2D_INT; break;
994 case SAMPLERTYPE_UINT: progSpec = useBias ? PROGRAM_2D_UINT_BIAS : PROGRAM_2D_UINT; break;
995 case SAMPLERTYPE_SHADOW: progSpec = useBias ? PROGRAM_2D_SHADOW_BIAS : PROGRAM_2D_SHADOW; break;
996 default: DE_ASSERT(false);
999 else if (params.texType == TEXTURETYPE_1D)
1003 switch (params.samplerType)
1005 case SAMPLERTYPE_FLOAT: progSpec = useBias ? PROGRAM_1D_FLOAT_BIAS : PROGRAM_1D_FLOAT; break;
1006 case SAMPLERTYPE_INT: progSpec = useBias ? PROGRAM_1D_INT_BIAS : PROGRAM_1D_INT; break;
1007 case SAMPLERTYPE_UINT: progSpec = useBias ? PROGRAM_1D_UINT_BIAS : PROGRAM_1D_UINT; break;
1008 case SAMPLERTYPE_SHADOW: progSpec = useBias ? PROGRAM_1D_SHADOW_BIAS : PROGRAM_1D_SHADOW; break;
1009 default: DE_ASSERT(false);
1012 else if (params.texType == TEXTURETYPE_CUBE)
1016 switch (params.samplerType)
1018 case SAMPLERTYPE_FLOAT: progSpec = useBias ? PROGRAM_CUBE_FLOAT_BIAS : PROGRAM_CUBE_FLOAT; break;
1019 case SAMPLERTYPE_INT: progSpec = useBias ? PROGRAM_CUBE_INT_BIAS : PROGRAM_CUBE_INT; break;
1020 case SAMPLERTYPE_UINT: progSpec = useBias ? PROGRAM_CUBE_UINT_BIAS : PROGRAM_CUBE_UINT; break;
1021 case SAMPLERTYPE_SHADOW: progSpec = useBias ? PROGRAM_CUBE_SHADOW_BIAS : PROGRAM_CUBE_SHADOW; break;
1022 default: DE_ASSERT(false);
1025 else if (params.texType == TEXTURETYPE_3D)
1029 switch (params.samplerType)
1031 case SAMPLERTYPE_FLOAT: progSpec = useBias ? PROGRAM_3D_FLOAT_BIAS : PROGRAM_3D_FLOAT; break;
1032 case SAMPLERTYPE_INT: progSpec = useBias ? PROGRAM_3D_INT_BIAS : PROGRAM_3D_INT; break;
1033 case SAMPLERTYPE_UINT: progSpec = useBias ? PROGRAM_3D_UINT_BIAS : PROGRAM_3D_UINT; break;
1034 default: DE_ASSERT(false);
1037 else if (params.texType == TEXTURETYPE_2D_ARRAY)
1039 DE_ASSERT(!useBias); // \todo [2012-02-17 pyry] Support bias.
1043 switch (params.samplerType)
1045 case SAMPLERTYPE_FLOAT: progSpec = PROGRAM_2D_ARRAY_FLOAT; break;
1046 case SAMPLERTYPE_INT: progSpec = PROGRAM_2D_ARRAY_INT; break;
1047 case SAMPLERTYPE_UINT: progSpec = PROGRAM_2D_ARRAY_UINT; break;
1048 case SAMPLERTYPE_SHADOW: progSpec = PROGRAM_2D_ARRAY_SHADOW; break;
1049 default: DE_ASSERT(false);
1052 else if (params.texType == TEXTURETYPE_CUBE_ARRAY)
1054 DE_ASSERT(!useBias);
1058 switch (params.samplerType)
1060 case SAMPLERTYPE_FLOAT: progSpec = PROGRAM_CUBE_ARRAY_FLOAT; break;
1061 case SAMPLERTYPE_INT: progSpec = PROGRAM_CUBE_ARRAY_INT; break;
1062 case SAMPLERTYPE_UINT: progSpec = PROGRAM_CUBE_ARRAY_UINT; break;
1063 case SAMPLERTYPE_SHADOW: progSpec = PROGRAM_CUBE_ARRAY_SHADOW; break;
1064 default: DE_ASSERT(false);
1067 else if (params.texType == TEXTURETYPE_1D_ARRAY)
1069 DE_ASSERT(!useBias); // \todo [2012-02-17 pyry] Support bias.
1073 switch (params.samplerType)
1075 case SAMPLERTYPE_FLOAT: progSpec = PROGRAM_1D_ARRAY_FLOAT; break;
1076 case SAMPLERTYPE_INT: progSpec = PROGRAM_1D_ARRAY_INT; break;
1077 case SAMPLERTYPE_UINT: progSpec = PROGRAM_1D_ARRAY_UINT; break;
1078 case SAMPLERTYPE_SHADOW: progSpec = PROGRAM_1D_ARRAY_SHADOW; break;
1079 default: DE_ASSERT(false);
1082 else if (params.texType == TEXTURETYPE_BUFFER)
1086 switch (params.samplerType)
1088 case SAMPLERTYPE_FETCH_FLOAT: progSpec = PROGRAM_BUFFER_FLOAT; break;
1089 case SAMPLERTYPE_FETCH_INT: progSpec = PROGRAM_BUFFER_INT; break;
1090 case SAMPLERTYPE_FETCH_UINT: progSpec = PROGRAM_BUFFER_UINT; break;
1091 default: DE_ASSERT(false);
1095 DE_ASSERT(DE_FALSE);
1097 Unique<VkShaderModule> vertexShaderModule (createShaderModule(vkd, vkDevice, m_context.getBinaryCollection().get("vertext_" + std::string(getProgramName(progSpec))), 0));
1098 Unique<VkShaderModule> fragmentShaderModule (createShaderModule(vkd, vkDevice, m_context.getBinaryCollection().get("fragment_" + std::string(getProgramName(progSpec))), 0));
1100 Move<VkSampler> sampler;
1101 Move<VkDescriptorSet> descriptorSet[2];
1102 Move<VkDescriptorSetLayout> descriptorSetLayout[2];
1103 Move<VkPipelineLayout> pipelineLayout;
1105 Move<VkCommandBuffer> commandBuffer;
1106 Move<VkPipeline> graphicsPipeline;
1107 Move<VkBuffer> vertexBuffer;
1108 de::MovePtr<Allocation> vertexBufferMemory;
1109 const deUint32 positionDataSize = deUint32(sizeof(float) * 4 * 4);
1110 const deUint32 textureCoordDataSize = deUint32(sizeof(float) * numComps * 4);
1112 const VkPhysicalDeviceProperties properties = m_context.getDeviceProperties();
1114 if (positionDataSize > properties.limits.maxVertexInputAttributeOffset)
1116 std::stringstream message;
1117 message << "Larger vertex input attribute offset is needed (" << positionDataSize << ") than the available maximum (" << properties.limits.maxVertexInputAttributeOffset << ").";
1118 TCU_THROW(NotSupportedError, message.str().c_str());
1121 // Create Graphics Pipeline
1123 const VkPipelineShaderStageCreateInfo shaderStageParams[2] =
1126 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, // VkStructureType sType;
1127 DE_NULL, // const void* pNext;
1128 0, // VkPipelineShaderStageCreateFlags flags;
1129 VK_SHADER_STAGE_VERTEX_BIT, // VkShaderStage stage;
1130 *vertexShaderModule, // VkShaderModule shader;
1131 "main", // const char* pName;
1132 DE_NULL // const VkSpecializationInfo* pSpecializationInfo;
1135 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, // VkStructureType sType;
1136 DE_NULL, // const void* pNext;
1137 0, // VkPipelineShaderStageCreateFlags flags;
1138 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStage stage;
1139 *fragmentShaderModule, // VkShaderModule shader;
1140 "main", // const char* pName;
1141 DE_NULL // const VkSpecializationInfo* pSpecializationInfo;
1145 const deUint32 vertexPositionStrideSize = deUint32(sizeof(tcu::Vec4));
1146 const deUint32 vertexTextureStrideSize = deUint32(numComps * sizeof(float));
1148 const VkVertexInputBindingDescription vertexInputBindingDescription[2] =
1151 0u, // deUint32 binding;
1152 vertexPositionStrideSize, // deUint32 strideInBytes;
1153 VK_VERTEX_INPUT_RATE_VERTEX // VkVertexInputStepRate stepRate;
1156 1u, // deUint32 binding;
1157 vertexTextureStrideSize, // deUint32 strideInBytes;
1158 VK_VERTEX_INPUT_RATE_VERTEX // VkVertexInputStepRate stepRate;
1162 VkFormat textureCoordinateFormat = VK_FORMAT_R32G32B32A32_SFLOAT;
1165 case 1: textureCoordinateFormat = VK_FORMAT_R32_SFLOAT; break;
1166 case 2: textureCoordinateFormat = VK_FORMAT_R32G32_SFLOAT; break;
1167 case 3: textureCoordinateFormat = VK_FORMAT_R32G32B32_SFLOAT; break;
1168 case 4: textureCoordinateFormat = VK_FORMAT_R32G32B32A32_SFLOAT; break;
1173 const VkVertexInputAttributeDescription vertexInputAttributeDescriptions[2] =
1176 0u, // deUint32 location;
1177 0u, // deUint32 binding;
1178 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format;
1179 0u // deUint32 offsetInBytes;
1182 1u, // deUint32 location;
1183 1u, // deUint32 binding;
1184 textureCoordinateFormat, // VkFormat format;
1185 positionDataSize // deUint32 offsetInBytes;
1189 const VkPipelineVertexInputStateCreateInfo vertexInputStateParams =
1191 VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, // VkStructureType sType;
1192 DE_NULL, // const void* pNext;
1193 0, // VkPipelineVertexInputStateCreateFlags flags;
1194 2u, // deUint32 bindingCount;
1195 vertexInputBindingDescription, // const VkVertexInputBindingDescription* pVertexBindingDescriptions;
1196 2u, // deUint32 attributeCount;
1197 vertexInputAttributeDescriptions // const VkVertexInputAttributeDescription* pVertexAttributeDescriptions;
1200 const VkPipelineInputAssemblyStateCreateInfo inputAssemblyStateParams =
1202 VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO, // VkStructureType sType;
1203 DE_NULL, // const void* pNext;
1204 0, // VkPipelineInputAssemblyStateCreateFlags flags;
1205 VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST, // VkPrimitiveTopology topology;
1206 VK_FALSE // VkBool32 primitiveRestartEnable;
1209 const VkViewport viewport =
1211 m_viewportOffsetX, // float originX;
1212 m_viewportOffsetY, // float originY;
1213 m_viewportWidth, // float width;
1214 m_viewportHeight, // float height;
1215 0.0f, // float minDepth;
1216 1.0f // float maxDepth;
1219 const VkRect2D scissor =
1221 { 0, 0 }, // VkOffset2D offset;
1222 { m_renderWidth, m_renderHeight } // VkExtent2D extent;
1225 const VkPipelineViewportStateCreateInfo viewportStateParams =
1227 VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO, // VkStructureType sType;
1228 DE_NULL, // const void* pNext;
1229 0, // VkPipelineViewportStateCreateFlags flags;
1230 1u, // deUint32 viewportCount;
1231 &viewport, // const VkViewport* pViewports;
1232 1u, // deUint32 scissorCount;
1233 &scissor // const VkRect2D* pScissors;
1236 const VkPipelineMultisampleStateCreateInfo multisampleStateParams =
1238 VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO, // VkStructureType sType;
1239 DE_NULL, // const void* pNext;
1240 0u, // VkPipelineMultisampleStateCreateFlags flags;
1241 m_sampleCount, // VkSampleCountFlagBits rasterizationSamples;
1242 VK_FALSE, // VkBool32 sampleShadingEnable;
1243 0.0f, // float minSampleShading;
1244 DE_NULL, // const VkSampleMask* pSampleMask;
1245 VK_FALSE, // VkBool32 alphaToCoverageEnable;
1246 VK_FALSE // VkBool32 alphaToOneEnable;
1249 const VkPipelineRasterizationStateCreateInfo rasterizationStateCreateInfo =
1251 VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO, // VkStructureType sType;
1252 DE_NULL, // const void* pNext;
1253 0, // VkPipelineRasterizationStateCreateFlags flags;
1254 VK_FALSE, // VkBool32 depthClipEnable;
1255 VK_FALSE, // VkBool32 rasterizerDiscardEnable;
1256 VK_POLYGON_MODE_FILL, // VkFillMode fillMode;
1257 VK_CULL_MODE_NONE, // VkCullMode cullMode;
1258 VK_FRONT_FACE_COUNTER_CLOCKWISE, // VkFrontFace frontFace;
1259 VK_FALSE, // VkBool32 depthBiasEnable;
1260 0.0f, // float depthBias;
1261 0.0f, // float depthBiasClamp;
1262 0.0f, // float slopeScaledDepthBias;
1263 1.0f, // float lineWidth;
1266 const VkPipelineColorBlendAttachmentState colorBlendAttachmentState =
1268 VK_FALSE, // VkBool32 blendEnable;
1269 VK_BLEND_FACTOR_ONE, // VkBlend srcBlendColor;
1270 VK_BLEND_FACTOR_ZERO, // VkBlend destBlendColor;
1271 VK_BLEND_OP_ADD, // VkBlendOp blendOpColor;
1272 VK_BLEND_FACTOR_ONE, // VkBlend srcBlendAlpha;
1273 VK_BLEND_FACTOR_ZERO, // VkBlend destBlendAlpha;
1274 VK_BLEND_OP_ADD, // VkBlendOp blendOpAlpha;
1275 (VK_COLOR_COMPONENT_R_BIT |
1276 VK_COLOR_COMPONENT_G_BIT |
1277 VK_COLOR_COMPONENT_B_BIT |
1278 VK_COLOR_COMPONENT_A_BIT) // VkChannelFlags channelWriteMask;
1281 const VkPipelineColorBlendStateCreateInfo colorBlendStateParams =
1283 VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO, // VkStructureType sType;
1284 DE_NULL, // const void* pNext;
1285 0, // VkPipelineColorBlendStateCreateFlags flags;
1286 VK_FALSE, // VkBool32 logicOpEnable;
1287 VK_LOGIC_OP_COPY, // VkLogicOp logicOp;
1288 1u, // deUint32 attachmentCount;
1289 &colorBlendAttachmentState, // const VkPipelineColorBlendAttachmentState* pAttachments;
1290 { 0.0f, 0.0f, 0.0f, 0.0f }, // float blendConst[4];
1293 VkSamplerCreateInfo samplerCreateInfo = mapSampler(params.sampler, m_textureBindings[texUnit]->getTestTexture().getTextureFormat(), params.minLod, params.maxLod);
1295 if (maxAnisotropy > 1.0f)
1297 samplerCreateInfo.anisotropyEnable = VK_TRUE;
1298 samplerCreateInfo.maxAnisotropy = maxAnisotropy;
1301 if (samplerCreateInfo.magFilter == VK_FILTER_LINEAR || samplerCreateInfo.minFilter == VK_FILTER_LINEAR || samplerCreateInfo.mipmapMode == VK_SAMPLER_MIPMAP_MODE_LINEAR)
1303 const pipeline::TestTexture& testTexture = m_textureBindings[texUnit]->getTestTexture();
1304 const VkFormat textureFormat = testTexture.isCompressed() ? mapCompressedTextureFormat(testTexture.getCompressedLevel(0, 0).getFormat())
1305 : mapTextureFormat (testTexture.getTextureFormat());
1306 const VkFormatProperties formatProperties = getPhysicalDeviceFormatProperties(m_context.getInstanceInterface(), m_context.getPhysicalDevice(), textureFormat);
1308 if (!(formatProperties.optimalTilingFeatures & VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT))
1309 TCU_THROW(NotSupportedError, "Linear filtering for this image format is not supported");
1312 sampler = createSampler(vkd, vkDevice, &samplerCreateInfo);
1314 descriptorSetLayout[0] = DescriptorSetLayoutBuilder()
1315 .addSingleBinding(VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, VK_SHADER_STAGE_FRAGMENT_BIT)
1316 .build(vkd, vkDevice);
1318 descriptorSetLayout[1] = DescriptorSetLayoutBuilder()
1319 .addSingleSamplerBinding(VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler.get())
1320 .build(vkd, vkDevice);
1323 descriptorSet[0] = makeDescriptorSet(*m_descriptorPool, *descriptorSetLayout[0]);
1324 descriptorSet[1] = makeDescriptorSet(*m_descriptorPool, *descriptorSetLayout[1]);
1327 const VkDescriptorBufferInfo descriptorBufferInfo =
1329 *m_uniformBuffer, // VkBuffer buffer;
1330 0u, // VkDeviceSize offset;
1331 VK_WHOLE_SIZE // VkDeviceSize range;
1334 DescriptorSetUpdateBuilder()
1335 .writeSingle(*descriptorSet[0], DescriptorSetUpdateBuilder::Location::binding(0), VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, &descriptorBufferInfo)
1336 .update(vkd, vkDevice);
1340 VkDescriptorImageInfo descriptorImageInfo =
1342 *sampler, // VkSampler sampler;
1343 m_textureBindings[texUnit]->getImageView(), // VkImageView imageView;
1344 VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL // VkImageLayout imageLayout;
1347 DescriptorSetUpdateBuilder()
1348 .writeSingle(*descriptorSet[1], DescriptorSetUpdateBuilder::Location::binding(0), VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, &descriptorImageInfo)
1349 .update(vkd, vkDevice);
1354 VkDescriptorSetLayout descriptorSetLayouts[2] =
1356 *descriptorSetLayout[0],
1357 *descriptorSetLayout[1]
1360 const VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo =
1362 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType;
1363 DE_NULL, // const void* pNext;
1364 0u, // VkPipelineLayoutCreateFlags flags;
1365 2u, // deUint32 descriptorSetCount;
1366 descriptorSetLayouts, // const VkDescriptorSetLayout* pSetLayouts;
1367 0u, // deUint32 pushConstantRangeCount;
1368 DE_NULL // const VkPushConstantRange* pPushConstantRanges;
1371 pipelineLayout = createPipelineLayout(vkd, vkDevice, &pipelineLayoutCreateInfo);
1374 const VkGraphicsPipelineCreateInfo graphicsPipelineParams =
1376 VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO, // VkStructureType sType;
1377 DE_NULL, // const void* pNext;
1378 0u, // VkPipelineCreateFlags flags;
1379 2u, // deUint32 stageCount;
1380 shaderStageParams, // const VkPipelineShaderStageCreateInfo* pStages;
1381 &vertexInputStateParams, // const VkPipelineVertexInputStateCreateInfo* pVertexInputState;
1382 &inputAssemblyStateParams, // const VkPipelineInputAssemblyStateCreateInfo* pInputAssemblyState;
1383 DE_NULL, // const VkPipelineTessellationStateCreateInfo* pTessellationState;
1384 &viewportStateParams, // const VkPipelineViewportStateCreateInfo* pViewportState;
1385 &rasterizationStateCreateInfo, // const VkPipelineRasterStateCreateInfo* pRasterizationState;
1386 &multisampleStateParams, // const VkPipelineMultisampleStateCreateInfo* pMultisampleState;
1387 DE_NULL, // const VkPipelineDepthStencilStateCreateInfo* pDepthStencilState;
1388 &colorBlendStateParams, // const VkPipelineColorBlendStateCreateInfo* pColorBlendState;
1389 DE_NULL, // const VkPipelineDynamicStateCreateInfo* pDynamicState;
1390 *pipelineLayout, // VkPipelineLayout layout;
1391 *m_renderPass, // VkRenderPass renderPass;
1392 0u, // deUint32 subpass;
1393 0u, // VkPipeline basePipelineHandle;
1394 0u // deInt32 basePipelineIndex;
1397 graphicsPipeline = createGraphicsPipeline(vkd, vkDevice, DE_NULL, &graphicsPipelineParams);
1400 // Create Vertex Buffer
1402 const VkBufferCreateInfo vertexBufferParams =
1404 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType;
1405 DE_NULL, // const void* pNext;
1406 0u, // VkBufferCreateFlags flags;
1407 positionDataSize + textureCoordDataSize, // VkDeviceSize size;
1408 VK_BUFFER_USAGE_VERTEX_BUFFER_BIT, // VkBufferUsageFlags usage;
1409 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
1410 1u, // deUint32 queueFamilyCount;
1411 &queueFamilyIndex // const deUint32* pQueueFamilyIndices;
1414 vertexBuffer = createBuffer(vkd, vkDevice, &vertexBufferParams);
1415 vertexBufferMemory = allocator.allocate(getBufferMemoryRequirements(vkd, vkDevice, *vertexBuffer), MemoryRequirement::HostVisible);
1417 VK_CHECK(vkd.bindBufferMemory(vkDevice, *vertexBuffer, vertexBufferMemory->getMemory(), vertexBufferMemory->getOffset()));
1419 // Load vertices into vertex buffer
1420 deMemcpy(vertexBufferMemory->getHostPtr(), position, positionDataSize);
1421 deMemcpy(reinterpret_cast<deUint8*>(vertexBufferMemory->getHostPtr()) + positionDataSize, texCoord, textureCoordDataSize);
1422 flushMappedMemoryRange(vkd, vkDevice, vertexBufferMemory->getMemory(), vertexBufferMemory->getOffset(), VK_WHOLE_SIZE);
1425 // Create Command Buffer
1426 commandBuffer = allocateCommandBuffer(vkd, vkDevice, *m_commandPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
1428 // Begin Command Buffer
1430 const VkCommandBufferBeginInfo cmdBufferBeginInfo =
1432 VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO, // VkStructureType sType;
1433 DE_NULL, // const void* pNext;
1434 0u, // VkCmdBufferOptimizeFlags flags;
1435 DE_NULL // const VkCommandBufferInheritanceInfo* pInheritanceInfo;
1438 VK_CHECK(vkd.beginCommandBuffer(*commandBuffer, &cmdBufferBeginInfo));
1441 // Begin Render Pass
1443 const VkRenderPassBeginInfo renderPassBeginInfo =
1445 VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO, // VkStructureType sType;
1446 DE_NULL, // const void* pNext;
1447 *m_renderPass, // VkRenderPass renderPass;
1448 *m_frameBuffer, // VkFramebuffer framebuffer;
1451 { m_renderWidth, m_renderHeight }
1452 }, // VkRect2D renderArea;
1453 0u, // deUint32 clearValueCount;
1454 DE_NULL // const VkClearValue* pClearValues;
1457 vkd.cmdBeginRenderPass(*commandBuffer, &renderPassBeginInfo, VK_SUBPASS_CONTENTS_INLINE);
1460 const VkDeviceSize vertexBufferOffset = 0;
1462 vkd.cmdBindPipeline(*commandBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *graphicsPipeline);
1463 vkd.cmdBindDescriptorSets(*commandBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *pipelineLayout, 0u, 1, &descriptorSet[0].get(), 0u, DE_NULL);
1464 vkd.cmdBindDescriptorSets(*commandBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *pipelineLayout, 1u, 1, &descriptorSet[1].get(), 0u, DE_NULL);
1465 vkd.cmdBindVertexBuffers(*commandBuffer, 0, 1, &vertexBuffer.get(), &vertexBufferOffset);
1466 vkd.cmdBindVertexBuffers(*commandBuffer, 1, 1, &vertexBuffer.get(), &vertexBufferOffset);
1467 vkd.cmdBindIndexBuffer(*commandBuffer, *m_vertexIndexBuffer, 0, VK_INDEX_TYPE_UINT16);
1468 vkd.cmdDrawIndexed(*commandBuffer, 6, 1, 0, 0, 0);
1469 vkd.cmdEndRenderPass(*commandBuffer);
1473 const VkBufferMemoryBarrier bufferBarrier =
1475 VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER, // VkStructureType sType;
1476 DE_NULL, // const void* pNext;
1477 VK_ACCESS_TRANSFER_WRITE_BIT, // VkMemoryOutputFlags outputMask;
1478 VK_ACCESS_HOST_READ_BIT, // VkMemoryInputFlags inputMask;
1479 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex;
1480 VK_QUEUE_FAMILY_IGNORED, // deUint32 destQueueFamilyIndex;
1481 *m_resultBuffer, // VkBuffer buffer;
1482 0u, // VkDeviceSize offset;
1483 m_resultBufferSize // VkDeviceSize size;
1486 const VkBufferImageCopy copyRegion =
1488 0u, // VkDeviceSize bufferOffset;
1489 m_renderWidth, // deUint32 bufferRowLength;
1490 m_renderHeight, // deUint32 bufferImageHeight;
1492 VK_IMAGE_ASPECT_COLOR_BIT,
1496 }, // VkImageSubresourceCopy imageSubresource;
1497 { 0, 0, 0 }, // VkOffset3D imageOffset;
1498 { m_renderWidth, m_renderHeight, 1u } // VkExtent3D imageExtent;
1501 addImageTransitionBarrier(*commandBuffer,
1502 m_multisampling ? *m_resolvedImage : *m_image,
1503 VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, // VkPipelineStageFlags srcStageMask
1504 VK_PIPELINE_STAGE_TRANSFER_BIT, // VkPipelineStageFlags dstStageMask
1505 VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, // VkAccessFlags srcAccessMask
1506 VK_ACCESS_TRANSFER_READ_BIT, // VkAccessFlags dstAccessMask
1507 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL, // VkImageLayout oldLayout;
1508 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL); // VkImageLayout newLayout;
1510 if (m_multisampling)
1511 vkd.cmdCopyImageToBuffer(*commandBuffer, *m_resolvedImage, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, *m_resultBuffer, 1, ©Region);
1513 vkd.cmdCopyImageToBuffer(*commandBuffer, *m_image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, *m_resultBuffer, 1, ©Region);
1515 vkd.cmdPipelineBarrier(*commandBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_HOST_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 1, &bufferBarrier, 0, (const VkImageMemoryBarrier*)DE_NULL);
1517 addImageTransitionBarrier(*commandBuffer,
1518 m_multisampling ? *m_resolvedImage : *m_image,
1519 VK_PIPELINE_STAGE_TRANSFER_BIT, // VkPipelineStageFlags srcStageMask
1520 VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, // VkPipelineStageFlags dstStageMask
1521 VK_ACCESS_TRANSFER_READ_BIT, // VkAccessFlags srcAccessMask
1522 VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, // VkAccessFlags dstAccessMask
1523 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, // VkImageLayout oldLayout;
1524 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL); // VkImageLayout newLayout;
1527 VK_CHECK(vkd.endCommandBuffer(*commandBuffer));
1529 // Upload uniform buffer data
1531 const ShaderParameters shaderParameters =
1533 params.bias, // float bias; //!< User-supplied bias.
1534 params.ref, // float ref; //!< Reference value for shadow lookups.
1535 tcu::Vec2(), // tcu::Vec2 padding; //!< Shader uniform padding.
1536 params.colorScale, // tcu::Vec4 colorScale; //!< Scale for texture color values.
1537 params.colorBias // tcu::Vec4 colorBias; //!< Bias for texture color values.
1539 deMemcpy(m_uniformBufferMemory->getHostPtr(), &shaderParameters, sizeof(shaderParameters));
1540 flushMappedMemoryRange(vkd, vkDevice, m_uniformBufferMemory->getMemory(), m_uniformBufferMemory->getOffset(), VK_WHOLE_SIZE);
1543 m_log << TestLog::Message << "u_sampler = " << texUnit << TestLog::EndMessage;
1548 m_log << TestLog::Message << "u_bias = " << shaderParameters.bias << TestLog::EndMessage;
1551 if (params.samplerType == SAMPLERTYPE_SHADOW)
1554 m_log << TestLog::Message << "u_ref = " << shaderParameters.ref << TestLog::EndMessage;
1559 m_log << TestLog::Message << "u_colorScale = " << shaderParameters.colorScale << TestLog::EndMessage;
1560 m_log << TestLog::Message << "u_colorBias = " << shaderParameters.colorBias << TestLog::EndMessage;
1566 const VkSubmitInfo submitInfo =
1568 VK_STRUCTURE_TYPE_SUBMIT_INFO, // VkStructureType sType;
1569 DE_NULL, // const void* pNext;
1570 0u, // deUint32 waitSemaphoreCount;
1571 DE_NULL, // const VkSemaphore* pWaitSemaphores;
1572 DE_NULL, // const VkPipelineStageFlags* pWaitDstStageMask;
1573 1u, // deUint32 commandBufferCount;
1574 &commandBuffer.get(), // const VkCommandBuffer* pCommandBuffers;
1575 0u, // deUint32 signalSemaphoreCount;
1576 DE_NULL, // const VkSemaphore* pSignalSemaphores;
1579 VK_CHECK(vkd.resetFences(vkDevice, 1, &m_fence.get()));
1580 VK_CHECK(vkd.queueSubmit(queue, 1, &submitInfo, *m_fence));
1581 VK_CHECK(vkd.waitForFences(vkDevice, 1, &m_fence.get(), true, ~(0ull) /* infinity */));
1584 invalidateMappedMemoryRange(vkd, vkDevice, m_resultBufferMemory->getMemory(), m_resultBufferMemory->getOffset(), VK_WHOLE_SIZE);
1586 tcu::copy(result.getAccess(), tcu::ConstPixelBufferAccess(m_textureFormat, tcu::IVec3(m_renderWidth, m_renderHeight, 1u), m_resultBufferMemory->getHostPtr()));
1589 /*--------------------------------------------------------------------*//*!
1590 * \brief Map Vulkan sampler parameters to tcu::Sampler.
1592 * If no mapping is found, throws tcu::InternalError.
1594 * \param wrapU U-component wrap mode
1595 * \param wrapV V-component wrap mode
1596 * \param wrapW W-component wrap mode
1597 * \param minFilterMode Minification filter mode
1598 * \param magFilterMode Magnification filter mode
1599 * \return Sampler description.
1600 *//*--------------------------------------------------------------------*/
1601 tcu::Sampler createSampler (tcu::Sampler::WrapMode wrapU, tcu::Sampler::WrapMode wrapV, tcu::Sampler::WrapMode wrapW, tcu::Sampler::FilterMode minFilterMode, tcu::Sampler::FilterMode magFilterMode)
1603 return tcu::Sampler(wrapU, wrapV, wrapW,
1604 minFilterMode, magFilterMode,
1605 0.0f /* lod threshold */,
1606 true /* normalized coords */,
1607 tcu::Sampler::COMPAREMODE_NONE /* no compare */,
1608 0 /* compare channel */,
1609 tcu::Vec4(0.0f) /* border color, not used */);
1612 /*--------------------------------------------------------------------*//*!
1613 * \brief Map Vulkan sampler parameters to tcu::Sampler.
1615 * If no mapping is found, throws tcu::InternalError.
1617 * \param wrapU U-component wrap mode
1618 * \param wrapV V-component wrap mode
1619 * \param minFilterMode Minification filter mode
1620 * \param minFilterMode Magnification filter mode
1621 * \return Sampler description.
1622 *//*--------------------------------------------------------------------*/
1623 tcu::Sampler createSampler (tcu::Sampler::WrapMode wrapU, tcu::Sampler::WrapMode wrapV, tcu::Sampler::FilterMode minFilterMode, tcu::Sampler::FilterMode magFilterMode)
1625 return createSampler(wrapU, wrapV, wrapU, minFilterMode, magFilterMode);
1628 /*--------------------------------------------------------------------*//*!
1629 * \brief Map Vulkan sampler parameters to tcu::Sampler.
1631 * If no mapping is found, throws tcu::InternalError.
1633 * \param wrapU U-component wrap mode
1634 * \param minFilterMode Minification filter mode
1635 * \return Sampler description.
1636 *//*--------------------------------------------------------------------*/
1637 tcu::Sampler createSampler (tcu::Sampler::WrapMode wrapU, tcu::Sampler::FilterMode minFilterMode, tcu::Sampler::FilterMode magFilterMode)
1639 return createSampler(wrapU, wrapU, wrapU, minFilterMode, magFilterMode);
1642 TestTexture2DSp loadTexture2D (const tcu::Archive& archive, const std::vector<std::string>& filenames)
1644 DE_ASSERT(filenames.size() > 0);
1646 TestTexture2DSp texture;
1648 std::string ext = de::FilePath(filenames[0]).getFileExtension();
1653 for (size_t fileIndex = 0; fileIndex < filenames.size(); ++fileIndex)
1655 tcu::TextureLevel level;
1657 tcu::ImageIO::loadImage(level, archive, filenames[fileIndex].c_str());
1659 TCU_CHECK_INTERNAL(level.getFormat() == tcu::TextureFormat(tcu::TextureFormat::RGBA, tcu::TextureFormat::UNORM_INT8) ||
1660 level.getFormat() == tcu::TextureFormat(tcu::TextureFormat::RGB, tcu::TextureFormat::UNORM_INT8));
1663 texture = TestTexture2DSp(new pipeline::TestTexture2D(tcu::TextureFormat(tcu::TextureFormat::RGBA, tcu::TextureFormat::UNORM_INT8), level.getWidth(), level.getHeight()));
1665 tcu::copy(texture->getLevel((int)fileIndex, 0), level.getAccess());
1668 else if (ext == "pkm")
1671 for (size_t fileIndex = 0; fileIndex < filenames.size(); ++fileIndex)
1673 // Compressed texture.
1674 tcu::CompressedTexture level;
1676 tcu::ImageIO::loadPKM(level, archive, filenames[fileIndex].c_str());
1678 tcu::TextureFormat uncompressedFormat = tcu::getUncompressedFormat(level.getFormat());
1679 std::vector<deUint8> uncompressedData (uncompressedFormat.getPixelSize() * level.getWidth() * level.getHeight(), 0);
1680 tcu::PixelBufferAccess decompressedBuffer (uncompressedFormat, level.getWidth(), level.getHeight(), 1, uncompressedData.data());
1682 tcu::TextureFormat commonFormat = tcu::TextureFormat(tcu::TextureFormat::RGBA, tcu::TextureFormat::UNORM_INT8);
1683 std::vector<deUint8> commonFromatData (commonFormat.getPixelSize() * level.getWidth() * level.getHeight(), 0);
1684 tcu::PixelBufferAccess commonFormatBuffer (commonFormat, level.getWidth(), level.getHeight(), 1, commonFromatData.data());
1687 texture = TestTexture2DSp(new pipeline::TestTexture2D(commonFormat, level.getWidth(), level.getHeight()));
1689 level.decompress(decompressedBuffer, tcu::TexDecompressionParams(tcu::TexDecompressionParams::ASTCMODE_LDR));
1691 tcu::copy(commonFormatBuffer, decompressedBuffer);
1692 tcu::copy(texture->getLevel((int)fileIndex, 0), commonFormatBuffer);
1696 TCU_FAIL("Unsupported file format");
1701 TestTextureCubeSp loadTextureCube (const tcu::Archive& archive, const std::vector<std::string>& filenames)
1703 DE_ASSERT(filenames.size() > 0);
1704 DE_STATIC_ASSERT(tcu::CUBEFACE_LAST == 6);
1705 TCU_CHECK((int)filenames.size() % tcu::CUBEFACE_LAST == 0);
1707 TestTextureCubeSp texture;
1709 std::string ext = de::FilePath(filenames[0]).getFileExtension();
1714 for (size_t fileIndex = 0; fileIndex < filenames.size(); ++fileIndex)
1716 tcu::TextureLevel level;
1718 tcu::ImageIO::loadImage(level, archive, filenames[fileIndex].c_str());
1720 TCU_CHECK_INTERNAL(level.getFormat() == tcu::TextureFormat(tcu::TextureFormat::RGBA, tcu::TextureFormat::UNORM_INT8) ||
1721 level.getFormat() == tcu::TextureFormat(tcu::TextureFormat::RGB, tcu::TextureFormat::UNORM_INT8));
1723 TCU_CHECK( level.getWidth() == level.getHeight());
1726 texture = TestTextureCubeSp(new pipeline::TestTextureCube(tcu::TextureFormat(tcu::TextureFormat::RGBA, tcu::TextureFormat::UNORM_INT8), level.getWidth()));
1728 tcu::copy(texture->getLevel((int)fileIndex / 6, (int)fileIndex % 6), level.getAccess());
1731 else if (ext == "pkm")
1733 for (size_t fileIndex = 0; fileIndex < filenames.size(); ++fileIndex)
1735 // Compressed texture.
1736 tcu::CompressedTexture level;
1738 tcu::ImageIO::loadPKM(level, archive, filenames[fileIndex].c_str());
1740 TCU_CHECK( level.getWidth() == level.getHeight());
1742 tcu::TextureFormat uncompressedFormat = tcu::getUncompressedFormat(level.getFormat());
1743 std::vector<deUint8> uncompressedData (uncompressedFormat.getPixelSize() * level.getWidth() * level.getHeight(), 0);
1744 tcu::PixelBufferAccess decompressedBuffer (uncompressedFormat, level.getWidth(), level.getHeight(), 1, uncompressedData.data());
1746 tcu::TextureFormat commonFormat = tcu::TextureFormat(tcu::TextureFormat::RGBA, tcu::TextureFormat::UNORM_INT8);
1747 std::vector<deUint8> commonFromatData (commonFormat.getPixelSize() * level.getWidth() * level.getHeight(), 0);
1748 tcu::PixelBufferAccess commonFormatBuffer (commonFormat, level.getWidth(), level.getHeight(), 1, commonFromatData.data());
1751 texture = TestTextureCubeSp(new pipeline::TestTextureCube(commonFormat, level.getWidth()));
1753 level.decompress(decompressedBuffer, tcu::TexDecompressionParams(tcu::TexDecompressionParams::ASTCMODE_LDR));
1755 tcu::copy(commonFormatBuffer, decompressedBuffer);
1756 tcu::copy(texture->getLevel((int)fileIndex / 6, (int)fileIndex % 6), commonFormatBuffer);
1760 TCU_FAIL("Unsupported file format");
1765 TextureCommonTestCaseParameters::TextureCommonTestCaseParameters (void)
1766 : sampleCount (VK_SAMPLE_COUNT_1_BIT)
1767 , texCoordPrecision (glu::PRECISION_HIGHP)
1768 , minFilter (tcu::Sampler::LINEAR)
1769 , magFilter (tcu::Sampler::LINEAR)
1770 , wrapS (tcu::Sampler::REPEAT_GL)
1771 , wrapT (tcu::Sampler::REPEAT_GL)
1772 , format (VK_FORMAT_R8G8B8A8_UNORM)
1776 Texture2DTestCaseParameters::Texture2DTestCaseParameters (void)
1782 TextureCubeTestCaseParameters::TextureCubeTestCaseParameters (void)
1787 Texture2DArrayTestCaseParameters::Texture2DArrayTestCaseParameters (void)
1792 Texture3DTestCaseParameters::Texture3DTestCaseParameters (void)
1793 : wrapR (tcu::Sampler::REPEAT_GL)