]>
Commit | Line | Data |
---|---|---|
6617aae9 WD |
1 | /* |
2 | * (C) Copyright 2005 | |
3 | * Martin Krause, TQ-Systems GmbH, martin.krause@tqs.de. | |
4 | * | |
5 | * See file CREDITS for list of people who contributed to this | |
6 | * project. | |
7 | * | |
8 | * This program is free software; you can redistribute it and/or | |
9 | * modify it under the terms of the GNU General Public License as | |
10 | * published by the Free Software Foundation; either version 2 of | |
11 | * the License, or (at your option) any later version. | |
12 | * | |
13 | * This program is distributed in the hope that it will be useful, | |
14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
16 | * GNU General Public License for more details. | |
17 | * | |
18 | * You should have received a copy of the GNU General Public License | |
19 | * along with this program; if not, write to the Free Software | |
20 | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, | |
21 | * MA 02111-1307 USA | |
22 | */ | |
23 | ||
24 | /* | |
45a212c4 | 25 | * STK52XX specific functions |
6617aae9 WD |
26 | */ |
27 | /*#define DEBUG*/ | |
28 | ||
29 | #include <common.h> | |
30 | #include <command.h> | |
31 | ||
ab3abcba | 32 | #if defined(CONFIG_CMD_BSP) |
6617aae9 | 33 | |
6d3bc9b8 | 34 | #if defined(CONFIG_STK52XX) || defined(CONFIG_FO300) |
6617aae9 WD |
35 | #define DEFAULT_VOL 45 |
36 | #define DEFAULT_FREQ 500 | |
37 | #define DEFAULT_DURATION 200 | |
38 | #define LEFT 1 | |
39 | #define RIGHT 2 | |
40 | #define LEFT_RIGHT 3 | |
41 | #define BL_OFF 0 | |
42 | #define BL_ON 1 | |
43 | ||
44 | #define SM501_GPIO_CTRL_LOW 0x00000008UL | |
45 | #define SM501_GPIO_CTRL_HIGH 0x0000000CUL | |
46 | #define SM501_POWER_MODE0_GATE 0x00000040UL | |
47 | #define SM501_POWER_MODE1_GATE 0x00000048UL | |
48 | #define POWER_MODE_GATE_GPIO_PWM_I2C 0x00000040UL | |
49 | #define SM501_GPIO_DATA_LOW 0x00010000UL | |
50 | #define SM501_GPIO_DATA_HIGH 0x00010004UL | |
51 | #define SM501_GPIO_DATA_DIR_LOW 0x00010008UL | |
52 | #define SM501_GPIO_DATA_DIR_HIGH 0x0001000CUL | |
53 | #define SM501_PANEL_DISPLAY_CONTROL 0x00080000UL | |
54 | ||
55 | static int i2s_squarewave(unsigned long duration, unsigned int freq, | |
56 | unsigned int channel); | |
57 | static int i2s_sawtooth(unsigned long duration, unsigned int freq, | |
58 | unsigned int channel); | |
59 | static void spi_init(void); | |
60 | static int spi_transmit(unsigned char data); | |
61 | static void pcm1772_write_reg(unsigned char addr, unsigned char data); | |
62 | static void set_attenuation(unsigned char attenuation); | |
63 | ||
6617aae9 WD |
64 | static void spi_init(void) |
65 | { | |
66 | struct mpc5xxx_spi *spi = (struct mpc5xxx_spi*)MPC5XXX_SPI; | |
67 | struct mpc5xxx_gpio *gpio = (struct mpc5xxx_gpio*)MPC5XXX_GPIO; | |
68 | ||
69 | /* PSC3 as SPI and GPIOs */ | |
70 | gpio->port_config &= 0xFFFFF0FF; | |
71 | gpio->port_config |= 0x00000800; | |
72 | /* | |
73 | * Its important to use the correct order when initializing the | |
74 | * registers | |
75 | */ | |
76 | spi->ddr = 0x0F; /* set all SPI pins as output */ | |
77 | spi->pdr = 0x08; /* set SS high */ | |
78 | spi->cr1 = 0x50; /* SPI is master, SS is general purpose output */ | |
79 | spi->cr2 = 0x00; /* normal operation */ | |
80 | spi->brr = 0xFF; /* baud rate: IPB clock / 2048 */ | |
81 | } | |
82 | ||
83 | static int spi_transmit(unsigned char data) | |
84 | { | |
85 | int dummy; | |
86 | struct mpc5xxx_spi *spi = (struct mpc5xxx_spi*)MPC5XXX_SPI; | |
87 | ||
88 | spi->dr = data; | |
89 | /* wait for SPI transmission completed */ | |
90 | while(!(spi->sr & 0x80)) | |
91 | { | |
92 | if (spi->sr & 0x40) /* if write collision occured */ | |
93 | { | |
94 | /* do dummy read to clear status register */ | |
95 | dummy = spi->dr; | |
96 | printf ("SPI write collision\n"); | |
97 | return -1; | |
98 | } | |
99 | } | |
100 | return (spi->dr); | |
101 | } | |
102 | ||
103 | static void pcm1772_write_reg(unsigned char addr, unsigned char data) | |
104 | { | |
105 | struct mpc5xxx_spi *spi = (struct mpc5xxx_spi*)MPC5XXX_SPI; | |
106 | ||
107 | spi->pdr = 0x00; /* Set SS low */ | |
108 | spi_transmit(addr); | |
109 | spi_transmit(data); | |
110 | /* wait some time to meet MS# hold time of PCM1772 */ | |
111 | udelay (1); | |
112 | spi->pdr = 0x08; /* set SS high */ | |
113 | } | |
114 | ||
115 | static void set_attenuation(unsigned char attenuation) | |
116 | { | |
117 | pcm1772_write_reg(0x01, attenuation); /* left channel */ | |
118 | debug ("PCM1772 attenuation left set to %d.\n", attenuation); | |
119 | pcm1772_write_reg(0x02, attenuation); /* right channel */ | |
120 | debug ("PCM1772 attenuation right set to %d.\n", attenuation); | |
121 | } | |
122 | ||
123 | void amplifier_init(void) | |
124 | { | |
125 | static int init_done = 0; | |
126 | int i; | |
127 | struct mpc5xxx_gpio *gpio = (struct mpc5xxx_gpio*)MPC5XXX_GPIO; | |
128 | ||
129 | /* Do this only once, because of the long time delay */ | |
130 | if (!init_done) { | |
131 | /* configure PCM1772 audio format as I2S */ | |
132 | pcm1772_write_reg(0x03, 0x01); | |
133 | /* enable audio amplifier */ | |
134 | gpio->sint_gpioe |= 0x02; /* PSC3_5 as GPIO */ | |
135 | gpio->sint_ode &= ~0x02; /* PSC3_5 is not open Drain */ | |
136 | gpio->sint_dvo &= ~0x02; /* PSC3_5 is LOW */ | |
137 | gpio->sint_ddr |= 0x02; /* PSC3_5 as output */ | |
138 | /* | |
139 | * wait some time to allow amplifier to recover from shutdown | |
140 | * mode. | |
141 | */ | |
142 | for(i = 0; i < 350; i++) | |
143 | udelay(1000); | |
144 | /* | |
145 | * The used amplifier (LM4867) has a so called "pop and click" | |
146 | * elmination filter. The input signal of the amplifier must | |
147 | * exceed a certain level once after power up to activate the | |
148 | * generation of the output signal. This is achieved by | |
149 | * sending a low frequent (nearly inaudible) sawtooth with a | |
150 | * sufficient signal level. | |
151 | */ | |
152 | set_attenuation(50); | |
153 | i2s_sawtooth (200, 5, LEFT_RIGHT); | |
154 | init_done = 1; | |
155 | } | |
156 | } | |
157 | ||
158 | static void i2s_init(void) | |
159 | { | |
160 | unsigned long i; | |
161 | struct mpc5xxx_psc *psc = (struct mpc5xxx_psc*)MPC5XXX_PSC2;; | |
162 | struct mpc5xxx_gpio *gpio = (struct mpc5xxx_gpio*)MPC5XXX_GPIO; | |
163 | ||
164 | gpio->port_config |= 0x00000070; /* PSC2 ports as Codec with MCLK */ | |
165 | psc->command = (PSC_RX_DISABLE | PSC_TX_DISABLE); | |
166 | psc->sicr = 0x22E00000; /* 16 bit data; I2S */ | |
167 | ||
168 | *(vu_long *)(CFG_MBAR + 0x22C) = 0x805d; /* PSC2 CDM MCLK config; MCLK | |
169 | * 5.617 MHz */ | |
170 | *(vu_long *)(CFG_MBAR + 0x214) |= 0x00000040; /* CDM clock enable | |
171 | * register */ | |
172 | psc->ccr = 0x1F03; /* 16 bit data width; 5.617MHz MCLK */ | |
173 | psc->ctur = 0x0F; /* 16 bit frame width */ | |
174 | ||
175 | for(i=0;i<128;i++) | |
176 | { | |
177 | psc->psc_buffer_32 = 0; /* clear tx fifo */ | |
178 | } | |
179 | } | |
180 | ||
181 | static int i2s_play_wave(unsigned long addr, unsigned long len) | |
182 | { | |
183 | unsigned long i; | |
77ddac94 | 184 | unsigned char *wave_file = (uchar *)addr + 44; /* quick'n dirty: skip |
6617aae9 WD |
185 | * wav header*/ |
186 | unsigned char swapped[4]; | |
187 | struct mpc5xxx_psc *psc = (struct mpc5xxx_psc*)MPC5XXX_PSC2; | |
188 | ||
189 | /* | |
190 | * play wave file in memory; bytes/words are be swapped | |
191 | */ | |
192 | psc->command = (PSC_RX_ENABLE | PSC_TX_ENABLE); | |
193 | ||
194 | for(i = 0;i < (len / 4); i++) { | |
195 | swapped[3]=*wave_file++; | |
196 | swapped[2]=*wave_file++; | |
197 | swapped[1]=*wave_file++; | |
198 | swapped[0]=*wave_file++; | |
199 | psc->psc_buffer_32 = *((unsigned long*)swapped); | |
200 | while (psc->tfnum > 400) { | |
201 | if(ctrlc()) | |
202 | return 0; | |
203 | } | |
204 | } | |
205 | while (psc->tfnum > 0); /* wait for fifo empty */ | |
206 | udelay (100); | |
207 | psc->command = (PSC_RX_DISABLE | PSC_TX_DISABLE); | |
208 | return 0; | |
209 | } | |
210 | ||
211 | static int i2s_sawtooth(unsigned long duration, unsigned int freq, | |
212 | unsigned int channel) | |
213 | { | |
214 | long i,j; | |
215 | unsigned long data; | |
216 | struct mpc5xxx_psc *psc = (struct mpc5xxx_psc*)MPC5XXX_PSC2; | |
217 | ||
218 | psc->command = (PSC_RX_ENABLE | PSC_TX_ENABLE); | |
219 | ||
220 | /* | |
221 | * Generate sawtooth. Start with middle level up to highest level. Then | |
222 | * go to lowest level and back to middle level. | |
223 | */ | |
224 | for(j = 0; j < ((duration * freq) / 1000); j++) { | |
225 | for(i = 0; i <= 0x7FFF; i += (0x7FFF/(44100/(freq*4)))) { | |
226 | data = (i & 0xFFFF); | |
227 | /* data format: right data left data) */ | |
228 | if (channel == LEFT_RIGHT) | |
229 | data |= (data<<16); | |
230 | if (channel == RIGHT) | |
231 | data = (data<<16); | |
232 | psc->psc_buffer_32 = data; | |
233 | while (psc->tfnum > 400); | |
234 | } | |
235 | for(i = 0x7FFF; i >= -0x7FFF; i -= (0xFFFF/(44100/(freq*2)))) { | |
236 | data = (i & 0xFFFF); | |
237 | /* data format: right data left data) */ | |
238 | if (channel == LEFT_RIGHT) | |
239 | data |= (data<<16); | |
240 | if (channel == RIGHT) | |
241 | data = (data<<16); | |
242 | psc->psc_buffer_32 = data; | |
243 | while (psc->tfnum > 400); | |
244 | } | |
245 | for(i = -0x7FFF; i <= 0; i += (0x7FFF/(44100/(freq*4)))) { | |
246 | data = (i & 0xFFFF); | |
247 | /* data format: right data left data) */ | |
248 | if (channel == LEFT_RIGHT) | |
249 | data |= (data<<16); | |
250 | if (channel == RIGHT) | |
251 | data = (data<<16); | |
252 | psc->psc_buffer_32 = data; | |
253 | while (psc->tfnum > 400); | |
254 | } | |
255 | } | |
256 | while (psc->tfnum > 0); /* wait for fifo empty */ | |
257 | udelay (100); | |
258 | psc->command = (PSC_RX_DISABLE | PSC_TX_DISABLE); | |
259 | ||
260 | return 0; | |
261 | } | |
262 | ||
263 | static int i2s_squarewave(unsigned long duration, unsigned int freq, | |
264 | unsigned int channel) | |
265 | { | |
266 | long i,j; | |
267 | unsigned long data; | |
268 | struct mpc5xxx_psc *psc = (struct mpc5xxx_psc*)MPC5XXX_PSC2; | |
269 | ||
270 | psc->command = (PSC_RX_ENABLE | PSC_TX_ENABLE); | |
271 | ||
272 | /* | |
273 | * Generate sqarewave. Start with high level, duty cycle 1:1. | |
274 | */ | |
275 | for(j = 0; j < ((duration * freq) / 1000); j++) { | |
276 | for(i = 0; i < (44100/(freq*2)); i ++) { | |
277 | data = 0x7FFF; | |
278 | /* data format: right data left data) */ | |
279 | if (channel == LEFT_RIGHT) | |
280 | data |= (data<<16); | |
281 | if (channel == RIGHT) | |
282 | data = (data<<16); | |
283 | psc->psc_buffer_32 = data; | |
284 | while (psc->tfnum > 400); | |
285 | } | |
286 | for(i = 0; i < (44100/(freq*2)); i ++) { | |
287 | data = 0x8000; | |
288 | /* data format: right data left data) */ | |
289 | if (channel == LEFT_RIGHT) | |
290 | data |= (data<<16); | |
291 | if (channel == RIGHT) | |
292 | data = (data<<16); | |
293 | psc->psc_buffer_32 = data; | |
294 | while (psc->tfnum > 400); | |
295 | } | |
296 | } | |
297 | while (psc->tfnum > 0); /* wait for fifo empty */ | |
298 | udelay (100); | |
299 | psc->command = (PSC_RX_DISABLE | PSC_TX_DISABLE); | |
300 | ||
301 | return 0; | |
302 | } | |
303 | ||
304 | static int cmd_sound(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) | |
305 | { | |
306 | unsigned long reg, val, duration; | |
77ddac94 | 307 | char *tmp; |
6617aae9 WD |
308 | unsigned int freq, channel; |
309 | unsigned char volume; | |
310 | int rcode = 1; | |
311 | ||
312 | #ifdef CONFIG_STK52XX_REV100 | |
313 | printf ("Revision 100 of STK52XX not supported!\n"); | |
314 | return 1; | |
315 | #endif | |
316 | spi_init(); | |
317 | i2s_init(); | |
318 | amplifier_init(); | |
319 | ||
320 | if ((tmp = getenv ("volume")) != NULL) { | |
321 | volume = simple_strtoul (tmp, NULL, 10); | |
322 | } else { | |
323 | volume = DEFAULT_VOL; | |
324 | } | |
325 | set_attenuation(volume); | |
326 | ||
327 | switch (argc) { | |
328 | case 0: | |
329 | case 1: | |
330 | printf ("Usage:\n%s\n", cmdtp->usage); | |
331 | return 1; | |
332 | case 2: | |
333 | if (strncmp(argv[1],"saw",3) == 0) { | |
334 | printf ("Play sawtooth\n"); | |
335 | rcode = i2s_sawtooth (DEFAULT_DURATION, DEFAULT_FREQ, | |
336 | LEFT_RIGHT); | |
337 | return rcode; | |
338 | } else if (strncmp(argv[1],"squ",3) == 0) { | |
339 | printf ("Play squarewave\n"); | |
340 | rcode = i2s_squarewave (DEFAULT_DURATION, DEFAULT_FREQ, | |
341 | LEFT_RIGHT); | |
342 | return rcode; | |
343 | } | |
344 | ||
345 | printf ("Usage:\n%s\n", cmdtp->usage); | |
346 | return 1; | |
347 | case 3: | |
348 | if (strncmp(argv[1],"saw",3) == 0) { | |
349 | duration = simple_strtoul(argv[2], NULL, 10); | |
350 | printf ("Play sawtooth\n"); | |
351 | rcode = i2s_sawtooth (duration, DEFAULT_FREQ, | |
352 | LEFT_RIGHT); | |
353 | return rcode; | |
354 | } else if (strncmp(argv[1],"squ",3) == 0) { | |
355 | duration = simple_strtoul(argv[2], NULL, 10); | |
356 | printf ("Play squarewave\n"); | |
357 | rcode = i2s_squarewave (duration, DEFAULT_FREQ, | |
358 | LEFT_RIGHT); | |
359 | return rcode; | |
360 | } | |
361 | printf ("Usage:\n%s\n", cmdtp->usage); | |
362 | return 1; | |
363 | case 4: | |
364 | if (strncmp(argv[1],"saw",3) == 0) { | |
365 | duration = simple_strtoul(argv[2], NULL, 10); | |
366 | freq = (unsigned int)simple_strtoul(argv[3], NULL, 10); | |
367 | printf ("Play sawtooth\n"); | |
368 | rcode = i2s_sawtooth (duration, freq, | |
369 | LEFT_RIGHT); | |
370 | return rcode; | |
371 | } else if (strncmp(argv[1],"squ",3) == 0) { | |
372 | duration = simple_strtoul(argv[2], NULL, 10); | |
373 | freq = (unsigned int)simple_strtoul(argv[3], NULL, 10); | |
374 | printf ("Play squarewave\n"); | |
375 | rcode = i2s_squarewave (duration, freq, | |
376 | LEFT_RIGHT); | |
377 | return rcode; | |
378 | } else if (strcmp(argv[1],"pcm1772") == 0) { | |
379 | reg = simple_strtoul(argv[2], NULL, 10); | |
380 | val = simple_strtoul(argv[3], NULL, 10); | |
381 | printf("Set PCM1772 %lu. %lu\n", reg, val); | |
382 | pcm1772_write_reg((uchar)reg, (uchar)val); | |
383 | return 0; | |
384 | } | |
385 | printf ("Usage:\n%s\n", cmdtp->usage); | |
386 | return 1; | |
387 | case 5: | |
388 | if (strncmp(argv[1],"saw",3) == 0) { | |
389 | duration = simple_strtoul(argv[2], NULL, 10); | |
390 | freq = (unsigned int)simple_strtoul(argv[3], NULL, 10); | |
391 | if (strncmp(argv[4],"l",1) == 0) | |
392 | channel = LEFT; | |
393 | else if (strncmp(argv[4],"r",1) == 0) | |
394 | channel = RIGHT; | |
395 | else | |
396 | channel = LEFT_RIGHT; | |
397 | printf ("Play squarewave\n"); | |
398 | rcode = i2s_sawtooth (duration, freq, | |
399 | channel); | |
400 | return rcode; | |
401 | } else if (strncmp(argv[1],"squ",3) == 0) { | |
402 | duration = simple_strtoul(argv[2], NULL, 10); | |
403 | freq = (unsigned int)simple_strtoul(argv[3], NULL, 10); | |
404 | if (strncmp(argv[4],"l",1) == 0) | |
405 | channel = LEFT; | |
406 | else if (strncmp(argv[4],"r",1) == 0) | |
407 | channel = RIGHT; | |
408 | else | |
409 | channel = LEFT_RIGHT; | |
410 | printf ("Play squarewave\n"); | |
411 | rcode = i2s_squarewave (duration, freq, | |
412 | channel); | |
413 | return rcode; | |
414 | } | |
415 | printf ("Usage:\n%s\n", cmdtp->usage); | |
416 | return 1; | |
417 | } | |
418 | printf ("Usage:\nsound cmd [arg1] [arg2] ...\n"); | |
419 | return 1; | |
420 | } | |
421 | ||
422 | static int cmd_wav(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) | |
423 | { | |
424 | unsigned long length, addr; | |
425 | unsigned char volume; | |
426 | int rcode = 1; | |
427 | char *tmp; | |
428 | ||
429 | #ifdef CONFIG_STK52XX_REV100 | |
430 | printf ("Revision 100 of STK52XX not supported!\n"); | |
431 | return 1; | |
432 | #endif | |
433 | spi_init(); | |
434 | i2s_init(); | |
435 | amplifier_init(); | |
436 | ||
437 | switch (argc) { | |
438 | ||
439 | case 3: | |
440 | length = simple_strtoul(argv[2], NULL, 16); | |
441 | addr = simple_strtoul(argv[1], NULL, 16); | |
442 | break; | |
443 | ||
444 | case 2: | |
445 | if ((tmp = getenv ("filesize")) != NULL) { | |
446 | length = simple_strtoul (tmp, NULL, 16); | |
447 | } else { | |
448 | puts ("No filesize provided\n"); | |
449 | return 1; | |
450 | } | |
451 | addr = simple_strtoul(argv[1], NULL, 16); | |
452 | ||
453 | case 1: | |
454 | if ((tmp = getenv ("filesize")) != NULL) { | |
455 | length = simple_strtoul (tmp, NULL, 16); | |
456 | } else { | |
457 | puts ("No filesize provided\n"); | |
458 | return 1; | |
459 | } | |
460 | if ((tmp = getenv ("loadaddr")) != NULL) { | |
461 | addr = simple_strtoul (tmp, NULL, 16); | |
462 | } else { | |
463 | puts ("No loadaddr provided\n"); | |
464 | return 1; | |
465 | } | |
466 | break; | |
467 | ||
468 | default: | |
469 | printf("Usage:\nwav <addr> <length[s]\n"); | |
470 | return 1; | |
471 | break; | |
472 | } | |
473 | ||
474 | if ((tmp = getenv ("volume")) != NULL) { | |
475 | volume = simple_strtoul (tmp, NULL, 10); | |
476 | } else { | |
477 | volume = DEFAULT_VOL; | |
478 | } | |
479 | set_attenuation(volume); | |
480 | ||
481 | printf("Play wave file at %#p with length %#x\n", addr, length); | |
482 | rcode = i2s_play_wave(addr, length); | |
483 | ||
484 | return rcode; | |
485 | } | |
486 | ||
487 | static int cmd_beep(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) | |
488 | { | |
489 | unsigned char volume; | |
490 | unsigned int channel; | |
491 | int rcode; | |
492 | char *tmp; | |
493 | ||
494 | #ifdef CONFIG_STK52XX_REV100 | |
495 | printf ("Revision 100 of STK52XX not supported!\n"); | |
496 | return 1; | |
497 | #endif | |
498 | spi_init(); | |
499 | i2s_init(); | |
500 | amplifier_init(); | |
501 | ||
502 | switch (argc) { | |
503 | case 0: | |
504 | case 1: | |
505 | channel = LEFT_RIGHT; | |
506 | break; | |
507 | case 2: | |
508 | if (strncmp(argv[1],"l",1) == 0) | |
509 | channel = LEFT; | |
510 | else if (strncmp(argv[1],"r",1) == 0) | |
511 | channel = RIGHT; | |
512 | else | |
513 | channel = LEFT_RIGHT; | |
514 | break; | |
515 | default: | |
516 | printf ("Usage:\n%s\n", cmdtp->usage); | |
517 | return 1; | |
518 | } | |
519 | ||
520 | if ((tmp = getenv ("volume")) != NULL) { | |
521 | volume = simple_strtoul (tmp, NULL, 10); | |
522 | } else { | |
523 | volume = DEFAULT_VOL; | |
524 | } | |
525 | set_attenuation(volume); | |
526 | ||
527 | printf("Beep on "); | |
528 | if (channel == LEFT) | |
529 | printf ("left "); | |
530 | else if (channel == RIGHT) | |
531 | printf ("right "); | |
532 | else | |
533 | printf ("left and right "); | |
534 | printf ("channel\n"); | |
535 | ||
536 | rcode = i2s_squarewave (DEFAULT_DURATION, DEFAULT_FREQ, channel); | |
537 | ||
538 | return rcode; | |
539 | } | |
6d3bc9b8 | 540 | #endif |
6617aae9 | 541 | |
6d3bc9b8 | 542 | #if defined(CONFIG_STK52XX) |
6617aae9 WD |
543 | void led_init(void) |
544 | { | |
545 | struct mpc5xxx_gpio *gpio = (struct mpc5xxx_gpio *)MPC5XXX_GPIO; | |
546 | struct mpc5xxx_gpt_0_7 *gpt = (struct mpc5xxx_gpt_0_7 *)MPC5XXX_GPT; | |
547 | ||
548 | /* configure PSC3 for SPI and GPIO */ | |
549 | gpio->port_config &= ~(0x00000F00); | |
550 | gpio->port_config |= 0x00000800; | |
551 | ||
552 | gpio->simple_gpioe &= ~(0x00000F00); | |
553 | gpio->simple_gpioe |= 0x00000F00; | |
554 | ||
555 | gpio->simple_ddr &= ~(0x00000F00); | |
556 | gpio->simple_ddr |= 0x00000F00; | |
557 | ||
558 | /* configure timer 4-7 for simple GPIO output */ | |
559 | gpt->gpt4.emsr |= 0x00000024; | |
560 | gpt->gpt5.emsr |= 0x00000024; | |
561 | gpt->gpt6.emsr |= 0x00000024; | |
562 | gpt->gpt7.emsr |= 0x00000024; | |
563 | ||
be4a87f1 | 564 | #ifndef CONFIG_TQM5200S |
6617aae9 WD |
565 | /* enable SM501 GPIO control (in both power modes) */ |
566 | *(vu_long *) (SM501_MMIO_BASE+SM501_POWER_MODE0_GATE) |= | |
567 | POWER_MODE_GATE_GPIO_PWM_I2C; | |
568 | *(vu_long *) (SM501_MMIO_BASE+SM501_POWER_MODE1_GATE) |= | |
569 | POWER_MODE_GATE_GPIO_PWM_I2C; | |
570 | ||
571 | /* configure SM501 gpio pins 24-27 as output */ | |
572 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_CTRL_LOW) &= ~(0xF << 24); | |
573 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_DIR_LOW) |= (0xF << 24); | |
574 | ||
575 | /* configure SM501 gpio pins 48-51 as output */ | |
576 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_DIR_HIGH) |= (0xF << 16); | |
be4a87f1 | 577 | #endif /* !CONFIG_TQM5200S */ |
6617aae9 WD |
578 | } |
579 | ||
580 | /* | |
581 | * return 1 if led number unknown | |
582 | * return 0 else | |
583 | */ | |
584 | int do_led(char *argv[]) | |
585 | { | |
586 | struct mpc5xxx_gpio *gpio = (struct mpc5xxx_gpio *)MPC5XXX_GPIO; | |
587 | struct mpc5xxx_gpt_0_7 *gpt = (struct mpc5xxx_gpt_0_7 *)MPC5XXX_GPT; | |
588 | ||
589 | switch (simple_strtoul(argv[2], NULL, 10)) { | |
590 | ||
591 | case 0: | |
592 | if (strcmp (argv[3], "on") == 0) { | |
593 | gpio->simple_dvo |= (1 << 8); | |
594 | } else { | |
595 | gpio->simple_dvo &= ~(1 << 8); | |
596 | } | |
597 | break; | |
598 | ||
599 | case 1: | |
600 | if (strcmp (argv[3], "on") == 0) { | |
601 | gpio->simple_dvo |= (1 << 9); | |
602 | } else { | |
603 | gpio->simple_dvo &= ~(1 << 9); | |
604 | } | |
605 | break; | |
606 | ||
607 | case 2: | |
608 | if (strcmp (argv[3], "on") == 0) { | |
609 | gpio->simple_dvo |= (1 << 10); | |
610 | } else { | |
611 | gpio->simple_dvo &= ~(1 << 10); | |
612 | } | |
613 | break; | |
614 | ||
615 | case 3: | |
616 | if (strcmp (argv[3], "on") == 0) { | |
617 | gpio->simple_dvo |= (1 << 11); | |
618 | } else { | |
619 | gpio->simple_dvo &= ~(1 << 11); | |
620 | } | |
621 | break; | |
622 | ||
623 | case 4: | |
624 | if (strcmp (argv[3], "on") == 0) { | |
625 | gpt->gpt4.emsr |= (1 << 4); | |
626 | } else { | |
627 | gpt->gpt4.emsr &= ~(1 << 4); | |
628 | } | |
629 | break; | |
630 | ||
631 | case 5: | |
632 | if (strcmp (argv[3], "on") == 0) { | |
633 | gpt->gpt5.emsr |= (1 << 4); | |
634 | } else { | |
635 | gpt->gpt5.emsr &= ~(1 << 4); | |
636 | } | |
637 | break; | |
638 | ||
639 | case 6: | |
640 | if (strcmp (argv[3], "on") == 0) { | |
641 | gpt->gpt6.emsr |= (1 << 4); | |
642 | } else { | |
643 | gpt->gpt6.emsr &= ~(1 << 4); | |
644 | } | |
645 | break; | |
646 | ||
647 | case 7: | |
648 | if (strcmp (argv[3], "on") == 0) { | |
649 | gpt->gpt7.emsr |= (1 << 4); | |
650 | } else { | |
651 | gpt->gpt7.emsr &= ~(1 << 4); | |
652 | } | |
653 | break; | |
be4a87f1 | 654 | #ifndef CONFIG_TQM5200S |
6617aae9 WD |
655 | case 24: |
656 | if (strcmp (argv[3], "on") == 0) { | |
657 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) |= | |
658 | (0x1 << 24); | |
659 | } else { | |
660 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) &= | |
661 | ~(0x1 << 24); | |
662 | } | |
663 | break; | |
664 | ||
665 | case 25: | |
666 | if (strcmp (argv[3], "on") == 0) { | |
667 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) |= | |
668 | (0x1 << 25); | |
669 | } else { | |
670 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) &= | |
671 | ~(0x1 << 25); | |
672 | } | |
673 | break; | |
674 | ||
675 | case 26: | |
676 | if (strcmp (argv[3], "on") == 0) { | |
677 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) |= | |
678 | (0x1 << 26); | |
679 | } else { | |
680 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) &= | |
681 | ~(0x1 << 26); | |
682 | } | |
683 | break; | |
684 | ||
685 | case 27: | |
686 | if (strcmp (argv[3], "on") == 0) { | |
687 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) |= | |
688 | (0x1 << 27); | |
689 | } else { | |
690 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_LOW) &= | |
691 | ~(0x1 << 27); | |
692 | } | |
693 | break; | |
694 | ||
695 | case 48: | |
696 | if (strcmp (argv[3], "on") == 0) { | |
697 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) |= | |
698 | (0x1 << 16); | |
699 | } else { | |
700 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) &= | |
701 | ~(0x1 << 16); | |
702 | } | |
703 | break; | |
704 | ||
705 | case 49: | |
706 | if (strcmp (argv[3], "on") == 0) { | |
707 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) |= | |
708 | (0x1 << 17); | |
709 | } else { | |
710 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) &= | |
711 | ~(0x1 << 17); | |
712 | } | |
713 | break; | |
714 | ||
715 | case 50: | |
716 | if (strcmp (argv[3], "on") == 0) { | |
717 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) |= | |
718 | (0x1 << 18); | |
719 | } else { | |
720 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) &= | |
721 | ~(0x1 << 18); | |
722 | } | |
723 | break; | |
724 | ||
725 | case 51: | |
726 | if (strcmp (argv[3], "on") == 0) { | |
727 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) |= | |
728 | (0x1 << 19); | |
729 | } else { | |
730 | *(vu_long *) (SM501_MMIO_BASE+SM501_GPIO_DATA_HIGH) &= | |
731 | ~(0x1 << 19); | |
732 | } | |
733 | break; | |
be4a87f1 | 734 | #endif /* !CONFIG_TQM5200S */ |
6617aae9 WD |
735 | default: |
736 | printf ("%s: invalid led number %s\n", __FUNCTION__, argv[2]); | |
737 | return 1; | |
738 | } | |
739 | ||
740 | return 0; | |
741 | } | |
6d3bc9b8 | 742 | #endif |
6617aae9 | 743 | |
6d3bc9b8 | 744 | #if defined(CONFIG_STK52XX) || defined(CONFIG_FO300) |
6617aae9 WD |
745 | /* |
746 | * return 1 on CAN initialization failure | |
747 | * return 0 if no failure | |
748 | */ | |
749 | int can_init(void) | |
750 | { | |
751 | static int init_done = 0; | |
752 | int i; | |
753 | struct mpc5xxx_mscan *can1 = | |
754 | (struct mpc5xxx_mscan *)(CFG_MBAR + 0x0900); | |
755 | struct mpc5xxx_mscan *can2 = | |
756 | (struct mpc5xxx_mscan *)(CFG_MBAR + 0x0980); | |
757 | ||
758 | /* GPIO configuration of the CAN pins is done in TQM5200.h */ | |
759 | ||
760 | if (!init_done) { | |
761 | /* init CAN 1 */ | |
762 | can1->canctl1 |= 0x80; /* CAN enable */ | |
763 | udelay(100); | |
764 | ||
765 | i = 0; | |
766 | can1->canctl0 |= 0x02; /* sleep mode */ | |
767 | /* wait until sleep mode reached */ | |
768 | while (!(can1->canctl1 & 0x02)) { | |
769 | udelay(10); | |
770 | i++; | |
771 | if (i == 10) { | |
772 | printf ("%s: CAN1 initialize error, " | |
773 | "can not enter sleep mode!\n", | |
774 | __FUNCTION__); | |
775 | return 1; | |
776 | } | |
777 | } | |
778 | i = 0; | |
779 | can1->canctl0 = 0x01; /* enter init mode */ | |
780 | /* wait until init mode reached */ | |
781 | while (!(can1->canctl1 & 0x01)) { | |
782 | udelay(10); | |
783 | i++; | |
784 | if (i == 10) { | |
785 | printf ("%s: CAN1 initialize error, " | |
786 | "can not enter init mode!\n", | |
787 | __FUNCTION__); | |
788 | return 1; | |
789 | } | |
790 | } | |
791 | can1->canctl1 = 0x80; | |
792 | can1->canctl1 |= 0x40; | |
793 | can1->canbtr0 = 0x0F; | |
794 | can1->canbtr1 = 0x7F; | |
795 | can1->canidac &= ~(0x30); | |
796 | can1->canidar1 = 0x00; | |
797 | can1->canidar3 = 0x00; | |
798 | can1->canidar5 = 0x00; | |
799 | can1->canidar7 = 0x00; | |
800 | can1->canidmr0 = 0xFF; | |
801 | can1->canidmr1 = 0xFF; | |
802 | can1->canidmr2 = 0xFF; | |
803 | can1->canidmr3 = 0xFF; | |
804 | can1->canidmr4 = 0xFF; | |
805 | can1->canidmr5 = 0xFF; | |
806 | can1->canidmr6 = 0xFF; | |
807 | can1->canidmr7 = 0xFF; | |
808 | ||
809 | i = 0; | |
810 | can1->canctl0 &= ~(0x01); /* leave init mode */ | |
811 | can1->canctl0 &= ~(0x02); | |
812 | /* wait until init and sleep mode left */ | |
813 | while ((can1->canctl1 & 0x01) || (can1->canctl1 & 0x02)) { | |
814 | udelay(10); | |
815 | i++; | |
816 | if (i == 10) { | |
817 | printf ("%s: CAN1 initialize error, " | |
818 | "can not leave init/sleep mode!\n", | |
819 | __FUNCTION__); | |
820 | return 1; | |
821 | } | |
822 | } | |
823 | ||
824 | /* init CAN 2 */ | |
825 | can2->canctl1 |= 0x80; /* CAN enable */ | |
826 | udelay(100); | |
827 | ||
828 | i = 0; | |
829 | can2->canctl0 |= 0x02; /* sleep mode */ | |
830 | /* wait until sleep mode reached */ | |
831 | while (!(can2->canctl1 & 0x02)) { | |
832 | udelay(10); | |
833 | i++; | |
834 | if (i == 10) { | |
835 | printf ("%s: CAN2 initialize error, " | |
836 | "can not enter sleep mode!\n", | |
837 | __FUNCTION__); | |
838 | return 1; | |
839 | } | |
840 | } | |
841 | i = 0; | |
842 | can2->canctl0 = 0x01; /* enter init mode */ | |
843 | /* wait until init mode reached */ | |
844 | while (!(can2->canctl1 & 0x01)) { | |
845 | udelay(10); | |
846 | i++; | |
847 | if (i == 10) { | |
848 | printf ("%s: CAN2 initialize error, " | |
849 | "can not enter init mode!\n", | |
850 | __FUNCTION__); | |
851 | return 1; | |
852 | } | |
853 | } | |
854 | can2->canctl1 = 0x80; | |
855 | can2->canctl1 |= 0x40; | |
856 | can2->canbtr0 = 0x0F; | |
857 | can2->canbtr1 = 0x7F; | |
858 | can2->canidac &= ~(0x30); | |
859 | can2->canidar1 = 0x00; | |
860 | can2->canidar3 = 0x00; | |
861 | can2->canidar5 = 0x00; | |
862 | can2->canidar7 = 0x00; | |
863 | can2->canidmr0 = 0xFF; | |
864 | can2->canidmr1 = 0xFF; | |
865 | can2->canidmr2 = 0xFF; | |
866 | can2->canidmr3 = 0xFF; | |
867 | can2->canidmr4 = 0xFF; | |
868 | can2->canidmr5 = 0xFF; | |
869 | can2->canidmr6 = 0xFF; | |
870 | can2->canidmr7 = 0xFF; | |
871 | can2->canctl0 &= ~(0x01); /* leave init mode */ | |
872 | can2->canctl0 &= ~(0x02); | |
873 | ||
874 | i = 0; | |
875 | /* wait until init mode left */ | |
876 | while ((can2->canctl1 & 0x01) || (can2->canctl1 & 0x02)) { | |
877 | udelay(10); | |
878 | i++; | |
879 | if (i == 10) { | |
880 | printf ("%s: CAN2 initialize error, " | |
881 | "can not leave init/sleep mode!\n", | |
882 | __FUNCTION__); | |
883 | return 1; | |
884 | } | |
885 | } | |
886 | init_done = 1; | |
887 | } | |
888 | return 0; | |
889 | } | |
890 | ||
891 | /* | |
892 | * return 1 on CAN failure | |
893 | * return 0 if no failure | |
894 | */ | |
895 | int do_can(char *argv[]) | |
896 | { | |
897 | int i; | |
898 | struct mpc5xxx_mscan *can1 = | |
899 | (struct mpc5xxx_mscan *)(CFG_MBAR + 0x0900); | |
900 | struct mpc5xxx_mscan *can2 = | |
901 | (struct mpc5xxx_mscan *)(CFG_MBAR + 0x0980); | |
902 | ||
903 | /* send a message on CAN1 */ | |
904 | can1->cantbsel = 0x01; | |
905 | can1->cantxfg.idr[0] = 0x55; | |
906 | can1->cantxfg.idr[1] = 0x00; | |
907 | can1->cantxfg.idr[1] &= ~0x8; | |
908 | can1->cantxfg.idr[1] &= ~0x10; | |
909 | can1->cantxfg.dsr[0] = 0xCC; | |
910 | can1->cantxfg.dlr = 1; | |
911 | can1->cantxfg.tbpr = 0; | |
912 | can1->cantflg = 0x01; | |
913 | ||
914 | i = 0; | |
915 | while ((can1->cantflg & 0x01) == 0) { | |
916 | i++; | |
917 | if (i == 10) { | |
918 | printf ("%s: CAN1 send timeout, " | |
919 | "can not send message!\n", | |
920 | __FUNCTION__); | |
921 | return 1; | |
922 | } | |
923 | udelay(1000); | |
924 | } | |
925 | udelay(1000); | |
926 | ||
927 | i = 0; | |
928 | while (!(can2->canrflg & 0x01)) { | |
929 | i++; | |
930 | if (i == 10) { | |
931 | printf ("%s: CAN2 receive timeout, " | |
932 | "no message received!\n", | |
933 | __FUNCTION__); | |
934 | return 1; | |
935 | } | |
936 | udelay(1000); | |
937 | } | |
938 | ||
939 | if (can2->canrxfg.dsr[0] != 0xCC) { | |
940 | printf ("%s: CAN2 receive error, " | |
941 | "data mismatch!\n", | |
942 | __FUNCTION__); | |
943 | return 1; | |
944 | } | |
945 | ||
946 | /* send a message on CAN2 */ | |
947 | can2->cantbsel = 0x01; | |
948 | can2->cantxfg.idr[0] = 0x55; | |
949 | can2->cantxfg.idr[1] = 0x00; | |
950 | can2->cantxfg.idr[1] &= ~0x8; | |
951 | can2->cantxfg.idr[1] &= ~0x10; | |
952 | can2->cantxfg.dsr[0] = 0xCC; | |
953 | can2->cantxfg.dlr = 1; | |
954 | can2->cantxfg.tbpr = 0; | |
955 | can2->cantflg = 0x01; | |
956 | ||
957 | i = 0; | |
958 | while ((can2->cantflg & 0x01) == 0) { | |
959 | i++; | |
960 | if (i == 10) { | |
961 | printf ("%s: CAN2 send error, " | |
962 | "can not send message!\n", | |
963 | __FUNCTION__); | |
964 | return 1; | |
965 | } | |
966 | udelay(1000); | |
967 | } | |
968 | udelay(1000); | |
969 | ||
970 | i = 0; | |
971 | while (!(can1->canrflg & 0x01)) { | |
972 | i++; | |
973 | if (i == 10) { | |
974 | printf ("%s: CAN1 receive timeout, " | |
975 | "no message received!\n", | |
976 | __FUNCTION__); | |
977 | return 1; | |
978 | } | |
979 | udelay(1000); | |
980 | } | |
981 | ||
982 | if (can1->canrxfg.dsr[0] != 0xCC) { | |
983 | printf ("%s: CAN1 receive error 0x%02x\n", | |
984 | __FUNCTION__, (can1->canrxfg.dsr[0])); | |
985 | return 1; | |
986 | } | |
987 | ||
988 | return 0; | |
989 | } | |
990 | ||
991 | /* | |
992 | * return 1 if rs232 port unknown | |
993 | * return 2 on txd/rxd failure (only rs232 2) | |
994 | * return 3 on rts/cts failure | |
995 | * return 0 if no failure | |
996 | */ | |
997 | int do_rs232(char *argv[]) | |
998 | { | |
999 | int error_status = 0; | |
1000 | struct mpc5xxx_gpio *gpio = (struct mpc5xxx_gpio *)MPC5XXX_GPIO; | |
1001 | struct mpc5xxx_psc *psc1 = (struct mpc5xxx_psc *)MPC5XXX_PSC1; | |
1002 | ||
1003 | switch (simple_strtoul(argv[2], NULL, 10)) { | |
1004 | ||
1005 | case 1: | |
1006 | /* check RTS <-> CTS loop */ | |
1007 | /* set rts to 0 */ | |
1008 | psc1->op1 |= 0x01; | |
1009 | ||
1010 | /* wait some time before requesting status */ | |
1011 | udelay(10); | |
1012 | ||
1013 | /* check status at cts */ | |
1014 | if ((psc1->ip & 0x01) != 0) { | |
1015 | error_status = 3; | |
1016 | printf ("%s: failure at rs232_1, cts status is %d " | |
1017 | "(should be 0)\n", | |
1018 | __FUNCTION__, (psc1->ip & 0x01)); | |
1019 | } | |
1020 | ||
1021 | /* set rts to 1 */ | |
1022 | psc1->op0 |= 0x01; | |
1023 | ||
1024 | /* wait some time before requesting status */ | |
1025 | udelay(10); | |
1026 | ||
1027 | /* check status at cts */ | |
1028 | if ((psc1->ip & 0x01) != 1) { | |
1029 | error_status = 3; | |
1030 | printf ("%s: failure at rs232_1, cts status is %d " | |
1031 | "(should be 1)\n", | |
1032 | __FUNCTION__, (psc1->ip & 0x01)); | |
1033 | } | |
1034 | ||
1035 | break; | |
1036 | ||
1037 | case 2: | |
1038 | /* set PSC3_0, PSC3_2 as output and PSC3_1, PSC3_3 as input */ | |
1039 | gpio->simple_ddr &= ~(0x00000F00); | |
1040 | gpio->simple_ddr |= 0x00000500; | |
1041 | ||
1042 | /* check TXD <-> RXD loop */ | |
1043 | /* set TXD to 1 */ | |
1044 | gpio->simple_dvo |= (1 << 8); | |
1045 | ||
1046 | /* wait some time before requesting status */ | |
1047 | udelay(10); | |
1048 | ||
1049 | if ((gpio->simple_ival & 0x00000200) != 0x00000200) { | |
1050 | error_status = 2; | |
1051 | printf ("%s: failure at rs232_2, rxd status is %d " | |
1052 | "(should be 1)\n", | |
1053 | __FUNCTION__, | |
1054 | (gpio->simple_ival & 0x00000200) >> 9); | |
1055 | } | |
1056 | ||
1057 | /* set TXD to 0 */ | |
1058 | gpio->simple_dvo &= ~(1 << 8); | |
1059 | ||
1060 | /* wait some time before requesting status */ | |
1061 | udelay(10); | |
1062 | ||
1063 | if ((gpio->simple_ival & 0x00000200) != 0x00000000) { | |
1064 | error_status = 2; | |
1065 | printf ("%s: failure at rs232_2, rxd status is %d " | |
1066 | "(should be 0)\n", | |
1067 | __FUNCTION__, | |
1068 | (gpio->simple_ival & 0x00000200) >> 9); | |
1069 | } | |
1070 | ||
1071 | /* check RTS <-> CTS loop */ | |
1072 | /* set RTS to 1 */ | |
1073 | gpio->simple_dvo |= (1 << 10); | |
1074 | ||
1075 | /* wait some time before requesting status */ | |
1076 | udelay(10); | |
1077 | ||
1078 | if ((gpio->simple_ival & 0x00000800) != 0x00000800) { | |
1079 | error_status = 3; | |
1080 | printf ("%s: failure at rs232_2, cts status is %d " | |
1081 | "(should be 1)\n", | |
1082 | __FUNCTION__, | |
1083 | (gpio->simple_ival & 0x00000800) >> 11); | |
1084 | } | |
1085 | ||
1086 | /* set RTS to 0 */ | |
1087 | gpio->simple_dvo &= ~(1 << 10); | |
1088 | ||
1089 | /* wait some time before requesting status */ | |
1090 | udelay(10); | |
1091 | ||
1092 | if ((gpio->simple_ival & 0x00000800) != 0x00000000) { | |
1093 | error_status = 3; | |
1094 | printf ("%s: failure at rs232_2, cts status is %d " | |
1095 | "(should be 0)\n", | |
1096 | __FUNCTION__, | |
1097 | (gpio->simple_ival & 0x00000800) >> 11); | |
1098 | } | |
1099 | ||
1100 | /* set PSC3_0, PSC3_1, PSC3_2 and PSC3_3 as output */ | |
1101 | gpio->simple_ddr &= ~(0x00000F00); | |
1102 | gpio->simple_ddr |= 0x00000F00; | |
1103 | break; | |
1104 | ||
1105 | default: | |
1106 | printf ("%s: invalid rs232 number %s\n", __FUNCTION__, argv[2]); | |
1107 | error_status = 1; | |
1108 | break; | |
1109 | } | |
1110 | ||
1111 | return error_status; | |
1112 | } | |
1113 | ||
be4a87f1 | 1114 | #if !defined(CONFIG_FO300) && !defined(CONFIG_TQM5200S) |
6617aae9 WD |
1115 | static void sm501_backlight (unsigned int state) |
1116 | { | |
1117 | if (state == BL_ON) { | |
1118 | *(vu_long *)(SM501_MMIO_BASE+SM501_PANEL_DISPLAY_CONTROL) |= | |
1119 | (1 << 26) | (1 << 27); | |
1120 | } else if (state == BL_OFF) | |
1121 | *(vu_long *)(SM501_MMIO_BASE+SM501_PANEL_DISPLAY_CONTROL) &= | |
1122 | ~((1 << 26) | (1 << 27)); | |
1123 | } | |
be4a87f1 | 1124 | #endif /* !CONFIG_FO300 & !CONFIG_TQM5200S */ |
6617aae9 WD |
1125 | |
1126 | int cmd_fkt(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) | |
1127 | { | |
1128 | int rcode; | |
1129 | ||
1130 | #ifdef CONFIG_STK52XX_REV100 | |
1131 | printf ("Revision 100 of STK52XX not supported!\n"); | |
1132 | return 1; | |
1133 | #endif | |
6d3bc9b8 | 1134 | #if defined(CONFIG_STK52XX) |
6617aae9 | 1135 | led_init(); |
6d3bc9b8 | 1136 | #endif |
6617aae9 WD |
1137 | can_init(); |
1138 | ||
1139 | switch (argc) { | |
1140 | ||
1141 | case 0: | |
1142 | case 1: | |
1143 | break; | |
1144 | ||
1145 | case 2: | |
1146 | if (strncmp (argv[1], "can", 3) == 0) { | |
1147 | rcode = do_can (argv); | |
1148 | if (rcode == 0) | |
1149 | printf ("OK\n"); | |
1150 | else | |
1151 | printf ("Error\n"); | |
1152 | return rcode; | |
1153 | } | |
1154 | break; | |
1155 | ||
1156 | case 3: | |
1157 | if (strncmp (argv[1], "rs232", 3) == 0) { | |
1158 | rcode = do_rs232 (argv); | |
1159 | if (rcode == 0) | |
1160 | printf ("OK\n"); | |
1161 | else | |
1162 | printf ("Error\n"); | |
1163 | return rcode; | |
be4a87f1 | 1164 | #if !defined(CONFIG_FO300) && !defined(CONFIG_TQM5200S) |
6617aae9 WD |
1165 | } else if (strncmp (argv[1], "backlight", 4) == 0) { |
1166 | if (strncmp (argv[2], "on", 2) == 0) { | |
1167 | sm501_backlight (BL_ON); | |
1168 | return 0; | |
1169 | } | |
1170 | else if (strncmp (argv[2], "off", 3) == 0) { | |
1171 | sm501_backlight (BL_OFF); | |
1172 | return 0; | |
1173 | } | |
be4a87f1 | 1174 | #endif /* !CONFIG_FO300 & !CONFIG_TQM5200S */ |
6617aae9 WD |
1175 | } |
1176 | break; | |
1177 | ||
6d3bc9b8 | 1178 | #if defined(CONFIG_STK52XX) |
6617aae9 WD |
1179 | case 4: |
1180 | if (strcmp (argv[1], "led") == 0) { | |
1181 | return (do_led (argv)); | |
1182 | } | |
1183 | break; | |
6d3bc9b8 | 1184 | #endif |
6617aae9 WD |
1185 | |
1186 | default: | |
1187 | break; | |
1188 | } | |
1189 | ||
1190 | printf ("Usage:\nfkt cmd [arg1] [arg2] ...\n"); | |
1191 | return 1; | |
1192 | } | |
1193 | ||
1194 | ||
1195 | U_BOOT_CMD( | |
1196 | sound , 5, 1, cmd_sound, | |
1197 | "sound - Sound sub-system\n", | |
1198 | "saw [duration] [freq] [channel]\n" | |
1199 | " - generate sawtooth for 'duration' ms with frequency 'freq'\n" | |
1200 | " on left \"l\" or right \"r\" channel\n" | |
1201 | "sound square [duration] [freq] [channel]\n" | |
1202 | " - generate squarewave for 'duration' ms with frequency 'freq'\n" | |
1203 | " on left \"l\" or right \"r\" channel\n" | |
1204 | "pcm1772 reg val\n" | |
1205 | ); | |
1206 | ||
1207 | U_BOOT_CMD( | |
1208 | wav , 3, 1, cmd_wav, | |
1209 | "wav - play wav file\n", | |
1210 | "[addr] [bytes]\n" | |
1211 | " - play wav file at address 'addr' with length 'bytes'\n" | |
1212 | ); | |
1213 | ||
1214 | U_BOOT_CMD( | |
1215 | beep , 2, 1, cmd_beep, | |
1216 | "beep - play short beep\n", | |
1217 | "[channel]\n" | |
1218 | " - play short beep on \"l\"eft or \"r\"ight channel\n" | |
1219 | ); | |
6d3bc9b8 | 1220 | #endif /* CONFIG_STK52XX || CONFIG_FO300 */ |
6617aae9 | 1221 | |
6d3bc9b8 | 1222 | #if defined(CONFIG_STK52XX) |
6617aae9 WD |
1223 | U_BOOT_CMD( |
1224 | fkt , 4, 1, cmd_fkt, | |
1225 | "fkt - Function test routines\n", | |
1226 | "led number on/off\n" | |
45a212c4 | 1227 | " - 'number's like printed on STK52XX board\n" |
6617aae9 WD |
1228 | "fkt can\n" |
1229 | " - loopback plug for X83 required\n" | |
1230 | "fkt rs232 number\n" | |
1231 | " - loopback plug(s) for X2 required\n" | |
be4a87f1 | 1232 | #ifndef CONFIG_TQM5200S |
6617aae9 WD |
1233 | "fkt backlight on/off\n" |
1234 | " - switch backlight on or off\n" | |
be4a87f1 | 1235 | #endif /* !CONFIG_TQM5200S */ |
6617aae9 | 1236 | ); |
6d3bc9b8 MB |
1237 | #elif defined(CONFIG_FO300) |
1238 | U_BOOT_CMD( | |
1239 | fkt , 3, 1, cmd_fkt, | |
1240 | "fkt - Function test routines\n", | |
1241 | "fkt can\n" | |
1242 | " - loopback plug for X16/X29 required\n" | |
1243 | "fkt rs232 number\n" | |
1244 | " - loopback plug(s) for X21/X22 required\n" | |
1245 | ); | |
1246 | #endif | |
d39b5741 | 1247 | #endif |