@@ -700,6 +700,57 @@ static bool is_sysenter_singlestep(struct pt_regs *regs)
700
700
#endif
701
701
}
702
702
703
+ static __always_inline void debug_enter (unsigned long * dr6 , unsigned long * dr7 )
704
+ {
705
+ /*
706
+ * Disable breakpoints during exception handling; recursive exceptions
707
+ * are exceedingly 'fun'.
708
+ *
709
+ * Since this function is NOKPROBE, and that also applies to
710
+ * HW_BREAKPOINT_X, we can't hit a breakpoint before this (XXX except a
711
+ * HW_BREAKPOINT_W on our stack)
712
+ *
713
+ * Entry text is excluded for HW_BP_X and cpu_entry_area, which
714
+ * includes the entry stack is excluded for everything.
715
+ */
716
+ get_debugreg (* dr7 , 7 );
717
+ set_debugreg (0 , 7 );
718
+
719
+ /*
720
+ * Ensure the compiler doesn't lower the above statements into
721
+ * the critical section; disabling breakpoints late would not
722
+ * be good.
723
+ */
724
+ barrier ();
725
+
726
+ /*
727
+ * The Intel SDM says:
728
+ *
729
+ * Certain debug exceptions may clear bits 0-3. The remaining
730
+ * contents of the DR6 register are never cleared by the
731
+ * processor. To avoid confusion in identifying debug
732
+ * exceptions, debug handlers should clear the register before
733
+ * returning to the interrupted task.
734
+ *
735
+ * Keep it simple: clear DR6 immediately.
736
+ */
737
+ get_debugreg (* dr6 , 6 );
738
+ set_debugreg (0 , 6 );
739
+ /* Filter out all the reserved bits which are preset to 1 */
740
+ * dr6 &= ~DR6_RESERVED ;
741
+ }
742
+
743
+ static __always_inline void debug_exit (unsigned long dr7 )
744
+ {
745
+ /*
746
+ * Ensure the compiler doesn't raise this statement into
747
+ * the critical section; enabling breakpoints early would
748
+ * not be good.
749
+ */
750
+ barrier ();
751
+ set_debugreg (dr7 , 7 );
752
+ }
753
+
703
754
/*
704
755
* Our handling of the processor debug registers is non-trivial.
705
756
* We do not clear them on entry and exit from the kernel. Therefore
@@ -727,28 +778,13 @@ static bool is_sysenter_singlestep(struct pt_regs *regs)
727
778
dotraplinkage void do_debug (struct pt_regs * regs , long error_code )
728
779
{
729
780
struct task_struct * tsk = current ;
781
+ unsigned long dr6 , dr7 ;
730
782
int user_icebp = 0 ;
731
- unsigned long dr6 ;
732
783
int si_code ;
733
784
734
- nmi_enter ();
735
-
736
- get_debugreg (dr6 , 6 );
737
- /*
738
- * The Intel SDM says:
739
- *
740
- * Certain debug exceptions may clear bits 0-3. The remaining
741
- * contents of the DR6 register are never cleared by the
742
- * processor. To avoid confusion in identifying debug
743
- * exceptions, debug handlers should clear the register before
744
- * returning to the interrupted task.
745
- *
746
- * Keep it simple: clear DR6 immediately.
747
- */
748
- set_debugreg (0 , 6 );
785
+ debug_enter (& dr6 , & dr7 );
749
786
750
- /* Filter out all the reserved bits which are preset to 1 */
751
- dr6 &= ~DR6_RESERVED ;
787
+ nmi_enter ();
752
788
753
789
/*
754
790
* The SDM says "The processor clears the BTF flag when it
@@ -786,7 +822,7 @@ dotraplinkage void do_debug(struct pt_regs *regs, long error_code)
786
822
#endif
787
823
788
824
if (notify_die (DIE_DEBUG , "debug" , regs , (long )& dr6 , error_code ,
789
- SIGTRAP ) == NOTIFY_STOP )
825
+ SIGTRAP ) == NOTIFY_STOP )
790
826
goto exit ;
791
827
792
828
/*
@@ -825,6 +861,7 @@ dotraplinkage void do_debug(struct pt_regs *regs, long error_code)
825
861
826
862
exit :
827
863
nmi_exit ();
864
+ debug_exit (dr7 );
828
865
}
829
866
NOKPROBE_SYMBOL (do_debug );
830
867
0 commit comments