* This file is part of the openHiTLS project.
*
* openHiTLS is licensed under the Mulan PSL v2.
* You can use this software according to the terms and conditions of the Mulan PSL v2.
* You may obtain a copy of Mulan PSL v2 at:
*
* http://license.coscl.org.cn/MulanPSL2
*
* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
* See the Mulan PSL v2 for more details.
*/
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include "crypt_errno.h"
#include "crypt_eal_provider.h"
#include "crypt_eal_implprovider.h"
#define CRYPT_EAL_DEFAULT_ATTR "provider=test1,compare1=one,cpmpare3=three"
#define RESULT 1415926
void *Provider_NewCtx(void *provCtx, int32_t algid, BSL_Param *param)
{
(void)provCtx;
(void)param;
int *ctx = malloc(sizeof(int));
return ctx;
}
int32_t Provider_FreeCtx(void *ctx)
{
free(ctx);
return 0;
}
int32_t MD5_Init(void *mdCtx)
{
mdCtx = NULL;
return RESULT;
}
int32_t MD5_GetParam(void *mdCtx, BSL_Param *param)
{
(void)mdCtx;
(void)param;
return CRYPT_SUCCESS;
}
const CRYPT_EAL_Func defMdMd5[] = {
{CRYPT_EAL_IMPLMD_NEWCTX, Provider_NewCtx},
{CRYPT_EAL_IMPLMD_INITCTX, MD5_Init},
{CRYPT_EAL_IMPLMD_UPDATE, NULL},
{CRYPT_EAL_IMPLMD_FINAL, NULL},
{CRYPT_EAL_IMPLMD_DEINITCTX, NULL},
{CRYPT_EAL_IMPLMD_DUPCTX, NULL},
{CRYPT_EAL_IMPLMD_GETPARAM, MD5_GetParam},
{CRYPT_EAL_IMPLMD_FREECTX, Provider_FreeCtx},
CRYPT_EAL_FUNC_END,
};
const CRYPT_EAL_Func defKdfScrypt[] = {
{CRYPT_EAL_IMPLKDF_NEWCTX, Provider_NewCtx},
{CRYPT_EAL_IMPLKDF_SETPARAM, NULL},
{CRYPT_EAL_IMPLKDF_DERIVE, NULL},
{CRYPT_EAL_IMPLKDF_DEINITCTX, NULL},
{CRYPT_EAL_IMPLKDF_CTRL, NULL},
{CRYPT_EAL_IMPLKDF_FREECTX, Provider_FreeCtx},
CRYPT_EAL_FUNC_END,
};
const CRYPT_EAL_Func defMacHmac[] = {
{CRYPT_EAL_IMPLMAC_NEWCTX, Provider_NewCtx},
{CRYPT_EAL_IMPLMAC_INIT, NULL},
{CRYPT_EAL_IMPLMAC_UPDATE, NULL},
{CRYPT_EAL_IMPLMAC_FINAL, NULL},
{CRYPT_EAL_IMPLMAC_REINITCTX, NULL},
{CRYPT_EAL_IMPLMAC_CTRL, NULL},
{CRYPT_EAL_IMPLMAC_FREECTX, Provider_FreeCtx},
CRYPT_EAL_FUNC_END,
};
const CRYPT_EAL_Func defKeyMgmtDsa[] = {
{CRYPT_EAL_IMPLPKEYMGMT_NEWCTX, Provider_NewCtx},
{CRYPT_EAL_IMPLPKEYMGMT_SETPARAM, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_GETPARAM, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_GENKEY, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_SETPRV, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_SETPUB, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_GETPRV, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_GETPUB, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_DUPCTX, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_CHECK, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_COMPARE, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_CTRL, NULL},
{CRYPT_EAL_IMPLPKEYMGMT_FREECTX, Provider_FreeCtx},
CRYPT_EAL_FUNC_END,
};
const CRYPT_EAL_Func defAsymCipherRsa[] = {
{CRYPT_EAL_IMPLPKEYCIPHER_ENCRYPT, NULL},
{CRYPT_EAL_IMPLPKEYCIPHER_DECRYPT, NULL},
CRYPT_EAL_FUNC_END
};
const CRYPT_EAL_Func defExchX25519[] = {
{CRYPT_EAL_IMPLPKEYEXCH_EXCH, NULL},
CRYPT_EAL_FUNC_END
};
const CRYPT_EAL_Func defSignDsa[] = {
{CRYPT_EAL_IMPLPKEYSIGN_SIGN, NULL},
{CRYPT_EAL_IMPLPKEYSIGN_VERIFY, NULL},
CRYPT_EAL_FUNC_END,
};
static const CRYPT_EAL_AlgInfo defMds[] = {
{CRYPT_MD_MD5, defMdMd5, CRYPT_EAL_DEFAULT_ATTR},
CRYPT_EAL_ALGINFO_END
};
static const CRYPT_EAL_AlgInfo defKdfs[] = {
{CRYPT_KDF_SCRYPT, defKdfScrypt, CRYPT_EAL_DEFAULT_ATTR},
CRYPT_EAL_ALGINFO_END
};
static const CRYPT_EAL_AlgInfo defKeyMgmt[] = {
{CRYPT_PKEY_DSA, defKeyMgmtDsa, CRYPT_EAL_DEFAULT_ATTR},
CRYPT_EAL_ALGINFO_END
};
static const CRYPT_EAL_AlgInfo defAsymCiphers[] = {
{CRYPT_PKEY_RSA, defAsymCipherRsa, CRYPT_EAL_DEFAULT_ATTR},
CRYPT_EAL_ALGINFO_END
};
static const CRYPT_EAL_AlgInfo defKeyExch[] = {
{CRYPT_PKEY_X25519, defExchX25519, CRYPT_EAL_DEFAULT_ATTR},
CRYPT_EAL_ALGINFO_END
};
static const CRYPT_EAL_AlgInfo defSigns[] = {
{CRYPT_PKEY_DSA, defSignDsa, CRYPT_EAL_DEFAULT_ATTR},
CRYPT_EAL_ALGINFO_END
};
static const CRYPT_EAL_AlgInfo defMacs[] = {
{CRYPT_MAC_HMAC_MD5, defMacHmac, CRYPT_EAL_DEFAULT_ATTR},
CRYPT_EAL_ALGINFO_END
};
static int32_t CRYPT_EAL_DefaultProvQuery(void *provCtx, int32_t operaId, const CRYPT_EAL_AlgInfo **algInfos)
{
(void) provCtx;
int32_t ret = CRYPT_SUCCESS;
switch (operaId) {
case CRYPT_EAL_OPERAID_SYMMCIPHER:
break;
case CRYPT_EAL_OPERAID_KEYMGMT:
*algInfos = defKeyMgmt;
break;
case CRYPT_EAL_OPERAID_SIGN:
*algInfos = defSigns;
break;
case CRYPT_EAL_OPERAID_ASYMCIPHER:
*algInfos = defAsymCiphers;
break;
case CRYPT_EAL_OPERAID_KEYEXCH:
*algInfos = defKeyExch;
break;
case CRYPT_EAL_OPERAID_KEM:
break;
case CRYPT_EAL_OPERAID_HASH:
*algInfos = defMds;
break;
case CRYPT_EAL_OPERAID_MAC:
*algInfos = defMacs;
break;
case CRYPT_EAL_OPERAID_KDF:
*algInfos = defKdfs;
break;
case CRYPT_EAL_OPERAID_RAND:
break;
default:
ret = CRYPT_NOT_SUPPORT;
break;
}
return ret;
}
static void CRYPT_EAL_DefaultProvFree(void *provCtx)
{
return;
}
static CRYPT_EAL_Func defProvOutFuncs[] = {
{CRYPT_EAL_PROVCB_QUERY, CRYPT_EAL_DefaultProvQuery},
{CRYPT_EAL_PROVCB_FREE, CRYPT_EAL_DefaultProvFree},
{CRYPT_EAL_PROVCB_CTRL, NULL},
CRYPT_EAL_FUNC_END
};
int32_t CRYPT_EAL_ProviderInit(CRYPT_EAL_ProvMgrCtx *mgrCtx,
BSL_Param *param, CRYPT_EAL_Func *capFuncs, CRYPT_EAL_Func **outFuncs, void **provCtx)
{
CRYPT_RandSeedMethod entroy = {0};
CRYPT_EAL_ProvMgrCtrlCb mgrCtrl = NULL;
int32_t index = 0;
while (capFuncs[index].id != 0) {
switch (capFuncs[index].id) {
case CRYPT_EAL_CAP_GETENTROPY:
entroy.getEntropy = capFuncs[index].func;
break;
case CRYPT_EAL_CAP_CLEANENTROPY:
entroy.cleanEntropy = capFuncs[index].func;
break;
case CRYPT_EAL_CAP_GETNONCE:
entroy.getNonce = capFuncs[index].func;
break;
case CRYPT_EAL_CAP_CLEANNONCE:
entroy.cleanNonce = capFuncs[index].func;
break;
case CRYPT_EAL_CAP_MGRCTXCTRL:
mgrCtrl = capFuncs[index].func;
break;
default:
return CRYPT_PROVIDER_ERR_UNEXPECTED_IMPL;
}
index++;
}
void *seedCtx = NULL;
void *libCtx = NULL;
if (entroy.getEntropy == NULL || entroy.cleanEntropy == NULL || entroy.getNonce == NULL ||
entroy.cleanNonce == NULL || mgrCtrl == NULL) {
return CRYPT_NULL_INPUT;
}
int32_t ret = mgrCtrl(mgrCtx, CRYPT_EAL_MGR_GETSEEDCTX, &seedCtx, 0);
if (ret != CRYPT_SUCCESS) {
return ret;
}
ret = mgrCtrl(mgrCtx, CRYPT_EAL_MGR_GETLIBCTX, &libCtx, 0);
if (ret != CRYPT_SUCCESS) {
return ret;
}
CRYPT_Data entropy = {NULL, 0};
CRYPT_Range entropyRange = {32, 2147483632};
ret = entroy.getEntropy(seedCtx, &entropy, 256, &entropyRange);
if (ret != CRYPT_SUCCESS) {
return CRYPT_DRBG_FAIL_GET_ENTROPY;
}
entroy.cleanEntropy(seedCtx, &entropy);
if (param != NULL) {
if (param[0].value != libCtx) {
return CRYPT_INVALID_ARG;
}
}
*outFuncs = defProvOutFuncs;
return 0;
}