public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.WriteGeneralizedTime(DateTimeOffset.UtcNow)); Assert.Throws <ObjectDisposedException>( () => writer.WriteGeneralizedTime(DateTimeOffset.UtcNow, true)); Assert.Throws <ArgumentException>( "tag", () => writer.WriteGeneralizedTime(Asn1Tag.Integer, DateTimeOffset.Now)); Assert.Throws <ArgumentException>( "tag", () => writer.WriteGeneralizedTime(Asn1Tag.Integer, DateTimeOffset.Now, true)); Asn1Tag tag = new Asn1Tag(TagClass.ContextSpecific, 18); Assert.Throws <ObjectDisposedException>( () => writer.WriteGeneralizedTime(tag, DateTimeOffset.Now)); Assert.Throws <ObjectDisposedException>( () => writer.WriteGeneralizedTime(tag, DateTimeOffset.Now, true)); } }
private unsafe AsnWriter WritePkcs8PrivateKey() { // A PKCS1 RSAPrivateKey is the Modulus (KeySize bits), D (~KeySize bits) // P, Q, DP, DQ, InverseQ (all ~KeySize/2 bits) // Each field can have up to 7 bytes of overhead, and then another 9 bytes // of fixed overhead. // So it should fit in 5 * KeySizeInBytes, but Exponent is a wildcard. int rentSize = checked (5 * KeySize / 8); while (true) { byte[] rented = ArrayPool <byte> .Shared.Rent(rentSize); rentSize = rented.Length; int pkcs1Size = 0; fixed(byte *rentPtr = rented) { try { if (!TryExportRSAPrivateKey(rented, out pkcs1Size)) { rentSize = checked (rentSize * 2); continue; } AsnWriter writer = new AsnWriter(AsnEncodingRules.BER); try { writer.PushSequence(); // Version 0 format (no attributes) writer.WriteInteger(0); WriteAlgorithmIdentifier(writer); writer.WriteOctetString(rented.AsSpan(0, pkcs1Size)); writer.PopSequence(); return(writer); } catch { writer.Dispose(); throw; } } finally { CryptographicOperations.ZeroMemory(rented.AsSpan(0, pkcs1Size)); ArrayPool <byte> .Shared.Return(rented); } } } }
public static void Pop_After_Dispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>(() => writer.PopSetOf()); } }
public static void Push_Custom_After_Dispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.PushSetOf(new Asn1Tag(TagClass.Application, 2))); } }
private AsnWriter EncodeToNewWriter() { AsnWriter writer = new AsnWriter(AsnEncodingRules.BER); try { EncodeTo(writer); return(writer); } catch { writer.Dispose(); throw; } }
public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.WriteUtcTime(DateTimeOffset.Now)); AssertExtensions.Throws <ArgumentOutOfRangeException>( "value", () => writer.WriteUtcTime(DateTimeOffset.Now, 1999)); AssertExtensions.Throws <ArgumentOutOfRangeException>( "value", () => writer.WriteUtcTime(DateTimeOffset.Now, 8999)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteUtcTime(Asn1Tag.Integer, DateTimeOffset.Now)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteUtcTime(Asn1Tag.Integer, DateTimeOffset.Now, 1999)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteUtcTime(Asn1Tag.Integer, DateTimeOffset.Now, 8999)); Asn1Tag tag = new Asn1Tag(TagClass.Application, 3); Assert.Throws <ObjectDisposedException>( () => writer.WriteUtcTime(tag, DateTimeOffset.Now)); AssertExtensions.Throws <ArgumentOutOfRangeException>( "value", () => writer.WriteUtcTime(tag, DateTimeOffset.Now, 1999)); AssertExtensions.Throws <ArgumentOutOfRangeException>( "value", () => writer.WriteUtcTime(tag, DateTimeOffset.Now, 8999)); } }
public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteBoolean(true); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.WriteNull()); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteNull(Asn1Tag.Integer)); Assert.Throws <ObjectDisposedException>( () => writer.WriteNull(new Asn1Tag(TagClass.Private, 3))); } }
public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.WriteBitString(ReadOnlySpan <byte> .Empty)); Assert.Throws <ObjectDisposedException>( () => writer.WriteBitString(ReadOnlySpan <byte> .Empty, 1)); Assert.Throws <ArgumentOutOfRangeException>( "unusedBitCount", () => writer.WriteBitString(ReadOnlySpan <byte> .Empty, 9)); Assert.Throws <ArgumentException>( "tag", () => writer.WriteBitString(Asn1Tag.Boolean, ReadOnlySpan <byte> .Empty)); Asn1Tag tag = new Asn1Tag(TagClass.ContextSpecific, 11); Assert.Throws <ObjectDisposedException>( () => writer.WriteBitString(tag, ReadOnlySpan <byte> .Empty)); Assert.Throws <ObjectDisposedException>( () => writer.WriteBitString(tag, ReadOnlySpan <byte> .Empty, 1)); Assert.Throws <ArgumentOutOfRangeException>( "unusedBitCount", () => writer.WriteBitString(tag, ReadOnlySpan <byte> .Empty, 9)); } }
internal AsnWriter Encode() { AsnWriter writer; if (ConfidentialityMode == Pkcs12ConfidentialityMode.Password || ConfidentialityMode == Pkcs12ConfidentialityMode.PublicKey) { writer = new AsnWriter(AsnEncodingRules.BER); writer.WriteEncodedValue(_encrypted.Span); return(writer); } Debug.Assert(ConfidentialityMode == Pkcs12ConfidentialityMode.None); writer = new AsnWriter(AsnEncodingRules.BER); try { writer.PushSequence(); if (_bags != null) { foreach (Pkcs12SafeBag safeBag in _bags) { safeBag.EncodeTo(writer); } } writer.PopSequence(); return(writer); } catch { writer.Dispose(); throw; } }
protected void WriteAfterDispose_String(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); string input = "1"; Assert.Throws <ObjectDisposedException>( () => WriteString(writer, input)); AssertExtensions.Throws <ArgumentException>( "tag", () => WriteString(writer, Asn1Tag.Boolean, input)); Assert.Throws <ObjectDisposedException>( () => WriteString(writer, new Asn1Tag(TagClass.Application, 0), input)); } }
public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.WriteOctetString(ReadOnlySpan <byte> .Empty)); Assert.Throws <ArgumentException>( "tag", () => writer.WriteOctetString(Asn1Tag.Integer, ReadOnlySpan <byte> .Empty)); Assert.Throws <ObjectDisposedException>( () => writer.WriteOctetString( new Asn1Tag(TagClass.Private, 3), ReadOnlySpan <byte> .Empty)); } }
internal byte[] Encrypt( ReadOnlySpan <char> password, ReadOnlySpan <byte> passwordBytes, PbeParameters pbeParameters) { Debug.Assert(pbeParameters != null); Debug.Assert(pbeParameters.IterationCount >= 1); AsnWriter writer = null; using (AsnWriter contentsWriter = Encode()) { ReadOnlySpan <byte> contentsSpan = contentsWriter.EncodeAsSpan(); PasswordBasedEncryption.InitiateEncryption( pbeParameters, out SymmetricAlgorithm cipher, out string hmacOid, out string encryptionAlgorithmOid, out bool isPkcs12); int cipherBlockBytes = cipher.BlockSize / 8; byte[] encryptedRent = CryptoPool.Rent(contentsSpan.Length + cipherBlockBytes); Span <byte> encryptedSpan = Span <byte> .Empty; Span <byte> iv = stackalloc byte[cipherBlockBytes]; Span <byte> salt = stackalloc byte[16]; RandomNumberGenerator.Fill(salt); try { int written = PasswordBasedEncryption.Encrypt( password, passwordBytes, cipher, isPkcs12, contentsSpan, pbeParameters, salt, encryptedRent, iv); encryptedSpan = encryptedRent.AsSpan(0, written); writer = new AsnWriter(AsnEncodingRules.DER); // EncryptedData writer.PushSequence(); // version // Since we're not writing unprotected attributes, version=0 writer.WriteInteger(0); // encryptedContentInfo { writer.PushSequence(); writer.WriteObjectIdentifier(Oids.Pkcs7Data); PasswordBasedEncryption.WritePbeAlgorithmIdentifier( writer, isPkcs12, encryptionAlgorithmOid, salt, pbeParameters.IterationCount, hmacOid, iv); writer.WriteOctetString( new Asn1Tag(TagClass.ContextSpecific, 0), encryptedSpan); writer.PopSequence(); } writer.PopSequence(); return(writer.Encode()); } finally { CryptographicOperations.ZeroMemory(encryptedSpan); CryptoPool.Return(encryptedRent, clearSize: 0); writer?.Dispose(); } } }
public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(1)); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(1UL)); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(BigInteger.One)); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(BigInteger.One.ToByteArray(isBigEndian: true))); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(Array.Empty <byte>())); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(new byte[] { 0, 0 })); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(new byte[] { 0xFF, 0xFF })); Assert.Throws <ArgumentException>( "tag", () => writer.WriteInteger(Asn1Tag.Boolean, 1)); Assert.Throws <ArgumentException>( "tag", () => writer.WriteInteger(Asn1Tag.Boolean, 1UL)); Assert.Throws <ArgumentException>( "tag", () => writer.WriteInteger(Asn1Tag.Boolean, BigInteger.One)); Assert.Throws <ArgumentException>( "tag", () => writer.WriteInteger(Asn1Tag.Boolean, BigInteger.One.ToByteArray(isBigEndian: true))); Assert.Throws <ArgumentException>( "tag", () => writer.WriteInteger(Asn1Tag.Boolean, Array.Empty <byte>())); Assert.Throws <ArgumentException>( "tag", () => writer.WriteInteger(Asn1Tag.Boolean, new byte[] { 0, 0 })); Assert.Throws <ArgumentException>( "tag", () => writer.WriteInteger(Asn1Tag.Boolean, new byte[] { 0xFF, 0xFF })); Asn1Tag tag = new Asn1Tag(TagClass.Application, 0); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(tag, 1)); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(tag, 1UL)); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(tag, BigInteger.One)); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(tag, BigInteger.One.ToByteArray(isBigEndian: true))); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(tag, Array.Empty <byte>())); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(tag, new byte[] { 0, 0 })); Assert.Throws <ObjectDisposedException>( () => writer.WriteInteger(tag, new byte[] { 0xFF, 0xFF })); } }
public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("0.0")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("0")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("0.0q")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("123")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("4.0")); AssertExtensions.Throws <ArgumentNullException>( "oidValue", () => writer.WriteObjectIdentifier((string)null)); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("0.0".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("0".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("0.0q".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("123".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier("4.0".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(new Oid("0.0", "valid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(new Oid("0", "short"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(new Oid("0.0q", "invalid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(new Oid("123", "invalid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(new Oid("4.0", "invalid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(new Oid(null, "null"))); AssertExtensions.Throws <ArgumentNullException>( "oid", () => writer.WriteObjectIdentifier((Oid)null)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteBoolean(Asn1Tag.Integer, false)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "0.0")); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "0")); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "0.0q")); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "123")); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "4.0")); AssertExtensions.Throws <ArgumentNullException>( "oidValue", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, (string)null)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "0.0".AsSpan())); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "0".AsSpan())); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "0.0q".AsSpan())); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "123".AsSpan())); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, "4.0".AsSpan())); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, new Oid("0.0", "valid"))); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, new Oid("0", "short"))); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, new Oid("0.0q", "invalid"))); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, new Oid("123", "invalid"))); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, new Oid("4.0", "invalid"))); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, new Oid(null, "null"))); AssertExtensions.Throws <ArgumentNullException>( "oid", () => writer.WriteObjectIdentifier(Asn1Tag.Integer, (Oid)null)); Asn1Tag tag = new Asn1Tag(TagClass.ContextSpecific, 123); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "0.0")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "0")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "0.0q")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "123")); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "4.0")); AssertExtensions.Throws <ArgumentNullException>( "oidValue", () => writer.WriteObjectIdentifier(tag, (string)null)); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "0.0".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "0".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "0.0q".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "123".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, "4.0".AsSpan())); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, new Oid("0.0", "valid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, new Oid("0", "short"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, new Oid("0.0q", "invalid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, new Oid("123", "valid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, new Oid("4.0", "valid"))); Assert.Throws <ObjectDisposedException>( () => writer.WriteObjectIdentifier(tag, new Oid(null, "null"))); AssertExtensions.Throws <ArgumentNullException>( "oid", () => writer.WriteObjectIdentifier(tag, (Oid)null)); } }
public static void WriteAfterDispose(bool empty) { using (AsnWriter writer = new AsnWriter(AsnEncodingRules.DER)) { if (!empty) { writer.WriteNull(); } writer.Dispose(); // Type not enum AssertExtensions.Throws <ArgumentException>( "enumType", () => writer.WriteNamedBitList(false)); // Type not enum AssertExtensions.Throws <ArgumentException>( "enumType", () => writer.WriteNamedBitList((object)"hi")); AssertExtensions.Throws <ArgumentNullException>( "enumValue", () => writer.WriteNamedBitList((object)null)); // valid input Assert.Throws <ObjectDisposedException>( () => writer.WriteNamedBitList(ReadNamedBitList.LongFlags.Mid)); // Type is not [Flags] AssertExtensions.Throws <ArgumentException>( "tEnum", () => writer.WriteNamedBitList(ReadEnumerated.UIntBacked.Fluff)); // valid input Assert.Throws <ObjectDisposedException>( () => writer.WriteNamedBitList((object)ReadNamedBitList.ULongFlags.Mid)); // Unboxed type is [Flags] AssertExtensions.Throws <ArgumentException>( "tEnum", () => writer.WriteNamedBitList((object)ReadEnumerated.SByteBacked.Fluff)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteNamedBitList(Asn1Tag.Integer, false)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteNamedBitList(Asn1Tag.Integer, (object)"hi")); AssertExtensions.Throws <ArgumentNullException>( "enumValue", () => writer.WriteNamedBitList(Asn1Tag.Integer, (object)null)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteNamedBitList(Asn1Tag.Integer, ReadNamedBitList.LongFlags.Mid)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteNamedBitList(Asn1Tag.Integer, ReadEnumerated.UIntBacked.Fluff)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteNamedBitList(Asn1Tag.Integer, (object)ReadNamedBitList.ULongFlags.Mid)); AssertExtensions.Throws <ArgumentException>( "tag", () => writer.WriteNamedBitList(Asn1Tag.Integer, (object)ReadEnumerated.SByteBacked.Fluff)); Asn1Tag tag = new Asn1Tag(TagClass.Private, 6); // Type not enum AssertExtensions.Throws <ArgumentException>( "enumType", () => writer.WriteNamedBitList(tag, false)); // Type not enum AssertExtensions.Throws <ArgumentException>( "enumType", () => writer.WriteNamedBitList(tag, (object)"hi")); AssertExtensions.Throws <ArgumentNullException>( "enumValue", () => writer.WriteNamedBitList(tag, (object)null)); // valid input Assert.Throws <ObjectDisposedException>( () => writer.WriteNamedBitList(tag, ReadNamedBitList.LongFlags.Mid)); // Type is [Flags] AssertExtensions.Throws <ArgumentException>( "tEnum", () => writer.WriteNamedBitList(tag, ReadEnumerated.UIntBacked.Fluff)); // valid input Assert.Throws <ObjectDisposedException>( () => writer.WriteNamedBitList(tag, (object)ReadNamedBitList.ULongFlags.Mid)); // Unboxed type is not [Flags] AssertExtensions.Throws <ArgumentException>( "tEnum", () => writer.WriteNamedBitList(tag, (object)ReadEnumerated.SByteBacked.Fluff)); } }
private byte[] ExportPfx(SafePasswordHandle password) { int certCount = 1; if (_singleCertPal == null) { Debug.Assert(_certs != null); certCount = _certs.Count; } CertBagAsn[] certBags = ArrayPool <CertBagAsn> .Shared.Rent(certCount); SafeBagAsn[] keyBags = ArrayPool <SafeBagAsn> .Shared.Rent(certCount); AttributeAsn[] certAttrs = ArrayPool <AttributeAsn> .Shared.Rent(certCount); certAttrs.AsSpan(0, certCount).Clear(); AsnWriter tmpWriter = new AsnWriter(AsnEncodingRules.DER); ArraySegment <byte> encodedAuthSafe = default; bool gotRef = false; password.DangerousAddRef(ref gotRef); try { ReadOnlySpan <char> passwordSpan = password.DangerousGetSpan(); int keyIdx = 0; int certIdx = 0; if (_singleCertPal != null) { BuildBags( _singleCertPal, passwordSpan, tmpWriter, certBags, certAttrs, keyBags, ref certIdx, ref keyIdx); } else { foreach (X509Certificate2 cert in _certs) { BuildBags( cert.Pal, passwordSpan, tmpWriter, certBags, certAttrs, keyBags, ref certIdx, ref keyIdx); } } encodedAuthSafe = EncodeAuthSafe( tmpWriter, keyBags, keyIdx, certBags, certAttrs, certIdx, passwordSpan); return(MacAndEncode(tmpWriter, encodedAuthSafe, passwordSpan)); } finally { password.DangerousRelease(); tmpWriter.Dispose(); certAttrs.AsSpan(0, certCount).Clear(); certBags.AsSpan(0, certCount).Clear(); keyBags.AsSpan(0, certCount).Clear(); ArrayPool <AttributeAsn> .Shared.Return(certAttrs); ArrayPool <CertBagAsn> .Shared.Return(certBags); ArrayPool <SafeBagAsn> .Shared.Return(keyBags); if (encodedAuthSafe.Array != null) { CryptoPool.Return(encodedAuthSafe); } } }