0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012 #include <crypto/hash.h>
0013 #include <crypto/sha2.h>
0014
0015 #include "fscrypt_private.h"
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028 #define HKDF_HMAC_ALG "hmac(sha512)"
0029 #define HKDF_HASHLEN SHA512_DIGEST_SIZE
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048 static int hkdf_extract(struct crypto_shash *hmac_tfm, const u8 *ikm,
0049 unsigned int ikmlen, u8 prk[HKDF_HASHLEN])
0050 {
0051 static const u8 default_salt[HKDF_HASHLEN];
0052 int err;
0053
0054 err = crypto_shash_setkey(hmac_tfm, default_salt, HKDF_HASHLEN);
0055 if (err)
0056 return err;
0057
0058 return crypto_shash_tfm_digest(hmac_tfm, ikm, ikmlen, prk);
0059 }
0060
0061
0062
0063
0064
0065
0066
0067
0068 int fscrypt_init_hkdf(struct fscrypt_hkdf *hkdf, const u8 *master_key,
0069 unsigned int master_key_size)
0070 {
0071 struct crypto_shash *hmac_tfm;
0072 u8 prk[HKDF_HASHLEN];
0073 int err;
0074
0075 hmac_tfm = crypto_alloc_shash(HKDF_HMAC_ALG, 0, 0);
0076 if (IS_ERR(hmac_tfm)) {
0077 fscrypt_err(NULL, "Error allocating " HKDF_HMAC_ALG ": %ld",
0078 PTR_ERR(hmac_tfm));
0079 return PTR_ERR(hmac_tfm);
0080 }
0081
0082 if (WARN_ON(crypto_shash_digestsize(hmac_tfm) != sizeof(prk))) {
0083 err = -EINVAL;
0084 goto err_free_tfm;
0085 }
0086
0087 err = hkdf_extract(hmac_tfm, master_key, master_key_size, prk);
0088 if (err)
0089 goto err_free_tfm;
0090
0091 err = crypto_shash_setkey(hmac_tfm, prk, sizeof(prk));
0092 if (err)
0093 goto err_free_tfm;
0094
0095 hkdf->hmac_tfm = hmac_tfm;
0096 goto out;
0097
0098 err_free_tfm:
0099 crypto_free_shash(hmac_tfm);
0100 out:
0101 memzero_explicit(prk, sizeof(prk));
0102 return err;
0103 }
0104
0105
0106
0107
0108
0109
0110
0111
0112
0113
0114
0115
0116 int fscrypt_hkdf_expand(const struct fscrypt_hkdf *hkdf, u8 context,
0117 const u8 *info, unsigned int infolen,
0118 u8 *okm, unsigned int okmlen)
0119 {
0120 SHASH_DESC_ON_STACK(desc, hkdf->hmac_tfm);
0121 u8 prefix[9];
0122 unsigned int i;
0123 int err;
0124 const u8 *prev = NULL;
0125 u8 counter = 1;
0126 u8 tmp[HKDF_HASHLEN];
0127
0128 if (WARN_ON(okmlen > 255 * HKDF_HASHLEN))
0129 return -EINVAL;
0130
0131 desc->tfm = hkdf->hmac_tfm;
0132
0133 memcpy(prefix, "fscrypt\0", 8);
0134 prefix[8] = context;
0135
0136 for (i = 0; i < okmlen; i += HKDF_HASHLEN) {
0137
0138 err = crypto_shash_init(desc);
0139 if (err)
0140 goto out;
0141
0142 if (prev) {
0143 err = crypto_shash_update(desc, prev, HKDF_HASHLEN);
0144 if (err)
0145 goto out;
0146 }
0147
0148 err = crypto_shash_update(desc, prefix, sizeof(prefix));
0149 if (err)
0150 goto out;
0151
0152 err = crypto_shash_update(desc, info, infolen);
0153 if (err)
0154 goto out;
0155
0156 BUILD_BUG_ON(sizeof(counter) != 1);
0157 if (okmlen - i < HKDF_HASHLEN) {
0158 err = crypto_shash_finup(desc, &counter, 1, tmp);
0159 if (err)
0160 goto out;
0161 memcpy(&okm[i], tmp, okmlen - i);
0162 memzero_explicit(tmp, sizeof(tmp));
0163 } else {
0164 err = crypto_shash_finup(desc, &counter, 1, &okm[i]);
0165 if (err)
0166 goto out;
0167 }
0168 counter++;
0169 prev = &okm[i];
0170 }
0171 err = 0;
0172 out:
0173 if (unlikely(err))
0174 memzero_explicit(okm, okmlen);
0175 shash_desc_zero(desc);
0176 return err;
0177 }
0178
0179 void fscrypt_destroy_hkdf(struct fscrypt_hkdf *hkdf)
0180 {
0181 crypto_free_shash(hkdf->hmac_tfm);
0182 }