src/audio/dmedia/SDL_irixaudio.c

/* [<][>]
[^][v][top][bottom][index][help] */

FUNCTIONS

This source file includes following functions.
  1. Audio_Available
  2. Audio_DeleteDevice
  3. Audio_CreateDevice
  4. AL_WaitAudio
  5. AL_PlayAudio
  6. AL_GetAudioBuf
  7. AL_CloseAudio
  8. AL_OpenAudio

   1 /*
   2     SDL - Simple DirectMedia Layer
   3     Copyright (C) 1997, 1998  Sam Lantinga
   4 
   5     This library is free software; you can redistribute it and/or
   6     modify it under the terms of the GNU Library General Public
   7     License as published by the Free Software Foundation; either
   8     version 2 of the License, or (at your option) any later version.
   9 
  10     This library is distributed in the hope that it will be useful,
  11     but WITHOUT ANY WARRANTY; without even the implied warranty of
  12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  13     Library General Public License for more details.
  14 
  15     You should have received a copy of the GNU Library General Public
  16     License along with this library; if not, write to the Free
  17     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  18 
  19     Sam Lantinga
  20     5635-34 Springhouse Dr.
  21     Pleasanton, CA 94588 (USA)
  22     slouken@devolution.com
  23 */
  24 
  25 #ifdef SAVE_RCSID
  26 static char rcsid =
  27  "@(#) $Id: SDL_irixaudio.c,v 1.1.2.2 2001/01/05 20:13:18 hercules Exp $";
  28 #endif
  29 
  30 /* Allow access to a raw mixing buffer (For IRIX 6.5 and higher) */
  31 
  32 #include <stdlib.h>
  33 
  34 #include "SDL_endian.h"
  35 #include "SDL_timer.h"
  36 #include "SDL_audio.h"
  37 #include "SDL_audiomem.h"
  38 #include "SDL_audio_c.h"
  39 #include "SDL_irixaudio.h"
  40 
  41 
  42 /* Audio driver functions */
  43 static int AL_OpenAudio(_THIS, SDL_AudioSpec *spec);
  44 static void AL_WaitAudio(_THIS);
  45 static void AL_PlayAudio(_THIS);
  46 static Uint8 *AL_GetAudioBuf(_THIS);
  47 static void AL_CloseAudio(_THIS);
  48 
  49 /* Audio driver bootstrap functions */
  50 
  51 static int Audio_Available(void)
     /* [<][>][^][v][top][bottom][index][help] */
  52 {
  53         return 1;
  54 }
  55 
  56 static void Audio_DeleteDevice(SDL_AudioDevice *device)
     /* [<][>][^][v][top][bottom][index][help] */
  57 {
  58         free(device->hidden);
  59         free(device);
  60 }
  61 
  62 static SDL_AudioDevice *Audio_CreateDevice(int devindex)
     /* [<][>][^][v][top][bottom][index][help] */
  63 {
  64         SDL_AudioDevice *this;
  65 
  66         /* Initialize all variables that we clean on shutdown */
  67         this = (SDL_AudioDevice *)malloc(sizeof(SDL_AudioDevice));
  68         if ( this ) {
  69                 memset(this, 0, (sizeof *this));
  70                 this->hidden = (struct SDL_PrivateAudioData *)
  71                                 malloc((sizeof *this->hidden));
  72         }
  73         if ( (this == NULL) || (this->hidden == NULL) ) {
  74                 SDL_OutOfMemory();
  75                 if ( this ) {
  76                         free(this);
  77                 }
  78                 return(0);
  79         }
  80         memset(this->hidden, 0, (sizeof *this->hidden));
  81 
  82         /* Set the function pointers */
  83         this->OpenAudio = AL_OpenAudio;
  84         this->WaitAudio = AL_WaitAudio;
  85         this->PlayAudio = AL_PlayAudio;
  86         this->GetAudioBuf = AL_GetAudioBuf;
  87         this->CloseAudio = AL_CloseAudio;
  88 
  89         this->free = Audio_DeleteDevice;
  90 
  91         return this;
  92 }
  93 
  94 AudioBootStrap AUDIO_bootstrap = {
  95         "AL", "IRIX DMedia audio",
  96         Audio_Available, Audio_CreateDevice
  97 };
  98 
  99 
 100 void static AL_WaitAudio(_THIS)
     /* [<][>][^][v][top][bottom][index][help] */
 101 {
 102         Sint32 timeleft;
 103 
 104         timeleft = this->spec.samples - alGetFillable(audio_port);
 105         if ( timeleft > 0 ) {
 106                 timeleft /= (this->spec.freq/1000);
 107                 SDL_Delay((Uint32)timeleft);
 108         }
 109 }
 110 
 111 static void AL_PlayAudio(_THIS)
     /* [<][>][^][v][top][bottom][index][help] */
 112 {
 113         /* Write the audio data out */
 114         if ( alWriteFrames(audio_port, mixbuf, this->spec.samples) < 0 ) {
 115                 /* Assume fatal error, for now */
 116                 this->enabled = 0;
 117         }
 118 }
 119 
 120 static Uint8 *AL_GetAudioBuf(_THIS)
     /* [<][>][^][v][top][bottom][index][help] */
 121 {
 122         return(mixbuf);
 123 }
 124 
 125 static void AL_CloseAudio(_THIS)
     /* [<][>][^][v][top][bottom][index][help] */
 126 {
 127         if ( mixbuf != NULL ) {
 128                 SDL_FreeAudioMem(mixbuf);
 129                 mixbuf = NULL;
 130         }
 131         if ( audio_port != NULL ) {
 132                 ALcloseport(audio_port);
 133                 audio_port = NULL;
 134         }
 135 }
 136 
 137 static int AL_OpenAudio(_THIS, SDL_AudioSpec *spec)
     /* [<][>][^][v][top][bottom][index][help] */
 138 {
 139         ALconfig audio_config;
 140         ALpv audio_param;
 141         int width;
 142 
 143         /* Determine the audio parameters from the AudioSpec */
 144         switch ( spec->format & 0xFF ) {
 145 
 146                 case 8: { /* Signed 8 bit audio data */
 147                         spec->format = AUDIO_S8;
 148                         width = AL_SAMPLE_8;
 149                 }
 150                 break;
 151 
 152                 case 16: { /* Signed 16 bit audio data */
 153                         spec->format = AUDIO_S16MSB;
 154                         width = AL_SAMPLE_16;
 155                 }
 156                 break;
 157 
 158                 default: {
 159                         SDL_SetError("Unsupported audio format");
 160                         return(-1);
 161                 }
 162         }
 163 
 164         /* Update the fragment size as size in bytes */
 165         SDL_CalculateAudioSpec(spec);
 166 
 167         /* Set output frequency */
 168         audio_param.param = AL_RATE;
 169         audio_param.value.i = spec->freq;
 170         if( alSetParams(AL_DEFAULT_OUTPUT, &audio_param, 1) < 0 ) {
 171                 SDL_SetError("alSetParams failed");
 172                 return(-1);
 173         }
 174 
 175         /* Open the audio port with the requested frequency */
 176         audio_port = NULL;
 177         audio_config = alNewConfig();
 178         if ( audio_config &&
 179              (alSetSampFmt(audio_config, AL_SAMPFMT_TWOSCOMP) >= 0) &&
 180              (alSetWidth(audio_config, width) >= 0) &&
 181              (alSetQueueSize(audio_config, spec->samples*2) >= 0) &&
 182              (alSetChannels(audio_config, spec->channels) >= 0) ) {
 183                 audio_port = ALopenport("SDL audio", "w", audio_config);
 184         }
 185         alFreeConfig(audio_config);
 186         if( audio_port == NULL ) {
 187                 SDL_SetError("Unable to open audio port");
 188                 return(-1);
 189         }
 190 
 191         /* Allocate mixing buffer */
 192         mixbuf = (Uint8 *)SDL_AllocAudioMem(spec->size);
 193         if ( mixbuf == NULL ) {
 194                 SDL_OutOfMemory();
 195                 return(-1);
 196         }
 197         memset(mixbuf, spec->silence, spec->size);
 198 
 199         /* We're ready to rock and roll. :-) */
 200         return(0);
 201 }

/* [<][>][^][v][top][bottom][index][help] */