diff options
author | Helge Deller <deller@gmx.de> | 2015-06-04 17:57:18 -0400 |
---|---|---|
committer | Helge Deller <deller@gmx.de> | 2015-06-04 17:57:18 -0400 |
commit | 9b7b819ca1e508195feed5ece558dca66adeef05 (patch) | |
tree | cf62f858c89c61d5b38052273ff7ca2defb3a818 | |
parent | ff25ea8f4eeea252bfcaf65289fa57ba6de080dd (diff) |
compat: cleanup coding in compat_get_bitmap() and compat_put_bitmap()
In the functions compat_get_bitmap() and compat_put_bitmap() the
variable nr_compat_longs stores how many compat_ulong_t words should be
copied in a loop.
The copy loop itself is this:
if (nr_compat_longs-- > 0) {
if (__get_user(um, umask)) return -EFAULT;
} else {
um = 0;
}
Since nr_compat_longs gets unconditionally decremented in each loop and
since it's type is unsigned this could theoretically lead to out of
bounds accesses to userspace if nr_compat_longs wraps around to
(unsigned)(-1).
Although the callers currently do not trigger out-of-bounds accesses, we
should better implement the loop in a safe way to completely avoid such
warp-arounds.
Signed-off-by: Helge Deller <deller@gmx.de>
Cc: Linus Torvalds <torvalds@linux-foundation.org>
Cc: Al Viro <viro@zeniv.linux.org.uk>
-rw-r--r-- | kernel/compat.c | 6 |
1 files changed, 4 insertions, 2 deletions
diff --git a/kernel/compat.c b/kernel/compat.c index 24f00610c575..333d364be29d 100644 --- a/kernel/compat.c +++ b/kernel/compat.c | |||
@@ -912,7 +912,8 @@ long compat_get_bitmap(unsigned long *mask, const compat_ulong_t __user *umask, | |||
912 | * bitmap. We must however ensure the end of the | 912 | * bitmap. We must however ensure the end of the |
913 | * kernel bitmap is zeroed. | 913 | * kernel bitmap is zeroed. |
914 | */ | 914 | */ |
915 | if (nr_compat_longs-- > 0) { | 915 | if (nr_compat_longs) { |
916 | nr_compat_longs--; | ||
916 | if (__get_user(um, umask)) | 917 | if (__get_user(um, umask)) |
917 | return -EFAULT; | 918 | return -EFAULT; |
918 | } else { | 919 | } else { |
@@ -954,7 +955,8 @@ long compat_put_bitmap(compat_ulong_t __user *umask, unsigned long *mask, | |||
954 | * We dont want to write past the end of the userspace | 955 | * We dont want to write past the end of the userspace |
955 | * bitmap. | 956 | * bitmap. |
956 | */ | 957 | */ |
957 | if (nr_compat_longs-- > 0) { | 958 | if (nr_compat_longs) { |
959 | nr_compat_longs--; | ||
958 | if (__put_user(um, umask)) | 960 | if (__put_user(um, umask)) |
959 | return -EFAULT; | 961 | return -EFAULT; |
960 | } | 962 | } |