src/audio/SDL_audio.c
branchSDL-1.3
changeset 1662 782fd950bd46
parent 1660 8b9d79e7eacf
child 1668 4da1ee79c9af
equal deleted inserted replaced
1661:281d3f4870e5 1662:782fd950bd46
    35 #endif
    35 #endif
    36 
    36 
    37 /* Available audio drivers */
    37 /* Available audio drivers */
    38 static AudioBootStrap *bootstrap[] = {
    38 static AudioBootStrap *bootstrap[] = {
    39 #if SDL_AUDIO_DRIVER_BSD
    39 #if SDL_AUDIO_DRIVER_BSD
    40 	&BSD_AUDIO_bootstrap,
    40     &BSD_AUDIO_bootstrap,
    41 #endif
    41 #endif
    42 #if SDL_AUDIO_DRIVER_OSS
    42 #if SDL_AUDIO_DRIVER_OSS
    43 	&DSP_bootstrap,
    43     &DSP_bootstrap,
    44 	&DMA_bootstrap,
    44     &DMA_bootstrap,
    45 #endif
    45 #endif
    46 #if SDL_AUDIO_DRIVER_ALSA
    46 #if SDL_AUDIO_DRIVER_ALSA
    47 	&ALSA_bootstrap,
    47     &ALSA_bootstrap,
    48 #endif
    48 #endif
    49 #if SDL_AUDIO_DRIVER_QNXNTO
    49 #if SDL_AUDIO_DRIVER_QNXNTO
    50 	&QNXNTOAUDIO_bootstrap,
    50     &QNXNTOAUDIO_bootstrap,
    51 #endif
    51 #endif
    52 #if SDL_AUDIO_DRIVER_SUNAUDIO
    52 #if SDL_AUDIO_DRIVER_SUNAUDIO
    53 	&SUNAUDIO_bootstrap,
    53     &SUNAUDIO_bootstrap,
    54 #endif
    54 #endif
    55 #if SDL_AUDIO_DRIVER_DMEDIA
    55 #if SDL_AUDIO_DRIVER_DMEDIA
    56 	&DMEDIA_bootstrap,
    56     &DMEDIA_bootstrap,
    57 #endif
    57 #endif
    58 #if SDL_AUDIO_DRIVER_ARTS
    58 #if SDL_AUDIO_DRIVER_ARTS
    59 	&ARTS_bootstrap,
    59     &ARTS_bootstrap,
    60 #endif
    60 #endif
    61 #if SDL_AUDIO_DRIVER_ESD
    61 #if SDL_AUDIO_DRIVER_ESD
    62 	&ESD_bootstrap,
    62     &ESD_bootstrap,
    63 #endif
    63 #endif
    64 #if SDL_AUDIO_DRIVER_NAS
    64 #if SDL_AUDIO_DRIVER_NAS
    65 	&NAS_bootstrap,
    65     &NAS_bootstrap,
    66 #endif
    66 #endif
    67 #if SDL_AUDIO_DRIVER_DSOUND
    67 #if SDL_AUDIO_DRIVER_DSOUND
    68 	&DSOUND_bootstrap,
    68     &DSOUND_bootstrap,
    69 #endif
    69 #endif
    70 #if SDL_AUDIO_DRIVER_WAVEOUT
    70 #if SDL_AUDIO_DRIVER_WAVEOUT
    71 	&WAVEOUT_bootstrap,
    71     &WAVEOUT_bootstrap,
    72 #endif
    72 #endif
    73 #if SDL_AUDIO_DRIVER_PAUD
    73 #if SDL_AUDIO_DRIVER_PAUD
    74 	&Paud_bootstrap,
    74     &Paud_bootstrap,
    75 #endif
    75 #endif
    76 #if SDL_AUDIO_DRIVER_BAUDIO
    76 #if SDL_AUDIO_DRIVER_BAUDIO
    77 	&BAUDIO_bootstrap,
    77     &BAUDIO_bootstrap,
    78 #endif
    78 #endif
    79 #if SDL_AUDIO_DRIVER_COREAUDIO
    79 #if SDL_AUDIO_DRIVER_COREAUDIO
    80 	&COREAUDIO_bootstrap,
    80     &COREAUDIO_bootstrap,
    81 #endif
    81 #endif
    82 #if SDL_AUDIO_DRIVER_SNDMGR
    82 #if SDL_AUDIO_DRIVER_SNDMGR
    83 	&SNDMGR_bootstrap,
    83     &SNDMGR_bootstrap,
    84 #endif
    84 #endif
    85 #if SDL_AUDIO_DRIVER_AHI
    85 #if SDL_AUDIO_DRIVER_AHI
    86 	&AHI_bootstrap,
    86     &AHI_bootstrap,
    87 #endif
    87 #endif
    88 #if SDL_AUDIO_DRIVER_MINT
    88 #if SDL_AUDIO_DRIVER_MINT
    89 	&MINTAUDIO_GSXB_bootstrap,
    89     &MINTAUDIO_GSXB_bootstrap,
    90 	&MINTAUDIO_MCSN_bootstrap,
    90     &MINTAUDIO_MCSN_bootstrap,
    91 	&MINTAUDIO_STFA_bootstrap,
    91     &MINTAUDIO_STFA_bootstrap,
    92 	&MINTAUDIO_XBIOS_bootstrap,
    92     &MINTAUDIO_XBIOS_bootstrap,
    93 	&MINTAUDIO_DMA8_bootstrap,
    93     &MINTAUDIO_DMA8_bootstrap,
    94 #endif
    94 #endif
    95 #if SDL_AUDIO_DRIVER_DISK
    95 #if SDL_AUDIO_DRIVER_DISK
    96 	&DISKAUD_bootstrap,
    96     &DISKAUD_bootstrap,
    97 #endif
    97 #endif
    98 #if SDL_AUDIO_DRIVER_DUMMY
    98 #if SDL_AUDIO_DRIVER_DUMMY
    99 	&DUMMYAUD_bootstrap,
    99     &DUMMYAUD_bootstrap,
   100 #endif
   100 #endif
   101 #if SDL_AUDIO_DRIVER_DC
   101 #if SDL_AUDIO_DRIVER_DC
   102 	&DCAUD_bootstrap,
   102     &DCAUD_bootstrap,
   103 #endif
   103 #endif
   104 #if SDL_AUDIO_DRIVER_MMEAUDIO
   104 #if SDL_AUDIO_DRIVER_MMEAUDIO
   105 	&MMEAUDIO_bootstrap,
   105     &MMEAUDIO_bootstrap,
   106 #endif
   106 #endif
   107 #if SDL_AUDIO_DRIVER_DART
   107 #if SDL_AUDIO_DRIVER_DART
   108 	&DART_bootstrap,
   108     &DART_bootstrap,
   109 #endif
   109 #endif
   110 	NULL
   110     NULL
   111 };
   111 };
   112 SDL_AudioDevice *current_audio = NULL;
   112 SDL_AudioDevice *current_audio = NULL;
   113 
   113 
   114 /* Various local functions */
   114 /* Various local functions */
   115 int SDL_AudioInit(const char *driver_name);
   115 int SDL_AudioInit (const char *driver_name);
   116 void SDL_AudioQuit(void);
   116 void SDL_AudioQuit (void);
   117 
   117 
   118 #if SDL_AUDIO_DRIVER_AHI
   118 #if SDL_AUDIO_DRIVER_AHI
   119 static int audio_configured = 0;
   119 static int audio_configured = 0;
   120 #endif
   120 #endif
   121 
   121 
   122 /* The general mixing thread function */
   122 /* The general mixing thread function */
   123 int SDLCALL SDL_RunAudio(void *audiop)
   123 int SDLCALL
   124 {
   124 SDL_RunAudio (void *audiop)
   125 	SDL_AudioDevice *audio = (SDL_AudioDevice *)audiop;
   125 {
   126 	Uint8 *stream;
   126     SDL_AudioDevice *audio = (SDL_AudioDevice *) audiop;
   127 	int    stream_len;
   127     Uint8 *stream;
   128 	void  *udata;
   128     int stream_len;
   129 	void (SDLCALL *fill)(void *userdata,Uint8 *stream, int len);
   129     void *udata;
   130 	int    silence;
   130     void (SDLCALL * fill) (void *userdata, Uint8 * stream, int len);
       
   131     int silence;
   131 #if SDL_AUDIO_DRIVER_AHI
   132 #if SDL_AUDIO_DRIVER_AHI
   132 	int started = 0;
   133     int started = 0;
   133 
   134 
   134 /* AmigaOS NEEDS that the audio driver is opened in the thread that uses it! */
   135 /* AmigaOS NEEDS that the audio driver is opened in the thread that uses it! */
   135 
   136 
   136 	D(bug("Task audio started audio struct:<%lx>...\n",audiop));
   137     D (bug ("Task audio started audio struct:<%lx>...\n", audiop));
   137 
   138 
   138 	D(bug("Before Openaudio..."));
   139     D (bug ("Before Openaudio..."));
   139 	if(audio->OpenAudio(audio, &audio->spec)==-1)
   140     if (audio->OpenAudio (audio, &audio->spec) == -1) {
   140 	{
   141         D (bug ("Open audio failed...\n"));
   141 		D(bug("Open audio failed...\n"));
   142         return (-1);
   142 		return(-1);
   143     }
   143 	}
   144     D (bug ("OpenAudio...OK\n"));
   144 	D(bug("OpenAudio...OK\n"));
   145 #endif
   145 #endif
   146 
   146 
   147     /* Perform any thread setup */
   147 	/* Perform any thread setup */
   148     if (audio->ThreadInit) {
   148 	if ( audio->ThreadInit ) {
   149         audio->ThreadInit (audio);
   149 		audio->ThreadInit(audio);
   150     }
   150 	}
   151     audio->threadid = SDL_ThreadID ();
   151 	audio->threadid = SDL_ThreadID();
   152 
   152 
   153     /* Set up the mixing function */
   153 	/* Set up the mixing function */
   154     fill = audio->spec.callback;
   154 	fill  = audio->spec.callback;
   155     udata = audio->spec.userdata;
   155 	udata = audio->spec.userdata;
       
   156 
   156 
   157 #if SDL_AUDIO_DRIVER_AHI
   157 #if SDL_AUDIO_DRIVER_AHI
   158 	audio_configured = 1;
   158     audio_configured = 1;
   159 
   159 
   160 	D(bug("Audio configured... Checking for conversion\n"));
   160     D (bug ("Audio configured... Checking for conversion\n"));
   161 	SDL_mutexP(audio->mixer_lock);
   161     SDL_mutexP (audio->mixer_lock);
   162 	D(bug("Semaphore obtained...\n"));
   162     D (bug ("Semaphore obtained...\n"));
   163 #endif
   163 #endif
   164 
   164 
   165 	if ( audio->convert.needed ) {
   165     if (audio->convert.needed) {
   166 		if ( audio->convert.src_format == AUDIO_U8 ) {
   166         if (audio->convert.src_format == AUDIO_U8) {
   167 			silence = 0x80;
   167             silence = 0x80;
   168 		} else {
   168         } else {
   169 			silence = 0;
   169             silence = 0;
   170 		}
   170         }
   171 		stream_len = audio->convert.len;
   171         stream_len = audio->convert.len;
   172 	} else {
   172     } else {
   173 		silence = audio->spec.silence;
   173         silence = audio->spec.silence;
   174 		stream_len = audio->spec.size;
   174         stream_len = audio->spec.size;
   175 	}
   175     }
   176 
   176 
   177 #if SDL_AUDIO_DRIVER_AHI
   177 #if SDL_AUDIO_DRIVER_AHI
   178 	SDL_mutexV(audio->mixer_lock);
   178     SDL_mutexV (audio->mixer_lock);
   179 	D(bug("Entering audio loop...\n"));
   179     D (bug ("Entering audio loop...\n"));
   180 #endif
   180 #endif
   181 
   181 
   182 #ifdef __OS2__
   182 #ifdef __OS2__
   183         /* Increase the priority of this thread to make sure that
   183     /* Increase the priority of this thread to make sure that
   184            the audio will be continuous all the time! */
   184        the audio will be continuous all the time! */
   185 #ifdef USE_DOSSETPRIORITY
   185 #ifdef USE_DOSSETPRIORITY
   186         if (SDL_getenv("SDL_USE_TIMECRITICAL_AUDIO"))
   186     if (SDL_getenv ("SDL_USE_TIMECRITICAL_AUDIO")) {
   187         {
       
   188 #ifdef DEBUG_BUILD
   187 #ifdef DEBUG_BUILD
   189           printf("[SDL_RunAudio] : Setting priority to TimeCritical+0! (TID%d)\n", SDL_ThreadID());
   188         printf
   190 #endif
   189             ("[SDL_RunAudio] : Setting priority to TimeCritical+0! (TID%d)\n",
   191           DosSetPriority(PRTYS_THREAD, PRTYC_TIMECRITICAL, 0, 0);
   190              SDL_ThreadID ());
   192         }
   191 #endif
   193         else
   192         DosSetPriority (PRTYS_THREAD, PRTYC_TIMECRITICAL, 0, 0);
   194         {
   193     } else {
   195 #ifdef DEBUG_BUILD
   194 #ifdef DEBUG_BUILD
   196           printf("[SDL_RunAudio] : Setting priority to ForegroundServer+0! (TID%d)\n", SDL_ThreadID());
   195         printf
   197 #endif
   196             ("[SDL_RunAudio] : Setting priority to ForegroundServer+0! (TID%d)\n",
   198           DosSetPriority(PRTYS_THREAD, PRTYC_FOREGROUNDSERVER, 0, 0);
   197              SDL_ThreadID ());
   199         }
   198 #endif
   200 #endif
   199         DosSetPriority (PRTYS_THREAD, PRTYC_FOREGROUNDSERVER, 0, 0);
   201 #endif
   200     }
   202 
   201 #endif
   203 	/* Loop, filling the audio buffers */
   202 #endif
   204 	while ( audio->enabled ) {
   203 
   205 
   204     /* Loop, filling the audio buffers */
   206 		/* Fill the current buffer with sound */
   205     while (audio->enabled) {
   207 		if ( audio->convert.needed ) {
   206 
   208 			if ( audio->convert.buf ) {
   207         /* Fill the current buffer with sound */
   209 				stream = audio->convert.buf;
   208         if (audio->convert.needed) {
   210 			} else {
   209             if (audio->convert.buf) {
   211 				continue;
   210                 stream = audio->convert.buf;
   212 			}
   211             } else {
   213 		} else {
   212                 continue;
   214 			stream = audio->GetAudioBuf(audio);
   213             }
   215 			if ( stream == NULL ) {
   214         } else {
   216 				stream = audio->fake_stream;
   215             stream = audio->GetAudioBuf (audio);
   217 			}
   216             if (stream == NULL) {
   218 		}
   217                 stream = audio->fake_stream;
   219 		SDL_memset(stream, silence, stream_len);
   218             }
   220 
   219         }
   221 		if ( ! audio->paused ) {
   220         SDL_memset (stream, silence, stream_len);
   222 			SDL_mutexP(audio->mixer_lock);
   221 
   223 			(*fill)(udata, stream, stream_len);
   222         if (!audio->paused) {
   224 			SDL_mutexV(audio->mixer_lock);
   223             SDL_mutexP (audio->mixer_lock);
   225 		}
   224             (*fill) (udata, stream, stream_len);
   226 
   225             SDL_mutexV (audio->mixer_lock);
   227 		/* Convert the audio if necessary */
   226         }
   228 		if ( audio->convert.needed ) {
   227 
   229 			SDL_ConvertAudio(&audio->convert);
   228         /* Convert the audio if necessary */
   230 			stream = audio->GetAudioBuf(audio);
   229         if (audio->convert.needed) {
   231 			if ( stream == NULL ) {
   230             SDL_ConvertAudio (&audio->convert);
   232 				stream = audio->fake_stream;
   231             stream = audio->GetAudioBuf (audio);
   233 			}
   232             if (stream == NULL) {
   234 			SDL_memcpy(stream, audio->convert.buf,
   233                 stream = audio->fake_stream;
   235 			               audio->convert.len_cvt);
   234             }
   236 		}
   235             SDL_memcpy (stream, audio->convert.buf, audio->convert.len_cvt);
   237 
   236         }
   238 		/* Ready current buffer for play and change current buffer */
   237 
   239 		if ( stream != audio->fake_stream ) {
   238         /* Ready current buffer for play and change current buffer */
   240 			audio->PlayAudio(audio);
   239         if (stream != audio->fake_stream) {
   241 		}
   240             audio->PlayAudio (audio);
   242 
   241         }
   243 		/* Wait for an audio buffer to become available */
   242 
   244 		if ( stream == audio->fake_stream ) {
   243         /* Wait for an audio buffer to become available */
   245 			SDL_Delay((audio->spec.samples*1000)/audio->spec.freq);
   244         if (stream == audio->fake_stream) {
   246 		} else {
   245             SDL_Delay ((audio->spec.samples * 1000) / audio->spec.freq);
   247 			audio->WaitAudio(audio);
   246         } else {
   248 		}
   247             audio->WaitAudio (audio);
   249 	}
   248         }
   250 
   249     }
   251 	/* Wait for the audio to drain.. */
   250 
   252 	if ( audio->WaitDone ) {
   251     /* Wait for the audio to drain.. */
   253 		audio->WaitDone(audio);
   252     if (audio->WaitDone) {
   254 	}
   253         audio->WaitDone (audio);
   255 
   254     }
   256 #if SDL_AUDIO_DRIVER_AHI
   255 #if SDL_AUDIO_DRIVER_AHI
   257 	D(bug("WaitAudio...Done\n"));
   256     D (bug ("WaitAudio...Done\n"));
   258 
   257 
   259 	audio->CloseAudio(audio);
   258     audio->CloseAudio (audio);
   260 
   259 
   261 	D(bug("CloseAudio..Done, subtask exiting...\n"));
   260     D (bug ("CloseAudio..Done, subtask exiting...\n"));
   262 	audio_configured = 0;
   261     audio_configured = 0;
   263 #endif
   262 #endif
   264 #ifdef __OS2__
   263 #ifdef __OS2__
   265 #ifdef DEBUG_BUILD
   264 #ifdef DEBUG_BUILD
   266         printf("[SDL_RunAudio] : Task exiting. (TID%d)\n", SDL_ThreadID());
   265     printf ("[SDL_RunAudio] : Task exiting. (TID%d)\n", SDL_ThreadID ());
   267 #endif
   266 #endif
   268 #endif
   267 #endif
   269 	return(0);
   268     return (0);
   270 }
   269 }
   271 
   270 
   272 static void SDL_LockAudio_Default(SDL_AudioDevice *audio)
   271 static void
   273 {
   272 SDL_LockAudio_Default (SDL_AudioDevice * audio)
   274 	if ( audio->thread && (SDL_ThreadID() == audio->threadid) ) {
   273 {
   275 		return;
   274     if (audio->thread && (SDL_ThreadID () == audio->threadid)) {
   276 	}
   275         return;
   277 	SDL_mutexP(audio->mixer_lock);
   276     }
   278 }
   277     SDL_mutexP (audio->mixer_lock);
   279 
   278 }
   280 static void SDL_UnlockAudio_Default(SDL_AudioDevice *audio)
   279 
   281 {
   280 static void
   282 	if ( audio->thread && (SDL_ThreadID() == audio->threadid) ) {
   281 SDL_UnlockAudio_Default (SDL_AudioDevice * audio)
   283 		return;
   282 {
   284 	}
   283     if (audio->thread && (SDL_ThreadID () == audio->threadid)) {
   285 	SDL_mutexV(audio->mixer_lock);
   284         return;
   286 }
   285     }
   287 
   286     SDL_mutexV (audio->mixer_lock);
   288 static Uint16 SDL_ParseAudioFormat(const char *string)
   287 }
   289 {
   288 
   290 	Uint16 format = 0;
   289 static Uint16
   291 
   290 SDL_ParseAudioFormat (const char *string)
   292 	switch (*string) {
   291 {
   293 	    case 'U':
   292     Uint16 format = 0;
   294 		++string;
   293 
   295 		format |= 0x0000;
   294     switch (*string) {
   296 		break;
   295     case 'U':
   297 	    case 'S':
   296         ++string;
   298 		++string;
   297         format |= 0x0000;
   299 		format |= 0x8000;
   298         break;
   300 		break;
   299     case 'S':
   301 	    default:
   300         ++string;
   302 		return 0;
   301         format |= 0x8000;
   303 	}
   302         break;
   304 	switch (SDL_atoi(string)) {
   303     default:
   305 	    case 8:
   304         return 0;
   306 		string += 1;
   305     }
   307 		format |= 8;
   306     switch (SDL_atoi (string)) {
   308 		break;
   307     case 8:
   309 	    case 16:
   308         string += 1;
   310 		string += 2;
   309         format |= 8;
   311 		format |= 16;
   310         break;
   312 		if ( SDL_strcmp(string, "LSB") == 0
   311     case 16:
       
   312         string += 2;
       
   313         format |= 16;
       
   314         if (SDL_strcmp (string, "LSB") == 0
   313 #if SDL_BYTEORDER == SDL_LIL_ENDIAN
   315 #if SDL_BYTEORDER == SDL_LIL_ENDIAN
   314 		     || SDL_strcmp(string, "SYS") == 0
   316             || SDL_strcmp (string, "SYS") == 0
   315 #endif
   317 #endif
   316 		    ) {
   318             ) {
   317 			format |= 0x0000;
   319             format |= 0x0000;
   318 		}
   320         }
   319 		if ( SDL_strcmp(string, "MSB") == 0
   321         if (SDL_strcmp (string, "MSB") == 0
   320 #if SDL_BYTEORDER == SDL_BIG_ENDIAN
   322 #if SDL_BYTEORDER == SDL_BIG_ENDIAN
   321 		     || SDL_strcmp(string, "SYS") == 0
   323             || SDL_strcmp (string, "SYS") == 0
   322 #endif
   324 #endif
   323 		    ) {
   325             ) {
   324 			format |= 0x1000;
   326             format |= 0x1000;
   325 		}
   327         }
   326 		break;
   328         break;
   327 	    default:
   329     default:
   328 		return 0;
   330         return 0;
   329 	}
   331     }
   330 	return format;
   332     return format;
   331 }
   333 }
   332 
   334 
   333 int SDL_GetNumAudioDrivers(void)
   335 int
   334 {
   336 SDL_GetNumAudioDrivers (void)
   335 	return(SDL_arraysize(bootstrap)-1);
   337 {
   336 }
   338     return (SDL_arraysize (bootstrap) - 1);
   337 
   339 }
   338 const char *SDL_GetAudioDriver(int index)
   340 
   339 {
   341 const char *
   340 	if ( index >= 0 && index < SDL_GetNumAudioDrivers() ) {
   342 SDL_GetAudioDriver (int index)
   341 		return(bootstrap[index]->name);
   343 {
   342 	}
   344     if (index >= 0 && index < SDL_GetNumAudioDrivers ()) {
   343 	return(NULL);
   345         return (bootstrap[index]->name);
   344 }
   346     }
   345 
   347     return (NULL);
   346 int SDL_AudioInit(const char *driver_name)
   348 }
   347 {
   349 
   348 	SDL_AudioDevice *audio;
   350 int
   349 	int i = 0, idx;
   351 SDL_AudioInit (const char *driver_name)
   350 
   352 {
   351 	/* Check to make sure we don't overwrite 'current_audio' */
   353     SDL_AudioDevice *audio;
   352 	if ( current_audio != NULL ) {
   354     int i = 0, idx;
   353 		SDL_AudioQuit();
   355 
   354 	}
   356     /* Check to make sure we don't overwrite 'current_audio' */
   355 
   357     if (current_audio != NULL) {
   356 	/* Select the proper audio driver */
   358         SDL_AudioQuit ();
   357 	audio = NULL;
   359     }
   358 	idx = 0;
   360 
       
   361     /* Select the proper audio driver */
       
   362     audio = NULL;
       
   363     idx = 0;
   359 #if SDL_AUDIO_DRIVER_ESD
   364 #if SDL_AUDIO_DRIVER_ESD
   360 	if ( (driver_name == NULL) && (SDL_getenv("ESPEAKER") != NULL) ) {
   365     if ((driver_name == NULL) && (SDL_getenv ("ESPEAKER") != NULL)) {
   361 		/* Ahem, we know that if ESPEAKER is set, user probably wants
   366         /* Ahem, we know that if ESPEAKER is set, user probably wants
   362 		   to use ESD, but don't start it if it's not already running.
   367            to use ESD, but don't start it if it's not already running.
   363 		   This probably isn't the place to do this, but... Shh! :)
   368            This probably isn't the place to do this, but... Shh! :)
   364 		 */
   369          */
   365 		for ( i=0; bootstrap[i]; ++i ) {
   370         for (i = 0; bootstrap[i]; ++i) {
   366 			if ( SDL_strcmp(bootstrap[i]->name, "esd") == 0 ) {
   371             if (SDL_strcmp (bootstrap[i]->name, "esd") == 0) {
   367 #ifdef HAVE_PUTENV
   372 #ifdef HAVE_PUTENV
   368 				const char *esd_no_spawn;
   373                 const char *esd_no_spawn;
   369 
   374 
   370 				/* Don't start ESD if it's not running */
   375                 /* Don't start ESD if it's not running */
   371 				esd_no_spawn = getenv("ESD_NO_SPAWN");
   376                 esd_no_spawn = getenv ("ESD_NO_SPAWN");
   372 				if ( esd_no_spawn == NULL ) {
   377                 if (esd_no_spawn == NULL) {
   373 					putenv("ESD_NO_SPAWN=1");
   378                     putenv ("ESD_NO_SPAWN=1");
   374 				}
   379                 }
   375 #endif
   380 #endif
   376 				if ( bootstrap[i]->available() ) {
   381                 if (bootstrap[i]->available ()) {
   377 					audio = bootstrap[i]->create(0);
   382                     audio = bootstrap[i]->create (0);
   378 					break;
   383                     break;
   379 				}
   384                 }
   380 #ifdef HAVE_UNSETENV
   385 #ifdef HAVE_UNSETENV
   381 				if ( esd_no_spawn == NULL ) {
   386                 if (esd_no_spawn == NULL) {
   382 					unsetenv("ESD_NO_SPAWN");
   387                     unsetenv ("ESD_NO_SPAWN");
   383 				}
   388                 }
   384 #endif
   389 #endif
   385 			}
   390             }
   386 		}
   391         }
   387 	}
   392     }
   388 #endif /* SDL_AUDIO_DRIVER_ESD */
   393 #endif /* SDL_AUDIO_DRIVER_ESD */
   389 	if ( audio == NULL ) {
   394     if (audio == NULL) {
   390 		if ( driver_name != NULL ) {
   395         if (driver_name != NULL) {
   391 #if 0	/* This will be replaced with a better driver selection API */
   396 #if 0                           /* This will be replaced with a better driver selection API */
   392 			if ( SDL_strrchr(driver_name, ':') != NULL ) {
   397             if (SDL_strrchr (driver_name, ':') != NULL) {
   393 				idx = atoi(SDL_strrchr(driver_name, ':')+1);
   398                 idx = atoi (SDL_strrchr (driver_name, ':') + 1);
   394 			}
   399             }
   395 #endif
   400 #endif
   396 			for ( i=0; bootstrap[i]; ++i ) {
   401             for (i = 0; bootstrap[i]; ++i) {
   397 				if (SDL_strncmp(bootstrap[i]->name, driver_name,
   402                 if (SDL_strncmp (bootstrap[i]->name, driver_name,
   398 				            SDL_strlen(bootstrap[i]->name)) == 0) {
   403                                  SDL_strlen (bootstrap[i]->name)) == 0) {
   399 					if ( bootstrap[i]->available() ) {
   404                     if (bootstrap[i]->available ()) {
   400 						audio=bootstrap[i]->create(idx);
   405                         audio = bootstrap[i]->create (idx);
   401 						break;
   406                     }
   402 					}
   407                     break;
   403 				}
   408                 }
   404 			}
   409             }
   405 		} else {
   410         } else {
   406 			for ( i=0; bootstrap[i]; ++i ) {
   411             for (i = 0; bootstrap[i]; ++i) {
   407 				if ( bootstrap[i]->available() ) {
   412                 if (bootstrap[i]->available ()) {
   408 					audio = bootstrap[i]->create(idx);
   413                     audio = bootstrap[i]->create (idx);
   409 					if ( audio != NULL ) {
   414                     if (audio != NULL) {
   410 						break;
   415                         break;
   411 					}
   416                     }
   412 				}
   417                 }
   413 			}
   418             }
   414 		}
   419         }
   415 		if ( audio == NULL ) {
   420         if (audio == NULL) {
   416 			SDL_SetError("No available audio device");
   421             if (driver_name) {
   417 #if 0 /* Don't fail SDL_Init() if audio isn't available.
   422                 SDL_SetError ("%s not available", driver_name);
   418          SDL_OpenAudio() will handle it at that point.  *sigh*
   423             } else {
   419        */
   424                 SDL_SetError ("No available audio device");
   420 			return(-1);
   425             }
   421 #endif
   426 #if 0                           /* Don't fail SDL_Init() if audio isn't available.
   422 		}
   427                                    SDL_OpenAudio() will handle it at that point.  *sigh*
   423 	}
   428                                  */
   424 	current_audio = audio;
   429             return (-1);
   425 	if ( current_audio ) {
   430 #endif
   426 		current_audio->name = bootstrap[i]->name;
   431         }
   427 		if ( !current_audio->LockAudio && !current_audio->UnlockAudio ) {
   432     }
   428 			current_audio->LockAudio = SDL_LockAudio_Default;
   433     current_audio = audio;
   429 			current_audio->UnlockAudio = SDL_UnlockAudio_Default;
   434     if (current_audio) {
   430 		}
   435         current_audio->name = bootstrap[i]->name;
   431 	}
   436         if (!current_audio->LockAudio && !current_audio->UnlockAudio) {
   432 	return(0);
   437             current_audio->LockAudio = SDL_LockAudio_Default;
   433 }
   438             current_audio->UnlockAudio = SDL_UnlockAudio_Default;
   434 
   439         }
   435 const char *SDL_GetCurrentAudioDriver()
   440     }
   436 {
   441     return (0);
   437 	if ( current_audio ) {
   442 }
   438 		return current_audio->name;
   443 
   439 	}
   444 /*
   440 	return(NULL);
   445  * Get the current audio driver name
   441 }
   446  */
   442 
   447 const char *
   443 int SDL_OpenAudio(SDL_AudioSpec *desired, SDL_AudioSpec *obtained)
   448 SDL_GetCurrentAudioDriver ()
   444 {
   449 {
   445 	SDL_AudioDevice *audio;
   450     if (current_audio) {
   446 	const char *env;
   451         return current_audio->name;
   447 
   452     }
   448 	/* Start up the audio driver, if necessary */
   453     return (NULL);
   449 	if ( ! current_audio ) {
   454 }
   450 		if ( (SDL_InitSubSystem(SDL_INIT_AUDIO) < 0) ||
   455 
   451 		     (current_audio == NULL) ) {
   456 int
   452 			return(-1);
   457 SDL_OpenAudio (SDL_AudioSpec * desired, SDL_AudioSpec * obtained)
   453 		}
   458 {
   454 	}
   459     SDL_AudioDevice *audio;
   455 	audio = current_audio;
   460     const char *env;
   456 
   461 
   457 	if (audio->opened) {
   462     /* Start up the audio driver, if necessary */
   458 		SDL_SetError("Audio device is already opened");
   463     if (!current_audio) {
   459 		return(-1);
   464         if ((SDL_InitSubSystem (SDL_INIT_AUDIO) < 0) ||
   460 	}
   465             (current_audio == NULL)) {
   461 
   466             return (-1);
   462 	/* Verify some parameters */
   467         }
   463 	if ( desired->freq == 0 ) {
   468     }
   464 		env = SDL_getenv("SDL_AUDIO_FREQUENCY");
   469     audio = current_audio;
   465 		if ( env ) {
   470 
   466 			desired->freq = SDL_atoi(env);
   471     if (audio->opened) {
   467 		}
   472         SDL_SetError ("Audio device is already opened");
   468 	}
   473         return (-1);
   469 	if ( desired->freq == 0 ) {
   474     }
   470 		/* Pick some default audio frequency */
   475 
   471 		desired->freq = 22050;
   476     /* Verify some parameters */
   472 	}
   477     if (desired->freq == 0) {
   473 	if ( desired->format == 0 ) {
   478         env = SDL_getenv ("SDL_AUDIO_FREQUENCY");
   474 		env = SDL_getenv("SDL_AUDIO_FORMAT");
   479         if (env) {
   475 		if ( env ) {
   480             desired->freq = SDL_atoi (env);
   476 			desired->format = SDL_ParseAudioFormat(env);
   481         }
   477 		}
   482     }
   478 	}
   483     if (desired->freq == 0) {
   479 	if ( desired->format == 0 ) {
   484         /* Pick some default audio frequency */
   480 		/* Pick some default audio format */
   485         desired->freq = 22050;
   481 		desired->format = AUDIO_S16;
   486     }
   482 	}
   487     if (desired->format == 0) {
   483 	if ( desired->channels == 0 ) {
   488         env = SDL_getenv ("SDL_AUDIO_FORMAT");
   484 		env = SDL_getenv("SDL_AUDIO_CHANNELS");
   489         if (env) {
   485 		if ( env ) {
   490             desired->format = SDL_ParseAudioFormat (env);
   486 			desired->channels = SDL_atoi(env);
   491         }
   487 		}
   492     }
   488 	}
   493     if (desired->format == 0) {
   489 	if ( desired->channels == 0 ) {
   494         /* Pick some default audio format */
   490 		/* Pick a default number of channels */
   495         desired->format = AUDIO_S16;
   491 		desired->channels = 2;
   496     }
   492 	}
   497     if (desired->channels == 0) {
   493 	switch ( desired->channels ) {
   498         env = SDL_getenv ("SDL_AUDIO_CHANNELS");
   494 	    case 1:	/* Mono */
   499         if (env) {
   495 	    case 2:	/* Stereo */
   500             desired->channels = SDL_atoi (env);
   496 	    case 4:	/* surround */
   501         }
   497 	    case 6:	/* surround with center and lfe */
   502     }
   498 		break;
   503     if (desired->channels == 0) {
   499 	    default:
   504         /* Pick a default number of channels */
   500 		SDL_SetError("1 (mono) and 2 (stereo) channels supported");
   505         desired->channels = 2;
   501 		return(-1);
   506     }
   502 	}
   507     switch (desired->channels) {
   503 	if ( desired->samples == 0 ) {
   508     case 1:                    /* Mono */
   504 		env = SDL_getenv("SDL_AUDIO_SAMPLES");
   509     case 2:                    /* Stereo */
   505 		if ( env ) {
   510     case 4:                    /* surround */
   506 			desired->samples = SDL_atoi(env);
   511     case 6:                    /* surround with center and lfe */
   507 		}
   512         break;
   508 	}
   513     default:
   509 	if ( desired->samples == 0 ) {
   514         SDL_SetError ("1 (mono) and 2 (stereo) channels supported");
   510 		/* Pick a default of ~46 ms at desired frequency */
   515         return (-1);
   511 		int samples = (desired->freq / 1000) * 46;
   516     }
   512 		int power2 = 1;
   517     if (desired->samples == 0) {
   513 		while ( power2 < samples ) {
   518         env = SDL_getenv ("SDL_AUDIO_SAMPLES");
   514 			power2 *= 2;
   519         if (env) {
   515 		}
   520             desired->samples = SDL_atoi (env);
   516 		desired->samples = power2;
   521         }
   517 	}
   522     }
   518 	if ( desired->callback == NULL ) {
   523     if (desired->samples == 0) {
   519 		SDL_SetError("SDL_OpenAudio() passed a NULL callback");
   524         /* Pick a default of ~46 ms at desired frequency */
   520 		return(-1);
   525         int samples = (desired->freq / 1000) * 46;
   521 	}
   526         int power2 = 1;
   522 
   527         while (power2 < samples) {
       
   528             power2 *= 2;
       
   529         }
       
   530         desired->samples = power2;
       
   531     }
       
   532     if (desired->callback == NULL) {
       
   533         SDL_SetError ("SDL_OpenAudio() passed a NULL callback");
       
   534         return (-1);
       
   535     }
   523 #if defined(__MACOS__) || (defined(__RISCOS__) && SDL_THREADS_DISABLED)
   536 #if defined(__MACOS__) || (defined(__RISCOS__) && SDL_THREADS_DISABLED)
   524 	/* FIXME: Need to implement PPC interrupt asm for SDL_LockAudio() */
   537     /* FIXME: Need to implement PPC interrupt asm for SDL_LockAudio() */
   525 #else
   538 #else
   526 #if defined(__MINT__) && SDL_THREADS_DISABLED
   539 #if defined(__MINT__) && SDL_THREADS_DISABLED
   527 	/* Uses interrupt driven audio, without thread */
   540     /* Uses interrupt driven audio, without thread */
   528 #else
   541 #else
   529 	/* Create a semaphore for locking the sound buffers */
   542     /* Create a semaphore for locking the sound buffers */
   530 	audio->mixer_lock = SDL_CreateMutex();
   543     audio->mixer_lock = SDL_CreateMutex ();
   531 	if ( audio->mixer_lock == NULL ) {
   544     if (audio->mixer_lock == NULL) {
   532 		SDL_SetError("Couldn't create mixer lock");
   545         SDL_SetError ("Couldn't create mixer lock");
   533 		SDL_CloseAudio();
   546         SDL_CloseAudio ();
   534 		return(-1);
   547         return (-1);
   535 	}
   548     }
   536 #endif /* __MINT__ */
   549 #endif /* __MINT__ */
   537 #endif /* __MACOS__ */
   550 #endif /* __MACOS__ */
   538 
   551 
   539 	/* Calculate the silence and size of the audio specification */
   552     /* Calculate the silence and size of the audio specification */
   540 	SDL_CalculateAudioSpec(desired);
   553     SDL_CalculateAudioSpec (desired);
   541 
   554 
   542 	/* Open the audio subsystem */
   555     /* Open the audio subsystem */
   543 	SDL_memcpy(&audio->spec, desired, sizeof(audio->spec));
   556     SDL_memcpy (&audio->spec, desired, sizeof (audio->spec));
   544 	audio->convert.needed = 0;
   557     audio->convert.needed = 0;
   545 	audio->enabled = 1;
   558     audio->enabled = 1;
   546 	audio->paused  = 1;
   559     audio->paused = 1;
   547 
   560 
   548 #if !SDL_AUDIO_DRIVER_AHI
   561 #if !SDL_AUDIO_DRIVER_AHI
   549 
   562 
   550 /* AmigaOS opens audio inside the main loop */
   563 /* AmigaOS opens audio inside the main loop */
   551 	audio->opened = audio->OpenAudio(audio, &audio->spec)+1;
   564     audio->opened = audio->OpenAudio (audio, &audio->spec) + 1;
   552 
   565 
   553 	if ( ! audio->opened ) {
   566     if (!audio->opened) {
   554 		SDL_CloseAudio();
   567         SDL_CloseAudio ();
   555 		return(-1);
   568         return (-1);
   556 	}
   569     }
   557 #else
   570 #else
   558 	D(bug("Locking semaphore..."));
   571     D (bug ("Locking semaphore..."));
   559 	SDL_mutexP(audio->mixer_lock);
   572     SDL_mutexP (audio->mixer_lock);
   560 
   573 
   561 
   574 
   562 	audio->thread = SDL_CreateThread(SDL_RunAudio, audio);
   575     audio->thread = SDL_CreateThread (SDL_RunAudio, audio);
   563 	D(bug("Created thread...\n"));
   576     D (bug ("Created thread...\n"));
   564 
   577 
   565 	if ( audio->thread == NULL ) {
   578     if (audio->thread == NULL) {
   566 		SDL_mutexV(audio->mixer_lock);
   579         SDL_mutexV (audio->mixer_lock);
   567 		SDL_CloseAudio();
   580         SDL_CloseAudio ();
   568 		SDL_SetError("Couldn't create audio thread");
   581         SDL_SetError ("Couldn't create audio thread");
   569 		return(-1);
   582         return (-1);
   570 	}
   583     }
   571 
   584 
   572 	while(!audio_configured)
   585     while (!audio_configured)
   573 		SDL_Delay(100);
   586         SDL_Delay (100);
   574 #endif
   587 #endif
   575 
   588 
   576 	/* If the audio driver changes the buffer size, accept it */
   589     /* If the audio driver changes the buffer size, accept it */
   577 	if ( audio->spec.samples != desired->samples ) {
   590     if (audio->spec.samples != desired->samples) {
   578 		desired->samples = audio->spec.samples;
   591         desired->samples = audio->spec.samples;
   579 		SDL_CalculateAudioSpec(desired);
   592         SDL_CalculateAudioSpec (desired);
   580 	}
   593     }
   581 
   594 
   582 	/* Allocate a fake audio memory buffer */
   595     /* Allocate a fake audio memory buffer */
   583 	audio->fake_stream = SDL_AllocAudioMem(audio->spec.size);
   596     audio->fake_stream = SDL_AllocAudioMem (audio->spec.size);
   584 	if ( audio->fake_stream == NULL ) {
   597     if (audio->fake_stream == NULL) {
   585 		SDL_CloseAudio();
   598         SDL_CloseAudio ();
   586 		SDL_OutOfMemory();
   599         SDL_OutOfMemory ();
   587 		return(-1);
   600         return (-1);
   588 	}
   601     }
   589 
   602 
   590 	/* See if we need to do any conversion */
   603     /* See if we need to do any conversion */
   591 	if ( obtained != NULL ) {
   604     if (obtained != NULL) {
   592 		SDL_memcpy(obtained, &audio->spec, sizeof(audio->spec));
   605         SDL_memcpy (obtained, &audio->spec, sizeof (audio->spec));
   593 	} else if ( desired->freq != audio->spec.freq ||
   606     } else if (desired->freq != audio->spec.freq ||
   594                     desired->format != audio->spec.format ||
   607                desired->format != audio->spec.format ||
   595 	            desired->channels != audio->spec.channels ) {
   608                desired->channels != audio->spec.channels) {
   596 		/* Build an audio conversion block */
   609         /* Build an audio conversion block */
   597 		if ( SDL_BuildAudioCVT(&audio->convert,
   610         if (SDL_BuildAudioCVT (&audio->convert,
   598 			desired->format, desired->channels,
   611                                desired->format, desired->channels,
   599 					desired->freq,
   612                                desired->freq,
   600 			audio->spec.format, audio->spec.channels,
   613                                audio->spec.format, audio->spec.channels,
   601 					audio->spec.freq) < 0 ) {
   614                                audio->spec.freq) < 0) {
   602 			SDL_CloseAudio();
   615             SDL_CloseAudio ();
   603 			return(-1);
   616             return (-1);
   604 		}
   617         }
   605 		if ( audio->convert.needed ) {
   618         if (audio->convert.needed) {
   606 			audio->convert.len = desired->size;
   619             audio->convert.len = desired->size;
   607 			audio->convert.buf =(Uint8 *)SDL_AllocAudioMem(
   620             audio->convert.buf =
   608 			   audio->convert.len*audio->convert.len_mult);
   621                 (Uint8 *) SDL_AllocAudioMem (audio->convert.len *
   609 			if ( audio->convert.buf == NULL ) {
   622                                              audio->convert.len_mult);
   610 				SDL_CloseAudio();
   623             if (audio->convert.buf == NULL) {
   611 				SDL_OutOfMemory();
   624                 SDL_CloseAudio ();
   612 				return(-1);
   625                 SDL_OutOfMemory ();
   613 			}
   626                 return (-1);
   614 		}
   627             }
   615 	}
   628         }
   616 
   629     }
   617 #if !SDL_AUDIO_DRIVER_AHI
   630 #if !SDL_AUDIO_DRIVER_AHI
   618 	/* Start the audio thread if necessary */
   631     /* Start the audio thread if necessary */
   619 	switch (audio->opened) {
   632     switch (audio->opened) {
   620 		case  1:
   633     case 1:
   621 			/* Start the audio thread */
   634         /* Start the audio thread */
   622 #if (defined(__WIN32__) && !defined(_WIN32_WCE)) && !defined(HAVE_LIBC)
   635 #if (defined(__WIN32__) && !defined(_WIN32_WCE)) && !defined(HAVE_LIBC)
   623 #undef SDL_CreateThread
   636 #undef SDL_CreateThread
   624 			audio->thread = SDL_CreateThread(SDL_RunAudio, audio, NULL, NULL);
   637         audio->thread = SDL_CreateThread (SDL_RunAudio, audio, NULL, NULL);
   625 #else
   638 #else
   626 			audio->thread = SDL_CreateThread(SDL_RunAudio, audio);
   639         audio->thread = SDL_CreateThread (SDL_RunAudio, audio);
   627 #endif
   640 #endif
   628 			if ( audio->thread == NULL ) {
   641         if (audio->thread == NULL) {
   629 				SDL_CloseAudio();
   642             SDL_CloseAudio ();
   630 				SDL_SetError("Couldn't create audio thread");
   643             SDL_SetError ("Couldn't create audio thread");
   631 				return(-1);
   644             return (-1);
   632 			}
   645         }
   633 			break;
   646         break;
   634 
   647 
   635 		default:
   648     default:
   636 			/* The audio is now playing */
   649         /* The audio is now playing */
   637 			break;
   650         break;
   638 	}
   651     }
   639 #else
   652 #else
   640 	SDL_mutexV(audio->mixer_lock);
   653     SDL_mutexV (audio->mixer_lock);
   641 	D(bug("SDL_OpenAudio USCITA...\n"));
   654     D (bug ("SDL_OpenAudio USCITA...\n"));
   642 
   655 
   643 #endif
   656 #endif
   644 
   657 
   645 	return(0);
   658     return (0);
   646 }
   659 }
   647 
   660 
   648 SDL_audiostatus SDL_GetAudioStatus(void)
   661 SDL_audiostatus
   649 {
   662 SDL_GetAudioStatus (void)
   650 	SDL_AudioDevice *audio = current_audio;
   663 {
   651 	SDL_audiostatus status;
   664     SDL_AudioDevice *audio = current_audio;
   652 
   665     SDL_audiostatus status;
   653 	status = SDL_AUDIO_STOPPED;
   666 
   654 	if ( audio && audio->enabled ) {
   667     status = SDL_AUDIO_STOPPED;
   655 		if ( audio->paused ) {
   668     if (audio && audio->enabled) {
   656 			status = SDL_AUDIO_PAUSED;
   669         if (audio->paused) {
   657 		} else {
   670             status = SDL_AUDIO_PAUSED;
   658 			status = SDL_AUDIO_PLAYING;
   671         } else {
   659 		}
   672             status = SDL_AUDIO_PLAYING;
   660 	}
   673         }
   661 	return(status);
   674     }
   662 }
   675     return (status);
   663 
   676 }
   664 void SDL_PauseAudio (int pause_on)
   677 
   665 {
   678 void
   666 	SDL_AudioDevice *audio = current_audio;
   679 SDL_PauseAudio (int pause_on)
   667 
   680 {
   668 	if ( audio ) {
   681     SDL_AudioDevice *audio = current_audio;
   669 		audio->paused = pause_on;
   682 
   670 	}
   683     if (audio) {
   671 }
   684         audio->paused = pause_on;
   672 
   685     }
   673 void SDL_LockAudio (void)
   686 }
   674 {
   687 
   675 	SDL_AudioDevice *audio = current_audio;
   688 void
   676 
   689 SDL_LockAudio (void)
   677 	/* Obtain a lock on the mixing buffers */
   690 {
   678 	if ( audio && audio->LockAudio ) {
   691     SDL_AudioDevice *audio = current_audio;
   679 		audio->LockAudio(audio);
   692 
   680 	}
   693     /* Obtain a lock on the mixing buffers */
   681 }
   694     if (audio && audio->LockAudio) {
   682 
   695         audio->LockAudio (audio);
   683 void SDL_UnlockAudio (void)
   696     }
   684 {
   697 }
   685 	SDL_AudioDevice *audio = current_audio;
   698 
   686 
   699 void
   687 	/* Release lock on the mixing buffers */
   700 SDL_UnlockAudio (void)
   688 	if ( audio && audio->UnlockAudio ) {
   701 {
   689 		audio->UnlockAudio(audio);
   702     SDL_AudioDevice *audio = current_audio;
   690 	}
   703 
   691 }
   704     /* Release lock on the mixing buffers */
   692 
   705     if (audio && audio->UnlockAudio) {
   693 void SDL_CloseAudio (void)
   706         audio->UnlockAudio (audio);
   694 {
   707     }
   695 	SDL_QuitSubSystem(SDL_INIT_AUDIO);
   708 }
   696 }
   709 
   697 
   710 void
   698 void SDL_AudioQuit(void)
   711 SDL_CloseAudio (void)
   699 {
   712 {
   700 	SDL_AudioDevice *audio = current_audio;
   713     SDL_QuitSubSystem (SDL_INIT_AUDIO);
   701 
   714 }
   702 	if ( audio ) {
   715 
   703 		audio->enabled = 0;
   716 void
   704 		if ( audio->thread != NULL ) {
   717 SDL_AudioQuit (void)
   705 			SDL_WaitThread(audio->thread, NULL);
   718 {
   706 		}
   719     SDL_AudioDevice *audio = current_audio;
   707 		if ( audio->mixer_lock != NULL ) {
   720 
   708 			SDL_DestroyMutex(audio->mixer_lock);
   721     if (audio) {
   709 		}
   722         audio->enabled = 0;
   710 		if ( audio->fake_stream != NULL ) {
   723         if (audio->thread != NULL) {
   711 			SDL_FreeAudioMem(audio->fake_stream);
   724             SDL_WaitThread (audio->thread, NULL);
   712 		}
   725         }
   713 		if ( audio->convert.needed ) {
   726         if (audio->mixer_lock != NULL) {
   714 			SDL_FreeAudioMem(audio->convert.buf);
   727             SDL_DestroyMutex (audio->mixer_lock);
   715 
   728         }
   716 		}
   729         if (audio->fake_stream != NULL) {
       
   730             SDL_FreeAudioMem (audio->fake_stream);
       
   731         }
       
   732         if (audio->convert.needed) {
       
   733             SDL_FreeAudioMem (audio->convert.buf);
       
   734 
       
   735         }
   717 #if !SDL_AUDIO_DRIVER_AHI
   736 #if !SDL_AUDIO_DRIVER_AHI
   718 		if ( audio->opened ) {
   737         if (audio->opened) {
   719 			audio->CloseAudio(audio);
   738             audio->CloseAudio (audio);
   720 			audio->opened = 0;
   739             audio->opened = 0;
   721 		}
   740         }
   722 #endif
   741 #endif
   723 		/* Free the driver data */
   742         /* Free the driver data */
   724 		audio->free(audio);
   743         audio->free (audio);
   725 		current_audio = NULL;
   744         current_audio = NULL;
   726 	}
   745     }
   727 }
   746 }
   728 
   747 
   729 #define NUM_FORMATS	6
   748 #define NUM_FORMATS	6
   730 static int format_idx;
   749 static int format_idx;
   731 static int format_idx_sub;
   750 static int format_idx_sub;
   732 static Uint16 format_list[NUM_FORMATS][NUM_FORMATS] = {
   751 static Uint16 format_list[NUM_FORMATS][NUM_FORMATS] = {
   733  { AUDIO_U8, AUDIO_S8, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB, AUDIO_U16MSB },
   752     {AUDIO_U8, AUDIO_S8, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB,
   734  { AUDIO_S8, AUDIO_U8, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB, AUDIO_U16MSB },
   753      AUDIO_U16MSB},
   735  { AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_U8, AUDIO_S8 },
   754     {AUDIO_S8, AUDIO_U8, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB,
   736  { AUDIO_S16MSB, AUDIO_S16LSB, AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_U8, AUDIO_S8 },
   755      AUDIO_U16MSB},
   737  { AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U8, AUDIO_S8 },
   756     {AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_U8,
   738  { AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_S16MSB, AUDIO_S16LSB, AUDIO_U8, AUDIO_S8 },
   757      AUDIO_S8},
       
   758     {AUDIO_S16MSB, AUDIO_S16LSB, AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_U8,
       
   759      AUDIO_S8},
       
   760     {AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U8,
       
   761      AUDIO_S8},
       
   762     {AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_S16MSB, AUDIO_S16LSB, AUDIO_U8,
       
   763      AUDIO_S8},
   739 };
   764 };
   740 
   765 
   741 Uint16 SDL_FirstAudioFormat(Uint16 format)
   766 Uint16
   742 {
   767 SDL_FirstAudioFormat (Uint16 format)
   743 	for ( format_idx=0; format_idx < NUM_FORMATS; ++format_idx ) {
   768 {
   744 		if ( format_list[format_idx][0] == format ) {
   769     for (format_idx = 0; format_idx < NUM_FORMATS; ++format_idx) {
   745 			break;
   770         if (format_list[format_idx][0] == format) {
   746 		}
   771             break;
   747 	}
   772         }
   748 	format_idx_sub = 0;
   773     }
   749 	return(SDL_NextAudioFormat());
   774     format_idx_sub = 0;
   750 }
   775     return (SDL_NextAudioFormat ());
   751 
   776 }
   752 Uint16 SDL_NextAudioFormat(void)
   777 
   753 {
   778 Uint16
   754 	if ( (format_idx == NUM_FORMATS) || (format_idx_sub == NUM_FORMATS) ) {
   779 SDL_NextAudioFormat (void)
   755 		return(0);
   780 {
   756 	}
   781     if ((format_idx == NUM_FORMATS) || (format_idx_sub == NUM_FORMATS)) {
   757 	return(format_list[format_idx][format_idx_sub++]);
   782         return (0);
   758 }
   783     }
   759 
   784     return (format_list[format_idx][format_idx_sub++]);
   760 void SDL_CalculateAudioSpec(SDL_AudioSpec *spec)
   785 }
   761 {
   786 
   762 	switch (spec->format) {
   787 void
   763 		case AUDIO_U8:
   788 SDL_CalculateAudioSpec (SDL_AudioSpec * spec)
   764 			spec->silence = 0x80;
   789 {
   765 			break;
   790     switch (spec->format) {
   766 		default:
   791     case AUDIO_U8:
   767 			spec->silence = 0x00;
   792         spec->silence = 0x80;
   768 			break;
   793         break;
   769 	}
   794     default:
   770 	spec->size = (spec->format&0xFF)/8;
   795         spec->silence = 0x00;
   771 	spec->size *= spec->channels;
   796         break;
   772 	spec->size *= spec->samples;
   797     }
   773 }
   798     spec->size = (spec->format & 0xFF) / 8;
       
   799     spec->size *= spec->channels;
       
   800     spec->size *= spec->samples;
       
   801 }
       
   802 
       
   803 /* vi: set ts=4 sw=4 expandtab: */