From: Greg Kroah-Hartman Date: Mon, 28 Oct 2024 01:39:21 +0000 (+0100) Subject: 6.11-stable patches X-Git-Tag: v5.15.170~14 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=ab123061eaee344a32978e027b72897a56b99d4f;p=thirdparty%2Fkernel%2Fstable-queue.git 6.11-stable patches added patches: platform-x86-dell-wmi-ignore-suspend-notifications.patch x86-fix-user-address-masking-non-canonical-speculation-issue.patch x86-fix-whitespace-in-runtime-const-assembler-output.patch x86-support-user-address-masking-instead-of-non-speculative-conditional.patch --- diff --git a/queue-6.11/platform-x86-dell-wmi-ignore-suspend-notifications.patch b/queue-6.11/platform-x86-dell-wmi-ignore-suspend-notifications.patch new file mode 100644 index 00000000000..a6675ca7bd5 --- /dev/null +++ b/queue-6.11/platform-x86-dell-wmi-ignore-suspend-notifications.patch @@ -0,0 +1,44 @@ +From a7990957fa53326fe9b47f0349373ed99bb69aaa Mon Sep 17 00:00:00 2001 +From: Armin Wolf +Date: Tue, 15 Oct 2024 00:05:29 +0200 +Subject: platform/x86: dell-wmi: Ignore suspend notifications +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Armin Wolf + +commit a7990957fa53326fe9b47f0349373ed99bb69aaa upstream. + +Some machines like the Dell G15 5155 emit WMI events when +suspending/resuming. Ignore those WMI events. + +Tested-by: siddharth.manthan@gmail.com +Signed-off-by: Armin Wolf +Acked-by: Pali Rohár +Link: https://lore.kernel.org/r/20241014220529.397390-1-W_Armin@gmx.de +Reviewed-by: Hans de Goede +Signed-off-by: Hans de Goede +Signed-off-by: Greg Kroah-Hartman +--- + drivers/platform/x86/dell/dell-wmi-base.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +--- a/drivers/platform/x86/dell/dell-wmi-base.c ++++ b/drivers/platform/x86/dell/dell-wmi-base.c +@@ -264,6 +264,15 @@ static const struct key_entry dell_wmi_k + /*Speaker Mute*/ + { KE_KEY, 0x109, { KEY_MUTE} }, + ++ /* S2Idle screen off */ ++ { KE_IGNORE, 0x120, { KEY_RESERVED }}, ++ ++ /* Leaving S4 or S2Idle suspend */ ++ { KE_IGNORE, 0x130, { KEY_RESERVED }}, ++ ++ /* Entering S2Idle suspend */ ++ { KE_IGNORE, 0x140, { KEY_RESERVED }}, ++ + /* Mic mute */ + { KE_KEY, 0x150, { KEY_MICMUTE } }, + diff --git a/queue-6.11/series b/queue-6.11/series index 6d47cd3e415..1df88ddf4f4 100644 --- a/queue-6.11/series +++ b/queue-6.11/series @@ -251,3 +251,7 @@ revert-fs-9p-remove-redundant-pointer-v9ses.patch revert-fs-9p-fix-uaf-in-in-v9fs_stat2inode_dotl.patch revert-fs-9p-simplify-iget-to-remove-unnecessary-paths.patch soundwire-intel_ace2x-send-pdi-stream-number-during-prepare.patch +x86-support-user-address-masking-instead-of-non-speculative-conditional.patch +x86-fix-whitespace-in-runtime-const-assembler-output.patch +x86-fix-user-address-masking-non-canonical-speculation-issue.patch +platform-x86-dell-wmi-ignore-suspend-notifications.patch diff --git a/queue-6.11/x86-fix-user-address-masking-non-canonical-speculation-issue.patch b/queue-6.11/x86-fix-user-address-masking-non-canonical-speculation-issue.patch new file mode 100644 index 00000000000..4680401bbec --- /dev/null +++ b/queue-6.11/x86-fix-user-address-masking-non-canonical-speculation-issue.patch @@ -0,0 +1,186 @@ +From 86e6b1547b3d013bc392adf775b89318441403c2 Mon Sep 17 00:00:00 2001 +From: Linus Torvalds +Date: Wed, 23 Oct 2024 18:17:46 -0700 +Subject: x86: fix user address masking non-canonical speculation issue +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Linus Torvalds + +commit 86e6b1547b3d013bc392adf775b89318441403c2 upstream. + +It turns out that AMD has a "Meltdown Lite(tm)" issue with non-canonical +accesses in kernel space. And so using just the high bit to decide +whether an access is in user space or kernel space ends up with the good +old "leak speculative data" if you have the right gadget using the +result: + + CVE-2020-12965 “Transient Execution of Non-Canonical Accesses“ + +Now, the kernel surrounds the access with a STAC/CLAC pair, and those +instructions end up serializing execution on older Zen architectures, +which closes the speculation window. + +But that was true only up until Zen 5, which renames the AC bit [1]. +That improves performance of STAC/CLAC a lot, but also means that the +speculation window is now open. + +Note that this affects not just the new address masking, but also the +regular valid_user_address() check used by access_ok(), and the asm +version of the sign bit check in the get_user() helpers. + +It does not affect put_user() or clear_user() variants, since there's no +speculative result to be used in a gadget for those operations. + +Reported-by: Andrew Cooper +Link: https://lore.kernel.org/all/80d94591-1297-4afb-b510-c665efd37f10@citrix.com/ +Link: https://lore.kernel.org/all/20241023094448.GAZxjFkEOOF_DM83TQ@fat_crate.local/ [1] +Link: https://www.amd.com/en/resources/product-security/bulletin/amd-sb-1010.html +Link: https://arxiv.org/pdf/2108.10771 +Cc: Josh Poimboeuf +Cc: Borislav Petkov +Tested-by: Maciej Wieczor-Retman # LAM case +Fixes: 2865baf54077 ("x86: support user address masking instead of non-speculative conditional") +Fixes: 6014bc27561f ("x86-64: make access_ok() independent of LAM") +Fixes: b19b74bc99b1 ("x86/mm: Rework address range check in get_user() and put_user()") +Signed-off-by: Linus Torvalds +Signed-off-by: Greg Kroah-Hartman +--- + arch/x86/include/asm/uaccess_64.h | 43 +++++++++++++++++++++----------------- + arch/x86/kernel/cpu/common.c | 10 ++++++++ + arch/x86/kernel/vmlinux.lds.S | 1 + arch/x86/lib/getuser.S | 9 ++++++- + 4 files changed, 42 insertions(+), 21 deletions(-) + +--- a/arch/x86/include/asm/uaccess_64.h ++++ b/arch/x86/include/asm/uaccess_64.h +@@ -12,6 +12,13 @@ + #include + #include + #include ++#include ++ ++/* ++ * Virtual variable: there's no actual backing store for this, ++ * it can purely be used as 'runtime_const_ptr(USER_PTR_MAX)' ++ */ ++extern unsigned long USER_PTR_MAX; + + #ifdef CONFIG_ADDRESS_MASKING + /* +@@ -46,19 +53,24 @@ static inline unsigned long __untagged_a + + #endif + +-/* +- * The virtual address space space is logically divided into a kernel +- * half and a user half. When cast to a signed type, user pointers +- * are positive and kernel pointers are negative. +- */ +-#define valid_user_address(x) ((__force long)(x) >= 0) ++#define valid_user_address(x) \ ++ ((__force unsigned long)(x) <= runtime_const_ptr(USER_PTR_MAX)) + + /* + * Masking the user address is an alternative to a conditional + * user_access_begin that can avoid the fencing. This only works + * for dense accesses starting at the address. + */ +-#define mask_user_address(x) ((typeof(x))((long)(x)|((long)(x)>>63))) ++static inline void __user *mask_user_address(const void __user *ptr) ++{ ++ unsigned long mask; ++ asm("cmp %1,%0\n\t" ++ "sbb %0,%0" ++ :"=r" (mask) ++ :"r" (ptr), ++ "0" (runtime_const_ptr(USER_PTR_MAX))); ++ return (__force void __user *)(mask | (__force unsigned long)ptr); ++} + #define masked_user_access_begin(x) ({ __uaccess_begin(); mask_user_address(x); }) + + /* +@@ -66,23 +78,16 @@ static inline unsigned long __untagged_a + * arbitrary values in those bits rather then masking them off. + * + * Enforce two rules: +- * 1. 'ptr' must be in the user half of the address space ++ * 1. 'ptr' must be in the user part of the address space + * 2. 'ptr+size' must not overflow into kernel addresses + * +- * Note that addresses around the sign change are not valid addresses, +- * and will GP-fault even with LAM enabled if the sign bit is set (see +- * "CR3.LAM_SUP" that can narrow the canonicality check if we ever +- * enable it, but not remove it entirely). +- * +- * So the "overflow into kernel addresses" does not imply some sudden +- * exact boundary at the sign bit, and we can allow a lot of slop on the +- * size check. ++ * Note that we always have at least one guard page between the ++ * max user address and the non-canonical gap, allowing us to ++ * ignore small sizes entirely. + * + * In fact, we could probably remove the size check entirely, since + * any kernel accesses will be in increasing address order starting +- * at 'ptr', and even if the end might be in kernel space, we'll +- * hit the GP faults for non-canonical accesses before we ever get +- * there. ++ * at 'ptr'. + * + * That's a separate optimization, for now just handle the small + * constant case. +--- a/arch/x86/kernel/cpu/common.c ++++ b/arch/x86/kernel/cpu/common.c +@@ -69,6 +69,7 @@ + #include + #include + #include ++#include + + #include "cpu.h" + +@@ -2371,6 +2372,15 @@ void __init arch_cpu_finalize_init(void) + alternative_instructions(); + + if (IS_ENABLED(CONFIG_X86_64)) { ++ unsigned long USER_PTR_MAX = TASK_SIZE_MAX-1; ++ ++ /* ++ * Enable this when LAM is gated on LASS support ++ if (cpu_feature_enabled(X86_FEATURE_LAM)) ++ USER_PTR_MAX = (1ul << 63) - PAGE_SIZE - 1; ++ */ ++ runtime_const_init(ptr, USER_PTR_MAX); ++ + /* + * Make sure the first 2MB area is not mapped by huge pages + * There are typically fixed size MTRRs in there and overlapping +--- a/arch/x86/kernel/vmlinux.lds.S ++++ b/arch/x86/kernel/vmlinux.lds.S +@@ -359,6 +359,7 @@ SECTIONS + + RUNTIME_CONST(shift, d_hash_shift) + RUNTIME_CONST(ptr, dentry_hashtable) ++ RUNTIME_CONST(ptr, USER_PTR_MAX) + + . = ALIGN(PAGE_SIZE); + +--- a/arch/x86/lib/getuser.S ++++ b/arch/x86/lib/getuser.S +@@ -39,8 +39,13 @@ + + .macro check_range size:req + .if IS_ENABLED(CONFIG_X86_64) +- mov %rax, %rdx +- sar $63, %rdx ++ movq $0x0123456789abcdef,%rdx ++ 1: ++ .pushsection runtime_ptr_USER_PTR_MAX,"a" ++ .long 1b - 8 - . ++ .popsection ++ cmp %rax, %rdx ++ sbb %rdx, %rdx + or %rdx, %rax + .else + cmp $TASK_SIZE_MAX-\size+1, %eax diff --git a/queue-6.11/x86-fix-whitespace-in-runtime-const-assembler-output.patch b/queue-6.11/x86-fix-whitespace-in-runtime-const-assembler-output.patch new file mode 100644 index 00000000000..9222d59ddca --- /dev/null +++ b/queue-6.11/x86-fix-whitespace-in-runtime-const-assembler-output.patch @@ -0,0 +1,39 @@ +From 4dc1f31ec3f13a065c7ae2ccdec562b0123e21bb Mon Sep 17 00:00:00 2001 +From: Linus Torvalds +Date: Thu, 24 Oct 2024 13:23:56 -0700 +Subject: x86: fix whitespace in runtime-const assembler output + +From: Linus Torvalds + +commit 4dc1f31ec3f13a065c7ae2ccdec562b0123e21bb upstream. + +The x86 user pointer validation changes made me look at compiler output +a lot, and the wrong indentation for the ".popsection" in the generated +assembler triggered me. + +Signed-off-by: Linus Torvalds +Signed-off-by: Greg Kroah-Hartman +--- + arch/x86/include/asm/runtime-const.h | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/arch/x86/include/asm/runtime-const.h ++++ b/arch/x86/include/asm/runtime-const.h +@@ -6,7 +6,7 @@ + typeof(sym) __ret; \ + asm_inline("mov %1,%0\n1:\n" \ + ".pushsection runtime_ptr_" #sym ",\"a\"\n\t" \ +- ".long 1b - %c2 - .\n\t" \ ++ ".long 1b - %c2 - .\n" \ + ".popsection" \ + :"=r" (__ret) \ + :"i" ((unsigned long)0x0123456789abcdefull), \ +@@ -20,7 +20,7 @@ + typeof(0u+(val)) __ret = (val); \ + asm_inline("shrl $12,%k0\n1:\n" \ + ".pushsection runtime_shift_" #sym ",\"a\"\n\t" \ +- ".long 1b - 1 - .\n\t" \ ++ ".long 1b - 1 - .\n" \ + ".popsection" \ + :"+r" (__ret)); \ + __ret; }) diff --git a/queue-6.11/x86-support-user-address-masking-instead-of-non-speculative-conditional.patch b/queue-6.11/x86-support-user-address-masking-instead-of-non-speculative-conditional.patch new file mode 100644 index 00000000000..1a0346db51a --- /dev/null +++ b/queue-6.11/x86-support-user-address-masking-instead-of-non-speculative-conditional.patch @@ -0,0 +1,147 @@ +From 2865baf54077aa98fcdb478cefe6a42c417b9374 Mon Sep 17 00:00:00 2001 +From: Linus Torvalds +Date: Mon, 8 Apr 2024 20:04:58 -0700 +Subject: x86: support user address masking instead of non-speculative conditional + +From: Linus Torvalds + +commit 2865baf54077aa98fcdb478cefe6a42c417b9374 upstream. + +The Spectre-v1 mitigations made "access_ok()" much more expensive, since +it has to serialize execution with the test for a valid user address. + +All the normal user copy routines avoid this by just masking the user +address with a data-dependent mask instead, but the fast +"unsafe_user_read()" kind of patterms that were supposed to be a fast +case got slowed down. + +This introduces a notion of using + + src = masked_user_access_begin(src); + +to do the user address sanity using a data-dependent mask instead of the +more traditional conditional + + if (user_read_access_begin(src, len)) { + +model. + +This model only works for dense accesses that start at 'src' and on +architectures that have a guard region that is guaranteed to fault in +between the user space and the kernel space area. + +With this, the user access doesn't need to be manually checked, because +a bad address is guaranteed to fault (by some architecture masking +trick: on x86-64 this involves just turning an invalid user address into +all ones, since we don't map the top of address space). + +This only converts a couple of examples for now. Example x86-64 code +generation for loading two words from user space: + + stac + mov %rax,%rcx + sar $0x3f,%rcx + or %rax,%rcx + mov (%rcx),%r13 + mov 0x8(%rcx),%r14 + clac + +where all the error handling and -EFAULT is now purely handled out of +line by the exception path. + +Of course, if the micro-architecture does badly at 'clac' and 'stac', +the above is still pitifully slow. But at least we did as well as we +could. + +Signed-off-by: Linus Torvalds +Signed-off-by: Greg Kroah-Hartman +--- + arch/x86/include/asm/uaccess_64.h | 8 ++++++++ + fs/select.c | 4 +++- + include/linux/uaccess.h | 7 +++++++ + lib/strncpy_from_user.c | 9 +++++++++ + lib/strnlen_user.c | 9 +++++++++ + 5 files changed, 36 insertions(+), 1 deletion(-) + +--- a/arch/x86/include/asm/uaccess_64.h ++++ b/arch/x86/include/asm/uaccess_64.h +@@ -54,6 +54,14 @@ static inline unsigned long __untagged_a + #define valid_user_address(x) ((__force long)(x) >= 0) + + /* ++ * Masking the user address is an alternative to a conditional ++ * user_access_begin that can avoid the fencing. This only works ++ * for dense accesses starting at the address. ++ */ ++#define mask_user_address(x) ((typeof(x))((long)(x)|((long)(x)>>63))) ++#define masked_user_access_begin(x) ({ __uaccess_begin(); mask_user_address(x); }) ++ ++/* + * User pointers can have tag bits on x86-64. This scheme tolerates + * arbitrary values in those bits rather then masking them off. + * +--- a/fs/select.c ++++ b/fs/select.c +@@ -780,7 +780,9 @@ static inline int get_sigset_argpack(str + { + // the path is hot enough for overhead of copy_from_user() to matter + if (from) { +- if (!user_read_access_begin(from, sizeof(*from))) ++ if (can_do_masked_user_access()) ++ from = masked_user_access_begin(from); ++ else if (!user_read_access_begin(from, sizeof(*from))) + return -EFAULT; + unsafe_get_user(to->p, &from->p, Efault); + unsafe_get_user(to->size, &from->size, Efault); +--- a/include/linux/uaccess.h ++++ b/include/linux/uaccess.h +@@ -33,6 +33,13 @@ + }) + #endif + ++#ifdef masked_user_access_begin ++ #define can_do_masked_user_access() 1 ++#else ++ #define can_do_masked_user_access() 0 ++ #define masked_user_access_begin(src) NULL ++#endif ++ + /* + * Architectures should provide two primitives (raw_copy_{to,from}_user()) + * and get rid of their private instances of copy_{to,from}_user() and +--- a/lib/strncpy_from_user.c ++++ b/lib/strncpy_from_user.c +@@ -120,6 +120,15 @@ long strncpy_from_user(char *dst, const + if (unlikely(count <= 0)) + return 0; + ++ if (can_do_masked_user_access()) { ++ long retval; ++ ++ src = masked_user_access_begin(src); ++ retval = do_strncpy_from_user(dst, src, count, count); ++ user_read_access_end(); ++ return retval; ++ } ++ + max_addr = TASK_SIZE_MAX; + src_addr = (unsigned long)untagged_addr(src); + if (likely(src_addr < max_addr)) { +--- a/lib/strnlen_user.c ++++ b/lib/strnlen_user.c +@@ -96,6 +96,15 @@ long strnlen_user(const char __user *str + if (unlikely(count <= 0)) + return 0; + ++ if (can_do_masked_user_access()) { ++ long retval; ++ ++ str = masked_user_access_begin(str); ++ retval = do_strnlen_user(str, count, count); ++ user_read_access_end(); ++ return retval; ++ } ++ + max_addr = TASK_SIZE_MAX; + src_addr = (unsigned long)untagged_addr(str); + if (likely(src_addr < max_addr)) {