To do this, make FFRefStructPool itself refcounted according to the RefStruct API.
Signed-off-by: Andreas Rheinhardt <andreas.rheinha...@outlook.com> --- libavcodec/refstruct.c | 29 ++++++++++++++++------------- libavcodec/refstruct.h | 5 ++++- 2 files changed, 20 insertions(+), 14 deletions(-) diff --git a/libavcodec/refstruct.c b/libavcodec/refstruct.c index f8d040874d..2108ff8163 100644 --- a/libavcodec/refstruct.c +++ b/libavcodec/refstruct.c @@ -187,7 +187,7 @@ static void pool_free(FFRefStructPool *pool) pthread_mutex_destroy(&pool->mutex); if (pool->free_cb) pool->free_cb(pool->opaque); - av_free(pool); + av_free(get_refcount(pool)); } static void pool_free_entry(FFRefStructPool *pool, RefCount *ref) @@ -278,13 +278,17 @@ void *ff_refstruct_pool_get(FFRefStructPool *pool) return ret; } -void ff_refstruct_pool_uninit(FFRefStructPool **poolp) +static void pool_unref(void *ref) { - FFRefStructPool *pool = *poolp; - RefCount *entry; + FFRefStructPool *pool = get_userdata(ref); + if (atomic_fetch_sub_explicit(&pool->refcount, 1, memory_order_acq_rel) == 1) + pool_free(pool); +} - if (!pool) - return; +static void refstruct_pool_uninit(FFRefStructOpaque unused, void *obj) +{ + FFRefStructPool *pool = obj; + RefCount *entry; pthread_mutex_lock(&pool->mutex); av_assert1(!pool->uninited); @@ -298,11 +302,6 @@ void ff_refstruct_pool_uninit(FFRefStructPool **poolp) pool_free_entry(pool, entry); entry = next; } - - if (atomic_fetch_sub_explicit(&pool->refcount, 1, memory_order_acq_rel) == 1) - pool_free(pool); - - *poolp = NULL; } FFRefStructPool *ff_refstruct_pool_alloc(size_t size, unsigned flags) @@ -317,11 +316,13 @@ FFRefStructPool *ff_refstruct_pool_alloc_ext_c(size_t size, unsigned flags, void (*free_entry_cb)(FFRefStructOpaque opaque, void *obj), void (*free_cb)(FFRefStructOpaque opaque)) { - FFRefStructPool *pool = av_mallocz(sizeof(*pool)); + FFRefStructPool *pool = ff_refstruct_alloc_ext(sizeof(*pool), 0, NULL, + refstruct_pool_uninit); int err; if (!pool) return NULL; + get_refcount(pool)->free = pool_unref; pool->size = size; pool->opaque = opaque; @@ -348,7 +349,9 @@ FFRefStructPool *ff_refstruct_pool_alloc_ext_c(size_t size, unsigned flags, err = pthread_mutex_init(&pool->mutex, NULL); if (err) { - av_free(pool); + // Don't call ff_refstruct_uninit() on pool, as it hasn't been properly + // set up and is just a POD right now. + av_free(get_refcount(pool)); return NULL; } return pool; diff --git a/libavcodec/refstruct.h b/libavcodec/refstruct.h index ce3830977f..d525be61e8 100644 --- a/libavcodec/refstruct.h +++ b/libavcodec/refstruct.h @@ -285,6 +285,9 @@ void *ff_refstruct_pool_get(FFRefStructPool *pool); * @param poolp pointer to a pointer to either NULL or a pool to be freed. * `*poolp` will be set to NULL. */ -void ff_refstruct_pool_uninit(FFRefStructPool **poolp); +static inline void ff_refstruct_pool_uninit(FFRefStructPool **poolp) +{ + ff_refstruct_unref(poolp); +} #endif /* AVCODEC_REFSTRUCT_H */ -- 2.34.1 _______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org https://ffmpeg.org/mailman/listinfo/ffmpeg-devel To unsubscribe, visit link above, or email ffmpeg-devel-requ...@ffmpeg.org with subject "unsubscribe".