dbri.c revision 1.36 1 /* $NetBSD: dbri.c,v 1.36 2017/12/08 07:47:00 mrg Exp $ */
2
3 /*
4 * Copyright (C) 1997 Rudolf Koenig (rfkoenig (at) immd4.informatik.uni-erlangen.de)
5 * Copyright (c) 1998, 1999 Brent Baccala (baccala (at) freesoft.org)
6 * Copyright (c) 2001, 2002 Jared D. McNeill <jmcneill (at) netbsd.org>
7 * Copyright (c) 2005 Michael Lorenz <macallan (at) netbsd.org>
8 * All rights reserved.
9 *
10 * This driver is losely based on a Linux driver written by Rudolf Koenig and
11 * Brent Baccala who kindly gave their permission to use their code in a
12 * BSD-licensed driver.
13 *
14 * Redistribution and use in source and binary forms, with or without
15 * modification, are permitted provided that the following conditions
16 * are met:
17 * 1. Redistributions of source code must retain the above copyright
18 * notice, this list of conditions and the following disclaimer.
19 * 2. Redistributions in binary form must reproduce the above copyright
20 * notice, this list of conditions and the following disclaimer in the
21 * documentation and/or other materials provided with the distribution.
22 *
23 * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
24 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
25 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
26 * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT,
27 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
28 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
29 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
32 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33 *
34 */
35
36 #include <sys/cdefs.h>
37 __KERNEL_RCSID(0, "$NetBSD: dbri.c,v 1.36 2017/12/08 07:47:00 mrg Exp $");
38
39 #include "audio.h"
40 #if NAUDIO > 0
41
42 #include <sys/param.h>
43 #include <sys/systm.h>
44 #include <sys/errno.h>
45 #include <sys/device.h>
46 #include <sys/proc.h>
47 #include <sys/kernel.h>
48 #include <sys/bus.h>
49 #include <sys/intr.h>
50 #include <sys/kmem.h>
51
52 #include <dev/sbus/sbusvar.h>
53 #include <sparc/sparc/auxreg.h>
54 #include <machine/autoconf.h>
55
56 #include <sys/audioio.h>
57 #include <dev/audio_if.h>
58 #include <dev/auconv.h>
59
60 #include <dev/ic/cs4215reg.h>
61 #include <dev/ic/cs4215var.h>
62 #include <dev/sbus/dbrireg.h>
63 #include <dev/sbus/dbrivar.h>
64
65 #include "opt_sbus_dbri.h"
66
67 #define DBRI_ROM_NAME_PREFIX "SUNW,DBRI"
68
69 #ifdef DBRI_DEBUG
70 # define DPRINTF aprint_normal
71 #else
72 # define DPRINTF while (0) printf
73 #endif
74
75 static const char *dbri_supported[] = {
76 "e",
77 "s3",
78 ""
79 };
80
81 enum ms {
82 CHImaster,
83 CHIslave
84 };
85
86 enum io {
87 PIPEinput,
88 PIPEoutput
89 };
90
91 /*
92 * Function prototypes
93 */
94
95 /* softc stuff */
96 static void dbri_attach_sbus(device_t, device_t, void *);
97 static int dbri_match_sbus(device_t, cfdata_t, void *);
98
99 static int dbri_config_interrupts(device_t);
100
101 /* interrupt handler */
102 static int dbri_intr(void *);
103 static void dbri_softint(void *);
104
105 /* supporting subroutines */
106 static int dbri_init(struct dbri_softc *);
107 static int dbri_reset(struct dbri_softc *);
108 static volatile uint32_t *dbri_command_lock(struct dbri_softc *);
109 static void dbri_command_send(struct dbri_softc *, volatile uint32_t *);
110 static void dbri_process_interrupt_buffer(struct dbri_softc *);
111 static void dbri_process_interrupt(struct dbri_softc *, int32_t);
112
113 /* mmcodec subroutines */
114 static int mmcodec_init(struct dbri_softc *);
115 static void mmcodec_init_data(struct dbri_softc *);
116 static void mmcodec_pipe_init(struct dbri_softc *);
117 static void mmcodec_default(struct dbri_softc *);
118 static void mmcodec_setgain(struct dbri_softc *, int);
119 static int mmcodec_setcontrol(struct dbri_softc *);
120
121 /* chi subroutines */
122 static void chi_reset(struct dbri_softc *, enum ms, int);
123
124 /* pipe subroutines */
125 static void pipe_setup(struct dbri_softc *, int, int);
126 static void pipe_reset(struct dbri_softc *, int);
127 static void pipe_receive_fixed(struct dbri_softc *, int,
128 volatile uint32_t *);
129 static void pipe_transmit_fixed(struct dbri_softc *, int, uint32_t);
130
131 static void pipe_ts_link(struct dbri_softc *, int, enum io, int, int, int);
132 static int pipe_active(struct dbri_softc *, int);
133
134 /* audio(9) stuff */
135 static int dbri_query_encoding(void *, struct audio_encoding *);
136 static int dbri_set_params(void *, int, int, struct audio_params *,
137 struct audio_params *,stream_filter_list_t *, stream_filter_list_t *);
138 static int dbri_round_blocksize(void *, int, int, const audio_params_t *);
139 static int dbri_halt_output(void *);
140 static int dbri_halt_input(void *);
141 static int dbri_getdev(void *, struct audio_device *);
142 static int dbri_set_port(void *, mixer_ctrl_t *);
143 static int dbri_get_port(void *, mixer_ctrl_t *);
144 static int dbri_query_devinfo(void *, mixer_devinfo_t *);
145 static size_t dbri_round_buffersize(void *, int, size_t);
146 static int dbri_get_props(void *);
147 static int dbri_open(void *, int);
148 static void dbri_close(void *);
149
150 static void setup_ring_xmit(struct dbri_softc *, int, int, int, int,
151 void (*)(void *), void *);
152 static void setup_ring_recv(struct dbri_softc *, int, int, int, int,
153 void (*)(void *), void *);
154
155 static int dbri_trigger_output(void *, void *, void *, int,
156 void (*)(void *), void *, const struct audio_params *);
157 static int dbri_trigger_input(void *, void *, void *, int,
158 void (*)(void *), void *, const struct audio_params *);
159 static void dbri_get_locks(void *, kmutex_t **, kmutex_t **);
160
161 static void *dbri_malloc(void *, int, size_t);
162 static void dbri_free(void *, void *, size_t);
163 static paddr_t dbri_mappage(void *, void *, off_t, int);
164 static void dbri_set_power(struct dbri_softc *, int);
165 static void dbri_bring_up(struct dbri_softc *);
166 static bool dbri_suspend(device_t, const pmf_qual_t *);
167 static bool dbri_resume(device_t, const pmf_qual_t *);
168
169 /* stupid support routines */
170 static uint32_t reverse_bytes(uint32_t, int);
171
172 struct audio_device dbri_device = {
173 "CS4215",
174 "",
175 "dbri"
176 };
177
178 struct audio_hw_if dbri_hw_if = {
179 .open = dbri_open,
180 .close = dbri_close,
181 .query_encoding = dbri_query_encoding,
182 .set_params = dbri_set_params,
183 .round_blocksize = dbri_round_blocksize,
184 .halt_output = dbri_halt_output,
185 .halt_input = dbri_halt_input,
186 .getdev = dbri_getdev,
187 .set_port = dbri_set_port,
188 .get_port = dbri_get_port,
189 .query_devinfo = dbri_query_devinfo,
190 .allocm = dbri_malloc,
191 .freem = dbri_free,
192 .round_buffersize = dbri_round_buffersize,
193 .mappage = dbri_mappage,
194 .get_props = dbri_get_props,
195 .trigger_output = dbri_trigger_output,
196 .trigger_input = dbri_trigger_input,
197 .get_locks = dbri_get_locks,
198 };
199
200 CFATTACH_DECL_NEW(dbri, sizeof(struct dbri_softc),
201 dbri_match_sbus, dbri_attach_sbus, NULL, NULL);
202
203 #define DBRI_NFORMATS 4
204 static const struct audio_format dbri_formats[DBRI_NFORMATS] = {
205 {NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_SLINEAR_BE, 16, 16,
206 2, AUFMT_STEREO, 8, {8000, 9600, 11025, 16000, 22050, 32000, 44100,
207 48000}},
208 /* {NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_ULAW, 8, 8,
209 2, AUFMT_STEREO, 8, {8000, 9600, 11025, 16000, 22050, 32000, 44100,
210 48000}},
211 {NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_ALAW, 8, 8,
212 2, AUFMT_STEREO, 8, {8000, 9600, 11025, 16000, 22050, 32000, 44100,
213 48000}},
214 {NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_ULINEAR, 8, 8,
215 2, AUFMT_STEREO, 8, {8000, 9600, 11025, 16000, 22050, 32000, 44100,
216 48000}},*/
217 {NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_ULAW, 8, 8,
218 1, AUFMT_MONAURAL, 8, {8000, 9600, 11025, 16000, 22050, 32000, 44100,
219 48000}},
220 {NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_ALAW, 8, 8,
221 1, AUFMT_MONAURAL, 8, {8000, 9600, 11025, 16000, 22050, 32000, 44100,
222 48000}},
223 {NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_ULINEAR, 8, 8,
224 1, AUFMT_MONAURAL, 8, {8000, 9600, 11025, 16000, 22050, 32000, 44100,
225 48000}},
226 };
227
228 enum {
229 DBRI_OUTPUT_CLASS,
230 DBRI_VOL_OUTPUT,
231 DBRI_ENABLE_MONO,
232 DBRI_ENABLE_HEADPHONE,
233 DBRI_ENABLE_LINE,
234 DBRI_MONITOR_CLASS,
235 DBRI_VOL_MONITOR,
236 DBRI_INPUT_CLASS,
237 DBRI_INPUT_GAIN,
238 DBRI_INPUT_SELECT,
239 DBRI_RECORD_CLASS,
240 DBRI_ENUM_LAST
241 };
242
243 /*
244 * Autoconfig routines
245 */
246 static int
247 dbri_match_sbus(device_t parent, cfdata_t match, void *aux)
248 {
249 struct sbus_attach_args *sa = aux;
250 char *ver;
251 int i;
252
253 if (strncmp(DBRI_ROM_NAME_PREFIX, sa->sa_name, 9))
254 return (0);
255
256 ver = &sa->sa_name[9];
257
258 for (i = 0; dbri_supported[i][0] != '\0'; i++)
259 if (strcmp(dbri_supported[i], ver) == 0)
260 return (1);
261
262 return (0);
263 }
264
265 static void
266 dbri_attach_sbus(device_t parent, device_t self, void *aux)
267 {
268 struct dbri_softc *sc = device_private(self);
269 struct sbus_attach_args *sa = aux;
270 bus_space_handle_t ioh;
271 bus_size_t size;
272 int error, rseg, pwr, i;
273 char *ver = &sa->sa_name[9];
274
275 sc->sc_dev = self;
276 sc->sc_iot = sa->sa_bustag;
277 sc->sc_dmat = sa->sa_dmatag;
278 sc->sc_powerstate = 1;
279
280 pwr = prom_getpropint(sa->sa_node,"pwr-on-auxio",0);
281 aprint_normal(": rev %s\n", ver);
282
283 if (pwr) {
284 /*
285 * we can control DBRI power via auxio and we're initially
286 * powered down
287 */
288
289 sc->sc_have_powerctl = 1;
290 sc->sc_powerstate = 0;
291 dbri_set_power(sc, 1);
292 if (!pmf_device_register(self, dbri_suspend, dbri_resume)) {
293 aprint_error_dev(self,
294 "cannot set power mgmt handler\n");
295 }
296 } else {
297 /* we can't control power so we're always up */
298 sc->sc_have_powerctl = 0;
299 sc->sc_powerstate = 1;
300 }
301
302 for (i = 0; i < DBRI_NUM_DESCRIPTORS; i++) {
303 sc->sc_desc[i].softint = softint_establish(SOFTINT_SERIAL,
304 dbri_softint, &sc->sc_desc[i]);
305 }
306
307 if (sa->sa_npromvaddrs)
308 ioh = (bus_space_handle_t)sa->sa_promvaddrs[0];
309 else {
310 if (sbus_bus_map(sa->sa_bustag, sa->sa_slot,
311 sa->sa_offset, sa->sa_size,
312 BUS_SPACE_MAP_LINEAR, /*0,*/ &ioh) != 0) {
313 aprint_error("%s @ sbus: cannot map registers\n",
314 device_xname(self));
315 return;
316 }
317 }
318
319 sc->sc_ioh = ioh;
320
321 size = sizeof(struct dbri_dma);
322
323 /* get a DMA handle */
324 if ((error = bus_dmamap_create(sc->sc_dmat, size, 1, size, 0,
325 BUS_DMA_NOWAIT, &sc->sc_dmamap)) != 0) {
326 aprint_error_dev(self, "DMA map create error %d\n",
327 error);
328 return;
329 }
330
331 /* allocate DMA buffer */
332 if ((error = bus_dmamem_alloc(sc->sc_dmat, size, 0, 0, &sc->sc_dmaseg,
333 1, &rseg, BUS_DMA_NOWAIT)) != 0) {
334 aprint_error_dev(self, "DMA buffer alloc error %d\n",
335 error);
336 return;
337 }
338
339 /* map DMA buffer into CPU addressable space */
340 if ((error = bus_dmamem_map(sc->sc_dmat, &sc->sc_dmaseg, rseg, size,
341 &sc->sc_membase,
342 BUS_DMA_NOWAIT|BUS_DMA_COHERENT)) != 0) {
343 aprint_error_dev(self, "DMA buffer map error %d\n",
344 error);
345 return;
346 }
347
348 /* load the buffer */
349 if ((error = bus_dmamap_load(sc->sc_dmat, sc->sc_dmamap,
350 sc->sc_membase, size, NULL,
351 BUS_DMA_NOWAIT)) != 0) {
352 aprint_error_dev(self, "DMA buffer map load error %d\n",
353 error);
354 bus_dmamem_unmap(sc->sc_dmat, sc->sc_membase, size);
355 bus_dmamem_free(sc->sc_dmat, &sc->sc_dmaseg, rseg);
356 return;
357 }
358
359 /* map the registers into memory */
360
361 /* kernel virtual address of DMA buffer */
362 sc->sc_dma = (struct dbri_dma *)sc->sc_membase;
363 /* physical address of DMA buffer */
364 sc->sc_dmabase = sc->sc_dmamap->dm_segs[0].ds_addr;
365 sc->sc_bufsiz = size;
366
367 mutex_init(&sc->sc_lock, MUTEX_DEFAULT, IPL_NONE);
368 mutex_init(&sc->sc_intr_lock, MUTEX_DEFAULT, IPL_SCHED);
369
370 #ifndef DBRI_SPIN
371 cv_init(&sc->sc_cv, "dbricv");
372 #endif
373
374 bus_intr_establish(sa->sa_bustag, sa->sa_pri, IPL_SCHED, dbri_intr,
375 sc);
376
377 sc->sc_locked = 0;
378 sc->sc_desc_used = 0;
379 sc->sc_refcount = 0;
380 sc->sc_playing = 0;
381 sc->sc_recording = 0;
382 sc->sc_init_done = 0;
383 config_finalize_register(self, &dbri_config_interrupts);
384
385 return;
386 }
387
388 /*
389 * lowlevel routine to switch power for the DBRI chip
390 */
391 static void
392 dbri_set_power(struct dbri_softc *sc, int state)
393 {
394 int s;
395
396 if (sc->sc_have_powerctl == 0)
397 return;
398 if (sc->sc_powerstate == state)
399 return;
400
401 if (state) {
402 DPRINTF("%s: waiting to power up... ",
403 device_xname(sc->sc_dev));
404 s = splhigh();
405 *AUXIO4M_REG |= (AUXIO4M_MMX);
406 splx(s);
407 delay(10000);
408 DPRINTF("done (%02x)\n", *AUXIO4M_REG);
409 } else {
410 DPRINTF("%s: powering down\n", device_xname(sc->sc_dev));
411 s = splhigh();
412 *AUXIO4M_REG &= ~AUXIO4M_MMX;
413 splx(s);
414 DPRINTF("done (%02x})\n", *AUXIO4M_REG);
415 }
416 sc->sc_powerstate = state;
417 }
418
419 /*
420 * power up and re-initialize the chip
421 */
422 static void
423 dbri_bring_up(struct dbri_softc *sc)
424 {
425
426 if (sc->sc_have_powerctl == 0)
427 return;
428
429 if (sc->sc_powerstate == 1)
430 return;
431
432 /* ok, we really need to do something */
433 dbri_set_power(sc, 1);
434
435 /*
436 * re-initialize the chip but skip all the probing, don't overwrite
437 * any other settings either
438 */
439 dbri_init(sc);
440 mmcodec_setgain(sc, 1);
441 mmcodec_pipe_init(sc);
442 mmcodec_init_data(sc);
443 mmcodec_setgain(sc, 0);
444 }
445
446 static int
447 dbri_config_interrupts(device_t dev)
448 {
449 struct dbri_softc *sc = device_private(dev);
450
451 mutex_spin_enter(&sc->sc_intr_lock);
452 if (sc->sc_init_done != 0) {
453 mutex_spin_exit(&sc->sc_intr_lock);
454 return 0;
455 }
456
457 sc->sc_init_done = 1;
458
459 dbri_init(sc);
460 if (mmcodec_init(sc) == -1) {
461 printf("%s: no codec detected, aborting\n",
462 device_xname(dev));
463 mutex_spin_exit(&sc->sc_intr_lock);
464 return 0;
465 }
466 mutex_spin_exit(&sc->sc_intr_lock);
467
468 /* Attach ourselves to the high level audio interface */
469 audio_attach_mi(&dbri_hw_if, sc, sc->sc_dev);
470
471 /* power down until open() */
472 mutex_spin_enter(&sc->sc_intr_lock);
473 dbri_set_power(sc, 0);
474 mutex_spin_exit(&sc->sc_intr_lock);
475
476 return 0;
477 }
478
479 static int
480 dbri_intr(void *hdl)
481 {
482 struct dbri_softc *sc = hdl;
483 bus_space_tag_t iot = sc->sc_iot;
484 bus_space_handle_t ioh = sc->sc_ioh;
485 int x;
486
487 mutex_spin_enter(&sc->sc_intr_lock);
488
489 /* clear interrupt */
490 x = bus_space_read_4(iot, ioh, DBRI_REG1);
491 if (x & (DBRI_MRR | DBRI_MLE | DBRI_LBG | DBRI_MBE)) {
492 uint32_t tmp;
493
494 if (x & DBRI_MRR)
495 aprint_debug_dev(sc->sc_dev,
496 "multiple ack error on sbus\n");
497 if (x & DBRI_MLE)
498 aprint_debug_dev(sc->sc_dev,
499 "multiple late error on sbus\n");
500 if (x & DBRI_LBG)
501 aprint_debug_dev(sc->sc_dev,
502 "lost bus grant on sbus\n");
503 if (x & DBRI_MBE)
504 aprint_debug_dev(sc->sc_dev, "burst error on sbus\n");
505
506 /*
507 * Some of these errors disable the chip's circuitry.
508 * Re-enable the circuitry and keep on going.
509 */
510
511 tmp = bus_space_read_4(iot, ioh, DBRI_REG0);
512 tmp &= ~(DBRI_DISABLE_MASTER);
513 bus_space_write_4(iot, ioh, DBRI_REG0, tmp);
514 }
515
516 #if 0
517 if (!x & 1) /* XXX: DBRI_INTR_REQ */
518 return (1);
519 #endif
520
521 dbri_process_interrupt_buffer(sc);
522
523 mutex_spin_exit(&sc->sc_intr_lock);
524
525 return (1);
526 }
527
528 static void
529 dbri_softint(void *cookie)
530 {
531 struct dbri_desc *dd = cookie;
532
533 if (dd->callback != NULL)
534 dd->callback(dd->callback_args);
535 }
536
537 static int
538 dbri_init(struct dbri_softc *sc)
539 {
540 bus_space_tag_t iot = sc->sc_iot;
541 bus_space_handle_t ioh = sc->sc_ioh;
542 uint32_t reg;
543 volatile uint32_t *cmd;
544 bus_addr_t dmaaddr;
545 int n;
546
547 KASSERT(mutex_owned(sc->sc_intr_lock));
548
549 dbri_reset(sc);
550
551 cmd = dbri_command_lock(sc);
552
553 /* XXX: Initialize interrupt ring buffer */
554 sc->sc_dma->intr[0] = (uint32_t)sc->sc_dmabase + dbri_dma_off(intr, 0);
555 sc->sc_irqp = 1;
556
557 /* Initialize pipes */
558 for (n = 0; n < DBRI_PIPE_MAX; n++)
559 sc->sc_pipe[n].desc = sc->sc_pipe[n].next = -1;
560
561 for (n = 1; n < DBRI_INT_BLOCKS; n++) {
562 sc->sc_dma->intr[n] = 0;
563 }
564
565 /* Disable all SBus bursts */
566 /* XXX 16 byte bursts cause errors, the rest works */
567 reg = bus_space_read_4(iot, ioh, DBRI_REG0);
568
569 /*reg &= ~(DBRI_BURST_4 | DBRI_BURST_8 | DBRI_BURST_16);*/
570 reg |= (DBRI_BURST_4 | DBRI_BURST_8);
571 bus_space_write_4(iot, ioh, DBRI_REG0, reg);
572
573 /* setup interrupt queue */
574 dmaaddr = (uint32_t)sc->sc_dmabase + dbri_dma_off(intr, 0);
575 *(cmd++) = DBRI_CMD(DBRI_COMMAND_IIQ, 0, 0);
576 *(cmd++) = dmaaddr;
577
578 dbri_command_send(sc, cmd);
579
580 return (0);
581 }
582
583 static int
584 dbri_reset(struct dbri_softc *sc)
585 {
586 int bail = 0;
587
588 bus_space_tag_t iot = sc->sc_iot;
589 bus_space_handle_t ioh = sc->sc_ioh;
590
591 bus_space_write_4(iot, ioh, DBRI_REG0, DBRI_SOFT_RESET);
592 while ((bus_space_read_4(iot, ioh, DBRI_REG0) & DBRI_SOFT_RESET) &&
593 (bail < 100000)) {
594 bail++;
595 delay(10);
596 }
597 if (bail == 100000)
598 aprint_error_dev(sc->sc_dev, "reset timed out\n");
599 return (0);
600 }
601
602 static volatile uint32_t *
603 dbri_command_lock(struct dbri_softc *sc)
604 {
605
606 if (sc->sc_locked)
607 aprint_debug_dev(sc->sc_dev, "command buffer locked\n");
608
609 sc->sc_locked++;
610
611 return (&sc->sc_dma->command[0]);
612 }
613
614 static void
615 dbri_command_send(struct dbri_softc *sc, volatile uint32_t *cmd)
616 {
617 bus_space_handle_t ioh = sc->sc_ioh;
618 bus_space_tag_t iot = sc->sc_iot;
619 int maxloops = 1000000;
620
621 KASSERT(mutex_owned(sc->sc_intr_lock));
622
623 sc->sc_locked--;
624
625 if (sc->sc_locked != 0) {
626 aprint_error_dev(sc->sc_dev,
627 "command buffer improperly locked\n");
628 } else if ((cmd - &sc->sc_dma->command[0]) >= DBRI_NUM_COMMANDS - 1) {
629 aprint_error_dev(sc->sc_dev, "command buffer overflow\n");
630 } else {
631 *(cmd++) = DBRI_CMD(DBRI_COMMAND_PAUSE, 0, 0);
632 *(cmd++) = DBRI_CMD(DBRI_COMMAND_WAIT, 1, 0);
633 sc->sc_waitseen = 0;
634 bus_space_write_4(iot, ioh, DBRI_REG8, sc->sc_dmabase);
635 while ((--maxloops) > 0 &&
636 (bus_space_read_4(iot, ioh, DBRI_REG0)
637 & DBRI_COMMAND_VALID)) {
638 bus_space_barrier(iot, ioh, DBRI_REG0, 4,
639 BUS_SPACE_BARRIER_READ);
640 delay(1000);
641 }
642
643 if (maxloops == 0) {
644 aprint_error_dev(sc->sc_dev,
645 "chip never completed command buffer\n");
646 } else {
647
648 DPRINTF("%s: command completed\n",
649 device_xname(sc->sc_dev));
650
651 while ((--maxloops) > 0 && (!sc->sc_waitseen))
652 dbri_process_interrupt_buffer(sc);
653 if (maxloops == 0) {
654 aprint_error_dev(sc->sc_dev, "chip never acked WAIT\n");
655 }
656 }
657 }
658
659 return;
660 }
661
662 static void
663 dbri_process_interrupt_buffer(struct dbri_softc *sc)
664 {
665 int32_t i;
666 int orig_irqp = sc->sc_irqp;
667
668 KASSERT(mutex_owned(sc->sc_intr_lock));
669
670 while ((i = sc->sc_dma->intr[sc->sc_irqp]) != 0) {
671 sc->sc_dma->intr[sc->sc_irqp] = 0;
672 sc->sc_irqp++;
673
674 if (sc->sc_irqp == DBRI_INT_BLOCKS)
675 sc->sc_irqp = 1;
676 else if ((sc->sc_irqp & (DBRI_INT_BLOCKS - 1)) == 0)
677 sc->sc_irqp++;
678
679 dbri_process_interrupt(sc, i);
680
681 /* don't loop more than once. */
682 if (orig_irqp == sc->sc_irqp)
683 break;
684 }
685
686 return;
687 }
688
689 static void
690 dbri_process_interrupt(struct dbri_softc *sc, int32_t i)
691 {
692 #if 0
693 const int liu_states[] = { 1, 0, 8, 3, 4, 5, 6, 7 };
694 #endif
695 int val = DBRI_INTR_GETVAL(i);
696 int channel = DBRI_INTR_GETCHAN(i);
697 int command = DBRI_INTR_GETCMD(i);
698 int code = DBRI_INTR_GETCODE(i);
699 #if 0
700 int rval = DBRI_INTR_GETRVAL(i);
701 #endif
702 if (channel == DBRI_INTR_CMD && command == DBRI_COMMAND_WAIT)
703 sc->sc_waitseen++;
704
705 switch (code) {
706 case DBRI_INTR_XCMP: /* transmission complete */
707 {
708 int td;
709 struct dbri_desc *dd;
710
711 DPRINTF("%s:%d tx complete\n", __func__, channel);
712 td = sc->sc_pipe[channel].desc;
713 dd = &sc->sc_desc[td];
714
715 if (dd->callback != NULL)
716 softint_schedule(dd->softint);
717 break;
718 }
719 case DBRI_INTR_FXDT: /* fixed data change */
720 DPRINTF("%s:%d: Fixed data change: %x\n", __func__, channel,
721 val);
722 #if 0
723 printf("reg: %08x\n", sc->sc_mm.status);
724 #endif
725 if (sc->sc_pipe[channel].sdp & DBRI_SDP_MSB)
726 val = reverse_bytes(val, sc->sc_pipe[channel].length);
727 if (sc->sc_pipe[channel].prec)
728 *(sc->sc_pipe[channel].prec) = val;
729 #ifndef DBRI_SPIN
730 DPRINTF("%s: cv_broadcast %p\n", device_xname(sc->sc_dev), sc);
731 cv_broadcast(&sc->sc_cv);
732 #endif
733 break;
734 case DBRI_INTR_SBRI:
735 DPRINTF("dbri_intr: SBRI\n");
736 break;
737 case DBRI_INTR_BRDY:
738 {
739 int td;
740 struct dbri_desc *dd;
741
742 DPRINTF("dbri_intr: buffer ready (%d)\n", channel);
743 td = sc->sc_pipe[channel].desc;
744 dd = &sc->sc_desc[td];
745
746 if (dd->callback != NULL)
747 softint_schedule(dd->softint);
748 break;
749 }
750 case DBRI_INTR_UNDR:
751 {
752 volatile uint32_t *cmd;
753 int td = sc->sc_pipe[channel].desc;
754
755 DPRINTF("%s: DBRI_INTR_UNDR\n", device_xname(sc->sc_dev));
756
757 sc->sc_dma->xmit[td].status = 0;
758
759 cmd = dbri_command_lock(sc);
760 *(cmd++) = DBRI_CMD(DBRI_COMMAND_SDP, 0,
761 sc->sc_pipe[channel].sdp |
762 DBRI_SDP_VALID_POINTER |
763 DBRI_SDP_CLEAR |
764 DBRI_SDP_2SAME);
765 *(cmd++) = sc->sc_dmabase + dbri_dma_off(xmit, td);
766 dbri_command_send(sc, cmd);
767 break;
768 }
769 case DBRI_INTR_CMDI:
770 DPRINTF("ok");
771 break;
772 default:
773
774 aprint_error_dev(sc->sc_dev, "unknown interrupt code %d\n",
775 code);
776 break;
777 }
778
779 return;
780 }
781
782 /*
783 * mmcodec stuff
784 */
785
786 static int
787 mmcodec_init(struct dbri_softc *sc)
788 {
789 bus_space_handle_t ioh = sc->sc_ioh;
790 bus_space_tag_t iot = sc->sc_iot;
791 uint32_t reg2;
792 int bail;
793
794 reg2 = bus_space_read_4(iot, ioh, DBRI_REG2);
795 DPRINTF("mmcodec_init: PIO reads %x\n", reg2);
796
797 if (reg2 & DBRI_PIO2) {
798 aprint_normal_dev(sc->sc_dev, " onboard CS4215 detected\n");
799 sc->sc_mm.onboard = 1;
800 }
801
802 if (reg2 & DBRI_PIO0) {
803 aprint_normal_dev(sc->sc_dev, "speakerbox detected\n");
804 bus_space_write_4(iot, ioh, DBRI_REG2, DBRI_PIO2_ENABLE);
805 sc->sc_mm.onboard = 0;
806 }
807
808 if ((reg2 & DBRI_PIO2) && (reg2 & DBRI_PIO0)) {
809 aprint_normal_dev(sc->sc_dev, "using speakerbox\n");
810 bus_space_write_4(iot, ioh, DBRI_REG2, DBRI_PIO2_ENABLE);
811 sc->sc_mm.onboard = 0;
812 }
813
814 if (!(reg2 & (DBRI_PIO0|DBRI_PIO2))) {
815 aprint_normal_dev(sc->sc_dev, "no mmcodec found\n");
816 return -1;
817 }
818
819 sc->sc_version = 0xff;
820
821 mmcodec_pipe_init(sc);
822 mmcodec_default(sc);
823
824 sc->sc_mm.offset = sc->sc_mm.onboard ? 0 : 8;
825
826 /*
827 * mmcodec_setcontrol() sometimes fails right after powerup
828 * so we just try again until we either get a useful response or run
829 * out of time
830 */
831 bail = 0;
832 while (mmcodec_setcontrol(sc) == -1 || sc->sc_version == 0xff) {
833
834 bail++;
835 if (bail > 100) {
836 DPRINTF("%s: cs4215 probe failed at offset %d\n",
837 device_xname(sc->sc_dev), sc->sc_mm.offset);
838 return (-1);
839 }
840 delay(10000);
841 }
842
843 aprint_normal_dev(sc->sc_dev, "cs4215 rev %c found at offset %d\n",
844 0x43 + (sc->sc_version & 0xf), sc->sc_mm.offset);
845
846 /* set some sane defaults for mmcodec_init_data */
847 sc->sc_params.channels = 2;
848 sc->sc_params.precision = 16;
849
850 mmcodec_init_data(sc);
851
852 return (0);
853 }
854
855 static void
856 mmcodec_init_data(struct dbri_softc *sc)
857 {
858 bus_space_tag_t iot = sc->sc_iot;
859 bus_space_handle_t ioh = sc->sc_ioh;
860 uint32_t tmp;
861 int data_width;
862
863 tmp = bus_space_read_4(iot, ioh, DBRI_REG0);
864 tmp &= ~(DBRI_CHI_ACTIVATE); /* disable CHI */
865 bus_space_write_4(iot, ioh, DBRI_REG0, tmp);
866
867 /* switch CS4215 to data mode - set PIO3 to 1 */
868 tmp = DBRI_PIO_ENABLE_ALL | DBRI_PIO1 | DBRI_PIO3;
869
870 /* XXX */
871 tmp |= (sc->sc_mm.onboard ? DBRI_PIO0 : DBRI_PIO2);
872
873 bus_space_write_4(iot, ioh, DBRI_REG2, tmp);
874 chi_reset(sc, CHIslave, 128);
875
876 data_width = sc->sc_params.channels * sc->sc_params.precision;
877
878 if ((data_width != 32) && (data_width != 8))
879 aprint_error("%s: data_width is %d\n", __func__, data_width);
880
881 pipe_ts_link(sc, 20, PIPEoutput, 16, 32, sc->sc_mm.offset + 32);
882 pipe_ts_link(sc, 4, PIPEoutput, 16, data_width, sc->sc_mm.offset);
883 pipe_ts_link(sc, 6, PIPEinput, 16, data_width, sc->sc_mm.offset);
884 pipe_ts_link(sc, 21, PIPEinput, 16, 32, sc->sc_mm.offset + 32);
885
886 pipe_receive_fixed(sc, 21, &sc->sc_mm.status);
887
888 mmcodec_setgain(sc, 0);
889
890 tmp = bus_space_read_4(iot, ioh, DBRI_REG0);
891 tmp |= DBRI_CHI_ACTIVATE;
892 bus_space_write_4(iot, ioh, DBRI_REG0, tmp);
893
894 return;
895 }
896
897 static void
898 mmcodec_pipe_init(struct dbri_softc *sc)
899 {
900
901 pipe_setup(sc, 4, DBRI_SDP_MEM | DBRI_SDP_TO_SER | DBRI_SDP_MSB);
902 pipe_setup(sc, 20, DBRI_SDP_FIXED | DBRI_SDP_TO_SER | DBRI_SDP_MSB);
903 pipe_setup(sc, 6, DBRI_SDP_MEM | DBRI_SDP_FROM_SER | DBRI_SDP_MSB);
904 pipe_setup(sc, 21, DBRI_SDP_FIXED | DBRI_SDP_FROM_SER | DBRI_SDP_MSB);
905
906 pipe_setup(sc, 17, DBRI_SDP_FIXED | DBRI_SDP_TO_SER | DBRI_SDP_MSB);
907 pipe_setup(sc, 18, DBRI_SDP_FIXED | DBRI_SDP_FROM_SER | DBRI_SDP_MSB);
908 pipe_setup(sc, 19, DBRI_SDP_FIXED | DBRI_SDP_FROM_SER | DBRI_SDP_MSB);
909
910 sc->sc_mm.status = 0;
911
912 pipe_receive_fixed(sc, 18, &sc->sc_mm.status);
913 pipe_receive_fixed(sc, 19, &sc->sc_mm.version);
914
915 return;
916 }
917
918 static void
919 mmcodec_default(struct dbri_softc *sc)
920 {
921 struct cs4215_state *mm = &sc->sc_mm;
922
923 /*
924 * no action, memory resetting only
925 *
926 * data time slots 5-8
927 * speaker, line and headphone enable. set gain to half.
928 * input is line
929 */
930 mm->d.bdata[0] = sc->sc_latt = 0x20 | CS4215_HE | CS4215_LE;
931 mm->d.bdata[1] = sc->sc_ratt = 0x20 | CS4215_SE;
932 sc->sc_linp = 128;
933 sc->sc_rinp = 128;
934 sc->sc_monitor = 0;
935 sc->sc_input = 1; /* line */
936 mm->d.bdata[2] = (CS4215_LG((sc->sc_linp >> 4)) & 0x0f) |
937 ((sc->sc_input == 2) ? CS4215_IS : 0) | CS4215_PIO0 | CS4215_PIO1;
938 mm->d.bdata[3] = (CS4215_RG((sc->sc_rinp >> 4) & 0x0f)) |
939 CS4215_MA(15 - ((sc->sc_monitor >> 4) & 0x0f));
940
941
942 /*
943 * control time slots 1-4
944 *
945 * 0: default I/O voltage scale
946 * 1: 8 bit ulaw, 8kHz, mono, high pass filter disabled
947 * 2: serial enable, CHI master, 128 bits per frame, clock 1
948 * 3: tests disabled
949 */
950 mm->c.bcontrol[0] = CS4215_RSRVD_1 | CS4215_MLB;
951 mm->c.bcontrol[1] = CS4215_DFR_ULAW | CS4215_FREQ[0].csval;
952 mm->c.bcontrol[2] = CS4215_XCLK | CS4215_BSEL_128 | CS4215_FREQ[0].xtal;
953 mm->c.bcontrol[3] = 0;
954
955 return;
956 }
957
958 static void
959 mmcodec_setgain(struct dbri_softc *sc, int mute)
960 {
961 if (mute) {
962 /* disable all outputs, max. attenuation */
963 sc->sc_mm.d.bdata[0] = sc->sc_latt | 63;
964 sc->sc_mm.d.bdata[1] = sc->sc_ratt | 63;
965 } else {
966
967 sc->sc_mm.d.bdata[0] = sc->sc_latt;
968 sc->sc_mm.d.bdata[1] = sc->sc_ratt;
969 }
970
971 /* input stuff */
972 sc->sc_mm.d.bdata[2] = CS4215_LG((sc->sc_linp >> 4) & 0x0f) |
973 ((sc->sc_input == 2) ? CS4215_IS : 0) | CS4215_PIO0 | CS4215_PIO1;
974 sc->sc_mm.d.bdata[3] = (CS4215_RG((sc->sc_rinp >> 4)) & 0x0f) |
975 (CS4215_MA(15 - ((sc->sc_monitor >> 4) & 0x0f)));
976
977 if (sc->sc_powerstate == 0)
978 return;
979 pipe_transmit_fixed(sc, 20, sc->sc_mm.d.ldata);
980
981 DPRINTF("mmcodec_setgain: %08x\n", sc->sc_mm.d.ldata);
982 /* give the chip some time to execute the command */
983 delay(250);
984
985 return;
986 }
987
988 static int
989 mmcodec_setcontrol(struct dbri_softc *sc)
990 {
991 bus_space_tag_t iot = sc->sc_iot;
992 bus_space_handle_t ioh = sc->sc_ioh;
993 uint32_t val;
994 uint32_t tmp;
995 int bail = 0;
996 #if DBRI_SPIN
997 int i;
998 #else
999 int error;
1000 #endif
1001
1002 /*
1003 * Temporarily mute outputs and wait 125 us to make sure that it
1004 * happens. This avoids clicking noises.
1005 */
1006 mmcodec_setgain(sc, 1);
1007 delay(125);
1008
1009 bus_space_write_4(iot, ioh, DBRI_REG2, 0);
1010 delay(125);
1011
1012 /* enable control mode */
1013 val = DBRI_PIO_ENABLE_ALL | DBRI_PIO1; /* was PIO1 */
1014
1015 /* XXX */
1016 val |= (sc->sc_mm.onboard ? DBRI_PIO0 : DBRI_PIO2);
1017
1018 bus_space_write_4(iot, ioh, DBRI_REG2, val);
1019
1020 delay(34);
1021
1022 /*
1023 * in control mode, the cs4215 is the slave device, so the
1024 * DBRI must act as the CHI master.
1025 *
1026 * in data mode, the cs4215 must be the CHI master to insure
1027 * that the data stream is in sync with its codec
1028 */
1029 tmp = bus_space_read_4(iot, ioh, DBRI_REG0);
1030 tmp &= ~DBRI_COMMAND_CHI;
1031 bus_space_write_4(iot, ioh, DBRI_REG0, tmp);
1032
1033 chi_reset(sc, CHImaster, 128);
1034
1035 /* control mode */
1036 pipe_ts_link(sc, 17, PIPEoutput, 16, 32, sc->sc_mm.offset);
1037 pipe_ts_link(sc, 18, PIPEinput, 16, 8, sc->sc_mm.offset);
1038 pipe_ts_link(sc, 19, PIPEinput, 16, 8, sc->sc_mm.offset + 48);
1039
1040 /* wait for the chip to echo back CLB as zero */
1041 sc->sc_mm.c.bcontrol[0] &= ~CS4215_CLB;
1042 pipe_transmit_fixed(sc, 17, sc->sc_mm.c.lcontrol);
1043
1044 tmp = bus_space_read_4(iot, ioh, DBRI_REG0);
1045 tmp |= DBRI_CHI_ACTIVATE;
1046 bus_space_write_4(iot, ioh, DBRI_REG0, tmp);
1047
1048 #if DBRI_SPIN
1049 i = 1024;
1050 while (((sc->sc_mm.status & 0xe4) != 0x20) && --i) {
1051 delay(125);
1052 }
1053
1054 if (i == 0) {
1055 DPRINTF("%s: cs4215 didn't respond to CLB (0x%02x)\n",
1056 device_xname(sc->sc_dev), sc->sc_mm.status);
1057 return (-1);
1058 }
1059 #else
1060 while (((sc->sc_mm.status & 0xe4) != 0x20) && (bail < 10)) {
1061 DPRINTF("%s: cv_wait_sig %p\n", device_xname(sc->sc_dev), sc);
1062 error = cv_timedwait_sig(&sc->sc_cv, &sc->sc_intr_lock, hz);
1063 if (error == EINTR) {
1064 DPRINTF("%s: interrupted\n", device_xname(sc->sc_dev));
1065 return -1;
1066 }
1067 bail++;
1068 }
1069 #endif
1070 if (bail >= 10) {
1071 DPRINTF("%s: switching to control mode timed out (%x %x)\n",
1072 device_xname(sc->sc_dev), sc->sc_mm.status,
1073 bus_space_read_4(iot, ioh, DBRI_REG2));
1074 return -1;
1075 }
1076
1077 /* copy the version information before it becomes unreadable again */
1078 sc->sc_version = sc->sc_mm.version;
1079
1080 /* terminate cs4215 control mode */
1081 sc->sc_mm.c.bcontrol[0] |= CS4215_CLB;
1082 pipe_transmit_fixed(sc, 17, sc->sc_mm.c.lcontrol);
1083
1084 /* two frames of control info @ 8kHz frame rate = 250us delay */
1085 delay(250);
1086
1087 mmcodec_setgain(sc, 0);
1088
1089 return (0);
1090
1091 }
1092
1093 /*
1094 * CHI combo
1095 */
1096 static void
1097 chi_reset(struct dbri_softc *sc, enum ms ms, int bpf)
1098 {
1099 volatile uint32_t *cmd;
1100 int val;
1101 int clockrate, divisor;
1102
1103 cmd = dbri_command_lock(sc);
1104
1105 /* set CHI anchor: pipe 16 */
1106 val = DBRI_DTS_VI | DBRI_DTS_INS | DBRI_DTS_PRVIN(16) | DBRI_PIPE(16);
1107 *(cmd++) = DBRI_CMD(DBRI_COMMAND_DTS, 0, val);
1108 *(cmd++) = DBRI_TS_ANCHOR | DBRI_TS_NEXT(16);
1109 *(cmd++) = 0;
1110
1111 val = DBRI_DTS_VO | DBRI_DTS_INS | DBRI_DTS_PRVOUT(16) | DBRI_PIPE(16);
1112 *(cmd++) = DBRI_CMD(DBRI_COMMAND_DTS, 0, val);
1113 *(cmd++) = 0;
1114 *(cmd++) = DBRI_TS_ANCHOR | DBRI_TS_NEXT(16);
1115
1116 sc->sc_pipe[16].sdp = 1;
1117 sc->sc_pipe[16].next = 16;
1118 sc->sc_chi_pipe_in = 16;
1119 sc->sc_chi_pipe_out = 16;
1120
1121 switch (ms) {
1122 case CHIslave:
1123 *(cmd++) = DBRI_CMD(DBRI_COMMAND_CHI, 0, DBRI_CHI_CHICM(0));
1124 break;
1125 case CHImaster:
1126 clockrate = bpf * 8;
1127 divisor = 12288 / clockrate;
1128
1129 if (divisor > 255 || divisor * clockrate != 12288)
1130 aprint_error_dev(sc->sc_dev,
1131 "illegal bits-per-frame %d\n", bpf);
1132
1133 *(cmd++) = DBRI_CMD(DBRI_COMMAND_CHI, 0,
1134 DBRI_CHI_CHICM(divisor) | DBRI_CHI_FD | DBRI_CHI_BPF(bpf));
1135 break;
1136 default:
1137 aprint_error_dev(sc->sc_dev, "unknown value for ms!\n");
1138 break;
1139 }
1140
1141 sc->sc_chi_bpf = bpf;
1142
1143 /* CHI data mode */
1144 *(cmd++) = DBRI_CMD(DBRI_COMMAND_PAUSE, 0, 0);
1145 *(cmd++) = DBRI_CMD(DBRI_COMMAND_CDM, 0,
1146 DBRI_CDM_XCE | DBRI_CDM_XEN | DBRI_CDM_REN);
1147
1148 dbri_command_send(sc, cmd);
1149
1150 return;
1151 }
1152
1153 /*
1154 * pipe stuff
1155 */
1156 static void
1157 pipe_setup(struct dbri_softc *sc, int pipe, int sdp)
1158 {
1159 DPRINTF("pipe setup: %d\n", pipe);
1160 if (pipe < 0 || pipe >= DBRI_PIPE_MAX) {
1161 aprint_error_dev(sc->sc_dev, "illegal pipe number %d\n",
1162 pipe);
1163 return;
1164 }
1165
1166 if ((sdp & 0xf800) != sdp)
1167 aprint_error_dev(sc->sc_dev, "strange SDP value %d\n",
1168 sdp);
1169
1170 if (DBRI_SDP_MODE(sdp) == DBRI_SDP_FIXED &&
1171 !(sdp & DBRI_SDP_TO_SER))
1172 sdp |= DBRI_SDP_CHANGE;
1173
1174 sdp |= DBRI_PIPE(pipe);
1175
1176 sc->sc_pipe[pipe].sdp = sdp;
1177 sc->sc_pipe[pipe].desc = -1;
1178
1179 pipe_reset(sc, pipe);
1180
1181 return;
1182 }
1183
1184 static void
1185 pipe_reset(struct dbri_softc *sc, int pipe)
1186 {
1187 struct dbri_desc *dd;
1188 int sdp;
1189 int desc;
1190 volatile uint32_t *cmd;
1191
1192 if (pipe < 0 || pipe >= DBRI_PIPE_MAX) {
1193 aprint_error_dev(sc->sc_dev, "illegal pipe number %d\n",
1194 pipe);
1195 return;
1196 }
1197
1198 sdp = sc->sc_pipe[pipe].sdp;
1199 if (sdp == 0) {
1200 aprint_error_dev(sc->sc_dev, "can not reset uninitialized pipe %d\n",
1201 pipe);
1202 return;
1203 }
1204
1205 cmd = dbri_command_lock(sc);
1206 *(cmd++) = DBRI_CMD(DBRI_COMMAND_SDP, 0,
1207 sdp | DBRI_SDP_CLEAR | DBRI_SDP_VALID_POINTER);
1208 *(cmd++) = 0;
1209 dbri_command_send(sc, cmd);
1210
1211 desc = sc->sc_pipe[pipe].desc;
1212
1213 dd = &sc->sc_desc[desc];
1214
1215 dd->busy = 0;
1216
1217 #if 0
1218 if (dd->callback)
1219 softint_schedule(dd->softint);
1220 #endif
1221
1222 sc->sc_pipe[pipe].desc = -1;
1223
1224 return;
1225 }
1226
1227 static void
1228 pipe_receive_fixed(struct dbri_softc *sc, int pipe, volatile uint32_t *prec)
1229 {
1230
1231 if (pipe < DBRI_PIPE_MAX / 2 || pipe >= DBRI_PIPE_MAX) {
1232 aprint_error_dev(sc->sc_dev, "illegal pipe number %d\n",
1233 pipe);
1234 return;
1235 }
1236
1237 if (DBRI_SDP_MODE(sc->sc_pipe[pipe].sdp) != DBRI_SDP_FIXED) {
1238 aprint_error_dev(sc->sc_dev, "non-fixed pipe %d\n",
1239 pipe);
1240 return;
1241 }
1242
1243 if (sc->sc_pipe[pipe].sdp & DBRI_SDP_TO_SER) {
1244 aprint_error_dev(sc->sc_dev, "can not receive on transmit pipe %d\b",
1245 pipe);
1246 return;
1247 }
1248
1249 sc->sc_pipe[pipe].prec = prec;
1250
1251 return;
1252 }
1253
1254 static void
1255 pipe_transmit_fixed(struct dbri_softc *sc, int pipe, uint32_t data)
1256 {
1257 volatile uint32_t *cmd;
1258
1259 if (pipe < DBRI_PIPE_MAX / 2 || pipe >= DBRI_PIPE_MAX) {
1260 aprint_error_dev(sc->sc_dev, "illegal pipe number %d\n",
1261 pipe);
1262 return;
1263 }
1264
1265 if (DBRI_SDP_MODE(sc->sc_pipe[pipe].sdp) == 0) {
1266 aprint_error_dev(sc->sc_dev, "uninitialized pipe %d\n",
1267 pipe);
1268 return;
1269 }
1270
1271 if (DBRI_SDP_MODE(sc->sc_pipe[pipe].sdp) != DBRI_SDP_FIXED) {
1272 aprint_error_dev(sc->sc_dev, "non-fixed pipe %d\n",
1273 pipe);
1274 return;
1275 }
1276
1277 if (!(sc->sc_pipe[pipe].sdp & DBRI_SDP_TO_SER)) {
1278 aprint_error_dev(sc->sc_dev, "called on receive pipe %d\n",
1279 pipe);
1280 return;
1281 }
1282
1283 if (sc->sc_pipe[pipe].sdp & DBRI_SDP_MSB)
1284 data = reverse_bytes(data, sc->sc_pipe[pipe].length);
1285
1286 cmd = dbri_command_lock(sc);
1287 *(cmd++) = DBRI_CMD(DBRI_COMMAND_SSP, 0, pipe);
1288 *(cmd++) = data;
1289
1290 dbri_command_send(sc, cmd);
1291
1292 return;
1293 }
1294
1295 static void
1296 setup_ring_xmit(struct dbri_softc *sc, int pipe, int which, int num, int blksz,
1297 void (*callback)(void *), void *callback_args)
1298 {
1299 volatile uint32_t *cmd;
1300 int i;
1301 #if 0
1302 int td;
1303 int td_first, td_last;
1304 #endif
1305 bus_addr_t dmabuf, dmabase;
1306 struct dbri_desc *dd = &sc->sc_desc[which];
1307
1308 switch (pipe) {
1309 case 4:
1310 /* output, offset 0 */
1311 break;
1312 default:
1313 aprint_error("%s: illegal pipe number (%d)\n",
1314 __func__, pipe);
1315 return;
1316 }
1317
1318 #if 0
1319 td = 0;
1320 td_first = td_last = -1;
1321 #endif
1322
1323 if (sc->sc_pipe[pipe].sdp == 0) {
1324 aprint_error_dev(sc->sc_dev, "uninitialized pipe %d\n",
1325 pipe);
1326 return;
1327 }
1328
1329 dmabuf = dd->dmabase;
1330 dmabase = sc->sc_dmabase;
1331
1332 for (i = 0; i < (num - 1); i++) {
1333
1334 sc->sc_dma->xmit[i].flags = TX_BCNT(blksz)
1335 | TX_EOF | TX_BINT;
1336 sc->sc_dma->xmit[i].ba = dmabuf;
1337 sc->sc_dma->xmit[i].nda = dmabase + dbri_dma_off(xmit, i + 1);
1338 sc->sc_dma->xmit[i].status = 0;
1339
1340 #if 0
1341 td_last = td;
1342 #endif
1343 dmabuf += blksz;
1344 }
1345
1346 sc->sc_dma->xmit[i].flags = TX_BCNT(blksz) | TX_EOF | TX_BINT;
1347
1348 sc->sc_dma->xmit[i].ba = dmabuf;
1349 sc->sc_dma->xmit[i].nda = dmabase + dbri_dma_off(xmit, 0);
1350 sc->sc_dma->xmit[i].status = 0;
1351
1352 dd->callback = callback;
1353 dd->callback_args = callback_args;
1354
1355 /* the pipe shouldn't be active */
1356 if (pipe_active(sc, pipe)) {
1357 aprint_error("pipe active (CDP)\n");
1358 /* pipe is already active */
1359 #if 0
1360 td_last = sc->sc_pipe[pipe].desc;
1361 while (sc->sc_desc[td_last].next != -1)
1362 td_last = sc->sc_desc[td_last].next;
1363
1364 sc->sc_desc[td_last].next = td_first;
1365 sc->sc_dma->desc[td_last].nda =
1366 sc->sc_dmabase + dbri_dma_off(desc, td_first);
1367
1368 cmd = dbri_command_lock(sc);
1369 *(cmd++) = DBRI_CMD(DBRI_COMMAND_CDP, 0, pipe);
1370 dbri_command_send(sc, cmd);
1371 #endif
1372 } else {
1373 /*
1374 * pipe isn't active - issue an SDP command to start our
1375 * chain of TDs running
1376 */
1377 sc->sc_pipe[pipe].desc = which;
1378 cmd = dbri_command_lock(sc);
1379 *(cmd++) = DBRI_CMD(DBRI_COMMAND_SDP, 0,
1380 sc->sc_pipe[pipe].sdp |
1381 DBRI_SDP_VALID_POINTER |
1382 DBRI_SDP_EVERY |
1383 DBRI_SDP_CLEAR);
1384 *(cmd++) = sc->sc_dmabase + dbri_dma_off(xmit, 0);
1385 dbri_command_send(sc, cmd);
1386 DPRINTF("%s: starting DMA\n", __func__);
1387 }
1388
1389 return;
1390 }
1391
1392 static void
1393 setup_ring_recv(struct dbri_softc *sc, int pipe, int which, int num, int blksz,
1394 void (*callback)(void *), void *callback_args)
1395 {
1396 volatile uint32_t *cmd;
1397 int i;
1398 #if 0
1399 int td_first, td_last;
1400 #endif
1401 bus_addr_t dmabuf, dmabase;
1402 struct dbri_desc *dd = &sc->sc_desc[which];
1403
1404 switch (pipe) {
1405 case 6:
1406 break;
1407 default:
1408 aprint_error("%s: illegal pipe number (%d)\n",
1409 __func__, pipe);
1410 return;
1411 }
1412
1413 #if 0
1414 td_first = td_last = -1;
1415 #endif
1416
1417 if (sc->sc_pipe[pipe].sdp == 0) {
1418 aprint_error_dev(sc->sc_dev, "uninitialized pipe %d\n",
1419 pipe);
1420 return;
1421 }
1422
1423 dmabuf = dd->dmabase;
1424 dmabase = sc->sc_dmabase;
1425
1426 for (i = 0; i < (num - 1); i++) {
1427
1428 sc->sc_dma->recv[i].flags = RX_BSIZE(blksz) | RX_FINAL;
1429 sc->sc_dma->recv[i].ba = dmabuf;
1430 sc->sc_dma->recv[i].nda = dmabase + dbri_dma_off(recv, i + 1);
1431 sc->sc_dma->recv[i].status = RX_EOF;
1432
1433 #if 0
1434 td_last = i;
1435 #endif
1436 dmabuf += blksz;
1437 }
1438
1439 sc->sc_dma->recv[i].flags = RX_BSIZE(blksz) | RX_FINAL;
1440
1441 sc->sc_dma->recv[i].ba = dmabuf;
1442 sc->sc_dma->recv[i].nda = dmabase + dbri_dma_off(recv, 0);
1443 sc->sc_dma->recv[i].status = RX_EOF;
1444
1445 dd->callback = callback;
1446 dd->callback_args = callback_args;
1447
1448 /* the pipe shouldn't be active */
1449 if (pipe_active(sc, pipe)) {
1450 aprint_error("pipe active (CDP)\n");
1451 /* pipe is already active */
1452 #if 0
1453 td_last = sc->sc_pipe[pipe].desc;
1454 while (sc->sc_desc[td_last].next != -1)
1455 td_last = sc->sc_desc[td_last].next;
1456
1457 sc->sc_desc[td_last].next = td_first;
1458 sc->sc_dma->desc[td_last].nda =
1459 sc->sc_dmabase + dbri_dma_off(desc, td_first);
1460
1461 cmd = dbri_command_lock(sc);
1462 *(cmd++) = DBRI_CMD(DBRI_COMMAND_CDP, 0, pipe);
1463 dbri_command_send(sc, cmd);
1464 #endif
1465 } else {
1466 /*
1467 * pipe isn't active - issue an SDP command to start our
1468 * chain of TDs running
1469 */
1470 sc->sc_pipe[pipe].desc = which;
1471 cmd = dbri_command_lock(sc);
1472 *(cmd++) = DBRI_CMD(DBRI_COMMAND_SDP, 0,
1473 sc->sc_pipe[pipe].sdp |
1474 DBRI_SDP_VALID_POINTER |
1475 DBRI_SDP_EVERY |
1476 DBRI_SDP_CLEAR);
1477 *(cmd++) = sc->sc_dmabase + dbri_dma_off(recv, 0);
1478 dbri_command_send(sc, cmd);
1479 DPRINTF("%s: starting DMA\n", __func__);
1480 }
1481
1482 return;
1483 }
1484
1485 static void
1486 pipe_ts_link(struct dbri_softc *sc, int pipe, enum io dir, int basepipe,
1487 int len, int cycle)
1488 {
1489 volatile uint32_t *cmd;
1490 int prevpipe, nextpipe;
1491 int val;
1492
1493 DPRINTF("%s: %d\n", __func__, pipe);
1494 if (pipe < 0 || pipe >= DBRI_PIPE_MAX ||
1495 basepipe < 0 || basepipe >= DBRI_PIPE_MAX) {
1496 aprint_error_dev(sc->sc_dev, "illegal pipe numbers (%d, %d)\n",
1497 pipe, basepipe);
1498 return;
1499 }
1500
1501 if (sc->sc_pipe[pipe].sdp == 0 || sc->sc_pipe[basepipe].sdp == 0) {
1502 aprint_error_dev(sc->sc_dev, "uninitialized pipe (%d, %d)\n",
1503 pipe, basepipe);
1504 return;
1505 }
1506
1507 if (basepipe == 16 && dir == PIPEoutput && cycle == 0)
1508 cycle = sc->sc_chi_bpf;
1509
1510 if (basepipe == pipe)
1511 prevpipe = nextpipe = pipe;
1512 else {
1513 if (basepipe == 16) {
1514 if (dir == PIPEinput) {
1515 prevpipe = sc->sc_chi_pipe_in;
1516 } else {
1517 prevpipe = sc->sc_chi_pipe_out;
1518 }
1519 } else
1520 prevpipe = basepipe;
1521
1522 nextpipe = sc->sc_pipe[prevpipe].next;
1523
1524 while (sc->sc_pipe[nextpipe].cycle < cycle &&
1525 sc->sc_pipe[nextpipe].next != basepipe) {
1526 prevpipe = nextpipe;
1527 nextpipe = sc->sc_pipe[nextpipe].next;
1528 }
1529 }
1530
1531 if (prevpipe == 16) {
1532 if (dir == PIPEinput) {
1533 sc->sc_chi_pipe_in = pipe;
1534 } else {
1535 sc->sc_chi_pipe_out = pipe;
1536 }
1537 } else
1538 sc->sc_pipe[prevpipe].next = pipe;
1539
1540 sc->sc_pipe[pipe].next = nextpipe;
1541 sc->sc_pipe[pipe].cycle = cycle;
1542 sc->sc_pipe[pipe].length = len;
1543
1544 cmd = dbri_command_lock(sc);
1545
1546 switch (dir) {
1547 case PIPEinput:
1548 val = DBRI_DTS_VI | DBRI_DTS_INS | DBRI_DTS_PRVIN(prevpipe);
1549 val |= pipe;
1550 *(cmd++) = DBRI_CMD(DBRI_COMMAND_DTS, 0, val);
1551 *(cmd++) = DBRI_TS_LEN(len) | DBRI_TS_CYCLE(cycle) |
1552 DBRI_TS_NEXT(nextpipe);
1553 *(cmd++) = 0;
1554 break;
1555 case PIPEoutput:
1556 val = DBRI_DTS_VO | DBRI_DTS_INS | DBRI_DTS_PRVOUT(prevpipe);
1557 val |= pipe;
1558 *(cmd++) = DBRI_CMD(DBRI_COMMAND_DTS, 0, val);
1559 *(cmd++) = 0;
1560 *(cmd++) = DBRI_TS_LEN(len) | DBRI_TS_CYCLE(cycle) |
1561 DBRI_TS_NEXT(nextpipe);
1562 break;
1563 default:
1564 DPRINTF("%s: should not have happened!\n",
1565 device_xname(sc->sc_dev));
1566 break;
1567 }
1568
1569 dbri_command_send(sc, cmd);
1570
1571 return;
1572 }
1573
1574 static int
1575 pipe_active(struct dbri_softc *sc, int pipe)
1576 {
1577
1578 return (sc->sc_pipe[pipe].desc != -1);
1579 }
1580
1581 /*
1582 * subroutines required to interface with audio(9)
1583 */
1584
1585 static int
1586 dbri_query_encoding(void *hdl, struct audio_encoding *ae)
1587 {
1588
1589 switch (ae->index) {
1590 case 0:
1591 strcpy(ae->name, AudioEulinear);
1592 ae->encoding = AUDIO_ENCODING_ULINEAR;
1593 ae->precision = 8;
1594 ae->flags = 0;
1595 break;
1596 case 1:
1597 strcpy(ae->name, AudioEmulaw);
1598 ae->encoding = AUDIO_ENCODING_ULAW;
1599 ae->precision = 8;
1600 ae->flags = 0;
1601 break;
1602 case 2:
1603 strcpy(ae->name, AudioEalaw);
1604 ae->encoding = AUDIO_ENCODING_ALAW;
1605 ae->precision = 8;
1606 ae->flags = 0;
1607 break;
1608 case 3:
1609 strcpy(ae->name, AudioEslinear);
1610 ae->encoding = AUDIO_ENCODING_SLINEAR;
1611 ae->precision = 8;
1612 ae->flags = AUDIO_ENCODINGFLAG_EMULATED;
1613 break;
1614 case 4:
1615 strcpy(ae->name, AudioEslinear_le);
1616 ae->encoding = AUDIO_ENCODING_SLINEAR_LE;
1617 ae->precision = 16;
1618 ae->flags = AUDIO_ENCODINGFLAG_EMULATED;
1619 break;
1620 case 5:
1621 strcpy(ae->name, AudioEulinear_le);
1622 ae->encoding = AUDIO_ENCODING_ULINEAR_LE;
1623 ae->precision = 16;
1624 ae->flags = AUDIO_ENCODINGFLAG_EMULATED;
1625 break;
1626 case 6:
1627 strcpy(ae->name, AudioEslinear_be);
1628 ae->encoding = AUDIO_ENCODING_SLINEAR_BE;
1629 ae->precision = 16;
1630 ae->flags = 0;
1631 break;
1632 case 7:
1633 strcpy(ae->name, AudioEulinear_be);
1634 ae->encoding = AUDIO_ENCODING_ULINEAR_BE;
1635 ae->precision = 16;
1636 ae->flags = AUDIO_ENCODINGFLAG_EMULATED;
1637 break;
1638 case 8:
1639 strcpy(ae->name, AudioEslinear);
1640 ae->encoding = AUDIO_ENCODING_SLINEAR;
1641 ae->precision = 16;
1642 ae->flags = 0;
1643 break;
1644 default:
1645 return (EINVAL);
1646 }
1647
1648 return (0);
1649 }
1650
1651 static int
1652 dbri_set_params(void *hdl, int setmode, int usemode,
1653 struct audio_params *play, struct audio_params *rec,
1654 stream_filter_list_t *pfil, stream_filter_list_t *rfil)
1655 {
1656 struct dbri_softc *sc = hdl;
1657 int rate;
1658 audio_params_t *p = NULL;
1659 stream_filter_list_t *fil;
1660 int mode;
1661
1662 /*
1663 * This device only has one clock, so make the sample rates match.
1664 */
1665 if (play->sample_rate != rec->sample_rate &&
1666 usemode == (AUMODE_PLAY | AUMODE_RECORD)) {
1667 if (setmode == AUMODE_PLAY) {
1668 rec->sample_rate = play->sample_rate;
1669 setmode |= AUMODE_RECORD;
1670 } else if (setmode == AUMODE_RECORD) {
1671 play->sample_rate = rec->sample_rate;
1672 setmode |= AUMODE_PLAY;
1673 } else
1674 return EINVAL;
1675 }
1676
1677 for (mode = AUMODE_RECORD; mode != -1;
1678 mode = mode == AUMODE_RECORD ? AUMODE_PLAY : -1) {
1679 if ((setmode & mode) == 0)
1680 continue;
1681
1682 p = mode == AUMODE_PLAY ? play : rec;
1683 if (p->sample_rate < 4000 || p->sample_rate > 50000) {
1684 DPRINTF("dbri_set_params: invalid rate %d\n",
1685 p->sample_rate);
1686 return EINVAL;
1687 }
1688
1689 fil = mode == AUMODE_PLAY ? pfil : rfil;
1690 DPRINTF("requested enc: %d rate: %d prec: %d chan: %d\n", p->encoding,
1691 p->sample_rate, p->precision, p->channels);
1692 if (auconv_set_converter(dbri_formats, DBRI_NFORMATS,
1693 mode, p, true, fil) < 0) {
1694 aprint_debug("dbri_set_params: auconv_set_converter failed\n");
1695 return EINVAL;
1696 }
1697 if (fil->req_size > 0)
1698 p = &fil->filters[0].param;
1699 }
1700
1701 if (p == NULL) {
1702 DPRINTF("dbri_set_params: no parameters to set\n");
1703 return 0;
1704 }
1705
1706 DPRINTF("native enc: %d rate: %d prec: %d chan: %d\n", p->encoding,
1707 p->sample_rate, p->precision, p->channels);
1708
1709 for (rate = 0; CS4215_FREQ[rate].freq; rate++)
1710 if (CS4215_FREQ[rate].freq == p->sample_rate)
1711 break;
1712
1713 if (CS4215_FREQ[rate].freq == 0)
1714 return (EINVAL);
1715
1716 /* set frequency */
1717 sc->sc_mm.c.bcontrol[1] &= ~0x38;
1718 sc->sc_mm.c.bcontrol[1] |= CS4215_FREQ[rate].csval;
1719 sc->sc_mm.c.bcontrol[2] &= ~0x70;
1720 sc->sc_mm.c.bcontrol[2] |= CS4215_FREQ[rate].xtal;
1721
1722 switch (p->encoding) {
1723 case AUDIO_ENCODING_ULAW:
1724 sc->sc_mm.c.bcontrol[1] &= ~3;
1725 sc->sc_mm.c.bcontrol[1] |= CS4215_DFR_ULAW;
1726 break;
1727 case AUDIO_ENCODING_ALAW:
1728 sc->sc_mm.c.bcontrol[1] &= ~3;
1729 sc->sc_mm.c.bcontrol[1] |= CS4215_DFR_ALAW;
1730 break;
1731 case AUDIO_ENCODING_ULINEAR:
1732 sc->sc_mm.c.bcontrol[1] &= ~3;
1733 if (p->precision == 8) {
1734 sc->sc_mm.c.bcontrol[1] |= CS4215_DFR_LINEAR8;
1735 } else {
1736 sc->sc_mm.c.bcontrol[1] |= CS4215_DFR_LINEAR16;
1737 }
1738 break;
1739 case AUDIO_ENCODING_SLINEAR_BE:
1740 case AUDIO_ENCODING_SLINEAR:
1741 sc->sc_mm.c.bcontrol[1] &= ~3;
1742 sc->sc_mm.c.bcontrol[1] |= CS4215_DFR_LINEAR16;
1743 break;
1744 }
1745
1746 switch (p->channels) {
1747 case 1:
1748 sc->sc_mm.c.bcontrol[1] &= ~CS4215_DFR_STEREO;
1749 break;
1750 case 2:
1751 sc->sc_mm.c.bcontrol[1] |= CS4215_DFR_STEREO;
1752 break;
1753 }
1754
1755 return (0);
1756 }
1757
1758 static int
1759 dbri_round_blocksize(void *hdl, int bs, int mode,
1760 const audio_params_t *param)
1761 {
1762
1763 /*
1764 * DBRI DMA segment size can be up to 0x1fff, sixes that are not powers
1765 * of two seem to confuse the upper audio layer so we're going with
1766 * 0x1000 here
1767 */
1768 return 0x1000;
1769 }
1770
1771 static int
1772 dbri_halt_output(void *hdl)
1773 {
1774 struct dbri_softc *sc = hdl;
1775
1776 if (!sc->sc_playing)
1777 return 0;
1778
1779 sc->sc_playing = 0;
1780 pipe_reset(sc, 4);
1781 return (0);
1782 }
1783
1784 static int
1785 dbri_getdev(void *hdl, struct audio_device *ret)
1786 {
1787
1788 *ret = dbri_device;
1789 return (0);
1790 }
1791
1792 static int
1793 dbri_set_port(void *hdl, mixer_ctrl_t *mc)
1794 {
1795 struct dbri_softc *sc = hdl;
1796 int latt = sc->sc_latt, ratt = sc->sc_ratt;
1797
1798 switch (mc->dev) {
1799 case DBRI_VOL_OUTPUT: /* master volume */
1800 latt = (latt & 0xc0) | (63 -
1801 min(mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] >> 2, 63));
1802 ratt = (ratt & 0xc0) | (63 -
1803 min(mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] >> 2, 63));
1804 break;
1805 case DBRI_ENABLE_MONO: /* built-in speaker */
1806 if (mc->un.ord == 1) {
1807 ratt |= CS4215_SE;
1808 } else
1809 ratt &= ~CS4215_SE;
1810 break;
1811 case DBRI_ENABLE_HEADPHONE: /* headphones output */
1812 if (mc->un.ord == 1) {
1813 latt |= CS4215_HE;
1814 } else
1815 latt &= ~CS4215_HE;
1816 break;
1817 case DBRI_ENABLE_LINE: /* line out */
1818 if (mc->un.ord == 1) {
1819 latt |= CS4215_LE;
1820 } else
1821 latt &= ~CS4215_LE;
1822 break;
1823 case DBRI_VOL_MONITOR:
1824 if (mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] ==
1825 sc->sc_monitor)
1826 return 0;
1827 sc->sc_monitor = mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT];
1828 break;
1829 case DBRI_INPUT_GAIN:
1830 sc->sc_linp = mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT];
1831 sc->sc_rinp = mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT];
1832 break;
1833 case DBRI_INPUT_SELECT:
1834 if (mc->un.mask == sc->sc_input)
1835 return 0;
1836 sc->sc_input = mc->un.mask;
1837 break;
1838 }
1839
1840 sc->sc_latt = latt;
1841 sc->sc_ratt = ratt;
1842
1843 mmcodec_setgain(sc, 0);
1844
1845 return (0);
1846 }
1847
1848 static int
1849 dbri_get_port(void *hdl, mixer_ctrl_t *mc)
1850 {
1851 struct dbri_softc *sc = hdl;
1852
1853 switch (mc->dev) {
1854 case DBRI_VOL_OUTPUT: /* master volume */
1855 mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] =
1856 (63 - (sc->sc_latt & 0x3f)) << 2;
1857 mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] =
1858 (63 - (sc->sc_ratt & 0x3f)) << 2;
1859 return (0);
1860 case DBRI_ENABLE_MONO: /* built-in speaker */
1861 mc->un.ord = (sc->sc_ratt & CS4215_SE) ? 1 : 0;
1862 return 0;
1863 case DBRI_ENABLE_HEADPHONE: /* headphones output */
1864 mc->un.ord = (sc->sc_latt & CS4215_HE) ? 1 : 0;
1865 return 0;
1866 case DBRI_ENABLE_LINE: /* line out */
1867 mc->un.ord = (sc->sc_latt & CS4215_LE) ? 1 : 0;
1868 return 0;
1869 case DBRI_VOL_MONITOR:
1870 mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] = sc->sc_monitor;
1871 return 0;
1872 case DBRI_INPUT_GAIN:
1873 mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] = sc->sc_linp;
1874 mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] = sc->sc_rinp;
1875 return 0;
1876 case DBRI_INPUT_SELECT:
1877 mc->un.mask = sc->sc_input;
1878 return 0;
1879 }
1880 return (EINVAL);
1881 }
1882
1883 static int
1884 dbri_query_devinfo(void *hdl, mixer_devinfo_t *di)
1885 {
1886
1887 switch (di->index) {
1888 case DBRI_MONITOR_CLASS:
1889 di->mixer_class = DBRI_MONITOR_CLASS;
1890 strcpy(di->label.name, AudioCmonitor);
1891 di->type = AUDIO_MIXER_CLASS;
1892 di->next = di->prev = AUDIO_MIXER_LAST;
1893 return 0;
1894 case DBRI_OUTPUT_CLASS:
1895 di->mixer_class = DBRI_OUTPUT_CLASS;
1896 strcpy(di->label.name, AudioCoutputs);
1897 di->type = AUDIO_MIXER_CLASS;
1898 di->next = di->prev = AUDIO_MIXER_LAST;
1899 return 0;
1900 case DBRI_INPUT_CLASS:
1901 di->mixer_class = DBRI_INPUT_CLASS;
1902 strcpy(di->label.name, AudioCinputs);
1903 di->type = AUDIO_MIXER_CLASS;
1904 di->next = di->prev = AUDIO_MIXER_LAST;
1905 return 0;
1906 case DBRI_VOL_OUTPUT: /* master volume */
1907 di->mixer_class = DBRI_OUTPUT_CLASS;
1908 di->next = di->prev = AUDIO_MIXER_LAST;
1909 strcpy(di->label.name, AudioNmaster);
1910 di->type = AUDIO_MIXER_VALUE;
1911 di->un.v.num_channels = 2;
1912 di->un.v.delta = 16;
1913 strcpy(di->un.v.units.name, AudioNvolume);
1914 return (0);
1915 case DBRI_INPUT_GAIN: /* input gain */
1916 di->mixer_class = DBRI_INPUT_CLASS;
1917 di->next = di->prev = AUDIO_MIXER_LAST;
1918 strcpy(di->label.name, AudioNrecord);
1919 di->type = AUDIO_MIXER_VALUE;
1920 di->un.v.num_channels = 2;
1921 strcpy(di->un.v.units.name, AudioNvolume);
1922 return (0);
1923 case DBRI_VOL_MONITOR: /* monitor volume */
1924 di->mixer_class = DBRI_MONITOR_CLASS;
1925 di->next = di->prev = AUDIO_MIXER_LAST;
1926 strcpy(di->label.name, AudioNmonitor);
1927 di->type = AUDIO_MIXER_VALUE;
1928 di->un.v.num_channels = 1;
1929 strcpy(di->un.v.units.name, AudioNvolume);
1930 return (0);
1931 case DBRI_ENABLE_MONO: /* built-in speaker */
1932 di->mixer_class = DBRI_OUTPUT_CLASS;
1933 di->next = di->prev = AUDIO_MIXER_LAST;
1934 strcpy(di->label.name, AudioNmono);
1935 di->type = AUDIO_MIXER_ENUM;
1936 di->un.e.num_mem = 2;
1937 strcpy(di->un.e.member[0].label.name, AudioNoff);
1938 di->un.e.member[0].ord = 0;
1939 strcpy(di->un.e.member[1].label.name, AudioNon);
1940 di->un.e.member[1].ord = 1;
1941 return (0);
1942 case DBRI_ENABLE_HEADPHONE: /* headphones output */
1943 di->mixer_class = DBRI_OUTPUT_CLASS;
1944 di->next = di->prev = AUDIO_MIXER_LAST;
1945 strcpy(di->label.name, AudioNheadphone);
1946 di->type = AUDIO_MIXER_ENUM;
1947 di->un.e.num_mem = 2;
1948 strcpy(di->un.e.member[0].label.name, AudioNoff);
1949 di->un.e.member[0].ord = 0;
1950 strcpy(di->un.e.member[1].label.name, AudioNon);
1951 di->un.e.member[1].ord = 1;
1952 return (0);
1953 case DBRI_ENABLE_LINE: /* line out */
1954 di->mixer_class = DBRI_OUTPUT_CLASS;
1955 di->next = di->prev = AUDIO_MIXER_LAST;
1956 strcpy(di->label.name, AudioNline);
1957 di->type = AUDIO_MIXER_ENUM;
1958 di->un.e.num_mem = 2;
1959 strcpy(di->un.e.member[0].label.name, AudioNoff);
1960 di->un.e.member[0].ord = 0;
1961 strcpy(di->un.e.member[1].label.name, AudioNon);
1962 di->un.e.member[1].ord = 1;
1963 return (0);
1964 case DBRI_INPUT_SELECT:
1965 di->mixer_class = DBRI_INPUT_CLASS;
1966 strcpy(di->label.name, AudioNsource);
1967 di->type = AUDIO_MIXER_SET;
1968 di->prev = di->next = AUDIO_MIXER_LAST;
1969 di->un.s.num_mem = 2;
1970 strcpy(di->un.s.member[0].label.name, AudioNline);
1971 di->un.s.member[0].mask = 1 << 0;
1972 strcpy(di->un.s.member[1].label.name, AudioNmicrophone);
1973 di->un.s.member[1].mask = 1 << 1;
1974 return 0;
1975 }
1976
1977 return (ENXIO);
1978 }
1979
1980 static size_t
1981 dbri_round_buffersize(void *hdl, int dir, size_t bufsize)
1982 {
1983 #ifdef DBRI_BIG_BUFFER
1984 return 0x20000; /* use 128KB buffer */
1985 #else
1986 return bufsize;
1987 #endif
1988 }
1989
1990 static int
1991 dbri_get_props(void *hdl)
1992 {
1993
1994 return AUDIO_PROP_MMAP | AUDIO_PROP_FULLDUPLEX;
1995 }
1996
1997 static int
1998 dbri_trigger_output(void *hdl, void *start, void *end, int blksize,
1999 void (*intr)(void *), void *intrarg,
2000 const struct audio_params *param)
2001 {
2002 struct dbri_softc *sc = hdl;
2003 unsigned long count, num;
2004
2005 if (sc->sc_playing)
2006 return 0;
2007
2008 count = (unsigned long)(((char *)end - (char *)start));
2009 num = count / blksize;
2010
2011 DPRINTF("trigger_output(%lx %lx) : %d %ld %ld\n",
2012 (unsigned long)intr,
2013 (unsigned long)intrarg, blksize, count, num);
2014
2015 sc->sc_params = *param;
2016
2017 if (sc->sc_recording == 0) {
2018 /* do not muck with the codec when it's already in use */
2019 if (mmcodec_setcontrol(sc) != 0)
2020 return -1;
2021 mmcodec_init_data(sc);
2022 }
2023
2024 /*
2025 * always use DMA descriptor 0 for output
2026 * no need to allocate them dynamically since we only ever have
2027 * exactly one input stream and exactly one output stream
2028 */
2029 setup_ring_xmit(sc, 4, 0, num, blksize, intr, intrarg);
2030 sc->sc_playing = 1;
2031 return 0;
2032 }
2033
2034 static int
2035 dbri_halt_input(void *cookie)
2036 {
2037 struct dbri_softc *sc = cookie;
2038
2039 if (!sc->sc_recording)
2040 return 0;
2041
2042 sc->sc_recording = 0;
2043 pipe_reset(sc, 6);
2044 return 0;
2045 }
2046
2047 static int
2048 dbri_trigger_input(void *hdl, void *start, void *end, int blksize,
2049 void (*intr)(void *), void *intrarg,
2050 const struct audio_params *param)
2051 {
2052 struct dbri_softc *sc = hdl;
2053 unsigned long count, num;
2054
2055 if (sc->sc_recording)
2056 return 0;
2057
2058 count = (unsigned long)(((char *)end - (char *)start));
2059 num = count / blksize;
2060
2061 DPRINTF("trigger_input(%lx %lx) : %d %ld %ld\n",
2062 (unsigned long)intr,
2063 (unsigned long)intrarg, blksize, count, num);
2064
2065 sc->sc_params = *param;
2066
2067 if (sc->sc_playing == 0) {
2068
2069 /*
2070 * we don't support different parameters for playing and
2071 * recording anyway so don't bother whacking the codec if
2072 * it's already set up
2073 */
2074 mmcodec_setcontrol(sc);
2075 mmcodec_init_data(sc);
2076 }
2077
2078 sc->sc_recording = 1;
2079 setup_ring_recv(sc, 6, 1, num, blksize, intr, intrarg);
2080 return 0;
2081 }
2082
2083 static void
2084 dbri_get_locks(void *opaque, kmutex_t **intr, kmutex_t **thread)
2085 {
2086 struct dbri_softc *sc = opaque;
2087
2088 *intr = &sc->sc_intr_lock;
2089 *thread = &sc->sc_lock;
2090 }
2091
2092 static uint32_t
2093 reverse_bytes(uint32_t b, int len)
2094 {
2095 switch (len) {
2096 case 32:
2097 b = ((b & 0xffff0000) >> 16) | ((b & 0x0000ffff) << 16);
2098 case 16:
2099 b = ((b & 0xff00ff00) >> 8) | ((b & 0x00ff00ff) << 8);
2100 case 8:
2101 b = ((b & 0xf0f0f0f0) >> 4) | ((b & 0x0f0f0f0f) << 4);
2102 case 4:
2103 b = ((b & 0xcccccccc) >> 2) | ((b & 0x33333333) << 2);
2104 case 2:
2105 b = ((b & 0xaaaaaaaa) >> 1) | ((b & 0x55555555) << 1);
2106 case 1:
2107 case 0:
2108 break;
2109 default:
2110 DPRINTF("reverse_bytes: unsupported length\n");
2111 };
2112
2113 return (b);
2114 }
2115
2116 static void *
2117 dbri_malloc(void *v, int dir, size_t s)
2118 {
2119 struct dbri_softc *sc = v;
2120 struct dbri_desc *dd = &sc->sc_desc[sc->sc_desc_used];
2121 int rseg;
2122
2123 if (bus_dmamap_create(sc->sc_dmat, s, 1, s, 0, BUS_DMA_NOWAIT,
2124 &dd->dmamap) == 0) {
2125 if (bus_dmamem_alloc(sc->sc_dmat, s, 0, 0, &dd->dmaseg,
2126 1, &rseg, BUS_DMA_NOWAIT) == 0) {
2127 if (bus_dmamem_map(sc->sc_dmat, &dd->dmaseg, rseg, s,
2128 &dd->buf, BUS_DMA_NOWAIT|BUS_DMA_COHERENT) == 0) {
2129 if (dd->buf != NULL) {
2130 if (bus_dmamap_load(sc->sc_dmat,
2131 dd->dmamap, dd->buf, s, NULL,
2132 BUS_DMA_NOWAIT) == 0) {
2133 dd->len = s;
2134 dd->busy = 0;
2135 dd->callback = NULL;
2136 dd->dmabase =
2137 dd->dmamap->dm_segs[0].ds_addr;
2138 DPRINTF("dbri_malloc: using buffer %d %08x\n",
2139 sc->sc_desc_used, (uint32_t)dd->buf);
2140 sc->sc_desc_used++;
2141 return dd->buf;
2142 } else
2143 aprint_error("dbri_malloc: load failed\n");
2144 } else
2145 aprint_error("dbri_malloc: map returned NULL\n");
2146 } else
2147 aprint_error("dbri_malloc: map failed\n");
2148 bus_dmamem_free(sc->sc_dmat, &dd->dmaseg, rseg);
2149 } else
2150 aprint_error("dbri_malloc: malloc() failed\n");
2151 bus_dmamap_destroy(sc->sc_dmat, dd->dmamap);
2152 } else
2153 aprint_error("dbri_malloc: bus_dmamap_create() failed\n");
2154 return NULL;
2155 }
2156
2157 static void
2158 dbri_free(void *v, void *p, size_t size)
2159 {
2160 struct dbri_softc *sc = v;
2161 struct dbri_desc *dd;
2162 int i;
2163
2164 for (i = 0; i < sc->sc_desc_used; i++) {
2165 dd = &sc->sc_desc[i];
2166 if (dd->buf == p)
2167 break;
2168 }
2169 if (i >= sc->sc_desc_used)
2170 return;
2171 bus_dmamap_unload(sc->sc_dmat, dd->dmamap);
2172 bus_dmamap_destroy(sc->sc_dmat, dd->dmamap);
2173 }
2174
2175 static paddr_t
2176 dbri_mappage(void *v, void *mem, off_t off, int prot)
2177 {
2178 struct dbri_softc *sc = v;
2179 int current;
2180
2181 if (off < 0)
2182 return -1;
2183
2184 current = 0;
2185 while ((current < sc->sc_desc_used) &&
2186 (sc->sc_desc[current].buf != mem))
2187 current++;
2188
2189 if (current < sc->sc_desc_used) {
2190 return bus_dmamem_mmap(sc->sc_dmat,
2191 &sc->sc_desc[current].dmaseg, 1, off, prot, BUS_DMA_WAITOK);
2192 }
2193
2194 return -1;
2195 }
2196
2197 static int
2198 dbri_open(void *cookie, int flags)
2199 {
2200 struct dbri_softc *sc = cookie;
2201
2202 DPRINTF("%s: %d\n", __func__, sc->sc_refcount);
2203
2204 if (sc->sc_refcount == 0)
2205 dbri_bring_up(sc);
2206
2207 sc->sc_refcount++;
2208
2209 return 0;
2210 }
2211
2212 static void
2213 dbri_close(void *cookie)
2214 {
2215 struct dbri_softc *sc = cookie;
2216
2217 DPRINTF("%s: %d\n", __func__, sc->sc_refcount);
2218
2219 sc->sc_refcount--;
2220 KASSERT(sc->sc_refcount >= 0);
2221 if (sc->sc_refcount > 0)
2222 return;
2223
2224 dbri_set_power(sc, 0);
2225 sc->sc_playing = 0;
2226 sc->sc_recording = 0;
2227 }
2228
2229 static bool
2230 dbri_suspend(device_t self, const pmf_qual_t *qual)
2231 {
2232 struct dbri_softc *sc = device_private(self);
2233
2234 mutex_spin_enter(&sc->sc_intr_lock);
2235 dbri_set_power(sc, 0);
2236 mutex_spin_exit(&sc->sc_intr_lock);
2237 return true;
2238 }
2239
2240 static bool
2241 dbri_resume(device_t self, const pmf_qual_t *qual)
2242 {
2243 struct dbri_softc *sc = device_private(self);
2244
2245 if (sc->sc_powerstate != 0)
2246 return true;
2247 aprint_verbose("resume: %d\n", sc->sc_refcount);
2248 if (sc->sc_playing) {
2249 volatile uint32_t *cmd;
2250
2251 mutex_spin_enter(&sc->sc_intr_lock);
2252 dbri_bring_up(sc);
2253 cmd = dbri_command_lock(sc);
2254 *(cmd++) = DBRI_CMD(DBRI_COMMAND_SDP,
2255 0, sc->sc_pipe[4].sdp |
2256 DBRI_SDP_VALID_POINTER |
2257 DBRI_SDP_EVERY | DBRI_SDP_CLEAR);
2258 *(cmd++) = sc->sc_dmabase +
2259 dbri_dma_off(xmit, 0);
2260 dbri_command_send(sc, cmd);
2261 mutex_spin_exit(&sc->sc_intr_lock);
2262 }
2263 return true;
2264 }
2265
2266 #endif /* NAUDIO > 0 */
2267