799 lines
23 KiB
Groff
799 lines
23 KiB
Groff
.\" $NetBSD: audio.4,v 1.90 2019/05/09 09:35:29 wiz Exp $
|
|
.\"
|
|
.\" Copyright (c) 1996 The NetBSD Foundation, Inc.
|
|
.\" All rights reserved.
|
|
.\"
|
|
.\" This code is derived from software contributed to The NetBSD Foundation
|
|
.\" by John T. Kohl.
|
|
.\"
|
|
.\" Redistribution and use in source and binary forms, with or without
|
|
.\" modification, are permitted provided that the following conditions
|
|
.\" are met:
|
|
.\" 1. Redistributions of source code must retain the above copyright
|
|
.\" notice, this list of conditions and the following disclaimer.
|
|
.\" 2. Redistributions in binary form must reproduce the above copyright
|
|
.\" notice, this list of conditions and the following disclaimer in the
|
|
.\" documentation and/or other materials provided with the distribution.
|
|
.\"
|
|
.\" THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
|
|
.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
|
|
.\" TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
|
.\" PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
|
|
.\" BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
|
.\" CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
|
.\" SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
|
.\" INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
|
.\" CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
|
.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
|
.\" POSSIBILITY OF SUCH DAMAGE.
|
|
.\"
|
|
.Dd May 8, 2019
|
|
.Dt AUDIO 4
|
|
.Os
|
|
.Sh NAME
|
|
.Nm audio
|
|
.Nd device-independent audio driver layer
|
|
.Sh SYNOPSIS
|
|
.In sys/audioio.h
|
|
.Sh DESCRIPTION
|
|
The
|
|
.Nm
|
|
driver provides support for various audio peripherals.
|
|
It provides a uniform programming interface layer above different
|
|
underlying audio hardware drivers.
|
|
The audio layer provides full-duplex operation if the
|
|
underlying hardware configuration supports it.
|
|
.Pp
|
|
There are four device files available for audio operation:
|
|
.Pa /dev/audio ,
|
|
.Pa /dev/sound ,
|
|
.Pa /dev/audioctl ,
|
|
and
|
|
.Pa /dev/mixer .
|
|
.Pp
|
|
.Pa /dev/audio
|
|
and
|
|
.Pa /dev/sound
|
|
are used for recording or playback of digital samples.
|
|
.Pp
|
|
.Pa /dev/mixer
|
|
is used to manipulate volume, recording source, or other audio mixer
|
|
functions.
|
|
.Pp
|
|
.Pa /dev/audioctl
|
|
accepts the same
|
|
.Xr ioctl 2
|
|
operations as
|
|
.Pa /dev/sound ,
|
|
but no other operations.
|
|
It can be opened at any time and can be used to manipulate the
|
|
audio device while it is in use.
|
|
.Sh SAMPLING DEVICES
|
|
When
|
|
.Pa /dev/audio
|
|
is opened, it automatically sets the track to manipulate
|
|
monaural 8-bit mu-law 8000Hz.
|
|
When
|
|
.Pa /dev/sound
|
|
is opened, it maintains the audio format and pause/unpause
|
|
state of the most recently opened track.
|
|
In all other respects
|
|
.Pa /dev/audio
|
|
and
|
|
.Pa /dev/sound
|
|
are identical.
|
|
.Pp
|
|
On a full-duplex device, reads and writes may operate concurrently
|
|
without interference.
|
|
If a full-duplex capable audio device is opened for both reading and writing
|
|
it will start in play mode but not start in record mode.
|
|
.Pp
|
|
On a half-duplex device, if there are any recording descriptors already,
|
|
opening with write mode will fail.
|
|
Similarly, if there are any playback descriptors already,
|
|
opening with read mode will fail.
|
|
If both playback and recording are requested on a half-duplex device,
|
|
it will be treated as playback mode.
|
|
.Pp
|
|
On either type of device, opening with write mode will start in playback mode,
|
|
opening with read mode will start in recording mode.
|
|
.Pp
|
|
If the playback mode is paused then silence is
|
|
played instead of the provided samples, and if recording is paused then
|
|
the process blocks in
|
|
.Xr read 2
|
|
until recording is unpaused.
|
|
.Pp
|
|
If a writing process does not call
|
|
.Xr write 2
|
|
frequently enough to provide samples at the pace the hardware
|
|
consumes them silence is inserted.
|
|
If a reading process does not call
|
|
.Xr read 2
|
|
frequently enough, it will simply miss samples.
|
|
.Pp
|
|
The audio driver supports track multiplexing.
|
|
All sampling devices can be opened at any time without interference.
|
|
For playback, all tracks opened simultaneously are mixed,
|
|
even if their specified format is different.
|
|
For recording, recorded data is distributed to all opened tracks,
|
|
even if their specified format is different.
|
|
To achieve this, the audio driver has a small efficient encoding converter,
|
|
a channel mixer, and a frequency converter.
|
|
The frequency conversion adapts the simplest way
|
|
(interpolation method for upward, and simple thinning method for downward)
|
|
due to restriction in kernel resources and processing time.
|
|
It will work well in most case but don't expect excessive quality.
|
|
.Pp
|
|
The audio device is normally accessed with
|
|
.Xr read 2
|
|
or
|
|
.Xr write 2
|
|
calls, but it can also be mapped into user memory with
|
|
.Xr mmap 2 .
|
|
Once the device has been mapped it can no longer be accessed
|
|
by read or write; all access is by reading and writing to
|
|
the mapped memory.
|
|
The mmap'ped buffer appears as a block of memory of size
|
|
.Va buffersize
|
|
(as available via
|
|
.Dv AUDIO_GETINFO
|
|
or
|
|
.Dv AUDIO_GETBUFINFO ) .
|
|
The audio driver will continuously move data from this buffer
|
|
from/to the mixing buffer, wrapping around at the end of the buffer.
|
|
To find out where the hardware is currently accessing data in the buffer the
|
|
.Dv AUDIO_GETIOFFS
|
|
and
|
|
.Dv AUDIO_GETOOFFS
|
|
calls can be used.
|
|
Note that
|
|
.Xr mmap 2
|
|
no longer maps hardware buffers directly.
|
|
Now it is achieved by emulation so don't expect any improvements excessively
|
|
rather than normal
|
|
.Xr write 2 .
|
|
For historical reasons, only encodings that are not set
|
|
.Dv AUDIO_ENCODINGFLAG_EMULATED
|
|
are able to
|
|
.Xr mmap 2 .
|
|
.Pp
|
|
The audio device, like most devices, can be used in
|
|
.Xr select 2 ,
|
|
can be set in non-blocking mode and can be set (with a
|
|
.Dv FIOASYNC
|
|
ioctl) to send a
|
|
.Dv SIGIO
|
|
when I/O is possible.
|
|
The mixer device can be set to generate a
|
|
.Dv SIGIO
|
|
whenever a mixer value is changed.
|
|
.Pp
|
|
The following
|
|
.Xr ioctl 2
|
|
commands are supported on the sample devices:
|
|
.Bl -tag -width indent
|
|
.It Dv AUDIO_FLUSH
|
|
This command stops all playback and recording, clears all queued
|
|
buffers, resets error counters on this track,
|
|
and restarts recording and playback as
|
|
appropriate for the current sampling mode.
|
|
.It Dv AUDIO_PERROR (int)
|
|
.It Dv AUDIO_RERROR (int)
|
|
This command fetches the count of dropped output (input)
|
|
bytes into its integer argument.
|
|
There is no information regarding when in the sample stream
|
|
they were dropped.
|
|
.It Dv AUDIO_WSEEK (u_long)
|
|
This command fetches the count of bytes that are queued ahead of the
|
|
first sample in the most recent sample block written into its integer argument.
|
|
.It Dv AUDIO_DRAIN
|
|
This command suspends the calling process until all queued playback
|
|
samples have been played.
|
|
.It Dv AUDIO_GETDEV (audio_device_t)
|
|
This command fetches the current hardware device information into the
|
|
.Vt audio_device_t
|
|
argument.
|
|
.Bd -literal
|
|
typedef struct audio_device {
|
|
char name[MAX_AUDIO_DEV_LEN];
|
|
char version[MAX_AUDIO_DEV_LEN];
|
|
char config[MAX_AUDIO_DEV_LEN];
|
|
} audio_device_t;
|
|
.Ed
|
|
.It Dv AUDIO_GETENC (audio_encoding_t)
|
|
This command is used iteratively to fetch sample encoding names and
|
|
format ids into the input/output audio_encoding_t argument.
|
|
The encoding returned by the command is user accessible encoding and
|
|
is not hardware supported encoding.
|
|
.Bd -literal
|
|
typedef struct audio_encoding {
|
|
int index; /* input: nth encoding */
|
|
char name[MAX_AUDIO_DEV_LEN]; /* name of encoding */
|
|
int encoding; /* value for encoding parameter */
|
|
int precision; /* value for precision parameter */
|
|
int flags;
|
|
#define AUDIO_ENCODINGFLAG_EMULATED 1 /* software emulation mode */
|
|
} audio_encoding_t;
|
|
.Ed
|
|
.Pp
|
|
To query
|
|
all the supported encodings, start with an index field of 0 and
|
|
continue with successive encodings (1, 2, ...) until the command returns
|
|
an error.
|
|
.It Dv AUDIO_GETFD (int)
|
|
This command is obsolete.
|
|
.It Dv AUDIO_SETFD (int)
|
|
This command is obsolete.
|
|
.It Dv AUDIO_GETPROPS (int)
|
|
This command gets a bit set of hardware properties.
|
|
If the hardware
|
|
has a certain property the corresponding bit is set, otherwise it is not.
|
|
The properties can have the following values:
|
|
.Pp
|
|
.Bl -tag -width AUDIO_PROP_INDEPENDENT -compact
|
|
.It Dv AUDIO_PROP_FULLDUPLEX
|
|
the device admits full duplex operation.
|
|
.It Dv AUDIO_PROP_MMAP
|
|
the device can be used with
|
|
.Xr mmap 2 .
|
|
.It Dv AUDIO_PROP_INDEPENDENT
|
|
the device can set the playing and recording encoding parameters
|
|
independently.
|
|
.It Dv AUDIO_PROP_PLAYBACK
|
|
the device is capable of audio playback.
|
|
.It Dv AUDIO_PROP_CAPTURE
|
|
the device is capable of audio capture.
|
|
.El
|
|
.It Dv AUDIO_GETIOFFS (audio_offset_t)
|
|
.It Dv AUDIO_GETOOFFS (audio_offset_t)
|
|
This command fetches the current offset in the input(output) buffer where
|
|
the track mixer will be putting(getting) data.
|
|
It mostly useful when the device
|
|
buffer is available in user space via the
|
|
.Xr mmap 2
|
|
call.
|
|
The information is returned in the
|
|
.Vt audio_offset_t
|
|
structure.
|
|
.Bd -literal
|
|
typedef struct audio_offset {
|
|
u_int samples; /* Total number of bytes transferred */
|
|
u_int deltablks; /* Blocks transferred since last checked */
|
|
u_int offset; /* Physical transfer offset in buffer */
|
|
} audio_offset_t;
|
|
.Ed
|
|
.It Dv AUDIO_GETINFO (audio_info_t)
|
|
.It Dv AUDIO_GETBUFINFO (audio_info_t)
|
|
.It Dv AUDIO_SETINFO (audio_info_t)
|
|
Get or set audio information as encoded in the audio_info structure.
|
|
For historical reasons, the audio_info structure has three different
|
|
layer's parameters: track, track mixer and hardware rich mixer.
|
|
.Bd -literal
|
|
typedef struct audio_info {
|
|
struct audio_prinfo play; /* info for play (output) side */
|
|
struct audio_prinfo record; /* info for record (input) side */
|
|
u_int monitor_gain; /* input to output mix [HWmixer] */
|
|
/* BSD extensions */
|
|
u_int blocksize; /* read/write block size [track] */
|
|
u_int hiwat; /* output high water mark [track] */
|
|
u_int lowat; /* output low water mark [track] */
|
|
u_int _ispare1;
|
|
u_int mode; /* current operation mode [track] */
|
|
#define AUMODE_PLAY 0x01
|
|
#define AUMODE_RECORD 0x02
|
|
#define AUMODE_PLAY_ALL 0x04 /* Not used anymore */
|
|
} audio_info_t;
|
|
.Ed
|
|
.Pp
|
|
When setting the current state with
|
|
.Dv AUDIO_SETINFO ,
|
|
the audio_info structure should first be initialized with
|
|
.Li AUDIO_INITINFO(&info)
|
|
and then the particular values to be changed should be set.
|
|
This allows the audio driver to only set those things that you wish
|
|
to change and eliminates the need to query the device with
|
|
.Dv AUDIO_GETINFO
|
|
or
|
|
.Dv AUDIO_GETBUFINFO
|
|
first.
|
|
.Pp
|
|
The
|
|
.Va mode
|
|
field indicates current operation mode, either one of
|
|
.Dv AUMODE_PLAY
|
|
or
|
|
.Dv AUMODE_RECORD .
|
|
These two flags can not be changed once this descriptor is opened.
|
|
For playback mode, the obsolete
|
|
.Dv AUMODE_PLAY_ALL
|
|
flag can be set but has no effect.
|
|
.Pp
|
|
.Va hiwat
|
|
and
|
|
.Va lowat
|
|
are used to control write behavior.
|
|
Writes to the audio devices will queue up blocks until the high-water
|
|
mark is reached, at which point any more write calls will block
|
|
until the queue is drained to the low-water mark.
|
|
.Va hiwat
|
|
and
|
|
.Va lowat
|
|
set those high- and low-water marks (in audio blocks).
|
|
The default for
|
|
.Va hiwat
|
|
is the maximum value and for
|
|
.Va lowat
|
|
75% of
|
|
.Va hiwat .
|
|
.Pp
|
|
.Va blocksize
|
|
sets the current audio blocksize.
|
|
The generic audio driver layer and the hardware driver have the
|
|
opportunity to adjust this block size to get it within
|
|
implementation-required limits.
|
|
Normally the
|
|
.Va blocksize
|
|
is calculated to correspond to 40ms
|
|
(for some hardware, this value may be different due to
|
|
the hardware restrictions)
|
|
of sound and it is recalculated
|
|
when the encoding parameters change.
|
|
If the descriptor is opened for read only,
|
|
.Va blocksize
|
|
indicates the blocksize for the recording track.
|
|
Otherwise,
|
|
.Va blocksize
|
|
indicates the blocksize for the playback track.
|
|
.Bd -literal
|
|
struct audio_prinfo {
|
|
u_int sample_rate; /* sample rate in samples/s [track] */
|
|
u_int channels; /* number of channels, usually 1 or 2 [track] */
|
|
u_int precision; /* number of bits/sample [track] */
|
|
u_int encoding; /* data encoding (AUDIO_ENCODING_* below) [track] */
|
|
u_int gain; /* volume level [HWmixer] */
|
|
u_int port; /* selected I/O port [HWmixer] */
|
|
u_long seek; /* BSD extension [track] */
|
|
u_int avail_ports; /* available I/O ports [HWmixer] */
|
|
u_int buffer_size; /* total size audio buffer [track] */
|
|
u_int _ispare[1];
|
|
u_int samples; /* number of samples [track] */
|
|
u_int eof; /* End Of File (zero-size writes) counter [track] */
|
|
u_char pause; /* non-zero if paused, zero to resume [track] */
|
|
u_char error; /* non-zero if underflow/overflow occurred [track] */
|
|
u_char waiting; /* non-zero if another process hangs in open [track] */
|
|
u_char balance; /* stereo channel balance [HWmixer] */
|
|
u_char cspare[2];
|
|
u_char open; /* non-zero if currently open [trackmixer] */
|
|
u_char active; /* non-zero if I/O is currently active [trackmixer] */
|
|
};
|
|
.Ed
|
|
.Pp
|
|
Note: many hardware audio drivers require identical playback and
|
|
recording sample rates, sample encodings, and channel counts.
|
|
The playing information is always set last and will prevail on such hardware.
|
|
If the hardware can handle different settings the
|
|
.Dv AUDIO_PROP_INDEPENDENT
|
|
property is set.
|
|
.Pp
|
|
The encoding parameter can have the following values:
|
|
.Pp
|
|
.Bl -tag -width AUDIO_ENCODING_SLINEAR_BE -compact
|
|
.It Dv AUDIO_ENCODING_ULAW
|
|
mu-law encoding, 8 bits/sample
|
|
.It Dv AUDIO_ENCODING_ALAW
|
|
A-law encoding, 8 bits/sample
|
|
.It Dv AUDIO_ENCODING_SLINEAR
|
|
two's complement signed linear encoding with the platform byte order
|
|
.It Dv AUDIO_ENCODING_ULINEAR
|
|
unsigned linear encoding
|
|
with the platform byte order
|
|
.It Dv AUDIO_ENCODING_ADPCM
|
|
ADPCM encoding, 8 bits/sample
|
|
.It Dv AUDIO_ENCODING_SLINEAR_LE
|
|
two's complement signed linear encoding with little endian byte order
|
|
.It Dv AUDIO_ENCODING_SLINEAR_BE
|
|
two's complement signed linear encoding with big endian byte order
|
|
.It Dv AUDIO_ENCODING_ULINEAR_LE
|
|
unsigned linear encoding with little endian byte order
|
|
.It Dv AUDIO_ENCODING_ULINEAR_BE
|
|
unsigned linear encoding with big endian byte order
|
|
.It Dv AUDIO_ENCODING_AC3
|
|
Dolby Digital AC3
|
|
.El
|
|
.Pp
|
|
Regardless of formats supported by underlying driver, the
|
|
.Nm
|
|
driver accepts the following formats.
|
|
.Va encoding
|
|
and
|
|
.Va precision
|
|
are one of the values obtained by
|
|
.Dv AUDIO_GETENC .
|
|
.Va channels
|
|
ranges from 1 to 12.
|
|
.Va frequency
|
|
ranges from 1000Hz to 192000Hz.
|
|
.Pp
|
|
The
|
|
.Va gain ,
|
|
.Va port
|
|
and
|
|
.Va balance
|
|
settings provide simple shortcuts to the richer mixer
|
|
interface described below and are not obtained by
|
|
.Dv AUDIO_GETBUFINFO .
|
|
The gain should be in the range
|
|
.Bq Dv AUDIO_MIN_GAIN , Dv AUDIO_MAX_GAIN
|
|
and the balance in the range
|
|
.Bq Dv AUDIO_LEFT_BALANCE , Dv AUDIO_RIGHT_BALANCE
|
|
with the normal setting at
|
|
.Dv AUDIO_MID_BALANCE .
|
|
.Pp
|
|
The input port should be a combination of:
|
|
.Pp
|
|
.Bl -tag -width AUDIO_MICROPHONE -compact
|
|
.It Dv AUDIO_MICROPHONE
|
|
to select microphone input.
|
|
.It Dv AUDIO_LINE_IN
|
|
to select line input.
|
|
.It Dv AUDIO_CD
|
|
to select CD input.
|
|
.El
|
|
.Pp
|
|
The output port should be a combination of:
|
|
.Pp
|
|
.Bl -tag -width AUDIO_HEADPHONE -compact
|
|
.It Dv AUDIO_SPEAKER
|
|
to select speaker output.
|
|
.It Dv AUDIO_HEADPHONE
|
|
to select headphone output.
|
|
.It Dv AUDIO_LINE_OUT
|
|
to select line output.
|
|
.El
|
|
.Pp
|
|
The available ports can be found in
|
|
.Va avail_ports
|
|
.Dv ( AUDIO_GETBUFINFO
|
|
only).
|
|
.Pp
|
|
.Va buffer_size
|
|
is the total size of the audio buffer.
|
|
The buffer size divided by the
|
|
.Va blocksize
|
|
gives the maximum value for
|
|
.Va hiwat .
|
|
Currently the
|
|
.Va buffer_size
|
|
can only be read and not set.
|
|
.Pp
|
|
The
|
|
.Va seek
|
|
and
|
|
.Va samples
|
|
fields are only used by
|
|
.Dv AUDIO_GETINFO
|
|
and
|
|
.Dv AUDIO_GETBUFINFO .
|
|
.Va seek
|
|
represents the count of
|
|
bytes pending;
|
|
.Va samples
|
|
represents the total number of bytes recorded or played, less those
|
|
that were dropped due to inadequate consumption/production rates.
|
|
.Pp
|
|
.Va pause
|
|
returns the current pause/unpause state for recording or playback.
|
|
For
|
|
.Dv AUDIO_SETINFO ,
|
|
if the pause value is specified it will either pause
|
|
or unpause the particular direction.
|
|
.It Dv AUDIO_QUERYFORMAT (audio_format_query_t)
|
|
This command enumerates formats supported by the hardware.
|
|
Similarly to
|
|
.Dv AUDIO_GETENC ,
|
|
to query all the supported formats,
|
|
start with an index field of 0 and continue with successive formats
|
|
(1, 2, ...) until the command returns an error.
|
|
.Bd -literal
|
|
typedef struct audio_format_query {
|
|
u_int index;
|
|
struct audio_format fmt;
|
|
} audio_format_query_t;
|
|
.Ed
|
|
.It Dv AUDIO_GETFORMAT (audio_info_t)
|
|
This command fetches the current hardware format.
|
|
Only the following members in audio_info_t are used.
|
|
Members which are not listed here or belong in invalid direction are
|
|
filled by \-1.
|
|
.Bl -bullet
|
|
.It
|
|
mode
|
|
.It
|
|
play.encoding
|
|
.It
|
|
play.precision
|
|
.It
|
|
play.channels
|
|
.It
|
|
play.sample_rate
|
|
.It
|
|
record.encoding
|
|
.It
|
|
record.precision
|
|
.It
|
|
record.channels
|
|
.It
|
|
record.sample_rate
|
|
.El
|
|
.Pp
|
|
.Va mode
|
|
indicates which direction is valid.
|
|
.It Dv AUDIO_SETFORMAT (audio_info_t)
|
|
This command sets the hardware format.
|
|
It will fail if there are any opened descriptors.
|
|
So obviously, it must be issued on
|
|
.Pa /dev/audioctl .
|
|
Similarly to
|
|
.Dv AUDIO_GETFORMAT ,
|
|
only above members in audio_info_t are used.
|
|
Members which is not listed or belong in invalid direction are ignored.
|
|
The parameters can be chosen from the choices obtained by
|
|
.Dv AUDIO_QUERYFORMAT .
|
|
.It Dv AUDIO_GETCHAN (int)
|
|
This command is obsolete.
|
|
.It Dv AUDIO_SETCHAN (int)
|
|
This command is obsolete.
|
|
.El
|
|
.Sh MIXER DEVICE
|
|
The mixer device,
|
|
.Pa /dev/mixer ,
|
|
may be manipulated with
|
|
.Xr ioctl 2
|
|
but does not support
|
|
.Xr read 2
|
|
or
|
|
.Xr write 2 .
|
|
It supports the following
|
|
.Xr ioctl 2
|
|
commands:
|
|
.Bl -tag -width indent
|
|
.It Dv AUDIO_GETDEV (audio_device_t)
|
|
This command is the same as described above for the sampling devices.
|
|
.It Dv AUDIO_MIXER_READ (mixer_ctrl_t)
|
|
.It Dv AUDIO_MIXER_WRITE (mixer_ctrl_t)
|
|
These commands read the current mixer state or set new mixer state for
|
|
the specified device
|
|
.Va dev .
|
|
.Va type
|
|
identifies which type of value is supplied in the
|
|
.Vt mixer_ctrl_t
|
|
argument.
|
|
.Bd -literal
|
|
#define AUDIO_MIXER_CLASS 0
|
|
#define AUDIO_MIXER_ENUM 1
|
|
#define AUDIO_MIXER_SET 2
|
|
#define AUDIO_MIXER_VALUE 3
|
|
typedef struct mixer_ctrl {
|
|
int dev; /* input: nth device */
|
|
int type;
|
|
union {
|
|
int ord; /* enum */
|
|
int mask; /* set */
|
|
mixer_level_t value; /* value */
|
|
} un;
|
|
} mixer_ctrl_t;
|
|
|
|
#define AUDIO_MIN_GAIN 0
|
|
#define AUDIO_MAX_GAIN 255
|
|
typedef struct mixer_level {
|
|
int num_channels;
|
|
u_char level[8]; /* [num_channels] */
|
|
} mixer_level_t;
|
|
#define AUDIO_MIXER_LEVEL_MONO 0
|
|
#define AUDIO_MIXER_LEVEL_LEFT 0
|
|
#define AUDIO_MIXER_LEVEL_RIGHT 1
|
|
.Ed
|
|
.Pp
|
|
For a mixer value, the
|
|
.Va value
|
|
field specifies both the number of channels and the values for each
|
|
channel.
|
|
If the channel count does not match the current channel count, the
|
|
attempt to change the setting may fail (depending on the hardware
|
|
device driver implementation).
|
|
For an enumeration value, the
|
|
.Va ord
|
|
field should be set to one of the possible values as returned by a prior
|
|
.Dv AUDIO_MIXER_DEVINFO
|
|
command.
|
|
The type
|
|
.Dv AUDIO_MIXER_CLASS
|
|
is only used for classifying particular mixer device
|
|
types and is not used for
|
|
.Dv AUDIO_MIXER_READ
|
|
or
|
|
.Dv AUDIO_MIXER_WRITE .
|
|
.It Dv AUDIO_MIXER_DEVINFO (mixer_devinfo_t)
|
|
This command is used iteratively to fetch audio mixer device information
|
|
into the input/output
|
|
.Vt mixer_devinfo_t
|
|
argument.
|
|
To query all the supported devices, start with an index field of
|
|
0 and continue with successive devices (1, 2, ...) until the
|
|
command returns an error.
|
|
.Bd -literal
|
|
typedef struct mixer_devinfo {
|
|
int index; /* input: nth mixer device */
|
|
audio_mixer_name_t label;
|
|
int type;
|
|
int mixer_class;
|
|
int next, prev;
|
|
#define AUDIO_MIXER_LAST -1
|
|
union {
|
|
struct audio_mixer_enum {
|
|
int num_mem;
|
|
struct {
|
|
audio_mixer_name_t label;
|
|
int ord;
|
|
} member[32];
|
|
} e;
|
|
struct audio_mixer_set {
|
|
int num_mem;
|
|
struct {
|
|
audio_mixer_name_t label;
|
|
int mask;
|
|
} member[32];
|
|
} s;
|
|
struct audio_mixer_value {
|
|
audio_mixer_name_t units;
|
|
int num_channels;
|
|
int delta;
|
|
} v;
|
|
} un;
|
|
} mixer_devinfo_t;
|
|
.Ed
|
|
.Pp
|
|
The
|
|
.Va label
|
|
field identifies the name of this particular mixer control.
|
|
The
|
|
.Va index
|
|
field may be used as the
|
|
.Va dev
|
|
field in
|
|
.Dv AUDIO_MIXER_READ
|
|
and
|
|
.Dv AUDIO_MIXER_WRITE
|
|
commands.
|
|
The
|
|
.Va type
|
|
field identifies the type of this mixer control.
|
|
Enumeration types are typically used for on/off style controls (e.g. a
|
|
mute control) or for input/output device selection (e.g. select
|
|
recording input source from CD, line in, or microphone).
|
|
Set types are similar to enumeration types but any combination
|
|
of the mask bits can be used.
|
|
.Pp
|
|
The
|
|
.Va mixer_class
|
|
field identifies what class of control this is.
|
|
The
|
|
.Pq arbitrary
|
|
value set by the hardware driver may be determined by examining the
|
|
.Va mixer_class
|
|
field of the class itself,
|
|
a mixer of type
|
|
.Dv AUDIO_MIXER_CLASS .
|
|
For example, a mixer controlling the input gain on the line in circuit
|
|
would have a
|
|
.Va mixer_class
|
|
that matches an input class device with the name
|
|
.Dq inputs
|
|
.Dv ( AudioCinputs ) ,
|
|
and would have a
|
|
.Va label
|
|
of
|
|
.Dq line
|
|
.Dv ( AudioNline ) .
|
|
Mixer controls which control audio circuitry for a particular audio
|
|
source (e.g. line-in, CD in, DAC output) are collected under the input class,
|
|
while those which control all audio sources (e.g. master volume,
|
|
equalization controls) are under the output class.
|
|
Hardware devices capable of recording typically also have a record class,
|
|
for controls that only affect recording,
|
|
and also a monitor class.
|
|
.Pp
|
|
The
|
|
.Va next
|
|
and
|
|
.Va prev
|
|
may be used by the hardware device driver to provide hints for the next
|
|
and previous devices in a related set (for example, the line in level
|
|
control would have the line in mute as its
|
|
.Dq next
|
|
value).
|
|
If there is no relevant next or previous value,
|
|
.Dv AUDIO_MIXER_LAST
|
|
is specified.
|
|
.Pp
|
|
For
|
|
.Dv AUDIO_MIXER_ENUM
|
|
mixer control types,
|
|
the enumeration values and their corresponding names are filled in.
|
|
For example, a mute control would return appropriate values paired with
|
|
.Dv AudioNon
|
|
and
|
|
.Dv AudioNoff .
|
|
For
|
|
.Dv AUDIO_MIXER_VALUE
|
|
and
|
|
.Dv AUDIO_MIXER_SET
|
|
mixer control types, the channel count is
|
|
returned; the units name specifies what the level controls (typical
|
|
values are
|
|
.Dv AudioNvolume ,
|
|
.Dv AudioNtreble ,
|
|
.Dv AudioNbass ) .
|
|
.\" For AUDIO_MIXER_SET mixer control types, what is what?
|
|
.El
|
|
.Pp
|
|
By convention, all the mixer devices can be distinguished from other
|
|
mixer controls because they use a name from one of the
|
|
.Dv AudioC*
|
|
string values.
|
|
.Sh FILES
|
|
.Bl -tag -width /dev/audioctl -compact
|
|
.It Pa /dev/audio
|
|
.It Pa /dev/audioctl
|
|
.It Pa /dev/sound
|
|
.It Pa /dev/mixer
|
|
.El
|
|
.Sh SEE ALSO
|
|
.Xr audiocfg 1 ,
|
|
.Xr audioctl 1 ,
|
|
.Xr mixerctl 1 ,
|
|
.Xr ioctl 2 ,
|
|
.Xr ossaudio 3 ,
|
|
.Xr midi 4 ,
|
|
.Xr radio 4 ,
|
|
.Ss ISA bus
|
|
.Xr aria 4 ,
|
|
.Xr ess 4 ,
|
|
.Xr gus 4 ,
|
|
.Xr guspnp 4 ,
|
|
.Xr pas 4 ,
|
|
.Xr sb 4 ,
|
|
.Xr wss 4 ,
|
|
.Xr ym 4
|
|
.Ss PCI bus
|
|
.Xr auacer 4 ,
|
|
.Xr auich 4 ,
|
|
.Xr auixp 4 ,
|
|
.Xr autri 4 ,
|
|
.Xr auvia 4 ,
|
|
.Xr azalia 4 ,
|
|
.Xr clcs 4 ,
|
|
.Xr clct 4 ,
|
|
.Xr cmpci 4 ,
|
|
.Xr eap 4 ,
|
|
.Xr emuxki 4 ,
|
|
.Xr esa 4 ,
|
|
.Xr esm 4 ,
|
|
.Xr eso 4 ,
|
|
.Xr fms 4 ,
|
|
.Xr neo 4 ,
|
|
.Xr sv 4 ,
|
|
.Xr yds 4
|
|
.Ss TURBOchannel
|
|
.Xr bba 4
|
|
.Ss USB
|
|
.Xr uaudio 4
|
|
.Sh HISTORY
|
|
Support for virtual channels and mixing first appeared in
|
|
.Nx 8.0 .
|
|
.Sh BUGS
|
|
If the device is used in
|
|
.Xr mmap 2
|
|
it is currently always mapped for writing (playing) due to VM system weirdness.
|