I want to derive a 256 bit encryption key and a 256 bit MAC key from a single 256 bit master key for an authenticated encryption scheme.

I was considering the following construction to derive the two keys using a secure 256 bit hash algorithm e.g. Keccak:

  1. Key 1 for encryption = H(master key | '0')
  2. Key 2 for MAC = H(master key | '1')

The advantage of this is that if the MAC key is compromised, it will not lead to decryption of messages as it should be hard to find a pre-image for the one-way hash to determine the master key and thus the derived encryption key.

Also, if only the encryption key was compromised, then this would also not compromise the master key so the attacker should not be able to determine the MAC key and be able to forge future transmissions.

Is this a secure method to derive two keys from one key? If not, what is a more secure method?

  • $\begingroup$ personally I would just run the thing through a 512-bit hash and split it in half $\endgroup$ Oct 23, 2014 at 9:15
  • $\begingroup$ @RichieFrame That's likely secure and likely the fastest method as well, but it doesn't scale with the size of the keys, hash or number of keys that required. Using a well defined KDF should be preferred IMHO. $\endgroup$
    – Maarten Bodewes
    Oct 23, 2014 at 13:02
  • 1
    $\begingroup$ I assumed the initial 256-bit key was generated by a suitable KDF, which would make the last hash a final step; and yes, it only generates 512-bits of key material, but that is what was asked for. $\endgroup$ Oct 23, 2014 at 19:01
  • $\begingroup$ @RichieFrame Let us agree that it is fast (especially on 64 bit) and secure, but that it doesn't scale well :) $\endgroup$
    – Maarten Bodewes
    Oct 24, 2014 at 13:19

2 Answers 2


Yes, this should be secure, as it is largely compatible with KDF1 and KDF2 which basically use a 4 byte big endian encoding of the counter instead of a direct ASCII conversion to a byte. Note that this construct works fine for master keys (short length, high entropy) but may be vulnerable to length extension attacks if larger input is allowed.

However, if you want to use the latest and greatest, you could use HKDF, possibly even augmented with a salt for session keys.

HKDF and the KDF's in NIST SP800-108 typically have a better security proof and supply methods of expanding the amount of key material after extracting the key material from the input. They also incorporate methods of supplying an explicit label and other information (using "enc" and "mac" instead of '1' / '2'). Unfortunately they are not often present in cryptographic libraries, they are harder to implement, they are badly defined and they seem to offer relatively few benefits over simpler schemes such as KDF1 and 2.

  • $\begingroup$ Would it not be possible to use e.g SCrypt with a salt to derive the required amount of data and split it into keys ? $\endgroup$
    – Thor
    Oct 23, 2014 at 14:22
  • $\begingroup$ Yes that's kind of possible, but scrypt was created to do key stretching using a work factor (and, in the case of scrypt, a large internal state). Usually it is possible to use a Password Based Key Derivation Function (PBKDF) instead of a Key Based Key Derivation Function (KBKDF), which is what is required. $\endgroup$
    – Maarten Bodewes
    Oct 23, 2014 at 14:30
  • $\begingroup$ Yes, this is secure - Thanks owlstead, I will stick with my construction as it seems simpler and easier to understand than HKDF. $\endgroup$
    – xenek
    Oct 24, 2014 at 4:07
  • $\begingroup$ I toned that down somewhat and expanded the answer. I based that assumption on that of Ilmari who supplied the other answer. Nevertheless, KDF1/2 are used in practice and I've not seen any attacks on it either. $\endgroup$
    – Maarten Bodewes
    Oct 24, 2014 at 12:44
  • $\begingroup$ @owlstead : $\;\;\;\;$ "for less structured" $\: \mapsto \:$ "for more structured" $\;\;$ ? $\;\;\;\;\;\;\;\;\;$ $\endgroup$
    – user991
    Oct 24, 2014 at 18:17

Depends on what you mean by Keccak.

There is actually a slight issue here that not all 256-bit Keccak variants have 256-bit preimage resistance. SHA3-256 (in the current SHA-3 draft) does have 256-bit preimage, but if you are using Keccak with 256-bit capacity it only has 128-bit preimage resistance. At least some of the earlier documents had 256-bit output Keccak with 256-bit capacity.

If your hash function has 128-bit preimage resistance, an attacker who gets your encryption key might also be able to break the authentication or vice versa, using "only" about $2^{128}$ operations. Of course, even that wouldn't be feasible currently, but since you are going with 256-bit encryption, you should ensure that all steps maintain 256-bit resistance.

If you are using the version from the current SHA-3 draft, you should be fine. However, I'd like to second the suggestion of using HKDF (perhaps with a more established hash like SHA-256), because it is a fairly standard way to derive keys.

  • $\begingroup$ Thanks otus, I was considering 256 bit output Keccak with capacity at 512 bits. This is the same as the SHA-3 latest draft I believe with capacity at C=2D with D being the digest output size. $\endgroup$
    – xenek
    Oct 24, 2014 at 4:09

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.