From c0507f561089d92d603e60c32aa6a8c87ea7e900 Mon Sep 17 00:00:00 2001 From: Bill Currie Date: Sat, 14 Apr 2001 02:30:30 +0000 Subject: [PATCH] update for the lastest alsa pcm mmap api. not as bad as at first appearance --- libs/audio/targets/snd_alsa_0_9.c | 79 ++++++++++--------------------- 1 file changed, 24 insertions(+), 55 deletions(-) diff --git a/libs/audio/targets/snd_alsa_0_9.c b/libs/audio/targets/snd_alsa_0_9.c index ee1686eee..4f36f22f4 100644 --- a/libs/audio/targets/snd_alsa_0_9.c +++ b/libs/audio/targets/snd_alsa_0_9.c @@ -43,7 +43,7 @@ static int snd_inited; static snd_pcm_t *pcm; -static const snd_pcm_channel_area_t *mmap_areas; +//static const snd_pcm_channel_area_t *mmap_areas; static char *pcmname = NULL; size_t buffer_size; @@ -187,7 +187,7 @@ SNDDMA_Init (void) goto error; } - mmap_areas = snd_pcm_mmap_running_areas (pcm); + //mmap_areas = snd_pcm_mmap_running_areas (pcm); shm = &sn; memset ((dma_t *) shm, 0, sizeof (*shm)); @@ -204,7 +204,8 @@ SNDDMA_Init (void) buffer_size = snd_pcm_hw_params_get_buffer_size (hw); shm->samples = buffer_size * shm->channels; // mono samples in buffer shm->speed = rate; - shm->buffer = (unsigned char *) mmap_areas->addr; + SNDDMA_GetDMAPos ();//XXX sets shm->buffer + //shm->buffer = (unsigned char *) mmap_areas->addr; Con_Printf ("%5d stereo\n", shm->channels - 1); Con_Printf ("%5d samples\n", shm->samples); Con_Printf ("%5d samplepos\n", shm->samplepos); @@ -221,34 +222,21 @@ SNDDMA_Init (void) return 0; } -static inline int -get_hw_ptr () -{ - size_t app_ptr; - snd_pcm_sframes_t delay; - int hw_ptr; - - if (snd_pcm_state (pcm) != SND_PCM_STATE_RUNNING) - return 0; - app_ptr = snd_pcm_mmap_offset (pcm); - snd_pcm_delay (pcm, &delay); - hw_ptr = app_ptr - delay; - if (hw_ptr < 0) - hw_ptr += buffer_size; - return hw_ptr; -} - int SNDDMA_GetDMAPos (void) { - int hw_ptr; + snd_pcm_uframes_t offset; + snd_pcm_uframes_t nframes = shm->samples/shm->channels; + const snd_pcm_channel_area_t *areas; if (!snd_inited) return 0; - hw_ptr = get_hw_ptr (); - hw_ptr *= shm->channels; - shm->samplepos = hw_ptr; + snd_pcm_mmap_begin (pcm, &areas, &offset, &nframes); + offset *= shm->channels; + nframes *= shm->channels; + shm->samplepos = offset; + shm->buffer = areas->addr;//XXX FIXME there's an area per channel return shm->samplepos; } @@ -262,51 +250,32 @@ SNDDMA_Shutdown (void) } /* -============== -SNDDMA_Submit + SNDDMA_Submit -Send sound to device if buffer isn't really the dma buffer -=============== + Send sound to device if buffer isn't really the dma buffer */ void SNDDMA_Submit (void) { - int count = paintedtime - soundtime; - int avail; - int missed; + snd_pcm_uframes_t offset; + snd_pcm_uframes_t nframes; + const snd_pcm_channel_area_t *areas; int state; - int hw_ptr; - int offset; + int count = paintedtime - soundtime; + + nframes = count / shm->channels; + + snd_pcm_mmap_begin (pcm, &areas, &offset, &nframes); state = snd_pcm_state (pcm); switch (state) { case SND_PCM_STATE_PREPARED: - snd_pcm_mmap_forward (pcm, count); + snd_pcm_mmap_commit (pcm, offset, nframes); snd_pcm_start (pcm); break; case SND_PCM_STATE_RUNNING: - hw_ptr = get_hw_ptr (); - missed = hw_ptr - shm->samplepos / shm->channels; - if (missed < 0) - missed += buffer_size; - count -= missed; - offset = snd_pcm_mmap_offset (pcm); - if (offset > hw_ptr) - count -= (offset - hw_ptr); - else - count -= (buffer_size - hw_ptr + offset); - if (count < 0) { - snd_pcm_rewind (pcm, -count); - } else { - avail = snd_pcm_avail_update (pcm); - if (avail < 0) - avail = buffer_size; - if (count > avail) - count = avail; - if (count) - snd_pcm_mmap_forward (pcm, count); - } + snd_pcm_mmap_commit (pcm, offset, nframes); break; default: break;