1/*-
2 * SPDX-License-Identifier: BSD-2-Clause-FreeBSD
3 *
4 * Copyright (c) 2016 Alex Teaca <iateaca@FreeBSD.org>
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
17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26 * SUCH DAMAGE.
27 *
28 */
29
30#include <sys/cdefs.h>
31__FBSDID("$FreeBSD$");
32
33#include <time.h>
34
35#include "pci_hda.h"
36#include "bhyverun.h"
37#include "pci_emul.h"
38#include "hdac_reg.h"
39
40/*
41 * HDA defines
42 */
43#define PCIR_HDCTL		0x40
44#define INTEL_VENDORID		0x8086
45#define HDA_INTEL_82801G	0x27d8
46
47#define HDA_IOSS_NO		0x08
48#define HDA_OSS_NO		0x04
49#define HDA_ISS_NO		0x04
50#define HDA_CODEC_MAX		0x0f
51#define HDA_LAST_OFFSET						\
52	(0x2084 + ((HDA_ISS_NO) * 0x20) + ((HDA_OSS_NO) * 0x20))
53#define HDA_SET_REG_TABLE_SZ					\
54	(0x80 + ((HDA_ISS_NO) * 0x20) + ((HDA_OSS_NO) * 0x20))
55#define HDA_CORB_ENTRY_LEN	0x04
56#define HDA_RIRB_ENTRY_LEN	0x08
57#define HDA_BDL_ENTRY_LEN	0x10
58#define HDA_DMA_PIB_ENTRY_LEN	0x08
59#define HDA_STREAM_TAGS_CNT	0x10
60#define HDA_STREAM_REGS_BASE	0x80
61#define HDA_STREAM_REGS_LEN	0x20
62
63#define HDA_DMA_ACCESS_LEN	(sizeof(uint32_t))
64#define HDA_BDL_MAX_LEN		0x0100
65
66#define HDAC_SDSTS_FIFORDY	(1 << 5)
67
68#define HDA_RIRBSTS_IRQ_MASK	(HDAC_RIRBSTS_RINTFL | HDAC_RIRBSTS_RIRBOIS)
69#define HDA_STATESTS_IRQ_MASK	((1 << HDA_CODEC_MAX) - 1)
70#define HDA_SDSTS_IRQ_MASK					\
71	(HDAC_SDSTS_DESE | HDAC_SDSTS_FIFOE | HDAC_SDSTS_BCIS)
72
73/*
74 * HDA data structures
75 */
76
77struct hda_softc;
78
79typedef void (*hda_set_reg_handler)(struct hda_softc *sc, uint32_t offset,
80		uint32_t old);
81
82struct hda_bdle {
83	uint32_t addrl;
84	uint32_t addrh;
85	uint32_t len;
86	uint32_t ioc;
87} __packed;
88
89struct hda_bdle_desc {
90	void *addr;
91	uint8_t ioc;
92	uint32_t len;
93};
94
95struct hda_codec_cmd_ctl {
96	char *name;
97	void *dma_vaddr;
98	uint8_t run;
99	uint16_t rp;
100	uint16_t size;
101	uint16_t wp;
102};
103
104struct hda_stream_desc {
105	uint8_t dir;
106	uint8_t run;
107	uint8_t stream;
108
109	/* bp is the no. of bytes transferred in the current bdle */
110	uint32_t bp;
111	/* be is the no. of bdles transferred in the bdl */
112	uint32_t be;
113
114	uint32_t bdl_cnt;
115	struct hda_bdle_desc bdl[HDA_BDL_MAX_LEN];
116};
117
118struct hda_softc {
119	struct pci_devinst *pci_dev;
120	uint32_t regs[HDA_LAST_OFFSET];
121
122	uint8_t lintr;
123	uint8_t rirb_cnt;
124	uint64_t wall_clock_start;
125
126	struct hda_codec_cmd_ctl corb;
127	struct hda_codec_cmd_ctl rirb;
128
129	uint8_t codecs_no;
130	struct hda_codec_inst *codecs[HDA_CODEC_MAX];
131
132	/* Base Address of the DMA Position Buffer */
133	void *dma_pib_vaddr;
134
135	struct hda_stream_desc streams[HDA_IOSS_NO];
136	/* 2 tables for output and input */
137	uint8_t stream_map[2][HDA_STREAM_TAGS_CNT];
138};
139
140/*
141 * HDA module function declarations
142 */
143static inline void hda_set_reg_by_offset(struct hda_softc *sc, uint32_t offset,
144    uint32_t value);
145static inline uint32_t hda_get_reg_by_offset(struct hda_softc *sc,
146    uint32_t offset);
147static inline void hda_set_field_by_offset(struct hda_softc *sc,
148    uint32_t offset, uint32_t mask, uint32_t value);
149
150static uint8_t hda_parse_config(const char *opts, const char *key, char *val);
151static struct hda_softc *hda_init(const char *opts);
152static void hda_update_intr(struct hda_softc *sc);
153static void hda_response_interrupt(struct hda_softc *sc);
154static int hda_codec_constructor(struct hda_softc *sc,
155    struct hda_codec_class *codec, const char *play, const char *rec,
156    const char *opts);
157static struct hda_codec_class *hda_find_codec_class(const char *name);
158
159static int hda_send_command(struct hda_softc *sc, uint32_t verb);
160static int hda_notify_codecs(struct hda_softc *sc, uint8_t run,
161    uint8_t stream, uint8_t dir);
162static void hda_reset(struct hda_softc *sc);
163static void hda_reset_regs(struct hda_softc *sc);
164static void hda_stream_reset(struct hda_softc *sc, uint8_t stream_ind);
165static int hda_stream_start(struct hda_softc *sc, uint8_t stream_ind);
166static int hda_stream_stop(struct hda_softc *sc, uint8_t stream_ind);
167static uint32_t hda_read(struct hda_softc *sc, uint32_t offset);
168static int hda_write(struct hda_softc *sc, uint32_t offset, uint8_t size,
169    uint32_t value);
170
171static inline void hda_print_cmd_ctl_data(struct hda_codec_cmd_ctl *p);
172static int hda_corb_start(struct hda_softc *sc);
173static int hda_corb_run(struct hda_softc *sc);
174static int hda_rirb_start(struct hda_softc *sc);
175
176static void *hda_dma_get_vaddr(struct hda_softc *sc, uint64_t dma_paddr,
177    size_t len);
178static void hda_dma_st_dword(void *dma_vaddr, uint32_t data);
179static uint32_t hda_dma_ld_dword(void *dma_vaddr);
180
181static inline uint8_t hda_get_stream_by_offsets(uint32_t offset,
182    uint8_t reg_offset);
183static inline uint32_t hda_get_offset_stream(uint8_t stream_ind);
184
185static void hda_set_gctl(struct hda_softc *sc, uint32_t offset, uint32_t old);
186static void hda_set_statests(struct hda_softc *sc, uint32_t offset,
187    uint32_t old);
188static void hda_set_corbwp(struct hda_softc *sc, uint32_t offset, uint32_t old);
189static void hda_set_corbctl(struct hda_softc *sc, uint32_t offset,
190    uint32_t old);
191static void hda_set_rirbctl(struct hda_softc *sc, uint32_t offset,
192    uint32_t old);
193static void hda_set_rirbsts(struct hda_softc *sc, uint32_t offset,
194    uint32_t old);
195static void hda_set_dpiblbase(struct hda_softc *sc, uint32_t offset,
196    uint32_t old);
197static void hda_set_sdctl(struct hda_softc *sc, uint32_t offset, uint32_t old);
198static void hda_set_sdctl2(struct hda_softc *sc, uint32_t offset, uint32_t old);
199static void hda_set_sdsts(struct hda_softc *sc, uint32_t offset, uint32_t old);
200
201static int hda_signal_state_change(struct hda_codec_inst *hci);
202static int hda_response(struct hda_codec_inst *hci, uint32_t response,
203    uint8_t unsol);
204static int hda_transfer(struct hda_codec_inst *hci, uint8_t stream,
205    uint8_t dir, void *buf, size_t count);
206
207static void hda_set_pib(struct hda_softc *sc, uint8_t stream_ind, uint32_t pib);
208static uint64_t hda_get_clock_ns(void);
209
210/*
211 * PCI HDA function declarations
212 */
213static int pci_hda_init(struct vmctx *ctx, struct pci_devinst *pi, char *opts);
214static void pci_hda_write(struct vmctx *ctx, int vcpu, struct pci_devinst *pi,
215    int baridx, uint64_t offset, int size, uint64_t value);
216static uint64_t pci_hda_read(struct vmctx *ctx, int vcpu, struct pci_devinst *pi,
217    int baridx, uint64_t offset, int size);
218/*
219 * HDA global data
220 */
221
222static const hda_set_reg_handler hda_set_reg_table[] = {
223	[HDAC_GCTL] = hda_set_gctl,
224	[HDAC_STATESTS] = hda_set_statests,
225	[HDAC_CORBWP] = hda_set_corbwp,
226	[HDAC_CORBCTL] = hda_set_corbctl,
227	[HDAC_RIRBCTL] = hda_set_rirbctl,
228	[HDAC_RIRBSTS] = hda_set_rirbsts,
229	[HDAC_DPIBLBASE] = hda_set_dpiblbase,
230
231#define HDAC_ISTREAM(n, iss, oss)				\
232	[_HDAC_ISDCTL(n, iss, oss)] = hda_set_sdctl,		\
233	[_HDAC_ISDCTL(n, iss, oss) + 2] = hda_set_sdctl2,	\
234	[_HDAC_ISDSTS(n, iss, oss)] = hda_set_sdsts,		\
235
236#define HDAC_OSTREAM(n, iss, oss)				\
237	[_HDAC_OSDCTL(n, iss, oss)] = hda_set_sdctl,		\
238	[_HDAC_OSDCTL(n, iss, oss) + 2] = hda_set_sdctl2,	\
239	[_HDAC_OSDSTS(n, iss, oss)] = hda_set_sdsts,		\
240
241	HDAC_ISTREAM(0, HDA_ISS_NO, HDA_OSS_NO)
242	HDAC_ISTREAM(1, HDA_ISS_NO, HDA_OSS_NO)
243	HDAC_ISTREAM(2, HDA_ISS_NO, HDA_OSS_NO)
244	HDAC_ISTREAM(3, HDA_ISS_NO, HDA_OSS_NO)
245
246	HDAC_OSTREAM(0, HDA_ISS_NO, HDA_OSS_NO)
247	HDAC_OSTREAM(1, HDA_ISS_NO, HDA_OSS_NO)
248	HDAC_OSTREAM(2, HDA_ISS_NO, HDA_OSS_NO)
249	HDAC_OSTREAM(3, HDA_ISS_NO, HDA_OSS_NO)
250
251	[HDA_SET_REG_TABLE_SZ] = NULL,
252};
253
254static const uint16_t hda_corb_sizes[] = {
255	[HDAC_CORBSIZE_CORBSIZE_2]	= 2,
256	[HDAC_CORBSIZE_CORBSIZE_16]	= 16,
257	[HDAC_CORBSIZE_CORBSIZE_256]	= 256,
258	[HDAC_CORBSIZE_CORBSIZE_MASK]	= 0,
259};
260
261static const uint16_t hda_rirb_sizes[] = {
262	[HDAC_RIRBSIZE_RIRBSIZE_2]	= 2,
263	[HDAC_RIRBSIZE_RIRBSIZE_16]	= 16,
264	[HDAC_RIRBSIZE_RIRBSIZE_256]	= 256,
265	[HDAC_RIRBSIZE_RIRBSIZE_MASK]	= 0,
266};
267
268static struct hda_ops hops = {
269	.signal		= hda_signal_state_change,
270	.response	= hda_response,
271	.transfer	= hda_transfer,
272};
273
274struct pci_devemu pci_de_hda = {
275	.pe_emu		= "hda",
276	.pe_init	= pci_hda_init,
277	.pe_barwrite	= pci_hda_write,
278	.pe_barread	= pci_hda_read
279};
280
281PCI_EMUL_SET(pci_de_hda);
282
283SET_DECLARE(hda_codec_class_set, struct hda_codec_class);
284
285#if DEBUG_HDA == 1
286FILE *dbg;
287#endif
288
289/*
290 * HDA module function definitions
291 */
292
293static inline void
294hda_set_reg_by_offset(struct hda_softc *sc, uint32_t offset, uint32_t value)
295{
296	assert(offset < HDA_LAST_OFFSET);
297	sc->regs[offset] = value;
298}
299
300static inline uint32_t
301hda_get_reg_by_offset(struct hda_softc *sc, uint32_t offset)
302{
303	assert(offset < HDA_LAST_OFFSET);
304	return sc->regs[offset];
305}
306
307static inline void
308hda_set_field_by_offset(struct hda_softc *sc, uint32_t offset,
309    uint32_t mask, uint32_t value)
310{
311	uint32_t reg_value = 0;
312
313	reg_value = hda_get_reg_by_offset(sc, offset);
314
315	reg_value &= ~mask;
316	reg_value |= (value & mask);
317
318	hda_set_reg_by_offset(sc, offset, reg_value);
319}
320
321static uint8_t
322hda_parse_config(const char *opts, const char *key, char *val)
323{
324	char buf[64];
325	char *s = buf;
326	char *tmp = NULL;
327	size_t len;
328	int i;
329
330	if (!opts)
331		return (0);
332
333	len = strlen(opts);
334	if (len >= sizeof(buf)) {
335		DPRINTF("Opts too big");
336		return (0);
337	}
338
339	DPRINTF("opts: %s", opts);
340
341	strcpy(buf, opts);
342
343	for (i = 0; i < len; i++)
344		if (buf[i] == ',') {
345			buf[i] = 0;
346			tmp = buf + i + 1;
347			break;
348		}
349
350	if (!memcmp(s, key, strlen(key))) {
351		strncpy(val, s + strlen(key), 64);
352		return (1);
353	}
354
355	if (!tmp)
356		return (0);
357
358	s = tmp;
359	if (!memcmp(s, key, strlen(key))) {
360		strncpy(val, s + strlen(key), 64);
361		return (1);
362	}
363
364	return (0);
365}
366
367static struct hda_softc *
368hda_init(const char *opts)
369{
370	struct hda_softc *sc = NULL;
371	struct hda_codec_class *codec = NULL;
372	char play[64];
373	char rec[64];
374	int err, p, r;
375
376#if DEBUG_HDA == 1
377	dbg = fopen("/tmp/bhyve_hda.log", "w+");
378#endif
379
380	DPRINTF("opts: %s", opts);
381
382	sc = calloc(1, sizeof(*sc));
383	if (!sc)
384		return (NULL);
385
386	hda_reset_regs(sc);
387
388	/*
389	 * TODO search all the codecs declared in opts
390	 * For now we play with one single codec
391	 */
392	codec = hda_find_codec_class("hda_codec");
393	if (codec) {
394		p = hda_parse_config(opts, "play=", play);
395		r = hda_parse_config(opts, "rec=", rec);
396		DPRINTF("play: %s rec: %s", play, rec);
397		if (p | r) {
398			err = hda_codec_constructor(sc, codec, p ?	\
399				play : NULL, r ? rec : NULL, NULL);
400			assert(!err);
401		}
402	}
403
404	return (sc);
405}
406
407static void
408hda_update_intr(struct hda_softc *sc)
409{
410	struct pci_devinst *pi = sc->pci_dev;
411	uint32_t intctl = hda_get_reg_by_offset(sc, HDAC_INTCTL);
412	uint32_t intsts = 0;
413	uint32_t sdsts = 0;
414	uint32_t rirbsts = 0;
415	uint32_t wakeen = 0;
416	uint32_t statests = 0;
417	uint32_t off = 0;
418	int i;
419
420	/* update the CIS bits */
421	rirbsts = hda_get_reg_by_offset(sc, HDAC_RIRBSTS);
422	if (rirbsts & (HDAC_RIRBSTS_RINTFL | HDAC_RIRBSTS_RIRBOIS))
423		intsts |= HDAC_INTSTS_CIS;
424
425	wakeen = hda_get_reg_by_offset(sc, HDAC_WAKEEN);
426	statests = hda_get_reg_by_offset(sc, HDAC_STATESTS);
427	if (statests & wakeen)
428		intsts |= HDAC_INTSTS_CIS;
429
430	/* update the SIS bits */
431	for (i = 0; i < HDA_IOSS_NO; i++) {
432		off = hda_get_offset_stream(i);
433		sdsts = hda_get_reg_by_offset(sc, off + HDAC_SDSTS);
434		if (sdsts & HDAC_SDSTS_BCIS)
435			intsts |= (1 << i);
436	}
437
438	/* update the GIS bit */
439	if (intsts)
440		intsts |= HDAC_INTSTS_GIS;
441
442	hda_set_reg_by_offset(sc, HDAC_INTSTS, intsts);
443
444	if ((intctl & HDAC_INTCTL_GIE) && ((intsts &			\
445		~HDAC_INTSTS_GIS) & intctl)) {
446		if (!sc->lintr) {
447			pci_lintr_assert(pi);
448			sc->lintr = 1;
449		}
450	} else {
451		if (sc->lintr) {
452			pci_lintr_deassert(pi);
453			sc->lintr = 0;
454		}
455	}
456}
457
458static void
459hda_response_interrupt(struct hda_softc *sc)
460{
461	uint8_t rirbctl = hda_get_reg_by_offset(sc, HDAC_RIRBCTL);
462
463	if ((rirbctl & HDAC_RIRBCTL_RINTCTL) && sc->rirb_cnt) {
464		sc->rirb_cnt = 0;
465		hda_set_field_by_offset(sc, HDAC_RIRBSTS, HDAC_RIRBSTS_RINTFL,
466				HDAC_RIRBSTS_RINTFL);
467		hda_update_intr(sc);
468	}
469}
470
471static int
472hda_codec_constructor(struct hda_softc *sc, struct hda_codec_class *codec,
473    const char *play, const char *rec, const char *opts)
474{
475	struct hda_codec_inst *hci = NULL;
476
477	if (sc->codecs_no >= HDA_CODEC_MAX)
478		return (-1);
479
480	hci = calloc(1, sizeof(struct hda_codec_inst));
481	if (!hci)
482		return (-1);
483
484	hci->hda = sc;
485	hci->hops = &hops;
486	hci->cad = sc->codecs_no;
487	hci->codec = codec;
488
489	sc->codecs[sc->codecs_no++] = hci;
490
491	if (!codec->init) {
492		DPRINTF("This codec does not implement the init function");
493		return (-1);
494	}
495
496	return (codec->init(hci, play, rec, opts));
497}
498
499static struct hda_codec_class *
500hda_find_codec_class(const char *name)
501{
502	struct hda_codec_class **pdpp = NULL, *pdp = NULL;
503
504	SET_FOREACH(pdpp, hda_codec_class_set) {
505		pdp = *pdpp;
506		if (!strcmp(pdp->name, name)) {
507			return (pdp);
508		}
509	}
510
511	return (NULL);
512}
513
514static int
515hda_send_command(struct hda_softc *sc, uint32_t verb)
516{
517	struct hda_codec_inst *hci = NULL;
518	struct hda_codec_class *codec = NULL;
519	uint8_t cad = (verb >> HDA_CMD_CAD_SHIFT) & 0x0f;
520
521	hci = sc->codecs[cad];
522	if (!hci)
523		return (-1);
524
525	DPRINTF("cad: 0x%x verb: 0x%x", cad, verb);
526
527	codec = hci->codec;
528	assert(codec);
529
530	if (!codec->command) {
531		DPRINTF("This codec does not implement the command function");
532		return (-1);
533	}
534
535	return (codec->command(hci, verb));
536}
537
538static int
539hda_notify_codecs(struct hda_softc *sc, uint8_t run, uint8_t stream,
540    uint8_t dir)
541{
542	struct hda_codec_inst *hci = NULL;
543	struct hda_codec_class *codec = NULL;
544	int err;
545	int i;
546
547	/* Notify each codec */
548	for (i = 0; i < sc->codecs_no; i++) {
549		hci = sc->codecs[i];
550		assert(hci);
551
552		codec = hci->codec;
553		assert(codec);
554
555		if (codec->notify) {
556			err = codec->notify(hci, run, stream, dir);
557			if (!err)
558				break;
559		}
560	}
561
562	return (i == sc->codecs_no ? (-1) : 0);
563}
564
565static void
566hda_reset(struct hda_softc *sc)
567{
568	int i;
569	struct hda_codec_inst *hci = NULL;
570	struct hda_codec_class *codec = NULL;
571
572	hda_reset_regs(sc);
573
574	/* Reset each codec */
575	for (i = 0; i < sc->codecs_no; i++) {
576		hci = sc->codecs[i];
577		assert(hci);
578
579		codec = hci->codec;
580		assert(codec);
581
582		if (codec->reset)
583			codec->reset(hci);
584	}
585
586	sc->wall_clock_start = hda_get_clock_ns();
587}
588
589static void
590hda_reset_regs(struct hda_softc *sc)
591{
592	uint32_t off = 0;
593	uint8_t i;
594
595	DPRINTF("Reset the HDA controller registers ...");
596
597	memset(sc->regs, 0, sizeof(sc->regs));
598
599	hda_set_reg_by_offset(sc, HDAC_GCAP,
600			HDAC_GCAP_64OK |
601			(HDA_ISS_NO << HDAC_GCAP_ISS_SHIFT) |
602			(HDA_OSS_NO << HDAC_GCAP_OSS_SHIFT));
603	hda_set_reg_by_offset(sc, HDAC_VMAJ, 0x01);
604	hda_set_reg_by_offset(sc, HDAC_OUTPAY, 0x3c);
605	hda_set_reg_by_offset(sc, HDAC_INPAY, 0x1d);
606	hda_set_reg_by_offset(sc, HDAC_CORBSIZE,
607	    HDAC_CORBSIZE_CORBSZCAP_256 | HDAC_CORBSIZE_CORBSIZE_256);
608	hda_set_reg_by_offset(sc, HDAC_RIRBSIZE,
609	    HDAC_RIRBSIZE_RIRBSZCAP_256 | HDAC_RIRBSIZE_RIRBSIZE_256);
610
611	for (i = 0; i < HDA_IOSS_NO; i++) {
612		off = hda_get_offset_stream(i);
613		hda_set_reg_by_offset(sc, off + HDAC_SDFIFOS, HDA_FIFO_SIZE);
614	}
615}
616
617static void
618hda_stream_reset(struct hda_softc *sc, uint8_t stream_ind)
619{
620	struct hda_stream_desc *st = &sc->streams[stream_ind];
621	uint32_t off = hda_get_offset_stream(stream_ind);
622
623	DPRINTF("Reset the HDA stream: 0x%x", stream_ind);
624
625	/* Reset the Stream Descriptor registers */
626	memset(sc->regs + HDA_STREAM_REGS_BASE + off, 0, HDA_STREAM_REGS_LEN);
627
628	/* Reset the Stream Descriptor */
629	memset(st, 0, sizeof(*st));
630
631	hda_set_field_by_offset(sc, off + HDAC_SDSTS,
632	    HDAC_SDSTS_FIFORDY, HDAC_SDSTS_FIFORDY);
633	hda_set_field_by_offset(sc, off + HDAC_SDCTL0,
634	    HDAC_SDCTL_SRST, HDAC_SDCTL_SRST);
635}
636
637static int
638hda_stream_start(struct hda_softc *sc, uint8_t stream_ind)
639{
640	struct hda_stream_desc *st = &sc->streams[stream_ind];
641	struct hda_bdle_desc *bdle_desc = NULL;
642	struct hda_bdle *bdle = NULL;
643	uint32_t lvi = 0;
644	uint32_t bdl_cnt = 0;
645	uint64_t bdpl = 0;
646	uint64_t bdpu = 0;
647	uint64_t bdl_paddr = 0;
648	void *bdl_vaddr = NULL;
649	uint32_t bdle_sz = 0;
650	uint64_t bdle_addrl = 0;
651	uint64_t bdle_addrh = 0;
652	uint64_t bdle_paddr = 0;
653	void *bdle_vaddr = NULL;
654	uint32_t off = hda_get_offset_stream(stream_ind);
655	uint32_t sdctl = 0;
656	uint8_t strm = 0;
657	uint8_t dir = 0;
658	int i;
659
660	assert(!st->run);
661
662	lvi = hda_get_reg_by_offset(sc, off + HDAC_SDLVI);
663	bdpl = hda_get_reg_by_offset(sc, off + HDAC_SDBDPL);
664	bdpu = hda_get_reg_by_offset(sc, off + HDAC_SDBDPU);
665
666	bdl_cnt = lvi + 1;
667	assert(bdl_cnt <= HDA_BDL_MAX_LEN);
668
669	bdl_paddr = bdpl | (bdpu << 32);
670	bdl_vaddr = hda_dma_get_vaddr(sc, bdl_paddr,
671	    HDA_BDL_ENTRY_LEN * bdl_cnt);
672	if (!bdl_vaddr) {
673		DPRINTF("Fail to get the guest virtual address");
674		return (-1);
675	}
676
677	DPRINTF("stream: 0x%x bdl_cnt: 0x%x bdl_paddr: 0x%lx",
678	    stream_ind, bdl_cnt, bdl_paddr);
679
680	st->bdl_cnt = bdl_cnt;
681
682	bdle = (struct hda_bdle *)bdl_vaddr;
683	for (i = 0; i < bdl_cnt; i++, bdle++) {
684		bdle_sz = bdle->len;
685		assert(!(bdle_sz % HDA_DMA_ACCESS_LEN));
686
687		bdle_addrl = bdle->addrl;
688		bdle_addrh = bdle->addrh;
689
690		bdle_paddr = bdle_addrl | (bdle_addrh << 32);
691		bdle_vaddr = hda_dma_get_vaddr(sc, bdle_paddr, bdle_sz);
692		if (!bdle_vaddr) {
693			DPRINTF("Fail to get the guest virtual address");
694			return (-1);
695		}
696
697		bdle_desc = &st->bdl[i];
698		bdle_desc->addr = bdle_vaddr;
699		bdle_desc->len = bdle_sz;
700		bdle_desc->ioc = bdle->ioc;
701
702		DPRINTF("bdle: 0x%x bdle_sz: 0x%x", i, bdle_sz);
703	}
704
705	sdctl = hda_get_reg_by_offset(sc, off + HDAC_SDCTL0);
706	strm = (sdctl >> 20) & 0x0f;
707	dir = stream_ind >= HDA_ISS_NO;
708
709	DPRINTF("strm: 0x%x, dir: 0x%x", strm, dir);
710
711	sc->stream_map[dir][strm] = stream_ind;
712	st->stream = strm;
713	st->dir = dir;
714	st->bp = 0;
715	st->be = 0;
716
717	hda_set_pib(sc, stream_ind, 0);
718
719	st->run = 1;
720
721	hda_notify_codecs(sc, 1, strm, dir);
722
723	return (0);
724}
725
726static int
727hda_stream_stop(struct hda_softc *sc, uint8_t stream_ind)
728{
729	struct hda_stream_desc *st = &sc->streams[stream_ind];
730	uint8_t strm = st->stream;
731	uint8_t dir = st->dir;
732
733	DPRINTF("stream: 0x%x, strm: 0x%x, dir: 0x%x", stream_ind, strm, dir);
734
735	st->run = 0;
736
737	hda_notify_codecs(sc, 0, strm, dir);
738
739	return (0);
740}
741
742static uint32_t
743hda_read(struct hda_softc *sc, uint32_t offset)
744{
745	if (offset == HDAC_WALCLK)
746		return (24 * (hda_get_clock_ns() -			\
747			sc->wall_clock_start) / 1000);
748
749	return (hda_get_reg_by_offset(sc, offset));
750}
751
752static int
753hda_write(struct hda_softc *sc, uint32_t offset, uint8_t size, uint32_t value)
754{
755	uint32_t old = hda_get_reg_by_offset(sc, offset);
756	uint32_t masks[] = {0x00000000, 0x000000ff, 0x0000ffff,
757			0x00ffffff, 0xffffffff};
758	hda_set_reg_handler set_reg_handler = hda_set_reg_table[offset];
759
760	hda_set_field_by_offset(sc, offset, masks[size], value);
761
762	if (set_reg_handler)
763		set_reg_handler(sc, offset, old);
764
765	return (0);
766}
767
768static inline void
769hda_print_cmd_ctl_data(struct hda_codec_cmd_ctl *p)
770{
771#if DEBUG_HDA == 1
772	char *name = p->name;
773#endif
774	DPRINTF("%s size: %d", name, p->size);
775	DPRINTF("%s dma_vaddr: %p", name, p->dma_vaddr);
776	DPRINTF("%s wp: 0x%x", name, p->wp);
777	DPRINTF("%s rp: 0x%x", name, p->rp);
778}
779
780static int
781hda_corb_start(struct hda_softc *sc)
782{
783	struct hda_codec_cmd_ctl *corb = &sc->corb;
784	uint8_t corbsize = 0;
785	uint64_t corblbase = 0;
786	uint64_t corbubase = 0;
787	uint64_t corbpaddr = 0;
788
789	corb->name = "CORB";
790
791	corbsize = hda_get_reg_by_offset(sc, HDAC_CORBSIZE) &		\
792		   HDAC_CORBSIZE_CORBSIZE_MASK;
793	corb->size = hda_corb_sizes[corbsize];
794
795	if (!corb->size) {
796		DPRINTF("Invalid corb size");
797		return (-1);
798	}
799
800	corblbase = hda_get_reg_by_offset(sc, HDAC_CORBLBASE);
801	corbubase = hda_get_reg_by_offset(sc, HDAC_CORBUBASE);
802
803	corbpaddr = corblbase | (corbubase << 32);
804	DPRINTF("CORB dma_paddr: %p", (void *)corbpaddr);
805
806	corb->dma_vaddr = hda_dma_get_vaddr(sc, corbpaddr,
807			HDA_CORB_ENTRY_LEN * corb->size);
808	if (!corb->dma_vaddr) {
809		DPRINTF("Fail to get the guest virtual address");
810		return (-1);
811	}
812
813	corb->wp = hda_get_reg_by_offset(sc, HDAC_CORBWP);
814	corb->rp = hda_get_reg_by_offset(sc, HDAC_CORBRP);
815
816	corb->run = 1;
817
818	hda_print_cmd_ctl_data(corb);
819
820	return (0);
821}
822
823static int
824hda_corb_run(struct hda_softc *sc)
825{
826	struct hda_codec_cmd_ctl *corb = &sc->corb;
827	uint32_t verb = 0;
828	int err;
829
830	corb->wp = hda_get_reg_by_offset(sc, HDAC_CORBWP);
831
832	while (corb->rp != corb->wp && corb->run) {
833		corb->rp++;
834		corb->rp %= corb->size;
835
836		verb = hda_dma_ld_dword(corb->dma_vaddr +		\
837				HDA_CORB_ENTRY_LEN * corb->rp);
838
839		err = hda_send_command(sc, verb);
840		assert(!err);
841	}
842
843	hda_set_reg_by_offset(sc, HDAC_CORBRP, corb->rp);
844
845	if (corb->run)
846		hda_response_interrupt(sc);
847
848	return (0);
849}
850
851static int
852hda_rirb_start(struct hda_softc *sc)
853{
854	struct hda_codec_cmd_ctl *rirb = &sc->rirb;
855	uint8_t rirbsize = 0;
856	uint64_t rirblbase = 0;
857	uint64_t rirbubase = 0;
858	uint64_t rirbpaddr = 0;
859
860	rirb->name = "RIRB";
861
862	rirbsize = hda_get_reg_by_offset(sc, HDAC_RIRBSIZE) &		\
863		   HDAC_RIRBSIZE_RIRBSIZE_MASK;
864	rirb->size = hda_rirb_sizes[rirbsize];
865
866	if (!rirb->size) {
867		DPRINTF("Invalid rirb size");
868		return (-1);
869	}
870
871	rirblbase = hda_get_reg_by_offset(sc, HDAC_RIRBLBASE);
872	rirbubase = hda_get_reg_by_offset(sc, HDAC_RIRBUBASE);
873
874	rirbpaddr = rirblbase | (rirbubase << 32);
875	DPRINTF("RIRB dma_paddr: %p", (void *)rirbpaddr);
876
877	rirb->dma_vaddr = hda_dma_get_vaddr(sc, rirbpaddr,
878			HDA_RIRB_ENTRY_LEN * rirb->size);
879	if (!rirb->dma_vaddr) {
880		DPRINTF("Fail to get the guest virtual address");
881		return (-1);
882	}
883
884	rirb->wp = hda_get_reg_by_offset(sc, HDAC_RIRBWP);
885	rirb->rp = 0x0000;
886
887	rirb->run = 1;
888
889	hda_print_cmd_ctl_data(rirb);
890
891	return (0);
892}
893
894static void *
895hda_dma_get_vaddr(struct hda_softc *sc, uint64_t dma_paddr, size_t len)
896{
897	struct pci_devinst *pi = sc->pci_dev;
898
899	assert(pi);
900
901	return (paddr_guest2host(pi->pi_vmctx, (uintptr_t)dma_paddr, len));
902}
903
904static void
905hda_dma_st_dword(void *dma_vaddr, uint32_t data)
906{
907	*(uint32_t*)dma_vaddr = data;
908}
909
910static uint32_t
911hda_dma_ld_dword(void *dma_vaddr)
912{
913	return (*(uint32_t*)dma_vaddr);
914}
915
916static inline uint8_t
917hda_get_stream_by_offsets(uint32_t offset, uint8_t reg_offset)
918{
919	uint8_t stream_ind = (offset - reg_offset) >> 5;
920
921	assert(stream_ind < HDA_IOSS_NO);
922
923	return (stream_ind);
924}
925
926static inline uint32_t
927hda_get_offset_stream(uint8_t stream_ind)
928{
929	return (stream_ind << 5);
930}
931
932static void
933hda_set_gctl(struct hda_softc *sc, uint32_t offset, uint32_t old)
934{
935	uint32_t value = hda_get_reg_by_offset(sc, offset);
936
937	if (!(value & HDAC_GCTL_CRST)) {
938		hda_reset(sc);
939	}
940}
941
942static void
943hda_set_statests(struct hda_softc *sc, uint32_t offset, uint32_t old)
944{
945	uint32_t value = hda_get_reg_by_offset(sc, offset);
946
947	hda_set_reg_by_offset(sc, offset, old);
948
949	/* clear the corresponding bits written by the software (guest) */
950	hda_set_field_by_offset(sc, offset, value & HDA_STATESTS_IRQ_MASK, 0);
951
952	hda_update_intr(sc);
953}
954
955static void
956hda_set_corbwp(struct hda_softc *sc, uint32_t offset, uint32_t old)
957{
958	hda_corb_run(sc);
959}
960
961static void
962hda_set_corbctl(struct hda_softc *sc, uint32_t offset, uint32_t old)
963{
964	uint32_t value = hda_get_reg_by_offset(sc, offset);
965	int err;
966	struct hda_codec_cmd_ctl *corb = NULL;
967
968	if (value & HDAC_CORBCTL_CORBRUN) {
969		if (!(old & HDAC_CORBCTL_CORBRUN)) {
970			err = hda_corb_start(sc);
971			assert(!err);
972		}
973	} else {
974		corb = &sc->corb;
975		memset(corb, 0, sizeof(*corb));
976	}
977
978	hda_corb_run(sc);
979}
980
981static void
982hda_set_rirbctl(struct hda_softc *sc, uint32_t offset, uint32_t old)
983{
984	uint32_t value = hda_get_reg_by_offset(sc, offset);
985	int err;
986	struct hda_codec_cmd_ctl *rirb = NULL;
987
988	if (value & HDAC_RIRBCTL_RIRBDMAEN) {
989		err = hda_rirb_start(sc);
990		assert(!err);
991	} else {
992		rirb = &sc->rirb;
993		memset(rirb, 0, sizeof(*rirb));
994	}
995}
996
997static void
998hda_set_rirbsts(struct hda_softc *sc, uint32_t offset, uint32_t old)
999{
1000	uint32_t value = hda_get_reg_by_offset(sc, offset);
1001
1002	hda_set_reg_by_offset(sc, offset, old);
1003
1004	/* clear the corresponding bits written by the software (guest) */
1005	hda_set_field_by_offset(sc, offset, value & HDA_RIRBSTS_IRQ_MASK, 0);
1006
1007	hda_update_intr(sc);
1008}
1009
1010static void
1011hda_set_dpiblbase(struct hda_softc *sc, uint32_t offset, uint32_t old)
1012{
1013	uint32_t value = hda_get_reg_by_offset(sc, offset);
1014	uint64_t dpiblbase = 0;
1015	uint64_t dpibubase = 0;
1016	uint64_t dpibpaddr = 0;
1017
1018	if ((value & HDAC_DPLBASE_DPLBASE_DMAPBE) != (old &		\
1019				HDAC_DPLBASE_DPLBASE_DMAPBE)) {
1020		if (value & HDAC_DPLBASE_DPLBASE_DMAPBE) {
1021			dpiblbase = value & HDAC_DPLBASE_DPLBASE_MASK;
1022			dpibubase = hda_get_reg_by_offset(sc, HDAC_DPIBUBASE);
1023
1024			dpibpaddr = dpiblbase | (dpibubase << 32);
1025			DPRINTF("DMA Position In Buffer dma_paddr: %p",
1026			    (void *)dpibpaddr);
1027
1028			sc->dma_pib_vaddr = hda_dma_get_vaddr(sc, dpibpaddr,
1029					HDA_DMA_PIB_ENTRY_LEN * HDA_IOSS_NO);
1030			if (!sc->dma_pib_vaddr) {
1031				DPRINTF("Fail to get the guest \
1032					 virtual address");
1033				assert(0);
1034			}
1035		} else {
1036			DPRINTF("DMA Position In Buffer Reset");
1037			sc->dma_pib_vaddr = NULL;
1038		}
1039	}
1040}
1041
1042static void
1043hda_set_sdctl(struct hda_softc *sc, uint32_t offset, uint32_t old)
1044{
1045	uint8_t stream_ind = hda_get_stream_by_offsets(offset, HDAC_SDCTL0);
1046	uint32_t value = hda_get_reg_by_offset(sc, offset);
1047	int err;
1048
1049	DPRINTF("stream_ind: 0x%x old: 0x%x value: 0x%x",
1050	    stream_ind, old, value);
1051
1052	if (value & HDAC_SDCTL_SRST) {
1053		hda_stream_reset(sc, stream_ind);
1054	}
1055
1056	if ((value & HDAC_SDCTL_RUN) != (old & HDAC_SDCTL_RUN)) {
1057		if (value & HDAC_SDCTL_RUN) {
1058			err = hda_stream_start(sc, stream_ind);
1059			assert(!err);
1060		} else {
1061			err = hda_stream_stop(sc, stream_ind);
1062			assert(!err);
1063		}
1064	}
1065}
1066
1067static void
1068hda_set_sdctl2(struct hda_softc *sc, uint32_t offset, uint32_t old)
1069{
1070	uint32_t value = hda_get_reg_by_offset(sc, offset);
1071
1072	hda_set_field_by_offset(sc, offset - 2, 0x00ff0000, value << 16);
1073}
1074
1075static void
1076hda_set_sdsts(struct hda_softc *sc, uint32_t offset, uint32_t old)
1077{
1078	uint32_t value = hda_get_reg_by_offset(sc, offset);
1079
1080	hda_set_reg_by_offset(sc, offset, old);
1081
1082	/* clear the corresponding bits written by the software (guest) */
1083	hda_set_field_by_offset(sc, offset, value & HDA_SDSTS_IRQ_MASK, 0);
1084
1085	hda_update_intr(sc);
1086}
1087
1088static int
1089hda_signal_state_change(struct hda_codec_inst *hci)
1090{
1091	struct hda_softc *sc = NULL;
1092	uint32_t sdiwake = 0;
1093
1094	assert(hci);
1095	assert(hci->hda);
1096
1097	DPRINTF("cad: 0x%x", hci->cad);
1098
1099	sc = hci->hda;
1100	sdiwake = 1 << hci->cad;
1101
1102	hda_set_field_by_offset(sc, HDAC_STATESTS, sdiwake, sdiwake);
1103	hda_update_intr(sc);
1104
1105	return (0);
1106}
1107
1108static int
1109hda_response(struct hda_codec_inst *hci, uint32_t response, uint8_t unsol)
1110{
1111	struct hda_softc *sc = NULL;
1112	struct hda_codec_cmd_ctl *rirb = NULL;
1113	uint32_t response_ex = 0;
1114	uint8_t rintcnt = 0;
1115
1116	assert(hci);
1117	assert(hci->cad <= HDA_CODEC_MAX);
1118
1119	response_ex = hci->cad | unsol;
1120
1121	sc = hci->hda;
1122	assert(sc);
1123
1124	rirb = &sc->rirb;
1125
1126	if (rirb->run) {
1127		rirb->wp++;
1128		rirb->wp %= rirb->size;
1129
1130		hda_dma_st_dword(rirb->dma_vaddr + HDA_RIRB_ENTRY_LEN *	\
1131				rirb->wp, response);
1132		hda_dma_st_dword(rirb->dma_vaddr + HDA_RIRB_ENTRY_LEN *	\
1133				rirb->wp + 0x04, response_ex);
1134
1135		hda_set_reg_by_offset(sc, HDAC_RIRBWP, rirb->wp);
1136
1137		sc->rirb_cnt++;
1138	}
1139
1140	rintcnt = hda_get_reg_by_offset(sc, HDAC_RINTCNT);
1141	if (sc->rirb_cnt == rintcnt)
1142		hda_response_interrupt(sc);
1143
1144	return (0);
1145}
1146
1147static int
1148hda_transfer(struct hda_codec_inst *hci, uint8_t stream, uint8_t dir,
1149    void *buf, size_t count)
1150{
1151	struct hda_softc *sc = NULL;
1152	struct hda_stream_desc *st = NULL;
1153	struct hda_bdle_desc *bdl = NULL;
1154	struct hda_bdle_desc *bdle_desc = NULL;
1155	uint8_t stream_ind = 0;
1156	uint32_t lpib = 0;
1157	uint32_t off = 0;
1158	size_t left = 0;
1159	uint8_t irq = 0;
1160
1161	assert(hci);
1162	assert(hci->hda);
1163	assert(buf);
1164	assert(!(count % HDA_DMA_ACCESS_LEN));
1165
1166	if (!stream) {
1167		DPRINTF("Invalid stream");
1168		return (-1);
1169	}
1170
1171	sc = hci->hda;
1172
1173	assert(stream < HDA_STREAM_TAGS_CNT);
1174	stream_ind = sc->stream_map[dir][stream];
1175
1176	if (!dir)
1177		assert(stream_ind < HDA_ISS_NO);
1178	else
1179		assert(stream_ind >= HDA_ISS_NO && stream_ind < HDA_IOSS_NO);
1180
1181	st = &sc->streams[stream_ind];
1182	if (!st->run) {
1183		DPRINTF("Stream 0x%x stopped", stream);
1184		return (-1);
1185	}
1186
1187	assert(st->stream == stream);
1188
1189	off = hda_get_offset_stream(stream_ind);
1190
1191	lpib = hda_get_reg_by_offset(sc, off + HDAC_SDLPIB);
1192
1193	bdl = st->bdl;
1194
1195	assert(st->be < st->bdl_cnt);
1196	assert(st->bp < bdl[st->be].len);
1197
1198	left = count;
1199	while (left) {
1200		bdle_desc = &bdl[st->be];
1201
1202		if (dir)
1203			*(uint32_t *)buf =				\
1204			    hda_dma_ld_dword(bdle_desc->addr + st->bp);
1205		else
1206			hda_dma_st_dword(bdle_desc->addr + st->bp,
1207					*(uint32_t *)buf);
1208
1209		buf += HDA_DMA_ACCESS_LEN;
1210		st->bp += HDA_DMA_ACCESS_LEN;
1211		lpib += HDA_DMA_ACCESS_LEN;
1212		left -= HDA_DMA_ACCESS_LEN;
1213
1214		if (st->bp == bdle_desc->len) {
1215			st->bp = 0;
1216			if (bdle_desc->ioc)
1217				irq = 1;
1218			st->be++;
1219			if (st->be == st->bdl_cnt) {
1220				st->be = 0;
1221				lpib = 0;
1222			}
1223			bdle_desc = &bdl[st->be];
1224		}
1225	}
1226
1227	hda_set_pib(sc, stream_ind, lpib);
1228
1229	if (irq) {
1230		hda_set_field_by_offset(sc, off + HDAC_SDSTS,
1231				HDAC_SDSTS_BCIS, HDAC_SDSTS_BCIS);
1232		hda_update_intr(sc);
1233	}
1234
1235	return (0);
1236}
1237
1238static void
1239hda_set_pib(struct hda_softc *sc, uint8_t stream_ind, uint32_t pib)
1240{
1241	uint32_t off = hda_get_offset_stream(stream_ind);
1242
1243	hda_set_reg_by_offset(sc, off + HDAC_SDLPIB, pib);
1244	/* LPIB Alias */
1245	hda_set_reg_by_offset(sc, 0x2000 + off + HDAC_SDLPIB, pib);
1246	if (sc->dma_pib_vaddr)
1247		*(uint32_t *)(sc->dma_pib_vaddr + stream_ind *	\
1248				HDA_DMA_PIB_ENTRY_LEN) = pib;
1249}
1250
1251static uint64_t hda_get_clock_ns(void)
1252{
1253	struct timespec ts;
1254	int err;
1255
1256	err = clock_gettime(CLOCK_MONOTONIC, &ts);
1257	assert(!err);
1258
1259	return (ts.tv_sec * 1000000000LL + ts.tv_nsec);
1260}
1261
1262/*
1263 * PCI HDA function definitions
1264 */
1265static int
1266pci_hda_init(struct vmctx *ctx, struct pci_devinst *pi, char *opts)
1267{
1268	struct hda_softc *sc = NULL;
1269
1270	assert(ctx != NULL);
1271	assert(pi != NULL);
1272
1273	pci_set_cfgdata16(pi, PCIR_VENDOR, INTEL_VENDORID);
1274	pci_set_cfgdata16(pi, PCIR_DEVICE, HDA_INTEL_82801G);
1275
1276	pci_set_cfgdata8(pi, PCIR_SUBCLASS, PCIS_MULTIMEDIA_HDA);
1277	pci_set_cfgdata8(pi, PCIR_CLASS, PCIC_MULTIMEDIA);
1278
1279	/* select the Intel HDA mode */
1280	pci_set_cfgdata8(pi, PCIR_HDCTL, 0x01);
1281
1282	/* allocate one BAR register for the Memory address offsets */
1283	pci_emul_alloc_bar(pi, 0, PCIBAR_MEM32, HDA_LAST_OFFSET);
1284
1285	/* allocate an IRQ pin for our slot */
1286	pci_lintr_request(pi);
1287
1288	sc = hda_init(opts);
1289	if (!sc)
1290		return (-1);
1291
1292	sc->pci_dev = pi;
1293	pi->pi_arg = sc;
1294
1295	return (0);
1296}
1297
1298static void
1299pci_hda_write(struct vmctx *ctx, int vcpu, struct pci_devinst *pi,
1300    int baridx, uint64_t offset, int size, uint64_t value)
1301{
1302	struct hda_softc *sc = pi->pi_arg;
1303	int err;
1304
1305	assert(sc);
1306	assert(baridx == 0);
1307	assert(size <= 4);
1308
1309	DPRINTF("offset: 0x%lx value: 0x%lx", offset, value);
1310
1311	err = hda_write(sc, offset, size, value);
1312	assert(!err);
1313}
1314
1315static uint64_t
1316pci_hda_read(struct vmctx *ctx, int vcpu, struct pci_devinst *pi,
1317    int baridx, uint64_t offset, int size)
1318{
1319	struct hda_softc *sc = pi->pi_arg;
1320	uint64_t value = 0;
1321
1322	assert(sc);
1323	assert(baridx == 0);
1324	assert(size <= 4);
1325
1326	value = hda_read(sc, offset);
1327
1328	DPRINTF("offset: 0x%lx value: 0x%lx", offset, value);
1329
1330	return (value);
1331}
1332