Skip to contentSkip to conversation

Patch "kprobes/x86: Clear TF bit in fault on single-stepping" has been added to the 4.4-stable tree

PATCH [email protected] 1 participant 1 message Jul 11, 2016

Subsystems (2)
lore
Share & tools
lore

[email protected]

author maintainer Applied
#0 lore raw

This is a note to let you know that I've just added the patch titled

kprobes/x86: Clear TF bit in fault on single-stepping

to the 4.4-stable tree which can be found at:
http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary

The filename of the patch is:
kprobes-x86-clear-tf-bit-in-fault-on-single-stepping.patch
and it can be found in the queue-4.4 subdirectory.

If you, or anyone else, feels it should not be added to the stable tree, please let <[email protected]> know about it.

Quoted 1 line

From dcfc47248d3f7d28df6f531e6426b933de94370d Mon Sep 17 00:00:00 2001

From: Masami Hiramatsu <[email protected]>
Date: Sat, 11 Jun 2016 23:06:53 +0900
Subject: kprobes/x86: Clear TF bit in fault on single-stepping

From: Masami Hiramatsu <[email protected]>

commit dcfc47248d3f7d28df6f531e6426b933de94370d upstream.

Fix kprobe_fault_handler() to clear the TF (trap flag) bit of the flags register in the case of a fault fixup on single-stepping.

If we put a kprobe on the instruction which caused a page fault (e.g. actual mov instructions in copy_user_*), that fault happens on the single-stepping buffer. In this case, kprobes resets running instance so that the CPU can retry execution on the original ip address.

However, current code forgets to reset the TF bit. Since this fault happens with TF bit set for enabling single-stepping, when it retries, it causes a debug exception and kprobes can not handle it because it already reset itself.

On the most of x86-64 platform, it can be easily reproduced by using kprobe tracer. E.g.

  # cd /sys/kernel/debug/tracing
  # echo p copy_user_enhanced_fast_string+5 > kprobe_events
  # echo 1 > events/kprobes/enable

And you'll see a kernel panic on do_debug(), since the debug trap is not handled by kprobes.

To fix this problem, we just need to clear the TF bit when resetting running kprobe.

Cc Alexander Shishkin <[email protected]>
Cc Andy Lutomirski <[email protected]>
Cc Arnaldo Carvalho de Melo <[email protected]>
Cc Borislav Petkov <[email protected]>
Cc Brian Gerst <[email protected]>
Cc Denys Vlasenko <[email protected]>
Cc H. Peter Anvin <[email protected]>
Cc Jiri Olsa <[email protected]>
Cc Linus Torvalds <[email protected]>
Cc Peter Zijlstra <[email protected]>
Cc Stephane Eranian <[email protected]>
Cc Thomas Gleixner <[email protected]>
Cc Vince Weaver <[email protected]>
[ Updated the comments. ]
---
 arch/x86/kernel/kprobes/core.c |   12 ++++++++++++
 1 file changed, 12 insertions(+)
arch/x86/kernel/kprobes/core.c +12 -0
@@ -959,7 +959,19 @@ int kprobe_fault_handler(struct pt_regs
 		 * normal page fault.
 		 */
 		regs->ip = (unsigned long)cur->addr;
+		/*
+		 * Trap flag (TF) has been set here because this fault
+		 * happened where the single stepping will be done.
+		 * So clear it by resetting the current kprobe:
+		 */
+		regs->flags &= ~X86_EFLAGS_TF;
+
+		/*
+		 * If the TF flag was set before the kprobe hit,
+		 * don't touch it:
+		 */
 		regs->flags |= kcb->kprobe_old_flags;
+
 		if (kcb->kprobe_status == KPROBE_REENTER)
 			restore_previous_kprobe(kcb);
 		else

Patches currently in stable-queue which might be from [email protected] are

queue-4.4/kprobes-x86-clear-tf-bit-in-fault-on-single-stepping.patch