test/loopwave.c
author Ryan C. Gordon <icculus@icculus.org>
Wed, 28 Sep 2005 11:36:20 +0000
changeset 1151 be9c9c8f6d53
parent 0 74212992fb08
child 1463 0394f8ebc42d
permissions -rw-r--r--
Removed atexit() from most of the test programs; atexit(SDL_Quit) isn't safe
if SDL is built with a non-cdecl calling convention, and it's just generally
bad practice anyhow.

Now programs explicitly call SDL_Quit() where appropriate, wrap SDL_Quit() in
a cdecl function where it can't be avoided, and rely on the parachute where
a crash might have hit the atexit() before (these ARE test programs, after
all!).
     1 
     2 /* Program to load a wave file and loop playing it using SDL sound */
     3 
     4 /* loopwaves.c is much more robust in handling WAVE files -- 
     5 	This is only for simple WAVEs
     6 */
     7 
     8 #include <stdio.h>
     9 #include <stdlib.h>
    10 #include <signal.h>
    11 
    12 #include "SDL.h"
    13 #include "SDL_audio.h"
    14 
    15 struct {
    16 	SDL_AudioSpec spec;
    17 	Uint8   *sound;			/* Pointer to wave data */
    18 	Uint32   soundlen;		/* Length of wave data */
    19 	int      soundpos;		/* Current play position */
    20 } wave;
    21 
    22 
    23 /* Call this instead of exit(), so we can clean up SDL: atexit() is evil. */
    24 static void quit(int rc)
    25 {
    26 	SDL_Quit();
    27 	exit(rc);
    28 }
    29 
    30 
    31 void fillerup(void *unused, Uint8 *stream, int len)
    32 {
    33 	Uint8 *waveptr;
    34 	int    waveleft;
    35 
    36 	/* Set up the pointers */
    37 	waveptr = wave.sound + wave.soundpos;
    38 	waveleft = wave.soundlen - wave.soundpos;
    39 
    40 	/* Go! */
    41 	while ( waveleft <= len ) {
    42 		SDL_MixAudio(stream, waveptr, waveleft, SDL_MIX_MAXVOLUME);
    43 		stream += waveleft;
    44 		len -= waveleft;
    45 		waveptr = wave.sound;
    46 		waveleft = wave.soundlen;
    47 		wave.soundpos = 0;
    48 	}
    49 	SDL_MixAudio(stream, waveptr, len, SDL_MIX_MAXVOLUME);
    50 	wave.soundpos += len;
    51 }
    52 
    53 static int done = 0;
    54 void poked(int sig)
    55 {
    56 	done = 1;
    57 }
    58 
    59 int main(int argc, char *argv[])
    60 {
    61 	char name[32];
    62 
    63 	/* Load the SDL library */
    64 	if ( SDL_Init(SDL_INIT_AUDIO) < 0 ) {
    65 		fprintf(stderr, "Couldn't initialize SDL: %s\n",SDL_GetError());
    66 		return(1);
    67 	}
    68 
    69 	if ( argv[1] == NULL ) {
    70 		fprintf(stderr, "Usage: %s <wavefile>\n", argv[0]);
    71 		quit(1);
    72 	}
    73 
    74 	/* Load the wave file into memory */
    75 	if ( SDL_LoadWAV(argv[1],
    76 			&wave.spec, &wave.sound, &wave.soundlen) == NULL ) {
    77 		fprintf(stderr, "Couldn't load %s: %s\n",
    78 						argv[1], SDL_GetError());
    79 		quit(1);
    80 	}
    81 	wave.spec.callback = fillerup;
    82 
    83 	/* Set the signals */
    84 #ifdef SIGHUP
    85 	signal(SIGHUP, poked);
    86 #endif
    87 	signal(SIGINT, poked);
    88 #ifdef SIGQUIT
    89 	signal(SIGQUIT, poked);
    90 #endif
    91 	signal(SIGTERM, poked);
    92 
    93 	/* Initialize fillerup() variables */
    94 	if ( SDL_OpenAudio(&wave.spec, NULL) < 0 ) {
    95 		fprintf(stderr, "Couldn't open audio: %s\n", SDL_GetError());
    96 		SDL_FreeWAV(wave.sound);
    97 		quit(2);
    98 	}
    99 	SDL_PauseAudio(0);
   100 
   101 	/* Let the audio run */
   102 	printf("Using audio driver: %s\n", SDL_AudioDriverName(name, 32));
   103 	while ( ! done && (SDL_GetAudioStatus() == SDL_AUDIO_PLAYING) )
   104 		SDL_Delay(1000);
   105 
   106 	/* Clean up on signal */
   107 	SDL_CloseAudio();
   108 	SDL_FreeWAV(wave.sound);
   109 	SDL_Quit();
   110 	return(0);
   111 }