Re: [RFC][PATCH] Make cryptoapi non-optional?

Matt Mackall
2003-08-18T15:47:02Z

On Sun, Aug 17, 2003 at 11:23:48PM -0400, Theodore Ts'o wrote:
> On Fri, Aug 15, 2003 at 06:55:01PM -0500, Matt Mackall wrote:
> > I posted a proof of concept patch for discussion on $SUBJECT. In that
> > patch, I removed the folding for the purposes of having a reasonable
> > comparison between cryptoapi and native. Cryptoapi does FIPS-180-1 and
> > thus does twice as much hashing on 512 bits.
>
> It would be nice if there was a Crypto API algorithm variant which
> didn't do the FIPS-180-1 padding, for those applications (like
> /dev/random) that don't need it.

I'm looking at one, but the two layers of indirection in cryptoapi make
this tricky.

> > As for "screwing with /dev/random", it's got rather more serious and
> > longstanding problems than speed that I've been addressing. For
> > instance, I'm pretty sure there was never a time when entropy
> > accounting wasn't racy let alone wrong, SMP or no (fixed in -mm, thank
> > you). Nor has there ever been a time when change_poolsize() wasn't an
> > oops waiting to happen (patch queued for resend).
>
> Agreed, fixing the locking is much more important than CryptoAPI
> changes. Can you send me a pointer to your latest locking patches?
> I'd like to look them over. Thanks!!

Locking fixes:

http://www.kernel.org/pub/linux/kernel/people/akpm/patches/2.6/2.6.0-test2/2.6.0-test2-mm4/broken-out/random-locking-fixes.patch

Ignore the changelog, it doesn't match the patch. Instead read what I
wrote to Andrew.

Accounting stuff at:

http://www.kernel.org/pub/linux/kernel/people/akpm/patches/2.6/2.6.0-test2/2.6.0-test2-mm4/broken-out/random-accounting-and-sleeping-fixes.patch

The above involved a lot of carefully going over logs with entropy
debugging turned on as most of it wasn't obvious from reading the
code. There are still a couple corner cases in the above but they fall
on the undercounting side. For the separated output pool patch, the xfer
code ends up looking like this, which is much easier to follow:

+static void reseed_pool(struct entropy_store *r, int margin, int wanted)
+{
+ __u32 tmp[TMP_BUF_SIZE];
+ int bytes;
+
+ DEBUG_ENT("reseed %s wants %d bits (margin %d)\n",
+ r->name, wanted*8, margin);
+
+ /* Never more than can fit in buffer */
+ bytes = min_t(int, wanted, sizeof(tmp));
+ /* Nor more than destination has room for */
+ bytes = min_t(int, bytes, (r->poolinfo->POOLBITS-r->entropy_count)/8);
+ /* Nor too much to starve other pools */
+ bytes = min_t(int, bytes, (input_pool->entropy_count - margin)/8);
+ /* And never less than catastrophic reseed threshold */
+ if(bytes < read_thresh/8)
+ return;
+
+ DEBUG_ENT("trying to reseed %s with %d bits\n", r->name, bytes*8);
+
+ bytes=extract_entropy(input_pool, tmp, bytes, EXTRACT_ENTROPY_LIMIT);
+ add_entropy_words(r, tmp, bytes+3/4);
+ credit_entropy_store(r, bytes*8);

--
Matt Mackall : http://www.selenic.com : of or relating to the moon