Farbschema: Dunkel
Sie befinden sich hier: start » en » Documentation » Post-Quantum Cryptography » WKL.System.Security.Cryptography overview » How-to guides » Sign CMS messages

Sign CMS messages

You sign messages in CMS (PKCS #7) format, for example to exchange documents, and you want to include an ML-DSA signature next to the RSA or ECDSA signature without recipients that don't know about PQ rejecting the message.

Solution overview

ElementPurpose
SignedDataExtensions.CreatePqAwareSignercreates a CmsSigner for a hybrid certificate and checks that its ML-DSA key is present
SignedCms.ComputeSignature with CryptoMode.Hybridsigns classically, announces the PQ signature in a signed attribute, and appends it
SignedCms.CheckSignature with CryptoMode.Hybridverifies the classical signature as .NET does, then the PQ signature of each signer

Implementation

Sign the message. Here, signerCertificate is a hybrid certificate with an RSA key whose ML-DSA key is in the process. In this example, it's self-signed:

using var signerRsa = RSA.Create(3072);
using var signerCertificate = new CertificateRequest(
        "CN=Contoso Accounting", signerRsa, HashAlgorithmName.SHA256, RSASignaturePadding.Pkcs1)
    .CreateSelfSigned(DateTimeOffset.UtcNow, DateTimeOffset.UtcNow.AddYears(1), CryptoMode.Hybrid);
 
var content = new ContentInfo("Invoice 2026-0042"u8.ToArray());
var outgoing = new SignedCms(content);
outgoing.ComputeSignature(SignedDataExtensions.CreatePqAwareSigner(signerCertificate), CryptoMode.Hybrid);
byte[] message = outgoing.Encode();

Verify the message at the recipient:

var incoming = new SignedCms();
incoming.Decode(message);
incoming.CheckSignature(verifySignatureOnly: true, CryptoMode.Hybrid);
Console.WriteLine("Both signatures are valid.");

Like the .NET method, CheckSignature returns nothing and throws a CryptographicException if a signature is invalid.

Remarks

  • Classical recipients. The PQ signature is in an unsigned attribute, and its announcement is in a signed attribute of the SignerInfo. Recipients without this library verify the message with the .NET CheckSignature like any other.
  • Downgrades are detected. Anyone can remove an unsigned attribute. Because the classical signature protects the announcement, CheckSignature with CryptoMode.Hybrid detects a removed PQ signature and throws a CryptographicException. It also rejects a PQ signature created with a key other than the announced one.
  • No on-the-fly key. CreatePqAwareSigner never generates an ML-DSA key. If the certificate's key isn't in the process, the method throws a CryptographicException right away. In that case, load the certificate from a PFX file, or use the overload that takes the key pair.
  • Provisional identifiers. The attributes use provisional identifiers; see Formats of the post-quantum parts.
  • Certificate validation. verifySignatureOnly: true only verifies the signatures. With false, .NET also validates the signer certificate's chain according to the operating system's rules, without the PQ part. To validate the PQ part of the chain, use X509Chain.Build with CryptoMode.Hybrid.
en/wiki/pqcrypt/lib/how-to/sign-cms-messages.txt · Zuletzt geändert: von Wolfgang van der Stille