github.com/Hyperledger-TWGC/tjfoc-gm@v1.4.0/x509/pkcs7.go (about)

     1  package x509
     2  
     3  import (
     4  	"bytes"
     5  	"crypto"
     6  	"crypto/aes"
     7  	"crypto/cipher"
     8  	"crypto/des"
     9  	"crypto/hmac"
    10  	"crypto/rand"
    11  	"crypto/rsa"
    12  	_ "crypto/sha1" // for crypto.SHA1
    13  	"crypto/x509/pkix"
    14  	"encoding/asn1"
    15  	"errors"
    16  	"fmt"
    17  	"math/big"
    18  	"sort"
    19  	"time"
    20  )
    21  
    22  // PKCS7 Represents a PKCS7 structure
    23  type PKCS7 struct {
    24  	Content      []byte
    25  	Certificates []*Certificate
    26  	CRLs         []pkix.CertificateList
    27  	Signers      []signerInfo
    28  	raw          interface{}
    29  }
    30  
    31  type contentInfo struct {
    32  	ContentType asn1.ObjectIdentifier
    33  	Content     asn1.RawValue `asn1:"explicit,optional,tag:0"`
    34  }
    35  
    36  // ErrUnsupportedContentType is returned when a PKCS7 content is not supported.
    37  // Currently only Data (1.2.156.10197.6.1.4.2.1), Signed Data (1.2.156.10197.6.1.4.2.2),
    38  // and Enveloped Data are supported (1.2.156.10197.6.1.4.2.3)
    39  var ErrUnsupportedContentType = errors.New("pkcs7: cannot parse data: unimplemented content type")
    40  
    41  type unsignedData []byte
    42  
    43  var (
    44  	oidData                   = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 7, 1}
    45  	oidSignedData             = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 7, 2}
    46  	oidSMSignedData           = asn1.ObjectIdentifier{1, 2, 156, 10197, 6, 1, 4, 2, 2}
    47  	oidEnvelopedData          = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 7, 3}
    48  	oidSignedAndEnvelopedData = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 7, 4}
    49  	oidDigestedData           = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 7, 5}
    50  	oidEncryptedData          = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 7, 6}
    51  	oidAttributeContentType   = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 9, 3}
    52  	oidAttributeMessageDigest = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 9, 4}
    53  	oidAttributeSigningTime   = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 9, 5}
    54  	oidSM3withSM2             = asn1.ObjectIdentifier{1, 2, 156, 10197, 1, 501}
    55  	oidDSASM2                 = asn1.ObjectIdentifier{1, 2, 156, 10197, 1, 301, 1}
    56  )
    57  
    58  type signedData struct {
    59  	Version                    int                        `asn1:"default:1"`
    60  	DigestAlgorithmIdentifiers []pkix.AlgorithmIdentifier `asn1:"set"`
    61  	ContentInfo                contentInfo
    62  	Certificates               rawCertificates        `asn1:"optional,tag:0"`
    63  	CRLs                       []pkix.CertificateList `asn1:"optional,tag:1"`
    64  	SignerInfos                []signerInfo           `asn1:"set"`
    65  }
    66  
    67  type rawCertificates struct {
    68  	Raw asn1.RawContent
    69  }
    70  
    71  type envelopedData struct {
    72  	Version              int
    73  	RecipientInfos       []recipientInfo `asn1:"set"`
    74  	EncryptedContentInfo encryptedContentInfo
    75  }
    76  
    77  type recipientInfo struct {
    78  	Version                int
    79  	IssuerAndSerialNumber  issuerAndSerial
    80  	KeyEncryptionAlgorithm pkix.AlgorithmIdentifier
    81  	EncryptedKey           []byte
    82  }
    83  
    84  type encryptedContentInfo struct {
    85  	ContentType                asn1.ObjectIdentifier
    86  	ContentEncryptionAlgorithm pkix.AlgorithmIdentifier
    87  	EncryptedContent           asn1.RawValue `asn1:"tag:0,optional"`
    88  }
    89  
    90  type attribute struct {
    91  	Type  asn1.ObjectIdentifier
    92  	Value asn1.RawValue `asn1:"set"`
    93  }
    94  
    95  type issuerAndSerial struct {
    96  	IssuerName   asn1.RawValue
    97  	SerialNumber *big.Int
    98  }
    99  
   100  // MessageDigestMismatchError is returned when the signer data digest does not
   101  // match the computed digest for the contained content
   102  type MessageDigestMismatchError struct {
   103  	ExpectedDigest []byte
   104  	ActualDigest   []byte
   105  }
   106  
   107  func (err *MessageDigestMismatchError) Error() string {
   108  	return fmt.Sprintf("pkcs7: Message digest mismatch\n\tExpected: %X\n\tActual  : %X", err.ExpectedDigest, err.ActualDigest)
   109  }
   110  
   111  type signerInfo struct {
   112  	Version                   int `asn1:"default:1"`
   113  	IssuerAndSerialNumber     issuerAndSerial
   114  	DigestAlgorithm           pkix.AlgorithmIdentifier
   115  	AuthenticatedAttributes   []attribute `asn1:"optional,tag:0"`
   116  	DigestEncryptionAlgorithm pkix.AlgorithmIdentifier
   117  	EncryptedDigest           []byte
   118  	UnauthenticatedAttributes []attribute `asn1:"optional,tag:1"`
   119  }
   120  
   121  // ParsePKCS7 decodes a DER encoded PKCS7.
   122  func ParsePKCS7(data []byte) (p7 *PKCS7, err error) {
   123  	if len(data) == 0 {
   124  		return nil, errors.New("pkcs7: input data is empty")
   125  	}
   126  	var info contentInfo
   127  	der, err := ber2der(data)
   128  	if err != nil {
   129  		return nil, err
   130  	}
   131  	rest, err := asn1.Unmarshal(der, &info)
   132  	if len(rest) > 0 {
   133  		err = asn1.SyntaxError{Msg: "trailing data"}
   134  		return
   135  	}
   136  
   137  	if err != nil {
   138  		return
   139  	}
   140  
   141  	// fmt.Printf("--> Content Type: %s", info.ContentType)
   142  	switch {
   143  	case info.ContentType.Equal(oidSignedData):
   144  		return parseSignedData(info.Content.Bytes)
   145  	case info.ContentType.Equal(oidSMSignedData):
   146  		return parseSignedData(info.Content.Bytes)
   147  	case info.ContentType.Equal(oidEnvelopedData):
   148  		return parseEnvelopedData(info.Content.Bytes)
   149  	}
   150  	return nil, ErrUnsupportedContentType
   151  }
   152  
   153  func parseSignedData(data []byte) (*PKCS7, error) {
   154  	var sd signedData
   155  	asn1.Unmarshal(data, &sd)
   156  	certs, err := sd.Certificates.Parse()
   157  	if err != nil {
   158  		return nil, err
   159  	}
   160  	// fmt.Printf("--> Signed Data Version %d\n", sd.Version)
   161  
   162  	var compound asn1.RawValue
   163  	var content unsignedData
   164  
   165  	// The Content.Bytes maybe empty on PKI responses.
   166  	if len(sd.ContentInfo.Content.Bytes) > 0 {
   167  		if _, err := asn1.Unmarshal(sd.ContentInfo.Content.Bytes, &compound); err != nil {
   168  			return nil, err
   169  		}
   170  	}
   171  	// Compound octet string
   172  	if compound.IsCompound {
   173  		if _, err = asn1.Unmarshal(compound.Bytes, &content); err != nil {
   174  			return nil, err
   175  		}
   176  	} else {
   177  		// assuming this is tag 04
   178  		content = compound.Bytes
   179  	}
   180  	return &PKCS7{
   181  		Content:      content,
   182  		Certificates: certs,
   183  		CRLs:         sd.CRLs,
   184  		Signers:      sd.SignerInfos,
   185  		raw:          sd}, nil
   186  }
   187  
   188  func (raw rawCertificates) Parse() ([]*Certificate, error) {
   189  	if len(raw.Raw) == 0 {
   190  		return nil, nil
   191  	}
   192  
   193  	var val asn1.RawValue
   194  	if _, err := asn1.Unmarshal(raw.Raw, &val); err != nil {
   195  		return nil, err
   196  	}
   197  
   198  	return ParseCertificates(val.Bytes)
   199  }
   200  
   201  func parseEnvelopedData(data []byte) (*PKCS7, error) {
   202  	var ed envelopedData
   203  	if _, err := asn1.Unmarshal(data, &ed); err != nil {
   204  		return nil, err
   205  	}
   206  	return &PKCS7{
   207  		raw: ed,
   208  	}, nil
   209  }
   210  
   211  // Verify checks the signatures of a PKCS7 object
   212  // WARNING: Verify does not check signing time or verify certificate chains at
   213  // this time.
   214  func (p7 *PKCS7) Verify() (err error) {
   215  	if len(p7.Signers) == 0 {
   216  		return errors.New("pkcs7: Message has no signers")
   217  	}
   218  	for _, signer := range p7.Signers {
   219  		if err := verifySignature(p7, signer); err != nil {
   220  			return err
   221  		}
   222  	}
   223  	return nil
   224  }
   225  
   226  func verifySignature(p7 *PKCS7, signer signerInfo) error {
   227  	signedData := p7.Content
   228  	hash, err := getHashForOID(signer.DigestAlgorithm.Algorithm)
   229  	if err != nil {
   230  		return err
   231  	}
   232  	// fmt.Println("===== hash algo=====:", hash)
   233  	if len(signer.AuthenticatedAttributes) > 0 {
   234  		var digest []byte
   235  		err := unmarshalAttribute(signer.AuthenticatedAttributes, oidAttributeMessageDigest, &digest)
   236  		if err != nil {
   237  			return err
   238  		}
   239  		h := hash.New()
   240  		h.Write(p7.Content)
   241  		computed := h.Sum(nil)
   242  		if !hmac.Equal(digest, computed) {
   243  			return &MessageDigestMismatchError{
   244  				ExpectedDigest: digest,
   245  				ActualDigest:   computed,
   246  			}
   247  		}
   248  		// TODO(shengzhi): Optionally verify certificate chain
   249  		// TODO(shengzhi): Optionally verify signingTime against certificate NotAfter/NotBefore
   250  		signedData, err = marshalAttributes(signer.AuthenticatedAttributes)
   251  		if err != nil {
   252  			return err
   253  		}
   254  	}
   255  	cert := getCertFromCertsByIssuerAndSerial(p7.Certificates, signer.IssuerAndSerialNumber)
   256  	if cert == nil {
   257  		return errors.New("pkcs7: No certificate for signer")
   258  	}
   259  
   260  	algo := getSignatureAlgorithmByHash(hash, signer.DigestEncryptionAlgorithm.Algorithm)
   261  	if algo == UnknownSignatureAlgorithm {
   262  		return ErrPKCS7UnsupportedAlgorithm
   263  	}
   264  	return cert.CheckSignature(algo, signedData, signer.EncryptedDigest)
   265  }
   266  
   267  func getSignatureAlgorithmByHash(hash Hash, oid asn1.ObjectIdentifier) SignatureAlgorithm {
   268  	switch hash {
   269  	case SM3:
   270  		switch {
   271  		case oid.Equal(oidSM3withSM2):
   272  			return SM2WithSM3
   273  		}
   274  	case SHA256:
   275  		switch {
   276  		case oid.Equal(oidDSASM2):
   277  			return SM2WithSHA256
   278  		}
   279  	}
   280  	return UnknownSignatureAlgorithm
   281  }
   282  
   283  func marshalAttributes(attrs []attribute) ([]byte, error) {
   284  	encodedAttributes, err := asn1.Marshal(struct {
   285  		A []attribute `asn1:"set"`
   286  	}{A: attrs})
   287  	if err != nil {
   288  		return nil, err
   289  	}
   290  
   291  	// Remove the leading sequence octets
   292  	var raw asn1.RawValue
   293  	_, err = asn1.Unmarshal(encodedAttributes, &raw)
   294  	if err != nil {
   295  		return nil, err
   296  	}
   297  	return raw.Bytes, nil
   298  }
   299  
   300  var (
   301  	oidDigestAlgorithmSHA1    = asn1.ObjectIdentifier{1, 3, 14, 3, 2, 26}
   302  	oidEncryptionAlgorithmRSA = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 1, 1}
   303  )
   304  
   305  func getCertFromCertsByIssuerAndSerial(certs []*Certificate, ias issuerAndSerial) *Certificate {
   306  	for _, cert := range certs {
   307  		if isCertMatchForIssuerAndSerial(cert, ias) {
   308  			return cert
   309  		}
   310  	}
   311  	return nil
   312  }
   313  
   314  func getHashForOID(oid asn1.ObjectIdentifier) (Hash, error) {
   315  	switch {
   316  	case oid.Equal(oidDigestAlgorithmSHA1):
   317  		return SHA1, nil
   318  	case oid.Equal(oidSHA256):
   319  		return SHA256, nil
   320  	case oid.Equal(oidSM3):
   321  	case oid.Equal(oidHashSM3):
   322  		return SM3, nil
   323  	}
   324  	return Hash(0), ErrPKCS7UnsupportedAlgorithm
   325  }
   326  
   327  // GetOnlySigner returns an x509.Certificate for the first signer of the signed
   328  // data payload. If there are more or less than one signer, nil is returned
   329  func (p7 *PKCS7) GetOnlySigner() *Certificate {
   330  	if len(p7.Signers) != 1 {
   331  		return nil
   332  	}
   333  	signer := p7.Signers[0]
   334  	return getCertFromCertsByIssuerAndSerial(p7.Certificates, signer.IssuerAndSerialNumber)
   335  }
   336  
   337  // ErrPKCS7UnsupportedAlgorithm tells you when our quick dev assumptions have failed
   338  var ErrPKCS7UnsupportedAlgorithm = errors.New("pkcs7: cannot decrypt data: only RSA, DES, DES-EDE3, AES-256-CBC and AES-128-GCM supported")
   339  
   340  // ErrNotEncryptedContent is returned when attempting to Decrypt data that is not encrypted data
   341  var ErrNotEncryptedContent = errors.New("pkcs7: content data is a decryptable data type")
   342  
   343  // Decrypt decrypts encrypted content info for recipient cert and private key
   344  func (p7 *PKCS7) Decrypt(cert *Certificate, pk crypto.PrivateKey) ([]byte, error) {
   345  	data, ok := p7.raw.(envelopedData)
   346  	if !ok {
   347  		return nil, ErrNotEncryptedContent
   348  	}
   349  	recipient := selectRecipientForCertificate(data.RecipientInfos, cert)
   350  	if recipient.EncryptedKey == nil {
   351  		return nil, errors.New("pkcs7: no enveloped recipient for provided certificate")
   352  	}
   353  	if priv := pk.(*rsa.PrivateKey); priv != nil {
   354  		var contentKey []byte
   355  		contentKey, err := rsa.DecryptPKCS1v15(rand.Reader, priv, recipient.EncryptedKey)
   356  		if err != nil {
   357  			return nil, err
   358  		}
   359  		return data.EncryptedContentInfo.decrypt(contentKey)
   360  	}
   361  	fmt.Printf("Unsupported Private Key: %v\n", pk)
   362  	// TODO: SM decript
   363  	return nil, ErrPKCS7UnsupportedAlgorithm
   364  }
   365  
   366  var oidEncryptionAlgorithmDESCBC = asn1.ObjectIdentifier{1, 3, 14, 3, 2, 7}
   367  var oidEncryptionAlgorithmDESEDE3CBC = asn1.ObjectIdentifier{1, 2, 840, 113549, 3, 7}
   368  var oidEncryptionAlgorithmAES256CBC = asn1.ObjectIdentifier{2, 16, 840, 1, 101, 3, 4, 1, 42}
   369  var oidEncryptionAlgorithmAES128GCM = asn1.ObjectIdentifier{2, 16, 840, 1, 101, 3, 4, 1, 6}
   370  var oidEncryptionAlgorithmAES128CBC = asn1.ObjectIdentifier{2, 16, 840, 1, 101, 3, 4, 1, 2}
   371  
   372  func (eci encryptedContentInfo) decrypt(key []byte) ([]byte, error) {
   373  	alg := eci.ContentEncryptionAlgorithm.Algorithm
   374  	if !alg.Equal(oidEncryptionAlgorithmDESCBC) &&
   375  		!alg.Equal(oidEncryptionAlgorithmDESEDE3CBC) &&
   376  		!alg.Equal(oidEncryptionAlgorithmAES256CBC) &&
   377  		!alg.Equal(oidEncryptionAlgorithmAES128CBC) &&
   378  		!alg.Equal(oidEncryptionAlgorithmAES128GCM) {
   379  		fmt.Printf("Unsupported Content Encryption Algorithm: %s\n", alg)
   380  		return nil, ErrPKCS7UnsupportedAlgorithm
   381  	}
   382  
   383  	// EncryptedContent can either be constructed of multple OCTET STRINGs
   384  	// or _be_ a tagged OCTET STRING
   385  	var cyphertext []byte
   386  	if eci.EncryptedContent.IsCompound {
   387  		// Complex case to concat all of the children OCTET STRINGs
   388  		var buf bytes.Buffer
   389  		cypherbytes := eci.EncryptedContent.Bytes
   390  		for {
   391  			var part []byte
   392  			cypherbytes, _ = asn1.Unmarshal(cypherbytes, &part)
   393  			buf.Write(part)
   394  			if cypherbytes == nil {
   395  				break
   396  			}
   397  		}
   398  		cyphertext = buf.Bytes()
   399  	} else {
   400  		// Simple case, the bytes _are_ the cyphertext
   401  		cyphertext = eci.EncryptedContent.Bytes
   402  	}
   403  
   404  	var block cipher.Block
   405  	var err error
   406  
   407  	switch {
   408  	case alg.Equal(oidEncryptionAlgorithmDESCBC):
   409  		block, err = des.NewCipher(key)
   410  	case alg.Equal(oidEncryptionAlgorithmDESEDE3CBC):
   411  		block, err = des.NewTripleDESCipher(key)
   412  	case alg.Equal(oidEncryptionAlgorithmAES256CBC):
   413  		fallthrough
   414  	case alg.Equal(oidEncryptionAlgorithmAES128GCM), alg.Equal(oidEncryptionAlgorithmAES128CBC):
   415  		block, err = aes.NewCipher(key)
   416  	}
   417  
   418  	if err != nil {
   419  		return nil, err
   420  	}
   421  
   422  	if alg.Equal(oidEncryptionAlgorithmAES128GCM) {
   423  		params := aesGCMParameters{}
   424  		paramBytes := eci.ContentEncryptionAlgorithm.Parameters.Bytes
   425  
   426  		_, err := asn1.Unmarshal(paramBytes, &params)
   427  		if err != nil {
   428  			return nil, err
   429  		}
   430  
   431  		gcm, err := cipher.NewGCM(block)
   432  		if err != nil {
   433  			return nil, err
   434  		}
   435  
   436  		if len(params.Nonce) != gcm.NonceSize() {
   437  			return nil, errors.New("pkcs7: encryption algorithm parameters are incorrect")
   438  		}
   439  		if params.ICVLen != gcm.Overhead() {
   440  			return nil, errors.New("pkcs7: encryption algorithm parameters are incorrect")
   441  		}
   442  
   443  		plaintext, err := gcm.Open(nil, params.Nonce, cyphertext, nil)
   444  		if err != nil {
   445  			return nil, err
   446  		}
   447  
   448  		return plaintext, nil
   449  	}
   450  
   451  	iv := eci.ContentEncryptionAlgorithm.Parameters.Bytes
   452  	if len(iv) != block.BlockSize() {
   453  		return nil, errors.New("pkcs7: encryption algorithm parameters are malformed")
   454  	}
   455  	mode := cipher.NewCBCDecrypter(block, iv)
   456  	plaintext := make([]byte, len(cyphertext))
   457  	mode.CryptBlocks(plaintext, cyphertext)
   458  	if plaintext, err = unpad(plaintext, mode.BlockSize()); err != nil {
   459  		return nil, err
   460  	}
   461  	return plaintext, nil
   462  }
   463  
   464  func selectRecipientForCertificate(recipients []recipientInfo, cert *Certificate) recipientInfo {
   465  	for _, recp := range recipients {
   466  		if isCertMatchForIssuerAndSerial(cert, recp.IssuerAndSerialNumber) {
   467  			return recp
   468  		}
   469  	}
   470  	return recipientInfo{}
   471  }
   472  
   473  func isCertMatchForIssuerAndSerial(cert *Certificate, ias issuerAndSerial) bool {
   474  	return cert.SerialNumber.Cmp(ias.SerialNumber) == 0 && bytes.Compare(cert.RawIssuer, ias.IssuerName.FullBytes) == 0
   475  }
   476  
   477  func pad(data []byte, blocklen int) ([]byte, error) {
   478  	if blocklen < 1 {
   479  		return nil, fmt.Errorf("invalid blocklen %d", blocklen)
   480  	}
   481  	padlen := blocklen - (len(data) % blocklen)
   482  	if padlen == 0 {
   483  		padlen = blocklen
   484  	}
   485  	pad := bytes.Repeat([]byte{byte(padlen)}, padlen)
   486  	return append(data, pad...), nil
   487  }
   488  
   489  func unpad(data []byte, blocklen int) ([]byte, error) {
   490  	if blocklen < 1 {
   491  		return nil, fmt.Errorf("invalid blocklen %d", blocklen)
   492  	}
   493  	if len(data)%blocklen != 0 || len(data) == 0 {
   494  		return nil, fmt.Errorf("invalid data len %d", len(data))
   495  	}
   496  
   497  	// the last byte is the length of padding
   498  	padlen := int(data[len(data)-1])
   499  
   500  	// check padding integrity, all bytes should be the same
   501  	pad := data[len(data)-padlen:]
   502  	for _, padbyte := range pad {
   503  		if padbyte != byte(padlen) {
   504  			return nil, errors.New("invalid padding")
   505  		}
   506  	}
   507  
   508  	return data[:len(data)-padlen], nil
   509  }
   510  
   511  func unmarshalAttribute(attrs []attribute, attributeType asn1.ObjectIdentifier, out interface{}) error {
   512  	for _, attr := range attrs {
   513  		if attr.Type.Equal(attributeType) {
   514  			_, err := asn1.Unmarshal(attr.Value.Bytes, out)
   515  			return err
   516  		}
   517  	}
   518  	return errors.New("pkcs7: attribute type not in attributes")
   519  }
   520  
   521  // UnmarshalSignedAttribute decodes a single attribute from the signer info
   522  func (p7 *PKCS7) UnmarshalSignedAttribute(attributeType asn1.ObjectIdentifier, out interface{}) error {
   523  	sd, ok := p7.raw.(signedData)
   524  	if !ok {
   525  		return errors.New("pkcs7: payload is not signedData content")
   526  	}
   527  	if len(sd.SignerInfos) < 1 {
   528  		return errors.New("pkcs7: payload has no signers")
   529  	}
   530  	attributes := sd.SignerInfos[0].AuthenticatedAttributes
   531  	return unmarshalAttribute(attributes, attributeType, out)
   532  }
   533  
   534  // SignedData is an opaque data structure for creating signed data payloads
   535  type SignedData struct {
   536  	sd            signedData
   537  	certs         []*Certificate
   538  	messageDigest []byte
   539  }
   540  
   541  // Attribute represents a key value pair attribute. Value must be marshalable byte
   542  // `encoding/asn1`
   543  type Attribute struct {
   544  	Type  asn1.ObjectIdentifier
   545  	Value interface{}
   546  }
   547  
   548  // SignerInfoConfig are optional values to include when adding a signer
   549  type SignerInfoConfig struct {
   550  	ExtraSignedAttributes []Attribute
   551  }
   552  
   553  // NewSignedData initializes a SignedData with content
   554  func NewSignedData(data []byte) (*SignedData, error) {
   555  	content, err := asn1.Marshal(data)
   556  	if err != nil {
   557  		return nil, err
   558  	}
   559  	ci := contentInfo{
   560  		ContentType: oidData,
   561  		Content:     asn1.RawValue{Class: 2, Tag: 0, Bytes: content, IsCompound: true},
   562  	}
   563  	digAlg := pkix.AlgorithmIdentifier{
   564  		Algorithm: oidDigestAlgorithmSHA1,
   565  	}
   566  	h := crypto.SHA1.New()
   567  	h.Write(data)
   568  	md := h.Sum(nil)
   569  	sd := signedData{
   570  		ContentInfo:                ci,
   571  		Version:                    1,
   572  		DigestAlgorithmIdentifiers: []pkix.AlgorithmIdentifier{digAlg},
   573  	}
   574  	return &SignedData{sd: sd, messageDigest: md}, nil
   575  }
   576  
   577  type attributes struct {
   578  	types  []asn1.ObjectIdentifier
   579  	values []interface{}
   580  }
   581  
   582  // Add adds the attribute, maintaining insertion order
   583  func (attrs *attributes) Add(attrType asn1.ObjectIdentifier, value interface{}) {
   584  	attrs.types = append(attrs.types, attrType)
   585  	attrs.values = append(attrs.values, value)
   586  }
   587  
   588  type sortableAttribute struct {
   589  	SortKey   []byte
   590  	Attribute attribute
   591  }
   592  
   593  type attributeSet []sortableAttribute
   594  
   595  func (sa attributeSet) Len() int {
   596  	return len(sa)
   597  }
   598  
   599  func (sa attributeSet) Less(i, j int) bool {
   600  	return bytes.Compare(sa[i].SortKey, sa[j].SortKey) < 0
   601  }
   602  
   603  func (sa attributeSet) Swap(i, j int) {
   604  	sa[i], sa[j] = sa[j], sa[i]
   605  }
   606  
   607  func (sa attributeSet) Attributes() []attribute {
   608  	attrs := make([]attribute, len(sa))
   609  	for i, attr := range sa {
   610  		attrs[i] = attr.Attribute
   611  	}
   612  	return attrs
   613  }
   614  
   615  func (attrs *attributes) ForMarshaling() ([]attribute, error) {
   616  	sortables := make(attributeSet, len(attrs.types))
   617  	for i := range sortables {
   618  		attrType := attrs.types[i]
   619  		attrValue := attrs.values[i]
   620  		asn1Value, err := asn1.Marshal(attrValue)
   621  		if err != nil {
   622  			return nil, err
   623  		}
   624  		attr := attribute{
   625  			Type:  attrType,
   626  			Value: asn1.RawValue{Tag: 17, IsCompound: true, Bytes: asn1Value}, // 17 == SET tag
   627  		}
   628  		encoded, err := asn1.Marshal(attr)
   629  		if err != nil {
   630  			return nil, err
   631  		}
   632  		sortables[i] = sortableAttribute{
   633  			SortKey:   encoded,
   634  			Attribute: attr,
   635  		}
   636  	}
   637  	sort.Sort(sortables)
   638  	return sortables.Attributes(), nil
   639  }
   640  
   641  // AddSigner signs attributes about the content and adds certificate to payload
   642  func (sd *SignedData) AddSigner(cert *Certificate, pkey crypto.PrivateKey, config SignerInfoConfig) error {
   643  	attrs := &attributes{}
   644  	attrs.Add(oidAttributeContentType, sd.sd.ContentInfo.ContentType)
   645  	attrs.Add(oidAttributeMessageDigest, sd.messageDigest)
   646  	attrs.Add(oidAttributeSigningTime, time.Now())
   647  	for _, attr := range config.ExtraSignedAttributes {
   648  		attrs.Add(attr.Type, attr.Value)
   649  	}
   650  	finalAttrs, err := attrs.ForMarshaling()
   651  	if err != nil {
   652  		return err
   653  	}
   654  	signature, err := signAttributes(finalAttrs, pkey, crypto.SHA1)
   655  	if err != nil {
   656  		return err
   657  	}
   658  
   659  	ias, err := cert2issuerAndSerial(cert)
   660  	if err != nil {
   661  		return err
   662  	}
   663  
   664  	signer := signerInfo{
   665  		AuthenticatedAttributes:   finalAttrs,
   666  		DigestAlgorithm:           pkix.AlgorithmIdentifier{Algorithm: oidDigestAlgorithmSHA1},
   667  		DigestEncryptionAlgorithm: pkix.AlgorithmIdentifier{Algorithm: oidSignatureSHA1WithRSA},
   668  		IssuerAndSerialNumber:     ias,
   669  		EncryptedDigest:           signature,
   670  		Version:                   1,
   671  	}
   672  	// create signature of signed attributes
   673  	sd.certs = append(sd.certs, cert)
   674  	sd.sd.SignerInfos = append(sd.sd.SignerInfos, signer)
   675  	return nil
   676  }
   677  
   678  // AddCertificate adds the certificate to the payload. Useful for parent certificates
   679  func (sd *SignedData) AddCertificate(cert *Certificate) {
   680  	sd.certs = append(sd.certs, cert)
   681  }
   682  
   683  // Detach removes content from the signed data struct to make it a detached signature.
   684  // This must be called right before Finish()
   685  func (sd *SignedData) Detach() {
   686  	sd.sd.ContentInfo = contentInfo{ContentType: oidData}
   687  }
   688  
   689  // Finish marshals the content and its signers
   690  func (sd *SignedData) Finish() ([]byte, error) {
   691  	sd.sd.Certificates = marshalCertificates(sd.certs)
   692  	inner, err := asn1.Marshal(sd.sd)
   693  	if err != nil {
   694  		return nil, err
   695  	}
   696  	outer := contentInfo{
   697  		ContentType: oidSignedData,
   698  		Content:     asn1.RawValue{Class: 2, Tag: 0, Bytes: inner, IsCompound: true},
   699  	}
   700  	return asn1.Marshal(outer)
   701  }
   702  
   703  func cert2issuerAndSerial(cert *Certificate) (issuerAndSerial, error) {
   704  	var ias issuerAndSerial
   705  	// The issuer RDNSequence has to match exactly the sequence in the certificate
   706  	// We cannot use cert.Issuer.ToRDNSequence() here since it mangles the sequence
   707  	ias.IssuerName = asn1.RawValue{FullBytes: cert.RawIssuer}
   708  	ias.SerialNumber = cert.SerialNumber
   709  
   710  	return ias, nil
   711  }
   712  
   713  // signs the DER encoded form of the attributes with the private key
   714  func signAttributes(attrs []attribute, pkey crypto.PrivateKey, hash crypto.Hash) ([]byte, error) {
   715  	attrBytes, err := marshalAttributes(attrs)
   716  	if err != nil {
   717  		return nil, err
   718  	}
   719  	h := hash.New()
   720  	h.Write(attrBytes)
   721  	hashed := h.Sum(nil)
   722  	switch priv := pkey.(type) {
   723  	case *rsa.PrivateKey:
   724  		return rsa.SignPKCS1v15(rand.Reader, priv, crypto.SHA1, hashed)
   725  	}
   726  	return nil, ErrPKCS7UnsupportedAlgorithm
   727  }
   728  
   729  // concats and wraps the certificates in the RawValue structure
   730  func marshalCertificates(certs []*Certificate) rawCertificates {
   731  	var buf bytes.Buffer
   732  	for _, cert := range certs {
   733  		buf.Write(cert.Raw)
   734  	}
   735  	rawCerts, _ := marshalCertificateBytes(buf.Bytes())
   736  	return rawCerts
   737  }
   738  
   739  // Even though, the tag & length are stripped out during marshalling the
   740  // RawContent, we have to encode it into the RawContent. If its missing,
   741  // then `asn1.Marshal()` will strip out the certificate wrapper instead.
   742  func marshalCertificateBytes(certs []byte) (rawCertificates, error) {
   743  	var val = asn1.RawValue{Bytes: certs, Class: 2, Tag: 0, IsCompound: true}
   744  	b, err := asn1.Marshal(val)
   745  	if err != nil {
   746  		return rawCertificates{}, err
   747  	}
   748  	return rawCertificates{Raw: b}, nil
   749  }
   750  
   751  // DegenerateCertificate creates a signed data structure containing only the
   752  // provided certificate or certificate chain.
   753  func DegenerateCertificate(cert []byte) ([]byte, error) {
   754  	rawCert, err := marshalCertificateBytes(cert)
   755  	if err != nil {
   756  		return nil, err
   757  	}
   758  	emptyContent := contentInfo{ContentType: oidData}
   759  	sd := signedData{
   760  		Version:      1,
   761  		ContentInfo:  emptyContent,
   762  		Certificates: rawCert,
   763  		CRLs:         []pkix.CertificateList{},
   764  	}
   765  	content, err := asn1.Marshal(sd)
   766  	if err != nil {
   767  		return nil, err
   768  	}
   769  	signedContent := contentInfo{
   770  		ContentType: oidSignedData,
   771  		Content:     asn1.RawValue{Class: 2, Tag: 0, Bytes: content, IsCompound: true},
   772  	}
   773  	return asn1.Marshal(signedContent)
   774  }
   775  
   776  const (
   777  	EncryptionAlgorithmDESCBC = iota
   778  	EncryptionAlgorithmAES128GCM
   779  )
   780  
   781  // ContentEncryptionAlgorithm determines the algorithm used to encrypt the
   782  // plaintext message. Change the value of this variable to change which
   783  // algorithm is used in the Encrypt() function.
   784  var ContentEncryptionAlgorithm = EncryptionAlgorithmDESCBC
   785  
   786  // ErrUnsupportedEncryptionAlgorithm is returned when attempting to encrypt
   787  // content with an unsupported algorithm.
   788  var ErrUnsupportedEncryptionAlgorithm = errors.New("pkcs7: cannot encrypt content: only DES-CBC and AES-128-GCM supported")
   789  
   790  const nonceSize = 12
   791  
   792  type aesGCMParameters struct {
   793  	Nonce  []byte `asn1:"tag:4"`
   794  	ICVLen int
   795  }
   796  
   797  func encryptAES128GCM(content []byte) ([]byte, *encryptedContentInfo, error) {
   798  	// Create AES key and nonce
   799  	key := make([]byte, 16)
   800  	nonce := make([]byte, nonceSize)
   801  
   802  	_, err := rand.Read(key)
   803  	if err != nil {
   804  		return nil, nil, err
   805  	}
   806  
   807  	_, err = rand.Read(nonce)
   808  	if err != nil {
   809  		return nil, nil, err
   810  	}
   811  
   812  	// Encrypt content
   813  	block, err := aes.NewCipher(key)
   814  	if err != nil {
   815  		return nil, nil, err
   816  	}
   817  
   818  	gcm, err := cipher.NewGCM(block)
   819  	if err != nil {
   820  		return nil, nil, err
   821  	}
   822  
   823  	ciphertext := gcm.Seal(nil, nonce, content, nil)
   824  
   825  	// Prepare ASN.1 Encrypted Content Info
   826  	paramSeq := aesGCMParameters{
   827  		Nonce:  nonce,
   828  		ICVLen: gcm.Overhead(),
   829  	}
   830  
   831  	paramBytes, err := asn1.Marshal(paramSeq)
   832  	if err != nil {
   833  		return nil, nil, err
   834  	}
   835  
   836  	eci := encryptedContentInfo{
   837  		ContentType: oidData,
   838  		ContentEncryptionAlgorithm: pkix.AlgorithmIdentifier{
   839  			Algorithm: oidEncryptionAlgorithmAES128GCM,
   840  			Parameters: asn1.RawValue{
   841  				Tag:   asn1.TagSequence,
   842  				Bytes: paramBytes,
   843  			},
   844  		},
   845  		EncryptedContent: marshalEncryptedContent(ciphertext),
   846  	}
   847  
   848  	return key, &eci, nil
   849  }
   850  
   851  func encryptDESCBC(content []byte) ([]byte, *encryptedContentInfo, error) {
   852  	// Create DES key & CBC IV
   853  	key := make([]byte, 8)
   854  	iv := make([]byte, des.BlockSize)
   855  	_, err := rand.Read(key)
   856  	if err != nil {
   857  		return nil, nil, err
   858  	}
   859  	_, err = rand.Read(iv)
   860  	if err != nil {
   861  		return nil, nil, err
   862  	}
   863  
   864  	// Encrypt padded content
   865  	block, err := des.NewCipher(key)
   866  	if err != nil {
   867  		return nil, nil, err
   868  	}
   869  	mode := cipher.NewCBCEncrypter(block, iv)
   870  	plaintext, err := pad(content, mode.BlockSize())
   871  	cyphertext := make([]byte, len(plaintext))
   872  	mode.CryptBlocks(cyphertext, plaintext)
   873  
   874  	// Prepare ASN.1 Encrypted Content Info
   875  	eci := encryptedContentInfo{
   876  		ContentType: oidData,
   877  		ContentEncryptionAlgorithm: pkix.AlgorithmIdentifier{
   878  			Algorithm:  oidEncryptionAlgorithmDESCBC,
   879  			Parameters: asn1.RawValue{Tag: 4, Bytes: iv},
   880  		},
   881  		EncryptedContent: marshalEncryptedContent(cyphertext),
   882  	}
   883  
   884  	return key, &eci, nil
   885  }
   886  
   887  // Encrypt creates and returns an envelope data PKCS7 structure with encrypted
   888  // recipient keys for each recipient public key.
   889  //
   890  // The algorithm used to perform encryption is determined by the current value
   891  // of the global ContentEncryptionAlgorithm package variable. By default, the
   892  // value is EncryptionAlgorithmDESCBC. To use a different algorithm, change the
   893  // value before calling Encrypt(). For example:
   894  //
   895  //     ContentEncryptionAlgorithm = EncryptionAlgorithmAES128GCM
   896  //
   897  // TODO(fullsailor): Add support for encrypting content with other algorithms
   898  func PKCS7Encrypt(content []byte, recipients []*Certificate) ([]byte, error) {
   899  	var eci *encryptedContentInfo
   900  	var key []byte
   901  	var err error
   902  
   903  	// Apply chosen symmetric encryption method
   904  	switch ContentEncryptionAlgorithm {
   905  	case EncryptionAlgorithmDESCBC:
   906  		key, eci, err = encryptDESCBC(content)
   907  
   908  	case EncryptionAlgorithmAES128GCM:
   909  		key, eci, err = encryptAES128GCM(content)
   910  
   911  	default:
   912  		return nil, ErrUnsupportedEncryptionAlgorithm
   913  	}
   914  
   915  	if err != nil {
   916  		return nil, err
   917  	}
   918  
   919  	// Prepare each recipient's encrypted cipher key
   920  	recipientInfos := make([]recipientInfo, len(recipients))
   921  	for i, recipient := range recipients {
   922  		encrypted, err := encryptKey(key, recipient)
   923  		if err != nil {
   924  			return nil, err
   925  		}
   926  		ias, err := cert2issuerAndSerial(recipient)
   927  		if err != nil {
   928  			return nil, err
   929  		}
   930  		info := recipientInfo{
   931  			Version:               0,
   932  			IssuerAndSerialNumber: ias,
   933  			KeyEncryptionAlgorithm: pkix.AlgorithmIdentifier{
   934  				Algorithm: oidEncryptionAlgorithmRSA,
   935  			},
   936  			EncryptedKey: encrypted,
   937  		}
   938  		recipientInfos[i] = info
   939  	}
   940  
   941  	// Prepare envelope content
   942  	envelope := envelopedData{
   943  		EncryptedContentInfo: *eci,
   944  		Version:              0,
   945  		RecipientInfos:       recipientInfos,
   946  	}
   947  	innerContent, err := asn1.Marshal(envelope)
   948  	if err != nil {
   949  		return nil, err
   950  	}
   951  
   952  	// Prepare outer payload structure
   953  	wrapper := contentInfo{
   954  		ContentType: oidEnvelopedData,
   955  		Content:     asn1.RawValue{Class: 2, Tag: 0, IsCompound: true, Bytes: innerContent},
   956  	}
   957  
   958  	return asn1.Marshal(wrapper)
   959  }
   960  
   961  func marshalEncryptedContent(content []byte) asn1.RawValue {
   962  	asn1Content, _ := asn1.Marshal(content)
   963  	return asn1.RawValue{Tag: 0, Class: 2, Bytes: asn1Content, IsCompound: true}
   964  }
   965  
   966  func encryptKey(key []byte, recipient *Certificate) ([]byte, error) {
   967  	if pub := recipient.PublicKey.(*rsa.PublicKey); pub != nil {
   968  		return rsa.EncryptPKCS1v15(rand.Reader, pub, key)
   969  	}
   970  	return nil, ErrPKCS7UnsupportedAlgorithm
   971  }