• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*-------------------------------------------------------------------------
2  * Vulkan CTS Framework
3  * --------------------
4  *
5  * Copyright (c) 2015 The Khronos Group Inc.
6  * Copyright (c) 2015 Imagination Technologies Ltd.
7  * Copyright (c) 2015 Google Inc.
8  *
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
12  *
13  *      http://www.apache.org/licenses/LICENSE-2.0
14  *
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.
20  *
21  *//*!
22  * \file
23  * \brief Utilities for images.
24  *//*--------------------------------------------------------------------*/
25 
26 #include "vkImageUtil.hpp"
27 #include "vkRefUtil.hpp"
28 #include "vkQueryUtil.hpp"
29 #include "vkTypeUtil.hpp"
30 #include "vkCmdUtil.hpp"
31 #include "tcuTextureUtil.hpp"
32 #include "deMath.h"
33 
34 namespace vk
35 {
36 
isFloatFormat(VkFormat format)37 bool isFloatFormat (VkFormat format)
38 {
39 	return tcu::getTextureChannelClass(mapVkFormat(format).type) == tcu::TEXTURECHANNELCLASS_FLOATING_POINT;
40 }
41 
isUnormFormat(VkFormat format)42 bool isUnormFormat (VkFormat format)
43 {
44 	return tcu::getTextureChannelClass(mapVkFormat(format).type) == tcu::TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT;
45 }
46 
isSnormFormat(VkFormat format)47 bool isSnormFormat (VkFormat format)
48 {
49 	return tcu::getTextureChannelClass(mapVkFormat(format).type) == tcu::TEXTURECHANNELCLASS_SIGNED_FIXED_POINT;
50 }
51 
isIntFormat(VkFormat format)52 bool isIntFormat (VkFormat format)
53 {
54 	return tcu::getTextureChannelClass(mapVkFormat(format).type) == tcu::TEXTURECHANNELCLASS_SIGNED_INTEGER;
55 }
56 
isUintFormat(VkFormat format)57 bool isUintFormat (VkFormat format)
58 {
59 	return tcu::getTextureChannelClass(mapVkFormat(format).type) == tcu::TEXTURECHANNELCLASS_UNSIGNED_INTEGER;
60 }
61 
isDepthStencilFormat(VkFormat format)62 bool isDepthStencilFormat (VkFormat format)
63 {
64 	if (isCompressedFormat(format))
65 		return false;
66 
67 	if (isYCbCrFormat(format))
68 		return false;
69 
70 	const tcu::TextureFormat tcuFormat = mapVkFormat(format);
71 	return tcuFormat.order == tcu::TextureFormat::D || tcuFormat.order == tcu::TextureFormat::S || tcuFormat.order == tcu::TextureFormat::DS;
72 }
73 
isSrgbFormat(VkFormat format)74 bool isSrgbFormat (VkFormat format)
75 {
76 	switch (mapVkFormat(format).order)
77 	{
78 		case tcu::TextureFormat::sR:
79 		case tcu::TextureFormat::sRG:
80 		case tcu::TextureFormat::sRGB:
81 		case tcu::TextureFormat::sRGBA:
82 		case tcu::TextureFormat::sBGR:
83 		case tcu::TextureFormat::sBGRA:
84 			return true;
85 
86 		default:
87 			return false;
88 	}
89 }
90 
isUfloatFormat(VkFormat format)91 bool isUfloatFormat (VkFormat format)
92 {
93 	DE_STATIC_ASSERT(VK_CORE_FORMAT_LAST == 185);
94 
95 	switch (format)
96 	{
97 		case VK_FORMAT_B10G11R11_UFLOAT_PACK32:
98 		case VK_FORMAT_E5B9G9R9_UFLOAT_PACK32:
99 		case VK_FORMAT_BC6H_UFLOAT_BLOCK:
100 			return true;
101 
102 		default:
103 			return false;
104 	}
105 }
106 
isSfloatFormat(VkFormat format)107 bool isSfloatFormat (VkFormat format)
108 {
109 	DE_STATIC_ASSERT(VK_CORE_FORMAT_LAST == 185);
110 
111 	switch (format)
112 	{
113 		case VK_FORMAT_R16_SFLOAT:
114 		case VK_FORMAT_R16G16_SFLOAT:
115 		case VK_FORMAT_R16G16B16_SFLOAT:
116 		case VK_FORMAT_R16G16B16A16_SFLOAT:
117 		case VK_FORMAT_R32_SFLOAT:
118 		case VK_FORMAT_R32G32_SFLOAT:
119 		case VK_FORMAT_R32G32B32_SFLOAT:
120 		case VK_FORMAT_R32G32B32A32_SFLOAT:
121 		case VK_FORMAT_R64_SFLOAT:
122 		case VK_FORMAT_R64G64_SFLOAT:
123 		case VK_FORMAT_R64G64B64_SFLOAT:
124 		case VK_FORMAT_R64G64B64A64_SFLOAT:
125 		case VK_FORMAT_D32_SFLOAT:
126 		case VK_FORMAT_BC6H_SFLOAT_BLOCK:
127 			return true;
128 
129 		default:
130 			return false;
131 	}
132 }
133 
isCompressedFormat(VkFormat format)134 bool isCompressedFormat (VkFormat format)
135 {
136 	// update this mapping if VkFormat changes
137 	DE_STATIC_ASSERT(VK_CORE_FORMAT_LAST == 185);
138 
139 	switch (format)
140 	{
141 		case VK_FORMAT_BC1_RGB_UNORM_BLOCK:
142 		case VK_FORMAT_BC1_RGB_SRGB_BLOCK:
143 		case VK_FORMAT_BC1_RGBA_UNORM_BLOCK:
144 		case VK_FORMAT_BC1_RGBA_SRGB_BLOCK:
145 		case VK_FORMAT_BC2_UNORM_BLOCK:
146 		case VK_FORMAT_BC2_SRGB_BLOCK:
147 		case VK_FORMAT_BC3_UNORM_BLOCK:
148 		case VK_FORMAT_BC3_SRGB_BLOCK:
149 		case VK_FORMAT_BC4_UNORM_BLOCK:
150 		case VK_FORMAT_BC4_SNORM_BLOCK:
151 		case VK_FORMAT_BC5_UNORM_BLOCK:
152 		case VK_FORMAT_BC5_SNORM_BLOCK:
153 		case VK_FORMAT_BC6H_UFLOAT_BLOCK:
154 		case VK_FORMAT_BC6H_SFLOAT_BLOCK:
155 		case VK_FORMAT_BC7_UNORM_BLOCK:
156 		case VK_FORMAT_BC7_SRGB_BLOCK:
157 		case VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK:
158 		case VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK:
159 		case VK_FORMAT_ETC2_R8G8B8A1_UNORM_BLOCK:
160 		case VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK:
161 		case VK_FORMAT_ETC2_R8G8B8A8_UNORM_BLOCK:
162 		case VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK:
163 		case VK_FORMAT_EAC_R11_UNORM_BLOCK:
164 		case VK_FORMAT_EAC_R11_SNORM_BLOCK:
165 		case VK_FORMAT_EAC_R11G11_UNORM_BLOCK:
166 		case VK_FORMAT_EAC_R11G11_SNORM_BLOCK:
167 		case VK_FORMAT_ASTC_4x4_UNORM_BLOCK:
168 		case VK_FORMAT_ASTC_4x4_SRGB_BLOCK:
169 		case VK_FORMAT_ASTC_5x4_UNORM_BLOCK:
170 		case VK_FORMAT_ASTC_5x4_SRGB_BLOCK:
171 		case VK_FORMAT_ASTC_5x5_UNORM_BLOCK:
172 		case VK_FORMAT_ASTC_5x5_SRGB_BLOCK:
173 		case VK_FORMAT_ASTC_6x5_UNORM_BLOCK:
174 		case VK_FORMAT_ASTC_6x5_SRGB_BLOCK:
175 		case VK_FORMAT_ASTC_6x6_UNORM_BLOCK:
176 		case VK_FORMAT_ASTC_6x6_SRGB_BLOCK:
177 		case VK_FORMAT_ASTC_8x5_UNORM_BLOCK:
178 		case VK_FORMAT_ASTC_8x5_SRGB_BLOCK:
179 		case VK_FORMAT_ASTC_8x6_UNORM_BLOCK:
180 		case VK_FORMAT_ASTC_8x6_SRGB_BLOCK:
181 		case VK_FORMAT_ASTC_8x8_UNORM_BLOCK:
182 		case VK_FORMAT_ASTC_8x8_SRGB_BLOCK:
183 		case VK_FORMAT_ASTC_10x5_UNORM_BLOCK:
184 		case VK_FORMAT_ASTC_10x5_SRGB_BLOCK:
185 		case VK_FORMAT_ASTC_10x6_UNORM_BLOCK:
186 		case VK_FORMAT_ASTC_10x6_SRGB_BLOCK:
187 		case VK_FORMAT_ASTC_10x8_UNORM_BLOCK:
188 		case VK_FORMAT_ASTC_10x8_SRGB_BLOCK:
189 		case VK_FORMAT_ASTC_10x10_UNORM_BLOCK:
190 		case VK_FORMAT_ASTC_10x10_SRGB_BLOCK:
191 		case VK_FORMAT_ASTC_12x10_UNORM_BLOCK:
192 		case VK_FORMAT_ASTC_12x10_SRGB_BLOCK:
193 		case VK_FORMAT_ASTC_12x12_UNORM_BLOCK:
194 		case VK_FORMAT_ASTC_12x12_SRGB_BLOCK:
195 			return true;
196 
197 		default:
198 			return false;
199 	}
200 }
201 
isYCbCrFormat(VkFormat format)202 bool isYCbCrFormat (VkFormat format)
203 {
204 	switch (format)
205 	{
206 		case VK_FORMAT_G8B8G8R8_422_UNORM_KHR:
207 		case VK_FORMAT_B8G8R8G8_422_UNORM_KHR:
208 		case VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM_KHR:
209 		case VK_FORMAT_G8_B8R8_2PLANE_420_UNORM_KHR:
210 		case VK_FORMAT_G8_B8_R8_3PLANE_422_UNORM_KHR:
211 		case VK_FORMAT_G8_B8R8_2PLANE_422_UNORM_KHR:
212 		case VK_FORMAT_G8_B8_R8_3PLANE_444_UNORM_KHR:
213 		case VK_FORMAT_R10X6_UNORM_PACK16_KHR:
214 		case VK_FORMAT_R10X6G10X6_UNORM_2PACK16_KHR:
215 		case VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16_KHR:
216 		case VK_FORMAT_G10X6B10X6G10X6R10X6_422_UNORM_4PACK16_KHR:
217 		case VK_FORMAT_B10X6G10X6R10X6G10X6_422_UNORM_4PACK16_KHR:
218 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_420_UNORM_3PACK16_KHR:
219 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_420_UNORM_3PACK16_KHR:
220 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_422_UNORM_3PACK16_KHR:
221 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_422_UNORM_3PACK16_KHR:
222 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_444_UNORM_3PACK16_KHR:
223 		case VK_FORMAT_R12X4_UNORM_PACK16_KHR:
224 		case VK_FORMAT_R12X4G12X4_UNORM_2PACK16_KHR:
225 		case VK_FORMAT_R12X4G12X4B12X4A12X4_UNORM_4PACK16_KHR:
226 		case VK_FORMAT_G12X4B12X4G12X4R12X4_422_UNORM_4PACK16_KHR:
227 		case VK_FORMAT_B12X4G12X4R12X4G12X4_422_UNORM_4PACK16_KHR:
228 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_420_UNORM_3PACK16_KHR:
229 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_420_UNORM_3PACK16_KHR:
230 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_422_UNORM_3PACK16_KHR:
231 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_422_UNORM_3PACK16_KHR:
232 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_444_UNORM_3PACK16_KHR:
233 		case VK_FORMAT_G16B16G16R16_422_UNORM_KHR:
234 		case VK_FORMAT_B16G16R16G16_422_UNORM_KHR:
235 		case VK_FORMAT_G16_B16_R16_3PLANE_420_UNORM_KHR:
236 		case VK_FORMAT_G16_B16R16_2PLANE_420_UNORM_KHR:
237 		case VK_FORMAT_G16_B16_R16_3PLANE_422_UNORM_KHR:
238 		case VK_FORMAT_G16_B16R16_2PLANE_422_UNORM_KHR:
239 		case VK_FORMAT_G16_B16_R16_3PLANE_444_UNORM_KHR:
240 			return true;
241 
242 		default:
243 			return false;
244 	}
245 }
246 
isYCbCr420Format(VkFormat format)247 bool isYCbCr420Format (VkFormat format)
248 {
249 	switch (format)
250 	{
251 		case VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM_KHR:
252 		case VK_FORMAT_G8_B8R8_2PLANE_420_UNORM_KHR:
253 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_420_UNORM_3PACK16_KHR:
254 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_420_UNORM_3PACK16_KHR:
255 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_420_UNORM_3PACK16_KHR:
256 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_420_UNORM_3PACK16_KHR:
257 		case VK_FORMAT_G16_B16_R16_3PLANE_420_UNORM_KHR:
258 		case VK_FORMAT_G16_B16R16_2PLANE_420_UNORM_KHR:
259 			return true;
260 
261 		default:
262 			return false;
263 	}
264 }
265 
isYCbCr422Format(VkFormat format)266 bool isYCbCr422Format (VkFormat format)
267 {
268 	switch (format)
269 	{
270 		case VK_FORMAT_G8B8G8R8_422_UNORM_KHR:
271 		case VK_FORMAT_B8G8R8G8_422_UNORM_KHR:
272 		case VK_FORMAT_G8_B8_R8_3PLANE_422_UNORM_KHR:
273 		case VK_FORMAT_G8_B8R8_2PLANE_422_UNORM_KHR:
274 		case VK_FORMAT_G10X6B10X6G10X6R10X6_422_UNORM_4PACK16_KHR:
275 		case VK_FORMAT_B10X6G10X6R10X6G10X6_422_UNORM_4PACK16_KHR:
276 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_422_UNORM_3PACK16_KHR:
277 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_422_UNORM_3PACK16_KHR:
278 		case VK_FORMAT_G12X4B12X4G12X4R12X4_422_UNORM_4PACK16_KHR:
279 		case VK_FORMAT_B12X4G12X4R12X4G12X4_422_UNORM_4PACK16_KHR:
280 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_422_UNORM_3PACK16_KHR:
281 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_422_UNORM_3PACK16_KHR:
282 		case VK_FORMAT_G16B16G16R16_422_UNORM_KHR:
283 		case VK_FORMAT_B16G16R16G16_422_UNORM_KHR:
284 		case VK_FORMAT_G16_B16_R16_3PLANE_422_UNORM_KHR:
285 		case VK_FORMAT_G16_B16R16_2PLANE_422_UNORM_KHR:
286 			return true;
287 
288 		default:
289 			return false;
290 	}
291 }
292 
getYCbCrPlanarFormatDescription(VkFormat format)293 const PlanarFormatDescription& getYCbCrPlanarFormatDescription (VkFormat format)
294 {
295 	using tcu::TextureFormat;
296 
297 	const deUint32	chanR			= PlanarFormatDescription::CHANNEL_R;
298 	const deUint32	chanG			= PlanarFormatDescription::CHANNEL_G;
299 	const deUint32	chanB			= PlanarFormatDescription::CHANNEL_B;
300 	const deUint32	chanA			= PlanarFormatDescription::CHANNEL_A;
301 
302 	const deUint8	unorm			= (deUint8)tcu::TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT;
303 
304 	static const PlanarFormatDescription s_formatInfo[] =
305 	{
306 		// VK_FORMAT_G8B8G8R8_422_UNORM_KHR
307 		{
308 			1, // planes
309 			chanR|chanG|chanB,
310 			2,1,
311 			{
312 			//		Size	WDiv	HDiv	planeCompatibleFormat
313 				{	4,		1,		1,		VK_FORMAT_G8B8G8R8_422_UNORM_KHR	},
314 				{	0,		0,		0,		VK_FORMAT_UNDEFINED	},
315 				{	0,		0,		0,		VK_FORMAT_UNDEFINED	},
316 			},
317 			{
318 			//		Plane	Type	Offs	Size	Stride
319 				{	0,		unorm,	24,		8,		4 },	// R
320 				{	0,		unorm,	0,		8,		2 },	// G
321 				{	0,		unorm,	8,		8,		4 },	// B
322 				{ 0, 0, 0, 0, 0 }
323 			}
324 		},
325 		// VK_FORMAT_B8G8R8G8_422_UNORM_KHR
326 		{
327 			1, // planes
328 			chanR|chanG|chanB,
329 			2,1,
330 			{
331 			//		Size	WDiv	HDiv	planeCompatibleFormat
332 				{	4,		1,		1,		VK_FORMAT_B8G8R8G8_422_UNORM_KHR },
333 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
334 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
335 			},
336 			{
337 			//		Plane	Type	Offs	Size	Stride
338 				{	0,		unorm,	16,		8,		4 },	// R
339 				{	0,		unorm,	8,		8,		2 },	// G
340 				{	0,		unorm,	0,		8,		4 },	// B
341 				{ 0, 0, 0, 0, 0 }
342 			}
343 		},
344 		// VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM_KHR
345 		{
346 			3, // planes
347 			chanR|chanG|chanB,
348 			1,1,
349 			{
350 			//		Size	WDiv	HDiv	planeCompatibleFormat
351 				{	1,		1,		1,		VK_FORMAT_R8_UNORM },
352 				{	1,		2,		2,		VK_FORMAT_R8_UNORM },
353 				{	1,		2,		2,		VK_FORMAT_R8_UNORM },
354 			},
355 			{
356 			//		Plane	Type	Offs	Size	Stride
357 				{	2,		unorm,	0,		8,		1 },	// R
358 				{	0,		unorm,	0,		8,		1 },	// G
359 				{	1,		unorm,	0,		8,		1 },	// B
360 				{ 0, 0, 0, 0, 0 }
361 			}
362 		},
363 		// VK_FORMAT_G8_B8R8_2PLANE_420_UNORM_KHR
364 		{
365 			2, // planes
366 			chanR|chanG|chanB,
367 			1,1,
368 			{
369 			//		Size	WDiv	HDiv	planeCompatibleFormat
370 				{	1,		1,		1,		VK_FORMAT_R8_UNORM },
371 				{	2,		2,		2,		VK_FORMAT_R8G8_UNORM },
372 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
373 			},
374 			{
375 			//		Plane	Type	Offs	Size	Stride
376 				{	1,		unorm,	8,		8,		2 },	// R
377 				{	0,		unorm,	0,		8,		1 },	// G
378 				{	1,		unorm,	0,		8,		2 },	// B
379 				{ 0, 0, 0, 0, 0 }
380 			}
381 		},
382 		// VK_FORMAT_G8_B8_R8_3PLANE_422_UNORM_KHR
383 		{
384 			3, // planes
385 			chanR|chanG|chanB,
386 			1,1,
387 			{
388 			//		Size	WDiv	HDiv	planeCompatibleFormat
389 				{	1,		1,		1,		VK_FORMAT_R8_UNORM },
390 				{	1,		2,		1,		VK_FORMAT_R8_UNORM },
391 				{	1,		2,		1,		VK_FORMAT_R8_UNORM },
392 			},
393 			{
394 			//		Plane	Type	Offs	Size	Stride
395 				{	2,		unorm,	0,		8,		1 },	// R
396 				{	0,		unorm,	0,		8,		1 },	// G
397 				{	1,		unorm,	0,		8,		1 },	// B
398 				{ 0, 0, 0, 0, 0 }
399 			}
400 		},
401 		// VK_FORMAT_G8_B8R8_2PLANE_422_UNORM_KHR
402 		{
403 			2, // planes
404 			chanR|chanG|chanB,
405 			1,1,
406 			{
407 			//		Size	WDiv	HDiv	planeCompatibleFormat
408 				{	1,		1,		1,		VK_FORMAT_R8_UNORM },
409 				{	2,		2,		1,		VK_FORMAT_R8G8_UNORM },
410 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
411 			},
412 			{
413 			//		Plane	Type	Offs	Size	Stride
414 				{	1,		unorm,	8,		8,		2 },	// R
415 				{	0,		unorm,	0,		8,		1 },	// G
416 				{	1,		unorm,	0,		8,		2 },	// B
417 				{ 0, 0, 0, 0, 0 }
418 			}
419 		},
420 		// VK_FORMAT_G8_B8_R8_3PLANE_444_UNORM_KHR
421 		{
422 			3, // planes
423 			chanR|chanG|chanB,
424 			1,1,
425 			{
426 			//		Size	WDiv	HDiv	planeCompatibleFormat
427 				{	1,		1,		1,		VK_FORMAT_R8_UNORM },
428 				{	1,		1,		1,		VK_FORMAT_R8_UNORM },
429 				{	1,		1,		1,		VK_FORMAT_R8_UNORM },
430 			},
431 			{
432 			//		Plane	Type	Offs	Size	Stride
433 				{	2,		unorm,	0,		8,		1 },	// R
434 				{	0,		unorm,	0,		8,		1 },	// G
435 				{	1,		unorm,	0,		8,		1 },	// B
436 				{ 0, 0, 0, 0, 0 }
437 			}
438 		},
439 		// VK_FORMAT_R10X6_UNORM_PACK16_KHR
440 		{
441 			1, // planes
442 			chanR,
443 			1,1,
444 			{
445 			//		Size	WDiv	HDiv	planeCompatibleFormat
446 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16_KHR },
447 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
448 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
449 			},
450 			{
451 			//		Plane	Type	Offs	Size	Stride
452 				{	0,		unorm,	6,		10,		2 },	// R
453 				{ 0, 0, 0, 0, 0 },
454 				{ 0, 0, 0, 0, 0 },
455 				{ 0, 0, 0, 0, 0 },
456 			}
457 		},
458 		// VK_FORMAT_R10X6G10X6_UNORM_2PACK16_KHR
459 		{
460 			1, // planes
461 			chanR|chanG,
462 			1,1,
463 			{
464 			//		Size	WDiv	HDiv	planeCompatibleFormat
465 				{	4,		1,		1,		VK_FORMAT_R10X6G10X6_UNORM_2PACK16_KHR },
466 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
467 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
468 			},
469 			{
470 			//		Plane	Type	Offs	Size	Stride
471 				{	0,		unorm,	6,		10,		4 },	// R
472 				{	0,		unorm,	22,		10,		4 },	// G
473 				{ 0, 0, 0, 0, 0 },
474 				{ 0, 0, 0, 0, 0 },
475 			}
476 		},
477 		// VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16_KHR
478 		{
479 			1, // planes
480 			chanR|chanG|chanB|chanA,
481 			1,1,
482 			{
483 			//		Size	WDiv	HDiv	planeCompatibleFormat
484 				{	8,		1,		1,		VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16_KHR },
485 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
486 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
487 			},
488 			{
489 			//		Plane	Type	Offs	Size	Stride
490 				{	0,		unorm,	6,		10,		8 },	// R
491 				{	0,		unorm,	22,		10,		8 },	// G
492 				{	0,		unorm,	38,		10,		8 },	// B
493 				{	0,		unorm,	54,		10,		8 },	// A
494 			}
495 		},
496 		// VK_FORMAT_G10X6B10X6G10X6R10X6_422_UNORM_4PACK16_KHR
497 		{
498 			1, // planes
499 			chanR|chanG|chanB,
500 			2,1,
501 			{
502 			//		Size	WDiv	HDiv	planeCompatibleFormat
503 				{	8,		1,		1,		VK_FORMAT_G10X6B10X6G10X6R10X6_422_UNORM_4PACK16_KHR },
504 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
505 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
506 			},
507 			{
508 			//		Plane	Type	Offs	Size	Stride
509 				{	0,		unorm,	54,		10,		8 },	// R
510 				{	0,		unorm,	6,		10,		4 },	// G
511 				{	0,		unorm,	22,		10,		8 },	// B
512 				{ 0, 0, 0, 0, 0 }
513 			}
514 		},
515 		// VK_FORMAT_B10X6G10X6R10X6G10X6_422_UNORM_4PACK16_KHR
516 		{
517 			1, // planes
518 			chanR|chanG|chanB,
519 			2,1,
520 			{
521 			//		Size	WDiv	HDiv	planeCompatibleFormat
522 				{	8,		1,		1,		VK_FORMAT_B10X6G10X6R10X6G10X6_422_UNORM_4PACK16_KHR },
523 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
524 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
525 			},
526 			{
527 			//		Plane	Type	Offs	Size	Stride
528 				{	0,		unorm,	38,		10,		8 },	// R
529 				{	0,		unorm,	22,		10,		4 },	// G
530 				{	0,		unorm,	6,		10,		8 },	// B
531 				{ 0, 0, 0, 0, 0 }
532 			}
533 		},
534 		// VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_420_UNORM_3PACK16_KHR
535 		{
536 			3, // planes
537 			chanR|chanG|chanB,
538 			1,1,
539 			{
540 			//		Size	WDiv	HDiv	planeCompatibleFormat
541 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
542 				{	2,		2,		2,		VK_FORMAT_R10X6_UNORM_PACK16 },
543 				{	2,		2,		2,		VK_FORMAT_R10X6_UNORM_PACK16 },
544 			},
545 			{
546 			//		Plane	Type	Offs	Size	Stride
547 				{	2,		unorm,	6,		10,		2 },	// R
548 				{	0,		unorm,	6,		10,		2 },	// G
549 				{	1,		unorm,	6,		10,		2 },	// B
550 				{ 0, 0, 0, 0, 0 }
551 			}
552 		},
553 		// VK_FORMAT_G10X6_B10X6R10X6_2PLANE_420_UNORM_3PACK16_KHR
554 		{
555 			2, // planes
556 			chanR|chanG|chanB,
557 			1,1,
558 			{
559 			//		Size	WDiv	HDiv	planeCompatibleFormat
560 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
561 				{	4,		2,		2,		VK_FORMAT_R10X6G10X6_UNORM_2PACK16 },
562 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
563 			},
564 			{
565 			//		Plane	Type	Offs	Size	Stride
566 				{	1,		unorm,	22,		10,		4 },	// R
567 				{	0,		unorm,	6,		10,		2 },	// G
568 				{	1,		unorm,	6,		10,		4 },	// B
569 				{ 0, 0, 0, 0, 0 }
570 			}
571 		},
572 		// VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_422_UNORM_3PACK16_KHR
573 		{
574 			3, // planes
575 			chanR|chanG|chanB,
576 			1,1,
577 			{
578 			//		Size	WDiv	HDiv	planeCompatibleFormat
579 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
580 				{	2,		2,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
581 				{	2,		2,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
582 			},
583 			{
584 			//		Plane	Type	Offs	Size	Stride
585 				{	2,		unorm,	6,		10,		2 },	// R
586 				{	0,		unorm,	6,		10,		2 },	// G
587 				{	1,		unorm,	6,		10,		2 },	// B
588 				{ 0, 0, 0, 0, 0 }
589 			}
590 		},
591 		// VK_FORMAT_G10X6_B10X6R10X6_2PLANE_422_UNORM_3PACK16_KHR
592 		{
593 			2, // planes
594 			chanR|chanG|chanB,
595 			1,1,
596 			{
597 			//		Size	WDiv	HDiv	planeCompatibleFormat
598 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
599 				{	4,		2,		1,		VK_FORMAT_R10X6G10X6_UNORM_2PACK16 },
600 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
601 			},
602 			{
603 			//		Plane	Type	Offs	Size	Stride
604 				{	1,		unorm,	22,		10,		4 },	// R
605 				{	0,		unorm,	6,		10,		2 },	// G
606 				{	1,		unorm,	6,		10,		4 },	// B
607 				{ 0, 0, 0, 0, 0 }
608 			}
609 		},
610 		// VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_444_UNORM_3PACK16_KHR
611 		{
612 			3, // planes
613 			chanR|chanG|chanB,
614 			1,1,
615 			{
616 			//		Size	WDiv	HDiv	planeCompatibleFormat
617 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
618 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
619 				{	2,		1,		1,		VK_FORMAT_R10X6_UNORM_PACK16 },
620 			},
621 			{
622 			//		Plane	Type	Offs	Size	Stride
623 				{	2,		unorm,	6,		10,		2 },	// R
624 				{	0,		unorm,	6,		10,		2 },	// G
625 				{	1,		unorm,	6,		10,		2 },	// B
626 				{ 0, 0, 0, 0, 0 }
627 			}
628 		},
629 		// VK_FORMAT_R12X4_UNORM_PACK16_KHR
630 		{
631 			1, // planes
632 			chanR,
633 			1,1,
634 			{
635 			//		Size	WDiv	HDiv	planeCompatibleFormat
636 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16_KHR },
637 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
638 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
639 			},
640 			{
641 			//		Plane	Type	Offs	Size	Stride
642 				{	0,		unorm,	4,		12,		2 },	// R
643 				{ 0, 0, 0, 0, 0 },
644 				{ 0, 0, 0, 0, 0 },
645 				{ 0, 0, 0, 0, 0 },
646 			}
647 		},
648 		// VK_FORMAT_R12X4G12X4_UNORM_2PACK16_KHR
649 		{
650 			1, // planes
651 			chanR|chanG,
652 			1,1,
653 			{
654 			//		Size	WDiv	HDiv	planeCompatibleFormat
655 				{	4,		1,		1,		VK_FORMAT_R12X4G12X4_UNORM_2PACK16_KHR },
656 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
657 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
658 			},
659 			{
660 			//		Plane	Type	Offs	Size	Stride
661 				{	0,		unorm,	4,		12,		4 },	// R
662 				{	0,		unorm,	20,		12,		4 },	// G
663 				{ 0, 0, 0, 0, 0 },
664 				{ 0, 0, 0, 0, 0 },
665 			}
666 		},
667 		// VK_FORMAT_R12X4G12X4B12X4A12X4_UNORM_4PACK16_KHR
668 		{
669 			1, // planes
670 			chanR|chanG|chanB|chanA,
671 			1,1,
672 			{
673 			//		Size	WDiv	HDiv	planeCompatibleFormat
674 				{	8,		1,		1,		VK_FORMAT_R12X4G12X4B12X4A12X4_UNORM_4PACK16_KHR },
675 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
676 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
677 			},
678 			{
679 			//		Plane	Type	Offs	Size	Stride
680 				{	0,		unorm,	4,		12,		8 },	// R
681 				{	0,		unorm,	20,		12,		8 },	// G
682 				{	0,		unorm,	36,		12,		8 },	// B
683 				{	0,		unorm,	52,		12,		8 },	// A
684 			}
685 		},
686 		// VK_FORMAT_G12X4B12X4G12X4R12X4_422_UNORM_4PACK16_KHR
687 		{
688 			1, // planes
689 			chanR|chanG|chanB,
690 			2,1,
691 			{
692 			//		Size	WDiv	HDiv	planeCompatibleFormat
693 				{	8,		1,		1,		VK_FORMAT_G12X4B12X4G12X4R12X4_422_UNORM_4PACK16_KHR },
694 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
695 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
696 			},
697 			{
698 			//		Plane	Type	Offs	Size	Stride
699 				{	0,		unorm,	52,		12,		8 },	// R
700 				{	0,		unorm,	4,		12,		4 },	// G
701 				{	0,		unorm,	20,		12,		8 },	// B
702 				{ 0, 0, 0, 0, 0 }
703 			}
704 		},
705 		// VK_FORMAT_B12X4G12X4R12X4G12X4_422_UNORM_4PACK16_KHR
706 		{
707 			1, // planes
708 			chanR|chanG|chanB,
709 			2,1,
710 			{
711 			//		Size	WDiv	HDiv	planeCompatibleFormat
712 				{	8,		1,		1,		VK_FORMAT_B12X4G12X4R12X4G12X4_422_UNORM_4PACK16_KHR },
713 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
714 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
715 			},
716 			{
717 			//		Plane	Type	Offs	Size	Stride
718 				{	0,		unorm,	36,		12,		8 },	// R
719 				{	0,		unorm,	20,		12,		4 },	// G
720 				{	0,		unorm,	4,		12,		8 },	// B
721 				{ 0, 0, 0, 0, 0 }
722 			}
723 		},
724 		// VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_420_UNORM_3PACK16_KHR
725 		{
726 			3, // planes
727 			chanR|chanG|chanB,
728 			1,1,
729 			{
730 			//		Size	WDiv	HDiv	planeCompatibleFormat
731 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
732 				{	2,		2,		2,		VK_FORMAT_R12X4_UNORM_PACK16 },
733 				{	2,		2,		2,		VK_FORMAT_R12X4_UNORM_PACK16 },
734 			},
735 			{
736 			//		Plane	Type	Offs	Size	Stride
737 				{	2,		unorm,	4,		12,		2 },	// R
738 				{	0,		unorm,	4,		12,		2 },	// G
739 				{	1,		unorm,	4,		12,		2 },	// B
740 				{ 0, 0, 0, 0, 0 }
741 			}
742 		},
743 		// VK_FORMAT_G12X4_B12X4R12X4_2PLANE_420_UNORM_3PACK16_KHR
744 		{
745 			2, // planes
746 			chanR|chanG|chanB,
747 			1,1,
748 			{
749 			//		Size	WDiv	HDiv	planeCompatibleFormat
750 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
751 				{	4,		2,		2,		VK_FORMAT_R12X4G12X4_UNORM_2PACK16 },
752 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
753 			},
754 			{
755 			//		Plane	Type	Offs	Size	Stride
756 				{	1,		unorm,	20,		12,		4 },	// R
757 				{	0,		unorm,	4,		12,		2 },	// G
758 				{	1,		unorm,	4,		12,		4 },	// B
759 				{ 0, 0, 0, 0, 0 }
760 			}
761 		},
762 		// VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_422_UNORM_3PACK16_KHR
763 		{
764 			3, // planes
765 			chanR|chanG|chanB,
766 			1,1,
767 			{
768 			//		Size	WDiv	HDiv	planeCompatibleFormat
769 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
770 				{	2,		2,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
771 				{	2,		2,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
772 			},
773 			{
774 			//		Plane	Type	Offs	Size	Stride
775 				{	2,		unorm,	4,		12,		2 },	// R
776 				{	0,		unorm,	4,		12,		2 },	// G
777 				{	1,		unorm,	4,		12,		2 },	// B
778 				{ 0, 0, 0, 0, 0 }
779 			}
780 		},
781 		// VK_FORMAT_G12X4_B12X4R12X4_2PLANE_422_UNORM_3PACK16_KHR
782 		{
783 			2, // planes
784 			chanR|chanG|chanB,
785 			1,1,
786 			{
787 			//		Size	WDiv	HDiv	planeCompatibleFormat
788 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
789 				{	4,		2,		1,		VK_FORMAT_R12X4G12X4_UNORM_2PACK16 },
790 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
791 			},
792 			{
793 			//		Plane	Type	Offs	Size	Stride
794 				{	1,		unorm,	20,		12,		4 },	// R
795 				{	0,		unorm,	4,		12,		2 },	// G
796 				{	1,		unorm,	4,		12,		4 },	// B
797 				{ 0, 0, 0, 0, 0 }
798 			}
799 		},
800 		// VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_444_UNORM_3PACK16_KHR
801 		{
802 			3, // planes
803 			chanR|chanG|chanB,
804 			1,1,
805 			{
806 			//		Size	WDiv	HDiv	planeCompatibleFormat
807 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
808 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
809 				{	2,		1,		1,		VK_FORMAT_R12X4_UNORM_PACK16 },
810 			},
811 			{
812 			//		Plane	Type	Offs	Size	Stride
813 				{	2,		unorm,	4,		12,		2 },	// R
814 				{	0,		unorm,	4,		12,		2 },	// G
815 				{	1,		unorm,	4,		12,		2 },	// B
816 				{ 0, 0, 0, 0, 0 }
817 			}
818 		},
819 		// VK_FORMAT_G16B16G16R16_422_UNORM_KHR
820 		{
821 			1, // planes
822 			chanR|chanG|chanB,
823 			2,1,
824 			{
825 			//		Size	WDiv	HDiv	planeCompatibleFormat
826 				{	8,		1,		1,		VK_FORMAT_G16B16G16R16_422_UNORM_KHR },
827 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
828 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
829 			},
830 			{
831 			//		Plane	Type	Offs	Size	Stride
832 				{	0,		unorm,	48,		16,		8 },	// R
833 				{	0,		unorm,	0,		16,		4 },	// G
834 				{	0,		unorm,	16,		16,		8 },	// B
835 				{ 0, 0, 0, 0, 0 }
836 			}
837 		},
838 		// VK_FORMAT_B16G16R16G16_422_UNORM_KHR
839 		{
840 			1, // planes
841 			chanR|chanG|chanB,
842 			2,1,
843 			{
844 			//		Size	WDiv	HDiv	planeCompatibleFormat
845 				{	8,		1,		1,		VK_FORMAT_B16G16R16G16_422_UNORM_KHR },
846 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
847 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
848 			},
849 			{
850 			//		Plane	Type	Offs	Size	Stride
851 				{	0,		unorm,	32,		16,		8 },	// R
852 				{	0,		unorm,	16,		16,		4 },	// G
853 				{	0,		unorm,	0,		16,		8 },	// B
854 				{ 0, 0, 0, 0, 0 }
855 			}
856 		},
857 		// VK_FORMAT_G16_B16_R16_3PLANE_420_UNORM_KHR
858 		{
859 			3, // planes
860 			chanR|chanG|chanB,
861 			1,1,
862 			{
863 			//		Size	WDiv	HDiv	planeCompatibleFormat
864 				{	2,		1,		1,		VK_FORMAT_R16_UNORM },
865 				{	2,		2,		2,		VK_FORMAT_R16_UNORM },
866 				{	2,		2,		2,		VK_FORMAT_R16_UNORM },
867 			},
868 			{
869 			//		Plane	Type	Offs	Size	Stride
870 				{	2,		unorm,	0,		16,		2 },	// R
871 				{	0,		unorm,	0,		16,		2 },	// G
872 				{	1,		unorm,	0,		16,		2 },	// B
873 				{ 0, 0, 0, 0, 0 }
874 			}
875 		},
876 		// VK_FORMAT_G16_B16R16_2PLANE_420_UNORM_KHR
877 		{
878 			2, // planes
879 			chanR|chanG|chanB,
880 			1,1,
881 			{
882 			//		Size	WDiv	HDiv	planeCompatibleFormat
883 				{	2,		1,		1,		VK_FORMAT_R16_UNORM },
884 				{	4,		2,		2,		VK_FORMAT_R16G16_UNORM },
885 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
886 			},
887 			{
888 			//		Plane	Type	Offs	Size	Stride
889 				{	1,		unorm,	16,		16,		4 },	// R
890 				{	0,		unorm,	0,		16,		2 },	// G
891 				{	1,		unorm,	0,		16,		4 },	// B
892 				{ 0, 0, 0, 0, 0 }
893 			}
894 		},
895 		// VK_FORMAT_G16_B16_R16_3PLANE_422_UNORM_KHR
896 		{
897 			3, // planes
898 			chanR|chanG|chanB,
899 			1,1,
900 			{
901 			//		Size	WDiv	HDiv	planeCompatibleFormat
902 				{	2,		1,		1,		VK_FORMAT_R16_UNORM },
903 				{	2,		2,		1,		VK_FORMAT_R16_UNORM },
904 				{	2,		2,		1,		VK_FORMAT_R16_UNORM },
905 			},
906 			{
907 			//		Plane	Type	Offs	Size	Stride
908 				{	2,		unorm,	0,		16,		2 },	// R
909 				{	0,		unorm,	0,		16,		2 },	// G
910 				{	1,		unorm,	0,		16,		2 },	// B
911 				{ 0, 0, 0, 0, 0 }
912 			}
913 		},
914 		// VK_FORMAT_G16_B16R16_2PLANE_422_UNORM_KHR
915 		{
916 			2, // planes
917 			chanR|chanG|chanB,
918 			1,1,
919 			{
920 			//		Size	WDiv	HDiv	planeCompatibleFormat
921 				{	2,		1,		1,		VK_FORMAT_R16_UNORM },
922 				{	4,		2,		1,		VK_FORMAT_R16G16_UNORM },
923 				{	0,		0,		0,		VK_FORMAT_UNDEFINED },
924 			},
925 			{
926 			//		Plane	Type	Offs	Size	Stride
927 				{	1,		unorm,	16,		16,		4 },	// R
928 				{	0,		unorm,	0,		16,		2 },	// G
929 				{	1,		unorm,	0,		16,		4 },	// B
930 				{ 0, 0, 0, 0, 0 }
931 			}
932 		},
933 		// VK_FORMAT_G16_B16_R16_3PLANE_444_UNORM_KHR
934 		{
935 			3, // planes
936 			chanR|chanG|chanB,
937 			1,1,
938 			{
939 			//		Size	WDiv	HDiv	planeCompatibleFormat
940 				{	2,		1,		1,		VK_FORMAT_R16_UNORM },
941 				{	2,		1,		1,		VK_FORMAT_R16_UNORM },
942 				{	2,		1,		1,		VK_FORMAT_R16_UNORM },
943 			},
944 			{
945 			//		Plane	Type	Offs	Size	Stride
946 				{	2,		unorm,	0,		16,		2 },	// R
947 				{	0,		unorm,	0,		16,		2 },	// G
948 				{	1,		unorm,	0,		16,		2 },	// B
949 				{ 0, 0, 0, 0, 0 }
950 			}
951 		},
952 	};
953 
954 	const size_t	offset	= (size_t)VK_FORMAT_G8B8G8R8_422_UNORM_KHR;
955 
956 	DE_ASSERT(de::inBounds<size_t>((size_t)format, offset, offset+(size_t)DE_LENGTH_OF_ARRAY(s_formatInfo)));
957 
958 	return s_formatInfo[(size_t)format-offset];
959 }
960 
getCorePlanarFormatDescription(VkFormat format)961 PlanarFormatDescription getCorePlanarFormatDescription (VkFormat format)
962 {
963 	const deUint8			snorm	= (deUint8)tcu::TEXTURECHANNELCLASS_SIGNED_FIXED_POINT;
964 	const deUint8			unorm	= (deUint8)tcu::TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT;
965 	const deUint8			sint	= (deUint8)tcu::TEXTURECHANNELCLASS_SIGNED_INTEGER;
966 	const deUint8			uint	= (deUint8)tcu::TEXTURECHANNELCLASS_UNSIGNED_INTEGER;
967 	const deUint8			sfloat	= (deUint8)tcu::TEXTURECHANNELCLASS_FLOATING_POINT;
968 
969 	const deUint8			chanR	= (deUint8)PlanarFormatDescription::CHANNEL_R;
970 	const deUint8			chanG	= (deUint8)PlanarFormatDescription::CHANNEL_G;
971 	const deUint8			chanB	= (deUint8)PlanarFormatDescription::CHANNEL_B;
972 	const deUint8			chanA	= (deUint8)PlanarFormatDescription::CHANNEL_A;
973 
974 	DE_ASSERT(de::inBounds<deUint32>(format, VK_FORMAT_UNDEFINED+1, VK_CORE_FORMAT_LAST));
975 
976 #if (DE_ENDIANNESS != DE_LITTLE_ENDIAN)
977 #	error "Big-endian is not supported"
978 #endif
979 
980 	switch (format)
981 	{
982 		case VK_FORMAT_R8_UNORM:
983 		{
984 			const PlanarFormatDescription	desc	=
985 			{
986 				1, // planes
987 				chanR,
988 				1,1,
989 				{
990 				//		Size	WDiv	HDiv	planeCompatibleFormat
991 					{	1,		1,		1,		VK_FORMAT_R8_UNORM },
992 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
993 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
994 				},
995 				{
996 				//		Plane	Type	Offs	Size	Stride
997 					{	0,		unorm,	0,		8,		1 },	// R
998 					{	0,		0,		0,		0,		0 },	// G
999 					{	0,		0,		0,		0,		0 },	// B
1000 					{	0,		0,		0,		0,		0 }		// A
1001 				}
1002 			};
1003 			return desc;
1004 		}
1005 
1006 		case VK_FORMAT_R8_SNORM:
1007 		{
1008 			const PlanarFormatDescription	desc	=
1009 			{
1010 				1, // planes
1011 				chanR,
1012 				1,1,
1013 				{
1014 				//		Size	WDiv	HDiv	planeCompatibleFormat
1015 					{	1,		1,		1,		VK_FORMAT_R8_SNORM },
1016 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1017 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1018 				},
1019 				{
1020 				//		Plane	Type	Offs	Size	Stride
1021 					{	0,		snorm,	0,		8,		1 },	// R
1022 					{	0,		0,		0,		0,		0 },	// G
1023 					{	0,		0,		0,		0,		0 },	// B
1024 					{	0,		0,		0,		0,		0 }		// A
1025 				}
1026 			};
1027 			return desc;
1028 		}
1029 
1030 
1031 		case VK_FORMAT_R8G8_UNORM:
1032 		{
1033 			const PlanarFormatDescription	desc	=
1034 			{
1035 				1, // planes
1036 				chanR|chanG,
1037 				1,1,
1038 				{
1039 				//		Size	WDiv	HDiv	planeCompatibleFormat
1040 					{	2,		1,		1,		VK_FORMAT_R8G8_UNORM },
1041 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1042 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1043 				},
1044 				{
1045 				//		Plane	Type	Offs	Size	Stride
1046 					{	0,		unorm,	0,		8,		2 },	// R
1047 					{	0,		unorm,	8,		8,		2 },	// G
1048 					{	0,		0,		0,		0,		0 },	// B
1049 					{	0,		0,		0,		0,		0 }		// A
1050 				}
1051 			};
1052 			return desc;
1053 		}
1054 
1055 		case VK_FORMAT_R8G8_SNORM:
1056 		{
1057 			const PlanarFormatDescription	desc	=
1058 			{
1059 				1, // planes
1060 				chanR | chanG,
1061 				1,1,
1062 				{
1063 				//		Size	WDiv	HDiv	planeCompatibleFormat
1064 					{	2,		1,		1,		VK_FORMAT_R8G8_SNORM },
1065 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1066 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1067 				},
1068 				{
1069 				//		Plane	Type	Offs	Size	Stride
1070 					{	0,		snorm,	0,		8,		2 },	// R
1071 					{	0,		snorm,	8,		8,		2 },	// G
1072 					{	0,		0,		0,		0,		0 },	// B
1073 					{	0,		0,		0,		0,		0 }		// A
1074 				}
1075 			};
1076 			return desc;
1077 		}
1078 
1079 		case VK_FORMAT_R16_UNORM:
1080 		{
1081 			const PlanarFormatDescription	desc	=
1082 			{
1083 				1, // planes
1084 				chanR,
1085 				1,1,
1086 				{
1087 				//		Size	WDiv	HDiv	planeCompatibleFormat
1088 					{	2,		1,		1,		VK_FORMAT_R16_UNORM },
1089 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1090 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1091 				},
1092 				{
1093 				//		Plane	Type	Offs	Size	Stride
1094 					{	0,		unorm,	0,		16,		2 },	// R
1095 					{	0,		0,		0,		0,		0 },	// G
1096 					{	0,		0,		0,		0,		0 },	// B
1097 					{	0,		0,		0,		0,		0 }		// A
1098 				}
1099 			};
1100 			return desc;
1101 		}
1102 
1103 		case VK_FORMAT_R16_SNORM:
1104 		{
1105 			const PlanarFormatDescription	desc	=
1106 			{
1107 				1, // planes
1108 				chanR,
1109 				1,1,
1110 				{
1111 				//		Size	WDiv	HDiv	planeCompatibleFormat
1112 					{	2,		1,		1,		VK_FORMAT_R16_SNORM },
1113 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1114 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1115 				},
1116 				{
1117 				//		Plane	Type	Offs	Size	Stride
1118 					{	0,		snorm,	0,		16,		2 },	// R
1119 					{	0,		0,		0,		0,		0 },	// G
1120 					{	0,		0,		0,		0,		0 },	// B
1121 					{	0,		0,		0,		0,		0 }		// A
1122 				}
1123 			};
1124 			return desc;
1125 		}
1126 
1127 		case VK_FORMAT_R16G16_UNORM:
1128 		{
1129 			const PlanarFormatDescription	desc	=
1130 			{
1131 				1, // planes
1132 				chanR|chanG,
1133 				1,1,
1134 				{
1135 				//		Size	WDiv	HDiv	planeCompatibleFormat
1136 					{	4,		1,		1,		VK_FORMAT_R16G16_UNORM },
1137 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1138 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1139 				},
1140 				{
1141 				//		Plane	Type	Offs	Size	Stride
1142 					{	0,		unorm,	0,		16,		4 },	// R
1143 					{	0,		unorm,	16,		16,		4 },	// G
1144 					{	0,		0,		0,		0,		0 },	// B
1145 					{	0,		0,		0,		0,		0 }		// A
1146 				}
1147 			};
1148 			return desc;
1149 		}
1150 
1151 		case VK_FORMAT_R16G16_SNORM:
1152 		{
1153 			const PlanarFormatDescription	desc	=
1154 			{
1155 				1, // planes
1156 				chanR | chanG,
1157 				1,1,
1158 				{
1159 				//		Size	WDiv	HDiv	planeCompatibleFormat
1160 					{	4,		1,		1,		VK_FORMAT_R16G16_SNORM },
1161 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1162 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1163 				},
1164 				{
1165 				//		Plane	Type	Offs	Size	Stride
1166 					{	0,		snorm,	0,		16,		4 },	// R
1167 					{	0,		snorm,	16,		16,		4 },	// G
1168 					{	0,		0,		0,		0,		0 },	// B
1169 					{	0,		0,		0,		0,		0 }		// A
1170 				}
1171 			};
1172 			return desc;
1173 		}
1174 
1175 		case VK_FORMAT_B10G11R11_UFLOAT_PACK32:
1176 		{
1177 			const PlanarFormatDescription	desc	=
1178 			{
1179 				1, // planes
1180 				chanR|chanG|chanB,
1181 				1,1,
1182 				{
1183 				//		Size	WDiv	HDiv	planeCompatibleFormat
1184 					{	4,		1,		1,		VK_FORMAT_B10G11R11_UFLOAT_PACK32 },
1185 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1186 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1187 				},
1188 				{
1189 				//		Plane	Type	Offs	Size	Stride
1190 					{	0,		unorm,	0,		11,		4 },	// R
1191 					{	0,		unorm,	11,		11,		4 },	// G
1192 					{	0,		unorm,	22,		10,		4 },	// B
1193 					{	0,		0,		0,		0,		0 }		// A
1194 				}
1195 			};
1196 			return desc;
1197 		}
1198 
1199 		case VK_FORMAT_R4G4_UNORM_PACK8:
1200 		{
1201 			const PlanarFormatDescription	desc	=
1202 			{
1203 				1, // planes
1204 				chanR|chanG,
1205 				1,1,
1206 				{
1207 				//		Size	WDiv	HDiv	planeCompatibleFormat
1208 					{	1,		1,		1,		VK_FORMAT_R4G4_UNORM_PACK8 },
1209 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1210 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1211 				},
1212 				{
1213 				//		Plane	Type	Offs	Size	Stride
1214 					{	0,		unorm,	4,		4,		1 },	// R
1215 					{	0,		unorm,	0,		4,		1 },	// G
1216 					{	0,		0,		0,		0,		0 },	// B
1217 					{	0,		0,		0,		0,		0 }		// A
1218 				}
1219 			};
1220 			return desc;
1221 		}
1222 
1223 		case VK_FORMAT_R4G4B4A4_UNORM_PACK16:
1224 		{
1225 			const PlanarFormatDescription	desc	=
1226 			{
1227 				1, // planes
1228 				chanR|chanG|chanB|chanA,
1229 				1,1,
1230 				{
1231 				//		Size	WDiv	HDiv	planeCompatibleFormat
1232 					{	2,		1,		1,		VK_FORMAT_R4G4B4A4_UNORM_PACK16 },
1233 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1234 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1235 				},
1236 				{
1237 				//		Plane	Type	Offs	Size	Stride
1238 					{	0,		unorm,	12,		4,		2 },	// R
1239 					{	0,		unorm,	8,		4,		2 },	// G
1240 					{	0,		unorm,	4,		4,		2 },	// B
1241 					{	0,		unorm,	0,		4,		2 }		// A
1242 				}
1243 			};
1244 			return desc;
1245 		}
1246 
1247 		case VK_FORMAT_B4G4R4A4_UNORM_PACK16:
1248 		{
1249 			const PlanarFormatDescription	desc	=
1250 			{
1251 				1, // planes
1252 				chanR|chanG|chanB|chanA,
1253 				1,1,
1254 				{
1255 				//		Size	WDiv	HDiv	planeCompatibleFormat
1256 					{	2,		1,		1,		VK_FORMAT_B4G4R4A4_UNORM_PACK16 },
1257 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1258 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1259 				},
1260 				{
1261 				//		Plane	Type	Offs	Size	Stride
1262 					{	0,		unorm,	4,		4,		2 },	// R
1263 					{	0,		unorm,	8,		4,		2 },	// G
1264 					{	0,		unorm,	12,		4,		2 },	// B
1265 					{	0,		unorm,	0,		4,		2 }		// A
1266 				}
1267 			};
1268 			return desc;
1269 		}
1270 
1271 		case VK_FORMAT_R5G6B5_UNORM_PACK16:
1272 		{
1273 			const PlanarFormatDescription	desc	=
1274 			{
1275 				1, // planes
1276 				chanR|chanG|chanB,
1277 				1,1,
1278 				{
1279 				//		Size	WDiv	HDiv	planeCompatibleFormat
1280 					{	2,		1,		1,		VK_FORMAT_R5G6B5_UNORM_PACK16 },
1281 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1282 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1283 				},
1284 				{
1285 				//		Plane	Type	Offs	Size	Stride
1286 					{	0,		unorm,	11,		5,		2 },	// R
1287 					{	0,		unorm,	5,		6,		2 },	// G
1288 					{	0,		unorm,	0,		5,		2 },	// B
1289 					{	0,		0,		0,		0,		0 }		// A
1290 				}
1291 			};
1292 			return desc;
1293 		}
1294 
1295 		case VK_FORMAT_B5G6R5_UNORM_PACK16:
1296 		{
1297 			const PlanarFormatDescription	desc	=
1298 			{
1299 				1, // planes
1300 				chanR|chanG|chanB,
1301 				1,1,
1302 				{
1303 				//		Size	WDiv	HDiv	planeCompatibleFormat
1304 					{	2,		1,		1,		VK_FORMAT_B5G6R5_UNORM_PACK16 },
1305 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1306 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1307 				},
1308 				{
1309 				//		Plane	Type	Offs	Size	Stride
1310 					{	0,		unorm,	0,		5,		2 },	// R
1311 					{	0,		unorm,	5,		6,		2 },	// G
1312 					{	0,		unorm,	11,		5,		2 },	// B
1313 					{	0,		0,		0,		0,		0 }		// A
1314 				}
1315 			};
1316 			return desc;
1317 		}
1318 
1319 		case VK_FORMAT_R5G5B5A1_UNORM_PACK16:
1320 		{
1321 			const PlanarFormatDescription	desc	=
1322 			{
1323 				1, // planes
1324 				chanR|chanG|chanB|chanA,
1325 				1,1,
1326 				{
1327 				//		Size	WDiv	HDiv	planeCompatibleFormat
1328 					{	2,		1,		1,		VK_FORMAT_R5G5B5A1_UNORM_PACK16 },
1329 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1330 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1331 				},
1332 				{
1333 				//		Plane	Type	Offs	Size	Stride
1334 					{	0,		unorm,	11,		5,		2 },	// R
1335 					{	0,		unorm,	6,		5,		2 },	// G
1336 					{	0,		unorm,	1,		5,		2 },	// B
1337 					{	0,		unorm,	0,		1,		2 }		// A
1338 				}
1339 			};
1340 			return desc;
1341 		}
1342 
1343 		case VK_FORMAT_B5G5R5A1_UNORM_PACK16:
1344 		{
1345 			const PlanarFormatDescription	desc	=
1346 			{
1347 				1, // planes
1348 				chanR|chanG|chanB|chanA,
1349 				1,1,
1350 				{
1351 				//		Size	WDiv	HDiv	planeCompatibleFormat
1352 					{	2,		1,		1,		VK_FORMAT_B5G5R5A1_UNORM_PACK16 },
1353 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1354 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1355 				},
1356 				{
1357 				//		Plane	Type	Offs	Size	Stride
1358 					{	0,		unorm,	1,		5,		2 },	// R
1359 					{	0,		unorm,	6,		5,		2 },	// G
1360 					{	0,		unorm,	11,		5,		2 },	// B
1361 					{	0,		unorm,	0,		1,		2 }		// A
1362 				}
1363 			};
1364 			return desc;
1365 		}
1366 
1367 		case VK_FORMAT_A1R5G5B5_UNORM_PACK16:
1368 		{
1369 			const PlanarFormatDescription	desc	=
1370 			{
1371 				1, // planes
1372 				chanR|chanG|chanB|chanA,
1373 				1,1,
1374 				{
1375 				//		Size	WDiv	HDiv	planeCompatibleFormat
1376 					{	2,		1,		1,		VK_FORMAT_A1R5G5B5_UNORM_PACK16 },
1377 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1378 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1379 				},
1380 				{
1381 				//		Plane	Type	Offs	Size	Stride
1382 					{	0,		unorm,	10,		5,		2 },	// R
1383 					{	0,		unorm,	5,		5,		2 },	// G
1384 					{	0,		unorm,	0,		5,		2 },	// B
1385 					{	0,		unorm,	15,		1,		2 }		// A
1386 				}
1387 			};
1388 			return desc;
1389 		}
1390 
1391 		case VK_FORMAT_R8G8B8_UNORM:
1392 		{
1393 			const PlanarFormatDescription	desc	=
1394 			{
1395 				1, // planes
1396 				chanR|chanG|chanB,
1397 				1,1,
1398 				{
1399 				//		Size	WDiv	HDiv	planeCompatibleFormat
1400 					{	3,		1,		1,		VK_FORMAT_R8G8B8_UNORM },
1401 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1402 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1403 				},
1404 				{
1405 				//		Plane	Type	Offs	Size	Stride
1406 					{	0,		unorm,	0,		8,		3 },	// R
1407 					{	0,		unorm,	8,		8,		3 },	// G
1408 					{	0,		unorm,	16,		8,		3 },	// B
1409 					{	0,		0,		0,		0,		0 }		// A
1410 				}
1411 			};
1412 			return desc;
1413 		}
1414 
1415 		case VK_FORMAT_B8G8R8_UNORM:
1416 		{
1417 			const PlanarFormatDescription	desc	=
1418 			{
1419 				1, // planes
1420 				chanR|chanG|chanB,
1421 				1,1,
1422 				{
1423 				//		Size	WDiv	HDiv	planeCompatibleFormat
1424 					{	3,		1,		1,		VK_FORMAT_B8G8R8_UNORM },
1425 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1426 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1427 				},
1428 				{
1429 				//		Plane	Type	Offs	Size	Stride
1430 					{	0,		unorm,	16,		8,		3 },	// R
1431 					{	0,		unorm,	8,		8,		3 },	// G
1432 					{	0,		unorm,	0,		8,		3 },	// B
1433 					{	0,		0,		0,		0,		0 }		// A
1434 				}
1435 			};
1436 			return desc;
1437 		}
1438 
1439 		case VK_FORMAT_R8G8B8A8_UNORM:
1440 		case VK_FORMAT_A8B8G8R8_UNORM_PACK32:
1441 		{
1442 			const PlanarFormatDescription	desc	=
1443 			{
1444 				1, // planes
1445 				chanR|chanG|chanB|chanA,
1446 				1,1,
1447 				{
1448 				//		Size	WDiv	HDiv	planeCompatibleFormat
1449 					{	4,		1,		1,		VK_FORMAT_R8G8B8A8_UNORM },
1450 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1451 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1452 				},
1453 				{
1454 				//		Plane	Type	Offs	Size	Stride
1455 					{	0,		unorm,	0,		8,		4 },	// R
1456 					{	0,		unorm,	8,		8,		4 },	// G
1457 					{	0,		unorm,	16,		8,		4 },	// B
1458 					{	0,		unorm,	24,		8,		4 }		// A
1459 				}
1460 			};
1461 			return desc;
1462 		}
1463 
1464 		case VK_FORMAT_B8G8R8A8_UNORM:
1465 		{
1466 			const PlanarFormatDescription	desc	=
1467 			{
1468 				1, // planes
1469 				chanR|chanG|chanB|chanA,
1470 				1,1,
1471 				{
1472 				//		Size	WDiv	HDiv	planeCompatibleFormat
1473 					{	4,		1,		1,		VK_FORMAT_B8G8R8A8_UNORM },
1474 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1475 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1476 				},
1477 				{
1478 				//		Plane	Type	Offs	Size	Stride
1479 					{	0,		unorm,	16,		8,		4 },	// R
1480 					{	0,		unorm,	8,		8,		4 },	// G
1481 					{	0,		unorm,	0,		8,		4 },	// B
1482 					{	0,		unorm,	24,		8,		4 }		// A
1483 				}
1484 			};
1485 			return desc;
1486 		}
1487 
1488 		case VK_FORMAT_A2R10G10B10_UNORM_PACK32:
1489 		{
1490 			const PlanarFormatDescription	desc	=
1491 			{
1492 				1, // planes
1493 				chanR|chanG|chanB|chanA,
1494 				1,1,
1495 				{
1496 				//		Size	WDiv	HDiv	planeCompatibleFormat
1497 					{	4,		1,		1,		VK_FORMAT_A2R10G10B10_UNORM_PACK32 },
1498 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1499 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1500 				},
1501 				{
1502 				//		Plane	Type	Offs	Size	Stride
1503 					{	0,		unorm,	20,		10,		4 },	// R
1504 					{	0,		unorm,	10,		10,		4 },	// G
1505 					{	0,		unorm,	0,		10,		4 },	// B
1506 					{	0,		unorm,	30,		2,		4 }		// A
1507 				}
1508 			};
1509 			return desc;
1510 		}
1511 
1512 		case VK_FORMAT_A2B10G10R10_UNORM_PACK32:
1513 		{
1514 			const PlanarFormatDescription	desc	=
1515 			{
1516 				1, // planes
1517 				chanR|chanG|chanB|chanA,
1518 				1,1,
1519 				{
1520 				//		Size	WDiv	HDiv	planeCompatibleFormat
1521 					{	4,		1,		1,		VK_FORMAT_A2B10G10R10_UNORM_PACK32 },
1522 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1523 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1524 				},
1525 				{
1526 				//		Plane	Type	Offs	Size	Stride
1527 					{	0,		unorm,	0,		10,		4 },	// R
1528 					{	0,		unorm,	10,		10,		4 },	// G
1529 					{	0,		unorm,	20,		10,		4 },	// B
1530 					{	0,		unorm,	30,		2,		4 }		// A
1531 				}
1532 			};
1533 			return desc;
1534 		}
1535 
1536 		case VK_FORMAT_R16G16B16_UNORM:
1537 		{
1538 			const PlanarFormatDescription	desc	=
1539 			{
1540 				1, // planes
1541 				chanR|chanG|chanB,
1542 				1,1,
1543 				{
1544 				//		Size	WDiv	HDiv	planeCompatibleFormat
1545 					{	6,		1,		1,		VK_FORMAT_R16G16B16_UNORM },
1546 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1547 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1548 				},
1549 				{
1550 				//		Plane	Type	Offs	Size	Stride
1551 					{	0,		unorm,	0,		16,		6 },	// R
1552 					{	0,		unorm,	16,		16,		6 },	// G
1553 					{	0,		unorm,	32,		16,		6 },	// B
1554 					{	0,		0,		0,		0,		0 }		// A
1555 				}
1556 			};
1557 			return desc;
1558 		}
1559 
1560 		case VK_FORMAT_R16G16B16A16_UNORM:
1561 		{
1562 			const PlanarFormatDescription	desc	=
1563 			{
1564 				1, // planes
1565 				chanR|chanG|chanB|chanA,
1566 				1,1,
1567 				{
1568 				//		Size	WDiv	HDiv	planeCompatibleFormat
1569 					{	8,		1,		1,		VK_FORMAT_R16G16B16A16_UNORM },
1570 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1571 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1572 				},
1573 				{
1574 				//		Plane	Type	Offs	Size	Stride
1575 					{	0,		unorm,	0,		16,		8 },	// R
1576 					{	0,		unorm,	16,		16,		8 },	// G
1577 					{	0,		unorm,	32,		16,		8 },	// B
1578 					{	0,		unorm,	48,		16,		8 }		// A
1579 				}
1580 			};
1581 			return desc;
1582 		}
1583 
1584 		case VK_FORMAT_R8_SINT:
1585 		{
1586 			const PlanarFormatDescription	desc	=
1587 			{
1588 				1, // planes
1589 				chanR,
1590 				1,1,
1591 				{
1592 				//		Size	WDiv	HDiv	planeCompatibleFormat
1593 					{	1,		1,		1,		VK_FORMAT_R8_SINT },
1594 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1595 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1596 				},
1597 				{
1598 				//		Plane	Type	Offs	Size	Stride
1599 					{	0,		sint,	0,		8,		1 },	// R
1600 					{	0,		0,		0,		0,		0 },	// G
1601 					{	0,		0,		0,		0,		0 },	// B
1602 					{	0,		0,		0,		0,		0 }		// A
1603 				}
1604 			};
1605 			return desc;
1606 		}
1607 
1608 		case VK_FORMAT_R16_SINT:
1609 		{
1610 			const PlanarFormatDescription	desc	=
1611 			{
1612 				1, // planes
1613 				chanR,
1614 				1,1,
1615 				{
1616 				//		Size	WDiv	HDiv	planeCompatibleFormat
1617 					{	2,		1,		1,		VK_FORMAT_R16_SINT },
1618 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1619 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1620 				},
1621 				{
1622 				//		Plane	Type	Offs	Size	Stride
1623 					{	0,		sint,	0,		16,		2 },	// R
1624 					{	0,		0,		0,		0,		0 },	// G
1625 					{	0,		0,		0,		0,		0 },	// B
1626 					{	0,		0,		0,		0,		0 }		// A
1627 				}
1628 			};
1629 			return desc;
1630 		}
1631 
1632 		case VK_FORMAT_R32_SINT:
1633 		{
1634 			const PlanarFormatDescription	desc	=
1635 			{
1636 				1, // planes
1637 				chanR,
1638 				1,1,
1639 				{
1640 				//		Size	WDiv	HDiv	planeCompatibleFormat
1641 					{	4,		1,		1,		VK_FORMAT_R32_SINT },
1642 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1643 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1644 				},
1645 				{
1646 				//		Plane	Type	Offs	Size	Stride
1647 					{	0,		sint,	0,		32,		4 },	// R
1648 					{	0,		0,		0,		0,		0 },	// G
1649 					{	0,		0,		0,		0,		0 },	// B
1650 					{	0,		0,		0,		0,		0 }		// A
1651 				}
1652 			};
1653 			return desc;
1654 		}
1655 
1656 		case VK_FORMAT_R8G8_SINT:
1657 		{
1658 			const PlanarFormatDescription	desc	=
1659 			{
1660 				1, // planes
1661 				chanR | chanG,
1662 				1,1,
1663 				{
1664 				//		Size	WDiv	HDiv	planeCompatibleFormat
1665 					{	2,		1,		1,		VK_FORMAT_R8G8_SINT },
1666 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1667 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1668 				},
1669 				{
1670 				//		Plane	Type	Offs	Size	Stride
1671 					{	0,		sint,	0,		8,		2 },	// R
1672 					{	0,		sint,	8,		8,		2 },	// G
1673 					{	0,		0,		0,		0,		0 },	// B
1674 					{	0,		0,		0,		0,		0 }		// A
1675 				}
1676 			};
1677 			return desc;
1678 		}
1679 
1680 		case VK_FORMAT_R16G16_SINT:
1681 		{
1682 			const PlanarFormatDescription	desc	=
1683 			{
1684 				1, // planes
1685 				chanR | chanG,
1686 				1,1,
1687 				{
1688 				//		Size	WDiv	HDiv	planeCompatibleFormat
1689 					{	4,		1,		1,		VK_FORMAT_R16G16_SINT },
1690 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1691 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1692 				},
1693 				{
1694 				//		Plane	Type	Offs	Size	Stride
1695 					{	0,		sint,	0,		16,		4 },	// R
1696 					{	0,		sint,	16,		16,		4 },	// G
1697 					{	0,		0,		0,		0,		0 },	// B
1698 					{	0,		0,		0,		0,		0 }		// A
1699 				}
1700 			};
1701 			return desc;
1702 		}
1703 
1704 		case VK_FORMAT_R32G32_SINT:
1705 		{
1706 			const PlanarFormatDescription	desc	=
1707 			{
1708 				1, // planes
1709 				chanR | chanG,
1710 				1,1,
1711 				{
1712 				//		Size	WDiv	HDiv	planeCompatibleFormat
1713 					{	8,		1,		1,		VK_FORMAT_R32G32_SINT },
1714 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1715 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1716 				},
1717 				{
1718 				//		Plane	Type	Offs	Size	Stride
1719 					{	0,		sint,	0,		32,		8 },	// R
1720 					{	0,		sint,	32,		32,		8 },	// G
1721 					{	0,		0,		0,		0,		0 },	// B
1722 					{	0,		0,		0,		0,		0 }		// A
1723 				}
1724 			};
1725 			return desc;
1726 		}
1727 
1728 		case VK_FORMAT_R8G8B8A8_SINT:
1729 		{
1730 			const PlanarFormatDescription	desc	=
1731 			{
1732 				1, // planes
1733 				chanR | chanG | chanB | chanA,
1734 				1,1,
1735 				{
1736 				//		Size	WDiv	HDiv	planeCompatibleFormat
1737 					{	4,		1,		1,		VK_FORMAT_R8G8B8A8_SINT },
1738 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1739 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1740 				},
1741 				{
1742 				//		Plane	Type	Offs	Size	Stride
1743 					{	0,		sint,	0,		8,		4 },	// R
1744 					{	0,		sint,	8,		8,		4 },	// G
1745 					{	0,		sint,	16,		8,		4 },	// B
1746 					{	0,		sint,	24,		8,		4 }		// A
1747 				}
1748 			};
1749 			return desc;
1750 		}
1751 
1752 		case VK_FORMAT_R16G16B16A16_SINT:
1753 		{
1754 			const PlanarFormatDescription	desc	=
1755 			{
1756 				1, // planes
1757 				chanR | chanG | chanB | chanA,
1758 				1,1,
1759 				{
1760 				//		Size	WDiv	HDiv	planeCompatibleFormat
1761 					{	8,		1,		1,		VK_FORMAT_R16G16B16A16_SINT },
1762 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1763 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1764 				},
1765 				{
1766 				//		Plane	Type	Offs	Size	Stride
1767 					{	0,		sint,	0,		16,		8 },	// R
1768 					{	0,		sint,	16,		16,		8 },	// G
1769 					{	0,		sint,	32,		16,		8 },	// B
1770 					{	0,		sint,	48,		16,		8 }		// A
1771 				}
1772 			};
1773 			return desc;
1774 		}
1775 
1776 		case VK_FORMAT_R32G32B32A32_SINT:
1777 		{
1778 			const PlanarFormatDescription	desc	=
1779 			{
1780 				1, // planes
1781 				chanR | chanG | chanB | chanA,
1782 				1,1,
1783 				{
1784 				//		Size	WDiv	HDiv	planeCompatibleFormat
1785 					{	16,		1,		1,		VK_FORMAT_R32G32B32A32_SINT },
1786 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1787 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1788 				},
1789 				{
1790 				//		Plane	Type	Offs	Size	Stride
1791 					{	0,		sint,	0,		32,		16 },	// R
1792 					{	0,		sint,	32,		32,		16 },	// G
1793 					{	0,		sint,	64,		32,		16 },	// B
1794 					{	0,		sint,	96,		32,		16 }	// A
1795 				}
1796 			};
1797 			return desc;
1798 		}
1799 
1800 		case VK_FORMAT_R8_UINT:
1801 		{
1802 			const PlanarFormatDescription	desc	=
1803 			{
1804 				1, // planes
1805 				chanR,
1806 				1,1,
1807 				{
1808 				//		Size	WDiv	HDiv	planeCompatibleFormat
1809 					{	1,		1,		1,		VK_FORMAT_R8_UINT },
1810 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1811 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1812 				},
1813 				{
1814 				//		Plane	Type	Offs	Size	Stride
1815 					{	0,		uint,	0,		8,		1 },	// R
1816 					{	0,		0,		0,		0,		0 },	// G
1817 					{	0,		0,		0,		0,		0 },	// B
1818 					{	0,		0,		0,		0,		0 }		// A
1819 				}
1820 			};
1821 			return desc;
1822 		}
1823 
1824 		case VK_FORMAT_R16_UINT:
1825 		{
1826 			const PlanarFormatDescription	desc	=
1827 			{
1828 				1, // planes
1829 				chanR,
1830 				1,1,
1831 				{
1832 				//		Size	WDiv	HDiv	planeCompatibleFormat
1833 					{	2,		1,		1,		VK_FORMAT_R16_UINT },
1834 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1835 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1836 				},
1837 				{
1838 				//		Plane	Type	Offs	Size	Stride
1839 					{	0,		uint,	0,		16,		2 },	// R
1840 					{	0,		0,		0,		0,		0 },	// G
1841 					{	0,		0,		0,		0,		0 },	// B
1842 					{	0,		0,		0,		0,		0 }		// A
1843 				}
1844 			};
1845 			return desc;
1846 		}
1847 
1848 		case VK_FORMAT_R32_UINT:
1849 		{
1850 			const PlanarFormatDescription	desc	=
1851 			{
1852 				1, // planes
1853 				chanR,
1854 				1,1,
1855 				{
1856 				//		Size	WDiv	HDiv	planeCompatibleFormat
1857 					{	4,		1,		1,		VK_FORMAT_R32_UINT },
1858 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1859 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1860 				},
1861 				{
1862 				//		Plane	Type	Offs	Size	Stride
1863 					{	0,		uint,	0,		32,		4 },	// R
1864 					{	0,		0,		0,		0,		0 },	// G
1865 					{	0,		0,		0,		0,		0 },	// B
1866 					{	0,		0,		0,		0,		0 }		// A
1867 				}
1868 			};
1869 			return desc;
1870 		}
1871 
1872 		case VK_FORMAT_R8G8_UINT:
1873 		{
1874 			const PlanarFormatDescription	desc	=
1875 			{
1876 				1, // planes
1877 				chanR | chanG,
1878 				1,1,
1879 				{
1880 				//		Size	WDiv	HDiv	planeCompatibleFormat
1881 					{	2,		1,		1,		VK_FORMAT_R8G8_UINT },
1882 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1883 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1884 				},
1885 				{
1886 				//		Plane	Type	Offs	Size	Stride
1887 					{	0,		uint,	0,		8,		2 },	// R
1888 					{	0,		uint,	8,		8,		2 },	// G
1889 					{	0,		0,		0,		0,		0 },	// B
1890 					{	0,		0,		0,		0,		0 }		// A
1891 				}
1892 			};
1893 			return desc;
1894 		}
1895 
1896 		case VK_FORMAT_R16G16_UINT:
1897 		{
1898 			const PlanarFormatDescription	desc	=
1899 			{
1900 				1, // planes
1901 				chanR | chanG,
1902 				1,1,
1903 				{
1904 				//		Size	WDiv	HDiv	planeCompatibleFormat
1905 					{	4,		1,		1,		VK_FORMAT_R16G16_UINT },
1906 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1907 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1908 				},
1909 				{
1910 				//		Plane	Type	Offs	Size	Stride
1911 					{	0,		uint,	0,		16,		4 },	// R
1912 					{	0,		uint,	16,		16,		4 },	// G
1913 					{	0,		0,		0,		0,		0 },	// B
1914 					{	0,		0,		0,		0,		0 }		// A
1915 				}
1916 			};
1917 			return desc;
1918 		}
1919 
1920 		case VK_FORMAT_R32G32_UINT:
1921 		{
1922 			const PlanarFormatDescription	desc	=
1923 			{
1924 				1, // planes
1925 				chanR | chanG,
1926 				1,1,
1927 				{
1928 				//		Size	WDiv	HDiv	planeCompatibleFormat
1929 					{	8,		1,		1,		VK_FORMAT_R32G32_UINT },
1930 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1931 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1932 				},
1933 				{
1934 				//		Plane	Type	Offs	Size	Stride
1935 					{	0,		uint,	0,		32,		8 },	// R
1936 					{	0,		uint,	32,		32,		8 },	// G
1937 					{	0,		0,		0,		0,		0 },	// B
1938 					{	0,		0,		0,		0,		0 }		// A
1939 				}
1940 			};
1941 			return desc;
1942 		}
1943 
1944 		case VK_FORMAT_R8G8B8A8_UINT:
1945 		{
1946 			const PlanarFormatDescription	desc	=
1947 			{
1948 				1, // planes
1949 				chanR | chanG | chanB | chanA,
1950 				1,1,
1951 				{
1952 				//		Size	WDiv	HDiv	planeCompatibleFormat
1953 					{	4,		1,		1,		VK_FORMAT_R8G8B8A8_UINT },
1954 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1955 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1956 				},
1957 				{
1958 				//		Plane	Type	Offs	Size	Stride
1959 					{	0,		uint,	0,		8,		4 },	// R
1960 					{	0,		uint,	8,		8,		4 },	// G
1961 					{	0,		uint,	16,		8,		4 },	// B
1962 					{	0,		uint,	24,		8,		4 }		// A
1963 				}
1964 			};
1965 			return desc;
1966 		}
1967 
1968 		case VK_FORMAT_R16G16B16A16_UINT:
1969 		{
1970 			const PlanarFormatDescription	desc	=
1971 			{
1972 				1, // planes
1973 				chanR | chanG | chanB | chanA,
1974 				1,1,
1975 				{
1976 				//		Size	WDiv	HDiv	planeCompatibleFormat
1977 					{	8,		1,		1,		VK_FORMAT_R16G16B16A16_UINT },
1978 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1979 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
1980 				},
1981 				{
1982 				//		Plane	Type	Offs	Size	Stride
1983 					{	0,		uint,	0,		16,		8 },	// R
1984 					{	0,		uint,	16,		16,		8 },	// G
1985 					{	0,		uint,	32,		16,		8 },	// B
1986 					{	0,		uint,	48,		16,		8 }		// A
1987 				}
1988 			};
1989 			return desc;
1990 		}
1991 
1992 		case VK_FORMAT_R32G32B32A32_UINT:
1993 		{
1994 			const PlanarFormatDescription	desc	=
1995 			{
1996 				1, // planes
1997 				chanR | chanG | chanB | chanA,
1998 				1,1,
1999 				{
2000 				//		Size	WDiv	HDiv	planeCompatibleFormat
2001 					{	16,		1,		1,		VK_FORMAT_R32G32B32A32_UINT },
2002 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2003 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2004 				},
2005 				{
2006 				//		Plane	Type	Offs	Size	Stride
2007 					{	0,		uint,	0,		32,		16 },	// R
2008 					{	0,		uint,	32,		32,		16 },	// G
2009 					{	0,		uint,	64,		32,		16 },	// B
2010 					{	0,		uint,	96,		32,		16 }	// A
2011 				}
2012 			};
2013 			return desc;
2014 		}
2015 
2016 		case VK_FORMAT_R8G8B8A8_SNORM:
2017 		{
2018 			const PlanarFormatDescription	desc	=
2019 			{
2020 				1, // planes
2021 				chanR | chanG | chanB | chanA,
2022 				1,1,
2023 				{
2024 				//		Size	WDiv	HDiv	planeCompatibleFormat
2025 					{	4,		1,		1,		VK_FORMAT_R8G8B8A8_SNORM },
2026 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2027 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2028 				},
2029 				{
2030 				//		Plane	Type	Offs	Size	Stride
2031 					{	0,		snorm,	0,		8,		4 },	// R
2032 					{	0,		snorm,	8,		8,		4 },	// G
2033 					{	0,		snorm,	16,		8,		4 },	// B
2034 					{	0,		snorm,	24,		8,		4 }		// A
2035 				}
2036 			};
2037 			return desc;
2038 		}
2039 
2040 		case VK_FORMAT_R16G16B16A16_SNORM:
2041 		{
2042 			const PlanarFormatDescription	desc	=
2043 			{
2044 				1, // planes
2045 				chanR | chanG | chanB | chanA,
2046 				1,1,
2047 				{
2048 				//		Size	WDiv	HDiv	planeCompatibleFormat
2049 					{	8,		1,		1,		VK_FORMAT_R16G16B16A16_SNORM },
2050 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2051 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2052 				},
2053 				{
2054 				//		Plane	Type	Offs	Size	Stride
2055 					{	0,		snorm,	0,		16,		8 },	// R
2056 					{	0,		snorm,	16,		16,		8 },	// G
2057 					{	0,		snorm,	32,		16,		8 },	// B
2058 					{	0,		snorm,	48,		16,		8 }		// A
2059 				}
2060 			};
2061 			return desc;
2062 		}
2063 		case VK_FORMAT_R32_SFLOAT:
2064 		case VK_FORMAT_D32_SFLOAT:
2065 		{
2066 			const PlanarFormatDescription	desc	=
2067 			{
2068 				1, // planes
2069 				chanR,
2070 				1,1,
2071 				{
2072 				//		Size	WDiv	HDiv	planeCompatibleFormat
2073 					{	4,		1,		1,		VK_FORMAT_R32_SFLOAT },
2074 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2075 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2076 				},
2077 				{
2078 				//		Plane	Type	Offs	Size	Stride
2079 					{	0,		sfloat,	0,		32,		4 },	// R
2080 					{	0,		0,		0,		0,		0 },	// G
2081 					{	0,		0,		0,		0,		0 },	// B
2082 					{	0,		0,		0,		0,		0 }		// A
2083 				}
2084 			};
2085 			return desc;
2086 		}
2087 
2088 		case VK_FORMAT_D16_UNORM:
2089 		{
2090 			const PlanarFormatDescription	desc	=
2091 			{
2092 				1, // planes
2093 				chanR,
2094 				1,1,
2095 				{
2096 				//		Size	WDiv	HDiv	planeCompatibleFormat
2097 					{	2,		1,		1,		VK_FORMAT_D16_UNORM },
2098 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2099 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2100 				},
2101 				{
2102 				//		Plane	Type	Offs	Size	Stride
2103 					{	0,		unorm,	0,		16,		2 },	// R
2104 					{	0,		0,		0,		0,		0 },	// G
2105 					{	0,		0,		0,		0,		0 },	// B
2106 					{	0,		0,		0,		0,		0 }		// A
2107 				}
2108 			};
2109 			return desc;
2110 		}
2111 
2112 		case VK_FORMAT_S8_UINT:
2113 		{
2114 			const PlanarFormatDescription	desc	=
2115 			{
2116 				1, // planes
2117 				chanR,
2118 				1,1,
2119 				{
2120 				//		Size	WDiv	HDiv	planeCompatibleFormat
2121 					{	1,		1,		1,		VK_FORMAT_S8_UINT },
2122 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2123 					{	0,		0,		0,		VK_FORMAT_UNDEFINED},
2124 				},
2125 				{
2126 				//		Plane	Type	Offs	Size	Stride
2127 					{	0,		uint,	0,		8,		1 },	// R
2128 					{	0,		0,		0,		0,		0 },	// G
2129 					{	0,		0,		0,		0,		0 },	// B
2130 					{	0,		0,		0,		0,		0 }		// A
2131 				}
2132 			};
2133 			return desc;
2134 		}
2135 
2136 		case VK_FORMAT_R32G32B32A32_SFLOAT:
2137 		{
2138 			const PlanarFormatDescription	desc	=
2139 			{
2140 				1, // planes
2141 				chanR|chanG|chanB|chanA,
2142 				1,1,
2143 				{
2144 				//		Size	WDiv	HDiv	planeCompatibleFormat
2145 					{	16,		1,		1,		VK_FORMAT_R32G32B32A32_SFLOAT },
2146 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2147 					{	0,		0,		0,		VK_FORMAT_UNDEFINED },
2148 				},
2149 				{
2150 				//		Plane	Type	Offs	Size	Stride
2151 					{	0,		sfloat,	0,		32,		16 },	// R
2152 					{	0,		sfloat,	32,		32,		16 },	// G
2153 					{	0,		sfloat,	64,		32,		16 },	// B
2154 					{	0,		sfloat,	96,		32,		16 },	// A
2155 				}
2156 			};
2157 			return desc;
2158 		}
2159 
2160 
2161 		default:
2162 			TCU_THROW(InternalError, "Not implemented");
2163 	}
2164 }
2165 
getPlanarFormatDescription(VkFormat format)2166 PlanarFormatDescription getPlanarFormatDescription (VkFormat format)
2167 {
2168 	if (isYCbCrFormat(format))
2169 		return getYCbCrPlanarFormatDescription(format);
2170 	else
2171 		return getCorePlanarFormatDescription(format);
2172 }
2173 
getPlaneCount(VkFormat format)2174 int getPlaneCount (VkFormat format)
2175 {
2176 	switch (format)
2177 	{
2178 		case VK_FORMAT_G8B8G8R8_422_UNORM_KHR:
2179 		case VK_FORMAT_B8G8R8G8_422_UNORM_KHR:
2180 		case VK_FORMAT_R10X6_UNORM_PACK16_KHR:
2181 		case VK_FORMAT_R10X6G10X6_UNORM_2PACK16_KHR:
2182 		case VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16_KHR:
2183 		case VK_FORMAT_G10X6B10X6G10X6R10X6_422_UNORM_4PACK16_KHR:
2184 		case VK_FORMAT_B10X6G10X6R10X6G10X6_422_UNORM_4PACK16_KHR:
2185 		case VK_FORMAT_R12X4_UNORM_PACK16_KHR:
2186 		case VK_FORMAT_R12X4G12X4_UNORM_2PACK16_KHR:
2187 		case VK_FORMAT_R12X4G12X4B12X4A12X4_UNORM_4PACK16_KHR:
2188 		case VK_FORMAT_G12X4B12X4G12X4R12X4_422_UNORM_4PACK16_KHR:
2189 		case VK_FORMAT_B12X4G12X4R12X4G12X4_422_UNORM_4PACK16_KHR:
2190 		case VK_FORMAT_G16B16G16R16_422_UNORM_KHR:
2191 		case VK_FORMAT_B16G16R16G16_422_UNORM_KHR:
2192 			return 1;
2193 
2194 		case VK_FORMAT_G8_B8R8_2PLANE_420_UNORM_KHR:
2195 		case VK_FORMAT_G8_B8R8_2PLANE_422_UNORM_KHR:
2196 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_420_UNORM_3PACK16_KHR:
2197 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_422_UNORM_3PACK16_KHR:
2198 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_420_UNORM_3PACK16_KHR:
2199 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_422_UNORM_3PACK16_KHR:
2200 		case VK_FORMAT_G16_B16R16_2PLANE_420_UNORM_KHR:
2201 		case VK_FORMAT_G16_B16R16_2PLANE_422_UNORM_KHR:
2202 			return 2;
2203 
2204 		case VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM_KHR:
2205 		case VK_FORMAT_G8_B8_R8_3PLANE_422_UNORM_KHR:
2206 		case VK_FORMAT_G8_B8_R8_3PLANE_444_UNORM_KHR:
2207 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_420_UNORM_3PACK16_KHR:
2208 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_422_UNORM_3PACK16_KHR:
2209 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_444_UNORM_3PACK16_KHR:
2210 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_420_UNORM_3PACK16_KHR:
2211 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_422_UNORM_3PACK16_KHR:
2212 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_444_UNORM_3PACK16_KHR:
2213 		case VK_FORMAT_G16_B16_R16_3PLANE_420_UNORM_KHR:
2214 		case VK_FORMAT_G16_B16_R16_3PLANE_422_UNORM_KHR:
2215 		case VK_FORMAT_G16_B16_R16_3PLANE_444_UNORM_KHR:
2216 			return 3;
2217 
2218 		default:
2219 			DE_FATAL("Not YCbCr format");
2220 			return 0;
2221 	}
2222 }
2223 
getMipmapCount(VkFormat format,const vk::PlanarFormatDescription & formatDescription,const VkImageFormatProperties & imageFormatProperties,const VkExtent3D & extent)2224 deUint32 getMipmapCount(VkFormat format, const vk::PlanarFormatDescription& formatDescription, const VkImageFormatProperties& imageFormatProperties, const VkExtent3D& extent)
2225 {
2226 	if (isYCbCrFormat(format))
2227 		return 1;
2228 	tcu::UVec3 imageAlignment	= getImageSizeAlignment(formatDescription);
2229 	deUint32 mipmapEdge			= std::max(std::max(extent.width, extent.height), extent.depth);
2230 	if (imageAlignment.x() > 1)
2231 		mipmapEdge = std::min(mipmapEdge, extent.width / imageAlignment.x());
2232 	if (imageAlignment.y() > 1)
2233 		mipmapEdge = std::min(mipmapEdge, extent.height / imageAlignment.y());
2234 	if (imageAlignment.z() > 1)
2235 		mipmapEdge = std::min(mipmapEdge, extent.depth / imageAlignment.z());
2236 	return std::min(static_cast<deUint32>(deFloatLog2(static_cast<float>(mipmapEdge))) + 1u, imageFormatProperties.maxMipLevels);
2237 }
2238 
getPlaneSizeInBytes(const PlanarFormatDescription & formatInfo,const VkExtent3D & baseExtents,const deUint32 planeNdx,const deUint32 mipmapLevel,const deUint32 mipmapMemoryAlignment)2239 deUint32 getPlaneSizeInBytes (const PlanarFormatDescription&	formatInfo,
2240 							  const VkExtent3D&					baseExtents,
2241 							  const deUint32					planeNdx,
2242 							  const deUint32					mipmapLevel,
2243 							  const deUint32					mipmapMemoryAlignment)
2244 {
2245 	VkExtent3D imageExtent	= getPlaneExtent(formatInfo, baseExtents, planeNdx, mipmapLevel);
2246 	imageExtent.width		/= formatInfo.blockWidth;
2247 	imageExtent.height		/= formatInfo.blockHeight;
2248 	return deAlign32( formatInfo.planes[planeNdx].elementSizeBytes * imageExtent.width * imageExtent.height * imageExtent.depth, mipmapMemoryAlignment);
2249 }
2250 
getPlaneSizeInBytes(const PlanarFormatDescription & formatInfo,const tcu::UVec2 & baseExtents,const deUint32 planeNdx,const deUint32 mipmapLevel,const deUint32 mipmapMemoryAlignment)2251 deUint32 getPlaneSizeInBytes (const PlanarFormatDescription&	formatInfo,
2252 							  const tcu::UVec2&					baseExtents,
2253 							  const deUint32					planeNdx,
2254 							  const deUint32					mipmapLevel,
2255 							  const deUint32					mipmapMemoryAlignment)
2256 {
2257 	tcu::UVec2 mipExtents = getPlaneExtent(formatInfo, baseExtents, planeNdx, mipmapLevel) / tcu::UVec2(formatInfo.blockWidth, formatInfo.blockHeight);
2258 	return deAlign32( formatInfo.planes[planeNdx].elementSizeBytes * mipExtents.x() * mipExtents.y(), mipmapMemoryAlignment);
2259 }
2260 
getPlaneExtent(const PlanarFormatDescription & formatInfo,const VkExtent3D & baseExtents,const deUint32 planeNdx,const deUint32 mipmapLevel)2261 VkExtent3D getPlaneExtent(const PlanarFormatDescription&	formatInfo,
2262 						  const VkExtent3D&					baseExtents,
2263 						  const deUint32					planeNdx,
2264 						  const deUint32					mipmapLevel)
2265 {
2266 	deUint32	widthDivisor	= formatInfo.planes[planeNdx].widthDivisor;
2267 	deUint32	heightDivisor	= formatInfo.planes[planeNdx].heightDivisor;
2268 	deUint32	depthDivisor	= 1u;
2269 	VkExtent3D	mip0Extents		{ baseExtents.width / widthDivisor, baseExtents.height / heightDivisor, baseExtents.depth / depthDivisor };
2270 
2271 	return mipLevelExtents(mip0Extents, mipmapLevel);
2272 }
2273 
getPlaneExtent(const PlanarFormatDescription & formatInfo,const tcu::UVec2 & baseExtents,const deUint32 planeNdx,const deUint32 mipmapLevel)2274 tcu::UVec2 getPlaneExtent(const PlanarFormatDescription&	formatInfo,
2275 						  const tcu::UVec2&					baseExtents,
2276 						  const deUint32					planeNdx,
2277 						  const deUint32					mipmapLevel)
2278 {
2279 	deUint32 widthDivisor			= formatInfo.planes[planeNdx].widthDivisor;
2280 	deUint32 heightDivisor			= formatInfo.planes[planeNdx].heightDivisor;
2281 	tcu::UVec2 mip0Extents			{ baseExtents.x() / widthDivisor, baseExtents.y() / heightDivisor };
2282 
2283 	return tcu::UVec2
2284 	{
2285 		std::max(mip0Extents.x() >> mipmapLevel, 1u),
2286 		std::max(mip0Extents.y() >> mipmapLevel, 1u)
2287 	};
2288 }
2289 
getImageSizeAlignment(VkFormat format)2290 tcu::UVec3 getImageSizeAlignment(VkFormat format)
2291 {
2292 	return getImageSizeAlignment(getPlanarFormatDescription(format));
2293 }
2294 
getImageSizeAlignment(const PlanarFormatDescription & formatInfo)2295 tcu::UVec3 getImageSizeAlignment(const PlanarFormatDescription&	formatInfo)
2296 {
2297 	tcu::UVec3 imgAlignment{ formatInfo.blockWidth, formatInfo.blockHeight, 1 };
2298 	for (deUint32 planeNdx = 0; planeNdx < formatInfo.numPlanes; ++planeNdx)
2299 	{
2300 		imgAlignment.x() = std::max(imgAlignment.x(), static_cast<deUint32>(formatInfo.planes[planeNdx].widthDivisor));
2301 		imgAlignment.y() = std::max(imgAlignment.y(), static_cast<deUint32>(formatInfo.planes[planeNdx].heightDivisor));
2302 	}
2303 	return imgAlignment;
2304 }
2305 
getBlockExtent(VkFormat format)2306 tcu::UVec2 getBlockExtent(VkFormat format)
2307 {
2308 	return getBlockExtent(getPlanarFormatDescription(format));
2309 }
2310 
getBlockExtent(const PlanarFormatDescription & formatInfo)2311 tcu::UVec2 getBlockExtent(const PlanarFormatDescription& formatInfo)
2312 {
2313 	return tcu::UVec2{ formatInfo.blockWidth, formatInfo.blockHeight };
2314 }
2315 
getPlaneCompatibleFormat(VkFormat format,deUint32 planeNdx)2316 VkFormat getPlaneCompatibleFormat(VkFormat format, deUint32 planeNdx)
2317 {
2318 	return getPlaneCompatibleFormat(getPlanarFormatDescription(format), planeNdx);
2319 }
2320 
getPlaneCompatibleFormat(const PlanarFormatDescription & formatInfo,deUint32 planeNdx)2321 VkFormat getPlaneCompatibleFormat(const PlanarFormatDescription& formatInfo, deUint32 planeNdx)
2322 {
2323 	DE_ASSERT(planeNdx < formatInfo.numPlanes);
2324 	return formatInfo.planes[planeNdx].planeCompatibleFormat;
2325 }
2326 
getPlaneAspect(deUint32 planeNdx)2327 VkImageAspectFlagBits getPlaneAspect (deUint32 planeNdx)
2328 {
2329 	DE_ASSERT(de::inBounds(planeNdx, 0u, 3u));
2330 	return (VkImageAspectFlagBits)(VK_IMAGE_ASPECT_PLANE_0_BIT_KHR << planeNdx);
2331 }
2332 
getAspectPlaneNdx(VkImageAspectFlagBits flags)2333 deUint32 getAspectPlaneNdx (VkImageAspectFlagBits flags)
2334 {
2335 	switch (flags)
2336 	{
2337 		case VK_IMAGE_ASPECT_PLANE_0_BIT_KHR:	return 0;
2338 		case VK_IMAGE_ASPECT_PLANE_1_BIT_KHR:	return 1;
2339 		case VK_IMAGE_ASPECT_PLANE_2_BIT_KHR:	return 2;
2340 		default:
2341 			DE_FATAL("Invalid plane aspect");
2342 			return 0;
2343 	}
2344 }
2345 
isChromaSubsampled(VkFormat format)2346 bool isChromaSubsampled (VkFormat format)
2347 {
2348 	switch (format)
2349 	{
2350 		case VK_FORMAT_G8B8G8R8_422_UNORM_KHR:
2351 		case VK_FORMAT_B8G8R8G8_422_UNORM_KHR:
2352 		case VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM_KHR:
2353 		case VK_FORMAT_G8_B8R8_2PLANE_420_UNORM_KHR:
2354 		case VK_FORMAT_G8_B8_R8_3PLANE_422_UNORM_KHR:
2355 		case VK_FORMAT_G8_B8R8_2PLANE_422_UNORM_KHR:
2356 		case VK_FORMAT_G8_B8_R8_3PLANE_444_UNORM_KHR:
2357 		case VK_FORMAT_G10X6B10X6G10X6R10X6_422_UNORM_4PACK16_KHR:
2358 		case VK_FORMAT_B10X6G10X6R10X6G10X6_422_UNORM_4PACK16_KHR:
2359 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_420_UNORM_3PACK16_KHR:
2360 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_420_UNORM_3PACK16_KHR:
2361 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_422_UNORM_3PACK16_KHR:
2362 		case VK_FORMAT_G10X6_B10X6R10X6_2PLANE_422_UNORM_3PACK16_KHR:
2363 		case VK_FORMAT_G10X6_B10X6_R10X6_3PLANE_444_UNORM_3PACK16_KHR:
2364 		case VK_FORMAT_G12X4B12X4G12X4R12X4_422_UNORM_4PACK16_KHR:
2365 		case VK_FORMAT_B12X4G12X4R12X4G12X4_422_UNORM_4PACK16_KHR:
2366 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_420_UNORM_3PACK16_KHR:
2367 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_420_UNORM_3PACK16_KHR:
2368 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_422_UNORM_3PACK16_KHR:
2369 		case VK_FORMAT_G12X4_B12X4R12X4_2PLANE_422_UNORM_3PACK16_KHR:
2370 		case VK_FORMAT_G12X4_B12X4_R12X4_3PLANE_444_UNORM_3PACK16_KHR:
2371 		case VK_FORMAT_G16B16G16R16_422_UNORM_KHR:
2372 		case VK_FORMAT_B16G16R16G16_422_UNORM_KHR:
2373 		case VK_FORMAT_G16_B16_R16_3PLANE_420_UNORM_KHR:
2374 		case VK_FORMAT_G16_B16R16_2PLANE_420_UNORM_KHR:
2375 		case VK_FORMAT_G16_B16_R16_3PLANE_422_UNORM_KHR:
2376 		case VK_FORMAT_G16_B16R16_2PLANE_422_UNORM_KHR:
2377 		case VK_FORMAT_G16_B16_R16_3PLANE_444_UNORM_KHR:
2378 			return true;
2379 
2380 		default:
2381 			return false;
2382 	}
2383 }
2384 
isSupportedByFramework(VkFormat format)2385 bool isSupportedByFramework (VkFormat format)
2386 {
2387 	if (format == VK_FORMAT_UNDEFINED || format > VK_CORE_FORMAT_LAST)
2388 		return false;
2389 
2390 	switch (format)
2391 	{
2392 		case VK_FORMAT_R64_UINT:
2393 		case VK_FORMAT_R64_SINT:
2394 		case VK_FORMAT_R64_SFLOAT:
2395 		case VK_FORMAT_R64G64_UINT:
2396 		case VK_FORMAT_R64G64_SINT:
2397 		case VK_FORMAT_R64G64_SFLOAT:
2398 		case VK_FORMAT_R64G64B64_UINT:
2399 		case VK_FORMAT_R64G64B64_SINT:
2400 		case VK_FORMAT_R64G64B64_SFLOAT:
2401 		case VK_FORMAT_R64G64B64A64_UINT:
2402 		case VK_FORMAT_R64G64B64A64_SINT:
2403 		case VK_FORMAT_R64G64B64A64_SFLOAT:
2404 			// \todo [2016-12-01 pyry] Support 64-bit channel types
2405 			return false;
2406 
2407 		case VK_FORMAT_BC1_RGB_UNORM_BLOCK:
2408 		case VK_FORMAT_BC1_RGB_SRGB_BLOCK:
2409 		case VK_FORMAT_BC1_RGBA_UNORM_BLOCK:
2410 		case VK_FORMAT_BC1_RGBA_SRGB_BLOCK:
2411 		case VK_FORMAT_BC2_UNORM_BLOCK:
2412 		case VK_FORMAT_BC2_SRGB_BLOCK:
2413 		case VK_FORMAT_BC3_UNORM_BLOCK:
2414 		case VK_FORMAT_BC3_SRGB_BLOCK:
2415 		case VK_FORMAT_BC4_UNORM_BLOCK:
2416 		case VK_FORMAT_BC4_SNORM_BLOCK:
2417 		case VK_FORMAT_BC5_UNORM_BLOCK:
2418 		case VK_FORMAT_BC5_SNORM_BLOCK:
2419 		case VK_FORMAT_BC6H_UFLOAT_BLOCK:
2420 		case VK_FORMAT_BC6H_SFLOAT_BLOCK:
2421 		case VK_FORMAT_BC7_UNORM_BLOCK:
2422 		case VK_FORMAT_BC7_SRGB_BLOCK:
2423 			return false;
2424 
2425 		default:
2426 			return true;
2427 	}
2428 }
2429 
checkImageSupport(const InstanceInterface & vki,VkPhysicalDevice physicalDevice,const VkImageCreateInfo & imageCreateInfo)2430 void checkImageSupport (const InstanceInterface& vki, VkPhysicalDevice physicalDevice, const VkImageCreateInfo& imageCreateInfo)
2431 {
2432 	VkImageFormatProperties imageFormatProperties;
2433 
2434 	if (vki.getPhysicalDeviceImageFormatProperties(physicalDevice, imageCreateInfo.format, imageCreateInfo.imageType,
2435 												   imageCreateInfo.tiling, imageCreateInfo.usage, imageCreateInfo.flags,
2436 												   &imageFormatProperties))
2437 	{
2438 		TCU_THROW(NotSupportedError, "Image format not supported.");
2439 	}
2440 	if (((VkSampleCountFlagBits)imageFormatProperties.sampleCounts & imageCreateInfo.samples) == 0)
2441 	{
2442 		TCU_THROW(NotSupportedError, "Sample count not supported.");
2443 	}
2444 	if (imageFormatProperties.maxArrayLayers < imageCreateInfo.arrayLayers)
2445 	{
2446 		TCU_THROW(NotSupportedError, "Layer count not supported.");
2447 	}
2448 }
2449 
mapTextureFormat(const tcu::TextureFormat & format)2450 VkFormat mapTextureFormat (const tcu::TextureFormat& format)
2451 {
2452 	DE_STATIC_ASSERT(tcu::TextureFormat::CHANNELORDER_LAST < (1<<16));
2453 	DE_STATIC_ASSERT(tcu::TextureFormat::CHANNELTYPE_LAST < (1<<16));
2454 
2455 #define PACK_FMT(ORDER, TYPE) ((int(ORDER) << 16) | int(TYPE))
2456 #define FMT_CASE(ORDER, TYPE) PACK_FMT(tcu::TextureFormat::ORDER, tcu::TextureFormat::TYPE)
2457 
2458 	// update this mapping if VkFormat changes
2459 	DE_STATIC_ASSERT(VK_CORE_FORMAT_LAST == 185);
2460 
2461 	switch (PACK_FMT(format.order, format.type))
2462 	{
2463 		case FMT_CASE(RG, UNORM_BYTE_44):					return VK_FORMAT_R4G4_UNORM_PACK8;
2464 		case FMT_CASE(RGB, UNORM_SHORT_565):				return VK_FORMAT_R5G6B5_UNORM_PACK16;
2465 		case FMT_CASE(RGBA, UNORM_SHORT_4444):				return VK_FORMAT_R4G4B4A4_UNORM_PACK16;
2466 		case FMT_CASE(RGBA, UNORM_SHORT_5551):				return VK_FORMAT_R5G5B5A1_UNORM_PACK16;
2467 
2468 		case FMT_CASE(BGR, UNORM_SHORT_565):				return VK_FORMAT_B5G6R5_UNORM_PACK16;
2469 		case FMT_CASE(BGRA, UNORM_SHORT_4444):				return VK_FORMAT_B4G4R4A4_UNORM_PACK16;
2470 		case FMT_CASE(BGRA, UNORM_SHORT_5551):				return VK_FORMAT_B5G5R5A1_UNORM_PACK16;
2471 
2472 		case FMT_CASE(ARGB, UNORM_SHORT_1555):				return VK_FORMAT_A1R5G5B5_UNORM_PACK16;
2473 
2474 		case FMT_CASE(R, UNORM_INT8):						return VK_FORMAT_R8_UNORM;
2475 		case FMT_CASE(R, SNORM_INT8):						return VK_FORMAT_R8_SNORM;
2476 		case FMT_CASE(R, UNSIGNED_INT8):					return VK_FORMAT_R8_UINT;
2477 		case FMT_CASE(R, SIGNED_INT8):						return VK_FORMAT_R8_SINT;
2478 		case FMT_CASE(sR, UNORM_INT8):						return VK_FORMAT_R8_SRGB;
2479 
2480 		case FMT_CASE(RG, UNORM_INT8):						return VK_FORMAT_R8G8_UNORM;
2481 		case FMT_CASE(RG, SNORM_INT8):						return VK_FORMAT_R8G8_SNORM;
2482 		case FMT_CASE(RG, UNSIGNED_INT8):					return VK_FORMAT_R8G8_UINT;
2483 		case FMT_CASE(RG, SIGNED_INT8):						return VK_FORMAT_R8G8_SINT;
2484 		case FMT_CASE(sRG, UNORM_INT8):						return VK_FORMAT_R8G8_SRGB;
2485 
2486 		case FMT_CASE(RGB, UNORM_INT8):						return VK_FORMAT_R8G8B8_UNORM;
2487 		case FMT_CASE(RGB, SNORM_INT8):						return VK_FORMAT_R8G8B8_SNORM;
2488 		case FMT_CASE(RGB, UNSIGNED_INT8):					return VK_FORMAT_R8G8B8_UINT;
2489 		case FMT_CASE(RGB, SIGNED_INT8):					return VK_FORMAT_R8G8B8_SINT;
2490 		case FMT_CASE(sRGB, UNORM_INT8):					return VK_FORMAT_R8G8B8_SRGB;
2491 
2492 		case FMT_CASE(RGBA, UNORM_INT8):					return VK_FORMAT_R8G8B8A8_UNORM;
2493 		case FMT_CASE(RGBA, SNORM_INT8):					return VK_FORMAT_R8G8B8A8_SNORM;
2494 		case FMT_CASE(RGBA, UNSIGNED_INT8):					return VK_FORMAT_R8G8B8A8_UINT;
2495 		case FMT_CASE(RGBA, SIGNED_INT8):					return VK_FORMAT_R8G8B8A8_SINT;
2496 		case FMT_CASE(sRGBA, UNORM_INT8):					return VK_FORMAT_R8G8B8A8_SRGB;
2497 
2498 		case FMT_CASE(RGBA, UNORM_INT_1010102_REV):			return VK_FORMAT_A2B10G10R10_UNORM_PACK32;
2499 		case FMT_CASE(RGBA, SNORM_INT_1010102_REV):			return VK_FORMAT_A2B10G10R10_SNORM_PACK32;
2500 		case FMT_CASE(RGBA, UNSIGNED_INT_1010102_REV):		return VK_FORMAT_A2B10G10R10_UINT_PACK32;
2501 		case FMT_CASE(RGBA, SIGNED_INT_1010102_REV):		return VK_FORMAT_A2B10G10R10_SINT_PACK32;
2502 
2503 		case FMT_CASE(R, UNORM_INT16):						return VK_FORMAT_R16_UNORM;
2504 		case FMT_CASE(R, SNORM_INT16):						return VK_FORMAT_R16_SNORM;
2505 		case FMT_CASE(R, UNSIGNED_INT16):					return VK_FORMAT_R16_UINT;
2506 		case FMT_CASE(R, SIGNED_INT16):						return VK_FORMAT_R16_SINT;
2507 		case FMT_CASE(R, HALF_FLOAT):						return VK_FORMAT_R16_SFLOAT;
2508 
2509 		case FMT_CASE(RG, UNORM_INT16):						return VK_FORMAT_R16G16_UNORM;
2510 		case FMT_CASE(RG, SNORM_INT16):						return VK_FORMAT_R16G16_SNORM;
2511 		case FMT_CASE(RG, UNSIGNED_INT16):					return VK_FORMAT_R16G16_UINT;
2512 		case FMT_CASE(RG, SIGNED_INT16):					return VK_FORMAT_R16G16_SINT;
2513 		case FMT_CASE(RG, HALF_FLOAT):						return VK_FORMAT_R16G16_SFLOAT;
2514 
2515 		case FMT_CASE(RGB, UNORM_INT16):					return VK_FORMAT_R16G16B16_UNORM;
2516 		case FMT_CASE(RGB, SNORM_INT16):					return VK_FORMAT_R16G16B16_SNORM;
2517 		case FMT_CASE(RGB, UNSIGNED_INT16):					return VK_FORMAT_R16G16B16_UINT;
2518 		case FMT_CASE(RGB, SIGNED_INT16):					return VK_FORMAT_R16G16B16_SINT;
2519 		case FMT_CASE(RGB, HALF_FLOAT):						return VK_FORMAT_R16G16B16_SFLOAT;
2520 
2521 		case FMT_CASE(RGBA, UNORM_INT16):					return VK_FORMAT_R16G16B16A16_UNORM;
2522 		case FMT_CASE(RGBA, SNORM_INT16):					return VK_FORMAT_R16G16B16A16_SNORM;
2523 		case FMT_CASE(RGBA, UNSIGNED_INT16):				return VK_FORMAT_R16G16B16A16_UINT;
2524 		case FMT_CASE(RGBA, SIGNED_INT16):					return VK_FORMAT_R16G16B16A16_SINT;
2525 		case FMT_CASE(RGBA, HALF_FLOAT):					return VK_FORMAT_R16G16B16A16_SFLOAT;
2526 
2527 		case FMT_CASE(R, UNSIGNED_INT32):					return VK_FORMAT_R32_UINT;
2528 		case FMT_CASE(R, SIGNED_INT32):						return VK_FORMAT_R32_SINT;
2529 		case FMT_CASE(R, FLOAT):							return VK_FORMAT_R32_SFLOAT;
2530 
2531 		case FMT_CASE(RG, UNSIGNED_INT32):					return VK_FORMAT_R32G32_UINT;
2532 		case FMT_CASE(RG, SIGNED_INT32):					return VK_FORMAT_R32G32_SINT;
2533 		case FMT_CASE(RG, FLOAT):							return VK_FORMAT_R32G32_SFLOAT;
2534 
2535 		case FMT_CASE(RGB, UNSIGNED_INT32):					return VK_FORMAT_R32G32B32_UINT;
2536 		case FMT_CASE(RGB, SIGNED_INT32):					return VK_FORMAT_R32G32B32_SINT;
2537 		case FMT_CASE(RGB, FLOAT):							return VK_FORMAT_R32G32B32_SFLOAT;
2538 
2539 		case FMT_CASE(RGBA, UNSIGNED_INT32):				return VK_FORMAT_R32G32B32A32_UINT;
2540 		case FMT_CASE(RGBA, SIGNED_INT32):					return VK_FORMAT_R32G32B32A32_SINT;
2541 		case FMT_CASE(RGBA, FLOAT):							return VK_FORMAT_R32G32B32A32_SFLOAT;
2542 
2543 		case FMT_CASE(R, FLOAT64):							return VK_FORMAT_R64_SFLOAT;
2544 		case FMT_CASE(RG, FLOAT64):							return VK_FORMAT_R64G64_SFLOAT;
2545 		case FMT_CASE(RGB, FLOAT64):						return VK_FORMAT_R64G64B64_SFLOAT;
2546 		case FMT_CASE(RGBA, FLOAT64):						return VK_FORMAT_R64G64B64A64_SFLOAT;
2547 
2548 		case FMT_CASE(RGB, UNSIGNED_INT_11F_11F_10F_REV):	return VK_FORMAT_B10G11R11_UFLOAT_PACK32;
2549 		case FMT_CASE(RGB, UNSIGNED_INT_999_E5_REV):		return VK_FORMAT_E5B9G9R9_UFLOAT_PACK32;
2550 
2551 		case FMT_CASE(BGR, UNORM_INT8):						return VK_FORMAT_B8G8R8_UNORM;
2552 		case FMT_CASE(BGR, SNORM_INT8):						return VK_FORMAT_B8G8R8_SNORM;
2553 		case FMT_CASE(BGR, UNSIGNED_INT8):					return VK_FORMAT_B8G8R8_UINT;
2554 		case FMT_CASE(BGR, SIGNED_INT8):					return VK_FORMAT_B8G8R8_SINT;
2555 		case FMT_CASE(sBGR, UNORM_INT8):					return VK_FORMAT_B8G8R8_SRGB;
2556 
2557 		case FMT_CASE(BGRA, UNORM_INT8):					return VK_FORMAT_B8G8R8A8_UNORM;
2558 		case FMT_CASE(BGRA, SNORM_INT8):					return VK_FORMAT_B8G8R8A8_SNORM;
2559 		case FMT_CASE(BGRA, UNSIGNED_INT8):					return VK_FORMAT_B8G8R8A8_UINT;
2560 		case FMT_CASE(BGRA, SIGNED_INT8):					return VK_FORMAT_B8G8R8A8_SINT;
2561 		case FMT_CASE(sBGRA, UNORM_INT8):					return VK_FORMAT_B8G8R8A8_SRGB;
2562 
2563 		case FMT_CASE(BGRA, UNORM_INT_1010102_REV):			return VK_FORMAT_A2R10G10B10_UNORM_PACK32;
2564 		case FMT_CASE(BGRA, SNORM_INT_1010102_REV):			return VK_FORMAT_A2R10G10B10_SNORM_PACK32;
2565 		case FMT_CASE(BGRA, UNSIGNED_INT_1010102_REV):		return VK_FORMAT_A2R10G10B10_UINT_PACK32;
2566 		case FMT_CASE(BGRA, SIGNED_INT_1010102_REV):		return VK_FORMAT_A2R10G10B10_SINT_PACK32;
2567 
2568 		case FMT_CASE(D, UNORM_INT16):						return VK_FORMAT_D16_UNORM;
2569 		case FMT_CASE(D, UNSIGNED_INT_24_8_REV):			return VK_FORMAT_X8_D24_UNORM_PACK32;
2570 		case FMT_CASE(D, FLOAT):							return VK_FORMAT_D32_SFLOAT;
2571 
2572 		case FMT_CASE(S, UNSIGNED_INT8):					return VK_FORMAT_S8_UINT;
2573 
2574 		case FMT_CASE(DS, UNSIGNED_INT_16_8_8):				return VK_FORMAT_D16_UNORM_S8_UINT;
2575 		case FMT_CASE(DS, UNSIGNED_INT_24_8_REV):			return VK_FORMAT_D24_UNORM_S8_UINT;
2576 		case FMT_CASE(DS, FLOAT_UNSIGNED_INT_24_8_REV):		return VK_FORMAT_D32_SFLOAT_S8_UINT;
2577 
2578 		case FMT_CASE(R,	UNORM_SHORT_10):				return VK_FORMAT_R10X6_UNORM_PACK16_KHR;
2579 		case FMT_CASE(RG,	UNORM_SHORT_10):				return VK_FORMAT_R10X6G10X6_UNORM_2PACK16_KHR;
2580 		case FMT_CASE(RGBA,	UNORM_SHORT_10):				return VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16_KHR;
2581 
2582 		case FMT_CASE(R,	UNORM_SHORT_12):				return VK_FORMAT_R12X4_UNORM_PACK16_KHR;
2583 		case FMT_CASE(RG,	UNORM_SHORT_12):				return VK_FORMAT_R12X4G12X4_UNORM_2PACK16_KHR;
2584 		case FMT_CASE(RGBA,	UNORM_SHORT_12):				return VK_FORMAT_R12X4G12X4B12X4A12X4_UNORM_4PACK16_KHR;
2585 
2586 		case FMT_CASE(R,	USCALED_INT8):					return VK_FORMAT_R8_USCALED;
2587 		case FMT_CASE(RG,	USCALED_INT8):					return VK_FORMAT_R8G8_USCALED;
2588 		case FMT_CASE(RGB,	USCALED_INT8):					return VK_FORMAT_R8G8B8_USCALED;
2589 		case FMT_CASE(RGBA,	USCALED_INT8):					return VK_FORMAT_R8G8B8A8_USCALED;
2590 
2591 		case FMT_CASE(R,	USCALED_INT16):					return VK_FORMAT_R16_USCALED;
2592 		case FMT_CASE(RG,	USCALED_INT16):					return VK_FORMAT_R16G16_USCALED;
2593 		case FMT_CASE(RGB,	USCALED_INT16):					return VK_FORMAT_R16G16B16_USCALED;
2594 		case FMT_CASE(RGBA,	USCALED_INT16):					return VK_FORMAT_R16G16B16A16_USCALED;
2595 
2596 		case FMT_CASE(R,	SSCALED_INT8):					return VK_FORMAT_R8_SSCALED;
2597 		case FMT_CASE(RG,	SSCALED_INT8):					return VK_FORMAT_R8G8_SSCALED;
2598 		case FMT_CASE(RGB,	SSCALED_INT8):					return VK_FORMAT_R8G8B8_SSCALED;
2599 		case FMT_CASE(RGBA,	SSCALED_INT8):					return VK_FORMAT_R8G8B8A8_SSCALED;
2600 
2601 		case FMT_CASE(R,	SSCALED_INT16):					return VK_FORMAT_R16_SSCALED;
2602 		case FMT_CASE(RG,	SSCALED_INT16):					return VK_FORMAT_R16G16_SSCALED;
2603 		case FMT_CASE(RGB,	SSCALED_INT16):					return VK_FORMAT_R16G16B16_SSCALED;
2604 		case FMT_CASE(RGBA,	SSCALED_INT16):					return VK_FORMAT_R16G16B16A16_SSCALED;
2605 
2606 		case FMT_CASE(RGBA, USCALED_INT_1010102_REV):		return VK_FORMAT_A2B10G10R10_USCALED_PACK32;
2607 		case FMT_CASE(RGBA, SSCALED_INT_1010102_REV):		return VK_FORMAT_A2B10G10R10_SSCALED_PACK32;
2608 
2609 		default:
2610 			TCU_THROW(InternalError, "Unknown texture format");
2611 	}
2612 
2613 #undef PACK_FMT
2614 #undef FMT_CASE
2615 }
2616 
mapCompressedTextureFormat(const tcu::CompressedTexFormat format)2617 VkFormat mapCompressedTextureFormat (const tcu::CompressedTexFormat format)
2618 {
2619 	// update this mapping if CompressedTexFormat changes
2620 	DE_STATIC_ASSERT(tcu::COMPRESSEDTEXFORMAT_LAST == 55);
2621 
2622 	switch (format)
2623 	{
2624 		case tcu::COMPRESSEDTEXFORMAT_ETC2_RGB8:						return VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK;
2625 		case tcu::COMPRESSEDTEXFORMAT_ETC2_SRGB8:						return VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK;
2626 		case tcu::COMPRESSEDTEXFORMAT_ETC2_RGB8_PUNCHTHROUGH_ALPHA1:	return VK_FORMAT_ETC2_R8G8B8A1_UNORM_BLOCK;
2627 		case tcu::COMPRESSEDTEXFORMAT_ETC2_SRGB8_PUNCHTHROUGH_ALPHA1:	return VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK;
2628 		case tcu::COMPRESSEDTEXFORMAT_ETC2_EAC_RGBA8:					return VK_FORMAT_ETC2_R8G8B8A8_UNORM_BLOCK;
2629 		case tcu::COMPRESSEDTEXFORMAT_ETC2_EAC_SRGB8_ALPHA8:			return VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK;
2630 
2631 		case tcu::COMPRESSEDTEXFORMAT_EAC_R11:							return VK_FORMAT_EAC_R11_UNORM_BLOCK;
2632 		case tcu::COMPRESSEDTEXFORMAT_EAC_SIGNED_R11:					return VK_FORMAT_EAC_R11_SNORM_BLOCK;
2633 		case tcu::COMPRESSEDTEXFORMAT_EAC_RG11:							return VK_FORMAT_EAC_R11G11_UNORM_BLOCK;
2634 		case tcu::COMPRESSEDTEXFORMAT_EAC_SIGNED_RG11:					return VK_FORMAT_EAC_R11G11_SNORM_BLOCK;
2635 
2636 		case tcu::COMPRESSEDTEXFORMAT_ASTC_4x4_RGBA:					return VK_FORMAT_ASTC_4x4_UNORM_BLOCK;
2637 		case tcu::COMPRESSEDTEXFORMAT_ASTC_4x4_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_4x4_SRGB_BLOCK;
2638 		case tcu::COMPRESSEDTEXFORMAT_ASTC_5x4_RGBA:					return VK_FORMAT_ASTC_5x4_UNORM_BLOCK;
2639 		case tcu::COMPRESSEDTEXFORMAT_ASTC_5x4_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_5x4_SRGB_BLOCK;
2640 		case tcu::COMPRESSEDTEXFORMAT_ASTC_5x5_RGBA:					return VK_FORMAT_ASTC_5x5_UNORM_BLOCK;
2641 		case tcu::COMPRESSEDTEXFORMAT_ASTC_5x5_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_5x5_SRGB_BLOCK;
2642 		case tcu::COMPRESSEDTEXFORMAT_ASTC_6x5_RGBA:					return VK_FORMAT_ASTC_6x5_UNORM_BLOCK;
2643 		case tcu::COMPRESSEDTEXFORMAT_ASTC_6x5_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_6x5_SRGB_BLOCK;
2644 		case tcu::COMPRESSEDTEXFORMAT_ASTC_6x6_RGBA:					return VK_FORMAT_ASTC_6x6_UNORM_BLOCK;
2645 		case tcu::COMPRESSEDTEXFORMAT_ASTC_6x6_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_6x6_SRGB_BLOCK;
2646 		case tcu::COMPRESSEDTEXFORMAT_ASTC_8x5_RGBA:					return VK_FORMAT_ASTC_8x5_UNORM_BLOCK;
2647 		case tcu::COMPRESSEDTEXFORMAT_ASTC_8x5_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_8x5_SRGB_BLOCK;
2648 		case tcu::COMPRESSEDTEXFORMAT_ASTC_8x6_RGBA:					return VK_FORMAT_ASTC_8x6_UNORM_BLOCK;
2649 		case tcu::COMPRESSEDTEXFORMAT_ASTC_8x6_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_8x6_SRGB_BLOCK;
2650 		case tcu::COMPRESSEDTEXFORMAT_ASTC_8x8_RGBA:					return VK_FORMAT_ASTC_8x8_UNORM_BLOCK;
2651 		case tcu::COMPRESSEDTEXFORMAT_ASTC_8x8_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_8x8_SRGB_BLOCK;
2652 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x5_RGBA:					return VK_FORMAT_ASTC_10x5_UNORM_BLOCK;
2653 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x5_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_10x5_SRGB_BLOCK;
2654 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x6_RGBA:					return VK_FORMAT_ASTC_10x6_UNORM_BLOCK;
2655 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x6_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_10x6_SRGB_BLOCK;
2656 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x8_RGBA:					return VK_FORMAT_ASTC_10x8_UNORM_BLOCK;
2657 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x8_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_10x8_SRGB_BLOCK;
2658 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x10_RGBA:					return VK_FORMAT_ASTC_10x10_UNORM_BLOCK;
2659 		case tcu::COMPRESSEDTEXFORMAT_ASTC_10x10_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_10x10_SRGB_BLOCK;
2660 		case tcu::COMPRESSEDTEXFORMAT_ASTC_12x10_RGBA:					return VK_FORMAT_ASTC_12x10_UNORM_BLOCK;
2661 		case tcu::COMPRESSEDTEXFORMAT_ASTC_12x10_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_12x10_SRGB_BLOCK;
2662 		case tcu::COMPRESSEDTEXFORMAT_ASTC_12x12_RGBA:					return VK_FORMAT_ASTC_12x12_UNORM_BLOCK;
2663 		case tcu::COMPRESSEDTEXFORMAT_ASTC_12x12_SRGB8_ALPHA8:			return VK_FORMAT_ASTC_12x12_SRGB_BLOCK;
2664 
2665 		case tcu::COMPRESSEDTEXFORMAT_BC1_RGB_UNORM_BLOCK:				return VK_FORMAT_BC1_RGB_UNORM_BLOCK;
2666 		case tcu::COMPRESSEDTEXFORMAT_BC1_RGB_SRGB_BLOCK:				return VK_FORMAT_BC1_RGB_SRGB_BLOCK;
2667 		case tcu::COMPRESSEDTEXFORMAT_BC1_RGBA_UNORM_BLOCK:				return VK_FORMAT_BC1_RGBA_UNORM_BLOCK;
2668 		case tcu::COMPRESSEDTEXFORMAT_BC1_RGBA_SRGB_BLOCK:				return VK_FORMAT_BC1_RGBA_SRGB_BLOCK;
2669 		case tcu::COMPRESSEDTEXFORMAT_BC2_UNORM_BLOCK:					return VK_FORMAT_BC2_UNORM_BLOCK;
2670 		case tcu::COMPRESSEDTEXFORMAT_BC2_SRGB_BLOCK:					return VK_FORMAT_BC2_SRGB_BLOCK;
2671 		case tcu::COMPRESSEDTEXFORMAT_BC3_UNORM_BLOCK:					return VK_FORMAT_BC3_UNORM_BLOCK;
2672 		case tcu::COMPRESSEDTEXFORMAT_BC3_SRGB_BLOCK:					return VK_FORMAT_BC3_SRGB_BLOCK;
2673 		case tcu::COMPRESSEDTEXFORMAT_BC4_UNORM_BLOCK:					return VK_FORMAT_BC4_UNORM_BLOCK;
2674 		case tcu::COMPRESSEDTEXFORMAT_BC4_SNORM_BLOCK:					return VK_FORMAT_BC4_SNORM_BLOCK;
2675 		case tcu::COMPRESSEDTEXFORMAT_BC5_UNORM_BLOCK:					return VK_FORMAT_BC5_UNORM_BLOCK;
2676 		case tcu::COMPRESSEDTEXFORMAT_BC5_SNORM_BLOCK:					return VK_FORMAT_BC5_SNORM_BLOCK;
2677 		case tcu::COMPRESSEDTEXFORMAT_BC6H_UFLOAT_BLOCK:				return VK_FORMAT_BC6H_UFLOAT_BLOCK;
2678 		case tcu::COMPRESSEDTEXFORMAT_BC6H_SFLOAT_BLOCK:				return VK_FORMAT_BC6H_SFLOAT_BLOCK;
2679 		case tcu::COMPRESSEDTEXFORMAT_BC7_UNORM_BLOCK:					return VK_FORMAT_BC7_UNORM_BLOCK;
2680 		case tcu::COMPRESSEDTEXFORMAT_BC7_SRGB_BLOCK:					return VK_FORMAT_BC7_SRGB_BLOCK;
2681 
2682 		default:
2683 			TCU_THROW(InternalError, "Unknown texture format");
2684 			return VK_FORMAT_UNDEFINED;
2685 	}
2686 }
2687 
mapVkFormat(VkFormat format)2688 tcu::TextureFormat mapVkFormat (VkFormat format)
2689 {
2690 	using tcu::TextureFormat;
2691 
2692 	// update this mapping if VkFormat changes
2693 	DE_STATIC_ASSERT(VK_CORE_FORMAT_LAST == 185);
2694 
2695 	switch (format)
2696 	{
2697 		case VK_FORMAT_R4G4_UNORM_PACK8:		return TextureFormat(TextureFormat::RG,		TextureFormat::UNORM_BYTE_44);
2698 		case VK_FORMAT_R5G6B5_UNORM_PACK16:		return TextureFormat(TextureFormat::RGB,	TextureFormat::UNORM_SHORT_565);
2699 		case VK_FORMAT_R4G4B4A4_UNORM_PACK16:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_SHORT_4444);
2700 		case VK_FORMAT_R5G5B5A1_UNORM_PACK16:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_SHORT_5551);
2701 
2702 		case VK_FORMAT_B5G6R5_UNORM_PACK16:		return TextureFormat(TextureFormat::BGR,	TextureFormat::UNORM_SHORT_565);
2703 		case VK_FORMAT_B4G4R4A4_UNORM_PACK16:	return TextureFormat(TextureFormat::BGRA,	TextureFormat::UNORM_SHORT_4444);
2704 		case VK_FORMAT_B5G5R5A1_UNORM_PACK16:	return TextureFormat(TextureFormat::BGRA,	TextureFormat::UNORM_SHORT_5551);
2705 
2706 		case VK_FORMAT_A1R5G5B5_UNORM_PACK16:	return TextureFormat(TextureFormat::ARGB,	TextureFormat::UNORM_SHORT_1555);
2707 
2708 		case VK_FORMAT_R8_UNORM:				return TextureFormat(TextureFormat::R,		TextureFormat::UNORM_INT8);
2709 		case VK_FORMAT_R8_SNORM:				return TextureFormat(TextureFormat::R,		TextureFormat::SNORM_INT8);
2710 		case VK_FORMAT_R8_USCALED:				return TextureFormat(TextureFormat::R,		TextureFormat::USCALED_INT8);
2711 		case VK_FORMAT_R8_SSCALED:				return TextureFormat(TextureFormat::R,		TextureFormat::SSCALED_INT8);
2712 		case VK_FORMAT_R8_UINT:					return TextureFormat(TextureFormat::R,		TextureFormat::UNSIGNED_INT8);
2713 		case VK_FORMAT_R8_SINT:					return TextureFormat(TextureFormat::R,		TextureFormat::SIGNED_INT8);
2714 		case VK_FORMAT_R8_SRGB:					return TextureFormat(TextureFormat::sR,		TextureFormat::UNORM_INT8);
2715 
2716 		case VK_FORMAT_R8G8_UNORM:				return TextureFormat(TextureFormat::RG,		TextureFormat::UNORM_INT8);
2717 		case VK_FORMAT_R8G8_SNORM:				return TextureFormat(TextureFormat::RG,		TextureFormat::SNORM_INT8);
2718 		case VK_FORMAT_R8G8_USCALED:			return TextureFormat(TextureFormat::RG,		TextureFormat::USCALED_INT8);
2719 		case VK_FORMAT_R8G8_SSCALED:			return TextureFormat(TextureFormat::RG,		TextureFormat::SSCALED_INT8);
2720 		case VK_FORMAT_R8G8_UINT:				return TextureFormat(TextureFormat::RG,		TextureFormat::UNSIGNED_INT8);
2721 		case VK_FORMAT_R8G8_SINT:				return TextureFormat(TextureFormat::RG,		TextureFormat::SIGNED_INT8);
2722 		case VK_FORMAT_R8G8_SRGB:				return TextureFormat(TextureFormat::sRG,	TextureFormat::UNORM_INT8);
2723 
2724 		case VK_FORMAT_R8G8B8_UNORM:			return TextureFormat(TextureFormat::RGB,	TextureFormat::UNORM_INT8);
2725 		case VK_FORMAT_R8G8B8_SNORM:			return TextureFormat(TextureFormat::RGB,	TextureFormat::SNORM_INT8);
2726 		case VK_FORMAT_R8G8B8_USCALED:			return TextureFormat(TextureFormat::RGB,	TextureFormat::USCALED_INT8);
2727 		case VK_FORMAT_R8G8B8_SSCALED:			return TextureFormat(TextureFormat::RGB,	TextureFormat::SSCALED_INT8);
2728 		case VK_FORMAT_R8G8B8_UINT:				return TextureFormat(TextureFormat::RGB,	TextureFormat::UNSIGNED_INT8);
2729 		case VK_FORMAT_R8G8B8_SINT:				return TextureFormat(TextureFormat::RGB,	TextureFormat::SIGNED_INT8);
2730 		case VK_FORMAT_R8G8B8_SRGB:				return TextureFormat(TextureFormat::sRGB,	TextureFormat::UNORM_INT8);
2731 
2732 		case VK_FORMAT_R8G8B8A8_UNORM:			return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_INT8);
2733 		case VK_FORMAT_R8G8B8A8_SNORM:			return TextureFormat(TextureFormat::RGBA,	TextureFormat::SNORM_INT8);
2734 		case VK_FORMAT_R8G8B8A8_USCALED:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::USCALED_INT8);
2735 		case VK_FORMAT_R8G8B8A8_SSCALED:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::SSCALED_INT8);
2736 		case VK_FORMAT_R8G8B8A8_UINT:			return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNSIGNED_INT8);
2737 		case VK_FORMAT_R8G8B8A8_SINT:			return TextureFormat(TextureFormat::RGBA,	TextureFormat::SIGNED_INT8);
2738 		case VK_FORMAT_R8G8B8A8_SRGB:			return TextureFormat(TextureFormat::sRGBA,	TextureFormat::UNORM_INT8);
2739 
2740 		case VK_FORMAT_R16_UNORM:				return TextureFormat(TextureFormat::R,		TextureFormat::UNORM_INT16);
2741 		case VK_FORMAT_R16_SNORM:				return TextureFormat(TextureFormat::R,		TextureFormat::SNORM_INT16);
2742 		case VK_FORMAT_R16_USCALED:				return TextureFormat(TextureFormat::R,		TextureFormat::USCALED_INT16);
2743 		case VK_FORMAT_R16_SSCALED:				return TextureFormat(TextureFormat::R,		TextureFormat::SSCALED_INT16);
2744 		case VK_FORMAT_R16_UINT:				return TextureFormat(TextureFormat::R,		TextureFormat::UNSIGNED_INT16);
2745 		case VK_FORMAT_R16_SINT:				return TextureFormat(TextureFormat::R,		TextureFormat::SIGNED_INT16);
2746 		case VK_FORMAT_R16_SFLOAT:				return TextureFormat(TextureFormat::R,		TextureFormat::HALF_FLOAT);
2747 
2748 		case VK_FORMAT_R16G16_UNORM:			return TextureFormat(TextureFormat::RG,		TextureFormat::UNORM_INT16);
2749 		case VK_FORMAT_R16G16_SNORM:			return TextureFormat(TextureFormat::RG,		TextureFormat::SNORM_INT16);
2750 		case VK_FORMAT_R16G16_USCALED:			return TextureFormat(TextureFormat::RG,		TextureFormat::USCALED_INT16);
2751 		case VK_FORMAT_R16G16_SSCALED:			return TextureFormat(TextureFormat::RG,		TextureFormat::SSCALED_INT16);
2752 		case VK_FORMAT_R16G16_UINT:				return TextureFormat(TextureFormat::RG,		TextureFormat::UNSIGNED_INT16);
2753 		case VK_FORMAT_R16G16_SINT:				return TextureFormat(TextureFormat::RG,		TextureFormat::SIGNED_INT16);
2754 		case VK_FORMAT_R16G16_SFLOAT:			return TextureFormat(TextureFormat::RG,		TextureFormat::HALF_FLOAT);
2755 
2756 		case VK_FORMAT_R16G16B16_UNORM:			return TextureFormat(TextureFormat::RGB,	TextureFormat::UNORM_INT16);
2757 		case VK_FORMAT_R16G16B16_SNORM:			return TextureFormat(TextureFormat::RGB,	TextureFormat::SNORM_INT16);
2758 		case VK_FORMAT_R16G16B16_USCALED:		return TextureFormat(TextureFormat::RGB,	TextureFormat::USCALED_INT16);
2759 		case VK_FORMAT_R16G16B16_SSCALED:		return TextureFormat(TextureFormat::RGB,	TextureFormat::SSCALED_INT16);
2760 		case VK_FORMAT_R16G16B16_UINT:			return TextureFormat(TextureFormat::RGB,	TextureFormat::UNSIGNED_INT16);
2761 		case VK_FORMAT_R16G16B16_SINT:			return TextureFormat(TextureFormat::RGB,	TextureFormat::SIGNED_INT16);
2762 		case VK_FORMAT_R16G16B16_SFLOAT:		return TextureFormat(TextureFormat::RGB,	TextureFormat::HALF_FLOAT);
2763 
2764 		case VK_FORMAT_R16G16B16A16_UNORM:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_INT16);
2765 		case VK_FORMAT_R16G16B16A16_SNORM:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::SNORM_INT16);
2766 		case VK_FORMAT_R16G16B16A16_USCALED:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::USCALED_INT16);
2767 		case VK_FORMAT_R16G16B16A16_SSCALED:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::SSCALED_INT16);
2768 		case VK_FORMAT_R16G16B16A16_UINT:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNSIGNED_INT16);
2769 		case VK_FORMAT_R16G16B16A16_SINT:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::SIGNED_INT16);
2770 		case VK_FORMAT_R16G16B16A16_SFLOAT:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::HALF_FLOAT);
2771 
2772 		case VK_FORMAT_R32_UINT:				return TextureFormat(TextureFormat::R,		TextureFormat::UNSIGNED_INT32);
2773 		case VK_FORMAT_R32_SINT:				return TextureFormat(TextureFormat::R,		TextureFormat::SIGNED_INT32);
2774 		case VK_FORMAT_R32_SFLOAT:				return TextureFormat(TextureFormat::R,		TextureFormat::FLOAT);
2775 
2776 		case VK_FORMAT_R32G32_UINT:				return TextureFormat(TextureFormat::RG,		TextureFormat::UNSIGNED_INT32);
2777 		case VK_FORMAT_R32G32_SINT:				return TextureFormat(TextureFormat::RG,		TextureFormat::SIGNED_INT32);
2778 		case VK_FORMAT_R32G32_SFLOAT:			return TextureFormat(TextureFormat::RG,		TextureFormat::FLOAT);
2779 
2780 		case VK_FORMAT_R32G32B32_UINT:			return TextureFormat(TextureFormat::RGB,	TextureFormat::UNSIGNED_INT32);
2781 		case VK_FORMAT_R32G32B32_SINT:			return TextureFormat(TextureFormat::RGB,	TextureFormat::SIGNED_INT32);
2782 		case VK_FORMAT_R32G32B32_SFLOAT:		return TextureFormat(TextureFormat::RGB,	TextureFormat::FLOAT);
2783 
2784 		case VK_FORMAT_R32G32B32A32_UINT:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNSIGNED_INT32);
2785 		case VK_FORMAT_R32G32B32A32_SINT:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::SIGNED_INT32);
2786 		case VK_FORMAT_R32G32B32A32_SFLOAT:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::FLOAT);
2787 
2788 		case VK_FORMAT_R64_UINT:				return TextureFormat(TextureFormat::R,		TextureFormat::UNSIGNED_INT64);
2789 		case VK_FORMAT_R64_SINT:				return TextureFormat(TextureFormat::R,		TextureFormat::SIGNED_INT64);
2790 		case VK_FORMAT_R64_SFLOAT:				return TextureFormat(TextureFormat::R,		TextureFormat::FLOAT64);
2791 		case VK_FORMAT_R64G64_SFLOAT:			return TextureFormat(TextureFormat::RG,		TextureFormat::FLOAT64);
2792 		case VK_FORMAT_R64G64B64_SFLOAT:		return TextureFormat(TextureFormat::RGB,	TextureFormat::FLOAT64);
2793 		case VK_FORMAT_R64G64B64A64_SFLOAT:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::FLOAT64);
2794 
2795 		case VK_FORMAT_B10G11R11_UFLOAT_PACK32:	return TextureFormat(TextureFormat::RGB,	TextureFormat::UNSIGNED_INT_11F_11F_10F_REV);
2796 		case VK_FORMAT_E5B9G9R9_UFLOAT_PACK32:	return TextureFormat(TextureFormat::RGB,	TextureFormat::UNSIGNED_INT_999_E5_REV);
2797 
2798 		case VK_FORMAT_B8G8R8_UNORM:			return TextureFormat(TextureFormat::BGR,	TextureFormat::UNORM_INT8);
2799 		case VK_FORMAT_B8G8R8_SNORM:			return TextureFormat(TextureFormat::BGR,	TextureFormat::SNORM_INT8);
2800 		case VK_FORMAT_B8G8R8_USCALED:			return TextureFormat(TextureFormat::BGR,	TextureFormat::USCALED_INT8);
2801 		case VK_FORMAT_B8G8R8_SSCALED:			return TextureFormat(TextureFormat::BGR,	TextureFormat::SSCALED_INT8);
2802 		case VK_FORMAT_B8G8R8_UINT:				return TextureFormat(TextureFormat::BGR,	TextureFormat::UNSIGNED_INT8);
2803 		case VK_FORMAT_B8G8R8_SINT:				return TextureFormat(TextureFormat::BGR,	TextureFormat::SIGNED_INT8);
2804 		case VK_FORMAT_B8G8R8_SRGB:				return TextureFormat(TextureFormat::sBGR,	TextureFormat::UNORM_INT8);
2805 
2806 		case VK_FORMAT_B8G8R8A8_UNORM:			return TextureFormat(TextureFormat::BGRA,	TextureFormat::UNORM_INT8);
2807 		case VK_FORMAT_B8G8R8A8_SNORM:			return TextureFormat(TextureFormat::BGRA,	TextureFormat::SNORM_INT8);
2808 		case VK_FORMAT_B8G8R8A8_USCALED:		return TextureFormat(TextureFormat::BGRA,	TextureFormat::USCALED_INT8);
2809 		case VK_FORMAT_B8G8R8A8_SSCALED:		return TextureFormat(TextureFormat::BGRA,	TextureFormat::SSCALED_INT8);
2810 		case VK_FORMAT_B8G8R8A8_UINT:			return TextureFormat(TextureFormat::BGRA,	TextureFormat::UNSIGNED_INT8);
2811 		case VK_FORMAT_B8G8R8A8_SINT:			return TextureFormat(TextureFormat::BGRA,	TextureFormat::SIGNED_INT8);
2812 		case VK_FORMAT_B8G8R8A8_SRGB:			return TextureFormat(TextureFormat::sBGRA,	TextureFormat::UNORM_INT8);
2813 
2814 		case VK_FORMAT_D16_UNORM:				return TextureFormat(TextureFormat::D,		TextureFormat::UNORM_INT16);
2815 		case VK_FORMAT_X8_D24_UNORM_PACK32:		return TextureFormat(TextureFormat::D,		TextureFormat::UNSIGNED_INT_24_8_REV);
2816 		case VK_FORMAT_D32_SFLOAT:				return TextureFormat(TextureFormat::D,		TextureFormat::FLOAT);
2817 
2818 		case VK_FORMAT_S8_UINT:					return TextureFormat(TextureFormat::S,		TextureFormat::UNSIGNED_INT8);
2819 
2820 		// \note There is no standard interleaved memory layout for DS formats; buffer-image copies
2821 		//		 will always operate on either D or S aspect only. See Khronos bug 12998
2822 		case VK_FORMAT_D16_UNORM_S8_UINT:		return TextureFormat(TextureFormat::DS,		TextureFormat::UNSIGNED_INT_16_8_8);
2823 		case VK_FORMAT_D24_UNORM_S8_UINT:		return TextureFormat(TextureFormat::DS,		TextureFormat::UNSIGNED_INT_24_8_REV);
2824 		case VK_FORMAT_D32_SFLOAT_S8_UINT:		return TextureFormat(TextureFormat::DS,		TextureFormat::FLOAT_UNSIGNED_INT_24_8_REV);
2825 
2826 #if (DE_ENDIANNESS == DE_LITTLE_ENDIAN)
2827 		case VK_FORMAT_A8B8G8R8_UNORM_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_INT8);
2828 		case VK_FORMAT_A8B8G8R8_SNORM_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::SNORM_INT8);
2829 		case VK_FORMAT_A8B8G8R8_USCALED_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::USCALED_INT8);
2830 		case VK_FORMAT_A8B8G8R8_SSCALED_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::SSCALED_INT8);
2831 		case VK_FORMAT_A8B8G8R8_UINT_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNSIGNED_INT8);
2832 		case VK_FORMAT_A8B8G8R8_SINT_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::SIGNED_INT8);
2833 		case VK_FORMAT_A8B8G8R8_SRGB_PACK32:	return TextureFormat(TextureFormat::sRGBA,	TextureFormat::UNORM_INT8);
2834 #else
2835 #	error "Big-endian not supported"
2836 #endif
2837 
2838 		case VK_FORMAT_A2R10G10B10_UNORM_PACK32:	return TextureFormat(TextureFormat::BGRA,	TextureFormat::UNORM_INT_1010102_REV);
2839 		case VK_FORMAT_A2R10G10B10_SNORM_PACK32:	return TextureFormat(TextureFormat::BGRA,	TextureFormat::SNORM_INT_1010102_REV);
2840 		case VK_FORMAT_A2R10G10B10_USCALED_PACK32:	return TextureFormat(TextureFormat::BGRA,	TextureFormat::USCALED_INT_1010102_REV);
2841 		case VK_FORMAT_A2R10G10B10_SSCALED_PACK32:	return TextureFormat(TextureFormat::BGRA,	TextureFormat::SSCALED_INT_1010102_REV);
2842 		case VK_FORMAT_A2R10G10B10_UINT_PACK32:		return TextureFormat(TextureFormat::BGRA,	TextureFormat::UNSIGNED_INT_1010102_REV);
2843 		case VK_FORMAT_A2R10G10B10_SINT_PACK32:		return TextureFormat(TextureFormat::BGRA,	TextureFormat::SIGNED_INT_1010102_REV);
2844 
2845 		case VK_FORMAT_A2B10G10R10_UNORM_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_INT_1010102_REV);
2846 		case VK_FORMAT_A2B10G10R10_SNORM_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::SNORM_INT_1010102_REV);
2847 		case VK_FORMAT_A2B10G10R10_USCALED_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::USCALED_INT_1010102_REV);
2848 		case VK_FORMAT_A2B10G10R10_SSCALED_PACK32:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::SSCALED_INT_1010102_REV);
2849 		case VK_FORMAT_A2B10G10R10_UINT_PACK32:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNSIGNED_INT_1010102_REV);
2850 		case VK_FORMAT_A2B10G10R10_SINT_PACK32:		return TextureFormat(TextureFormat::RGBA,	TextureFormat::SIGNED_INT_1010102_REV);
2851 
2852 		// YCbCr formats that can be mapped
2853 		case VK_FORMAT_R10X6_UNORM_PACK16_KHR:					return TextureFormat(TextureFormat::R,		TextureFormat::UNORM_SHORT_10);
2854 		case VK_FORMAT_R10X6G10X6_UNORM_2PACK16_KHR:			return TextureFormat(TextureFormat::RG,		TextureFormat::UNORM_SHORT_10);
2855 		case VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16_KHR:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_SHORT_10);
2856 
2857 		case VK_FORMAT_R12X4_UNORM_PACK16_KHR:					return TextureFormat(TextureFormat::R,		TextureFormat::UNORM_SHORT_12);
2858 		case VK_FORMAT_R12X4G12X4_UNORM_2PACK16_KHR:			return TextureFormat(TextureFormat::RG,		TextureFormat::UNORM_SHORT_12);
2859 		case VK_FORMAT_R12X4G12X4B12X4A12X4_UNORM_4PACK16_KHR:	return TextureFormat(TextureFormat::RGBA,	TextureFormat::UNORM_SHORT_12);
2860 
2861 		default:
2862 			TCU_THROW(InternalError, "Unknown image format");
2863 	}
2864 }
2865 
mapVkCompressedFormat(VkFormat format)2866 tcu::CompressedTexFormat mapVkCompressedFormat (VkFormat format)
2867 {
2868 	// update this mapping if VkFormat changes
2869 	DE_STATIC_ASSERT(VK_CORE_FORMAT_LAST == 185);
2870 
2871 	switch (format)
2872 	{
2873 		case VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ETC2_RGB8;
2874 		case VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ETC2_SRGB8;
2875 		case VK_FORMAT_ETC2_R8G8B8A1_UNORM_BLOCK:	return tcu::COMPRESSEDTEXFORMAT_ETC2_RGB8_PUNCHTHROUGH_ALPHA1;
2876 		case VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK:	return tcu::COMPRESSEDTEXFORMAT_ETC2_SRGB8_PUNCHTHROUGH_ALPHA1;
2877 		case VK_FORMAT_ETC2_R8G8B8A8_UNORM_BLOCK:	return tcu::COMPRESSEDTEXFORMAT_ETC2_EAC_RGBA8;
2878 		case VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK:	return tcu::COMPRESSEDTEXFORMAT_ETC2_EAC_SRGB8_ALPHA8;
2879 
2880 		case VK_FORMAT_EAC_R11_UNORM_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_EAC_R11;
2881 		case VK_FORMAT_EAC_R11_SNORM_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_EAC_SIGNED_R11;
2882 		case VK_FORMAT_EAC_R11G11_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_EAC_RG11;
2883 		case VK_FORMAT_EAC_R11G11_SNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_EAC_SIGNED_RG11;
2884 
2885 		case VK_FORMAT_ASTC_4x4_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_4x4_RGBA;
2886 		case VK_FORMAT_ASTC_4x4_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_4x4_SRGB8_ALPHA8;
2887 		case VK_FORMAT_ASTC_5x4_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_5x4_RGBA;
2888 		case VK_FORMAT_ASTC_5x4_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_5x4_SRGB8_ALPHA8;
2889 		case VK_FORMAT_ASTC_5x5_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_5x5_RGBA;
2890 		case VK_FORMAT_ASTC_5x5_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_5x5_SRGB8_ALPHA8;
2891 		case VK_FORMAT_ASTC_6x5_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_6x5_RGBA;
2892 		case VK_FORMAT_ASTC_6x5_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_6x5_SRGB8_ALPHA8;
2893 		case VK_FORMAT_ASTC_6x6_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_6x6_RGBA;
2894 		case VK_FORMAT_ASTC_6x6_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_6x6_SRGB8_ALPHA8;
2895 		case VK_FORMAT_ASTC_8x5_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_8x5_RGBA;
2896 		case VK_FORMAT_ASTC_8x5_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_8x5_SRGB8_ALPHA8;
2897 		case VK_FORMAT_ASTC_8x6_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_8x6_RGBA;
2898 		case VK_FORMAT_ASTC_8x6_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_8x6_SRGB8_ALPHA8;
2899 		case VK_FORMAT_ASTC_8x8_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_8x8_RGBA;
2900 		case VK_FORMAT_ASTC_8x8_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_ASTC_8x8_SRGB8_ALPHA8;
2901 		case VK_FORMAT_ASTC_10x5_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x5_RGBA;
2902 		case VK_FORMAT_ASTC_10x5_SRGB_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x5_SRGB8_ALPHA8;
2903 		case VK_FORMAT_ASTC_10x6_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x6_RGBA;
2904 		case VK_FORMAT_ASTC_10x6_SRGB_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x6_SRGB8_ALPHA8;
2905 		case VK_FORMAT_ASTC_10x8_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x8_RGBA;
2906 		case VK_FORMAT_ASTC_10x8_SRGB_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x8_SRGB8_ALPHA8;
2907 		case VK_FORMAT_ASTC_10x10_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x10_RGBA;
2908 		case VK_FORMAT_ASTC_10x10_SRGB_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_10x10_SRGB8_ALPHA8;
2909 		case VK_FORMAT_ASTC_12x10_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_12x10_RGBA;
2910 		case VK_FORMAT_ASTC_12x10_SRGB_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_12x10_SRGB8_ALPHA8;
2911 		case VK_FORMAT_ASTC_12x12_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_12x12_RGBA;
2912 		case VK_FORMAT_ASTC_12x12_SRGB_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_ASTC_12x12_SRGB8_ALPHA8;
2913 
2914 		case VK_FORMAT_BC1_RGB_UNORM_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_BC1_RGB_UNORM_BLOCK;
2915 		case VK_FORMAT_BC1_RGB_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_BC1_RGB_SRGB_BLOCK;
2916 		case VK_FORMAT_BC1_RGBA_UNORM_BLOCK:		return tcu::COMPRESSEDTEXFORMAT_BC1_RGBA_UNORM_BLOCK;
2917 		case VK_FORMAT_BC1_RGBA_SRGB_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_BC1_RGBA_SRGB_BLOCK;
2918 		case VK_FORMAT_BC2_UNORM_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC2_UNORM_BLOCK;
2919 		case VK_FORMAT_BC2_SRGB_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC2_SRGB_BLOCK;
2920 		case VK_FORMAT_BC3_UNORM_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC3_UNORM_BLOCK;
2921 		case VK_FORMAT_BC3_SRGB_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC3_SRGB_BLOCK;
2922 		case VK_FORMAT_BC4_UNORM_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC4_UNORM_BLOCK;
2923 		case VK_FORMAT_BC4_SNORM_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC4_SNORM_BLOCK;
2924 		case VK_FORMAT_BC5_UNORM_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC5_UNORM_BLOCK;
2925 		case VK_FORMAT_BC5_SNORM_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC5_SNORM_BLOCK;
2926 		case VK_FORMAT_BC6H_UFLOAT_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_BC6H_UFLOAT_BLOCK;
2927 		case VK_FORMAT_BC6H_SFLOAT_BLOCK:			return tcu::COMPRESSEDTEXFORMAT_BC6H_SFLOAT_BLOCK;
2928 		case VK_FORMAT_BC7_UNORM_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC7_UNORM_BLOCK;
2929 		case VK_FORMAT_BC7_SRGB_BLOCK:				return tcu::COMPRESSEDTEXFORMAT_BC7_SRGB_BLOCK;
2930 
2931 		default:
2932 			TCU_THROW(InternalError, "Unknown image format");
2933 			return tcu::COMPRESSEDTEXFORMAT_LAST;
2934 	}
2935 }
2936 
isScaledFormat(VkFormat format)2937 static bool isScaledFormat (VkFormat format)
2938 {
2939 	// update this mapping if VkFormat changes
2940 	DE_STATIC_ASSERT(VK_CORE_FORMAT_LAST == 185);
2941 
2942 	switch (format)
2943 	{
2944 		case VK_FORMAT_R8_USCALED:
2945 		case VK_FORMAT_R8_SSCALED:
2946 		case VK_FORMAT_R8G8_USCALED:
2947 		case VK_FORMAT_R8G8_SSCALED:
2948 		case VK_FORMAT_R8G8B8_USCALED:
2949 		case VK_FORMAT_R8G8B8_SSCALED:
2950 		case VK_FORMAT_R8G8B8A8_USCALED:
2951 		case VK_FORMAT_R8G8B8A8_SSCALED:
2952 		case VK_FORMAT_A2B10G10R10_USCALED_PACK32:
2953 		case VK_FORMAT_A2B10G10R10_SSCALED_PACK32:
2954 		case VK_FORMAT_R16_USCALED:
2955 		case VK_FORMAT_R16_SSCALED:
2956 		case VK_FORMAT_R16G16_USCALED:
2957 		case VK_FORMAT_R16G16_SSCALED:
2958 		case VK_FORMAT_R16G16B16_USCALED:
2959 		case VK_FORMAT_R16G16B16_SSCALED:
2960 		case VK_FORMAT_R16G16B16A16_USCALED:
2961 		case VK_FORMAT_R16G16B16A16_SSCALED:
2962 		case VK_FORMAT_B8G8R8_USCALED:
2963 		case VK_FORMAT_B8G8R8_SSCALED:
2964 		case VK_FORMAT_B8G8R8A8_USCALED:
2965 		case VK_FORMAT_B8G8R8A8_SSCALED:
2966 		case VK_FORMAT_A2R10G10B10_USCALED_PACK32:
2967 		case VK_FORMAT_A2R10G10B10_SSCALED_PACK32:
2968 			return true;
2969 
2970 		default:
2971 			return false;
2972 	}
2973 }
2974 
fullTextureFormatRoundTripSupported(VkFormat format)2975 static bool fullTextureFormatRoundTripSupported (VkFormat format)
2976 {
2977 	if (isScaledFormat(format))
2978 	{
2979 		// *SCALED formats get mapped to correspoding (u)int formats since
2980 		// accessing them through (float) getPixel/setPixel has same behavior
2981 		// as in shader access in Vulkan.
2982 		// Unfortunately full round-trip between tcu::TextureFormat and VkFormat
2983 		// for most SCALED formats is not supported though.
2984 
2985 		const tcu::TextureFormat	tcuFormat	= mapVkFormat(format);
2986 
2987 		switch (tcuFormat.type)
2988 		{
2989 			case tcu::TextureFormat::UNSIGNED_INT8:
2990 			case tcu::TextureFormat::UNSIGNED_INT16:
2991 			case tcu::TextureFormat::UNSIGNED_INT32:
2992 			case tcu::TextureFormat::SIGNED_INT8:
2993 			case tcu::TextureFormat::SIGNED_INT16:
2994 			case tcu::TextureFormat::SIGNED_INT32:
2995 			case tcu::TextureFormat::UNSIGNED_INT_1010102_REV:
2996 			case tcu::TextureFormat::SIGNED_INT_1010102_REV:
2997 				return false;
2998 
2999 			default:
3000 				return true;
3001 		}
3002 	}
3003 	else
3004 	{
3005 		switch (format)
3006 		{
3007 			case VK_FORMAT_A8B8G8R8_UNORM_PACK32:
3008 			case VK_FORMAT_A8B8G8R8_SNORM_PACK32:
3009 			case VK_FORMAT_A8B8G8R8_USCALED_PACK32:
3010 			case VK_FORMAT_A8B8G8R8_SSCALED_PACK32:
3011 			case VK_FORMAT_A8B8G8R8_UINT_PACK32:
3012 			case VK_FORMAT_A8B8G8R8_SINT_PACK32:
3013 			case VK_FORMAT_A8B8G8R8_SRGB_PACK32:
3014 				return false; // These map to regular byte array formats
3015 
3016 			default:
3017 				break;
3018 		}
3019 
3020 		return (format != VK_FORMAT_UNDEFINED);
3021 	}
3022 }
3023 
getChannelAccessFormat(tcu::TextureChannelClass type,deUint32 offsetBits,deUint32 sizeBits)3024 tcu::TextureFormat getChannelAccessFormat (tcu::TextureChannelClass	type,
3025 										   deUint32					offsetBits,
3026 										   deUint32					sizeBits)
3027 {
3028 	using tcu::TextureFormat;
3029 
3030 	if (offsetBits == 0)
3031 	{
3032 		static const TextureFormat::ChannelType	s_size8[tcu::TEXTURECHANNELCLASS_LAST] =
3033 		{
3034 			TextureFormat::SNORM_INT8,			// snorm
3035 			TextureFormat::UNORM_INT8,			// unorm
3036 			TextureFormat::SIGNED_INT8,			// sint
3037 			TextureFormat::UNSIGNED_INT8,		// uint
3038 			TextureFormat::CHANNELTYPE_LAST,	// float
3039 		};
3040 		static const TextureFormat::ChannelType	s_size16[tcu::TEXTURECHANNELCLASS_LAST] =
3041 		{
3042 			TextureFormat::SNORM_INT16,			// snorm
3043 			TextureFormat::UNORM_INT16,			// unorm
3044 			TextureFormat::SIGNED_INT16,		// sint
3045 			TextureFormat::UNSIGNED_INT16,		// uint
3046 			TextureFormat::HALF_FLOAT,			// float
3047 		};
3048 		static const TextureFormat::ChannelType	s_size32[tcu::TEXTURECHANNELCLASS_LAST] =
3049 		{
3050 			TextureFormat::SNORM_INT32,			// snorm
3051 			TextureFormat::UNORM_INT32,			// unorm
3052 			TextureFormat::SIGNED_INT32,		// sint
3053 			TextureFormat::UNSIGNED_INT32,		// uint
3054 			TextureFormat::FLOAT,				// float
3055 		};
3056 
3057 		TextureFormat::ChannelType	chnType		= TextureFormat::CHANNELTYPE_LAST;
3058 
3059 		if (sizeBits == 8)
3060 			chnType = s_size8[type];
3061 		else if (sizeBits == 16)
3062 			chnType = s_size16[type];
3063 		else if (sizeBits == 32)
3064 			chnType = s_size32[type];
3065 
3066 		if (chnType != TextureFormat::CHANNELTYPE_LAST)
3067 			return TextureFormat(TextureFormat::R, chnType);
3068 	}
3069 	else
3070 	{
3071 		if (type		== tcu::TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT	&&
3072 			offsetBits	== 6												&&
3073 			sizeBits	== 10)
3074 			return TextureFormat(TextureFormat::R, TextureFormat::UNORM_SHORT_10);
3075 		else if (type		== tcu::TEXTURECHANNELCLASS_UNSIGNED_FIXED_POINT	&&
3076 				 offsetBits	== 4												&&
3077 				 sizeBits	== 12)
3078 			return TextureFormat(TextureFormat::R, TextureFormat::UNORM_SHORT_12);
3079 	}
3080 
3081 	TCU_THROW(InternalError, "Channel access format is not supported");
3082 }
3083 
getChannelAccess(const PlanarFormatDescription & formatInfo,const tcu::UVec2 & size,const deUint32 * planeRowPitches,void * const * planePtrs,deUint32 channelNdx)3084 tcu::PixelBufferAccess getChannelAccess (const PlanarFormatDescription&	formatInfo,
3085 										 const tcu::UVec2&				size,
3086 										 const deUint32*				planeRowPitches,
3087 										 void* const*					planePtrs,
3088 										 deUint32						channelNdx)
3089 {
3090 	DE_ASSERT(formatInfo.hasChannelNdx(channelNdx));
3091 
3092 	const deUint32	planeNdx			= formatInfo.channels[channelNdx].planeNdx;
3093 	const deUint32	planeOffsetBytes	= formatInfo.channels[channelNdx].offsetBits / 8;
3094 	const deUint32	valueOffsetBits		= formatInfo.channels[channelNdx].offsetBits % 8;
3095 	const deUint32	pixelStrideBytes	= formatInfo.channels[channelNdx].strideBytes;
3096 
3097 	DE_ASSERT(size.x() % (formatInfo.blockWidth * formatInfo.planes[planeNdx].widthDivisor) == 0);
3098 	DE_ASSERT(size.y() % (formatInfo.blockHeight * formatInfo.planes[planeNdx].heightDivisor) == 0);
3099 
3100 	const deUint32	accessHeight		= size.y() / ( formatInfo.blockHeight * formatInfo.planes[planeNdx].heightDivisor );
3101 	const deUint32	elementSizeBytes	= formatInfo.planes[planeNdx].elementSizeBytes;
3102 	const deUint32	rowPitch			= planeRowPitches[planeNdx];
3103 
3104 	DE_ASSERT(elementSizeBytes % pixelStrideBytes == 0);
3105 
3106 	tcu::IVec3		texDivider(
3107 		std::max(formatInfo.blockWidth * formatInfo.planes[planeNdx].widthDivisor * pixelStrideBytes / elementSizeBytes, 1u),
3108 		std::max(formatInfo.blockHeight * formatInfo.planes[planeNdx].heightDivisor * pixelStrideBytes / elementSizeBytes, 1u),
3109 		1);
3110 
3111 	return tcu::PixelBufferAccess(getChannelAccessFormat((tcu::TextureChannelClass)formatInfo.channels[channelNdx].type,
3112 														 valueOffsetBits,
3113 														 formatInfo.channels[channelNdx].sizeBits),
3114 														 tcu::IVec3((int)size.x(), (int)size.y(), 1),
3115 														 tcu::IVec3((int)pixelStrideBytes, (int)rowPitch, (int)(accessHeight*rowPitch)),
3116 														 texDivider,
3117 														 (deUint8*)planePtrs[planeNdx] + planeOffsetBytes);
3118 }
3119 
getChannelAccess(const PlanarFormatDescription & formatInfo,const tcu::UVec2 & size,const deUint32 * planeRowPitches,const void * const * planePtrs,deUint32 channelNdx)3120 tcu::ConstPixelBufferAccess getChannelAccess (const PlanarFormatDescription&	formatInfo,
3121 											  const tcu::UVec2&					size,
3122 											  const deUint32*					planeRowPitches,
3123 											  const void* const*				planePtrs,
3124 											  deUint32							channelNdx)
3125 {
3126 	return getChannelAccess(formatInfo, size, planeRowPitches, const_cast<void* const*>(planePtrs), channelNdx);
3127 }
3128 
getChannelAccess(const PlanarFormatDescription & formatInfo,const tcu::UVec3 & size,const deUint32 * planeRowPitches,void * const * planePtrs,deUint32 channelNdx)3129 tcu::PixelBufferAccess getChannelAccess (const PlanarFormatDescription&	formatInfo,
3130 										 const tcu::UVec3&				size,
3131 										 const deUint32*				planeRowPitches,
3132 										 void* const*					planePtrs,
3133 										 deUint32						channelNdx)
3134 {
3135 	DE_ASSERT(formatInfo.hasChannelNdx(channelNdx));
3136 
3137 	const deUint32	planeNdx			= formatInfo.channels[channelNdx].planeNdx;
3138 	const deUint32	planeOffsetBytes	= formatInfo.channels[channelNdx].offsetBits / 8;
3139 	const deUint32	valueOffsetBits		= formatInfo.channels[channelNdx].offsetBits % 8;
3140 	const deUint32	pixelStrideBytes	= formatInfo.channels[channelNdx].strideBytes;
3141 
3142 	DE_ASSERT(size.x() % (formatInfo.blockWidth * formatInfo.planes[planeNdx].widthDivisor) == 0);
3143 	DE_ASSERT(size.y() % (formatInfo.blockHeight * formatInfo.planes[planeNdx].heightDivisor) == 0);
3144 
3145 	const deUint32	accessHeight		= size.y() / ( formatInfo.blockHeight * formatInfo.planes[planeNdx].heightDivisor );
3146 	const deUint32	elementSizeBytes	= formatInfo.planes[planeNdx].elementSizeBytes;
3147 	const deUint32	rowPitch			= planeRowPitches[planeNdx];
3148 
3149 	DE_ASSERT(elementSizeBytes % pixelStrideBytes == 0);
3150 
3151 	tcu::IVec3		texDivider(
3152 		std::max(formatInfo.blockWidth * formatInfo.planes[planeNdx].widthDivisor * pixelStrideBytes / elementSizeBytes, 1u),
3153 		std::max(formatInfo.blockHeight * formatInfo.planes[planeNdx].heightDivisor * pixelStrideBytes / elementSizeBytes, 1u),
3154 		1);
3155 
3156 	return tcu::PixelBufferAccess(getChannelAccessFormat((tcu::TextureChannelClass)formatInfo.channels[channelNdx].type,
3157 														 valueOffsetBits,
3158 														 formatInfo.channels[channelNdx].sizeBits),
3159 														 tcu::IVec3((int)size.x(), (int)size.y(), (int)size.z()),
3160 														 tcu::IVec3((int)pixelStrideBytes, (int)rowPitch, (int)(accessHeight*rowPitch)),
3161 														 texDivider,
3162 														 (deUint8*)planePtrs[planeNdx] + planeOffsetBytes);
3163 }
3164 
getChannelAccess(const PlanarFormatDescription & formatInfo,const tcu::UVec3 & size,const deUint32 * planeRowPitches,const void * const * planePtrs,deUint32 channelNdx)3165 tcu::ConstPixelBufferAccess getChannelAccess (const PlanarFormatDescription&	formatInfo,
3166 											  const tcu::UVec3&					size,
3167 											  const deUint32*					planeRowPitches,
3168 											  const void* const*				planePtrs,
3169 											  deUint32							channelNdx)
3170 {
3171 	return getChannelAccess(formatInfo, size, planeRowPitches, const_cast<void* const*>(planePtrs), channelNdx);
3172 }
3173 
imageUtilSelfTest(void)3174 void imageUtilSelfTest (void)
3175 {
3176 	for (int formatNdx = 0; formatNdx < VK_CORE_FORMAT_LAST; formatNdx++)
3177 	{
3178 		const VkFormat	format	= (VkFormat)formatNdx;
3179 
3180 		if (format == VK_FORMAT_R64_UINT			||
3181 			format == VK_FORMAT_R64_SINT			||
3182 			format == VK_FORMAT_R64G64_UINT			||
3183 			format == VK_FORMAT_R64G64_SINT			||
3184 			format == VK_FORMAT_R64G64B64_UINT		||
3185 			format == VK_FORMAT_R64G64B64_SINT		||
3186 			format == VK_FORMAT_R64G64B64A64_UINT	||
3187 			format == VK_FORMAT_R64G64B64A64_SINT)
3188 			continue; // \todo [2015-12-05 pyry] Add framework support for (u)int64 channel type
3189 
3190 		if (format != VK_FORMAT_UNDEFINED && !isCompressedFormat(format))
3191 		{
3192 			const tcu::TextureFormat	tcuFormat		= mapVkFormat(format);
3193 			const VkFormat				remappedFormat	= mapTextureFormat(tcuFormat);
3194 
3195 			DE_TEST_ASSERT(isValid(tcuFormat));
3196 
3197 			if (fullTextureFormatRoundTripSupported(format))
3198 				DE_TEST_ASSERT(format == remappedFormat);
3199 		}
3200 	}
3201 
3202 	for (int formatNdx = VK_FORMAT_G8B8G8R8_422_UNORM_KHR; formatNdx <= VK_FORMAT_G16_B16_R16_3PLANE_444_UNORM_KHR; formatNdx++)
3203 	{
3204 		const VkFormat					format	= (VkFormat)formatNdx;
3205 		const PlanarFormatDescription&	info	= getPlanarFormatDescription(format);
3206 
3207 		DE_TEST_ASSERT(isYCbCrFormat(format));
3208 		DE_TEST_ASSERT(de::inRange<deUint8>(info.numPlanes, 1u, 3u));
3209 		DE_TEST_ASSERT(info.numPlanes == getPlaneCount(format));
3210 	}
3211 }
3212 
3213 struct CompressedFormatParameters
3214 {
3215 	VkFormat	format;
3216 	deUint32	blockBytes;
3217 	deUint32	blockWidth;
3218 	deUint32	blockHeight;
3219 };
3220 
3221 CompressedFormatParameters	compressedFormatParameters[VK_FORMAT_ASTC_12x12_SRGB_BLOCK - VK_FORMAT_BC1_RGB_UNORM_BLOCK + 1] =
3222 {
3223 	{ VK_FORMAT_BC1_RGB_UNORM_BLOCK,		8,	4,	4 },
3224 	{ VK_FORMAT_BC1_RGB_SRGB_BLOCK,			8,	4,	4 },
3225 	{ VK_FORMAT_BC1_RGBA_UNORM_BLOCK,		8,	4,	4 },
3226 	{ VK_FORMAT_BC1_RGBA_SRGB_BLOCK,		8,	4,	4 },
3227 	{ VK_FORMAT_BC2_UNORM_BLOCK,			16,	4,	4 },
3228 	{ VK_FORMAT_BC2_SRGB_BLOCK,				16,	4,	4 },
3229 	{ VK_FORMAT_BC3_UNORM_BLOCK,			16,	4,	4 },
3230 	{ VK_FORMAT_BC3_SRGB_BLOCK,				16,	4,	4 },
3231 	{ VK_FORMAT_BC4_UNORM_BLOCK,			8,	4,	4 },
3232 	{ VK_FORMAT_BC4_SNORM_BLOCK,			8,	4,	4 },
3233 	{ VK_FORMAT_BC5_UNORM_BLOCK,			16,	4,	4 },
3234 	{ VK_FORMAT_BC5_SNORM_BLOCK,			16,	4,	4 },
3235 	{ VK_FORMAT_BC6H_UFLOAT_BLOCK,			16,	4,	4 },
3236 	{ VK_FORMAT_BC6H_SFLOAT_BLOCK,			16,	4,	4 },
3237 	{ VK_FORMAT_BC7_UNORM_BLOCK,			16,	4,	4 },
3238 	{ VK_FORMAT_BC7_SRGB_BLOCK,				16,	4,	4 },
3239 	{ VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK,	8,	4,	4 },
3240 	{ VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK,		8,	4,	4 },
3241 	{ VK_FORMAT_ETC2_R8G8B8A1_UNORM_BLOCK,	8,	4,	4 },
3242 	{ VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK,	8,	4,	4 },
3243 	{ VK_FORMAT_ETC2_R8G8B8A8_UNORM_BLOCK,	16,	4,	4 },
3244 	{ VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK,	16,	4,	4 },
3245 	{ VK_FORMAT_EAC_R11_UNORM_BLOCK,		8,	4,	4 },
3246 	{ VK_FORMAT_EAC_R11_SNORM_BLOCK,		8,	4,	4 },
3247 	{ VK_FORMAT_EAC_R11G11_UNORM_BLOCK,		16,	4,	4 },
3248 	{ VK_FORMAT_EAC_R11G11_SNORM_BLOCK,		16,	4,	4 },
3249 	{ VK_FORMAT_ASTC_4x4_UNORM_BLOCK,		16,	4,	4 },
3250 	{ VK_FORMAT_ASTC_4x4_SRGB_BLOCK,		16,	4,	4 },
3251 	{ VK_FORMAT_ASTC_5x4_UNORM_BLOCK,		16,	5,	4 },
3252 	{ VK_FORMAT_ASTC_5x4_SRGB_BLOCK,		16,	5,	4 },
3253 	{ VK_FORMAT_ASTC_5x5_UNORM_BLOCK,		16,	5,	5 },
3254 	{ VK_FORMAT_ASTC_5x5_SRGB_BLOCK,		16,	5,	5 },
3255 	{ VK_FORMAT_ASTC_6x5_UNORM_BLOCK,		16,	6,	5 },
3256 	{ VK_FORMAT_ASTC_6x5_SRGB_BLOCK,		16,	6,	5 },
3257 	{ VK_FORMAT_ASTC_6x6_UNORM_BLOCK,		16,	6,	6 },
3258 	{ VK_FORMAT_ASTC_6x6_SRGB_BLOCK,		16,	6,	6 },
3259 	{ VK_FORMAT_ASTC_8x5_UNORM_BLOCK,		16,	8,	5 },
3260 	{ VK_FORMAT_ASTC_8x5_SRGB_BLOCK,		16,	8,	5 },
3261 	{ VK_FORMAT_ASTC_8x6_UNORM_BLOCK,		16,	8,	6 },
3262 	{ VK_FORMAT_ASTC_8x6_SRGB_BLOCK,		16,	8,	6 },
3263 	{ VK_FORMAT_ASTC_8x8_UNORM_BLOCK,		16,	8,	8 },
3264 	{ VK_FORMAT_ASTC_8x8_SRGB_BLOCK,		16,	8,	8 },
3265 	{ VK_FORMAT_ASTC_10x5_UNORM_BLOCK,		16,	10,	5 },
3266 	{ VK_FORMAT_ASTC_10x5_SRGB_BLOCK,		16,	10,	5 },
3267 	{ VK_FORMAT_ASTC_10x6_UNORM_BLOCK,		16,	10,	6 },
3268 	{ VK_FORMAT_ASTC_10x6_SRGB_BLOCK,		16,	10,	6 },
3269 	{ VK_FORMAT_ASTC_10x8_UNORM_BLOCK,		16,	10,	8 },
3270 	{ VK_FORMAT_ASTC_10x8_SRGB_BLOCK,		16,	10,	8 },
3271 	{ VK_FORMAT_ASTC_10x10_UNORM_BLOCK,		16,	10,	10 },
3272 	{ VK_FORMAT_ASTC_10x10_SRGB_BLOCK,		16,	10,	10 },
3273 	{ VK_FORMAT_ASTC_12x10_UNORM_BLOCK,		16,	12,	10 },
3274 	{ VK_FORMAT_ASTC_12x10_SRGB_BLOCK,		16,	12,	10 },
3275 	{ VK_FORMAT_ASTC_12x12_UNORM_BLOCK,		16,	12,	12 },
3276 	{ VK_FORMAT_ASTC_12x12_SRGB_BLOCK,		16,	12,	12 }
3277 };
3278 
getFormatComponentWidth(const VkFormat format,const deUint32 componentNdx)3279 deUint32 getFormatComponentWidth (const VkFormat format, const deUint32 componentNdx)
3280 {
3281 	const tcu::TextureFormat	tcuFormat		(mapVkFormat(format));
3282 	const deUint32				componentCount	(tcu::getNumUsedChannels(tcuFormat.order));
3283 
3284 	if (componentNdx >= componentCount)
3285 		DE_FATAL("Component index out of range");
3286 	else
3287 	{
3288 		switch (tcuFormat.type)
3289 		{
3290 			case tcu::TextureFormat::UNORM_INT8:
3291 			case tcu::TextureFormat::SNORM_INT8:
3292 			case tcu::TextureFormat::UNSIGNED_INT8:
3293 			case tcu::TextureFormat::SIGNED_INT8:
3294 				return 8;
3295 
3296 			case tcu::TextureFormat::UNORM_SHORT_12:
3297 				return 12;
3298 
3299 			case tcu::TextureFormat::UNORM_INT16:
3300 			case tcu::TextureFormat::SNORM_INT16:
3301 			case tcu::TextureFormat::UNSIGNED_INT16:
3302 			case tcu::TextureFormat::SIGNED_INT16:
3303 				return 16;
3304 
3305 			case tcu::TextureFormat::UNORM_INT24:
3306 			case tcu::TextureFormat::UNSIGNED_INT24:
3307 				return 24;
3308 
3309 			case tcu::TextureFormat::UNORM_INT32:
3310 			case tcu::TextureFormat::SNORM_INT32:
3311 			case tcu::TextureFormat::UNSIGNED_INT32:
3312 			case tcu::TextureFormat::SIGNED_INT32:
3313 				return 32;
3314 
3315 			case tcu::TextureFormat::FLOAT64:
3316 			return 64;
3317 
3318 			// Packed formats
3319 			case tcu::TextureFormat::UNORM_SHORT_4444:
3320 			case tcu::TextureFormat::UNSIGNED_SHORT_4444:
3321 			return 4;
3322 
3323 			case tcu::TextureFormat::UNORM_SHORT_565:
3324 			case tcu::TextureFormat::UNSIGNED_SHORT_565:
3325 				return (componentNdx == 1 ? 6 : 5);
3326 
3327 			case tcu::TextureFormat::UNSIGNED_INT_24_8:
3328 			case tcu::TextureFormat::UNSIGNED_INT_24_8_REV:
3329 			case tcu::TextureFormat::FLOAT_UNSIGNED_INT_24_8_REV:
3330 				return (componentNdx == 0 ? 24 : 8);
3331 
3332 			case tcu::TextureFormat::UNORM_SHORT_1555:
3333 				return (componentNdx == 0 ? 1 : 5);
3334 
3335 			case tcu::TextureFormat::UNORM_INT_1010102_REV:
3336 			case tcu::TextureFormat::SNORM_INT_1010102_REV:
3337 			case tcu::TextureFormat::UNSIGNED_INT_1010102_REV:
3338 			case tcu::TextureFormat::SIGNED_INT_1010102_REV:
3339 				return (componentNdx == 3 ? 2 : 10);
3340 
3341 			default:
3342 				DE_FATAL("Format unimplemented");
3343 		}
3344 	}
3345 
3346 	return 0;
3347 }
3348 
getRepresentableDiffUnorm(const VkFormat format,const deUint32 componentNdx)3349 float getRepresentableDiffUnorm (const VkFormat format, const deUint32 componentNdx)
3350 {
3351 	const deUint32 size (getFormatComponentWidth(format, componentNdx));
3352 
3353 	return 1.0f / float((1 << (size)) - 1);
3354 }
3355 
getRepresentableDiffSnorm(const VkFormat format,const deUint32 componentNdx)3356 float getRepresentableDiffSnorm (const VkFormat format, const deUint32 componentNdx)
3357 {
3358 	const deUint32 size (getFormatComponentWidth(format, componentNdx));
3359 
3360 	return 1.0f / float((1 << (size - 1)) - 1);
3361 }
3362 
getBlockSizeInBytes(const VkFormat compressedFormat)3363 deUint32 getBlockSizeInBytes (const VkFormat compressedFormat)
3364 {
3365 	deUint32 formatNdx = static_cast<deUint32>(compressedFormat - VK_FORMAT_BC1_RGB_UNORM_BLOCK);
3366 
3367 	DE_ASSERT(deInRange32(formatNdx, 0, DE_LENGTH_OF_ARRAY(compressedFormatParameters)));
3368 	DE_ASSERT(compressedFormatParameters[formatNdx].format == compressedFormat);
3369 
3370 	return compressedFormatParameters[formatNdx].blockBytes;
3371 }
3372 
getBlockWidth(const VkFormat compressedFormat)3373 deUint32 getBlockWidth (const VkFormat compressedFormat)
3374 {
3375 	deUint32 formatNdx = static_cast<deUint32>(compressedFormat - VK_FORMAT_BC1_RGB_UNORM_BLOCK);
3376 
3377 	DE_ASSERT(deInRange32(formatNdx, 0, DE_LENGTH_OF_ARRAY(compressedFormatParameters)));
3378 	DE_ASSERT(compressedFormatParameters[formatNdx].format == compressedFormat);
3379 
3380 	return compressedFormatParameters[formatNdx].blockWidth;
3381 }
3382 
getBlockHeight(const VkFormat compressedFormat)3383 deUint32 getBlockHeight (const VkFormat compressedFormat)
3384 {
3385 	deUint32 formatNdx = static_cast<deUint32>(compressedFormat - VK_FORMAT_BC1_RGB_UNORM_BLOCK);
3386 
3387 	DE_ASSERT(deInRange32(formatNdx, 0, DE_LENGTH_OF_ARRAY(compressedFormatParameters)));
3388 	DE_ASSERT(compressedFormatParameters[formatNdx].format == compressedFormat);
3389 
3390 	return compressedFormatParameters[formatNdx].blockHeight;
3391 }
3392 
mapFilterMode(tcu::Sampler::FilterMode filterMode)3393 VkFilter mapFilterMode (tcu::Sampler::FilterMode filterMode)
3394 {
3395 	DE_STATIC_ASSERT(tcu::Sampler::FILTERMODE_LAST == 6);
3396 
3397 	switch (filterMode)
3398 	{
3399 		case tcu::Sampler::NEAREST:					return VK_FILTER_NEAREST;
3400 		case tcu::Sampler::LINEAR:					return VK_FILTER_LINEAR;
3401 		case tcu::Sampler::NEAREST_MIPMAP_NEAREST:	return VK_FILTER_NEAREST;
3402 		case tcu::Sampler::NEAREST_MIPMAP_LINEAR:	return VK_FILTER_NEAREST;
3403 		case tcu::Sampler::LINEAR_MIPMAP_NEAREST:	return VK_FILTER_LINEAR;
3404 		case tcu::Sampler::LINEAR_MIPMAP_LINEAR:	return VK_FILTER_LINEAR;
3405 		default:
3406 			DE_FATAL("Illegal filter mode");
3407 			return (VkFilter)0;
3408 	}
3409 }
3410 
mapMipmapMode(tcu::Sampler::FilterMode filterMode)3411 VkSamplerMipmapMode mapMipmapMode (tcu::Sampler::FilterMode filterMode)
3412 {
3413 	DE_STATIC_ASSERT(tcu::Sampler::FILTERMODE_LAST == 6);
3414 
3415 	// \note VkSamplerCreateInfo doesn't have a flag for disabling mipmapping. Instead
3416 	//		 minLod = 0 and maxLod = 0.25 should be used to match OpenGL NEAREST and LINEAR
3417 	//		 filtering mode behavior.
3418 
3419 	switch (filterMode)
3420 	{
3421 		case tcu::Sampler::NEAREST:					return VK_SAMPLER_MIPMAP_MODE_NEAREST;
3422 		case tcu::Sampler::LINEAR:					return VK_SAMPLER_MIPMAP_MODE_NEAREST;
3423 		case tcu::Sampler::NEAREST_MIPMAP_NEAREST:	return VK_SAMPLER_MIPMAP_MODE_NEAREST;
3424 		case tcu::Sampler::NEAREST_MIPMAP_LINEAR:	return VK_SAMPLER_MIPMAP_MODE_LINEAR;
3425 		case tcu::Sampler::LINEAR_MIPMAP_NEAREST:	return VK_SAMPLER_MIPMAP_MODE_NEAREST;
3426 		case tcu::Sampler::LINEAR_MIPMAP_LINEAR:	return VK_SAMPLER_MIPMAP_MODE_LINEAR;
3427 		default:
3428 			DE_FATAL("Illegal filter mode");
3429 			return (VkSamplerMipmapMode)0;
3430 	}
3431 }
3432 
mapWrapMode(tcu::Sampler::WrapMode wrapMode)3433 VkSamplerAddressMode mapWrapMode (tcu::Sampler::WrapMode wrapMode)
3434 {
3435 	switch (wrapMode)
3436 	{
3437 		case tcu::Sampler::CLAMP_TO_EDGE:		return VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE;
3438 		case tcu::Sampler::CLAMP_TO_BORDER:		return VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER;
3439 		case tcu::Sampler::REPEAT_GL:			return VK_SAMPLER_ADDRESS_MODE_REPEAT;
3440 		case tcu::Sampler::MIRRORED_REPEAT_GL:	return VK_SAMPLER_ADDRESS_MODE_MIRRORED_REPEAT;
3441 		case tcu::Sampler::MIRRORED_ONCE:		return VK_SAMPLER_ADDRESS_MODE_MIRROR_CLAMP_TO_EDGE;
3442 		default:
3443 			DE_FATAL("Wrap mode can't be mapped to Vulkan");
3444 			return (vk::VkSamplerAddressMode)0;
3445 	}
3446 }
3447 
mapCompareMode(tcu::Sampler::CompareMode mode)3448 vk::VkCompareOp mapCompareMode (tcu::Sampler::CompareMode mode)
3449 {
3450 	switch (mode)
3451 	{
3452 		case tcu::Sampler::COMPAREMODE_NONE:				return vk::VK_COMPARE_OP_NEVER;
3453 		case tcu::Sampler::COMPAREMODE_LESS:				return vk::VK_COMPARE_OP_LESS;
3454 		case tcu::Sampler::COMPAREMODE_LESS_OR_EQUAL:		return vk::VK_COMPARE_OP_LESS_OR_EQUAL;
3455 		case tcu::Sampler::COMPAREMODE_GREATER:				return vk::VK_COMPARE_OP_GREATER;
3456 		case tcu::Sampler::COMPAREMODE_GREATER_OR_EQUAL:	return vk::VK_COMPARE_OP_GREATER_OR_EQUAL;
3457 		case tcu::Sampler::COMPAREMODE_EQUAL:				return vk::VK_COMPARE_OP_EQUAL;
3458 		case tcu::Sampler::COMPAREMODE_NOT_EQUAL:			return vk::VK_COMPARE_OP_NOT_EQUAL;
3459 		case tcu::Sampler::COMPAREMODE_ALWAYS:				return vk::VK_COMPARE_OP_ALWAYS;
3460 		case tcu::Sampler::COMPAREMODE_NEVER:				return vk::VK_COMPARE_OP_NEVER;
3461 		default:
3462 			DE_FATAL("Illegal compare mode");
3463 			return (vk::VkCompareOp)0;
3464 	}
3465 }
3466 
mapBorderColor(tcu::TextureChannelClass channelClass,const rr::GenericVec4 & color)3467 static VkBorderColor mapBorderColor (tcu::TextureChannelClass channelClass, const rr::GenericVec4& color)
3468 {
3469 	if (channelClass == tcu::TEXTURECHANNELCLASS_UNSIGNED_INTEGER)
3470 	{
3471 		const tcu::UVec4	uColor	= color.get<deUint32>();
3472 
3473 		if (uColor		== tcu::UVec4(0, 0, 0, 0)) return VK_BORDER_COLOR_INT_TRANSPARENT_BLACK;
3474 		else if (uColor	== tcu::UVec4(0, 0, 0, 1)) return VK_BORDER_COLOR_INT_OPAQUE_BLACK;
3475 		else if (uColor == tcu::UVec4(1, 1, 1, 1)) return VK_BORDER_COLOR_INT_OPAQUE_WHITE;
3476 	}
3477 	else if (channelClass == tcu::TEXTURECHANNELCLASS_SIGNED_INTEGER)
3478 	{
3479 		const tcu::IVec4	sColor	= color.get<deInt32>();
3480 
3481 		if (sColor		== tcu::IVec4(0, 0, 0, 0)) return VK_BORDER_COLOR_INT_TRANSPARENT_BLACK;
3482 		else if (sColor	== tcu::IVec4(0, 0, 0, 1)) return VK_BORDER_COLOR_INT_OPAQUE_BLACK;
3483 		else if (sColor == tcu::IVec4(1, 1, 1, 1)) return VK_BORDER_COLOR_INT_OPAQUE_WHITE;
3484 	}
3485 	else
3486 	{
3487 		const tcu::Vec4		fColor	= color.get<float>();
3488 
3489 		if (fColor		== tcu::Vec4(0.0f, 0.0f, 0.0f, 0.0f)) return VK_BORDER_COLOR_FLOAT_TRANSPARENT_BLACK;
3490 		else if (fColor == tcu::Vec4(0.0f, 0.0f, 0.0f, 1.0f)) return VK_BORDER_COLOR_FLOAT_OPAQUE_BLACK;
3491 		else if (fColor == tcu::Vec4(1.0f, 1.0f, 1.0f, 1.0f)) return VK_BORDER_COLOR_FLOAT_OPAQUE_WHITE;
3492 	}
3493 
3494 	DE_FATAL("Unsupported border color");
3495 	return VK_BORDER_COLOR_LAST;
3496 }
3497 
mapSampler(const tcu::Sampler & sampler,const tcu::TextureFormat & format,float minLod,float maxLod,bool unnormal)3498 VkSamplerCreateInfo mapSampler (const tcu::Sampler& sampler, const tcu::TextureFormat& format, float minLod, float maxLod, bool unnormal)
3499 {
3500 	const bool					compareEnabled	= (sampler.compare != tcu::Sampler::COMPAREMODE_NONE);
3501 	const VkCompareOp			compareOp		= (compareEnabled) ? (mapCompareMode(sampler.compare)) : (VK_COMPARE_OP_ALWAYS);
3502 	const VkBorderColor			borderColor		= mapBorderColor(getTextureChannelClass(format.type), sampler.borderColor);
3503 	const bool					isMipmapEnabled	= (sampler.minFilter != tcu::Sampler::NEAREST && sampler.minFilter != tcu::Sampler::LINEAR);
3504 
3505 	const VkSamplerCreateInfo	createInfo		=
3506 	{
3507 		VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO,
3508 		DE_NULL,
3509 		(VkSamplerCreateFlags)0,
3510 		mapFilterMode(sampler.magFilter),							// magFilter
3511 		mapFilterMode(sampler.minFilter),							// minFilter
3512 		mapMipmapMode(sampler.minFilter),							// mipMode
3513 		mapWrapMode(sampler.wrapS),									// addressU
3514 		mapWrapMode(sampler.wrapT),									// addressV
3515 		mapWrapMode(sampler.wrapR),									// addressW
3516 		0.0f,														// mipLodBias
3517 		VK_FALSE,													// anisotropyEnable
3518 		1.0f,														// maxAnisotropy
3519 		(VkBool32)(compareEnabled ? VK_TRUE : VK_FALSE),			// compareEnable
3520 		compareOp,													// compareOp
3521 		(isMipmapEnabled ? minLod : 0.0f),							// minLod
3522 		(isMipmapEnabled ? maxLod : (unnormal ? 0.0f : 0.25f)),		// maxLod
3523 		borderColor,												// borderColor
3524 		(VkBool32)(sampler.normalizedCoords ? VK_FALSE : VK_TRUE),	// unnormalizedCoords
3525 	};
3526 
3527 	return createInfo;
3528 }
3529 
mapVkSampler(const VkSamplerCreateInfo & samplerCreateInfo)3530 tcu::Sampler mapVkSampler (const VkSamplerCreateInfo& samplerCreateInfo)
3531 {
3532 	// \note minLod & maxLod are not supported by tcu::Sampler. LOD must be clamped
3533 	//       before passing it to tcu::Texture*::sample*()
3534 
3535 	tcu::Sampler::ReductionMode reductionMode = tcu::Sampler::WEIGHTED_AVERAGE;
3536 
3537 	void const *pNext = samplerCreateInfo.pNext;
3538 	while (pNext != DE_NULL)
3539 	{
3540 		const VkStructureType nextType = *reinterpret_cast<const VkStructureType*>(pNext);
3541 		switch (nextType)
3542 		{
3543 			case VK_STRUCTURE_TYPE_SAMPLER_REDUCTION_MODE_CREATE_INFO_EXT:
3544 			{
3545 				const VkSamplerReductionModeCreateInfo reductionModeCreateInfo = *reinterpret_cast<const VkSamplerReductionModeCreateInfo*>(pNext);
3546 				reductionMode = mapVkSamplerReductionMode(reductionModeCreateInfo.reductionMode);
3547 				pNext = reinterpret_cast<const VkSamplerReductionModeCreateInfo*>(pNext)->pNext;
3548 				break;
3549 			}
3550 			case VK_STRUCTURE_TYPE_SAMPLER_YCBCR_CONVERSION_INFO:
3551 				pNext = reinterpret_cast<const VkSamplerYcbcrConversionInfo*>(pNext)->pNext;
3552 				break;
3553 			default:
3554 				TCU_FAIL("Unrecognized sType in chained sampler create info");
3555 		}
3556 	}
3557 
3558 
3559 
3560 	tcu::Sampler sampler(mapVkSamplerAddressMode(samplerCreateInfo.addressModeU),
3561 						 mapVkSamplerAddressMode(samplerCreateInfo.addressModeV),
3562 						 mapVkSamplerAddressMode(samplerCreateInfo.addressModeW),
3563 						 mapVkMinTexFilter(samplerCreateInfo.minFilter, samplerCreateInfo.mipmapMode),
3564 						 mapVkMagTexFilter(samplerCreateInfo.magFilter),
3565 						 0.0f,
3566 						 !samplerCreateInfo.unnormalizedCoordinates,
3567 						 samplerCreateInfo.compareEnable ? mapVkSamplerCompareOp(samplerCreateInfo.compareOp)
3568 														 : tcu::Sampler::COMPAREMODE_NONE,
3569 						 0,
3570 						 tcu::Vec4(0.0f, 0.0f, 0.0f, 0.0f),
3571 						 true,
3572 						 tcu::Sampler::MODE_DEPTH,
3573 						 reductionMode);
3574 
3575 	if (samplerCreateInfo.anisotropyEnable)
3576 		TCU_THROW(InternalError, "Anisotropic filtering is not supported by tcu::Sampler");
3577 
3578 	switch (samplerCreateInfo.borderColor)
3579 	{
3580 		case VK_BORDER_COLOR_INT_OPAQUE_BLACK:
3581 			sampler.borderColor = tcu::UVec4(0,0,0,1);
3582 			break;
3583 		case VK_BORDER_COLOR_FLOAT_OPAQUE_BLACK:
3584 			sampler.borderColor = tcu::Vec4(0.0f, 0.0f, 0.0f, 1.0f);
3585 			break;
3586 		case VK_BORDER_COLOR_INT_OPAQUE_WHITE:
3587 			sampler.borderColor = tcu::UVec4(1, 1, 1, 1);
3588 			break;
3589 		case VK_BORDER_COLOR_FLOAT_OPAQUE_WHITE:
3590 			sampler.borderColor = tcu::Vec4(1.0f, 1.0f, 1.0f, 1.0f);
3591 			break;
3592 		case VK_BORDER_COLOR_INT_TRANSPARENT_BLACK:
3593 			sampler.borderColor = tcu::UVec4(0,0,0,0);
3594 			break;
3595 		case VK_BORDER_COLOR_FLOAT_TRANSPARENT_BLACK:
3596 			sampler.borderColor = tcu::Vec4(0.0f, 0.0f, 0.0f, 0.0f);
3597 			break;
3598 
3599 		default:
3600 			DE_ASSERT(false);
3601 			break;
3602 	}
3603 
3604 	return sampler;
3605 }
3606 
mapVkSamplerCompareOp(VkCompareOp compareOp)3607 tcu::Sampler::CompareMode mapVkSamplerCompareOp (VkCompareOp compareOp)
3608 {
3609 	switch (compareOp)
3610 	{
3611 		case VK_COMPARE_OP_NEVER:				return tcu::Sampler::COMPAREMODE_NEVER;
3612 		case VK_COMPARE_OP_LESS:				return tcu::Sampler::COMPAREMODE_LESS;
3613 		case VK_COMPARE_OP_EQUAL:				return tcu::Sampler::COMPAREMODE_EQUAL;
3614 		case VK_COMPARE_OP_LESS_OR_EQUAL:		return tcu::Sampler::COMPAREMODE_LESS_OR_EQUAL;
3615 		case VK_COMPARE_OP_GREATER:				return tcu::Sampler::COMPAREMODE_GREATER;
3616 		case VK_COMPARE_OP_NOT_EQUAL:			return tcu::Sampler::COMPAREMODE_NOT_EQUAL;
3617 		case VK_COMPARE_OP_GREATER_OR_EQUAL:	return tcu::Sampler::COMPAREMODE_GREATER_OR_EQUAL;
3618 		case VK_COMPARE_OP_ALWAYS:				return tcu::Sampler::COMPAREMODE_ALWAYS;
3619 		default:
3620 			break;
3621 	}
3622 
3623 	DE_ASSERT(false);
3624 	return tcu::Sampler::COMPAREMODE_LAST;
3625 }
3626 
mapVkSamplerAddressMode(VkSamplerAddressMode addressMode)3627 tcu::Sampler::WrapMode mapVkSamplerAddressMode (VkSamplerAddressMode addressMode)
3628 {
3629 	switch (addressMode)
3630 	{
3631 		case VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE:			return tcu::Sampler::CLAMP_TO_EDGE;
3632 		case VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER:		return tcu::Sampler::CLAMP_TO_BORDER;
3633 		case VK_SAMPLER_ADDRESS_MODE_MIRRORED_REPEAT:		return tcu::Sampler::MIRRORED_REPEAT_GL;
3634 		case VK_SAMPLER_ADDRESS_MODE_MIRROR_CLAMP_TO_EDGE:	return tcu::Sampler::MIRRORED_ONCE;
3635 		case VK_SAMPLER_ADDRESS_MODE_REPEAT:				return tcu::Sampler::REPEAT_GL;
3636 		default:
3637 			break;
3638 	}
3639 
3640 	DE_ASSERT(false);
3641 	return tcu::Sampler::WRAPMODE_LAST;
3642 }
3643 
mapVkSamplerReductionMode(VkSamplerReductionMode reductionMode)3644 tcu::Sampler::ReductionMode mapVkSamplerReductionMode (VkSamplerReductionMode reductionMode)
3645 {
3646 	switch (reductionMode)
3647 	{
3648 		case VK_SAMPLER_REDUCTION_MODE_WEIGHTED_AVERAGE:	return tcu::Sampler::WEIGHTED_AVERAGE;
3649 		case VK_SAMPLER_REDUCTION_MODE_MIN:					return tcu::Sampler::MIN;
3650 		case VK_SAMPLER_REDUCTION_MODE_MAX:					return tcu::Sampler::MAX;
3651 		default:
3652 			break;
3653 	}
3654 
3655 	DE_ASSERT(false);
3656 	return tcu::Sampler::REDUCTIONMODE_LAST;
3657 }
3658 
mapVkMinTexFilter(VkFilter filter,VkSamplerMipmapMode mipMode)3659 tcu::Sampler::FilterMode mapVkMinTexFilter (VkFilter filter, VkSamplerMipmapMode mipMode)
3660 {
3661 	switch (filter)
3662 	{
3663 		case VK_FILTER_LINEAR:
3664 			switch (mipMode)
3665 			{
3666 				case VK_SAMPLER_MIPMAP_MODE_LINEAR:		return tcu::Sampler::LINEAR_MIPMAP_LINEAR;
3667 				case VK_SAMPLER_MIPMAP_MODE_NEAREST:	return tcu::Sampler::LINEAR_MIPMAP_NEAREST;
3668 				default:
3669 					break;
3670 			}
3671 			break;
3672 
3673 		case VK_FILTER_NEAREST:
3674 			switch (mipMode)
3675 			{
3676 				case VK_SAMPLER_MIPMAP_MODE_LINEAR:		return tcu::Sampler::NEAREST_MIPMAP_LINEAR;
3677 				case VK_SAMPLER_MIPMAP_MODE_NEAREST:	return tcu::Sampler::NEAREST_MIPMAP_NEAREST;
3678 				default:
3679 					break;
3680 			}
3681 			break;
3682 
3683 		default:
3684 			break;
3685 	}
3686 
3687 	DE_ASSERT(false);
3688 	return tcu::Sampler::FILTERMODE_LAST;
3689 }
3690 
mapVkMagTexFilter(VkFilter filter)3691 tcu::Sampler::FilterMode mapVkMagTexFilter (VkFilter filter)
3692 {
3693 	switch (filter)
3694 	{
3695 		case VK_FILTER_LINEAR:		return tcu::Sampler::LINEAR;
3696 		case VK_FILTER_NEAREST:		return tcu::Sampler::NEAREST;
3697 		default:
3698 			break;
3699 	}
3700 
3701 	DE_ASSERT(false);
3702 	return tcu::Sampler::FILTERMODE_LAST;
3703 }
3704 
3705 //! Get a format the matches the layout in buffer memory used for a
3706 //! buffer<->image copy on a depth/stencil format.
getDepthCopyFormat(VkFormat combinedFormat)3707 tcu::TextureFormat getDepthCopyFormat (VkFormat combinedFormat)
3708 {
3709 	switch (combinedFormat)
3710 	{
3711 		case VK_FORMAT_D16_UNORM:
3712 		case VK_FORMAT_X8_D24_UNORM_PACK32:
3713 		case VK_FORMAT_D32_SFLOAT:
3714 			return mapVkFormat(combinedFormat);
3715 
3716 		case VK_FORMAT_D16_UNORM_S8_UINT:
3717 			return mapVkFormat(VK_FORMAT_D16_UNORM);
3718 		case VK_FORMAT_D24_UNORM_S8_UINT:
3719 			return mapVkFormat(VK_FORMAT_X8_D24_UNORM_PACK32);
3720 		case VK_FORMAT_D32_SFLOAT_S8_UINT:
3721 			return mapVkFormat(VK_FORMAT_D32_SFLOAT);
3722 
3723 		case VK_FORMAT_S8_UINT:
3724 		default:
3725 			DE_FATAL("Unexpected depth/stencil format");
3726 			return tcu::TextureFormat();
3727 	}
3728 }
3729 
3730 //! Get a format the matches the layout in buffer memory used for a
3731 //! buffer<->image copy on a depth/stencil format.
getStencilCopyFormat(VkFormat combinedFormat)3732 tcu::TextureFormat getStencilCopyFormat (VkFormat combinedFormat)
3733 {
3734 	switch (combinedFormat)
3735 	{
3736 		case VK_FORMAT_D16_UNORM_S8_UINT:
3737 		case VK_FORMAT_D24_UNORM_S8_UINT:
3738 		case VK_FORMAT_D32_SFLOAT_S8_UINT:
3739 		case VK_FORMAT_S8_UINT:
3740 			return mapVkFormat(VK_FORMAT_S8_UINT);
3741 
3742 		case VK_FORMAT_D16_UNORM:
3743 		case VK_FORMAT_X8_D24_UNORM_PACK32:
3744 		case VK_FORMAT_D32_SFLOAT:
3745 		default:
3746 			DE_FATAL("Unexpected depth/stencil format");
3747 			return tcu::TextureFormat();
3748 	}
3749 }
3750 
getImageAspectFlags(const tcu::TextureFormat textureFormat)3751 VkImageAspectFlags getImageAspectFlags (const tcu::TextureFormat textureFormat)
3752 {
3753 	VkImageAspectFlags imageAspectFlags = 0;
3754 
3755 	if (tcu::hasDepthComponent(textureFormat.order))
3756 		imageAspectFlags |= VK_IMAGE_ASPECT_DEPTH_BIT;
3757 
3758 	if (tcu::hasStencilComponent(textureFormat.order))
3759 		imageAspectFlags |= VK_IMAGE_ASPECT_STENCIL_BIT;
3760 
3761 	if (imageAspectFlags == 0)
3762 		imageAspectFlags = VK_IMAGE_ASPECT_COLOR_BIT;
3763 
3764 	return imageAspectFlags;
3765 }
3766 
mipLevelExtents(const VkExtent3D & baseExtents,const deUint32 mipLevel)3767 VkExtent3D mipLevelExtents (const VkExtent3D& baseExtents, const deUint32 mipLevel)
3768 {
3769 	VkExtent3D result;
3770 
3771 	result.width	= std::max(baseExtents.width >> mipLevel, 1u);
3772 	result.height	= std::max(baseExtents.height >> mipLevel, 1u);
3773 	result.depth	= std::max(baseExtents.depth >> mipLevel, 1u);
3774 
3775 	return result;
3776 }
3777 
alignedDivide(const VkExtent3D & extent,const VkExtent3D & divisor)3778 tcu::UVec3 alignedDivide (const VkExtent3D& extent, const VkExtent3D& divisor)
3779 {
3780 	tcu::UVec3 result;
3781 
3782 	result.x() = extent.width  / divisor.width  + ((extent.width  % divisor.width != 0)  ? 1u : 0u);
3783 	result.y() = extent.height / divisor.height + ((extent.height % divisor.height != 0) ? 1u : 0u);
3784 	result.z() = extent.depth  / divisor.depth  + ((extent.depth  % divisor.depth != 0)  ? 1u : 0u);
3785 
3786 	return result;
3787 }
3788 
copyBufferToImage(const DeviceInterface & vk,const VkCommandBuffer & cmdBuffer,const VkBuffer & buffer,VkDeviceSize bufferSize,const std::vector<VkBufferImageCopy> & copyRegions,VkImageAspectFlags imageAspectFlags,deUint32 mipLevels,deUint32 arrayLayers,VkImage destImage,VkImageLayout destImageLayout,VkPipelineStageFlags destImageDstStageFlags)3789 void copyBufferToImage (const DeviceInterface&					vk,
3790 						const VkCommandBuffer&					cmdBuffer,
3791 						const VkBuffer&							buffer,
3792 						VkDeviceSize							bufferSize,
3793 						const std::vector<VkBufferImageCopy>&	copyRegions,
3794 						VkImageAspectFlags						imageAspectFlags,
3795 						deUint32								mipLevels,
3796 						deUint32								arrayLayers,
3797 						VkImage									destImage,
3798 						VkImageLayout							destImageLayout,
3799 						VkPipelineStageFlags					destImageDstStageFlags)
3800 {
3801 	// Barriers for copying buffer to image
3802 	const VkBufferMemoryBarrier preBufferBarrier =
3803 	{
3804 		VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,	// VkStructureType	sType;
3805 		DE_NULL,									// const void*		pNext;
3806 		VK_ACCESS_HOST_WRITE_BIT,					// VkAccessFlags	srcAccessMask;
3807 		VK_ACCESS_TRANSFER_READ_BIT,				// VkAccessFlags	dstAccessMask;
3808 		VK_QUEUE_FAMILY_IGNORED,					// deUint32			srcQueueFamilyIndex;
3809 		VK_QUEUE_FAMILY_IGNORED,					// deUint32			dstQueueFamilyIndex;
3810 		buffer,										// VkBuffer			buffer;
3811 		0u,											// VkDeviceSize		offset;
3812 		bufferSize									// VkDeviceSize		size;
3813 	};
3814 
3815 	const VkImageMemoryBarrier preImageBarrier =
3816 	{
3817 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,			// VkStructureType			sType;
3818 		DE_NULL,										// const void*				pNext;
3819 		0u,												// VkAccessFlags			srcAccessMask;
3820 		VK_ACCESS_TRANSFER_WRITE_BIT,					// VkAccessFlags			dstAccessMask;
3821 		VK_IMAGE_LAYOUT_UNDEFINED,						// VkImageLayout			oldLayout;
3822 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,			// VkImageLayout			newLayout;
3823 		VK_QUEUE_FAMILY_IGNORED,						// deUint32					srcQueueFamilyIndex;
3824 		VK_QUEUE_FAMILY_IGNORED,						// deUint32					dstQueueFamilyIndex;
3825 		destImage,										// VkImage					image;
3826 		{												// VkImageSubresourceRange	subresourceRange;
3827 			imageAspectFlags,							// VkImageAspectFlags		aspect;
3828 			0u,											// deUint32					baseMipLevel;
3829 			mipLevels,									// deUint32					mipLevels;
3830 			0u,											// deUint32					baseArraySlice;
3831 			arrayLayers									// deUint32					arraySize;
3832 		}
3833 	};
3834 
3835 	const VkImageMemoryBarrier postImageBarrier =
3836 	{
3837 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,			// VkStructureType			sType;
3838 		DE_NULL,										// const void*				pNext;
3839 		VK_ACCESS_TRANSFER_WRITE_BIT,					// VkAccessFlags			srcAccessMask;
3840 		VK_ACCESS_SHADER_READ_BIT,						// VkAccessFlags			dstAccessMask;
3841 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,			// VkImageLayout			oldLayout;
3842 		destImageLayout,								// VkImageLayout			newLayout;
3843 		VK_QUEUE_FAMILY_IGNORED,						// deUint32					srcQueueFamilyIndex;
3844 		VK_QUEUE_FAMILY_IGNORED,						// deUint32					dstQueueFamilyIndex;
3845 		destImage,										// VkImage					image;
3846 		{												// VkImageSubresourceRange	subresourceRange;
3847 			imageAspectFlags,							// VkImageAspectFlags		aspect;
3848 			0u,											// deUint32					baseMipLevel;
3849 			mipLevels,									// deUint32					mipLevels;
3850 			0u,											// deUint32					baseArraySlice;
3851 			arrayLayers									// deUint32					arraySize;
3852 		}
3853 	};
3854 
3855 	// Copy buffer to image
3856 	vk.cmdPipelineBarrier(cmdBuffer, VK_PIPELINE_STAGE_HOST_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 1, &preBufferBarrier, 1, &preImageBarrier);
3857 	vk.cmdCopyBufferToImage(cmdBuffer, buffer, destImage, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, (deUint32)copyRegions.size(), copyRegions.data());
3858 	vk.cmdPipelineBarrier(cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, destImageDstStageFlags, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &postImageBarrier);
3859 }
3860 
copyBufferToImage(const DeviceInterface & vk,VkDevice device,VkQueue queue,deUint32 queueFamilyIndex,const VkBuffer & buffer,VkDeviceSize bufferSize,const std::vector<VkBufferImageCopy> & copyRegions,const VkSemaphore * waitSemaphore,VkImageAspectFlags imageAspectFlags,deUint32 mipLevels,deUint32 arrayLayers,VkImage destImage,VkImageLayout destImageLayout,VkPipelineStageFlags destImageDstStageFlags)3861 void copyBufferToImage (const DeviceInterface&					vk,
3862 						VkDevice								device,
3863 						VkQueue									queue,
3864 						deUint32								queueFamilyIndex,
3865 						const VkBuffer&							buffer,
3866 						VkDeviceSize							bufferSize,
3867 						const std::vector<VkBufferImageCopy>&	copyRegions,
3868 						const VkSemaphore*						waitSemaphore,
3869 						VkImageAspectFlags						imageAspectFlags,
3870 						deUint32								mipLevels,
3871 						deUint32								arrayLayers,
3872 						VkImage									destImage,
3873 						VkImageLayout							destImageLayout,
3874 						VkPipelineStageFlags					destImageDstStageFlags)
3875 {
3876 	Move<VkCommandPool>		cmdPool		= createCommandPool(vk, device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, queueFamilyIndex);
3877 	Move<VkCommandBuffer>	cmdBuffer	= allocateCommandBuffer(vk, device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
3878 	Move<VkFence>			fence		= createFence(vk, device);
3879 
3880 	const VkCommandBufferBeginInfo cmdBufferBeginInfo =
3881 	{
3882 		VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO,	// VkStructureType					sType;
3883 		DE_NULL,										// const void*						pNext;
3884 		VK_COMMAND_BUFFER_USAGE_ONE_TIME_SUBMIT_BIT,	// VkCommandBufferUsageFlags		flags;
3885 		(const VkCommandBufferInheritanceInfo*)DE_NULL,
3886 	};
3887 
3888 	VK_CHECK(vk.beginCommandBuffer(*cmdBuffer, &cmdBufferBeginInfo));
3889 	copyBufferToImage(vk, *cmdBuffer, buffer, bufferSize, copyRegions, imageAspectFlags, mipLevels, arrayLayers, destImage, destImageLayout, destImageDstStageFlags);
3890 	VK_CHECK(vk.endCommandBuffer(*cmdBuffer));
3891 
3892 	const VkPipelineStageFlags pipelineStageFlags = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT;
3893 
3894 	const VkSubmitInfo submitInfo =
3895 	{
3896 		VK_STRUCTURE_TYPE_SUBMIT_INFO,	// VkStructureType				sType;
3897 		DE_NULL,						// const void*					pNext;
3898 		waitSemaphore ? 1u : 0u,		// deUint32						waitSemaphoreCount;
3899 		waitSemaphore,					// const VkSemaphore*			pWaitSemaphores;
3900 		&pipelineStageFlags,			// const VkPipelineStageFlags*	pWaitDstStageMask;
3901 		1u,								// deUint32						commandBufferCount;
3902 		&cmdBuffer.get(),				// const VkCommandBuffer*		pCommandBuffers;
3903 		0u,								// deUint32						signalSemaphoreCount;
3904 		DE_NULL							// const VkSemaphore*			pSignalSemaphores;
3905 	};
3906 
3907 	try
3908 	{
3909 		VK_CHECK(vk.queueSubmit(queue, 1, &submitInfo, *fence));
3910 		VK_CHECK(vk.waitForFences(device, 1, &fence.get(), true, ~(0ull) /* infinity */));
3911 	}
3912 	catch (...)
3913 	{
3914 		VK_CHECK(vk.deviceWaitIdle(device));
3915 		throw;
3916 	}
3917 }
3918 
copyImageToBuffer(const DeviceInterface & vk,VkCommandBuffer cmdBuffer,VkImage image,VkBuffer buffer,tcu::IVec2 size,VkAccessFlags srcAccessMask,VkImageLayout oldLayout,deUint32 numLayers,VkImageAspectFlags barrierAspect,VkImageAspectFlags copyAspect)3919 void copyImageToBuffer (const DeviceInterface&	vk,
3920 						VkCommandBuffer			cmdBuffer,
3921 						VkImage					image,
3922 						VkBuffer				buffer,
3923 						tcu::IVec2				size,
3924 						VkAccessFlags			srcAccessMask,
3925 						VkImageLayout			oldLayout,
3926 						deUint32				numLayers,
3927 						VkImageAspectFlags		barrierAspect,
3928 						VkImageAspectFlags		copyAspect)
3929 {
3930 	const VkImageMemoryBarrier	imageBarrier	=
3931 	{
3932 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,							// VkStructureType			sType;
3933 		DE_NULL,														// const void*				pNext;
3934 		srcAccessMask,													// VkAccessFlags			srcAccessMask;
3935 		VK_ACCESS_TRANSFER_READ_BIT,									// VkAccessFlags			dstAccessMask;
3936 		oldLayout,														// VkImageLayout			oldLayout;
3937 		VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,							// VkImageLayout			newLayout;
3938 		VK_QUEUE_FAMILY_IGNORED,										// deUint32					srcQueueFamilyIndex;
3939 		VK_QUEUE_FAMILY_IGNORED,										// deUint32					destQueueFamilyIndex;
3940 		image,															// VkImage					image;
3941 		makeImageSubresourceRange(barrierAspect, 0u, 1u, 0, numLayers)	// VkImageSubresourceRange	subresourceRange;
3942 	};
3943 
3944 	vk.cmdPipelineBarrier(cmdBuffer, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0u,
3945 						  0u, DE_NULL, 0u, DE_NULL, 1u, &imageBarrier);
3946 
3947 	const VkImageSubresourceLayers	subresource	=
3948 	{
3949 		copyAspect,									// VkImageAspectFlags	aspectMask;
3950 		0u,											// deUint32				mipLevel;
3951 		0u,											// deUint32				baseArrayLayer;
3952 		numLayers									// deUint32				layerCount;
3953 	};
3954 
3955 	const VkBufferImageCopy			region		=
3956 	{
3957 		0ull,										// VkDeviceSize					bufferOffset;
3958 		0u,											// deUint32						bufferRowLength;
3959 		0u,											// deUint32						bufferImageHeight;
3960 		subresource,								// VkImageSubresourceLayers		imageSubresource;
3961 		makeOffset3D(0, 0, 0),						// VkOffset3D					imageOffset;
3962 		makeExtent3D(size.x(), size.y(), 1u)		// VkExtent3D					imageExtent;
3963 	};
3964 
3965 	vk.cmdCopyImageToBuffer(cmdBuffer, image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, buffer, 1u, &region);
3966 
3967 	const VkBufferMemoryBarrier	bufferBarrier =
3968 	{
3969 		VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,	// VkStructureType	sType;
3970 		DE_NULL,									// const void*		pNext;
3971 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags	srcAccessMask;
3972 		VK_ACCESS_HOST_READ_BIT,					// VkAccessFlags	dstAccessMask;
3973 		VK_QUEUE_FAMILY_IGNORED,					// deUint32			srcQueueFamilyIndex;
3974 		VK_QUEUE_FAMILY_IGNORED,					// deUint32			dstQueueFamilyIndex;
3975 		buffer,										// VkBuffer			buffer;
3976 		0ull,										// VkDeviceSize		offset;
3977 		VK_WHOLE_SIZE								// VkDeviceSize		size;
3978 	};
3979 
3980 	vk.cmdPipelineBarrier(cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_HOST_BIT, 0u,
3981 						  0u, DE_NULL, 1u, &bufferBarrier, 0u, DE_NULL);
3982 }
3983 
clearColorImage(const DeviceInterface & vk,const VkDevice device,const VkQueue queue,deUint32 queueFamilyIndex,VkImage image,tcu::Vec4 clearColor,VkImageLayout oldLayout,VkImageLayout newLayout,VkPipelineStageFlags dstStageFlags)3984 void clearColorImage (const DeviceInterface&	vk,
3985 					  const VkDevice			device,
3986 					  const VkQueue				queue,
3987 					  deUint32					queueFamilyIndex,
3988 					  VkImage					image,
3989 					  tcu::Vec4					clearColor,
3990 					  VkImageLayout				oldLayout,
3991 					  VkImageLayout				newLayout,
3992 					  VkPipelineStageFlags		dstStageFlags)
3993 {
3994 	Move<VkCommandPool>				cmdPool				= createCommandPool(vk, device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, queueFamilyIndex);
3995 	Move<VkCommandBuffer>			cmdBuffer			= allocateCommandBuffer(vk, device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
3996 
3997 	const VkClearColorValue			clearColorValue		= makeClearValueColor(clearColor).color;
3998 
3999 	const VkImageSubresourceRange	subresourceRange	=
4000 	{
4001 		VK_IMAGE_ASPECT_COLOR_BIT,	// VkImageAspectFlags	aspectMask
4002 		0u,							// deUint32				baseMipLevel
4003 		1u,							// deUint32				levelCount
4004 		0u,							// deUint32				baseArrayLayer
4005 		1u,							// deUint32				layerCount
4006 	};
4007 
4008 	const VkImageMemoryBarrier		preImageBarrier		=
4009 	{
4010 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4011 		DE_NULL,									// const void*				pNext;
4012 		0u,											// VkAccessFlags			srcAccessMask;
4013 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			dstAccessMask;
4014 		oldLayout,									// VkImageLayout			oldLayout;
4015 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			newLayout;
4016 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4017 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4018 		image,										// VkImage					image;
4019 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4020 	};
4021 
4022 	const VkImageMemoryBarrier		postImageBarrier	=
4023 	{
4024 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4025 		DE_NULL,									// const void*				pNext;
4026 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			srcAccessMask;
4027 		VK_ACCESS_SHADER_WRITE_BIT,					// VkAccessFlags			dstAccessMask;
4028 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			oldLayout;
4029 		newLayout,									// VkImageLayout			newLayout;
4030 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4031 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4032 		image,										// VkImage					image;
4033 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4034 	};
4035 
4036 	beginCommandBuffer(vk, *cmdBuffer);
4037 	vk.cmdPipelineBarrier(*cmdBuffer,
4038 						  VK_PIPELINE_STAGE_HOST_BIT,
4039 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4040 						  (VkDependencyFlags)0,
4041 						  0, (const VkMemoryBarrier*)DE_NULL,
4042 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4043 						  1, &preImageBarrier);
4044 	vk.cmdClearColorImage(*cmdBuffer, image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearColorValue, 1, &subresourceRange);
4045 	vk.cmdPipelineBarrier(*cmdBuffer,
4046 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4047 						  dstStageFlags,
4048 						  (VkDependencyFlags)0,
4049 						  0, (const VkMemoryBarrier*)DE_NULL,
4050 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4051 						  1, &postImageBarrier);
4052 	endCommandBuffer(vk, *cmdBuffer);
4053 
4054 	submitCommandsAndWait(vk, device, queue, *cmdBuffer);
4055 }
4056 
generateChessboardCopyRegions(deUint32 tileSize,deUint32 imageWidth,deUint32 imageHeight,deUint32 tileIdx,VkImageAspectFlags aspectMask)4057 std::vector<VkBufferImageCopy> generateChessboardCopyRegions (deUint32				tileSize,
4058 															  deUint32				imageWidth,
4059 															  deUint32				imageHeight,
4060 															  deUint32				tileIdx,
4061 															  VkImageAspectFlags	aspectMask)
4062 {
4063 	std::vector<VkBufferImageCopy>	copyRegions;
4064 
4065 	for (deUint32 x = 0; x < (deUint32)deFloatCeil((float)imageWidth / (float)tileSize); x++)
4066 		for (deUint32 y = 0; y < (deUint32)deFloatCeil((float)imageHeight / (float)tileSize); y++)
4067 		{
4068 			if ((x + tileIdx) % 2 == y % 2) continue;
4069 
4070 			const deUint32					tileWidth			= de::min(tileSize, imageWidth - tileSize * x);
4071 			const deUint32					tileHeight			= de::min(tileSize, imageHeight - tileSize * y);
4072 
4073 			const VkOffset3D				offset				=
4074 			{
4075 				(deInt32)x * (deInt32)tileWidth,	// deInt32	x
4076 				(deInt32)y * (deInt32)tileHeight,	// deInt32	y
4077 				0									// deInt32	z
4078 			};
4079 
4080 			const VkExtent3D				extent				=
4081 			{
4082 				tileWidth,	// deUint32	width
4083 				tileHeight,	// deUint32	height
4084 				1u			// deUint32	depth
4085 			};
4086 
4087 			const VkImageSubresourceLayers	subresourceLayers	=
4088 			{
4089 				aspectMask,	// VkImageAspectFlags	aspectMask
4090 				0u,			// deUint32				mipLevel
4091 				0u,			// deUint32				baseArrayLayer
4092 				1u,			// deUint32				layerCount
4093 			};
4094 
4095 			const VkBufferImageCopy			copy				=
4096 			{
4097 				(VkDeviceSize)0,	// VkDeviceSize				bufferOffset
4098 				0u,					// deUint32					bufferRowLength
4099 				0u,					// deUint32					bufferImageHeight
4100 				subresourceLayers,	// VkImageSubresourceLayers	imageSubresource
4101 				offset,				// VkOffset3D				imageOffset
4102 				extent				// VkExtent3D				imageExtent
4103 			};
4104 
4105 			copyRegions.push_back(copy);
4106 		}
4107 
4108 	return copyRegions;
4109 }
4110 
initColorImageChessboardPattern(const DeviceInterface & vk,const VkDevice device,const VkQueue queue,deUint32 queueFamilyIndex,Allocator & allocator,VkImage image,VkFormat format,tcu::Vec4 colorValue0,tcu::Vec4 colorValue1,deUint32 imageWidth,deUint32 imageHeight,deUint32 tileSize,VkImageLayout oldLayout,VkImageLayout newLayout,VkPipelineStageFlags dstStageFlags)4111 void initColorImageChessboardPattern (const DeviceInterface&	vk,
4112 									  const VkDevice			device,
4113 									  const VkQueue				queue,
4114 									  deUint32					queueFamilyIndex,
4115 									  Allocator&				allocator,
4116 									  VkImage					image,
4117 									  VkFormat					format,
4118 									  tcu::Vec4					colorValue0,
4119 									  tcu::Vec4					colorValue1,
4120 									  deUint32					imageWidth,
4121 									  deUint32					imageHeight,
4122 									  deUint32					tileSize,
4123 									  VkImageLayout				oldLayout,
4124 									  VkImageLayout				newLayout,
4125 									  VkPipelineStageFlags		dstStageFlags)
4126 {
4127 	Move<VkCommandPool>				cmdPool				= createCommandPool(vk, device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, queueFamilyIndex);
4128 	Move<VkCommandBuffer>			cmdBuffer			= allocateCommandBuffer(vk, device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
4129 	const tcu::TextureFormat		tcuFormat			= mapVkFormat(format);
4130 	const tcu::Vec4					colorValues[]		= { colorValue0, colorValue1 };
4131 	const deUint32					bufferSize			= tileSize * tileSize * tcuFormat.getPixelSize();
4132 
4133 	const VkImageSubresourceRange	subresourceRange	=
4134 	{
4135 		VK_IMAGE_ASPECT_COLOR_BIT,	// VkImageAspectFlags	aspectMask
4136 		0u,							// deUint32				baseMipLevel
4137 		1u,							// deUint32				levelCount
4138 		0u,							// deUint32				baseArrayLayer
4139 		1u							// deUint32				layerCount
4140 	};
4141 
4142 	const VkImageMemoryBarrier		preImageBarrier		=
4143 	{
4144 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4145 		DE_NULL,									// const void*				pNext;
4146 		0u,											// VkAccessFlags			srcAccessMask;
4147 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			dstAccessMask;
4148 		oldLayout,									// VkImageLayout			oldLayout;
4149 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			newLayout;
4150 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4151 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4152 		image,										// VkImage					image;
4153 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4154 	};
4155 
4156 	const VkImageMemoryBarrier		postImageBarrier	=
4157 	{
4158 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4159 		DE_NULL,									// const void*				pNext;
4160 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			srcAccessMask;
4161 		VK_ACCESS_SHADER_WRITE_BIT,					// VkAccessFlags			dstAccessMask;
4162 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			oldLayout;
4163 		newLayout,									// VkImageLayout			newLayout;
4164 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4165 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4166 		image,										// VkImage					image;
4167 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4168 	};
4169 
4170 	// Create staging buffers for both color values
4171 	Move<VkBuffer>					buffers[2];
4172 	de::MovePtr<Allocation>			bufferAllocs[2];
4173 
4174 	const VkBufferCreateInfo		bufferParams		=
4175 	{
4176 		VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,	// VkStructureType		sType
4177 		DE_NULL,								// const void*			pNext
4178 		0u,										// VkBufferCreateFlags	flags
4179 		(VkDeviceSize)bufferSize,				// VkDeviceSize			size
4180 		VK_BUFFER_USAGE_TRANSFER_SRC_BIT,		// VkBufferUsageFlags	usage
4181 		VK_SHARING_MODE_EXCLUSIVE,				// VkSharingMode		sharingMode
4182 		0u,										// deUint32				queueFamilyIndexCount
4183 		DE_NULL									// const deUint32*		pQueueFamilyIndices
4184 	};
4185 
4186 	for (deUint32 bufferIdx = 0; bufferIdx < 2; bufferIdx++)
4187 	{
4188 		buffers[bufferIdx]		= createBuffer(vk, device, &bufferParams);
4189 		bufferAllocs[bufferIdx]	= allocator.allocate(getBufferMemoryRequirements(vk, device, *buffers[bufferIdx]), MemoryRequirement::HostVisible);
4190 		VK_CHECK(vk.bindBufferMemory(device, *buffers[bufferIdx], bufferAllocs[bufferIdx]->getMemory(), bufferAllocs[bufferIdx]->getOffset()));
4191 
4192 		deUint32*				dstPtr	= (deUint32*)bufferAllocs[bufferIdx]->getHostPtr();
4193 		tcu::PixelBufferAccess	access	(tcuFormat, tileSize, tileSize, 1, dstPtr);
4194 
4195 		for (deUint32 x = 0; x < tileSize; x++)
4196 			for (deUint32 y = 0; y < tileSize; y++)
4197 				access.setPixel(colorValues[bufferIdx], x, y, 0);
4198 
4199 		flushAlloc(vk, device, *bufferAllocs[bufferIdx]);
4200 	}
4201 
4202 	beginCommandBuffer(vk, *cmdBuffer);
4203 	vk.cmdPipelineBarrier(*cmdBuffer,
4204 						  VK_PIPELINE_STAGE_HOST_BIT,
4205 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4206 						  (VkDependencyFlags)0,
4207 						  0, (const VkMemoryBarrier*)DE_NULL,
4208 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4209 						  1, &preImageBarrier);
4210 
4211 	for (deUint32 bufferIdx = 0; bufferIdx < 2; bufferIdx++)
4212 	{
4213 		std::vector<VkBufferImageCopy> copyRegions = generateChessboardCopyRegions(tileSize, imageWidth, imageHeight, bufferIdx, VK_IMAGE_ASPECT_COLOR_BIT);
4214 
4215 		vk.cmdCopyBufferToImage(*cmdBuffer, *buffers[bufferIdx], image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, (deUint32)copyRegions.size(), copyRegions.data());
4216 	}
4217 
4218 	vk.cmdPipelineBarrier(*cmdBuffer,
4219 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4220 						  dstStageFlags,
4221 						  (VkDependencyFlags)0,
4222 						  0, (const VkMemoryBarrier*)DE_NULL,
4223 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4224 						  1, &postImageBarrier);
4225 
4226 	endCommandBuffer(vk, *cmdBuffer);
4227 
4228 	submitCommandsAndWait(vk, device, queue, *cmdBuffer);
4229 }
4230 
copyDepthStencilImageToBuffers(const DeviceInterface & vk,VkCommandBuffer cmdBuffer,VkImage image,VkBuffer depthBuffer,VkBuffer stencilBuffer,tcu::IVec2 size,VkAccessFlags srcAccessMask,VkImageLayout oldLayout,deUint32 numLayers)4231 void copyDepthStencilImageToBuffers (const DeviceInterface&	vk,
4232 									 VkCommandBuffer		cmdBuffer,
4233 									 VkImage				image,
4234 									 VkBuffer				depthBuffer,
4235 									 VkBuffer				stencilBuffer,
4236 									 tcu::IVec2				size,
4237 									 VkAccessFlags			srcAccessMask,
4238 									 VkImageLayout			oldLayout,
4239 									 deUint32				numLayers)
4240 {
4241 	const VkImageAspectFlags		aspect				= VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT;
4242 	const VkImageMemoryBarrier		imageBarrier		=
4243 	{
4244 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,					// VkStructureType			sType;
4245 		DE_NULL,												// const void*				pNext;
4246 		srcAccessMask,											// VkAccessFlags			srcAccessMask;
4247 		VK_ACCESS_TRANSFER_READ_BIT,							// VkAccessFlags			dstAccessMask;
4248 		oldLayout,												// VkImageLayout			oldLayout;
4249 		VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,					// VkImageLayout			newLayout;
4250 		VK_QUEUE_FAMILY_IGNORED,								// deUint32					srcQueueFamilyIndex;
4251 		VK_QUEUE_FAMILY_IGNORED,								// deUint32					destQueueFamilyIndex;
4252 		image,													// VkImage					image;
4253 		makeImageSubresourceRange(aspect, 0u, 1u, 0, numLayers)	// VkImageSubresourceRange	subresourceRange;
4254 	};
4255 
4256 	vk.cmdPipelineBarrier(cmdBuffer, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0u,
4257 						  0u, DE_NULL, 0u, DE_NULL, 1u, &imageBarrier);
4258 
4259 	const VkImageSubresourceLayers	subresourceDepth	=
4260 	{
4261 		VK_IMAGE_ASPECT_DEPTH_BIT,					// VkImageAspectFlags	aspectMask;
4262 		0u,											// deUint32				mipLevel;
4263 		0u,											// deUint32				baseArrayLayer;
4264 		numLayers									// deUint32				layerCount;
4265 	};
4266 
4267 	const VkBufferImageCopy			regionDepth			=
4268 	{
4269 		0ull,										// VkDeviceSize					bufferOffset;
4270 		0u,											// deUint32						bufferRowLength;
4271 		0u,											// deUint32						bufferImageHeight;
4272 		subresourceDepth,							// VkImageSubresourceLayers		imageSubresource;
4273 		makeOffset3D(0, 0, 0),						// VkOffset3D					imageOffset;
4274 		makeExtent3D(size.x(), size.y(), 1u)		// VkExtent3D					imageExtent;
4275 	};
4276 
4277 	const VkImageSubresourceLayers	subresourceStencil	=
4278 	{
4279 		VK_IMAGE_ASPECT_STENCIL_BIT,				// VkImageAspectFlags	aspectMask;
4280 		0u,											// deUint32				mipLevel;
4281 		0u,											// deUint32				baseArrayLayer;
4282 		numLayers									// deUint32				layerCount;
4283 	};
4284 
4285 	const VkBufferImageCopy			regionStencil		=
4286 	{
4287 		0ull,										// VkDeviceSize					bufferOffset;
4288 		0u,											// deUint32						bufferRowLength;
4289 		0u,											// deUint32						bufferImageHeight;
4290 		subresourceStencil,							// VkImageSubresourceLayers		imageSubresource;
4291 		makeOffset3D(0, 0, 0),						// VkOffset3D					imageOffset;
4292 		makeExtent3D(size.x(), size.y(), 1u)		// VkExtent3D					imageExtent;
4293 	};
4294 
4295 	vk.cmdCopyImageToBuffer(cmdBuffer, image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, depthBuffer, 1u, &regionDepth);
4296 	vk.cmdCopyImageToBuffer(cmdBuffer, image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, stencilBuffer, 1u, &regionStencil);
4297 
4298 	const VkBufferMemoryBarrier	bufferBarriers[]		=
4299 	{
4300 		{
4301 			VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,	// VkStructureType	sType;
4302 			DE_NULL,									// const void*		pNext;
4303 			VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags	srcAccessMask;
4304 			VK_ACCESS_HOST_READ_BIT,					// VkAccessFlags	dstAccessMask;
4305 			VK_QUEUE_FAMILY_IGNORED,					// deUint32			srcQueueFamilyIndex;
4306 			VK_QUEUE_FAMILY_IGNORED,					// deUint32			dstQueueFamilyIndex;
4307 			depthBuffer,								// VkBuffer			buffer;
4308 			0ull,										// VkDeviceSize		offset;
4309 			VK_WHOLE_SIZE								// VkDeviceSize		size;
4310 		},
4311 		{
4312 			VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER,	// VkStructureType	sType;
4313 			DE_NULL,									// const void*		pNext;
4314 			VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags	srcAccessMask;
4315 			VK_ACCESS_HOST_READ_BIT,					// VkAccessFlags	dstAccessMask;
4316 			VK_QUEUE_FAMILY_IGNORED,					// deUint32			srcQueueFamilyIndex;
4317 			VK_QUEUE_FAMILY_IGNORED,					// deUint32			dstQueueFamilyIndex;
4318 			stencilBuffer,								// VkBuffer			buffer;
4319 			0ull,										// VkDeviceSize		offset;
4320 			VK_WHOLE_SIZE								// VkDeviceSize		size;
4321 		}
4322 	};
4323 
4324 	vk.cmdPipelineBarrier(cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_HOST_BIT, 0u,
4325 						  0u, DE_NULL, 2u, bufferBarriers, 0u, DE_NULL);
4326 }
4327 
clearDepthStencilImage(const DeviceInterface & vk,const VkDevice device,const VkQueue queue,deUint32 queueFamilyIndex,VkImage image,float depthValue,deUint32 stencilValue,VkImageLayout oldLayout,VkImageLayout newLayout,VkPipelineStageFlags dstStageFlags)4328 void clearDepthStencilImage (const DeviceInterface&	vk,
4329 							 const VkDevice			device,
4330 							 const VkQueue			queue,
4331 							 deUint32				queueFamilyIndex,
4332 							 VkImage				image,
4333 							 float					depthValue,
4334 							 deUint32				stencilValue,
4335 							 VkImageLayout			oldLayout,
4336 							 VkImageLayout			newLayout,
4337 							 VkPipelineStageFlags	dstStageFlags)
4338 {
4339 	Move<VkCommandPool>				cmdPool				= createCommandPool(vk, device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, queueFamilyIndex);
4340 	Move<VkCommandBuffer>			cmdBuffer			= allocateCommandBuffer(vk, device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
4341 
4342 	const VkClearDepthStencilValue	clearValue			= makeClearValueDepthStencil(depthValue, stencilValue).depthStencil;
4343 
4344 	const VkImageSubresourceRange	subresourceRange	=
4345 	{
4346 		VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT,	// VkImageAspectFlags	aspectMask
4347 		0u,															// deUint32				baseMipLevel
4348 		1u,															// deUint32				levelCount
4349 		0u,															// deUint32				baseArrayLayer
4350 		1u															// deUint32				layerCount
4351 	};
4352 
4353 	const VkImageMemoryBarrier		preImageBarrier		=
4354 	{
4355 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4356 		DE_NULL,									// const void*				pNext;
4357 		0u,											// VkAccessFlags			srcAccessMask;
4358 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			dstAccessMask;
4359 		oldLayout,									// VkImageLayout			oldLayout;
4360 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			newLayout;
4361 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4362 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4363 		image,										// VkImage					image;
4364 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4365 	};
4366 
4367 	const VkImageMemoryBarrier		postImageBarrier	=
4368 	{
4369 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4370 		DE_NULL,									// const void*				pNext;
4371 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			srcAccessMask;
4372 		VK_ACCESS_SHADER_WRITE_BIT,					// VkAccessFlags			dstAccessMask;
4373 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			oldLayout;
4374 		newLayout,									// VkImageLayout			newLayout;
4375 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4376 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4377 		image,										// VkImage					image;
4378 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4379 	};
4380 
4381 	beginCommandBuffer(vk, *cmdBuffer);
4382 	vk.cmdPipelineBarrier(*cmdBuffer,
4383 						  VK_PIPELINE_STAGE_HOST_BIT,
4384 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4385 						  (VkDependencyFlags)0,
4386 						  0, (const VkMemoryBarrier*)DE_NULL,
4387 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4388 						  1, &preImageBarrier);
4389 	vk.cmdClearDepthStencilImage(*cmdBuffer, image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearValue, 1, &subresourceRange);
4390 	vk.cmdPipelineBarrier(*cmdBuffer,
4391 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4392 						  dstStageFlags,
4393 						  (VkDependencyFlags)0,
4394 						  0, (const VkMemoryBarrier*)DE_NULL,
4395 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4396 						  1, &postImageBarrier);
4397 	endCommandBuffer(vk, *cmdBuffer);
4398 
4399 	submitCommandsAndWait(vk, device, queue, *cmdBuffer);
4400 }
4401 
initDepthStencilImageChessboardPattern(const DeviceInterface & vk,const VkDevice device,const VkQueue queue,deUint32 queueFamilyIndex,Allocator & allocator,VkImage image,VkFormat format,float depthValue0,float depthValue1,deUint32 stencilValue0,deUint32 stencilValue1,deUint32 imageWidth,deUint32 imageHeight,deUint32 tileSize,VkImageLayout oldLayout,VkImageLayout newLayout,VkPipelineStageFlags dstStageFlags)4402 void initDepthStencilImageChessboardPattern (const DeviceInterface&	vk,
4403 											 const VkDevice			device,
4404 											 const VkQueue			queue,
4405 											 deUint32				queueFamilyIndex,
4406 											 Allocator&				allocator,
4407 											 VkImage				image,
4408 											 VkFormat				format,
4409 											 float					depthValue0,
4410 											 float					depthValue1,
4411 											 deUint32				stencilValue0,
4412 											 deUint32				stencilValue1,
4413 											 deUint32				imageWidth,
4414 											 deUint32				imageHeight,
4415 											 deUint32				tileSize,
4416 											 VkImageLayout			oldLayout,
4417 											 VkImageLayout			newLayout,
4418 											 VkPipelineStageFlags	dstStageFlags)
4419 {
4420 	Move<VkCommandPool>				cmdPool				= createCommandPool(vk, device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, queueFamilyIndex);
4421 	Move<VkCommandBuffer>			cmdBuffer			= allocateCommandBuffer(vk, device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
4422 
4423 	const deUint32					depthBufferSize		= tileSize * tileSize * 4;
4424 	const deUint32					stencilBufferSize	= tileSize * tileSize;
4425 	const float						depthValues[]		= { depthValue0, depthValue1 };
4426 	const deUint32					stencilValues[]		= { stencilValue0, stencilValue1 };
4427 	const tcu::TextureFormat		tcuFormat			= mapVkFormat(format);
4428 
4429 	const VkImageSubresourceRange	subresourceRange	=
4430 	{
4431 		VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT,	// VkImageAspectFlags	aspectMask
4432 		0u,															// deUint32				baseMipLevel
4433 		1u,															// deUint32				levelCount
4434 		0u,															// deUint32				baseArrayLayer
4435 		1u															// deUint32				layerCount
4436 	};
4437 
4438 	const VkImageMemoryBarrier		preImageBarrier		=
4439 	{
4440 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4441 		DE_NULL,									// const void*				pNext;
4442 		0u,											// VkAccessFlags			srcAccessMask;
4443 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			dstAccessMask;
4444 		oldLayout,									// VkImageLayout			oldLayout;
4445 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			newLayout;
4446 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4447 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4448 		image,										// VkImage					image;
4449 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4450 	};
4451 
4452 	const VkImageMemoryBarrier		postImageBarrier	=
4453 	{
4454 		VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER,		// VkStructureType			sType;
4455 		DE_NULL,									// const void*				pNext;
4456 		VK_ACCESS_TRANSFER_WRITE_BIT,				// VkAccessFlags			srcAccessMask;
4457 		VK_ACCESS_SHADER_WRITE_BIT,					// VkAccessFlags			dstAccessMask;
4458 		VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,		// VkImageLayout			oldLayout;
4459 		newLayout,									// VkImageLayout			newLayout;
4460 		queueFamilyIndex,							// deUint32					srcQueueFamilyIndex;
4461 		queueFamilyIndex,							// deUint32					dstQueueFamilyIndex;
4462 		image,										// VkImage					image;
4463 		subresourceRange							// VkImageSubresourceRange	subresourceRange;
4464 	};
4465 
4466 	// Create staging buffers for depth and stencil values
4467 	Move<VkBuffer>					depthBuffers[2];
4468 	de::MovePtr<Allocation>			depthBufferAllocs[2];
4469 	Move<VkBuffer>					stencilBuffers[2];
4470 	de::MovePtr<Allocation>			stencilBufferAllocs[2];
4471 
4472 	const VkBufferCreateInfo		depthBufferParams	=
4473 	{
4474 		VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,	// VkStructureType		sType
4475 		DE_NULL,								// const void*			pNext
4476 		0u,										// VkBufferCreateFlags	flags
4477 		(VkDeviceSize)depthBufferSize,			// VkDeviceSize			size
4478 		VK_BUFFER_USAGE_TRANSFER_SRC_BIT,		// VkBufferUsageFlags	usage
4479 		VK_SHARING_MODE_EXCLUSIVE,				// VkSharingMode		sharingMode
4480 		0u,										// deUint32				queueFamilyIndexCount
4481 		DE_NULL									// const deUint32*		pQueueFamilyIndices
4482 	};
4483 
4484 	const VkBufferCreateInfo		stencilBufferParams	=
4485 	{
4486 		VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,	// VkStructureType		sType
4487 		DE_NULL,								// const void*			pNext
4488 		0u,										// VkBufferCreateFlags	flags
4489 		(VkDeviceSize)stencilBufferSize,		// VkDeviceSize			size
4490 		VK_BUFFER_USAGE_TRANSFER_SRC_BIT,		// VkBufferUsageFlags	usage
4491 		VK_SHARING_MODE_EXCLUSIVE,				// VkSharingMode		sharingMode
4492 		0u,										// deUint32				queueFamilyIndexCount
4493 		DE_NULL									// const deUint32*		pQueueFamilyIndices
4494 	};
4495 
4496 	for (deUint32 bufferIdx = 0; bufferIdx < 2; bufferIdx++)
4497 	{
4498 		depthBuffers[bufferIdx]			= createBuffer(vk, device, &depthBufferParams);
4499 		depthBufferAllocs[bufferIdx]	= allocator.allocate(getBufferMemoryRequirements(vk, device, *depthBuffers[bufferIdx]), MemoryRequirement::HostVisible);
4500 		VK_CHECK(vk.bindBufferMemory(device, *depthBuffers[bufferIdx], depthBufferAllocs[bufferIdx]->getMemory(), depthBufferAllocs[bufferIdx]->getOffset()));
4501 		stencilBuffers[bufferIdx]		= createBuffer(vk, device, &stencilBufferParams);
4502 		stencilBufferAllocs[bufferIdx]	= allocator.allocate(getBufferMemoryRequirements(vk, device, *stencilBuffers[bufferIdx]), MemoryRequirement::HostVisible);
4503 		VK_CHECK(vk.bindBufferMemory(device, *stencilBuffers[bufferIdx], stencilBufferAllocs[bufferIdx]->getMemory(), stencilBufferAllocs[bufferIdx]->getOffset()));
4504 
4505 		deUint32*	depthPtr	= (deUint32*)depthBufferAllocs[bufferIdx]->getHostPtr();
4506 		deUint32*	stencilPtr	= (deUint32*)stencilBufferAllocs[bufferIdx]->getHostPtr();
4507 
4508 		if (format == VK_FORMAT_D24_UNORM_S8_UINT)
4509 		{
4510 			tcu::PixelBufferAccess access(tcuFormat, tileSize, tileSize, 1, depthPtr);
4511 
4512 			for (deUint32 x = 0; x < tileSize; x++)
4513 				for (deUint32 y = 0; y < tileSize; y++)
4514 					access.setPixDepth(depthValues[bufferIdx], x, y, 0);
4515 		}
4516 		else
4517 		{
4518 			DE_ASSERT(format == VK_FORMAT_D32_SFLOAT_S8_UINT);
4519 
4520 			for (deUint32 i = 0; i < tileSize * tileSize; i++)
4521 				((float*)depthPtr)[i] = depthValues[bufferIdx];
4522 		}
4523 
4524 		deMemset(stencilPtr, stencilValues[bufferIdx], stencilBufferSize);
4525 		flushAlloc(vk, device, *depthBufferAllocs[bufferIdx]);
4526 		flushAlloc(vk, device, *stencilBufferAllocs[bufferIdx]);
4527 	}
4528 
4529 	beginCommandBuffer(vk, *cmdBuffer);
4530 	vk.cmdPipelineBarrier(*cmdBuffer,
4531 						  VK_PIPELINE_STAGE_HOST_BIT,
4532 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4533 						  (VkDependencyFlags)0,
4534 						  0, (const VkMemoryBarrier*)DE_NULL,
4535 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4536 						  1, &preImageBarrier);
4537 
4538 	for (deUint32 bufferIdx = 0; bufferIdx < 2; bufferIdx++)
4539 	{
4540 		std::vector<VkBufferImageCopy>	copyRegionsDepth	= generateChessboardCopyRegions(tileSize, imageWidth, imageHeight, bufferIdx, VK_IMAGE_ASPECT_DEPTH_BIT);
4541 		std::vector<VkBufferImageCopy>	copyRegionsStencil	= generateChessboardCopyRegions(tileSize, imageWidth, imageHeight, bufferIdx, VK_IMAGE_ASPECT_STENCIL_BIT);
4542 
4543 		vk.cmdCopyBufferToImage(*cmdBuffer, *depthBuffers[bufferIdx], image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, (deUint32)copyRegionsDepth.size(), copyRegionsDepth.data());
4544 		vk.cmdCopyBufferToImage(*cmdBuffer, *stencilBuffers[bufferIdx], image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, (deUint32)copyRegionsStencil.size(), copyRegionsStencil.data());
4545 	}
4546 
4547 	vk.cmdPipelineBarrier(*cmdBuffer,
4548 						  VK_PIPELINE_STAGE_TRANSFER_BIT,
4549 						  dstStageFlags,
4550 						  (VkDependencyFlags)0,
4551 						  0, (const VkMemoryBarrier*)DE_NULL,
4552 						  0, (const VkBufferMemoryBarrier*)DE_NULL,
4553 						  1, &postImageBarrier);
4554 
4555 	endCommandBuffer(vk, *cmdBuffer);
4556 
4557 	submitCommandsAndWait(vk, device, queue, *cmdBuffer);
4558 }
4559 
allocateAndBindSparseImage(const DeviceInterface & vk,VkDevice device,const VkPhysicalDevice physicalDevice,const InstanceInterface & instance,const VkImageCreateInfo & imageCreateInfo,const VkSemaphore & signalSemaphore,VkQueue queue,Allocator & allocator,std::vector<de::SharedPtr<Allocation>> & allocations,tcu::TextureFormat format,VkImage destImage)4560 void allocateAndBindSparseImage (const DeviceInterface&						vk,
4561 								 VkDevice									device,
4562 								 const VkPhysicalDevice						physicalDevice,
4563 								 const InstanceInterface&					instance,
4564 								 const VkImageCreateInfo&					imageCreateInfo,
4565 								 const VkSemaphore&							signalSemaphore,
4566 								 VkQueue									queue,
4567 								 Allocator&									allocator,
4568 								 std::vector<de::SharedPtr<Allocation> >&	allocations,
4569 								 tcu::TextureFormat							format,
4570 								 VkImage									destImage)
4571 {
4572 	const VkImageAspectFlags				imageAspectFlags		= getImageAspectFlags(format);
4573 	const VkPhysicalDeviceProperties		deviceProperties		= getPhysicalDeviceProperties(instance, physicalDevice);
4574 	const VkPhysicalDeviceMemoryProperties	deviceMemoryProperties	= getPhysicalDeviceMemoryProperties(instance, physicalDevice);
4575 	deUint32								sparseMemoryReqCount	= 0;
4576 
4577 	// Check if the image format supports sparse operations
4578 	if (!checkSparseImageFormatSupport(physicalDevice, instance, imageCreateInfo))
4579 		TCU_THROW(NotSupportedError, "The image format does not support sparse operations.");
4580 
4581 	vk.getImageSparseMemoryRequirements(device, destImage, &sparseMemoryReqCount, DE_NULL);
4582 
4583 	DE_ASSERT(sparseMemoryReqCount != 0);
4584 
4585 	std::vector<VkSparseImageMemoryRequirements> sparseImageMemoryRequirements;
4586 	sparseImageMemoryRequirements.resize(sparseMemoryReqCount);
4587 
4588 	vk.getImageSparseMemoryRequirements(device, destImage, &sparseMemoryReqCount, &sparseImageMemoryRequirements[0]);
4589 
4590 	const deUint32 noMatchFound = ~((deUint32)0);
4591 
4592 	deUint32 aspectIndex = noMatchFound;
4593 	for (deUint32 memoryReqNdx = 0; memoryReqNdx < sparseMemoryReqCount; ++memoryReqNdx)
4594 	{
4595 		if (sparseImageMemoryRequirements[memoryReqNdx].formatProperties.aspectMask == imageAspectFlags)
4596 		{
4597 			aspectIndex = memoryReqNdx;
4598 			break;
4599 		}
4600 	}
4601 
4602 	deUint32 metadataAspectIndex = noMatchFound;
4603 	for (deUint32 memoryReqNdx = 0; memoryReqNdx < sparseMemoryReqCount; ++memoryReqNdx)
4604 	{
4605 		if (sparseImageMemoryRequirements[memoryReqNdx].formatProperties.aspectMask & VK_IMAGE_ASPECT_METADATA_BIT)
4606 		{
4607 			metadataAspectIndex = memoryReqNdx;
4608 			break;
4609 		}
4610 	}
4611 
4612 	if (aspectIndex == noMatchFound)
4613 		TCU_THROW(NotSupportedError, "Required image aspect not supported.");
4614 
4615 	const VkMemoryRequirements	memoryRequirements	= getImageMemoryRequirements(vk, device, destImage);
4616 
4617 	deUint32 memoryType = noMatchFound;
4618 	for (deUint32 memoryTypeNdx = 0; memoryTypeNdx < deviceMemoryProperties.memoryTypeCount; ++memoryTypeNdx)
4619 	{
4620 		if ((memoryRequirements.memoryTypeBits & (1u << memoryTypeNdx)) != 0 &&
4621 			MemoryRequirement::Any.matchesHeap(deviceMemoryProperties.memoryTypes[memoryTypeNdx].propertyFlags))
4622 		{
4623 			memoryType = memoryTypeNdx;
4624 			break;
4625 		}
4626 	}
4627 
4628 	if (memoryType == noMatchFound)
4629 		TCU_THROW(NotSupportedError, "No matching memory type found.");
4630 
4631 	if (memoryRequirements.size > deviceProperties.limits.sparseAddressSpaceSize)
4632 		TCU_THROW(NotSupportedError, "Required memory size for sparse resource exceeds device limits.");
4633 
4634 	const VkSparseImageMemoryRequirements		aspectRequirements	= sparseImageMemoryRequirements[aspectIndex];
4635 	const VkExtent3D							imageGranularity	= aspectRequirements.formatProperties.imageGranularity;
4636 
4637 	std::vector<VkSparseImageMemoryBind>		imageResidencyMemoryBinds;
4638 	std::vector<VkSparseMemoryBind>				imageMipTailMemoryBinds;
4639 
4640 	for (deUint32 layerNdx = 0; layerNdx < imageCreateInfo.arrayLayers; ++layerNdx)
4641 	{
4642 		for (deUint32 mipLevelNdx = 0; mipLevelNdx < aspectRequirements.imageMipTailFirstLod; ++mipLevelNdx)
4643 		{
4644 			const VkExtent3D	mipExtent		= mipLevelExtents(imageCreateInfo.extent, mipLevelNdx);
4645 			const tcu::UVec3	numSparseBinds	= alignedDivide(mipExtent, imageGranularity);
4646 			const tcu::UVec3	lastBlockExtent	= tcu::UVec3(mipExtent.width  % imageGranularity.width  ? mipExtent.width  % imageGranularity.width  : imageGranularity.width,
4647 															 mipExtent.height % imageGranularity.height ? mipExtent.height % imageGranularity.height : imageGranularity.height,
4648 															 mipExtent.depth  % imageGranularity.depth  ? mipExtent.depth  % imageGranularity.depth  : imageGranularity.depth );
4649 
4650 			for (deUint32 z = 0; z < numSparseBinds.z(); ++z)
4651 			for (deUint32 y = 0; y < numSparseBinds.y(); ++y)
4652 			for (deUint32 x = 0; x < numSparseBinds.x(); ++x)
4653 			{
4654 				const VkMemoryRequirements allocRequirements =
4655 				{
4656 					// 28.7.5 alignment shows the block size in bytes
4657 					memoryRequirements.alignment,		// VkDeviceSize	size;
4658 					memoryRequirements.alignment,		// VkDeviceSize	alignment;
4659 					memoryRequirements.memoryTypeBits,	// uint32_t		memoryTypeBits;
4660 				};
4661 
4662 				de::SharedPtr<Allocation> allocation(allocator.allocate(allocRequirements, MemoryRequirement::Any).release());
4663 				allocations.push_back(allocation);
4664 
4665 				VkOffset3D offset;
4666 				offset.x = x*imageGranularity.width;
4667 				offset.y = y*imageGranularity.height;
4668 				offset.z = z*imageGranularity.depth;
4669 
4670 				VkExtent3D extent;
4671 				extent.width	= (x == numSparseBinds.x() - 1) ? lastBlockExtent.x() : imageGranularity.width;
4672 				extent.height	= (y == numSparseBinds.y() - 1) ? lastBlockExtent.y() : imageGranularity.height;
4673 				extent.depth	= (z == numSparseBinds.z() - 1) ? lastBlockExtent.z() : imageGranularity.depth;
4674 
4675 				const VkSparseImageMemoryBind imageMemoryBind =
4676 				{
4677 					{
4678 						imageAspectFlags,	// VkImageAspectFlags	aspectMask;
4679 						mipLevelNdx,		// uint32_t				mipLevel;
4680 						layerNdx,			// uint32_t				arrayLayer;
4681 					},							// VkImageSubresource		subresource;
4682 					offset,						// VkOffset3D				offset;
4683 					extent,						// VkExtent3D				extent;
4684 					allocation->getMemory(),	// VkDeviceMemory			memory;
4685 					allocation->getOffset(),	// VkDeviceSize				memoryOffset;
4686 					0u,							// VkSparseMemoryBindFlags	flags;
4687 				};
4688 
4689 				imageResidencyMemoryBinds.push_back(imageMemoryBind);
4690 			}
4691 		}
4692 
4693 		// Handle MIP tail. There are two cases to consider here:
4694 		//
4695 		// 1) VK_SPARSE_IMAGE_FORMAT_SINGLE_MIPTAIL_BIT is requested by the driver: each layer needs a separate tail.
4696 		// 2) otherwise:                                                            only one tail is needed.
4697 		if (aspectRequirements.imageMipTailSize > 0)
4698 		{
4699 			if (layerNdx == 0 || (aspectRequirements.formatProperties.flags & VK_SPARSE_IMAGE_FORMAT_SINGLE_MIPTAIL_BIT) == 0)
4700 			{
4701 				const VkMemoryRequirements allocRequirements =
4702 				{
4703 					aspectRequirements.imageMipTailSize,	// VkDeviceSize	size;
4704 					memoryRequirements.alignment,			// VkDeviceSize	alignment;
4705 					memoryRequirements.memoryTypeBits,		// uint32_t		memoryTypeBits;
4706 				};
4707 
4708 				const de::SharedPtr<Allocation> allocation(allocator.allocate(allocRequirements, MemoryRequirement::Any).release());
4709 
4710 				const VkSparseMemoryBind imageMipTailMemoryBind =
4711 				{
4712 					aspectRequirements.imageMipTailOffset + layerNdx * aspectRequirements.imageMipTailStride,	// VkDeviceSize					resourceOffset;
4713 					aspectRequirements.imageMipTailSize,														// VkDeviceSize					size;
4714 					allocation->getMemory(),																	// VkDeviceMemory				memory;
4715 					allocation->getOffset(),																	// VkDeviceSize					memoryOffset;
4716 					0u,																							// VkSparseMemoryBindFlags		flags;
4717 				};
4718 
4719 				allocations.push_back(allocation);
4720 
4721 				imageMipTailMemoryBinds.push_back(imageMipTailMemoryBind);
4722 			}
4723 		}
4724 
4725 		// Handle Metadata. Similarly to MIP tail in aspectRequirements, there are two cases to consider here:
4726 		//
4727 		// 1) VK_SPARSE_IMAGE_FORMAT_SINGLE_MIPTAIL_BIT is requested by the driver: each layer needs a separate tail.
4728 		// 2) otherwise:
4729 		if (metadataAspectIndex != noMatchFound)
4730 		{
4731 			const VkSparseImageMemoryRequirements	metadataAspectRequirements = sparseImageMemoryRequirements[metadataAspectIndex];
4732 
4733 			if (layerNdx == 0 || (metadataAspectRequirements.formatProperties.flags & VK_SPARSE_IMAGE_FORMAT_SINGLE_MIPTAIL_BIT) == 0)
4734 			{
4735 				const VkMemoryRequirements metadataAllocRequirements =
4736 				{
4737 					metadataAspectRequirements.imageMipTailSize,	// VkDeviceSize	size;
4738 					memoryRequirements.alignment,					// VkDeviceSize	alignment;
4739 					memoryRequirements.memoryTypeBits,				// uint32_t		memoryTypeBits;
4740 				};
4741 				const de::SharedPtr<Allocation>	metadataAllocation(allocator.allocate(metadataAllocRequirements, MemoryRequirement::Any).release());
4742 
4743 				const VkSparseMemoryBind metadataMipTailMemoryBind =
4744 				{
4745 					metadataAspectRequirements.imageMipTailOffset +
4746 					layerNdx * metadataAspectRequirements.imageMipTailStride,			// VkDeviceSize					resourceOffset;
4747 					metadataAspectRequirements.imageMipTailSize,						// VkDeviceSize					size;
4748 					metadataAllocation->getMemory(),									// VkDeviceMemory				memory;
4749 					metadataAllocation->getOffset(),									// VkDeviceSize					memoryOffset;
4750 					VK_SPARSE_MEMORY_BIND_METADATA_BIT									// VkSparseMemoryBindFlags		flags;
4751 				};
4752 
4753 				allocations.push_back(metadataAllocation);
4754 
4755 				imageMipTailMemoryBinds.push_back(metadataMipTailMemoryBind);
4756 			}
4757 		}
4758 	}
4759 
4760 	VkBindSparseInfo bindSparseInfo =
4761 	{
4762 		VK_STRUCTURE_TYPE_BIND_SPARSE_INFO,			//VkStructureType							sType;
4763 		DE_NULL,									//const void*								pNext;
4764 		0u,											//deUint32									waitSemaphoreCount;
4765 		DE_NULL,									//const VkSemaphore*						pWaitSemaphores;
4766 		0u,											//deUint32									bufferBindCount;
4767 		DE_NULL,									//const VkSparseBufferMemoryBindInfo*		pBufferBinds;
4768 		0u,											//deUint32									imageOpaqueBindCount;
4769 		DE_NULL,									//const VkSparseImageOpaqueMemoryBindInfo*	pImageOpaqueBinds;
4770 		0u,											//deUint32									imageBindCount;
4771 		DE_NULL,									//const VkSparseImageMemoryBindInfo*		pImageBinds;
4772 		1u,											//deUint32									signalSemaphoreCount;
4773 		&signalSemaphore							//const VkSemaphore*						pSignalSemaphores;
4774 	};
4775 
4776 	VkSparseImageMemoryBindInfo			imageResidencyBindInfo;
4777 	VkSparseImageOpaqueMemoryBindInfo	imageMipTailBindInfo;
4778 
4779 	if (imageResidencyMemoryBinds.size() > 0)
4780 	{
4781 		imageResidencyBindInfo.image		= destImage;
4782 		imageResidencyBindInfo.bindCount	= static_cast<deUint32>(imageResidencyMemoryBinds.size());
4783 		imageResidencyBindInfo.pBinds		= &imageResidencyMemoryBinds[0];
4784 
4785 		bindSparseInfo.imageBindCount		= 1u;
4786 		bindSparseInfo.pImageBinds			= &imageResidencyBindInfo;
4787 	}
4788 
4789 	if (imageMipTailMemoryBinds.size() > 0)
4790 	{
4791 		imageMipTailBindInfo.image			= destImage;
4792 		imageMipTailBindInfo.bindCount		= static_cast<deUint32>(imageMipTailMemoryBinds.size());
4793 		imageMipTailBindInfo.pBinds			= &imageMipTailMemoryBinds[0];
4794 
4795 		bindSparseInfo.imageOpaqueBindCount	= 1u;
4796 		bindSparseInfo.pImageOpaqueBinds	= &imageMipTailBindInfo;
4797 	}
4798 
4799 	VK_CHECK(vk.queueBindSparse(queue, 1u, &bindSparseInfo, DE_NULL));
4800 }
4801 
checkSparseImageFormatSupport(const VkPhysicalDevice physicalDevice,const InstanceInterface & instance,const VkImageCreateInfo & imageCreateInfo)4802 bool checkSparseImageFormatSupport (const VkPhysicalDevice		physicalDevice,
4803 									const InstanceInterface&	instance,
4804 									const VkImageCreateInfo&	imageCreateInfo)
4805 {
4806 	const std::vector<VkSparseImageFormatProperties> sparseImageFormatPropVec =
4807 		getPhysicalDeviceSparseImageFormatProperties(instance, physicalDevice, imageCreateInfo.format, imageCreateInfo.imageType, imageCreateInfo.samples, imageCreateInfo.usage, imageCreateInfo.tiling);
4808 
4809 	return (sparseImageFormatPropVec.size() != 0);
4810 }
4811 
4812 } // vk
4813