#include <string.h>
#include <unistd.h>
#include <fcntl.h>
+#include <sys/mman.h>
#include "anv_private.h"
#include "util/debug.h"
.array_len = vk_info->arrayLayers,
.samples = vk_info->samples,
.min_alignment = 0,
- .min_pitch = anv_info->stride,
+ .row_pitch = anv_info->stride,
.usage = choose_isl_surf_usage(image->usage, aspect),
.tiling_flags = tiling_flags);
*/
if (!(image->usage & VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT)) {
/* It will never be used as an attachment, HiZ is pointless. */
- } else if (image->usage & VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT) {
- /* From the 1.0.37 spec:
- *
- * "An attachment used as an input attachment and depth/stencil
- * attachment must be in either VK_IMAGE_LAYOUT_GENERAL or
- * VK_IMAGE_LAYOUT_DEPTH_STENCIL_READ_ONLY_OPTIMAL."
- *
- * It will never have a layout of
- * VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL, so HiZ is
- * currently pointless. If transfer operations learn to use the HiZ
- * buffer, we can enable HiZ for VK_IMAGE_LAYOUT_GENERAL and support
- * input attachments.
- */
- anv_finishme("Implement HiZ for input attachments");
- } else if (!env_var_as_boolean("INTEL_VK_HIZ", dev->info.gen >= 8)) {
- anv_finishme("Implement gen7 HiZ");
+ } else if (dev->info.gen == 7) {
+ anv_perf_warn("Implement gen7 HiZ");
} else if (vk_info->mipLevels > 1) {
- anv_finishme("Test multi-LOD HiZ");
+ anv_perf_warn("Enable multi-LOD HiZ");
} else if (vk_info->arrayLayers > 1) {
- anv_finishme("Implement multi-arrayLayer HiZ clears and resolves");
+ anv_perf_warn("Implement multi-arrayLayer HiZ clears and resolves");
} else if (dev->info.gen == 8 && vk_info->samples > 1) {
- anv_finishme("Test gen8 multisampled HiZ");
- } else {
+ anv_perf_warn("Enable gen8 multisampled HiZ");
+ } else if (!unlikely(INTEL_DEBUG & DEBUG_NO_HIZ)) {
assert(image->aux_surface.isl.size == 0);
ok = isl_surf_get_hiz_surf(&dev->isl_dev, &image->depth_surface.isl,
&image->aux_surface.isl);
VkDeviceMemory _memory,
VkDeviceSize memoryOffset)
{
- ANV_FROM_HANDLE(anv_device, device, _device);
ANV_FROM_HANDLE(anv_device_memory, mem, _memory);
ANV_FROM_HANDLE(anv_image, image, _image);
- if (mem) {
- image->bo = &mem->bo;
- image->offset = memoryOffset;
- } else {
+ if (mem == NULL) {
image->bo = NULL;
image->offset = 0;
+ return VK_SUCCESS;
}
- if (image->aux_surface.isl.size > 0) {
-
- /* The offset and size must be a multiple of 4K or else the
- * anv_gem_mmap call below will return NULL.
- */
- assert((image->offset + image->aux_surface.offset) % 4096 == 0);
- assert(image->aux_surface.isl.size % 4096 == 0);
-
- /* Auxiliary surfaces need to have their memory cleared to 0 before they
- * can be used. For CCS surfaces, this puts them in the "resolved"
- * state so they can be used with CCS enabled before we ever touch it
- * from the GPU. For HiZ, we need something valid or else we may get
- * GPU hangs on some hardware and 0 works fine.
- */
- void *map = anv_gem_mmap(device, image->bo->gem_handle,
- image->offset + image->aux_surface.offset,
- image->aux_surface.isl.size,
- device->info.has_llc ? 0 : I915_MMAP_WC);
-
- /* If anv_gem_mmap returns NULL, it's likely that the kernel was
- * not able to find space on the host to create a proper mapping.
- */
- if (map == NULL)
- return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY);
-
- memset(map, 0, image->aux_surface.isl.size);
-
- anv_gem_munmap(map, image->aux_surface.isl.size);
- }
+ image->bo = mem->bo;
+ image->offset = memoryOffset;
return VK_SUCCESS;
}
}
/**
- * This function determines the optimal buffer to use for device
- * accesses given a VkImageLayout and other pieces of information needed to
- * make that determination. This does not determine the optimal buffer to
- * use during a resolve operation.
- *
- * NOTE: Some layouts do not support device access.
+ * This function determines the optimal buffer to use for a given
+ * VkImageLayout and other pieces of information needed to make that
+ * determination. This does not determine the optimal buffer to use
+ * during a resolve operation.
*
* @param devinfo The device information of the Intel GPU.
* @param image The image that may contain a collection of buffers.
switch (layout) {
/* Invalid Layouts */
+ case VK_IMAGE_LAYOUT_RANGE_SIZE:
+ case VK_IMAGE_LAYOUT_MAX_ENUM:
+ unreachable("Invalid image layout.");
- /* According to the Vulkan Spec, the following layouts are valid only as
- * initial layouts in a layout transition and don't support device access.
+ /* Undefined layouts
+ *
+ * The pre-initialized layout is equivalent to the undefined layout for
+ * optimally-tiled images. We can only do color compression (CCS or HiZ)
+ * on tiled images.
*/
case VK_IMAGE_LAYOUT_UNDEFINED:
case VK_IMAGE_LAYOUT_PREINITIALIZED:
- case VK_IMAGE_LAYOUT_RANGE_SIZE:
- case VK_IMAGE_LAYOUT_MAX_ENUM:
- unreachable("Invalid image layout for device access.");
+ return ISL_AUX_USAGE_NONE;
/* Transfer Layouts
(image->usage & VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT &&
!(iview->aspect_mask & VK_IMAGE_ASPECT_COLOR_BIT))) {
iview->sampler_surface_state = alloc_surface_state(device);
+ iview->no_aux_sampler_surface_state = alloc_surface_state(device);
+
+ /* Sampling is performed in one of two buffer configurations in anv: with
+ * an auxiliary buffer or without it. Sampler states aren't always needed
+ * for both configurations, but are currently created unconditionally for
+ * simplicity.
+ *
+ * TODO: Consider allocating each surface state only when necessary.
+ */
- /* Select the optimal aux_usage for sampling. */
+ /* Create a sampler state with the optimal aux_usage for sampling. This
+ * may use the aux_buffer.
+ */
const enum isl_aux_usage surf_usage =
anv_layout_to_aux_usage(&device->info, image, iview->aspect_mask,
VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
.aux_usage = surf_usage,
.mocs = device->default_mocs);
+ /* Create a sampler state that only uses the main buffer. */
+ isl_surf_fill_state(&device->isl_dev,
+ iview->no_aux_sampler_surface_state.map,
+ .surf = &surface->isl,
+ .view = &view,
+ .mocs = device->default_mocs);
+
anv_state_flush(device, iview->sampler_surface_state);
+ anv_state_flush(device, iview->no_aux_sampler_surface_state);
} else {
iview->sampler_surface_state.alloc_size = 0;
+ iview->no_aux_sampler_surface_state.alloc_size = 0;
}
/* NOTE: This one needs to go last since it may stomp isl_view.format */
const uint32_t format_bs = isl_format_get_layout(view->format)->bpb / 8;
view->bo = buffer->bo;
view->offset = buffer->offset + pCreateInfo->offset;
- view->range = pCreateInfo->range == VK_WHOLE_SIZE ?
- buffer->size - pCreateInfo->offset : pCreateInfo->range;
+ view->range = anv_buffer_get_range(buffer, pCreateInfo->offset,
+ pCreateInfo->range);
view->range = align_down_npot_u32(view->range, format_bs);
if (buffer->usage & VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT) {