[vlc-devel] [PATCH 4/6] lib: media_track: add a refcount
Thomas Guillem
thomas at gllm.fr
Mon Jun 15 23:10:05 CEST 2020
libvlc_media_track_hold() can be used in order to have a track outliving the
tracklist.
---
include/vlc/libvlc_media_track.h | 26 +++++++++++++++++++++-----
lib/libvlc.sym | 1 +
lib/media_internal.h | 2 ++
lib/media_track.c | 29 +++++++++++++++++++----------
4 files changed, 43 insertions(+), 15 deletions(-)
diff --git a/include/vlc/libvlc_media_track.h b/include/vlc/libvlc_media_track.h
index 46bbbaf4bd6..f1da2478714 100644
--- a/include/vlc/libvlc_media_track.h
+++ b/include/vlc/libvlc_media_track.h
@@ -202,17 +202,33 @@ libvlc_media_tracklist_at( libvlc_media_tracklist_t *list, size_t index );
LIBVLC_API void
libvlc_media_tracklist_delete( libvlc_media_tracklist_t *list );
+
+/**
+ * Hold a single track reference
+ *
+ * \version LibVLC 4.0.0 and later.
+ *
+ * This function can be used to hold a track from a tracklist. In that case,
+ * the track can outlive its tracklist.
+ *
+ * \param track valid track
+ * \return the same track, need to be released with libvlc_media_track_release()
+ */
+LIBVLC_API libvlc_media_track_t *
+libvlc_media_track_hold( libvlc_media_track_t * );
+
/**
* Release a single track
*
* \version LibVLC 4.0.0 and later.
*
- * \warning Don't release tracks from a tracklist with this function. Tracks
- * from a tracklist are released alongside the list with
- * libvlc_media_tracklist_delete()
+ * \warning Tracks from a tracklist are released alongside the list with
+ * libvlc_media_tracklist_delete().
*
- * \see libvlc_media_player_get_selected_track
- * \see libvlc_media_player_get_track_from_id
+ * \note You only need to release tracks previously held with
+ * libvlc_media_track_hold() or returned by
+ * libvlc_media_player_get_selected_track() and
+ * libvlc_media_player_get_track_from_id()
*
* \param track valid track
*/
diff --git a/lib/libvlc.sym b/lib/libvlc.sym
index 739f7d444e8..3753ddb89be 100644
--- a/lib/libvlc.sym
+++ b/lib/libvlc.sym
@@ -86,6 +86,7 @@ libvlc_media_thumbnail_request_by_time
libvlc_media_thumbnail_request_by_pos
libvlc_media_thumbnail_request_cancel
libvlc_media_thumbnail_request_destroy
+libvlc_media_track_hold
libvlc_media_track_release
libvlc_media_tracklist_at
libvlc_media_tracklist_count
diff --git a/lib/media_internal.h b/lib/media_internal.h
index 8acb116e8fe..5f43a2b3de4 100644
--- a/lib/media_internal.h
+++ b/lib/media_internal.h
@@ -30,6 +30,7 @@
#include <vlc_common.h>
#include <vlc_input.h>
#include <vlc_player.h>
+#include <vlc_atomic.h>
struct libvlc_media_t
{
@@ -83,6 +84,7 @@ typedef struct libvlc_media_trackpriv_t
libvlc_subtitle_track_t subtitle;
};
vlc_es_id_t *es_id;
+ vlc_atomic_rc_t rc;
} libvlc_media_trackpriv_t;
static inline const libvlc_media_trackpriv_t *
diff --git a/lib/media_track.c b/lib/media_track.c
index 515970a5319..bca82f384b6 100644
--- a/lib/media_track.c
+++ b/lib/media_track.c
@@ -119,6 +119,7 @@ libvlc_media_trackpriv_new( void )
return NULL;
trackpriv->es_id = NULL;
+ vlc_atomic_rc_init( &trackpriv->rc );
return trackpriv;
}
@@ -143,15 +144,28 @@ libvlc_media_track_clean( libvlc_media_track_t *track )
}
}
+libvlc_media_track_t *
+libvlc_media_track_hold( libvlc_media_track_t *track )
+{
+ libvlc_media_trackpriv_t *trackpriv =
+ container_of( track, libvlc_media_trackpriv_t, t );
+ vlc_atomic_rc_inc( &trackpriv->rc );
+ return track;
+}
+
void
libvlc_media_track_release( libvlc_media_track_t *track )
{
libvlc_media_trackpriv_t *trackpriv =
container_of( track, libvlc_media_trackpriv_t, t );
- libvlc_media_track_clean( track );
- if( trackpriv->es_id )
- vlc_es_id_Release( trackpriv->es_id );
- free( trackpriv );
+
+ if( vlc_atomic_rc_dec( &trackpriv->rc ) )
+ {
+ libvlc_media_track_clean( track );
+ if( trackpriv->es_id )
+ vlc_es_id_Release( trackpriv->es_id );
+ free( trackpriv );
+ }
}
static libvlc_media_tracklist_t *
@@ -282,12 +296,7 @@ libvlc_media_tracklist_delete( libvlc_media_tracklist_t *list )
for( size_t i = 0; i < list->count; ++i )
{
libvlc_media_trackpriv_t *trackpriv = list->tracks[i];
- libvlc_media_track_clean( &trackpriv->t );
-
- if( trackpriv->es_id != NULL )
- vlc_es_id_Release( trackpriv->es_id );
-
- free( trackpriv );
+ libvlc_media_track_release( &trackpriv->t );
}
free( list );
}
--
2.20.1
More information about the vlc-devel
mailing list