diff --git a/libgcrypt-1.4.5-fips-cfgrandom.patch b/libgcrypt-1.4.5-fips-cfgrandom.patch deleted file mode 100644 index 4fa689d..0000000 --- a/libgcrypt-1.4.5-fips-cfgrandom.patch +++ /dev/null @@ -1,126 +0,0 @@ -diff -up libgcrypt-1.4.5/random/random-fips.c.cfgrandom libgcrypt-1.4.5/random/random-fips.c ---- libgcrypt-1.4.5/random/random-fips.c.cfgrandom 2011-05-06 10:58:55.000000000 +0200 -+++ libgcrypt-1.4.5/random/random-fips.c 2011-05-06 10:58:55.000000000 +0200 -@@ -27,10 +27,10 @@ - There are 3 random context which map to the different levels of - random quality: - -- Generator Seed and Key Kernel entropy (init/reseed) -- ------------------------------------------------------------ -- GCRY_VERY_STRONG_RANDOM /dev/urandom 256/128 bits -- GCRY_STRONG_RANDOM /dev/urandom 256/128 bits -+ Generator Seed and Key Kernel entropy (init/reseed) -+ --------------------------------------------------------------------------------------- -+ GCRY_VERY_STRONG_RANDOM /etc/gcrypt/rngseed+/dev/urandom 256/128 bits -+ GCRY_STRONG_RANDOM /etc/gcrypt/rngseed+/dev/urandom 256/128 bits - gcry_create_nonce GCRY_STRONG_RANDOM n/a - - All random generators return their data in 128 bit blocks. If the -@@ -40,7 +40,10 @@ - (SEED_TTL) output blocks; the re-seeding is disabled in test mode. - - The GCRY_VERY_STRONG_RANDOM and GCRY_STRONG_RANDOM generators are -- keyed and seeded from the /dev/urandom device. -+ keyed and seeded with data that is loaded from the /etc/gcrypt/rngseed -+ if the device or symlink to device exists xored with the data -+ from the /dev/urandom device. This allows the system administrator -+ to always seed the RNGs from /dev/random if it is required. - - The gcry_create_nonce generator is keyed and seeded from the - GCRY_STRONG_RANDOM generator. It may also block if the -@@ -561,7 +564,7 @@ get_entropy (size_t nbytes) - #if USE_RNDLINUX - rc = _gcry_rndlinux_gather_random (entropy_collect_cb, 0, - X931_AES_KEYLEN, -- GCRY_STRONG_RANDOM); -+ -1); - #elif USE_RNDW32 - do - { -diff -up libgcrypt-1.4.5/random/rndlinux.c.cfgrandom libgcrypt-1.4.5/random/rndlinux.c ---- libgcrypt-1.4.5/random/rndlinux.c.cfgrandom 2009-04-02 11:25:34.000000000 +0200 -+++ libgcrypt-1.4.5/random/rndlinux.c 2011-05-06 11:35:39.000000000 +0200 -@@ -35,7 +35,9 @@ - #include "g10lib.h" - #include "rand-internal.h" - --static int open_device ( const char *name ); -+#define NAME_OF_CFG_RNGSEED "/etc/gcrypt/rngseed" -+ -+static int open_device ( const char *name, int fatal ); - - - static int -@@ -56,13 +58,17 @@ set_cloexec_flag (int fd) - * Used to open the /dev/random devices (Linux, xBSD, Solaris (if it exists)). - */ - static int --open_device ( const char *name ) -+open_device ( const char *name, int fatal ) - { - int fd; - - fd = open ( name, O_RDONLY ); - if ( fd == -1 ) -- log_fatal ("can't open %s: %s\n", name, strerror(errno) ); -+ { -+ if (! fatal) -+ return fd; -+ log_fatal ("can't open %s: %s\n", name, strerror(errno) ); -+ } - - if (set_cloexec_flag (fd)) - log_error ("error setting FD_CLOEXEC on fd %d: %s\n", -@@ -91,11 +97,13 @@ _gcry_rndlinux_gather_random (void (*add - { - static int fd_urandom = -1; - static int fd_random = -1; -+ static int fd_configured = -1; - int fd; - int n; - int warn=0; - byte buffer[768]; - size_t n_hw; -+ size_t orig_length = length; - - /* First read from a hardware source. However let it account only - for up to 50% of the requested bytes. */ -@@ -106,16 +114,26 @@ _gcry_rndlinux_gather_random (void (*add - length -= n_hw; - - /* Open the requested device. */ -+ -+ if (level == -1) -+ { -+ if (fd_configured == -1) -+ fd_configured = open_device ( NAME_OF_CFG_RNGSEED, 0 ); -+ fd = fd_configured; -+ if (fd == -1) -+ level = 1; -+ } -+ - if (level >= 2) - { - if( fd_random == -1 ) -- fd_random = open_device ( NAME_OF_DEV_RANDOM ); -+ fd_random = open_device ( NAME_OF_DEV_RANDOM, 1 ); - fd = fd_random; - } -- else -+ else if (level != -1) - { - if( fd_urandom == -1 ) -- fd_urandom = open_device ( NAME_OF_DEV_URANDOM ); -+ fd_urandom = open_device ( NAME_OF_DEV_URANDOM, 1 ); - fd = fd_urandom; - } - -@@ -163,5 +181,8 @@ _gcry_rndlinux_gather_random (void (*add - } - memset(buffer, 0, sizeof(buffer) ); - -+ if (level == -1) -+ _gcry_rndlinux_gather_random(add, origin, orig_length, 1); -+ - return 0; /* success */ - } diff --git a/libgcrypt-1.4.6-cavs.patch b/libgcrypt-1.4.6-cavs.patch index c41e900..b23129b 100644 --- a/libgcrypt-1.4.6-cavs.patch +++ b/libgcrypt-1.4.6-cavs.patch @@ -51,7 +51,7 @@ diff -up libgcrypt-1.4.6/cipher/dsa.c.cavs libgcrypt-1.4.6/cipher/dsa.c diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_driver.pl --- libgcrypt-1.4.6/tests/cavs_driver.pl.cavs 2009-04-02 11:25:34.000000000 +0200 -+++ libgcrypt-1.4.6/tests/cavs_driver.pl 2011-05-27 21:32:14.000000000 +0200 ++++ libgcrypt-1.4.6/tests/cavs_driver.pl 2011-06-20 20:00:13.000000000 +0200 @@ -1,9 +1,11 @@ #!/usr/bin/env perl # @@ -178,22 +178,22 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr -sub libgcrypt_dsa_pqggen($) { +sub libgcrypt_dsa_pqggen($$$) { - my $mod = shift; ++ my $mod = shift; + my $qsize = shift; + my $seed = shift; + + my $program = "fipsdrv --keysize $mod --qsize $qsize dsa-pqg-gen"; + return pipe_through_program($seed, $program); +} - -- my $program = "fipsdrv --keysize $mod dsa-pqg-gen"; ++ +sub libgcrypt_dsa_ggen($$$$) { -+ my $mod = shift; + my $mod = shift; + my $qsize = shift; + my $p = shift; + my $q = shift; + my $domain = "(domain (p #$p#)(q #$q#))"; -+ + +- my $program = "fipsdrv --keysize $mod dsa-pqg-gen"; + my $program = "fipsdrv --keysize $mod --qsize $qsize --key \'$domain\' dsa-g-gen"; return pipe_through_program("", $program); } @@ -303,7 +303,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr # now change the counter to decimal as CAVS wants decimal # counter value although all other is HEX -@@ -1525,15 +1617,149 @@ sub dsa_pqggen_driver($$) { +@@ -1525,15 +1617,166 @@ sub dsa_pqggen_driver($$) { $out .= "P = $P\n"; $out .= "Q = $Q\n"; @@ -341,6 +341,23 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr + return $out; +} + ++sub hexcomp($$) { ++ my $a = lc shift; ++ my $b = lc shift; ++ ++ if (length $a < length $b) { ++ my $c = $a; ++ $a = $b; ++ $b = $a; ++ } ++ ++ while (length $b < length $a) { ++ $b = "00$b"; ++ } ++ ++ return $a eq $b; ++} ++ +# DSA PQVer test +# $1 modulus size +# $2 q size @@ -369,7 +386,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr + $out .= "Seed = $seed\n"; + $out .= "c = $c\n"; + -+ if ($P eq $p && $Q eq $q && $seed eq lc $seed2 && $c eq $c2) { ++ if (hexcomp($P, $p) && hexcomp($Q, $q) && hexcomp($seed, $seed2) && $c == $c2) { + $out .= "Result = P\n\n"; + } + else { @@ -413,8 +430,8 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr + + $c2 = hex($c2); + -+ if ($P eq $p && $Q eq $q && $G eq $g && $seed eq lc $seed2 && -+ $c eq $c2 && hex($h) == hex($h2)) { ++ if (hexcomp($P, $p) && hexcomp($Q, $q) && hexcomp($G, $g) && hexcomp($seed, $seed2) && ++ $c == $c2 && hex($h) == hex($h2)) { + $out .= "Result = P\n\n"; + } + else { @@ -457,7 +474,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr # DSA SigGen test # $1: Message to be signed in hex form -@@ -1658,12 +1884,16 @@ sub parse($$) { +@@ -1658,12 +1901,16 @@ sub parse($$) { my $klen = ""; my $tlen = ""; my $modulus = ""; @@ -474,7 +491,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr my $xp1 = ""; my $xp2 = ""; my $Xp = ""; -@@ -1700,7 +1930,7 @@ sub parse($$) { +@@ -1700,7 +1947,7 @@ sub parse($$) { ##### Extract cipher # XXX there may be more - to be added @@ -483,7 +500,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr if ($tmpline =~ /CBC/) { $mode="cbc"; } elsif ($tmpline =~ /ECB/) { $mode="ecb"; } elsif ($tmpline =~ /OFB/) { $mode="ofb"; } -@@ -1749,7 +1979,15 @@ sub parse($$) { +@@ -1749,7 +1996,15 @@ sub parse($$) { if ($tt == 0) { ##### Identify the test type @@ -500,7 +517,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr $tt = 13; die "Interface function rsa_derive for RSA key generation not defined for tested library" if (!defined($rsa_derive)); -@@ -1760,11 +1998,11 @@ sub parse($$) { +@@ -1760,11 +2015,11 @@ sub parse($$) { } elsif ($tmpline =~ /SigGen/ && $opt{'D'}) { $tt = 11; die "Interface function dsa_sign or gen_dsakey for DSA sign not defined for tested library" @@ -514,7 +531,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr } elsif ($tmpline =~ /Hash sizes tested/) { $tt = 9; die "Interface function hmac for HMAC testing not defined for tested library" -@@ -1792,7 +2030,7 @@ sub parse($$) { +@@ -1792,7 +2047,7 @@ sub parse($$) { } elsif ($tmpline =~ /Monte|MCT|Carlo/) { $tt = 2; die "Interface function state_cipher for Stateful Cipher operation defined for tested library" @@ -523,7 +540,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr } elsif ($cipher =~ /^sha/) { $tt = 3; die "Interface function hash for Hashing not defined for tested library" -@@ -1875,18 +2113,44 @@ sub parse($$) { +@@ -1875,18 +2130,44 @@ sub parse($$) { die "Msg/Seed seen twice - input file crap" if ($pt ne ""); $pt=$2; } @@ -572,7 +589,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr # XXX maybe a secure temp file name is better here # but since it is not run on a security sensitive # system, I hope that this is fine -@@ -1932,11 +2196,16 @@ sub parse($$) { +@@ -1932,11 +2213,16 @@ sub parse($$) { if ($tlen ne ""); $tlen=$1; } @@ -590,7 +607,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr elsif ($line =~ /^P\s*=\s*(.*)/) { #DSA SigVer die "P seen twice - check input file" if ($capital_p); -@@ -1965,6 +2234,16 @@ sub parse($$) { +@@ -1965,6 +2251,16 @@ sub parse($$) { if ($capital_r); $capital_r = $1; } @@ -607,7 +624,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr elsif ($line =~ /^xp1\s*=\s*(.*)/) { #RSA key gen die "xp1 seen twice - check input file" if ($xp1); -@@ -2074,11 +2353,10 @@ sub parse($$) { +@@ -2074,11 +2370,10 @@ sub parse($$) { } } elsif ($tt == 10) { @@ -623,7 +640,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr } elsif ($tt == 11) { if ($pt ne "" && $dsa_keyfile ne "") { -@@ -2141,6 +2419,74 @@ sub parse($$) { +@@ -2141,6 +2436,74 @@ sub parse($$) { $Xq = ""; } } @@ -698,7 +715,7 @@ diff -up libgcrypt-1.4.6/tests/cavs_driver.pl.cavs libgcrypt-1.4.6/tests/cavs_dr elsif ($tt > 0) { die "Test case $tt not defined"; } -@@ -2199,7 +2545,9 @@ sub main() { +@@ -2199,7 +2562,9 @@ sub main() { $state_rng = \&libgcrypt_state_rng; $hmac = \&libgcrypt_hmac; $dsa_pqggen = \&libgcrypt_dsa_pqggen; diff --git a/libgcrypt-1.4.6-fips-cfgrandom.patch b/libgcrypt-1.4.6-fips-cfgrandom.patch new file mode 100644 index 0000000..574d6a0 --- /dev/null +++ b/libgcrypt-1.4.6-fips-cfgrandom.patch @@ -0,0 +1,119 @@ +diff -up libgcrypt-1.4.6/random/random-fips.c.cfgrandom libgcrypt-1.4.6/random/random-fips.c +--- libgcrypt-1.4.6/random/random-fips.c.cfgrandom 2011-06-20 21:13:38.000000000 +0200 ++++ libgcrypt-1.4.6/random/random-fips.c 2011-06-20 21:32:47.000000000 +0200 +@@ -27,10 +27,10 @@ + There are 3 random context which map to the different levels of + random quality: + +- Generator Seed and Key Kernel entropy (init/reseed) +- ------------------------------------------------------------ +- GCRY_VERY_STRONG_RANDOM /dev/urandom 256/128 bits +- GCRY_STRONG_RANDOM /dev/urandom 256/128 bits ++ Generator Seed and Key Kernel entropy (init/reseed) ++ --------------------------------------------------------------------------------------- ++ GCRY_VERY_STRONG_RANDOM /etc/gcrypt/rngseed+/dev/urandom 256/128 bits ++ GCRY_STRONG_RANDOM /etc/gcrypt/rngseed+/dev/urandom 256/128 bits + gcry_create_nonce GCRY_STRONG_RANDOM n/a + + All random generators return their data in 128 bit blocks. If the +@@ -40,7 +40,10 @@ + (SEED_TTL) output blocks; the re-seeding is disabled in test mode. + + The GCRY_VERY_STRONG_RANDOM and GCRY_STRONG_RANDOM generators are +- keyed and seeded from the /dev/urandom device. ++ keyed and seeded with data that is loaded from the /etc/gcrypt/rngseed ++ if the device or symlink to device exists xored with the data ++ from the /dev/urandom device. This allows the system administrator ++ to always seed the RNGs from /dev/random if it is required. + + The gcry_create_nonce generator is keyed and seeded from the + GCRY_STRONG_RANDOM generator. It may also block if the +@@ -559,6 +562,10 @@ get_entropy (size_t nbytes) + entropy_collect_buffer_len = 0; + + #if USE_RNDLINUX ++ _gcry_rndlinux_gather_random (entropy_collect_cb, 0, ++ X931_AES_KEYLEN, ++ -1); ++ entropy_collect_buffer_len = 0; + rc = _gcry_rndlinux_gather_random (entropy_collect_cb, 0, + X931_AES_KEYLEN, + GCRY_STRONG_RANDOM); +diff -up libgcrypt-1.4.6/random/rndlinux.c.cfgrandom libgcrypt-1.4.6/random/rndlinux.c +--- libgcrypt-1.4.6/random/rndlinux.c.cfgrandom 2009-04-02 11:25:34.000000000 +0200 ++++ libgcrypt-1.4.6/random/rndlinux.c 2011-06-20 21:34:09.000000000 +0200 +@@ -35,7 +35,9 @@ + #include "g10lib.h" + #include "rand-internal.h" + +-static int open_device ( const char *name ); ++#define NAME_OF_CFG_RNGSEED "/etc/gcrypt/rngseed" ++ ++static int open_device ( const char *name, int fatal ); + + + static int +@@ -56,13 +58,17 @@ set_cloexec_flag (int fd) + * Used to open the /dev/random devices (Linux, xBSD, Solaris (if it exists)). + */ + static int +-open_device ( const char *name ) ++open_device ( const char *name, int fatal ) + { + int fd; + + fd = open ( name, O_RDONLY ); + if ( fd == -1 ) +- log_fatal ("can't open %s: %s\n", name, strerror(errno) ); ++ { ++ if (! fatal) ++ return fd; ++ log_fatal ("can't open %s: %s\n", name, strerror(errno) ); ++ } + + if (set_cloexec_flag (fd)) + log_error ("error setting FD_CLOEXEC on fd %d: %s\n", +@@ -91,11 +97,13 @@ _gcry_rndlinux_gather_random (void (*add + { + static int fd_urandom = -1; + static int fd_random = -1; ++ static int fd_configured = -1; + int fd; + int n; + int warn=0; + byte buffer[768]; + size_t n_hw; ++ size_t orig_length = length; + + /* First read from a hardware source. However let it account only + for up to 50% of the requested bytes. */ +@@ -106,16 +114,26 @@ _gcry_rndlinux_gather_random (void (*add + length -= n_hw; + + /* Open the requested device. */ ++ ++ if (level == -1) ++ { ++ if (fd_configured == -1) ++ fd_configured = open_device ( NAME_OF_CFG_RNGSEED, 0 ); ++ fd = fd_configured; ++ if (fd == -1) ++ return -1; ++ } ++ + if (level >= 2) + { + if( fd_random == -1 ) +- fd_random = open_device ( NAME_OF_DEV_RANDOM ); ++ fd_random = open_device ( NAME_OF_DEV_RANDOM, 1 ); + fd = fd_random; + } +- else ++ else if (level != -1) + { + if( fd_urandom == -1 ) +- fd_urandom = open_device ( NAME_OF_DEV_URANDOM ); ++ fd_urandom = open_device ( NAME_OF_DEV_URANDOM, 1 ); + fd = fd_urandom; + } + diff --git a/libgcrypt.spec b/libgcrypt.spec index 9f1a62a..b430412 100644 --- a/libgcrypt.spec +++ b/libgcrypt.spec @@ -1,6 +1,6 @@ Name: libgcrypt Version: 1.4.6 -Release: 3%{?dist} +Release: 4%{?dist} URL: http://www.gnupg.org/ Source0: libgcrypt-%{version}-hobbled.tar.bz2 # The original libgcrypt sources now contain potentially patented ECC @@ -19,7 +19,7 @@ Patch4: libgcrypt-1.4.5-urandom.patch # fix tests in the FIPS mode, fix the FIPS-186-3 DSA keygen Patch5: libgcrypt-1.4.5-tests.patch # add configurable source of RNG seed in the FIPS mode -Patch6: libgcrypt-1.4.5-fips-cfgrandom.patch +Patch6: libgcrypt-1.4.6-fips-cfgrandom.patch # make the FIPS-186-3 DSA CAVS testable Patch7: libgcrypt-1.4.6-cavs.patch @@ -171,6 +171,9 @@ exit 0 %doc COPYING %changelog +* Mon Jun 20 2011 Tomas Mraz 1.4.6-4 +- Always xor seed from /dev/urandom over /etc/gcrypt/rngseed + * Mon May 30 2011 Tomas Mraz 1.4.6-3 - Make the FIPS-186-3 DSA implementation CAVS testable - add configurable source of RNG seed /etc/gcrypt/rngseed