From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-17.4 required=3.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER, INCLUDES_PATCH,MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,URIBL_BLOCKED, USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 6C3BFC43461 for ; Mon, 3 May 2021 17:38:26 +0000 (UTC) Received: from desiato.infradead.org (desiato.infradead.org [90.155.92.199]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id D53C7610A6 for ; Mon, 3 May 2021 17:38:25 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.3.2 mail.kernel.org D53C7610A6 Authentication-Results: mail.kernel.org; dmarc=fail (p=none dis=none) header.from=linux.microsoft.com Authentication-Results: mail.kernel.org; spf=none smtp.mailfrom=linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=desiato.20200630; h=Sender:Content-Transfer-Encoding :Content-Type:List-Subscribe:List-Help:List-Post:List-Archive: List-Unsubscribe:List-Id:MIME-Version:References:In-Reply-To:Message-Id:Date: Subject:To:From:Reply-To:Cc:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=XgbO8f/ZZk6DQoIov9czYV8Ix2m4DDFrACq04bvkJ6o=; b=EwVafWKG+ZOWPZXhXx1yydYXu 2hiyN4BXoBsMPcygesJusWXKnlodls4uuhFd6exzI9+LKsHzPl031GOKth0doZsMFniAm++VvFe2B +Pace1jQTtpBVhatBNU3DIBWnBf86pqaj5lwwqs5O7N0hir2J6D420IbAfIvC3YtebJ5FpeTKGGHX 0Zx8wOqW4JNlQfXDLnOK4vENffsFxbWmRIl+3Ssfh9XIqZjn1VRywTMfl7F94KZeATpgntMgUGjU6 GYYGBz5hU4Cwh8IG+l3zVY/eeKVVA4HbvthxutDbpOEYzUYsNchJ43tqsjwZAFqI+uVswtNLiX0TL vs3NPG3PQ==; Received: from localhost ([::1] helo=desiato.infradead.org) by desiato.infradead.org with esmtp (Exim 4.94 #2 (Red Hat Linux)) id 1ldcV8-00EWUe-Vz; Mon, 03 May 2021 17:36:59 +0000 Received: from bombadil.infradead.org ([2607:7c80:54:e::133]) by desiato.infradead.org with esmtps (Exim 4.94 #2 (Red Hat Linux)) id 1ldcUh-00EWS0-2b for linux-arm-kernel@desiato.infradead.org; Mon, 03 May 2021 17:36:31 +0000 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=infradead.org; s=bombadil.20210309; h=Content-Transfer-Encoding: MIME-Version:References:In-Reply-To:Message-Id:Date:Subject:To:From:Sender: Reply-To:Cc:Content-Type:Content-ID:Content-Description; bh=EYht7bnnZALqCAngJGQY0oHKDEKVB3mk09HnhdDDWvk=; b=2AhHoQj6UIO/tTtJy0UiLK3H1U 0acbr6lvspYf2VmudI3Ve2b3TpOEWS/OP96CWVJZHOATlpX0hIs0nOmxh/namrTsAHDudPjkejHKI 6kLkBKvvPI/FFpjHia7oE1weH8a7Y1qItjyLIk+u+blw/q2/RP97gTIh7ThdqrlGEdyBRngjPGkc7 NNt/DaAg/dJhwRJVIw7XN3/oTHaRWCobnFh5X5oLc6WvaoVc9MR5j1bccUgLavXQtk/yX1Hen+u5G 4a6Sgbe9oRCuyYAqhFND6VsSk+9DR7sHxmQkFkdnvdLWZxIkZBlnfJje+VBmhC06GZq1znq85udIY Dwt71iSA==; Received: from linux.microsoft.com ([13.77.154.182]) by bombadil.infradead.org with esmtp (Exim 4.94 #2 (Red Hat Linux)) id 1ldcUd-003MIY-2s for linux-arm-kernel@lists.infradead.org; Mon, 03 May 2021 17:36:29 +0000 Received: from x64host.home (unknown [47.187.223.33]) by linux.microsoft.com (Postfix) with ESMTPSA id 02C9920B8008; Mon, 3 May 2021 10:36:24 -0700 (PDT) DKIM-Filter: OpenDKIM Filter v2.11.0 linux.microsoft.com 02C9920B8008 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linux.microsoft.com; s=default; t=1620063385; bh=EYht7bnnZALqCAngJGQY0oHKDEKVB3mk09HnhdDDWvk=; h=From:To:Subject:Date:In-Reply-To:References:From; b=k223RR53gCBeR0IYEEx2yTde/21IkoXVl7restM7bssa2WtPe/+q/LDATZTRexhGT apAZ38tojvUlpG1qXWDwE0WPk3Tt8Ylk2028pLx/ruhcc1CeTEQ7DeXnPcHE9dbg5k GYdcoU6v5P/kCeNomEshBtzuJRFn0RU3ONJILvsU= From: madvenka@linux.microsoft.com To: broonie@kernel.org, jpoimboe@redhat.com, mark.rutland@arm.com, jthierry@redhat.com, catalin.marinas@arm.com, will@kernel.org, jmorris@namei.org, pasha.tatashin@soleen.com, linux-arm-kernel@lists.infradead.org, live-patching@vger.kernel.org, linux-kernel@vger.kernel.org, madvenka@linux.microsoft.com Subject: [RFC PATCH v3 2/4] arm64: Check the return PC against unreliable code sections Date: Mon, 3 May 2021 12:36:13 -0500 Message-Id: <20210503173615.21576-3-madvenka@linux.microsoft.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20210503173615.21576-1-madvenka@linux.microsoft.com> References: <65cf4dfbc439b010b50a0c46ec500432acde86d6> <20210503173615.21576-1-madvenka@linux.microsoft.com> MIME-Version: 1.0 X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20210503_103627_224700_1C021C42 X-CRM114-Status: GOOD ( 19.07 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org From: "Madhavan T. Venkataraman" Create a sym_code_ranges[] array to cover the following text sections that contain functions defined as SYM_CODE_*(). These functions are low-level functions (and do not have a proper frame pointer prolog and epilog). So, they are inherently unreliable from a stack unwinding perspective. .entry.text .idmap.text .hyp.idmap.text .hyp.text .hibernate_exit.text .entry.tramp.text If a return PC falls in any of these, mark the stack trace unreliable. The only exception to this is - if the unwinder has reached the last frame already, it will not mark the stack trace unreliable since there is no more unwinding to do. E.g., - ret_from_fork() occurs at the end of the stack trace of kernel tasks. - el0_*() functions occur at the end of EL0 exception stack traces. This covers all user task entries into the kernel. NOTE: - EL1 exception handlers are in .entry.text. So, stack traces that contain those functions will be marked not reliable. This covers interrupts, exceptions and breakpoints encountered while executing in the kernel. - At the end of an interrupt, the kernel can preempt the current task if required. So, the stack traces of all preempted tasks will show the interrupt frame and will be considered unreliable. Signed-off-by: Madhavan T. Venkataraman --- arch/arm64/kernel/stacktrace.c | 54 ++++++++++++++++++++++++++++++++++ 1 file changed, 54 insertions(+) diff --git a/arch/arm64/kernel/stacktrace.c b/arch/arm64/kernel/stacktrace.c index c21a1bca28f3..1ff14615a55a 100644 --- a/arch/arm64/kernel/stacktrace.c +++ b/arch/arm64/kernel/stacktrace.c @@ -15,9 +15,48 @@ #include #include +#include #include #include +struct code_range { + unsigned long start; + unsigned long end; +}; + +struct code_range sym_code_ranges[] = +{ + /* non-unwindable ranges */ + { (unsigned long)__entry_text_start, + (unsigned long)__entry_text_end }, + { (unsigned long)__idmap_text_start, + (unsigned long)__idmap_text_end }, + { (unsigned long)__hyp_idmap_text_start, + (unsigned long)__hyp_idmap_text_end }, + { (unsigned long)__hyp_text_start, + (unsigned long)__hyp_text_end }, +#ifdef CONFIG_HIBERNATION + { (unsigned long)__hibernate_exit_text_start, + (unsigned long)__hibernate_exit_text_end }, +#endif +#ifdef CONFIG_UNMAP_KERNEL_AT_EL0 + { (unsigned long)__entry_tramp_text_start, + (unsigned long)__entry_tramp_text_end }, +#endif + { /* sentinel */ } +}; + +static struct code_range *lookup_range(unsigned long pc) +{ + struct code_range *range; + + for (range = sym_code_ranges; range->start; range++) { + if (pc >= range->start && pc < range->end) + return range; + } + return range; +} + /* * AArch64 PCS assigns the frame pointer to x29. * @@ -43,6 +82,7 @@ int notrace unwind_frame(struct task_struct *tsk, struct stackframe *frame) { unsigned long fp = frame->fp; struct stack_info info; + struct code_range *range; frame->reliable = true; @@ -103,6 +143,8 @@ int notrace unwind_frame(struct task_struct *tsk, struct stackframe *frame) return 0; } + range = lookup_range(frame->pc); + #ifdef CONFIG_FUNCTION_GRAPH_TRACER if (tsk->ret_stack && frame->pc == (unsigned long)return_to_handler) { @@ -118,9 +160,21 @@ int notrace unwind_frame(struct task_struct *tsk, struct stackframe *frame) return -EINVAL; frame->pc = ret_stack->ret; frame->pc = ptrauth_strip_insn_pac(frame->pc); + return 0; } #endif /* CONFIG_FUNCTION_GRAPH_TRACER */ + if (!range->start) + return 0; + + /* + * The return PC falls in an unreliable function. If the final frame + * has been reached, no more unwinding is needed. Otherwise, mark the + * stack trace not reliable. + */ + if (frame->fp) + frame->reliable = false; + return 0; } NOKPROBE_SYMBOL(unwind_frame); -- 2.25.1 _______________________________________________ linux-arm-kernel mailing list linux-arm-kernel@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-arm-kernel