]> git.kernelconcepts.de Git - karo-tx-linux.git/blob - arch/powerpc/xmon/xmon.c
af9d3469fb9933e4f3d424f01e3230ddeb580c67
[karo-tx-linux.git] / arch / powerpc / xmon / xmon.c
1 /*
2  * Routines providing a simple monitor for use on the PowerMac.
3  *
4  * Copyright (C) 1996-2005 Paul Mackerras.
5  * Copyright (C) 2001 PPC64 Team, IBM Corp
6  * Copyrignt (C) 2006 Michael Ellerman, IBM Corp
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
10  *      as published by the Free Software Foundation; either version
11  *      2 of the License, or (at your option) any later version.
12  */
13 #include <linux/errno.h>
14 #include <linux/sched.h>
15 #include <linux/smp.h>
16 #include <linux/mm.h>
17 #include <linux/reboot.h>
18 #include <linux/delay.h>
19 #include <linux/kallsyms.h>
20 #include <linux/kmsg_dump.h>
21 #include <linux/cpumask.h>
22 #include <linux/export.h>
23 #include <linux/sysrq.h>
24 #include <linux/interrupt.h>
25 #include <linux/irq.h>
26 #include <linux/bug.h>
27
28 #include <asm/ptrace.h>
29 #include <asm/string.h>
30 #include <asm/prom.h>
31 #include <asm/machdep.h>
32 #include <asm/xmon.h>
33 #include <asm/processor.h>
34 #include <asm/pgtable.h>
35 #include <asm/mmu.h>
36 #include <asm/mmu_context.h>
37 #include <asm/cputable.h>
38 #include <asm/rtas.h>
39 #include <asm/sstep.h>
40 #include <asm/irq_regs.h>
41 #include <asm/spu.h>
42 #include <asm/spu_priv1.h>
43 #include <asm/setjmp.h>
44 #include <asm/reg.h>
45 #include <asm/debug.h>
46 #include <asm/hw_breakpoint.h>
47
48 #ifdef CONFIG_PPC64
49 #include <asm/hvcall.h>
50 #include <asm/paca.h>
51 #endif
52
53 #include "nonstdio.h"
54 #include "dis-asm.h"
55
56 #ifdef CONFIG_SMP
57 static cpumask_t cpus_in_xmon = CPU_MASK_NONE;
58 static unsigned long xmon_taken = 1;
59 static int xmon_owner;
60 static int xmon_gate;
61 #else
62 #define xmon_owner 0
63 #endif /* CONFIG_SMP */
64
65 static unsigned long in_xmon __read_mostly = 0;
66
67 static unsigned long adrs;
68 static int size = 1;
69 #define MAX_DUMP (128 * 1024)
70 static unsigned long ndump = 64;
71 static unsigned long nidump = 16;
72 static unsigned long ncsum = 4096;
73 static int termch;
74 static char tmpstr[128];
75
76 static long bus_error_jmp[JMP_BUF_LEN];
77 static int catch_memory_errors;
78 static long *xmon_fault_jmp[NR_CPUS];
79
80 /* Breakpoint stuff */
81 struct bpt {
82         unsigned long   address;
83         unsigned int    instr[2];
84         atomic_t        ref_count;
85         int             enabled;
86         unsigned long   pad;
87 };
88
89 /* Bits in bpt.enabled */
90 #define BP_IABR_TE      1               /* IABR translation enabled */
91 #define BP_IABR         2
92 #define BP_TRAP         8
93 #define BP_DABR         0x10
94
95 #define NBPTS   256
96 static struct bpt bpts[NBPTS];
97 static struct bpt dabr;
98 static struct bpt *iabr;
99 static unsigned bpinstr = 0x7fe00008;   /* trap */
100
101 #define BP_NUM(bp)      ((bp) - bpts + 1)
102
103 /* Prototypes */
104 static int cmds(struct pt_regs *);
105 static int mread(unsigned long, void *, int);
106 static int mwrite(unsigned long, void *, int);
107 static int handle_fault(struct pt_regs *);
108 static void byterev(unsigned char *, int);
109 static void memex(void);
110 static int bsesc(void);
111 static void dump(void);
112 static void prdump(unsigned long, long);
113 static int ppc_inst_dump(unsigned long, long, int);
114 static void dump_log_buf(void);
115 static void backtrace(struct pt_regs *);
116 static void excprint(struct pt_regs *);
117 static void prregs(struct pt_regs *);
118 static void memops(int);
119 static void memlocate(void);
120 static void memzcan(void);
121 static void memdiffs(unsigned char *, unsigned char *, unsigned, unsigned);
122 int skipbl(void);
123 int scanhex(unsigned long *valp);
124 static void scannl(void);
125 static int hexdigit(int);
126 void getstring(char *, int);
127 static void flush_input(void);
128 static int inchar(void);
129 static void take_input(char *);
130 static unsigned long read_spr(int);
131 static void write_spr(int, unsigned long);
132 static void super_regs(void);
133 static void remove_bpts(void);
134 static void insert_bpts(void);
135 static void remove_cpu_bpts(void);
136 static void insert_cpu_bpts(void);
137 static struct bpt *at_breakpoint(unsigned long pc);
138 static struct bpt *in_breakpoint_table(unsigned long pc, unsigned long *offp);
139 static int  do_step(struct pt_regs *);
140 static void bpt_cmds(void);
141 static void cacheflush(void);
142 static int  cpu_cmd(void);
143 static void csum(void);
144 static void bootcmds(void);
145 static void proccall(void);
146 void dump_segments(void);
147 static void symbol_lookup(void);
148 static void xmon_show_stack(unsigned long sp, unsigned long lr,
149                             unsigned long pc);
150 static void xmon_print_symbol(unsigned long address, const char *mid,
151                               const char *after);
152 static const char *getvecname(unsigned long vec);
153
154 static int do_spu_cmd(void);
155
156 #ifdef CONFIG_44x
157 static void dump_tlb_44x(void);
158 #endif
159 #ifdef CONFIG_PPC_BOOK3E
160 static void dump_tlb_book3e(void);
161 #endif
162
163 static int xmon_no_auto_backtrace;
164
165 extern void xmon_enter(void);
166 extern void xmon_leave(void);
167
168 #ifdef CONFIG_PPC64
169 #define REG             "%.16lx"
170 #else
171 #define REG             "%.8lx"
172 #endif
173
174 #define GETWORD(v)      (((v)[0] << 24) + ((v)[1] << 16) + ((v)[2] << 8) + (v)[3])
175
176 #define isxdigit(c)     (('0' <= (c) && (c) <= '9') \
177                          || ('a' <= (c) && (c) <= 'f') \
178                          || ('A' <= (c) && (c) <= 'F'))
179 #define isalnum(c)      (('0' <= (c) && (c) <= '9') \
180                          || ('a' <= (c) && (c) <= 'z') \
181                          || ('A' <= (c) && (c) <= 'Z'))
182 #define isspace(c)      (c == ' ' || c == '\t' || c == 10 || c == 13 || c == 0)
183
184 static char *help_string = "\
185 Commands:\n\
186   b     show breakpoints\n\
187   bd    set data breakpoint\n\
188   bi    set instruction breakpoint\n\
189   bc    clear breakpoint\n"
190 #ifdef CONFIG_SMP
191   "\
192   c     print cpus stopped in xmon\n\
193   c#    try to switch to cpu number h (in hex)\n"
194 #endif
195   "\
196   C     checksum\n\
197   d     dump bytes\n\
198   di    dump instructions\n\
199   df    dump float values\n\
200   dd    dump double values\n\
201   dl    dump the kernel log buffer\n"
202 #ifdef CONFIG_PPC64
203   "\
204   dp[#] dump paca for current cpu, or cpu #\n\
205   dpa   dump paca for all possible cpus\n"
206 #endif
207   "\
208   dr    dump stream of raw bytes\n\
209   e     print exception information\n\
210   f     flush cache\n\
211   la    lookup symbol+offset of specified address\n\
212   ls    lookup address of specified symbol\n\
213   m     examine/change memory\n\
214   mm    move a block of memory\n\
215   ms    set a block of memory\n\
216   md    compare two blocks of memory\n\
217   ml    locate a block of memory\n\
218   mz    zero a block of memory\n\
219   mi    show information about memory allocation\n\
220   p     call a procedure\n\
221   r     print registers\n\
222   s     single step\n"
223 #ifdef CONFIG_SPU_BASE
224 "  ss   stop execution on all spus\n\
225   sr    restore execution on stopped spus\n\
226   sf  # dump spu fields for spu # (in hex)\n\
227   sd  # dump spu local store for spu # (in hex)\n\
228   sdi # disassemble spu local store for spu # (in hex)\n"
229 #endif
230 "  S    print special registers\n\
231   t     print backtrace\n\
232   x     exit monitor and recover\n\
233   X     exit monitor and dont recover\n"
234 #if defined(CONFIG_PPC64) && !defined(CONFIG_PPC_BOOK3E)
235 "  u    dump segment table or SLB\n"
236 #elif defined(CONFIG_PPC_STD_MMU_32)
237 "  u    dump segment registers\n"
238 #elif defined(CONFIG_44x) || defined(CONFIG_PPC_BOOK3E)
239 "  u    dump TLB\n"
240 #endif
241 "  ?    help\n"
242 "  zr   reboot\n\
243   zh    halt\n"
244 ;
245
246 static struct pt_regs *xmon_regs;
247
248 static inline void sync(void)
249 {
250         asm volatile("sync; isync");
251 }
252
253 static inline void store_inst(void *p)
254 {
255         asm volatile ("dcbst 0,%0; sync; icbi 0,%0; isync" : : "r" (p));
256 }
257
258 static inline void cflush(void *p)
259 {
260         asm volatile ("dcbf 0,%0; icbi 0,%0" : : "r" (p));
261 }
262
263 static inline void cinval(void *p)
264 {
265         asm volatile ("dcbi 0,%0; icbi 0,%0" : : "r" (p));
266 }
267
268 /*
269  * Disable surveillance (the service processor watchdog function)
270  * while we are in xmon.
271  * XXX we should re-enable it when we leave. :)
272  */
273 #define SURVEILLANCE_TOKEN      9000
274
275 static inline void disable_surveillance(void)
276 {
277 #ifdef CONFIG_PPC_PSERIES
278         /* Since this can't be a module, args should end up below 4GB. */
279         static struct rtas_args args;
280
281         /*
282          * At this point we have got all the cpus we can into
283          * xmon, so there is hopefully no other cpu calling RTAS
284          * at the moment, even though we don't take rtas.lock.
285          * If we did try to take rtas.lock there would be a
286          * real possibility of deadlock.
287          */
288         args.token = rtas_token("set-indicator");
289         if (args.token == RTAS_UNKNOWN_SERVICE)
290                 return;
291         args.nargs = 3;
292         args.nret = 1;
293         args.rets = &args.args[3];
294         args.args[0] = SURVEILLANCE_TOKEN;
295         args.args[1] = 0;
296         args.args[2] = 0;
297         enter_rtas(__pa(&args));
298 #endif /* CONFIG_PPC_PSERIES */
299 }
300
301 #ifdef CONFIG_SMP
302 static int xmon_speaker;
303
304 static void get_output_lock(void)
305 {
306         int me = smp_processor_id() + 0x100;
307         int last_speaker = 0, prev;
308         long timeout;
309
310         if (xmon_speaker == me)
311                 return;
312         for (;;) {
313                 if (xmon_speaker == 0) {
314                         last_speaker = cmpxchg(&xmon_speaker, 0, me);
315                         if (last_speaker == 0)
316                                 return;
317                 }
318                 timeout = 10000000;
319                 while (xmon_speaker == last_speaker) {
320                         if (--timeout > 0)
321                                 continue;
322                         /* hostile takeover */
323                         prev = cmpxchg(&xmon_speaker, last_speaker, me);
324                         if (prev == last_speaker)
325                                 return;
326                         break;
327                 }
328         }
329 }
330
331 static void release_output_lock(void)
332 {
333         xmon_speaker = 0;
334 }
335
336 int cpus_are_in_xmon(void)
337 {
338         return !cpumask_empty(&cpus_in_xmon);
339 }
340 #endif
341
342 static inline int unrecoverable_excp(struct pt_regs *regs)
343 {
344 #if defined(CONFIG_4xx) || defined(CONFIG_PPC_BOOK3E)
345         /* We have no MSR_RI bit on 4xx or Book3e, so we simply return false */
346         return 0;
347 #else
348         return ((regs->msr & MSR_RI) == 0);
349 #endif
350 }
351
352 static int xmon_core(struct pt_regs *regs, int fromipi)
353 {
354         int cmd = 0;
355         struct bpt *bp;
356         long recurse_jmp[JMP_BUF_LEN];
357         unsigned long offset;
358         unsigned long flags;
359 #ifdef CONFIG_SMP
360         int cpu;
361         int secondary;
362         unsigned long timeout;
363 #endif
364
365         local_irq_save(flags);
366
367         bp = in_breakpoint_table(regs->nip, &offset);
368         if (bp != NULL) {
369                 regs->nip = bp->address + offset;
370                 atomic_dec(&bp->ref_count);
371         }
372
373         remove_cpu_bpts();
374
375 #ifdef CONFIG_SMP
376         cpu = smp_processor_id();
377         if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
378                 get_output_lock();
379                 excprint(regs);
380                 printf("cpu 0x%x: Exception %lx %s in xmon, "
381                        "returning to main loop\n",
382                        cpu, regs->trap, getvecname(TRAP(regs)));
383                 release_output_lock();
384                 longjmp(xmon_fault_jmp[cpu], 1);
385         }
386
387         if (setjmp(recurse_jmp) != 0) {
388                 if (!in_xmon || !xmon_gate) {
389                         get_output_lock();
390                         printf("xmon: WARNING: bad recursive fault "
391                                "on cpu 0x%x\n", cpu);
392                         release_output_lock();
393                         goto waiting;
394                 }
395                 secondary = !(xmon_taken && cpu == xmon_owner);
396                 goto cmdloop;
397         }
398
399         xmon_fault_jmp[cpu] = recurse_jmp;
400         cpumask_set_cpu(cpu, &cpus_in_xmon);
401
402         bp = NULL;
403         if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT))
404                 bp = at_breakpoint(regs->nip);
405         if (bp || unrecoverable_excp(regs))
406                 fromipi = 0;
407
408         if (!fromipi) {
409                 get_output_lock();
410                 excprint(regs);
411                 if (bp) {
412                         printf("cpu 0x%x stopped at breakpoint 0x%x (",
413                                cpu, BP_NUM(bp));
414                         xmon_print_symbol(regs->nip, " ", ")\n");
415                 }
416                 if (unrecoverable_excp(regs))
417                         printf("WARNING: exception is not recoverable, "
418                                "can't continue\n");
419                 release_output_lock();
420         }
421
422  waiting:
423         secondary = 1;
424         while (secondary && !xmon_gate) {
425                 if (in_xmon == 0) {
426                         if (fromipi)
427                                 goto leave;
428                         secondary = test_and_set_bit(0, &in_xmon);
429                 }
430                 barrier();
431         }
432
433         if (!secondary && !xmon_gate) {
434                 /* we are the first cpu to come in */
435                 /* interrupt other cpu(s) */
436                 int ncpus = num_online_cpus();
437
438                 xmon_owner = cpu;
439                 mb();
440                 if (ncpus > 1) {
441                         smp_send_debugger_break();
442                         /* wait for other cpus to come in */
443                         for (timeout = 100000000; timeout != 0; --timeout) {
444                                 if (cpumask_weight(&cpus_in_xmon) >= ncpus)
445                                         break;
446                                 barrier();
447                         }
448                 }
449                 remove_bpts();
450                 disable_surveillance();
451                 /* for breakpoint or single step, print the current instr. */
452                 if (bp || TRAP(regs) == 0xd00)
453                         ppc_inst_dump(regs->nip, 1, 0);
454                 printf("enter ? for help\n");
455                 mb();
456                 xmon_gate = 1;
457                 barrier();
458         }
459
460  cmdloop:
461         while (in_xmon) {
462                 if (secondary) {
463                         if (cpu == xmon_owner) {
464                                 if (!test_and_set_bit(0, &xmon_taken)) {
465                                         secondary = 0;
466                                         continue;
467                                 }
468                                 /* missed it */
469                                 while (cpu == xmon_owner)
470                                         barrier();
471                         }
472                         barrier();
473                 } else {
474                         cmd = cmds(regs);
475                         if (cmd != 0) {
476                                 /* exiting xmon */
477                                 insert_bpts();
478                                 xmon_gate = 0;
479                                 wmb();
480                                 in_xmon = 0;
481                                 break;
482                         }
483                         /* have switched to some other cpu */
484                         secondary = 1;
485                 }
486         }
487  leave:
488         cpumask_clear_cpu(cpu, &cpus_in_xmon);
489         xmon_fault_jmp[cpu] = NULL;
490 #else
491         /* UP is simple... */
492         if (in_xmon) {
493                 printf("Exception %lx %s in xmon, returning to main loop\n",
494                        regs->trap, getvecname(TRAP(regs)));
495                 longjmp(xmon_fault_jmp[0], 1);
496         }
497         if (setjmp(recurse_jmp) == 0) {
498                 xmon_fault_jmp[0] = recurse_jmp;
499                 in_xmon = 1;
500
501                 excprint(regs);
502                 bp = at_breakpoint(regs->nip);
503                 if (bp) {
504                         printf("Stopped at breakpoint %x (", BP_NUM(bp));
505                         xmon_print_symbol(regs->nip, " ", ")\n");
506                 }
507                 if (unrecoverable_excp(regs))
508                         printf("WARNING: exception is not recoverable, "
509                                "can't continue\n");
510                 remove_bpts();
511                 disable_surveillance();
512                 /* for breakpoint or single step, print the current instr. */
513                 if (bp || TRAP(regs) == 0xd00)
514                         ppc_inst_dump(regs->nip, 1, 0);
515                 printf("enter ? for help\n");
516         }
517
518         cmd = cmds(regs);
519
520         insert_bpts();
521         in_xmon = 0;
522 #endif
523
524 #ifdef CONFIG_BOOKE
525         if (regs->msr & MSR_DE) {
526                 bp = at_breakpoint(regs->nip);
527                 if (bp != NULL) {
528                         regs->nip = (unsigned long) &bp->instr[0];
529                         atomic_inc(&bp->ref_count);
530                 }
531         }
532 #else
533         if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
534                 bp = at_breakpoint(regs->nip);
535                 if (bp != NULL) {
536                         int stepped = emulate_step(regs, bp->instr[0]);
537                         if (stepped == 0) {
538                                 regs->nip = (unsigned long) &bp->instr[0];
539                                 atomic_inc(&bp->ref_count);
540                         } else if (stepped < 0) {
541                                 printf("Couldn't single-step %s instruction\n",
542                                     (IS_RFID(bp->instr[0])? "rfid": "mtmsrd"));
543                         }
544                 }
545         }
546 #endif
547         insert_cpu_bpts();
548
549         local_irq_restore(flags);
550
551         return cmd != 'X' && cmd != EOF;
552 }
553
554 int xmon(struct pt_regs *excp)
555 {
556         struct pt_regs regs;
557
558         if (excp == NULL) {
559                 ppc_save_regs(&regs);
560                 excp = &regs;
561         }
562
563         return xmon_core(excp, 0);
564 }
565 EXPORT_SYMBOL(xmon);
566
567 irqreturn_t xmon_irq(int irq, void *d)
568 {
569         unsigned long flags;
570         local_irq_save(flags);
571         printf("Keyboard interrupt\n");
572         xmon(get_irq_regs());
573         local_irq_restore(flags);
574         return IRQ_HANDLED;
575 }
576
577 static int xmon_bpt(struct pt_regs *regs)
578 {
579         struct bpt *bp;
580         unsigned long offset;
581
582         if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
583                 return 0;
584
585         /* Are we at the trap at bp->instr[1] for some bp? */
586         bp = in_breakpoint_table(regs->nip, &offset);
587         if (bp != NULL && offset == 4) {
588                 regs->nip = bp->address + 4;
589                 atomic_dec(&bp->ref_count);
590                 return 1;
591         }
592
593         /* Are we at a breakpoint? */
594         bp = at_breakpoint(regs->nip);
595         if (!bp)
596                 return 0;
597
598         xmon_core(regs, 0);
599
600         return 1;
601 }
602
603 static int xmon_sstep(struct pt_regs *regs)
604 {
605         if (user_mode(regs))
606                 return 0;
607         xmon_core(regs, 0);
608         return 1;
609 }
610
611 static int xmon_break_match(struct pt_regs *regs)
612 {
613         if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
614                 return 0;
615         if (dabr.enabled == 0)
616                 return 0;
617         xmon_core(regs, 0);
618         return 1;
619 }
620
621 static int xmon_iabr_match(struct pt_regs *regs)
622 {
623         if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
624                 return 0;
625         if (iabr == NULL)
626                 return 0;
627         xmon_core(regs, 0);
628         return 1;
629 }
630
631 static int xmon_ipi(struct pt_regs *regs)
632 {
633 #ifdef CONFIG_SMP
634         if (in_xmon && !cpumask_test_cpu(smp_processor_id(), &cpus_in_xmon))
635                 xmon_core(regs, 1);
636 #endif
637         return 0;
638 }
639
640 static int xmon_fault_handler(struct pt_regs *regs)
641 {
642         struct bpt *bp;
643         unsigned long offset;
644
645         if (in_xmon && catch_memory_errors)
646                 handle_fault(regs);     /* doesn't return */
647
648         if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
649                 bp = in_breakpoint_table(regs->nip, &offset);
650                 if (bp != NULL) {
651                         regs->nip = bp->address + offset;
652                         atomic_dec(&bp->ref_count);
653                 }
654         }
655
656         return 0;
657 }
658
659 static struct bpt *at_breakpoint(unsigned long pc)
660 {
661         int i;
662         struct bpt *bp;
663
664         bp = bpts;
665         for (i = 0; i < NBPTS; ++i, ++bp)
666                 if (bp->enabled && pc == bp->address)
667                         return bp;
668         return NULL;
669 }
670
671 static struct bpt *in_breakpoint_table(unsigned long nip, unsigned long *offp)
672 {
673         unsigned long off;
674
675         off = nip - (unsigned long) bpts;
676         if (off >= sizeof(bpts))
677                 return NULL;
678         off %= sizeof(struct bpt);
679         if (off != offsetof(struct bpt, instr[0])
680             && off != offsetof(struct bpt, instr[1]))
681                 return NULL;
682         *offp = off - offsetof(struct bpt, instr[0]);
683         return (struct bpt *) (nip - off);
684 }
685
686 static struct bpt *new_breakpoint(unsigned long a)
687 {
688         struct bpt *bp;
689
690         a &= ~3UL;
691         bp = at_breakpoint(a);
692         if (bp)
693                 return bp;
694
695         for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
696                 if (!bp->enabled && atomic_read(&bp->ref_count) == 0) {
697                         bp->address = a;
698                         bp->instr[1] = bpinstr;
699                         store_inst(&bp->instr[1]);
700                         return bp;
701                 }
702         }
703
704         printf("Sorry, no free breakpoints.  Please clear one first.\n");
705         return NULL;
706 }
707
708 static void insert_bpts(void)
709 {
710         int i;
711         struct bpt *bp;
712
713         bp = bpts;
714         for (i = 0; i < NBPTS; ++i, ++bp) {
715                 if ((bp->enabled & (BP_TRAP|BP_IABR)) == 0)
716                         continue;
717                 if (mread(bp->address, &bp->instr[0], 4) != 4) {
718                         printf("Couldn't read instruction at %lx, "
719                                "disabling breakpoint there\n", bp->address);
720                         bp->enabled = 0;
721                         continue;
722                 }
723                 if (IS_MTMSRD(bp->instr[0]) || IS_RFID(bp->instr[0])) {
724                         printf("Breakpoint at %lx is on an mtmsrd or rfid "
725                                "instruction, disabling it\n", bp->address);
726                         bp->enabled = 0;
727                         continue;
728                 }
729                 store_inst(&bp->instr[0]);
730                 if (bp->enabled & BP_IABR)
731                         continue;
732                 if (mwrite(bp->address, &bpinstr, 4) != 4) {
733                         printf("Couldn't write instruction at %lx, "
734                                "disabling breakpoint there\n", bp->address);
735                         bp->enabled &= ~BP_TRAP;
736                         continue;
737                 }
738                 store_inst((void *)bp->address);
739         }
740 }
741
742 static void insert_cpu_bpts(void)
743 {
744         struct arch_hw_breakpoint brk;
745
746         if (dabr.enabled) {
747                 brk.address = dabr.address;
748                 brk.type = (dabr.enabled & HW_BRK_TYPE_DABR) | HW_BRK_TYPE_PRIV_ALL;
749                 brk.len = 8;
750                 set_breakpoint(&brk);
751         }
752         if (iabr && cpu_has_feature(CPU_FTR_IABR))
753                 mtspr(SPRN_IABR, iabr->address
754                          | (iabr->enabled & (BP_IABR|BP_IABR_TE)));
755 }
756
757 static void remove_bpts(void)
758 {
759         int i;
760         struct bpt *bp;
761         unsigned instr;
762
763         bp = bpts;
764         for (i = 0; i < NBPTS; ++i, ++bp) {
765                 if ((bp->enabled & (BP_TRAP|BP_IABR)) != BP_TRAP)
766                         continue;
767                 if (mread(bp->address, &instr, 4) == 4
768                     && instr == bpinstr
769                     && mwrite(bp->address, &bp->instr, 4) != 4)
770                         printf("Couldn't remove breakpoint at %lx\n",
771                                bp->address);
772                 else
773                         store_inst((void *)bp->address);
774         }
775 }
776
777 static void remove_cpu_bpts(void)
778 {
779         hw_breakpoint_disable();
780         if (cpu_has_feature(CPU_FTR_IABR))
781                 mtspr(SPRN_IABR, 0);
782 }
783
784 /* Command interpreting routine */
785 static char *last_cmd;
786
787 static int
788 cmds(struct pt_regs *excp)
789 {
790         int cmd = 0;
791
792         last_cmd = NULL;
793         xmon_regs = excp;
794
795         if (!xmon_no_auto_backtrace) {
796                 xmon_no_auto_backtrace = 1;
797                 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
798         }
799
800         for(;;) {
801 #ifdef CONFIG_SMP
802                 printf("%x:", smp_processor_id());
803 #endif /* CONFIG_SMP */
804                 printf("mon> ");
805                 flush_input();
806                 termch = 0;
807                 cmd = skipbl();
808                 if( cmd == '\n' ) {
809                         if (last_cmd == NULL)
810                                 continue;
811                         take_input(last_cmd);
812                         last_cmd = NULL;
813                         cmd = inchar();
814                 }
815                 switch (cmd) {
816                 case 'm':
817                         cmd = inchar();
818                         switch (cmd) {
819                         case 'm':
820                         case 's':
821                         case 'd':
822                                 memops(cmd);
823                                 break;
824                         case 'l':
825                                 memlocate();
826                                 break;
827                         case 'z':
828                                 memzcan();
829                                 break;
830                         case 'i':
831                                 show_mem(0);
832                                 break;
833                         default:
834                                 termch = cmd;
835                                 memex();
836                         }
837                         break;
838                 case 'd':
839                         dump();
840                         break;
841                 case 'l':
842                         symbol_lookup();
843                         break;
844                 case 'r':
845                         prregs(excp);   /* print regs */
846                         break;
847                 case 'e':
848                         excprint(excp);
849                         break;
850                 case 'S':
851                         super_regs();
852                         break;
853                 case 't':
854                         backtrace(excp);
855                         break;
856                 case 'f':
857                         cacheflush();
858                         break;
859                 case 's':
860                         if (do_spu_cmd() == 0)
861                                 break;
862                         if (do_step(excp))
863                                 return cmd;
864                         break;
865                 case 'x':
866                 case 'X':
867                         return cmd;
868                 case EOF:
869                         printf(" <no input ...>\n");
870                         mdelay(2000);
871                         return cmd;
872                 case '?':
873                         xmon_puts(help_string);
874                         break;
875                 case 'b':
876                         bpt_cmds();
877                         break;
878                 case 'C':
879                         csum();
880                         break;
881                 case 'c':
882                         if (cpu_cmd())
883                                 return 0;
884                         break;
885                 case 'z':
886                         bootcmds();
887                         break;
888                 case 'p':
889                         proccall();
890                         break;
891 #ifdef CONFIG_PPC_STD_MMU
892                 case 'u':
893                         dump_segments();
894                         break;
895 #elif defined(CONFIG_4xx)
896                 case 'u':
897                         dump_tlb_44x();
898                         break;
899 #elif defined(CONFIG_PPC_BOOK3E)
900                 case 'u':
901                         dump_tlb_book3e();
902                         break;
903 #endif
904                 default:
905                         printf("Unrecognized command: ");
906                         do {
907                                 if (' ' < cmd && cmd <= '~')
908                                         putchar(cmd);
909                                 else
910                                         printf("\\x%x", cmd);
911                                 cmd = inchar();
912                         } while (cmd != '\n');
913                         printf(" (type ? for help)\n");
914                         break;
915                 }
916         }
917 }
918
919 #ifdef CONFIG_BOOKE
920 static int do_step(struct pt_regs *regs)
921 {
922         regs->msr |= MSR_DE;
923         mtspr(SPRN_DBCR0, mfspr(SPRN_DBCR0) | DBCR0_IC | DBCR0_IDM);
924         return 1;
925 }
926 #else
927 /*
928  * Step a single instruction.
929  * Some instructions we emulate, others we execute with MSR_SE set.
930  */
931 static int do_step(struct pt_regs *regs)
932 {
933         unsigned int instr;
934         int stepped;
935
936         /* check we are in 64-bit kernel mode, translation enabled */
937         if ((regs->msr & (MSR_64BIT|MSR_PR|MSR_IR)) == (MSR_64BIT|MSR_IR)) {
938                 if (mread(regs->nip, &instr, 4) == 4) {
939                         stepped = emulate_step(regs, instr);
940                         if (stepped < 0) {
941                                 printf("Couldn't single-step %s instruction\n",
942                                        (IS_RFID(instr)? "rfid": "mtmsrd"));
943                                 return 0;
944                         }
945                         if (stepped > 0) {
946                                 regs->trap = 0xd00 | (regs->trap & 1);
947                                 printf("stepped to ");
948                                 xmon_print_symbol(regs->nip, " ", "\n");
949                                 ppc_inst_dump(regs->nip, 1, 0);
950                                 return 0;
951                         }
952                 }
953         }
954         regs->msr |= MSR_SE;
955         return 1;
956 }
957 #endif
958
959 static void bootcmds(void)
960 {
961         int cmd;
962
963         cmd = inchar();
964         if (cmd == 'r')
965                 ppc_md.restart(NULL);
966         else if (cmd == 'h')
967                 ppc_md.halt();
968         else if (cmd == 'p')
969                 ppc_md.power_off();
970 }
971
972 static int cpu_cmd(void)
973 {
974 #ifdef CONFIG_SMP
975         unsigned long cpu, first_cpu, last_cpu;
976         int timeout;
977
978         if (!scanhex(&cpu)) {
979                 /* print cpus waiting or in xmon */
980                 printf("cpus stopped:");
981                 last_cpu = first_cpu = NR_CPUS;
982                 for_each_possible_cpu(cpu) {
983                         if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
984                                 if (cpu == last_cpu + 1) {
985                                         last_cpu = cpu;
986                                 } else {
987                                         if (last_cpu != first_cpu)
988                                                 printf("-%lx", last_cpu);
989                                         last_cpu = first_cpu = cpu;
990                                         printf(" %lx", cpu);
991                                 }
992                         }
993                 }
994                 if (last_cpu != first_cpu)
995                         printf("-%lx", last_cpu);
996                 printf("\n");
997                 return 0;
998         }
999         /* try to switch to cpu specified */
1000         if (!cpumask_test_cpu(cpu, &cpus_in_xmon)) {
1001                 printf("cpu 0x%x isn't in xmon\n", cpu);
1002                 return 0;
1003         }
1004         xmon_taken = 0;
1005         mb();
1006         xmon_owner = cpu;
1007         timeout = 10000000;
1008         while (!xmon_taken) {
1009                 if (--timeout == 0) {
1010                         if (test_and_set_bit(0, &xmon_taken))
1011                                 break;
1012                         /* take control back */
1013                         mb();
1014                         xmon_owner = smp_processor_id();
1015                         printf("cpu %u didn't take control\n", cpu);
1016                         return 0;
1017                 }
1018                 barrier();
1019         }
1020         return 1;
1021 #else
1022         return 0;
1023 #endif /* CONFIG_SMP */
1024 }
1025
1026 static unsigned short fcstab[256] = {
1027         0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
1028         0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
1029         0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
1030         0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
1031         0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
1032         0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
1033         0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
1034         0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
1035         0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
1036         0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
1037         0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
1038         0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
1039         0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
1040         0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
1041         0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
1042         0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
1043         0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
1044         0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
1045         0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
1046         0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
1047         0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
1048         0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
1049         0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
1050         0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
1051         0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
1052         0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
1053         0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
1054         0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
1055         0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
1056         0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
1057         0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
1058         0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
1059 };
1060
1061 #define FCS(fcs, c)     (((fcs) >> 8) ^ fcstab[((fcs) ^ (c)) & 0xff])
1062
1063 static void
1064 csum(void)
1065 {
1066         unsigned int i;
1067         unsigned short fcs;
1068         unsigned char v;
1069
1070         if (!scanhex(&adrs))
1071                 return;
1072         if (!scanhex(&ncsum))
1073                 return;
1074         fcs = 0xffff;
1075         for (i = 0; i < ncsum; ++i) {
1076                 if (mread(adrs+i, &v, 1) == 0) {
1077                         printf("csum stopped at %x\n", adrs+i);
1078                         break;
1079                 }
1080                 fcs = FCS(fcs, v);
1081         }
1082         printf("%x\n", fcs);
1083 }
1084
1085 /*
1086  * Check if this is a suitable place to put a breakpoint.
1087  */
1088 static long check_bp_loc(unsigned long addr)
1089 {
1090         unsigned int instr;
1091
1092         addr &= ~3;
1093         if (!is_kernel_addr(addr)) {
1094                 printf("Breakpoints may only be placed at kernel addresses\n");
1095                 return 0;
1096         }
1097         if (!mread(addr, &instr, sizeof(instr))) {
1098                 printf("Can't read instruction at address %lx\n", addr);
1099                 return 0;
1100         }
1101         if (IS_MTMSRD(instr) || IS_RFID(instr)) {
1102                 printf("Breakpoints may not be placed on mtmsrd or rfid "
1103                        "instructions\n");
1104                 return 0;
1105         }
1106         return 1;
1107 }
1108
1109 static char *breakpoint_help_string =
1110     "Breakpoint command usage:\n"
1111     "b                show breakpoints\n"
1112     "b <addr> [cnt]   set breakpoint at given instr addr\n"
1113     "bc               clear all breakpoints\n"
1114     "bc <n/addr>      clear breakpoint number n or at addr\n"
1115     "bi <addr> [cnt]  set hardware instr breakpoint (POWER3/RS64 only)\n"
1116     "bd <addr> [cnt]  set hardware data breakpoint\n"
1117     "";
1118
1119 static void
1120 bpt_cmds(void)
1121 {
1122         int cmd;
1123         unsigned long a;
1124         int mode, i;
1125         struct bpt *bp;
1126         const char badaddr[] = "Only kernel addresses are permitted "
1127                 "for breakpoints\n";
1128
1129         cmd = inchar();
1130         switch (cmd) {
1131 #ifndef CONFIG_8xx
1132         case 'd':       /* bd - hardware data breakpoint */
1133                 mode = 7;
1134                 cmd = inchar();
1135                 if (cmd == 'r')
1136                         mode = 5;
1137                 else if (cmd == 'w')
1138                         mode = 6;
1139                 else
1140                         termch = cmd;
1141                 dabr.address = 0;
1142                 dabr.enabled = 0;
1143                 if (scanhex(&dabr.address)) {
1144                         if (!is_kernel_addr(dabr.address)) {
1145                                 printf(badaddr);
1146                                 break;
1147                         }
1148                         dabr.address &= ~HW_BRK_TYPE_DABR;
1149                         dabr.enabled = mode | BP_DABR;
1150                 }
1151                 break;
1152
1153         case 'i':       /* bi - hardware instr breakpoint */
1154                 if (!cpu_has_feature(CPU_FTR_IABR)) {
1155                         printf("Hardware instruction breakpoint "
1156                                "not supported on this cpu\n");
1157                         break;
1158                 }
1159                 if (iabr) {
1160                         iabr->enabled &= ~(BP_IABR | BP_IABR_TE);
1161                         iabr = NULL;
1162                 }
1163                 if (!scanhex(&a))
1164                         break;
1165                 if (!check_bp_loc(a))
1166                         break;
1167                 bp = new_breakpoint(a);
1168                 if (bp != NULL) {
1169                         bp->enabled |= BP_IABR | BP_IABR_TE;
1170                         iabr = bp;
1171                 }
1172                 break;
1173 #endif
1174
1175         case 'c':
1176                 if (!scanhex(&a)) {
1177                         /* clear all breakpoints */
1178                         for (i = 0; i < NBPTS; ++i)
1179                                 bpts[i].enabled = 0;
1180                         iabr = NULL;
1181                         dabr.enabled = 0;
1182                         printf("All breakpoints cleared\n");
1183                         break;
1184                 }
1185
1186                 if (a <= NBPTS && a >= 1) {
1187                         /* assume a breakpoint number */
1188                         bp = &bpts[a-1];        /* bp nums are 1 based */
1189                 } else {
1190                         /* assume a breakpoint address */
1191                         bp = at_breakpoint(a);
1192                         if (bp == NULL) {
1193                                 printf("No breakpoint at %x\n", a);
1194                                 break;
1195                         }
1196                 }
1197
1198                 printf("Cleared breakpoint %x (", BP_NUM(bp));
1199                 xmon_print_symbol(bp->address, " ", ")\n");
1200                 bp->enabled = 0;
1201                 break;
1202
1203         default:
1204                 termch = cmd;
1205                 cmd = skipbl();
1206                 if (cmd == '?') {
1207                         printf(breakpoint_help_string);
1208                         break;
1209                 }
1210                 termch = cmd;
1211                 if (!scanhex(&a)) {
1212                         /* print all breakpoints */
1213                         printf("   type            address\n");
1214                         if (dabr.enabled) {
1215                                 printf("   data   "REG"  [", dabr.address);
1216                                 if (dabr.enabled & 1)
1217                                         printf("r");
1218                                 if (dabr.enabled & 2)
1219                                         printf("w");
1220                                 printf("]\n");
1221                         }
1222                         for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
1223                                 if (!bp->enabled)
1224                                         continue;
1225                                 printf("%2x %s   ", BP_NUM(bp),
1226                                     (bp->enabled & BP_IABR)? "inst": "trap");
1227                                 xmon_print_symbol(bp->address, "  ", "\n");
1228                         }
1229                         break;
1230                 }
1231
1232                 if (!check_bp_loc(a))
1233                         break;
1234                 bp = new_breakpoint(a);
1235                 if (bp != NULL)
1236                         bp->enabled |= BP_TRAP;
1237                 break;
1238         }
1239 }
1240
1241 /* Very cheap human name for vector lookup. */
1242 static
1243 const char *getvecname(unsigned long vec)
1244 {
1245         char *ret;
1246
1247         switch (vec) {
1248         case 0x100:     ret = "(System Reset)"; break;
1249         case 0x200:     ret = "(Machine Check)"; break;
1250         case 0x300:     ret = "(Data Access)"; break;
1251         case 0x380:     ret = "(Data SLB Access)"; break;
1252         case 0x400:     ret = "(Instruction Access)"; break;
1253         case 0x480:     ret = "(Instruction SLB Access)"; break;
1254         case 0x500:     ret = "(Hardware Interrupt)"; break;
1255         case 0x600:     ret = "(Alignment)"; break;
1256         case 0x700:     ret = "(Program Check)"; break;
1257         case 0x800:     ret = "(FPU Unavailable)"; break;
1258         case 0x900:     ret = "(Decrementer)"; break;
1259         case 0x980:     ret = "(Hypervisor Decrementer)"; break;
1260         case 0xa00:     ret = "(Doorbell)"; break;
1261         case 0xc00:     ret = "(System Call)"; break;
1262         case 0xd00:     ret = "(Single Step)"; break;
1263         case 0xe40:     ret = "(Emulation Assist)"; break;
1264         case 0xe60:     ret = "(HMI)"; break;
1265         case 0xe80:     ret = "(Hypervisor Doorbell)"; break;
1266         case 0xf00:     ret = "(Performance Monitor)"; break;
1267         case 0xf20:     ret = "(Altivec Unavailable)"; break;
1268         case 0x1300:    ret = "(Instruction Breakpoint)"; break;
1269         case 0x1500:    ret = "(Denormalisation)"; break;
1270         case 0x1700:    ret = "(Altivec Assist)"; break;
1271         default: ret = "";
1272         }
1273         return ret;
1274 }
1275
1276 static void get_function_bounds(unsigned long pc, unsigned long *startp,
1277                                 unsigned long *endp)
1278 {
1279         unsigned long size, offset;
1280         const char *name;
1281
1282         *startp = *endp = 0;
1283         if (pc == 0)
1284                 return;
1285         if (setjmp(bus_error_jmp) == 0) {
1286                 catch_memory_errors = 1;
1287                 sync();
1288                 name = kallsyms_lookup(pc, &size, &offset, NULL, tmpstr);
1289                 if (name != NULL) {
1290                         *startp = pc - offset;
1291                         *endp = pc - offset + size;
1292                 }
1293                 sync();
1294         }
1295         catch_memory_errors = 0;
1296 }
1297
1298 #define LRSAVE_OFFSET           (STACK_FRAME_LR_SAVE * sizeof(unsigned long))
1299 #define MARKER_OFFSET           (STACK_FRAME_MARKER * sizeof(unsigned long))
1300
1301 static void xmon_show_stack(unsigned long sp, unsigned long lr,
1302                             unsigned long pc)
1303 {
1304         int max_to_print = 64;
1305         unsigned long ip;
1306         unsigned long newsp;
1307         unsigned long marker;
1308         struct pt_regs regs;
1309
1310         while (max_to_print--) {
1311                 if (sp < PAGE_OFFSET) {
1312                         if (sp != 0)
1313                                 printf("SP (%lx) is in userspace\n", sp);
1314                         break;
1315                 }
1316
1317                 if (!mread(sp + LRSAVE_OFFSET, &ip, sizeof(unsigned long))
1318                     || !mread(sp, &newsp, sizeof(unsigned long))) {
1319                         printf("Couldn't read stack frame at %lx\n", sp);
1320                         break;
1321                 }
1322
1323                 /*
1324                  * For the first stack frame, try to work out if
1325                  * LR and/or the saved LR value in the bottommost
1326                  * stack frame are valid.
1327                  */
1328                 if ((pc | lr) != 0) {
1329                         unsigned long fnstart, fnend;
1330                         unsigned long nextip;
1331                         int printip = 1;
1332
1333                         get_function_bounds(pc, &fnstart, &fnend);
1334                         nextip = 0;
1335                         if (newsp > sp)
1336                                 mread(newsp + LRSAVE_OFFSET, &nextip,
1337                                       sizeof(unsigned long));
1338                         if (lr == ip) {
1339                                 if (lr < PAGE_OFFSET
1340                                     || (fnstart <= lr && lr < fnend))
1341                                         printip = 0;
1342                         } else if (lr == nextip) {
1343                                 printip = 0;
1344                         } else if (lr >= PAGE_OFFSET
1345                                    && !(fnstart <= lr && lr < fnend)) {
1346                                 printf("[link register   ] ");
1347                                 xmon_print_symbol(lr, " ", "\n");
1348                         }
1349                         if (printip) {
1350                                 printf("["REG"] ", sp);
1351                                 xmon_print_symbol(ip, " ", " (unreliable)\n");
1352                         }
1353                         pc = lr = 0;
1354
1355                 } else {
1356                         printf("["REG"] ", sp);
1357                         xmon_print_symbol(ip, " ", "\n");
1358                 }
1359
1360                 /* Look for "regshere" marker to see if this is
1361                    an exception frame. */
1362                 if (mread(sp + MARKER_OFFSET, &marker, sizeof(unsigned long))
1363                     && marker == STACK_FRAME_REGS_MARKER) {
1364                         if (mread(sp + STACK_FRAME_OVERHEAD, &regs, sizeof(regs))
1365                             != sizeof(regs)) {
1366                                 printf("Couldn't read registers at %lx\n",
1367                                        sp + STACK_FRAME_OVERHEAD);
1368                                 break;
1369                         }
1370                         printf("--- Exception: %lx %s at ", regs.trap,
1371                                getvecname(TRAP(&regs)));
1372                         pc = regs.nip;
1373                         lr = regs.link;
1374                         xmon_print_symbol(pc, " ", "\n");
1375                 }
1376
1377                 if (newsp == 0)
1378                         break;
1379
1380                 sp = newsp;
1381         }
1382 }
1383
1384 static void backtrace(struct pt_regs *excp)
1385 {
1386         unsigned long sp;
1387
1388         if (scanhex(&sp))
1389                 xmon_show_stack(sp, 0, 0);
1390         else
1391                 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
1392         scannl();
1393 }
1394
1395 static void print_bug_trap(struct pt_regs *regs)
1396 {
1397 #ifdef CONFIG_BUG
1398         const struct bug_entry *bug;
1399         unsigned long addr;
1400
1401         if (regs->msr & MSR_PR)
1402                 return;         /* not in kernel */
1403         addr = regs->nip;       /* address of trap instruction */
1404         if (addr < PAGE_OFFSET)
1405                 return;
1406         bug = find_bug(regs->nip);
1407         if (bug == NULL)
1408                 return;
1409         if (is_warning_bug(bug))
1410                 return;
1411
1412 #ifdef CONFIG_DEBUG_BUGVERBOSE
1413         printf("kernel BUG at %s:%u!\n",
1414                bug->file, bug->line);
1415 #else
1416         printf("kernel BUG at %p!\n", (void *)bug->bug_addr);
1417 #endif
1418 #endif /* CONFIG_BUG */
1419 }
1420
1421 static void excprint(struct pt_regs *fp)
1422 {
1423         unsigned long trap;
1424
1425 #ifdef CONFIG_SMP
1426         printf("cpu 0x%x: ", smp_processor_id());
1427 #endif /* CONFIG_SMP */
1428
1429         trap = TRAP(fp);
1430         printf("Vector: %lx %s at [%lx]\n", fp->trap, getvecname(trap), fp);
1431         printf("    pc: ");
1432         xmon_print_symbol(fp->nip, ": ", "\n");
1433
1434         printf("    lr: ", fp->link);
1435         xmon_print_symbol(fp->link, ": ", "\n");
1436
1437         printf("    sp: %lx\n", fp->gpr[1]);
1438         printf("   msr: %lx\n", fp->msr);
1439
1440         if (trap == 0x300 || trap == 0x380 || trap == 0x600 || trap == 0x200) {
1441                 printf("   dar: %lx\n", fp->dar);
1442                 if (trap != 0x380)
1443                         printf(" dsisr: %lx\n", fp->dsisr);
1444         }
1445
1446         printf("  current = 0x%lx\n", current);
1447 #ifdef CONFIG_PPC64
1448         printf("  paca    = 0x%lx\t softe: %d\t irq_happened: 0x%02x\n",
1449                local_paca, local_paca->soft_enabled, local_paca->irq_happened);
1450 #endif
1451         if (current) {
1452                 printf("    pid   = %ld, comm = %s\n",
1453                        current->pid, current->comm);
1454         }
1455
1456         if (trap == 0x700)
1457                 print_bug_trap(fp);
1458 }
1459
1460 static void prregs(struct pt_regs *fp)
1461 {
1462         int n, trap;
1463         unsigned long base;
1464         struct pt_regs regs;
1465
1466         if (scanhex(&base)) {
1467                 if (setjmp(bus_error_jmp) == 0) {
1468                         catch_memory_errors = 1;
1469                         sync();
1470                         regs = *(struct pt_regs *)base;
1471                         sync();
1472                         __delay(200);
1473                 } else {
1474                         catch_memory_errors = 0;
1475                         printf("*** Error reading registers from "REG"\n",
1476                                base);
1477                         return;
1478                 }
1479                 catch_memory_errors = 0;
1480                 fp = &regs;
1481         }
1482
1483 #ifdef CONFIG_PPC64
1484         if (FULL_REGS(fp)) {
1485                 for (n = 0; n < 16; ++n)
1486                         printf("R%.2ld = "REG"   R%.2ld = "REG"\n",
1487                                n, fp->gpr[n], n+16, fp->gpr[n+16]);
1488         } else {
1489                 for (n = 0; n < 7; ++n)
1490                         printf("R%.2ld = "REG"   R%.2ld = "REG"\n",
1491                                n, fp->gpr[n], n+7, fp->gpr[n+7]);
1492         }
1493 #else
1494         for (n = 0; n < 32; ++n) {
1495                 printf("R%.2d = %.8x%s", n, fp->gpr[n],
1496                        (n & 3) == 3? "\n": "   ");
1497                 if (n == 12 && !FULL_REGS(fp)) {
1498                         printf("\n");
1499                         break;
1500                 }
1501         }
1502 #endif
1503         printf("pc  = ");
1504         xmon_print_symbol(fp->nip, " ", "\n");
1505         if (TRAP(fp) != 0xc00 && cpu_has_feature(CPU_FTR_CFAR)) {
1506                 printf("cfar= ");
1507                 xmon_print_symbol(fp->orig_gpr3, " ", "\n");
1508         }
1509         printf("lr  = ");
1510         xmon_print_symbol(fp->link, " ", "\n");
1511         printf("msr = "REG"   cr  = %.8lx\n", fp->msr, fp->ccr);
1512         printf("ctr = "REG"   xer = "REG"   trap = %4lx\n",
1513                fp->ctr, fp->xer, fp->trap);
1514         trap = TRAP(fp);
1515         if (trap == 0x300 || trap == 0x380 || trap == 0x600)
1516                 printf("dar = "REG"   dsisr = %.8lx\n", fp->dar, fp->dsisr);
1517 }
1518
1519 static void cacheflush(void)
1520 {
1521         int cmd;
1522         unsigned long nflush;
1523
1524         cmd = inchar();
1525         if (cmd != 'i')
1526                 termch = cmd;
1527         scanhex((void *)&adrs);
1528         if (termch != '\n')
1529                 termch = 0;
1530         nflush = 1;
1531         scanhex(&nflush);
1532         nflush = (nflush + L1_CACHE_BYTES - 1) / L1_CACHE_BYTES;
1533         if (setjmp(bus_error_jmp) == 0) {
1534                 catch_memory_errors = 1;
1535                 sync();
1536
1537                 if (cmd != 'i') {
1538                         for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1539                                 cflush((void *) adrs);
1540                 } else {
1541                         for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1542                                 cinval((void *) adrs);
1543                 }
1544                 sync();
1545                 /* wait a little while to see if we get a machine check */
1546                 __delay(200);
1547         }
1548         catch_memory_errors = 0;
1549 }
1550
1551 static unsigned long
1552 read_spr(int n)
1553 {
1554         unsigned int instrs[2];
1555         unsigned long (*code)(void);
1556         unsigned long ret = -1UL;
1557 #ifdef CONFIG_PPC64
1558         unsigned long opd[3];
1559
1560         opd[0] = (unsigned long)instrs;
1561         opd[1] = 0;
1562         opd[2] = 0;
1563         code = (unsigned long (*)(void)) opd;
1564 #else
1565         code = (unsigned long (*)(void)) instrs;
1566 #endif
1567
1568         /* mfspr r3,n; blr */
1569         instrs[0] = 0x7c6002a6 + ((n & 0x1F) << 16) + ((n & 0x3e0) << 6);
1570         instrs[1] = 0x4e800020;
1571         store_inst(instrs);
1572         store_inst(instrs+1);
1573
1574         if (setjmp(bus_error_jmp) == 0) {
1575                 catch_memory_errors = 1;
1576                 sync();
1577
1578                 ret = code();
1579
1580                 sync();
1581                 /* wait a little while to see if we get a machine check */
1582                 __delay(200);
1583                 n = size;
1584         }
1585
1586         return ret;
1587 }
1588
1589 static void
1590 write_spr(int n, unsigned long val)
1591 {
1592         unsigned int instrs[2];
1593         unsigned long (*code)(unsigned long);
1594 #ifdef CONFIG_PPC64
1595         unsigned long opd[3];
1596
1597         opd[0] = (unsigned long)instrs;
1598         opd[1] = 0;
1599         opd[2] = 0;
1600         code = (unsigned long (*)(unsigned long)) opd;
1601 #else
1602         code = (unsigned long (*)(unsigned long)) instrs;
1603 #endif
1604
1605         instrs[0] = 0x7c6003a6 + ((n & 0x1F) << 16) + ((n & 0x3e0) << 6);
1606         instrs[1] = 0x4e800020;
1607         store_inst(instrs);
1608         store_inst(instrs+1);
1609
1610         if (setjmp(bus_error_jmp) == 0) {
1611                 catch_memory_errors = 1;
1612                 sync();
1613
1614                 code(val);
1615
1616                 sync();
1617                 /* wait a little while to see if we get a machine check */
1618                 __delay(200);
1619                 n = size;
1620         }
1621 }
1622
1623 static unsigned long regno;
1624 extern char exc_prolog;
1625 extern char dec_exc;
1626
1627 static void super_regs(void)
1628 {
1629         int cmd;
1630         unsigned long val;
1631
1632         cmd = skipbl();
1633         if (cmd == '\n') {
1634                 unsigned long sp, toc;
1635                 asm("mr %0,1" : "=r" (sp) :);
1636                 asm("mr %0,2" : "=r" (toc) :);
1637
1638                 printf("msr  = "REG"  sprg0= "REG"\n",
1639                        mfmsr(), mfspr(SPRN_SPRG0));
1640                 printf("pvr  = "REG"  sprg1= "REG"\n",
1641                        mfspr(SPRN_PVR), mfspr(SPRN_SPRG1));
1642                 printf("dec  = "REG"  sprg2= "REG"\n",
1643                        mfspr(SPRN_DEC), mfspr(SPRN_SPRG2));
1644                 printf("sp   = "REG"  sprg3= "REG"\n", sp, mfspr(SPRN_SPRG3));
1645                 printf("toc  = "REG"  dar  = "REG"\n", toc, mfspr(SPRN_DAR));
1646
1647                 return;
1648         }
1649
1650         scanhex(&regno);
1651         switch (cmd) {
1652         case 'w':
1653                 val = read_spr(regno);
1654                 scanhex(&val);
1655                 write_spr(regno, val);
1656                 /* fall through */
1657         case 'r':
1658                 printf("spr %lx = %lx\n", regno, read_spr(regno));
1659                 break;
1660         }
1661         scannl();
1662 }
1663
1664 /*
1665  * Stuff for reading and writing memory safely
1666  */
1667 static int
1668 mread(unsigned long adrs, void *buf, int size)
1669 {
1670         volatile int n;
1671         char *p, *q;
1672
1673         n = 0;
1674         if (setjmp(bus_error_jmp) == 0) {
1675                 catch_memory_errors = 1;
1676                 sync();
1677                 p = (char *)adrs;
1678                 q = (char *)buf;
1679                 switch (size) {
1680                 case 2:
1681                         *(u16 *)q = *(u16 *)p;
1682                         break;
1683                 case 4:
1684                         *(u32 *)q = *(u32 *)p;
1685                         break;
1686                 case 8:
1687                         *(u64 *)q = *(u64 *)p;
1688                         break;
1689                 default:
1690                         for( ; n < size; ++n) {
1691                                 *q++ = *p++;
1692                                 sync();
1693                         }
1694                 }
1695                 sync();
1696                 /* wait a little while to see if we get a machine check */
1697                 __delay(200);
1698                 n = size;
1699         }
1700         catch_memory_errors = 0;
1701         return n;
1702 }
1703
1704 static int
1705 mwrite(unsigned long adrs, void *buf, int size)
1706 {
1707         volatile int n;
1708         char *p, *q;
1709
1710         n = 0;
1711         if (setjmp(bus_error_jmp) == 0) {
1712                 catch_memory_errors = 1;
1713                 sync();
1714                 p = (char *) adrs;
1715                 q = (char *) buf;
1716                 switch (size) {
1717                 case 2:
1718                         *(u16 *)p = *(u16 *)q;
1719                         break;
1720                 case 4:
1721                         *(u32 *)p = *(u32 *)q;
1722                         break;
1723                 case 8:
1724                         *(u64 *)p = *(u64 *)q;
1725                         break;
1726                 default:
1727                         for ( ; n < size; ++n) {
1728                                 *p++ = *q++;
1729                                 sync();
1730                         }
1731                 }
1732                 sync();
1733                 /* wait a little while to see if we get a machine check */
1734                 __delay(200);
1735                 n = size;
1736         } else {
1737                 printf("*** Error writing address %x\n", adrs + n);
1738         }
1739         catch_memory_errors = 0;
1740         return n;
1741 }
1742
1743 static int fault_type;
1744 static int fault_except;
1745 static char *fault_chars[] = { "--", "**", "##" };
1746
1747 static int handle_fault(struct pt_regs *regs)
1748 {
1749         fault_except = TRAP(regs);
1750         switch (TRAP(regs)) {
1751         case 0x200:
1752                 fault_type = 0;
1753                 break;
1754         case 0x300:
1755         case 0x380:
1756                 fault_type = 1;
1757                 break;
1758         default:
1759                 fault_type = 2;
1760         }
1761
1762         longjmp(bus_error_jmp, 1);
1763
1764         return 0;
1765 }
1766
1767 #define SWAP(a, b, t)   ((t) = (a), (a) = (b), (b) = (t))
1768
1769 static void
1770 byterev(unsigned char *val, int size)
1771 {
1772         int t;
1773         
1774         switch (size) {
1775         case 2:
1776                 SWAP(val[0], val[1], t);
1777                 break;
1778         case 4:
1779                 SWAP(val[0], val[3], t);
1780                 SWAP(val[1], val[2], t);
1781                 break;
1782         case 8: /* is there really any use for this? */
1783                 SWAP(val[0], val[7], t);
1784                 SWAP(val[1], val[6], t);
1785                 SWAP(val[2], val[5], t);
1786                 SWAP(val[3], val[4], t);
1787                 break;
1788         }
1789 }
1790
1791 static int brev;
1792 static int mnoread;
1793
1794 static char *memex_help_string =
1795     "Memory examine command usage:\n"
1796     "m [addr] [flags] examine/change memory\n"
1797     "  addr is optional.  will start where left off.\n"
1798     "  flags may include chars from this set:\n"
1799     "    b   modify by bytes (default)\n"
1800     "    w   modify by words (2 byte)\n"
1801     "    l   modify by longs (4 byte)\n"
1802     "    d   modify by doubleword (8 byte)\n"
1803     "    r   toggle reverse byte order mode\n"
1804     "    n   do not read memory (for i/o spaces)\n"
1805     "    .   ok to read (default)\n"
1806     "NOTE: flags are saved as defaults\n"
1807     "";
1808
1809 static char *memex_subcmd_help_string =
1810     "Memory examine subcommands:\n"
1811     "  hexval   write this val to current location\n"
1812     "  'string' write chars from string to this location\n"
1813     "  '        increment address\n"
1814     "  ^        decrement address\n"
1815     "  /        increment addr by 0x10.  //=0x100, ///=0x1000, etc\n"
1816     "  \\        decrement addr by 0x10.  \\\\=0x100, \\\\\\=0x1000, etc\n"
1817     "  `        clear no-read flag\n"
1818     "  ;        stay at this addr\n"
1819     "  v        change to byte mode\n"
1820     "  w        change to word (2 byte) mode\n"
1821     "  l        change to long (4 byte) mode\n"
1822     "  u        change to doubleword (8 byte) mode\n"
1823     "  m addr   change current addr\n"
1824     "  n        toggle no-read flag\n"
1825     "  r        toggle byte reverse flag\n"
1826     "  < count  back up count bytes\n"
1827     "  > count  skip forward count bytes\n"
1828     "  x        exit this mode\n"
1829     "";
1830
1831 static void
1832 memex(void)
1833 {
1834         int cmd, inc, i, nslash;
1835         unsigned long n;
1836         unsigned char val[16];
1837
1838         scanhex((void *)&adrs);
1839         cmd = skipbl();
1840         if (cmd == '?') {
1841                 printf(memex_help_string);
1842                 return;
1843         } else {
1844                 termch = cmd;
1845         }
1846         last_cmd = "m\n";
1847         while ((cmd = skipbl()) != '\n') {
1848                 switch( cmd ){
1849                 case 'b':       size = 1;       break;
1850                 case 'w':       size = 2;       break;
1851                 case 'l':       size = 4;       break;
1852                 case 'd':       size = 8;       break;
1853                 case 'r':       brev = !brev;   break;
1854                 case 'n':       mnoread = 1;    break;
1855                 case '.':       mnoread = 0;    break;
1856                 }
1857         }
1858         if( size <= 0 )
1859                 size = 1;
1860         else if( size > 8 )
1861                 size = 8;
1862         for(;;){
1863                 if (!mnoread)
1864                         n = mread(adrs, val, size);
1865                 printf(REG"%c", adrs, brev? 'r': ' ');
1866                 if (!mnoread) {
1867                         if (brev)
1868                                 byterev(val, size);
1869                         putchar(' ');
1870                         for (i = 0; i < n; ++i)
1871                                 printf("%.2x", val[i]);
1872                         for (; i < size; ++i)
1873                                 printf("%s", fault_chars[fault_type]);
1874                 }
1875                 putchar(' ');
1876                 inc = size;
1877                 nslash = 0;
1878                 for(;;){
1879                         if( scanhex(&n) ){
1880                                 for (i = 0; i < size; ++i)
1881                                         val[i] = n >> (i * 8);
1882                                 if (!brev)
1883                                         byterev(val, size);
1884                                 mwrite(adrs, val, size);
1885                                 inc = size;
1886                         }
1887                         cmd = skipbl();
1888                         if (cmd == '\n')
1889                                 break;
1890                         inc = 0;
1891                         switch (cmd) {
1892                         case '\'':
1893                                 for(;;){
1894                                         n = inchar();
1895                                         if( n == '\\' )
1896                                                 n = bsesc();
1897                                         else if( n == '\'' )
1898                                                 break;
1899                                         for (i = 0; i < size; ++i)
1900                                                 val[i] = n >> (i * 8);
1901                                         if (!brev)
1902                                                 byterev(val, size);
1903                                         mwrite(adrs, val, size);
1904                                         adrs += size;
1905                                 }
1906                                 adrs -= size;
1907                                 inc = size;
1908                                 break;
1909                         case ',':
1910                                 adrs += size;
1911                                 break;
1912                         case '.':
1913                                 mnoread = 0;
1914                                 break;
1915                         case ';':
1916                                 break;
1917                         case 'x':
1918                         case EOF:
1919                                 scannl();
1920                                 return;
1921                         case 'b':
1922                         case 'v':
1923                                 size = 1;
1924                                 break;
1925                         case 'w':
1926                                 size = 2;
1927                                 break;
1928                         case 'l':
1929                                 size = 4;
1930                                 break;
1931                         case 'u':
1932                                 size = 8;
1933                                 break;
1934                         case '^':
1935                                 adrs -= size;
1936                                 break;
1937                                 break;
1938                         case '/':
1939                                 if (nslash > 0)
1940                                         adrs -= 1 << nslash;
1941                                 else
1942                                         nslash = 0;
1943                                 nslash += 4;
1944                                 adrs += 1 << nslash;
1945                                 break;
1946                         case '\\':
1947                                 if (nslash < 0)
1948                                         adrs += 1 << -nslash;
1949                                 else
1950                                         nslash = 0;
1951                                 nslash -= 4;
1952                                 adrs -= 1 << -nslash;
1953                                 break;
1954                         case 'm':
1955                                 scanhex((void *)&adrs);
1956                                 break;
1957                         case 'n':
1958                                 mnoread = 1;
1959                                 break;
1960                         case 'r':
1961                                 brev = !brev;
1962                                 break;
1963                         case '<':
1964                                 n = size;
1965                                 scanhex(&n);
1966                                 adrs -= n;
1967                                 break;
1968                         case '>':
1969                                 n = size;
1970                                 scanhex(&n);
1971                                 adrs += n;
1972                                 break;
1973                         case '?':
1974                                 printf(memex_subcmd_help_string);
1975                                 break;
1976                         }
1977                 }
1978                 adrs += inc;
1979         }
1980 }
1981
1982 static int
1983 bsesc(void)
1984 {
1985         int c;
1986
1987         c = inchar();
1988         switch( c ){
1989         case 'n':       c = '\n';       break;
1990         case 'r':       c = '\r';       break;
1991         case 'b':       c = '\b';       break;
1992         case 't':       c = '\t';       break;
1993         }
1994         return c;
1995 }
1996
1997 static void xmon_rawdump (unsigned long adrs, long ndump)
1998 {
1999         long n, m, r, nr;
2000         unsigned char temp[16];
2001
2002         for (n = ndump; n > 0;) {
2003                 r = n < 16? n: 16;
2004                 nr = mread(adrs, temp, r);
2005                 adrs += nr;
2006                 for (m = 0; m < r; ++m) {
2007                         if (m < nr)
2008                                 printf("%.2x", temp[m]);
2009                         else
2010                                 printf("%s", fault_chars[fault_type]);
2011                 }
2012                 n -= r;
2013                 if (nr < r)
2014                         break;
2015         }
2016         printf("\n");
2017 }
2018
2019 #ifdef CONFIG_PPC64
2020 static void dump_one_paca(int cpu)
2021 {
2022         struct paca_struct *p;
2023
2024         if (setjmp(bus_error_jmp) != 0) {
2025                 printf("*** Error dumping paca for cpu 0x%x!\n", cpu);
2026                 return;
2027         }
2028
2029         catch_memory_errors = 1;
2030         sync();
2031
2032         p = &paca[cpu];
2033
2034         printf("paca for cpu 0x%x @ %p:\n", cpu, p);
2035
2036         printf(" %-*s = %s\n", 16, "possible", cpu_possible(cpu) ? "yes" : "no");
2037         printf(" %-*s = %s\n", 16, "present", cpu_present(cpu) ? "yes" : "no");
2038         printf(" %-*s = %s\n", 16, "online", cpu_online(cpu) ? "yes" : "no");
2039
2040 #define DUMP(paca, name, format) \
2041         printf(" %-*s = %#-*"format"\t(0x%lx)\n", 16, #name, 18, paca->name, \
2042                 offsetof(struct paca_struct, name));
2043
2044         DUMP(p, lock_token, "x");
2045         DUMP(p, paca_index, "x");
2046         DUMP(p, kernel_toc, "lx");
2047         DUMP(p, kernelbase, "lx");
2048         DUMP(p, kernel_msr, "lx");
2049 #ifdef CONFIG_PPC_STD_MMU_64
2050         DUMP(p, stab_real, "lx");
2051         DUMP(p, stab_addr, "lx");
2052 #endif
2053         DUMP(p, emergency_sp, "p");
2054         DUMP(p, data_offset, "lx");
2055         DUMP(p, hw_cpu_id, "x");
2056         DUMP(p, cpu_start, "x");
2057         DUMP(p, kexec_state, "x");
2058         DUMP(p, __current, "p");
2059         DUMP(p, kstack, "lx");
2060         DUMP(p, stab_rr, "lx");
2061         DUMP(p, saved_r1, "lx");
2062         DUMP(p, trap_save, "x");
2063         DUMP(p, soft_enabled, "x");
2064         DUMP(p, irq_happened, "x");
2065         DUMP(p, io_sync, "x");
2066         DUMP(p, irq_work_pending, "x");
2067         DUMP(p, nap_state_lost, "x");
2068
2069 #undef DUMP
2070
2071         catch_memory_errors = 0;
2072         sync();
2073 }
2074
2075 static void dump_all_pacas(void)
2076 {
2077         int cpu;
2078
2079         if (num_possible_cpus() == 0) {
2080                 printf("No possible cpus, use 'dp #' to dump individual cpus\n");
2081                 return;
2082         }
2083
2084         for_each_possible_cpu(cpu)
2085                 dump_one_paca(cpu);
2086 }
2087
2088 static void dump_pacas(void)
2089 {
2090         unsigned long num;
2091         int c;
2092
2093         c = inchar();
2094         if (c == 'a') {
2095                 dump_all_pacas();
2096                 return;
2097         }
2098
2099         termch = c;     /* Put c back, it wasn't 'a' */
2100
2101         if (scanhex(&num))
2102                 dump_one_paca(num);
2103         else
2104                 dump_one_paca(xmon_owner);
2105 }
2106 #endif
2107
2108 #define isxdigit(c)     (('0' <= (c) && (c) <= '9') \
2109                          || ('a' <= (c) && (c) <= 'f') \
2110                          || ('A' <= (c) && (c) <= 'F'))
2111 static void
2112 dump(void)
2113 {
2114         int c;
2115
2116         c = inchar();
2117
2118 #ifdef CONFIG_PPC64
2119         if (c == 'p') {
2120                 dump_pacas();
2121                 return;
2122         }
2123 #endif
2124
2125         if ((isxdigit(c) && c != 'f' && c != 'd') || c == '\n')
2126                 termch = c;
2127         scanhex((void *)&adrs);
2128         if (termch != '\n')
2129                 termch = 0;
2130         if (c == 'i') {
2131                 scanhex(&nidump);
2132                 if (nidump == 0)
2133                         nidump = 16;
2134                 else if (nidump > MAX_DUMP)
2135                         nidump = MAX_DUMP;
2136                 adrs += ppc_inst_dump(adrs, nidump, 1);
2137                 last_cmd = "di\n";
2138         } else if (c == 'l') {
2139                 dump_log_buf();
2140         } else if (c == 'r') {
2141                 scanhex(&ndump);
2142                 if (ndump == 0)
2143                         ndump = 64;
2144                 xmon_rawdump(adrs, ndump);
2145                 adrs += ndump;
2146                 last_cmd = "dr\n";
2147         } else {
2148                 scanhex(&ndump);
2149                 if (ndump == 0)
2150                         ndump = 64;
2151                 else if (ndump > MAX_DUMP)
2152                         ndump = MAX_DUMP;
2153                 prdump(adrs, ndump);
2154                 adrs += ndump;
2155                 last_cmd = "d\n";
2156         }
2157 }
2158
2159 static void
2160 prdump(unsigned long adrs, long ndump)
2161 {
2162         long n, m, c, r, nr;
2163         unsigned char temp[16];
2164
2165         for (n = ndump; n > 0;) {
2166                 printf(REG, adrs);
2167                 putchar(' ');
2168                 r = n < 16? n: 16;
2169                 nr = mread(adrs, temp, r);
2170                 adrs += nr;
2171                 for (m = 0; m < r; ++m) {
2172                         if ((m & (sizeof(long) - 1)) == 0 && m > 0)
2173                                 putchar(' ');
2174                         if (m < nr)
2175                                 printf("%.2x", temp[m]);
2176                         else
2177                                 printf("%s", fault_chars[fault_type]);
2178                 }
2179                 for (; m < 16; ++m) {
2180                         if ((m & (sizeof(long) - 1)) == 0)
2181                                 putchar(' ');
2182                         printf("  ");
2183                 }
2184                 printf("  |");
2185                 for (m = 0; m < r; ++m) {
2186                         if (m < nr) {
2187                                 c = temp[m];
2188                                 putchar(' ' <= c && c <= '~'? c: '.');
2189                         } else
2190                                 putchar(' ');
2191                 }
2192                 n -= r;
2193                 for (; m < 16; ++m)
2194                         putchar(' ');
2195                 printf("|\n");
2196                 if (nr < r)
2197                         break;
2198         }
2199 }
2200
2201 typedef int (*instruction_dump_func)(unsigned long inst, unsigned long addr);
2202
2203 static int
2204 generic_inst_dump(unsigned long adr, long count, int praddr,
2205                         instruction_dump_func dump_func)
2206 {
2207         int nr, dotted;
2208         unsigned long first_adr;
2209         unsigned long inst, last_inst = 0;
2210         unsigned char val[4];
2211
2212         dotted = 0;
2213         for (first_adr = adr; count > 0; --count, adr += 4) {
2214                 nr = mread(adr, val, 4);
2215                 if (nr == 0) {
2216                         if (praddr) {
2217                                 const char *x = fault_chars[fault_type];
2218                                 printf(REG"  %s%s%s%s\n", adr, x, x, x, x);
2219                         }
2220                         break;
2221                 }
2222                 inst = GETWORD(val);
2223                 if (adr > first_adr && inst == last_inst) {
2224                         if (!dotted) {
2225                                 printf(" ...\n");
2226                                 dotted = 1;
2227                         }
2228                         continue;
2229                 }
2230                 dotted = 0;
2231                 last_inst = inst;
2232                 if (praddr)
2233                         printf(REG"  %.8x", adr, inst);
2234                 printf("\t");
2235                 dump_func(inst, adr);
2236                 printf("\n");
2237         }
2238         return adr - first_adr;
2239 }
2240
2241 static int
2242 ppc_inst_dump(unsigned long adr, long count, int praddr)
2243 {
2244         return generic_inst_dump(adr, count, praddr, print_insn_powerpc);
2245 }
2246
2247 void
2248 print_address(unsigned long addr)
2249 {
2250         xmon_print_symbol(addr, "\t# ", "");
2251 }
2252
2253 void
2254 dump_log_buf(void)
2255 {
2256         struct kmsg_dumper dumper = { .active = 1 };
2257         unsigned char buf[128];
2258         size_t len;
2259
2260         if (setjmp(bus_error_jmp) != 0) {
2261                 printf("Error dumping printk buffer!\n");
2262                 return;
2263         }
2264
2265         catch_memory_errors = 1;
2266         sync();
2267
2268         kmsg_dump_rewind_nolock(&dumper);
2269         while (kmsg_dump_get_line_nolock(&dumper, false, buf, sizeof(buf), &len)) {
2270                 buf[len] = '\0';
2271                 printf("%s", buf);
2272         }
2273
2274         sync();
2275         /* wait a little while to see if we get a machine check */
2276         __delay(200);
2277         catch_memory_errors = 0;
2278 }
2279
2280 /*
2281  * Memory operations - move, set, print differences
2282  */
2283 static unsigned long mdest;             /* destination address */
2284 static unsigned long msrc;              /* source address */
2285 static unsigned long mval;              /* byte value to set memory to */
2286 static unsigned long mcount;            /* # bytes to affect */
2287 static unsigned long mdiffs;            /* max # differences to print */
2288
2289 static void
2290 memops(int cmd)
2291 {
2292         scanhex((void *)&mdest);
2293         if( termch != '\n' )
2294                 termch = 0;
2295         scanhex((void *)(cmd == 's'? &mval: &msrc));
2296         if( termch != '\n' )
2297                 termch = 0;
2298         scanhex((void *)&mcount);
2299         switch( cmd ){
2300         case 'm':
2301                 memmove((void *)mdest, (void *)msrc, mcount);
2302                 break;
2303         case 's':
2304                 memset((void *)mdest, mval, mcount);
2305                 break;
2306         case 'd':
2307                 if( termch != '\n' )
2308                         termch = 0;
2309                 scanhex((void *)&mdiffs);
2310                 memdiffs((unsigned char *)mdest, (unsigned char *)msrc, mcount, mdiffs);
2311                 break;
2312         }
2313 }
2314
2315 static void
2316 memdiffs(unsigned char *p1, unsigned char *p2, unsigned nb, unsigned maxpr)
2317 {
2318         unsigned n, prt;
2319
2320         prt = 0;
2321         for( n = nb; n > 0; --n )
2322                 if( *p1++ != *p2++ )
2323                         if( ++prt <= maxpr )
2324                                 printf("%.16x %.2x # %.16x %.2x\n", p1 - 1,
2325                                         p1[-1], p2 - 1, p2[-1]);
2326         if( prt > maxpr )
2327                 printf("Total of %d differences\n", prt);
2328 }
2329
2330 static unsigned mend;
2331 static unsigned mask;
2332
2333 static void
2334 memlocate(void)
2335 {
2336         unsigned a, n;
2337         unsigned char val[4];
2338
2339         last_cmd = "ml";
2340         scanhex((void *)&mdest);
2341         if (termch != '\n') {
2342                 termch = 0;
2343                 scanhex((void *)&mend);
2344                 if (termch != '\n') {
2345                         termch = 0;
2346                         scanhex((void *)&mval);
2347                         mask = ~0;
2348                         if (termch != '\n') termch = 0;
2349                         scanhex((void *)&mask);
2350                 }
2351         }
2352         n = 0;
2353         for (a = mdest; a < mend; a += 4) {
2354                 if (mread(a, val, 4) == 4
2355                         && ((GETWORD(val) ^ mval) & mask) == 0) {
2356                         printf("%.16x:  %.16x\n", a, GETWORD(val));
2357                         if (++n >= 10)
2358                                 break;
2359                 }
2360         }
2361 }
2362
2363 static unsigned long mskip = 0x1000;
2364 static unsigned long mlim = 0xffffffff;
2365
2366 static void
2367 memzcan(void)
2368 {
2369         unsigned char v;
2370         unsigned a;
2371         int ok, ook;
2372
2373         scanhex(&mdest);
2374         if (termch != '\n') termch = 0;
2375         scanhex(&mskip);
2376         if (termch != '\n') termch = 0;
2377         scanhex(&mlim);
2378         ook = 0;
2379         for (a = mdest; a < mlim; a += mskip) {
2380                 ok = mread(a, &v, 1);
2381                 if (ok && !ook) {
2382                         printf("%.8x .. ", a);
2383                 } else if (!ok && ook)
2384                         printf("%.8x\n", a - mskip);
2385                 ook = ok;
2386                 if (a + mskip < a)
2387                         break;
2388         }
2389         if (ook)
2390                 printf("%.8x\n", a - mskip);
2391 }
2392
2393 static void proccall(void)
2394 {
2395         unsigned long args[8];
2396         unsigned long ret;
2397         int i;
2398         typedef unsigned long (*callfunc_t)(unsigned long, unsigned long,
2399                         unsigned long, unsigned long, unsigned long,
2400                         unsigned long, unsigned long, unsigned long);
2401         callfunc_t func;
2402
2403         if (!scanhex(&adrs))
2404                 return;
2405         if (termch != '\n')
2406                 termch = 0;
2407         for (i = 0; i < 8; ++i)
2408                 args[i] = 0;
2409         for (i = 0; i < 8; ++i) {
2410                 if (!scanhex(&args[i]) || termch == '\n')
2411                         break;
2412                 termch = 0;
2413         }
2414         func = (callfunc_t) adrs;
2415         ret = 0;
2416         if (setjmp(bus_error_jmp) == 0) {
2417                 catch_memory_errors = 1;
2418                 sync();
2419                 ret = func(args[0], args[1], args[2], args[3],
2420                            args[4], args[5], args[6], args[7]);
2421                 sync();
2422                 printf("return value is %x\n", ret);
2423         } else {
2424                 printf("*** %x exception occurred\n", fault_except);
2425         }
2426         catch_memory_errors = 0;
2427 }
2428
2429 /* Input scanning routines */
2430 int
2431 skipbl(void)
2432 {
2433         int c;
2434
2435         if( termch != 0 ){
2436                 c = termch;
2437                 termch = 0;
2438         } else
2439                 c = inchar();
2440         while( c == ' ' || c == '\t' )
2441                 c = inchar();
2442         return c;
2443 }
2444
2445 #define N_PTREGS        44
2446 static char *regnames[N_PTREGS] = {
2447         "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
2448         "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
2449         "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
2450         "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
2451         "pc", "msr", "or3", "ctr", "lr", "xer", "ccr",
2452 #ifdef CONFIG_PPC64
2453         "softe",
2454 #else
2455         "mq",
2456 #endif
2457         "trap", "dar", "dsisr", "res"
2458 };
2459
2460 int
2461 scanhex(unsigned long *vp)
2462 {
2463         int c, d;
2464         unsigned long v;
2465
2466         c = skipbl();
2467         if (c == '%') {
2468                 /* parse register name */
2469                 char regname[8];
2470                 int i;
2471
2472                 for (i = 0; i < sizeof(regname) - 1; ++i) {
2473                         c = inchar();
2474                         if (!isalnum(c)) {
2475                                 termch = c;
2476                                 break;
2477                         }
2478                         regname[i] = c;
2479                 }
2480                 regname[i] = 0;
2481                 for (i = 0; i < N_PTREGS; ++i) {
2482                         if (strcmp(regnames[i], regname) == 0) {
2483                                 if (xmon_regs == NULL) {
2484                                         printf("regs not available\n");
2485                                         return 0;
2486                                 }
2487                                 *vp = ((unsigned long *)xmon_regs)[i];
2488                                 return 1;
2489                         }
2490                 }
2491                 printf("invalid register name '%%%s'\n", regname);
2492                 return 0;
2493         }
2494
2495         /* skip leading "0x" if any */
2496
2497         if (c == '0') {
2498                 c = inchar();
2499                 if (c == 'x') {
2500                         c = inchar();
2501                 } else {
2502                         d = hexdigit(c);
2503                         if (d == EOF) {
2504                                 termch = c;
2505                                 *vp = 0;
2506                                 return 1;
2507                         }
2508                 }
2509         } else if (c == '$') {
2510                 int i;
2511                 for (i=0; i<63; i++) {
2512                         c = inchar();
2513                         if (isspace(c)) {
2514                                 termch = c;
2515                                 break;
2516                         }
2517                         tmpstr[i] = c;
2518                 }
2519                 tmpstr[i++] = 0;
2520                 *vp = 0;
2521                 if (setjmp(bus_error_jmp) == 0) {
2522                         catch_memory_errors = 1;
2523                         sync();
2524                         *vp = kallsyms_lookup_name(tmpstr);
2525                         sync();
2526                 }
2527                 catch_memory_errors = 0;
2528                 if (!(*vp)) {
2529                         printf("unknown symbol '%s'\n", tmpstr);
2530                         return 0;
2531                 }
2532                 return 1;
2533         }
2534
2535         d = hexdigit(c);
2536         if (d == EOF) {
2537                 termch = c;
2538                 return 0;
2539         }
2540         v = 0;
2541         do {
2542                 v = (v << 4) + d;
2543                 c = inchar();
2544                 d = hexdigit(c);
2545         } while (d != EOF);
2546         termch = c;
2547         *vp = v;
2548         return 1;
2549 }
2550
2551 static void
2552 scannl(void)
2553 {
2554         int c;
2555
2556         c = termch;
2557         termch = 0;
2558         while( c != '\n' )
2559                 c = inchar();
2560 }
2561
2562 static int hexdigit(int c)
2563 {
2564         if( '0' <= c && c <= '9' )
2565                 return c - '0';
2566         if( 'A' <= c && c <= 'F' )
2567                 return c - ('A' - 10);
2568         if( 'a' <= c && c <= 'f' )
2569                 return c - ('a' - 10);
2570         return EOF;
2571 }
2572
2573 void
2574 getstring(char *s, int size)
2575 {
2576         int c;
2577
2578         c = skipbl();
2579         do {
2580                 if( size > 1 ){
2581                         *s++ = c;
2582                         --size;
2583                 }
2584                 c = inchar();
2585         } while( c != ' ' && c != '\t' && c != '\n' );
2586         termch = c;
2587         *s = 0;
2588 }
2589
2590 static char line[256];
2591 static char *lineptr;
2592
2593 static void
2594 flush_input(void)
2595 {
2596         lineptr = NULL;
2597 }
2598
2599 static int
2600 inchar(void)
2601 {
2602         if (lineptr == NULL || *lineptr == 0) {
2603                 if (xmon_gets(line, sizeof(line)) == NULL) {
2604                         lineptr = NULL;
2605                         return EOF;
2606                 }
2607                 lineptr = line;
2608         }
2609         return *lineptr++;
2610 }
2611
2612 static void
2613 take_input(char *str)
2614 {
2615         lineptr = str;
2616 }
2617
2618
2619 static void
2620 symbol_lookup(void)
2621 {
2622         int type = inchar();
2623         unsigned long addr;
2624         static char tmp[64];
2625
2626         switch (type) {
2627         case 'a':
2628                 if (scanhex(&addr))
2629                         xmon_print_symbol(addr, ": ", "\n");
2630                 termch = 0;
2631                 break;
2632         case 's':
2633                 getstring(tmp, 64);
2634                 if (setjmp(bus_error_jmp) == 0) {
2635                         catch_memory_errors = 1;
2636                         sync();
2637                         addr = kallsyms_lookup_name(tmp);
2638                         if (addr)
2639                                 printf("%s: %lx\n", tmp, addr);
2640                         else
2641                                 printf("Symbol '%s' not found.\n", tmp);
2642                         sync();
2643                 }
2644                 catch_memory_errors = 0;
2645                 termch = 0;
2646                 break;
2647         }
2648 }
2649
2650
2651 /* Print an address in numeric and symbolic form (if possible) */
2652 static void xmon_print_symbol(unsigned long address, const char *mid,
2653                               const char *after)
2654 {
2655         char *modname;
2656         const char *name = NULL;
2657         unsigned long offset, size;
2658
2659         printf(REG, address);
2660         if (setjmp(bus_error_jmp) == 0) {
2661                 catch_memory_errors = 1;
2662                 sync();
2663                 name = kallsyms_lookup(address, &size, &offset, &modname,
2664                                        tmpstr);
2665                 sync();
2666                 /* wait a little while to see if we get a machine check */
2667                 __delay(200);
2668         }
2669
2670         catch_memory_errors = 0;
2671
2672         if (name) {
2673                 printf("%s%s+%#lx/%#lx", mid, name, offset, size);
2674                 if (modname)
2675                         printf(" [%s]", modname);
2676         }
2677         printf("%s", after);
2678 }
2679
2680 #ifdef CONFIG_PPC_BOOK3S_64
2681 static void dump_slb(void)
2682 {
2683         int i;
2684         unsigned long esid,vsid,valid;
2685         unsigned long llp;
2686
2687         printf("SLB contents of cpu %x\n", smp_processor_id());
2688
2689         for (i = 0; i < mmu_slb_size; i++) {
2690                 asm volatile("slbmfee  %0,%1" : "=r" (esid) : "r" (i));
2691                 asm volatile("slbmfev  %0,%1" : "=r" (vsid) : "r" (i));
2692                 valid = (esid & SLB_ESID_V);
2693                 if (valid | esid | vsid) {
2694                         printf("%02d %016lx %016lx", i, esid, vsid);
2695                         if (valid) {
2696                                 llp = vsid & SLB_VSID_LLP;
2697                                 if (vsid & SLB_VSID_B_1T) {
2698                                         printf("  1T  ESID=%9lx  VSID=%13lx LLP:%3lx \n",
2699                                                 GET_ESID_1T(esid),
2700                                                 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT_1T,
2701                                                 llp);
2702                                 } else {
2703                                         printf(" 256M ESID=%9lx  VSID=%13lx LLP:%3lx \n",
2704                                                 GET_ESID(esid),
2705                                                 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT,
2706                                                 llp);
2707                                 }
2708                         } else
2709                                 printf("\n");
2710                 }
2711         }
2712 }
2713
2714 static void dump_stab(void)
2715 {
2716         int i;
2717         unsigned long *tmp = (unsigned long *)local_paca->stab_addr;
2718
2719         printf("Segment table contents of cpu %x\n", smp_processor_id());
2720
2721         for (i = 0; i < PAGE_SIZE/16; i++) {
2722                 unsigned long a, b;
2723
2724                 a = *tmp++;
2725                 b = *tmp++;
2726
2727                 if (a || b) {
2728                         printf("%03d %016lx ", i, a);
2729                         printf("%016lx\n", b);
2730                 }
2731         }
2732 }
2733
2734 void dump_segments(void)
2735 {
2736         if (mmu_has_feature(MMU_FTR_SLB))
2737                 dump_slb();
2738         else
2739                 dump_stab();
2740 }
2741 #endif
2742
2743 #ifdef CONFIG_PPC_STD_MMU_32
2744 void dump_segments(void)
2745 {
2746         int i;
2747
2748         printf("sr0-15 =");
2749         for (i = 0; i < 16; ++i)
2750                 printf(" %x", mfsrin(i));
2751         printf("\n");
2752 }
2753 #endif
2754
2755 #ifdef CONFIG_44x
2756 static void dump_tlb_44x(void)
2757 {
2758         int i;
2759
2760         for (i = 0; i < PPC44x_TLB_SIZE; i++) {
2761                 unsigned long w0,w1,w2;
2762                 asm volatile("tlbre  %0,%1,0" : "=r" (w0) : "r" (i));
2763                 asm volatile("tlbre  %0,%1,1" : "=r" (w1) : "r" (i));
2764                 asm volatile("tlbre  %0,%1,2" : "=r" (w2) : "r" (i));
2765                 printf("[%02x] %08x %08x %08x ", i, w0, w1, w2);
2766                 if (w0 & PPC44x_TLB_VALID) {
2767                         printf("V %08x -> %01x%08x %c%c%c%c%c",
2768                                w0 & PPC44x_TLB_EPN_MASK,
2769                                w1 & PPC44x_TLB_ERPN_MASK,
2770                                w1 & PPC44x_TLB_RPN_MASK,
2771                                (w2 & PPC44x_TLB_W) ? 'W' : 'w',
2772                                (w2 & PPC44x_TLB_I) ? 'I' : 'i',
2773                                (w2 & PPC44x_TLB_M) ? 'M' : 'm',
2774                                (w2 & PPC44x_TLB_G) ? 'G' : 'g',
2775                                (w2 & PPC44x_TLB_E) ? 'E' : 'e');
2776                 }
2777                 printf("\n");
2778         }
2779 }
2780 #endif /* CONFIG_44x */
2781
2782 #ifdef CONFIG_PPC_BOOK3E
2783 static void dump_tlb_book3e(void)
2784 {
2785         u32 mmucfg, pidmask, lpidmask;
2786         u64 ramask;
2787         int i, tlb, ntlbs, pidsz, lpidsz, rasz, lrat = 0;
2788         int mmu_version;
2789         static const char *pgsz_names[] = {
2790                 "  1K",
2791                 "  2K",
2792                 "  4K",
2793                 "  8K",
2794                 " 16K",
2795                 " 32K",
2796                 " 64K",
2797                 "128K",
2798                 "256K",
2799                 "512K",
2800                 "  1M",
2801                 "  2M",
2802                 "  4M",
2803                 "  8M",
2804                 " 16M",
2805                 " 32M",
2806                 " 64M",
2807                 "128M",
2808                 "256M",
2809                 "512M",
2810                 "  1G",
2811                 "  2G",
2812                 "  4G",
2813                 "  8G",
2814                 " 16G",
2815                 " 32G",
2816                 " 64G",
2817                 "128G",
2818                 "256G",
2819                 "512G",
2820                 "  1T",
2821                 "  2T",
2822         };
2823
2824         /* Gather some infos about the MMU */
2825         mmucfg = mfspr(SPRN_MMUCFG);
2826         mmu_version = (mmucfg & 3) + 1;
2827         ntlbs = ((mmucfg >> 2) & 3) + 1;
2828         pidsz = ((mmucfg >> 6) & 0x1f) + 1;
2829         lpidsz = (mmucfg >> 24) & 0xf;
2830         rasz = (mmucfg >> 16) & 0x7f;
2831         if ((mmu_version > 1) && (mmucfg & 0x10000))
2832                 lrat = 1;
2833         printf("Book3E MMU MAV=%d.0,%d TLBs,%d-bit PID,%d-bit LPID,%d-bit RA\n",
2834                mmu_version, ntlbs, pidsz, lpidsz, rasz);
2835         pidmask = (1ul << pidsz) - 1;
2836         lpidmask = (1ul << lpidsz) - 1;
2837         ramask = (1ull << rasz) - 1;
2838
2839         for (tlb = 0; tlb < ntlbs; tlb++) {
2840                 u32 tlbcfg;
2841                 int nent, assoc, new_cc = 1;
2842                 printf("TLB %d:\n------\n", tlb);
2843                 switch(tlb) {
2844                 case 0:
2845                         tlbcfg = mfspr(SPRN_TLB0CFG);
2846                         break;
2847                 case 1:
2848                         tlbcfg = mfspr(SPRN_TLB1CFG);
2849                         break;
2850                 case 2:
2851                         tlbcfg = mfspr(SPRN_TLB2CFG);
2852                         break;
2853                 case 3:
2854                         tlbcfg = mfspr(SPRN_TLB3CFG);
2855                         break;
2856                 default:
2857                         printf("Unsupported TLB number !\n");
2858                         continue;
2859                 }
2860                 nent = tlbcfg & 0xfff;
2861                 assoc = (tlbcfg >> 24) & 0xff;
2862                 for (i = 0; i < nent; i++) {
2863                         u32 mas0 = MAS0_TLBSEL(tlb);
2864                         u32 mas1 = MAS1_TSIZE(BOOK3E_PAGESZ_4K);
2865                         u64 mas2 = 0;
2866                         u64 mas7_mas3;
2867                         int esel = i, cc = i;
2868
2869                         if (assoc != 0) {
2870                                 cc = i / assoc;
2871                                 esel = i % assoc;
2872                                 mas2 = cc * 0x1000;
2873                         }
2874
2875                         mas0 |= MAS0_ESEL(esel);
2876                         mtspr(SPRN_MAS0, mas0);
2877                         mtspr(SPRN_MAS1, mas1);
2878                         mtspr(SPRN_MAS2, mas2);
2879                         asm volatile("tlbre  0,0,0" : : : "memory");
2880                         mas1 = mfspr(SPRN_MAS1);
2881                         mas2 = mfspr(SPRN_MAS2);
2882                         mas7_mas3 = mfspr(SPRN_MAS7_MAS3);
2883                         if (assoc && (i % assoc) == 0)
2884                                 new_cc = 1;
2885                         if (!(mas1 & MAS1_VALID))
2886                                 continue;
2887                         if (assoc == 0)
2888                                 printf("%04x- ", i);
2889                         else if (new_cc)
2890                                 printf("%04x-%c", cc, 'A' + esel);
2891                         else
2892                                 printf("    |%c", 'A' + esel);
2893                         new_cc = 0;
2894                         printf(" %016llx %04x %s %c%c AS%c",
2895                                mas2 & ~0x3ffull,
2896                                (mas1 >> 16) & 0x3fff,
2897                                pgsz_names[(mas1 >> 7) & 0x1f],
2898                                mas1 & MAS1_IND ? 'I' : ' ',
2899                                mas1 & MAS1_IPROT ? 'P' : ' ',
2900                                mas1 & MAS1_TS ? '1' : '0');
2901                         printf(" %c%c%c%c%c%c%c",
2902                                mas2 & MAS2_X0 ? 'a' : ' ',
2903                                mas2 & MAS2_X1 ? 'v' : ' ',
2904                                mas2 & MAS2_W  ? 'w' : ' ',
2905                                mas2 & MAS2_I  ? 'i' : ' ',
2906                                mas2 & MAS2_M  ? 'm' : ' ',
2907                                mas2 & MAS2_G  ? 'g' : ' ',
2908                                mas2 & MAS2_E  ? 'e' : ' ');
2909                         printf(" %016llx", mas7_mas3 & ramask & ~0x7ffull);
2910                         if (mas1 & MAS1_IND)
2911                                 printf(" %s\n",
2912                                        pgsz_names[(mas7_mas3 >> 1) & 0x1f]);
2913                         else
2914                                 printf(" U%c%c%c S%c%c%c\n",
2915                                        mas7_mas3 & MAS3_UX ? 'x' : ' ',
2916                                        mas7_mas3 & MAS3_UW ? 'w' : ' ',
2917                                        mas7_mas3 & MAS3_UR ? 'r' : ' ',
2918                                        mas7_mas3 & MAS3_SX ? 'x' : ' ',
2919                                        mas7_mas3 & MAS3_SW ? 'w' : ' ',
2920                                        mas7_mas3 & MAS3_SR ? 'r' : ' ');
2921                 }
2922         }
2923 }
2924 #endif /* CONFIG_PPC_BOOK3E */
2925
2926 static void xmon_init(int enable)
2927 {
2928         if (enable) {
2929                 __debugger = xmon;
2930                 __debugger_ipi = xmon_ipi;
2931                 __debugger_bpt = xmon_bpt;
2932                 __debugger_sstep = xmon_sstep;
2933                 __debugger_iabr_match = xmon_iabr_match;
2934                 __debugger_break_match = xmon_break_match;
2935                 __debugger_fault_handler = xmon_fault_handler;
2936         } else {
2937                 __debugger = NULL;
2938                 __debugger_ipi = NULL;
2939                 __debugger_bpt = NULL;
2940                 __debugger_sstep = NULL;
2941                 __debugger_iabr_match = NULL;
2942                 __debugger_break_match = NULL;
2943                 __debugger_fault_handler = NULL;
2944         }
2945 }
2946
2947 #ifdef CONFIG_MAGIC_SYSRQ
2948 static void sysrq_handle_xmon(int key)
2949 {
2950         /* ensure xmon is enabled */
2951         xmon_init(1);
2952         debugger(get_irq_regs());
2953 }
2954
2955 static struct sysrq_key_op sysrq_xmon_op = {
2956         .handler =      sysrq_handle_xmon,
2957         .help_msg =     "xmon(x)",
2958         .action_msg =   "Entering xmon",
2959 };
2960
2961 static int __init setup_xmon_sysrq(void)
2962 {
2963         register_sysrq_key('x', &sysrq_xmon_op);
2964         return 0;
2965 }
2966 __initcall(setup_xmon_sysrq);
2967 #endif /* CONFIG_MAGIC_SYSRQ */
2968
2969 static int __initdata xmon_early, xmon_off;
2970
2971 static int __init early_parse_xmon(char *p)
2972 {
2973         if (!p || strncmp(p, "early", 5) == 0) {
2974                 /* just "xmon" is equivalent to "xmon=early" */
2975                 xmon_init(1);
2976                 xmon_early = 1;
2977         } else if (strncmp(p, "on", 2) == 0)
2978                 xmon_init(1);
2979         else if (strncmp(p, "off", 3) == 0)
2980                 xmon_off = 1;
2981         else if (strncmp(p, "nobt", 4) == 0)
2982                 xmon_no_auto_backtrace = 1;
2983         else
2984                 return 1;
2985
2986         return 0;
2987 }
2988 early_param("xmon", early_parse_xmon);
2989
2990 void __init xmon_setup(void)
2991 {
2992 #ifdef CONFIG_XMON_DEFAULT
2993         if (!xmon_off)
2994                 xmon_init(1);
2995 #endif
2996         if (xmon_early)
2997                 debugger(NULL);
2998 }
2999
3000 #ifdef CONFIG_SPU_BASE
3001
3002 struct spu_info {
3003         struct spu *spu;
3004         u64 saved_mfc_sr1_RW;
3005         u32 saved_spu_runcntl_RW;
3006         unsigned long dump_addr;
3007         u8 stopped_ok;
3008 };
3009
3010 #define XMON_NUM_SPUS   16      /* Enough for current hardware */
3011
3012 static struct spu_info spu_info[XMON_NUM_SPUS];
3013
3014 void xmon_register_spus(struct list_head *list)
3015 {
3016         struct spu *spu;
3017
3018         list_for_each_entry(spu, list, full_list) {
3019                 if (spu->number >= XMON_NUM_SPUS) {
3020                         WARN_ON(1);
3021                         continue;
3022                 }
3023
3024                 spu_info[spu->number].spu = spu;
3025                 spu_info[spu->number].stopped_ok = 0;
3026                 spu_info[spu->number].dump_addr = (unsigned long)
3027                                 spu_info[spu->number].spu->local_store;
3028         }
3029 }
3030
3031 static void stop_spus(void)
3032 {
3033         struct spu *spu;
3034         int i;
3035         u64 tmp;
3036
3037         for (i = 0; i < XMON_NUM_SPUS; i++) {
3038                 if (!spu_info[i].spu)
3039                         continue;
3040
3041                 if (setjmp(bus_error_jmp) == 0) {
3042                         catch_memory_errors = 1;
3043                         sync();
3044
3045                         spu = spu_info[i].spu;
3046
3047                         spu_info[i].saved_spu_runcntl_RW =
3048                                 in_be32(&spu->problem->spu_runcntl_RW);
3049
3050                         tmp = spu_mfc_sr1_get(spu);
3051                         spu_info[i].saved_mfc_sr1_RW = tmp;
3052
3053                         tmp &= ~MFC_STATE1_MASTER_RUN_CONTROL_MASK;
3054                         spu_mfc_sr1_set(spu, tmp);
3055
3056                         sync();
3057                         __delay(200);
3058
3059                         spu_info[i].stopped_ok = 1;
3060
3061                         printf("Stopped spu %.2d (was %s)\n", i,
3062                                         spu_info[i].saved_spu_runcntl_RW ?
3063                                         "running" : "stopped");
3064                 } else {
3065                         catch_memory_errors = 0;
3066                         printf("*** Error stopping spu %.2d\n", i);
3067                 }
3068                 catch_memory_errors = 0;
3069         }
3070 }
3071
3072 static void restart_spus(void)
3073 {
3074         struct spu *spu;
3075         int i;
3076
3077         for (i = 0; i < XMON_NUM_SPUS; i++) {
3078                 if (!spu_info[i].spu)
3079                         continue;
3080
3081                 if (!spu_info[i].stopped_ok) {
3082                         printf("*** Error, spu %d was not successfully stopped"
3083                                         ", not restarting\n", i);
3084                         continue;
3085                 }
3086
3087                 if (setjmp(bus_error_jmp) == 0) {
3088                         catch_memory_errors = 1;
3089                         sync();
3090
3091                         spu = spu_info[i].spu;
3092                         spu_mfc_sr1_set(spu, spu_info[i].saved_mfc_sr1_RW);
3093                         out_be32(&spu->problem->spu_runcntl_RW,
3094                                         spu_info[i].saved_spu_runcntl_RW);
3095
3096                         sync();
3097                         __delay(200);
3098
3099                         printf("Restarted spu %.2d\n", i);
3100                 } else {
3101                         catch_memory_errors = 0;
3102                         printf("*** Error restarting spu %.2d\n", i);
3103                 }
3104                 catch_memory_errors = 0;
3105         }
3106 }
3107
3108 #define DUMP_WIDTH      23
3109 #define DUMP_VALUE(format, field, value)                                \
3110 do {                                                                    \
3111         if (setjmp(bus_error_jmp) == 0) {                               \
3112                 catch_memory_errors = 1;                                \
3113                 sync();                                                 \
3114                 printf("  %-*s = "format"\n", DUMP_WIDTH,               \
3115                                 #field, value);                         \
3116                 sync();                                                 \
3117                 __delay(200);                                           \
3118         } else {                                                        \
3119                 catch_memory_errors = 0;                                \
3120                 printf("  %-*s = *** Error reading field.\n",           \
3121                                         DUMP_WIDTH, #field);            \
3122         }                                                               \
3123         catch_memory_errors = 0;                                        \
3124 } while (0)
3125
3126 #define DUMP_FIELD(obj, format, field)  \
3127         DUMP_VALUE(format, field, obj->field)
3128
3129 static void dump_spu_fields(struct spu *spu)
3130 {
3131         printf("Dumping spu fields at address %p:\n", spu);
3132
3133         DUMP_FIELD(spu, "0x%x", number);
3134         DUMP_FIELD(spu, "%s", name);
3135         DUMP_FIELD(spu, "0x%lx", local_store_phys);
3136         DUMP_FIELD(spu, "0x%p", local_store);
3137         DUMP_FIELD(spu, "0x%lx", ls_size);
3138         DUMP_FIELD(spu, "0x%x", node);
3139         DUMP_FIELD(spu, "0x%lx", flags);
3140         DUMP_FIELD(spu, "%d", class_0_pending);
3141         DUMP_FIELD(spu, "0x%lx", class_0_dar);
3142         DUMP_FIELD(spu, "0x%lx", class_1_dar);
3143         DUMP_FIELD(spu, "0x%lx", class_1_dsisr);
3144         DUMP_FIELD(spu, "0x%lx", irqs[0]);
3145         DUMP_FIELD(spu, "0x%lx", irqs[1]);
3146         DUMP_FIELD(spu, "0x%lx", irqs[2]);
3147         DUMP_FIELD(spu, "0x%x", slb_replace);
3148         DUMP_FIELD(spu, "%d", pid);
3149         DUMP_FIELD(spu, "0x%p", mm);
3150         DUMP_FIELD(spu, "0x%p", ctx);
3151         DUMP_FIELD(spu, "0x%p", rq);
3152         DUMP_FIELD(spu, "0x%p", timestamp);
3153         DUMP_FIELD(spu, "0x%lx", problem_phys);
3154         DUMP_FIELD(spu, "0x%p", problem);
3155         DUMP_VALUE("0x%x", problem->spu_runcntl_RW,
3156                         in_be32(&spu->problem->spu_runcntl_RW));
3157         DUMP_VALUE("0x%x", problem->spu_status_R,
3158                         in_be32(&spu->problem->spu_status_R));
3159         DUMP_VALUE("0x%x", problem->spu_npc_RW,
3160                         in_be32(&spu->problem->spu_npc_RW));
3161         DUMP_FIELD(spu, "0x%p", priv2);
3162         DUMP_FIELD(spu, "0x%p", pdata);
3163 }
3164
3165 int
3166 spu_inst_dump(unsigned long adr, long count, int praddr)
3167 {
3168         return generic_inst_dump(adr, count, praddr, print_insn_spu);
3169 }
3170
3171 static void dump_spu_ls(unsigned long num, int subcmd)
3172 {
3173         unsigned long offset, addr, ls_addr;
3174
3175         if (setjmp(bus_error_jmp) == 0) {
3176                 catch_memory_errors = 1;
3177                 sync();
3178                 ls_addr = (unsigned long)spu_info[num].spu->local_store;
3179                 sync();
3180                 __delay(200);
3181         } else {
3182                 catch_memory_errors = 0;
3183                 printf("*** Error: accessing spu info for spu %d\n", num);
3184                 return;
3185         }
3186         catch_memory_errors = 0;
3187
3188         if (scanhex(&offset))
3189                 addr = ls_addr + offset;
3190         else
3191                 addr = spu_info[num].dump_addr;
3192
3193         if (addr >= ls_addr + LS_SIZE) {
3194                 printf("*** Error: address outside of local store\n");
3195                 return;
3196         }
3197
3198         switch (subcmd) {
3199         case 'i':
3200                 addr += spu_inst_dump(addr, 16, 1);
3201                 last_cmd = "sdi\n";
3202                 break;
3203         default:
3204                 prdump(addr, 64);
3205                 addr += 64;
3206                 last_cmd = "sd\n";
3207                 break;
3208         }
3209
3210         spu_info[num].dump_addr = addr;
3211 }
3212
3213 static int do_spu_cmd(void)
3214 {
3215         static unsigned long num = 0;
3216         int cmd, subcmd = 0;
3217
3218         cmd = inchar();
3219         switch (cmd) {
3220         case 's':
3221                 stop_spus();
3222                 break;
3223         case 'r':
3224                 restart_spus();
3225                 break;
3226         case 'd':
3227                 subcmd = inchar();
3228                 if (isxdigit(subcmd) || subcmd == '\n')
3229                         termch = subcmd;
3230         case 'f':
3231                 scanhex(&num);
3232                 if (num >= XMON_NUM_SPUS || !spu_info[num].spu) {
3233                         printf("*** Error: invalid spu number\n");
3234                         return 0;
3235                 }
3236
3237                 switch (cmd) {
3238                 case 'f':
3239                         dump_spu_fields(spu_info[num].spu);
3240                         break;
3241                 default:
3242                         dump_spu_ls(num, subcmd);
3243                         break;
3244                 }
3245
3246                 break;
3247         default:
3248                 return -1;
3249         }
3250
3251         return 0;
3252 }
3253 #else /* ! CONFIG_SPU_BASE */
3254 static int do_spu_cmd(void)
3255 {
3256         return -1;
3257 }
3258 #endif