From: "Jason A. Donenfeld" <Jason@zx2c4.com>
To: Florian Weimer <fweimer@redhat.com>
Cc: linux-kernel@vger.kernel.org, patches@lists.linux.dev,
tglx@linutronix.de, linux-crypto@vger.kernel.org,
linux-api@vger.kernel.org, x86@kernel.org,
Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
Adhemerval Zanella Netto <adhemerval.zanella@linaro.org>,
Carlos O'Donell <carlos@redhat.com>,
Arnd Bergmann <arnd@arndb.de>,
Christian Brauner <brauner@kernel.org>
Subject: Re: [PATCH v10 1/4] random: add vgetrandom_alloc() syscall
Date: Thu, 1 Dec 2022 03:16:20 +0100 [thread overview]
Message-ID: <Y4gOdC8J+zzRsago@zx2c4.com> (raw)
In-Reply-To: <Y4d5SyU3akA9ZBaJ@zx2c4.com>
On Wed, Nov 30, 2022 at 04:39:55PM +0100, Jason A. Donenfeld wrote:
> > Can userspace use the memory for something else if it's not passed to
> > getrandom?
>
> I suspect the documentation answer here is, "no", even if technically it
> might happen to work on this kernel or that kernel. I suppose this could
> even be quasi-enforced by xoring the top bits with some vdso
> compile-time constant, so you can't rely on being able to dereference
> it yourself.
> [...]
> Then they're caught holding the bag? This doesn't seem much different
> from userspace shooting themselves in general, like writing garbage into
> the allocated states and then trying to use them. If this is something
> you really, really are concerned about, then maybe my cheesy dumb xor
> thing mentioned above would be a low effort mitigation here.
I implemented a sample of this, below. I think this is a bit silly,
though, and making this fully robust could take some effort. Overall, I
don't think we should do this.
However, the more I think about the args thing from the last email,
the more I like *that* idea. So I think I'll roll with that.
But this cheesy pointer obfuscation thing here, meh. But here's what it
could look like anyway:
diff --git a/drivers/char/random.c b/drivers/char/random.c
index 2aaeb48d11be..7aff45165ce5 100644
--- a/drivers/char/random.c
+++ b/drivers/char/random.c
@@ -228,7 +228,7 @@ SYSCALL_DEFINE2(vgetrandom_alloc, struct vgetrandom_alloc_args __user *, uargs,
if (args.flags & VGRA_DEALLOCATE) {
if (args.size_per_each != state_size || args.num > max_states || !args.states)
return -EINVAL;
- return vm_munmap(args.states, args.num * state_size);
+ return vm_munmap(args.states ^ VGETRANDOM_STATE_HI_TAINT, args.num * state_size);
}
/* These don't make sense as input values if allocating, so reject them. */
@@ -249,7 +249,7 @@ SYSCALL_DEFINE2(vgetrandom_alloc, struct vgetrandom_alloc_args __user *, uargs,
args.num = num_states;
args.size_per_each = state_size;
- args.states = pages_addr;
+ args.states = pages_addr ^ VGETRANDOM_STATE_HI_TAINT;
ret = -EFAULT;
if (copy_to_user(uargs, &args, sizeof(args)))
diff --git a/include/vdso/getrandom.h b/include/vdso/getrandom.h
index cb624799a8e7..9a6aaf4d99d4 100644
--- a/include/vdso/getrandom.h
+++ b/include/vdso/getrandom.h
@@ -8,6 +8,7 @@
#include <crypto/chacha.h>
#include <vdso/limits.h>
+#include <linux/version.h>
/**
* struct vgetrandom_state - State used by vDSO getrandom() and allocated by vgetrandom_alloc().
@@ -41,4 +42,10 @@ struct vgetrandom_state {
bool in_use;
};
+/* Be annoying by changing frequently enough. */
+#define VGETRANDOM_STATE_HI_TAINT ((unsigned long)(((LINUX_VERSION_CODE >> 16) + \
+ (LINUX_VERSION_CODE >> 8) + (LINUX_VERSION_CODE >> 0) + \
+ __GNUC__ + __GNUC_MINOR__ + __GNUC_PATCHLEVEL__) \
+ & 0xff) << (BITS_PER_LONG - 8))
+
#endif /* _VDSO_GETRANDOM_H */
diff --git a/lib/vdso/getrandom.c b/lib/vdso/getrandom.c
index 9ca624756432..14cbd349186c 100644
--- a/lib/vdso/getrandom.c
+++ b/lib/vdso/getrandom.c
@@ -57,7 +57,7 @@ __cvdso_getrandom_data(const struct vdso_rng_data *rng_info, void *buffer, size_
unsigned int flags, void *opaque_state)
{
ssize_t ret = min_t(size_t, INT_MAX & PAGE_MASK /* = MAX_RW_COUNT */, len);
- struct vgetrandom_state *state = opaque_state;
+ struct vgetrandom_state *state = (void *)((unsigned long)opaque_state ^ VGETRANDOM_STATE_HI_TAINT);
size_t batch_len, nblocks, orig_len = len;
unsigned long current_generation;
void *orig_buffer = buffer;
next prev parent reply other threads:[~2022-12-01 2:16 UTC|newest]
Thread overview: 37+ messages / expand[flat|nested] mbox.gz Atom feed top
2022-11-29 21:06 [PATCH v10 0/4] implement getrandom() in vDSO Jason A. Donenfeld
2022-11-29 21:06 ` [PATCH v10 1/4] random: add vgetrandom_alloc() syscall Jason A. Donenfeld
2022-11-29 22:02 ` Thomas Gleixner
2022-11-30 0:59 ` Jason A. Donenfeld
2022-11-30 1:37 ` Thomas Gleixner
2022-11-30 1:42 ` Jason A. Donenfeld
2022-11-30 22:39 ` David Laight
2022-12-01 0:14 ` Jason A. Donenfeld
2022-11-30 10:51 ` Florian Weimer
2022-11-30 15:39 ` Jason A. Donenfeld
2022-11-30 16:38 ` Jason A. Donenfeld
2022-12-02 14:38 ` Jason A. Donenfeld
2022-12-01 2:16 ` Jason A. Donenfeld [this message]
2022-12-02 17:17 ` Florian Weimer
2022-12-02 18:29 ` Jason A. Donenfeld
2022-11-29 21:06 ` [PATCH v10 2/4] arch: allocate vgetrandom_alloc() syscall number Jason A. Donenfeld
2022-11-30 8:56 ` Geert Uytterhoeven
2022-11-30 10:06 ` Jason A. Donenfeld
2022-11-30 10:51 ` Arnd Bergmann
2022-11-29 21:06 ` [PATCH v10 3/4] random: introduce generic vDSO getrandom() implementation Jason A. Donenfeld
2022-11-29 22:42 ` Thomas Gleixner
2022-11-30 1:09 ` Jason A. Donenfeld
2022-11-30 10:44 ` Florian Weimer
2022-11-30 14:51 ` Jason A. Donenfeld
2022-11-30 14:59 ` Jason A. Donenfeld
2022-11-30 15:07 ` Arnd Bergmann
2022-11-30 15:12 ` Jason A. Donenfeld
2022-11-30 15:29 ` Arnd Bergmann
2022-11-30 15:47 ` Jason A. Donenfeld
2022-11-30 16:13 ` Arnd Bergmann
2022-11-30 16:40 ` Jason A. Donenfeld
2022-11-30 17:00 ` Thomas Gleixner
2022-11-29 21:06 ` [PATCH v10 4/4] x86: vdso: Wire up getrandom() vDSO implementation Jason A. Donenfeld
2022-11-29 22:52 ` Thomas Gleixner
2022-11-30 1:11 ` Jason A. Donenfeld
2022-11-30 5:22 ` Eric Biggers
2022-11-30 10:12 ` Jason A. Donenfeld
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=Y4gOdC8J+zzRsago@zx2c4.com \
--to=jason@zx2c4.com \
--cc=adhemerval.zanella@linaro.org \
--cc=arnd@arndb.de \
--cc=brauner@kernel.org \
--cc=carlos@redhat.com \
--cc=fweimer@redhat.com \
--cc=gregkh@linuxfoundation.org \
--cc=linux-api@vger.kernel.org \
--cc=linux-crypto@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=patches@lists.linux.dev \
--cc=tglx@linutronix.de \
--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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.