vlc | branch: master | Rémi Denis-Courmont <[email protected]> | Wed Jul 24 23:25:10 2013 +0300| [4f96c31975d02c5341d049d3d2b3cbd5ee8881eb] | committer: Rémi Denis-Courmont
avcodec: pass AVFrame.opaque to hwaccel release callback With the reference counting stuff, the AVFrame structure is gone or unreachable by the time the release function is called. > http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=4f96c31975d02c5341d049d3d2b3cbd5ee8881eb --- modules/codec/avcodec/dxva2.c | 4 ++-- modules/codec/avcodec/hwdummy.c | 4 ++-- modules/codec/avcodec/va.h | 8 +++++--- modules/codec/avcodec/vaapi.c | 4 ++-- modules/codec/avcodec/vda.c | 5 ++++- modules/codec/avcodec/video.c | 10 +++++----- modules/hw/vdpau/avcodec.c | 4 ++-- 7 files changed, 22 insertions(+), 17 deletions(-) diff --git a/modules/codec/avcodec/dxva2.c b/modules/codec/avcodec/dxva2.c index 184af9e..d33b571 100644 --- a/modules/codec/avcodec/dxva2.c +++ b/modules/codec/avcodec/dxva2.c @@ -471,9 +471,9 @@ static int Get(vlc_va_t *external, AVFrame *ff) ff->opaque = surface; return VLC_SUCCESS; } -static void Release(AVFrame *ff) +static void Release(void *opaque) { - vlc_va_surface_t *surface = ff->opaque; + vlc_va_surface_t *surface = opaque; surface->refcount--; } diff --git a/modules/codec/avcodec/hwdummy.c b/modules/codec/avcodec/hwdummy.c index 95d95e5..ead7ccd 100644 --- a/modules/codec/avcodec/hwdummy.c +++ b/modules/codec/avcodec/hwdummy.c @@ -69,9 +69,9 @@ static int Lock(vlc_va_t *va, AVFrame *ff) return VLC_SUCCESS; } -static void Unlock(AVFrame *ff) +static void Unlock(void *opaque) { - assert((uintptr_t)ff->opaque == SURFACE_MAGIC); + assert((uintptr_t)opaque == SURFACE_MAGIC); } static VdpStatus Render(VdpDecoder decoder, VdpVideoSurface target, diff --git a/modules/codec/avcodec/va.h b/modules/codec/avcodec/va.h index d297114..128942c 100644 --- a/modules/codec/avcodec/va.h +++ b/modules/codec/avcodec/va.h @@ -38,7 +38,7 @@ struct vlc_va_t { int (*setup)(vlc_va_t *, void **hw, vlc_fourcc_t *output, int width, int height); int (*get)(vlc_va_t *, AVFrame *frame); - void (*release)(AVFrame *frame); + void (*release)(void *opaque); int (*extract)(vlc_va_t *, picture_t *dst, AVFrame *src); }; @@ -86,15 +86,17 @@ static inline int vlc_va_Get(vlc_va_t *va, AVFrame *frame) * Releases a hardware surface from a libavcodec frame. * The surface has been previously allocated with vlc_va_Get(). * + * @param opaque opaque data pointer of the AVFrame passed to vlc_va_Get(). + * * @note This function needs not be reentrant. However it may be called * concurrently with vlc_va_Get() and/or vlc_va_Extract() from other threads * and other frames. * * @param frame libavcodec frame previously allocated by vlc_va_Get() */ -static inline void vlc_va_Release(vlc_va_t *va, AVFrame *frame) +static inline void vlc_va_Release(vlc_va_t *va, void *opaque) { - va->release(frame); + va->release(opaque); } /** diff --git a/modules/codec/avcodec/vaapi.c b/modules/codec/avcodec/vaapi.c index 7068ce4..df3fc4a 100644 --- a/modules/codec/avcodec/vaapi.c +++ b/modules/codec/avcodec/vaapi.c @@ -518,9 +518,9 @@ static int Get( vlc_va_t *va, AVFrame *p_ff ) return VLC_SUCCESS; } -static void Release( AVFrame *p_ff ) +static void Release( void *opaque ) { - vlc_va_surface_t *p_surface = p_ff->opaque; + vlc_va_surface_t *p_surface = opaque; vlc_mutex_lock( p_surface->p_lock ); p_surface->i_refcount--; diff --git a/modules/codec/avcodec/vda.c b/modules/codec/avcodec/vda.c index 396ba87..e0f293b 100644 --- a/modules/codec/avcodec/vda.c +++ b/modules/codec/avcodec/vda.c @@ -254,12 +254,15 @@ static int Extract( vlc_va_t *external, picture_t *p_picture, AVFrame *p_ff ) return VLC_SUCCESS; } -static void Release( AVFrame *p_ff ) +static void Release( void *opaque ) { + assert( opaque == NULL ); +#if 0 CVPixelBufferRef cv_buffer = ( CVPixelBufferRef )p_ff->data[3]; if ( cv_buffer ) CVPixelBufferRelease( cv_buffer ); +#endif } static void Close( vlc_va_t *external ) diff --git a/modules/codec/avcodec/video.c b/modules/codec/avcodec/video.c index 967cb2e..d6a966f 100644 --- a/modules/codec/avcodec/video.c +++ b/modules/codec/avcodec/video.c @@ -897,14 +897,14 @@ static void ffmpeg_CopyPicture( decoder_t *p_dec, typedef struct { vlc_va_t *va; - AVFrame *frame; + void *opaque; } lavc_hw_ref_t; static void lavc_va_ReleaseFrame(void *opaque, uint8_t *data) { lavc_hw_ref_t *ref = opaque; - vlc_va_Release(ref->va, ref->frame); + vlc_va_Release(ref->va, ref->opaque); free(ref); (void) data; } @@ -931,11 +931,11 @@ static int lavc_va_GetFrame(struct AVCodecContext *ctx, AVFrame *frame, lavc_hw_ref_t *ref = malloc(sizeof (*ref)); if (unlikely(ref == NULL)) { - vlc_va_Release(va, frame); + vlc_va_Release(va, frame->opaque); return -1; } ref->va = va; - ref->frame = frame; + ref->opaque = frame->opaque; frame->buf[0] = av_buffer_create(frame->data[0], 0, lavc_va_ReleaseFrame, ref, 0); @@ -1262,7 +1262,7 @@ static void ffmpeg_ReleaseFrameBuf( struct AVCodecContext *p_context, decoder_sys_t *p_sys = p_dec->p_sys; if( p_sys->p_va ) - vlc_va_Release( p_sys->p_va, p_ff_pic ); + vlc_va_Release( p_sys->p_va, p_ff_pic->opaque ); else if( p_ff_pic->opaque ) decoder_UnlinkPicture( p_dec, (picture_t*)p_ff_pic->opaque); else if( p_ff_pic->type == FF_BUFFER_TYPE_INTERNAL ) diff --git a/modules/hw/vdpau/avcodec.c b/modules/hw/vdpau/avcodec.c index 12af892..8c027d3 100644 --- a/modules/hw/vdpau/avcodec.c +++ b/modules/hw/vdpau/avcodec.c @@ -91,9 +91,9 @@ static int Lock(vlc_va_t *va, AVFrame *ff) return VLC_SUCCESS; } -static void Unlock(AVFrame *ff) +static void Unlock(void *opaque) { - vlc_vdp_video_field_t *field = ff->opaque; + vlc_vdp_video_field_t *field = opaque; assert(field != NULL); field->destroy(field); _______________________________________________ vlc-commits mailing list [email protected] http://mailman.videolan.org/listinfo/vlc-commits
