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