xref: /openbsd-src/sys/dev/pci/auich.c (revision 5054e3e78af0749a9bb00ba9a024b3ee2d90290f)
1 /*	$OpenBSD: auich.c,v 1.79 2009/11/05 01:29:06 jakemsr Exp $	*/
2 
3 /*
4  * Copyright (c) 2000,2001 Michael Shalayeff
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19  * IN NO EVENT SHALL THE AUTHOR OR HIS RELATIVES BE LIABLE FOR ANY DIRECT,
20  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
22  * SERVICES; LOSS OF MIND, USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
24  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
25  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
26  * THE POSSIBILITY OF SUCH DAMAGE.
27  */
28 
29 /* #define	AUICH_DEBUG */
30 /*
31  * AC'97 audio found on Intel 810/815/820/440MX chipsets.
32  *	http://developer.intel.com/design/chipsets/datashts/290655.htm
33  *	http://developer.intel.com/design/chipsets/manuals/298028.htm
34  *	http://www.intel.com/design/chipsets/datashts/290716.htm
35  *	http://www.intel.com/design/chipsets/datashts/290744.htm
36  */
37 
38 #include <sys/param.h>
39 #include <sys/systm.h>
40 #include <sys/kernel.h>
41 #include <sys/malloc.h>
42 #include <sys/device.h>
43 
44 #include <dev/pci/pcidevs.h>
45 #include <dev/pci/pcivar.h>
46 
47 #include <sys/audioio.h>
48 #include <dev/audio_if.h>
49 #include <dev/mulaw.h>
50 #include <dev/auconv.h>
51 
52 #include <machine/bus.h>
53 
54 #include <dev/ic/ac97.h>
55 
56 /* 12.1.10 NAMBAR - native audio mixer base address register */
57 #define	AUICH_NAMBAR	0x10
58 /* 12.1.11 NABMBAR - native audio bus mastering base address register */
59 #define	AUICH_NABMBAR	0x14
60 #define	AUICH_CFG	0x41
61 #define	AUICH_CFG_IOSE	0x01
62 /* ICH4/ICH5/ICH6/ICH7 native audio mixer BAR */
63 #define	AUICH_MMBAR	0x18
64 /* ICH4/ICH5/ICH6/ICH7 native bus mastering BAR */
65 #define	AUICH_MBBAR	0x1c
66 #define	AUICH_S2CR	0x10000000	/* tertiary codec ready */
67 
68 /* table 12-3. native audio bus master control registers */
69 #define	AUICH_BDBAR	0x00	/* 8-byte aligned address */
70 #define	AUICH_CIV		0x04	/* 5 bits current index value */
71 #define	AUICH_LVI		0x05	/* 5 bits last valid index value */
72 #define		AUICH_LVI_MASK	0x1f
73 #define	AUICH_STS		0x06	/* 16 bits status */
74 #define		AUICH_FIFOE	0x10	/* fifo error */
75 #define		AUICH_BCIS	0x08	/* r- buf cmplt int sts; wr ack */
76 #define		AUICH_LVBCI	0x04	/* r- last valid bci, wr ack */
77 #define		AUICH_CELV	0x02	/* current equals last valid */
78 #define		AUICH_DCH		0x01	/* dma halted */
79 #define		AUICH_ISTS_BITS	"\020\01dch\02celv\03lvbci\04bcis\05fifoe"
80 #define	AUICH_PICB	0x08	/* 16 bits */
81 #define	AUICH_PIV		0x0a	/* 5 bits prefetched index value */
82 #define	AUICH_CTRL	0x0b	/* control */
83 #define		AUICH_IOCE	0x10	/* int on completion enable */
84 #define		AUICH_FEIE	0x08	/* fifo error int enable */
85 #define		AUICH_LVBIE	0x04	/* last valid buf int enable */
86 #define		AUICH_RR		0x02	/* 1 - reset regs */
87 #define		AUICH_RPBM	0x01	/* 1 - run, 0 - pause */
88 
89 #define	AUICH_PCMI	0x00
90 #define	AUICH_PCMO	0x10
91 #define	AUICH_MICI	0x20
92 
93 #define	AUICH_GCTRL	0x2c
94 #define		AUICH_SSM_78	0x40000000	/* S/PDIF slots 7 and 8 */
95 #define		AUICH_SSM_69	0x80000000	/* S/PDIF slots 6 and 9 */
96 #define		AUICH_SSM_1011	0xc0000000	/* S/PDIF slots 10 and 11 */
97 #define		AUICH_POM16	0x000000	/* PCM out precision 16bit */
98 #define		AUICH_POM20	0x400000	/* PCM out precision 20bit */
99 #define		AUICH_PCM246_MASK 0x300000
100 #define		AUICH_PCM2	0x000000	/* 2ch output */
101 #define		AUICH_PCM4	0x100000	/* 4ch output */
102 #define		AUICH_PCM6	0x200000	/* 6ch output */
103 #define		AUICH_SIS_PCM246_MASK 0x0000c0	/* SiS 7012 */
104 #define		AUICH_SIS_PCM2	0x000000	/* SiS 7012 2ch output */
105 #define		AUICH_SIS_PCM4	0x000040	/* SiS 7012 4ch output */
106 #define		AUICH_SIS_PCM6	0x000080	/* SiS 7012 6ch output */
107 #define		AUICH_S2RIE	0x40	/* int when tertiary codec resume */
108 #define		AUICH_SRIE	0x20	/* int when 2ndary codec resume */
109 #define		AUICH_PRIE	0x10	/* int when primary codec resume */
110 #define		AUICH_ACLSO	0x08	/* aclink shut off */
111 #define		AUICH_WRESET	0x04	/* warm reset */
112 #define		AUICH_CRESET	0x02	/* cold reset */
113 #define		AUICH_GIE		0x01	/* gpi int enable */
114 #define	AUICH_GSTS	0x30
115 #define		AUICH_MD3		0x20000	/* pwr-dn semaphore for modem */
116 #define		AUICH_AD3		0x10000	/* pwr-dn semaphore for audio */
117 #define		AUICH_RCS		0x08000	/* read completion status */
118 #define		AUICH_B3S12	0x04000	/* bit 3 of slot 12 */
119 #define		AUICH_B2S12	0x02000	/* bit 2 of slot 12 */
120 #define		AUICH_B1S12	0x01000	/* bit 1 of slot 12 */
121 #define		AUICH_SRI		0x00800	/* secondary resume int */
122 #define		AUICH_PRI		0x00400	/* primary resume int */
123 #define		AUICH_SCR		0x00200	/* secondary codec ready */
124 #define		AUICH_PCR		0x00100	/* primary codec ready */
125 #define		AUICH_MINT	0x00080	/* mic in int */
126 #define		AUICH_POINT	0x00040	/* pcm out int */
127 #define		AUICH_PIINT	0x00020	/* pcm in int */
128 #define		AUICH_MOINT	0x00004	/* modem out int */
129 #define		AUICH_MIINT	0x00002	/* modem in int */
130 #define		AUICH_GSCI	0x00001	/* gpi status change */
131 #define		AUICH_GSTS_BITS	"\020\01gsci\02miict\03moint\06piint\07point\010mint\011pcr\012scr\013pri\014sri\015b1s12\016b2s12\017b3s12\020rcs\021ad3\022md3"
132 #define	AUICH_CAS		0x34	/* 1/8 bit */
133 #define	AUICH_SEMATIMO		1000	/* us */
134 #define	AUICH_RESETIMO		500000	/* us */
135 
136 #define	ICH_SIS_NV_CTL	0x4c	/* some SiS/NVIDIA register.  From Linux */
137 #define		ICH_SIS_CTL_UNMUTE	0x01	/* un-mute the output */
138 
139 /*
140  * There are 32 buffer descriptors.  Each can reference up to 2^16 16-bit
141  * samples.
142  */
143 #define	AUICH_DMALIST_MAX	32
144 #define	AUICH_DMASEG_MAX	(65536*2)
145 struct auich_dmalist {
146 	u_int32_t	base;
147 	u_int32_t	len;
148 #define	AUICH_DMAF_IOC	0x80000000	/* 1-int on complete */
149 #define	AUICH_DMAF_BUP	0x40000000	/* 0-retrans last, 1-transmit 0 */
150 };
151 
152 #define	AUICH_FIXED_RATE 48000
153 
154 struct auich_dma {
155 	bus_dmamap_t map;
156 	caddr_t addr;
157 	bus_dma_segment_t segs[1];
158 	int nsegs;
159 	size_t size;
160 };
161 
162 struct auich_cdata {
163 	struct auich_dmalist ic_dmalist_pcmo[AUICH_DMALIST_MAX];
164 	struct auich_dmalist ic_dmalist_pcmi[AUICH_DMALIST_MAX];
165 	struct auich_dmalist ic_dmalist_mici[AUICH_DMALIST_MAX];
166 };
167 
168 #define	AUICH_CDOFF(x)		offsetof(struct auich_cdata, x)
169 #define	AUICH_PCMO_OFF(x)	AUICH_CDOFF(ic_dmalist_pcmo[(x)])
170 #define	AUICH_PCMI_OFF(x)	AUICH_CDOFF(ic_dmalist_pcmi[(x)])
171 #define	AUICH_MICI_OFF(x)	AUICH_CDOFF(ic_dmalist_mici[(x)])
172 
173 struct auich_softc {
174 	struct device sc_dev;
175 	void *sc_ih;
176 
177 	audio_device_t sc_audev;
178 
179 	bus_space_tag_t iot;
180 	bus_space_tag_t iot_mix;
181 	bus_space_handle_t mix_ioh;
182 	bus_space_handle_t aud_ioh;
183 	bus_dma_tag_t dmat;
184 
185 	struct ac97_codec_if *codec_if;
186 	struct ac97_host_if host_if;
187 	int sc_spdif;
188 
189 	/* dma scatter-gather buffer lists */
190 
191 	bus_dmamap_t sc_cddmamap;
192 #define	sc_cddma	sc_cddmamap->dm_segs[0].ds_addr
193 
194 	struct auich_cdata *sc_cdata;
195 
196 	struct auich_ring {
197 		int qptr;
198 		struct auich_dmalist *dmalist;
199 
200 		uint32_t start, p, end;
201 		int blksize;
202 
203 		void (*intr)(void *);
204 		void *arg;
205 	} pcmo, pcmi, mici;
206 
207 	struct auich_dma *sc_pdma;	/* play */
208 	struct auich_dma *sc_rdma;	/* record */
209 	struct auich_dma *sc_cdma;	/* calibrate */
210 
211 #ifdef AUICH_DEBUG
212 	int pcmi_fifoe;
213 	int pcmo_fifoe;
214 #endif
215 
216 	void *powerhook;
217 	int suspend;
218 	u_int16_t ext_ctrl;
219 	int sc_sample_size;
220 	int sc_sts_reg;
221 	int sc_dmamap_flags;
222 	int sc_ignore_codecready;
223 	int flags;
224 	int sc_ac97rate;
225 
226 	/* multi-channel control bits */
227 	int sc_pcm246_mask;
228 	int sc_pcm2;
229 	int sc_pcm4;
230 	int sc_pcm6;
231 };
232 
233 #ifdef AUICH_DEBUG
234 #define	DPRINTF(l,x)	do { if (auich_debug & (l)) printf x; } while(0)
235 int auich_debug = 0xfffe;
236 #define	AUICH_DEBUG_CODECIO	0x0001
237 #define	AUICH_DEBUG_DMA		0x0002
238 #define	AUICH_DEBUG_INTR	0x0004
239 #else
240 #define	DPRINTF(x,y)	/* nothing */
241 #endif
242 
243 struct cfdriver	auich_cd = {
244 	NULL, "auich", DV_DULL
245 };
246 
247 int  auich_match(struct device *, void *, void *);
248 void auich_attach(struct device *, struct device *, void *);
249 int  auich_intr(void *);
250 
251 struct cfattach auich_ca = {
252 	sizeof(struct auich_softc), auich_match, auich_attach
253 };
254 
255 static const struct auich_devtype {
256 	int	vendor;
257 	int	product;
258 	int	options;
259 	char	name[8];
260 } auich_devices[] = {
261 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_6300ESB_ACA,	0, "ESB" },
262 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_6321ESB_ACA,	0, "ESB2" },
263 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801AA_ACA,	0, "ICH" },
264 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801AB_ACA,	0, "ICH0" },
265 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801BA_ACA,	0, "ICH2" },
266 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801CA_ACA,	0, "ICH3" },
267 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801DB_ACA,	0, "ICH4" },
268 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801EB_ACA,	0, "ICH5" },
269 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801FB_ACA,	0, "ICH6" },
270 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82801GB_ACA,	0, "ICH7" },
271 	{ PCI_VENDOR_INTEL,	PCI_PRODUCT_INTEL_82440MX_ACA,	0, "440MX" },
272 	{ PCI_VENDOR_SIS,	PCI_PRODUCT_SIS_7012_ACA,	0, "SiS7012" },
273 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_NFORCE_ACA,	0, "nForce" },
274 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_NFORCE2_ACA,	0, "nForce2" },
275 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_NFORCE2_400_ACA,
276 	    0, "nForce2" },
277 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_NFORCE3_ACA,	0, "nForce3" },
278 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_NFORCE3_250_ACA,
279 	    0, "nForce3" },
280 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_NFORCE4_AC,	0, "nForce4" },
281 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_MCP04_AC97,	0, "MCP04" },
282 	{ PCI_VENDOR_NVIDIA,	PCI_PRODUCT_NVIDIA_MCP51_ACA,	0, "MCP51" },
283 	{ PCI_VENDOR_AMD,	PCI_PRODUCT_AMD_PBC768_ACA,	0, "AMD768" },
284 	{ PCI_VENDOR_AMD,	PCI_PRODUCT_AMD_8111_ACA,	0, "AMD8111" },
285 };
286 
287 int auich_open(void *, int);
288 void auich_close(void *);
289 int auich_query_encoding(void *, struct audio_encoding *);
290 int auich_set_params(void *, int, int, struct audio_params *,
291     struct audio_params *);
292 int auich_round_blocksize(void *, int);
293 void auich_halt_pipe(struct auich_softc *, int);
294 int auich_halt_output(void *);
295 int auich_halt_input(void *);
296 int auich_getdev(void *, struct audio_device *);
297 int auich_set_port(void *, mixer_ctrl_t *);
298 int auich_get_port(void *, mixer_ctrl_t *);
299 int auich_query_devinfo(void *, mixer_devinfo_t *);
300 void *auich_allocm(void *, int, size_t, int, int);
301 void auich_freem(void *, void *, int);
302 size_t auich_round_buffersize(void *, int, size_t);
303 paddr_t auich_mappage(void *, void *, off_t, int);
304 int auich_get_props(void *);
305 void auich_trigger_pipe(struct auich_softc *, int, struct auich_ring *);
306 void auich_intr_pipe(struct auich_softc *, int, struct auich_ring *);
307 int auich_trigger_output(void *, void *, void *, int, void (*)(void *),
308     void *, struct audio_params *);
309 int auich_trigger_input(void *, void *, void *, int, void (*)(void *),
310     void *, struct audio_params *);
311 int auich_alloc_cdata(struct auich_softc *);
312 int auich_allocmem(struct auich_softc *, size_t, size_t, struct auich_dma *);
313 int auich_freemem(struct auich_softc *, struct auich_dma *);
314 void auich_get_default_params(void *, int, struct audio_params *);
315 
316 void auich_powerhook(int, void *);
317 
318 struct audio_hw_if auich_hw_if = {
319 	auich_open,
320 	auich_close,
321 	NULL,			/* drain */
322 	auich_query_encoding,
323 	auich_set_params,
324 	auich_round_blocksize,
325 	NULL,			/* commit_setting */
326 	NULL,			/* init_output */
327 	NULL,			/* init_input */
328 	NULL,			/* start_output */
329 	NULL,			/* start_input */
330 	auich_halt_output,
331 	auich_halt_input,
332 	NULL,			/* speaker_ctl */
333 	auich_getdev,
334 	NULL,			/* getfd */
335 	auich_set_port,
336 	auich_get_port,
337 	auich_query_devinfo,
338 	auich_allocm,
339 	auich_freem,
340 	auich_round_buffersize,
341 	auich_mappage,
342 	auich_get_props,
343 	auich_trigger_output,
344 	auich_trigger_input,
345 	auich_get_default_params
346 };
347 
348 int  auich_attach_codec(void *, struct ac97_codec_if *);
349 int  auich_read_codec(void *, u_int8_t, u_int16_t *);
350 int  auich_write_codec(void *, u_int8_t, u_int16_t);
351 void auich_reset_codec(void *);
352 enum ac97_host_flags auich_flags_codec(void *);
353 unsigned int auich_calibrate(struct auich_softc *);
354 void auich_spdif_event(void *, int);
355 
356 int
357 auich_match(parent, match, aux)
358 	struct device *parent;
359 	void *match;
360 	void *aux;
361 {
362 	struct pci_attach_args *pa = aux;
363 	int i;
364 
365 	for (i = sizeof(auich_devices)/sizeof(auich_devices[0]); i--;)
366 		if (PCI_VENDOR(pa->pa_id) == auich_devices[i].vendor &&
367 		    PCI_PRODUCT(pa->pa_id) == auich_devices[i].product)
368 			return 1;
369 
370 	return 0;
371 }
372 
373 void
374 auich_attach(parent, self, aux)
375 	struct device *parent, *self;
376 	void *aux;
377 {
378 	struct auich_softc *sc = (struct auich_softc *)self;
379 	struct pci_attach_args *pa = aux;
380 	pci_intr_handle_t ih;
381 	bus_size_t mix_size, aud_size;
382 	pcireg_t csr;
383 	const char *intrstr;
384 	u_int32_t status;
385 	int i;
386 
387 	if (PCI_VENDOR(pa->pa_id) == PCI_VENDOR_INTEL &&
388 	    (PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801DB_ACA ||
389 	    PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801EB_ACA ||
390 	    PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801FB_ACA ||
391 	    PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801GB_ACA)) {
392 		/*
393 		 * Use native mode for ICH4/ICH5/ICH6/ICH7
394 		 */
395 		if (pci_mapreg_map(pa, AUICH_MMBAR, PCI_MAPREG_TYPE_MEM, 0,
396 		    &sc->iot_mix, &sc->mix_ioh, NULL, &mix_size, 0)) {
397 			csr = pci_conf_read(pa->pa_pc, pa->pa_tag, AUICH_CFG);
398 			pci_conf_write(pa->pa_pc, pa->pa_tag, AUICH_CFG,
399 			    csr | AUICH_CFG_IOSE);
400 			if (pci_mapreg_map(pa, AUICH_NAMBAR, PCI_MAPREG_TYPE_IO,
401 			    0, &sc->iot_mix, &sc->mix_ioh, NULL, &mix_size, 0)) {
402 				printf(": can't map codec mem/io space\n");
403 				return;
404 			}
405 		}
406 
407 		if (pci_mapreg_map(pa, AUICH_MBBAR, PCI_MAPREG_TYPE_MEM, 0,
408 		    &sc->iot, &sc->aud_ioh, NULL, &aud_size, 0)) {
409 			csr = pci_conf_read(pa->pa_pc, pa->pa_tag, AUICH_CFG);
410 			pci_conf_write(pa->pa_pc, pa->pa_tag, AUICH_CFG,
411 			    csr | AUICH_CFG_IOSE);
412 			if (pci_mapreg_map(pa, AUICH_NABMBAR,
413 			    PCI_MAPREG_TYPE_IO, 0, &sc->iot,
414 			    &sc->aud_ioh, NULL, &aud_size, 0)) {
415 				printf(": can't map device mem/io space\n");
416 				bus_space_unmap(sc->iot_mix, sc->mix_ioh, mix_size);
417 				return;
418 			}
419 		}
420 	} else {
421 		if (pci_mapreg_map(pa, AUICH_NAMBAR, PCI_MAPREG_TYPE_IO,
422 		    0, &sc->iot_mix, &sc->mix_ioh, NULL, &mix_size, 0)) {
423 			printf(": can't map codec i/o space\n");
424 			return;
425 		}
426 
427 		if (pci_mapreg_map(pa, AUICH_NABMBAR, PCI_MAPREG_TYPE_IO,
428 		    0, &sc->iot, &sc->aud_ioh, NULL, &aud_size, 0)) {
429 			printf(": can't map device i/o space\n");
430 			bus_space_unmap(sc->iot_mix, sc->mix_ioh, mix_size);
431 			return;
432 		}
433 	}
434 	sc->dmat = pa->pa_dmat;
435 
436 	if (pci_intr_map(pa, &ih)) {
437 		bus_space_unmap(sc->iot, sc->aud_ioh, aud_size);
438 		bus_space_unmap(sc->iot_mix, sc->mix_ioh, mix_size);
439 		return;
440 	}
441 	intrstr = pci_intr_string(pa->pa_pc, ih);
442 	sc->sc_ih = pci_intr_establish(pa->pa_pc, ih, IPL_AUDIO, auich_intr,
443 				       sc, sc->sc_dev.dv_xname);
444 	if (!sc->sc_ih) {
445 		printf(": can't establish interrupt");
446 		if (intrstr)
447 			printf(" at %s", intrstr);
448 		printf("\n");
449 		bus_space_unmap(sc->iot, sc->aud_ioh, aud_size);
450 		bus_space_unmap(sc->iot_mix, sc->mix_ioh, mix_size);
451 		return;
452 	}
453 
454 	for (i = sizeof(auich_devices)/sizeof(auich_devices[0]); i--;)
455 		if (PCI_PRODUCT(pa->pa_id) == auich_devices[i].product)
456 			break;
457 
458 	snprintf(sc->sc_audev.name, sizeof sc->sc_audev.name, "%s AC97",
459 		 auich_devices[i].name);
460 	snprintf(sc->sc_audev.version, sizeof sc->sc_audev.version, "0x%02x",
461 		 PCI_REVISION(pa->pa_class));
462 	strlcpy(sc->sc_audev.config, sc->sc_dev.dv_xname,
463 		sizeof sc->sc_audev.config);
464 
465 	printf(": %s, %s\n", intrstr, sc->sc_audev.name);
466 
467 	/* SiS 7012 needs special handling */
468 	if (PCI_VENDOR(pa->pa_id) == PCI_VENDOR_SIS &&
469 	    PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_SIS_7012_ACA) {
470 		sc->sc_sts_reg = AUICH_PICB;
471 		sc->sc_sample_size = 1;
472 		sc->sc_pcm246_mask = AUICH_SIS_PCM246_MASK;
473 		sc->sc_pcm2 = AUICH_SIS_PCM2;
474 		sc->sc_pcm4 = AUICH_SIS_PCM4;
475 		sc->sc_pcm6 = AUICH_SIS_PCM6;
476 		/* un-mute output */
477 		bus_space_write_4(sc->iot, sc->aud_ioh, ICH_SIS_NV_CTL,
478 		    bus_space_read_4(sc->iot, sc->aud_ioh, ICH_SIS_NV_CTL) |
479 		    ICH_SIS_CTL_UNMUTE);
480 	} else {
481 		sc->sc_sts_reg = AUICH_STS;
482 		sc->sc_sample_size = 2;
483 		sc->sc_pcm246_mask = AUICH_PCM246_MASK;
484 		sc->sc_pcm2 = AUICH_PCM2;
485 		sc->sc_pcm4 = AUICH_PCM4;
486 		sc->sc_pcm6 = AUICH_PCM6;
487 	}
488 
489 	/* Workaround for a 440MX B-stepping erratum */
490 	sc->sc_dmamap_flags = BUS_DMA_COHERENT;
491 	if (PCI_VENDOR(pa->pa_id) == PCI_VENDOR_INTEL &&
492 	    PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82440MX_ACA) {
493 		sc->sc_dmamap_flags |= BUS_DMA_NOCACHE;
494 		printf("%s: DMA bug workaround enabled\n", sc->sc_dev.dv_xname);
495 	}
496 
497 	/* Set up DMA lists. */
498 	sc->pcmo.qptr = sc->pcmi.qptr = sc->mici.qptr = 0;
499 	auich_alloc_cdata(sc);
500 
501 	DPRINTF(AUICH_DEBUG_DMA, ("auich_attach: lists %p %p %p\n",
502 	    sc->pcmo.dmalist, sc->pcmi.dmalist, sc->mici.dmalist));
503 
504 	/* Reset codec and AC'97 */
505 	auich_reset_codec(sc);
506 	status = bus_space_read_4(sc->iot, sc->aud_ioh, AUICH_GSTS);
507 	if (!(status & AUICH_PCR)) {	/* reset failure */
508 		if (PCI_VENDOR(pa->pa_id) == PCI_VENDOR_INTEL &&
509 		    (PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801DB_ACA ||
510 		     PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801EB_ACA ||
511 		     PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801FB_ACA ||
512 		     PCI_PRODUCT(pa->pa_id) == PCI_PRODUCT_INTEL_82801GB_ACA)) {
513 			/* MSI 845G Max never return AUICH_PCR */
514 			sc->sc_ignore_codecready = 1;
515 		} else {
516 			printf("%s: reset failed!\n", sc->sc_dev.dv_xname);
517 			return;
518 		}
519 	}
520 
521 	sc->host_if.arg = sc;
522 	sc->host_if.attach = auich_attach_codec;
523 	sc->host_if.read = auich_read_codec;
524 	sc->host_if.write = auich_write_codec;
525 	sc->host_if.reset = auich_reset_codec;
526 	sc->host_if.flags = auich_flags_codec;
527 	sc->host_if.spdif_event = auich_spdif_event;
528 	if (sc->sc_dev.dv_cfdata->cf_flags & 0x0001)
529 		sc->flags = AC97_HOST_SWAPPED_CHANNELS;
530 
531 	if (ac97_attach(&sc->host_if) != 0) {
532 		pci_intr_disestablish(pa->pa_pc, sc->sc_ih);
533 		bus_space_unmap(sc->iot, sc->aud_ioh, aud_size);
534 		bus_space_unmap(sc->iot_mix, sc->mix_ioh, mix_size);
535 		return;
536 	}
537 	sc->codec_if->vtbl->unlock(sc->codec_if);
538 
539 	audio_attach_mi(&auich_hw_if, sc, &sc->sc_dev);
540 
541 	/* Watch for power changes */
542 	sc->suspend = PWR_RESUME;
543 	sc->powerhook = powerhook_establish(auich_powerhook, sc);
544 
545 	sc->sc_ac97rate = -1;
546 }
547 
548 int
549 auich_read_codec(v, reg, val)
550 	void *v;
551 	u_int8_t reg;
552 	u_int16_t *val;
553 {
554 	struct auich_softc *sc = v;
555 	int i;
556 
557 	/* wait for an access semaphore */
558 	for (i = AUICH_SEMATIMO; i-- &&
559 	    bus_space_read_1(sc->iot, sc->aud_ioh, AUICH_CAS) & 1; DELAY(1));
560 
561 	if (!sc->sc_ignore_codecready && i < 0) {
562 		DPRINTF(AUICH_DEBUG_CODECIO,
563 		    ("%s: read_codec timeout\n", sc->sc_dev.dv_xname));
564 		return (-1);
565 	}
566 
567 	*val = bus_space_read_2(sc->iot_mix, sc->mix_ioh, reg);
568 	DPRINTF(AUICH_DEBUG_CODECIO, ("%s: read_codec(%x, %x)\n",
569 	    sc->sc_dev.dv_xname, reg, *val));
570 	return (0);
571 }
572 
573 int
574 auich_write_codec(v, reg, val)
575 	void *v;
576 	u_int8_t reg;
577 	u_int16_t val;
578 {
579 	struct auich_softc *sc = v;
580 	int i;
581 
582 	/* wait for an access semaphore */
583 	for (i = AUICH_SEMATIMO; i-- &&
584 	    bus_space_read_1(sc->iot, sc->aud_ioh, AUICH_CAS) & 1; DELAY(1));
585 
586 	if (sc->sc_ignore_codecready || i >= 0) {
587 		DPRINTF(AUICH_DEBUG_CODECIO, ("%s: write_codec(%x, %x)\n",
588 		    sc->sc_dev.dv_xname, reg, val));
589 		bus_space_write_2(sc->iot_mix, sc->mix_ioh, reg, val);
590 		return (0);
591 	} else {
592 		DPRINTF(AUICH_DEBUG_CODECIO,
593 		    ("%s: write_codec timeout\n", sc->sc_dev.dv_xname));
594 		return (-1);
595 	}
596 }
597 
598 int
599 auich_attach_codec(v, cif)
600 	void *v;
601 	struct ac97_codec_if *cif;
602 {
603 	struct auich_softc *sc = v;
604 
605 	sc->codec_if = cif;
606 	return 0;
607 }
608 
609 void
610 auich_reset_codec(v)
611 	void *v;
612 {
613 	struct auich_softc *sc = v;
614 	u_int32_t control;
615 	int i;
616 
617 	control = bus_space_read_4(sc->iot, sc->aud_ioh, AUICH_GCTRL);
618 	control &= ~(AUICH_ACLSO | sc->sc_pcm246_mask);
619 	control |= (control & AUICH_CRESET) ? AUICH_WRESET : AUICH_CRESET;
620 	bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_GCTRL, control);
621 
622 	for (i = AUICH_RESETIMO; i-- &&
623 	    !(bus_space_read_4(sc->iot, sc->aud_ioh, AUICH_GSTS) & AUICH_PCR);
624 	    DELAY(1));
625 
626 	if (i < 0)
627 		DPRINTF(AUICH_DEBUG_CODECIO,
628 		    ("%s: reset_codec timeout\n", sc->sc_dev.dv_xname));
629 }
630 
631 enum ac97_host_flags
632 auich_flags_codec(void *v)
633 {
634 	struct auich_softc *sc = v;
635 
636 	return (sc->flags);
637 }
638 
639 void
640 auich_spdif_event(void *v, int flag)
641 {
642 	struct auich_softc *sc = v;
643 	sc->sc_spdif = flag;
644 }
645 
646 int
647 auich_open(v, flags)
648 	void *v;
649 	int flags;
650 {
651 	struct auich_softc *sc = v;
652 
653 	if (sc->sc_ac97rate == -1)
654 		sc->sc_ac97rate = auich_calibrate(sc);
655 
656 	sc->codec_if->vtbl->lock(sc->codec_if);
657 
658 	return 0;
659 }
660 
661 void
662 auich_close(v)
663 	void *v;
664 {
665 	struct auich_softc *sc = v;
666 
667 	sc->codec_if->vtbl->unlock(sc->codec_if);
668 }
669 
670 void
671 auich_get_default_params(void *addr, int mode, struct audio_params *params)
672 {
673 	ac97_get_default_params(params);
674 }
675 
676 int
677 auich_query_encoding(v, aep)
678 	void *v;
679 	struct audio_encoding *aep;
680 {
681 	struct auich_softc *sc = v;
682 	if (sc->sc_spdif) {
683 		switch (aep->index) {
684 		case 0:
685 			strlcpy(aep->name, AudioEslinear_le, sizeof aep->name);
686 			aep->encoding = AUDIO_ENCODING_SLINEAR_LE;
687 			aep->precision = 16;
688 			aep->flags = 0;
689 			return (0);
690 		default:
691 			return (EINVAL);
692 		}
693 	} else {
694 		switch (aep->index) {
695 		case 0:
696 			strlcpy(aep->name, AudioEulinear, sizeof aep->name);
697 			aep->encoding = AUDIO_ENCODING_ULINEAR;
698 			aep->precision = 8;
699 			aep->flags = 0;
700 			return (0);
701 		case 1:
702 			strlcpy(aep->name, AudioEmulaw, sizeof aep->name);
703 			aep->encoding = AUDIO_ENCODING_ULAW;
704 			aep->precision = 8;
705 			aep->flags = AUDIO_ENCODINGFLAG_EMULATED;
706 			return (0);
707 		case 2:
708 			strlcpy(aep->name, AudioEalaw, sizeof aep->name);
709 			aep->encoding = AUDIO_ENCODING_ALAW;
710 			aep->precision = 8;
711 			aep->flags = AUDIO_ENCODINGFLAG_EMULATED;
712 			return (0);
713 		case 3:
714 			strlcpy(aep->name, AudioEslinear, sizeof aep->name);
715 			aep->encoding = AUDIO_ENCODING_SLINEAR;
716 			aep->precision = 8;
717 			aep->flags = AUDIO_ENCODINGFLAG_EMULATED;
718 			return (0);
719 		case 4:
720 			strlcpy(aep->name, AudioEslinear_le, sizeof aep->name);
721 			aep->encoding = AUDIO_ENCODING_SLINEAR_LE;
722 			aep->precision = 16;
723 			aep->flags = 0;
724 			return (0);
725 		case 5:
726 			strlcpy(aep->name, AudioEulinear_le, sizeof aep->name);
727 			aep->encoding = AUDIO_ENCODING_ULINEAR_LE;
728 			aep->precision = 16;
729 			aep->flags = AUDIO_ENCODINGFLAG_EMULATED;
730 			return (0);
731 		case 6:
732 			strlcpy(aep->name, AudioEslinear_be, sizeof aep->name);
733 			aep->encoding = AUDIO_ENCODING_SLINEAR_BE;
734 			aep->precision = 16;
735 			aep->flags = AUDIO_ENCODINGFLAG_EMULATED;
736 			return (0);
737 		case 7:
738 			strlcpy(aep->name, AudioEulinear_be, sizeof aep->name);
739 			aep->encoding = AUDIO_ENCODING_ULINEAR_BE;
740 			aep->precision = 16;
741 			aep->flags = AUDIO_ENCODINGFLAG_EMULATED;
742 			return (0);
743 		default:
744 			return (EINVAL);
745 		}
746 	}
747 }
748 
749 int
750 auich_set_params(v, setmode, usemode, play, rec)
751 	void *v;
752 	int setmode, usemode;
753 	struct audio_params *play, *rec;
754 {
755 	struct auich_softc *sc = v;
756 	struct ac97_codec_if *codec = sc->codec_if;
757 	int error;
758 	u_int orate;
759 	u_int adj_rate;
760 	u_int32_t control;
761 	u_int16_t ext_id;
762 
763 	if (setmode & AUMODE_PLAY) {
764 		/* only 16-bit 48kHz slinear_le if s/pdif enabled */
765 		if (sc->sc_spdif) {
766 			play->sample_rate = 48000;
767 			play->precision = 16;
768 			play->encoding = AUDIO_ENCODING_SLINEAR_LE;
769 		}
770 	}
771 	if (setmode & AUMODE_PLAY) {
772 		play->factor = 1;
773 		play->sw_code = NULL;
774 		if (play->precision > 16)
775 			play->precision = 16;
776 		switch(play->encoding) {
777 		case AUDIO_ENCODING_ULAW:
778 			if (play->channels > 2)
779 				play->channels = 2;
780 			switch (play->channels) {
781 			case 1:
782 				play->factor = 4;
783 				play->sw_code = mulaw_to_slinear16_le_mts;
784 				break;
785 			case 2:
786 				play->factor = 2;
787 				play->sw_code = mulaw_to_slinear16_le;
788 				break;
789 			default:
790 				return (EINVAL);
791 			}
792 			break;
793 		case AUDIO_ENCODING_SLINEAR_LE:
794 			switch (play->precision) {
795 			case 8:
796 				if (play->channels > 2)
797 					play->channels = 2;
798 				switch (play->channels) {
799 				case 1:
800 					play->factor = 4;
801 					play->sw_code = linear8_to_linear16_le_mts;
802 					break;
803 				case 2:
804 					play->factor = 2;
805 					play->sw_code = linear8_to_linear16_le;
806 					break;
807 				default:
808 					return (EINVAL);
809 				}
810 				break;
811 			case 16:
812 				if (play->channels > 6)
813 					play->channels = 6;
814 				if (play->channels > 1)
815 					play->channels &= ~1;
816 				switch (play->channels) {
817 				case 1:
818 					play->factor = 2;
819 					play->sw_code = noswap_bytes_mts;
820 					break;
821 				case 2:
822 					break;
823 				case 4:
824 					ext_id = codec->vtbl->get_caps(codec);
825 					if (!(ext_id & AC97_EXT_AUDIO_SDAC))
826 						play->channels = 2;
827 					break;
828 				case 6:
829 					ext_id = codec->vtbl->get_caps(codec);
830 					if ((ext_id & AC97_BITS_6CH) !=
831 					    AC97_BITS_6CH)
832 						play->channels = 2;
833 					break;
834 				default:
835 					return (EINVAL);
836 				}
837 				break;
838 			}
839 			break;
840 		case AUDIO_ENCODING_ULINEAR_LE:
841 			if (play->channels > 2)
842 				play->channels = 2;
843 			switch (play->precision) {
844 			case 8:
845 				switch (play->channels) {
846 				case 1:
847 					play->factor = 4;
848 					play->sw_code = ulinear8_to_linear16_le_mts;
849 					break;
850 				case 2:
851 					play->factor = 2;
852 					play->sw_code = ulinear8_to_linear16_le;
853 					break;
854 				default:
855 					return (EINVAL);
856 				}
857 				break;
858 			case 16:
859 				switch (play->channels) {
860 				case 1:
861 					play->factor = 2;
862 					play->sw_code = change_sign16_le_mts;
863 					break;
864 				case 2:
865 					play->sw_code = change_sign16_le;
866 					break;
867 				default:
868 					return (EINVAL);
869 				}
870 				break;
871 			default:
872 				return (EINVAL);
873 			}
874 			break;
875 		case AUDIO_ENCODING_ALAW:
876 			if (play->channels > 2)
877 				play->channels = 2;
878 			switch (play->channels) {
879 			case 1:
880 				play->factor = 4;
881 				play->sw_code = alaw_to_slinear16_le_mts;
882 				break;
883 			case 2:
884 				play->factor = 2;
885 				play->sw_code = alaw_to_slinear16_le;
886 				break;
887 			default:
888 				return (EINVAL);
889 			}
890 			break;
891 		case AUDIO_ENCODING_SLINEAR_BE:
892 			if (play->channels > 2)
893 				play->channels = 2;
894 			switch (play->precision) {
895 			case 8:
896 				switch (play->channels) {
897 				case 1:
898 					play->factor = 4;
899 					play->sw_code = linear8_to_linear16_le_mts;
900 					break;
901 				case 2:
902 					play->factor = 2;
903 					play->sw_code = linear8_to_linear16_le;
904 					break;
905 				default:
906 					return (EINVAL);
907 				}
908 				break;
909 			case 16:
910 				switch (play->channels) {
911 				case 1:
912 					play->factor = 2;
913 					play->sw_code = swap_bytes_mts;
914 					break;
915 				case 2:
916 					play->sw_code = swap_bytes;
917 					break;
918 				default:
919 					return (EINVAL);
920 				}
921 				break;
922 			default:
923 				return (EINVAL);
924 			}
925 			break;
926 		case AUDIO_ENCODING_ULINEAR_BE:
927 			if (play->channels > 2)
928 				play->channels = 2;
929 			switch (play->precision) {
930 			case 8:
931 				switch (play->channels) {
932 				case 1:
933 					play->factor = 4;
934 					play->sw_code = ulinear8_to_linear16_le_mts;
935 					break;
936 				case 2:
937 					play->factor = 2;
938 					play->sw_code = ulinear8_to_linear16_le;
939 					break;
940 				default:
941 					return (EINVAL);
942 				}
943 				break;
944 			case 16:
945 				switch (play->channels) {
946 				case 1:
947 					play->factor = 2;
948 					play->sw_code = swap_bytes_change_sign16_le_mts;
949 					break;
950 				case 2:
951 					play->sw_code = swap_bytes_change_sign16_le;
952 					break;
953 				default:
954 					return (EINVAL);
955 				}
956 				break;
957 			default:
958 				return (EINVAL);
959 			}
960 			break;
961 		default:
962 			return (EINVAL);
963 		}
964 
965 		orate = adj_rate = play->sample_rate;
966 		if (sc->sc_ac97rate != 0)
967 			adj_rate = orate * AUICH_FIXED_RATE / sc->sc_ac97rate;
968 
969 		play->sample_rate = adj_rate;
970 		error = ac97_set_rate(sc->codec_if,
971 		    AC97_REG_PCM_LFE_DAC_RATE, &play->sample_rate);
972 		if (error)
973 			return (error);
974 
975 		play->sample_rate = adj_rate;
976 		error = ac97_set_rate(sc->codec_if,
977 		    AC97_REG_PCM_SURR_DAC_RATE, &play->sample_rate);
978 		if (error)
979 			return (error);
980 
981 		play->sample_rate = adj_rate;
982 		error = ac97_set_rate(sc->codec_if,
983 		    AC97_REG_PCM_FRONT_DAC_RATE, &play->sample_rate);
984 		if (error)
985 			return (error);
986 
987 		if (play->sample_rate == adj_rate)
988 			play->sample_rate = orate;
989 
990 		control = bus_space_read_4(sc->iot, sc->aud_ioh, AUICH_GCTRL);
991 		control &= ~(sc->sc_pcm246_mask);
992 		if (play->channels == 4)
993 			control |= sc->sc_pcm4;
994 		else if (play->channels == 6)
995 			control |= sc->sc_pcm6;
996 		bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_GCTRL, control);
997 	}
998 
999 	if (setmode & AUMODE_RECORD) {
1000 		rec->factor = 1;
1001 		rec->sw_code = 0;
1002 		if (rec->channels > 2)
1003 			rec->channels = 2;
1004 		if (rec->precision > 16)
1005 			rec->precision = 16;
1006 		switch(rec->encoding) {
1007 		case AUDIO_ENCODING_ULAW:
1008 			switch (rec->channels) {
1009 			case 1:
1010 				rec->sw_code = slinear16_to_mulaw_le_stm;
1011 				rec->factor = 4;
1012 				break;
1013 			case 2:
1014 				rec->sw_code = slinear16_to_mulaw_le;
1015 				rec->factor = 2;
1016 				break;
1017 			}
1018 			break;
1019 		case AUDIO_ENCODING_ALAW:
1020 			switch (rec->channels) {
1021 			case 1:
1022 				rec->sw_code = slinear16_to_alaw_le_stm;
1023 				rec->factor = 4;
1024 				break;
1025 			case 2:
1026 				rec->sw_code = slinear16_to_alaw_le;
1027 				rec->factor = 2;
1028 				break;
1029 			}
1030 			break;
1031 		case AUDIO_ENCODING_SLINEAR_LE:
1032 			switch (rec->precision) {
1033 			case 8:
1034 				switch (rec->channels) {
1035 				case 1:
1036 					rec->sw_code = linear16_to_linear8_le_stm;
1037 					rec->factor = 4;
1038 					break;
1039 				case 2:
1040 					rec->sw_code = linear16_to_linear8_le;
1041 					rec->factor = 2;
1042 					break;
1043 				}
1044 				break;
1045 			case 16:
1046 				switch (rec->channels) {
1047 				case 1:
1048 					rec->sw_code = linear16_decimator;
1049 					rec->factor = 2;
1050 					break;
1051 				case 2:
1052 					break;
1053 				}
1054 				break;
1055 			default:
1056 				return (EINVAL);
1057 			}
1058 			break;
1059 		case AUDIO_ENCODING_ULINEAR_LE:
1060 			switch (rec->precision) {
1061 			case 8:
1062 				switch (rec->channels) {
1063 				case 1:
1064 					rec->sw_code = linear16_to_ulinear8_le_stm;
1065 					rec->factor = 4;
1066 					break;
1067 				case 2:
1068 					rec->sw_code = linear16_to_ulinear8_le;
1069 					rec->factor = 2;
1070 					break;
1071 				}
1072 				break;
1073 			case 16:
1074 				switch (rec->channels) {
1075 				case 1:
1076 					rec->sw_code = change_sign16_le_stm;
1077 					rec->factor = 2;
1078 					break;
1079 				case 2:
1080 					rec->sw_code = change_sign16_le;
1081 					break;
1082 				}
1083 				break;
1084 			default:
1085 				return (EINVAL);
1086 			}
1087 			break;
1088 		case AUDIO_ENCODING_SLINEAR_BE:
1089 			switch (rec->precision) {
1090 			case 8:
1091 				switch (rec->channels) {
1092 				case 1:
1093 					rec->sw_code = linear16_to_linear8_le_stm;
1094 					rec->factor = 4;
1095 					break;
1096 				case 2:
1097 					rec->sw_code = linear16_to_linear8_le;
1098 					rec->factor = 2;
1099 					break;
1100 				}
1101 				break;
1102 			case 16:
1103 				switch (rec->channels) {
1104 				case 1:
1105 					rec->sw_code = swap_bytes_stm;
1106 					rec->factor = 2;
1107 					break;
1108 				case 2:
1109 					rec->sw_code = swap_bytes;
1110 					break;
1111 				}
1112 				break;
1113 			default:
1114 				return (EINVAL);
1115 			}
1116 			break;
1117 		case AUDIO_ENCODING_ULINEAR_BE:
1118 			switch (rec->precision) {
1119 			case 8:
1120 				switch (rec->channels) {
1121 				case 1:
1122 					rec->sw_code = linear16_to_ulinear8_le_stm;
1123 					rec->factor = 4;
1124 					break;
1125 				case 2:
1126 					rec->sw_code = linear16_to_ulinear8_le;
1127 					rec->factor = 2;
1128 					break;
1129 				}
1130 				break;
1131 			case 16:
1132 				switch (rec->channels) {
1133 				case 1:
1134 					rec->sw_code = change_sign16_swap_bytes_le_stm;
1135 					rec->factor = 2;
1136 					break;
1137 				case 2:
1138 					rec->sw_code = change_sign16_swap_bytes_le;
1139 					break;
1140 				}
1141 				break;
1142 			default:
1143 				return (EINVAL);
1144 			}
1145 			break;
1146 		default:
1147 			return (EINVAL);
1148 		}
1149 
1150 		orate = rec->sample_rate;
1151 		if (sc->sc_ac97rate != 0)
1152 			rec->sample_rate = orate * AUICH_FIXED_RATE /
1153 			    sc->sc_ac97rate;
1154 		error = ac97_set_rate(sc->codec_if, AC97_REG_PCM_LR_ADC_RATE,
1155 		    &rec->sample_rate);
1156 		if (error)
1157 			return (error);
1158 		rec->sample_rate = orate;
1159 	}
1160 
1161 	return (0);
1162 }
1163 
1164 int
1165 auich_round_blocksize(v, blk)
1166 	void *v;
1167 	int blk;
1168 {
1169 	return (blk + 0x3f) & ~0x3f;
1170 }
1171 
1172 
1173 void
1174 auich_halt_pipe(struct auich_softc *sc, int pipe)
1175 {
1176 	int i;
1177 	uint32_t status;
1178 
1179 	bus_space_write_1(sc->iot, sc->aud_ioh, pipe + AUICH_CTRL, 0);
1180 	for (i = 0; i < 100; i++) {
1181 		status = bus_space_read_4(sc->iot, sc->aud_ioh, pipe + AUICH_STS);
1182 		if (status & AUICH_DCH)
1183 			break;
1184 		DELAY(1);
1185 	}
1186 	bus_space_write_1(sc->iot, sc->aud_ioh, pipe + AUICH_CTRL, AUICH_RR);
1187 
1188 	if (i > 0)
1189 		DPRINTF(AUICH_DEBUG_DMA,
1190 		    ("auich_halt_pipe: halt took %d cycles\n", i));
1191 }
1192 
1193 
1194 int
1195 auich_halt_output(v)
1196 	void *v;
1197 {
1198 	struct auich_softc *sc = v;
1199 
1200 	DPRINTF(AUICH_DEBUG_DMA, ("%s: halt_output\n", sc->sc_dev.dv_xname));
1201 
1202 	bus_space_write_1(sc->iot, sc->aud_ioh, AUICH_PCMO + AUICH_CTRL, AUICH_RR);
1203 	sc->pcmo.intr = NULL;
1204 
1205 	return 0;
1206 }
1207 
1208 int
1209 auich_halt_input(v)
1210 	void *v;
1211 {
1212 	struct auich_softc *sc = v;
1213 
1214 	DPRINTF(AUICH_DEBUG_DMA,
1215 	    ("%s: halt_input\n", sc->sc_dev.dv_xname));
1216 
1217 	/* XXX halt both unless known otherwise */
1218 
1219 	bus_space_write_1(sc->iot, sc->aud_ioh, AUICH_PCMI + AUICH_CTRL, AUICH_RR);
1220 	bus_space_write_1(sc->iot, sc->aud_ioh, AUICH_MICI + AUICH_CTRL, AUICH_RR);
1221 	sc->pcmi.intr = NULL;
1222 
1223 	return 0;
1224 }
1225 
1226 int
1227 auich_getdev(v, adp)
1228 	void *v;
1229 	struct audio_device *adp;
1230 {
1231 	struct auich_softc *sc = v;
1232 	*adp = sc->sc_audev;
1233 	return 0;
1234 }
1235 
1236 int
1237 auich_set_port(v, cp)
1238 	void *v;
1239 	mixer_ctrl_t *cp;
1240 {
1241 	struct auich_softc *sc = v;
1242 	return sc->codec_if->vtbl->mixer_set_port(sc->codec_if, cp);
1243 }
1244 
1245 int
1246 auich_get_port(v, cp)
1247 	void *v;
1248 	mixer_ctrl_t *cp;
1249 {
1250 	struct auich_softc *sc = v;
1251 	return sc->codec_if->vtbl->mixer_get_port(sc->codec_if, cp);
1252 }
1253 
1254 int
1255 auich_query_devinfo(v, dp)
1256 	void *v;
1257 	mixer_devinfo_t *dp;
1258 {
1259 	struct auich_softc *sc = v;
1260 	return sc->codec_if->vtbl->query_devinfo(sc->codec_if, dp);
1261 }
1262 
1263 void *
1264 auich_allocm(v, direction, size, pool, flags)
1265 	void *v;
1266 	int direction;
1267 	size_t size;
1268 	int pool, flags;
1269 {
1270 	struct auich_softc *sc = v;
1271 	struct auich_dma *p;
1272 	int error;
1273 
1274 	/* can only use 1 segment */
1275 	if (size > AUICH_DMASEG_MAX) {
1276 		DPRINTF(AUICH_DEBUG_DMA,
1277 		    ("%s: requested buffer size too large: %d", \
1278 		    sc->sc_dev.dv_xname, size));
1279 		return NULL;
1280 	}
1281 
1282 	p = malloc(sizeof(*p), pool, flags | M_ZERO);
1283 	if (!p)
1284 		return NULL;
1285 
1286 	error = auich_allocmem(sc, size, PAGE_SIZE, p);
1287 	if (error) {
1288 		free(p, pool);
1289 		return NULL;
1290 	}
1291 
1292 	if (direction == AUMODE_PLAY)
1293 		sc->sc_pdma = p;
1294 	else if (direction == AUMODE_RECORD)
1295 		sc->sc_rdma = p;
1296 	else
1297 		sc->sc_cdma = p;
1298 
1299 	return p->addr;
1300 }
1301 
1302 void
1303 auich_freem(void *v, void *ptr, int pool)
1304 {
1305 	struct auich_softc *sc;
1306 	struct auich_dma *p;
1307 
1308 	sc = v;
1309 	if (sc->sc_pdma != NULL && sc->sc_pdma->addr == ptr)
1310 		p = sc->sc_pdma;
1311 	else if (sc->sc_rdma != NULL && sc->sc_rdma->addr == ptr)
1312 		p = sc->sc_rdma;
1313 	else if (sc->sc_cdma != NULL && sc->sc_cdma->addr == ptr)
1314 		p = sc->sc_cdma;
1315 	else
1316 		return;
1317 
1318 	auich_freemem(sc, p);
1319 	free(p, pool);
1320 }
1321 
1322 size_t
1323 auich_round_buffersize(v, direction, size)
1324 	void *v;
1325 	int direction;
1326 	size_t size;
1327 {
1328 	if (size > AUICH_DMALIST_MAX * AUICH_DMASEG_MAX)
1329 		size = AUICH_DMALIST_MAX * AUICH_DMASEG_MAX;
1330 
1331 	return size;
1332 }
1333 
1334 paddr_t
1335 auich_mappage(v, mem, off, prot)
1336 	void *v;
1337 	void *mem;
1338 	off_t off;
1339 	int prot;
1340 {
1341 	struct auich_softc *sc = v;
1342 	struct auich_dma *p;
1343 
1344 	if (off < 0)
1345 		return -1;
1346 
1347 	p = NULL;
1348 	if (sc->sc_pdma != NULL && sc->sc_pdma->addr == mem)
1349 		p = sc->sc_pdma;
1350 	else if (sc->sc_rdma != NULL && sc->sc_rdma->addr == mem)
1351 		p = sc->sc_rdma;
1352 	else
1353 		return -1;
1354 
1355 	return bus_dmamem_mmap(sc->dmat, p->segs, p->nsegs,
1356 	    off, prot, BUS_DMA_WAITOK);
1357 }
1358 
1359 int
1360 auich_get_props(v)
1361 	void *v;
1362 {
1363 	return AUDIO_PROP_MMAP | AUDIO_PROP_INDEPENDENT | AUDIO_PROP_FULLDUPLEX;
1364 }
1365 
1366 int
1367 auich_intr(v)
1368 	void *v;
1369 {
1370 	struct auich_softc *sc = v;
1371 	int ret = 0, sts, gsts;
1372 
1373 	gsts = bus_space_read_4(sc->iot, sc->aud_ioh, AUICH_GSTS);
1374 	DPRINTF(AUICH_DEBUG_INTR, ("auich_intr: gsts=%b\n", gsts, AUICH_GSTS_BITS));
1375 
1376 	if (gsts & AUICH_POINT) {
1377 		sts = bus_space_read_2(sc->iot, sc->aud_ioh,
1378 		    AUICH_PCMO + sc->sc_sts_reg);
1379 		DPRINTF(AUICH_DEBUG_INTR,
1380 		    ("auich_intr: osts=%b\n", sts, AUICH_ISTS_BITS));
1381 
1382 #ifdef AUICH_DEBUG
1383 		if (sts & AUICH_FIFOE) {
1384 			printf("%s: fifo underrun # %u\n",
1385 			    sc->sc_dev.dv_xname, ++sc->pcmo_fifoe);
1386 		}
1387 #endif
1388 
1389 		if (sts & AUICH_BCIS)
1390 			auich_intr_pipe(sc, AUICH_PCMO, &sc->pcmo);
1391 
1392 		/* int ack */
1393 		bus_space_write_2(sc->iot, sc->aud_ioh,
1394 		    AUICH_PCMO + sc->sc_sts_reg, sts &
1395 		    (AUICH_BCIS | AUICH_FIFOE));
1396 		bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_GSTS, AUICH_POINT);
1397 		ret++;
1398 	}
1399 
1400 	if (gsts & AUICH_PIINT) {
1401 		sts = bus_space_read_2(sc->iot, sc->aud_ioh,
1402 		    AUICH_PCMI + sc->sc_sts_reg);
1403 		DPRINTF(AUICH_DEBUG_INTR,
1404 		    ("auich_intr: ists=%b\n", sts, AUICH_ISTS_BITS));
1405 
1406 #ifdef AUICH_DEBUG
1407 		if (sts & AUICH_FIFOE) {
1408 			printf("%s: in fifo overrun # %u\n",
1409 			    sc->sc_dev.dv_xname, ++sc->pcmi_fifoe);
1410 		}
1411 #endif
1412 
1413 		if (sts & AUICH_BCIS)
1414 			auich_intr_pipe(sc, AUICH_PCMI, &sc->pcmi);
1415 
1416 		/* int ack */
1417 		bus_space_write_2(sc->iot, sc->aud_ioh,
1418 		    AUICH_PCMI + sc->sc_sts_reg, sts &
1419 		    (AUICH_BCIS | AUICH_FIFOE));
1420 		bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_GSTS, AUICH_PIINT);
1421 		ret++;
1422 	}
1423 
1424 	if (gsts & AUICH_MINT) {
1425 		sts = bus_space_read_2(sc->iot, sc->aud_ioh,
1426 		    AUICH_MICI + sc->sc_sts_reg);
1427 		DPRINTF(AUICH_DEBUG_INTR,
1428 		    ("auich_intr: ists=%b\n", sts, AUICH_ISTS_BITS));
1429 #ifdef AUICH_DEBUG
1430 		if (sts & AUICH_FIFOE)
1431 			printf("%s: mic fifo overrun\n", sc->sc_dev.dv_xname);
1432 #endif
1433 
1434 		if (sts & AUICH_BCIS)
1435 			auich_intr_pipe(sc, AUICH_MICI, &sc->mici);
1436 
1437 		/* int ack */
1438 		bus_space_write_2(sc->iot, sc->aud_ioh,
1439 		    AUICH_MICI + sc->sc_sts_reg,
1440 		    sts + (AUICH_BCIS | AUICH_FIFOE));
1441 
1442 		bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_GSTS, AUICH_MINT);
1443 		ret++;
1444 	}
1445 
1446 	return ret;
1447 }
1448 
1449 
1450 void
1451 auich_trigger_pipe(struct auich_softc *sc, int pipe, struct auich_ring *ring)
1452 {
1453 	int blksize, qptr;
1454 	struct auich_dmalist *q;
1455 
1456 	blksize = ring->blksize;
1457 
1458 	for (qptr = 0; qptr < AUICH_DMALIST_MAX; qptr++) {
1459 		q = &ring->dmalist[qptr];
1460 		q->base = ring->p;
1461 		q->len = (blksize / sc->sc_sample_size) | AUICH_DMAF_IOC;
1462 
1463 		ring->p += blksize;
1464 		if (ring->p >= ring->end)
1465 			ring->p = ring->start;
1466 	}
1467 	ring->qptr = 0;
1468 
1469 	bus_space_write_1(sc->iot, sc->aud_ioh, pipe + AUICH_LVI,
1470 	    (qptr - 1) & AUICH_LVI_MASK);
1471 	bus_space_write_1(sc->iot, sc->aud_ioh, pipe + AUICH_CTRL,
1472 	    AUICH_IOCE | AUICH_FEIE | AUICH_RPBM);
1473 }
1474 
1475 void
1476 auich_intr_pipe(struct auich_softc *sc, int pipe, struct auich_ring *ring)
1477 {
1478 	int blksize, qptr, nqptr;
1479 	struct auich_dmalist *q;
1480 
1481 	blksize = ring->blksize;
1482 	qptr = ring->qptr;
1483 	nqptr = bus_space_read_1(sc->iot, sc->aud_ioh, pipe + AUICH_CIV);
1484 
1485 	while (qptr != nqptr) {
1486 		q = &ring->dmalist[qptr];
1487 		q->base = ring->p;
1488 		q->len = (blksize / sc->sc_sample_size) | AUICH_DMAF_IOC;
1489 
1490 		DPRINTF(AUICH_DEBUG_INTR,
1491 		    ("auich_intr: %p, %p = %x @ 0x%x\n",
1492 		    &ring->dmalist[qptr], q, q->len, q->base));
1493 
1494 		ring->p += blksize;
1495 		if (ring->p >= ring->end)
1496 			ring->p = ring->start;
1497 
1498 		qptr = (qptr + 1) & AUICH_LVI_MASK;
1499 		if (ring->intr)
1500 			ring->intr(ring->arg);
1501 	}
1502 	ring->qptr = qptr;
1503 
1504 	bus_space_write_1(sc->iot, sc->aud_ioh, pipe + AUICH_LVI,
1505 	    (qptr - 1) & AUICH_LVI_MASK);
1506 }
1507 
1508 
1509 int
1510 auich_trigger_output(v, start, end, blksize, intr, arg, param)
1511 	void *v;
1512 	void *start, *end;
1513 	int blksize;
1514 	void (*intr)(void *);
1515 	void *arg;
1516 	struct audio_params *param;
1517 {
1518 	struct auich_softc *sc = v;
1519 	struct auich_dma *p;
1520 	size_t size;
1521 
1522 	DPRINTF(AUICH_DEBUG_DMA,
1523 	    ("auich_trigger_output(%x, %x, %d, %p, %p, %p)\n",
1524 	    start, end, blksize, intr, arg, param));
1525 
1526 	if (sc->sc_pdma->addr == start)
1527 		p = sc->sc_pdma;
1528 	else
1529 		return -1;
1530 
1531 	size = (size_t)((caddr_t)end - (caddr_t)start);
1532 
1533 	sc->pcmo.intr = intr;
1534 	sc->pcmo.arg = arg;
1535 
1536 	/*
1537 	 * The logic behind this is:
1538 	 * setup one buffer to play, then LVI dump out the rest
1539 	 * to the scatter-gather chain.
1540 	 */
1541 	sc->pcmo.start = p->segs->ds_addr;
1542 	sc->pcmo.p = sc->pcmo.start;
1543 	sc->pcmo.end = sc->pcmo.start + size;
1544 	sc->pcmo.blksize = blksize;
1545 
1546 	bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_PCMO + AUICH_BDBAR,
1547 	    sc->sc_cddma + AUICH_PCMO_OFF(0));
1548 	auich_trigger_pipe(sc, AUICH_PCMO, &sc->pcmo);
1549 
1550 	return 0;
1551 }
1552 
1553 int
1554 auich_trigger_input(v, start, end, blksize, intr, arg, param)
1555 	void *v;
1556 	void *start, *end;
1557 	int blksize;
1558 	void (*intr)(void *);
1559 	void *arg;
1560 	struct audio_params *param;
1561 {
1562 	struct auich_softc *sc = v;
1563 	struct auich_dma *p;
1564 	size_t size;
1565 
1566 	DPRINTF(AUICH_DEBUG_DMA,
1567 	    ("auich_trigger_input(%x, %x, %d, %p, %p, %p)\n",
1568 	    start, end, blksize, intr, arg, param));
1569 
1570 	if (sc->sc_rdma->addr == start)
1571 		p = sc->sc_rdma;
1572 	else
1573 		return -1;
1574 
1575 	size = (size_t)((caddr_t)end - (caddr_t)start);
1576 
1577 	sc->pcmi.intr = intr;
1578 	sc->pcmi.arg = arg;
1579 
1580 	/*
1581 	 * The logic behind this is:
1582 	 * setup one buffer to play, then LVI dump out the rest
1583 	 * to the scatter-gather chain.
1584 	 */
1585 	sc->pcmi.start = p->segs->ds_addr;
1586 	sc->pcmi.p = sc->pcmi.start;
1587 	sc->pcmi.end = sc->pcmi.start + size;
1588 	sc->pcmi.blksize = blksize;
1589 
1590 	bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_PCMI + AUICH_BDBAR,
1591 	    sc->sc_cddma + AUICH_PCMI_OFF(0));
1592 	auich_trigger_pipe(sc, AUICH_PCMI, &sc->pcmi);
1593 
1594 	return 0;
1595 }
1596 
1597 
1598 int
1599 auich_allocmem(struct auich_softc *sc, size_t size, size_t align,
1600     struct auich_dma *p)
1601 {
1602 	int error;
1603 
1604 	p->size = size;
1605 	error = bus_dmamem_alloc(sc->dmat, p->size, align, 0, p->segs, 1,
1606 	    &p->nsegs, BUS_DMA_NOWAIT);
1607 	if (error) {
1608 		DPRINTF(AUICH_DEBUG_DMA,
1609 		    ("%s: bus_dmamem_alloc failed: error %d\n",
1610 		    sc->sc_dev.dv_xname, error));
1611 		return error;
1612 	}
1613 
1614 	error = bus_dmamem_map(sc->dmat, p->segs, 1, p->size, &p->addr,
1615 	    BUS_DMA_NOWAIT | sc->sc_dmamap_flags);
1616 	if (error) {
1617 		DPRINTF(AUICH_DEBUG_DMA,
1618 		    ("%s: bus_dmamem_map failed: error %d\n",
1619 		    sc->sc_dev.dv_xname, error));
1620 		goto free;
1621 	}
1622 
1623 	error = bus_dmamap_create(sc->dmat, p->size, 1, p->size, 0,
1624 	    BUS_DMA_NOWAIT, &p->map);
1625 	if (error) {
1626 		DPRINTF(AUICH_DEBUG_DMA,
1627 		    ("%s: bus_dmamap_create failed: error %d\n",
1628 		    sc->sc_dev.dv_xname, error));
1629 		goto unmap;
1630 	}
1631 
1632 	error = bus_dmamap_load(sc->dmat, p->map, p->addr, p->size, NULL,
1633 	    BUS_DMA_NOWAIT);
1634 	if (error) {
1635 		DPRINTF(AUICH_DEBUG_DMA,
1636 		    ("%s: bus_dmamap_load failed: error %d\n",
1637 		    sc->sc_dev.dv_xname, error));
1638 		goto destroy;
1639 	}
1640 	return 0;
1641 
1642  destroy:
1643 	bus_dmamap_destroy(sc->dmat, p->map);
1644  unmap:
1645 	bus_dmamem_unmap(sc->dmat, p->addr, p->size);
1646  free:
1647 	bus_dmamem_free(sc->dmat, p->segs, p->nsegs);
1648 	return error;
1649 }
1650 
1651 
1652 int
1653 auich_freemem(struct auich_softc *sc, struct auich_dma *p)
1654 {
1655 	bus_dmamap_unload(sc->dmat, p->map);
1656 	bus_dmamap_destroy(sc->dmat, p->map);
1657 	bus_dmamem_unmap(sc->dmat, p->addr, p->size);
1658 	bus_dmamem_free(sc->dmat, p->segs, p->nsegs);
1659 	return 0;
1660 }
1661 
1662 
1663 
1664 int
1665 auich_alloc_cdata(struct auich_softc *sc)
1666 {
1667 	bus_dma_segment_t seg;
1668 	int error, rseg;
1669 
1670 	/*
1671 	 * Allocate the control data structure, and create and load the
1672 	 * DMA map for it.
1673 	 */
1674 	if ((error = bus_dmamem_alloc(sc->dmat, sizeof(struct auich_cdata),
1675 	    PAGE_SIZE, 0, &seg, 1, &rseg, 0)) != 0) {
1676 		printf("%s: unable to allocate control data, error = %d\n",
1677 		    sc->sc_dev.dv_xname, error);
1678 		goto fail_0;
1679 	}
1680 
1681 	if ((error = bus_dmamem_map(sc->dmat, &seg, 1,
1682 	    sizeof(struct auich_cdata), (caddr_t *) &sc->sc_cdata,
1683 	    sc->sc_dmamap_flags)) != 0) {
1684 		printf("%s: unable to map control data, error = %d\n",
1685 		    sc->sc_dev.dv_xname, error);
1686 		goto fail_1;
1687 	}
1688 
1689 	if ((error = bus_dmamap_create(sc->dmat, sizeof(struct auich_cdata), 1,
1690 	    sizeof(struct auich_cdata), 0, 0, &sc->sc_cddmamap)) != 0) {
1691 		printf("%s: unable to create control data DMA map, "
1692 		    "error = %d\n", sc->sc_dev.dv_xname, error);
1693 		goto fail_2;
1694 	}
1695 
1696 	if ((error = bus_dmamap_load(sc->dmat, sc->sc_cddmamap, sc->sc_cdata,
1697 	    sizeof(struct auich_cdata), NULL, 0)) != 0) {
1698 		printf("%s: unable tp load control data DMA map, "
1699 		    "error = %d\n", sc->sc_dev.dv_xname, error);
1700 		goto fail_3;
1701 	}
1702 
1703 	sc->pcmo.dmalist = sc->sc_cdata->ic_dmalist_pcmo;
1704 	sc->pcmi.dmalist = sc->sc_cdata->ic_dmalist_pcmi;
1705 	sc->mici.dmalist = sc->sc_cdata->ic_dmalist_mici;
1706 
1707 	return 0;
1708 
1709  fail_3:
1710 	bus_dmamap_destroy(sc->dmat, sc->sc_cddmamap);
1711  fail_2:
1712 	bus_dmamem_unmap(sc->dmat, (caddr_t) sc->sc_cdata,
1713 	    sizeof(struct auich_cdata));
1714  fail_1:
1715 	bus_dmamem_free(sc->dmat, &seg, rseg);
1716  fail_0:
1717 	return error;
1718 }
1719 
1720 
1721 void
1722 auich_powerhook(why, self)
1723 	int why;
1724 	void *self;
1725 {
1726 	struct auich_softc *sc = (struct auich_softc *)self;
1727 
1728 	if (why != PWR_RESUME) {
1729 		/* Power down */
1730 		DPRINTF(1, ("auich: power down\n"));
1731 		sc->suspend = why;
1732 		auich_read_codec(sc, AC97_REG_EXT_AUDIO_CTRL, &sc->ext_ctrl);
1733 
1734 	} else {
1735 		/* Wake up */
1736 		DPRINTF(1, ("auich: power resume\n"));
1737 		if (sc->suspend == PWR_RESUME) {
1738 			printf("%s: resume without suspend?\n",
1739 			    sc->sc_dev.dv_xname);
1740 			sc->suspend = why;
1741 			return;
1742 		}
1743 		sc->suspend = why;
1744 		auich_reset_codec(sc);
1745 		DELAY(1000);
1746 		(sc->codec_if->vtbl->restore_ports)(sc->codec_if);
1747 		auich_write_codec(sc, AC97_REG_EXT_AUDIO_CTRL, sc->ext_ctrl);
1748 	}
1749 }
1750 
1751 
1752 /* -------------------------------------------------------------------- */
1753 /* Calibrate card (some boards are overclocked and need scaling) */
1754 
1755 unsigned int
1756 auich_calibrate(struct auich_softc *sc)
1757 {
1758 	struct timeval t1, t2;
1759 	u_int8_t ociv, nciv;
1760 	u_int32_t wait_us, actual_48k_rate, bytes, ac97rate;
1761 	void *temp_buffer;
1762 	struct auich_dma *p;
1763 
1764 	ac97rate = AUICH_FIXED_RATE;
1765 	/*
1766 	 * Grab audio from input for fixed interval and compare how
1767 	 * much we actually get with what we expect.  Interval needs
1768 	 * to be sufficiently short that no interrupts are
1769 	 * generated.
1770 	 */
1771 
1772 	/* Setup a buffer */
1773 	bytes = 16000;
1774 	temp_buffer = auich_allocm(sc, 0, bytes, M_DEVBUF, M_NOWAIT);
1775 	if (temp_buffer == NULL)
1776 		return (ac97rate);
1777 	if (sc->sc_cdma->addr == temp_buffer) {
1778 		p = sc->sc_cdma;
1779 	} else {
1780 		printf("auich_calibrate: bad address %p\n", temp_buffer);
1781 		return (ac97rate);
1782 	}
1783 
1784 	sc->pcmi.dmalist[0].base = p->map->dm_segs[0].ds_addr;
1785 	sc->pcmi.dmalist[0].len = bytes / sc->sc_sample_size;
1786 
1787 
1788 	/*
1789 	 * our data format is stereo, 16 bit so each sample is 4 bytes.
1790 	 * assuming we get 48000 samples per second, we get 192000 bytes/sec.
1791 	 * we're going to start recording with interrupts disabled and measure
1792 	 * the time taken for one block to complete.  we know the block size,
1793 	 * we know the time in microseconds, we calculate the sample rate:
1794 	 *
1795 	 * actual_rate [bps] = bytes / (time [s] * 4)
1796 	 * actual_rate [bps] = (bytes * 1000000) / (time [us] * 4)
1797 	 * actual_rate [Hz] = (bytes * 250000) / time [us]
1798 	 */
1799 
1800 	/* prepare */
1801 	ociv = bus_space_read_1(sc->iot, sc->aud_ioh, AUICH_PCMI + AUICH_CIV);
1802 	nciv = ociv;
1803 	bus_space_write_4(sc->iot, sc->aud_ioh, AUICH_PCMI + AUICH_BDBAR,
1804 	    sc->sc_cddma + AUICH_PCMI_OFF(0));
1805 	bus_space_write_1(sc->iot, sc->aud_ioh, AUICH_PCMI + AUICH_LVI,
1806 			  (0 - 1) & AUICH_LVI_MASK);
1807 
1808 	/* start */
1809 	microuptime(&t1);
1810 	bus_space_write_1(sc->iot, sc->aud_ioh, AUICH_PCMI + AUICH_CTRL,
1811 	    AUICH_RPBM);
1812 
1813 	/* wait */
1814 	while (nciv == ociv) {
1815 		microuptime(&t2);
1816 		if (t2.tv_sec - t1.tv_sec > 1)
1817 			break;
1818 		nciv = bus_space_read_1(sc->iot, sc->aud_ioh,
1819 					AUICH_PCMI + AUICH_CIV);
1820 	}
1821 	microuptime(&t2);
1822 
1823 	/* reset */
1824 	bus_space_write_1(sc->iot, sc->aud_ioh, AUICH_PCMI + AUICH_CTRL, AUICH_RR);
1825 	bus_space_write_1(sc->iot, sc->aud_ioh, AUICH_MICI + AUICH_CTRL, AUICH_RR);
1826 	DELAY(100);
1827 
1828 	/* turn time delta into us */
1829 	wait_us = ((t2.tv_sec - t1.tv_sec) * 1000000) + t2.tv_usec - t1.tv_usec;
1830 
1831 	auich_freem(sc, temp_buffer, M_DEVBUF);
1832 
1833 	if (nciv == ociv) {
1834 		printf("%s: ac97 link rate calibration timed out after %d us\n",
1835 		       sc->sc_dev.dv_xname, wait_us);
1836 		return (ac97rate);
1837 	}
1838 
1839 	actual_48k_rate = (bytes * 250000) / wait_us;
1840 
1841 	if (actual_48k_rate <= 48500)
1842 		ac97rate = AUICH_FIXED_RATE;
1843 	else
1844 		ac97rate = actual_48k_rate;
1845 
1846 	printf("%s: measured ac97 link rate at %d Hz",
1847 	       sc->sc_dev.dv_xname, actual_48k_rate);
1848 	if (ac97rate != actual_48k_rate)
1849 		printf(", will use %d Hz", ac97rate);
1850 	printf("\n");
1851 
1852 	return (ac97rate);
1853 }
1854