void g_eli_crypto_hmac(const uint8_t *hkey, size_t hkeysize, const uint8_t *data, size_t datasize, uint8_t *md, size_t mdsize) { struct hmac_ctx ctx; g_eli_crypto_hmac_init(&ctx, hkey, hkeysize); g_eli_crypto_hmac_update(&ctx, data, datasize); g_eli_crypto_hmac_final(&ctx, md, mdsize); }
void pkcs5v2_genkey(uint8_t *key, unsigned keylen, const uint8_t *salt, size_t saltsize, const char *passphrase, u_int iterations) { uint8_t md[SHA512_MDLEN], saltcount[saltsize + sizeof(uint32_t)]; uint8_t *counter, *keyp; u_int i, bsize, passlen; uint32_t count; struct hmac_ctx startpoint, ctx; passlen = strlen(passphrase); bzero(key, keylen); bcopy(salt, saltcount, saltsize); counter = saltcount + saltsize; keyp = key; for (count = 1; keylen > 0; count++, keylen -= bsize, keyp += bsize) { bsize = MIN(keylen, sizeof(md)); be32enc(counter, count); g_eli_crypto_hmac_init(&startpoint, passphrase, passlen); ctx = startpoint; g_eli_crypto_hmac_update(&ctx, saltcount, sizeof(saltcount)); g_eli_crypto_hmac_final(&ctx, md, sizeof(md)); xor(keyp, md, bsize); for(i = 1; i < iterations; i++) { ctx = startpoint; g_eli_crypto_hmac_update(&ctx, md, sizeof(md)); g_eli_crypto_hmac_final(&ctx, md, sizeof(md)); xor(keyp, md, bsize); } } explicit_bzero(&startpoint, sizeof(startpoint)); explicit_bzero(&ctx, sizeof(ctx)); }