*/
device->has_clear_state = device->rad_info.chip_class >= CIK;
+ device->cpdma_prefetch_writes_memory = device->rad_info.chip_class <= VI;
+
+ /* Vega10/Raven need a special workaround for a hardware bug. */
+ device->has_scissor_bug = device->rad_info.family == CHIP_VEGA10 ||
+ device->rad_info.family == CHIP_RAVEN;
+
radv_physical_device_init_mem_types(device);
result = radv_init_wsi(device);
static const struct debug_control radv_perftest_options[] = {
{"nobatchchain", RADV_PERFTEST_NO_BATCHCHAIN},
{"sisched", RADV_PERFTEST_SISCHED},
+ {"localbos", RADV_PERFTEST_LOCAL_BOS},
+ {"binning", RADV_PERFTEST_BINNING},
{NULL, 0}
};
properties->pointClippingBehavior = VK_POINT_CLIPPING_BEHAVIOR_ALL_CLIP_PLANES_KHR;
break;
}
+ case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DISCARD_RECTANGLE_PROPERTIES_EXT: {
+ VkPhysicalDeviceDiscardRectanglePropertiesEXT *properties =
+ (VkPhysicalDeviceDiscardRectanglePropertiesEXT*)ext;
+ properties->maxDiscardRectangles = MAX_DISCARD_RECTANGLES;
+ break;
+ }
default:
break;
}
}
}
+ device->pbb_allowed = device->physical_device->rad_info.chip_class >= GFX9 &&
+ (device->instance->perftest_flags & RADV_PERFTEST_BINNING);
+
+ /* Disabled and not implemented for now. */
+ device->dfsm_allowed = device->pbb_allowed && false;
+
+
#if HAVE_LLVM < 0x0400
device->llvm_supports_spill = false;
#else
size,
4096,
RADEON_DOMAIN_VRAM,
- RADEON_FLAG_CPU_ACCESS|RADEON_FLAG_NO_INTERPROCESS_SHARING);
+ RADEON_FLAG_CPU_ACCESS |
+ RADEON_FLAG_NO_INTERPROCESS_SHARING |
+ RADEON_FLAG_READ_ONLY);
if (!descriptor_bo)
goto fail;
} else
/* create a syncobject if we are going to export this semaphore */
if (handleTypes) {
assert (device->physical_device->rad_info.has_syncobj);
- assert (handleTypes == VK_EXTERNAL_FENCE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR);
int ret = device->ws->create_syncobj(device->ws, &sem->syncobj);
if (ret) {
vk_free2(&device->alloc, pAllocator, sem);
return image->surface.u.legacy.tiling_index[level];
}
-static uint32_t radv_surface_layer_count(struct radv_image_view *iview)
+static uint32_t radv_surface_max_layer_count(struct radv_image_view *iview)
{
- return iview->type == VK_IMAGE_VIEW_TYPE_3D ? iview->extent.depth : iview->layer_count;
+ return iview->type == VK_IMAGE_VIEW_TYPE_3D ? iview->extent.depth : (iview->base_layer + iview->layer_count);
}
static void
cb->cb_dcc_base = va >> 8;
cb->cb_dcc_base |= iview->image->surface.tile_swizzle;
- uint32_t max_slice = radv_surface_layer_count(iview);
+ uint32_t max_slice = radv_surface_max_layer_count(iview) - 1;
cb->cb_color_view = S_028C6C_SLICE_START(iview->base_layer) |
- S_028C6C_SLICE_MAX(iview->base_layer + max_slice - 1);
+ S_028C6C_SLICE_MAX(max_slice);
if (iview->image->info.samples > 1) {
unsigned log_samples = util_logbase2(iview->image->info.samples);
cb->cb_color_info |= S_028C70_DCC_ENABLE(1);
if (device->physical_device->rad_info.chip_class >= VI) {
- unsigned max_uncompressed_block_size = 2;
+ unsigned max_uncompressed_block_size = V_028C78_MAX_BLOCK_SIZE_256B;
+ unsigned min_compressed_block_size = V_028C78_MIN_BLOCK_SIZE_32B;
+ unsigned independent_64b_blocks = 0;
+ unsigned max_compressed_block_size;
+
+ /* amdvlk: [min-compressed-block-size] should be set to 32 for dGPU and
+ 64 for APU because all of our APUs to date use DIMMs which have
+ a request granularity size of 64B while all other chips have a
+ 32B request size */
+ if (!device->physical_device->rad_info.has_dedicated_vram)
+ min_compressed_block_size = V_028C78_MIN_BLOCK_SIZE_64B;
+
if (iview->image->info.samples > 1) {
if (iview->image->surface.bpe == 1)
- max_uncompressed_block_size = 0;
+ max_uncompressed_block_size = V_028C78_MAX_BLOCK_SIZE_64B;
else if (iview->image->surface.bpe == 2)
- max_uncompressed_block_size = 1;
+ max_uncompressed_block_size = V_028C78_MAX_BLOCK_SIZE_128B;
}
+ if (iview->image->usage & (VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
+ VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT)) {
+ independent_64b_blocks = 1;
+ max_compressed_block_size = V_028C78_MAX_BLOCK_SIZE_64B;
+ } else
+ max_compressed_block_size = max_uncompressed_block_size;
+
cb->cb_dcc_control = S_028C78_MAX_UNCOMPRESSED_BLOCK_SIZE(max_uncompressed_block_size) |
- S_028C78_INDEPENDENT_64B_BLOCKS(1);
+ S_028C78_MAX_COMPRESSED_BLOCK_SIZE(max_compressed_block_size) |
+ S_028C78_MIN_COMPRESSED_BLOCK_SIZE(min_compressed_block_size) |
+ S_028C78_INDEPENDENT_64B_BLOCKS(independent_64b_blocks);
}
/* This must be set for fast clear to work without FMASK. */
stencil_format = iview->image->surface.has_stencil ?
V_028044_STENCIL_8 : V_028044_STENCIL_INVALID;
- uint32_t max_slice = radv_surface_layer_count(iview);
+ uint32_t max_slice = radv_surface_max_layer_count(iview) - 1;
ds->db_depth_view = S_028008_SLICE_START(iview->base_layer) |
- S_028008_SLICE_MAX(iview->base_layer + max_slice - 1);
+ S_028008_SLICE_MAX(max_slice);
ds->db_htile_data_base = 0;
ds->db_htile_surface = 0;
}
framebuffer->width = MIN2(framebuffer->width, iview->extent.width);
framebuffer->height = MIN2(framebuffer->height, iview->extent.height);
- framebuffer->layers = MIN2(framebuffer->layers, radv_surface_layer_count(iview));
+ framebuffer->layers = MIN2(framebuffer->layers, radv_surface_max_layer_count(iview));
}
*pFramebuffer = radv_framebuffer_to_handle(framebuffer);
}
}
+static VkResult radv_import_opaque_fd(struct radv_device *device,
+ int fd,
+ uint32_t *syncobj)
+{
+ uint32_t syncobj_handle = 0;
+ int ret = device->ws->import_syncobj(device->ws, fd, &syncobj_handle);
+ if (ret != 0)
+ return vk_error(VK_ERROR_INVALID_EXTERNAL_HANDLE_KHR);
+
+ if (*syncobj)
+ device->ws->destroy_syncobj(device->ws, *syncobj);
+
+ *syncobj = syncobj_handle;
+ close(fd);
+
+ return VK_SUCCESS;
+}
+
+static VkResult radv_import_sync_fd(struct radv_device *device,
+ int fd,
+ uint32_t *syncobj)
+{
+ /* If we create a syncobj we do it locally so that if we have an error, we don't
+ * leave a syncobj in an undetermined state in the fence. */
+ uint32_t syncobj_handle = *syncobj;
+ if (!syncobj_handle) {
+ int ret = device->ws->create_syncobj(device->ws, &syncobj_handle);
+ if (ret) {
+ return vk_error(VK_ERROR_INVALID_EXTERNAL_HANDLE_KHR);
+ }
+ }
+
+ if (fd == -1) {
+ device->ws->signal_syncobj(device->ws, syncobj_handle);
+ } else {
+ int ret = device->ws->import_syncobj_from_sync_file(device->ws, syncobj_handle, fd);
+ if (ret != 0)
+ return vk_error(VK_ERROR_INVALID_EXTERNAL_HANDLE_KHR);
+ }
+
+ *syncobj = syncobj_handle;
+ if (fd != -1)
+ close(fd);
+
+ return VK_SUCCESS;
+}
+
VkResult radv_ImportSemaphoreFdKHR(VkDevice _device,
const VkImportSemaphoreFdInfoKHR *pImportSemaphoreFdInfo)
{
RADV_FROM_HANDLE(radv_device, device, _device);
RADV_FROM_HANDLE(radv_semaphore, sem, pImportSemaphoreFdInfo->semaphore);
- uint32_t syncobj_handle = 0;
uint32_t *syncobj_dst = NULL;
- assert(pImportSemaphoreFdInfo->handleType == VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR);
-
- int ret = device->ws->import_syncobj(device->ws, pImportSemaphoreFdInfo->fd, &syncobj_handle);
- if (ret != 0)
- return vk_error(VK_ERROR_INVALID_EXTERNAL_HANDLE_KHR);
if (pImportSemaphoreFdInfo->flags & VK_SEMAPHORE_IMPORT_TEMPORARY_BIT_KHR) {
syncobj_dst = &sem->temp_syncobj;
syncobj_dst = &sem->syncobj;
}
- if (*syncobj_dst)
- device->ws->destroy_syncobj(device->ws, *syncobj_dst);
-
- *syncobj_dst = syncobj_handle;
- close(pImportSemaphoreFdInfo->fd);
- return VK_SUCCESS;
+ switch(pImportSemaphoreFdInfo->handleType) {
+ case VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR:
+ return radv_import_opaque_fd(device, pImportSemaphoreFdInfo->fd, syncobj_dst);
+ case VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_SYNC_FD_BIT_KHR:
+ return radv_import_sync_fd(device, pImportSemaphoreFdInfo->fd, syncobj_dst);
+ default:
+ unreachable("Unhandled semaphore handle type");
+ }
}
VkResult radv_GetSemaphoreFdKHR(VkDevice _device,
int ret;
uint32_t syncobj_handle;
- assert(pGetFdInfo->handleType == VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR);
if (sem->temp_syncobj)
syncobj_handle = sem->temp_syncobj;
else
syncobj_handle = sem->syncobj;
- ret = device->ws->export_syncobj(device->ws, syncobj_handle, pFd);
+
+ switch(pGetFdInfo->handleType) {
+ case VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR:
+ ret = device->ws->export_syncobj(device->ws, syncobj_handle, pFd);
+ break;
+ case VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_SYNC_FD_BIT_KHR:
+ ret = device->ws->export_syncobj_to_sync_file(device->ws, syncobj_handle, pFd);
+ break;
+ default:
+ unreachable("Unhandled semaphore handle type");
+ }
+
if (ret)
return vk_error(VK_ERROR_INVALID_EXTERNAL_HANDLE_KHR);
return VK_SUCCESS;
const VkPhysicalDeviceExternalSemaphoreInfoKHR* pExternalSemaphoreInfo,
VkExternalSemaphorePropertiesKHR* pExternalSemaphoreProperties)
{
- if (pExternalSemaphoreInfo->handleType == VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR) {
+ RADV_FROM_HANDLE(radv_physical_device, pdevice, physicalDevice);
+
+ /* Require has_syncobj_wait_for_submit for the syncobj signal ioctl introduced at virtually the same time */
+ if (pdevice->rad_info.has_syncobj_wait_for_submit &&
+ (pExternalSemaphoreInfo->handleType == VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR ||
+ pExternalSemaphoreInfo->handleType == VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_SYNC_FD_BIT_KHR)) {
+ pExternalSemaphoreProperties->exportFromImportedHandleTypes = VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR | VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_SYNC_FD_BIT_KHR;
+ pExternalSemaphoreProperties->compatibleHandleTypes = VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR | VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_SYNC_FD_BIT_KHR;
+ pExternalSemaphoreProperties->externalSemaphoreFeatures = VK_EXTERNAL_SEMAPHORE_FEATURE_EXPORTABLE_BIT_KHR |
+ VK_EXTERNAL_SEMAPHORE_FEATURE_IMPORTABLE_BIT_KHR;
+ } else if (pExternalSemaphoreInfo->handleType == VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR) {
pExternalSemaphoreProperties->exportFromImportedHandleTypes = VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR;
pExternalSemaphoreProperties->compatibleHandleTypes = VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR;
pExternalSemaphoreProperties->externalSemaphoreFeatures = VK_EXTERNAL_SEMAPHORE_FEATURE_EXPORTABLE_BIT_KHR |
pExternalSemaphoreProperties->externalSemaphoreFeatures = 0;
}
}
+
+VkResult radv_ImportFenceFdKHR(VkDevice _device,
+ const VkImportFenceFdInfoKHR *pImportFenceFdInfo)
+{
+ RADV_FROM_HANDLE(radv_device, device, _device);
+ RADV_FROM_HANDLE(radv_fence, fence, pImportFenceFdInfo->fence);
+ uint32_t *syncobj_dst = NULL;
+
+
+ if (pImportFenceFdInfo->flags & VK_FENCE_IMPORT_TEMPORARY_BIT_KHR) {
+ syncobj_dst = &fence->temp_syncobj;
+ } else {
+ syncobj_dst = &fence->syncobj;
+ }
+
+ switch(pImportFenceFdInfo->handleType) {
+ case VK_EXTERNAL_FENCE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR:
+ return radv_import_opaque_fd(device, pImportFenceFdInfo->fd, syncobj_dst);
+ case VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT_KHR:
+ return radv_import_sync_fd(device, pImportFenceFdInfo->fd, syncobj_dst);
+ default:
+ unreachable("Unhandled fence handle type");
+ }
+}
+
+VkResult radv_GetFenceFdKHR(VkDevice _device,
+ const VkFenceGetFdInfoKHR *pGetFdInfo,
+ int *pFd)
+{
+ RADV_FROM_HANDLE(radv_device, device, _device);
+ RADV_FROM_HANDLE(radv_fence, fence, pGetFdInfo->fence);
+ int ret;
+ uint32_t syncobj_handle;
+
+ if (fence->temp_syncobj)
+ syncobj_handle = fence->temp_syncobj;
+ else
+ syncobj_handle = fence->syncobj;
+
+ switch(pGetFdInfo->handleType) {
+ case VK_EXTERNAL_FENCE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR:
+ ret = device->ws->export_syncobj(device->ws, syncobj_handle, pFd);
+ break;
+ case VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT_KHR:
+ ret = device->ws->export_syncobj_to_sync_file(device->ws, syncobj_handle, pFd);
+ break;
+ default:
+ unreachable("Unhandled fence handle type");
+ }
+
+ if (ret)
+ return vk_error(VK_ERROR_INVALID_EXTERNAL_HANDLE_KHR);
+ return VK_SUCCESS;
+}
+
+void radv_GetPhysicalDeviceExternalFencePropertiesKHR(
+ VkPhysicalDevice physicalDevice,
+ const VkPhysicalDeviceExternalFenceInfoKHR* pExternalFenceInfo,
+ VkExternalFencePropertiesKHR* pExternalFenceProperties)
+{
+ RADV_FROM_HANDLE(radv_physical_device, pdevice, physicalDevice);
+
+ if (pdevice->rad_info.has_syncobj_wait_for_submit &&
+ (pExternalFenceInfo->handleType == VK_EXTERNAL_FENCE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR ||
+ pExternalFenceInfo->handleType == VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT_KHR)) {
+ pExternalFenceProperties->exportFromImportedHandleTypes = VK_EXTERNAL_FENCE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR | VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT_KHR;
+ pExternalFenceProperties->compatibleHandleTypes = VK_EXTERNAL_FENCE_HANDLE_TYPE_OPAQUE_FD_BIT_KHR | VK_EXTERNAL_FENCE_HANDLE_TYPE_SYNC_FD_BIT_KHR;
+ pExternalFenceProperties->externalFenceFeatures = VK_EXTERNAL_FENCE_FEATURE_EXPORTABLE_BIT_KHR |
+ VK_EXTERNAL_SEMAPHORE_FEATURE_IMPORTABLE_BIT_KHR;
+ } else {
+ pExternalFenceProperties->exportFromImportedHandleTypes = 0;
+ pExternalFenceProperties->compatibleHandleTypes = 0;
+ pExternalFenceProperties->externalFenceFeatures = 0;
+ }
+}