blob: f0fa22e7d36c78b0011e4a7932266a9609f825bb [file] [log] [blame]
xjb04a4022021-11-25 15:01:52 +08001/*
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
14#include <linux/kernel.h>
15#include <linux/errno.h>
16#include <linux/sched/signal.h>
17#include <linux/smp.h>
18#include <linux/mm.h>
19#include <linux/reboot.h>
20#include <linux/delay.h>
21#include <linux/kallsyms.h>
22#include <linux/kmsg_dump.h>
23#include <linux/cpumask.h>
24#include <linux/export.h>
25#include <linux/sysrq.h>
26#include <linux/interrupt.h>
27#include <linux/irq.h>
28#include <linux/bug.h>
29#include <linux/nmi.h>
30#include <linux/ctype.h>
31#include <linux/highmem.h>
32
33#include <asm/debugfs.h>
34#include <asm/ptrace.h>
35#include <asm/smp.h>
36#include <asm/string.h>
37#include <asm/prom.h>
38#include <asm/machdep.h>
39#include <asm/xmon.h>
40#include <asm/processor.h>
41#include <asm/pgtable.h>
42#include <asm/mmu.h>
43#include <asm/mmu_context.h>
44#include <asm/plpar_wrappers.h>
45#include <asm/cputable.h>
46#include <asm/rtas.h>
47#include <asm/sstep.h>
48#include <asm/irq_regs.h>
49#include <asm/spu.h>
50#include <asm/spu_priv1.h>
51#include <asm/setjmp.h>
52#include <asm/reg.h>
53#include <asm/debug.h>
54#include <asm/hw_breakpoint.h>
55#include <asm/xive.h>
56#include <asm/opal.h>
57#include <asm/firmware.h>
58#include <asm/code-patching.h>
59#include <asm/sections.h>
60
61#ifdef CONFIG_PPC64
62#include <asm/hvcall.h>
63#include <asm/paca.h>
64#endif
65
66#include "nonstdio.h"
67#include "dis-asm.h"
68
69#ifdef CONFIG_SMP
70static cpumask_t cpus_in_xmon = CPU_MASK_NONE;
71static unsigned long xmon_taken = 1;
72static int xmon_owner;
73static int xmon_gate;
74#else
75#define xmon_owner 0
76#endif /* CONFIG_SMP */
77
78#ifdef CONFIG_PPC_PSERIES
79static int set_indicator_token = RTAS_UNKNOWN_SERVICE;
80#endif
81static unsigned long in_xmon __read_mostly = 0;
82static int xmon_on = IS_ENABLED(CONFIG_XMON_DEFAULT);
83
84static unsigned long adrs;
85static int size = 1;
86#define MAX_DUMP (128 * 1024)
87static unsigned long ndump = 64;
88static unsigned long nidump = 16;
89static unsigned long ncsum = 4096;
90static int termch;
91static char tmpstr[128];
92static int tracing_enabled;
93
94static long bus_error_jmp[JMP_BUF_LEN];
95static int catch_memory_errors;
96static int catch_spr_faults;
97static long *xmon_fault_jmp[NR_CPUS];
98
99/* Breakpoint stuff */
100struct bpt {
101 unsigned long address;
102 unsigned int instr[2];
103 atomic_t ref_count;
104 int enabled;
105 unsigned long pad;
106};
107
108/* Bits in bpt.enabled */
109#define BP_CIABR 1
110#define BP_TRAP 2
111#define BP_DABR 4
112
113#define NBPTS 256
114static struct bpt bpts[NBPTS];
115static struct bpt dabr;
116static struct bpt *iabr;
117static unsigned bpinstr = 0x7fe00008; /* trap */
118
119#define BP_NUM(bp) ((bp) - bpts + 1)
120
121/* Prototypes */
122static int cmds(struct pt_regs *);
123static int mread(unsigned long, void *, int);
124static int mwrite(unsigned long, void *, int);
125static int handle_fault(struct pt_regs *);
126static void byterev(unsigned char *, int);
127static void memex(void);
128static int bsesc(void);
129static void dump(void);
130static void show_pte(unsigned long);
131static void prdump(unsigned long, long);
132static int ppc_inst_dump(unsigned long, long, int);
133static void dump_log_buf(void);
134
135#ifdef CONFIG_PPC_POWERNV
136static void dump_opal_msglog(void);
137#else
138static inline void dump_opal_msglog(void)
139{
140 printf("Machine is not running OPAL firmware.\n");
141}
142#endif
143
144static void backtrace(struct pt_regs *);
145static void excprint(struct pt_regs *);
146static void prregs(struct pt_regs *);
147static void memops(int);
148static void memlocate(void);
149static void memzcan(void);
150static void memdiffs(unsigned char *, unsigned char *, unsigned, unsigned);
151int skipbl(void);
152int scanhex(unsigned long *valp);
153static void scannl(void);
154static int hexdigit(int);
155void getstring(char *, int);
156static void flush_input(void);
157static int inchar(void);
158static void take_input(char *);
159static int read_spr(int, unsigned long *);
160static void write_spr(int, unsigned long);
161static void super_regs(void);
162static void remove_bpts(void);
163static void insert_bpts(void);
164static void remove_cpu_bpts(void);
165static void insert_cpu_bpts(void);
166static struct bpt *at_breakpoint(unsigned long pc);
167static struct bpt *in_breakpoint_table(unsigned long pc, unsigned long *offp);
168static int do_step(struct pt_regs *);
169static void bpt_cmds(void);
170static void cacheflush(void);
171static int cpu_cmd(void);
172static void csum(void);
173static void bootcmds(void);
174static void proccall(void);
175static void show_tasks(void);
176void dump_segments(void);
177static void symbol_lookup(void);
178static void xmon_show_stack(unsigned long sp, unsigned long lr,
179 unsigned long pc);
180static void xmon_print_symbol(unsigned long address, const char *mid,
181 const char *after);
182static const char *getvecname(unsigned long vec);
183
184static int do_spu_cmd(void);
185
186#ifdef CONFIG_44x
187static void dump_tlb_44x(void);
188#endif
189#ifdef CONFIG_PPC_BOOK3E
190static void dump_tlb_book3e(void);
191#endif
192
193#ifdef CONFIG_PPC64
194#define REG "%.16lx"
195#else
196#define REG "%.8lx"
197#endif
198
199#ifdef __LITTLE_ENDIAN__
200#define GETWORD(v) (((v)[3] << 24) + ((v)[2] << 16) + ((v)[1] << 8) + (v)[0])
201#else
202#define GETWORD(v) (((v)[0] << 24) + ((v)[1] << 16) + ((v)[2] << 8) + (v)[3])
203#endif
204
205static char *help_string = "\
206Commands:\n\
207 b show breakpoints\n\
208 bd set data breakpoint\n\
209 bi set instruction breakpoint\n\
210 bc clear breakpoint\n"
211#ifdef CONFIG_SMP
212 "\
213 c print cpus stopped in xmon\n\
214 c# try to switch to cpu number h (in hex)\n"
215#endif
216 "\
217 C checksum\n\
218 d dump bytes\n\
219 d1 dump 1 byte values\n\
220 d2 dump 2 byte values\n\
221 d4 dump 4 byte values\n\
222 d8 dump 8 byte values\n\
223 di dump instructions\n\
224 df dump float values\n\
225 dd dump double values\n\
226 dl dump the kernel log buffer\n"
227#ifdef CONFIG_PPC_POWERNV
228 "\
229 do dump the OPAL message log\n"
230#endif
231#ifdef CONFIG_PPC64
232 "\
233 dp[#] dump paca for current cpu, or cpu #\n\
234 dpa dump paca for all possible cpus\n"
235#endif
236 "\
237 dr dump stream of raw bytes\n\
238 dv dump virtual address translation \n\
239 dt dump the tracing buffers (uses printk)\n\
240 dtc dump the tracing buffers for current CPU (uses printk)\n\
241"
242#ifdef CONFIG_PPC_POWERNV
243" dx# dump xive on CPU #\n\
244 dxi# dump xive irq state #\n\
245 dxa dump xive on all CPUs\n"
246#endif
247" e print exception information\n\
248 f flush cache\n\
249 la lookup symbol+offset of specified address\n\
250 ls lookup address of specified symbol\n\
251 lp s [#] lookup address of percpu symbol s for current cpu, or cpu #\n\
252 m examine/change memory\n\
253 mm move a block of memory\n\
254 ms set a block of memory\n\
255 md compare two blocks of memory\n\
256 ml locate a block of memory\n\
257 mz zero a block of memory\n\
258 mi show information about memory allocation\n\
259 p call a procedure\n\
260 P list processes/tasks\n\
261 r print registers\n\
262 s single step\n"
263#ifdef CONFIG_SPU_BASE
264" ss stop execution on all spus\n\
265 sr restore execution on stopped spus\n\
266 sf # dump spu fields for spu # (in hex)\n\
267 sd # dump spu local store for spu # (in hex)\n\
268 sdi # disassemble spu local store for spu # (in hex)\n"
269#endif
270" S print special registers\n\
271 Sa print all SPRs\n\
272 Sr # read SPR #\n\
273 Sw #v write v to SPR #\n\
274 t print backtrace\n\
275 x exit monitor and recover\n\
276 X exit monitor and don't recover\n"
277#if defined(CONFIG_PPC64) && !defined(CONFIG_PPC_BOOK3E)
278" u dump segment table or SLB\n"
279#elif defined(CONFIG_PPC_STD_MMU_32)
280" u dump segment registers\n"
281#elif defined(CONFIG_44x) || defined(CONFIG_PPC_BOOK3E)
282" u dump TLB\n"
283#endif
284" U show uptime information\n"
285" ? help\n"
286" # n limit output to n lines per page (for dp, dpa, dl)\n"
287" zr reboot\n\
288 zh halt\n"
289;
290
291static struct pt_regs *xmon_regs;
292
293static inline void sync(void)
294{
295 asm volatile("sync; isync");
296}
297
298static inline void store_inst(void *p)
299{
300 asm volatile ("dcbst 0,%0; sync; icbi 0,%0; isync" : : "r" (p));
301}
302
303static inline void cflush(void *p)
304{
305 asm volatile ("dcbf 0,%0; icbi 0,%0" : : "r" (p));
306}
307
308static inline void cinval(void *p)
309{
310 asm volatile ("dcbi 0,%0; icbi 0,%0" : : "r" (p));
311}
312
313/**
314 * write_ciabr() - write the CIABR SPR
315 * @ciabr: The value to write.
316 *
317 * This function writes a value to the CIARB register either directly
318 * through mtspr instruction if the kernel is in HV privilege mode or
319 * call a hypervisor function to achieve the same in case the kernel
320 * is in supervisor privilege mode.
321 */
322static void write_ciabr(unsigned long ciabr)
323{
324 if (!cpu_has_feature(CPU_FTR_ARCH_207S))
325 return;
326
327 if (cpu_has_feature(CPU_FTR_HVMODE)) {
328 mtspr(SPRN_CIABR, ciabr);
329 return;
330 }
331 plpar_set_ciabr(ciabr);
332}
333
334/**
335 * set_ciabr() - set the CIABR
336 * @addr: The value to set.
337 *
338 * This function sets the correct privilege value into the the HW
339 * breakpoint address before writing it up in the CIABR register.
340 */
341static void set_ciabr(unsigned long addr)
342{
343 addr &= ~CIABR_PRIV;
344
345 if (cpu_has_feature(CPU_FTR_HVMODE))
346 addr |= CIABR_PRIV_HYPER;
347 else
348 addr |= CIABR_PRIV_SUPER;
349 write_ciabr(addr);
350}
351
352/*
353 * Disable surveillance (the service processor watchdog function)
354 * while we are in xmon.
355 * XXX we should re-enable it when we leave. :)
356 */
357#define SURVEILLANCE_TOKEN 9000
358
359static inline void disable_surveillance(void)
360{
361#ifdef CONFIG_PPC_PSERIES
362 /* Since this can't be a module, args should end up below 4GB. */
363 static struct rtas_args args;
364
365 /*
366 * At this point we have got all the cpus we can into
367 * xmon, so there is hopefully no other cpu calling RTAS
368 * at the moment, even though we don't take rtas.lock.
369 * If we did try to take rtas.lock there would be a
370 * real possibility of deadlock.
371 */
372 if (set_indicator_token == RTAS_UNKNOWN_SERVICE)
373 return;
374
375 rtas_call_unlocked(&args, set_indicator_token, 3, 1, NULL,
376 SURVEILLANCE_TOKEN, 0, 0);
377
378#endif /* CONFIG_PPC_PSERIES */
379}
380
381#ifdef CONFIG_SMP
382static int xmon_speaker;
383
384static void get_output_lock(void)
385{
386 int me = smp_processor_id() + 0x100;
387 int last_speaker = 0, prev;
388 long timeout;
389
390 if (xmon_speaker == me)
391 return;
392
393 for (;;) {
394 last_speaker = cmpxchg(&xmon_speaker, 0, me);
395 if (last_speaker == 0)
396 return;
397
398 /*
399 * Wait a full second for the lock, we might be on a slow
400 * console, but check every 100us.
401 */
402 timeout = 10000;
403 while (xmon_speaker == last_speaker) {
404 if (--timeout > 0) {
405 udelay(100);
406 continue;
407 }
408
409 /* hostile takeover */
410 prev = cmpxchg(&xmon_speaker, last_speaker, me);
411 if (prev == last_speaker)
412 return;
413 break;
414 }
415 }
416}
417
418static void release_output_lock(void)
419{
420 xmon_speaker = 0;
421}
422
423int cpus_are_in_xmon(void)
424{
425 return !cpumask_empty(&cpus_in_xmon);
426}
427
428static bool wait_for_other_cpus(int ncpus)
429{
430 unsigned long timeout;
431
432 /* We wait for 2s, which is a metric "little while" */
433 for (timeout = 20000; timeout != 0; --timeout) {
434 if (cpumask_weight(&cpus_in_xmon) >= ncpus)
435 return true;
436 udelay(100);
437 barrier();
438 }
439
440 return false;
441}
442#endif /* CONFIG_SMP */
443
444static inline int unrecoverable_excp(struct pt_regs *regs)
445{
446#if defined(CONFIG_4xx) || defined(CONFIG_PPC_BOOK3E)
447 /* We have no MSR_RI bit on 4xx or Book3e, so we simply return false */
448 return 0;
449#else
450 return ((regs->msr & MSR_RI) == 0);
451#endif
452}
453
454static int xmon_core(struct pt_regs *regs, int fromipi)
455{
456 int cmd = 0;
457 struct bpt *bp;
458 long recurse_jmp[JMP_BUF_LEN];
459 unsigned long offset;
460 unsigned long flags;
461#ifdef CONFIG_SMP
462 int cpu;
463 int secondary;
464#endif
465
466 local_irq_save(flags);
467 hard_irq_disable();
468
469 if (!fromipi) {
470 tracing_enabled = tracing_is_on();
471 tracing_off();
472 }
473
474 bp = in_breakpoint_table(regs->nip, &offset);
475 if (bp != NULL) {
476 regs->nip = bp->address + offset;
477 atomic_dec(&bp->ref_count);
478 }
479
480 remove_cpu_bpts();
481
482#ifdef CONFIG_SMP
483 cpu = smp_processor_id();
484 if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
485 /*
486 * We catch SPR read/write faults here because the 0x700, 0xf60
487 * etc. handlers don't call debugger_fault_handler().
488 */
489 if (catch_spr_faults)
490 longjmp(bus_error_jmp, 1);
491 get_output_lock();
492 excprint(regs);
493 printf("cpu 0x%x: Exception %lx %s in xmon, "
494 "returning to main loop\n",
495 cpu, regs->trap, getvecname(TRAP(regs)));
496 release_output_lock();
497 longjmp(xmon_fault_jmp[cpu], 1);
498 }
499
500 if (setjmp(recurse_jmp) != 0) {
501 if (!in_xmon || !xmon_gate) {
502 get_output_lock();
503 printf("xmon: WARNING: bad recursive fault "
504 "on cpu 0x%x\n", cpu);
505 release_output_lock();
506 goto waiting;
507 }
508 secondary = !(xmon_taken && cpu == xmon_owner);
509 goto cmdloop;
510 }
511
512 xmon_fault_jmp[cpu] = recurse_jmp;
513
514 bp = NULL;
515 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT))
516 bp = at_breakpoint(regs->nip);
517 if (bp || unrecoverable_excp(regs))
518 fromipi = 0;
519
520 if (!fromipi) {
521 get_output_lock();
522 excprint(regs);
523 if (bp) {
524 printf("cpu 0x%x stopped at breakpoint 0x%tx (",
525 cpu, BP_NUM(bp));
526 xmon_print_symbol(regs->nip, " ", ")\n");
527 }
528 if (unrecoverable_excp(regs))
529 printf("WARNING: exception is not recoverable, "
530 "can't continue\n");
531 release_output_lock();
532 }
533
534 cpumask_set_cpu(cpu, &cpus_in_xmon);
535
536 waiting:
537 secondary = 1;
538 spin_begin();
539 while (secondary && !xmon_gate) {
540 if (in_xmon == 0) {
541 if (fromipi) {
542 spin_end();
543 goto leave;
544 }
545 secondary = test_and_set_bit(0, &in_xmon);
546 }
547 spin_cpu_relax();
548 touch_nmi_watchdog();
549 }
550 spin_end();
551
552 if (!secondary && !xmon_gate) {
553 /* we are the first cpu to come in */
554 /* interrupt other cpu(s) */
555 int ncpus = num_online_cpus();
556
557 xmon_owner = cpu;
558 mb();
559 if (ncpus > 1) {
560 /*
561 * A system reset (trap == 0x100) can be triggered on
562 * all CPUs, so when we come in via 0x100 try waiting
563 * for the other CPUs to come in before we send the
564 * debugger break (IPI). This is similar to
565 * crash_kexec_secondary().
566 */
567 if (TRAP(regs) != 0x100 || !wait_for_other_cpus(ncpus))
568 smp_send_debugger_break();
569
570 wait_for_other_cpus(ncpus);
571 }
572 remove_bpts();
573 disable_surveillance();
574 /* for breakpoint or single step, print the current instr. */
575 if (bp || TRAP(regs) == 0xd00)
576 ppc_inst_dump(regs->nip, 1, 0);
577 printf("enter ? for help\n");
578 mb();
579 xmon_gate = 1;
580 barrier();
581 touch_nmi_watchdog();
582 }
583
584 cmdloop:
585 while (in_xmon) {
586 if (secondary) {
587 spin_begin();
588 if (cpu == xmon_owner) {
589 if (!test_and_set_bit(0, &xmon_taken)) {
590 secondary = 0;
591 spin_end();
592 continue;
593 }
594 /* missed it */
595 while (cpu == xmon_owner)
596 spin_cpu_relax();
597 }
598 spin_cpu_relax();
599 touch_nmi_watchdog();
600 } else {
601 cmd = cmds(regs);
602 if (cmd != 0) {
603 /* exiting xmon */
604 insert_bpts();
605 xmon_gate = 0;
606 wmb();
607 in_xmon = 0;
608 break;
609 }
610 /* have switched to some other cpu */
611 secondary = 1;
612 }
613 }
614 leave:
615 cpumask_clear_cpu(cpu, &cpus_in_xmon);
616 xmon_fault_jmp[cpu] = NULL;
617#else
618 /* UP is simple... */
619 if (in_xmon) {
620 printf("Exception %lx %s in xmon, returning to main loop\n",
621 regs->trap, getvecname(TRAP(regs)));
622 longjmp(xmon_fault_jmp[0], 1);
623 }
624 if (setjmp(recurse_jmp) == 0) {
625 xmon_fault_jmp[0] = recurse_jmp;
626 in_xmon = 1;
627
628 excprint(regs);
629 bp = at_breakpoint(regs->nip);
630 if (bp) {
631 printf("Stopped at breakpoint %tx (", BP_NUM(bp));
632 xmon_print_symbol(regs->nip, " ", ")\n");
633 }
634 if (unrecoverable_excp(regs))
635 printf("WARNING: exception is not recoverable, "
636 "can't continue\n");
637 remove_bpts();
638 disable_surveillance();
639 /* for breakpoint or single step, print the current instr. */
640 if (bp || TRAP(regs) == 0xd00)
641 ppc_inst_dump(regs->nip, 1, 0);
642 printf("enter ? for help\n");
643 }
644
645 cmd = cmds(regs);
646
647 insert_bpts();
648 in_xmon = 0;
649#endif
650
651#ifdef CONFIG_BOOKE
652 if (regs->msr & MSR_DE) {
653 bp = at_breakpoint(regs->nip);
654 if (bp != NULL) {
655 regs->nip = (unsigned long) &bp->instr[0];
656 atomic_inc(&bp->ref_count);
657 }
658 }
659#else
660 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
661 bp = at_breakpoint(regs->nip);
662 if (bp != NULL) {
663 int stepped = emulate_step(regs, bp->instr[0]);
664 if (stepped == 0) {
665 regs->nip = (unsigned long) &bp->instr[0];
666 atomic_inc(&bp->ref_count);
667 } else if (stepped < 0) {
668 printf("Couldn't single-step %s instruction\n",
669 (IS_RFID(bp->instr[0])? "rfid": "mtmsrd"));
670 }
671 }
672 }
673#endif
674 insert_cpu_bpts();
675
676 touch_nmi_watchdog();
677 local_irq_restore(flags);
678
679 return cmd != 'X' && cmd != EOF;
680}
681
682int xmon(struct pt_regs *excp)
683{
684 struct pt_regs regs;
685
686 if (excp == NULL) {
687 ppc_save_regs(&regs);
688 excp = &regs;
689 }
690
691 return xmon_core(excp, 0);
692}
693EXPORT_SYMBOL(xmon);
694
695irqreturn_t xmon_irq(int irq, void *d)
696{
697 unsigned long flags;
698 local_irq_save(flags);
699 printf("Keyboard interrupt\n");
700 xmon(get_irq_regs());
701 local_irq_restore(flags);
702 return IRQ_HANDLED;
703}
704
705static int xmon_bpt(struct pt_regs *regs)
706{
707 struct bpt *bp;
708 unsigned long offset;
709
710 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
711 return 0;
712
713 /* Are we at the trap at bp->instr[1] for some bp? */
714 bp = in_breakpoint_table(regs->nip, &offset);
715 if (bp != NULL && offset == 4) {
716 regs->nip = bp->address + 4;
717 atomic_dec(&bp->ref_count);
718 return 1;
719 }
720
721 /* Are we at a breakpoint? */
722 bp = at_breakpoint(regs->nip);
723 if (!bp)
724 return 0;
725
726 xmon_core(regs, 0);
727
728 return 1;
729}
730
731static int xmon_sstep(struct pt_regs *regs)
732{
733 if (user_mode(regs))
734 return 0;
735 xmon_core(regs, 0);
736 return 1;
737}
738
739static int xmon_break_match(struct pt_regs *regs)
740{
741 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
742 return 0;
743 if (dabr.enabled == 0)
744 return 0;
745 xmon_core(regs, 0);
746 return 1;
747}
748
749static int xmon_iabr_match(struct pt_regs *regs)
750{
751 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
752 return 0;
753 if (iabr == NULL)
754 return 0;
755 xmon_core(regs, 0);
756 return 1;
757}
758
759static int xmon_ipi(struct pt_regs *regs)
760{
761#ifdef CONFIG_SMP
762 if (in_xmon && !cpumask_test_cpu(smp_processor_id(), &cpus_in_xmon))
763 xmon_core(regs, 1);
764#endif
765 return 0;
766}
767
768static int xmon_fault_handler(struct pt_regs *regs)
769{
770 struct bpt *bp;
771 unsigned long offset;
772
773 if (in_xmon && catch_memory_errors)
774 handle_fault(regs); /* doesn't return */
775
776 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
777 bp = in_breakpoint_table(regs->nip, &offset);
778 if (bp != NULL) {
779 regs->nip = bp->address + offset;
780 atomic_dec(&bp->ref_count);
781 }
782 }
783
784 return 0;
785}
786
787/* Force enable xmon if not already enabled */
788static inline void force_enable_xmon(void)
789{
790 /* Enable xmon hooks if needed */
791 if (!xmon_on) {
792 printf("xmon: Enabling debugger hooks\n");
793 xmon_on = 1;
794 }
795}
796
797static struct bpt *at_breakpoint(unsigned long pc)
798{
799 int i;
800 struct bpt *bp;
801
802 bp = bpts;
803 for (i = 0; i < NBPTS; ++i, ++bp)
804 if (bp->enabled && pc == bp->address)
805 return bp;
806 return NULL;
807}
808
809static struct bpt *in_breakpoint_table(unsigned long nip, unsigned long *offp)
810{
811 unsigned long off;
812
813 off = nip - (unsigned long) bpts;
814 if (off >= sizeof(bpts))
815 return NULL;
816 off %= sizeof(struct bpt);
817 if (off != offsetof(struct bpt, instr[0])
818 && off != offsetof(struct bpt, instr[1]))
819 return NULL;
820 *offp = off - offsetof(struct bpt, instr[0]);
821 return (struct bpt *) (nip - off);
822}
823
824static struct bpt *new_breakpoint(unsigned long a)
825{
826 struct bpt *bp;
827
828 a &= ~3UL;
829 bp = at_breakpoint(a);
830 if (bp)
831 return bp;
832
833 for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
834 if (!bp->enabled && atomic_read(&bp->ref_count) == 0) {
835 bp->address = a;
836 bp->instr[1] = bpinstr;
837 store_inst(&bp->instr[1]);
838 return bp;
839 }
840 }
841
842 printf("Sorry, no free breakpoints. Please clear one first.\n");
843 return NULL;
844}
845
846static void insert_bpts(void)
847{
848 int i;
849 struct bpt *bp;
850
851 bp = bpts;
852 for (i = 0; i < NBPTS; ++i, ++bp) {
853 if ((bp->enabled & (BP_TRAP|BP_CIABR)) == 0)
854 continue;
855 if (mread(bp->address, &bp->instr[0], 4) != 4) {
856 printf("Couldn't read instruction at %lx, "
857 "disabling breakpoint there\n", bp->address);
858 bp->enabled = 0;
859 continue;
860 }
861 if (IS_MTMSRD(bp->instr[0]) || IS_RFID(bp->instr[0])) {
862 printf("Breakpoint at %lx is on an mtmsrd or rfid "
863 "instruction, disabling it\n", bp->address);
864 bp->enabled = 0;
865 continue;
866 }
867 store_inst(&bp->instr[0]);
868 if (bp->enabled & BP_CIABR)
869 continue;
870 if (patch_instruction((unsigned int *)bp->address,
871 bpinstr) != 0) {
872 printf("Couldn't write instruction at %lx, "
873 "disabling breakpoint there\n", bp->address);
874 bp->enabled &= ~BP_TRAP;
875 continue;
876 }
877 store_inst((void *)bp->address);
878 }
879}
880
881static void insert_cpu_bpts(void)
882{
883 struct arch_hw_breakpoint brk;
884
885 if (dabr.enabled) {
886 brk.address = dabr.address;
887 brk.type = (dabr.enabled & HW_BRK_TYPE_DABR) | HW_BRK_TYPE_PRIV_ALL;
888 brk.len = 8;
889 __set_breakpoint(&brk);
890 }
891
892 if (iabr)
893 set_ciabr(iabr->address);
894}
895
896static void remove_bpts(void)
897{
898 int i;
899 struct bpt *bp;
900 unsigned instr;
901
902 bp = bpts;
903 for (i = 0; i < NBPTS; ++i, ++bp) {
904 if ((bp->enabled & (BP_TRAP|BP_CIABR)) != BP_TRAP)
905 continue;
906 if (mread(bp->address, &instr, 4) == 4
907 && instr == bpinstr
908 && patch_instruction(
909 (unsigned int *)bp->address, bp->instr[0]) != 0)
910 printf("Couldn't remove breakpoint at %lx\n",
911 bp->address);
912 else
913 store_inst((void *)bp->address);
914 }
915}
916
917static void remove_cpu_bpts(void)
918{
919 hw_breakpoint_disable();
920 write_ciabr(0);
921}
922
923/* Based on uptime_proc_show(). */
924static void
925show_uptime(void)
926{
927 struct timespec64 uptime;
928
929 if (setjmp(bus_error_jmp) == 0) {
930 catch_memory_errors = 1;
931 sync();
932
933 ktime_get_coarse_boottime_ts64(&uptime);
934 printf("Uptime: %lu.%.2lu seconds\n", (unsigned long)uptime.tv_sec,
935 ((unsigned long)uptime.tv_nsec / (NSEC_PER_SEC/100)));
936
937 sync();
938 __delay(200); \
939 }
940 catch_memory_errors = 0;
941}
942
943static void set_lpp_cmd(void)
944{
945 unsigned long lpp;
946
947 if (!scanhex(&lpp)) {
948 printf("Invalid number.\n");
949 lpp = 0;
950 }
951 xmon_set_pagination_lpp(lpp);
952}
953/* Command interpreting routine */
954static char *last_cmd;
955
956static int
957cmds(struct pt_regs *excp)
958{
959 int cmd = 0;
960
961 last_cmd = NULL;
962 xmon_regs = excp;
963
964 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
965
966 for(;;) {
967#ifdef CONFIG_SMP
968 printf("%x:", smp_processor_id());
969#endif /* CONFIG_SMP */
970 printf("mon> ");
971 flush_input();
972 termch = 0;
973 cmd = skipbl();
974 if( cmd == '\n' ) {
975 if (last_cmd == NULL)
976 continue;
977 take_input(last_cmd);
978 last_cmd = NULL;
979 cmd = inchar();
980 }
981 switch (cmd) {
982 case 'm':
983 cmd = inchar();
984 switch (cmd) {
985 case 'm':
986 case 's':
987 case 'd':
988 memops(cmd);
989 break;
990 case 'l':
991 memlocate();
992 break;
993 case 'z':
994 memzcan();
995 break;
996 case 'i':
997 show_mem(0, NULL);
998 break;
999 default:
1000 termch = cmd;
1001 memex();
1002 }
1003 break;
1004 case 'd':
1005 dump();
1006 break;
1007 case 'l':
1008 symbol_lookup();
1009 break;
1010 case 'r':
1011 prregs(excp); /* print regs */
1012 break;
1013 case 'e':
1014 excprint(excp);
1015 break;
1016 case 'S':
1017 super_regs();
1018 break;
1019 case 't':
1020 backtrace(excp);
1021 break;
1022 case 'f':
1023 cacheflush();
1024 break;
1025 case 's':
1026 if (do_spu_cmd() == 0)
1027 break;
1028 if (do_step(excp))
1029 return cmd;
1030 break;
1031 case 'x':
1032 case 'X':
1033 if (tracing_enabled)
1034 tracing_on();
1035 return cmd;
1036 case EOF:
1037 printf(" <no input ...>\n");
1038 mdelay(2000);
1039 return cmd;
1040 case '?':
1041 xmon_puts(help_string);
1042 break;
1043 case '#':
1044 set_lpp_cmd();
1045 break;
1046 case 'b':
1047 bpt_cmds();
1048 break;
1049 case 'C':
1050 csum();
1051 break;
1052 case 'c':
1053 if (cpu_cmd())
1054 return 0;
1055 break;
1056 case 'z':
1057 bootcmds();
1058 break;
1059 case 'p':
1060 proccall();
1061 break;
1062 case 'P':
1063 show_tasks();
1064 break;
1065#ifdef CONFIG_PPC_STD_MMU
1066 case 'u':
1067 dump_segments();
1068 break;
1069#elif defined(CONFIG_44x)
1070 case 'u':
1071 dump_tlb_44x();
1072 break;
1073#elif defined(CONFIG_PPC_BOOK3E)
1074 case 'u':
1075 dump_tlb_book3e();
1076 break;
1077#endif
1078 case 'U':
1079 show_uptime();
1080 break;
1081 default:
1082 printf("Unrecognized command: ");
1083 do {
1084 if (' ' < cmd && cmd <= '~')
1085 putchar(cmd);
1086 else
1087 printf("\\x%x", cmd);
1088 cmd = inchar();
1089 } while (cmd != '\n');
1090 printf(" (type ? for help)\n");
1091 break;
1092 }
1093 }
1094}
1095
1096#ifdef CONFIG_BOOKE
1097static int do_step(struct pt_regs *regs)
1098{
1099 regs->msr |= MSR_DE;
1100 mtspr(SPRN_DBCR0, mfspr(SPRN_DBCR0) | DBCR0_IC | DBCR0_IDM);
1101 return 1;
1102}
1103#else
1104/*
1105 * Step a single instruction.
1106 * Some instructions we emulate, others we execute with MSR_SE set.
1107 */
1108static int do_step(struct pt_regs *regs)
1109{
1110 unsigned int instr;
1111 int stepped;
1112
1113 force_enable_xmon();
1114 /* check we are in 64-bit kernel mode, translation enabled */
1115 if ((regs->msr & (MSR_64BIT|MSR_PR|MSR_IR)) == (MSR_64BIT|MSR_IR)) {
1116 if (mread(regs->nip, &instr, 4) == 4) {
1117 stepped = emulate_step(regs, instr);
1118 if (stepped < 0) {
1119 printf("Couldn't single-step %s instruction\n",
1120 (IS_RFID(instr)? "rfid": "mtmsrd"));
1121 return 0;
1122 }
1123 if (stepped > 0) {
1124 regs->trap = 0xd00 | (regs->trap & 1);
1125 printf("stepped to ");
1126 xmon_print_symbol(regs->nip, " ", "\n");
1127 ppc_inst_dump(regs->nip, 1, 0);
1128 return 0;
1129 }
1130 }
1131 }
1132 regs->msr |= MSR_SE;
1133 return 1;
1134}
1135#endif
1136
1137static void bootcmds(void)
1138{
1139 int cmd;
1140
1141 cmd = inchar();
1142 if (cmd == 'r')
1143 ppc_md.restart(NULL);
1144 else if (cmd == 'h')
1145 ppc_md.halt();
1146 else if (cmd == 'p')
1147 if (pm_power_off)
1148 pm_power_off();
1149}
1150
1151static int cpu_cmd(void)
1152{
1153#ifdef CONFIG_SMP
1154 unsigned long cpu, first_cpu, last_cpu;
1155 int timeout;
1156
1157 if (!scanhex(&cpu)) {
1158 /* print cpus waiting or in xmon */
1159 printf("cpus stopped:");
1160 last_cpu = first_cpu = NR_CPUS;
1161 for_each_possible_cpu(cpu) {
1162 if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
1163 if (cpu == last_cpu + 1) {
1164 last_cpu = cpu;
1165 } else {
1166 if (last_cpu != first_cpu)
1167 printf("-0x%lx", last_cpu);
1168 last_cpu = first_cpu = cpu;
1169 printf(" 0x%lx", cpu);
1170 }
1171 }
1172 }
1173 if (last_cpu != first_cpu)
1174 printf("-0x%lx", last_cpu);
1175 printf("\n");
1176 return 0;
1177 }
1178 /* try to switch to cpu specified */
1179 if (!cpumask_test_cpu(cpu, &cpus_in_xmon)) {
1180 printf("cpu 0x%lx isn't in xmon\n", cpu);
1181#ifdef CONFIG_PPC64
1182 printf("backtrace of paca[0x%lx].saved_r1 (possibly stale):\n", cpu);
1183 xmon_show_stack(paca_ptrs[cpu]->saved_r1, 0, 0);
1184#endif
1185 return 0;
1186 }
1187 xmon_taken = 0;
1188 mb();
1189 xmon_owner = cpu;
1190 timeout = 10000000;
1191 while (!xmon_taken) {
1192 if (--timeout == 0) {
1193 if (test_and_set_bit(0, &xmon_taken))
1194 break;
1195 /* take control back */
1196 mb();
1197 xmon_owner = smp_processor_id();
1198 printf("cpu 0x%lx didn't take control\n", cpu);
1199 return 0;
1200 }
1201 barrier();
1202 }
1203 return 1;
1204#else
1205 return 0;
1206#endif /* CONFIG_SMP */
1207}
1208
1209static unsigned short fcstab[256] = {
1210 0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
1211 0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
1212 0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
1213 0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
1214 0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
1215 0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
1216 0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
1217 0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
1218 0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
1219 0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
1220 0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
1221 0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
1222 0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
1223 0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
1224 0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
1225 0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
1226 0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
1227 0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
1228 0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
1229 0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
1230 0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
1231 0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
1232 0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
1233 0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
1234 0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
1235 0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
1236 0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
1237 0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
1238 0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
1239 0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
1240 0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
1241 0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
1242};
1243
1244#define FCS(fcs, c) (((fcs) >> 8) ^ fcstab[((fcs) ^ (c)) & 0xff])
1245
1246static void
1247csum(void)
1248{
1249 unsigned int i;
1250 unsigned short fcs;
1251 unsigned char v;
1252
1253 if (!scanhex(&adrs))
1254 return;
1255 if (!scanhex(&ncsum))
1256 return;
1257 fcs = 0xffff;
1258 for (i = 0; i < ncsum; ++i) {
1259 if (mread(adrs+i, &v, 1) == 0) {
1260 printf("csum stopped at "REG"\n", adrs+i);
1261 break;
1262 }
1263 fcs = FCS(fcs, v);
1264 }
1265 printf("%x\n", fcs);
1266}
1267
1268/*
1269 * Check if this is a suitable place to put a breakpoint.
1270 */
1271static long check_bp_loc(unsigned long addr)
1272{
1273 unsigned int instr;
1274
1275 addr &= ~3;
1276 if (!is_kernel_addr(addr)) {
1277 printf("Breakpoints may only be placed at kernel addresses\n");
1278 return 0;
1279 }
1280 if (!mread(addr, &instr, sizeof(instr))) {
1281 printf("Can't read instruction at address %lx\n", addr);
1282 return 0;
1283 }
1284 if (IS_MTMSRD(instr) || IS_RFID(instr)) {
1285 printf("Breakpoints may not be placed on mtmsrd or rfid "
1286 "instructions\n");
1287 return 0;
1288 }
1289 return 1;
1290}
1291
1292static char *breakpoint_help_string =
1293 "Breakpoint command usage:\n"
1294 "b show breakpoints\n"
1295 "b <addr> [cnt] set breakpoint at given instr addr\n"
1296 "bc clear all breakpoints\n"
1297 "bc <n/addr> clear breakpoint number n or at addr\n"
1298 "bi <addr> [cnt] set hardware instr breakpoint (POWER8 only)\n"
1299 "bd <addr> [cnt] set hardware data breakpoint\n"
1300 "";
1301
1302static void
1303bpt_cmds(void)
1304{
1305 int cmd;
1306 unsigned long a;
1307 int i;
1308 struct bpt *bp;
1309
1310 cmd = inchar();
1311 switch (cmd) {
1312#ifndef CONFIG_PPC_8xx
1313 static const char badaddr[] = "Only kernel addresses are permitted for breakpoints\n";
1314 int mode;
1315 case 'd': /* bd - hardware data breakpoint */
1316 if (!ppc_breakpoint_available()) {
1317 printf("Hardware data breakpoint not supported on this cpu\n");
1318 break;
1319 }
1320 mode = 7;
1321 cmd = inchar();
1322 if (cmd == 'r')
1323 mode = 5;
1324 else if (cmd == 'w')
1325 mode = 6;
1326 else
1327 termch = cmd;
1328 dabr.address = 0;
1329 dabr.enabled = 0;
1330 if (scanhex(&dabr.address)) {
1331 if (!is_kernel_addr(dabr.address)) {
1332 printf(badaddr);
1333 break;
1334 }
1335 dabr.address &= ~HW_BRK_TYPE_DABR;
1336 dabr.enabled = mode | BP_DABR;
1337 }
1338
1339 force_enable_xmon();
1340 break;
1341
1342 case 'i': /* bi - hardware instr breakpoint */
1343 if (!cpu_has_feature(CPU_FTR_ARCH_207S)) {
1344 printf("Hardware instruction breakpoint "
1345 "not supported on this cpu\n");
1346 break;
1347 }
1348 if (iabr) {
1349 iabr->enabled &= ~BP_CIABR;
1350 iabr = NULL;
1351 }
1352 if (!scanhex(&a))
1353 break;
1354 if (!check_bp_loc(a))
1355 break;
1356 bp = new_breakpoint(a);
1357 if (bp != NULL) {
1358 bp->enabled |= BP_CIABR;
1359 iabr = bp;
1360 force_enable_xmon();
1361 }
1362 break;
1363#endif
1364
1365 case 'c':
1366 if (!scanhex(&a)) {
1367 /* clear all breakpoints */
1368 for (i = 0; i < NBPTS; ++i)
1369 bpts[i].enabled = 0;
1370 iabr = NULL;
1371 dabr.enabled = 0;
1372 printf("All breakpoints cleared\n");
1373 break;
1374 }
1375
1376 if (a <= NBPTS && a >= 1) {
1377 /* assume a breakpoint number */
1378 bp = &bpts[a-1]; /* bp nums are 1 based */
1379 } else {
1380 /* assume a breakpoint address */
1381 bp = at_breakpoint(a);
1382 if (bp == NULL) {
1383 printf("No breakpoint at %lx\n", a);
1384 break;
1385 }
1386 }
1387
1388 printf("Cleared breakpoint %tx (", BP_NUM(bp));
1389 xmon_print_symbol(bp->address, " ", ")\n");
1390 bp->enabled = 0;
1391 break;
1392
1393 default:
1394 termch = cmd;
1395 cmd = skipbl();
1396 if (cmd == '?') {
1397 printf(breakpoint_help_string);
1398 break;
1399 }
1400 termch = cmd;
1401 if (!scanhex(&a)) {
1402 /* print all breakpoints */
1403 printf(" type address\n");
1404 if (dabr.enabled) {
1405 printf(" data "REG" [", dabr.address);
1406 if (dabr.enabled & 1)
1407 printf("r");
1408 if (dabr.enabled & 2)
1409 printf("w");
1410 printf("]\n");
1411 }
1412 for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
1413 if (!bp->enabled)
1414 continue;
1415 printf("%tx %s ", BP_NUM(bp),
1416 (bp->enabled & BP_CIABR) ? "inst": "trap");
1417 xmon_print_symbol(bp->address, " ", "\n");
1418 }
1419 break;
1420 }
1421
1422 if (!check_bp_loc(a))
1423 break;
1424 bp = new_breakpoint(a);
1425 if (bp != NULL) {
1426 bp->enabled |= BP_TRAP;
1427 force_enable_xmon();
1428 }
1429 break;
1430 }
1431}
1432
1433/* Very cheap human name for vector lookup. */
1434static
1435const char *getvecname(unsigned long vec)
1436{
1437 char *ret;
1438
1439 switch (vec) {
1440 case 0x100: ret = "(System Reset)"; break;
1441 case 0x200: ret = "(Machine Check)"; break;
1442 case 0x300: ret = "(Data Access)"; break;
1443 case 0x380:
1444 if (radix_enabled())
1445 ret = "(Data Access Out of Range)";
1446 else
1447 ret = "(Data SLB Access)";
1448 break;
1449 case 0x400: ret = "(Instruction Access)"; break;
1450 case 0x480:
1451 if (radix_enabled())
1452 ret = "(Instruction Access Out of Range)";
1453 else
1454 ret = "(Instruction SLB Access)";
1455 break;
1456 case 0x500: ret = "(Hardware Interrupt)"; break;
1457 case 0x600: ret = "(Alignment)"; break;
1458 case 0x700: ret = "(Program Check)"; break;
1459 case 0x800: ret = "(FPU Unavailable)"; break;
1460 case 0x900: ret = "(Decrementer)"; break;
1461 case 0x980: ret = "(Hypervisor Decrementer)"; break;
1462 case 0xa00: ret = "(Doorbell)"; break;
1463 case 0xc00: ret = "(System Call)"; break;
1464 case 0xd00: ret = "(Single Step)"; break;
1465 case 0xe40: ret = "(Emulation Assist)"; break;
1466 case 0xe60: ret = "(HMI)"; break;
1467 case 0xe80: ret = "(Hypervisor Doorbell)"; break;
1468 case 0xf00: ret = "(Performance Monitor)"; break;
1469 case 0xf20: ret = "(Altivec Unavailable)"; break;
1470 case 0x1300: ret = "(Instruction Breakpoint)"; break;
1471 case 0x1500: ret = "(Denormalisation)"; break;
1472 case 0x1700: ret = "(Altivec Assist)"; break;
1473 default: ret = "";
1474 }
1475 return ret;
1476}
1477
1478static void get_function_bounds(unsigned long pc, unsigned long *startp,
1479 unsigned long *endp)
1480{
1481 unsigned long size, offset;
1482 const char *name;
1483
1484 *startp = *endp = 0;
1485 if (pc == 0)
1486 return;
1487 if (setjmp(bus_error_jmp) == 0) {
1488 catch_memory_errors = 1;
1489 sync();
1490 name = kallsyms_lookup(pc, &size, &offset, NULL, tmpstr);
1491 if (name != NULL) {
1492 *startp = pc - offset;
1493 *endp = pc - offset + size;
1494 }
1495 sync();
1496 }
1497 catch_memory_errors = 0;
1498}
1499
1500#define LRSAVE_OFFSET (STACK_FRAME_LR_SAVE * sizeof(unsigned long))
1501#define MARKER_OFFSET (STACK_FRAME_MARKER * sizeof(unsigned long))
1502
1503static void xmon_show_stack(unsigned long sp, unsigned long lr,
1504 unsigned long pc)
1505{
1506 int max_to_print = 64;
1507 unsigned long ip;
1508 unsigned long newsp;
1509 unsigned long marker;
1510 struct pt_regs regs;
1511
1512 while (max_to_print--) {
1513 if (!is_kernel_addr(sp)) {
1514 if (sp != 0)
1515 printf("SP (%lx) is in userspace\n", sp);
1516 break;
1517 }
1518
1519 if (!mread(sp + LRSAVE_OFFSET, &ip, sizeof(unsigned long))
1520 || !mread(sp, &newsp, sizeof(unsigned long))) {
1521 printf("Couldn't read stack frame at %lx\n", sp);
1522 break;
1523 }
1524
1525 /*
1526 * For the first stack frame, try to work out if
1527 * LR and/or the saved LR value in the bottommost
1528 * stack frame are valid.
1529 */
1530 if ((pc | lr) != 0) {
1531 unsigned long fnstart, fnend;
1532 unsigned long nextip;
1533 int printip = 1;
1534
1535 get_function_bounds(pc, &fnstart, &fnend);
1536 nextip = 0;
1537 if (newsp > sp)
1538 mread(newsp + LRSAVE_OFFSET, &nextip,
1539 sizeof(unsigned long));
1540 if (lr == ip) {
1541 if (!is_kernel_addr(lr)
1542 || (fnstart <= lr && lr < fnend))
1543 printip = 0;
1544 } else if (lr == nextip) {
1545 printip = 0;
1546 } else if (is_kernel_addr(lr)
1547 && !(fnstart <= lr && lr < fnend)) {
1548 printf("[link register ] ");
1549 xmon_print_symbol(lr, " ", "\n");
1550 }
1551 if (printip) {
1552 printf("["REG"] ", sp);
1553 xmon_print_symbol(ip, " ", " (unreliable)\n");
1554 }
1555 pc = lr = 0;
1556
1557 } else {
1558 printf("["REG"] ", sp);
1559 xmon_print_symbol(ip, " ", "\n");
1560 }
1561
1562 /* Look for "regshere" marker to see if this is
1563 an exception frame. */
1564 if (mread(sp + MARKER_OFFSET, &marker, sizeof(unsigned long))
1565 && marker == STACK_FRAME_REGS_MARKER) {
1566 if (mread(sp + STACK_FRAME_OVERHEAD, &regs, sizeof(regs))
1567 != sizeof(regs)) {
1568 printf("Couldn't read registers at %lx\n",
1569 sp + STACK_FRAME_OVERHEAD);
1570 break;
1571 }
1572 printf("--- Exception: %lx %s at ", regs.trap,
1573 getvecname(TRAP(&regs)));
1574 pc = regs.nip;
1575 lr = regs.link;
1576 xmon_print_symbol(pc, " ", "\n");
1577 }
1578
1579 if (newsp == 0)
1580 break;
1581
1582 sp = newsp;
1583 }
1584}
1585
1586static void backtrace(struct pt_regs *excp)
1587{
1588 unsigned long sp;
1589
1590 if (scanhex(&sp))
1591 xmon_show_stack(sp, 0, 0);
1592 else
1593 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
1594 scannl();
1595}
1596
1597static void print_bug_trap(struct pt_regs *regs)
1598{
1599#ifdef CONFIG_BUG
1600 const struct bug_entry *bug;
1601 unsigned long addr;
1602
1603 if (regs->msr & MSR_PR)
1604 return; /* not in kernel */
1605 addr = regs->nip; /* address of trap instruction */
1606 if (!is_kernel_addr(addr))
1607 return;
1608 bug = find_bug(regs->nip);
1609 if (bug == NULL)
1610 return;
1611 if (is_warning_bug(bug))
1612 return;
1613
1614#ifdef CONFIG_DEBUG_BUGVERBOSE
1615 printf("kernel BUG at %s:%u!\n",
1616 bug->file, bug->line);
1617#else
1618 printf("kernel BUG at %px!\n", (void *)bug->bug_addr);
1619#endif
1620#endif /* CONFIG_BUG */
1621}
1622
1623static void excprint(struct pt_regs *fp)
1624{
1625 unsigned long trap;
1626
1627#ifdef CONFIG_SMP
1628 printf("cpu 0x%x: ", smp_processor_id());
1629#endif /* CONFIG_SMP */
1630
1631 trap = TRAP(fp);
1632 printf("Vector: %lx %s at [%px]\n", fp->trap, getvecname(trap), fp);
1633 printf(" pc: ");
1634 xmon_print_symbol(fp->nip, ": ", "\n");
1635
1636 printf(" lr: ");
1637 xmon_print_symbol(fp->link, ": ", "\n");
1638
1639 printf(" sp: %lx\n", fp->gpr[1]);
1640 printf(" msr: %lx\n", fp->msr);
1641
1642 if (trap == 0x300 || trap == 0x380 || trap == 0x600 || trap == 0x200) {
1643 printf(" dar: %lx\n", fp->dar);
1644 if (trap != 0x380)
1645 printf(" dsisr: %lx\n", fp->dsisr);
1646 }
1647
1648 printf(" current = 0x%px\n", current);
1649#ifdef CONFIG_PPC64
1650 printf(" paca = 0x%px\t irqmask: 0x%02x\t irq_happened: 0x%02x\n",
1651 local_paca, local_paca->irq_soft_mask, local_paca->irq_happened);
1652#endif
1653 if (current) {
1654 printf(" pid = %d, comm = %s\n",
1655 current->pid, current->comm);
1656 }
1657
1658 if (trap == 0x700)
1659 print_bug_trap(fp);
1660
1661 printf(linux_banner);
1662}
1663
1664static void prregs(struct pt_regs *fp)
1665{
1666 int n, trap;
1667 unsigned long base;
1668 struct pt_regs regs;
1669
1670 if (scanhex(&base)) {
1671 if (setjmp(bus_error_jmp) == 0) {
1672 catch_memory_errors = 1;
1673 sync();
1674 regs = *(struct pt_regs *)base;
1675 sync();
1676 __delay(200);
1677 } else {
1678 catch_memory_errors = 0;
1679 printf("*** Error reading registers from "REG"\n",
1680 base);
1681 return;
1682 }
1683 catch_memory_errors = 0;
1684 fp = &regs;
1685 }
1686
1687#ifdef CONFIG_PPC64
1688 if (FULL_REGS(fp)) {
1689 for (n = 0; n < 16; ++n)
1690 printf("R%.2d = "REG" R%.2d = "REG"\n",
1691 n, fp->gpr[n], n+16, fp->gpr[n+16]);
1692 } else {
1693 for (n = 0; n < 7; ++n)
1694 printf("R%.2d = "REG" R%.2d = "REG"\n",
1695 n, fp->gpr[n], n+7, fp->gpr[n+7]);
1696 }
1697#else
1698 for (n = 0; n < 32; ++n) {
1699 printf("R%.2d = %.8lx%s", n, fp->gpr[n],
1700 (n & 3) == 3? "\n": " ");
1701 if (n == 12 && !FULL_REGS(fp)) {
1702 printf("\n");
1703 break;
1704 }
1705 }
1706#endif
1707 printf("pc = ");
1708 xmon_print_symbol(fp->nip, " ", "\n");
1709 if (TRAP(fp) != 0xc00 && cpu_has_feature(CPU_FTR_CFAR)) {
1710 printf("cfar= ");
1711 xmon_print_symbol(fp->orig_gpr3, " ", "\n");
1712 }
1713 printf("lr = ");
1714 xmon_print_symbol(fp->link, " ", "\n");
1715 printf("msr = "REG" cr = %.8lx\n", fp->msr, fp->ccr);
1716 printf("ctr = "REG" xer = "REG" trap = %4lx\n",
1717 fp->ctr, fp->xer, fp->trap);
1718 trap = TRAP(fp);
1719 if (trap == 0x300 || trap == 0x380 || trap == 0x600)
1720 printf("dar = "REG" dsisr = %.8lx\n", fp->dar, fp->dsisr);
1721}
1722
1723static void cacheflush(void)
1724{
1725 int cmd;
1726 unsigned long nflush;
1727
1728 cmd = inchar();
1729 if (cmd != 'i')
1730 termch = cmd;
1731 scanhex((void *)&adrs);
1732 if (termch != '\n')
1733 termch = 0;
1734 nflush = 1;
1735 scanhex(&nflush);
1736 nflush = (nflush + L1_CACHE_BYTES - 1) / L1_CACHE_BYTES;
1737 if (setjmp(bus_error_jmp) == 0) {
1738 catch_memory_errors = 1;
1739 sync();
1740
1741 if (cmd != 'i') {
1742 for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1743 cflush((void *) adrs);
1744 } else {
1745 for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1746 cinval((void *) adrs);
1747 }
1748 sync();
1749 /* wait a little while to see if we get a machine check */
1750 __delay(200);
1751 }
1752 catch_memory_errors = 0;
1753}
1754
1755extern unsigned long xmon_mfspr(int spr, unsigned long default_value);
1756extern void xmon_mtspr(int spr, unsigned long value);
1757
1758static int
1759read_spr(int n, unsigned long *vp)
1760{
1761 unsigned long ret = -1UL;
1762 int ok = 0;
1763
1764 if (setjmp(bus_error_jmp) == 0) {
1765 catch_spr_faults = 1;
1766 sync();
1767
1768 ret = xmon_mfspr(n, *vp);
1769
1770 sync();
1771 *vp = ret;
1772 ok = 1;
1773 }
1774 catch_spr_faults = 0;
1775
1776 return ok;
1777}
1778
1779static void
1780write_spr(int n, unsigned long val)
1781{
1782 if (setjmp(bus_error_jmp) == 0) {
1783 catch_spr_faults = 1;
1784 sync();
1785
1786 xmon_mtspr(n, val);
1787
1788 sync();
1789 } else {
1790 printf("SPR 0x%03x (%4d) Faulted during write\n", n, n);
1791 }
1792 catch_spr_faults = 0;
1793}
1794
1795static void dump_206_sprs(void)
1796{
1797#ifdef CONFIG_PPC64
1798 if (!cpu_has_feature(CPU_FTR_ARCH_206))
1799 return;
1800
1801 /* Actually some of these pre-date 2.06, but whatevs */
1802
1803 printf("srr0 = %.16lx srr1 = %.16lx dsisr = %.8lx\n",
1804 mfspr(SPRN_SRR0), mfspr(SPRN_SRR1), mfspr(SPRN_DSISR));
1805 printf("dscr = %.16lx ppr = %.16lx pir = %.8lx\n",
1806 mfspr(SPRN_DSCR), mfspr(SPRN_PPR), mfspr(SPRN_PIR));
1807 printf("amr = %.16lx uamor = %.16lx\n",
1808 mfspr(SPRN_AMR), mfspr(SPRN_UAMOR));
1809
1810 if (!(mfmsr() & MSR_HV))
1811 return;
1812
1813 printf("sdr1 = %.16lx hdar = %.16lx hdsisr = %.8lx\n",
1814 mfspr(SPRN_SDR1), mfspr(SPRN_HDAR), mfspr(SPRN_HDSISR));
1815 printf("hsrr0 = %.16lx hsrr1 = %.16lx hdec = %.16lx\n",
1816 mfspr(SPRN_HSRR0), mfspr(SPRN_HSRR1), mfspr(SPRN_HDEC));
1817 printf("lpcr = %.16lx pcr = %.16lx lpidr = %.8lx\n",
1818 mfspr(SPRN_LPCR), mfspr(SPRN_PCR), mfspr(SPRN_LPID));
1819 printf("hsprg0 = %.16lx hsprg1 = %.16lx amor = %.16lx\n",
1820 mfspr(SPRN_HSPRG0), mfspr(SPRN_HSPRG1), mfspr(SPRN_AMOR));
1821 printf("dabr = %.16lx dabrx = %.16lx\n",
1822 mfspr(SPRN_DABR), mfspr(SPRN_DABRX));
1823#endif
1824}
1825
1826static void dump_207_sprs(void)
1827{
1828#ifdef CONFIG_PPC64
1829 unsigned long msr;
1830
1831 if (!cpu_has_feature(CPU_FTR_ARCH_207S))
1832 return;
1833
1834 printf("dpdes = %.16lx tir = %.16lx cir = %.8lx\n",
1835 mfspr(SPRN_DPDES), mfspr(SPRN_TIR), mfspr(SPRN_CIR));
1836
1837 printf("fscr = %.16lx tar = %.16lx pspb = %.8lx\n",
1838 mfspr(SPRN_FSCR), mfspr(SPRN_TAR), mfspr(SPRN_PSPB));
1839
1840 msr = mfmsr();
1841 if (msr & MSR_TM) {
1842 /* Only if TM has been enabled in the kernel */
1843 printf("tfhar = %.16lx tfiar = %.16lx texasr = %.16lx\n",
1844 mfspr(SPRN_TFHAR), mfspr(SPRN_TFIAR),
1845 mfspr(SPRN_TEXASR));
1846 }
1847
1848 printf("mmcr0 = %.16lx mmcr1 = %.16lx mmcr2 = %.16lx\n",
1849 mfspr(SPRN_MMCR0), mfspr(SPRN_MMCR1), mfspr(SPRN_MMCR2));
1850 printf("pmc1 = %.8lx pmc2 = %.8lx pmc3 = %.8lx pmc4 = %.8lx\n",
1851 mfspr(SPRN_PMC1), mfspr(SPRN_PMC2),
1852 mfspr(SPRN_PMC3), mfspr(SPRN_PMC4));
1853 printf("mmcra = %.16lx siar = %.16lx pmc5 = %.8lx\n",
1854 mfspr(SPRN_MMCRA), mfspr(SPRN_SIAR), mfspr(SPRN_PMC5));
1855 printf("sdar = %.16lx sier = %.16lx pmc6 = %.8lx\n",
1856 mfspr(SPRN_SDAR), mfspr(SPRN_SIER), mfspr(SPRN_PMC6));
1857 printf("ebbhr = %.16lx ebbrr = %.16lx bescr = %.16lx\n",
1858 mfspr(SPRN_EBBHR), mfspr(SPRN_EBBRR), mfspr(SPRN_BESCR));
1859 printf("iamr = %.16lx\n", mfspr(SPRN_IAMR));
1860
1861 if (!(msr & MSR_HV))
1862 return;
1863
1864 printf("hfscr = %.16lx dhdes = %.16lx rpr = %.16lx\n",
1865 mfspr(SPRN_HFSCR), mfspr(SPRN_DHDES), mfspr(SPRN_RPR));
1866 printf("dawr = %.16lx dawrx = %.16lx ciabr = %.16lx\n",
1867 mfspr(SPRN_DAWR), mfspr(SPRN_DAWRX), mfspr(SPRN_CIABR));
1868#endif
1869}
1870
1871static void dump_300_sprs(void)
1872{
1873#ifdef CONFIG_PPC64
1874 bool hv = mfmsr() & MSR_HV;
1875
1876 if (!cpu_has_feature(CPU_FTR_ARCH_300))
1877 return;
1878
1879 printf("pidr = %.16lx tidr = %.16lx\n",
1880 mfspr(SPRN_PID), mfspr(SPRN_TIDR));
1881 printf("asdr = %.16lx psscr = %.16lx\n",
1882 mfspr(SPRN_ASDR), hv ? mfspr(SPRN_PSSCR)
1883 : mfspr(SPRN_PSSCR_PR));
1884
1885 if (!hv)
1886 return;
1887
1888 printf("ptcr = %.16lx\n",
1889 mfspr(SPRN_PTCR));
1890#endif
1891}
1892
1893static void dump_one_spr(int spr, bool show_unimplemented)
1894{
1895 unsigned long val;
1896
1897 val = 0xdeadbeef;
1898 if (!read_spr(spr, &val)) {
1899 printf("SPR 0x%03x (%4d) Faulted during read\n", spr, spr);
1900 return;
1901 }
1902
1903 if (val == 0xdeadbeef) {
1904 /* Looks like read was a nop, confirm */
1905 val = 0x0badcafe;
1906 if (!read_spr(spr, &val)) {
1907 printf("SPR 0x%03x (%4d) Faulted during read\n", spr, spr);
1908 return;
1909 }
1910
1911 if (val == 0x0badcafe) {
1912 if (show_unimplemented)
1913 printf("SPR 0x%03x (%4d) Unimplemented\n", spr, spr);
1914 return;
1915 }
1916 }
1917
1918 printf("SPR 0x%03x (%4d) = 0x%lx\n", spr, spr, val);
1919}
1920
1921static void super_regs(void)
1922{
1923 static unsigned long regno;
1924 int cmd;
1925 int spr;
1926
1927 cmd = skipbl();
1928
1929 switch (cmd) {
1930 case '\n': {
1931 unsigned long sp, toc;
1932 asm("mr %0,1" : "=r" (sp) :);
1933 asm("mr %0,2" : "=r" (toc) :);
1934
1935 printf("msr = "REG" sprg0 = "REG"\n",
1936 mfmsr(), mfspr(SPRN_SPRG0));
1937 printf("pvr = "REG" sprg1 = "REG"\n",
1938 mfspr(SPRN_PVR), mfspr(SPRN_SPRG1));
1939 printf("dec = "REG" sprg2 = "REG"\n",
1940 mfspr(SPRN_DEC), mfspr(SPRN_SPRG2));
1941 printf("sp = "REG" sprg3 = "REG"\n", sp, mfspr(SPRN_SPRG3));
1942 printf("toc = "REG" dar = "REG"\n", toc, mfspr(SPRN_DAR));
1943
1944 dump_206_sprs();
1945 dump_207_sprs();
1946 dump_300_sprs();
1947
1948 return;
1949 }
1950 case 'w': {
1951 unsigned long val;
1952 scanhex(&regno);
1953 val = 0;
1954 read_spr(regno, &val);
1955 scanhex(&val);
1956 write_spr(regno, val);
1957 dump_one_spr(regno, true);
1958 break;
1959 }
1960 case 'r':
1961 scanhex(&regno);
1962 dump_one_spr(regno, true);
1963 break;
1964 case 'a':
1965 /* dump ALL SPRs */
1966 for (spr = 1; spr < 1024; ++spr)
1967 dump_one_spr(spr, false);
1968 break;
1969 }
1970
1971 scannl();
1972}
1973
1974/*
1975 * Stuff for reading and writing memory safely
1976 */
1977static int
1978mread(unsigned long adrs, void *buf, int size)
1979{
1980 volatile int n;
1981 char *p, *q;
1982
1983 n = 0;
1984 if (setjmp(bus_error_jmp) == 0) {
1985 catch_memory_errors = 1;
1986 sync();
1987 p = (char *)adrs;
1988 q = (char *)buf;
1989 switch (size) {
1990 case 2:
1991 *(u16 *)q = *(u16 *)p;
1992 break;
1993 case 4:
1994 *(u32 *)q = *(u32 *)p;
1995 break;
1996 case 8:
1997 *(u64 *)q = *(u64 *)p;
1998 break;
1999 default:
2000 for( ; n < size; ++n) {
2001 *q++ = *p++;
2002 sync();
2003 }
2004 }
2005 sync();
2006 /* wait a little while to see if we get a machine check */
2007 __delay(200);
2008 n = size;
2009 }
2010 catch_memory_errors = 0;
2011 return n;
2012}
2013
2014static int
2015mwrite(unsigned long adrs, void *buf, int size)
2016{
2017 volatile int n;
2018 char *p, *q;
2019
2020 n = 0;
2021 if (setjmp(bus_error_jmp) == 0) {
2022 catch_memory_errors = 1;
2023 sync();
2024 p = (char *) adrs;
2025 q = (char *) buf;
2026 switch (size) {
2027 case 2:
2028 *(u16 *)p = *(u16 *)q;
2029 break;
2030 case 4:
2031 *(u32 *)p = *(u32 *)q;
2032 break;
2033 case 8:
2034 *(u64 *)p = *(u64 *)q;
2035 break;
2036 default:
2037 for ( ; n < size; ++n) {
2038 *p++ = *q++;
2039 sync();
2040 }
2041 }
2042 sync();
2043 /* wait a little while to see if we get a machine check */
2044 __delay(200);
2045 n = size;
2046 } else {
2047 printf("*** Error writing address "REG"\n", adrs + n);
2048 }
2049 catch_memory_errors = 0;
2050 return n;
2051}
2052
2053static int fault_type;
2054static int fault_except;
2055static char *fault_chars[] = { "--", "**", "##" };
2056
2057static int handle_fault(struct pt_regs *regs)
2058{
2059 fault_except = TRAP(regs);
2060 switch (TRAP(regs)) {
2061 case 0x200:
2062 fault_type = 0;
2063 break;
2064 case 0x300:
2065 case 0x380:
2066 fault_type = 1;
2067 break;
2068 default:
2069 fault_type = 2;
2070 }
2071
2072 longjmp(bus_error_jmp, 1);
2073
2074 return 0;
2075}
2076
2077#define SWAP(a, b, t) ((t) = (a), (a) = (b), (b) = (t))
2078
2079static void
2080byterev(unsigned char *val, int size)
2081{
2082 int t;
2083
2084 switch (size) {
2085 case 2:
2086 SWAP(val[0], val[1], t);
2087 break;
2088 case 4:
2089 SWAP(val[0], val[3], t);
2090 SWAP(val[1], val[2], t);
2091 break;
2092 case 8: /* is there really any use for this? */
2093 SWAP(val[0], val[7], t);
2094 SWAP(val[1], val[6], t);
2095 SWAP(val[2], val[5], t);
2096 SWAP(val[3], val[4], t);
2097 break;
2098 }
2099}
2100
2101static int brev;
2102static int mnoread;
2103
2104static char *memex_help_string =
2105 "Memory examine command usage:\n"
2106 "m [addr] [flags] examine/change memory\n"
2107 " addr is optional. will start where left off.\n"
2108 " flags may include chars from this set:\n"
2109 " b modify by bytes (default)\n"
2110 " w modify by words (2 byte)\n"
2111 " l modify by longs (4 byte)\n"
2112 " d modify by doubleword (8 byte)\n"
2113 " r toggle reverse byte order mode\n"
2114 " n do not read memory (for i/o spaces)\n"
2115 " . ok to read (default)\n"
2116 "NOTE: flags are saved as defaults\n"
2117 "";
2118
2119static char *memex_subcmd_help_string =
2120 "Memory examine subcommands:\n"
2121 " hexval write this val to current location\n"
2122 " 'string' write chars from string to this location\n"
2123 " ' increment address\n"
2124 " ^ decrement address\n"
2125 " / increment addr by 0x10. //=0x100, ///=0x1000, etc\n"
2126 " \\ decrement addr by 0x10. \\\\=0x100, \\\\\\=0x1000, etc\n"
2127 " ` clear no-read flag\n"
2128 " ; stay at this addr\n"
2129 " v change to byte mode\n"
2130 " w change to word (2 byte) mode\n"
2131 " l change to long (4 byte) mode\n"
2132 " u change to doubleword (8 byte) mode\n"
2133 " m addr change current addr\n"
2134 " n toggle no-read flag\n"
2135 " r toggle byte reverse flag\n"
2136 " < count back up count bytes\n"
2137 " > count skip forward count bytes\n"
2138 " x exit this mode\n"
2139 "";
2140
2141static void
2142memex(void)
2143{
2144 int cmd, inc, i, nslash;
2145 unsigned long n;
2146 unsigned char val[16];
2147
2148 scanhex((void *)&adrs);
2149 cmd = skipbl();
2150 if (cmd == '?') {
2151 printf(memex_help_string);
2152 return;
2153 } else {
2154 termch = cmd;
2155 }
2156 last_cmd = "m\n";
2157 while ((cmd = skipbl()) != '\n') {
2158 switch( cmd ){
2159 case 'b': size = 1; break;
2160 case 'w': size = 2; break;
2161 case 'l': size = 4; break;
2162 case 'd': size = 8; break;
2163 case 'r': brev = !brev; break;
2164 case 'n': mnoread = 1; break;
2165 case '.': mnoread = 0; break;
2166 }
2167 }
2168 if( size <= 0 )
2169 size = 1;
2170 else if( size > 8 )
2171 size = 8;
2172 for(;;){
2173 if (!mnoread)
2174 n = mread(adrs, val, size);
2175 printf(REG"%c", adrs, brev? 'r': ' ');
2176 if (!mnoread) {
2177 if (brev)
2178 byterev(val, size);
2179 putchar(' ');
2180 for (i = 0; i < n; ++i)
2181 printf("%.2x", val[i]);
2182 for (; i < size; ++i)
2183 printf("%s", fault_chars[fault_type]);
2184 }
2185 putchar(' ');
2186 inc = size;
2187 nslash = 0;
2188 for(;;){
2189 if( scanhex(&n) ){
2190 for (i = 0; i < size; ++i)
2191 val[i] = n >> (i * 8);
2192 if (!brev)
2193 byterev(val, size);
2194 mwrite(adrs, val, size);
2195 inc = size;
2196 }
2197 cmd = skipbl();
2198 if (cmd == '\n')
2199 break;
2200 inc = 0;
2201 switch (cmd) {
2202 case '\'':
2203 for(;;){
2204 n = inchar();
2205 if( n == '\\' )
2206 n = bsesc();
2207 else if( n == '\'' )
2208 break;
2209 for (i = 0; i < size; ++i)
2210 val[i] = n >> (i * 8);
2211 if (!brev)
2212 byterev(val, size);
2213 mwrite(adrs, val, size);
2214 adrs += size;
2215 }
2216 adrs -= size;
2217 inc = size;
2218 break;
2219 case ',':
2220 adrs += size;
2221 break;
2222 case '.':
2223 mnoread = 0;
2224 break;
2225 case ';':
2226 break;
2227 case 'x':
2228 case EOF:
2229 scannl();
2230 return;
2231 case 'b':
2232 case 'v':
2233 size = 1;
2234 break;
2235 case 'w':
2236 size = 2;
2237 break;
2238 case 'l':
2239 size = 4;
2240 break;
2241 case 'u':
2242 size = 8;
2243 break;
2244 case '^':
2245 adrs -= size;
2246 break;
2247 case '/':
2248 if (nslash > 0)
2249 adrs -= 1 << nslash;
2250 else
2251 nslash = 0;
2252 nslash += 4;
2253 adrs += 1 << nslash;
2254 break;
2255 case '\\':
2256 if (nslash < 0)
2257 adrs += 1 << -nslash;
2258 else
2259 nslash = 0;
2260 nslash -= 4;
2261 adrs -= 1 << -nslash;
2262 break;
2263 case 'm':
2264 scanhex((void *)&adrs);
2265 break;
2266 case 'n':
2267 mnoread = 1;
2268 break;
2269 case 'r':
2270 brev = !brev;
2271 break;
2272 case '<':
2273 n = size;
2274 scanhex(&n);
2275 adrs -= n;
2276 break;
2277 case '>':
2278 n = size;
2279 scanhex(&n);
2280 adrs += n;
2281 break;
2282 case '?':
2283 printf(memex_subcmd_help_string);
2284 break;
2285 }
2286 }
2287 adrs += inc;
2288 }
2289}
2290
2291static int
2292bsesc(void)
2293{
2294 int c;
2295
2296 c = inchar();
2297 switch( c ){
2298 case 'n': c = '\n'; break;
2299 case 'r': c = '\r'; break;
2300 case 'b': c = '\b'; break;
2301 case 't': c = '\t'; break;
2302 }
2303 return c;
2304}
2305
2306static void xmon_rawdump (unsigned long adrs, long ndump)
2307{
2308 long n, m, r, nr;
2309 unsigned char temp[16];
2310
2311 for (n = ndump; n > 0;) {
2312 r = n < 16? n: 16;
2313 nr = mread(adrs, temp, r);
2314 adrs += nr;
2315 for (m = 0; m < r; ++m) {
2316 if (m < nr)
2317 printf("%.2x", temp[m]);
2318 else
2319 printf("%s", fault_chars[fault_type]);
2320 }
2321 n -= r;
2322 if (nr < r)
2323 break;
2324 }
2325 printf("\n");
2326}
2327
2328static void dump_tracing(void)
2329{
2330 int c;
2331
2332 c = inchar();
2333 if (c == 'c')
2334 ftrace_dump(DUMP_ORIG);
2335 else
2336 ftrace_dump(DUMP_ALL);
2337}
2338
2339#ifdef CONFIG_PPC64
2340static void dump_one_paca(int cpu)
2341{
2342 struct paca_struct *p;
2343#ifdef CONFIG_PPC_BOOK3S_64
2344 int i = 0;
2345#endif
2346
2347 if (setjmp(bus_error_jmp) != 0) {
2348 printf("*** Error dumping paca for cpu 0x%x!\n", cpu);
2349 return;
2350 }
2351
2352 catch_memory_errors = 1;
2353 sync();
2354
2355 p = paca_ptrs[cpu];
2356
2357 printf("paca for cpu 0x%x @ %px:\n", cpu, p);
2358
2359 printf(" %-*s = %s\n", 25, "possible", cpu_possible(cpu) ? "yes" : "no");
2360 printf(" %-*s = %s\n", 25, "present", cpu_present(cpu) ? "yes" : "no");
2361 printf(" %-*s = %s\n", 25, "online", cpu_online(cpu) ? "yes" : "no");
2362
2363#define DUMP(paca, name, format) \
2364 printf(" %-*s = "format"\t(0x%lx)\n", 25, #name, 18, paca->name, \
2365 offsetof(struct paca_struct, name));
2366
2367 DUMP(p, lock_token, "%#-*x");
2368 DUMP(p, paca_index, "%#-*x");
2369 DUMP(p, kernel_toc, "%#-*llx");
2370 DUMP(p, kernelbase, "%#-*llx");
2371 DUMP(p, kernel_msr, "%#-*llx");
2372 DUMP(p, emergency_sp, "%-*px");
2373#ifdef CONFIG_PPC_BOOK3S_64
2374 DUMP(p, nmi_emergency_sp, "%-*px");
2375 DUMP(p, mc_emergency_sp, "%-*px");
2376 DUMP(p, in_nmi, "%#-*x");
2377 DUMP(p, in_mce, "%#-*x");
2378 DUMP(p, hmi_event_available, "%#-*x");
2379#endif
2380 DUMP(p, data_offset, "%#-*llx");
2381 DUMP(p, hw_cpu_id, "%#-*x");
2382 DUMP(p, cpu_start, "%#-*x");
2383 DUMP(p, kexec_state, "%#-*x");
2384#ifdef CONFIG_PPC_BOOK3S_64
2385 for (i = 0; i < SLB_NUM_BOLTED; i++) {
2386 u64 esid, vsid;
2387
2388 if (!p->slb_shadow_ptr)
2389 continue;
2390
2391 esid = be64_to_cpu(p->slb_shadow_ptr->save_area[i].esid);
2392 vsid = be64_to_cpu(p->slb_shadow_ptr->save_area[i].vsid);
2393
2394 if (esid || vsid) {
2395 printf(" %-*s[%d] = 0x%016llx 0x%016llx\n",
2396 22, "slb_shadow", i, esid, vsid);
2397 }
2398 }
2399 DUMP(p, vmalloc_sllp, "%#-*x");
2400 DUMP(p, slb_cache_ptr, "%#-*x");
2401 for (i = 0; i < SLB_CACHE_ENTRIES; i++)
2402 printf(" %-*s[%d] = 0x%016x\n",
2403 22, "slb_cache", i, p->slb_cache[i]);
2404
2405 DUMP(p, rfi_flush_fallback_area, "%-*px");
2406#endif
2407 DUMP(p, dscr_default, "%#-*llx");
2408#ifdef CONFIG_PPC_BOOK3E
2409 DUMP(p, pgd, "%-*px");
2410 DUMP(p, kernel_pgd, "%-*px");
2411 DUMP(p, tcd_ptr, "%-*px");
2412 DUMP(p, mc_kstack, "%-*px");
2413 DUMP(p, crit_kstack, "%-*px");
2414 DUMP(p, dbg_kstack, "%-*px");
2415#endif
2416 DUMP(p, __current, "%-*px");
2417 DUMP(p, kstack, "%#-*llx");
2418 printf(" %-*s = 0x%016llx\n", 25, "kstack_base", p->kstack & ~(THREAD_SIZE - 1));
2419 DUMP(p, stab_rr, "%#-*llx");
2420 DUMP(p, saved_r1, "%#-*llx");
2421 DUMP(p, trap_save, "%#-*x");
2422 DUMP(p, irq_soft_mask, "%#-*x");
2423 DUMP(p, irq_happened, "%#-*x");
2424 DUMP(p, io_sync, "%#-*x");
2425 DUMP(p, irq_work_pending, "%#-*x");
2426 DUMP(p, nap_state_lost, "%#-*x");
2427 DUMP(p, sprg_vdso, "%#-*llx");
2428
2429#ifdef CONFIG_PPC_TRANSACTIONAL_MEM
2430 DUMP(p, tm_scratch, "%#-*llx");
2431#endif
2432
2433#ifdef CONFIG_PPC_POWERNV
2434 DUMP(p, core_idle_state_ptr, "%-*px");
2435 DUMP(p, thread_idle_state, "%#-*x");
2436 DUMP(p, thread_mask, "%#-*x");
2437 DUMP(p, subcore_sibling_mask, "%#-*x");
2438 DUMP(p, requested_psscr, "%#-*llx");
2439 DUMP(p, stop_sprs.pid, "%#-*llx");
2440 DUMP(p, stop_sprs.ldbar, "%#-*llx");
2441 DUMP(p, stop_sprs.fscr, "%#-*llx");
2442 DUMP(p, stop_sprs.hfscr, "%#-*llx");
2443 DUMP(p, stop_sprs.mmcr1, "%#-*llx");
2444 DUMP(p, stop_sprs.mmcr2, "%#-*llx");
2445 DUMP(p, stop_sprs.mmcra, "%#-*llx");
2446 DUMP(p, dont_stop.counter, "%#-*x");
2447#endif
2448
2449 DUMP(p, accounting.utime, "%#-*lx");
2450 DUMP(p, accounting.stime, "%#-*lx");
2451 DUMP(p, accounting.utime_scaled, "%#-*lx");
2452 DUMP(p, accounting.starttime, "%#-*lx");
2453 DUMP(p, accounting.starttime_user, "%#-*lx");
2454 DUMP(p, accounting.startspurr, "%#-*lx");
2455 DUMP(p, accounting.utime_sspurr, "%#-*lx");
2456 DUMP(p, accounting.steal_time, "%#-*lx");
2457#undef DUMP
2458
2459 catch_memory_errors = 0;
2460 sync();
2461}
2462
2463static void dump_all_pacas(void)
2464{
2465 int cpu;
2466
2467 if (num_possible_cpus() == 0) {
2468 printf("No possible cpus, use 'dp #' to dump individual cpus\n");
2469 return;
2470 }
2471
2472 for_each_possible_cpu(cpu)
2473 dump_one_paca(cpu);
2474}
2475
2476static void dump_pacas(void)
2477{
2478 unsigned long num;
2479 int c;
2480
2481 c = inchar();
2482 if (c == 'a') {
2483 dump_all_pacas();
2484 return;
2485 }
2486
2487 termch = c; /* Put c back, it wasn't 'a' */
2488
2489 if (scanhex(&num))
2490 dump_one_paca(num);
2491 else
2492 dump_one_paca(xmon_owner);
2493}
2494#endif
2495
2496#ifdef CONFIG_PPC_POWERNV
2497static void dump_one_xive(int cpu)
2498{
2499 unsigned int hwid = get_hard_smp_processor_id(cpu);
2500 bool hv = cpu_has_feature(CPU_FTR_HVMODE);
2501
2502 if (hv) {
2503 opal_xive_dump(XIVE_DUMP_TM_HYP, hwid);
2504 opal_xive_dump(XIVE_DUMP_TM_POOL, hwid);
2505 opal_xive_dump(XIVE_DUMP_TM_OS, hwid);
2506 opal_xive_dump(XIVE_DUMP_TM_USER, hwid);
2507 opal_xive_dump(XIVE_DUMP_VP, hwid);
2508 opal_xive_dump(XIVE_DUMP_EMU_STATE, hwid);
2509 }
2510
2511 if (setjmp(bus_error_jmp) != 0) {
2512 catch_memory_errors = 0;
2513 printf("*** Error dumping xive on cpu %d\n", cpu);
2514 return;
2515 }
2516
2517 catch_memory_errors = 1;
2518 sync();
2519 xmon_xive_do_dump(cpu);
2520 sync();
2521 __delay(200);
2522 catch_memory_errors = 0;
2523}
2524
2525static void dump_all_xives(void)
2526{
2527 int cpu;
2528
2529 if (num_possible_cpus() == 0) {
2530 printf("No possible cpus, use 'dx #' to dump individual cpus\n");
2531 return;
2532 }
2533
2534 for_each_possible_cpu(cpu)
2535 dump_one_xive(cpu);
2536}
2537
2538static void dump_one_xive_irq(u32 num)
2539{
2540 s64 rc;
2541 __be64 vp;
2542 u8 prio;
2543 __be32 lirq;
2544
2545 rc = opal_xive_get_irq_config(num, &vp, &prio, &lirq);
2546 xmon_printf("IRQ 0x%x config: vp=0x%llx prio=%d lirq=0x%x (rc=%lld)\n",
2547 num, be64_to_cpu(vp), prio, be32_to_cpu(lirq), rc);
2548}
2549
2550static void dump_xives(void)
2551{
2552 unsigned long num;
2553 int c;
2554
2555 if (!xive_enabled()) {
2556 printf("Xive disabled on this system\n");
2557 return;
2558 }
2559
2560 c = inchar();
2561 if (c == 'a') {
2562 dump_all_xives();
2563 return;
2564 } else if (c == 'i') {
2565 if (scanhex(&num))
2566 dump_one_xive_irq(num);
2567 return;
2568 }
2569
2570 termch = c; /* Put c back, it wasn't 'a' */
2571
2572 if (scanhex(&num))
2573 dump_one_xive(num);
2574 else
2575 dump_one_xive(xmon_owner);
2576}
2577#endif /* CONFIG_PPC_POWERNV */
2578
2579static void dump_by_size(unsigned long addr, long count, int size)
2580{
2581 unsigned char temp[16];
2582 int i, j;
2583 u64 val;
2584
2585 count = ALIGN(count, 16);
2586
2587 for (i = 0; i < count; i += 16, addr += 16) {
2588 printf(REG, addr);
2589
2590 if (mread(addr, temp, 16) != 16) {
2591 printf("\nFaulted reading %d bytes from 0x"REG"\n", 16, addr);
2592 return;
2593 }
2594
2595 for (j = 0; j < 16; j += size) {
2596 putchar(' ');
2597 switch (size) {
2598 case 1: val = temp[j]; break;
2599 case 2: val = *(u16 *)&temp[j]; break;
2600 case 4: val = *(u32 *)&temp[j]; break;
2601 case 8: val = *(u64 *)&temp[j]; break;
2602 default: val = 0;
2603 }
2604
2605 printf("%0*llx", size * 2, val);
2606 }
2607 printf("\n");
2608 }
2609}
2610
2611static void
2612dump(void)
2613{
2614 static char last[] = { "d?\n" };
2615 int c;
2616
2617 c = inchar();
2618
2619#ifdef CONFIG_PPC64
2620 if (c == 'p') {
2621 xmon_start_pagination();
2622 dump_pacas();
2623 xmon_end_pagination();
2624 return;
2625 }
2626#endif
2627#ifdef CONFIG_PPC_POWERNV
2628 if (c == 'x') {
2629 xmon_start_pagination();
2630 dump_xives();
2631 xmon_end_pagination();
2632 return;
2633 }
2634#endif
2635
2636 if (c == 't') {
2637 dump_tracing();
2638 return;
2639 }
2640
2641 if (c == '\n')
2642 termch = c;
2643
2644 scanhex((void *)&adrs);
2645 if (termch != '\n')
2646 termch = 0;
2647 if (c == 'i') {
2648 scanhex(&nidump);
2649 if (nidump == 0)
2650 nidump = 16;
2651 else if (nidump > MAX_DUMP)
2652 nidump = MAX_DUMP;
2653 adrs += ppc_inst_dump(adrs, nidump, 1);
2654 last_cmd = "di\n";
2655 } else if (c == 'l') {
2656 dump_log_buf();
2657 } else if (c == 'o') {
2658 dump_opal_msglog();
2659 } else if (c == 'v') {
2660 /* dump virtual to physical translation */
2661 show_pte(adrs);
2662 } else if (c == 'r') {
2663 scanhex(&ndump);
2664 if (ndump == 0)
2665 ndump = 64;
2666 xmon_rawdump(adrs, ndump);
2667 adrs += ndump;
2668 last_cmd = "dr\n";
2669 } else {
2670 scanhex(&ndump);
2671 if (ndump == 0)
2672 ndump = 64;
2673 else if (ndump > MAX_DUMP)
2674 ndump = MAX_DUMP;
2675
2676 switch (c) {
2677 case '8':
2678 case '4':
2679 case '2':
2680 case '1':
2681 ndump = ALIGN(ndump, 16);
2682 dump_by_size(adrs, ndump, c - '0');
2683 last[1] = c;
2684 last_cmd = last;
2685 break;
2686 default:
2687 prdump(adrs, ndump);
2688 last_cmd = "d\n";
2689 }
2690
2691 adrs += ndump;
2692 }
2693}
2694
2695static void
2696prdump(unsigned long adrs, long ndump)
2697{
2698 long n, m, c, r, nr;
2699 unsigned char temp[16];
2700
2701 for (n = ndump; n > 0;) {
2702 printf(REG, adrs);
2703 putchar(' ');
2704 r = n < 16? n: 16;
2705 nr = mread(adrs, temp, r);
2706 adrs += nr;
2707 for (m = 0; m < r; ++m) {
2708 if ((m & (sizeof(long) - 1)) == 0 && m > 0)
2709 putchar(' ');
2710 if (m < nr)
2711 printf("%.2x", temp[m]);
2712 else
2713 printf("%s", fault_chars[fault_type]);
2714 }
2715 for (; m < 16; ++m) {
2716 if ((m & (sizeof(long) - 1)) == 0)
2717 putchar(' ');
2718 printf(" ");
2719 }
2720 printf(" |");
2721 for (m = 0; m < r; ++m) {
2722 if (m < nr) {
2723 c = temp[m];
2724 putchar(' ' <= c && c <= '~'? c: '.');
2725 } else
2726 putchar(' ');
2727 }
2728 n -= r;
2729 for (; m < 16; ++m)
2730 putchar(' ');
2731 printf("|\n");
2732 if (nr < r)
2733 break;
2734 }
2735}
2736
2737typedef int (*instruction_dump_func)(unsigned long inst, unsigned long addr);
2738
2739static int
2740generic_inst_dump(unsigned long adr, long count, int praddr,
2741 instruction_dump_func dump_func)
2742{
2743 int nr, dotted;
2744 unsigned long first_adr;
2745 unsigned int inst, last_inst = 0;
2746 unsigned char val[4];
2747
2748 dotted = 0;
2749 for (first_adr = adr; count > 0; --count, adr += 4) {
2750 nr = mread(adr, val, 4);
2751 if (nr == 0) {
2752 if (praddr) {
2753 const char *x = fault_chars[fault_type];
2754 printf(REG" %s%s%s%s\n", adr, x, x, x, x);
2755 }
2756 break;
2757 }
2758 inst = GETWORD(val);
2759 if (adr > first_adr && inst == last_inst) {
2760 if (!dotted) {
2761 printf(" ...\n");
2762 dotted = 1;
2763 }
2764 continue;
2765 }
2766 dotted = 0;
2767 last_inst = inst;
2768 if (praddr)
2769 printf(REG" %.8x", adr, inst);
2770 printf("\t");
2771 dump_func(inst, adr);
2772 printf("\n");
2773 }
2774 return adr - first_adr;
2775}
2776
2777static int
2778ppc_inst_dump(unsigned long adr, long count, int praddr)
2779{
2780 return generic_inst_dump(adr, count, praddr, print_insn_powerpc);
2781}
2782
2783void
2784print_address(unsigned long addr)
2785{
2786 xmon_print_symbol(addr, "\t# ", "");
2787}
2788
2789void
2790dump_log_buf(void)
2791{
2792 struct kmsg_dumper dumper = { .active = 1 };
2793 unsigned char buf[128];
2794 size_t len;
2795
2796 if (setjmp(bus_error_jmp) != 0) {
2797 printf("Error dumping printk buffer!\n");
2798 return;
2799 }
2800
2801 catch_memory_errors = 1;
2802 sync();
2803
2804 kmsg_dump_rewind_nolock(&dumper);
2805 xmon_start_pagination();
2806 while (kmsg_dump_get_line_nolock(&dumper, false, buf, sizeof(buf), &len)) {
2807 buf[len] = '\0';
2808 printf("%s", buf);
2809 }
2810 xmon_end_pagination();
2811
2812 sync();
2813 /* wait a little while to see if we get a machine check */
2814 __delay(200);
2815 catch_memory_errors = 0;
2816}
2817
2818#ifdef CONFIG_PPC_POWERNV
2819static void dump_opal_msglog(void)
2820{
2821 unsigned char buf[128];
2822 ssize_t res;
2823 loff_t pos = 0;
2824
2825 if (!firmware_has_feature(FW_FEATURE_OPAL)) {
2826 printf("Machine is not running OPAL firmware.\n");
2827 return;
2828 }
2829
2830 if (setjmp(bus_error_jmp) != 0) {
2831 printf("Error dumping OPAL msglog!\n");
2832 return;
2833 }
2834
2835 catch_memory_errors = 1;
2836 sync();
2837
2838 xmon_start_pagination();
2839 while ((res = opal_msglog_copy(buf, pos, sizeof(buf) - 1))) {
2840 if (res < 0) {
2841 printf("Error dumping OPAL msglog! Error: %zd\n", res);
2842 break;
2843 }
2844 buf[res] = '\0';
2845 printf("%s", buf);
2846 pos += res;
2847 }
2848 xmon_end_pagination();
2849
2850 sync();
2851 /* wait a little while to see if we get a machine check */
2852 __delay(200);
2853 catch_memory_errors = 0;
2854}
2855#endif
2856
2857/*
2858 * Memory operations - move, set, print differences
2859 */
2860static unsigned long mdest; /* destination address */
2861static unsigned long msrc; /* source address */
2862static unsigned long mval; /* byte value to set memory to */
2863static unsigned long mcount; /* # bytes to affect */
2864static unsigned long mdiffs; /* max # differences to print */
2865
2866static void
2867memops(int cmd)
2868{
2869 scanhex((void *)&mdest);
2870 if( termch != '\n' )
2871 termch = 0;
2872 scanhex((void *)(cmd == 's'? &mval: &msrc));
2873 if( termch != '\n' )
2874 termch = 0;
2875 scanhex((void *)&mcount);
2876 switch( cmd ){
2877 case 'm':
2878 memmove((void *)mdest, (void *)msrc, mcount);
2879 break;
2880 case 's':
2881 memset((void *)mdest, mval, mcount);
2882 break;
2883 case 'd':
2884 if( termch != '\n' )
2885 termch = 0;
2886 scanhex((void *)&mdiffs);
2887 memdiffs((unsigned char *)mdest, (unsigned char *)msrc, mcount, mdiffs);
2888 break;
2889 }
2890}
2891
2892static void
2893memdiffs(unsigned char *p1, unsigned char *p2, unsigned nb, unsigned maxpr)
2894{
2895 unsigned n, prt;
2896
2897 prt = 0;
2898 for( n = nb; n > 0; --n )
2899 if( *p1++ != *p2++ )
2900 if( ++prt <= maxpr )
2901 printf("%px %.2x # %px %.2x\n", p1 - 1,
2902 p1[-1], p2 - 1, p2[-1]);
2903 if( prt > maxpr )
2904 printf("Total of %d differences\n", prt);
2905}
2906
2907static unsigned mend;
2908static unsigned mask;
2909
2910static void
2911memlocate(void)
2912{
2913 unsigned a, n;
2914 unsigned char val[4];
2915
2916 last_cmd = "ml";
2917 scanhex((void *)&mdest);
2918 if (termch != '\n') {
2919 termch = 0;
2920 scanhex((void *)&mend);
2921 if (termch != '\n') {
2922 termch = 0;
2923 scanhex((void *)&mval);
2924 mask = ~0;
2925 if (termch != '\n') termch = 0;
2926 scanhex((void *)&mask);
2927 }
2928 }
2929 n = 0;
2930 for (a = mdest; a < mend; a += 4) {
2931 if (mread(a, val, 4) == 4
2932 && ((GETWORD(val) ^ mval) & mask) == 0) {
2933 printf("%.16x: %.16x\n", a, GETWORD(val));
2934 if (++n >= 10)
2935 break;
2936 }
2937 }
2938}
2939
2940static unsigned long mskip = 0x1000;
2941static unsigned long mlim = 0xffffffff;
2942
2943static void
2944memzcan(void)
2945{
2946 unsigned char v;
2947 unsigned a;
2948 int ok, ook;
2949
2950 scanhex(&mdest);
2951 if (termch != '\n') termch = 0;
2952 scanhex(&mskip);
2953 if (termch != '\n') termch = 0;
2954 scanhex(&mlim);
2955 ook = 0;
2956 for (a = mdest; a < mlim; a += mskip) {
2957 ok = mread(a, &v, 1);
2958 if (ok && !ook) {
2959 printf("%.8x .. ", a);
2960 } else if (!ok && ook)
2961 printf("%.8lx\n", a - mskip);
2962 ook = ok;
2963 if (a + mskip < a)
2964 break;
2965 }
2966 if (ook)
2967 printf("%.8lx\n", a - mskip);
2968}
2969
2970static void show_task(struct task_struct *tsk)
2971{
2972 char state;
2973
2974 /*
2975 * Cloned from kdb_task_state_char(), which is not entirely
2976 * appropriate for calling from xmon. This could be moved
2977 * to a common, generic, routine used by both.
2978 */
2979 state = (tsk->state == 0) ? 'R' :
2980 (tsk->state < 0) ? 'U' :
2981 (tsk->state & TASK_UNINTERRUPTIBLE) ? 'D' :
2982 (tsk->state & TASK_STOPPED) ? 'T' :
2983 (tsk->state & TASK_TRACED) ? 'C' :
2984 (tsk->exit_state & EXIT_ZOMBIE) ? 'Z' :
2985 (tsk->exit_state & EXIT_DEAD) ? 'E' :
2986 (tsk->state & TASK_INTERRUPTIBLE) ? 'S' : '?';
2987
2988 printf("%px %016lx %6d %6d %c %2d %s\n", tsk,
2989 tsk->thread.ksp,
2990 tsk->pid, tsk->parent->pid,
2991 state, task_thread_info(tsk)->cpu,
2992 tsk->comm);
2993}
2994
2995#ifdef CONFIG_PPC_BOOK3S_64
2996void format_pte(void *ptep, unsigned long pte)
2997{
2998 printf("ptep @ 0x%016lx = 0x%016lx\n", (unsigned long)ptep, pte);
2999 printf("Maps physical address = 0x%016lx\n", pte & PTE_RPN_MASK);
3000
3001 printf("Flags = %s%s%s%s%s\n",
3002 (pte & _PAGE_ACCESSED) ? "Accessed " : "",
3003 (pte & _PAGE_DIRTY) ? "Dirty " : "",
3004 (pte & _PAGE_READ) ? "Read " : "",
3005 (pte & _PAGE_WRITE) ? "Write " : "",
3006 (pte & _PAGE_EXEC) ? "Exec " : "");
3007}
3008
3009static void show_pte(unsigned long addr)
3010{
3011 unsigned long tskv = 0;
3012 struct task_struct *tsk = NULL;
3013 struct mm_struct *mm;
3014 pgd_t *pgdp, *pgdir;
3015 pud_t *pudp;
3016 pmd_t *pmdp;
3017 pte_t *ptep;
3018
3019 if (!scanhex(&tskv))
3020 mm = &init_mm;
3021 else
3022 tsk = (struct task_struct *)tskv;
3023
3024 if (tsk == NULL)
3025 mm = &init_mm;
3026 else
3027 mm = tsk->active_mm;
3028
3029 if (setjmp(bus_error_jmp) != 0) {
3030 catch_memory_errors = 0;
3031 printf("*** Error dumping pte for task %px\n", tsk);
3032 return;
3033 }
3034
3035 catch_memory_errors = 1;
3036 sync();
3037
3038 if (mm == &init_mm) {
3039 pgdp = pgd_offset_k(addr);
3040 pgdir = pgd_offset_k(0);
3041 } else {
3042 pgdp = pgd_offset(mm, addr);
3043 pgdir = pgd_offset(mm, 0);
3044 }
3045
3046 if (pgd_none(*pgdp)) {
3047 printf("no linux page table for address\n");
3048 return;
3049 }
3050
3051 printf("pgd @ 0x%px\n", pgdir);
3052
3053 if (pgd_huge(*pgdp)) {
3054 format_pte(pgdp, pgd_val(*pgdp));
3055 return;
3056 }
3057 printf("pgdp @ 0x%px = 0x%016lx\n", pgdp, pgd_val(*pgdp));
3058
3059 pudp = pud_offset(pgdp, addr);
3060
3061 if (pud_none(*pudp)) {
3062 printf("No valid PUD\n");
3063 return;
3064 }
3065
3066 if (pud_huge(*pudp)) {
3067 format_pte(pudp, pud_val(*pudp));
3068 return;
3069 }
3070
3071 printf("pudp @ 0x%px = 0x%016lx\n", pudp, pud_val(*pudp));
3072
3073 pmdp = pmd_offset(pudp, addr);
3074
3075 if (pmd_none(*pmdp)) {
3076 printf("No valid PMD\n");
3077 return;
3078 }
3079
3080 if (pmd_huge(*pmdp)) {
3081 format_pte(pmdp, pmd_val(*pmdp));
3082 return;
3083 }
3084 printf("pmdp @ 0x%px = 0x%016lx\n", pmdp, pmd_val(*pmdp));
3085
3086 ptep = pte_offset_map(pmdp, addr);
3087 if (pte_none(*ptep)) {
3088 printf("no valid PTE\n");
3089 return;
3090 }
3091
3092 format_pte(ptep, pte_val(*ptep));
3093
3094 sync();
3095 __delay(200);
3096 catch_memory_errors = 0;
3097}
3098#else
3099static void show_pte(unsigned long addr)
3100{
3101 printf("show_pte not yet implemented\n");
3102}
3103#endif /* CONFIG_PPC_BOOK3S_64 */
3104
3105static void show_tasks(void)
3106{
3107 unsigned long tskv;
3108 struct task_struct *tsk = NULL;
3109
3110 printf(" task_struct ->thread.ksp PID PPID S P CMD\n");
3111
3112 if (scanhex(&tskv))
3113 tsk = (struct task_struct *)tskv;
3114
3115 if (setjmp(bus_error_jmp) != 0) {
3116 catch_memory_errors = 0;
3117 printf("*** Error dumping task %px\n", tsk);
3118 return;
3119 }
3120
3121 catch_memory_errors = 1;
3122 sync();
3123
3124 if (tsk)
3125 show_task(tsk);
3126 else
3127 for_each_process(tsk)
3128 show_task(tsk);
3129
3130 sync();
3131 __delay(200);
3132 catch_memory_errors = 0;
3133}
3134
3135static void proccall(void)
3136{
3137 unsigned long args[8];
3138 unsigned long ret;
3139 int i;
3140 typedef unsigned long (*callfunc_t)(unsigned long, unsigned long,
3141 unsigned long, unsigned long, unsigned long,
3142 unsigned long, unsigned long, unsigned long);
3143 callfunc_t func;
3144
3145 if (!scanhex(&adrs))
3146 return;
3147 if (termch != '\n')
3148 termch = 0;
3149 for (i = 0; i < 8; ++i)
3150 args[i] = 0;
3151 for (i = 0; i < 8; ++i) {
3152 if (!scanhex(&args[i]) || termch == '\n')
3153 break;
3154 termch = 0;
3155 }
3156 func = (callfunc_t) adrs;
3157 ret = 0;
3158 if (setjmp(bus_error_jmp) == 0) {
3159 catch_memory_errors = 1;
3160 sync();
3161 ret = func(args[0], args[1], args[2], args[3],
3162 args[4], args[5], args[6], args[7]);
3163 sync();
3164 printf("return value is 0x%lx\n", ret);
3165 } else {
3166 printf("*** %x exception occurred\n", fault_except);
3167 }
3168 catch_memory_errors = 0;
3169}
3170
3171/* Input scanning routines */
3172int
3173skipbl(void)
3174{
3175 int c;
3176
3177 if( termch != 0 ){
3178 c = termch;
3179 termch = 0;
3180 } else
3181 c = inchar();
3182 while( c == ' ' || c == '\t' )
3183 c = inchar();
3184 return c;
3185}
3186
3187#define N_PTREGS 44
3188static const char *regnames[N_PTREGS] = {
3189 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
3190 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
3191 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
3192 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
3193 "pc", "msr", "or3", "ctr", "lr", "xer", "ccr",
3194#ifdef CONFIG_PPC64
3195 "softe",
3196#else
3197 "mq",
3198#endif
3199 "trap", "dar", "dsisr", "res"
3200};
3201
3202int
3203scanhex(unsigned long *vp)
3204{
3205 int c, d;
3206 unsigned long v;
3207
3208 c = skipbl();
3209 if (c == '%') {
3210 /* parse register name */
3211 char regname[8];
3212 int i;
3213
3214 for (i = 0; i < sizeof(regname) - 1; ++i) {
3215 c = inchar();
3216 if (!isalnum(c)) {
3217 termch = c;
3218 break;
3219 }
3220 regname[i] = c;
3221 }
3222 regname[i] = 0;
3223 i = match_string(regnames, N_PTREGS, regname);
3224 if (i < 0) {
3225 printf("invalid register name '%%%s'\n", regname);
3226 return 0;
3227 }
3228 if (xmon_regs == NULL) {
3229 printf("regs not available\n");
3230 return 0;
3231 }
3232 *vp = ((unsigned long *)xmon_regs)[i];
3233 return 1;
3234 }
3235
3236 /* skip leading "0x" if any */
3237
3238 if (c == '0') {
3239 c = inchar();
3240 if (c == 'x') {
3241 c = inchar();
3242 } else {
3243 d = hexdigit(c);
3244 if (d == EOF) {
3245 termch = c;
3246 *vp = 0;
3247 return 1;
3248 }
3249 }
3250 } else if (c == '$') {
3251 int i;
3252 for (i=0; i<63; i++) {
3253 c = inchar();
3254 if (isspace(c) || c == '\0') {
3255 termch = c;
3256 break;
3257 }
3258 tmpstr[i] = c;
3259 }
3260 tmpstr[i++] = 0;
3261 *vp = 0;
3262 if (setjmp(bus_error_jmp) == 0) {
3263 catch_memory_errors = 1;
3264 sync();
3265 *vp = kallsyms_lookup_name(tmpstr);
3266 sync();
3267 }
3268 catch_memory_errors = 0;
3269 if (!(*vp)) {
3270 printf("unknown symbol '%s'\n", tmpstr);
3271 return 0;
3272 }
3273 return 1;
3274 }
3275
3276 d = hexdigit(c);
3277 if (d == EOF) {
3278 termch = c;
3279 return 0;
3280 }
3281 v = 0;
3282 do {
3283 v = (v << 4) + d;
3284 c = inchar();
3285 d = hexdigit(c);
3286 } while (d != EOF);
3287 termch = c;
3288 *vp = v;
3289 return 1;
3290}
3291
3292static void
3293scannl(void)
3294{
3295 int c;
3296
3297 c = termch;
3298 termch = 0;
3299 while( c != '\n' )
3300 c = inchar();
3301}
3302
3303static int hexdigit(int c)
3304{
3305 if( '0' <= c && c <= '9' )
3306 return c - '0';
3307 if( 'A' <= c && c <= 'F' )
3308 return c - ('A' - 10);
3309 if( 'a' <= c && c <= 'f' )
3310 return c - ('a' - 10);
3311 return EOF;
3312}
3313
3314void
3315getstring(char *s, int size)
3316{
3317 int c;
3318
3319 c = skipbl();
3320 do {
3321 if( size > 1 ){
3322 *s++ = c;
3323 --size;
3324 }
3325 c = inchar();
3326 } while( c != ' ' && c != '\t' && c != '\n' );
3327 termch = c;
3328 *s = 0;
3329}
3330
3331static char line[256];
3332static char *lineptr;
3333
3334static void
3335flush_input(void)
3336{
3337 lineptr = NULL;
3338}
3339
3340static int
3341inchar(void)
3342{
3343 if (lineptr == NULL || *lineptr == 0) {
3344 if (xmon_gets(line, sizeof(line)) == NULL) {
3345 lineptr = NULL;
3346 return EOF;
3347 }
3348 lineptr = line;
3349 }
3350 return *lineptr++;
3351}
3352
3353static void
3354take_input(char *str)
3355{
3356 lineptr = str;
3357}
3358
3359
3360static void
3361symbol_lookup(void)
3362{
3363 int type = inchar();
3364 unsigned long addr, cpu;
3365 void __percpu *ptr = NULL;
3366 static char tmp[64];
3367
3368 switch (type) {
3369 case 'a':
3370 if (scanhex(&addr))
3371 xmon_print_symbol(addr, ": ", "\n");
3372 termch = 0;
3373 break;
3374 case 's':
3375 getstring(tmp, 64);
3376 if (setjmp(bus_error_jmp) == 0) {
3377 catch_memory_errors = 1;
3378 sync();
3379 addr = kallsyms_lookup_name(tmp);
3380 if (addr)
3381 printf("%s: %lx\n", tmp, addr);
3382 else
3383 printf("Symbol '%s' not found.\n", tmp);
3384 sync();
3385 }
3386 catch_memory_errors = 0;
3387 termch = 0;
3388 break;
3389 case 'p':
3390 getstring(tmp, 64);
3391 if (setjmp(bus_error_jmp) == 0) {
3392 catch_memory_errors = 1;
3393 sync();
3394 ptr = (void __percpu *)kallsyms_lookup_name(tmp);
3395 sync();
3396 }
3397
3398 if (ptr &&
3399 ptr >= (void __percpu *)__per_cpu_start &&
3400 ptr < (void __percpu *)__per_cpu_end)
3401 {
3402 if (scanhex(&cpu) && cpu < num_possible_cpus()) {
3403 addr = (unsigned long)per_cpu_ptr(ptr, cpu);
3404 } else {
3405 cpu = raw_smp_processor_id();
3406 addr = (unsigned long)this_cpu_ptr(ptr);
3407 }
3408
3409 printf("%s for cpu 0x%lx: %lx\n", tmp, cpu, addr);
3410 } else {
3411 printf("Percpu symbol '%s' not found.\n", tmp);
3412 }
3413
3414 catch_memory_errors = 0;
3415 termch = 0;
3416 break;
3417 }
3418}
3419
3420
3421/* Print an address in numeric and symbolic form (if possible) */
3422static void xmon_print_symbol(unsigned long address, const char *mid,
3423 const char *after)
3424{
3425 char *modname;
3426 const char *name = NULL;
3427 unsigned long offset, size;
3428
3429 printf(REG, address);
3430 if (setjmp(bus_error_jmp) == 0) {
3431 catch_memory_errors = 1;
3432 sync();
3433 name = kallsyms_lookup(address, &size, &offset, &modname,
3434 tmpstr);
3435 sync();
3436 /* wait a little while to see if we get a machine check */
3437 __delay(200);
3438 }
3439
3440 catch_memory_errors = 0;
3441
3442 if (name) {
3443 printf("%s%s+%#lx/%#lx", mid, name, offset, size);
3444 if (modname)
3445 printf(" [%s]", modname);
3446 }
3447 printf("%s", after);
3448}
3449
3450#ifdef CONFIG_PPC_BOOK3S_64
3451void dump_segments(void)
3452{
3453 int i;
3454 unsigned long esid,vsid;
3455 unsigned long llp;
3456
3457 printf("SLB contents of cpu 0x%x\n", smp_processor_id());
3458
3459 for (i = 0; i < mmu_slb_size; i++) {
3460 asm volatile("slbmfee %0,%1" : "=r" (esid) : "r" (i));
3461 asm volatile("slbmfev %0,%1" : "=r" (vsid) : "r" (i));
3462
3463 if (!esid && !vsid)
3464 continue;
3465
3466 printf("%02d %016lx %016lx", i, esid, vsid);
3467
3468 if (!(esid & SLB_ESID_V)) {
3469 printf("\n");
3470 continue;
3471 }
3472
3473 llp = vsid & SLB_VSID_LLP;
3474 if (vsid & SLB_VSID_B_1T) {
3475 printf(" 1T ESID=%9lx VSID=%13lx LLP:%3lx \n",
3476 GET_ESID_1T(esid),
3477 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT_1T,
3478 llp);
3479 } else {
3480 printf(" 256M ESID=%9lx VSID=%13lx LLP:%3lx \n",
3481 GET_ESID(esid),
3482 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT,
3483 llp);
3484 }
3485 }
3486}
3487#endif
3488
3489#ifdef CONFIG_PPC_STD_MMU_32
3490void dump_segments(void)
3491{
3492 int i;
3493
3494 printf("sr0-15 =");
3495 for (i = 0; i < 16; ++i)
3496 printf(" %x", mfsrin(i << 28));
3497 printf("\n");
3498}
3499#endif
3500
3501#ifdef CONFIG_44x
3502static void dump_tlb_44x(void)
3503{
3504 int i;
3505
3506 for (i = 0; i < PPC44x_TLB_SIZE; i++) {
3507 unsigned long w0,w1,w2;
3508 asm volatile("tlbre %0,%1,0" : "=r" (w0) : "r" (i));
3509 asm volatile("tlbre %0,%1,1" : "=r" (w1) : "r" (i));
3510 asm volatile("tlbre %0,%1,2" : "=r" (w2) : "r" (i));
3511 printf("[%02x] %08lx %08lx %08lx ", i, w0, w1, w2);
3512 if (w0 & PPC44x_TLB_VALID) {
3513 printf("V %08lx -> %01lx%08lx %c%c%c%c%c",
3514 w0 & PPC44x_TLB_EPN_MASK,
3515 w1 & PPC44x_TLB_ERPN_MASK,
3516 w1 & PPC44x_TLB_RPN_MASK,
3517 (w2 & PPC44x_TLB_W) ? 'W' : 'w',
3518 (w2 & PPC44x_TLB_I) ? 'I' : 'i',
3519 (w2 & PPC44x_TLB_M) ? 'M' : 'm',
3520 (w2 & PPC44x_TLB_G) ? 'G' : 'g',
3521 (w2 & PPC44x_TLB_E) ? 'E' : 'e');
3522 }
3523 printf("\n");
3524 }
3525}
3526#endif /* CONFIG_44x */
3527
3528#ifdef CONFIG_PPC_BOOK3E
3529static void dump_tlb_book3e(void)
3530{
3531 u32 mmucfg, pidmask, lpidmask;
3532 u64 ramask;
3533 int i, tlb, ntlbs, pidsz, lpidsz, rasz, lrat = 0;
3534 int mmu_version;
3535 static const char *pgsz_names[] = {
3536 " 1K",
3537 " 2K",
3538 " 4K",
3539 " 8K",
3540 " 16K",
3541 " 32K",
3542 " 64K",
3543 "128K",
3544 "256K",
3545 "512K",
3546 " 1M",
3547 " 2M",
3548 " 4M",
3549 " 8M",
3550 " 16M",
3551 " 32M",
3552 " 64M",
3553 "128M",
3554 "256M",
3555 "512M",
3556 " 1G",
3557 " 2G",
3558 " 4G",
3559 " 8G",
3560 " 16G",
3561 " 32G",
3562 " 64G",
3563 "128G",
3564 "256G",
3565 "512G",
3566 " 1T",
3567 " 2T",
3568 };
3569
3570 /* Gather some infos about the MMU */
3571 mmucfg = mfspr(SPRN_MMUCFG);
3572 mmu_version = (mmucfg & 3) + 1;
3573 ntlbs = ((mmucfg >> 2) & 3) + 1;
3574 pidsz = ((mmucfg >> 6) & 0x1f) + 1;
3575 lpidsz = (mmucfg >> 24) & 0xf;
3576 rasz = (mmucfg >> 16) & 0x7f;
3577 if ((mmu_version > 1) && (mmucfg & 0x10000))
3578 lrat = 1;
3579 printf("Book3E MMU MAV=%d.0,%d TLBs,%d-bit PID,%d-bit LPID,%d-bit RA\n",
3580 mmu_version, ntlbs, pidsz, lpidsz, rasz);
3581 pidmask = (1ul << pidsz) - 1;
3582 lpidmask = (1ul << lpidsz) - 1;
3583 ramask = (1ull << rasz) - 1;
3584
3585 for (tlb = 0; tlb < ntlbs; tlb++) {
3586 u32 tlbcfg;
3587 int nent, assoc, new_cc = 1;
3588 printf("TLB %d:\n------\n", tlb);
3589 switch(tlb) {
3590 case 0:
3591 tlbcfg = mfspr(SPRN_TLB0CFG);
3592 break;
3593 case 1:
3594 tlbcfg = mfspr(SPRN_TLB1CFG);
3595 break;
3596 case 2:
3597 tlbcfg = mfspr(SPRN_TLB2CFG);
3598 break;
3599 case 3:
3600 tlbcfg = mfspr(SPRN_TLB3CFG);
3601 break;
3602 default:
3603 printf("Unsupported TLB number !\n");
3604 continue;
3605 }
3606 nent = tlbcfg & 0xfff;
3607 assoc = (tlbcfg >> 24) & 0xff;
3608 for (i = 0; i < nent; i++) {
3609 u32 mas0 = MAS0_TLBSEL(tlb);
3610 u32 mas1 = MAS1_TSIZE(BOOK3E_PAGESZ_4K);
3611 u64 mas2 = 0;
3612 u64 mas7_mas3;
3613 int esel = i, cc = i;
3614
3615 if (assoc != 0) {
3616 cc = i / assoc;
3617 esel = i % assoc;
3618 mas2 = cc * 0x1000;
3619 }
3620
3621 mas0 |= MAS0_ESEL(esel);
3622 mtspr(SPRN_MAS0, mas0);
3623 mtspr(SPRN_MAS1, mas1);
3624 mtspr(SPRN_MAS2, mas2);
3625 asm volatile("tlbre 0,0,0" : : : "memory");
3626 mas1 = mfspr(SPRN_MAS1);
3627 mas2 = mfspr(SPRN_MAS2);
3628 mas7_mas3 = mfspr(SPRN_MAS7_MAS3);
3629 if (assoc && (i % assoc) == 0)
3630 new_cc = 1;
3631 if (!(mas1 & MAS1_VALID))
3632 continue;
3633 if (assoc == 0)
3634 printf("%04x- ", i);
3635 else if (new_cc)
3636 printf("%04x-%c", cc, 'A' + esel);
3637 else
3638 printf(" |%c", 'A' + esel);
3639 new_cc = 0;
3640 printf(" %016llx %04x %s %c%c AS%c",
3641 mas2 & ~0x3ffull,
3642 (mas1 >> 16) & 0x3fff,
3643 pgsz_names[(mas1 >> 7) & 0x1f],
3644 mas1 & MAS1_IND ? 'I' : ' ',
3645 mas1 & MAS1_IPROT ? 'P' : ' ',
3646 mas1 & MAS1_TS ? '1' : '0');
3647 printf(" %c%c%c%c%c%c%c",
3648 mas2 & MAS2_X0 ? 'a' : ' ',
3649 mas2 & MAS2_X1 ? 'v' : ' ',
3650 mas2 & MAS2_W ? 'w' : ' ',
3651 mas2 & MAS2_I ? 'i' : ' ',
3652 mas2 & MAS2_M ? 'm' : ' ',
3653 mas2 & MAS2_G ? 'g' : ' ',
3654 mas2 & MAS2_E ? 'e' : ' ');
3655 printf(" %016llx", mas7_mas3 & ramask & ~0x7ffull);
3656 if (mas1 & MAS1_IND)
3657 printf(" %s\n",
3658 pgsz_names[(mas7_mas3 >> 1) & 0x1f]);
3659 else
3660 printf(" U%c%c%c S%c%c%c\n",
3661 mas7_mas3 & MAS3_UX ? 'x' : ' ',
3662 mas7_mas3 & MAS3_UW ? 'w' : ' ',
3663 mas7_mas3 & MAS3_UR ? 'r' : ' ',
3664 mas7_mas3 & MAS3_SX ? 'x' : ' ',
3665 mas7_mas3 & MAS3_SW ? 'w' : ' ',
3666 mas7_mas3 & MAS3_SR ? 'r' : ' ');
3667 }
3668 }
3669}
3670#endif /* CONFIG_PPC_BOOK3E */
3671
3672static void xmon_init(int enable)
3673{
3674 if (enable) {
3675 __debugger = xmon;
3676 __debugger_ipi = xmon_ipi;
3677 __debugger_bpt = xmon_bpt;
3678 __debugger_sstep = xmon_sstep;
3679 __debugger_iabr_match = xmon_iabr_match;
3680 __debugger_break_match = xmon_break_match;
3681 __debugger_fault_handler = xmon_fault_handler;
3682
3683#ifdef CONFIG_PPC_PSERIES
3684 /*
3685 * Get the token here to avoid trying to get a lock
3686 * during the crash, causing a deadlock.
3687 */
3688 set_indicator_token = rtas_token("set-indicator");
3689#endif
3690 } else {
3691 __debugger = NULL;
3692 __debugger_ipi = NULL;
3693 __debugger_bpt = NULL;
3694 __debugger_sstep = NULL;
3695 __debugger_iabr_match = NULL;
3696 __debugger_break_match = NULL;
3697 __debugger_fault_handler = NULL;
3698 }
3699}
3700
3701#ifdef CONFIG_MAGIC_SYSRQ
3702static void sysrq_handle_xmon(int key)
3703{
3704 /* ensure xmon is enabled */
3705 xmon_init(1);
3706 debugger(get_irq_regs());
3707 if (!xmon_on)
3708 xmon_init(0);
3709}
3710
3711static struct sysrq_key_op sysrq_xmon_op = {
3712 .handler = sysrq_handle_xmon,
3713 .help_msg = "xmon(x)",
3714 .action_msg = "Entering xmon",
3715};
3716
3717static int __init setup_xmon_sysrq(void)
3718{
3719 register_sysrq_key('x', &sysrq_xmon_op);
3720 return 0;
3721}
3722device_initcall(setup_xmon_sysrq);
3723#endif /* CONFIG_MAGIC_SYSRQ */
3724
3725#ifdef CONFIG_DEBUG_FS
3726static void clear_all_bpt(void)
3727{
3728 int i;
3729
3730 /* clear/unpatch all breakpoints */
3731 remove_bpts();
3732 remove_cpu_bpts();
3733
3734 /* Disable all breakpoints */
3735 for (i = 0; i < NBPTS; ++i)
3736 bpts[i].enabled = 0;
3737
3738 /* Clear any data or iabr breakpoints */
3739 if (iabr || dabr.enabled) {
3740 iabr = NULL;
3741 dabr.enabled = 0;
3742 }
3743
3744 printf("xmon: All breakpoints cleared\n");
3745}
3746
3747static int xmon_dbgfs_set(void *data, u64 val)
3748{
3749 xmon_on = !!val;
3750 xmon_init(xmon_on);
3751
3752 /* make sure all breakpoints removed when disabling */
3753 if (!xmon_on)
3754 clear_all_bpt();
3755 return 0;
3756}
3757
3758static int xmon_dbgfs_get(void *data, u64 *val)
3759{
3760 *val = xmon_on;
3761 return 0;
3762}
3763
3764DEFINE_SIMPLE_ATTRIBUTE(xmon_dbgfs_ops, xmon_dbgfs_get,
3765 xmon_dbgfs_set, "%llu\n");
3766
3767static int __init setup_xmon_dbgfs(void)
3768{
3769 debugfs_create_file("xmon", 0600, powerpc_debugfs_root, NULL,
3770 &xmon_dbgfs_ops);
3771 return 0;
3772}
3773device_initcall(setup_xmon_dbgfs);
3774#endif /* CONFIG_DEBUG_FS */
3775
3776static int xmon_early __initdata;
3777
3778static int __init early_parse_xmon(char *p)
3779{
3780 if (!p || strncmp(p, "early", 5) == 0) {
3781 /* just "xmon" is equivalent to "xmon=early" */
3782 xmon_init(1);
3783 xmon_early = 1;
3784 xmon_on = 1;
3785 } else if (strncmp(p, "on", 2) == 0) {
3786 xmon_init(1);
3787 xmon_on = 1;
3788 } else if (strncmp(p, "off", 3) == 0)
3789 xmon_on = 0;
3790 else
3791 return 1;
3792
3793 return 0;
3794}
3795early_param("xmon", early_parse_xmon);
3796
3797void __init xmon_setup(void)
3798{
3799 if (xmon_on)
3800 xmon_init(1);
3801 if (xmon_early)
3802 debugger(NULL);
3803}
3804
3805#ifdef CONFIG_SPU_BASE
3806
3807struct spu_info {
3808 struct spu *spu;
3809 u64 saved_mfc_sr1_RW;
3810 u32 saved_spu_runcntl_RW;
3811 unsigned long dump_addr;
3812 u8 stopped_ok;
3813};
3814
3815#define XMON_NUM_SPUS 16 /* Enough for current hardware */
3816
3817static struct spu_info spu_info[XMON_NUM_SPUS];
3818
3819void xmon_register_spus(struct list_head *list)
3820{
3821 struct spu *spu;
3822
3823 list_for_each_entry(spu, list, full_list) {
3824 if (spu->number >= XMON_NUM_SPUS) {
3825 WARN_ON(1);
3826 continue;
3827 }
3828
3829 spu_info[spu->number].spu = spu;
3830 spu_info[spu->number].stopped_ok = 0;
3831 spu_info[spu->number].dump_addr = (unsigned long)
3832 spu_info[spu->number].spu->local_store;
3833 }
3834}
3835
3836static void stop_spus(void)
3837{
3838 struct spu *spu;
3839 int i;
3840 u64 tmp;
3841
3842 for (i = 0; i < XMON_NUM_SPUS; i++) {
3843 if (!spu_info[i].spu)
3844 continue;
3845
3846 if (setjmp(bus_error_jmp) == 0) {
3847 catch_memory_errors = 1;
3848 sync();
3849
3850 spu = spu_info[i].spu;
3851
3852 spu_info[i].saved_spu_runcntl_RW =
3853 in_be32(&spu->problem->spu_runcntl_RW);
3854
3855 tmp = spu_mfc_sr1_get(spu);
3856 spu_info[i].saved_mfc_sr1_RW = tmp;
3857
3858 tmp &= ~MFC_STATE1_MASTER_RUN_CONTROL_MASK;
3859 spu_mfc_sr1_set(spu, tmp);
3860
3861 sync();
3862 __delay(200);
3863
3864 spu_info[i].stopped_ok = 1;
3865
3866 printf("Stopped spu %.2d (was %s)\n", i,
3867 spu_info[i].saved_spu_runcntl_RW ?
3868 "running" : "stopped");
3869 } else {
3870 catch_memory_errors = 0;
3871 printf("*** Error stopping spu %.2d\n", i);
3872 }
3873 catch_memory_errors = 0;
3874 }
3875}
3876
3877static void restart_spus(void)
3878{
3879 struct spu *spu;
3880 int i;
3881
3882 for (i = 0; i < XMON_NUM_SPUS; i++) {
3883 if (!spu_info[i].spu)
3884 continue;
3885
3886 if (!spu_info[i].stopped_ok) {
3887 printf("*** Error, spu %d was not successfully stopped"
3888 ", not restarting\n", i);
3889 continue;
3890 }
3891
3892 if (setjmp(bus_error_jmp) == 0) {
3893 catch_memory_errors = 1;
3894 sync();
3895
3896 spu = spu_info[i].spu;
3897 spu_mfc_sr1_set(spu, spu_info[i].saved_mfc_sr1_RW);
3898 out_be32(&spu->problem->spu_runcntl_RW,
3899 spu_info[i].saved_spu_runcntl_RW);
3900
3901 sync();
3902 __delay(200);
3903
3904 printf("Restarted spu %.2d\n", i);
3905 } else {
3906 catch_memory_errors = 0;
3907 printf("*** Error restarting spu %.2d\n", i);
3908 }
3909 catch_memory_errors = 0;
3910 }
3911}
3912
3913#define DUMP_WIDTH 23
3914#define DUMP_VALUE(format, field, value) \
3915do { \
3916 if (setjmp(bus_error_jmp) == 0) { \
3917 catch_memory_errors = 1; \
3918 sync(); \
3919 printf(" %-*s = "format"\n", DUMP_WIDTH, \
3920 #field, value); \
3921 sync(); \
3922 __delay(200); \
3923 } else { \
3924 catch_memory_errors = 0; \
3925 printf(" %-*s = *** Error reading field.\n", \
3926 DUMP_WIDTH, #field); \
3927 } \
3928 catch_memory_errors = 0; \
3929} while (0)
3930
3931#define DUMP_FIELD(obj, format, field) \
3932 DUMP_VALUE(format, field, obj->field)
3933
3934static void dump_spu_fields(struct spu *spu)
3935{
3936 printf("Dumping spu fields at address %p:\n", spu);
3937
3938 DUMP_FIELD(spu, "0x%x", number);
3939 DUMP_FIELD(spu, "%s", name);
3940 DUMP_FIELD(spu, "0x%lx", local_store_phys);
3941 DUMP_FIELD(spu, "0x%p", local_store);
3942 DUMP_FIELD(spu, "0x%lx", ls_size);
3943 DUMP_FIELD(spu, "0x%x", node);
3944 DUMP_FIELD(spu, "0x%lx", flags);
3945 DUMP_FIELD(spu, "%llu", class_0_pending);
3946 DUMP_FIELD(spu, "0x%llx", class_0_dar);
3947 DUMP_FIELD(spu, "0x%llx", class_1_dar);
3948 DUMP_FIELD(spu, "0x%llx", class_1_dsisr);
3949 DUMP_FIELD(spu, "0x%x", irqs[0]);
3950 DUMP_FIELD(spu, "0x%x", irqs[1]);
3951 DUMP_FIELD(spu, "0x%x", irqs[2]);
3952 DUMP_FIELD(spu, "0x%x", slb_replace);
3953 DUMP_FIELD(spu, "%d", pid);
3954 DUMP_FIELD(spu, "0x%p", mm);
3955 DUMP_FIELD(spu, "0x%p", ctx);
3956 DUMP_FIELD(spu, "0x%p", rq);
3957 DUMP_FIELD(spu, "0x%llx", timestamp);
3958 DUMP_FIELD(spu, "0x%lx", problem_phys);
3959 DUMP_FIELD(spu, "0x%p", problem);
3960 DUMP_VALUE("0x%x", problem->spu_runcntl_RW,
3961 in_be32(&spu->problem->spu_runcntl_RW));
3962 DUMP_VALUE("0x%x", problem->spu_status_R,
3963 in_be32(&spu->problem->spu_status_R));
3964 DUMP_VALUE("0x%x", problem->spu_npc_RW,
3965 in_be32(&spu->problem->spu_npc_RW));
3966 DUMP_FIELD(spu, "0x%p", priv2);
3967 DUMP_FIELD(spu, "0x%p", pdata);
3968}
3969
3970int
3971spu_inst_dump(unsigned long adr, long count, int praddr)
3972{
3973 return generic_inst_dump(adr, count, praddr, print_insn_spu);
3974}
3975
3976static void dump_spu_ls(unsigned long num, int subcmd)
3977{
3978 unsigned long offset, addr, ls_addr;
3979
3980 if (setjmp(bus_error_jmp) == 0) {
3981 catch_memory_errors = 1;
3982 sync();
3983 ls_addr = (unsigned long)spu_info[num].spu->local_store;
3984 sync();
3985 __delay(200);
3986 } else {
3987 catch_memory_errors = 0;
3988 printf("*** Error: accessing spu info for spu %ld\n", num);
3989 return;
3990 }
3991 catch_memory_errors = 0;
3992
3993 if (scanhex(&offset))
3994 addr = ls_addr + offset;
3995 else
3996 addr = spu_info[num].dump_addr;
3997
3998 if (addr >= ls_addr + LS_SIZE) {
3999 printf("*** Error: address outside of local store\n");
4000 return;
4001 }
4002
4003 switch (subcmd) {
4004 case 'i':
4005 addr += spu_inst_dump(addr, 16, 1);
4006 last_cmd = "sdi\n";
4007 break;
4008 default:
4009 prdump(addr, 64);
4010 addr += 64;
4011 last_cmd = "sd\n";
4012 break;
4013 }
4014
4015 spu_info[num].dump_addr = addr;
4016}
4017
4018static int do_spu_cmd(void)
4019{
4020 static unsigned long num = 0;
4021 int cmd, subcmd = 0;
4022
4023 cmd = inchar();
4024 switch (cmd) {
4025 case 's':
4026 stop_spus();
4027 break;
4028 case 'r':
4029 restart_spus();
4030 break;
4031 case 'd':
4032 subcmd = inchar();
4033 if (isxdigit(subcmd) || subcmd == '\n')
4034 termch = subcmd;
4035 case 'f':
4036 scanhex(&num);
4037 if (num >= XMON_NUM_SPUS || !spu_info[num].spu) {
4038 printf("*** Error: invalid spu number\n");
4039 return 0;
4040 }
4041
4042 switch (cmd) {
4043 case 'f':
4044 dump_spu_fields(spu_info[num].spu);
4045 break;
4046 default:
4047 dump_spu_ls(num, subcmd);
4048 break;
4049 }
4050
4051 break;
4052 default:
4053 return -1;
4054 }
4055
4056 return 0;
4057}
4058#else /* ! CONFIG_SPU_BASE */
4059static int do_spu_cmd(void)
4060{
4061 return -1;
4062}
4063#endif