[FFmpeg-cvslog] lavc: make avcodec_close() work properly on unopened codecs.
Anton Khirnov
git at videolan.org
Wed Feb 1 03:06:32 CET 2012
ffmpeg | branch: master | Anton Khirnov <anton at khirnov.net> | Sun Jan 29 12:17:30 2012 +0100| [0e72ad95f9fef6a6b8ae55e47339a5c40526502f] | committer: Anton Khirnov
lavc: make avcodec_close() work properly on unopened codecs.
I.e. free the priv_data and other stuff allocated in
avcodec_alloc_context3() and not segfault.
> http://git.videolan.org/gitweb.cgi/ffmpeg.git/?a=commit;h=0e72ad95f9fef6a6b8ae55e47339a5c40526502f
---
libavcodec/avcodec.h | 12 +++++++++++-
libavcodec/utils.c | 19 +++++++++++--------
2 files changed, 22 insertions(+), 9 deletions(-)
diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h
index 284c7f8..77abec5 100644
--- a/libavcodec/avcodec.h
+++ b/libavcodec/avcodec.h
@@ -3417,7 +3417,8 @@ int avcodec_get_context_defaults3(AVCodecContext *s, AVCodec *codec);
/**
* Allocate an AVCodecContext and set its fields to default values. The
- * resulting struct can be deallocated by simply calling av_free().
+ * resulting struct can be deallocated by calling avcodec_close() on it followed
+ * by av_free().
*
* @param codec if non-NULL, allocate private data and initialize defaults
* for the given codec. It is illegal to then call avcodec_open2()
@@ -3809,6 +3810,15 @@ int avcodec_encode_video(AVCodecContext *avctx, uint8_t *buf, int buf_size,
int avcodec_encode_subtitle(AVCodecContext *avctx, uint8_t *buf, int buf_size,
const AVSubtitle *sub);
+/**
+ * Close a given AVCodecContext and free all the data associated with it
+ * (but not the AVCodecContext itself).
+ *
+ * Calling this function on an AVCodecContext that hasn't been opened will free
+ * the codec-specific data allocated in avcodec_alloc_context3() /
+ * avcodec_get_context_defaults3() with a non-NULL codec. Subsequent calls will
+ * do nothing.
+ */
int avcodec_close(AVCodecContext *avctx);
/**
diff --git a/libavcodec/utils.c b/libavcodec/utils.c
index 3ee6b09..9cdae22 100644
--- a/libavcodec/utils.c
+++ b/libavcodec/utils.c
@@ -1267,14 +1267,17 @@ av_cold int avcodec_close(AVCodecContext *avctx)
return -1;
}
- if (HAVE_THREADS && avctx->thread_opaque)
- ff_thread_free(avctx);
- if (avctx->codec && avctx->codec->close)
- avctx->codec->close(avctx);
- avcodec_default_free_buffers(avctx);
- avctx->coded_frame = NULL;
- av_freep(&avctx->internal);
- if (avctx->codec && avctx->codec->priv_class)
+ if (avcodec_is_open(avctx)) {
+ if (HAVE_THREADS && avctx->thread_opaque)
+ ff_thread_free(avctx);
+ if (avctx->codec && avctx->codec->close)
+ avctx->codec->close(avctx);
+ avcodec_default_free_buffers(avctx);
+ avctx->coded_frame = NULL;
+ av_freep(&avctx->internal);
+ }
+
+ if (avctx->priv_data && avctx->codec && avctx->codec->priv_class)
av_opt_free(avctx->priv_data);
av_opt_free(avctx);
av_freep(&avctx->priv_data);
More information about the ffmpeg-cvslog
mailing list