From patchwork Fri Feb 2 21:22:19 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kevin Becker X-Patchwork-Id: 1894770 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.ubuntu.com (client-ip=185.125.189.65; helo=lists.ubuntu.com; envelope-from=kernel-team-bounces@lists.ubuntu.com; receiver=patchwork.ozlabs.org) Received: from lists.ubuntu.com (lists.ubuntu.com [185.125.189.65]) (using TLSv1.2 with cipher ECDHE-ECDSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4TRTJH64wkz23gM for ; Sat, 3 Feb 2024 08:22:39 +1100 (AEDT) Received: from localhost ([127.0.0.1] helo=lists.ubuntu.com) by lists.ubuntu.com with esmtp (Exim 4.86_2) (envelope-from ) id 1rW0zY-00037o-Pu; Fri, 02 Feb 2024 21:22:33 +0000 Received: from smtp-relay-internal-1.internal ([10.131.114.114] helo=smtp-relay-internal-1.canonical.com) by lists.ubuntu.com with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.86_2) (envelope-from ) id 1rW0zR-00036s-Tq for kernel-team@lists.ubuntu.com; Fri, 02 Feb 2024 21:22:26 +0000 Received: from mail-qk1-f197.google.com (mail-qk1-f197.google.com [209.85.222.197]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by smtp-relay-internal-1.canonical.com (Postfix) with ESMTPS id 5DCD33F829 for ; Fri, 2 Feb 2024 21:22:23 +0000 (UTC) Received: by mail-qk1-f197.google.com with SMTP id af79cd13be357-7842e5e4645so344955285a.0 for ; Fri, 02 Feb 2024 13:22:23 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1706908942; x=1707513742; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=Tk34kvQIXpNLSTQLsYqVw6RcKZTnH6bKRAl2bPoX9jw=; b=cDoVP0MNfuwqpIoJ4isN2xbIQ5R5z/7KdvOv4XX9417FtgJcHG9ao0CPW+TeIvFXrQ hXPtabMgjkjQdh1wS0jo/aaiLrRuoROObYn/+URKdW0TJ3AJ+ljYuNaafZ/8Jf1uNmf9 E5huQ5jpaAI9u/4ZxBfJ6Iuv1kp8gJItWON99zVatgh6KgIYOZopji7Nmb+QaLy+a3ZH cfM2dQlmm8WnIsXbgHMXPSOQGm8MKNY+4en/2flM10vn0mQexI5kCzIPEqPhR4t/ZnDu qtl/eL+aJS1s94zeHntlZ3i4qKf94smKPxKKdhppRz4w7sRYAeoWvkceQmFdRq9E2Bs6 7Nvg== X-Gm-Message-State: AOJu0YxTFfeUPgYnx96Pb89ekK1MjnFTii4xJISWRPcNWOpIS/crzeHM dMCfP57m90GpRbYRqgBDuZlT5wbrTtPliJjKMqZxlS/H744rUgn82cF/O8jED9nWiXO6q8CJgrB Hmbpjn/Smd6kIywRiu9eB9HG9Z+dXUMM1tNijcrK38PXW8g05LFHn6jRFevAQiKOVg34ny3aRW9 N20sk+QzGTxQ== X-Received: by 2002:a05:620a:9c5:b0:785:3749:7cba with SMTP id y5-20020a05620a09c500b0078537497cbamr7589380qky.65.1706908942162; Fri, 02 Feb 2024 13:22:22 -0800 (PST) X-Google-Smtp-Source: AGHT+IEYfpZUaQcPdr57ErHf//4kzQZK60y5CRK2LLk/wRkHc/HCzBhcuX2xtBVpv/mHTthKdIDTCQ== X-Received: by 2002:a05:620a:9c5:b0:785:3749:7cba with SMTP id y5-20020a05620a09c500b0078537497cbamr7589365qky.65.1706908941712; Fri, 02 Feb 2024 13:22:21 -0800 (PST) Received: from kevinbecker.lan ([72.75.204.92]) by smtp.gmail.com with ESMTPSA id f26-20020a05620a12fa00b0078550013a3esm981076qkl.41.2024.02.02.13.22.21 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 02 Feb 2024 13:22:21 -0800 (PST) From: Kevin Becker To: kernel-team@lists.ubuntu.com Subject: [SRU][jammy:linux-aws][PATCH 1/1] arm64: pauth: don't sign leaf functions Date: Fri, 2 Feb 2024 16:22:19 -0500 Message-Id: <20240202212219.200147-2-kevin.becker@canonical.com> X-Mailer: git-send-email 2.40.1 In-Reply-To: <20240202212219.200147-1-kevin.becker@canonical.com> References: <20240202212219.200147-1-kevin.becker@canonical.com> MIME-Version: 1.0 X-BeenThere: kernel-team@lists.ubuntu.com X-Mailman-Version: 2.1.20 Precedence: list List-Id: Kernel team discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: kernel-team-bounces@lists.ubuntu.com Sender: "kernel-team" BugLink: https://bugs.launchpad.net/bugs/2043811 Currently, when CONFIG_ARM64_PTR_AUTH_KERNEL=y (and CONFIG_UNWIND_PATCH_PAC_INTO_SCS=n), we enable pointer authentication for all functions, including leaf functions. This isn't necessary, and is unfortunate for a few reasons: * Any PACIASP instruction is implicitly a `BTI C` landing pad, and forcing the addition of a PACIASP in every function introduces a larger set of BTI gadgets than is necessary. * The PACIASP and AUTIASP instructions make leaf functions larger than necessary, bloating the kernel Image. For a defconfig v6.2-rc3 kernel, this appears to add ~64KiB relative to not signing leaf functions, which is unfortunate but not entirely onerous. * The PACIASP and AUTIASP instructions potentially make leaf functions more expensive in terms of performance and/or power. For many trivial leaf functions, this is clearly unnecessary, e.g. | : | d503233f paciasp | d53b4220 mrs x0, daif | d50323bf autiasp | d65f03c0 ret | : | d503233f paciasp | d50323bf autiasp | d65f03c0 ret | d503201f nop * When CONFIG_UNWIND_PATCH_PAC_INTO_SCS=y we disable pointer authentication for leaf functions, so clearly this is not functionally necessary, indicates we have an inconsistent threat model, and convolutes the Makefile logic. We've used pointer authentication in leaf functions since the introduction of in-kernel pointer authentication in commit: 74afda4 ("arm64: compile the kernel with ptrauth return address signing") ... but at the time we had no rationale for signing leaf functions. Subsequently, we considered avoiding signing leaf functions: https://lore.kernel.org/linux-arm-kernel/1586856741-26839-1-git-send-email-amit.kachhap@arm.com/ https://lore.kernel.org/linux-arm-kernel/1588149371-20310-1-git-send-email-amit.kachhap@arm.com/ ... however at the time we didn't have an abundance of reasons to avoid signing leaf functions as above (e.g. the BTI case), we had no hardware to make performance measurements, and it was reasoned that this gave some level of protection against a limited set of code-reuse gadgets which would fall through to a RET. We documented this in commit: 717b938 ("arm64: Document why we enable PAC support for leaf functions") Notably, this was before we supported any forward-edge CFI scheme (e.g. Arm BTI, or Clang CFI/kCFI), which would prevent jumping into the middle of a function. In addition, even with signing forced for leaf functions, AUTIASP may be placed before a number of instructions which might constitute such a gadget, e.g. | : | f9400022 ldr x2, [x1] | d503233f paciasp | d50323bf autiasp | f9408401 ldr x1, [x0, #264] | 720b005f tst w2, #0x200000 | b26b0022 orr x2, x1, #0x200000 | 926af821 and x1, x1, #0xffffffffffdfffff | 9a820021 csel x1, x1, x2, eq // eq = none | f9008401 str x1, [x0, #264] | d65f03c0 ret | : | 2a0003e3 mov w3, w0 | 9000ff42 adrp x2, ffff800009ffd000 | 9120e042 add x2, x2, #0x838 | 52800000 mov w0, #0x0 // #0 | d503233f paciasp | f000d041 adrp x1, ffff800009a20000 | d50323bf autiasp | 9102c021 add x1, x1, #0xb0 | f8635842 ldr x2, [x2, w3, uxtw #3] | f821685f str xzr, [x2, x1] | d65f03c0 ret | d503201f nop So generally, trying to use AUTIASP to detect such gadgetization is not robust, and this is dealt with far better by forward-edge CFI (which is designed to prevent such cases). We should bite the bullet and stop pretending that AUTIASP is a mitigation for such forward-edge gadgetization. For the above reasons, this patch has the kernel consistently sign non-leaf functions and avoid signing leaf functions. Considering a defconfig v6.2-rc3 kernel built with LLVM 15.0.6: * The vmlinux is ~43KiB smaller: | [mark@lakrids:~/src/linux]% ls -al vmlinux-* | -rwxr-xr-x 1 mark mark 338547808 Jan 25 17:17 vmlinux-after | -rwxr-xr-x 1 mark mark 338591472 Jan 25 17:22 vmlinux-before * The resulting Image is 64KiB smaller: | [mark@lakrids:~/src/linux]% ls -al Image-* | -rwxr-xr-x 1 mark mark 32702976 Jan 25 17:17 Image-after | -rwxr-xr-x 1 mark mark 32768512 Jan 25 17:22 Image-before * There are ~400 fewer BTI gadgets: | [mark@lakrids:~/src/linux]% usekorg 12.1.0 aarch64-linux-objdump -d vmlinux-before 2> /dev/null | grep -ow 'paciasp\|bti\sc\?' | sort | uniq -c | 1219 bti c | 61982 paciasp | [mark@lakrids:~/src/linux]% usekorg 12.1.0 aarch64-linux-objdump -d vmlinux-after 2> /dev/null | grep -ow 'paciasp\|bti\sc\?' | sort | uniq -c | 10099 bti c | 52699 paciasp Which is +8880 BTIs, and -9283 PACIASPs, for -403 unnecessary BTI gadgets. While this is small relative to the total, distinguishing the two cases will make it easier to analyse and reduce this set further in future. Signed-off-by: Mark Rutland Reviewed-by: Ard Biesheuvel Reviewed-by: Mark Brown Cc: Amit Daniel Kachhap Cc: Will Deacon Link: https://lore.kernel.org/r/20230131105809.991288-3-mark.rutland@arm.com Signed-off-by: Catalin Marinas (backported from mainline commit c68cf5285e1896a2b725ec01a1351f08610165b8) [kevinbecker: context conflict - some lines were added after relevant code so patch didn't match exactly. Added exact changes from mainline commit to current Makefile.] BugLink: https://bugs.launchpad.net/ubuntu/lunar/+source/linux-aws/+bug/2043811 Signed-off-by: Kevin Becker --- arch/arm64/Makefile | 22 ++++++++-------------- 1 file changed, 8 insertions(+), 14 deletions(-) diff --git a/arch/arm64/Makefile b/arch/arm64/Makefile index c744b1e7b356..213636a422da 100644 --- a/arch/arm64/Makefile +++ b/arch/arm64/Makefile @@ -58,19 +58,16 @@ stack_protector_prepare: prepare0 include/generated/asm-offsets.h)) endif -# Ensure that if the compiler supports branch protection we default it -# off, this will be overridden if we are using branch protection. -branch-prot-flags-y += $(call cc-option,-mbranch-protection=none) - -ifeq ($(CONFIG_ARM64_PTR_AUTH_KERNEL),y) -branch-prot-flags-$(CONFIG_CC_HAS_SIGN_RETURN_ADDRESS) := -msign-return-address=all -# We enable additional protection for leaf functions as there is some -# narrow potential for ROP protection benefits and no substantial -# performance impact has been observed. ifeq ($(CONFIG_ARM64_BTI_KERNEL),y) -branch-prot-flags-$(CONFIG_CC_HAS_BRANCH_PROT_PAC_RET_BTI) := -mbranch-protection=pac-ret+leaf+bti + KBUILD_CFLAGS += -mbranch-protection=pac-ret+bti +else ifeq ($(CONFIG_ARM64_PTR_AUTH_KERNEL),y) + ifeq ($(CONFIG_CC_HAS_BRANCH_PROT_PAC_RET),y) + KBUILD_CFLAGS += -mbranch-protection=pac-ret + else + KBUILD_CFLAGS += -msign-return-address=non-leaf + endif else -branch-prot-flags-$(CONFIG_CC_HAS_BRANCH_PROT_PAC_RET) := -mbranch-protection=pac-ret+leaf + KBUILD_CFLAGS += $(call cc-option,-mbranch-protection=none) endif # -march=armv8.3-a enables the non-nops instructions for PAC, to avoid the # compiler to generate them and consequently to break the single image contract @@ -79,9 +76,6 @@ endif ifeq ($(CONFIG_AS_HAS_PAC), y) asm-arch := armv8.3-a endif -endif - -KBUILD_CFLAGS += $(branch-prot-flags-y) ifeq ($(CONFIG_AS_HAS_ARMV8_4), y) # make sure to pass the newest target architecture to -march.