uda1341.c revision 1.4 1 /* $NetBSD: uda1341.c,v 1.4 2002/10/02 05:18:53 thorpej Exp $ */
2
3 /*-
4 * Copyright (c) 2001 The NetBSD Foundation, Inc. All rights reserved.
5 *
6 * This code is derived from software contributed to The NetBSD Foundation
7 * by Ichiro FUKUHARA (ichiro (at) ichiro.org).
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 * 1. Redistributions of source code must retain the above copyright
13 * notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 * notice, this list of conditions and the following disclaimer in the
16 * documentation and/or other materials provided with the distribution.
17 * 3. All advertising materials mentioning features or use of this software
18 * must display the following acknowledgement:
19 * This product includes software developed by the NetBSD
20 * Foundation, Inc. and its contributors.
21 * 4. Neither the name of The NetBSD Foundation nor the names of its
22 * contributors may be used to endorse or promote products derived
23 * from this software without specific prior written permission.
24 *
25 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
26 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
27 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
28 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
29 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
30 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
31 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
32 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
33 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
34 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
35 * POSSIBILITY OF SUCH DAMAGE.
36 */
37
38 #include <sys/param.h>
39 #include <sys/systm.h>
40 #include <sys/types.h>
41 #include <sys/conf.h>
42 #include <sys/file.h>
43 #include <sys/device.h>
44 #include <sys/kernel.h>
45 #include <sys/kthread.h>
46 #include <sys/malloc.h>
47
48 #include <machine/bus.h>
49
50 #include <hpcarm/dev/ipaq_saipvar.h>
51 #include <hpcarm/dev/ipaq_gpioreg.h>
52 #include <hpcarm/dev/uda1341.h>
53 #include <hpcarm/sa11x0/sa11x0_gpioreg.h>
54 #include <hpcarm/sa11x0/sa11x0_sspreg.h>
55
56 struct uda1341_softc {
57 struct device sc_dev;
58 bus_space_tag_t sc_iot;
59 bus_space_handle_t sc_ioh;
60 struct ipaq_softc *sc_parent;
61 };
62
63 static int uda1341_match(struct device *, struct cfdata *, void *);
64 static void uda1341_attach(struct device *, struct device *, void *);
65 static int uda1341_print(void *, const char *);
66 static int uda1341_search(struct device *, struct cfdata *, void *);
67
68 static void uda1341_output_high(struct uda1341_softc *);
69 static void uda1341_output_low(struct uda1341_softc *);
70 static void uda1341_L3_init(struct uda1341_softc *);
71 static void uda1341_init(struct uda1341_softc *);
72 static void uda1341_reset(struct uda1341_softc *);
73 static void uda1341_reginit(struct uda1341_softc *);
74
75 static int L3_getbit(struct uda1341_softc *);
76 static void L3_sendbit(struct uda1341_softc *, int);
77 static u_int8_t L3_getbyte(struct uda1341_softc *, int);
78 static void L3_sendbyte(struct uda1341_softc *, u_int8_t, int);
79 static int L3_read(struct uda1341_softc *, u_int8_t, u_int8_t *, int);
80 static int L3_write(struct uda1341_softc *, u_int8_t, u_int8_t *, int);
81
82 CFATTACH_DECL(uda, sizeof(struct uda1341_softc),
83 uda1341_match, uda1341_attach, NULL, NULL);
84
85 /*
86 * Philips L3 bus support.
87 * GPIO lines are used for clock, data and mode pins.
88 */
89 #define L3_DATA GPIO_H3600_L3_DATA
90 #define L3_MODE GPIO_H3600_L3_MODE
91 #define L3_CLK GPIO_H3600_L3_CLK
92
93 static struct {
94 u_int8_t data0; /* direct addressing register */
95 } DIRECT_REG = {0};
96
97 static struct {
98 u_int8_t data0; /* extended addressing register 1 */
99 u_int8_t data1; /* extended addressing register 2 */
100 } EXTEND_REG = {0, 0};
101
102 /*
103 * register space access macros
104 */
105 #define GPIO_WRITE(sc, reg, val) \
106 bus_space_write_4(sc->sc_iot, sc->sc_parent->sc_gpioh, reg, val)
107 #define GPIO_READ(sc, reg) \
108 bus_space_read_4(sc->sc_iot, sc->sc_parent->sc_gpioh, reg)
109 #define EGPIO_WRITE(sc) \
110 bus_space_write_2(sc->sc_iot, sc->sc_parent->sc_egpioh, \
111 0, sc->sc_parent->ipaq_egpio)
112 #define SSP_WRITE(sc, reg, val) \
113 bus_space_write_4(sc->sc_iot, sc->sc_parent->sc_ssph, reg, val)
114
115 static int
116 uda1341_match(parent, cf, aux)
117 struct device *parent;
118 struct cfdata *cf;
119 void *aux;
120 {
121 return (1);
122 }
123
124 static void
125 uda1341_attach(parent, self, aux)
126 struct device *parent;
127 struct device *self;
128 void *aux;
129 {
130 struct uda1341_softc *sc = (struct uda1341_softc *)self;
131 struct ipaq_softc *psc = (struct ipaq_softc *)parent;
132
133 printf("\n");
134 printf("%s: UDA1341 CODEC\n", sc->sc_dev.dv_xname);
135
136 sc->sc_iot = psc->sc_iot;
137 sc->sc_ioh = psc->sc_ioh;
138 sc->sc_parent = (struct ipaq_softc *)parent;
139
140 uda1341_L3_init(sc);
141 uda1341_init(sc);
142
143 uda1341_reset(sc);
144
145 uda1341_reginit(sc);
146
147
148 /*
149 * Attach each devices
150 */
151
152 config_search(uda1341_search, self, NULL);
153 }
154
155 static int
156 uda1341_search(parent, cf, aux)
157 struct device *parent;
158 struct cfdata *cf;
159 void *aux;
160 {
161 if (config_match(parent, cf, NULL) > 0)
162 config_attach(parent, cf, NULL, uda1341_print);
163 return 0;
164 }
165
166
167 static int
168 uda1341_print(aux, name)
169 void *aux;
170 const char *name;
171 {
172 return (UNCONF);
173 }
174
175 static void
176 uda1341_output_high(sc)
177 struct uda1341_softc *sc;
178 {
179 int cr;
180
181 GPIO_WRITE(sc, SAGPIO_PSR, (L3_DATA | L3_MODE | L3_CLK));
182 cr = GPIO_READ(sc, SAGPIO_PDR) | (L3_DATA | L3_MODE | L3_CLK);
183 GPIO_WRITE(sc, SAGPIO_PDR, cr);
184 }
185
186 static void
187 uda1341_output_low(sc)
188 struct uda1341_softc *sc;
189 {
190 int cr;
191
192 cr = GPIO_READ(sc, SAGPIO_PDR);
193 cr &= ~(L3_DATA | L3_MODE | L3_CLK);
194 GPIO_WRITE(sc, SAGPIO_PDR, cr);
195 }
196
197 static void
198 uda1341_L3_init(sc)
199 struct uda1341_softc *sc;
200 {
201 int cr;
202
203 cr = GPIO_READ(sc, SAGPIO_AFR);
204 cr &= ~(L3_DATA | L3_MODE | L3_CLK);
205 GPIO_WRITE(sc, SAGPIO_AFR, cr);
206
207 uda1341_output_low(sc);
208 }
209
210 static void
211 uda1341_init(sc)
212 struct uda1341_softc *sc;
213 {
214 int cr;
215
216 /* GPIO initialize */
217 cr = GPIO_READ(sc, SAGPIO_AFR);
218 cr &= ~(GPIO_ALT_SSP_TXD | GPIO_ALT_SSP_RXD | GPIO_ALT_SSP_SCLK |
219 GPIO_ALT_SSP_SFRM);
220 cr |= GPIO_ALT_SSP_CLK;
221 GPIO_WRITE(sc, SAGPIO_AFR, cr);
222
223 cr = GPIO_READ(sc, SAGPIO_PDR);
224 cr &= ~GPIO_ALT_SSP_CLK;
225 GPIO_WRITE(sc, SAGPIO_PDR, cr);
226
227 /* SSP initialize & enable */
228 SSP_WRITE(sc, SASSP_CR1, CR1_ECS);
229 cr = 0xF | (CR0_FRF_MASK & (1<<4)) | (CR0_SCR_MASK & (3<<8)) | CR0_SSE;
230 SSP_WRITE(sc, SASSP_CR0, cr);
231
232 /* Enable the audio power */
233 sc->sc_parent->ipaq_egpio |=
234 (EGPIO_H3600_AUD_PWRON | EGPIO_H3600_AUD_ON);
235 sc->sc_parent->ipaq_egpio &=
236 ~(EGPIO_H3600_CODEC_RESET | EGPIO_H3600_QMUTE);
237 EGPIO_WRITE(sc);
238
239 /* external clock configured for 44100 samples/sec */
240 cr = GPIO_READ(sc, SAGPIO_PDR);
241 cr |= (GPIO_H3600_CLK_SET0 | GPIO_H3600_CLK_SET1);
242 GPIO_WRITE(sc, SAGPIO_PDR, cr);
243 GPIO_WRITE(sc, SAGPIO_PSR, GPIO_H3600_CLK_SET0);
244 GPIO_WRITE(sc, SAGPIO_PCR, GPIO_H3600_CLK_SET1);
245
246 /* wait for power on */
247 delay(100*1000);
248 sc->sc_parent->ipaq_egpio |= EGPIO_H3600_CODEC_RESET;
249 EGPIO_WRITE(sc);
250
251 /* Wait for the UDA1341 to wake up */
252 delay(100*1000);
253 }
254
255 static void
256 uda1341_reset(sc)
257 struct uda1341_softc *sc;
258 {
259 u_int8_t command;
260
261 command = (L3_ADDRESS_COM << 2) | L3_ADDRESS_STATUS;
262 DIRECT_REG.data0 = STATUS0_RST | STATUS0_SC_256 | STATUS0_IF_LSB16;
263 L3_write(sc, command, (u_int8_t *) &DIRECT_REG, 1);
264
265 sc->sc_parent->ipaq_egpio &= ~EGPIO_H3600_CODEC_RESET;
266 EGPIO_WRITE(sc);
267 sc->sc_parent->ipaq_egpio |= EGPIO_H3600_CODEC_RESET;
268 EGPIO_WRITE(sc);
269
270 DIRECT_REG.data0 &= ~STATUS0_RST;
271 L3_write(sc, command, (u_int8_t *) &DIRECT_REG, 1);
272 }
273
274 static void
275 uda1341_reginit(sc)
276 struct uda1341_softc *sc;
277 {
278 u_int8_t command;
279
280 /* STATUS 0 */
281 command = (L3_ADDRESS_COM << 2) | L3_ADDRESS_STATUS;
282 DIRECT_REG.data0 = STATUS0_SC_256 | STATUS0_IF_LSB16;
283 L3_write(sc, command, (u_int8_t *) &DIRECT_REG, 1);
284
285 /* STATUS 1 */
286 DIRECT_REG.data0 = STATUS1_OGS | STATUS1_IGS | (1<<7);
287 L3_write(sc, command, (u_int8_t *) &DIRECT_REG, 1);
288
289 /* DATA 0 */
290 command = (L3_ADDRESS_COM << 2) | L3_ADDRESS_DATA0;
291 DIRECT_REG.data0 = DATA0_VC(100) | DATA0_COMMON;
292 L3_write(sc, command, (u_int8_t *) &DIRECT_REG, 1);
293
294 /* DATA 1 */
295 DIRECT_REG.data0 = DATA1_BB(0) | DATA1_TR(0) | DATA1_COMMON;
296 L3_write(sc, command, (u_int8_t *) &DIRECT_REG, 1);
297
298 /* DATA 2*/
299 DIRECT_REG.data0 = DATA2_PP | DATA2_COMMON;
300 L3_write(sc, command, (u_int8_t *) &DIRECT_REG, 1);
301
302 /* Extended DATA 0 */
303 EXTEND_REG.data0 = EXT_ADDR_COMMON | EXT_ADDR_E0;
304 EXTEND_REG.data1 = EXT_DATA_COMMN | 0x4 ;
305 L3_write(sc, command, (u_int8_t *) &EXTEND_REG, 2);
306
307 /* Extended DATA 1 */
308 EXTEND_REG.data0 = EXT_ADDR_COMMON | EXT_ADDR_E1;
309 EXTEND_REG.data1 = EXT_DATA_COMMN | 0x4 ;
310 L3_write(sc, command, (u_int8_t *) &EXTEND_REG, 2);
311
312 /* Extended DATA 2 */
313 EXTEND_REG.data0 = EXT_ADDR_COMMON | EXT_ADDR_E2;
314 EXTEND_REG.data1 = EXT_DATA_COMMN | DATA_E2_MS(30);
315 L3_write(sc, command, (u_int8_t *) &EXTEND_REG, 2);
316
317 /* Extended DATA 3 */
318 EXTEND_REG.data0 = EXT_ADDR_COMMON | EXT_ADDR_E3;
319 EXTEND_REG.data1 = EXT_DATA_COMMN | DATA_E3_IG_L(0);
320 L3_write(sc, command, (u_int8_t *) &EXTEND_REG, 2);
321
322 /* Extended DATA 4 */
323 EXTEND_REG.data0 = EXT_ADDR_COMMON | EXT_ADDR_E4;
324 EXTEND_REG.data1 = EXT_DATA_COMMN | DATA_E4_IG_H(0);
325 L3_write(sc, command, (u_int8_t *) &EXTEND_REG, 2);
326
327 /* Extended DATA 5 */
328 EXTEND_REG.data0 = EXT_ADDR_COMMON | EXT_ADDR_E5;
329 EXTEND_REG.data1 = EXT_DATA_COMMN;
330 L3_write(sc, command, (u_int8_t *) &EXTEND_REG, 2);
331 }
332
333 static int
334 L3_getbit(sc)
335 struct uda1341_softc *sc;
336 {
337 int cr, data;
338
339 GPIO_WRITE(sc, SAGPIO_PCR, L3_CLK); /* Clock down */
340 delay(L3_CLK_LOW);
341
342 cr = GPIO_READ(sc, SAGPIO_PLR);
343 data = (cr & L3_DATA) ? 1 : 0;
344
345 GPIO_WRITE(sc, SAGPIO_PSR, L3_CLK); /* Clock up */
346 delay(L3_CLK_HIGH);
347
348 return (data);
349 }
350
351 static void
352 L3_sendbit(sc, bit)
353 struct uda1341_softc *sc;
354 int bit;
355 {
356 GPIO_WRITE(sc, SAGPIO_PCR, L3_CLK); /* Clock down */
357
358 if (bit & 0x01)
359 GPIO_WRITE(sc, SAGPIO_PSR, L3_DATA);
360 else
361 GPIO_WRITE(sc, SAGPIO_PCR, L3_DATA);
362
363 delay(L3_CLK_LOW);
364 GPIO_WRITE(sc, SAGPIO_PSR, L3_CLK); /* Clock up */
365 delay(L3_CLK_HIGH);
366 }
367
368 static u_int8_t
369 L3_getbyte(sc, mode)
370 struct uda1341_softc *sc;
371 int mode;
372 {
373 int i;
374 u_int8_t data;
375
376 switch (mode) {
377 case 0: /* Address mode */
378 case 1: /* First data byte */
379 break;
380 default: /* second data byte via halt-Time */
381 GPIO_WRITE(sc, SAGPIO_PCR, L3_CLK); /* Clock down */
382 delay(L3_HALT);
383 GPIO_WRITE(sc, SAGPIO_PSR, L3_CLK); /* Clock up */
384 break;
385 }
386
387 delay(L3_MODE_SETUP);
388
389 for (i = 0; i < 8; i++)
390 data |= (L3_getbit(sc) << i);
391
392 delay(L3_MODE_HOLD);
393
394 return (data);
395 }
396
397 static void
398 L3_sendbyte(sc, data, mode)
399 struct uda1341_softc *sc;
400 u_int8_t data;
401 int mode;
402 {
403 int i;
404
405 switch (mode) {
406 case 0: /* Address mode */
407 GPIO_WRITE(sc, SAGPIO_PCR, L3_CLK); /* Clock down */
408 break;
409 case 1: /* First data byte */
410 break;
411 default: /* second data byte via halt-Time */
412 GPIO_WRITE(sc, SAGPIO_PCR, L3_CLK); /* Clock down */
413 delay(L3_HALT);
414 GPIO_WRITE(sc, SAGPIO_PSR, L3_CLK); /* Clock up */
415 break;
416 }
417
418 delay(L3_MODE_SETUP);
419
420 for (i = 0; i < 8; i++)
421 L3_sendbit(sc, data >> i);
422
423 if (mode == 0) /* Address mode */
424 GPIO_WRITE(sc, SAGPIO_PSR, L3_CLK); /* Clock up */
425
426 delay(L3_MODE_HOLD);
427 }
428
429 static int
430 L3_read(sc, addr, data, len)
431 struct uda1341_softc *sc;
432 u_int8_t addr, *data;
433 int len;
434 {
435 int cr, mode;
436 mode = 0;
437
438 uda1341_output_high(sc);
439 L3_sendbyte(sc, addr, mode++);
440
441 cr = GPIO_READ(sc, SAGPIO_PDR);
442 cr &= ~(L3_DATA);
443 GPIO_WRITE(sc, SAGPIO_PDR, cr);
444
445 while(len--)
446 *data++ = L3_getbyte(sc, mode++);
447 uda1341_output_low(sc);
448
449 return len;
450 }
451
452 static int
453 L3_write(sc, addr, data, len)
454 struct uda1341_softc *sc;
455 u_int8_t addr, *data;
456 int len;
457 {
458 int mode = 0;
459
460 uda1341_output_high(sc);
461 L3_sendbyte(sc, addr, mode++);
462 while(len--)
463 L3_sendbyte(sc, *data++, mode++);
464 uda1341_output_low(sc);
465
466 return len;
467 }
468