History

hwcontext_vulkan: properly support STORAGE usage for mutliplane images

Fixes multiplane support on Nvidia. Also, remove the ENCODE usage, even if the driver signals it as supported. Currently, it's not used, and when it is used, it'll be gated behind two extension checks.

Lynne committed 3 years ago

Commit 81cc0e11 parent 2a36e442 files · +39 −21Browse files

Unified · Split

2 files
  1. libavfilter/vulkan_filter.c +15 −9
  2. libavutil/hwcontext_vulkan.c +24 −12
libavfilter/vulkan_filter.c+15−9
@@ -42,18 +42,23 @@ int ff_vk_filter_init_context(AVFilterContext *avctx, FFVulkanContext *s, · 41 unmodified lines
42 vk_frames = frames_ctx->hwctx;42 vk_frames = frames_ctx->hwctx;
43 vk_dev = device_ctx->hwctx;43 vk_dev = device_ctx->hwctx;
44 44
45 /* Basic format validation */45 /* Width and height mismatch */
46 if (width != frames_ctx->width ||46 if (width != frames_ctx->width ||
47 height != frames_ctx->height ||47 height != frames_ctx->height)
48 sw_format != frames_ctx->sw_format ||48 goto skip;
49 (vk_frames->tiling != VK_IMAGE_TILING_LINEAR &&49
50 vk_frames->tiling != VK_IMAGE_TILING_OPTIMAL) ||50 /* Format mismatch */
51 !(vk_frames->usage & VK_IMAGE_USAGE_SAMPLED_BIT)) {51 if (sw_format != frames_ctx->sw_format)
52 goto skip;52 goto skip;
53 }
54 53
55 if (vk_frames->usage & VK_IMAGE_USAGE_STORAGE_BIT)54 /* Unusual tiling mismatch. Don't let linear through either. */
56 goto accept;55 if (vk_frames->tiling != VK_IMAGE_TILING_OPTIMAL)
56 goto skip;
57
58 /* Usage mismatch */
59 if ((vk_frames->usage & (VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_STORAGE_BIT)) !=
60 (VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_STORAGE_BIT))
61 goto skip;
57 62
58 s->extensions = ff_vk_extensions_to_mask(vk_dev->enabled_dev_extensions,63 s->extensions = ff_vk_extensions_to_mask(vk_dev->enabled_dev_extensions,
59 vk_dev->nb_enabled_dev_extensions);64 vk_dev->nb_enabled_dev_extensions);
@@ -110,6 +115,7 @@ accept: · 50 unmodified lines
110 vk_frames = frames_ctx->hwctx;115 vk_frames = frames_ctx->hwctx;
111 vk_frames->tiling = VK_IMAGE_TILING_OPTIMAL;116 vk_frames->tiling = VK_IMAGE_TILING_OPTIMAL;
112 vk_frames->usage = VK_IMAGE_USAGE_SAMPLED_BIT |117 vk_frames->usage = VK_IMAGE_USAGE_SAMPLED_BIT |
118 VK_IMAGE_USAGE_STORAGE_BIT |
113 VK_IMAGE_USAGE_TRANSFER_SRC_BIT |119 VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
114 VK_IMAGE_USAGE_TRANSFER_DST_BIT;120 VK_IMAGE_USAGE_TRANSFER_DST_BIT;
115 121
libavutil/hwcontext_vulkan.c+24−12
@@ -282,9 +282,11 @@ FN_MAP_TO(VkImageUsageFlags, usage, VkFormatFeatureFlagBits2, feats) · 281 unmodified lines
282 282
283static int vkfmt_from_pixfmt2(AVHWDeviceContext *dev_ctx, enum AVPixelFormat p,283static int vkfmt_from_pixfmt2(AVHWDeviceContext *dev_ctx, enum AVPixelFormat p,
284 VkImageTiling tiling,284 VkImageTiling tiling,
285 VkFormat fmts[AV_NUM_DATA_POINTERS],285 VkFormat fmts[AV_NUM_DATA_POINTERS], /* Output format list */
286 int *nb_images, VkImageAspectFlags *aspect,286 int *nb_images, /* Output number of images */
287 VkImageUsageFlags *supported_usage, int disable_multiplane)287 VkImageAspectFlags *aspect, /* Output aspect */
288 VkImageUsageFlags *supported_usage, /* Output supported usage */
289 int disable_multiplane, int need_storage)
288{290{
289 AVVulkanDeviceContext *hwctx = dev_ctx->hwctx;291 AVVulkanDeviceContext *hwctx = dev_ctx->hwctx;
290 VulkanDevicePriv *priv = dev_ctx->internal->priv;292 VulkanDevicePriv *priv = dev_ctx->internal->priv;
@@ -301,6 +303,7 @@ static int vkfmt_from_pixfmt2(AVHWDeviceContext *dev_ctx, enum AVPixelFormat p, · 10 unmodified lines
301 };303 };
302 VkFormatFeatureFlagBits2 feats_primary, feats_secondary;304 VkFormatFeatureFlagBits2 feats_primary, feats_secondary;
303 int basics_primary = 0, basics_secondary = 0;305 int basics_primary = 0, basics_secondary = 0;
306 int storage_primary = 0, storage_secondary = 0;
304 307
305 vk->GetPhysicalDeviceFormatProperties2(hwctx->phys_dev,308 vk->GetPhysicalDeviceFormatProperties2(hwctx->phys_dev,
306 vk_formats_list[i].vkf,309 vk_formats_list[i].vkf,
@@ -310,6 +313,7 @@ static int vkfmt_from_pixfmt2(AVHWDeviceContext *dev_ctx, enum AVPixelFormat p, · 3 unmodified lines
310 prop.formatProperties.linearTilingFeatures :313 prop.formatProperties.linearTilingFeatures :
311 prop.formatProperties.optimalTilingFeatures;314 prop.formatProperties.optimalTilingFeatures;
312 basics_primary = (feats_primary & basic_flags) == basic_flags;315 basics_primary = (feats_primary & basic_flags) == basic_flags;
316 storage_primary = !!(feats_primary & VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT);
313 317
314 if (vk_formats_list[i].vkf != vk_formats_list[i].fallback[0]) {318 if (vk_formats_list[i].vkf != vk_formats_list[i].fallback[0]) {
315 vk->GetPhysicalDeviceFormatProperties2(hwctx->phys_dev,319 vk->GetPhysicalDeviceFormatProperties2(hwctx->phys_dev,
@@ -319,11 +323,15 @@ static int vkfmt_from_pixfmt2(AVHWDeviceContext *dev_ctx, enum AVPixelFormat p, · 3 unmodified lines
319 prop.formatProperties.linearTilingFeatures :323 prop.formatProperties.linearTilingFeatures :
320 prop.formatProperties.optimalTilingFeatures;324 prop.formatProperties.optimalTilingFeatures;
321 basics_secondary = (feats_secondary & basic_flags) == basic_flags;325 basics_secondary = (feats_secondary & basic_flags) == basic_flags;
326 storage_secondary = !!(feats_secondary & VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT);
322 } else {327 } else {
323 basics_secondary = basics_primary;328 basics_secondary = basics_primary;
329 storage_secondary = storage_primary;
324 }330 }
325 331
326 if (basics_primary && !(disable_multiplane && vk_formats_list[i].vk_planes > 1)) {332 if (basics_primary &&
333 !(disable_multiplane && vk_formats_list[i].vk_planes > 1) &&
334 (!need_storage || (need_storage && (storage_primary | storage_secondary)))) {
327 if (fmts)335 if (fmts)
328 fmts[0] = vk_formats_list[i].vkf;336 fmts[0] = vk_formats_list[i].vkf;
329 if (nb_images)337 if (nb_images)
@@ -331,9 +339,12 @@ static int vkfmt_from_pixfmt2(AVHWDeviceContext *dev_ctx, enum AVPixelFormat p, · 1 unmodified line
331 if (aspect)339 if (aspect)
332 *aspect = vk_formats_list[i].aspect;340 *aspect = vk_formats_list[i].aspect;
333 if (supported_usage)341 if (supported_usage)
334 *supported_usage = map_feats_to_usage(feats_primary);342 *supported_usage = map_feats_to_usage(feats_primary) |
343 ((need_storage && (storage_primary | storage_secondary)) ?
344 VK_IMAGE_USAGE_STORAGE_BIT : 0);
335 return 0;345 return 0;
336 } else if (basics_secondary) {346 } else if (basics_secondary &&
347 (!need_storage || (need_storage && storage_secondary))) {
337 if (fmts) {348 if (fmts) {
338 for (int j = 0; j < vk_formats_list[i].nb_images_fallback; j++)349 for (int j = 0; j < vk_formats_list[i].nb_images_fallback; j++)
339 fmts[j] = vk_formats_list[i].fallback[j];350 fmts[j] = vk_formats_list[i].fallback[j];
@@ -1640,7 +1651,7 @@ static int vulkan_frames_get_constraints(AVHWDeviceContext *ctx, · 1300 unmodified lines
1640 count += vkfmt_from_pixfmt2(ctx, vk_formats_list[i].pixfmt,1651 count += vkfmt_from_pixfmt2(ctx, vk_formats_list[i].pixfmt,
1641 p->use_linear_images ? VK_IMAGE_TILING_LINEAR :1652 p->use_linear_images ? VK_IMAGE_TILING_LINEAR :
1642 VK_IMAGE_TILING_OPTIMAL,1653 VK_IMAGE_TILING_OPTIMAL,
1643 NULL, NULL, NULL, NULL, 0) >= 0;1654 NULL, NULL, NULL, NULL, 0, 0) >= 0;
1644 }1655 }
1645 1656
1646#if CONFIG_CUDA1657#if CONFIG_CUDA
@@ -1658,7 +1669,7 @@ static int vulkan_frames_get_constraints(AVHWDeviceContext *ctx, · 11 unmodified lines
1658 if (vkfmt_from_pixfmt2(ctx, vk_formats_list[i].pixfmt,1669 if (vkfmt_from_pixfmt2(ctx, vk_formats_list[i].pixfmt,
1659 p->use_linear_images ? VK_IMAGE_TILING_LINEAR :1670 p->use_linear_images ? VK_IMAGE_TILING_LINEAR :
1660 VK_IMAGE_TILING_OPTIMAL,1671 VK_IMAGE_TILING_OPTIMAL,
1661 NULL, NULL, NULL, NULL, 0) >= 0) {1672 NULL, NULL, NULL, NULL, 0, 0) >= 0) {
1662 constraints->valid_sw_formats[count++] = vk_formats_list[i].pixfmt;1673 constraints->valid_sw_formats[count++] = vk_formats_list[i].pixfmt;
1663 }1674 }
1664 }1675 }
@@ -2294,7 +2305,8 @@ static int vulkan_frames_init(AVHWFramesContext *hwfc) · 629 unmodified lines
2294 /* Check if the sw_format itself is supported */2305 /* Check if the sw_format itself is supported */
2295 err = vkfmt_from_pixfmt2(hwfc->device_ctx, hwfc->sw_format,2306 err = vkfmt_from_pixfmt2(hwfc->device_ctx, hwfc->sw_format,
2296 hwctx->tiling, NULL,2307 hwctx->tiling, NULL,
2297 NULL, NULL, &supported_usage, 0);2308 NULL, NULL, &supported_usage, 0,
2309 hwctx->usage & VK_IMAGE_USAGE_STORAGE_BIT);
2298 if (err < 0) {2310 if (err < 0) {
2299 av_log(hwfc, AV_LOG_ERROR, "Unsupported sw format: %s!\n",2311 av_log(hwfc, AV_LOG_ERROR, "Unsupported sw format: %s!\n",
2300 av_get_pix_fmt_name(hwfc->sw_format));2312 av_get_pix_fmt_name(hwfc->sw_format));
@@ -2304,7 +2316,8 @@ static int vulkan_frames_init(AVHWFramesContext *hwfc) · 3 unmodified lines
2304 err = vkfmt_from_pixfmt2(hwfc->device_ctx, hwfc->sw_format,2316 err = vkfmt_from_pixfmt2(hwfc->device_ctx, hwfc->sw_format,
2305 hwctx->tiling, hwctx->format, NULL,2317 hwctx->tiling, hwctx->format, NULL,
2306 NULL, &supported_usage,2318 NULL, &supported_usage,
2307 disable_multiplane);2319 disable_multiplane,
2320 hwctx->usage & VK_IMAGE_USAGE_STORAGE_BIT);
2308 if (err < 0)2321 if (err < 0)
2309 return err;2322 return err;
2310 }2323 }
@@ -2314,8 +2327,7 @@ static int vulkan_frames_init(AVHWFramesContext *hwfc) · 3 unmodified lines
2314 hwctx->usage = supported_usage & (VK_BUFFER_USAGE_TRANSFER_DST_BIT |2327 hwctx->usage = supported_usage & (VK_BUFFER_USAGE_TRANSFER_DST_BIT |
2315 VK_BUFFER_USAGE_TRANSFER_SRC_BIT |2328 VK_BUFFER_USAGE_TRANSFER_SRC_BIT |
2316 VK_IMAGE_USAGE_STORAGE_BIT |2329 VK_IMAGE_USAGE_STORAGE_BIT |
2317 VK_IMAGE_USAGE_SAMPLED_BIT |2330 VK_IMAGE_USAGE_SAMPLED_BIT);
2318 VK_IMAGE_USAGE_VIDEO_ENCODE_SRC_BIT_KHR);
2319 }2331 }
2320 2332
2321 /* Image creation flags.2333 /* Image creation flags.

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t