From 6c437577dc3a65632bb7a6a5511c5ef1563b538b Mon Sep 17 00:00:00 2001 From: Kangping Dong Date: Thu, 30 May 2019 20:19:46 +0800 Subject: [PATCH 1/3] sign and validate using public key; kill warnings; --- CMakeLists.txt | 2 +- dumper/dumper.c | 2 +- include/cose.h | 11 ++++ src/CMakeLists.txt | 3 +- src/Cose.c | 2 - src/Encrypt.c | 6 +-- src/Encrypt0.c | 8 +-- src/MacMessage.c | 10 ++-- src/MacMessage0.c | 6 +-- src/Recipient.c | 19 +++++-- src/Sign.c | 6 +-- src/Sign0.c | 73 +++++++++++++++++++------ src/SignerInfo.c | 34 +++++++++--- src/cose_int.h | 3 ++ src/crypto.h | 6 +-- src/key.c | 127 ++++++++++++++++++++++++++++++++++++++++++++ src/mbedtls.c | 107 +++---------------------------------- src/openssl.c | 28 ++++------ test/CMakeLists.txt | 2 +- test/context.c | 5 +- test/encrypt.c | 6 +-- test/json.c | 8 +-- test/sign.c | 14 ++++- test/test.c | 17 ++++-- test/test.h | 2 +- 25 files changed, 319 insertions(+), 188 deletions(-) create mode 100644 src/key.c diff --git a/CMakeLists.txt b/CMakeLists.txt index 679ee0c..e3eb262 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -20,7 +20,7 @@ find_package(OpenSSL 1.0 REQUIRED) option (use_context "Use context pointer for COSE functions" ON) option (verbose "Produce verbose makefile output" OFF) option (optimize "Optimize for size" OFF) -option (fatal_warnings "Treat build warnings as error" OFF) +option (fatal_warnings "Treat build warnings as error" ON) option (coveralls "Generate coveralls data" ON) option ( coveralls_send "Send data to coveralls site" OFF ) option (build_docs "Create docs using Doxygen" ${DOXYGEN_FOUND} ) diff --git a/dumper/dumper.c b/dumper/dumper.c index 945226b..6571074 100644 --- a/dumper/dumper.c +++ b/dumper/dumper.c @@ -394,7 +394,7 @@ void DumpTree(const cn_cbor * cbor, FILE * out, const FOO *pFOO, int depth, int if (pFOO != NULL) { // Locate the right entry in foo for (i2 = 0, pFoo2 = pFOO->children; i2 < pFOO->count; pFoo2++, i2 += 1) { - if (pFoo2->type != cbor2->type) continue; + if ((unsigned)pFoo2->type != cbor2->type) continue; switch (cbor2->type) { case CN_CBOR_UINT: if ((group != 0) && (pFoo2->group != 0) && (pFoo2->group != group)) continue; diff --git a/include/cose.h b/include/cose.h index 85e70e0..c96036a 100644 --- a/include/cose.h +++ b/include/cose.h @@ -314,6 +314,15 @@ bool COSE_Signer_SetExternal(HCOSE_SIGNER hcose, const byte * pbExternalData, si * Sign routines */ +#if USE_MBED_TLS + typedef struct mbedtls_ecp_keypair eckey_t; +#else + typedef struct eckey_t { + struct ec_key_st *key; + int group; + } eckey_t; +#endif // USE_MBED_TLS + HCOSE_SIGN0 COSE_Sign0_Init(COSE_INIT_FLAGS flags, CBOR_CONTEXT_COMMA cose_errback * perr); bool COSE_Sign0_Free(HCOSE_SIGN0 cose); @@ -321,7 +330,9 @@ bool COSE_Sign0_SetContent(HCOSE_SIGN0 cose, const byte * rgbContent, size_t cbC bool COSE_Sign0_SetExternal(HCOSE_SIGN0 hcose, const byte * pbExternalData, size_t cbExternalData, cose_errback * perr); bool COSE_Sign0_Sign(HCOSE_SIGN0 h, const cn_cbor * pkey, cose_errback * perr); +bool COSE_Sign0_Sign_eckey(HCOSE_SIGN0 h, const eckey_t * pbKey, cose_errback * perr); bool COSE_Sign0_validate(HCOSE_SIGN0 hSign, const cn_cbor * pkey, cose_errback * perr); +bool COSE_Sign0_validate_eckey(HCOSE_SIGN0 hSign, const eckey_t * pbKey, cose_errback * perr); cn_cbor * COSE_Sign0_map_get_int(HCOSE_SIGN0 h, int key, int flags, cose_errback * perror); bool COSE_Sign0_map_put_int(HCOSE_SIGN0 cose, int key, cn_cbor * value, int flags, cose_errback * errp); diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 8e7ba3e..e9ca7fd 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -9,7 +9,8 @@ else () endif() set ( cose_sources - Cose.c + Cose.c + key.c MacMessage.c MacMessage0.c Sign.c diff --git a/src/Cose.c b/src/Cose.c index 1e4d3cc..75115b2 100644 --- a/src/Cose.c +++ b/src/Cose.c @@ -15,7 +15,6 @@ bool IsValidCOSEHandle(HCOSE h) return true; } - bool _COSE_Init(COSE_INIT_FLAGS flags, COSE* pobj, int msgType, CBOR_CONTEXT_COMMA cose_errback * perr) { cn_cbor_errback errState;; @@ -45,7 +44,6 @@ bool _COSE_Init(COSE_INIT_FLAGS flags, COSE* pobj, int msgType, CBOR_CONTEXT_COM CHECK_CONDITION_CBOR(_COSE_array_replace(pobj, pobj->m_unprotectMap, INDEX_UNPROTECTED, CBOR_CONTEXT_PARAM_COMMA &errState), errState); pobj->m_ownUnprotectedMap = false; - if (!(flags & COSE_INIT_FLAGS_NO_CBOR_TAG)) { cn_cbor_errback cbor_error; cn_cbor * cn = cn_cbor_tag_create(msgType, pobj->m_cborRoot, CBOR_CONTEXT_PARAM_COMMA &cbor_error); diff --git a/src/Encrypt.c b/src/Encrypt.c index 5967245..fbae506 100644 --- a/src/Encrypt.c +++ b/src/Encrypt.c @@ -129,7 +129,7 @@ HCOSE_ENVELOPED _COSE_Enveloped_Init_From_Object(cn_cbor * cbor, COSE_Enveloped bool COSE_Enveloped_Free(HCOSE_ENVELOPED h) { #ifdef USE_CBOR_CONTEXT - cn_cbor_context context; + cn_cbor_context *context; #endif COSE_Enveloped * p = (COSE_Enveloped *)h; @@ -141,14 +141,14 @@ bool COSE_Enveloped_Free(HCOSE_ENVELOPED h) } #ifdef USE_CBOR_CONTEXT - context = ((COSE_Enveloped *)h)->m_message.m_allocContext; + context = &((COSE_Enveloped *)h)->m_message.m_allocContext; #endif _COSE_RemoveFromList(&EnvelopedRoot, &p->m_message); _COSE_Enveloped_Release((COSE_Enveloped *)h); - COSE_FREE((COSE_Enveloped *)h, &context); + COSE_FREE((COSE_Enveloped *)h, context); return true; } diff --git a/src/Encrypt0.c b/src/Encrypt0.c index 189bbc7..1e582f3 100644 --- a/src/Encrypt0.c +++ b/src/Encrypt0.c @@ -128,21 +128,21 @@ HCOSE_ENCRYPT _COSE_Encrypt_Init_From_Object(cn_cbor * cbor, COSE_Encrypt * pIn, bool COSE_Encrypt_Free(HCOSE_ENCRYPT h) { #ifdef USE_CBOR_CONTEXT - cn_cbor_context context; + cn_cbor_context *context; #endif COSE_Encrypt * pEncrypt = (COSE_Encrypt *)h; if (!IsValidEncryptHandle(h)) return false; #ifdef USE_CBOR_CONTEXT - context = ((COSE_Encrypt *)h)->m_message.m_allocContext; + context = &((COSE_Encrypt *)h)->m_message.m_allocContext; #endif _COSE_Encrypt_Release(pEncrypt); _COSE_RemoveFromList(&EncryptRoot, &pEncrypt->m_message); - - COSE_FREE((COSE_Encrypt *)h, &context); + + COSE_FREE((COSE_Encrypt *)h, context); return true; } diff --git a/src/MacMessage.c b/src/MacMessage.c index 62be761..b2a6f00 100644 --- a/src/MacMessage.c +++ b/src/MacMessage.c @@ -113,7 +113,7 @@ HCOSE_MAC _COSE_Mac_Init_From_Object(cn_cbor * cbor, COSE_MacMessage * pIn, CBOR bool COSE_Mac_Free(HCOSE_MAC h) { #ifdef USE_CBOR_CONTEXT - cn_cbor_context context; + cn_cbor_context *context; #endif COSE_MacMessage * p = (COSE_MacMessage *)h; @@ -127,12 +127,12 @@ bool COSE_Mac_Free(HCOSE_MAC h) _COSE_RemoveFromList(&MacRoot, &p->m_message); #ifdef USE_CBOR_CONTEXT - context = ((COSE_MacMessage *)h)->m_message.m_allocContext; + context = &((COSE_MacMessage *)h)->m_message.m_allocContext; #endif _COSE_Mac_Release((COSE_MacMessage *)h); - COSE_FREE((COSE_MacMessage *)h, &context); + COSE_FREE((COSE_MacMessage *)h, context); return true; } @@ -234,6 +234,7 @@ bool _COSE_Mac_Build_AAD(COSE * pCose, const char * szContext, byte ** ppbAuthDa cn_cbor * ptmp = NULL; cn_cbor * pcn; size_t cbAuthData; + ssize_t written; byte * pbAuthData = NULL; // Build authenticated data @@ -286,7 +287,8 @@ bool _COSE_Mac_Build_AAD(COSE * pCose, const char * szContext, byte ** ppbAuthDa CHECK_CONDITION(cbAuthData > 0, COSE_ERR_CBOR); pbAuthData = (byte *)COSE_CALLOC(cbAuthData, 1, context); CHECK_CONDITION(pbAuthData != NULL, COSE_ERR_OUT_OF_MEMORY); - CHECK_CONDITION(cn_cbor_encoder_write(pbAuthData, 0, cbAuthData, pAuthData) == cbAuthData, COSE_ERR_CBOR); + written = cn_cbor_encoder_write(pbAuthData, 0, cbAuthData, pAuthData); + CHECK_CONDITION(written >= 0 && (size_t)written == cbAuthData, COSE_ERR_CBOR); *ppbAuthData = pbAuthData; *pcbAuthData = cbAuthData; diff --git a/src/MacMessage0.c b/src/MacMessage0.c index 47ed015..407b22a 100644 --- a/src/MacMessage0.c +++ b/src/MacMessage0.c @@ -100,7 +100,7 @@ HCOSE_MAC0 _COSE_Mac0_Init_From_Object(cn_cbor * cbor, COSE_Mac0Message * pIn, C bool COSE_Mac0_Free(HCOSE_MAC0 h) { #ifdef USE_CBOR_CONTEXT - cn_cbor_context context; + cn_cbor_context *context; #endif COSE_Mac0Message * p = (COSE_Mac0Message *)h; @@ -114,12 +114,12 @@ bool COSE_Mac0_Free(HCOSE_MAC0 h) _COSE_RemoveFromList(&Mac0Root, &p->m_message); #ifdef USE_CBOR_CONTEXT - context = p->m_message.m_allocContext; + context = &p->m_message.m_allocContext; #endif _COSE_Mac0_Release(p); - COSE_FREE(p, &context); + COSE_FREE(p, context); return true; } diff --git a/src/Recipient.c b/src/Recipient.c index 7ada624..ec01a9c 100644 --- a/src/Recipient.c +++ b/src/Recipient.c @@ -205,7 +205,7 @@ static bool HKDF_X(COSE * pCose, bool fHMAC, bool fECDH, bool fStatic, bool fSen if (fHMAC) { #ifdef USE_HKDF_SHA2 - if (!HKDF_Extract(pCose, pbSecret, cbSecret, cbitHash, rgbDigest, &cbDigest, CBOR_CONTEXT_PARAM_COMMA perr)) goto errorReturn; + if (!HKDF_Extract(pCose, pbSecret, cbSecret, cbitHash, rgbDigest, &cbDigest, perr)) goto errorReturn; if (!HKDF_Expand(pCose, cbitHash, rgbDigest, cbDigest, pbContext, cbContext, pbKey, cbitKey / 8, perr)) goto errorReturn; #else @@ -251,6 +251,10 @@ bool _COSE_Recipient_decrypt(COSE_RecipientInfo * pRecip, COSE_RecipientInfo * p int cbitKeyX = 0; byte rgbKey[256 / 8]; + UNUSED(rgbKey); + UNUSED(cbKey2); + UNUSED(pRecipUse); + UNUSED(algIn); UNUSED(pcose); #ifdef USE_CBOR_CONTEXT @@ -279,7 +283,7 @@ bool _COSE_Recipient_decrypt(COSE_RecipientInfo * pRecip, COSE_RecipientInfo * p CHECK_CONDITION(pRecip->m_pkey != NULL, COSE_ERR_INVALID_PARAMETER); cn = cn_cbor_mapget_int(pRecip->m_pkey, -1); CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_BYTES), COSE_ERR_INVALID_PARAMETER); - CHECK_CONDITION((cn->length == (unsigned int)cbitKeyOut / 8), COSE_ERR_INVALID_PARAMETER); + CHECK_CONDITION(((size_t)cn->length == cbitKeyOut / 8), COSE_ERR_INVALID_PARAMETER); memcpy(pbKeyOut, cn->v.bytes, cn->length); return true; @@ -574,6 +578,9 @@ bool _COSE_Recipient_encrypt(COSE_RecipientInfo * pRecipient, const byte * pbCon byte * pbKey = NULL; size_t cbKey = 0; + UNUSED(pbContent); + UNUSED(cbContent); + #ifdef USE_CBOR_CONTEXT context = &pRecipient->m_encrypt.m_message.m_allocContext; #endif // USE_CBOR_CONTEXT @@ -867,6 +874,8 @@ byte * _COSE_RecipientInfo_generateKey(COSE_RecipientInfo * pRecipient, int algI const cn_cbor * pK; byte *pbSecret = NULL; + UNUSED(algIn); + CHECK_CONDITION(cn_Alg != NULL, COSE_ERR_INVALID_PARAMETER); CHECK_CONDITION((cn_Alg->type == CN_CBOR_UINT) || (cn_Alg->type == CN_CBOR_INT), COSE_ERR_INVALID_PARAMETER); alg = (int)cn_Alg->v.uint; @@ -881,7 +890,7 @@ byte * _COSE_RecipientInfo_generateKey(COSE_RecipientInfo * pRecipient, int algI CHECK_CONDITION(pRecipient->m_pkey != NULL, COSE_ERR_INVALID_PARAMETER); pK = cn_cbor_mapget_int(pRecipient->m_pkey, -1); CHECK_CONDITION((pK != NULL) && (pK->type == CN_CBOR_BYTES), COSE_ERR_INVALID_PARAMETER); - CHECK_CONDITION(pK->length == cbitKeySize / 8, COSE_ERR_INVALID_PARAMETER); + CHECK_CONDITION((size_t)pK->length == cbitKeySize / 8, COSE_ERR_INVALID_PARAMETER); memcpy(pb, pK->v.bytes, cbitKeySize / 8); break; @@ -1226,6 +1235,7 @@ bool BuildContextBytes(COSE * pcose, int algID, size_t cbitKey, byte ** ppbConte cn_cbor * cnParam; byte * pbContext = NULL; size_t cbContext; + ssize_t written; pArray = cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA &cbor_error); CHECK_CONDITION_CBOR(pArray != NULL, cbor_error); @@ -1350,7 +1360,8 @@ bool BuildContextBytes(COSE * pcose, int algID, size_t cbitKey, byte ** ppbConte CHECK_CONDITION(cbContext > 0, COSE_ERR_CBOR); pbContext = (byte *)COSE_CALLOC(cbContext, 1, context); CHECK_CONDITION(pbContext != NULL, COSE_ERR_OUT_OF_MEMORY); - CHECK_CONDITION(cn_cbor_encoder_write(pbContext, 0, cbContext, pArray) == cbContext, COSE_ERR_CBOR); + written = cn_cbor_encoder_write(pbContext, 0, cbContext, pArray); + CHECK_CONDITION(written >= 0 && (size_t)written == cbContext, COSE_ERR_CBOR); *ppbContext = pbContext; *pcbContext = cbContext; diff --git a/src/Sign.c b/src/Sign.c index 59e2972..39e5c56 100644 --- a/src/Sign.c +++ b/src/Sign.c @@ -107,7 +107,7 @@ HCOSE_SIGN _COSE_Sign_Init_From_Object(cn_cbor * cbor, COSE_SignMessage * pIn, C bool COSE_Sign_Free(HCOSE_SIGN h) { #ifdef USE_CBOR_CONTEXT - cn_cbor_context context; + cn_cbor_context *context; #endif COSE_SignMessage * pMessage = (COSE_SignMessage *)h; @@ -122,12 +122,12 @@ bool COSE_Sign_Free(HCOSE_SIGN h) _COSE_RemoveFromList(&SignRoot, &pMessage->m_message); #ifdef USE_CBOR_CONTEXT - context = pMessage->m_message.m_allocContext; + context = &pMessage->m_message.m_allocContext; #endif _COSE_Sign_Release(pMessage); - COSE_FREE(pMessage, &context); + COSE_FREE(pMessage, context); return true; } diff --git a/src/Sign0.c b/src/Sign0.c index 73b8e1e..d03731e 100644 --- a/src/Sign0.c +++ b/src/Sign0.c @@ -9,10 +9,16 @@ #include "configure.h" #include "crypto.h" +#if USE_MBED_TLS +#include "mbedtls/ecp.h" +#else + +#endif + #if INCLUDE_SIGN0 -bool _COSE_Signer0_sign(COSE_Sign0Message * pSigner, const cn_cbor * pKey, cose_errback * perr); -bool _COSE_Signer0_validate(COSE_Sign0Message * pSign, const cn_cbor * pKey, cose_errback * perr); +bool _COSE_Signer0_sign(COSE_Sign0Message * pSigner, const eckey_t * eckey, cose_errback * perr); +bool _COSE_Signer0_validate(COSE_Sign0Message * pSign, const eckey_t * eckey, cose_errback * perr); void _COSE_Sign0_Release(COSE_Sign0Message * p); COSE * Sign0Root = NULL; @@ -92,7 +98,7 @@ HCOSE_SIGN0 _COSE_Sign0_Init_From_Object(cn_cbor * cbor, COSE_Sign0Message * pIn bool COSE_Sign0_Free(HCOSE_SIGN0 h) { #ifdef USE_CBOR_CONTEXT - cn_cbor_context context; + cn_cbor_context *context; #endif COSE_Sign0Message * pMessage = (COSE_Sign0Message *)h; @@ -107,12 +113,12 @@ bool COSE_Sign0_Free(HCOSE_SIGN0 h) _COSE_RemoveFromList(&Sign0Root, &pMessage->m_message); #ifdef USE_CBOR_CONTEXT - context = pMessage->m_message.m_allocContext; + context = &pMessage->m_message.m_allocContext; #endif _COSE_Sign0_Release(pMessage); - COSE_FREE(pMessage, &context); + COSE_FREE(pMessage, context); return true; } @@ -177,6 +183,23 @@ bool COSE_Sign0_SetExternal(HCOSE_SIGN0 hcose, const byte * pbExternalData, size } bool COSE_Sign0_Sign(HCOSE_SIGN0 h, const cn_cbor * pKey, cose_errback * perr) +{ + bool ret = false; + eckey_t eckey; + + CHECK_CONDITION(pKey != NULL, COSE_ERR_INVALID_PARAMETER); + if (eckey_from_cbor(&eckey, pKey, perr)) + { + ret = COSE_Sign0_Sign_eckey(h, &eckey, perr); + } + + eckey_release(&eckey); + +errorReturn: + return ret; +} + +bool COSE_Sign0_Sign_eckey(HCOSE_SIGN0 h, const eckey_t * eckey, cose_errback * perr) { #ifdef USE_CBOR_CONTEXT // cn_cbor_context * context = NULL; @@ -196,12 +219,28 @@ bool COSE_Sign0_Sign(HCOSE_SIGN0 h, const cn_cbor * pKey, cose_errback * perr) pcborProtected = _COSE_encode_protected(&pMessage->m_message, perr); if (pcborProtected == NULL) goto errorReturn; - if (!_COSE_Signer0_sign(pMessage, pKey, perr)) goto errorReturn; + if (!_COSE_Signer0_sign(pMessage, eckey, perr)) goto errorReturn; return true; } bool COSE_Sign0_validate(HCOSE_SIGN0 hSign, const cn_cbor * pKey, cose_errback * perr) +{ + bool ret = false; + eckey_t eckey; + + CHECK_CONDITION(pKey != NULL, COSE_ERR_INVALID_PARAMETER); + if (eckey_from_cbor(&eckey, pKey, perr)) + { + ret = COSE_Sign0_validate_eckey(hSign, &eckey, perr); + } + eckey_release(&eckey); + +errorReturn: + return ret; +} + +bool COSE_Sign0_validate_eckey(HCOSE_SIGN0 hSign, const eckey_t * eckey, cose_errback * perr) { bool f; COSE_Sign0Message * pSign; @@ -218,7 +257,7 @@ bool COSE_Sign0_validate(HCOSE_SIGN0 hSign, const cn_cbor * pKey, cose_errback * cnProtected = _COSE_arrayget_int(&pSign->m_message, INDEX_PROTECTED); CHECK_CONDITION(cnProtected != NULL && cnProtected->type == CN_CBOR_BYTES, COSE_ERR_INVALID_PARAMETER); - f = _COSE_Signer0_validate(pSign, pKey, perr); + f = _COSE_Signer0_validate(pSign, eckey, perr); return f; @@ -259,6 +298,7 @@ static bool CreateSign0AAD(COSE_Sign0Message * pMessage, byte ** ppbToSign, size cn_cbor * cn = NULL; cn_cbor * cn2; size_t cbToSign; + ssize_t written; byte * pbToSign = NULL; pArray = cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA &cbor_error); @@ -294,7 +334,8 @@ static bool CreateSign0AAD(COSE_Sign0Message * pMessage, byte ** ppbToSign, size CHECK_CONDITION(cbToSign > 0, COSE_ERR_CBOR); pbToSign = (byte *)COSE_CALLOC(cbToSign, 1, context); CHECK_CONDITION(pbToSign != NULL, COSE_ERR_OUT_OF_MEMORY); - CHECK_CONDITION(cn_cbor_encoder_write(pbToSign, 0, cbToSign, pArray) == cbToSign, COSE_ERR_CBOR); + written = cn_cbor_encoder_write(pbToSign, 0, cbToSign, pArray); + CHECK_CONDITION(written >= 0 && (size_t)written == cbToSign, COSE_ERR_CBOR); *ppbToSign = pbToSign; *pcbToSign = cbToSign; @@ -311,7 +352,7 @@ static bool CreateSign0AAD(COSE_Sign0Message * pMessage, byte ** ppbToSign, size return false; } -bool _COSE_Signer0_sign(COSE_Sign0Message * pSigner, const cn_cbor * pKey, cose_errback * perr) +bool _COSE_Signer0_sign(COSE_Sign0Message * pSigner, const eckey_t * eckey, cose_errback * perr) { #ifdef USE_CBOR_CONTEXT cn_cbor_context * context = &pSigner->m_message.m_allocContext; @@ -354,19 +395,19 @@ bool _COSE_Signer0_sign(COSE_Sign0Message * pSigner, const cn_cbor * pKey, cose_ switch (alg) { #ifdef USE_ECDSA_SHA_256 case COSE_Algorithm_ECDSA_SHA_256: - f = ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE+1, pKey, 256, pbToSign, cbToSign, perr); + f = ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE+1, eckey, 256, pbToSign, cbToSign, perr); break; #endif #ifdef USE_ECDSA_SHA_384 case COSE_Algorithm_ECDSA_SHA_384: - f = ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE+1, pKey, 384, pbToSign, cbToSign, perr); + f = ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE+1, eckey, 384, pbToSign, cbToSign, perr); break; #endif #ifdef USE_ECDSA_SHA_512 case COSE_Algorithm_ECDSA_SHA_512: - f = ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE+1, pKey, 512, pbToSign, cbToSign, perr); + f = ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE+1, eckey, 512, pbToSign, cbToSign, perr); break; #endif default: @@ -379,7 +420,7 @@ bool _COSE_Signer0_sign(COSE_Sign0Message * pSigner, const cn_cbor * pKey, cose_ return f; } -bool _COSE_Signer0_validate(COSE_Sign0Message * pSign, const cn_cbor * pKey, cose_errback * perr) +bool _COSE_Signer0_validate(COSE_Sign0Message * pSign, const eckey_t * eckey, cose_errback * perr) { byte * pbToSign = NULL; int alg; @@ -413,19 +454,19 @@ bool _COSE_Signer0_validate(COSE_Sign0Message * pSign, const cn_cbor * pKey, cos switch (alg) { #ifdef USE_ECDSA_SHA_256 case COSE_Algorithm_ECDSA_SHA_256: - if (!ECDSA_Verify(&pSign->m_message, INDEX_SIGNATURE+1, pKey, 256, pbToSign, cbToSign, perr)) goto errorReturn; + if (!ECDSA_Verify(&pSign->m_message, INDEX_SIGNATURE+1, eckey, 256, pbToSign, cbToSign, perr)) goto errorReturn; break; #endif #ifdef USE_ECDSA_SHA_384 case COSE_Algorithm_ECDSA_SHA_384: - if (!ECDSA_Verify(&pSign->m_message, INDEX_SIGNATURE+1, pKey, 384, pbToSign, cbToSign, perr)) goto errorReturn; + if (!ECDSA_Verify(&pSign->m_message, INDEX_SIGNATURE+1, eckey, 384, pbToSign, cbToSign, perr)) goto errorReturn; break; #endif #ifdef USE_ECDSA_SHA_512 case COSE_Algorithm_ECDSA_SHA_512: - if (!ECDSA_Verify(&pSign->m_message, INDEX_SIGNATURE+1, pKey, 512, pbToSign, cbToSign, perr)) goto errorReturn; + if (!ECDSA_Verify(&pSign->m_message, INDEX_SIGNATURE+1, eckey, 512, pbToSign, cbToSign, perr)) goto errorReturn; break; #endif diff --git a/src/SignerInfo.c b/src/SignerInfo.c index 0f7d7b3..509b94b 100644 --- a/src/SignerInfo.c +++ b/src/SignerInfo.c @@ -12,6 +12,12 @@ #include "configure.h" #include "crypto.h" +#ifdef USE_MBED_TLS +#include "mbedtls/ecp.h" +#else + +#endif + #if INCLUDE_SIGN extern bool IsValidSignHandle(HCOSE_SIGN h); @@ -115,6 +121,7 @@ bool BuildToBeSigned(byte ** ppbToSign, size_t * pcbToSign, const cn_cbor * pcbo cn_cbor * pArray = NULL; cn_cbor_errback cbor_error; size_t cbToSign; + ssize_t written; byte * pbToSign = NULL; bool f = false; cn_cbor * cn = NULL; @@ -153,7 +160,8 @@ bool BuildToBeSigned(byte ** ppbToSign, size_t * pcbToSign, const cn_cbor * pcbo CHECK_CONDITION(cbToSign > 0, COSE_ERR_CBOR); pbToSign = (byte *)COSE_CALLOC(cbToSign, 1, context); CHECK_CONDITION(pbToSign != NULL, COSE_ERR_OUT_OF_MEMORY); - CHECK_CONDITION(cn_cbor_encoder_write(pbToSign, 0, cbToSign, pArray) == cbToSign, COSE_ERR_CBOR); + written = cn_cbor_encoder_write(pbToSign, 0, cbToSign, pArray); + CHECK_CONDITION(written >= 0 && (size_t)written == cbToSign, COSE_ERR_CBOR); *ppbToSign = pbToSign; *pcbToSign = cbToSign; @@ -182,6 +190,10 @@ bool _COSE_Signer_sign(COSE_SignerInfo * pSigner, const cn_cbor * pcborBody, con bool f; int alg; bool fRet = false; + eckey_t eckey; + + UNUSED(f); + CHECK_CONDITION(eckey_from_cbor(&eckey, pSigner->m_pkey, perr), COSE_ERR_INVALID_PARAMETER); pArray = cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA NULL); CHECK_CONDITION(pArray != NULL, COSE_ERR_OUT_OF_MEMORY); @@ -206,19 +218,19 @@ bool _COSE_Signer_sign(COSE_SignerInfo * pSigner, const cn_cbor * pcborBody, con switch (alg) { #ifdef USE_ECDSA_SHA_256 case COSE_Algorithm_ECDSA_SHA_256: - if (!ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE, pSigner->m_pkey, 256, pbToSign, cbToSign, perr)) goto errorReturn; + if (!ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE, &eckey, 256, pbToSign, cbToSign, perr)) goto errorReturn; break; #endif #ifdef USE_ECDSA_SHA_384 case COSE_Algorithm_ECDSA_SHA_384: - if (!ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE, pSigner->m_pkey, 384, pbToSign, cbToSign, perr)) goto errorReturn; + if (!ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE, &eckey, 384, pbToSign, cbToSign, perr)) goto errorReturn; break; #endif #ifdef USE_ECDSA_SHA_512 case COSE_Algorithm_ECDSA_SHA_512: - if (!ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE, pSigner->m_pkey, 512, pbToSign, cbToSign, perr)) goto errorReturn; + if (!ECDSA_Sign(&pSigner->m_message, INDEX_SIGNATURE, &eckey, 512, pbToSign, cbToSign, perr)) goto errorReturn; break; #endif @@ -231,6 +243,7 @@ bool _COSE_Signer_sign(COSE_SignerInfo * pSigner, const cn_cbor * pcborBody, con errorReturn: if (pArray != NULL) COSE_FREE(pArray, context); if (pbToSign != NULL) COSE_FREE(pbToSign, context); + eckey_release(&eckey); return fRet; } @@ -286,6 +299,11 @@ bool _COSE_Signer_validate(COSE_SignMessage * pSign, COSE_SignerInfo * pSigner, #endif size_t cbToBeSigned; bool fRet = false; + eckey_t eckey; + + UNUSED(pSign); + + CHECK_CONDITION(eckey_from_cbor(&eckey, pSigner->m_pkey, perr), COSE_ERR_INVALID_PARAMETER); #ifdef USE_CBOR_CONTEXT context = &pSign->m_message.m_allocContext; @@ -318,19 +336,19 @@ bool _COSE_Signer_validate(COSE_SignMessage * pSign, COSE_SignerInfo * pSigner, switch (alg) { #ifdef USE_ECDSA_SHA_256 case COSE_Algorithm_ECDSA_SHA_256: - if (!ECDSA_Verify(&pSigner->m_message, INDEX_SIGNATURE, pSigner->m_pkey, 256, pbToBeSigned, cbToBeSigned, perr)) goto errorReturn; + if (!ECDSA_Verify(&pSigner->m_message, INDEX_SIGNATURE, &eckey, 256, pbToBeSigned, cbToBeSigned, perr)) goto errorReturn; break; #endif #ifdef USE_ECDSA_SHA_384 case COSE_Algorithm_ECDSA_SHA_384: - if (!ECDSA_Verify(&pSigner->m_message, INDEX_SIGNATURE, pSigner->m_pkey, 384, pbToBeSigned, cbToBeSigned, perr)) goto errorReturn; + if (!ECDSA_Verify(&pSigner->m_message, INDEX_SIGNATURE, &eckey, 384, pbToBeSigned, cbToBeSigned, perr)) goto errorReturn; break; #endif #ifdef USE_ECDSA_SHA_512 case COSE_Algorithm_ECDSA_SHA_512: - if (!ECDSA_Verify(&pSigner->m_message, INDEX_SIGNATURE, pSigner->m_pkey, 512, pbToBeSigned, cbToBeSigned, perr)) goto errorReturn; + if (!ECDSA_Verify(&pSigner->m_message, INDEX_SIGNATURE, &eckey, 512, pbToBeSigned, cbToBeSigned, perr)) goto errorReturn; break; #endif @@ -343,7 +361,7 @@ bool _COSE_Signer_validate(COSE_SignMessage * pSign, COSE_SignerInfo * pSigner, errorReturn: if (pbToBeSigned != NULL) COSE_FREE(pbToBeSigned, context); - + eckey_release(&eckey); return fRet; } diff --git a/src/cose_int.h b/src/cose_int.h index 2cd8a6b..da73594 100644 --- a/src/cose_int.h +++ b/src/cose_int.h @@ -280,6 +280,9 @@ enum { COSE_Int_Alg_AES_CBC_MAC_256_64 = -22 }; +// KEY +void eckey_release(eckey_t * eckey); +bool eckey_from_cbor(eckey_t * eckey, const cn_cbor * pKey, cose_errback * perr); #define COSE_CounterSign_object 1000 #endif // __COSE_INT_H__ diff --git a/src/crypto.h b/src/crypto.h index 894cb44..d52e683 100644 --- a/src/crypto.h +++ b/src/crypto.h @@ -46,7 +46,7 @@ extern bool AES_CBC_MAC_Validate(COSE_MacMessage * pcose, int TagSize, const byt bool HMAC_Create(COSE_MacMessage * pcose, int HSize, int TSize, const byte * pbKey, size_t cbKey, const byte * pbAuthData, size_t cbAuthData, cose_errback * perr); bool HMAC_Validate(COSE_MacMessage * pcose, int HSize, int TSize, const byte * pbKey, size_t cbitKey, const byte * pbAuthData, size_t cbAuthData, cose_errback * perr); -bool HKDF_Extract(COSE * pcose, const byte * pbKey, size_t cbKey, size_t cbitDigest, byte * rgbDigest, size_t * pcbDigest, CBOR_CONTEXT_COMMA cose_errback * perr); +bool HKDF_Extract(COSE * pcose, const byte * pbKey, size_t cbKey, size_t cbitDigest, byte * rgbDigest, size_t * pcbDigest, cose_errback * perr); bool HKDF_Expand(COSE * pcose, size_t cbitDigest, const byte * pbPRK, size_t cbPRK, const byte * pbInfo, size_t cbInfo, byte * pbOutput, size_t cbOutput, cose_errback * perr); bool HKDF_AES_Expand(COSE * pcose, size_t cbitKey, const byte * pbPRK, size_t cbPRK, const byte * pbInfo, size_t cbInfo, byte * pbOutput, size_t cbOutput, cose_errback * perr); @@ -60,8 +60,8 @@ bool HKDF_AES_Expand(COSE * pcose, size_t cbitKey, const byte * pbPRK, size_t cb * @param[in] cose_errback * Error return location * @return Did the function succeed? */ -bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitsDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr); -bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitsDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr); +bool ECDSA_Sign(COSE * pSigner, int index, const eckey_t * eckey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr); +bool ECDSA_Verify(COSE * pSigner, int index, const eckey_t * eckey, int cbitsDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr); bool ECDH_ComputeSecret(COSE * pReciient, cn_cbor ** ppKeyMe, const cn_cbor * pKeyYou, byte ** ppbSecret, size_t * pcbSecret, CBOR_CONTEXT_COMMA cose_errback *perr); diff --git a/src/key.c b/src/key.c new file mode 100644 index 0000000..cc9758b --- /dev/null +++ b/src/key.c @@ -0,0 +1,127 @@ + +#include "cose.h" +#include "cose_int.h" + +#include + +#include + + +#ifdef USE_MBED_TLS +#include +#else +#include +#include +#include +#endif + +#define COSE_Key_EC_Curve -1 +#define COSE_Key_EC_X -2 +#define COSE_Key_EC_Y -3 +#define COSE_Key_EC_d -4 + +#if USE_MBED_TLS + +void eckey_release(eckey_t * eckey) +{ + if (eckey != NULL) { + mbedtls_ecp_keypair_free(eckey); + } +} + +bool eckey_from_cbor(eckey_t * eckey, const cn_cbor * pKey, cose_errback * perr) +{ + byte rgbKey[MBEDTLS_ECP_MAX_PT_LEN]; + int cbKey; + int cbGroup; + const cn_cbor * p; + mbedtls_ecp_group_id groupId; + + mbedtls_ecp_keypair_init(eckey); + + p = cn_cbor_mapget_int(pKey, COSE_Key_Type); + CHECK_CONDITION(p != NULL, COSE_ERR_INVALID_PARAMETER); + if(p->type == CN_CBOR_UINT) { + CHECK_CONDITION(p->v.uint == COSE_Key_Type_EC2, COSE_ERR_INVALID_PARAMETER); + } + else { + FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER); + } + + p = cn_cbor_mapget_int(pKey, COSE_Key_EC_Curve); + CHECK_CONDITION((p != NULL) && (p->type == CN_CBOR_UINT), COSE_ERR_INVALID_PARAMETER); + + switch (p->v.uint) { + case 1: // P-256 + groupId = MBEDTLS_ECP_DP_SECP256R1; + break; + + case 2: // P-384 + groupId = MBEDTLS_ECP_DP_SECP384R1; + break; + + case 3: // P-521 + groupId = MBEDTLS_ECP_DP_SECP521R1; + break; + + default: + FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER); + } + CHECK_CONDITION(mbedtls_ecp_group_load(&eckey->grp, groupId) == 0, COSE_ERR_INVALID_PARAMETER); + cbGroup = (eckey->grp.nbits + 7) / 8; + + p = cn_cbor_mapget_int(pKey, COSE_Key_EC_X); + CHECK_CONDITION((p != NULL) && (p->type == CN_CBOR_BYTES), COSE_ERR_INVALID_PARAMETER); + CHECK_CONDITION(p->length == cbGroup, COSE_ERR_INVALID_PARAMETER); + memcpy(rgbKey+1, p->v.str, p->length); + + p = cn_cbor_mapget_int(pKey, COSE_Key_EC_Y); + CHECK_CONDITION((p != NULL), COSE_ERR_INVALID_PARAMETER); + if (p->type == CN_CBOR_BYTES) { + rgbKey[0] = 0x04; + cbKey = cbGroup * 2 + 1; + CHECK_CONDITION(p->length == cbGroup, COSE_ERR_INVALID_PARAMETER); + memcpy(rgbKey + p->length + 1, p->v.str, p->length); + } + else if (p->type == CN_CBOR_TRUE) { + cbKey = cbGroup + 1; + rgbKey[0] = 0x03; + } + else if (p->type == CN_CBOR_FALSE) { + cbKey = cbGroup + 1; + rgbKey[0] = 0x02; + } + else FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER); + + CHECK_CONDITION(mbedtls_ecp_point_read_binary(&eckey->grp, &eckey->Q, rgbKey, cbKey) == 0, COSE_ERR_INVALID_PARAMETER); + + p = cn_cbor_mapget_int(pKey, COSE_Key_EC_d); + if (p != NULL) { + CHECK_CONDITION(p->type == CN_CBOR_BYTES, COSE_ERR_INVALID_PARAMETER); + CHECK_CONDITION(mbedtls_mpi_read_binary( &eckey->d, p->v.bytes, p->length) == 0, COSE_ERR_CRYPTO_FAIL); + } + return true; + +errorReturn: + return false; +} + +#else + +extern EC_KEY * ECKey_From(const cn_cbor * pKey, int * cbGroup, cose_errback * perr); + +void eckey_release(eckey_t * eckey) +{ + if (eckey != NULL && eckey->key != NULL) { + EC_KEY_free(eckey->key); + eckey->key = NULL; + } +} + +bool eckey_from_cbor(eckey_t * eckey, const cn_cbor * pKey, cose_errback * perr) +{ + eckey->key = ECKey_From(pKey, &eckey->group, perr); + return eckey->key != NULL; +} + +#endif // USE_MBED_TLS diff --git a/src/mbedtls.c b/src/mbedtls.c index 2180f61..8a84507 100644 --- a/src/mbedtls.c +++ b/src/mbedtls.c @@ -547,7 +547,7 @@ bool HKDF_AES_Expand(COSE * pcose, size_t cbitKey, const byte * pbPRK, size_t cb } -bool HKDF_Extract(COSE * pcose, const byte * pbKey, size_t cbKey, size_t cbitDigest, byte * rgbDigest, size_t * pcbDigest, CBOR_CONTEXT_COMMA cose_errback * perr) +bool HKDF_Extract(COSE * pcose, const byte * pbKey, size_t cbKey, size_t cbitDigest, byte * rgbDigest, size_t * pcbDigest, cose_errback * perr) { byte rgbSalt[EVP_MAX_MD_SIZE] = { 0 }; int cbSalt; @@ -763,87 +763,6 @@ bool HMAC_Validate(COSE_MacMessage * pcose, int HSize, int TSize, const byte * p return false; } -#define COSE_Key_EC_Curve -1 -#define COSE_Key_EC_X -2 -#define COSE_Key_EC_Y -3 -#define COSE_Key_EC_d -4 - -bool ECKey_From(const cn_cbor * pKey, mbedtls_ecp_keypair *keypair, cose_errback * perr) -{ - byte rgbKey[MBEDTLS_ECP_MAX_PT_LEN]; - int cbKey; - int cbGroup; - const cn_cbor * p; - mbedtls_ecp_group_id groupId; - - p = cn_cbor_mapget_int(pKey, COSE_Key_Type); - CHECK_CONDITION(p != NULL, COSE_ERR_INVALID_PARAMETER); - if(p->type == CN_CBOR_UINT) { - CHECK_CONDITION(p->v.uint == COSE_Key_Type_EC2, COSE_ERR_INVALID_PARAMETER); - } - else { - FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER); - } - - p = cn_cbor_mapget_int(pKey, COSE_Key_EC_Curve); - CHECK_CONDITION((p != NULL) && (p->type == CN_CBOR_UINT), COSE_ERR_INVALID_PARAMETER); - - switch (p->v.uint) { - case 1: // P-256 - groupId = MBEDTLS_ECP_DP_SECP256R1; - break; - - case 2: // P-384 - groupId = MBEDTLS_ECP_DP_SECP384R1; - break; - - case 3: // P-521 - groupId = MBEDTLS_ECP_DP_SECP521R1; - break; - - default: - FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER); - } - CHECK_CONDITION(mbedtls_ecp_group_load(&keypair->grp, groupId) == 0, COSE_ERR_INVALID_PARAMETER); - cbGroup = (keypair->grp.nbits + 7) / 8; - - p = cn_cbor_mapget_int(pKey, COSE_Key_EC_X); - CHECK_CONDITION((p != NULL) && (p->type == CN_CBOR_BYTES), COSE_ERR_INVALID_PARAMETER); - CHECK_CONDITION(p->length == cbGroup, COSE_ERR_INVALID_PARAMETER); - memcpy(rgbKey+1, p->v.str, p->length); - - - p = cn_cbor_mapget_int(pKey, COSE_Key_EC_Y); - CHECK_CONDITION((p != NULL), COSE_ERR_INVALID_PARAMETER); - if (p->type == CN_CBOR_BYTES) { - rgbKey[0] = 0x04; - cbKey = cbGroup * 2 + 1; - CHECK_CONDITION(p->length == cbGroup, COSE_ERR_INVALID_PARAMETER); - memcpy(rgbKey + p->length + 1, p->v.str, p->length); - } - else if (p->type == CN_CBOR_TRUE) { - cbKey = cbGroup + 1; - rgbKey[0] = 0x03; - } - else if (p->type == CN_CBOR_FALSE) { - cbKey = cbGroup + 1; - rgbKey[0] = 0x02; - } - else FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER); - - CHECK_CONDITION(mbedtls_ecp_point_read_binary(&keypair->grp, &keypair->Q, rgbKey, cbKey) == 0, COSE_ERR_INVALID_PARAMETER); - - p = cn_cbor_mapget_int(pKey, COSE_Key_EC_d); - if (p != NULL) { - CHECK_CONDITION(p->type == CN_CBOR_BYTES, COSE_ERR_INVALID_PARAMETER); - CHECK_CONDITION(mbedtls_mpi_read_binary( &keypair->d, p->v.bytes, p->length) == 0, COSE_ERR_CRYPTO_FAIL); - } - return true; - -errorReturn: - return false; -} - /* cn_cbor * EC_FromKey(const EC_KEY * pKey, CBOR_CONTEXT_COMMA cose_errback * perr) { @@ -929,7 +848,7 @@ cn_cbor * EC_FromKey(const EC_KEY * pKey, CBOR_CONTEXT_COMMA cose_errback * perr } */ -bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) +bool ECDSA_Sign(COSE * pSigner, int index, const eckey_t * eckey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) { #if defined(MBEDTLS_ECDSA_DETERMINISTIC) byte rgbDigest[MBEDTLS_MD_MAX_SIZE]; @@ -938,7 +857,6 @@ bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, int cbR; mbedtls_md_type_t mdType; const mbedtls_md_info_t *pmdInfo; - mbedtls_ecp_keypair keypair; mbedtls_mpi r; mbedtls_mpi s; #ifdef USE_CBOR_CONTEXT @@ -947,13 +865,10 @@ bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, cn_cbor * p = NULL; bool result = false; - mbedtls_ecp_keypair_init(&keypair); mbedtls_mpi_init(&r); mbedtls_mpi_init(&s); - if(!ECKey_From(pKey, &keypair, perr)) goto errorReturn; - - CHECK_CONDITION(keypair.d.n != 0, COSE_ERR_INVALID_PARAMETER); + CHECK_CONDITION(eckey->d.n != 0, COSE_ERR_INVALID_PARAMETER); switch(cbitDigest) { @@ -976,9 +891,9 @@ bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, CHECK_CONDITION(pmdInfo != NULL, COSE_ERR_INVALID_PARAMETER); CHECK_CONDITION(mbedtls_md(pmdInfo, rgbToSign, cbToSign, rgbDigest) == 0, COSE_ERR_INVALID_PARAMETER); - CHECK_CONDITION(mbedtls_ecdsa_sign_det(&keypair.grp, &r, &s, &keypair.d, rgbDigest, mbedtls_md_get_size(pmdInfo), mdType) == 0, COSE_ERR_CRYPTO_FAIL); + CHECK_CONDITION(mbedtls_ecdsa_sign_det((mbedtls_ecp_group*)&eckey->grp, &r, &s, &eckey->d, rgbDigest, mbedtls_md_get_size(pmdInfo), mdType) == 0, COSE_ERR_CRYPTO_FAIL); - cbR = (keypair.grp.nbits + 7) / 8; + cbR = (eckey->grp.nbits + 7) / 8; pbSig = COSE_CALLOC(cbR, 2, context); CHECK_CONDITION(pbSig != NULL, COSE_ERR_OUT_OF_MEMORY); @@ -1000,7 +915,6 @@ bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, COSE_FREE(pbSig, context); mbedtls_mpi_free(&r); mbedtls_mpi_free(&s); - mbedtls_ecp_keypair_free(&keypair); return result; #else return false; @@ -1008,9 +922,8 @@ bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, } -bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) +bool ECDSA_Verify(COSE * pSigner, int index, const eckey_t * eckey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) { - mbedtls_ecp_keypair keypair; mbedtls_mpi r; mbedtls_mpi s; mbedtls_md_type_t mdType; @@ -1019,12 +932,9 @@ bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDiges cn_cbor * pSig; bool result = false; - mbedtls_ecp_keypair_init(&keypair); mbedtls_mpi_init(&r); mbedtls_mpi_init(&s); - if(!ECKey_From(pKey, &keypair, perr)) goto errorReturn; - switch(cbitDigest) { case 256: @@ -1051,14 +961,13 @@ bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDiges CHECK_CONDITION(mbedtls_mpi_read_binary( &r, pSig->v.bytes, pSig->length / 2 ) == 0, COSE_ERR_OUT_OF_MEMORY); CHECK_CONDITION(mbedtls_mpi_read_binary( &s, pSig->v.bytes + pSig->length / 2, pSig->length / 2 ) == 0, COSE_ERR_OUT_OF_MEMORY); - CHECK_CONDITION(mbedtls_ecdsa_verify(&keypair.grp, rgbDigest, mbedtls_md_get_size(pmdInfo), &keypair.Q, &r, &s) == 0, COSE_ERR_CRYPTO_FAIL); + CHECK_CONDITION(mbedtls_ecdsa_verify((mbedtls_ecp_group*)&eckey->grp, rgbDigest, mbedtls_md_get_size(pmdInfo), &eckey->Q, &r, &s) == 0, COSE_ERR_CRYPTO_FAIL); result = true; errorReturn: mbedtls_mpi_free(&r); mbedtls_mpi_free(&s); - mbedtls_ecp_keypair_free(&keypair); return result; } @@ -1114,7 +1023,7 @@ bool AES_KW_Encrypt(COSE_RecipientInfo * pcose, const byte * pbKeyIn, int cbitKe /* //#include //TODO void rand_bytes(byte * pb, size_t cb){ -//ctx->aes_ctx->rk e null... i callchainen längst in. prova istället: +//ctx->aes_ctx->rk e null... i callchainen l�ngst in. prova ist�llet: //kolla https://tls.mbed.org/kb/how-to/add-a-random-generator //init random mbedtls_ctr_drbg_context ctr_drbg; diff --git a/src/openssl.c b/src/openssl.c index 4907996..ced5e58 100644 --- a/src/openssl.c +++ b/src/openssl.c @@ -643,7 +643,7 @@ bool HKDF_AES_Expand(COSE * pcose, size_t cbitKey, const byte * pbPRK, size_t cb } -bool HKDF_Extract(COSE * pcose, const byte * pbKey, size_t cbKey, size_t cbitDigest, byte * rgbDigest, size_t * pcbDigest, CBOR_CONTEXT_COMMA cose_errback * perr) +bool HKDF_Extract(COSE * pcose, const byte * pbKey, size_t cbKey, size_t cbitDigest, byte * rgbDigest, size_t * pcbDigest, cose_errback * perr) { byte rgbSalt[EVP_MAX_MD_SIZE] = { 0 }; int cbSalt; @@ -995,9 +995,11 @@ bool ECDSA_Sign(const cn_cbor * pKey) } */ -bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) +bool ECDSA_Sign(COSE * pSigner, int index, const eckey_t * pKey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) { - EC_KEY * eckey = NULL; + EC_KEY * eckey = pKey->key; + int cbR = pKey->group; + byte rgbDigest[EVP_MAX_MD_SIZE]; unsigned int cbDigest = sizeof(rgbDigest); byte * pbSig = NULL; @@ -1008,16 +1010,13 @@ bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, cn_cbor * p = NULL; ECDSA_SIG * psig = NULL; cn_cbor_errback cbor_error; - int cbR; byte rgbSig[66]; int cb; - - eckey = ECKey_From(pKey, &cbR, perr); + if (eckey == NULL) { errorReturn: if (pbSig != NULL) COSE_FREE(pbSig, context); if (p != NULL) CN_CBOR_FREE(p, context); - if (eckey != NULL) EC_KEY_free(eckey); return false; } @@ -1052,17 +1051,16 @@ bool ECDSA_Sign(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, CHECK_CONDITION_CBOR(p != NULL, cbor_error); CHECK_CONDITION(_COSE_array_replace(pSigner, p, index, CBOR_CONTEXT_PARAM_COMMA NULL), COSE_ERR_CBOR); - - pbSig = NULL; - if (eckey != NULL) EC_KEY_free(eckey); + pbSig = NULL; return true; } -bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) +bool ECDSA_Verify(COSE * pSigner, int index, const eckey_t * pKey, int cbitDigest, const byte * rgbToSign, size_t cbToSign, cose_errback * perr) { - EC_KEY * eckey = NULL; + EC_KEY * eckey = pKey->key; + int cbR = pKey->group; byte rgbDigest[EVP_MAX_MD_SIZE]; unsigned int cbDigest = sizeof(rgbDigest); const EVP_MD * digest; @@ -1071,17 +1069,14 @@ bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDiges #endif cn_cbor * p = NULL; ECDSA_SIG *sig = NULL; - int cbR; cn_cbor * pSig; size_t cbSignature; BIGNUM *r, *s; - eckey = ECKey_From(pKey, &cbR, perr); if (eckey == NULL) { errorReturn: if (p != NULL) CN_CBOR_FREE(p, context); - if (eckey != NULL) EC_KEY_free(eckey); if (sig != NULL) ECDSA_SIG_free(sig); return false; } @@ -1099,7 +1094,7 @@ bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDiges CHECK_CONDITION(pSig != NULL, COSE_ERR_INVALID_PARAMETER); cbSignature = pSig->length; - CHECK_CONDITION(cbSignature / 2 == cbR, COSE_ERR_INVALID_PARAMETER); + CHECK_CONDITION(cbSignature / 2 == (size_t)cbR, COSE_ERR_INVALID_PARAMETER); r = BN_bin2bn(pSig->v.bytes,(int) cbSignature/2, NULL); CHECK_CONDITION(NULL != r, COSE_ERR_OUT_OF_MEMORY); s = BN_bin2bn(pSig->v.bytes+cbSignature/2, (int) cbSignature/2, NULL); @@ -1112,7 +1107,6 @@ bool ECDSA_Verify(COSE * pSigner, int index, const cn_cbor * pKey, int cbitDiges CHECK_CONDITION(ECDSA_do_verify(rgbDigest, cbDigest, sig, eckey) == 1, COSE_ERR_CRYPTO_FAIL); - if (eckey != NULL) EC_KEY_free(eckey); if (sig != NULL) ECDSA_SIG_free(sig); return true; diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index 6e36d39..de97575 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -62,7 +62,7 @@ add_test ( NAME sign WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND cose_test --d add_test ( NAME sign1 WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND cose_test --dir Examples/sign1-tests ) -add_test (NAME corner-cases WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND cose_test --corners ) +add_test (NAME corner-cases WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND cose_test --corners Examples/ecdsa-examples/ecdsa-sig-01.json ) add_test (NAME Memory-mac-hmac WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND cose_test --memory Examples/hmac-examples/HMac-01.json ) add_test (NAME Memory-mac-cbc-mac WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND cose_test --memory Examples/cbc-mac-examples/cbc-mac-01.json ) diff --git a/test/context.c b/test/context.c index dbdea88..e0160b0 100644 --- a/test/context.c +++ b/test/context.c @@ -29,14 +29,13 @@ typedef struct _MyItem { bool CheckMemory(MyContext * pContext) { MyItem * p; - int i; // Walk memory and check every block for (p = (MyItem *) pContext->pFirst; p != NULL; p = p->pNext) { if (p->pad[0] == (byte) 0xab) { // Block has been freed - for (i = 0; i < p->size + 8; i++) { + for (unsigned i = 0; i < p->size + 8; i++) { if (p->pad[i] != (byte) 0xab) { fprintf(stderr, "Freed block is modified"); assert(false); @@ -44,7 +43,7 @@ bool CheckMemory(MyContext * pContext) } } else if (p->pad[0] == (byte) 0xef) { - for (i = 0; i < 4; i++) { + for (unsigned i = 0; i < 4; i++) { if ((p->pad[i] != (byte) 0xef) || (p->pad[i + 4 + p->size] != (byte) 0xef)) { fprintf(stderr, "Curent block was overrun"); assert(false); diff --git a/test/encrypt.c b/test/encrypt.c index 0fb56c8..25bc293 100644 --- a/test/encrypt.c +++ b/test/encrypt.c @@ -423,10 +423,8 @@ int _ValidateEncrypt(const cn_cbor * pControl, const byte * pbEncoded, size_t cb fAlgSupport = false; } else if ((pFail != NULL) && (pFail->type != CN_CBOR_TRUE)) fFail = true; - - size_t cb; - byte * pb; - pb = COSE_Encrypt_GetContent(hEnc, &cb, NULL); + size_t cb; + COSE_Encrypt_GetContent(hEnc, &cb, NULL); } else { if (fAlgSupport) { diff --git a/test/json.c b/test/json.c index 9508126..b026ffe 100644 --- a/test/json.c +++ b/test/json.c @@ -217,10 +217,10 @@ unsigned char *base64_decode(const char *data, for (unsigned int i = 0, j = 0; i < input_length;) { - uint32_t sextet_a = data[i] == '=' ? 0 & i++ : decoding_table[(int) data[i++]]; - uint32_t sextet_b = data[i] == '=' ? 0 & i++ : decoding_table[(int) data[i++]]; - uint32_t sextet_c = data[i] == '=' ? 0 & i++ : decoding_table[(int) data[i++]]; - uint32_t sextet_d = data[i] == '=' ? 0 & i++ : decoding_table[(int) data[i++]]; + uint32_t sextet_a = data[i] == '=' ? 0 & i++ : (unsigned)decoding_table[(int) data[i++]]; + uint32_t sextet_b = data[i] == '=' ? 0 & i++ : (unsigned)decoding_table[(int) data[i++]]; + uint32_t sextet_c = data[i] == '=' ? 0 & i++ : (unsigned)decoding_table[(int) data[i++]]; + uint32_t sextet_d = data[i] == '=' ? 0 & i++ : (unsigned)decoding_table[(int) data[i++]]; uint32_t triple = (sextet_a << 3 * 6) + (sextet_b << 2 * 6) diff --git a/test/sign.c b/test/sign.c index 6231526..2708cc7 100644 --- a/test/sign.c +++ b/test/sign.c @@ -500,14 +500,20 @@ void Sign_Corners() #endif #if INCLUDE_SIGN0 -void Sign0_Corners() +void Sign0_Corners(const cn_cbor * pControl) { HCOSE_SIGN0 hSign = NULL; HCOSE_SIGN0 hSignNULL = NULL; HCOSE_SIGN0 hSignBad; byte rgb[10]; - cn_cbor * cn = cn_cbor_int_create(5, CBOR_CONTEXT_PARAM_COMMA NULL); + const cn_cbor * pInputs = cn_cbor_mapget_string(pControl, "input"); + if (pInputs == NULL) goto returnError; + const cn_cbor * pSign = cn_cbor_mapget_string(pInputs, "sign0"); + if (pSign == NULL) goto returnError; + cn_cbor * cn = BuildKey(cn_cbor_mapget_string(pSign, "key"), false); + if (cn == NULL) goto returnError; + cose_errback cose_error; hSign = COSE_Sign0_Init(0, CBOR_CONTEXT_PARAM_COMMA NULL); @@ -571,5 +577,9 @@ void Sign0_Corners() COSE_Sign0_Free(hSign); return; + +returnError: + ++CFails; + return; } #endif diff --git a/test/test.c b/test/test.c index 1fbc21f..8063ed1 100644 --- a/test/test.c +++ b/test/test.c @@ -320,6 +320,8 @@ bool SetAttributes(HCOSE hHandle, const cn_cbor * pAttributes, int which, int ms cn_cbor * pValueNew; bool f = false; + (void)(f); + if (pAttributes == NULL) return true; if (pAttributes->type != CN_CBOR_MAP) return false; @@ -572,7 +574,7 @@ cn_cbor * BuildKey(const cn_cbor * pKeyIn, bool fPublicKey) if (pKey->type == CN_CBOR_TEXT) { for (i = 0; i < 7; i++) { - if ((pKey->length == strlen(RgStringKeys[i].szKey)) && + if (((size_t)pKey->length == strlen(RgStringKeys[i].szKey)) && (strncmp(pKey->v.str, RgStringKeys[i].szKey, strlen(RgStringKeys[i].szKey)) == 0) && ((RgStringKeys[i].kty == 0) || (RgStringKeys[i].kty == kty))) { switch (RgStringKeys[i].operation) { @@ -640,8 +642,14 @@ bool Test_cn_cbor_array_replace() } -void RunCorners() +void RunCorners(const char *szFileName) { + const cn_cbor *pControl = ParseJson(szFileName); + if (pControl == NULL) { + CFails += 1; + return; + } + Test_cn_cbor_array_replace(); #if INCLUDE_MAC MAC_Corners(); @@ -659,7 +667,7 @@ void RunCorners() Sign_Corners(); #endif #if INCLUDE_SIGN0 - Sign0_Corners(); + Sign0_Corners(pControl); #endif #if INCLUDE_ENCRYPT || INCLUDE_MAC Recipient_Corners(); @@ -818,6 +826,7 @@ void RunMemoryTest(const char * szFileName) CFails = 0; context = NULL; #else + (void)(szFileName); return; #endif } @@ -1027,7 +1036,7 @@ int main(int argc, char ** argv) else RunFileTest(szWhere); } else if (fCorners) { - RunCorners(); + RunCorners(szWhere); } else { #ifdef USE_CBOR_CONTEXT diff --git a/test/test.h b/test/test.h index 752f788..f2f19d8 100644 --- a/test/test.h +++ b/test/test.h @@ -32,7 +32,7 @@ int BuildSignedMessage(const cn_cbor * pControl); int ValidateSign0(const cn_cbor * pControl); int BuildSign0Message(const cn_cbor * pControl); void Sign_Corners(); -void Sign0_Corners(); +void Sign0_Corners(const cn_cbor * pControl); // mac_testc From 059e8f4dbe9827ed89f6731e95052a5a1b79ed94 Mon Sep 17 00:00:00 2001 From: Kangping Dong Date: Sun, 11 Aug 2019 16:21:39 +0800 Subject: [PATCH 2/3] add definition of USE_MBED_TLS --- include/cose.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/cose.h b/include/cose.h index c96036a..3e3d9ec 100644 --- a/include/cose.h +++ b/include/cose.h @@ -1,3 +1,5 @@ +#define USE_MBED_TLS 1 + #include #ifdef __cplusplus From d26157bdb7d4a9d1a8ebb9b8dd9e88c079193ae0 Mon Sep 17 00:00:00 2001 From: Kangping Dong Date: Tue, 2 Apr 2024 19:51:05 +0800 Subject: [PATCH 3/3] upgrade to support mbedtls 3.x --- src/key.c | 1 + src/mbedtls.c | 36 ++++++++++++++++++++---------------- 2 files changed, 21 insertions(+), 16 deletions(-) diff --git a/src/key.c b/src/key.c index cc9758b..61baa63 100644 --- a/src/key.c +++ b/src/key.c @@ -8,6 +8,7 @@ #ifdef USE_MBED_TLS +#define MBEDTLS_ALLOW_PRIVATE_ACCESS #include #else #include diff --git a/src/mbedtls.c b/src/mbedtls.c index 8a84507..bcdcdcb 100644 --- a/src/mbedtls.c +++ b/src/mbedtls.c @@ -10,6 +10,7 @@ #include #ifdef USE_MBED_TLS +#define MBEDTLS_ALLOW_PRIVATE_ACCESS #include "mbedtls/ccm.h" #include "mbedtls/md.h" @@ -857,6 +858,8 @@ bool ECDSA_Sign(COSE * pSigner, int index, const eckey_t * eckey, int cbitDigest int cbR; mbedtls_md_type_t mdType; const mbedtls_md_info_t *pmdInfo; + mbedtls_entropy_context entropy; + mbedtls_ctr_drbg_context ctrDrbg; mbedtls_mpi r; mbedtls_mpi s; #ifdef USE_CBOR_CONTEXT @@ -865,6 +868,9 @@ bool ECDSA_Sign(COSE * pSigner, int index, const eckey_t * eckey, int cbitDigest cn_cbor * p = NULL; bool result = false; + mbedtls_entropy_init(&entropy); + mbedtls_ctr_drbg_init(&ctrDrbg); + mbedtls_ctr_drbg_seed(&ctrDrbg, mbedtls_entropy_func, &entropy, NULL, 0); mbedtls_mpi_init(&r); mbedtls_mpi_init(&s); @@ -891,7 +897,7 @@ bool ECDSA_Sign(COSE * pSigner, int index, const eckey_t * eckey, int cbitDigest CHECK_CONDITION(pmdInfo != NULL, COSE_ERR_INVALID_PARAMETER); CHECK_CONDITION(mbedtls_md(pmdInfo, rgbToSign, cbToSign, rgbDigest) == 0, COSE_ERR_INVALID_PARAMETER); - CHECK_CONDITION(mbedtls_ecdsa_sign_det((mbedtls_ecp_group*)&eckey->grp, &r, &s, &eckey->d, rgbDigest, mbedtls_md_get_size(pmdInfo), mdType) == 0, COSE_ERR_CRYPTO_FAIL); + CHECK_CONDITION(mbedtls_ecdsa_sign_det_ext((mbedtls_ecp_group*)&eckey->grp, &r, &s, &eckey->d, rgbDigest, mbedtls_md_get_size(pmdInfo), mdType, mbedtls_ctr_drbg_random, &ctrDrbg) == 0, COSE_ERR_CRYPTO_FAIL); cbR = (eckey->grp.nbits + 7) / 8; @@ -915,6 +921,8 @@ bool ECDSA_Sign(COSE * pSigner, int index, const eckey_t * eckey, int cbitDigest COSE_FREE(pbSig, context); mbedtls_mpi_free(&r); mbedtls_mpi_free(&s); + mbedtls_entropy_free(&entropy); + mbedtls_ctr_drbg_free(&ctrDrbg); return result; #else return false; @@ -1069,22 +1077,18 @@ static int ctr_drbg_self_test_entropy( void *data, unsigned char *buf, size_t le return( 0 ); } -void rand_bytes(byte* pb, size_t cb){ - - mbedtls_ctr_drbg_context ctx; - // unsigned char buf[16]; - - mbedtls_ctr_drbg_init( &ctx ); - - mbedtls_ctr_drbg_seed_entropy_len( &ctx, ctr_drbg_self_test_entropy, (void *) entropy_source_pr, nonce_pers_pr, 16, 32 ); - - //mbedtls_ctr_drbg_set_prediction_resistance( &ctx, MBEDTLS_CTR_DRBG_PR_ON ); +void rand_bytes(byte* pb, size_t cb) { + mbedtls_entropy_context entropy; + mbedtls_ctr_drbg_context ctrDrbg; + + mbedtls_entropy_init(&entropy); + mbedtls_ctr_drbg_init(&ctrDrbg); + mbedtls_ctr_drbg_seed(&ctrDrbg, mbedtls_entropy_func, &entropy, nonce_pers_pr, sizeof(nonce_pers_pr)); - mbedtls_ctr_drbg_random( &ctx, pb, cb ); - //mbedtls_ctr_drbg_random( &ctx, buf, MBEDTLS_CTR_DRBG_BLOCKSIZE ); - //memcmp( buf, result_pr, MBEDTLS_CTR_DRBG_BLOCKSIZE ) ); - - mbedtls_ctr_drbg_free( &ctx ); + mbedtls_ctr_drbg_random(&ctrDrbg, pb, cb); + + mbedtls_ctr_drbg_free(&ctrDrbg); + mbedtls_entropy_free(&entropy); } //END OF TODO RANDOM BYTES