tweaks to reduce latency/pauses in output

This commit is contained in:
Cameron Grant 2001-08-29 09:17:43 +00:00
parent 02d4de1533
commit edecdda7b9
2 changed files with 11 additions and 8 deletions

View File

@ -258,6 +258,7 @@ chn_write(struct pcm_channel *c, struct uio *buf)
timeout = (hz * sndbuf_getblksz(bs)) / (sndbuf_getspd(bs) * sndbuf_getbps(bs)); timeout = (hz * sndbuf_getblksz(bs)) / (sndbuf_getspd(bs) * sndbuf_getbps(bs));
if (timeout < 1) if (timeout < 1)
timeout = 1; timeout = 1;
timeout = 1;
ret = chn_sleep(c, "pcmwr", timeout); ret = chn_sleep(c, "pcmwr", timeout);
if (ret == EWOULDBLOCK) { if (ret == EWOULDBLOCK) {
count -= timeout; count -= timeout;
@ -353,7 +354,7 @@ chn_rdintr(struct pcm_channel *c)
CHN_LOCKASSERT(c); CHN_LOCKASSERT(c);
/* tell the driver to update the primary buffer if non-dma */ /* tell the driver to update the primary buffer if non-dma */
chn_trigger(c, PCMTRIG_EMLDMARD); chn_trigger(c, PCMTRIG_EMLDMARD);
/* update pointers in primary bufhard */ /* update pointers in primary buffer */
chn_dmaupdate(c); chn_dmaupdate(c);
/* ...and feed from primary to secondary */ /* ...and feed from primary to secondary */
ret = chn_rdfeed(c); ret = chn_rdfeed(c);
@ -422,7 +423,7 @@ chn_intr(struct pcm_channel *c)
u_int32_t u_int32_t
chn_start(struct pcm_channel *c, int force) chn_start(struct pcm_channel *c, int force)
{ {
u_int32_t i; u_int32_t i, j;
struct snd_dbuf *b = c->bufhard; struct snd_dbuf *b = c->bufhard;
struct snd_dbuf *bs = c->bufsoft; struct snd_dbuf *bs = c->bufsoft;
@ -432,7 +433,8 @@ chn_start(struct pcm_channel *c, int force)
return EINVAL; return EINVAL;
i = (c->direction == PCMDIR_PLAY)? sndbuf_getready(bs) : sndbuf_getfree(bs); i = (c->direction == PCMDIR_PLAY)? sndbuf_getready(bs) : sndbuf_getfree(bs);
if (force || (i >= sndbuf_getblksz(b))) { j = (c->direction == PCMDIR_PLAY)? sndbuf_getfree(b) : sndbuf_getready(b);
if (force || (i >= j)) {
c->flags |= CHN_F_TRIGGERED; c->flags |= CHN_F_TRIGGERED;
/* /*
* if we're starting because a vchan started, don't feed any data * if we're starting because a vchan started, don't feed any data
@ -448,6 +450,7 @@ chn_start(struct pcm_channel *c, int force)
sndbuf_fillsilence(b); sndbuf_fillsilence(b);
} }
sndbuf_setrun(b, 1); sndbuf_setrun(b, 1);
c->xruns = 0;
chn_trigger(c, PCMTRIG_START); chn_trigger(c, PCMTRIG_START);
return 0; return 0;
} }

View File

@ -675,18 +675,18 @@ sndstat_prepare_pcm(struct sbuf *s, device_t dev, int verbose)
if (c->pid != -1) if (c->pid != -1)
sbuf_printf(s, ", pid %d", c->pid); sbuf_printf(s, ", pid %d", c->pid);
sbuf_printf(s, "\n\t"); sbuf_printf(s, "\n\t");
if (c->pid != -1 && c->bufhard != NULL && c->bufsoft != NULL) { if (c->bufhard != NULL && c->bufsoft != NULL) {
sbuf_printf(s, "interrupts %d, ", c->interrupts); sbuf_printf(s, "interrupts %d, ", c->interrupts);
if (c->direction == PCMDIR_REC) if (c->direction == PCMDIR_REC)
sbuf_printf(s, "overruns %d, hfree %d, sfree %d", sbuf_printf(s, "overruns %d, hfree %d, sfree %d",
c->xruns, sndbuf_getfree(c->bufhard), sndbuf_getfree(c->bufsoft)); c->xruns, sndbuf_getfree(c->bufhard), sndbuf_getfree(c->bufsoft));
else else
sbuf_printf(s, "underruns %d, hready %d, sready %d", sbuf_printf(s, "underruns %d, ready %d",
c->xruns, sndbuf_getready(c->bufhard), sndbuf_getready(c->bufsoft)); c->xruns, sndbuf_getready(c->bufsoft));
sbuf_printf(s, "\n\t"); sbuf_printf(s, "\n\t");
} }
fsep = (c->direction == PCMDIR_REC)? " -> " : " <- "; fsep = (c->direction == PCMDIR_REC)? " -> " : " <- ";
sbuf_printf(s, "[hardware]%s", fsep); sbuf_printf(s, "{hardware}%s", fsep);
f = c->feeder; f = c->feeder;
while (f) { while (f) {
sbuf_printf(s, "%s", f->class->name); sbuf_printf(s, "%s", f->class->name);
@ -699,7 +699,7 @@ sndstat_prepare_pcm(struct sbuf *s, device_t dev, int verbose)
sbuf_printf(s, "%s", fsep); sbuf_printf(s, "%s", fsep);
f = f->source; f = f->source;
} }
sbuf_printf(s, "[userland]"); sbuf_printf(s, "{userland}");
} }
skipverbose: skipverbose:
} else } else