[vlc-commits] audiotrack: add AudioTrack_Reset

Thomas Guillem git at videolan.org
Fri Jul 3 10:43:22 CEST 2015


vlc | branch: master | Thomas Guillem <thomas at gllm.fr> | Fri Jul  3 09:47:54 2015 +0200| [b83d1386d7ef2817a83c41dde370fefd5a1aaa3a] | committer: Thomas Guillem

audiotrack: add AudioTrack_Reset

Refactor AudioTrack creation, and add a function that destroy and recreate an
AudioTrack object using the previous arguments.

> http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=b83d1386d7ef2817a83c41dde370fefd5a1aaa3a
---

 modules/audio_output/audiotrack.c |  139 ++++++++++++++++++++++++-------------
 1 file changed, 89 insertions(+), 50 deletions(-)

diff --git a/modules/audio_output/audiotrack.c b/modules/audio_output/audiotrack.c
index 29c77dd..07ca81e 100644
--- a/modules/audio_output/audiotrack.c
+++ b/modules/audio_output/audiotrack.c
@@ -61,6 +61,13 @@ struct aout_sys_t {
     jobject p_bytebuffer; /* ByteBuffer ref (for WriteV21) */
     audio_sample_format_t fmt; /* fmt setup by Start */
 
+    struct {
+        unsigned int i_rate;
+        int i_channel_config;
+        int i_format;
+        int i_size;
+    } audiotrack_args;
+
     /* Used by AudioTrack_GetPosition / AudioTrack_getPlaybackHeadPosition */
     struct {
         uint64_t i_initial;
@@ -727,19 +734,69 @@ AudioTrack_GetChanOrder( uint16_t i_physical_channels, uint32_t p_chans_out[] )
 }
 
 /**
+ * Create an Android AudioTrack.
+ * returns -1 on error, 0 on success.
+ */
+static int
+AudioTrack_New( JNIEnv *env, audio_output_t *p_aout, unsigned int i_rate,
+                int i_channel_config, int i_format, int i_size )
+{
+    aout_sys_t *p_sys = p_aout->sys;
+    jobject p_audiotrack = JNI_AT_NEW( jfields.AudioManager.STREAM_MUSIC,
+                                       i_rate, i_channel_config, i_format,
+                                       i_size, jfields.AudioTrack.MODE_STREAM );
+    if( CHECK_AT_EXCEPTION( "AudioTrack<init>" ) || !p_audiotrack )
+    {
+        msg_Warn( p_aout, "AudioTrack Init failed" ) ;
+        return -1;
+    }
+    if( JNI_CALL_INT( p_audiotrack, jfields.AudioTrack.getState )
+        != jfields.AudioTrack.STATE_INITIALIZED )
+    {
+        JNI_CALL_VOID( p_audiotrack, jfields.AudioTrack.release );
+        (*env)->DeleteLocalRef( env, p_audiotrack );
+        msg_Err( p_aout, "AudioTrack getState failed" );
+        return -1;
+    }
+
+    p_sys->p_audiotrack = (*env)->NewGlobalRef( env, p_audiotrack );
+    (*env)->DeleteLocalRef( env, p_audiotrack );
+    if( !p_sys->p_audiotrack )
+        return -1;
+
+    return 0;
+}
+
+/**
+ * Destroy and recreate an Android AudioTrack using the same arguments.
+ * returns -1 on error, 0 on success.
+ */
+static int
+AudioTrack_Reset( JNIEnv *env, audio_output_t *p_aout )
+{
+    aout_sys_t *p_sys = p_aout->sys;
+
+    JNI_AT_CALL_VOID( release );
+    (*env)->DeleteGlobalRef( env, p_sys->p_audiotrack );
+    return AudioTrack_New( env, p_aout, p_sys->audiotrack_args.i_rate,
+                           p_sys->audiotrack_args.i_channel_config,
+                           p_sys->audiotrack_args.i_format,
+                           p_sys->audiotrack_args.i_size );
+}
+
+/**
  * Configure and create an Android AudioTrack.
- * returns NULL on configuration error
+ * returns -1 on configuration error, 0 on success.
  */
-static jobject
-AudioTrack_New( JNIEnv *env, audio_output_t *p_aout,
-                unsigned int i_rate,
-                vlc_fourcc_t i_vlc_format,
-                uint16_t i_physical_channels,
-                int i_bytes_per_frame,
-                int *p_audiotrack_size )
+static int
+AudioTrack_Create( JNIEnv *env, audio_output_t *p_aout,
+                   unsigned int i_rate,
+                   vlc_fourcc_t i_vlc_format,
+                   uint16_t i_physical_channels,
+                   int i_bytes_per_frame )
 {
+    aout_sys_t *p_sys = p_aout->sys;
     int i_size, i_min_buffer_size, i_channel_config, i_format;
-    jobject p_audiotrack;
 
     switch( i_vlc_format )
     {
@@ -785,7 +842,7 @@ AudioTrack_New( JNIEnv *env, audio_output_t *p_aout,
     if( i_min_buffer_size <= 0 )
     {
         msg_Warn( p_aout, "getMinBufferSize returned an invalid size" ) ;
-        return NULL;
+        return -1;
     }
     if( i_vlc_format == VLC_CODEC_SPDIFB )
         i_size = ( i_min_buffer_size / AOUT_SPDIF_SIZE + 1 ) * AOUT_SPDIF_SIZE;
@@ -805,25 +862,16 @@ AudioTrack_New( JNIEnv *env, audio_output_t *p_aout,
     }
 
     /* create AudioTrack object */
-    p_audiotrack = JNI_AT_NEW( jfields.AudioManager.STREAM_MUSIC, i_rate,
-                               i_channel_config, i_format, i_size,
-                               jfields.AudioTrack.MODE_STREAM );
-    if( CHECK_AT_EXCEPTION( "AudioTrack<init>" ) || !p_audiotrack )
-    {
-        msg_Warn( p_aout, "AudioTrack Init failed" ) ;
-        return NULL;
-    }
-    if( JNI_CALL_INT( p_audiotrack, jfields.AudioTrack.getState )
-        != jfields.AudioTrack.STATE_INITIALIZED )
-    {
-        JNI_CALL_VOID( p_audiotrack, jfields.AudioTrack.release );
-        (*env)->DeleteLocalRef( env, p_audiotrack );
-        msg_Err( p_aout, "AudioTrack getState failed" );
-        return NULL;
-    }
-    *p_audiotrack_size = i_size;
+    if( AudioTrack_New( env, p_aout, i_rate, i_channel_config,
+                        i_format , i_size ) != 0 )
+        return -1;
 
-    return p_audiotrack;
+    p_sys->audiotrack_args.i_rate = i_rate;
+    p_sys->audiotrack_args.i_channel_config = i_channel_config;
+    p_sys->audiotrack_args.i_format = i_format;
+    p_sys->audiotrack_args.i_size = i_size;
+
+    return 0;
 }
 
 static int
@@ -831,9 +879,8 @@ Start( audio_output_t *p_aout, audio_sample_format_t *restrict p_fmt )
 {
     aout_sys_t *p_sys = p_aout->sys;
     JNIEnv *env;
-    jobject p_audiotrack = NULL;
-    int i_nb_channels, i_max_channels, i_audiotrack_size, i_bytes_per_frame,
-        i_native_rate = 0;
+    int i_nb_channels, i_max_channels, i_bytes_per_frame, i_native_rate = 0,
+        i_ret;
     unsigned int i_rate;
     bool b_spdif;
 
@@ -916,15 +963,13 @@ Start( audio_output_t *p_aout, audio_sample_format_t *restrict p_fmt )
                                         : (unsigned int) i_native_rate;
 
         /* Try to create an AudioTrack with the most advanced channel and
-         * format configuration. If AudioTrack_New fails, try again with a less
-         * advanced format (PCM S16N). If it fails again, try again with Stereo
-         * channels. */
-        p_audiotrack = AudioTrack_New( env, p_aout, i_rate,
-                                       p_sys->fmt.i_format,
-                                       p_sys->fmt.i_physical_channels,
-                                       i_bytes_per_frame,
-                                       &i_audiotrack_size );
-        if( !p_audiotrack )
+         * format configuration. If AudioTrack_Create fails, try again with a
+         * less advanced format (PCM S16N). If it fails again, try again with
+         * Stereo channels. */
+        i_ret = AudioTrack_Create( env, p_aout, i_rate, p_sys->fmt.i_format,
+                                   p_sys->fmt.i_physical_channels,
+                                   i_bytes_per_frame );
+        if( i_ret != 0 )
         {
             if( p_sys->fmt.i_format == VLC_CODEC_SPDIFB )
             {
@@ -950,14 +995,9 @@ Start( audio_output_t *p_aout, audio_sample_format_t *restrict p_fmt )
             else
                 break;
         }
-    } while( !p_audiotrack );
+    } while( i_ret != 0 );
 
-    if( !p_audiotrack )
-        return VLC_EGENERIC;
-
-    p_sys->p_audiotrack = (*env)->NewGlobalRef( env, p_audiotrack );
-    (*env)->DeleteLocalRef( env, p_audiotrack );
-    if( !p_sys->p_audiotrack )
+    if( i_ret != 0 )
         return VLC_EGENERIC;
 
     p_sys->fmt.i_rate = i_rate;
@@ -980,7 +1020,7 @@ Start( audio_output_t *p_aout, audio_sample_format_t *restrict p_fmt )
                                       p_sys->p_chan_table );
         p_sys->i_bytes_per_frame = i_bytes_per_frame;
     }
-    p_sys->i_max_audiotrack_samples = BYTES_TO_FRAMES( i_audiotrack_size );
+    p_sys->i_max_audiotrack_samples = BYTES_TO_FRAMES( p_sys->audiotrack_args.i_size );
 
 #ifdef AUDIOTRACK_HW_LATENCY
     if( jfields.AudioTimestamp.clazz )
@@ -1282,8 +1322,7 @@ AudioTrack_Play( JNIEnv *env, audio_output_t *p_aout,
         {
             msg_Warn( p_aout, "ERROR_DEAD_OBJECT: "
                               "try recreating AudioTrack" );
-            Stop( p_aout );
-            i_ret = Start( p_aout, &p_sys->fmt );
+            i_ret = AudioTrack_Reset( env, p_aout );
         } else
         {
             const char *str;



More information about the vlc-commits mailing list