#!/bin/sh # # Starts the proper sound driver type and version # this script starts and shuts down (properly?) either the # commercial oss driver (installed for different kernels) or # the alsa driver. Easier said than done. Beware, this is not # an elegant solution :-) # # CCRMA, nando@ccrma.stanford.edu; February 2000 # Copyright (c) by Fernando Lopez-Lezcano # # This script is based on a preexisting initialization script # for oss I run at ccrma and on the alsasound script distributed # with the alsa sound driver. The alsasound script is Copyright # (c) by Jaroslav Kysela # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. # # Usage: # # /etc/rc.d/init.d/sounddriver start OSS|ALSA # /etc/sysconfg/sounddriver is sourced and can supply the default # value for DRIVER (either ALSA or OSS). If the file is not found # and alsa is installed, alsa is started. Otherwise oss is started # if it is found. The driver to start can also be manually selected # with the second parameter to the script. For alsa the oss mixer # and pcm emulation modules are started as well. # # NOTE: the oss startup is unnecesarily complicated by the need at # ccrma of being able to boot into different kernels and have # the sound driver work on all. Oss out of the box cannot do that. # The driver has to be installed in a different directory for each # kernel, and is not very happy to have other sound drivers around. # Here at ccrma I install oss in the default location (/usr/lib/oss). # During the installation of oss /usr/lib/oss has to be a real directory # (not a link) and no sound modules have to be present in /etc/conf.modules # (or /etc/modules.conf) - so move that file away before starting the # install). After the driver is happily installed you can move back the # conf.modules file to its home in /etc (and oss will not complain, but # see below for more caveats). The oss installation directory is renamed # to /usr/lib/oss-KERNEL_VERSION and a link is made from /usr/lib/oss # to /usr/lib/oss-KERNEL_VERSION. This script will keep the link pointed # to the proper version of the driver for the kernel that is running. # Sigh. Alsa is also modular but it is installed in the modules directory # for the kernel so kernel version matching is handled automatically. # As it should be.... # # NOTE: /etc/sndstat is a problem. It is a link in alsa and a device # in oss. It is erased when any of the two drivers stops and restored # automatically by the oss startup program soundon and by hand # thorough this script when alsa restarts. If left over oss gets # thoroughly confused and the alsa modules get loaded as a side effect # of doing a cat /dev/sndstat in the soundon script (as far as I can tell # from a cursory debugging session)... so oss can't start at all. # # ALSA Mixer: it is automatically reloaded by alsactl from the defaults # stored in /etc/asound.conf, use alsactl to create it. # OSS Mixer: it is automatically reset by using ossmix and restoring # defaults from /etc/ossmix.conf. This file is just a listing # of the parameter|value pairs that ossmix expects, on pair per # line, lines starting with "#" are comments. # # /etc/rc.d/init.d/sounddriver stop # the currently running driver will be stopped. # /etc/rc.d/init.d/sounddriver restart # stop the current driver and restart the default # Source function library (for RedHat). . /etc/rc.d/init.d/functions KERNEL=`/bin/uname -r` # Source sound driver configuration file if [ -f /etc/sysconfig/sounddriver ]; then . /etc/sysconfig/sounddriver else # No configuration, figure out reasonable defaults... if [ -f /lib/modules/${KERNEL}/misc/snd.o ] ; then # ALSA is installed, first choice DRIVER=ALSA else if [ -d /usr/lib/oss-${KERNEL} ] ; then # OSS is installed for current kernel DRIVER=OSS fi fi fi # second argument in command line overrides choice if [ ! "$2" = "" ] ; then DRIVER=$2 fi # Support functions for ALSA driver function alsa_start() { # # insert all alsa sound modules # cat $MODCONF | \ grep -E "^alias( |\t)+snd-card-[[:digit:]]" | \ awk '{print $3}' | \ while read line; do \ echo -n "Starting sound driver: $line "; \ /sbin/modprobe $line; \ echo "done"; \ done # load oss/free emulation echo -n "Starting oss/free emulation " /sbin/modprobe snd-pcm-oss /sbin/modprobe snd-mixer-oss /sbin/modprobe snd-seq-oss /sbin/modprobe snd-seq-midi # make sure there's a link to sndstat # the file or link is erased when either # driver is stopped if [ ! -L /dev/sndstat ] ; then /bin/rm -f /dev/sndstat /bin/ln -s /proc/asound/sndstat /dev/sndstat fi echo "done" # # restore driver settings # if [ -x $ALSACTL ]; then $ALSACTL restore else echo "ERROR: alsactl not found" fi } function alsa_detect_stop() { # # remove all sound modules # /sbin/lsmod | grep -E "^snd" | while read line; do \ /sbin/rmmod `echo $line | cut -d ' ' -f 1`; \ done # remove the 2.2 soundcore module (if possible) /sbin/rmmod soundcore 2> /dev/null } function alsa_stop() { # # remove all sound modules # alsa_detect_stop # make sure there nothing left of sndstat, it is a source # of problems with a mixed driver (oss/alsa) configuration if [ -L /dev/sndstat ] ; then /bin/rm -f /dev/sndstat fi } function alsa_detect_start() { # # run only detect module # /sbin/modprobe snd-detect } # set up defaults MODCONF=/etc/modules.conf ALSACTL=/usr/sbin/alsactl if [ ! -r $MODCONF ]; then if [ -r /etc/conf.modules ]; then MODCONF=/etc/conf.modules fi fi OSSBASE=/usr/lib/oss # See how we were called. case "$1" in start) if [ ${DRIVER} = "ALSA" ]; then # # start alsa driver (humm, we should check oss is not running) # if [ ! -d /proc/asound ]; then alsa_start if [ -d /proc/asound ] && [ -d /var/lock/subsys ]; then touch /var/lock/subsys/alsasound success "ALSA sound driver load" echo fi else if [ -f /proc/asound/detect ]; then echo -n "Shutting down sound detect module: " alsa_detect_stop echo "done" alsa_start if [ -d /proc/asound ] && [ -d /var/lock/subsys ]; then touch /var/lock/subsys/alsasound success "ALSA sound driver load" echo fi else echo -n "ALSA driver is already running" failure "ALSA sound driver load" echo fi fi fi if [ ${DRIVER} = "OSS" ]; then # # start oss driver (we should check alsa is not running) # echo -n "Loading sound driver for kernel ${KERNEL}: " if [ -d ${OSSBASE}-${KERNEL} ] ; then # there is an oss installation for this kernel if [ ! -e ${OSSBASE} -o -L ${OSSBASE} ] ; then # link it to the base name /bin/rm -f ${OSSBASE} /bin/ln -s oss-${KERNEL} ${OSSBASE} fi fi if [ -x ${OSSBASE}-${KERNEL}/soundon ] ; then # make sure sndstat is not there, if left over # from a previous alsa start the oss script # gets confused and won't start... if [ -e /dev/sndstat ] ; then rm -f /dev/sndstat fi ${OSSBASE}-${KERNEL}/soundon if [ $? -ne 0 ] ; then failure "sound driver load [$?]" echo else # initialize mixer if [ -x ${OSSBASE}-${KERNEL}/ossmix ] ; then if [ -f /etc/ossmix.conf ] ; then ${OSSBASE}-${KERNEL}/ossmix `/bin/egrep -v "^#" /etc/ossmix.conf` >/dev/null echo "OSS mixer initialized" fi fi touch /var/lock/subsys/sound cat /dev/sndstat | head -1 cat /dev/sndstat | awk 'BEGIN { RS=""} ; /config:/{ print }' success "OSS sound driver load" echo fi else # could not find soundon for current kernel failure "finding ${OSSBASE}-${KERNEL}/soundon" echo fi fi ;; stop) if [ -d /proc/asound ]; then # # stop alsa driver # if [ -d /proc/asound ]; then echo -n "Shutting down sound driver: " if [ -f /proc/asound/detect ]; then alsa_detect_stop else alsa_stop fi if [ -d /var/lock/subsys ]; then rm -f /var/lock/subsys/alsasound fi echo "done" success "ALSA sound driver stop" echo else echo "ALSA driver isn't running." failure "ALSA sound driver stop" echo fi else # # stop oss driver # echo -n "Unloading OSS sound driver: " if [ -x ${OSSBASE}/soundoff ] ; then rm -f /var/lock/subsys/sound ${OSSBASE}/soundoff # make sure there's no sndstat, if there is one # then the alsa drivers get loaded on the next # oss driver start through "cat /dev/sndstat" # (part of soundon) and the driver cannot restart # properly... if [ -e /dev/sndstat ] ; then /bin/rm -f /dev/sndstat fi success "OSS sound driver unload" echo else failure "finding ${OSSBASE}/soundoff" echo fi fi ;; restart) $0 stop $0 start ;; detect) if [ ${DRIVER} = "ALSA" ]; then # # start alsa driver in detect mode. # if [ -d /proc/asound ]; then if [ -f /proc/asound/detect ]; then echo "ALSA driver is already running in detect mode." exit 0 else echo -n "Shutting down sound driver: " alsa_stop echo "done" fi fi echo -n "Starting sound detect module: " alsa_detect_start echo "done" if [ -d /var/lock/subsys ]; then touch /var/lock/subsys/alsasound fi success "ALSA detect sound driver load" echo fi ;; *) echo "Usage: sounddriver {start|stop|restart|detect}" exit 1 esac exit 0