mirror of
https://github.com/wolfSSL/wolfssl.git
synced 2025-08-01 03:34:39 +02:00
allow different hashes with PKCS7 SignedData, cleanup conditional builds
This commit is contained in:
13
.gitignore
vendored
13
.gitignore
vendored
@@ -91,7 +91,18 @@ ecc-key.pem
|
||||
certreq.der
|
||||
certreq.pem
|
||||
pkcs7cert.der
|
||||
pkcs7signedData.der
|
||||
pkcs7signedData_RSA_SHA.der
|
||||
pkcs7signedData_RSA_SHA_noattr.der
|
||||
pkcs7signedData_RSA_SHA224.der
|
||||
pkcs7signedData_RSA_SHA256.der
|
||||
pkcs7signedData_RSA_SHA384.der
|
||||
pkcs7signedData_RSA_SHA512.der
|
||||
pkcs7signedData_ECDSA_SHA.der
|
||||
pkcs7signedData_ECDSA_SHA_noattr.der
|
||||
pkcs7signedData_ECDSA_SHA224.der
|
||||
pkcs7signedData_ECDSA_SHA256.der
|
||||
pkcs7signedData_ECDSA_SHA384.der
|
||||
pkcs7signedData_ECDSA_SHA512.der
|
||||
pkcs7envelopedDataDES3.der
|
||||
pkcs7envelopedDataAES128CBC.der
|
||||
pkcs7envelopedDataAES192CBC.der
|
||||
|
13
Makefile.am
13
Makefile.am
@@ -54,7 +54,18 @@ CLEANFILES+= cert.der \
|
||||
pkcs7envelopedDataAES128CBC.der \
|
||||
pkcs7envelopedDataAES192CBC.der \
|
||||
pkcs7envelopedDataAES256CBC.der \
|
||||
pkcs7signedData.der
|
||||
pkcs7signedData_RSA_SHA.der \
|
||||
pkcs7signedData_RSA_SHA_noattr.der \
|
||||
pkcs7signedData_RSA_SHA224.der \
|
||||
pkcs7signedData_RSA_SHA256.der \
|
||||
pkcs7signedData_RSA_SHA384.der \
|
||||
pkcs7signedData_RSA_SHA512.der \
|
||||
pkcs7signedData_ECDSA_SHA.der \
|
||||
pkcs7signedData_ECDSA_SHA_noattr.der \
|
||||
pkcs7signedData_ECDSA_SHA224.der \
|
||||
pkcs7signedData_ECDSA_SHA256.der \
|
||||
pkcs7signedData_ECDSA_SHA384.der \
|
||||
pkcs7signedData_ECDSA_SHA512.der
|
||||
|
||||
exampledir = $(docdir)/example
|
||||
dist_example_DATA=
|
||||
|
@@ -31,6 +31,7 @@
|
||||
#include <wolfssl/wolfcrypt/pkcs7.h>
|
||||
#include <wolfssl/wolfcrypt/error-crypt.h>
|
||||
#include <wolfssl/wolfcrypt/logging.h>
|
||||
#include <wolfssl/wolfcrypt/hash.h>
|
||||
#ifndef NO_RSA
|
||||
#include <wolfssl/wolfcrypt/rsa.h>
|
||||
#endif
|
||||
@@ -346,9 +347,10 @@ typedef struct EncodedAttrib {
|
||||
|
||||
|
||||
typedef struct ESD {
|
||||
Sha sha;
|
||||
byte contentDigest[SHA_DIGEST_SIZE + 2]; /* content only + ASN.1 heading */
|
||||
byte contentAttribsDigest[SHA_DIGEST_SIZE];
|
||||
wc_HashAlg hash;
|
||||
enum wc_HashType hashType;
|
||||
byte contentDigest[WC_MAX_DIGEST_SIZE + 2]; /* content only + ASN.1 heading */
|
||||
byte contentAttribsDigest[WC_MAX_DIGEST_SIZE];
|
||||
byte encContentDigest[512];
|
||||
|
||||
byte outerSeq[MAX_SEQ_SZ];
|
||||
@@ -434,6 +436,8 @@ static int FlattenAttributes(byte* output, EncodedAttrib* ea, int eaSz)
|
||||
}
|
||||
|
||||
|
||||
#ifndef NO_RSA
|
||||
|
||||
/* returns size of signature put into out, negative on error */
|
||||
static int wc_PKCS7_RsaSign(PKCS7* pkcs7, byte* in, word32 inSz, ESD* esd)
|
||||
{
|
||||
@@ -459,6 +463,7 @@ static int wc_PKCS7_RsaSign(PKCS7* pkcs7, byte* in, word32 inSz, ESD* esd)
|
||||
ret = wc_InitRsaKey(privKey, pkcs7->heap);
|
||||
|
||||
if (ret == 0) {
|
||||
idx = 0;
|
||||
ret = wc_RsaPrivateKeyDecode(pkcs7->privateKey, &idx, privKey,
|
||||
pkcs7->privateKeySz);
|
||||
}
|
||||
@@ -477,6 +482,10 @@ static int wc_PKCS7_RsaSign(PKCS7* pkcs7, byte* in, word32 inSz, ESD* esd)
|
||||
return ret;
|
||||
}
|
||||
|
||||
#endif /* NO_RSA */
|
||||
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
|
||||
/* returns size of signature put into out, negative on error */
|
||||
static int wc_PKCS7_EcdsaSign(PKCS7* pkcs7, byte* in, word32 inSz, ESD* esd)
|
||||
@@ -524,6 +533,8 @@ static int wc_PKCS7_EcdsaSign(PKCS7* pkcs7, byte* in, word32 inSz, ESD* esd)
|
||||
return ret;
|
||||
}
|
||||
|
||||
#endif /* HAVE_ECC */
|
||||
|
||||
|
||||
/* builds up SignedData signed attributes, including default ones.
|
||||
*
|
||||
@@ -533,6 +544,7 @@ static int wc_PKCS7_EcdsaSign(PKCS7* pkcs7, byte* in, word32 inSz, ESD* esd)
|
||||
* return 0 on success, negative on error */
|
||||
static int wc_PKCS7_BuildSignedAttributes(PKCS7* pkcs7, ESD* esd)
|
||||
{
|
||||
int hashSz;
|
||||
|
||||
byte contentTypeOid[] =
|
||||
{ ASN_OBJECT_ID, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xF7, 0x0d, 0x01,
|
||||
@@ -547,9 +559,13 @@ static int wc_PKCS7_BuildSignedAttributes(PKCS7* pkcs7, ESD* esd)
|
||||
PKCS7Attrib cannedAttribs[2];
|
||||
word32 cannedAttribsCount;
|
||||
|
||||
if (pkcs7 == NULL || esd == NULL)
|
||||
if (pkcs7 == NULL || esd == NULL || &esd->hash == NULL)
|
||||
return BAD_FUNC_ARG;
|
||||
|
||||
hashSz = wc_HashGetDigestSize(esd->hashType);
|
||||
if (hashSz < 0)
|
||||
return hashSz;
|
||||
|
||||
cannedAttribsCount = sizeof(cannedAttribs)/sizeof(PKCS7Attrib);
|
||||
|
||||
cannedAttribs[0].oid = contentTypeOid;
|
||||
@@ -559,7 +575,7 @@ static int wc_PKCS7_BuildSignedAttributes(PKCS7* pkcs7, ESD* esd)
|
||||
cannedAttribs[1].oid = messageDigestOid;
|
||||
cannedAttribs[1].oidSz = sizeof(messageDigestOid);
|
||||
cannedAttribs[1].value = esd->contentDigest;
|
||||
cannedAttribs[1].valueSz = sizeof(esd->contentDigest);
|
||||
cannedAttribs[1].valueSz = hashSz + 2; /* ASN.1 heading */
|
||||
|
||||
esd->signedAttribsCount += cannedAttribsCount;
|
||||
esd->signedAttribsSz += EncodeAttributes(&esd->signedAttribs[0], 2,
|
||||
@@ -648,19 +664,24 @@ static int wc_PKCS7_BuildDigestInfo(PKCS7* pkcs7, byte* flatSignedAttribs,
|
||||
word32 flatSignedAttribsSz, ESD* esd,
|
||||
byte* digestInfo, word32* digestInfoSz)
|
||||
{
|
||||
int ret, digIdx = 0;
|
||||
int ret, hashSz, digIdx = 0;
|
||||
byte digestInfoSeq[MAX_SEQ_SZ];
|
||||
byte digestStr[MAX_OCTET_STR_SZ];
|
||||
byte attribSet[MAX_SET_SZ];
|
||||
word32 digestInfoSeqSz, digestStrSz;
|
||||
byte algoId[MAX_ALGO_SZ];
|
||||
word32 digestInfoSeqSz, digestStrSz, algoIdSz;
|
||||
word32 attribSetSz;
|
||||
|
||||
if (pkcs7 == NULL || esd == NULL || &esd->sha == NULL ||
|
||||
if (pkcs7 == NULL || esd == NULL || &esd->hash == NULL ||
|
||||
esd->contentDigest == NULL || esd->signerDigAlgoId == NULL ||
|
||||
digestInfo == NULL || digestInfoSz == NULL) {
|
||||
return BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
hashSz = wc_HashGetDigestSize(esd->hashType);
|
||||
if (hashSz < 0)
|
||||
return hashSz;
|
||||
|
||||
if (pkcs7->signedAttribsSz != 0) {
|
||||
|
||||
if (flatSignedAttribs == NULL)
|
||||
@@ -668,38 +689,49 @@ static int wc_PKCS7_BuildDigestInfo(PKCS7* pkcs7, byte* flatSignedAttribs,
|
||||
|
||||
attribSetSz = SetSet(flatSignedAttribsSz, attribSet);
|
||||
|
||||
ret = wc_InitSha(&esd->sha);
|
||||
ret = wc_HashInit(&esd->hash, esd->hashType);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
wc_ShaUpdate(&esd->sha, attribSet, attribSetSz);
|
||||
wc_ShaUpdate(&esd->sha, flatSignedAttribs, flatSignedAttribsSz);
|
||||
wc_ShaFinal(&esd->sha, esd->contentAttribsDigest);
|
||||
ret = wc_HashUpdate(&esd->hash, esd->hashType,
|
||||
attribSet, attribSetSz);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
ret = wc_HashUpdate(&esd->hash, esd->hashType,
|
||||
flatSignedAttribs, flatSignedAttribsSz);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
ret = wc_HashFinal(&esd->hash, esd->hashType,
|
||||
esd->contentAttribsDigest);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
} else {
|
||||
/* when no attrs, digest is contentDigest without tag and length */
|
||||
XMEMCPY(esd->contentAttribsDigest, esd->contentDigest + 2,
|
||||
SHA_DIGEST_SIZE);
|
||||
XMEMCPY(esd->contentAttribsDigest, esd->contentDigest + 2, hashSz);
|
||||
}
|
||||
|
||||
digestStrSz = SetOctetString(SHA_DIGEST_SIZE, digestStr);
|
||||
digestInfoSeqSz = SetSequence(esd->signerDigAlgoIdSz +
|
||||
digestStrSz + SHA_DIGEST_SIZE,
|
||||
/* set algoID, with NULL attributes */
|
||||
algoIdSz = SetAlgoID(pkcs7->hashOID, algoId, oidHashType, 0);
|
||||
|
||||
digestStrSz = SetOctetString(hashSz, digestStr);
|
||||
digestInfoSeqSz = SetSequence(algoIdSz + digestStrSz + hashSz,
|
||||
digestInfoSeq);
|
||||
|
||||
if (*digestInfoSz < (digestInfoSeqSz + esd->signerDigAlgoIdSz +
|
||||
digestStrSz + SHA_DIGEST_SIZE)) {
|
||||
if (*digestInfoSz < (digestInfoSeqSz + algoIdSz + digestStrSz + hashSz)) {
|
||||
return BUFFER_E;
|
||||
}
|
||||
|
||||
XMEMCPY(digestInfo + digIdx, digestInfoSeq, digestInfoSeqSz);
|
||||
digIdx += digestInfoSeqSz;
|
||||
XMEMCPY(digestInfo + digIdx, esd->signerDigAlgoId, esd->signerDigAlgoIdSz);
|
||||
digIdx += esd->signerDigAlgoIdSz;
|
||||
XMEMCPY(digestInfo + digIdx, algoId, algoIdSz);
|
||||
digIdx += algoIdSz;
|
||||
XMEMCPY(digestInfo + digIdx, digestStr, digestStrSz);
|
||||
digIdx += digestStrSz;
|
||||
XMEMCPY(digestInfo + digIdx, esd->contentAttribsDigest, SHA_DIGEST_SIZE);
|
||||
digIdx += SHA_DIGEST_SIZE;
|
||||
XMEMCPY(digestInfo + digIdx, esd->contentAttribsDigest, hashSz);
|
||||
digIdx += hashSz;
|
||||
|
||||
*digestInfoSz = digIdx;
|
||||
|
||||
@@ -721,8 +753,11 @@ static int wc_PKCS7_SignedDataBuildSignature(PKCS7* pkcs7,
|
||||
ESD* esd)
|
||||
{
|
||||
int ret;
|
||||
#ifdef HAVE_ECC
|
||||
int hashSz;
|
||||
#endif
|
||||
word32 digestInfoSz = MAX_SEQ_SZ + MAX_ALGO_SZ +
|
||||
MAX_OCTET_STR_SZ + SHA_DIGEST_SIZE;
|
||||
MAX_OCTET_STR_SZ + WC_MAX_DIGEST_SIZE;
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
byte* digestInfo;
|
||||
#else
|
||||
@@ -752,16 +787,28 @@ static int wc_PKCS7_SignedDataBuildSignature(PKCS7* pkcs7,
|
||||
/* sign digestInfo */
|
||||
switch (pkcs7->publicKeyOID) {
|
||||
|
||||
#ifndef NO_RSA
|
||||
case RSAk:
|
||||
ret = wc_PKCS7_RsaSign(pkcs7, digestInfo, digestInfoSz, esd);
|
||||
break;
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
case ECDSAk:
|
||||
/* CMS with ECDSA does not sign DigestInfo structure
|
||||
* like PKCS#7 with RSA does */
|
||||
hashSz = wc_HashGetDigestSize(esd->hashType);
|
||||
if (hashSz < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return hashSz;
|
||||
}
|
||||
|
||||
ret = wc_PKCS7_EcdsaSign(pkcs7, esd->contentAttribsDigest,
|
||||
SHA_DIGEST_SIZE, esd);
|
||||
hashSz, esd);
|
||||
break;
|
||||
#endif
|
||||
|
||||
default:
|
||||
WOLFSSL_MSG("Unsupported public key type");
|
||||
@@ -780,6 +827,53 @@ static int wc_PKCS7_SignedDataBuildSignature(PKCS7* pkcs7,
|
||||
}
|
||||
|
||||
|
||||
/* sets the wc_HashType in ESD struct based on pkcs7->hashOID
|
||||
*
|
||||
* pkcs7 - pointer to initialized PKCS7 struct
|
||||
* type - [OUT] pointer to wc_HashType for output
|
||||
*
|
||||
* returns hash digest size on success, negative on error */
|
||||
static enum wc_HashType wc_PKCS7_SetHashType(PKCS7* pkcs7,
|
||||
enum wc_HashType* type)
|
||||
{
|
||||
if (pkcs7 == NULL || type == NULL)
|
||||
return BAD_FUNC_ARG;
|
||||
|
||||
switch (pkcs7->hashOID) {
|
||||
|
||||
#ifndef NO_SHA
|
||||
case SHAh:
|
||||
*type = WC_HASH_TYPE_SHA;
|
||||
break;
|
||||
#endif
|
||||
#ifdef WOLFSSL_SHA224
|
||||
case SHA224h:
|
||||
*type = WC_HASH_TYPE_SHA224;
|
||||
break;
|
||||
#endif
|
||||
#ifndef NO_SHA256
|
||||
case SHA256h:
|
||||
*type = WC_HASH_TYPE_SHA256;
|
||||
break;
|
||||
#endif
|
||||
#ifdef WOLFSSL_SHA384
|
||||
case SHA384h:
|
||||
*type = WC_HASH_TYPE_SHA384;
|
||||
break;
|
||||
#endif
|
||||
#ifdef WOLFSSL_SHA512
|
||||
case SHA512h:
|
||||
*type = WC_HASH_TYPE_SHA512;
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
return BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
return wc_HashGetDigestSize(*type);
|
||||
}
|
||||
|
||||
|
||||
/* build PKCS#7 signedData content type */
|
||||
int wc_PKCS7_EncodeSignedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
{
|
||||
@@ -800,7 +894,7 @@ int wc_PKCS7_EncodeSignedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
word32 signerInfoSz = 0;
|
||||
word32 totalSz = 0;
|
||||
int idx = 0, ret = 0;
|
||||
int digEncAlgoId, digEncAlgoType;
|
||||
int digEncAlgoId, digEncAlgoType, hashSz;
|
||||
byte* flatSignedAttribs = NULL;
|
||||
word32 flatSignedAttribsSz = 0;
|
||||
word32 innerOidSz = sizeof(innerOid);
|
||||
@@ -820,7 +914,16 @@ int wc_PKCS7_EncodeSignedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
#endif
|
||||
|
||||
XMEMSET(esd, 0, sizeof(ESD));
|
||||
ret = wc_InitSha(&esd->sha);
|
||||
|
||||
hashSz = wc_PKCS7_SetHashType(pkcs7, &esd->hashType);
|
||||
if (hashSz < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(esd, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return hashSz;
|
||||
}
|
||||
|
||||
ret = wc_HashInit(&esd->hash, esd->hashType);
|
||||
if (ret != 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(esd, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
@@ -830,10 +933,24 @@ int wc_PKCS7_EncodeSignedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
|
||||
if (pkcs7->contentSz != 0)
|
||||
{
|
||||
wc_ShaUpdate(&esd->sha, pkcs7->content, pkcs7->contentSz);
|
||||
ret = wc_HashUpdate(&esd->hash, esd->hashType,
|
||||
pkcs7->content, pkcs7->contentSz);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(esd, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
esd->contentDigest[0] = ASN_OCTET_STRING;
|
||||
esd->contentDigest[1] = SHA_DIGEST_SIZE;
|
||||
wc_ShaFinal(&esd->sha, &esd->contentDigest[2]);
|
||||
esd->contentDigest[1] = hashSz;
|
||||
ret = wc_HashFinal(&esd->hash, esd->hashType,
|
||||
&esd->contentDigest[2]);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(esd, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
esd->innerOctetsSz = SetOctetString(pkcs7->contentSz, esd->innerOctets);
|
||||
@@ -873,6 +990,12 @@ int wc_PKCS7_EncodeSignedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
|
||||
/* build up signed attributes */
|
||||
ret = wc_PKCS7_BuildSignedAttributes(pkcs7, esd);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(esd, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return MEMORY_E;
|
||||
}
|
||||
|
||||
flatSignedAttribs = (byte*)XMALLOC(esd->signedAttribsSz, pkcs7->heap,
|
||||
DYNAMIC_TYPE_PKCS);
|
||||
@@ -1014,26 +1137,31 @@ int wc_PKCS7_EncodeSignedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
}
|
||||
|
||||
|
||||
#ifndef NO_RSA
|
||||
|
||||
/* returns size of signature put into out, negative on error */
|
||||
static int wc_PKCS7_RsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
byte* hash, word32 hashSz)
|
||||
{
|
||||
(void)hash;
|
||||
(void)hashSz;
|
||||
|
||||
#define MAX_PKCS7_DIGEST_SZ (MAX_SEQ_SZ + MAX_ALGO_SZ +\
|
||||
MAX_OCTET_STR_SZ + WC_MAX_DIGEST_SIZE)
|
||||
int ret = 0;
|
||||
word32 scratch = 0;
|
||||
#define MAX_PKCS7_DIGEST_SZ (MAX_SEQ_SZ + MAX_ALGO_SZ +\
|
||||
MAX_OCTET_STR_SZ + SHA_DIGEST_SIZE)
|
||||
|
||||
if (pkcs7 == NULL || pkcs7->publicKey == NULL || sig == NULL ||
|
||||
hash == NULL)
|
||||
return BAD_FUNC_ARG;
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
byte* digest;
|
||||
RsaKey* key;
|
||||
#else
|
||||
byte digest[MAX_PKCS7_DIGEST_SZ];
|
||||
RsaKey stack_key;
|
||||
RsaKey* key = &stack_key;
|
||||
#endif
|
||||
|
||||
if (pkcs7 == NULL || pkcs7->publicKey == NULL ||
|
||||
sig == NULL || hash == NULL) {
|
||||
return BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
digest = (byte*)XMALLOC(MAX_PKCS7_DIGEST_SZ, NULL,
|
||||
DYNAMIC_TYPE_TMP_BUFFER);
|
||||
|
||||
@@ -1045,10 +1173,6 @@ static int wc_PKCS7_RsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
XFREE(digest, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
return MEMORY_E;
|
||||
}
|
||||
#else
|
||||
byte digest[MAX_PKCS7_DIGEST_SZ];
|
||||
RsaKey stack_key;
|
||||
RsaKey* key = &stack_key;
|
||||
#endif
|
||||
|
||||
XMEMSET(digest, 0, MAX_PKCS7_DIGEST_SZ);
|
||||
@@ -1061,6 +1185,7 @@ static int wc_PKCS7_RsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (wc_RsaPublicKeyDecode(pkcs7->publicKey, &scratch, key,
|
||||
pkcs7->publicKeySz) < 0) {
|
||||
WOLFSSL_MSG("ASN RSA key decode error");
|
||||
@@ -1075,8 +1200,9 @@ static int wc_PKCS7_RsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
|
||||
wc_FreeRsaKey(key);
|
||||
|
||||
if (XMEMCMP(digest, hash, ret) != 0)
|
||||
if (((int)hashSz != ret) || (XMEMCMP(digest, hash, ret) != 0)) {
|
||||
ret = SIG_VERIFY_E;
|
||||
}
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digest, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
@@ -1086,23 +1212,32 @@ static int wc_PKCS7_RsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
return ret;
|
||||
}
|
||||
|
||||
#endif /* NO_RSA */
|
||||
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
|
||||
/* returns size of signature put into out, negative on error */
|
||||
static int wc_PKCS7_EcdsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
byte* hash, word32 hashSz)
|
||||
{
|
||||
#define MAX_PKCS7_DIGEST_SZ (MAX_SEQ_SZ + MAX_ALGO_SZ +\
|
||||
MAX_OCTET_STR_SZ + WC_MAX_DIGEST_SIZE)
|
||||
int ret = 0;
|
||||
int stat = 0;
|
||||
#define MAX_PKCS7_DIGEST_SZ (MAX_SEQ_SZ + MAX_ALGO_SZ +\
|
||||
MAX_OCTET_STR_SZ + SHA_DIGEST_SIZE)
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
byte* digest;
|
||||
ecc_key* key;
|
||||
#else
|
||||
byte digest[MAX_PKCS7_DIGEST_SZ];
|
||||
ecc_key stack_key;
|
||||
ecc_key* key = &stack_key;
|
||||
#endif
|
||||
|
||||
if (pkcs7 == NULL || pkcs7->publicKey == NULL || sig == NULL)
|
||||
return BAD_FUNC_ARG;
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
byte* digest;
|
||||
ecc_key* key;
|
||||
|
||||
digest = (byte*)XMALLOC(MAX_PKCS7_DIGEST_SZ, NULL,
|
||||
DYNAMIC_TYPE_TMP_BUFFER);
|
||||
|
||||
@@ -1114,10 +1249,6 @@ static int wc_PKCS7_EcdsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
XFREE(digest, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
return MEMORY_E;
|
||||
}
|
||||
#else
|
||||
byte digest[MAX_PKCS7_DIGEST_SZ];
|
||||
ecc_key stack_key;
|
||||
ecc_key* key = &stack_key;
|
||||
#endif
|
||||
|
||||
XMEMSET(digest, 0, MAX_PKCS7_DIGEST_SZ);
|
||||
@@ -1130,6 +1261,7 @@ static int wc_PKCS7_EcdsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (wc_ecc_import_x963(pkcs7->publicKey, pkcs7->publicKeySz, key) < 0) {
|
||||
WOLFSSL_MSG("ASN ECDSA key decode error");
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
@@ -1155,97 +1287,258 @@ static int wc_PKCS7_EcdsaVerify(PKCS7* pkcs7, byte* sig, int sigSz,
|
||||
return ret;
|
||||
}
|
||||
|
||||
#endif /* HAVE_ECC */
|
||||
|
||||
|
||||
/* build SignedData digest, both in PKCS#7 DigestInfo format and
|
||||
* as plain digest for CMS.
|
||||
*
|
||||
* pkcs7 - pointer to initialized PKCS7 struct
|
||||
* signedAttrib - signed attributes
|
||||
* signedAttribSz - size of signedAttrib, octets
|
||||
* pkcs7Digest - [OUT] PKCS#7 DigestInfo
|
||||
* pkcs7DigestSz - [IN/OUT] size of pkcs7Digest
|
||||
* plainDigest - [OUT] pointer to plain digest, offset into pkcs7Digest
|
||||
* plainDigestSz - [OUT] size of digest at plainDigest
|
||||
*
|
||||
* returns 0 on success, negative on error */
|
||||
static int wc_PKCS7_BuildSignedDataDigest(PKCS7* pkcs7, byte* signedAttrib,
|
||||
word32 signedAttribSz, byte* digAlgId,
|
||||
word32 digAlgIdSz, byte* out,
|
||||
word32 outSz)
|
||||
word32 signedAttribSz, byte* pkcs7Digest,
|
||||
word32* pkcs7DigestSz, byte** plainDigest,
|
||||
word32* plainDigestSz)
|
||||
{
|
||||
int ret = 0;
|
||||
int ret = 0, digIdx = 0, hashSz;
|
||||
word32 attribSetSz;
|
||||
byte attribSet[MAX_SET_SZ];
|
||||
|
||||
byte digest[SHA_DIGEST_SIZE];
|
||||
|
||||
byte digestInfo[MAX_SEQ_SZ + MAX_ALGO_SZ + MAX_OCTET_STR_SZ +
|
||||
SHA_DIGEST_SIZE];
|
||||
byte digest[WC_MAX_DIGEST_SIZE];
|
||||
byte digestInfoSeq[MAX_SEQ_SZ];
|
||||
byte digestStr[MAX_OCTET_STR_SZ];
|
||||
word32 digestInfoSeqSz, digestStrSz;
|
||||
int digIdx = 0;
|
||||
byte algoId[MAX_ALGO_SZ];
|
||||
word32 digestInfoSeqSz, digestStrSz, algoIdSz;
|
||||
word32 digestInfoSz = MAX_SEQ_SZ + MAX_ALGO_SZ + MAX_OCTET_STR_SZ +
|
||||
WC_MAX_DIGEST_SIZE;
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
byte* digestInfo;
|
||||
#else
|
||||
byte digestInfo[digestInfoSz];
|
||||
#endif
|
||||
|
||||
Sha sha;
|
||||
wc_HashAlg hash;
|
||||
enum wc_HashType hashType;
|
||||
|
||||
if (pkcs7 == NULL || digAlgId == NULL || out == NULL)
|
||||
if (pkcs7 == NULL || pkcs7Digest == NULL ||
|
||||
pkcs7DigestSz == NULL || plainDigest == NULL) {
|
||||
return BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
XMEMSET(out, 0, outSz);
|
||||
XMEMSET(digest, 0, SHA_DIGEST_SIZE);
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
digestInfo = (byte*)XMALLOC(digestInfoSz, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
if (digestInfo == NULL)
|
||||
return MEMORY_E;
|
||||
#endif
|
||||
|
||||
XMEMSET(pkcs7Digest, 0, *pkcs7DigestSz);
|
||||
XMEMSET(digest, 0, WC_MAX_DIGEST_SIZE);
|
||||
XMEMSET(digestInfo, 0, digestInfoSz);
|
||||
|
||||
hashSz = wc_PKCS7_SetHashType(pkcs7, &hashType);
|
||||
if (hashSz < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return hashSz;
|
||||
}
|
||||
|
||||
/* calculate digest */
|
||||
ret = wc_InitSha(&sha);
|
||||
if (ret < 0)
|
||||
ret = wc_HashInit(&hash, hashType);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (signedAttribSz > 0) {
|
||||
|
||||
if (signedAttrib == NULL)
|
||||
if (signedAttrib == NULL) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
attribSetSz = SetSet(signedAttribSz, attribSet);
|
||||
wc_ShaUpdate(&sha, attribSet, attribSetSz);
|
||||
wc_ShaUpdate(&sha, signedAttrib, signedAttribSz);
|
||||
wc_ShaFinal(&sha, digest);
|
||||
ret = wc_HashUpdate(&hash, hashType, attribSet, attribSetSz);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = wc_HashUpdate(&hash, hashType, signedAttrib, signedAttribSz);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = wc_HashFinal(&hash, hashType, digest);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
if (pkcs7->content == NULL)
|
||||
if (pkcs7->content == NULL) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
wc_ShaUpdate(&sha, pkcs7->content, pkcs7->contentSz);
|
||||
wc_ShaFinal(&sha, digest);
|
||||
ret = wc_HashUpdate(&hash, hashType, pkcs7->content, pkcs7->contentSz);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = wc_HashFinal(&hash, hashType, digest);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
/* form input to verify operation */
|
||||
if (pkcs7->publicKeyOID == RSAk) {
|
||||
/* Set algoID, with NULL attributes */
|
||||
algoIdSz = SetAlgoID(pkcs7->hashOID, algoId, oidHashType, 0);
|
||||
|
||||
digestStrSz = SetOctetString(SHA_DIGEST_SIZE, digestStr);
|
||||
digestInfoSeqSz = SetSequence(digAlgIdSz + digestStrSz +
|
||||
SHA_DIGEST_SIZE, digestInfoSeq);
|
||||
digestStrSz = SetOctetString(hashSz, digestStr);
|
||||
digestInfoSeqSz = SetSequence(algoIdSz + digestStrSz + hashSz,
|
||||
digestInfoSeq);
|
||||
|
||||
XMEMCPY(digestInfo + digIdx, digestInfoSeq, digestInfoSeqSz);
|
||||
digIdx += digestInfoSeqSz;
|
||||
XMEMCPY(digestInfo + digIdx, digAlgId, digAlgIdSz);
|
||||
digIdx += digAlgIdSz;
|
||||
XMEMCPY(digestInfo + digIdx, digestStr, digestStrSz);
|
||||
digIdx += digestStrSz;
|
||||
XMEMCPY(digestInfo + digIdx, digest, SHA_DIGEST_SIZE);
|
||||
digIdx += SHA_DIGEST_SIZE;
|
||||
XMEMCPY(digestInfo + digIdx, digestInfoSeq, digestInfoSeqSz);
|
||||
digIdx += digestInfoSeqSz;
|
||||
XMEMCPY(digestInfo + digIdx, algoId, algoIdSz);
|
||||
digIdx += algoIdSz;
|
||||
XMEMCPY(digestInfo + digIdx, digestStr, digestStrSz);
|
||||
digIdx += digestStrSz;
|
||||
XMEMCPY(digestInfo + digIdx, digest, hashSz);
|
||||
digIdx += hashSz;
|
||||
|
||||
XMEMCPY(out, digestInfo, digIdx);
|
||||
XMEMCPY(pkcs7Digest, digestInfo, digIdx);
|
||||
*pkcs7DigestSz = digIdx;
|
||||
|
||||
} else if (pkcs7->publicKeyOID == ECDSAk) {
|
||||
/* set plain digest pointer */
|
||||
*plainDigest = pkcs7Digest + digIdx - hashSz;
|
||||
*plainDigestSz = hashSz;
|
||||
|
||||
XMEMCPY(out, digest, SHA_DIGEST_SIZE);
|
||||
digIdx = SHA_DIGEST_SIZE;
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(digestInfo, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* verifies SignedData signature, over either PKCS#7 DigestInfo or
|
||||
* content digest.
|
||||
*
|
||||
* pkcs7 - pointer to initialized PKCS7 struct
|
||||
* sig - signature to verify
|
||||
* sigSz - size of sig
|
||||
* signedAttrib - signed attributes, or null if empty
|
||||
* signedAttribSz - size of signedAttributes
|
||||
*
|
||||
* return 0 on success, negative on error */
|
||||
static int wc_PKCS7_SignedDataVerifySignature(PKCS7* pkcs7, byte* sig,
|
||||
word32 sigSz, byte* signedAttrib,
|
||||
word32 signedAttribSz)
|
||||
{
|
||||
int ret = 0;
|
||||
word32 plainDigestSz, pkcs7DigestSz;
|
||||
word32 maxDigestSz = MAX_SEQ_SZ + MAX_ALGO_SZ + MAX_OCTET_STR_SZ +
|
||||
WC_MAX_DIGEST_SIZE;
|
||||
|
||||
byte* plainDigest; /* offset into pkcs7Digest */
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
byte* pkcs7Digest;
|
||||
#else
|
||||
byte pkcs7Digest[maxDigestSz];
|
||||
#endif
|
||||
|
||||
if (pkcs7 == NULL)
|
||||
return BAD_FUNC_ARG;
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
pkcs7Digest = (byte*)XMALLOC(maxDigestSz, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
if (pkcs7Digest == NULL)
|
||||
return MEMORY_E;
|
||||
#endif
|
||||
|
||||
/* build hash to verify against */
|
||||
pkcs7DigestSz = maxDigestSz;
|
||||
ret = wc_PKCS7_BuildSignedDataDigest(pkcs7, signedAttrib,
|
||||
signedAttribSz, pkcs7Digest,
|
||||
&pkcs7DigestSz, &plainDigest,
|
||||
&plainDigestSz);
|
||||
if (ret < 0) {
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(pkcs7Digest, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
return digIdx;
|
||||
switch (pkcs7->publicKeyOID) {
|
||||
|
||||
#ifndef NO_RSA
|
||||
case RSAk:
|
||||
ret = wc_PKCS7_RsaVerify(pkcs7, sig, sigSz, pkcs7Digest,
|
||||
pkcs7DigestSz);
|
||||
if (ret < 0) {
|
||||
WOLFSSL_MSG("PKCS#7 verification failed, trying CMS");
|
||||
ret = wc_PKCS7_RsaVerify(pkcs7, sig, sigSz, plainDigest,
|
||||
plainDigestSz);
|
||||
}
|
||||
break;
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
case ECDSAk:
|
||||
ret = wc_PKCS7_EcdsaVerify(pkcs7, sig, sigSz, plainDigest,
|
||||
plainDigestSz);
|
||||
break;
|
||||
#endif
|
||||
|
||||
default:
|
||||
WOLFSSL_MSG("Unsupported public key type");
|
||||
ret = BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
#ifdef WOLFSSL_SMALL_STACK
|
||||
XFREE(pkcs7Digest, NULL, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/* Finds the certificates in the message and saves it. */
|
||||
int wc_PKCS7_VerifySignedData(PKCS7* pkcs7, byte* pkiMsg, word32 pkiMsgSz)
|
||||
{
|
||||
word32 idx, contentType;
|
||||
word32 idx, contentType, hashOID;
|
||||
int length, version, ret;
|
||||
byte* content = NULL;
|
||||
byte* sig = NULL;
|
||||
byte* cert = NULL;
|
||||
byte* signedAttrib = NULL;
|
||||
byte* digAlgId = NULL;
|
||||
int contentSz = 0, sigSz = 0, certSz = 0, signedAttribSz = 0;
|
||||
int digAlgIdSz = 0;
|
||||
|
||||
if (pkcs7 == NULL || pkiMsg == NULL || pkiMsgSz == 0)
|
||||
return BAD_FUNC_ARG;
|
||||
@@ -1387,18 +1680,11 @@ int wc_PKCS7_VerifySignedData(PKCS7* pkcs7, byte* pkiMsg, word32 pkiMsgSz)
|
||||
/* Skip it */
|
||||
idx += length;
|
||||
|
||||
/* Get the sequence of digestAlgorithm, saving pointer */
|
||||
digAlgId = &pkiMsg[idx];
|
||||
digAlgIdSz = idx;
|
||||
|
||||
if (GetSequence(pkiMsg, &idx, &length, pkiMsgSz) < 0)
|
||||
/* Get the sequence of digestAlgorithm */
|
||||
if (GetAlgoId(pkiMsg, &idx, &hashOID, oidHashType, pkiMsgSz) < 0) {
|
||||
return ASN_PARSE_E;
|
||||
|
||||
/* update digAlgIdSz with sequence and length */
|
||||
digAlgIdSz = length + (idx - digAlgIdSz);
|
||||
|
||||
/* Skip it */
|
||||
idx += length;
|
||||
}
|
||||
pkcs7->hashOID = (int)hashOID;
|
||||
|
||||
/* Get the IMPLICIT[0] SET OF signedAttributes */
|
||||
if (pkiMsg[idx] == (ASN_CONSTRUCTED | ASN_CONTEXT_SPECIFIC | 0)) {
|
||||
@@ -1438,34 +1724,8 @@ int wc_PKCS7_VerifySignedData(PKCS7* pkcs7, byte* pkiMsg, word32 pkiMsgSz)
|
||||
pkcs7->content = content;
|
||||
pkcs7->contentSz = contentSz;
|
||||
|
||||
#define MAX_PKCS7_DIGEST_SZ (MAX_SEQ_SZ + MAX_ALGO_SZ +\
|
||||
MAX_OCTET_STR_SZ + SHA_DIGEST_SIZE)
|
||||
|
||||
/* build hash to verify against */
|
||||
byte finalDigest[MAX_PKCS7_DIGEST_SZ];
|
||||
|
||||
ret = wc_PKCS7_BuildSignedDataDigest(pkcs7, signedAttrib,
|
||||
signedAttribSz, digAlgId,
|
||||
digAlgIdSz, finalDigest,
|
||||
SHA_DIGEST_SIZE);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
switch (pkcs7->publicKeyOID) {
|
||||
|
||||
case RSAk:
|
||||
ret = wc_PKCS7_RsaVerify(pkcs7, sig, sigSz, finalDigest, ret);
|
||||
break;
|
||||
|
||||
case ECDSAk:
|
||||
ret = wc_PKCS7_EcdsaVerify(pkcs7, sig, sigSz, finalDigest, ret);
|
||||
break;
|
||||
|
||||
default:
|
||||
WOLFSSL_MSG("Unsupported public key type");
|
||||
ret = BAD_FUNC_ARG;
|
||||
}
|
||||
|
||||
ret = wc_PKCS7_SignedDataVerifySignature(pkcs7, sig, sigSz,
|
||||
signedAttrib, signedAttribSz);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
}
|
||||
@@ -1474,6 +1734,8 @@ int wc_PKCS7_VerifySignedData(PKCS7* pkcs7, byte* pkiMsg, word32 pkiMsgSz)
|
||||
}
|
||||
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
|
||||
/* KARI == KeyAgreeRecipientInfo (key agreement) */
|
||||
typedef struct WC_PKCS7_KARI {
|
||||
DecodedCert* decoded; /* decoded recip cert */
|
||||
@@ -2199,6 +2461,8 @@ static int wc_CreateKeyAgreeRecipientInfo(PKCS7* pkcs7, const byte* cert,
|
||||
return idx;
|
||||
}
|
||||
|
||||
#endif /* HAVE_ECC */
|
||||
|
||||
|
||||
/* create ASN.1 formatted RecipientInfo structure, returns sequence size */
|
||||
static int wc_CreateRecipientInfo(const byte* cert, word32 certSz,
|
||||
@@ -2729,6 +2993,7 @@ int wc_PKCS7_EncodeEnvelopedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
MAX_RECIP_SZ, pkcs7->heap);
|
||||
break;
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
case ECDSAk:
|
||||
recipSz = wc_CreateKeyAgreeRecipientInfo(pkcs7, pkcs7->singleCert,
|
||||
pkcs7->singleCertSz,
|
||||
@@ -2738,6 +3003,7 @@ int wc_PKCS7_EncodeEnvelopedData(PKCS7* pkcs7, byte* output, word32 outputSz)
|
||||
contentKeyPlain, contentKeyEnc,
|
||||
&contentKeyEncSz, recip, MAX_RECIP_SZ);
|
||||
break;
|
||||
#endif
|
||||
|
||||
default:
|
||||
WOLFSSL_MSG("Unsupported RecipientInfo public key type");
|
||||
@@ -3081,6 +3347,8 @@ static int wc_PKCS7_DecodeKtri(PKCS7* pkcs7, byte* pkiMsg, word32 pkiMsgSz,
|
||||
}
|
||||
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
|
||||
/* remove ASN.1 OriginatorIdentifierOrKey, return 0 on success, <0 on error */
|
||||
static int wc_PKCS7_KariGetOriginatorIdentifierOrKey(WC_PKCS7_KARI* kari,
|
||||
byte* pkiMsg, word32 pkiMsgSz, word32* idx)
|
||||
@@ -3290,6 +3558,8 @@ static int wc_PKCS7_KariGetRecipientEncryptedKeys(WC_PKCS7_KARI* kari,
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif /* HAVE_ECC */
|
||||
|
||||
|
||||
/* decode ASN.1 KeyAgreeRecipientInfo (kari), return 0 on success,
|
||||
* < 0 on error */
|
||||
@@ -3297,6 +3567,7 @@ static int wc_PKCS7_DecodeKari(PKCS7* pkcs7, byte* pkiMsg, word32 pkiMsgSz,
|
||||
word32* idx, byte* decryptedKey,
|
||||
word32* decryptedKeySz, int* recipFound)
|
||||
{
|
||||
#ifdef HAVE_ECC
|
||||
int ret, keySz;
|
||||
int encryptedKeySz;
|
||||
int direction = 0;
|
||||
@@ -3430,6 +3701,17 @@ static int wc_PKCS7_DecodeKari(PKCS7* pkcs7, byte* pkiMsg, word32 pkiMsgSz,
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
#else
|
||||
(void)pkcs7;
|
||||
(void)pkiMsg;
|
||||
(void)pkiMsgSz;
|
||||
(void)idx;
|
||||
(void)decryptedKey;
|
||||
(void)decryptedKeySz;
|
||||
(void)recipFound;
|
||||
|
||||
return NOT_COMPILED_IN;
|
||||
#endif /* HAVE_ECC */
|
||||
}
|
||||
|
||||
|
||||
|
@@ -549,7 +549,7 @@ int wolfcrypt_test(void* args)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_X963_KDF
|
||||
#if defined(HAVE_X963_KDF) && defined(HAVE_ECC)
|
||||
if ( (ret = x963kdf_test()) != 0)
|
||||
return err_sys("X963-KDF test failed!\n", ret);
|
||||
else
|
||||
@@ -5266,7 +5266,7 @@ byte GetEntropy(ENTROPY_CMD cmd, byte* out)
|
||||
#ifndef NO_RSA
|
||||
static const char* clientKey = CERT_ROOT "client-key.der";
|
||||
static const char* clientCert = CERT_ROOT "client-cert.der";
|
||||
#ifdef HAVE_PKCS7
|
||||
#if defined(HAVE_PKCS7) && defined(HAVE_ECC)
|
||||
static const char* eccClientKey = CERT_ROOT "ecc-client-key.der";
|
||||
static const char* eccClientCert = CERT_ROOT "client-ecc-cert.der";
|
||||
#endif
|
||||
@@ -9384,7 +9384,7 @@ int hkdf_test(void)
|
||||
#endif /* HAVE_HKDF */
|
||||
|
||||
|
||||
#if defined(HAVE_X963_KDF)
|
||||
#if defined(HAVE_ECC) && defined(HAVE_X963_KDF)
|
||||
|
||||
int x963kdf_test(void)
|
||||
{
|
||||
@@ -12266,6 +12266,10 @@ static int pkcs7_load_certs_keys(byte* rsaCert, word32* rsaCertSz,
|
||||
#endif /* USE_CERT_BUFFERS_256 */
|
||||
#endif /* HAVE_ECC */
|
||||
|
||||
(void)eccCert;
|
||||
(void)eccCertSz;
|
||||
(void)eccPrivKey;
|
||||
(void)eccPrivKeySz;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -12307,7 +12311,7 @@ static int pkcs7enveloped_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
0x72,0x6c,0x64
|
||||
};
|
||||
|
||||
#ifndef NO_AES
|
||||
#if !defined(NO_AES) && defined(HAVE_ECC)
|
||||
byte optionalUkm[] = {
|
||||
0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07
|
||||
};
|
||||
@@ -12409,8 +12413,11 @@ static int pkcs7enveloped_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
if (!pkcs7File)
|
||||
return -213;
|
||||
|
||||
ret = (int)fwrite(enveloped, envelopedSz, 1, pkcs7File);
|
||||
ret = (int)fwrite(enveloped, 1, envelopedSz, pkcs7File);
|
||||
fclose(pkcs7File);
|
||||
if (ret != envelopedSz) {
|
||||
return -214;
|
||||
}
|
||||
#endif /* PKCS7_OUTPUT_TEST_BUNDLES */
|
||||
|
||||
wc_PKCS7_Free(&pkcs7);
|
||||
@@ -12722,6 +12729,7 @@ static int pkcs7signed_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
byte* eccPrivKey, word32 eccPrivKeySz)
|
||||
{
|
||||
int ret, testSz, i;
|
||||
int encodedSz;
|
||||
byte* out;
|
||||
word32 outSz;
|
||||
WC_RNG rng;
|
||||
@@ -12760,11 +12768,46 @@ static int pkcs7signed_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
|
||||
const pkcs7SignedVector testVectors[] =
|
||||
{
|
||||
#ifndef NO_RSA
|
||||
#ifndef NO_SHA
|
||||
/* RSA with SHA */
|
||||
{data, (word32)sizeof(data), SHAh, RSAk, rsaPrivKey, rsaPrivKeySz,
|
||||
rsaCert, rsaCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_RSA_SHA.der"},
|
||||
|
||||
/* RSA with SHA, no signed attributes */
|
||||
{data, (word32)sizeof(data), SHAh, RSAk, rsaPrivKey, rsaPrivKeySz,
|
||||
rsaCert, rsaCertSz, NULL, 0,
|
||||
"pkcs7signedData_RSA_SHA_noattr.der"},
|
||||
#endif
|
||||
#ifdef WOLFSSL_SHA224
|
||||
/* RSA with SHA224 */
|
||||
{data, (word32)sizeof(data), SHA224h, RSAk, rsaPrivKey, rsaPrivKeySz,
|
||||
rsaCert, rsaCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_RSA_SHA224.der"},
|
||||
#endif
|
||||
#ifndef NO_SHA256
|
||||
/* RSA with SHA256 */
|
||||
{data, (word32)sizeof(data), SHA256h, RSAk, rsaPrivKey, rsaPrivKeySz,
|
||||
rsaCert, rsaCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_RSA_SHA256.der"},
|
||||
#endif
|
||||
#if defined(WOLFSSL_SHA384)
|
||||
/* RSA with SHA384 */
|
||||
{data, (word32)sizeof(data), SHA384h, RSAk, rsaPrivKey, rsaPrivKeySz,
|
||||
rsaCert, rsaCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_RSA_SHA384.der"},
|
||||
#endif
|
||||
#if defined(WOLFSSL_SHA512)
|
||||
/* RSA with SHA512 */
|
||||
{data, (word32)sizeof(data), SHA512h, RSAk, rsaPrivKey, rsaPrivKeySz,
|
||||
rsaCert, rsaCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_RSA_SHA512.der"},
|
||||
#endif
|
||||
#endif /* NO_RSA */
|
||||
|
||||
#ifdef HAVE_ECC
|
||||
#ifndef NO_SHA
|
||||
/* ECDSA with SHA */
|
||||
{data, (word32)sizeof(data), SHAh, ECDSAk, eccPrivKey, eccPrivKeySz,
|
||||
eccCert, eccCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
@@ -12774,6 +12817,32 @@ static int pkcs7signed_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
{data, (word32)sizeof(data), SHAh, ECDSAk, eccPrivKey, eccPrivKeySz,
|
||||
eccCert, eccCertSz, NULL, 0,
|
||||
"pkcs7signedData_ECDSA_SHA_noattr.der"},
|
||||
#endif
|
||||
#ifdef WOLFSSL_SHA224
|
||||
/* ECDSA with SHA224 */
|
||||
{data, (word32)sizeof(data), SHA224h, ECDSAk, eccPrivKey, eccPrivKeySz,
|
||||
eccCert, eccCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_ECDSA_SHA224.der"},
|
||||
#endif
|
||||
#ifndef NO_SHA256
|
||||
/* ECDSA with SHA256 */
|
||||
{data, (word32)sizeof(data), SHA256h, ECDSAk, eccPrivKey, eccPrivKeySz,
|
||||
eccCert, eccCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_ECDSA_SHA256.der"},
|
||||
#endif
|
||||
#ifdef WOLFSSL_SHA384
|
||||
/* ECDSA with SHA384 */
|
||||
{data, (word32)sizeof(data), SHA384h, ECDSAk, eccPrivKey, eccPrivKeySz,
|
||||
eccCert, eccCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_ECDSA_SHA384.der"},
|
||||
#endif
|
||||
#ifdef WOLFSSL_SHA512
|
||||
/* ECDSA with SHA512 */
|
||||
{data, (word32)sizeof(data), SHA512h, ECDSAk, eccPrivKey, eccPrivKeySz,
|
||||
eccCert, eccCertSz, attribs, (sizeof(attribs)/sizeof(PKCS7Attrib)),
|
||||
"pkcs7signedData_ECDSA_SHA512.der"},
|
||||
#endif
|
||||
#endif /* HAVE_ECC */
|
||||
};
|
||||
|
||||
testSz = sizeof(testVectors) / sizeof(pkcs7SignedVector);
|
||||
@@ -12848,14 +12917,12 @@ static int pkcs7signed_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
}
|
||||
}
|
||||
|
||||
ret = wc_PKCS7_EncodeSignedData(&pkcs7, out, outSz);
|
||||
if (ret < 0) {
|
||||
encodedSz = wc_PKCS7_EncodeSignedData(&pkcs7, out, outSz);
|
||||
if (encodedSz < 0) {
|
||||
XFREE(out, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
wc_PKCS7_Free(&pkcs7);
|
||||
return -214;
|
||||
}
|
||||
else
|
||||
outSz = ret;
|
||||
|
||||
#ifdef PKCS7_OUTPUT_TEST_BUNDLES
|
||||
/* write PKCS#7 to output file for more testing */
|
||||
@@ -12865,9 +12932,9 @@ static int pkcs7signed_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
wc_PKCS7_Free(&pkcs7);
|
||||
return -215;
|
||||
}
|
||||
ret = (int)fwrite(out, 1, outSz, file);
|
||||
ret = (int)fwrite(out, 1, encodedSz, file);
|
||||
fclose(file);
|
||||
if (ret != (int)outSz) {
|
||||
if (ret != (int)encodedSz) {
|
||||
XFREE(out, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
|
||||
wc_PKCS7_Free(&pkcs7);
|
||||
return -216;
|
||||
@@ -12910,6 +12977,10 @@ static int pkcs7signed_run_vectors(byte* rsaCert, word32 rsaCertSz,
|
||||
if (ret > 0)
|
||||
return 0;
|
||||
|
||||
(void)eccCert;
|
||||
(void)eccCertSz;
|
||||
(void)eccPrivKey;
|
||||
(void)eccPrivKeySz;
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user