Question

I'm developing a simple software that do aes256-cbc file encryption. This software is developed on GNU/Linux using libgcrypt-1.5.0.

I want to use the above function with GCRY_KDF_PBKDF2 as algo and SHA512 as subalgo.

gcry_kdf_derive( const void *passphrase, size_t passphraselen, int algo, int subalgo,
                 const void *salt, size_t saltlen, unsigned long iterations, 
                 size_t keysize, void *keybuffer )

This function derive a key from a passphrase. keysize gives the requested size of the keys in octets. keybuffer is a caller provided buffer filled on success with the derived key. The input passphrase is taken from passphrase which is an arbitrary memory buffer of passphraselen octets. algo specifies the KDF algorithm to use; see below. subalgo specifies an algorithm used internally by the KDF algorithms; this is usually a hash algorithm but certain KDF algorithms may use it differently. salt is a salt of length saltlen octets, as needed by most KDF algorithms. iterations is a positive integer parameter to most KDFs.

I don't have understand three things about how to use this function:

  1. salt must be generate randomly so it must be put not encrypted into the output file, isn't it? (IV-CIPHERTEXT-SALT-MAC)
  2. saltlen has a correct "crypto" value or can i choose whatever i prefer? Like 10,20,30...
  3. keysize (in this case) must be 512, right?
Was it helpful?

Solution

1) salt must be generate randomly so it must be put not encrypted into the output file, isn't it? (IV-CIPHERTEXT-SALT-MAC)

Correct, although the more logical form would be SALT-IV-CIPHERTEXT-MAC in some kind of container format. This would be the order in which the other party would need the components to

  1. calculate the keys
  2. verify the data
  3. decrypt the data

2) saltlen has a correct "crypto" value or can i choose whatever i prefer? Like 10,20,30...

The bare minimum (for a highly secure system) would be 64 bits or 8 bytes, but since you are using high end crypto primitives, why not go for 256 bits secure random, to match your key size.

3) keysize (in this case) must be 512, right?

That is correct, the key size in bits must be 512. The API expects the KEYSIZE argument to be in octets so that would be 64 octets. It seems you want to perform MAC signing/verification. This requires a separate key from the one used for encryption/decryption. So you need two 256 bit keys, which fortunately matches the output of the SHA-512 algorithm. I said "fortunately" because you really don't want PBKDF2 to calculate another block - it would go through all the iterations once again.

The IV value is best calculated separately, and put in front of the ciphertext. You should include the IV value in the MAC calculation (otherwise the first block of plain text won't be verified). The IV should be a random block of data, so that would be 128 bits or 16 bytes of secure random data for AES.

OTHER TIPS

1) Salt values are non-secret, and can be stored alongside the encrypted data. All they do jumble the encrypted values so that the password "cat" using GCRY_KDF_PBKDF2 and SHA512 to encrypt the word "the" doesn't always produce the cyphertext "86c8z385a33146b59d", or whatever. This protects against attacks using rainbow tables. You can put it in the encrypted file, but it's more useful as metadata.

2) I don't think it matters. Whatever you want. Although with the price of hard-drives, multiplying the size of a rainbow table by 8 isn't ludicrous. So you might want more than one byte.

3) Yeah, since you're using SHA-512, your keysize is 512.

Also, since I'm not a real cryptophile, you might want to take all this (dons sunglasses) with a grain of salt.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top