Commit e1f1d28f authored by Dr. Stephen Henson's avatar Dr. Stephen Henson
Browse files

Add function CMS_RecipientInfo_encrypt

Add CMS_RecipientInfo_encrypt: this function encrypts an existing content
encryption key to match the key in the RecipientInfo structure: this is
useful if a new recpient is added to and existing enveloped data structure.

Add documentation.
parent 388aff08
Loading
Loading
Loading
Loading
+2 −0
Original line number Diff line number Diff line
@@ -233,6 +233,7 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms,
					const EVP_CIPHER *kekciph);

int CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);
int CMS_RecipientInfo_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);
	
int CMS_uncompress(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
							unsigned int flags);
@@ -384,6 +385,7 @@ void ERR_load_CMS_strings(void);
#define CMS_F_CMS_RECEIPTREQUEST_CREATE0		 159
#define CMS_F_CMS_RECEIPT_VERIFY			 160
#define CMS_F_CMS_RECIPIENTINFO_DECRYPT			 134
#define CMS_F_CMS_RECIPIENTINFO_ENCRYPT			 169
#define CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT		 135
#define CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT		 136
#define CMS_F_CMS_RECIPIENTINFO_KEKRI_GET0_ID		 137
+24 −23
Original line number Diff line number Diff line
@@ -803,12 +803,34 @@ int CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
		}
	}

int CMS_RecipientInfo_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
	{
	switch (ri->type)
		{
		case CMS_RECIPINFO_TRANS:
		return cms_RecipientInfo_ktri_encrypt(cms, ri);

		case CMS_RECIPINFO_KEK:
		return cms_RecipientInfo_kekri_encrypt(cms, ri);
		break;

		case CMS_RECIPINFO_PASS:
		return cms_RecipientInfo_pwri_crypt(cms, ri, 1);
		break;

		default:
		CMSerr(CMS_F_CMS_RECIPIENTINFO_ENCRYPT,
				CMS_R_UNSUPPORTED_RECIPIENT_TYPE);
		return 0;
		}
	}

BIO *cms_EnvelopedData_init_bio(CMS_ContentInfo *cms)
	{
	CMS_EncryptedContentInfo *ec;
	STACK_OF(CMS_RecipientInfo) *rinfos;
	CMS_RecipientInfo *ri;
	int i, r, ok = 0;
	int i, ok = 0;
	BIO *ret;

	/* Get BIO first to set up key */
@@ -828,28 +850,7 @@ BIO *cms_EnvelopedData_init_bio(CMS_ContentInfo *cms)
	for (i = 0; i < sk_CMS_RecipientInfo_num(rinfos); i++)
		{
		ri = sk_CMS_RecipientInfo_value(rinfos, i);

		switch (ri->type)
			{
			case CMS_RECIPINFO_TRANS:
			r = cms_RecipientInfo_ktri_encrypt(cms, ri);
			break;

			case CMS_RECIPINFO_KEK:
			r = cms_RecipientInfo_kekri_encrypt(cms, ri);
			break;

			case CMS_RECIPINFO_PASS:
			r = cms_RecipientInfo_pwri_crypt(cms, ri, 1);
			break;

			default:
			CMSerr(CMS_F_CMS_ENVELOPEDDATA_INIT_BIO,
				CMS_R_UNSUPPORTED_RECIPIENT_TYPE);
			goto err;
			}

		if (r <= 0)
		if (CMS_RecipientInfo_encrypt(cms, ri) <= 0)
			{
			CMSerr(CMS_F_CMS_ENVELOPEDDATA_INIT_BIO,
				CMS_R_ERROR_SETTING_RECIPIENTINFO);
+2 −1
Original line number Diff line number Diff line
/* crypto/cms/cms_err.c */
/* ====================================================================
 * Copyright (c) 1999-2009 The OpenSSL Project.  All rights reserved.
 * Copyright (c) 1999-2013 The OpenSSL Project.  All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
@@ -114,6 +114,7 @@ static ERR_STRING_DATA CMS_str_functs[]=
{ERR_FUNC(CMS_F_CMS_RECEIPTREQUEST_CREATE0),	"CMS_ReceiptRequest_create0"},
{ERR_FUNC(CMS_F_CMS_RECEIPT_VERIFY),	"cms_Receipt_verify"},
{ERR_FUNC(CMS_F_CMS_RECIPIENTINFO_DECRYPT),	"CMS_RecipientInfo_decrypt"},
{ERR_FUNC(CMS_F_CMS_RECIPIENTINFO_ENCRYPT),	"CMS_RecipientInfo_encrypt"},
{ERR_FUNC(CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT),	"CMS_RECIPIENTINFO_KEKRI_DECRYPT"},
{ERR_FUNC(CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT),	"CMS_RECIPIENTINFO_KEKRI_ENCRYPT"},
{ERR_FUNC(CMS_F_CMS_RECIPIENTINFO_KEKRI_GET0_ID),	"CMS_RecipientInfo_kekri_get0_id"},
+14 −0
Original line number Diff line number Diff line
@@ -20,6 +20,7 @@
 int CMS_RecipientInfo_set0_key(CMS_RecipientInfo *ri, unsigned char *key, size_t keylen);

 int CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);
 int CMS_RecipientInfo_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);

=head1 DESCRIPTION

@@ -66,6 +67,11 @@ CMS_RecipientInfo_decrypt() attempts to decrypt CMS_RecipientInfo structure
B<ri> in structure B<cms>. A key must have been associated with the structure
first.

CMS_RecipientInfo_encrypt() attempts to encrypt CMS_RecipientInfo structure
B<ri> in structure B<cms>. A key must have been associated with the structure
first and the content encryption key must be available: for example by a
previous call to CMS_RecipientInfo_decrypt().

=head1 NOTES

The main purpose of these functions is to enable an application to lookup
@@ -81,6 +87,13 @@ any appropriate means it can then associated with the structure and
CMS_RecpientInfo_decrypt() called. If successful CMS_decrypt() can be called
with a NULL key to decrypt the enveloped content.

The CMS_RecipientInfo_encrypt() can be used to add a new recipient to an
existing enveloped data structure. Typically an application will first decrypt
an appropriate CMS_RecipientInfo structure to make the content encrypt key
available, it will then add a new recipient using a function such as
CMS_add1_recipient_cert() and finally encrypt the content encryption key
using CMS_RecipientInfo_encrypt().

=head1 RETURN VALUES

CMS_get0_RecipientInfos() returns all CMS_RecipientInfo structures, or NULL if
@@ -89,6 +102,7 @@ an error occurs.
CMS_RecipientInfo_ktri_get0_signer_id(), CMS_RecipientInfo_set0_pkey(),
CMS_RecipientInfo_kekri_get0_id(), CMS_RecipientInfo_set0_key() and
CMS_RecipientInfo_decrypt() return 1 for success or 0 if an error occurs.
CMS_RecipientInfo_encrypt() return 1 for success or 0 if an error occurs.

CMS_RecipientInfo_ktri_cert_cmp() and CMS_RecipientInfo_kekri_cmp() return 0
for a successful comparison and non zero otherwise.