CommonKeyDerivationSPI.c [plain text]
#include <CommonCrypto/CommonKeyDerivationSPI.h>
#include <corecrypto/cchkdf.h>
#include <corecrypto/ccnistkdf.h>
#include <corecrypto/ccpbkdf2.h>
#include "CommonDigestPriv.h"
#include "ccMemory.h"
#include "ccdebug.h"
CCStatus
CCKeyDerivationHMac(CCKDFAlgorithm algorithm, CCDigestAlgorithm digest,
unsigned rounds, const void *keyDerivationKey, size_t keyDerivationKeyLen,
const void *label, size_t labelLen,
const void *context, size_t contextLen, const void * __unused iv, size_t __unused ivLen, const void *salt, size_t saltLen, void *derivedKey, size_t derivedKeyLen) {
int cc_retval = 0;
const struct ccdigest_info *di = CCDigestGetDigestInfo(digest);
if(di == NULL) {
CC_DEBUG_LOG("CCKeyDerivationHMac Unknown Digest %d\n");
return kCCParamError;
}
if(!keyDerivationKeyLen || !keyDerivationKey) {
CC_DEBUG_LOG("CCKeyDerivationHMac bad KDK parameters %d\n");
return kCCParamError;
}
if(!derivedKeyLen || !derivedKey) {
CC_DEBUG_LOG("CCKeyDerivationHMac bad derived key parameters %d\n");
return kCCParamError;
}
switch(algorithm) {
case kCCKDFAlgorithmPBKDF2_HMAC:
if(!salt) {
if(saltLen) return kCCParamError;
salt = "";
}
cc_retval = ccpbkdf2_hmac(di, keyDerivationKeyLen, keyDerivationKey,
saltLen, salt, rounds,
derivedKeyLen, derivedKey);
if(cc_retval) return kCCParamError; break;
case kCCKDFAlgorithmCTR_HMAC:
cc_retval = ccnistkdf_ctr_hmac(di, keyDerivationKeyLen, keyDerivationKey,
labelLen, label, contextLen, context,
derivedKeyLen, derivedKey);
if(cc_retval) return kCCParamError; break;
case kCCKDFAlgorithmCTR_HMAC_FIXED:
cc_retval = ccnistkdf_ctr_hmac_fixed(di, keyDerivationKeyLen, keyDerivationKey,
contextLen, context,
derivedKeyLen, derivedKey);
if(cc_retval) return kCCParamError; break;
case kCCKDFAlgorithmHKDF:
cc_retval = cchkdf(di, keyDerivationKeyLen, keyDerivationKey, saltLen, salt,
contextLen, context, derivedKeyLen, derivedKey);
if(cc_retval) return kCCParamError; break;
case kCCKDFAlgorithmFB_HMAC:
case kCCKDFAlgorithmFB_HMAC_FIXED:
case kCCKDFAlgorithmDPIPE_HMAC:
default:
return kCCUnimplemented;
}
return kCCSuccess;
}