X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavcodec%2Fcuvid.c;h=288083423ebbf51b9d4f9861101a4f5d09398265;hb=54a4c9b4e9a1524b1ac5d2be97c8042272402d0a;hp=916d7e9987ebb18326d796ac0f57915fc700bd0e;hpb=9ae1ffe64126bda204e498c83e414dad7ff078f8;p=ffmpeg diff --git a/libavcodec/cuvid.c b/libavcodec/cuvid.c index 916d7e9987e..288083423eb 100644 --- a/libavcodec/cuvid.c +++ b/libavcodec/cuvid.c @@ -31,6 +31,7 @@ #include "libavutil/pixdesc.h" #include "avcodec.h" +#include "decode.h" #include "internal.h" typedef struct CuvidContext @@ -357,6 +358,13 @@ static int CUDAAPI cuvid_handle_picture_display(void *opaque, CUVIDPARSERDISPINF return 1; } +static int cuvid_is_buffer_full(AVCodecContext *avctx) +{ + CuvidContext *ctx = avctx->priv_data; + + return (av_fifo_size(ctx->frame_queue) / sizeof(CuvidParsedFrame)) + 2 > ctx->nb_surfaces; +} + static int cuvid_decode_packet(AVCodecContext *avctx, const AVPacket *avpkt) { CuvidContext *ctx = avctx->priv_data; @@ -373,7 +381,7 @@ static int cuvid_decode_packet(AVCodecContext *avctx, const AVPacket *avpkt) if (is_flush && avpkt && avpkt->size) return AVERROR_EOF; - if ((av_fifo_size(ctx->frame_queue) / sizeof(CuvidParsedFrame)) + 2 > ctx->nb_surfaces && avpkt && avpkt->size) + if (cuvid_is_buffer_full(avctx) && avpkt && avpkt->size) return AVERROR(EAGAIN); if (ctx->bsf && avpkt && avpkt->size) { @@ -464,6 +472,20 @@ static int cuvid_output_frame(AVCodecContext *avctx, AVFrame *frame) return ret; } + if (!cuvid_is_buffer_full(avctx)) { + AVPacket pkt = {0}; + ret = ff_decode_get_packet(avctx, &pkt); + if (ret < 0 && ret != AVERROR_EOF) + return ret; + ret = cuvid_decode_packet(avctx, &pkt); + av_packet_unref(&pkt); + // cuvid_is_buffer_full() should avoid this. + if (ret == AVERROR(EAGAIN)) + ret = AVERROR_EXTERNAL; + if (ret < 0 && ret != AVERROR_EOF) + return ret; + } + ret = CHECK_CU(ctx->cudl->cuCtxPushCurrent(cuda_ctx)); if (ret < 0) return ret; @@ -582,9 +604,9 @@ FF_DISABLE_DEPRECATION_WARNINGS frame->pkt_pts = frame->pts; FF_ENABLE_DEPRECATION_WARNINGS #endif - av_frame_set_pkt_pos(frame, -1); - av_frame_set_pkt_duration(frame, 0); - av_frame_set_pkt_size(frame, -1); + frame->pkt_pos = -1; + frame->pkt_duration = 0; + frame->pkt_size = -1; frame->interlaced_frame = !parsed_frame.is_deinterlacing && !parsed_frame.dispinfo.progressive_frame; @@ -1026,7 +1048,6 @@ static const AVOption options[] = { .init = cuvid_decode_init, \ .close = cuvid_decode_end, \ .decode = cuvid_decode_frame, \ - .send_packet = cuvid_decode_packet, \ .receive_frame = cuvid_output_frame, \ .flush = cuvid_flush, \ .capabilities = AV_CODEC_CAP_DELAY | AV_CODEC_CAP_AVOID_PROBING, \