#include <stdlib.h>
#ifndef __MBED__
#include <memory.h>
#endif

#include "cose/cose.h"
#include "cose_int.h"
#include "cose/cose_configure.h"
#include "crypto.h"

#if INCLUDE_ENCRYPT || INCLUDE_ENCRYPT0 || INCLUDE_MAC || INCLUDE_MAC0
static bool BuildContextBytes(COSE *pcose,
	int algID,
	size_t cbitKey,
	byte **ppbContext,
	size_t *pcbContext,
	CBOR_CONTEXT_COMMA cose_errback *perr);
#endif

#if INCLUDE_ENCRYPT || INCLUDE_MAC
COSE *RecipientRoot = NULL;

/*! \private
 * @brief Test if a HCOSE_RECIPIENT handle is valid
 *
 *  Internal function to test if a recipient handle is valid.
 *  This will start returning invalid results and cause the code to
 *  crash if handles are not released before the memory that underlies them
 *  is deallocated.  This is an issue of a block allocator is used since
 *  in that case it is common to allocate memory but never to de-allocate it
 *  and just do that in a single big block.
 *
 *  @param h handle to be validated
 *  @returns result of check
 */
bool IsValidRecipientHandle(HCOSE_RECIPIENT h)
{
	COSE_RecipientInfo *p = (COSE_RecipientInfo *)h;

	if (p == NULL) {
		return false;
	}
	return _COSE_IsInList(RecipientRoot, &p->m_encrypt.m_message);
}

HCOSE_RECIPIENT COSE_Recipient_Init(COSE_INIT_FLAGS flags,
	CBOR_CONTEXT_COMMA cose_errback *perr)
{
	CHECK_CONDITION(flags == COSE_INIT_FLAGS_NONE, COSE_ERR_INVALID_PARAMETER);
	COSE_RecipientInfo *pobj = (COSE_RecipientInfo *)COSE_CALLOC(
		1, sizeof(COSE_RecipientInfo), context);
	CHECK_CONDITION(pobj != NULL, COSE_ERR_OUT_OF_MEMORY);

	if (!_COSE_Init(flags | COSE_INIT_FLAGS_NO_CBOR_TAG,
			&pobj->m_encrypt.m_message, COSE_recipient_object,
			CBOR_CONTEXT_PARAM_COMMA perr)) {
		_COSE_Recipient_Free(pobj);
		return NULL;
	}

	_COSE_InsertInList(&RecipientRoot, &pobj->m_encrypt.m_message);
	return (HCOSE_RECIPIENT)pobj;

errorReturn:
	return NULL;
}

bool COSE_Recipient_Free(HCOSE_RECIPIENT hRecipient)
{
	if (IsValidRecipientHandle(hRecipient)) {
		COSE_RecipientInfo *p = (COSE_RecipientInfo *)hRecipient;

		if (p->m_encrypt.m_message.m_refCount > 1) {
			p->m_encrypt.m_message.m_refCount--;
			return true;
		}

		_COSE_RemoveFromList(&RecipientRoot, &p->m_encrypt.m_message);

		_COSE_Recipient_Free(p);
		return true;
	}

	return false;
}

HCOSE_RECIPIENT COSE_Recipient_from_shared_secret(byte *rgbKey,
	int cbKey,
	byte *rgbKid,
	int cbKid,
	CBOR_CONTEXT_COMMA cose_errback *perr)
{
	HCOSE_RECIPIENT hRecipient = NULL;

	hRecipient = COSE_Recipient_Init(0, CBOR_CONTEXT_PARAM_COMMA perr);
	if (hRecipient == NULL) {
		goto errorReturn;
	}

	if (!COSE_Recipient_SetKey_secret(
			hRecipient, rgbKey, cbKey, rgbKid, cbKid, perr)) {
		goto errorReturn;
	}

	return hRecipient;

errorReturn:
	if (hRecipient != NULL) {
		COSE_Recipient_Free(hRecipient);
	}
	return NULL;
}

COSE_RecipientInfo *_COSE_Recipient_Init_From_Object(cn_cbor *cbor,
	CBOR_CONTEXT_COMMA cose_errback *perr)
{
	COSE_RecipientInfo *pRecipient = NULL;

	pRecipient = (COSE_RecipientInfo *)COSE_CALLOC(
		1, sizeof(COSE_RecipientInfo), context);
	CHECK_CONDITION(pRecipient != NULL, COSE_ERR_OUT_OF_MEMORY);

	CHECK_CONDITION(cbor->type == CN_CBOR_ARRAY, COSE_ERR_INVALID_PARAMETER);

	if (_COSE_Enveloped_Init_From_Object(cbor, &pRecipient->m_encrypt,
			CBOR_CONTEXT_PARAM_COMMA perr) == NULL) {
		goto errorReturn;
	}

	_COSE_InsertInList(&RecipientRoot, &pRecipient->m_encrypt.m_message);

	return pRecipient;

errorReturn:
	if (pRecipient != NULL) {
		_COSE_Recipient_Free(pRecipient);
	}
	return NULL;
}

void _COSE_Recipient_Free(COSE_RecipientInfo *pRecipient)
{
	if (pRecipient->m_encrypt.m_message.m_refCount > 1) {
		pRecipient->m_encrypt.m_message.m_refCount--;
		return;
	}

	_COSE_Enveloped_Release(&pRecipient->m_encrypt);
	COSE_FREE(pRecipient, &pRecipient->m_encrypt.m_message.m_allocContext);

	return;
}
#endif

#if INCLUDE_ENCRYPT || INCLUDE_ENCRYPT0 || INCLUDE_MAC || INCLUDE_MAC0
#if defined(USE_HKDF_SHA2) || defined(USE_HKDF_AES)
/**
 * Perform an AES-CCM Decryption operation
 *
 * @param[in]	COSE *		Pointer to COSE Encryption context object
 * @param[in]	int			Alorithm key is being generated for
 * @param[in]	cn_cbor *	Private key
 * @param[in]	cn_cbor *	Public Key
 * @param[out]	byte *		Buffer to return new key in
 * @param[in]	size_t       Size of key to create in bits
 * @param[in]    size_t		Size of digest function
 * @param[in]	cbor_context * Allocation context
 * @param[out]	cose_errback * Returned error information
 * @return                   Did the function succeed?
 */

static bool HKDF_X(COSE *pCose,
	bool fHMAC,
	bool fECDH,
	bool fStatic,
	bool fSend,
	int algResult,
	const cn_cbor *pKeyPrivate,
	const cn_cbor *pKeyPublic,
	byte *pbKey,
	size_t cbitKey,
	size_t cbitHash,
	CBOR_CONTEXT_COMMA cose_errback *perr)
{
	byte *pbContext = NULL;
	size_t cbContext;
	bool fRet = false;
	const cn_cbor *cn;
	byte rgbDigest[512 / 8];
	size_t cbDigest;
	byte *pbSecret = NULL;
	size_t cbSecret = 0;

	if (!BuildContextBytes(pCose, algResult, cbitKey, &pbContext, &cbContext,
			CBOR_CONTEXT_PARAM_COMMA perr)) {
		goto errorReturn;
	}

	if (fECDH) {
#ifdef USE_ECDH
		cn_cbor *pkeyMessage;

		if (pKeyPrivate != NULL) {
			cn = cn_cbor_mapget_int(pKeyPrivate, COSE_Key_Type);
			CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_UINT),
				COSE_ERR_INVALID_PARAMETER);
			CHECK_CONDITION(
				cn->v.uint == COSE_Key_Type_EC2, COSE_ERR_INVALID_PARAMETER);
		}

		if (pKeyPublic != NULL) {
			cn = cn_cbor_mapget_int(pKeyPublic, COSE_Key_Type);
			CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_UINT),
				COSE_ERR_INVALID_PARAMETER);
			CHECK_CONDITION(
				cn->v.uint == COSE_Key_Type_EC2, COSE_ERR_INVALID_PARAMETER);
		}

		if (fSend) {
			CHECK_CONDITION(pKeyPublic != NULL, COSE_ERR_INVALID_PARAMETER);
			pkeyMessage = (cn_cbor *)pKeyPrivate;

			if (!ECDH_ComputeSecret(pCose, &pkeyMessage, pKeyPublic, &pbSecret,
					&cbSecret, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			if (!fStatic && pkeyMessage->parent == NULL) {
				if (!_COSE_map_put(pCose, COSE_Header_ECDH_EPHEMERAL,
						pkeyMessage, COSE_UNPROTECT_ONLY, perr)) {
					goto errorReturn;
				}
			}
		}
		else {
			pkeyMessage = _COSE_map_get_int(pCose,
				fStatic ? COSE_Header_ECDH_STATIC : COSE_Header_ECDH_EPHEMERAL,
				COSE_BOTH, perr);

			CHECK_CONDITION(pkeyMessage != NULL, COSE_ERR_INVALID_PARAMETER);
			CHECK_CONDITION(pKeyPrivate != NULL, COSE_ERR_INVALID_PARAMETER);

			if (!ECDH_ComputeSecret(pCose, (cn_cbor **)&pKeyPrivate,
					pkeyMessage, &pbSecret, &cbSecret,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
		}
#else
		goto errorReturn;
#endif
	}
	else {
		CHECK_CONDITION(pKeyPrivate != NULL, COSE_ERR_INVALID_PARAMETER);
		cn = cn_cbor_mapget_int(pKeyPrivate, COSE_Key_Type);
		CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_UINT),
			COSE_ERR_INVALID_PARAMETER);
		CHECK_CONDITION(
			cn->v.uint == COSE_Key_Type_OCTET, COSE_ERR_INVALID_PARAMETER);

		CHECK_CONDITION(cn->v.sint == 4, COSE_ERR_INVALID_PARAMETER);

		cn = cn_cbor_mapget_int(pKeyPrivate, -1);
		CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_BYTES),
			COSE_ERR_INVALID_PARAMETER);
		pbSecret = (byte *)cn->v.bytes;
		cbSecret = cn->length;
	}

	if (fHMAC) {
#ifdef USE_HKDF_SHA2
		if (!HKDF_Extract(pCose, pbSecret, cbSecret, cbitHash, rgbDigest,
				&cbDigest, CBOR_CONTEXT_PARAM_COMMA perr)) {
			goto errorReturn;
		}

		if (!HKDF_Expand(pCose, cbitHash, rgbDigest, cbDigest, pbContext,
				cbContext, pbKey, cbitKey / 8, perr)) {
			goto errorReturn;
		}
#else
		goto errorReturn;
#endif
	}
	else {
#ifdef USE_HKDF_AES
		if (!HKDF_AES_Expand(pCose, cbitHash, pbSecret, cbSecret, pbContext,
				cbContext, pbKey, cbitKey / 8, perr)) {
			goto errorReturn;
		}
#else
		goto errorReturn;
#endif
	}
	fRet = true;

errorReturn:
	if (fECDH && pbSecret != NULL) {
		memset(pbSecret, 0, cbSecret);
		COSE_FREE(pbSecret, context);
	}
	memset(rgbDigest, 0, sizeof(rgbDigest));
	if (pbContext != NULL) {
		COSE_FREE(pbContext, context);
	}
	return fRet;
}
#endif	// defined(USE_HKDF_SHA2) || defined(USE_HKDF_AES)

bool _COSE_Recipient_decrypt(COSE_RecipientInfo *pRecip,
	COSE_RecipientInfo *pRecipUse,
	int algIn,
	size_t cbitKeyOut,
	byte *pbKeyOut,
	cose_errback *perr)
{
	UNUSED(pRecipUse);
	int alg;
	const cn_cbor *cn = NULL;
	COSE_RecipientInfo *pRecip2;
#ifdef USE_CBOR_CONTEXT
	cn_cbor_context *context;
#endif
	byte *pbAuthData = NULL;
	byte *pbProtected = NULL;
	COSE_Enveloped *pcose = &pRecip->m_encrypt;
	cn_cbor *cnBody = NULL;
	byte *pbContext = NULL;
	byte *pbSecret = NULL;
	int cbKey2;
	byte *pbKeyX = NULL;
	int cbitKeyX = 0;
	byte rgbKey[256 / 8];

#ifdef USE_CBOR_CONTEXT
	context = &pcose->m_message.m_allocContext;
#else
	UNUSED(pcose);
#endif

	cn = _COSE_map_get_int(
		&pRecip->m_encrypt.m_message, COSE_Header_Algorithm, COSE_BOTH, perr);
	if (cn == NULL) {
	errorReturn:
		if (pbContext != NULL) {
			COSE_FREE(pbContext, context);
		}
		if (pbProtected != NULL) {
			COSE_FREE(pbProtected, context);
		}
		if (pbAuthData != NULL) {
			COSE_FREE(pbAuthData, context);
		}
		if (pbSecret != NULL) {
			COSE_FREE(pbSecret, context);
		}
		return false;
	}
	CHECK_CONDITION(cn->type != CN_CBOR_TEXT, COSE_ERR_UNKNOWN_ALGORITHM);
	CHECK_CONDITION((cn->type == CN_CBOR_UINT) || (cn->type == CN_CBOR_INT),
		COSE_ERR_INVALID_PARAMETER);
	alg = (int)cn->v.uint;

	CHECK_CONDITION(pbKeyOut != NULL, COSE_ERR_INVALID_PARAMETER);

	switch (alg) {
		case COSE_Algorithm_Direct:
			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(((size_t)cn->length == cbitKeyOut / 8),
				COSE_ERR_INVALID_PARAMETER);
			memcpy(pbKeyOut, cn->v.bytes, cn->length);

			return true;

#ifdef USE_AES_KW_128
		case COSE_Algorithm_AES_KW_128:
			cbitKeyX = 128;
			break;
#endif

#ifdef USE_AES_KW_192
		case COSE_Algorithm_AES_KW_192:
			cbitKeyX = 192;
			break;
#endif

#ifdef USE_AES_KW_256
		case COSE_Algorithm_AES_KW_256:
			cbitKeyX = 192;
			break;
#endif

#ifdef USE_Direct_HKDF_AES_128
		case COSE_Algorithm_Direct_HKDF_AES_128:
			break;
#endif

#ifdef USE_Direct_HKDF_AES_256
		case COSE_Algorithm_Direct_HKDF_AES_256:
			break;
#endif

#ifdef USE_Direct_HKDF_HMAC_SHA_256
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_256:
			break;
#endif

#ifdef USE_Direct_HKDF_HMAC_SHA_512
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_512:
			break;
#endif

#ifdef USE_ECDH_ES_HKDF_256
		case COSE_Algorithm_ECDH_ES_HKDF_256:
			break;
#endif

#ifdef USE_ECDH_ES_HKDF_512
		case COSE_Algorithm_ECDH_ES_HKDF_512:
			break;
#endif

#ifdef USE_ECDH_SS_HKDF_256
		case COSE_Algorithm_ECDH_SS_HKDF_256:
			break;
#endif

#ifdef USE_ECDH_SS_HKDF_512
		case COSE_Algorithm_ECDH_SS_HKDF_512:
			break;
#endif

#ifdef USE_ECDH_ES_A128KW
		case COSE_Algorithm_ECDH_ES_A128KW:
			break;
#endif

#ifdef USE_ECDH_ES_A192KW
		case COSE_Algorithm_ECDH_ES_A192KW:
			break;
#endif

#ifdef USE_ECDH_ES_A256KW
		case COSE_Algorithm_ECDH_ES_A256KW:
			break;
#endif

#ifdef USE_ECDH_SS_A128KW
		case COSE_Algorithm_ECDH_SS_A128KW:
			break;
#endif

#ifdef USE_ECDH_SS_A192KW
		case COSE_Algorithm_ECDH_SS_A192KW:
			break;
#endif

#ifdef USE_ECDH_SS_A256KW
		case COSE_Algorithm_ECDH_SS_A256KW:
			break;
#endif

		default:
			FAIL_CONDITION(COSE_ERR_UNKNOWN_ALGORITHM);
			break;
	}

	if (pcose->m_recipientFirst != NULL) {
		//  If there is a recipient - ask it for the key
		CHECK_CONDITION(cbitKeyX != 0, COSE_ERR_INVALID_PARAMETER);
		pbKeyX = COSE_CALLOC(cbitKeyX / 8, 1, context);
		CHECK_CONDITION(pbKeyX != NULL, COSE_ERR_OUT_OF_MEMORY);

		for (pRecip2 = pcose->m_recipientFirst; pRecip2 != NULL;
			 pRecip2 = pRecip->m_recipientNext) {
			if (_COSE_Recipient_decrypt(
					pRecip2, NULL, alg, cbitKeyX, pbKeyX, perr)) {
				break;
			}
		}
		CHECK_CONDITION(pRecip2 != NULL, COSE_ERR_NO_RECIPIENT_FOUND);
	}

	cnBody = _COSE_arrayget_int(&pcose->m_message, INDEX_BODY);
	CHECK_CONDITION(cnBody != NULL, COSE_ERR_INVALID_PARAMETER);

	switch (alg) {
#ifdef USE_AES_KW_128
		case COSE_Algorithm_AES_KW_128:
			if (pbKeyX != NULL) {
				int x = cbitKeyOut / 8;
				if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, pbKeyX, cbitKeyX,
						cnBody->v.bytes, cnBody->length, pbKeyOut, &x, perr)) {
					goto errorReturn;
				}
			}
			else {
				CHECK_CONDITION(
					pRecip->m_pkey != NULL, COSE_ERR_INVALID_PARAMETER);
				int x = cbitKeyOut / 8;
				cn = cn_cbor_mapget_int(pRecip->m_pkey, -1);
				CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_BYTES),
					COSE_ERR_INVALID_PARAMETER);

				if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, cn->v.bytes,
						cn->length * 8, cnBody->v.bytes, cnBody->length,
						pbKeyOut, &x, perr)) {
					goto errorReturn;
				}
			}
			break;
#endif

#ifdef USE_AES_KW_192
		case COSE_Algorithm_AES_KW_192:
			if (pbKeyX != NULL) {
				int x = cbitKeyOut / 8;
				if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, pbKeyX, cbitKeyX,
						cnBody->v.bytes, cnBody->length, pbKeyOut, &x, perr)) {
					goto errorReturn;
				}
			}
			else {
				CHECK_CONDITION(
					pRecip->m_pkey != NULL, COSE_ERR_INVALID_PARAMETER);
				int x = cbitKeyOut / 8;
				cn = cn_cbor_mapget_int(pRecip->m_pkey, -1);
				CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_BYTES),
					COSE_ERR_INVALID_PARAMETER);

				if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, cn->v.bytes,
						cn->length * 8, cnBody->v.bytes, cnBody->length,
						pbKeyOut, &x, perr)) {
					goto errorReturn;
				}
			}
			break;
#endif

#ifdef USE_AES_KW_256
		case COSE_Algorithm_AES_KW_256:
			if (pbKeyX != NULL) {
				int x = cbitKeyOut / 8;
				if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, pbKeyX, cbitKeyX,
						cnBody->v.bytes, cnBody->length, pbKeyOut, &x, perr)) {
					goto errorReturn;
				}
			}
			else {
				CHECK_CONDITION(
					pRecip->m_pkey != NULL, COSE_ERR_INVALID_PARAMETER);
				int x = cbitKeyOut / 8;
				cn = cn_cbor_mapget_int(pRecip->m_pkey, -1);
				CHECK_CONDITION((cn != NULL) && (cn->type == CN_CBOR_BYTES),
					COSE_ERR_INVALID_PARAMETER);

				if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, cn->v.bytes,
						cn->length * 8, cnBody->v.bytes, cnBody->length,
						pbKeyOut, &x, perr)) {
					goto errorReturn;
				}
			}
			break;
#endif

#ifdef USE_Direct_HKDF_HMAC_SHA_256
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_256:
			if (!HKDF_X(&pcose->m_message, true, false, false, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_Direct_HKDF_HMAC_SHA_512
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_512:
			if (!HKDF_X(&pcose->m_message, true, false, false, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 512,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_Direct_HKDF_AES_128
		case COSE_Algorithm_Direct_HKDF_AES_128:
			if (!HKDF_X(&pcose->m_message, false, false, false, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 128,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_Direct_HKDF_AES_256
		case COSE_Algorithm_Direct_HKDF_AES_256:
			if (!HKDF_X(&pcose->m_message, false, false, false, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_ES_HKDF_256
		case COSE_Algorithm_ECDH_ES_HKDF_256:
			if (!HKDF_X(&pcose->m_message, true, true, false, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_ES_HKDF_512
		case COSE_Algorithm_ECDH_ES_HKDF_512:
			if (!HKDF_X(&pcose->m_message, true, true, false, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 512,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_SS_HKDF_256
		case COSE_Algorithm_ECDH_SS_HKDF_256:
			if (!HKDF_X(&pcose->m_message, true, true, true, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_SS_HKDF_512
		case COSE_Algorithm_ECDH_SS_HKDF_512:
			if (!HKDF_X(&pcose->m_message, true, true, true, false, algIn,
					pRecip->m_pkey, NULL, pbKeyOut, cbitKeyOut, 512,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_ES_A128KW
		case COSE_Algorithm_ECDH_ES_A128KW:
			if (!HKDF_X(&pcose->m_message, true, true, false, false,
					COSE_Algorithm_AES_KW_128, pRecip->m_pkey, NULL, rgbKey,
					128, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}

			if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, rgbKey, 128,
					cnBody->v.bytes, cnBody->length, pbKeyOut, &cbKey2, perr)) {
				goto errorReturn;
			}

			break;
#endif

#ifdef USE_ECDH_ES_A192KW
		case COSE_Algorithm_ECDH_ES_A192KW:
			if (!HKDF_X(&pcose->m_message, true, true, false, false,
					COSE_Algorithm_AES_KW_192, pRecip->m_pkey, NULL, rgbKey,
					192, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}

			if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, rgbKey, 192,
					cnBody->v.bytes, cnBody->length, pbKeyOut, &cbKey2, perr)) {
				goto errorReturn;
			}

			break;
#endif

#ifdef USE_ECDH_ES_A256KW
		case COSE_Algorithm_ECDH_ES_A256KW:
			if (!HKDF_X(&pcose->m_message, true, true, false, false,
					COSE_Algorithm_AES_KW_256, pRecip->m_pkey, NULL, rgbKey,
					256, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}

			if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, rgbKey, 256,
					cnBody->v.bytes, cnBody->length, pbKeyOut, &cbKey2, perr)) {
				goto errorReturn;
			}

			break;
#endif

#ifdef USE_ECDH_SS_A128KW
		case COSE_Algorithm_ECDH_SS_A128KW:
			if (!HKDF_X(&pcose->m_message, true, true, true, false,
					COSE_Algorithm_AES_KW_128, pRecip->m_pkey, NULL, rgbKey,
					128, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}

			if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, rgbKey, 128,
					cnBody->v.bytes, cnBody->length, pbKeyOut, &cbKey2, perr)) {
				goto errorReturn;
			}

			break;
#endif

#ifdef USE_ECDH_SS_A192KW
		case COSE_Algorithm_ECDH_SS_A192KW:
			if (!HKDF_X(&pcose->m_message, true, true, true, false,
					COSE_Algorithm_AES_KW_192, pRecip->m_pkey, NULL, rgbKey,
					192, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}

			if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, rgbKey, 192,
					cnBody->v.bytes, cnBody->length, pbKeyOut, &cbKey2, perr)) {
				goto errorReturn;
			}

			break;
#endif

#ifdef USE_ECDH_SS_A256KW
		case COSE_Algorithm_ECDH_SS_A256KW:
			if (!HKDF_X(&pcose->m_message, true, true, true, false,
					COSE_Algorithm_AES_KW_256, pRecip->m_pkey, NULL, rgbKey,
					256, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}

			if (!AES_KW_Decrypt((COSE_Enveloped *)pcose, rgbKey, 256,
					cnBody->v.bytes, cnBody->length, pbKeyOut, &cbKey2, perr)) {
				goto errorReturn;
			}

			break;
#endif

		default:
			FAIL_CONDITION(COSE_ERR_UNKNOWN_ALGORITHM);
			break;
	}

	return true;
}

bool _COSE_Recipient_encrypt(COSE_RecipientInfo *pRecipient,
	const byte *pbContent,
	size_t cbContent,
	cose_errback *perr)
{
	int alg;
	int t = 0;
	COSE_RecipientInfo *pri;
	const cn_cbor *cn_Alg = NULL;
	byte *pbAuthData = NULL;
	cn_cbor *ptmp = NULL;
	size_t cbitKey;
#ifdef USE_CBOR_CONTEXT
	cn_cbor_context *context = NULL;
#endif
	cn_cbor_errback cbor_error;
	bool fRet = false;
	byte *pbContext = NULL;
	byte rgbKey[256 / 8];
	byte *pbSecret = NULL;
	byte *pbKey = NULL;
	size_t cbKey = 0;

#ifdef USE_CBOR_CONTEXT
	context = &pRecipient->m_encrypt.m_message.m_allocContext;
#endif	// USE_CBOR_CONTEXT

	cn_Alg = _COSE_map_get_int(&pRecipient->m_encrypt.m_message,
		COSE_Header_Algorithm, COSE_BOTH, perr);
	if (cn_Alg == NULL) {
		goto errorReturn;
	}

	CHECK_CONDITION(cn_Alg->type != CN_CBOR_TEXT, COSE_ERR_UNKNOWN_ALGORITHM);
	CHECK_CONDITION(
		(cn_Alg->type == CN_CBOR_UINT) || (cn_Alg->type == CN_CBOR_INT),
		COSE_ERR_INVALID_PARAMETER);
	alg = (int)cn_Alg->v.uint;

	//  Get the key size

	switch (alg) {
		case COSE_Algorithm_Direct:
#ifdef USE_Direct_HKDF_HMAC_SHA_256
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_256:
#endif

#ifdef USE_Direct_HKDF_HMAC_SHA_512
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_512:
#endif
#ifdef USE_Direct_HKDF_AES_128
		case COSE_Algorithm_Direct_HKDF_AES_128:
#endif
#ifdef USE_Direct_HKDF_AES_256
		case COSE_Algorithm_Direct_HKDF_AES_256:
#endif
#ifdef USE_ECDH_ES_HKDF_256
		case COSE_Algorithm_ECDH_ES_HKDF_256:
#endif
#ifdef USE_ECDH_ES_HKDF_512
		case COSE_Algorithm_ECDH_ES_HKDF_512:
#endif
#ifdef USE_ECDH_SS_HKDF_256
		case COSE_Algorithm_ECDH_SS_HKDF_256:
#endif
#ifdef USE_ECDH_SS_HKDF_512
		case COSE_Algorithm_ECDH_SS_HKDF_512:
#endif
			//  This is a NOOP
			cbitKey = 0;
			CHECK_CONDITION(pRecipient->m_encrypt.m_recipientFirst == NULL,
				COSE_ERR_INVALID_PARAMETER);
			break;

#ifdef USE_AES_KW_128
		case COSE_Algorithm_AES_KW_128:
			cbitKey = 128;
			break;
#endif

#ifdef USE_ECDH_ES_A128KW
		case COSE_Algorithm_ECDH_ES_A128KW:
			cbitKey = 128;
			break;
#endif

#ifdef USE_ECDH_SS_A128KW
		case COSE_Algorithm_ECDH_SS_A128KW:
			cbitKey = 128;
			break;
#endif

#ifdef USE_AES_KW_192
		case COSE_Algorithm_AES_KW_192:
			cbitKey = 192;
			break;
#endif

#ifdef USE_ECDH_ES_A192KW
		case COSE_Algorithm_ECDH_ES_A192KW:
			cbitKey = 192;
			break;
#endif

#ifdef USE_ECDH_SS_A192KW
		case COSE_Algorithm_ECDH_SS_A192KW:
			cbitKey = 192;
			break;
#endif

#ifdef USE_AES_KW_256
		case COSE_Algorithm_AES_KW_256:
			cbitKey = 256;
			break;
#endif

#ifdef USE_ECDH_ES_A256KW
		case COSE_Algorithm_ECDH_ES_A256KW:
			cbitKey = 256;
			break;
#endif

#ifdef USE_ECDH_SS_A256KW
		case COSE_Algorithm_ECDH_SS_A256KW:
			cbitKey = 256;
			break;
#endif

		default:
			FAIL_CONDITION(COSE_ERR_UNKNOWN_ALGORITHM);
	}

	//  If we are doing direct encryption - then recipient generates the key

	if (pRecipient->m_encrypt.m_recipientFirst != NULL) {
		t = 0;
		for (pri = pRecipient->m_encrypt.m_recipientFirst; pri != NULL;
			 pri = pri->m_recipientNext) {
			if (pri->m_encrypt.m_message.m_flags & 1) {
				t |= 1;
				pbKey =
					_COSE_RecipientInfo_generateKey(pri, alg, cbitKey, perr);
				if (pbKey == NULL) {
					goto errorReturn;
				}
				cbKey = cbitKey / 8;
			}
			else {
				t |= 2;
			}
		}
		CHECK_CONDITION(t != 3, COSE_ERR_INVALID_PARAMETER);

		// Do we need to generate a random key at this point -
		//   This is only true if we both haven't done it and and we have a
		//   recipient to encrypt it.

		if (t == 2) {
			pbKey = (byte *)COSE_CALLOC(cbitKey / 8, 1, context);
			CHECK_CONDITION(pbKey != NULL, COSE_ERR_OUT_OF_MEMORY);
			cbKey = cbitKey / 8;
			rand_bytes(pbKey, cbKey);
		}
	}

	//  Build protected headers

	const cn_cbor *cbProtected =
		_COSE_encode_protected(&pRecipient->m_encrypt.m_message, perr);
	if (cbProtected == NULL) {
		goto errorReturn;
	}

	//  Build authenticated data
	size_t cbAuthData = 0;
	if (!_COSE_Encrypt_Build_AAD(&pRecipient->m_encrypt.m_message, &pbAuthData,
			&cbAuthData, "Recipient", perr)) {
		goto errorReturn;
	}

	switch (alg) {
		case COSE_Algorithm_Direct:
#ifdef USE_Direct_HKDF_HMAC_SHA_256
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_256:
#endif

#ifdef USE_Direct_HKDF_HMAC_SHA_512
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_512:
#endif
#ifdef USE_Direct_HKDF_AES_128
		case COSE_Algorithm_Direct_HKDF_AES_128:
#endif
#ifdef USE_Direct_HKDF_AES_256
		case COSE_Algorithm_Direct_HKDF_AES_256:
#endif
#ifdef USE_ECDH_ES_HKDF_256
		case COSE_Algorithm_ECDH_ES_HKDF_256:
#endif
#ifdef USE_ECDH_ES_HKDF_512
		case COSE_Algorithm_ECDH_ES_HKDF_512:
#endif
#ifdef USE_ECDH_SS_HKDF_256
		case COSE_Algorithm_ECDH_SS_HKDF_256:
#endif
#ifdef USE_ECDH_SS_HKDF_512
		case COSE_Algorithm_ECDH_SS_HKDF_512:
#endif
			ptmp = cn_cbor_data_create(
				NULL, 0, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
			CHECK_CONDITION_CBOR(ptmp != NULL, cbor_error);
			CHECK_CONDITION_CBOR(
				_COSE_array_replace(&pRecipient->m_encrypt.m_message, ptmp,
					INDEX_BODY, CBOR_CONTEXT_PARAM_COMMA & cbor_error),
				cbor_error);
			ptmp = NULL;
			break;

#ifdef USE_AES_KW_128
		case COSE_Algorithm_AES_KW_128:
			if (pRecipient->m_pkey != NULL) {
				cn_cbor *pK = cn_cbor_mapget_int(pRecipient->m_pkey, -1);
				CHECK_CONDITION(pK != NULL, COSE_ERR_INVALID_PARAMETER);
				if (!AES_KW_Encrypt(pRecipient, pK->v.bytes,
						(int)pK->length * 8, pbContent, (int)cbContent, perr)) {
					goto errorReturn;
				}
			}
			else {
				if (!AES_KW_Encrypt(pRecipient, pbKey, (int)cbKey * 8,
						pbContent, (int)cbContent, perr)) {
					goto errorReturn;
				}
			}
			break;
#endif

#ifdef USE_AES_KW_192
		case COSE_Algorithm_AES_KW_192:
			if (pRecipient->m_pkey != NULL) {
				cn_cbor *pK = cn_cbor_mapget_int(pRecipient->m_pkey, -1);
				CHECK_CONDITION(pK != NULL, COSE_ERR_INVALID_PARAMETER);
				if (!AES_KW_Encrypt(pRecipient, pK->v.bytes,
						(int)pK->length * 8, pbContent, (int)cbContent, perr)) {
					goto errorReturn;
				}
			}
			else {
				if (!AES_KW_Encrypt(pRecipient, pbKey, (int)cbKey * 8,
						pbContent, (int)cbContent, perr)) {
					goto errorReturn;
				}
			}
			break;
#endif

#ifdef USE_AES_KW_256
		case COSE_Algorithm_AES_KW_256:
			if (pRecipient->m_pkey != NULL) {
				cn_cbor *pK = cn_cbor_mapget_int(pRecipient->m_pkey, -1);
				CHECK_CONDITION(pK != NULL, COSE_ERR_INVALID_PARAMETER);
				if (!AES_KW_Encrypt(pRecipient, pK->v.bytes,
						(int)pK->length * 8, pbContent, (int)cbContent, perr)) {
					goto errorReturn;
				}
			}
			else {
				if (!AES_KW_Encrypt(pRecipient, pbKey, (int)cbKey * 8,
						pbContent, (int)cbContent, perr)) {
					goto errorReturn;
				}
			}
			break;
#endif

#ifdef USE_ECDH_ES_A128KW
		case COSE_Algorithm_ECDH_ES_A128KW:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, false,
					true, COSE_Algorithm_AES_KW_128, NULL, pRecipient->m_pkey,
					rgbKey, 128, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			if (!AES_KW_Encrypt(
					pRecipient, rgbKey, 128, pbContent, (int)cbContent, perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_ES_A192KW
		case COSE_Algorithm_ECDH_ES_A192KW:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, false,
					true, COSE_Algorithm_AES_KW_192, NULL, pRecipient->m_pkey,
					rgbKey, 192, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			if (!AES_KW_Encrypt(
					pRecipient, rgbKey, 192, pbContent, (int)cbContent, perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_ES_A256KW
		case COSE_Algorithm_ECDH_ES_A256KW:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, false,
					true, COSE_Algorithm_AES_KW_256, NULL, pRecipient->m_pkey,
					rgbKey, 256, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			if (!AES_KW_Encrypt(
					pRecipient, rgbKey, 256, pbContent, (int)cbContent, perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_SS_A128KW
		case COSE_Algorithm_ECDH_SS_A128KW:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, true,
					true, COSE_Algorithm_AES_KW_128, pRecipient->m_pkeyStatic,
					pRecipient->m_pkey, rgbKey, 128, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			if (!AES_KW_Encrypt(
					pRecipient, rgbKey, 128, pbContent, (int)cbContent, perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_SS_A192KW
		case COSE_Algorithm_ECDH_SS_A192KW:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, true,
					true, COSE_Algorithm_AES_KW_192, pRecipient->m_pkeyStatic,
					pRecipient->m_pkey, rgbKey, 192, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			if (!AES_KW_Encrypt(
					pRecipient, rgbKey, 192, pbContent, (int)cbContent, perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_SS_A256KW
		case COSE_Algorithm_ECDH_SS_A256KW:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, true,
					true, COSE_Algorithm_AES_KW_256, pRecipient->m_pkeyStatic,
					pRecipient->m_pkey, rgbKey, 256, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			if (!AES_KW_Encrypt(
					pRecipient, rgbKey, 256, pbContent, (int)cbContent, perr)) {
				goto errorReturn;
			}
			break;
#endif

		default:
			FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER);
	}

	for (pri = pRecipient->m_encrypt.m_recipientFirst; pri != NULL;
		 pri = pri->m_recipientNext) {
		if (!_COSE_Recipient_encrypt(pri, pbKey, cbKey, perr)) {
			goto errorReturn;
		}
	}

	//  Figure out the clean up

	fRet = true;

errorReturn:
	memset(rgbKey, 0, sizeof(rgbKey));
	if (pbKey != NULL) {
		memset(pbKey, 0, cbKey);
		COSE_FREE(pbKey, context);
	}
	if (pbSecret != NULL) {
		COSE_FREE(pbSecret, context);
	}
	if (pbContext != NULL) {
		COSE_FREE(pbContext, context);
	}
	if (pbAuthData != NULL) {
		COSE_FREE(pbAuthData, context);
	}
	if (ptmp != NULL) {
		cn_cbor_free(ptmp CBOR_CONTEXT_PARAM);
	}
	return fRet;
}

byte *_COSE_RecipientInfo_generateKey(COSE_RecipientInfo *pRecipient,
	int algIn,
	size_t cbitKeySize,
	cose_errback *perr)
{
	int alg;
	const cn_cbor *cn_Alg = _COSE_map_get_int(&pRecipient->m_encrypt.m_message,
		COSE_Header_Algorithm, COSE_BOTH, perr);
	byte *pbContext = NULL;
	byte *pb = NULL;
#ifdef USE_CBOR_CONTEXT
	cn_cbor_context *context = &pRecipient->m_encrypt.m_message.m_allocContext;
#endif
	const cn_cbor *pK;
	byte *pbSecret = NULL;

	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;

	_COSE_encode_protected(&pRecipient->m_encrypt.m_message, perr);

	pb = COSE_CALLOC(cbitKeySize / 8, 1, context);
	CHECK_CONDITION(pb != NULL, COSE_ERR_OUT_OF_MEMORY);

	switch (alg) {
		case COSE_Algorithm_Direct:
			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((size_t)pK->length == cbitKeySize / 8,
				COSE_ERR_INVALID_PARAMETER);
			memcpy(pb, pK->v.bytes, cbitKeySize / 8);
			break;

#ifdef USE_Direct_HKDF_HMAC_SHA_256
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_256:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, false, false,
					true, algIn, pRecipient->m_pkey, NULL, pb, cbitKeySize, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_Direct_HKDF_HMAC_SHA_512
		case COSE_Algorithm_Direct_HKDF_HMAC_SHA_512:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, false, false,
					true, algIn, pRecipient->m_pkey, NULL, pb, cbitKeySize, 512,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_Direct_HKDF_AES_128
		case COSE_Algorithm_Direct_HKDF_AES_128:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, false, false, false,
					true, algIn, pRecipient->m_pkey, NULL, pb, cbitKeySize, 128,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_Direct_HKDF_AES_256
		case COSE_Algorithm_Direct_HKDF_AES_256:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, false, false, false,
					true, algIn, pRecipient->m_pkey, NULL, pb, cbitKeySize, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_ES_HKDF_256
		case COSE_Algorithm_ECDH_ES_HKDF_256:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, false,
					true, algIn, NULL, pRecipient->m_pkey, pb, cbitKeySize, 256,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_ES_HKDF_512
		case COSE_Algorithm_ECDH_ES_HKDF_512:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, false,
					true, algIn, NULL, pRecipient->m_pkey, pb, cbitKeySize, 512,
					CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_SS_HKDF_256
		case COSE_Algorithm_ECDH_SS_HKDF_256:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, true,
					true, algIn, pRecipient->m_pkeyStatic, pRecipient->m_pkey,
					pb, cbitKeySize, 256, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

#ifdef USE_ECDH_SS_HKDF_512
		case COSE_Algorithm_ECDH_SS_HKDF_512:
			if (!HKDF_X(&pRecipient->m_encrypt.m_message, true, true, true,
					true, algIn, pRecipient->m_pkeyStatic, pRecipient->m_pkey,
					pb, cbitKeySize, 512, CBOR_CONTEXT_PARAM_COMMA perr)) {
				goto errorReturn;
			}
			break;
#endif

		default:
			FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER);
	}

	if (pbSecret != NULL) {
		COSE_FREE(pbSecret, context);
	}
	if (pbContext != NULL) {
		COSE_FREE(pbContext, context);
	}
	return pb;

errorReturn:

	if (pbSecret != NULL) {
		COSE_FREE(pbSecret, context);
	}
	if (pbContext != NULL) {
		COSE_FREE(pbContext, context);
	}
	if (pb != NULL) {
		COSE_FREE(pb, context);
	}
	return NULL;
}
#endif

#if INCLUDE_ENCRYPT || INCLUDE_MAC
bool COSE_Recipient_SetKey_secret(HCOSE_RECIPIENT hRecipient,
	const byte *rgbKey,
	int cbKey,
	const byte *rgbKid,
	int cbKid,
	cose_errback *perr)
{
	COSE_RecipientInfo *p;
	cn_cbor *cn_Temp = NULL;
	cn_cbor *cnTemp = NULL;
	cn_cbor_errback cbor_error;
	byte *pbTemp = NULL;
	byte *pbKey = NULL;
#ifdef USE_CBOR_CONTEXT
	cn_cbor_context *context = NULL;
#endif

	CHECK_CONDITION(
		IsValidRecipientHandle(hRecipient), COSE_ERR_INVALID_HANDLE);
	CHECK_CONDITION(rgbKey != NULL, COSE_ERR_INVALID_PARAMETER);

	p = (COSE_RecipientInfo *)hRecipient;

#ifdef USE_CBOR_CONTEXT
	context = &p->m_encrypt.m_message.m_allocContext;
#endif

	cn_cbor *cnAlg = _COSE_map_get_int(
		&p->m_encrypt.m_message, COSE_Header_Algorithm, COSE_BOTH, perr);
	if (cnAlg != NULL) {
		CHECK_CONDITION(cnAlg->type == CN_CBOR_INT &&
							cnAlg->v.sint == COSE_Algorithm_Direct,
			COSE_ERR_INVALID_PARAMETER);
	}
	else {
		cn_Temp = cn_cbor_int_create(
			COSE_Algorithm_Direct, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
		CHECK_CONDITION_CBOR(cn_Temp != NULL, cbor_error);
		if (!COSE_Recipient_map_put_int(hRecipient, COSE_Header_Algorithm,
				cn_Temp, COSE_UNPROTECT_ONLY, perr)) {
			goto errorReturn;
		}
		cn_Temp = NULL;
	}

	if (cbKid > 0) {
		pbTemp = (byte *)COSE_CALLOC(cbKid, 1, context);
		CHECK_CONDITION(pbTemp != NULL, COSE_ERR_OUT_OF_MEMORY);

		memcpy(pbTemp, rgbKid, cbKid);
		cnTemp = cn_cbor_data_create(
			pbTemp, cbKid, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
		CHECK_CONDITION_CBOR(cnTemp != NULL, cbor_error);
		pbTemp = NULL;

		if (!COSE_Recipient_map_put_int(hRecipient, COSE_Header_KID, cnTemp,
				COSE_UNPROTECT_ONLY, perr)) {
			goto errorReturn;
		}
	}

	pbKey = (byte *)COSE_CALLOC(cbKey, 1, context);
	CHECK_CONDITION(pbKey != NULL, COSE_ERR_OUT_OF_MEMORY);

	memcpy(pbKey, rgbKey, cbKey);

	cn_Temp = cn_cbor_map_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cn_Temp != NULL, cbor_error);

	cnTemp = cn_cbor_int_create(4, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cnTemp != NULL, cbor_error);
	CHECK_CONDITION_CBOR(cn_cbor_mapput_int(cn_Temp, COSE_Key_Type, cnTemp,
							 CBOR_CONTEXT_PARAM_COMMA & cbor_error),
		cbor_error);
	cnTemp = NULL;

	cnTemp = cn_cbor_data_create(
		pbKey, cbKey, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cnTemp != NULL, cbor_error);
	pbKey = NULL;
	CHECK_CONDITION_CBOR(cn_cbor_mapput_int(cn_Temp, -1, cnTemp,
							 CBOR_CONTEXT_PARAM_COMMA & cbor_error),
		cbor_error);
	cnTemp = NULL;

	if (!COSE_Recipient_SetKey(hRecipient, cn_Temp, perr)) {
		goto errorReturn;
	}
	cn_Temp = NULL;

	return true;

errorReturn:
	if (cn_Temp != NULL) {
		CN_CBOR_FREE(cn_Temp, context);
	}
	if (cnTemp != NULL) {
		CN_CBOR_FREE(cnTemp, context);
	}
	if (pbTemp != NULL) {
		COSE_FREE(pbTemp, context);
	}
	if (pbKey != NULL) {
		COSE_FREE(pbKey, context);
	}
	return false;
}

bool COSE_Recipient_SetKey(HCOSE_RECIPIENT h,
	const cn_cbor *pKey,
	cose_errback *perr)
{
	COSE_RecipientInfo *p;

	CHECK_CONDITION(IsValidRecipientHandle(h), COSE_ERR_INVALID_HANDLE);
	CHECK_CONDITION(pKey != NULL, COSE_ERR_INVALID_PARAMETER);

	p = (COSE_RecipientInfo *)h;
	p->m_pkey = pKey;

	return true;

errorReturn:
	return false;
}

/*!
 * @brief Set the senders static key for ECDH key agreement algorithms
 *
 * Set the Static private key to be used in computing ECDH key agreement
 * operation.
 *
 * Private portion of the key is not zeroed when the recipient object is
 * released.
 *
 * @param h  Handle to the recipient object
 * @param pKey pointer to COSE key structure contiaing the private key
 * @param destination 0 - set nothing, 1 - set spk_kid, 2 - set spk
 * @param perr location for return of error code
 * @return true on success
 */

bool COSE_Recipient_SetSenderKey(HCOSE_RECIPIENT h,
	const cn_cbor *pKey,
	int destination,
	cose_errback *perr)
{
	COSE_RecipientInfo *p;
	bool f = false;
	cn_cbor *cn;
	cn_cbor *cn2 = NULL;
	cn_cbor *cn3 = NULL;
	cn_cbor_errback cbor_err;
#ifdef USE_CBOR_CONTEXT
	cn_cbor_context *context = NULL;
#endif

	CHECK_CONDITION(IsValidRecipientHandle(h), COSE_ERR_INVALID_HANDLE);
	CHECK_CONDITION(pKey != NULL, COSE_ERR_INVALID_PARAMETER);

	p = (COSE_RecipientInfo *)h;

#ifdef USE_CBOR_CONTEXT
	context = &p->m_encrypt.m_message.m_allocContext;
#endif

	switch (destination) {
		case 0:
			break;

		case 1:
			cn = cn_cbor_mapget_int(pKey, COSE_Key_ID);
			CHECK_CONDITION(cn != NULL, COSE_ERR_INVALID_PARAMETER);
			cn2 = cn_cbor_clone(cn, CBOR_CONTEXT_PARAM_COMMA & cbor_err);
			CHECK_CONDITION_CBOR(cn2 != NULL, cbor_err);
			CHECK_CONDITION(
				_COSE_map_put(&p->m_encrypt.m_message, COSE_Header_ECDH_SPK_KID,
					cn2, COSE_UNPROTECT_ONLY, perr),
				perr->err);
			cn2 = NULL;
			break;

		case 2:
			cn2 = cn_cbor_map_create(CBOR_CONTEXT_PARAM_COMMA & cbor_err);
			CHECK_CONDITION_CBOR(cn2 != NULL, cbor_err);
			cn = cn_cbor_mapget_int(pKey, COSE_Key_Type);
			CHECK_CONDITION(cn != NULL, COSE_ERR_INVALID_PARAMETER);
			cn3 = cn_cbor_clone(cn, CBOR_CONTEXT_PARAM_COMMA & cbor_err);
			CHECK_CONDITION_CBOR(cn3 != NULL, cbor_err);
			CHECK_CONDITION_CBOR(cn_cbor_mapput_int(cn2, COSE_Key_Type, cn3,
									 CBOR_CONTEXT_PARAM_COMMA & cbor_err),
				cbor_err);
			cn3 = NULL;
			cn = cn_cbor_mapget_int(pKey, COSE_Key_EC2_Curve);
			cn3 = cn_cbor_clone(cn, CBOR_CONTEXT_PARAM_COMMA & cbor_err);
			CHECK_CONDITION_CBOR(cn3 != NULL, cbor_err);
			CHECK_CONDITION_CBOR(cn_cbor_mapput_int(cn2, COSE_Key_EC2_Curve,
									 cn3, CBOR_CONTEXT_PARAM_COMMA & cbor_err),
				cbor_err);
			cn3 = NULL;
			cn = cn_cbor_mapget_int(pKey, COSE_Key_EC2_X);
			cn3 = cn_cbor_clone(cn, CBOR_CONTEXT_PARAM_COMMA & cbor_err);
			CHECK_CONDITION_CBOR(cn3 != NULL, cbor_err);
			CHECK_CONDITION_CBOR(cn_cbor_mapput_int(cn2, COSE_Key_EC2_X, cn3,
									 CBOR_CONTEXT_PARAM_COMMA & cbor_err),
				cbor_err);
			cn3 = NULL;
			cn = cn_cbor_mapget_int(pKey, COSE_Key_EC2_Y);
			cn3 = cn_cbor_clone(cn, CBOR_CONTEXT_PARAM_COMMA & cbor_err);
			CHECK_CONDITION_CBOR(cn3 != NULL, cbor_err);
			CHECK_CONDITION_CBOR(cn_cbor_mapput_int(cn2, COSE_Key_EC2_Y, cn3,
									 CBOR_CONTEXT_PARAM_COMMA & cbor_err),
				cbor_err);
			cn3 = NULL;
			CHECK_CONDITION(
				_COSE_map_put(&p->m_encrypt.m_message, COSE_Header_ECDH_SPK,
					cn2, COSE_UNPROTECT_ONLY, perr),
				perr->err);
			cn2 = NULL;
			break;

		default:
			FAIL_CONDITION(COSE_ERR_INVALID_PARAMETER);
	}

	p->m_pkeyStatic = pKey;

	f = true;
errorReturn:
	if (cn2 != NULL) {
		CN_CBOR_FREE(cn2, context);
	}
	if (cn3 != NULL) {
		CN_CBOR_FREE(cn3, context);
	}
	return f;
}

/*!
 * @brief Set the application external data for authentication
 *
 * Recipient data objects support the authentication of external application
 * supplied data.  This function is provided to supply that data to the library.
 *
 * The external data is not copied, nor will be it freed when the handle is
 * released.
 *
 * @param hcose  Handle for the COSE recipient data object
 * @param pbEternalData  point to the external data
 * @param cbExternalData size of the external data
 * @param perr  location to return errors
 * @return result of the operation.
 */

bool COSE_Recipient_SetExternal(HCOSE_RECIPIENT hcose,
	const byte *pbExternalData,
	size_t cbExternalData,
	cose_errback *perr)
{
	if (!IsValidRecipientHandle(hcose)) {
		if (perr != NULL) {
			perr->err = COSE_ERR_INVALID_HANDLE;
		}
		return false;
	}

	return _COSE_SetExternal(
		&((COSE_RecipientInfo *)hcose)->m_encrypt.m_message, pbExternalData,
		cbExternalData, perr);
}

bool COSE_Recipient_map_put_int(HCOSE_RECIPIENT h,
	int key,
	cn_cbor *value,
	int flags,
	cose_errback *perr)
{
	CHECK_CONDITION(IsValidRecipientHandle(h), COSE_ERR_INVALID_HANDLE);
	CHECK_CONDITION(value != NULL, COSE_ERR_INVALID_PARAMETER);

	if (!_COSE_map_put(&((COSE_RecipientInfo *)h)->m_encrypt.m_message, key,
			value, flags, perr)) {
		return false;
	}

	if (key == COSE_Header_Algorithm) {
		if (value->type == CN_CBOR_INT) {
			switch (value->v.uint) {
				case COSE_Algorithm_Direct:
#ifdef USE_Direct_HKDF_AES_128
				case COSE_Algorithm_Direct_HKDF_AES_128:
#endif
#ifdef USE_Direct_HKDF_AES_256
				case COSE_Algorithm_Direct_HKDF_AES_256:
#endif
#ifdef USE_Direct_HKDF_HMAC_SHA_256
				case COSE_Algorithm_Direct_HKDF_HMAC_SHA_256:
#endif
#ifdef USE_Direct_HKDF_HMAC_SHA_512
				case COSE_Algorithm_Direct_HKDF_HMAC_SHA_512:
#endif
#ifdef USE_ECDH_ES_HKDF_256
				case COSE_Algorithm_ECDH_ES_HKDF_256:
#endif
#ifdef USE_ECDH_ES_HKDF_512
				case COSE_Algorithm_ECDH_ES_HKDF_512:
#endif
#ifdef USE_ECDH_SS_HKDF_256
				case COSE_Algorithm_ECDH_SS_HKDF_256:
#endif
#ifdef USE_ECDH_SS_HKDF_512
				case COSE_Algorithm_ECDH_SS_HKDF_512:
#endif
					((COSE_RecipientInfo *)h)->m_encrypt.m_message.m_flags |= 1;
					break;

				default:
					((COSE_RecipientInfo *)h)->m_encrypt.m_message.m_flags &=
						~1;
					break;
			}
		}
		else {
			((COSE_RecipientInfo *)h)->m_encrypt.m_message.m_flags &= ~1;
		}
	}

	return true;

errorReturn:
	return false;
}
#endif

#if INCLUDE_ENCRYPT || INCLUDE_ENCRYPT0 || INCLUDE_MAC || INCLUDE_MAC0
static bool BuildContextBytes(COSE *pcose,
	int algID,
	size_t cbitKey,
	byte **ppbContext,
	size_t *pcbContext,
	CBOR_CONTEXT_COMMA cose_errback *perr)
{
	cn_cbor *pArray;
	cn_cbor_errback cbor_error;
	bool fReturn = false;
	cn_cbor *cnT = NULL;
	cn_cbor *cnArrayT = NULL;
	cn_cbor *cnParam;
	byte *pbContext = NULL;

	pArray = cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(pArray != NULL, cbor_error);

	cnT = cn_cbor_int_create(algID, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(pArray, cnT, &cbor_error), cbor_error);
	cnT = NULL;

	cnArrayT = cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cnArrayT != NULL, cbor_error);

	cnParam = _COSE_map_get_int(pcose, COSE_Header_KDF_U_name, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	else {
		cnT = cn_cbor_null_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
	cnT = NULL;
	cnParam = NULL;

	cnParam =
		_COSE_map_get_int(pcose, COSE_Header_KDF_U_nonce, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	else {
		cnT = cn_cbor_null_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
	cnT = NULL;
	cnParam = NULL;

	cnParam =
		_COSE_map_get_int(pcose, COSE_Header_KDF_U_other, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	else {
		cnT = cn_cbor_null_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
	cnT = NULL;
	cnParam = NULL;

	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(pArray, cnArrayT, &cbor_error), cbor_error);
	cnArrayT = NULL;

	cnArrayT = cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cnArrayT != NULL, cbor_error);

	cnParam = _COSE_map_get_int(pcose, COSE_Header_KDF_V_name, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	else {
		cnT = cn_cbor_null_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
	cnT = NULL;
	cnParam = NULL;

	cnParam =
		_COSE_map_get_int(pcose, COSE_Header_KDF_V_nonce, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	else {
		cnT = cn_cbor_null_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
	cnT = NULL;
	cnParam = NULL;

	cnParam =
		_COSE_map_get_int(pcose, COSE_Header_KDF_V_other, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	else {
		cnT = cn_cbor_null_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	}
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
	cnT = NULL;
	cnParam = NULL;

	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(pArray, cnArrayT, &cbor_error), cbor_error);
	cnArrayT = NULL;

	cnArrayT = cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cnArrayT != NULL, cbor_error);

	cnT = cn_cbor_int_create(cbitKey, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
	CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
	cnT = NULL;

	cnParam = _COSE_arrayget_int(pcose, INDEX_PROTECTED);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
		CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
		CHECK_CONDITION_CBOR(
			cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
		cnT = NULL;
		cnParam = NULL;
	}

	cnParam =
		_COSE_map_get_int(pcose, COSE_Header_KDF_PUB_other, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
		CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
		CHECK_CONDITION_CBOR(
			cn_cbor_array_append(cnArrayT, cnT, &cbor_error), cbor_error);
		cnT = NULL;
		cnParam = NULL;
	}

	CHECK_CONDITION_CBOR(
		cn_cbor_array_append(pArray, cnArrayT, &cbor_error), cbor_error);
	cnArrayT = NULL;

	cnParam = _COSE_map_get_int(pcose, COSE_Header_KDF_PRIV, COSE_BOTH, perr);
	if (cnParam != NULL) {
		cnT = cn_cbor_clone(cnParam, CBOR_CONTEXT_PARAM_COMMA & cbor_error);
		CHECK_CONDITION_CBOR(cnT != NULL, cbor_error);
		CHECK_CONDITION_CBOR(
			cn_cbor_array_append(pArray, cnT, &cbor_error), cbor_error);
		cnT = NULL;
		cnParam = NULL;
	}

	size_t cbContext = cn_cbor_encode_size(pArray);
	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) ==
						(ssize_t)cbContext,
		COSE_ERR_CBOR);

	*ppbContext = pbContext;
	*pcbContext = cbContext;
	pbContext = NULL;
	fReturn = true;

returnHere:
	if (pbContext != NULL) {
		COSE_FREE(pbContext, context);
	}
	if (pArray != NULL) {
		CN_CBOR_FREE(pArray, context);
	}
	if (cnArrayT != NULL) {
		CN_CBOR_FREE(cnArrayT, context);
	}
	if (cnT != NULL) {
		CN_CBOR_FREE(cnT, context);
	}
	return fReturn;

errorReturn:
	fReturn = false;
	goto returnHere;
}
#endif

#if INCLUDE_ENCRYPT || INCLUDE_MAC
/*! brief Retrieve header parameter from a recipient structure
 *
 * Retrieve a header parameter from the message.
 * Retrieved object is the same as the one in the message - do not delete it
 *
 * @param[in]	h	Handle of recipient object
 * @param[in]    key	Key to look for
 * @param[in]	flags	What buckets should we look for the message
 * @param[out]	perror	Location to return error codes
 * @return	Object which is found or NULL
 */

cn_cbor *COSE_Recipient_map_get_int(HCOSE_RECIPIENT h,
	int key,
	int flags,
	cose_errback *perror)
{
	if (!IsValidRecipientHandle(h)) {
		if (perror != NULL) {
			perror->err = COSE_ERR_INVALID_HANDLE;
		}
		return NULL;
	}

	return _COSE_map_get_int(
		&((COSE_RecipientInfo *)h)->m_encrypt.m_message, key, flags, perror);
}

HCOSE_RECIPIENT COSE_Recipient_GetRecipient(HCOSE_RECIPIENT cose,
	int iRecipient,
	cose_errback *perr)
{
	int i;
	COSE_RecipientInfo *p = NULL;

	CHECK_CONDITION(IsValidRecipientHandle(cose), COSE_ERR_INVALID_HANDLE);
	CHECK_CONDITION(iRecipient >= 0, COSE_ERR_INVALID_PARAMETER);

	p = ((COSE_RecipientInfo *)cose)->m_encrypt.m_recipientFirst;
	for (i = 0; i < iRecipient; i++) {
		CHECK_CONDITION(p != NULL, COSE_ERR_INVALID_PARAMETER);
		p = p->m_recipientNext;
	}
	if (p != NULL) {
		p->m_encrypt.m_message.m_refCount++;
	}

errorReturn:
	return (HCOSE_RECIPIENT)p;
}

bool COSE_Recipient_AddRecipient(HCOSE_RECIPIENT hEnc,
	HCOSE_RECIPIENT hRecip,
	cose_errback *perr)
{
	COSE_RecipientInfo *pRecip;
	COSE_Enveloped *pEncrypt;
	cn_cbor *pRecipients = NULL;
#ifdef USE_CBOR_CONTEXT
	cn_cbor_context *context;
#endif
	cn_cbor_errback cbor_error;

	CHECK_CONDITION(IsValidRecipientHandle(hEnc), COSE_ERR_INVALID_HANDLE);
	CHECK_CONDITION(IsValidRecipientHandle(hRecip), COSE_ERR_INVALID_HANDLE);

	pEncrypt = &((COSE_RecipientInfo *)hEnc)->m_encrypt;
	pRecip = (COSE_RecipientInfo *)hRecip;

#ifdef USE_CBOR_CONTEXT
	context = &pEncrypt->m_message.m_allocContext;
#endif	// USE_CBOR_CONTEXT

	pRecip->m_recipientNext = pEncrypt->m_recipientFirst;
	pEncrypt->m_recipientFirst = pRecip;

	pRecipients = _COSE_arrayget_int(&pEncrypt->m_message, INDEX_RECIPIENTS);
	if (pRecipients == NULL) {
		pRecipients =
			cn_cbor_array_create(CBOR_CONTEXT_PARAM_COMMA & cbor_error);
		CHECK_CONDITION_CBOR(pRecipients != NULL, cbor_error);

		if (!_COSE_array_replace(&pEncrypt->m_message, pRecipients,
				INDEX_RECIPIENTS, CBOR_CONTEXT_PARAM_COMMA & cbor_error)) {
			CN_CBOR_FREE(pRecipients, context);
			if (perr != NULL) {
				perr->err = _MapFromCBOR(cbor_error);
			}
			goto errorReturn;
		}
	}

	CHECK_CONDITION_CBOR(cn_cbor_array_append(pRecipients,
							 pRecip->m_encrypt.m_message.m_cbor, &cbor_error),
		cbor_error);

	pRecip->m_encrypt.m_message.m_refCount++;

	return true;

errorReturn:
	return false;
}

#endif
