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>
30 #include <asm/debugfs.h>
31 #include <asm/ptrace.h>
33 #include <asm/string.h>
35 #include <asm/machdep.h>
37 #include <asm/processor.h>
38 #include <asm/pgtable.h>
40 #include <asm/mmu_context.h>
41 #include <asm/plpar_wrappers.h>
42 #include <asm/cputable.h>
44 #include <asm/sstep.h>
45 #include <asm/irq_regs.h>
47 #include <asm/spu_priv1.h>
48 #include <asm/setjmp.h>
50 #include <asm/debug.h>
51 #include <asm/hw_breakpoint.h>
54 #include <asm/firmware.h>
55 #include <asm/code-patching.h>
56 #include <asm/sections.h>
59 #include <asm/hvcall.h>
67 static cpumask_t cpus_in_xmon = CPU_MASK_NONE;
68 static unsigned long xmon_taken = 1;
69 static int xmon_owner;
73 #endif /* CONFIG_SMP */
75 #ifdef CONFIG_PPC_PSERIES
76 static int set_indicator_token = RTAS_UNKNOWN_SERVICE;
78 static unsigned long in_xmon __read_mostly = 0;
79 static int xmon_on = IS_ENABLED(CONFIG_XMON_DEFAULT);
80 static bool xmon_is_ro = IS_ENABLED(CONFIG_XMON_DEFAULT_RO_MODE);
82 static unsigned long adrs;
84 #define MAX_DUMP (128 * 1024)
85 static unsigned long ndump = 64;
86 static unsigned long nidump = 16;
87 static unsigned long ncsum = 4096;
89 static char tmpstr[128];
90 static int tracing_enabled;
92 static long bus_error_jmp[JMP_BUF_LEN];
93 static int catch_memory_errors;
94 static int catch_spr_faults;
95 static long *xmon_fault_jmp[NR_CPUS];
97 /* Breakpoint stuff */
99 unsigned long address;
100 unsigned int instr[2];
106 /* Bits in bpt.enabled */
112 static struct bpt bpts[NBPTS];
113 static struct bpt dabr;
114 static struct bpt *iabr;
115 static unsigned bpinstr = 0x7fe00008; /* trap */
117 #define BP_NUM(bp) ((bp) - bpts + 1)
120 static int cmds(struct pt_regs *);
121 static int mread(unsigned long, void *, int);
122 static int mwrite(unsigned long, void *, int);
123 static int handle_fault(struct pt_regs *);
124 static void byterev(unsigned char *, int);
125 static void memex(void);
126 static int bsesc(void);
127 static void dump(void);
128 static void show_pte(unsigned long);
129 static void prdump(unsigned long, long);
130 static int ppc_inst_dump(unsigned long, long, int);
131 static void dump_log_buf(void);
133 #ifdef CONFIG_PPC_POWERNV
134 static void dump_opal_msglog(void);
136 static inline void dump_opal_msglog(void)
138 printf("Machine is not running OPAL firmware.\n");
142 static void backtrace(struct pt_regs *);
143 static void excprint(struct pt_regs *);
144 static void prregs(struct pt_regs *);
145 static void memops(int);
146 static void memlocate(void);
147 static void memzcan(void);
148 static void memdiffs(unsigned char *, unsigned char *, unsigned, unsigned);
150 int scanhex(unsigned long *valp);
151 static void scannl(void);
152 static int hexdigit(int);
153 void getstring(char *, int);
154 static void flush_input(void);
155 static int inchar(void);
156 static void take_input(char *);
157 static int read_spr(int, unsigned long *);
158 static void write_spr(int, unsigned long);
159 static void super_regs(void);
160 static void remove_bpts(void);
161 static void insert_bpts(void);
162 static void remove_cpu_bpts(void);
163 static void insert_cpu_bpts(void);
164 static struct bpt *at_breakpoint(unsigned long pc);
165 static struct bpt *in_breakpoint_table(unsigned long pc, unsigned long *offp);
166 static int do_step(struct pt_regs *);
167 static void bpt_cmds(void);
168 static void cacheflush(void);
169 static int cpu_cmd(void);
170 static void csum(void);
171 static void bootcmds(void);
172 static void proccall(void);
173 static void show_tasks(void);
174 void dump_segments(void);
175 static void symbol_lookup(void);
176 static void xmon_show_stack(unsigned long sp, unsigned long lr,
178 static void xmon_print_symbol(unsigned long address, const char *mid,
180 static const char *getvecname(unsigned long vec);
182 static int do_spu_cmd(void);
185 static void dump_tlb_44x(void);
187 #ifdef CONFIG_PPC_BOOK3E
188 static void dump_tlb_book3e(void);
191 static void clear_all_bpt(void);
199 #ifdef __LITTLE_ENDIAN__
200 #define GETWORD(v) (((v)[3] << 24) + ((v)[2] << 16) + ((v)[1] << 8) + (v)[0])
202 #define GETWORD(v) (((v)[0] << 24) + ((v)[1] << 16) + ((v)[2] << 8) + (v)[3])
205 static const char *xmon_ro_msg = "Operation disabled: xmon in read-only mode\n";
207 static char *help_string = "\
209 b show breakpoints\n\
210 bd set data breakpoint\n\
211 bi set instruction breakpoint\n\
212 bc clear breakpoint\n"
215 c print cpus stopped in xmon\n\
216 c# try to switch to cpu number h (in hex)\n"
221 d1 dump 1 byte values\n\
222 d2 dump 2 byte values\n\
223 d4 dump 4 byte values\n\
224 d8 dump 8 byte values\n\
225 di dump instructions\n\
226 df dump float values\n\
227 dd dump double values\n\
228 dl dump the kernel log buffer\n"
229 #ifdef CONFIG_PPC_POWERNV
231 do dump the OPAL message log\n"
235 dp[#] dump paca for current cpu, or cpu #\n\
236 dpa dump paca for all possible cpus\n"
239 dr dump stream of raw bytes\n\
240 dv dump virtual address translation \n\
241 dt dump the tracing buffers (uses printk)\n\
242 dtc dump the tracing buffers for current CPU (uses printk)\n\
244 #ifdef CONFIG_PPC_POWERNV
245 " dx# dump xive on CPU #\n\
246 dxi# dump xive irq state #\n\
247 dxa dump xive on all CPUs\n"
249 " e print exception information\n\
251 la lookup symbol+offset of specified address\n\
252 ls lookup address of specified symbol\n\
253 lp s [#] lookup address of percpu symbol s for current cpu, or cpu #\n\
254 m examine/change memory\n\
255 mm move a block of memory\n\
256 ms set a block of memory\n\
257 md compare two blocks of memory\n\
258 ml locate a block of memory\n\
259 mz zero a block of memory\n\
260 mi show information about memory allocation\n\
261 p call a procedure\n\
262 P list processes/tasks\n\
265 #ifdef CONFIG_SPU_BASE
266 " ss stop execution on all spus\n\
267 sr restore execution on stopped spus\n\
268 sf # dump spu fields for spu # (in hex)\n\
269 sd # dump spu local store for spu # (in hex)\n\
270 sdi # disassemble spu local store for spu # (in hex)\n"
272 " S print special registers\n\
275 Sw #v write v to SPR #\n\
277 x exit monitor and recover\n\
278 X exit monitor and don't recover\n"
279 #if defined(CONFIG_PPC64) && !defined(CONFIG_PPC_BOOK3E)
280 " u dump segment table or SLB\n"
281 #elif defined(CONFIG_PPC_BOOK3S_32)
282 " u dump segment registers\n"
283 #elif defined(CONFIG_44x) || defined(CONFIG_PPC_BOOK3E)
286 " U show uptime information\n"
288 " # n limit output to n lines per page (for dp, dpa, dl)\n"
293 #ifdef CONFIG_SECURITY
294 static bool xmon_is_locked_down(void)
296 static bool lockdown;
299 lockdown = !!security_locked_down(LOCKDOWN_XMON_RW);
301 printf("xmon: Disabled due to kernel lockdown\n");
307 xmon_is_ro = !!security_locked_down(LOCKDOWN_XMON_WR);
309 printf("xmon: Read-only due to kernel lockdown\n");
314 #else /* CONFIG_SECURITY */
315 static inline bool xmon_is_locked_down(void)
321 static struct pt_regs *xmon_regs;
323 static inline void sync(void)
325 asm volatile("sync; isync");
328 static inline void store_inst(void *p)
330 asm volatile ("dcbst 0,%0; sync; icbi 0,%0; isync" : : "r" (p));
333 static inline void cflush(void *p)
335 asm volatile ("dcbf 0,%0; icbi 0,%0" : : "r" (p));
338 static inline void cinval(void *p)
340 asm volatile ("dcbi 0,%0; icbi 0,%0" : : "r" (p));
344 * write_ciabr() - write the CIABR SPR
345 * @ciabr: The value to write.
347 * This function writes a value to the CIARB register either directly
348 * through mtspr instruction if the kernel is in HV privilege mode or
349 * call a hypervisor function to achieve the same in case the kernel
350 * is in supervisor privilege mode.
352 static void write_ciabr(unsigned long ciabr)
354 if (!cpu_has_feature(CPU_FTR_ARCH_207S))
357 if (cpu_has_feature(CPU_FTR_HVMODE)) {
358 mtspr(SPRN_CIABR, ciabr);
361 plpar_set_ciabr(ciabr);
365 * set_ciabr() - set the CIABR
366 * @addr: The value to set.
368 * This function sets the correct privilege value into the the HW
369 * breakpoint address before writing it up in the CIABR register.
371 static void set_ciabr(unsigned long addr)
375 if (cpu_has_feature(CPU_FTR_HVMODE))
376 addr |= CIABR_PRIV_HYPER;
378 addr |= CIABR_PRIV_SUPER;
383 * Disable surveillance (the service processor watchdog function)
384 * while we are in xmon.
385 * XXX we should re-enable it when we leave. :)
387 #define SURVEILLANCE_TOKEN 9000
389 static inline void disable_surveillance(void)
391 #ifdef CONFIG_PPC_PSERIES
392 /* Since this can't be a module, args should end up below 4GB. */
393 static struct rtas_args args;
396 * At this point we have got all the cpus we can into
397 * xmon, so there is hopefully no other cpu calling RTAS
398 * at the moment, even though we don't take rtas.lock.
399 * If we did try to take rtas.lock there would be a
400 * real possibility of deadlock.
402 if (set_indicator_token == RTAS_UNKNOWN_SERVICE)
405 rtas_call_unlocked(&args, set_indicator_token, 3, 1, NULL,
406 SURVEILLANCE_TOKEN, 0, 0);
408 #endif /* CONFIG_PPC_PSERIES */
412 static int xmon_speaker;
414 static void get_output_lock(void)
416 int me = smp_processor_id() + 0x100;
417 int last_speaker = 0, prev;
420 if (xmon_speaker == me)
424 last_speaker = cmpxchg(&xmon_speaker, 0, me);
425 if (last_speaker == 0)
429 * Wait a full second for the lock, we might be on a slow
430 * console, but check every 100us.
433 while (xmon_speaker == last_speaker) {
439 /* hostile takeover */
440 prev = cmpxchg(&xmon_speaker, last_speaker, me);
441 if (prev == last_speaker)
448 static void release_output_lock(void)
453 int cpus_are_in_xmon(void)
455 return !cpumask_empty(&cpus_in_xmon);
458 static bool wait_for_other_cpus(int ncpus)
460 unsigned long timeout;
462 /* We wait for 2s, which is a metric "little while" */
463 for (timeout = 20000; timeout != 0; --timeout) {
464 if (cpumask_weight(&cpus_in_xmon) >= ncpus)
472 #else /* CONFIG_SMP */
473 static inline void get_output_lock(void) {}
474 static inline void release_output_lock(void) {}
477 static inline int unrecoverable_excp(struct pt_regs *regs)
479 #if defined(CONFIG_4xx) || defined(CONFIG_PPC_BOOK3E)
480 /* We have no MSR_RI bit on 4xx or Book3e, so we simply return false */
483 return ((regs->msr & MSR_RI) == 0);
487 static int xmon_core(struct pt_regs *regs, int fromipi)
491 long recurse_jmp[JMP_BUF_LEN];
493 unsigned long offset;
500 local_irq_save(flags);
503 locked_down = xmon_is_locked_down();
506 tracing_enabled = tracing_is_on();
510 bp = in_breakpoint_table(regs->nip, &offset);
512 regs->nip = bp->address + offset;
513 atomic_dec(&bp->ref_count);
519 cpu = smp_processor_id();
520 if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
522 * We catch SPR read/write faults here because the 0x700, 0xf60
523 * etc. handlers don't call debugger_fault_handler().
525 if (catch_spr_faults)
526 longjmp(bus_error_jmp, 1);
529 printf("cpu 0x%x: Exception %lx %s in xmon, "
530 "returning to main loop\n",
531 cpu, regs->trap, getvecname(TRAP(regs)));
532 release_output_lock();
533 longjmp(xmon_fault_jmp[cpu], 1);
536 if (setjmp(recurse_jmp) != 0) {
537 if (!in_xmon || !xmon_gate) {
539 printf("xmon: WARNING: bad recursive fault "
540 "on cpu 0x%x\n", cpu);
541 release_output_lock();
544 secondary = !(xmon_taken && cpu == xmon_owner);
548 xmon_fault_jmp[cpu] = recurse_jmp;
551 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT))
552 bp = at_breakpoint(regs->nip);
553 if (bp || unrecoverable_excp(regs))
561 printf("cpu 0x%x stopped at breakpoint 0x%tx (",
563 xmon_print_symbol(regs->nip, " ", ")\n");
565 if (unrecoverable_excp(regs))
566 printf("WARNING: exception is not recoverable, "
568 release_output_lock();
571 cpumask_set_cpu(cpu, &cpus_in_xmon);
576 while (secondary && !xmon_gate) {
582 secondary = test_and_set_bit(0, &in_xmon);
585 touch_nmi_watchdog();
589 if (!secondary && !xmon_gate) {
590 /* we are the first cpu to come in */
591 /* interrupt other cpu(s) */
592 int ncpus = num_online_cpus();
598 * A system reset (trap == 0x100) can be triggered on
599 * all CPUs, so when we come in via 0x100 try waiting
600 * for the other CPUs to come in before we send the
601 * debugger break (IPI). This is similar to
602 * crash_kexec_secondary().
604 if (TRAP(regs) != 0x100 || !wait_for_other_cpus(ncpus))
605 smp_send_debugger_break();
607 wait_for_other_cpus(ncpus);
610 disable_surveillance();
613 /* for breakpoint or single step, print curr insn */
614 if (bp || TRAP(regs) == 0xd00)
615 ppc_inst_dump(regs->nip, 1, 0);
616 printf("enter ? for help\n");
622 touch_nmi_watchdog();
629 if (cpu == xmon_owner) {
630 if (!test_and_set_bit(0, &xmon_taken)) {
636 while (cpu == xmon_owner)
640 touch_nmi_watchdog();
644 if (locked_down || cmd != 0) {
652 /* have switched to some other cpu */
657 cpumask_clear_cpu(cpu, &cpus_in_xmon);
658 xmon_fault_jmp[cpu] = NULL;
660 /* UP is simple... */
662 printf("Exception %lx %s in xmon, returning to main loop\n",
663 regs->trap, getvecname(TRAP(regs)));
664 longjmp(xmon_fault_jmp[0], 1);
666 if (setjmp(recurse_jmp) == 0) {
667 xmon_fault_jmp[0] = recurse_jmp;
671 bp = at_breakpoint(regs->nip);
673 printf("Stopped at breakpoint %tx (", BP_NUM(bp));
674 xmon_print_symbol(regs->nip, " ", ")\n");
676 if (unrecoverable_excp(regs))
677 printf("WARNING: exception is not recoverable, "
680 disable_surveillance();
682 /* for breakpoint or single step, print current insn */
683 if (bp || TRAP(regs) == 0xd00)
684 ppc_inst_dump(regs->nip, 1, 0);
685 printf("enter ? for help\n");
697 if (regs->msr & MSR_DE) {
698 bp = at_breakpoint(regs->nip);
700 regs->nip = (unsigned long) &bp->instr[0];
701 atomic_inc(&bp->ref_count);
705 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
706 bp = at_breakpoint(regs->nip);
708 int stepped = emulate_step(regs, bp->instr[0]);
710 regs->nip = (unsigned long) &bp->instr[0];
711 atomic_inc(&bp->ref_count);
712 } else if (stepped < 0) {
713 printf("Couldn't single-step %s instruction\n",
714 (IS_RFID(bp->instr[0])? "rfid": "mtmsrd"));
724 touch_nmi_watchdog();
725 local_irq_restore(flags);
727 return cmd != 'X' && cmd != EOF;
730 int xmon(struct pt_regs *excp)
735 ppc_save_regs(®s);
739 return xmon_core(excp, 0);
743 irqreturn_t xmon_irq(int irq, void *d)
746 local_irq_save(flags);
747 printf("Keyboard interrupt\n");
748 xmon(get_irq_regs());
749 local_irq_restore(flags);
753 static int xmon_bpt(struct pt_regs *regs)
756 unsigned long offset;
758 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
761 /* Are we at the trap at bp->instr[1] for some bp? */
762 bp = in_breakpoint_table(regs->nip, &offset);
763 if (bp != NULL && offset == 4) {
764 regs->nip = bp->address + 4;
765 atomic_dec(&bp->ref_count);
769 /* Are we at a breakpoint? */
770 bp = at_breakpoint(regs->nip);
779 static int xmon_sstep(struct pt_regs *regs)
787 static int xmon_break_match(struct pt_regs *regs)
789 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
791 if (dabr.enabled == 0)
797 static int xmon_iabr_match(struct pt_regs *regs)
799 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) != (MSR_IR|MSR_64BIT))
807 static int xmon_ipi(struct pt_regs *regs)
810 if (in_xmon && !cpumask_test_cpu(smp_processor_id(), &cpus_in_xmon))
816 static int xmon_fault_handler(struct pt_regs *regs)
819 unsigned long offset;
821 if (in_xmon && catch_memory_errors)
822 handle_fault(regs); /* doesn't return */
824 if ((regs->msr & (MSR_IR|MSR_PR|MSR_64BIT)) == (MSR_IR|MSR_64BIT)) {
825 bp = in_breakpoint_table(regs->nip, &offset);
827 regs->nip = bp->address + offset;
828 atomic_dec(&bp->ref_count);
835 /* Force enable xmon if not already enabled */
836 static inline void force_enable_xmon(void)
838 /* Enable xmon hooks if needed */
840 printf("xmon: Enabling debugger hooks\n");
845 static struct bpt *at_breakpoint(unsigned long pc)
851 for (i = 0; i < NBPTS; ++i, ++bp)
852 if (bp->enabled && pc == bp->address)
857 static struct bpt *in_breakpoint_table(unsigned long nip, unsigned long *offp)
861 off = nip - (unsigned long) bpts;
862 if (off >= sizeof(bpts))
864 off %= sizeof(struct bpt);
865 if (off != offsetof(struct bpt, instr[0])
866 && off != offsetof(struct bpt, instr[1]))
868 *offp = off - offsetof(struct bpt, instr[0]);
869 return (struct bpt *) (nip - off);
872 static struct bpt *new_breakpoint(unsigned long a)
877 bp = at_breakpoint(a);
881 for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
882 if (!bp->enabled && atomic_read(&bp->ref_count) == 0) {
884 bp->instr[1] = bpinstr;
885 store_inst(&bp->instr[1]);
890 printf("Sorry, no free breakpoints. Please clear one first.\n");
894 static void insert_bpts(void)
900 for (i = 0; i < NBPTS; ++i, ++bp) {
901 if ((bp->enabled & (BP_TRAP|BP_CIABR)) == 0)
903 if (mread(bp->address, &bp->instr[0], 4) != 4) {
904 printf("Couldn't read instruction at %lx, "
905 "disabling breakpoint there\n", bp->address);
909 if (IS_MTMSRD(bp->instr[0]) || IS_RFID(bp->instr[0])) {
910 printf("Breakpoint at %lx is on an mtmsrd or rfid "
911 "instruction, disabling it\n", bp->address);
915 store_inst(&bp->instr[0]);
916 if (bp->enabled & BP_CIABR)
918 if (patch_instruction((unsigned int *)bp->address,
920 printf("Couldn't write instruction at %lx, "
921 "disabling breakpoint there\n", bp->address);
922 bp->enabled &= ~BP_TRAP;
925 store_inst((void *)bp->address);
929 static void insert_cpu_bpts(void)
931 struct arch_hw_breakpoint brk;
934 brk.address = dabr.address;
935 brk.type = (dabr.enabled & HW_BRK_TYPE_DABR) | HW_BRK_TYPE_PRIV_ALL;
936 brk.len = DABR_MAX_LEN;
937 __set_breakpoint(&brk);
941 set_ciabr(iabr->address);
944 static void remove_bpts(void)
951 for (i = 0; i < NBPTS; ++i, ++bp) {
952 if ((bp->enabled & (BP_TRAP|BP_CIABR)) != BP_TRAP)
954 if (mread(bp->address, &instr, 4) == 4
956 && patch_instruction(
957 (unsigned int *)bp->address, bp->instr[0]) != 0)
958 printf("Couldn't remove breakpoint at %lx\n",
961 store_inst((void *)bp->address);
965 static void remove_cpu_bpts(void)
967 hw_breakpoint_disable();
971 /* Based on uptime_proc_show(). */
975 struct timespec64 uptime;
977 if (setjmp(bus_error_jmp) == 0) {
978 catch_memory_errors = 1;
981 ktime_get_coarse_boottime_ts64(&uptime);
982 printf("Uptime: %lu.%.2lu seconds\n", (unsigned long)uptime.tv_sec,
983 ((unsigned long)uptime.tv_nsec / (NSEC_PER_SEC/100)));
988 catch_memory_errors = 0;
991 static void set_lpp_cmd(void)
995 if (!scanhex(&lpp)) {
996 printf("Invalid number.\n");
999 xmon_set_pagination_lpp(lpp);
1001 /* Command interpreting routine */
1002 static char *last_cmd;
1005 cmds(struct pt_regs *excp)
1012 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
1016 printf("%x:", smp_processor_id());
1017 #endif /* CONFIG_SMP */
1023 if (last_cmd == NULL)
1025 take_input(last_cmd);
1043 printf(xmon_ro_msg);
1063 prregs(excp); /* print regs */
1078 if (do_spu_cmd() == 0)
1085 if (tracing_enabled)
1089 printf(" <no input ...>\n");
1093 xmon_puts(help_string);
1113 printf(xmon_ro_msg);
1121 #ifdef CONFIG_PPC_BOOK3S
1125 #elif defined(CONFIG_44x)
1129 #elif defined(CONFIG_PPC_BOOK3E)
1138 printf("Unrecognized command: ");
1140 if (' ' < cmd && cmd <= '~')
1143 printf("\\x%x", cmd);
1145 } while (cmd != '\n');
1146 printf(" (type ? for help)\n");
1153 static int do_step(struct pt_regs *regs)
1155 regs->msr |= MSR_DE;
1156 mtspr(SPRN_DBCR0, mfspr(SPRN_DBCR0) | DBCR0_IC | DBCR0_IDM);
1161 * Step a single instruction.
1162 * Some instructions we emulate, others we execute with MSR_SE set.
1164 static int do_step(struct pt_regs *regs)
1169 force_enable_xmon();
1170 /* check we are in 64-bit kernel mode, translation enabled */
1171 if ((regs->msr & (MSR_64BIT|MSR_PR|MSR_IR)) == (MSR_64BIT|MSR_IR)) {
1172 if (mread(regs->nip, &instr, 4) == 4) {
1173 stepped = emulate_step(regs, instr);
1175 printf("Couldn't single-step %s instruction\n",
1176 (IS_RFID(instr)? "rfid": "mtmsrd"));
1180 regs->trap = 0xd00 | (regs->trap & 1);
1181 printf("stepped to ");
1182 xmon_print_symbol(regs->nip, " ", "\n");
1183 ppc_inst_dump(regs->nip, 1, 0);
1188 regs->msr |= MSR_SE;
1193 static void bootcmds(void)
1201 ppc_md.restart(tmp);
1202 } else if (cmd == 'h') {
1204 } else if (cmd == 'p') {
1210 static int cpu_cmd(void)
1213 unsigned long cpu, first_cpu, last_cpu;
1216 if (!scanhex(&cpu)) {
1217 /* print cpus waiting or in xmon */
1218 printf("cpus stopped:");
1219 last_cpu = first_cpu = NR_CPUS;
1220 for_each_possible_cpu(cpu) {
1221 if (cpumask_test_cpu(cpu, &cpus_in_xmon)) {
1222 if (cpu == last_cpu + 1) {
1225 if (last_cpu != first_cpu)
1226 printf("-0x%lx", last_cpu);
1227 last_cpu = first_cpu = cpu;
1228 printf(" 0x%lx", cpu);
1232 if (last_cpu != first_cpu)
1233 printf("-0x%lx", last_cpu);
1237 /* try to switch to cpu specified */
1238 if (!cpumask_test_cpu(cpu, &cpus_in_xmon)) {
1239 printf("cpu 0x%lx isn't in xmon\n", cpu);
1241 printf("backtrace of paca[0x%lx].saved_r1 (possibly stale):\n", cpu);
1242 xmon_show_stack(paca_ptrs[cpu]->saved_r1, 0, 0);
1250 while (!xmon_taken) {
1251 if (--timeout == 0) {
1252 if (test_and_set_bit(0, &xmon_taken))
1254 /* take control back */
1256 xmon_owner = smp_processor_id();
1257 printf("cpu 0x%lx didn't take control\n", cpu);
1265 #endif /* CONFIG_SMP */
1268 static unsigned short fcstab[256] = {
1269 0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
1270 0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
1271 0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
1272 0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
1273 0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
1274 0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
1275 0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
1276 0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
1277 0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
1278 0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
1279 0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
1280 0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
1281 0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
1282 0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
1283 0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
1284 0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
1285 0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
1286 0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
1287 0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
1288 0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
1289 0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
1290 0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
1291 0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
1292 0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
1293 0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
1294 0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
1295 0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
1296 0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
1297 0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
1298 0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
1299 0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
1300 0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
1303 #define FCS(fcs, c) (((fcs) >> 8) ^ fcstab[((fcs) ^ (c)) & 0xff])
1312 if (!scanhex(&adrs))
1314 if (!scanhex(&ncsum))
1317 for (i = 0; i < ncsum; ++i) {
1318 if (mread(adrs+i, &v, 1) == 0) {
1319 printf("csum stopped at "REG"\n", adrs+i);
1324 printf("%x\n", fcs);
1328 * Check if this is a suitable place to put a breakpoint.
1330 static long check_bp_loc(unsigned long addr)
1335 if (!is_kernel_addr(addr)) {
1336 printf("Breakpoints may only be placed at kernel addresses\n");
1339 if (!mread(addr, &instr, sizeof(instr))) {
1340 printf("Can't read instruction at address %lx\n", addr);
1343 if (IS_MTMSRD(instr) || IS_RFID(instr)) {
1344 printf("Breakpoints may not be placed on mtmsrd or rfid "
1351 static char *breakpoint_help_string =
1352 "Breakpoint command usage:\n"
1353 "b show breakpoints\n"
1354 "b <addr> [cnt] set breakpoint at given instr addr\n"
1355 "bc clear all breakpoints\n"
1356 "bc <n/addr> clear breakpoint number n or at addr\n"
1357 "bi <addr> [cnt] set hardware instr breakpoint (POWER8 only)\n"
1358 "bd <addr> [cnt] set hardware data breakpoint\n"
1372 #ifndef CONFIG_PPC_8xx
1373 static const char badaddr[] = "Only kernel addresses are permitted for breakpoints\n";
1375 case 'd': /* bd - hardware data breakpoint */
1377 printf(xmon_ro_msg);
1380 if (!ppc_breakpoint_available()) {
1381 printf("Hardware data breakpoint not supported on this cpu\n");
1388 else if (cmd == 'w')
1394 if (scanhex(&dabr.address)) {
1395 if (!is_kernel_addr(dabr.address)) {
1399 dabr.address &= ~HW_BRK_TYPE_DABR;
1400 dabr.enabled = mode | BP_DABR;
1403 force_enable_xmon();
1406 case 'i': /* bi - hardware instr breakpoint */
1408 printf(xmon_ro_msg);
1411 if (!cpu_has_feature(CPU_FTR_ARCH_207S)) {
1412 printf("Hardware instruction breakpoint "
1413 "not supported on this cpu\n");
1417 iabr->enabled &= ~BP_CIABR;
1422 if (!check_bp_loc(a))
1424 bp = new_breakpoint(a);
1426 bp->enabled |= BP_CIABR;
1428 force_enable_xmon();
1435 /* clear all breakpoints */
1436 for (i = 0; i < NBPTS; ++i)
1437 bpts[i].enabled = 0;
1440 printf("All breakpoints cleared\n");
1444 if (a <= NBPTS && a >= 1) {
1445 /* assume a breakpoint number */
1446 bp = &bpts[a-1]; /* bp nums are 1 based */
1448 /* assume a breakpoint address */
1449 bp = at_breakpoint(a);
1451 printf("No breakpoint at %lx\n", a);
1456 printf("Cleared breakpoint %tx (", BP_NUM(bp));
1457 xmon_print_symbol(bp->address, " ", ")\n");
1465 printf(breakpoint_help_string);
1470 if (xmon_is_ro || !scanhex(&a)) {
1471 /* print all breakpoints */
1472 printf(" type address\n");
1474 printf(" data "REG" [", dabr.address);
1475 if (dabr.enabled & 1)
1477 if (dabr.enabled & 2)
1481 for (bp = bpts; bp < &bpts[NBPTS]; ++bp) {
1484 printf("%tx %s ", BP_NUM(bp),
1485 (bp->enabled & BP_CIABR) ? "inst": "trap");
1486 xmon_print_symbol(bp->address, " ", "\n");
1491 if (!check_bp_loc(a))
1493 bp = new_breakpoint(a);
1495 bp->enabled |= BP_TRAP;
1496 force_enable_xmon();
1502 /* Very cheap human name for vector lookup. */
1504 const char *getvecname(unsigned long vec)
1509 case 0x100: ret = "(System Reset)"; break;
1510 case 0x200: ret = "(Machine Check)"; break;
1511 case 0x300: ret = "(Data Access)"; break;
1513 if (radix_enabled())
1514 ret = "(Data Access Out of Range)";
1516 ret = "(Data SLB Access)";
1518 case 0x400: ret = "(Instruction Access)"; break;
1520 if (radix_enabled())
1521 ret = "(Instruction Access Out of Range)";
1523 ret = "(Instruction SLB Access)";
1525 case 0x500: ret = "(Hardware Interrupt)"; break;
1526 case 0x600: ret = "(Alignment)"; break;
1527 case 0x700: ret = "(Program Check)"; break;
1528 case 0x800: ret = "(FPU Unavailable)"; break;
1529 case 0x900: ret = "(Decrementer)"; break;
1530 case 0x980: ret = "(Hypervisor Decrementer)"; break;
1531 case 0xa00: ret = "(Doorbell)"; break;
1532 case 0xc00: ret = "(System Call)"; break;
1533 case 0xd00: ret = "(Single Step)"; break;
1534 case 0xe40: ret = "(Emulation Assist)"; break;
1535 case 0xe60: ret = "(HMI)"; break;
1536 case 0xe80: ret = "(Hypervisor Doorbell)"; break;
1537 case 0xf00: ret = "(Performance Monitor)"; break;
1538 case 0xf20: ret = "(Altivec Unavailable)"; break;
1539 case 0x1300: ret = "(Instruction Breakpoint)"; break;
1540 case 0x1500: ret = "(Denormalisation)"; break;
1541 case 0x1700: ret = "(Altivec Assist)"; break;
1547 static void get_function_bounds(unsigned long pc, unsigned long *startp,
1548 unsigned long *endp)
1550 unsigned long size, offset;
1553 *startp = *endp = 0;
1556 if (setjmp(bus_error_jmp) == 0) {
1557 catch_memory_errors = 1;
1559 name = kallsyms_lookup(pc, &size, &offset, NULL, tmpstr);
1561 *startp = pc - offset;
1562 *endp = pc - offset + size;
1566 catch_memory_errors = 0;
1569 #define LRSAVE_OFFSET (STACK_FRAME_LR_SAVE * sizeof(unsigned long))
1570 #define MARKER_OFFSET (STACK_FRAME_MARKER * sizeof(unsigned long))
1572 static void xmon_show_stack(unsigned long sp, unsigned long lr,
1575 int max_to_print = 64;
1577 unsigned long newsp;
1578 unsigned long marker;
1579 struct pt_regs regs;
1581 while (max_to_print--) {
1582 if (!is_kernel_addr(sp)) {
1584 printf("SP (%lx) is in userspace\n", sp);
1588 if (!mread(sp + LRSAVE_OFFSET, &ip, sizeof(unsigned long))
1589 || !mread(sp, &newsp, sizeof(unsigned long))) {
1590 printf("Couldn't read stack frame at %lx\n", sp);
1595 * For the first stack frame, try to work out if
1596 * LR and/or the saved LR value in the bottommost
1597 * stack frame are valid.
1599 if ((pc | lr) != 0) {
1600 unsigned long fnstart, fnend;
1601 unsigned long nextip;
1604 get_function_bounds(pc, &fnstart, &fnend);
1607 mread(newsp + LRSAVE_OFFSET, &nextip,
1608 sizeof(unsigned long));
1610 if (!is_kernel_addr(lr)
1611 || (fnstart <= lr && lr < fnend))
1613 } else if (lr == nextip) {
1615 } else if (is_kernel_addr(lr)
1616 && !(fnstart <= lr && lr < fnend)) {
1617 printf("[link register ] ");
1618 xmon_print_symbol(lr, " ", "\n");
1621 printf("["REG"] ", sp);
1622 xmon_print_symbol(ip, " ", " (unreliable)\n");
1627 printf("["REG"] ", sp);
1628 xmon_print_symbol(ip, " ", "\n");
1631 /* Look for "regshere" marker to see if this is
1632 an exception frame. */
1633 if (mread(sp + MARKER_OFFSET, &marker, sizeof(unsigned long))
1634 && marker == STACK_FRAME_REGS_MARKER) {
1635 if (mread(sp + STACK_FRAME_OVERHEAD, ®s, sizeof(regs))
1637 printf("Couldn't read registers at %lx\n",
1638 sp + STACK_FRAME_OVERHEAD);
1641 printf("--- Exception: %lx %s at ", regs.trap,
1642 getvecname(TRAP(®s)));
1645 xmon_print_symbol(pc, " ", "\n");
1655 static void backtrace(struct pt_regs *excp)
1660 xmon_show_stack(sp, 0, 0);
1662 xmon_show_stack(excp->gpr[1], excp->link, excp->nip);
1666 static void print_bug_trap(struct pt_regs *regs)
1669 const struct bug_entry *bug;
1672 if (regs->msr & MSR_PR)
1673 return; /* not in kernel */
1674 addr = regs->nip; /* address of trap instruction */
1675 if (!is_kernel_addr(addr))
1677 bug = find_bug(regs->nip);
1680 if (is_warning_bug(bug))
1683 #ifdef CONFIG_DEBUG_BUGVERBOSE
1684 printf("kernel BUG at %s:%u!\n",
1685 bug->file, bug->line);
1687 printf("kernel BUG at %px!\n", (void *)bug->bug_addr);
1689 #endif /* CONFIG_BUG */
1692 static void excprint(struct pt_regs *fp)
1697 printf("cpu 0x%x: ", smp_processor_id());
1698 #endif /* CONFIG_SMP */
1701 printf("Vector: %lx %s at [%px]\n", fp->trap, getvecname(trap), fp);
1703 xmon_print_symbol(fp->nip, ": ", "\n");
1706 xmon_print_symbol(fp->link, ": ", "\n");
1708 printf(" sp: %lx\n", fp->gpr[1]);
1709 printf(" msr: %lx\n", fp->msr);
1711 if (trap == 0x300 || trap == 0x380 || trap == 0x600 || trap == 0x200) {
1712 printf(" dar: %lx\n", fp->dar);
1714 printf(" dsisr: %lx\n", fp->dsisr);
1717 printf(" current = 0x%px\n", current);
1719 printf(" paca = 0x%px\t irqmask: 0x%02x\t irq_happened: 0x%02x\n",
1720 local_paca, local_paca->irq_soft_mask, local_paca->irq_happened);
1723 printf(" pid = %d, comm = %s\n",
1724 current->pid, current->comm);
1730 printf(linux_banner);
1733 static void prregs(struct pt_regs *fp)
1737 struct pt_regs regs;
1739 if (scanhex(&base)) {
1740 if (setjmp(bus_error_jmp) == 0) {
1741 catch_memory_errors = 1;
1743 regs = *(struct pt_regs *)base;
1747 catch_memory_errors = 0;
1748 printf("*** Error reading registers from "REG"\n",
1752 catch_memory_errors = 0;
1757 if (FULL_REGS(fp)) {
1758 for (n = 0; n < 16; ++n)
1759 printf("R%.2d = "REG" R%.2d = "REG"\n",
1760 n, fp->gpr[n], n+16, fp->gpr[n+16]);
1762 for (n = 0; n < 7; ++n)
1763 printf("R%.2d = "REG" R%.2d = "REG"\n",
1764 n, fp->gpr[n], n+7, fp->gpr[n+7]);
1767 for (n = 0; n < 32; ++n) {
1768 printf("R%.2d = %.8lx%s", n, fp->gpr[n],
1769 (n & 3) == 3? "\n": " ");
1770 if (n == 12 && !FULL_REGS(fp)) {
1777 xmon_print_symbol(fp->nip, " ", "\n");
1778 if (TRAP(fp) != 0xc00 && cpu_has_feature(CPU_FTR_CFAR)) {
1780 xmon_print_symbol(fp->orig_gpr3, " ", "\n");
1783 xmon_print_symbol(fp->link, " ", "\n");
1784 printf("msr = "REG" cr = %.8lx\n", fp->msr, fp->ccr);
1785 printf("ctr = "REG" xer = "REG" trap = %4lx\n",
1786 fp->ctr, fp->xer, fp->trap);
1788 if (trap == 0x300 || trap == 0x380 || trap == 0x600)
1789 printf("dar = "REG" dsisr = %.8lx\n", fp->dar, fp->dsisr);
1792 static void cacheflush(void)
1795 unsigned long nflush;
1800 scanhex((void *)&adrs);
1805 nflush = (nflush + L1_CACHE_BYTES - 1) / L1_CACHE_BYTES;
1806 if (setjmp(bus_error_jmp) == 0) {
1807 catch_memory_errors = 1;
1811 for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1812 cflush((void *) adrs);
1814 for (; nflush > 0; --nflush, adrs += L1_CACHE_BYTES)
1815 cinval((void *) adrs);
1818 /* wait a little while to see if we get a machine check */
1821 catch_memory_errors = 0;
1824 extern unsigned long xmon_mfspr(int spr, unsigned long default_value);
1825 extern void xmon_mtspr(int spr, unsigned long value);
1828 read_spr(int n, unsigned long *vp)
1830 unsigned long ret = -1UL;
1833 if (setjmp(bus_error_jmp) == 0) {
1834 catch_spr_faults = 1;
1837 ret = xmon_mfspr(n, *vp);
1843 catch_spr_faults = 0;
1849 write_spr(int n, unsigned long val)
1852 printf(xmon_ro_msg);
1856 if (setjmp(bus_error_jmp) == 0) {
1857 catch_spr_faults = 1;
1864 printf("SPR 0x%03x (%4d) Faulted during write\n", n, n);
1866 catch_spr_faults = 0;
1869 static void dump_206_sprs(void)
1872 if (!cpu_has_feature(CPU_FTR_ARCH_206))
1875 /* Actually some of these pre-date 2.06, but whatevs */
1877 printf("srr0 = %.16lx srr1 = %.16lx dsisr = %.8lx\n",
1878 mfspr(SPRN_SRR0), mfspr(SPRN_SRR1), mfspr(SPRN_DSISR));
1879 printf("dscr = %.16lx ppr = %.16lx pir = %.8lx\n",
1880 mfspr(SPRN_DSCR), mfspr(SPRN_PPR), mfspr(SPRN_PIR));
1881 printf("amr = %.16lx uamor = %.16lx\n",
1882 mfspr(SPRN_AMR), mfspr(SPRN_UAMOR));
1884 if (!(mfmsr() & MSR_HV))
1887 printf("sdr1 = %.16lx hdar = %.16lx hdsisr = %.8lx\n",
1888 mfspr(SPRN_SDR1), mfspr(SPRN_HDAR), mfspr(SPRN_HDSISR));
1889 printf("hsrr0 = %.16lx hsrr1 = %.16lx hdec = %.16lx\n",
1890 mfspr(SPRN_HSRR0), mfspr(SPRN_HSRR1), mfspr(SPRN_HDEC));
1891 printf("lpcr = %.16lx pcr = %.16lx lpidr = %.8lx\n",
1892 mfspr(SPRN_LPCR), mfspr(SPRN_PCR), mfspr(SPRN_LPID));
1893 printf("hsprg0 = %.16lx hsprg1 = %.16lx amor = %.16lx\n",
1894 mfspr(SPRN_HSPRG0), mfspr(SPRN_HSPRG1), mfspr(SPRN_AMOR));
1895 printf("dabr = %.16lx dabrx = %.16lx\n",
1896 mfspr(SPRN_DABR), mfspr(SPRN_DABRX));
1900 static void dump_207_sprs(void)
1905 if (!cpu_has_feature(CPU_FTR_ARCH_207S))
1908 printf("dpdes = %.16lx tir = %.16lx cir = %.8lx\n",
1909 mfspr(SPRN_DPDES), mfspr(SPRN_TIR), mfspr(SPRN_CIR));
1911 printf("fscr = %.16lx tar = %.16lx pspb = %.8lx\n",
1912 mfspr(SPRN_FSCR), mfspr(SPRN_TAR), mfspr(SPRN_PSPB));
1916 /* Only if TM has been enabled in the kernel */
1917 printf("tfhar = %.16lx tfiar = %.16lx texasr = %.16lx\n",
1918 mfspr(SPRN_TFHAR), mfspr(SPRN_TFIAR),
1919 mfspr(SPRN_TEXASR));
1922 printf("mmcr0 = %.16lx mmcr1 = %.16lx mmcr2 = %.16lx\n",
1923 mfspr(SPRN_MMCR0), mfspr(SPRN_MMCR1), mfspr(SPRN_MMCR2));
1924 printf("pmc1 = %.8lx pmc2 = %.8lx pmc3 = %.8lx pmc4 = %.8lx\n",
1925 mfspr(SPRN_PMC1), mfspr(SPRN_PMC2),
1926 mfspr(SPRN_PMC3), mfspr(SPRN_PMC4));
1927 printf("mmcra = %.16lx siar = %.16lx pmc5 = %.8lx\n",
1928 mfspr(SPRN_MMCRA), mfspr(SPRN_SIAR), mfspr(SPRN_PMC5));
1929 printf("sdar = %.16lx sier = %.16lx pmc6 = %.8lx\n",
1930 mfspr(SPRN_SDAR), mfspr(SPRN_SIER), mfspr(SPRN_PMC6));
1931 printf("ebbhr = %.16lx ebbrr = %.16lx bescr = %.16lx\n",
1932 mfspr(SPRN_EBBHR), mfspr(SPRN_EBBRR), mfspr(SPRN_BESCR));
1933 printf("iamr = %.16lx\n", mfspr(SPRN_IAMR));
1935 if (!(msr & MSR_HV))
1938 printf("hfscr = %.16lx dhdes = %.16lx rpr = %.16lx\n",
1939 mfspr(SPRN_HFSCR), mfspr(SPRN_DHDES), mfspr(SPRN_RPR));
1940 printf("dawr = %.16lx dawrx = %.16lx ciabr = %.16lx\n",
1941 mfspr(SPRN_DAWR), mfspr(SPRN_DAWRX), mfspr(SPRN_CIABR));
1945 static void dump_300_sprs(void)
1948 bool hv = mfmsr() & MSR_HV;
1950 if (!cpu_has_feature(CPU_FTR_ARCH_300))
1953 printf("pidr = %.16lx tidr = %.16lx\n",
1954 mfspr(SPRN_PID), mfspr(SPRN_TIDR));
1955 printf("psscr = %.16lx\n",
1956 hv ? mfspr(SPRN_PSSCR) : mfspr(SPRN_PSSCR_PR));
1961 printf("ptcr = %.16lx asdr = %.16lx\n",
1962 mfspr(SPRN_PTCR), mfspr(SPRN_ASDR));
1966 static void dump_one_spr(int spr, bool show_unimplemented)
1971 if (!read_spr(spr, &val)) {
1972 printf("SPR 0x%03x (%4d) Faulted during read\n", spr, spr);
1976 if (val == 0xdeadbeef) {
1977 /* Looks like read was a nop, confirm */
1979 if (!read_spr(spr, &val)) {
1980 printf("SPR 0x%03x (%4d) Faulted during read\n", spr, spr);
1984 if (val == 0x0badcafe) {
1985 if (show_unimplemented)
1986 printf("SPR 0x%03x (%4d) Unimplemented\n", spr, spr);
1991 printf("SPR 0x%03x (%4d) = 0x%lx\n", spr, spr, val);
1994 static void super_regs(void)
1996 static unsigned long regno;
2004 unsigned long sp, toc;
2005 asm("mr %0,1" : "=r" (sp) :);
2006 asm("mr %0,2" : "=r" (toc) :);
2008 printf("msr = "REG" sprg0 = "REG"\n",
2009 mfmsr(), mfspr(SPRN_SPRG0));
2010 printf("pvr = "REG" sprg1 = "REG"\n",
2011 mfspr(SPRN_PVR), mfspr(SPRN_SPRG1));
2012 printf("dec = "REG" sprg2 = "REG"\n",
2013 mfspr(SPRN_DEC), mfspr(SPRN_SPRG2));
2014 printf("sp = "REG" sprg3 = "REG"\n", sp, mfspr(SPRN_SPRG3));
2015 printf("toc = "REG" dar = "REG"\n", toc, mfspr(SPRN_DAR));
2027 read_spr(regno, &val);
2029 write_spr(regno, val);
2030 dump_one_spr(regno, true);
2035 dump_one_spr(regno, true);
2039 for (spr = 1; spr < 1024; ++spr)
2040 dump_one_spr(spr, false);
2048 * Stuff for reading and writing memory safely
2051 mread(unsigned long adrs, void *buf, int size)
2057 if (setjmp(bus_error_jmp) == 0) {
2058 catch_memory_errors = 1;
2064 *(u16 *)q = *(u16 *)p;
2067 *(u32 *)q = *(u32 *)p;
2070 *(u64 *)q = *(u64 *)p;
2073 for( ; n < size; ++n) {
2079 /* wait a little while to see if we get a machine check */
2083 catch_memory_errors = 0;
2088 mwrite(unsigned long adrs, void *buf, int size)
2096 printf(xmon_ro_msg);
2100 if (setjmp(bus_error_jmp) == 0) {
2101 catch_memory_errors = 1;
2107 *(u16 *)p = *(u16 *)q;
2110 *(u32 *)p = *(u32 *)q;
2113 *(u64 *)p = *(u64 *)q;
2116 for ( ; n < size; ++n) {
2122 /* wait a little while to see if we get a machine check */
2126 printf("*** Error writing address "REG"\n", adrs + n);
2128 catch_memory_errors = 0;
2132 static int fault_type;
2133 static int fault_except;
2134 static char *fault_chars[] = { "--", "**", "##" };
2136 static int handle_fault(struct pt_regs *regs)
2138 fault_except = TRAP(regs);
2139 switch (TRAP(regs)) {
2151 longjmp(bus_error_jmp, 1);
2156 #define SWAP(a, b, t) ((t) = (a), (a) = (b), (b) = (t))
2159 byterev(unsigned char *val, int size)
2165 SWAP(val[0], val[1], t);
2168 SWAP(val[0], val[3], t);
2169 SWAP(val[1], val[2], t);
2171 case 8: /* is there really any use for this? */
2172 SWAP(val[0], val[7], t);
2173 SWAP(val[1], val[6], t);
2174 SWAP(val[2], val[5], t);
2175 SWAP(val[3], val[4], t);
2183 static char *memex_help_string =
2184 "Memory examine command usage:\n"
2185 "m [addr] [flags] examine/change memory\n"
2186 " addr is optional. will start where left off.\n"
2187 " flags may include chars from this set:\n"
2188 " b modify by bytes (default)\n"
2189 " w modify by words (2 byte)\n"
2190 " l modify by longs (4 byte)\n"
2191 " d modify by doubleword (8 byte)\n"
2192 " r toggle reverse byte order mode\n"
2193 " n do not read memory (for i/o spaces)\n"
2194 " . ok to read (default)\n"
2195 "NOTE: flags are saved as defaults\n"
2198 static char *memex_subcmd_help_string =
2199 "Memory examine subcommands:\n"
2200 " hexval write this val to current location\n"
2201 " 'string' write chars from string to this location\n"
2202 " ' increment address\n"
2203 " ^ decrement address\n"
2204 " / increment addr by 0x10. //=0x100, ///=0x1000, etc\n"
2205 " \\ decrement addr by 0x10. \\\\=0x100, \\\\\\=0x1000, etc\n"
2206 " ` clear no-read flag\n"
2207 " ; stay at this addr\n"
2208 " v change to byte mode\n"
2209 " w change to word (2 byte) mode\n"
2210 " l change to long (4 byte) mode\n"
2211 " u change to doubleword (8 byte) mode\n"
2212 " m addr change current addr\n"
2213 " n toggle no-read flag\n"
2214 " r toggle byte reverse flag\n"
2215 " < count back up count bytes\n"
2216 " > count skip forward count bytes\n"
2217 " x exit this mode\n"
2223 int cmd, inc, i, nslash;
2225 unsigned char val[16];
2227 scanhex((void *)&adrs);
2230 printf(memex_help_string);
2236 while ((cmd = skipbl()) != '\n') {
2238 case 'b': size = 1; break;
2239 case 'w': size = 2; break;
2240 case 'l': size = 4; break;
2241 case 'd': size = 8; break;
2242 case 'r': brev = !brev; break;
2243 case 'n': mnoread = 1; break;
2244 case '.': mnoread = 0; break;
2253 n = mread(adrs, val, size);
2254 printf(REG"%c", adrs, brev? 'r': ' ');
2259 for (i = 0; i < n; ++i)
2260 printf("%.2x", val[i]);
2261 for (; i < size; ++i)
2262 printf("%s", fault_chars[fault_type]);
2269 for (i = 0; i < size; ++i)
2270 val[i] = n >> (i * 8);
2273 mwrite(adrs, val, size);
2286 else if( n == '\'' )
2288 for (i = 0; i < size; ++i)
2289 val[i] = n >> (i * 8);
2292 mwrite(adrs, val, size);
2328 adrs -= 1 << nslash;
2332 adrs += 1 << nslash;
2336 adrs += 1 << -nslash;
2340 adrs -= 1 << -nslash;
2343 scanhex((void *)&adrs);
2362 printf(memex_subcmd_help_string);
2377 case 'n': c = '\n'; break;
2378 case 'r': c = '\r'; break;
2379 case 'b': c = '\b'; break;
2380 case 't': c = '\t'; break;
2385 static void xmon_rawdump (unsigned long adrs, long ndump)
2388 unsigned char temp[16];
2390 for (n = ndump; n > 0;) {
2392 nr = mread(adrs, temp, r);
2394 for (m = 0; m < r; ++m) {
2396 printf("%.2x", temp[m]);
2398 printf("%s", fault_chars[fault_type]);
2407 static void dump_tracing(void)
2413 ftrace_dump(DUMP_ORIG);
2415 ftrace_dump(DUMP_ALL);
2419 static void dump_one_paca(int cpu)
2421 struct paca_struct *p;
2422 #ifdef CONFIG_PPC_BOOK3S_64
2426 if (setjmp(bus_error_jmp) != 0) {
2427 printf("*** Error dumping paca for cpu 0x%x!\n", cpu);
2431 catch_memory_errors = 1;
2436 printf("paca for cpu 0x%x @ %px:\n", cpu, p);
2438 printf(" %-*s = %s\n", 25, "possible", cpu_possible(cpu) ? "yes" : "no");
2439 printf(" %-*s = %s\n", 25, "present", cpu_present(cpu) ? "yes" : "no");
2440 printf(" %-*s = %s\n", 25, "online", cpu_online(cpu) ? "yes" : "no");
2442 #define DUMP(paca, name, format) \
2443 printf(" %-*s = "format"\t(0x%lx)\n", 25, #name, 18, paca->name, \
2444 offsetof(struct paca_struct, name));
2446 DUMP(p, lock_token, "%#-*x");
2447 DUMP(p, paca_index, "%#-*x");
2448 DUMP(p, kernel_toc, "%#-*llx");
2449 DUMP(p, kernelbase, "%#-*llx");
2450 DUMP(p, kernel_msr, "%#-*llx");
2451 DUMP(p, emergency_sp, "%-*px");
2452 #ifdef CONFIG_PPC_BOOK3S_64
2453 DUMP(p, nmi_emergency_sp, "%-*px");
2454 DUMP(p, mc_emergency_sp, "%-*px");
2455 DUMP(p, in_nmi, "%#-*x");
2456 DUMP(p, in_mce, "%#-*x");
2457 DUMP(p, hmi_event_available, "%#-*x");
2459 DUMP(p, data_offset, "%#-*llx");
2460 DUMP(p, hw_cpu_id, "%#-*x");
2461 DUMP(p, cpu_start, "%#-*x");
2462 DUMP(p, kexec_state, "%#-*x");
2463 #ifdef CONFIG_PPC_BOOK3S_64
2464 if (!early_radix_enabled()) {
2465 for (i = 0; i < SLB_NUM_BOLTED; i++) {
2468 if (!p->slb_shadow_ptr)
2471 esid = be64_to_cpu(p->slb_shadow_ptr->save_area[i].esid);
2472 vsid = be64_to_cpu(p->slb_shadow_ptr->save_area[i].vsid);
2475 printf(" %-*s[%d] = 0x%016llx 0x%016llx\n",
2476 22, "slb_shadow", i, esid, vsid);
2479 DUMP(p, vmalloc_sllp, "%#-*x");
2480 DUMP(p, stab_rr, "%#-*x");
2481 DUMP(p, slb_used_bitmap, "%#-*x");
2482 DUMP(p, slb_kern_bitmap, "%#-*x");
2484 if (!early_cpu_has_feature(CPU_FTR_ARCH_300)) {
2485 DUMP(p, slb_cache_ptr, "%#-*x");
2486 for (i = 0; i < SLB_CACHE_ENTRIES; i++)
2487 printf(" %-*s[%d] = 0x%016x\n",
2488 22, "slb_cache", i, p->slb_cache[i]);
2492 DUMP(p, rfi_flush_fallback_area, "%-*px");
2494 DUMP(p, dscr_default, "%#-*llx");
2495 #ifdef CONFIG_PPC_BOOK3E
2496 DUMP(p, pgd, "%-*px");
2497 DUMP(p, kernel_pgd, "%-*px");
2498 DUMP(p, tcd_ptr, "%-*px");
2499 DUMP(p, mc_kstack, "%-*px");
2500 DUMP(p, crit_kstack, "%-*px");
2501 DUMP(p, dbg_kstack, "%-*px");
2503 DUMP(p, __current, "%-*px");
2504 DUMP(p, kstack, "%#-*llx");
2505 printf(" %-*s = 0x%016llx\n", 25, "kstack_base", p->kstack & ~(THREAD_SIZE - 1));
2506 #ifdef CONFIG_STACKPROTECTOR
2507 DUMP(p, canary, "%#-*lx");
2509 DUMP(p, saved_r1, "%#-*llx");
2510 #ifdef CONFIG_PPC_BOOK3E
2511 DUMP(p, trap_save, "%#-*x");
2513 DUMP(p, irq_soft_mask, "%#-*x");
2514 DUMP(p, irq_happened, "%#-*x");
2515 #ifdef CONFIG_MMIOWB
2516 DUMP(p, mmiowb_state.nesting_count, "%#-*x");
2517 DUMP(p, mmiowb_state.mmiowb_pending, "%#-*x");
2519 DUMP(p, irq_work_pending, "%#-*x");
2520 DUMP(p, sprg_vdso, "%#-*llx");
2522 #ifdef CONFIG_PPC_TRANSACTIONAL_MEM
2523 DUMP(p, tm_scratch, "%#-*llx");
2526 #ifdef CONFIG_PPC_POWERNV
2527 DUMP(p, idle_state, "%#-*lx");
2528 if (!early_cpu_has_feature(CPU_FTR_ARCH_300)) {
2529 DUMP(p, thread_idle_state, "%#-*x");
2530 DUMP(p, subcore_sibling_mask, "%#-*x");
2532 #ifdef CONFIG_KVM_BOOK3S_HV_POSSIBLE
2533 DUMP(p, requested_psscr, "%#-*llx");
2534 DUMP(p, dont_stop.counter, "%#-*x");
2539 DUMP(p, accounting.utime, "%#-*lx");
2540 DUMP(p, accounting.stime, "%#-*lx");
2541 #ifdef CONFIG_ARCH_HAS_SCALED_CPUTIME
2542 DUMP(p, accounting.utime_scaled, "%#-*lx");
2544 DUMP(p, accounting.starttime, "%#-*lx");
2545 DUMP(p, accounting.starttime_user, "%#-*lx");
2546 #ifdef CONFIG_ARCH_HAS_SCALED_CPUTIME
2547 DUMP(p, accounting.startspurr, "%#-*lx");
2548 DUMP(p, accounting.utime_sspurr, "%#-*lx");
2550 DUMP(p, accounting.steal_time, "%#-*lx");
2553 catch_memory_errors = 0;
2557 static void dump_all_pacas(void)
2561 if (num_possible_cpus() == 0) {
2562 printf("No possible cpus, use 'dp #' to dump individual cpus\n");
2566 for_each_possible_cpu(cpu)
2570 static void dump_pacas(void)
2581 termch = c; /* Put c back, it wasn't 'a' */
2586 dump_one_paca(xmon_owner);
2590 #ifdef CONFIG_PPC_POWERNV
2591 static void dump_one_xive(int cpu)
2593 unsigned int hwid = get_hard_smp_processor_id(cpu);
2594 bool hv = cpu_has_feature(CPU_FTR_HVMODE);
2597 opal_xive_dump(XIVE_DUMP_TM_HYP, hwid);
2598 opal_xive_dump(XIVE_DUMP_TM_POOL, hwid);
2599 opal_xive_dump(XIVE_DUMP_TM_OS, hwid);
2600 opal_xive_dump(XIVE_DUMP_TM_USER, hwid);
2601 opal_xive_dump(XIVE_DUMP_VP, hwid);
2602 opal_xive_dump(XIVE_DUMP_EMU_STATE, hwid);
2605 if (setjmp(bus_error_jmp) != 0) {
2606 catch_memory_errors = 0;
2607 printf("*** Error dumping xive on cpu %d\n", cpu);
2611 catch_memory_errors = 1;
2613 xmon_xive_do_dump(cpu);
2616 catch_memory_errors = 0;
2619 static void dump_all_xives(void)
2623 if (num_possible_cpus() == 0) {
2624 printf("No possible cpus, use 'dx #' to dump individual cpus\n");
2628 for_each_possible_cpu(cpu)
2632 static void dump_one_xive_irq(u32 num, struct irq_data *d)
2634 xmon_xive_get_irq_config(num, d);
2637 static void dump_all_xive_irq(void)
2640 struct irq_desc *desc;
2642 for_each_irq_desc(i, desc) {
2643 struct irq_data *d = irq_desc_get_irq_data(desc);
2649 hwirq = (unsigned int)irqd_to_hwirq(d);
2650 /* IPIs are special (HW number 0) */
2652 dump_one_xive_irq(hwirq, d);
2656 static void dump_xives(void)
2661 if (!xive_enabled()) {
2662 printf("Xive disabled on this system\n");
2670 } else if (c == 'i') {
2672 dump_one_xive_irq(num, NULL);
2674 dump_all_xive_irq();
2678 termch = c; /* Put c back, it wasn't 'a' */
2683 dump_one_xive(xmon_owner);
2685 #endif /* CONFIG_PPC_POWERNV */
2687 static void dump_by_size(unsigned long addr, long count, int size)
2689 unsigned char temp[16];
2693 count = ALIGN(count, 16);
2695 for (i = 0; i < count; i += 16, addr += 16) {
2698 if (mread(addr, temp, 16) != 16) {
2699 printf("\nFaulted reading %d bytes from 0x"REG"\n", 16, addr);
2703 for (j = 0; j < 16; j += size) {
2706 case 1: val = temp[j]; break;
2707 case 2: val = *(u16 *)&temp[j]; break;
2708 case 4: val = *(u32 *)&temp[j]; break;
2709 case 8: val = *(u64 *)&temp[j]; break;
2713 printf("%0*llx", size * 2, val);
2722 static char last[] = { "d?\n" };
2729 xmon_start_pagination();
2731 xmon_end_pagination();
2735 #ifdef CONFIG_PPC_POWERNV
2737 xmon_start_pagination();
2739 xmon_end_pagination();
2752 scanhex((void *)&adrs);
2759 else if (nidump > MAX_DUMP)
2761 adrs += ppc_inst_dump(adrs, nidump, 1);
2763 } else if (c == 'l') {
2765 } else if (c == 'o') {
2767 } else if (c == 'v') {
2768 /* dump virtual to physical translation */
2770 } else if (c == 'r') {
2774 xmon_rawdump(adrs, ndump);
2781 else if (ndump > MAX_DUMP)
2789 ndump = ALIGN(ndump, 16);
2790 dump_by_size(adrs, ndump, c - '0');
2795 prdump(adrs, ndump);
2804 prdump(unsigned long adrs, long ndump)
2806 long n, m, c, r, nr;
2807 unsigned char temp[16];
2809 for (n = ndump; n > 0;) {
2813 nr = mread(adrs, temp, r);
2815 for (m = 0; m < r; ++m) {
2816 if ((m & (sizeof(long) - 1)) == 0 && m > 0)
2819 printf("%.2x", temp[m]);
2821 printf("%s", fault_chars[fault_type]);
2823 for (; m < 16; ++m) {
2824 if ((m & (sizeof(long) - 1)) == 0)
2829 for (m = 0; m < r; ++m) {
2832 putchar(' ' <= c && c <= '~'? c: '.');
2845 typedef int (*instruction_dump_func)(unsigned long inst, unsigned long addr);
2848 generic_inst_dump(unsigned long adr, long count, int praddr,
2849 instruction_dump_func dump_func)
2852 unsigned long first_adr;
2853 unsigned int inst, last_inst = 0;
2854 unsigned char val[4];
2857 for (first_adr = adr; count > 0; --count, adr += 4) {
2858 nr = mread(adr, val, 4);
2861 const char *x = fault_chars[fault_type];
2862 printf(REG" %s%s%s%s\n", adr, x, x, x, x);
2866 inst = GETWORD(val);
2867 if (adr > first_adr && inst == last_inst) {
2877 printf(REG" %.8x", adr, inst);
2879 dump_func(inst, adr);
2882 return adr - first_adr;
2886 ppc_inst_dump(unsigned long adr, long count, int praddr)
2888 return generic_inst_dump(adr, count, praddr, print_insn_powerpc);
2892 print_address(unsigned long addr)
2894 xmon_print_symbol(addr, "\t# ", "");
2900 struct kmsg_dumper dumper = { .active = 1 };
2901 unsigned char buf[128];
2904 if (setjmp(bus_error_jmp) != 0) {
2905 printf("Error dumping printk buffer!\n");
2909 catch_memory_errors = 1;
2912 kmsg_dump_rewind_nolock(&dumper);
2913 xmon_start_pagination();
2914 while (kmsg_dump_get_line_nolock(&dumper, false, buf, sizeof(buf), &len)) {
2918 xmon_end_pagination();
2921 /* wait a little while to see if we get a machine check */
2923 catch_memory_errors = 0;
2926 #ifdef CONFIG_PPC_POWERNV
2927 static void dump_opal_msglog(void)
2929 unsigned char buf[128];
2933 if (!firmware_has_feature(FW_FEATURE_OPAL)) {
2934 printf("Machine is not running OPAL firmware.\n");
2938 if (setjmp(bus_error_jmp) != 0) {
2939 printf("Error dumping OPAL msglog!\n");
2943 catch_memory_errors = 1;
2946 xmon_start_pagination();
2947 while ((res = opal_msglog_copy(buf, pos, sizeof(buf) - 1))) {
2949 printf("Error dumping OPAL msglog! Error: %zd\n", res);
2956 xmon_end_pagination();
2959 /* wait a little while to see if we get a machine check */
2961 catch_memory_errors = 0;
2966 * Memory operations - move, set, print differences
2968 static unsigned long mdest; /* destination address */
2969 static unsigned long msrc; /* source address */
2970 static unsigned long mval; /* byte value to set memory to */
2971 static unsigned long mcount; /* # bytes to affect */
2972 static unsigned long mdiffs; /* max # differences to print */
2977 scanhex((void *)&mdest);
2978 if( termch != '\n' )
2980 scanhex((void *)(cmd == 's'? &mval: &msrc));
2981 if( termch != '\n' )
2983 scanhex((void *)&mcount);
2987 printf(xmon_ro_msg);
2990 memmove((void *)mdest, (void *)msrc, mcount);
2994 printf(xmon_ro_msg);
2997 memset((void *)mdest, mval, mcount);
3000 if( termch != '\n' )
3002 scanhex((void *)&mdiffs);
3003 memdiffs((unsigned char *)mdest, (unsigned char *)msrc, mcount, mdiffs);
3009 memdiffs(unsigned char *p1, unsigned char *p2, unsigned nb, unsigned maxpr)
3014 for( n = nb; n > 0; --n )
3015 if( *p1++ != *p2++ )
3016 if( ++prt <= maxpr )
3017 printf("%px %.2x # %px %.2x\n", p1 - 1,
3018 p1[-1], p2 - 1, p2[-1]);
3020 printf("Total of %d differences\n", prt);
3023 static unsigned mend;
3024 static unsigned mask;
3030 unsigned char val[4];
3033 scanhex((void *)&mdest);
3034 if (termch != '\n') {
3036 scanhex((void *)&mend);
3037 if (termch != '\n') {
3039 scanhex((void *)&mval);
3041 if (termch != '\n') termch = 0;
3042 scanhex((void *)&mask);
3046 for (a = mdest; a < mend; a += 4) {
3047 if (mread(a, val, 4) == 4
3048 && ((GETWORD(val) ^ mval) & mask) == 0) {
3049 printf("%.16x: %.16x\n", a, GETWORD(val));
3056 static unsigned long mskip = 0x1000;
3057 static unsigned long mlim = 0xffffffff;
3067 if (termch != '\n') termch = 0;
3069 if (termch != '\n') termch = 0;
3072 for (a = mdest; a < mlim; a += mskip) {
3073 ok = mread(a, &v, 1);
3075 printf("%.8x .. ", a);
3076 } else if (!ok && ook)
3077 printf("%.8lx\n", a - mskip);
3083 printf("%.8lx\n", a - mskip);
3086 static void show_task(struct task_struct *tsk)
3091 * Cloned from kdb_task_state_char(), which is not entirely
3092 * appropriate for calling from xmon. This could be moved
3093 * to a common, generic, routine used by both.
3095 state = (tsk->state == 0) ? 'R' :
3096 (tsk->state < 0) ? 'U' :
3097 (tsk->state & TASK_UNINTERRUPTIBLE) ? 'D' :
3098 (tsk->state & TASK_STOPPED) ? 'T' :
3099 (tsk->state & TASK_TRACED) ? 'C' :
3100 (tsk->exit_state & EXIT_ZOMBIE) ? 'Z' :
3101 (tsk->exit_state & EXIT_DEAD) ? 'E' :
3102 (tsk->state & TASK_INTERRUPTIBLE) ? 'S' : '?';
3104 printf("%px %016lx %6d %6d %c %2d %s\n", tsk,
3106 tsk->pid, rcu_dereference(tsk->parent)->pid,
3107 state, task_cpu(tsk),
3111 #ifdef CONFIG_PPC_BOOK3S_64
3112 static void format_pte(void *ptep, unsigned long pte)
3114 pte_t entry = __pte(pte);
3116 printf("ptep @ 0x%016lx = 0x%016lx\n", (unsigned long)ptep, pte);
3117 printf("Maps physical address = 0x%016lx\n", pte & PTE_RPN_MASK);
3119 printf("Flags = %s%s%s%s%s\n",
3120 pte_young(entry) ? "Accessed " : "",
3121 pte_dirty(entry) ? "Dirty " : "",
3122 pte_read(entry) ? "Read " : "",
3123 pte_write(entry) ? "Write " : "",
3124 pte_exec(entry) ? "Exec " : "");
3127 static void show_pte(unsigned long addr)
3129 unsigned long tskv = 0;
3130 struct task_struct *tsk = NULL;
3131 struct mm_struct *mm;
3132 pgd_t *pgdp, *pgdir;
3137 if (!scanhex(&tskv))
3140 tsk = (struct task_struct *)tskv;
3145 mm = tsk->active_mm;
3147 if (setjmp(bus_error_jmp) != 0) {
3148 catch_memory_errors = 0;
3149 printf("*** Error dumping pte for task %px\n", tsk);
3153 catch_memory_errors = 1;
3156 if (mm == &init_mm) {
3157 pgdp = pgd_offset_k(addr);
3158 pgdir = pgd_offset_k(0);
3160 pgdp = pgd_offset(mm, addr);
3161 pgdir = pgd_offset(mm, 0);
3164 if (pgd_none(*pgdp)) {
3165 printf("no linux page table for address\n");
3169 printf("pgd @ 0x%px\n", pgdir);
3171 if (pgd_is_leaf(*pgdp)) {
3172 format_pte(pgdp, pgd_val(*pgdp));
3175 printf("pgdp @ 0x%px = 0x%016lx\n", pgdp, pgd_val(*pgdp));
3177 pudp = pud_offset(pgdp, addr);
3179 if (pud_none(*pudp)) {
3180 printf("No valid PUD\n");
3184 if (pud_is_leaf(*pudp)) {
3185 format_pte(pudp, pud_val(*pudp));
3189 printf("pudp @ 0x%px = 0x%016lx\n", pudp, pud_val(*pudp));
3191 pmdp = pmd_offset(pudp, addr);
3193 if (pmd_none(*pmdp)) {
3194 printf("No valid PMD\n");
3198 if (pmd_is_leaf(*pmdp)) {
3199 format_pte(pmdp, pmd_val(*pmdp));
3202 printf("pmdp @ 0x%px = 0x%016lx\n", pmdp, pmd_val(*pmdp));
3204 ptep = pte_offset_map(pmdp, addr);
3205 if (pte_none(*ptep)) {
3206 printf("no valid PTE\n");
3210 format_pte(ptep, pte_val(*ptep));
3214 catch_memory_errors = 0;
3217 static void show_pte(unsigned long addr)
3219 printf("show_pte not yet implemented\n");
3221 #endif /* CONFIG_PPC_BOOK3S_64 */
3223 static void show_tasks(void)
3226 struct task_struct *tsk = NULL;
3228 printf(" task_struct ->thread.ksp PID PPID S P CMD\n");
3231 tsk = (struct task_struct *)tskv;
3233 if (setjmp(bus_error_jmp) != 0) {
3234 catch_memory_errors = 0;
3235 printf("*** Error dumping task %px\n", tsk);
3239 catch_memory_errors = 1;
3245 for_each_process(tsk)
3250 catch_memory_errors = 0;
3253 static void proccall(void)
3255 unsigned long args[8];
3258 typedef unsigned long (*callfunc_t)(unsigned long, unsigned long,
3259 unsigned long, unsigned long, unsigned long,
3260 unsigned long, unsigned long, unsigned long);
3263 if (!scanhex(&adrs))
3267 for (i = 0; i < 8; ++i)
3269 for (i = 0; i < 8; ++i) {
3270 if (!scanhex(&args[i]) || termch == '\n')
3274 func = (callfunc_t) adrs;
3276 if (setjmp(bus_error_jmp) == 0) {
3277 catch_memory_errors = 1;
3279 ret = func(args[0], args[1], args[2], args[3],
3280 args[4], args[5], args[6], args[7]);
3282 printf("return value is 0x%lx\n", ret);
3284 printf("*** %x exception occurred\n", fault_except);
3286 catch_memory_errors = 0;
3289 /* Input scanning routines */
3300 while( c == ' ' || c == '\t' )
3306 static const char *regnames[N_PTREGS] = {
3307 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
3308 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
3309 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
3310 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
3311 "pc", "msr", "or3", "ctr", "lr", "xer", "ccr",
3317 "trap", "dar", "dsisr", "res"
3321 scanhex(unsigned long *vp)
3328 /* parse register name */
3332 for (i = 0; i < sizeof(regname) - 1; ++i) {
3341 i = match_string(regnames, N_PTREGS, regname);
3343 printf("invalid register name '%%%s'\n", regname);
3346 if (xmon_regs == NULL) {
3347 printf("regs not available\n");
3350 *vp = ((unsigned long *)xmon_regs)[i];
3354 /* skip leading "0x" if any */
3368 } else if (c == '$') {
3370 for (i=0; i<63; i++) {
3372 if (isspace(c) || c == '\0') {
3380 if (setjmp(bus_error_jmp) == 0) {
3381 catch_memory_errors = 1;
3383 *vp = kallsyms_lookup_name(tmpstr);
3386 catch_memory_errors = 0;
3388 printf("unknown symbol '%s'\n", tmpstr);
3421 static int hexdigit(int c)
3423 if( '0' <= c && c <= '9' )
3425 if( 'A' <= c && c <= 'F' )
3426 return c - ('A' - 10);
3427 if( 'a' <= c && c <= 'f' )
3428 return c - ('a' - 10);
3433 getstring(char *s, int size)
3449 } while( c != ' ' && c != '\t' && c != '\n' );
3454 static char line[256];
3455 static char *lineptr;
3466 if (lineptr == NULL || *lineptr == 0) {
3467 if (xmon_gets(line, sizeof(line)) == NULL) {
3477 take_input(char *str)
3486 int type = inchar();
3487 unsigned long addr, cpu;
3488 void __percpu *ptr = NULL;
3489 static char tmp[64];
3494 xmon_print_symbol(addr, ": ", "\n");
3499 if (setjmp(bus_error_jmp) == 0) {
3500 catch_memory_errors = 1;
3502 addr = kallsyms_lookup_name(tmp);
3504 printf("%s: %lx\n", tmp, addr);
3506 printf("Symbol '%s' not found.\n", tmp);
3509 catch_memory_errors = 0;
3514 if (setjmp(bus_error_jmp) == 0) {
3515 catch_memory_errors = 1;
3517 ptr = (void __percpu *)kallsyms_lookup_name(tmp);
3522 ptr >= (void __percpu *)__per_cpu_start &&
3523 ptr < (void __percpu *)__per_cpu_end)
3525 if (scanhex(&cpu) && cpu < num_possible_cpus()) {
3526 addr = (unsigned long)per_cpu_ptr(ptr, cpu);
3528 cpu = raw_smp_processor_id();
3529 addr = (unsigned long)this_cpu_ptr(ptr);
3532 printf("%s for cpu 0x%lx: %lx\n", tmp, cpu, addr);
3534 printf("Percpu symbol '%s' not found.\n", tmp);
3537 catch_memory_errors = 0;
3544 /* Print an address in numeric and symbolic form (if possible) */
3545 static void xmon_print_symbol(unsigned long address, const char *mid,
3549 const char *name = NULL;
3550 unsigned long offset, size;
3552 printf(REG, address);
3553 if (setjmp(bus_error_jmp) == 0) {
3554 catch_memory_errors = 1;
3556 name = kallsyms_lookup(address, &size, &offset, &modname,
3559 /* wait a little while to see if we get a machine check */
3563 catch_memory_errors = 0;
3566 printf("%s%s+%#lx/%#lx", mid, name, offset, size);
3568 printf(" [%s]", modname);
3570 printf("%s", after);
3573 #ifdef CONFIG_PPC_BOOK3S_64
3574 void dump_segments(void)
3577 unsigned long esid,vsid;
3580 printf("SLB contents of cpu 0x%x\n", smp_processor_id());
3582 for (i = 0; i < mmu_slb_size; i++) {
3583 asm volatile("slbmfee %0,%1" : "=r" (esid) : "r" (i));
3584 asm volatile("slbmfev %0,%1" : "=r" (vsid) : "r" (i));
3589 printf("%02d %016lx %016lx", i, esid, vsid);
3591 if (!(esid & SLB_ESID_V)) {
3596 llp = vsid & SLB_VSID_LLP;
3597 if (vsid & SLB_VSID_B_1T) {
3598 printf(" 1T ESID=%9lx VSID=%13lx LLP:%3lx \n",
3600 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT_1T,
3603 printf(" 256M ESID=%9lx VSID=%13lx LLP:%3lx \n",
3605 (vsid & ~SLB_VSID_B) >> SLB_VSID_SHIFT,
3612 #ifdef CONFIG_PPC_BOOK3S_32
3613 void dump_segments(void)
3618 for (i = 0; i < 16; ++i)
3619 printf(" %x", mfsrin(i << 28));
3625 static void dump_tlb_44x(void)
3629 for (i = 0; i < PPC44x_TLB_SIZE; i++) {
3630 unsigned long w0,w1,w2;
3631 asm volatile("tlbre %0,%1,0" : "=r" (w0) : "r" (i));
3632 asm volatile("tlbre %0,%1,1" : "=r" (w1) : "r" (i));
3633 asm volatile("tlbre %0,%1,2" : "=r" (w2) : "r" (i));
3634 printf("[%02x] %08lx %08lx %08lx ", i, w0, w1, w2);
3635 if (w0 & PPC44x_TLB_VALID) {
3636 printf("V %08lx -> %01lx%08lx %c%c%c%c%c",
3637 w0 & PPC44x_TLB_EPN_MASK,
3638 w1 & PPC44x_TLB_ERPN_MASK,
3639 w1 & PPC44x_TLB_RPN_MASK,
3640 (w2 & PPC44x_TLB_W) ? 'W' : 'w',
3641 (w2 & PPC44x_TLB_I) ? 'I' : 'i',
3642 (w2 & PPC44x_TLB_M) ? 'M' : 'm',
3643 (w2 & PPC44x_TLB_G) ? 'G' : 'g',
3644 (w2 & PPC44x_TLB_E) ? 'E' : 'e');
3649 #endif /* CONFIG_44x */
3651 #ifdef CONFIG_PPC_BOOK3E
3652 static void dump_tlb_book3e(void)
3654 u32 mmucfg, pidmask, lpidmask;
3656 int i, tlb, ntlbs, pidsz, lpidsz, rasz, lrat = 0;
3658 static const char *pgsz_names[] = {
3693 /* Gather some infos about the MMU */
3694 mmucfg = mfspr(SPRN_MMUCFG);
3695 mmu_version = (mmucfg & 3) + 1;
3696 ntlbs = ((mmucfg >> 2) & 3) + 1;
3697 pidsz = ((mmucfg >> 6) & 0x1f) + 1;
3698 lpidsz = (mmucfg >> 24) & 0xf;
3699 rasz = (mmucfg >> 16) & 0x7f;
3700 if ((mmu_version > 1) && (mmucfg & 0x10000))
3702 printf("Book3E MMU MAV=%d.0,%d TLBs,%d-bit PID,%d-bit LPID,%d-bit RA\n",
3703 mmu_version, ntlbs, pidsz, lpidsz, rasz);
3704 pidmask = (1ul << pidsz) - 1;
3705 lpidmask = (1ul << lpidsz) - 1;
3706 ramask = (1ull << rasz) - 1;
3708 for (tlb = 0; tlb < ntlbs; tlb++) {
3710 int nent, assoc, new_cc = 1;
3711 printf("TLB %d:\n------\n", tlb);
3714 tlbcfg = mfspr(SPRN_TLB0CFG);
3717 tlbcfg = mfspr(SPRN_TLB1CFG);
3720 tlbcfg = mfspr(SPRN_TLB2CFG);
3723 tlbcfg = mfspr(SPRN_TLB3CFG);
3726 printf("Unsupported TLB number !\n");
3729 nent = tlbcfg & 0xfff;
3730 assoc = (tlbcfg >> 24) & 0xff;
3731 for (i = 0; i < nent; i++) {
3732 u32 mas0 = MAS0_TLBSEL(tlb);
3733 u32 mas1 = MAS1_TSIZE(BOOK3E_PAGESZ_4K);
3736 int esel = i, cc = i;
3744 mas0 |= MAS0_ESEL(esel);
3745 mtspr(SPRN_MAS0, mas0);
3746 mtspr(SPRN_MAS1, mas1);
3747 mtspr(SPRN_MAS2, mas2);
3748 asm volatile("tlbre 0,0,0" : : : "memory");
3749 mas1 = mfspr(SPRN_MAS1);
3750 mas2 = mfspr(SPRN_MAS2);
3751 mas7_mas3 = mfspr(SPRN_MAS7_MAS3);
3752 if (assoc && (i % assoc) == 0)
3754 if (!(mas1 & MAS1_VALID))
3757 printf("%04x- ", i);
3759 printf("%04x-%c", cc, 'A' + esel);
3761 printf(" |%c", 'A' + esel);
3763 printf(" %016llx %04x %s %c%c AS%c",
3765 (mas1 >> 16) & 0x3fff,
3766 pgsz_names[(mas1 >> 7) & 0x1f],
3767 mas1 & MAS1_IND ? 'I' : ' ',
3768 mas1 & MAS1_IPROT ? 'P' : ' ',
3769 mas1 & MAS1_TS ? '1' : '0');
3770 printf(" %c%c%c%c%c%c%c",
3771 mas2 & MAS2_X0 ? 'a' : ' ',
3772 mas2 & MAS2_X1 ? 'v' : ' ',
3773 mas2 & MAS2_W ? 'w' : ' ',
3774 mas2 & MAS2_I ? 'i' : ' ',
3775 mas2 & MAS2_M ? 'm' : ' ',
3776 mas2 & MAS2_G ? 'g' : ' ',
3777 mas2 & MAS2_E ? 'e' : ' ');
3778 printf(" %016llx", mas7_mas3 & ramask & ~0x7ffull);
3779 if (mas1 & MAS1_IND)
3781 pgsz_names[(mas7_mas3 >> 1) & 0x1f]);
3783 printf(" U%c%c%c S%c%c%c\n",
3784 mas7_mas3 & MAS3_UX ? 'x' : ' ',
3785 mas7_mas3 & MAS3_UW ? 'w' : ' ',
3786 mas7_mas3 & MAS3_UR ? 'r' : ' ',
3787 mas7_mas3 & MAS3_SX ? 'x' : ' ',
3788 mas7_mas3 & MAS3_SW ? 'w' : ' ',
3789 mas7_mas3 & MAS3_SR ? 'r' : ' ');
3793 #endif /* CONFIG_PPC_BOOK3E */
3795 static void xmon_init(int enable)
3799 __debugger_ipi = xmon_ipi;
3800 __debugger_bpt = xmon_bpt;
3801 __debugger_sstep = xmon_sstep;
3802 __debugger_iabr_match = xmon_iabr_match;
3803 __debugger_break_match = xmon_break_match;
3804 __debugger_fault_handler = xmon_fault_handler;
3806 #ifdef CONFIG_PPC_PSERIES
3808 * Get the token here to avoid trying to get a lock
3809 * during the crash, causing a deadlock.
3811 set_indicator_token = rtas_token("set-indicator");
3815 __debugger_ipi = NULL;
3816 __debugger_bpt = NULL;
3817 __debugger_sstep = NULL;
3818 __debugger_iabr_match = NULL;
3819 __debugger_break_match = NULL;
3820 __debugger_fault_handler = NULL;
3824 #ifdef CONFIG_MAGIC_SYSRQ
3825 static void sysrq_handle_xmon(int key)
3827 if (xmon_is_locked_down()) {
3832 /* ensure xmon is enabled */
3834 debugger(get_irq_regs());
3839 static struct sysrq_key_op sysrq_xmon_op = {
3840 .handler = sysrq_handle_xmon,
3841 .help_msg = "xmon(x)",
3842 .action_msg = "Entering xmon",
3845 static int __init setup_xmon_sysrq(void)
3847 register_sysrq_key('x', &sysrq_xmon_op);
3850 device_initcall(setup_xmon_sysrq);
3851 #endif /* CONFIG_MAGIC_SYSRQ */
3853 static void clear_all_bpt(void)
3857 /* clear/unpatch all breakpoints */
3861 /* Disable all breakpoints */
3862 for (i = 0; i < NBPTS; ++i)
3863 bpts[i].enabled = 0;
3865 /* Clear any data or iabr breakpoints */
3866 if (iabr || dabr.enabled) {
3872 #ifdef CONFIG_DEBUG_FS
3873 static int xmon_dbgfs_set(void *data, u64 val)
3878 /* make sure all breakpoints removed when disabling */
3882 printf("xmon: All breakpoints cleared\n");
3883 release_output_lock();
3889 static int xmon_dbgfs_get(void *data, u64 *val)
3895 DEFINE_SIMPLE_ATTRIBUTE(xmon_dbgfs_ops, xmon_dbgfs_get,
3896 xmon_dbgfs_set, "%llu\n");
3898 static int __init setup_xmon_dbgfs(void)
3900 debugfs_create_file("xmon", 0600, powerpc_debugfs_root, NULL,
3904 device_initcall(setup_xmon_dbgfs);
3905 #endif /* CONFIG_DEBUG_FS */
3907 static int xmon_early __initdata;
3909 static int __init early_parse_xmon(char *p)
3911 if (xmon_is_locked_down()) {
3915 } else if (!p || strncmp(p, "early", 5) == 0) {
3916 /* just "xmon" is equivalent to "xmon=early" */
3920 } else if (strncmp(p, "on", 2) == 0) {
3923 } else if (strncmp(p, "rw", 2) == 0) {
3927 } else if (strncmp(p, "ro", 2) == 0) {
3931 } else if (strncmp(p, "off", 3) == 0)
3938 early_param("xmon", early_parse_xmon);
3940 void __init xmon_setup(void)
3948 #ifdef CONFIG_SPU_BASE
3952 u64 saved_mfc_sr1_RW;
3953 u32 saved_spu_runcntl_RW;
3954 unsigned long dump_addr;
3958 #define XMON_NUM_SPUS 16 /* Enough for current hardware */
3960 static struct spu_info spu_info[XMON_NUM_SPUS];
3962 void xmon_register_spus(struct list_head *list)
3966 list_for_each_entry(spu, list, full_list) {
3967 if (spu->number >= XMON_NUM_SPUS) {
3972 spu_info[spu->number].spu = spu;
3973 spu_info[spu->number].stopped_ok = 0;
3974 spu_info[spu->number].dump_addr = (unsigned long)
3975 spu_info[spu->number].spu->local_store;
3979 static void stop_spus(void)
3985 for (i = 0; i < XMON_NUM_SPUS; i++) {
3986 if (!spu_info[i].spu)
3989 if (setjmp(bus_error_jmp) == 0) {
3990 catch_memory_errors = 1;
3993 spu = spu_info[i].spu;
3995 spu_info[i].saved_spu_runcntl_RW =
3996 in_be32(&spu->problem->spu_runcntl_RW);
3998 tmp = spu_mfc_sr1_get(spu);
3999 spu_info[i].saved_mfc_sr1_RW = tmp;
4001 tmp &= ~MFC_STATE1_MASTER_RUN_CONTROL_MASK;
4002 spu_mfc_sr1_set(spu, tmp);
4007 spu_info[i].stopped_ok = 1;
4009 printf("Stopped spu %.2d (was %s)\n", i,
4010 spu_info[i].saved_spu_runcntl_RW ?
4011 "running" : "stopped");
4013 catch_memory_errors = 0;
4014 printf("*** Error stopping spu %.2d\n", i);
4016 catch_memory_errors = 0;
4020 static void restart_spus(void)
4025 for (i = 0; i < XMON_NUM_SPUS; i++) {
4026 if (!spu_info[i].spu)
4029 if (!spu_info[i].stopped_ok) {
4030 printf("*** Error, spu %d was not successfully stopped"
4031 ", not restarting\n", i);
4035 if (setjmp(bus_error_jmp) == 0) {
4036 catch_memory_errors = 1;
4039 spu = spu_info[i].spu;
4040 spu_mfc_sr1_set(spu, spu_info[i].saved_mfc_sr1_RW);
4041 out_be32(&spu->problem->spu_runcntl_RW,
4042 spu_info[i].saved_spu_runcntl_RW);
4047 printf("Restarted spu %.2d\n", i);
4049 catch_memory_errors = 0;
4050 printf("*** Error restarting spu %.2d\n", i);
4052 catch_memory_errors = 0;
4056 #define DUMP_WIDTH 23
4057 #define DUMP_VALUE(format, field, value) \
4059 if (setjmp(bus_error_jmp) == 0) { \
4060 catch_memory_errors = 1; \
4062 printf(" %-*s = "format"\n", DUMP_WIDTH, \
4067 catch_memory_errors = 0; \
4068 printf(" %-*s = *** Error reading field.\n", \
4069 DUMP_WIDTH, #field); \
4071 catch_memory_errors = 0; \
4074 #define DUMP_FIELD(obj, format, field) \
4075 DUMP_VALUE(format, field, obj->field)
4077 static void dump_spu_fields(struct spu *spu)
4079 printf("Dumping spu fields at address %p:\n", spu);
4081 DUMP_FIELD(spu, "0x%x", number);
4082 DUMP_FIELD(spu, "%s", name);
4083 DUMP_FIELD(spu, "0x%lx", local_store_phys);
4084 DUMP_FIELD(spu, "0x%p", local_store);
4085 DUMP_FIELD(spu, "0x%lx", ls_size);
4086 DUMP_FIELD(spu, "0x%x", node);
4087 DUMP_FIELD(spu, "0x%lx", flags);
4088 DUMP_FIELD(spu, "%llu", class_0_pending);
4089 DUMP_FIELD(spu, "0x%llx", class_0_dar);
4090 DUMP_FIELD(spu, "0x%llx", class_1_dar);
4091 DUMP_FIELD(spu, "0x%llx", class_1_dsisr);
4092 DUMP_FIELD(spu, "0x%x", irqs[0]);
4093 DUMP_FIELD(spu, "0x%x", irqs[1]);
4094 DUMP_FIELD(spu, "0x%x", irqs[2]);
4095 DUMP_FIELD(spu, "0x%x", slb_replace);
4096 DUMP_FIELD(spu, "%d", pid);
4097 DUMP_FIELD(spu, "0x%p", mm);
4098 DUMP_FIELD(spu, "0x%p", ctx);
4099 DUMP_FIELD(spu, "0x%p", rq);
4100 DUMP_FIELD(spu, "0x%llx", timestamp);
4101 DUMP_FIELD(spu, "0x%lx", problem_phys);
4102 DUMP_FIELD(spu, "0x%p", problem);
4103 DUMP_VALUE("0x%x", problem->spu_runcntl_RW,
4104 in_be32(&spu->problem->spu_runcntl_RW));
4105 DUMP_VALUE("0x%x", problem->spu_status_R,
4106 in_be32(&spu->problem->spu_status_R));
4107 DUMP_VALUE("0x%x", problem->spu_npc_RW,
4108 in_be32(&spu->problem->spu_npc_RW));
4109 DUMP_FIELD(spu, "0x%p", priv2);
4110 DUMP_FIELD(spu, "0x%p", pdata);
4114 spu_inst_dump(unsigned long adr, long count, int praddr)
4116 return generic_inst_dump(adr, count, praddr, print_insn_spu);
4119 static void dump_spu_ls(unsigned long num, int subcmd)
4121 unsigned long offset, addr, ls_addr;
4123 if (setjmp(bus_error_jmp) == 0) {
4124 catch_memory_errors = 1;
4126 ls_addr = (unsigned long)spu_info[num].spu->local_store;
4130 catch_memory_errors = 0;
4131 printf("*** Error: accessing spu info for spu %ld\n", num);
4134 catch_memory_errors = 0;
4136 if (scanhex(&offset))
4137 addr = ls_addr + offset;
4139 addr = spu_info[num].dump_addr;
4141 if (addr >= ls_addr + LS_SIZE) {
4142 printf("*** Error: address outside of local store\n");
4148 addr += spu_inst_dump(addr, 16, 1);
4158 spu_info[num].dump_addr = addr;
4161 static int do_spu_cmd(void)
4163 static unsigned long num = 0;
4164 int cmd, subcmd = 0;
4176 if (isxdigit(subcmd) || subcmd == '\n')
4181 if (num >= XMON_NUM_SPUS || !spu_info[num].spu) {
4182 printf("*** Error: invalid spu number\n");
4188 dump_spu_fields(spu_info[num].spu);
4191 dump_spu_ls(num, subcmd);
4202 #else /* ! CONFIG_SPU_BASE */
4203 static int do_spu_cmd(void)