\author {Sven Goldt}
\title {The Linux Programmer's Guide}

\section {Sound Programming}
A PC at least has one sound device - the internal speaker.
But you can aswell buy a more sophisticated sound device to
plug in your PC called sound card.
Look at the Linux Sound User's Guide or the Sound-HOWTO for supported
sound cards.

\subsection {Programming the internal speaker}
Believe it or not, your PC speaker is part of the linux console
and thus a character device. Therefore ioctl() requests exist
to manipulate it.
For the internal speaker the following 2 requests exist:\\
\begin {enumerate}
\item KDMKTONE\\
will generate a beep for a specified time using the kernel timer.\\
Example: ioctl(fd,KDMKTONE,(long) {\tt argument}).\\
\item KIOCSOUND\\
will generate an endless beep or stop a beep.\\
Example: ioctl(fd,KIOCSOUND,(int) {\tt tone}).
\end {enumerate}

The {\tt argument} consists of the {\tt tone} value in the low word and
the duration in the high word. The {\tt tone} value is not the frequency,
but for some hardware dependent reason that i don't recall it's
1190000/frequency. The duration is measured in timer ticks.
Both ioctl calls return immediately so you can this way produce
beeps without blocking the program.\\
KDMKTONE should be used for warning signals because you don't have
to care for stopping the tone.\\
KIOCSOUND can be used to play melodies as demonstrated in the
example program splay {\it (please send more .sng files to me).}\\
To stop the beep you have to use the {\tt tone} value 0.

\subsection {Programming a sound card}
For you as a programmer it is important to know if the current linux
system has a sound card plugged in. One way to check it is to examine
/dev/sndstat. If opening /dev/sndstat fails and errno=ENODEV then
no sound driver is activated which means you will get no help from the
kernel sound driver. The same result might be achieved by a try to
open /dev/dsp until it is no link to the pcsnd driver.
But if you want to mess with a sound card at the
hardware level you know that some outb() and inb() will detect
the sound card you are looking for.
Lucky you are that if you use the sound driver for your programs
the chance is high that they will work on other i386 systems
aswell because some clever people decided to use the same driver
for linux, isc, FreeBSD and most other i386 based systems.
It would be a good idea if linux on other architectures offers
at least the same sound device interface.
A sound card is not part of the linux console, but is a special
device. A sound card mostly offers 3 features:
\begin {samepage}
\begin {itemize}
\item digital sample in/output
\item frequency modulation output
\item midi interface
\end {itemize}
\end {samepage}
These features all have it's own device driver interface. For
digital samples it is /dev/dsp, for the frequence modulation it is
/dev/sequencer and for the midi interface it is /dev/midi.
The sound settings like volume, balance or bass can be controlled
via the /dev/mixer interface.
For compatibility reasons a /dev/audio device exists which can read
SUN $\mu$-law sound data but it maps to the digital sample device.
Now you guess right that you have to use ioctl() to manipulate
these devices. The ioctl() requests are defined in $<linux/soundcard.h>$
and begin with SNDCTL\_.\\
\bigskip
{\bf Since i don't own a soundcard someone else has to continue here}

\endinput
