comparison src/audio/disk/SDL_diskaudio.c @ 3784:37c9c4590689 SDL-ryan-multiple-audio-device

First batch of heavy lifting on supporting multiple audio devices at once. This has a long way to go yet, most of the drivers aren't updated for the new interfaces, and it's still got some obvious bugs, FIXMEs, and wistlist items. Don't use yet.
author Ryan C. Gordon <icculus@icculus.org>
date Sun, 01 Oct 2006 05:24:03 +0000
parents c121d94672cb
children 866c310e2cb5
comparison
equal deleted inserted replaced
3783:dc3870a3f30d 3784:37c9c4590689
45 #define DISKDEFAULT_OUTFILE "sdlaudio.raw" 45 #define DISKDEFAULT_OUTFILE "sdlaudio.raw"
46 #define DISKENVR_WRITEDELAY "SDL_DISKAUDIODELAY" 46 #define DISKENVR_WRITEDELAY "SDL_DISKAUDIODELAY"
47 #define DISKDEFAULT_WRITEDELAY 150 47 #define DISKDEFAULT_WRITEDELAY 150
48 48
49 /* Audio driver functions */ 49 /* Audio driver functions */
50 static int DISKAUD_OpenAudio(_THIS, SDL_AudioSpec * spec); 50 static int DISKAUD_OpenAudio(_THIS, const char *devname, int iscapture);
51 static void DISKAUD_WaitAudio(_THIS); 51 static void DISKAUD_WaitAudio(_THIS);
52 static void DISKAUD_PlayAudio(_THIS); 52 static void DISKAUD_PlayAudio(_THIS);
53 static Uint8 *DISKAUD_GetAudioBuf(_THIS); 53 static Uint8 *DISKAUD_GetAudioBuf(_THIS);
54 static void DISKAUD_CloseAudio(_THIS); 54 static void DISKAUD_CloseAudio(_THIS);
55 55
62 62
63 /* Audio driver bootstrap functions */ 63 /* Audio driver bootstrap functions */
64 static int 64 static int
65 DISKAUD_Available(void) 65 DISKAUD_Available(void)
66 { 66 {
67 /* !!! FIXME: check this at a higher level... */
68 /* only ever use this driver if explicitly requested. */
67 const char *envr = SDL_getenv("SDL_AUDIODRIVER"); 69 const char *envr = SDL_getenv("SDL_AUDIODRIVER");
68 if (envr && (SDL_strcmp(envr, DISKAUD_DRIVER_NAME) == 0)) { 70 if (envr && (SDL_strcasecmp(envr, DISKAUD_DRIVER_NAME) == 0)) {
69 return (1); 71 return (1);
70 } 72 }
71 return (0); 73 return (0);
72 } 74 }
73 75
74 static void 76 static int
75 DISKAUD_DeleteDevice(SDL_AudioDevice * device) 77 DISKAUD_Init(SDL_AudioDriverImpl *impl)
76 { 78 {
77 SDL_free(device->hidden);
78 SDL_free(device);
79 }
80
81 static SDL_AudioDevice *
82 DISKAUD_CreateDevice(int devindex)
83 {
84 SDL_AudioDevice *this;
85 const char *envr;
86
87 /* Initialize all variables that we clean on shutdown */ 79 /* Initialize all variables that we clean on shutdown */
88 this = (SDL_AudioDevice *) SDL_malloc(sizeof(SDL_AudioDevice)); 80 SDL_memset(impl, '\0', sizeof (SDL_AudioDriverImpl));
89 if (this) {
90 SDL_memset(this, 0, (sizeof *this));
91 this->hidden = (struct SDL_PrivateAudioData *)
92 SDL_malloc((sizeof *this->hidden));
93 }
94 if ((this == NULL) || (this->hidden == NULL)) {
95 SDL_OutOfMemory();
96 if (this) {
97 SDL_free(this);
98 }
99 return (0);
100 }
101 SDL_memset(this->hidden, 0, (sizeof *this->hidden));
102
103 envr = SDL_getenv(DISKENVR_WRITEDELAY);
104 this->hidden->write_delay =
105 (envr) ? SDL_atoi(envr) : DISKDEFAULT_WRITEDELAY;
106 81
107 /* Set the function pointers */ 82 /* Set the function pointers */
108 this->OpenAudio = DISKAUD_OpenAudio; 83 impl->OpenAudio = DISKAUD_OpenAudio;
109 this->WaitAudio = DISKAUD_WaitAudio; 84 impl->WaitAudio = DISKAUD_WaitAudio;
110 this->PlayAudio = DISKAUD_PlayAudio; 85 impl->PlayAudio = DISKAUD_PlayAudio;
111 this->GetAudioBuf = DISKAUD_GetAudioBuf; 86 impl->GetAudioBuf = DISKAUD_GetAudioBuf;
112 this->CloseAudio = DISKAUD_CloseAudio; 87 impl->CloseAudio = DISKAUD_CloseAudio;
113 88
114 this->free = DISKAUD_DeleteDevice; 89 return 1;
115
116 return this;
117 } 90 }
118 91
119 AudioBootStrap DISKAUD_bootstrap = { 92 AudioBootStrap DISKAUD_bootstrap = {
120 DISKAUD_DRIVER_NAME, "direct-to-disk audio", 93 DISKAUD_DRIVER_NAME, "direct-to-disk audio",
121 DISKAUD_Available, DISKAUD_CreateDevice 94 DISKAUD_Available, DISKAUD_Init
122 }; 95 };
123 96
124 /* This function waits until it is possible to write a full sound buffer */ 97 /* This function waits until it is possible to write a full sound buffer */
125 static void 98 static void
126 DISKAUD_WaitAudio(_THIS) 99 DISKAUD_WaitAudio(_THIS)
161 } 134 }
162 if (this->hidden->output != NULL) { 135 if (this->hidden->output != NULL) {
163 SDL_RWclose(this->hidden->output); 136 SDL_RWclose(this->hidden->output);
164 this->hidden->output = NULL; 137 this->hidden->output = NULL;
165 } 138 }
139 SDL_free(this->hidden);
140 this->hidden = NULL;
166 } 141 }
167 142
168 static int 143 static int
169 DISKAUD_OpenAudio(_THIS, SDL_AudioSpec * spec) 144 DISKAUD_OpenAudio(_THIS, const char *devname, int iscapture)
170 { 145 {
146 const char *envr = SDL_getenv(DISKENVR_WRITEDELAY);
171 const char *fname = DISKAUD_GetOutputFilename(); 147 const char *fname = DISKAUD_GetOutputFilename();
148
149 /* !!! FIXME: use device name for non-default filename? */
150 if (devname != NULL) {
151 SDL_SetError("Disk audio device name must be NULL");
152 return 0;
153 }
154
155 this->hidden = (struct SDL_PrivateAudioData *)
156 SDL_malloc(sizeof (*this->hidden));
157 if (this->hidden == NULL) {
158 SDL_OutOfMemory();
159 return 0;
160 }
161 SDL_memset(this->hidden, 0, sizeof (*this->hidden));
172 162
173 /* Open the audio device */ 163 /* Open the audio device */
174 this->hidden->output = SDL_RWFromFile(fname, "wb"); 164 this->hidden->output = SDL_RWFromFile(fname, "wb");
175 if (this->hidden->output == NULL) { 165 if (this->hidden->output == NULL) {
176 return (-1); 166 DISKAUD_CloseAudio(this);
167 return 0;
177 } 168 }
169
170 /* Allocate mixing buffer */
171 this->hidden->mixbuf = (Uint8 *) SDL_AllocAudioMem(this->hidden->mixlen);
172 if (this->hidden->mixbuf == NULL) {
173 DISKAUD_CloseAudio(this);
174 return 0;
175 }
176 SDL_memset(this->hidden->mixbuf, this->spec.silence, this->spec.size);
177
178 this->hidden->mixlen = this->spec.size;
179 this->hidden->write_delay =
180 (envr) ? SDL_atoi(envr) : DISKDEFAULT_WRITEDELAY;
181
178 #if HAVE_STDIO_H 182 #if HAVE_STDIO_H
179 fprintf(stderr, "WARNING: You are using the SDL disk writer" 183 fprintf(stderr,
180 " audio driver!\n Writing to file [%s].\n", fname); 184 "WARNING: You are using the SDL disk writer audio driver!\n"
185 " Writing to file [%s].\n", fname);
181 #endif 186 #endif
182 187
183 /* Allocate mixing buffer */
184 this->hidden->mixlen = spec->size;
185 this->hidden->mixbuf = (Uint8 *) SDL_AllocAudioMem(this->hidden->mixlen);
186 if (this->hidden->mixbuf == NULL) {
187 return (-1);
188 }
189 SDL_memset(this->hidden->mixbuf, spec->silence, spec->size);
190
191 /* We're ready to rock and roll. :-) */ 188 /* We're ready to rock and roll. :-) */
192 return (0); 189 return 1;
193 } 190 }
194 191
195 /* vi: set ts=4 sw=4 expandtab: */ 192 /* vi: set ts=4 sw=4 expandtab: */