Added SHA2 OAEP decryption support for EnvelopedCms CEK.
authorKevin Jones <kevin@vcsjones.com>
Thu, 3 Jan 2019 06:18:19 +0000 (01:18 -0500)
committerKevin Jones <kevin@vcsjones.com>
Fri, 4 Jan 2019 04:58:33 +0000 (23:58 -0500)
Fixes dotnet/corefx#32913.

Commit migrated from https://github.com/dotnet/corefx/commit/1de58afa5edd914cbc50cb2cbcf87cc4278b10b8

src/libraries/Common/src/System/Security/Cryptography/Asn1/OaepParamsAsn.xml [new file with mode: 0644]
src/libraries/Common/src/System/Security/Cryptography/Asn1/OaepParamsAsn.xml.cs [new file with mode: 0644]
src/libraries/Common/src/System/Security/Cryptography/Oids.cs
src/libraries/System.Security.Cryptography.Pkcs/src/Internal/Cryptography/Pal/AnyOS/ManagedPal.KeyTrans.cs
src/libraries/System.Security.Cryptography.Pkcs/src/Internal/Cryptography/Pal/Windows/DecryptorPalWindows.Decrypt.cs
src/libraries/System.Security.Cryptography.Pkcs/src/Internal/Cryptography/Pal/Windows/HelpersWindows.cs
src/libraries/System.Security.Cryptography.Pkcs/src/System.Security.Cryptography.Pkcs.csproj
src/libraries/System.Security.Cryptography.Pkcs/tests/Certificates.cs
src/libraries/System.Security.Cryptography.Pkcs/tests/EnvelopedCms/DecryptTests.cs
src/libraries/System.Security.Cryptography.Pkcs/tests/EnvelopedCms/DecryptTestsUsingExplicitPrivateKey.cs

diff --git a/src/libraries/Common/src/System/Security/Cryptography/Asn1/OaepParamsAsn.xml b/src/libraries/Common/src/System/Security/Cryptography/Asn1/OaepParamsAsn.xml
new file mode 100644 (file)
index 0000000..b4f065e
--- /dev/null
@@ -0,0 +1,41 @@
+<?xml version="1.0" encoding="utf-8" ?>
+<asn:Sequence
+  xmlns:asn="http://schemas.dot.net/asnxml/201808/"
+  name="OaepParamsAsn"
+  namespace="System.Security.Cryptography.Asn1">
+
+  <!--
+    https://tools.ietf.org/html/rfc3560#section-3
+
+   RSAES-OAEP-params  ::=  SEQUENCE  {
+     hashFunc    [0] AlgorithmIdentifier DEFAULT sha1Identifier,
+     maskGenFunc [1] AlgorithmIdentifier DEFAULT mgf1SHA1Identifier,
+     pSourceFunc [2] AlgorithmIdentifier DEFAULT
+                         pSpecifiedEmptyIdentifier  }
+
+   sha1Identifier  AlgorithmIdentifier  ::=  { id-sha1, NULL }
+
+   mgf1SHA1Identifier  AlgorithmIdentifier  ::=
+                         { id-mgf1, sha1Identifier }
+
+   pSpecifiedEmptyIdentifier  AlgorithmIdentifier ::=
+                         { id-pSpecified, nullOctetString }
+
+   nullOctetString  OCTET STRING (SIZE (0))  ::=  { ''H }
+
+   id-sha1  OBJECT IDENTIFIER  ::=  { iso(1)
+                         identified-organization(3) oiw(14)
+                         secsig(3) algorithms(2) 26 }
+
+   pkcs-1  OBJECT IDENTIFIER  ::=  { iso(1) member-body(2)
+                         us(840) rsadsi(113549) pkcs(1) pkcs-1(1) }
+
+   id-mgf1  OBJECT IDENTIFIER  ::=  { pkcs-1 8 }
+
+   id-pSpecified  OBJECT IDENTIFIER  ::=  { pkcs-1 9 }
+
+  -->
+  <asn:AsnType name="HashFunc" typeName="System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn" explicitTag="0" defaultDerInit="0x30, 0x09, 0x06, 0x05, 0x2B, 0x0E, 0x03, 0x02, 0x1A, 0x05, 0x00" />
+  <asn:AsnType name="MaskGenFunc" typeName="System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn" explicitTag="1" defaultDerInit="0x30, 0x16, 0x06, 0x09, 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x08, 0x30, 0x09, 0x06, 0x05, 0x2B, 0x0E, 0x03, 0x02, 0x1A, 0x05, 0x00" />
+  <asn:AsnType name="PSourceFunc" typeName="System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn" explicitTag="2" defaultDerInit="0x30, 0x0D, 0x06, 0x09, 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x09, 0x04, 0x00" />
+</asn:Sequence>
diff --git a/src/libraries/Common/src/System/Security/Cryptography/Asn1/OaepParamsAsn.xml.cs b/src/libraries/Common/src/System/Security/Cryptography/Asn1/OaepParamsAsn.xml.cs
new file mode 100644 (file)
index 0000000..cf99794
--- /dev/null
@@ -0,0 +1,179 @@
+using System;
+using System.Runtime.InteropServices;
+using System.Security.Cryptography;
+using System.Security.Cryptography.Asn1;
+
+namespace System.Security.Cryptography.Asn1
+{
+    [StructLayout(LayoutKind.Sequential)]
+    internal partial struct OaepParamsAsn
+    {
+        private static byte[] s_defaultHashFunc = { 0x30, 0x09, 0x06, 0x05, 0x2B, 0x0E, 0x03, 0x02, 0x1A, 0x05, 0x00 };
+  
+        private static byte[] s_defaultMaskGenFunc = { 0x30, 0x16, 0x06, 0x09, 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x08, 0x30, 0x09, 0x06, 0x05, 0x2B, 0x0E, 0x03, 0x02, 0x1A, 0x05, 0x00 };
+  
+        private static byte[] s_defaultPSourceFunc = { 0x30, 0x0D, 0x06, 0x09, 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x09, 0x04, 0x00 };
+  
+        internal System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn HashFunc;
+        internal System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn MaskGenFunc;
+        internal System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn PSourceFunc;
+      
+#if DEBUG  
+        static OaepParamsAsn()
+        {
+            OaepParamsAsn decoded = default;
+            AsnReader reader;
+
+            reader = new AsnReader(s_defaultHashFunc, AsnEncodingRules.DER);
+            System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(reader, out decoded.HashFunc);
+            reader.ThrowIfNotEmpty();
+
+            reader = new AsnReader(s_defaultMaskGenFunc, AsnEncodingRules.DER);
+            System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(reader, out decoded.MaskGenFunc);
+            reader.ThrowIfNotEmpty();
+
+            reader = new AsnReader(s_defaultPSourceFunc, AsnEncodingRules.DER);
+            System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(reader, out decoded.PSourceFunc);
+            reader.ThrowIfNotEmpty();
+        }
+#endif
+        internal void Encode(AsnWriter writer)
+        {
+            Encode(writer, Asn1Tag.Sequence);
+        }
+    
+        internal void Encode(AsnWriter writer, Asn1Tag tag)
+        {
+            writer.PushSequence(tag);
+            
+
+            // DEFAULT value handler for HashFunc.
+            {
+                using (AsnWriter tmp = new AsnWriter(AsnEncodingRules.DER))
+                {
+                    HashFunc.Encode(tmp);
+                    ReadOnlySpan<byte> encoded = tmp.EncodeAsSpan();
+
+                    if (!encoded.SequenceEqual(s_defaultHashFunc))
+                    {
+                        writer.PushSequence(new Asn1Tag(TagClass.ContextSpecific, 0));
+                        writer.WriteEncodedValue(encoded.ToArray());
+                        writer.PopSequence(new Asn1Tag(TagClass.ContextSpecific, 0));
+                    }
+                }
+            }
+
+
+            // DEFAULT value handler for MaskGenFunc.
+            {
+                using (AsnWriter tmp = new AsnWriter(AsnEncodingRules.DER))
+                {
+                    MaskGenFunc.Encode(tmp);
+                    ReadOnlySpan<byte> encoded = tmp.EncodeAsSpan();
+
+                    if (!encoded.SequenceEqual(s_defaultMaskGenFunc))
+                    {
+                        writer.PushSequence(new Asn1Tag(TagClass.ContextSpecific, 1));
+                        writer.WriteEncodedValue(encoded.ToArray());
+                        writer.PopSequence(new Asn1Tag(TagClass.ContextSpecific, 1));
+                    }
+                }
+            }
+
+
+            // DEFAULT value handler for PSourceFunc.
+            {
+                using (AsnWriter tmp = new AsnWriter(AsnEncodingRules.DER))
+                {
+                    PSourceFunc.Encode(tmp);
+                    ReadOnlySpan<byte> encoded = tmp.EncodeAsSpan();
+
+                    if (!encoded.SequenceEqual(s_defaultPSourceFunc))
+                    {
+                        writer.PushSequence(new Asn1Tag(TagClass.ContextSpecific, 2));
+                        writer.WriteEncodedValue(encoded.ToArray());
+                        writer.PopSequence(new Asn1Tag(TagClass.ContextSpecific, 2));
+                    }
+                }
+            }
+
+            writer.PopSequence(tag);
+        }
+
+        internal static OaepParamsAsn Decode(ReadOnlyMemory<byte> encoded, AsnEncodingRules ruleSet)
+        {
+            return Decode(Asn1Tag.Sequence, encoded, ruleSet);
+        }
+        
+        internal static OaepParamsAsn Decode(Asn1Tag expectedTag, ReadOnlyMemory<byte> encoded, AsnEncodingRules ruleSet)
+        {
+            AsnReader reader = new AsnReader(encoded, ruleSet);
+            
+            Decode(reader, expectedTag, out OaepParamsAsn decoded);
+            reader.ThrowIfNotEmpty();
+            return decoded;
+        }
+
+        internal static void Decode(AsnReader reader, out OaepParamsAsn decoded)
+        {
+            if (reader == null)
+                throw new ArgumentNullException(nameof(reader));
+
+            Decode(reader, Asn1Tag.Sequence, out decoded);
+        }
+
+        internal static void Decode(AsnReader reader, Asn1Tag expectedTag, out OaepParamsAsn decoded)
+        {
+            if (reader == null)
+                throw new ArgumentNullException(nameof(reader));
+
+            decoded = default;
+            AsnReader sequenceReader = reader.ReadSequence(expectedTag);
+            AsnReader explicitReader;
+            AsnReader defaultReader;
+            
+
+            if (sequenceReader.HasData && sequenceReader.PeekTag().HasSameClassAndValue(new Asn1Tag(TagClass.ContextSpecific, 0)))
+            {
+                explicitReader = sequenceReader.ReadSequence(new Asn1Tag(TagClass.ContextSpecific, 0));
+                System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(explicitReader, out decoded.HashFunc);
+                explicitReader.ThrowIfNotEmpty();
+            }
+            else
+            {
+                defaultReader = new AsnReader(s_defaultHashFunc, AsnEncodingRules.DER);
+                System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(defaultReader, out decoded.HashFunc);
+            }
+
+
+            if (sequenceReader.HasData && sequenceReader.PeekTag().HasSameClassAndValue(new Asn1Tag(TagClass.ContextSpecific, 1)))
+            {
+                explicitReader = sequenceReader.ReadSequence(new Asn1Tag(TagClass.ContextSpecific, 1));
+                System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(explicitReader, out decoded.MaskGenFunc);
+                explicitReader.ThrowIfNotEmpty();
+            }
+            else
+            {
+                defaultReader = new AsnReader(s_defaultMaskGenFunc, AsnEncodingRules.DER);
+                System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(defaultReader, out decoded.MaskGenFunc);
+            }
+
+
+            if (sequenceReader.HasData && sequenceReader.PeekTag().HasSameClassAndValue(new Asn1Tag(TagClass.ContextSpecific, 2)))
+            {
+                explicitReader = sequenceReader.ReadSequence(new Asn1Tag(TagClass.ContextSpecific, 2));
+                System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(explicitReader, out decoded.PSourceFunc);
+                explicitReader.ThrowIfNotEmpty();
+            }
+            else
+            {
+                defaultReader = new AsnReader(s_defaultPSourceFunc, AsnEncodingRules.DER);
+                System.Security.Cryptography.Asn1.AlgorithmIdentifierAsn.Decode(defaultReader, out decoded.PSourceFunc);
+            }
+
+
+            sequenceReader.ThrowIfNotEmpty();
+        }
+    }
+}
index eaf9305..08404bf 100644 (file)
@@ -78,6 +78,7 @@ namespace System.Security.Cryptography
         internal const string ECDsaWithSha512 = "1.2.840.10045.4.3.4";
 
         internal const string Mgf1 = "1.2.840.113549.1.1.8";
+        internal const string PSpecified = "1.2.840.113549.1.1.9";
 
         // PKCS#7
         internal const string NoSignature = "1.3.6.1.5.5.7.6.2";
index 6d60063..2fb843f 100644 (file)
@@ -6,6 +6,7 @@ using System;
 using System.Buffers;
 using System.Diagnostics;
 using System.Security.Cryptography;
+using System.Security.Cryptography.Asn1;
 using System.Security.Cryptography.Pkcs;
 using System.Security.Cryptography.Pkcs.Asn1;
 using System.Security.Cryptography.X509Certificates;
@@ -16,6 +17,7 @@ namespace Internal.Cryptography.Pal.AnyOS
     {
         private static readonly byte[] s_rsaPkcsParameters = { 0x05, 0x00 };
         private static readonly byte[] s_rsaOaepSha1Parameters = { 0x30, 0x00 };
+        private static readonly byte[] s_pSpecifiedDefaultParameters = { 0x04, 0x00 };
 
         internal sealed class ManagedKeyTransPal : KeyTransRecipientInfoPal
         {
@@ -53,12 +55,6 @@ namespace Internal.Cryptography.Pal.AnyOS
                         }
                         break;
                     case Oids.RsaOaep:
-                        if (parameters != null &&
-                            !parameters.Value.Span.SequenceEqual(s_rsaOaepSha1Parameters))
-                        {
-                            exception = new CryptographicException(SR.Cryptography_Der_Invalid_Encoding);
-                            return null;
-                        }
                         break;
                     default:
                         exception = new CryptographicException(
@@ -68,7 +64,7 @@ namespace Internal.Cryptography.Pal.AnyOS
                         return null;
                 }
 
-                return DecryptCekCore(cert, privateKey, _asn.EncryptedKey.Span, keyEncryptionAlgorithm, out exception);
+                return DecryptCekCore(cert, privateKey, _asn.EncryptedKey.Span, keyEncryptionAlgorithm, parameters, out exception);
             }
 
             internal static byte[] DecryptCekCore(
@@ -76,6 +72,7 @@ namespace Internal.Cryptography.Pal.AnyOS
                 RSA privateKey,
                 ReadOnlySpan<byte> encryptedKey,
                 string keyEncryptionAlgorithm,
+                ReadOnlyMemory<byte>? algorithmParameters,
                 out Exception exception)
             {
                 RSAEncryptionPadding encryptionPadding;
@@ -86,7 +83,10 @@ namespace Internal.Cryptography.Pal.AnyOS
                         encryptionPadding = RSAEncryptionPadding.Pkcs1;
                         break;
                     case Oids.RsaOaep:
-                        encryptionPadding = RSAEncryptionPadding.OaepSHA1;
+                        if (!TryGetRsaOaepEncryptionPadding(algorithmParameters, out encryptionPadding, out exception))
+                        {
+                            return null;
+                        }
                         break;
                     default:
                         exception = new CryptographicException(
@@ -223,5 +223,75 @@ namespace Internal.Cryptography.Pal.AnyOS
             }
 #endif
         }
+
+        private static bool TryGetRsaOaepEncryptionPadding(
+            ReadOnlyMemory<byte>? parameters,
+            out RSAEncryptionPadding rsaEncryptionPadding,
+            out Exception exception)
+        {
+            exception = null;
+            rsaEncryptionPadding = null;
+
+            if (parameters == null || parameters.Value.IsEmpty)
+            {
+                exception = new CryptographicException(SR.Cryptography_Der_Invalid_Encoding);
+                return false;
+            }
+
+            try
+            {
+                OaepParamsAsn oaepParameters = OaepParamsAsn.Decode(parameters.Value, AsnEncodingRules.DER);
+
+                if (oaepParameters.MaskGenFunc.Algorithm.Value != Oids.Mgf1 ||
+                    oaepParameters.MaskGenFunc.Parameters == null ||
+                    oaepParameters.PSourceFunc.Algorithm.Value != Oids.PSpecified
+                    )
+                {
+                    exception = new CryptographicException(SR.Cryptography_Der_Invalid_Encoding);
+                    return false;
+                }
+
+                AlgorithmIdentifierAsn mgf1AlgorithmIdentifier = AlgorithmIdentifierAsn.Decode(oaepParameters.MaskGenFunc.Parameters.Value, AsnEncodingRules.DER);
+
+                if (mgf1AlgorithmIdentifier.Algorithm.Value != oaepParameters.HashFunc.Algorithm.Value)
+                {
+                    exception = new CryptographicException(SR.Cryptography_Der_Invalid_Encoding);
+                    return false;
+                }
+
+                if (oaepParameters.PSourceFunc.Parameters != null &&
+                    !oaepParameters.PSourceFunc.Parameters.Value.Span.SequenceEqual(s_pSpecifiedDefaultParameters))
+                {
+                    exception = new CryptographicException(SR.Cryptography_Der_Invalid_Encoding);
+                    return false;
+                }
+
+                switch (oaepParameters.HashFunc.Algorithm.Value)
+                {
+                    case Oids.Sha1:
+                        rsaEncryptionPadding = RSAEncryptionPadding.OaepSHA1;
+                        return true;
+                    case Oids.Sha256:
+                        rsaEncryptionPadding = RSAEncryptionPadding.OaepSHA256;
+                        return true;
+                    case Oids.Sha384:
+                        rsaEncryptionPadding = RSAEncryptionPadding.OaepSHA384;
+                        return true;
+                    case Oids.Sha512:
+                        rsaEncryptionPadding = RSAEncryptionPadding.OaepSHA512;
+                        return true;
+                    default:
+                        exception = new CryptographicException(
+                            SR.Cryptography_Cms_UnknownAlgorithm,
+                            oaepParameters.HashFunc.Algorithm.Value);
+                        return false;
+                }
+            }
+            catch (CryptographicException e)
+            {
+                exception = e;
+                return false;
+            }
+        }
     }
 }
index 7b675e0..10df1a9 100644 (file)
@@ -43,6 +43,7 @@ namespace Internal.Cryptography.Pal.Windows
                     key,
                     recipientInfo.EncryptedKey,
                     recipientInfo.KeyEncryptionAlgorithm.Oid.Value,
+                    recipientInfo.KeyEncryptionAlgorithm.Parameters,
                     out exception);
 
                 // Pin CEK to prevent it from getting copied during heap compaction.
index 75b054e..c1db134 100644 (file)
@@ -327,6 +327,12 @@ namespace Internal.Cryptography.Pal.Windows
             }
 
             AlgorithmIdentifier algorithmIdentifier = new AlgorithmIdentifier(Oid.FromOidValue(oidValue, OidGroup.All), keyLength);
+            switch (oidValue)
+            {
+                case Oids.RsaOaep:
+                    algorithmIdentifier.Parameters = cryptAlgorithmIdentifer.Parameters.ToByteArray();
+                    break;
+            }
             return algorithmIdentifier;
         }
 
index 9152532..4af36c0 100644 (file)
       <Link>Common\System\Security\Cryptography\Asn1\PssParamsAsn.xml.cs</Link>
       <DependentUpon>Common\System\Security\Cryptography\Asn1\PssParamsAsn.xml</DependentUpon>
     </Compile>
+    <AsnXml Include="$(CommonPath)\System\Security\Cryptography\Asn1\OaepParamsAsn.xml">
+      <Link>Common\System\Security\Cryptography\Asn1\OaepParamsAsn.xml</Link>
+    </AsnXml>
+    <Compile Include="$(CommonPath)\System\Security\Cryptography\Asn1\OaepParamsAsn.xml.cs">
+      <Link>Common\System\Security\Cryptography\Asn1\OaepParamsAsn.xml.cs</Link>
+      <DependentUpon>Common\System\Security\Cryptography\Asn1\OaepParamsAsn.xml</DependentUpon>
+    </Compile>
     <AsnXml Include="$(CommonPath)\System\Security\Cryptography\Asn1\PrivateKeyInfoAsn.xml">
       <Link>Common\System\Security\Cryptography\Asn1\PrivateKeyInfoAsn.xml</Link>
     </AsnXml>
index dc5b095..5ab90c3 100644 (file)
@@ -16,6 +16,7 @@ namespace System.Security.Cryptography.Pkcs.Tests
         public static readonly CertLoader RSASha256KeyTransfer1 = new CertLoaderFromRawData(RawData.s_RSASha256KeyTransfer1Cer, RawData.s_RSASha256KeyTransfer1Pfx, "1111");
         public static readonly CertLoader RSASha384KeyTransfer1 = new CertLoaderFromRawData(RawData.s_RSASha384KeyTransfer1Cer, RawData.s_RSASha384KeyTransfer1Pfx, "1111");
         public static readonly CertLoader RSASha512KeyTransfer1 = new CertLoaderFromRawData(RawData.s_RSASha512KeyTransfer1Cer, RawData.s_RSASha512KeyTransfer1Pfx, "1111");
+        public static readonly CertLoader RSA2048Sha256KeyTransfer1 = new CertLoaderFromRawData(RawData.s_RSA2048Sha256KeyTransfer1Cer, RawData.s_RSA2048Sha256KeyTransfer1Pfx, "1111");
         public static readonly CertLoader DHKeyAgree1 = new CertLoaderFromRawData(RawData.s_DHKeyAgree1Cer);
         public static readonly CertLoader RSA2048SignatureOnly = new CertLoaderFromRawData(RawData.s_Rsa2048SignatureOnlyCer, RawData.s_Rsa2048SignatureOnlyPfx, "12345");
         public static readonly CertLoader Dsa1024 = new CertLoaderFromRawData(RawData.s_dsa1024Cert, RawData.s_dsa1024Pfx, "1234");
@@ -359,6 +360,86 @@ namespace System.Security.Cryptography.Pkcs.Tests
                 + "0706052b0e03021a041401844058f6e177051a87eedcc55cc4fa8d567ff10414669cb82c9cc3ceb4d3ca9f65bd57ba829616"
                 + "60d9020207d0").HexToByteArray();
 
+            public static byte[] s_RSA2048Sha256KeyTransfer1Cer =
+                 ("3082031e30820206a003020102020900dce4d72a7f3ca58e300d06092a86"
+                + "4886f70d01010b050030243122302006035504030c195253413230343853"
+                + "68613235364b65795472616e7366657231301e170d313930313033323034"
+                + "3133345a170d3238313233313230343133345a3024312230200603550403"
+                + "0c19525341323034385368613235364b65795472616e7366657231308201"
+                + "22300d06092a864886f70d01010105000382010f003082010a0282010100"
+                + "bf8495ef84c91eb42ae9196c52aa2c6e22a258c4d76e09e93980d81fafe6"
+                + "977fe1a3c8b4e9ca414405a1a4db6d549a4849189d568aa639f10fa556f5"
+                + "5377c8fde8ec33ccdc833c4c5b8b36275e8f1899443871b7363f204a2826"
+                + "8bd9e890fdd488b17bc49890f78fab5d8a5927b69655760d400a30e0ee87"
+                + "dd38b4168df6814596e0efaafb2f9cc134664bb8629e65aa107847b4416b"
+                + "d57f0b701c30e9a160aa589646e981815d9823201ae0ee601208c51c08d3"
+                + "e50b1fab1560802916e678310c03e3cff3bcc039f98d5b254e2baf027ae9"
+                + "f78faef72c2d93075eca64b5ad3e92348068c4dcb8cad0bad954a7d04fce"
+                + "3aff94ef8cf282095db75a25a4114f8f0203010001a3533051301d060355"
+                + "1d0e04160414fedfd2558b95e705584a50008ed0d1683aee840e301f0603"
+                + "551d23041830168014fedfd2558b95e705584a50008ed0d1683aee840e30"
+                + "0f0603551d130101ff040530030101ff300d06092a864886f70d01010b05"
+                + "00038201010031c46689db724a1a8d268eaa7139efcf8a31496f15f325a1"
+                + "9349547114d7992ead5fa0bd6ffd5539b1639f0cf8f975c5e9ebed8a0482"
+                + "89c782ec7e0342f339f53e811cc6a6864173502388875964f0c50d84aba9"
+                + "228dd2e3ddd3339374b76a6826f4f848a403adda2e095974232b084c8672"
+                + "b12c18d675d81ed8fa4b15a1c7abc73f9ccb5bc25716eeb9d2c97f8ebcb9"
+                + "d4824fb23c7fbc78e1d3b9b1b3749f6c0981b2b6cc81dc723aa5cc589346"
+                + "dceca222c78f68fe80563e12282f7df936a161163f86a9eadba2e180a906"
+                + "de73aebeea0775f6ab9ae97c71f26e187e3d8cb50c8137663c99d440877d"
+                + "5a5e17df9785976e9031dd96134a07899281b6b64e3f").HexToByteArray();
+
+            public static byte[] s_RSA2048Sha256KeyTransfer1Pfx =
+                 ("308209710201033082093706092a864886f70d010701a08209280482092430820920308203c706092a864886f70d010706a0"
+                + "8203b8308203b4020100308203ad06092a864886f70d010701301c060a2a864886f70d010c0106300e04081681e2854fdf32"
+                + "7702020800808203807561ee3de7d54036ba61f41f76155bd406cd909358a12db40e07698863cc1143c77becf6dcb87a4a8a"
+                + "701c8ff59021431a98ff6193c6d36e3bd7d11806c788042bc6f5dbceede60a1d6a314300ceca09b571e1a7842db92e19185b"
+                + "e2408db8458d3e9127096b1f8a8c493aebc22bdfeb48bcd6d592b9db1d075fc7468cae8bf5bc01a0fa93bb2047981c5a4e23"
+                + "f8c8e7795b1f94f5fbe2dbd03578ae2cdf13560bb73c219d258919f002217cb15a8b6e037da01c1de49b4c699c74c5396cf8"
+                + "67bb308026c3a6b85da079de0aedecea0770a6b76128d185fc94a955789f3f26ffb99689b7311c7619ad24a33c6be16e022b"
+                + "7216de49e1f11c9b4ded79aa438f535dbdb8bcc9f58ed2b3cd62515c5742f5e2ae0e9f791b83d4ebba5b3766e10194ae27f0"
+                + "68960d039777c5ce71b11da9a4c791f612e06cddd2e474cfb8bda95faf88f6a854c26f6c787d20db07aa777f6ec2c208760c"
+                + "67cb51cc5c79e13ba2760013d4ff54ab33a0aff355fea7aabd607a4fd8449d16173249be6785be5fa2e415932b6be65b483c"
+                + "718e151e820bb4930f7df183cfa8c4a88b989a133ddb1717ea5b73f0950bf485de09d335347a16b96f02a4417e3671856c19"
+                + "8b45462a21ce0df8f8e4c5178aae1999dc936aff91512ef9b7667de37e924118a6e958b111bf33088938987136143fa28ec7"
+                + "216f77f4fecf87cfe3cd6af4d73a2e544d2f24a915de8d619faf0a4b891f09a9365bdd6dc48bc1eed864354e84c1bf0bc9dd"
+                + "99a9e1280f6c81501424700960209ce0da9fd9e1b462d06673bb041439c8726f2b8890b90e859f717478637594675299c29c"
+                + "da3f2dc6b6b9f1b72befc542407f180c89204774965c277fec78905b14b0ba54d19a9e8c3eb9c6ec6d056773a248908a6483"
+                + "de20539b75de610c4ebdc77dc3a903a7e00fb1f6f46bfc97fe08a75b9d82bc4c536e4c71cf7c88d2eb57c50a97278ea5a254"
+                + "1c5ee418f2aeccf800dd1dee31aacb4e6c679c58400757817a08ad7ec12e128f2e177bf2870d68c6d9fb4b2987abee13bfc1"
+                + "7b529dd00edc8eea55fc8268e02dcbd84e7cb2cfe1ae8d4c1fb0a486871e18ddde79759ad0127e5dac938a105aaee9368901"
+                + "186c149424ec992b57fe927b1f6c35142229e3d427a0d86d454d302c3cf4fa4f1b75c42813e8029a1428570aa1903acde079"
+                + "6d0d2259780bf4752a70788fc642c372009f57cd430ee2edc01954e5a615744e7cd3bd8784e3c3b80b0b63847464207f92ec"
+                + "821dd564f43082055106092a864886f70d010701a08205420482053e3082053a30820536060b2a864886f70d010c0a0102a0"
+                + "8204fe308204fa301c060a2a864886f70d010c0103300e04084dcda62e7b3f05f602020800048204d87345553aefe9a5c6d8"
+                + "488c069190343bd43adcb7a3058066b12b01f58d238b517627b440b704a1944955c4f97b59eb0bafb4d6ea35f6d931773013"
+                + "e0202a1229659ab32469edd459a7712757457a5a967af3a4328d772a87ca46076c76dcbcb3671be555969826e1f94d2879be"
+                + "9f464bca6d970cc31ac485ff50d2f055a1cf1cfe1aa0a14e166a85bf27c9d5f8d2ba876e54d737936a6f5f61d6e2dd7cf4e1"
+                + "3bd34e397809cf62de6d793944d37c82b180bf98d1ffd7b345174883864fd31b80fb598ba4eb63c1f7ca9c676ec0c38f2306"
+                + "7329f63b28ca0dd17f0f78caa00d1953d818bf198f769095ed84a8fa50888ee3327ffcd2eb508545dc961435ced61d5af9d9"
+                + "7cdae7fa44ab658ecbf7bc4656deb32cdb8fbf45538c21d653f89cdeed08f84a732cd1a9f3f5d27231daf06fb80e8521dec5"
+                + "51331466c851d133648e9ed978aca042d66a8dd224b6bd3ebd861302c1c096247a193beb6fc37a50c6b79e3751bf68b4bf45"
+                + "2ff71bfa07ae20d22d3003c92bd1f7907850c0a689ed2ed15466f23e164d5356cf8c0fdf22c109e2de5178a3e58216402f6a"
+                + "ffffd911924dfebe0d771b4056399753972ed7006f0e89ca0a6e256c8d439c0199bc2407e2ddadf820edb464cee1cf059d9a"
+                + "eae490493dcbc3c59c1bdcc70059a636a6d6092fe554efb616bcf653b4d673e025569fc95218ce99aa48bd01832f76739f30"
+                + "05ddb6616e0f42cf236f30aacd261afd567765b5b2e8363d94e871f32755b8b2a9170d40ecfe497f88c4287550df80a9b802"
+                + "2560d6137f6f4641c8479535e4f2c2f66f60843623f30a8201422c797b7ba8df24440249571203eacc6d362c2c87c417f854"
+                + "dc64194e8e8566a414bb32d2eb8a316296286ed36767bdc34c97ee9d891c6d28453b1e83a525b8dcddcb20510c913acea8e3"
+                + "3053784a36097f8cd2984c8ee6623c1e0875046769cda607cba996417ee97b788819e476425a9b5369bd8affcc867c5974ba"
+                + "639a5c2d1ad33d63776a06b040e364233e9407f7004200fe1716a55ca6871f5e68033a8c0b5d1392df55f39ee2c751bcacc5"
+                + "3c8347870e453c2fa4e0abbf3ed9a668bdb2839ca9529292a9545db18af6d0213d67fca687d164a7fce7a7c1482f3788bf8e"
+                + "77e5d820f75a975e3b4b00a4ee9d2a21cb4eb81c5e31a48d82f7c09b92eff40a83dc0e5528c2f90442ef85e47e3af680ac74"
+                + "4117add8582e293b78d078f0f07307453be0e7a64ff9cae27eb51fb14eb5b8760643ad1204b352a9a9772f419f92a37a0ce9"
+                + "2f002b5a34b97bbd9df209a090df38fe67244fd01e19b92fa881d00b70c6083480c12483a2fe1103c1c12f3148819728ce30"
+                + "11678d6711452bda6163911d2c29168f3e915f3b7e9afc6fa8b7d1e21c32db0252f784f33341b87107af7c783a05270ef2de"
+                + "48175e147683e515fa97f4d3fe8dd77b1d4e24e6049fbf1ed9d08d0dc6b2be65554ba116b25e3cb1462f3aaf1fbd60624909"
+                + "a579a726f6176552000e84ab323a88f23a630985685e3aeb0b08c9f027f717257c595d053f257d6e5f2ecfd30903bdc35868"
+                + "f4b20f86938102d22c782713e3ea01d67bfa0ecea9668b6b15de3198adb4e87e438634cb3fa3ea7e2c195d9616dd2b42e107"
+                + "3e29e94dc9067f2794f25f8a78108db5c99a51298353cb7c1c0352d76f19ea6222e03836cc7bcf9f8873b07d4e0ba845b3f2"
+                + "f19eb36e9cc8215f28f2b911f772d4330340fbb6f8cc1840241720074c0c743125302306092a864886f70d01091531160414"
+                + "c6fe1078ea0dbc7c8d7f96ad3b7157625c8aab8c30313021300906052b0e03021a05000414bd17b7ccb644846ca45544381e"
+                + "b780abf0ccc2650408e4b108ac25f3820e02020800").HexToByteArray();
+
             public static byte[] s_DHKeyAgree1Cer =
                  ("3082041930820305a00302010202100ae59b0cb8119f8942eda74163413a02300906052b0e03021d0500304f314d304b0603"
                 + "5504031e44004d0061006e006100670065006400200050004b00430053002300370020005400650073007400200052006f00"
index cede9a7..c7ae3bc 100644 (file)
@@ -562,6 +562,136 @@ namespace System.Security.Cryptography.Pkcs.EnvelopedCmsTests.Tests
         }
 
         [Fact]
+        [OuterLoop(/* Leaks key on disk if interrupted */)]
+        public void TestDecryptSimpleAes256_RsaOaepSha256()
+        {
+            // Generated with:
+            // openssl cms -encrypt -in input.txt -out out.msg -recip cert.pem -keyopt rsa_padding_mode:oaep -keyopt rsa_mgf1_md:sha256 --aes256 -keyopt rsa_oaep_md:sha256
+            byte[] encodedMessage = Convert.FromBase64String(
+                    "MIIBUAYJKoZIhvcNAQcDoIIBQTCCAT0CAQAxgfkwgfYCAQAwNDAgMR4wHAYDVQQD" +
+                    "ExVSU0FTaGEyNTZLZXlUcmFuc2ZlcjECEHLGx3NJFkaMTWCCU9oBdnYwOAYJKoZI" +
+                    "hvcNAQEHMCugDTALBglghkgBZQMEAgGhGjAYBgkqhkiG9w0BAQgwCwYJYIZIAWUD" +
+                    "BAIBBIGAuobMSz1Q4OHRX2aX9AutOPdZX2phA6WATQTOKOWCD//LQwrHYtuNIPAG" +
+                    "Tld+JTZ1EMQD9PoEMyxdkllyie2dn/PSvnE0q/WU+IrHzGzoWofuNs9M6g9Gvpg5" +
+                    "qCGAXK9cL3WkZ9S+M1r6BqlCLwU03bJr6292PiLyjIH80CdMuRUwPAYJKoZIhvcN" +
+                    "AQcBMB0GCWCGSAFlAwQBKgQQezbMDGrefOaUPpfIXBpw7oAQazcOoj9GkvzZMR9Z" +
+                    "NU22nQ==");
+            byte[] content = "68690D0A".HexToByteArray();
+            ContentInfo expectedContentInfo = new ContentInfo(new Oid(Oids.Pkcs7Data), content);
+
+            VerifySimpleDecrypt(encodedMessage, Certificates.RSASha256KeyTransfer1, expectedContentInfo);
+        }
+
+        [Fact]
+        [OuterLoop(/* Leaks key on disk if interrupted */)]
+        public void TestDecryptSimpleAes256_RsaOaepSha384()
+        {
+            // Generated with:
+            // openssl cms -encrypt -in input.txt -out out.msg -recip cert.pem -keyopt rsa_padding_mode:oaep -keyopt rsa_mgf1_md:sha384 --aes256 -keyopt rsa_oaep_md:sha384
+            byte[] encodedMessage = Convert.FromBase64String(
+                    "MIIB0AYJKoZIhvcNAQcDoIIBwTCCAb0CAQAxggF4MIIBdAIBADAxMCQxIjAgBgNV" +
+                    "BAMMGVJTQTIwNDhTaGEyNTZLZXlUcmFuc2ZlcjECCQDc5NcqfzyljjA4BgkqhkiG" +
+                    "9w0BAQcwK6ANMAsGCWCGSAFlAwQCAqEaMBgGCSqGSIb3DQEBCDALBglghkgBZQME" +
+                    "AgIEggEAIqqdx5zCFnGSNzV+/N0Mu8S8CVABuPv+RcpV8fiFj5TLcHe84lYI/ptr" +
+                    "F7FwyQRfHVDWgJrJqDS/wYfzD6Ar8qLRdfBswCotn/QYm/VLzBXNRLM402t3lWq+" +
+                    "2pgucyGghpnf2I1aZo8U9hJGUOUPISQqkiol9I1O/JYfo9B7sBTW8Vp22W/c8nTI" +
+                    "huQx+tOhzqGAMElrsd+cEaTiVqAMmNU20B2du0wWs0nckzg4KLbz2g/g8L699luU" +
+                    "t8OluQclxfVgruLY28RY8R5w7OH2LZSEhyKxq3PG3KqXqR+E1MCkpdg8PhTJkeYO" +
+                    "Msz1J70aVA8L8nrhtS9xXq0dd8jyfzA8BgkqhkiG9w0BBwEwHQYJYIZIAWUDBAEq" +
+                    "BBA/xHlg1Der3mxzmvPvUcqogBDEEZmz+ECEWMeNGBv/Cw82");
+            byte[] content = "68690D0A".HexToByteArray();
+            ContentInfo expectedContentInfo = new ContentInfo(new Oid(Oids.Pkcs7Data), content);
+
+            VerifySimpleDecrypt(encodedMessage, Certificates.RSA2048Sha256KeyTransfer1, expectedContentInfo);
+        }
+
+        [Fact]
+        [OuterLoop(/* Leaks key on disk if interrupted */)]
+        public void TestDecryptSimpleAes256_RsaOaepSha512()
+        {
+            // Generated with:
+            // openssl cms -encrypt -in input.txt -out out.msg -recip cert.pem -keyopt rsa_padding_mode:oaep -keyopt rsa_mgf1_md:sha512 --aes256 -keyopt rsa_oaep_md:sha512
+            byte[] encodedMessage = Convert.FromBase64String(
+                    "MIIB0AYJKoZIhvcNAQcDoIIBwTCCAb0CAQAxggF4MIIBdAIBADAxMCQxIjAgBgNV" +
+                    "BAMMGVJTQTIwNDhTaGEyNTZLZXlUcmFuc2ZlcjECCQDc5NcqfzyljjA4BgkqhkiG" +
+                    "9w0BAQcwK6ANMAsGCWCGSAFlAwQCA6EaMBgGCSqGSIb3DQEBCDALBglghkgBZQME" +
+                    "AgMEggEAc6QULhpkV7C63HhSbdYM7QFDTtRj8Wch3QHrFB0jIYlLGxcMuOB3Kw6f" +
+                    "P1Q4W8qmVJgH+dyeKcpu2J6OrjlZVDtK166DrmKCflTMCGhCsPsmCMbKlpBihuXo" +
+                    "7xQ13Fzs9QhudY/B/jUNjOTb3nONBqOdDJVLFsoMxm9cJqnDcdFPJVgIFl3IQW7X" +
+                    "I1ZFdnS6FVKybR94jU4ASx8awQ+zDOgnCsyZ7t5cOwca2NgyQxZCf92WEJjdXqbl" +
+                    "3ax/ULfSWD104Fp4N7lf8Z9BAkjIVJh3EeROzWgDkP5FQ9bDqkn3x+IlVKHfu+3r" +
+                    "fmaUWI/sZCMXnUnLFEEILwCBcZlvBzA8BgkqhkiG9w0BBwEwHQYJYIZIAWUDBAEq" +
+                    "BBDJhteA5Rpug15ksuJ9o/9vgBDQzvGRyFU8AKtfSpF6jBkB");
+            byte[] content = "68690D0A".HexToByteArray();
+            ContentInfo expectedContentInfo = new ContentInfo(new Oid(Oids.Pkcs7Data), content);
+
+            VerifySimpleDecrypt(encodedMessage, Certificates.RSA2048Sha256KeyTransfer1, expectedContentInfo);
+        }
+
+        [Fact]
+        [OuterLoop(/* Leaks key on disk if interrupted */)]
+        public void TestDecryptSimpleAes256_RsaOaepSha1_Default()
+        {
+            // Generated with:
+            // openssl cms -encrypt -in input.txt -out out.msg -recip cert.pem -keyopt rsa_padding_mode:oaep -keyopt rsa_mgf1_md:sha1 --aes256 -keyopt rsa_oaep_md:sha1
+            byte[] encodedMessage = Convert.FromBase64String(
+                    "MIIBJQYJKoZIhvcNAQcDoIIBFjCCARICAQAxgc4wgcsCAQAwNDAgMR4wHAYDVQQD" +
+                    "ExVSU0FTaGEyNTZLZXlUcmFuc2ZlcjECEHLGx3NJFkaMTWCCU9oBdnYwDQYJKoZI" +
+                    "hvcNAQEHMAAEgYCLNNE4H03P0aP1lBDwKrm549DajTVSeyseWxv7TDDdVVWOTNgh" +
+                    "c5OEVT2lmzxWD6lq28aZqmV8PPxJhvOZl4mnY9ycA5hgwmFRdKyI2hBTWQL8GQcF" +
+                    "nYKc54BMKNaJsfIUIwN89knw7AEYEchGF+USKgQY1qsvdag6ZNBuhs5uwTA8Bgkq" +
+                    "hkiG9w0BBwEwHQYJYIZIAWUDBAEqBBB/OyPGgn42q2XoDE4o8+2ggBDRXtH4O1xQ" +
+                    "BHevgmD2Ev8V");
+            byte[] content = "68690D0A".HexToByteArray();
+            ContentInfo expectedContentInfo = new ContentInfo(new Oid(Oids.Pkcs7Data), content);
+
+            VerifySimpleDecrypt(encodedMessage, Certificates.RSASha256KeyTransfer1, expectedContentInfo);
+        }
+
+        [Fact]
+        [OuterLoop(/* Leaks key on disk if interrupted */)]
+        public void TestDecryptSimpleAes256_RsaOaep_MaskGenFunc_HashFunc_Mismatch()
+        {
+            // Generated with:
+            // openssl cms -encrypt -in input.txt -out out.msg -recip cert.pem -keyopt rsa_padding_mode:oaep -keyopt rsa_mgf1_md:sha1 --aes256 -keyopt rsa_oaep_md:sha256
+            byte[] encodedMessage = Convert.FromBase64String(
+                    "MIIBNAYJKoZIhvcNAQcDoIIBJTCCASECAQAxgd0wgdoCAQAwNDAgMR4wHAYDVQQD" +
+                    "ExVSU0FTaGEyNTZLZXlUcmFuc2ZlcjECEHLGx3NJFkaMTWCCU9oBdnYwHAYJKoZI" +
+                    "hvcNAQEHMA+gDTALBglghkgBZQMEAgEEgYCw85yDulRtibSZm0xy1mOTIGjDu4yy" +
+                    "pMT++3dV5Cy2GF4vp3mxp89Ylq2boYZ8b4B86IcJqUfyU/fG19O+vXyjn/0VUP3f" +
+                    "OjMM71oqvQc/Qou/LvgDYQZY1koDldoeH89waZ1hgFaVpFEwGZUPSHmzgfsxMOpj" +
+                    "RoToifiTsP3PkjA8BgkqhkiG9w0BBwEwHQYJYIZIAWUDBAEqBBCCufI08zVL4KVc" +
+                    "WgKwZxCNgBA9M9KpJHmKwm5dMtvdcs/Q");
+            byte[] content = "68690D0A".HexToByteArray();
+            ContentInfo expectedContentInfo = new ContentInfo(new Oid(Oids.Pkcs7Data), content);
+
+            Assert.ThrowsAny<CryptographicException>(
+                () => VerifySimpleDecrypt(encodedMessage, Certificates.RSASha256KeyTransfer1, expectedContentInfo));
+        }
+
+        [Fact]
+        [OuterLoop(/* Leaks key on disk if interrupted */)]
+        public void TestDecryptSimpleAes256_RsaOaep_PSpecified_NonDefault()
+        {
+            // Generated with:
+            // openssl cms -encrypt -in input.txt -out out.msg -recip cert.pem -keyopt rsa_padding_mode:oaep \
+            //   -keyopt rsa_mgf1_md:sha1 --aes256 -keyopt rsa_oaep_md:sha1 -keyopt rsa_oaep_label:0102030405
+            byte[] encodedMessage = Convert.FromBase64String(
+                    "MIIBOwYJKoZIhvcNAQcDoIIBLDCCASgCAQAxgeQwgeECAQAwNDAgMR4wHAYDVQQD" +
+                    "ExVSU0FTaGEyNTZLZXlUcmFuc2ZlcjECEHLGx3NJFkaMTWCCU9oBdnYwIwYJKoZI" +
+                    "hvcNAQEHMBaiFDASBgkqhkiG9w0BAQkEBQECAwQFBIGAoJ7P69rwtexRcLbK+K8z" +
+                    "UrKROLk2tVU8xGA056j8o2GfqQPxGsHl1w8Q3lsnSPsjGHY30+KYmQMQrZJd5zIW" +
+                    "2OpgriYeqnHUwNCd9CrRFVvEqqACZlzTw/L+DgeDXwSNPRzNghjIqWo79FFT9kRI" +
+                    "DHUB10A+sIZevVYtFrWxbVQwPAYJKoZIhvcNAQcBMB0GCWCGSAFlAwQBKgQQfxMe" +
+                    "56xuPm9lTJYYozmQ6oAQd1RIE2hhgx1kdJmIW1Z4/w==");
+            byte[] content = "68690D0A".HexToByteArray();
+            ContentInfo expectedContentInfo = new ContentInfo(new Oid(Oids.Pkcs7Data), content);
+
+            Assert.ThrowsAny<CryptographicException>(
+                () => VerifySimpleDecrypt(encodedMessage, Certificates.RSASha256KeyTransfer1, expectedContentInfo));
+        }
+
+        [Fact]
         public void DecryptEnvelopedOctetStringWithDefiniteLength()
         {
             // enveloped content consists of 5 bytes: <id: 1 byte><length: 1 byte><content: 3 bytes>
@@ -697,7 +827,7 @@ namespace System.Security.Cryptography.Pkcs.EnvelopedCmsTests.Tests
             VerifySimpleDecrypt(encodedMessage, certLoader, expectedContentInfo);
         }
 
-        private void VerifySimpleDecrypt(byte[] encodedMessage, CertLoader certLoader, ContentInfo expectedContent)
+        internal void VerifySimpleDecrypt(byte[] encodedMessage, CertLoader certLoader, ContentInfo expectedContent)
         {
             EnvelopedCms ecms = new EnvelopedCms();
             ecms.Decode(encodedMessage);
index 64587a3..65717e5 100644 (file)
@@ -4,6 +4,7 @@
 
 using System.Security.Cryptography.Pkcs.Tests;
 using System.Security.Cryptography.X509Certificates;
+using Test.Cryptography;
 using Xunit;
 
 namespace System.Security.Cryptography.Pkcs.EnvelopedCmsTests.Tests
@@ -36,5 +37,27 @@ namespace System.Security.Cryptography.Pkcs.EnvelopedCmsTests.Tests
                 Assert.Throws<CryptographicException>(() => ecms.Decrypt(ecms.RecipientInfos[0], ecdsa));
             }
         }
+
+        [Fact]
+        [OuterLoop(/* Leaks key on disk if interrupted */)]
+        public void TestDecryptSimpleAes256_RsaOaepMd5_Throws()
+        {
+            // Generated with:
+            // openssl cms -encrypt -in input.txt -out out.msg -recip cert.pem -keyopt rsa_padding_mode:oaep -keyopt rsa_mgf1_md:md5 --aes256 -keyopt rsa_oaep_md:md5
+            byte[] encodedMessage = Convert.FromBase64String(
+                    "MIIBUgYJKoZIhvcNAQcDoIIBQzCCAT8CAQAxgfswgfgCAQAwNDAgMR4wHAYDVQQD" +
+                    "ExVSU0FTaGEyNTZLZXlUcmFuc2ZlcjECEHLGx3NJFkaMTWCCU9oBdnYwOgYJKoZI" +
+                    "hvcNAQEHMC2gDjAMBggqhkiG9w0CBQUAoRswGQYJKoZIhvcNAQEIMAwGCCqGSIb3" +
+                    "DQIFBQAEgYCqBXo+gdyWvxfMJ3WR6Tw76i8N69awXjhuCQulWqZtYQiBoVb1fptK" +
+                    "mBIcsnEHuHvG8s4UIU/vzLvB/SFCTYR0pJAT0rY2dkjQYsGtup822qO0cbWE9aqO" +
+                    "D/fkVd8LREoMrMF3AGF6r9SclgWUDi871sfGcKwpjzU9gx5C9aasIjA8BgkqhkiG" +
+                    "9w0BBwEwHQYJYIZIAWUDBAEqBBAA7mDmj510sKUxedURDS2lgBD7or6d7ZeMhZL6" +
+                    "6rUUMLoU");
+            byte[] content = "68690D0A".HexToByteArray();
+            ContentInfo expectedContentInfo = new ContentInfo(new Oid(Oids.Pkcs7Data), content);
+
+            Assert.ThrowsAny<CryptographicException>(
+                () => VerifySimpleDecrypt(encodedMessage, Certificates.RSASha256KeyTransfer1, expectedContentInfo));
+        }
     }
 }