blob: 9a0bf1e360337ff730ddbc00290987da4cd44501 [file] [log] [blame]
stroesed69b1002003-03-25 14:41:35 +00001/*
stroesec2642d12004-12-16 18:38:22 +00002 * (C) Copyright 2002-2004
stroesed69b1002003-03-25 14:41:35 +00003 * Stefan Roese, esd gmbh germany, stefan.roese@esd-electronics.com
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#include <common.h>
wdenk8bde7f72003-06-27 21:31:46 +000025#include <command.h>
stroesed69b1002003-03-25 14:41:35 +000026#include <malloc.h>
27#include <net.h>
28#include <asm/io.h>
29#include <pci.h>
Stefan Roese3048bcb2007-10-03 15:01:02 +020030#include <asm/4xx_pci.h>
stroesec2642d12004-12-16 18:38:22 +000031#include <asm/processor.h>
stroesed69b1002003-03-25 14:41:35 +000032
33#include "pci405.h"
34
35
Jon Loeligerb9307262007-07-09 18:24:55 -050036#if defined(CONFIG_CMD_BSP)
stroesed69b1002003-03-25 14:41:35 +000037
38extern int do_bootm (cmd_tbl_t *, int, int, char *[]);
stroesec2642d12004-12-16 18:38:22 +000039extern int do_bootvx (cmd_tbl_t *, int, int, char *[]);
40unsigned long get_dcr(unsigned short);
stroesed69b1002003-03-25 14:41:35 +000041
stroesed69b1002003-03-25 14:41:35 +000042
stroesed69b1002003-03-25 14:41:35 +000043/*
44 * Command loadpci: wait for signal from host and boot image.
45 */
46int do_loadpci(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
47{
48 unsigned int *ptr = 0;
49 int count = 0;
50 int count2 = 0;
51 int status;
52 int i;
53 char addr[16];
54 char str[] = "\\|/-";
55 char *local_args[2];
56
stroesed69b1002003-03-25 14:41:35 +000057 /*
58 * Mark sync address
59 */
60 ptr = 0;
61 *ptr = 0xffffffff;
62 puts("\nWaiting for image from pci host -");
63
64 /*
65 * Wait for host to write the start address
66 */
67 while (*ptr == 0xffffffff) {
68 count++;
69 if (!(count % 100)) {
70 count2++;
71 putc(0x08); /* backspace */
72 putc(str[count2 % 4]);
73 }
74
75 /* Abort if ctrl-c was pressed */
76 if (ctrlc()) {
77 puts("\nAbort\n");
78 return 0;
79 }
80
81 udelay(1000);
82 }
83
84 if (*ptr == PCI_RECONFIG_MAGIC) {
85 /*
86 * Save own pci configuration in PRAM
87 */
88 memset((char *)PCI_REGS_ADDR, 0, PCI_REGS_LEN);
89 ptr = (unsigned int *)PCI_REGS_ADDR + 1;
90 for (i=0; i<0x40; i+=4) {
91 pci_read_config_dword(PCIDEVID_405GP, i, ptr++);
92 }
93 ptr = (unsigned int *)PCI_REGS_ADDR;
Wolfgang Denk77ddac92005-10-13 16:45:02 +020094 *ptr = crc32(0, (uchar *)PCI_REGS_ADDR+4, PCI_REGS_LEN-4);
stroesed69b1002003-03-25 14:41:35 +000095
96 printf("\nStoring PCI Configuration Regs...\n");
97 } else {
98 sprintf(addr, "%08x", *ptr);
stroese38718422003-05-23 11:35:09 +000099
stroesec2642d12004-12-16 18:38:22 +0000100#if 0
stroesed69b1002003-03-25 14:41:35 +0000101 /*
102 * Boot image
103 */
stroesec2642d12004-12-16 18:38:22 +0000104 if (*ptr & 0x00000001) {
105 /*
106 * Boot VxWorks image via bootvx
107 */
108 addr[strlen(addr)-1] = '0';
109 printf("\nBooting VxWorks-Image at addr 0x%s ...\n", addr);
110 setenv("loadaddr", addr);
111
112 local_args[0] = argv[0];
113 local_args[1] = NULL;
114 status = do_bootvx (cmdtp, 0, 1, local_args);
115 } else {
116 /*
117 * Boot image via bootm (normally Linux)
118 */
119 printf("\nBooting Image at addr 0x%s ...\n", addr);
120 setenv("loadaddr", addr);
121
122 local_args[0] = argv[0];
123 local_args[1] = NULL;
124 status = do_bootm (cmdtp, 0, 1, local_args);
125 }
126#else
127 /*
128 * Boot image via bootm
129 */
130 printf("\nBooting Image at addr 0x%s ...\n", addr);
stroesed69b1002003-03-25 14:41:35 +0000131 setenv("loadaddr", addr);
stroese38718422003-05-23 11:35:09 +0000132
stroesed69b1002003-03-25 14:41:35 +0000133 local_args[0] = argv[0];
134 local_args[1] = NULL;
135 status = do_bootm (cmdtp, 0, 1, local_args);
stroesec2642d12004-12-16 18:38:22 +0000136#endif
stroesed69b1002003-03-25 14:41:35 +0000137 }
138
139 return 0;
140}
stroese09433a72003-09-12 08:46:10 +0000141U_BOOT_CMD(
142 loadpci, 1, 1, do_loadpci,
143 "loadpci - Wait for pci-image and boot it\n",
144 NULL
145);
stroesed69b1002003-03-25 14:41:35 +0000146
147#endif
stroesec2642d12004-12-16 18:38:22 +0000148
149#if 1 /* test-only */
150int do_getpci(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
151{
152 unsigned int val;
153 int i;
154
155 printf("\nPCI Configuration Regs for PPC405GP:");
156 for (i=0; i<0x64; i+=4) {
157 pci_read_config_dword(PCIDEVID_405GP, i, &val);
158 if (!(i % 0x10)) {
159 printf("\n%02x: ", i);
160 }
161 printf("%08x ", val);
162 }
163 printf("\n");
164
165 return 0;
166}
167U_BOOT_CMD(
168 getpci, 1, 1, do_getpci,
169 "getpci - Print own pci configuration registers\n",
170 NULL
171);
172
173int do_setpci(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
174{
175 unsigned int addr;
176 unsigned int val;
177
178 addr = simple_strtol (argv[1], NULL, 16);
179 val = simple_strtol (argv[2], NULL, 16);
180
181 printf("\nWriting %08x to PCI reg %08x.\n", val, addr);
182 pci_write_config_dword(PCIDEVID_405GP, addr, val);
183
184 return 0;
185}
186U_BOOT_CMD(
187 setpci, 3, 1, do_setpci,
188 "setpci - Set one pci configuration lword\n",
189 "<addr> <val>\n"
190 " - Write pci configuration lword <val> to <addr>.\n"
191);
192
193int do_dumpdcr(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
194{
195 int i;
196
197 printf("\nDevice Configuration Registers (DCR's) for PPC405GP:");
198 for (i=0; i<=0x1e0; i++) {
199 if (!(i % 0x8)) {
200 printf("\n%04x ", i);
201 }
202 printf("%08lx ", get_dcr(i));
203 }
204 printf("\n");
205
206 return 0;
207}
208U_BOOT_CMD(
209 dumpdcr, 1, 1, do_dumpdcr,
210 "dumpdcr - Dump all DCR registers\n",
211 NULL
212);
213
214
215int do_dumpspr(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
216{
217 printf("\nSpecial Purpose Registers (SPR's) for PPC405GP:");
218 printf("\n%04x %08x ", 947, mfspr(947));
219 printf("\n%04x %08x ", 9, mfspr(9));
220 printf("\n%04x %08x ", 1014, mfspr(1014));
221 printf("\n%04x %08x ", 1015, mfspr(1015));
222 printf("\n%04x %08x ", 1010, mfspr(1010));
223 printf("\n%04x %08x ", 957, mfspr(957));
224 printf("\n%04x %08x ", 1008, mfspr(1008));
225 printf("\n%04x %08x ", 1018, mfspr(1018));
226 printf("\n%04x %08x ", 954, mfspr(954));
227 printf("\n%04x %08x ", 950, mfspr(950));
228 printf("\n%04x %08x ", 951, mfspr(951));
229 printf("\n%04x %08x ", 981, mfspr(981));
230 printf("\n%04x %08x ", 980, mfspr(980));
231 printf("\n%04x %08x ", 982, mfspr(982));
232 printf("\n%04x %08x ", 1012, mfspr(1012));
233 printf("\n%04x %08x ", 1013, mfspr(1013));
234 printf("\n%04x %08x ", 948, mfspr(948));
235 printf("\n%04x %08x ", 949, mfspr(949));
236 printf("\n%04x %08x ", 1019, mfspr(1019));
237 printf("\n%04x %08x ", 979, mfspr(979));
238 printf("\n%04x %08x ", 8, mfspr(8));
239 printf("\n%04x %08x ", 945, mfspr(945));
240 printf("\n%04x %08x ", 987, mfspr(987));
241 printf("\n%04x %08x ", 287, mfspr(287));
242 printf("\n%04x %08x ", 953, mfspr(953));
243 printf("\n%04x %08x ", 955, mfspr(955));
244 printf("\n%04x %08x ", 272, mfspr(272));
245 printf("\n%04x %08x ", 273, mfspr(273));
246 printf("\n%04x %08x ", 274, mfspr(274));
247 printf("\n%04x %08x ", 275, mfspr(275));
248 printf("\n%04x %08x ", 260, mfspr(260));
249 printf("\n%04x %08x ", 276, mfspr(276));
250 printf("\n%04x %08x ", 261, mfspr(261));
251 printf("\n%04x %08x ", 277, mfspr(277));
252 printf("\n%04x %08x ", 262, mfspr(262));
253 printf("\n%04x %08x ", 278, mfspr(278));
254 printf("\n%04x %08x ", 263, mfspr(263));
255 printf("\n%04x %08x ", 279, mfspr(279));
256 printf("\n%04x %08x ", 26, mfspr(26));
257 printf("\n%04x %08x ", 27, mfspr(27));
258 printf("\n%04x %08x ", 990, mfspr(990));
259 printf("\n%04x %08x ", 991, mfspr(991));
260 printf("\n%04x %08x ", 956, mfspr(956));
261 printf("\n%04x %08x ", 284, mfspr(284));
262 printf("\n%04x %08x ", 285, mfspr(285));
263 printf("\n%04x %08x ", 986, mfspr(986));
264 printf("\n%04x %08x ", 984, mfspr(984));
265 printf("\n%04x %08x ", 256, mfspr(256));
266 printf("\n%04x %08x ", 1, mfspr(1));
267 printf("\n%04x %08x ", 944, mfspr(944));
268 printf("\n");
269
270 return 0;
271}
272U_BOOT_CMD(
273 dumpspr, 1, 1, do_dumpspr,
274 "dumpspr - Dump all SPR registers\n",
275 NULL
276);
277
278
279#define PCI0_BRDGOPT1 0x4a
280#define plb0_acr 0x87
281
282int do_getplb(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
283{
284 unsigned short val;
285
286 printf("PLB0_ACR=%08lx\n", get_dcr(0x87));
287 pci_read_config_word(PCIDEVID_405GP, PCI0_BRDGOPT1, &val);
288 printf("PCI0_BRDGOPT1=%04x\n", val);
289 printf("CCR0=%08x\n", mfspr(ccr0));
290
291 return 0;
292}
293U_BOOT_CMD(
294 getplb, 1, 1, do_getplb,
295 "getplb - Dump all plb arbiter registers\n",
296 NULL
297);
298
299int do_setplb(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
300{
301 unsigned int my_acr;
302 unsigned int my_brdgopt1;
303 unsigned int my_ccr0;
304
305 my_acr = simple_strtol (argv[1], NULL, 16);
306 my_brdgopt1 = simple_strtol (argv[2], NULL, 16);
307 my_ccr0 = simple_strtol (argv[3], NULL, 16);
308
309 mtdcr(plb0_acr, my_acr);
310 pci_write_config_word(PCIDEVID_405GP, PCI0_BRDGOPT1, my_brdgopt1);
311 mtspr(ccr0, my_ccr0);
312
313 return 0;
314}
315U_BOOT_CMD(
316 setplb, 4, 1, do_setplb,
317 "setplb - Set all plb arbiter registers\n",
318 "PLB0_ACR PCI0_BRDGOPT1 CCR0\n"
319 " - Set all plb arbiter registers\n"
320);
321
322
323/***********************************************************************
324 *
325 * The following code is only for test purposes!!!!
326 * Please ignore this ugly stuff!!!!!!!!!!!!!!!!!!!
327 *
328 ***********************************************************************/
329
330#define PCI_ADDR 0xc0000000
331
332int do_writepci(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
333{
334 unsigned int addr;
335 unsigned int size;
336 unsigned int countmax;
337 int i;
338 int max;
339 volatile unsigned long *ptr;
340 volatile unsigned long val;
341 int loopcount = 0;
342 int test_pci_read = 0;
343 int test_pci_cfg_write = 0;
344 int test_sync = 0;
345 int test_pci_pre_read = 0;
346
347 addr = simple_strtol (argv[1], NULL, 16);
348 size = simple_strtol (argv[2], NULL, 16);
349 countmax = simple_strtol (argv[3], NULL, 16);
350 if (countmax == 0)
351 countmax = 1000;
352
353 do_getplb(NULL, 0, 0, NULL);
354
355#if 0
356 out32r(PMM0LA, 0);
357 out32r(PMM0PCILA, 0);
358 out32r(PMM0PCIHA, 0);
359 out32r(PMM0MA, 0);
360 out32r(PMM1LA, PCI_ADDR);
361 out32r(PMM1PCILA, addr & 0xff000000);
362 out32r(PMM1PCIHA, 0x00000000);
363 out32r(PMM1MA, 0xff000001);
364#endif
365
366 printf("PMM1LA =%08lx\n", in32r(PMM1LA));
367 printf("PMM1MA =%08lx\n", in32r(PMM1MA));
368 printf("PMM1PCILA =%08lx\n", in32r(PMM1PCILA));
369 printf("PMM1PCIHA =%08lx\n", in32r(PMM1PCIHA));
370
371 addr = PCI_ADDR | (addr & 0x00ffffff);
372 printf("\nWriting at addr %08x, size %08x (countmax=%x)\n", addr, size, countmax);
373
374 max = size >> 2;
375
376 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
377
378 val = *(ulong *)0x00000000;
379 if (val & 0x00000008) {
380 test_pci_pre_read = 1;
381 printf("Running test with pre pci-memory-read access!\n");
382 }
383 if (val & 0x00000004) {
384 test_sync = 1;
385 printf("Running test with sync instruction!\n");
386 }
387 if (val & 0x00000001) {
388 test_pci_read = 1;
389 printf("Running test with pci-memory-read access!\n");
390 }
391 if (val & 0x00000002) {
392 test_pci_cfg_write = 1;
393 printf("Running test with pci-config-write access!\n");
394 }
395
396 while (1) {
397
398 if (test_pci_pre_read) {
399 /*
400 * Read one value back
401 */
402 ptr = (volatile unsigned long *)addr;
403 val = *ptr;
404 }
405
406 /*
407 * Write some values to host via pci busmastering
408 */
409 ptr = (volatile unsigned long *)addr;
410 for (i=0; i<max; i++) {
411 *ptr++ = i;
412 }
413
414 if (test_sync) {
415 /*
416 * Sync previous writes
417 */
418 ppcSync();
419 }
420
421 if (test_pci_read) {
422 /*
423 * Read one value back
424 */
425 ptr = (volatile unsigned long *)addr;
426 val = *ptr;
427 }
428
429 if (test_pci_cfg_write) {
430 /*
431 * Generate IRQ to host via config regs
432 */
433 pci_write_config_byte(PCIDEVID_405GP, 0x44, 0x00);
434 }
435
436 if (loopcount++ > countmax) {
437 /* Abort if ctrl-c was pressed */
438 if (ctrlc()) {
439 puts("\nAbort\n");
440 return 0;
441 }
442
443 putc('.');
444
445 loopcount = 0;
446 }
447 }
448
449 return 0;
450}
451U_BOOT_CMD(
452 writepci, 4, 1, do_writepci,
453 "writepci - Write some data to pcibus\n",
454 "<addr> <size>\n"
455 " - Write some data to pcibus.\n"
456);
457
458#define PCI_CFGADDR 0xeec00000
459#define PCI_CFGDATA 0xeec00004
460
461int ibmPciConfigWrite
462(
463 int offset, /* offset into the configuration space */
464 int width, /* data width */
465 unsigned int data /* data to be written */
466 )
467{
468 /*
469 * Write config register address to the PCI config address register
470 * bit 31 must be 1 and bits 1:0 must be 0 (note LE bit notation)
471 */
472 out32r(PCI_CFGADDR, 0x80000000 | (offset & 0xFFFFFFFC));
473
474#if 0 /* test-only */
475 ppcSync();
476#endif
477
478 /*
479 * Write value to be written to the PCI config data register
480 */
481 switch ( width ) {
482 case 1: out32r(PCI_CFGDATA | (offset & 0x3), (unsigned char)(data & 0xFF));
483 break;
484 case 2: out32r(PCI_CFGDATA | (offset & 0x3), (unsigned short)(data & 0xFFFF));
485 break;
486 case 4: out32r(PCI_CFGDATA | (offset & 0x3), data);
487 break;
488 }
489
490 return (0);
491}
492
493int do_writepci2(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
494{
495 unsigned int addr;
496 unsigned int size;
497 unsigned int countmax;
498 int max;
499 volatile unsigned long *ptr;
500 volatile unsigned long val;
501 int loopcount = 0;
502
503 addr = simple_strtol (argv[1], NULL, 16);
504 size = simple_strtol (argv[2], NULL, 16);
505 countmax = simple_strtol (argv[3], NULL, 16);
506 if (countmax == 0)
507 countmax = 1000;
508
509 do_getplb(NULL, 0, 0, NULL);
510
511#if 0
512 out32r(PMM0LA, 0);
513 out32r(PMM0PCILA, 0);
514 out32r(PMM0PCIHA, 0);
515 out32r(PMM0MA, 0);
516 out32r(PMM1LA, PCI_ADDR);
517 out32r(PMM1PCILA, addr & 0xff000000);
518 out32r(PMM1PCIHA, 0x00000000);
519 out32r(PMM1MA, 0xff000001);
520#endif
521
522 printf("PMM1LA =%08lx\n", in32r(PMM1LA));
523 printf("PMM1MA =%08lx\n", in32r(PMM1MA));
524 printf("PMM1PCILA =%08lx\n", in32r(PMM1PCILA));
525 printf("PMM1PCIHA =%08lx\n", in32r(PMM1PCIHA));
526
527 addr = PCI_ADDR | (addr & 0x00ffffff);
528 printf("\nWriting at addr %08x, size %08x (countmax=%x)\n", addr, size, countmax);
529
530 max = size >> 2;
531
532 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
533
534 while (1) {
535
536 /*
537 * Write one values to host via pci busmastering
538 */
539 ptr = (volatile unsigned long *)addr;
540 *ptr = 0x01234567;
541
542 /*
543 * Read one value back
544 */
545 ptr = (volatile unsigned long *)addr;
546 val = *ptr;
547
548 /*
549 * One pci config write
550 */
551/* pci_write_config_byte(PCIDEVID_405GP, 0x44, 0x00); */
552/* ibmPciConfigWrite(0x44, 1, 0x00); */
553 ibmPciConfigWrite(0x2e, 2, 0x1234); /* subsystem id */
554
555 if (loopcount++ > countmax) {
556 /* Abort if ctrl-c was pressed */
557 if (ctrlc()) {
558 puts("\nAbort\n");
559 return 0;
560 }
561
562 putc('.');
563
564 loopcount = 0;
565 }
566 }
567
568 return 0;
569}
570U_BOOT_CMD(
571 writepci2, 4, 1, do_writepci2,
572 "writepci2- Write some data to pcibus\n",
573 "<addr> <size>\n"
574 " - Write some data to pcibus.\n"
575);
576
577int do_writepci22(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
578{
579 unsigned int addr;
580 unsigned int size;
581 unsigned int countmax = 0;
582 volatile unsigned long *ptr;
583 volatile unsigned long val;
584
585 addr = simple_strtol (argv[1], NULL, 16);
586 size = simple_strtol (argv[2], NULL, 16);
587
588 addr = PCI_ADDR | (addr & 0x00ffffff);
589 printf("\nWriting at addr %08x, size %08x (countmax=%x)\n", addr, size, countmax);
590 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
591
592 while (1) {
593
594 /*
595 * Write one values to host via pci busmastering
596 */
597 ptr = (volatile unsigned long *)addr;
598 *ptr = 0x01234567;
599
600 /*
601 * Read one value back
602 */
603 ptr = (volatile unsigned long *)addr;
604 val = *ptr;
605
606 /*
607 * One pci config write
608 */
609 ibmPciConfigWrite(0x2e, 2, 0x1234); /* subsystem id */
610 }
611
612 return 0;
613}
614U_BOOT_CMD(
615 writepci22, 4, 1, do_writepci22,
616 "writepci22- Write some data to pcibus\n",
617 "<addr> <size>\n"
618 " - Write some data to pcibus.\n"
619);
620
621int ibmPciConfigWrite3
622(
623 int offset, /* offset into the configuration space */
624 int width, /* data width */
625 unsigned int data /* data to be written */
626 )
627{
628 /*
629 * Write config register address to the PCI config address register
630 * bit 31 must be 1 and bits 1:0 must be 0 (note LE bit notation)
631 */
632 out32r(PCI_CFGADDR, 0x80000000 | (offset & 0xFFFFFFFC));
633
634#if 1 /* test-only */
635 ppcSync();
636#endif
637
638 /*
639 * Write value to be written to the PCI config data register
640 */
641 switch ( width ) {
642 case 1: out32r(PCI_CFGDATA | (offset & 0x3), (unsigned char)(data & 0xFF));
643 break;
644 case 2: out32r(PCI_CFGDATA | (offset & 0x3), (unsigned short)(data & 0xFFFF));
645 break;
646 case 4: out32r(PCI_CFGDATA | (offset & 0x3), data);
647 break;
648 }
649
650 return (0);
651}
652
653int do_writepci3(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
654{
655 unsigned int addr;
656 unsigned int size;
657 unsigned int countmax;
658 int max;
659 volatile unsigned long *ptr;
660 volatile unsigned long val;
661 int loopcount = 0;
662
663 addr = simple_strtol (argv[1], NULL, 16);
664 size = simple_strtol (argv[2], NULL, 16);
665 countmax = simple_strtol (argv[3], NULL, 16);
666 if (countmax == 0)
667 countmax = 1000;
668
669 do_getplb(NULL, 0, 0, NULL);
670
671#if 0
672 out32r(PMM0LA, 0);
673 out32r(PMM0PCILA, 0);
674 out32r(PMM0PCIHA, 0);
675 out32r(PMM0MA, 0);
676 out32r(PMM1LA, PCI_ADDR);
677 out32r(PMM1PCILA, addr & 0xff000000);
678 out32r(PMM1PCIHA, 0x00000000);
679 out32r(PMM1MA, 0xff000001);
680#endif
681
682 printf("PMM1LA =%08lx\n", in32r(PMM1LA));
683 printf("PMM1MA =%08lx\n", in32r(PMM1MA));
684 printf("PMM1PCILA =%08lx\n", in32r(PMM1PCILA));
685 printf("PMM1PCIHA =%08lx\n", in32r(PMM1PCIHA));
686
687 addr = PCI_ADDR | (addr & 0x00ffffff);
688 printf("\nWriting at addr %08x, size %08x (countmax=%x)\n", addr, size, countmax);
689
690 max = size >> 2;
691
692 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
693
694 while (1) {
695
696 /*
697 * Write one values to host via pci busmastering
698 */
699 ptr = (volatile unsigned long *)addr;
700 *ptr = 0x01234567;
701
702 /*
703 * Read one value back
704 */
705 ptr = (volatile unsigned long *)addr;
706 val = *ptr;
707
708 /*
709 * One pci config write
710 */
711/* pci_write_config_byte(PCIDEVID_405GP, 0x44, 0x00); */
712/* ibmPciConfigWrite(0x44, 1, 0x00); */
713 ibmPciConfigWrite3(0x2e, 2, 0x1234); /* subsystem id */
714
715 if (loopcount++ > countmax) {
716 /* Abort if ctrl-c was pressed */
717 if (ctrlc()) {
718 puts("\nAbort\n");
719 return 0;
720 }
721
722 putc('.');
723
724 loopcount = 0;
725 }
726 }
727
728 return 0;
729}
730U_BOOT_CMD(
731 writepci3, 4, 1, do_writepci3,
732 "writepci3- Write some data to pcibus\n",
733 "<addr> <size>\n"
734 " - Write some data to pcibus.\n"
735);
736
737
738#define SECTOR_SIZE 32 /* 32 byte cache line */
739#define SECTOR_MASK 0x1F
740
741void my_flush_dcache(ulong lcl_addr, ulong count)
742{
743 unsigned int lcl_target;
744
745 /* promote to nearest cache sector */
746 lcl_target = (lcl_addr + count + SECTOR_SIZE - 1) & ~SECTOR_MASK;
747 lcl_addr &= ~SECTOR_MASK;
748 while (lcl_addr != lcl_target)
749 {
750 /* ppcDcbf((void *)lcl_addr);*/
751 __asm__("dcbf 0,%0": :"r" (lcl_addr));
752 lcl_addr += SECTOR_SIZE;
753 }
754 __asm__("sync"); /* Always flush prefetch queue in any case */
755}
756
757int do_writepci_cache(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
758{
759 unsigned int addr;
760 unsigned int size;
761 unsigned int countmax;
762 int i;
763 volatile unsigned long *ptr;
764 volatile unsigned long val;
765 int loopcount = 0;
766
767 addr = simple_strtol (argv[1], NULL, 16);
768 size = simple_strtol (argv[2], NULL, 16);
769 countmax = simple_strtol (argv[3], NULL, 16);
770 if (countmax == 0)
771 countmax = 1000;
772
773 do_getplb(NULL, 0, 0, NULL);
774
775#if 0
776 out32r(PMM0LA, 0);
777 out32r(PMM0PCILA, 0);
778 out32r(PMM0PCIHA, 0);
779 out32r(PMM0MA, 0);
780 out32r(PMM1LA, PCI_ADDR);
781 out32r(PMM1PCILA, addr & 0xff000000);
782 out32r(PMM1PCIHA, 0x00000000);
783 out32r(PMM1MA, 0xff000001);
784#endif
785
786 printf("PMM1LA =%08lx\n", in32r(PMM1LA));
787 printf("PMM1MA =%08lx\n", in32r(PMM1MA));
788 printf("PMM1PCILA =%08lx\n", in32r(PMM1PCILA));
789 printf("PMM1PCIHA =%08lx\n", in32r(PMM1PCIHA));
790
791 addr = PCI_ADDR | (addr & 0x00ffffff);
792 printf("\nWriting at addr %08x, size %08x (countmax=%x)\n", addr, size, countmax);
793
794 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
795
796 i = 0;
797
798 /*
799 * Set pci region as cachable
800 */
801 ppcSync();
802 __asm__ volatile (" addis 4,0,0x0000 ");
803 __asm__ volatile (" addi 4,4,0x0080 ");
804 __asm__ volatile (" mtdccr 4 ");
805 ppcSync();
806
807 while (1) {
808
809 /*
810 * Write one values to host via pci busmastering
811 */
812 ptr = (volatile unsigned long *)addr;
813 printf("A\n"); /* test-only */
814 *ptr++ = i++;
815 *ptr++ = i++;
816 *ptr++ = i++;
817 *ptr++ = i++;
818 *ptr++ = i++;
819 *ptr++ = i++;
820 *ptr++ = i++;
821 *ptr++ = i++;
822 printf("B\n"); /* test-only */
823 my_flush_dcache(addr, 32);
824 printf("C\n"); /* test-only */
825
826 /*
827 * Read one value back
828 */
829 ptr = (volatile unsigned long *)addr;
830 val = *ptr;
831 printf("D\n"); /* test-only */
832
833 /*
834 * One pci config write
835 */
836/* pci_write_config_byte(PCIDEVID_405GP, 0x44, 0x00); */
837/* ibmPciConfigWrite(0x44, 1, 0x00); */
838 ibmPciConfigWrite3(0x2e, 2, 0x1234); /* subsystem id */
839 printf("E\n"); /* test-only */
840
841 if (loopcount++ > countmax) {
842 /* Abort if ctrl-c was pressed */
843 if (ctrlc()) {
844 puts("\nAbort\n");
845 return 0;
846 }
847
848 putc('.');
849
850 loopcount = 0;
851 }
852 }
853
854 return 0;
855}
856U_BOOT_CMD(
857 writepci_cache, 4, 1, do_writepci_cache,
858 "writepci_cache - Write some data to pcibus\n",
859 "<addr> <size>\n"
860 " - Write some data to pcibus.\n"
861);
862
863int do_savepci(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
864{
865 unsigned int *ptr;
866 int i;
867
868 /*
869 * Save own pci configuration in PRAM
870 */
871 memset((char *)PCI_REGS_ADDR, 0, PCI_REGS_LEN);
872 ptr = (unsigned int *)PCI_REGS_ADDR + 1;
873 for (i=0; i<0x40; i+=4) {
874 pci_read_config_dword(PCIDEVID_405GP, i, ptr++);
875 }
876 ptr = (unsigned int *)PCI_REGS_ADDR;
Wolfgang Denk77ddac92005-10-13 16:45:02 +0200877 *ptr = crc32(0, (uchar *)PCI_REGS_ADDR+4, PCI_REGS_LEN-4);
stroesec2642d12004-12-16 18:38:22 +0000878
879 printf("\nStoring PCI Configuration Regs...\n");
880
881 return 0;
882}
883U_BOOT_CMD(
884 savepci, 4, 1, do_savepci,
885 "savepci - Save all pci regs\n",
886 "<addr> <size>\n"
887 " - Write some data to pcibus.\n"
888);
889
890int do_restorepci(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
891{
892 unsigned int *ptr;
893 int i;
894
895 /*
896 * Rewrite pci config regs (only after soft-reset with magic set)
897 */
898 ptr = (unsigned int *)PCI_REGS_ADDR;
Wolfgang Denk77ddac92005-10-13 16:45:02 +0200899 if (crc32(0, (uchar *)PCI_REGS_ADDR+4, PCI_REGS_LEN-4) == *ptr) {
stroesec2642d12004-12-16 18:38:22 +0000900 puts("Restoring PCI Configurations Regs!\n");
901 ptr = (unsigned int *)PCI_REGS_ADDR + 1;
902 for (i=0; i<0x40; i+=4) {
903 pci_write_config_dword(PCIDEVID_405GP, i, *ptr++);
904 }
905 }
906 mtdcr(uicsr, 0xFFFFFFFF); /* clear all ints */
907
908 return 0;
909}
910U_BOOT_CMD(
911 restorepci, 4, 1, do_restorepci,
912 "restorepci - Restore all pci regs\n",
913 "<addr> <size>\n"
914 " - Write some data to pcibus.\n"
915);
916
917
918extern void write_without_sync(void);
919extern void write_with_sync(void);
920extern void write_with_less_sync(void);
921extern void write_with_more_sync(void);
922
923/*
924 * code from IBM-PPCSUPP
925 */
926int do_writeibm1(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
927{
928 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
929
930 write_without_sync();
931
932 return 0;
933}
934U_BOOT_CMD(
935 writeibm1, 4, 1, do_writeibm1,
936 "writeibm1- Write some data to pcibus (without sync)\n",
937 "<addr> <size>\n"
938 " - Write some data to pcibus.\n"
939);
940
941int do_writeibm2(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
942{
943 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
944
945 write_with_sync();
946
947 return 0;
948}
949U_BOOT_CMD(
950 writeibm2, 4, 1, do_writeibm2,
951 "writeibm2- Write some data to pcibus (with sync)\n",
952 "<addr> <size>\n"
953 " - Write some data to pcibus.\n"
954);
955
956int do_writeibm22(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
957{
958 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
959
960 write_with_less_sync();
961
962 return 0;
963}
964U_BOOT_CMD(
965 writeibm22, 4, 1, do_writeibm22,
966 "writeibm22- Write some data to pcibus (with less sync)\n",
967 "<addr> <size>\n"
968 " - Write some data to pcibus.\n"
969);
970
971int do_writeibm3(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
972{
973 pci_write_config_word(PCIDEVID_405GP, 0x04, 0x0106); /* write command reg */
974
975 write_with_more_sync();
976
977 return 0;
978}
979U_BOOT_CMD(
980 writeibm3, 4, 1, do_writeibm3,
981 "writeibm3- Write some data to pcibus (with more sync)\n",
982 "<addr> <size>\n"
983 " - Write some data to pcibus.\n"
984);
985#endif