From owner-svn-src-head@freebsd.org Tue Jun 30 17:00:48 2015 Return-Path: Delivered-To: svn-src-head@mailman.ysv.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) by mailman.ysv.freebsd.org (Postfix) with ESMTP id 9C89A990530; Tue, 30 Jun 2015 17:00:48 +0000 (UTC) (envelope-from markm@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:1900:2254:2068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mx1.freebsd.org (Postfix) with ESMTPS id 8A4C31894; Tue, 30 Jun 2015 17:00:48 +0000 (UTC) (envelope-from markm@FreeBSD.org) Received: from svn.freebsd.org ([127.0.1.70]) by svn.freebsd.org (8.14.9/8.14.9) with ESMTP id t5UH0mvl001512; Tue, 30 Jun 2015 17:00:48 GMT (envelope-from markm@FreeBSD.org) Received: (from markm@localhost) by svn.freebsd.org (8.14.9/8.14.9/Submit) id t5UH0jPq001498; Tue, 30 Jun 2015 17:00:45 GMT (envelope-from markm@FreeBSD.org) Message-Id: <201506301700.t5UH0jPq001498@svn.freebsd.org> X-Authentication-Warning: svn.freebsd.org: markm set sender to markm@FreeBSD.org using -f From: Mark Murray Date: Tue, 30 Jun 2015 17:00:45 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r284959 - in head: . share/man/man4 share/man/man9 sys/conf sys/dev/glxsb sys/dev/hifn sys/dev/random sys/dev/rndtest sys/dev/safe sys/dev/syscons sys/dev/ubsec sys/dev/virtio/random sy... X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.20 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 30 Jun 2015 17:00:48 -0000 Author: markm Date: Tue Jun 30 17:00:45 2015 New Revision: 284959 URL: https://svnweb.freebsd.org/changeset/base/284959 Log: Huge cleanup of random(4) code. * GENERAL - Update copyright. - Make kernel options for RANDOM_YARROW and RANDOM_DUMMY. Set neither to ON, which means we want Fortuna - If there is no 'device random' in the kernel, there will be NO random(4) device in the kernel, and the KERN_ARND sysctl will return nothing. With RANDOM_DUMMY there will be a random(4) that always blocks. - Repair kern.arandom (KERN_ARND sysctl). The old version went through arc4random(9) and was a bit weird. - Adjust arc4random stirring a bit - the existing code looks a little suspect. - Fix the nasty pre- and post-read overloading by providing explictit functions to do these tasks. - Redo read_random(9) so as to duplicate random(4)'s read internals. This makes it a first-class citizen rather than a hack. - Move stuff out of locked regions when it does not need to be there. - Trim RANDOM_DEBUG printfs. Some are excess to requirement, some behind boot verbose. - Use SYSINIT to sequence the startup. - Fix init/deinit sysctl stuff. - Make relevant sysctls also tunables. - Add different harvesting "styles" to allow for different requirements (direct, queue, fast). - Add harvesting of FFS atime events. This needs to be checked for weighing down the FS code. - Add harvesting of slab allocator events. This needs to be checked for weighing down the allocator code. - Fix the random(9) manpage. - Loadable modules are not present for now. These will be re-engineered when the dust settles. - Use macros for locks. - Fix comments. * src/share/man/... - Update the man pages. * src/etc/... - The startup/shutdown work is done in D2924. * src/UPDATING - Add UPDATING announcement. * src/sys/dev/random/build.sh - Add copyright. - Add libz for unit tests. * src/sys/dev/random/dummy.c - Remove; no longer needed. Functionality incorporated into randomdev.*. * live_entropy_sources.c live_entropy_sources.h - Remove; content moved. - move content to randomdev.[ch] and optimise. * src/sys/dev/random/random_adaptors.c src/sys/dev/random/random_adaptors.h - Remove; plugability is no longer used. Compile-time algorithm selection is the way to go. * src/sys/dev/random/random_harvestq.c src/sys/dev/random/random_harvestq.h - Add early (re)boot-time randomness caching. * src/sys/dev/random/randomdev_soft.c src/sys/dev/random/randomdev_soft.h - Remove; no longer needed. * src/sys/dev/random/uint128.h - Provide a fake uint128_t; if a real one ever arrived, we can use that instead. All that is needed here is N=0, N++, N==0, and some localised trickery is used to manufacture a 128-bit 0ULLL. * src/sys/dev/random/unit_test.c src/sys/dev/random/unit_test.h - Improve unit tests; previously the testing human needed clairvoyance; now the test will do a basic check of compressibility. Clairvoyant talent is still a good idea. - This is still a long way off a proper unit test. * src/sys/dev/random/fortuna.c src/sys/dev/random/fortuna.h - Improve messy union to just uint128_t. - Remove unneeded 'static struct fortuna_start_cache'. - Tighten up up arithmetic. - Provide a method to allow eternal junk to be introduced; harden it against blatant by compress/hashing. - Assert that locks are held correctly. - Fix the nasty pre- and post-read overloading by providing explictit functions to do these tasks. - Turn into self-sufficient module (no longer requires randomdev_soft.[ch]) * src/sys/dev/random/yarrow.c src/sys/dev/random/yarrow.h - Improve messy union to just uint128_t. - Remove unneeded 'staic struct start_cache'. - Tighten up up arithmetic. - Provide a method to allow eternal junk to be introduced; harden it against blatant by compress/hashing. - Assert that locks are held correctly. - Fix the nasty pre- and post-read overloading by providing explictit functions to do these tasks. - Turn into self-sufficient module (no longer requires randomdev_soft.[ch]) - Fix some magic numbers elsewhere used as FAST and SLOW. Differential Revision: https://reviews.freebsd.org/D2025 Reviewed by: vsevolod,delphij,rwatson,trasz,jmg Approved by: so (delphij) Added: head/sys/dev/random/randomdev_none.c (contents, props changed) - copied, changed from r284956, head/sys/dev/random/randomdev_soft.h Deleted: head/sys/dev/random/dummy_rng.c head/sys/dev/random/live_entropy_sources.c head/sys/dev/random/live_entropy_sources.h head/sys/dev/random/random_adaptors.c head/sys/dev/random/random_adaptors.h head/sys/dev/random/randomdev_soft.c head/sys/dev/random/randomdev_soft.h head/sys/modules/random/Makefile Modified: head/UPDATING head/share/man/man4/random.4 head/share/man/man9/random.9 head/share/man/man9/random_harvest.9 head/sys/conf/files head/sys/conf/options head/sys/dev/glxsb/glxsb.c head/sys/dev/hifn/hifn7751.c head/sys/dev/random/build.sh head/sys/dev/random/fortuna.c head/sys/dev/random/fortuna.h head/sys/dev/random/hash.c head/sys/dev/random/hash.h head/sys/dev/random/ivy.c head/sys/dev/random/nehemiah.c head/sys/dev/random/random_harvestq.c head/sys/dev/random/random_harvestq.h head/sys/dev/random/randomdev.c head/sys/dev/random/randomdev.h head/sys/dev/random/uint128.h head/sys/dev/random/unit_test.c head/sys/dev/random/unit_test.h head/sys/dev/random/yarrow.c head/sys/dev/random/yarrow.h head/sys/dev/rndtest/rndtest.c head/sys/dev/safe/safe.c head/sys/dev/syscons/scmouse.c head/sys/dev/syscons/syscons.c head/sys/dev/ubsec/ubsec.c head/sys/dev/virtio/random/virtio_random.c head/sys/dev/vt/vt_core.c head/sys/dev/vt/vt_sysmouse.c head/sys/fs/tmpfs/tmpfs_subr.c head/sys/kern/kern_intr.c head/sys/kern/kern_mib.c head/sys/kern/subr_bus.c head/sys/libkern/arc4random.c head/sys/libkern/random.c head/sys/mips/cavium/octeon_rnd.c head/sys/mips/conf/AR71XX_BASE head/sys/mips/conf/AR724X_BASE head/sys/mips/conf/AR91XX_BASE head/sys/mips/conf/AR933X_BASE head/sys/mips/conf/AR934X_BASE head/sys/mips/conf/PB92 head/sys/mips/conf/QCA955X_BASE head/sys/mips/conf/RT305X head/sys/modules/Makefile head/sys/modules/crypto/Makefile head/sys/net/if_ethersubr.c head/sys/net/if_tun.c head/sys/netgraph/ng_iface.c head/sys/sys/kernel.h head/sys/sys/random.h head/sys/ufs/ffs/ffs_inode.c head/sys/vm/uma_core.c Modified: head/UPDATING ============================================================================== --- head/UPDATING Tue Jun 30 16:26:13 2015 (r284958) +++ head/UPDATING Tue Jun 30 17:00:45 2015 (r284959) @@ -31,6 +31,41 @@ NOTE TO PEOPLE WHO THINK THAT FreeBSD 11 disable the most expensive debugging functionality run "ln -s 'abort:false,junk:false' /etc/malloc.conf".) +20150630: + The default kernel entropy-processing algorithm is now + Fortuna, replacing Yarrow. + + Assuming you have 'device random' in your kernel config + file, the configurations allow a kernel option to override + this default. You may choose *ONE* of: + + options RANDOM_YARROW # Legacy /dev/random algorithm. + options RANDOM_DUMMY # Blocking-only driver. + + If you have neither, you get Fortuna. For most people, + read no further, Fortuna will give a /dev/random that works + like it always used to, and the difference will be irrelevant. + + If you remove 'device random', you get *NO* kernel-processed + entopy at all. This may be acceptable to folks building + embedded systems, but has complications. Carry on reading, + and it is assumed you know what you need. + + *PLEASE* read random(4) and random(9) if you are in the + habit of tweeking kernel configs, and/or if you are a member + of the embedded community, wanting specific and not-usual + behaviour from your security subsystems. + + NOTE!! If you use RANDOM_DUMMY and/or have no 'device + random', you will NOT have a functioning /dev/random, and + many cryptographic features will not work, including SSH. + You may also find strange behaviour from the random(3) set + of library functions, in particular sranddev(3), srandomdev(3) + and arc4random(3). The reason for this is that the KERN_ARND + sysctl only returns entropy if it thinks it has some to + share, and with RANDOM_DUMMY or no 'device random' this + will never happen. + 20150623: An additional fix for the issue described in the 20150614 sendmail entry below has been been committed in revision 284717. Modified: head/share/man/man4/random.4 ============================================================================== --- head/share/man/man4/random.4 Tue Jun 30 16:26:13 2015 (r284958) +++ head/share/man/man4/random.4 Tue Jun 30 17:00:45 2015 (r284959) @@ -1,4 +1,4 @@ -.\" Copyright (c) 2001-2013 Mark R V Murray. All rights reserved. +.\" Copyright (c) 2001-2015 Mark R V Murray. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions @@ -23,7 +23,7 @@ .\" .\" $FreeBSD$ .\" -.Dd October 12, 2013 +.Dd June 30, 2015 .Dt RANDOM 4 .Os .Sh NAME @@ -37,31 +37,32 @@ The device returns an endless supply of random bytes when read. It also accepts and reads data -as any ordinary (and willing) file, -but discards data written to it. -The device will probe for -certain hardware entropy sources, -and use these in preference to the fallback, -which is a generator implemented in software. +as any ordinary file. .Pp -The software generator will start in an +The generator will start in an .Em unseeded state, and will block reads until -it is (re)seeded. +it is seeded for the first time. This may cause trouble at system boot when keys and the like are generated from -/dev/random +.Xr random 4 so steps should be taken to ensure a -reseed as soon as possible. -The -.Xr sysctl 8 -controlling the -.Em seeded -status (see below) may be used -if security is not an issue -or for convenience -during setup or development. +seeding as soon as possible. +.Pp +It is also possible +to read random bytes +by using the KERN_ARND sysctl. +On the command line +this could be done by +.Pp +.Dl "sysctl -x -B 16 kern.arandom" +.Pp +This sysctl will not return +random bytes unless +the +.Xr random 4 +is seeded. .Pp This initial seeding of random number generators @@ -90,101 +91,57 @@ To see the current settings of the softw .Nm device, use the command line: .Pp -.Dl sysctl kern.random +.Dl "sysctl kern.random" .Pp which results in something like: .Bd -literal -offset indent -kern.random.adaptors: yarrow,dummy -kern.random.active_adaptor: yarrow -kern.random.yarrow.gengateinterval: 10 -kern.random.yarrow.bins: 10 -kern.random.yarrow.fastthresh: 96 -kern.random.yarrow.slowthresh: 128 -kern.random.yarrow.slowoverthresh: 2 -kern.random.sys.seeded: 1 -kern.random.sys.harvest.ethernet: 1 -kern.random.sys.harvest.point_to_point: 1 -kern.random.sys.harvest.interrupt: 1 -kern.random.sys.harvest.swi: 1 +kern.random.fortuna.minpoolsize: 64 +kern.random.harvest.mask_symbolic: [HIGH_PERFORMANCE], ... ,CACHED +kern.random.harvest.mask_bin: 00111111111 +kern.random.harvest.mask: 511 +kern.random.random_sources: 'Intel Secure Key RNG' .Ed .Pp Other than -.Dl kern.random.adaptors -all settings are read/write. -.Pp -The -.Va kern.random.sys.seeded -variable indicates whether or not the -.Nm -device is in an acceptably secure state -as a result of reseeding. -If set to 0, -the device will block (on read) -until the next reseed -as a result of entropy harvesting. -A reseed will set the value to 1 (non-blocking). -.Pp -The -.Va kern.random.sys.harvest.ethernet -variable is used to select LAN traffic as an entropy source. -A 0 (zero) value means that LAN traffic -is not considered as an entropy source. -Set the variable to 1 (one) -if you wish to use LAN traffic for entropy harvesting. +.Dl kern.random.fortuna.minpoolsize +and +.Dl kern.random.harvest.mask +all settings are read-only. .Pp The -.Va kern.random.sys.harvest.point_to_point -variable is used to select serial line traffic as an entropy source. -(Serial line traffic includes PPP, SLIP and all tun0 traffic.) -A 0 (zero) value means such traffic -is not considered as an entropy source. -Set the variable to 1 (one) -if you wish to use it for entropy harvesting. +.Pa kern.random.fortuna.minpoolsize +sysctl is used +to set the seed threshhold. +A smaller number gives a faster seed, +but a less secure one. +In practice, +values between 64 and 256 +are acceptable. .Pp The -.Va kern.random.sys.harvest.interrupt -variable is used to select hardware interrupts +.Va kern.random.harvest.mask +bitmask is used to select +the possible entropy sources. +A 0 (zero) value means +the corresponding source +is not considered as an entropy source. -A 0 (zero) value means hardware interrupts -are not considered as an entropy source. -Set the variable to 1 (one) -if you wish to use them for entropy harvesting. -All hardware interrupt harvesting is set up by the -individual device drivers. -.Pp +Set the bit to 1 (one) +if you wish to use +that source. The -.Va kern.random.sys.harvest.swi -variable is used to select software interrupts -as an entropy source. -A 0 (zero) value means software interrupts -are not considered as an entropy source. -Set the variable to 1 (one) -if you wish to use them for entropy harvesting. -.Pp -The other variables are explained in the paper describing the -.Em Yarrow -algorithm at -.Pa http://www.schneier.com/yarrow.html . -.Pp -These variables are all limited -in terms of the values they may contain: -.Bl -tag -width "kern.random.yarrow.gengateinterval" -compact -offset indent -.It Va kern.random.yarrow.gengateinterval -.Bq 4..64 -.It Va kern.random.yarrow.bins -.Bq 2..16 -.It Va kern.random.yarrow.fastthresh -.Bq 64..256 -.It Va kern.random.yarrow.slowthresh -.Bq 64..256 -.It Va kern.random.yarrow.slowoverthresh -.Bq 1..5 -.El -.Pp -Internal -.Xr sysctl 3 -handlers force the above variables -into the stated ranges. +.Va kern.random.harvest.mask_bin +and +.Va kern.random.harvest.mask_symbolic +sysctl +can be used confirm +that your choices are correct. +Note that disabled items +in the latter item +are listed in square brackets. +See +.Xr random_harvest 9 +for more on the harvesting of entropy. .Sh RANDOMNESS The use of randomness in the field of computing is a rather subtle issue because randomness means @@ -308,23 +265,36 @@ so its use is discouraged. .Xr RAND_add 3 , .Xr RAND_bytes 3 , .Xr random 3 , -.Xr sysctl 8 +.Xr sysctl 8 , +.Xr random 9 +.Rs +.%A Ferguson +.%A Schneier +.%A Kohno +.%B Cryptography Engineering +.%I Wiley +.%O ISBN 978-0-470-47424-2 +.Re .Sh HISTORY A .Nm device appeared in .Fx 2.2 . -The early version was taken from Theodore Ts'o's entropy driver for Linux. The current software implementation, introduced in -.Fx 5.0 , -is a complete rewrite by +.Fx 10.0 , +is by .An Mark R V Murray , and is an implementation of the -.Em Yarrow -algorithm by Bruce Schneier, +.Em Fortuna +algorithm by Ferguson .Em et al . -Significant infrastructure work was done by Arthur Mesh. -.Pp -The author gratefully acknowledges -significant assistance from VIA Technologies, Inc. +It replaces the previous +.Em Yarrow +implementation, +introduced in +.Fx 5.0 . +The older +.Em Yarrow +algorithm remains available +as a compile-time fallback. Modified: head/share/man/man9/random.9 ============================================================================== --- head/share/man/man9/random.9 Tue Jun 30 16:26:13 2015 (r284958) +++ head/share/man/man9/random.9 Tue Jun 30 17:00:45 2015 (r284959) @@ -1,4 +1,6 @@ .\" +.\" Copyright (c) 2015 +.\" Mark R V Murray .\" Copyright (c) 2000 .\" The Regents of the University of California. All rights reserved. .\" @@ -26,7 +28,7 @@ .\" .\" $FreeBSD$ .\" " -.Dd September 25, 2000 +.Dd June 30, 2015 .Dt RANDOM 9 .Os .Sh NAME @@ -53,11 +55,12 @@ .Sh DESCRIPTION The .Fn random -function will by default produce a sequence of numbers that can be duplicated +function will by default produce +a sequence of numbers +that can be duplicated by calling .Fn srandom -with -.Ql 1 +with some constant as the .Fa seed . The @@ -67,19 +70,28 @@ function may be called with any arbitrar value to get slightly more unpredictable numbers. It is important to remember that the .Fn random -function is entirely predictable, and is therefore not of use where -knowledge of the sequence of numbers may be of benefit to an attacker. +function is entirely predictable, +and is therefore not of use where +knowledge of the sequence of numbers +may be of benefit to an attacker. .Pp The .Fn arc4rand -function will return very good quality random numbers, slightly better -suited for security-related purposes. +function will return very good quality random numbers, +better suited +for security-related purposes. The random numbers from .Fn arc4rand -are seeded from the entropy device if it is available. -Automatic reseeds happen after a certain timeinterval and after a -certain number of bytes have been delivered. -A forced reseed can be forced by passing a non-zero value in the +are seeded from the entropy device +if it is available. +Automatic reseeds happen +after a certain timeinterval +and after a certain number of bytes +have been delivered. +A forced reseed +can be forced +by passing a non-zero +value in the .Fa reseed argument. .Pp @@ -90,19 +102,24 @@ if it has been loaded. If the entropy device is not loaded, then the .Fa buffer -is filled with output generated by -.Fn random . +is ignored +and zero is returned. The .Fa buffer is filled with no more than .Fa count bytes. -It is advised that +It is strongly advised that .Fn read_random -is not used; instead use +is not used; +instead use .Fn arc4rand +unless it is +necessary to know +that no entropy +has been returned. .Pp -All the bits generated by +All the bits returned by .Fn random , .Fn arc4rand and @@ -120,32 +137,38 @@ to return a 32 bit pseudo-random integer .Sh RETURN VALUES The .Fn random -function -uses a non-linear additive feedback random number generator employing a -default table of size 31 long integers to return successive pseudo-random +function uses +a non-linear additive feedback random number generator +employing a default table +of size 31 +containing long integers +to return successive pseudo-random numbers in the range from 0 to .if t 2\u\s731\s10\d\(mi1. .if n (2**31)\(mi1. -The period of this random number generator is very large, approximately +The period of this random number generator +is very large, +approximately .if t 16\(mu(2\u\s731\s10\d\(mi1). .if n 16*((2**31)\(mi1). .Pp The .Fn arc4rand -function uses the RC4 algorithm to generate successive pseudo-random -bytes. +function uses the RC4 algorithm +to generate successive pseudo-random bytes. The .Fn arc4random -function -uses +function uses .Fn arc4rand -to generate pseudo-random numbers in the range from 0 to +to generate pseudo-random numbers +in the range from 0 to .if t 2\u\s732\s10\d\(mi1. .if n (2**32)\(mi1. .Pp The .Fn read_random -function returns the number of bytes placed in +function returns +the number of bytes placed in .Fa buffer . .Sh AUTHORS .An Dan Moschuk Modified: head/share/man/man9/random_harvest.9 ============================================================================== --- head/share/man/man9/random_harvest.9 Tue Jun 30 16:26:13 2015 (r284958) +++ head/share/man/man9/random_harvest.9 Tue Jun 30 17:00:45 2015 (r284959) @@ -1,5 +1,5 @@ .\" -.\" Copyright (c) 2002 Mark R V Murray +.\" Copyright (c) 2002-2015 Mark R V Murray .\" All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without @@ -25,7 +25,7 @@ .\" .\" $FreeBSD$ .\" -.Dd February 6, 2002 +.Dd June 30, 2015 .Dt RANDOM_HARVEST 9 .Os .Sh NAME @@ -35,59 +35,93 @@ .In sys/types.h .In sys/random.h .Ft void -.Fo random_harvest +.Fo random_harvest_direct +.Fa "void *entropy" +.Fa "u_int size" +.Fa "u_int bits" +.Fa "enum esource source" +.Fc +.Ft void +.Fo random_harvest_fast +.Fa "void *entropy" +.Fa "u_int size" +.Fa "u_int bits" +.Fa "enum esource source" +.Fc +.Ft void +.Fo random_harvest_queue .Fa "void *entropy" .Fa "u_int size" .Fa "u_int bits" -.Fa "u_int frac" .Fa "enum esource source" .Fc .Sh DESCRIPTION The -.Fn random_harvest -function is used by device drivers +.Fn random_harvest_* +functions are used by device drivers and other kernel processes to pass data that is considered (at least partially) stochastic to the entropy device. .Pp -The caller should pass a pointer (to no more than 16 bytes) of -the +The caller should pass +a pointer pointing to the .Dq random data in .Fa entropy . The argument .Fa size contains the number of bytes pointed to. -The caller should +The +.Fa source +is chosen from one of +the values enumerated in +.Pa sys/dev/random.h . +and is used to indicate the source of the entropy. +.Pp +The +.Fo random_harvest_direct +.Fc +variant is used +for early harvesting +before any multitasking +is enabled. +.Pp +The +.Fn random_harvest_fast +variant is used +by sources that +should not take +a performance hit +from harvesting, +as they are high-rate +sources. +Some entropy is sacrificed, +but the hig rate of supply +will compensate for this. +.Pp +The +.Fn random_harvest_queue +variant is used +for general harvesting +and is the default +choice for most entropy sources +such as interrupts +or console events. +.Pp +The +.Fa bits +argument is only used +by the deprecated Yarrow algorithm. +For compatibility, +the caller should .Em "very conservatively" estimate the number of random bits in the sample, and pass this in -.Fa bits -or -.Fa frac . -If the estimated number of bits per sample is an integer, then -.Fa bits -is used, and -.Fa frac -is 0. -Otherwise, -for low-entropy samples, -.Dq fractional -entropy can be supplied in -.Fa frac . -(This is considered to be -.Fa frac / -1024 bits of entropy.) -The -.Fa source -is chosen from -.Dv RANDOM_WRITE , RANDOM_KEYBOARD , RANDOM_MOUSE , RANDOM_NET -and -.Dv RANDOM_INTERRUPT , -and is used to indicate the source of the entropy. +.Fa bits . .Pp -Interrupt harvesting has been simplified +Interrupt harvesting has been +in part simplified simplified for the kernel programmer. If a device driver registers an interrupt handler with @@ -101,6 +135,7 @@ bit in the .Fa flags argument to have that interrupt source be used for entropy harvesting. +This should be done wherever practicable. .Sh SEE ALSO .Xr random 4 , .Xr BUS_SETUP_INTR 9 Modified: head/sys/conf/files ============================================================================== --- head/sys/conf/files Tue Jun 30 16:26:13 2015 (r284958) +++ head/sys/conf/files Tue Jun 30 17:00:45 2015 (r284959) @@ -528,14 +528,14 @@ crypto/des/des_ecb.c optional crypto | crypto/des/des_setkey.c optional crypto | ipsec | netsmb crypto/rc4/rc4.c optional netgraph_mppc_encryption | kgssapi crypto/rijndael/rijndael-alg-fst.c optional crypto | geom_bde | \ - ipsec | random | wlan_ccmp -crypto/rijndael/rijndael-api-fst.c optional geom_bde | random + ipsec | random random_yarrow | random !random_yarrow !random_dummy | wlan_ccmp +crypto/rijndael/rijndael-api-fst.c optional geom_bde | random random_yarrow | random !random_yarrow !random_dummy crypto/rijndael/rijndael-api.c optional crypto | ipsec | wlan_ccmp crypto/sha1.c optional carp | crypto | ipsec | \ netgraph_mppc_encryption | sctp -crypto/sha2/sha2.c optional crypto | geom_bde | ipsec | random | \ +crypto/sha2/sha2.c optional crypto | geom_bde | ipsec | random random_yarrow | random !random_yarrow !random_dummy | \ sctp | zfs -crypto/sha2/sha256c.c optional crypto | geom_bde | ipsec | random | \ +crypto/sha2/sha256c.c optional crypto | geom_bde | ipsec | random random_yarrow | random !random_yarrow !random_dummy | \ sctp | zfs crypto/siphash/siphash.c optional inet | inet6 crypto/siphash/siphash_test.c optional inet | inet6 @@ -2139,15 +2139,12 @@ rt2860.fw optional rt2860fw | ralfw \ compile-with "${NORMAL_FW}" \ no-obj no-implicit-rule \ clean "rt2860.fw" -dev/random/randomdev.c standard -dev/random/random_adaptors.c standard -dev/random/dummy_rng.c standard -dev/random/live_entropy_sources.c standard -dev/random/random_harvestq.c standard -dev/random/randomdev_soft.c optional random -dev/random/yarrow.c optional random -dev/random/fortuna.c optional random -dev/random/hash.c optional random +dev/random/randomdev_none.c optional !random +dev/random/randomdev.c optional random +dev/random/random_harvestq.c optional random random_yarrow | random !random_dummy +dev/random/yarrow.c optional random random_yarrow +dev/random/fortuna.c optional random !random_yarrow !random_dummy +dev/random/hash.c optional random random_yarrow | random !random_dummy dev/rc/rc.c optional rc dev/re/if_re.c optional re dev/rl/if_rl.c optional rl pci Modified: head/sys/conf/options ============================================================================== --- head/sys/conf/options Tue Jun 30 16:26:13 2015 (r284958) +++ head/sys/conf/options Tue Jun 30 17:00:45 2015 (r284959) @@ -939,9 +939,16 @@ RACCT_DEFAULT_TO_DISABLED opt_global.h RCTL opt_global.h # Random number generator(s) +# The DEBUG option is in global.h as the random harvesting +# puts probes all over the place, and it makes little sense +# to pollute these headers with an extra include. +# the DUMMY option is in global.h because it is used to +# turn off harvesting all over the kernel. +RANDOM_DEBUG opt_global.h +# Which CSPRNG hashes we get. +# These are mutually exclusive. With neither, Fortuna is selected. +RANDOM_DUMMY opt_global.h RANDOM_YARROW opt_random.h -RANDOM_FORTUNA opt_random.h -RANDOM_DEBUG opt_random.h # Intel em(4) driver EM_MULTIQUEUE opt_em.h Modified: head/sys/dev/glxsb/glxsb.c ============================================================================== --- head/sys/dev/glxsb/glxsb.c Tue Jun 30 16:26:13 2015 (r284958) +++ head/sys/dev/glxsb/glxsb.c Tue Jun 30 17:00:45 2015 (r284959) @@ -476,7 +476,8 @@ glxsb_rnd(void *v) if (status & SB_RNS_TRNG_VALID) { value = bus_read_4(sc->sc_sr, SB_RANDOM_NUM); /* feed with one uint32 */ - random_harvest(&value, sizeof(value), 32/2, RANDOM_PURE_GLXSB); + /* MarkM: FIX!! Check that this does not swamp the harvester! */ + random_harvest_queue(&value, sizeof(value), 32/2, RANDOM_PURE_GLXSB); } callout_reset(&sc->sc_rngco, sc->sc_rnghz, glxsb_rnd, sc); Modified: head/sys/dev/hifn/hifn7751.c ============================================================================== --- head/sys/dev/hifn/hifn7751.c Tue Jun 30 16:26:13 2015 (r284958) +++ head/sys/dev/hifn/hifn7751.c Tue Jun 30 17:00:45 2015 (r284959) @@ -258,7 +258,8 @@ hifn_partname(struct hifn_softc *sc) static void default_harvest(struct rndtest_state *rsp, void *buf, u_int count) { - random_harvest(buf, count, count*NBBY/2, RANDOM_PURE_HIFN); + /* MarkM: FIX!! Check that this does not swamp the harvester! */ + random_harvest_queue(buf, count, count*NBBY/2, RANDOM_PURE_HIFN); } static u_int Modified: head/sys/dev/random/build.sh ============================================================================== --- head/sys/dev/random/build.sh Tue Jun 30 16:26:13 2015 (r284958) +++ head/sys/dev/random/build.sh Tue Jun 30 17:00:45 2015 (r284959) @@ -1,3 +1,29 @@ +#!/bin/sh +#- +# Copyright (c) 2013-2015 Mark R V Murray +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer +# in this position and unchanged. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +# OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +# IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# # $FreeBSD$ # # Basic script to build crude unit tests. @@ -11,6 +37,7 @@ cc -g -O0 -pthread -DRANDOM_DEBUG -DRAND ../../crypto/rijndael/rijndael-alg-fst.c \ ../../crypto/sha2/sha2.c \ ../../crypto/sha2/sha256c.c \ + -lz \ -o yunit_test cc -g -O0 -pthread -DRANDOM_DEBUG -DRANDOM_FORTUNA \ -I../.. -lstdthreads -Wall \ @@ -21,4 +48,5 @@ cc -g -O0 -pthread -DRANDOM_DEBUG -DRAND ../../crypto/rijndael/rijndael-alg-fst.c \ ../../crypto/sha2/sha2.c \ ../../crypto/sha2/sha256c.c \ + -lz \ -o funit_test Modified: head/sys/dev/random/fortuna.c ============================================================================== --- head/sys/dev/random/fortuna.c Tue Jun 30 16:26:13 2015 (r284958) +++ head/sys/dev/random/fortuna.c Tue Jun 30 17:00:45 2015 (r284959) @@ -1,5 +1,5 @@ /*- - * Copyright (c) 2013-2014 Mark R V Murray + * Copyright (c) 2013-2015 Mark R V Murray * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -25,25 +25,24 @@ * */ -/* This implementation of Fortuna is based on the descriptions found in - * ISBN 0-471-22357-3 "Practical Cryptography" by Ferguson and Schneier - * ("F&S"). - * - * The above book is superseded by ISBN 978-0-470-47424-2 "Cryptography - * Engineering" by Ferguson, Schneier and Kohno ("FS&K"). The code has - * not yet fully caught up with FS&K. +/* + * This implementation of Fortuna is based on the descriptions found in + * ISBN 978-0-470-47424-2 "Cryptography Engineering" by Ferguson, Schneier + * and Kohno ("FS&K"). */ #include __FBSDID("$FreeBSD$"); -#ifdef _KERNEL -#include "opt_random.h" +#include +#ifdef _KERNEL #include #include +#include #include #include +#include #include #include #include @@ -56,13 +55,10 @@ __FBSDID("$FreeBSD$"); #include #include -#include #include #include #include #else /* !_KERNEL */ -#include -#include #include #include #include @@ -79,351 +75,405 @@ __FBSDID("$FreeBSD$"); #include #endif /* _KERNEL */ -#if !defined(RANDOM_YARROW) && !defined(RANDOM_FORTUNA) -#define RANDOM_YARROW -#elif defined(RANDOM_YARROW) && defined(RANDOM_FORTUNA) -#error "Must define either RANDOM_YARROW or RANDOM_FORTUNA" -#endif - -#if defined(RANDOM_FORTUNA) - -#define NPOOLS 32 -#define MINPOOLSIZE 64 -#define DEFPOOLSIZE 256 -#define MAXPOOLSIZE 65536 - -/* This algorithm (and code) presumes that KEYSIZE is twice as large as BLOCKSIZE */ -CTASSERT(BLOCKSIZE == sizeof(uint128_t)); -CTASSERT(KEYSIZE == 2*BLOCKSIZE); - -/* This is the beastie that needs protecting. It contains all of the - * state that we are excited about. - * Exactly one is instantiated. +/* Defined in FS&K */ +#define RANDOM_FORTUNA_NPOOLS 32 /* The number of accumulation pools */ +#define RANDOM_FORTUNA_DEFPOOLSIZE 64 /* The default pool size/length for a (re)seed */ +#define RANDOM_FORTUNA_MAX_READ (1 << 20) /* Max bytes in a single read */ + +/* + * The allowable range of RANDOM_FORTUNA_DEFPOOLSIZE. The default value is above. + * Making RANDOM_FORTUNA_DEFPOOLSIZE too large will mean a long time between reseeds, + * and too small may compromise initial security but get faster reseeds. + */ +#define RANDOM_FORTUNA_MINPOOLSIZE 16 +#define RANDOM_FORTUNA_MAXPOOLSIZE UINT_MAX +CTASSERT(RANDOM_FORTUNA_MINPOOLSIZE <= RANDOM_FORTUNA_DEFPOOLSIZE); +CTASSERT(RANDOM_FORTUNA_DEFPOOLSIZE <= RANDOM_FORTUNA_MAXPOOLSIZE); + +/* This algorithm (and code) presumes that RANDOM_KEYSIZE is twice as large as RANDOM_BLOCKSIZE */ +CTASSERT(RANDOM_BLOCKSIZE == sizeof(uint128_t)); +CTASSERT(RANDOM_KEYSIZE == 2*RANDOM_BLOCKSIZE); + +/* + * This is the beastie that needs protecting. It contains all of the + * state that we are excited about. Exactly one is instantiated. */ static struct fortuna_state { - /* P_i */ - struct pool { - u_int length; - struct randomdev_hash hash; - } pool[NPOOLS]; - - /* ReseedCnt */ - u_int reseedcount; - - /* C - 128 bits */ - union { - uint8_t byte[BLOCKSIZE]; - uint128_t whole; - } counter; - - /* K */ - struct randomdev_key key; - - /* Extras */ - u_int minpoolsize; - + struct fs_pool { /* P_i */ + u_int fsp_length; /* Only the first one is used by Fortuna */ + struct randomdev_hash fsp_hash; + } fs_pool[RANDOM_FORTUNA_NPOOLS]; + u_int fs_reseedcount; /* ReseedCnt */ + uint128_t fs_counter; /* C */ + struct randomdev_key fs_key; /* K */ + u_int fs_minpoolsize; /* Extras */ /* Extras for the OS */ - #ifdef _KERNEL /* For use when 'pacing' the reseeds */ - sbintime_t lasttime; + sbintime_t fs_lasttime; #endif + /* Reseed lock */ + mtx_t fs_mtx; } fortuna_state; -/* The random_reseed_mtx mutex protects seeding and polling/blocking. */ -static mtx_t random_reseed_mtx; +#ifdef _KERNEL +static struct sysctl_ctx_list random_clist; +RANDOM_CHECK_UINT(fs_minpoolsize, RANDOM_FORTUNA_MINPOOLSIZE, RANDOM_FORTUNA_MAXPOOLSIZE); +#else +static uint8_t zero_region[RANDOM_ZERO_BLOCKSIZE]; +#endif -static struct fortuna_start_cache { - uint8_t junk[PAGE_SIZE]; - size_t length; - struct randomdev_hash hash; -} fortuna_start_cache; +static void random_fortuna_pre_read(void); +static void random_fortuna_read(uint8_t *, u_int); +static void random_fortuna_post_read(void); +static void random_fortuna_write(uint8_t *, u_int); +static void random_fortuna_reseed(void); +static int random_fortuna_seeded(void); +static void random_fortuna_process_event(struct harvest_event *); #ifdef _KERNEL -static struct sysctl_ctx_list random_clist; -RANDOM_CHECK_UINT(minpoolsize, MINPOOLSIZE, MAXPOOLSIZE); +/* Interface to Adaptors system */ +struct random_algorithm random_alg_context = { + .ra_ident = "Fortuna", + .ra_pre_read = random_fortuna_pre_read, + .ra_read = random_fortuna_read, + .ra_post_read = random_fortuna_post_read, + .ra_write = random_fortuna_write, + .ra_reseed = random_fortuna_reseed, + .ra_seeded = random_fortuna_seeded, + .ra_event_processor = random_fortuna_process_event, + .ra_poolcount = RANDOM_FORTUNA_NPOOLS, +}; #endif -void -random_fortuna_init_alg(void) +/* ARGSUSED */ +static void +random_fortuna_init_alg(void *unused __unused) { int i; #ifdef _KERNEL struct sysctl_oid *random_fortuna_o; #endif - memset(fortuna_start_cache.junk, 0, sizeof(fortuna_start_cache.junk)); - fortuna_start_cache.length = 0U; - randomdev_hash_init(&fortuna_start_cache.hash); - - /* Set up a lock for the reseed process */ -#ifdef _KERNEL - mtx_init(&random_reseed_mtx, "reseed mutex", NULL, MTX_DEF); -#else /* !_KERNEL */ - mtx_init(&random_reseed_mtx, mtx_plain); -#endif /* _KERNEL */ - -#ifdef _KERNEL - /* Fortuna parameters. Do not adjust these unless you have + RANDOM_RESEED_INIT_LOCK(); + /* + * Fortuna parameters. Do not adjust these unless you have * have a very good clue about what they do! */ + fortuna_state.fs_minpoolsize = RANDOM_FORTUNA_DEFPOOLSIZE; +#ifdef _KERNEL + fortuna_state.fs_lasttime = 0; random_fortuna_o = SYSCTL_ADD_NODE(&random_clist, SYSCTL_STATIC_CHILDREN(_kern_random), OID_AUTO, "fortuna", CTLFLAG_RW, 0, "Fortuna Parameters"); - SYSCTL_ADD_PROC(&random_clist, SYSCTL_CHILDREN(random_fortuna_o), OID_AUTO, - "minpoolsize", CTLTYPE_UINT|CTLFLAG_RW, - &fortuna_state.minpoolsize, DEFPOOLSIZE, - random_check_uint_minpoolsize, "IU", - "Minimum pool size necessary to cause a reseed automatically"); - - fortuna_state.lasttime = 0U; + "minpoolsize", CTLTYPE_UINT | CTLFLAG_RWTUN, + &fortuna_state.fs_minpoolsize, RANDOM_FORTUNA_DEFPOOLSIZE, + random_check_uint_fs_minpoolsize, "IU", + "Minimum pool size necessary to cause a reseed"); + KASSERT(fortuna_state.fs_minpoolsize > 0, ("random: Fortuna threshold must be > 0 at startup")); #endif - fortuna_state.minpoolsize = DEFPOOLSIZE; - - /* F&S - InitializePRNG() */ - - /* F&S - P_i = \epsilon */ - for (i = 0; i < NPOOLS; i++) { - randomdev_hash_init(&fortuna_state.pool[i].hash); - fortuna_state.pool[i].length = 0U; + /*- + * FS&K - InitializePRNG() + * - P_i = \epsilon + * - ReseedCNT = 0 + */ + for (i = 0; i < RANDOM_FORTUNA_NPOOLS; i++) { + randomdev_hash_init(&fortuna_state.fs_pool[i].fsp_hash); + fortuna_state.fs_pool[i].fsp_length = 0; } - - /* F&S - ReseedCNT = 0 */ - fortuna_state.reseedcount = 0U; - - /* F&S - InitializeGenerator() */ - - /* F&S - C = 0 */ - uint128_clear(&fortuna_state.counter.whole); - - /* F&S - K = 0 */ - memset(&fortuna_state.key, 0, sizeof(fortuna_state.key)); + fortuna_state.fs_reseedcount = 0; *** DIFF OUTPUT TRUNCATED AT 1000 LINES ***