NetBSD-Bugs archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
Re: lib/46611
The following reply was made to PR lib/46611; it has been noted by GNATS.
From: Nat Sloss <nathanialsloss%yahoo.com.au@localhost>
To: "gnats-bugs" <gnats-bugs%netbsd.org@localhost>
Cc: Thomas Klausner <wiz%netbsd.org@localhost>
Subject: Re: lib/46611
Date: Sat, 19 Apr 2014 12:32:28 +1000
Here is a better patch as it also supports SNDCTL_DSP_SILENCE and adds
additional missing defines (3 of them):
SNDCTL_DSP_SILENCE and SNDCTL_DSP_SKIP return EINVAL for now as they are
supposed to manipulate kernel sound buffers directly and I'm as yet to think
of
a way of emulating this. On the packages I have tried so far retuning EINVAL
seems OK.
Index: libossaudio/soundcard.h
===================================================================
RCS file: /cvsroot/src/lib/libossaudio/soundcard.h,v
retrieving revision 1.22
diff -u -r1.22 soundcard.h
--- libossaudio/soundcard.h 5 May 2012 15:57:45 -0000 1.22
+++ libossaudio/soundcard.h 19 Apr 2014 02:02:18 -0000
@@ -39,7 +39,9 @@
#ifndef _SOUNDCARD_H_
#define _SOUNDCARD_H_
-#define SOUND_VERSION 0x030001
+#ifndef SOUND_VERSION
+#define SOUND_VERSION 0x030001
+#endif
#define SNDCTL_DSP_RESET _IO ('P', 0)
#define SNDCTL_DSP_SYNC _IO ('P', 1)
@@ -60,6 +62,11 @@
#define AFMT_U16_BE 0x00000100
#define AFMT_MPEG 0x00000200
#define AFMT_AC3 0x00000400
+#define AFMT_S24_LE 0x00000800
+#define AFMT_S24_BE 0x00001000
+#define AFMT_S32_LE 0x00002000
+#define AFMT_S32_BE 0x00004000
+#define AFMT_S32_NE 0x00008000
#define SNDCTL_DSP_SAMPLESIZE SNDCTL_DSP_SETFMT
#define SOUND_PCM_READ_BITS _IOR ('P', 5, int)
#define SNDCTL_DSP_CHANNELS _IOWR('P', 6, int)
@@ -82,6 +89,10 @@
# define DSP_CAP_COPROC 0x00000800
# define DSP_CAP_TRIGGER 0x00001000
# define DSP_CAP_MMAP 0x00002000
+# define PCM_CAP_INPUT 0x00004000
+# define PCM_CAP_OUTPUT 0x00008000
+# define PCM_CAP_MODEM 0x00010000
+# define PCM_CAP_HIDDEN 0x00020000
#define SNDCTL_DSP_GETTRIGGER _IOR ('P', 16, int)
#define SNDCTL_DSP_SETTRIGGER _IOW ('P', 16, int)
# define PCM_ENABLE_INPUT 0x00000001
@@ -291,6 +302,77 @@
int size;
} buffmem_desc;
+/* Some OSSv4 calls. */
+
+#define OSS_DEVNODE_SIZE 32
+#define OSS_LABEL_SIZE 16
+#define OSS_LONGNAME_SIZE 64
+#define OSS_MAX_AUDIO_DEVS 64
+
+#define SNDCTL_SYSINFO _IOR ('P',24, struct
oss_sysinfo)
+#define SNDCTL_AUDIOINFO _IOWR ('P',25, struct oss_audioinfo)
+#define SNDCTL_ENGINEINFO _IOWR ('P',26, struct oss_audioinfo)
+#define SNDCTL_DSP_GETPLAYVOL _IOR ('P',27, uint)
+#define SNDCTL_DSP_SETPLAYVOL _IOW ('P',28, uint)
+#define SNDCTL_DSP_GETRECVOL _IOR ('P',29, uint)
+#define SNDCTL_DSP_SETRECVOL _IOW ('P',30, uint)
+#define SNDCTL_DSP_SKIP _IO ('P',31)
+#define SNDCTL_DSP_SILENCE _IO ('P',32)
+
+typedef struct oss_sysinfo {
+ char product[32];
+ char version[32];
+ int versionnum;
+ char options[128]; /* Future use */
+ int numaudios;
+ int openedaudio[8]; /* Obsolete */
+ int numsynths; /* Obsolete */
+ int nummidis;
+ int numtimers;
+ int nummixers;
+ int openedmidi[8];
+ int numcards;
+ int numaudioengines;
+ char license[16];
+ char revision_info[256]; /* Internal Use */
+ int filler[172]; /* For expansion */
+} oss_sysinfo;
+
+typedef struct oss_audioinfo {
+ int dev; /* Set by caller */
+ char name[OSS_LONGNAME_SIZE];
+ int busy;
+ int pid;
+ int caps;
+ int iformats;
+ int oformats;
+ int magic; /* Unused */
+ char cmd[OSS_LONGNAME_SIZE];
+ int card_number;
+ int port_number;
+ int mixer_dev;
+ int legacy_device; /* Obsolete */
+ int enabled;
+ int flags; /* Reserved */
+ int min_rate;
+ int max_rate;
+ int min_channels;
+ int max_channels;
+ int binding; /* Reserved */
+ int rate_source;
+ char handle[32];
+#define OSS_MAX_SAMPLE_RATES 20
+ int nrates;
+ int rates[OSS_MAX_SAMPLE_RATES];
+ char song_name[OSS_LONGNAME_SIZE];
+ char label[OSS_LABEL_SIZE];
+ int latency; /* In usecs -1 = unknown */
+ char devnode[OSS_DEVNODE_SIZE];
+ int next_play_engine;
+ int next_rec_engine;
+ int filler[184]; /* For expansion */
+} oss_audioinfo;
+
#define ioctl _oss_ioctl
/*
* If we already included <sys/ioctl.h>, then we define our own prototype,
@@ -302,6 +384,15 @@
#else
__BEGIN_DECLS
int _oss_ioctl(int, unsigned long, ...);
+#include <fcntl.h>
+#include <unistd.h>
+
+#ifdef OSS_OPEN_OVERLOAD
+#define open(x,y,...) _oss_open(x,y,##__VA_ARGS__)
+#define close(x) _oss_close(x)
+int _oss_open(char *path, int flags, ...);
+int _oss_close(int fd);
+#endif
__END_DECLS
#endif
Index: libossaudio/ossaudio.c
===================================================================
RCS file: /cvsroot/src/lib/libossaudio/ossaudio.c,v
retrieving revision 1.28
diff -u -r1.28 ossaudio.c
--- libossaudio/ossaudio.c 5 May 2012 15:57:45 -0000 1.28
+++ libossaudio/ossaudio.c 19 Apr 2014 02:03:49 -0000
@@ -44,6 +44,9 @@
#include <sys/audioio.h>
#include <sys/stat.h>
#include <errno.h>
+#include <fcntl.h>
+#include <stdio.h>
+#include <unistd.h>
#include <stdarg.h>
#include "soundcard.h"
@@ -93,9 +96,17 @@
struct audio_buf_info bufinfo;
struct count_info cntinfo;
struct audio_encoding tmpenc;
+ struct oss_sysinfo tmpsysinfo;
+ struct oss_audioinfo *tmpaudioinfo;
+ audio_device_t tmpaudiodev;
+ struct stat tmpstat;
+ dev_t devno;
+ char version[32] = "4.01";
+ char license[16] = "NetBSD";
u_int u;
int idat, idata;
int retval;
+ int i;
idat = 0;
@@ -316,13 +327,21 @@
idat |= AFMT_S8;
break;
case AUDIO_ENCODING_SLINEAR_LE:
- if (tmpenc.precision == 16)
+ if (tmpenc.precision == 32)
+ idat |= AFMT_S32_LE;
+ else if (tmpenc.precision == 24)
+ idat |= AFMT_S24_LE;
+ else if (tmpenc.precision == 16)
idat |= AFMT_S16_LE;
else
idat |= AFMT_S8;
break;
case AUDIO_ENCODING_SLINEAR_BE:
- if (tmpenc.precision == 16)
+ if (tmpenc.precision == 32)
+ idat |= AFMT_S32_BE;
+ else if (tmpenc.precision == 24)
+ idat |= AFMT_S24_BE;
+ else if (tmpenc.precision == 16)
idat |= AFMT_S16_BE;
else
idat |= AFMT_S8;
@@ -445,6 +464,130 @@
cntinfo.ptr = tmpoffs.offset;
*(struct count_info *)argp = cntinfo;
break;
+ case SNDCTL_SYSINFO:
+ strncpy(tmpsysinfo.product, "OSS/NetBSD", 31);
+ tmpsysinfo.product[31] = 0;
+ strncpy(tmpsysinfo.version, version, 31);
+ tmpsysinfo.version[31] = 0;
+ strncpy(tmpsysinfo.license, license, 15);
+ tmpsysinfo.license[15] = 0;
+ tmpsysinfo.versionnum = SOUND_VERSION;
+ memset(tmpsysinfo.options, 0, 8);
+ tmpsysinfo.numaudios = OSS_MAX_AUDIO_DEVS;
+ tmpsysinfo.numaudioengines = 1;
+ memset(tmpsysinfo.openedaudio, 0, 8);
+ tmpsysinfo.numsynths = 1;
+ tmpsysinfo.nummidis = -1;
+ tmpsysinfo.numtimers = -1;
+ tmpsysinfo.nummixers = 1;
+ tmpsysinfo.numcards = 1;
+ memset(tmpsysinfo.openedmidi, 0, 8);
+ *(struct oss_sysinfo *)argp = tmpsysinfo;
+ break;
+ case SNDCTL_ENGINEINFO:
+ case SNDCTL_AUDIOINFO:
+ devno = 0;
+ tmpaudioinfo = (struct oss_audioinfo*)argp;
+ if (tmpaudioinfo == NULL)
+ return EINVAL;
+ if (tmpaudioinfo->dev < 0) {
+ fstat(fd, &tmpstat);
+ if ((tmpstat.st_rdev & 0xff00) == 0x2a00)
+ devno = tmpstat.st_rdev & 0xff;
+ if (devno >= 0x80)
+ tmpaudioinfo->dev = devno & 0x7f;
+ }
+ if (tmpaudioinfo->dev < 0)
+ tmpaudioinfo->dev = 0;
+
+ snprintf(tmpaudioinfo->devnode, OSS_DEVNODE_SIZE,
+ "/dev/audio%d", tmpaudioinfo->dev);
+
+ retval = ioctl(fd, AUDIO_GETDEV, &tmpaudiodev);
+ if (retval < 0)
+ return retval;
+ retval = ioctl(fd, AUDIO_GETINFO, &tmpinfo);
+ if (retval < 0)
+ return retval;
+ retval = ioctl(fd, AUDIO_GETPROPS, &idata);
+ if (retval < 0)
+ return retval;
+ idat = DSP_CAP_TRIGGER; /* pretend we have trigger */
+ if (idata & AUDIO_PROP_FULLDUPLEX)
+ idat |= DSP_CAP_DUPLEX;
+ if (idata & AUDIO_PROP_MMAP)
+ idat |= DSP_CAP_MMAP;
+ idat = PCM_CAP_INPUT | PCM_CAP_OUTPUT;
+ strncpy(tmpaudioinfo->name, tmpaudiodev.name, 64);
+ tmpaudioinfo->name[63] = 0;
+ tmpaudioinfo->busy = tmpinfo.play.open;
+ tmpaudioinfo->pid = -1;
+ tmpaudioinfo->caps = idat;
+ ioctl(fd, SNDCTL_DSP_GETFMTS, &tmpaudioinfo->iformats);
+ tmpaudioinfo->oformats = tmpaudioinfo->iformats;
+ tmpaudioinfo->magic = -1;
+ memset(tmpaudioinfo->cmd, 0, 64);
+ tmpaudioinfo->card_number = -1;
+ memset(tmpaudioinfo->song_name, 0, 64);
+ memset(tmpaudioinfo->label, 0, 16);
+ tmpaudioinfo->port_number = tmpinfo.play.port;
+ tmpaudioinfo->mixer_dev = tmpaudioinfo->dev;
+ tmpaudioinfo->legacy_device = -1;
+ tmpaudioinfo->enabled = 1;
+ tmpaudioinfo->flags = -1;
+ tmpaudioinfo->min_rate = tmpinfo.play.sample_rate;
+ tmpaudioinfo->max_rate = tmpinfo.play.sample_rate;
+ tmpaudioinfo->nrates = 2;
+ for (i = 0; i < tmpaudioinfo->nrates; i++)
+ tmpaudioinfo->rates[i] = tmpinfo.play.sample_rate;
+ tmpaudioinfo->min_channels = tmpinfo.play.channels;
+ tmpaudioinfo->max_channels = tmpinfo.play.channels;
+ tmpaudioinfo->binding = -1;
+ tmpaudioinfo->rate_source = -1;
+ memset(tmpaudioinfo->handle, 0, 16);
+ tmpaudioinfo->next_play_engine = 0;
+ tmpaudioinfo->next_rec_engine = 0;
+ argp = tmpaudioinfo;
+ break;
+ case SNDCTL_DSP_GETPLAYVOL:
+ retval = ioctl(fd, AUDIO_GETBUFINFO, &tmpinfo);
+ if (retval < 0)
+ return retval;
+ *(uint *)argp = tmpinfo.play.gain;
+ break;
+ case SNDCTL_DSP_SETPLAYVOL:
+ retval = ioctl(fd, AUDIO_GETBUFINFO, &tmpinfo);
+ if (retval < 0)
+ return retval;
+ if (*(uint *)argp > 255)
+ tmpinfo.play.gain = 255;
+ else
+ tmpinfo.play.gain = *(uint *)argp;
+ retval = ioctl(fd, AUDIO_SETINFO, &tmpinfo);
+ if (retval < 0)
+ return retval;
+ break;
+ case SNDCTL_DSP_GETRECVOL:
+ retval = ioctl(fd, AUDIO_GETBUFINFO, &tmpinfo);
+ if (retval < 0)
+ return retval;
+ *(uint *)argp = tmpinfo.record.gain;
+ break;
+ case SNDCTL_DSP_SETRECVOL:
+ retval = ioctl(fd, AUDIO_GETBUFINFO, &tmpinfo);
+ if (retval < 0)
+ return retval;
+ if (*(uint *)argp > 255)
+ tmpinfo.record.gain = 255;
+ else
+ tmpinfo.record.gain = *(uint *)argp;
+ retval = ioctl(fd, AUDIO_SETINFO, &tmpinfo);
+ if (retval < 0)
+ return retval;
+ break;
+ case SNDCTL_DSP_SKIP:
+ case SNDCTL_DSP_SILENCE:
+ return EINVAL;
case SNDCTL_DSP_SETDUPLEX:
idat = 1;
retval = ioctl(fd, AUDIO_SETFD, &idat);
This allows wip/vlc21 to compile and run with oss but you have to specify the
audio device ie: vlc -Aoss -oss-audio-device=/dev/audio somefile
Regards,
Nat.
Home |
Main Index |
Thread Index |
Old Index