@ -28,7 +28,6 @@
# include "av1.h"
# endif
# include "libavutil/buffer.h"
# include "libavutil/hwcontext_cuda.h"
# include "libavutil/hwcontext.h"
# include "libavutil/cuda_check.h"
@ -168,27 +167,6 @@ static int nvenc_print_error(AVCodecContext *avctx, NVENCSTATUS err,
return ret ;
}
typedef struct FrameData {
int64_t pts ;
int64_t duration ;
# if FF_API_REORDERED_OPAQUE
int64_t reordered_opaque ;
# endif
void * frame_opaque ;
AVBufferRef * frame_opaque_ref ;
} FrameData ;
static void reorder_queue_flush ( AVFifo * queue )
{
FrameData fd ;
av_assert0 ( queue ) ;
while ( av_fifo_read ( queue , & fd , 1 ) > = 0 )
av_buffer_unref ( & fd . frame_opaque_ref ) ;
}
typedef struct GUIDTuple {
const GUID guid ;
int flags ;
@ -1789,8 +1767,8 @@ static av_cold int nvenc_setup_surfaces(AVCodecContext *avctx)
if ( ! ctx - > surfaces )
return AVERROR ( ENOMEM ) ;
ctx - > reorder_queue = av_fifo_alloc2 ( ctx - > nb_surfaces , sizeof ( FrameData ) , 0 ) ;
if ( ! ctx - > reorder_queue )
ctx - > timestamp_list = av_fifo_alloc2 ( ctx - > nb_surfaces , sizeof ( int64_t ) , 0 ) ;
if ( ! ctx - > timestamp_list )
return AVERROR ( ENOMEM ) ;
ctx - > unused_surface_queue = av_fifo_alloc2 ( ctx - > nb_surfaces , sizeof ( NvencSurface * ) , 0 ) ;
@ -1874,11 +1852,7 @@ av_cold int ff_nvenc_encode_close(AVCodecContext *avctx)
p_nvenc - > nvEncEncodePicture ( ctx - > nvencoder , & params ) ;
}
if ( ctx - > reorder_queue ) {
reorder_queue_flush ( ctx - > reorder_queue ) ;
av_fifo_freep2 ( & ctx - > reorder_queue ) ;
}
av_fifo_freep2 ( & ctx - > timestamp_list ) ;
av_fifo_freep2 ( & ctx - > output_surface_ready_queue ) ;
av_fifo_freep2 ( & ctx - > output_surface_queue ) ;
av_fifo_freep2 ( & ctx - > unused_surface_queue ) ;
@ -2222,53 +2196,18 @@ static void nvenc_codec_specific_pic_params(AVCodecContext *avctx,
}
}
static void reorder_queue_enqueue ( AVFifo * queue , const AVCodecContext * avctx ,
const AVFrame * frame , AVBufferRef * * opaque_ref )
static inline void timestamp_queue_enqueue ( AVFifo * queue , int64_t timestamp )
{
FrameData fd ;
fd . pts = frame - > pts ;
fd . duration = frame - > duration ;
# if FF_API_REORDERED_OPAQUE
FF_DISABLE_DEPRECATION_WARNINGS
fd . reordered_opaque = frame - > reordered_opaque ;
FF_ENABLE_DEPRECATION_WARNINGS
# endif
fd . frame_opaque = frame - > opaque ;
fd . frame_opaque_ref = * opaque_ref ;
* opaque_ref = NULL ;
av_fifo_write ( queue , & fd , 1 ) ;
av_fifo_write ( queue , & timestamp , 1 ) ;
}
static int64_t reorder_queue_dequeue ( AVFifo * queue , AVCodecContext * avctx ,
AVPacket * pkt )
static inline int64_t timestamp_queue_dequeue ( AVFifo * queue )
{
FrameData fd ;
int64_t timestamp = AV_NOPTS_VALUE ;
// The following call might fail if the queue is empty.
if ( av_fifo_read ( queue , & fd , 1 ) < 0 )
return AV_NOPTS_VALUE ;
if ( pkt ) {
# if FF_API_REORDERED_OPAQUE
FF_DISABLE_DEPRECATION_WARNINGS
avctx - > reordered_opaque = fd . reordered_opaque ;
FF_ENABLE_DEPRECATION_WARNINGS
# endif
pkt - > duration = fd . duration ;
av_fifo_read ( queue , & timestamp , 1 ) ;
if ( avctx - > flags & AV_CODEC_FLAG_COPY_OPAQUE ) {
pkt - > opaque = fd . frame_opaque ;
pkt - > opaque_ref = fd . frame_opaque_ref ;
fd . frame_opaque_ref = NULL ;
}
}
av_buffer_unref ( & fd . frame_opaque_ref ) ;
return fd . pts ;
return timestamp ;
}
static int nvenc_set_timestamp ( AVCodecContext * avctx ,
@ -2276,15 +2215,12 @@ static int nvenc_set_timestamp(AVCodecContext *avctx,
AVPacket * pkt )
{
NvencContext * ctx = avctx - > priv_data ;
int64_t dts ;
pkt - > pts = params - > outputTimeStamp ;
dts = reorder_queue_dequeue ( ctx - > reorder_queue , avctx , pkt ) ;
if ( avctx - > codec_descriptor - > props & AV_CODEC_PROP_REORDER ) {
FF_DISABLE_DEPRECATION_WARNINGS
pkt - > dts = dts -
pkt - > dts = timestamp_queue_ dequeue ( c tx - > timestamp_list ) -
# if FF_API_TICKS_PER_FRAME
FFMAX ( avctx - > ticks_per_frame , 1 ) *
# endif
@ -2386,7 +2322,7 @@ static int process_output_surface(AVCodecContext *avctx, AVPacket *pkt, NvencSur
return 0 ;
error :
reorder _queue_dequeue( ctx - > reorder_queue , avctx , NULL ) ;
timestamp _queue_dequeue( ctx - > timestamp_list ) ;
error2 :
return res ;
@ -2616,8 +2552,6 @@ static int nvenc_send_frame(AVCodecContext *avctx, const AVFrame *frame)
int sei_count = 0 ;
int i ;
AVBufferRef * opaque_ref = NULL ;
NvencContext * ctx = avctx - > priv_data ;
NvencDynLoadFunctions * dl_fn = & ctx - > nvenc_dload_funcs ;
NV_ENCODE_API_FUNCTION_LIST * p_nvenc = & dl_fn - > nvenc_funcs ;
@ -2685,17 +2619,9 @@ static int nvenc_send_frame(AVCodecContext *avctx, const AVFrame *frame)
pic_params . encodePicFlags = NV_ENC_PIC_FLAG_EOS ;
}
// make a reference for enqueing in the reorder queue here,
// so that reorder_queue_enqueue() cannot fail
if ( frame & & frame - > opaque_ref & & avctx - > flags & AV_CODEC_FLAG_COPY_OPAQUE ) {
opaque_ref = av_buffer_ref ( frame - > opaque_ref ) ;
if ( ! opaque_ref )
return AVERROR ( ENOMEM ) ;
}
res = nvenc_push_context ( avctx ) ;
if ( res < 0 )
goto opaque_ref_fail ;
return res ;
nv_status = p_nvenc - > nvEncEncodePicture ( ctx - > nvencoder , & pic_params ) ;
@ -2704,17 +2630,17 @@ static int nvenc_send_frame(AVCodecContext *avctx, const AVFrame *frame)
res = nvenc_pop_context ( avctx ) ;
if ( res < 0 )
goto opaque_ref_fail ;
return res ;
if ( nv_status ! = NV_ENC_SUCCESS & &
nv_status ! = NV_ENC_ERR_NEED_MORE_INPUT ) {
res = nvenc_print_error ( avctx , nv_status , " EncodePicture failed! " ) ;
goto opaque_ref_fail ;
}
nv_status ! = NV_ENC_ERR_NEED_MORE_INPUT )
return nvenc_print_error ( avctx , nv_status , " EncodePicture failed! " ) ;
if ( frame & & frame - > buf [ 0 ] ) {
av_fifo_write ( ctx - > output_surface_queue , & in_surf , 1 ) ;
reorder_queue_enqueue ( ctx - > reorder_queue , avctx , frame , & opaque_ref ) ;
if ( avctx - > codec_descriptor - > props & AV_CODEC_PROP_REORDER )
timestamp_queue_enqueue ( ctx - > timestamp_list , frame - > pts ) ;
}
/* all the pending buffers are now ready for output */
@ -2724,10 +2650,6 @@ static int nvenc_send_frame(AVCodecContext *avctx, const AVFrame *frame)
}
return 0 ;
opaque_ref_fail :
av_buffer_unref ( & opaque_ref ) ;
return res ;
}
int ff_nvenc_receive_packet ( AVCodecContext * avctx , AVPacket * pkt )
@ -2786,5 +2708,5 @@ av_cold void ff_nvenc_encode_flush(AVCodecContext *avctx)
NvencContext * ctx = avctx - > priv_data ;
nvenc_send_frame ( avctx , NULL ) ;
reorder_queue_flush ( ctx - > reorder_queue ) ;
av_fifo_reset2 ( ctx - > timestamp_list ) ;
}