RFC 2315

PKCS #7: Cryptographic Message Syntax Version 1.5

๐Ÿ“… published March 1998, from ietf

PKCS #7: Cryptographic Message Syntax Version 1.5 ๐Ÿ’Œ

Okay bestie, here's the title block tea โ˜•:

  • Series: Network Working Group
  • RFC number: 2315
  • Author: B. Kaliski, RSA Laboratories, East
  • Category: Informational (not a standard, just info, fr ๐Ÿซถ)
  • Date: March 1998
  • Obsoletes / Updates: The title block doesn't list anything it obsoletes or updates ๐Ÿฆ‹

Status of This Memo โœจ

This memo provides information for the Internet community. It does not specify an Internet standard of any kind. Distribution of this memo is unlimited.

Copyright (C) The Internet Society (1998). All Rights Reserved.

Overview ๐ŸŒธ

Okay so this doc describes a general syntax for data that might have cryptography applied to it, like digital signatures and digital envelopes ๐Ÿ’…. The syntax is recursive, which is iconic, because one envelope can be nested inside another, or one party can sign data that was already enveloped. It also lets you authenticate arbitrary attributes (like signing time) along with the message content, and attributes like countersignatures can be attached to a signature ๐Ÿ”ฅ. There's also a degenerate case of the syntax that's used for passing around certificates and certificate-revocation lists ๐Ÿงš.

1. Scope ๐ŸŒˆ

This document is compatible with Privacy-Enhanced Mail (PEM) ๐Ÿ’œ. Signed-data and signed-and-enveloped-data content that's built in a PEM-compatible mode can be converted into PEM messages without doing any cryptographic operations, and PEM messages can be converted the other way into the signed-data and signed-and-enveloped-data content types, no extra crypto needed โœจ.

This document can support a bunch of different architectures for certificate-based key management, like the one proposed for Privacy-Enhanced Mail in RFC 1422 ๐Ÿ“. The big architectural decisions are left outside this document, things like which certificate issuers count as "top-level," what entities issuers are allowed to certify, which distinguished names are acceptable, and what policies issuers have to follow (for example, only signing with secure hardware, or requiring entities to show specific forms of ID) ๐Ÿ™ˆ.

The values this document produces are meant to be BER-encoded, which means they'd typically be represented as octet strings. Lots of systems can transmit arbitrary octet strings reliably, but it's well known that lots of electronic-mail systems can't ๐Ÿ˜ญ. This document doesn't cover how to encode octet strings as, say, strings of ASCII characters, or any other way of re-encoding the octet string for reliable transmission. RFC 1421 suggests one possible solution to this problem ๐Ÿฆ‹.

2. References ๐Ÿ“š

  • FIPS PUB 46-1: National Bureau of Standards. FIPS PUB 46-1: Data Encryption Standard. January 1988.
  • PKCS #1: RSA Laboratories. PKCS #1: RSA Encryption. Version 1.5, November 1993.
  • PKCS #6: RSA Laboratories. PKCS #6: Extended-Certificate Syntax. Version 1.5, November 1993.
  • PKCS #9: RSA Laboratories. PKCS #9: Selected Attribute Types. Version 1.1, November 1993.
  • RFC 1421: Linn, J., "Privacy Enhancement for Internet Electronic Mail: Part I: Message Encryption and Authentication Procedures," RFC 1421 February 1993.
  • RFC 1422: Kent, S., "Privacy Enhancement for Internet Electronic Mail: Part II: Certificate-Based Key Management," RFC 1422, February 1993.
  • RFC 1423: Balenson, D., "Privacy Enhancement for Internet Electronic Mail: Part III: Algorithms, Modes, and Identifiers," RFC 1423, February 1993.
  • RFC 1424: Kaliski, B., "Privacy Enhancement for Internet Electronic Mail: Part IV: Key Certification and Related Services," RFC 1424, February 1993.
  • RFC 1319: Kaliski, B., "The MD2 Message-Digest Algorithm," RFC 1319, April 1992.
  • RFC 1321: Rivest, R., "The MD5 Message-Digest Algorithm," RFC 1321, April 1992.
  • X.208: CCITT. Recommendation X.208: Specification of Abstract Syntax Notation One (ASN.1). 1988.
  • X.209: CCITT. Recommendation X.209: Specification of Basic Encoding Rules for Abstract Syntax Notation One (ASN.1). 1988.
  • X.500: CCITT. Recommendation X.500: The Directory--Overview of Concepts, Models and Services. 1988.
  • X.501: CCITT. Recommendation X.501: The Directory--Models. 1988.
  • X.509: CCITT. Recommendation X.509: The Directory--Authentication Framework. 1988.
  • [NIST91]: NIST. Special Publication 500-202: Stable Implementation Agreements for Open Systems Interconnection Protocols. Version 5, Edition 1, Part 12. December 1991.
  • [RSA78]: R.L. Rivest, A. Shamir, and L. Adleman. A method for obtaining digital signatures and public-key cryptosystems. Communications of the ACM, 21(2):120-126, February 1978.

3. Definitions ๐ŸŽ€

For the purposes of this document, the following definitions apply. Let's go, bestie ๐Ÿ’–:

  • AlgorithmIdentifier: A type that identifies an algorithm (by object identifier) and its associated parameters. This type is defined in X.509.
  • ASN.1: Abstract Syntax Notation One, as defined in X.208.
  • Attribute: A type that contains an attribute type (specified by object identifier) and one or more attribute values. This type is defined in X.501.
  • BER: Basic Encoding Rules, as defined in X.209.
  • Certificate: A type that binds an entity's distinguished name to a public key with a digital signature. This type is defined in X.509. It also contains the distinguished name of the certificate issuer (the signer), an issuer-specific serial number, the issuer's signature algorithm identifier, and a validity period ๐Ÿ”ฅ.
  • CertificateSerialNumber: A type that uniquely identifies a certificate (and therefore an entity and a public key) among those signed by a particular certificate issuer. This type is defined in X.509.
  • CertificateRevocationList: A type that contains information about certificates whose validity an issuer has prematurely revoked. The information consists of an issuer name, the time of issue, the next scheduled time of issue, and a list of certificate serial numbers and their associated revocation times. The CRL is signed by the issuer. The type intended by this document is the one defined RFC 1422 ๐Ÿ‘‘.
  • DER: Distinguished Encoding Rules for ASN.1, as defined in X.509, Section 8.7.
  • DES: Data Encryption Standard, as defined in FIPS PUB 46-1.
  • desCBC: The object identifier for DES in cipher-block chaining (CBC) mode, as defined in [NIST91].
  • ExtendedCertificate: A type that consists of an X.509 public-key certificate and a set of attributes, collectively signed by the issuer of the X.509 public-key certificate. This type is defined in PKCS #6.
  • MD2: RSA Data Security, Inc.'s MD2 message-digest algorithm, as defined in RFC 1319.
  • md2: The object identifier for MD2, as defined in RFC 1319.
  • MD5: RSA Data Security, Inc.'s MD5 message-digest algorithm, as defined in RFC 1321.
  • md5: The object identifier for MD5, as defined in RFC 1321.
  • Name: A type that uniquely identifies or "distinguishes" objects in an X.500 directory. This type is defined in X.501. In an X.509 certificate, the type identifies the certificate issuer and the entity whose public key is certified ๐Ÿงš.
  • PEM: Internet Privacy-Enhanced Mail, as defined in RFCs 1421-1424.
  • RSA: The RSA public-key cryptosystem, as defined in [RSA78].
  • rsaEncryption: The object identifier for RSA encryption, as defined in PKCS #1.

4. Symbols and abbreviations ๐Ÿ“

No symbols or abbreviations are defined in this document. Easy ๐Ÿ™Œ.

5. General overview ๐ŸŒธ

The following nine sections specify useful types, general syntax, six content types, and object identifiers ๐Ÿ’….

The syntax is general enough to support lots of different content types. This document defines six of them: data, signed data, enveloped data, signed-and-enveloped data, digested data, and encrypted data. Other content types may be added in the future. Using content types defined outside this document is possible, but it's subject to bilateral agreement between the parties exchanging content ๐Ÿฆ‹.

This document exports one type, ContentInfo, plus the various object identifiers โœจ.

There are two classes of content types: base and enhanced. Content types in the base class contain "just data," with no cryptographic enhancements. Right now, the only content type in this class is the data content type ๐Ÿ™ˆ. Content types in the enhanced class contain content of some type (possibly encrypted), plus other cryptographic enhancements. For example, enveloped-data content can contain (encrypted) signed-data content, which can contain data content. The four non-data content types all fall into the enhanced class. Since the enhanced content types use encapsulation, you get the terms "outer" content (the one containing the enhancements) and "inner" content (the one being enhanced) ๐Ÿซถ.

The document is designed so that the enhanced content types can be prepared in a single pass using indefinite-length BER encoding, and processed in a single pass with any BER encoding. Single-pass operation is especially helpful if content is stored on tapes, or is "piped" from another process ๐ŸŽ€. The drawback of single-pass operation is that it's hard to output a DER encoding in a single pass, since the lengths of the various components may not be known in advance ๐Ÿ˜ญ. DER encoding is required for the signed-data, signed-and-enveloped data, and digested-data content types, so an extra pass may be necessary when a content type other than data is the inner content of one of those content types ๐Ÿ’€.

6. Useful types ๐Ÿ’œ

This section defines types that are useful in at least two places in the document. Main character types only ๐Ÿ‘‘.

6.1 CertificateRevocationLists ๐Ÿ”ฅ

The CertificateRevocationLists type gives a set of certificate-revocation lists. The set is intended to contain enough information to determine whether the certificates it's associated with are "hot listed," but there may be more certificate-revocation lists than necessary, or fewer than necessary ๐Ÿ™ˆ.

CertificateRevocationLists ::=
  SET OF CertificateRevocationList

6.2 ContentEncryptionAlgorithmIdentifier ๐ŸŒˆ

The ContentEncryptionAlgorithmIdentifier type identifies a content-encryption algorithm, such as DES. A content-encryption algorithm supports encryption and decryption operations. The encryption operation maps an octet string (the message) to another octet string (the ciphertext) under control of a content-encryption key. The decryption operation is the inverse of the encryption operation. Context determines which operation is intended โœจ.

ContentEncryptionAlgorithmIdentifier ::=
  AlgorithmIdentifier

6.3 DigestAlgorithmIdentifier ๐Ÿงš

The DigestAlgorithmIdentifier type identifies a message-digest algorithm. Examples include MD2 and MD5. A message-digest algorithm maps an octet string (the message) to another octet string (the message digest) ๐Ÿ“.

DigestAlgorithmIdentifier ::= AlgorithmIdentifier

6.4 DigestEncryptionAlgorithmIdentifier ๐Ÿ”

okay so the DigestEncryptionAlgorithmIdentifier type tells you which digest-encryption algorithm was used to encrypt a message digest. PKCS #1's rsaEncryption is one example ๐Ÿ’…. A digest-encryption algorithm does two jobs: encryption and decryption. Encryption takes an octet string (the message digest) and turns it into another octet string (the encrypted message digest) using a digest-encryption key ๐Ÿ”‘. Decryption is just the reverse, undoing what encryption did. Context tells you which one is meant ๐Ÿซถ

DigestEncryptionAlgorithmIdentifier ::=
  AlgorithmIdentifier

6.5 ExtendedCertificateOrCertificate ๐ŸŽ€

this type gives you either a PKCS #6 extended certificate or an X.509 certificate. It follows the syntax recommended in Section 6 of PKCS #6, so it's giving standards-approved energy โœจ

ExtendedCertificateOrCertificate ::= CHOICE {
  certificate Certificate, -- X.509

  extendedCertificate [0] IMPLICIT ExtendedCertificate }

6.6 ExtendedCertificatesAndCertificates ๐Ÿงš

this type is a set of extended certificates and X.509 certificates. The goal is for the set to be enough to hold the chains from a recognized "root" or "top-level certification authority" down to all of the signers the set is linked to. Lowkey, there might be more certificates than needed, or there might be fewer than needed ๐Ÿ™ˆ

ExtendedCertificatesAndCertificates ::=
  SET OF ExtendedCertificateOrCertificate
Note. The precise meaning of a "chain" is outside the scope of this document. Some applications of this document may impose upper limits on the length of a chain; others may enforce certain relationships between the subjects and issuers of certificates in a chain. An example of such relationships has been proposed for Privacy-Enhanced Mail in RFC 1422. ๐Ÿ“

6.7 IssuerAndSerialNumber ๐Ÿ†”

this type identifies a certificate (which means it also identifies an entity and a public key ๐Ÿ”‘) using two things: the distinguished name of the certificate issuer, and a serial number that the issuer assigned to that certificate ๐Ÿ’œ

IssuerAndSerialNumber ::= SEQUENCE {
  issuer Name,
  serialNumber CertificateSerialNumber }

6.8 KeyEncryptionAlgorithmIdentifier ๐Ÿ—๏ธ

this type identifies a key-encryption algorithm, which is the thing a content-encryption key gets locked up with ๐Ÿ”’. PKCS #1's rsaEncryption is one example. A key-encryption algorithm also does encryption and decryption. Encryption takes an octet string (the key) and turns it into another octet string (the encrypted key) using a key-encryption key. Decryption is the inverse. Context decides which operation is meant ๐ŸŒธ

KeyEncryptionAlgorithmIdentifier ::=
  AlgorithmIdentifier

6.9 Version ๐Ÿ”ข

the Version type is a syntax version number. It's there so the document can stay compatible with future revisions ๐Ÿฆ‹

Version ::= INTEGER

7. General syntax ๐Ÿ“ฆ

the general syntax for content swapped between entities under this document pairs a content type with the content itself. The syntax shall have the ASN.1 type ContentInfo:

ContentInfo ::= SEQUENCE {
  contentType ContentType,
  content
    [0] EXPLICIT ANY DEFINED BY contentType OPTIONAL }

ContentType ::= OBJECT IDENTIFIER

here's what the fields of ContentInfo mean ๐Ÿ‘€

  • contentType says what kind of content it is. It's an object identifier, which is a unique string of integers handed out by whoever defines that content type. This document defines six content types (see Section 14): data, signedData, envelopedData, signedAndEnvelopedData, digestedData, and encryptedData. ๐Ÿ’–
  • content is the content itself. The field is optional. If it's missing, its intended value must be supplied by other means. Its type is defined together with the object identifier for contentType. โœจ

Notes ๐Ÿ—’๏ธ

  1. The methods below assume that contentType can uniquely determine the type of content, so the type defined with the object identifier should not be a CHOICE type. ๐Ÿ™…โ€โ™€๏ธ
  2. When a ContentInfo value is the inner content of signed-data, signed-and-enveloped-data, or digested-data content, a message-digest algorithm is applied to the contents octets of the DER encoding of the content field. When a ContentInfo value is the inner content of enveloped-data or signed-and-enveloped-data content, a content-encryption algorithm is applied to the contents octets of a definite-length BER encoding of the content field. ๐Ÿ”ฅ
  3. Leaving out the content field is what makes "external signatures" possible, for example, without changing or copying the content the signatures apply to ๐Ÿงš. With external signatures, the content being signed would be left out of the "inner" encapsulated ContentInfo value that's included in the signed-data content type.

8. Data content type ๐Ÿ“

the data content type is just an octet string. It shall have the ASN.1 type Data:

Data ::= OCTET STRING

the data content type is meant for arbitrary octet strings, like ASCII text files. What they mean is up to the application ๐Ÿคทโ€โ™€๏ธ. These strings don't have to have any internal structure, though they can. They could even be DER encodings ๐ŸŒˆ

9. Signed-data content type โœ๏ธ

the signed-data content type holds content of any type, plus encrypted message digests of that content for zero or more signers. The encrypted digest for a signer is a "digital signature" on the content for that signer ๐Ÿ’…. Any type of content can be signed by any number of signers in parallel ๐Ÿ‘‘. There's also a degenerate case with no signers on the content at all, which is a way to pass around certificates and certificate-revocation lists ๐Ÿซถ

it's expected that the typical use of signed-data will be to represent one signer's digital signature on content of the data content type. Another typical use is passing around certificates and certificate-revocation lists ๐Ÿ’œ

here's how signed data gets built, step by step ๐Ÿช„

  1. For each signer, a message digest is computed on the content with a signer-specific message-digest algorithm. (If two signers use the same message-digest algorithm, the message digest only needs to be computed once for them both ๐Ÿ™Œ.) If the signer is authenticating anything other than the content (see Section 9.2), the message digest of the content and the other information are digested with the signer's message digest algorithm, and the result becomes the "message digest."
  2. For each signer, the message digest and associated information are encrypted with the signer's private key ๐Ÿ”.
  3. For each signer, the encrypted message digest and other signer-specific information are collected into a SignerInfo value, defined in Section 9.2. Certificates and certificate-revocation lists for each signer, and those not corresponding to any signer, are collected in this step ๐Ÿ“œ.
  4. The message-digest algorithms for all the signers and the SignerInfo values for all the signers are gathered together with the content into a SignedData value, defined in Section 9.1 ๐ŸŽ€.

a recipient verifies the signatures by decrypting the encrypted message digest for each signer with that signer's public key, then comparing the recovered message digest to an independently computed message digest โœจ. The signer's public key is either inside a certificate included in the signer information, or it's referenced by an issuer distinguished name and an issuer-specific serial number that uniquely identify the certificate for the public key ๐Ÿ”.

This section is divided into five parts. The first part describes the top-level type SignedData, the second part describes the per-signer information type SignerInfo, and the third and fourth parts describe the message-digesting and digest-encryption processes. The fifth part summarizes compatibility with Privacy-Enhanced Mail. ๐Ÿงš

9.1. SignedData type โœจ

okay bestie, this is where the signed-data content type gets its ASN.1 type ๐ŸŽ€ the type SignedData SHALL look like this:

SignedData ::= SEQUENCE {
  version Version,
  digestAlgorithms DigestAlgorithmIdentifiers,
  contentInfo ContentInfo,
  certificates
     [0] IMPLICIT ExtendedCertificatesAndCertificates
       OPTIONAL,
  crls
    [1] IMPLICIT CertificateRevocationLists OPTIONAL,
  signerInfos SignerInfos }

DigestAlgorithmIdentifiers ::=

  SET OF DigestAlgorithmIdentifier

SignerInfos ::= SET OF SignerInfo

the fields of SignedData mean the following things ๐Ÿ’…

  • version is the syntax version number. It SHALL be 1 for this version of the document. ๐Ÿฆ‹
  • digestAlgorithms is a collection of message-digest algorithm identifiers. It MAY have any number of elements, including zero. Each element identifies the message-digest algorithm (and any associated parameters) under which the content is digested for some signer. The collection is intended to list the message-digest algorithms used by all of the signers, in any order, so you can do one-pass signature verification โœจ The message-digesting process is described in Section 9.3.
  • contentInfo is the content that gets signed. It can have any of the defined content types. ๐Ÿ“
  • certificates is a set of PKCS #6 extended certificates and X.509 certificates. The set is intended to be enough to hold chains from a recognized "root" or "top-level certification authority" to all of the signers in the signerInfos field. It MAY have more certificates than necessary, and it MAY have certificates enough to hold chains from two or more independent top-level certification authorities. It MAY also have fewer certificates than necessary, if the people verifying the signatures are expected to have another way to get the certificates they need (for example, from a previous set of certificates) ๐Ÿซถ
  • crls is a set of certificate-revocation lists. The set is intended to hold enough info to tell whether or not the certificates in the certificates field are "hot listed," but that matching is not necessary. It MAY have more certificate-revocation lists than necessary, and it MAY also have fewer than necessary. ๐ŸŒธ
  • signerInfos is a collection of per-signer information. It MAY have any number of elements, including zero. ๐Ÿ‘‘

Notes.

  1. The fact that digestAlgorithms comes before contentInfo, and signerInfos comes after it, is what makes it possible to process a SignedData value in a single pass. (Single-pass processing is described in Section 5.) It's giving efficiency ๐Ÿงš
  2. The differences between version 1 SignedData and version 0 SignedData (defined in PKCS #7, Version 1.4) are these:
    • digestAlgorithms and signerInfos MAY contain zero elements in version 1, but not in version 0
    • the crls field is allowed in version 1, but not in version 0

Except for the version number, version 0 SignedData values are acceptable as version 1 values. So an implementation can process SignedData values of either version as though they were version 1 values. It is suggested that PKCS implementations generate only version 1 SignedData values, but be prepared to process SignedData values of either version. ๐ŸŽ€

  1. If there are no signers on the content at all, the ContentInfo value being "signed" doesn't really matter. In that case it is RECOMMENDED that the content type of the ContentInfo value being "signed" be data, and that the content field of that ContentInfo value be omitted. ๐Ÿ™ˆ

9.2. SignerInfo type

per-signer info is represented in the type SignerInfo ๐Ÿ’–

SignerInfo ::= SEQUENCE {
  version Version,
  issuerAndSerialNumber IssuerAndSerialNumber,
  digestAlgorithm DigestAlgorithmIdentifier,
  authenticatedAttributes
    [0] IMPLICIT Attributes OPTIONAL,
  digestEncryptionAlgorithm
    DigestEncryptionAlgorithmIdentifier,
  encryptedDigest EncryptedDigest,
  unauthenticatedAttributes
    [1] IMPLICIT Attributes OPTIONAL }

EncryptedDigest ::= OCTET STRING

the fields of SignerInfo mean the following ๐Ÿ‘‘

  • version is the syntax version number. It SHALL be 1 for this version of the document.
  • issuerAndSerialNumber specifies the signer's certificate (and therefore the signer's distinguished name and public key) by issuer distinguished name and issuer-specific serial number. ๐Ÿ”ฅ
  • digestAlgorithm identifies the message-digest algorithm (and any associated parameters) under which the content and the authenticated attributes (if present) are digested. It SHOULD be among those in the digestAlgorithms field of the superior SignedData... wait, of the superior SignerInfo value ๐Ÿ™ˆ The message-digesting process is described in Section 9.3.
  • authenticatedAttributes is a set of attributes that are signed (aka authenticated) by the signer. The field is optional, but it MUST be present if the content type of the ContentInfo value being signed is not data. If the field is present, it MUST contain, at a minimum, two attributes:
    1. A PKCS #9 content-type attribute, whose value is the content type of the ContentInfo value being signed.
    2. A PKCS #9 message-digest attribute, whose value is the message digest of the content (see below).

other attribute types that might be useful here, like signing time, are also defined in PKCS #9 โฐ

  • digestEncryptionAlgorithm identifies the digest-encryption algorithm (and any associated parameters) that the message digest and associated information get encrypted with, using the signer's private key. The digest-encryption process is described in Section 9.4. ๐Ÿ”
  • encryptedDigest is the result of encrypting the message digest and associated information with the signer's private key. ๐Ÿฆ‹
  • unauthenticatedAttributes is a set of attributes that are not signed (aka authenticated) by the signer. The field is optional. Attribute types that might be useful here, like countersignatures, are defined in PKCS #9. ๐ŸŒˆ

Notes.

  1. It is RECOMMENDED, for the sake of PEM compatibility, that the authenticatedAttributes field be omitted whenever the content type of the ContentInfo value being signed is data and there are no other authenticated attributes. โœจ
  2. The difference between version 1 SignerInfo and version 0 SignerInfo (defined in PKCS #7, Version 1.4) is in the message-digest encryption process (see Section 9.4). Only the PEM-compatible processes are different, reflecting changes in Privacy-Enhanced Mail signature methods. The non-PEM-compatible message-digest encryption process has no difference at all.

It is suggested that PKCS implementations generate only version 1 SignedData values. Since the PEM signature method that version 0 is compatible with is obsolescent, it is suggested that PKCS implementations be prepared to receive only version 1 SignedData values. ๐Ÿฅบ


9.3. Message-digesting process

okay so the message-digesting process computes a message digest on either the content being signed, or on the content together with the signer's authenticated attributes ๐Ÿง  in both cases, the starting input is the "value" of the content being signed. To be specific, it's the contents octets of the DER encoding of the content field of the ContentInfo value the signing process is applied to. Only the contents octets of the DER encoding of that field get digested, not the identifier octets or the length octets ๐Ÿ’œ

the result of the message-digesting process (informally called the "message digest") depends on whether the authenticatedAttributes field is present. When the field is absent, the result is just the message digest of the content. When the field is present, the result is the message digest of the complete DER encoding of the Attributes value contained in the authenticatedAttributes field. (For clarity: the IMPLICIT [0] tag in the authenticatedAttributes field is not part of the Attributes value. The Attributes value's tag is SET OF, and it's the DER encoding of the SET OF tag, not the IMPLICIT [0] tag, that gets digested along with the length and contents octets of the Attributes value.) Since the Attributes value MUST contain the content type and the message digest of the content as attributes when the field is present, those values are indirectly included in the result ๐ŸŽ€

when the content being signed has content type data and the authenticatedAttributes field is absent, only the value of the data (like the contents of a file) gets digested. This has the advantage that the length of the content being signed doesn't need to be known in advance of the encryption process ๐ŸŒธ This method is compatible with Privacy-Enhanced Mail.

even though the identifier octets and the length octets aren't digested, they're still protected by other means ๐Ÿ›ก๏ธ The length octets are protected by the nature of the message-digest algorithm, since it is assumed to be computationally infeasible to find any two distinct messages of any length that have the same message digest. Also, assuming the content type uniquely determines the identifier octets, the identifier octets are protected implicitly in one of two ways: either by including the content type in the authenticated attributes, or by using the PEM-compatible alternative in Section 9.4, which implies that the content type is data. ๐Ÿ”’

Note: the fact that the message digest is computed on part of a DER encoding does NOT mean that DER is the REQUIRED method of representing that part for data transfer. Honestly, it is expected that some implementations of this document MAY store objects in other than their DER encodings, but those practices don't affect message-digest computation. ๐Ÿ’…

9.4. Digest-encryption process

okay so the digest-encryption process is where the signature gets locked in ๐Ÿ”โœจ the input is the message digest (aka the "message digest," yes that's literally its name lol) plus the digest algorithm identifier or object identifier. the output is the signer's private key encrypting the BER encoding of a DigestInfo value. slay ๐Ÿ’…

DigestInfo ::= SEQUENCE {
  digestAlgorithm DigestAlgorithmIdentifier,
  digest Digest }

Digest ::= OCTET STRING

here's what the DigestInfo fields mean, bestie ๐ŸŽ€

  • digestAlgorithm tells you which message-digest algorithm (plus any associated parameters) the content and authenticated attributes were digested under. it should be the same as the digestAlgorithm field of the superior SignerInfo value.
  • digest is the result of the message-digesting process ๐Ÿซถ

Notes time ๐Ÿ“

  1. the only difference between this signature process and the signature algorithms in PKCS #1 is how the signatures get represented. PKCS #1 uses bit strings, to match the X.509 SIGNED macro. here, encrypted message digests are octet strings ๐Ÿฆ‹
  2. the input to the encryption process typically will have 30 or fewer octets. if digestEncryptionAlgorithm is PKCS #1's rsaEncryption, then the input can be encrypted in a single block as long as the RSA modulus is at least 328 bits. that's reasonable and consistent with security recommendations ๐Ÿ”ฅ
  3. a message-digest algorithm identifier gets included in the DigestInfo value so the damage is limited if one message-digest algorithm gets compromised ๐Ÿ’€ for example, say an adversary can find messages with a given MD2 message digest. that adversary could then forge a signature by finding a message with the same MD2 message digest as one a signer already signed, and presenting the old signature on the new message. this attack only works if the signer previously used MD2, since the DigestInfo value contains the message-digest algorithm. if a signer never trusted MD2 and always used MD5, then compromising MD2 wouldn't affect them at all ๐Ÿ™ˆ but if the DigestInfo value only contained the message digest, the compromise of MD2 would affect signers using any message-digest algorithm ๐Ÿ˜ญ
  4. there's potential for ambiguity here, because the DigestInfo value doesn't say whether the digest field holds just the message digest of the content, or the message digest of the complete DER encoding of the authenticatedAttributes field. so an adversary could turn a signature on authenticated attributes into one that looks like it's only on content. they'd do that by changing the content to be the DER encoding of the authenticatedAttributes field, then removing the authenticatedAttributes field. (the reverse trick is possible too, but it requires the content to be the DER encoding of an authenticated attributes value, which is pretty unlikely ๐Ÿค) this ambiguity isn't a new problem, and it isn't a significant one either, since context will generally prevent misuse ๐Ÿซถ and yes, it's also possible for an adversary to turn a signature on a certificate or certificate-revocation list into one that looks like it's only on signed-data content ๐Ÿ‘€

9.5. Compatibility with Privacy-Enhanced Mail

ok this part is giving backwards compatibility vibes ๐Ÿงš the MIC-ONLY and MIC-CLEAR process types in PEM are compatible when the content type of the ContentInfo value being signed is data, there are no authenticated attributes, the message-digest algorithm is md2 or md5, and the digest-encryption algorithm is PKCS #1's rsaEncryption. when all of those conditions are true, the encrypted message digest produced here matches the one produced in PEM, and here's why ๐ŸŒธ

  1. the value input to the message-digest algorithm in PEM is the same as it is in this document when there are no authenticated attributes. MD2 and MD5 in PEM are the same as md2 and md5 ๐Ÿ’œ
  2. the value encrypted with the signer's private key in PEM (as specified in RFC 1423) is the same as it is in this document when there are no authenticated attributes. RSA private-key encryption in PEM is the same as PKCS #1's rsaEncryption โœจ

the other parts of the signed-data content type (certificates, CRLs, algorithm identifiers, etc.) can be easily translated to and from their PEM counterparts ๐Ÿฆ‹


10. Enveloped-data content type โœจ

the enveloped-data content type is basically encrypted content of any type, plus encrypted content-encryption keys for one or more recipients ๐Ÿ” the combo of encrypted content and an encrypted content-encryption key for a recipient is a "digital envelope" for that person. any type of content can be enveloped for any number of recipients in parallel, which is so iconic ๐Ÿ‘‘

the typical use is expected to be representing one or more recipients' digital envelopes on content of the data, digested-data, or signed-data content types ๐ŸŽ€

here's how enveloped data gets constructed ๐Ÿ’–

  1. a content-encryption key for a particular content-encryption algorithm is generated at random ๐ŸŽฒ
  2. for each recipient, the content-encryption key is encrypted with the recipient's public key ๐Ÿ—๏ธ
  3. for each recipient, the encrypted content-encryption key and other recipient-specific information get collected into a RecipientInfo value, defined in Section 10.2 ๐Ÿ“ฆ
  4. the content gets encrypted with the content-encryption key. (content encryption may require that the content be padded to a multiple of some block size; see Section 10.3 for discussion.) ๐Ÿง
  5. the RecipientInfo values for all the recipients get collected together with the encrypted content into an EnvelopedData value, defined in Section 10.1 ๐Ÿซถ

to open the envelope, a recipient decrypts one of the encrypted content-encryption keys with their private key, then decrypts the encrypted content with the recovered content-encryption key ๐Ÿ”“ the recipient's private key is referenced by an issuer distinguished name and an issuer-specific serial number, which together uniquely identify the certificate for the corresponding public key ๐Ÿชช

this section is split into four parts. part one describes the top-level type EnvelopedData, part two describes the per-recipient type RecipientInfo, and parts three and four describe the content-encryption and key-encryption processes ๐Ÿงš

this content type is NOT compatible with Privacy-Enhanced Mail. (some of the processes it defines are compatible with their PEM counterparts, though) that's because PEM always involves digital signatures, never digital envelopes alone ๐Ÿ™ˆ

10.1. EnvelopedData type

the enveloped-data content type shall have the ASN.1 type EnvelopedData ๐Ÿ’…

EnvelopedData ::= SEQUENCE {
  version Version,
  recipientInfos RecipientInfos,
  encryptedContentInfo EncryptedContentInfo }

RecipientInfos ::= SET OF RecipientInfo

EncryptedContentInfo ::= SEQUENCE {
  contentType ContentType,
  contentEncryptionAlgorithm
    ContentEncryptionAlgorithmIdentifier,
  encryptedContent
    [0] IMPLICIT EncryptedContent OPTIONAL }

EncryptedContent ::= OCTET STRING

the EnvelopedData fields, bestie ๐ŸŽ€

  • version is the syntax version number. it shall be 0 for this version of the document.
  • recipientInfos is a collection of per-recipient information. there must be at least one element in the collection.
  • encryptedContentInfo is the encrypted content information ๐Ÿฆ‹

the EncryptedContentInfo fields are:

  • contentType indicates the type of content.
  • contentEncryptionAlgorithm identifies the content-encryption algorithm (and any associated parameters) the content is encrypted under. the content-encryption process is described in Section 10.3. this algorithm is the same for all recipients ๐Ÿ”
  • encryptedContent is the result of encrypting the content. the field is optional, and if it isn't present, its intended value must be supplied by other means ๐Ÿซถ

Note ๐Ÿ“ the fact that recipientInfos comes before encryptedContentInfo makes it possible to process an EnvelopedData value in a single pass. (single-pass processing is described in Section 5.) it's giving efficiency ๐Ÿ”ฅ

10.2. RecipientInfo type

per-recipient information is represented in the type RecipientInfo ๐Ÿ’–

RecipientInfo ::= SEQUENCE {
  version Version,
  issuerAndSerialNumber IssuerAndSerialNumber,
  keyEncryptionAlgorithm

    KeyEncryptionAlgorithmIdentifier,
  encryptedKey EncryptedKey }

EncryptedKey ::= OCTET STRING

the RecipientInfo fields, no cap ๐Ÿง

  • version is the syntax version number. it shall be 0 for this version of the document.
  • issuerAndSerialNumber specifies the recipient's certificate (and therefore the recipient's distinguished name and public key) by issuer distinguished name and issuer-specific serial number ๐Ÿชช
  • keyEncryptionAlgorithm identifies the key-encryption algorithm (and any associated parameters) under which the content-encryption key is encrypted with the recipient's public key. the key-encryption process is described in Section 10.4 ๐Ÿ—๏ธ
  • encryptedKey is the result of encrypting the content-encryption key with the recipient's public key (see below) โœจ

10.3 Content-encryption process ๐ŸŽ€

Okay so the content-encryption process takes the "value" of the content being enveloped as its input ๐Ÿ’– Specifically, it's the contents octets of a definite-length BER encoding of the content field of the ContentInfo value that the enveloping process gets applied to. Only those contents octets get encrypted. The identifier octets and length octets are NOT encrypted, and they aren't represented at all ๐Ÿ™ˆ

When the content being enveloped has content type data, just the value of the data (like the contents of a file) gets encrypted โœจ The big perk is that the length of the content doesn't need to be known before the encryption process starts. This method is compatible with Privacy-Enhanced Mail ๐Ÿ’…

The identifier and length octets aren't encrypted ๐Ÿ˜ญ The length octets MAY be protected implicitly by the encryption process, depending on the encryption algorithm. The identifier octets aren't protected at all, though they can be recovered from the content type, assuming the content type uniquely determines the identifier octets. If you want explicit protection of the identifier and length octets, you need the signed-and-enveloped-data content type, or the digested-data and enveloped-data content types applied one after the other ๐Ÿฆ‹

Notes.

  1. The reason a definite-length BER encoding is REQUIRED is that the bit showing whether the length is definite or indefinite isn't recorded anywhere in the enveloped-data content type. Definite-length encoding is more appropriate for simple types like octet strings, so that's the one that gets chosen ๐Ÿงš
  2. Some content-encryption algorithms assume the input length is a multiple of k octets, where k > 1, and let the application define a method for handling inputs whose lengths aren't a multiple of k octets. For these algorithms, the method SHALL be to pad the input at the trailing end with k - (l mod k) octets, all having the value k - (l mod k), where l is the length of the input. In other words, the input gets padded at the trailing end with one of the following strings:
                 01 -- if l mod k = k-1
              02 02 -- if l mod k = k-2
                            .
                            .
                            .
           k k ... k k -- if l mod k = 0

The padding can be removed unambiguously, since all input is padded and no padding string is a suffix of another. This padding method is well-defined if and only if k < 256. Methods for larger k are an open issue for further study ๐Ÿ”ฅ

10.4 Key-encryption process ๐Ÿ”‘

The input to the key-encryption process (the value supplied to the recipient's key-encryption algorithm) is just the "value" of the content-encryption key ๐Ÿ’œ


11. Signed-and-enveloped-data content type ๐Ÿฆ‹

This section defines the signed-and-enveloped-data content type. To keep things brief, a lot of this section is explained in terms of stuff from Sections 9 and 10 ๐Ÿซถ

The signed-and-enveloped-data content type is made up of encrypted content of any type, encrypted content-encryption keys for one or more recipients, and doubly encrypted message digests for one or more signers. The "double encryption" means an encryption with a signer's private key, followed by an encryption with the content-encryption key ๐Ÿ‘‘

The combo of encrypted content and an encrypted content-encryption key for a recipient is a "digital envelope" for that recipient. The recovered, singly encrypted message digest for a signer is a "digital signature" on the recovered content for that signer. Any type of content can be enveloped for any number of recipients and signed by any number of signers, all in parallel โœจ

It's expected that the typical use of the signed-and-enveloped-data content type will be one signer's digital signature plus one or more recipients' digital envelopes on content of the data content type ๐Ÿ’…

The process for building signed-and-enveloped data has these steps:

  1. A content-encryption key for a particular content-encryption algorithm is generated at random.
  2. For each recipient, the content-encryption key is encrypted with the recipient's public key.
  3. For each recipient, the encrypted content-encryption key and other recipient-specific information are collected into a RecipientInfo value, defined in Section 10.2.
  4. For each signer, a message digest is computed on the content with a signer-specific message-digest algorithm. (If two signers use the same message-digest algorithm, the message digest only needs to be computed for one of them.)
  5. For each signer, the message digest and associated information are encrypted with the signer's private key, and the result is encrypted with the content-encryption key. (The second encryption MAY require that the result of the first encryption be padded to a multiple of some block size; see Section 10.3 for discussion.)
  6. For each signer, the doubly encrypted message digest and other signer-specific information are collected into a SignerInfo value, defined in Section 9.2.
  7. The content is encrypted with the content-encryption key. (See Section 10.3 for discussion.)
  8. The message-digest algorithms for all the signers, the SignerInfo values for all the signers, and the RecipientInfo values for all the recipients are collected together with the encrypted content into a SignedAndEnvelopedData value, defined in Section 11.1.

A recipient opens the envelope and checks the signatures in two steps ๐Ÿ•ต๏ธโ€โ™€๏ธ First, one of the encrypted content-encryption keys is decrypted with the recipient's private key, and the encrypted content is decrypted with the recovered content-encryption key. Second, the doubly encrypted message digest for each signer is decrypted with the recovered content-encryption key, the result is decrypted with the signer's public key, and the recovered message digest is compared to an independently computed message digest ๐Ÿซง

Recipient private keys and signer public keys are contained or referenced the way Sections 9 and 10 describe ๐Ÿงš

This section has three parts. The first part describes the top-level type SignedAndEnvelopedData, the second part describes the digest-encryption process, and the other types and processes are the same as in Sections 9 and 10. The third part sums up compatibility with Privacy-Enhanced Mail ๐ŸŒธ

Note. The signed-and-enveloped-data content type gives you cryptographic enhancements similar to what you get from running the signed-data and enveloped-data content types one after the other. BUT the signed-and-enveloped-data content type has no authenticated or unauthenticated attributes, and it doesn't envelope signer information other than the signature. So the sequential combination of signed-data and enveloped-data content types is generally preferable to the SignedAndEnvelopedData content type, unless you need compatibility with the ENCRYPTED process type in Privacy-Enhanced Mail ๐Ÿ™ˆ

11.1 SignedAndEnvelopedData type ๐Ÿ’ซ

The signed-and-enveloped-data content type SHALL have the ASN.1 type SignedAndEnvelopedData:

   SignedAndEnvelopedData ::= SEQUENCE {
     version Version,
     recipientInfos RecipientInfos,
     digestAlgorithms DigestAlgorithmIdentifiers,
     encryptedContentInfo EncryptedContentInfo,
     certificates
        [0] IMPLICIT ExtendedCertificatesAndCertificates
          OPTIONAL,
     crls
       [1] IMPLICIT CertificateRevocationLists OPTIONAL,
     signerInfos SignerInfos }

The fields of SignedAndEnvelopedData mean the following:

  • version is the syntax version number. It SHALL be 1 for this version of the document.
  • recipientInfos is a collection of per-recipient information, as in Section 10. There MUST be at least one element in the collection.
  • digestAlgorithms is a collection of message-digest algorithm identifiers, as in Section 9. The message-digesting process is the same as in Section 9 when there are no authenticated attributes.
  • encryptedContentInfo is the encrypted content, as in Section 10. It can have any of the defined content types.
  • certificates is a set of PKCS #6 extended certificates and X.509 certificates, as in Section 9.
  • crls is a set of certificate-revocation lists, as in Section 9.
  • signerInfos is a collection of per-signer information. There MUST be at least one element in the collection. SignerInfo values have the same meaning as in Section 9, except for the encryptedDigest field (see below).

Notes.

  1. The fact that the recipientInfos and digestAlgorithms fields come before the contentInfo field, and the signerInfos field comes after it, makes it possible to process a SignedAndEnvelopedData value in a single pass. (Single-pass processing is described in Section 5.) ๐Ÿง
  2. The difference between version 1 SignedAndEnvelopedData and version 0 SignedAndEnvelopedData (defined in PKCS #7, Version 1.4) is that the crls field is allowed in version 1, but not in version 0. Apart from the version number, version 0 SignedAndEnvelopedData values are acceptable as version 1 values. An implementation can therefore process SignedAndEnvelopedData values of either version as though they were version 1 values. It is suggested that PKCS implementations generate only version 1 SignedAndEnvelopedData values, but be prepared to process SignedAndEnvelopedData values of either version. ๐ŸŒˆ

11.2 Digest-encryption process ๐Ÿง

The input to the digest-encryption process is the same as in Section 9, but the process itself is different. Specifically, the process has two steps. First, the input is supplied to the signer's digest-encryption algorithm, as in Section 9. Second, the result of the first step is encrypted with the content-encryption key. There is no DER encoding between the two steps. The "value" output by the first step goes directly into the second step (see Section 10.3 for discussion) โœจ

This process is compatible with the ENCRYPTED process type in Privacy-Enhanced Mail ๐Ÿ’–

Note. The point of the second step is to stop an adversary from recovering the message digest of the content. Otherwise, an adversary could figure out which of a list of candidate contents (e.g., "Yes" or "No") is the actual content by comparing their message digests to the actual message digest ๐Ÿ™ˆ

11.3 Compatibility with Privacy-Enhanced Mail โœจ

okay so PEM compat is lowkey the best part ๐Ÿซถ PEM has its own ENCRYPTED process type, and this stuff lines up with it perfectly, but only when ALL of these are true: the content type of the ContentInfo value being signed and enveloped is data, the message-digest algorithm is md2 or md5, the content-encryption algorithm is DES in CBC mode, the digest-encryption algorithm is PKCS #1's rsaEncryption, and the key-encryption algorithm is PKCS #1's rsaEncryption. ๐Ÿ’… When all five line up, the doubly encrypted message digest and the encrypted content-encryption key come out matching the ones PEM makes, and that's for reasons similar to the ones in Section 9.5, plus these:

  1. The value fed into the content-encryption algorithm is the same in PEM as it is here. DES in CBC mode is the same thing as desCBC. ๐ŸŽ€
  2. The value fed into the key-encryption algorithm is the same in PEM as it is here (see Section 10.4). RSA public-key encryption in PEM is the same thing as PKCS #1's rsaEncryption. ๐Ÿฆ‹
  3. The double-encryption process applied to the message digest is the same in this document and in PEM. ๐Ÿ“

The rest of the signed-and-enveloped-data stuff (certificates, CRLs, algorithm identifiers, and so on) translates to and from the matching PEM pieces pretty easily โœจ (just a heads up: CRLs get carried in a separate PEM message ๐Ÿ™ˆ).


12. Digested-data content type โœจ

okay the digested-data content type is basically content of any type plus a message digest of that content ๐ŸŒธ

And it's expected that the main way people use digested-data is to add integrity to content of the data content type, and then that result becomes the content input to the enveloped-data content type. Iconic layering ๐Ÿ‘‘

Here's how a digested-data value gets built:

  1. A message digest is computed on the content using a message-digest algorithm.
  2. The message-digest algorithm and the message digest get bundled up together with the content into a DigestedData value. ๐ŸŽ

To verify it, a recipient compares the message digest they're handed against a message digest they compute on their own. ๐Ÿง

The digested-data content type shall have ASN.1 type DigestedData:

DigestedData ::= SEQUENCE {
  version Version,
  digestAlgorithm DigestAlgorithmIdentifier,
  contentInfo ContentInfo,
  digest Digest }

Digest ::= OCTET STRING

Here's what the DigestedData fields mean:

  • version is the syntax version number. It shall be 0 for this version of the document. ๐Ÿ”ข
  • digestAlgorithm identifies the message-digest algorithm (and any associated parameters) that the content is digested under. (The message-digesting process is the same as in Section 9 when there are no authenticated attributes.) ๐Ÿง
  • contentInfo is the content that gets digested. It can have any of the defined content types. โœจ
  • digest is the result of the message-digesting process. ๐Ÿ’–
Note. The fact that the digestAlgorithm field comes before the contentInfo field, and the digest field comes after it, is what makes it possible to process a DigestedData value in a single pass. (Single-pass processing is described in Section 5.) ๐Ÿง ๐Ÿ’…

13. Encrypted-data content type ๐Ÿ”

the encrypted-data content type is encrypted content of any type ๐Ÿซง The big difference from enveloped-data is that encrypted-data has NO recipients and NO encrypted content-encryption keys. Keys are assumed to be managed some other way ๐Ÿ—๏ธ

It's expected that the typical use of encrypted-data is encrypting content of the data content type for local storage, maybe where the encryption key is a password ๐Ÿ™ˆ๐Ÿ”’

The encrypted-data content type shall have ASN.1 type EncryptedData:

EncryptedData ::= SEQUENCE {
  version Version,
  encryptedContentInfo EncryptedContentInfo }

The EncryptedData fields mean:

  • version is the syntax version number. It shall be 0 for this version of the document. ๐Ÿ”ข
  • encryptedContentInfo is the encrypted content information, as in Section 10. ๐ŸŽ€

14. Object identifiers ๐Ÿ†”

This document defines seven object identifiers: pkcs-7, data, signedData, envelopedData, signedAndEnvelopedData, digestedData, and encryptedData. Okay, that's a lot of IDs, but they're all iconic ๐Ÿ‘‘

The object identifier pkcs-7 identifies this document itself:

pkcs-7 OBJECT IDENTIFIER ::=
  { iso(1) member-body(2) US(840) rsadsi(113549)
      pkcs(1) 7 }

The object identifiers data, signedData, envelopedData, signedAndEnvelopedData, digestedData, and encryptedData identify, in that order, the data, signed-data, enveloped-data, signed-and-enveloped-data, digested-data, and encrypted-data content types defined in Sections 8-13. ๐Ÿ’œ

data OBJECT IDENTIFIER ::= { pkcs-7 1 }
signedData OBJECT IDENTIFIER ::= { pkcs-7 2 }
envelopedData OBJECT IDENTIFIER ::= { pkcs-7 3 }
signedAndEnvelopedData OBJECT IDENTIFIER ::=
   { pkcs-7 4 }
digestedData OBJECT IDENTIFIER ::= { pkcs-7 5 }
encryptedData OBJECT IDENTIFIER ::= { pkcs-7 6 }

These OIDs are meant to go in the contentType field of a ContentInfo value (see Section 5). The content field of that type, which has the content-type-specific syntax ANY DEFINED BY contentType, would have ASN.1 type Data, SignedData, EnvelopedData, SignedAndEnvelopedData, DigestedData, and EncryptedData, respectively. These OIDs are also meant to be used in a PKCS #9 content-type attribute. ๐Ÿงš


Security Considerations ๐Ÿšจ

okay this part is SERIOUS ๐Ÿ˜ญ Security issues are discussed throughout this memo. Like, all of it. Read the whole thing bestie ๐Ÿซถ


Revision history ๐Ÿ“œ

Versions 1.0-1.3

Versions 1.0-1.3 were passed around to participants in RSA Data Security, Inc.'s Public-Key Cryptography Standards meetings in February and March 1991. Ancient history, but iconic ๐Ÿฆ–

Version 1.4

Version 1.4 is part of the June 3, 1991 initial public release of PKCS. It was published as NIST/OSI Implementors' Workshop document SEC-SIG-91-22. ๐ŸŒˆ

Version 1.5

Version 1.5 has several editorial changes, including updates to the references and the addition of a revision history. Here are the substantive changes:

  • Section 6: CertificateRevocationLists type is added. ๐Ÿ“ƒ
  • Section 9.1: SignedData syntax is revised. The new version lets certificate-revocation lists get disseminated along with signatures. It also lets certificates and certificate-revocation lists get disseminated alone, without any signatures. ๐Ÿ”
  • Section 9.2: SignerInfo syntax is revised. The new version includes a message-digest encryption process compatible with Privacy-Enhanced Mail as specified in RFC 1423. ๐Ÿ’…
  • Section 9.3: The meaning of "the DER encoding of the authenticatedAttributes field" is clarified as "the DER encoding of the Attributes value." โœจ
  • Section 10.3: The padding method for content-encryption algorithms is described. ๐Ÿงฉ
  • Section 11.1: SignedAndEnvelopedData syntax is revised. The new version lets certificate-revocation lists get disseminated. ๐ŸŽ€
  • Section 13: Encrypted-data content type is added. This content type consists of encrypted content of any type. ๐Ÿ”
  • Section 14: encryptedData object identifier is added. ๐Ÿ†”

This supersedes the June 3, 1991 version, which was also published as NIST/OSI Implementors' Workshop document SEC-SIG-91-22. ๐Ÿ‘‘


Acknowledgements ๐Ÿซถ

This document is based on a contribution from RSA Laboratories, a division of RSA Data Security, Inc. Any substantial use of the text from this document must acknowledge RSA Data Security, Inc. RSA Data Security, Inc. requests that all material mentioning or referencing this document identify it as "RSA Data Security, Inc. PKCS #7". Credit where credit is due, periodt ๐Ÿ’–


Author's Address ๐Ÿ“ฎ

Burt Kaliski
RSA Laboratories East
20 Crosby Drive
Bedford, MA  01730

Phone: (617) 687-7000
EMail: burt@rsa.com

Copyright (C) The Internet Society (1998). All Rights Reserved.

This document and translations of it may be copied and furnished to others, and derivative works that comment on or otherwise explain it or assist in its implementation may be prepared, copied, published and distributed, in whole or in part, without restriction of any kind, provided that the above copyright notice and this paragraph are included on all such copies and derivative works. However, this document itself may not be modified in any way, such as by removing the copyright notice or references to the Internet Society or other Internet organizations, except as needed for the purpose of developing Internet standards in which case the procedures for copyrights defined in the Internet Standards process must be followed, or as required to translate it into languages other than English.

The limited permissions granted above are perpetual and will not be revoked by the Internet Society or its successors or assigns.

This document and the information contained herein is provided on an "AS IS" basis and THE INTERNET SOCIETY AND THE INTERNET ENGINEERING TASK FORCE DISCLAIMS ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTY THAT THE USE OF THE INFORMATION HEREIN WILL NOT INFRINGE ANY RIGHTS OR ANY IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. ๐ŸŒธ

๐Ÿ“ฆ where this page comes from