chiark
/
gitweb
/
~mdw
/
disorder
/ commitdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
| commitdiff |
tree
raw
|
patch
|
inline
| side by side (parent:
413799e
)
playrtp: cope better with spurious ALSA underruns
author
Richard Kettlewell
<rjk@greenend.org.uk>
Mon, 24 Mar 2008 15:21:22 +0000
(15:21 +0000)
committer
Richard Kettlewell
<rjk@greenend.org.uk>
Mon, 24 Mar 2008 15:21:22 +0000
(15:21 +0000)
clients/playrtp-alsa.c
patch
|
blob
|
blame
|
history
diff --git
a/clients/playrtp-alsa.c
b/clients/playrtp-alsa.c
index 142f1eef72823dbbfbd43c2e4aa1727a1c203888..f2336e4fc8e40053fb334b6bbf2ff6fc4adadf14 100644
(file)
--- a/
clients/playrtp-alsa.c
+++ b/
clients/playrtp-alsa.c
@@
-84,8
+84,8
@@
static void playrtp_alsa_init(void) {
channels, err);
if((err = snd_pcm_hw_params_set_buffer_size_near(pcm, hwparams,
&pcm_bufsize)) < 0)
channels, err);
if((err = snd_pcm_hw_params_set_buffer_size_near(pcm, hwparams,
&pcm_bufsize)) < 0)
- fatal(0, "error from snd_pcm_hw_params_set_buffer_size (%d): %d",
-
MAXSAMPLES * samplesize * 3
, err);
+ fatal(0, "error from snd_pcm_hw_params_set_buffer_size (%
l
d): %d",
+
(long)pcm_bufsize
, err);
if((err = snd_pcm_hw_params(pcm, hwparams)) < 0)
fatal(0, "error calling snd_pcm_hw_params: %d", err);
/* Set up 'software' parameters */
if((err = snd_pcm_hw_params(pcm, hwparams)) < 0)
fatal(0, "error calling snd_pcm_hw_params: %d", err);
/* Set up 'software' parameters */
@@
-95,6
+95,12
@@
static void playrtp_alsa_init(void) {
if((err = snd_pcm_sw_params_set_avail_min(pcm, swparams, avail_min)) < 0)
fatal(0, "error calling snd_pcm_sw_params_set_avail_min %d: %d",
avail_min, err);
if((err = snd_pcm_sw_params_set_avail_min(pcm, swparams, avail_min)) < 0)
fatal(0, "error calling snd_pcm_sw_params_set_avail_min %d: %d",
avail_min, err);
+ /* Default start threshold is 1, which means that PCM starts as soon as we've
+ * written anything. Setting it to pcm_bufsize (around 15000) produces
+ * -EINVAL. 1024 is a guess... */
+ if((err = snd_pcm_sw_params_set_start_threshold(pcm, swparams, 1024)) < 0)
+ fatal(0, "error calling snd_pcm_sw_params_set_start_threshold %d: %d",
+ 1024, err);
if((err = snd_pcm_sw_params(pcm, swparams)) < 0)
fatal(0, "error calling snd_pcm_sw_params: %d", err);
}
if((err = snd_pcm_sw_params(pcm, swparams)) < 0)
fatal(0, "error calling snd_pcm_sw_params: %d", err);
}
@@
-124,8
+130,11
@@
static void wait_alsa(void) {
* @return 0 on success, -1 on non-fatal error
*/
static int playrtp_alsa_writei(const void *s, size_t n) {
* @return 0 on success, -1 on non-fatal error
*/
static int playrtp_alsa_writei(const void *s, size_t n) {
+ int err;
+ snd_pcm_sframes_t frames_written;
+
/* Do the write */
/* Do the write */
-
const snd_pcm_sframes_t
frames_written = snd_pcm_writei(pcm, s, n / 2);
+ frames_written = snd_pcm_writei(pcm, s, n / 2);
if(frames_written < 0) {
/* Something went wrong */
switch(frames_written) {
if(frames_written < 0) {
/* Something went wrong */
switch(frames_written) {
@@
-134,25
+143,36
@@
static int playrtp_alsa_writei(const void *s, size_t n) {
case -EPIPE:
error(0, "error calling snd_pcm_writei: %ld",
(long)frames_written);
case -EPIPE:
error(0, "error calling snd_pcm_writei: %ld",
(long)frames_written);
- return -1;
+ if((err = snd_pcm_prepare(pcm)) < 0) {
+ error(0, "error calling snd_pcm_prepare: %d", err);
+ return -1;
+ }
+ frames_written = snd_pcm_writei(pcm, s, n / 2);
+ if(frames_written == -EAGAIN)
+ return 0;
+ else if(frames_written < 0) {
+ error(0, "error calling snd_pcm_writei: %ld",
+ (long)frames_written);
+ return -1;
+ }
+ break;
default:
fatal(0, "error calling snd_pcm_writei: %ld",
(long)frames_written);
}
default:
fatal(0, "error calling snd_pcm_writei: %ld",
(long)frames_written);
}
- } else {
- /* Success */
- next_timestamp += frames_written * 2;
- if(dump_buffer) {
- snd_pcm_sframes_t count;
- const int16_t *sp = s;
-
- for(count = 0; count < frames_written * 2; ++count) {
- dump_buffer[dump_index++] = (int16_t)ntohs(*sp++);
- dump_index %= dump_size;
- }
+ }
+ /* Success */
+ next_timestamp += frames_written * 2;
+ if(dump_buffer) {
+ snd_pcm_sframes_t count;
+ const int16_t *sp = s;
+
+ for(count = 0; count < frames_written * 2; ++count) {
+ dump_buffer[dump_index++] = (int16_t)ntohs(*sp++);
+ dump_index %= dump_size;
}
}
- return 0;
}
}
+ return 0;
}
/** @brief Play the relevant part of a packet
}
/** @brief Play the relevant part of a packet