audio810.c revision 11936:54dc8a89ba0d
1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21/*
22 * Copyright 2010 Sun Microsystems, Inc.  All rights reserved.
23 * Use is subject to license terms.
24 */
25
26
27/*
28 * audio810 Audio Driver
29 *
30 * The driver is primarily targeted at providing audio support for the
31 * Intel ICHx family of AC'97 controllers and compatible parts (such
32 * as those from nVidia and AMD.)
33 *
34 * These audio parts have independent channels for PCM in, PCM out,
35 * mic in, and sometimes modem in, and modem out.  The AC'97
36 * controller is a PCI bus master with scatter/gather support. Each
37 * channel has a DMA engine. Currently, we use only the PCM in and PCM
38 * out channels. Each DMA engine uses one buffer descriptor list. And
39 * the buffer descriptor list is an array of up to 32 entries, each of
40 * which describes a data buffer.  Each entry contains a pointer to a
41 * data buffer, control bits, and the length of the buffer being
42 * pointed to, where the length is expressed as the number of
43 * samples. This, combined with the 16-bit sample size, gives the
44 * actual physical length of the buffer.
45 *
46 * A workaround for the AD1980 and AD1985 codec:
47 *	Most vendors connect the surr-out of the codecs to the line-out jack.
48 *	So far we haven't found which vendors don't do that. So we assume that
49 *	all vendors swap the surr-out and the line-out outputs. So we need swap
50 *	the two outputs. But we still internally process the
51 *	"ad198x-swap-output" property. If someday some vendors do not swap the
52 *	outputs, we would set "ad198x-swap-output = 0" in the
53 *	/kernel/drv/audio810.conf file, and unload and reload the audio810
54 *	driver (or reboot).
55 *
56 * 	NOTE:
57 * 	This driver depends on the drv/audio and misc/ac97
58 * 	modules being loaded first.
59 *
60 * The audio framework guarantees that our entry points are exclusive
61 * with suspend and resume.  This includes data flow and control entry
62 * points alike.
63 *
64 * The audio framework guarantees that only one control is being
65 * accessed on any given audio device at a time.
66 *
67 * The audio framework guarantees that entry points are themselves
68 * serialized for a given engine.
69 *
70 * We have no interrupt routine or other internal asynchronous routines.
71 *
72 * Our device uses completely separate registers for each engine,
73 * except for the start/stop registers, which are implemented in a
74 * manner that allows for them to be accessed concurrently safely from
75 * different threads.
76 *
77 * Hence, it turns out that we simply don't need any locking in this
78 * driver.
79 */
80#include <sys/types.h>
81#include <sys/modctl.h>
82#include <sys/kmem.h>
83#include <sys/conf.h>
84#include <sys/ddi.h>
85#include <sys/sunddi.h>
86#include <sys/pci.h>
87#include <sys/note.h>
88#include <sys/audio/audio_driver.h>
89#include <sys/audio/ac97.h>
90#include "audio810.h"
91
92/*
93 * Module linkage routines for the kernel
94 */
95static int audio810_ddi_attach(dev_info_t *, ddi_attach_cmd_t);
96static int audio810_ddi_detach(dev_info_t *, ddi_detach_cmd_t);
97static int audio810_ddi_quiesce(dev_info_t *);
98
99/*
100 * Entry point routine prototypes
101 */
102static int audio810_open(void *, int, unsigned *, caddr_t *);
103static void audio810_close(void *);
104static int audio810_start(void *);
105static void audio810_stop(void *);
106static int audio810_format(void *);
107static int audio810_channels(void *);
108static int audio810_rate(void *);
109static uint64_t audio810_count(void *);
110static void audio810_sync(void *, unsigned);
111static unsigned audio810_playahead(void *);
112
113static audio_engine_ops_t audio810_engine_ops = {
114	AUDIO_ENGINE_VERSION,
115	audio810_open,
116	audio810_close,
117	audio810_start,
118	audio810_stop,
119	audio810_count,
120	audio810_format,
121	audio810_channels,
122	audio810_rate,
123	audio810_sync,
124	NULL,
125	NULL,
126	audio810_playahead
127};
128
129/*
130 * Local Routine Prototypes
131 */
132static int audio810_attach(dev_info_t *);
133static int audio810_resume(dev_info_t *);
134static int audio810_detach(dev_info_t *);
135static int audio810_suspend(dev_info_t *);
136
137static int audio810_alloc_port(audio810_state_t *, int, uint8_t);
138static int audio810_codec_sync(audio810_state_t *);
139static void audio810_write_ac97(void *, uint8_t, uint16_t);
140static uint16_t audio810_read_ac97(void *, uint8_t);
141static int audio810_map_regs(dev_info_t *, audio810_state_t *);
142static void audio810_unmap_regs(audio810_state_t *);
143static void audio810_stop_dma(audio810_state_t *);
144static int audio810_chip_init(audio810_state_t *);
145static void audio810_set_channels(audio810_state_t *);
146static void audio810_destroy(audio810_state_t *);
147
148/*
149 * Global variables, but used only by this file.
150 */
151
152/*
153 * DDI Structures
154 */
155
156/* Device operations structure */
157static struct dev_ops audio810_dev_ops = {
158	DEVO_REV,		/* devo_rev */
159	0,			/* devo_refcnt */
160	NULL,			/* devo_getinfo */
161	nulldev,		/* devo_identify - obsolete */
162	nulldev,		/* devo_probe */
163	audio810_ddi_attach,	/* devo_attach */
164	audio810_ddi_detach,	/* devo_detach */
165	nodev,			/* devo_reset */
166	NULL,			/* devi_cb_ops */
167	NULL,			/* devo_bus_ops */
168	NULL,			/* devo_power */
169	audio810_ddi_quiesce,	/* devo_quiesce */
170};
171
172/* Linkage structure for loadable drivers */
173static struct modldrv audio810_modldrv = {
174	&mod_driverops,		/* drv_modops */
175	I810_MOD_NAME,		/* drv_linkinfo */
176	&audio810_dev_ops,	/* drv_dev_ops */
177};
178
179/* Module linkage structure */
180static struct modlinkage audio810_modlinkage = {
181	MODREV_1,			/* ml_rev */
182	(void *)&audio810_modldrv,	/* ml_linkage */
183	NULL				/* NULL terminates the list */
184};
185
186/*
187 * device access attributes for register mapping
188 */
189static struct ddi_device_acc_attr dev_attr = {
190	DDI_DEVICE_ATTR_V0,
191	DDI_STRUCTURE_LE_ACC,
192	DDI_STRICTORDER_ACC
193};
194
195static struct ddi_device_acc_attr buf_attr = {
196	DDI_DEVICE_ATTR_V0,
197	DDI_STRUCTURE_LE_ACC,
198	DDI_STRICTORDER_ACC
199};
200
201/*
202 * DMA attributes of buffer descriptor list
203 */
204static ddi_dma_attr_t	bdlist_dma_attr = {
205	DMA_ATTR_V0,	/* version */
206	0,		/* addr_lo */
207	0xffffffff,	/* addr_hi */
208	0x0000ffff,	/* count_max */
209	8,		/* align, BDL must be aligned on a 8-byte boundary */
210	0x3c,		/* burstsize */
211	8,		/* minxfer, set to the size of a BDlist entry */
212	0x0000ffff,	/* maxxfer */
213	0x00000fff,	/* seg, set to the RAM pagesize of intel platform */
214	1,		/* sgllen, there's no scatter-gather list */
215	8,		/* granular, set to the value of minxfer */
216	0		/* flags, use virtual address */
217};
218
219/*
220 * DMA attributes of buffers to be used to receive/send audio data
221 */
222static ddi_dma_attr_t	sample_buf_dma_attr = {
223	DMA_ATTR_V0,
224	0,		/* addr_lo */
225	0xffffffff,	/* addr_hi */
226	0x0001ffff,	/* count_max */
227	4,		/* align, data buffer is aligned on a 4-byte boundary */
228	0x3c,		/* burstsize */
229	4,		/* minxfer, set to the size of a sample data */
230	0x0001ffff,	/* maxxfer */
231	0x0001ffff,	/* seg */
232	1,		/* sgllen, no scatter-gather */
233	4,		/* granular, set to the value of minxfer */
234	0,		/* flags, use virtual address */
235};
236
237/*
238 * _init()
239 *
240 * Description:
241 *	Driver initialization, called when driver is first loaded.
242 *	This is how access is initially given to all the static structures.
243 *
244 * Arguments:
245 *	None
246 *
247 * Returns:
248 *	mod_install() status, see mod_install(9f)
249 */
250int
251_init(void)
252{
253	int	error;
254
255	audio_init_ops(&audio810_dev_ops, I810_NAME);
256
257	if ((error = mod_install(&audio810_modlinkage)) != 0) {
258		audio_fini_ops(&audio810_dev_ops);
259	}
260
261	return (error);
262}
263
264/*
265 * _fini()
266 *
267 * Description:
268 *	Module de-initialization, called when the driver is to be unloaded.
269 *
270 * Arguments:
271 *	None
272 *
273 * Returns:
274 *	mod_remove() status, see mod_remove(9f)
275 */
276int
277_fini(void)
278{
279	int		error;
280
281	if ((error = mod_remove(&audio810_modlinkage)) != 0) {
282		return (error);
283	}
284
285	/* clean up ops */
286	audio_fini_ops(&audio810_dev_ops);
287
288	return (0);
289}
290
291/*
292 * _info()
293 *
294 * Description:
295 *	Module information, returns information about the driver.
296 *
297 * Arguments:
298 *	modinfo		*modinfop	Pointer to the opaque modinfo structure
299 *
300 * Returns:
301 *	mod_info() status, see mod_info(9f)
302 */
303int
304_info(struct modinfo *modinfop)
305{
306	return (mod_info(&audio810_modlinkage, modinfop));
307}
308
309
310/* ******************* Driver Entry Points ********************************* */
311
312/*
313 * audio810_ddi_attach()
314 *
315 * Description:
316 *	Implements the DDI attach(9e) entry point.
317 *
318 * Arguments:
319 *	dev_info_t	*dip	Pointer to the device's dev_info struct
320 *	ddi_attach_cmd_t cmd	Attach command
321 *
322 * Returns:
323 *	DDI_SUCCESS		The driver was initialized properly
324 *	DDI_FAILURE		The driver couldn't be initialized properly
325 */
326static int
327audio810_ddi_attach(dev_info_t *dip, ddi_attach_cmd_t cmd)
328{
329	switch (cmd) {
330	case DDI_ATTACH:
331		return (audio810_attach(dip));
332
333	case DDI_RESUME:
334		return (audio810_resume(dip));
335	}
336	return (DDI_FAILURE);
337}
338
339/*
340 * audio810_ddi_detach()
341 *
342 * Description:
343 *	Implements the detach(9e) entry point.
344 *
345 * Arguments:
346 *	dev_info_t		*dip	Pointer to the device's dev_info struct
347 *	ddi_detach_cmd_t	cmd	Detach command
348 *
349 * Returns:
350 *	DDI_SUCCESS	The driver was detached
351 *	DDI_FAILURE	The driver couldn't be detached
352 */
353static int
354audio810_ddi_detach(dev_info_t *dip, ddi_detach_cmd_t cmd)
355{
356	switch (cmd) {
357	case DDI_DETACH:
358		return (audio810_detach(dip));
359
360	case DDI_SUSPEND:
361		return (audio810_suspend(dip));
362	}
363	return (DDI_FAILURE);
364}
365
366/*
367 * audio810_ddi_quiesce()
368 *
369 * Description:
370 *	Implements the quiesce(9e) entry point.
371 *
372 * Arguments:
373 *	dev_info_t		*dip	Pointer to the device's dev_info struct
374 *
375 * Returns:
376 *	DDI_SUCCESS	The driver was quiesced
377 *	DDI_FAILURE	The driver couldn't be quiesced
378 */
379static int
380audio810_ddi_quiesce(dev_info_t *dip)
381{
382	audio810_state_t	*statep;
383
384	if ((statep = ddi_get_driver_private(dip)) == NULL)
385		return (DDI_FAILURE);
386
387	audio810_stop_dma(statep);
388	return (DDI_SUCCESS);
389}
390
391/*
392 * audio810_open()
393 *
394 * Description:
395 *	Opens a DMA engine for use.
396 *
397 * Arguments:
398 *	void		*arg		The DMA engine to set up
399 *	int		flag		Open flags
400 *	unsigned	*nframes	Receives total number of frames
401 *	caddr_t		*bufp		Receives kernel data buffer
402 *
403 * Returns:
404 *	0	on success
405 *	errno	on failure
406 */
407static int
408audio810_open(void *arg, int flag, unsigned *nframes, caddr_t *bufp)
409{
410	audio810_port_t	*port = arg;
411
412	_NOTE(ARGUNUSED(flag));
413
414	port->count = 0;
415	*nframes = port->samp_frames;
416	*bufp = port->samp_kaddr;
417
418	return (0);
419}
420
421/*
422 * audio810_close()
423 *
424 * Description:
425 *	Closes an audio DMA engine that was previously opened.  Since
426 *	nobody is using it, we take this opportunity to possibly power
427 *	down the entire device.
428 *
429 * Arguments:
430 *	void	*arg		The DMA engine to shut down
431 */
432static void
433audio810_close(void *arg)
434{
435	_NOTE(ARGUNUSED(arg));
436}
437
438/*
439 * audio810_stop()
440 *
441 * Description:
442 *	This is called by the framework to stop a port that is
443 *	transferring data.
444 *
445 * Arguments:
446 *	void	*arg		The DMA engine to stop
447 */
448static void
449audio810_stop(void *arg)
450{
451	audio810_port_t		*port = arg;
452	audio810_state_t	*statep = port->statep;
453	uint8_t			cr;
454
455	cr = I810_BM_GET8(port->regoff + I810_OFFSET_CR);
456	cr &= ~I810_BM_CR_RUN;
457	I810_BM_PUT8(port->regoff + I810_OFFSET_CR, cr);
458}
459
460/*
461 * audio810_start()
462 *
463 * Description:
464 *	This is called by the framework to start a port transferring data.
465 *
466 * Arguments:
467 *	void	*arg		The DMA engine to start
468 *
469 * Returns:
470 *	0 	on success (never fails, errno if it did)
471 */
472static int
473audio810_start(void *arg)
474{
475	audio810_port_t		*port = arg;
476	audio810_state_t	*statep = port->statep;
477	uint8_t			regoff, cr;
478
479	regoff = port->regoff;
480	port->offset = 0;
481
482	/* program multiple channel settings */
483	if (port->num == I810_PCM_OUT) {
484		audio810_set_channels(statep);
485
486		if (statep->quirk == QUIRK_SIS7012) {
487			/*
488			 * SiS 7012 has special unmute bit.
489			 */
490			I810_BM_PUT8(I810_REG_SISCTL, I810_SISCTL_UNMUTE);
491		}
492	}
493
494	/*
495	 * Perform full reset of the engine, but leave it turned off.
496	 */
497	I810_BM_PUT8(regoff + I810_OFFSET_CR, 0);
498	I810_BM_PUT8(regoff + I810_OFFSET_CR, I810_BM_CR_RST);
499
500	/* program the offset of the BD list */
501	I810_BM_PUT32(regoff + I810_OFFSET_BD_BASE, port->bdl_paddr);
502
503	/* we set the last index to the full count -- all buffers are valid */
504	I810_BM_PUT8(regoff + I810_OFFSET_LVI, I810_BD_NUMS - 1);
505
506	cr = I810_BM_GET8(regoff + I810_OFFSET_CR);
507	cr |= I810_BM_CR_RUN;
508	I810_BM_PUT8(regoff + I810_OFFSET_CR, cr);
509
510	(void) I810_BM_GET8(regoff + I810_OFFSET_CR);
511
512	return (0);
513}
514
515/*
516 * audio810_format()
517 *
518 * Description:
519 *	This is called by the framework to query the format of the device.
520 *
521 * Arguments:
522 *	void	*arg		The DMA engine to query
523 *
524 * Returns:
525 *	Format of the device (fixed at AUDIO_FORMAT_S16_LE)
526 */
527static int
528audio810_format(void *arg)
529{
530	_NOTE(ARGUNUSED(arg));
531
532	return (AUDIO_FORMAT_S16_LE);
533}
534
535/*
536 * audio810_channels()
537 *
538 * Description:
539 *	This is called by the framework to query the num channels of
540 *	the device.
541 *
542 * Arguments:
543 *	void	*arg		The DMA engine to query
544 *
545 * Returns:
546 *	0 number of channels for device
547 */
548static int
549audio810_channels(void *arg)
550{
551	audio810_port_t	*port = arg;
552
553	return (port->nchan);
554}
555
556/*
557 * audio810_rate()
558 *
559 * Description:
560 *	This is called by the framework to query the rate of the device.
561 *
562 * Arguments:
563 *	void	*arg		The DMA engine to query
564 *
565 * Returns:
566 *	Rate of device (fixed at 48000 Hz)
567 */
568static int
569audio810_rate(void *arg)
570{
571	_NOTE(ARGUNUSED(arg));
572
573	return (48000);
574}
575
576/*
577 * audio810_count()
578 *
579 * Description:
580 *	This is called by the framework to get the engine's frame counter
581 *
582 * Arguments:
583 *	void	*arg		The DMA engine to query
584 *
585 * Returns:
586 *	frame count for current engine
587 */
588static uint64_t
589audio810_count(void *arg)
590{
591	audio810_port_t		*port = arg;
592	audio810_state_t	*statep = port->statep;
593	uint8_t			regoff = port->regoff;
594	uint64_t		val;
595	uint32_t		offset;
596	uint8_t			civ;
597
598	/*
599	 * Read the position counters.  We also take this opportunity
600	 * to update the last valid index to the one just previous to
601	 * the one we're working on (so we'll fully loop.)
602	 */
603	offset = I810_BM_GET16(port->picboff);
604	civ = I810_BM_GET8(regoff + I810_OFFSET_CIV);
605	I810_BM_PUT8(port->regoff + I810_OFFSET_LVI, (civ - 1) % I810_BD_NUMS);
606
607	/* SiS counts in bytes, all others in words. */
608	if (statep->quirk != QUIRK_SIS7012)
609		offset *= 2;
610
611	/* counter is reversed */
612	offset = port->samp_size - offset;
613
614	if (offset < port->offset) {
615		val = (port->samp_size - port->offset) + offset;
616	} else {
617		val = offset - port->offset;
618	}
619	port->offset = offset;
620	port->count += (val / (port->nchan * 2));
621	val = port->count;
622
623	return (val);
624}
625
626/*
627 * audio810_sync()
628 *
629 * Description:
630 *	This is called by the framework to synchronize DMA caches.
631 *
632 * Arguments:
633 *	void	*arg		The DMA engine to sync
634 */
635static void
636audio810_sync(void *arg, unsigned nframes)
637{
638	audio810_port_t *port = arg;
639	_NOTE(ARGUNUSED(nframes));
640
641	(void) ddi_dma_sync(port->samp_dmah, 0, 0, port->sync_dir);
642}
643
644/*
645 * audio810_playahead()
646 *
647 * Description:
648 *	This is called by the framework to determine how much data it
649 *	should queue up.  We desire a deeper playahead than most to
650 *	allow for virtualized devices which have less "regular"
651 *	interrupt scheduling.
652 *
653 * Arguments:
654 *	void	*arg		The DMA engine to query
655 *
656 * Returns:
657 *	Play ahead in frames.
658 */
659static unsigned
660audio810_playahead(void *arg)
661{
662	audio810_port_t *port = arg;
663	audio810_state_t	*statep = port->statep;
664
665	/* Older ICH is likely to be emulated, deeper (40 ms) playahead */
666	return (statep->quirk == QUIRK_OLDICH ? 1920 : 0);
667}
668
669
670
671/* *********************** Local Routines *************************** */
672
673/*
674 * audio810_attach()
675 *
676 * Description:
677 *	Attach an instance of the audio810 driver. This routine does the
678 * 	device dependent attach tasks, and registers with the audio framework.
679 *
680 * Arguments:
681 *	dev_info_t	*dip	Pointer to the device's dev_info struct
682 *	ddi_attach_cmd_t cmd	Attach command
683 *
684 * Returns:
685 *	DDI_SUCCESS		The driver was initialized properly
686 *	DDI_FAILURE		The driver couldn't be initialized properly
687 */
688static int
689audio810_attach(dev_info_t *dip)
690{
691	uint16_t		cmdreg;
692	audio810_state_t	*statep;
693	audio_dev_t		*adev;
694	ddi_acc_handle_t	pcih;
695	uint32_t		devid;
696	uint32_t		gsr;
697	const char		*name;
698	const char		*vers;
699	uint8_t			nch;
700	int			maxch;
701
702	/* allocate the soft state structure */
703	statep = kmem_zalloc(sizeof (*statep), KM_SLEEP);
704	ddi_set_driver_private(dip, statep);
705
706	if ((adev = audio_dev_alloc(dip, 0)) == NULL) {
707		cmn_err(CE_WARN, "!%s%d: unable to allocate audio dev",
708		    ddi_driver_name(dip), ddi_get_instance(dip));
709		goto error;
710	}
711	statep->adev = adev;
712	statep->dip = dip;
713
714	/* map in the registers, allocate DMA buffers, etc. */
715	if (audio810_map_regs(dip, statep) != DDI_SUCCESS) {
716		audio_dev_warn(adev, "couldn't map registers");
717		goto error;
718	}
719
720	/* set PCI command register */
721	if (pci_config_setup(dip, &pcih) != DDI_SUCCESS) {
722		audio_dev_warn(adev, "pci conf mapping failed");
723		goto error;
724	}
725	cmdreg = pci_config_get16(pcih, PCI_CONF_COMM);
726	pci_config_put16(pcih, PCI_CONF_COMM,
727	    cmdreg | PCI_COMM_IO | PCI_COMM_MAE | PCI_COMM_ME);
728	devid = pci_config_get16(pcih, PCI_CONF_VENID);
729	devid <<= 16;
730	devid |= pci_config_get16(pcih, PCI_CONF_DEVID);
731	pci_config_teardown(&pcih);
732
733	name = "Unknown AC'97";
734	vers = "";
735
736	statep->quirk = QUIRK_NONE;
737	switch (devid) {
738	case 0x80862415:
739		name = "Intel AC'97";
740		vers = "ICH";
741		statep->quirk = QUIRK_OLDICH;
742		break;
743	case 0x80862425:
744		name = "Intel AC'97";
745		vers = "ICH0";
746		break;
747	case 0x80867195:
748		name = "Intel AC'97";
749		vers = "440MX";
750		break;
751	case 0x80862445:
752		name = "Intel AC'97";
753		vers = "ICH2";
754		break;
755	case 0x80862485:
756		name = "Intel AC'97";
757		vers = "ICH3";
758		break;
759	case 0x808624C5:
760		name = "Intel AC'97";
761		vers = "ICH4";
762		break;
763	case 0x808624D5:
764		name = "Intel AC'97";
765		vers = "ICH5";
766		break;
767	case 0x8086266E:
768		name = "Intel AC'97";
769		vers = "ICH6";
770		break;
771	case 0x808627DE:
772		name = "Intel AC'97";
773		vers = "ICH7";
774		break;
775	case 0x808625A6:
776		name = "Intel AC'97";
777		vers = "6300ESB";
778		break;
779	case 0x80862698:
780		name = "Intel AC'97";
781		vers = "ESB2";
782		break;
783	case 0x10397012:
784		name = "SiS AC'97";
785		vers = "7012";
786		statep->quirk = QUIRK_SIS7012;
787		break;
788	case 0x10de01b1:	/* nForce */
789		name = "NVIDIA AC'97";
790		vers = "MCP1";
791		break;
792	case 0x10de006a:	/* nForce 2 */
793		name = "NVIDIA AC'97";
794		vers = "MCP2";
795		break;
796	case 0x10de00da:	/* nForce 3 */
797		name = "NVIDIA AC'97";
798		vers = "MCP3";
799		break;
800	case 0x10de00ea:
801		name = "NVIDIA AC'97";
802		vers = "CK8S";
803		break;
804	case 0x10de0059:
805		name = "NVIDIA AC'97";
806		vers = "CK804";
807		break;
808	case 0x10de008a:
809		name = "NVIDIA AC'97";
810		vers = "CK8";
811		break;
812	case 0x10de003a:	/* nForce 4 */
813		name = "NVIDIA AC'97";
814		vers = "MCP4";
815		break;
816	case 0x10de026b:
817		name = "NVIDIA AC'97";
818		vers = "MCP51";
819		break;
820	case 0x1022746d:
821		name = "AMD AC'97";
822		vers = "8111";
823		break;
824	case 0x10227445:
825		name = "AMD AC'97";
826		vers = "AMD768";
827		break;
828	}
829	/* set device information */
830	audio_dev_set_description(adev, name);
831	audio_dev_set_version(adev, vers);
832
833	/* initialize audio controller and AC97 codec */
834	if (audio810_chip_init(statep) != DDI_SUCCESS) {
835		audio_dev_warn(adev, "failed to init chip");
836		goto error;
837	}
838
839	/* allocate ac97 handle */
840	statep->ac97 = ac97_alloc(dip, audio810_read_ac97, audio810_write_ac97,
841	    statep);
842	if (statep->ac97 == NULL) {
843		audio_dev_warn(adev, "failed to allocate ac97 handle");
844		goto error;
845	}
846
847	/* initialize the AC'97 part */
848	if (ac97_init(statep->ac97, adev) != DDI_SUCCESS) {
849		audio_dev_warn(adev, "ac'97 initialization failed");
850		goto error;
851	}
852
853	/*
854	 * Override "max-channels" property to prevent configuration
855	 * of 4 or 6 (or possibly even 8!) channel audio.  The default
856	 * is to support as many channels as the hardware can do.
857	 *
858	 * (Hmmm... perhaps this should be driven in the common
859	 * framework.  The framework could even offer simplistic upmix
860	 * and downmix for various standard configs.)
861	 */
862	maxch = ddi_prop_get_int(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
863	    "max-channels", ac97_num_channels(statep->ac97));
864	if (maxch < 2) {
865		maxch = 2;
866	}
867
868	gsr = I810_BM_GET32(I810_REG_GSR);
869	if (gsr & I810_GSR_CAP6CH) {
870		nch = 6;
871	} else if (gsr & I810_GSR_CAP4CH) {
872		nch = 4;
873	} else {
874		nch = 2;
875	}
876
877	statep->maxch = (uint8_t)min(nch, maxch);
878	statep->maxch &= ~1;
879
880	/* allocate port structures */
881	if ((audio810_alloc_port(statep, I810_PCM_OUT, statep->maxch) !=
882	    DDI_SUCCESS) ||
883	    (audio810_alloc_port(statep, I810_PCM_IN, 2) != DDI_SUCCESS)) {
884		goto error;
885	}
886
887	if (audio_dev_register(adev) != DDI_SUCCESS) {
888		audio_dev_warn(adev, "unable to register with framework");
889		goto error;
890	}
891
892	ddi_report_dev(dip);
893
894	return (DDI_SUCCESS);
895
896error:
897	audio810_destroy(statep);
898
899	return (DDI_FAILURE);
900}
901
902
903/*
904 * audio810_resume()
905 *
906 * Description:
907 *	Resume operation of the device after sleeping or hibernating.
908 *	Note that this should never fail, even if hardware goes wonky,
909 *	because the current PM framework will panic if it does.
910 *
911 * Arguments:
912 *	dev_info_t	*dip	Pointer to the device's dev_info struct
913 *
914 * Returns:
915 *	DDI_SUCCESS		The driver was resumed.
916 */
917static int
918audio810_resume(dev_info_t *dip)
919{
920	audio810_state_t	*statep;
921	audio_dev_t		*adev;
922
923	/* this should always be valid */
924	statep = ddi_get_driver_private(dip);
925	adev = statep->adev;
926
927	ASSERT(statep != NULL);
928	ASSERT(dip == statep->dip);
929
930	/* Restore the audio810 chip's state */
931	if (audio810_chip_init(statep) != DDI_SUCCESS) {
932		/*
933		 * Note that PM gurus say we should return success
934		 * here.  Failure of audio shouldn't be considered
935		 * FATAL to the system.
936		 *
937		 * It turns out that the only way that the
938		 * audio810_chip_init fails is that the codec won't
939		 * re-initialize.  Audio streams may or may not make
940		 * progress; setting changes may or may not have the
941		 * desired effect.  What we'd really to do at this
942		 * point is use FMA to offline the part.  In the
943		 * meantime, we just muddle on logging the error.
944		 *
945		 * Note that returning from this routine without
946		 * allowing the audio_dev_resume() to take place can
947		 * have bad effects, as the framework does not know
948		 * what to do in the event of a failure of this
949		 * nature.  (It may be unsafe to call ENG_CLOSE(), for
950		 * example.)
951		 */
952		audio_dev_warn(adev, "failure to resume codec");
953	}
954
955	/* Reset the AC'97 codec. */
956	ac97_reset(statep->ac97);
957
958	/* And let the framework know we're ready for business again. */
959	audio_dev_resume(statep->adev);
960
961	return (DDI_SUCCESS);
962}
963
964/*
965 * audio810_detach()
966 *
967 * Description:
968 *	Detach an instance of the audio810 driver.
969 *
970 * Arguments:
971 *	dev_info_t		*dip	Pointer to the device's dev_info struct
972 *
973 * Returns:
974 *	DDI_SUCCESS	The driver was detached
975 *	DDI_FAILURE	The driver couldn't be detached
976 */
977static int
978audio810_detach(dev_info_t *dip)
979{
980	audio810_state_t	*statep;
981
982	statep = ddi_get_driver_private(dip);
983	ASSERT(statep != NULL);
984
985	/* don't detach us if we are still in use */
986	if (audio_dev_unregister(statep->adev) != DDI_SUCCESS) {
987		return (DDI_FAILURE);
988	}
989
990	audio810_destroy(statep);
991	return (DDI_SUCCESS);
992}
993
994/*
995 * audio810_suspend()
996 *
997 * Description:
998 *	Suspend an instance of the audio810 driver, in preparation for
999 *	sleep or hibernation.
1000 *
1001 * Arguments:
1002 *	dev_info_t		*dip	Pointer to the device's dev_info struct
1003 *
1004 * Returns:
1005 *	DDI_SUCCESS	The driver was suspended
1006 */
1007static int
1008audio810_suspend(dev_info_t *dip)
1009{
1010	audio810_state_t	*statep;
1011
1012	statep = ddi_get_driver_private(dip);
1013	ASSERT(statep != NULL);
1014
1015	audio_dev_suspend(statep->adev);
1016
1017	/* stop DMA engines - should be redundant (paranoia) */
1018	audio810_stop_dma(statep);
1019
1020	return (DDI_SUCCESS);
1021}
1022
1023/*
1024 * audio810_alloc_port()
1025 *
1026 * Description:
1027 *	This routine allocates the DMA handles and the memory for the
1028 *	DMA engines to use.  It also configures the BDL lists properly
1029 *	for use.
1030 *
1031 * Arguments:
1032 *	dev_info_t	*dip	Pointer to the device's devinfo
1033 *
1034 * Returns:
1035 *	DDI_SUCCESS		Registers successfully mapped
1036 *	DDI_FAILURE		Registers not successfully mapped
1037 */
1038static int
1039audio810_alloc_port(audio810_state_t *statep, int num, uint8_t nchan)
1040{
1041	ddi_dma_cookie_t	cookie;
1042	uint_t			count;
1043	int			dir;
1044	unsigned		caps;
1045	audio_dev_t		*adev;
1046	audio810_port_t		*port;
1047	int			rc;
1048	dev_info_t		*dip;
1049	i810_bd_entry_t		*bdentry;
1050
1051	adev = statep->adev;
1052	dip = statep->dip;
1053
1054	port = kmem_zalloc(sizeof (*port), KM_SLEEP);
1055	statep->ports[num] = port;
1056	port->statep = statep;
1057	port->nchan = nchan;
1058	port->num = num;
1059
1060	switch (num) {
1061	case I810_PCM_IN:
1062		dir = DDI_DMA_READ;
1063		caps = ENGINE_INPUT_CAP;
1064		port->sync_dir = DDI_DMA_SYNC_FORKERNEL;
1065		port->regoff = I810_BASE_PCM_IN;
1066		break;
1067	case I810_PCM_OUT:
1068		dir = DDI_DMA_WRITE;
1069		caps = ENGINE_OUTPUT_CAP;
1070		port->sync_dir = DDI_DMA_SYNC_FORDEV;
1071		port->regoff = I810_BASE_PCM_OUT;
1072		break;
1073	default:
1074		audio_dev_warn(adev, "bad port number (%d)!", num);
1075		return (DDI_FAILURE);
1076	}
1077
1078	/*
1079	 * SiS 7012 swaps status and picb registers.
1080	 */
1081	if (statep->quirk == QUIRK_SIS7012) {
1082		port->stsoff = port->regoff + I810_OFFSET_PICB;
1083		port->picboff = port->regoff + I810_OFFSET_SR;
1084	} else {
1085		port->stsoff = port->regoff + I810_OFFSET_SR;
1086		port->picboff = port->regoff + I810_OFFSET_PICB;
1087	}
1088
1089	/*
1090	 * We use one big sample area.  The sample area must be larger
1091	 * than about 1.5 framework fragment sizes.  (Currently 480 *
1092	 * 1.5 = 720 frames.)  This is necessary to ensure that we
1093	 * don't have to involve an interrupt service routine on our
1094	 * own, to keep the last valid index updated reasonably.
1095	 */
1096	port->samp_frames = 4096;
1097	port->samp_size = port->samp_frames * port->nchan * sizeof (int16_t);
1098
1099	/* allocate dma handle */
1100	rc = ddi_dma_alloc_handle(dip, &sample_buf_dma_attr, DDI_DMA_SLEEP,
1101	    NULL, &port->samp_dmah);
1102	if (rc != DDI_SUCCESS) {
1103		audio_dev_warn(adev, "ddi_dma_alloc_handle failed: %d", rc);
1104		return (DDI_FAILURE);
1105	}
1106	/* allocate DMA buffer */
1107	rc = ddi_dma_mem_alloc(port->samp_dmah, port->samp_size, &buf_attr,
1108	    DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, NULL, &port->samp_kaddr,
1109	    &port->samp_size, &port->samp_acch);
1110	if (rc == DDI_FAILURE) {
1111		audio_dev_warn(adev, "dma_mem_alloc (%d) failed: %d",
1112		    port->samp_size, rc);
1113		return (DDI_FAILURE);
1114	}
1115
1116	/* bind DMA buffer */
1117	rc = ddi_dma_addr_bind_handle(port->samp_dmah, NULL,
1118	    port->samp_kaddr, port->samp_size, dir|DDI_DMA_CONSISTENT,
1119	    DDI_DMA_SLEEP, NULL, &cookie, &count);
1120	if ((rc != DDI_DMA_MAPPED) || (count != 1)) {
1121		audio_dev_warn(adev,
1122		    "ddi_dma_addr_bind_handle failed: %d", rc);
1123		return (DDI_FAILURE);
1124	}
1125	port->samp_paddr = cookie.dmac_address;
1126
1127	/*
1128	 * now, from here we allocate DMA memory for buffer descriptor list.
1129	 * we allocate adjacent DMA memory for all DMA engines.
1130	 */
1131	rc = ddi_dma_alloc_handle(dip, &bdlist_dma_attr, DDI_DMA_SLEEP,
1132	    NULL, &port->bdl_dmah);
1133	if (rc != DDI_SUCCESS) {
1134		audio_dev_warn(adev, "ddi_dma_alloc_handle(bdlist) failed");
1135		return (DDI_FAILURE);
1136	}
1137
1138	/*
1139	 * we allocate all buffer descriptors lists in continuous dma memory.
1140	 */
1141	port->bdl_size = sizeof (i810_bd_entry_t) * I810_BD_NUMS;
1142	rc = ddi_dma_mem_alloc(port->bdl_dmah, port->bdl_size,
1143	    &dev_attr, DDI_DMA_CONSISTENT, DDI_DMA_SLEEP, NULL,
1144	    &port->bdl_kaddr, &port->bdl_size, &port->bdl_acch);
1145	if (rc != DDI_SUCCESS) {
1146		audio_dev_warn(adev, "ddi_dma_mem_alloc(bdlist) failed");
1147		return (DDI_FAILURE);
1148	}
1149
1150	rc = ddi_dma_addr_bind_handle(port->bdl_dmah, NULL, port->bdl_kaddr,
1151	    port->bdl_size, DDI_DMA_WRITE|DDI_DMA_CONSISTENT, DDI_DMA_SLEEP,
1152	    NULL, &cookie, &count);
1153	if ((rc != DDI_DMA_MAPPED) || (count != 1)) {
1154		audio_dev_warn(adev, "addr_bind_handle failed");
1155		return (DDI_FAILURE);
1156	}
1157	port->bdl_paddr = cookie.dmac_address;
1158
1159	/*
1160	 * Wire up the BD list.
1161	 */
1162	bdentry = (void *)port->bdl_kaddr;
1163	for (int i = 0; i < I810_BD_NUMS; i++) {
1164
1165		/* set base address of buffer */
1166		ddi_put32(port->bdl_acch, &bdentry->buf_base,
1167		    port->samp_paddr);
1168		/* SiS 7012 counts in bytes, all others in words */
1169		ddi_put16(port->bdl_acch, &bdentry->buf_len,
1170		    statep->quirk == QUIRK_SIS7012 ? port->samp_size :
1171		    port->samp_size / 2);
1172		ddi_put16(port->bdl_acch, &bdentry->buf_cmd, BUF_CMD_BUP);
1173
1174		bdentry++;
1175	}
1176	(void) ddi_dma_sync(port->bdl_dmah, 0, 0, DDI_DMA_SYNC_FORDEV);
1177
1178	port->engine = audio_engine_alloc(&audio810_engine_ops, caps);
1179	if (port->engine == NULL) {
1180		audio_dev_warn(adev, "audio_engine_alloc failed");
1181		return (DDI_FAILURE);
1182	}
1183
1184	audio_engine_set_private(port->engine, port);
1185	audio_dev_add_engine(adev, port->engine);
1186
1187	return (DDI_SUCCESS);
1188}
1189
1190/*
1191 * audio810_free_port()
1192 *
1193 * Description:
1194 *	This routine unbinds the DMA cookies, frees the DMA buffers,
1195 *	deallocates the DMA handles.
1196 *
1197 * Arguments:
1198 *	audio810_port_t	*port	The port structure for a DMA engine.
1199 */
1200static void
1201audio810_free_port(audio810_port_t *port)
1202{
1203	if (port == NULL)
1204		return;
1205
1206	if (port->engine) {
1207		audio_dev_remove_engine(port->statep->adev, port->engine);
1208		audio_engine_free(port->engine);
1209	}
1210	if (port->bdl_paddr) {
1211		(void) ddi_dma_unbind_handle(port->bdl_dmah);
1212	}
1213	if (port->bdl_acch) {
1214		ddi_dma_mem_free(&port->bdl_acch);
1215	}
1216	if (port->bdl_dmah) {
1217		ddi_dma_free_handle(&port->bdl_dmah);
1218	}
1219	if (port->samp_paddr) {
1220		(void) ddi_dma_unbind_handle(port->samp_dmah);
1221	}
1222	if (port->samp_acch) {
1223		ddi_dma_mem_free(&port->samp_acch);
1224	}
1225	if (port->samp_dmah) {
1226		ddi_dma_free_handle(&port->samp_dmah);
1227	}
1228	kmem_free(port, sizeof (*port));
1229}
1230
1231/*
1232 * audio810_map_regs()
1233 *
1234 * Description:
1235 *	The registers are mapped in.
1236 *
1237 * Arguments:
1238 *	dev_info_t	*dip	Pointer to the device's devinfo
1239 *
1240 * Returns:
1241 *	DDI_SUCCESS		Registers successfully mapped
1242 *	DDI_FAILURE		Registers not successfully mapped
1243 */
1244static int
1245audio810_map_regs(dev_info_t *dip, audio810_state_t *statep)
1246{
1247	uint_t			nregs = 0;
1248	int			*regs_list;
1249	int			i;
1250	int			pciBar1 = 0;
1251	int			pciBar2 = 0;
1252	int			pciBar3 = 0;
1253	int			pciBar4 = 0;
1254
1255	/* check the "reg" property to get the length of memory-mapped I/O */
1256	if (ddi_prop_lookup_int_array(DDI_DEV_T_ANY, dip, DDI_PROP_DONTPASS,
1257	    "reg", (int **)&regs_list, &nregs) != DDI_PROP_SUCCESS) {
1258		audio_dev_warn(statep->adev, "inquire regs property failed");
1259		goto error;
1260	}
1261	/*
1262	 * Some hardwares, such as Intel ICH0/ICH and AMD 8111, use PCI 0x10
1263	 * and 0x14 BAR separately for native audio mixer BAR and native bus
1264	 * mastering BAR. More advanced hardwares, such as Intel ICH4 and ICH5,
1265	 * support PCI memory BAR, via PCI 0x18 and 0x1C BAR, that allows for
1266	 * higher performance access to the controller register. All features
1267	 * can be accessed via this BAR making the I/O BAR (PCI 0x10 and 0x14
1268	 * BAR) capabilities obsolete. However, these controller maintain the
1269	 * I/O BAR capability to allow for the reuse of legacy code maintaining
1270	 * backward compatibility. The I/O BAR is disabled unless system BIOS
1271	 * enables the simultaneous backward compatible capability on the 0x41
1272	 * register.
1273	 *
1274	 * When I/O BAR is enabled, the value of "reg" property should be like
1275	 * this,
1276	 *	phys_hi   phys_mid  phys_lo   size_hi   size_lo
1277	 * --------------------------------------------------------
1278	 *	0000fd00  00000000  00000000  00000000  00000000
1279	 *	0100fd10  00000000  00000000  00000000  00000100
1280	 *	0100fd14  00000000  00000000  00000000  00000040
1281	 *	0200fd18  00000000  00000000  00000000  00000200
1282	 *	0200fd1c  00000000  00000000  00000000  00000100
1283	 *
1284	 * When I/O BAR is disabled, the "reg" property of the device node does
1285	 * not consist of the description for the I/O BAR. The following example
1286	 * illustrates the vaule of "reg" property,
1287	 *
1288	 *	phys_hi   phys_mid  phys_lo   size_hi   size_lo
1289	 * --------------------------------------------------------
1290	 *	0000fd00  00000000  00000000  00000000  00000000
1291	 *	0200fd18  00000000  00000000  00000000  00000200
1292	 *	0200fd1c  00000000  00000000  00000000  00000100
1293	 *
1294	 * If the hardware has memory-mapped I/O access, first try to use
1295	 * this facility, otherwise we will try I/O access.
1296	 */
1297	for (i = 1; i < nregs/I810_INTS_PER_REG_PROP; i++) {
1298		switch (regs_list[I810_INTS_PER_REG_PROP * i] & 0x000000ff) {
1299			case 0x10:
1300				pciBar1 = i;
1301				break;
1302			case 0x14:
1303				pciBar2 = i;
1304				break;
1305			case 0x18:
1306				pciBar3 = i;
1307				break;
1308			case 0x1c:
1309				pciBar4 = i;
1310				break;
1311			default:	/* we don't care others */
1312				break;
1313		}
1314	}
1315
1316	if ((pciBar3 != 0) && (pciBar4 != 0)) {
1317		/* map audio mixer registers */
1318		if ((ddi_regs_map_setup(dip, pciBar3, &statep->am_regs_base, 0,
1319		    0, &dev_attr, &statep->am_regs_handle)) != DDI_SUCCESS) {
1320			audio_dev_warn(statep->adev,
1321			    "memory am mapping failed");
1322			goto error;
1323		}
1324
1325		/* map bus master register */
1326		if ((ddi_regs_map_setup(dip, pciBar4, &statep->bm_regs_base, 0,
1327		    0, &dev_attr, &statep->bm_regs_handle)) != DDI_SUCCESS) {
1328			audio_dev_warn(statep->adev,
1329			    "memory bm mapping failed");
1330			goto error;
1331		}
1332
1333	} else if ((pciBar1 != 0) && (pciBar2 != 0)) {
1334		/* map audio mixer registers */
1335		if ((ddi_regs_map_setup(dip, pciBar1, &statep->am_regs_base, 0,
1336		    0, &dev_attr, &statep->am_regs_handle)) != DDI_SUCCESS) {
1337			audio_dev_warn(statep->adev, "I/O am mapping failed");
1338			goto error;
1339		}
1340
1341		/* map bus master register */
1342		if ((ddi_regs_map_setup(dip, pciBar2, &statep->bm_regs_base, 0,
1343		    0, &dev_attr, &statep->bm_regs_handle)) != DDI_SUCCESS) {
1344			audio_dev_warn(statep->adev, "I/O bm mapping failed");
1345			goto error;
1346		}
1347	} else {
1348		audio_dev_warn(statep->adev, "map_regs() pci BAR error");
1349		goto error;
1350	}
1351
1352	ddi_prop_free(regs_list);
1353
1354	return (DDI_SUCCESS);
1355
1356error:
1357	if (nregs > 0) {
1358		ddi_prop_free(regs_list);
1359	}
1360	audio810_unmap_regs(statep);
1361
1362	return (DDI_FAILURE);
1363}
1364
1365/*
1366 * audio810_unmap_regs()
1367 *
1368 * Description:
1369 *	This routine unmaps control registers.
1370 *
1371 * Arguments:
1372 *	audio810_state_t	*state	The device's state structure
1373 */
1374static void
1375audio810_unmap_regs(audio810_state_t *statep)
1376{
1377	if (statep->bm_regs_handle) {
1378		ddi_regs_map_free(&statep->bm_regs_handle);
1379	}
1380
1381	if (statep->am_regs_handle) {
1382		ddi_regs_map_free(&statep->am_regs_handle);
1383	}
1384}
1385
1386/*
1387 * audio810_chip_init()
1388 *
1389 * Description:
1390 *	This routine initializes the audio controller.
1391 *
1392 * Arguments:
1393 *	audio810_state_t	*state		The device's state structure
1394 *
1395 * Returns:
1396 *	DDI_SUCCESS	The hardware was initialized properly
1397 *	DDI_FAILURE	The hardware couldn't be initialized properly
1398 */
1399static int
1400audio810_chip_init(audio810_state_t *statep)
1401{
1402	uint32_t	gcr;
1403	uint32_t	gsr;
1404	uint32_t	codec_ready;
1405	int 		loop;
1406	clock_t		ticks;
1407
1408	gcr = I810_BM_GET32(I810_REG_GCR);
1409	ticks = drv_usectohz(100);
1410
1411	/*
1412	 * Clear the channels bits for now.  We'll set them later in
1413	 * reset port.
1414	 */
1415	if (statep->quirk == QUIRK_SIS7012) {
1416		gcr &= ~(I810_GCR_ACLINK_OFF | I810_GCR_SIS_CHANNELS_MASK);
1417	} else {
1418		gcr &= ~(I810_GCR_ACLINK_OFF | I810_GCR_CHANNELS_MASK);
1419	}
1420
1421	/*
1422	 * Datasheet(ICH5, document number of Intel: 252751-001):
1423	 * 3.6.5.5(page 37)
1424	 * 	if reset bit(bit1) is "0", driver must set it
1425	 * 	to "1" to de-assert the AC_RESET# signal in AC
1426	 * 	link, thus completing a cold reset. But if the
1427	 * 	bit is "1", then a warm reset is required.
1428	 */
1429	gcr |= (gcr & I810_GCR_COLD_RST) == 0 ?
1430	    I810_GCR_COLD_RST:I810_GCR_WARM_RST;
1431	I810_BM_PUT32(I810_REG_GCR, gcr);
1432
1433	/* according AC'97 spec, wait for codec reset */
1434	for (loop = 6000; --loop >= 0; ) {
1435		delay(ticks);
1436		gcr = I810_BM_GET32(I810_REG_GCR);
1437		if ((gcr & I810_GCR_WARM_RST) == 0) {
1438			break;
1439		}
1440	}
1441
1442	/* codec reset failed */
1443	if (loop < 0) {
1444		audio_dev_warn(statep->adev, "Failed to reset codec");
1445		return (DDI_FAILURE);
1446	}
1447
1448	/*
1449	 * Wait for codec ready. The hardware can provide the state of
1450	 * codec ready bit on SDATA_IN[0], SDATA_IN[1] or SDATA_IN[2]
1451	 */
1452	codec_ready =
1453	    I810_GSR_PRI_READY | I810_GSR_SEC_READY | I810_GSR_TRI_READY;
1454	for (loop = 7000; --loop >= 0; ) {
1455		delay(ticks);
1456		gsr = I810_BM_GET32(I810_REG_GSR);
1457		if ((gsr & codec_ready) != 0) {
1458			break;
1459		}
1460	}
1461	if (loop < 0) {
1462		audio_dev_warn(statep->adev, "No codec ready signal received");
1463		return (DDI_FAILURE);
1464	}
1465
1466	/*
1467	 * put the audio controller into quiet state, everything off
1468	 */
1469	audio810_stop_dma(statep);
1470
1471	return (DDI_SUCCESS);
1472}
1473
1474/*
1475 * audio810_set_channels()
1476 *
1477 * Description:
1478 *	This routine initializes the multichannel configuration.
1479 *
1480 * Arguments:
1481 *	audio810_state_t	*state		The device's state structure
1482 */
1483static void
1484audio810_set_channels(audio810_state_t *statep)
1485{
1486	uint32_t	gcr;
1487
1488	/*
1489	 * Configure multi-channel.
1490	 */
1491	if (statep->quirk == QUIRK_SIS7012) {
1492		/*
1493		 * SiS 7012 needs its own special multichannel config.
1494		 */
1495		gcr = I810_BM_GET32(I810_REG_GCR);
1496		gcr &= ~I810_GCR_SIS_CHANNELS_MASK;
1497		I810_BM_PUT32(I810_REG_GCR, gcr);
1498		delay(drv_usectohz(50000));	/* 50 msec */
1499
1500		switch (statep->maxch) {
1501		case 2:
1502			gcr |= I810_GCR_SIS_2_CHANNELS;
1503			break;
1504		case 4:
1505			gcr |= I810_GCR_SIS_4_CHANNELS;
1506			break;
1507		case 6:
1508			gcr |= I810_GCR_SIS_6_CHANNELS;
1509			break;
1510		}
1511		I810_BM_PUT32(I810_REG_GCR, gcr);
1512		delay(drv_usectohz(50000));	/* 50 msec */
1513	} else {
1514
1515		/*
1516		 * All other devices work the same.
1517		 */
1518		gcr = I810_BM_GET32(I810_REG_GCR);
1519		gcr &= ~I810_GCR_CHANNELS_MASK;
1520
1521		I810_BM_PUT32(I810_REG_GCR, gcr);
1522		delay(drv_usectohz(50000));	/* 50 msec */
1523
1524		switch (statep->maxch) {
1525		case 2:
1526			gcr |= I810_GCR_2_CHANNELS;
1527			break;
1528		case 4:
1529			gcr |= I810_GCR_4_CHANNELS;
1530			break;
1531		case 6:
1532			gcr |= I810_GCR_6_CHANNELS;
1533			break;
1534		}
1535		I810_BM_PUT32(I810_REG_GCR, gcr);
1536		delay(drv_usectohz(50000));	/* 50 msec */
1537	}
1538}
1539
1540/*
1541 * audio810_stop_dma()
1542 *
1543 * Description:
1544 *	This routine is used to put each DMA engine into the quiet state.
1545 *
1546 * Arguments:
1547 *	audio810_state_t	*state		The device's state structure
1548 */
1549static void
1550audio810_stop_dma(audio810_state_t *statep)
1551{
1552	if (statep->bm_regs_handle == NULL) {
1553		return;
1554	}
1555	/* pause bus master (needed for the following reset register) */
1556	I810_BM_PUT8(I810_BASE_PCM_IN + I810_OFFSET_CR, 0x0);
1557	I810_BM_PUT8(I810_BASE_PCM_OUT + I810_OFFSET_CR, 0x0);
1558	I810_BM_PUT8(I810_BASE_MIC + I810_OFFSET_CR, 0x0);
1559
1560	/* and then reset the bus master registers for a three DMA engines */
1561	I810_BM_PUT8(I810_BASE_PCM_IN + I810_OFFSET_CR, I810_BM_CR_RST);
1562	I810_BM_PUT8(I810_BASE_PCM_OUT + I810_OFFSET_CR, I810_BM_CR_RST);
1563	I810_BM_PUT8(I810_BASE_MIC + I810_OFFSET_CR, I810_BM_CR_RST);
1564}
1565
1566
1567/*
1568 * audio810_codec_sync()
1569 *
1570 * Description:
1571 *	Serialize access to the AC97 audio mixer registers.
1572 *
1573 * Arguments:
1574 *	audio810_state_t	*state		The device's state structure
1575 *
1576 * Returns:
1577 *	DDI_SUCCESS		Ready for an I/O access to the codec
1578 *	DDI_FAILURE		An I/O access is currently in progress, can't
1579 *				perform another I/O access.
1580 */
1581static int
1582audio810_codec_sync(audio810_state_t *statep)
1583{
1584	int 		i;
1585	uint16_t	casr;
1586
1587	for (i = 0; i < 300; i++) {
1588		casr = I810_BM_GET8(I810_REG_CASR);
1589		if ((casr & 1) == 0) {
1590			return (DDI_SUCCESS);
1591		}
1592		drv_usecwait(10);
1593	}
1594
1595	return (DDI_FAILURE);
1596}
1597
1598/*
1599 * audio810_write_ac97()
1600 *
1601 * Description:
1602 *	Set the specific AC97 Codec register.
1603 *
1604 * Arguments:
1605 *	void		*arg		The device's state structure
1606 *	uint8_t		reg		AC97 register number
1607 *	uint16_t	data		The data want to be set
1608 */
1609static void
1610audio810_write_ac97(void *arg, uint8_t reg, uint16_t data)
1611{
1612	audio810_state_t	*statep = arg;
1613
1614	if (audio810_codec_sync(statep) == DDI_SUCCESS) {
1615		I810_AM_PUT16(reg, data);
1616	}
1617
1618	(void) audio810_read_ac97(statep, reg);
1619}
1620
1621/*
1622 * audio810_read_ac97()
1623 *
1624 * Description:
1625 *	Get the specific AC97 Codec register.
1626 *
1627 * Arguments:
1628 *	void		*arg		The device's state structure
1629 *	uint8_t		reg		AC97 register number
1630 *
1631 * Returns:
1632 *	The register value.
1633 */
1634static uint16_t
1635audio810_read_ac97(void *arg, uint8_t reg)
1636{
1637	audio810_state_t	*statep = arg;
1638	uint16_t		val = 0xffff;
1639
1640	if (audio810_codec_sync(statep) == DDI_SUCCESS) {
1641		val = I810_AM_GET16(reg);
1642	}
1643	return (val);
1644}
1645
1646/*
1647 * audio810_destroy()
1648 *
1649 * Description:
1650 *	This routine releases all resources held by the device instance,
1651 *	as part of either detach or a failure in attach.
1652 *
1653 * Arguments:
1654 *	audio810_state_t	*state	The device soft state.
1655 */
1656void
1657audio810_destroy(audio810_state_t *statep)
1658{
1659	/* stop DMA engines */
1660	audio810_stop_dma(statep);
1661
1662	for (int i = 0; i < I810_NUM_PORTS; i++) {
1663		audio810_free_port(statep->ports[i]);
1664	}
1665
1666	audio810_unmap_regs(statep);
1667
1668	if (statep->ac97)
1669		ac97_free(statep->ac97);
1670
1671	if (statep->adev)
1672		audio_dev_free(statep->adev);
1673
1674	kmem_free(statep, sizeof (*statep));
1675}
1676