Mercurial > mplayer.hg
annotate libao2/ao_oss.c @ 29697:1cd8a8e2c144
Simplify aac_get_sample_rate_index
author | reimar |
---|---|
date | Wed, 30 Sep 2009 07:52:37 +0000 |
parents | f01023c524c3 |
children | 38a054e832c7 |
rev | line source |
---|---|
28343 | 1 /* |
2 * OSS audio output driver | |
3 * | |
4 * This file is part of MPlayer. | |
5 * | |
6 * MPlayer is free software; you can redistribute it and/or modify | |
7 * it under the terms of the GNU General Public License as published by | |
8 * the Free Software Foundation; either version 2 of the License, or | |
9 * (at your option) any later version. | |
10 * | |
11 * MPlayer is distributed in the hope that it will be useful, | |
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
14 * GNU General Public License for more details. | |
15 * | |
16 * You should have received a copy of the GNU General Public License along | |
17 * with MPlayer; if not, write to the Free Software Foundation, Inc., | |
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. | |
19 */ | |
20 | |
954 | 21 #include <stdio.h> |
22 #include <stdlib.h> | |
23 | |
24 #include <sys/ioctl.h> | |
25 #include <unistd.h> | |
26 #include <sys/time.h> | |
27 #include <sys/types.h> | |
28 #include <sys/stat.h> | |
29 #include <fcntl.h> | |
5204
6bbf3271a694
non-blocking open - patch by Fredrik Kuivinen <freku045@student.liu.se>
arpi
parents:
4803
diff
changeset
|
30 #include <errno.h> |
6bbf3271a694
non-blocking open - patch by Fredrik Kuivinen <freku045@student.liu.se>
arpi
parents:
4803
diff
changeset
|
31 #include <string.h> |
954 | 32 |
14123 | 33 #include "config.h" |
34 #include "mp_msg.h" | |
35 #include "mixer.h" | |
36 #include "help_mp.h" | |
954 | 37 |
14245 | 38 #ifdef HAVE_SYS_SOUNDCARD_H |
39 #include <sys/soundcard.h> | |
40 #else | |
41 #ifdef HAVE_SOUNDCARD_H | |
42 #include <soundcard.h> | |
43 #endif | |
44 #endif | |
45 | |
17020 | 46 #include "libaf/af_format.h" |
1532 | 47 |
954 | 48 #include "audio_out.h" |
49 #include "audio_out_internal.h" | |
50 | |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
51 static const ao_info_t info = |
954 | 52 { |
53 "OSS/ioctl audio output", | |
956
a6cecd9a1bad
'-ao' switch (including '-ao help'), fixing Arpi's bug (short name 'null' for both of oss and null driver ;)
lgb
parents:
954
diff
changeset
|
54 "oss", |
954 | 55 "A'rpi", |
56 "" | |
57 }; | |
58 | |
3181
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
59 /* Support for >2 output channels added 2001-11-25 - Steve Davies <steve@daviesfam.org> */ |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
60 |
954 | 61 LIBAO_EXTERN(oss) |
62 | |
14245 | 63 static int format2oss(int format) |
64 { | |
65 switch(format) | |
66 { | |
67 case AF_FORMAT_U8: return AFMT_U8; | |
68 case AF_FORMAT_S8: return AFMT_S8; | |
69 case AF_FORMAT_U16_LE: return AFMT_U16_LE; | |
70 case AF_FORMAT_U16_BE: return AFMT_U16_BE; | |
71 case AF_FORMAT_S16_LE: return AFMT_S16_LE; | |
72 case AF_FORMAT_S16_BE: return AFMT_S16_BE; | |
29396
2de35e358503
Use the correct OSS format, where possible, for mplayer's packed 24-bit
cladisch
parents:
29263
diff
changeset
|
73 #ifdef AFMT_S24_PACKED |
2de35e358503
Use the correct OSS format, where possible, for mplayer's packed 24-bit
cladisch
parents:
29263
diff
changeset
|
74 case AF_FORMAT_S24_LE: return AFMT_S24_PACKED; |
14245 | 75 #endif |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
76 #ifdef AFMT_U32_LE |
14245 | 77 case AF_FORMAT_U32_LE: return AFMT_U32_LE; |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
78 #endif |
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
79 #ifdef AFMT_U32_BE |
14245 | 80 case AF_FORMAT_U32_BE: return AFMT_U32_BE; |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
81 #endif |
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
82 #ifdef AFMT_S32_LE |
14245 | 83 case AF_FORMAT_S32_LE: return AFMT_S32_LE; |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
84 #endif |
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
85 #ifdef AFMT_S32_BE |
14245 | 86 case AF_FORMAT_S32_BE: return AFMT_S32_BE; |
87 #endif | |
88 #ifdef AFMT_FLOAT | |
89 case AF_FORMAT_FLOAT_NE: return AFMT_FLOAT; | |
90 #endif | |
91 // SPECIALS | |
92 case AF_FORMAT_MU_LAW: return AFMT_MU_LAW; | |
93 case AF_FORMAT_A_LAW: return AFMT_A_LAW; | |
94 case AF_FORMAT_IMA_ADPCM: return AFMT_IMA_ADPCM; | |
95 #ifdef AFMT_MPEG | |
96 case AF_FORMAT_MPEG2: return AFMT_MPEG; | |
97 #endif | |
98 #ifdef AFMT_AC3 | |
99 case AF_FORMAT_AC3: return AFMT_AC3; | |
100 #endif | |
101 } | |
14609
082177fb93b1
print "Unknown/not supported internal format" message only with -v as it
reimar
parents:
14404
diff
changeset
|
102 mp_msg(MSGT_AO, MSGL_V, "OSS: Unknown/not supported internal format: %s\n", af_fmt2str_short(format)); |
14245 | 103 return -1; |
104 } | |
105 | |
106 static int oss2format(int format) | |
107 { | |
108 switch(format) | |
109 { | |
110 case AFMT_U8: return AF_FORMAT_U8; | |
111 case AFMT_S8: return AF_FORMAT_S8; | |
112 case AFMT_U16_LE: return AF_FORMAT_U16_LE; | |
113 case AFMT_U16_BE: return AF_FORMAT_U16_BE; | |
114 case AFMT_S16_LE: return AF_FORMAT_S16_LE; | |
115 case AFMT_S16_BE: return AF_FORMAT_S16_BE; | |
29396
2de35e358503
Use the correct OSS format, where possible, for mplayer's packed 24-bit
cladisch
parents:
29263
diff
changeset
|
116 #ifdef AFMT_S24_PACKED |
2de35e358503
Use the correct OSS format, where possible, for mplayer's packed 24-bit
cladisch
parents:
29263
diff
changeset
|
117 case AFMT_S24_PACKED: return AF_FORMAT_S24_LE; |
14245 | 118 #endif |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
119 #ifdef AFMT_U32_LE |
14245 | 120 case AFMT_U32_LE: return AF_FORMAT_U32_LE; |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
121 #endif |
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
122 #ifdef AFMT_U32_BE |
14245 | 123 case AFMT_U32_BE: return AF_FORMAT_U32_BE; |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
124 #endif |
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
125 #ifdef AFMT_S32_LE |
14245 | 126 case AFMT_S32_LE: return AF_FORMAT_S32_LE; |
14397
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
127 #endif |
d862ff282815
Check for every 24 and 32 bit AFMT_ separately if it is defined.
reimar
parents:
14273
diff
changeset
|
128 #ifdef AFMT_S32_BE |
14245 | 129 case AFMT_S32_BE: return AF_FORMAT_S32_BE; |
130 #endif | |
131 #ifdef AFMT_FLOAT | |
132 case AFMT_FLOAT: return AF_FORMAT_FLOAT_NE; | |
133 #endif | |
134 // SPECIALS | |
135 case AFMT_MU_LAW: return AF_FORMAT_MU_LAW; | |
136 case AFMT_A_LAW: return AF_FORMAT_A_LAW; | |
137 case AFMT_IMA_ADPCM: return AF_FORMAT_IMA_ADPCM; | |
138 #ifdef AFMT_MPEG | |
139 case AFMT_MPEG: return AF_FORMAT_MPEG2; | |
140 #endif | |
141 #ifdef AFMT_AC3 | |
142 case AFMT_AC3: return AF_FORMAT_AC3; | |
143 #endif | |
144 } | |
17994
6927fabaef92
Part1 of several printf2mp_msg changes in patch from Otvos Attila oattila AT chello DOT hu
reynaldo
parents:
17566
diff
changeset
|
145 mp_msg(MSGT_GLOBAL,MSGL_ERR,MSGTR_AO_OSS_UnknownUnsupportedFormat, format); |
14245 | 146 return -1; |
147 } | |
148 | |
4803 | 149 static char *dsp=PATH_DEV_DSP; |
1020
72cacd3b8f30
Solaris 8 support - patch by Marcus Comstedt <marcus@idonex.se>
arpi_esp
parents:
956
diff
changeset
|
150 static audio_buf_info zz; |
954 | 151 static int audio_fd=-1; |
23809
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
152 static int prepause_space; |
954 | 153 |
18966
0662e5119de2
two variables are made static, one of them additionaly modified to const char*. Patch by Stefan Huehner, stefan AT huehner-org
reynaldo
parents:
18842
diff
changeset
|
154 static const char *oss_mixer_device = PATH_DEV_MIXER; |
0662e5119de2
two variables are made static, one of them additionaly modified to const char*. Patch by Stefan Huehner, stefan AT huehner-org
reynaldo
parents:
18842
diff
changeset
|
155 static int oss_mixer_channel = SOUND_MIXER_PCM; |
1191 | 156 |
954 | 157 // to set/get/query special features/parameters |
9633
12b1790038b0
64bit libao2 fix by Jens Axboe <mplayer-dev@kernel.dk>
alex
parents:
9141
diff
changeset
|
158 static int control(int cmd,void *arg){ |
954 | 159 switch(cmd){ |
160 case AOCONTROL_SET_DEVICE: | |
161 dsp=(char*)arg; | |
162 return CONTROL_OK; | |
6795 | 163 case AOCONTROL_GET_DEVICE: |
12383
94ba609e53f7
ok this one is beyond stupid. the code didn't even do what was intended
rfelker
parents:
12145
diff
changeset
|
164 *(char**)arg=dsp; |
6795 | 165 return CONTROL_OK; |
15898 | 166 #ifdef SNDCTL_DSP_GETFMTS |
954 | 167 case AOCONTROL_QUERY_FORMAT: |
15898 | 168 { |
169 int format; | |
170 if (!ioctl(audio_fd, SNDCTL_DSP_GETFMTS, &format)) | |
27450
4da9ce4d8327
Fix 'cast from pointer to integer of different size' on 64bit architectures. Casting to long should work for 32bit and 64bit and not make a difference to the boolean operation (since 'format' is always 32bit (int) the upper 32bit of 'arg' won't matter, but the compiler should be happy now. Casting both to unsigned makes sure the compiler isn't messing things up by sign-extending 'format' to 64bit before masking)
ranma
parents:
23809
diff
changeset
|
171 if ((unsigned int)format & (unsigned long)arg) |
15898 | 172 return CONTROL_TRUE; |
173 return CONTROL_FALSE; | |
174 } | |
175 #endif | |
1191 | 176 case AOCONTROL_GET_VOLUME: |
177 case AOCONTROL_SET_VOLUME: | |
178 { | |
179 ao_control_vol_t *vol = (ao_control_vol_t *)arg; | |
7472
c4434bdf6e51
tons of warning fixes, also some 10l bugfixes, including Dominik's PVA bug
arpi
parents:
7118
diff
changeset
|
180 int fd, v, devs; |
1528
a444bd456fcc
ac3/spdif patch by German Gomez Garcia <german@piraos.com>
arpi
parents:
1456
diff
changeset
|
181 |
14245 | 182 if(ao_data.format == AF_FORMAT_AC3) |
1528
a444bd456fcc
ac3/spdif patch by German Gomez Garcia <german@piraos.com>
arpi
parents:
1456
diff
changeset
|
183 return CONTROL_TRUE; |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
184 |
4788
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
185 if ((fd = open(oss_mixer_device, O_RDONLY)) > 0) |
1191 | 186 { |
187 ioctl(fd, SOUND_MIXER_READ_DEVMASK, &devs); | |
11837 | 188 if (devs & (1 << oss_mixer_channel)) |
4788
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
189 { |
1191 | 190 if (cmd == AOCONTROL_GET_VOLUME) |
4788
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
191 { |
11837 | 192 ioctl(fd, MIXER_READ(oss_mixer_channel), &v); |
4788
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
193 vol->right = (v & 0xFF00) >> 8; |
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
194 vol->left = v & 0x00FF; |
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
195 } |
1191 | 196 else |
4788
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
197 { |
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
198 v = ((int)vol->right << 8) | (int)vol->left; |
11837 | 199 ioctl(fd, MIXER_WRITE(oss_mixer_channel), &v); |
4788
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
200 } |
d678ce495a75
Moved HW dependent mixer stuff to libao and removed master switch
anders
parents:
4184
diff
changeset
|
201 } |
1191 | 202 else |
203 { | |
204 close(fd); | |
205 return CONTROL_ERROR; | |
206 } | |
207 close(fd); | |
208 return CONTROL_OK; | |
209 } | |
210 } | |
211 return CONTROL_ERROR; | |
954 | 212 } |
213 return CONTROL_UNKNOWN; | |
214 } | |
215 | |
216 // open & setup audio device | |
217 // return: 1=success 0=fail | |
218 static int init(int rate,int channels,int format,int flags){ | |
11837 | 219 char *mixer_channels [SOUND_MIXER_NRDEVICES] = SOUND_DEVICE_NAMES; |
14245 | 220 int oss_format; |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
221 char *mdev = mixer_device, *mchan = mixer_channel; |
954 | 222 |
14264 | 223 mp_msg(MSGT_AO,MSGL_V,"ao2: %d Hz %d chans %s\n",rate,channels, |
224 af_fmt2str_short(format)); | |
954 | 225 |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
226 if (ao_subdevice) { |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
227 char *m,*c; |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
228 m = strchr(ao_subdevice,':'); |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
229 if(m) { |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
230 c = strchr(m+1,':'); |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
231 if(c) { |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
232 mchan = c+1; |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
233 c[0] = '\0'; |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
234 } |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
235 mdev = m+1; |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
236 m[0] = '\0'; |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
237 } |
1191 | 238 dsp = ao_subdevice; |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
239 } |
1191 | 240 |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
241 if(mdev) |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
242 oss_mixer_device=mdev; |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
243 else |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
244 oss_mixer_device=PATH_DEV_MIXER; |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
245 |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
246 if(mchan){ |
11837 | 247 int fd, devs, i; |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
248 |
11837 | 249 if ((fd = open(oss_mixer_device, O_RDONLY)) == -1){ |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
250 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_CantOpenMixer, |
11837 | 251 oss_mixer_device, strerror(errno)); |
252 }else{ | |
253 ioctl(fd, SOUND_MIXER_READ_DEVMASK, &devs); | |
254 close(fd); | |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
255 |
11837 | 256 for (i=0; i<SOUND_MIXER_NRDEVICES; i++){ |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
257 if(!strcasecmp(mixer_channels[i], mchan)){ |
11837 | 258 if(!(devs & (1 << i))){ |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
259 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_ChanNotFound,mchan); |
11837 | 260 i = SOUND_MIXER_NRDEVICES+1; |
261 break; | |
262 } | |
263 oss_mixer_channel = i; | |
264 break; | |
265 } | |
266 } | |
267 if(i==SOUND_MIXER_NRDEVICES){ | |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
268 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_ChanNotFound,mchan); |
11837 | 269 } |
270 } | |
16959
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
271 } else |
832a93fc5deb
Allow setting the mixer per instance so one can fallback between
albeu
parents:
15898
diff
changeset
|
272 oss_mixer_channel = SOUND_MIXER_PCM; |
11837 | 273 |
6296 | 274 mp_msg(MSGT_AO,MSGL_V,"audio_setup: using '%s' dsp device\n", dsp); |
11837 | 275 mp_msg(MSGT_AO,MSGL_V,"audio_setup: using '%s' mixer device\n", oss_mixer_device); |
276 mp_msg(MSGT_AO,MSGL_V,"audio_setup: using '%s' mixer device\n", mixer_channels[oss_mixer_channel]); | |
1191 | 277 |
5907
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
278 #ifdef __linux__ |
5204
6bbf3271a694
non-blocking open - patch by Fredrik Kuivinen <freku045@student.liu.se>
arpi
parents:
4803
diff
changeset
|
279 audio_fd=open(dsp, O_WRONLY | O_NONBLOCK); |
5907
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
280 #else |
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
281 audio_fd=open(dsp, O_WRONLY); |
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
282 #endif |
954 | 283 if(audio_fd<0){ |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
284 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_CantOpenDev, dsp, strerror(errno)); |
954 | 285 return 0; |
286 } | |
287 | |
5907
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
288 #ifdef __linux__ |
5204
6bbf3271a694
non-blocking open - patch by Fredrik Kuivinen <freku045@student.liu.se>
arpi
parents:
4803
diff
changeset
|
289 /* Remove the non-blocking flag */ |
6bbf3271a694
non-blocking open - patch by Fredrik Kuivinen <freku045@student.liu.se>
arpi
parents:
4803
diff
changeset
|
290 if(fcntl(audio_fd, F_SETFL, 0) < 0) { |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
291 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_CantMakeFd, strerror(errno)); |
5204
6bbf3271a694
non-blocking open - patch by Fredrik Kuivinen <freku045@student.liu.se>
arpi
parents:
4803
diff
changeset
|
292 return 0; |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
293 } |
5907
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
294 #endif |
8303 | 295 |
296 #if defined(FD_CLOEXEC) && defined(F_SETFD) | |
297 fcntl(audio_fd, F_SETFD, FD_CLOEXEC); | |
298 #endif | |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
299 |
14245 | 300 if(format == AF_FORMAT_AC3) { |
4184
f648f699eda6
hwac3 fix for cmedia 8738 by Hans-Peter Raschke <Hans-Peter.Raschke@wintermann-datenservice.de>
arpi
parents:
3455
diff
changeset
|
301 ao_data.samplerate=rate; |
f648f699eda6
hwac3 fix for cmedia 8738 by Hans-Peter Raschke <Hans-Peter.Raschke@wintermann-datenservice.de>
arpi
parents:
3455
diff
changeset
|
302 ioctl (audio_fd, SNDCTL_DSP_SPEED, &ao_data.samplerate); |
f648f699eda6
hwac3 fix for cmedia 8738 by Hans-Peter Raschke <Hans-Peter.Raschke@wintermann-datenservice.de>
arpi
parents:
3455
diff
changeset
|
303 } |
5790 | 304 |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
305 ac3_retry: |
3095 | 306 ao_data.format=format; |
14245 | 307 oss_format=format2oss(format); |
14260
7f3c14830dcd
100l set default format for AF_FORMATs not supported by sound card
rtognimp
parents:
14245
diff
changeset
|
308 if (oss_format == -1) { |
29401
f01023c524c3
Replace WORDS_BIGENDIAN by HAVE_BIGENDIAN in all internal code.
diego
parents:
29396
diff
changeset
|
309 #if HAVE_BIGENDIAN |
14245 | 310 oss_format=AFMT_S16_BE; |
5790 | 311 #else |
14245 | 312 oss_format=AFMT_S16_LE; |
5790 | 313 #endif |
14404
e4a52af25ee4
Use AF_FORMAT_S16_NE instead of #ifdef WORDS_BIGENDIAN ...
reimar
parents:
14397
diff
changeset
|
314 format=AF_FORMAT_S16_NE; |
14260
7f3c14830dcd
100l set default format for AF_FORMATs not supported by sound card
rtognimp
parents:
14245
diff
changeset
|
315 } |
7f3c14830dcd
100l set default format for AF_FORMATs not supported by sound card
rtognimp
parents:
14245
diff
changeset
|
316 if( ioctl(audio_fd, SNDCTL_DSP_SETFMT, &oss_format)<0 || |
14834
2d919650990a
Have OSS audio out fall back to s16ne instead of u8 if it can't open the
ivo
parents:
14609
diff
changeset
|
317 oss_format != format2oss(format)) { |
2d919650990a
Have OSS audio out fall back to s16ne instead of u8 if it can't open the
ivo
parents:
14609
diff
changeset
|
318 mp_msg(MSGT_AO,MSGL_WARN, MSGTR_AO_OSS_CantSet, dsp, |
2d919650990a
Have OSS audio out fall back to s16ne instead of u8 if it can't open the
ivo
parents:
14609
diff
changeset
|
319 af_fmt2str_short(format), af_fmt2str_short(AF_FORMAT_S16_NE) ); |
14404
e4a52af25ee4
Use AF_FORMAT_S16_NE instead of #ifdef WORDS_BIGENDIAN ...
reimar
parents:
14397
diff
changeset
|
320 format=AF_FORMAT_S16_NE; |
5790 | 321 goto ac3_retry; |
1528
a444bd456fcc
ac3/spdif patch by German Gomez Garcia <german@piraos.com>
arpi
parents:
1456
diff
changeset
|
322 } |
7668 | 323 #if 0 |
14245 | 324 if(oss_format!=format2oss(format)) |
17058 | 325 mp_msg(MSGT_AO,MSGL_WARN,"WARNING! Your soundcard does NOT support %s sample format! Broken audio or bad playback speed are possible! Try with '-af format'\n",audio_out_format_name(format)); |
7668 | 326 #endif |
14245 | 327 |
328 ao_data.format = oss2format(oss_format); | |
329 if (ao_data.format == -1) return 0; | |
14264 | 330 |
331 mp_msg(MSGT_AO,MSGL_V,"audio_setup: sample format: %s (requested: %s)\n", | |
332 af_fmt2str_short(ao_data.format), af_fmt2str_short(format)); | |
29263
0f1b5b68af32
whitespace cosmetics: Remove all trailing whitespace.
diego
parents:
28823
diff
changeset
|
333 |
8848 | 334 ao_data.channels = channels; |
14245 | 335 if(format != AF_FORMAT_AC3) { |
3181
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
336 // We only use SNDCTL_DSP_CHANNELS for >2 channels, in case some drivers don't have it |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
337 if (ao_data.channels > 2) { |
3319
66134af21278
fixed to check that SNDCTL_DSP_CHANNELS actually grants the requested number of channels
steve
parents:
3181
diff
changeset
|
338 if ( ioctl(audio_fd, SNDCTL_DSP_CHANNELS, &ao_data.channels) == -1 || |
66134af21278
fixed to check that SNDCTL_DSP_CHANNELS actually grants the requested number of channels
steve
parents:
3181
diff
changeset
|
339 ao_data.channels != channels ) { |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
340 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_CantSetChans, channels); |
3181
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
341 return 0; |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
342 } |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
343 } |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
344 else { |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
345 int c = ao_data.channels-1; |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
346 if (ioctl (audio_fd, SNDCTL_DSP_STEREO, &c) == -1) { |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
347 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_CantSetChans, ao_data.channels); |
3181
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
348 return 0; |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
349 } |
9141
20793317e5ff
nice 10l bug, found by Balatoni Denes <pnis@coder.hu>
arpi
parents:
8848
diff
changeset
|
350 ao_data.channels=c+1; |
3181
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
351 } |
6296 | 352 mp_msg(MSGT_AO,MSGL_V,"audio_setup: using %d channels (requested: %d)\n", ao_data.channels, channels); |
3181
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
353 // set rate |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
354 ao_data.samplerate=rate; |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
355 ioctl (audio_fd, SNDCTL_DSP_SPEED, &ao_data.samplerate); |
6296 | 356 mp_msg(MSGT_AO,MSGL_V,"audio_setup: using %d Hz samplerate (requested: %d)\n",ao_data.samplerate,rate); |
1528
a444bd456fcc
ac3/spdif patch by German Gomez Garcia <german@piraos.com>
arpi
parents:
1456
diff
changeset
|
357 } |
954 | 358 |
359 if(ioctl(audio_fd, SNDCTL_DSP_GETOSPACE, &zz)==-1){ | |
360 int r=0; | |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
361 mp_msg(MSGT_AO,MSGL_WARN,MSGTR_AO_OSS_CantUseGetospace); |
954 | 362 if(ioctl(audio_fd, SNDCTL_DSP_GETBLKSIZE, &r)==-1){ |
6296 | 363 mp_msg(MSGT_AO,MSGL_V,"audio_setup: %d bytes/frag (config.h)\n",ao_data.outburst); |
954 | 364 } else { |
3095 | 365 ao_data.outburst=r; |
6296 | 366 mp_msg(MSGT_AO,MSGL_V,"audio_setup: %d bytes/frag (GETBLKSIZE)\n",ao_data.outburst); |
954 | 367 } |
368 } else { | |
6296 | 369 mp_msg(MSGT_AO,MSGL_V,"audio_setup: frags: %3d/%d (%d bytes/frag) free: %6d\n", |
954 | 370 zz.fragments, zz.fragstotal, zz.fragsize, zz.bytes); |
3095 | 371 if(ao_data.buffersize==-1) ao_data.buffersize=zz.bytes; |
372 ao_data.outburst=zz.fragsize; | |
954 | 373 } |
374 | |
3095 | 375 if(ao_data.buffersize==-1){ |
954 | 376 // Measuring buffer size: |
377 void* data; | |
3095 | 378 ao_data.buffersize=0; |
954 | 379 #ifdef HAVE_AUDIO_SELECT |
3095 | 380 data=malloc(ao_data.outburst); memset(data,0,ao_data.outburst); |
381 while(ao_data.buffersize<0x40000){ | |
954 | 382 fd_set rfds; |
383 struct timeval tv; | |
384 FD_ZERO(&rfds); FD_SET(audio_fd,&rfds); | |
385 tv.tv_sec=0; tv.tv_usec = 0; | |
386 if(!select(audio_fd+1, NULL, &rfds, NULL, &tv)) break; | |
3095 | 387 write(audio_fd,data,ao_data.outburst); |
388 ao_data.buffersize+=ao_data.outburst; | |
954 | 389 } |
390 free(data); | |
3095 | 391 if(ao_data.buffersize==0){ |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
392 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_CantUseSelect); |
954 | 393 return 0; |
394 } | |
395 #endif | |
396 } | |
397 | |
8603
30bef3c97b8b
ao_oss was not using the channel & format returned by the soundcard
arpi
parents:
8304
diff
changeset
|
398 ao_data.bps=ao_data.channels; |
14245 | 399 if(ao_data.format != AF_FORMAT_U8 && ao_data.format != AF_FORMAT_S8) |
8603
30bef3c97b8b
ao_oss was not using the channel & format returned by the soundcard
arpi
parents:
8304
diff
changeset
|
400 ao_data.bps*=2; |
30bef3c97b8b
ao_oss was not using the channel & format returned by the soundcard
arpi
parents:
8304
diff
changeset
|
401 |
6075
0b3b6d03779c
fix for L<->R swap with 6ch playback - based on patch by Eric Lammerts <eric@lammerts.org>
arpi
parents:
5907
diff
changeset
|
402 ao_data.outburst-=ao_data.outburst % ao_data.bps; // round down |
8603
30bef3c97b8b
ao_oss was not using the channel & format returned by the soundcard
arpi
parents:
8304
diff
changeset
|
403 ao_data.bps*=ao_data.samplerate; |
6075
0b3b6d03779c
fix for L<->R swap with 6ch playback - based on patch by Eric Lammerts <eric@lammerts.org>
arpi
parents:
5907
diff
changeset
|
404 |
954 | 405 return 1; |
406 } | |
407 | |
408 // close audio device | |
12145 | 409 static void uninit(int immed){ |
7118
4332922afec4
release /dev/dsp on pause patch by Eric Lammerts <eric@lammerts.org> (and D Richard Felker III <dalias@aerifal.cx>)
alex
parents:
6899
diff
changeset
|
410 if(audio_fd == -1) return; |
12145 | 411 #ifdef SNDCTL_DSP_SYNC |
412 // to get the buffer played | |
413 if (!immed) | |
414 ioctl(audio_fd, SNDCTL_DSP_SYNC, NULL); | |
415 #endif | |
1020
72cacd3b8f30
Solaris 8 support - patch by Marcus Comstedt <marcus@idonex.se>
arpi_esp
parents:
956
diff
changeset
|
416 #ifdef SNDCTL_DSP_RESET |
12145 | 417 if (immed) |
418 ioctl(audio_fd, SNDCTL_DSP_RESET, NULL); | |
1020
72cacd3b8f30
Solaris 8 support - patch by Marcus Comstedt <marcus@idonex.se>
arpi_esp
parents:
956
diff
changeset
|
419 #endif |
954 | 420 close(audio_fd); |
7118
4332922afec4
release /dev/dsp on pause patch by Eric Lammerts <eric@lammerts.org> (and D Richard Felker III <dalias@aerifal.cx>)
alex
parents:
6899
diff
changeset
|
421 audio_fd = -1; |
954 | 422 } |
423 | |
424 // stop playing and empty buffers (for seeking/pause) | |
17566
f580a7755ac5
Patch by Stefan Huehner / stefan % huehner ! org \
rathann
parents:
17058
diff
changeset
|
425 static void reset(void){ |
14245 | 426 int oss_format; |
12145 | 427 uninit(1); |
5907
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
428 audio_fd=open(dsp, O_WRONLY); |
d8c34a35ccb9
nonblock open is not legal for OSS (see OSS api docs), and causes problems on freebsd (and maybe other OSs)
arpi
parents:
5872
diff
changeset
|
429 if(audio_fd < 0){ |
13383
c1955840883d
mp_msg transition of unmaintained audio output drivers.
ivo
parents:
12383
diff
changeset
|
430 mp_msg(MSGT_AO,MSGL_ERR,MSGTR_AO_OSS_CantReopen, strerror(errno)); |
954 | 431 return; |
432 } | |
433 | |
10600
3cf428b56cde
Set close-on-exec after newer open (in reset func). Patch by Andriy Gapon <agapon@cv-nj.com>
alex
parents:
9633
diff
changeset
|
434 #if defined(FD_CLOEXEC) && defined(F_SETFD) |
3cf428b56cde
Set close-on-exec after newer open (in reset func). Patch by Andriy Gapon <agapon@cv-nj.com>
alex
parents:
9633
diff
changeset
|
435 fcntl(audio_fd, F_SETFD, FD_CLOEXEC); |
3cf428b56cde
Set close-on-exec after newer open (in reset func). Patch by Andriy Gapon <agapon@cv-nj.com>
alex
parents:
9633
diff
changeset
|
436 #endif |
3cf428b56cde
Set close-on-exec after newer open (in reset func). Patch by Andriy Gapon <agapon@cv-nj.com>
alex
parents:
9633
diff
changeset
|
437 |
14245 | 438 oss_format = format2oss(ao_data.format); |
28605
65e49c604b25
Set samplerate in reset also for AC3, and set it before the format in that
reimar
parents:
28579
diff
changeset
|
439 if(ao_data.format == AF_FORMAT_AC3) |
65e49c604b25
Set samplerate in reset also for AC3, and set it before the format in that
reimar
parents:
28579
diff
changeset
|
440 ioctl (audio_fd, SNDCTL_DSP_SPEED, &ao_data.samplerate); |
14245 | 441 ioctl (audio_fd, SNDCTL_DSP_SETFMT, &oss_format); |
442 if(ao_data.format != AF_FORMAT_AC3) { | |
3181
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
443 if (ao_data.channels > 2) |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
444 ioctl (audio_fd, SNDCTL_DSP_CHANNELS, &ao_data.channels); |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
445 else { |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
446 int c = ao_data.channels-1; |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
447 ioctl (audio_fd, SNDCTL_DSP_STEREO, &c); |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
448 } |
c8edb0691f09
Extended oss output driver and libac3 to support 4 and 6 channel output mixes. added -channels command line option
steve
parents:
3137
diff
changeset
|
449 ioctl (audio_fd, SNDCTL_DSP_SPEED, &ao_data.samplerate); |
1528
a444bd456fcc
ac3/spdif patch by German Gomez Garcia <german@piraos.com>
arpi
parents:
1456
diff
changeset
|
450 } |
954 | 451 } |
452 | |
1038
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
453 // stop playing, keep buffers (for pause) |
17566
f580a7755ac5
Patch by Stefan Huehner / stefan % huehner ! org \
rathann
parents:
17058
diff
changeset
|
454 static void audio_pause(void) |
1038
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
455 { |
23809
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
456 prepause_space = get_space(); |
12145 | 457 uninit(1); |
1038
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
458 } |
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
459 |
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
460 // resume playing, after audio_pause() |
17566
f580a7755ac5
Patch by Stefan Huehner / stefan % huehner ! org \
rathann
parents:
17058
diff
changeset
|
461 static void audio_resume(void) |
1038
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
462 { |
23809
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
463 int fillcnt; |
7118
4332922afec4
release /dev/dsp on pause patch by Eric Lammerts <eric@lammerts.org> (and D Richard Felker III <dalias@aerifal.cx>)
alex
parents:
6899
diff
changeset
|
464 reset(); |
23809
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
465 fillcnt = get_space() - prepause_space; |
28579
0405513156d1
100l, do 0-filling on resume (to avoid desync after pause) in ao_oss only when
reimar
parents:
28343
diff
changeset
|
466 if (fillcnt > 0 && !(ao_data.format & AF_FORMAT_SPECIAL_MASK)) { |
23809
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
467 void *silence = calloc(fillcnt, 1); |
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
468 play(silence, fillcnt, 0); |
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
469 free(silence); |
6c348181fb20
Somewhat hackish fix for A-V desync with ao_oss and frame stepping:
reimar
parents:
21547
diff
changeset
|
470 } |
1038
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
471 } |
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
472 |
b36fb1ae4b53
applied solaris8/netbsd/other fixes patch by J¸«ärgen Keil <jk@tools.de>
arpi_esp
parents:
1020
diff
changeset
|
473 |
954 | 474 // return: how many bytes can be played without blocking |
17566
f580a7755ac5
Patch by Stefan Huehner / stefan % huehner ! org \
rathann
parents:
17058
diff
changeset
|
475 static int get_space(void){ |
3095 | 476 int playsize=ao_data.outburst; |
954 | 477 |
1020
72cacd3b8f30
Solaris 8 support - patch by Marcus Comstedt <marcus@idonex.se>
arpi_esp
parents:
956
diff
changeset
|
478 #ifdef SNDCTL_DSP_GETOSPACE |
954 | 479 if(ioctl(audio_fd, SNDCTL_DSP_GETOSPACE, &zz)!=-1){ |
480 // calculate exact buffer space: | |
3455
921a78c7b4aa
limit get_space return <= MAX_OUTBURST, whilst always an exact number of fragments
steve
parents:
3319
diff
changeset
|
481 playsize = zz.fragments*zz.fragsize; |
921a78c7b4aa
limit get_space return <= MAX_OUTBURST, whilst always an exact number of fragments
steve
parents:
3319
diff
changeset
|
482 if (playsize > MAX_OUTBURST) |
921a78c7b4aa
limit get_space return <= MAX_OUTBURST, whilst always an exact number of fragments
steve
parents:
3319
diff
changeset
|
483 playsize = (MAX_OUTBURST / zz.fragsize) * zz.fragsize; |
921a78c7b4aa
limit get_space return <= MAX_OUTBURST, whilst always an exact number of fragments
steve
parents:
3319
diff
changeset
|
484 return playsize; |
954 | 485 } |
1020
72cacd3b8f30
Solaris 8 support - patch by Marcus Comstedt <marcus@idonex.se>
arpi_esp
parents:
956
diff
changeset
|
486 #endif |
954 | 487 |
488 // check buffer | |
489 #ifdef HAVE_AUDIO_SELECT | |
490 { fd_set rfds; | |
491 struct timeval tv; | |
492 FD_ZERO(&rfds); | |
493 FD_SET(audio_fd, &rfds); | |
494 tv.tv_sec = 0; | |
495 tv.tv_usec = 0; | |
496 if(!select(audio_fd+1, NULL, &rfds, NULL, &tv)) return 0; // not block! | |
497 } | |
498 #endif | |
499 | |
3095 | 500 return ao_data.outburst; |
954 | 501 } |
502 | |
503 // plays 'len' bytes of 'data' | |
504 // it should round it down to outburst*n | |
505 // return: number of bytes played | |
506 static int play(void* data,int len,int flags){ | |
18842 | 507 if(len==0) |
508 return len; | |
509 if(len>ao_data.outburst || !(flags & AOPLAY_FINAL_CHUNK)) { | |
510 len/=ao_data.outburst; | |
511 len*=ao_data.outburst; | |
512 } | |
513 len=write(audio_fd,data,len); | |
954 | 514 return len; |
515 } | |
516 | |
517 static int audio_delay_method=2; | |
518 | |
3095 | 519 // return: delay in seconds between first and last sample in buffer |
17566
f580a7755ac5
Patch by Stefan Huehner / stefan % huehner ! org \
rathann
parents:
17058
diff
changeset
|
520 static float get_delay(void){ |
3095 | 521 /* Calculate how many bytes/second is sent out */ |
954 | 522 if(audio_delay_method==2){ |
5872 | 523 #ifdef SNDCTL_DSP_GETODELAY |
954 | 524 int r=0; |
525 if(ioctl(audio_fd, SNDCTL_DSP_GETODELAY, &r)!=-1) | |
3095 | 526 return ((float)r)/(float)ao_data.bps; |
5872 | 527 #endif |
954 | 528 audio_delay_method=1; // fallback if not supported |
529 } | |
530 if(audio_delay_method==1){ | |
531 // SNDCTL_DSP_GETOSPACE | |
532 if(ioctl(audio_fd, SNDCTL_DSP_GETOSPACE, &zz)!=-1) | |
3095 | 533 return ((float)(ao_data.buffersize-zz.bytes))/(float)ao_data.bps; |
954 | 534 audio_delay_method=0; // fallback if not supported |
535 } | |
3095 | 536 return ((float)ao_data.buffersize)/(float)ao_data.bps; |
954 | 537 } |