avfilter/vf_lcevc: attach a reference to the source frame to each passed in base picture

And free them once they are guaranteed to be no longer needed, instead of freeing them
when returned with an enhanced output.

Signed-off-by: James Almer <jamrial@gmail.com>
This commit is contained in:
James Almer
2026-01-10 15:48:46 -03:00
parent 188521c7ad
commit af136db1c3

View File

@@ -148,6 +148,13 @@ static int send_frame(AVFilterLink *inlink, AVFrame *in)
}
}
res = LCEVC_SetPictureUserData(lcevc->decoder, picture, in);
if (res != LCEVC_Success) {
av_log(ctx, AV_LOG_ERROR, "LCEVC_SetPictureUserData failed\n");
LCEVC_FreePicture(lcevc->decoder, picture);
return AVERROR_EXTERNAL;
}
res = LCEVC_SendDecoderBase(lcevc->decoder, in->pts, picture, -1, in);
if (res != LCEVC_Success) {
av_log(ctx, AV_LOG_ERROR, "LCEVC_SendDecoderBase failed\n");
@@ -215,8 +222,6 @@ static int generate_output(AVFilterLink *inlink, AVFrame *out)
av_frame_copy_props(out, (AVFrame *)info.baseUserData);
av_frame_remove_side_data(out, AV_FRAME_DATA_LCEVC);
av_frame_free((AVFrame **)&info.baseUserData);
res = LCEVC_GetPictureDesc(lcevc->decoder, picture, &desc);
LCEVC_FreePicture(lcevc->decoder, picture);
@@ -284,8 +289,12 @@ static void flush_bases(AVFilterContext *ctx)
LCEVCContext *lcevc = ctx->priv;
LCEVC_PictureHandle picture;
while (LCEVC_ReceiveDecoderBase(lcevc->decoder, &picture) == LCEVC_Success)
while (LCEVC_ReceiveDecoderBase(lcevc->decoder, &picture) == LCEVC_Success) {
AVFrame *base = NULL;
LCEVC_GetPictureUserData(lcevc->decoder, picture, (void **)&base);
LCEVC_FreePicture(lcevc->decoder, picture);
av_frame_free(&base);
}
}
static int activate(AVFilterContext *ctx)
@@ -399,6 +408,8 @@ static av_cold void uninit(AVFilterContext *ctx)
{
LCEVCContext *lcevc = ctx->priv;
LCEVC_FlushDecoder(lcevc->decoder);
flush_bases(ctx);
LCEVC_DestroyDecoder(lcevc->decoder);
}