anv_image.c revision 01e04c3f
1/*
2 * Copyright © 2015 Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is 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
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
21 * IN THE SOFTWARE.
22 */
23
24#include <assert.h>
25#include <stdbool.h>
26#include <string.h>
27#include <unistd.h>
28#include <fcntl.h>
29#include <sys/mman.h>
30#include <drm_fourcc.h>
31
32#include "anv_private.h"
33#include "util/debug.h"
34#include "vk_util.h"
35#include "util/u_math.h"
36
37#include "vk_format_info.h"
38
39static isl_surf_usage_flags_t
40choose_isl_surf_usage(VkImageCreateFlags vk_create_flags,
41                      VkImageUsageFlags vk_usage,
42                      isl_surf_usage_flags_t isl_extra_usage,
43                      VkImageAspectFlagBits aspect)
44{
45   isl_surf_usage_flags_t isl_usage = isl_extra_usage;
46
47   if (vk_usage & VK_IMAGE_USAGE_SAMPLED_BIT)
48      isl_usage |= ISL_SURF_USAGE_TEXTURE_BIT;
49
50   if (vk_usage & VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT)
51      isl_usage |= ISL_SURF_USAGE_TEXTURE_BIT;
52
53   if (vk_usage & VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT)
54      isl_usage |= ISL_SURF_USAGE_RENDER_TARGET_BIT;
55
56   if (vk_create_flags & VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT)
57      isl_usage |= ISL_SURF_USAGE_CUBE_BIT;
58
59   /* Even if we're only using it for transfer operations, clears to depth and
60    * stencil images happen as depth and stencil so they need the right ISL
61    * usage bits or else things will fall apart.
62    */
63   switch (aspect) {
64   case VK_IMAGE_ASPECT_DEPTH_BIT:
65      isl_usage |= ISL_SURF_USAGE_DEPTH_BIT;
66      break;
67   case VK_IMAGE_ASPECT_STENCIL_BIT:
68      isl_usage |= ISL_SURF_USAGE_STENCIL_BIT;
69      break;
70   case VK_IMAGE_ASPECT_COLOR_BIT:
71   case VK_IMAGE_ASPECT_PLANE_0_BIT:
72   case VK_IMAGE_ASPECT_PLANE_1_BIT:
73   case VK_IMAGE_ASPECT_PLANE_2_BIT:
74      break;
75   default:
76      unreachable("bad VkImageAspect");
77   }
78
79   if (vk_usage & VK_IMAGE_USAGE_TRANSFER_SRC_BIT) {
80      /* blorp implements transfers by sampling from the source image. */
81      isl_usage |= ISL_SURF_USAGE_TEXTURE_BIT;
82   }
83
84   if (vk_usage & VK_IMAGE_USAGE_TRANSFER_DST_BIT &&
85       aspect == VK_IMAGE_ASPECT_COLOR_BIT) {
86      /* blorp implements transfers by rendering into the destination image.
87       * Only request this with color images, as we deal with depth/stencil
88       * formats differently. */
89      isl_usage |= ISL_SURF_USAGE_RENDER_TARGET_BIT;
90   }
91
92   return isl_usage;
93}
94
95static isl_tiling_flags_t
96choose_isl_tiling_flags(const struct anv_image_create_info *anv_info,
97                        const struct isl_drm_modifier_info *isl_mod_info,
98                        bool legacy_scanout)
99{
100   const VkImageCreateInfo *base_info = anv_info->vk_info;
101   isl_tiling_flags_t flags = 0;
102
103   switch (base_info->tiling) {
104   default:
105      unreachable("bad VkImageTiling");
106   case VK_IMAGE_TILING_OPTIMAL:
107      flags = ISL_TILING_ANY_MASK;
108      break;
109   case VK_IMAGE_TILING_LINEAR:
110      flags = ISL_TILING_LINEAR_BIT;
111      break;
112   }
113
114   if (anv_info->isl_tiling_flags)
115      flags &= anv_info->isl_tiling_flags;
116
117   if (legacy_scanout)
118      flags &= ISL_TILING_LINEAR_BIT | ISL_TILING_X_BIT;
119
120   if (isl_mod_info)
121      flags &= 1 << isl_mod_info->tiling;
122
123   assert(flags);
124
125   return flags;
126}
127
128static struct anv_surface *
129get_surface(struct anv_image *image, VkImageAspectFlagBits aspect)
130{
131   uint32_t plane = anv_image_aspect_to_plane(image->aspects, aspect);
132   return &image->planes[plane].surface;
133}
134
135static void
136add_surface(struct anv_image *image, struct anv_surface *surf, uint32_t plane)
137{
138   assert(surf->isl.size_B > 0); /* isl surface must be initialized */
139
140   if (image->disjoint) {
141      surf->offset = align_u32(image->planes[plane].size,
142                               surf->isl.alignment_B);
143      /* Plane offset is always 0 when it's disjoint. */
144   } else {
145      surf->offset = align_u32(image->size, surf->isl.alignment_B);
146      /* Determine plane's offset only once when the first surface is added. */
147      if (image->planes[plane].size == 0)
148         image->planes[plane].offset = image->size;
149   }
150
151   image->size = surf->offset + surf->isl.size_B;
152   image->planes[plane].size = (surf->offset + surf->isl.size_B) - image->planes[plane].offset;
153
154   image->alignment = MAX2(image->alignment, surf->isl.alignment_B);
155   image->planes[plane].alignment = MAX2(image->planes[plane].alignment,
156                                         surf->isl.alignment_B);
157}
158
159
160static bool
161all_formats_ccs_e_compatible(const struct gen_device_info *devinfo,
162                             const struct VkImageCreateInfo *vk_info)
163{
164   enum isl_format format =
165      anv_get_isl_format(devinfo, vk_info->format,
166                         VK_IMAGE_ASPECT_COLOR_BIT, vk_info->tiling);
167
168   if (!isl_format_supports_ccs_e(devinfo, format))
169      return false;
170
171   if (!(vk_info->flags & VK_IMAGE_CREATE_MUTABLE_FORMAT_BIT))
172      return true;
173
174   const VkImageFormatListCreateInfoKHR *fmt_list =
175      vk_find_struct_const(vk_info->pNext, IMAGE_FORMAT_LIST_CREATE_INFO_KHR);
176
177   if (!fmt_list || fmt_list->viewFormatCount == 0)
178      return false;
179
180   for (uint32_t i = 0; i < fmt_list->viewFormatCount; i++) {
181      enum isl_format view_format =
182         anv_get_isl_format(devinfo, fmt_list->pViewFormats[i],
183                            VK_IMAGE_ASPECT_COLOR_BIT, vk_info->tiling);
184
185      if (!isl_formats_are_ccs_e_compatible(devinfo, format, view_format))
186         return false;
187   }
188
189   return true;
190}
191
192/**
193 * For color images that have an auxiliary surface, request allocation for an
194 * additional buffer that mainly stores fast-clear values. Use of this buffer
195 * allows us to access the image's subresources while being aware of their
196 * fast-clear values in non-trivial cases (e.g., outside of a render pass in
197 * which a fast clear has occurred).
198 *
199 * In order to avoid having multiple clear colors for a single plane of an
200 * image (hence a single RENDER_SURFACE_STATE), we only allow fast-clears on
201 * the first slice (level 0, layer 0).  At the time of our testing (Jan 17,
202 * 2018), there were no known applications which would benefit from fast-
203 * clearing more than just the first slice.
204 *
205 * The fast clear portion of the image is laid out in the following order:
206 *
207 *  * 1 or 4 dwords (depending on hardware generation) for the clear color
208 *  * 1 dword for the anv_fast_clear_type of the clear color
209 *  * On gen9+, 1 dword per level and layer of the image (3D levels count
210 *    multiple layers) in level-major order for compression state.
211 *
212 * For the purpose of discoverability, the algorithm used to manage
213 * compression and fast-clears is described here:
214 *
215 *  * On a transition from UNDEFINED or PREINITIALIZED to a defined layout,
216 *    all of the values in the fast clear portion of the image are initialized
217 *    to default values.
218 *
219 *  * On fast-clear, the clear value is written into surface state and also
220 *    into the buffer and the fast clear type is set appropriately.  Both
221 *    setting the fast-clear value in the buffer and setting the fast-clear
222 *    type happen from the GPU using MI commands.
223 *
224 *  * Whenever a render or blorp operation is performed with CCS_E, we call
225 *    genX(cmd_buffer_mark_image_written) to set the compression state to
226 *    true (which is represented by UINT32_MAX).
227 *
228 *  * On pipeline barrier transitions, the worst-case transition is computed
229 *    from the image layouts.  The command streamer inspects the fast clear
230 *    type and compression state dwords and constructs a predicate.  The
231 *    worst-case resolve is performed with the given predicate and the fast
232 *    clear and compression state is set accordingly.
233 *
234 * See anv_layout_to_aux_usage and anv_layout_to_fast_clear_type functions for
235 * details on exactly what is allowed in what layouts.
236 *
237 * On gen7-9, we do not have a concept of indirect clear colors in hardware.
238 * In order to deal with this, we have to do some clear color management.
239 *
240 *  * For LOAD_OP_LOAD at the top of a renderpass, we have to copy the clear
241 *    value from the buffer into the surface state with MI commands.
242 *
243 *  * For any blorp operations, we pass the address to the clear value into
244 *    blorp and it knows to copy the clear color.
245 */
246static void
247add_aux_state_tracking_buffer(struct anv_image *image,
248                              VkImageAspectFlagBits aspect,
249                              uint32_t plane,
250                              const struct anv_device *device)
251{
252   assert(image && device);
253   assert(image->planes[plane].aux_surface.isl.size_B > 0 &&
254          image->aspects & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV);
255
256   /* Compressed images must be tiled and therefore everything should be 4K
257    * aligned.  The CCS has the same alignment requirements.  This is good
258    * because we need at least dword-alignment for MI_LOAD/STORE operations.
259    */
260   assert(image->alignment % 4 == 0);
261   assert((image->planes[plane].offset + image->planes[plane].size) % 4 == 0);
262
263   /* This buffer should be at the very end of the plane. */
264   if (image->disjoint) {
265      assert(image->planes[plane].size ==
266             (image->planes[plane].offset + image->planes[plane].size));
267   } else {
268      assert(image->size ==
269             (image->planes[plane].offset + image->planes[plane].size));
270   }
271
272   const unsigned clear_color_state_size = device->info.gen >= 10 ?
273      device->isl_dev.ss.clear_color_state_size :
274      device->isl_dev.ss.clear_value_size;
275
276   /* Clear color and fast clear type */
277   unsigned state_size = clear_color_state_size + 4;
278
279   /* We only need to track compression on CCS_E surfaces. */
280   if (image->planes[plane].aux_usage == ISL_AUX_USAGE_CCS_E) {
281      if (image->type == VK_IMAGE_TYPE_3D) {
282         for (uint32_t l = 0; l < image->levels; l++)
283            state_size += anv_minify(image->extent.depth, l) * 4;
284      } else {
285         state_size += image->levels * image->array_size * 4;
286      }
287   }
288
289   image->planes[plane].fast_clear_state_offset =
290      image->planes[plane].offset + image->planes[plane].size;
291
292   image->planes[plane].size += state_size;
293   image->size += state_size;
294}
295
296/**
297 * Initialize the anv_image::*_surface selected by \a aspect. Then update the
298 * image's memory requirements (that is, the image's size and alignment).
299 */
300static VkResult
301make_surface(const struct anv_device *dev,
302             struct anv_image *image,
303             const struct anv_image_create_info *anv_info,
304             isl_tiling_flags_t tiling_flags,
305             VkImageAspectFlagBits aspect)
306{
307   const VkImageCreateInfo *vk_info = anv_info->vk_info;
308   bool ok;
309
310   static const enum isl_surf_dim vk_to_isl_surf_dim[] = {
311      [VK_IMAGE_TYPE_1D] = ISL_SURF_DIM_1D,
312      [VK_IMAGE_TYPE_2D] = ISL_SURF_DIM_2D,
313      [VK_IMAGE_TYPE_3D] = ISL_SURF_DIM_3D,
314   };
315
316   image->extent = anv_sanitize_image_extent(vk_info->imageType,
317                                             vk_info->extent);
318
319   const unsigned plane = anv_image_aspect_to_plane(image->aspects, aspect);
320   const  struct anv_format_plane plane_format =
321      anv_get_format_plane(&dev->info, image->vk_format, aspect, image->tiling);
322   struct anv_surface *anv_surf = &image->planes[plane].surface;
323
324   const isl_surf_usage_flags_t usage =
325      choose_isl_surf_usage(vk_info->flags, image->usage,
326                            anv_info->isl_extra_usage_flags, aspect);
327
328   /* If an image is created as BLOCK_TEXEL_VIEW_COMPATIBLE, then we need to
329    * fall back to linear on Broadwell and earlier because we aren't
330    * guaranteed that we can handle offsets correctly.  On Sky Lake, the
331    * horizontal and vertical alignments are sufficiently high that we can
332    * just use RENDER_SURFACE_STATE::X/Y Offset.
333    */
334   bool needs_shadow = false;
335   if (dev->info.gen <= 8 &&
336       (vk_info->flags & VK_IMAGE_CREATE_BLOCK_TEXEL_VIEW_COMPATIBLE_BIT) &&
337       vk_info->tiling == VK_IMAGE_TILING_OPTIMAL) {
338      assert(isl_format_is_compressed(plane_format.isl_format));
339      tiling_flags = ISL_TILING_LINEAR_BIT;
340      needs_shadow = true;
341   }
342
343   ok = isl_surf_init(&dev->isl_dev, &anv_surf->isl,
344      .dim = vk_to_isl_surf_dim[vk_info->imageType],
345      .format = plane_format.isl_format,
346      .width = image->extent.width / plane_format.denominator_scales[0],
347      .height = image->extent.height / plane_format.denominator_scales[1],
348      .depth = image->extent.depth,
349      .levels = vk_info->mipLevels,
350      .array_len = vk_info->arrayLayers,
351      .samples = vk_info->samples,
352      .min_alignment_B = 0,
353      .row_pitch_B = anv_info->stride,
354      .usage = usage,
355      .tiling_flags = tiling_flags);
356
357   if (!ok)
358      return VK_ERROR_OUT_OF_DEVICE_MEMORY;
359
360   image->planes[plane].aux_usage = ISL_AUX_USAGE_NONE;
361
362   add_surface(image, anv_surf, plane);
363
364   /* If an image is created as BLOCK_TEXEL_VIEW_COMPATIBLE, then we need to
365    * create an identical tiled shadow surface for use while texturing so we
366    * don't get garbage performance.
367    */
368   if (needs_shadow) {
369      assert(aspect == VK_IMAGE_ASPECT_COLOR_BIT);
370      assert(tiling_flags == ISL_TILING_LINEAR_BIT);
371
372      ok = isl_surf_init(&dev->isl_dev, &image->planes[plane].shadow_surface.isl,
373         .dim = vk_to_isl_surf_dim[vk_info->imageType],
374         .format = plane_format.isl_format,
375         .width = image->extent.width,
376         .height = image->extent.height,
377         .depth = image->extent.depth,
378         .levels = vk_info->mipLevels,
379         .array_len = vk_info->arrayLayers,
380         .samples = vk_info->samples,
381         .min_alignment_B = 0,
382         .row_pitch_B = anv_info->stride,
383         .usage = usage,
384         .tiling_flags = ISL_TILING_ANY_MASK);
385
386      /* isl_surf_init() will fail only if provided invalid input. Invalid input
387       * is illegal in Vulkan.
388       */
389      assert(ok);
390
391      add_surface(image, &image->planes[plane].shadow_surface, plane);
392   }
393
394   /* Add a HiZ surface to a depth buffer that will be used for rendering.
395    */
396   if (aspect == VK_IMAGE_ASPECT_DEPTH_BIT) {
397      /* We don't advertise that depth buffers could be used as storage
398       * images.
399       */
400       assert(!(image->usage & VK_IMAGE_USAGE_STORAGE_BIT));
401
402      /* Allow the user to control HiZ enabling. Disable by default on gen7
403       * because resolves are not currently implemented pre-BDW.
404       */
405      if (!(image->usage & VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT)) {
406         /* It will never be used as an attachment, HiZ is pointless. */
407      } else if (dev->info.gen == 7) {
408         anv_perf_warn(dev->instance, image, "Implement gen7 HiZ");
409      } else if (vk_info->mipLevels > 1) {
410         anv_perf_warn(dev->instance, image, "Enable multi-LOD HiZ");
411      } else if (vk_info->arrayLayers > 1) {
412         anv_perf_warn(dev->instance, image,
413                       "Implement multi-arrayLayer HiZ clears and resolves");
414      } else if (dev->info.gen == 8 && vk_info->samples > 1) {
415         anv_perf_warn(dev->instance, image, "Enable gen8 multisampled HiZ");
416      } else if (!unlikely(INTEL_DEBUG & DEBUG_NO_HIZ)) {
417         assert(image->planes[plane].aux_surface.isl.size_B == 0);
418         ok = isl_surf_get_hiz_surf(&dev->isl_dev,
419                                    &image->planes[plane].surface.isl,
420                                    &image->planes[plane].aux_surface.isl);
421         assert(ok);
422         add_surface(image, &image->planes[plane].aux_surface, plane);
423         image->planes[plane].aux_usage = ISL_AUX_USAGE_HIZ;
424      }
425   } else if ((aspect & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV) && vk_info->samples == 1) {
426      /* TODO: Disallow compression with :
427       *
428       *     1) non multiplanar images (We appear to hit a sampler bug with
429       *        CCS & R16G16 format. Putting the clear state a page/4096bytes
430       *        further fixes the issue).
431       *
432       *     2) alias images, because they might be aliases of images
433       *        described in 1)
434       *
435       *     3) compression disabled by debug
436       */
437      const bool allow_compression =
438         image->n_planes == 1 &&
439         (vk_info->flags & VK_IMAGE_CREATE_ALIAS_BIT) == 0 &&
440         likely((INTEL_DEBUG & DEBUG_NO_RBC) == 0);
441
442      if (allow_compression) {
443         assert(image->planes[plane].aux_surface.isl.size_B == 0);
444         ok = isl_surf_get_ccs_surf(&dev->isl_dev,
445                                    &image->planes[plane].surface.isl,
446                                    &image->planes[plane].aux_surface.isl, 0);
447         if (ok) {
448
449            /* Disable CCS when it is not useful (i.e., when you can't render
450             * to the image with CCS enabled).
451             */
452            if (!isl_format_supports_rendering(&dev->info,
453                                               plane_format.isl_format)) {
454               /* While it may be technically possible to enable CCS for this
455                * image, we currently don't have things hooked up to get it
456                * working.
457                */
458               anv_perf_warn(dev->instance, image,
459                             "This image format doesn't support rendering. "
460                             "Not allocating an CCS buffer.");
461               image->planes[plane].aux_surface.isl.size_B = 0;
462               return VK_SUCCESS;
463            }
464
465            add_surface(image, &image->planes[plane].aux_surface, plane);
466            add_aux_state_tracking_buffer(image, aspect, plane, dev);
467
468            /* For images created without MUTABLE_FORMAT_BIT set, we know that
469             * they will always be used with the original format.  In
470             * particular, they will always be used with a format that
471             * supports color compression.  If it's never used as a storage
472             * image, then it will only be used through the sampler or the as
473             * a render target.  This means that it's safe to just leave
474             * compression on at all times for these formats.
475             */
476            if (!(vk_info->usage & VK_IMAGE_USAGE_STORAGE_BIT) &&
477                all_formats_ccs_e_compatible(&dev->info, vk_info)) {
478               image->planes[plane].aux_usage = ISL_AUX_USAGE_CCS_E;
479            }
480         }
481      }
482   } else if ((aspect & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV) && vk_info->samples > 1) {
483      assert(!(vk_info->usage & VK_IMAGE_USAGE_STORAGE_BIT));
484      assert(image->planes[plane].aux_surface.isl.size_B == 0);
485      ok = isl_surf_get_mcs_surf(&dev->isl_dev,
486                                 &image->planes[plane].surface.isl,
487                                 &image->planes[plane].aux_surface.isl);
488      if (ok) {
489         add_surface(image, &image->planes[plane].aux_surface, plane);
490         add_aux_state_tracking_buffer(image, aspect, plane, dev);
491         image->planes[plane].aux_usage = ISL_AUX_USAGE_MCS;
492      }
493   }
494
495   assert((image->planes[plane].offset + image->planes[plane].size) == image->size);
496
497   /* Upper bound of the last surface should be smaller than the plane's
498    * size.
499    */
500   assert((MAX2(image->planes[plane].surface.offset,
501                image->planes[plane].aux_surface.offset) +
502           (image->planes[plane].aux_surface.isl.size_B > 0 ?
503            image->planes[plane].aux_surface.isl.size_B :
504            image->planes[plane].surface.isl.size_B)) <=
505          (image->planes[plane].offset + image->planes[plane].size));
506
507   if (image->planes[plane].aux_surface.isl.size_B) {
508      /* assert(image->planes[plane].fast_clear_state_offset == */
509      /*        (image->planes[plane].aux_surface.offset + image->planes[plane].aux_surface.isl.size_B)); */
510      assert(image->planes[plane].fast_clear_state_offset <
511             (image->planes[plane].offset + image->planes[plane].size));
512   }
513
514   return VK_SUCCESS;
515}
516
517static uint32_t
518score_drm_format_mod(uint64_t modifier)
519{
520   switch (modifier) {
521   case DRM_FORMAT_MOD_LINEAR: return 1;
522   case I915_FORMAT_MOD_X_TILED: return 2;
523   case I915_FORMAT_MOD_Y_TILED: return 3;
524   case I915_FORMAT_MOD_Y_TILED_CCS: return 4;
525   default: unreachable("bad DRM format modifier");
526   }
527}
528
529static const struct isl_drm_modifier_info *
530choose_drm_format_mod(const struct anv_physical_device *device,
531                      uint32_t modifier_count, const uint64_t *modifiers)
532{
533   uint64_t best_mod = UINT64_MAX;
534   uint32_t best_score = 0;
535
536   for (uint32_t i = 0; i < modifier_count; ++i) {
537      uint32_t score = score_drm_format_mod(modifiers[i]);
538      if (score > best_score) {
539         best_mod = modifiers[i];
540         best_score = score;
541      }
542   }
543
544   if (best_score > 0)
545      return isl_drm_modifier_get_info(best_mod);
546   else
547      return NULL;
548}
549
550VkResult
551anv_image_create(VkDevice _device,
552                 const struct anv_image_create_info *create_info,
553                 const VkAllocationCallbacks* alloc,
554                 VkImage *pImage)
555{
556   ANV_FROM_HANDLE(anv_device, device, _device);
557   const VkImageCreateInfo *pCreateInfo = create_info->vk_info;
558   const struct isl_drm_modifier_info *isl_mod_info = NULL;
559   struct anv_image *image = NULL;
560   VkResult r;
561
562   assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO);
563
564   const struct wsi_image_create_info *wsi_info =
565      vk_find_struct_const(pCreateInfo->pNext, WSI_IMAGE_CREATE_INFO_MESA);
566   if (wsi_info && wsi_info->modifier_count > 0) {
567      isl_mod_info = choose_drm_format_mod(&device->instance->physicalDevice,
568                                           wsi_info->modifier_count,
569                                           wsi_info->modifiers);
570      assert(isl_mod_info);
571   }
572
573   anv_assert(pCreateInfo->mipLevels > 0);
574   anv_assert(pCreateInfo->arrayLayers > 0);
575   anv_assert(pCreateInfo->samples > 0);
576   anv_assert(pCreateInfo->extent.width > 0);
577   anv_assert(pCreateInfo->extent.height > 0);
578   anv_assert(pCreateInfo->extent.depth > 0);
579
580   image = vk_zalloc2(&device->alloc, alloc, sizeof(*image), 8,
581                       VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
582   if (!image)
583      return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
584
585   image->type = pCreateInfo->imageType;
586   image->extent = pCreateInfo->extent;
587   image->vk_format = pCreateInfo->format;
588   image->format = anv_get_format(pCreateInfo->format);
589   image->aspects = vk_format_aspects(image->vk_format);
590   image->levels = pCreateInfo->mipLevels;
591   image->array_size = pCreateInfo->arrayLayers;
592   image->samples = pCreateInfo->samples;
593   image->usage = pCreateInfo->usage;
594   image->tiling = pCreateInfo->tiling;
595   image->disjoint = pCreateInfo->flags & VK_IMAGE_CREATE_DISJOINT_BIT;
596   image->needs_set_tiling = wsi_info && wsi_info->scanout;
597   image->drm_format_mod = isl_mod_info ? isl_mod_info->modifier :
598                                          DRM_FORMAT_MOD_INVALID;
599
600   const struct anv_format *format = anv_get_format(image->vk_format);
601   assert(format != NULL);
602
603   const isl_tiling_flags_t isl_tiling_flags =
604      choose_isl_tiling_flags(create_info, isl_mod_info,
605                              image->needs_set_tiling);
606
607   image->n_planes = format->n_planes;
608
609   uint32_t b;
610   for_each_bit(b, image->aspects) {
611      r = make_surface(device, image, create_info, isl_tiling_flags,
612                       (1 << b));
613      if (r != VK_SUCCESS)
614         goto fail;
615   }
616
617   *pImage = anv_image_to_handle(image);
618
619   return VK_SUCCESS;
620
621fail:
622   if (image)
623      vk_free2(&device->alloc, alloc, image);
624
625   return r;
626}
627
628VkResult
629anv_CreateImage(VkDevice device,
630                const VkImageCreateInfo *pCreateInfo,
631                const VkAllocationCallbacks *pAllocator,
632                VkImage *pImage)
633{
634#ifdef ANDROID
635   const VkNativeBufferANDROID *gralloc_info =
636      vk_find_struct_const(pCreateInfo->pNext, NATIVE_BUFFER_ANDROID);
637
638   if (gralloc_info)
639      return anv_image_from_gralloc(device, pCreateInfo, gralloc_info,
640                                    pAllocator, pImage);
641#endif
642
643   return anv_image_create(device,
644      &(struct anv_image_create_info) {
645         .vk_info = pCreateInfo,
646      },
647      pAllocator,
648      pImage);
649}
650
651void
652anv_DestroyImage(VkDevice _device, VkImage _image,
653                 const VkAllocationCallbacks *pAllocator)
654{
655   ANV_FROM_HANDLE(anv_device, device, _device);
656   ANV_FROM_HANDLE(anv_image, image, _image);
657
658   if (!image)
659      return;
660
661   for (uint32_t p = 0; p < image->n_planes; ++p) {
662      if (image->planes[p].bo_is_owned) {
663         assert(image->planes[p].address.bo != NULL);
664         anv_bo_cache_release(device, &device->bo_cache,
665                              image->planes[p].address.bo);
666      }
667   }
668
669   vk_free2(&device->alloc, pAllocator, image);
670}
671
672static void anv_image_bind_memory_plane(struct anv_device *device,
673                                        struct anv_image *image,
674                                        uint32_t plane,
675                                        struct anv_device_memory *memory,
676                                        uint32_t memory_offset)
677{
678   assert(!image->planes[plane].bo_is_owned);
679
680   if (!memory) {
681      image->planes[plane].address = ANV_NULL_ADDRESS;
682      return;
683   }
684
685   image->planes[plane].address = (struct anv_address) {
686      .bo = memory->bo,
687      .offset = memory_offset,
688   };
689}
690
691VkResult anv_BindImageMemory(
692    VkDevice                                    _device,
693    VkImage                                     _image,
694    VkDeviceMemory                              _memory,
695    VkDeviceSize                                memoryOffset)
696{
697   ANV_FROM_HANDLE(anv_device, device, _device);
698   ANV_FROM_HANDLE(anv_device_memory, mem, _memory);
699   ANV_FROM_HANDLE(anv_image, image, _image);
700
701   uint32_t aspect_bit;
702   anv_foreach_image_aspect_bit(aspect_bit, image, image->aspects) {
703      uint32_t plane =
704         anv_image_aspect_to_plane(image->aspects, 1UL << aspect_bit);
705      anv_image_bind_memory_plane(device, image, plane, mem, memoryOffset);
706   }
707
708   return VK_SUCCESS;
709}
710
711VkResult anv_BindImageMemory2(
712    VkDevice                                    _device,
713    uint32_t                                    bindInfoCount,
714    const VkBindImageMemoryInfo*                pBindInfos)
715{
716   ANV_FROM_HANDLE(anv_device, device, _device);
717
718   for (uint32_t i = 0; i < bindInfoCount; i++) {
719      const VkBindImageMemoryInfo *bind_info = &pBindInfos[i];
720      ANV_FROM_HANDLE(anv_device_memory, mem, bind_info->memory);
721      ANV_FROM_HANDLE(anv_image, image, bind_info->image);
722      VkImageAspectFlags aspects = image->aspects;
723
724      vk_foreach_struct_const(s, bind_info->pNext) {
725         switch (s->sType) {
726         case VK_STRUCTURE_TYPE_BIND_IMAGE_PLANE_MEMORY_INFO: {
727            const VkBindImagePlaneMemoryInfo *plane_info =
728               (const VkBindImagePlaneMemoryInfo *) s;
729
730            aspects = plane_info->planeAspect;
731            break;
732         }
733         default:
734            anv_debug_ignored_stype(s->sType);
735            break;
736         }
737      }
738
739      uint32_t aspect_bit;
740      anv_foreach_image_aspect_bit(aspect_bit, image, aspects) {
741         uint32_t plane =
742            anv_image_aspect_to_plane(image->aspects, 1UL << aspect_bit);
743         anv_image_bind_memory_plane(device, image, plane,
744                                     mem, bind_info->memoryOffset);
745      }
746   }
747
748   return VK_SUCCESS;
749}
750
751void anv_GetImageSubresourceLayout(
752    VkDevice                                    device,
753    VkImage                                     _image,
754    const VkImageSubresource*                   subresource,
755    VkSubresourceLayout*                        layout)
756{
757   ANV_FROM_HANDLE(anv_image, image, _image);
758
759   const struct anv_surface *surface;
760   if (subresource->aspectMask == VK_IMAGE_ASPECT_PLANE_1_BIT_KHR &&
761       image->drm_format_mod != DRM_FORMAT_MOD_INVALID &&
762       isl_drm_modifier_has_aux(image->drm_format_mod))
763      surface = &image->planes[0].aux_surface;
764   else
765      surface = get_surface(image, subresource->aspectMask);
766
767   assert(__builtin_popcount(subresource->aspectMask) == 1);
768
769   layout->offset = surface->offset;
770   layout->rowPitch = surface->isl.row_pitch_B;
771   layout->depthPitch = isl_surf_get_array_pitch(&surface->isl);
772   layout->arrayPitch = isl_surf_get_array_pitch(&surface->isl);
773
774   if (subresource->mipLevel > 0 || subresource->arrayLayer > 0) {
775      assert(surface->isl.tiling == ISL_TILING_LINEAR);
776
777      uint32_t offset_B;
778      isl_surf_get_image_offset_B_tile_sa(&surface->isl,
779                                          subresource->mipLevel,
780                                          subresource->arrayLayer,
781                                          0 /* logical_z_offset_px */,
782                                          &offset_B, NULL, NULL);
783      layout->offset += offset_B;
784      layout->size = layout->rowPitch * anv_minify(image->extent.height,
785                                                   subresource->mipLevel);
786   } else {
787      layout->size = surface->isl.size_B;
788   }
789}
790
791/**
792 * This function determines the optimal buffer to use for a given
793 * VkImageLayout and other pieces of information needed to make that
794 * determination. This does not determine the optimal buffer to use
795 * during a resolve operation.
796 *
797 * @param devinfo The device information of the Intel GPU.
798 * @param image The image that may contain a collection of buffers.
799 * @param aspect The aspect of the image to be accessed.
800 * @param layout The current layout of the image aspect(s).
801 *
802 * @return The primary buffer that should be used for the given layout.
803 */
804enum isl_aux_usage
805anv_layout_to_aux_usage(const struct gen_device_info * const devinfo,
806                        const struct anv_image * const image,
807                        const VkImageAspectFlagBits aspect,
808                        const VkImageLayout layout)
809{
810   /* Validate the inputs. */
811
812   /* The devinfo is needed as the optimal buffer varies across generations. */
813   assert(devinfo != NULL);
814
815   /* The layout of a NULL image is not properly defined. */
816   assert(image != NULL);
817
818   /* The aspect must be exactly one of the image aspects. */
819   assert(util_bitcount(aspect) == 1 && (aspect & image->aspects));
820
821   /* Determine the optimal buffer. */
822
823   uint32_t plane = anv_image_aspect_to_plane(image->aspects, aspect);
824
825   /* If there is no auxiliary surface allocated, we must use the one and only
826    * main buffer.
827    */
828   if (image->planes[plane].aux_surface.isl.size_B == 0)
829      return ISL_AUX_USAGE_NONE;
830
831   /* All images that use an auxiliary surface are required to be tiled. */
832   assert(image->tiling == VK_IMAGE_TILING_OPTIMAL);
833
834   /* Stencil has no aux */
835   assert(aspect != VK_IMAGE_ASPECT_STENCIL_BIT);
836
837   switch (layout) {
838
839   /* Invalid Layouts */
840   case VK_IMAGE_LAYOUT_RANGE_SIZE:
841   case VK_IMAGE_LAYOUT_MAX_ENUM:
842      unreachable("Invalid image layout.");
843
844   /* Undefined layouts
845    *
846    * The pre-initialized layout is equivalent to the undefined layout for
847    * optimally-tiled images.  We can only do color compression (CCS or HiZ)
848    * on tiled images.
849    */
850   case VK_IMAGE_LAYOUT_UNDEFINED:
851   case VK_IMAGE_LAYOUT_PREINITIALIZED:
852      return ISL_AUX_USAGE_NONE;
853
854
855   /* Transfer Layouts
856    */
857   case VK_IMAGE_LAYOUT_GENERAL:
858   case VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL:
859   case VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL:
860      if (aspect == VK_IMAGE_ASPECT_DEPTH_BIT) {
861         /* This buffer could be a depth buffer used in a transfer operation.
862          * BLORP currently doesn't use HiZ for transfer operations so we must
863          * use the main buffer for this layout. TODO: Enable HiZ in BLORP.
864          */
865         assert(image->planes[plane].aux_usage == ISL_AUX_USAGE_HIZ);
866         return ISL_AUX_USAGE_NONE;
867      } else {
868         assert(image->aspects & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV);
869         return image->planes[plane].aux_usage;
870      }
871
872
873   /* Sampling Layouts */
874   case VK_IMAGE_LAYOUT_DEPTH_STENCIL_READ_ONLY_OPTIMAL:
875   case VK_IMAGE_LAYOUT_DEPTH_READ_ONLY_STENCIL_ATTACHMENT_OPTIMAL:
876      assert((image->aspects & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV) == 0);
877      /* Fall-through */
878   case VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL:
879      if (aspect == VK_IMAGE_ASPECT_DEPTH_BIT) {
880         if (anv_can_sample_with_hiz(devinfo, image))
881            return ISL_AUX_USAGE_HIZ;
882         else
883            return ISL_AUX_USAGE_NONE;
884      } else {
885         return image->planes[plane].aux_usage;
886      }
887
888
889   case VK_IMAGE_LAYOUT_PRESENT_SRC_KHR: {
890      assert(image->aspects == VK_IMAGE_ASPECT_COLOR_BIT);
891
892      /* When handing the image off to the presentation engine, we need to
893       * ensure that things are properly resolved.  For images with no
894       * modifier, we assume that they follow the old rules and always need
895       * a full resolve because the PE doesn't understand any form of
896       * compression.  For images with modifiers, we use the aux usage from
897       * the modifier.
898       */
899      const struct isl_drm_modifier_info *mod_info =
900         isl_drm_modifier_get_info(image->drm_format_mod);
901      return mod_info ? mod_info->aux_usage : ISL_AUX_USAGE_NONE;
902   }
903
904
905   /* Rendering Layouts */
906   case VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL:
907      assert(aspect & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV);
908      if (image->planes[plane].aux_usage == ISL_AUX_USAGE_NONE) {
909         assert(image->samples == 1);
910         return ISL_AUX_USAGE_CCS_D;
911      } else {
912         assert(image->planes[plane].aux_usage != ISL_AUX_USAGE_CCS_D);
913         return image->planes[plane].aux_usage;
914      }
915
916   case VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL:
917   case VK_IMAGE_LAYOUT_DEPTH_ATTACHMENT_STENCIL_READ_ONLY_OPTIMAL:
918      assert(aspect == VK_IMAGE_ASPECT_DEPTH_BIT);
919      return ISL_AUX_USAGE_HIZ;
920
921   case VK_IMAGE_LAYOUT_SHARED_PRESENT_KHR:
922      unreachable("VK_KHR_shared_presentable_image is unsupported");
923
924   case VK_IMAGE_LAYOUT_SHADING_RATE_OPTIMAL_NV:
925      unreachable("VK_NV_shading_rate_image is unsupported");
926   }
927
928   /* If the layout isn't recognized in the exhaustive switch above, the
929    * VkImageLayout value is not defined in vulkan.h.
930    */
931   unreachable("layout is not a VkImageLayout enumeration member.");
932}
933
934/**
935 * This function returns the level of unresolved fast-clear support of the
936 * given image in the given VkImageLayout.
937 *
938 * @param devinfo The device information of the Intel GPU.
939 * @param image The image that may contain a collection of buffers.
940 * @param aspect The aspect of the image to be accessed.
941 * @param layout The current layout of the image aspect(s).
942 */
943enum anv_fast_clear_type
944anv_layout_to_fast_clear_type(const struct gen_device_info * const devinfo,
945                              const struct anv_image * const image,
946                              const VkImageAspectFlagBits aspect,
947                              const VkImageLayout layout)
948{
949   /* The aspect must be exactly one of the image aspects. */
950   assert(util_bitcount(aspect) == 1 && (aspect & image->aspects));
951
952   uint32_t plane = anv_image_aspect_to_plane(image->aspects, aspect);
953
954   /* If there is no auxiliary surface allocated, there are no fast-clears */
955   if (image->planes[plane].aux_surface.isl.size_B == 0)
956      return ANV_FAST_CLEAR_NONE;
957
958   /* All images that use an auxiliary surface are required to be tiled. */
959   assert(image->tiling == VK_IMAGE_TILING_OPTIMAL);
960
961   /* Stencil has no aux */
962   assert(aspect != VK_IMAGE_ASPECT_STENCIL_BIT);
963
964   if (aspect == VK_IMAGE_ASPECT_DEPTH_BIT) {
965      /* For depth images (with HiZ), the layout supports fast-clears if and
966       * only if it supports HiZ.  However, we only support fast-clears to the
967       * default depth value.
968       */
969      enum isl_aux_usage aux_usage =
970         anv_layout_to_aux_usage(devinfo, image, aspect, layout);
971      return aux_usage == ISL_AUX_USAGE_HIZ ?
972             ANV_FAST_CLEAR_DEFAULT_VALUE : ANV_FAST_CLEAR_NONE;
973   }
974
975   assert(image->aspects & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV);
976
977   /* We don't support MSAA fast-clears on Ivybridge or Bay Trail because they
978    * lack the MI ALU which we need to determine the predicates.
979    */
980   if (devinfo->gen == 7 && !devinfo->is_haswell && image->samples > 1)
981      return ANV_FAST_CLEAR_NONE;
982
983   switch (layout) {
984   case VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL:
985      return ANV_FAST_CLEAR_ANY;
986
987   case VK_IMAGE_LAYOUT_PRESENT_SRC_KHR: {
988      assert(image->aspects == VK_IMAGE_ASPECT_COLOR_BIT);
989#ifndef NDEBUG
990      /* We do not yet support any modifiers which support clear color so we
991       * just always return NONE.  One day, this will change.
992       */
993      const struct isl_drm_modifier_info *mod_info =
994         isl_drm_modifier_get_info(image->drm_format_mod);
995      assert(!mod_info || !mod_info->supports_clear_color);
996#endif
997      return ANV_FAST_CLEAR_NONE;
998   }
999
1000   default:
1001      /* If the image has MCS or CCS_E enabled all the time then we can use
1002       * fast-clear as long as the clear color is the default value of zero
1003       * since this is the default value we program into every surface state
1004       * used for texturing.
1005       */
1006      if (image->planes[plane].aux_usage == ISL_AUX_USAGE_MCS ||
1007          image->planes[plane].aux_usage == ISL_AUX_USAGE_CCS_E)
1008         return ANV_FAST_CLEAR_DEFAULT_VALUE;
1009      else
1010         return ANV_FAST_CLEAR_NONE;
1011   }
1012}
1013
1014
1015static struct anv_state
1016alloc_surface_state(struct anv_device *device)
1017{
1018   return anv_state_pool_alloc(&device->surface_state_pool, 64, 64);
1019}
1020
1021static enum isl_channel_select
1022remap_swizzle(VkComponentSwizzle swizzle, VkComponentSwizzle component,
1023              struct isl_swizzle format_swizzle)
1024{
1025   if (swizzle == VK_COMPONENT_SWIZZLE_IDENTITY)
1026      swizzle = component;
1027
1028   switch (swizzle) {
1029   case VK_COMPONENT_SWIZZLE_ZERO:  return ISL_CHANNEL_SELECT_ZERO;
1030   case VK_COMPONENT_SWIZZLE_ONE:   return ISL_CHANNEL_SELECT_ONE;
1031   case VK_COMPONENT_SWIZZLE_R:     return format_swizzle.r;
1032   case VK_COMPONENT_SWIZZLE_G:     return format_swizzle.g;
1033   case VK_COMPONENT_SWIZZLE_B:     return format_swizzle.b;
1034   case VK_COMPONENT_SWIZZLE_A:     return format_swizzle.a;
1035   default:
1036      unreachable("Invalid swizzle");
1037   }
1038}
1039
1040void
1041anv_image_fill_surface_state(struct anv_device *device,
1042                             const struct anv_image *image,
1043                             VkImageAspectFlagBits aspect,
1044                             const struct isl_view *view_in,
1045                             isl_surf_usage_flags_t view_usage,
1046                             enum isl_aux_usage aux_usage,
1047                             const union isl_color_value *clear_color,
1048                             enum anv_image_view_state_flags flags,
1049                             struct anv_surface_state *state_inout,
1050                             struct brw_image_param *image_param_out)
1051{
1052   uint32_t plane = anv_image_aspect_to_plane(image->aspects, aspect);
1053
1054   const struct anv_surface *surface = &image->planes[plane].surface,
1055      *aux_surface = &image->planes[plane].aux_surface;
1056
1057   struct isl_view view = *view_in;
1058   view.usage |= view_usage;
1059
1060   /* For texturing with VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL from a
1061    * compressed surface with a shadow surface, we use the shadow instead of
1062    * the primary surface.  The shadow surface will be tiled, unlike the main
1063    * surface, so it should get significantly better performance.
1064    */
1065   if (image->planes[plane].shadow_surface.isl.size_B > 0 &&
1066       isl_format_is_compressed(view.format) &&
1067       (flags & ANV_IMAGE_VIEW_STATE_TEXTURE_OPTIMAL)) {
1068      assert(isl_format_is_compressed(surface->isl.format));
1069      assert(surface->isl.tiling == ISL_TILING_LINEAR);
1070      assert(image->planes[plane].shadow_surface.isl.tiling != ISL_TILING_LINEAR);
1071      surface = &image->planes[plane].shadow_surface;
1072   }
1073
1074   if (view_usage == ISL_SURF_USAGE_RENDER_TARGET_BIT)
1075      view.swizzle = anv_swizzle_for_render(view.swizzle);
1076
1077   /* If this is a HiZ buffer we can sample from with a programmable clear
1078    * value (SKL+), define the clear value to the optimal constant.
1079    */
1080   union isl_color_value default_clear_color = { .u32 = { 0, } };
1081   if (device->info.gen >= 9 && aux_usage == ISL_AUX_USAGE_HIZ)
1082      default_clear_color.f32[0] = ANV_HZ_FC_VAL;
1083   if (!clear_color)
1084      clear_color = &default_clear_color;
1085
1086   const struct anv_address address =
1087      anv_address_add(image->planes[plane].address, surface->offset);
1088
1089   if (view_usage == ISL_SURF_USAGE_STORAGE_BIT &&
1090       !(flags & ANV_IMAGE_VIEW_STATE_STORAGE_WRITE_ONLY) &&
1091       !isl_has_matching_typed_storage_image_format(&device->info,
1092                                                    view.format)) {
1093      /* In this case, we are a writeable storage buffer which needs to be
1094       * lowered to linear. All tiling and offset calculations will be done in
1095       * the shader.
1096       */
1097      assert(aux_usage == ISL_AUX_USAGE_NONE);
1098      isl_buffer_fill_state(&device->isl_dev, state_inout->state.map,
1099                            .address = anv_address_physical(address),
1100                            .size_B = surface->isl.size_B,
1101                            .format = ISL_FORMAT_RAW,
1102                            .stride_B = 1,
1103                            .mocs = anv_mocs_for_bo(device, address.bo));
1104      state_inout->address = address,
1105      state_inout->aux_address = ANV_NULL_ADDRESS;
1106      state_inout->clear_address = ANV_NULL_ADDRESS;
1107   } else {
1108      if (view_usage == ISL_SURF_USAGE_STORAGE_BIT &&
1109          !(flags & ANV_IMAGE_VIEW_STATE_STORAGE_WRITE_ONLY)) {
1110         /* Typed surface reads support a very limited subset of the shader
1111          * image formats.  Translate it into the closest format the hardware
1112          * supports.
1113          */
1114         assert(aux_usage == ISL_AUX_USAGE_NONE);
1115         view.format = isl_lower_storage_image_format(&device->info,
1116                                                      view.format);
1117      }
1118
1119      const struct isl_surf *isl_surf = &surface->isl;
1120
1121      struct isl_surf tmp_surf;
1122      uint32_t offset_B = 0, tile_x_sa = 0, tile_y_sa = 0;
1123      if (isl_format_is_compressed(surface->isl.format) &&
1124          !isl_format_is_compressed(view.format)) {
1125         /* We're creating an uncompressed view of a compressed surface.  This
1126          * is allowed but only for a single level/layer.
1127          */
1128         assert(surface->isl.samples == 1);
1129         assert(view.levels == 1);
1130         assert(view.array_len == 1);
1131
1132         isl_surf_get_image_surf(&device->isl_dev, isl_surf,
1133                                 view.base_level,
1134                                 surface->isl.dim == ISL_SURF_DIM_3D ?
1135                                    0 : view.base_array_layer,
1136                                 surface->isl.dim == ISL_SURF_DIM_3D ?
1137                                    view.base_array_layer : 0,
1138                                 &tmp_surf,
1139                                 &offset_B, &tile_x_sa, &tile_y_sa);
1140
1141         /* The newly created image represents the one subimage we're
1142          * referencing with this view so it only has one array slice and
1143          * miplevel.
1144          */
1145         view.base_array_layer = 0;
1146         view.base_level = 0;
1147
1148         /* We're making an uncompressed view here.  The image dimensions need
1149          * to be scaled down by the block size.
1150          */
1151         const struct isl_format_layout *fmtl =
1152            isl_format_get_layout(surface->isl.format);
1153         tmp_surf.format = view.format;
1154         tmp_surf.logical_level0_px.width =
1155            DIV_ROUND_UP(tmp_surf.logical_level0_px.width, fmtl->bw);
1156         tmp_surf.logical_level0_px.height =
1157            DIV_ROUND_UP(tmp_surf.logical_level0_px.height, fmtl->bh);
1158         tmp_surf.phys_level0_sa.width /= fmtl->bw;
1159         tmp_surf.phys_level0_sa.height /= fmtl->bh;
1160         tile_x_sa /= fmtl->bw;
1161         tile_y_sa /= fmtl->bh;
1162
1163         isl_surf = &tmp_surf;
1164
1165         if (device->info.gen <= 8) {
1166            assert(surface->isl.tiling == ISL_TILING_LINEAR);
1167            assert(tile_x_sa == 0);
1168            assert(tile_y_sa == 0);
1169         }
1170      }
1171
1172      state_inout->address = anv_address_add(address, offset_B);
1173
1174      struct anv_address aux_address = ANV_NULL_ADDRESS;
1175      if (aux_usage != ISL_AUX_USAGE_NONE) {
1176         aux_address = anv_address_add(image->planes[plane].address,
1177                                       aux_surface->offset);
1178      }
1179      state_inout->aux_address = aux_address;
1180
1181      struct anv_address clear_address = ANV_NULL_ADDRESS;
1182      if (device->info.gen >= 10 && aux_usage != ISL_AUX_USAGE_NONE) {
1183         if (aux_usage == ISL_AUX_USAGE_HIZ) {
1184            clear_address = (struct anv_address) {
1185               .bo = &device->hiz_clear_bo,
1186               .offset = 0,
1187            };
1188         } else {
1189            clear_address = anv_image_get_clear_color_addr(device, image, aspect);
1190         }
1191      }
1192      state_inout->clear_address = clear_address;
1193
1194      isl_surf_fill_state(&device->isl_dev, state_inout->state.map,
1195                          .surf = isl_surf,
1196                          .view = &view,
1197                          .address = anv_address_physical(state_inout->address),
1198                          .clear_color = *clear_color,
1199                          .aux_surf = &aux_surface->isl,
1200                          .aux_usage = aux_usage,
1201                          .aux_address = anv_address_physical(aux_address),
1202                          .clear_address = anv_address_physical(clear_address),
1203                          .use_clear_address = !anv_address_is_null(clear_address),
1204                          .mocs = anv_mocs_for_bo(device,
1205                                                  state_inout->address.bo),
1206                          .x_offset_sa = tile_x_sa,
1207                          .y_offset_sa = tile_y_sa);
1208
1209      /* With the exception of gen8, the bottom 12 bits of the MCS base address
1210       * are used to store other information.  This should be ok, however,
1211       * because the surface buffer addresses are always 4K page aligned.
1212       */
1213      uint32_t *aux_addr_dw = state_inout->state.map +
1214         device->isl_dev.ss.aux_addr_offset;
1215      assert((aux_address.offset & 0xfff) == 0);
1216      state_inout->aux_address.offset |= *aux_addr_dw & 0xfff;
1217
1218      if (device->info.gen >= 10 && clear_address.bo) {
1219         uint32_t *clear_addr_dw = state_inout->state.map +
1220                                   device->isl_dev.ss.clear_color_state_offset;
1221         assert((clear_address.offset & 0x3f) == 0);
1222         state_inout->clear_address.offset |= *clear_addr_dw & 0x3f;
1223      }
1224   }
1225
1226   anv_state_flush(device, state_inout->state);
1227
1228   if (image_param_out) {
1229      assert(view_usage == ISL_SURF_USAGE_STORAGE_BIT);
1230      isl_surf_fill_image_param(&device->isl_dev, image_param_out,
1231                                &surface->isl, &view);
1232   }
1233}
1234
1235static VkImageAspectFlags
1236remap_aspect_flags(VkImageAspectFlags view_aspects)
1237{
1238   if (view_aspects & VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV) {
1239      if (util_bitcount(view_aspects) == 1)
1240         return VK_IMAGE_ASPECT_COLOR_BIT;
1241
1242      VkImageAspectFlags color_aspects = 0;
1243      for (uint32_t i = 0; i < util_bitcount(view_aspects); i++)
1244         color_aspects |= VK_IMAGE_ASPECT_PLANE_0_BIT << i;
1245      return color_aspects;
1246   }
1247   /* No special remapping needed for depth & stencil aspects. */
1248   return view_aspects;
1249}
1250
1251VkResult
1252anv_CreateImageView(VkDevice _device,
1253                    const VkImageViewCreateInfo *pCreateInfo,
1254                    const VkAllocationCallbacks *pAllocator,
1255                    VkImageView *pView)
1256{
1257   ANV_FROM_HANDLE(anv_device, device, _device);
1258   ANV_FROM_HANDLE(anv_image, image, pCreateInfo->image);
1259   struct anv_image_view *iview;
1260
1261   iview = vk_zalloc2(&device->alloc, pAllocator, sizeof(*iview), 8,
1262                      VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
1263   if (iview == NULL)
1264      return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1265
1266   const VkImageSubresourceRange *range = &pCreateInfo->subresourceRange;
1267
1268   assert(range->layerCount > 0);
1269   assert(range->baseMipLevel < image->levels);
1270
1271   const VkImageViewUsageCreateInfo *usage_info =
1272      vk_find_struct_const(pCreateInfo, IMAGE_VIEW_USAGE_CREATE_INFO);
1273   VkImageUsageFlags view_usage = usage_info ? usage_info->usage : image->usage;
1274   /* View usage should be a subset of image usage */
1275   assert((view_usage & ~image->usage) == 0);
1276   assert(view_usage & (VK_IMAGE_USAGE_SAMPLED_BIT |
1277                        VK_IMAGE_USAGE_STORAGE_BIT |
1278                        VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT |
1279                        VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT |
1280                        VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT));
1281
1282   switch (image->type) {
1283   default:
1284      unreachable("bad VkImageType");
1285   case VK_IMAGE_TYPE_1D:
1286   case VK_IMAGE_TYPE_2D:
1287      assert(range->baseArrayLayer + anv_get_layerCount(image, range) - 1 <= image->array_size);
1288      break;
1289   case VK_IMAGE_TYPE_3D:
1290      assert(range->baseArrayLayer + anv_get_layerCount(image, range) - 1
1291             <= anv_minify(image->extent.depth, range->baseMipLevel));
1292      break;
1293   }
1294
1295   /* First expand aspects to the image's ones (for example
1296    * VK_IMAGE_ASPECT_COLOR_BIT will be converted to
1297    * VK_IMAGE_ASPECT_PLANE_0_BIT | VK_IMAGE_ASPECT_PLANE_1_BIT |
1298    * VK_IMAGE_ASPECT_PLANE_2_BIT for an image of format
1299    * VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM_KHR.
1300    */
1301   VkImageAspectFlags expanded_aspects =
1302      anv_image_expand_aspects(image, range->aspectMask);
1303
1304   iview->image = image;
1305
1306   /* Remap the expanded aspects for the image view. For example if only
1307    * VK_IMAGE_ASPECT_PLANE_1_BIT was given in range->aspectMask, we will
1308    * convert it to VK_IMAGE_ASPECT_COLOR_BIT since from the point of view of
1309    * the image view, it only has a single plane.
1310    */
1311   iview->aspect_mask = remap_aspect_flags(expanded_aspects);
1312   iview->n_planes = anv_image_aspect_get_planes(iview->aspect_mask);
1313   iview->vk_format = pCreateInfo->format;
1314
1315   iview->extent = (VkExtent3D) {
1316      .width  = anv_minify(image->extent.width , range->baseMipLevel),
1317      .height = anv_minify(image->extent.height, range->baseMipLevel),
1318      .depth  = anv_minify(image->extent.depth , range->baseMipLevel),
1319   };
1320
1321   /* Now go through the underlying image selected planes (computed in
1322    * expanded_aspects) and map them to planes in the image view.
1323    */
1324   uint32_t iaspect_bit, vplane = 0;
1325   anv_foreach_image_aspect_bit(iaspect_bit, image, expanded_aspects) {
1326      uint32_t iplane =
1327         anv_image_aspect_to_plane(expanded_aspects, 1UL << iaspect_bit);
1328      VkImageAspectFlags vplane_aspect =
1329         anv_plane_to_aspect(iview->aspect_mask, vplane);
1330      struct anv_format_plane format =
1331         anv_get_format_plane(&device->info, pCreateInfo->format,
1332                              vplane_aspect, image->tiling);
1333
1334      iview->planes[vplane].image_plane = iplane;
1335
1336      iview->planes[vplane].isl = (struct isl_view) {
1337         .format = format.isl_format,
1338         .base_level = range->baseMipLevel,
1339         .levels = anv_get_levelCount(image, range),
1340         .base_array_layer = range->baseArrayLayer,
1341         .array_len = anv_get_layerCount(image, range),
1342         .swizzle = {
1343            .r = remap_swizzle(pCreateInfo->components.r,
1344                               VK_COMPONENT_SWIZZLE_R, format.swizzle),
1345            .g = remap_swizzle(pCreateInfo->components.g,
1346                               VK_COMPONENT_SWIZZLE_G, format.swizzle),
1347            .b = remap_swizzle(pCreateInfo->components.b,
1348                               VK_COMPONENT_SWIZZLE_B, format.swizzle),
1349            .a = remap_swizzle(pCreateInfo->components.a,
1350                               VK_COMPONENT_SWIZZLE_A, format.swizzle),
1351         },
1352      };
1353
1354      if (pCreateInfo->viewType == VK_IMAGE_VIEW_TYPE_3D) {
1355         iview->planes[vplane].isl.base_array_layer = 0;
1356         iview->planes[vplane].isl.array_len = iview->extent.depth;
1357      }
1358
1359      if (pCreateInfo->viewType == VK_IMAGE_VIEW_TYPE_CUBE ||
1360          pCreateInfo->viewType == VK_IMAGE_VIEW_TYPE_CUBE_ARRAY) {
1361         iview->planes[vplane].isl.usage = ISL_SURF_USAGE_CUBE_BIT;
1362      } else {
1363         iview->planes[vplane].isl.usage = 0;
1364      }
1365
1366      if (view_usage & VK_IMAGE_USAGE_SAMPLED_BIT ||
1367          (view_usage & VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT &&
1368           !(iview->aspect_mask & VK_IMAGE_ASPECT_COLOR_BIT))) {
1369         iview->planes[vplane].optimal_sampler_surface_state.state = alloc_surface_state(device);
1370         iview->planes[vplane].general_sampler_surface_state.state = alloc_surface_state(device);
1371
1372         enum isl_aux_usage general_aux_usage =
1373            anv_layout_to_aux_usage(&device->info, image, 1UL << iaspect_bit,
1374                                    VK_IMAGE_LAYOUT_GENERAL);
1375         enum isl_aux_usage optimal_aux_usage =
1376            anv_layout_to_aux_usage(&device->info, image, 1UL << iaspect_bit,
1377                                    VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
1378
1379         anv_image_fill_surface_state(device, image, 1ULL << iaspect_bit,
1380                                      &iview->planes[vplane].isl,
1381                                      ISL_SURF_USAGE_TEXTURE_BIT,
1382                                      optimal_aux_usage, NULL,
1383                                      ANV_IMAGE_VIEW_STATE_TEXTURE_OPTIMAL,
1384                                      &iview->planes[vplane].optimal_sampler_surface_state,
1385                                      NULL);
1386
1387         anv_image_fill_surface_state(device, image, 1ULL << iaspect_bit,
1388                                      &iview->planes[vplane].isl,
1389                                      ISL_SURF_USAGE_TEXTURE_BIT,
1390                                      general_aux_usage, NULL,
1391                                      0,
1392                                      &iview->planes[vplane].general_sampler_surface_state,
1393                                      NULL);
1394      }
1395
1396      /* NOTE: This one needs to go last since it may stomp isl_view.format */
1397      if (view_usage & VK_IMAGE_USAGE_STORAGE_BIT) {
1398         iview->planes[vplane].storage_surface_state.state = alloc_surface_state(device);
1399         iview->planes[vplane].writeonly_storage_surface_state.state = alloc_surface_state(device);
1400
1401         anv_image_fill_surface_state(device, image, 1ULL << iaspect_bit,
1402                                      &iview->planes[vplane].isl,
1403                                      ISL_SURF_USAGE_STORAGE_BIT,
1404                                      ISL_AUX_USAGE_NONE, NULL,
1405                                      0,
1406                                      &iview->planes[vplane].storage_surface_state,
1407                                      &iview->planes[vplane].storage_image_param);
1408
1409         anv_image_fill_surface_state(device, image, 1ULL << iaspect_bit,
1410                                      &iview->planes[vplane].isl,
1411                                      ISL_SURF_USAGE_STORAGE_BIT,
1412                                      ISL_AUX_USAGE_NONE, NULL,
1413                                      ANV_IMAGE_VIEW_STATE_STORAGE_WRITE_ONLY,
1414                                      &iview->planes[vplane].writeonly_storage_surface_state,
1415                                      NULL);
1416      }
1417
1418      vplane++;
1419   }
1420
1421   *pView = anv_image_view_to_handle(iview);
1422
1423   return VK_SUCCESS;
1424}
1425
1426void
1427anv_DestroyImageView(VkDevice _device, VkImageView _iview,
1428                     const VkAllocationCallbacks *pAllocator)
1429{
1430   ANV_FROM_HANDLE(anv_device, device, _device);
1431   ANV_FROM_HANDLE(anv_image_view, iview, _iview);
1432
1433   if (!iview)
1434      return;
1435
1436   for (uint32_t plane = 0; plane < iview->n_planes; plane++) {
1437      if (iview->planes[plane].optimal_sampler_surface_state.state.alloc_size > 0) {
1438         anv_state_pool_free(&device->surface_state_pool,
1439                             iview->planes[plane].optimal_sampler_surface_state.state);
1440      }
1441
1442      if (iview->planes[plane].general_sampler_surface_state.state.alloc_size > 0) {
1443         anv_state_pool_free(&device->surface_state_pool,
1444                             iview->planes[plane].general_sampler_surface_state.state);
1445      }
1446
1447      if (iview->planes[plane].storage_surface_state.state.alloc_size > 0) {
1448         anv_state_pool_free(&device->surface_state_pool,
1449                             iview->planes[plane].storage_surface_state.state);
1450      }
1451
1452      if (iview->planes[plane].writeonly_storage_surface_state.state.alloc_size > 0) {
1453         anv_state_pool_free(&device->surface_state_pool,
1454                             iview->planes[plane].writeonly_storage_surface_state.state);
1455      }
1456   }
1457
1458   vk_free2(&device->alloc, pAllocator, iview);
1459}
1460
1461
1462VkResult
1463anv_CreateBufferView(VkDevice _device,
1464                     const VkBufferViewCreateInfo *pCreateInfo,
1465                     const VkAllocationCallbacks *pAllocator,
1466                     VkBufferView *pView)
1467{
1468   ANV_FROM_HANDLE(anv_device, device, _device);
1469   ANV_FROM_HANDLE(anv_buffer, buffer, pCreateInfo->buffer);
1470   struct anv_buffer_view *view;
1471
1472   view = vk_alloc2(&device->alloc, pAllocator, sizeof(*view), 8,
1473                     VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
1474   if (!view)
1475      return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
1476
1477   /* TODO: Handle the format swizzle? */
1478
1479   view->format = anv_get_isl_format(&device->info, pCreateInfo->format,
1480                                     VK_IMAGE_ASPECT_COLOR_BIT,
1481                                     VK_IMAGE_TILING_LINEAR);
1482   const uint32_t format_bs = isl_format_get_layout(view->format)->bpb / 8;
1483   view->range = anv_buffer_get_range(buffer, pCreateInfo->offset,
1484                                              pCreateInfo->range);
1485   view->range = align_down_npot_u32(view->range, format_bs);
1486
1487   view->address = anv_address_add(buffer->address, pCreateInfo->offset);
1488
1489   if (buffer->usage & VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT) {
1490      view->surface_state = alloc_surface_state(device);
1491
1492      anv_fill_buffer_surface_state(device, view->surface_state,
1493                                    view->format,
1494                                    view->address, view->range, format_bs);
1495   } else {
1496      view->surface_state = (struct anv_state){ 0 };
1497   }
1498
1499   if (buffer->usage & VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT) {
1500      view->storage_surface_state = alloc_surface_state(device);
1501      view->writeonly_storage_surface_state = alloc_surface_state(device);
1502
1503      enum isl_format storage_format =
1504         isl_has_matching_typed_storage_image_format(&device->info,
1505                                                     view->format) ?
1506         isl_lower_storage_image_format(&device->info, view->format) :
1507         ISL_FORMAT_RAW;
1508
1509      anv_fill_buffer_surface_state(device, view->storage_surface_state,
1510                                    storage_format,
1511                                    view->address, view->range,
1512                                    (storage_format == ISL_FORMAT_RAW ? 1 :
1513                                     isl_format_get_layout(storage_format)->bpb / 8));
1514
1515      /* Write-only accesses should use the original format. */
1516      anv_fill_buffer_surface_state(device, view->writeonly_storage_surface_state,
1517                                    view->format,
1518                                    view->address, view->range,
1519                                    isl_format_get_layout(view->format)->bpb / 8);
1520
1521      isl_buffer_fill_image_param(&device->isl_dev,
1522                                  &view->storage_image_param,
1523                                  view->format, view->range);
1524   } else {
1525      view->storage_surface_state = (struct anv_state){ 0 };
1526      view->writeonly_storage_surface_state = (struct anv_state){ 0 };
1527   }
1528
1529   *pView = anv_buffer_view_to_handle(view);
1530
1531   return VK_SUCCESS;
1532}
1533
1534void
1535anv_DestroyBufferView(VkDevice _device, VkBufferView bufferView,
1536                      const VkAllocationCallbacks *pAllocator)
1537{
1538   ANV_FROM_HANDLE(anv_device, device, _device);
1539   ANV_FROM_HANDLE(anv_buffer_view, view, bufferView);
1540
1541   if (!view)
1542      return;
1543
1544   if (view->surface_state.alloc_size > 0)
1545      anv_state_pool_free(&device->surface_state_pool,
1546                          view->surface_state);
1547
1548   if (view->storage_surface_state.alloc_size > 0)
1549      anv_state_pool_free(&device->surface_state_pool,
1550                          view->storage_surface_state);
1551
1552   if (view->writeonly_storage_surface_state.alloc_size > 0)
1553      anv_state_pool_free(&device->surface_state_pool,
1554                          view->writeonly_storage_surface_state);
1555
1556   vk_free2(&device->alloc, pAllocator, view);
1557}
1558
1559const struct anv_surface *
1560anv_image_get_surface_for_aspect_mask(const struct anv_image *image,
1561                                      VkImageAspectFlags aspect_mask)
1562{
1563   VkImageAspectFlags sanitized_mask;
1564
1565   switch (aspect_mask) {
1566   case VK_IMAGE_ASPECT_COLOR_BIT:
1567      assert(image->aspects == VK_IMAGE_ASPECT_COLOR_BIT);
1568      sanitized_mask = VK_IMAGE_ASPECT_COLOR_BIT;
1569      break;
1570   case VK_IMAGE_ASPECT_DEPTH_BIT:
1571      assert(image->aspects & VK_IMAGE_ASPECT_DEPTH_BIT);
1572      sanitized_mask = VK_IMAGE_ASPECT_DEPTH_BIT;
1573      break;
1574   case VK_IMAGE_ASPECT_STENCIL_BIT:
1575      assert(image->aspects & VK_IMAGE_ASPECT_STENCIL_BIT);
1576      sanitized_mask = VK_IMAGE_ASPECT_STENCIL_BIT;
1577      break;
1578   case VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT:
1579      /* FINISHME: The Vulkan spec (git a511ba2) requires support for
1580       * combined depth stencil formats. Specifically, it states:
1581       *
1582       *    At least one of ename:VK_FORMAT_D24_UNORM_S8_UINT or
1583       *    ename:VK_FORMAT_D32_SFLOAT_S8_UINT must be supported.
1584       *
1585       * Image views with both depth and stencil aspects are only valid for
1586       * render target attachments, in which case
1587       * cmd_buffer_emit_depth_stencil() will pick out both the depth and
1588       * stencil surfaces from the underlying surface.
1589       */
1590      if (image->aspects & VK_IMAGE_ASPECT_DEPTH_BIT) {
1591         sanitized_mask = VK_IMAGE_ASPECT_DEPTH_BIT;
1592      } else {
1593         assert(image->aspects == VK_IMAGE_ASPECT_STENCIL_BIT);
1594         sanitized_mask = VK_IMAGE_ASPECT_STENCIL_BIT;
1595      }
1596      break;
1597   case VK_IMAGE_ASPECT_PLANE_0_BIT:
1598      assert((image->aspects & ~VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV) == 0);
1599      sanitized_mask = VK_IMAGE_ASPECT_PLANE_0_BIT;
1600      break;
1601   case VK_IMAGE_ASPECT_PLANE_1_BIT:
1602      assert((image->aspects & ~VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV) == 0);
1603      sanitized_mask = VK_IMAGE_ASPECT_PLANE_1_BIT;
1604      break;
1605   case VK_IMAGE_ASPECT_PLANE_2_BIT:
1606      assert((image->aspects & ~VK_IMAGE_ASPECT_ANY_COLOR_BIT_ANV) == 0);
1607      sanitized_mask = VK_IMAGE_ASPECT_PLANE_2_BIT;
1608      break;
1609   default:
1610       unreachable("image does not have aspect");
1611       return NULL;
1612   }
1613
1614   uint32_t plane = anv_image_aspect_to_plane(image->aspects, sanitized_mask);
1615   return &image->planes[plane].surface;
1616}
1617