Dr. Stephen Henson wrote:

>On Thu, Sep 09, 2004, Steve Hay wrote:
>  
>
>>I'm afraid I don't know what "password based encryption" is, so I don't 
>>know if this is the right thing to even be trying to do.  It doesn't 
>>sound like what I wanted...
>>
>>    
>>
>
>It one of various standards which convert a password into a key (and sometimes
>and IV). For various reasons it is not advisable to use a password directly as
>a key.
>
The thing that I'm converting into a key+IV is random bytes to start 
with, so I suspect there is virtually no distinction between "password" 
and "key" in my case, which could be why I'm getting confused.

>
>  
>
>>>Alternatively you can get at the "guts" of the function by using
>>>PKCS5_PBKDF2_HMAC_SHA1(). Then you have to generate your own salt and pass it
>>>to the function along with the password and interation count.
>>>
>>>      
>>>
>>Sounds a little more hopeful.  Where do I get the "salt" from?  Would 
>>randomly generating it lead to the same encryption/decryption problem as 
>>with the IV above?  Would hard-coding something in the source code 
>>suffice or is that not advisable?
>>
>>However, PKCS5_PBKDF2_HMAC_SHA1() only seems to generate a key, not an 
>>IV, but I already have a key -- it's the IV that I want!
>>
>>It may be worth taking a step back and reconsidering what I'm trying to 
>>achieve.  I'm just trying to create a program to encrypt (and later 
>>decrypt) a plain text file.  The user chooses (or more likely randomly 
>>generates) a key and specifies this as the key to use when *building* 
>>the program.
>>
>>I then discovered that the encryption/decryption functions require an IV 
>>too, but still don't really know what an IV is...
>>
>>At the moment I'm trying to generate the IV, and also getting a new key, 
>>from the "key" that the user has supplied, and I'm getting lost in all 
>>sorts of things that I don't understand and wasn't expecting to 
>>encounter -- passwords, IV's, salt, PKCS#5, etc :(
>>
>>    
>>
>
>How is the "key" user supplied? Will then just input some human readable
>string or generate a random value in some way?
>
The "key" supplied by the user is just random bytes, probably generated 
with "openssl rand ..." or Perl's built-in rand() function or similar.  
In fact, the user can opt to not specify any key at all, in which case 
the build process for this program will generate one automatically using 
one of those means.

The key is then written into a .h header file and built into the program.

>
>  
>
>>Is it necessary/advisable to generate a key+IV in this way, or would it 
>>in fact suffice to have the user supply the IV too and just use the 
>>given key+IV?
>>
>>    
>>
>
>The IV is an initial value used by some ciphersuites. Unlike the key it is not
>sensitive information and can be included along with the message itself.
>
>So you might generate a random IV, write it out to a file, use it to
>initialize an encryption context then write out the encrypted data.
>
>At the other end you would read the IV from the file and use that.
>
Ah, that rings a bell.  I think I've seen other software that writes out 
the IV as the first X bytes of the encrypted data; the decrypt operation 
then reads it back from there.

Is there any harm in having a fixed IV?

>
>A salt is designed to avoid certain attacks on password based encryption.
>Specifically if the same password is used multiple times or if the password is
>vaguely guessable.
>
My key isn't going to be guessable, but many files could be encrypted by 
the same program, i.e. all using the same key, so it sounds like I 
should be thinking of my key as a password and generating the real key 
from it using a salt after all.

>
>Again you can generate a random value and prepend that to the data. Using a
>fixed value removes the protection a salt provides.
>
So what's the best way to do it?

At the moment I have roughly this to initialise the EVP_CIPHER_CTX:

EVP_BytesToKey(cipher_func, EVP_md5(), NULL, user_key, KEY_LEN, 1, key, iv)
EVP_CIPHER_CTX_init(&ctx)
EVP_CipherInit_ex(&ctx, cipher_func, NULL, NULL, NULL, crypt_mode)
EVP_CIPHER_CTX_set_key_length(&ctx, KEY_LEN)
EVP_CipherInit_ex(&ctx, NULL, NULL, key, iv, crypt_mode)

That's no good because EVP_BytesToKey() doesn't work for variable key 
length cipher's with non-default key lengths (and uses an old PKCS#5 
standard?).

So one solution would be simply to replace EVP_BytesToKey() above with this:

if (encrypting)
  generate random salt
else
  read salt from data
PKCS5_PBKDF2_HMAC_SHA1(user_key, KEY_LEN, salt, saltlen, iter, KEY_LEN, key)

The iv would have to generated/read from data as per the salt since 
PKCS5_PBKDF2_HMAC_SHA1() doesn't seem to create an IV.  Presumably the 
iter value needs to be treated similarly too to ensure it is the same 
for decryption as for encryption, or can iter safely be hard-coded in 
the program?

Another approach might have been to replace the whole initialisation 
with something like:

EVP_CIPHER_CTX_init(&ctx)
if (encrypting)
  generate random salt
else
  read salt from data
pbe2 = PKCS5_pbe2_set(cipher_func, iter, salt, saltlen)
EVP_PBE_CipherInit(pbe2->algorithm, user_key, KEY_LEN, pbe2->parameter, 
&ctx, crypt_mode)

but if PKCS5_pbe2_set() randomly generates the IV then that's no use is it?

Is the PKCS5_PBKDF2_HMAC_SHA1() pseudo-code above OK or is there a 
better way to do this?

Are EVP_CIPHER_param_to_asn1() / EVP_CIPHER_asn1_to_param() or 
PKCS5_v2_PBE_keyivgen() any use to me?

- Steve



------------------------------------------------
Radan Computational Ltd.

The information contained in this message and any files transmitted with it are 
confidential and intended for the addressee(s) only.  If you have received this 
message in error or there are any problems, please notify the sender immediately.  The 
unauthorized use, disclosure, copying or alteration of this message is strictly 
forbidden.  Note that any views or opinions presented in this email are solely those 
of the author and do not necessarily represent those of Radan Computational Ltd.  The 
recipient(s) of this message should check it and any attached files for viruses: Radan 
Computational will accept no liability for any damage caused by any virus transmitted 
by this email.

______________________________________________________________________
OpenSSL Project                                 http://www.openssl.org
User Support Mailing List                    [EMAIL PROTECTED]
Automated List Manager                           [EMAIL PROTECTED]

Reply via email to