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.
(cherry picked from commit e1f1d28f34)
This commit is contained in:
Dr. Stephen Henson 2013-02-26 16:48:49 +00:00
parent 3c53fd892c
commit e1dee801b9
4 changed files with 42 additions and 24 deletions

View File

@ -233,6 +233,7 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms,
const EVP_CIPHER *kekciph); const EVP_CIPHER *kekciph);
int CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri); 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, int CMS_uncompress(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
unsigned int flags); unsigned int flags);
@ -384,6 +385,7 @@ void ERR_load_CMS_strings(void);
#define CMS_F_CMS_RECEIPTREQUEST_CREATE0 159 #define CMS_F_CMS_RECEIPTREQUEST_CREATE0 159
#define CMS_F_CMS_RECEIPT_VERIFY 160 #define CMS_F_CMS_RECEIPT_VERIFY 160
#define CMS_F_CMS_RECIPIENTINFO_DECRYPT 134 #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_DECRYPT 135
#define CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT 136 #define CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT 136
#define CMS_F_CMS_RECIPIENTINFO_KEKRI_GET0_ID 137 #define CMS_F_CMS_RECIPIENTINFO_KEKRI_GET0_ID 137

View File

@ -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) BIO *cms_EnvelopedData_init_bio(CMS_ContentInfo *cms)
{ {
CMS_EncryptedContentInfo *ec; CMS_EncryptedContentInfo *ec;
STACK_OF(CMS_RecipientInfo) *rinfos; STACK_OF(CMS_RecipientInfo) *rinfos;
CMS_RecipientInfo *ri; CMS_RecipientInfo *ri;
int i, r, ok = 0; int i, ok = 0;
BIO *ret; BIO *ret;
/* Get BIO first to set up key */ /* 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++) for (i = 0; i < sk_CMS_RecipientInfo_num(rinfos); i++)
{ {
ri = sk_CMS_RecipientInfo_value(rinfos, i); ri = sk_CMS_RecipientInfo_value(rinfos, i);
if (CMS_RecipientInfo_encrypt(cms, ri) <= 0)
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)
{ {
CMSerr(CMS_F_CMS_ENVELOPEDDATA_INIT_BIO, CMSerr(CMS_F_CMS_ENVELOPEDDATA_INIT_BIO,
CMS_R_ERROR_SETTING_RECIPIENTINFO); CMS_R_ERROR_SETTING_RECIPIENTINFO);

View File

@ -1,6 +1,6 @@
/* crypto/cms/cms_err.c */ /* 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 * Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions * 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_RECEIPTREQUEST_CREATE0), "CMS_ReceiptRequest_create0"},
{ERR_FUNC(CMS_F_CMS_RECEIPT_VERIFY), "cms_Receipt_verify"}, {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_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_DECRYPT), "CMS_RECIPIENTINFO_KEKRI_DECRYPT"},
{ERR_FUNC(CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT), "CMS_RECIPIENTINFO_KEKRI_ENCRYPT"}, {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"}, {ERR_FUNC(CMS_F_CMS_RECIPIENTINFO_KEKRI_GET0_ID), "CMS_RecipientInfo_kekri_get0_id"},

View File

@ -20,6 +20,7 @@
int CMS_RecipientInfo_set0_key(CMS_RecipientInfo *ri, unsigned char *key, size_t keylen); 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_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);
int CMS_RecipientInfo_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);
=head1 DESCRIPTION =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 B<ri> in structure B<cms>. A key must have been associated with the structure
first. 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 =head1 NOTES
The main purpose of these functions is to enable an application to lookup 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 CMS_RecpientInfo_decrypt() called. If successful CMS_decrypt() can be called
with a NULL key to decrypt the enveloped content. 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 =head1 RETURN VALUES
CMS_get0_RecipientInfos() returns all CMS_RecipientInfo structures, or NULL if 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_ktri_get0_signer_id(), CMS_RecipientInfo_set0_pkey(),
CMS_RecipientInfo_kekri_get0_id(), CMS_RecipientInfo_set0_key() and 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_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 CMS_RecipientInfo_ktri_cert_cmp() and CMS_RecipientInfo_kekri_cmp() return 0
for a successful comparison and non zero otherwise. for a successful comparison and non zero otherwise.