blob: 442c01ac6f4b23403d6c70223dfa465794bc8976 [file] [log] [blame]
Tom Rini10e47792018-05-06 17:58:06 -04001// SPDX-License-Identifier: GPL-2.0+
Christophe Leroy069fa832017-07-06 10:23:22 +02002/*
3 * (C) Copyright 2000-2003
4 * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
Christophe Leroy069fa832017-07-06 10:23:22 +02005 */
6
7/*
8 * MPC8xx Internal Memory Map Functions
9 */
10
11#include <common.h>
12#include <command.h>
13
Christophe Leroyb3510fb2018-03-16 17:20:41 +010014#include <asm/immap_8xx.h>
Christophe Leroy10ff63a2018-03-16 17:20:43 +010015#include <asm/cpm_8xx.h>
Christophe Leroy069fa832017-07-06 10:23:22 +020016#include <asm/iopin_8xx.h>
Christophe Leroy394f9b32017-07-06 10:33:13 +020017#include <asm/io.h>
Christophe Leroy069fa832017-07-06 10:23:22 +020018
19DECLARE_GLOBAL_DATA_PTR;
20
Christophe Leroy4a4750b2017-07-13 15:10:08 +020021static int do_siuinfo(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
Christophe Leroy069fa832017-07-06 10:23:22 +020022{
Christophe Leroy394f9b32017-07-06 10:33:13 +020023 immap_t __iomem *immap = (immap_t __iomem *)CONFIG_SYS_IMMR;
24 sysconf8xx_t __iomem *sc = &immap->im_siu_conf;
Christophe Leroy069fa832017-07-06 10:23:22 +020025
Christophe Leroy394f9b32017-07-06 10:33:13 +020026 printf("SIUMCR= %08x SYPCR = %08x\n",
27 in_be32(&sc->sc_siumcr), in_be32(&sc->sc_sypcr));
28 printf("SWT = %08x\n", in_be32(&sc->sc_swt));
29 printf("SIPEND= %08x SIMASK= %08x\n",
30 in_be32(&sc->sc_sipend), in_be32(&sc->sc_simask));
31 printf("SIEL = %08x SIVEC = %08x\n",
32 in_be32(&sc->sc_siel), in_be32(&sc->sc_sivec));
33 printf("TESR = %08x SDCR = %08x\n",
34 in_be32(&sc->sc_tesr), in_be32(&sc->sc_sdcr));
Christophe Leroy069fa832017-07-06 10:23:22 +020035 return 0;
36}
37
Christophe Leroy4a4750b2017-07-13 15:10:08 +020038static int do_memcinfo(cmd_tbl_t *cmdtp, int flag, int argc,
39 char * const argv[])
Christophe Leroy069fa832017-07-06 10:23:22 +020040{
Christophe Leroy394f9b32017-07-06 10:33:13 +020041 immap_t __iomem *immap = (immap_t __iomem *)CONFIG_SYS_IMMR;
42 memctl8xx_t __iomem *memctl = &immap->im_memctl;
Christophe Leroy069fa832017-07-06 10:23:22 +020043 int nbanks = 8;
Christophe Leroy394f9b32017-07-06 10:33:13 +020044 uint __iomem *p = &memctl->memc_br0;
Christophe Leroy069fa832017-07-06 10:23:22 +020045 int i;
46
Christophe Leroy394f9b32017-07-06 10:33:13 +020047 for (i = 0; i < nbanks; i++, p += 2)
48 printf("BR%-2d = %08x OR%-2d = %08x\n",
49 i, in_be32(p), i, in_be32(p + 1));
Christophe Leroy069fa832017-07-06 10:23:22 +020050
Christophe Leroy394f9b32017-07-06 10:33:13 +020051 printf("MAR = %08x", in_be32(&memctl->memc_mar));
52 printf(" MCR = %08x\n", in_be32(&memctl->memc_mcr));
53 printf("MAMR = %08x MBMR = %08x",
54 in_be32(&memctl->memc_mamr), in_be32(&memctl->memc_mbmr));
55 printf("\nMSTAT = %04x\n", in_be16(&memctl->memc_mstat));
56 printf("MPTPR = %04x MDR = %08x\n",
57 in_be16(&memctl->memc_mptpr), in_be32(&memctl->memc_mdr));
Christophe Leroy069fa832017-07-06 10:23:22 +020058 return 0;
59}
60
Christophe Leroy4a4750b2017-07-13 15:10:08 +020061static int do_carinfo(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
Christophe Leroy069fa832017-07-06 10:23:22 +020062{
Christophe Leroy394f9b32017-07-06 10:33:13 +020063 immap_t __iomem *immap = (immap_t __iomem *)CONFIG_SYS_IMMR;
64 car8xx_t __iomem *car = &immap->im_clkrst;
Christophe Leroy069fa832017-07-06 10:23:22 +020065
Christophe Leroy394f9b32017-07-06 10:33:13 +020066 printf("SCCR = %08x\n", in_be32(&car->car_sccr));
67 printf("PLPRCR= %08x\n", in_be32(&car->car_plprcr));
68 printf("RSR = %08x\n", in_be32(&car->car_rsr));
Christophe Leroy069fa832017-07-06 10:23:22 +020069 return 0;
70}
71
72static int counter;
73
Christophe Leroy48f896d2017-07-06 10:33:17 +020074static void header(void)
Christophe Leroy069fa832017-07-06 10:23:22 +020075{
76 char *data = "\
77 -------------------------------- --------------------------------\
78 00000000001111111111222222222233 00000000001111111111222222222233\
79 01234567890123456789012345678901 01234567890123456789012345678901\
80 -------------------------------- --------------------------------\
81 ";
82 int i;
83
84 if (counter % 2)
85 putc('\n');
86 counter = 0;
87
88 for (i = 0; i < 4; i++, data += 79)
89 printf("%.79s\n", data);
90}
91
Christophe Leroy48f896d2017-07-06 10:33:17 +020092static void binary(char *label, uint value, int nbits)
Christophe Leroy069fa832017-07-06 10:23:22 +020093{
94 uint mask = 1 << (nbits - 1);
95 int i, second = (counter++ % 2);
96
97 if (second)
Christophe Leroy48f896d2017-07-06 10:33:17 +020098 putc(' ');
99 puts(label);
Christophe Leroy069fa832017-07-06 10:23:22 +0200100 for (i = 32 + 1; i != nbits; i--)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200101 putc(' ');
Christophe Leroy069fa832017-07-06 10:23:22 +0200102
103 while (mask != 0) {
104 if (value & mask)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200105 putc('1');
Christophe Leroy069fa832017-07-06 10:23:22 +0200106 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200107 putc('0');
Christophe Leroy069fa832017-07-06 10:23:22 +0200108 mask >>= 1;
109 }
110
111 if (second)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200112 putc('\n');
Christophe Leroy069fa832017-07-06 10:23:22 +0200113}
114
115#define PA_NBITS 16
116#define PA_NB_ODR 8
117#define PB_NBITS 18
118#define PB_NB_ODR 16
119#define PC_NBITS 12
120#define PD_NBITS 13
121
Christophe Leroy4a4750b2017-07-13 15:10:08 +0200122static int do_iopinfo(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
Christophe Leroy069fa832017-07-06 10:23:22 +0200123{
Christophe Leroy394f9b32017-07-06 10:33:13 +0200124 immap_t __iomem *immap = (immap_t __iomem *)CONFIG_SYS_IMMR;
125 iop8xx_t __iomem *iop = &immap->im_ioport;
126 ushort __iomem *l, *r;
127 uint __iomem *R;
Christophe Leroy069fa832017-07-06 10:23:22 +0200128
129 counter = 0;
Christophe Leroy48f896d2017-07-06 10:33:17 +0200130 header();
Christophe Leroy069fa832017-07-06 10:23:22 +0200131
132 /*
133 * Ports A & B
134 */
135
136 l = &iop->iop_padir;
137 R = &immap->im_cpm.cp_pbdir;
Christophe Leroy394f9b32017-07-06 10:33:13 +0200138 binary("PA_DIR", in_be16(l++), PA_NBITS);
139 binary("PB_DIR", in_be32(R++), PB_NBITS);
140 binary("PA_PAR", in_be16(l++), PA_NBITS);
141 binary("PB_PAR", in_be32(R++), PB_NBITS);
142 binary("PA_ODR", in_be16(l++), PA_NB_ODR);
143 binary("PB_ODR", in_be32(R++), PB_NB_ODR);
144 binary("PA_DAT", in_be16(l++), PA_NBITS);
145 binary("PB_DAT", in_be32(R++), PB_NBITS);
Christophe Leroy069fa832017-07-06 10:23:22 +0200146
Christophe Leroy48f896d2017-07-06 10:33:17 +0200147 header();
Christophe Leroy069fa832017-07-06 10:23:22 +0200148
149 /*
150 * Ports C & D
151 */
152
153 l = &iop->iop_pcdir;
154 r = &iop->iop_pddir;
Christophe Leroy394f9b32017-07-06 10:33:13 +0200155 binary("PC_DIR", in_be16(l++), PC_NBITS);
156 binary("PD_DIR", in_be16(r++), PD_NBITS);
157 binary("PC_PAR", in_be16(l++), PC_NBITS);
158 binary("PD_PAR", in_be16(r++), PD_NBITS);
159 binary("PC_SO ", in_be16(l++), PC_NBITS);
160 binary(" ", 0, 0);
Christophe Leroy069fa832017-07-06 10:23:22 +0200161 r++;
Christophe Leroy394f9b32017-07-06 10:33:13 +0200162 binary("PC_DAT", in_be16(l++), PC_NBITS);
163 binary("PD_DAT", in_be16(r++), PD_NBITS);
164 binary("PC_INT", in_be16(l++), PC_NBITS);
Christophe Leroy069fa832017-07-06 10:23:22 +0200165
Christophe Leroy48f896d2017-07-06 10:33:17 +0200166 header();
Christophe Leroy069fa832017-07-06 10:23:22 +0200167 return 0;
168}
169
170/*
171 * set the io pins
172 * this needs a clean up for smaller tighter code
173 * use *uint and set the address based on cmd + port
174 */
Christophe Leroy4a4750b2017-07-13 15:10:08 +0200175static int do_iopset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
Christophe Leroy069fa832017-07-06 10:23:22 +0200176{
177 uint rcode = 0;
178 iopin_t iopin;
Christophe Leroy48f896d2017-07-06 10:33:17 +0200179 static uint port;
180 static uint pin;
181 static uint value;
Christophe Leroy069fa832017-07-06 10:23:22 +0200182 static enum {
183 DIR,
184 PAR,
185 SOR,
186 ODR,
187 DAT,
188 INT
189 } cmd = DAT;
190
191 if (argc != 5) {
Christophe Leroy48f896d2017-07-06 10:33:17 +0200192 puts("iopset PORT PIN CMD VALUE\n");
Christophe Leroy069fa832017-07-06 10:23:22 +0200193 return 1;
194 }
195 port = argv[1][0] - 'A';
196 if (port > 3)
197 port -= 0x20;
198 if (port > 3)
199 rcode = 1;
Christophe Leroy48f896d2017-07-06 10:33:17 +0200200 pin = simple_strtol(argv[2], NULL, 10);
Christophe Leroy069fa832017-07-06 10:23:22 +0200201 if (pin > 31)
202 rcode = 1;
203
204
205 switch (argv[3][0]) {
206 case 'd':
207 if (argv[3][1] == 'a')
208 cmd = DAT;
209 else if (argv[3][1] == 'i')
210 cmd = DIR;
211 else
212 rcode = 1;
213 break;
214 case 'p':
215 cmd = PAR;
216 break;
217 case 'o':
218 cmd = ODR;
219 break;
220 case 's':
221 cmd = SOR;
222 break;
223 case 'i':
224 cmd = INT;
225 break;
226 default:
Christophe Leroy48f896d2017-07-06 10:33:17 +0200227 printf("iopset: unknown command %s\n", argv[3]);
Christophe Leroy069fa832017-07-06 10:23:22 +0200228 rcode = 1;
229 }
230 if (argv[4][0] == '1')
231 value = 1;
232 else if (argv[4][0] == '0')
233 value = 0;
234 else
235 rcode = 1;
236 if (rcode == 0) {
237 iopin.port = port;
238 iopin.pin = pin;
239 iopin.flag = 0;
240 switch (cmd) {
241 case DIR:
242 if (value)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200243 iopin_set_out(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200244 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200245 iopin_set_in(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200246 break;
247 case PAR:
248 if (value)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200249 iopin_set_ded(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200250 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200251 iopin_set_gen(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200252 break;
253 case SOR:
254 if (value)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200255 iopin_set_opt2(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200256 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200257 iopin_set_opt1(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200258 break;
259 case ODR:
260 if (value)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200261 iopin_set_odr(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200262 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200263 iopin_set_act(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200264 break;
265 case DAT:
266 if (value)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200267 iopin_set_high(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200268 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200269 iopin_set_low(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200270 break;
271 case INT:
272 if (value)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200273 iopin_set_falledge(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200274 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200275 iopin_set_anyedge(&iopin);
Christophe Leroy069fa832017-07-06 10:23:22 +0200276 break;
277 }
Christophe Leroy069fa832017-07-06 10:23:22 +0200278 }
279 return rcode;
280}
281
Christophe Leroy48f896d2017-07-06 10:33:17 +0200282static void prbrg(int n, uint val)
Christophe Leroy069fa832017-07-06 10:23:22 +0200283{
284 uint extc = (val >> 14) & 3;
285 uint cd = (val & CPM_BRG_CD_MASK) >> 1;
286 uint div16 = (val & CPM_BRG_DIV16) != 0;
287
288 ulong clock = gd->cpu_clk;
289
Christophe Leroy48f896d2017-07-06 10:33:17 +0200290 printf("BRG%d:", n);
Christophe Leroy069fa832017-07-06 10:23:22 +0200291
292 if (val & CPM_BRG_RST)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200293 puts(" RESET");
Christophe Leroy069fa832017-07-06 10:23:22 +0200294 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200295 puts(" ");
Christophe Leroy069fa832017-07-06 10:23:22 +0200296
297 if (val & CPM_BRG_EN)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200298 puts(" ENABLED");
Christophe Leroy069fa832017-07-06 10:23:22 +0200299 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200300 puts(" DISABLED");
Christophe Leroy069fa832017-07-06 10:23:22 +0200301
Christophe Leroy48f896d2017-07-06 10:33:17 +0200302 printf(" EXTC=%d", extc);
Christophe Leroy069fa832017-07-06 10:23:22 +0200303
304 if (val & CPM_BRG_ATB)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200305 puts(" ATB");
Christophe Leroy069fa832017-07-06 10:23:22 +0200306 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200307 puts(" ");
Christophe Leroy069fa832017-07-06 10:23:22 +0200308
Christophe Leroy48f896d2017-07-06 10:33:17 +0200309 printf(" DIVIDER=%4d", cd);
Christophe Leroy069fa832017-07-06 10:23:22 +0200310 if (extc == 0 && cd != 0) {
311 uint baudrate;
312
313 if (div16)
314 baudrate = (clock / 16) / (cd + 1);
315 else
316 baudrate = clock / (cd + 1);
317
Christophe Leroy48f896d2017-07-06 10:33:17 +0200318 printf("=%6d bps", baudrate);
Christophe Leroy069fa832017-07-06 10:23:22 +0200319 } else {
Christophe Leroy48f896d2017-07-06 10:33:17 +0200320 puts(" ");
Christophe Leroy069fa832017-07-06 10:23:22 +0200321 }
322
323 if (val & CPM_BRG_DIV16)
Christophe Leroy48f896d2017-07-06 10:33:17 +0200324 puts(" DIV16");
Christophe Leroy069fa832017-07-06 10:23:22 +0200325 else
Christophe Leroy48f896d2017-07-06 10:33:17 +0200326 puts(" ");
Christophe Leroy069fa832017-07-06 10:23:22 +0200327
Christophe Leroy48f896d2017-07-06 10:33:17 +0200328 putc('\n');
Christophe Leroy069fa832017-07-06 10:23:22 +0200329}
330
Christophe Leroy4a4750b2017-07-13 15:10:08 +0200331static int do_brginfo(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
Christophe Leroy069fa832017-07-06 10:23:22 +0200332{
Christophe Leroy394f9b32017-07-06 10:33:13 +0200333 immap_t __iomem *immap = (immap_t __iomem *)CONFIG_SYS_IMMR;
334 cpm8xx_t __iomem *cp = &immap->im_cpm;
335 uint __iomem *p = &cp->cp_brgc1;
Christophe Leroy069fa832017-07-06 10:23:22 +0200336 int i = 1;
337
338 while (i <= 4)
Christophe Leroy394f9b32017-07-06 10:33:13 +0200339 prbrg(i++, in_be32(p++));
Christophe Leroy069fa832017-07-06 10:23:22 +0200340
341 return 0;
342}
343
Christophe Leroyb4ebefa2018-03-16 17:20:57 +0100344#ifdef CONFIG_CMD_REGINFO
345void print_reginfo(void)
346{
347 immap_t __iomem *immap = (immap_t __iomem *)CONFIG_SYS_IMMR;
348 sit8xx_t __iomem *timers = &immap->im_sit;
349
350 printf("\nSystem Configuration registers\n"
351 "\tIMMR\t0x%08X\n", get_immr());
352 do_siuinfo(NULL, 0, 0, NULL);
353
354 printf("Memory Controller Registers\n");
355 do_memcinfo(NULL, 0, 0, NULL);
356
357 printf("\nSystem Integration Timers\n");
358 printf("\tTBSCR\t0x%04X\tRTCSC\t0x%04X\n",
359 in_be16(&timers->sit_tbscr), in_be16(&timers->sit_rtcsc));
360 printf("\tPISCR\t0x%04X\n", in_be16(&timers->sit_piscr));
361}
362#endif
363
Christophe Leroy069fa832017-07-06 10:23:22 +0200364/***************************************************/
365
366U_BOOT_CMD(
367 siuinfo, 1, 1, do_siuinfo,
368 "print System Interface Unit (SIU) registers",
369 ""
370);
371
372U_BOOT_CMD(
373 memcinfo, 1, 1, do_memcinfo,
374 "print Memory Controller registers",
375 ""
376);
377
378U_BOOT_CMD(
379 carinfo, 1, 1, do_carinfo,
380 "print Clocks and Reset registers",
381 ""
382);
383
384U_BOOT_CMD(
385 iopinfo, 1, 1, do_iopinfo,
386 "print I/O Port registers",
387 ""
388);
389
390U_BOOT_CMD(
391 iopset, 5, 0, do_iopset,
392 "set I/O Port registers",
393 "PORT PIN CMD VALUE\nPORT: A-D, PIN: 0-31, CMD: [dat|dir|odr|sor], VALUE: 0|1"
394);
395
396U_BOOT_CMD(
397 brginfo, 1, 1, do_brginfo,
398 "print Baud Rate Generator (BRG) registers",
399 ""
400);