Using KDF output for password validation I am currently revising an AES data format. I would like to determine whether a provided password/key is incorrect. Previously this was done by validating the HMAC, but this makes it impossible to distinguish between data corruption and a bad password. It also requires reading the entire stream before validating the password, which is problematic.

My new design is as follows (the HMAC step is HKDF):

prk = PBKDF2(SHA512, password, salt, rounds, 512 bits)
(validator[16], iv[16]) = HMAC(SHA512, prk, "rncryptor.validator+iv" || 0x01, 256 bits)


The validator is 16 bytes that are written to the header. During decryption, I recompute the validator to check the password before proceeding.

I believe this scheme is secure. Common best-practice for password validation is a salted and stretched hash. I believe HKDF is providing the same. My one slight concern is NIST SP 800-56a, Section 5.8:


  An Approved key derivation function (KDF) shall be used to derive secret keying material from a shared secret. The output from a KDF shall only be used for secret keying material, such as a symmetric key used for data encryption or message integrity, a secret initialization vector, or a master key that will be used to generate other keys (possibly using a different process). Non- secret keying material (such as a non-secret initialization vector) shall not be generated using the shared secret.


The validator is not "keying material" at all, so I don't believe this is relevant, but I don't understand the restriction even for "a non-secret initialization vector." Why would it be dangerous to use a proper, salted KDF to generate a non-secret IV? Does this impact my use as a key/password validator?
It's best practice to use the KBKDF to generate separate key material for validation as well as for generating the key used for encryption using a different input or counter of each key.

If you do apply a KBKDF for each key / IV (using different ID's/counters for each) then you should not have any concern leaking any information. These KBKDF's are plenty fast (especially in comparison with PBKDF2 of course) so speed should not be a concern.

I would suggest to use a counter mode KDF in NIST SP800-108 if you want to stay within NIST boundaries. You can still use your favourite HMAC as PRF.

Note that there is some discussions regarding the security of KDF's. NIST approved KDF's may not always be the most safe. For instance, consider scrypt over PBKDF2 and HKDF-Expand (your currently selected KBKDF) over NIST SP800-108 if you don't require NIST approved algorithms.

Note that all the KBKDF's of NIST as well as HKDF have been added to Bouncy Castle 1.50 lightweight API for Java (I did the implementation / testing against NIST CAVP vectors), in case you require an implementation.