2013-09-05 12:18:53

by Prarit Bhargava

[permalink] [raw]
Subject: [PATCH] random, Add user configurable get_bytes_random()

The current code has two exported functions, get_bytes_random() and
get_bytes_random_arch(). The first function only calls the entropy
store to get random data, and the second only calls the arch specific
hardware random number generator.

The problem is that no code is using the get_bytes_random_arch() and switching
over will require a significant code change. Even if the change is
made it will be static forcing a recompile of code if/when a user has a
system with a trusted random HW source. A better thing to do is allow
users to decide whether they trust their hardare random number generator.

This patchset adds a kernel parameter, hw_random_bytes, and a kernel config
option, CONFIG_HW_RANDOM_BYTES, which allows the enabling and disabling
of the hardware random number generator at boot time and at compile time.
This will allow distributions to decide if they want to use the hardware
random number generator while allowing individual users to enable or
disable generator.

Signed-off-by: Prarit Bhargava <[email protected]>
Cc: Theodore Ts'o <[email protected]>
---
Documentation/kernel-parameters.txt | 5 +++++
drivers/char/Kconfig | 8 ++++++++
drivers/char/random.c | 37 +++++++++++++++++++++++++++--------
3 files changed, 42 insertions(+), 8 deletions(-)

diff --git a/Documentation/kernel-parameters.txt b/Documentation/kernel-parameters.txt
index 31a9e51..310663c 100644
--- a/Documentation/kernel-parameters.txt
+++ b/Documentation/kernel-parameters.txt
@@ -1029,6 +1029,11 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
If specified, z/VM IUCV HVC accepts connections
from listed z/VM user IDs only.

+ hw_random_bytes= [HW] Enable/Disable use of arch specific hardware
+ random number generator in calls to
+ get_random_bytes()
+ Format: 0 (disable/default) | 1 (enable)
+
hwthread_map= [METAG] Comma-separated list of Linux cpu id to
hardware thread id mappings.
Format: <cpu>:<hwthread>
diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig
index 1421997..1de2a0d 100644
--- a/drivers/char/Kconfig
+++ b/drivers/char/Kconfig
@@ -235,6 +235,14 @@ config NWFLASH
If you're not sure, say N.

source "drivers/char/hw_random/Kconfig"
+config HW_RANDOM_BYTES
+ bool "Enable Hardware Random Number Generator for get_random_bytes()"
+ default "n"
+ help
+ Some architectures provide a default hardware random number
+ generator. By default, get_random_bytes() does not use this
+ generator to provide data. Setting this to "y" switches
+ get_random_bytes() to use the hardware random number generator.

config NVRAM
tristate "/dev/nvram support"
diff --git a/drivers/char/random.c b/drivers/char/random.c
index 0d91fe5..44ab100 100644
--- a/drivers/char/random.c
+++ b/drivers/char/random.c
@@ -1049,19 +1049,27 @@ static ssize_t extract_entropy_user(struct entropy_store *r, void __user *buf,
}

/*
- * This function is the exported kernel interface. It returns some
- * number of good random numbers, suitable for key generation, seeding
- * TCP sequence numbers, etc. It does not use the hw random number
- * generator, if available; use get_random_bytes_arch() for that.
+ * Setting of hw_random_bytes will force get_random_bytes() to use the
+ * arch-specific hardware random number generator.
*/
-void get_random_bytes(void *buf, int nbytes)
+#ifdef CONFIG_HW_RANDOM_BYTES
+static int hw_random_bytes = 1;
+#else
+static int hw_random_bytes = 0;
+#endif
+static __init int set_hw_random_bytes(char *s)
{
- extract_entropy(&nonblocking_pool, buf, nbytes, 0, 0);
+ get_option(&s, &hw_random_bytes);
+ if (hw_random_bytes)
+ pr_info("get_random_bytes() using HW RNG\n");
+ else
+ pr_info("get_random_bytes() not using HW RNG\n");
+ return 0;
}
-EXPORT_SYMBOL(get_random_bytes);
+__setup("hw_random_bytes=", set_hw_random_bytes);

/*
- * This function will use the architecture-specific hardware random
+ * This function will always use the architecture-specific hardware random
* number generator if it is available. The arch-specific hw RNG will
* almost certainly be faster than what we can do in software, but it
* is impossible to verify that it is implemented securely (as
@@ -1092,6 +1100,19 @@ void get_random_bytes_arch(void *buf, int nbytes)
}
EXPORT_SYMBOL(get_random_bytes_arch);

+/*
+ * This function is the well-known exported kernel interface. It returns some
+ * number of good random numbers, suitable for key generation, seeding
+ * TCP sequence numbers, etc.
+ */
+void get_random_bytes(void *buf, int nbytes)
+{
+ if (hw_random_bytes)
+ get_random_bytes_arch(buf, nbytes);
+ else
+ extract_entropy(&nonblocking_pool, buf, nbytes, 0, 0);
+}
+EXPORT_SYMBOL(get_random_bytes);

/*
* init_std_data - initialize pool with system data
--
1.7.9.3


2013-09-05 14:48:25

by Theodore Ts'o

[permalink] [raw]
Subject: Re: [PATCH] random, Add user configurable get_bytes_random()

On Thu, Sep 05, 2013 at 08:18:44AM -0400, Prarit Bhargava wrote:
> The current code has two exported functions, get_bytes_random() and
> get_bytes_random_arch(). The first function only calls the entropy
> store to get random data, and the second only calls the arch specific
> hardware random number generator.
>
> The problem is that no code is using the get_bytes_random_arch() and switching
> over will require a significant code change. Even if the change is
> made it will be static forcing a recompile of code if/when a user has a
> system with a trusted random HW source. A better thing to do is allow
> users to decide whether they trust their hardare random number generator.

I fail to see the benefit of just using the hardware random number
generator. We are already mixing in the hardware random number
generator into the /dev/random pool, and so the only thing that using
only the HW source is to make the kernel more vulnerable to an attack
where the NSA leans on a few Intel employee and forces/bribes them to
make a change such that the last step in the RDRAND's AES whitening
step is changed to use a counter plus a AES key known by the NSA.

- Ted

2013-09-05 15:08:33

by Prarit Bhargava

[permalink] [raw]
Subject: Re: [PATCH] random, Add user configurable get_bytes_random()



On 09/05/2013 10:48 AM, Theodore Ts'o wrote:
> On Thu, Sep 05, 2013 at 08:18:44AM -0400, Prarit Bhargava wrote:
>> The current code has two exported functions, get_bytes_random() and
>> get_bytes_random_arch(). The first function only calls the entropy
>> store to get random data, and the second only calls the arch specific
>> hardware random number generator.
>>
>> The problem is that no code is using the get_bytes_random_arch() and switching
>> over will require a significant code change. Even if the change is
>> made it will be static forcing a recompile of code if/when a user has a
>> system with a trusted random HW source. A better thing to do is allow
>> users to decide whether they trust their hardare random number generator.
>
> I fail to see the benefit of just using the hardware random number
> generator. We are already mixing in the hardware random number
> generator into the /dev/random pool, and so the only thing that using

The issue isn't userspace /dev/random as much as it is the use of
get_random_bytes() through out the kernel. Switching to get_random_bytes_arch()
is a search'n'replace on the entire kernel. If a user wants the faster random
HW generator why shouldn't they be able to use it by default?

P.

2013-09-05 19:03:39

by Theodore Ts'o

[permalink] [raw]
Subject: Re: [PATCH] random, Add user configurable get_bytes_random()

On Thu, Sep 05, 2013 at 11:08:28AM -0400, Prarit Bhargava wrote:
>
> The issue isn't userspace /dev/random as much as it is the use of
> get_random_bytes() through out the kernel. Switching to get_random_bytes_arch()
> is a search'n'replace on the entire kernel. If a user wants the faster random
> HW generator why shouldn't they be able to use it by default?

Where is the speed of the random number generator a bottleneck?

In general, adding knobs when users can make what might be potentially
the wrong chance is very dangerous. There is a reason why there
aren't convenient knobs to allow users to select the use of the MD4
checksum, "because it might be faster, why shouldn't the user be
allowed to shoot themselves in the foot"?

- Ted

2013-09-05 19:49:12

by Theodore Ts'o

[permalink] [raw]
Subject: Re: [PATCH] random, Add user configurable get_bytes_random()

BTW, note the following article, published today:

http://www.nytimes.com/2013/09/06/us/nsa-foils-much-internet-encryption.html?pagewanted=all

"By this year, the Sigint Enabling Project had found ways inside some
of the encryption chips that scramble information for businesses and
governments, either by working with chipmakers to insert back doors...."

Relying solely and blindly on a magic hardware random number generator
which is sealed inside a CPU chip and which is impossible to audit is
a ***BAD*** idea.

- Ted

2013-09-06 12:08:56

by Prarit Bhargava

[permalink] [raw]
Subject: Re: [PATCH] random, Add user configurable get_bytes_random()



On 09/05/2013 03:49 PM, Theodore Ts'o wrote:
> BTW, note the following article, published today:
>
> http://www.nytimes.com/2013/09/06/us/nsa-foils-much-internet-encryption.html?pagewanted=all
>
> "By this year, the Sigint Enabling Project had found ways inside some
> of the encryption chips that scramble information for businesses and
> governments, either by working with chipmakers to insert back doors...."
>
> Relying solely and blindly on a magic hardware random number generator
> which is sealed inside a CPU chip and which is impossible to audit is
> a ***BAD*** idea.

Your argument seems to surround the idea that putting stuff on the internet is
safe. It isn't. If you've believed that then you've had your head in the sand
and I've got a lot of land in Florida to sell you.

Either way ... it's obvious you're not willing to take this patch and I respect
that decision.

Thanks,

P.

2013-09-06 13:57:41

by Theodore Ts'o

[permalink] [raw]
Subject: Re: [PATCH] random, Add user configurable get_bytes_random()

On Fri, Sep 06, 2013 at 08:08:52AM -0400, Prarit Bhargava wrote:
>
> Your argument seems to surround the idea that putting stuff on the internet is
> safe. It isn't. If you've believed that then you've had your head in the sand
> and I've got a lot of land in Florida to sell you.

I have no idea how you are getting this idea. My argument is that
putting all of our faith in one person (whether it is DNI Clapper
lying to the US Congress), or one company (like Intel, Qualcomm, TI,
etc.) is a bad idea. Software can be audited. Hardware can not. We
can at least test whether or not a network card is performing
according to its specifications. But a HWRNG is by definition
something that can't be tested. Statistical tests are not sufficient
to prove that the HWRNG has not been gimmicked.

Hence, unless you can show me where the speed advantage of bypassing
the entropy pool is needed, why should we do this? And if there is a
specific place where need to consider adjusting the security
vs. performance tradeoff, let's do that on a case by case basis,
instead of making a global change.

Hence, your patch is IMHO irresponsible. It exposes us to more risk,
for an undefined theoretical benefit.

Of course nothing on the internet is going to be perfectly safe. But
that doesn't mean that we shouldn't make it harder for any government
agency, whether it is the Chinese MSS, the US NSA, or the UK GHCQ,
from being able to easily perform casual, dragnet-style surveillence.

- Ted

2013-09-12 19:15:31

by Jörn Engel

[permalink] [raw]
Subject: Re: [PATCH] random, Add user configurable get_bytes_random()

On Fri, 6 September 2013 09:57:31 -0400, Theodore Ts'o wrote:
> according to its specifications. But a HWRNG is by definition
> something that can't be tested. Statistical tests are not sufficient
> to prove that the HWRNG has not been gimmicked.

And just to prove your point even more:
http://people.umass.edu/gbecker/BeckerChes13.pdf

Jörn

--
...one more straw can't possibly matter...
-- Kirby Bakken