You've already forked FFmpeg
mirror of
https://github.com/FFmpeg/FFmpeg.git
synced 2025-08-10 06:10:52 +02:00
lavu/hwcontext_vaapi: fix a race mapping to allow CSC to YUV420P
There's a race condition for YUV420P when mapping from pix_fmt to VA fourcc, both I420 and YV12 could be found by pix_fmt. Currently, vaapi_get_image_format() iterates over the query results of pix_fmt and returns the first matching result in the order declared in the driver. This may result in an incorrect image_format. Now use fourcc to find the image_format. Fixes: ffmpeg -hwaccel vaapi -hwaccel_output_format vaapi -i INPUT \ -vf scale_vaapi=format=yuv420p,hwmap,format=yuv420p \ -vframes 1 -f rawvideo -y yuv420p.yuv Signed-off-by: nyanmisaka <nst799610810@gmail.com>
This commit is contained in:
@@ -72,6 +72,7 @@ typedef struct VAAPIDevicePriv {
|
||||
typedef struct VAAPISurfaceFormat {
|
||||
enum AVPixelFormat pix_fmt;
|
||||
VAImageFormat image_format;
|
||||
unsigned int fourcc;
|
||||
} VAAPISurfaceFormat;
|
||||
|
||||
typedef struct VAAPIDeviceContext {
|
||||
@@ -218,15 +219,21 @@ static int vaapi_get_image_format(AVHWDeviceContext *hwdev,
|
||||
VAImageFormat **image_format)
|
||||
{
|
||||
VAAPIDeviceContext *ctx = hwdev->hwctx;
|
||||
const VAAPIFormatDescriptor *desc;
|
||||
int i;
|
||||
|
||||
desc = vaapi_format_from_pix_fmt(pix_fmt);
|
||||
if (!desc || !image_format)
|
||||
goto fail;
|
||||
|
||||
for (i = 0; i < ctx->nb_formats; i++) {
|
||||
if (ctx->formats[i].pix_fmt == pix_fmt) {
|
||||
if (image_format)
|
||||
if (ctx->formats[i].fourcc == desc->fourcc) {
|
||||
*image_format = &ctx->formats[i].image_format;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
fail:
|
||||
return AVERROR(ENOSYS);
|
||||
}
|
||||
|
||||
@@ -435,6 +442,7 @@ static int vaapi_device_init(AVHWDeviceContext *hwdev)
|
||||
av_log(hwdev, AV_LOG_DEBUG, "Format %#x -> %s.\n",
|
||||
fourcc, av_get_pix_fmt_name(pix_fmt));
|
||||
ctx->formats[ctx->nb_formats].pix_fmt = pix_fmt;
|
||||
ctx->formats[ctx->nb_formats].fourcc = fourcc;
|
||||
ctx->formats[ctx->nb_formats].image_format = image_list[i];
|
||||
++ctx->nb_formats;
|
||||
}
|
||||
|
Reference in New Issue
Block a user