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