Home | History | Annotate | Line # | Download | only in isa
gus.c revision 1.27.2.1
      1 /*	$NetBSD: gus.c,v 1.27.2.1 1997/05/13 03:08:40 thorpej Exp $	*/
      2 
      3 /*-
      4  * Copyright (c) 1996 The NetBSD Foundation, Inc.
      5  * All rights reserved.
      6  *
      7  * This code is derived from software contributed to The NetBSD Foundation
      8  * by Ken Hornstein and John Kohl.
      9  *
     10  * Redistribution and use in source and binary forms, with or without
     11  * modification, are permitted provided that the following conditions
     12  * are met:
     13  * 1. Redistributions of source code must retain the above copyright
     14  *    notice, this list of conditions and the following disclaimer.
     15  * 2. Redistributions in binary form must reproduce the above copyright
     16  *    notice, this list of conditions and the following disclaimer in the
     17  *    documentation and/or other materials provided with the distribution.
     18  * 3. All advertising materials mentioning features or use of this software
     19  *    must display the following acknowledgement:
     20  *        This product includes software developed by the NetBSD
     21  *	  Foundation, Inc. and its contributors.
     22  * 4. Neither the name of The NetBSD Foundation nor the names of its
     23  *    contributors may be used to endorse or promote products derived
     24  *    from this software without specific prior written permission.
     25  *
     26  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
     27  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
     28  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     29  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
     30  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     31  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     32  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     33  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     34  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     35  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     36  * POSSIBILITY OF SUCH DAMAGE.
     37  */
     38 
     39 /*
     40  *
     41  * TODO:
     42  *	. figure out why mixer activity while sound is playing causes problems
     43  *	  (phantom interrupts?)
     44  *  	. figure out a better deinterleave strategy that avoids sucking up
     45  *	  CPU, memory and cache bandwidth.  (Maybe a special encoding?
     46  *	  Maybe use the double-speed sampling/hardware deinterleave trick
     47  *	  from the GUS SDK?)  A 486/33 isn't quite fast enough to keep
     48  *	  up with 44.1kHz 16-bit stereo output without some drop-outs.
     49  *	. use CS4231 for 16-bit sampling, for a-law and mu-law playback.
     50  *	. actually test full-duplex sampling(recording) and playback.
     51  */
     52 
     53 /*
     54  * Gravis UltraSound driver
     55  *
     56  * For more detailed information, see the GUS developers' kit
     57  * available on the net at:
     58  *
     59  * ftp://freedom.nmsu.edu/pub/ultrasound/gravis/util/
     60  * 	gusdkXXX.zip (developers' kit--get rev 2.22 or later)
     61  *		See ultrawrd.doc inside--it's MS Word (ick), but it's the bible
     62  *
     63  */
     64 
     65 /*
     66  * The GUS Max has a slightly strange set of connections between the CS4231
     67  * and the GF1 and the DMA interconnects.  It's set up so that the CS4231 can
     68  * be playing while the GF1 is loading patches from the system.
     69  *
     70  * Here's a recreation of the DMA interconnect diagram:
     71  *
     72  *       GF1
     73  *   +---------+				 digital
     74  *   |         |  record			 ASIC
     75  *   |         |--------------+
     76  *   |         |              |		       +--------+
     77  *   |         | play (dram)  |      +----+    |	|
     78  *   |         |--------------(------|-\  |    |   +-+  |
     79  *   +---------+              |      |  >-|----|---|C|--|------  dma chan 1
     80  *                            |  +---|-/  |    |   +-+ 	|
     81  *                            |  |   +----+    |    |   |
     82  *                            |	 |   +----+    |    |   |
     83  *   +---------+        +-+   +--(---|-\  |    |    |   |
     84  *   |         | play   |8|      |   |  >-|----|----+---|------  dma chan 2
     85  *   | ---C----|--------|/|------(---|-/  |    |        |
     86  *   |    ^    |record  |1|      |   +----+    |	|
     87  *   |    |    |   /----|6|------+   	       +--------+
     88  *   | ---+----|--/     +-+
     89  *   +---------+
     90  *     CS4231   	8-to-16 bit bus conversion, if needed
     91  *
     92  *
     93  * "C" is an optional combiner.
     94  *
     95  */
     96 
     97 #include "gus.h"
     98 #if NGUS > 0
     99 
    100 #include <sys/param.h>
    101 #include <sys/systm.h>
    102 #include <sys/errno.h>
    103 #include <sys/ioctl.h>
    104 #include <sys/syslog.h>
    105 #include <sys/device.h>
    106 #include <sys/proc.h>
    107 #include <sys/buf.h>
    108 #include <sys/fcntl.h>
    109 #include <sys/malloc.h>
    110 #include <sys/kernel.h>
    111 
    112 #include <machine/cpu.h>
    113 #include <machine/intr.h>
    114 #include <machine/bus.h>
    115 #include <machine/pio.h>
    116 #include <machine/cpufunc.h>
    117 #include <sys/audioio.h>
    118 #include <dev/audio_if.h>
    119 #include <dev/mulaw.h>
    120 
    121 #include <dev/isa/isavar.h>
    122 #include <dev/isa/isadmavar.h>
    123 #include <i386/isa/icu.h>
    124 
    125 #include <dev/ic/ics2101reg.h>
    126 #include <dev/ic/cs4231reg.h>
    127 #include <dev/ic/ad1848reg.h>
    128 #include <dev/isa/ics2101var.h>
    129 #include <dev/isa/ad1848var.h>
    130 #include <dev/isa/cs4231var.h>
    131 #include "gusreg.h"
    132 
    133 #ifdef AUDIO_DEBUG
    134 #define STATIC /* empty; for debugging symbols */
    135 #else
    136 #define STATIC static
    137 #endif
    138 
    139 /*
    140  * Software state of a single "voice" on the GUS
    141  */
    142 
    143 struct gus_voice {
    144 
    145 	/*
    146 	 * Various control bits
    147 	 */
    148 
    149 	unsigned char voccntl;	/* State of voice control register */
    150 	unsigned char volcntl;	/* State of volume control register */
    151 	unsigned char pan_pos;	/* Position of volume panning (4 bits) */
    152 	int rate;		/* Sample rate of voice being played back */
    153 
    154 	/*
    155 	 * Address of the voice data into the GUS's DRAM.  20 bits each
    156 	 */
    157 
    158 	u_long start_addr;	/* Starting address of voice data loop area */
    159 	u_long end_addr;	/* Ending address of voice data loop */
    160 	u_long current_addr;	/* Beginning address of voice data
    161 				   (start playing here) */
    162 
    163 	/*
    164 	 * linear volume values for the GUS's volume ramp.  0-511 (9 bits).
    165 	 * These values must be translated into the logarithmic values using
    166 	 * gus_log_volumes[]
    167 	 */
    168 
    169 	int start_volume;	/* Starting position of volume ramp */
    170 	int current_volume;	/* Current position of volume on volume ramp */
    171 	int end_volume;		/* Ending position of volume on volume ramp */
    172 };
    173 
    174 /*
    175  * Software state of GUS
    176  */
    177 
    178 struct gus_softc {
    179 	struct device sc_dev;		/* base device */
    180 	struct isadev sc_id;		/* ISA device */
    181 	void *sc_ih;			/* interrupt vector */
    182 	bus_space_tag_t sc_iot;		/* tag */
    183 	bus_space_handle_t sc_ioh;	/* handle */
    184 
    185 	int sc_iobase;			/* I/O base address */
    186 	int sc_irq;			/* IRQ used */
    187 	int sc_drq;			/* DMA channel for play */
    188 	int sc_recdrq;			/* DMA channel for recording */
    189 
    190 	int sc_flags;			/* Various flags about the GUS */
    191 #define GUS_MIXER_INSTALLED	0x01	/* An ICS mixer is installed */
    192 #define GUS_LOCKED		0x02	/* GUS is busy doing multi-phase DMA */
    193 #define GUS_CODEC_INSTALLED	0x04	/* CS4231 installed/MAX */
    194 #define GUS_PLAYING		0x08	/* GUS is playing a voice */
    195 #define GUS_DMAOUT_ACTIVE	0x10	/* GUS is busy doing audio DMA */
    196 #define GUS_DMAIN_ACTIVE	0x20	/* GUS is busy sampling  */
    197 #define GUS_OPEN		0x100	/* GUS is open */
    198 	int sc_dsize;			/* Size of GUS DRAM */
    199 	int sc_voices;			/* Number of active voices */
    200 	u_char sc_revision;		/* Board revision of GUS */
    201 	u_char sc_mixcontrol;		/* Value of GUS_MIX_CONTROL register */
    202 
    203 	u_long sc_orate;		/* Output sampling rate */
    204 	u_long sc_irate;		/* Input sampling rate */
    205 
    206 	int sc_encoding;		/* Current data encoding type */
    207 	int sc_precision;		/* # of bits of precision */
    208 	int sc_channels;		/* Number of active channels */
    209 	int sc_blocksize;		/* Current blocksize */
    210 	int sc_chanblocksize;		/* Current blocksize for each in-use
    211 					   channel */
    212 	short sc_nbufs;			/* how many on-GUS bufs per-channel */
    213 	short sc_bufcnt;		/* how many need to be played */
    214 	void *sc_deintr_buf;		/* deinterleave buffer for stereo */
    215 
    216 	int sc_ogain;			/* Output gain control */
    217 	u_char sc_out_port;		/* Current out port (generic only) */
    218 	u_char sc_in_port;		/* keep track of it when no codec */
    219 
    220 	void (*sc_dmaoutintr) __P((void*)); /* DMA completion intr handler */
    221 	void *sc_outarg;		/* argument for sc_dmaoutintr() */
    222 	u_char *sc_dmaoutaddr;		/* for isa_dmadone */
    223 	u_long sc_gusaddr;		/* where did we just put it? */
    224 	int sc_dmaoutcnt;		/* for isa_dmadone */
    225 
    226 	void (*sc_dmainintr) __P((void*)); /* DMA completion intr handler */
    227 	void *sc_inarg;			/* argument for sc_dmaoutintr() */
    228 	u_char *sc_dmainaddr;		/* for isa_dmadone */
    229 	int sc_dmaincnt;		/* for isa_dmadone */
    230 
    231 	struct stereo_dma_intr {
    232 		void (*intr)__P((void *));
    233 		void *arg;
    234 		u_char *buffer;
    235 		u_long dmabuf;
    236 		int size;
    237 		int flags;
    238 	} sc_stereo;
    239 
    240 	/*
    241 	 * State information for linear audio layer
    242 	 */
    243 
    244 	int sc_dmabuf;			/* Which ring buffer we're DMA'ing to */
    245 	int sc_playbuf;			/* Which ring buffer we're playing */
    246 
    247 	/*
    248 	 * Voice information array.  All voice-specific information is stored
    249 	 * here
    250 	 */
    251 
    252 	struct gus_voice sc_voc[32];	/* Voice data for each voice */
    253 	union {
    254 		struct ics2101_softc sc_mixer_u;
    255 		struct ad1848_softc sc_codec_u;
    256 	} u;
    257 #define sc_mixer u.sc_mixer_u
    258 #define sc_codec u.sc_codec_u
    259 };
    260 
    261 struct ics2101_volume {
    262 	u_char left;
    263 	u_char right;
    264 };
    265 
    266 #define HAS_CODEC(sc) ((sc)->sc_flags & GUS_CODEC_INSTALLED)
    267 #define HAS_MIXER(sc) ((sc)->sc_flags & GUS_MIXER_INSTALLED)
    268 
    269 /*
    270  * Mixer devices for ICS2101
    271  */
    272 /* MIC IN mute, line in mute, line out mute are first since they can be done
    273    even if no ICS mixer. */
    274 #define GUSICS_MIC_IN_MUTE		0
    275 #define GUSICS_LINE_IN_MUTE		1
    276 #define GUSICS_MASTER_MUTE		2
    277 #define GUSICS_CD_MUTE			3
    278 #define GUSICS_DAC_MUTE			4
    279 #define GUSICS_MIC_IN_LVL		5
    280 #define GUSICS_LINE_IN_LVL		6
    281 #define GUSICS_CD_LVL			7
    282 #define GUSICS_DAC_LVL			8
    283 #define GUSICS_MASTER_LVL		9
    284 
    285 #define GUSICS_RECORD_SOURCE		10
    286 
    287 /* Classes */
    288 #define GUSICS_INPUT_CLASS		11
    289 #define GUSICS_OUTPUT_CLASS		12
    290 #define GUSICS_RECORD_CLASS		13
    291 
    292 /*
    293  * Mixer & MUX devices for CS4231
    294  */
    295 #define GUSMAX_MIX_IN			0 /* input to MUX from mixer output */
    296 #define GUSMAX_MONO_LVL			1 /* mic input to MUX;
    297 					     also mono mixer input */
    298 #define GUSMAX_DAC_LVL			2 /* input to MUX; also mixer input */
    299 #define GUSMAX_LINE_IN_LVL		3 /* input to MUX; also mixer input */
    300 #define GUSMAX_CD_LVL			4 /* mixer input only */
    301 #define GUSMAX_MONITOR_LVL		5 /* digital mix (?) */
    302 #define GUSMAX_OUT_LVL			6 /* output level. (?) */
    303 #define GUSMAX_SPEAKER_LVL		7 /* pseudo-device for mute */
    304 #define GUSMAX_LINE_IN_MUTE		8 /* pre-mixer */
    305 #define GUSMAX_DAC_MUTE			9 /* pre-mixer */
    306 #define GUSMAX_CD_MUTE			10 /* pre-mixer */
    307 #define GUSMAX_MONO_MUTE		11 /* pre-mixer--microphone/mono */
    308 #define GUSMAX_MONITOR_MUTE		12 /* post-mixer level/mute */
    309 #define GUSMAX_SPEAKER_MUTE		13 /* speaker mute */
    310 
    311 #define GUSMAX_REC_LVL			14 /* post-MUX gain */
    312 
    313 #define GUSMAX_RECORD_SOURCE		15
    314 
    315 /* Classes */
    316 #define GUSMAX_INPUT_CLASS		16
    317 #define GUSMAX_RECORD_CLASS		17
    318 #define GUSMAX_MONITOR_CLASS		18
    319 #define GUSMAX_OUTPUT_CLASS		19
    320 
    321 #ifdef AUDIO_DEBUG
    322 #define GUSPLAYDEBUG	/*XXX*/
    323 extern void Dprintf __P((const char *, ...));
    324 #define DPRINTF(x)	if (gusdebug) Dprintf x
    325 #define DMAPRINTF(x)	if (gusdmadebug) Dprintf x
    326 int	gusdebug = 0;
    327 int	gusdmadebug = 0;
    328 #else
    329 #define DPRINTF(x)
    330 #define DMAPRINTF(x)
    331 #endif
    332 int	gus_dostereo = 1;
    333 
    334 #define NDMARECS 2048
    335 #ifdef GUSPLAYDEBUG
    336 int	gusstats = 0;
    337 struct dma_record {
    338     struct timeval tv;
    339     u_long gusaddr;
    340     caddr_t bsdaddr;
    341     u_short count;
    342     u_char channel;
    343     u_char direction;
    344 } dmarecords[NDMARECS];
    345 
    346 int dmarecord_index = 0;
    347 #endif
    348 
    349 /*
    350  * local routines
    351  */
    352 
    353 int	gusopen __P((dev_t, int));
    354 void	gusclose __P((void *));
    355 void	gusmax_close __P((void *));
    356 int	gusintr __P((void *));
    357 int	gus_set_in_gain __P((caddr_t, u_int, u_char));
    358 int	gus_get_in_gain __P((caddr_t));
    359 int	gus_set_out_gain __P((caddr_t, u_int, u_char));
    360 int	gus_get_out_gain __P((caddr_t));
    361 int 	gus_set_params __P((void *, int, struct audio_params *, struct audio_params *));
    362 int 	gusmax_set_params __P((void *, int, struct audio_params *, struct audio_params *));
    363 int	gus_round_blocksize __P((void *, int));
    364 int	gus_set_out_port __P((void *, int));
    365 int	gus_get_out_port __P((void *));
    366 int	gus_set_in_port __P((void *, int));
    367 int	gus_get_in_port __P((void *));
    368 int	gus_commit_settings __P((void *));
    369 int	gus_dma_output __P((void *, void *, int, void (*)(void *), void *));
    370 int	gus_dma_input __P((void *, void *, int, void (*)(void *), void *));
    371 int	gus_halt_out_dma __P((void *));
    372 int	gus_halt_in_dma __P((void *));
    373 int	gus_cont_out_dma __P((void *));
    374 int	gus_cont_in_dma __P((void *));
    375 int	gus_speaker_ctl __P((void *, int));
    376 int	gusmax_round_blocksize __P((void *, int));
    377 int	gusmax_commit_settings __P((void *));
    378 int	gusmax_dma_output __P((void *, void *, int, void (*)(void *), void *));
    379 int	gusmax_dma_input __P((void *, void *, int, void (*)(void *), void *));
    380 int	gusmax_halt_out_dma __P((void *));
    381 int	gusmax_halt_in_dma __P((void *));
    382 int	gusmax_cont_out_dma __P((void *));
    383 int	gusmax_cont_in_dma __P((void *));
    384 int	gusmax_speaker_ctl __P((void *, int));
    385 int	gusmax_set_out_port __P((void *, int));
    386 int	gusmax_get_out_port __P((void *));
    387 int	gusmax_set_in_port __P((void *, int));
    388 int	gusmax_get_in_port __P((void *));
    389 int	gus_getdev __P((void *, struct audio_device *));
    390 int	gus_set_io_params __P((struct gus_softc *, struct audio_params *));
    391 
    392 STATIC void	gus_deinterleave __P((struct gus_softc *, void *, int));
    393 STATIC void	gus_expand __P((void *, u_char *, int));
    394 STATIC void	gusmax_expand __P((void *, u_char *, int));
    395 STATIC void	gus_compress __P((void *, u_char *, int));
    396 
    397 STATIC int	gus_mic_ctl __P((void *, int));
    398 STATIC int	gus_linein_ctl __P((void *, int));
    399 STATIC int	gus_test_iobase __P((int));
    400 STATIC void	guspoke __P((int, long, u_char));
    401 STATIC void	gusdmaout __P((struct gus_softc *, int, u_long, caddr_t, int));
    402 STATIC void	gus_init_cs4231 __P((struct gus_softc *));
    403 STATIC void	gus_init_ics2101 __P((struct gus_softc *));
    404 
    405 STATIC void	gus_set_chan_addrs __P((struct gus_softc *));
    406 STATIC void	gusreset __P((struct gus_softc *, int));
    407 STATIC void	gus_set_voices __P((struct gus_softc *, int));
    408 STATIC void	gus_set_volume __P((struct gus_softc *, int, int));
    409 STATIC void	gus_set_samprate __P((struct gus_softc *, int, int));
    410 STATIC void	gus_set_recrate __P((struct gus_softc *, u_long));
    411 STATIC void	gus_start_voice __P((struct gus_softc *, int, int));
    412 STATIC void	gus_stop_voice __P((struct gus_softc *, int, int));
    413 STATIC void	gus_set_endaddr __P((struct gus_softc *, int, u_long));
    414 #ifdef GUSPLAYDEBUG
    415 STATIC void	gus_set_curaddr __P((struct gus_softc *, int, u_long));
    416 STATIC u_long	gus_get_curaddr __P((struct gus_softc *, int));
    417 #endif
    418 STATIC int	gus_dmaout_intr __P((struct gus_softc *));
    419 STATIC void	gus_dmaout_dointr __P((struct gus_softc *));
    420 STATIC void	gus_dmaout_timeout __P((void *));
    421 STATIC int	gus_dmain_intr __P((struct gus_softc *));
    422 STATIC int	gus_voice_intr __P((struct gus_softc *));
    423 STATIC void	gus_start_playing __P((struct gus_softc *, int));
    424 STATIC int	gus_continue_playing __P((struct gus_softc *, int));
    425 STATIC u_char guspeek __P((int, u_long));
    426 STATIC u_long convert_to_16bit __P((u_long));
    427 STATIC int	gus_setfd __P((void *, int));
    428 STATIC int	gus_mixer_set_port __P((void *, mixer_ctrl_t *));
    429 STATIC int	gus_mixer_get_port __P((void *, mixer_ctrl_t *));
    430 STATIC int	gusmax_mixer_set_port __P((void *, mixer_ctrl_t *));
    431 STATIC int	gusmax_mixer_get_port __P((void *, mixer_ctrl_t *));
    432 STATIC int	gus_mixer_query_devinfo __P((void *, mixer_devinfo_t *));
    433 STATIC int	gusmax_mixer_query_devinfo __P((void *, mixer_devinfo_t *));
    434 STATIC int	gus_query_encoding __P((void *, struct audio_encoding *));
    435 
    436 STATIC void	gusics_master_mute __P((struct ics2101_softc *, int));
    437 STATIC void	gusics_dac_mute __P((struct ics2101_softc *, int));
    438 STATIC void	gusics_mic_mute __P((struct ics2101_softc *, int));
    439 STATIC void	gusics_linein_mute __P((struct ics2101_softc *, int));
    440 STATIC void	gusics_cd_mute __P((struct ics2101_softc *, int));
    441 
    442 STATIC __inline int gus_to_vol __P((mixer_ctrl_t *, struct ad1848_volume *));
    443 STATIC __inline int gus_from_vol __P((mixer_ctrl_t *, struct ad1848_volume *));
    444 
    445 void	stereo_dmaintr __P((void *));
    446 
    447 /*
    448  * ISA bus driver routines
    449  */
    450 
    451 int	gusprobe __P((struct device *, void *, void *));
    452 void	gusattach __P((struct device *, struct device *, void *));
    453 
    454 struct cfattach gus_ca = {
    455 	sizeof(struct gus_softc), gusprobe, gusattach,
    456 };
    457 
    458 struct cfdriver gus_cd = {
    459 	NULL, "gus", DV_DULL
    460 };
    461 
    462 
    463 /*
    464  * A mapping from IRQ/DRQ values to the values used in the GUS's internal
    465  * registers.  A zero means that the referenced IRQ/DRQ is invalid
    466  */
    467 
    468 static int gus_irq_map[] = {
    469 	IRQUNK, IRQUNK, 1, 3, IRQUNK, 2, IRQUNK, 4, IRQUNK, 1, IRQUNK, 5, 6,
    470 	IRQUNK, IRQUNK, 7
    471 };
    472 static int gus_drq_map[] = {
    473 	DRQUNK, 1, DRQUNK, 2, DRQUNK, 3, 4, 5
    474 };
    475 
    476 /*
    477  * A list of valid base addresses for the GUS
    478  */
    479 
    480 static int gus_base_addrs[] = {
    481 	0x210, 0x220, 0x230, 0x240, 0x250, 0x260
    482 };
    483 static int gus_addrs = sizeof(gus_base_addrs) / sizeof(gus_base_addrs[0]);
    484 
    485 /*
    486  * Maximum frequency values of the GUS based on the number of currently active
    487  * voices.  Since the GUS samples a voice every 1.6 us, the maximum frequency
    488  * is dependent on the number of active voices.  Yes, it is pretty weird.
    489  */
    490 
    491 static int gus_max_frequency[] = {
    492 		44100,		/* 14 voices */
    493 		41160,		/* 15 voices */
    494 		38587,		/* 16 voices */
    495 		36317,		/* 17 voices */
    496 		34300,		/* 18 voices */
    497 		32494,		/* 19 voices */
    498 		30870,		/* 20 voices */
    499 		29400,		/* 21 voices */
    500 		28063,		/* 22 voices */
    501 		26843,		/* 23 voices */
    502 		25725,		/* 24 voices */
    503 		24696,		/* 25 voices */
    504 		23746,		/* 26 voices */
    505 		22866,		/* 27 voices */
    506 		22050,		/* 28 voices */
    507 		21289,		/* 29 voices */
    508 		20580,		/* 30 voices */
    509 		19916,		/* 31 voices */
    510 		19293		/* 32 voices */
    511 };
    512 /*
    513  * A mapping of linear volume levels to the logarithmic volume values used
    514  * by the GF1 chip on the GUS.  From GUS SDK vol1.c.
    515  */
    516 
    517 static unsigned short gus_log_volumes[512] = {
    518  0x0000,
    519  0x0700, 0x07ff, 0x0880, 0x08ff, 0x0940, 0x0980, 0x09c0, 0x09ff, 0x0a20,
    520  0x0a40, 0x0a60, 0x0a80, 0x0aa0, 0x0ac0, 0x0ae0, 0x0aff, 0x0b10, 0x0b20,
    521  0x0b30, 0x0b40, 0x0b50, 0x0b60, 0x0b70, 0x0b80, 0x0b90, 0x0ba0, 0x0bb0,
    522  0x0bc0, 0x0bd0, 0x0be0, 0x0bf0, 0x0bff, 0x0c08, 0x0c10, 0x0c18, 0x0c20,
    523  0x0c28, 0x0c30, 0x0c38, 0x0c40, 0x0c48, 0x0c50, 0x0c58, 0x0c60, 0x0c68,
    524  0x0c70, 0x0c78, 0x0c80, 0x0c88, 0x0c90, 0x0c98, 0x0ca0, 0x0ca8, 0x0cb0,
    525  0x0cb8, 0x0cc0, 0x0cc8, 0x0cd0, 0x0cd8, 0x0ce0, 0x0ce8, 0x0cf0, 0x0cf8,
    526  0x0cff, 0x0d04, 0x0d08, 0x0d0c, 0x0d10, 0x0d14, 0x0d18, 0x0d1c, 0x0d20,
    527  0x0d24, 0x0d28, 0x0d2c, 0x0d30, 0x0d34, 0x0d38, 0x0d3c, 0x0d40, 0x0d44,
    528  0x0d48, 0x0d4c, 0x0d50, 0x0d54, 0x0d58, 0x0d5c, 0x0d60, 0x0d64, 0x0d68,
    529  0x0d6c, 0x0d70, 0x0d74, 0x0d78, 0x0d7c, 0x0d80, 0x0d84, 0x0d88, 0x0d8c,
    530  0x0d90, 0x0d94, 0x0d98, 0x0d9c, 0x0da0, 0x0da4, 0x0da8, 0x0dac, 0x0db0,
    531  0x0db4, 0x0db8, 0x0dbc, 0x0dc0, 0x0dc4, 0x0dc8, 0x0dcc, 0x0dd0, 0x0dd4,
    532  0x0dd8, 0x0ddc, 0x0de0, 0x0de4, 0x0de8, 0x0dec, 0x0df0, 0x0df4, 0x0df8,
    533  0x0dfc, 0x0dff, 0x0e02, 0x0e04, 0x0e06, 0x0e08, 0x0e0a, 0x0e0c, 0x0e0e,
    534  0x0e10, 0x0e12, 0x0e14, 0x0e16, 0x0e18, 0x0e1a, 0x0e1c, 0x0e1e, 0x0e20,
    535  0x0e22, 0x0e24, 0x0e26, 0x0e28, 0x0e2a, 0x0e2c, 0x0e2e, 0x0e30, 0x0e32,
    536  0x0e34, 0x0e36, 0x0e38, 0x0e3a, 0x0e3c, 0x0e3e, 0x0e40, 0x0e42, 0x0e44,
    537  0x0e46, 0x0e48, 0x0e4a, 0x0e4c, 0x0e4e, 0x0e50, 0x0e52, 0x0e54, 0x0e56,
    538  0x0e58, 0x0e5a, 0x0e5c, 0x0e5e, 0x0e60, 0x0e62, 0x0e64, 0x0e66, 0x0e68,
    539  0x0e6a, 0x0e6c, 0x0e6e, 0x0e70, 0x0e72, 0x0e74, 0x0e76, 0x0e78, 0x0e7a,
    540  0x0e7c, 0x0e7e, 0x0e80, 0x0e82, 0x0e84, 0x0e86, 0x0e88, 0x0e8a, 0x0e8c,
    541  0x0e8e, 0x0e90, 0x0e92, 0x0e94, 0x0e96, 0x0e98, 0x0e9a, 0x0e9c, 0x0e9e,
    542  0x0ea0, 0x0ea2, 0x0ea4, 0x0ea6, 0x0ea8, 0x0eaa, 0x0eac, 0x0eae, 0x0eb0,
    543  0x0eb2, 0x0eb4, 0x0eb6, 0x0eb8, 0x0eba, 0x0ebc, 0x0ebe, 0x0ec0, 0x0ec2,
    544  0x0ec4, 0x0ec6, 0x0ec8, 0x0eca, 0x0ecc, 0x0ece, 0x0ed0, 0x0ed2, 0x0ed4,
    545  0x0ed6, 0x0ed8, 0x0eda, 0x0edc, 0x0ede, 0x0ee0, 0x0ee2, 0x0ee4, 0x0ee6,
    546  0x0ee8, 0x0eea, 0x0eec, 0x0eee, 0x0ef0, 0x0ef2, 0x0ef4, 0x0ef6, 0x0ef8,
    547  0x0efa, 0x0efc, 0x0efe, 0x0eff, 0x0f01, 0x0f02, 0x0f03, 0x0f04, 0x0f05,
    548  0x0f06, 0x0f07, 0x0f08, 0x0f09, 0x0f0a, 0x0f0b, 0x0f0c, 0x0f0d, 0x0f0e,
    549  0x0f0f, 0x0f10, 0x0f11, 0x0f12, 0x0f13, 0x0f14, 0x0f15, 0x0f16, 0x0f17,
    550  0x0f18, 0x0f19, 0x0f1a, 0x0f1b, 0x0f1c, 0x0f1d, 0x0f1e, 0x0f1f, 0x0f20,
    551  0x0f21, 0x0f22, 0x0f23, 0x0f24, 0x0f25, 0x0f26, 0x0f27, 0x0f28, 0x0f29,
    552  0x0f2a, 0x0f2b, 0x0f2c, 0x0f2d, 0x0f2e, 0x0f2f, 0x0f30, 0x0f31, 0x0f32,
    553  0x0f33, 0x0f34, 0x0f35, 0x0f36, 0x0f37, 0x0f38, 0x0f39, 0x0f3a, 0x0f3b,
    554  0x0f3c, 0x0f3d, 0x0f3e, 0x0f3f, 0x0f40, 0x0f41, 0x0f42, 0x0f43, 0x0f44,
    555  0x0f45, 0x0f46, 0x0f47, 0x0f48, 0x0f49, 0x0f4a, 0x0f4b, 0x0f4c, 0x0f4d,
    556  0x0f4e, 0x0f4f, 0x0f50, 0x0f51, 0x0f52, 0x0f53, 0x0f54, 0x0f55, 0x0f56,
    557  0x0f57, 0x0f58, 0x0f59, 0x0f5a, 0x0f5b, 0x0f5c, 0x0f5d, 0x0f5e, 0x0f5f,
    558  0x0f60, 0x0f61, 0x0f62, 0x0f63, 0x0f64, 0x0f65, 0x0f66, 0x0f67, 0x0f68,
    559  0x0f69, 0x0f6a, 0x0f6b, 0x0f6c, 0x0f6d, 0x0f6e, 0x0f6f, 0x0f70, 0x0f71,
    560  0x0f72, 0x0f73, 0x0f74, 0x0f75, 0x0f76, 0x0f77, 0x0f78, 0x0f79, 0x0f7a,
    561  0x0f7b, 0x0f7c, 0x0f7d, 0x0f7e, 0x0f7f, 0x0f80, 0x0f81, 0x0f82, 0x0f83,
    562  0x0f84, 0x0f85, 0x0f86, 0x0f87, 0x0f88, 0x0f89, 0x0f8a, 0x0f8b, 0x0f8c,
    563  0x0f8d, 0x0f8e, 0x0f8f, 0x0f90, 0x0f91, 0x0f92, 0x0f93, 0x0f94, 0x0f95,
    564  0x0f96, 0x0f97, 0x0f98, 0x0f99, 0x0f9a, 0x0f9b, 0x0f9c, 0x0f9d, 0x0f9e,
    565  0x0f9f, 0x0fa0, 0x0fa1, 0x0fa2, 0x0fa3, 0x0fa4, 0x0fa5, 0x0fa6, 0x0fa7,
    566  0x0fa8, 0x0fa9, 0x0faa, 0x0fab, 0x0fac, 0x0fad, 0x0fae, 0x0faf, 0x0fb0,
    567  0x0fb1, 0x0fb2, 0x0fb3, 0x0fb4, 0x0fb5, 0x0fb6, 0x0fb7, 0x0fb8, 0x0fb9,
    568  0x0fba, 0x0fbb, 0x0fbc, 0x0fbd, 0x0fbe, 0x0fbf, 0x0fc0, 0x0fc1, 0x0fc2,
    569  0x0fc3, 0x0fc4, 0x0fc5, 0x0fc6, 0x0fc7, 0x0fc8, 0x0fc9, 0x0fca, 0x0fcb,
    570  0x0fcc, 0x0fcd, 0x0fce, 0x0fcf, 0x0fd0, 0x0fd1, 0x0fd2, 0x0fd3, 0x0fd4,
    571  0x0fd5, 0x0fd6, 0x0fd7, 0x0fd8, 0x0fd9, 0x0fda, 0x0fdb, 0x0fdc, 0x0fdd,
    572  0x0fde, 0x0fdf, 0x0fe0, 0x0fe1, 0x0fe2, 0x0fe3, 0x0fe4, 0x0fe5, 0x0fe6,
    573  0x0fe7, 0x0fe8, 0x0fe9, 0x0fea, 0x0feb, 0x0fec, 0x0fed, 0x0fee, 0x0fef,
    574  0x0ff0, 0x0ff1, 0x0ff2, 0x0ff3, 0x0ff4, 0x0ff5, 0x0ff6, 0x0ff7, 0x0ff8,
    575  0x0ff9, 0x0ffa, 0x0ffb, 0x0ffc, 0x0ffd, 0x0ffe, 0x0fff};
    576 
    577 #define SELECT_GUS_REG(port,x) outb(port+GUS_REG_SELECT,x)
    578 #define WHICH_GUS_REG(port) inb(port+GUS_REG_SELECT)
    579 #define ADDR_HIGH(x) (unsigned int) ((x >> 7L) & 0x1fffL)
    580 #define ADDR_LOW(x) (unsigned int) ((x & 0x7fL) << 9L)
    581 
    582 #define GUS_MIN_VOICES 14	/* Minimum possible number of voices */
    583 #define GUS_MAX_VOICES 32	/* Maximum possible number of voices */
    584 #define GUS_VOICE_LEFT 0	/* Voice used for left (and mono) playback */
    585 #define GUS_VOICE_RIGHT 1	/* Voice used for right playback */
    586 #define GUS_MEM_OFFSET 32	/* Offset into GUS memory to begin of buffer */
    587 #define GUS_BUFFER_MULTIPLE 1024	/* Audio buffers are multiples of this */
    588 #define	GUS_MEM_FOR_BUFFERS	131072	/* use this many bytes on-GUS */
    589 #define	GUS_LEFT_RIGHT_OFFSET	(sc->sc_nbufs * sc->sc_chanblocksize + GUS_MEM_OFFSET)
    590 
    591 #define GUS_PREC_BYTES (sc->sc_precision >> 3) /* precision to bytes */
    592 
    593 /* splgus() must be splaudio() */
    594 
    595 #define splgus splaudio
    596 
    597 /*
    598  * Interface to higher level audio driver
    599  */
    600 
    601 struct audio_hw_if gus_hw_if = {
    602 	gusopen,
    603 	gusclose,
    604 	NULL,				/* drain */
    605 
    606 	gus_query_encoding,
    607 
    608 	gus_set_params,
    609 
    610 	gus_round_blocksize,
    611 
    612 	gus_set_out_port,
    613 	gus_get_out_port,
    614 	gus_set_in_port,
    615 	gus_get_in_port,
    616 
    617 	gus_commit_settings,
    618 
    619 	gus_dma_output,
    620 	gus_dma_input,
    621 	gus_halt_out_dma,
    622 	gus_halt_in_dma,
    623 	gus_cont_out_dma,
    624 	gus_cont_in_dma,
    625 
    626 	gus_speaker_ctl,
    627 
    628 	gus_getdev,
    629 	gus_setfd,
    630 	gus_mixer_set_port,
    631 	gus_mixer_get_port,
    632 	gus_mixer_query_devinfo,
    633 	1,				/* full-duplex */
    634 	0,
    635 };
    636 
    637 
    638 /*
    639  * Some info about the current audio device
    640  */
    641 
    642 struct audio_device gus_device = {
    643 	"UltraSound",
    644 	"",
    645 	"gus",
    646 };
    647 
    648 #define FLIP_REV	5		/* This rev has flipped mixer chans */
    649 
    650 
    651 int
    652 gusprobe(parent, match, aux)
    653 	struct device *parent;
    654 	void *match, *aux;
    655 {
    656 	register struct gus_softc *sc = match;
    657 	register struct isa_attach_args *ia = aux;
    658 	struct cfdata *cf = sc->sc_dev.dv_cfdata;
    659 	register int iobase = ia->ia_iobase;
    660 	int recdrq = cf->cf_flags;
    661 
    662 	sc->sc_iot = ia->ia_iot;
    663 	/*
    664 	 * Before we do anything else, make sure requested IRQ and DRQ are
    665 	 * valid for this card.
    666 	 */
    667 
    668 	if (gus_irq_map[ia->ia_irq] == IRQUNK) {
    669 		printf("gus: invalid irq %d, card not probed\n", ia->ia_irq);
    670 		return(0);
    671 	}
    672 
    673 	if (gus_drq_map[ia->ia_drq] == DRQUNK) {
    674 		printf("gus: invalid drq %d, card not probed\n", ia->ia_drq);
    675 		return(0);
    676 	}
    677 
    678 	if (recdrq != 0x00) {
    679 		if (recdrq > 7 || gus_drq_map[recdrq] == DRQUNK) {
    680 		   printf("gus: invalid flag given for second DMA channel (0x%x), card not probed\n", recdrq);
    681 		   return(0);
    682 	        }
    683 	} else
    684 		recdrq = ia->ia_drq;
    685 
    686 	if (iobase == IOBASEUNK) {
    687 		int i;
    688 		for(i = 0; i < gus_addrs; i++)
    689 			if (gus_test_iobase(gus_base_addrs[i])) {
    690 				iobase = gus_base_addrs[i];
    691 				goto done;
    692 			}
    693 		return 0;
    694 	} else if (! gus_test_iobase(iobase))
    695 			return 0;
    696 
    697 done:
    698 	sc->sc_iobase = iobase;
    699 	sc->sc_irq = ia->ia_irq;
    700 	sc->sc_drq = ia->ia_drq;
    701 	sc->sc_recdrq = recdrq;
    702 
    703 	ia->ia_iobase = sc->sc_iobase;
    704 	ia->ia_iosize = 16;		/* XXX */
    705 	return(1);
    706 }
    707 
    708 /*
    709  * Test to see if a particular I/O base is valid for the GUS.  Return true
    710  * if it is.
    711  */
    712 
    713 STATIC int
    714 gus_test_iobase (int iobase)
    715 {
    716 	int i = splgus();
    717 	u_char s1, s2;
    718 
    719 	/*
    720 	 * Reset GUS to an initial state before we do anything.
    721 	 */
    722 
    723 	delay(500);
    724 
    725  	SELECT_GUS_REG(iobase, GUSREG_RESET);
    726  	outb(iobase+GUS_DATA_HIGH, 0x00);
    727 
    728  	delay(500);
    729 
    730 	SELECT_GUS_REG(iobase, GUSREG_RESET);
    731  	outb(iobase+GUS_DATA_HIGH, GUSMASK_MASTER_RESET);
    732 
    733  	delay(500);
    734 
    735 	splx(i);
    736 
    737 	/*
    738 	 * See if we can write to the board's memory
    739 	 */
    740 
    741  	s1 = guspeek(iobase, 0L);
    742  	s2 = guspeek(iobase, 1L);
    743 
    744  	guspoke(iobase, 0L, 0xaa);
    745  	guspoke(iobase, 1L, 0x55);
    746 
    747  	if ((i=(int)guspeek(iobase, 0L)) != 0xaa) {
    748 		return(0);
    749 	}
    750 
    751 	guspoke(iobase, 0L, s1);
    752 	guspoke(iobase, 1L, s2);
    753 
    754 	return 1;
    755 }
    756 
    757 /*
    758  * Setup the GUS for use; called shortly after probe
    759  */
    760 
    761 void
    762 gusattach(parent, self, aux)
    763 	struct device *parent, *self;
    764 	void *aux;
    765 {
    766 	register struct gus_softc *sc = (void *) self;
    767 	register struct isa_attach_args *ia = aux;
    768 	register int port = ia->ia_iobase;
    769 	int		i;
    770 	register unsigned char	c,d,m;
    771 
    772 	/*
    773 	 * Figure out our board rev, and see if we need to initialize the
    774 	 * mixer
    775 	 */
    776 
    777  	delay(500);
    778 
    779  	c = inb(port+GUS_BOARD_REV);
    780 	if (c != 0xff)
    781 		sc->sc_revision = c;
    782 	else
    783 		sc->sc_revision = 0;
    784 
    785 
    786  	SELECT_GUS_REG(port, GUSREG_RESET);
    787  	outb(port+GUS_DATA_HIGH, 0x00);
    788 
    789 	gusreset(sc, GUS_MAX_VOICES); /* initialize all voices */
    790 	gusreset(sc, GUS_MIN_VOICES); /* then set to just the ones we use */
    791 
    792 	/*
    793 	 * Setup the IRQ and DRQ lines in software, using values from
    794 	 * config file
    795 	 */
    796 
    797 	m = GUSMASK_LINE_IN|GUSMASK_LINE_OUT;		/* disable all */
    798 
    799 	c = ((unsigned char) gus_irq_map[ia->ia_irq]) | GUSMASK_BOTH_RQ;
    800 
    801 	if (sc->sc_recdrq == sc->sc_drq)
    802 		d = (unsigned char) (gus_drq_map[sc->sc_drq] |
    803 				GUSMASK_BOTH_RQ);
    804 	else
    805 		d = (unsigned char) (gus_drq_map[sc->sc_drq] |
    806 				gus_drq_map[sc->sc_recdrq] << 3);
    807 
    808 	/*
    809 	 * Program the IRQ and DMA channels on the GUS.  Note that we hardwire
    810 	 * the GUS to only use one IRQ channel, but we give the user the
    811 	 * option of using two DMA channels (the other one given by the flags
    812 	 * option in the config file).  Two DMA channels are needed for full-
    813 	 * duplex operation.
    814 	 *
    815 	 * The order of these operations is very magical.
    816 	 */
    817 
    818 	disable_intr();
    819 
    820 	outb(port+GUS_REG_CONTROL, GUS_REG_IRQCTL);
    821 	outb(port+GUS_MIX_CONTROL, m);
    822 	outb(port+GUS_IRQCTL_CONTROL, 0x00);
    823 	outb(port+0x0f, 0x00);
    824 
    825 	outb(port+GUS_MIX_CONTROL, m);
    826 	outb(port+GUS_DMA_CONTROL, d | 0x80); /* magic reset? */
    827 
    828 	outb(port+GUS_MIX_CONTROL, m | GUSMASK_CONTROL_SEL);
    829 	outb(port+GUS_IRQ_CONTROL, c);
    830 
    831 	outb(port+GUS_MIX_CONTROL, m);
    832 	outb(port+GUS_DMA_CONTROL, d);
    833 
    834 	outb(port+GUS_MIX_CONTROL, m | GUSMASK_CONTROL_SEL);
    835 	outb(port+GUS_IRQ_CONTROL, c);
    836 
    837 	outb(port+GUS_VOICE_SELECT, 0x00);
    838 
    839 	/* enable line in, line out.  leave mic disabled. */
    840 	outb(port+GUS_MIX_CONTROL,
    841 	     (m | GUSMASK_LATCHES) & ~(GUSMASK_LINE_OUT|GUSMASK_LINE_IN));
    842 	outb(port+GUS_VOICE_SELECT, 0x00);
    843 
    844 	enable_intr();
    845 
    846 	sc->sc_mixcontrol =
    847 		(m | GUSMASK_LATCHES) & ~(GUSMASK_LINE_OUT|GUSMASK_LINE_IN);
    848 
    849 	/* XXX WILL THIS ALWAYS WORK THE WAY THEY'RE OVERLAYED?! */
    850 	sc->sc_codec.sc_isa = sc->sc_dev.dv_parent;
    851 
    852  	if (sc->sc_revision >= 5 && sc->sc_revision <= 9) {
    853  		sc->sc_flags |= GUS_MIXER_INSTALLED;
    854  		gus_init_ics2101(sc);
    855 	}
    856 	if (sc->sc_revision >= 0xa) {
    857 		gus_init_cs4231(sc);
    858 	}
    859 
    860  	SELECT_GUS_REG(port, GUSREG_RESET);
    861  	/*
    862  	 * Check to see how much memory we have on this card; see if any
    863  	 * "mirroring" occurs.  We're assuming at least 256K already exists
    864  	 * on the card; otherwise the initial probe would have failed
    865  	 */
    866 
    867 	guspoke(port, 0L, 0x00);
    868 	for(i = 1; i < 1024; i++) {
    869 		u_long loc;
    870 
    871 		/*
    872 		 * See if we've run into mirroring yet
    873 		 */
    874 
    875 		if (guspeek(port, 0L) != 0)
    876 			break;
    877 
    878 		loc = i << 10;
    879 
    880 		guspoke(port, loc, 0xaa);
    881 		if (guspeek(port, loc) != 0xaa)
    882 			break;
    883 	}
    884 
    885 	sc->sc_dsize = i;
    886 	sprintf(gus_device.version, "3.%d", sc->sc_revision);
    887 
    888 	printf("\n <Gravis UltraSound version 3.%d, %dKB DRAM, ",
    889 	       sc->sc_revision, sc->sc_dsize);
    890 	if (HAS_MIXER(sc))
    891 		printf("ICS2101 mixer, ");
    892 	if (HAS_CODEC(sc))
    893 		printf("%s codec/mixer, ", sc->sc_codec.chip_name);
    894 	if (sc->sc_recdrq == sc->sc_drq) {
    895 		printf("half-duplex");
    896 		gus_hw_if.full_duplex = 0;
    897 	} else {
    898 		printf("full-duplex, record drq %d", sc->sc_recdrq);
    899 		gus_hw_if.full_duplex = 1;
    900 	}
    901 
    902 	printf(">\n");
    903 
    904 	/*
    905 	 * Setup a default interrupt handler
    906 	 */
    907 
    908 	/* XXX we shouldn't have to use splgus == splclock, nor should
    909 	 * we use IPL_CLOCK.
    910 	 */
    911 	sc->sc_ih = isa_intr_establish(ia->ia_ic, ia->ia_irq, IST_EDGE,
    912 	    IPL_AUDIO, gusintr, sc /* sc->sc_gusdsp */);
    913 
    914 	/*
    915 	 * Set some default values
    916 	 */
    917 
    918 	sc->sc_irate = sc->sc_orate = 44100;
    919 	sc->sc_encoding = AUDIO_ENCODING_LINEAR_LE;
    920 	sc->sc_precision = 16;
    921 	sc->sc_voc[GUS_VOICE_LEFT].voccntl |= GUSMASK_DATA_SIZE16;
    922 	sc->sc_voc[GUS_VOICE_RIGHT].voccntl |= GUSMASK_DATA_SIZE16;
    923 	sc->sc_channels = 1;
    924 	sc->sc_ogain = 340;
    925 	gus_commit_settings(sc);
    926 
    927 	/*
    928 	 * We always put the left channel full left & right channel
    929 	 * full right.
    930 	 * For mono playback, we set up both voices playing the same buffer.
    931 	 */
    932 	outb(sc->sc_iobase+GUS_VOICE_SELECT, (unsigned char) GUS_VOICE_LEFT);
    933 	SELECT_GUS_REG(sc->sc_iobase, GUSREG_PAN_POS);
    934 	outb(sc->sc_iobase+GUS_DATA_HIGH, GUS_PAN_FULL_LEFT);
    935 
    936 	outb(sc->sc_iobase+GUS_VOICE_SELECT, (unsigned char) GUS_VOICE_RIGHT);
    937 	SELECT_GUS_REG(sc->sc_iobase, GUSREG_PAN_POS);
    938 	outb(sc->sc_iobase+GUS_DATA_HIGH, GUS_PAN_FULL_RIGHT);
    939 
    940 	/*
    941 	 * Attach to the generic audio layer
    942 	 */
    943 
    944 	if (audio_hardware_attach(&gus_hw_if, HAS_CODEC(sc) ? (void *)&sc->sc_codec : (void *)sc) != 0)
    945 		printf("gus: could not attach to audio pseudo-device driver\n");
    946 }
    947 
    948 int
    949 gusopen(dev, flags)
    950 	dev_t dev;
    951 	int flags;
    952 {
    953 	int unit = AUDIOUNIT(dev);
    954 	struct gus_softc *sc;
    955 
    956 	DPRINTF(("gusopen() called\n"));
    957 
    958 	if (unit >= gus_cd.cd_ndevs)
    959 		return ENXIO;
    960 	sc = gus_cd.cd_devs[unit];
    961 	if (!sc)
    962 		return ENXIO;
    963 
    964 	if (sc->sc_flags & GUS_OPEN)
    965 		return EBUSY;
    966 
    967 	/*
    968 	 * Some initialization
    969 	 */
    970 
    971 	sc->sc_flags |= GUS_OPEN;
    972 	sc->sc_dmabuf = 0;
    973 	sc->sc_playbuf = -1;
    974 	sc->sc_bufcnt = 0;
    975 	sc->sc_voc[GUS_VOICE_LEFT].start_addr = GUS_MEM_OFFSET - 1;
    976 	sc->sc_voc[GUS_VOICE_LEFT].current_addr = GUS_MEM_OFFSET;
    977 
    978 	if (HAS_CODEC(sc)) {
    979 		ad1848_open(&sc->sc_codec, dev, flags);
    980 		sc->sc_codec.aux1_mute = 0;
    981 		ad1848_mute_aux1(&sc->sc_codec, 0); /* turn on DAC output */
    982 		if (flags & FREAD) {
    983 			sc->sc_codec.mono_mute = 0;
    984 			cs4231_mute_mono(&sc->sc_codec, 0);
    985 		}
    986 	} else if (flags & FREAD) {
    987 		/* enable/unmute the microphone */
    988 		if (HAS_MIXER(sc)) {
    989 			gusics_mic_mute(&sc->sc_mixer, 0);
    990 		} else
    991 			gus_mic_ctl(sc, SPKR_ON);
    992 	}
    993 	if (sc->sc_nbufs == 0)
    994 	    gus_round_blocksize(sc, GUS_BUFFER_MULTIPLE); /* default blksiz */
    995 	return 0;
    996 }
    997 
    998 STATIC void
    999 gusmax_expand(hdl, buf, count)
   1000 	void *hdl;
   1001 	u_char *buf;
   1002 	int count;
   1003 {
   1004 	register struct ad1848_softc *ac = hdl;
   1005 
   1006 	gus_expand(ac->parent, buf, count);
   1007 }
   1008 
   1009 STATIC void
   1010 gus_expand(hdl, buf, count)
   1011 	void *hdl;
   1012 	u_char *buf;
   1013 	int count;
   1014 {
   1015 	struct gus_softc *sc = hdl;
   1016 
   1017 	if (sc->sc_encoding == AUDIO_ENCODING_ULAW)
   1018 		mulaw_to_ulinear8(buf, count);
   1019 	/*
   1020 	 * If we need stereo deinterleaving, do it now.
   1021 	 */
   1022 	if (sc->sc_channels == 2)
   1023 		gus_deinterleave(sc, (void *)buf, count);
   1024 }
   1025 
   1026 STATIC void
   1027 gus_compress(hdl, buf, count)
   1028 	void *hdl;
   1029 	u_char *buf;
   1030 	int count;
   1031 {
   1032 
   1033 	ulinear8_to_mulaw(buf, count);
   1034 }
   1035 
   1036 STATIC void
   1037 gus_deinterleave(sc, buf, size)
   1038 	register struct gus_softc *sc;
   1039 	void *buf;
   1040 	int size;
   1041 {
   1042 	/* deinterleave the stereo data.  We can use sc->sc_deintr_buf
   1043 	   for scratch space. */
   1044 	register int i;
   1045 
   1046 	/*
   1047 	 * size is in bytes.
   1048 	 */
   1049 	if (sc->sc_precision == 16) {
   1050 		register u_short *dei = sc->sc_deintr_buf;
   1051 		register u_short *sbuf = buf;
   1052 		size >>= 1;		/* bytecnt to shortcnt */
   1053 		/* copy 2nd of each pair of samples to the staging area, while
   1054 		   compacting the 1st of each pair into the original area. */
   1055 		for (i = 0; i < size/2-1; i++)  {
   1056 			dei[i] = sbuf[i*2+1];
   1057 			sbuf[i+1] = sbuf[i*2+2];
   1058 		}
   1059 		/*
   1060 		 * this has copied one less sample than half of the
   1061 		 * buffer.  The first sample of the 1st stream was
   1062 		 * already in place and didn't need copying.
   1063 		 * Therefore, we've moved all of the 1st stream's
   1064 		 * samples into place.  We have one sample from 2nd
   1065 		 * stream in the last slot of original area, not
   1066 		 * copied to the staging area (But we don't need to!).
   1067 		 * Copy the remainder of the original stream into place.
   1068 		 */
   1069 		bcopy(dei, &sbuf[size/2], i * sizeof(short));
   1070 	} else {
   1071 		register u_char *dei = sc->sc_deintr_buf;
   1072 		register u_char *sbuf = buf;
   1073 		for (i = 0; i < size/2-1; i++)  {
   1074 			dei[i] = sbuf[i*2+1];
   1075 			sbuf[i+1] = sbuf[i*2+2];
   1076 		}
   1077 		bcopy(dei, &sbuf[size/2], i);
   1078 	}
   1079 }
   1080 
   1081 /*
   1082  * Actually output a buffer to the DSP chip
   1083  */
   1084 
   1085 int
   1086 gusmax_dma_output(addr, buf, size, intr, arg)
   1087 	void * addr;
   1088 	void *buf;
   1089 	int size;
   1090 	void (*intr) __P((void *));
   1091 	void *arg;
   1092 {
   1093 	register struct ad1848_softc *ac = addr;
   1094 	return gus_dma_output(ac->parent, buf, size, intr, arg);
   1095 }
   1096 
   1097 /*
   1098  * called at splgus() from interrupt handler.
   1099  */
   1100 void
   1101 stereo_dmaintr(arg)
   1102 	void *arg;
   1103 {
   1104     struct gus_softc *sc = arg;
   1105     struct stereo_dma_intr *sa = &sc->sc_stereo;
   1106 
   1107     DMAPRINTF(("stereo_dmaintr"));
   1108 
   1109     /*
   1110      * Put other half in its place, then call the real interrupt routine :)
   1111      */
   1112 
   1113     sc->sc_dmaoutintr = sa->intr;
   1114     sc->sc_outarg = sa->arg;
   1115 
   1116 #ifdef GUSPLAYDEBUG
   1117     if (gusstats) {
   1118       microtime(&dmarecords[dmarecord_index].tv);
   1119       dmarecords[dmarecord_index].gusaddr = sa->dmabuf;
   1120       dmarecords[dmarecord_index].bsdaddr = sa->buffer;
   1121       dmarecords[dmarecord_index].count = sa->size;
   1122       dmarecords[dmarecord_index].channel = 1;
   1123       dmarecords[dmarecord_index].direction = 1;
   1124       dmarecord_index = ++dmarecord_index % NDMARECS;
   1125     }
   1126 #endif
   1127 
   1128     gusdmaout(sc, sa->flags, sa->dmabuf, (caddr_t) sa->buffer, sa->size);
   1129 
   1130     sa->flags = 0;
   1131     sa->dmabuf = 0;
   1132     sa->buffer = 0;
   1133     sa->size = 0;
   1134     sa->intr = 0;
   1135     sa->arg = 0;
   1136 }
   1137 
   1138 /*
   1139  * Start up DMA output to the card.
   1140  * Called at splgus/splaudio already, either from intr handler or from
   1141  * generic audio code.
   1142  */
   1143 int
   1144 gus_dma_output(addr, buf, size, intr, arg)
   1145 	void * addr;
   1146 	void *buf;
   1147 	int size;
   1148 	void (*intr) __P((void *));
   1149 	void *arg;
   1150 {
   1151 	struct gus_softc *sc = addr;
   1152 	u_char *buffer = buf;
   1153 	u_long boarddma;
   1154 	int flags;
   1155 
   1156 	DMAPRINTF(("gus_dma_output %d @ %x\n", size, buf));
   1157 
   1158 	if (size != sc->sc_blocksize) {
   1159 	    DPRINTF(("gus_dma_output reqsize %d not sc_blocksize %d\n",
   1160 		     size, sc->sc_blocksize));
   1161 	    return EINVAL;
   1162 	}
   1163 
   1164 	flags = GUSMASK_DMA_WRITE;
   1165 	if (sc->sc_precision == 16)
   1166 	    flags |= GUSMASK_DMA_DATA_SIZE;
   1167 	if (sc->sc_encoding == AUDIO_ENCODING_ULAW ||
   1168 	    sc->sc_encoding == AUDIO_ENCODING_ULINEAR_LE)
   1169 	    flags |= GUSMASK_DMA_INVBIT;
   1170 
   1171 	if (sc->sc_channels == 2) {
   1172 		if (sc->sc_precision == 16) {
   1173 			if (size & 3) {
   1174 				DPRINTF(("gus_dma_output: unpaired 16bit samples"));
   1175 				size &= 3;
   1176 			}
   1177 		} else if (size & 1) {
   1178 			DPRINTF(("gus_dma_output: unpaired samples"));
   1179 			size &= 1;
   1180 		}
   1181 		if (size == 0)
   1182 			return 0;
   1183 		size >>= 1;
   1184 
   1185 		boarddma = size * sc->sc_dmabuf + GUS_MEM_OFFSET;
   1186 
   1187 		sc->sc_stereo.intr = intr;
   1188 		sc->sc_stereo.arg = arg;
   1189 		sc->sc_stereo.size = size;
   1190 		sc->sc_stereo.dmabuf = boarddma + GUS_LEFT_RIGHT_OFFSET;
   1191 		sc->sc_stereo.buffer = buffer + size;
   1192 		sc->sc_stereo.flags = flags;
   1193 		if (gus_dostereo) {
   1194 		  intr = stereo_dmaintr;
   1195 		  arg = sc;
   1196 		}
   1197 	} else
   1198 		boarddma = size * sc->sc_dmabuf + GUS_MEM_OFFSET;
   1199 
   1200 
   1201 	sc->sc_flags |= GUS_LOCKED;
   1202 	sc->sc_dmaoutintr = intr;
   1203 	sc->sc_outarg = arg;
   1204 
   1205 #ifdef GUSPLAYDEBUG
   1206 	if (gusstats) {
   1207 	  microtime(&dmarecords[dmarecord_index].tv);
   1208 	  dmarecords[dmarecord_index].gusaddr = boarddma;
   1209 	  dmarecords[dmarecord_index].bsdaddr = buffer;
   1210 	  dmarecords[dmarecord_index].count = size;
   1211 	  dmarecords[dmarecord_index].channel = 0;
   1212 	  dmarecords[dmarecord_index].direction = 1;
   1213 	  dmarecord_index = ++dmarecord_index % NDMARECS;
   1214 	}
   1215 #endif
   1216 
   1217 	gusdmaout(sc, flags, boarddma, (caddr_t) buffer, size);
   1218 
   1219 	return 0;
   1220 }
   1221 
   1222 void
   1223 gusmax_close(addr)
   1224 	void *addr;
   1225 {
   1226 	register struct ad1848_softc *ac = addr;
   1227 	register struct gus_softc *sc = ac->parent;
   1228 #if 0
   1229 	ac->aux1_mute = 1;
   1230 	ad1848_mute_aux1(ac, 1);	/* turn off DAC output */
   1231 #endif
   1232 	ad1848_close(ac);
   1233 	gusclose(sc);
   1234 }
   1235 
   1236 /*
   1237  * Close out device stuff.  Called at splgus() from generic audio layer.
   1238  */
   1239 void
   1240 gusclose(addr)
   1241 	void *addr;
   1242 {
   1243 	struct gus_softc *sc = addr;
   1244 
   1245         DPRINTF(("gus_close: sc=0x%x\n", sc));
   1246 
   1247 
   1248 /*	if (sc->sc_flags & GUS_DMAOUT_ACTIVE) */ {
   1249 		gus_halt_out_dma(sc);
   1250 	}
   1251 /*	if (sc->sc_flags & GUS_DMAIN_ACTIVE) */ {
   1252 		gus_halt_in_dma(sc);
   1253 	}
   1254 	sc->sc_flags &= ~(GUS_OPEN|GUS_LOCKED|GUS_DMAOUT_ACTIVE|GUS_DMAIN_ACTIVE);
   1255 
   1256 	if (sc->sc_deintr_buf) {
   1257 		FREE(sc->sc_deintr_buf, M_DEVBUF);
   1258 		sc->sc_deintr_buf = NULL;
   1259 	}
   1260 	/* turn off speaker, etc. */
   1261 
   1262 	/* make sure the voices shut up: */
   1263 	gus_stop_voice(sc, GUS_VOICE_LEFT, 1);
   1264 	gus_stop_voice(sc, GUS_VOICE_RIGHT, 0);
   1265 }
   1266 
   1267 /*
   1268  * Service interrupts.  Farm them off to helper routines if we are using the
   1269  * GUS for simple playback/record
   1270  */
   1271 
   1272 #ifdef DIAGNOSTIC
   1273 int gusintrcnt;
   1274 int gusdmaintrcnt;
   1275 int gusvocintrcnt;
   1276 #endif
   1277 
   1278 int
   1279 gusintr(arg)
   1280 	void *arg;
   1281 {
   1282 	register struct gus_softc *sc = arg;
   1283 	unsigned char intr;
   1284 	register int port = sc->sc_iobase;
   1285 	int retval = 0;
   1286 
   1287 	DPRINTF(("gusintr\n"));
   1288 #ifdef DIAGNOSTIC
   1289 	gusintrcnt++;
   1290 #endif
   1291 	if (HAS_CODEC(sc))
   1292 		retval = ad1848_intr(&sc->sc_codec);
   1293 	if ((intr = inb(port+GUS_IRQ_STATUS)) & GUSMASK_IRQ_DMATC) {
   1294 		DMAPRINTF(("gusintr dma flags=%x\n", sc->sc_flags));
   1295 #ifdef DIAGNOSTIC
   1296 		gusdmaintrcnt++;
   1297 #endif
   1298 		retval += gus_dmaout_intr(sc);
   1299 		if (sc->sc_flags & GUS_DMAIN_ACTIVE) {
   1300 		    SELECT_GUS_REG(port, GUSREG_SAMPLE_CONTROL);
   1301 		    intr = inb(port+GUS_DATA_HIGH);
   1302 		    if (intr & GUSMASK_SAMPLE_DMATC) {
   1303 			retval += gus_dmain_intr(sc);
   1304 		    }
   1305 		}
   1306 	}
   1307 	if (intr & (GUSMASK_IRQ_VOICE | GUSMASK_IRQ_VOLUME)) {
   1308 		DMAPRINTF(("gusintr voice flags=%x\n", sc->sc_flags));
   1309 #ifdef DIAGNOSTIC
   1310 		gusvocintrcnt++;
   1311 #endif
   1312 		retval += gus_voice_intr(sc);
   1313 	}
   1314 	if (retval)
   1315 		return 1;
   1316 	return retval;
   1317 }
   1318 
   1319 int gus_bufcnt[GUS_MEM_FOR_BUFFERS / GUS_BUFFER_MULTIPLE];
   1320 int gus_restart;				/* how many restarts? */
   1321 int gus_stops;				/* how many times did voice stop? */
   1322 int gus_falsestops;			/* stopped but not done? */
   1323 int gus_continues;
   1324 
   1325 struct playcont {
   1326 	struct timeval tv;
   1327 	u_int playbuf;
   1328 	u_int dmabuf;
   1329 	u_char bufcnt;
   1330 	u_char vaction;
   1331 	u_char voccntl;
   1332 	u_char volcntl;
   1333 	u_long curaddr;
   1334 	u_long endaddr;
   1335 } playstats[NDMARECS];
   1336 
   1337 int playcntr;
   1338 
   1339 STATIC void
   1340 gus_dmaout_timeout(arg)
   1341      void *arg;
   1342 {
   1343     register struct gus_softc *sc = arg;
   1344     register int port = sc->sc_iobase;
   1345     int s;
   1346 
   1347     printf("%s: dmaout timeout\n", sc->sc_dev.dv_xname);
   1348     /*
   1349      * Stop any DMA.
   1350      */
   1351 
   1352     s = splgus();
   1353     SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   1354     outb(sc->sc_iobase+GUS_DATA_HIGH, 0);
   1355 
   1356 #if 0
   1357     /* XXX we will dmadone below? */
   1358     isa_dmaabort(sc->sc_dev.dv_parent, sc->sc_drq);
   1359 #endif
   1360 
   1361     gus_dmaout_dointr(sc);
   1362     splx(s);
   1363 }
   1364 
   1365 
   1366 /*
   1367  * Service DMA interrupts.  This routine will only get called if we're doing
   1368  * a DMA transfer for playback/record requests from the audio layer.
   1369  */
   1370 
   1371 STATIC int
   1372 gus_dmaout_intr(sc)
   1373 	struct gus_softc *sc;
   1374 {
   1375 	register int port = sc->sc_iobase;
   1376 
   1377 	/*
   1378 	 * If we got a DMA transfer complete from the GUS DRAM, then deal
   1379 	 * with it.
   1380 	 */
   1381 
   1382 	SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   1383  	if (inb(port+GUS_DATA_HIGH) & GUSMASK_DMA_IRQPEND) {
   1384 	    untimeout(gus_dmaout_timeout, sc);
   1385 	    gus_dmaout_dointr(sc);
   1386 	    return 1;
   1387 	}
   1388 	return 0;
   1389 }
   1390 
   1391 STATIC void
   1392 gus_dmaout_dointr(sc)
   1393 	struct gus_softc *sc;
   1394 {
   1395 	register int port = sc->sc_iobase;
   1396 
   1397 	/* sc->sc_dmaoutcnt - 1 because DMA controller counts from zero?. */
   1398 	isa_dmadone(sc->sc_dev.dv_parent, sc->sc_drq);
   1399 	sc->sc_flags &= ~GUS_DMAOUT_ACTIVE;  /* pending DMA is done */
   1400 	DMAPRINTF(("gus_dmaout_dointr %d @ %x\n", sc->sc_dmaoutcnt,
   1401 		   sc->sc_dmaoutaddr));
   1402 
   1403 	/*
   1404 	 * to prevent clicking, we need to copy last sample
   1405 	 * from last buffer to scratch area just before beginning of
   1406 	 * buffer.  However, if we're doing formats that are converted by
   1407 	 * the card during the DMA process, we need to pick up the converted
   1408 	 * byte rather than the one we have in memory.
   1409 	 */
   1410 	if (sc->sc_dmabuf == sc->sc_nbufs - 1) {
   1411 	  register int i;
   1412 	  switch (sc->sc_encoding) {
   1413 	  case AUDIO_ENCODING_LINEAR_LE:
   1414 	  case AUDIO_ENCODING_ULINEAR_LE:
   1415 	    if (sc->sc_precision == 8)
   1416 	      goto byte;
   1417 	    /* we have the native format */
   1418 	    for (i = 1; i <= 2; i++)
   1419 	      guspoke(port, sc->sc_gusaddr -
   1420 		      (sc->sc_nbufs - 1) * sc->sc_chanblocksize - i,
   1421 		      sc->sc_dmaoutaddr[sc->sc_dmaoutcnt-i]);
   1422 	    break;
   1423 	  case AUDIO_ENCODING_ULAW:
   1424 	  byte:
   1425 	    /* we need to fetch the translated byte, then stuff it. */
   1426 	    guspoke(port, sc->sc_gusaddr -
   1427 		    (sc->sc_nbufs - 1) * sc->sc_chanblocksize - 1,
   1428 		    guspeek(port,
   1429 			    sc->sc_gusaddr + sc->sc_chanblocksize - 1));
   1430 	    break;
   1431 	  }
   1432 	}
   1433 	/*
   1434 	 * If this is the first half of stereo, "ignore" this one
   1435 	 * and copy out the second half.
   1436 	 */
   1437 	if (sc->sc_dmaoutintr == stereo_dmaintr) {
   1438 	    (*sc->sc_dmaoutintr)(sc->sc_outarg);
   1439 	    return;
   1440 	}
   1441 	/*
   1442 	 * If the voice is stopped, then start it.  Reset the loop
   1443 	 * and roll bits.  Call the audio layer routine, since if
   1444 	 * we're starting a stopped voice, that means that the next
   1445 	 * buffer can be filled
   1446 	 */
   1447 
   1448 	sc->sc_flags &= ~GUS_LOCKED;
   1449 	if (sc->sc_voc[GUS_VOICE_LEFT].voccntl &
   1450 	    GUSMASK_VOICE_STOPPED) {
   1451 	    if (sc->sc_flags & GUS_PLAYING) {
   1452 		printf("%s: playing yet stopped?\n", sc->sc_dev.dv_xname);
   1453 	    }
   1454 	    sc->sc_bufcnt++; /* another yet to be played */
   1455 	    gus_start_playing(sc, sc->sc_dmabuf);
   1456 	    gus_restart++;
   1457 	} else {
   1458 	    /*
   1459 	     * set the sound action based on which buffer we
   1460 	     * just transferred.  If we just transferred buffer 0
   1461 	     * we want the sound to loop when it gets to the nth
   1462 	     * buffer; if we just transferred
   1463 	     * any other buffer, we want the sound to roll over
   1464 	     * at least one more time.  The voice interrupt
   1465 	     * handlers will take care of accounting &
   1466 	     * setting control bits if it's not caught up to us
   1467 	     * yet.
   1468 	     */
   1469 	    if (++sc->sc_bufcnt == 2) {
   1470 		/*
   1471 		 * XXX
   1472 		 * If we're too slow in reaction here,
   1473 		 * the voice could be just approaching the
   1474 		 * end of its run.  It should be set to stop,
   1475 		 * so these adjustments might not DTRT.
   1476 		 */
   1477 		if (sc->sc_dmabuf == 0 &&
   1478 		    sc->sc_playbuf == sc->sc_nbufs - 1) {
   1479 		    /* player is just at the last buf, we're at the
   1480 		       first.  Turn on looping, turn off rolling. */
   1481 		    sc->sc_voc[GUS_VOICE_LEFT].voccntl |= GUSMASK_LOOP_ENABLE;
   1482 		    sc->sc_voc[GUS_VOICE_LEFT].volcntl &= ~GUSMASK_VOICE_ROLL;
   1483 		    playstats[playcntr].vaction = 3;
   1484 		} else {
   1485 		    /* player is at previous buf:
   1486 		       turn on rolling, turn off looping */
   1487 		    sc->sc_voc[GUS_VOICE_LEFT].voccntl &= ~GUSMASK_LOOP_ENABLE;
   1488 		    sc->sc_voc[GUS_VOICE_LEFT].volcntl |= GUSMASK_VOICE_ROLL;
   1489 		    playstats[playcntr].vaction = 4;
   1490 		}
   1491 #ifdef GUSPLAYDEBUG
   1492 		if (gusstats) {
   1493 		  microtime(&playstats[playcntr].tv);
   1494 		  playstats[playcntr].endaddr = sc->sc_voc[GUS_VOICE_LEFT].end_addr;
   1495 		  playstats[playcntr].voccntl = sc->sc_voc[GUS_VOICE_LEFT].voccntl;
   1496 		  playstats[playcntr].volcntl = sc->sc_voc[GUS_VOICE_LEFT].volcntl;
   1497 		  playstats[playcntr].playbuf = sc->sc_playbuf;
   1498 		  playstats[playcntr].dmabuf = sc->sc_dmabuf;
   1499 		  playstats[playcntr].bufcnt = sc->sc_bufcnt;
   1500 		  playstats[playcntr].curaddr = gus_get_curaddr(sc, GUS_VOICE_LEFT);
   1501 		  playcntr = ++playcntr % NDMARECS;
   1502 		}
   1503 #endif
   1504 		outb(port+GUS_VOICE_SELECT, GUS_VOICE_LEFT);
   1505 		SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   1506 		outb(port+GUS_DATA_HIGH, sc->sc_voc[GUS_VOICE_LEFT].voccntl);
   1507 		SELECT_GUS_REG(port, GUSREG_VOLUME_CONTROL);
   1508 		outb(port+GUS_DATA_HIGH, sc->sc_voc[GUS_VOICE_LEFT].volcntl);
   1509 	    }
   1510 	}
   1511 	gus_bufcnt[sc->sc_bufcnt-1]++;
   1512 	/*
   1513 	 * flip to the next DMA buffer
   1514 	 */
   1515 
   1516 	sc->sc_dmabuf = ++sc->sc_dmabuf % sc->sc_nbufs;
   1517 	/*
   1518 	 * See comments below about DMA admission control strategy.
   1519 	 * We can call the upper level here if we have an
   1520 	 * idle buffer (not currently playing) to DMA into.
   1521 	 */
   1522 	if (sc->sc_dmaoutintr && sc->sc_bufcnt < sc->sc_nbufs) {
   1523 	    /* clean out to prevent double calls */
   1524 	    void (*pfunc) __P((void *)) = sc->sc_dmaoutintr;
   1525 	    void *arg = sc->sc_outarg;
   1526 
   1527 	    sc->sc_outarg = 0;
   1528 	    sc->sc_dmaoutintr = 0;
   1529 	    (*pfunc)(arg);
   1530 	}
   1531 }
   1532 
   1533 /*
   1534  * Service voice interrupts
   1535  */
   1536 
   1537 STATIC int
   1538 gus_voice_intr(sc)
   1539 	struct gus_softc *sc;
   1540 {
   1541 	register int port = sc->sc_iobase;
   1542 	int ignore = 0, voice, rval = 0;
   1543 	unsigned char intr, status;
   1544 
   1545 	/*
   1546 	 * The point of this may not be obvious at first.  A voice can
   1547 	 * interrupt more than once; according to the GUS SDK we are supposed
   1548 	 * to ignore multiple interrupts for the same voice.
   1549 	 */
   1550 
   1551 	while(1) {
   1552 		SELECT_GUS_REG(port, GUSREG_IRQ_STATUS);
   1553 		intr = inb(port+GUS_DATA_HIGH);
   1554 
   1555 		if ((intr & (GUSMASK_WIRQ_VOLUME | GUSMASK_WIRQ_VOICE))
   1556 			== (GUSMASK_WIRQ_VOLUME | GUSMASK_WIRQ_VOICE))
   1557 			/*
   1558 			 * No more interrupts, time to return
   1559 			 */
   1560 		 	return rval;
   1561 
   1562 		if ((intr & GUSMASK_WIRQ_VOICE) == 0) {
   1563 
   1564 		    /*
   1565 		     * We've got a voice interrupt.  Ignore previous
   1566 		     * interrupts by the same voice.
   1567 		     */
   1568 
   1569 		    rval = 1;
   1570 		    voice = intr & GUSMASK_WIRQ_VOICEMASK;
   1571 
   1572 		    if ((1 << voice) & ignore)
   1573 			break;
   1574 
   1575 		    ignore |= 1 << voice;
   1576 
   1577 		    /*
   1578 		     * If the voice is stopped, then force it to stop
   1579 		     * (this stops it from continuously generating IRQs)
   1580 		     */
   1581 
   1582 		    SELECT_GUS_REG(port, GUSREG_VOICE_CNTL+0x80);
   1583 		    status = inb(port+GUS_DATA_HIGH);
   1584 		    if (status & GUSMASK_VOICE_STOPPED) {
   1585 			if (voice != GUS_VOICE_LEFT) {
   1586 			    DMAPRINTF(("%s: spurious voice %d stop?\n",
   1587 				       sc->sc_dev.dv_xname, voice));
   1588 			    gus_stop_voice(sc, voice, 0);
   1589 			    continue;
   1590 			}
   1591 			gus_stop_voice(sc, voice, 1);
   1592 			/* also kill right voice */
   1593 			gus_stop_voice(sc, GUS_VOICE_RIGHT, 0);
   1594 			sc->sc_bufcnt--; /* it finished a buffer */
   1595 			if (sc->sc_bufcnt > 0) {
   1596 			    /*
   1597 			     * probably a race to get here: the voice
   1598 			     * stopped while the DMA code was just trying to
   1599 			     * get the next buffer in place.
   1600 			     * Start the voice again.
   1601 			     */
   1602 			    printf("%s: stopped voice not drained? (%x)\n",
   1603 				   sc->sc_dev.dv_xname, sc->sc_bufcnt);
   1604 			    gus_falsestops++;
   1605 
   1606 			    sc->sc_playbuf = ++sc->sc_playbuf % sc->sc_nbufs;
   1607 			    gus_start_playing(sc, sc->sc_playbuf);
   1608 			} else if (sc->sc_bufcnt < 0) {
   1609 #ifdef DDB
   1610 			    printf("%s: negative bufcnt in stopped voice\n",
   1611 				   sc->sc_dev.dv_xname);
   1612 			    Debugger();
   1613 #else
   1614 			    panic("%s: negative bufcnt in stopped voice",
   1615 				  sc->sc_dev.dv_xname);
   1616 #endif
   1617 			} else {
   1618 			    sc->sc_playbuf = -1; /* none are active */
   1619 			    gus_stops++;
   1620 			}
   1621 			/* fall through to callback and admit another
   1622 			   buffer.... */
   1623 		    } else if (sc->sc_bufcnt != 0) {
   1624 			/*
   1625 			 * This should always be taken if the voice
   1626 			 * is not stopped.
   1627 			 */
   1628 			gus_continues++;
   1629 			if (gus_continue_playing(sc, voice)) {
   1630 				/*
   1631 				 * we shouldn't have continued--active DMA
   1632 				 * is in the way in the ring, for
   1633 				 * some as-yet undebugged reason.
   1634 				 */
   1635 				gus_stop_voice(sc, GUS_VOICE_LEFT, 1);
   1636 				/* also kill right voice */
   1637 				gus_stop_voice(sc, GUS_VOICE_RIGHT, 0);
   1638 				sc->sc_playbuf = -1;
   1639 				gus_stops++;
   1640 			}
   1641 		    }
   1642 		    /*
   1643 		     * call the upper level to send on down another
   1644 		     * block. We do admission rate control as follows:
   1645 		     *
   1646 		     * When starting up output (in the first N
   1647 		     * blocks), call the upper layer after the DMA is
   1648 		     * complete (see above in gus_dmaout_intr()).
   1649 		     *
   1650 		     * When output is already in progress and we have
   1651 		     * no more GUS buffers to use for DMA, the DMA
   1652 		     * output routines do not call the upper layer.
   1653 		     * Instead, we call the DMA completion routine
   1654 		     * here, after the voice interrupts indicating
   1655 		     * that it's finished with a buffer.
   1656 		     *
   1657 		     * However, don't call anything here if the DMA
   1658 		     * output flag is set, (which shouldn't happen)
   1659 		     * because we'll squish somebody else's DMA if
   1660 		     * that's the case.  When DMA is done, it will
   1661 		     * call back if there is a spare buffer.
   1662 		     */
   1663 		    if (sc->sc_dmaoutintr && !(sc->sc_flags & GUS_LOCKED)) {
   1664 			if (sc->sc_dmaoutintr == stereo_dmaintr)
   1665 			    printf("gusdmaout botch?\n");
   1666 			else {
   1667 			    /* clean out to avoid double calls */
   1668 			    void (*pfunc) __P((void *)) = sc->sc_dmaoutintr;
   1669 			    void *arg = sc->sc_outarg;
   1670 
   1671 			    sc->sc_outarg = 0;
   1672 			    sc->sc_dmaoutintr = 0;
   1673 			    (*pfunc)(arg);
   1674 			}
   1675 		    }
   1676 		}
   1677 
   1678 		/*
   1679 		 * Ignore other interrupts for now
   1680 		 */
   1681 	}
   1682 	return 0;
   1683 }
   1684 
   1685 STATIC void
   1686 gus_start_playing(sc, bufno)
   1687 struct gus_softc *sc;
   1688 int bufno;
   1689 {
   1690     register int port = sc->sc_iobase;
   1691     /*
   1692      * Start the voices playing, with buffer BUFNO.
   1693      */
   1694 
   1695     /*
   1696      * Loop or roll if we have buffers ready.
   1697      */
   1698 
   1699     if (sc->sc_bufcnt == 1) {
   1700 	sc->sc_voc[GUS_VOICE_LEFT].voccntl &= ~(GUSMASK_LOOP_ENABLE);
   1701 	sc->sc_voc[GUS_VOICE_LEFT].volcntl &= ~(GUSMASK_VOICE_ROLL);
   1702     } else {
   1703 	if (bufno == sc->sc_nbufs - 1) {
   1704 	    sc->sc_voc[GUS_VOICE_LEFT].voccntl |= GUSMASK_LOOP_ENABLE;
   1705 	    sc->sc_voc[GUS_VOICE_LEFT].volcntl &= ~(GUSMASK_VOICE_ROLL);
   1706 	} else {
   1707 	    sc->sc_voc[GUS_VOICE_LEFT].voccntl &= ~GUSMASK_LOOP_ENABLE;
   1708 	    sc->sc_voc[GUS_VOICE_LEFT].volcntl |= GUSMASK_VOICE_ROLL;
   1709 	}
   1710     }
   1711 
   1712     outb(port+GUS_VOICE_SELECT, GUS_VOICE_LEFT);
   1713 
   1714     SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   1715     outb(port+GUS_DATA_HIGH, sc->sc_voc[GUS_VOICE_LEFT].voccntl);
   1716 
   1717     SELECT_GUS_REG(port, GUSREG_VOLUME_CONTROL);
   1718     outb(port+GUS_DATA_HIGH, sc->sc_voc[GUS_VOICE_LEFT].volcntl);
   1719 
   1720     sc->sc_voc[GUS_VOICE_LEFT].current_addr =
   1721 	GUS_MEM_OFFSET + sc->sc_chanblocksize * bufno;
   1722     sc->sc_voc[GUS_VOICE_LEFT].end_addr =
   1723 	sc->sc_voc[GUS_VOICE_LEFT].current_addr + sc->sc_chanblocksize - 1;
   1724     sc->sc_voc[GUS_VOICE_RIGHT].current_addr =
   1725 	sc->sc_voc[GUS_VOICE_LEFT].current_addr +
   1726 	(gus_dostereo && sc->sc_channels == 2 ? GUS_LEFT_RIGHT_OFFSET : 0);
   1727     /*
   1728      * set up right channel to just loop forever, no interrupts,
   1729      * starting at the buffer we just filled.  We'll feed it data
   1730      * at the same time as left channel.
   1731      */
   1732     sc->sc_voc[GUS_VOICE_RIGHT].voccntl |= GUSMASK_LOOP_ENABLE;
   1733     sc->sc_voc[GUS_VOICE_RIGHT].volcntl &= ~(GUSMASK_VOICE_ROLL);
   1734 
   1735 #ifdef GUSPLAYDEBUG
   1736     if (gusstats) {
   1737       microtime(&playstats[playcntr].tv);
   1738       playstats[playcntr].curaddr = sc->sc_voc[GUS_VOICE_LEFT].current_addr;
   1739 
   1740       playstats[playcntr].voccntl = sc->sc_voc[GUS_VOICE_LEFT].voccntl;
   1741       playstats[playcntr].volcntl = sc->sc_voc[GUS_VOICE_LEFT].volcntl;
   1742       playstats[playcntr].endaddr = sc->sc_voc[GUS_VOICE_LEFT].end_addr;
   1743       playstats[playcntr].playbuf = bufno;
   1744       playstats[playcntr].dmabuf = sc->sc_dmabuf;
   1745       playstats[playcntr].bufcnt = sc->sc_bufcnt;
   1746       playstats[playcntr].vaction = 5;
   1747       playcntr = ++playcntr % NDMARECS;
   1748     }
   1749 #endif
   1750 
   1751     outb(port+GUS_VOICE_SELECT, GUS_VOICE_RIGHT);
   1752     SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   1753     outb(port+GUS_DATA_HIGH, sc->sc_voc[GUS_VOICE_RIGHT].voccntl);
   1754     SELECT_GUS_REG(port, GUSREG_VOLUME_CONTROL);
   1755     outb(port+GUS_DATA_HIGH, sc->sc_voc[GUS_VOICE_RIGHT].volcntl);
   1756 
   1757     gus_start_voice(sc, GUS_VOICE_RIGHT, 0);
   1758     gus_start_voice(sc, GUS_VOICE_LEFT, 1);
   1759     if (sc->sc_playbuf == -1)
   1760 	/* mark start of playing */
   1761 	sc->sc_playbuf = bufno;
   1762 }
   1763 
   1764 STATIC int
   1765 gus_continue_playing(sc, voice)
   1766 register struct gus_softc *sc;
   1767 int voice;
   1768 {
   1769     register int port = sc->sc_iobase;
   1770 
   1771     /*
   1772      * stop this voice from interrupting while we work.
   1773      */
   1774 
   1775     SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   1776     outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].voccntl & ~(GUSMASK_VOICE_IRQ));
   1777 
   1778     /*
   1779      * update playbuf to point to the buffer the hardware just started
   1780      * playing
   1781      */
   1782     sc->sc_playbuf = ++sc->sc_playbuf % sc->sc_nbufs;
   1783 
   1784     /*
   1785      * account for buffer just finished
   1786      */
   1787     if (--sc->sc_bufcnt == 0) {
   1788 	DPRINTF(("gus: bufcnt 0 on continuing voice?\n"));
   1789     }
   1790     if (sc->sc_playbuf == sc->sc_dmabuf && (sc->sc_flags & GUS_LOCKED)) {
   1791 	printf("%s: continue into active dmabuf?\n", sc->sc_dev.dv_xname);
   1792 	return 1;
   1793     }
   1794 
   1795     /*
   1796      * Select the end of the buffer based on the currently active
   1797      * buffer, [plus extra contiguous buffers (if ready)].
   1798      */
   1799 
   1800     /*
   1801      * set endpoint at end of buffer we just started playing.
   1802      *
   1803      * The total gets -1 because end addrs are one less than you might
   1804      * think (the end_addr is the address of the last sample to play)
   1805      */
   1806     gus_set_endaddr(sc, voice, GUS_MEM_OFFSET +
   1807 		    sc->sc_chanblocksize * (sc->sc_playbuf + 1) - 1);
   1808 
   1809     if (sc->sc_bufcnt < 2) {
   1810 	/*
   1811 	 * Clear out the loop and roll flags, and rotate the currently
   1812 	 * playing buffer.  That way, if we don't manage to get more
   1813 	 * data before this buffer finishes, we'll just stop.
   1814 	 */
   1815 	sc->sc_voc[voice].voccntl &= ~GUSMASK_LOOP_ENABLE;
   1816 	sc->sc_voc[voice].volcntl &= ~GUSMASK_VOICE_ROLL;
   1817 	playstats[playcntr].vaction = 0;
   1818     } else {
   1819 	/*
   1820 	 * We have some buffers to play.  set LOOP if we're on the
   1821 	 * last buffer in the ring, otherwise set ROLL.
   1822 	 */
   1823 	if (sc->sc_playbuf == sc->sc_nbufs - 1) {
   1824 	    sc->sc_voc[voice].voccntl |= GUSMASK_LOOP_ENABLE;
   1825 	    sc->sc_voc[voice].volcntl &= ~GUSMASK_VOICE_ROLL;
   1826 	    playstats[playcntr].vaction = 1;
   1827 	} else {
   1828 	    sc->sc_voc[voice].voccntl &= ~GUSMASK_LOOP_ENABLE;
   1829 	    sc->sc_voc[voice].volcntl |= GUSMASK_VOICE_ROLL;
   1830 	    playstats[playcntr].vaction = 2;
   1831 	}
   1832     }
   1833 #ifdef GUSPLAYDEBUG
   1834     if (gusstats) {
   1835       microtime(&playstats[playcntr].tv);
   1836       playstats[playcntr].curaddr = gus_get_curaddr(sc, voice);
   1837 
   1838       playstats[playcntr].voccntl = sc->sc_voc[voice].voccntl;
   1839       playstats[playcntr].volcntl = sc->sc_voc[voice].volcntl;
   1840       playstats[playcntr].endaddr = sc->sc_voc[voice].end_addr;
   1841       playstats[playcntr].playbuf = sc->sc_playbuf;
   1842       playstats[playcntr].dmabuf = sc->sc_dmabuf;
   1843       playstats[playcntr].bufcnt = sc->sc_bufcnt;
   1844       playcntr = ++playcntr % NDMARECS;
   1845     }
   1846 #endif
   1847 
   1848     /*
   1849      * (re-)set voice parameters.  This will reenable interrupts from this
   1850      * voice.
   1851      */
   1852 
   1853     SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   1854     outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].voccntl);
   1855     SELECT_GUS_REG(port, GUSREG_VOLUME_CONTROL);
   1856     outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].volcntl);
   1857     return 0;
   1858 }
   1859 
   1860 /*
   1861  * Send/receive data into GUS's DRAM using DMA.  Called at splgus()
   1862  */
   1863 
   1864 STATIC void
   1865 gusdmaout(sc, flags, gusaddr, buffaddr, length)
   1866 	struct gus_softc *sc;
   1867 	int flags, length;
   1868 	u_long gusaddr;
   1869 	caddr_t buffaddr;
   1870 {
   1871 	register unsigned char c = (unsigned char) flags;
   1872 	register int port = sc->sc_iobase;
   1873 
   1874 	DMAPRINTF(("gusdmaout flags=%x scflags=%x\n", flags, sc->sc_flags));
   1875 
   1876 	sc->sc_gusaddr = gusaddr;
   1877 
   1878 	/*
   1879 	 * If we're using a 16 bit DMA channel, we have to jump through some
   1880 	 * extra hoops; this includes translating the DRAM address a bit
   1881 	 */
   1882 
   1883 	if (sc->sc_drq >= 4) {
   1884 		c |= GUSMASK_DMA_WIDTH;
   1885 		gusaddr = convert_to_16bit(gusaddr);
   1886 	}
   1887 
   1888 	/*
   1889 	 * Add flag bits that we always set - fast DMA, enable IRQ
   1890 	 */
   1891 
   1892 	c |= GUSMASK_DMA_ENABLE | GUSMASK_DMA_R0 | GUSMASK_DMA_IRQ;
   1893 
   1894 	/*
   1895 	 * Make sure the GUS _isn't_ setup for DMA
   1896 	 */
   1897 
   1898  	SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   1899 	outb(port+GUS_DATA_HIGH, 0);
   1900 
   1901 	/*
   1902 	 * Tell the PC DMA controller to start doing DMA
   1903 	 */
   1904 
   1905 	sc->sc_dmaoutaddr = (u_char *) buffaddr;
   1906 	sc->sc_dmaoutcnt = length;
   1907 	isa_dmastart(sc->sc_dev.dv_parent, sc->sc_drq, buffaddr, length,
   1908 	    NULL, DMAMODE_WRITE, BUS_DMA_NOWAIT);
   1909 
   1910 	/*
   1911 	 * Set up DMA address - use the upper 16 bits ONLY
   1912 	 */
   1913 
   1914 	sc->sc_flags |= GUS_DMAOUT_ACTIVE;
   1915 
   1916  	SELECT_GUS_REG(port, GUSREG_DMA_START);
   1917  	outw(port+GUS_DATA_LOW, (int) (gusaddr >> 4));
   1918 
   1919  	/*
   1920  	 * Tell the GUS to start doing DMA
   1921  	 */
   1922 
   1923  	SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   1924 	outb(port+GUS_DATA_HIGH, c);
   1925 
   1926 	/*
   1927 	 * XXX If we don't finish in one second, give up...
   1928 	 */
   1929 	untimeout(gus_dmaout_timeout, sc); /* flush old one, if there is one */
   1930 	timeout(gus_dmaout_timeout, sc, hz);
   1931 }
   1932 
   1933 /*
   1934  * Start a voice playing on the GUS.  Called from interrupt handler at
   1935  * splgus().
   1936  */
   1937 
   1938 STATIC void
   1939 gus_start_voice(sc, voice, intrs)
   1940 	struct gus_softc *sc;
   1941 	int voice;
   1942 	int intrs;
   1943 {
   1944 	register int port = sc->sc_iobase;
   1945 	u_long start;
   1946 	u_long current;
   1947 	u_long end;
   1948 
   1949 	/*
   1950 	 * Pick all the values for the voice out of the gus_voice struct
   1951 	 * and use those to program the voice
   1952 	 */
   1953 
   1954  	start = sc->sc_voc[voice].start_addr;
   1955  	current = sc->sc_voc[voice].current_addr;
   1956  	end = sc->sc_voc[voice].end_addr;
   1957 
   1958  	/*
   1959 	 * If we're using 16 bit data, mangle the addresses a bit
   1960 	 */
   1961 
   1962 	if (sc->sc_voc[voice].voccntl & GUSMASK_DATA_SIZE16) {
   1963 	        /* -1 on start so that we get onto sample boundary--other
   1964 		   code always sets it for 1-byte rollover protection */
   1965 		start = convert_to_16bit(start-1);
   1966 		current = convert_to_16bit(current);
   1967 		end = convert_to_16bit(end);
   1968 	}
   1969 
   1970 	/*
   1971 	 * Select the voice we want to use, and program the data addresses
   1972 	 */
   1973 
   1974 	outb(port+GUS_VOICE_SELECT, (unsigned char) voice);
   1975 
   1976 	SELECT_GUS_REG(port, GUSREG_START_ADDR_HIGH);
   1977 	outw(port+GUS_DATA_LOW, ADDR_HIGH(start));
   1978 	SELECT_GUS_REG(port, GUSREG_START_ADDR_LOW);
   1979 	outw(port+GUS_DATA_LOW, ADDR_LOW(start));
   1980 
   1981 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_HIGH);
   1982 	outw(port+GUS_DATA_LOW, ADDR_HIGH(current));
   1983 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_LOW);
   1984 	outw(port+GUS_DATA_LOW, ADDR_LOW(current));
   1985 
   1986 	SELECT_GUS_REG(port, GUSREG_END_ADDR_HIGH);
   1987 	outw(port+GUS_DATA_LOW, ADDR_HIGH(end));
   1988 	SELECT_GUS_REG(port, GUSREG_END_ADDR_LOW);
   1989 	outw(port+GUS_DATA_LOW, ADDR_LOW(end));
   1990 
   1991 	/*
   1992 	 * (maybe) enable interrupts, disable voice stopping
   1993 	 */
   1994 
   1995 	if (intrs) {
   1996 		sc->sc_flags |= GUS_PLAYING; /* playing is about to start */
   1997 		sc->sc_voc[voice].voccntl |= GUSMASK_VOICE_IRQ;
   1998 		DMAPRINTF(("gus voice playing=%x\n", sc->sc_flags));
   1999 	} else
   2000 		sc->sc_voc[voice].voccntl &= ~GUSMASK_VOICE_IRQ;
   2001 	sc->sc_voc[voice].voccntl &= ~(GUSMASK_VOICE_STOPPED |
   2002 		GUSMASK_STOP_VOICE);
   2003 
   2004 	/*
   2005 	 * Tell the GUS about it.  Note that we're doing volume ramping here
   2006 	 * from 0 up to the set volume to help reduce clicks.
   2007 	 */
   2008 
   2009 	SELECT_GUS_REG(port, GUSREG_START_VOLUME);
   2010 	outb(port+GUS_DATA_HIGH, 0x00);
   2011 	SELECT_GUS_REG(port, GUSREG_END_VOLUME);
   2012 	outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].current_volume >> 4);
   2013 	SELECT_GUS_REG(port, GUSREG_CUR_VOLUME);
   2014 	outw(port+GUS_DATA_LOW, 0x00);
   2015 	SELECT_GUS_REG(port, GUSREG_VOLUME_RATE);
   2016 	outb(port+GUS_DATA_HIGH, 63);
   2017 
   2018 	SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   2019 	outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].voccntl);
   2020 	SELECT_GUS_REG(port, GUSREG_VOLUME_CONTROL);
   2021 	outb(port+GUS_DATA_HIGH, 0x00);
   2022 	delay(50);
   2023 	SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   2024 	outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].voccntl);
   2025 	SELECT_GUS_REG(port, GUSREG_VOLUME_CONTROL);
   2026 	outb(port+GUS_DATA_HIGH, 0x00);
   2027 
   2028 }
   2029 
   2030 /*
   2031  * Stop a given voice.  called at splgus()
   2032  */
   2033 
   2034 STATIC void
   2035 gus_stop_voice(sc, voice, intrs_too)
   2036 	struct gus_softc *sc;
   2037 	int voice;
   2038 	int intrs_too;
   2039 {
   2040 	register int port = sc->sc_iobase;
   2041 
   2042 	sc->sc_voc[voice].voccntl |= GUSMASK_VOICE_STOPPED |
   2043 		GUSMASK_STOP_VOICE;
   2044 	if (intrs_too) {
   2045 	  sc->sc_voc[voice].voccntl &= ~(GUSMASK_VOICE_IRQ);
   2046 	  /* no more DMA to do */
   2047 	  sc->sc_flags &= ~GUS_PLAYING;
   2048 	}
   2049 	DMAPRINTF(("gusintr voice notplaying=%x\n", sc->sc_flags));
   2050 
   2051 	guspoke(port, 0L, 0);
   2052 
   2053 	outb(port+GUS_VOICE_SELECT, (unsigned char) voice);
   2054 
   2055 	SELECT_GUS_REG(port, GUSREG_CUR_VOLUME);
   2056 	outw(port+GUS_DATA_LOW, 0x0000);
   2057 	SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   2058 	outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].voccntl);
   2059 	delay(100);
   2060 	SELECT_GUS_REG(port, GUSREG_CUR_VOLUME);
   2061 	outw(port+GUS_DATA_LOW, 0x0000);
   2062 	SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   2063 	outb(port+GUS_DATA_HIGH, sc->sc_voc[voice].voccntl);
   2064 
   2065 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_HIGH);
   2066 	outw(port+GUS_DATA_LOW, 0x0000);
   2067 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_LOW);
   2068 	outw(port+GUS_DATA_LOW, 0x0000);
   2069 
   2070 }
   2071 
   2072 
   2073 /*
   2074  * Set the volume of a given voice.  Called at splgus().
   2075  */
   2076 STATIC void
   2077 gus_set_volume(sc, voice, volume)
   2078 	struct gus_softc *sc;
   2079 	int voice, volume;
   2080 {
   2081 	register int port = sc->sc_iobase;
   2082 	unsigned int gusvol;
   2083 
   2084 	gusvol = gus_log_volumes[volume < 512 ? volume : 511];
   2085 
   2086 	sc->sc_voc[voice].current_volume = gusvol;
   2087 
   2088 	outb(port+GUS_VOICE_SELECT, (unsigned char) voice);
   2089 
   2090 	SELECT_GUS_REG(port, GUSREG_START_VOLUME);
   2091 	outb(port+GUS_DATA_HIGH, (unsigned char) (gusvol >> 4));
   2092 
   2093 	SELECT_GUS_REG(port, GUSREG_END_VOLUME);
   2094 	outb(port+GUS_DATA_HIGH, (unsigned char) (gusvol >> 4));
   2095 
   2096 	SELECT_GUS_REG(port, GUSREG_CUR_VOLUME);
   2097 	outw(port+GUS_DATA_LOW, gusvol << 4);
   2098 	delay(500);
   2099 	outw(port+GUS_DATA_LOW, gusvol << 4);
   2100 
   2101 }
   2102 
   2103 /*
   2104  * Interface to the audio layer.
   2105  */
   2106 
   2107 int
   2108 gusmax_set_params(addr, mode, p, q)
   2109 	void *addr;
   2110 	int mode;
   2111 	struct audio_params *p, *q;
   2112 {
   2113 	register struct ad1848_softc *ac = addr;
   2114 	register struct gus_softc *sc = ac->parent;
   2115 	int error;
   2116 
   2117 	error = ad1848_set_params(ac, mode, p, q);
   2118 	if (error)
   2119 		return error;
   2120 	error = gus_set_params(sc, mode, p, q);
   2121 	p->sw_code = mode == AUMODE_RECORD ? gus_compress : gusmax_expand;
   2122 	return error;
   2123 }
   2124 
   2125 int
   2126 gus_set_params(addr, mode, p, q)
   2127 	void *addr;
   2128 	int mode;
   2129 	struct audio_params *p, *q;
   2130 {
   2131 	register struct gus_softc *sc = addr;
   2132 	int error;
   2133 
   2134 	error = gus_set_io_params(sc, p);
   2135 	if (error)
   2136 		return error;
   2137 	if (p->sample_rate > gus_max_frequency[sc->sc_voices - GUS_MIN_VOICES])
   2138 		p->sample_rate = gus_max_frequency[sc->sc_voices - GUS_MIN_VOICES];
   2139 	if (mode == AUMODE_RECORD)
   2140 		sc->sc_irate = p->sample_rate;
   2141 	else
   2142 		sc->sc_orate = p->sample_rate;
   2143 
   2144 	p->sw_code = mode == AUMODE_RECORD ? gus_compress : gus_expand;
   2145 
   2146 	/* Update setting for the other mode. */
   2147 	q->encoding = p->encoding;
   2148 	q->channels = p->channels;
   2149 	q->precision = p->precision;
   2150 	return 0;
   2151 }
   2152 
   2153 int
   2154 gus_set_io_params(sc, p)
   2155 	struct gus_softc *sc;
   2156 	struct audio_params *p;
   2157 {
   2158 	int s;
   2159 
   2160 	switch (p->encoding) {
   2161 	case AUDIO_ENCODING_ULAW:
   2162 	case AUDIO_ENCODING_LINEAR_LE:
   2163 	case AUDIO_ENCODING_ULINEAR_LE:
   2164 		break;
   2165 	default:
   2166 		return (EINVAL);
   2167 	}
   2168 
   2169 	s = splaudio();
   2170 
   2171 	if (p->precision == 8) {
   2172 		sc->sc_voc[GUS_VOICE_LEFT].voccntl &= ~GUSMASK_DATA_SIZE16;
   2173 		sc->sc_voc[GUS_VOICE_RIGHT].voccntl &= ~GUSMASK_DATA_SIZE16;
   2174 	} else {
   2175 		sc->sc_voc[GUS_VOICE_LEFT].voccntl |= GUSMASK_DATA_SIZE16;
   2176 		sc->sc_voc[GUS_VOICE_RIGHT].voccntl |= GUSMASK_DATA_SIZE16;
   2177 	}
   2178 
   2179 	sc->sc_encoding = p->encoding;
   2180 	sc->sc_precision = p->precision;
   2181 	sc->sc_channels = p->channels;
   2182 
   2183 	splx(s);
   2184 
   2185 	return 0;
   2186 }
   2187 
   2188 /*
   2189  * Interface to the audio layer - set the blocksize to the correct number
   2190  * of units
   2191  */
   2192 
   2193 int
   2194 gusmax_round_blocksize(addr, blocksize)
   2195 	void * addr;
   2196 	int blocksize;
   2197 {
   2198 	register struct ad1848_softc *ac = addr;
   2199 	register struct gus_softc *sc = ac->parent;
   2200 
   2201 /*	blocksize = ad1848_round_blocksize(ac, blocksize);*/
   2202 	return gus_round_blocksize(sc, blocksize);
   2203 }
   2204 
   2205 int
   2206 gus_round_blocksize(addr, blocksize)
   2207 	void * addr;
   2208 	int blocksize;
   2209 {
   2210 	register struct gus_softc *sc = addr;
   2211 
   2212 	DPRINTF(("gus_round_blocksize called\n"));
   2213 
   2214 	if (sc->sc_encoding == AUDIO_ENCODING_ULAW && blocksize > 32768)
   2215 		blocksize = 32768;
   2216 	else if (blocksize > 65536)
   2217 		blocksize = 65536;
   2218 
   2219 	if ((blocksize % GUS_BUFFER_MULTIPLE) != 0)
   2220 		blocksize = (blocksize / GUS_BUFFER_MULTIPLE + 1) *
   2221 			GUS_BUFFER_MULTIPLE;
   2222 
   2223 	/* set up temporary buffer to hold the deinterleave, if necessary
   2224 	   for stereo output */
   2225 	if (sc->sc_deintr_buf) {
   2226 		FREE(sc->sc_deintr_buf, M_DEVBUF);
   2227 		sc->sc_deintr_buf = NULL;
   2228 	}
   2229 	MALLOC(sc->sc_deintr_buf, void *, blocksize>>1, M_DEVBUF, M_WAITOK);
   2230 
   2231 	sc->sc_blocksize = blocksize;
   2232 	/* multi-buffering not quite working yet. */
   2233 	sc->sc_nbufs = /*GUS_MEM_FOR_BUFFERS / blocksize*/ 2;
   2234 
   2235 	gus_set_chan_addrs(sc);
   2236 
   2237 	return blocksize;
   2238 }
   2239 
   2240 int
   2241 gus_get_out_gain(addr)
   2242 	caddr_t addr;
   2243 {
   2244 	register struct gus_softc *sc = (struct gus_softc *) addr;
   2245 
   2246 	DPRINTF(("gus_get_out_gain called\n"));
   2247 	return sc->sc_ogain / 2;
   2248 }
   2249 
   2250 STATIC inline void gus_set_voices(sc, voices)
   2251 struct gus_softc *sc;
   2252 int voices;
   2253 {
   2254 	register int port = sc->sc_iobase;
   2255 	/*
   2256 	 * Select the active number of voices
   2257 	 */
   2258 
   2259 	SELECT_GUS_REG(port, GUSREG_ACTIVE_VOICES);
   2260 	outb(port+GUS_DATA_HIGH, (voices-1) | 0xc0);
   2261 
   2262 	sc->sc_voices = voices;
   2263 }
   2264 
   2265 /*
   2266  * Actually set the settings of various values on the card
   2267  */
   2268 
   2269 int
   2270 gusmax_commit_settings(addr)
   2271 	void * addr;
   2272 {
   2273 	register struct ad1848_softc *ac = addr;
   2274 	register struct gus_softc *sc = ac->parent;
   2275 
   2276 	(void) ad1848_commit_settings(ac);
   2277 	return gus_commit_settings(sc);
   2278 }
   2279 
   2280 /*
   2281  * Commit the settings.  Called at normal IPL.
   2282  */
   2283 int
   2284 gus_commit_settings(addr)
   2285 	void * addr;
   2286 {
   2287 	register struct gus_softc *sc = addr;
   2288 	int s;
   2289 
   2290 	DPRINTF(("gus_commit_settings called (gain = %d)\n",sc->sc_ogain));
   2291 
   2292 
   2293 	s = splgus();
   2294 
   2295 	gus_set_recrate(sc, sc->sc_irate);
   2296 	gus_set_volume(sc, GUS_VOICE_LEFT, sc->sc_ogain);
   2297 	gus_set_volume(sc, GUS_VOICE_RIGHT, sc->sc_ogain);
   2298 	gus_set_samprate(sc, GUS_VOICE_LEFT, sc->sc_orate);
   2299 	gus_set_samprate(sc, GUS_VOICE_RIGHT, sc->sc_orate);
   2300 	splx(s);
   2301 	gus_set_chan_addrs(sc);
   2302 
   2303 	return 0;
   2304 }
   2305 
   2306 STATIC void
   2307 gus_set_chan_addrs(sc)
   2308 struct gus_softc *sc;
   2309 {
   2310 	/*
   2311 	 * We use sc_nbufs * blocksize bytes of storage in the on-board GUS
   2312 	 * ram.
   2313 	 * For mono, each of the sc_nbufs buffers is DMA'd to in one chunk,
   2314 	 * and both left & right channels play the same buffer.
   2315 	 *
   2316 	 * For stereo, each channel gets a contiguous half of the memory,
   2317 	 * and each has sc_nbufs buffers of size blocksize/2.
   2318 	 * Stereo data are deinterleaved in main memory before the DMA out
   2319 	 * routines are called to queue the output.
   2320 	 *
   2321 	 * The blocksize per channel is kept in sc_chanblocksize.
   2322 	 */
   2323 	if (sc->sc_channels == 2)
   2324 	    sc->sc_chanblocksize = sc->sc_blocksize/2;
   2325 	else
   2326 	    sc->sc_chanblocksize = sc->sc_blocksize;
   2327 
   2328 	sc->sc_voc[GUS_VOICE_LEFT].start_addr = GUS_MEM_OFFSET - 1;
   2329 	sc->sc_voc[GUS_VOICE_RIGHT].start_addr =
   2330 	    (gus_dostereo && sc->sc_channels == 2 ? GUS_LEFT_RIGHT_OFFSET : 0)
   2331 	      + GUS_MEM_OFFSET - 1;
   2332 	sc->sc_voc[GUS_VOICE_RIGHT].current_addr =
   2333 	    sc->sc_voc[GUS_VOICE_RIGHT].start_addr + 1;
   2334 	sc->sc_voc[GUS_VOICE_RIGHT].end_addr =
   2335 	    sc->sc_voc[GUS_VOICE_RIGHT].start_addr +
   2336 	    sc->sc_nbufs * sc->sc_chanblocksize;
   2337 
   2338 }
   2339 
   2340 /*
   2341  * Set the sample rate of the given voice.  Called at splgus().
   2342  */
   2343 
   2344 STATIC void
   2345 gus_set_samprate(sc, voice, freq)
   2346 	struct gus_softc *sc;
   2347 	int voice, freq;
   2348 {
   2349 	register int port = sc->sc_iobase;
   2350 	unsigned int fc;
   2351 	u_long temp, f = (u_long) freq;
   2352 
   2353 	/*
   2354 	 * calculate fc based on the number of active voices;
   2355 	 * we need to use longs to preserve enough bits
   2356 	 */
   2357 
   2358 	temp = (u_long) gus_max_frequency[sc->sc_voices-GUS_MIN_VOICES];
   2359 
   2360  	fc = (unsigned int)(((f << 9L) + (temp >> 1L)) / temp);
   2361 
   2362  	fc <<= 1;
   2363 
   2364 
   2365 	/*
   2366 	 * Program the voice frequency, and set it in the voice data record
   2367 	 */
   2368 
   2369 	outb(port+GUS_VOICE_SELECT, (unsigned char) voice);
   2370 	SELECT_GUS_REG(port, GUSREG_FREQ_CONTROL);
   2371 	outw(port+GUS_DATA_LOW, fc);
   2372 
   2373 	sc->sc_voc[voice].rate = freq;
   2374 
   2375 }
   2376 
   2377 /*
   2378  * Set the sample rate of the recording frequency.  Formula is from the GUS
   2379  * SDK.  Called at splgus().
   2380  */
   2381 
   2382 STATIC void
   2383 gus_set_recrate(sc, rate)
   2384 	struct gus_softc *sc;
   2385 	u_long rate;
   2386 {
   2387 	register int port = sc->sc_iobase;
   2388 	u_char realrate;
   2389 	DPRINTF(("gus_set_recrate %lu\n", rate));
   2390 
   2391 #if 0
   2392 	realrate = 9878400/(16*(rate+2)); /* formula from GUS docs */
   2393 #endif
   2394 	realrate = (9878400 >> 4)/rate - 2; /* formula from code, sigh. */
   2395 
   2396 	SELECT_GUS_REG(port, GUSREG_SAMPLE_FREQ);
   2397  	outb(port+GUS_DATA_HIGH, realrate);
   2398 }
   2399 
   2400 /*
   2401  * Interface to the audio layer - turn the output on or off.  Note that some
   2402  * of these bits are flipped in the register
   2403  */
   2404 
   2405 int
   2406 gusmax_speaker_ctl(addr, newstate)
   2407 	void * addr;
   2408 	int newstate;
   2409 {
   2410 	register struct ad1848_softc *sc = addr;
   2411 	return gus_speaker_ctl(sc->parent, newstate);
   2412 }
   2413 
   2414 int
   2415 gus_speaker_ctl(addr, newstate)
   2416 	void * addr;
   2417 	int newstate;
   2418 {
   2419 	register struct gus_softc *sc = (struct gus_softc *) addr;
   2420 
   2421 	/* Line out bit is flipped: 0 enables, 1 disables */
   2422 	if ((newstate == SPKR_ON) &&
   2423 	    (sc->sc_mixcontrol & GUSMASK_LINE_OUT)) {
   2424 		sc->sc_mixcontrol &= ~GUSMASK_LINE_OUT;
   2425 		outb(sc->sc_iobase+GUS_MIX_CONTROL, sc->sc_mixcontrol);
   2426 	}
   2427 	if ((newstate == SPKR_OFF) &&
   2428 	    (sc->sc_mixcontrol & GUSMASK_LINE_OUT) == 0) {
   2429 		sc->sc_mixcontrol |= GUSMASK_LINE_OUT;
   2430 		outb(sc->sc_iobase+GUS_MIX_CONTROL, sc->sc_mixcontrol);
   2431 	}
   2432 
   2433 	return 0;
   2434 }
   2435 
   2436 STATIC int
   2437 gus_linein_ctl(addr, newstate)
   2438 	void * addr;
   2439 	int newstate;
   2440 {
   2441 	register struct gus_softc *sc = (struct gus_softc *) addr;
   2442 
   2443 	/* Line in bit is flipped: 0 enables, 1 disables */
   2444 	if ((newstate == SPKR_ON) &&
   2445 	    (sc->sc_mixcontrol & GUSMASK_LINE_IN)) {
   2446 		sc->sc_mixcontrol &= ~GUSMASK_LINE_IN;
   2447 		outb(sc->sc_iobase+GUS_MIX_CONTROL, sc->sc_mixcontrol);
   2448 	}
   2449 	if ((newstate == SPKR_OFF) &&
   2450 	    (sc->sc_mixcontrol & GUSMASK_LINE_IN) == 0) {
   2451 		sc->sc_mixcontrol |= GUSMASK_LINE_IN;
   2452 		outb(sc->sc_iobase+GUS_MIX_CONTROL, sc->sc_mixcontrol);
   2453 	}
   2454 
   2455 	return 0;
   2456 }
   2457 
   2458 STATIC int
   2459 gus_mic_ctl(addr, newstate)
   2460 	void * addr;
   2461 	int newstate;
   2462 {
   2463 	register struct gus_softc *sc = (struct gus_softc *) addr;
   2464 
   2465 	/* Mic bit is normal: 1 enables, 0 disables */
   2466 	if ((newstate == SPKR_ON) &&
   2467 	    (sc->sc_mixcontrol & GUSMASK_MIC_IN) == 0) {
   2468 		sc->sc_mixcontrol |= GUSMASK_MIC_IN;
   2469 		outb(sc->sc_iobase+GUS_MIX_CONTROL, sc->sc_mixcontrol);
   2470 	}
   2471 	if ((newstate == SPKR_OFF) &&
   2472 	    (sc->sc_mixcontrol & GUSMASK_MIC_IN)) {
   2473 		sc->sc_mixcontrol &= ~GUSMASK_MIC_IN;
   2474 		outb(sc->sc_iobase+GUS_MIX_CONTROL, sc->sc_mixcontrol);
   2475 	}
   2476 
   2477 	return 0;
   2478 }
   2479 
   2480 /*
   2481  * Set the end address of a give voice.  Called at splgus()
   2482  */
   2483 
   2484 STATIC void
   2485 gus_set_endaddr(sc, voice, addr)
   2486 	struct gus_softc *sc;
   2487 	int voice;
   2488 	u_long addr;
   2489 {
   2490 	register int port = sc->sc_iobase;
   2491 
   2492 	sc->sc_voc[voice].end_addr = addr;
   2493 
   2494 	if (sc->sc_voc[voice].voccntl & GUSMASK_DATA_SIZE16)
   2495 		addr = convert_to_16bit(addr);
   2496 
   2497 	SELECT_GUS_REG(port, GUSREG_END_ADDR_HIGH);
   2498 	outw(port+GUS_DATA_LOW, ADDR_HIGH(addr));
   2499 	SELECT_GUS_REG(port, GUSREG_END_ADDR_LOW);
   2500 	outw(port+GUS_DATA_LOW, ADDR_LOW(addr));
   2501 
   2502 }
   2503 
   2504 #ifdef GUSPLAYDEBUG
   2505 /*
   2506  * Set current address.  called at splgus()
   2507  */
   2508 STATIC void
   2509 gus_set_curaddr(sc, voice, addr)
   2510 	struct gus_softc *sc;
   2511 	int voice;
   2512 	u_long addr;
   2513 {
   2514 	register int port = sc->sc_iobase;
   2515 
   2516 	sc->sc_voc[voice].current_addr = addr;
   2517 
   2518 	if (sc->sc_voc[voice].voccntl & GUSMASK_DATA_SIZE16)
   2519 		addr = convert_to_16bit(addr);
   2520 
   2521 	outb(port+GUS_VOICE_SELECT, (unsigned char) voice);
   2522 
   2523 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_HIGH);
   2524 	outw(port+GUS_DATA_LOW, ADDR_HIGH(addr));
   2525 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_LOW);
   2526 	outw(port+GUS_DATA_LOW, ADDR_LOW(addr));
   2527 
   2528 }
   2529 
   2530 /*
   2531  * Get current GUS playback address.  Called at splgus().
   2532  */
   2533 STATIC u_long
   2534 gus_get_curaddr(sc, voice)
   2535 	struct gus_softc *sc;
   2536 	int voice;
   2537 {
   2538 	register int port = sc->sc_iobase;
   2539 	u_long addr;
   2540 
   2541 	outb(port+GUS_VOICE_SELECT, (unsigned char) voice);
   2542 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_HIGH|GUSREG_READ);
   2543 	addr = (inw(port+GUS_DATA_LOW) & 0x1fff) << 7;
   2544 	SELECT_GUS_REG(port, GUSREG_CUR_ADDR_LOW|GUSREG_READ);
   2545 	addr |= (inw(port+GUS_DATA_LOW) >> 9L) & 0x7f;
   2546 
   2547 	if (sc->sc_voc[voice].voccntl & GUSMASK_DATA_SIZE16)
   2548 	    addr = (addr & 0xc0000) | ((addr & 0x1ffff) << 1); /* undo 16-bit change */
   2549 	DPRINTF(("gus voice %d curaddr %d end_addr %d\n",
   2550 		 voice, addr, sc->sc_voc[voice].end_addr));
   2551 	/* XXX sanity check the address? */
   2552 
   2553 	return(addr);
   2554 }
   2555 #endif
   2556 
   2557 /*
   2558  * Convert an address value to a "16 bit" value - why this is necessary I
   2559  * have NO idea
   2560  */
   2561 
   2562 STATIC u_long
   2563 convert_to_16bit(address)
   2564 	u_long address;
   2565 {
   2566 	u_long old_address;
   2567 
   2568 	old_address = address;
   2569 	address >>= 1;
   2570 	address &= 0x0001ffffL;
   2571 	address |= (old_address & 0x000c0000L);
   2572 
   2573 	return (address);
   2574 }
   2575 
   2576 /*
   2577  * Write a value into the GUS's DRAM
   2578  */
   2579 
   2580 STATIC void
   2581 guspoke(port, address, value)
   2582 	int port;
   2583 	long address;
   2584 	unsigned char value;
   2585 {
   2586 
   2587 	/*
   2588 	 * Select the DRAM address
   2589 	 */
   2590 
   2591  	SELECT_GUS_REG(port, GUSREG_DRAM_ADDR_LOW);
   2592  	outw(port+GUS_DATA_LOW, (unsigned int) (address & 0xffff));
   2593  	SELECT_GUS_REG(port, GUSREG_DRAM_ADDR_HIGH);
   2594  	outb(port+GUS_DATA_HIGH, (unsigned char) ((address >> 16) & 0xff));
   2595 
   2596 	/*
   2597 	 * Actually write the data
   2598 	 */
   2599 
   2600 	outb(port+GUS_DRAM_DATA, value);
   2601 }
   2602 
   2603 /*
   2604  * Read a value from the GUS's DRAM
   2605  */
   2606 
   2607 STATIC unsigned char
   2608 guspeek(port, address)
   2609 	int port;
   2610 	u_long address;
   2611 {
   2612 
   2613 	/*
   2614 	 * Select the DRAM address
   2615 	 */
   2616 
   2617  	SELECT_GUS_REG(port, GUSREG_DRAM_ADDR_LOW);
   2618  	outw(port+GUS_DATA_LOW, (unsigned int) (address & 0xffff));
   2619  	SELECT_GUS_REG(port, GUSREG_DRAM_ADDR_HIGH);
   2620  	outb(port+GUS_DATA_HIGH, (unsigned char) ((address >> 16) & 0xff));
   2621 
   2622 	/*
   2623 	 * Read in the data from the board
   2624 	 */
   2625 
   2626 	return (unsigned char) inb(port+GUS_DRAM_DATA);
   2627 }
   2628 
   2629 /*
   2630  * Reset the Gravis UltraSound card, completely
   2631  */
   2632 
   2633 STATIC void
   2634 gusreset(sc, voices)
   2635 	struct gus_softc *sc;
   2636 	int voices;
   2637 {
   2638 	register int port = sc->sc_iobase;
   2639 	int i,s;
   2640 
   2641 	s = splgus();
   2642 
   2643 	/*
   2644 	 * Reset the GF1 chip
   2645 	 */
   2646 
   2647 	SELECT_GUS_REG(port, GUSREG_RESET);
   2648 	outb(port+GUS_DATA_HIGH, 0x00);
   2649 
   2650 	delay(500);
   2651 
   2652 	/*
   2653 	 * Release reset
   2654 	 */
   2655 
   2656 	SELECT_GUS_REG(port, GUSREG_RESET);
   2657 	outb(port+GUS_DATA_HIGH, GUSMASK_MASTER_RESET);
   2658 
   2659 	delay(500);
   2660 
   2661 	/*
   2662 	 * Reset MIDI port as well
   2663 	 */
   2664 
   2665 	outb(GUS_MIDI_CONTROL,MIDI_RESET);
   2666 
   2667 	delay(500);
   2668 
   2669 	outb(GUS_MIDI_CONTROL,0x00);
   2670 
   2671 	/*
   2672 	 * Clear interrupts
   2673 	 */
   2674 
   2675 	SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   2676 	outb(port+GUS_DATA_HIGH, 0x00);
   2677 	SELECT_GUS_REG(port, GUSREG_TIMER_CONTROL);
   2678 	outb(port+GUS_DATA_HIGH, 0x00);
   2679 	SELECT_GUS_REG(port, GUSREG_SAMPLE_CONTROL);
   2680 	outb(port+GUS_DATA_HIGH, 0x00);
   2681 
   2682 	gus_set_voices(sc, voices);
   2683 
   2684 	inb(port+GUS_IRQ_STATUS);
   2685 	SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   2686 	inb(port+GUS_DATA_HIGH);
   2687 	SELECT_GUS_REG(port, GUSREG_SAMPLE_CONTROL);
   2688 	inb(port+GUS_DATA_HIGH);
   2689 	SELECT_GUS_REG(port, GUSREG_IRQ_STATUS);
   2690 	inb(port+GUS_DATA_HIGH);
   2691 
   2692 	/*
   2693 	 * Reset voice specific information
   2694 	 */
   2695 
   2696 	for(i = 0; i < voices; i++) {
   2697 		outb(port+GUS_VOICE_SELECT, (unsigned char) i);
   2698 
   2699 		SELECT_GUS_REG(port, GUSREG_VOICE_CNTL);
   2700 
   2701 		sc->sc_voc[i].voccntl = GUSMASK_VOICE_STOPPED |
   2702 			GUSMASK_STOP_VOICE;
   2703 
   2704 		outb(port+GUS_DATA_HIGH, sc->sc_voc[i].voccntl);
   2705 
   2706 		sc->sc_voc[i].volcntl = GUSMASK_VOLUME_STOPPED |
   2707 				GUSMASK_STOP_VOLUME;
   2708 
   2709 		SELECT_GUS_REG(port, GUSREG_VOLUME_CONTROL);
   2710 		outb(port+GUS_DATA_HIGH, sc->sc_voc[i].volcntl);
   2711 
   2712 		delay(100);
   2713 
   2714 		gus_set_samprate(sc, i, 8000);
   2715 		SELECT_GUS_REG(port, GUSREG_START_ADDR_HIGH);
   2716 		outw(port+GUS_DATA_LOW, 0x0000);
   2717 		SELECT_GUS_REG(port, GUSREG_START_ADDR_LOW);
   2718 		outw(port+GUS_DATA_LOW, 0x0000);
   2719 		SELECT_GUS_REG(port, GUSREG_END_ADDR_HIGH);
   2720 		outw(port+GUS_DATA_LOW, 0x0000);
   2721 		SELECT_GUS_REG(port, GUSREG_END_ADDR_LOW);
   2722 		outw(port+GUS_DATA_LOW, 0x0000);
   2723 		SELECT_GUS_REG(port, GUSREG_VOLUME_RATE);
   2724 		outb(port+GUS_DATA_HIGH, 0x01);
   2725 		SELECT_GUS_REG(port, GUSREG_START_VOLUME);
   2726 		outb(port+GUS_DATA_HIGH, 0x10);
   2727 		SELECT_GUS_REG(port, GUSREG_END_VOLUME);
   2728 		outb(port+GUS_DATA_HIGH, 0xe0);
   2729 		SELECT_GUS_REG(port, GUSREG_CUR_VOLUME);
   2730 		outw(port+GUS_DATA_LOW, 0x0000);
   2731 
   2732 		SELECT_GUS_REG(port, GUSREG_CUR_ADDR_HIGH);
   2733 		outw(port+GUS_DATA_LOW, 0x0000);
   2734 		SELECT_GUS_REG(port, GUSREG_CUR_ADDR_LOW);
   2735 		outw(port+GUS_DATA_LOW, 0x0000);
   2736 		SELECT_GUS_REG(port, GUSREG_PAN_POS);
   2737 		outb(port+GUS_DATA_HIGH, 0x07);
   2738 	}
   2739 
   2740 	/*
   2741 	 * Clear out any pending IRQs
   2742 	 */
   2743 
   2744 	inb(port+GUS_IRQ_STATUS);
   2745 	SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   2746 	inb(port+GUS_DATA_HIGH);
   2747 	SELECT_GUS_REG(port, GUSREG_SAMPLE_CONTROL);
   2748 	inb(port+GUS_DATA_HIGH);
   2749 	SELECT_GUS_REG(port, GUSREG_IRQ_STATUS);
   2750 	inb(port+GUS_DATA_HIGH);
   2751 
   2752 	SELECT_GUS_REG(port, GUSREG_RESET);
   2753 	outb(port+GUS_DATA_HIGH, GUSMASK_MASTER_RESET | GUSMASK_DAC_ENABLE |
   2754 		GUSMASK_IRQ_ENABLE);
   2755 
   2756 	splx(s);
   2757 }
   2758 
   2759 
   2760 STATIC void
   2761 gus_init_cs4231(sc)
   2762 	struct gus_softc *sc;
   2763 {
   2764 	register int port = sc->sc_iobase;
   2765 	u_char ctrl;
   2766 
   2767 	ctrl = (port & 0xf0) >> 4;	/* set port address middle nibble */
   2768 	/*
   2769 	 * The codec is a bit weird--swapped dma channels.
   2770 	 */
   2771 	ctrl |= GUS_MAX_CODEC_ENABLE;
   2772 	if (sc->sc_drq >= 4)
   2773 		ctrl |= GUS_MAX_RECCHAN16;
   2774 	if (sc->sc_recdrq >= 4)
   2775 		ctrl |= GUS_MAX_PLAYCHAN16;
   2776 
   2777 	outb(port+GUS_MAX_CTRL, ctrl);
   2778 
   2779 	sc->sc_codec.sc_iot = sc->sc_iot;
   2780 	sc->sc_codec.sc_iobase = port+GUS_MAX_CODEC_BASE;
   2781 
   2782 	if (ad1848_probe(&sc->sc_codec) == 0) {
   2783 		sc->sc_flags &= ~GUS_CODEC_INSTALLED;
   2784 	} else {
   2785 		struct ad1848_volume vol = {AUDIO_MAX_GAIN, AUDIO_MAX_GAIN};
   2786 		struct audio_hw_if gusmax_hw_if = {
   2787 			gusopen,
   2788 			gusmax_close,
   2789 			NULL,				/* drain */
   2790 
   2791 			gus_query_encoding, /* query encoding */
   2792 
   2793 			gusmax_set_params,
   2794 
   2795 			gusmax_round_blocksize,
   2796 
   2797 			gusmax_set_out_port,
   2798 			gusmax_get_out_port,
   2799 			gusmax_set_in_port,
   2800 			gusmax_get_in_port,
   2801 
   2802 			gusmax_commit_settings,
   2803 
   2804 			gusmax_dma_output,
   2805 			gusmax_dma_input,
   2806 			gusmax_halt_out_dma,
   2807 			gusmax_halt_in_dma,
   2808 			gusmax_cont_out_dma,
   2809 			gusmax_cont_in_dma,
   2810 
   2811 			gusmax_speaker_ctl,
   2812 
   2813 			gus_getdev,
   2814 			gus_setfd,
   2815 			gusmax_mixer_set_port,
   2816 			gusmax_mixer_get_port,
   2817 			gusmax_mixer_query_devinfo,
   2818 			1,				/* full-duplex */
   2819 			0,
   2820 		};
   2821 		sc->sc_flags |= GUS_CODEC_INSTALLED;
   2822 		sc->sc_codec.parent = sc;
   2823 		sc->sc_codec.sc_drq = sc->sc_recdrq;
   2824 		sc->sc_codec.sc_recdrq = sc->sc_drq;
   2825 		gus_hw_if = gusmax_hw_if;
   2826 		/* enable line in and mic in the GUS mixer; the codec chip
   2827 		   will do the real mixing for them. */
   2828 		sc->sc_mixcontrol &= ~GUSMASK_LINE_IN; /* 0 enables. */
   2829 		sc->sc_mixcontrol |= GUSMASK_MIC_IN; /* 1 enables. */
   2830 		outb(sc->sc_iobase+GUS_MIX_CONTROL, sc->sc_mixcontrol);
   2831 
   2832 		ad1848_attach(&sc->sc_codec);
   2833 		/* turn on pre-MUX microphone gain. */
   2834 		ad1848_set_mic_gain(&sc->sc_codec, &vol);
   2835 	}
   2836 }
   2837 
   2838 
   2839 /*
   2840  * Return info about the audio device, for the AUDIO_GETINFO ioctl
   2841  */
   2842 
   2843 int
   2844 gus_getdev(addr, dev)
   2845 	void * addr;
   2846 	struct audio_device *dev;
   2847 {
   2848 	*dev = gus_device;
   2849 	return 0;
   2850 }
   2851 
   2852 /*
   2853  * stubs (XXX)
   2854  */
   2855 
   2856 int
   2857 gus_set_in_gain(addr, gain, balance)
   2858 	caddr_t addr;
   2859 	u_int gain;
   2860 	u_char balance;
   2861 {
   2862 	DPRINTF(("gus_set_in_gain called\n"));
   2863 	return 0;
   2864 }
   2865 
   2866 int
   2867 gus_get_in_gain(addr)
   2868 	caddr_t addr;
   2869 {
   2870 	DPRINTF(("gus_get_in_gain called\n"));
   2871 	return 0;
   2872 }
   2873 
   2874 int
   2875 gusmax_set_out_port(addr, port)
   2876 	void * addr;
   2877 	int port;
   2878 {
   2879 	register struct ad1848_softc *sc = addr;
   2880 	return gus_set_out_port(sc->parent, port);
   2881 }
   2882 
   2883 int
   2884 gus_set_out_port(addr, port)
   2885 	void * addr;
   2886 	int port;
   2887 {
   2888 	register struct gus_softc *sc = addr;
   2889 	DPRINTF(("gus_set_out_port called\n"));
   2890 	sc->sc_out_port = port;
   2891 
   2892 	return 0;
   2893 }
   2894 
   2895 int
   2896 gusmax_get_out_port(addr)
   2897 	void * addr;
   2898 {
   2899 	register struct ad1848_softc *sc = addr;
   2900 	return gus_get_out_port(sc->parent);
   2901 }
   2902 
   2903 int
   2904 gus_get_out_port(addr)
   2905 	void * addr;
   2906 {
   2907 	register struct gus_softc *sc = addr;
   2908 	DPRINTF(("gus_get_out_port() called\n"));
   2909 	return sc->sc_out_port;
   2910 }
   2911 
   2912 int
   2913 gusmax_set_in_port(addr, port)
   2914 	void * addr;
   2915 	int port;
   2916 {
   2917 	register struct ad1848_softc *sc = addr;
   2918 	DPRINTF(("gusmax_set_in_port: %d\n", port));
   2919 
   2920 	switch(port) {
   2921 	case GUSMAX_MONO_LVL:
   2922 		port = MIC_IN_PORT;
   2923 		break;
   2924 	case GUSMAX_LINE_IN_LVL:
   2925 		port = LINE_IN_PORT;
   2926 		break;
   2927 	case GUSMAX_DAC_LVL:
   2928 		port = AUX1_IN_PORT;
   2929 		break;
   2930 	case GUSMAX_MIX_IN:
   2931 		port = DAC_IN_PORT;
   2932 		break;
   2933 	default:
   2934 		return(EINVAL);
   2935 		/*NOTREACHED*/
   2936 	}
   2937 	return(ad1848_set_rec_port(sc, port));
   2938 }
   2939 
   2940 int
   2941 gusmax_get_in_port(addr)
   2942 	void * addr;
   2943 {
   2944 	register struct ad1848_softc *sc = addr;
   2945 	int port = GUSMAX_MONO_LVL;
   2946 
   2947 	switch(ad1848_get_rec_port(sc)) {
   2948 	case MIC_IN_PORT:
   2949 		port = GUSMAX_MONO_LVL;
   2950 		break;
   2951 	case LINE_IN_PORT:
   2952 		port = GUSMAX_LINE_IN_LVL;
   2953 		break;
   2954 	case DAC_IN_PORT:
   2955 		port = GUSMAX_MIX_IN;
   2956 		break;
   2957 	case AUX1_IN_PORT:
   2958 		port = GUSMAX_DAC_LVL;
   2959 		break;
   2960 	}
   2961 
   2962 	DPRINTF(("gusmax_get_in_port: %d\n", port));
   2963 
   2964 	return(port);
   2965 }
   2966 
   2967 int
   2968 gus_set_in_port(addr, port)
   2969 	void * addr;
   2970 	int port;
   2971 {
   2972 	register struct gus_softc *sc = addr;
   2973 	DPRINTF(("gus_set_in_port called\n"));
   2974 	/*
   2975 	 * On the GUS with ICS mixer, the ADC input is after the mixer stage,
   2976 	 * so we can't set the input port.
   2977 	 *
   2978 	 * On the GUS with CS4231 codec/mixer, see gusmax_set_in_port().
   2979 	 */
   2980 	sc->sc_in_port = port;
   2981 
   2982 	return 0;
   2983 }
   2984 
   2985 
   2986 int
   2987 gus_get_in_port(addr)
   2988 	void * addr;
   2989 {
   2990 	register struct gus_softc *sc = addr;
   2991 	DPRINTF(("gus_get_in_port called\n"));
   2992 	return sc->sc_in_port;
   2993 }
   2994 
   2995 
   2996 int
   2997 gusmax_dma_input(addr, buf, size, callback, arg)
   2998 	void * addr;
   2999 	void *buf;
   3000 	int size;
   3001 	void (*callback) __P((void *));
   3002 	void *arg;
   3003 {
   3004 	register struct ad1848_softc *sc = addr;
   3005 	return gus_dma_input(sc->parent, buf, size, callback, arg);
   3006 }
   3007 
   3008 /*
   3009  * Start sampling the input source into the requested DMA buffer.
   3010  * Called at splgus(), either from top-half or from interrupt handler.
   3011  */
   3012 int
   3013 gus_dma_input(addr, buf, size, callback, arg)
   3014 	void * addr;
   3015 	void *buf;
   3016 	int size;
   3017 	void (*callback) __P((void *));
   3018 	void *arg;
   3019 {
   3020 	register struct gus_softc *sc = addr;
   3021 	register int port = sc->sc_iobase;
   3022 	register u_char dmac;
   3023 	DMAPRINTF(("gus_dma_input called\n"));
   3024 
   3025 	/*
   3026 	 * Sample SIZE bytes of data from the card, into buffer at BUF.
   3027 	 */
   3028 
   3029 	if (sc->sc_precision == 16)
   3030 	    return EINVAL;		/* XXX */
   3031 
   3032 	/* set DMA modes */
   3033 	dmac = GUSMASK_SAMPLE_IRQ|GUSMASK_SAMPLE_START;
   3034 	if (sc->sc_recdrq >= 4)
   3035 		dmac |= GUSMASK_SAMPLE_DATA16;
   3036 	if (sc->sc_encoding == AUDIO_ENCODING_ULAW ||
   3037 	    sc->sc_encoding == AUDIO_ENCODING_ULINEAR_LE)
   3038 	    dmac |= GUSMASK_SAMPLE_INVBIT;
   3039 	if (sc->sc_channels == 2)
   3040 	    dmac |= GUSMASK_SAMPLE_STEREO;
   3041 	isa_dmastart(sc->sc_dev.dv_parent, sc->sc_recdrq, buf, size,
   3042 	    NULL, DMAMODE_READ, BUS_DMA_NOWAIT);
   3043 
   3044 	DMAPRINTF(("gus_dma_input isa_dmastarted\n"));
   3045 	sc->sc_flags |= GUS_DMAIN_ACTIVE;
   3046 	sc->sc_dmainintr = callback;
   3047 	sc->sc_inarg = arg;
   3048 	sc->sc_dmaincnt = size;
   3049 	sc->sc_dmainaddr = buf;
   3050 
   3051 	SELECT_GUS_REG(port, GUSREG_SAMPLE_CONTROL);
   3052 	outb(port+GUS_DATA_HIGH, dmac);	/* Go! */
   3053 
   3054 
   3055 	DMAPRINTF(("gus_dma_input returning\n"));
   3056 
   3057 	return 0;
   3058 }
   3059 
   3060 STATIC int
   3061 gus_dmain_intr(sc)
   3062 	struct gus_softc *sc;
   3063 {
   3064         void (*callback) __P((void *));
   3065 	void *arg;
   3066 
   3067 	DMAPRINTF(("gus_dmain_intr called\n"));
   3068 	if (sc->sc_dmainintr) {
   3069 	    isa_dmadone(sc->sc_dev.dv_parent, sc->sc_recdrq);
   3070 	    callback = sc->sc_dmainintr;
   3071 	    arg = sc->sc_inarg;
   3072 
   3073 	    sc->sc_dmainaddr = 0;
   3074 	    sc->sc_dmaincnt = 0;
   3075 	    sc->sc_dmainintr = 0;
   3076 	    sc->sc_inarg = 0;
   3077 
   3078 	    sc->sc_flags &= ~GUS_DMAIN_ACTIVE;
   3079 	    DMAPRINTF(("calling dmain_intr callback %x(%x)\n", callback, arg));
   3080 	    (*callback)(arg);
   3081 	    return 1;
   3082 	} else {
   3083 	    DMAPRINTF(("gus_dmain_intr false?\n"));
   3084 	    return 0;			/* XXX ??? */
   3085 	}
   3086 }
   3087 
   3088 int
   3089 gusmax_halt_out_dma(addr)
   3090 	void * addr;
   3091 {
   3092 	register struct ad1848_softc *sc = addr;
   3093 	return gus_halt_out_dma(sc->parent);
   3094 }
   3095 
   3096 
   3097 int
   3098 gusmax_halt_in_dma(addr)
   3099 	void * addr;
   3100 {
   3101 	register struct ad1848_softc *sc = addr;
   3102 	return gus_halt_in_dma(sc->parent);
   3103 }
   3104 
   3105 int
   3106 gusmax_cont_out_dma(addr)
   3107 	void * addr;
   3108 {
   3109 	register struct ad1848_softc *sc = addr;
   3110 	return gus_cont_out_dma(sc->parent);
   3111 }
   3112 
   3113 int
   3114 gusmax_cont_in_dma(addr)
   3115 	void * addr;
   3116 {
   3117 	register struct ad1848_softc *sc = addr;
   3118 	return gus_cont_in_dma(sc->parent);
   3119 }
   3120 
   3121 /*
   3122  * Stop any DMA output.  Called at splgus().
   3123  */
   3124 int
   3125 gus_halt_out_dma(addr)
   3126 	void * addr;
   3127 {
   3128 	register struct gus_softc *sc = addr;
   3129 	register int port = sc->sc_iobase;
   3130 
   3131 	DMAPRINTF(("gus_halt_out_dma called\n"));
   3132 	/*
   3133 	 * Make sure the GUS _isn't_ setup for DMA
   3134 	 */
   3135 
   3136  	SELECT_GUS_REG(port, GUSREG_DMA_CONTROL);
   3137 	outb(sc->sc_iobase+GUS_DATA_HIGH, 0);
   3138 
   3139 	untimeout(gus_dmaout_timeout, sc);
   3140 	isa_dmaabort(sc->sc_dev.dv_parent, sc->sc_drq);
   3141 	sc->sc_flags &= ~(GUS_DMAOUT_ACTIVE|GUS_LOCKED);
   3142 	sc->sc_dmaoutintr = 0;
   3143 	sc->sc_outarg = 0;
   3144 	sc->sc_dmaoutaddr = 0;
   3145 	sc->sc_dmaoutcnt = 0;
   3146 	sc->sc_dmabuf = 0;
   3147 	sc->sc_bufcnt = 0;
   3148 	sc->sc_playbuf = -1;
   3149 	/* also stop playing */
   3150 	gus_stop_voice(sc, GUS_VOICE_LEFT, 1);
   3151 	gus_stop_voice(sc, GUS_VOICE_RIGHT, 0);
   3152 
   3153 	return 0;
   3154 }
   3155 
   3156 /*
   3157  * Stop any DMA output.  Called at splgus().
   3158  */
   3159 int
   3160 gus_halt_in_dma(addr)
   3161 	void * addr;
   3162 {
   3163 	register struct gus_softc *sc = addr;
   3164 	register int port = sc->sc_iobase;
   3165 	DMAPRINTF(("gus_halt_in_dma called\n"));
   3166 
   3167 	/*
   3168 	 * Make sure the GUS _isn't_ setup for DMA
   3169 	 */
   3170 
   3171  	SELECT_GUS_REG(port, GUSREG_SAMPLE_CONTROL);
   3172 	outb(port+GUS_DATA_HIGH,
   3173 	     inb(port+GUS_DATA_HIGH) & ~(GUSMASK_SAMPLE_START|GUSMASK_SAMPLE_IRQ));
   3174 
   3175 	isa_dmaabort(sc->sc_dev.dv_parent, sc->sc_recdrq);
   3176 	sc->sc_flags &= ~GUS_DMAIN_ACTIVE;
   3177 	sc->sc_dmainintr = 0;
   3178 	sc->sc_inarg = 0;
   3179 	sc->sc_dmainaddr = 0;
   3180 	sc->sc_dmaincnt = 0;
   3181 
   3182 	return 0;
   3183 }
   3184 
   3185 int
   3186 gus_cont_out_dma(addr)
   3187 	void * addr;
   3188 {
   3189 	DPRINTF(("gus_cont_out_dma called\n"));
   3190 	return EOPNOTSUPP;
   3191 }
   3192 
   3193 int
   3194 gus_cont_in_dma(addr)
   3195 	void * addr;
   3196 {
   3197 	DPRINTF(("gus_cont_in_dma called\n"));
   3198 	return EOPNOTSUPP;
   3199 }
   3200 
   3201 
   3202 STATIC int
   3203 gus_setfd(addr, flag)
   3204 	void *addr;
   3205 	int flag;
   3206 {
   3207     if (gus_hw_if.full_duplex == 0)
   3208 	 return ENOTTY;
   3209 
   3210     return(0);				/* nothing fancy to do. */
   3211 }
   3212 
   3213 STATIC __inline int
   3214 gus_to_vol(cp, vol)
   3215 	mixer_ctrl_t *cp;
   3216 	struct ad1848_volume *vol;
   3217 {
   3218 	if (cp->un.value.num_channels == 1) {
   3219 		vol->left = vol->right = cp->un.value.level[AUDIO_MIXER_LEVEL_MONO];
   3220 		return(1);
   3221 	}
   3222 	else if (cp->un.value.num_channels == 2) {
   3223 		vol->left  = cp->un.value.level[AUDIO_MIXER_LEVEL_LEFT];
   3224 		vol->right = cp->un.value.level[AUDIO_MIXER_LEVEL_RIGHT];
   3225 		return(1);
   3226 	}
   3227 	return(0);
   3228 }
   3229 
   3230 STATIC __inline int
   3231 gus_from_vol(cp, vol)
   3232 	mixer_ctrl_t *cp;
   3233 	struct ad1848_volume *vol;
   3234 {
   3235 	if (cp->un.value.num_channels == 1) {
   3236 		cp->un.value.level[AUDIO_MIXER_LEVEL_MONO] = vol->left;
   3237 		return(1);
   3238 	}
   3239 	else if (cp->un.value.num_channels == 2) {
   3240 		cp->un.value.level[AUDIO_MIXER_LEVEL_LEFT] = vol->left;
   3241 		cp->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] = vol->right;
   3242 		return(1);
   3243 	}
   3244 	return(0);
   3245 }
   3246 
   3247 STATIC int
   3248 gusmax_mixer_get_port(addr, cp)
   3249 	void *addr;
   3250 	mixer_ctrl_t *cp;
   3251 {
   3252 	register struct ad1848_softc *ac = addr;
   3253 	register struct gus_softc *sc = ac->parent;
   3254 	struct ad1848_volume vol;
   3255 	int error = EINVAL;
   3256 
   3257 	DPRINTF(("gusmax_mixer_get_port: port=%d\n", cp->dev));
   3258 
   3259 	switch (cp->dev) {
   3260 #if 0 /* use mono level instead */
   3261 	case GUSMAX_MIC_IN_LVL:	/* Microphone */
   3262 		if (cp->type == AUDIO_MIXER_VALUE) {
   3263 			error = ad1848_get_mic_gain(ac, &vol);
   3264 			if (!error)
   3265 				gus_from_vol(cp, &vol);
   3266 		}
   3267 		break;
   3268 #endif
   3269 
   3270 	case GUSMAX_DAC_LVL:		/* dac out */
   3271 		if (cp->type == AUDIO_MIXER_VALUE) {
   3272 			error = ad1848_get_aux1_gain(ac, &vol);
   3273 			if (!error)
   3274 				gus_from_vol(cp, &vol);
   3275 		}
   3276 		break;
   3277 
   3278 	case GUSMAX_LINE_IN_LVL:	/* line in */
   3279 		if (cp->type == AUDIO_MIXER_VALUE) {
   3280 			error = cs4231_get_linein_gain(ac, &vol);
   3281 			if (!error)
   3282 				gus_from_vol(cp, &vol);
   3283 		}
   3284 		break;
   3285 
   3286 	case GUSMAX_MONO_LVL:	/* mono */
   3287 		if (cp->type == AUDIO_MIXER_VALUE &&
   3288 		    cp->un.value.num_channels == 1) {
   3289 			error = cs4231_get_mono_gain(ac, &vol);
   3290 			if (!error)
   3291 				gus_from_vol(cp, &vol);
   3292 		}
   3293 		break;
   3294 
   3295 	case GUSMAX_CD_LVL:	/* CD */
   3296 		if (cp->type == AUDIO_MIXER_VALUE) {
   3297 			error = ad1848_get_aux2_gain(ac, &vol);
   3298 			if (!error)
   3299 				gus_from_vol(cp, &vol);
   3300 		}
   3301 		break;
   3302 
   3303 	case GUSMAX_MONITOR_LVL:	/* monitor level */
   3304 		if (cp->type == AUDIO_MIXER_VALUE &&
   3305 		    cp->un.value.num_channels == 1) {
   3306 			error = ad1848_get_mon_gain(ac, &vol);
   3307 			if (!error)
   3308 				cp->un.value.level[AUDIO_MIXER_LEVEL_MONO] =
   3309 					vol.left;
   3310 		}
   3311 		break;
   3312 
   3313 	case GUSMAX_OUT_LVL:	/* output level */
   3314 		if (cp->type == AUDIO_MIXER_VALUE) {
   3315 			error = ad1848_get_out_gain(ac, &vol);
   3316 			if (!error)
   3317 				gus_from_vol(cp, &vol);
   3318 		}
   3319 		break;
   3320 
   3321 	case GUSMAX_SPEAKER_LVL:	/* fake speaker for mute naming */
   3322 		if (cp->type == AUDIO_MIXER_VALUE) {
   3323 			if (sc->sc_mixcontrol & GUSMASK_LINE_OUT)
   3324 				vol.left = vol.right = AUDIO_MAX_GAIN;
   3325 			else
   3326 				vol.left = vol.right = AUDIO_MIN_GAIN;
   3327 			error = 0;
   3328 			gus_from_vol(cp, &vol);
   3329 		}
   3330 		break;
   3331 
   3332 	case GUSMAX_LINE_IN_MUTE:
   3333 		if (cp->type == AUDIO_MIXER_ENUM) {
   3334 			cp->un.ord = ac->line_mute;
   3335 			error = 0;
   3336 		}
   3337 		break;
   3338 
   3339 
   3340 	case GUSMAX_DAC_MUTE:
   3341 		if (cp->type == AUDIO_MIXER_ENUM) {
   3342 			cp->un.ord = ac->aux1_mute;
   3343 			error = 0;
   3344 		}
   3345 		break;
   3346 
   3347 	case GUSMAX_CD_MUTE:
   3348 		if (cp->type == AUDIO_MIXER_ENUM) {
   3349 			cp->un.ord = ac->aux2_mute;
   3350 			error = 0;
   3351 		}
   3352 		break;
   3353 
   3354 	case GUSMAX_MONO_MUTE:
   3355 		if (cp->type == AUDIO_MIXER_ENUM) {
   3356 			cp->un.ord = ac->mono_mute;
   3357 			error = 0;
   3358 		}
   3359 		break;
   3360 
   3361 	case GUSMAX_MONITOR_MUTE:
   3362 		if (cp->type == AUDIO_MIXER_ENUM) {
   3363 			cp->un.ord = ac->mon_mute;
   3364 			error = 0;
   3365 		}
   3366 		break;
   3367 
   3368 	case GUSMAX_SPEAKER_MUTE:
   3369 		if (cp->type == AUDIO_MIXER_ENUM) {
   3370 			cp->un.ord = sc->sc_mixcontrol & GUSMASK_LINE_OUT ? 1 : 0;
   3371 			error = 0;
   3372 		}
   3373 		break;
   3374 
   3375 	case GUSMAX_REC_LVL:		/* record level */
   3376 		if (cp->type == AUDIO_MIXER_VALUE) {
   3377 			error = ad1848_get_rec_gain(ac, &vol);
   3378 			if (!error)
   3379 				gus_from_vol(cp, &vol);
   3380 		}
   3381 		break;
   3382 
   3383 	case GUSMAX_RECORD_SOURCE:
   3384 		if (cp->type == AUDIO_MIXER_ENUM) {
   3385 			cp->un.ord = ad1848_get_rec_port(ac);
   3386 			error = 0;
   3387 		}
   3388 		break;
   3389 
   3390 	default:
   3391 		error = ENXIO;
   3392 		break;
   3393 	}
   3394 
   3395 	return(error);
   3396 }
   3397 
   3398 STATIC int
   3399 gus_mixer_get_port(addr, cp)
   3400 	void *addr;
   3401 	mixer_ctrl_t *cp;
   3402 {
   3403 	register struct gus_softc *sc = addr;
   3404 	register struct ics2101_softc *ic = &sc->sc_mixer;
   3405 	struct ad1848_volume vol;
   3406 	int error = EINVAL;
   3407 
   3408 	DPRINTF(("gus_mixer_get_port: dev=%d type=%d\n", cp->dev, cp->type));
   3409 
   3410 	if (!HAS_MIXER(sc) && cp->dev > GUSICS_MASTER_MUTE)
   3411 		return ENXIO;
   3412 
   3413 	switch (cp->dev) {
   3414 
   3415 	case GUSICS_MIC_IN_MUTE:	/* Microphone */
   3416 		if (cp->type == AUDIO_MIXER_ENUM) {
   3417 			if (HAS_MIXER(sc))
   3418 				cp->un.ord = ic->sc_mute[GUSMIX_CHAN_MIC][ICSMIX_LEFT];
   3419 			else
   3420 				cp->un.ord =
   3421 				    sc->sc_mixcontrol & GUSMASK_MIC_IN ? 0 : 1;
   3422 			error = 0;
   3423 		}
   3424 		break;
   3425 
   3426 	case GUSICS_LINE_IN_MUTE:
   3427 		if (cp->type == AUDIO_MIXER_ENUM) {
   3428 			if (HAS_MIXER(sc))
   3429 				cp->un.ord = ic->sc_mute[GUSMIX_CHAN_LINE][ICSMIX_LEFT];
   3430 			else
   3431 				cp->un.ord =
   3432 				    sc->sc_mixcontrol & GUSMASK_LINE_IN ? 1 : 0;
   3433 			error = 0;
   3434 		}
   3435 		break;
   3436 
   3437 	case GUSICS_MASTER_MUTE:
   3438 		if (cp->type == AUDIO_MIXER_ENUM) {
   3439 			if (HAS_MIXER(sc))
   3440 				cp->un.ord = ic->sc_mute[GUSMIX_CHAN_MASTER][ICSMIX_LEFT];
   3441 			else
   3442 				cp->un.ord =
   3443 				    sc->sc_mixcontrol & GUSMASK_LINE_OUT ? 1 : 0;
   3444 			error = 0;
   3445 		}
   3446 		break;
   3447 
   3448 	case GUSICS_DAC_MUTE:
   3449 		if (cp->type == AUDIO_MIXER_ENUM) {
   3450 			cp->un.ord = ic->sc_mute[GUSMIX_CHAN_DAC][ICSMIX_LEFT];
   3451 			error = 0;
   3452 		}
   3453 		break;
   3454 
   3455 	case GUSICS_CD_MUTE:
   3456 		if (cp->type == AUDIO_MIXER_ENUM) {
   3457 			cp->un.ord = ic->sc_mute[GUSMIX_CHAN_CD][ICSMIX_LEFT];
   3458 			error = 0;
   3459 		}
   3460 		break;
   3461 
   3462 	case GUSICS_MASTER_LVL:
   3463 		if (cp->type == AUDIO_MIXER_VALUE) {
   3464 			vol.left = ic->sc_setting[GUSMIX_CHAN_MASTER][ICSMIX_LEFT];
   3465 			vol.right = ic->sc_setting[GUSMIX_CHAN_MASTER][ICSMIX_RIGHT];
   3466 			if (gus_from_vol(cp, &vol))
   3467 				error = 0;
   3468 		}
   3469 		break;
   3470 
   3471 	case GUSICS_MIC_IN_LVL:	/* Microphone */
   3472 		if (cp->type == AUDIO_MIXER_VALUE) {
   3473 			vol.left = ic->sc_setting[GUSMIX_CHAN_MIC][ICSMIX_LEFT];
   3474 			vol.right = ic->sc_setting[GUSMIX_CHAN_MIC][ICSMIX_RIGHT];
   3475 			if (gus_from_vol(cp, &vol))
   3476 				error = 0;
   3477 		}
   3478 		break;
   3479 
   3480 	case GUSICS_LINE_IN_LVL:	/* line in */
   3481 		if (cp->type == AUDIO_MIXER_VALUE) {
   3482 			vol.left = ic->sc_setting[GUSMIX_CHAN_LINE][ICSMIX_LEFT];
   3483 			vol.right = ic->sc_setting[GUSMIX_CHAN_LINE][ICSMIX_RIGHT];
   3484 			if (gus_from_vol(cp, &vol))
   3485 				error = 0;
   3486 		}
   3487 		break;
   3488 
   3489 
   3490 	case GUSICS_CD_LVL:
   3491 		if (cp->type == AUDIO_MIXER_VALUE) {
   3492 			vol.left = ic->sc_setting[GUSMIX_CHAN_CD][ICSMIX_LEFT];
   3493 			vol.right = ic->sc_setting[GUSMIX_CHAN_CD][ICSMIX_RIGHT];
   3494 			if (gus_from_vol(cp, &vol))
   3495 				error = 0;
   3496 		}
   3497 		break;
   3498 
   3499 	case GUSICS_DAC_LVL:		/* dac out */
   3500 		if (cp->type == AUDIO_MIXER_VALUE) {
   3501 			vol.left = ic->sc_setting[GUSMIX_CHAN_DAC][ICSMIX_LEFT];
   3502 			vol.right = ic->sc_setting[GUSMIX_CHAN_DAC][ICSMIX_RIGHT];
   3503 			if (gus_from_vol(cp, &vol))
   3504 				error = 0;
   3505 		}
   3506 		break;
   3507 
   3508 
   3509 	case GUSICS_RECORD_SOURCE:
   3510 		if (cp->type == AUDIO_MIXER_ENUM) {
   3511 			/* Can't set anything else useful, sigh. */
   3512 			 cp->un.ord = 0;
   3513 		}
   3514 		break;
   3515 
   3516 	default:
   3517 		return ENXIO;
   3518 	    /*NOTREACHED*/
   3519 	}
   3520 	return error;
   3521 }
   3522 
   3523 STATIC void
   3524 gusics_master_mute(ic, mute)
   3525 	struct ics2101_softc *ic;
   3526 	int mute;
   3527 {
   3528 	ics2101_mix_mute(ic, GUSMIX_CHAN_MASTER, ICSMIX_LEFT, mute);
   3529 	ics2101_mix_mute(ic, GUSMIX_CHAN_MASTER, ICSMIX_RIGHT, mute);
   3530 }
   3531 
   3532 STATIC void
   3533 gusics_mic_mute(ic, mute)
   3534 	struct ics2101_softc *ic;
   3535 	int mute;
   3536 {
   3537 	ics2101_mix_mute(ic, GUSMIX_CHAN_MIC, ICSMIX_LEFT, mute);
   3538 	ics2101_mix_mute(ic, GUSMIX_CHAN_MIC, ICSMIX_RIGHT, mute);
   3539 }
   3540 
   3541 STATIC void
   3542 gusics_linein_mute(ic, mute)
   3543 	struct ics2101_softc *ic;
   3544 	int mute;
   3545 {
   3546 	ics2101_mix_mute(ic, GUSMIX_CHAN_LINE, ICSMIX_LEFT, mute);
   3547 	ics2101_mix_mute(ic, GUSMIX_CHAN_LINE, ICSMIX_RIGHT, mute);
   3548 }
   3549 
   3550 STATIC void
   3551 gusics_cd_mute(ic, mute)
   3552 	struct ics2101_softc *ic;
   3553 	int mute;
   3554 {
   3555 	ics2101_mix_mute(ic, GUSMIX_CHAN_CD, ICSMIX_LEFT, mute);
   3556 	ics2101_mix_mute(ic, GUSMIX_CHAN_CD, ICSMIX_RIGHT, mute);
   3557 }
   3558 
   3559 STATIC void
   3560 gusics_dac_mute(ic, mute)
   3561 	struct ics2101_softc *ic;
   3562 	int mute;
   3563 {
   3564 	ics2101_mix_mute(ic, GUSMIX_CHAN_DAC, ICSMIX_LEFT, mute);
   3565 	ics2101_mix_mute(ic, GUSMIX_CHAN_DAC, ICSMIX_RIGHT, mute);
   3566 }
   3567 
   3568 STATIC int
   3569 gusmax_mixer_set_port(addr, cp)
   3570 	void *addr;
   3571 	mixer_ctrl_t *cp;
   3572 {
   3573 	register struct ad1848_softc *ac = addr;
   3574 	register struct gus_softc *sc = ac->parent;
   3575 	struct ad1848_volume vol;
   3576 	int error = EINVAL;
   3577 
   3578 	DPRINTF(("gusmax_mixer_set_port: dev=%d type=%d\n", cp->dev, cp->type));
   3579 
   3580 	switch (cp->dev) {
   3581 #if 0
   3582 	case GUSMAX_MIC_IN_LVL:	/* Microphone */
   3583 		if (cp->type == AUDIO_MIXER_VALUE &&
   3584 		    cp->un.value.num_channels == 1) {
   3585 			/* XXX enable/disable pre-MUX fixed gain */
   3586 			if (gus_to_vol(cp, &vol))
   3587 				error = ad1848_set_mic_gain(ac, &vol);
   3588 		}
   3589 		break;
   3590 #endif
   3591 
   3592 	case GUSMAX_DAC_LVL:		/* dac out */
   3593 		if (cp->type == AUDIO_MIXER_VALUE) {
   3594 			if (gus_to_vol(cp, &vol))
   3595 				error = ad1848_set_aux1_gain(ac, &vol);
   3596 		}
   3597 		break;
   3598 
   3599 	case GUSMAX_LINE_IN_LVL:	/* line in */
   3600 		if (cp->type == AUDIO_MIXER_VALUE) {
   3601 			if (gus_to_vol(cp, &vol))
   3602 				error = cs4231_set_linein_gain(ac, &vol);
   3603 		}
   3604 		break;
   3605 
   3606 	case GUSMAX_MONO_LVL:	/* mic/mono in */
   3607 		if (cp->type == AUDIO_MIXER_VALUE &&
   3608 		    cp->un.value.num_channels == 1) {
   3609 			if (gus_to_vol(cp, &vol))
   3610 				error = cs4231_set_mono_gain(ac, &vol);
   3611 		}
   3612 		break;
   3613 
   3614 	case GUSMAX_CD_LVL:	/* CD: AUX2 */
   3615 		if (cp->type == AUDIO_MIXER_VALUE) {
   3616 			if (gus_to_vol(cp, &vol))
   3617 				error = ad1848_set_aux2_gain(ac, &vol);
   3618 		}
   3619 		break;
   3620 
   3621 	case GUSMAX_MONITOR_LVL:
   3622 		if (cp->type == AUDIO_MIXER_VALUE &&
   3623 		    cp->un.value.num_channels == 1) {
   3624 			vol.left  = cp->un.value.level[AUDIO_MIXER_LEVEL_MONO];
   3625 			error = ad1848_set_mon_gain(ac, &vol);
   3626 		}
   3627 		break;
   3628 
   3629 	case GUSMAX_OUT_LVL:	/* output volume */
   3630 		if (cp->type == AUDIO_MIXER_VALUE) {
   3631 			if (gus_to_vol(cp, &vol))
   3632 				error = ad1848_set_out_gain(ac, &vol);
   3633 		}
   3634 		break;
   3635 
   3636 	case GUSMAX_SPEAKER_LVL:
   3637 		if (cp->type == AUDIO_MIXER_VALUE &&
   3638 		    cp->un.value.num_channels == 1) {
   3639 			if (gus_to_vol(cp, &vol)) {
   3640 				gus_speaker_ctl(sc, vol.left > AUDIO_MIN_GAIN ?
   3641 						SPKR_ON : SPKR_OFF);
   3642 				error = 0;
   3643 			}
   3644 		}
   3645 		break;
   3646 
   3647 	case GUSMAX_LINE_IN_MUTE:
   3648 		if (cp->type == AUDIO_MIXER_ENUM) {
   3649 			ac->line_mute = cp->un.ord ? 1 : 0;
   3650 			DPRINTF(("line mute %d\n", cp->un.ord));
   3651 			cs4231_mute_line(ac, ac->line_mute);
   3652 			gus_linein_ctl(sc, ac->line_mute ? SPKR_OFF : SPKR_ON);
   3653 			error = 0;
   3654 		}
   3655 		break;
   3656 
   3657 	case GUSMAX_DAC_MUTE:
   3658 		if (cp->type == AUDIO_MIXER_ENUM) {
   3659 			ac->aux1_mute = cp->un.ord ? 1 : 0;
   3660 			DPRINTF(("dac mute %d\n", cp->un.ord));
   3661 			ad1848_mute_aux1(ac, ac->aux1_mute);
   3662 			error = 0;
   3663 		}
   3664 		break;
   3665 
   3666 	case GUSMAX_CD_MUTE:
   3667 		if (cp->type == AUDIO_MIXER_ENUM) {
   3668 			ac->aux2_mute = cp->un.ord ? 1 : 0;
   3669 			DPRINTF(("cd mute %d\n", cp->un.ord));
   3670 			ad1848_mute_aux2(ac, ac->aux2_mute);
   3671 			error = 0;
   3672 		}
   3673 		break;
   3674 
   3675 	case GUSMAX_MONO_MUTE:	/* Microphone */
   3676 		if (cp->type == AUDIO_MIXER_ENUM) {
   3677 			ac->mono_mute = cp->un.ord ? 1 : 0;
   3678 			DPRINTF(("mono mute %d\n", cp->un.ord));
   3679 			cs4231_mute_mono(ac, ac->mono_mute);
   3680 			gus_mic_ctl(sc, ac->mono_mute ? SPKR_OFF : SPKR_ON);
   3681 			error = 0;
   3682 		}
   3683 		break;
   3684 
   3685 	case GUSMAX_MONITOR_MUTE:
   3686 		if (cp->type == AUDIO_MIXER_ENUM) {
   3687 			ac->mon_mute = cp->un.ord ? 1 : 0;
   3688 			DPRINTF(("mono mute %d\n", cp->un.ord));
   3689 			cs4231_mute_monitor(ac, ac->mon_mute);
   3690 			error = 0;
   3691 		}
   3692 		break;
   3693 
   3694 	case GUSMAX_SPEAKER_MUTE:
   3695 		if (cp->type == AUDIO_MIXER_ENUM) {
   3696 			gus_speaker_ctl(sc, cp->un.ord ? SPKR_OFF : SPKR_ON);
   3697 			error = 0;
   3698 		}
   3699 		break;
   3700 
   3701 	case GUSMAX_REC_LVL:		/* record level */
   3702 		if (cp->type == AUDIO_MIXER_VALUE) {
   3703 			if (gus_to_vol(cp, &vol))
   3704 				error = ad1848_set_rec_gain(ac, &vol);
   3705 		}
   3706 		break;
   3707 
   3708 	case GUSMAX_RECORD_SOURCE:
   3709 		if (cp->type == AUDIO_MIXER_ENUM) {
   3710 			error = ad1848_set_rec_port(ac, cp->un.ord);
   3711 		}
   3712 		break;
   3713 
   3714 	default:
   3715 		return ENXIO;
   3716 	    /*NOTREACHED*/
   3717     }
   3718     return error;
   3719 }
   3720 
   3721 STATIC int
   3722 gus_mixer_set_port(addr, cp)
   3723 	void *addr;
   3724 	mixer_ctrl_t *cp;
   3725 {
   3726 	register struct gus_softc *sc = addr;
   3727 	register struct ics2101_softc *ic = &sc->sc_mixer;
   3728 	struct ad1848_volume vol;
   3729 	int error = EINVAL;
   3730 
   3731 	DPRINTF(("gus_mixer_set_port: dev=%d type=%d\n", cp->dev, cp->type));
   3732 
   3733 	if (!HAS_MIXER(sc) && cp->dev > GUSICS_MASTER_MUTE)
   3734 		return ENXIO;
   3735 
   3736 	switch (cp->dev) {
   3737 
   3738 	case GUSICS_MIC_IN_MUTE:	/* Microphone */
   3739 		if (cp->type == AUDIO_MIXER_ENUM) {
   3740 			DPRINTF(("mic mute %d\n", cp->un.ord));
   3741 			if (HAS_MIXER(sc)) {
   3742 				gusics_mic_mute(ic, cp->un.ord);
   3743 			}
   3744 			gus_mic_ctl(sc, cp->un.ord ? SPKR_OFF : SPKR_ON);
   3745 			error = 0;
   3746 		}
   3747 		break;
   3748 
   3749 	case GUSICS_LINE_IN_MUTE:
   3750 		if (cp->type == AUDIO_MIXER_ENUM) {
   3751 			DPRINTF(("linein mute %d\n", cp->un.ord));
   3752 			if (HAS_MIXER(sc)) {
   3753 				gusics_linein_mute(ic, cp->un.ord);
   3754 			}
   3755 			gus_linein_ctl(sc, cp->un.ord ? SPKR_OFF : SPKR_ON);
   3756 			error = 0;
   3757 		}
   3758 		break;
   3759 
   3760 	case GUSICS_MASTER_MUTE:
   3761 		if (cp->type == AUDIO_MIXER_ENUM) {
   3762 			DPRINTF(("master mute %d\n", cp->un.ord));
   3763 			if (HAS_MIXER(sc)) {
   3764 				gusics_master_mute(ic, cp->un.ord);
   3765 			}
   3766 			gus_speaker_ctl(sc, cp->un.ord ? SPKR_OFF : SPKR_ON);
   3767 			error = 0;
   3768 		}
   3769 		break;
   3770 
   3771 	case GUSICS_DAC_MUTE:
   3772 		if (cp->type == AUDIO_MIXER_ENUM) {
   3773 			gusics_dac_mute(ic, cp->un.ord);
   3774 			error = 0;
   3775 		}
   3776 		break;
   3777 
   3778 	case GUSICS_CD_MUTE:
   3779 		if (cp->type == AUDIO_MIXER_ENUM) {
   3780 			gusics_cd_mute(ic, cp->un.ord);
   3781 			error = 0;
   3782 		}
   3783 		break;
   3784 
   3785 	case GUSICS_MASTER_LVL:
   3786 		if (cp->type == AUDIO_MIXER_VALUE) {
   3787 			if (gus_to_vol(cp, &vol)) {
   3788 				ics2101_mix_attenuate(ic,
   3789 						      GUSMIX_CHAN_MASTER,
   3790 						      ICSMIX_LEFT,
   3791 						      vol.left);
   3792 				ics2101_mix_attenuate(ic,
   3793 						      GUSMIX_CHAN_MASTER,
   3794 						      ICSMIX_RIGHT,
   3795 						      vol.right);
   3796 				error = 0;
   3797 			}
   3798 		}
   3799 		break;
   3800 
   3801 	case GUSICS_MIC_IN_LVL:	/* Microphone */
   3802 		if (cp->type == AUDIO_MIXER_VALUE) {
   3803 			if (gus_to_vol(cp, &vol)) {
   3804 				ics2101_mix_attenuate(ic,
   3805 						      GUSMIX_CHAN_MIC,
   3806 						      ICSMIX_LEFT,
   3807 						      vol.left);
   3808 				ics2101_mix_attenuate(ic,
   3809 						      GUSMIX_CHAN_MIC,
   3810 						      ICSMIX_RIGHT,
   3811 						      vol.right);
   3812 				error = 0;
   3813 			}
   3814 		}
   3815 		break;
   3816 
   3817 	case GUSICS_LINE_IN_LVL:	/* line in */
   3818 		if (cp->type == AUDIO_MIXER_VALUE) {
   3819 			if (gus_to_vol(cp, &vol)) {
   3820 				ics2101_mix_attenuate(ic,
   3821 						      GUSMIX_CHAN_LINE,
   3822 						      ICSMIX_LEFT,
   3823 						      vol.left);
   3824 				ics2101_mix_attenuate(ic,
   3825 						      GUSMIX_CHAN_LINE,
   3826 						      ICSMIX_RIGHT,
   3827 						      vol.right);
   3828 				error = 0;
   3829 			}
   3830 		}
   3831 		break;
   3832 
   3833 
   3834 	case GUSICS_CD_LVL:
   3835 		if (cp->type == AUDIO_MIXER_VALUE) {
   3836 			if (gus_to_vol(cp, &vol)) {
   3837 				ics2101_mix_attenuate(ic,
   3838 						      GUSMIX_CHAN_CD,
   3839 						      ICSMIX_LEFT,
   3840 						      vol.left);
   3841 				ics2101_mix_attenuate(ic,
   3842 						      GUSMIX_CHAN_CD,
   3843 						      ICSMIX_RIGHT,
   3844 						      vol.right);
   3845 				error = 0;
   3846 			}
   3847 		}
   3848 		break;
   3849 
   3850 	case GUSICS_DAC_LVL:		/* dac out */
   3851 		if (cp->type == AUDIO_MIXER_VALUE) {
   3852 			if (gus_to_vol(cp, &vol)) {
   3853 				ics2101_mix_attenuate(ic,
   3854 						      GUSMIX_CHAN_DAC,
   3855 						      ICSMIX_LEFT,
   3856 						      vol.left);
   3857 				ics2101_mix_attenuate(ic,
   3858 						      GUSMIX_CHAN_DAC,
   3859 						      ICSMIX_RIGHT,
   3860 						      vol.right);
   3861 				error = 0;
   3862 			}
   3863 		}
   3864 		break;
   3865 
   3866 
   3867 	case GUSICS_RECORD_SOURCE:
   3868 		if (cp->type == AUDIO_MIXER_ENUM && cp->un.ord == 0) {
   3869 			/* Can't set anything else useful, sigh. */
   3870 			error = 0;
   3871 		}
   3872 		break;
   3873 
   3874 	default:
   3875 		return ENXIO;
   3876 	    /*NOTREACHED*/
   3877 	}
   3878 	return error;
   3879 }
   3880 
   3881 STATIC int
   3882 gusmax_mixer_query_devinfo(addr, dip)
   3883 	void *addr;
   3884 	register mixer_devinfo_t *dip;
   3885 {
   3886 	DPRINTF(("gusmax_query_devinfo: index=%d\n", dip->index));
   3887 
   3888 	switch(dip->index) {
   3889 	case GUSMAX_MIX_IN:	/* mixed MUX input */
   3890 		dip->type = AUDIO_MIXER_ENUM;
   3891 		dip->mixer_class = GUSMAX_INPUT_CLASS;
   3892 		dip->prev = dip->next = AUDIO_MIXER_LAST;
   3893 		strcpy(dip->label.name, AudioNmixerout);
   3894 		dip->un.e.num_mem = 0;		/* XXX */
   3895 		break;
   3896 
   3897 #if 0
   3898     case GUSMAX_MIC_IN_LVL:	/* Microphone */
   3899 	dip->type = AUDIO_MIXER_VALUE;
   3900 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3901 	dip->prev = AUDIO_MIXER_LAST;
   3902 	dip->next = GUSMAX_MIC_IN_MUTE;
   3903 	strcpy(dip->label.name, AudioNmicrophone);
   3904 	dip->un.v.num_channels = 2;
   3905 	strcpy(dip->un.v.units.name, AudioNvolume);
   3906 	break;
   3907 #endif
   3908 
   3909     case GUSMAX_MONO_LVL:	/* mono/microphone mixer */
   3910 	dip->type = AUDIO_MIXER_VALUE;
   3911 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3912 	dip->prev = AUDIO_MIXER_LAST;
   3913 	dip->next = GUSMAX_MONO_MUTE;
   3914 	strcpy(dip->label.name, AudioNmicrophone);
   3915 	dip->un.v.num_channels = 1;
   3916 	strcpy(dip->un.v.units.name, AudioNvolume);
   3917 	break;
   3918 
   3919     case GUSMAX_DAC_LVL:		/*  dacout */
   3920 	dip->type = AUDIO_MIXER_VALUE;
   3921 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3922 	dip->prev = AUDIO_MIXER_LAST;
   3923 	dip->next = GUSMAX_DAC_MUTE;
   3924 	strcpy(dip->label.name, AudioNdac);
   3925 	dip->un.v.num_channels = 2;
   3926 	strcpy(dip->un.v.units.name, AudioNvolume);
   3927 	break;
   3928 
   3929     case GUSMAX_LINE_IN_LVL:	/* line */
   3930 	dip->type = AUDIO_MIXER_VALUE;
   3931 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3932 	dip->prev = AUDIO_MIXER_LAST;
   3933 	dip->next = GUSMAX_LINE_IN_MUTE;
   3934 	strcpy(dip->label.name, AudioNline);
   3935 	dip->un.v.num_channels = 2;
   3936 	strcpy(dip->un.v.units.name, AudioNvolume);
   3937 	break;
   3938 
   3939     case GUSMAX_CD_LVL:		/* cd */
   3940 	dip->type = AUDIO_MIXER_VALUE;
   3941 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3942 	dip->prev = AUDIO_MIXER_LAST;
   3943 	dip->next = GUSMAX_CD_MUTE;
   3944 	strcpy(dip->label.name, AudioNcd);
   3945 	dip->un.v.num_channels = 2;
   3946 	strcpy(dip->un.v.units.name, AudioNvolume);
   3947 	break;
   3948 
   3949 
   3950     case GUSMAX_MONITOR_LVL:	/* monitor level */
   3951 	dip->type = AUDIO_MIXER_VALUE;
   3952 	dip->mixer_class = GUSMAX_MONITOR_CLASS;
   3953 	dip->next = GUSMAX_MONITOR_MUTE;
   3954 	dip->prev = AUDIO_MIXER_LAST;
   3955 	strcpy(dip->label.name, AudioNmonitor);
   3956 	dip->un.v.num_channels = 1;
   3957 	strcpy(dip->un.v.units.name, AudioNvolume);
   3958 	break;
   3959 
   3960     case GUSMAX_OUT_LVL:		/* cs4231 output volume: not useful? */
   3961 	dip->type = AUDIO_MIXER_VALUE;
   3962 	dip->mixer_class = GUSMAX_MONITOR_CLASS;
   3963 	dip->prev = dip->next = AUDIO_MIXER_LAST;
   3964 	strcpy(dip->label.name, AudioNoutput);
   3965 	dip->un.v.num_channels = 2;
   3966 	strcpy(dip->un.v.units.name, AudioNvolume);
   3967 	break;
   3968 
   3969     case GUSMAX_SPEAKER_LVL:		/* fake speaker volume */
   3970 	dip->type = AUDIO_MIXER_VALUE;
   3971 	dip->mixer_class = GUSMAX_MONITOR_CLASS;
   3972 	dip->prev = AUDIO_MIXER_LAST;
   3973 	dip->next = GUSMAX_SPEAKER_MUTE;
   3974 	strcpy(dip->label.name, AudioNspeaker);
   3975 	dip->un.v.num_channels = 2;
   3976 	strcpy(dip->un.v.units.name, AudioNvolume);
   3977 	break;
   3978 
   3979     case GUSMAX_LINE_IN_MUTE:
   3980 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3981 	dip->type = AUDIO_MIXER_ENUM;
   3982 	dip->prev = GUSMAX_LINE_IN_LVL;
   3983 	dip->next = AUDIO_MIXER_LAST;
   3984 	goto mute;
   3985 
   3986     case GUSMAX_DAC_MUTE:
   3987 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3988 	dip->type = AUDIO_MIXER_ENUM;
   3989 	dip->prev = GUSMAX_DAC_LVL;
   3990 	dip->next = AUDIO_MIXER_LAST;
   3991 	goto mute;
   3992 
   3993     case GUSMAX_CD_MUTE:
   3994 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   3995 	dip->type = AUDIO_MIXER_ENUM;
   3996 	dip->prev = GUSMAX_CD_LVL;
   3997 	dip->next = AUDIO_MIXER_LAST;
   3998 	goto mute;
   3999 
   4000     case GUSMAX_MONO_MUTE:
   4001 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   4002 	dip->type = AUDIO_MIXER_ENUM;
   4003 	dip->prev = GUSMAX_MONO_LVL;
   4004 	dip->next = AUDIO_MIXER_LAST;
   4005 	goto mute;
   4006 
   4007     case GUSMAX_MONITOR_MUTE:
   4008 	dip->mixer_class = GUSMAX_OUTPUT_CLASS;
   4009 	dip->type = AUDIO_MIXER_ENUM;
   4010 	dip->prev = GUSMAX_MONITOR_LVL;
   4011 	dip->next = AUDIO_MIXER_LAST;
   4012 	goto mute;
   4013 
   4014     case GUSMAX_SPEAKER_MUTE:
   4015 	dip->mixer_class = GUSMAX_OUTPUT_CLASS;
   4016 	dip->type = AUDIO_MIXER_ENUM;
   4017 	dip->prev = GUSMAX_SPEAKER_LVL;
   4018 	dip->next = AUDIO_MIXER_LAST;
   4019     mute:
   4020 	strcpy(dip->label.name, AudioNmute);
   4021 	dip->un.e.num_mem = 2;
   4022 	strcpy(dip->un.e.member[0].label.name, AudioNoff);
   4023 	dip->un.e.member[0].ord = 0;
   4024 	strcpy(dip->un.e.member[1].label.name, AudioNon);
   4025 	dip->un.e.member[1].ord = 1;
   4026 	break;
   4027 
   4028     case GUSMAX_REC_LVL:	/* record level */
   4029 	dip->type = AUDIO_MIXER_VALUE;
   4030 	dip->mixer_class = GUSMAX_RECORD_CLASS;
   4031 	dip->prev = AUDIO_MIXER_LAST;
   4032 	dip->next = GUSMAX_RECORD_SOURCE;
   4033 	strcpy(dip->label.name, AudioNrecord);
   4034 	dip->un.v.num_channels = 2;
   4035 	strcpy(dip->un.v.units.name, AudioNvolume);
   4036 	break;
   4037 
   4038     case GUSMAX_RECORD_SOURCE:
   4039 	dip->mixer_class = GUSMAX_RECORD_CLASS;
   4040 	dip->type = AUDIO_MIXER_ENUM;
   4041 	dip->prev = GUSMAX_REC_LVL;
   4042 	dip->next = AUDIO_MIXER_LAST;
   4043 	strcpy(dip->label.name, AudioNsource);
   4044 	dip->un.e.num_mem = 4;
   4045 	strcpy(dip->un.e.member[0].label.name, AudioNoutput);
   4046 	dip->un.e.member[0].ord = GUSMAX_MIX_IN;
   4047 	strcpy(dip->un.e.member[1].label.name, AudioNmicrophone);
   4048 	dip->un.e.member[1].ord = GUSMAX_MONO_LVL;
   4049 	strcpy(dip->un.e.member[2].label.name, AudioNdac);
   4050 	dip->un.e.member[2].ord = GUSMAX_DAC_LVL;
   4051 	strcpy(dip->un.e.member[3].label.name, AudioNline);
   4052 	dip->un.e.member[3].ord = GUSMAX_LINE_IN_LVL;
   4053 	break;
   4054 
   4055     case GUSMAX_INPUT_CLASS:			/* input class descriptor */
   4056 	dip->type = AUDIO_MIXER_CLASS;
   4057 	dip->mixer_class = GUSMAX_INPUT_CLASS;
   4058 	dip->next = dip->prev = AUDIO_MIXER_LAST;
   4059 	strcpy(dip->label.name, AudioCInputs);
   4060 	break;
   4061 
   4062     case GUSMAX_OUTPUT_CLASS:			/* output class descriptor */
   4063 	dip->type = AUDIO_MIXER_CLASS;
   4064 	dip->mixer_class = GUSMAX_OUTPUT_CLASS;
   4065 	dip->next = dip->prev = AUDIO_MIXER_LAST;
   4066 	strcpy(dip->label.name, AudioCOutputs);
   4067 	break;
   4068 
   4069     case GUSMAX_MONITOR_CLASS:			/* monitor class descriptor */
   4070 	dip->type = AUDIO_MIXER_CLASS;
   4071 	dip->mixer_class = GUSMAX_MONITOR_CLASS;
   4072 	dip->next = dip->prev = AUDIO_MIXER_LAST;
   4073 	strcpy(dip->label.name, AudioCMonitor);
   4074 	break;
   4075 
   4076     case GUSMAX_RECORD_CLASS:			/* record source class */
   4077 	dip->type = AUDIO_MIXER_CLASS;
   4078 	dip->mixer_class = GUSMAX_RECORD_CLASS;
   4079 	dip->next = dip->prev = AUDIO_MIXER_LAST;
   4080 	strcpy(dip->label.name, AudioCRecord);
   4081 	break;
   4082 
   4083     default:
   4084 	return ENXIO;
   4085 	/*NOTREACHED*/
   4086     }
   4087     DPRINTF(("AUDIO_MIXER_DEVINFO: name=%s\n", dip->label.name));
   4088 	return 0;
   4089 }
   4090 
   4091 STATIC int
   4092 gus_mixer_query_devinfo(addr, dip)
   4093 	void *addr;
   4094 	register mixer_devinfo_t *dip;
   4095 {
   4096 	register struct gus_softc *sc = addr;
   4097 
   4098 	DPRINTF(("gusmax_query_devinfo: index=%d\n", dip->index));
   4099 
   4100 	if (!HAS_MIXER(sc) && dip->index > GUSICS_MASTER_MUTE)
   4101 		return ENXIO;
   4102 
   4103 	switch(dip->index) {
   4104 
   4105 	case GUSICS_MIC_IN_LVL:	/* Microphone */
   4106 		dip->type = AUDIO_MIXER_VALUE;
   4107 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4108 		dip->prev = AUDIO_MIXER_LAST;
   4109 		dip->next = GUSICS_MIC_IN_MUTE;
   4110 		strcpy(dip->label.name, AudioNmicrophone);
   4111 		dip->un.v.num_channels = 2;
   4112 		strcpy(dip->un.v.units.name, AudioNvolume);
   4113 		break;
   4114 
   4115 	case GUSICS_LINE_IN_LVL:	/* line */
   4116 		dip->type = AUDIO_MIXER_VALUE;
   4117 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4118 		dip->prev = AUDIO_MIXER_LAST;
   4119 		dip->next = GUSICS_LINE_IN_MUTE;
   4120 		strcpy(dip->label.name, AudioNline);
   4121 		dip->un.v.num_channels = 2;
   4122 		strcpy(dip->un.v.units.name, AudioNvolume);
   4123 		break;
   4124 
   4125 	case GUSICS_CD_LVL:		/* cd */
   4126 		dip->type = AUDIO_MIXER_VALUE;
   4127 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4128 		dip->prev = AUDIO_MIXER_LAST;
   4129 		dip->next = GUSICS_CD_MUTE;
   4130 		strcpy(dip->label.name, AudioNcd);
   4131 		dip->un.v.num_channels = 2;
   4132 		strcpy(dip->un.v.units.name, AudioNvolume);
   4133 		break;
   4134 
   4135 	case GUSICS_DAC_LVL:		/*  dacout */
   4136 		dip->type = AUDIO_MIXER_VALUE;
   4137 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4138 		dip->prev = AUDIO_MIXER_LAST;
   4139 		dip->next = GUSICS_DAC_MUTE;
   4140 		strcpy(dip->label.name, AudioNdac);
   4141 		dip->un.v.num_channels = 2;
   4142 		strcpy(dip->un.v.units.name, AudioNvolume);
   4143 		break;
   4144 
   4145 	case GUSICS_MASTER_LVL:		/*  master output */
   4146 		dip->type = AUDIO_MIXER_VALUE;
   4147 		dip->mixer_class = GUSICS_OUTPUT_CLASS;
   4148 		dip->prev = AUDIO_MIXER_LAST;
   4149 		dip->next = GUSICS_MASTER_MUTE;
   4150 		strcpy(dip->label.name, AudioNvolume);
   4151 		dip->un.v.num_channels = 2;
   4152 		strcpy(dip->un.v.units.name, AudioNvolume);
   4153 		break;
   4154 
   4155 
   4156 	case GUSICS_LINE_IN_MUTE:
   4157 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4158 		dip->type = AUDIO_MIXER_ENUM;
   4159 		dip->prev = GUSICS_LINE_IN_LVL;
   4160 		dip->next = AUDIO_MIXER_LAST;
   4161 		goto mute;
   4162 
   4163 	case GUSICS_DAC_MUTE:
   4164 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4165 		dip->type = AUDIO_MIXER_ENUM;
   4166 		dip->prev = GUSICS_DAC_LVL;
   4167 		dip->next = AUDIO_MIXER_LAST;
   4168 		goto mute;
   4169 
   4170 	case GUSICS_CD_MUTE:
   4171 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4172 		dip->type = AUDIO_MIXER_ENUM;
   4173 		dip->prev = GUSICS_CD_LVL;
   4174 		dip->next = AUDIO_MIXER_LAST;
   4175 		goto mute;
   4176 
   4177 	case GUSICS_MIC_IN_MUTE:
   4178 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4179 		dip->type = AUDIO_MIXER_ENUM;
   4180 		dip->prev = GUSICS_MIC_IN_LVL;
   4181 		dip->next = AUDIO_MIXER_LAST;
   4182 		goto mute;
   4183 
   4184 	case GUSICS_MASTER_MUTE:
   4185 		dip->mixer_class = GUSICS_OUTPUT_CLASS;
   4186 		dip->type = AUDIO_MIXER_ENUM;
   4187 		dip->prev = GUSICS_MASTER_LVL;
   4188 		dip->next = AUDIO_MIXER_LAST;
   4189 mute:
   4190 		strcpy(dip->label.name, AudioNmute);
   4191 		dip->un.e.num_mem = 2;
   4192 		strcpy(dip->un.e.member[0].label.name, AudioNoff);
   4193 		dip->un.e.member[0].ord = 0;
   4194 		strcpy(dip->un.e.member[1].label.name, AudioNon);
   4195 		dip->un.e.member[1].ord = 1;
   4196 		break;
   4197 
   4198 	case GUSICS_RECORD_SOURCE:
   4199 		dip->mixer_class = GUSICS_RECORD_CLASS;
   4200 		dip->type = AUDIO_MIXER_ENUM;
   4201 		dip->prev = dip->next = AUDIO_MIXER_LAST;
   4202 		strcpy(dip->label.name, AudioNsource);
   4203 		dip->un.e.num_mem = 1;
   4204 		strcpy(dip->un.e.member[0].label.name, AudioNoutput);
   4205 		dip->un.e.member[0].ord = GUSICS_MASTER_LVL;
   4206 		break;
   4207 
   4208 	case GUSICS_INPUT_CLASS:
   4209 		dip->type = AUDIO_MIXER_CLASS;
   4210 		dip->mixer_class = GUSICS_INPUT_CLASS;
   4211 		dip->next = dip->prev = AUDIO_MIXER_LAST;
   4212 		strcpy(dip->label.name, AudioCInputs);
   4213 		break;
   4214 
   4215 	case GUSICS_OUTPUT_CLASS:
   4216 		dip->type = AUDIO_MIXER_CLASS;
   4217 		dip->mixer_class = GUSICS_OUTPUT_CLASS;
   4218 		dip->next = dip->prev = AUDIO_MIXER_LAST;
   4219 		strcpy(dip->label.name, AudioCOutputs);
   4220 		break;
   4221 
   4222 	case GUSICS_RECORD_CLASS:
   4223 		dip->type = AUDIO_MIXER_CLASS;
   4224 		dip->mixer_class = GUSICS_RECORD_CLASS;
   4225 		dip->next = dip->prev = AUDIO_MIXER_LAST;
   4226 		strcpy(dip->label.name, AudioCRecord);
   4227 		break;
   4228 
   4229 	default:
   4230 		return ENXIO;
   4231 	/*NOTREACHED*/
   4232 	}
   4233 	DPRINTF(("AUDIO_MIXER_DEVINFO: name=%s\n", dip->label.name));
   4234 	return 0;
   4235 }
   4236 
   4237 STATIC int
   4238 gus_query_encoding(addr, fp)
   4239 	void *addr;
   4240 	struct audio_encoding *fp;
   4241 {
   4242 	switch (fp->index) {
   4243 	case 0:
   4244 		strcpy(fp->name, AudioEmulaw);
   4245 		fp->encoding = AUDIO_ENCODING_ULAW;
   4246 		fp->precision = 8;
   4247 		fp->flags = AUDIO_ENCODINGFLAG_EMULATED;
   4248 		break;
   4249 	case 1:
   4250 		strcpy(fp->name, AudioElinear);
   4251 		fp->encoding = AUDIO_ENCODING_LINEAR;
   4252 		fp->precision = 8;
   4253 		fp->flags = 0;
   4254 		break;
   4255 	case 2:
   4256 		strcpy(fp->name, AudioElinear_le);
   4257 		fp->encoding = AUDIO_ENCODING_LINEAR_LE;
   4258 		fp->precision = 16;
   4259 		fp->flags = 0;
   4260 		break;
   4261 	case 3:
   4262 		strcpy(fp->name, AudioEulinear);
   4263 		fp->encoding = AUDIO_ENCODING_ULINEAR;
   4264 		fp->precision = 8;
   4265 		fp->flags = 0;
   4266 		break;
   4267 	case 4:
   4268 		strcpy(fp->name, AudioEulinear_le);
   4269 		fp->encoding = AUDIO_ENCODING_ULINEAR_LE;
   4270 		fp->precision = 16;
   4271 		fp->flags = 0;
   4272 		break;
   4273 	default:
   4274 		return(EINVAL);
   4275 		/*NOTREACHED*/
   4276 	}
   4277 	return (0);
   4278 }
   4279 
   4280 /*
   4281  * Setup the ICS mixer in "transparent" mode: reset everything to a sensible
   4282  * level.  Levels as suggested by GUS SDK code.
   4283  */
   4284 
   4285 STATIC void
   4286 gus_init_ics2101(sc)
   4287 	struct gus_softc *sc;
   4288 {
   4289 	register int port = sc->sc_iobase;
   4290 	register struct ics2101_softc *ic = &sc->sc_mixer;
   4291 	sc->sc_mixer.sc_selio = port+GUS_MIXER_SELECT;
   4292 	sc->sc_mixer.sc_dataio = port+GUS_MIXER_DATA;
   4293 	sc->sc_mixer.sc_flags = (sc->sc_revision == 5) ? ICS_FLIP : 0;
   4294 
   4295 	ics2101_mix_attenuate(ic,
   4296 			      GUSMIX_CHAN_MIC,
   4297 			      ICSMIX_LEFT,
   4298 			      ICSMIX_MIN_ATTN);
   4299 	ics2101_mix_attenuate(ic,
   4300 			      GUSMIX_CHAN_MIC,
   4301 			      ICSMIX_RIGHT,
   4302 			      ICSMIX_MIN_ATTN);
   4303 	/*
   4304 	 * Start with microphone muted by the mixer...
   4305 	 */
   4306 	gusics_mic_mute(ic, 1);
   4307 
   4308 	/* ... and enabled by the GUS master mix control */
   4309 	gus_mic_ctl(sc, SPKR_ON);
   4310 
   4311 	ics2101_mix_attenuate(ic,
   4312 			      GUSMIX_CHAN_LINE,
   4313 			      ICSMIX_LEFT,
   4314 			      ICSMIX_MIN_ATTN);
   4315 	ics2101_mix_attenuate(ic,
   4316 			      GUSMIX_CHAN_LINE,
   4317 			      ICSMIX_RIGHT,
   4318 			      ICSMIX_MIN_ATTN);
   4319 
   4320 	ics2101_mix_attenuate(ic,
   4321 			      GUSMIX_CHAN_CD,
   4322 			      ICSMIX_LEFT,
   4323 			      ICSMIX_MIN_ATTN);
   4324 	ics2101_mix_attenuate(ic,
   4325 			      GUSMIX_CHAN_CD,
   4326 			      ICSMIX_RIGHT,
   4327 			      ICSMIX_MIN_ATTN);
   4328 
   4329 	ics2101_mix_attenuate(ic,
   4330 			      GUSMIX_CHAN_DAC,
   4331 			      ICSMIX_LEFT,
   4332 			      ICSMIX_MIN_ATTN);
   4333 	ics2101_mix_attenuate(ic,
   4334 			      GUSMIX_CHAN_DAC,
   4335 			      ICSMIX_RIGHT,
   4336 			      ICSMIX_MIN_ATTN);
   4337 
   4338 	ics2101_mix_attenuate(ic,
   4339 			      ICSMIX_CHAN_4,
   4340 			      ICSMIX_LEFT,
   4341 			      ICSMIX_MAX_ATTN);
   4342 	ics2101_mix_attenuate(ic,
   4343 			      ICSMIX_CHAN_4,
   4344 			      ICSMIX_RIGHT,
   4345 			      ICSMIX_MAX_ATTN);
   4346 
   4347 	ics2101_mix_attenuate(ic,
   4348 			      GUSMIX_CHAN_MASTER,
   4349 			      ICSMIX_LEFT,
   4350 			      ICSMIX_MIN_ATTN);
   4351 	ics2101_mix_attenuate(ic,
   4352 			      GUSMIX_CHAN_MASTER,
   4353 			      ICSMIX_RIGHT,
   4354 			      ICSMIX_MIN_ATTN);
   4355 	/* unmute other stuff: */
   4356 	gusics_cd_mute(ic, 0);
   4357 	gusics_dac_mute(ic, 0);
   4358 	gusics_linein_mute(ic, 0);
   4359 	return;
   4360 }
   4361 
   4362 
   4363 #endif /* NGUS */
   4364