From: Amit Daniel Kachhap amitdaniel.kachhap@arm.com
Add user_ptr_is_valid() and user_ptr_set_addr() helpers to operate on user pointers in different situations in subsequent patches.
* user_ptr_is_valid() returns the tag value in PCuABI.
* user_ptr_set_addr() sets the address field of the user pointer.
Both of the above helpers use CHERI compiler builtins for PCuABI case.
Signed-off-by: Amit Daniel Kachhap amitdaniel.kachhap@arm.com Signed-off-by: Kevin Brodsky kevin.brodsky@arm.com --- Documentation/core-api/user_ptr.rst | 12 +++++++++++ include/linux/user_ptr.h | 33 ++++++++++++++++++++++++++++- 2 files changed, 44 insertions(+), 1 deletion(-)
diff --git a/Documentation/core-api/user_ptr.rst b/Documentation/core-api/user_ptr.rst index 6ac493f7e461..d314bc215c65 100644 --- a/Documentation/core-api/user_ptr.rst +++ b/Documentation/core-api/user_ptr.rst @@ -212,6 +212,12 @@ should always be used when error codes are stored in user pointers. Operating on user pointers ==========================
+Validity +---------- + +``user_ptr_is_valid(p)`` (``<linux/user_ptr.h>``) can be used to check +whether a user pointer is valid, + Comparison ----------
@@ -250,6 +256,12 @@ This can be done using the ``check_user_ptr_*()`` functions, see Note that these functions are no-ops (always succeed) when PCuABI is not selected, as there is no user pointer metadata to check in that case.
+Setting the address +------------------- + +``user_ptr_set_addr(p, a)`` (``<linux/user_ptr.h>``) can be used to set +the address of a user pointer. + Bounds ------
diff --git a/include/linux/user_ptr.h b/include/linux/user_ptr.h index 997e6cfa95e2..3b0bc117fcfb 100644 --- a/include/linux/user_ptr.h +++ b/include/linux/user_ptr.h @@ -207,7 +207,22 @@ static inline ptraddr_t user_ptr_limit(const void __user *ptr) }
/** - * user_ptr_is_same() - Checks where two user pointers are exactly the same. + * user_ptr_is_valid() - Check if a user pointer is valid. + * @ptr: The user pointer to check. + * + * Return: true if @ptr is valid (tag set in PCuABI). + */ +static inline bool user_ptr_is_valid(const void __user *ptr) +{ +#ifdef CONFIG_CHERI_PURECAP_UABI + return __builtin_cheri_tag_get(ptr); +#else + return 0; +#endif +} + +/** + * user_ptr_is_same() - Check whether two user pointers are exactly the same. * @p1: The first user pointer to check. * @p2: The second user pointer to check. * @@ -226,6 +241,22 @@ static inline bool user_ptr_is_same(const void __user *p1, const void __user *p2 #endif }
+/** + * user_ptr_set_addr() - Set the address of the user pointer. + * @ptr: The user pointer to set the address of. + * @addr: The address to set the pointer to. + * + * Return: A user pointer with its address set to @addr. + */ +static inline void __user *user_ptr_set_addr(void __user *ptr, ptraddr_t addr) +{ +#ifdef CONFIG_CHERI_PURECAP_UABI + return __builtin_cheri_address_set(ptr, addr); +#else + return as_user_ptr(addr); +#endif +} + /** * user_ptr_set_bounds() - Set the lower and upper bounds of a user pointer. * @ptr: The input user pointer.