[Pkg-gnupg-commit] r389 - in /gnupg/branches/squeeze/debian: changelog patches/00list patches/CVE-2013-4576.dpatch
thijs at users.alioth.debian.org
thijs at users.alioth.debian.org
Tue Jan 7 08:29:43 UTC 2014
Author: thijs
Date: Tue Jan 7 08:29:43 2014
New Revision: 389
URL: http://svn.debian.org/wsvn/pkg-gnupg/?sc=1&rev=389
Log:
1.4.10-4+squeeze4 prepared outside of public repo
Added:
gnupg/branches/squeeze/debian/patches/CVE-2013-4576.dpatch
Modified:
gnupg/branches/squeeze/debian/changelog
gnupg/branches/squeeze/debian/patches/00list
Modified: gnupg/branches/squeeze/debian/changelog
URL: http://svn.debian.org/wsvn/pkg-gnupg/gnupg/branches/squeeze/debian/changelog?rev=389&op=diff
==============================================================================
--- gnupg/branches/squeeze/debian/changelog (original)
+++ gnupg/branches/squeeze/debian/changelog Tue Jan 7 08:29:43 2014
@@ -1,3 +1,11 @@
+gnupg (1.4.10-4+squeeze4) squeeze-security; urgency=high
+
+ * Fixed the RSA Key Extraction via Low-Bandwidth Acoustic
+ Cryptanalysis attack as described by Genkin, Shamir, and Tromer.
+ See <http://www.cs.tau.ac.il/~tromer/acoustic/>. [CVE-2013-4576]
+
+ -- Thijs Kinkhorst <thijs at debian.org> Sat, 14 Dec 2013 08:28:15 +0100
+
gnupg (1.4.10-4+squeeze3) squeeze-security; urgency=high
* Apply upstream patch to fix infinite recursion in the
Modified: gnupg/branches/squeeze/debian/patches/00list
URL: http://svn.debian.org/wsvn/pkg-gnupg/gnupg/branches/squeeze/debian/patches/00list?rev=389&op=diff
==============================================================================
--- gnupg/branches/squeeze/debian/patches/00list (original)
+++ gnupg/branches/squeeze/debian/patches/00list Tue Jan 7 08:29:43 2014
@@ -11,3 +11,4 @@
CVE-2013-4242
CVE-2013-4402
CVE-2013-4351
+CVE-2013-4576
Added: gnupg/branches/squeeze/debian/patches/CVE-2013-4576.dpatch
URL: http://svn.debian.org/wsvn/pkg-gnupg/gnupg/branches/squeeze/debian/patches/CVE-2013-4576.dpatch?rev=389&op=file
==============================================================================
--- gnupg/branches/squeeze/debian/patches/CVE-2013-4576.dpatch (added)
+++ gnupg/branches/squeeze/debian/patches/CVE-2013-4576.dpatch Tue Jan 7 08:29:43 2014
@@ -0,0 +1,363 @@
+#! /bin/sh /usr/share/dpatch/dpatch-run
+## CVE-2013-4576 by Werner Koch
+##
+## All lines beginning with `## DP:' are a description of the patch.
+## DP: CVE-2013-4576
+
+From 93a96e3c0c33370248f6570d8285c4e811d305d4 Mon Sep 17 00:00:00 2001
+From: Werner Koch <wk at gnupg.org>
+Date: Tue, 22 Oct 2013 14:26:53 +0200
+Subject: [PATCH 1/2] Use blinding for the RSA secret operation.
+
+* cipher/random.c (randomize_mpi): New.
+* g10/gpgv.c (randomize_mpi): New stub.
+* cipher/rsa.c (USE_BLINDING): Define macro.
+(secret): Implement blinding.
+--
+
+GPG 1.x has never used any protection against timing attacks on the
+RSA secret operation. The rationale for this has been that there was
+no way to mount a remote timing attack on GnuPG. With the turning up
+of Acoustic Cryptanalysis (http://cs.tau.ac.il/~tromer/acoustic) this
+assumption no longer holds true and thus we need to do do something
+about it. Blinding seems to be a suitable mitigation to the threat of
+key extraction. It does not help against distinguishing used keys,
+though.
+
+Note that GPG 2.x uses Libgcrypt which does blinding by default.
+
+The performance penalty is negligible: Modifying the core pubkey_sign
+or pubkey_decrypt function to run 100 times in a loop, the entire
+execution times for signing or decrypting a small message using a 4K
+RSA key on a Thinkpad X220 are
+
+ Without blinding: 5.2s (8.9s)
+ With blinding: 5.6s (9.3s)
+
+The numbers in parentheses give the values without the recently
+implemented k-ary exponentiation code. Thus for the next release the
+user will actually experience faster signing and decryption. A
+drawback of blinding is that we need random numbers even for
+decryption (albeit at low quality).
+
+Signed-off-by: Werner Koch <wk at gnupg.org>
+
+CVE-id: CVE-2013-4576
+---
+ cipher/random.c | 12 ++++++++++++
+ cipher/random.h | 1 +
+ cipher/rsa.c | 58 ++++++++++++++++++++++++++++++++++++++++-----------------
+ g10/gpgv.c | 1 +
+ 4 files changed, 55 insertions(+), 17 deletions(-)
+
+diff --git a/cipher/random.c b/cipher/random.c
+index b634161..7549517 100644
+--- a/cipher/random.c
++++ b/cipher/random.c
+@@ -284,6 +284,18 @@ randomize_buffer( byte *buffer, size_t length, int level )
+ }
+
+
++/* Randomize the MPI by setting it to NBITS of random of quality LEVEL. */
++void
++randomize_mpi (MPI mpi, size_t nbits, int level)
++{
++ unsigned char *buffer;
++
++ buffer = get_random_bits (nbits, level, mpi_is_secure (mpi));
++ mpi_set_buffer (mpi, buffer, (nbits+7)/8, 0);
++ xfree (buffer);
++}
++
++
+ int
+ random_is_faked()
+ {
+diff --git a/cipher/random.h b/cipher/random.h
+index ca02df1..01ee11b 100644
+--- a/cipher/random.h
++++ b/cipher/random.h
+@@ -30,6 +30,7 @@ int quick_random_gen( int onoff );
+ int random_is_faked(void);
+ void random_disable_locking (void);
+ void randomize_buffer( byte *buffer, size_t length, int level );
++void randomize_mpi (MPI mpi, size_t nbits, int level);
+ byte *get_random_bits( size_t nbits, int level, int secure );
+ void fast_random_poll( void );
+
+diff --git a/cipher/rsa.c b/cipher/rsa.c
+index 1cdc600..c52704c 100644
+--- a/cipher/rsa.c
++++ b/cipher/rsa.c
+@@ -1,5 +1,5 @@
+ /* rsa.c - RSA function
+- * Copyright (C) 1997, 1998, 1999 by Werner Koch (dd9jn)
++ * Copyright (C) 1997, 1998, 1999, 2013 by Werner Koch (dd9jn)
+ * Copyright (C) 2000, 2001 Free Software Foundation, Inc.
+ *
+ * This file is part of GnuPG.
+@@ -22,7 +22,7 @@
+ which expires on September 20, 2000. The patent holder placed that
+ patent into the public domain on Sep 6th, 2000.
+ */
+-
++
+ #include <config.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -32,6 +32,10 @@
+ #include "cipher.h"
+ #include "rsa.h"
+
++/* Blinding is used to mitigate side-channel attacks. You may undef
++ this to speed up the operation in case the system is secured
++ against physical and network mounted side-channel attacks. */
++#define USE_BLINDING 1
+
+ typedef struct {
+ MPI n; /* modulus */
+@@ -103,7 +107,7 @@ generate( RSA_secret_key *sk, unsigned nbits )
+
+ /* make sure that nbits is even so that we generate p, q of equal size */
+ if ( (nbits&1) )
+- nbits++;
++ nbits++;
+
+ n = mpi_alloc ( mpi_nlimb_hint_from_nbits (nbits) );
+
+@@ -146,7 +150,7 @@ generate( RSA_secret_key *sk, unsigned nbits )
+ 65537 as the new best practice. See FIPS-186-3.
+ */
+ e = mpi_alloc ( mpi_nlimb_hint_from_nbits (32) );
+- mpi_set_ui( e, 65537);
++ mpi_set_ui( e, 65537);
+ while( !mpi_gcd(t1, e, phi) ) /* (while gcd is not 1) */
+ mpi_add_ui( e, e, 2);
+
+@@ -268,7 +272,7 @@ stronger_key_check ( RSA_secret_key *skey )
+ mpi_invm(t, skey->p, skey->q );
+ if ( mpi_cmp(t, skey->u ) )
+ log_info ( "RSA Oops: u is wrong\n");
+-
++
+ log_info ( "RSA secret key check finished\n");
+
+ mpi_free (t);
+@@ -286,9 +290,9 @@ stronger_key_check ( RSA_secret_key *skey )
+ *
+ * Or faster:
+ *
+- * m1 = c ^ (d mod (p-1)) mod p
+- * m2 = c ^ (d mod (q-1)) mod q
+- * h = u * (m2 - m1) mod q
++ * m1 = c ^ (d mod (p-1)) mod p
++ * m2 = c ^ (d mod (q-1)) mod q
++ * h = u * (m2 - m1) mod q
+ * m = m1 + h * p
+ *
+ * Where m is OUTPUT, c is INPUT and d,n,p,q,u are elements of SKEY.
+@@ -299,13 +303,26 @@ secret(MPI output, MPI input, RSA_secret_key *skey )
+ #if 0
+ mpi_powm( output, input, skey->d, skey->n );
+ #else
+- MPI m1 = mpi_alloc_secure( mpi_get_nlimbs(skey->n)+1 );
+- MPI m2 = mpi_alloc_secure( mpi_get_nlimbs(skey->n)+1 );
+- MPI h = mpi_alloc_secure( mpi_get_nlimbs(skey->n)+1 );
+-
++ int nlimbs = mpi_get_nlimbs (skey->n)+1;
++ MPI m1 = mpi_alloc_secure (nlimbs);
++ MPI m2 = mpi_alloc_secure (nlimbs);
++ MPI h = mpi_alloc_secure (nlimbs);
++# ifdef USE_BLINDING
++ MPI r = mpi_alloc_secure (nlimbs);
++ MPI bdata= mpi_alloc_secure (nlimbs);
++
++ /* Blind: bdata = (data * r^e) mod n */
++ randomize_mpi (r, mpi_get_nbits (skey->n), 0);
++ mpi_fdiv_r (r, r, skey->n);
++ mpi_powm (bdata, r, skey->e, skey->n);
++ mpi_mulm (bdata, bdata, input, skey->n);
++ input = bdata;
++# endif /* USE_BLINDING */
++
++ /* RSA secret operation: */
+ /* m1 = c ^ (d mod (p-1)) mod p */
+ mpi_sub_ui( h, skey->p, 1 );
+- mpi_fdiv_r( h, skey->d, h );
++ mpi_fdiv_r( h, skey->d, h );
+ mpi_powm( m1, input, h, skey->p );
+ /* m2 = c ^ (d mod (q-1)) mod q */
+ mpi_sub_ui( h, skey->q, 1 );
+@@ -313,14 +330,21 @@ secret(MPI output, MPI input, RSA_secret_key *skey )
+ mpi_powm( m2, input, h, skey->q );
+ /* h = u * ( m2 - m1 ) mod q */
+ mpi_sub( h, m2, m1 );
+- if ( mpi_is_neg( h ) )
++ if ( mpi_is_neg( h ) )
+ mpi_add ( h, h, skey->q );
+- mpi_mulm( h, skey->u, h, skey->q );
++ mpi_mulm( h, skey->u, h, skey->q );
+ /* m = m2 + h * p */
+ mpi_mul ( h, h, skey->p );
+ mpi_add ( output, m1, h );
+- /* ready */
+-
++
++# ifdef USE_BLINDING
++ /* Unblind: output = (output * r^(-1)) mod n */
++ mpi_free (bdata);
++ mpi_invm (r, r, skey->n);
++ mpi_mulm (output, output, r, skey->n);
++ mpi_free (r);
++# endif /* USE_BLINDING */
++
+ mpi_free ( h );
+ mpi_free ( m1 );
+ mpi_free ( m2 );
+diff --git a/g10/gpgv.c b/g10/gpgv.c
+index a337fc7..b679853 100644
+--- a/g10/gpgv.c
++++ b/g10/gpgv.c
+@@ -389,6 +389,7 @@ void cipher_sync( CIPHER_HANDLE c ) {}
+ void random_dump_stats(void) {}
+ int quick_random_gen( int onoff ) { return -1;}
+ void randomize_buffer( byte *buffer, size_t length, int level ) {}
++void randomize_mpi (MPI mpi, size_t nbits, int level) {}
+ int random_is_faked() { return -1;}
+ byte *get_random_bits( size_t nbits, int level, int secure ) { return NULL;}
+ void set_random_seed_file( const char *name ) {}
+--
+1.8.4.3
+
+From d0d72d98f34579213230b3febfebd2fd8dff272b Mon Sep 17 00:00:00 2001
+From: Werner Koch <wk at gnupg.org>
+Date: Wed, 27 Nov 2013 14:22:10 +0100
+Subject: [PATCH 2/2] Normalize the MPIs used as input to secret key functions.
+
+* cipher/rsa.c (secret): Normalize the INPUT.
+(rsa_decrypt): Pass reduced data to secret.
+* cipher/elgamal.c (decrypt): Normalize A and B.
+* cipher/dsa.c (sign): Normalize HASH.
+--
+
+mpi_normalize is in general not required because extra leading zeroes
+do not harm the computation. However, adding extra all zero limbs or
+padding with multiples of N may be useful in side-channel attacks. In
+particular they are used by the acoustic crypt-analysis. This is an
+extra pre-caution which alone would not be sufficient to mitigate the
+described attack.
+
+CVE-id: CVE-2013-4576
+
+Signed-off-by: Werner Koch <wk at gnupg.org>
+---
+ cipher/dsa.c | 6 ++++--
+ cipher/elgamal.c | 3 +++
+ cipher/rsa.c | 22 ++++++++++++++++++----
+ 3 files changed, 25 insertions(+), 6 deletions(-)
+
+diff --git a/cipher/dsa.c b/cipher/dsa.c
+index 69b7d1b..e23f05c 100644
+--- a/cipher/dsa.c
++++ b/cipher/dsa.c
+@@ -274,7 +274,7 @@ check_secret_key( DSA_secret_key *sk )
+ /****************
+ * Make a DSA signature from HASH and put it into r and s.
+ *
+- * Without generating the k this function runs in
++ * Without generating the k this function runs in
+ * about 26ms on a 300 Mhz Mobile Pentium
+ */
+
+@@ -285,6 +285,8 @@ sign(MPI r, MPI s, MPI hash, DSA_secret_key *skey )
+ MPI kinv;
+ MPI tmp;
+
++ mpi_normalize (hash);
++
+ /* select a random k with 0 < k < q */
+ k = gen_k( skey->q );
+
+@@ -311,7 +313,7 @@ sign(MPI r, MPI s, MPI hash, DSA_secret_key *skey )
+ /****************
+ * Returns true if the signature composed from R and S is valid.
+ *
+- * Without the checks this function runs in
++ * Without the checks this function runs in
+ * about 31ms on a 300 Mhz Mobile Pentium
+ */
+ static int
+diff --git a/cipher/elgamal.c b/cipher/elgamal.c
+index c3f0862..5143ecc 100644
+--- a/cipher/elgamal.c
++++ b/cipher/elgamal.c
+@@ -374,6 +374,9 @@ decrypt(MPI output, MPI a, MPI b, ELG_secret_key *skey )
+ {
+ MPI t1 = mpi_alloc_secure( mpi_get_nlimbs( skey->p ) );
+
++ mpi_normalize (a);
++ mpi_normalize (b);
++
+ /* output = b/(a^x) mod p */
+ mpi_powm( t1, a, skey->x, skey->p );
+ mpi_invm( t1, t1, skey->p );
+diff --git a/cipher/rsa.c b/cipher/rsa.c
+index c52704c..c4d5161 100644
+--- a/cipher/rsa.c
++++ b/cipher/rsa.c
+@@ -308,9 +308,14 @@ secret(MPI output, MPI input, RSA_secret_key *skey )
+ MPI m2 = mpi_alloc_secure (nlimbs);
+ MPI h = mpi_alloc_secure (nlimbs);
+ # ifdef USE_BLINDING
+- MPI r = mpi_alloc_secure (nlimbs);
+ MPI bdata= mpi_alloc_secure (nlimbs);
++ MPI r = mpi_alloc_secure (nlimbs);
++# endif /* USE_BLINDING */
++
++ /* Remove superfluous leading zeroes from INPUT. */
++ mpi_normalize (input);
+
++# ifdef USE_BLINDING
+ /* Blind: bdata = (data * r^e) mod n */
+ randomize_mpi (r, mpi_get_nbits (skey->n), 0);
+ mpi_fdiv_r (r, r, skey->n);
+@@ -338,8 +343,8 @@ secret(MPI output, MPI input, RSA_secret_key *skey )
+ mpi_add ( output, m1, h );
+
+ # ifdef USE_BLINDING
+- /* Unblind: output = (output * r^(-1)) mod n */
+ mpi_free (bdata);
++ /* Unblind: output = (output * r^(-1)) mod n */
+ mpi_invm (r, r, skey->n);
+ mpi_mulm (output, output, r, skey->n);
+ mpi_free (r);
+@@ -419,6 +424,7 @@ int
+ rsa_decrypt( int algo, MPI *result, MPI *data, MPI *skey )
+ {
+ RSA_secret_key sk;
++ MPI input;
+
+ if( algo != 1 && algo != 2 )
+ return G10ERR_PUBKEY_ALGO;
+@@ -429,8 +435,16 @@ rsa_decrypt( int algo, MPI *result, MPI *data, MPI *skey )
+ sk.p = skey[3];
+ sk.q = skey[4];
+ sk.u = skey[5];
+- *result = mpi_alloc_secure( mpi_get_nlimbs( sk.n ) );
+- secret( *result, data[0], &sk );
++
++ /* Better make sure that there are no superfluous leading zeroes
++ in the input and it has not been padded using multiples of N.
++ This mitigates side-channel attacks (CVE-2013-4576). */
++ input = mpi_alloc (0);
++ mpi_normalize (data[0]);
++ mpi_fdiv_r (input, data[0], sk.n);
++ *result = mpi_alloc_secure (mpi_get_nlimbs (sk.n));
++ secret (*result, input, &sk);
++ mpi_free (input);
+ return 0;
+ }
+
+--
+1.8.4.3
+
More information about the Pkg-gnupg-commit
mailing list