how does openssl smime determine micalg parameter?

199 Views Asked by At

When I build a signed S/MIME message using openssl smime -sign, how does openssl determine what value to use for the micalg parameter? (ie: micalg="sha-256" in my example below...) I can see this value in the S/MIME text and in the ASN of the generated signature, but I can't figure out where it's coming from or how I could change it.

I am using the ruby openssl wrapper library. When I create a PKCS7 document, I want to inspect it to determine the correct value to use for micalg (when I send an AS2 MDN back to a client)...

pkcs7 = OpenSSL::PKCS7.sign certificate, pkey, message
pkcs7.detached = true

I'm trying to understand how to inspect pkcs7 here to determine the micalg I should use when constructing a Content-Type header like openssl smime -sign does.

I first thought this was somehow derived from the certificate and/or key I used to sign the message, but I still see micalg="sha-256" even when I generate a certificate using another algorithm like md5.

Here are sample commands using openssl cli tool, since I'm guessing that's familiar to more folks here than the ruby wrapper. (It's a very thin wrapper, so translating between the two is usually straightforward.)

-> % openssl req -x509 -md5 -newkey rsa:2048 -nodes -keyout server_md5.key -out server_md5.crt -days 365

-> % openssl smime -sign -text -in message.txt -signer test/certificates/server_md5.crt -inkey test/certificates/server_md5.key

MIME-Version: 1.0
Content-Type: multipart/signed; protocol="application/x-pkcs7-signature"; micalg="sha-256"; boundary="----FA974EDD77D0E708FEB7C0F3E6B14F13"

This is an S/MIME signed message

------FA974EDD77D0E708FEB7C0F3E6B14F13
Content-Type: text/plain

this is the content of message.txt

------FA974EDD77D0E708FEB7C0F3E6B14F13
Content-Type: application/x-pkcs7-signature; name="smime.p7s"
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename="smime.p7s"

MIIFhgYJKoZIhvcNAQcCoIIFdzCCBXMCAQExDzANBglghkgBZQMEAgEFADALBgkq
... signature removed for length ...
ppMlHw6KISLkBtFChJvSx5EyeeyN6cMfiXs=

------FA974EDD77D0E708FEB7C0F3E6B14F13--

If i save the generated signature into a separate file & inspect it, i think i see the data i'm interested in in in the d.sign > md_algs portion of the raw ASN1.

openssl pkcs7 -in signature.p7m -print
PKCS7: 
  type: pkcs7-signedData (1.2.840.113549.1.7.2)
  d.sign: 
    version: 1
    md_algs:
        algorithm: sha256 (2.16.840.1.101.3.4.2.1)
        parameter: NULL
    contents: 
      type: pkcs7-data (1.2.840.113549.1.7.1)
      d.data: <ABSENT>

d.sign > md_algs seems to correspond with the following from the S/MIME RFC

digestAlgorithms is a collection of message-digest algorithm identifiers. There may be any number of elements in the collection, including zero. Each element identifies the message-digest algorithm (and any associated parameters) under which the content is digested for a some signer. The collection is intended to list the message-digest algorithms employed by all of the signers, in any order, to facilitate one-pass signature verification.

https://www.rfc-editor.org/rfc/rfc2315#section-9.1

I just can't determine how to either

  1. specify this value when I sign the message
  2. or how to inspect the generated signature to determine the micalg
0

There are 0 best solutions below