MIPS: Add SysRq operation to dump TLBs on all CPUs
Add a MIPS specific SysRq operation to dump the TLB entries on all CPUs, using the 'x' trigger key. Signed-off-by: James Hogan <james.hogan@imgtec.com> Cc: linux-mips@linux-mips.org Patchwork: https://patchwork.linux-mips.org/patch/10072/ Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
This commit is contained in:
		
							parent
							
								
									37dd3818d1
								
							
						
					
					
						commit
						d1e9a4f547
					
				| @ -77,6 +77,7 @@ obj-$(CONFIG_MIPS32_O32)	+= binfmt_elfo32.o scall64-o32.o | |||||||
| 
 | 
 | ||||||
| obj-$(CONFIG_KGDB)		+= kgdb.o | obj-$(CONFIG_KGDB)		+= kgdb.o | ||||||
| obj-$(CONFIG_PROC_FS)		+= proc.o | obj-$(CONFIG_PROC_FS)		+= proc.o | ||||||
|  | obj-$(CONFIG_MAGIC_SYSRQ)	+= sysrq.o | ||||||
| 
 | 
 | ||||||
| obj-$(CONFIG_64BIT)		+= cpu-bugs64.o | obj-$(CONFIG_64BIT)		+= cpu-bugs64.o | ||||||
| 
 | 
 | ||||||
|  | |||||||
							
								
								
									
										77
									
								
								arch/mips/kernel/sysrq.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										77
									
								
								arch/mips/kernel/sysrq.c
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,77 @@ | |||||||
|  | /*
 | ||||||
|  |  * MIPS specific sysrq operations. | ||||||
|  |  * | ||||||
|  |  * Copyright (C) 2015 Imagination Technologies Ltd. | ||||||
|  |  */ | ||||||
|  | #include <linux/init.h> | ||||||
|  | #include <linux/smp.h> | ||||||
|  | #include <linux/spinlock.h> | ||||||
|  | #include <linux/sysrq.h> | ||||||
|  | #include <linux/workqueue.h> | ||||||
|  | 
 | ||||||
|  | #include <asm/cpu-features.h> | ||||||
|  | #include <asm/mipsregs.h> | ||||||
|  | #include <asm/tlbdebug.h> | ||||||
|  | 
 | ||||||
|  | /*
 | ||||||
|  |  * Dump TLB entries on all CPUs. | ||||||
|  |  */ | ||||||
|  | 
 | ||||||
|  | static DEFINE_SPINLOCK(show_lock); | ||||||
|  | 
 | ||||||
|  | static void sysrq_tlbdump_single(void *dummy) | ||||||
|  | { | ||||||
|  | 	const int field = 2 * sizeof(unsigned long); | ||||||
|  | 	unsigned long flags; | ||||||
|  | 
 | ||||||
|  | 	spin_lock_irqsave(&show_lock, flags); | ||||||
|  | 
 | ||||||
|  | 	pr_info("CPU%d:\n", smp_processor_id()); | ||||||
|  | 	pr_info("Index	: %0x\n", read_c0_index()); | ||||||
|  | 	pr_info("Pagemask: %0x\n", read_c0_pagemask()); | ||||||
|  | 	pr_info("EntryHi : %0*lx\n", field, read_c0_entryhi()); | ||||||
|  | 	pr_info("EntryLo0: %0*lx\n", field, read_c0_entrylo0()); | ||||||
|  | 	pr_info("EntryLo1: %0*lx\n", field, read_c0_entrylo1()); | ||||||
|  | 	pr_info("Wired   : %0x\n", read_c0_wired()); | ||||||
|  | 	pr_info("Pagegrain: %0x\n", read_c0_pagegrain()); | ||||||
|  | 	if (cpu_has_htw) { | ||||||
|  | 		pr_info("PWField : %0*lx\n", field, read_c0_pwfield()); | ||||||
|  | 		pr_info("PWSize  : %0*lx\n", field, read_c0_pwsize()); | ||||||
|  | 		pr_info("PWCtl   : %0x\n", read_c0_pwctl()); | ||||||
|  | 	} | ||||||
|  | 	pr_info("\n"); | ||||||
|  | 	dump_tlb_all(); | ||||||
|  | 	pr_info("\n"); | ||||||
|  | 
 | ||||||
|  | 	spin_unlock_irqrestore(&show_lock, flags); | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | #ifdef CONFIG_SMP | ||||||
|  | static void sysrq_tlbdump_othercpus(struct work_struct *dummy) | ||||||
|  | { | ||||||
|  | 	smp_call_function(sysrq_tlbdump_single, NULL, 0); | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | static DECLARE_WORK(sysrq_tlbdump, sysrq_tlbdump_othercpus); | ||||||
|  | #endif | ||||||
|  | 
 | ||||||
|  | static void sysrq_handle_tlbdump(int key) | ||||||
|  | { | ||||||
|  | 	sysrq_tlbdump_single(NULL); | ||||||
|  | #ifdef CONFIG_SMP | ||||||
|  | 	schedule_work(&sysrq_tlbdump); | ||||||
|  | #endif | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | static struct sysrq_key_op sysrq_tlbdump_op = { | ||||||
|  | 	.handler        = sysrq_handle_tlbdump, | ||||||
|  | 	.help_msg       = "show-tlbs(x)", | ||||||
|  | 	.action_msg     = "Show TLB entries", | ||||||
|  | 	.enable_mask	= SYSRQ_ENABLE_DUMP, | ||||||
|  | }; | ||||||
|  | 
 | ||||||
|  | static int __init mips_sysrq_init(void) | ||||||
|  | { | ||||||
|  | 	return register_sysrq_key('x', &sysrq_tlbdump_op); | ||||||
|  | } | ||||||
|  | arch_initcall(mips_sysrq_init); | ||||||
| @ -463,6 +463,7 @@ static struct sysrq_key_op *sysrq_key_table[36] = { | |||||||
| 	/* v: May be registered for frame buffer console restore */ | 	/* v: May be registered for frame buffer console restore */ | ||||||
| 	NULL,				/* v */ | 	NULL,				/* v */ | ||||||
| 	&sysrq_showstate_blocked_op,	/* w */ | 	&sysrq_showstate_blocked_op,	/* w */ | ||||||
|  | 	/* x: May be registered on mips for TLB dump */ | ||||||
| 	/* x: May be registered on ppc/powerpc for xmon */ | 	/* x: May be registered on ppc/powerpc for xmon */ | ||||||
| 	/* x: May be registered on sparc64 for global PMU dump */ | 	/* x: May be registered on sparc64 for global PMU dump */ | ||||||
| 	NULL,				/* x */ | 	NULL,				/* x */ | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user