Lennart Poettering ad57e0
--- alsa-plugins-1.0.14.lennart/pulse/pcm_pulse.c	2007-09-24 01:43:01.000000000 +0200
Lennart Poettering ad57e0
+++ alsa-plugins-1.0.14/pulse/pcm_pulse.c	2007-10-01 21:36:53.000000000 +0200
Lennart Poettering ad57e0
@@ -36,6 +36,7 @@
Lennart Poettering ad57e0
     /* Since ALSA expects a ring buffer we must do some voodoo. */
Lennart Poettering ad57e0
     size_t last_size;
Lennart Poettering ad57e0
     size_t ptr;
Lennart Poettering ad57e0
+    int underrun;
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
     size_t offset;
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
@@ -90,7 +91,9 @@
Lennart Poettering ad57e0
     if (err < 0) {
Lennart Poettering ad57e0
         err = -EIO;
Lennart Poettering ad57e0
         goto finish;
Lennart Poettering ad57e0
-    }
Lennart Poettering ad57e0
+    } else
Lennart Poettering ad57e0
+    	pcm->underrun = 0;
Lennart Poettering ad57e0
+
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
 finish:
Lennart Poettering ad57e0
     pa_threaded_mainloop_unlock(pcm->p->mainloop);
Lennart Poettering ad57e0
@@ -200,6 +203,9 @@
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
 	err = snd_pcm_bytes_to_frames(io->pcm, pcm->ptr);
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
+	if (pcm->underrun)
Lennart Poettering ad57e0
+		err = -EPIPE;
Lennart Poettering ad57e0
+
Lennart Poettering ad57e0
 finish:
Lennart Poettering ad57e0
     pa_threaded_mainloop_unlock(pcm->p->mainloop);
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
@@ -231,6 +237,10 @@
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
 	*delayp = snd_pcm_bytes_to_frames(io->pcm, pa_usec_to_bytes(lat, &pcm->ss));
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
+ 	/* Yes, this is evil, and we're not supposed to do this.  */	
Lennart Poettering ad57e0
+ 	if (pcm->underrun && pcm->io.state == SND_PCM_STATE_RUNNING)
Lennart Poettering ad57e0
+		pcm->io.state = SND_PCM_STATE_XRUN;
Lennart Poettering ad57e0
+
Lennart Poettering ad57e0
 finish:
Lennart Poettering ad57e0
     pa_threaded_mainloop_unlock(pcm->p->mainloop);
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
@@ -273,6 +283,7 @@
Lennart Poettering ad57e0
         pulse_poll_deactivate(pcm->p);
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
     err = size;
Lennart Poettering ad57e0
+    pcm->underrun = 0;
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
 finish:
Lennart Poettering ad57e0
     pa_threaded_mainloop_unlock(pcm->p->mainloop);
Lennart Poettering ad57e0
@@ -354,6 +365,15 @@
Lennart Poettering ad57e0
     pulse_poll_activate(pcm->p);
Lennart Poettering ad57e0
 }
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
+static void stream_underrun_cb(pa_stream *p, void *userdata) {
Lennart Poettering ad57e0
+	snd_pcm_pulse_t *pcm = userdata;
Lennart Poettering ad57e0
+
Lennart Poettering ad57e0
+	assert(pcm);
Lennart Poettering ad57e0
+	assert(pcm->p);
Lennart Poettering ad57e0
+
Lennart Poettering ad57e0
+	pcm->underrun = 1;
Lennart Poettering ad57e0
+}
Lennart Poettering ad57e0
+
Lennart Poettering ad57e0
 static int pulse_pcm_poll_descriptors_count(snd_pcm_ioplug_t *io)
Lennart Poettering ad57e0
 {
Lennart Poettering ad57e0
 	snd_pcm_pulse_t *pcm = io->private_data;
Lennart Poettering ad57e0
@@ -461,6 +481,7 @@
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
     if (io->stream == SND_PCM_STREAM_PLAYBACK) {
Lennart Poettering ad57e0
         pa_stream_set_write_callback(pcm->stream, stream_request_cb, pcm);
Lennart Poettering ad57e0
+	pa_stream_set_underflow_callback(pcm->stream, stream_underrun_cb, pcm);
Lennart Poettering ad57e0
         pa_stream_connect_playback(pcm->stream, pcm->device, &pcm->buffer_attr,
Lennart Poettering ad57e0
         	PA_STREAM_AUTO_TIMING_UPDATE | PA_STREAM_INTERPOLATE_TIMING, NULL, NULL);
Lennart Poettering ad57e0
     } else {
Lennart Poettering ad57e0
@@ -480,6 +501,7 @@
Lennart Poettering ad57e0
     pcm->last_size = 0;
Lennart Poettering ad57e0
     pcm->ptr = 0;
Lennart Poettering ad57e0
     pcm->offset = 0;
Lennart Poettering ad57e0
+    pcm->underrun = 0;
Lennart Poettering ad57e0
 
Lennart Poettering ad57e0
 finish:
Lennart Poettering ad57e0
     pa_threaded_mainloop_unlock(pcm->p->mainloop);