• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright © 2022 Imagination Technologies Ltd.
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a copy
5  * of this software and associated documentation files (the "Software"), to deal
6  * in the Software without restriction, including without limitation the rights
7  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8  * copies of the Software, and to permit persons to whom the Software is
9  * furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice (including the next
12  * paragraph) shall be included in all copies or substantial portions of the
13  * Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21  * SOFTWARE.
22  */
23 
24 #include <assert.h>
25 #include <stdbool.h>
26 #include <stddef.h>
27 #include <stdint.h>
28 #include <vulkan/vulkan.h>
29 
30 #include "hwdef/rogue_hw_utils.h"
31 #include "pvr_common.h"
32 #include "pvr_formats.h"
33 #include "pvr_private.h"
34 #include "util/bitpack_helpers.h"
35 #include "util/compiler.h"
36 #include "util/format/format_utils.h"
37 #include "util/format/u_formats.h"
38 #include "util/half_float.h"
39 #include "util/log.h"
40 #include "util/macros.h"
41 #include "util/u_math.h"
42 #include "vk_enum_defines.h"
43 #include "vk_enum_to_str.h"
44 #include "vk_format.h"
45 #include "vk_log.h"
46 #include "vk_util.h"
47 
48 #define FORMAT(vk, tex_fmt, pack_mode, accum_format)           \
49    [VK_FORMAT_##vk] = {                                        \
50       .vk_format = VK_FORMAT_##vk,                             \
51       .tex_format = ROGUE_TEXSTATE_FORMAT_##tex_fmt,           \
52       .depth_tex_format = ROGUE_TEXSTATE_FORMAT_INVALID,       \
53       .stencil_tex_format = ROGUE_TEXSTATE_FORMAT_INVALID,     \
54       .pbe_packmode = ROGUE_PBESTATE_PACKMODE_##pack_mode,     \
55       .pbe_accum_format = PVR_PBE_ACCUM_FORMAT_##accum_format, \
56       .supported = true,                                       \
57    }
58 
59 #define FORMAT_COMPRESSED(vk, tex_fmt)                          \
60    [VK_FORMAT_##vk] = {                                         \
61       .vk_format = VK_FORMAT_##vk,                              \
62       .tex_format = ROGUE_TEXSTATE_FORMAT_COMPRESSED_##tex_fmt, \
63       .depth_tex_format = ROGUE_TEXSTATE_FORMAT_INVALID,        \
64       .stencil_tex_format = ROGUE_TEXSTATE_FORMAT_INVALID,      \
65       .pbe_packmode = ROGUE_PBESTATE_PACKMODE_INVALID,          \
66       .pbe_accum_format = PVR_PBE_ACCUM_FORMAT_INVALID,         \
67       .supported = true,                                        \
68    }
69 
70 #define FORMAT_DEPTH_STENCIL(vk, combined_fmt, d_fmt, s_fmt)  \
71    [VK_FORMAT_##vk] = {                                       \
72       .vk_format = VK_FORMAT_##vk,                            \
73       .tex_format = ROGUE_TEXSTATE_FORMAT_##combined_fmt,     \
74       .depth_tex_format = ROGUE_TEXSTATE_FORMAT_##d_fmt,      \
75       .stencil_tex_format = ROGUE_TEXSTATE_FORMAT_##s_fmt,    \
76       .pbe_packmode = ROGUE_PBESTATE_PACKMODE_##combined_fmt, \
77       .pbe_accum_format = PVR_PBE_ACCUM_FORMAT_INVALID,       \
78       .supported = true,                                      \
79    }
80 
81 struct pvr_format {
82    VkFormat vk_format;
83    uint32_t tex_format;
84    uint32_t depth_tex_format;
85    uint32_t stencil_tex_format;
86    uint32_t pbe_packmode;
87    enum pvr_pbe_accum_format pbe_accum_format;
88    bool supported;
89 };
90 
91 static const struct pvr_format pvr_format_table[] = {
92    /* VK_FORMAT_B4G4R4A4_UNORM_PACK16 = 3. */
93    FORMAT(B4G4R4A4_UNORM_PACK16, A4R4G4B4, A4R4G4B4, U8),
94    /* VK_FORMAT_R5G6B5_UNORM_PACK16 = 4. */
95    FORMAT(R5G6B5_UNORM_PACK16, R5G6B5, R5G6B5, U8),
96    /* VK_FORMAT_A1R5G5B5_UNORM_PACK16 = 8. */
97    FORMAT(A1R5G5B5_UNORM_PACK16, A1R5G5B5, A1R5G5B5, U8),
98    /* VK_FORMAT_R8_UNORM = 9. */
99    FORMAT(R8_UNORM, U8, U8, U8),
100    /* VK_FORMAT_R8_SNORM = 10. */
101    FORMAT(R8_SNORM, S8, S8, S8),
102    /* VK_FORMAT_R8_UINT = 13. */
103    FORMAT(R8_UINT, U8, U8, UINT8),
104    /* VK_FORMAT_R8_SINT = 14. */
105    FORMAT(R8_SINT, S8, S8, SINT8),
106    /* VK_FORMAT_R8G8_UNORM = 16. */
107    FORMAT(R8G8_UNORM, U8U8, U8U8, U8),
108    /* VK_FORMAT_R8G8_SNORM = 17. */
109    FORMAT(R8G8_SNORM, S8S8, S8S8, S8),
110    /* VK_FORMAT_R8G8_UINT = 20. */
111    FORMAT(R8G8_UINT, U8U8, U8U8, UINT8),
112    /* VK_FORMAT_R8G8_SINT = 21. */
113    FORMAT(R8G8_SINT, S8S8, S8S8, SINT8),
114    /* VK_FORMAT_R8G8B8A8_UNORM = 37. */
115    FORMAT(R8G8B8A8_UNORM, U8U8U8U8, U8U8U8U8, U8),
116    /* VK_FORMAT_R8G8B8A8_SNORM = 38. */
117    FORMAT(R8G8B8A8_SNORM, S8S8S8S8, S8S8S8S8, S8),
118    /* VK_FORMAT_R8G8B8A8_UINT = 41. */
119    FORMAT(R8G8B8A8_UINT, U8U8U8U8, U8U8U8U8, UINT8),
120    /* VK_FORMAT_R8G8B8A8_SINT = 42. */
121    FORMAT(R8G8B8A8_SINT, S8S8S8S8, S8S8S8S8, SINT8),
122    /* VK_FORMAT_R8G8B8A8_SRGB = 43. */
123    FORMAT(R8G8B8A8_SRGB, U8U8U8U8, U8U8U8U8, F16),
124    /* VK_FORMAT_B8G8R8A8_UNORM = 44. */
125    FORMAT(B8G8R8A8_UNORM, U8U8U8U8, U8U8U8U8, U8),
126    /* VK_FORMAT_B8G8R8A8_SRGB = 50. */
127    FORMAT(B8G8R8A8_SRGB, U8U8U8U8, U8U8U8U8, F16),
128    /* VK_FORMAT_A8B8G8R8_UNORM_PACK32 = 51. */
129    FORMAT(A8B8G8R8_UNORM_PACK32, U8U8U8U8, U8U8U8U8, U8),
130    /* VK_FORMAT_A8B8G8R8_SNORM_PACK32 = 52. */
131    FORMAT(A8B8G8R8_SNORM_PACK32, S8S8S8S8, S8S8S8S8, S8),
132    /* VK_FORMAT_A8B8G8R8_UINT_PACK32 = 55. */
133    FORMAT(A8B8G8R8_UINT_PACK32, U8U8U8U8, U8U8U8U8, UINT8),
134    /* VK_FORMAT_A8B8G8R8_SINT_PACK32 = 56. */
135    FORMAT(A8B8G8R8_SINT_PACK32, S8S8S8S8, S8S8S8S8, SINT8),
136    /* VK_FORMAT_A8B8G8R8_SRGB_PACK32 = 57. */
137    FORMAT(A8B8G8R8_SRGB_PACK32, U8U8U8U8, U8U8U8U8, F16),
138    /* VK_FORMAT_A2B10G10R10_UNORM_PACK32 = 64. */
139    FORMAT(A2B10G10R10_UNORM_PACK32, A2R10B10G10, A2R10B10G10, F16),
140    /* VK_FORMAT_A2B10G10R10_UINT_PACK32 = 68. */
141    FORMAT(A2B10G10R10_UINT_PACK32, A2R10B10G10, U32, U1010102),
142    /* VK_FORMAT_R16_UNORM = 70. */
143    FORMAT(R16_UNORM, U16, U16, U16),
144    /* VK_FORMAT_R16_SNORM = 71. */
145    FORMAT(R16_SNORM, S16, S16, S16),
146    /* VK_FORMAT_R16_UINT = 74. */
147    FORMAT(R16_UINT, U16, U16, UINT16),
148    /* VK_FORMAT_R16_SINT = 75. */
149    FORMAT(R16_SINT, S16, S16, SINT16),
150    /* VK_FORMAT_R16_SFLOAT = 76. */
151    FORMAT(R16_SFLOAT, F16, F16, F16),
152    /* VK_FORMAT_R16G16_UNORM = 77. */
153    FORMAT(R16G16_UNORM, U16U16, U16U16, U16),
154    /* VK_FORMAT_R16G16_SNORM = 78. */
155    FORMAT(R16G16_SNORM, S16S16, S16S16, S16),
156    /* VK_FORMAT_R16G16_UINT = 81. */
157    FORMAT(R16G16_UINT, U16U16, U16U16, UINT16),
158    /* VK_FORMAT_R16G16_SINT = 82. */
159    FORMAT(R16G16_SINT, S16S16, S16S16, SINT16),
160    /* VK_FORMAT_R16G16_SFLOAT = 83. */
161    FORMAT(R16G16_SFLOAT, F16F16, F16F16, F16),
162    /* VK_FORMAT_R16G16B16A16_UNORM = 91. */
163    FORMAT(R16G16B16A16_UNORM, U16U16U16U16, U16U16U16U16, U16),
164    /* VK_FORMAT_R16G16B16A16_SNORM = 92. */
165    FORMAT(R16G16B16A16_SNORM, S16S16S16S16, S16S16S16S16, S16),
166    /* VK_FORMAT_R16G16B16A16_UINT = 95. */
167    FORMAT(R16G16B16A16_UINT, U16U16U16U16, U16U16U16U16, UINT16),
168    /* VK_FORMAT_R16G16B16A16_SINT = 96 */
169    FORMAT(R16G16B16A16_SINT, S16S16S16S16, S16S16S16S16, SINT16),
170    /* VK_FORMAT_R16G16B16A16_SFLOAT = 97. */
171    FORMAT(R16G16B16A16_SFLOAT, F16F16F16F16, F16F16F16F16, F16),
172    /* VK_FORMAT_R32_UINT = 98. */
173    FORMAT(R32_UINT, U32, U32, UINT32),
174    /* VK_FORMAT_R32_SINT = 99. */
175    FORMAT(R32_SINT, S32, S32, SINT32),
176    /* VK_FORMAT_R32_SFLOAT = 100. */
177    FORMAT(R32_SFLOAT, F32, F32, F32),
178    /* VK_FORMAT_R32G32_UINT = 101. */
179    FORMAT(R32G32_UINT, U32U32, U32U32, UINT32),
180    /* VK_FORMAT_R32G32_SINT = 102. */
181    FORMAT(R32G32_SINT, S32S32, S32S32, SINT32),
182    /* VK_FORMAT_R32G32_SFLOAT = 103. */
183    FORMAT(R32G32_SFLOAT, F32F32, F32F32, F32),
184    /* VK_FORMAT_R32G32B32_UINT = 104. */
185    FORMAT(R32G32B32_UINT, U32U32U32, U32U32U32, UINT32),
186    /* VK_FORMAT_R32G32B32_SINT = 105. */
187    FORMAT(R32G32B32_SINT, S32S32S32, S32S32S32, SINT32),
188    /* VK_FORMAT_R32G32B32_SFLOAT = 106. */
189    FORMAT(R32G32B32_SFLOAT, F32F32F32, F32F32F32, F32),
190    /* VK_FORMAT_R32G32B32A32_UINT = 107. */
191    FORMAT(R32G32B32A32_UINT, U32U32U32U32, U32U32U32U32, UINT32),
192    /* VK_FORMAT_R32G32B32A32_SINT = 108. */
193    FORMAT(R32G32B32A32_SINT, S32S32S32S32, S32S32S32S32, SINT32),
194    /* VK_FORMAT_R32G32B32A32_SFLOAT = 109. */
195    FORMAT(R32G32B32A32_SFLOAT, F32F32F32F32, F32F32F32F32, F32),
196    /* VK_FORMAT_B10G11R11_UFLOAT_PACK32 = 122. */
197    FORMAT(B10G11R11_UFLOAT_PACK32, F10F11F11, F10F11F11, F16),
198    /* VK_FORMAT_E5B9G9R9_UFLOAT_PACK32 = 123. */
199    FORMAT(E5B9G9R9_UFLOAT_PACK32, SE9995, SE9995, INVALID),
200    /* VK_FORMAT_D16_UNORM = 124. */
201    FORMAT_DEPTH_STENCIL(D16_UNORM, U16, U16, INVALID),
202    /* VK_FORMAT_D32_SFLOAT = 126. */
203    FORMAT_DEPTH_STENCIL(D32_SFLOAT, F32, F32, INVALID),
204    /* VK_FORMAT_S8_UINT = 127. */
205    FORMAT_DEPTH_STENCIL(S8_UINT, U8, INVALID, U8),
206    /* VK_FORMAT_D24_UNORM_S8_UINT = 129. */
207    FORMAT_DEPTH_STENCIL(D24_UNORM_S8_UINT, ST8U24, X8U24, U8X24),
208    /* VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK = 147. */
209    FORMAT_COMPRESSED(ETC2_R8G8B8_UNORM_BLOCK, ETC2_RGB),
210    /* VK_FORMAT_ETC2_R8G8B8_SRGB_BLOCK = 148. */
211    FORMAT_COMPRESSED(ETC2_R8G8B8_SRGB_BLOCK, ETC2_RGB),
212    /* VK_FORMAT_ETC2_R8G8B8A1_UNORM_BLOCK = 149. */
213    FORMAT_COMPRESSED(ETC2_R8G8B8A1_UNORM_BLOCK, ETC2_PUNCHTHROUGHA),
214    /* VK_FORMAT_ETC2_R8G8B8A1_SRGB_BLOCK = 150. */
215    FORMAT_COMPRESSED(ETC2_R8G8B8A1_SRGB_BLOCK, ETC2_PUNCHTHROUGHA),
216    /* VK_FORMAT_ETC2_R8G8B8A8_UNORM_BLOCK = 150. */
217    FORMAT_COMPRESSED(ETC2_R8G8B8A8_UNORM_BLOCK, ETC2A_RGBA),
218    /* VK_FORMAT_ETC2_R8G8B8A8_SRGB_BLOCK = 152. */
219    FORMAT_COMPRESSED(ETC2_R8G8B8A8_SRGB_BLOCK, ETC2A_RGBA),
220    /* VK_FORMAT_EAC_R11_UNORM_BLOCK = 153. */
221    FORMAT_COMPRESSED(EAC_R11_UNORM_BLOCK, EAC_R11_UNSIGNED),
222    /* VK_FORMAT_EAC_R11_SNORM_BLOCK = 154. */
223    FORMAT_COMPRESSED(EAC_R11_SNORM_BLOCK, EAC_R11_SIGNED),
224    /* VK_FORMAT_EAC_R11G11_UNORM_BLOCK = 155. */
225    FORMAT_COMPRESSED(EAC_R11G11_UNORM_BLOCK, EAC_RG11_UNSIGNED),
226    /* VK_FORMAT_EAC_R11G11_SNORM_BLOCK = 156. */
227    FORMAT_COMPRESSED(EAC_R11G11_SNORM_BLOCK, EAC_RG11_SIGNED),
228 };
229 
230 #undef FORMAT
231 #undef FORMAT_DEPTH_STENCIL
232 #undef FORMAT_COMPRESSED
233 
234 #define FORMAT(tex_fmt, pipe_fmt_int, pipe_fmt_float) \
235    [ROGUE_TEXSTATE_FORMAT_##tex_fmt] = {                    \
236       .desc = {                                             \
237          .tex_format = ROGUE_TEXSTATE_FORMAT_##tex_fmt,     \
238          .pipe_format_int = PIPE_FORMAT_##pipe_fmt_int,     \
239          .pipe_format_float = PIPE_FORMAT_##pipe_fmt_float, \
240       },                                                    \
241       .present = true,                                      \
242    }
243 
244 static const struct pvr_tex_format_table_entry {
245    struct pvr_tex_format_description desc;
246    bool present;
247 } pvr_tex_format_table[PVR_TEX_FORMAT_COUNT] = {
248    /*   0 */ FORMAT(U8, R8_UINT, R8_UNORM),
249    /*   1 */ FORMAT(S8, R8_SINT, R8_SNORM),
250    /*   2 */ FORMAT(A4R4G4B4, NONE, A4R4G4B4_UNORM),
251    /*   4 */ FORMAT(A1R5G5B5, NONE, B5G5R5A1_UNORM),
252    /*   5 */ FORMAT(R5G6B5, NONE, B5G6R5_UNORM),
253    /*   7 */ FORMAT(U8U8, R8G8_UINT, R8G8_UNORM),
254    /*   8 */ FORMAT(S8S8, R8G8_SINT, R8G8_SNORM),
255    /*   9 */ FORMAT(U16, R16_UINT, R16_UNORM),
256    /*  10 */ FORMAT(S16, R16_SINT, R16_SNORM),
257    /*  11 */ FORMAT(F16, NONE, R16_FLOAT),
258    /*  12 */ FORMAT(U8U8U8U8, R8G8B8A8_UINT, R8G8B8A8_UNORM),
259    /*  13 */ FORMAT(S8S8S8S8, R8G8B8A8_SINT, R8G8B8A8_SNORM),
260    /*  14 */ FORMAT(A2R10B10G10, R10G10B10A2_UINT, R10G10B10A2_UNORM),
261    /*  15 */ FORMAT(U16U16, R16G16_UINT, R16G16_UNORM),
262    /*  16 */ FORMAT(S16S16, R16G16_SINT, R16G16_SNORM),
263    /*  17 */ FORMAT(F16F16, NONE, R16G16_FLOAT),
264    /*  18 */ FORMAT(F32, NONE, R32_FLOAT),
265    /*  22 */ FORMAT(ST8U24, Z24_UNORM_S8_UINT, Z24_UNORM_S8_UINT),
266    /*  24 */ FORMAT(U32, R32_UINT, NONE),
267    /*  25 */ FORMAT(S32, R32_SINT, NONE),
268    /*  26 */ FORMAT(SE9995, NONE, R9G9B9E5_FLOAT),
269    /*  28 */ FORMAT(F16F16F16F16, NONE, R16G16B16A16_FLOAT),
270    /*  29 */ FORMAT(U16U16U16U16, R16G16B16A16_UINT, R16G16B16A16_UNORM),
271    /*  30 */ FORMAT(S16S16S16S16, R16G16B16A16_SINT, R16G16B16A16_SNORM),
272    /*  34 */ FORMAT(F32F32, NONE, R32G32_FLOAT),
273    /*  35 */ FORMAT(U32U32, R32G32_UINT, NONE),
274    /*  36 */ FORMAT(S32S32, R32G32_SINT, NONE),
275    /*  61 */ FORMAT(F32F32F32F32, NONE, R32G32B32A32_FLOAT),
276    /*  62 */ FORMAT(U32U32U32U32, R32G32B32A32_UINT, NONE),
277    /*  63 */ FORMAT(S32S32S32S32, R32G32B32A32_SINT, NONE),
278    /*  64 */ FORMAT(F32F32F32, NONE, R32G32B32_FLOAT),
279    /*  65 */ FORMAT(U32U32U32, R32G32B32_UINT, NONE),
280    /*  66 */ FORMAT(S32S32S32, R32G32B32_SINT, NONE),
281    /*  88 */ FORMAT(F10F11F11, NONE, R11G11B10_FLOAT),
282 };
283 
284 #undef FORMAT
285 
286 #define FORMAT(tex_fmt, pipe_fmt, tex_fmt_simple) \
287    [ROGUE_TEXSTATE_FORMAT_COMPRESSED_##tex_fmt] = {                   \
288       .desc = {                                                       \
289          .tex_format = ROGUE_TEXSTATE_FORMAT_COMPRESSED_##tex_fmt,    \
290          .pipe_format = PIPE_FORMAT_##pipe_fmt,                       \
291          .tex_format_simple = ROGUE_TEXSTATE_FORMAT_##tex_fmt_simple, \
292       },                                                              \
293       .present = true,                                                \
294    }
295 
296 static const struct pvr_tex_format_compressed_table_entry {
297    struct pvr_tex_format_compressed_description desc;
298    bool present;
299 } pvr_tex_format_compressed_table[PVR_TEX_FORMAT_COUNT] = {
300    /*  68 */ FORMAT(ETC2_RGB, ETC2_RGB8, U8U8U8U8),
301    /*  69 */ FORMAT(ETC2A_RGBA, ETC2_RGBA8, U8U8U8U8),
302    /*  70 */ FORMAT(ETC2_PUNCHTHROUGHA, ETC2_RGB8A1, U8U8U8U8),
303    /*  71 */ FORMAT(EAC_R11_UNSIGNED, ETC2_R11_UNORM, U16U16U16U16),
304    /*  72 */ FORMAT(EAC_R11_SIGNED, ETC2_R11_SNORM, S16S16S16S16),
305    /*  73 */ FORMAT(EAC_RG11_UNSIGNED, ETC2_RG11_UNORM, U16U16U16U16),
306    /*  74 */ FORMAT(EAC_RG11_SIGNED, ETC2_RG11_SNORM, S16S16S16S16),
307 };
308 
309 #undef FORMAT
310 
pvr_get_format(VkFormat vk_format)311 static inline const struct pvr_format *pvr_get_format(VkFormat vk_format)
312 {
313    if (vk_format < ARRAY_SIZE(pvr_format_table) &&
314        pvr_format_table[vk_format].supported) {
315       return &pvr_format_table[vk_format];
316    }
317 
318    mesa_logd("Format %s(%d) not supported\n",
319              vk_Format_to_str(vk_format),
320              vk_format);
321 
322    return NULL;
323 }
324 
pvr_tex_format_is_supported(const uint32_t tex_format)325 bool pvr_tex_format_is_supported(const uint32_t tex_format)
326 {
327    return tex_format < ARRAY_SIZE(pvr_tex_format_table) &&
328           pvr_tex_format_table[tex_format].present;
329 }
330 
331 const struct pvr_tex_format_description *
pvr_get_tex_format_description(const uint32_t tex_format)332 pvr_get_tex_format_description(const uint32_t tex_format)
333 {
334    if (pvr_tex_format_is_supported(tex_format))
335       return &pvr_tex_format_table[tex_format].desc;
336 
337    mesa_logd("Tex format %s (%d) not supported\n",
338              ROGUE_TEXSTATE_FORMAT_to_str(tex_format),
339              tex_format);
340 
341    return NULL;
342 }
343 
pvr_tex_format_compressed_is_supported(uint32_t tex_format)344 bool pvr_tex_format_compressed_is_supported(uint32_t tex_format)
345 {
346    /* In some contexts, the sequence of compressed tex format ids are appended
347     * to the normal tex format ids; in that case, we need to remove that offset
348     * before lookup.
349     */
350    if (tex_format >= PVR_TEX_FORMAT_COUNT)
351       tex_format -= PVR_TEX_FORMAT_COUNT;
352 
353    return tex_format < ARRAY_SIZE(pvr_tex_format_compressed_table) &&
354           pvr_tex_format_compressed_table[tex_format].present;
355 }
356 
357 const struct pvr_tex_format_compressed_description *
pvr_get_tex_format_compressed_description(uint32_t tex_format)358 pvr_get_tex_format_compressed_description(uint32_t tex_format)
359 {
360    /* In some contexts, the sequence of compressed tex format ids are appended
361     * to the normal tex format ids; in that case, we need to remove that offset
362     * before lookup.
363     */
364    if (tex_format >= PVR_TEX_FORMAT_COUNT)
365       tex_format -= PVR_TEX_FORMAT_COUNT;
366 
367    if (pvr_tex_format_compressed_is_supported(tex_format))
368       return &pvr_tex_format_compressed_table[tex_format].desc;
369 
370    mesa_logd("Compressed tex format %s (%d) not supported\n",
371              ROGUE_TEXSTATE_FORMAT_COMPRESSED_to_str(tex_format),
372              tex_format);
373 
374    return NULL;
375 }
376 
pvr_get_tex_format(VkFormat vk_format)377 uint32_t pvr_get_tex_format(VkFormat vk_format)
378 {
379    const struct pvr_format *pvr_format = pvr_get_format(vk_format);
380    if (pvr_format) {
381       return pvr_format->tex_format;
382    }
383 
384    return ROGUE_TEXSTATE_FORMAT_INVALID;
385 }
386 
pvr_get_tex_format_aspect(VkFormat vk_format,VkImageAspectFlags aspect_mask)387 uint32_t pvr_get_tex_format_aspect(VkFormat vk_format,
388                                    VkImageAspectFlags aspect_mask)
389 {
390    const struct pvr_format *pvr_format = pvr_get_format(vk_format);
391    if (pvr_format) {
392       if (aspect_mask == VK_IMAGE_ASPECT_DEPTH_BIT)
393          return pvr_format->depth_tex_format;
394       else if (aspect_mask == VK_IMAGE_ASPECT_STENCIL_BIT)
395          return pvr_format->stencil_tex_format;
396 
397       return pvr_format->tex_format;
398    }
399 
400    return ROGUE_TEXSTATE_FORMAT_INVALID;
401 }
402 
pvr_get_pbe_packmode(VkFormat vk_format)403 uint32_t pvr_get_pbe_packmode(VkFormat vk_format)
404 {
405    const struct pvr_format *pvr_format = pvr_get_format(vk_format);
406    if (pvr_format)
407       return pvr_format->pbe_packmode;
408 
409    return ROGUE_PBESTATE_PACKMODE_INVALID;
410 }
411 
pvr_get_pbe_accum_format(VkFormat vk_format)412 uint32_t pvr_get_pbe_accum_format(VkFormat vk_format)
413 {
414    const struct pvr_format *pvr_format = pvr_get_format(vk_format);
415    if (pvr_format)
416       return pvr_format->pbe_accum_format;
417 
418    return PVR_PBE_ACCUM_FORMAT_INVALID;
419 }
420 
pvr_get_pbe_accum_format_size_in_bytes(VkFormat vk_format)421 uint32_t pvr_get_pbe_accum_format_size_in_bytes(VkFormat vk_format)
422 {
423    enum pvr_pbe_accum_format pbe_accum_format;
424    uint32_t nr_components;
425 
426    pbe_accum_format = pvr_get_pbe_accum_format(vk_format);
427    nr_components = vk_format_get_nr_components(vk_format);
428 
429    switch (pbe_accum_format) {
430    case PVR_PBE_ACCUM_FORMAT_U8:
431    case PVR_PBE_ACCUM_FORMAT_S8:
432    case PVR_PBE_ACCUM_FORMAT_UINT8:
433    case PVR_PBE_ACCUM_FORMAT_SINT8:
434       return nr_components * 1;
435 
436    case PVR_PBE_ACCUM_FORMAT_U16:
437    case PVR_PBE_ACCUM_FORMAT_S16:
438    case PVR_PBE_ACCUM_FORMAT_F16:
439    case PVR_PBE_ACCUM_FORMAT_UINT16:
440    case PVR_PBE_ACCUM_FORMAT_SINT16:
441       return nr_components * 2;
442 
443    case PVR_PBE_ACCUM_FORMAT_F32:
444    case PVR_PBE_ACCUM_FORMAT_UINT32:
445    case PVR_PBE_ACCUM_FORMAT_SINT32:
446    case PVR_PBE_ACCUM_FORMAT_UINT32_MEDP:
447    case PVR_PBE_ACCUM_FORMAT_SINT32_MEDP:
448    case PVR_PBE_ACCUM_FORMAT_U24:
449       return nr_components * 4;
450 
451    case PVR_PBE_ACCUM_FORMAT_U1010102:
452       assert(nr_components == 4);
453       return 4;
454 
455    default:
456       unreachable("Unknown pbe accum format. Implementation error");
457    }
458 }
459 
460 /**
461  * \brief Packs VK_FORMAT_A2B10G10R10_UINT_PACK32 or A2R10G10B10.
462  *
463  * \param[in] values   RGBA ordered values to pack.
464  * \param[in] swap_rb  If true pack A2B10G10R10 else pack A2R10G10B10.
465  */
pvr_pack_a2x10y10z10_uint(const uint32_t values[static const PVR_CLEAR_COLOR_ARRAY_SIZE],bool swap_rb)466 static inline uint32_t pvr_pack_a2x10y10z10_uint(
467    const uint32_t values[static const PVR_CLEAR_COLOR_ARRAY_SIZE],
468    bool swap_rb)
469 {
470    const uint32_t blue = swap_rb ? values[0] : values[2];
471    const uint32_t red = swap_rb ? values[2] : values[0];
472    uint32_t packed_val;
473 
474    /* The user is allowed to specify a value which is over the range
475     * representable for a component so we need to AND before packing.
476     */
477 
478    packed_val = util_bitpack_uint(values[3] & BITSET_MASK(2), 30, 31);
479    packed_val |= util_bitpack_uint(red & BITSET_MASK(10), 20, 29);
480    packed_val |= util_bitpack_uint(values[1] & BITSET_MASK(10), 10, 19);
481    packed_val |= util_bitpack_uint(blue & BITSET_MASK(10), 0, 9);
482 
483    return packed_val;
484 }
485 
486 #define APPLY_FUNC_4V(DST, FUNC, ARG) \
487    ASSIGN_4V(DST, FUNC(ARG[0]), FUNC(ARG[1]), FUNC(ARG[2]), FUNC(ARG[3]))
488 
489 #define f32_to_unorm8(val) _mesa_float_to_unorm(val, 8)
490 #define f32_to_unorm16(val) _mesa_float_to_unorm(val, 16)
491 #define f32_to_snorm8(val) _mesa_float_to_snorm(val, 8)
492 #define f32_to_snorm16(val) _mesa_float_to_snorm(val, 16)
493 #define f32_to_f16(val) _mesa_float_to_half(val)
494 
495 /**
496  * \brief Packs clear color input values into the appropriate accum format.
497  *
498  * The input value array must have zeroed out elements for components not
499  * present in the format. E.g. R8G8B8 has no A component so [3] must be 0.
500  *
501  * Note: the output is not swizzled so it's packed in RGBA order no matter the
502  * component order specified by the vk_format.
503  *
504  * \param[in] vk_format   Vulkan format of the input color value.
505  * \param[in] value       Unpacked RGBA input color values.
506  * \param[out] packed_out Accum format packed values.
507  */
pvr_get_hw_clear_color(VkFormat vk_format,VkClearColorValue value,uint32_t packed_out[static const PVR_CLEAR_COLOR_ARRAY_SIZE])508 void pvr_get_hw_clear_color(
509    VkFormat vk_format,
510    VkClearColorValue value,
511    uint32_t packed_out[static const PVR_CLEAR_COLOR_ARRAY_SIZE])
512 {
513    union {
514       uint32_t u32[PVR_CLEAR_COLOR_ARRAY_SIZE];
515       int32_t i32[PVR_CLEAR_COLOR_ARRAY_SIZE];
516       uint16_t u16[PVR_CLEAR_COLOR_ARRAY_SIZE * 2];
517       int16_t i16[PVR_CLEAR_COLOR_ARRAY_SIZE * 2];
518       uint8_t u8[PVR_CLEAR_COLOR_ARRAY_SIZE * 4];
519       int8_t i8[PVR_CLEAR_COLOR_ARRAY_SIZE * 4];
520    } packed_val = { 0 };
521 
522    const enum pvr_pbe_accum_format pbe_accum_format =
523       pvr_get_pbe_accum_format(vk_format);
524 
525    static_assert(ARRAY_SIZE(value.uint32) == PVR_CLEAR_COLOR_ARRAY_SIZE,
526                  "Size mismatch. Unknown/unhandled extra values.");
527 
528    /* TODO: Right now we pack all RGBA values. Would we get any benefit in
529     * packing just the components required by the format?
530     */
531 
532    switch (pbe_accum_format) {
533    case PVR_PBE_ACCUM_FORMAT_U8:
534       APPLY_FUNC_4V(packed_val.u8, f32_to_unorm8, value.float32);
535       break;
536    case PVR_PBE_ACCUM_FORMAT_S8:
537       APPLY_FUNC_4V(packed_val.i8, f32_to_snorm8, value.float32);
538       break;
539    case PVR_PBE_ACCUM_FORMAT_UINT8:
540       COPY_4V(packed_val.u8, value.uint32);
541       break;
542    case PVR_PBE_ACCUM_FORMAT_SINT8:
543       COPY_4V(packed_val.i8, value.int32);
544       break;
545 
546    case PVR_PBE_ACCUM_FORMAT_U16:
547       APPLY_FUNC_4V(packed_val.u16, f32_to_unorm16, value.float32);
548       break;
549    case PVR_PBE_ACCUM_FORMAT_S16:
550       APPLY_FUNC_4V(packed_val.i16, f32_to_snorm16, value.float32);
551       break;
552    case PVR_PBE_ACCUM_FORMAT_F16:
553       APPLY_FUNC_4V(packed_val.u16, f32_to_f16, value.float32);
554       break;
555    case PVR_PBE_ACCUM_FORMAT_UINT16:
556       COPY_4V(packed_val.u16, value.uint32);
557       break;
558    case PVR_PBE_ACCUM_FORMAT_SINT16:
559       COPY_4V(packed_val.i16, value.int32);
560       break;
561 
562    case PVR_PBE_ACCUM_FORMAT_U1010102:
563       /* The PBE can't handle swizzled 1010102 UINT. */
564       packed_val.u32[0] = pvr_pack_a2x10y10z10_uint(
565          value.uint32,
566          vk_format == VK_FORMAT_A2B10G10R10_UINT_PACK32);
567       break;
568 
569    case PVR_PBE_ACCUM_FORMAT_F32:
570       COPY_4V(packed_val.u32, value.uint32);
571       break;
572    case PVR_PBE_ACCUM_FORMAT_UINT32:
573       COPY_4V(packed_val.u32, value.uint32);
574       break;
575    case PVR_PBE_ACCUM_FORMAT_SINT32:
576       COPY_4V(packed_val.i32, value.int32);
577       break;
578 
579    default:
580       unreachable("Packing not supported for the accum format.");
581       break;
582    }
583 
584    COPY_4V(packed_out, packed_val.u32);
585 }
586 
587 #undef APPLY_FUNC_4V
588 #undef f32_to_unorm8
589 #undef f32_to_unorm16
590 #undef f32_to_snorm8
591 #undef f32_to_snorm16
592 #undef f32_to_f16
593 
594 static VkFormatFeatureFlags2
pvr_get_image_format_features2(const struct pvr_format * pvr_format,VkImageTiling vk_tiling)595 pvr_get_image_format_features2(const struct pvr_format *pvr_format,
596                                VkImageTiling vk_tiling)
597 {
598    VkFormatFeatureFlags2 flags = 0;
599    VkFormat vk_format;
600 
601    if (!pvr_format)
602       return 0;
603 
604    assert(pvr_format->supported);
605 
606    vk_format = pvr_format->vk_format;
607 
608    if (pvr_get_tex_format(vk_format) != ROGUE_TEXSTATE_FORMAT_INVALID) {
609       if (vk_tiling == VK_IMAGE_TILING_OPTIMAL) {
610          const uint32_t first_component_size =
611             vk_format_get_component_bits(vk_format,
612                                          UTIL_FORMAT_COLORSPACE_RGB,
613                                          0);
614 
615          flags |= VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_BIT |
616                   VK_FORMAT_FEATURE_2_BLIT_SRC_BIT;
617 
618          if (!vk_format_is_int(vk_format) &&
619              !vk_format_is_depth_or_stencil(vk_format) &&
620              (first_component_size < 32 ||
621               vk_format_is_block_compressed(vk_format))) {
622             flags |= VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_FILTER_LINEAR_BIT;
623          }
624       } else if (!vk_format_is_block_compressed(vk_format)) {
625          flags |= VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_BIT |
626                   VK_FORMAT_FEATURE_2_BLIT_SRC_BIT;
627       }
628    }
629 
630    if (pvr_get_pbe_accum_format(vk_format) != PVR_PBE_ACCUM_FORMAT_INVALID) {
631       if (vk_format_is_color(vk_format)) {
632          flags |= VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BIT |
633                   VK_FORMAT_FEATURE_2_BLIT_DST_BIT;
634 
635          if (!vk_format_is_int(vk_format)) {
636             flags |= VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BLEND_BIT;
637          }
638       }
639    } else if (vk_format_is_depth_or_stencil(vk_format)) {
640       flags |= VK_FORMAT_FEATURE_2_DEPTH_STENCIL_ATTACHMENT_BIT |
641                VK_FORMAT_FEATURE_2_BLIT_DST_BIT |
642                VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_DEPTH_COMPARISON_BIT;
643    }
644 
645    if (vk_tiling == VK_IMAGE_TILING_OPTIMAL) {
646       if (vk_format_is_color(vk_format) &&
647           vk_format_get_nr_components(vk_format) == 1 &&
648           vk_format_get_blocksizebits(vk_format) == 32 &&
649           vk_format_is_int(vk_format)) {
650          flags |= VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT |
651                   VK_FORMAT_FEATURE_2_STORAGE_IMAGE_ATOMIC_BIT;
652       }
653 
654       switch (vk_format) {
655       case VK_FORMAT_R8_UNORM:
656       case VK_FORMAT_R8_SNORM:
657       case VK_FORMAT_R8_UINT:
658       case VK_FORMAT_R8_SINT:
659       case VK_FORMAT_R8G8_UNORM:
660       case VK_FORMAT_R8G8_SNORM:
661       case VK_FORMAT_R8G8_UINT:
662       case VK_FORMAT_R8G8_SINT:
663       case VK_FORMAT_R8G8B8A8_UNORM:
664       case VK_FORMAT_R8G8B8A8_SNORM:
665       case VK_FORMAT_R8G8B8A8_UINT:
666       case VK_FORMAT_R8G8B8A8_SINT:
667       case VK_FORMAT_A2B10G10R10_UNORM_PACK32:
668       case VK_FORMAT_A2B10G10R10_UINT_PACK32:
669       case VK_FORMAT_R16_UNORM:
670       case VK_FORMAT_R16_SNORM:
671       case VK_FORMAT_R16_UINT:
672       case VK_FORMAT_R16_SINT:
673       case VK_FORMAT_R16_SFLOAT:
674       case VK_FORMAT_R16G16_UNORM:
675       case VK_FORMAT_R16G16_SNORM:
676       case VK_FORMAT_R16G16_UINT:
677       case VK_FORMAT_R16G16_SINT:
678       case VK_FORMAT_R16G16_SFLOAT:
679       case VK_FORMAT_R16G16B16A16_UNORM:
680       case VK_FORMAT_R16G16B16A16_SNORM:
681       case VK_FORMAT_R16G16B16A16_UINT:
682       case VK_FORMAT_R16G16B16A16_SINT:
683       case VK_FORMAT_R16G16B16A16_SFLOAT:
684       case VK_FORMAT_R32_SFLOAT:
685       case VK_FORMAT_R32G32_UINT:
686       case VK_FORMAT_R32G32_SINT:
687       case VK_FORMAT_R32G32_SFLOAT:
688       case VK_FORMAT_R32G32B32A32_UINT:
689       case VK_FORMAT_R32G32B32A32_SINT:
690       case VK_FORMAT_R32G32B32A32_SFLOAT:
691       case VK_FORMAT_B10G11R11_UFLOAT_PACK32:
692          flags |= VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT;
693          break;
694       default:
695          break;
696       }
697    }
698 
699    if (flags & VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT) {
700       flags |= VK_FORMAT_FEATURE_2_STORAGE_READ_WITHOUT_FORMAT_BIT |
701                VK_FORMAT_FEATURE_2_STORAGE_WRITE_WITHOUT_FORMAT_BIT;
702    }
703 
704    return flags;
705 }
706 
pvr_get_format_swizzle(VkFormat vk_format)707 const uint8_t *pvr_get_format_swizzle(VkFormat vk_format)
708 {
709    const struct util_format_description *vf = vk_format_description(vk_format);
710 
711    return vf->swizzle;
712 }
713 
714 static VkFormatFeatureFlags2
pvr_get_buffer_format_features2(const struct pvr_format * pvr_format)715 pvr_get_buffer_format_features2(const struct pvr_format *pvr_format)
716 {
717    const struct util_format_description *desc;
718    VkFormatFeatureFlags2 flags = 0;
719    VkFormat vk_format;
720 
721    if (!pvr_format)
722       return 0;
723 
724    assert(pvr_format->supported);
725 
726    vk_format = pvr_format->vk_format;
727 
728    if (!vk_format_is_color(vk_format))
729       return 0;
730 
731    desc = vk_format_description(vk_format);
732 
733    if (desc->layout == UTIL_FORMAT_LAYOUT_PLAIN &&
734        desc->colorspace == UTIL_FORMAT_COLORSPACE_RGB) {
735       flags |= VK_FORMAT_FEATURE_2_VERTEX_BUFFER_BIT;
736 
737       if (desc->is_array && vk_format != VK_FORMAT_R32G32B32_UINT &&
738           vk_format != VK_FORMAT_R32G32B32_SINT &&
739           vk_format != VK_FORMAT_R32G32B32_SFLOAT) {
740          flags |= VK_FORMAT_FEATURE_2_UNIFORM_TEXEL_BUFFER_BIT;
741       } else if (vk_format == VK_FORMAT_A2B10G10R10_UNORM_PACK32 ||
742                  vk_format == VK_FORMAT_A2B10G10R10_UINT_PACK32) {
743          flags |= VK_FORMAT_FEATURE_2_UNIFORM_TEXEL_BUFFER_BIT;
744       }
745    } else if (vk_format == VK_FORMAT_E5B9G9R9_UFLOAT_PACK32) {
746       flags |= VK_FORMAT_FEATURE_2_VERTEX_BUFFER_BIT;
747    }
748 
749    if (vk_format_is_color(vk_format) &&
750        vk_format_get_nr_components(vk_format) == 1 &&
751        vk_format_get_blocksizebits(vk_format) == 32 &&
752        vk_format_is_int(vk_format)) {
753       flags |= VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_BIT |
754                VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_ATOMIC_BIT;
755    }
756 
757    switch (vk_format) {
758    case VK_FORMAT_R8G8B8A8_UNORM:
759    case VK_FORMAT_R8G8B8A8_SNORM:
760    case VK_FORMAT_R8G8B8A8_UINT:
761    case VK_FORMAT_R8G8B8A8_SINT:
762    case VK_FORMAT_A8B8G8R8_UNORM_PACK32:
763    case VK_FORMAT_A8B8G8R8_SNORM_PACK32:
764    case VK_FORMAT_A8B8G8R8_UINT_PACK32:
765    case VK_FORMAT_A8B8G8R8_SINT_PACK32:
766    case VK_FORMAT_R16G16B16A16_UINT:
767    case VK_FORMAT_R16G16B16A16_SINT:
768    case VK_FORMAT_R16G16B16A16_SFLOAT:
769    case VK_FORMAT_R32_SFLOAT:
770    case VK_FORMAT_R32G32_UINT:
771    case VK_FORMAT_R32G32_SINT:
772    case VK_FORMAT_R32G32_SFLOAT:
773    case VK_FORMAT_R32G32B32A32_UINT:
774    case VK_FORMAT_R32G32B32A32_SINT:
775    case VK_FORMAT_R32G32B32A32_SFLOAT:
776       flags |= VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_BIT;
777       break;
778 
779    case VK_FORMAT_B10G11R11_UFLOAT_PACK32:
780       flags |= VK_FORMAT_FEATURE_2_UNIFORM_TEXEL_BUFFER_BIT;
781       break;
782 
783    default:
784       break;
785    }
786 
787    if (flags & VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_BIT) {
788       flags |= VK_FORMAT_FEATURE_2_STORAGE_READ_WITHOUT_FORMAT_BIT |
789                VK_FORMAT_FEATURE_2_STORAGE_WRITE_WITHOUT_FORMAT_BIT;
790    }
791 
792    return flags;
793 }
794 
pvr_GetPhysicalDeviceFormatProperties2(VkPhysicalDevice physicalDevice,VkFormat format,VkFormatProperties2 * pFormatProperties)795 void pvr_GetPhysicalDeviceFormatProperties2(
796    VkPhysicalDevice physicalDevice,
797    VkFormat format,
798    VkFormatProperties2 *pFormatProperties)
799 {
800    const struct pvr_format *pvr_format = pvr_get_format(format);
801    VkFormatFeatureFlags2 linear2, optimal2, buffer2;
802 
803    linear2 = pvr_get_image_format_features2(pvr_format, VK_IMAGE_TILING_LINEAR);
804    optimal2 =
805       pvr_get_image_format_features2(pvr_format, VK_IMAGE_TILING_OPTIMAL);
806    buffer2 = pvr_get_buffer_format_features2(pvr_format);
807 
808    pFormatProperties->formatProperties = (VkFormatProperties){
809       .linearTilingFeatures = vk_format_features2_to_features(linear2),
810       .optimalTilingFeatures = vk_format_features2_to_features(optimal2),
811       .bufferFeatures = vk_format_features2_to_features(buffer2),
812    };
813 
814    vk_foreach_struct (ext, pFormatProperties->pNext) {
815       switch (ext->sType) {
816       case VK_STRUCTURE_TYPE_FORMAT_PROPERTIES_3: {
817          VkFormatProperties3 *pFormatProperties3 = (VkFormatProperties3 *)ext;
818          pFormatProperties3->linearTilingFeatures = linear2;
819          pFormatProperties3->optimalTilingFeatures = optimal2;
820          pFormatProperties3->bufferFeatures = buffer2;
821          break;
822       }
823       default:
824          vk_debug_ignored_stype(ext->sType);
825          break;
826       }
827    }
828 }
829 
830 static VkResult
pvr_get_image_format_properties(struct pvr_physical_device * pdevice,const VkPhysicalDeviceImageFormatInfo2 * info,VkImageFormatProperties * pImageFormatProperties)831 pvr_get_image_format_properties(struct pvr_physical_device *pdevice,
832                                 const VkPhysicalDeviceImageFormatInfo2 *info,
833                                 VkImageFormatProperties *pImageFormatProperties)
834 {
835    /* Input attachments aren't rendered but they must have the same size
836     * restrictions as any framebuffer attachment.
837     */
838    const VkImageUsageFlags render_usage =
839       VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_STORAGE_BIT |
840       VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT |
841       VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT |
842       VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
843    const struct pvr_format *pvr_format = pvr_get_format(info->format);
844    VkFormatFeatureFlags2 tiling_features2;
845    VkResult result;
846 
847    if (!pvr_format) {
848       result = vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
849       goto err_unsupported_format;
850    }
851 
852    tiling_features2 = pvr_get_image_format_features2(pvr_format, info->tiling);
853    if (tiling_features2 == 0) {
854       result = vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
855       goto err_unsupported_format;
856    }
857 
858    if (info->flags & VK_IMAGE_CREATE_MUTABLE_FORMAT_BIT) {
859       result = vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
860       goto err_unsupported_format;
861    }
862 
863    /* If VK_IMAGE_CREATE_EXTENDED_USAGE_BIT is set, the driver can't decide if a
864     * specific format isn't supported based on the usage.
865     */
866    if ((info->flags & VK_IMAGE_CREATE_EXTENDED_USAGE_BIT) == 0 &&
867        info->usage & (VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT |
868                       VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT) &&
869        pvr_format->pbe_accum_format == PVR_PBE_ACCUM_FORMAT_INVALID) {
870       result = vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
871       goto err_unsupported_format;
872    }
873 
874    if (info->type == VK_IMAGE_TYPE_3D) {
875       const VkImageUsageFlags transfer_usage = VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
876                                                VK_IMAGE_USAGE_TRANSFER_DST_BIT;
877 
878       /* We don't support 3D depth/stencil images. */
879       if (tiling_features2 & VK_FORMAT_FEATURE_2_DEPTH_STENCIL_ATTACHMENT_BIT) {
880          result = vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
881          goto err_unsupported_format;
882       }
883 
884       /* Linear tiled 3D images may only be used for transfer or blit
885        * operations.
886        */
887       if (info->tiling == VK_IMAGE_TILING_LINEAR &&
888           info->usage & ~transfer_usage) {
889          result = vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
890          goto err_unsupported_format;
891       }
892 
893       /* Block compressed with 3D layout not supported */
894       if (vk_format_is_block_compressed(info->format)) {
895          result = vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
896          goto err_unsupported_format;
897       }
898    }
899 
900    if (info->usage & render_usage) {
901       const uint32_t max_render_size =
902          rogue_get_render_size_max(&pdevice->dev_info);
903 
904       pImageFormatProperties->maxExtent.width = max_render_size;
905       pImageFormatProperties->maxExtent.height = max_render_size;
906       pImageFormatProperties->maxExtent.depth = PVR_MAX_TEXTURE_EXTENT_Z;
907    } else {
908       const uint32_t max_texture_extent_xy =
909          ROGUE_TEXSTATE_IMAGE_WORD0_WIDTH_MAX_SIZE + 1U;
910 
911       pImageFormatProperties->maxExtent.width = max_texture_extent_xy;
912       pImageFormatProperties->maxExtent.height = max_texture_extent_xy;
913       pImageFormatProperties->maxExtent.depth = PVR_MAX_TEXTURE_EXTENT_Z;
914    }
915 
916    if (info->tiling == VK_IMAGE_TILING_LINEAR) {
917       pImageFormatProperties->maxExtent.depth = 1;
918       pImageFormatProperties->maxArrayLayers = 1;
919       pImageFormatProperties->sampleCounts = VK_SAMPLE_COUNT_1_BIT;
920    } else {
921       /* Default value is the minimum value found in all existing cores. */
922       const uint32_t max_multisample =
923          PVR_GET_FEATURE_VALUE(&pdevice->dev_info, max_multisample, 4);
924 
925       const uint32_t max_sample_bits = ((max_multisample << 1) - 1);
926 
927       pImageFormatProperties->maxArrayLayers = PVR_MAX_ARRAY_LAYERS;
928       pImageFormatProperties->sampleCounts = max_sample_bits;
929    }
930 
931    if (!(tiling_features2 & VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BIT ||
932          tiling_features2 & VK_FORMAT_FEATURE_2_DEPTH_STENCIL_ATTACHMENT_BIT)) {
933       pImageFormatProperties->sampleCounts = VK_SAMPLE_COUNT_1_BIT;
934    }
935 
936    switch (info->type) {
937    case VK_IMAGE_TYPE_1D:
938       pImageFormatProperties->maxExtent.height = 1;
939       pImageFormatProperties->maxExtent.depth = 1;
940       pImageFormatProperties->sampleCounts = VK_SAMPLE_COUNT_1_BIT;
941       break;
942 
943    case VK_IMAGE_TYPE_2D:
944       pImageFormatProperties->maxExtent.depth = 1;
945 
946       /* If a 2D image is created to be used in a cube map, then the sample
947        * count must be restricted to 1 sample.
948        */
949       if (info->flags & VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT)
950          pImageFormatProperties->sampleCounts = VK_SAMPLE_COUNT_1_BIT;
951 
952       break;
953 
954    case VK_IMAGE_TYPE_3D:
955       pImageFormatProperties->maxArrayLayers = 1;
956       pImageFormatProperties->sampleCounts = VK_SAMPLE_COUNT_1_BIT;
957       break;
958 
959    default:
960       unreachable("Invalid image type.");
961    }
962 
963    /* The spec says maxMipLevels may be 1 when tiling is VK_IMAGE_TILING_LINEAR
964     * or VK_IMAGE_TILING_DRM_FORMAT_MODIFIER_EXT, so for simplicity don't
965     * support miplevels for these tilings.
966     */
967    if (info->tiling == VK_IMAGE_TILING_LINEAR) {
968       pImageFormatProperties->maxMipLevels = 1;
969    } else {
970       const uint32_t max_size = MAX3(pImageFormatProperties->maxExtent.width,
971                                      pImageFormatProperties->maxExtent.height,
972                                      pImageFormatProperties->maxExtent.depth);
973 
974       pImageFormatProperties->maxMipLevels = util_logbase2(max_size) + 1U;
975    }
976 
977    /* Return 2GB (minimum required from spec).
978     *
979     * From the Vulkan spec:
980     *
981     *    maxResourceSize is an upper bound on the total image size in bytes,
982     *    inclusive of all image subresources. Implementations may have an
983     *    address space limit on total size of a resource, which is advertised by
984     *    this property. maxResourceSize must be at least 2^31.
985     */
986    pImageFormatProperties->maxResourceSize = 2ULL * 1024 * 1024 * 1024;
987 
988    return VK_SUCCESS;
989 
990 err_unsupported_format:
991    /* From the Vulkan 1.0.42 spec:
992     *
993     *    If the combination of parameters to
994     *    vkGetPhysicalDeviceImageFormatProperties2 is not supported by the
995     *    implementation for use in vkCreateImage, then all members of
996     *    imageFormatProperties will be filled with zero.
997     */
998    *pImageFormatProperties = (VkImageFormatProperties){ 0 };
999 
1000    return result;
1001 }
1002 
1003 /* FIXME: Should this be returning VK_ERROR_FORMAT_NOT_SUPPORTED when tiling is
1004  * linear and the image type is 3D or flags contains
1005  * VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT? This should avoid well behaved apps
1006  * attempting to create invalid image views, as pvr_pack_tex_state() will return
1007  * VK_ERROR_FORMAT_NOT_SUPPORTED in these cases.
1008  */
pvr_GetPhysicalDeviceImageFormatProperties2(VkPhysicalDevice physicalDevice,const VkPhysicalDeviceImageFormatInfo2 * pImageFormatInfo,VkImageFormatProperties2 * pImageFormatProperties)1009 VkResult pvr_GetPhysicalDeviceImageFormatProperties2(
1010    VkPhysicalDevice physicalDevice,
1011    const VkPhysicalDeviceImageFormatInfo2 *pImageFormatInfo,
1012    VkImageFormatProperties2 *pImageFormatProperties)
1013 {
1014    const VkPhysicalDeviceExternalImageFormatInfo *external_info = NULL;
1015    PVR_FROM_HANDLE(pvr_physical_device, pdevice, physicalDevice);
1016    VkExternalImageFormatProperties *external_props = NULL;
1017    VkResult result;
1018 
1019    result = pvr_get_image_format_properties(
1020       pdevice,
1021       pImageFormatInfo,
1022       &pImageFormatProperties->imageFormatProperties);
1023    if (result != VK_SUCCESS)
1024       return result;
1025 
1026    /* Extract input structs */
1027    vk_foreach_struct_const (ext, pImageFormatInfo->pNext) {
1028       switch (ext->sType) {
1029       case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTERNAL_IMAGE_FORMAT_INFO:
1030          external_info = (const void *)ext;
1031          break;
1032       case VK_STRUCTURE_TYPE_IMAGE_FORMAT_LIST_CREATE_INFO:
1033          break;
1034       default:
1035          vk_debug_ignored_stype(ext->sType);
1036          break;
1037       }
1038    }
1039 
1040    /* Extract output structs */
1041    vk_foreach_struct (ext, pImageFormatProperties->pNext) {
1042       switch (ext->sType) {
1043       case VK_STRUCTURE_TYPE_EXTERNAL_IMAGE_FORMAT_PROPERTIES:
1044          external_props = (void *)ext;
1045          break;
1046       default:
1047          vk_debug_ignored_stype(ext->sType);
1048          break;
1049       }
1050    }
1051 
1052    /* From the Vulkan 1.0.42 spec:
1053     *
1054     *    If handleType is 0, vkGetPhysicalDeviceImageFormatProperties2 will
1055     *    behave as if VkPhysicalDeviceExternalImageFormatInfo was not
1056     *    present and VkExternalImageFormatProperties will be ignored.
1057     */
1058    if (external_info && external_info->handleType != 0) {
1059       switch (external_info->handleType) {
1060       case VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT:
1061       case VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT:
1062          if (!external_props)
1063             break;
1064 
1065          external_props->externalMemoryProperties.externalMemoryFeatures =
1066             VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT |
1067             VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT;
1068          external_props->externalMemoryProperties.compatibleHandleTypes =
1069             VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT |
1070             VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
1071          external_props->externalMemoryProperties.exportFromImportedHandleTypes =
1072             VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT |
1073             VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
1074          break;
1075       default:
1076          return vk_error(pdevice, VK_ERROR_FORMAT_NOT_SUPPORTED);
1077       }
1078    }
1079 
1080    return VK_SUCCESS;
1081 }
1082 
pvr_GetPhysicalDeviceSparseImageFormatProperties(VkPhysicalDevice physicalDevice,VkFormat format,VkImageType type,VkSampleCountFlagBits samples,VkImageUsageFlags usage,VkImageTiling tiling,uint32_t * pNumProperties,VkSparseImageFormatProperties * pProperties)1083 void pvr_GetPhysicalDeviceSparseImageFormatProperties(
1084    VkPhysicalDevice physicalDevice,
1085    VkFormat format,
1086    VkImageType type,
1087    VkSampleCountFlagBits samples,
1088    VkImageUsageFlags usage,
1089    VkImageTiling tiling,
1090    uint32_t *pNumProperties,
1091    VkSparseImageFormatProperties *pProperties)
1092 {
1093    /* Sparse images are not yet supported. */
1094    *pNumProperties = 0;
1095 }
1096 
pvr_GetPhysicalDeviceSparseImageFormatProperties2(VkPhysicalDevice physicalDevice,const VkPhysicalDeviceSparseImageFormatInfo2 * pFormatInfo,uint32_t * pPropertyCount,VkSparseImageFormatProperties2 * pProperties)1097 void pvr_GetPhysicalDeviceSparseImageFormatProperties2(
1098    VkPhysicalDevice physicalDevice,
1099    const VkPhysicalDeviceSparseImageFormatInfo2 *pFormatInfo,
1100    uint32_t *pPropertyCount,
1101    VkSparseImageFormatProperties2 *pProperties)
1102 {
1103    /* Sparse images are not yet supported. */
1104    *pPropertyCount = 0;
1105 }
1106 
pvr_GetPhysicalDeviceExternalBufferProperties(VkPhysicalDevice physicalDevice,const VkPhysicalDeviceExternalBufferInfo * pExternalBufferInfo,VkExternalBufferProperties * pExternalBufferProperties)1107 void pvr_GetPhysicalDeviceExternalBufferProperties(
1108    VkPhysicalDevice physicalDevice,
1109    const VkPhysicalDeviceExternalBufferInfo *pExternalBufferInfo,
1110    VkExternalBufferProperties *pExternalBufferProperties)
1111 {
1112    /* The Vulkan 1.0.42 spec says "handleType must be a valid
1113     * VkExternalMemoryHandleTypeFlagBits value" in
1114     * VkPhysicalDeviceExternalBufferInfo. This differs from
1115     * VkPhysicalDeviceExternalImageFormatInfo, which surprisingly permits
1116     * handleType == 0.
1117     */
1118    assert(pExternalBufferInfo->handleType != 0);
1119 
1120    /* All of the current flags are for sparse which we don't support. */
1121    if (pExternalBufferInfo->flags)
1122       goto unsupported;
1123 
1124    switch (pExternalBufferInfo->handleType) {
1125    case VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT:
1126    case VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT:
1127       /* clang-format off */
1128       pExternalBufferProperties->externalMemoryProperties.externalMemoryFeatures =
1129          VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT |
1130          VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT;
1131       pExternalBufferProperties->externalMemoryProperties.exportFromImportedHandleTypes =
1132          VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT |
1133          VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
1134       pExternalBufferProperties->externalMemoryProperties.compatibleHandleTypes =
1135          VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_FD_BIT |
1136          VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
1137       /* clang-format on */
1138       return;
1139    default:
1140       break;
1141    }
1142 
1143 unsupported:
1144    /* From the Vulkan 1.1.113 spec:
1145     *
1146     *    compatibleHandleTypes must include at least handleType.
1147     */
1148    pExternalBufferProperties->externalMemoryProperties =
1149       (VkExternalMemoryProperties){
1150          .compatibleHandleTypes = pExternalBufferInfo->handleType,
1151       };
1152 }
1153 
pvr_format_is_pbe_downscalable(VkFormat vk_format)1154 bool pvr_format_is_pbe_downscalable(VkFormat vk_format)
1155 {
1156    if (vk_format_is_int(vk_format)) {
1157       /* PBE downscale behavior for integer formats does not match Vulkan
1158        * spec. Vulkan requires a single sample to be chosen instead of
1159        * taking the average sample color.
1160        */
1161       return false;
1162    }
1163 
1164    switch (pvr_get_pbe_packmode(vk_format)) {
1165    default:
1166       return true;
1167 
1168    case ROGUE_PBESTATE_PACKMODE_U16U16U16U16:
1169    case ROGUE_PBESTATE_PACKMODE_S16S16S16S16:
1170    case ROGUE_PBESTATE_PACKMODE_U32U32U32U32:
1171    case ROGUE_PBESTATE_PACKMODE_S32S32S32S32:
1172    case ROGUE_PBESTATE_PACKMODE_F32F32F32F32:
1173    case ROGUE_PBESTATE_PACKMODE_U16U16U16:
1174    case ROGUE_PBESTATE_PACKMODE_S16S16S16:
1175    case ROGUE_PBESTATE_PACKMODE_U32U32U32:
1176    case ROGUE_PBESTATE_PACKMODE_S32S32S32:
1177    case ROGUE_PBESTATE_PACKMODE_F32F32F32:
1178    case ROGUE_PBESTATE_PACKMODE_U16U16:
1179    case ROGUE_PBESTATE_PACKMODE_S16S16:
1180    case ROGUE_PBESTATE_PACKMODE_U32U32:
1181    case ROGUE_PBESTATE_PACKMODE_S32S32:
1182    case ROGUE_PBESTATE_PACKMODE_F32F32:
1183    case ROGUE_PBESTATE_PACKMODE_U24ST8:
1184    case ROGUE_PBESTATE_PACKMODE_ST8U24:
1185    case ROGUE_PBESTATE_PACKMODE_U16:
1186    case ROGUE_PBESTATE_PACKMODE_S16:
1187    case ROGUE_PBESTATE_PACKMODE_U32:
1188    case ROGUE_PBESTATE_PACKMODE_S32:
1189    case ROGUE_PBESTATE_PACKMODE_F32:
1190    case ROGUE_PBESTATE_PACKMODE_X24U8F32:
1191    case ROGUE_PBESTATE_PACKMODE_X24X8F32:
1192    case ROGUE_PBESTATE_PACKMODE_X24G8X32:
1193    case ROGUE_PBESTATE_PACKMODE_X8U24:
1194    case ROGUE_PBESTATE_PACKMODE_U8X24:
1195    case ROGUE_PBESTATE_PACKMODE_PBYTE:
1196    case ROGUE_PBESTATE_PACKMODE_PWORD:
1197    case ROGUE_PBESTATE_PACKMODE_INVALID:
1198       return false;
1199    }
1200 }
1201 
pvr_pbe_pixel_num_loads(enum pvr_transfer_pbe_pixel_src pbe_format)1202 uint32_t pvr_pbe_pixel_num_loads(enum pvr_transfer_pbe_pixel_src pbe_format)
1203 {
1204    switch (pbe_format) {
1205    case PVR_TRANSFER_PBE_PIXEL_SRC_UU8888:
1206    case PVR_TRANSFER_PBE_PIXEL_SRC_US8888:
1207    case PVR_TRANSFER_PBE_PIXEL_SRC_UU16U16:
1208    case PVR_TRANSFER_PBE_PIXEL_SRC_US16S16:
1209    case PVR_TRANSFER_PBE_PIXEL_SRC_SU8888:
1210    case PVR_TRANSFER_PBE_PIXEL_SRC_SS8888:
1211    case PVR_TRANSFER_PBE_PIXEL_SRC_SU16U16:
1212    case PVR_TRANSFER_PBE_PIXEL_SRC_SS16S16:
1213    case PVR_TRANSFER_PBE_PIXEL_SRC_UU1010102:
1214    case PVR_TRANSFER_PBE_PIXEL_SRC_SU1010102:
1215    case PVR_TRANSFER_PBE_PIXEL_SRC_RBSWAP_UU1010102:
1216    case PVR_TRANSFER_PBE_PIXEL_SRC_RBSWAP_SU1010102:
1217    case PVR_TRANSFER_PBE_PIXEL_SRC_SU32U32:
1218    case PVR_TRANSFER_PBE_PIXEL_SRC_S4XU32:
1219    case PVR_TRANSFER_PBE_PIXEL_SRC_US32S32:
1220    case PVR_TRANSFER_PBE_PIXEL_SRC_U4XS32:
1221    case PVR_TRANSFER_PBE_PIXEL_SRC_F16F16:
1222    case PVR_TRANSFER_PBE_PIXEL_SRC_U16NORM:
1223    case PVR_TRANSFER_PBE_PIXEL_SRC_S16NORM:
1224    case PVR_TRANSFER_PBE_PIXEL_SRC_F32:
1225    case PVR_TRANSFER_PBE_PIXEL_SRC_F32X2:
1226    case PVR_TRANSFER_PBE_PIXEL_SRC_F32X4:
1227    case PVR_TRANSFER_PBE_PIXEL_SRC_RAW32:
1228    case PVR_TRANSFER_PBE_PIXEL_SRC_RAW64:
1229    case PVR_TRANSFER_PBE_PIXEL_SRC_RAW128:
1230    case PVR_TRANSFER_PBE_PIXEL_SRC_F16_U8:
1231    case PVR_TRANSFER_PBE_PIXEL_SRC_SWAP_LMSB:
1232    case PVR_TRANSFER_PBE_PIXEL_SRC_MOV_BY45:
1233    case PVR_TRANSFER_PBE_PIXEL_SRC_D24S8:
1234    case PVR_TRANSFER_PBE_PIXEL_SRC_S8D24:
1235    case PVR_TRANSFER_PBE_PIXEL_SRC_D32S8:
1236 
1237    case PVR_TRANSFER_PBE_PIXEL_SRC_CONV_D24_D32:
1238    case PVR_TRANSFER_PBE_PIXEL_SRC_CONV_D32U_D32F:
1239    case PVR_TRANSFER_PBE_PIXEL_SRC_CONV_D32_D24S8:
1240    case PVR_TRANSFER_PBE_PIXEL_SRC_CONV_S8D24_D24S8:
1241    case PVR_TRANSFER_PBE_PIXEL_SRC_SMRG_S8_D32S8:
1242 
1243    case PVR_TRANSFER_PBE_PIXEL_SRC_SMRG_D24S8_D32S8:
1244    case PVR_TRANSFER_PBE_PIXEL_SRC_SMRG_D32S8_D32S8:
1245    case PVR_TRANSFER_PBE_PIXEL_SRC_DMRG_D32S8_D32S8:
1246    case PVR_TRANSFER_PBE_PIXEL_SRC_SMRG_S8_D24S8:
1247    case PVR_TRANSFER_PBE_PIXEL_SRC_SMRG_D24S8_D24S8:
1248    case PVR_TRANSFER_PBE_PIXEL_SRC_DMRG_D24S8_D24S8:
1249    case PVR_TRANSFER_PBE_PIXEL_SRC_DMRG_D32_D24S8:
1250    case PVR_TRANSFER_PBE_PIXEL_SRC_DMRG_D32U_D24S8:
1251    case PVR_TRANSFER_PBE_PIXEL_SRC_Y_UV_INTERLEAVED:
1252    case PVR_TRANSFER_PBE_PIXEL_SRC_Y_U_V:
1253    case PVR_TRANSFER_PBE_PIXEL_SRC_YUV_PACKED:
1254    case PVR_TRANSFER_PBE_PIXEL_SRC_YVU_PACKED:
1255       return 1U;
1256 
1257    case PVR_TRANSFER_PBE_PIXEL_SRC_NUM:
1258    default:
1259       return 0U;
1260    }
1261 }
1262