summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ffmpeg.h1
-rw-r--r--ffmpeg_opt.c3
-rw-r--r--ffmpeg_vdpau.c48
3 files changed, 52 insertions, 0 deletions
diff --git a/ffmpeg.h b/ffmpeg.h
index 56eb66a6e8..c45660309e 100644
--- a/ffmpeg.h
+++ b/ffmpeg.h
@@ -490,6 +490,7 @@ extern int stdin_interaction;
extern int frame_bits_per_raw_sample;
extern AVIOContext *progress_avio;
extern float max_error_rate;
+extern int vdpau_api_ver;
extern const AVIOInterruptCB int_cb;
diff --git a/ffmpeg_opt.c b/ffmpeg_opt.c
index 4fb6fa36b1..10aaa3a6af 100644
--- a/ffmpeg_opt.c
+++ b/ffmpeg_opt.c
@@ -2984,6 +2984,9 @@ const OptionDef options[] = {
{ "hwaccel_device", OPT_VIDEO | OPT_STRING | HAS_ARG | OPT_EXPERT |
OPT_SPEC | OPT_INPUT, { .off = OFFSET(hwaccel_devices) },
"select a device for HW acceleration" "devicename" },
+#if HAVE_VDPAU_X11
+ { "vdpau_api_ver", HAS_ARG | OPT_INT | OPT_EXPERT, { &vdpau_api_ver }, "" },
+#endif
/* audio options */
{ "aframes", OPT_AUDIO | HAS_ARG | OPT_PERFILE | OPT_OUTPUT, { .func_arg = opt_audio_frames },
diff --git a/ffmpeg_vdpau.c b/ffmpeg_vdpau.c
index fe0930695e..ef35d22ae8 100644
--- a/ffmpeg_vdpau.c
+++ b/ffmpeg_vdpau.c
@@ -57,6 +57,8 @@ typedef struct VDPAUContext {
VdpYCbCrFormat vdpau_format;
} VDPAUContext;
+int vdpau_api_ver = 2;
+
static void vdpau_uninit(AVCodecContext *s)
{
InputStream *ist = s->opaque;
@@ -291,6 +293,49 @@ fail:
return AVERROR(EINVAL);
}
+static int vdpau_old_init(AVCodecContext *s)
+{
+ InputStream *ist = s->opaque;
+ int loglevel = (ist->hwaccel_id == HWACCEL_AUTO) ? AV_LOG_VERBOSE : AV_LOG_ERROR;
+ AVVDPAUContext *vdpau_ctx;
+ VDPAUContext *ctx;
+ VdpStatus err;
+ int profile, ret;
+
+ if (!ist->hwaccel_ctx) {
+ ret = vdpau_alloc(s);
+ if (ret < 0)
+ return ret;
+ }
+ ctx = ist->hwaccel_ctx;
+ vdpau_ctx = s->hwaccel_context;
+
+ ret = av_vdpau_get_profile(s, &profile);
+ if (ret < 0) {
+ av_log(NULL, loglevel, "No known VDPAU decoder profile for this stream.\n");
+ return AVERROR(EINVAL);
+ }
+
+ if (ctx->decoder)
+ ctx->decoder_destroy(ctx->decoder);
+
+ err = ctx->decoder_create(ctx->device, profile,
+ s->coded_width, s->coded_height,
+ 16, &ctx->decoder);
+ if (err != VDP_STATUS_OK) {
+ av_log(NULL, loglevel, "Error creating the VDPAU decoder: %s\n",
+ ctx->get_error_string(err));
+ return AVERROR_UNKNOWN;
+ }
+
+ vdpau_ctx->decoder = ctx->decoder;
+
+ ist->hwaccel_get_buffer = vdpau_get_buffer;
+ ist->hwaccel_retrieve_data = vdpau_retrieve_data;
+
+ return 0;
+}
+
int vdpau_init(AVCodecContext *s)
{
InputStream *ist = s->opaque;
@@ -300,6 +345,9 @@ int vdpau_init(AVCodecContext *s)
VdpStatus err;
int profile, ret;
+ if (vdpau_api_ver == 1)
+ return vdpau_old_init(s);
+
if (!ist->hwaccel_ctx) {
ret = vdpau_alloc(s);
if (ret < 0)