linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Andy Lutomirski <luto@kernel.org>
To: x86@kernel.org
Cc: LKML <linux-kernel@vger.kernel.org>,
	Mark Rutland <mark.rutland@arm.com>,
	Brian Gerst <brgerst@gmail.com>,
	Andy Lutomirski <luto@kernel.org>,
	Josh Poimboeuf <jpoimboe@redhat.com>
Subject: [PATCH v4 2/9] x86/kthread,dumpstack: Set task_pt_regs->cs.RPL=3 for kernel threads
Date: Wed, 17 Mar 2021 11:12:41 -0700	[thread overview]
Message-ID: <cbe4b7d77b62419749c5ab242ab0270026dc5062.1616004689.git.luto@kernel.org> (raw)
In-Reply-To: <cover.1616004689.git.luto@kernel.org>

For kernel threads, task_pt_regs is currently all zeros, a valid user state
(if kernel_execve() has been called), or some combination thereof during
execution of kernel_execve().  If a stack trace is printed, the unwinder
might get confused and treat task_pt_regs as a kernel state.  Indeed,
forcing a stack dump results in an attempt to display _kernel_ code bytes
from a bogus address at the very top of kernel memory.

Fix the confusion by setting cs=3 so that user_mode(task_pt_regs(...)) ==
true for kernel threads.

Also improve the error when failing to fetch code bytes to show which type
of fetch failed.  This makes it much easier to understand what's happening.

Cc: Josh Poimboeuf <jpoimboe@redhat.com>
Signed-off-by: Andy Lutomirski <luto@kernel.org>
---
 arch/x86/kernel/dumpstack.c |  4 ++--
 arch/x86/kernel/process.c   | 13 +++++++++++++
 2 files changed, 15 insertions(+), 2 deletions(-)

diff --git a/arch/x86/kernel/dumpstack.c b/arch/x86/kernel/dumpstack.c
index 55cf3c8325c6..9b7b69bb12e5 100644
--- a/arch/x86/kernel/dumpstack.c
+++ b/arch/x86/kernel/dumpstack.c
@@ -128,8 +128,8 @@ void show_opcodes(struct pt_regs *regs, const char *loglvl)
 		/* No access to the user space stack of other tasks. Ignore. */
 		break;
 	default:
-		printk("%sCode: Unable to access opcode bytes at RIP 0x%lx.\n",
-		       loglvl, prologue);
+		printk("%sCode: Unable to access %s opcode bytes at RIP 0x%lx.\n",
+		       loglvl, user_mode(regs) ? "user" : "kernel", prologue);
 		break;
 	}
 }
diff --git a/arch/x86/kernel/process.c b/arch/x86/kernel/process.c
index 145a7ac0c19a..f6f16df04cb9 100644
--- a/arch/x86/kernel/process.c
+++ b/arch/x86/kernel/process.c
@@ -163,6 +163,19 @@ int copy_thread(unsigned long clone_flags, unsigned long sp, unsigned long arg,
 	/* Kernel thread ? */
 	if (unlikely(p->flags & PF_KTHREAD)) {
 		memset(childregs, 0, sizeof(struct pt_regs));
+
+		/*
+		 * Even though there is no real user state here, these
+		 * are were user regs belong, and kernel_execve() will
+		 * overwrite them with user regs.  Put an obviously
+		 * invalid value that nonetheless causes user_mode(regs)
+		 * to return true in CS.
+		 *
+		 * This also prevents the unwinder from thinking that there
+		 * is invalid kernel state at the top of the stack.
+		 */
+		childregs->cs = 3;
+
 		kthread_frame_init(frame, sp, arg);
 		return 0;
 	}
-- 
2.30.2


  parent reply	other threads:[~2021-03-17 18:13 UTC|newest]

Thread overview: 18+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-03-17 18:12 [PATCH v4 0/9] kentry: A stable bugfix and a bunch of improvements Andy Lutomirski
2021-03-17 18:12 ` [PATCH v4 1/9] x86/dumpstack: Remove unnecessary range check fetching opcode bytes Andy Lutomirski
2021-03-17 18:12 ` Andy Lutomirski [this message]
2021-03-18  0:36   ` [PATCH v4 2/9] x86/kthread,dumpstack: Set task_pt_regs->cs.RPL=3 for kernel threads Josh Poimboeuf
2021-03-17 18:12 ` [PATCH v4 3/9] x86/entry: Convert ret_from_fork to C Andy Lutomirski
2021-03-18  0:38   ` Josh Poimboeuf
2021-03-19 16:05   ` Thomas Gleixner
2021-03-17 18:12 ` [PATCH v4 4/9] kentry: Simplify the common syscall API Andy Lutomirski
2021-03-19 16:09   ` Thomas Gleixner
2021-03-19 18:07   ` Thomas Gleixner
2021-03-17 18:12 ` [PATCH v4 5/9] kentry: Remove enter_from/exit_to_user_mode() Andy Lutomirski
2021-03-19 18:08   ` Thomas Gleixner
2021-03-17 18:12 ` [PATCH v4 6/9] entry: Make CONFIG_DEBUG_ENTRY available outside x86 Andy Lutomirski
2021-03-17 18:12 ` [PATCH v4 7/9] kentry: Add debugging checks for proper kentry API usage Andy Lutomirski
2021-03-19 16:17   ` Thomas Gleixner
2021-03-19 18:16     ` Thomas Gleixner
2021-03-17 18:12 ` [PATCH v4 8/9] kentry: Check that syscall entries and syscall exits match Andy Lutomirski
2021-03-17 18:12 ` [PATCH v4 9/9] kentry: Verify kentry state in instrumentation_begin/end() Andy Lutomirski

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=cbe4b7d77b62419749c5ab242ab0270026dc5062.1616004689.git.luto@kernel.org \
    --to=luto@kernel.org \
    --cc=brgerst@gmail.com \
    --cc=jpoimboe@redhat.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=mark.rutland@arm.com \
    --cc=x86@kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).