Modify process handling code to recognise hardware debug registers during copy
and flush operations. Introduce a new TIF_DEBUG task flag to indicate a
process's use of debug register. Load the debug register values into a
new CPU during initialisation.

Signed-off-by: K.Prasad <pra...@linux.vnet.ibm.com>
---
 arch/powerpc/kernel/process.c |   15 +++++++++++++++
 arch/powerpc/kernel/smp.c     |    2 ++
 2 files changed, 17 insertions(+)

Index: linux-2.6-tip.hbkpt/arch/powerpc/kernel/process.c
===================================================================
--- linux-2.6-tip.hbkpt.orig/arch/powerpc/kernel/process.c
+++ linux-2.6-tip.hbkpt/arch/powerpc/kernel/process.c
@@ -50,6 +50,7 @@
 #include <asm/syscalls.h>
 #ifdef CONFIG_PPC64
 #include <asm/firmware.h>
+#include <asm/hw_breakpoint.h>
 #endif
 #include <linux/kprobes.h>
 #include <linux/kdebug.h>
@@ -254,8 +255,10 @@ void do_dabr(struct pt_regs *regs, unsig
                        11, SIGSEGV) == NOTIFY_STOP)
                return;
 
+#ifndef CONFIG_PPC64
        if (debugger_dabr_match(regs))
                return;
+#endif
 
        /* Clear the DAC and struct entries.  One shot trigger */
 #if defined(CONFIG_BOOKE)
@@ -372,8 +375,13 @@ struct task_struct *__switch_to(struct t
 
 #endif /* CONFIG_SMP */
 
+#ifdef CONFIG_PPC64
+               if (unlikely(test_tsk_thread_flag(new, TIF_DEBUG)))
+                       arch_install_thread_hw_breakpoint(new);
+#else
        if (unlikely(__get_cpu_var(current_dabr) != new->thread.dabr))
                set_dabr(new->thread.dabr);
+#endif /* CONFIG_PPC64 */
 
 #if defined(CONFIG_BOOKE)
        /* If new thread DAC (HW breakpoint) is the same then leave it */
@@ -550,6 +558,10 @@ void show_regs(struct pt_regs * regs)
 void exit_thread(void)
 {
        discard_lazy_cpu_state();
+#ifdef CONFIG_PPC64
+       if (unlikely(test_tsk_thread_flag(current, TIF_DEBUG)))
+               flush_thread_hw_breakpoint(current);
+#endif /* CONFIG_PPC64 */
 }
 
 void flush_thread(void)
@@ -672,6 +684,9 @@ int copy_thread(unsigned long clone_flag
         * function.
         */
        kregs->nip = *((unsigned long *)ret_from_fork);
+
+       if (unlikely(test_tsk_thread_flag(current, TIF_DEBUG)))
+               copy_thread_hw_breakpoint(current, p, clone_flags);
 #else
        kregs->nip = (unsigned long)ret_from_fork;
 #endif
Index: linux-2.6-tip.hbkpt/arch/powerpc/kernel/smp.c
===================================================================
--- linux-2.6-tip.hbkpt.orig/arch/powerpc/kernel/smp.c
+++ linux-2.6-tip.hbkpt/arch/powerpc/kernel/smp.c
@@ -48,6 +48,7 @@
 #include <asm/vdso_datapage.h>
 #ifdef CONFIG_PPC64
 #include <asm/paca.h>
+#include <asm/hw_breakpoint.h>
 #endif
 
 #ifdef DEBUG
@@ -537,6 +538,7 @@ int __devinit start_secondary(void *unus
 
        local_irq_enable();
 
+       load_debug_registers();
        cpu_idle();
        return 0;
 }

_______________________________________________
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev

Reply via email to