On 11/20/2017 11:17 AM, Michael StJohns wrote:
One additional topic for discussion: Late in the week we talked about
the current state of the API internally and one item to revisit is
where the DerivationParameterSpec objects are passed. It was brought
up by a couple people that it would be better to provide the DPS
objects pertaining to keys at the time they are called for through
deriveKey() and deriveKeys() (and possibly deriveData).
Originally we had them all grouped in a List in the init method. One
reason for needing it up there was to know the total length of
material to generate. If we can provide the total length through the
AlgorithmParameterSpec passed in via init() then things like:
Key deriveKey(DerivationParameterSpec param);
List<Key> deriveKeys(List<DerivationParameterSpec> params);
become possible. To my eyes at least it does make it more clear what
DPS you're processing since they're provided at derive time, rather
than the caller having to keep track in their heads where in the DPS
list they might be with each successive deriveKey or deriveKeys
calls. And I think we could do away with deriveKeys(int), too.
See above - the key stream is logically produced in its entirety
before any assignment of that stream is made to any cryptographic
objects because the mixins (except for the round differentiator) are
the same for each key stream production round. Simply passing in the
total length may not give you the right result if the KDF requires a
per component length (and it should to defeat (5) or it should only
produce a single key).
In general, if the KDF needs any information up front to produce the
output bits, then that information can be supplied in init using the
APS. In your example attack for (5), an implementation that prevents
this attack would probably take a length and label (e.g. "key1", "key2",
"iv1", "iv2") for each derived value. Then the HSM would need to enforce
that any value derived with a "key*" label could not be extracted. If
that entire sequence of lengths and labels needs to be known up front,
then it can be supplied in the APS. In this organization, the only
additional information that the DPS passed to deriveKey() needs to
provide is the encryption algorithm name and parameters (though taking a
length and checking it is probably a good idea).