]> code.delx.au - pulseaudio/commitdiff
latency calculation fix
authorLennart Poettering <lennart@poettering.net>
Wed, 27 Oct 2004 14:14:30 +0000 (14:14 +0000)
committerLennart Poettering <lennart@poettering.net>
Wed, 27 Oct 2004 14:14:30 +0000 (14:14 +0000)
git-svn-id: file:///home/lennart/svn/public/pulseaudio/trunk@258 fefdeb5f-60dc-0310-8127-8f9354f1896f

polyp/polyplib-stream.c
polyp/sink-input.c
polyp/sink-input.h

index c8fef6737d86a7e6fd15c635b8b651a8b482b144..286702b24a71a1adeb3635b6614ab5a131e6151e 100644 (file)
@@ -687,6 +687,24 @@ pa_usec_t pa_stream_get_time(struct pa_stream *s, const struct pa_latency_info *
     return usec;
 }
 
+static pa_usec_t time_counter_diff(struct pa_stream *s, pa_usec_t t, pa_usec_t c, int *negative) {
+    assert(s);
+    
+    if (negative)
+        *negative = 0;
+
+    if (c < t) {
+        if (s->direction == PA_STREAM_RECORD) {
+            if (negative)
+                *negative = 1;
+
+            return t-c;
+        } else
+            return 0;
+    } else
+        return c-t;
+}
+
 pa_usec_t pa_stream_get_latency(struct pa_stream *s, const struct pa_latency_info *i, int *negative) {
     pa_usec_t t, c;
     assert(s && i);
@@ -694,18 +712,7 @@ pa_usec_t pa_stream_get_latency(struct pa_stream *s, const struct pa_latency_inf
     t = pa_stream_get_time(s, i);
     c = pa_bytes_to_usec(s->counter, &s->sample_spec);
 
-    if (t <= c) {
-        if (negative)
-            *negative = 1;
-
-        return c-t;
-    } else {
-        if (negative)
-            *negative = 0;
-        return t-c;
-    }
-
-    return 0;
+    return time_counter_diff(s, t, c, negative);
 }
 
 const struct pa_sample_spec* pa_stream_get_sample_spec(struct pa_stream *s) {
@@ -749,15 +756,6 @@ pa_usec_t pa_stream_get_interpolated_latency(struct pa_stream *s, int *negative)
 
     t = pa_stream_get_interpolated_time(s);
     c = pa_bytes_to_usec(s->counter, &s->sample_spec);
-
-    if (t <= c) {
-        if (negative)
-            *negative = 1;
-
-        return c-t;
-    } else {
-        if (negative)
-            *negative = 0;
-        return t-c;
-    }
+    
+    return time_counter_diff(s, t, c, negative);
 }
index 5c8675dec827191a3f731baf58eee62dc6ce99a9..dac1095349edd779d467596796b0277a0441675a 100644 (file)
@@ -69,8 +69,10 @@ struct pa_sink_input* pa_sink_input_new(struct pa_sink *s, const char *name, con
     i->kill = NULL;
     i->get_latency = NULL;
     i->userdata = NULL;
+    i->underrun = NULL;
 
     i->volume = PA_VOLUME_NORM;
+    i->playing = 0;
 
     i->resampled_chunk.memblock = NULL;
     i->resampled_chunk.index = i->resampled_chunk.length = 0;
@@ -156,20 +158,19 @@ pa_usec_t pa_sink_input_get_latency(struct pa_sink_input *i) {
 }
 
 int pa_sink_input_peek(struct pa_sink_input *i, struct pa_memchunk *chunk) {
-    int ret = 0;
+    int ret = -1;
     assert(i && chunk && i->ref >= 1);
 
-    if (!i->peek || !i->drop)
-        return -1;
-
-    if (i->state == PA_SINK_INPUT_CORKED)
-        return -1;
-    
-    if (!i->resampler)
-        return i->peek(i, chunk);
-
     pa_sink_input_ref(i);
 
+    if (!i->peek || !i->drop || i->state == PA_SINK_INPUT_CORKED)
+        goto finish;
+        
+    if (!i->resampler) {
+        ret = i->peek(i, chunk);
+        goto finish;
+    }
+
     while (!i->resampled_chunk.memblock) {
         struct pa_memchunk tchunk;
         size_t l;
@@ -199,6 +200,11 @@ int pa_sink_input_peek(struct pa_sink_input *i, struct pa_memchunk *chunk) {
 
 finish:
 
+    if (ret < 0 && i->playing && i->underrun)
+        i->underrun(i);
+
+    i->playing = ret >= 0;
+    
     pa_sink_input_unref(i);
     
     return ret;
index aed5f521ef218934a48bc087cdf4e1f0d8769759..eb2cb2399aaf4b6c1df1ac6c36e25a02fb6142bc 100644 (file)
@@ -54,9 +54,12 @@ struct pa_sink_input {
     void (*drop) (struct pa_sink_input *i, const struct pa_memchunk *chunk, size_t length);
     void (*kill) (struct pa_sink_input *i);
     pa_usec_t (*get_latency) (struct pa_sink_input *i);
+    void (*underrun) (struct pa_sink_input *i);
 
     void *userdata;
 
+    int playing;
+
     struct pa_memchunk resampled_chunk;
     struct pa_resampler *resampler;
 };