21 #include "../../SDL_internal.h"
23 #if SDL_AUDIO_DRIVER_OSS
34 #include <sys/ioctl.h>
37 #if SDL_AUDIO_DRIVER_OSS_SOUNDCARD_H
39 #include <soundcard.h>
42 #include <sys/soundcard.h>
47 #include "../SDL_audio_c.h"
48 #include "../SDL_audiodev_c.h"
53 DSP_DetectDevices(
void)
60 DSP_CloseDevice(
_THIS)
62 if (this->hidden->audio_fd >= 0) {
63 close(this->hidden->audio_fd);
71 DSP_OpenDevice(
_THIS,
void *
handle,
const char *devname,
int iscapture)
81 if (devname ==
NULL) {
83 if (devname ==
NULL) {
100 if (this->hidden ==
NULL) {
106 this->hidden->audio_fd = open(devname,
flags, 0);
107 if (this->hidden->audio_fd < 0) {
108 return SDL_SetError(
"Couldn't open %s: %s", devname, strerror(errno));
114 ctlflags = fcntl(this->hidden->audio_fd, F_GETFL);
115 ctlflags &= ~O_NONBLOCK;
116 if (fcntl(this->hidden->audio_fd, F_SETFL, ctlflags) < 0) {
117 return SDL_SetError(
"Couldn't set audio blocking mode");
122 if (ioctl(this->hidden->audio_fd, SNDCTL_DSP_GETFMTS, &
value) < 0) {
123 perror(
"SNDCTL_DSP_GETFMTS");
130 !format && test_format;) {
132 fprintf(stderr,
"Trying format 0x%4.4x\n", test_format);
134 switch (test_format) {
136 if (
value & AFMT_U8) {
141 if (
value & AFMT_S16_LE) {
146 if (
value & AFMT_S16_BE) {
156 if (
value & AFMT_S8) {
161 if (
value & AFMT_U16_LE) {
166 if (
value & AFMT_U16_BE) {
180 return SDL_SetError(
"Couldn't find any hardware audio formats");
186 if ((ioctl(this->hidden->audio_fd, SNDCTL_DSP_SETFMT, &
value) < 0) ||
188 perror(
"SNDCTL_DSP_SETFMT");
194 if (ioctl(this->hidden->audio_fd, SNDCTL_DSP_CHANNELS, &
value) < 0) {
195 perror(
"SNDCTL_DSP_CHANNELS");
196 return SDL_SetError(
"Cannot set the number of channels");
202 if (ioctl(this->hidden->audio_fd, SNDCTL_DSP_SPEED, &
value) < 0) {
203 perror(
"SNDCTL_DSP_SPEED");
212 for (frag_spec = 0; (0x01U << frag_spec) < this->
spec.
size; ++frag_spec);
213 if ((0x01U << frag_spec) != this->
spec.
size) {
214 return SDL_SetError(
"Fragment size must be a power of two");
216 frag_spec |= 0x00020000;
220 fprintf(stderr,
"Requesting %d fragments of size %d\n",
221 (frag_spec >> 16), 1 << (frag_spec & 0xFFFF));
223 if (ioctl(this->hidden->audio_fd, SNDCTL_DSP_SETFRAGMENT, &frag_spec) < 0) {
224 perror(
"SNDCTL_DSP_SETFRAGMENT");
229 ioctl(this->hidden->audio_fd, SNDCTL_DSP_GETOSPACE, &info);
230 fprintf(stderr,
"fragments = %d\n", info.fragments);
231 fprintf(stderr,
"fragstotal = %d\n", info.fragstotal);
232 fprintf(stderr,
"fragsize = %d\n", info.fragsize);
233 fprintf(stderr,
"bytes = %d\n", info.bytes);
239 this->hidden->mixlen = this->
spec.
size;
241 if (this->hidden->mixbuf ==
NULL) {
244 SDL_memset(this->hidden->mixbuf, this->spec.silence, this->spec.size);
253 DSP_PlayDevice(
_THIS)
256 if (write(
h->audio_fd,
h->mixbuf,
h->mixlen) == -1) {
257 perror(
"Audio write");
261 fprintf(stderr,
"Wrote %d bytes of audio data\n",
h->mixlen);
266 DSP_GetDeviceBuf(
_THIS)
268 return (this->hidden->mixbuf);
272 DSP_CaptureFromDevice(
_THIS,
void *
buffer,
int buflen)
274 return (
int) read(this->hidden->audio_fd,
buffer, buflen);
278 DSP_FlushCapture(
_THIS)
282 if (ioctl(
h->audio_fd, SNDCTL_DSP_GETISPACE, &info) == 0) {
283 while (info.bytes > 0) {
286 const ssize_t br = read(
h->audio_fd,
buf,
len);
315 "dsp",
"OSS /dev/dsp standard audio", DSP_Init, 0