1 #include <errno.h> 2 3 #include "crypto_kdf_blake2b.h" 4 #include "crypto_generichash_blake2b.h" 5 #include "private/common.h" 6 7 size_t 8 crypto_kdf_blake2b_bytes_min(void) 9 { 10 return crypto_kdf_blake2b_BYTES_MIN; 11 } 12 13 size_t 14 crypto_kdf_blake2b_bytes_max(void) 15 { 16 return crypto_kdf_blake2b_BYTES_MAX; 17 } 18 19 size_t 20 crypto_kdf_blake2b_contextbytes(void) 21 { 22 return crypto_kdf_blake2b_CONTEXTBYTES; 23 } 24 25 size_t 26 crypto_kdf_blake2b_keybytes(void) 27 { 28 return crypto_kdf_blake2b_KEYBYTES; 29 } 30 31 int crypto_kdf_blake2b_derive_from_key(unsigned char *subkey, size_t subkey_len, 32 uint64_t subkey_id, 33 const char ctx[crypto_kdf_blake2b_CONTEXTBYTES], 34 const unsigned char key[crypto_kdf_blake2b_KEYBYTES]) 35 { 36 unsigned char ctx_padded[crypto_generichash_blake2b_PERSONALBYTES]; 37 unsigned char salt[crypto_generichash_blake2b_SALTBYTES]; 38 39 memcpy(ctx_padded, ctx, crypto_kdf_blake2b_CONTEXTBYTES); 40 memset(ctx_padded + crypto_kdf_blake2b_CONTEXTBYTES, 0, sizeof ctx_padded - crypto_kdf_blake2b_CONTEXTBYTES); 41 STORE64_LE(salt, subkey_id); 42 memset(salt + 8, 0, (sizeof salt) - 8); 43 if (subkey_len < crypto_kdf_blake2b_BYTES_MIN || 44 subkey_len > crypto_kdf_blake2b_BYTES_MAX) { 45 errno = EINVAL; 46 return -1; 47 } 48 return crypto_generichash_blake2b_salt_personal(subkey, subkey_len, 49 NULL, 0, 50 key, crypto_kdf_blake2b_KEYBYTES, 51 salt, ctx_padded); 52 } 53