[FFmpeg-devel] [PATCH] ALSA: fix timefilter divergence

Michael Niedermayer michaelni at gmx.at
Thu Feb 16 18:38:58 CET 2012


On Wed, Feb 15, 2012 at 07:35:09PM +0100, Nicolas George wrote:
> [PATCH 1/3] timefilter: internally compute feedback factors.
> [PATCH 2/3] timefilter: allow irregular updates.
> [PATCH 3/3] alsa: use the irregular timefilter update.
> 
> The attached patch series fixes the divergence of the timefilter results
> with ALSA and long periods, such as can be caused by a dsnoop plugin, and
> inaccuracy in all cases.

could you post a list of input values to the filter that cause the
current timefiler to fail?

Iam quite interrested to see it failing, also heres some simple change
that vastly improves the timefilters performance in its selftest
from:
 [0.800000 0.000800  0.000000] [1.021025 0.998922  0.000000] [1.021025 0.998922  0.000000] [1.021025 0.998922  0.000000]
 [0.001003 0.000000  0.004341] [0.041562 0.000996  0.045245] [0.081175 0.002874  0.074431] [0.118380 0.006568  0.108913]
 [0.001003 0.000000  0.039073] [0.013619 0.000455  0.224390] [0.041562 0.000996  0.407205] [0.068719 0.002305  0.600848]
 [0.001003 0.000000  0.212729] [0.022518 0.000060  0.941262] [0.015889 0.000507  1.391585] [0.041562 0.000996  2.217003]
 [0.001003 0.000000  0.976818] [0.014412 0.000021  2.712350] [0.013691 0.000370  4.648765] [0.018915 0.000542  6.709646]
 [0.001003 0.000000  4.172097] [0.010677 0.000007  7.809261] [0.018915 0.000032 14.578784] [0.013619 0.000387 20.628496]

to:
 [0.800000 0.000800  0.000000] [1.021025 20106283742.519314  0.000000] [1.021025 21978021419.207241  0.000000] [1.021025 114933694372.458130  0.000000]
 [0.001018 0.000000  0.004341] [0.014412 0.386610  0.014807] [0.013619 0.939146  0.013449] [0.012988 1.961913  0.012757]
 [0.001018 0.000000  0.039073] [0.001264 0.057740  0.079849] [0.014412 0.386610  0.133261] [0.014412 0.774574  0.123942]
 [0.001018 0.000000  0.212729] [0.000990 0.021474  0.310709] [0.001261 0.077263  0.487556] [0.014412 0.386610  0.725534]
 [0.001018 0.000000  0.976818] [0.000792 0.009242  1.190805] [0.000990 0.031560  1.600010] [0.001256 0.086704  2.344437]
 [0.001018 0.000000  4.172097] [0.000990 0.004099  4.533166] [0.000990 0.013727  5.493652] [0.000990 0.035484  7.150269]

maybe its also fixing the problem you see with alsa ?
note, the variable names in the patch below are not very good, dont
be mislead by them
note2: the feedback factors change in meaning, especially the 
feedback3_factor so tests (with alsa) would likely need new values
for them. And i havnt really thought about what value would be
appropriate.

diff --git a/libavdevice/timefilter.c b/libavdevice/timefilter.c
index ff6552f..44119eb 100644
--- a/libavdevice/timefilter.c
+++ b/libavdevice/timefilter.c
@@ -32,7 +32,8 @@ struct TimeFilter {
     double cycle_time;
     double feedback2_factor;
     double feedback3_factor;
-    double clock_period;
+    double first_time;
+    double clock_period_den;
     int count;
 };

@@ -41,9 +42,9 @@ TimeFilter *ff_timefilter_new(double clock_period,
                               double feedback3_factor)
 {
     TimeFilter *self       = av_mallocz(sizeof(TimeFilter));
-    self->clock_period     = clock_period;
+    self->feedback3_factor = clock_period/feedback3_factor;
+    self->clock_period_den = 1.0/feedback3_factor;
     self->feedback2_factor = feedback2_factor;
-    self->feedback3_factor = feedback3_factor;
     return self;
 }

@@ -62,16 +63,18 @@ double ff_timefilter_update(TimeFilter *self, double system_time, double period)
     self->count++;
     if (self->count == 1) {
         /// init loop
+        self->first_time =
         self->cycle_time = system_time;
     } else {
         double loop_error;
-        self->cycle_time += self->clock_period * period;
+        double num = FFMAX(self->cycle_time - self->first_time, 0) + self->feedback3_factor;
+        self->cycle_time +=  num * period / self->clock_period_den;
         /// calculate loop error
         loop_error = system_time - self->cycle_time;

         /// update loop
         self->cycle_time   += FFMAX(self->feedback2_factor, 1.0 / self->count) * loop_error;
-        self->clock_period += self->feedback3_factor * loop_error / period;
+        self->clock_period_den += period;
     }
     return self->cycle_time;
 }

[...]

-- 
Michael     GnuPG fingerprint: 9FF2128B147EF6730BADF133611EC787040B0FAB

Breaking DRM is a little like attempting to break through a door even
though the window is wide open and the only thing in the house is a bunch
of things you dont want and which you would get tomorrow for free anyway
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 198 bytes
Desc: Digital signature
URL: <http://ffmpeg.org/pipermail/ffmpeg-devel/attachments/20120216/472e7221/attachment.asc>


More information about the ffmpeg-devel mailing list