aboutsummaryrefslogtreecommitdiffstats
path: root/arch/powerpc/kernel/process.c
diff options
context:
space:
mode:
authorK.Prasad <prasad@linux.vnet.ibm.com>2010-06-15 02:05:19 -0400
committerPaul Mackerras <paulus@samba.org>2010-06-22 05:40:50 -0400
commit5aae8a53708025d4e718f0d2e7c2f766779ddc71 (patch)
treed151e2c29e78248cee620cf5094a15316abd17d2 /arch/powerpc/kernel/process.c
parentf7136c5150c29846d7a1d09109449d96b2f63445 (diff)
powerpc, hw_breakpoints: Implement hw_breakpoints for 64-bit server processors
Implement perf-events based hw-breakpoint interfaces for PowerPC 64-bit server (Book III S) processors. This allows access to a given location to be used as an event that can be counted or profiled by the perf_events subsystem. This is done using the DABR (data breakpoint register), which can also be used for process debugging via ptrace. When perf_event hw_breakpoint support is configured in, the perf_event subsystem manages the DABR and arbitrates access to it, and ptrace then creates a perf_event when it is requested to set a data breakpoint. [Adopted suggestions from Paul Mackerras <paulus@samba.org> to - emulate_step() all system-wide breakpoints and single-step only the per-task breakpoints - perform arch-specific cleanup before unregistration through arch_unregister_hw_breakpoint() ] Signed-off-by: K.Prasad <prasad@linux.vnet.ibm.com> Signed-off-by: Paul Mackerras <paulus@samba.org>
Diffstat (limited to 'arch/powerpc/kernel/process.c')
-rw-r--r--arch/powerpc/kernel/process.c14
1 files changed, 14 insertions, 0 deletions
diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 9d255b4f0a0e..cbf3521d50b6 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -37,6 +37,7 @@
37#include <linux/kernel_stat.h> 37#include <linux/kernel_stat.h>
38#include <linux/personality.h> 38#include <linux/personality.h>
39#include <linux/random.h> 39#include <linux/random.h>
40#include <linux/hw_breakpoint.h>
40 41
41#include <asm/pgtable.h> 42#include <asm/pgtable.h>
42#include <asm/uaccess.h> 43#include <asm/uaccess.h>
@@ -462,8 +463,14 @@ struct task_struct *__switch_to(struct task_struct *prev,
462#ifdef CONFIG_PPC_ADV_DEBUG_REGS 463#ifdef CONFIG_PPC_ADV_DEBUG_REGS
463 switch_booke_debug_regs(&new->thread); 464 switch_booke_debug_regs(&new->thread);
464#else 465#else
466/*
467 * For PPC_BOOK3S_64, we use the hw-breakpoint interfaces that would
468 * schedule DABR
469 */
470#ifndef CONFIG_HAVE_HW_BREAKPOINT
465 if (unlikely(__get_cpu_var(current_dabr) != new->thread.dabr)) 471 if (unlikely(__get_cpu_var(current_dabr) != new->thread.dabr))
466 set_dabr(new->thread.dabr); 472 set_dabr(new->thread.dabr);
473#endif /* CONFIG_HAVE_HW_BREAKPOINT */
467#endif 474#endif
468 475
469 476
@@ -642,7 +649,11 @@ void flush_thread(void)
642{ 649{
643 discard_lazy_cpu_state(); 650 discard_lazy_cpu_state();
644 651
652#ifdef CONFIG_HAVE_HW_BREAKPOINTS
653 flush_ptrace_hw_breakpoint(current);
654#else /* CONFIG_HAVE_HW_BREAKPOINTS */
645 set_debug_reg_defaults(&current->thread); 655 set_debug_reg_defaults(&current->thread);
656#endif /* CONFIG_HAVE_HW_BREAKPOINTS */
646} 657}
647 658
648void 659void
@@ -660,6 +671,9 @@ void prepare_to_copy(struct task_struct *tsk)
660 flush_altivec_to_thread(current); 671 flush_altivec_to_thread(current);
661 flush_vsx_to_thread(current); 672 flush_vsx_to_thread(current);
662 flush_spe_to_thread(current); 673 flush_spe_to_thread(current);
674#ifdef CONFIG_HAVE_HW_BREAKPOINT
675 flush_ptrace_hw_breakpoint(tsk);
676#endif /* CONFIG_HAVE_HW_BREAKPOINT */
663} 677}
664 678
665/* 679/*