ess.c revision 1.44 1 /* $NetBSD: ess.c,v 1.44 1999/03/19 12:40:21 mycroft Exp $ */
2
3 /*
4 * Copyright 1997
5 * Digital Equipment Corporation. All rights reserved.
6 *
7 * This software is furnished under license and may be used and
8 * copied only in accordance with the following terms and conditions.
9 * Subject to these conditions, you may download, copy, install,
10 * use, modify and distribute this software in source and/or binary
11 * form. No title or ownership is transferred hereby.
12 *
13 * 1) Any source code used, modified or distributed must reproduce
14 * and retain this copyright notice and list of conditions as
15 * they appear in the source file.
16 *
17 * 2) No right is granted to use any trade name, trademark, or logo of
18 * Digital Equipment Corporation. Neither the "Digital Equipment
19 * Corporation" name nor any trademark or logo of Digital Equipment
20 * Corporation may be used to endorse or promote products derived
21 * from this software without the prior written permission of
22 * Digital Equipment Corporation.
23 *
24 * 3) This software is provided "AS-IS" and any express or implied
25 * warranties, including but not limited to, any implied warranties
26 * of merchantability, fitness for a particular purpose, or
27 * non-infringement are disclaimed. In no event shall DIGITAL be
28 * liable for any damages whatsoever, and in particular, DIGITAL
29 * shall not be liable for special, indirect, consequential, or
30 * incidental damages or damages for lost profits, loss of
31 * revenue or loss of use, whether such damages arise in contract,
32 * negligence, tort, under statute, in equity, at law or otherwise,
33 * even if advised of the possibility of such damage.
34 */
35
36 /*
37 **++
38 **
39 ** ess.c
40 **
41 ** FACILITY:
42 **
43 ** DIGITAL Network Appliance Reference Design (DNARD)
44 **
45 ** MODULE DESCRIPTION:
46 **
47 ** This module contains the device driver for the ESS
48 ** Technologies 1888/1887/888 sound chip. The code in sbdsp.c was
49 ** used as a reference point when implementing this driver.
50 **
51 ** AUTHORS:
52 **
53 ** Blair Fidler Software Engineering Australia
54 ** Gold Coast, Australia.
55 **
56 ** CREATION DATE:
57 **
58 ** March 10, 1997.
59 **
60 ** MODIFICATION HISTORY:
61 **
62 ** Heavily modified by Lennart Augustsson and Charles M. Hannum for
63 ** bus_dma, changes to audio interface, and many bug fixes.
64 ** ESS1788 support by Nathan J. Williams and Charles M. Hannum.
65 **--
66 */
67
68 #include <sys/param.h>
69 #include <sys/systm.h>
70 #include <sys/errno.h>
71 #include <sys/ioctl.h>
72 #include <sys/syslog.h>
73 #include <sys/device.h>
74 #include <sys/proc.h>
75 #include <sys/kernel.h>
76
77 #include <machine/cpu.h>
78 #include <machine/intr.h>
79 #include <machine/bus.h>
80
81 #include <sys/audioio.h>
82 #include <dev/audio_if.h>
83 #include <dev/auconv.h>
84 #include <dev/mulaw.h>
85
86 #include <dev/isa/isavar.h>
87 #include <dev/isa/isadmavar.h>
88
89 #include <dev/isa/essvar.h>
90 #include <dev/isa/essreg.h>
91
92 #ifdef AUDIO_DEBUG
93 #define DPRINTF(x) if (essdebug) printf x
94 #define DPRINTFN(n,x) if (essdebug>(n)) printf x
95 int essdebug = 0;
96 #else
97 #define DPRINTF(x)
98 #define DPRINTFN(n,x)
99 #endif
100
101 #if 0
102 unsigned uuu;
103 #define EREAD1(t, h, a) (uuu=bus_space_read_1(t, h, a),printf("EREAD %02x=%02x\n", ((int)h&0xfff)+a, uuu),uuu)
104 #define EWRITE1(t, h, a, d) (printf("EWRITE %02x=%02x\n", ((int)h & 0xfff)+a, d), bus_space_write_1(t, h, a, d))
105 #else
106 #define EREAD1(t, h, a) bus_space_read_1(t, h, a)
107 #define EWRITE1(t, h, a, d) bus_space_write_1(t, h, a, d)
108 #endif
109
110
111 int ess_setup_sc __P((struct ess_softc *, int));
112
113 int ess_open __P((void *, int));
114 void ess_1788_close __P((void *));
115 void ess_1888_close __P((void *));
116 int ess_getdev __P((void *, struct audio_device *));
117 int ess_drain __P((void *));
118
119 int ess_query_encoding __P((void *, struct audio_encoding *));
120
121 int ess_set_params __P((void *, int, int, struct audio_params *,
122 struct audio_params *));
123
124 int ess_round_blocksize __P((void *, int));
125
126 int ess_audio1_trigger_output __P((void *, void *, void *, int,
127 void (*)(void *), void *, struct audio_params *));
128 int ess_audio2_trigger_output __P((void *, void *, void *, int,
129 void (*)(void *), void *, struct audio_params *));
130 int ess_audio1_trigger_input __P((void *, void *, void *, int,
131 void (*)(void *), void *, struct audio_params *));
132 int ess_audio1_halt __P((void *));
133 int ess_audio2_halt __P((void *));
134 int ess_audio1_intr __P((void *));
135 int ess_audio2_intr __P((void *));
136 void ess_audio1_poll __P((void *));
137 void ess_audio2_poll __P((void *));
138
139 int ess_speaker_ctl __P((void *, int));
140
141 int ess_getdev __P((void *, struct audio_device *));
142
143 int ess_set_port __P((void *, mixer_ctrl_t *));
144 int ess_get_port __P((void *, mixer_ctrl_t *));
145
146 void *ess_malloc __P((void *, int, size_t, int, int));
147 void ess_free __P((void *, void *, int));
148 size_t ess_round_buffersize __P((void *, int, size_t));
149 int ess_mappage __P((void *, void *, int, int));
150
151
152 int ess_query_devinfo __P((void *, mixer_devinfo_t *));
153 int ess_1788_get_props __P((void *));
154 int ess_1888_get_props __P((void *));
155
156 void ess_speaker_on __P((struct ess_softc *));
157 void ess_speaker_off __P((struct ess_softc *));
158
159 int ess_config_addr __P((struct ess_softc *));
160 void ess_config_irq __P((struct ess_softc *));
161 void ess_config_drq __P((struct ess_softc *));
162 void ess_setup __P((struct ess_softc *));
163 int ess_identify __P((struct ess_softc *));
164
165 int ess_reset __P((struct ess_softc *));
166 void ess_set_gain __P((struct ess_softc *, int, int));
167 int ess_set_in_port __P((struct ess_softc *, int));
168 int ess_set_in_ports __P((struct ess_softc *, int));
169 u_int ess_srtotc __P((u_int));
170 u_int ess_srtofc __P((u_int));
171 u_char ess_get_dsp_status __P((struct ess_softc *));
172 u_char ess_dsp_read_ready __P((struct ess_softc *));
173 u_char ess_dsp_write_ready __P((struct ess_softc *sc));
174 int ess_rdsp __P((struct ess_softc *));
175 int ess_wdsp __P((struct ess_softc *, u_char));
176 u_char ess_read_x_reg __P((struct ess_softc *, u_char));
177 int ess_write_x_reg __P((struct ess_softc *, u_char, u_char));
178 void ess_clear_xreg_bits __P((struct ess_softc *, u_char, u_char));
179 void ess_set_xreg_bits __P((struct ess_softc *, u_char, u_char));
180 u_char ess_read_mix_reg __P((struct ess_softc *, u_char));
181 void ess_write_mix_reg __P((struct ess_softc *, u_char, u_char));
182 void ess_clear_mreg_bits __P((struct ess_softc *, u_char, u_char));
183 void ess_set_mreg_bits __P((struct ess_softc *, u_char, u_char));
184
185 static char *essmodel[] = {
186 "unsupported",
187 "1888",
188 "1887",
189 "888",
190 "1788"
191 };
192
193 struct audio_device ess_device = {
194 "ESS Technology",
195 "x",
196 "ess"
197 };
198
199 /*
200 * Define our interface to the higher level audio driver.
201 */
202
203 struct audio_hw_if ess_1788_hw_if = {
204 ess_open,
205 ess_1788_close,
206 ess_drain,
207 ess_query_encoding,
208 ess_set_params,
209 ess_round_blocksize,
210 NULL,
211 NULL,
212 NULL,
213 NULL,
214 NULL,
215 ess_audio1_halt,
216 ess_audio1_halt,
217 ess_speaker_ctl,
218 ess_getdev,
219 NULL,
220 ess_set_port,
221 ess_get_port,
222 ess_query_devinfo,
223 ess_malloc,
224 ess_free,
225 ess_round_buffersize,
226 ess_mappage,
227 ess_1788_get_props,
228 ess_audio1_trigger_output,
229 ess_audio1_trigger_input,
230 };
231
232 struct audio_hw_if ess_1888_hw_if = {
233 ess_open,
234 ess_1888_close,
235 ess_drain,
236 ess_query_encoding,
237 ess_set_params,
238 ess_round_blocksize,
239 NULL,
240 NULL,
241 NULL,
242 NULL,
243 NULL,
244 ess_audio2_halt,
245 ess_audio1_halt,
246 ess_speaker_ctl,
247 ess_getdev,
248 NULL,
249 ess_set_port,
250 ess_get_port,
251 ess_query_devinfo,
252 ess_malloc,
253 ess_free,
254 ess_round_buffersize,
255 ess_mappage,
256 ess_1888_get_props,
257 ess_audio2_trigger_output,
258 ess_audio1_trigger_input,
259 };
260
261 #ifdef AUDIO_DEBUG
262 void ess_printsc __P((struct ess_softc *));
263 void ess_dump_mixer __P((struct ess_softc *));
264
265 void
266 ess_printsc(sc)
267 struct ess_softc *sc;
268 {
269 int i;
270
271 printf("open %d iobase 0x%x outport %u inport %u speaker %s\n",
272 (int)sc->sc_open, sc->sc_iobase, sc->out_port,
273 sc->in_port, sc->spkr_state ? "on" : "off");
274
275 printf("audio1: dmachan %d irq %d nintr %lu intr %p arg %p\n",
276 sc->sc_audio1.drq, sc->sc_audio1.irq, sc->sc_audio1.nintr,
277 sc->sc_audio1.intr, sc->sc_audio1.arg);
278
279 if (sc->sc_model != ESS_1788) {
280 printf("audio2: dmachan %d irq %d nintr %lu intr %p arg %p\n",
281 sc->sc_audio2.drq, sc->sc_audio2.irq, sc->sc_audio2.nintr,
282 sc->sc_audio2.intr, sc->sc_audio2.arg);
283 }
284
285 printf("gain:");
286 for (i = 0; i < sc->ndevs; i++)
287 printf(" %u,%u", sc->gain[i][ESS_LEFT], sc->gain[i][ESS_RIGHT]);
288 printf("\n");
289 }
290
291 void
292 ess_dump_mixer(sc)
293 struct ess_softc *sc;
294 {
295 printf("ESS_DAC_PLAY_VOL: mix reg 0x%02x=0x%02x\n",
296 0x7C, ess_read_mix_reg(sc, 0x7C));
297 printf("ESS_MIC_PLAY_VOL: mix reg 0x%02x=0x%02x\n",
298 0x1A, ess_read_mix_reg(sc, 0x1A));
299 printf("ESS_LINE_PLAY_VOL: mix reg 0x%02x=0x%02x\n",
300 0x3E, ess_read_mix_reg(sc, 0x3E));
301 printf("ESS_SYNTH_PLAY_VOL: mix reg 0x%02x=0x%02x\n",
302 0x36, ess_read_mix_reg(sc, 0x36));
303 printf("ESS_CD_PLAY_VOL: mix reg 0x%02x=0x%02x\n",
304 0x38, ess_read_mix_reg(sc, 0x38));
305 printf("ESS_AUXB_PLAY_VOL: mix reg 0x%02x=0x%02x\n",
306 0x3A, ess_read_mix_reg(sc, 0x3A));
307 printf("ESS_MASTER_VOL: mix reg 0x%02x=0x%02x\n",
308 0x32, ess_read_mix_reg(sc, 0x32));
309 printf("ESS_PCSPEAKER_VOL: mix reg 0x%02x=0x%02x\n",
310 0x3C, ess_read_mix_reg(sc, 0x3C));
311 printf("ESS_DAC_REC_VOL: mix reg 0x%02x=0x%02x\n",
312 0x69, ess_read_mix_reg(sc, 0x69));
313 printf("ESS_MIC_REC_VOL: mix reg 0x%02x=0x%02x\n",
314 0x68, ess_read_mix_reg(sc, 0x68));
315 printf("ESS_LINE_REC_VOL: mix reg 0x%02x=0x%02x\n",
316 0x6E, ess_read_mix_reg(sc, 0x6E));
317 printf("ESS_SYNTH_REC_VOL: mix reg 0x%02x=0x%02x\n",
318 0x6B, ess_read_mix_reg(sc, 0x6B));
319 printf("ESS_CD_REC_VOL: mix reg 0x%02x=0x%02x\n",
320 0x6A, ess_read_mix_reg(sc, 0x6A));
321 printf("ESS_AUXB_REC_VOL: mix reg 0x%02x=0x%02x\n",
322 0x6C, ess_read_mix_reg(sc, 0x6C));
323 printf("ESS_RECORD_VOL: x reg 0x%02x=0x%02x\n",
324 0xB4, ess_read_x_reg(sc, 0xB4));
325 printf("Audio 1 play vol (unused): mix reg 0x%02x=0x%02x\n",
326 0x14, ess_read_mix_reg(sc, 0x14));
327
328 printf("ESS_MIC_PREAMP: x reg 0x%02x=0x%02x\n",
329 ESS_XCMD_PREAMP_CTRL, ess_read_x_reg(sc, ESS_XCMD_PREAMP_CTRL));
330 printf("ESS_RECORD_MONITOR: x reg 0x%02x=0x%02x\n",
331 ESS_XCMD_AUDIO_CTRL, ess_read_x_reg(sc, ESS_XCMD_AUDIO_CTRL));
332 printf("Record source: mix reg 0x%02x=0x%02x, 0x%02x=0x%02x\n",
333 ESS_MREG_ADC_SOURCE, ess_read_mix_reg(sc, ESS_MREG_ADC_SOURCE),
334 ESS_MREG_AUDIO2_CTRL2, ess_read_mix_reg(sc, ESS_MREG_AUDIO2_CTRL2));
335 }
336
337 #endif
338
339 /*
340 * Configure the ESS chip for the desired audio base address.
341 */
342 int
343 ess_config_addr(sc)
344 struct ess_softc *sc;
345 {
346 int iobase = sc->sc_iobase;
347 bus_space_tag_t iot = sc->sc_iot;
348
349 /*
350 * Configure using the System Control Register method. This
351 * method is used when the AMODE line is tied high, which is
352 * the case for the Shark, but not for the evaluation board.
353 */
354
355 bus_space_handle_t scr_access_ioh;
356 bus_space_handle_t scr_ioh;
357 u_short scr_value;
358
359 /*
360 * Set the SCR bit to enable audio.
361 */
362 scr_value = ESS_SCR_AUDIO_ENABLE;
363
364 /*
365 * Set the SCR bits necessary to select the specified audio
366 * base address.
367 */
368 switch(iobase) {
369 case 0x220:
370 scr_value |= ESS_SCR_AUDIO_220;
371 break;
372 case 0x230:
373 scr_value |= ESS_SCR_AUDIO_230;
374 break;
375 case 0x240:
376 scr_value |= ESS_SCR_AUDIO_240;
377 break;
378 case 0x250:
379 scr_value |= ESS_SCR_AUDIO_250;
380 break;
381 default:
382 printf("ess: configured iobase 0x%x invalid\n", iobase);
383 return (1);
384 break;
385 }
386
387 /*
388 * Get a mapping for the System Control Register (SCR) access
389 * registers and the SCR data registers.
390 */
391 if (bus_space_map(iot, ESS_SCR_ACCESS_BASE, ESS_SCR_ACCESS_PORTS,
392 0, &scr_access_ioh)) {
393 printf("ess: can't map SCR access registers\n");
394 return (1);
395 }
396 if (bus_space_map(iot, ESS_SCR_BASE, ESS_SCR_PORTS,
397 0, &scr_ioh)) {
398 printf("ess: can't map SCR registers\n");
399 bus_space_unmap(iot, scr_access_ioh, ESS_SCR_ACCESS_PORTS);
400 return (1);
401 }
402
403 /* Unlock the SCR. */
404 EWRITE1(iot, scr_access_ioh, ESS_SCR_UNLOCK, 0);
405
406 /* Write the base address information into SCR[0]. */
407 EWRITE1(iot, scr_ioh, ESS_SCR_INDEX, 0);
408 EWRITE1(iot, scr_ioh, ESS_SCR_DATA, scr_value);
409
410 /* Lock the SCR. */
411 EWRITE1(iot, scr_access_ioh, ESS_SCR_LOCK, 0);
412
413 /* Unmap the SCR access ports and the SCR data ports. */
414 bus_space_unmap(iot, scr_access_ioh, ESS_SCR_ACCESS_PORTS);
415 bus_space_unmap(iot, scr_ioh, ESS_SCR_PORTS);
416
417 return 0;
418 }
419
420
421 /*
422 * Configure the ESS chip for the desired IRQ and DMA channels.
423 * ESS ISA
424 * --------
425 * IRQA irq9
426 * IRQB irq5
427 * IRQC irq7
428 * IRQD irq10
429 * IRQE irq15
430 *
431 * DRQA drq0
432 * DRQB drq1
433 * DRQC drq3
434 * DRQD drq5
435 */
436 void
437 ess_config_irq(sc)
438 struct ess_softc *sc;
439 {
440 int v;
441
442 DPRINTFN(2,("ess_config_irq\n"));
443
444 if (sc->sc_model == ESS_1887 &&
445 sc->sc_audio1.irq == sc->sc_audio2.irq &&
446 sc->sc_audio1.irq != -1) {
447 /* Use new method, both interrupts are the same. */
448 v = ESS_IS_SELECT_IRQ; /* enable intrs */
449 switch (sc->sc_audio1.irq) {
450 case 5:
451 v |= ESS_IS_INTRB;
452 break;
453 case 7:
454 v |= ESS_IS_INTRC;
455 break;
456 case 9:
457 v |= ESS_IS_INTRA;
458 break;
459 case 10:
460 v |= ESS_IS_INTRD;
461 break;
462 case 15:
463 v |= ESS_IS_INTRE;
464 break;
465 #ifdef DIAGNOSTIC
466 default:
467 printf("ess_config_irq: configured irq %d not supported for Audio 1\n",
468 sc->sc_audio1.irq);
469 return;
470 #endif
471 }
472 /* Set the IRQ */
473 ess_write_mix_reg(sc, ESS_MREG_INTR_ST, v);
474 return;
475 }
476
477 if (sc->sc_model == ESS_1887) {
478 /* Tell the 1887 to use the old interrupt method. */
479 ess_write_mix_reg(sc, ESS_MREG_INTR_ST, ESS_IS_ES1888);
480 }
481
482 if (sc->sc_audio1.polled) {
483 /* Turn off Audio1 interrupts. */
484 v = 0;
485 } else {
486 /* Configure Audio 1 for the appropriate IRQ line. */
487 v = ESS_IRQ_CTRL_MASK | ESS_IRQ_CTRL_EXT; /* All intrs on */
488 switch (sc->sc_audio1.irq) {
489 case 5:
490 v |= ESS_IRQ_CTRL_INTRB;
491 break;
492 case 7:
493 v |= ESS_IRQ_CTRL_INTRC;
494 break;
495 case 9:
496 v |= ESS_IRQ_CTRL_INTRA;
497 break;
498 case 10:
499 v |= ESS_IRQ_CTRL_INTRD;
500 break;
501 #ifdef DIAGNOSTIC
502 default:
503 printf("ess: configured irq %d not supported for Audio 1\n",
504 sc->sc_audio1.irq);
505 return;
506 #endif
507 }
508 }
509 ess_write_x_reg(sc, ESS_XCMD_IRQ_CTRL, v);
510
511 if (sc->sc_model == ESS_1788)
512 return;
513
514 if (sc->sc_audio2.polled) {
515 /* Turn off Audio2 interrupts. */
516 ess_clear_mreg_bits(sc, ESS_MREG_AUDIO2_CTRL2,
517 ESS_AUDIO2_CTRL2_IRQ2_ENABLE);
518 } else {
519 /* Audio2 is hardwired to INTRE in this mode. */
520 ess_set_mreg_bits(sc, ESS_MREG_AUDIO2_CTRL2,
521 ESS_AUDIO2_CTRL2_IRQ2_ENABLE);
522 }
523 }
524
525
526 void
527 ess_config_drq(sc)
528 struct ess_softc *sc;
529 {
530 int v;
531
532 DPRINTFN(2,("ess_config_drq\n"));
533
534 /* Configure Audio 1 (record) for DMA on the appropriate channel. */
535 v = ESS_DRQ_CTRL_PU | ESS_DRQ_CTRL_EXT;
536 switch (sc->sc_audio1.drq) {
537 case 0:
538 v |= ESS_DRQ_CTRL_DRQA;
539 break;
540 case 1:
541 v |= ESS_DRQ_CTRL_DRQB;
542 break;
543 case 3:
544 v |= ESS_DRQ_CTRL_DRQC;
545 break;
546 #ifdef DIAGNOSTIC
547 default:
548 printf("ess_config_drq: configured dma chan %d not supported for Audio 1\n",
549 sc->sc_audio1.drq);
550 return;
551 #endif
552 }
553 /* Set DRQ1 */
554 ess_write_x_reg(sc, ESS_XCMD_DRQ_CTRL, v);
555
556 if (sc->sc_model == ESS_1788)
557 return;
558
559 /* Configure DRQ2 */
560 v = ESS_AUDIO2_CTRL3_DRQ_PD;
561 switch (sc->sc_audio2.drq) {
562 case 0:
563 v |= ESS_AUDIO2_CTRL3_DRQA;
564 break;
565 case 1:
566 v |= ESS_AUDIO2_CTRL3_DRQB;
567 break;
568 case 3:
569 v |= ESS_AUDIO2_CTRL3_DRQC;
570 break;
571 case 5:
572 v |= ESS_AUDIO2_CTRL3_DRQD;
573 break;
574 #ifdef DIAGNOSTIC
575 default:
576 printf("ess_config_drq: configured dma chan %d not supported for Audio 2\n",
577 sc->sc_audio2.drq);
578 return;
579 #endif
580 }
581 ess_write_mix_reg(sc, ESS_MREG_AUDIO2_CTRL3, v);
582 /* Enable DMA 2 */
583 ess_set_mreg_bits(sc, ESS_MREG_AUDIO2_CTRL2,
584 ESS_AUDIO2_CTRL2_DMA_ENABLE);
585 }
586
587 /*
588 * Set up registers after a reset.
589 */
590 void
591 ess_setup(sc)
592 struct ess_softc *sc;
593 {
594
595 ess_config_irq(sc);
596 ess_config_drq(sc);
597
598 DPRINTFN(2,("ess_setup: done\n"));
599 }
600
601 /*
602 * Determine the model of ESS chip we are talking to. Currently we
603 * only support ES1888, ES1887 and ES888. The method of determining
604 * the chip is based on the information on page 27 of the ES1887 data
605 * sheet.
606 *
607 * This routine sets the values of sc->sc_model and sc->sc_version.
608 */
609 int
610 ess_identify(sc)
611 struct ess_softc *sc;
612 {
613 u_char reg1;
614 u_char reg2;
615 u_char reg3;
616
617 sc->sc_model = ESS_UNSUPPORTED;
618 sc->sc_version = 0;
619
620
621 /*
622 * 1. Check legacy ID bytes. These should be 0x68 0x8n, where
623 * n >= 8 for an ES1887 or an ES888. Other values indicate
624 * earlier (unsupported) chips.
625 */
626 ess_wdsp(sc, ESS_ACMD_LEGACY_ID);
627
628 if ((reg1 = ess_rdsp(sc)) != 0x68) {
629 printf("ess: First ID byte wrong (0x%02x)\n", reg1);
630 return 1;
631 }
632
633 reg2 = ess_rdsp(sc);
634 if (((reg2 & 0xf0) != 0x80) ||
635 ((reg2 & 0x0f) < 8)) {
636 printf("ess: Second ID byte wrong (0x%02x)\n", reg2);
637 return 1;
638 }
639
640 /*
641 * Store the ID bytes as the version.
642 */
643 sc->sc_version = (reg1 << 8) + reg2;
644
645
646 /*
647 * 2. Verify we can change bit 2 in mixer register 0x64. This
648 * should be possible on all supported chips.
649 */
650 reg1 = ess_read_mix_reg(sc, ESS_MREG_VOLUME_CTRL);
651 reg2 = reg1 ^ 0x04; /* toggle bit 2 */
652
653 ess_write_mix_reg(sc, ESS_MREG_VOLUME_CTRL, reg2);
654
655 if (ess_read_mix_reg(sc, ESS_MREG_VOLUME_CTRL) != reg2) {
656 printf("ess: Hardware error (unable to toggle bit 2 of mixer register 0x64)\n");
657 return 1;
658 }
659
660 /*
661 * Restore the original value of mixer register 0x64.
662 */
663 ess_write_mix_reg(sc, ESS_MREG_VOLUME_CTRL, reg1);
664
665
666 /*
667 * 3. Verify we can change the value of mixer register
668 * ESS_MREG_SAMPLE_RATE.
669 * This is possible on the 1888/1887/888, but not on the 1788.
670 * It is not necessary to restore the value of this mixer register.
671 */
672 reg1 = ess_read_mix_reg(sc, ESS_MREG_SAMPLE_RATE);
673 reg2 = reg1 ^ 0xff; /* toggle all bits */
674
675 ess_write_mix_reg(sc, ESS_MREG_SAMPLE_RATE, reg2);
676
677 if (ess_read_mix_reg(sc, ESS_MREG_SAMPLE_RATE) != reg2) {
678 /* If we got this far before failing, it's a 1788. */
679 sc->sc_model = ESS_1788;
680 } else {
681 /*
682 * 4. Determine if we can change bit 5 in mixer register 0x64.
683 * This determines whether we have an ES1887:
684 *
685 * - can change indicates ES1887
686 * - can't change indicates ES1888 or ES888
687 */
688 reg1 = ess_read_mix_reg(sc, ESS_MREG_VOLUME_CTRL);
689 reg2 = reg1 ^ 0x20; /* toggle bit 5 */
690
691 ess_write_mix_reg(sc, ESS_MREG_VOLUME_CTRL, reg2);
692
693 if (ess_read_mix_reg(sc, ESS_MREG_VOLUME_CTRL) == reg2) {
694 sc->sc_model = ESS_1887;
695
696 /*
697 * Restore the original value of mixer register 0x64.
698 */
699 ess_write_mix_reg(sc, ESS_MREG_VOLUME_CTRL, reg1);
700 } else {
701 /*
702 * 5. Determine if we can change the value of mixer
703 * register 0x69 independently of mixer register
704 * 0x68. This determines which chip we have:
705 *
706 * - can modify idependently indicates ES888
707 * - register 0x69 is an alias of 0x68 indicates ES1888
708 */
709 reg1 = ess_read_mix_reg(sc, 0x68);
710 reg2 = ess_read_mix_reg(sc, 0x69);
711 reg3 = reg2 ^ 0xff; /* toggle all bits */
712
713 /*
714 * Write different values to each register.
715 */
716 ess_write_mix_reg(sc, 0x68, reg2);
717 ess_write_mix_reg(sc, 0x69, reg3);
718
719 if (ess_read_mix_reg(sc, 0x68) == reg2 &&
720 ess_read_mix_reg(sc, 0x69) == reg3)
721 sc->sc_model = ESS_888;
722 else
723 sc->sc_model = ESS_1888;
724
725 /*
726 * Restore the original value of the registers.
727 */
728 ess_write_mix_reg(sc, 0x68, reg1);
729 ess_write_mix_reg(sc, 0x69, reg2);
730 }
731 }
732
733 return 0;
734 }
735
736
737 int
738 ess_setup_sc(sc, doinit)
739 struct ess_softc *sc;
740 int doinit;
741 {
742 /* Reset the chip. */
743 if (ess_reset(sc) != 0) {
744 DPRINTF(("ess_setup_sc: couldn't reset chip\n"));
745 return (1);
746 }
747
748 /* Identify the ESS chip, and check that it is supported. */
749 if (ess_identify(sc)) {
750 DPRINTF(("ess_setup_sc: couldn't identify\n"));
751 return (1);
752 }
753
754 return (0);
755 }
756
757 /*
758 * Probe for the ESS hardware.
759 */
760 int
761 essmatch(sc)
762 struct ess_softc *sc;
763 {
764 if (!ESS_BASE_VALID(sc->sc_iobase)) {
765 printf("ess: configured iobase 0x%x invalid\n", sc->sc_iobase);
766 return (0);
767 }
768
769 /* Configure the ESS chip for the desired audio base address. */
770 if (ess_config_addr(sc))
771 return (0);
772
773 if (ess_setup_sc(sc, 1))
774 return (0);
775
776 if (sc->sc_model == ESS_UNSUPPORTED) {
777 DPRINTF(("ess: Unsupported model\n"));
778 return (0);
779 }
780
781 /* Check that requested DMA channels are valid and different. */
782 if (!ESS_DRQ1_VALID(sc->sc_audio1.drq)) {
783 printf("ess: record drq %d invalid\n", sc->sc_audio1.drq);
784 return (0);
785 }
786 if (!isa_drq_isfree(sc->sc_ic, sc->sc_audio1.drq))
787 return (0);
788 if (sc->sc_model != ESS_1788) {
789 if (!ESS_DRQ2_VALID(sc->sc_audio2.drq)) {
790 printf("ess: play drq %d invalid\n", sc->sc_audio2.drq);
791 return (0);
792 }
793 if (sc->sc_audio1.drq == sc->sc_audio2.drq) {
794 printf("ess: play and record drq both %d\n",
795 sc->sc_audio1.drq);
796 return (0);
797 }
798 if (!isa_drq_isfree(sc->sc_ic, sc->sc_audio2.drq))
799 return (0);
800 }
801
802 /*
803 * The 1887 has an additional IRQ mode where both channels are mapped
804 * to the same IRQ.
805 */
806 if (sc->sc_model == ESS_1887 &&
807 sc->sc_audio1.irq == sc->sc_audio2.irq &&
808 sc->sc_audio1.irq != -1 &&
809 ESS_IRQ12_VALID(sc->sc_audio1.irq))
810 goto irq_not1888;
811
812 /* Check that requested IRQ lines are valid and different. */
813 if (sc->sc_audio1.irq != -1 &&
814 !ESS_IRQ1_VALID(sc->sc_audio1.irq)) {
815 printf("ess: record irq %d invalid\n", sc->sc_audio1.irq);
816 return (0);
817 }
818 if (sc->sc_model != ESS_1788) {
819 if (sc->sc_audio2.irq != -1 &&
820 !ESS_IRQ2_VALID(sc->sc_audio2.irq)) {
821 printf("ess: play irq %d invalid\n", sc->sc_audio2.irq);
822 return (0);
823 }
824 if (sc->sc_audio1.irq == sc->sc_audio2.irq &&
825 sc->sc_audio1.irq != -1) {
826 printf("ess: play and record irq both %d\n",
827 sc->sc_audio1.irq);
828 return (0);
829 }
830 }
831
832 irq_not1888:
833 /* XXX should we check IRQs as well? */
834
835 return (1);
836 }
837
838
839 /*
840 * Attach hardware to driver, attach hardware driver to audio
841 * pseudo-device driver.
842 */
843 void
844 essattach(sc)
845 struct ess_softc *sc;
846 {
847 struct audio_attach_args arg;
848 struct audio_params pparams, rparams;
849 int i;
850 u_int v;
851
852 if (ess_setup_sc(sc, 0)) {
853 printf(": setup failed\n");
854 return;
855 }
856
857 printf(": ESS Technology ES%s [version 0x%04x]\n",
858 essmodel[sc->sc_model], sc->sc_version);
859
860 sc->sc_audio1.irq = -1;
861 sc->sc_audio2.irq = -1;
862
863 sc->sc_audio1.polled = sc->sc_audio1.irq == -1;
864 if (!sc->sc_audio1.polled) {
865 sc->sc_audio1.ih = isa_intr_establish(sc->sc_ic,
866 sc->sc_audio1.irq, sc->sc_audio1.ist, IPL_AUDIO,
867 ess_audio1_intr, sc);
868 printf("%s: audio1 interrupting at irq %d\n",
869 sc->sc_dev.dv_xname, sc->sc_audio1.irq);
870 } else
871 printf("%s: audio1 polled\n", sc->sc_dev.dv_xname);
872 if (isa_dmamap_create(sc->sc_ic, sc->sc_audio1.drq,
873 MAX_ISADMA, BUS_DMA_NOWAIT|BUS_DMA_ALLOCNOW)) {
874 printf("%s: can't create map for drq %d\n",
875 sc->sc_dev.dv_xname, sc->sc_audio1.drq);
876 return;
877 }
878
879 if (sc->sc_model != ESS_1788) {
880 sc->sc_audio2.polled = sc->sc_audio2.irq == -1;
881 if (!sc->sc_audio2.polled) {
882 sc->sc_audio2.ih = isa_intr_establish(sc->sc_ic,
883 sc->sc_audio2.irq, sc->sc_audio2.ist, IPL_AUDIO,
884 ess_audio2_intr, sc);
885 printf("%s: audio2 interrupting at irq %d\n",
886 sc->sc_dev.dv_xname, sc->sc_audio2.irq);
887 } else
888 printf("%s: audio2 polled\n", sc->sc_dev.dv_xname);
889 if (isa_dmamap_create(sc->sc_ic, sc->sc_audio2.drq,
890 MAX_ISADMA, BUS_DMA_NOWAIT|BUS_DMA_ALLOCNOW)) {
891 printf("%s: can't create map for drq %d\n",
892 sc->sc_dev.dv_xname, sc->sc_audio2.drq);
893 return;
894 }
895 }
896
897 /*
898 * Set record and play parameters to default values defined in
899 * generic audio driver.
900 */
901 pparams = audio_default;
902 rparams = audio_default;
903 ess_set_params(sc, AUMODE_RECORD|AUMODE_PLAY, 0, &pparams, &rparams);
904
905 /* Do a hardware reset on the mixer. */
906 ess_write_mix_reg(sc, ESS_MIX_RESET, ESS_MIX_RESET);
907
908 /*
909 * Set volume of Audio 1 to zero and disable Audio 1 DAC input
910 * to playback mixer, since playback is always through Audio 2.
911 */
912 if (sc->sc_model != ESS_1788)
913 ess_write_mix_reg(sc, ESS_MREG_VOLUME_VOICE, 0);
914 ess_wdsp(sc, ESS_ACMD_DISABLE_SPKR);
915
916 if (sc->sc_model == ESS_1788) {
917 ess_write_mix_reg(sc, ESS_MREG_ADC_SOURCE, ESS_SOURCE_MIC);
918 sc->in_port = ESS_SOURCE_MIC;
919 sc->ndevs = ESS_1788_NDEVS;
920 } else {
921 /*
922 * Set hardware record source to use output of the record
923 * mixer. We do the selection of record source in software by
924 * setting the gain of the unused sources to zero. (See
925 * ess_set_in_ports.)
926 */
927 ess_write_mix_reg(sc, ESS_MREG_ADC_SOURCE, ESS_SOURCE_MIXER);
928 sc->in_mask = 1 << ESS_MIC_REC_VOL;
929 sc->ndevs = ESS_1888_NDEVS;
930 ess_clear_mreg_bits(sc, ESS_MREG_AUDIO2_CTRL2, 0x10);
931 ess_set_mreg_bits(sc, ESS_MREG_AUDIO2_CTRL2, 0x08);
932 }
933
934 /*
935 * Set gain on each mixer device to a sensible value.
936 * Devices not normally used are turned off, and other devices
937 * are set to 50% volume.
938 */
939 for (i = 0; i < sc->ndevs; i++) {
940 switch (i) {
941 case ESS_MIC_PLAY_VOL:
942 case ESS_LINE_PLAY_VOL:
943 case ESS_CD_PLAY_VOL:
944 case ESS_AUXB_PLAY_VOL:
945 case ESS_DAC_REC_VOL:
946 case ESS_LINE_REC_VOL:
947 case ESS_SYNTH_REC_VOL:
948 case ESS_CD_REC_VOL:
949 case ESS_AUXB_REC_VOL:
950 v = 0;
951 break;
952 default:
953 v = ESS_4BIT_GAIN(AUDIO_MAX_GAIN / 2);
954 break;
955 }
956 sc->gain[i][ESS_LEFT] = sc->gain[i][ESS_RIGHT] = v;
957 ess_set_gain(sc, i, 1);
958 }
959
960 ess_setup(sc);
961
962 /* Disable the speaker until the device is opened. */
963 ess_speaker_off(sc);
964 sc->spkr_state = SPKR_OFF;
965
966 sprintf(ess_device.name, "ES%s", essmodel[sc->sc_model]);
967 sprintf(ess_device.version, "0x%04x", sc->sc_version);
968
969 if (sc->sc_model == ESS_1788)
970 audio_attach_mi(&ess_1788_hw_if, sc, &sc->sc_dev);
971 else
972 audio_attach_mi(&ess_1888_hw_if, sc, &sc->sc_dev);
973
974 arg.type = AUDIODEV_TYPE_OPL;
975 arg.hwif = 0;
976 arg.hdl = 0;
977 (void)config_found(&sc->sc_dev, &arg, audioprint);
978
979 #ifdef AUDIO_DEBUG
980 if (essdebug > 0)
981 ess_printsc(sc);
982 #endif
983 }
984
985 /*
986 * Various routines to interface to higher level audio driver
987 */
988
989 int
990 ess_open(addr, flags)
991 void *addr;
992 int flags;
993 {
994 struct ess_softc *sc = addr;
995
996 DPRINTF(("ess_open: sc=%p\n", sc));
997
998 if (sc->sc_open != 0 || ess_reset(sc) != 0)
999 return ENXIO;
1000
1001 ess_setup(sc); /* because we did a reset */
1002
1003 sc->sc_open = 1;
1004
1005 DPRINTF(("ess_open: opened\n"));
1006
1007 return (0);
1008 }
1009
1010 void
1011 ess_1788_close(addr)
1012 void *addr;
1013 {
1014 struct ess_softc *sc = addr;
1015
1016 DPRINTF(("ess_1788_close: sc=%p\n", sc));
1017
1018 ess_speaker_off(sc);
1019 sc->spkr_state = SPKR_OFF;
1020
1021 ess_audio1_halt(sc);
1022
1023 sc->sc_open = 0;
1024 DPRINTF(("ess_1788_close: closed\n"));
1025 }
1026
1027 void
1028 ess_1888_close(addr)
1029 void *addr;
1030 {
1031 struct ess_softc *sc = addr;
1032
1033 DPRINTF(("ess_1888_close: sc=%p\n", sc));
1034
1035 ess_speaker_off(sc);
1036 sc->spkr_state = SPKR_OFF;
1037
1038 ess_audio1_halt(sc);
1039 ess_audio2_halt(sc);
1040
1041 sc->sc_open = 0;
1042 DPRINTF(("ess_1888_close: closed\n"));
1043 }
1044
1045 /*
1046 * Wait for FIFO to drain, and analog section to settle.
1047 * XXX should check FIFO empty bit.
1048 */
1049 int
1050 ess_drain(addr)
1051 void *addr;
1052 {
1053 tsleep(addr, PWAIT | PCATCH, "essdr", hz/20); /* XXX */
1054 return (0);
1055 }
1056
1057 /* XXX should use reference count */
1058 int
1059 ess_speaker_ctl(addr, newstate)
1060 void *addr;
1061 int newstate;
1062 {
1063 struct ess_softc *sc = addr;
1064
1065 if ((newstate == SPKR_ON) && (sc->spkr_state == SPKR_OFF)) {
1066 ess_speaker_on(sc);
1067 sc->spkr_state = SPKR_ON;
1068 }
1069 if ((newstate == SPKR_OFF) && (sc->spkr_state == SPKR_ON)) {
1070 ess_speaker_off(sc);
1071 sc->spkr_state = SPKR_OFF;
1072 }
1073 return (0);
1074 }
1075
1076 int
1077 ess_getdev(addr, retp)
1078 void *addr;
1079 struct audio_device *retp;
1080 {
1081 *retp = ess_device;
1082 return (0);
1083 }
1084
1085 int
1086 ess_query_encoding(addr, fp)
1087 void *addr;
1088 struct audio_encoding *fp;
1089 {
1090 /*struct ess_softc *sc = addr;*/
1091
1092 switch (fp->index) {
1093 case 0:
1094 strcpy(fp->name, AudioEulinear);
1095 fp->encoding = AUDIO_ENCODING_ULINEAR;
1096 fp->precision = 8;
1097 fp->flags = 0;
1098 return (0);
1099 case 1:
1100 strcpy(fp->name, AudioEmulaw);
1101 fp->encoding = AUDIO_ENCODING_ULAW;
1102 fp->precision = 8;
1103 fp->flags = AUDIO_ENCODINGFLAG_EMULATED;
1104 return (0);
1105 case 2:
1106 strcpy(fp->name, AudioEalaw);
1107 fp->encoding = AUDIO_ENCODING_ALAW;
1108 fp->precision = 8;
1109 fp->flags = AUDIO_ENCODINGFLAG_EMULATED;
1110 return (0);
1111 case 3:
1112 strcpy(fp->name, AudioEslinear);
1113 fp->encoding = AUDIO_ENCODING_SLINEAR;
1114 fp->precision = 8;
1115 fp->flags = 0;
1116 return (0);
1117 case 4:
1118 strcpy(fp->name, AudioEslinear_le);
1119 fp->encoding = AUDIO_ENCODING_SLINEAR_LE;
1120 fp->precision = 16;
1121 fp->flags = 0;
1122 return (0);
1123 case 5:
1124 strcpy(fp->name, AudioEulinear_le);
1125 fp->encoding = AUDIO_ENCODING_ULINEAR_LE;
1126 fp->precision = 16;
1127 fp->flags = 0;
1128 return (0);
1129 case 6:
1130 strcpy(fp->name, AudioEslinear_be);
1131 fp->encoding = AUDIO_ENCODING_SLINEAR_BE;
1132 fp->precision = 16;
1133 fp->flags = AUDIO_ENCODINGFLAG_EMULATED;
1134 return (0);
1135 case 7:
1136 strcpy(fp->name, AudioEulinear_be);
1137 fp->encoding = AUDIO_ENCODING_ULINEAR_BE;
1138 fp->precision = 16;
1139 fp->flags = AUDIO_ENCODINGFLAG_EMULATED;
1140 return (0);
1141 default:
1142 return EINVAL;
1143 }
1144 return (0);
1145 }
1146
1147 int
1148 ess_set_params(addr, setmode, usemode, play, rec)
1149 void *addr;
1150 int setmode, usemode;
1151 struct audio_params *play, *rec;
1152 {
1153 struct ess_softc *sc = addr;
1154 struct audio_params *p;
1155 int mode;
1156 int rate;
1157
1158 DPRINTF(("ess_set_params: set=%d use=%d\n", setmode, usemode));
1159
1160 /*
1161 * The ES1887 manual (page 39, `Full-Duplex DMA Mode') claims that in
1162 * full-duplex operation the sample rates must be the same for both
1163 * channels. This appears to be false; the only bit in common is the
1164 * clock source selection. However, we'll be conservative here.
1165 * - mycroft
1166 */
1167 if (play->sample_rate != rec->sample_rate &&
1168 usemode == (AUMODE_PLAY | AUMODE_RECORD)) {
1169 if (setmode == AUMODE_PLAY) {
1170 rec->sample_rate = play->sample_rate;
1171 setmode |= AUMODE_RECORD;
1172 } else if (setmode == AUMODE_RECORD) {
1173 play->sample_rate = rec->sample_rate;
1174 setmode |= AUMODE_PLAY;
1175 } else
1176 return (EINVAL);
1177 }
1178
1179 for (mode = AUMODE_RECORD; mode != -1;
1180 mode = mode == AUMODE_RECORD ? AUMODE_PLAY : -1) {
1181 if ((setmode & mode) == 0)
1182 continue;
1183
1184 p = mode == AUMODE_PLAY ? play : rec;
1185
1186 if (p->sample_rate < ESS_MINRATE ||
1187 p->sample_rate > ESS_MAXRATE ||
1188 (p->precision != 8 && p->precision != 16) ||
1189 (p->channels != 1 && p->channels != 2))
1190 return (EINVAL);
1191
1192 p->factor = 1;
1193 p->sw_code = 0;
1194 switch (p->encoding) {
1195 case AUDIO_ENCODING_SLINEAR_BE:
1196 case AUDIO_ENCODING_ULINEAR_BE:
1197 if (p->precision == 16)
1198 p->sw_code = swap_bytes;
1199 break;
1200 case AUDIO_ENCODING_SLINEAR_LE:
1201 case AUDIO_ENCODING_ULINEAR_LE:
1202 break;
1203 case AUDIO_ENCODING_ULAW:
1204 if (mode == AUMODE_PLAY) {
1205 p->factor = 2;
1206 p->sw_code = mulaw_to_ulinear16;
1207 } else
1208 p->sw_code = ulinear8_to_mulaw;
1209 break;
1210 case AUDIO_ENCODING_ALAW:
1211 if (mode == AUMODE_PLAY) {
1212 p->factor = 2;
1213 p->sw_code = alaw_to_ulinear16;
1214 } else
1215 p->sw_code = ulinear8_to_alaw;
1216 break;
1217 default:
1218 return (EINVAL);
1219 }
1220 }
1221
1222 if (usemode == AUMODE_RECORD)
1223 rate = rec->sample_rate;
1224 else
1225 rate = play->sample_rate;
1226
1227 ess_write_x_reg(sc, ESS_XCMD_SAMPLE_RATE, ess_srtotc(rate));
1228 ess_write_x_reg(sc, ESS_XCMD_FILTER_CLOCK, ess_srtofc(rate));
1229
1230 if (sc->sc_model != ESS_1788) {
1231 ess_write_mix_reg(sc, ESS_MREG_SAMPLE_RATE, ess_srtotc(rate));
1232 ess_write_mix_reg(sc, ESS_MREG_FILTER_CLOCK, ess_srtofc(rate));
1233 }
1234
1235 return (0);
1236 }
1237
1238 int
1239 ess_audio1_trigger_output(addr, start, end, blksize, intr, arg, param)
1240 void *addr;
1241 void *start, *end;
1242 int blksize;
1243 void (*intr) __P((void *));
1244 void *arg;
1245 struct audio_params *param;
1246 {
1247 struct ess_softc *sc = addr;
1248 u_int8_t reg;
1249
1250 DPRINTFN(1, ("ess_audio1_trigger_output: sc=%p start=%p end=%p blksize=%d intr=%p(%p)\n",
1251 addr, start, end, blksize, intr, arg));
1252
1253 if (sc->sc_audio1.active)
1254 panic("ess_audio1_trigger_output: already running");
1255
1256 sc->sc_audio1.active = 1;
1257 sc->sc_audio1.intr = intr;
1258 sc->sc_audio1.arg = arg;
1259 if (sc->sc_audio1.polled) {
1260 sc->sc_audio1.dmapos = 0;
1261 sc->sc_audio1.buffersize = (char *)end - (char *)start;
1262 sc->sc_audio1.dmacount = 0;
1263 sc->sc_audio1.blksize = blksize;
1264 timeout(ess_audio1_poll, sc, hz/30);
1265 }
1266
1267 reg = ess_read_x_reg(sc, ESS_XCMD_AUDIO_CTRL);
1268 if (param->channels == 2) {
1269 reg &= ~ESS_AUDIO_CTRL_MONO;
1270 reg |= ESS_AUDIO_CTRL_STEREO;
1271 } else {
1272 reg |= ESS_AUDIO_CTRL_MONO;
1273 reg &= ~ESS_AUDIO_CTRL_STEREO;
1274 }
1275 ess_write_x_reg(sc, ESS_XCMD_AUDIO_CTRL, reg);
1276
1277 reg = ess_read_x_reg(sc, ESS_XCMD_AUDIO1_CTRL1);
1278 if (param->precision * param->factor == 16)
1279 reg |= ESS_AUDIO1_CTRL1_FIFO_SIZE;
1280 else
1281 reg &= ~ESS_AUDIO1_CTRL1_FIFO_SIZE;
1282 if (param->channels == 2)
1283 reg |= ESS_AUDIO1_CTRL1_FIFO_STEREO;
1284 else
1285 reg &= ~ESS_AUDIO1_CTRL1_FIFO_STEREO;
1286 if (param->encoding == AUDIO_ENCODING_SLINEAR_BE ||
1287 param->encoding == AUDIO_ENCODING_SLINEAR_LE)
1288 reg |= ESS_AUDIO1_CTRL1_FIFO_SIGNED;
1289 else
1290 reg &= ~ESS_AUDIO1_CTRL1_FIFO_SIGNED;
1291 reg |= ESS_AUDIO1_CTRL1_FIFO_CONNECT;
1292 ess_write_x_reg(sc, ESS_XCMD_AUDIO1_CTRL1, reg);
1293
1294 isa_dmastart(sc->sc_ic, sc->sc_audio1.drq, start,
1295 (char *)end - (char *)start, NULL,
1296 DMAMODE_WRITE | DMAMODE_LOOPDEMAND, BUS_DMA_NOWAIT);
1297
1298 /* Program transfer count registers with 2's complement of count. */
1299 blksize = -blksize;
1300 ess_write_x_reg(sc, ESS_XCMD_XFER_COUNTLO, blksize);
1301 ess_write_x_reg(sc, ESS_XCMD_XFER_COUNTHI, blksize >> 8);
1302
1303 /* Use 4 bytes per output DMA. */
1304 ess_set_xreg_bits(sc, ESS_XCMD_DEMAND_CTRL, ESS_DEMAND_CTRL_DEMAND_4);
1305
1306 /* Start auto-init DMA */
1307 ess_wdsp(sc, ESS_ACMD_ENABLE_SPKR);
1308 reg = ess_read_x_reg(sc, ESS_XCMD_AUDIO1_CTRL2);
1309 reg &= ~(ESS_AUDIO1_CTRL2_DMA_READ | ESS_AUDIO1_CTRL2_ADC_ENABLE);
1310 reg |= ESS_AUDIO1_CTRL2_FIFO_ENABLE | ESS_AUDIO1_CTRL2_AUTO_INIT;
1311 ess_write_x_reg(sc, ESS_XCMD_AUDIO1_CTRL2, reg);
1312
1313 return (0);
1314 }
1315
1316 int
1317 ess_audio2_trigger_output(addr, start, end, blksize, intr, arg, param)
1318 void *addr;
1319 void *start, *end;
1320 int blksize;
1321 void (*intr) __P((void *));
1322 void *arg;
1323 struct audio_params *param;
1324 {
1325 struct ess_softc *sc = addr;
1326 u_int8_t reg;
1327
1328 DPRINTFN(1, ("ess_audio2_trigger_output: sc=%p start=%p end=%p blksize=%d intr=%p(%p)\n",
1329 addr, start, end, blksize, intr, arg));
1330
1331 if (sc->sc_audio2.active)
1332 panic("ess_audio2_trigger_output: already running");
1333
1334 sc->sc_audio2.active = 1;
1335 sc->sc_audio2.intr = intr;
1336 sc->sc_audio2.arg = arg;
1337 if (sc->sc_audio2.polled) {
1338 sc->sc_audio2.dmapos = 0;
1339 sc->sc_audio2.buffersize = (char *)end - (char *)start;
1340 sc->sc_audio2.dmacount = 0;
1341 sc->sc_audio2.blksize = blksize;
1342 timeout(ess_audio2_poll, sc, hz/30);
1343 }
1344
1345 reg = ess_read_mix_reg(sc, ESS_MREG_AUDIO2_CTRL2);
1346 if (param->precision * param->factor == 16)
1347 reg |= ESS_AUDIO2_CTRL2_FIFO_SIZE;
1348 else
1349 reg &= ~ESS_AUDIO2_CTRL2_FIFO_SIZE;
1350 if (param->channels == 2)
1351 reg |= ESS_AUDIO2_CTRL2_CHANNELS;
1352 else
1353 reg &= ~ESS_AUDIO2_CTRL2_CHANNELS;
1354 if (param->encoding == AUDIO_ENCODING_SLINEAR_BE ||
1355 param->encoding == AUDIO_ENCODING_SLINEAR_LE)
1356 reg |= ESS_AUDIO2_CTRL2_FIFO_SIGNED;
1357 else
1358 reg &= ~ESS_AUDIO2_CTRL2_FIFO_SIGNED;
1359 ess_write_mix_reg(sc, ESS_MREG_AUDIO2_CTRL2, reg);
1360
1361 isa_dmastart(sc->sc_ic, sc->sc_audio2.drq, start,
1362 (char *)end - (char *)start, NULL,
1363 DMAMODE_WRITE | DMAMODE_LOOPDEMAND, BUS_DMA_NOWAIT);
1364
1365 if (IS16BITDRQ(sc->sc_audio2.drq))
1366 blksize >>= 1; /* use word count for 16 bit DMA */
1367 /* Program transfer count registers with 2's complement of count. */
1368 blksize = -blksize;
1369 ess_write_mix_reg(sc, ESS_MREG_XFER_COUNTLO, blksize);
1370 ess_write_mix_reg(sc, ESS_MREG_XFER_COUNTHI, blksize >> 8);
1371
1372 reg = ess_read_mix_reg(sc, ESS_MREG_AUDIO2_CTRL1);
1373 if (IS16BITDRQ(sc->sc_audio2.drq))
1374 reg |= ESS_AUDIO2_CTRL1_XFER_SIZE;
1375 else
1376 reg &= ~ESS_AUDIO2_CTRL1_XFER_SIZE;
1377 reg |= ESS_AUDIO2_CTRL1_DEMAND_8;
1378 reg |= ESS_AUDIO2_CTRL1_DAC_ENABLE | ESS_AUDIO2_CTRL1_FIFO_ENABLE |
1379 ESS_AUDIO2_CTRL1_AUTO_INIT;
1380 ess_write_mix_reg(sc, ESS_MREG_AUDIO2_CTRL1, reg);
1381
1382 return (0);
1383 }
1384
1385 int
1386 ess_audio1_trigger_input(addr, start, end, blksize, intr, arg, param)
1387 void *addr;
1388 void *start, *end;
1389 int blksize;
1390 void (*intr) __P((void *));
1391 void *arg;
1392 struct audio_params *param;
1393 {
1394 struct ess_softc *sc = addr;
1395 u_int8_t reg;
1396
1397 DPRINTFN(1, ("ess_audio1_trigger_input: sc=%p start=%p end=%p blksize=%d intr=%p(%p)\n",
1398 addr, start, end, blksize, intr, arg));
1399
1400 if (sc->sc_audio1.active)
1401 panic("ess_audio1_trigger_input: already running");
1402
1403 sc->sc_audio1.active = 1;
1404 sc->sc_audio1.intr = intr;
1405 sc->sc_audio1.arg = arg;
1406 if (sc->sc_audio1.polled) {
1407 sc->sc_audio1.dmapos = 0;
1408 sc->sc_audio1.buffersize = (char *)end - (char *)start;
1409 sc->sc_audio1.dmacount = 0;
1410 sc->sc_audio1.blksize = blksize;
1411 timeout(ess_audio1_poll, sc, hz/30);
1412 }
1413
1414 reg = ess_read_x_reg(sc, ESS_XCMD_AUDIO_CTRL);
1415 if (param->channels == 2) {
1416 reg &= ~ESS_AUDIO_CTRL_MONO;
1417 reg |= ESS_AUDIO_CTRL_STEREO;
1418 } else {
1419 reg |= ESS_AUDIO_CTRL_MONO;
1420 reg &= ~ESS_AUDIO_CTRL_STEREO;
1421 }
1422 ess_write_x_reg(sc, ESS_XCMD_AUDIO_CTRL, reg);
1423
1424 reg = ess_read_x_reg(sc, ESS_XCMD_AUDIO1_CTRL1);
1425 if (param->precision * param->factor == 16)
1426 reg |= ESS_AUDIO1_CTRL1_FIFO_SIZE;
1427 else
1428 reg &= ~ESS_AUDIO1_CTRL1_FIFO_SIZE;
1429 if (param->channels == 2)
1430 reg |= ESS_AUDIO1_CTRL1_FIFO_STEREO;
1431 else
1432 reg &= ~ESS_AUDIO1_CTRL1_FIFO_STEREO;
1433 if (param->encoding == AUDIO_ENCODING_SLINEAR_BE ||
1434 param->encoding == AUDIO_ENCODING_SLINEAR_LE)
1435 reg |= ESS_AUDIO1_CTRL1_FIFO_SIGNED;
1436 else
1437 reg &= ~ESS_AUDIO1_CTRL1_FIFO_SIGNED;
1438 reg |= ESS_AUDIO1_CTRL1_FIFO_CONNECT;
1439 ess_write_x_reg(sc, ESS_XCMD_AUDIO1_CTRL1, reg);
1440
1441 isa_dmastart(sc->sc_ic, sc->sc_audio1.drq, start,
1442 (char *)end - (char *)start, NULL,
1443 DMAMODE_READ | DMAMODE_LOOPDEMAND, BUS_DMA_NOWAIT);
1444
1445 /* Program transfer count registers with 2's complement of count. */
1446 blksize = -blksize;
1447 ess_write_x_reg(sc, ESS_XCMD_XFER_COUNTLO, blksize);
1448 ess_write_x_reg(sc, ESS_XCMD_XFER_COUNTHI, blksize >> 8);
1449
1450 /* Use 4 bytes per input DMA. */
1451 ess_set_xreg_bits(sc, ESS_XCMD_DEMAND_CTRL, ESS_DEMAND_CTRL_DEMAND_4);
1452
1453 /* Start auto-init DMA */
1454 ess_wdsp(sc, ESS_ACMD_DISABLE_SPKR);
1455 reg = ess_read_x_reg(sc, ESS_XCMD_AUDIO1_CTRL2);
1456 reg |= ESS_AUDIO1_CTRL2_DMA_READ | ESS_AUDIO1_CTRL2_ADC_ENABLE;
1457 reg |= ESS_AUDIO1_CTRL2_FIFO_ENABLE | ESS_AUDIO1_CTRL2_AUTO_INIT;
1458 ess_write_x_reg(sc, ESS_XCMD_AUDIO1_CTRL2, reg);
1459
1460 return (0);
1461 }
1462
1463 int
1464 ess_audio1_halt(addr)
1465 void *addr;
1466 {
1467 struct ess_softc *sc = addr;
1468
1469 DPRINTF(("ess_audio1_halt: sc=%p\n", sc));
1470
1471 if (sc->sc_audio1.active) {
1472 ess_clear_xreg_bits(sc, ESS_XCMD_AUDIO1_CTRL2,
1473 ESS_AUDIO1_CTRL2_FIFO_ENABLE);
1474 isa_dmaabort(sc->sc_ic, sc->sc_audio1.drq);
1475 if (sc->sc_audio1.polled)
1476 untimeout(ess_audio1_poll, sc);
1477 sc->sc_audio1.active = 0;
1478 }
1479
1480 return (0);
1481 }
1482
1483 int
1484 ess_audio2_halt(addr)
1485 void *addr;
1486 {
1487 struct ess_softc *sc = addr;
1488
1489 DPRINTF(("ess_audio2_halt: sc=%p\n", sc));
1490
1491 if (sc->sc_audio2.active) {
1492 ess_clear_mreg_bits(sc, ESS_MREG_AUDIO2_CTRL1,
1493 ESS_AUDIO2_CTRL1_DAC_ENABLE |
1494 ESS_AUDIO2_CTRL1_FIFO_ENABLE);
1495 isa_dmaabort(sc->sc_ic, sc->sc_audio2.drq);
1496 if (sc->sc_audio2.polled)
1497 untimeout(ess_audio2_poll, sc);
1498 sc->sc_audio2.active = 0;
1499 }
1500
1501 return (0);
1502 }
1503
1504 int
1505 ess_audio1_intr(arg)
1506 void *arg;
1507 {
1508 struct ess_softc *sc = arg;
1509 u_int8_t reg;
1510
1511 DPRINTFN(1,("ess_audio1_intr: intr=%p\n", sc->sc_audio1.intr));
1512
1513 /* Check and clear interrupt on Audio1. */
1514 reg = EREAD1(sc->sc_iot, sc->sc_ioh, ESS_DSP_RW_STATUS);
1515 if ((reg & ESS_DSP_READ_OFLOW) == 0)
1516 return (0);
1517 reg = EREAD1(sc->sc_iot, sc->sc_ioh, ESS_CLEAR_INTR);
1518
1519 sc->sc_audio1.nintr++;
1520
1521 if (sc->sc_audio1.active) {
1522 (*sc->sc_audio1.intr)(sc->sc_audio1.arg);
1523 return (1);
1524 } else
1525 return (0);
1526 }
1527
1528 int
1529 ess_audio2_intr(arg)
1530 void *arg;
1531 {
1532 struct ess_softc *sc = arg;
1533 u_int8_t reg;
1534
1535 DPRINTFN(1,("ess_audio2_intr: intr=%p\n", sc->sc_audio2.intr));
1536
1537 /* Check and clear interrupt on Audio2. */
1538 reg = ess_read_mix_reg(sc, ESS_MREG_AUDIO2_CTRL2);
1539 if ((reg & ESS_AUDIO2_CTRL2_IRQ_LATCH) == 0)
1540 return (0);
1541 reg &= ~ESS_AUDIO2_CTRL2_IRQ_LATCH;
1542 ess_write_mix_reg(sc, ESS_MREG_AUDIO2_CTRL2, reg);
1543
1544 sc->sc_audio2.nintr++;
1545
1546 if (sc->sc_audio2.active) {
1547 (*sc->sc_audio2.intr)(sc->sc_audio2.arg);
1548 return (1);
1549 } else
1550 return (0);
1551 }
1552
1553 void
1554 ess_audio1_poll(addr)
1555 void *addr;
1556 {
1557 struct ess_softc *sc = addr;
1558 int dmapos, dmacount;
1559
1560 if (!sc->sc_audio1.active)
1561 return;
1562
1563 sc->sc_audio1.nintr++;
1564
1565 dmapos = isa_dmacount(sc->sc_ic, sc->sc_audio1.drq);
1566 dmacount = sc->sc_audio1.dmapos - dmapos;
1567 if (dmacount < 0)
1568 dmacount += sc->sc_audio1.buffersize;
1569 sc->sc_audio1.dmapos = dmapos;
1570 #if 1
1571 dmacount += sc->sc_audio1.dmacount;
1572 while (dmacount > sc->sc_audio1.blksize) {
1573 dmacount -= sc->sc_audio1.blksize;
1574 (*sc->sc_audio1.intr)(sc->sc_audio1.arg);
1575 }
1576 sc->sc_audio1.dmacount = dmacount;
1577 #else
1578 (*sc->sc_audio1.intr)(sc->sc_audio1.arg, dmacount);
1579 #endif
1580
1581 timeout(ess_audio1_poll, sc, hz/30);
1582 }
1583
1584 void
1585 ess_audio2_poll(addr)
1586 void *addr;
1587 {
1588 struct ess_softc *sc = addr;
1589 int dmapos, dmacount;
1590
1591 if (!sc->sc_audio2.active)
1592 return;
1593
1594 sc->sc_audio2.nintr++;
1595
1596 dmapos = isa_dmacount(sc->sc_ic, sc->sc_audio2.drq);
1597 dmacount = sc->sc_audio2.dmapos - dmapos;
1598 if (dmacount < 0)
1599 dmacount += sc->sc_audio2.buffersize;
1600 sc->sc_audio2.dmapos = dmapos;
1601 #if 1
1602 dmacount += sc->sc_audio2.dmacount;
1603 while (dmacount > sc->sc_audio2.blksize) {
1604 dmacount -= sc->sc_audio2.blksize;
1605 (*sc->sc_audio2.intr)(sc->sc_audio2.arg);
1606 }
1607 sc->sc_audio2.dmacount = dmacount;
1608 #else
1609 (*sc->sc_audio2.intr)(sc->sc_audio2.arg, dmacount);
1610 #endif
1611
1612 timeout(ess_audio2_poll, sc, hz/30);
1613 }
1614
1615 int
1616 ess_round_blocksize(addr, blk)
1617 void *addr;
1618 int blk;
1619 {
1620 return (blk & -8); /* round for max DMA size */
1621 }
1622
1623 int
1624 ess_set_port(addr, cp)
1625 void *addr;
1626 mixer_ctrl_t *cp;
1627 {
1628 struct ess_softc *sc = addr;
1629 int lgain, rgain;
1630
1631 DPRINTFN(5,("ess_set_port: port=%d num_channels=%d\n",
1632 cp->dev, cp->un.value.num_channels));
1633
1634 switch (cp->dev) {
1635 /*
1636 * The following mixer ports are all stereo. If we get a
1637 * single-channel gain value passed in, then we duplicate it
1638 * to both left and right channels.
1639 */
1640 case ESS_MASTER_VOL:
1641 case ESS_DAC_PLAY_VOL:
1642 case ESS_MIC_PLAY_VOL:
1643 case ESS_LINE_PLAY_VOL:
1644 case ESS_SYNTH_PLAY_VOL:
1645 case ESS_CD_PLAY_VOL:
1646 case ESS_AUXB_PLAY_VOL:
1647 case ESS_RECORD_VOL:
1648 if (cp->type != AUDIO_MIXER_VALUE)
1649 return EINVAL;
1650
1651 switch (cp->un.value.num_channels) {
1652 case 1:
1653 lgain = rgain = ESS_4BIT_GAIN(
1654 cp->un.value.level[AUDIO_MIXER_LEVEL_MONO]);
1655 break;
1656 case 2:
1657 lgain = ESS_4BIT_GAIN(
1658 cp->un.value.level[AUDIO_MIXER_LEVEL_LEFT]);
1659 rgain = ESS_4BIT_GAIN(
1660 cp->un.value.level[AUDIO_MIXER_LEVEL_RIGHT]);
1661 break;
1662 default:
1663 return EINVAL;
1664 }
1665
1666 sc->gain[cp->dev][ESS_LEFT] = lgain;
1667 sc->gain[cp->dev][ESS_RIGHT] = rgain;
1668 ess_set_gain(sc, cp->dev, 1);
1669 return (0);
1670
1671 /*
1672 * The PC speaker port is mono. If we get a stereo gain value
1673 * passed in, then we return EINVAL.
1674 */
1675 case ESS_PCSPEAKER_VOL:
1676 if (cp->un.value.num_channels != 1)
1677 return EINVAL;
1678
1679 sc->gain[cp->dev][ESS_LEFT] = sc->gain[cp->dev][ESS_RIGHT] =
1680 ESS_3BIT_GAIN(cp->un.value.level[AUDIO_MIXER_LEVEL_MONO]);
1681 ess_set_gain(sc, cp->dev, 1);
1682 return (0);
1683
1684 case ESS_RECORD_SOURCE:
1685 if (sc->sc_model == ESS_1788) {
1686 if (cp->type == AUDIO_MIXER_ENUM)
1687 return (ess_set_in_port(sc, cp->un.ord));
1688 else
1689 return (EINVAL);
1690 } else {
1691 if (cp->type == AUDIO_MIXER_SET)
1692 return (ess_set_in_ports(sc, cp->un.mask));
1693 else
1694 return (EINVAL);
1695 }
1696 return (0);
1697
1698 case ESS_RECORD_MONITOR:
1699 if (cp->type != AUDIO_MIXER_ENUM)
1700 return EINVAL;
1701
1702 if (cp->un.ord)
1703 /* Enable monitor */
1704 ess_set_xreg_bits(sc, ESS_XCMD_AUDIO_CTRL,
1705 ESS_AUDIO_CTRL_MONITOR);
1706 else
1707 /* Disable monitor */
1708 ess_clear_xreg_bits(sc, ESS_XCMD_AUDIO_CTRL,
1709 ESS_AUDIO_CTRL_MONITOR);
1710 return (0);
1711 }
1712
1713 if (sc->sc_model == ESS_1788)
1714 return (EINVAL);
1715
1716 switch (cp->dev) {
1717 case ESS_DAC_REC_VOL:
1718 case ESS_MIC_REC_VOL:
1719 case ESS_LINE_REC_VOL:
1720 case ESS_SYNTH_REC_VOL:
1721 case ESS_CD_REC_VOL:
1722 case ESS_AUXB_REC_VOL:
1723 if (cp->type != AUDIO_MIXER_VALUE)
1724 return EINVAL;
1725
1726 switch (cp->un.value.num_channels) {
1727 case 1:
1728 lgain = rgain = ESS_4BIT_GAIN(
1729 cp->un.value.level[AUDIO_MIXER_LEVEL_MONO]);
1730 break;
1731 case 2:
1732 lgain = ESS_4BIT_GAIN(
1733 cp->un.value.level[AUDIO_MIXER_LEVEL_LEFT]);
1734 rgain = ESS_4BIT_GAIN(
1735 cp->un.value.level[AUDIO_MIXER_LEVEL_RIGHT]);
1736 break;
1737 default:
1738 return EINVAL;
1739 }
1740
1741 sc->gain[cp->dev][ESS_LEFT] = lgain;
1742 sc->gain[cp->dev][ESS_RIGHT] = rgain;
1743 ess_set_gain(sc, cp->dev, 1);
1744 return (0);
1745
1746 case ESS_MIC_PREAMP:
1747 if (cp->type != AUDIO_MIXER_ENUM)
1748 return EINVAL;
1749
1750 if (cp->un.ord)
1751 /* Enable microphone preamp */
1752 ess_set_xreg_bits(sc, ESS_XCMD_PREAMP_CTRL,
1753 ESS_PREAMP_CTRL_ENABLE);
1754 else
1755 /* Disable microphone preamp */
1756 ess_clear_xreg_bits(sc, ESS_XCMD_PREAMP_CTRL,
1757 ESS_PREAMP_CTRL_ENABLE);
1758 return (0);
1759 }
1760
1761 return (EINVAL);
1762 }
1763
1764 int
1765 ess_get_port(addr, cp)
1766 void *addr;
1767 mixer_ctrl_t *cp;
1768 {
1769 struct ess_softc *sc = addr;
1770
1771 DPRINTFN(5,("ess_get_port: port=%d\n", cp->dev));
1772
1773 switch (cp->dev) {
1774 case ESS_MASTER_VOL:
1775 case ESS_DAC_PLAY_VOL:
1776 case ESS_MIC_PLAY_VOL:
1777 case ESS_LINE_PLAY_VOL:
1778 case ESS_SYNTH_PLAY_VOL:
1779 case ESS_CD_PLAY_VOL:
1780 case ESS_AUXB_PLAY_VOL:
1781 case ESS_RECORD_VOL:
1782 switch (cp->un.value.num_channels) {
1783 case 1:
1784 cp->un.value.level[AUDIO_MIXER_LEVEL_MONO] =
1785 sc->gain[cp->dev][ESS_LEFT];
1786 break;
1787 case 2:
1788 cp->un.value.level[AUDIO_MIXER_LEVEL_LEFT] =
1789 sc->gain[cp->dev][ESS_LEFT];
1790 cp->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] =
1791 sc->gain[cp->dev][ESS_RIGHT];
1792 break;
1793 default:
1794 return EINVAL;
1795 }
1796 return (0);
1797
1798 case ESS_PCSPEAKER_VOL:
1799 if (cp->un.value.num_channels != 1)
1800 return EINVAL;
1801
1802 cp->un.value.level[AUDIO_MIXER_LEVEL_MONO] =
1803 sc->gain[cp->dev][ESS_LEFT];
1804 return (0);
1805
1806 case ESS_RECORD_SOURCE:
1807 if (sc->sc_model == ESS_1788)
1808 cp->un.ord = sc->in_port;
1809 else
1810 cp->un.mask = sc->in_mask;
1811 return (0);
1812
1813 case ESS_RECORD_MONITOR:
1814 cp->un.ord = (ess_read_x_reg(sc, ESS_XCMD_AUDIO_CTRL) &
1815 ESS_AUDIO_CTRL_MONITOR) ? 1 : 0;
1816 return (0);
1817 }
1818
1819 if (sc->sc_model == ESS_1788)
1820 return (EINVAL);
1821
1822 switch (cp->dev) {
1823 case ESS_DAC_REC_VOL:
1824 case ESS_MIC_REC_VOL:
1825 case ESS_LINE_REC_VOL:
1826 case ESS_SYNTH_REC_VOL:
1827 case ESS_CD_REC_VOL:
1828 case ESS_AUXB_REC_VOL:
1829 switch (cp->un.value.num_channels) {
1830 case 1:
1831 cp->un.value.level[AUDIO_MIXER_LEVEL_MONO] =
1832 sc->gain[cp->dev][ESS_LEFT];
1833 break;
1834 case 2:
1835 cp->un.value.level[AUDIO_MIXER_LEVEL_LEFT] =
1836 sc->gain[cp->dev][ESS_LEFT];
1837 cp->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] =
1838 sc->gain[cp->dev][ESS_RIGHT];
1839 break;
1840 default:
1841 return EINVAL;
1842 }
1843 return (0);
1844
1845 case ESS_MIC_PREAMP:
1846 cp->un.ord = (ess_read_x_reg(sc, ESS_XCMD_PREAMP_CTRL) &
1847 ESS_PREAMP_CTRL_ENABLE) ? 1 : 0;
1848 return (0);
1849 }
1850
1851 return (EINVAL);
1852 }
1853
1854 int
1855 ess_query_devinfo(addr, dip)
1856 void *addr;
1857 mixer_devinfo_t *dip;
1858 {
1859 struct ess_softc *sc = addr;
1860
1861 DPRINTFN(5,("ess_query_devinfo: model=%d index=%d\n",
1862 sc->sc_model, dip->index));
1863
1864 /*
1865 * REVISIT: There are some slight differences between the
1866 * mixers on the different ESS chips, which can
1867 * be sorted out using the chip model rather than a
1868 * separate mixer model.
1869 * This is currently coded assuming an ES1887; we
1870 * need to work out which bits are not applicable to
1871 * the other models (1888 and 888).
1872 */
1873 switch (dip->index) {
1874 case ESS_DAC_PLAY_VOL:
1875 dip->mixer_class = ESS_INPUT_CLASS;
1876 dip->next = dip->prev = AUDIO_MIXER_LAST;
1877 strcpy(dip->label.name, AudioNdac);
1878 dip->type = AUDIO_MIXER_VALUE;
1879 dip->un.v.num_channels = 2;
1880 strcpy(dip->un.v.units.name, AudioNvolume);
1881 return (0);
1882
1883 case ESS_MIC_PLAY_VOL:
1884 dip->mixer_class = ESS_INPUT_CLASS;
1885 dip->prev = AUDIO_MIXER_LAST;
1886 if (sc->sc_model == ESS_1788)
1887 dip->next = AUDIO_MIXER_LAST;
1888 else
1889 dip->next = ESS_MIC_PREAMP;
1890 strcpy(dip->label.name, AudioNmicrophone);
1891 dip->type = AUDIO_MIXER_VALUE;
1892 dip->un.v.num_channels = 2;
1893 strcpy(dip->un.v.units.name, AudioNvolume);
1894 return (0);
1895
1896 case ESS_LINE_PLAY_VOL:
1897 dip->mixer_class = ESS_INPUT_CLASS;
1898 dip->next = dip->prev = AUDIO_MIXER_LAST;
1899 strcpy(dip->label.name, AudioNline);
1900 dip->type = AUDIO_MIXER_VALUE;
1901 dip->un.v.num_channels = 2;
1902 strcpy(dip->un.v.units.name, AudioNvolume);
1903 return (0);
1904
1905 case ESS_SYNTH_PLAY_VOL:
1906 dip->mixer_class = ESS_INPUT_CLASS;
1907 dip->next = dip->prev = AUDIO_MIXER_LAST;
1908 strcpy(dip->label.name, AudioNfmsynth);
1909 dip->type = AUDIO_MIXER_VALUE;
1910 dip->un.v.num_channels = 2;
1911 strcpy(dip->un.v.units.name, AudioNvolume);
1912 return (0);
1913
1914 case ESS_CD_PLAY_VOL:
1915 dip->mixer_class = ESS_INPUT_CLASS;
1916 dip->next = dip->prev = AUDIO_MIXER_LAST;
1917 strcpy(dip->label.name, AudioNcd);
1918 dip->type = AUDIO_MIXER_VALUE;
1919 dip->un.v.num_channels = 2;
1920 strcpy(dip->un.v.units.name, AudioNvolume);
1921 return (0);
1922
1923 case ESS_AUXB_PLAY_VOL:
1924 dip->mixer_class = ESS_INPUT_CLASS;
1925 dip->next = dip->prev = AUDIO_MIXER_LAST;
1926 strcpy(dip->label.name, "auxb");
1927 dip->type = AUDIO_MIXER_VALUE;
1928 dip->un.v.num_channels = 2;
1929 strcpy(dip->un.v.units.name, AudioNvolume);
1930 return (0);
1931
1932 case ESS_INPUT_CLASS:
1933 dip->mixer_class = ESS_INPUT_CLASS;
1934 dip->next = dip->prev = AUDIO_MIXER_LAST;
1935 strcpy(dip->label.name, AudioCinputs);
1936 dip->type = AUDIO_MIXER_CLASS;
1937 return (0);
1938
1939 case ESS_MASTER_VOL:
1940 dip->mixer_class = ESS_OUTPUT_CLASS;
1941 dip->next = dip->prev = AUDIO_MIXER_LAST;
1942 strcpy(dip->label.name, AudioNmaster);
1943 dip->type = AUDIO_MIXER_VALUE;
1944 dip->un.v.num_channels = 2;
1945 strcpy(dip->un.v.units.name, AudioNvolume);
1946 return (0);
1947
1948 case ESS_PCSPEAKER_VOL:
1949 dip->mixer_class = ESS_OUTPUT_CLASS;
1950 dip->next = dip->prev = AUDIO_MIXER_LAST;
1951 strcpy(dip->label.name, "pc_speaker");
1952 dip->type = AUDIO_MIXER_VALUE;
1953 dip->un.v.num_channels = 1;
1954 strcpy(dip->un.v.units.name, AudioNvolume);
1955 return (0);
1956
1957 case ESS_OUTPUT_CLASS:
1958 dip->mixer_class = ESS_OUTPUT_CLASS;
1959 dip->next = dip->prev = AUDIO_MIXER_LAST;
1960 strcpy(dip->label.name, AudioCoutputs);
1961 dip->type = AUDIO_MIXER_CLASS;
1962 return (0);
1963
1964 case ESS_RECORD_VOL:
1965 dip->mixer_class = ESS_RECORD_CLASS;
1966 dip->next = dip->prev = AUDIO_MIXER_LAST;
1967 strcpy(dip->label.name, AudioNrecord);
1968 dip->type = AUDIO_MIXER_VALUE;
1969 dip->un.v.num_channels = 2;
1970 strcpy(dip->un.v.units.name, AudioNvolume);
1971 return (0);
1972
1973 case ESS_RECORD_SOURCE:
1974 dip->mixer_class = ESS_RECORD_CLASS;
1975 dip->next = dip->prev = AUDIO_MIXER_LAST;
1976 strcpy(dip->label.name, AudioNsource);
1977 if (sc->sc_model == ESS_1788) {
1978 /*
1979 * The 1788 doesn't use the input mixer control that
1980 * the 1888 uses, because it's a pain when you only
1981 * have one mixer.
1982 * Perhaps it could be emulated by keeping both sets of
1983 * gain values, and doing a `context switch' of the
1984 * mixer registers when shifting from playing to
1985 * recording.
1986 */
1987 dip->type = AUDIO_MIXER_ENUM;
1988 dip->un.e.num_mem = 4;
1989 strcpy(dip->un.e.member[0].label.name, AudioNmicrophone);
1990 dip->un.e.member[0].ord = ESS_SOURCE_MIC;
1991 strcpy(dip->un.e.member[1].label.name, AudioNline);
1992 dip->un.e.member[1].ord = ESS_SOURCE_LINE;
1993 strcpy(dip->un.e.member[2].label.name, AudioNcd);
1994 dip->un.e.member[2].ord = ESS_SOURCE_CD;
1995 strcpy(dip->un.e.member[3].label.name, AudioNmixerout);
1996 dip->un.e.member[3].ord = ESS_SOURCE_MIXER;
1997 } else {
1998 dip->type = AUDIO_MIXER_SET;
1999 dip->un.s.num_mem = 6;
2000 strcpy(dip->un.s.member[0].label.name, AudioNdac);
2001 dip->un.s.member[0].mask = 1 << ESS_DAC_REC_VOL;
2002 strcpy(dip->un.s.member[1].label.name, AudioNmicrophone);
2003 dip->un.s.member[1].mask = 1 << ESS_MIC_REC_VOL;
2004 strcpy(dip->un.s.member[2].label.name, AudioNline);
2005 dip->un.s.member[2].mask = 1 << ESS_LINE_REC_VOL;
2006 strcpy(dip->un.s.member[3].label.name, AudioNfmsynth);
2007 dip->un.s.member[3].mask = 1 << ESS_SYNTH_REC_VOL;
2008 strcpy(dip->un.s.member[4].label.name, AudioNcd);
2009 dip->un.s.member[4].mask = 1 << ESS_CD_REC_VOL;
2010 strcpy(dip->un.s.member[5].label.name, "auxb");
2011 dip->un.s.member[5].mask = 1 << ESS_AUXB_REC_VOL;
2012 }
2013 return (0);
2014
2015 case ESS_RECORD_CLASS:
2016 dip->mixer_class = ESS_RECORD_CLASS;
2017 dip->next = dip->prev = AUDIO_MIXER_LAST;
2018 strcpy(dip->label.name, AudioCrecord);
2019 dip->type = AUDIO_MIXER_CLASS;
2020 return (0);
2021
2022 case ESS_RECORD_MONITOR:
2023 dip->prev = dip->next = AUDIO_MIXER_LAST;
2024 strcpy(dip->label.name, AudioNmonitor);
2025 dip->type = AUDIO_MIXER_ENUM;
2026 dip->mixer_class = ESS_MONITOR_CLASS;
2027 dip->un.e.num_mem = 2;
2028 strcpy(dip->un.e.member[0].label.name, AudioNoff);
2029 dip->un.e.member[0].ord = 0;
2030 strcpy(dip->un.e.member[1].label.name, AudioNon);
2031 dip->un.e.member[1].ord = 1;
2032 return (0);
2033
2034 case ESS_MONITOR_CLASS:
2035 dip->mixer_class = ESS_MONITOR_CLASS;
2036 dip->next = dip->prev = AUDIO_MIXER_LAST;
2037 strcpy(dip->label.name, AudioCmonitor);
2038 dip->type = AUDIO_MIXER_CLASS;
2039 return (0);
2040 }
2041
2042 if (sc->sc_model == ESS_1788)
2043 return (ENXIO);
2044
2045 switch (dip->index) {
2046 case ESS_DAC_REC_VOL:
2047 dip->mixer_class = ESS_RECORD_CLASS;
2048 dip->next = dip->prev = AUDIO_MIXER_LAST;
2049 strcpy(dip->label.name, AudioNdac);
2050 dip->type = AUDIO_MIXER_VALUE;
2051 dip->un.v.num_channels = 2;
2052 strcpy(dip->un.v.units.name, AudioNvolume);
2053 return (0);
2054
2055 case ESS_MIC_REC_VOL:
2056 dip->mixer_class = ESS_RECORD_CLASS;
2057 dip->next = dip->prev = AUDIO_MIXER_LAST;
2058 strcpy(dip->label.name, AudioNmicrophone);
2059 dip->type = AUDIO_MIXER_VALUE;
2060 dip->un.v.num_channels = 2;
2061 strcpy(dip->un.v.units.name, AudioNvolume);
2062 return (0);
2063
2064 case ESS_LINE_REC_VOL:
2065 dip->mixer_class = ESS_RECORD_CLASS;
2066 dip->next = dip->prev = AUDIO_MIXER_LAST;
2067 strcpy(dip->label.name, AudioNline);
2068 dip->type = AUDIO_MIXER_VALUE;
2069 dip->un.v.num_channels = 2;
2070 strcpy(dip->un.v.units.name, AudioNvolume);
2071 return (0);
2072
2073 case ESS_SYNTH_REC_VOL:
2074 dip->mixer_class = ESS_RECORD_CLASS;
2075 dip->next = dip->prev = AUDIO_MIXER_LAST;
2076 strcpy(dip->label.name, AudioNfmsynth);
2077 dip->type = AUDIO_MIXER_VALUE;
2078 dip->un.v.num_channels = 2;
2079 strcpy(dip->un.v.units.name, AudioNvolume);
2080 return (0);
2081
2082 case ESS_CD_REC_VOL:
2083 dip->mixer_class = ESS_RECORD_CLASS;
2084 dip->next = dip->prev = AUDIO_MIXER_LAST;
2085 strcpy(dip->label.name, AudioNcd);
2086 dip->type = AUDIO_MIXER_VALUE;
2087 dip->un.v.num_channels = 2;
2088 strcpy(dip->un.v.units.name, AudioNvolume);
2089 return (0);
2090
2091 case ESS_AUXB_REC_VOL:
2092 dip->mixer_class = ESS_RECORD_CLASS;
2093 dip->next = dip->prev = AUDIO_MIXER_LAST;
2094 strcpy(dip->label.name, "auxb");
2095 dip->type = AUDIO_MIXER_VALUE;
2096 dip->un.v.num_channels = 2;
2097 strcpy(dip->un.v.units.name, AudioNvolume);
2098 return (0);
2099
2100 case ESS_MIC_PREAMP:
2101 dip->mixer_class = ESS_INPUT_CLASS;
2102 dip->prev = ESS_MIC_PLAY_VOL;
2103 dip->next = AUDIO_MIXER_LAST;
2104 strcpy(dip->label.name, AudioNpreamp);
2105 dip->type = AUDIO_MIXER_ENUM;
2106 dip->un.e.num_mem = 2;
2107 strcpy(dip->un.e.member[0].label.name, AudioNoff);
2108 dip->un.e.member[0].ord = 0;
2109 strcpy(dip->un.e.member[1].label.name, AudioNon);
2110 dip->un.e.member[1].ord = 1;
2111 return (0);
2112 }
2113
2114 return (ENXIO);
2115 }
2116
2117 void *
2118 ess_malloc(addr, direction, size, pool, flags)
2119 void *addr;
2120 int direction;
2121 size_t size;
2122 int pool, flags;
2123 {
2124 struct ess_softc *sc = addr;
2125 int drq;
2126
2127 if (sc->sc_model != ESS_1788 && direction == AUMODE_PLAY)
2128 drq = sc->sc_audio2.drq;
2129 else
2130 drq = sc->sc_audio1.drq;
2131 return (isa_malloc(sc->sc_ic, drq, size, pool, flags));
2132 }
2133
2134 void
2135 ess_free(addr, ptr, pool)
2136 void *addr;
2137 void *ptr;
2138 int pool;
2139 {
2140 isa_free(ptr, pool);
2141 }
2142
2143 size_t
2144 ess_round_buffersize(addr, direction, size)
2145 void *addr;
2146 int direction;
2147 size_t size;
2148 {
2149 if (size > MAX_ISADMA)
2150 size = MAX_ISADMA;
2151 return (size);
2152 }
2153
2154 int
2155 ess_mappage(addr, mem, off, prot)
2156 void *addr;
2157 void *mem;
2158 int off;
2159 int prot;
2160 {
2161 return (isa_mappage(mem, off, prot));
2162 }
2163
2164 int
2165 ess_1788_get_props(addr)
2166 void *addr;
2167 {
2168
2169 return (AUDIO_PROP_MMAP | AUDIO_PROP_INDEPENDENT);
2170 }
2171
2172 int
2173 ess_1888_get_props(addr)
2174 void *addr;
2175 {
2176
2177 return (AUDIO_PROP_MMAP | AUDIO_PROP_INDEPENDENT | AUDIO_PROP_FULLDUPLEX);
2178 }
2179
2180 /* ============================================
2181 * Generic functions for ess, not used by audio h/w i/f
2182 * =============================================
2183 */
2184
2185 /*
2186 * Reset the chip.
2187 * Return non-zero if the chip isn't detected.
2188 */
2189 int
2190 ess_reset(sc)
2191 struct ess_softc *sc;
2192 {
2193 bus_space_tag_t iot = sc->sc_iot;
2194 bus_space_handle_t ioh = sc->sc_ioh;
2195
2196 sc->sc_audio1.active = 0;
2197 sc->sc_audio2.active = 0;
2198
2199 EWRITE1(iot, ioh, ESS_DSP_RESET, ESS_RESET_EXT);
2200 delay(10000);
2201 EWRITE1(iot, ioh, ESS_DSP_RESET, 0);
2202 if (ess_rdsp(sc) != ESS_MAGIC)
2203 return (1);
2204
2205 /* Enable access to the ESS extension commands. */
2206 ess_wdsp(sc, ESS_ACMD_ENABLE_EXT);
2207
2208 return (0);
2209 }
2210
2211 void
2212 ess_set_gain(sc, port, on)
2213 struct ess_softc *sc;
2214 int port;
2215 int on;
2216 {
2217 int gain, left, right;
2218 int mix;
2219 int src;
2220 int stereo;
2221
2222 /*
2223 * Most gain controls are found in the mixer registers and
2224 * are stereo. Any that are not, must set mix and stereo as
2225 * required.
2226 */
2227 mix = 1;
2228 stereo = 1;
2229
2230 switch (port) {
2231 case ESS_MASTER_VOL:
2232 src = ESS_MREG_VOLUME_MASTER;
2233 break;
2234 case ESS_DAC_PLAY_VOL:
2235 if (sc->sc_model == ESS_1788)
2236 src = ESS_MREG_VOLUME_VOICE;
2237 else
2238 src = 0x7C;
2239 break;
2240 case ESS_MIC_PLAY_VOL:
2241 src = ESS_MREG_VOLUME_MIC;
2242 break;
2243 case ESS_LINE_PLAY_VOL:
2244 src = ESS_MREG_VOLUME_LINE;
2245 break;
2246 case ESS_SYNTH_PLAY_VOL:
2247 src = ESS_MREG_VOLUME_SYNTH;
2248 break;
2249 case ESS_CD_PLAY_VOL:
2250 src = ESS_MREG_VOLUME_CD;
2251 break;
2252 case ESS_AUXB_PLAY_VOL:
2253 src = ESS_MREG_VOLUME_AUXB;
2254 break;
2255 case ESS_PCSPEAKER_VOL:
2256 src = ESS_MREG_VOLUME_PCSPKR;
2257 stereo = 0;
2258 break;
2259 case ESS_DAC_REC_VOL:
2260 src = 0x69;
2261 break;
2262 case ESS_MIC_REC_VOL:
2263 src = 0x68;
2264 break;
2265 case ESS_LINE_REC_VOL:
2266 src = 0x6E;
2267 break;
2268 case ESS_SYNTH_REC_VOL:
2269 src = 0x6B;
2270 break;
2271 case ESS_CD_REC_VOL:
2272 src = 0x6A;
2273 break;
2274 case ESS_AUXB_REC_VOL:
2275 src = 0x6C;
2276 break;
2277 case ESS_RECORD_VOL:
2278 src = ESS_XCMD_VOLIN_CTRL;
2279 mix = 0;
2280 break;
2281 default:
2282 return;
2283 }
2284
2285 /* 1788 doesn't have a separate recording mixer */
2286 if (sc->sc_model == ESS_1788 && mix && src > 0x62)
2287 return;
2288
2289 if (on) {
2290 left = sc->gain[port][ESS_LEFT];
2291 right = sc->gain[port][ESS_RIGHT];
2292 } else {
2293 left = right = 0;
2294 }
2295
2296 if (stereo)
2297 gain = ESS_STEREO_GAIN(left, right);
2298 else
2299 gain = ESS_MONO_GAIN(left);
2300
2301 if (mix)
2302 ess_write_mix_reg(sc, src, gain);
2303 else
2304 ess_write_x_reg(sc, src, gain);
2305 }
2306
2307 /* Set the input device on devices without an input mixer. */
2308 int
2309 ess_set_in_port(sc, ord)
2310 struct ess_softc *sc;
2311 int ord;
2312 {
2313 mixer_devinfo_t di;
2314 int i;
2315
2316 DPRINTF(("ess_set_in_port: ord=0x%x\n", ord));
2317
2318 /*
2319 * Get the device info for the record source control,
2320 * including the list of available sources.
2321 */
2322 di.index = ESS_RECORD_SOURCE;
2323 if (ess_query_devinfo(sc, &di))
2324 return EINVAL;
2325
2326 /* See if the given ord value was anywhere in the list. */
2327 for (i = 0; i < di.un.e.num_mem; i++) {
2328 if (ord == di.un.e.member[i].ord)
2329 break;
2330 }
2331 if (i == di.un.e.num_mem)
2332 return EINVAL;
2333
2334 ess_write_mix_reg(sc, ESS_MREG_ADC_SOURCE, ord);
2335
2336 sc->in_port = ord;
2337 return (0);
2338 }
2339
2340 /* Set the input device levels on input-mixer-enabled devices. */
2341 int
2342 ess_set_in_ports(sc, mask)
2343 struct ess_softc *sc;
2344 int mask;
2345 {
2346 mixer_devinfo_t di;
2347 int i, port;
2348
2349 DPRINTF(("ess_set_in_ports: mask=0x%x\n", mask));
2350
2351 /*
2352 * Get the device info for the record source control,
2353 * including the list of available sources.
2354 */
2355 di.index = ESS_RECORD_SOURCE;
2356 if (ess_query_devinfo(sc, &di))
2357 return EINVAL;
2358
2359 /*
2360 * Set or disable the record volume control for each of the
2361 * possible sources.
2362 */
2363 for (i = 0; i < di.un.s.num_mem; i++) {
2364 /*
2365 * Calculate the source port number from its mask.
2366 */
2367 port = ffs(di.un.s.member[i].mask);
2368
2369 /*
2370 * Set the source gain:
2371 * to the current value if source is enabled
2372 * to zero if source is disabled
2373 */
2374 ess_set_gain(sc, port, mask & di.un.s.member[i].mask);
2375 }
2376
2377 sc->in_mask = mask;
2378 return (0);
2379 }
2380
2381 void
2382 ess_speaker_on(sc)
2383 struct ess_softc *sc;
2384 {
2385 /* Disable mute on left- and right-master volume. */
2386 ess_clear_mreg_bits(sc, ESS_MREG_VOLUME_LEFT, ESS_VOLUME_MUTE);
2387 ess_clear_mreg_bits(sc, ESS_MREG_VOLUME_RIGHT, ESS_VOLUME_MUTE);
2388 }
2389
2390 void
2391 ess_speaker_off(sc)
2392 struct ess_softc *sc;
2393 {
2394 /* Enable mute on left- and right-master volume. */
2395 ess_set_mreg_bits(sc, ESS_MREG_VOLUME_LEFT, ESS_VOLUME_MUTE);
2396 ess_set_mreg_bits(sc, ESS_MREG_VOLUME_RIGHT, ESS_VOLUME_MUTE);
2397 }
2398
2399 /*
2400 * Calculate the time constant for the requested sampling rate.
2401 */
2402 u_int
2403 ess_srtotc(rate)
2404 u_int rate;
2405 {
2406 u_int tc;
2407
2408 /* The following formulae are from the ESS data sheet. */
2409 if (rate <= 22050)
2410 tc = 128 - 397700L / rate;
2411 else
2412 tc = 256 - 795500L / rate;
2413
2414 return (tc);
2415 }
2416
2417
2418 /*
2419 * Calculate the filter constant for the reuqested sampling rate.
2420 */
2421 u_int
2422 ess_srtofc(rate)
2423 u_int rate;
2424 {
2425 /*
2426 * The following formula is derived from the information in
2427 * the ES1887 data sheet, based on a roll-off frequency of
2428 * 87%.
2429 */
2430 return (256 - 200279L / rate);
2431 }
2432
2433
2434 /*
2435 * Return the status of the DSP.
2436 */
2437 u_char
2438 ess_get_dsp_status(sc)
2439 struct ess_softc *sc;
2440 {
2441 return (EREAD1(sc->sc_iot, sc->sc_ioh, ESS_DSP_RW_STATUS));
2442 }
2443
2444
2445 /*
2446 * Return the read status of the DSP: 1 -> DSP ready for reading
2447 * 0 -> DSP not ready for reading
2448 */
2449 u_char
2450 ess_dsp_read_ready(sc)
2451 struct ess_softc *sc;
2452 {
2453 return ((ess_get_dsp_status(sc) & ESS_DSP_READ_READY) ? 1 : 0);
2454 }
2455
2456
2457 /*
2458 * Return the write status of the DSP: 1 -> DSP ready for writing
2459 * 0 -> DSP not ready for writing
2460 */
2461 u_char
2462 ess_dsp_write_ready(sc)
2463 struct ess_softc *sc;
2464 {
2465 return ((ess_get_dsp_status(sc) & ESS_DSP_WRITE_BUSY) ? 0 : 1);
2466 }
2467
2468
2469 /*
2470 * Read a byte from the DSP.
2471 */
2472 int
2473 ess_rdsp(sc)
2474 struct ess_softc *sc;
2475 {
2476 bus_space_tag_t iot = sc->sc_iot;
2477 bus_space_handle_t ioh = sc->sc_ioh;
2478 int i;
2479
2480 for (i = ESS_READ_TIMEOUT; i > 0; --i) {
2481 if (ess_dsp_read_ready(sc)) {
2482 i = EREAD1(iot, ioh, ESS_DSP_READ);
2483 DPRINTFN(8,("ess_rdsp() = 0x%02x\n", i));
2484 return i;
2485 } else
2486 delay(10);
2487 }
2488
2489 DPRINTF(("ess_rdsp: timed out\n"));
2490 return (-1);
2491 }
2492
2493 /*
2494 * Write a byte to the DSP.
2495 */
2496 int
2497 ess_wdsp(sc, v)
2498 struct ess_softc *sc;
2499 u_char v;
2500 {
2501 bus_space_tag_t iot = sc->sc_iot;
2502 bus_space_handle_t ioh = sc->sc_ioh;
2503 int i;
2504
2505 DPRINTFN(8,("ess_wdsp(0x%02x)\n", v));
2506
2507 for (i = ESS_WRITE_TIMEOUT; i > 0; --i) {
2508 if (ess_dsp_write_ready(sc)) {
2509 EWRITE1(iot, ioh, ESS_DSP_WRITE, v);
2510 return (0);
2511 } else
2512 delay(10);
2513 }
2514
2515 DPRINTF(("ess_wdsp(0x%02x): timed out\n", v));
2516 return (-1);
2517 }
2518
2519 /*
2520 * Write a value to one of the ESS extended registers.
2521 */
2522 int
2523 ess_write_x_reg(sc, reg, val)
2524 struct ess_softc *sc;
2525 u_char reg;
2526 u_char val;
2527 {
2528 int error;
2529
2530 DPRINTFN(2,("ess_write_x_reg: %02x=%02x\n", reg, val));
2531 if ((error = ess_wdsp(sc, reg)) == 0)
2532 error = ess_wdsp(sc, val);
2533
2534 return error;
2535 }
2536
2537 /*
2538 * Read the value of one of the ESS extended registers.
2539 */
2540 u_char
2541 ess_read_x_reg(sc, reg)
2542 struct ess_softc *sc;
2543 u_char reg;
2544 {
2545 int error;
2546 int val;
2547
2548 if ((error = ess_wdsp(sc, 0xC0)) == 0)
2549 error = ess_wdsp(sc, reg);
2550 if (error)
2551 DPRINTF(("Error reading extended register 0x%02x\n", reg));
2552 /* REVISIT: what if an error is returned above? */
2553 val = ess_rdsp(sc);
2554 DPRINTFN(2,("ess_read_x_reg: %02x=%02x\n", reg, val));
2555 return val;
2556 }
2557
2558 void
2559 ess_clear_xreg_bits(sc, reg, mask)
2560 struct ess_softc *sc;
2561 u_char reg;
2562 u_char mask;
2563 {
2564 if (ess_write_x_reg(sc, reg, ess_read_x_reg(sc, reg) & ~mask) == -1)
2565 DPRINTF(("Error clearing bits in extended register 0x%02x\n",
2566 reg));
2567 }
2568
2569 void
2570 ess_set_xreg_bits(sc, reg, mask)
2571 struct ess_softc *sc;
2572 u_char reg;
2573 u_char mask;
2574 {
2575 if (ess_write_x_reg(sc, reg, ess_read_x_reg(sc, reg) | mask) == -1)
2576 DPRINTF(("Error setting bits in extended register 0x%02x\n",
2577 reg));
2578 }
2579
2580
2581 /*
2582 * Write a value to one of the ESS mixer registers.
2583 */
2584 void
2585 ess_write_mix_reg(sc, reg, val)
2586 struct ess_softc *sc;
2587 u_char reg;
2588 u_char val;
2589 {
2590 bus_space_tag_t iot = sc->sc_iot;
2591 bus_space_handle_t ioh = sc->sc_ioh;
2592 int s;
2593
2594 DPRINTFN(2,("ess_write_mix_reg: %x=%x\n", reg, val));
2595
2596 s = splaudio();
2597 EWRITE1(iot, ioh, ESS_MIX_REG_SELECT, reg);
2598 EWRITE1(iot, ioh, ESS_MIX_REG_DATA, val);
2599 splx(s);
2600 }
2601
2602 /*
2603 * Read the value of one of the ESS mixer registers.
2604 */
2605 u_char
2606 ess_read_mix_reg(sc, reg)
2607 struct ess_softc *sc;
2608 u_char reg;
2609 {
2610 bus_space_tag_t iot = sc->sc_iot;
2611 bus_space_handle_t ioh = sc->sc_ioh;
2612 int s;
2613 u_char val;
2614
2615 s = splaudio();
2616 EWRITE1(iot, ioh, ESS_MIX_REG_SELECT, reg);
2617 val = EREAD1(iot, ioh, ESS_MIX_REG_DATA);
2618 splx(s);
2619
2620 DPRINTFN(2,("ess_read_mix_reg: %x=%x\n", reg, val));
2621 return val;
2622 }
2623
2624 void
2625 ess_clear_mreg_bits(sc, reg, mask)
2626 struct ess_softc *sc;
2627 u_char reg;
2628 u_char mask;
2629 {
2630 ess_write_mix_reg(sc, reg, ess_read_mix_reg(sc, reg) & ~mask);
2631 }
2632
2633 void
2634 ess_set_mreg_bits(sc, reg, mask)
2635 struct ess_softc *sc;
2636 u_char reg;
2637 u_char mask;
2638 {
2639 ess_write_mix_reg(sc, reg, ess_read_mix_reg(sc, reg) | mask);
2640 }
2641