This repository has been archived by the owner on Feb 11, 2021. It is now read-only.
/
SDL_irixaudio.c
229 lines (194 loc) · 5.82 KB
1
2
/*
SDL - Simple DirectMedia Layer
3
Copyright (C) 1997-2006 Sam Lantinga
4
5
This library is free software; you can redistribute it and/or
6
modify it under the terms of the GNU Lesser General Public
7
License as published by the Free Software Foundation; either
8
version 2.1 of the License, or (at your option) any later version.
9
10
11
12
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13
Lesser General Public License for more details.
14
15
16
17
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
18
19
Sam Lantinga
20
slouken@libsdl.org
21
*/
22
#include "SDL_config.h"
23
24
/* Allow access to a raw mixing buffer (For IRIX 6.5 and higher) */
25
/* patch for IRIX 5 by Georg Schwarz 18/07/2004 */
26
27
28
#include "SDL_timer.h"
#include "SDL_audio.h"
29
30
#include "../SDL_audiomem.h"
#include "../SDL_audio_c.h"
31
32
33
#include "SDL_irixaudio.h"
34
#ifndef AL_RESOURCE /* as a test whether we use the old IRIX audio libraries */
35
36
37
38
39
40
41
42
43
44
45
46
#define OLD_IRIX_AUDIO
#define alClosePort(x) ALcloseport(x)
#define alFreeConfig(x) ALfreeconfig(x)
#define alGetFillable(x) ALgetfillable(x)
#define alNewConfig() ALnewconfig()
#define alOpenPort(x,y,z) ALopenport(x,y,z)
#define alSetChannels(x,y) ALsetchannels(x,y)
#define alSetQueueSize(x,y) ALsetqueuesize(x,y)
#define alSetSampFmt(x,y) ALsetsampfmt(x,y)
#define alSetWidth(x,y) ALsetwidth(x,y)
#endif
47
/* Audio driver functions */
48
49
50
51
52
static int AL_OpenAudio(_THIS, SDL_AudioSpec * spec);
static void AL_WaitAudio(_THIS);
static void AL_PlayAudio(_THIS);
static Uint8 *AL_GetAudioBuf(_THIS);
static void AL_CloseAudio(_THIS);
53
54
55
/* Audio driver bootstrap functions */
56
static int
57
Audio_Available(void)
58
{
59
return 1;
60
61
}
62
static void
63
Audio_DeleteDevice(SDL_AudioDevice * device)
64
{
65
66
SDL_free(device->hidden);
SDL_free(device);
67
68
}
69
static SDL_AudioDevice *
70
Audio_CreateDevice(int devindex)
71
{
72
73
74
SDL_AudioDevice *this;
/* Initialize all variables that we clean on shutdown */
75
this = (SDL_AudioDevice *) SDL_malloc(sizeof(SDL_AudioDevice));
76
if (this) {
77
SDL_memset(this, 0, (sizeof *this));
78
this->hidden = (struct SDL_PrivateAudioData *)
79
SDL_malloc((sizeof *this->hidden));
80
81
}
if ((this == NULL) || (this->hidden == NULL)) {
82
SDL_OutOfMemory();
83
if (this) {
84
SDL_free(this);
85
86
87
}
return (0);
}
88
SDL_memset(this->hidden, 0, (sizeof *this->hidden));
89
90
91
92
93
94
95
96
97
98
99
/* Set the function pointers */
this->OpenAudio = AL_OpenAudio;
this->WaitAudio = AL_WaitAudio;
this->PlayAudio = AL_PlayAudio;
this->GetAudioBuf = AL_GetAudioBuf;
this->CloseAudio = AL_CloseAudio;
this->free = Audio_DeleteDevice;
return this;
100
101
}
102
AudioBootStrap DMEDIA_bootstrap = {
103
104
"AL", "IRIX DMedia audio",
Audio_Available, Audio_CreateDevice
105
106
107
};
108
void static
109
AL_WaitAudio(_THIS)
110
{
111
Sint32 timeleft;
112
113
timeleft = this->spec.samples - alGetFillable(audio_port);
114
115
if (timeleft > 0) {
timeleft /= (this->spec.freq / 1000);
116
SDL_Delay((Uint32) timeleft);
117
}
118
119
}
120
static void
121
AL_PlayAudio(_THIS)
122
{
123
/* Write the audio data out */
124
if (alWriteFrames(audio_port, mixbuf, this->spec.samples) < 0) {
125
126
127
/* Assume fatal error, for now */
this->enabled = 0;
}
128
129
}
130
static Uint8 *
131
AL_GetAudioBuf(_THIS)
132
{
133
return (mixbuf);
134
135
}
136
static void
137
AL_CloseAudio(_THIS)
138
{
139
if (mixbuf != NULL) {
140
SDL_FreeAudioMem(mixbuf);
141
142
143
mixbuf = NULL;
}
if (audio_port != NULL) {
144
alClosePort(audio_port);
145
146
audio_port = NULL;
}
147
148
}
149
static int
150
AL_OpenAudio(_THIS, SDL_AudioSpec * spec)
151
{
152
ALconfig audio_config;
153
#ifdef OLD_IRIX_AUDIO
154
long audio_param[2];
155
#else
156
ALpv audio_param;
157
#endif
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
int width;
/* Determine the audio parameters from the AudioSpec */
switch (spec->format & 0xFF) {
case 8:
{ /* Signed 8 bit audio data */
spec->format = AUDIO_S8;
width = AL_SAMPLE_8;
}
break;
case 16:
{ /* Signed 16 bit audio data */
spec->format = AUDIO_S16MSB;
width = AL_SAMPLE_16;
}
break;
default:
{
179
SDL_SetError("Unsupported audio format");
180
181
182
183
184
return (-1);
}
}
/* Update the fragment size as size in bytes */
185
SDL_CalculateAudioSpec(spec);
186
187
/* Set output frequency */
188
#ifdef OLD_IRIX_AUDIO
189
190
audio_param[0] = AL_OUTPUT_RATE;
audio_param[1] = spec->freq;
191
if (ALsetparams(AL_DEFAULT_DEVICE, audio_param, 2) < 0) {
192
#else
193
194
audio_param.param = AL_RATE;
audio_param.value.i = spec->freq;
195
if (alSetParams(AL_DEFAULT_OUTPUT, &audio_param, 1) < 0) {
196
#endif
197
SDL_SetError("alSetParams failed");
198
199
200
201
202
return (-1);
}
/* Open the audio port with the requested frequency */
audio_port = NULL;
203
audio_config = alNewConfig();
204
if (audio_config &&
205
206
207
208
209
(alSetSampFmt(audio_config, AL_SAMPFMT_TWOSCOMP) >= 0) &&
(alSetWidth(audio_config, width) >= 0) &&
(alSetQueueSize(audio_config, spec->samples * 2) >= 0) &&
(alSetChannels(audio_config, spec->channels) >= 0)) {
audio_port = alOpenPort("SDL audio", "w", audio_config);
210
}
211
alFreeConfig(audio_config);
212
if (audio_port == NULL) {
213
SDL_SetError("Unable to open audio port");
214
215
216
217
return (-1);
}
/* Allocate mixing buffer */
218
mixbuf = (Uint8 *) SDL_AllocAudioMem(spec->size);
219
if (mixbuf == NULL) {
220
SDL_OutOfMemory();
221
222
return (-1);
}
223
SDL_memset(mixbuf, spec->silence, spec->size);
224
225
226
/* We're ready to rock and roll. :-) */
return (0);
227
}
228
229
/* vi: set ts=4 sw=4 expandtab: */