Fri May 24 18:13:36 2019 UTC ()
SDL2: Audio changes!

SDL_netbsdaudio.c:

* Rework the NetBSD audio driver significantly. Use blocking i/o as
suggested on the SDL bug tracker. Rework the intialization steps
since they were very wrong. All calls to Delay now removed.

* Fixes the horrible stuttering on my system.

* Performance now approximately matches SDL_AUDIODRIVER=dsp. Code
is also closer to SDL_dspaudio.

* Tested with multimedia/mpv, games/etlegacy, emulators/retroarch,
wip/tesseract-game, using SDL audio outputs.

options.mk:

* Add "jack" option, disabled by default.
* Enable ALSA by default on Linux.
* Fix some whitespace problems.

Bump PKGREVISION.


(nia)
diff -r1.34 -r1.35 pkgsrc/devel/SDL2/Makefile
diff -r1.32 -r1.33 pkgsrc/devel/SDL2/distinfo
diff -r1.10 -r1.11 pkgsrc/devel/SDL2/options.mk
diff -r1.1 -r1.2 pkgsrc/devel/SDL2/patches/patch-src_audio_netbsd_SDL__netbsdaudio.c

cvs diff -r1.34 -r1.35 pkgsrc/devel/SDL2/Makefile (expand / switch to unified diff)

--- pkgsrc/devel/SDL2/Makefile 2018/12/30 14:47:04 1.34
+++ pkgsrc/devel/SDL2/Makefile 2019/05/24 18:13:36 1.35
@@ -1,17 +1,17 @@ @@ -1,17 +1,17 @@
1# $NetBSD: Makefile,v 1.34 2018/12/30 14:47:04 maya Exp $ 1# $NetBSD: Makefile,v 1.35 2019/05/24 18:13:36 nia Exp $
2 2
3DISTNAME= SDL2-2.0.9 3DISTNAME= SDL2-2.0.9
4PKGREVISION= 2 4PKGREVISION= 3
5CATEGORIES= devel 5CATEGORIES= devel
6MASTER_SITES= http://www.libsdl.org/release/ 6MASTER_SITES= http://www.libsdl.org/release/
7 7
8MAINTAINER= pkgsrc-users@NetBSD.org 8MAINTAINER= pkgsrc-users@NetBSD.org
9HOMEPAGE= http://www.libsdl.org/ 9HOMEPAGE= http://www.libsdl.org/
10COMMENT= Simple DirectMedia Layer is a cross-platform multimedia library 10COMMENT= Simple DirectMedia Layer is a cross-platform multimedia library
11LICENSE= zlib 11LICENSE= zlib
12 12
13USE_LANGUAGES= c c++ 13USE_LANGUAGES= c c++
14USE_LIBTOOL= yes 14USE_LIBTOOL= yes
15USE_TOOLS+= gmake pkg-config autoconf automake autoreconf 15USE_TOOLS+= gmake pkg-config autoconf automake autoreconf
16GNU_CONFIGURE= yes 16GNU_CONFIGURE= yes
17PKGCONFIG_OVERRIDE+= sdl2.pc.in 17PKGCONFIG_OVERRIDE+= sdl2.pc.in

cvs diff -r1.32 -r1.33 pkgsrc/devel/SDL2/distinfo (expand / switch to unified diff)

--- pkgsrc/devel/SDL2/distinfo 2018/12/30 14:47:04 1.32
+++ pkgsrc/devel/SDL2/distinfo 2019/05/24 18:13:36 1.33
@@ -1,11 +1,11 @@ @@ -1,11 +1,11 @@
1$NetBSD: distinfo,v 1.32 2018/12/30 14:47:04 maya Exp $ 1$NetBSD: distinfo,v 1.33 2019/05/24 18:13:36 nia Exp $
2 2
3SHA1 (SDL2-2.0.9.tar.gz) = 4354c6baad9a48486182656a7506abfb63e9bff5 3SHA1 (SDL2-2.0.9.tar.gz) = 4354c6baad9a48486182656a7506abfb63e9bff5
4RMD160 (SDL2-2.0.9.tar.gz) = db2efabf55af41cddf015db0b5213b11ef22b9d0 4RMD160 (SDL2-2.0.9.tar.gz) = db2efabf55af41cddf015db0b5213b11ef22b9d0
5SHA512 (SDL2-2.0.9.tar.gz) = a78a4708b2bb5b35a7c7b7501eb3bd60a9aa3bb95a3d84e57763df4a377185e7312a94b66321eef7ca0d17255e4b402fc950e83ef0dbbd08f14ff1194107dc10 5SHA512 (SDL2-2.0.9.tar.gz) = a78a4708b2bb5b35a7c7b7501eb3bd60a9aa3bb95a3d84e57763df4a377185e7312a94b66321eef7ca0d17255e4b402fc950e83ef0dbbd08f14ff1194107dc10
6Size (SDL2-2.0.9.tar.gz) = 5246942 bytes 6Size (SDL2-2.0.9.tar.gz) = 5246942 bytes
7SHA1 (patch-configure) = 1631314dab18886ea553ee53fac89e16718cacab 7SHA1 (patch-configure) = 1631314dab18886ea553ee53fac89e16718cacab
8SHA1 (patch-src_audio_netbsd_SDL__netbsdaudio.c) = 7a1f32ea7029f8dc99aecfaead7c68f2fd6cb230 8SHA1 (patch-src_audio_netbsd_SDL__netbsdaudio.c) = a495f5ede3ab1bd01b0703b50081748a0e57f1c4
9SHA1 (patch-src_joystick_bsd_SDL__sysjoystick.c) = 152b5df76a91c7e7acde126b1464fdd464cf1ba2 9SHA1 (patch-src_joystick_bsd_SDL__sysjoystick.c) = 152b5df76a91c7e7acde126b1464fdd464cf1ba2
10SHA1 (patch-src_video_cocoa_SDL__cocoawindow.m) = 1d5ac9c17ceadf668925734b5cad311e26f2fc58 10SHA1 (patch-src_video_cocoa_SDL__cocoawindow.m) = 1d5ac9c17ceadf668925734b5cad311e26f2fc58
11SHA1 (patch-src_video_x11_SDL__x11opengl.c) = 70b63021c12c52760c0811c673b259844bdfcdc0 11SHA1 (patch-src_video_x11_SDL__x11opengl.c) = 70b63021c12c52760c0811c673b259844bdfcdc0

cvs diff -r1.10 -r1.11 pkgsrc/devel/SDL2/options.mk (expand / switch to unified diff)

--- pkgsrc/devel/SDL2/options.mk 2018/12/24 16:25:30 1.10
+++ pkgsrc/devel/SDL2/options.mk 2019/05/24 18:13:36 1.11
@@ -1,54 +1,61 @@ @@ -1,54 +1,61 @@
1# $NetBSD: options.mk,v 1.10 2018/12/24 16:25:30 nia Exp $ 1# $NetBSD: options.mk,v 1.11 2019/05/24 18:13:36 nia Exp $
2 2
3PKG_OPTIONS_VAR= PKG_OPTIONS.SDL2 3PKG_OPTIONS_VAR= PKG_OPTIONS.SDL2
4PKG_OPTIONS_REQUIRED_GROUPS= gl 4PKG_OPTIONS_REQUIRED_GROUPS= gl
5PKG_SUPPORTED_OPTIONS= alsa dbus esound nas oss pulseaudio x11 5PKG_SUPPORTED_OPTIONS= alsa dbus esound nas oss jack pulseaudio x11
6PKG_OPTIONS_GROUP.gl= opengl 6PKG_OPTIONS_GROUP.gl= opengl
7PKG_SUGGESTED_OPTIONS+= oss 7PKG_SUGGESTED_OPTIONS+= oss
 8PKG_SUGGESTED_OPTIONS.Linux+= alsa
8 9
9.if ${OPSYS} != "Darwin" 10.if ${OPSYS} != "Darwin"
10PKG_SUGGESTED_OPTIONS+= x11 11PKG_SUGGESTED_OPTIONS+= x11
11.endif 12.endif
12 13
13.include "../../mk/bsd.fast.prefs.mk" 14.include "../../mk/bsd.fast.prefs.mk"
14 15
15.if !empty(MACHINE_ARCH:M*arm*) 16.if !empty(MACHINE_ARCH:M*arm*)
16PKG_OPTIONS_GROUP.gl+= rpi 17PKG_OPTIONS_GROUP.gl+= rpi
17PKG_SUGGESTED_OPTIONS+= rpi 18PKG_SUGGESTED_OPTIONS+= rpi
18.else 19.else
19PKG_SUGGESTED_OPTIONS+= opengl 20PKG_SUGGESTED_OPTIONS+= opengl
20.endif 21.endif
21 22
22.include "../../mk/bsd.options.mk" 23.include "../../mk/bsd.options.mk"
23 24
24.if !empty(PKG_OPTIONS:Malsa) 25.if !empty(PKG_OPTIONS:Malsa)
25.include "../../audio/alsa-lib/buildlink3.mk" 26.include "../../audio/alsa-lib/buildlink3.mk"
26.else 27.else
27CONFIGURE_ARGS+= --disable-alsa 28CONFIGURE_ARGS+= --disable-alsa
28.endif 29.endif
29 30
30.if !empty(PKG_OPTIONS:Mdbus) 31.if !empty(PKG_OPTIONS:Mdbus)
31.include "../../sysutils/dbus/buildlink3.mk" 32.include "../../sysutils/dbus/buildlink3.mk"
32.else 33.else
33CONFIGURE_ARGS+= --disable-dbus 34CONFIGURE_ARGS+= --disable-dbus
34.endif 35.endif
35 36
36.if !empty(PKG_OPTIONS:Mesound) 37.if !empty(PKG_OPTIONS:Mesound)
37.include "../../audio/esound/buildlink3.mk" 38.include "../../audio/esound/buildlink3.mk"
38.else 39.else
39CONFIGURE_ARGS+= --disable-esd 40CONFIGURE_ARGS+= --disable-esd
40.endif 41.endif
41 42
 43.if !empty(PKG_OPTIONS:Mjack)
 44.include "../../audio/jack/buildlink3.mk"
 45.else
 46CONFIGURE_ARGS+= --disable-jack
 47.endif
 48
42.if !empty(PKG_OPTIONS:Mnas) 49.if !empty(PKG_OPTIONS:Mnas)
43.include "../../audio/nas/buildlink3.mk" 50.include "../../audio/nas/buildlink3.mk"
44.else 51.else
45CONFIGURE_ARGS+= --disable-nas 52CONFIGURE_ARGS+= --disable-nas
46.endif 53.endif
47 54
48.if !empty(PKG_OPTIONS:Mopengl) 55.if !empty(PKG_OPTIONS:Mopengl)
49. if ${OPSYS} != "Darwin" 56. if ${OPSYS} != "Darwin"
50.include "../../graphics/MesaLib/buildlink3.mk" 57.include "../../graphics/MesaLib/buildlink3.mk"
51. endif 58. endif
52.else 59.else
53CONFIGURE_ARGS+= --disable-video-opengl 60CONFIGURE_ARGS+= --disable-video-opengl
54.endif 61.endif
@@ -68,20 +75,20 @@ CONFIGURE_ARGS+= --disable-pulseaudio @@ -68,20 +75,20 @@ CONFIGURE_ARGS+= --disable-pulseaudio
68.if !empty(PKG_OPTIONS:Mx11) 75.if !empty(PKG_OPTIONS:Mx11)
69.include "../../x11/libXScrnSaver/buildlink3.mk" 76.include "../../x11/libXScrnSaver/buildlink3.mk"
70.include "../../x11/libXcursor/buildlink3.mk" 77.include "../../x11/libXcursor/buildlink3.mk"
71.include "../../x11/libXi/buildlink3.mk" 78.include "../../x11/libXi/buildlink3.mk"
72.include "../../x11/libXinerama/buildlink3.mk" 79.include "../../x11/libXinerama/buildlink3.mk"
73.include "../../x11/libXrandr/buildlink3.mk" 80.include "../../x11/libXrandr/buildlink3.mk"
74.else 81.else
75CONFIGURE_ARGS+= --disable-video-x11 82CONFIGURE_ARGS+= --disable-video-x11
76CONFIGURE_ARGS+= --disable-x11-shared 83CONFIGURE_ARGS+= --disable-x11-shared
77.endif 84.endif
78 85
79.if !empty(PKG_OPTIONS:Mrpi) 86.if !empty(PKG_OPTIONS:Mrpi)
80LOWER_VENDOR= raspberry 87LOWER_VENDOR= raspberry
81SUBST_CLASSES+= vc  88SUBST_CLASSES+= vc
82SUBST_STAGE.vc= pre-configure  89SUBST_STAGE.vc= pre-configure
83SUBST_MESSAGE.vc= Fixing path to VideoCore libraries.  90SUBST_MESSAGE.vc= Fixing path to VideoCore libraries.
84SUBST_FILES.vc= configure  91SUBST_FILES.vc= configure
85SUBST_SED.vc+= -e "s;/opt/vc;${PREFIX};g" 92SUBST_SED.vc+= -e "s;/opt/vc;${PREFIX};g"
86.include "../../misc/raspberrypi-userland/buildlink3.mk" 93.include "../../misc/raspberrypi-userland/buildlink3.mk"
87.endif 94.endif

cvs diff -r1.1 -r1.2 pkgsrc/devel/SDL2/patches/Attic/patch-src_audio_netbsd_SDL__netbsdaudio.c (expand / switch to unified diff)

--- pkgsrc/devel/SDL2/patches/Attic/patch-src_audio_netbsd_SDL__netbsdaudio.c 2017/09/26 13:10:56 1.1
+++ pkgsrc/devel/SDL2/patches/Attic/patch-src_audio_netbsd_SDL__netbsdaudio.c 2019/05/24 18:13:36 1.2
@@ -1,56 +1,284 @@ @@ -1,56 +1,284 @@
1$NetBSD: patch-src_audio_netbsd_SDL__netbsdaudio.c,v 1.1 2017/09/26 13:10:56 adam Exp $ 1$NetBSD: patch-src_audio_netbsd_SDL__netbsdaudio.c,v 1.2 2019/05/24 18:13:36 nia Exp $
2 2
3Remove delay as there is already an inherent delay in writing audio. 3Remove delays and use blocking i/o
4https://bugzilla.libsdl.org/show_bug.cgi?id=3177 4https://bugzilla.libsdl.org/show_bug.cgi?id=3177
5 5
6audio_prinfo needs 'struct' on NetBSD. 6audio_prinfo needs 'struct' on NetBSD.
7Use correct prinfo. 7Use correct prinfo type (play/record)
8Inform upper layer of blocksize 8Rework initialization
9 9
10--- src/audio/netbsd/SDL_netbsdaudio.c.orig 2017-09-26 12:34:35.000000000 +0000 10--- src/audio/netbsd/SDL_netbsdaudio.c.orig 2018-10-31 15:07:22.000000000 +0000
11+++ src/audio/netbsd/SDL_netbsdaudio.c 11+++ src/audio/netbsd/SDL_netbsdaudio.c
12@@ -63,14 +63,14 @@ NETBSDAUDIO_Status(_THIS) 12@@ -43,12 +43,7 @@
 13 #include "../SDL_audiodev_c.h"
 14 #include "SDL_netbsdaudio.h"
 15
 16-/* Use timer for synchronization */
 17-/* #define USE_TIMER_SYNC */
 18-
 19 /* #define DEBUG_AUDIO */
 20-/* #define DEBUG_AUDIO_STREAM */
 21-
 22
 23 static void
 24 NETBSDAUDIO_DetectDevices(void)
 25@@ -63,14 +58,14 @@ NETBSDAUDIO_Status(_THIS)
13 #ifdef DEBUG_AUDIO 26 #ifdef DEBUG_AUDIO
14 /* *INDENT-OFF* */ 27 /* *INDENT-OFF* */
15 audio_info_t info; 28 audio_info_t info;
16- const audio_prinfo *prinfo; 29- const audio_prinfo *prinfo;
17+ const struct audio_prinfo *prinfo; 30+ const struct audio_prinfo *prinfo;
18  31
19 if (ioctl(this->hidden->audio_fd, AUDIO_GETINFO, &info) < 0) { 32 if (ioctl(this->hidden->audio_fd, AUDIO_GETINFO, &info) < 0) {
20 fprintf(stderr, "AUDIO_GETINFO failed.\n"); 33 fprintf(stderr, "AUDIO_GETINFO failed.\n");
21 return; 34 return;
22 } 35 }
23  36
24- prinfo = this->iscapture ? &info.play : &info.record; 37- prinfo = this->iscapture ? &info.play : &info.record;
25+ prinfo = this->iscapture ? &info.record : &info.play; 38+ prinfo = this->iscapture ? &info.record : &info.play;
26  39
27 fprintf(stderr, "\n" 40 fprintf(stderr, "\n"
28 "[%s info]\n" 41 "[%s info]\n"
29@@ -184,10 +184,6 @@ NETBSDAUDIO_PlayDevice(_THIS) 42@@ -115,90 +110,37 @@ NETBSDAUDIO_Status(_THIS)
30 fprintf(stderr, "Wrote %d bytes of audio data\n", written); 43 (info.mode == AUMODE_PLAY) ? "PLAY"
31 #endif 44 : (info.mode = AUMODE_RECORD) ? "RECORD"
 45 : (info.mode == AUMODE_PLAY_ALL ? "PLAY_ALL" : "?"));
 46+
 47+ fprintf(stderr, "\n"
 48+ "[audio spec]\n"
 49+ "format : 0x%x\n"
 50+ "size : %u\n"
 51+ "",
 52+ this->spec.format,
 53+ this->spec.size);
 54 /* *INDENT-ON* */
 55 #endif /* DEBUG_AUDIO */
 56 }
 57
32  58
 59-/* This function waits until it is possible to write a full sound buffer */
 60-static void
 61-NETBSDAUDIO_WaitDevice(_THIS)
 62-{
 63-#ifndef USE_BLOCKING_WRITES /* Not necessary when using blocking writes */
 64- /* See if we need to use timed audio synchronization */
 65- if (this->hidden->frame_ticks) {
 66- /* Use timer for general audio synchronization */
 67- Sint32 ticks;
 68-
 69- ticks = ((Sint32) (this->hidden->next_frame - SDL_GetTicks())) - FUDGE_TICKS;
 70- if (ticks > 0) {
 71- SDL_Delay(ticks);
 72- }
 73- } else {
 74- /* Use SDL_IOReady() for audio synchronization */
 75-#ifdef DEBUG_AUDIO
 76- fprintf(stderr, "Waiting for audio to get ready\n");
 77-#endif
 78- if (SDL_IOReady(this->hidden->audio_fd, SDL_TRUE, 10 * 1000)
 79- <= 0) {
 80- const char *message =
 81- "Audio timeout - buggy audio driver? (disabled)";
 82- /* In general we should never print to the screen,
 83- but in this case we have no other way of letting
 84- the user know what happened.
 85- */
 86- fprintf(stderr, "SDL: %s\n", message);
 87- SDL_OpenedAudioDeviceDisconnected(this);
 88- /* Don't try to close - may hang */
 89- this->hidden->audio_fd = -1;
 90-#ifdef DEBUG_AUDIO
 91- fprintf(stderr, "Done disabling audio\n");
 92-#endif
 93- }
 94-#ifdef DEBUG_AUDIO
 95- fprintf(stderr, "Ready!\n");
 96-#endif
 97- }
 98-#endif /* !USE_BLOCKING_WRITES */
 99-}
 100-
 101 static void
 102 NETBSDAUDIO_PlayDevice(_THIS)
 103 {
 104- int written, p = 0;
 105+ struct SDL_PrivateAudioData *h = this->hidden;
 106+ int written;
 107
 108- /* Write the audio data, checking for EAGAIN on broken audio drivers */
 109- do {
 110- written = write(this->hidden->audio_fd,
 111- &this->hidden->mixbuf[p], this->hidden->mixlen - p);
 112-
 113- if (written > 0)
 114- p += written;
 115- if (written == -1 && errno != 0 && errno != EAGAIN && errno != EINTR) {
 116- /* Non recoverable error has occurred. It should be reported!!! */
 117- perror("audio");
 118- break;
 119- }
 120+ /* Write the audio data */
 121+ written = write(h->audio_fd, h->mixbuf, h->mixlen);
 122+ if (written == -1) {
 123+ /* Non recoverable error has occurred. It should be reported!!! */
 124+ SDL_OpenedAudioDeviceDisconnected(this);
 125+ perror("audio");
 126+ return;
 127+ }
 128
 129 #ifdef DEBUG_AUDIO
 130- fprintf(stderr, "Wrote %d bytes of audio data\n", written);
 131+ fprintf(stderr, "Wrote %d bytes of audio data\n", written);
 132 #endif
 133-
33- if (p < this->hidden->mixlen 134- if (p < this->hidden->mixlen
34- || ((written < 0) && ((errno == 0) || (errno == EAGAIN)))) { 135- || ((written < 0) && ((errno == 0) || (errno == EAGAIN)))) {
35- SDL_Delay(1); /* Let a little CPU time go by */ 136- SDL_Delay(1); /* Let a little CPU time go by */
36- } 137- }
37 } while (p < this->hidden->mixlen); 138- } while (p < this->hidden->mixlen);
 139-
 140- /* If timer synchronization is enabled, set the next write frame */
 141- if (this->hidden->frame_ticks) {
 142- this->hidden->next_frame += this->hidden->frame_ticks;
 143- }
 144-
 145- /* If we couldn't write, assume fatal error for now */
 146- if (written < 0) {
 147- SDL_OpenedAudioDeviceDisconnected(this);
 148- }
 149 }
 150
 151 static Uint8 *
 152@@ -212,28 +154,19 @@ static int
 153 NETBSDAUDIO_CaptureFromDevice(_THIS, void *_buffer, int buflen)
 154 {
 155 Uint8 *buffer = (Uint8 *) _buffer;
 156- int br, p = 0;
 157+ int br;
38  158
39 /* If timer synchronization is enabled, set the next write frame */ 159- /* Capture the audio data, checking for EAGAIN on broken audio drivers */
40@@ -274,7 +270,7 @@ NETBSDAUDIO_OpenDevice(_THIS, void *hand 160- do {
41 const int flags = iscapture ? OPEN_FLAGS_INPUT : OPEN_FLAGS_OUTPUT; 161- br = read(this->hidden->audio_fd, buffer + p, buflen - p);
 162- if (br > 0)
 163- p += br;
 164- if (br == -1 && errno != 0 && errno != EAGAIN && errno != EINTR) {
 165- /* Non recoverable error has occurred. It should be reported!!! */
 166- perror("audio");
 167- return p ? p : -1;
 168- }
 169+ br = read(this->hidden->audio_fd, buffer, buflen);
 170+ if (br == -1) {
 171+ /* Non recoverable error has occurred. It should be reported!!! */
 172+ perror("audio");
 173+ return -1;
 174+ }
 175
 176 #ifdef DEBUG_AUDIO
 177- fprintf(stderr, "Captured %d bytes of audio data\n", br);
 178+ fprintf(stderr, "Captured %d bytes of audio data\n", br);
 179 #endif
 180-
 181- if (p < buflen
 182- || ((br < 0) && ((errno == 0) || (errno == EAGAIN)))) {
 183- SDL_Delay(1); /* Let a little CPU time go by */
 184- }
 185- } while (p < buflen);
 186+ return 0;
 187 }
 188
 189 static void
 190@@ -271,10 +204,9 @@ NETBSDAUDIO_CloseDevice(_THIS)
 191 static int
 192 NETBSDAUDIO_OpenDevice(_THIS, void *handle, const char *devname, int iscapture)
 193 {
 194- const int flags = iscapture ? OPEN_FLAGS_INPUT : OPEN_FLAGS_OUTPUT;
42 SDL_AudioFormat format = 0; 195 SDL_AudioFormat format = 0;
43 audio_info_t info; 196 audio_info_t info;
44- audio_prinfo *prinfo = iscapture ? &info.play : &info.record; 197- audio_prinfo *prinfo = iscapture ? &info.play : &info.record;
45+ struct audio_prinfo *prinfo = iscapture ? &info.record : &info.play; 198+ struct audio_prinfo *prinfo = iscapture ? &info.record : &info.play;
46  199
47 /* We don't care what the devname is...we'll try to open anything. */ 200 /* We don't care what the devname is...we'll try to open anything. */
48 /* ...but default to first name in the list... */ 201 /* ...but default to first name in the list... */
49@@ -366,6 +362,7 @@ NETBSDAUDIO_OpenDevice(_THIS, void *hand 202@@ -294,25 +226,16 @@ NETBSDAUDIO_OpenDevice(_THIS, void *hand
 203 SDL_zerop(this->hidden);
 204
 205 /* Open the audio device */
 206- this->hidden->audio_fd = open(devname, flags, 0);
 207+ this->hidden->audio_fd = open(devname, iscapture ? O_RDONLY : O_WRONLY);
 208 if (this->hidden->audio_fd < 0) {
 209 return SDL_SetError("Couldn't open %s: %s", devname, strerror(errno));
 210 }
 211
 212 AUDIO_INITINFO(&info);
 213
 214- /* Calculate the final parameters for this audio specification */
 215- SDL_CalculateAudioSpec(&this->spec);
 216-
 217- /* Set to play mode */
 218- info.mode = iscapture ? AUMODE_RECORD : AUMODE_PLAY;
 219- if (ioctl(this->hidden->audio_fd, AUDIO_SETINFO, &info) < 0) {
 220- return SDL_SetError("Couldn't put device into play mode");
 221- }
 222+ prinfo->encoding = AUDIO_ENCODING_NONE;
 223
 224- AUDIO_INITINFO(&info);
 225- for (format = SDL_FirstAudioFormat(this->spec.format);
 226- format; format = SDL_NextAudioFormat()) {
 227+ for (format = SDL_FirstAudioFormat(this->spec.format); format;) {
 228 switch (format) {
 229 case AUDIO_U8:
 230 prinfo->encoding = AUDIO_ENCODING_ULINEAR;
 231@@ -338,34 +261,33 @@ NETBSDAUDIO_OpenDevice(_THIS, void *hand
 232 prinfo->encoding = AUDIO_ENCODING_ULINEAR_BE;
 233 prinfo->precision = 16;
 234 break;
 235- default:
 236- continue;
 237 }
 238-
 239- if (ioctl(this->hidden->audio_fd, AUDIO_SETINFO, &info) == 0) {
 240+ if (prinfo->encoding != AUDIO_ENCODING_NONE) {
 241 break;
 242 }
 243+ format = SDL_NextAudioFormat();
 244 }
 245
 246- if (!format) {
 247+ if (prinfo->encoding == AUDIO_ENCODING_NONE) {
 248 return SDL_SetError("No supported encoding for 0x%x", this->spec.format);
 249 }
 250
 251 this->spec.format = format;
 252
 253- AUDIO_INITINFO(&info);
 254- prinfo->channels = this->spec.channels;
 255- if (ioctl(this->hidden->audio_fd, AUDIO_SETINFO, &info) == -1) {
 256- this->spec.channels = 1;
 257- }
 258- AUDIO_INITINFO(&info);
 259- prinfo->sample_rate = this->spec.freq;
 260+ /* Calculate spec parameters based on our chosen format */
 261+ SDL_CalculateAudioSpec(&this->spec);
 262+
 263+ info.mode = iscapture ? AUMODE_RECORD : AUMODE_PLAY;
 264 info.blocksize = this->spec.size;
 265 info.hiwat = 5;
 266 info.lowat = 3;
 267+ prinfo->sample_rate = this->spec.freq;
 268+ prinfo->channels = this->spec.channels;
50 (void) ioctl(this->hidden->audio_fd, AUDIO_SETINFO, &info); 269 (void) ioctl(this->hidden->audio_fd, AUDIO_SETINFO, &info);
 270+
51 (void) ioctl(this->hidden->audio_fd, AUDIO_GETINFO, &info); 271 (void) ioctl(this->hidden->audio_fd, AUDIO_GETINFO, &info);
52 this->spec.freq = prinfo->sample_rate; 272 this->spec.freq = prinfo->sample_rate;
53+ this->spec.size = info.blocksize; 273+ this->spec.channels = prinfo->channels;
54  274
55 if (!iscapture) { 275 if (!iscapture) {
56 /* Allocate mixing buffer */ 276 /* Allocate mixing buffer */
 277@@ -390,7 +312,6 @@ NETBSDAUDIO_Init(SDL_AudioDriverImpl * i
 278 impl->DetectDevices = NETBSDAUDIO_DetectDevices;
 279 impl->OpenDevice = NETBSDAUDIO_OpenDevice;
 280 impl->PlayDevice = NETBSDAUDIO_PlayDevice;
 281- impl->WaitDevice = NETBSDAUDIO_WaitDevice;
 282 impl->GetDeviceBuf = NETBSDAUDIO_GetDeviceBuf;
 283 impl->CloseDevice = NETBSDAUDIO_CloseDevice;
 284 impl->CaptureFromDevice = NETBSDAUDIO_CaptureFromDevice;