mavb.c revision 1.2.2.2 1 1.2.2.2 yamt /* $NetBSD: mavb.c,v 1.2.2.2 2007/04/15 16:02:55 yamt Exp $ */
2 1.2.2.2 yamt /* $OpenBSD: mavb.c,v 1.6 2005/04/15 13:05:14 mickey Exp $ */
3 1.2.2.2 yamt
4 1.2.2.2 yamt /*
5 1.2.2.2 yamt * Copyright (c) 2005 Mark Kettenis
6 1.2.2.2 yamt *
7 1.2.2.2 yamt * Permission to use, copy, modify, and distribute this software for any
8 1.2.2.2 yamt * purpose with or without fee is hereby granted, provided that the above
9 1.2.2.2 yamt * copyright notice and this permission notice appear in all copies.
10 1.2.2.2 yamt *
11 1.2.2.2 yamt * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
12 1.2.2.2 yamt * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13 1.2.2.2 yamt * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
14 1.2.2.2 yamt * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15 1.2.2.2 yamt * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16 1.2.2.2 yamt * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
17 1.2.2.2 yamt * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18 1.2.2.2 yamt */
19 1.2.2.2 yamt
20 1.2.2.2 yamt #include <sys/param.h>
21 1.2.2.2 yamt #include <sys/systm.h>
22 1.2.2.2 yamt #include <sys/device.h>
23 1.2.2.2 yamt #include <sys/kernel.h>
24 1.2.2.2 yamt #include <sys/malloc.h>
25 1.2.2.2 yamt #include <sys/callout.h>
26 1.2.2.2 yamt
27 1.2.2.2 yamt #include <machine/bus.h>
28 1.2.2.2 yamt #include <machine/intr.h>
29 1.2.2.2 yamt #include <machine/autoconf.h>
30 1.2.2.2 yamt
31 1.2.2.2 yamt #include <sys/audioio.h>
32 1.2.2.2 yamt #include <dev/auconv.h>
33 1.2.2.2 yamt #include <dev/audio_if.h>
34 1.2.2.2 yamt
35 1.2.2.2 yamt #include <arch/sgimips/mace/macevar.h>
36 1.2.2.2 yamt #include <arch/sgimips/mace/macereg.h>
37 1.2.2.2 yamt #include <arch/sgimips/mace/mavbreg.h>
38 1.2.2.2 yamt
39 1.2.2.2 yamt #include <dev/ic/ad1843reg.h>
40 1.2.2.2 yamt
41 1.2.2.2 yamt #undef MAVB_DEBUG
42 1.2.2.2 yamt
43 1.2.2.2 yamt #ifdef MAVB_DEBUG
44 1.2.2.2 yamt #define DPRINTF(l,x) do { if (mavb_debug & (l)) printf x; } while (0)
45 1.2.2.2 yamt #define MAVB_DEBUG_INTR 0x0100
46 1.2.2.2 yamt int mavb_debug = ~MAVB_DEBUG_INTR;
47 1.2.2.2 yamt #else
48 1.2.2.2 yamt #define DPRINTF(l,x) /* nothing */
49 1.2.2.2 yamt #endif
50 1.2.2.2 yamt
51 1.2.2.2 yamt /* Repeat delays for volume buttons. */
52 1.2.2.2 yamt #define MAVB_VOLUME_BUTTON_REPEAT_DEL1 400 /* 400ms to start repeating */
53 1.2.2.2 yamt #define MAVB_VOLUME_BUTTON_REPEAT_DELN 100 /* 100ms between repeats */
54 1.2.2.2 yamt
55 1.2.2.2 yamt /* XXX We need access to some of the MACE ISA registers. */
56 1.2.2.2 yamt #define MAVB_ISA_NREGS 0x20
57 1.2.2.2 yamt
58 1.2.2.2 yamt /*
59 1.2.2.2 yamt * AD1843 Mixer.
60 1.2.2.2 yamt */
61 1.2.2.2 yamt
62 1.2.2.2 yamt enum {
63 1.2.2.2 yamt AD1843_RECORD_CLASS,
64 1.2.2.2 yamt AD1843_ADC_SOURCE, /* ADC Source Select */
65 1.2.2.2 yamt AD1843_ADC_GAIN, /* ADC Input Gain */
66 1.2.2.2 yamt
67 1.2.2.2 yamt AD1843_INPUT_CLASS,
68 1.2.2.2 yamt AD1843_DAC1_GAIN, /* DAC1 Analog/Digital Gain/Attenuation */
69 1.2.2.2 yamt AD1843_DAC1_MUTE, /* DAC1 Analog Mute */
70 1.2.2.2 yamt AD1843_DAC2_GAIN, /* DAC2 Mix Gain */
71 1.2.2.2 yamt AD1843_AUX1_GAIN, /* Auxilliary 1 Mix Gain */
72 1.2.2.2 yamt AD1843_AUX2_GAIN, /* Auxilliary 2 Mix Gain */
73 1.2.2.2 yamt AD1843_AUX3_GAIN, /* Auxilliary 3 Mix Gain */
74 1.2.2.2 yamt AD1843_MIC_GAIN, /* Microphone Mix Gain */
75 1.2.2.2 yamt AD1843_MONO_GAIN, /* Mono Mix Gain */
76 1.2.2.2 yamt AD1843_DAC2_MUTE, /* DAC2 Mix Mute */
77 1.2.2.2 yamt AD1843_AUX1_MUTE, /* Auxilliary 1 Mix Mute */
78 1.2.2.2 yamt AD1843_AUX2_MUTE, /* Auxilliary 2 Mix Mute */
79 1.2.2.2 yamt AD1843_AUX3_MUTE, /* Auxilliary 3 Mix Mute */
80 1.2.2.2 yamt AD1843_MIC_MUTE, /* Microphone Mix Mute */
81 1.2.2.2 yamt AD1843_MONO_MUTE, /* Mono Mix Mute */
82 1.2.2.2 yamt AD1843_SUM_MUTE, /* Sum Mute */
83 1.2.2.2 yamt
84 1.2.2.2 yamt AD1843_OUTPUT_CLASS,
85 1.2.2.2 yamt AD1843_MNO_MUTE, /* Mono Output Mute */
86 1.2.2.2 yamt AD1843_HPO_MUTE /* Headphone Output Mute */
87 1.2.2.2 yamt };
88 1.2.2.2 yamt
89 1.2.2.2 yamt /* ADC Source Select. The order matches the hardware bits. */
90 1.2.2.2 yamt const char *ad1843_source[] = {
91 1.2.2.2 yamt AudioNline,
92 1.2.2.2 yamt AudioNmicrophone,
93 1.2.2.2 yamt AudioNaux "1",
94 1.2.2.2 yamt AudioNaux "2",
95 1.2.2.2 yamt AudioNaux "3",
96 1.2.2.2 yamt AudioNmono,
97 1.2.2.2 yamt AudioNdac "1",
98 1.2.2.2 yamt AudioNdac "2"
99 1.2.2.2 yamt };
100 1.2.2.2 yamt
101 1.2.2.2 yamt /* Mix Control. The order matches the hardware register numbering. */
102 1.2.2.2 yamt const char *ad1843_input[] = {
103 1.2.2.2 yamt AudioNdac "2", /* AD1843_DAC2__TO_MIXER */
104 1.2.2.2 yamt AudioNaux "1",
105 1.2.2.2 yamt AudioNaux "2",
106 1.2.2.2 yamt AudioNaux "3",
107 1.2.2.2 yamt AudioNmicrophone,
108 1.2.2.2 yamt AudioNmono /* AD1843_MISC_SETTINGS */
109 1.2.2.2 yamt };
110 1.2.2.2 yamt
111 1.2.2.2 yamt struct mavb_softc {
112 1.2.2.2 yamt struct device sc_dev;
113 1.2.2.2 yamt bus_space_tag_t sc_st;
114 1.2.2.2 yamt bus_space_handle_t sc_sh;
115 1.2.2.2 yamt bus_dma_tag_t sc_dmat;
116 1.2.2.2 yamt bus_dmamap_t sc_dmamap;
117 1.2.2.2 yamt
118 1.2.2.2 yamt /* XXX We need access to some of the MACE ISA registers. */
119 1.2.2.2 yamt bus_space_handle_t sc_isash;
120 1.2.2.2 yamt
121 1.2.2.2 yamt #define MAVB_ISA_RING_SIZE 0x1000
122 1.2.2.2 yamt uint8_t *sc_ring;
123 1.2.2.2 yamt
124 1.2.2.2 yamt uint8_t *sc_start, *sc_end;
125 1.2.2.2 yamt int sc_blksize;
126 1.2.2.2 yamt void (*sc_intr)(void *);
127 1.2.2.2 yamt void *sc_intrarg;
128 1.2.2.2 yamt
129 1.2.2.2 yamt void *sc_get;
130 1.2.2.2 yamt int sc_count;
131 1.2.2.2 yamt
132 1.2.2.2 yamt u_long sc_play_rate;
133 1.2.2.2 yamt u_int sc_play_format;
134 1.2.2.2 yamt
135 1.2.2.2 yamt struct callout sc_volume_button_ch;
136 1.2.2.2 yamt };
137 1.2.2.2 yamt
138 1.2.2.2 yamt /* XXX mavb supports way more than this, but for now I'm going to be
139 1.2.2.2 yamt * lazy and let auconv work its magic
140 1.2.2.2 yamt */
141 1.2.2.2 yamt #define MAVB_NENCODINGS 8
142 1.2.2.2 yamt static audio_encoding_t mavb_encoding[MAVB_NENCODINGS] = {
143 1.2.2.2 yamt { 0, AudioEulinear, AUDIO_ENCODING_ULINEAR, 8,
144 1.2.2.2 yamt AUDIO_ENCODINGFLAG_EMULATED },
145 1.2.2.2 yamt { 1, AudioEmulaw, AUDIO_ENCODING_ULAW, 8,
146 1.2.2.2 yamt AUDIO_ENCODINGFLAG_EMULATED },
147 1.2.2.2 yamt { 2, AudioEalaw, AUDIO_ENCODING_ALAW, 8,
148 1.2.2.2 yamt AUDIO_ENCODINGFLAG_EMULATED },
149 1.2.2.2 yamt { 3, AudioEslinear, AUDIO_ENCODING_SLINEAR, 8,
150 1.2.2.2 yamt AUDIO_ENCODINGFLAG_EMULATED },
151 1.2.2.2 yamt { 4, AudioEslinear_le, AUDIO_ENCODING_SLINEAR, 16,
152 1.2.2.2 yamt AUDIO_ENCODINGFLAG_EMULATED },
153 1.2.2.2 yamt { 5, AudioEulinear_le, AUDIO_ENCODING_ULINEAR, 16,
154 1.2.2.2 yamt AUDIO_ENCODINGFLAG_EMULATED },
155 1.2.2.2 yamt { 6, AudioEslinear_be, AUDIO_ENCODING_SLINEAR, 16,
156 1.2.2.2 yamt 0 },
157 1.2.2.2 yamt { 7, AudioEulinear_be, AUDIO_ENCODING_ULINEAR, 16,
158 1.2.2.2 yamt AUDIO_ENCODINGFLAG_EMULATED },
159 1.2.2.2 yamt };
160 1.2.2.2 yamt
161 1.2.2.2 yamt #define MAVB_NFORMATS 3
162 1.2.2.2 yamt static const struct audio_format mavb_formats[MAVB_NFORMATS] = {
163 1.2.2.2 yamt { NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_SLINEAR_BE, 16, 16,
164 1.2.2.2 yamt 2, AUFMT_STEREO, 0, { 8000, 48000 } },
165 1.2.2.2 yamt { NULL, AUMODE_PLAY | AUMODE_RECORD, AUDIO_ENCODING_SLINEAR_BE, 16, 16,
166 1.2.2.2 yamt 1, AUFMT_MONAURAL, 0, { 8000, 48000 } },
167 1.2.2.2 yamt };
168 1.2.2.2 yamt
169 1.2.2.2 yamt struct mavb_codecvar {
170 1.2.2.2 yamt stream_filter_t base;
171 1.2.2.2 yamt };
172 1.2.2.2 yamt
173 1.2.2.2 yamt static stream_filter_t *mavb_factory
174 1.2.2.2 yamt (int (*)(stream_fetcher_t *, audio_stream_t *, int));
175 1.2.2.2 yamt static void mavb_dtor(stream_filter_t *);
176 1.2.2.2 yamt
177 1.2.2.2 yamt /* XXX I'm going to complain every time I have to copy this macro */
178 1.2.2.2 yamt #define DEFINE_FILTER(name) \
179 1.2.2.2 yamt static int \
180 1.2.2.2 yamt name##_fetch_to(stream_fetcher_t *, audio_stream_t *, int); \
181 1.2.2.2 yamt stream_filter_t *name(struct audio_softc *, \
182 1.2.2.2 yamt const audio_params_t *, const audio_params_t *); \
183 1.2.2.2 yamt stream_filter_t * \
184 1.2.2.2 yamt name(struct audio_softc *sc, const audio_params_t *from, \
185 1.2.2.2 yamt const audio_params_t *to) \
186 1.2.2.2 yamt { \
187 1.2.2.2 yamt return mavb_factory(name##_fetch_to); \
188 1.2.2.2 yamt } \
189 1.2.2.2 yamt static int \
190 1.2.2.2 yamt name##_fetch_to(stream_fetcher_t *self, audio_stream_t *dst, int max_used)
191 1.2.2.2 yamt
192 1.2.2.2 yamt DEFINE_FILTER(mavb_16to24)
193 1.2.2.2 yamt {
194 1.2.2.2 yamt stream_filter_t *this;
195 1.2.2.2 yamt int m, err;
196 1.2.2.2 yamt
197 1.2.2.2 yamt this = (stream_filter_t *)self;
198 1.2.2.2 yamt max_used = (max_used + 1) & ~1;
199 1.2.2.2 yamt if ((err = this->prev->fetch_to(this->prev, this->src, max_used)))
200 1.2.2.2 yamt return err;
201 1.2.2.2 yamt m = (dst->end - dst->start) & ~1;
202 1.2.2.2 yamt m = min(m, max_used);
203 1.2.2.2 yamt FILTER_LOOP_PROLOGUE(this->src, 2, dst, 4, m) {
204 1.2.2.2 yamt d[3] = 0;
205 1.2.2.2 yamt d[2] = s[1];
206 1.2.2.2 yamt d[1] = s[0];
207 1.2.2.2 yamt d[0] = (s[0] & 0x80) ? 0xff : 0;
208 1.2.2.2 yamt } FILTER_LOOP_EPILOGUE(this->src, dst);
209 1.2.2.2 yamt
210 1.2.2.2 yamt return 0;
211 1.2.2.2 yamt }
212 1.2.2.2 yamt
213 1.2.2.2 yamt DEFINE_FILTER(mavb_mts)
214 1.2.2.2 yamt {
215 1.2.2.2 yamt stream_filter_t *this;
216 1.2.2.2 yamt int m, err;
217 1.2.2.2 yamt
218 1.2.2.2 yamt this = (stream_filter_t *)self;
219 1.2.2.2 yamt max_used = (max_used + 1) & ~1;
220 1.2.2.2 yamt if ((err = this->prev->fetch_to(this->prev, this->src, max_used)))
221 1.2.2.2 yamt return err;
222 1.2.2.2 yamt m = (dst->end - dst->start) & ~1;
223 1.2.2.2 yamt m = min(m, max_used);
224 1.2.2.2 yamt FILTER_LOOP_PROLOGUE(this->src, 4, dst, 8, m) {
225 1.2.2.2 yamt d[3] = d[7] = s[3];
226 1.2.2.2 yamt d[2] = d[6] = s[2];
227 1.2.2.2 yamt d[1] = d[5] = s[1];
228 1.2.2.2 yamt d[0] = d[4] = s[0];
229 1.2.2.2 yamt } FILTER_LOOP_EPILOGUE(this->src, dst);
230 1.2.2.2 yamt
231 1.2.2.2 yamt return 0;
232 1.2.2.2 yamt }
233 1.2.2.2 yamt
234 1.2.2.2 yamt static stream_filter_t *
235 1.2.2.2 yamt mavb_factory(int (*fetch_to)(stream_fetcher_t *, audio_stream_t *, int))
236 1.2.2.2 yamt {
237 1.2.2.2 yamt struct mavb_codecvar *this;
238 1.2.2.2 yamt
239 1.2.2.2 yamt this = malloc(sizeof(*this), M_DEVBUF, M_WAITOK | M_ZERO);
240 1.2.2.2 yamt this->base.base.fetch_to = fetch_to;
241 1.2.2.2 yamt this->base.dtor = mavb_dtor;
242 1.2.2.2 yamt this->base.set_fetcher = stream_filter_set_fetcher;
243 1.2.2.2 yamt this->base.set_inputbuffer = stream_filter_set_inputbuffer;
244 1.2.2.2 yamt
245 1.2.2.2 yamt return &this->base;
246 1.2.2.2 yamt }
247 1.2.2.2 yamt
248 1.2.2.2 yamt static void
249 1.2.2.2 yamt mavb_dtor(stream_filter_t *this)
250 1.2.2.2 yamt {
251 1.2.2.2 yamt if (this != NULL)
252 1.2.2.2 yamt free(this, M_DEVBUF);
253 1.2.2.2 yamt }
254 1.2.2.2 yamt
255 1.2.2.2 yamt typedef u_int64_t ad1843_addr_t;
256 1.2.2.2 yamt
257 1.2.2.2 yamt u_int16_t ad1843_reg_read(struct mavb_softc *, ad1843_addr_t);
258 1.2.2.2 yamt u_int16_t ad1843_reg_write(struct mavb_softc *, ad1843_addr_t, u_int16_t);
259 1.2.2.2 yamt void ad1843_dump_regs(struct mavb_softc *);
260 1.2.2.2 yamt
261 1.2.2.2 yamt int mavb_match(struct device *, struct cfdata *, void *);
262 1.2.2.2 yamt void mavb_attach(struct device *, struct device *, void *);
263 1.2.2.2 yamt
264 1.2.2.2 yamt CFATTACH_DECL(mavb, sizeof(struct mavb_softc),
265 1.2.2.2 yamt mavb_match, mavb_attach, NULL, NULL);
266 1.2.2.2 yamt
267 1.2.2.2 yamt int mavb_open(void *, int);
268 1.2.2.2 yamt void mavb_close(void *);
269 1.2.2.2 yamt int mavb_query_encoding(void *, struct audio_encoding *);
270 1.2.2.2 yamt int mavb_set_params(void *, int, int, struct audio_params *,
271 1.2.2.2 yamt struct audio_params *, stream_filter_list_t *,
272 1.2.2.2 yamt stream_filter_list_t *);
273 1.2.2.2 yamt int mavb_round_blocksize(void *hdl, int, int, const audio_params_t *);
274 1.2.2.2 yamt int mavb_halt_output(void *);
275 1.2.2.2 yamt int mavb_halt_input(void *);
276 1.2.2.2 yamt int mavb_getdev(void *, struct audio_device *);
277 1.2.2.2 yamt int mavb_set_port(void *, struct mixer_ctrl *);
278 1.2.2.2 yamt int mavb_get_port(void *, struct mixer_ctrl *);
279 1.2.2.2 yamt int mavb_query_devinfo(void *, struct mixer_devinfo *);
280 1.2.2.2 yamt size_t mavb_round_buffersize(void *, int, size_t);
281 1.2.2.2 yamt int mavb_get_props(void *);
282 1.2.2.2 yamt int mavb_trigger_output(void *, void *, void *, int, void (*)(void *),
283 1.2.2.2 yamt void *, const audio_params_t *);
284 1.2.2.2 yamt int mavb_trigger_input(void *, void *, void *, int, void (*)(void *),
285 1.2.2.2 yamt void *, const audio_params_t *);
286 1.2.2.2 yamt
287 1.2.2.2 yamt struct audio_hw_if mavb_sa_hw_if = {
288 1.2.2.2 yamt mavb_open,
289 1.2.2.2 yamt mavb_close,
290 1.2.2.2 yamt 0,
291 1.2.2.2 yamt mavb_query_encoding,
292 1.2.2.2 yamt mavb_set_params,
293 1.2.2.2 yamt mavb_round_blocksize,
294 1.2.2.2 yamt 0,
295 1.2.2.2 yamt 0,
296 1.2.2.2 yamt 0,
297 1.2.2.2 yamt 0,
298 1.2.2.2 yamt 0,
299 1.2.2.2 yamt mavb_halt_output,
300 1.2.2.2 yamt mavb_halt_input,
301 1.2.2.2 yamt 0,
302 1.2.2.2 yamt mavb_getdev,
303 1.2.2.2 yamt 0,
304 1.2.2.2 yamt mavb_set_port,
305 1.2.2.2 yamt mavb_get_port,
306 1.2.2.2 yamt mavb_query_devinfo,
307 1.2.2.2 yamt 0,
308 1.2.2.2 yamt 0,
309 1.2.2.2 yamt mavb_round_buffersize,
310 1.2.2.2 yamt 0,
311 1.2.2.2 yamt mavb_get_props,
312 1.2.2.2 yamt mavb_trigger_output,
313 1.2.2.2 yamt mavb_trigger_input,
314 1.2.2.2 yamt NULL,
315 1.2.2.2 yamt };
316 1.2.2.2 yamt
317 1.2.2.2 yamt struct audio_device mavb_device = {
318 1.2.2.2 yamt "A3",
319 1.2.2.2 yamt "",
320 1.2.2.2 yamt "mavb"
321 1.2.2.2 yamt };
322 1.2.2.2 yamt
323 1.2.2.2 yamt int
324 1.2.2.2 yamt mavb_open(void *hdl, int flags)
325 1.2.2.2 yamt {
326 1.2.2.2 yamt return (0);
327 1.2.2.2 yamt }
328 1.2.2.2 yamt
329 1.2.2.2 yamt void
330 1.2.2.2 yamt mavb_close(void *hdl)
331 1.2.2.2 yamt {
332 1.2.2.2 yamt }
333 1.2.2.2 yamt
334 1.2.2.2 yamt int
335 1.2.2.2 yamt mavb_query_encoding(void *hdl, struct audio_encoding *ae)
336 1.2.2.2 yamt {
337 1.2.2.2 yamt if (ae->index < 0 || ae->index >= MAVB_NENCODINGS)
338 1.2.2.2 yamt return (EINVAL);
339 1.2.2.2 yamt *ae = mavb_encoding[ae->index];
340 1.2.2.2 yamt
341 1.2.2.2 yamt return (0);
342 1.2.2.2 yamt }
343 1.2.2.2 yamt
344 1.2.2.2 yamt static int
345 1.2.2.2 yamt mavb_set_play_rate(struct mavb_softc *sc, u_long sample_rate)
346 1.2.2.2 yamt {
347 1.2.2.2 yamt if (sample_rate < 4000 || sample_rate > 48000)
348 1.2.2.2 yamt return (EINVAL);
349 1.2.2.2 yamt
350 1.2.2.2 yamt if (sc->sc_play_rate != sample_rate) {
351 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_CLOCK2_SAMPLE_RATE, sample_rate);
352 1.2.2.2 yamt sc->sc_play_rate = sample_rate;
353 1.2.2.2 yamt }
354 1.2.2.2 yamt return (0);
355 1.2.2.2 yamt }
356 1.2.2.2 yamt
357 1.2.2.2 yamt static int
358 1.2.2.2 yamt mavb_set_play_format(struct mavb_softc *sc, u_int encoding)
359 1.2.2.2 yamt {
360 1.2.2.2 yamt u_int16_t value;
361 1.2.2.2 yamt u_int format;
362 1.2.2.2 yamt
363 1.2.2.2 yamt switch(encoding) {
364 1.2.2.2 yamt case AUDIO_ENCODING_ULINEAR_BE:
365 1.2.2.2 yamt format = AD1843_PCM8;
366 1.2.2.2 yamt break;
367 1.2.2.2 yamt case AUDIO_ENCODING_SLINEAR_BE:
368 1.2.2.2 yamt format = AD1843_PCM16;
369 1.2.2.2 yamt break;
370 1.2.2.2 yamt case AUDIO_ENCODING_ULAW:
371 1.2.2.2 yamt format = AD1843_ULAW;
372 1.2.2.2 yamt break;
373 1.2.2.2 yamt case AUDIO_ENCODING_ALAW:
374 1.2.2.2 yamt format = AD1843_ALAW;
375 1.2.2.2 yamt break;
376 1.2.2.2 yamt default:
377 1.2.2.2 yamt return (EINVAL);
378 1.2.2.2 yamt }
379 1.2.2.2 yamt
380 1.2.2.2 yamt if (sc->sc_play_format != format) {
381 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_SERIAL_INTERFACE);
382 1.2.2.2 yamt value &= ~AD1843_DA1F_MASK;
383 1.2.2.2 yamt value |= (format << AD1843_DA1F_SHIFT);
384 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_SERIAL_INTERFACE, value);
385 1.2.2.2 yamt sc->sc_play_format = format;
386 1.2.2.2 yamt }
387 1.2.2.2 yamt return (0);
388 1.2.2.2 yamt }
389 1.2.2.2 yamt
390 1.2.2.2 yamt int
391 1.2.2.2 yamt mavb_set_params(void *hdl, int setmode, int usemode,
392 1.2.2.2 yamt struct audio_params *play, struct audio_params *rec,
393 1.2.2.2 yamt stream_filter_list_t *pfil, stream_filter_list_t *rfil)
394 1.2.2.2 yamt {
395 1.2.2.2 yamt struct mavb_softc *sc = (struct mavb_softc *)hdl;
396 1.2.2.2 yamt struct audio_params *p;
397 1.2.2.2 yamt stream_filter_list_t *fil;
398 1.2.2.2 yamt int error;
399 1.2.2.2 yamt
400 1.2.2.2 yamt DPRINTF(1, ("%s: mavb_set_params: sample=%u precision=%d "
401 1.2.2.2 yamt "channels=%d\n", sc->sc_dev.dv_xname, play->sample_rate,
402 1.2.2.2 yamt play->precision, play->channels));
403 1.2.2.2 yamt
404 1.2.2.2 yamt if (setmode & AUMODE_PLAY) {
405 1.2.2.2 yamt if (play->sample_rate < 4000 || play->sample_rate > 48000)
406 1.2.2.2 yamt return (EINVAL);
407 1.2.2.2 yamt
408 1.2.2.2 yamt p = play;
409 1.2.2.2 yamt fil = pfil;
410 1.2.2.2 yamt if (auconv_set_converter(mavb_formats, MAVB_NFORMATS,
411 1.2.2.2 yamt AUMODE_PLAY, p, FALSE, fil) < 0)
412 1.2.2.2 yamt return (EINVAL);
413 1.2.2.2 yamt
414 1.2.2.2 yamt fil->append(fil, mavb_16to24, p);
415 1.2.2.2 yamt if (p->channels == 1)
416 1.2.2.2 yamt fil->append(fil, mavb_mts, p);
417 1.2.2.2 yamt if (fil->req_size > 0)
418 1.2.2.2 yamt p = &fil->filters[0].param;
419 1.2.2.2 yamt
420 1.2.2.2 yamt error = mavb_set_play_rate(sc, p->sample_rate);
421 1.2.2.2 yamt if (error)
422 1.2.2.2 yamt return (error);
423 1.2.2.2 yamt
424 1.2.2.2 yamt error = mavb_set_play_format(sc, p->encoding);
425 1.2.2.2 yamt if (error)
426 1.2.2.2 yamt return (error);
427 1.2.2.2 yamt }
428 1.2.2.2 yamt
429 1.2.2.2 yamt #if 0
430 1.2.2.2 yamt if (setmode & AUMODE_RECORD) {
431 1.2.2.2 yamt if (rec->sample_rate < 4000 || rec->sample_rate > 48000)
432 1.2.2.2 yamt return (EINVAL);
433 1.2.2.2 yamt }
434 1.2.2.2 yamt #endif
435 1.2.2.2 yamt
436 1.2.2.2 yamt return (0);
437 1.2.2.2 yamt }
438 1.2.2.2 yamt
439 1.2.2.2 yamt int
440 1.2.2.2 yamt mavb_round_blocksize(void *hdl, int bs, int mode, const audio_params_t *p)
441 1.2.2.2 yamt {
442 1.2.2.2 yamt /* Block size should be a multiple of 32. */
443 1.2.2.2 yamt return (bs + 0x1f) & ~0x1f;
444 1.2.2.2 yamt }
445 1.2.2.2 yamt
446 1.2.2.2 yamt int
447 1.2.2.2 yamt mavb_halt_output(void *hdl)
448 1.2.2.2 yamt {
449 1.2.2.2 yamt struct mavb_softc *sc = (struct mavb_softc *)hdl;
450 1.2.2.2 yamt
451 1.2.2.2 yamt DPRINTF(1, ("%s: mavb_halt_output called\n", sc->sc_dev.dv_xname));
452 1.2.2.2 yamt
453 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CHANNEL2_CONTROL, 0);
454 1.2.2.2 yamt return (0);
455 1.2.2.2 yamt }
456 1.2.2.2 yamt
457 1.2.2.2 yamt int
458 1.2.2.2 yamt mavb_halt_input(void *hdl)
459 1.2.2.2 yamt {
460 1.2.2.2 yamt return (0);
461 1.2.2.2 yamt }
462 1.2.2.2 yamt
463 1.2.2.2 yamt int
464 1.2.2.2 yamt mavb_getdev(void *hdl, struct audio_device *ret)
465 1.2.2.2 yamt {
466 1.2.2.2 yamt *ret = mavb_device;
467 1.2.2.2 yamt return (0);
468 1.2.2.2 yamt }
469 1.2.2.2 yamt
470 1.2.2.2 yamt int
471 1.2.2.2 yamt mavb_set_port(void *hdl, struct mixer_ctrl *mc)
472 1.2.2.2 yamt {
473 1.2.2.2 yamt struct mavb_softc *sc = (struct mavb_softc *)hdl;
474 1.2.2.2 yamt u_char left, right;
475 1.2.2.2 yamt ad1843_addr_t reg;
476 1.2.2.2 yamt u_int16_t value;
477 1.2.2.2 yamt
478 1.2.2.2 yamt DPRINTF(1, ("%s: mavb_set_port: dev=%d\n", sc->sc_dev.dv_xname,
479 1.2.2.2 yamt mc->dev));
480 1.2.2.2 yamt
481 1.2.2.2 yamt switch (mc->dev) {
482 1.2.2.2 yamt case AD1843_ADC_SOURCE:
483 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_ADC_SOURCE_GAIN);
484 1.2.2.2 yamt value &= ~(AD1843_LSS_MASK | AD1843_RSS_MASK);
485 1.2.2.2 yamt value |= ((mc->un.ord << AD1843_LSS_SHIFT) & AD1843_LSS_MASK);
486 1.2.2.2 yamt value |= ((mc->un.ord << AD1843_RSS_SHIFT) & AD1843_RSS_MASK);
487 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_ADC_SOURCE_GAIN, value);
488 1.2.2.2 yamt break;
489 1.2.2.2 yamt case AD1843_ADC_GAIN:
490 1.2.2.2 yamt left = mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT];
491 1.2.2.2 yamt right = mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT];
492 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_ADC_SOURCE_GAIN);
493 1.2.2.2 yamt value &= ~(AD1843_LIG_MASK | AD1843_RIG_MASK);
494 1.2.2.2 yamt value |= ((left >> 4) << AD1843_LIG_SHIFT);
495 1.2.2.2 yamt value |= ((right >> 4) << AD1843_RIG_SHIFT);
496 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_ADC_SOURCE_GAIN, value);
497 1.2.2.2 yamt break;
498 1.2.2.2 yamt
499 1.2.2.2 yamt case AD1843_DAC1_GAIN:
500 1.2.2.2 yamt left = AUDIO_MAX_GAIN -
501 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT];
502 1.2.2.2 yamt right = AUDIO_MAX_GAIN -
503 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT];
504 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_DAC1_ANALOG_GAIN);
505 1.2.2.2 yamt value &= ~(AD1843_LDA1G_MASK | AD1843_RDA1G_MASK);
506 1.2.2.2 yamt value |= ((left >> 2) << AD1843_LDA1G_SHIFT);
507 1.2.2.2 yamt value |= ((right >> 2) << AD1843_RDA1G_SHIFT);
508 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_DAC1_ANALOG_GAIN, value);
509 1.2.2.2 yamt break;
510 1.2.2.2 yamt case AD1843_DAC1_MUTE:
511 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_DAC1_ANALOG_GAIN);
512 1.2.2.2 yamt if (mc->un.ord == 0)
513 1.2.2.2 yamt value &= ~(AD1843_LDA1GM | AD1843_RDA1GM);
514 1.2.2.2 yamt else
515 1.2.2.2 yamt value |= (AD1843_LDA1GM | AD1843_RDA1GM);
516 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_DAC1_ANALOG_GAIN, value);
517 1.2.2.2 yamt break;
518 1.2.2.2 yamt
519 1.2.2.2 yamt case AD1843_DAC2_GAIN:
520 1.2.2.2 yamt case AD1843_AUX1_GAIN:
521 1.2.2.2 yamt case AD1843_AUX2_GAIN:
522 1.2.2.2 yamt case AD1843_AUX3_GAIN:
523 1.2.2.2 yamt case AD1843_MIC_GAIN:
524 1.2.2.2 yamt left = AUDIO_MAX_GAIN -
525 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT];
526 1.2.2.2 yamt right = AUDIO_MAX_GAIN -
527 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT];
528 1.2.2.2 yamt reg = AD1843_DAC2_TO_MIXER + mc->dev - AD1843_DAC2_GAIN;
529 1.2.2.2 yamt value = ad1843_reg_read(sc, reg);
530 1.2.2.2 yamt value &= ~(AD1843_LD2M_MASK | AD1843_RD2M_MASK);
531 1.2.2.2 yamt value |= ((left >> 3) << AD1843_LD2M_SHIFT);
532 1.2.2.2 yamt value |= ((right >> 3) << AD1843_RD2M_SHIFT);
533 1.2.2.2 yamt ad1843_reg_write(sc, reg, value);
534 1.2.2.2 yamt break;
535 1.2.2.2 yamt case AD1843_MONO_GAIN:
536 1.2.2.2 yamt left = AUDIO_MAX_GAIN -
537 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_MONO];
538 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
539 1.2.2.2 yamt value &= ~AD1843_MNM_MASK;
540 1.2.2.2 yamt value |= ((left >> 3) << AD1843_MNM_SHIFT);
541 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_MISC_SETTINGS, value);
542 1.2.2.2 yamt break;
543 1.2.2.2 yamt case AD1843_DAC2_MUTE:
544 1.2.2.2 yamt case AD1843_AUX1_MUTE:
545 1.2.2.2 yamt case AD1843_AUX2_MUTE:
546 1.2.2.2 yamt case AD1843_AUX3_MUTE:
547 1.2.2.2 yamt case AD1843_MIC_MUTE:
548 1.2.2.2 yamt case AD1843_MONO_MUTE: /* matches left channel */
549 1.2.2.2 yamt reg = AD1843_DAC2_TO_MIXER + mc->dev - AD1843_DAC2_MUTE;
550 1.2.2.2 yamt value = ad1843_reg_read(sc, reg);
551 1.2.2.2 yamt if (mc->un.ord == 0)
552 1.2.2.2 yamt value &= ~(AD1843_LD2MM | AD1843_RD2MM);
553 1.2.2.2 yamt else
554 1.2.2.2 yamt value |= (AD1843_LD2MM | AD1843_RD2MM);
555 1.2.2.2 yamt ad1843_reg_write(sc, reg, value);
556 1.2.2.2 yamt break;
557 1.2.2.2 yamt
558 1.2.2.2 yamt case AD1843_SUM_MUTE:
559 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
560 1.2.2.2 yamt if (mc->un.ord == 0)
561 1.2.2.2 yamt value &= ~AD1843_SUMM;
562 1.2.2.2 yamt else
563 1.2.2.2 yamt value |= AD1843_SUMM;
564 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_MISC_SETTINGS, value);
565 1.2.2.2 yamt break;
566 1.2.2.2 yamt
567 1.2.2.2 yamt case AD1843_MNO_MUTE:
568 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
569 1.2.2.2 yamt if (mc->un.ord == 0)
570 1.2.2.2 yamt value &= ~AD1843_MNOM;
571 1.2.2.2 yamt else
572 1.2.2.2 yamt value |= AD1843_MNOM;
573 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_MISC_SETTINGS, value);
574 1.2.2.2 yamt break;
575 1.2.2.2 yamt
576 1.2.2.2 yamt case AD1843_HPO_MUTE:
577 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
578 1.2.2.2 yamt if (mc->un.ord == 0)
579 1.2.2.2 yamt value &= ~AD1843_HPOM;
580 1.2.2.2 yamt else
581 1.2.2.2 yamt value |= AD1843_HPOM;
582 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_MISC_SETTINGS, value);
583 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
584 1.2.2.2 yamt break;
585 1.2.2.2 yamt
586 1.2.2.2 yamt default:
587 1.2.2.2 yamt return (EINVAL);
588 1.2.2.2 yamt }
589 1.2.2.2 yamt
590 1.2.2.2 yamt return (0);
591 1.2.2.2 yamt }
592 1.2.2.2 yamt
593 1.2.2.2 yamt int
594 1.2.2.2 yamt mavb_get_port(void *hdl, struct mixer_ctrl *mc)
595 1.2.2.2 yamt {
596 1.2.2.2 yamt struct mavb_softc *sc = (struct mavb_softc *)hdl;
597 1.2.2.2 yamt u_char left, right;
598 1.2.2.2 yamt ad1843_addr_t reg;
599 1.2.2.2 yamt u_int16_t value;
600 1.2.2.2 yamt
601 1.2.2.2 yamt DPRINTF(1, ("%s: mavb_get_port: dev=%d\n", sc->sc_dev.dv_xname,
602 1.2.2.2 yamt mc->dev));
603 1.2.2.2 yamt
604 1.2.2.2 yamt switch (mc->dev) {
605 1.2.2.2 yamt case AD1843_ADC_SOURCE:
606 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_ADC_SOURCE_GAIN);
607 1.2.2.2 yamt mc->un.ord = (value & AD1843_LSS_MASK) >> AD1843_LSS_SHIFT;
608 1.2.2.2 yamt break;
609 1.2.2.2 yamt case AD1843_ADC_GAIN:
610 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_ADC_SOURCE_GAIN);
611 1.2.2.2 yamt left = (value & AD1843_LIG_MASK) >> AD1843_LIG_SHIFT;
612 1.2.2.2 yamt right = (value & AD1843_RIG_MASK) >> AD1843_RIG_SHIFT;
613 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] =
614 1.2.2.2 yamt (left << 4) | left;
615 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] =
616 1.2.2.2 yamt (right << 2) | right;
617 1.2.2.2 yamt break;
618 1.2.2.2 yamt
619 1.2.2.2 yamt case AD1843_DAC1_GAIN:
620 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_DAC1_ANALOG_GAIN);
621 1.2.2.2 yamt left = (value & AD1843_LDA1G_MASK) >> AD1843_LDA1G_SHIFT;
622 1.2.2.2 yamt right = (value & AD1843_RDA1G_MASK) >> AD1843_RDA1G_SHIFT;
623 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] =
624 1.2.2.2 yamt AUDIO_MAX_GAIN - (left << 2);
625 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] =
626 1.2.2.2 yamt AUDIO_MAX_GAIN - (right << 2);
627 1.2.2.2 yamt break;
628 1.2.2.2 yamt case AD1843_DAC1_MUTE:
629 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_DAC1_ANALOG_GAIN);
630 1.2.2.2 yamt mc->un.ord = (value & AD1843_LDA1GM) ? 1 : 0;
631 1.2.2.2 yamt break;
632 1.2.2.2 yamt
633 1.2.2.2 yamt case AD1843_DAC2_GAIN:
634 1.2.2.2 yamt case AD1843_AUX1_GAIN:
635 1.2.2.2 yamt case AD1843_AUX2_GAIN:
636 1.2.2.2 yamt case AD1843_AUX3_GAIN:
637 1.2.2.2 yamt case AD1843_MIC_GAIN:
638 1.2.2.2 yamt reg = AD1843_DAC2_TO_MIXER + mc->dev - AD1843_DAC2_GAIN;
639 1.2.2.2 yamt value = ad1843_reg_read(sc, reg);
640 1.2.2.2 yamt left = (value & AD1843_LD2M_MASK) >> AD1843_LD2M_SHIFT;
641 1.2.2.2 yamt right = (value & AD1843_RD2M_MASK) >> AD1843_RD2M_SHIFT;
642 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_LEFT] =
643 1.2.2.2 yamt AUDIO_MAX_GAIN - (left << 3);
644 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_RIGHT] =
645 1.2.2.2 yamt AUDIO_MAX_GAIN - (right << 3);
646 1.2.2.2 yamt break;
647 1.2.2.2 yamt case AD1843_MONO_GAIN:
648 1.2.2.2 yamt if (mc->un.value.num_channels != 1)
649 1.2.2.2 yamt return (EINVAL);
650 1.2.2.2 yamt
651 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
652 1.2.2.2 yamt left = (value & AD1843_MNM_MASK) >> AD1843_MNM_SHIFT;
653 1.2.2.2 yamt mc->un.value.level[AUDIO_MIXER_LEVEL_MONO] =
654 1.2.2.2 yamt AUDIO_MAX_GAIN - (left << 3);
655 1.2.2.2 yamt break;
656 1.2.2.2 yamt case AD1843_DAC2_MUTE:
657 1.2.2.2 yamt case AD1843_AUX1_MUTE:
658 1.2.2.2 yamt case AD1843_AUX2_MUTE:
659 1.2.2.2 yamt case AD1843_AUX3_MUTE:
660 1.2.2.2 yamt case AD1843_MIC_MUTE:
661 1.2.2.2 yamt case AD1843_MONO_MUTE: /* matches left channel */
662 1.2.2.2 yamt reg = AD1843_DAC2_TO_MIXER + mc->dev - AD1843_DAC2_MUTE;
663 1.2.2.2 yamt value = ad1843_reg_read(sc, reg);
664 1.2.2.2 yamt mc->un.ord = (value & AD1843_LD2MM) ? 1 : 0;
665 1.2.2.2 yamt break;
666 1.2.2.2 yamt
667 1.2.2.2 yamt case AD1843_SUM_MUTE:
668 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
669 1.2.2.2 yamt mc->un.ord = (value & AD1843_SUMM) ? 1 : 0;
670 1.2.2.2 yamt break;
671 1.2.2.2 yamt
672 1.2.2.2 yamt case AD1843_MNO_MUTE:
673 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
674 1.2.2.2 yamt mc->un.ord = (value & AD1843_MNOM) ? 1 : 0;
675 1.2.2.2 yamt break;
676 1.2.2.2 yamt
677 1.2.2.2 yamt case AD1843_HPO_MUTE:
678 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
679 1.2.2.2 yamt mc->un.ord = (value & AD1843_HPOM) ? 1 : 0;
680 1.2.2.2 yamt break;
681 1.2.2.2 yamt
682 1.2.2.2 yamt default:
683 1.2.2.2 yamt return (EINVAL);
684 1.2.2.2 yamt }
685 1.2.2.2 yamt
686 1.2.2.2 yamt return (0);
687 1.2.2.2 yamt }
688 1.2.2.2 yamt
689 1.2.2.2 yamt int
690 1.2.2.2 yamt mavb_query_devinfo(void *hdl, struct mixer_devinfo *di)
691 1.2.2.2 yamt {
692 1.2.2.2 yamt int i;
693 1.2.2.2 yamt
694 1.2.2.2 yamt di->prev = di->next = AUDIO_MIXER_LAST;
695 1.2.2.2 yamt
696 1.2.2.2 yamt switch (di->index) {
697 1.2.2.2 yamt case AD1843_RECORD_CLASS:
698 1.2.2.2 yamt di->type = AUDIO_MIXER_CLASS;
699 1.2.2.2 yamt di->mixer_class = AD1843_RECORD_CLASS;
700 1.2.2.2 yamt strlcpy(di->label.name, AudioCrecord, sizeof di->label.name);
701 1.2.2.2 yamt break;
702 1.2.2.2 yamt
703 1.2.2.2 yamt case AD1843_ADC_SOURCE:
704 1.2.2.2 yamt di->type = AUDIO_MIXER_ENUM;
705 1.2.2.2 yamt di->mixer_class = AD1843_RECORD_CLASS;
706 1.2.2.2 yamt di->next = AD1843_ADC_GAIN;
707 1.2.2.2 yamt strlcpy(di->label.name, AudioNsource, sizeof di->label.name);
708 1.2.2.2 yamt di->un.e.num_mem =
709 1.2.2.2 yamt sizeof ad1843_source / sizeof ad1843_source[1];
710 1.2.2.2 yamt for (i = 0; i < di->un.e.num_mem; i++) {
711 1.2.2.2 yamt strlcpy(di->un.e.member[i].label.name,
712 1.2.2.2 yamt ad1843_source[i],
713 1.2.2.2 yamt sizeof di->un.e.member[0].label.name);
714 1.2.2.2 yamt di->un.e.member[i].ord = i;
715 1.2.2.2 yamt }
716 1.2.2.2 yamt break;
717 1.2.2.2 yamt case AD1843_ADC_GAIN:
718 1.2.2.2 yamt di->type = AUDIO_MIXER_VALUE;
719 1.2.2.2 yamt di->mixer_class = AD1843_RECORD_CLASS;
720 1.2.2.2 yamt di->prev = AD1843_ADC_SOURCE;
721 1.2.2.2 yamt strlcpy(di->label.name, AudioNvolume, sizeof di->label.name);
722 1.2.2.2 yamt di->un.v.num_channels = 2;
723 1.2.2.2 yamt strlcpy(di->un.v.units.name, AudioNvolume,
724 1.2.2.2 yamt sizeof di->un.v.units.name);
725 1.2.2.2 yamt break;
726 1.2.2.2 yamt
727 1.2.2.2 yamt case AD1843_INPUT_CLASS:
728 1.2.2.2 yamt di->type = AUDIO_MIXER_CLASS;
729 1.2.2.2 yamt di->mixer_class = AD1843_INPUT_CLASS;
730 1.2.2.2 yamt strlcpy(di->label.name, AudioCinputs, sizeof di->label.name);
731 1.2.2.2 yamt break;
732 1.2.2.2 yamt
733 1.2.2.2 yamt case AD1843_DAC1_GAIN:
734 1.2.2.2 yamt di->type = AUDIO_MIXER_VALUE;
735 1.2.2.2 yamt di->mixer_class = AD1843_INPUT_CLASS;
736 1.2.2.2 yamt di->next = AD1843_DAC1_MUTE;
737 1.2.2.2 yamt strlcpy(di->label.name, AudioNdac "1", sizeof di->label.name);
738 1.2.2.2 yamt di->un.v.num_channels = 2;
739 1.2.2.2 yamt strlcpy(di->un.v.units.name, AudioNvolume,
740 1.2.2.2 yamt sizeof di->un.v.units.name);
741 1.2.2.2 yamt break;
742 1.2.2.2 yamt case AD1843_DAC1_MUTE:
743 1.2.2.2 yamt di->type = AUDIO_MIXER_ENUM;
744 1.2.2.2 yamt di->mixer_class = AD1843_INPUT_CLASS;
745 1.2.2.2 yamt di->prev = AD1843_DAC1_GAIN;
746 1.2.2.2 yamt strlcpy(di->label.name, AudioNmute, sizeof di->label.name);
747 1.2.2.2 yamt di->un.e.num_mem = 2;
748 1.2.2.2 yamt strlcpy(di->un.e.member[0].label.name, AudioNoff,
749 1.2.2.2 yamt sizeof di->un.e.member[0].label.name);
750 1.2.2.2 yamt di->un.e.member[0].ord = 0;
751 1.2.2.2 yamt strlcpy(di->un.e.member[1].label.name, AudioNon,
752 1.2.2.2 yamt sizeof di->un.e.member[1].label.name);
753 1.2.2.2 yamt di->un.e.member[1].ord = 1;
754 1.2.2.2 yamt break;
755 1.2.2.2 yamt
756 1.2.2.2 yamt case AD1843_DAC2_GAIN:
757 1.2.2.2 yamt case AD1843_AUX1_GAIN:
758 1.2.2.2 yamt case AD1843_AUX2_GAIN:
759 1.2.2.2 yamt case AD1843_AUX3_GAIN:
760 1.2.2.2 yamt case AD1843_MIC_GAIN:
761 1.2.2.2 yamt case AD1843_MONO_GAIN:
762 1.2.2.2 yamt di->type = AUDIO_MIXER_VALUE;
763 1.2.2.2 yamt di->mixer_class = AD1843_INPUT_CLASS;
764 1.2.2.2 yamt di->next = di->index + AD1843_DAC2_MUTE - AD1843_DAC2_GAIN;
765 1.2.2.2 yamt strlcpy(di->label.name,
766 1.2.2.2 yamt ad1843_input[di->index - AD1843_DAC2_GAIN],
767 1.2.2.2 yamt sizeof di->label.name);
768 1.2.2.2 yamt if (di->index == AD1843_MONO_GAIN)
769 1.2.2.2 yamt di->un.v.num_channels = 1;
770 1.2.2.2 yamt else
771 1.2.2.2 yamt di->un.v.num_channels = 2;
772 1.2.2.2 yamt strlcpy(di->un.v.units.name, AudioNvolume,
773 1.2.2.2 yamt sizeof di->un.v.units.name);
774 1.2.2.2 yamt break;
775 1.2.2.2 yamt case AD1843_DAC2_MUTE:
776 1.2.2.2 yamt case AD1843_AUX1_MUTE:
777 1.2.2.2 yamt case AD1843_AUX2_MUTE:
778 1.2.2.2 yamt case AD1843_AUX3_MUTE:
779 1.2.2.2 yamt case AD1843_MIC_MUTE:
780 1.2.2.2 yamt case AD1843_MONO_MUTE:
781 1.2.2.2 yamt di->type = AUDIO_MIXER_ENUM;
782 1.2.2.2 yamt di->mixer_class = AD1843_INPUT_CLASS;
783 1.2.2.2 yamt di->prev = di->index + AD1843_DAC2_GAIN - AD1843_DAC2_MUTE;
784 1.2.2.2 yamt strlcpy(di->label.name, AudioNmute, sizeof di->label.name);
785 1.2.2.2 yamt di->un.e.num_mem = 2;
786 1.2.2.2 yamt strlcpy(di->un.e.member[0].label.name, AudioNoff,
787 1.2.2.2 yamt sizeof di->un.e.member[0].label.name);
788 1.2.2.2 yamt di->un.e.member[0].ord = 0;
789 1.2.2.2 yamt strlcpy(di->un.e.member[1].label.name, AudioNon,
790 1.2.2.2 yamt sizeof di->un.e.member[1].label.name);
791 1.2.2.2 yamt di->un.e.member[1].ord = 1;
792 1.2.2.2 yamt break;
793 1.2.2.2 yamt
794 1.2.2.2 yamt case AD1843_SUM_MUTE:
795 1.2.2.2 yamt di->type = AUDIO_MIXER_ENUM;
796 1.2.2.2 yamt di->mixer_class = AD1843_INPUT_CLASS;
797 1.2.2.2 yamt strlcpy(di->label.name, "sum." AudioNmute,
798 1.2.2.2 yamt sizeof di->label.name);
799 1.2.2.2 yamt di->un.e.num_mem = 2;
800 1.2.2.2 yamt strlcpy(di->un.e.member[0].label.name, AudioNoff,
801 1.2.2.2 yamt sizeof di->un.e.member[0].label.name);
802 1.2.2.2 yamt di->un.e.member[0].ord = 0;
803 1.2.2.2 yamt strlcpy(di->un.e.member[1].label.name, AudioNon,
804 1.2.2.2 yamt sizeof di->un.e.member[1].label.name);
805 1.2.2.2 yamt di->un.e.member[1].ord = 1;
806 1.2.2.2 yamt break;
807 1.2.2.2 yamt
808 1.2.2.2 yamt case AD1843_OUTPUT_CLASS:
809 1.2.2.2 yamt di->type = AUDIO_MIXER_CLASS;
810 1.2.2.2 yamt di->mixer_class = AD1843_OUTPUT_CLASS;
811 1.2.2.2 yamt strlcpy(di->label.name, AudioCoutputs, sizeof di->label.name);
812 1.2.2.2 yamt break;
813 1.2.2.2 yamt
814 1.2.2.2 yamt case AD1843_MNO_MUTE:
815 1.2.2.2 yamt di->type = AUDIO_MIXER_ENUM;
816 1.2.2.2 yamt di->mixer_class = AD1843_OUTPUT_CLASS;
817 1.2.2.2 yamt strlcpy(di->label.name, AudioNmono "." AudioNmute,
818 1.2.2.2 yamt sizeof di->label.name);
819 1.2.2.2 yamt di->un.e.num_mem = 2;
820 1.2.2.2 yamt strlcpy(di->un.e.member[0].label.name, AudioNoff,
821 1.2.2.2 yamt sizeof di->un.e.member[0].label.name);
822 1.2.2.2 yamt di->un.e.member[0].ord = 0;
823 1.2.2.2 yamt strlcpy(di->un.e.member[1].label.name, AudioNon,
824 1.2.2.2 yamt sizeof di->un.e.member[1].label.name);
825 1.2.2.2 yamt di->un.e.member[1].ord = 1;
826 1.2.2.2 yamt break;
827 1.2.2.2 yamt
828 1.2.2.2 yamt case AD1843_HPO_MUTE:
829 1.2.2.2 yamt di->type = AUDIO_MIXER_ENUM;
830 1.2.2.2 yamt di->mixer_class = AD1843_OUTPUT_CLASS;
831 1.2.2.2 yamt strlcpy(di->label.name, AudioNheadphone "." AudioNmute,
832 1.2.2.2 yamt sizeof di->label.name);
833 1.2.2.2 yamt di->un.e.num_mem = 2;
834 1.2.2.2 yamt strlcpy(di->un.e.member[0].label.name, AudioNoff,
835 1.2.2.2 yamt sizeof di->un.e.member[0].label.name);
836 1.2.2.2 yamt di->un.e.member[0].ord = 0;
837 1.2.2.2 yamt strlcpy(di->un.e.member[1].label.name, AudioNon,
838 1.2.2.2 yamt sizeof di->un.e.member[1].label.name);
839 1.2.2.2 yamt di->un.e.member[1].ord = 1;
840 1.2.2.2 yamt break;
841 1.2.2.2 yamt
842 1.2.2.2 yamt default:
843 1.2.2.2 yamt return (EINVAL);
844 1.2.2.2 yamt }
845 1.2.2.2 yamt
846 1.2.2.2 yamt return (0);
847 1.2.2.2 yamt }
848 1.2.2.2 yamt
849 1.2.2.2 yamt size_t
850 1.2.2.2 yamt mavb_round_buffersize(void *hdl, int dir, size_t bufsize)
851 1.2.2.2 yamt {
852 1.2.2.2 yamt
853 1.2.2.2 yamt return bufsize;
854 1.2.2.2 yamt }
855 1.2.2.2 yamt
856 1.2.2.2 yamt int
857 1.2.2.2 yamt mavb_get_props(void *hdl)
858 1.2.2.2 yamt {
859 1.2.2.2 yamt return (AUDIO_PROP_FULLDUPLEX | AUDIO_PROP_INDEPENDENT);
860 1.2.2.2 yamt }
861 1.2.2.2 yamt
862 1.2.2.2 yamt static void
863 1.2.2.2 yamt mavb_dma_output(struct mavb_softc *sc)
864 1.2.2.2 yamt {
865 1.2.2.2 yamt bus_space_tag_t st = sc->sc_st;
866 1.2.2.2 yamt bus_space_handle_t sh = sc->sc_sh;
867 1.2.2.2 yamt u_int64_t write_ptr;
868 1.2.2.2 yamt u_int64_t depth;
869 1.2.2.2 yamt uint8_t *src, *dst;
870 1.2.2.2 yamt int count;
871 1.2.2.2 yamt
872 1.2.2.2 yamt write_ptr = bus_space_read_8(st, sh, MAVB_CHANNEL2_WRITE_PTR);
873 1.2.2.2 yamt depth = bus_space_read_8(st, sh, MAVB_CHANNEL2_DEPTH);
874 1.2.2.2 yamt
875 1.2.2.2 yamt dst = sc->sc_ring + write_ptr;
876 1.2.2.2 yamt src = sc->sc_get;
877 1.2.2.2 yamt
878 1.2.2.2 yamt count = (MAVB_ISA_RING_SIZE - depth - 32);
879 1.2.2.2 yamt while (--count >= 0) {
880 1.2.2.2 yamt *dst++ = *src++;
881 1.2.2.2 yamt if (dst >= sc->sc_ring + MAVB_ISA_RING_SIZE)
882 1.2.2.2 yamt dst = sc->sc_ring;
883 1.2.2.2 yamt if (src >= sc->sc_end)
884 1.2.2.2 yamt src = sc->sc_start;
885 1.2.2.2 yamt if (++sc->sc_count >= sc->sc_blksize) {
886 1.2.2.2 yamt if (sc->sc_intr)
887 1.2.2.2 yamt sc->sc_intr(sc->sc_intrarg);
888 1.2.2.2 yamt sc->sc_count = 0;
889 1.2.2.2 yamt }
890 1.2.2.2 yamt }
891 1.2.2.2 yamt
892 1.2.2.2 yamt write_ptr = dst - sc->sc_ring;
893 1.2.2.2 yamt bus_space_write_8(st, sh, MAVB_CHANNEL2_WRITE_PTR, write_ptr);
894 1.2.2.2 yamt sc->sc_get = src;
895 1.2.2.2 yamt }
896 1.2.2.2 yamt
897 1.2.2.2 yamt int
898 1.2.2.2 yamt mavb_trigger_output(void *hdl, void *start, void *end, int blksize,
899 1.2.2.2 yamt void (*intr)(void *), void *intrarg,
900 1.2.2.2 yamt const audio_params_t *param)
901 1.2.2.2 yamt {
902 1.2.2.2 yamt struct mavb_softc *sc = (struct mavb_softc *)hdl;
903 1.2.2.2 yamt
904 1.2.2.2 yamt DPRINTF(1, ("%s: mavb_trigger_output: start=%p end=%p "
905 1.2.2.2 yamt "blksize=%d intr=%p(%p)\n", sc->sc_dev.dv_xname,
906 1.2.2.2 yamt start, end, blksize, intr, intrarg));
907 1.2.2.2 yamt
908 1.2.2.2 yamt sc->sc_blksize = blksize;
909 1.2.2.2 yamt sc->sc_intr = intr;
910 1.2.2.2 yamt sc->sc_intrarg = intrarg;
911 1.2.2.2 yamt
912 1.2.2.2 yamt sc->sc_start = sc->sc_get = start;
913 1.2.2.2 yamt sc->sc_end = end;
914 1.2.2.2 yamt
915 1.2.2.2 yamt sc->sc_count = 0;
916 1.2.2.2 yamt
917 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CHANNEL2_CONTROL,
918 1.2.2.2 yamt MAVB_CHANNEL_RESET);
919 1.2.2.2 yamt delay(1000);
920 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CHANNEL2_CONTROL, 0);
921 1.2.2.2 yamt
922 1.2.2.2 yamt mavb_dma_output(sc);
923 1.2.2.2 yamt
924 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CHANNEL2_CONTROL,
925 1.2.2.2 yamt MAVB_CHANNEL_DMA_ENABLE | MAVB_CHANNEL_INT_50);
926 1.2.2.2 yamt return (0);
927 1.2.2.2 yamt }
928 1.2.2.2 yamt
929 1.2.2.2 yamt int
930 1.2.2.2 yamt mavb_trigger_input(void *hdl, void *start, void *end, int blksize,
931 1.2.2.2 yamt void (*intr)(void *), void *intrarg,
932 1.2.2.2 yamt const audio_params_t *param)
933 1.2.2.2 yamt {
934 1.2.2.2 yamt return (0);
935 1.2.2.2 yamt }
936 1.2.2.2 yamt
937 1.2.2.2 yamt static void
938 1.2.2.2 yamt mavb_button_repeat(void *hdl)
939 1.2.2.2 yamt {
940 1.2.2.2 yamt struct mavb_softc *sc = (struct mavb_softc *)hdl;
941 1.2.2.2 yamt u_int64_t intmask, control;
942 1.2.2.2 yamt u_int16_t value, left, right;
943 1.2.2.2 yamt
944 1.2.2.2 yamt DPRINTF(1, ("%s: mavb_repeat called\n", sc->sc_dev.dv_xname));
945 1.2.2.2 yamt
946 1.2.2.2 yamt #define MAVB_CONTROL_VOLUME_BUTTONS \
947 1.2.2.2 yamt (MAVB_CONTROL_VOLUME_BUTTON_UP | MAVB_CONTROL_VOLUME_BUTTON_DOWN)
948 1.2.2.2 yamt
949 1.2.2.2 yamt control = bus_space_read_8(sc->sc_st, sc->sc_sh, MAVB_CONTROL);
950 1.2.2.2 yamt if (control & MAVB_CONTROL_VOLUME_BUTTONS) {
951 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_DAC1_ANALOG_GAIN);
952 1.2.2.2 yamt left = (value & AD1843_LDA1G_MASK) >> AD1843_LDA1G_SHIFT;
953 1.2.2.2 yamt right = (value & AD1843_RDA1G_MASK) >> AD1843_RDA1G_SHIFT;
954 1.2.2.2 yamt if (control & MAVB_CONTROL_VOLUME_BUTTON_UP) {
955 1.2.2.2 yamt control &= ~MAVB_CONTROL_VOLUME_BUTTON_UP;
956 1.2.2.2 yamt if (left > 0)
957 1.2.2.2 yamt left--; /* attenuation! */
958 1.2.2.2 yamt if (right > 0)
959 1.2.2.2 yamt right--;
960 1.2.2.2 yamt }
961 1.2.2.2 yamt if (control & MAVB_CONTROL_VOLUME_BUTTON_DOWN) {
962 1.2.2.2 yamt control &= ~MAVB_CONTROL_VOLUME_BUTTON_DOWN;
963 1.2.2.2 yamt if (left < 63)
964 1.2.2.2 yamt left++;
965 1.2.2.2 yamt if (right < 63)
966 1.2.2.2 yamt right++;
967 1.2.2.2 yamt }
968 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CONTROL, control);
969 1.2.2.2 yamt
970 1.2.2.2 yamt value &= ~(AD1843_LDA1G_MASK | AD1843_RDA1G_MASK);
971 1.2.2.2 yamt value |= (left << AD1843_LDA1G_SHIFT);
972 1.2.2.2 yamt value |= (right << AD1843_RDA1G_SHIFT);
973 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_DAC1_ANALOG_GAIN, value);
974 1.2.2.2 yamt
975 1.2.2.2 yamt callout_reset(&sc->sc_volume_button_ch,
976 1.2.2.2 yamt (hz * MAVB_VOLUME_BUTTON_REPEAT_DELN) / 1000,
977 1.2.2.2 yamt mavb_button_repeat, sc);
978 1.2.2.2 yamt } else {
979 1.2.2.2 yamt /* Enable volume button interrupts again. */
980 1.2.2.2 yamt intmask = bus_space_read_8(sc->sc_st, sc->sc_isash,
981 1.2.2.2 yamt MACE_ISA_INT_MASK);
982 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_isash, MACE_ISA_INT_MASK,
983 1.2.2.2 yamt intmask | MACE_ISA_INT_AUDIO_SC);
984 1.2.2.2 yamt }
985 1.2.2.2 yamt }
986 1.2.2.2 yamt
987 1.2.2.2 yamt static int
988 1.2.2.2 yamt mavb_intr(void *arg)
989 1.2.2.2 yamt {
990 1.2.2.2 yamt struct mavb_softc *sc = arg;
991 1.2.2.2 yamt u_int64_t stat, intmask;
992 1.2.2.2 yamt
993 1.2.2.2 yamt stat = bus_space_read_8(sc->sc_st, sc->sc_isash, MACE_ISA_INT_STATUS);
994 1.2.2.2 yamt DPRINTF(MAVB_DEBUG_INTR, ("%s: mavb_intr: stat = 0x%llx\n",
995 1.2.2.2 yamt sc->sc_dev.dv_xname, stat));
996 1.2.2.2 yamt
997 1.2.2.2 yamt if (stat & MACE_ISA_INT_AUDIO_SC) {
998 1.2.2.2 yamt /* Disable volume button interrupts. */
999 1.2.2.2 yamt intmask = bus_space_read_8(sc->sc_st, sc->sc_isash,
1000 1.2.2.2 yamt MACE_ISA_INT_MASK);
1001 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_isash, MACE_ISA_INT_MASK,
1002 1.2.2.2 yamt intmask & ~MACE_ISA_INT_AUDIO_SC);
1003 1.2.2.2 yamt
1004 1.2.2.2 yamt callout_reset(&sc->sc_volume_button_ch,
1005 1.2.2.2 yamt (hz * MAVB_VOLUME_BUTTON_REPEAT_DEL1) / 1000,
1006 1.2.2.2 yamt mavb_button_repeat, sc);
1007 1.2.2.2 yamt }
1008 1.2.2.2 yamt
1009 1.2.2.2 yamt if (stat & MACE_ISA_INT_AUDIO_DMA2)
1010 1.2.2.2 yamt mavb_dma_output(sc);
1011 1.2.2.2 yamt
1012 1.2.2.2 yamt return 1;
1013 1.2.2.2 yamt }
1014 1.2.2.2 yamt
1015 1.2.2.2 yamt int
1016 1.2.2.2 yamt mavb_match(struct device *parent, struct cfdata *match, void *aux)
1017 1.2.2.2 yamt {
1018 1.2.2.2 yamt return (1);
1019 1.2.2.2 yamt }
1020 1.2.2.2 yamt
1021 1.2.2.2 yamt void
1022 1.2.2.2 yamt mavb_attach(struct device *parent, struct device *self, void *aux)
1023 1.2.2.2 yamt {
1024 1.2.2.2 yamt struct mavb_softc *sc = (void *)self;
1025 1.2.2.2 yamt struct mace_attach_args *maa = aux;
1026 1.2.2.2 yamt bus_dma_segment_t seg;
1027 1.2.2.2 yamt u_int64_t control;
1028 1.2.2.2 yamt u_int16_t value;
1029 1.2.2.2 yamt int rseg;
1030 1.2.2.2 yamt
1031 1.2.2.2 yamt sc->sc_st = maa->maa_st;
1032 1.2.2.2 yamt if (bus_space_subregion(sc->sc_st, maa->maa_sh, maa->maa_offset,
1033 1.2.2.2 yamt 0, &sc->sc_sh) != 0) {
1034 1.2.2.2 yamt printf(": can't map i/o space\n");
1035 1.2.2.2 yamt return;
1036 1.2.2.2 yamt }
1037 1.2.2.2 yamt
1038 1.2.2.2 yamt /* XXX We need access to some of the MACE ISA registers. */
1039 1.2.2.2 yamt if (bus_space_subregion(sc->sc_st, maa->maa_sh, 0, 0,
1040 1.2.2.2 yamt &sc->sc_isash) != 0) {
1041 1.2.2.2 yamt printf(": can't map isa i/o space\n");
1042 1.2.2.2 yamt return;
1043 1.2.2.2 yamt }
1044 1.2.2.2 yamt
1045 1.2.2.2 yamt /* Set up DMA structures. */
1046 1.2.2.2 yamt sc->sc_dmat = maa->maa_dmat;
1047 1.2.2.2 yamt if (bus_dmamap_create(sc->sc_dmat, 4 * MAVB_ISA_RING_SIZE, 1,
1048 1.2.2.2 yamt 4 * MAVB_ISA_RING_SIZE, 0, 0, &sc->sc_dmamap)) {
1049 1.2.2.2 yamt printf(": can't create MACE ISA DMA map\n");
1050 1.2.2.2 yamt return;
1051 1.2.2.2 yamt }
1052 1.2.2.2 yamt
1053 1.2.2.2 yamt if (bus_dmamem_alloc(sc->sc_dmat, 4 * MAVB_ISA_RING_SIZE,
1054 1.2.2.2 yamt MACE_ISA_RING_ALIGN, 0, &seg, 1, &rseg, BUS_DMA_NOWAIT)) {
1055 1.2.2.2 yamt printf(": can't allocate ring buffer\n");
1056 1.2.2.2 yamt return;
1057 1.2.2.2 yamt }
1058 1.2.2.2 yamt
1059 1.2.2.2 yamt if (bus_dmamem_map(sc->sc_dmat, &seg, rseg, 4 * MAVB_ISA_RING_SIZE,
1060 1.2.2.2 yamt (void *)&sc->sc_ring, BUS_DMA_COHERENT)) {
1061 1.2.2.2 yamt printf(": can't map ring buffer\n");
1062 1.2.2.2 yamt return;
1063 1.2.2.2 yamt }
1064 1.2.2.2 yamt
1065 1.2.2.2 yamt if (bus_dmamap_load(sc->sc_dmat, sc->sc_dmamap, sc->sc_ring,
1066 1.2.2.2 yamt 4 * MAVB_ISA_RING_SIZE, NULL, BUS_DMA_NOWAIT)) {
1067 1.2.2.2 yamt printf(": can't load MACE ISA DMA map\n");
1068 1.2.2.2 yamt return;
1069 1.2.2.2 yamt }
1070 1.2.2.2 yamt
1071 1.2.2.2 yamt sc->sc_ring += MAVB_ISA_RING_SIZE; /* XXX */
1072 1.2.2.2 yamt
1073 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_isash, MACE_ISA_RINGBASE,
1074 1.2.2.2 yamt sc->sc_dmamap->dm_segs[0].ds_addr);
1075 1.2.2.2 yamt
1076 1.2.2.2 yamt /* Establish interrupt. */
1077 1.2.2.2 yamt cpu_intr_establish(maa->maa_intr, maa->maa_intrmask,
1078 1.2.2.2 yamt mavb_intr, sc);
1079 1.2.2.2 yamt
1080 1.2.2.2 yamt control = bus_space_read_8(sc->sc_st, sc->sc_sh, MAVB_CONTROL);
1081 1.2.2.2 yamt if (!(control & MAVB_CONTROL_CODEC_PRESENT)) {
1082 1.2.2.2 yamt printf(": no codec present\n");
1083 1.2.2.2 yamt return;
1084 1.2.2.2 yamt }
1085 1.2.2.2 yamt
1086 1.2.2.2 yamt /* 2. Assert the RESET signal. */
1087 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CONTROL,
1088 1.2.2.2 yamt MAVB_CONTROL_RESET);
1089 1.2.2.2 yamt delay(1); /* at least 100 ns */
1090 1.2.2.2 yamt
1091 1.2.2.2 yamt /* 3. Deassert the RESET signal and enter a wait period to
1092 1.2.2.2 yamt allow the AD1843 internal clocks and the external
1093 1.2.2.2 yamt crystal oscillator to stabilize. */
1094 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CONTROL, 0);
1095 1.2.2.2 yamt delay(800); /* typically 400 us to 800 us */
1096 1.2.2.2 yamt if (ad1843_reg_read(sc, AD1843_CODEC_STATUS) & AD1843_INIT) {
1097 1.2.2.2 yamt printf(": codec not ready\n");
1098 1.2.2.2 yamt return;
1099 1.2.2.2 yamt }
1100 1.2.2.2 yamt
1101 1.2.2.2 yamt /* 4. Put the conversion sources into standby. */
1102 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_FUNDAMENTAL_SETTINGS);
1103 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_FUNDAMENTAL_SETTINGS,
1104 1.2.2.2 yamt value & ~AD1843_PDNI);
1105 1.2.2.2 yamt delay (500000); /* approximately 474 ms */
1106 1.2.2.2 yamt if (ad1843_reg_read(sc, AD1843_CODEC_STATUS) & AD1843_PDNO) {
1107 1.2.2.2 yamt printf(": can't power up conversion resources\n");
1108 1.2.2.2 yamt return;
1109 1.2.2.2 yamt }
1110 1.2.2.2 yamt
1111 1.2.2.2 yamt /* 5. Power up the clock generators and enable clock output pins. */
1112 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_FUNDAMENTAL_SETTINGS);
1113 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_FUNDAMENTAL_SETTINGS, value | AD1843_C2EN);
1114 1.2.2.2 yamt
1115 1.2.2.2 yamt /* 6. Configure conversion resources while they are in standby. */
1116 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_CHANNEL_SAMPLE_RATE);
1117 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_CHANNEL_SAMPLE_RATE,
1118 1.2.2.2 yamt value | (2 << AD1843_DA1C_SHIFT));
1119 1.2.2.2 yamt
1120 1.2.2.2 yamt /* 7. Enable conversion resources. */
1121 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_CHANNEL_POWER_DOWN);
1122 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_CHANNEL_POWER_DOWN,
1123 1.2.2.2 yamt value | (AD1843_DA1EN | AD1843_AAMEN));
1124 1.2.2.2 yamt
1125 1.2.2.2 yamt /* 8. Configure conversion resources while they are enabled. */
1126 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_DAC1_ANALOG_GAIN);
1127 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_DAC1_ANALOG_GAIN,
1128 1.2.2.2 yamt value & ~(AD1843_LDA1GM | AD1843_RDA1GM));
1129 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_DAC1_DIGITAL_GAIN);
1130 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_DAC1_DIGITAL_GAIN,
1131 1.2.2.2 yamt value & ~(AD1843_LDA1AM | AD1843_RDA1AM));
1132 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_MISC_SETTINGS);
1133 1.2.2.2 yamt ad1843_reg_write(sc, AD1843_MISC_SETTINGS,
1134 1.2.2.2 yamt value & ~(AD1843_HPOM | AD1843_MNOM));
1135 1.2.2.2 yamt
1136 1.2.2.2 yamt value = ad1843_reg_read(sc, AD1843_CODEC_STATUS);
1137 1.2.2.2 yamt printf(": AD1843 rev %d\n", (u_int)value & AD1843_REVISION_MASK);
1138 1.2.2.2 yamt
1139 1.2.2.2 yamt sc->sc_play_rate = 48000;
1140 1.2.2.2 yamt sc->sc_play_format = AD1843_PCM8;
1141 1.2.2.2 yamt
1142 1.2.2.2 yamt callout_init(&sc->sc_volume_button_ch);
1143 1.2.2.2 yamt
1144 1.2.2.2 yamt audio_attach_mi(&mavb_sa_hw_if, sc, &sc->sc_dev);
1145 1.2.2.2 yamt
1146 1.2.2.2 yamt return;
1147 1.2.2.2 yamt }
1148 1.2.2.2 yamt
1149 1.2.2.2 yamt u_int16_t
1150 1.2.2.2 yamt ad1843_reg_read(struct mavb_softc *sc, ad1843_addr_t addr)
1151 1.2.2.2 yamt {
1152 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CODEC_CONTROL,
1153 1.2.2.2 yamt (addr & MAVB_CODEC_ADDRESS_MASK) << MAVB_CODEC_ADDRESS_SHIFT |
1154 1.2.2.2 yamt MAVB_CODEC_READ);
1155 1.2.2.2 yamt delay(200);
1156 1.2.2.2 yamt return bus_space_read_8(sc->sc_st, sc->sc_sh, MAVB_CODEC_STATUS);
1157 1.2.2.2 yamt }
1158 1.2.2.2 yamt
1159 1.2.2.2 yamt u_int16_t
1160 1.2.2.2 yamt ad1843_reg_write(struct mavb_softc *sc, ad1843_addr_t addr, u_int16_t value)
1161 1.2.2.2 yamt {
1162 1.2.2.2 yamt bus_space_write_8(sc->sc_st, sc->sc_sh, MAVB_CODEC_CONTROL,
1163 1.2.2.2 yamt (addr & MAVB_CODEC_ADDRESS_MASK) << MAVB_CODEC_ADDRESS_SHIFT |
1164 1.2.2.2 yamt (value & MAVB_CODEC_WORD_MASK) << MAVB_CODEC_WORD_SHIFT);
1165 1.2.2.2 yamt delay(200);
1166 1.2.2.2 yamt return bus_space_read_8(sc->sc_st, sc->sc_sh, MAVB_CODEC_STATUS);
1167 1.2.2.2 yamt }
1168 1.2.2.2 yamt
1169 1.2.2.2 yamt void
1170 1.2.2.2 yamt ad1843_dump_regs(struct mavb_softc *sc)
1171 1.2.2.2 yamt {
1172 1.2.2.2 yamt u_int16_t addr;
1173 1.2.2.2 yamt
1174 1.2.2.2 yamt for (addr = 0; addr < AD1843_NREGS; addr++)
1175 1.2.2.2 yamt printf("%d: 0x%04x\n", addr, ad1843_reg_read(sc, addr));
1176 1.2.2.2 yamt }
1177