Home | History | Annotate | Download | only in api
      1 /*------------------------------------------------------------------------
      2  * Vulkan Conformance Tests
      3  * ------------------------
      4  *
      5  * Copyright (c) 2016 The Khronos Group Inc.
      6  * Copyright (c) 2016 Samsung Electronics Co., Ltd.
      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 Vulkan Image Clearing Tests
     23  *//*--------------------------------------------------------------------*/
     24 
     25 #include "vktApiImageClearingTests.hpp"
     26 
     27 #include "deRandom.hpp"
     28 #include "deMath.h"
     29 #include "deSTLUtil.hpp"
     30 #include "deStringUtil.hpp"
     31 #include "deUniquePtr.hpp"
     32 #include "deArrayUtil.hpp"
     33 #include "deInt32.h"
     34 #include "vkImageUtil.hpp"
     35 #include "vkMemUtil.hpp"
     36 #include "vktTestCase.hpp"
     37 #include "vktTestCaseUtil.hpp"
     38 #include "vktTestGroupUtil.hpp"
     39 #include "vkQueryUtil.hpp"
     40 #include "vkRefUtil.hpp"
     41 #include "vkTypeUtil.hpp"
     42 #include "tcuImageCompare.hpp"
     43 #include "tcuTexture.hpp"
     44 #include "tcuTextureUtil.hpp"
     45 #include "tcuVectorType.hpp"
     46 #include "tcuTexture.hpp"
     47 #include "tcuFloat.hpp"
     48 #include "tcuTestLog.hpp"
     49 #include "tcuVectorUtil.hpp"
     50 #include <sstream>
     51 #include <numeric>
     52 
     53 namespace vkt
     54 {
     55 
     56 namespace api
     57 {
     58 
     59 using namespace vk;
     60 using namespace tcu;
     61 
     62 namespace
     63 {
     64 
     65 enum AllocationKind
     66 {
     67 	ALLOCATION_KIND_SUBALLOCATED,
     68 	ALLOCATION_KIND_DEDICATED,
     69 };
     70 
     71 
     72 de::MovePtr<Allocation> allocateBuffer (const InstanceInterface&	vki,
     73 										const DeviceInterface&		vkd,
     74 										const VkPhysicalDevice&		physDevice,
     75 										const VkDevice				device,
     76 										const VkBuffer&				buffer,
     77 										const MemoryRequirement		requirement,
     78 										Allocator&					allocator,
     79 										AllocationKind				allocationKind)
     80 {
     81 	switch (allocationKind)
     82 	{
     83 		case ALLOCATION_KIND_SUBALLOCATED:
     84 		{
     85 			const VkMemoryRequirements memoryRequirements = getBufferMemoryRequirements(vkd, device, buffer);
     86 
     87 			return allocator.allocate(memoryRequirements, requirement);
     88 		}
     89 
     90 		case ALLOCATION_KIND_DEDICATED:
     91 		{
     92 			return allocateDedicated(vki, vkd, physDevice, device, buffer, requirement);
     93 		}
     94 
     95 		default:
     96 		{
     97 			TCU_THROW(InternalError, "Invalid allocation kind");
     98 		}
     99 	}
    100 }
    101 
    102 de::MovePtr<Allocation> allocateImage (const InstanceInterface&		vki,
    103 									   const DeviceInterface&		vkd,
    104 									   const VkPhysicalDevice&		physDevice,
    105 									   const VkDevice				device,
    106 									   const VkImage&				image,
    107 									   const MemoryRequirement		requirement,
    108 									   Allocator&					allocator,
    109 									   AllocationKind				allocationKind)
    110 {
    111 	switch (allocationKind)
    112 	{
    113 		case ALLOCATION_KIND_SUBALLOCATED:
    114 		{
    115 			const VkMemoryRequirements memoryRequirements = getImageMemoryRequirements(vkd, device, image);
    116 
    117 			return allocator.allocate(memoryRequirements, requirement);
    118 		}
    119 
    120 		case ALLOCATION_KIND_DEDICATED:
    121 		{
    122 			return allocateDedicated(vki, vkd, physDevice, device, image, requirement);
    123 		}
    124 
    125 		default:
    126 		{
    127 			TCU_THROW(InternalError, "Invalid allocation kind");
    128 		}
    129 	}
    130 }
    131 
    132 VkExtent3D getMipLevelExtent (VkExtent3D baseExtent, const deUint32 mipLevel)
    133 {
    134 	baseExtent.width	= std::max(baseExtent.width  >> mipLevel, 1u);
    135 	baseExtent.height	= std::max(baseExtent.height >> mipLevel, 1u);
    136 	baseExtent.depth	= std::max(baseExtent.depth  >> mipLevel, 1u);
    137 	return baseExtent;
    138 }
    139 
    140 deUint32 getNumMipLevels (const VkExtent3D& baseExtent, const deUint32 maxMipLevels)
    141 {
    142 	const deUint32 widestEdge = std::max(std::max(baseExtent.width, baseExtent.height), baseExtent.depth);
    143 	return std::min(static_cast<deUint32>(deFloatLog2(static_cast<float>(widestEdge))) + 1u, maxMipLevels);
    144 }
    145 
    146 deUint32 greatestCommonDivisor (const deUint32 a, const deUint32 b)
    147 {
    148 	/* Find GCD */
    149 	deUint32 temp;
    150 	deUint32 x=a;
    151 	deUint32 y=b;
    152 
    153 	while (x%y != 0)
    154 	{
    155 		temp = y;
    156 		y = x%y;
    157 		x = temp;
    158 	}
    159 	return y;
    160 }
    161 
    162 deUint32 lowestCommonMultiple (const deUint32 a, const deUint32 b)
    163 {
    164 	return (a*b)/greatestCommonDivisor(a,b);
    165 }
    166 
    167 std::vector<deUint32> getImageMipLevelSizes (const deUint32 pixelSize, const VkExtent3D& baseExtent, const deUint32 numMipLevels, const deUint32 perLevelAlignment = 1u)
    168 {
    169 	std::vector<deUint32> results(numMipLevels);
    170 
    171 	for (deUint32 mipLevel = 0; mipLevel < numMipLevels; ++mipLevel)
    172 	{
    173 		const VkExtent3D extent = getMipLevelExtent(baseExtent, mipLevel);
    174 		results[mipLevel] = static_cast<deUint32>(extent.width * extent.height * extent.depth * pixelSize);
    175 		results[mipLevel] = ((results[mipLevel] + perLevelAlignment-1) / perLevelAlignment) * perLevelAlignment;
    176 	}
    177 
    178 	return results;
    179 }
    180 
    181 struct LayerRange
    182 {
    183 	deUint32 baseArrayLayer;
    184 	deUint32 layerCount;
    185 };
    186 
    187 inline bool isInClearRange (const UVec4& clearCoords, const deUint32 x, const deUint32 y, deUint32 arrayLayer = 0, tcu::Maybe<LayerRange> imageViewLayerRange = tcu::Maybe<LayerRange>(), tcu::Maybe<LayerRange> attachmentClearLayerRange = tcu::Maybe<LayerRange>())
    188 {
    189 	if (attachmentClearLayerRange)
    190 	{
    191 		// Only layers in range passed to clear command are cleared
    192 
    193 		const deUint32 clearBaseLayer = (imageViewLayerRange ? imageViewLayerRange->baseArrayLayer : 0) + attachmentClearLayerRange->baseArrayLayer;
    194 
    195 		if ((arrayLayer < clearBaseLayer) || (arrayLayer >= (clearBaseLayer + attachmentClearLayerRange->layerCount)))
    196 		{
    197 			return false;
    198 		}
    199 	}
    200 
    201 	if (clearCoords == UVec4())
    202 	{
    203 		return true;
    204 	}
    205 
    206 	//! Check if a point lies in a cross-like area.
    207 	return !((x <  clearCoords[0] && y <  clearCoords[1]) ||
    208 			 (x <  clearCoords[0] && y >= clearCoords[3]) ||
    209 			 (x >= clearCoords[2] && y <  clearCoords[1]) ||
    210 			 (x >= clearCoords[2] && y >= clearCoords[3]));
    211 }
    212 
    213 inline bool isInInitialClearRange (bool isAttachmentformat, deUint32 mipLevel, deUint32 arrayLayer, LayerRange imageViewLayerRange)
    214 {
    215 	if (!isAttachmentformat)
    216 	{
    217 		// initial clear is done using renderpass load op - does not apply for non-renderable formats
    218 		return false;
    219 	}
    220 
    221 	if (mipLevel > 0)
    222 	{
    223 		// intial clear is done using FB bound to level 0 only
    224 		return false;
    225 	}
    226 
    227 	// Only layers in range bound to framebuffer are cleared to initial color
    228 	if ((arrayLayer < imageViewLayerRange.baseArrayLayer) || (arrayLayer >= (imageViewLayerRange.baseArrayLayer + imageViewLayerRange.layerCount)))
    229 	{
    230 		return false;
    231 	}
    232 
    233 	return true;
    234 }
    235 
    236 // This method is copied from the vktRenderPassTests.cpp. It should be moved to a common place.
    237 int calcFloatDiff (float a, float b)
    238 {
    239 	const int			asign	= Float32(a).sign();
    240 	const int			bsign	= Float32(a).sign();
    241 
    242 	const deUint32		avalue	= (Float32(a).bits() & ((0x1u << 31u) - 1u));
    243 	const deUint32		bvalue	= (Float32(b).bits() & ((0x1u << 31u) - 1u));
    244 
    245 	if (asign != bsign)
    246 		return avalue + bvalue + 1u;
    247 	else if (avalue < bvalue)
    248 		return bvalue - avalue;
    249 	else
    250 		return avalue - bvalue;
    251 }
    252 
    253 // This method is copied from the vktRenderPassTests.cpp and extended with the stringResult parameter.
    254 bool comparePixelToDepthClearValue (const ConstPixelBufferAccess&	access,
    255 									int								x,
    256 									int								y,
    257 									float							ref,
    258 									std::string&					stringResult)
    259 {
    260 	const TextureFormat			format			= getEffectiveDepthStencilTextureFormat(access.getFormat(), Sampler::MODE_DEPTH);
    261 	const TextureChannelClass	channelClass	= getTextureChannelClass(format.type);
    262 
    263 	switch (channelClass)
    264 	{
    265 		case TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT:
    266 		case TEXTURECHANNELCLASS_SIGNED_FIXED_POINT:
    267 		{
    268 			const int	bitDepth	= getTextureFormatBitDepth(format).x();
    269 			const float	depth		= access.getPixDepth(x, y);
    270 			const float	threshold	= 2.0f / (float)((1 << bitDepth) - 1);
    271 			const bool	result		= deFloatAbs(depth - ref) <= threshold;
    272 
    273 			if (!result)
    274 			{
    275 				std::stringstream s;
    276 				s << "Ref:" << ref << " Threshold:" << threshold << " Depth:" << depth;
    277 				stringResult	= s.str();
    278 			}
    279 
    280 			return result;
    281 		}
    282 
    283 		case TEXTURECHANNELCLASS_FLOATING_POINT:
    284 		{
    285 			const float	depth			= access.getPixDepth(x, y);
    286 			const int	mantissaBits	= getTextureFormatMantissaBitDepth(format).x();
    287 			const int	threshold		= 10 * 1 << (23 - mantissaBits);
    288 
    289 			DE_ASSERT(mantissaBits <= 23);
    290 
    291 			const bool	result			= calcFloatDiff(depth, ref) <= threshold;
    292 
    293 			if (!result)
    294 			{
    295 				float				floatThreshold	= Float32((deUint32)threshold).asFloat();
    296 				std::stringstream	s;
    297 
    298 				s << "Ref:" << ref << " Threshold:" << floatThreshold << " Depth:" << depth;
    299 				stringResult	= s.str();
    300 			}
    301 
    302 			return result;
    303 		}
    304 
    305 		default:
    306 			DE_FATAL("Invalid channel class");
    307 			return false;
    308 	}
    309 }
    310 
    311 // This method is copied from the vktRenderPassTests.cpp and extended with the stringResult parameter.
    312 bool comparePixelToStencilClearValue (const ConstPixelBufferAccess&	access,
    313 									  int							x,
    314 									  int							y,
    315 									  deUint32						ref,
    316 									  std::string&					stringResult)
    317 {
    318 	const deUint32	stencil	= access.getPixStencil(x, y);
    319 	const bool		result	= stencil == ref;
    320 
    321 	if (!result)
    322 	{
    323 		std::stringstream s;
    324 		s << "Ref:" << ref << " Threshold:0" << " Stencil:" << stencil;
    325 		stringResult	= s.str();
    326 	}
    327 
    328 	return result;
    329 }
    330 
    331 // This method is copied from the vktRenderPassTests.cpp and extended with the stringResult parameter.
    332 bool comparePixelToColorClearValue (const ConstPixelBufferAccess&	access,
    333 									int								x,
    334 									int								y,
    335 									int								z,
    336 									const VkClearColorValue&		ref,
    337 									std::string&					stringResult)
    338 {
    339 	const TextureFormat				format			= access.getFormat();
    340 	const TextureChannelClass		channelClass	= getTextureChannelClass(format.type);
    341 	const BVec4						channelMask		= getTextureFormatChannelMask(format);
    342 
    343 	switch (channelClass)
    344 	{
    345 		case TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT:
    346 		case TEXTURECHANNELCLASS_SIGNED_FIXED_POINT:
    347 		{
    348 			const IVec4	bitDepth	(getTextureFormatBitDepth(format));
    349 			const Vec4	resColor	(access.getPixel(x, y, z));
    350 			Vec4		refColor	(ref.float32[0],
    351 									 ref.float32[1],
    352 									 ref.float32[2],
    353 									 ref.float32[3]);
    354 			const int	modifier	= (channelClass == TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT) ? 0 : 1;
    355 			const Vec4	threshold	(bitDepth[0] > 0 ? 1.0f / ((float)(1 << (bitDepth[0] - modifier)) - 1.0f) : 1.0f,
    356 									 bitDepth[1] > 0 ? 1.0f / ((float)(1 << (bitDepth[1] - modifier)) - 1.0f) : 1.0f,
    357 									 bitDepth[2] > 0 ? 1.0f / ((float)(1 << (bitDepth[2] - modifier)) - 1.0f) : 1.0f,
    358 									 bitDepth[3] > 0 ? 1.0f / ((float)(1 << (bitDepth[3] - modifier)) - 1.0f) : 1.0f);
    359 
    360 			if (isSRGB(access.getFormat()))
    361 				refColor	= linearToSRGB(refColor);
    362 
    363 			const bool	result		= !(anyNotEqual(logicalAnd(lessThanEqual(absDiff(resColor, refColor), threshold), channelMask), channelMask));
    364 
    365 			if (!result)
    366 			{
    367 				std::stringstream s;
    368 				s << "Ref:" << refColor << " Mask:" << channelMask << " Threshold:" << threshold << " Color:" << resColor;
    369 				stringResult	= s.str();
    370 			}
    371 
    372 			return result;
    373 		}
    374 
    375 		case TEXTURECHANNELCLASS_UNSIGNED_INTEGER:
    376 		{
    377 			const UVec4	resColor	(access.getPixelUint(x, y, z));
    378 			const UVec4	refColor	(ref.uint32[0],
    379 									 ref.uint32[1],
    380 									 ref.uint32[2],
    381 									 ref.uint32[3]);
    382 			const UVec4	threshold	(1);
    383 
    384 			const bool	result		= !(anyNotEqual(logicalAnd(lessThanEqual(absDiff(resColor, refColor), threshold), channelMask), channelMask));
    385 
    386 			if (!result)
    387 			{
    388 				std::stringstream s;
    389 				s << "Ref:" << refColor << " Mask:" << channelMask << " Threshold:" << threshold << " Color:" << resColor;
    390 				stringResult	= s.str();
    391 			}
    392 
    393 			return result;
    394 		}
    395 
    396 		case TEXTURECHANNELCLASS_SIGNED_INTEGER:
    397 		{
    398 			const IVec4	resColor	(access.getPixelInt(x, y, z));
    399 			const IVec4	refColor	(ref.int32[0],
    400 									 ref.int32[1],
    401 									 ref.int32[2],
    402 									 ref.int32[3]);
    403 			const IVec4	threshold	(1);
    404 
    405 			const bool	result		= !(anyNotEqual(logicalAnd(lessThanEqual(absDiff(resColor, refColor), threshold), channelMask), channelMask));
    406 
    407 			if (!result)
    408 			{
    409 				std::stringstream s;
    410 				s << "Ref:" << refColor << " Mask:" << channelMask << " Threshold:" << threshold << " Color:" << resColor;
    411 				stringResult	= s.str();
    412 			}
    413 
    414 			return result;
    415 		}
    416 
    417 		case TEXTURECHANNELCLASS_FLOATING_POINT:
    418 		{
    419 			const Vec4	resColor		(access.getPixel(x, y, z));
    420 			const Vec4	refColor		(ref.float32[0],
    421 										 ref.float32[1],
    422 										 ref.float32[2],
    423 										 ref.float32[3]);
    424 			const IVec4	mantissaBits	(getTextureFormatMantissaBitDepth(format));
    425 			const IVec4	threshold		(10 * IVec4(1) << (23 - mantissaBits));
    426 
    427 			DE_ASSERT(allEqual(greaterThanEqual(threshold, IVec4(0)), BVec4(true)));
    428 
    429 			for (int ndx = 0; ndx < 4; ndx++)
    430 			{
    431 				const bool result	= !(calcFloatDiff(resColor[ndx], refColor[ndx]) > threshold[ndx] && channelMask[ndx]);
    432 
    433 				if (!result)
    434 				{
    435 					float				floatThreshold	= Float32((deUint32)(threshold)[0]).asFloat();
    436 					Vec4				thresholdVec4	(floatThreshold,
    437 														 floatThreshold,
    438 														 floatThreshold,
    439 														 floatThreshold);
    440 					std::stringstream	s;
    441 					s << "Ref:" << refColor << " Mask:" << channelMask << " Threshold:" << thresholdVec4 << " Color:" << resColor;
    442 					stringResult	= s.str();
    443 
    444 					return false;
    445 				}
    446 			}
    447 
    448 			return true;
    449 		}
    450 
    451 		default:
    452 			DE_FATAL("Invalid channel class");
    453 			return false;
    454 	}
    455 }
    456 
    457 struct TestParams
    458 {
    459 	bool			useSingleMipLevel;	//!< only mip level 0, otherwise up to maxMipLevels
    460 	VkImageType		imageType;
    461 	VkFormat		imageFormat;
    462 	VkExtent3D		imageExtent;
    463 	deUint32        imageLayerCount;
    464 	LayerRange      imageViewLayerRange;
    465 	VkClearValue	initValue;
    466 	VkClearValue	clearValue[2];		//!< the second value is used with more than one mip map
    467 	LayerRange		clearLayerRange;
    468 	AllocationKind	allocationKind;
    469 };
    470 
    471 class ImageClearingTestInstance : public vkt::TestInstance
    472 {
    473 public:
    474 										ImageClearingTestInstance		(Context&			context,
    475 																		 const TestParams&	testParams);
    476 
    477 	Move<VkCommandPool>					createCommandPool				(VkCommandPoolCreateFlags commandPoolCreateFlags) const;
    478 	Move<VkCommandBuffer>				allocatePrimaryCommandBuffer	(VkCommandPool commandPool) const;
    479 	Move<VkImage>						createImage						(VkImageType imageType, VkFormat format, VkExtent3D extent, deUint32 arrayLayerCount, VkImageUsageFlags usage) const;
    480 	Move<VkImageView>					createImageView					(VkImage image, VkImageViewType viewType, VkFormat format, VkImageAspectFlags aspectMask, LayerRange layerRange) const;
    481 	Move<VkRenderPass>					createRenderPass				(VkFormat format) const;
    482 	Move<VkFramebuffer>					createFrameBuffer				(VkImageView imageView, VkRenderPass renderPass, deUint32 imageWidth, deUint32 imageHeight, deUint32 imageLayersCount) const;
    483 
    484 	void								beginCommandBuffer				(VkCommandBufferUsageFlags usageFlags) const;
    485 	void								endCommandBuffer				(void) const;
    486 	void								submitCommandBuffer				(void) const;
    487 	void								beginRenderPass					(VkSubpassContents content, VkClearValue clearValue) const;
    488 
    489 	void								pipelineImageBarrier			(VkPipelineStageFlags srcStageMask, VkPipelineStageFlags dstStageMask, VkAccessFlags srcAccessMask, VkAccessFlags dstAccessMask, VkImageLayout oldLayout, VkImageLayout newLayout) const;
    490 	de::MovePtr<TextureLevelPyramid>	readImage						(VkImageAspectFlags aspectMask, deUint32 baseLayer) const;
    491 	tcu::TestStatus						verifyResultImage				(const std::string& successMessage, const UVec4& clearCoords = UVec4()) const;
    492 
    493 protected:
    494 	enum ViewType
    495 	{
    496 		VIEW_TYPE_SINGLE,
    497 		VIEW_TYPE_ARRAY
    498 	};
    499 	VkImageViewType						getCorrespondingImageViewType	(VkImageType imageType, ViewType viewType) const;
    500 	VkImageUsageFlags					getImageUsageFlags				(VkFormat format) const;
    501 	VkImageAspectFlags					getImageAspectFlags				(VkFormat format) const;
    502 	bool								getIsAttachmentFormat			(VkFormat format) const;
    503 	bool								getIsStencilFormat				(VkFormat format) const;
    504 	bool								getIsDepthFormat				(VkFormat format) const;
    505 	VkImageFormatProperties				getImageFormatProperties		(void) const;
    506 	de::MovePtr<Allocation>				allocateAndBindImageMemory		(VkImage image) const;
    507 
    508 	const TestParams&					m_params;
    509 	const VkDevice						m_device;
    510 	const InstanceInterface&			m_vki;
    511 	const DeviceInterface&				m_vkd;
    512 	const VkQueue						m_queue;
    513 	const deUint32						m_queueFamilyIndex;
    514 	Allocator&							m_allocator;
    515 
    516 	const bool							m_isAttachmentFormat;
    517 	const VkImageUsageFlags				m_imageUsageFlags;
    518 	const VkImageAspectFlags			m_imageAspectFlags;
    519 	const VkImageFormatProperties		m_imageFormatProperties;
    520 	const deUint32						m_imageMipLevels;
    521 	const deUint32						m_thresholdMipLevel;
    522 
    523 	Unique<VkCommandPool>				m_commandPool;
    524 	Unique<VkCommandBuffer>				m_commandBuffer;
    525 
    526 	Unique<VkImage>						m_image;
    527 	de::MovePtr<Allocation>				m_imageMemory;
    528 	Unique<VkImageView>					m_imageView;
    529 	Unique<VkRenderPass>				m_renderPass;
    530 	Unique<VkFramebuffer>				m_frameBuffer;
    531 };
    532 
    533 ImageClearingTestInstance::ImageClearingTestInstance (Context& context, const TestParams& params)
    534 	: TestInstance				(context)
    535 	, m_params					(params)
    536 	, m_device					(context.getDevice())
    537 	, m_vki						(context.getInstanceInterface())
    538 	, m_vkd						(context.getDeviceInterface())
    539 	, m_queue					(context.getUniversalQueue())
    540 	, m_queueFamilyIndex		(context.getUniversalQueueFamilyIndex())
    541 	, m_allocator				(context.getDefaultAllocator())
    542 	, m_isAttachmentFormat		(getIsAttachmentFormat(params.imageFormat))
    543 	, m_imageUsageFlags			(getImageUsageFlags(params.imageFormat))
    544 	, m_imageAspectFlags		(getImageAspectFlags(params.imageFormat))
    545 	, m_imageFormatProperties	(getImageFormatProperties())
    546 	, m_imageMipLevels			(params.useSingleMipLevel ? 1u : getNumMipLevels(params.imageExtent, m_imageFormatProperties.maxMipLevels))
    547 	, m_thresholdMipLevel		(std::max(m_imageMipLevels / 2u, 1u))
    548 	, m_commandPool				(createCommandPool(VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT))
    549 	, m_commandBuffer			(allocatePrimaryCommandBuffer(*m_commandPool))
    550 
    551 	, m_image					(createImage(params.imageType,
    552 											 params.imageFormat,
    553 											 params.imageExtent,
    554 											 params.imageLayerCount,
    555 											 m_imageUsageFlags))
    556 
    557 	, m_imageMemory				(allocateAndBindImageMemory(*m_image))
    558 	, m_imageView				(m_isAttachmentFormat ? createImageView(*m_image,
    559 												 getCorrespondingImageViewType(params.imageType, params.imageLayerCount > 1u ? VIEW_TYPE_ARRAY : VIEW_TYPE_SINGLE),
    560 												 params.imageFormat,
    561 												 m_imageAspectFlags,
    562 												 params.imageViewLayerRange) : vk::Move<VkImageView>())
    563 
    564 	, m_renderPass				(m_isAttachmentFormat ? createRenderPass(params.imageFormat) : vk::Move<vk::VkRenderPass>())
    565 	, m_frameBuffer				(m_isAttachmentFormat ? createFrameBuffer(*m_imageView, *m_renderPass, params.imageExtent.width, params.imageExtent.height, params.imageViewLayerRange.layerCount) : vk::Move<vk::VkFramebuffer>())
    566 {
    567 	if (m_params.allocationKind == ALLOCATION_KIND_DEDICATED)
    568 	{
    569 		const std::string extensionName("VK_KHR_dedicated_allocation");
    570 
    571 		if (!de::contains(context.getDeviceExtensions().begin(), context.getDeviceExtensions().end(), extensionName))
    572 			TCU_THROW(NotSupportedError, std::string(extensionName + " is not supported").c_str());
    573 	}
    574 }
    575 
    576 VkImageViewType ImageClearingTestInstance::getCorrespondingImageViewType (VkImageType imageType, ViewType viewType) const
    577 {
    578 	switch (imageType)
    579 	{
    580 	case VK_IMAGE_TYPE_1D:
    581 		return (viewType == VIEW_TYPE_ARRAY) ?  VK_IMAGE_VIEW_TYPE_1D_ARRAY : VK_IMAGE_VIEW_TYPE_1D;
    582 	case VK_IMAGE_TYPE_2D:
    583 		return (viewType == VIEW_TYPE_ARRAY) ?  VK_IMAGE_VIEW_TYPE_2D_ARRAY : VK_IMAGE_VIEW_TYPE_2D;
    584 	case VK_IMAGE_TYPE_3D:
    585 		if (viewType != VIEW_TYPE_SINGLE)
    586 		{
    587 			DE_FATAL("Cannot have 3D image array");
    588 		}
    589 		return VK_IMAGE_VIEW_TYPE_3D;
    590 	default:
    591 		DE_FATAL("Unknown image type!");
    592 	}
    593 
    594 	return VK_IMAGE_VIEW_TYPE_2D;
    595 }
    596 
    597 VkImageUsageFlags ImageClearingTestInstance::getImageUsageFlags (VkFormat format) const
    598 {
    599 	VkImageUsageFlags	commonFlags	= VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT;
    600 
    601 	if (m_isAttachmentFormat)
    602 	{
    603 		if (isDepthStencilFormat(format))
    604 			return commonFlags | VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
    605 
    606 		return commonFlags | VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT;
    607 	}
    608 	return commonFlags;
    609 }
    610 
    611 VkImageAspectFlags ImageClearingTestInstance::getImageAspectFlags (VkFormat format) const
    612 {
    613 	VkImageAspectFlags	imageAspectFlags	= 0;
    614 
    615 	if (getIsDepthFormat(format))
    616 		imageAspectFlags |= VK_IMAGE_ASPECT_DEPTH_BIT;
    617 
    618 	if (getIsStencilFormat(format))
    619 		imageAspectFlags |= VK_IMAGE_ASPECT_STENCIL_BIT;
    620 
    621 	if (imageAspectFlags == 0)
    622 		imageAspectFlags = VK_IMAGE_ASPECT_COLOR_BIT;
    623 
    624 	return imageAspectFlags;
    625 }
    626 
    627 bool ImageClearingTestInstance::getIsAttachmentFormat (VkFormat format) const
    628 {
    629 	const VkFormatProperties props	= vk::getPhysicalDeviceFormatProperties(m_vki, m_context.getPhysicalDevice(), format);
    630 
    631 	return (props.optimalTilingFeatures & (vk::VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT | vk::VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT)) != 0;
    632 }
    633 
    634 bool ImageClearingTestInstance::getIsStencilFormat (VkFormat format) const
    635 {
    636 	const TextureFormat tcuFormat	= mapVkFormat(format);
    637 
    638 	if (tcuFormat.order == TextureFormat::S || tcuFormat.order == TextureFormat::DS)
    639 		return true;
    640 
    641 	return false;
    642 }
    643 
    644 bool ImageClearingTestInstance::getIsDepthFormat (VkFormat format) const
    645 {
    646 	const TextureFormat	tcuFormat	= mapVkFormat(format);
    647 
    648 	if (tcuFormat.order == TextureFormat::D || tcuFormat.order == TextureFormat::DS)
    649 		return true;
    650 
    651 	return false;
    652 }
    653 
    654 VkImageFormatProperties ImageClearingTestInstance::getImageFormatProperties (void) const
    655 {
    656 	VkImageFormatProperties properties;
    657 	const VkResult result = m_vki.getPhysicalDeviceImageFormatProperties(m_context.getPhysicalDevice(), m_params.imageFormat, m_params.imageType,
    658 																		 VK_IMAGE_TILING_OPTIMAL, m_imageUsageFlags, (VkImageCreateFlags)0, &properties);
    659 
    660 	if (result == VK_ERROR_FORMAT_NOT_SUPPORTED)
    661 		TCU_THROW(NotSupportedError, "Format not supported");
    662 	else
    663 		return properties;
    664 }
    665 
    666 de::MovePtr<Allocation> ImageClearingTestInstance::allocateAndBindImageMemory (VkImage image) const
    667 {
    668 	de::MovePtr<Allocation>	imageMemory	(allocateImage(m_vki, m_vkd, m_context.getPhysicalDevice(), m_device, image, MemoryRequirement::Any, m_allocator, m_params.allocationKind));
    669 	VK_CHECK(m_vkd.bindImageMemory(m_device, image, imageMemory->getMemory(), imageMemory->getOffset()));
    670 	return imageMemory;
    671 }
    672 
    673 Move<VkCommandPool> ImageClearingTestInstance::createCommandPool (VkCommandPoolCreateFlags commandPoolCreateFlags) const
    674 {
    675 	return vk::createCommandPool(m_vkd, m_device, commandPoolCreateFlags, m_queueFamilyIndex);
    676 }
    677 
    678 Move<VkCommandBuffer> ImageClearingTestInstance::allocatePrimaryCommandBuffer (VkCommandPool commandPool) const
    679 {
    680 	return vk::allocateCommandBuffer(m_vkd, m_device, commandPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
    681 }
    682 
    683 Move<VkImage> ImageClearingTestInstance::createImage (VkImageType imageType, VkFormat format, VkExtent3D extent, deUint32 arrayLayerCount, VkImageUsageFlags usage) const
    684 {
    685 	const VkImageCreateInfo					imageCreateInfo			=
    686 	{
    687 		VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,		// VkStructureType			sType;
    688 		DE_NULL,									// const void*				pNext;
    689 		0u,											// VkImageCreateFlags		flags;
    690 		imageType,									// VkImageType				imageType;
    691 		format,										// VkFormat					format;
    692 		extent,										// VkExtent3D				extent;
    693 		m_imageMipLevels,							// deUint32					mipLevels;
    694 		arrayLayerCount,							// deUint32					arrayLayers;
    695 		VK_SAMPLE_COUNT_1_BIT,						// VkSampleCountFlagBits	samples;
    696 		VK_IMAGE_TILING_OPTIMAL,					// VkImageTiling			tiling;
    697 		usage,										// VkImageUsageFlags		usage;
    698 		VK_SHARING_MODE_EXCLUSIVE,					// VkSharingMode			sharingMode;
    699 		1u,											// deUint32					queueFamilyIndexCount;
    700 		&m_queueFamilyIndex,						// const deUint32*			pQueueFamilyIndices;
    701 		VK_IMAGE_LAYOUT_UNDEFINED					// VkImageLayout			initialLayout;
    702 	};
    703 
    704 	return vk::createImage(m_vkd, m_device, &imageCreateInfo, DE_NULL);
    705 }
    706 
    707 Move<VkImageView> ImageClearingTestInstance::createImageView (VkImage image, VkImageViewType viewType, VkFormat format, VkImageAspectFlags aspectMask, LayerRange layerRange) const
    708 {
    709 	const VkImageViewCreateInfo				imageViewCreateInfo		=
    710 	{
    711 		VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,	// VkStructureType				sType;
    712 		DE_NULL,									// const void*					pNext;
    713 		0u,											// VkImageViewCreateFlags		flags;
    714 		image,										// VkImage						image;
    715 		viewType,									// VkImageViewType				viewType;
    716 		format,										// VkFormat						format;
    717 		{
    718 			VK_COMPONENT_SWIZZLE_IDENTITY,				// VkComponentSwizzle			r;
    719 			VK_COMPONENT_SWIZZLE_IDENTITY,				// VkComponentSwizzle			g;
    720 			VK_COMPONENT_SWIZZLE_IDENTITY,				// VkComponentSwizzle			b;
    721 			VK_COMPONENT_SWIZZLE_IDENTITY,				// VkComponentSwizzle			a;
    722 		},											// VkComponentMapping			components;
    723 		{
    724 			aspectMask,									// VkImageAspectFlags			aspectMask;
    725 			0u,											// deUint32						baseMipLevel;
    726 			1u,											// deUint32						mipLevels;
    727 			layerRange.baseArrayLayer,					// deUint32						baseArrayLayer;
    728 			layerRange.layerCount,						// deUint32						arraySize;
    729 		},												// VkImageSubresourceRange		subresourceRange;
    730 	};
    731 
    732 	return vk::createImageView(m_vkd, m_device, &imageViewCreateInfo, DE_NULL);
    733 }
    734 
    735 Move<VkRenderPass> ImageClearingTestInstance::createRenderPass (VkFormat format) const
    736 {
    737 	VkImageLayout							imageLayout;
    738 
    739 	if (isDepthStencilFormat(format))
    740 		imageLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL;
    741 	else
    742 		imageLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
    743 
    744 	const VkAttachmentDescription			attachmentDesc			=
    745 	{
    746 		0u,													// VkAttachmentDescriptionFlags		flags;
    747 		format,												// VkFormat							format;
    748 		VK_SAMPLE_COUNT_1_BIT,								// VkSampleCountFlagBits			samples;
    749 		VK_ATTACHMENT_LOAD_OP_CLEAR,						// VkAttachmentLoadOp				loadOp;
    750 		VK_ATTACHMENT_STORE_OP_STORE,						// VkAttachmentStoreOp				storeOp;
    751 		VK_ATTACHMENT_LOAD_OP_CLEAR,						// VkAttachmentLoadOp				stencilLoadOp;
    752 		VK_ATTACHMENT_STORE_OP_STORE,						// VkAttachmentStoreOp				stencilStoreOp;
    753 		imageLayout,										// VkImageLayout					initialLayout;
    754 		imageLayout,										// VkImageLayout					finalLayout;
    755 	};
    756 
    757 	const VkAttachmentDescription			attachments[1]			=
    758 	{
    759 		attachmentDesc
    760 	};
    761 
    762 	const VkAttachmentReference				attachmentRef			=
    763 	{
    764 		0u,													// deUint32							attachment;
    765 		imageLayout,										// VkImageLayout					layout;
    766 	};
    767 
    768 	const VkAttachmentReference*			pColorAttachments		= DE_NULL;
    769 	const VkAttachmentReference*			pDepthStencilAttachment	= DE_NULL;
    770 	deUint32								colorAttachmentCount	= 1;
    771 
    772 	if (isDepthStencilFormat(format))
    773 	{
    774 		colorAttachmentCount	= 0;
    775 		pDepthStencilAttachment	= &attachmentRef;
    776 	}
    777 	else
    778 	{
    779 		colorAttachmentCount	= 1;
    780 		pColorAttachments		= &attachmentRef;
    781 	}
    782 
    783 	const VkSubpassDescription				subpassDesc[1]			=
    784 	{
    785 		{
    786 			0u,												// VkSubpassDescriptionFlags		flags;
    787 			VK_PIPELINE_BIND_POINT_GRAPHICS,				// VkPipelineBindPoint				pipelineBindPoint;
    788 			0u,												// deUint32							inputAttachmentCount;
    789 			DE_NULL,										// const VkAttachmentReference*		pInputAttachments;
    790 			colorAttachmentCount,							// deUint32							colorAttachmentCount;
    791 			pColorAttachments,								// const VkAttachmentReference*		pColorAttachments;
    792 			DE_NULL,										// const VkAttachmentReference*		pResolveAttachments;
    793 			pDepthStencilAttachment,						// const VkAttachmentReference*		pDepthStencilAttachment;
    794 			0u,												// deUint32							preserveAttachmentCount;
    795 			DE_NULL,										// const VkAttachmentReference*		pPreserveAttachments;
    796 		}
    797 	};
    798 
    799 	const VkRenderPassCreateInfo			renderPassCreateInfo	=
    800 	{
    801 		VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,			// VkStructureType					sType;
    802 		DE_NULL,											// const void*						pNext;
    803 		0u,													// VkRenderPassCreateFlags			flags;
    804 		1u,													// deUint32							attachmentCount;
    805 		attachments,										// const VkAttachmentDescription*	pAttachments;
    806 		1u,													// deUint32							subpassCount;
    807 		subpassDesc,										// const VkSubpassDescription*		pSubpasses;
    808 		0u,													// deUint32							dependencyCount;
    809 		DE_NULL,											// const VkSubpassDependency*		pDependencies;
    810 	};
    811 
    812 	return vk::createRenderPass(m_vkd, m_device, &renderPassCreateInfo, DE_NULL);
    813 }
    814 
    815 Move<VkFramebuffer> ImageClearingTestInstance::createFrameBuffer (VkImageView imageView, VkRenderPass renderPass, deUint32 imageWidth, deUint32 imageHeight, deUint32 imageLayersCount) const
    816 {
    817 	const VkImageView						attachmentViews[1]		=
    818 	{
    819 		imageView
    820 	};
    821 
    822 	const VkFramebufferCreateInfo			framebufferCreateInfo	=
    823 	{
    824 		VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,	// VkStructureType			sType;
    825 		DE_NULL,									// const void*				pNext;
    826 		0u,											// VkFramebufferCreateFlags	flags;
    827 		renderPass,									// VkRenderPass				renderPass;
    828 		1,											// deUint32					attachmentCount;
    829 		attachmentViews,							// const VkImageView*		pAttachments;
    830 		imageWidth,									// deUint32					width;
    831 		imageHeight,								// deUint32					height;
    832 		imageLayersCount,							// deUint32					layers;
    833 	};
    834 
    835 	return createFramebuffer(m_vkd, m_device, &framebufferCreateInfo, DE_NULL);
    836 }
    837 
    838 void ImageClearingTestInstance::beginCommandBuffer (VkCommandBufferUsageFlags usageFlags) const
    839 {
    840 	const VkCommandBufferBeginInfo			commandBufferBeginInfo	=
    841 	{
    842 		VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO,			// VkStructureType                          sType;
    843 		DE_NULL,												// const void*                              pNext;
    844 		usageFlags,												// VkCommandBufferUsageFlags                flags;
    845 		DE_NULL													// const VkCommandBufferInheritanceInfo*    pInheritanceInfo;
    846 	};
    847 
    848 	VK_CHECK(m_vkd.beginCommandBuffer(*m_commandBuffer, &commandBufferBeginInfo));
    849 }
    850 
    851 void ImageClearingTestInstance::endCommandBuffer (void) const
    852 {
    853 	VK_CHECK(m_vkd.endCommandBuffer(*m_commandBuffer));
    854 }
    855 
    856 void ImageClearingTestInstance::submitCommandBuffer (void) const
    857 {
    858 	const Unique<VkFence>					fence					(createFence(m_vkd, m_device));
    859 
    860 	const VkSubmitInfo						submitInfo				=
    861 	{
    862 		VK_STRUCTURE_TYPE_SUBMIT_INFO,							// VkStructureType                sType;
    863 		DE_NULL,												// const void*                    pNext;
    864 		0u,														// deUint32                       waitSemaphoreCount;
    865 		DE_NULL,												// const VkSemaphore*             pWaitSemaphores;
    866 		DE_NULL,												// const VkPipelineStageFlags*    pWaitDstStageMask;
    867 		1u,														// deUint32                       commandBufferCount;
    868 		&(*m_commandBuffer),									// const VkCommandBuffer*         pCommandBuffers;
    869 		0u,														// deUint32                       signalSemaphoreCount;
    870 		DE_NULL													// const VkSemaphore*             pSignalSemaphores;
    871 	};
    872 
    873 	VK_CHECK(m_vkd.queueSubmit(m_queue, 1, &submitInfo, *fence));
    874 
    875 	VK_CHECK(m_vkd.waitForFences(m_device, 1, &fence.get(), VK_TRUE, ~0ull));
    876 }
    877 
    878 void ImageClearingTestInstance::pipelineImageBarrier(VkPipelineStageFlags srcStageMask, VkPipelineStageFlags dstStageMask, VkAccessFlags srcAccessMask, VkAccessFlags dstAccessMask, VkImageLayout oldLayout, VkImageLayout newLayout) const
    879 {
    880 	const VkImageMemoryBarrier		imageBarrier	=
    881 	{
    882 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
    883 		DE_NULL,									// const void*				pNext;
    884 		srcAccessMask,								// VkAccessFlags			srcAccessMask;
    885 		dstAccessMask,								// VkAccessFlags			dstAccessMask;
    886 		oldLayout,									// VkImageLayout			oldLayout;
    887 		newLayout,									// VkImageLayout			newLayout;
    888 		VK_QUEUE_FAMILY_IGNORED,					// deUint32					srcQueueFamilyIndex;
    889 		VK_QUEUE_FAMILY_IGNORED,					// deUint32					destQueueFamilyIndex;
    890 		*m_image,									// VkImage					image;
    891 		{
    892 			m_imageAspectFlags,							// VkImageAspectFlags	aspectMask;
    893 			0u,											// deUint32				baseMipLevel;
    894 			VK_REMAINING_MIP_LEVELS,					// deUint32				levelCount;
    895 			0u,											// deUint32				baseArrayLayer;
    896 			VK_REMAINING_ARRAY_LAYERS,					// deUint32				layerCount;
    897 		},											// VkImageSubresourceRange	subresourceRange;
    898 	};
    899 
    900 	m_vkd.cmdPipelineBarrier(*m_commandBuffer, srcStageMask, dstStageMask, 0, 0, DE_NULL, 0, DE_NULL, 1, &imageBarrier);
    901 }
    902 
    903 de::MovePtr<TextureLevelPyramid> ImageClearingTestInstance::readImage (VkImageAspectFlags aspectMask, deUint32 arrayLayer) const
    904 {
    905 	const TextureFormat					tcuFormat		= aspectMask == VK_IMAGE_ASPECT_COLOR_BIT ? mapVkFormat(m_params.imageFormat) :
    906 														  aspectMask == VK_IMAGE_ASPECT_DEPTH_BIT ? getDepthCopyFormat(m_params.imageFormat) :
    907 														  aspectMask == VK_IMAGE_ASPECT_STENCIL_BIT ? getStencilCopyFormat(m_params.imageFormat) :
    908 														  TextureFormat();
    909 	const deUint32						pixelSize		= getPixelSize(tcuFormat);
    910 	deUint32							alignment		= 4;	// subsequent mip levels aligned to 4 bytes
    911 
    912 	if (!getIsDepthFormat(m_params.imageFormat) && !getIsStencilFormat(m_params.imageFormat))
    913 		alignment = lowestCommonMultiple(pixelSize, alignment); // alignment must be multiple of pixel size, if not D/S.
    914 
    915 	const std::vector<deUint32>			mipLevelSizes	= getImageMipLevelSizes(pixelSize, m_params.imageExtent, m_imageMipLevels, alignment);
    916 	const VkDeviceSize					imageTotalSize	= std::accumulate(mipLevelSizes.begin(), mipLevelSizes.end(), 0u);
    917 
    918 	de::MovePtr<TextureLevelPyramid>	result			(new TextureLevelPyramid(tcuFormat, m_imageMipLevels));
    919 	Move<VkBuffer>						buffer;
    920 	de::MovePtr<Allocation>				bufferAlloc;
    921 
    922 	// Create destination buffer
    923 	{
    924 		const VkBufferCreateInfo	bufferParams	=
    925 		{
    926 			VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,		// VkStructureType		sType;
    927 			DE_NULL,									// const void*			pNext;
    928 			0u,											// VkBufferCreateFlags	flags;
    929 			imageTotalSize,								// VkDeviceSize			size;
    930 			VK_BUFFER_USAGE_TRANSFER_DST_BIT,			// VkBufferUsageFlags	usage;
    931 			VK_SHARING_MODE_EXCLUSIVE,					// VkSharingMode		sharingMode;
    932 			0u,											// deUint32				queueFamilyIndexCount;
    933 			DE_NULL										// const deUint32*		pQueueFamilyIndices;
    934 		};
    935 
    936 		buffer		= createBuffer(m_vkd, m_device, &bufferParams);
    937 		bufferAlloc	= allocateBuffer(m_vki, m_vkd, m_context.getPhysicalDevice(), m_device, *buffer, MemoryRequirement::HostVisible, m_allocator, m_params.allocationKind);
    938 		VK_CHECK(m_vkd.bindBufferMemory(m_device, *buffer, bufferAlloc->getMemory(), bufferAlloc->getOffset()));
    939 	}
    940 
    941 	// Barriers for copying image to buffer
    942 
    943 	const VkBufferMemoryBarrier		bufferBarrier	=
    944 	{
    945 		VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,	// VkStructureType	sType;
    946 		DE_NULL,									// const void*		pNext;
    947 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags	srcAccessMask;
    948 		VK_ACCESS_HOST_READ_BIT,					// VkAccessFlags	dstAccessMask;
    949 		VK_QUEUE_FAMILY_IGNORED,					// deUint32			srcQueueFamilyIndex;
    950 		VK_QUEUE_FAMILY_IGNORED,					// deUint32			dstQueueFamilyIndex;
    951 		*buffer,									// VkBuffer			buffer;
    952 		0u,											// VkDeviceSize		offset;
    953 		imageTotalSize,								// VkDeviceSize		size;
    954 	};
    955 
    956 	// Copy image to buffer
    957 	std::vector<VkBufferImageCopy> copyRegions;
    958 	{
    959 		deUint32 offset = 0u;
    960 		for (deUint32 mipLevel = 0; mipLevel < m_imageMipLevels; ++mipLevel)
    961 		{
    962 			const VkExtent3D		extent	= getMipLevelExtent(m_params.imageExtent, mipLevel);
    963 			const VkBufferImageCopy	region	=
    964 			{
    965 				offset,										// VkDeviceSize				bufferOffset;
    966 				0u,											// deUint32					bufferRowLength;
    967 				0u,											// deUint32					bufferImageHeight;
    968 				{ aspectMask, mipLevel, arrayLayer, 1u },	// VkImageSubresourceLayers	imageSubresource;
    969 				{ 0, 0, 0 },								// VkOffset3D				imageOffset;
    970 				extent										// VkExtent3D				imageExtent;
    971 			};
    972 			copyRegions.push_back(region);
    973 			offset += mipLevelSizes[mipLevel];
    974 		}
    975 	}
    976 
    977 	beginCommandBuffer(0);
    978 
    979 	pipelineImageBarrier(VK_PIPELINE_STAGE_TRANSFER_BIT,
    980 						 VK_PIPELINE_STAGE_TRANSFER_BIT,
    981 						 VK_ACCESS_TRANSFER_WRITE_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT | VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT,
    982 						 VK_ACCESS_TRANSFER_READ_BIT,
    983 						 VK_IMAGE_LAYOUT_GENERAL,
    984 						 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL);
    985 
    986 	m_vkd.cmdCopyImageToBuffer(*m_commandBuffer, *m_image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, *buffer, static_cast<deUint32>(copyRegions.size()), &copyRegions[0]);
    987 	m_vkd.cmdPipelineBarrier(*m_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);
    988 
    989 	pipelineImageBarrier(VK_PIPELINE_STAGE_TRANSFER_BIT,
    990 						 VK_PIPELINE_STAGE_TRANSFER_BIT,
    991 						 VK_ACCESS_TRANSFER_READ_BIT,
    992 						 VK_ACCESS_TRANSFER_READ_BIT | VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_READ_BIT,
    993 						 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,
    994 						 VK_IMAGE_LAYOUT_GENERAL);
    995 
    996 	endCommandBuffer();
    997 	submitCommandBuffer();
    998 
    999 	invalidateMappedMemoryRange(m_vkd, m_device, bufferAlloc->getMemory(), bufferAlloc->getOffset(), imageTotalSize);
   1000 
   1001 	{
   1002 		deUint32 offset = 0u;
   1003 		for (deUint32 mipLevel = 0; mipLevel < m_imageMipLevels; ++mipLevel)
   1004 		{
   1005 			const VkExtent3D	extent		= getMipLevelExtent(m_params.imageExtent, mipLevel);
   1006 			const void*			pLevelData	= static_cast<const void*>(reinterpret_cast<deUint8*>(bufferAlloc->getHostPtr()) + offset);
   1007 
   1008 			result->allocLevel(mipLevel, extent.width, extent.height, extent.depth);
   1009 			copy(result->getLevel(mipLevel), ConstPixelBufferAccess(result->getFormat(), result->getLevel(mipLevel).getSize(), pLevelData));
   1010 
   1011 			offset += mipLevelSizes[mipLevel];
   1012 		}
   1013 	}
   1014 
   1015 	return result;
   1016 }
   1017 
   1018 tcu::TestStatus ImageClearingTestInstance::verifyResultImage (const std::string& successMessage, const UVec4& clearCoords) const
   1019 {
   1020 	DE_ASSERT((clearCoords == UVec4()) || m_params.imageExtent.depth == 1u);
   1021 
   1022 	if (getIsDepthFormat(m_params.imageFormat))
   1023 	{
   1024 		DE_ASSERT(m_imageMipLevels == 1u);
   1025 
   1026 		for (deUint32 arrayLayer = 0; arrayLayer < m_params.imageLayerCount; ++arrayLayer)
   1027 		{
   1028 			de::MovePtr<TextureLevelPyramid>	image			= readImage(VK_IMAGE_ASPECT_DEPTH_BIT, arrayLayer);
   1029 			std::string							message;
   1030 			float								depthValue;
   1031 
   1032 			for (deUint32 y = 0; y < m_params.imageExtent.height; ++y)
   1033 			for (deUint32 x = 0; x < m_params.imageExtent.width; ++x)
   1034 			{
   1035 				if (isInClearRange(clearCoords, x, y, arrayLayer, m_params.imageViewLayerRange, m_params.clearLayerRange))
   1036 					depthValue = m_params.clearValue[0].depthStencil.depth;
   1037 				else
   1038 				if (isInInitialClearRange(m_isAttachmentFormat, 0u /* mipLevel */, arrayLayer, m_params.imageViewLayerRange))
   1039 				{
   1040 					depthValue = m_params.initValue.depthStencil.depth;
   1041 				}
   1042 				else
   1043 					continue;
   1044 
   1045 				if (!comparePixelToDepthClearValue(image->getLevel(0), x, y, depthValue, message))
   1046 					return TestStatus::fail("Depth value mismatch! " + message);
   1047 			}
   1048 		}
   1049 	}
   1050 
   1051 	if (getIsStencilFormat(m_params.imageFormat))
   1052 	{
   1053 		DE_ASSERT(m_imageMipLevels == 1u);
   1054 
   1055 		for (deUint32 arrayLayer = 0; arrayLayer < m_params.imageLayerCount; ++arrayLayer)
   1056 		{
   1057 			de::MovePtr<TextureLevelPyramid>	image			= readImage(VK_IMAGE_ASPECT_STENCIL_BIT, arrayLayer);
   1058 			std::string							message;
   1059 			deUint32							stencilValue;
   1060 
   1061 			for (deUint32 y = 0; y < m_params.imageExtent.height; ++y)
   1062 			for (deUint32 x = 0; x < m_params.imageExtent.width; ++x)
   1063 			{
   1064 				if (isInClearRange(clearCoords, x, y, arrayLayer, m_params.imageViewLayerRange, m_params.clearLayerRange))
   1065 					stencilValue = m_params.clearValue[0].depthStencil.stencil;
   1066 				else
   1067 				if (isInInitialClearRange(m_isAttachmentFormat, 0u /* mipLevel */, arrayLayer, m_params.imageViewLayerRange))
   1068 				{
   1069 					stencilValue = m_params.initValue.depthStencil.stencil;
   1070 				}
   1071 				else
   1072 					continue;
   1073 
   1074 				if (!comparePixelToStencilClearValue(image->getLevel(0), x, y, stencilValue, message))
   1075 					return TestStatus::fail("Stencil value mismatch! " + message);
   1076 			}
   1077 		}
   1078 	}
   1079 
   1080 	if (!isDepthStencilFormat(m_params.imageFormat))
   1081 	{
   1082 		for (deUint32 arrayLayer = 0; arrayLayer < m_params.imageLayerCount; ++arrayLayer)
   1083 		{
   1084 			de::MovePtr<TextureLevelPyramid>	image			= readImage(VK_IMAGE_ASPECT_COLOR_BIT, arrayLayer);
   1085 			std::string							message;
   1086 			const VkClearColorValue*			pColorValue;
   1087 
   1088 			for (deUint32 mipLevel = 0; mipLevel < m_imageMipLevels; ++mipLevel)
   1089 			{
   1090 				const int			clearColorNdx	= (mipLevel < m_thresholdMipLevel ? 0 : 1);
   1091 				const VkExtent3D	extent			= getMipLevelExtent(m_params.imageExtent, mipLevel);
   1092 
   1093 				for (deUint32 z = 0; z < extent.depth;  ++z)
   1094 				for (deUint32 y = 0; y < extent.height; ++y)
   1095 				for (deUint32 x = 0; x < extent.width;  ++x)
   1096 				{
   1097 					if (isInClearRange(clearCoords, x, y, arrayLayer, m_params.imageViewLayerRange, m_params.clearLayerRange))
   1098 						pColorValue = &m_params.clearValue[clearColorNdx].color;
   1099 					else
   1100 					{
   1101 						if (isInInitialClearRange(m_isAttachmentFormat, mipLevel, arrayLayer, m_params.imageViewLayerRange))
   1102 						{
   1103 							pColorValue = &m_params.initValue.color;
   1104 						}
   1105 						else
   1106 							continue;
   1107 					}
   1108 					if (!comparePixelToColorClearValue(image->getLevel(mipLevel), x, y, z, *pColorValue, message))
   1109 						return TestStatus::fail("Color value mismatch! " + message);
   1110 				}
   1111 			}
   1112 		}
   1113 	}
   1114 
   1115 	return TestStatus::pass(successMessage);
   1116 }
   1117 
   1118 void ImageClearingTestInstance::beginRenderPass (VkSubpassContents content, VkClearValue clearValue) const
   1119 {
   1120 	const VkRenderPassBeginInfo renderPassBeginInfo =
   1121 	{
   1122 		VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO,				// VkStructureType		sType;
   1123 		DE_NULL,												// const void*			pNext;
   1124 		*m_renderPass,											// VkRenderPass			renderPass;
   1125 		*m_frameBuffer,											// VkFramebuffer		framebuffer;
   1126 		{
   1127 			{ 0, 0 },												// VkOffset2D			offset;
   1128 			{
   1129 				m_params.imageExtent.width,								// deUint32				width;
   1130 				m_params.imageExtent.height								// deUint32				height;
   1131 			}														// VkExtent2D			extent;
   1132 		},														// VkRect2D				renderArea;
   1133 		1u,														// deUint32				clearValueCount;
   1134 		&clearValue												// const VkClearValue*	pClearValues;
   1135 	};
   1136 
   1137 	m_vkd.cmdBeginRenderPass(*m_commandBuffer, &renderPassBeginInfo, content);
   1138 }
   1139 
   1140 class ClearColorImageTestInstance : public ImageClearingTestInstance
   1141 {
   1142 public:
   1143 				ClearColorImageTestInstance	(Context& context, const TestParams& testParams) : ImageClearingTestInstance (context, testParams) {}
   1144 	TestStatus	iterate						(void);
   1145 };
   1146 
   1147 TestStatus ClearColorImageTestInstance::iterate (void)
   1148 {
   1149 	std::vector<VkImageSubresourceRange> subresourceRanges;
   1150 
   1151 	if (m_imageMipLevels == 1)
   1152 		subresourceRanges.push_back(makeImageSubresourceRange(m_imageAspectFlags, 0u, 1u, m_params.clearLayerRange.baseArrayLayer, m_params.clearLayerRange.layerCount));
   1153 	else
   1154 	{
   1155 		subresourceRanges.push_back(makeImageSubresourceRange(m_imageAspectFlags,	0u,						m_thresholdMipLevel,		m_params.clearLayerRange.baseArrayLayer, m_params.clearLayerRange.layerCount));
   1156 		subresourceRanges.push_back(makeImageSubresourceRange(m_imageAspectFlags,	m_thresholdMipLevel,	VK_REMAINING_MIP_LEVELS,	m_params.clearLayerRange.baseArrayLayer, m_params.clearLayerRange.layerCount));
   1157 	}
   1158 
   1159 	beginCommandBuffer(0);
   1160 
   1161 	pipelineImageBarrier(VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT,				// VkPipelineStageFlags		srcStageMask
   1162 						 VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,			// VkPipelineStageFlags		dstStageMask
   1163 						 0,												// VkAccessFlags			srcAccessMask
   1164 						 (m_isAttachmentFormat
   1165 							? VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT
   1166 							: VK_ACCESS_TRANSFER_WRITE_BIT),			// VkAccessFlags			dstAccessMask
   1167 						 VK_IMAGE_LAYOUT_UNDEFINED,						// VkImageLayout			oldLayout;
   1168 						 (m_isAttachmentFormat
   1169 							? VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL
   1170 							: VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL));	// VkImageLayout			newLayout;
   1171 
   1172 	if (m_isAttachmentFormat)
   1173 	{
   1174 		beginRenderPass(VK_SUBPASS_CONTENTS_INLINE, m_params.initValue);
   1175 		m_vkd.cmdEndRenderPass(*m_commandBuffer);
   1176 
   1177 		pipelineImageBarrier(VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT,		// VkPipelineStageFlags		srcStageMask
   1178 			VK_PIPELINE_STAGE_TRANSFER_BIT,								// VkPipelineStageFlags		dstStageMask
   1179 			VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT,						// VkAccessFlags			srcAccessMask
   1180 			VK_ACCESS_TRANSFER_WRITE_BIT,								// VkAccessFlags			dstAccessMask
   1181 			VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,					// VkImageLayout			oldLayout;
   1182 			VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL);						// VkImageLayout			newLayout;
   1183 	}
   1184 
   1185 	// Different clear color per range
   1186 	for (std::size_t i = 0u; i < subresourceRanges.size(); ++i)
   1187 		m_vkd.cmdClearColorImage(*m_commandBuffer, *m_image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &m_params.clearValue[i].color, 1, &subresourceRanges[i]);
   1188 
   1189 	pipelineImageBarrier(VK_PIPELINE_STAGE_TRANSFER_BIT,				// VkPipelineStageFlags		srcStageMask
   1190 						 VK_PIPELINE_STAGE_TRANSFER_BIT,				// VkPipelineStageFlags		dstStageMask
   1191 						 VK_ACCESS_TRANSFER_WRITE_BIT,					// VkAccessFlags			srcAccessMask
   1192 						 VK_ACCESS_TRANSFER_READ_BIT,					// VkAccessFlags			dstAccessMask
   1193 						 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,			// VkImageLayout			oldLayout;
   1194 						 VK_IMAGE_LAYOUT_GENERAL);						// VkImageLayout			newLayout;
   1195 
   1196 	endCommandBuffer();
   1197 	submitCommandBuffer();
   1198 
   1199 	return verifyResultImage("cmdClearColorImage passed");
   1200 }
   1201 
   1202 class ClearDepthStencilImageTestInstance : public ImageClearingTestInstance
   1203 {
   1204 public:
   1205 				ClearDepthStencilImageTestInstance	(Context& context, const TestParams& testParams) : ImageClearingTestInstance (context, testParams) {}
   1206 	TestStatus	iterate								(void);
   1207 };
   1208 
   1209 TestStatus ClearDepthStencilImageTestInstance::iterate (void)
   1210 {
   1211 	const VkImageSubresourceRange subresourceRange = makeImageSubresourceRange(m_imageAspectFlags, 0u, 1u, m_params.clearLayerRange.baseArrayLayer, m_params.clearLayerRange.layerCount);
   1212 
   1213 	beginCommandBuffer(0);
   1214 
   1215 	pipelineImageBarrier(VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT,					// VkPipelineStageFlags		srcStageMask
   1216 						 VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,				// VkPipelineStageFlags		dstStageMask
   1217 						 0,													// VkAccessFlags			srcAccessMask
   1218 						 (m_isAttachmentFormat
   1219 							?	VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT
   1220 							:	VK_ACCESS_TRANSFER_WRITE_BIT),				// VkAccessFlags			dstAccessMask
   1221 						 VK_IMAGE_LAYOUT_UNDEFINED,							// VkImageLayout			oldLayout;
   1222 						 (m_isAttachmentFormat
   1223 							?	VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL
   1224 							:	VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL));		// VkImageLayout			newLayout;
   1225 
   1226 	if (m_isAttachmentFormat)
   1227 	{
   1228 		beginRenderPass(VK_SUBPASS_CONTENTS_INLINE, m_params.initValue);
   1229 		m_vkd.cmdEndRenderPass(*m_commandBuffer);
   1230 
   1231 		pipelineImageBarrier(VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT,					// VkPipelineStageFlags		srcStageMask
   1232 							 VK_PIPELINE_STAGE_TRANSFER_BIT,						// VkPipelineStageFlags		dstStageMask
   1233 							 VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT,			// VkAccessFlags			srcAccessMask
   1234 							 VK_ACCESS_TRANSFER_WRITE_BIT,							// VkAccessFlags			dstAccessMask
   1235 							 VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,		// VkImageLayout			oldLayout;
   1236 							 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL);					// VkImageLayout			newLayout;
   1237 	}
   1238 
   1239 	m_vkd.cmdClearDepthStencilImage(*m_commandBuffer, *m_image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &m_params.clearValue[0].depthStencil, 1, &subresourceRange);
   1240 
   1241 	pipelineImageBarrier(VK_PIPELINE_STAGE_TRANSFER_BIT,					// VkPipelineStageFlags		srcStageMask
   1242 						 VK_PIPELINE_STAGE_TRANSFER_BIT,					// VkPipelineStageFlags		dstStageMask
   1243 						 VK_ACCESS_TRANSFER_WRITE_BIT,						// VkAccessFlags			srcAccessMask
   1244 						 VK_ACCESS_TRANSFER_READ_BIT,						// VkAccessFlags			dstAccessMask
   1245 						 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,				// VkImageLayout			oldLayout;
   1246 						 VK_IMAGE_LAYOUT_GENERAL);							// VkImageLayout			newLayout;
   1247 
   1248 	endCommandBuffer();
   1249 	submitCommandBuffer();
   1250 
   1251 	return verifyResultImage("cmdClearDepthStencilImage passed");
   1252 }
   1253 
   1254 class ClearAttachmentTestInstance : public ImageClearingTestInstance
   1255 {
   1256 public:
   1257 	enum ClearType
   1258 	{
   1259 		FULL_CLEAR,
   1260 		PARTIAL_CLEAR,
   1261 	};
   1262 
   1263 	ClearAttachmentTestInstance (Context& context, const TestParams& testParams, const ClearType clearType = FULL_CLEAR)
   1264 		: ImageClearingTestInstance	(context, testParams)
   1265 		, m_clearType				(clearType)
   1266 	{
   1267 		if (!m_isAttachmentFormat)
   1268 			TCU_THROW(NotSupportedError, "Format not renderable");
   1269 	}
   1270 
   1271 	TestStatus iterate (void)
   1272 	{
   1273 		const VkClearAttachment clearAttachment =
   1274 		{
   1275 			m_imageAspectFlags,					// VkImageAspectFlags	aspectMask;
   1276 			0u,									// deUint32				colorAttachment;
   1277 			m_params.clearValue[0]				// VkClearValue			clearValue;
   1278 		};
   1279 
   1280 		UVec4						clearCoords;
   1281 		std::vector<VkClearRect>	clearRects;
   1282 
   1283 		if (m_clearType == FULL_CLEAR)
   1284 		{
   1285 			const VkClearRect rect =
   1286 			{
   1287 				{
   1288 					{ 0, 0 },																	// VkOffset2D    offset;
   1289 					{ m_params.imageExtent.width, m_params.imageExtent.height }					// VkExtent2D    extent;
   1290 				},																			// VkRect2D	rect;
   1291 				m_params.clearLayerRange.baseArrayLayer,								// deUint32	baseArrayLayer;
   1292 				m_params.clearLayerRange.layerCount,									// deUint32	layerCount;
   1293 			};
   1294 
   1295 			clearRects.push_back(rect);
   1296 		}
   1297 		else
   1298 		{
   1299 			const deUint32	clearX		= m_params.imageExtent.width  / 4u;
   1300 			const deUint32	clearY		= m_params.imageExtent.height / 4u;
   1301 			const deUint32	clearWidth	= m_params.imageExtent.width  / 2u;
   1302 			const deUint32	clearHeight	= m_params.imageExtent.height / 2u;
   1303 
   1304 			clearCoords	= UVec4(clearX,					clearY,
   1305 								clearX + clearWidth,	clearY + clearHeight);
   1306 
   1307 			const VkClearRect rects[2] =
   1308 			{
   1309 				{
   1310 					{
   1311 						{ 0,							static_cast<deInt32>(clearY)	},		// VkOffset2D    offset;
   1312 						{ m_params.imageExtent.width,	clearHeight						}		// VkExtent2D    extent;
   1313 					},																		// VkRect2D	rect;
   1314 					m_params.clearLayerRange.baseArrayLayer,								// deUint32	baseArrayLayer;
   1315 					m_params.clearLayerRange.layerCount										// deUint32	layerCount;
   1316 				},
   1317 				{
   1318 					{
   1319 						{ static_cast<deInt32>(clearX),	0							},			// VkOffset2D    offset;
   1320 						{ clearWidth,					m_params.imageExtent.height	}			// VkExtent2D    extent;
   1321 					},																		// VkRect2D	rect;
   1322 					m_params.clearLayerRange.baseArrayLayer,								// deUint32	baseArrayLayer;
   1323 					m_params.clearLayerRange.layerCount										// deUint32	layerCount;
   1324 				}
   1325 			};
   1326 
   1327 			clearRects.push_back(rects[0]);
   1328 			clearRects.push_back(rects[1]);
   1329 		}
   1330 
   1331 		const bool			isDepthStencil		= isDepthStencilFormat(m_params.imageFormat);
   1332 		const VkAccessFlags	accessMask			= (isDepthStencil ? VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT     : VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT);
   1333 		const VkImageLayout	attachmentLayout	= (isDepthStencil ? VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL : VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL);
   1334 
   1335 		beginCommandBuffer(0);
   1336 
   1337 		pipelineImageBarrier(VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT,				// VkPipelineStageFlags		srcStageMask
   1338 							 VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,			// VkPipelineStageFlags		dstStageMask
   1339 							 0,												// VkAccessFlags			srcAccessMask
   1340 							 accessMask,									// VkAccessFlags			dstAccessMask
   1341 							 VK_IMAGE_LAYOUT_UNDEFINED,						// VkImageLayout			oldLayout;
   1342 							 attachmentLayout);								// VkImageLayout			newLayout;
   1343 
   1344 		beginRenderPass(VK_SUBPASS_CONTENTS_INLINE, m_params.initValue);
   1345 		m_vkd.cmdClearAttachments(*m_commandBuffer, 1, &clearAttachment, static_cast<deUint32>(clearRects.size()), &clearRects[0]);
   1346 		m_vkd.cmdEndRenderPass(*m_commandBuffer);
   1347 
   1348 		pipelineImageBarrier(VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT,			// VkPipelineStageFlags		srcStageMask
   1349 							 VK_PIPELINE_STAGE_TRANSFER_BIT,				// VkPipelineStageFlags		dstStageMask
   1350 							 accessMask,									// VkAccessFlags			srcAccessMask
   1351 							 VK_ACCESS_TRANSFER_READ_BIT,					// VkAccessFlags			dstAccessMask
   1352 							 attachmentLayout,								// VkImageLayout			oldLayout;
   1353 							 VK_IMAGE_LAYOUT_GENERAL);						// VkImageLayout			newLayout;
   1354 
   1355 		endCommandBuffer();
   1356 		submitCommandBuffer();
   1357 
   1358 		return verifyResultImage("cmdClearAttachments passed", clearCoords);
   1359 	}
   1360 
   1361 private:
   1362 	const ClearType	m_clearType;
   1363 };
   1364 
   1365 class PartialClearAttachmentTestInstance : public ClearAttachmentTestInstance
   1366 {
   1367 public:
   1368 	PartialClearAttachmentTestInstance (Context& context, const TestParams& testParams) : ClearAttachmentTestInstance (context, testParams, PARTIAL_CLEAR) {}
   1369 };
   1370 
   1371 VkClearValue makeClearColorValue (VkFormat format, float r, float g, float b, float a)
   1372 {
   1373 	const	TextureFormat tcuFormat	= mapVkFormat(format);
   1374 	VkClearValue clearValue;
   1375 
   1376 	if (getTextureChannelClass(tcuFormat.type) == TEXTURECHANNELCLASS_FLOATING_POINT
   1377 		|| getTextureChannelClass(tcuFormat.type) == TEXTURECHANNELCLASS_SIGNED_FIXED_POINT
   1378 		|| getTextureChannelClass(tcuFormat.type) == TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT)
   1379 	{
   1380 		clearValue.color.float32[0] = r;
   1381 		clearValue.color.float32[1] = g;
   1382 		clearValue.color.float32[2] = b;
   1383 		clearValue.color.float32[3] = a;
   1384 	}
   1385 	else if (getTextureChannelClass(tcuFormat.type) == TEXTURECHANNELCLASS_UNSIGNED_INTEGER)
   1386 	{
   1387 		UVec4 maxValues = getFormatMaxUintValue(tcuFormat);
   1388 
   1389 		clearValue.color.uint32[0] = (deUint32)((float)maxValues[0] * r);
   1390 		clearValue.color.uint32[1] = (deUint32)((float)maxValues[1] * g);
   1391 		clearValue.color.uint32[2] = (deUint32)((float)maxValues[2] * b);
   1392 		clearValue.color.uint32[3] = (deUint32)((float)maxValues[3] * a);
   1393 	}
   1394 	else if (getTextureChannelClass(tcuFormat.type) == TEXTURECHANNELCLASS_SIGNED_INTEGER)
   1395 	{
   1396 		IVec4 maxValues = getFormatMaxIntValue(tcuFormat);
   1397 
   1398 		clearValue.color.int32[0] = (deUint32)((float)maxValues[0] * r);
   1399 		clearValue.color.int32[1] = (deUint32)((float)maxValues[1] * g);
   1400 		clearValue.color.int32[2] = (deUint32)((float)maxValues[2] * b);
   1401 		clearValue.color.int32[3] = (deUint32)((float)maxValues[3] * a);
   1402 	}
   1403 	else
   1404 		DE_FATAL("Unknown channel class");
   1405 
   1406 	return clearValue;
   1407 }
   1408 
   1409 std::string getFormatCaseName (VkFormat format)
   1410 {
   1411 	return de::toLower(de::toString(getFormatStr(format)).substr(10));
   1412 }
   1413 
   1414 const char* getImageTypeCaseName (VkImageType type)
   1415 {
   1416 	const char* s_names[] =
   1417 	{
   1418 		"1d",
   1419 		"2d",
   1420 		"3d"
   1421 	};
   1422 	return de::getSizedArrayElement<VK_IMAGE_TYPE_LAST>(s_names, type);
   1423 }
   1424 
   1425 TestCaseGroup* createImageClearingTestsCommon (TestContext& testCtx, tcu::TestCaseGroup* imageClearingTests, AllocationKind allocationKind)
   1426 {
   1427 	de::MovePtr<TestCaseGroup>	colorImageClearTests					(new TestCaseGroup(testCtx, "clear_color_image", "Color Image Clear Tests"));
   1428 	de::MovePtr<TestCaseGroup>	depthStencilImageClearTests				(new TestCaseGroup(testCtx, "clear_depth_stencil_image", "Color Depth/Stencil Image Tests"));
   1429 	de::MovePtr<TestCaseGroup>	colorAttachmentClearTests				(new TestCaseGroup(testCtx, "clear_color_attachment", "Color Color Attachment Tests"));
   1430 	de::MovePtr<TestCaseGroup>	depthStencilAttachmentClearTests		(new TestCaseGroup(testCtx, "clear_depth_stencil_attachment", "Color Depth/Stencil Attachment Tests"));
   1431 	de::MovePtr<TestCaseGroup>	partialColorAttachmentClearTests		(new TestCaseGroup(testCtx, "partial_clear_color_attachment", "Clear Partial Color Attachment Tests"));
   1432 	de::MovePtr<TestCaseGroup>	partialDepthStencilAttachmentClearTests	(new TestCaseGroup(testCtx, "partial_clear_depth_stencil_attachment", "Clear Partial Depth/Stencil Attachment Tests"));
   1433 
   1434 	// Some formats are commented out due to the tcu::TextureFormat does not support them yet.
   1435 	const VkFormat		colorImageFormatsToTest[]	=
   1436 	{
   1437 		VK_FORMAT_R4G4_UNORM_PACK8,
   1438 		VK_FORMAT_R4G4B4A4_UNORM_PACK16,
   1439 		VK_FORMAT_B4G4R4A4_UNORM_PACK16,
   1440 		VK_FORMAT_R5G6B5_UNORM_PACK16,
   1441 		VK_FORMAT_B5G6R5_UNORM_PACK16,
   1442 		VK_FORMAT_R5G5B5A1_UNORM_PACK16,
   1443 		VK_FORMAT_B5G5R5A1_UNORM_PACK16,
   1444 		VK_FORMAT_A1R5G5B5_UNORM_PACK16,
   1445 		VK_FORMAT_R8_UNORM,
   1446 		VK_FORMAT_R8_SNORM,
   1447 		VK_FORMAT_R8_USCALED,
   1448 		VK_FORMAT_R8_SSCALED,
   1449 		VK_FORMAT_R8_UINT,
   1450 		VK_FORMAT_R8_SINT,
   1451 		VK_FORMAT_R8_SRGB,
   1452 		VK_FORMAT_R8G8_UNORM,
   1453 		VK_FORMAT_R8G8_SNORM,
   1454 		VK_FORMAT_R8G8_USCALED,
   1455 		VK_FORMAT_R8G8_SSCALED,
   1456 		VK_FORMAT_R8G8_UINT,
   1457 		VK_FORMAT_R8G8_SINT,
   1458 		VK_FORMAT_R8G8_SRGB,
   1459 		VK_FORMAT_R8G8B8_UNORM,
   1460 		VK_FORMAT_R8G8B8_SNORM,
   1461 		VK_FORMAT_R8G8B8_USCALED,
   1462 		VK_FORMAT_R8G8B8_SSCALED,
   1463 		VK_FORMAT_R8G8B8_UINT,
   1464 		VK_FORMAT_R8G8B8_SINT,
   1465 		VK_FORMAT_R8G8B8_SRGB,
   1466 		VK_FORMAT_B8G8R8_UNORM,
   1467 		VK_FORMAT_B8G8R8_SNORM,
   1468 		VK_FORMAT_B8G8R8_USCALED,
   1469 		VK_FORMAT_B8G8R8_SSCALED,
   1470 		VK_FORMAT_B8G8R8_UINT,
   1471 		VK_FORMAT_B8G8R8_SINT,
   1472 		VK_FORMAT_B8G8R8_SRGB,
   1473 		VK_FORMAT_R8G8B8A8_UNORM,
   1474 		VK_FORMAT_R8G8B8A8_SNORM,
   1475 		VK_FORMAT_R8G8B8A8_USCALED,
   1476 		VK_FORMAT_R8G8B8A8_SSCALED,
   1477 		VK_FORMAT_R8G8B8A8_UINT,
   1478 		VK_FORMAT_R8G8B8A8_SINT,
   1479 		VK_FORMAT_R8G8B8A8_SRGB,
   1480 		VK_FORMAT_B8G8R8A8_UNORM,
   1481 		VK_FORMAT_B8G8R8A8_SNORM,
   1482 		VK_FORMAT_B8G8R8A8_USCALED,
   1483 		VK_FORMAT_B8G8R8A8_SSCALED,
   1484 		VK_FORMAT_B8G8R8A8_UINT,
   1485 		VK_FORMAT_B8G8R8A8_SINT,
   1486 		VK_FORMAT_B8G8R8A8_SRGB,
   1487 		VK_FORMAT_A8B8G8R8_UNORM_PACK32,
   1488 		VK_FORMAT_A8B8G8R8_SNORM_PACK32,
   1489 		VK_FORMAT_A8B8G8R8_USCALED_PACK32,
   1490 		VK_FORMAT_A8B8G8R8_SSCALED_PACK32,
   1491 		VK_FORMAT_A8B8G8R8_UINT_PACK32,
   1492 		VK_FORMAT_A8B8G8R8_SINT_PACK32,
   1493 		VK_FORMAT_A8B8G8R8_SRGB_PACK32,
   1494 		VK_FORMAT_A2R10G10B10_UNORM_PACK32,
   1495 		VK_FORMAT_A2R10G10B10_SNORM_PACK32,
   1496 		VK_FORMAT_A2R10G10B10_USCALED_PACK32,
   1497 		VK_FORMAT_A2R10G10B10_SSCALED_PACK32,
   1498 		VK_FORMAT_A2R10G10B10_UINT_PACK32,
   1499 		VK_FORMAT_A2R10G10B10_SINT_PACK32,
   1500 		VK_FORMAT_A2B10G10R10_UNORM_PACK32,
   1501 		VK_FORMAT_A2B10G10R10_SNORM_PACK32,
   1502 		VK_FORMAT_A2B10G10R10_USCALED_PACK32,
   1503 		VK_FORMAT_A2B10G10R10_SSCALED_PACK32,
   1504 		VK_FORMAT_A2B10G10R10_UINT_PACK32,
   1505 		VK_FORMAT_A2B10G10R10_SINT_PACK32,
   1506 		VK_FORMAT_R16_UNORM,
   1507 		VK_FORMAT_R16_SNORM,
   1508 		VK_FORMAT_R16_USCALED,
   1509 		VK_FORMAT_R16_SSCALED,
   1510 		VK_FORMAT_R16_UINT,
   1511 		VK_FORMAT_R16_SINT,
   1512 		VK_FORMAT_R16_SFLOAT,
   1513 		VK_FORMAT_R16G16_UNORM,
   1514 		VK_FORMAT_R16G16_SNORM,
   1515 		VK_FORMAT_R16G16_USCALED,
   1516 		VK_FORMAT_R16G16_SSCALED,
   1517 		VK_FORMAT_R16G16_UINT,
   1518 		VK_FORMAT_R16G16_SINT,
   1519 		VK_FORMAT_R16G16_SFLOAT,
   1520 		VK_FORMAT_R16G16B16_UNORM,
   1521 		VK_FORMAT_R16G16B16_SNORM,
   1522 		VK_FORMAT_R16G16B16_USCALED,
   1523 		VK_FORMAT_R16G16B16_SSCALED,
   1524 		VK_FORMAT_R16G16B16_UINT,
   1525 		VK_FORMAT_R16G16B16_SINT,
   1526 		VK_FORMAT_R16G16B16_SFLOAT,
   1527 		VK_FORMAT_R16G16B16A16_UNORM,
   1528 		VK_FORMAT_R16G16B16A16_SNORM,
   1529 		VK_FORMAT_R16G16B16A16_USCALED,
   1530 		VK_FORMAT_R16G16B16A16_SSCALED,
   1531 		VK_FORMAT_R16G16B16A16_UINT,
   1532 		VK_FORMAT_R16G16B16A16_SINT,
   1533 		VK_FORMAT_R16G16B16A16_SFLOAT,
   1534 		VK_FORMAT_R32_UINT,
   1535 		VK_FORMAT_R32_SINT,
   1536 		VK_FORMAT_R32_SFLOAT,
   1537 		VK_FORMAT_R32G32_UINT,
   1538 		VK_FORMAT_R32G32_SINT,
   1539 		VK_FORMAT_R32G32_SFLOAT,
   1540 		VK_FORMAT_R32G32B32_UINT,
   1541 		VK_FORMAT_R32G32B32_SINT,
   1542 		VK_FORMAT_R32G32B32_SFLOAT,
   1543 		VK_FORMAT_R32G32B32A32_UINT,
   1544 		VK_FORMAT_R32G32B32A32_SINT,
   1545 		VK_FORMAT_R32G32B32A32_SFLOAT,
   1546 //		VK_FORMAT_R64_UINT,
   1547 //		VK_FORMAT_R64_SINT,
   1548 //		VK_FORMAT_R64_SFLOAT,
   1549 //		VK_FORMAT_R64G64_UINT,
   1550 //		VK_FORMAT_R64G64_SINT,
   1551 //		VK_FORMAT_R64G64_SFLOAT,
   1552 //		VK_FORMAT_R64G64B64_UINT,
   1553 //		VK_FORMAT_R64G64B64_SINT,
   1554 //		VK_FORMAT_R64G64B64_SFLOAT,
   1555 //		VK_FORMAT_R64G64B64A64_UINT,
   1556 //		VK_FORMAT_R64G64B64A64_SINT,
   1557 //		VK_FORMAT_R64G64B64A64_SFLOAT,
   1558 		VK_FORMAT_B10G11R11_UFLOAT_PACK32,
   1559 		VK_FORMAT_E5B9G9R9_UFLOAT_PACK32,
   1560 //		VK_FORMAT_BC1_RGB_UNORM_BLOCK,
   1561 //		VK_FORMAT_BC1_RGB_SRGB_BLOCK,
   1562 //		VK_FORMAT_BC1_RGBA_UNORM_BLOCK,
   1563 //		VK_FORMAT_BC1_RGBA_SRGB_BLOCK,
   1564 //		VK_FORMAT_BC2_UNORM_BLOCK,
   1565 //		VK_FORMAT_BC2_SRGB_BLOCK,
   1566 //		VK_FORMAT_BC3_UNORM_BLOCK,
   1567 //		VK_FORMAT_BC3_SRGB_BLOCK,
   1568 //		VK_FORMAT_BC4_UNORM_BLOCK,
   1569 //		VK_FORMAT_BC4_SNORM_BLOCK,
   1570 //		VK_FORMAT_BC5_UNORM_BLOCK,
   1571 //		VK_FORMAT_BC5_SNORM_BLOCK,
   1572 //		VK_FORMAT_BC6H_UFLOAT_BLOCK,
   1573 //		VK_FORMAT_BC6H_SFLOAT_BLOCK,
   1574 //		VK_FORMAT_BC7_UNORM_BLOCK,
   1575 //		VK_FORMAT_BC7_SRGB_BLOCK,
   1576 //		VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK,
   1577 //		VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK,
   1578 //		VK_FORMAT_ETC2_R8G8B8A1_UNORM_BLOCK,
   1579 //		VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK,
   1580 //		VK_FORMAT_ETC2_R8G8B8A8_UNORM_BLOCK,
   1581 //		VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK,
   1582 //		VK_FORMAT_EAC_R11_UNORM_BLOCK,
   1583 //		VK_FORMAT_EAC_R11_SNORM_BLOCK,
   1584 //		VK_FORMAT_EAC_R11G11_UNORM_BLOCK,
   1585 //		VK_FORMAT_EAC_R11G11_SNORM_BLOCK,
   1586 //		VK_FORMAT_ASTC_4x4_UNORM_BLOCK,
   1587 //		VK_FORMAT_ASTC_4x4_SRGB_BLOCK,
   1588 //		VK_FORMAT_ASTC_5x4_UNORM_BLOCK,
   1589 //		VK_FORMAT_ASTC_5x4_SRGB_BLOCK,
   1590 //		VK_FORMAT_ASTC_5x5_UNORM_BLOCK,
   1591 //		VK_FORMAT_ASTC_5x5_SRGB_BLOCK,
   1592 //		VK_FORMAT_ASTC_6x5_UNORM_BLOCK,
   1593 //		VK_FORMAT_ASTC_6x5_SRGB_BLOCK,
   1594 //		VK_FORMAT_ASTC_6x6_UNORM_BLOCK,
   1595 //		VK_FORMAT_ASTC_6x6_SRGB_BLOCK,
   1596 //		VK_FORMAT_ASTC_8x5_UNORM_BLOCK,
   1597 //		VK_FORMAT_ASTC_8x5_SRGB_BLOCK,
   1598 //		VK_FORMAT_ASTC_8x6_UNORM_BLOCK,
   1599 //		VK_FORMAT_ASTC_8x6_SRGB_BLOCK,
   1600 //		VK_FORMAT_ASTC_8x8_UNORM_BLOCK,
   1601 //		VK_FORMAT_ASTC_8x8_SRGB_BLOCK,
   1602 //		VK_FORMAT_ASTC_10x5_UNORM_BLOCK,
   1603 //		VK_FORMAT_ASTC_10x5_SRGB_BLOCK,
   1604 //		VK_FORMAT_ASTC_10x6_UNORM_BLOCK,
   1605 //		VK_FORMAT_ASTC_10x6_SRGB_BLOCK,
   1606 //		VK_FORMAT_ASTC_10x8_UNORM_BLOCK,
   1607 //		VK_FORMAT_ASTC_10x8_SRGB_BLOCK,
   1608 //		VK_FORMAT_ASTC_10x10_UNORM_BLOCK,
   1609 //		VK_FORMAT_ASTC_10x10_SRGB_BLOCK,
   1610 //		VK_FORMAT_ASTC_12x10_UNORM_BLOCK,
   1611 //		VK_FORMAT_ASTC_12x10_SRGB_BLOCK,
   1612 //		VK_FORMAT_ASTC_12x12_UNORM_BLOCK,
   1613 //		VK_FORMAT_ASTC_12x12_SRGB_BLOCK
   1614 	};
   1615 	const size_t	numOfColorImageFormatsToTest			= DE_LENGTH_OF_ARRAY(colorImageFormatsToTest);
   1616 
   1617 	const VkFormat	depthStencilImageFormatsToTest[]		=
   1618 	{
   1619 		VK_FORMAT_D16_UNORM,
   1620 		VK_FORMAT_X8_D24_UNORM_PACK32,
   1621 		VK_FORMAT_D32_SFLOAT,
   1622 		VK_FORMAT_S8_UINT,
   1623 		VK_FORMAT_D16_UNORM_S8_UINT,
   1624 		VK_FORMAT_D24_UNORM_S8_UINT,
   1625 		VK_FORMAT_D32_SFLOAT_S8_UINT
   1626 	};
   1627 	const size_t	numOfDepthStencilImageFormatsToTest		= DE_LENGTH_OF_ARRAY(depthStencilImageFormatsToTest);
   1628 
   1629 	struct ImageLayerParams
   1630 	{
   1631 		deUint32		imageLayerCount;
   1632 		LayerRange		imageViewRange;
   1633 		LayerRange		clearLayerRange;
   1634 		const char*		testName;
   1635 	};
   1636 	const ImageLayerParams imageLayerParamsToTest[] =
   1637 	{
   1638 		{
   1639 			1u,					// imageLayerCount
   1640 			{0u, 1u},			// imageViewRange
   1641 			{0u, 1u},			// clearLayerRange
   1642 			DE_NULL				// testName
   1643 		},
   1644 		{
   1645 			16u,				// imageLayerCount
   1646 			{3u, 12u},			// imageViewRange
   1647 			{2u, 5u},			// clearLayerRange
   1648 			"multiple_layers"	// testName
   1649 		},
   1650 	};
   1651 
   1652 	const size_t	numOfImageLayerParamsToTest				= DE_LENGTH_OF_ARRAY(imageLayerParamsToTest);
   1653 
   1654 	// Clear color image
   1655 	{
   1656 		const VkImageType			imageTypesToTest[]		=
   1657 		{
   1658 			VK_IMAGE_TYPE_1D,
   1659 			VK_IMAGE_TYPE_2D,
   1660 			VK_IMAGE_TYPE_3D
   1661 		};
   1662 		const size_t				numOfImageTypesToTest	= DE_LENGTH_OF_ARRAY(imageTypesToTest);
   1663 
   1664 		const VkExtent3D			imageDimensionsByType[]	=
   1665 		{
   1666 			{ 256, 1, 1},
   1667 			{ 256, 256, 1},
   1668 			{ 256, 256, 16}
   1669 		};
   1670 
   1671 		for (size_t	imageTypeIndex = 0; imageTypeIndex < numOfImageTypesToTest; ++imageTypeIndex)
   1672 		for (size_t imageFormatIndex = 0; imageFormatIndex < numOfColorImageFormatsToTest; ++imageFormatIndex)
   1673 		for (size_t imageLayerParamsIndex = 0; imageLayerParamsIndex < numOfImageLayerParamsToTest; ++imageLayerParamsIndex)
   1674 		{
   1675 
   1676 			if (imageLayerParamsToTest[imageLayerParamsIndex].imageLayerCount > 1u && imageTypesToTest[imageTypeIndex] == VK_IMAGE_TYPE_3D)
   1677 			{
   1678 				// 3D ARRAY images are not supported
   1679 				continue;
   1680 			}
   1681 
   1682 			const VkFormat		format		= colorImageFormatsToTest[imageFormatIndex];
   1683 			const TestParams	testParams	=
   1684 			{
   1685 				false,																// bool				useSingleMipLevel;
   1686 				imageTypesToTest[imageTypeIndex],									// VkImageType		imageType;
   1687 				format,																// VkFormat			imageFormat;
   1688 				imageDimensionsByType[imageTypeIndex],								// VkExtent3D		imageExtent;
   1689 				imageLayerParamsToTest[imageLayerParamsIndex].imageLayerCount,		// deUint32         imageLayerCount;
   1690 				{
   1691 					0u,
   1692 					imageLayerParamsToTest[imageLayerParamsIndex].imageLayerCount
   1693 				},																	// LayerRange		imageViewLayerRange;
   1694 				makeClearColorValue(format, 0.2f, 0.1f, 0.7f, 0.8f),				// VkClearValue		initValue;
   1695 				{
   1696 					makeClearColorValue(format, 0.1f, 0.5f, 0.3f, 0.9f),				// VkClearValue		clearValue[0];
   1697 					makeClearColorValue(format, 0.3f, 0.6f, 0.2f, 0.7f),				// VkClearValue		clearValue[1];
   1698 				},
   1699 				imageLayerParamsToTest[imageLayerParamsIndex].clearLayerRange,		// LayerRange       clearLayerRange;
   1700 				allocationKind														// AllocationKind	allocationKind;
   1701 			};
   1702 
   1703 			std::ostringstream	testCaseName;
   1704 			testCaseName << getImageTypeCaseName(testParams.imageType) << "_" << getFormatCaseName(format);
   1705 			if (imageLayerParamsToTest[imageLayerParamsIndex].testName != DE_NULL)
   1706 				testCaseName << "_" << imageLayerParamsToTest[imageLayerParamsIndex].testName;
   1707 
   1708 			colorImageClearTests->addChild(new InstanceFactory1<ClearColorImageTestInstance, TestParams>(testCtx, NODETYPE_SELF_VALIDATE, testCaseName.str(), "Clear Color Image", testParams));
   1709 		}
   1710 
   1711 		imageClearingTests->addChild(colorImageClearTests.release());
   1712 	}
   1713 
   1714 	// Clear depth/stencil image
   1715 	{
   1716 		for (size_t imageFormatIndex = 0; imageFormatIndex < numOfDepthStencilImageFormatsToTest; ++imageFormatIndex)
   1717 		for (size_t imageLayerParamsIndex = 0; imageLayerParamsIndex < numOfImageLayerParamsToTest; ++imageLayerParamsIndex)
   1718 		{
   1719 			const TestParams testParams =
   1720 			{
   1721 				true,																// bool				useSingleMipLevel;
   1722 				VK_IMAGE_TYPE_2D,													// VkImageType		imageType;
   1723 				depthStencilImageFormatsToTest[imageFormatIndex],					// VkFormat			format;
   1724 				{ 256, 256, 1 },													// VkExtent3D		extent;
   1725 				imageLayerParamsToTest[imageLayerParamsIndex].imageLayerCount,		// deUint32         imageLayerCount;
   1726 				{
   1727 					0u,
   1728 					imageLayerParamsToTest[imageLayerParamsIndex].imageLayerCount
   1729 				},																	// LayerRange		imageViewLayerRange;
   1730 				makeClearValueDepthStencil(0.5f, 0x03),								// VkClearValue		initValue
   1731 				{
   1732 					makeClearValueDepthStencil(0.1f, 0x06),								// VkClearValue		clearValue[0];
   1733 					makeClearValueDepthStencil(0.3f, 0x04),								// VkClearValue		clearValue[1];
   1734 				},
   1735 				imageLayerParamsToTest[imageLayerParamsIndex].clearLayerRange,		// LayerRange       clearLayerRange;
   1736 				allocationKind														// AllocationKind	allocationKind;
   1737 			};
   1738 
   1739 			std::ostringstream	testCaseName;
   1740 			testCaseName << getImageTypeCaseName(testParams.imageType) << "_" << getFormatCaseName(testParams.imageFormat);
   1741 			if (imageLayerParamsToTest[imageLayerParamsIndex].testName != DE_NULL)
   1742 				testCaseName << "_" << imageLayerParamsToTest[imageLayerParamsIndex].testName;
   1743 
   1744 			depthStencilImageClearTests->addChild(new InstanceFactory1<ClearDepthStencilImageTestInstance, TestParams>(testCtx, NODETYPE_SELF_VALIDATE, testCaseName.str(), "Clear Depth/Stencil Image", testParams));
   1745 		}
   1746 
   1747 		imageClearingTests->addChild(depthStencilImageClearTests.release());
   1748 	}
   1749 
   1750 	// Clear color attachment
   1751 	{
   1752 		for (size_t imageFormatIndex = 0; imageFormatIndex < numOfColorImageFormatsToTest; ++imageFormatIndex)
   1753 		for (size_t imageLayerParamsIndex = 0; imageLayerParamsIndex < numOfImageLayerParamsToTest; ++imageLayerParamsIndex)
   1754 		{
   1755 			const VkFormat		format		= colorImageFormatsToTest[imageFormatIndex];
   1756 
   1757 			const TestParams	testParams =
   1758 			{
   1759 				true,															// bool				useSingleMipLevel;
   1760 				VK_IMAGE_TYPE_2D,												// VkImageType		imageType;
   1761 				format,															// VkFormat			format;
   1762 				{ 256, 256, 1 },												// VkExtent3D		extent;
   1763 				imageLayerParamsToTest[imageLayerParamsIndex].imageLayerCount,	// deUint32         imageLayerCount;
   1764 				imageLayerParamsToTest[imageLayerParamsIndex].imageViewRange,	// LayerRange		imageViewLayerRange;
   1765 				makeClearColorValue(format, 0.2f, 0.1f, 0.7f, 0.8f),			// VkClearValue		initValue
   1766 				{
   1767 					makeClearColorValue(format, 0.1f, 0.5f, 0.3f, 0.9f),			// VkClearValue		clearValue[0];
   1768 					makeClearColorValue(format, 0.3f, 0.6f, 0.2f, 0.7f),			// VkClearValue		clearValue[1];
   1769 				},
   1770 				imageLayerParamsToTest[imageLayerParamsIndex].clearLayerRange,	// LayerRange       clearLayerRange;
   1771 				allocationKind													// AllocationKind	allocationKind;
   1772 			};
   1773 
   1774 			std::ostringstream	testCaseName;
   1775 			testCaseName << getImageTypeCaseName(testParams.imageType) << "_" << getFormatCaseName(format);
   1776 			if (imageLayerParamsToTest[imageLayerParamsIndex].testName != DE_NULL)
   1777 				testCaseName << "_" << imageLayerParamsToTest[imageLayerParamsIndex].testName;
   1778 
   1779 			colorAttachmentClearTests->addChild(new InstanceFactory1<ClearAttachmentTestInstance, TestParams>(testCtx, NODETYPE_SELF_VALIDATE, testCaseName.str(), "Clear Color Attachment", testParams));
   1780 			partialColorAttachmentClearTests->addChild(new InstanceFactory1<PartialClearAttachmentTestInstance, TestParams>(testCtx, NODETYPE_SELF_VALIDATE, testCaseName.str(), "Partial Clear Color Attachment", testParams));
   1781 		}
   1782 
   1783 		imageClearingTests->addChild(colorAttachmentClearTests.release());
   1784 		imageClearingTests->addChild(partialColorAttachmentClearTests.release());
   1785 	}
   1786 
   1787 	// Clear depth/stencil attachment
   1788 	{
   1789 		for (size_t imageFormatIndex = 0; imageFormatIndex < numOfDepthStencilImageFormatsToTest; ++imageFormatIndex)
   1790 		for (size_t imageLayerParamsIndex = 0; imageLayerParamsIndex < numOfImageLayerParamsToTest; ++imageLayerParamsIndex)
   1791 		{
   1792 			const TestParams testParams =
   1793 			{
   1794 				true,															// bool				useSingleMipLevel;
   1795 				VK_IMAGE_TYPE_2D,												// VkImageType		imageType;
   1796 				depthStencilImageFormatsToTest[imageFormatIndex],				// VkFormat			format;
   1797 				{ 256, 256, 1 },												// VkExtent3D		extent;
   1798 				imageLayerParamsToTest[imageLayerParamsIndex].imageLayerCount,	// deUint32         imageLayerCount;
   1799 				imageLayerParamsToTest[imageLayerParamsIndex].imageViewRange,	// LayerRange		imageViewLayerRange;
   1800 				makeClearValueDepthStencil(0.5f, 0x03),							// VkClearValue		initValue
   1801 				{
   1802 					makeClearValueDepthStencil(0.1f, 0x06),							// VkClearValue		clearValue[0];
   1803 					makeClearValueDepthStencil(0.3f, 0x04),							// VkClearValue		clearValue[1];
   1804 				},
   1805 				imageLayerParamsToTest[imageLayerParamsIndex].clearLayerRange,	// LayerRange       clearLayerRange;
   1806 				allocationKind													// AllocationKind	allocationKind;
   1807 			};
   1808 
   1809 			std::ostringstream	testCaseName;
   1810 			testCaseName << getImageTypeCaseName(testParams.imageType) << "_" << getFormatCaseName(testParams.imageFormat);
   1811 			if (imageLayerParamsToTest[imageLayerParamsIndex].testName != DE_NULL)
   1812 				testCaseName << "_" << imageLayerParamsToTest[imageLayerParamsIndex].testName;
   1813 
   1814 			depthStencilAttachmentClearTests->addChild(new InstanceFactory1<ClearAttachmentTestInstance, TestParams>(testCtx, NODETYPE_SELF_VALIDATE, testCaseName.str(), "Clear Depth/Stencil Attachment", testParams));
   1815 			partialDepthStencilAttachmentClearTests->addChild(new InstanceFactory1<PartialClearAttachmentTestInstance, TestParams>(testCtx, NODETYPE_SELF_VALIDATE, testCaseName.str(), "Parital Clear Depth/Stencil Attachment", testParams));
   1816 		}
   1817 
   1818 		imageClearingTests->addChild(depthStencilAttachmentClearTests.release());
   1819 		imageClearingTests->addChild(partialDepthStencilAttachmentClearTests.release());
   1820 	}
   1821 
   1822 	return imageClearingTests;
   1823 }
   1824 
   1825 void createCoreImageClearingTests (tcu::TestCaseGroup* group)
   1826 {
   1827 	createImageClearingTestsCommon(group->getTestContext(), group, ALLOCATION_KIND_SUBALLOCATED);
   1828 }
   1829 
   1830 void createDedicatedAllocationImageClearingTests (tcu::TestCaseGroup* group)
   1831 {
   1832 	createImageClearingTestsCommon(group->getTestContext(), group, ALLOCATION_KIND_DEDICATED);
   1833 }
   1834 
   1835 } // anonymous
   1836 
   1837 TestCaseGroup* createImageClearingTests (TestContext& testCtx)
   1838 {
   1839 	de::MovePtr<TestCaseGroup>	imageClearingTests	(new TestCaseGroup(testCtx, "image_clearing", "Image Clearing Tests"));
   1840 
   1841 	imageClearingTests->addChild(createTestGroup(testCtx, "core",					"Core Image Clearing Tests",							createCoreImageClearingTests));
   1842 	imageClearingTests->addChild(createTestGroup(testCtx, "dedicated_allocation",	"Image Clearing Tests For Dedicated Memory Allocation",	createDedicatedAllocationImageClearingTests));
   1843 
   1844 	return imageClearingTests.release();
   1845 }
   1846 
   1847 } // api
   1848 } // vkt
   1849