Merged Ryan's 5.1 audio fix from SDL 1.2 SDL-1.3
authorSam Lantinga <slouken@libsdl.org>
Fri, 23 Jun 2006 09:01:08 +0000
branchSDL-1.3
changeset 1702a7ad7081b977
parent 1701 442248d4e738
child 1703 a51dfda0ff33
Merged Ryan's 5.1 audio fix from SDL 1.2
src/audio/alsa/SDL_alsa_audio.c
     1.1 --- a/src/audio/alsa/SDL_alsa_audio.c	Fri Jun 23 08:48:24 2006 +0000
     1.2 +++ b/src/audio/alsa/SDL_alsa_audio.c	Fri Jun 23 09:01:08 2006 +0000
     1.3 @@ -351,6 +351,69 @@
     1.4      }
     1.5  }
     1.6  
     1.7 +
     1.8 +/*
     1.9 + * http://bugzilla.libsdl.org/show_bug.cgi?id=110
    1.10 + * "For Linux ALSA, this is FL-FR-RL-RR-C-LFE
    1.11 + *  and for Windows DirectX [and CoreAudio], this is FL-FR-C-LFE-RL-RR"
    1.12 + */
    1.13 +#define SWIZ6(T) \
    1.14 +    T *ptr = (T *) mixbuf; \
    1.15 +    const Uint32 count = (this->spec.samples / 6); \
    1.16 +    Uint32 i; \
    1.17 +    for (i = 0; i < count; i++, ptr += 6) { \
    1.18 +        T tmp; \
    1.19 +        tmp = ptr[2]; ptr[2] = ptr[4]; ptr[4] = tmp; \
    1.20 +        tmp = ptr[3]; ptr[3] = ptr[5]; ptr[5] = tmp; \
    1.21 +    }
    1.22 +
    1.23 +static __inline__ void
    1.24 +swizzle_alsa_channels_6_64bit(_THIS)
    1.25 +{
    1.26 +    SWIZ6(Uint64);
    1.27 +}
    1.28 +static __inline__ void
    1.29 +swizzle_alsa_channels_6_32bit(_THIS)
    1.30 +{
    1.31 +    SWIZ6(Uint32);
    1.32 +}
    1.33 +static __inline__ void
    1.34 +swizzle_alsa_channels_6_16bit(_THIS)
    1.35 +{
    1.36 +    SWIZ6(Uint16);
    1.37 +}
    1.38 +static __inline__ void
    1.39 +swizzle_alsa_channels_6_8bit(_THIS)
    1.40 +{
    1.41 +    SWIZ6(Uint8);
    1.42 +}
    1.43 +
    1.44 +#undef SWIZ6
    1.45 +
    1.46 +
    1.47 +/*
    1.48 + * Called right before feeding this->mixbuf to the hardware. Swizzle channels
    1.49 + *  from Windows/Mac order to the format alsalib will want.
    1.50 + */
    1.51 +static __inline__ void
    1.52 +swizzle_alsa_channels(_THIS)
    1.53 +{
    1.54 +    if (this->spec.channels == 6) {
    1.55 +        const Uint16 fmtsize = (this->spec.format & 0xFF);      /* bits/channel. */
    1.56 +        if (fmtsize == 16)
    1.57 +            swizzle_alsa_channels_6_16bit(this);
    1.58 +        else if (fmtsize == 8)
    1.59 +            swizzle_alsa_channels_6_8bit(this);
    1.60 +        else if (fmtsize == 32)
    1.61 +            swizzle_alsa_channels_6_32bit(this);
    1.62 +        else if (fmtsize == 64)
    1.63 +            swizzle_alsa_channels_6_64bit(this);
    1.64 +    }
    1.65 +
    1.66 +    /* !!! FIXME: update this for 7.1 if needed, later. */
    1.67 +}
    1.68 +
    1.69 +
    1.70  static void
    1.71  ALSA_PlayAudio(_THIS)
    1.72  {
    1.73 @@ -358,8 +421,11 @@
    1.74      int sample_len;
    1.75      signed short *sample_buf;
    1.76  
    1.77 +    swizzle_alsa_channels(this);
    1.78 +
    1.79      sample_len = this->spec.samples;
    1.80      sample_buf = (signed short *) mixbuf;
    1.81 +
    1.82      while (sample_len > 0) {
    1.83          status =
    1.84              SDL_NAME(snd_pcm_writei) (pcm_handle, sample_buf, sample_len);
    1.85 @@ -372,8 +438,7 @@
    1.86                  do {
    1.87                      SDL_Delay(1);
    1.88                      status = SDL_NAME(snd_pcm_resume) (pcm_handle);
    1.89 -                }
    1.90 -                while (status == -EAGAIN);
    1.91 +                } while (status == -EAGAIN);
    1.92              }
    1.93              if (status < 0) {
    1.94                  status = SDL_NAME(snd_pcm_prepare) (pcm_handle);