Subversion Repositories Kolibri OS

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
5131 clevermous 1
/*
2
Copyright (C) 1996-1997 Id Software, Inc.
3
 
4
This program is free software; you can redistribute it and/or
5
modify it under the terms of the GNU General Public License
6
as published by the Free Software Foundation; either version 2
7
of the License, or (at your option) any later version.
8
 
9
This program is distributed in the hope that it will be useful,
10
but WITHOUT ANY WARRANTY; without even the implied warranty of
11
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12
 
13
See the GNU General Public License for more details.
14
 
15
You should have received a copy of the GNU General Public License
16
along with this program; if not, write to the Free Software
17
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
18
 
19
*/
20
#include 
21
#include 
22
#include 
23
#include 
24
#include 
25
#include 
26
#include 
27
#include 
28
#include 
29
#include 
30
#include "quakedef.h"
31
 
32
int audio_fd;
33
int snd_inited;
34
 
35
static int tryrates[] = { 11025, 22051, 44100, 8000 };
36
 
37
qboolean SNDDMA_Init(void)
38
{
39
 
40
	int rc;
41
    int fmt;
42
	int tmp;
43
    int i;
44
    char *s;
45
	struct audio_buf_info info;
46
	int caps;
47
 
48
	snd_inited = 0;
49
 
50
// open /dev/dsp, confirm capability to mmap, and get size of dma buffer
51
 
52
    audio_fd = open("/dev/dsp", O_RDWR);
53
    if (audio_fd < 0)
54
	{
55
		perror("/dev/dsp");
56
        Con_Printf("Could not open /dev/dsp\n");
57
		return 0;
58
	}
59
 
60
    rc = ioctl(audio_fd, SNDCTL_DSP_RESET, 0);
61
    if (rc < 0)
62
	{
63
		perror("/dev/dsp");
64
		Con_Printf("Could not reset /dev/dsp\n");
65
		close(audio_fd);
66
		return 0;
67
	}
68
 
69
	if (ioctl(audio_fd, SNDCTL_DSP_GETCAPS, &caps)==-1)
70
	{
71
		perror("/dev/dsp");
72
        Con_Printf("Sound driver too old\n");
73
		close(audio_fd);
74
		return 0;
75
	}
76
 
77
	if (!(caps & DSP_CAP_TRIGGER) || !(caps & DSP_CAP_MMAP))
78
	{
79
		Con_Printf("Sorry but your soundcard can't do this\n");
80
		close(audio_fd);
81
		return 0;
82
	}
83
 
84
    if (ioctl(audio_fd, SNDCTL_DSP_GETOSPACE, &info)==-1)
85
    {
86
        perror("GETOSPACE");
87
		Con_Printf("Um, can't do GETOSPACE?\n");
88
		close(audio_fd);
89
		return 0;
90
    }
91
 
92
	shm = &sn;
93
    shm->splitbuffer = 0;
94
 
95
// set sample bits & speed
96
 
97
    s = getenv("QUAKE_SOUND_SAMPLEBITS");
98
    if (s) shm->samplebits = atoi(s);
99
	else if ((i = COM_CheckParm("-sndbits")) != 0)
100
		shm->samplebits = atoi(com_argv[i+1]);
101
	if (shm->samplebits != 16 && shm->samplebits != 8)
102
    {
103
        ioctl(audio_fd, SNDCTL_DSP_GETFMTS, &fmt);
104
        if (fmt & AFMT_S16_LE) shm->samplebits = 16;
105
        else if (fmt & AFMT_U8) shm->samplebits = 8;
106
    }
107
 
108
    s = getenv("QUAKE_SOUND_SPEED");
109
    if (s) shm->speed = atoi(s);
110
	else if ((i = COM_CheckParm("-sndspeed")) != 0)
111
		shm->speed = atoi(com_argv[i+1]);
112
    else
113
    {
114
        for (i=0 ; i
115
            if (!ioctl(audio_fd, SNDCTL_DSP_SPEED, &tryrates[i])) break;
116
        shm->speed = tryrates[i];
117
    }
118
 
119
    s = getenv("QUAKE_SOUND_CHANNELS");
120
    if (s) shm->channels = atoi(s);
121
	else if ((i = COM_CheckParm("-sndmono")) != 0)
122
		shm->channels = 1;
123
	else if ((i = COM_CheckParm("-sndstereo")) != 0)
124
		shm->channels = 2;
125
    else shm->channels = 2;
126
 
127
	shm->samples = info.fragstotal * info.fragsize / (shm->samplebits/8);
128
	shm->submission_chunk = 1;
129
 
130
// memory map the dma buffer
131
 
132
	shm->buffer = (unsigned char *) mmap(NULL, info.fragstotal
133
		* info.fragsize, PROT_WRITE, MAP_FILE|MAP_SHARED, audio_fd, 0);
134
	if (!shm->buffer || shm->buffer == (unsigned char *)-1)
135
	{
136
		perror("/dev/dsp");
137
		Con_Printf("Could not mmap /dev/dsp\n");
138
		close(audio_fd);
139
		return 0;
140
	}
141
 
142
	tmp = 0;
143
	if (shm->channels == 2)
144
		tmp = 1;
145
    rc = ioctl(audio_fd, SNDCTL_DSP_STEREO, &tmp);
146
    if (rc < 0)
147
    {
148
		perror("/dev/dsp");
149
        Con_Printf("Could not set /dev/dsp to stereo=%d", shm->channels);
150
		close(audio_fd);
151
        return 0;
152
    }
153
	if (tmp)
154
		shm->channels = 2;
155
	else
156
		shm->channels = 1;
157
 
158
    rc = ioctl(audio_fd, SNDCTL_DSP_SPEED, &shm->speed);
159
    if (rc < 0)
160
    {
161
		perror("/dev/dsp");
162
        Con_Printf("Could not set /dev/dsp speed to %d", shm->speed);
163
		close(audio_fd);
164
        return 0;
165
    }
166
 
167
    if (shm->samplebits == 16)
168
    {
169
        rc = AFMT_S16_LE;
170
        rc = ioctl(audio_fd, SNDCTL_DSP_SETFMT, &rc);
171
        if (rc < 0)
172
		{
173
			perror("/dev/dsp");
174
			Con_Printf("Could not support 16-bit data.  Try 8-bit.\n");
175
			close(audio_fd);
176
			return 0;
177
		}
178
    }
179
    else if (shm->samplebits == 8)
180
    {
181
        rc = AFMT_U8;
182
        rc = ioctl(audio_fd, SNDCTL_DSP_SETFMT, &rc);
183
        if (rc < 0)
184
		{
185
			perror("/dev/dsp");
186
			Con_Printf("Could not support 8-bit data.\n");
187
			close(audio_fd);
188
			return 0;
189
		}
190
    }
191
	else
192
	{
193
		perror("/dev/dsp");
194
		Con_Printf("%d-bit sound not supported.", shm->samplebits);
195
		close(audio_fd);
196
		return 0;
197
	}
198
 
199
// toggle the trigger & start her up
200
 
201
    tmp = 0;
202
    rc  = ioctl(audio_fd, SNDCTL_DSP_SETTRIGGER, &tmp);
203
	if (rc < 0)
204
	{
205
		perror("/dev/dsp");
206
		Con_Printf("Could not toggle.\n");
207
		close(audio_fd);
208
		return 0;
209
	}
210
    tmp = PCM_ENABLE_OUTPUT;
211
    rc = ioctl(audio_fd, SNDCTL_DSP_SETTRIGGER, &tmp);
212
	if (rc < 0)
213
	{
214
		perror("/dev/dsp");
215
		Con_Printf("Could not toggle.\n");
216
		close(audio_fd);
217
		return 0;
218
	}
219
 
220
	shm->samplepos = 0;
221
 
222
	snd_inited = 1;
223
	return 1;
224
 
225
}
226
 
227
int SNDDMA_GetDMAPos(void)
228
{
229
 
230
	struct count_info count;
231
 
232
	if (!snd_inited) return 0;
233
 
234
	if (ioctl(audio_fd, SNDCTL_DSP_GETOPTR, &count)==-1)
235
	{
236
		perror("/dev/dsp");
237
		Con_Printf("Uh, sound dead.\n");
238
		close(audio_fd);
239
		snd_inited = 0;
240
		return 0;
241
	}
242
//	shm->samplepos = (count.bytes / (shm->samplebits / 8)) & (shm->samples-1);
243
//	fprintf(stderr, "%d    \r", count.ptr);
244
	shm->samplepos = count.ptr / (shm->samplebits / 8);
245
 
246
	return shm->samplepos;
247
 
248
}
249
 
250
void SNDDMA_Shutdown(void)
251
{
252
	if (snd_inited)
253
	{
254
		close(audio_fd);
255
		snd_inited = 0;
256
	}
257
}
258
 
259
/*
260
==============
261
SNDDMA_Submit
262
 
263
Send sound to device if buffer isn't really the dma buffer
264
===============
265
*/
266
void SNDDMA_Submit(void)
267
{
268
}
269