[vlc-devel] [RFC PATCH 3/6] lib: move track in media_track.c

Thomas Guillem thomas at gllm.fr
Tue Jun 2 22:02:07 CEST 2020


And use a trackpriv struct to hold the specific audio/video/sub part, removing
an extra alloc usage.
---
 lib/Makefile.am      |   1 +
 lib/media.c          |  85 ++----------------------------
 lib/media_internal.h |  17 ++++++
 lib/media_track.c    | 120 +++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 143 insertions(+), 80 deletions(-)
 create mode 100644 lib/media_track.c

diff --git a/lib/Makefile.am b/lib/Makefile.am
index 2e397cf7d4..15763fb97a 100644
--- a/lib/Makefile.am
+++ b/lib/Makefile.am
@@ -47,6 +47,7 @@ libvlc_la_SOURCES = \
 	audio.c \
 	event.c \
 	media.c \
+	media_track.c \
 	media_player.c \
 	media_list.c \
 	media_list_path.h \
diff --git a/lib/media.c b/lib/media.c
index fbf37f3fac..8d663bc48b 100644
--- a/lib/media.c
+++ b/lib/media.c
@@ -875,80 +875,20 @@ libvlc_media_tracks_get( libvlc_media_t *p_md, libvlc_media_track_t *** pp_es )
     /* Fill array */
     for( int i = 0; i < i_es; i++ )
     {
-        libvlc_media_track_t *p_mes = calloc( 1, sizeof(*p_mes) );
-        if ( p_mes )
-        {
-            p_mes->audio = malloc( __MAX(__MAX(sizeof(*p_mes->audio),
-                                               sizeof(*p_mes->video)),
-                                               sizeof(*p_mes->subtitle)) );
-        }
-        if ( !p_mes || !p_mes->audio )
+        libvlc_media_trackpriv_t *p_trackpriv = calloc( 1, sizeof(*p_trackpriv) );
+        if ( !p_trackpriv )
         {
             libvlc_media_tracks_release( *pp_es, i_es );
             *pp_es = NULL;
-            free( p_mes );
             vlc_mutex_unlock( &p_input_item->lock );
             return 0;
         }
+        libvlc_media_track_t *p_mes = &p_trackpriv->t;
         (*pp_es)[i] = p_mes;
 
         const es_format_t *p_es = p_input_item->es[i];
 
-        p_mes->i_codec = p_es->i_codec;
-        p_mes->i_original_fourcc = p_es->i_original_fourcc;
-        p_mes->i_id = p_es->i_id;
-
-        p_mes->i_profile = p_es->i_profile;
-        p_mes->i_level = p_es->i_level;
-
-        p_mes->i_bitrate = p_es->i_bitrate;
-        p_mes->psz_language = p_es->psz_language != NULL ? strdup(p_es->psz_language) : NULL;
-        p_mes->psz_description = p_es->psz_description != NULL ? strdup(p_es->psz_description) : NULL;
-
-        switch(p_es->i_cat)
-        {
-        case UNKNOWN_ES:
-        default:
-            p_mes->i_type = libvlc_track_unknown;
-            break;
-        case VIDEO_ES:
-            p_mes->i_type = libvlc_track_video;
-            p_mes->video->i_height = p_es->video.i_visible_height;
-            p_mes->video->i_width = p_es->video.i_visible_width;
-            p_mes->video->i_sar_num = p_es->video.i_sar_num;
-            p_mes->video->i_sar_den = p_es->video.i_sar_den;
-            p_mes->video->i_frame_rate_num = p_es->video.i_frame_rate;
-            p_mes->video->i_frame_rate_den = p_es->video.i_frame_rate_base;
-
-            assert( p_es->video.orientation >= ORIENT_TOP_LEFT &&
-                    p_es->video.orientation <= ORIENT_RIGHT_BOTTOM );
-            p_mes->video->i_orientation = (int) p_es->video.orientation;
-
-            assert( ( p_es->video.projection_mode >= PROJECTION_MODE_RECTANGULAR &&
-                    p_es->video.projection_mode <= PROJECTION_MODE_EQUIRECTANGULAR ) ||
-                    ( p_es->video.projection_mode == PROJECTION_MODE_CUBEMAP_LAYOUT_STANDARD ) );
-            p_mes->video->i_projection = (int) p_es->video.projection_mode;
-
-            p_mes->video->pose.f_yaw = p_es->video.pose.yaw;
-            p_mes->video->pose.f_pitch = p_es->video.pose.pitch;
-            p_mes->video->pose.f_roll = p_es->video.pose.roll;
-            p_mes->video->pose.f_field_of_view = p_es->video.pose.fov;
-
-            assert( p_es->video.multiview_mode >= MULTIVIEW_2D &&
-                    p_es->video.multiview_mode <= MULTIVIEW_STEREO_CHECKERBOARD );
-            p_mes->video->i_multiview = (int) p_es->video.multiview_mode;
-            break;
-        case AUDIO_ES:
-            p_mes->i_type = libvlc_track_audio;
-            p_mes->audio->i_channels = p_es->audio.i_channels;
-            p_mes->audio->i_rate = p_es->audio.i_rate;
-            break;
-        case SPU_ES:
-            p_mes->i_type = libvlc_track_text;
-            p_mes->subtitle->psz_encoding = p_es->subs.psz_encoding != NULL ?
-                                            strdup(p_es->subs.psz_encoding) : NULL;
-            break;
-        }
+        libvlc_media_trackpriv_from_es( p_trackpriv, p_es );
     }
 
     vlc_mutex_unlock( &p_input_item->lock );
@@ -971,22 +911,7 @@ void libvlc_media_tracks_release( libvlc_media_track_t **p_tracks, unsigned i_co
     {
         if ( !p_tracks[i] )
             continue;
-        free( p_tracks[i]->psz_language );
-        free( p_tracks[i]->psz_description );
-        switch( p_tracks[i]->i_type )
-        {
-        case libvlc_track_audio:
-            break;
-        case libvlc_track_video:
-            break;
-        case libvlc_track_text:
-            free( p_tracks[i]->subtitle->psz_encoding );
-            break;
-        case libvlc_track_unknown:
-        default:
-            break;
-        }
-        free( p_tracks[i]->audio );
+        libvlc_media_track_clean( p_tracks[i] );
         free( p_tracks[i] );
     }
     free( p_tracks );
diff --git a/lib/media_internal.h b/lib/media_internal.h
index 89adfd73ff..2aa944806a 100644
--- a/lib/media_internal.h
+++ b/lib/media_internal.h
@@ -73,4 +73,21 @@ libvlc_track_type_to_escat( libvlc_track_type_t i_type )
     }
 }
 
+typedef struct libvlc_media_trackpriv_t
+{
+    libvlc_media_track_t t;
+    union {
+        libvlc_audio_track_t audio;
+        libvlc_video_track_t video;
+        libvlc_subtitle_track_t subtitle;
+    };
+} libvlc_media_trackpriv_t;
+
+void
+libvlc_media_trackpriv_from_es( libvlc_media_trackpriv_t *trackpriv,
+                                const es_format_t *es  );
+
+void
+libvlc_media_track_clean( libvlc_media_track_t *track );
+
 #endif
diff --git a/lib/media_track.c b/lib/media_track.c
new file mode 100644
index 0000000000..91b4d2d3b1
--- /dev/null
+++ b/lib/media_track.c
@@ -0,0 +1,120 @@
+/*****************************************************************************
+ * media_track.c: Libvlc API media track
+ *****************************************************************************
+ * Copyright (C) 2020 VLC authors and VideoLAN
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as published by
+ * the Free Software Foundation; either version 2.1 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#ifdef HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include <assert.h>
+#include <errno.h>
+
+#include <vlc/libvlc.h>
+#include <vlc/libvlc_picture.h>
+#include <vlc/libvlc_media.h>
+#include <vlc/libvlc_events.h>
+
+#include "libvlc_internal.h"
+#include "media_internal.h"
+
+void
+libvlc_media_trackpriv_from_es( libvlc_media_trackpriv_t *trackpriv,
+                                const es_format_t *es  )
+{
+    libvlc_media_track_t *track = &trackpriv->t;
+
+    track->i_codec = es->i_codec;
+    track->i_original_fourcc = es->i_original_fourcc;
+    track->i_id = es->i_id;
+
+    track->i_profile = es->i_profile;
+    track->i_level = es->i_level;
+
+    track->i_bitrate = es->i_bitrate;
+    track->psz_language = es->psz_language != NULL ? strdup(es->psz_language) : NULL;
+    track->psz_description = es->psz_description != NULL ? strdup(es->psz_description) : NULL;
+
+    switch( es->i_cat )
+    {
+    case UNKNOWN_ES:
+    default:
+        track->i_type = libvlc_track_unknown;
+        break;
+    case VIDEO_ES:
+        track->video = &trackpriv->video;
+        track->i_type = libvlc_track_video;
+        track->video->i_height = es->video.i_visible_height;
+        track->video->i_width = es->video.i_visible_width;
+        track->video->i_sar_num = es->video.i_sar_num;
+        track->video->i_sar_den = es->video.i_sar_den;
+        track->video->i_frame_rate_num = es->video.i_frame_rate;
+        track->video->i_frame_rate_den = es->video.i_frame_rate_base;
+
+        assert( es->video.orientation >= ORIENT_TOP_LEFT &&
+                es->video.orientation <= ORIENT_RIGHT_BOTTOM );
+        track->video->i_orientation = (int) es->video.orientation;
+
+        assert( ( es->video.projection_mode >= PROJECTION_MODE_RECTANGULAR &&
+                es->video.projection_mode <= PROJECTION_MODE_EQUIRECTANGULAR ) ||
+                ( es->video.projection_mode == PROJECTION_MODE_CUBEMAP_LAYOUT_STANDARD ) );
+        track->video->i_projection = (int) es->video.projection_mode;
+
+        track->video->pose.f_yaw = es->video.pose.yaw;
+        track->video->pose.f_pitch = es->video.pose.pitch;
+        track->video->pose.f_roll = es->video.pose.roll;
+        track->video->pose.f_field_of_view = es->video.pose.fov;
+
+        assert( es->video.multiview_mode >= MULTIVIEW_2D &&
+                es->video.multiview_mode <= MULTIVIEW_STEREO_CHECKERBOARD );
+        track->video->i_multiview = (int) es->video.multiview_mode;
+        break;
+    case AUDIO_ES:
+        track->audio = &trackpriv->audio;
+        track->i_type = libvlc_track_audio;
+        track->audio->i_channels = es->audio.i_channels;
+        track->audio->i_rate = es->audio.i_rate;
+        break;
+    case SPU_ES:
+        track->subtitle = &trackpriv->subtitle;
+        track->i_type = libvlc_track_text;
+        track->subtitle->psz_encoding = es->subs.psz_encoding != NULL ?
+                                        strdup(es->subs.psz_encoding) : NULL;
+        break;
+    }
+}
+
+void
+libvlc_media_track_clean( libvlc_media_track_t *track )
+{
+    free( track->psz_language );
+    free( track->psz_description );
+    switch( track->i_type )
+    {
+    case libvlc_track_audio:
+        break;
+    case libvlc_track_video:
+        break;
+    case libvlc_track_text:
+        free( track->subtitle->psz_encoding );
+        break;
+    case libvlc_track_unknown:
+    default:
+        break;
+    }
+}
-- 
2.20.1



More information about the vlc-devel mailing list