diff options
| author | Pierre Ossman <ossman@cendio.se> | 2006-08-22 16:15:47 +0000 | 
|---|---|---|
| committer | Pierre Ossman <ossman@cendio.se> | 2006-08-22 16:15:47 +0000 | 
| commit | d194604402648fbab61bde3d1106fecb1b82dc83 (patch) | |
| tree | 5d292d96daa5272d720ecd964d5a37f5f66d0390 | |
| parent | 095f35725d644e0284c4b2d99b6fab71290eaeaa (diff) | |
Remove silence generation in waveout module.
git-svn-id: file:///home/lennart/svn/public/pulseaudio/trunk@1325 fefdeb5f-60dc-0310-8127-8f9354f1896f
| -rw-r--r-- | src/modules/module-waveout.c | 83 | 
1 files changed, 33 insertions, 50 deletions
diff --git a/src/modules/module-waveout.c b/src/modules/module-waveout.c index f1861466..4043c136 100644 --- a/src/modules/module-waveout.c +++ b/src/modules/module-waveout.c @@ -75,11 +75,10 @@ struct userdata {      uint32_t free_ofrags, free_ifrags;      DWORD written_bytes; +    int sink_underflow;      int cur_ohdr, cur_ihdr; -    unsigned int oremain;      WAVEHDR *ohdrs, *ihdrs; -    pa_memchunk silence;      HWAVEOUT hwo;      HWAVEIN hwi; @@ -110,8 +109,8 @@ static void update_usage(struct userdata *u) {  static void do_write(struct userdata *u)  { -    uint32_t free_frags, remain; -    pa_memchunk memchunk, *cur_chunk; +    uint32_t free_frags; +    pa_memchunk memchunk;      WAVEHDR *hdr;      MMRESULT res; @@ -119,13 +118,10 @@ static void do_write(struct userdata *u)          return;      EnterCriticalSection(&u->crit); -      free_frags = u->free_ofrags; -    u->free_ofrags = 0; -      LeaveCriticalSection(&u->crit); -    if (free_frags == u->fragments) +    if (!u->sink_underflow && (free_frags == u->fragments))          pa_log_debug("WaveOut underflow!");      while (free_frags) { @@ -133,45 +129,39 @@ static void do_write(struct userdata *u)          if (hdr->dwFlags & WHDR_PREPARED)              waveOutUnprepareHeader(u->hwo, hdr, sizeof(WAVEHDR)); -        remain = u->oremain; -        while (remain) { -            cur_chunk = &memchunk; +        hdr->dwBufferLength = 0; +        while (hdr->dwBufferLength < u->fragment_size) { +            size_t len; -            if (pa_sink_render(u->sink, remain, cur_chunk) < 0) { -                /* -                 * Don't fill with silence unless we're getting close to -                 * underflowing. -                 */ -                if (free_frags > u->fragments/2) -                    cur_chunk = &u->silence; -                else { -                    EnterCriticalSection(&u->crit); +            len = u->fragment_size - hdr->dwBufferLength; -                    u->free_ofrags += free_frags; +            if (pa_sink_render(u->sink, len, &memchunk) < 0) +                break; -                    LeaveCriticalSection(&u->crit); +            assert(memchunk.memblock); +            assert(memchunk.memblock->data); +            assert(memchunk.length); -                    u->oremain = remain; -                    return; -                } -            } +            if (memchunk.length < len) +                len = memchunk.length; -            assert(cur_chunk->memblock); -            assert(cur_chunk->memblock->data); -            assert(cur_chunk->length); +            memcpy(hdr->lpData + hdr->dwBufferLength, +                (char*)memchunk.memblock->data + memchunk.index, len); -            memcpy(hdr->lpData + u->fragment_size - remain, -                (char*)cur_chunk->memblock->data + cur_chunk->index, -                (cur_chunk->length < remain)?cur_chunk->length:remain); +            hdr->dwBufferLength += len; -            remain -= (cur_chunk->length < remain)?cur_chunk->length:remain; +            pa_memblock_unref(memchunk.memblock); +            memchunk.memblock = NULL; +        } -            if (cur_chunk != &u->silence) { -                pa_memblock_unref(cur_chunk->memblock); -                cur_chunk->memblock = NULL; -            } +        /* Insufficient data in sink buffer? */ +        if (hdr->dwBufferLength == 0) { +            u->sink_underflow = 1; +            break;          } +        u->sink_underflow = 0; +          res = waveOutPrepareHeader(u->hwo, hdr, sizeof(WAVEHDR));          if (res != MMSYSERR_NOERROR) {              pa_log_error(__FILE__ ": ERROR: Unable to prepare waveOut block: %d", @@ -183,12 +173,15 @@ static void do_write(struct userdata *u)                  res);          } -        u->written_bytes += u->fragment_size; +        u->written_bytes += hdr->dwBufferLength; + +        EnterCriticalSection(&u->crit); +        u->free_ofrags--; +        LeaveCriticalSection(&u->crit);          free_frags--;          u->cur_ohdr++;          u->cur_ohdr %= u->fragments; -        u->oremain = u->fragment_size;      }  } @@ -540,8 +533,7 @@ int pa__init(pa_core *c, pa_module*m) {      u->fragment_size = frag_size - (frag_size % pa_frame_size(&ss));      u->written_bytes = 0; - -    u->oremain = u->fragment_size; +    u->sink_underflow = 1;      u->poll_timeout = pa_bytes_to_usec(u->fragments * u->fragment_size / 10, &ss); @@ -570,12 +562,6 @@ int pa__init(pa_core *c, pa_module*m) {          assert(u->ohdrs);      } -    u->silence.length = u->fragment_size; -    u->silence.memblock = pa_memblock_new(u->core->mempool, u->silence.length); -    assert(u->silence.memblock); -    pa_silence_memblock(u->silence.memblock, &ss); -    u->silence.index = 0; -      u->module = m;      m->userdata = u; @@ -611,9 +597,6 @@ void pa__done(pa_core *c, pa_module*m) {      if (!(u = m->userdata))          return; - -    if (u->silence.memblock) -        pa_memblock_unref(u->silence.memblock);      if (u->event)          c->mainloop->time_free(u->event);  | 
