{Spam?} Re: loading psk credentials from encrypted file

Michael Weiser michael at weiser.dinsnail.net
Fri Oct 23 20:07:12 CEST 2009


almost a year ago I asked the question below about putting PSK keys into
an encrypted file. I had a look at how to do it using a block cipher
directly. After seeing, what this entailed, and considering my crypto
knowledge, I was sure, I couldn't do this correctly. So I put the
project aside.

A few days ago I had an idea though: Why not abuse the PKCS12 functions
to save the datum_t holding the PSK key out in an encrypted PKCS12
structure? The code looks as shown below (without the error checking for
readability). It works fine, but my questions are:

- Is this at all sensible or (will it break|is it braindead|other
  reason for never ever doing it)?
- Is my PSK key secure this way or do I have an inherent security hole
- Can I use something stronger than RC4-128 for encryption?
- Can I have my own bag type GNUTLS_BAG_PSK_KEY so I don't need to abuse
  for generic encrypted data?
- Or is there some similar interface I might abuse which supports
  stronger encryption or generic data content?

(And yes: I save a randomly generated key that way, not one derived from
 a password.)


Saving the key in key_datum:

gnutls_pkcs12_bag_set_data(bag, GNUTLS_BAG_CERTIFICATE, &key_datum);
pkcs12_password = getpass("Verify Passphrase: ");
gnutls_pkcs12_bag_encrypt(bag, pkcs12_password, GNUTLS_PKCS_USE_PKCS12_ARCFOUR);
gnutls_pkcs12_set_bag(pkcs12, bag);
gnutls_pkcs12_generate_mac(pkcs12, pkcs12_password);
memset(pkcs12_password, 0x0, strlen(pkcs12_password));
pkcs12_struct_size = sizeof(pkcs12_struct);
gnutls_pkcs12_export(pkcs12, GNUTLS_X509_FMT_PEM, pkcs12_struct, &pkcs12_struct_size);
fd = open(psk_outfile, O_WRONLY | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR);
write(fd, pkcs12_struct, pkcs12_struct_size);

Loading the key into key_datum:

pkcs12_datum.size = 1024 * 10;
pkcs12_datum.data = malloc(pkcs12_datum.size);
fd = open(keyfile, O_RDONLY);
pkcs12_datum.size = read(fd, pkcs12_datum.data, pkcs12_datum.size);
gnutls_pkcs12_import(pkcs12, &pkcs12_datum, GNUTLS_X509_FMT_PEM, 0);
do {
	passphrase = getpass("Passphrase: ");
} while (gnutls_pkcs12_verify_mac(pkcs12, passphrase) < 0);
gnutls_pkcs12_get_bag(pkcs12, 0, bag);
gnutls_pkcs12_bag_decrypt(bag, passphrase);
memset(passphrase, 0x0, strlen(passphrase));
gnutls_pkcs12_bag_get_data(bag, 0, &key_datum);

On Mon, Dec 22, 2008 at 11:55:04PM +0100, Michael Weiser wrote:

> I've written a small program that uses gnutls for authentication. I've
> chosen to use PSK authentication because it is simple to implement (no
> certificate checking and the like) and fits my use case well (single
> user). Now I've got a small usability problem:

> On the client side I have to enter a password to derive the PSK key
> from. Whether I've entered it correctly or not can only be determined by
> trying a handshake. With my application this can be some time after I've
> entered the password and can be confused with connectivity and other
> problems on the network or server side.

> So I'd like to enter the password just once, derive the PSK key from it
> and store it in an AES-encrypted file. When starting my client
> application, it would then ask for the passphrase of that file and could
> immediately determine if the file can be decrypted using that key. This
> way it can produce a proper error message or just ask for the passphrase
> again.

> (This would be analogous to using an encrypted RSA private key for X509
> authentication and being asked for its passphrase.)

> Is this directly supported by gnutls?
> How would I best go about implementing it?
> Is this a case for enhancing gnutls or should I rather implement the
> neccessary logic in my application?
bye, Michael
I hate forms!

More information about the Gnutls-help mailing list