linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Josh Poimboeuf <jpoimboe@redhat.com>
To: Arnd Bergmann <arnd@arndb.de>
Cc: Peter Zijlstra <peterz@infradead.org>,
	the arch/x86 maintainers <x86@kernel.org>,
	Linux Kernel Mailing List <linux-kernel@vger.kernel.org>
Subject: Re: Remaining randconfig objtool warnings, linux-next-20200428
Date: Thu, 30 Apr 2020 20:07:33 -0500	[thread overview]
Message-ID: <20200501010733.ptvgzl3nbxybo4rd@treble> (raw)
In-Reply-To: <CAK8P3a2Gzj9SVZSGo+PxWR0cMJb1sFwv+ii9J6jEGE-Z41Fr+A@mail.gmail.com>

On Thu, Apr 30, 2020 at 04:05:07PM +0200, Arnd Bergmann wrote:
> lib/strncpy_from_user.o: warning: objtool: strncpy_from_user()+0x133: call to do_strncpy_from_user() with UACCESS enabled
> lib/strnlen_user.o: warning: objtool: strnlen_user()+0x122: call to do_strnlen_user() with UACCESS enabled

Does this fix it?

diff --git a/lib/strncpy_from_user.c b/lib/strncpy_from_user.c
index 706020b06617..cb3ae7a093c3 100644
--- a/lib/strncpy_from_user.c
+++ b/lib/strncpy_from_user.c
@@ -30,6 +30,9 @@ static inline long do_strncpy_from_user(char *dst, const char __user *src,
 	const struct word_at_a_time constants = WORD_AT_A_TIME_CONSTANTS;
 	unsigned long res = 0;
 
+	if (!user_access_begin(src, max))
+		return -EFAULT;
+
 	if (IS_UNALIGNED(src, dst))
 		goto byte_at_a_time;
 
@@ -43,7 +46,8 @@ static inline long do_strncpy_from_user(char *dst, const char __user *src,
 		if (has_zero(c, &data, &constants)) {
 			data = prep_zero_mask(c, data, &constants);
 			data = create_zero_mask(data);
-			return res + find_zero(data);
+			res += find_zero(data);
+			goto done;
 		}
 		res += sizeof(unsigned long);
 		max -= sizeof(unsigned long);
@@ -56,7 +60,7 @@ static inline long do_strncpy_from_user(char *dst, const char __user *src,
 		unsafe_get_user(c,src+res, efault);
 		dst[res] = c;
 		if (!c)
-			return res;
+			goto done;
 		res++;
 		max--;
 	}
@@ -65,14 +69,20 @@ static inline long do_strncpy_from_user(char *dst, const char __user *src,
 	 * Uhhuh. We hit 'max'. But was that the user-specified maximum
 	 * too? If so, that's ok - we got as much as the user asked for.
 	 */
-	if (res >= count)
-		return res;
+	if (res < count) {
+		/*
+		 * Nope: we hit the address space limit, and we still had more
+		 * characters the caller would have wanted. That's an EFAULT.
+		 */
+		goto efault;
+	}
+
+done:
+	user_access_end();
+	return res;
 
-	/*
-	 * Nope: we hit the address space limit, and we still had more
-	 * characters the caller would have wanted. That's an EFAULT.
-	 */
 efault:
+	user_access_end();
 	return -EFAULT;
 }
 
@@ -105,7 +115,6 @@ long strncpy_from_user(char *dst, const char __user *src, long count)
 	src_addr = (unsigned long)untagged_addr(src);
 	if (likely(src_addr < max_addr)) {
 		unsigned long max = max_addr - src_addr;
-		long retval;
 
 		/*
 		 * Truncate 'max' to the user-specified limit, so that
@@ -116,11 +125,7 @@ long strncpy_from_user(char *dst, const char __user *src, long count)
 
 		kasan_check_write(dst, count);
 		check_object_size(dst, count, false);
-		if (user_access_begin(src, max)) {
-			retval = do_strncpy_from_user(dst, src, count, max);
-			user_access_end();
-			return retval;
-		}
+		return do_strncpy_from_user(dst, src, count, max);
 	}
 	return -EFAULT;
 }
diff --git a/lib/strnlen_user.c b/lib/strnlen_user.c
index 41670d4a5816..f1e9e447bef1 100644
--- a/lib/strnlen_user.c
+++ b/lib/strnlen_user.c
@@ -26,6 +26,9 @@ static inline long do_strnlen_user(const char __user *src, unsigned long count,
 	unsigned long align, res = 0;
 	unsigned long c;
 
+	if (!user_access_begin(src, max))
+		return 0;
+
 	/*
 	 * Do everything aligned. But that means that we
 	 * need to also expand the maximum..
@@ -39,10 +42,12 @@ static inline long do_strnlen_user(const char __user *src, unsigned long count,
 
 	for (;;) {
 		unsigned long data;
+
 		if (has_zero(c, &data, &constants)) {
 			data = prep_zero_mask(c, data, &constants);
 			data = create_zero_mask(data);
-			return res + find_zero(data) + 1 - align;
+			res += find_zero(data) + 1 - align;
+			goto done;
 		}
 		res += sizeof(unsigned long);
 		/* We already handled 'unsigned long' bytes. Did we do it all ? */
@@ -58,13 +63,21 @@ static inline long do_strnlen_user(const char __user *src, unsigned long count,
 	 * too? If so, return the marker for "too long".
 	 */
 	if (res >= count)
-		return count+1;
+		res = count + 1;
+	else {
+		/*
+		 * Nope: we hit the address space limit, and we still had more
+		 * characters the caller would have wanted. That's 0.
+		 */
+		goto efault;
+	}
+
+done:
+	user_access_end();
+	return res;
 
-	/*
-	 * Nope: we hit the address space limit, and we still had more
-	 * characters the caller would have wanted. That's 0.
-	 */
 efault:
+	user_access_end();
 	return 0;
 }
 
@@ -100,7 +113,6 @@ long strnlen_user(const char __user *str, long count)
 	src_addr = (unsigned long)untagged_addr(str);
 	if (likely(src_addr < max_addr)) {
 		unsigned long max = max_addr - src_addr;
-		long retval;
 
 		/*
 		 * Truncate 'max' to the user-specified limit, so that
@@ -109,11 +121,7 @@ long strnlen_user(const char __user *str, long count)
 		if (max > count)
 			max = count;
 
-		if (user_access_begin(str, max)) {
-			retval = do_strnlen_user(str, count, max);
-			user_access_end();
-			return retval;
-		}
+		return do_strnlen_user(str, count, max);
 	}
 	return 0;
 }


  parent reply	other threads:[~2020-05-01  1:07 UTC|newest]

Thread overview: 38+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-04-28 14:49 Remaining randconfig objtool warnings, linux-next-20200428 Arnd Bergmann
2020-04-28 16:10 ` Josh Poimboeuf
2020-04-28 19:11   ` Kees Cook
2020-04-28 20:19   ` Arnd Bergmann
2020-04-28 20:38     ` Josh Poimboeuf
2020-04-28 21:55       ` Peter Zijlstra
2020-04-28 22:03         ` Josh Poimboeuf
2020-04-28 22:33           ` Peter Zijlstra
2020-04-28 22:48             ` Josh Poimboeuf
2020-04-28 23:08               ` Josh Poimboeuf
2020-04-29 18:55   ` Josh Poimboeuf
2020-04-29 22:46     ` Arnd Bergmann
2020-04-29 23:01       ` Josh Poimboeuf
2020-04-29 23:11       ` Josh Poimboeuf
2020-04-29 23:28         ` Josh Poimboeuf
2020-04-30 13:41           ` Arnd Bergmann
2020-04-30 14:33             ` Josh Poimboeuf
2020-04-30 19:46               ` Josh Poimboeuf
2020-04-30 20:59                 ` Arnd Bergmann
2020-04-30 21:10                   ` Josh Poimboeuf
2020-04-30 21:08                 ` Josh Poimboeuf
2020-04-30 23:02                   ` Josh Poimboeuf
2020-04-29 19:18   ` Josh Poimboeuf
2020-05-01 12:23     ` Peter Zijlstra
2020-04-30 14:05 ` Arnd Bergmann
2020-05-01  0:28   ` Josh Poimboeuf
2020-05-01 11:41     ` Arnd Bergmann
2020-05-01 17:16       ` Peter Zijlstra
2020-05-01 12:27     ` Peter Zijlstra
2020-05-01  1:07   ` Josh Poimboeuf [this message]
2020-05-01 11:18     ` Arnd Bergmann
2020-05-01 12:33     ` Peter Zijlstra
2020-05-01 13:08       ` Arnd Bergmann
2020-05-01 15:49       ` Josh Poimboeuf
2020-05-01 17:21   ` Arnd Bergmann
2020-05-01 17:26     ` Peter Zijlstra
2020-05-01 17:50       ` Josh Poimboeuf
2020-05-01 19:47         ` Arnd Bergmann

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20200501010733.ptvgzl3nbxybo4rd@treble \
    --to=jpoimboe@redhat.com \
    --cc=arnd@arndb.de \
    --cc=linux-kernel@vger.kernel.org \
    --cc=peterz@infradead.org \
    --cc=x86@kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).