[vlc-commits] aout_PacketNext: restore feedback to input for resampling

Rémi Denis-Courmont git at videolan.org
Sat Aug 6 21:53:23 CEST 2011


vlc | branch: master | Rémi Denis-Courmont <remi at remlab.net> | Sat Aug  6 22:53:01 2011 +0300| [3cfd772b3243f1354541f373d57c7f00a979cd00] | committer: Rémi Denis-Courmont

aout_PacketNext: restore feedback to input for resampling

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

 include/vlc_aout.h        |    2 ++
 src/audio_output/dec.c    |   45 +++++++++++++++++++++++++++++++++++++++++++++
 src/audio_output/output.c |   29 +++++++++++++++++------------
 src/libvlccore.sym        |    1 +
 4 files changed, 65 insertions(+), 12 deletions(-)

diff --git a/include/vlc_aout.h b/include/vlc_aout.h
index f5eaafb..b3d4954 100644
--- a/include/vlc_aout.h
+++ b/include/vlc_aout.h
@@ -244,6 +244,8 @@ VLC_API void aout_VolumeSoftInit( audio_output_t * );
 VLC_API void aout_VolumeHardInit( audio_output_t *, aout_volume_cb );
 VLC_API void aout_VolumeHardSet( audio_output_t *, float, bool );
 
+VLC_API void aout_TimeReport(audio_output_t *, mtime_t);
+
 VLC_API int aout_ChannelsRestart( vlc_object_t *, const char *, vlc_value_t, vlc_value_t, void * );
 
 /* */
diff --git a/src/audio_output/dec.c b/src/audio_output/dec.c
index 0f3adda..fb56f10 100644
--- a/src/audio_output/dec.c
+++ b/src/audio_output/dec.c
@@ -311,3 +311,48 @@ bool aout_DecIsEmpty (audio_output_t *aout)
     aout_unlock (aout);
     return end_date == VLC_TS_INVALID || end_date <= mdate();
 }
+
+/**
+ * Notifies the audio input of the drift from the requested audio
+ * playback timestamp (@ref block_t.i_pts) to the anticipated playback time
+ * as reported by the audio output hardware.
+ * Depending on the drift amplitude, the input core may ignore the drift
+ * trigger upsampling or downsampling, or even discard samples.
+ * Future VLC versions may instead adjust the input decoding speed.
+ *
+ * The audio output plugin is responsible for estimating the ideal current
+ * playback time defined as follows:
+ *  ideal time = buffer timestamp - (output latency + pending buffer duration)
+ *
+ * Practically, this is the PTS (block_t.i_pts) of the current buffer minus
+ * the latency reported by the output programming interface.
+ * Computing the estimated drift directly would probably be more intuitive.
+ * However the use of an absolute time value does not introduce extra
+ * measurement errors due to the CPU scheduling jitter and clock resolution.
+ * Furthermore, the ideal while it is an abstract value, is easy for most
+ * audio output plugins to compute.
+ * The following definition is equivalent but depends on the clock time:
+ *  ideal time = real time + drift
+
+ * @note If aout_LatencyReport() is never called, the core will assume that
+ * there is no drift.
+ *
+ * @param ideal estimated ideal time as defined above.
+ */
+void aout_TimeReport (audio_output_t *aout, mtime_t ideal)
+{
+    mtime_t now = mdate (), delta = ideal - now;
+
+    aout_assert_locked (aout);
+    if (delta < -AOUT_MAX_PTS_DELAY || +AOUT_MAX_PTS_ADVANCE < delta)
+    {
+        aout_owner_t *owner = aout_owner (aout);
+
+        msg_Warn (aout, "not synchronized (%"PRId64" us), resampling",
+                  delta);
+        if (date_Get (&owner->sync.date) != VLC_TS_INVALID)
+            date_Move (&owner->sync.date, delta);
+    }
+    else
+        msg_Dbg (aout, "in sync: %"PRId64" us", delta);
+}
diff --git a/src/audio_output/output.c b/src/audio_output/output.c
index 08535f6..7d12380 100644
--- a/src/audio_output/output.c
+++ b/src/audio_output/output.c
@@ -613,10 +613,11 @@ block_t *aout_PacketNext (audio_output_t *p_aout, mtime_t start_date)
 {
     aout_packet_t *p = aout_packet (p_aout);
     aout_fifo_t *p_fifo = &p->fifo;
-    aout_buffer_t *p_buffer = NULL;
+    block_t *p_buffer;
     const bool b_can_sleek = AOUT_FMT_NON_LINEAR (&p_aout->format);
+    const mtime_t now = mdate ();
     const mtime_t threshold =
-        b_can_sleek ? start_date : mdate () - AOUT_MAX_PTS_DELAY;
+        (b_can_sleek ? start_date : now) - AOUT_MAX_PTS_DELAY;
 
     vlc_mutex_lock( &p->lock );
     if( p->pause_date != VLC_TS_INVALID )
@@ -640,10 +641,10 @@ block_t *aout_PacketNext (audio_output_t *p_aout, mtime_t start_date)
         block_Release (aout_FifoPop (p_fifo));
     }
 
-    mtime_t delta = p_buffer->i_pts - start_date;
+    mtime_t delta = start_date - p_buffer->i_pts;
     /* This assumes that all buffers have the same duration. This is true
      * since aout_PacketPlay() (aout_OutputSlice()) is used. */
-    if (delta >= p_buffer->i_length)
+    if (0 >= delta + p_buffer->i_length)
     {
         if (!p->starving)
         {
@@ -651,7 +652,6 @@ block_t *aout_PacketNext (audio_output_t *p_aout, mtime_t start_date)
                      "playing silence", delta);
             p->starving = true;
         }
-        p_buffer = NULL;
         goto out; /* nothing to play _yet_ */
     }
 
@@ -659,17 +659,22 @@ block_t *aout_PacketNext (audio_output_t *p_aout, mtime_t start_date)
     p_buffer = aout_FifoPop( p_fifo );
 
     if (!b_can_sleek
-     && (delta > AOUT_MAX_PTS_ADVANCE || delta < -AOUT_MAX_PTS_DELAY))
+     && (delta < -AOUT_MAX_PTS_ADVANCE || AOUT_MAX_PTS_DELAY < delta))
     {
-        /* Try to compensate the drift by doing some resampling. */
-        msg_Warn( p_aout, "output date isn't PTS date, requesting "
-                  "resampling (%"PRId64")", delta );
-
+        msg_Warn (p_aout, "audio output out of sync, "
+                          "adjusting dates (%"PRId64" us)", delta);
         aout_FifoMoveDates (&p->partial, delta);
         aout_FifoMoveDates (p_fifo, delta);
-#warning FIXME: feed back to input for resampling!!!
     }
-out:
     vlc_mutex_unlock( &p->lock );
+    if (!b_can_sleek)
+    {
+       aout_lock (p_aout);
+       aout_TimeReport (p_aout, now + delta);
+       aout_unlock (p_aout);
+    }
     return p_buffer;
+out:
+    vlc_mutex_unlock( &p->lock );
+    return NULL;
 }
diff --git a/src/libvlccore.sym b/src/libvlccore.sym
index 9f6a0ff..f6216c9 100644
--- a/src/libvlccore.sym
+++ b/src/libvlccore.sym
@@ -29,6 +29,7 @@ aout_VolumeUp
 aout_ToggleMute
 aout_IsMuted
 aout_SetMute
+aout_TimeReport
 aout_VolumeNoneInit
 aout_VolumeSoftInit
 aout_VolumeHardInit



More information about the vlc-commits mailing list