RSA 2048 keypair generation: via openssl 0.5s via gpg 30s, why the difference

gpgopensslrandom

RSA 2048 keypair generation: via openssl 0.5s via gpg 30s, why the difference
There are several programs which can gerate RSA public/private keypairs

GnuPG/OpenPGP for instance has a wizzard being envoked via

gpg --gen-key

OpenSSL can generate a keypair using theses command lines

openssl genrsa -out testkey.private 2048
openssl rsa -in testkey.private -pubout -out testkey.public

for the very same thing, that is generating a keypair RSA 2048 bit
I can perceive -on the very same machine- very different times.

openssl generates a keypair in about 0.5s
gpg takes about 30 and even adverts "move mouse to generate randomness/ entropy"

Can the difference be explained?
I know that gpg does some littel more then just the RSA key creation, yet I do specifically choose option (4)

Please select what kind of key you want:
   (1) RSA and RSA (default)
   (2) DSA and Elgamal
   (3) DSA (sign only)
   (4) RSA (sign only)
Your selection?

Therefore really the only thing generated is a 2048bit RSA keypair.
Yet the time difference is strinking 30 seconds?

To me it seems that either gpg is wasting needlessly time or OpenSSL is not waiting enough time and hence creates insecure keys.

My question is what could explain the difference?

Update

The RSA creating must take as an input some randomness. Hence to make certain that the speedy openssl is not simply the result of using some stored up randomness I batchrun it several time

time bash -c "for i in {1..50}; do  openssl genrsa -out /dev/null 2048 ;  done;"

which yields

real    0m16.577s
user    0m16.309s
sys 0m0.092s

which is that for 50 2048bits RSA keys (I assume need a lot of entropy/randomness) openssl still only needed 16 seconds. My assumption here would hence be the "answer" that openssl must be broken. After all I am distrustful my Linux (a 3.2.0-59 kernel) has become so great in generating randomness.

Maybe the difference is simply that openssl uses /dev/urandom and
gpg uses /dev/random which if true could explain the time difference my problem is that I do not know how I would find out about this, to verify this.

update2

To test the source of openssl's random I used

strace -xe trace=file,read,write,close openssl genrsa -out testkey5.private 2048 2>&1 | grep random -A1

which yields

open("/dev/urandom", O_RDONLY|O_NOCTTY|O_NONBLOCK) = 4
read(4, "\x21\xd8\xaa\xf1\x2b\x5f\x4a\x89\x5d\x6c\x58\x82\xc1\x88\x21\x04\xfa\x5b\x18\x98\x8a\x34\x2b\xe3\xf3\xc0\xb1\xef\xfb\x44\x15\x09", 32) = 32

so it seems that 32 bytes from /dev/urandom (not the "better" /dev/random) is enough for th 2048bit RSA keypair in openssl. Therefore it is so fast!

Measurements

2048bit RSA keypair generation means

  • 32 bytes of only /dev/urandom (using openssl)
  • 300 bytes of /dev/random (using openPGP GNU Privacy Guard)

this explains of course the time difference!

Best Answer

GnuPG consumes several bytes from /dev/random for each random byte it actually uses. You can easily check that with this command:

start cmd:> strace -e trace=open,read gpg --armor --gen-random 2 16 2>&1 | tail
open("/etc/gcrypt/rngseed", O_RDONLY)   = -1 ENOENT (No such file or directory)
open("/dev/urandom", O_RDONLY)          = 3
read(3, "\\\224F\33p\314j\235\7\200F9\306V\3108", 16) = 16
open("/dev/random", O_RDONLY)           = 4
read(4, "/\311\342\377...265\213I"..., 300) = 128
read(4, "\325\3\2161+1...302@\202"..., 172) = 128
read(4, "\5[\372l\16?\...6iY\363z"..., 44) = 44
open("/home/hl/.gnupg/random_seed", O_WRONLY|O_CREAT, 0600) = 5
cCVg2XuvdjzYiV0RE1uzGQ==
+++ exited with 0 +++

In order to output 16 bytes of high-quality entropy GnuPG reads 300 bytes from /dev/random.

This is explained here: Random-Number Subsystem Architecture

Linux stores a maximum of 4096 bytes (see cat /proc/sys/kernel/random/poolsize) of entropy. If a process needs more than available (see cat /proc/sys/kernel/random/entropy_avail) then the CPU usage becomes more or less irrelevant as the feeding speed of the kernel's entropy pool becomes the relevant factor.

Related Question