1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * Routines providing a simple monitor for use on the PowerMac.
5 * Copyright (C) 1996-2005 Paul Mackerras.
6 * Copyright (C) 2001 PPC64 Team, IBM Corp
7 * Copyrignt (C) 2006 Michael Ellerman, IBM Corp
10 #include <linux/kernel.h>
11 #include <linux/errno.h>
12 #include <linux/sched/signal.h>
13 #include <linux/smp.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>
31 #include <asm/ptrace.h>
33 #include <asm/string.h>
34 #include <asm/machdep.h>
36 #include <asm/processor.h>
38 #include <asm/mmu_context.h>
39 #include <asm/plpar_wrappers.h>
40 #include <asm/cputable.h>
42 #include <asm/sstep.h>
43 #include <asm/irq_regs.h>
45 #include <asm/spu_priv1.h>
46 #include <asm/setjmp.h>
48 #include <asm/debug.h>
49 #include <asm/hw_breakpoint.h>
52 #include <asm/firmware.h>
53 #include <asm/code-patching.h>
54 #include <asm/sections.h>
56 #include <asm/interrupt.h>
59 #include <asm/hvcall.h>
65 #include "xmon_bpts.h"
68 static cpumask_t cpus_in_xmon = CPU_MASK_NONE;
69 static unsigned long xmon_taken = 1;
70 static int xmon_owner;
72 static int xmon_batch;
73 static unsigned long xmon_batch_start_cpu;
74 static cpumask_t xmon_batch_cpus = CPU_MASK_NONE;
77 #endif /* CONFIG_SMP */
79 static unsigned long in_xmon __read_mostly = 0;
80 static int xmon_on = IS_ENABLED(CONFIG_XMON_DEFAULT);
81 static bool xmon_is_ro = IS_ENABLED(CONFIG_XMON_DEFAULT_RO_MODE);
83 static unsigned long adrs;
85 #define MAX_DUMP (64 * 1024)
86 static unsigned long ndump = 64;
87 #define MAX_IDUMP (MAX_DUMP >> 2)
88 static unsigned long nidump = 16;
89 static unsigned long ncsum = 4096;
91 static char tmpstr[128];
92 static int tracing_enabled;
94 static long bus_error_jmp[JMP_BUF_LEN];
95 static int catch_memory_errors;
96 static int catch_spr_faults;
97 static long *xmon_fault_jmp[NR_CPUS];
99 /* Breakpoint stuff */
101 unsigned long address;
108 /* Bits in bpt.enabled */
113 static struct bpt bpts[NBPTS];
114 static struct bpt dabr[HBP_NUM_MAX];
115 static struct bpt *iabr;
116 static unsigned int bpinstr = PPC_RAW_TRAP();
118 #define BP_NUM(bp) ((bp) - bpts + 1)
121 static int cmds(struct pt_regs *);
122 static int mread(unsigned long, void *, int);
123 static int mwrite(unsigned long, void *, int);
124 static int mread_instr(unsigned long, ppc_inst_t *);
125 static int handle_fault(struct pt_regs *);
126 static void byterev(unsigned char *, int);
127 static void memex(void);
128 static int bsesc(void);
129 static void dump(void);
130 static void show_pte(unsigned long);
131 static void prdump(unsigned long, long);
132 static int ppc_inst_dump(unsigned long, long, int);
133 static void dump_log_buf(void);
136 static int xmon_switch_cpu(unsigned long);
137 static int xmon_batch_next_cpu(void);
138 static int batch_cmds(struct pt_regs *);
141 #ifdef CONFIG_PPC_POWERNV
142 static void dump_opal_msglog(void);
144 static inline void dump_opal_msglog(void)
146 printf("Machine is not running OPAL firmware.\n");
150 static void backtrace(struct pt_regs *);
151 static void excprint(struct pt_regs *);
152 static void prregs(struct pt_regs *);
153 static void memops(int);
154 static void memlocate(void);
155 static void memzcan(void);
156 static void memdiffs(unsigned char *, unsigned char *, unsigned, unsigned);
158 int scanhex(unsigned long *valp);
159 static void scannl(void);
160 static int hexdigit(int);
161 void getstring(char *, int);
162 static void flush_input(void);
163 static int inchar(void);
164 static void take_input(char *);
165 static int read_spr(int, unsigned long *);
166 static void write_spr(int, unsigned long);
167 static void super_regs(void);
168 static void remove_bpts(void);
169 static void insert_bpts(void);
170 static void remove_cpu_bpts(void);
171 static void insert_cpu_bpts(void);
172 static struct bpt *at_breakpoint(unsigned long pc);
173 static struct bpt *in_breakpoint_table(unsigned long pc, unsigned long *offp);
174 static int do_step(struct pt_regs *);
175 static void bpt_cmds(void);
176 static void cacheflush(void);
177 static int cpu_cmd(void);
178 static void csum(void);
179 static void bootcmds(void);
180 static void proccall(void);
181 static void show_tasks(void);
182 void dump_segments(void);
183 static void symbol_lookup(void);
184 static void xmon_show_stack(unsigned long sp, unsigned long lr,
186 static void xmon_print_symbol(unsigned long address, const char *mid,
188 static const char *getvecname(unsigned long vec);
190 static int do_spu_cmd(void);
193 static void dump_tlb_44x(void);
195 #ifdef CONFIG_PPC_BOOK3E_64
196 static void dump_tlb_book3e(void);
199 static void clear_all_bpt(void);
207 #ifdef __LITTLE_ENDIAN__
208 #define GETWORD(v) (((v)[3] << 24) + ((v)[2] << 16) + ((v)[1] << 8) + (v)[0])
210 #define GETWORD(v) (((v)[0] << 24) + ((v)[1] << 16) + ((v)[2] << 8) + (v)[3])
213 static const char *xmon_ro_msg = "Operation disabled: xmon in read-only mode\n";
215 static char *help_string = "\
217 b show breakpoints\n\
218 bd set data breakpoint\n\
219 bi set instruction breakpoint\n\
220 bc clear breakpoint\n"
223 c print cpus stopped in xmon\n\
224 c# try to switch to cpu number h (in hex)\n\
225 c# $ run command '$' (one of 'r','S' or 't') on all cpus in xmon\n"
230 d1 dump 1 byte values\n\
231 d2 dump 2 byte values\n\
232 d4 dump 4 byte values\n\
233 d8 dump 8 byte values\n\
234 di dump instructions\n\
235 df dump float values\n\
236 dd dump double values\n\
237 dl dump the kernel log buffer\n"
238 #ifdef CONFIG_PPC_POWERNV
240 do dump the OPAL message log\n"
244 dp[#] dump paca for current cpu, or cpu #\n\
245 dpa dump paca for all possible cpus\n"
248 dr dump stream of raw bytes\n\
249 dv dump virtual address translation \n\
250 dt dump the tracing buffers (uses printk)\n\
251 dtc dump the tracing buffers for current CPU (uses printk)\n\
253 #ifdef CONFIG_PPC_POWERNV
254 " dx# dump xive on CPU #\n\
255 dxi# dump xive irq state #\n\
256 dxa dump xive on all CPUs\n"
258 " e print exception information\n\
260 la lookup symbol+offset of specified address\n\
261 ls lookup address of specified symbol\n\
262 lp s [#] lookup address of percpu symbol s for current cpu, or cpu #\n\
263 m examine/change memory\n\
264 mm move a block of memory\n\
265 ms set a block of memory\n\
266 md compare two blocks of memory\n\
267 ml locate a block of memory\n\
268 mz zero a block of memory\n\
269 mi show information about memory allocation\n\
270 p call a procedure\n\
271 P list processes/tasks\n\
274 #ifdef CONFIG_SPU_BASE
275 " ss stop execution on all spus\n\
276 sr restore execution on stopped spus\n\
277 sf # dump spu fields for spu # (in hex)\n\
278 sd # dump spu local store for spu # (in hex)\n\
279 sdi # disassemble spu local store for spu # (in hex)\n"
281 " S print special registers\n\
284 Sw #v write v to SPR #\n\
286 x exit monitor and recover\n\
287 X exit monitor and don't recover\n"
288 #if defined(CONFIG_PPC_BOOK3S_64)
289 " u dump segment table or SLB\n"
290 #elif defined(CONFIG_PPC_BOOK3S_32)
291 " u dump segment registers\n"
292 #elif defined(CONFIG_44x) || defined(CONFIG_PPC_BOOK3E_64)
295 " U show uptime information\n"
297 " # n limit output to n lines per page (for dp, dpa, dl)\n"
302 #ifdef CONFIG_SECURITY
303 static bool xmon_is_locked_down(void)
305 static bool lockdown;
308 lockdown = !!security_locked_down(LOCKDOWN_XMON_RW);
310 printf("xmon: Disabled due to kernel lockdown\n");
316 xmon_is_ro = !!security_locked_down(LOCKDOWN_XMON_WR);
318 printf("xmon: Read-only due to kernel lockdown\n");
323 #else /* CONFIG_SECURITY */
324 static inline bool xmon_is_locked_down(void)
330 static struct pt_regs *xmon_regs;
332 static inline void sync(void)
334 asm volatile("sync; isync");
337 static inline void cflush(void *p)
339 asm volatile ("dcbf 0,%0; icbi 0,%0" : : "r" (p));
342 static inline void cinval(void *p)
344 asm volatile ("dcbi 0,%0; icbi 0,%0" : : "r" (p));
348 * write_ciabr() - write the CIABR SPR
349 * @ciabr: The value to write.
351 * This function writes a value to the CIARB register either directly
352 * through mtspr instruction if the kernel is in HV privilege mode or
353 * call a hypervisor function to achieve the same in case the kernel
354 * is in supervisor privilege mode.
356 static void write_ciabr(unsigned long ciabr)
358 if (!cpu_has_feature(CPU_FTR_ARCH_207S))
361 if (cpu_has_feature(CPU_FTR_HVMODE)) {
362 mtspr(SPRN_CIABR, ciabr);
365 plpar_set_ciabr(ciabr);
369 * set_ciabr() - set the CIABR
370 * @addr: The value to set.
372 * This function sets the correct privilege value into the HW
373 * breakpoint address before writing it up in the CIABR register.
375 static void set_ciabr(unsigned long addr)
379 if (cpu_has_feature(CPU_FTR_HVMODE))
380 addr |= CIABR_PRIV_HYPER;
382 addr |= CIABR_PRIV_SUPER;
387 * Disable surveillance (the service processor watchdog function)
388 * while we are in xmon.
389 * XXX we should re-enable it when we leave. :)
391 #define SURVEILLANCE_TOKEN 9000
393 static inline void disable_surveillance(void)
395 #ifdef CONFIG_PPC_PSERIES
396 /* Since this can't be a module, args should end up below 4GB. */
397 static struct rtas_args args;
398 const s32 token = rtas_function_token(RTAS_FN_SET_INDICATOR);
401 * At this point we have got all the cpus we can into
402 * xmon, so there is hopefully no other cpu calling RTAS
403 * at the moment, even though we don't take rtas.lock.
404 * If we did try to take rtas.lock there would be a
405 * real possibility of deadlock.
407 if (token == RTAS_UNKNOWN_SERVICE)
410 rtas_call_unlocked(&args, token, 3, 1, NULL,
411 SURVEILLANCE_TOKEN, 0, 0);
413 #endif /* CONFIG_PPC_PSERIES */
417 static int xmon_speaker;
419 static void get_output_lock(void)
421 int me = smp_processor_id() + 0x100;
422 int last_speaker = 0, prev;
425 if (xmon_speaker == me)
429 last_speaker = cmpxchg(&xmon_speaker, 0, me);
430 if (last_speaker == 0)
434 * Wait a full second for the lock, we might be on a slow
435 * console, but check every 100us.
438 while (xmon_speaker == last_speaker) {
444 /* hostile takeover */
445 prev = cmpxchg(&xmon_speaker, last_speaker, me);
446 if (prev == last_speaker)
453 static void release_output_lock(void)
458 int cpus_are_in_xmon(void)
460 return !cpumask_empty(&cpus_in_xmon);
463 static bool wait_for_other_cpus(int ncpus)
465 unsigned long timeout;
467 /* We wait for 2s, which is a metric "little while" */
468 for (timeout = 20000; timeout != 0; --timeout) {
469 if (cpumask_weight(&cpus_in_xmon) >= ncpus)
477 #else /* CONFIG_SMP */
478 static inline void get_output_lock(void) {}
479 static inline void release_output_lock(void) {}
482 static void xmon_touch_watchdogs(void)
484 touch_softlockup_watchdog_sync();
485 rcu_cpu_stall_reset();
486 touch_nmi_watchdog();
489 static int xmon_core(struct pt_regs *regs, volatile int fromipi)
491 volatile int cmd = 0;
492 struct bpt *volatile bp;
493 long recurse_jmp[JMP_BUF_LEN];
495 unsigned long offset;
502 local_irq_save(flags);
505 locked_down = xmon_is_locked_down();
508 tracing_enabled = tracing_is_on();
512 bp = in_breakpoint_table(regs->nip, &offset);
514 regs_set_return_ip(regs, bp->address + offset);
515 atomic_dec(&bp->ref_count);
521 cpu = smp_processor_id();
522 if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
524 * We catch SPR read/write faults here because the 0x700, 0xf60
525 * etc. handlers don't call debugger_fault_handler().
527 if (catch_spr_faults)
528 longjmp(bus_error_jmp, 1);
531 printf("cpu 0x%x: Exception %lx %s in xmon, "
532 "returning to main loop\n",
533 cpu, regs->trap, getvecname(TRAP(regs)));
534 release_output_lock();
535 longjmp(xmon_fault_jmp[cpu], 1);
538 if (setjmp(recurse_jmp) != 0) {
539 if (!in_xmon || !xmon_gate) {
541 printf("xmon: WARNING: bad recursive fault "
542 "on cpu 0x%x\n", cpu);
543 release_output_lock();
546 secondary = !(xmon_taken && cpu == xmon_owner);
550 xmon_fault_jmp[cpu] = recurse_jmp;
553 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT))
554 bp = at_breakpoint(regs->nip);
555 if (bp || regs_is_unrecoverable(regs))
563 printf("cpu 0x%x stopped at breakpoint 0x%tx (",
565 xmon_print_symbol(regs->nip, " ", ")\n");
567 if (regs_is_unrecoverable(regs))
568 printf("WARNING: exception is not recoverable, "
570 release_output_lock();
573 cpumask_set_cpu(cpu, &cpus_in_xmon);
578 while (secondary && !xmon_gate) {
584 secondary = test_and_set_bit(0, &in_xmon);
587 touch_nmi_watchdog();
591 if (!secondary && !xmon_gate) {
592 /* we are the first cpu to come in */
593 /* interrupt other cpu(s) */
594 int ncpus = num_online_cpus();
600 * A system reset (trap == 0x100) can be triggered on
601 * all CPUs, so when we come in via 0x100 try waiting
602 * for the other CPUs to come in before we send the
603 * debugger break (IPI). This is similar to
604 * crash_kexec_secondary().
606 if (TRAP(regs) != INTERRUPT_SYSTEM_RESET || !wait_for_other_cpus(ncpus))
607 smp_send_debugger_break();
609 wait_for_other_cpus(ncpus);
612 disable_surveillance();
615 /* for breakpoint or single step, print curr insn */
616 if (bp || TRAP(regs) == INTERRUPT_TRACE)
617 ppc_inst_dump(regs->nip, 1, 0);
618 printf("enter ? for help\n");
624 touch_nmi_watchdog();
631 if (cpu == xmon_owner) {
632 if (!test_and_set_bit(0, &xmon_taken)) {
638 while (cpu == xmon_owner)
642 touch_nmi_watchdog();
647 cmd = batch_cmds(regs);
649 if (!locked_down && cmd)
651 if (locked_down || cmd != 0) {
659 /* have switched to some other cpu */
664 cpumask_clear_cpu(cpu, &cpus_in_xmon);
665 xmon_fault_jmp[cpu] = NULL;
667 /* UP is simple... */
669 printf("Exception %lx %s in xmon, returning to main loop\n",
670 regs->trap, getvecname(TRAP(regs)));
671 longjmp(xmon_fault_jmp[0], 1);
673 if (setjmp(recurse_jmp) == 0) {
674 xmon_fault_jmp[0] = recurse_jmp;
678 bp = at_breakpoint(regs->nip);
680 printf("Stopped at breakpoint %tx (", BP_NUM(bp));
681 xmon_print_symbol(regs->nip, " ", ")\n");
683 if (regs_is_unrecoverable(regs))
684 printf("WARNING: exception is not recoverable, "
687 disable_surveillance();
689 /* for breakpoint or single step, print current insn */
690 if (bp || TRAP(regs) == INTERRUPT_TRACE)
691 ppc_inst_dump(regs->nip, 1, 0);
692 printf("enter ? for help\n");
704 if (regs->msr & MSR_DE) {
705 bp = at_breakpoint(regs->nip);
707 regs_set_return_ip(regs, (unsigned long) &bp->instr[0]);
708 atomic_inc(&bp->ref_count);
712 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
713 bp = at_breakpoint(regs->nip);
715 int stepped = emulate_step(regs, ppc_inst_read(bp->instr));
717 regs_set_return_ip(regs, (unsigned long) &bp->instr[0]);
718 atomic_inc(&bp->ref_count);
719 } else if (stepped < 0) {
720 printf("Couldn't single-step %s instruction\n",
721 IS_RFID(ppc_inst_read(bp->instr))? "rfid": "mtmsrd");
731 xmon_touch_watchdogs();
732 local_irq_restore(flags);
734 return cmd != 'X' && cmd != EOF;
737 int xmon(struct pt_regs *excp)
742 ppc_save_regs(®s);
746 return xmon_core(excp, 0);
750 irqreturn_t xmon_irq(int irq, void *d)
753 local_irq_save(flags);
754 printf("Keyboard interrupt\n");
755 xmon(get_irq_regs());
756 local_irq_restore(flags);
760 static int xmon_bpt(struct pt_regs *regs)
763 unsigned long offset;
765 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
768 /* Are we at the trap at bp->instr[1] for some bp? */
769 bp = in_breakpoint_table(regs->nip, &offset);
770 if (bp != NULL && (offset == 4 || offset == 8)) {
771 regs_set_return_ip(regs, bp->address + offset);
772 atomic_dec(&bp->ref_count);
776 /* Are we at a breakpoint? */
777 bp = at_breakpoint(regs->nip);
786 static int xmon_sstep(struct pt_regs *regs)
794 static int xmon_break_match(struct pt_regs *regs)
798 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
800 for (i = 0; i < nr_wp_slots(); i++) {
811 static int xmon_iabr_match(struct pt_regs *regs)
813 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
821 static int xmon_ipi(struct pt_regs *regs)
824 if (in_xmon && !cpumask_test_cpu(smp_processor_id(), &cpus_in_xmon))
830 static int xmon_fault_handler(struct pt_regs *regs)
833 unsigned long offset;
835 if (in_xmon && catch_memory_errors)
836 handle_fault(regs); /* doesn't return */
838 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
839 bp = in_breakpoint_table(regs->nip, &offset);
841 regs_set_return_ip(regs, bp->address + offset);
842 atomic_dec(&bp->ref_count);
849 /* Force enable xmon if not already enabled */
850 static inline void force_enable_xmon(void)
852 /* Enable xmon hooks if needed */
854 printf("xmon: Enabling debugger hooks\n");
859 static struct bpt *at_breakpoint(unsigned long pc)
862 struct bpt *volatile bp;
865 for (i = 0; i < NBPTS; ++i, ++bp)
866 if (bp->enabled && pc == bp->address)
871 static struct bpt *in_breakpoint_table(unsigned long nip, unsigned long *offp)
875 off = nip - (unsigned long)bpt_table;
876 if (off >= sizeof(bpt_table))
878 *offp = off & (BPT_SIZE - 1);
881 return bpts + (off / BPT_SIZE);
884 static struct bpt *new_breakpoint(unsigned long a)
889 bp = at_breakpoint(a);
893 for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
894 if (!bp->enabled && atomic_read(&bp->ref_count) == 0) {
896 bp->instr = (void *)(bpt_table + ((bp - bpts) * BPT_WORDS));
901 printf("Sorry, no free breakpoints. Please clear one first.\n");
905 static void insert_bpts(void)
908 ppc_inst_t instr, instr2;
909 struct bpt *bp, *bp2;
912 for (i = 0; i < NBPTS; ++i, ++bp) {
913 if ((bp->enabled & (BP_TRAP|BP_CIABR)) == 0)
915 if (!mread_instr(bp->address, &instr)) {
916 printf("Couldn't read instruction at %lx, "
917 "disabling breakpoint there\n", bp->address);
921 if (!can_single_step(ppc_inst_val(instr))) {
922 printf("Breakpoint at %lx is on an instruction that can't be single stepped, disabling it\n",
928 * Check the address is not a suffix by looking for a prefix in
931 if (mread_instr(bp->address - 4, &instr2) == 8) {
932 printf("Breakpoint at %lx is on the second word of a prefixed instruction, disabling it\n",
938 * We might still be a suffix - if the prefix has already been
939 * replaced by a breakpoint we won't catch it with the above
942 bp2 = at_breakpoint(bp->address - 4);
943 if (bp2 && ppc_inst_prefixed(ppc_inst_read(bp2->instr))) {
944 printf("Breakpoint at %lx is on the second word of a prefixed instruction, disabling it\n",
950 patch_instruction(bp->instr, instr);
951 patch_instruction(ppc_inst_next(bp->instr, bp->instr),
953 if (bp->enabled & BP_CIABR)
955 if (patch_instruction((u32 *)bp->address,
956 ppc_inst(bpinstr)) != 0) {
957 printf("Couldn't write instruction at %lx, "
958 "disabling breakpoint there\n", bp->address);
959 bp->enabled &= ~BP_TRAP;
965 static void insert_cpu_bpts(void)
968 struct arch_hw_breakpoint brk;
970 for (i = 0; i < nr_wp_slots(); i++) {
971 if (dabr[i].enabled) {
972 brk.address = dabr[i].address;
973 brk.type = (dabr[i].enabled & HW_BRK_TYPE_DABR) | HW_BRK_TYPE_PRIV_ALL;
976 __set_breakpoint(i, &brk);
981 set_ciabr(iabr->address);
984 static void remove_bpts(void)
991 for (i = 0; i < NBPTS; ++i, ++bp) {
992 if ((bp->enabled & (BP_TRAP|BP_CIABR)) != BP_TRAP)
994 if (mread_instr(bp->address, &instr)
995 && ppc_inst_equal(instr, ppc_inst(bpinstr))
996 && patch_instruction(
997 (u32 *)bp->address, ppc_inst_read(bp->instr)) != 0)
998 printf("Couldn't remove breakpoint at %lx\n",
1003 static void remove_cpu_bpts(void)
1005 hw_breakpoint_disable();
1009 /* Based on uptime_proc_show(). */
1013 struct timespec64 uptime;
1015 if (setjmp(bus_error_jmp) == 0) {
1016 catch_memory_errors = 1;
1019 ktime_get_coarse_boottime_ts64(&uptime);
1020 printf("Uptime: %lu.%.2lu seconds\n", (unsigned long)uptime.tv_sec,
1021 ((unsigned long)uptime.tv_nsec / (NSEC_PER_SEC/100)));
1026 catch_memory_errors = 0;
1029 static void set_lpp_cmd(void)
1033 if (!scanhex(&lpp)) {
1034 printf("Invalid number.\n");
1037 xmon_set_pagination_lpp(lpp);
1039 /* Command interpreting routine */
1040 static char *last_cmd;
1043 cmds(struct pt_regs *excp)
1050 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
1054 printf("%x:", smp_processor_id());
1055 #endif /* CONFIG_SMP */
1061 if (last_cmd == NULL)
1063 take_input(last_cmd);
1081 printf(xmon_ro_msg);
1101 prregs(excp); /* print regs */
1116 if (do_spu_cmd() == 0)
1123 if (tracing_enabled)
1127 printf(" <no input ...>\n");
1131 xmon_puts(help_string);
1151 printf(xmon_ro_msg);
1159 #if defined(CONFIG_PPC_BOOK3S_32) || defined(CONFIG_PPC_64S_HASH_MMU)
1163 #elif defined(CONFIG_44x)
1167 #elif defined(CONFIG_PPC_BOOK3E_64)
1176 printf("Unrecognized command: ");
1178 if (' ' < cmd && cmd <= '~')
1181 printf("\\x%x", cmd);
1183 } while (cmd != '\n');
1184 printf(" (type ? for help)\n");
1191 static int do_step(struct pt_regs *regs)
1193 regs_set_return_msr(regs, regs->msr | MSR_DE);
1194 mtspr(SPRN_DBCR0, mfspr(SPRN_DBCR0) | DBCR0_IC | DBCR0_IDM);
1199 * Step a single instruction.
1200 * Some instructions we emulate, others we execute with MSR_SE set.
1202 static int do_step(struct pt_regs *regs)
1207 force_enable_xmon();
1208 /* check we are in 64-bit kernel mode, translation enabled */
1209 if ((regs->msr & (MSR_64BIT|MSR_PR|MSR_IR)) == (MSR_64BIT|MSR_IR)) {
1210 if (mread_instr(regs->nip, &instr)) {
1211 stepped = emulate_step(regs, instr);
1213 printf("Couldn't single-step %s instruction\n",
1214 (IS_RFID(instr)? "rfid": "mtmsrd"));
1218 set_trap(regs, 0xd00);
1219 printf("stepped to ");
1220 xmon_print_symbol(regs->nip, " ", "\n");
1221 ppc_inst_dump(regs->nip, 1, 0);
1226 regs_set_return_msr(regs, regs->msr | MSR_SE);
1231 static void bootcmds(void)
1239 ppc_md.restart(tmp);
1240 } else if (cmd == 'h') {
1242 } else if (cmd == 'p') {
1243 do_kernel_power_off();
1248 static int xmon_switch_cpu(unsigned long cpu)
1256 while (!xmon_taken) {
1257 if (--timeout == 0) {
1258 if (test_and_set_bit(0, &xmon_taken))
1260 /* take control back */
1262 xmon_owner = smp_processor_id();
1263 printf("cpu 0x%lx didn't take control\n", cpu);
1271 static int xmon_batch_next_cpu(void)
1275 while (!cpumask_empty(&xmon_batch_cpus)) {
1276 cpu = cpumask_next_wrap(smp_processor_id(), &xmon_batch_cpus,
1277 xmon_batch_start_cpu, true);
1278 if (cpu >= nr_cpu_ids)
1280 if (xmon_batch_start_cpu == -1)
1281 xmon_batch_start_cpu = cpu;
1282 if (xmon_switch_cpu(cpu))
1284 cpumask_clear_cpu(cpu, &xmon_batch_cpus);
1288 printf("%x:mon> \n", smp_processor_id());
1292 static int batch_cmds(struct pt_regs *excp)
1296 /* simulate command entry */
1303 printf("%x:", smp_processor_id());
1305 printf("%c\n", (char)cmd);
1309 prregs(excp); /* print regs */
1319 cpumask_clear_cpu(smp_processor_id(), &xmon_batch_cpus);
1321 return xmon_batch_next_cpu();
1324 static int cpu_cmd(void)
1326 unsigned long cpu, first_cpu, last_cpu;
1330 xmon_batch = skipbl();
1332 switch (xmon_batch) {
1336 cpumask_copy(&xmon_batch_cpus, &cpus_in_xmon);
1337 if (cpumask_weight(&xmon_batch_cpus) <= 1) {
1338 printf("There are no other cpus in xmon\n");
1341 xmon_batch_start_cpu = -1;
1342 if (!xmon_batch_next_cpu())
1346 printf("c# only supports 'r', 'S' and 't' commands\n");
1354 if (!scanhex(&cpu)) {
1355 /* print cpus waiting or in xmon */
1356 printf("cpus stopped:");
1357 last_cpu = first_cpu = NR_CPUS;
1358 for_each_possible_cpu(cpu) {
1359 if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
1360 if (cpu == last_cpu + 1) {
1363 if (last_cpu != first_cpu)
1364 printf("-0x%lx", last_cpu);
1365 last_cpu = first_cpu = cpu;
1366 printf(" 0x%lx", cpu);
1370 if (last_cpu != first_cpu)
1371 printf("-0x%lx", last_cpu);
1375 /* try to switch to cpu specified */
1376 if (!cpumask_test_cpu(cpu, &cpus_in_xmon)) {
1377 printf("cpu 0x%lx isn't in xmon\n", cpu);
1379 printf("backtrace of paca[0x%lx].saved_r1 (possibly stale):\n", cpu);
1380 xmon_show_stack(paca_ptrs[cpu]->saved_r1, 0, 0);
1385 return xmon_switch_cpu(cpu);
1388 static int cpu_cmd(void)
1392 #endif /* CONFIG_SMP */
1394 static unsigned short fcstab[256] = {
1395 0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
1396 0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
1397 0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
1398 0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
1399 0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
1400 0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
1401 0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
1402 0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
1403 0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
1404 0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
1405 0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
1406 0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
1407 0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
1408 0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
1409 0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
1410 0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
1411 0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
1412 0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
1413 0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
1414 0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
1415 0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
1416 0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
1417 0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
1418 0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
1419 0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
1420 0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
1421 0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
1422 0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
1423 0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
1424 0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
1425 0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
1426 0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
1429 #define FCS(fcs, c) (((fcs) >> 8) ^ fcstab[((fcs) ^ (c)) & 0xff])
1438 if (!scanhex(&adrs))
1440 if (!scanhex(&ncsum))
1443 for (i = 0; i < ncsum; ++i) {
1444 if (mread(adrs+i, &v, 1) == 0) {
1445 printf("csum stopped at "REG"\n", adrs+i);
1450 printf("%x\n", fcs);
1454 * Check if this is a suitable place to put a breakpoint.
1456 static long check_bp_loc(unsigned long addr)
1461 if (!is_kernel_addr(addr)) {
1462 printf("Breakpoints may only be placed at kernel addresses\n");
1465 if (!mread_instr(addr, &instr)) {
1466 printf("Can't read instruction at address %lx\n", addr);
1469 if (!can_single_step(ppc_inst_val(instr))) {
1470 printf("Breakpoints may not be placed on instructions that can't be single stepped\n");
1476 static int find_free_data_bpt(void)
1480 for (i = 0; i < nr_wp_slots(); i++) {
1481 if (!dabr[i].enabled)
1484 printf("Couldn't find free breakpoint register\n");
1488 static void print_data_bpts(void)
1492 for (i = 0; i < nr_wp_slots(); i++) {
1493 if (!dabr[i].enabled)
1496 printf(" data "REG" [", dabr[i].address);
1497 if (dabr[i].enabled & 1)
1499 if (dabr[i].enabled & 2)
1505 static char *breakpoint_help_string =
1506 "Breakpoint command usage:\n"
1507 "b show breakpoints\n"
1508 "b <addr> [cnt] set breakpoint at given instr addr\n"
1509 "bc clear all breakpoints\n"
1510 "bc <n/addr> clear breakpoint number n or at addr\n"
1511 "bi <addr> [cnt] set hardware instr breakpoint (POWER8 only)\n"
1512 "bd <addr> [cnt] set hardware data breakpoint\n"
1526 case 'd': { /* bd - hardware data breakpoint */
1527 static const char badaddr[] = "Only kernel addresses are permitted for breakpoints\n";
1530 printf(xmon_ro_msg);
1533 if (!ppc_breakpoint_available()) {
1534 printf("Hardware data breakpoint not supported on this cpu\n");
1537 i = find_free_data_bpt();
1544 else if (cmd == 'w')
1548 dabr[i].address = 0;
1549 dabr[i].enabled = 0;
1550 if (scanhex(&dabr[i].address)) {
1551 if (!is_kernel_addr(dabr[i].address)) {
1555 dabr[i].address &= ~HW_BRK_TYPE_DABR;
1556 dabr[i].enabled = mode | BP_DABR;
1559 force_enable_xmon();
1563 case 'i': /* bi - hardware instr breakpoint */
1565 printf(xmon_ro_msg);
1568 if (!cpu_has_feature(CPU_FTR_ARCH_207S)) {
1569 printf("Hardware instruction breakpoint "
1570 "not supported on this cpu\n");
1574 iabr->enabled &= ~BP_CIABR;
1579 if (!check_bp_loc(a))
1581 bp = new_breakpoint(a);
1583 bp->enabled |= BP_CIABR;
1585 force_enable_xmon();
1591 /* clear all breakpoints */
1592 for (i = 0; i < NBPTS; ++i)
1593 bpts[i].enabled = 0;
1595 for (i = 0; i < nr_wp_slots(); i++)
1596 dabr[i].enabled = 0;
1598 printf("All breakpoints cleared\n");
1602 if (a <= NBPTS && a >= 1) {
1603 /* assume a breakpoint number */
1604 bp = &bpts[a-1]; /* bp nums are 1 based */
1606 /* assume a breakpoint address */
1607 bp = at_breakpoint(a);
1609 printf("No breakpoint at %lx\n", a);
1614 printf("Cleared breakpoint %tx (", BP_NUM(bp));
1615 xmon_print_symbol(bp->address, " ", ")\n");
1623 printf(breakpoint_help_string);
1628 if (xmon_is_ro || !scanhex(&a)) {
1629 /* print all breakpoints */
1630 printf(" type address\n");
1632 for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
1635 printf("%tx %s ", BP_NUM(bp),
1636 (bp->enabled & BP_CIABR) ? "inst": "trap");
1637 xmon_print_symbol(bp->address, " ", "\n");
1642 if (!check_bp_loc(a))
1644 bp = new_breakpoint(a);
1646 bp->enabled |= BP_TRAP;
1647 force_enable_xmon();
1653 /* Very cheap human name for vector lookup. */
1655 const char *getvecname(unsigned long vec)
1660 case 0x100: ret = "(System Reset)"; break;
1661 case 0x200: ret = "(Machine Check)"; break;
1662 case 0x300: ret = "(Data Access)"; break;
1664 if (radix_enabled())
1665 ret = "(Data Access Out of Range)";
1667 ret = "(Data SLB Access)";
1669 case 0x400: ret = "(Instruction Access)"; break;
1671 if (radix_enabled())
1672 ret = "(Instruction Access Out of Range)";
1674 ret = "(Instruction SLB Access)";
1676 case 0x500: ret = "(Hardware Interrupt)"; break;
1677 case 0x600: ret = "(Alignment)"; break;
1678 case 0x700: ret = "(Program Check)"; break;
1679 case 0x800: ret = "(FPU Unavailable)"; break;
1680 case 0x900: ret = "(Decrementer)"; break;
1681 case 0x980: ret = "(Hypervisor Decrementer)"; break;
1682 case 0xa00: ret = "(Doorbell)"; break;
1683 case 0xc00: ret = "(System Call)"; break;
1684 case 0xd00: ret = "(Single Step)"; break;
1685 case 0xe40: ret = "(Emulation Assist)"; break;
1686 case 0xe60: ret = "(HMI)"; break;
1687 case 0xe80: ret = "(Hypervisor Doorbell)"; break;
1688 case 0xf00: ret = "(Performance Monitor)"; break;
1689 case 0xf20: ret = "(Altivec Unavailable)"; break;
1690 case 0x1300: ret = "(Instruction Breakpoint)"; break;
1691 case 0x1500: ret = "(Denormalisation)"; break;
1692 case 0x1700: ret = "(Altivec Assist)"; break;
1693 case 0x3000: ret = "(System Call Vectored)"; break;
1699 static void get_function_bounds(unsigned long pc, unsigned long *startp,
1700 unsigned long *endp)
1702 unsigned long size, offset;
1705 *startp = *endp = 0;
1708 if (setjmp(bus_error_jmp) == 0) {
1709 catch_memory_errors = 1;
1711 name = kallsyms_lookup(pc, &size, &offset, NULL, tmpstr);
1713 *startp = pc - offset;
1714 *endp = pc - offset + size;
1718 catch_memory_errors = 0;
1721 #define LRSAVE_OFFSET (STACK_FRAME_LR_SAVE * sizeof(unsigned long))
1723 static void xmon_show_stack(unsigned long sp, unsigned long lr,
1726 int max_to_print = 64;
1728 unsigned long newsp;
1729 unsigned long marker;
1730 struct pt_regs regs;
1732 while (max_to_print--) {
1733 if (!is_kernel_addr(sp)) {
1735 printf("SP (%lx) is in userspace\n", sp);
1739 if (!mread(sp + LRSAVE_OFFSET, &ip, sizeof(unsigned long))
1740 || !mread(sp, &newsp, sizeof(unsigned long))) {
1741 printf("Couldn't read stack frame at %lx\n", sp);
1746 * For the first stack frame, try to work out if
1747 * LR and/or the saved LR value in the bottommost
1748 * stack frame are valid.
1750 if ((pc | lr) != 0) {
1751 unsigned long fnstart, fnend;
1752 unsigned long nextip;
1755 get_function_bounds(pc, &fnstart, &fnend);
1758 mread(newsp + LRSAVE_OFFSET, &nextip,
1759 sizeof(unsigned long));
1761 if (!is_kernel_addr(lr)
1762 || (fnstart <= lr && lr < fnend))
1764 } else if (lr == nextip) {
1766 } else if (is_kernel_addr(lr)
1767 && !(fnstart <= lr && lr < fnend)) {
1768 printf("[link register ] ");
1769 xmon_print_symbol(lr, " ", "\n");
1772 printf("["REG"] ", sp);
1773 xmon_print_symbol(ip, " ", " (unreliable)\n");
1778 printf("["REG"] ", sp);
1779 xmon_print_symbol(ip, " ", "\n");
1782 /* Look for "regs" marker to see if this is
1783 an exception frame. */
1784 if (mread(sp + STACK_INT_FRAME_MARKER, &marker, sizeof(unsigned long))
1785 && marker == STACK_FRAME_REGS_MARKER) {
1786 if (mread(sp + STACK_INT_FRAME_REGS, ®s, sizeof(regs)) != sizeof(regs)) {
1787 printf("Couldn't read registers at %lx\n",
1788 sp + STACK_INT_FRAME_REGS);
1791 printf("--- Exception: %lx %s at ", regs.trap,
1792 getvecname(TRAP(®s)));
1795 xmon_print_symbol(pc, " ", "\n");
1805 static void backtrace(struct pt_regs *excp)
1810 xmon_show_stack(sp, 0, 0);
1812 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
1816 static void print_bug_trap(struct pt_regs *regs)
1819 const struct bug_entry *bug;
1822 if (regs->msr & MSR_PR)
1823 return; /* not in kernel */
1824 addr = regs->nip; /* address of trap instruction */
1825 if (!is_kernel_addr(addr))
1827 bug = find_bug(regs->nip);
1830 if (is_warning_bug(bug))
1833 #ifdef CONFIG_DEBUG_BUGVERBOSE
1834 printf("kernel BUG at %s:%u!\n",
1835 (char *)bug + bug->file_disp, bug->line);
1837 printf("kernel BUG at %px!\n", (void *)bug + bug->bug_addr_disp);
1839 #endif /* CONFIG_BUG */
1842 static void excprint(struct pt_regs *fp)
1847 printf("cpu 0x%x: ", smp_processor_id());
1848 #endif /* CONFIG_SMP */
1851 printf("Vector: %lx %s at [%px]\n", fp->trap, getvecname(trap), fp);
1853 xmon_print_symbol(fp->nip, ": ", "\n");
1856 xmon_print_symbol(fp->link, ": ", "\n");
1858 printf(" sp: %lx\n", fp->gpr[1]);
1859 printf(" msr: %lx\n", fp->msr);
1861 if (trap == INTERRUPT_DATA_STORAGE ||
1862 trap == INTERRUPT_DATA_SEGMENT ||
1863 trap == INTERRUPT_ALIGNMENT ||
1864 trap == INTERRUPT_MACHINE_CHECK) {
1865 printf(" dar: %lx\n", fp->dar);
1866 if (trap != INTERRUPT_DATA_SEGMENT)
1867 printf(" dsisr: %lx\n", fp->dsisr);
1870 printf(" current = 0x%px\n", current);
1872 printf(" paca = 0x%px\t irqmask: 0x%02x\t irq_happened: 0x%02x\n",
1873 local_paca, local_paca->irq_soft_mask, local_paca->irq_happened);
1876 printf(" pid = %d, comm = %s\n",
1877 current->pid, current->comm);
1880 if (trap == INTERRUPT_PROGRAM)
1883 printf(linux_banner);
1886 static void prregs(struct pt_regs *fp)
1890 struct pt_regs regs;
1892 if (scanhex(&base)) {
1893 if (setjmp(bus_error_jmp) == 0) {
1894 catch_memory_errors = 1;
1896 regs = *(struct pt_regs *)base;
1900 catch_memory_errors = 0;
1901 printf("*** Error reading registers from "REG"\n",
1905 catch_memory_errors = 0;
1910 #define R_PER_LINE 2
1912 #define R_PER_LINE 4
1915 for (n = 0; n < 32; ++n) {
1916 printf("R%.2d = "REG"%s", n, fp->gpr[n],
1917 (n % R_PER_LINE) == R_PER_LINE - 1 ? "\n" : " ");
1921 xmon_print_symbol(fp->nip, " ", "\n");
1922 if (!trap_is_syscall(fp) && cpu_has_feature(CPU_FTR_CFAR)) {
1924 xmon_print_symbol(fp->orig_gpr3, " ", "\n");
1927 xmon_print_symbol(fp->link, " ", "\n");
1928 printf("msr = "REG" cr = %.8lx\n", fp->msr, fp->ccr);
1929 printf("ctr = "REG" xer = "REG" trap = %4lx\n",
1930 fp->ctr, fp->xer, fp->trap);
1932 if (trap == INTERRUPT_DATA_STORAGE ||
1933 trap == INTERRUPT_DATA_SEGMENT ||
1934 trap == INTERRUPT_ALIGNMENT)
1935 printf("dar = "REG" dsisr = %.8lx\n", fp->dar, fp->dsisr);
1938 static void cacheflush(void)
1941 unsigned long nflush;
1946 scanhex((void *)&adrs);
1951 nflush = (nflush + L1_CACHE_BYTES - 1) / L1_CACHE_BYTES;
1952 if (setjmp(bus_error_jmp) == 0) {
1953 catch_memory_errors = 1;
1956 if (cmd != 'i' || IS_ENABLED(CONFIG_PPC_BOOK3S_64)) {
1957 for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1958 cflush((void *) adrs);
1960 for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1961 cinval((void *) adrs);
1964 /* wait a little while to see if we get a machine check */
1967 catch_memory_errors = 0;
1970 extern unsigned long xmon_mfspr(int spr, unsigned long default_value);
1971 extern void xmon_mtspr(int spr, unsigned long value);
1974 read_spr(int n, unsigned long *vp)
1976 unsigned long ret = -1UL;
1979 if (setjmp(bus_error_jmp) == 0) {
1980 catch_spr_faults = 1;
1983 ret = xmon_mfspr(n, *vp);
1989 catch_spr_faults = 0;
1995 write_spr(int n, unsigned long val)
1998 printf(xmon_ro_msg);
2002 if (setjmp(bus_error_jmp) == 0) {
2003 catch_spr_faults = 1;
2010 printf("SPR 0x%03x (%4d) Faulted during write\n", n, n);
2012 catch_spr_faults = 0;
2015 static void dump_206_sprs(void)
2018 if (!cpu_has_feature(CPU_FTR_ARCH_206))
2021 /* Actually some of these pre-date 2.06, but whatever */
2023 printf("srr0 = %.16lx srr1 = %.16lx dsisr = %.8lx\n",
2024 mfspr(SPRN_SRR0), mfspr(SPRN_SRR1), mfspr(SPRN_DSISR));
2025 printf("dscr = %.16lx ppr = %.16lx pir = %.8lx\n",
2026 mfspr(SPRN_DSCR), mfspr(SPRN_PPR), mfspr(SPRN_PIR));
2027 printf("amr = %.16lx uamor = %.16lx\n",
2028 mfspr(SPRN_AMR), mfspr(SPRN_UAMOR));
2030 if (!(mfmsr() & MSR_HV))
2033 printf("sdr1 = %.16lx hdar = %.16lx hdsisr = %.8lx\n",
2034 mfspr(SPRN_SDR1), mfspr(SPRN_HDAR), mfspr(SPRN_HDSISR));
2035 printf("hsrr0 = %.16lx hsrr1 = %.16lx hdec = %.16lx\n",
2036 mfspr(SPRN_HSRR0), mfspr(SPRN_HSRR1), mfspr(SPRN_HDEC));
2037 printf("lpcr = %.16lx pcr = %.16lx lpidr = %.8lx\n",
2038 mfspr(SPRN_LPCR), mfspr(SPRN_PCR), mfspr(SPRN_LPID));
2039 printf("hsprg0 = %.16lx hsprg1 = %.16lx amor = %.16lx\n",
2040 mfspr(SPRN_HSPRG0), mfspr(SPRN_HSPRG1), mfspr(SPRN_AMOR));
2041 printf("dabr = %.16lx dabrx = %.16lx\n",
2042 mfspr(SPRN_DABR), mfspr(SPRN_DABRX));
2046 static void dump_207_sprs(void)
2051 if (!cpu_has_feature(CPU_FTR_ARCH_207S))
2054 printf("dpdes = %.16lx tir = %.16lx cir = %.8lx\n",
2055 mfspr(SPRN_DPDES), mfspr(SPRN_TIR), mfspr(SPRN_CIR));
2057 printf("fscr = %.16lx tar = %.16lx pspb = %.8lx\n",
2058 mfspr(SPRN_FSCR), mfspr(SPRN_TAR), mfspr(SPRN_PSPB));
2062 /* Only if TM has been enabled in the kernel */
2063 printf("tfhar = %.16lx tfiar = %.16lx texasr = %.16lx\n",
2064 mfspr(SPRN_TFHAR), mfspr(SPRN_TFIAR),
2065 mfspr(SPRN_TEXASR));
2068 printf("mmcr0 = %.16lx mmcr1 = %.16lx mmcr2 = %.16lx\n",
2069 mfspr(SPRN_MMCR0), mfspr(SPRN_MMCR1), mfspr(SPRN_MMCR2));
2070 printf("pmc1 = %.8lx pmc2 = %.8lx pmc3 = %.8lx pmc4 = %.8lx\n",
2071 mfspr(SPRN_PMC1), mfspr(SPRN_PMC2),
2072 mfspr(SPRN_PMC3), mfspr(SPRN_PMC4));
2073 printf("mmcra = %.16lx siar = %.16lx pmc5 = %.8lx\n",
2074 mfspr(SPRN_MMCRA), mfspr(SPRN_SIAR), mfspr(SPRN_PMC5));
2075 printf("sdar = %.16lx sier = %.16lx pmc6 = %.8lx\n",
2076 mfspr(SPRN_SDAR), mfspr(SPRN_SIER), mfspr(SPRN_PMC6));
2077 printf("ebbhr = %.16lx ebbrr = %.16lx bescr = %.16lx\n",
2078 mfspr(SPRN_EBBHR), mfspr(SPRN_EBBRR), mfspr(SPRN_BESCR));
2079 printf("iamr = %.16lx\n", mfspr(SPRN_IAMR));
2081 if (!(msr & MSR_HV))
2084 printf("hfscr = %.16lx dhdes = %.16lx rpr = %.16lx\n",
2085 mfspr(SPRN_HFSCR), mfspr(SPRN_DHDES), mfspr(SPRN_RPR));
2086 printf("dawr0 = %.16lx dawrx0 = %.16lx\n",
2087 mfspr(SPRN_DAWR0), mfspr(SPRN_DAWRX0));
2088 if (nr_wp_slots() > 1) {
2089 printf("dawr1 = %.16lx dawrx1 = %.16lx\n",
2090 mfspr(SPRN_DAWR1), mfspr(SPRN_DAWRX1));
2092 printf("ciabr = %.16lx\n", mfspr(SPRN_CIABR));
2096 static void dump_300_sprs(void)
2099 bool hv = mfmsr() & MSR_HV;
2101 if (!cpu_has_feature(CPU_FTR_ARCH_300))
2104 if (cpu_has_feature(CPU_FTR_P9_TIDR)) {
2105 printf("pidr = %.16lx tidr = %.16lx\n",
2106 mfspr(SPRN_PID), mfspr(SPRN_TIDR));
2108 printf("pidr = %.16lx\n",
2112 printf("psscr = %.16lx\n",
2113 hv ? mfspr(SPRN_PSSCR) : mfspr(SPRN_PSSCR_PR));
2118 printf("ptcr = %.16lx asdr = %.16lx\n",
2119 mfspr(SPRN_PTCR), mfspr(SPRN_ASDR));
2123 static void dump_310_sprs(void)
2126 if (!cpu_has_feature(CPU_FTR_ARCH_31))
2129 printf("mmcr3 = %.16lx, sier2 = %.16lx, sier3 = %.16lx\n",
2130 mfspr(SPRN_MMCR3), mfspr(SPRN_SIER2), mfspr(SPRN_SIER3));
2135 static void dump_one_spr(int spr, bool show_unimplemented)
2140 if (!read_spr(spr, &val)) {
2141 printf("SPR 0x%03x (%4d) Faulted during read\n", spr, spr);
2145 if (val == 0xdeadbeef) {
2146 /* Looks like read was a nop, confirm */
2148 if (!read_spr(spr, &val)) {
2149 printf("SPR 0x%03x (%4d) Faulted during read\n", spr, spr);
2153 if (val == 0x0badcafe) {
2154 if (show_unimplemented)
2155 printf("SPR 0x%03x (%4d) Unimplemented\n", spr, spr);
2160 printf("SPR 0x%03x (%4d) = 0x%lx\n", spr, spr, val);
2163 static void super_regs(void)
2165 static unsigned long regno;
2173 unsigned long sp, toc;
2174 asm("mr %0,1" : "=r" (sp) :);
2175 asm("mr %0,2" : "=r" (toc) :);
2177 printf("msr = "REG" sprg0 = "REG"\n",
2178 mfmsr(), mfspr(SPRN_SPRG0));
2179 printf("pvr = "REG" sprg1 = "REG"\n",
2180 mfspr(SPRN_PVR), mfspr(SPRN_SPRG1));
2181 printf("dec = "REG" sprg2 = "REG"\n",
2182 mfspr(SPRN_DEC), mfspr(SPRN_SPRG2));
2183 printf("sp = "REG" sprg3 = "REG"\n", sp, mfspr(SPRN_SPRG3));
2184 printf("toc = "REG" dar = "REG"\n", toc, mfspr(SPRN_DAR));
2197 read_spr(regno, &val);
2199 write_spr(regno, val);
2200 dump_one_spr(regno, true);
2205 dump_one_spr(regno, true);
2209 for (spr = 1; spr < 1024; ++spr)
2210 dump_one_spr(spr, false);
2218 * Stuff for reading and writing memory safely
2221 mread(unsigned long adrs, void *buf, int size)
2227 if (setjmp(bus_error_jmp) == 0) {
2228 catch_memory_errors = 1;
2234 *(u16 *)q = *(u16 *)p;
2237 *(u32 *)q = *(u32 *)p;
2240 *(u64 *)q = *(u64 *)p;
2243 for( ; n < size; ++n) {
2249 /* wait a little while to see if we get a machine check */
2253 catch_memory_errors = 0;
2258 mwrite(unsigned long adrs, void *buf, int size)
2266 printf(xmon_ro_msg);
2270 if (setjmp(bus_error_jmp) == 0) {
2271 catch_memory_errors = 1;
2277 *(u16 *)p = *(u16 *)q;
2280 *(u32 *)p = *(u32 *)q;
2283 *(u64 *)p = *(u64 *)q;
2286 for ( ; n < size; ++n) {
2292 /* wait a little while to see if we get a machine check */
2296 printf("*** Error writing address "REG"\n", adrs + n);
2298 catch_memory_errors = 0;
2303 mread_instr(unsigned long adrs, ppc_inst_t *instr)
2308 if (setjmp(bus_error_jmp) == 0) {
2309 catch_memory_errors = 1;
2311 *instr = ppc_inst_read((u32 *)adrs);
2313 /* wait a little while to see if we get a machine check */
2315 n = ppc_inst_len(*instr);
2317 catch_memory_errors = 0;
2321 static int fault_type;
2322 static int fault_except;
2323 static char *fault_chars[] = { "--", "**", "##" };
2325 static int handle_fault(struct pt_regs *regs)
2327 fault_except = TRAP(regs);
2328 switch (TRAP(regs)) {
2340 longjmp(bus_error_jmp, 1);
2345 #define SWAP(a, b, t) ((t) = (a), (a) = (b), (b) = (t))
2348 byterev(unsigned char *val, int size)
2354 SWAP(val[0], val[1], t);
2357 SWAP(val[0], val[3], t);
2358 SWAP(val[1], val[2], t);
2360 case 8: /* is there really any use for this? */
2361 SWAP(val[0], val[7], t);
2362 SWAP(val[1], val[6], t);
2363 SWAP(val[2], val[5], t);
2364 SWAP(val[3], val[4], t);
2372 static char *memex_help_string =
2373 "Memory examine command usage:\n"
2374 "m [addr] [flags] examine/change memory\n"
2375 " addr is optional. will start where left off.\n"
2376 " flags may include chars from this set:\n"
2377 " b modify by bytes (default)\n"
2378 " w modify by words (2 byte)\n"
2379 " l modify by longs (4 byte)\n"
2380 " d modify by doubleword (8 byte)\n"
2381 " r toggle reverse byte order mode\n"
2382 " n do not read memory (for i/o spaces)\n"
2383 " . ok to read (default)\n"
2384 "NOTE: flags are saved as defaults\n"
2387 static char *memex_subcmd_help_string =
2388 "Memory examine subcommands:\n"
2389 " hexval write this val to current location\n"
2390 " 'string' write chars from string to this location\n"
2391 " ' increment address\n"
2392 " ^ decrement address\n"
2393 " / increment addr by 0x10. //=0x100, ///=0x1000, etc\n"
2394 " \\ decrement addr by 0x10. \\\\=0x100, \\\\\\=0x1000, etc\n"
2395 " ` clear no-read flag\n"
2396 " ; stay at this addr\n"
2397 " v change to byte mode\n"
2398 " w change to word (2 byte) mode\n"
2399 " l change to long (4 byte) mode\n"
2400 " u change to doubleword (8 byte) mode\n"
2401 " m addr change current addr\n"
2402 " n toggle no-read flag\n"
2403 " r toggle byte reverse flag\n"
2404 " < count back up count bytes\n"
2405 " > count skip forward count bytes\n"
2406 " x exit this mode\n"
2412 int cmd, inc, i, nslash;
2414 unsigned char val[16];
2416 scanhex((void *)&adrs);
2419 printf(memex_help_string);
2425 while ((cmd = skipbl()) != '\n') {
2427 case 'b': size = 1; break;
2428 case 'w': size = 2; break;
2429 case 'l': size = 4; break;
2430 case 'd': size = 8; break;
2431 case 'r': brev = !brev; break;
2432 case 'n': mnoread = 1; break;
2433 case '.': mnoread = 0; break;
2442 n = mread(adrs, val, size);
2443 printf(REG"%c", adrs, brev? 'r': ' ');
2448 for (i = 0; i < n; ++i)
2449 printf("%.2x", val[i]);
2450 for (; i < size; ++i)
2451 printf("%s", fault_chars[fault_type]);
2458 for (i = 0; i < size; ++i)
2459 val[i] = n >> (i * 8);
2462 mwrite(adrs, val, size);
2475 else if( n == '\'' )
2477 for (i = 0; i < size; ++i)
2478 val[i] = n >> (i * 8);
2481 mwrite(adrs, val, size);
2517 adrs -= 1 << nslash;
2521 adrs += 1 << nslash;
2525 adrs += 1 << -nslash;
2529 adrs -= 1 << -nslash;
2532 scanhex((void *)&adrs);
2551 printf(memex_subcmd_help_string);
2566 case 'n': c = '\n'; break;
2567 case 'r': c = '\r'; break;
2568 case 'b': c = '\b'; break;
2569 case 't': c = '\t'; break;
2574 static void xmon_rawdump (unsigned long adrs, long ndump)
2577 unsigned char temp[16];
2579 for (n = ndump; n > 0;) {
2581 nr = mread(adrs, temp, r);
2583 for (m = 0; m < r; ++m) {
2585 printf("%.2x", temp[m]);
2587 printf("%s", fault_chars[fault_type]);
2596 static void dump_tracing(void)
2602 ftrace_dump(DUMP_ORIG);
2604 ftrace_dump(DUMP_ALL);
2608 static void dump_one_paca(int cpu)
2610 struct paca_struct *p;
2611 #ifdef CONFIG_PPC_64S_HASH_MMU
2615 if (setjmp(bus_error_jmp) != 0) {
2616 printf("*** Error dumping paca for cpu 0x%x!\n", cpu);
2620 catch_memory_errors = 1;
2625 printf("paca for cpu 0x%x @ %px:\n", cpu, p);
2627 printf(" %-*s = %s\n", 25, "possible", cpu_possible(cpu) ? "yes" : "no");
2628 printf(" %-*s = %s\n", 25, "present", cpu_present(cpu) ? "yes" : "no");
2629 printf(" %-*s = %s\n", 25, "online", cpu_online(cpu) ? "yes" : "no");
2631 #define DUMP(paca, name, format) \
2632 printf(" %-*s = "format"\t(0x%lx)\n", 25, #name, 18, paca->name, \
2633 offsetof(struct paca_struct, name));
2635 DUMP(p, lock_token, "%#-*x");
2636 DUMP(p, paca_index, "%#-*x");
2637 #ifndef CONFIG_PPC_KERNEL_PCREL
2638 DUMP(p, kernel_toc, "%#-*llx");
2640 DUMP(p, kernelbase, "%#-*llx");
2641 DUMP(p, kernel_msr, "%#-*llx");
2642 DUMP(p, emergency_sp, "%-*px");
2643 #ifdef CONFIG_PPC_BOOK3S_64
2644 DUMP(p, nmi_emergency_sp, "%-*px");
2645 DUMP(p, mc_emergency_sp, "%-*px");
2646 DUMP(p, in_nmi, "%#-*x");
2647 DUMP(p, in_mce, "%#-*x");
2648 DUMP(p, hmi_event_available, "%#-*x");
2650 DUMP(p, data_offset, "%#-*llx");
2651 DUMP(p, hw_cpu_id, "%#-*x");
2652 DUMP(p, cpu_start, "%#-*x");
2653 DUMP(p, kexec_state, "%#-*x");
2654 #ifdef CONFIG_PPC_BOOK3S_64
2655 #ifdef CONFIG_PPC_64S_HASH_MMU
2656 if (!early_radix_enabled()) {
2657 for (i = 0; i < SLB_NUM_BOLTED; i++) {
2660 if (!p->slb_shadow_ptr)
2663 esid = be64_to_cpu(p->slb_shadow_ptr->save_area[i].esid);
2664 vsid = be64_to_cpu(p->slb_shadow_ptr->save_area[i].vsid);
2667 printf(" %-*s[%d] = 0x%016llx 0x%016llx\n",
2668 22, "slb_shadow", i, esid, vsid);
2671 DUMP(p, vmalloc_sllp, "%#-*x");
2672 DUMP(p, stab_rr, "%#-*x");
2673 DUMP(p, slb_used_bitmap, "%#-*x");
2674 DUMP(p, slb_kern_bitmap, "%#-*x");
2676 if (!early_cpu_has_feature(CPU_FTR_ARCH_300)) {
2677 DUMP(p, slb_cache_ptr, "%#-*x");
2678 for (i = 0; i < SLB_CACHE_ENTRIES; i++)
2679 printf(" %-*s[%d] = 0x%016x\n",
2680 22, "slb_cache", i, p->slb_cache[i]);
2685 DUMP(p, rfi_flush_fallback_area, "%-*px");
2687 DUMP(p, dscr_default, "%#-*llx");
2688 #ifdef CONFIG_PPC_BOOK3E_64
2689 DUMP(p, pgd, "%-*px");
2690 DUMP(p, kernel_pgd, "%-*px");
2691 DUMP(p, tcd_ptr, "%-*px");
2692 DUMP(p, mc_kstack, "%-*px");
2693 DUMP(p, crit_kstack, "%-*px");
2694 DUMP(p, dbg_kstack, "%-*px");
2696 DUMP(p, __current, "%-*px");
2697 DUMP(p, kstack, "%#-*llx");
2698 printf(" %-*s = 0x%016llx\n", 25, "kstack_base", p->kstack & ~(THREAD_SIZE - 1));
2699 #ifdef CONFIG_STACKPROTECTOR
2700 DUMP(p, canary, "%#-*lx");
2702 DUMP(p, saved_r1, "%#-*llx");
2703 #ifdef CONFIG_PPC_BOOK3E_64
2704 DUMP(p, trap_save, "%#-*x");
2706 DUMP(p, irq_soft_mask, "%#-*x");
2707 DUMP(p, irq_happened, "%#-*x");
2708 #ifdef CONFIG_MMIOWB
2709 DUMP(p, mmiowb_state.nesting_count, "%#-*x");
2710 DUMP(p, mmiowb_state.mmiowb_pending, "%#-*x");
2712 DUMP(p, irq_work_pending, "%#-*x");
2713 DUMP(p, sprg_vdso, "%#-*llx");
2715 #ifdef CONFIG_PPC_TRANSACTIONAL_MEM
2716 DUMP(p, tm_scratch, "%#-*llx");
2719 #ifdef CONFIG_PPC_POWERNV
2720 DUMP(p, idle_state, "%#-*lx");
2721 if (!early_cpu_has_feature(CPU_FTR_ARCH_300)) {
2722 DUMP(p, thread_idle_state, "%#-*x");
2723 DUMP(p, subcore_sibling_mask, "%#-*x");
2725 #ifdef CONFIG_KVM_BOOK3S_HV_POSSIBLE
2726 DUMP(p, requested_psscr, "%#-*llx");
2727 DUMP(p, dont_stop.counter, "%#-*x");
2732 DUMP(p, accounting.utime, "%#-*lx");
2733 DUMP(p, accounting.stime, "%#-*lx");
2734 #ifdef CONFIG_ARCH_HAS_SCALED_CPUTIME
2735 DUMP(p, accounting.utime_scaled, "%#-*lx");
2737 DUMP(p, accounting.starttime, "%#-*lx");
2738 DUMP(p, accounting.starttime_user, "%#-*lx");
2739 #ifdef CONFIG_ARCH_HAS_SCALED_CPUTIME
2740 DUMP(p, accounting.startspurr, "%#-*lx");
2741 DUMP(p, accounting.utime_sspurr, "%#-*lx");
2743 DUMP(p, accounting.steal_time, "%#-*lx");
2746 catch_memory_errors = 0;
2750 static void dump_all_pacas(void)
2754 if (num_possible_cpus() == 0) {
2755 printf("No possible cpus, use 'dp #' to dump individual cpus\n");
2759 for_each_possible_cpu(cpu)
2763 static void dump_pacas(void)
2774 termch = c; /* Put c back, it wasn't 'a' */
2779 dump_one_paca(xmon_owner);
2783 #ifdef CONFIG_PPC_POWERNV
2784 static void dump_one_xive(int cpu)
2786 unsigned int hwid = get_hard_smp_processor_id(cpu);
2787 bool hv = cpu_has_feature(CPU_FTR_HVMODE);
2790 opal_xive_dump(XIVE_DUMP_TM_HYP, hwid);
2791 opal_xive_dump(XIVE_DUMP_TM_POOL, hwid);
2792 opal_xive_dump(XIVE_DUMP_TM_OS, hwid);
2793 opal_xive_dump(XIVE_DUMP_TM_USER, hwid);
2794 opal_xive_dump(XIVE_DUMP_VP, hwid);
2795 opal_xive_dump(XIVE_DUMP_EMU_STATE, hwid);
2798 if (setjmp(bus_error_jmp) != 0) {
2799 catch_memory_errors = 0;
2800 printf("*** Error dumping xive on cpu %d\n", cpu);
2804 catch_memory_errors = 1;
2806 xmon_xive_do_dump(cpu);
2809 catch_memory_errors = 0;
2812 static void dump_all_xives(void)
2816 if (num_online_cpus() == 0) {
2817 printf("No possible cpus, use 'dx #' to dump individual cpus\n");
2821 for_each_online_cpu(cpu)
2825 static void dump_xives(void)
2830 if (!xive_enabled()) {
2831 printf("Xive disabled on this system\n");
2839 } else if (c == 'i') {
2841 xmon_xive_get_irq_config(num, NULL);
2843 xmon_xive_get_irq_all();
2847 termch = c; /* Put c back, it wasn't 'a' */
2852 dump_one_xive(xmon_owner);
2854 #endif /* CONFIG_PPC_POWERNV */
2856 static void dump_by_size(unsigned long addr, long count, int size)
2858 unsigned char temp[16];
2862 count = ALIGN(count, 16);
2864 for (i = 0; i < count; i += 16, addr += 16) {
2867 if (mread(addr, temp, 16) != 16) {
2868 printf("\nFaulted reading %d bytes from 0x"REG"\n", 16, addr);
2872 for (j = 0; j < 16; j += size) {
2875 case 1: val = temp[j]; break;
2876 case 2: val = *(u16 *)&temp[j]; break;
2877 case 4: val = *(u32 *)&temp[j]; break;
2878 case 8: val = *(u64 *)&temp[j]; break;
2882 printf("%0*llx", size * 2, val);
2885 for (j = 0; j < 16; ++j) {
2887 putchar(' ' <= val && val <= '~' ? val : '.');
2896 static char last[] = { "d?\n" };
2903 xmon_start_pagination();
2905 xmon_end_pagination();
2909 #ifdef CONFIG_PPC_POWERNV
2911 xmon_start_pagination();
2913 xmon_end_pagination();
2926 scanhex((void *)&adrs);
2933 else if (nidump > MAX_IDUMP)
2935 adrs += ppc_inst_dump(adrs, nidump, 1);
2937 } else if (c == 'l') {
2939 } else if (c == 'o') {
2941 } else if (c == 'v') {
2942 /* dump virtual to physical translation */
2944 } else if (c == 'r') {
2948 xmon_rawdump(adrs, ndump);
2955 else if (ndump > MAX_DUMP)
2963 ndump = ALIGN(ndump, 16);
2964 dump_by_size(adrs, ndump, c - '0');
2969 prdump(adrs, ndump);
2978 prdump(unsigned long adrs, long ndump)
2980 long n, m, c, r, nr;
2981 unsigned char temp[16];
2983 for (n = ndump; n > 0;) {
2987 nr = mread(adrs, temp, r);
2989 for (m = 0; m < r; ++m) {
2990 if ((m & (sizeof(long) - 1)) == 0 && m > 0)
2993 printf("%.2x", temp[m]);
2995 printf("%s", fault_chars[fault_type]);
2997 for (; m < 16; ++m) {
2998 if ((m & (sizeof(long) - 1)) == 0)
3003 for (m = 0; m < r; ++m) {
3006 putchar(' ' <= c && c <= '~'? c: '.');
3019 typedef int (*instruction_dump_func)(unsigned long inst, unsigned long addr);
3022 generic_inst_dump(unsigned long adr, long count, int praddr,
3023 instruction_dump_func dump_func)
3026 unsigned long first_adr;
3027 ppc_inst_t inst, last_inst = ppc_inst(0);
3030 for (first_adr = adr; count > 0; --count, adr += ppc_inst_len(inst)) {
3031 nr = mread_instr(adr, &inst);
3034 const char *x = fault_chars[fault_type];
3035 printf(REG" %s%s%s%s\n", adr, x, x, x, x);
3039 if (adr > first_adr && ppc_inst_equal(inst, last_inst)) {
3049 printf(REG" %08lx", adr, ppc_inst_as_ulong(inst));
3051 if (!ppc_inst_prefixed(inst))
3052 dump_func(ppc_inst_val(inst), adr);
3054 dump_func(ppc_inst_as_ulong(inst), adr);
3057 return adr - first_adr;
3061 ppc_inst_dump(unsigned long adr, long count, int praddr)
3063 return generic_inst_dump(adr, count, praddr, print_insn_powerpc);
3067 print_address(unsigned long addr)
3069 xmon_print_symbol(addr, "\t# ", "");
3075 struct kmsg_dump_iter iter;
3076 static unsigned char buf[1024];
3079 if (setjmp(bus_error_jmp) != 0) {
3080 printf("Error dumping printk buffer!\n");
3084 catch_memory_errors = 1;
3087 kmsg_dump_rewind(&iter);
3088 xmon_start_pagination();
3089 while (kmsg_dump_get_line(&iter, false, buf, sizeof(buf), &len)) {
3093 xmon_end_pagination();
3096 /* wait a little while to see if we get a machine check */
3098 catch_memory_errors = 0;
3101 #ifdef CONFIG_PPC_POWERNV
3102 static void dump_opal_msglog(void)
3104 unsigned char buf[128];
3106 volatile loff_t pos = 0;
3108 if (!firmware_has_feature(FW_FEATURE_OPAL)) {
3109 printf("Machine is not running OPAL firmware.\n");
3113 if (setjmp(bus_error_jmp) != 0) {
3114 printf("Error dumping OPAL msglog!\n");
3118 catch_memory_errors = 1;
3121 xmon_start_pagination();
3122 while ((res = opal_msglog_copy(buf, pos, sizeof(buf) - 1))) {
3124 printf("Error dumping OPAL msglog! Error: %zd\n", res);
3131 xmon_end_pagination();
3134 /* wait a little while to see if we get a machine check */
3136 catch_memory_errors = 0;
3141 * Memory operations - move, set, print differences
3143 static unsigned long mdest; /* destination address */
3144 static unsigned long msrc; /* source address */
3145 static unsigned long mval; /* byte value to set memory to */
3146 static unsigned long mcount; /* # bytes to affect */
3147 static unsigned long mdiffs; /* max # differences to print */
3152 scanhex((void *)&mdest);
3153 if( termch != '\n' )
3155 scanhex((void *)(cmd == 's'? &mval: &msrc));
3156 if( termch != '\n' )
3158 scanhex((void *)&mcount);
3162 printf(xmon_ro_msg);
3165 memmove((void *)mdest, (void *)msrc, mcount);
3169 printf(xmon_ro_msg);
3172 memset((void *)mdest, mval, mcount);
3175 if( termch != '\n' )
3177 scanhex((void *)&mdiffs);
3178 memdiffs((unsigned char *)mdest, (unsigned char *)msrc, mcount, mdiffs);
3184 memdiffs(unsigned char *p1, unsigned char *p2, unsigned nb, unsigned maxpr)
3189 for( n = nb; n > 0; --n )
3190 if( *p1++ != *p2++ )
3191 if( ++prt <= maxpr )
3192 printf("%px %.2x # %px %.2x\n", p1 - 1,
3193 p1[-1], p2 - 1, p2[-1]);
3195 printf("Total of %d differences\n", prt);
3198 static unsigned mend;
3199 static unsigned mask;
3205 unsigned char val[4];
3208 scanhex((void *)&mdest);
3209 if (termch != '\n') {
3211 scanhex((void *)&mend);
3212 if (termch != '\n') {
3214 scanhex((void *)&mval);
3216 if (termch != '\n') termch = 0;
3217 scanhex((void *)&mask);
3221 for (a = mdest; a < mend; a += 4) {
3222 if (mread(a, val, 4) == 4
3223 && ((GETWORD(val) ^ mval) & mask) == 0) {
3224 printf("%.16x: %.16x\n", a, GETWORD(val));
3231 static unsigned long mskip = 0x1000;
3232 static unsigned long mlim = 0xffffffff;
3242 if (termch != '\n') termch = 0;
3244 if (termch != '\n') termch = 0;
3247 for (a = mdest; a < mlim; a += mskip) {
3248 ok = mread(a, &v, 1);
3250 printf("%.8x .. ", a);
3251 } else if (!ok && ook)
3252 printf("%.8lx\n", a - mskip);
3258 printf("%.8lx\n", a - mskip);
3261 static void show_task(struct task_struct *volatile tsk)
3263 unsigned int p_state = READ_ONCE(tsk->__state);
3267 * Cloned from kdb_task_state_char(), which is not entirely
3268 * appropriate for calling from xmon. This could be moved
3269 * to a common, generic, routine used by both.
3271 state = (p_state == TASK_RUNNING) ? 'R' :
3272 (p_state & TASK_UNINTERRUPTIBLE) ? 'D' :
3273 (p_state & TASK_STOPPED) ? 'T' :
3274 (p_state & TASK_TRACED) ? 'C' :
3275 (tsk->exit_state & EXIT_ZOMBIE) ? 'Z' :
3276 (tsk->exit_state & EXIT_DEAD) ? 'E' :
3277 (p_state & TASK_INTERRUPTIBLE) ? 'S' : '?';
3279 printf("%16px %16lx %16px %6d %6d %c %2d %s\n", tsk,
3280 tsk->thread.ksp, tsk->thread.regs,
3281 tsk->pid, rcu_dereference(tsk->parent)->pid,
3282 state, task_cpu(tsk),
3286 #ifdef CONFIG_PPC_BOOK3S_64
3287 static void format_pte(void *ptep, unsigned long pte)
3289 pte_t entry = __pte(pte);
3291 printf("ptep @ 0x%016lx = 0x%016lx\n", (unsigned long)ptep, pte);
3292 printf("Maps physical address = 0x%016lx\n", pte & PTE_RPN_MASK);
3294 printf("Flags = %s%s%s%s%s\n",
3295 pte_young(entry) ? "Accessed " : "",
3296 pte_dirty(entry) ? "Dirty " : "",
3297 pte_read(entry) ? "Read " : "",
3298 pte_write(entry) ? "Write " : "",
3299 pte_exec(entry) ? "Exec " : "");
3302 static void show_pte(unsigned long addr)
3304 unsigned long tskv = 0;
3305 struct task_struct *volatile tsk = NULL;
3306 struct mm_struct *mm;
3313 if (!scanhex(&tskv))
3316 tsk = (struct task_struct *)tskv;
3321 mm = tsk->active_mm;
3323 if (setjmp(bus_error_jmp) != 0) {
3324 catch_memory_errors = 0;
3325 printf("*** Error dumping pte for task %px\n", tsk);
3329 catch_memory_errors = 1;
3333 pgdp = pgd_offset_k(addr);
3335 pgdp = pgd_offset(mm, addr);
3337 p4dp = p4d_offset(pgdp, addr);
3339 if (p4d_none(*p4dp)) {
3340 printf("No valid P4D\n");
3344 if (p4d_is_leaf(*p4dp)) {
3345 format_pte(p4dp, p4d_val(*p4dp));
3349 printf("p4dp @ 0x%px = 0x%016lx\n", p4dp, p4d_val(*p4dp));
3351 pudp = pud_offset(p4dp, addr);
3353 if (pud_none(*pudp)) {
3354 printf("No valid PUD\n");
3358 if (pud_is_leaf(*pudp)) {
3359 format_pte(pudp, pud_val(*pudp));
3363 printf("pudp @ 0x%px = 0x%016lx\n", pudp, pud_val(*pudp));
3365 pmdp = pmd_offset(pudp, addr);
3367 if (pmd_none(*pmdp)) {
3368 printf("No valid PMD\n");
3372 if (pmd_is_leaf(*pmdp)) {
3373 format_pte(pmdp, pmd_val(*pmdp));
3376 printf("pmdp @ 0x%px = 0x%016lx\n", pmdp, pmd_val(*pmdp));
3378 ptep = pte_offset_map(pmdp, addr);
3379 if (pte_none(*ptep)) {
3380 printf("no valid PTE\n");
3384 format_pte(ptep, pte_val(*ptep));
3388 catch_memory_errors = 0;
3391 static void show_pte(unsigned long addr)
3393 printf("show_pte not yet implemented\n");
3395 #endif /* CONFIG_PPC_BOOK3S_64 */
3397 static void show_tasks(void)
3400 struct task_struct *volatile tsk = NULL;
3402 printf(" task_struct ->thread.ksp ->thread.regs PID PPID S P CMD\n");
3405 tsk = (struct task_struct *)tskv;
3407 if (setjmp(bus_error_jmp) != 0) {
3408 catch_memory_errors = 0;
3409 printf("*** Error dumping task %px\n", tsk);
3413 catch_memory_errors = 1;
3419 for_each_process(tsk)
3424 catch_memory_errors = 0;
3427 static void proccall(void)
3429 unsigned long args[8];
3432 typedef unsigned long (*callfunc_t)(unsigned long, unsigned long,
3433 unsigned long, unsigned long, unsigned long,
3434 unsigned long, unsigned long, unsigned long);
3437 if (!scanhex(&adrs))
3441 for (i = 0; i < 8; ++i)
3443 for (i = 0; i < 8; ++i) {
3444 if (!scanhex(&args[i]) || termch == '\n')
3448 func = (callfunc_t) adrs;
3450 if (setjmp(bus_error_jmp) == 0) {
3451 catch_memory_errors = 1;
3453 ret = func(args[0], args[1], args[2], args[3],
3454 args[4], args[5], args[6], args[7]);
3456 printf("return value is 0x%lx\n", ret);
3458 printf("*** %x exception occurred\n", fault_except);
3460 catch_memory_errors = 0;
3463 /* Input scanning routines */
3474 while( c == ' ' || c == '\t' )
3480 static const char *regnames[N_PTREGS] = {
3481 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
3482 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
3483 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
3484 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
3485 "pc", "msr", "or3", "ctr", "lr", "xer", "ccr",
3491 "trap", "dar", "dsisr", "res"
3495 scanhex(unsigned long *vp)
3502 /* parse register name */
3506 for (i = 0; i < sizeof(regname) - 1; ++i) {
3515 i = match_string(regnames, N_PTREGS, regname);
3517 printf("invalid register name '%%%s'\n", regname);
3520 if (xmon_regs == NULL) {
3521 printf("regs not available\n");
3524 *vp = ((unsigned long *)xmon_regs)[i];
3528 /* skip leading "0x" if any */
3542 } else if (c == '$') {
3544 for (i=0; i<63; i++) {
3546 if (isspace(c) || c == '\0') {
3554 if (setjmp(bus_error_jmp) == 0) {
3555 catch_memory_errors = 1;
3557 *vp = kallsyms_lookup_name(tmpstr);
3560 catch_memory_errors = 0;
3562 printf("unknown symbol '%s'\n", tmpstr);
3595 static int hexdigit(int c)
3597 if( '0' <= c && c <= '9' )
3599 if( 'A' <= c && c <= 'F' )
3600 return c - ('A' - 10);
3601 if( 'a' <= c && c <= 'f' )
3602 return c - ('a' - 10);
3607 getstring(char *s, int size)
3623 } while( c != ' ' && c != '\t' && c != '\n' );
3628 static char line[256];
3629 static char *lineptr;
3640 if (lineptr == NULL || *lineptr == 0) {
3641 if (xmon_gets(line, sizeof(line)) == NULL) {
3651 take_input(char *str)
3660 int type = inchar();
3661 unsigned long addr, cpu;
3662 void __percpu *ptr = NULL;
3663 static char tmp[64];
3668 xmon_print_symbol(addr, ": ", "\n");
3673 if (setjmp(bus_error_jmp) == 0) {
3674 catch_memory_errors = 1;
3676 addr = kallsyms_lookup_name(tmp);
3678 printf("%s: %lx\n", tmp, addr);
3680 printf("Symbol '%s' not found.\n", tmp);
3683 catch_memory_errors = 0;
3688 if (setjmp(bus_error_jmp) == 0) {
3689 catch_memory_errors = 1;
3691 ptr = (void __percpu *)kallsyms_lookup_name(tmp);
3696 ptr >= (void __percpu *)__per_cpu_start &&
3697 ptr < (void __percpu *)__per_cpu_end)
3699 if (scanhex(&cpu) && cpu < num_possible_cpus()) {
3700 addr = (unsigned long)per_cpu_ptr(ptr, cpu);
3702 cpu = raw_smp_processor_id();
3703 addr = (unsigned long)this_cpu_ptr(ptr);
3706 printf("%s for cpu 0x%lx: %lx\n", tmp, cpu, addr);
3708 printf("Percpu symbol '%s' not found.\n", tmp);
3711 catch_memory_errors = 0;
3718 /* Print an address in numeric and symbolic form (if possible) */
3719 static void xmon_print_symbol(unsigned long address, const char *mid,
3723 const char *volatile name = NULL;
3724 unsigned long offset, size;
3726 printf(REG, address);
3727 if (setjmp(bus_error_jmp) == 0) {
3728 catch_memory_errors = 1;
3730 name = kallsyms_lookup(address, &size, &offset, &modname,
3733 /* wait a little while to see if we get a machine check */
3737 catch_memory_errors = 0;
3740 printf("%s%s+%#lx/%#lx", mid, name, offset, size);
3742 printf(" [%s]", modname);
3744 printf("%s", after);
3747 #ifdef CONFIG_PPC_64S_HASH_MMU
3748 void dump_segments(void)
3751 unsigned long esid,vsid;
3754 printf("SLB contents of cpu 0x%x\n", smp_processor_id());
3756 for (i = 0; i < mmu_slb_size; i++) {
3757 asm volatile("slbmfee %0,%1" : "=r" (esid) : "r" (i));
3758 asm volatile("slbmfev %0,%1" : "=r" (vsid) : "r" (i));
3763 printf("%02d %016lx %016lx", i, esid, vsid);
3765 if (!(esid & SLB_ESID_V)) {
3770 llp = vsid & SLB_VSID_LLP;
3771 if (vsid & SLB_VSID_B_1T) {
3772 printf(" 1T ESID=%9lx VSID=%13lx LLP:%3lx \n",
3774 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT_1T,
3777 printf(" 256M ESID=%9lx VSID=%13lx LLP:%3lx \n",
3779 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT,
3786 #ifdef CONFIG_PPC_BOOK3S_32
3787 void dump_segments(void)
3792 for (i = 0; i < 16; ++i)
3793 printf(" %x", mfsr(i << 28));
3799 static void dump_tlb_44x(void)
3803 for (i = 0; i < PPC44x_TLB_SIZE; i++) {
3804 unsigned long w0,w1,w2;
3805 asm volatile("tlbre %0,%1,0" : "=r" (w0) : "r" (i));
3806 asm volatile("tlbre %0,%1,1" : "=r" (w1) : "r" (i));
3807 asm volatile("tlbre %0,%1,2" : "=r" (w2) : "r" (i));
3808 printf("[%02x] %08lx %08lx %08lx ", i, w0, w1, w2);
3809 if (w0 & PPC44x_TLB_VALID) {
3810 printf("V %08lx -> %01lx%08lx %c%c%c%c%c",
3811 w0 & PPC44x_TLB_EPN_MASK,
3812 w1 & PPC44x_TLB_ERPN_MASK,
3813 w1 & PPC44x_TLB_RPN_MASK,
3814 (w2 & PPC44x_TLB_W) ? 'W' : 'w',
3815 (w2 & PPC44x_TLB_I) ? 'I' : 'i',
3816 (w2 & PPC44x_TLB_M) ? 'M' : 'm',
3817 (w2 & PPC44x_TLB_G) ? 'G' : 'g',
3818 (w2 & PPC44x_TLB_E) ? 'E' : 'e');
3823 #endif /* CONFIG_44x */
3825 #ifdef CONFIG_PPC_BOOK3E_64
3826 static void dump_tlb_book3e(void)
3828 u32 mmucfg, pidmask, lpidmask;
3830 int i, tlb, ntlbs, pidsz, lpidsz, rasz, lrat = 0;
3832 static const char *pgsz_names[] = {
3867 /* Gather some infos about the MMU */
3868 mmucfg = mfspr(SPRN_MMUCFG);
3869 mmu_version = (mmucfg & 3) + 1;
3870 ntlbs = ((mmucfg >> 2) & 3) + 1;
3871 pidsz = ((mmucfg >> 6) & 0x1f) + 1;
3872 lpidsz = (mmucfg >> 24) & 0xf;
3873 rasz = (mmucfg >> 16) & 0x7f;
3874 if ((mmu_version > 1) && (mmucfg & 0x10000))
3876 printf("Book3E MMU MAV=%d.0,%d TLBs,%d-bit PID,%d-bit LPID,%d-bit RA\n",
3877 mmu_version, ntlbs, pidsz, lpidsz, rasz);
3878 pidmask = (1ul << pidsz) - 1;
3879 lpidmask = (1ul << lpidsz) - 1;
3880 ramask = (1ull << rasz) - 1;
3882 for (tlb = 0; tlb < ntlbs; tlb++) {
3884 int nent, assoc, new_cc = 1;
3885 printf("TLB %d:\n------\n", tlb);
3888 tlbcfg = mfspr(SPRN_TLB0CFG);
3891 tlbcfg = mfspr(SPRN_TLB1CFG);
3894 tlbcfg = mfspr(SPRN_TLB2CFG);
3897 tlbcfg = mfspr(SPRN_TLB3CFG);
3900 printf("Unsupported TLB number !\n");
3903 nent = tlbcfg & 0xfff;
3904 assoc = (tlbcfg >> 24) & 0xff;
3905 for (i = 0; i < nent; i++) {
3906 u32 mas0 = MAS0_TLBSEL(tlb);
3907 u32 mas1 = MAS1_TSIZE(BOOK3E_PAGESZ_4K);
3910 int esel = i, cc = i;
3918 mas0 |= MAS0_ESEL(esel);
3919 mtspr(SPRN_MAS0, mas0);
3920 mtspr(SPRN_MAS1, mas1);
3921 mtspr(SPRN_MAS2, mas2);
3922 asm volatile("tlbre 0,0,0" : : : "memory");
3923 mas1 = mfspr(SPRN_MAS1);
3924 mas2 = mfspr(SPRN_MAS2);
3925 mas7_mas3 = mfspr(SPRN_MAS7_MAS3);
3926 if (assoc && (i % assoc) == 0)
3928 if (!(mas1 & MAS1_VALID))
3931 printf("%04x- ", i);
3933 printf("%04x-%c", cc, 'A' + esel);
3935 printf(" |%c", 'A' + esel);
3937 printf(" %016llx %04x %s %c%c AS%c",
3939 (mas1 >> 16) & 0x3fff,
3940 pgsz_names[(mas1 >> 7) & 0x1f],
3941 mas1 & MAS1_IND ? 'I' : ' ',
3942 mas1 & MAS1_IPROT ? 'P' : ' ',
3943 mas1 & MAS1_TS ? '1' : '0');
3944 printf(" %c%c%c%c%c%c%c",
3945 mas2 & MAS2_X0 ? 'a' : ' ',
3946 mas2 & MAS2_X1 ? 'v' : ' ',
3947 mas2 & MAS2_W ? 'w' : ' ',
3948 mas2 & MAS2_I ? 'i' : ' ',
3949 mas2 & MAS2_M ? 'm' : ' ',
3950 mas2 & MAS2_G ? 'g' : ' ',
3951 mas2 & MAS2_E ? 'e' : ' ');
3952 printf(" %016llx", mas7_mas3 & ramask & ~0x7ffull);
3953 if (mas1 & MAS1_IND)
3955 pgsz_names[(mas7_mas3 >> 1) & 0x1f]);
3957 printf(" U%c%c%c S%c%c%c\n",
3958 mas7_mas3 & MAS3_UX ? 'x' : ' ',
3959 mas7_mas3 & MAS3_UW ? 'w' : ' ',
3960 mas7_mas3 & MAS3_UR ? 'r' : ' ',
3961 mas7_mas3 & MAS3_SX ? 'x' : ' ',
3962 mas7_mas3 & MAS3_SW ? 'w' : ' ',
3963 mas7_mas3 & MAS3_SR ? 'r' : ' ');
3967 #endif /* CONFIG_PPC_BOOK3E_64 */
3969 static void xmon_init(int enable)
3973 __debugger_ipi = xmon_ipi;
3974 __debugger_bpt = xmon_bpt;
3975 __debugger_sstep = xmon_sstep;
3976 __debugger_iabr_match = xmon_iabr_match;
3977 __debugger_break_match = xmon_break_match;
3978 __debugger_fault_handler = xmon_fault_handler;
3981 __debugger_ipi = NULL;
3982 __debugger_bpt = NULL;
3983 __debugger_sstep = NULL;
3984 __debugger_iabr_match = NULL;
3985 __debugger_break_match = NULL;
3986 __debugger_fault_handler = NULL;
3990 #ifdef CONFIG_MAGIC_SYSRQ
3991 static void sysrq_handle_xmon(int key)
3993 if (xmon_is_locked_down()) {
3998 /* ensure xmon is enabled */
4000 debugger(get_irq_regs());
4005 static const struct sysrq_key_op sysrq_xmon_op = {
4006 .handler = sysrq_handle_xmon,
4007 .help_msg = "xmon(x)",
4008 .action_msg = "Entering xmon",
4011 static int __init setup_xmon_sysrq(void)
4013 register_sysrq_key('x', &sysrq_xmon_op);
4016 device_initcall(setup_xmon_sysrq);
4017 #endif /* CONFIG_MAGIC_SYSRQ */
4019 static void clear_all_bpt(void)
4023 /* clear/unpatch all breakpoints */
4027 /* Disable all breakpoints */
4028 for (i = 0; i < NBPTS; ++i)
4029 bpts[i].enabled = 0;
4031 /* Clear any data or iabr breakpoints */
4033 for (i = 0; i < nr_wp_slots(); i++)
4034 dabr[i].enabled = 0;
4037 #ifdef CONFIG_DEBUG_FS
4038 static int xmon_dbgfs_set(void *data, u64 val)
4043 /* make sure all breakpoints removed when disabling */
4047 printf("xmon: All breakpoints cleared\n");
4048 release_output_lock();
4054 static int xmon_dbgfs_get(void *data, u64 *val)
4060 DEFINE_SIMPLE_ATTRIBUTE(xmon_dbgfs_ops, xmon_dbgfs_get,
4061 xmon_dbgfs_set, "%llu\n");
4063 static int __init setup_xmon_dbgfs(void)
4065 debugfs_create_file("xmon", 0600, arch_debugfs_dir, NULL,
4069 device_initcall(setup_xmon_dbgfs);
4070 #endif /* CONFIG_DEBUG_FS */
4072 static int xmon_early __initdata;
4074 static int __init early_parse_xmon(char *p)
4076 if (xmon_is_locked_down()) {
4080 } else if (!p || strncmp(p, "early", 5) == 0) {
4081 /* just "xmon" is equivalent to "xmon=early" */
4085 } else if (strncmp(p, "on", 2) == 0) {
4088 } else if (strncmp(p, "rw", 2) == 0) {
4092 } else if (strncmp(p, "ro", 2) == 0) {
4096 } else if (strncmp(p, "off", 3) == 0)
4103 early_param("xmon", early_parse_xmon);
4105 void __init xmon_setup(void)
4113 #ifdef CONFIG_SPU_BASE
4117 u64 saved_mfc_sr1_RW;
4118 u32 saved_spu_runcntl_RW;
4119 unsigned long dump_addr;
4123 #define XMON_NUM_SPUS 16 /* Enough for current hardware */
4125 static struct spu_info spu_info[XMON_NUM_SPUS];
4127 void __init xmon_register_spus(struct list_head *list)
4131 list_for_each_entry(spu, list, full_list) {
4132 if (spu->number >= XMON_NUM_SPUS) {
4137 spu_info[spu->number].spu = spu;
4138 spu_info[spu->number].stopped_ok = 0;
4139 spu_info[spu->number].dump_addr = (unsigned long)
4140 spu_info[spu->number].spu->local_store;
4144 static void stop_spus(void)
4150 for (i = 0; i < XMON_NUM_SPUS; i++) {
4151 if (!spu_info[i].spu)
4154 if (setjmp(bus_error_jmp) == 0) {
4155 catch_memory_errors = 1;
4158 spu = spu_info[i].spu;
4160 spu_info[i].saved_spu_runcntl_RW =
4161 in_be32(&spu->problem->spu_runcntl_RW);
4163 tmp = spu_mfc_sr1_get(spu);
4164 spu_info[i].saved_mfc_sr1_RW = tmp;
4166 tmp &= ~MFC_STATE1_MASTER_RUN_CONTROL_MASK;
4167 spu_mfc_sr1_set(spu, tmp);
4172 spu_info[i].stopped_ok = 1;
4174 printf("Stopped spu %.2d (was %s)\n", i,
4175 spu_info[i].saved_spu_runcntl_RW ?
4176 "running" : "stopped");
4178 catch_memory_errors = 0;
4179 printf("*** Error stopping spu %.2d\n", i);
4181 catch_memory_errors = 0;
4185 static void restart_spus(void)
4190 for (i = 0; i < XMON_NUM_SPUS; i++) {
4191 if (!spu_info[i].spu)
4194 if (!spu_info[i].stopped_ok) {
4195 printf("*** Error, spu %d was not successfully stopped"
4196 ", not restarting\n", i);
4200 if (setjmp(bus_error_jmp) == 0) {
4201 catch_memory_errors = 1;
4204 spu = spu_info[i].spu;
4205 spu_mfc_sr1_set(spu, spu_info[i].saved_mfc_sr1_RW);
4206 out_be32(&spu->problem->spu_runcntl_RW,
4207 spu_info[i].saved_spu_runcntl_RW);
4212 printf("Restarted spu %.2d\n", i);
4214 catch_memory_errors = 0;
4215 printf("*** Error restarting spu %.2d\n", i);
4217 catch_memory_errors = 0;
4221 #define DUMP_WIDTH 23
4222 #define DUMP_VALUE(format, field, value) \
4224 if (setjmp(bus_error_jmp) == 0) { \
4225 catch_memory_errors = 1; \
4227 printf(" %-*s = "format"\n", DUMP_WIDTH, \
4232 catch_memory_errors = 0; \
4233 printf(" %-*s = *** Error reading field.\n", \
4234 DUMP_WIDTH, #field); \
4236 catch_memory_errors = 0; \
4239 #define DUMP_FIELD(obj, format, field) \
4240 DUMP_VALUE(format, field, obj->field)
4242 static void dump_spu_fields(struct spu *spu)
4244 printf("Dumping spu fields at address %p:\n", spu);
4246 DUMP_FIELD(spu, "0x%x", number);
4247 DUMP_FIELD(spu, "%s", name);
4248 DUMP_FIELD(spu, "0x%lx", local_store_phys);
4249 DUMP_FIELD(spu, "0x%p", local_store);
4250 DUMP_FIELD(spu, "0x%lx", ls_size);
4251 DUMP_FIELD(spu, "0x%x", node);
4252 DUMP_FIELD(spu, "0x%lx", flags);
4253 DUMP_FIELD(spu, "%llu", class_0_pending);
4254 DUMP_FIELD(spu, "0x%llx", class_0_dar);
4255 DUMP_FIELD(spu, "0x%llx", class_1_dar);
4256 DUMP_FIELD(spu, "0x%llx", class_1_dsisr);
4257 DUMP_FIELD(spu, "0x%x", irqs[0]);
4258 DUMP_FIELD(spu, "0x%x", irqs[1]);
4259 DUMP_FIELD(spu, "0x%x", irqs[2]);
4260 DUMP_FIELD(spu, "0x%x", slb_replace);
4261 DUMP_FIELD(spu, "%d", pid);
4262 DUMP_FIELD(spu, "0x%p", mm);
4263 DUMP_FIELD(spu, "0x%p", ctx);
4264 DUMP_FIELD(spu, "0x%p", rq);
4265 DUMP_FIELD(spu, "0x%llx", timestamp);
4266 DUMP_FIELD(spu, "0x%lx", problem_phys);
4267 DUMP_FIELD(spu, "0x%p", problem);
4268 DUMP_VALUE("0x%x", problem->spu_runcntl_RW,
4269 in_be32(&spu->problem->spu_runcntl_RW));
4270 DUMP_VALUE("0x%x", problem->spu_status_R,
4271 in_be32(&spu->problem->spu_status_R));
4272 DUMP_VALUE("0x%x", problem->spu_npc_RW,
4273 in_be32(&spu->problem->spu_npc_RW));
4274 DUMP_FIELD(spu, "0x%p", priv2);
4275 DUMP_FIELD(spu, "0x%p", pdata);
4278 static int spu_inst_dump(unsigned long adr, long count, int praddr)
4280 return generic_inst_dump(adr, count, praddr, print_insn_spu);
4283 static void dump_spu_ls(unsigned long num, int subcmd)
4285 unsigned long offset, addr, ls_addr;
4287 if (setjmp(bus_error_jmp) == 0) {
4288 catch_memory_errors = 1;
4290 ls_addr = (unsigned long)spu_info[num].spu->local_store;
4294 catch_memory_errors = 0;
4295 printf("*** Error: accessing spu info for spu %ld\n", num);
4298 catch_memory_errors = 0;
4300 if (scanhex(&offset))
4301 addr = ls_addr + offset;
4303 addr = spu_info[num].dump_addr;
4305 if (addr >= ls_addr + LS_SIZE) {
4306 printf("*** Error: address outside of local store\n");
4312 addr += spu_inst_dump(addr, 16, 1);
4322 spu_info[num].dump_addr = addr;
4325 static int do_spu_cmd(void)
4327 static unsigned long num = 0;
4328 int cmd, subcmd = 0;
4340 if (isxdigit(subcmd) || subcmd == '\n')
4345 if (num >= XMON_NUM_SPUS || !spu_info[num].spu) {
4346 printf("*** Error: invalid spu number\n");
4352 dump_spu_fields(spu_info[num].spu);
4355 dump_spu_ls(num, subcmd);
4366 #else /* ! CONFIG_SPU_BASE */
4367 static int do_spu_cmd(void)