Skip to content

Commit af4e9ef

Browse files
David Laighttorvalds
authored andcommitted
uaccess: Fix scoped_user_read_access() for 'pointer to const'
If a 'const struct foo __user *ptr' is used for the address passed to scoped_user_read_access() then you get a warning/error uaccess.h:691:1: error: initialization discards 'const' qualifier from pointer target type [-Werror=discarded-qualifiers] for the void __user *_tmpptr = __scoped_user_access_begin(mode, uptr, size, elbl) assignment. Fix by using 'auto' for both _tmpptr and the redeclaration of uptr. Replace the CLASS() with explicit __cleanup() functions on uptr. Fixes: e497310 ("uaccess: Provide scoped user access regions") Signed-off-by: David Laight <david.laight.linux@gmail.com> Reviewed-and-tested-by: Christophe Leroy (CS GROUP) <chleroy@kernel.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
1 parent 1b37ac2 commit af4e9ef

File tree

1 file changed

+20
-34
lines changed

1 file changed

+20
-34
lines changed

include/linux/uaccess.h

Lines changed: 20 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -647,36 +647,22 @@ static inline void user_access_restore(unsigned long flags) { }
647647
/* Define RW variant so the below _mode macro expansion works */
648648
#define masked_user_rw_access_begin(u) masked_user_access_begin(u)
649649
#define user_rw_access_begin(u, s) user_access_begin(u, s)
650-
#define user_rw_access_end() user_access_end()
651650

652651
/* Scoped user access */
653-
#define USER_ACCESS_GUARD(_mode) \
654-
static __always_inline void __user * \
655-
class_user_##_mode##_begin(void __user *ptr) \
656-
{ \
657-
return ptr; \
658-
} \
659-
\
660-
static __always_inline void \
661-
class_user_##_mode##_end(void __user *ptr) \
662-
{ \
663-
user_##_mode##_access_end(); \
664-
} \
665-
\
666-
DEFINE_CLASS(user_ ##_mode## _access, void __user *, \
667-
class_user_##_mode##_end(_T), \
668-
class_user_##_mode##_begin(ptr), void __user *ptr) \
669-
\
670-
static __always_inline class_user_##_mode##_access_t \
671-
class_user_##_mode##_access_ptr(void __user *scope) \
672-
{ \
673-
return scope; \
674-
}
675652

676-
USER_ACCESS_GUARD(read)
677-
USER_ACCESS_GUARD(write)
678-
USER_ACCESS_GUARD(rw)
679-
#undef USER_ACCESS_GUARD
653+
/* Cleanup wrapper functions */
654+
static __always_inline void __scoped_user_read_access_end(const void *p)
655+
{
656+
user_read_access_end();
657+
};
658+
static __always_inline void __scoped_user_write_access_end(const void *p)
659+
{
660+
user_write_access_end();
661+
};
662+
static __always_inline void __scoped_user_rw_access_end(const void *p)
663+
{
664+
user_access_end();
665+
};
680666

681667
/**
682668
* __scoped_user_access_begin - Start a scoped user access
@@ -750,13 +736,13 @@ USER_ACCESS_GUARD(rw)
750736
*
751737
* Don't use directly. Use scoped_masked_user_$MODE_access() instead.
752738
*/
753-
#define __scoped_user_access(mode, uptr, size, elbl) \
754-
for (bool done = false; !done; done = true) \
755-
for (void __user *_tmpptr = __scoped_user_access_begin(mode, uptr, size, elbl); \
756-
!done; done = true) \
757-
for (CLASS(user_##mode##_access, scope)(_tmpptr); !done; done = true) \
758-
/* Force modified pointer usage within the scope */ \
759-
for (const typeof(uptr) uptr = _tmpptr; !done; done = true)
739+
#define __scoped_user_access(mode, uptr, size, elbl) \
740+
for (bool done = false; !done; done = true) \
741+
for (auto _tmpptr = __scoped_user_access_begin(mode, uptr, size, elbl); \
742+
!done; done = true) \
743+
/* Force modified pointer usage within the scope */ \
744+
for (const auto uptr __cleanup(__scoped_user_##mode##_access_end) = \
745+
_tmpptr; !done; done = true)
760746

761747
/**
762748
* scoped_user_read_access_size - Start a scoped user read access with given size

0 commit comments

Comments
 (0)