From 6ccdc91d6af922f3ded5de494ff27daedeb6d6c9 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Tue, 2 May 2023 12:35:01 -0700 Subject: x86: mm: remove architecture-specific 'access_ok()' define There's already a generic definition of 'access_ok()' in the asm-generic/access_ok.h header file, and the only difference bwteen that and the x86-specific one is the added check for WARN_ON_IN_IRQ(). And it turns out that the reason for that check is long gone: it used to use a "user_addr_max()" inline function that depended on the current thread, and caused problems in non-thread contexts. For details, see commits 7c4788950ba5 ("x86/uaccess, sched/preempt: Verify access_ok() context") and in particular commit ae31fe51a3cc ("perf/x86: Restore TASK_SIZE check on frame pointer") about how and why this came to be. But that "current task" issue was removed in the big set_fs() removal by Christoph Hellwig in commit 47058bb54b57 ("x86: remove address space overrides using set_fs()"). So the reason for the test and the architecture-specific access_ok() define no longer exists, and is actually harmful these days. For example, it led various 'copy_from_user_nmi()' games (eg using __range_not_ok() instead, and then later converted to __access_ok() when that became ok). And that in turn meant that LAM was broken for the frame following before this series, because __access_ok() used to not do the address untagging. Accessing user state still needs care in many contexts, but access_ok() is not the place for this test. Acked-by: Peter Zijlstra (Intel) Signed-off-by: Linus Torvalds torvalds@linux-foundation.org> --- arch/x86/include/asm/uaccess.h | 34 ---------------------------------- 1 file changed, 34 deletions(-) (limited to 'arch/x86/include/asm/uaccess.h') diff --git a/arch/x86/include/asm/uaccess.h b/arch/x86/include/asm/uaccess.h index 123135d60f72..cad17e11aa83 100644 --- a/arch/x86/include/asm/uaccess.h +++ b/arch/x86/include/asm/uaccess.h @@ -16,14 +16,6 @@ #include #include -#ifdef CONFIG_DEBUG_ATOMIC_SLEEP -static inline bool pagefault_disabled(void); -# define WARN_ON_IN_IRQ() \ - WARN_ON_ONCE(!in_task() && !pagefault_disabled()) -#else -# define WARN_ON_IN_IRQ() -#endif - #ifdef CONFIG_ADDRESS_MASKING /* * Mask out tag bits from the address. @@ -103,32 +95,6 @@ static inline bool __access_ok(const void __user *ptr, unsigned long size) #define __access_ok __access_ok #endif -/** - * access_ok - Checks if a user space pointer is valid - * @addr: User space pointer to start of block to check - * @size: Size of block to check - * - * Context: User context only. This function may sleep if pagefaults are - * enabled. - * - * Checks if a pointer to a block of memory in user space is valid. - * - * Note that, depending on architecture, this function probably just - * checks that the pointer is in the user space range - after calling - * this function, memory access functions may still return -EFAULT. - * - * Return: true (nonzero) if the memory block may be valid, false (zero) - * if it is definitely invalid. - * - * This should not be x86-specific. The only odd things out here is - * the WARN_ON_IN_IRQ(), which doesn't exist in the generic version. - */ -#define access_ok(addr, size) \ -({ \ - WARN_ON_IN_IRQ(); \ - likely(__access_ok(addr, size)); \ -}) - #include extern int __get_user_1(void); -- cgit v1.2.3