radv_formats.c revision 01e04c3f
1/*
2 * Copyright © 2016 Red Hat.
3 * Copyright © 2016 Bas Nieuwenhuizen
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the "Software"),
7 * to deal in the Software without restriction, including without limitation
8 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9 * and/or sell copies of the Software, and to permit persons to whom the
10 * Software is furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice (including the next
13 * paragraph) shall be included in all copies or substantial portions of the
14 * Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
22 * IN THE SOFTWARE.
23 */
24
25#include "radv_private.h"
26
27#include "vk_format.h"
28#include "sid.h"
29
30#include "vk_util.h"
31
32#include "util/u_half.h"
33#include "util/format_srgb.h"
34#include "util/format_r11g11b10f.h"
35
36uint32_t radv_translate_buffer_dataformat(const struct vk_format_description *desc,
37					  int first_non_void)
38{
39	unsigned type;
40	int i;
41
42	if (desc->format == VK_FORMAT_B10G11R11_UFLOAT_PACK32)
43		return V_008F0C_BUF_DATA_FORMAT_10_11_11;
44
45	if (first_non_void < 0)
46		return V_008F0C_BUF_DATA_FORMAT_INVALID;
47	type = desc->channel[first_non_void].type;
48
49	if (type == VK_FORMAT_TYPE_FIXED)
50		return V_008F0C_BUF_DATA_FORMAT_INVALID;
51	if (desc->nr_channels == 4 &&
52	    desc->channel[0].size == 10 &&
53	    desc->channel[1].size == 10 &&
54	    desc->channel[2].size == 10 &&
55	    desc->channel[3].size == 2)
56		return V_008F0C_BUF_DATA_FORMAT_2_10_10_10;
57
58	/* See whether the components are of the same size. */
59	for (i = 0; i < desc->nr_channels; i++) {
60		if (desc->channel[first_non_void].size != desc->channel[i].size)
61			return V_008F0C_BUF_DATA_FORMAT_INVALID;
62	}
63
64	switch (desc->channel[first_non_void].size) {
65	case 8:
66		switch (desc->nr_channels) {
67		case 1:
68			return V_008F0C_BUF_DATA_FORMAT_8;
69		case 2:
70			return V_008F0C_BUF_DATA_FORMAT_8_8;
71		case 4:
72			return V_008F0C_BUF_DATA_FORMAT_8_8_8_8;
73		}
74		break;
75	case 16:
76		switch (desc->nr_channels) {
77		case 1:
78			return V_008F0C_BUF_DATA_FORMAT_16;
79		case 2:
80			return V_008F0C_BUF_DATA_FORMAT_16_16;
81		case 4:
82			return V_008F0C_BUF_DATA_FORMAT_16_16_16_16;
83		}
84		break;
85	case 32:
86		/* From the Southern Islands ISA documentation about MTBUF:
87		 * 'Memory reads of data in memory that is 32 or 64 bits do not
88		 * undergo any format conversion.'
89		 */
90		if (type != VK_FORMAT_TYPE_FLOAT &&
91		    !desc->channel[first_non_void].pure_integer)
92			return V_008F0C_BUF_DATA_FORMAT_INVALID;
93
94		switch (desc->nr_channels) {
95		case 1:
96			return V_008F0C_BUF_DATA_FORMAT_32;
97		case 2:
98			return V_008F0C_BUF_DATA_FORMAT_32_32;
99		case 3:
100			return V_008F0C_BUF_DATA_FORMAT_32_32_32;
101		case 4:
102			return V_008F0C_BUF_DATA_FORMAT_32_32_32_32;
103		}
104		break;
105	}
106
107	return V_008F0C_BUF_DATA_FORMAT_INVALID;
108}
109
110uint32_t radv_translate_buffer_numformat(const struct vk_format_description *desc,
111					 int first_non_void)
112{
113	if (desc->format == VK_FORMAT_B10G11R11_UFLOAT_PACK32)
114		return V_008F0C_BUF_NUM_FORMAT_FLOAT;
115
116	if (first_non_void < 0)
117		return ~0;
118
119	switch (desc->channel[first_non_void].type) {
120	case VK_FORMAT_TYPE_SIGNED:
121		if (desc->channel[first_non_void].normalized)
122			return V_008F0C_BUF_NUM_FORMAT_SNORM;
123		else if (desc->channel[first_non_void].pure_integer)
124			return V_008F0C_BUF_NUM_FORMAT_SINT;
125		else
126			return V_008F0C_BUF_NUM_FORMAT_SSCALED;
127		break;
128	case VK_FORMAT_TYPE_UNSIGNED:
129		if (desc->channel[first_non_void].normalized)
130			return V_008F0C_BUF_NUM_FORMAT_UNORM;
131		else if (desc->channel[first_non_void].pure_integer)
132			return V_008F0C_BUF_NUM_FORMAT_UINT;
133		else
134			return V_008F0C_BUF_NUM_FORMAT_USCALED;
135		break;
136	case VK_FORMAT_TYPE_FLOAT:
137	default:
138		return V_008F0C_BUF_NUM_FORMAT_FLOAT;
139	}
140}
141
142uint32_t radv_translate_tex_dataformat(VkFormat format,
143				       const struct vk_format_description *desc,
144				       int first_non_void)
145{
146	bool uniform = true;
147	int i;
148
149	if (!desc)
150		return ~0;
151	/* Colorspace (return non-RGB formats directly). */
152	switch (desc->colorspace) {
153		/* Depth stencil formats */
154	case VK_FORMAT_COLORSPACE_ZS:
155		switch (format) {
156		case VK_FORMAT_D16_UNORM:
157			return V_008F14_IMG_DATA_FORMAT_16;
158		case VK_FORMAT_D24_UNORM_S8_UINT:
159		case VK_FORMAT_X8_D24_UNORM_PACK32:
160			return V_008F14_IMG_DATA_FORMAT_8_24;
161		case VK_FORMAT_S8_UINT:
162			return V_008F14_IMG_DATA_FORMAT_8;
163		case VK_FORMAT_D32_SFLOAT:
164			return V_008F14_IMG_DATA_FORMAT_32;
165		case VK_FORMAT_D32_SFLOAT_S8_UINT:
166			return V_008F14_IMG_DATA_FORMAT_X24_8_32;
167		default:
168			goto out_unknown;
169		}
170
171	case VK_FORMAT_COLORSPACE_YUV:
172		goto out_unknown; /* TODO */
173
174	case VK_FORMAT_COLORSPACE_SRGB:
175		if (desc->nr_channels != 4 && desc->nr_channels != 1)
176			goto out_unknown;
177		break;
178
179	default:
180		break;
181	}
182
183	if (desc->layout == VK_FORMAT_LAYOUT_RGTC) {
184		switch(format) {
185		case VK_FORMAT_BC4_UNORM_BLOCK:
186		case VK_FORMAT_BC4_SNORM_BLOCK:
187			return V_008F14_IMG_DATA_FORMAT_BC4;
188		case VK_FORMAT_BC5_UNORM_BLOCK:
189		case VK_FORMAT_BC5_SNORM_BLOCK:
190			return V_008F14_IMG_DATA_FORMAT_BC5;
191		default:
192			break;
193		}
194	}
195
196	if (desc->layout == VK_FORMAT_LAYOUT_S3TC) {
197		switch(format) {
198		case VK_FORMAT_BC1_RGB_UNORM_BLOCK:
199		case VK_FORMAT_BC1_RGB_SRGB_BLOCK:
200		case VK_FORMAT_BC1_RGBA_UNORM_BLOCK:
201		case VK_FORMAT_BC1_RGBA_SRGB_BLOCK:
202			return V_008F14_IMG_DATA_FORMAT_BC1;
203		case VK_FORMAT_BC2_UNORM_BLOCK:
204		case VK_FORMAT_BC2_SRGB_BLOCK:
205			return V_008F14_IMG_DATA_FORMAT_BC2;
206		case VK_FORMAT_BC3_UNORM_BLOCK:
207		case VK_FORMAT_BC3_SRGB_BLOCK:
208			return V_008F14_IMG_DATA_FORMAT_BC3;
209		default:
210			break;
211		}
212	}
213
214	if (desc->layout == VK_FORMAT_LAYOUT_BPTC) {
215		switch(format) {
216		case VK_FORMAT_BC6H_UFLOAT_BLOCK:
217		case VK_FORMAT_BC6H_SFLOAT_BLOCK:
218			return V_008F14_IMG_DATA_FORMAT_BC6;
219		case VK_FORMAT_BC7_UNORM_BLOCK:
220		case VK_FORMAT_BC7_SRGB_BLOCK:
221			return V_008F14_IMG_DATA_FORMAT_BC7;
222		default:
223			break;
224		}
225	}
226
227	if (desc->layout == VK_FORMAT_LAYOUT_ETC) {
228		switch (format) {
229		case VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK:
230		case VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK:
231			return V_008F14_IMG_DATA_FORMAT_ETC2_RGB;
232		case VK_FORMAT_ETC2_R8G8B8A1_UNORM_BLOCK:
233		case VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK:
234			return V_008F14_IMG_DATA_FORMAT_ETC2_RGBA1;
235		case VK_FORMAT_ETC2_R8G8B8A8_UNORM_BLOCK:
236		case VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK:
237			return V_008F14_IMG_DATA_FORMAT_ETC2_RGBA;
238		case VK_FORMAT_EAC_R11_UNORM_BLOCK:
239		case VK_FORMAT_EAC_R11_SNORM_BLOCK:
240			return V_008F14_IMG_DATA_FORMAT_ETC2_R;
241		case VK_FORMAT_EAC_R11G11_UNORM_BLOCK:
242		case VK_FORMAT_EAC_R11G11_SNORM_BLOCK:
243			return V_008F14_IMG_DATA_FORMAT_ETC2_RG;
244		default:
245			break;
246		}
247	}
248
249	if (format == VK_FORMAT_E5B9G9R9_UFLOAT_PACK32) {
250		return V_008F14_IMG_DATA_FORMAT_5_9_9_9;
251	} else if (format == VK_FORMAT_B10G11R11_UFLOAT_PACK32) {
252		return V_008F14_IMG_DATA_FORMAT_10_11_11;
253	}
254
255	/* R8G8Bx_SNORM - TODO CxV8U8 */
256
257	/* hw cannot support mixed formats (except depth/stencil, since only
258	 * depth is read).*/
259	if (desc->is_mixed && desc->colorspace != VK_FORMAT_COLORSPACE_ZS)
260		goto out_unknown;
261
262	/* See whether the components are of the same size. */
263	for (i = 1; i < desc->nr_channels; i++) {
264		uniform = uniform && desc->channel[0].size == desc->channel[i].size;
265	}
266
267	/* Non-uniform formats. */
268	if (!uniform) {
269		switch(desc->nr_channels) {
270		case 3:
271			if (desc->channel[0].size == 5 &&
272			    desc->channel[1].size == 6 &&
273			    desc->channel[2].size == 5) {
274				return V_008F14_IMG_DATA_FORMAT_5_6_5;
275			}
276			goto out_unknown;
277		case 4:
278			if (desc->channel[0].size == 5 &&
279			    desc->channel[1].size == 5 &&
280			    desc->channel[2].size == 5 &&
281			    desc->channel[3].size == 1) {
282				return V_008F14_IMG_DATA_FORMAT_1_5_5_5;
283			}
284			if (desc->channel[0].size == 1 &&
285			    desc->channel[1].size == 5 &&
286			    desc->channel[2].size == 5 &&
287			    desc->channel[3].size == 5) {
288				return V_008F14_IMG_DATA_FORMAT_5_5_5_1;
289			}
290			if (desc->channel[0].size == 10 &&
291			    desc->channel[1].size == 10 &&
292			    desc->channel[2].size == 10 &&
293			    desc->channel[3].size == 2) {
294				/* Closed VK driver does this also no 2/10/10/10 snorm */
295				if (desc->channel[0].type == VK_FORMAT_TYPE_SIGNED &&
296				    desc->channel[0].normalized)
297					goto out_unknown;
298				return V_008F14_IMG_DATA_FORMAT_2_10_10_10;
299			}
300			goto out_unknown;
301		}
302		goto out_unknown;
303	}
304
305	if (first_non_void < 0 || first_non_void > 3)
306		goto out_unknown;
307
308	/* uniform formats */
309	switch (desc->channel[first_non_void].size) {
310	case 4:
311		switch (desc->nr_channels) {
312#if 0 /* Not supported for render targets */
313		case 2:
314			return V_008F14_IMG_DATA_FORMAT_4_4;
315#endif
316		case 4:
317			return V_008F14_IMG_DATA_FORMAT_4_4_4_4;
318		}
319		break;
320	case 8:
321		switch (desc->nr_channels) {
322		case 1:
323			return V_008F14_IMG_DATA_FORMAT_8;
324		case 2:
325			return V_008F14_IMG_DATA_FORMAT_8_8;
326		case 4:
327			return V_008F14_IMG_DATA_FORMAT_8_8_8_8;
328		}
329		break;
330	case 16:
331		switch (desc->nr_channels) {
332		case 1:
333			return V_008F14_IMG_DATA_FORMAT_16;
334		case 2:
335			return V_008F14_IMG_DATA_FORMAT_16_16;
336		case 4:
337			return V_008F14_IMG_DATA_FORMAT_16_16_16_16;
338		}
339		break;
340	case 32:
341		switch (desc->nr_channels) {
342		case 1:
343			return V_008F14_IMG_DATA_FORMAT_32;
344		case 2:
345			return V_008F14_IMG_DATA_FORMAT_32_32;
346		case 3:
347			return V_008F14_IMG_DATA_FORMAT_32_32_32;
348		case 4:
349			return V_008F14_IMG_DATA_FORMAT_32_32_32_32;
350		}
351	}
352
353out_unknown:
354	/* R600_ERR("Unable to handle texformat %d %s\n", format, vk_format_name(format)); */
355	return ~0;
356}
357
358uint32_t radv_translate_tex_numformat(VkFormat format,
359				      const struct vk_format_description *desc,
360				      int first_non_void)
361{
362	switch (format) {
363	case VK_FORMAT_D24_UNORM_S8_UINT:
364		return V_008F14_IMG_NUM_FORMAT_UNORM;
365	default:
366		if (first_non_void < 0) {
367			if (vk_format_is_compressed(format)) {
368				switch (format) {
369				case VK_FORMAT_BC1_RGB_SRGB_BLOCK:
370				case VK_FORMAT_BC1_RGBA_SRGB_BLOCK:
371				case VK_FORMAT_BC2_SRGB_BLOCK:
372				case VK_FORMAT_BC3_SRGB_BLOCK:
373				case VK_FORMAT_BC7_SRGB_BLOCK:
374				case VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK:
375				case VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK:
376				case VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK:
377					return V_008F14_IMG_NUM_FORMAT_SRGB;
378				case VK_FORMAT_BC4_SNORM_BLOCK:
379				case VK_FORMAT_BC5_SNORM_BLOCK:
380			        case VK_FORMAT_BC6H_SFLOAT_BLOCK:
381				case VK_FORMAT_EAC_R11_SNORM_BLOCK:
382				case VK_FORMAT_EAC_R11G11_SNORM_BLOCK:
383					return V_008F14_IMG_NUM_FORMAT_SNORM;
384				default:
385					return V_008F14_IMG_NUM_FORMAT_UNORM;
386				}
387			} else if (desc->layout == VK_FORMAT_LAYOUT_SUBSAMPLED) {
388				return V_008F14_IMG_NUM_FORMAT_UNORM;
389			} else {
390				return V_008F14_IMG_NUM_FORMAT_FLOAT;
391			}
392		} else if (desc->colorspace == VK_FORMAT_COLORSPACE_SRGB) {
393			return V_008F14_IMG_NUM_FORMAT_SRGB;
394		} else {
395			switch (desc->channel[first_non_void].type) {
396			case VK_FORMAT_TYPE_FLOAT:
397				return V_008F14_IMG_NUM_FORMAT_FLOAT;
398			case VK_FORMAT_TYPE_SIGNED:
399				if (desc->channel[first_non_void].normalized)
400					return V_008F14_IMG_NUM_FORMAT_SNORM;
401				else if (desc->channel[first_non_void].pure_integer)
402					return V_008F14_IMG_NUM_FORMAT_SINT;
403				else
404					return V_008F14_IMG_NUM_FORMAT_SSCALED;
405			case VK_FORMAT_TYPE_UNSIGNED:
406				if (desc->channel[first_non_void].normalized)
407					return V_008F14_IMG_NUM_FORMAT_UNORM;
408				else if (desc->channel[first_non_void].pure_integer)
409					return V_008F14_IMG_NUM_FORMAT_UINT;
410				else
411					return V_008F14_IMG_NUM_FORMAT_USCALED;
412			default:
413				return V_008F14_IMG_NUM_FORMAT_UNORM;
414			}
415		}
416	}
417}
418
419uint32_t radv_translate_color_numformat(VkFormat format,
420					const struct vk_format_description *desc,
421					int first_non_void)
422{
423	unsigned ntype;
424	if (first_non_void == -1 || desc->channel[first_non_void].type == VK_FORMAT_TYPE_FLOAT)
425		ntype = V_028C70_NUMBER_FLOAT;
426	else {
427		ntype = V_028C70_NUMBER_UNORM;
428		if (desc->colorspace == VK_FORMAT_COLORSPACE_SRGB)
429			ntype = V_028C70_NUMBER_SRGB;
430		else if (desc->channel[first_non_void].type == VK_FORMAT_TYPE_SIGNED) {
431			if (desc->channel[first_non_void].pure_integer) {
432				ntype = V_028C70_NUMBER_SINT;
433			} else if (desc->channel[first_non_void].normalized) {
434				ntype = V_028C70_NUMBER_SNORM;
435			} else
436				ntype = ~0u;
437		} else if (desc->channel[first_non_void].type == VK_FORMAT_TYPE_UNSIGNED) {
438			if (desc->channel[first_non_void].pure_integer) {
439				ntype = V_028C70_NUMBER_UINT;
440			} else if (desc->channel[first_non_void].normalized) {
441				ntype = V_028C70_NUMBER_UNORM;
442			} else
443				ntype = ~0u;
444		}
445	}
446	return ntype;
447}
448
449static bool radv_is_sampler_format_supported(VkFormat format, bool *linear_sampling)
450{
451	const struct vk_format_description *desc = vk_format_description(format);
452	uint32_t num_format;
453	if (!desc || format == VK_FORMAT_UNDEFINED)
454		return false;
455	num_format = radv_translate_tex_numformat(format, desc,
456						  vk_format_get_first_non_void_channel(format));
457
458	if (num_format == V_008F14_IMG_NUM_FORMAT_USCALED ||
459	    num_format == V_008F14_IMG_NUM_FORMAT_SSCALED)
460		return false;
461
462	if (num_format == V_008F14_IMG_NUM_FORMAT_UNORM ||
463	    num_format == V_008F14_IMG_NUM_FORMAT_SNORM ||
464	    num_format == V_008F14_IMG_NUM_FORMAT_FLOAT ||
465	    num_format == V_008F14_IMG_NUM_FORMAT_SRGB)
466		*linear_sampling = true;
467	else
468		*linear_sampling = false;
469	return radv_translate_tex_dataformat(format, vk_format_description(format),
470					     vk_format_get_first_non_void_channel(format)) != ~0U;
471}
472
473
474static bool radv_is_storage_image_format_supported(struct radv_physical_device *physical_device,
475						   VkFormat format)
476{
477	const struct vk_format_description *desc = vk_format_description(format);
478	unsigned data_format, num_format;
479	if (!desc || format == VK_FORMAT_UNDEFINED)
480		return false;
481
482	data_format = radv_translate_tex_dataformat(format, desc,
483						    vk_format_get_first_non_void_channel(format));
484	num_format = radv_translate_tex_numformat(format, desc,
485						  vk_format_get_first_non_void_channel(format));
486
487	if(data_format == ~0 || num_format == ~0)
488		return false;
489
490	/* Extracted from the GCN3 ISA document. */
491	switch(num_format) {
492	case V_008F14_IMG_NUM_FORMAT_UNORM:
493	case V_008F14_IMG_NUM_FORMAT_SNORM:
494	case V_008F14_IMG_NUM_FORMAT_UINT:
495	case V_008F14_IMG_NUM_FORMAT_SINT:
496	case V_008F14_IMG_NUM_FORMAT_FLOAT:
497		break;
498	default:
499		return false;
500	}
501
502	switch(data_format) {
503	case V_008F14_IMG_DATA_FORMAT_8:
504	case V_008F14_IMG_DATA_FORMAT_16:
505	case V_008F14_IMG_DATA_FORMAT_8_8:
506	case V_008F14_IMG_DATA_FORMAT_32:
507	case V_008F14_IMG_DATA_FORMAT_16_16:
508	case V_008F14_IMG_DATA_FORMAT_10_11_11:
509	case V_008F14_IMG_DATA_FORMAT_11_11_10:
510	case V_008F14_IMG_DATA_FORMAT_10_10_10_2:
511	case V_008F14_IMG_DATA_FORMAT_2_10_10_10:
512	case V_008F14_IMG_DATA_FORMAT_8_8_8_8:
513	case V_008F14_IMG_DATA_FORMAT_32_32:
514	case V_008F14_IMG_DATA_FORMAT_16_16_16_16:
515	case V_008F14_IMG_DATA_FORMAT_32_32_32_32:
516	case V_008F14_IMG_DATA_FORMAT_5_6_5:
517	case V_008F14_IMG_DATA_FORMAT_1_5_5_5:
518	case V_008F14_IMG_DATA_FORMAT_5_5_5_1:
519	case V_008F14_IMG_DATA_FORMAT_4_4_4_4:
520		/* TODO: FMASK formats. */
521		return true;
522	default:
523		return false;
524	}
525}
526
527static bool radv_is_buffer_format_supported(VkFormat format, bool *scaled)
528{
529	const struct vk_format_description *desc = vk_format_description(format);
530	unsigned data_format, num_format;
531	if (!desc || format == VK_FORMAT_UNDEFINED)
532		return false;
533
534	data_format = radv_translate_buffer_dataformat(desc,
535						       vk_format_get_first_non_void_channel(format));
536	num_format = radv_translate_buffer_numformat(desc,
537						     vk_format_get_first_non_void_channel(format));
538
539	*scaled = (num_format == V_008F0C_BUF_NUM_FORMAT_SSCALED) || (num_format == V_008F0C_BUF_NUM_FORMAT_USCALED);
540	return data_format != V_008F0C_BUF_DATA_FORMAT_INVALID &&
541		num_format != ~0;
542}
543
544bool radv_is_colorbuffer_format_supported(VkFormat format, bool *blendable)
545{
546	const struct vk_format_description *desc = vk_format_description(format);
547	uint32_t color_format = radv_translate_colorformat(format);
548	uint32_t color_swap = radv_translate_colorswap(format, false);
549	uint32_t color_num_format = radv_translate_color_numformat(format,
550								   desc,
551								   vk_format_get_first_non_void_channel(format));
552
553	if (color_num_format == V_028C70_NUMBER_UINT || color_num_format == V_028C70_NUMBER_SINT ||
554	    color_format == V_028C70_COLOR_8_24 || color_format == V_028C70_COLOR_24_8 ||
555	    color_format == V_028C70_COLOR_X24_8_32_FLOAT) {
556		*blendable = false;
557	} else
558		*blendable = true;
559	return color_format != V_028C70_COLOR_INVALID &&
560		color_swap != ~0U &&
561		color_num_format != ~0;
562}
563
564static bool radv_is_zs_format_supported(VkFormat format)
565{
566	return radv_translate_dbformat(format) != V_028040_Z_INVALID || format == VK_FORMAT_S8_UINT;
567}
568
569static bool radv_is_filter_minmax_format_supported(VkFormat format)
570{
571	/* From the Vulkan spec 1.1.71:
572	 *
573	 * "The following formats must support the
574	 *  VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_MINMAX_BIT_EXT feature with
575	 *  VK_IMAGE_TILING_OPTIMAL, if they support
576	 *  VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT."
577	 */
578	/* TODO: enable more formats. */
579	switch (format) {
580	case VK_FORMAT_R8_UNORM:
581	case VK_FORMAT_R8_SNORM:
582	case VK_FORMAT_R16_UNORM:
583	case VK_FORMAT_R16_SNORM:
584	case VK_FORMAT_R16_SFLOAT:
585	case VK_FORMAT_R32_SFLOAT:
586	case VK_FORMAT_D16_UNORM:
587	case VK_FORMAT_X8_D24_UNORM_PACK32:
588	case VK_FORMAT_D32_SFLOAT:
589	case VK_FORMAT_D16_UNORM_S8_UINT:
590	case VK_FORMAT_D24_UNORM_S8_UINT:
591	case VK_FORMAT_D32_SFLOAT_S8_UINT:
592		return true;
593	default:
594		return false;
595	}
596}
597
598static void
599radv_physical_device_get_format_properties(struct radv_physical_device *physical_device,
600					   VkFormat format,
601					   VkFormatProperties *out_properties)
602{
603	VkFormatFeatureFlags linear = 0, tiled = 0, buffer = 0;
604	const struct vk_format_description *desc = vk_format_description(format);
605	bool blendable;
606	bool scaled = false;
607	if (!desc) {
608		out_properties->linearTilingFeatures = linear;
609		out_properties->optimalTilingFeatures = tiled;
610		out_properties->bufferFeatures = buffer;
611		return;
612	}
613
614	if (desc->layout == VK_FORMAT_LAYOUT_ETC &&
615	    physical_device->rad_info.family != CHIP_VEGA10 &&
616	    physical_device->rad_info.family != CHIP_RAVEN &&
617	    physical_device->rad_info.family != CHIP_STONEY) {
618		out_properties->linearTilingFeatures = linear;
619		out_properties->optimalTilingFeatures = tiled;
620		out_properties->bufferFeatures = buffer;
621		return;
622	}
623
624	if (radv_is_storage_image_format_supported(physical_device, format)) {
625		tiled |= VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT;
626		linear |= VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT;
627	}
628
629	if (radv_is_buffer_format_supported(format, &scaled)) {
630		buffer |= VK_FORMAT_FEATURE_VERTEX_BUFFER_BIT;
631		if (!scaled)
632			buffer |= VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT |
633				VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT;
634	}
635
636	if (vk_format_is_depth_or_stencil(format)) {
637		if (radv_is_zs_format_supported(format)) {
638			tiled |= VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT;
639			tiled |= VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT;
640			tiled |= VK_FORMAT_FEATURE_BLIT_SRC_BIT |
641			         VK_FORMAT_FEATURE_BLIT_DST_BIT;
642			tiled |= VK_FORMAT_FEATURE_TRANSFER_SRC_BIT_KHR |
643			         VK_FORMAT_FEATURE_TRANSFER_DST_BIT_KHR;
644
645			if (radv_is_filter_minmax_format_supported(format))
646				 tiled |= VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_MINMAX_BIT_EXT;
647
648			/* Don't support blitting surfaces with depth/stencil. */
649			if (vk_format_is_depth(format) && vk_format_is_stencil(format))
650				tiled &= ~VK_FORMAT_FEATURE_BLIT_DST_BIT;
651
652			/* Don't support linear depth surfaces */
653			linear = 0;
654		}
655	} else {
656		bool linear_sampling;
657		if (radv_is_sampler_format_supported(format, &linear_sampling)) {
658			linear |= VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT |
659				VK_FORMAT_FEATURE_BLIT_SRC_BIT;
660			tiled |= VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT |
661				VK_FORMAT_FEATURE_BLIT_SRC_BIT;
662
663			if (radv_is_filter_minmax_format_supported(format))
664				 tiled |= VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_MINMAX_BIT_EXT;
665
666			if (linear_sampling) {
667				linear |= VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT;
668				tiled |= VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT;
669			}
670
671			/* Don't support blitting for R32G32B32 formats. */
672			if (format == VK_FORMAT_R32G32B32_SFLOAT ||
673			    format == VK_FORMAT_R32G32B32_UINT ||
674			    format == VK_FORMAT_R32G32B32_SINT) {
675				linear &= ~VK_FORMAT_FEATURE_BLIT_SRC_BIT;
676			}
677		}
678		if (radv_is_colorbuffer_format_supported(format, &blendable)) {
679			linear |= VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT | VK_FORMAT_FEATURE_BLIT_DST_BIT;
680			tiled |= VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT | VK_FORMAT_FEATURE_BLIT_DST_BIT;
681			if (blendable) {
682				linear |= VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BLEND_BIT;
683				tiled |= VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BLEND_BIT;
684			}
685		}
686		if (tiled && !scaled) {
687			tiled |= VK_FORMAT_FEATURE_TRANSFER_SRC_BIT_KHR |
688			         VK_FORMAT_FEATURE_TRANSFER_DST_BIT_KHR;
689		}
690
691		/* Tiled formatting does not support NPOT pixel sizes */
692		if (!util_is_power_of_two_or_zero(vk_format_get_blocksize(format)))
693			tiled = 0;
694	}
695
696	if (linear && !scaled) {
697		linear |= VK_FORMAT_FEATURE_TRANSFER_SRC_BIT_KHR |
698		          VK_FORMAT_FEATURE_TRANSFER_DST_BIT_KHR;
699	}
700
701	if (format == VK_FORMAT_R32_UINT || format == VK_FORMAT_R32_SINT) {
702		buffer |= VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_ATOMIC_BIT;
703		linear |= VK_FORMAT_FEATURE_STORAGE_IMAGE_ATOMIC_BIT;
704		tiled |= VK_FORMAT_FEATURE_STORAGE_IMAGE_ATOMIC_BIT;
705	}
706
707	switch(format) {
708	case VK_FORMAT_A2R10G10B10_SNORM_PACK32:
709	case VK_FORMAT_A2B10G10R10_SNORM_PACK32:
710	case VK_FORMAT_A2R10G10B10_SSCALED_PACK32:
711	case VK_FORMAT_A2B10G10R10_SSCALED_PACK32:
712	case VK_FORMAT_A2R10G10B10_SINT_PACK32:
713	case VK_FORMAT_A2B10G10R10_SINT_PACK32:
714		if (physical_device->rad_info.chip_class <= VI &&
715		    physical_device->rad_info.family != CHIP_STONEY) {
716			buffer &= ~(VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT |
717			            VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT);
718			linear = 0;
719			tiled = 0;
720		}
721		break;
722	default:
723		break;
724	}
725
726	out_properties->linearTilingFeatures = linear;
727	out_properties->optimalTilingFeatures = tiled;
728	out_properties->bufferFeatures = buffer;
729}
730
731uint32_t radv_translate_colorformat(VkFormat format)
732{
733	const struct vk_format_description *desc = vk_format_description(format);
734
735#define HAS_SIZE(x,y,z,w)						\
736	(desc->channel[0].size == (x) && desc->channel[1].size == (y) && \
737         desc->channel[2].size == (z) && desc->channel[3].size == (w))
738
739	if (format == VK_FORMAT_B10G11R11_UFLOAT_PACK32) /* isn't plain */
740		return V_028C70_COLOR_10_11_11;
741
742	if (desc->layout != VK_FORMAT_LAYOUT_PLAIN)
743		return V_028C70_COLOR_INVALID;
744
745	/* hw cannot support mixed formats (except depth/stencil, since
746	 * stencil is not written to). */
747	if (desc->is_mixed && desc->colorspace != VK_FORMAT_COLORSPACE_ZS)
748		return V_028C70_COLOR_INVALID;
749
750	switch (desc->nr_channels) {
751	case 1:
752		switch (desc->channel[0].size) {
753		case 8:
754			return V_028C70_COLOR_8;
755		case 16:
756			return V_028C70_COLOR_16;
757		case 32:
758			return V_028C70_COLOR_32;
759		}
760		break;
761	case 2:
762		if (desc->channel[0].size == desc->channel[1].size) {
763			switch (desc->channel[0].size) {
764			case 8:
765				return V_028C70_COLOR_8_8;
766			case 16:
767				return V_028C70_COLOR_16_16;
768			case 32:
769				return V_028C70_COLOR_32_32;
770			}
771		} else if (HAS_SIZE(8,24,0,0)) {
772			return V_028C70_COLOR_24_8;
773		} else if (HAS_SIZE(24,8,0,0)) {
774			return V_028C70_COLOR_8_24;
775		}
776		break;
777	case 3:
778		if (HAS_SIZE(5,6,5,0)) {
779			return V_028C70_COLOR_5_6_5;
780		} else if (HAS_SIZE(32,8,24,0)) {
781			return V_028C70_COLOR_X24_8_32_FLOAT;
782		}
783		break;
784	case 4:
785		if (desc->channel[0].size == desc->channel[1].size &&
786		    desc->channel[0].size == desc->channel[2].size &&
787		    desc->channel[0].size == desc->channel[3].size) {
788			switch (desc->channel[0].size) {
789			case 4:
790				return V_028C70_COLOR_4_4_4_4;
791			case 8:
792				return V_028C70_COLOR_8_8_8_8;
793			case 16:
794				return V_028C70_COLOR_16_16_16_16;
795			case 32:
796				return V_028C70_COLOR_32_32_32_32;
797			}
798		} else if (HAS_SIZE(5,5,5,1)) {
799			return V_028C70_COLOR_1_5_5_5;
800		} else if (HAS_SIZE(1,5,5,5)) {
801			return V_028C70_COLOR_5_5_5_1;
802		} else if (HAS_SIZE(10,10,10,2)) {
803			return V_028C70_COLOR_2_10_10_10;
804		}
805		break;
806	}
807	return V_028C70_COLOR_INVALID;
808}
809
810uint32_t radv_colorformat_endian_swap(uint32_t colorformat)
811{
812	if (0/*SI_BIG_ENDIAN*/) {
813		switch(colorformat) {
814			/* 8-bit buffers. */
815		case V_028C70_COLOR_8:
816			return V_028C70_ENDIAN_NONE;
817
818			/* 16-bit buffers. */
819		case V_028C70_COLOR_5_6_5:
820		case V_028C70_COLOR_1_5_5_5:
821		case V_028C70_COLOR_4_4_4_4:
822		case V_028C70_COLOR_16:
823		case V_028C70_COLOR_8_8:
824			return V_028C70_ENDIAN_8IN16;
825
826			/* 32-bit buffers. */
827		case V_028C70_COLOR_8_8_8_8:
828		case V_028C70_COLOR_2_10_10_10:
829		case V_028C70_COLOR_8_24:
830		case V_028C70_COLOR_24_8:
831		case V_028C70_COLOR_16_16:
832			return V_028C70_ENDIAN_8IN32;
833
834			/* 64-bit buffers. */
835		case V_028C70_COLOR_16_16_16_16:
836			return V_028C70_ENDIAN_8IN16;
837
838		case V_028C70_COLOR_32_32:
839			return V_028C70_ENDIAN_8IN32;
840
841			/* 128-bit buffers. */
842		case V_028C70_COLOR_32_32_32_32:
843			return V_028C70_ENDIAN_8IN32;
844		default:
845			return V_028C70_ENDIAN_NONE; /* Unsupported. */
846		}
847	} else {
848		return V_028C70_ENDIAN_NONE;
849	}
850}
851
852uint32_t radv_translate_dbformat(VkFormat format)
853{
854	switch (format) {
855	case VK_FORMAT_D16_UNORM:
856	case VK_FORMAT_D16_UNORM_S8_UINT:
857		return V_028040_Z_16;
858	case VK_FORMAT_D32_SFLOAT:
859	case VK_FORMAT_D32_SFLOAT_S8_UINT:
860		return V_028040_Z_32_FLOAT;
861	default:
862		return V_028040_Z_INVALID;
863	}
864}
865
866unsigned radv_translate_colorswap(VkFormat format, bool do_endian_swap)
867{
868	const struct vk_format_description *desc = vk_format_description(format);
869
870#define HAS_SWIZZLE(chan,swz) (desc->swizzle[chan] == VK_SWIZZLE_##swz)
871
872	if (format == VK_FORMAT_B10G11R11_UFLOAT_PACK32)
873		return V_028C70_SWAP_STD;
874
875	if (desc->layout != VK_FORMAT_LAYOUT_PLAIN)
876		return ~0U;
877
878	switch (desc->nr_channels) {
879	case 1:
880		if (HAS_SWIZZLE(0,X))
881			return V_028C70_SWAP_STD; /* X___ */
882		else if (HAS_SWIZZLE(3,X))
883			return V_028C70_SWAP_ALT_REV; /* ___X */
884		break;
885	case 2:
886		if ((HAS_SWIZZLE(0,X) && HAS_SWIZZLE(1,Y)) ||
887		    (HAS_SWIZZLE(0,X) && HAS_SWIZZLE(1,NONE)) ||
888		    (HAS_SWIZZLE(0,NONE) && HAS_SWIZZLE(1,Y)))
889			return V_028C70_SWAP_STD; /* XY__ */
890		else if ((HAS_SWIZZLE(0,Y) && HAS_SWIZZLE(1,X)) ||
891			 (HAS_SWIZZLE(0,Y) && HAS_SWIZZLE(1,NONE)) ||
892		         (HAS_SWIZZLE(0,NONE) && HAS_SWIZZLE(1,X)))
893			/* YX__ */
894			return (do_endian_swap ? V_028C70_SWAP_STD : V_028C70_SWAP_STD_REV);
895		else if (HAS_SWIZZLE(0,X) && HAS_SWIZZLE(3,Y))
896			return V_028C70_SWAP_ALT; /* X__Y */
897		else if (HAS_SWIZZLE(0,Y) && HAS_SWIZZLE(3,X))
898			return V_028C70_SWAP_ALT_REV; /* Y__X */
899		break;
900	case 3:
901		if (HAS_SWIZZLE(0,X))
902			return (do_endian_swap ? V_028C70_SWAP_STD_REV : V_028C70_SWAP_STD);
903		else if (HAS_SWIZZLE(0,Z))
904			return V_028C70_SWAP_STD_REV; /* ZYX */
905		break;
906	case 4:
907		/* check the middle channels, the 1st and 4th channel can be NONE */
908		if (HAS_SWIZZLE(1,Y) && HAS_SWIZZLE(2,Z)) {
909			return V_028C70_SWAP_STD; /* XYZW */
910		} else if (HAS_SWIZZLE(1,Z) && HAS_SWIZZLE(2,Y)) {
911			return V_028C70_SWAP_STD_REV; /* WZYX */
912		} else if (HAS_SWIZZLE(1,Y) && HAS_SWIZZLE(2,X)) {
913			return V_028C70_SWAP_ALT; /* ZYXW */
914		} else if (HAS_SWIZZLE(1,Z) && HAS_SWIZZLE(2,W)) {
915			/* YZWX */
916			if (desc->is_array)
917				return V_028C70_SWAP_ALT_REV;
918			else
919				return (do_endian_swap ? V_028C70_SWAP_ALT : V_028C70_SWAP_ALT_REV);
920		}
921		break;
922	}
923	return ~0U;
924}
925
926bool radv_format_pack_clear_color(VkFormat format,
927				  uint32_t clear_vals[2],
928				  VkClearColorValue *value)
929{
930	const struct vk_format_description *desc = vk_format_description(format);
931
932	if (format == VK_FORMAT_B10G11R11_UFLOAT_PACK32) {
933		clear_vals[0] = float3_to_r11g11b10f(value->float32);
934		clear_vals[1] = 0;
935		return true;
936	}
937
938	if (desc->layout != VK_FORMAT_LAYOUT_PLAIN) {
939		fprintf(stderr, "failed to fast clear for non-plain format %d\n", format);
940		return false;
941	}
942
943	if (!util_is_power_of_two_or_zero(desc->block.bits)) {
944		fprintf(stderr, "failed to fast clear for NPOT format %d\n", format);
945		return false;
946	}
947
948	if (desc->block.bits > 64) {
949		/*
950		 * We have a 128 bits format, check if the first 3 components are the same.
951		 * Every elements has to be 32 bits since we don't support 64-bit formats,
952		 * and we can skip swizzling checks as alpha always comes last for these and
953		 * we do not care about the rest as they have to be the same.
954		 */
955		if (desc->channel[0].type == VK_FORMAT_TYPE_FLOAT) {
956			if (value->float32[0] != value->float32[1] ||
957			    value->float32[0] != value->float32[2])
958				return false;
959		} else {
960			if (value->uint32[0] != value->uint32[1] ||
961			    value->uint32[0] != value->uint32[2])
962				return false;
963		}
964		clear_vals[0] = value->uint32[0];
965		clear_vals[1] = value->uint32[3];
966		return true;
967	}
968	uint64_t clear_val = 0;
969
970	for (unsigned c = 0; c < 4; ++c) {
971		if (desc->swizzle[c] >= 4)
972			continue;
973
974		const struct vk_format_channel_description *channel = &desc->channel[desc->swizzle[c]];
975		assert(channel->size);
976
977		uint64_t v = 0;
978		if (channel->pure_integer) {
979			v = value->uint32[c]  & ((1ULL << channel->size) - 1);
980		} else if (channel->normalized) {
981			if (channel->type == VK_FORMAT_TYPE_UNSIGNED &&
982			    desc->swizzle[c] < 3 &&
983			    desc->colorspace == VK_FORMAT_COLORSPACE_SRGB) {
984				assert(channel->size == 8);
985
986				v = util_format_linear_float_to_srgb_8unorm(value->float32[c]);
987			} else if (channel->type == VK_FORMAT_TYPE_UNSIGNED) {
988				v = MAX2(MIN2(value->float32[c], 1.0f), 0.0f) * ((1ULL << channel->size) - 1);
989			} else  {
990				v = MAX2(MIN2(value->float32[c], 1.0f), -1.0f) * ((1ULL << (channel->size - 1)) - 1);
991			}
992		} else if (channel->type == VK_FORMAT_TYPE_FLOAT) {
993			if (channel->size == 32) {
994				memcpy(&v, &value->float32[c], 4);
995			} else if(channel->size == 16) {
996				v = util_float_to_half(value->float32[c]);
997			} else {
998				fprintf(stderr, "failed to fast clear for unhandled float size in format %d\n", format);
999				return false;
1000			}
1001		} else {
1002			fprintf(stderr, "failed to fast clear for unhandled component type in format %d\n", format);
1003			return false;
1004		}
1005		clear_val |= (v & ((1ULL << channel->size) - 1)) << channel->shift;
1006	}
1007
1008	clear_vals[0] = clear_val;
1009	clear_vals[1] = clear_val >> 32;
1010
1011	return true;
1012}
1013
1014void radv_GetPhysicalDeviceFormatProperties(
1015	VkPhysicalDevice                            physicalDevice,
1016	VkFormat                                    format,
1017	VkFormatProperties*                         pFormatProperties)
1018{
1019	RADV_FROM_HANDLE(radv_physical_device, physical_device, physicalDevice);
1020
1021	radv_physical_device_get_format_properties(physical_device,
1022						   format,
1023						   pFormatProperties);
1024}
1025
1026void radv_GetPhysicalDeviceFormatProperties2(
1027	VkPhysicalDevice                            physicalDevice,
1028	VkFormat                                    format,
1029	VkFormatProperties2KHR*                         pFormatProperties)
1030{
1031	RADV_FROM_HANDLE(radv_physical_device, physical_device, physicalDevice);
1032
1033	radv_physical_device_get_format_properties(physical_device,
1034						   format,
1035						   &pFormatProperties->formatProperties);
1036}
1037
1038static VkResult radv_get_image_format_properties(struct radv_physical_device *physical_device,
1039						 const VkPhysicalDeviceImageFormatInfo2KHR *info,
1040						 VkImageFormatProperties *pImageFormatProperties)
1041
1042{
1043	VkFormatProperties format_props;
1044	VkFormatFeatureFlags format_feature_flags;
1045	VkExtent3D maxExtent;
1046	uint32_t maxMipLevels;
1047	uint32_t maxArraySize;
1048	VkSampleCountFlags sampleCounts = VK_SAMPLE_COUNT_1_BIT;
1049
1050	radv_physical_device_get_format_properties(physical_device, info->format,
1051						   &format_props);
1052	if (info->tiling == VK_IMAGE_TILING_LINEAR) {
1053		format_feature_flags = format_props.linearTilingFeatures;
1054	} else if (info->tiling == VK_IMAGE_TILING_OPTIMAL) {
1055		format_feature_flags = format_props.optimalTilingFeatures;
1056	} else {
1057		unreachable("bad VkImageTiling");
1058	}
1059
1060	if (format_feature_flags == 0)
1061		goto unsupported;
1062
1063	if (info->type != VK_IMAGE_TYPE_2D && vk_format_is_depth_or_stencil(info->format))
1064		goto unsupported;
1065
1066	switch (info->type) {
1067	default:
1068		unreachable("bad vkimage type\n");
1069	case VK_IMAGE_TYPE_1D:
1070		maxExtent.width = 16384;
1071		maxExtent.height = 1;
1072		maxExtent.depth = 1;
1073		maxMipLevels = 15; /* log2(maxWidth) + 1 */
1074		maxArraySize = 2048;
1075		break;
1076	case VK_IMAGE_TYPE_2D:
1077		maxExtent.width = 16384;
1078		maxExtent.height = 16384;
1079		maxExtent.depth = 1;
1080		maxMipLevels = 15; /* log2(maxWidth) + 1 */
1081		maxArraySize = 2048;
1082		break;
1083	case VK_IMAGE_TYPE_3D:
1084		maxExtent.width = 2048;
1085		maxExtent.height = 2048;
1086		maxExtent.depth = 2048;
1087		maxMipLevels = 12; /* log2(maxWidth) + 1 */
1088		maxArraySize = 1;
1089		break;
1090	}
1091
1092	if (info->tiling == VK_IMAGE_TILING_OPTIMAL &&
1093	    info->type == VK_IMAGE_TYPE_2D &&
1094	    (format_feature_flags & (VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT |
1095				     VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT)) &&
1096	    !(info->flags & VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT) &&
1097	    !(info->usage & VK_IMAGE_USAGE_STORAGE_BIT)) {
1098		sampleCounts |= VK_SAMPLE_COUNT_2_BIT | VK_SAMPLE_COUNT_4_BIT | VK_SAMPLE_COUNT_8_BIT;
1099	}
1100
1101	if (info->tiling == VK_IMAGE_TILING_LINEAR &&
1102	    (info->format == VK_FORMAT_R32G32B32_SFLOAT ||
1103	     info->format == VK_FORMAT_R32G32B32_SINT ||
1104	     info->format == VK_FORMAT_R32G32B32_UINT)) {
1105		/* R32G32B32 is a weird format and the driver currently only
1106		 * supports the barely minimum.
1107		 * TODO: Implement more if we really need to.
1108		 */
1109		if (info->type == VK_IMAGE_TYPE_3D)
1110			goto unsupported;
1111		maxArraySize = 1;
1112		maxMipLevels = 1;
1113	}
1114
1115	if (info->usage & VK_IMAGE_USAGE_SAMPLED_BIT) {
1116		if (!(format_feature_flags & VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT)) {
1117			goto unsupported;
1118		}
1119	}
1120
1121	if (info->usage & VK_IMAGE_USAGE_STORAGE_BIT) {
1122		if (!(format_feature_flags & VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT)) {
1123			goto unsupported;
1124		}
1125	}
1126
1127	if (info->usage & VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT) {
1128		if (!(format_feature_flags & VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT)) {
1129			goto unsupported;
1130		}
1131	}
1132
1133	if (info->usage & VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT) {
1134		if (!(format_feature_flags & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT)) {
1135			goto unsupported;
1136		}
1137	}
1138
1139	if (info->usage & VK_IMAGE_USAGE_TRANSFER_SRC_BIT) {
1140		if (!(format_feature_flags & VK_FORMAT_FEATURE_TRANSFER_SRC_BIT)) {
1141			goto unsupported;
1142		}
1143	}
1144
1145	if (info->usage & VK_IMAGE_USAGE_TRANSFER_DST_BIT) {
1146		if (!(format_feature_flags & VK_FORMAT_FEATURE_TRANSFER_DST_BIT)) {
1147			goto unsupported;
1148		}
1149	}
1150
1151	if (info->usage & VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT) {
1152		if (!(format_feature_flags & (VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT |
1153		                              VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT))) {
1154			goto unsupported;
1155		}
1156	}
1157
1158	*pImageFormatProperties = (VkImageFormatProperties) {
1159		.maxExtent = maxExtent,
1160		.maxMipLevels = maxMipLevels,
1161		.maxArrayLayers = maxArraySize,
1162		.sampleCounts = sampleCounts,
1163
1164		/* FINISHME: Accurately calculate
1165		 * VkImageFormatProperties::maxResourceSize.
1166		 */
1167		.maxResourceSize = UINT32_MAX,
1168	};
1169
1170	return VK_SUCCESS;
1171unsupported:
1172	*pImageFormatProperties = (VkImageFormatProperties) {
1173		.maxExtent = { 0, 0, 0 },
1174		.maxMipLevels = 0,
1175		.maxArrayLayers = 0,
1176		.sampleCounts = 0,
1177		.maxResourceSize = 0,
1178	};
1179
1180	return VK_ERROR_FORMAT_NOT_SUPPORTED;
1181}
1182
1183VkResult radv_GetPhysicalDeviceImageFormatProperties(
1184	VkPhysicalDevice                            physicalDevice,
1185	VkFormat                                    format,
1186	VkImageType                                 type,
1187	VkImageTiling                               tiling,
1188	VkImageUsageFlags                           usage,
1189	VkImageCreateFlags                          createFlags,
1190	VkImageFormatProperties*                    pImageFormatProperties)
1191{
1192	RADV_FROM_HANDLE(radv_physical_device, physical_device, physicalDevice);
1193
1194	const VkPhysicalDeviceImageFormatInfo2KHR info = {
1195		.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_FORMAT_INFO_2_KHR,
1196		.pNext = NULL,
1197		.format = format,
1198		.type = type,
1199		.tiling = tiling,
1200		.usage = usage,
1201		.flags = createFlags,
1202	};
1203
1204	return radv_get_image_format_properties(physical_device, &info,
1205						pImageFormatProperties);
1206}
1207
1208static void
1209get_external_image_format_properties(const VkPhysicalDeviceImageFormatInfo2KHR *pImageFormatInfo,
1210				     VkExternalMemoryHandleTypeFlagBitsKHR handleType,
1211				     VkExternalMemoryPropertiesKHR *external_properties)
1212{
1213	VkExternalMemoryFeatureFlagBitsKHR flags = 0;
1214	VkExternalMemoryHandleTypeFlagsKHR export_flags = 0;
1215	VkExternalMemoryHandleTypeFlagsKHR compat_flags = 0;
1216	switch (handleType) {
1217	case VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT_KHR:
1218	case VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT:
1219		switch (pImageFormatInfo->type) {
1220		case VK_IMAGE_TYPE_2D:
1221			flags = VK_EXTERNAL_MEMORY_FEATURE_DEDICATED_ONLY_BIT_KHR|VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT_KHR|VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT_KHR;
1222			compat_flags = export_flags = VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT_KHR |
1223						      VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
1224			break;
1225		default:
1226			break;
1227		}
1228		break;
1229	case VK_EXTERNAL_MEMORY_HANDLE_TYPE_HOST_ALLOCATION_BIT_EXT:
1230		flags = VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT_KHR;
1231		compat_flags = VK_EXTERNAL_MEMORY_HANDLE_TYPE_HOST_ALLOCATION_BIT_EXT;
1232		break;
1233	default:
1234		break;
1235	}
1236
1237	*external_properties = (VkExternalMemoryPropertiesKHR) {
1238		.externalMemoryFeatures = flags,
1239		.exportFromImportedHandleTypes = export_flags,
1240		.compatibleHandleTypes = compat_flags,
1241	};
1242}
1243
1244VkResult radv_GetPhysicalDeviceImageFormatProperties2(
1245	VkPhysicalDevice                            physicalDevice,
1246	const VkPhysicalDeviceImageFormatInfo2KHR  *base_info,
1247	VkImageFormatProperties2KHR                *base_props)
1248{
1249	RADV_FROM_HANDLE(radv_physical_device, physical_device, physicalDevice);
1250	const VkPhysicalDeviceExternalImageFormatInfoKHR *external_info = NULL;
1251	VkExternalImageFormatPropertiesKHR *external_props = NULL;
1252	VkResult result;
1253
1254	result = radv_get_image_format_properties(physical_device, base_info,
1255						&base_props->imageFormatProperties);
1256	if (result != VK_SUCCESS)
1257		return result;
1258
1259	   /* Extract input structs */
1260	vk_foreach_struct_const(s, base_info->pNext) {
1261		switch (s->sType) {
1262		case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTERNAL_IMAGE_FORMAT_INFO_KHR:
1263			external_info = (const void *) s;
1264			break;
1265		default:
1266			break;
1267		}
1268	}
1269
1270	/* Extract output structs */
1271	vk_foreach_struct(s, base_props->pNext) {
1272		switch (s->sType) {
1273		case VK_STRUCTURE_TYPE_EXTERNAL_IMAGE_FORMAT_PROPERTIES_KHR:
1274			external_props = (void *) s;
1275			break;
1276		default:
1277			break;
1278		}
1279	}
1280
1281	/* From the Vulkan 1.0.42 spec:
1282	 *
1283	 *    If handleType is 0, vkGetPhysicalDeviceImageFormatProperties2KHR will
1284	 *    behave as if VkPhysicalDeviceExternalImageFormatInfoKHR was not
1285	 *    present and VkExternalImageFormatPropertiesKHR will be ignored.
1286	 */
1287	if (external_info && external_info->handleType != 0) {
1288		switch (external_info->handleType) {
1289		case VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT_KHR:
1290		case VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT:
1291		case VK_EXTERNAL_MEMORY_HANDLE_TYPE_HOST_ALLOCATION_BIT_EXT:
1292			get_external_image_format_properties(base_info, external_info->handleType,
1293			                                     &external_props->externalMemoryProperties);
1294			break;
1295		default:
1296			/* From the Vulkan 1.0.42 spec:
1297			 *
1298			 *    If handleType is not compatible with the [parameters] specified
1299			 *    in VkPhysicalDeviceImageFormatInfo2KHR, then
1300			 *    vkGetPhysicalDeviceImageFormatProperties2KHR returns
1301			 *    VK_ERROR_FORMAT_NOT_SUPPORTED.
1302			 */
1303			result = vk_errorf(physical_device->instance, VK_ERROR_FORMAT_NOT_SUPPORTED,
1304					   "unsupported VkExternalMemoryTypeFlagBitsKHR 0x%x",
1305					   external_info->handleType);
1306			goto fail;
1307		}
1308	}
1309
1310	return VK_SUCCESS;
1311
1312fail:
1313	if (result == VK_ERROR_FORMAT_NOT_SUPPORTED) {
1314		/* From the Vulkan 1.0.42 spec:
1315		 *
1316		 *    If the combination of parameters to
1317		 *    vkGetPhysicalDeviceImageFormatProperties2KHR is not supported by
1318		 *    the implementation for use in vkCreateImage, then all members of
1319		 *    imageFormatProperties will be filled with zero.
1320		 */
1321		base_props->imageFormatProperties = (VkImageFormatProperties) {0};
1322	}
1323
1324	return result;
1325}
1326
1327void radv_GetPhysicalDeviceSparseImageFormatProperties(
1328	VkPhysicalDevice                            physicalDevice,
1329	VkFormat                                    format,
1330	VkImageType                                 type,
1331	uint32_t                                    samples,
1332	VkImageUsageFlags                           usage,
1333	VkImageTiling                               tiling,
1334	uint32_t*                                   pNumProperties,
1335	VkSparseImageFormatProperties*              pProperties)
1336{
1337	/* Sparse images are not yet supported. */
1338	*pNumProperties = 0;
1339}
1340
1341void radv_GetPhysicalDeviceSparseImageFormatProperties2(
1342	VkPhysicalDevice                            physicalDevice,
1343	const VkPhysicalDeviceSparseImageFormatInfo2KHR* pFormatInfo,
1344	uint32_t                                   *pPropertyCount,
1345	VkSparseImageFormatProperties2KHR*          pProperties)
1346{
1347	/* Sparse images are not yet supported. */
1348	*pPropertyCount = 0;
1349}
1350
1351void radv_GetPhysicalDeviceExternalBufferProperties(
1352	VkPhysicalDevice                            physicalDevice,
1353	const VkPhysicalDeviceExternalBufferInfoKHR *pExternalBufferInfo,
1354	VkExternalBufferPropertiesKHR               *pExternalBufferProperties)
1355{
1356	VkExternalMemoryFeatureFlagBitsKHR flags = 0;
1357	VkExternalMemoryHandleTypeFlagsKHR export_flags = 0;
1358	VkExternalMemoryHandleTypeFlagsKHR compat_flags = 0;
1359	switch(pExternalBufferInfo->handleType) {
1360	case VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT_KHR:
1361	case VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT:
1362		flags = VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT_KHR |
1363		        VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT_KHR;
1364		compat_flags = export_flags = VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT_KHR |
1365					      VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
1366		break;
1367	case VK_EXTERNAL_MEMORY_HANDLE_TYPE_HOST_ALLOCATION_BIT_EXT:
1368		flags = VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT_KHR;
1369		compat_flags = VK_EXTERNAL_MEMORY_HANDLE_TYPE_HOST_ALLOCATION_BIT_EXT;
1370		break;
1371	default:
1372		break;
1373	}
1374	pExternalBufferProperties->externalMemoryProperties = (VkExternalMemoryPropertiesKHR) {
1375		.externalMemoryFeatures = flags,
1376		.exportFromImportedHandleTypes = export_flags,
1377		.compatibleHandleTypes = compat_flags,
1378	};
1379}
1380
1381/* DCC channel type categories within which formats can be reinterpreted
1382 * while keeping the same DCC encoding. The swizzle must also match. */
1383enum dcc_channel_type {
1384        dcc_channel_float32,
1385        dcc_channel_uint32,
1386        dcc_channel_sint32,
1387        dcc_channel_float16,
1388        dcc_channel_uint16,
1389        dcc_channel_sint16,
1390        dcc_channel_uint_10_10_10_2,
1391        dcc_channel_uint8,
1392        dcc_channel_sint8,
1393        dcc_channel_incompatible,
1394};
1395
1396/* Return the type of DCC encoding. */
1397static enum dcc_channel_type
1398radv_get_dcc_channel_type(const struct vk_format_description *desc)
1399{
1400        int i;
1401
1402        /* Find the first non-void channel. */
1403        for (i = 0; i < desc->nr_channels; i++)
1404                if (desc->channel[i].type != VK_FORMAT_TYPE_VOID)
1405                        break;
1406        if (i == desc->nr_channels)
1407                return dcc_channel_incompatible;
1408
1409        switch (desc->channel[i].size) {
1410        case 32:
1411                if (desc->channel[i].type == VK_FORMAT_TYPE_FLOAT)
1412                        return dcc_channel_float32;
1413                if (desc->channel[i].type == VK_FORMAT_TYPE_UNSIGNED)
1414                        return dcc_channel_uint32;
1415                return dcc_channel_sint32;
1416        case 16:
1417                if (desc->channel[i].type == VK_FORMAT_TYPE_FLOAT)
1418                        return dcc_channel_float16;
1419                if (desc->channel[i].type == VK_FORMAT_TYPE_UNSIGNED)
1420                        return dcc_channel_uint16;
1421                return dcc_channel_sint16;
1422        case 10:
1423                return dcc_channel_uint_10_10_10_2;
1424        case 8:
1425                if (desc->channel[i].type == VK_FORMAT_TYPE_UNSIGNED)
1426                        return dcc_channel_uint8;
1427                return dcc_channel_sint8;
1428        default:
1429                return dcc_channel_incompatible;
1430        }
1431}
1432
1433/* Return if it's allowed to reinterpret one format as another with DCC enabled. */
1434bool radv_dcc_formats_compatible(VkFormat format1,
1435                                 VkFormat format2)
1436{
1437        const struct vk_format_description *desc1, *desc2;
1438        enum dcc_channel_type type1, type2;
1439        int i;
1440
1441        if (format1 == format2)
1442                return true;
1443
1444        desc1 = vk_format_description(format1);
1445        desc2 = vk_format_description(format2);
1446
1447        if (desc1->nr_channels != desc2->nr_channels)
1448                return false;
1449
1450        /* Swizzles must be the same. */
1451        for (i = 0; i < desc1->nr_channels; i++)
1452                if (desc1->swizzle[i] <= VK_SWIZZLE_W &&
1453                    desc2->swizzle[i] <= VK_SWIZZLE_W &&
1454                    desc1->swizzle[i] != desc2->swizzle[i])
1455                        return false;
1456
1457        type1 = radv_get_dcc_channel_type(desc1);
1458        type2 = radv_get_dcc_channel_type(desc2);
1459
1460        return type1 != dcc_channel_incompatible &&
1461               type2 != dcc_channel_incompatible &&
1462               type1 == type2;
1463}
1464
1465