#2 Update to .NET Core Runtime 2.2.1 and SDK 2.2.103
Merged 5 years ago by rhea. Opened 5 years ago by omajid.
dotnet-sig/ omajid/dotnet-2-2 master  into  master

@@ -0,0 +1,724 @@ 

+ From 7f5ccbde792c7fd94ec27c33861ae1c3118ecf93 Mon Sep 17 00:00:00 2001

+ From: Filip Navara <filip.navara@gmail.com>

+ Date: Sun, 24 Jun 2018 06:29:39 +0200

+ Subject: [PATCH 1/7] NetFX compatibility fixes for X500DistinguishedName.

+ 

+ * Don't write a separator after the empty DN

+ * Make T61String behave like it does on Windows (UTF-8 with a Latin-1 fallback)

+ * Use the managed decoder on Linux, instead of a lot of P/Invokes back into OpenSSL.

+ ---

+  .../Interop.ASN1.cs                           |  27 ----

+  .../Interop.X509Name.cs                       |  39 ------

+  .../Interop.X509NameEntry.cs                  |  61 ---------

+  .../SafeHandles/SafeX509NameHandle.Unix.cs    |  30 -----

+  .../Cryptography/DerSequenceReader.cs         |  35 +++++

+  .../pal_x509_name.cpp                         |   5 +

+  .../pal_x509_name.h                           |   5 +

+  .../src/System.Net.Http.csproj                |   3 -

+  .../src/System.Net.Security.csproj            |   3 -

+  ...em.Security.Cryptography.Algorithms.csproj |   1 +

+  ...stem.Security.Cryptography.Encoding.csproj |   1 +

+  ...ystem.Security.Cryptography.OpenSsl.csproj |   1 +

+  .../Pal.Unix/X500NameEncoder.ManagedDecode.cs |   4 +-

+  .../Pal.Unix/X500NameEncoder.OpenSslDecode.cs | 123 ------------------

+  .../Cryptography/Pal.Unix/X500NameEncoder.cs  |   7 +-

+  ...urity.Cryptography.X509Certificates.csproj |  10 +-

+  .../tests/X500DistinguishedNameTests.cs       |  69 ++++++++++

+  17 files changed, 125 insertions(+), 299 deletions(-)

+  delete mode 100644 src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509NameEntry.cs

+  delete mode 100644 src/Common/src/Microsoft/Win32/SafeHandles/SafeX509NameHandle.Unix.cs

+  delete mode 100644 src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.OpenSslDecode.cs

+ 

+ diff --git a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.cs b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.cs

+ index 962eaa426f..5bd2e8b9b4 100644

+ --- a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.cs

+ +++ b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.cs

+ @@ -61,22 +61,6 @@ internal static partial class Interop

+          [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_Asn1StringFree")]

+          internal static extern void Asn1StringFree(IntPtr o);

+  

+ -        internal static string GetOidValue(SafeSharedAsn1ObjectHandle asn1Object)

+ -        {

+ -            Debug.Assert(asn1Object != null);

+ -

+ -            bool added = false;

+ -            asn1Object.DangerousAddRef(ref added);

+ -            try

+ -            {

+ -                return GetOidValue(asn1Object.DangerousGetHandle());

+ -            }

+ -            finally

+ -            {

+ -                asn1Object.DangerousRelease();

+ -            }

+ -        }

+ -

+          internal static unsafe string GetOidValue(IntPtr asn1ObjectPtr)

+          {

+              // OBJ_obj2txt returns the number of bytes that should have been in the answer, but it does not accept

+ @@ -127,14 +111,3 @@ internal static partial class Interop

+          }

+      }

+  }

+ -

+ -namespace Microsoft.Win32.SafeHandles

+ -{

+ -    internal class SafeSharedAsn1ObjectHandle : SafeInteriorHandle

+ -    {

+ -        private SafeSharedAsn1ObjectHandle() :

+ -            base(IntPtr.Zero, ownsHandle: true)

+ -        {

+ -        }

+ -    }

+ -}

+ diff --git a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509Name.cs b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509Name.cs

+ index 0f0fecad24..70097d7db2 100644

+ --- a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509Name.cs

+ +++ b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509Name.cs

+ @@ -15,16 +15,6 @@ internal static partial class Interop

+          [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509NameStackFieldCount")]

+          internal static extern int GetX509NameStackFieldCount(SafeSharedX509NameStackHandle sk);

+  

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_PushX509NameStackField")]

+ -        [return: MarshalAs(UnmanagedType.Bool)]

+ -        internal static extern bool PushX509NameStackField(SafeX509NameStackHandle stack, SafeX509NameHandle x509_Name);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_RecursiveFreeX509NameStack")]

+ -        internal static extern void RecursiveFreeX509NameStack(IntPtr stack);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_NewX509NameStack")]

+ -        internal static extern SafeX509NameStackHandle NewX509NameStack();

+ -

+          [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509NameStackField")]

+          private static extern SafeSharedX509NameHandle GetX509NameStackField_private(SafeSharedX509NameStackHandle sk,

+              int loc);

+ @@ -32,15 +22,6 @@ internal static partial class Interop

+          [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509NameRawBytes")]

+          private static extern int GetX509NameRawBytes(SafeSharedX509NameHandle x509Name, byte[] buf, int cBuf);

+  

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_DecodeX509Name")]

+ -        internal static extern SafeX509NameHandle DecodeX509Name(byte[] buf, int len);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_X509NameDestroy")]

+ -        internal static extern void X509NameDestroy(IntPtr a);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509NameEntryCount")]

+ -        internal static extern int GetX509NameEntryCount(SafeX509NameHandle x509Name);

+ -

+          internal static X500DistinguishedName LoadX500Name(SafeSharedX509NameHandle namePtr)

+          {

+              CheckValidOpenSslHandle(namePtr);

+ @@ -86,25 +67,5 @@ namespace Microsoft.Win32.SafeHandles

+          {

+          }

+      }

+ -

+ -    internal sealed class SafeX509NameStackHandle : SafeHandle

+ -    {

+ -        private SafeX509NameStackHandle() :

+ -            base(IntPtr.Zero, ownsHandle: true)

+ -        {

+ -        }

+ -

+ -        protected override bool ReleaseHandle()

+ -        {

+ -            Interop.Crypto.RecursiveFreeX509NameStack(handle);

+ -            SetHandle(IntPtr.Zero);

+ -            return true;

+ -        }

+ -

+ -        public override bool IsInvalid

+ -        {

+ -            get { return handle == IntPtr.Zero; }

+ -        }

+ -    }

+  }

+  

+ diff --git a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509NameEntry.cs b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509NameEntry.cs

+ deleted file mode 100644

+ index eeeea54d0c..0000000000

+ --- a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.X509NameEntry.cs

+ +++ /dev/null

+ @@ -1,61 +0,0 @@

+ -// Licensed to the .NET Foundation under one or more agreements.

+ -// The .NET Foundation licenses this file to you under the MIT license.

+ -// See the LICENSE file in the project root for more information.

+ -

+ -using System;

+ -using System.Runtime.InteropServices;

+ -using Microsoft.Win32.SafeHandles;

+ -

+ -internal static partial class Interop

+ -{

+ -    internal static partial class Crypto

+ -    {

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509NameEntry")]

+ -        private static extern SafeSharedX509NameEntryHandle GetX509NameEntry_private(SafeX509NameHandle x509Name, int loc);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509NameEntryOid")]

+ -        private static extern SafeSharedAsn1ObjectHandle GetX509NameEntryOid_private(SafeSharedX509NameEntryHandle nameEntry);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_GetX509NameEntryData")]

+ -        private static extern SafeSharedAsn1StringHandle GetX509NameEntryData_private(SafeSharedX509NameEntryHandle nameEntry);

+ -

+ -        internal static SafeSharedX509NameEntryHandle GetX509NameEntry(SafeX509NameHandle x509Name, int loc)

+ -        {

+ -            CheckValidOpenSslHandle(x509Name);

+ -

+ -            return SafeInteriorHandle.OpenInteriorHandle(

+ -                (nameHandle, i) => GetX509NameEntry_private(nameHandle, i),

+ -                x509Name,

+ -                loc);

+ -        }

+ -

+ -        internal static SafeSharedAsn1ObjectHandle GetX509NameEntryOid(SafeSharedX509NameEntryHandle nameEntry)

+ -        {

+ -            CheckValidOpenSslHandle(nameEntry);

+ -

+ -            return SafeInteriorHandle.OpenInteriorHandle(

+ -                handle => GetX509NameEntryOid_private(handle),

+ -                nameEntry);

+ -        }

+ -

+ -        internal static SafeSharedAsn1StringHandle GetX509NameEntryData(SafeSharedX509NameEntryHandle nameEntry)

+ -        {

+ -            CheckValidOpenSslHandle(nameEntry);

+ -

+ -            return SafeInteriorHandle.OpenInteriorHandle(

+ -                handle => GetX509NameEntryData_private(handle),

+ -                nameEntry);

+ -        }

+ -    }

+ -}

+ -

+ -namespace Microsoft.Win32.SafeHandles

+ -{

+ -    internal sealed class SafeSharedX509NameEntryHandle : SafeInteriorHandle

+ -    {

+ -        private SafeSharedX509NameEntryHandle() :

+ -            base(IntPtr.Zero, ownsHandle: true)

+ -        {

+ -        }

+ -    }

+ -}

+ diff --git a/src/Common/src/Microsoft/Win32/SafeHandles/SafeX509NameHandle.Unix.cs b/src/Common/src/Microsoft/Win32/SafeHandles/SafeX509NameHandle.Unix.cs

+ deleted file mode 100644

+ index ae22b92303..0000000000

+ --- a/src/Common/src/Microsoft/Win32/SafeHandles/SafeX509NameHandle.Unix.cs

+ +++ /dev/null

+ @@ -1,30 +0,0 @@

+ -// Licensed to the .NET Foundation under one or more agreements.

+ -// The .NET Foundation licenses this file to you under the MIT license.

+ -// See the LICENSE file in the project root for more information.

+ -

+ -using System;

+ -using System.Security;

+ -using System.Runtime.InteropServices;

+ -

+ -namespace Microsoft.Win32.SafeHandles

+ -{

+ -    internal sealed class SafeX509NameHandle : SafeHandle

+ -    {

+ -        private SafeX509NameHandle() :

+ -            base(IntPtr.Zero, ownsHandle: true)

+ -        {

+ -        }

+ -

+ -        protected override bool ReleaseHandle()

+ -        {

+ -            Interop.Crypto.X509NameDestroy(handle);

+ -            SetHandle(IntPtr.Zero);

+ -            return true;

+ -        }

+ -

+ -        public override bool IsInvalid

+ -        {

+ -            get { return handle == IntPtr.Zero; }

+ -        }

+ -    }

+ -}

+ diff --git a/src/Common/src/System/Security/Cryptography/DerSequenceReader.cs b/src/Common/src/System/Security/Cryptography/DerSequenceReader.cs

+ index b68c9da093..68d9ac1bd2 100644

+ --- a/src/Common/src/System/Security/Cryptography/DerSequenceReader.cs

+ +++ b/src/Common/src/System/Security/Cryptography/DerSequenceReader.cs

+ @@ -30,6 +30,9 @@ namespace System.Security.Cryptography

+  

+          internal static DateTimeFormatInfo s_validityDateTimeFormatInfo;

+  

+ +        private static System.Text.Encoding s_utf8EncodingWithExceptionFallback;

+ +        private static System.Text.Encoding s_latin1Encoding;

+ +

+          private readonly byte[] _data;

+          private readonly int _end;

+          private int _position;

+ @@ -383,6 +386,38 @@ namespace System.Security.Cryptography

+              return TrimTrailingNulls(ia5String);

+          }

+  

+ +        internal string ReadT61String()

+ +        {

+ +            EatTag(DerTag.T61String);

+ +            int contentLength = EatLength();

+ +            string t61String;

+ +

+ +            // Technically the T.61 encoding (code page 20261) should be used here, but many

+ +            // implementations don't follow that and use different character sets. CryptoAPI

+ +            // on NetFX seems to interpret it as UTF-8 with fallback to ISO 8859-1. OpenSSL

+ +            // seems to interpret it as ISO 8859-1 with no support for UTF-8.

+ +            // https://github.com/dotnet/corefx/issues/27466

+ +

+ +            System.Text.Encoding utf8EncodingWithExceptionFallback = LazyInitializer.EnsureInitialized(

+ +                ref s_utf8EncodingWithExceptionFallback,

+ +                () => new UTF8Encoding(false, true));

+ +            System.Text.Encoding latin1Encoding = LazyInitializer.EnsureInitialized(

+ +                ref s_latin1Encoding,

+ +                () => System.Text.Encoding.GetEncoding("iso-8859-1"));

+ +            

+ +            try

+ +            {

+ +                t61String = utf8EncodingWithExceptionFallback.GetString(_data, _position, contentLength);

+ +            }

+ +            catch (DecoderFallbackException)

+ +            {

+ +                t61String = latin1Encoding.GetString(_data, _position, contentLength);

+ +            }

+ +            _position += contentLength;

+ +

+ +            return TrimTrailingNulls(t61String);

+ +        }

+ +

+          internal DateTime ReadX509Date()

+          {

+              byte tag = PeekTag();

+ diff --git a/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.cpp b/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.cpp

+ index 2195b74906..02cbfee4a2 100644

+ --- a/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.cpp

+ +++ b/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.cpp

+ @@ -14,6 +14,11 @@ extern "C" X509_NAME* CryptoNative_GetX509NameStackField(X509NameStack* sk, int3

+      return sk_X509_NAME_value(sk, loc);

+  }

+  

+ +/*

+ + * The following methods are kept around for compatiblity during servicing.

+ + * They are not used.

+ + */

+ +

+  extern "C" X509_NAME* CryptoNative_DecodeX509Name(const uint8_t* buf, int32_t len)

+  {

+      if (!buf || !len)

+ diff --git a/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.h b/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.h

+ index 76a77ccc1f..b24a794bbd 100644

+ --- a/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.h

+ +++ b/src/Native/Unix/System.Security.Cryptography.Native/pal_x509_name.h

+ @@ -18,6 +18,11 @@ Direct shim to sk_X509_NAME_value

+  */

+  extern "C" X509_NAME* CryptoNative_GetX509NameStackField(X509NameStack* sk, int32_t loc);

+  

+ +/*

+ + * The following methods are kept around for compatiblity during servicing.

+ + * They are not used.

+ + */

+ +

+  /*

+  Shims the d2i_X509_NAME method and makes it easier to invoke from managed code.

+  */

+ diff --git a/src/System.Net.Http/src/System.Net.Http.csproj b/src/System.Net.Http/src/System.Net.Http.csproj

+ index 3fa7cdd26f..66e5b8d5f8 100644

+ --- a/src/System.Net.Http/src/System.Net.Http.csproj

+ +++ b/src/System.Net.Http/src/System.Net.Http.csproj

+ @@ -530,9 +530,6 @@

+      <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\SafeX509Handles.Unix.cs">

+        <Link>Common\Microsoft\Win32\SafeHandles\SafeX509Handles.Unix.cs</Link>

+      </Compile>

+ -    <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\SafeX509NameHandle.Unix.cs">

+ -      <Link>Common\Microsoft\Win32\SafeHandles\SafeX509NameHandle.Unix.cs</Link>

+ -    </Compile>

+      <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\X509ExtensionSafeHandles.Unix.cs">

+        <Link>Common\Microsoft\Win32\SafeHandles\X509ExtensionSafeHandles.Unix.cs</Link>

+      </Compile>

+ diff --git a/src/System.Net.Security/src/System.Net.Security.csproj b/src/System.Net.Security/src/System.Net.Security.csproj

+ index 9dff20160e..bf8d773a4e 100644

+ --- a/src/System.Net.Security/src/System.Net.Security.csproj

+ +++ b/src/System.Net.Security/src/System.Net.Security.csproj

+ @@ -328,9 +328,6 @@

+      <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\SafeX509Handles.Unix.cs">

+        <Link>Common\Microsoft\Win32\SafeHandles\SafeX509Handles.Unix.cs</Link>

+      </Compile>

+ -    <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\SafeX509NameHandle.Unix.cs">

+ -      <Link>Common\Microsoft\Win32\SafeHandles\SafeX509NameHandle.Unix.cs</Link>

+ -    </Compile>

+      <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\X509ExtensionSafeHandles.Unix.cs">

+        <Link>Common\Microsoft\Win32\SafeHandles\X509ExtensionSafeHandles.Unix.cs</Link>

+      </Compile>

+ diff --git a/src/System.Security.Cryptography.Algorithms/src/System.Security.Cryptography.Algorithms.csproj b/src/System.Security.Cryptography.Algorithms/src/System.Security.Cryptography.Algorithms.csproj

+ index 9b1cb26508..fbe6f4c269 100644

+ --- a/src/System.Security.Cryptography.Algorithms/src/System.Security.Cryptography.Algorithms.csproj

+ +++ b/src/System.Security.Cryptography.Algorithms/src/System.Security.Cryptography.Algorithms.csproj

+ @@ -558,6 +558,7 @@

+      <Reference Include="System.Security.Cryptography.Encoding" />

+      <Reference Include="System.Security.Cryptography.Primitives" />

+      <Reference Include="System.Threading" />

+ +    <Reference Include="System.Text.Encoding.Extensions" />

+    </ItemGroup>

+    <ItemGroup Condition="'$(TargetsUnix)' == 'true'">

+      <Reference Include="System.Runtime.Numerics" />

+ diff --git a/src/System.Security.Cryptography.Encoding/src/System.Security.Cryptography.Encoding.csproj b/src/System.Security.Cryptography.Encoding/src/System.Security.Cryptography.Encoding.csproj

+ index 9681ef62e4..388d4f36a6 100644

+ --- a/src/System.Security.Cryptography.Encoding/src/System.Security.Cryptography.Encoding.csproj

+ +++ b/src/System.Security.Cryptography.Encoding/src/System.Security.Cryptography.Encoding.csproj

+ @@ -106,6 +106,7 @@

+      <Reference Include="System.Runtime.Extensions" />

+      <Reference Include="System.Runtime.InteropServices" />

+      <Reference Include="System.Security.Cryptography.Primitives" />

+ +    <Reference Include="System.Text.Encoding.Extensions" />

+    </ItemGroup>

+    <ItemGroup Condition=" '$(TargetsOSX)' == 'true' ">

+      <Reference Include="System.Runtime.Numerics" />

+ diff --git a/src/System.Security.Cryptography.OpenSsl/src/System.Security.Cryptography.OpenSsl.csproj b/src/System.Security.Cryptography.OpenSsl/src/System.Security.Cryptography.OpenSsl.csproj

+ index 095d62bc6d..3846bcad23 100644

+ --- a/src/System.Security.Cryptography.OpenSsl/src/System.Security.Cryptography.OpenSsl.csproj

+ +++ b/src/System.Security.Cryptography.OpenSsl/src/System.Security.Cryptography.OpenSsl.csproj

+ @@ -160,6 +160,7 @@

+      <Reference Include="System.Security.Cryptography.Algorithms" />

+      <Reference Include="System.Security.Cryptography.Encoding" />

+      <Reference Include="System.Security.Cryptography.Primitives" />

+ +    <Reference Include="System.Text.Encoding.Extensions" />

+      <Reference Include="System.Threading" />

+    </ItemGroup>

+    <Import Project="$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory), dir.targets))\dir.targets" />

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.ManagedDecode.cs b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.ManagedDecode.cs

+ index 094e95c20d..0285415ba3 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.ManagedDecode.cs

+ +++ b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.ManagedDecode.cs

+ @@ -127,7 +127,7 @@ namespace Internal.Cryptography.Pal

+                  }

+              }

+  

+ -            if (addTrailingDelimiter)

+ +            if (addTrailingDelimiter && decodedName.Length > 0)

+              {

+                  decodedName.Append(dnSeparator);

+              }

+ @@ -150,7 +150,7 @@ namespace Internal.Cryptography.Pal

+                  case DerSequenceReader.DerTag.UTF8String:

+                      return tavReader.ReadUtf8String();

+                  case DerSequenceReader.DerTag.T61String:

+ -                    return "";

+ +                    return tavReader.ReadT61String();

+                  default:

+                      throw new CryptographicException(SR.Cryptography_Der_Invalid_Encoding);

+              }

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.OpenSslDecode.cs b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.OpenSslDecode.cs

+ deleted file mode 100644

+ index 0c03283475..0000000000

+ --- a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.OpenSslDecode.cs

+ +++ /dev/null

+ @@ -1,123 +0,0 @@

+ -// Licensed to the .NET Foundation under one or more agreements.

+ -// The .NET Foundation licenses this file to you under the MIT license.

+ -// See the LICENSE file in the project root for more information.

+ -

+ -using System.Text;

+ -

+ -using Microsoft.Win32.SafeHandles;

+ -

+ -namespace Internal.Cryptography.Pal

+ -{

+ -    internal static partial class X500NameEncoder

+ -    {

+ -        private static string X500DistinguishedNameDecode(

+ -            byte[] encodedName,

+ -            bool printOid,

+ -            bool reverse,

+ -            bool quoteIfNeeded,

+ -            string dnSeparator,

+ -            string multiValueSeparator,

+ -            bool addTrailingDelimiter)

+ -        {

+ -            using (SafeX509NameHandle x509Name = Interop.Crypto.DecodeX509Name(encodedName, encodedName.Length))

+ -            {

+ -                if (x509Name.IsInvalid)

+ -                {

+ -                    Interop.Crypto.ErrClearError();

+ -                    return "";

+ -                }

+ -

+ -                // We need to allocate a StringBuilder to hold the data as we're building it, and there's the usual

+ -                // arbitrary process of choosing a number that's "big enough" to minimize reallocations without wasting

+ -                // too much space in the average case.

+ -                //

+ -                // So, let's look at an example of what our output might be.

+ -                //

+ -                // GitHub.com's SSL cert has a "pretty long" subject (partially due to the unknown OIDs):

+ -                //   businessCategory=Private Organization

+ -                //   1.3.6.1.4.1.311.60.2.1.3=US

+ -                //   1.3.6.1.4.1.311.60.2.1.2=Delaware

+ -                //   serialNumber=5157550

+ -                //   street=548 4th Street

+ -                //   postalCode=94107

+ -                //   C=US

+ -                //   ST=California

+ -                //   L=San Francisco

+ -                //   O=GitHub, Inc.

+ -                //   CN=github.com

+ -                //

+ -                // Which comes out to 228 characters using OpenSSL's default pretty-print

+ -                // (openssl x509 -in github.cer -text -noout)

+ -                // Throw in some "maybe-I-need-to-quote-this" quotes, and a couple of extra/extra-long O/OU values

+ -                // and round that up to the next programmer number, and you get that 512 should avoid reallocations

+ -                // in all but the most dire of cases.

+ -                StringBuilder decodedName = new StringBuilder(512);

+ -                int entryCount = Interop.Crypto.GetX509NameEntryCount(x509Name);

+ -                bool printSpacing = false;

+ -

+ -                for (int i = 0; i < entryCount; i++)

+ -                {

+ -                    int loc = reverse ? entryCount - i - 1 : i;

+ -

+ -                    using (SafeSharedX509NameEntryHandle nameEntry = Interop.Crypto.GetX509NameEntry(x509Name, loc))

+ -                    {

+ -                        Interop.Crypto.CheckValidOpenSslHandle(nameEntry);

+ -

+ -                        string thisOidValue;

+ -

+ -                        using (SafeSharedAsn1ObjectHandle oidHandle = Interop.Crypto.GetX509NameEntryOid(nameEntry))

+ -                        {

+ -                            thisOidValue = Interop.Crypto.GetOidValue(oidHandle);

+ -                        }

+ -

+ -                        if (printSpacing)

+ -                        {

+ -                            decodedName.Append(dnSeparator);

+ -                        }

+ -                        else

+ -                        {

+ -                            printSpacing = true;

+ -                        }

+ -

+ -                        if (printOid)

+ -                        {

+ -                            AppendOid(decodedName, thisOidValue);

+ -                        }

+ -

+ -                        string rdnValue;

+ -

+ -                        using (SafeSharedAsn1StringHandle valueHandle = Interop.Crypto.GetX509NameEntryData(nameEntry))

+ -                        {

+ -                            rdnValue = Interop.Crypto.Asn1StringToManagedString(valueHandle);

+ -                        }

+ -

+ -                        bool quote = quoteIfNeeded && NeedsQuoting(rdnValue);

+ -

+ -                        if (quote)

+ -                        {

+ -                            decodedName.Append('"');

+ -

+ -                            // If the RDN itself had a quote within it, that quote needs to be escaped

+ -                            // with another quote.

+ -                            rdnValue = rdnValue.Replace("\"", "\"\"");

+ -                        }

+ -

+ -                        decodedName.Append(rdnValue);

+ -

+ -                        if (quote)

+ -                        {

+ -                            decodedName.Append('"');

+ -                        }

+ -                    }

+ -                }

+ -

+ -                if (addTrailingDelimiter)

+ -                {

+ -                    decodedName.Append(dnSeparator);

+ -                }

+ -

+ -                return decodedName.ToString();

+ -            }

+ -        }

+ -    }

+ -}

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.cs b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.cs

+ index 56da9ae40c..005e09abe3 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.cs

+ +++ b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/X500NameEncoder.cs

+ @@ -40,7 +40,7 @@ namespace Internal.Cryptography.Pal

+              byte[] encodedName,

+              bool printOid,

+              X500DistinguishedNameFlags flags,

+ -            bool addTrailingDelimieter=false)

+ +            bool addTrailingDelimiter = false)

+          {

+              bool reverse = (flags & X500DistinguishedNameFlags.Reversed) == X500DistinguishedNameFlags.Reversed;

+              bool quoteIfNeeded = (flags & X500DistinguishedNameFlags.DoNotUseQuotes) != X500DistinguishedNameFlags.DoNotUseQuotes;

+ @@ -51,7 +51,8 @@ namespace Internal.Cryptography.Pal

+              {

+                  dnSeparator = "; ";

+              }

+ -            else if ((flags & X500DistinguishedNameFlags.UseNewLines) == X500DistinguishedNameFlags.UseNewLines)

+ +            // Explicit UseCommas has preference over explicit UseNewLines.

+ +            else if ((flags & (X500DistinguishedNameFlags.UseNewLines | X500DistinguishedNameFlags.UseCommas)) == X500DistinguishedNameFlags.UseNewLines)

+              {

+                  dnSeparator = Environment.NewLine;

+              }

+ @@ -73,7 +74,7 @@ namespace Internal.Cryptography.Pal

+                      quoteIfNeeded,

+                      dnSeparator,

+                      multiValueSparator,

+ -                    addTrailingDelimieter);

+ +                    addTrailingDelimiter);

+              }

+              catch (CryptographicException)

+              {

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj b/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj

+ index 20b0328943..3bdef009b9 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj

+ +++ b/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj

+ @@ -169,7 +169,6 @@

+      <Compile Include="Internal\Cryptography\Pal.Unix\PkcsFormatReader.cs" />

+      <Compile Include="Internal\Cryptography\Pal.Unix\SingleCertLoader.cs" />

+      <Compile Include="Internal\Cryptography\Pal.Unix\StorePal.cs" />

+ -    <Compile Include="Internal\Cryptography\Pal.Unix\X500NameEncoder.OpenSslDecode.cs" />

+      <Compile Include="Internal\Cryptography\Pal.Unix\X509Pal.cs" />

+      <Compile Include="Internal\Cryptography\Pal.Unix\X509Persistence.cs" />

+      <Compile Include="$(CommonPath)\Interop\Unix\Interop.Libraries.cs">

+ @@ -223,9 +222,6 @@

+      <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.X509Name.cs">

+        <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.X509Name.cs</Link>

+      </Compile>

+ -    <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.X509NameEntry.cs">

+ -      <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.X509NameEntry.cs</Link>

+ -    </Compile>

+      <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.X509Stack.cs">

+        <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.X509Stack.cs</Link>

+      </Compile>

+ @@ -274,9 +270,6 @@

+      <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\SafeX509Handles.Unix.cs">

+        <Link>Common\Microsoft\Win32\SafeHandles\SafeX509Handles.Unix.cs</Link>

+      </Compile>

+ -    <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\SafeX509NameHandle.Unix.cs">

+ -      <Link>Common\Microsoft\Win32\SafeHandles\SafeX509NameHandle.Unix.cs</Link>

+ -    </Compile>

+      <Compile Include="$(CommonPath)\Microsoft\Win32\SafeHandles\X509ExtensionSafeHandles.Unix.cs">

+        <Link>Common\Microsoft\Win32\SafeHandles\X509ExtensionSafeHandles.Unix.cs</Link>

+      </Compile>

+ @@ -390,7 +383,6 @@

+      <Compile Include="Internal\Cryptography\Pal.OSX\StorePal.ExportPal.cs" />

+      <Compile Include="Internal\Cryptography\Pal.OSX\StorePal.LoaderPal.cs" />

+      <Compile Include="Internal\Cryptography\Pal.OSX\X509Pal.cs" />

+ -    <Compile Include="Internal\Cryptography\Pal.Unix\X500NameEncoder.ManagedDecode.cs" />

+    </ItemGroup>

+    <ItemGroup Condition=" '$(TargetsUnix)' == 'true'">

+      <Compile Include="Internal\Cryptography\Pal.Unix\CertificatePolicy.cs" />

+ @@ -398,6 +390,7 @@

+      <Compile Include="Internal\Cryptography\Pal.Unix\ManagedCertificateFinder.cs" />

+      <Compile Include="Internal\Cryptography\Pal.Unix\ManagedX509ExtensionProcessor.cs" />

+      <Compile Include="Internal\Cryptography\Pal.Unix\X500NameEncoder.cs" />

+ +    <Compile Include="Internal\Cryptography\Pal.Unix\X500NameEncoder.ManagedDecode.cs" />

+    </ItemGroup>

+    <ItemGroup>

+      <Reference Include="System.Buffers" />

+ @@ -417,6 +410,7 @@

+      <Reference Include="System.Security.Cryptography.Algorithms" />

+      <Reference Include="System.Security.Cryptography.Encoding" />

+      <Reference Include="System.Security.Cryptography.Primitives" />

+ +    <Reference Include="System.Text.Encoding.Extensions" />

+      <Reference Include="System.Threading" />

+    </ItemGroup>

+    <ItemGroup Condition="'$(TargetsWindows)' == 'true'">

+ diff --git a/src/System.Security.Cryptography.X509Certificates/tests/X500DistinguishedNameTests.cs b/src/System.Security.Cryptography.X509Certificates/tests/X500DistinguishedNameTests.cs

+ index 027823ffbd..95ac1ed519 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/tests/X500DistinguishedNameTests.cs

+ +++ b/src/System.Security.Cryptography.X509Certificates/tests/X500DistinguishedNameTests.cs

+ @@ -126,6 +126,16 @@ namespace System.Security.Cryptography.X509Certificates.Tests

+  

+              Assert.Equal(notQuoted, dn.Decode(X500DistinguishedNameFlags.DoNotUseQuotes));

+          }

+ +        

+ +        [Theory]

+ +        [MemberData(nameof(T61Cases))]

+ +        public static void T61Strings(string expected, string hexEncoded)

+ +        {

+ +            byte[] encoded = hexEncoded.HexToByteArray();

+ +            X500DistinguishedName dn = new X500DistinguishedName(encoded);

+ +

+ +            Assert.Equal(expected, dn.Name);

+ +        }

+  

+          [Fact]

+          public static void PrintComplexReversed()

+ @@ -158,6 +168,22 @@ namespace System.Security.Cryptography.X509Certificates.Tests

+              Assert.EndsWith(expected, dn.Decode(X500DistinguishedNameFlags.None), StringComparison.Ordinal);

+          }

+  

+ +        [Fact]

+ +        public static void EdgeCaseEmptyFormat()

+ +        {

+ +            X500DistinguishedName dn = new X500DistinguishedName("");

+ +            Assert.Equal(String.Empty, dn.Format(true));

+ +            Assert.Equal(String.Empty, dn.Format(false));

+ +        }

+ +

+ +        [Fact]

+ +        public static void EdgeCaseUseCommaAndNewLines()

+ +        {

+ +            const string rname = "C=US, O=\"RSA Data Security, Inc.\", OU=Secure Server Certification Authority";

+ +            X500DistinguishedName dn = new X500DistinguishedName(rname, X500DistinguishedNameFlags.None);

+ +            Assert.Equal(rname, dn.Decode(X500DistinguishedNameFlags.UseCommas | X500DistinguishedNameFlags.UseNewLines));

+ +        }

+ +

+          public static readonly object[][] WhitespaceBeforeCases =

+          {

+              // Regular space.

+ @@ -386,6 +412,49 @@ namespace System.Security.Cryptography.X509Certificates.Tests

+              },

+          };

+  

+ +        public static readonly object[][] T61Cases =

+ +        {

+ +            // https://github.com/dotnet/corefx/issues/27466

+ +            new object[]

+ +            {

+ +                "CN=GrapeCity inc., OU=Tools Development, O=GrapeCity inc., " +

+ +                "L=Sendai Izumi-ku, S=Miyagi, C=JP",

+ +                "308186310b3009060355040613024a50310f300d060355040813064d69796167" +

+ +                "69311830160603550407130f53656e64616920497a756d692d6b753117301506" +

+ +                "0355040a140e47726170654369747920696e632e311a3018060355040b141154" +

+ +                "6f6f6c7320446576656c6f706d656e74311730150603550403140e4772617065" +

+ +                "4369747920696e632e"

+ +            },

+ +

+ +            // Mono test case taken from old bug report

+ +            new object[]

+ +            {

+ +                "SERIALNUMBER=CVR:13471967-UID:121212121212, E=vhm@use.test.dk, " +

+ +                "CN=Hedeby's M\u00f8belhandel - Salgsafdelingen, " + 

+ +                "O=Hedeby's M\u00f8belhandel // CVR:13471967, C=DK",

+ +                "3081B5310B300906035504061302444B312D302B060355040A14244865646562" +

+ +                "792773204DF862656C68616E64656C202F2F204356523A313334373139363731" +

+ +                "2F302D060355040314264865646562792773204DF862656C68616E64656C202D" +

+ +                "2053616C6773616664656C696E67656E311E301C06092A864886F70D01090116" +

+ +                "0F76686D407573652E746573742E646B312630240603550405131D4356523A31" +

+ +                "333437313936372D5549443A313231323132313231323132"

+ +            },

+ +

+ +            // Valid UTF-8 string is interpreted as UTF-8

+ +            new object[]

+ +            {

+ +                "C=\u00a2",

+ +                "300D310B300906035504061402C2A2"

+ +            },

+ +

+ +            // Invalid UTF-8 string with valid UTF-8 sequence is interpreted as ISO 8859-1

+ +            new object[]

+ +            {

+ +                "L=\u00c2\u00a2\u00f8",

+ +                "300E310C300A06035504071403C2A2F8"

+ +            },

+ +        };

+ +

+          private const string MicrosoftDotComSubject =

+              "3082010F31133011060B2B0601040182373C02010313025553311B3019060B2B" +

+              "0601040182373C0201020C0A57617368696E67746F6E311D301B060355040F13" +

+ -- 

+ 2.20.1

+ 

@@ -0,0 +1,355 @@ 

+ From 3fd578c3ccea681efd14aea07a0364b3baa3cca7 Mon Sep 17 00:00:00 2001

+ From: Filip Navara <filip.navara@gmail.com>

+ Date: Mon, 9 Jul 2018 19:08:50 +0200

+ Subject: [PATCH 2/7] Drop pal_asn1_print in favor of the managed code

+ 

+ * Drop pal_asn1_print in favor of the managed code that is already used on macOS.

+ 

+ * Add handling of T61 strings to ManagedCertificateFinder.DerStringToManagedString.

+ ---

+  .../Interop.ASN1.Print.cs                     | 144 ------------------

+  .../Win32/SafeHandles/Asn1SafeHandles.Unix.cs |  28 ----

+  .../pal_asn1_print.cpp                        |   5 +

+  .../pal_asn1_print.h                          |   5 +

+  .../Internal/Cryptography/Pal.OSX/FindPal.cs  |  28 ----

+  .../Pal.Unix/ManagedCertificateFinder.cs      |  31 +++-

+  .../Pal.Unix/OpenSslCertificateFinder.cs      |   5 -

+  ...urity.Cryptography.X509Certificates.csproj |   3 -

+  8 files changed, 40 insertions(+), 209 deletions(-)

+  delete mode 100644 src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.Print.cs

+ 

+ diff --git a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.Print.cs b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.Print.cs

+ deleted file mode 100644

+ index 12199563c8..0000000000

+ --- a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.ASN1.Print.cs

+ +++ /dev/null

+ @@ -1,144 +0,0 @@

+ -// Licensed to the .NET Foundation under one or more agreements.

+ -// The .NET Foundation licenses this file to you under the MIT license.

+ -// See the LICENSE file in the project root for more information.

+ -

+ -using System;

+ -using System.Runtime.InteropServices;

+ -using System.Text;

+ -using Microsoft.Win32.SafeHandles;

+ -

+ -internal static partial class Interop

+ -{

+ -    internal static partial class Crypto

+ -    {

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_DecodeAsn1TypeBytes")]

+ -        private static extern SafeAsn1StringHandle DecodeAsn1TypeBytes(byte[] buf, int len, Asn1StringTypeFlags flags);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_Asn1StringPrintEx")]

+ -        private static extern int Asn1StringPrintEx(SafeBioHandle bio, SafeAsn1StringHandle str, Asn1StringPrintFlags flags);

+ -

+ -        [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_Asn1StringPrintEx")]

+ -        private static extern int Asn1StringPrintEx(SafeBioHandle bio, SafeSharedAsn1StringHandle str, Asn1StringPrintFlags flags);

+ -

+ -        internal static string DerStringToManagedString(byte[] derString)

+ -        {

+ -            SafeAsn1StringHandle asn1String = DecodeAsn1TypeBytes(derString, derString.Length, AnyTextStringType);

+ -

+ -            if (asn1String.IsInvalid)

+ -            {

+ -                Interop.Crypto.ErrClearError();

+ -                return null;

+ -            }

+ -

+ -            using (asn1String)

+ -            {

+ -                return Asn1StringToManagedString(

+ -                    asn1String,

+ -                    (bio, str, flags) => Asn1StringPrintEx(bio, str, flags));

+ -            }

+ -        }

+ -

+ -        internal static string Asn1StringToManagedString(SafeSharedAsn1StringHandle asn1String)

+ -        {

+ -            CheckValidOpenSslHandle(asn1String);

+ -

+ -            return Asn1StringToManagedString(

+ -                asn1String,

+ -                (bio, str, flags) => Asn1StringPrintEx(bio, str, flags));

+ -        }

+ -

+ -        private static string Asn1StringToManagedString<THandle>(

+ -            THandle asn1String,

+ -            Func<SafeBioHandle, THandle, Asn1StringPrintFlags, int> asn1StringPrintEx)

+ -        {

+ -            byte[] utf8Bytes;

+ -

+ -            using (SafeBioHandle bio = CreateMemoryBio())

+ -            {

+ -                CheckValidOpenSslHandle(bio);

+ -                

+ -                int len = asn1StringPrintEx(bio, asn1String, Asn1StringPrintFlags.ASN1_STRFLGS_UTF8_CONVERT);

+ -

+ -                if (len < 0)

+ -                {

+ -                    throw CreateOpenSslCryptographicException();

+ -                }

+ -

+ -                if (len == 0)

+ -                {

+ -                    return "";

+ -                }

+ -

+ -                int bioSize = GetMemoryBioSize(bio);

+ -                utf8Bytes = new byte[bioSize + 1];

+ -

+ -                int read = BioRead(bio, utf8Bytes, utf8Bytes.Length);

+ -

+ -                if (read < 0)

+ -                {

+ -                    throw CreateOpenSslCryptographicException();

+ -                }

+ -            }

+ -

+ -            int nonNullCount = utf8Bytes.Length;

+ -

+ -            if (utf8Bytes[utf8Bytes.Length - 1] == 0)

+ -            {

+ -                for (int i = utf8Bytes.Length - 1; i >= 0; i--)

+ -                {

+ -                    if (utf8Bytes[i] != 0)

+ -                    {

+ -                        break;

+ -                    }

+ -

+ -                    nonNullCount = i;

+ -                }

+ -            }

+ -

+ -            return Encoding.UTF8.GetString(utf8Bytes, 0, nonNullCount);

+ -        }

+ -

+ -        [Flags]

+ -        private enum Asn1StringPrintFlags : ulong

+ -        {

+ -            ASN1_STRFLGS_UTF8_CONVERT = 0x10,

+ -        }

+ -

+ -        [Flags]

+ -        private enum Asn1StringTypeFlags

+ -        {

+ -            B_ASN1_NUMERICSTRING = 0x0001,

+ -            B_ASN1_PRINTABLESTRING = 0x0002,

+ -            B_ASN1_T61STRING = 0x0004,

+ -            B_ASN1_VIDEOTEXSTRING = 0x0008,

+ -            B_ASN1_IA5STRING = 0x0010,

+ -            B_ASN1_GRAPHICSTRING = 0x0020,

+ -            B_ASN1_VISIBLESTRING = 0x0040,

+ -            B_ASN1_GENERALSTRING = 0x0080,

+ -            B_ASN1_UNIVERSALSTRING = 0x0100,

+ -            B_ASN1_OCTET_STRING = 0x0200,

+ -            B_ASN1_BIT_STRING = 0x0400,

+ -            B_ASN1_BMPSTRING = 0x0800,

+ -            B_ASN1_UNKNOWN = 0x1000,

+ -            B_ASN1_UTF8STRING = 0x2000,

+ -            B_ASN1_UTCTIME = 0x4000,

+ -            B_ASN1_GENERALIZEDTIME = 0x8000,

+ -            B_ASN1_SEQUENCE = 0x10000,

+ -        }

+ -

+ -        private const Asn1StringTypeFlags AnyTextStringType =

+ -            Asn1StringTypeFlags.B_ASN1_NUMERICSTRING |

+ -            Asn1StringTypeFlags.B_ASN1_PRINTABLESTRING |

+ -            Asn1StringTypeFlags.B_ASN1_T61STRING |

+ -            Asn1StringTypeFlags.B_ASN1_VIDEOTEXSTRING |

+ -            Asn1StringTypeFlags.B_ASN1_IA5STRING |

+ -            Asn1StringTypeFlags.B_ASN1_GRAPHICSTRING |

+ -            Asn1StringTypeFlags.B_ASN1_VISIBLESTRING |

+ -            Asn1StringTypeFlags.B_ASN1_GENERALSTRING |

+ -            Asn1StringTypeFlags.B_ASN1_UNIVERSALSTRING |

+ -            Asn1StringTypeFlags.B_ASN1_BMPSTRING |

+ -            Asn1StringTypeFlags.B_ASN1_UTF8STRING |

+ -            Asn1StringTypeFlags.B_ASN1_UTCTIME |

+ -            Asn1StringTypeFlags.B_ASN1_GENERALIZEDTIME;

+ -    }

+ -}

+ diff --git a/src/Common/src/Microsoft/Win32/SafeHandles/Asn1SafeHandles.Unix.cs b/src/Common/src/Microsoft/Win32/SafeHandles/Asn1SafeHandles.Unix.cs

+ index 3fdde3f602..ddf413110c 100644

+ --- a/src/Common/src/Microsoft/Win32/SafeHandles/Asn1SafeHandles.Unix.cs

+ +++ b/src/Common/src/Microsoft/Win32/SafeHandles/Asn1SafeHandles.Unix.cs

+ @@ -68,34 +68,6 @@ namespace Microsoft.Win32.SafeHandles

+          }

+      }

+  

+ -    internal sealed class SafeAsn1StringHandle : SafeHandle

+ -    {

+ -        private SafeAsn1StringHandle() :

+ -            base(IntPtr.Zero, ownsHandle: true)

+ -        {

+ -        }

+ -

+ -        protected override bool ReleaseHandle()

+ -        {

+ -            Interop.Crypto.Asn1StringFree(handle);

+ -            SetHandle(IntPtr.Zero);

+ -            return true;

+ -        }

+ -

+ -        public override bool IsInvalid

+ -        {

+ -            get { return handle == IntPtr.Zero; }

+ -        }

+ -    }

+ -

+ -    internal sealed class SafeSharedAsn1StringHandle : SafeInteriorHandle

+ -    {

+ -        private SafeSharedAsn1StringHandle() :

+ -            base(IntPtr.Zero, ownsHandle: true)

+ -        {

+ -        }

+ -    }

+ -

+      internal sealed class SafeSharedAsn1IntegerHandle : SafeInteriorHandle

+      {

+          private SafeSharedAsn1IntegerHandle() :

+ diff --git a/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.cpp b/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.cpp

+ index ffbfef980d..01a544f5e9 100644

+ --- a/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.cpp

+ +++ b/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.cpp

+ @@ -4,6 +4,11 @@

+  

+  #include "pal_asn1_print.h"

+  

+ +/*

+ + * This file is completely unused. It's kept around for compatiblity between

+ + * servicing updates.

+ + */

+ +

+  static_assert(PAL_B_ASN1_NUMERICSTRING == B_ASN1_NUMERICSTRING, "");

+  static_assert(PAL_B_ASN1_PRINTABLESTRING == B_ASN1_PRINTABLESTRING, "");

+  static_assert(PAL_B_ASN1_T61STRING == B_ASN1_T61STRING, "");

+ diff --git a/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.h b/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.h

+ index 982506e420..71205cc13c 100644

+ --- a/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.h

+ +++ b/src/Native/Unix/System.Security.Cryptography.Native/pal_asn1_print.h

+ @@ -5,6 +5,11 @@

+  #include "pal_types.h"

+  #include "opensslshim.h"

+  

+ +/*

+ + * This file is completely unused. It's kept around for compatiblity between

+ + * servicing updates.

+ + */

+ +

+  /*

+  Flags for the 'type' parameter of CryptoNative_DecodeAsn1TypeBytes.

+  */

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.OSX/FindPal.cs b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.OSX/FindPal.cs

+ index b2d2846c1a..e66bad7e76 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.OSX/FindPal.cs

+ +++ b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.OSX/FindPal.cs

+ @@ -22,34 +22,6 @@ namespace Internal.Cryptography.Pal

+              {

+              }

+  

+ -            protected override string DerStringToManagedString(byte[] anyString)

+ -            {

+ -                DerSequenceReader reader = DerSequenceReader.CreateForPayload(anyString);

+ -

+ -                var tag = (DerSequenceReader.DerTag)reader.PeekTag();

+ -                string value = null;

+ -

+ -                switch (tag)

+ -                {

+ -                    case DerSequenceReader.DerTag.BMPString:

+ -                        value = reader.ReadBMPString();

+ -                        break;

+ -                    case DerSequenceReader.DerTag.IA5String:

+ -                        value = reader.ReadIA5String();

+ -                        break;

+ -                    case DerSequenceReader.DerTag.PrintableString:

+ -                        value = reader.ReadPrintableString();

+ -                        break;

+ -                    case DerSequenceReader.DerTag.UTF8String:

+ -                        value = reader.ReadUtf8String();

+ -                        break;

+ -

+ -                    // Ignore anything we don't know how to read.

+ -                }

+ -

+ -                return value;

+ -            }

+ -

+              protected override byte[] GetSubjectPublicKeyInfo(X509Certificate2 cert)

+              {

+                  AppleCertificatePal pal = (AppleCertificatePal)cert.Pal;

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/ManagedCertificateFinder.cs b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/ManagedCertificateFinder.cs

+ index ebc5ee48d1..a70bf1488d 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/ManagedCertificateFinder.cs

+ +++ b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/ManagedCertificateFinder.cs

+ @@ -123,7 +123,36 @@ namespace Internal.Cryptography.Pal

+              FindCore(cert => cert.NotAfter < normalized);

+          }

+  

+ -        protected abstract string DerStringToManagedString(byte[] anyString);

+ +        private string DerStringToManagedString(byte[] anyString)

+ +        {

+ +            DerSequenceReader reader = DerSequenceReader.CreateForPayload(anyString);

+ +

+ +            var tag = (DerSequenceReader.DerTag)reader.PeekTag();

+ +            string value = null;

+ +

+ +            switch (tag)

+ +            {

+ +                case DerSequenceReader.DerTag.BMPString:

+ +                    value = reader.ReadBMPString();

+ +                    break;

+ +                case DerSequenceReader.DerTag.IA5String:

+ +                    value = reader.ReadIA5String();

+ +                    break;

+ +                case DerSequenceReader.DerTag.PrintableString:

+ +                    value = reader.ReadPrintableString();

+ +                    break;

+ +                case DerSequenceReader.DerTag.UTF8String:

+ +                    value = reader.ReadUtf8String();

+ +                    break;

+ +                case DerSequenceReader.DerTag.T61String:

+ +                    value = reader.ReadT61String();

+ +                    break;

+ +

+ +                // Ignore anything we don't know how to read.

+ +            }

+ +

+ +            return value;

+ +        }

+  

+          public void FindByTemplateName(string templateName)

+          {

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/OpenSslCertificateFinder.cs b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/OpenSslCertificateFinder.cs

+ index 720c298994..717ee3753b 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/OpenSslCertificateFinder.cs

+ +++ b/src/System.Security.Cryptography.X509Certificates/src/Internal/Cryptography/Pal.Unix/OpenSslCertificateFinder.cs

+ @@ -13,11 +13,6 @@ namespace Internal.Cryptography.Pal

+          {

+          }

+  

+ -        protected override string DerStringToManagedString(byte[] anyString)

+ -        {

+ -            return Interop.Crypto.DerStringToManagedString(anyString);

+ -        }

+ -

+          protected override byte[] GetSubjectPublicKeyInfo(X509Certificate2 cert)

+          {

+              OpenSslX509CertificateReader certPal = (OpenSslX509CertificateReader)cert.Pal;

+ diff --git a/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj b/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj

+ index 3bdef009b9..5d9e22a7f3 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj

+ +++ b/src/System.Security.Cryptography.X509Certificates/src/System.Security.Cryptography.X509Certificates.csproj

+ @@ -186,9 +186,6 @@

+      <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.ASN1.GetIntegerBytes.cs">

+        <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.ASN1.GetIntegerBytes.cs</Link>

+      </Compile>

+ -    <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.ASN1.Print.cs">

+ -      <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.ASN1.Print.cs</Link>

+ -    </Compile>

+      <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.Bignum.cs">

+        <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.Bignum.cs</Link>

+      </Compile>

+ -- 

+ 2.20.1

+ 

The added file is too large to be shown here, see it at: 0003-Add-hybrid-support-for-OpenSSL-1.0-and-1.1.patch
@@ -0,0 +1,30 @@ 

+ From fc9d3560b4a84bab784574cfe9700125065713c3 Mon Sep 17 00:00:00 2001

+ From: Omair Majid <omajid@redhat.com>

+ Date: Sat, 22 Dec 2018 15:06:18 -0500

+ Subject: [PATCH 4/7] Use HMAC_CTX_free() instead of free() on a HMAC_CTX*

+  (#34222)

+ 

+ This is a leftover from before the OpenSSL 1.0/1.1 hybridization. There

+ was no HMAC_CTX_free() in 1.0.

+ 

+ Fixes #34210

+ ---

+  .../Unix/System.Security.Cryptography.Native/pal_hmac.cpp       | 2 +-

+  1 file changed, 1 insertion(+), 1 deletion(-)

+ 

+ diff --git a/src/Native/Unix/System.Security.Cryptography.Native/pal_hmac.cpp b/src/Native/Unix/System.Security.Cryptography.Native/pal_hmac.cpp

+ index 539dc07683..979750cb40 100644

+ --- a/src/Native/Unix/System.Security.Cryptography.Native/pal_hmac.cpp

+ +++ b/src/Native/Unix/System.Security.Cryptography.Native/pal_hmac.cpp

+ @@ -31,7 +31,7 @@ extern "C" HMAC_CTX* CryptoNative_HmacCreate(const uint8_t* key, int32_t keyLen,

+  

+      if (!ret)

+      {

+ -        free(ctx);

+ +        HMAC_CTX_free(ctx);

+          return nullptr;

+      }

+  

+ -- 

+ 2.20.1

+ 

@@ -0,0 +1,43 @@ 

+ From 60e4274ff758af0d68ba585e7286a5cddb7c4778 Mon Sep 17 00:00:00 2001

+ From: Omair Majid <omajid@redhat.com>

+ Date: Thu, 10 Jan 2019 18:37:24 -0500

+ Subject: [PATCH 5/7] Prefer OpenSSL 1.0.x for portable builds

+ 

+ Future releases of .NET Core prefer OpenSSL 1.1.x. For the sake of

+ compatiblity, 2.x releases should prefer 1.0.x.

+ ---

+  .../opensslshim.cpp                                   | 11 +++++------

+  1 file changed, 5 insertions(+), 6 deletions(-)

+ 

+ diff --git a/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.cpp b/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.cpp

+ index 585f7ac23f..c98869a94e 100644

+ --- a/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.cpp

+ +++ b/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.cpp

+ @@ -47,12 +47,6 @@ bool OpenLibrary()

+          libssl = dlopen(soName, RTLD_LAZY);

+      }

+  

+ -    if (libssl == nullptr)

+ -    {

+ -        // Prefer OpenSSL 1.1.x

+ -        libssl = dlopen("libssl.so.1.1", RTLD_LAZY);

+ -    }

+ -

+      if (libssl == nullptr)

+      {

+          // Debian 9 has dropped support for SSLv3 and so they have bumped their soname. Let's try it

+ @@ -73,6 +67,11 @@ bool OpenLibrary()

+          libssl = dlopen("libssl.so.10", RTLD_LAZY);

+      }

+  

+ +    if (libssl == nullptr)

+ +    {

+ +        libssl = dlopen("libssl.so.1.1", RTLD_LAZY);

+ +    }

+ +

+      return libssl != nullptr;

+  }

+  

+ -- 

+ 2.20.1

+ 

@@ -0,0 +1,350 @@ 

+ From dfa0c242cd9b329554971cf80c094e8f58d756e3 Mon Sep 17 00:00:00 2001

+ From: Jeremy Barton <jbarton@microsoft.com>

+ Date: Wed, 26 Sep 2018 15:35:35 -0700

+ Subject: [PATCH 6/7] Check for the specific in-use version of OpenSSL when

+  working with libcurl

+ 

+ Rather than check a generic 1.0/1.1, test for the specific library version that

+ the crypto shim has loaded.  This makes things work when both libcurl

+ and the crypto shim are using OpenSSL 1.1 and also prevents a state where two

+ different copies of the library (at different patch versions) are utilized.

+ ---

+  .../Interop.Initialization.cs                 |  8 +--

+  .../Interop.VersionInfo.cs                    | 44 +++++++++++-

+  .../Interop.OpenSslVersion.cs                 |  2 +-

+  .../src/System.Net.Http.csproj                |  3 +

+  .../CurlHandler.SslProvider.Linux.cs          |  8 +--

+  .../FunctionalTests/HttpClientEKUTest.cs      |  2 +-

+  ...ttpClientHandlerTest.ClientCertificates.cs | 14 +---

+  ...ientHandlerTest.ServerCertificates.Unix.cs |  9 +--

+  ...HttpClientHandlerTest.SslProtocols.Unix.cs |  3 +-

+  .../System.Net.Http.Functional.Tests.csproj   |  3 +-

+  .../tests/FunctionalTests/TestHelper.cs       | 69 +++++++++++++++++++

+  11 files changed, 130 insertions(+), 35 deletions(-)

+ 

+ diff --git a/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.Initialization.cs b/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.Initialization.cs

+ index eef56ec0b3..d6bcc8df02 100644

+ --- a/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.Initialization.cs

+ +++ b/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.Initialization.cs

+ @@ -26,11 +26,11 @@ internal static partial class Interop

+  #if !SYSNETHTTP_NO_OPENSSL

+              string opensslVersion = Interop.Http.GetSslVersionDescription();

+              if (string.IsNullOrEmpty(opensslVersion) ||

+ -                opensslVersion.IndexOf(Interop.Http.OpenSsl10Description, StringComparison.OrdinalIgnoreCase) != -1)

+ +                opensslVersion.IndexOf(Interop.Http.OpenSslDescriptionPrefix, StringComparison.OrdinalIgnoreCase) != -1)

+              {

+ -                // CURL uses OpenSSL which we must initialize first to guarantee thread-safety

+ -                // Only initialize for OpenSSL/1.0, any newer versions may have mismatched

+ -                // pointers, resulting in segfaults.

+ +                // CURL uses OpenSSL which we must initialize first to guarantee thread-safety.

+ +                // We'll wake up whatever OpenSSL we're going to run against, but might later determine that

+ +                // they aren't compatible.

+                  CryptoInitializer.Initialize();

+              }

+  #endif

+ diff --git a/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.VersionInfo.cs b/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.VersionInfo.cs

+ index 1899fd0af3..8175159b6f 100644

+ --- a/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.VersionInfo.cs

+ +++ b/src/Common/src/Interop/Unix/System.Net.Http.Native/Interop.VersionInfo.cs

+ @@ -3,6 +3,7 @@

+  // See the LICENSE file in the project root for more information.

+  

+  using System;

+ +using System.Diagnostics;

+  using System.Runtime.InteropServices;

+  

+  internal static partial class Interop

+ @@ -47,8 +48,49 @@ internal static partial class Interop

+          [DllImport(Libraries.HttpNative, EntryPoint = "HttpNative_GetSslVersionDescription")]

+          internal static extern string GetSslVersionDescription();

+  

+ -        internal const string OpenSsl10Description = "openssl/1.0";

+ +        internal const string OpenSslDescriptionPrefix = "OpenSSL/";

+          internal const string SecureTransportDescription = "SecureTransport";

+          internal const string LibreSslDescription = "LibreSSL";

+ +

+ +#if !SYSNETHTTP_NO_OPENSSL

+ +        private static readonly Lazy<string> s_requiredOpenSslDescription =

+ +            new Lazy<string>(() => DetermineRequiredOpenSslDescription());

+ +

+ +        private static readonly Lazy<bool> s_hasMatchingOpenSsl =

+ +            new Lazy<bool>(() => RequiredOpenSslDescription == GetSslVersionDescription());

+ +

+ +        internal static string RequiredOpenSslDescription => s_requiredOpenSslDescription.Value;

+ +        internal static bool HasMatchingOpenSslVersion => s_hasMatchingOpenSsl.Value;

+ +

+ +        private static string DetermineRequiredOpenSslDescription()

+ +        {

+ +            string versionDescription = Interop.OpenSsl.OpenSslVersionDescription();

+ +            var version = versionDescription.AsSpan();

+ +

+ +            // OpenSSL version description looks like this:

+ +            //

+ +            // OpenSSL 1.1.1 FIPS  11 Sep 2018

+ +            //

+ +            // libcurl's OpenSSL vtls backend ignores status in the version string.

+ +            // Major, minor, and fix are encoded (by libcurl) as unpadded hex

+ +            // (0 => "0", 15 => "f", 16 => "10").

+ +            //

+ +            // Patch is encoded as in the way OpenSSL would do it.

+ +

+ +            string prefix = "OpenSSL ";

+ +            if (version.StartsWith(prefix))

+ +            {

+ +                version = version.Slice(prefix.Length).Trim();

+ +            }

+ +            int end = version.IndexOf(" ");

+ +            if (end != -1)

+ +            {

+ +                version = version.Slice(0, end);

+ +            }

+ +            version = version.Trim();

+ +

+ +            return $"{OpenSslDescriptionPrefix}{version.ToString()}";

+ +        }

+ +#endif

+      }

+  }

+ diff --git a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.OpenSslVersion.cs b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.OpenSslVersion.cs

+ index 70805706ef..13c2339ce6 100644

+ --- a/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.OpenSslVersion.cs

+ +++ b/src/Common/src/Interop/Unix/System.Security.Cryptography.Native/Interop.OpenSslVersion.cs

+ @@ -12,7 +12,7 @@ internal static partial class Interop

+          private static Version s_opensslVersion;

+  

+          [DllImport(Libraries.CryptoNative, EntryPoint = "CryptoNative_SSLEayVersion")]

+ -        private static extern string OpenSslVersionDescription();

+ +        internal static extern string OpenSslVersionDescription();

+  

+          internal static Version OpenSslVersion

+          {

+ diff --git a/src/System.Net.Http/src/System.Net.Http.csproj b/src/System.Net.Http/src/System.Net.Http.csproj

+ index 66e5b8d5f8..34b4d22e15 100644

+ --- a/src/System.Net.Http/src/System.Net.Http.csproj

+ +++ b/src/System.Net.Http/src/System.Net.Http.csproj

+ @@ -500,6 +500,9 @@

+      <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.Crypto.cs">

+        <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.Crypto.cs</Link>

+      </Compile>

+ +    <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.OpenSslVersion.cs">

+ +      <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.OpenSslVersion.cs</Link>

+ +    </Compile>

+      <Compile Include="$(CommonPath)\Interop\Unix\System.Security.Cryptography.Native\Interop.Ssl.cs">

+        <Link>Common\Interop\Unix\System.Security.Cryptography.Native\Interop.Ssl.cs</Link>

+      </Compile>

+ diff --git a/src/System.Net.Http/src/System/Net/Http/CurlHandler/CurlHandler.SslProvider.Linux.cs b/src/System.Net.Http/src/System/Net/Http/CurlHandler/CurlHandler.SslProvider.Linux.cs

+ index 55e583e137..2fdcde686d 100644

+ --- a/src/System.Net.Http/src/System/Net/Http/CurlHandler/CurlHandler.SslProvider.Linux.cs

+ +++ b/src/System.Net.Http/src/System/Net/Http/CurlHandler/CurlHandler.SslProvider.Linux.cs

+ @@ -55,7 +55,7 @@ namespace System.Net.Http

+  

+                  // Configure the options.  Our best support is when targeting OpenSSL/1.0.  For other backends,

+                  // we fall back to a minimal amount of support, and may throw a PNSE based on the options requested.

+ -                if (CurlSslVersionDescription.IndexOf(Interop.Http.OpenSsl10Description, StringComparison.OrdinalIgnoreCase) != -1)

+ +                if (Interop.Http.HasMatchingOpenSslVersion)

+                  {

+                      // Register the callback with libcurl.  We need to register even if there's no user-provided

+                      // server callback and even if there are no client certificates, because we support verifying

+ @@ -169,12 +169,12 @@ namespace System.Net.Http

+              {

+                  if (certProvider != null)

+                  {

+ -                    throw new PlatformNotSupportedException(SR.Format(SR.net_http_libcurl_clientcerts_notsupported_sslbackend, CurlVersionDescription, CurlSslVersionDescription, Interop.Http.OpenSsl10Description));

+ +                    throw new PlatformNotSupportedException(SR.Format(SR.net_http_libcurl_clientcerts_notsupported_sslbackend, CurlVersionDescription, CurlSslVersionDescription, Interop.Http.RequiredOpenSslDescription));

+                  }

+  

+                  if (easy._handler.CheckCertificateRevocationList)

+                  {

+ -                    throw new PlatformNotSupportedException(SR.Format(SR.net_http_libcurl_revocation_notsupported_sslbackend, CurlVersionDescription, CurlSslVersionDescription, Interop.Http.OpenSsl10Description));

+ +                    throw new PlatformNotSupportedException(SR.Format(SR.net_http_libcurl_revocation_notsupported_sslbackend, CurlVersionDescription, CurlSslVersionDescription, Interop.Http.RequiredOpenSslDescription));

+                  }

+  

+                  if (easy._handler.ServerCertificateCustomValidationCallback != null)

+ @@ -187,7 +187,7 @@ namespace System.Net.Http

+                      }

+                      else

+                      {

+ -                        throw new PlatformNotSupportedException(SR.Format(SR.net_http_libcurl_callback_notsupported_sslbackend, CurlVersionDescription, CurlSslVersionDescription, Interop.Http.OpenSsl10Description));

+ +                        throw new PlatformNotSupportedException(SR.Format(SR.net_http_libcurl_callback_notsupported_sslbackend, CurlVersionDescription, CurlSslVersionDescription, Interop.Http.RequiredOpenSslDescription));

+                      }

+                  }

+                  else

+ diff --git a/src/System.Net.Http/tests/FunctionalTests/HttpClientEKUTest.cs b/src/System.Net.Http/tests/FunctionalTests/HttpClientEKUTest.cs

+ index c6badc770e..9ac90390e3 100644

+ --- a/src/System.Net.Http/tests/FunctionalTests/HttpClientEKUTest.cs

+ +++ b/src/System.Net.Http/tests/FunctionalTests/HttpClientEKUTest.cs

+ @@ -22,7 +22,7 @@ namespace System.Net.Http.Functional.Tests

+  #if TargetsWindows

+              true;

+  #else

+ -            Interop.Http.GetSslVersionDescription()?.StartsWith(Interop.Http.OpenSsl10Description, StringComparison.OrdinalIgnoreCase) ?? false;

+ +            TestHelper.NativeHandlerSupportsSslConfiguration();

+  #endif

+  

+          private static bool CanTestCertificates =>

+ diff --git a/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ClientCertificates.cs b/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ClientCertificates.cs

+ index 78d0fdb09f..217726db64 100644

+ --- a/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ClientCertificates.cs

+ +++ b/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ClientCertificates.cs

+ @@ -319,19 +319,7 @@ namespace System.Net.Http.Functional.Tests

+  #if TargetsWindows

+                  return true;

+  #else

+ -                if (UseSocketsHttpHandler)

+ -                {

+ -                    return true;

+ -                }

+ -

+ -                if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX))

+ -                {

+ -                    return false;

+ -                }

+ -

+ -                // For other Unix-based systems it's true if (and only if) the openssl backend

+ -                // is used with libcurl.

+ -                return (Interop.Http.GetSslVersionDescription()?.StartsWith(Interop.Http.OpenSsl10Description, StringComparison.OrdinalIgnoreCase) ?? false);

+ +                return TestHelper.NativeHandlerSupportsSslConfiguration();

+  #endif

+              }

+          }

+ diff --git a/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ServerCertificates.Unix.cs b/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ServerCertificates.Unix.cs

+ index d19a63f598..eb38f93615 100644

+ --- a/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ServerCertificates.Unix.cs

+ +++ b/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.ServerCertificates.Unix.cs

+ @@ -58,14 +58,7 @@ namespace System.Net.Http.Functional.Tests

+                      return true;

+                  }

+  

+ -                if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX))

+ -                {

+ -                    return false;

+ -                }

+ -

+ -                // For other Unix-based systems it's true if (and only if) the openssl backend

+ -                // is used with libcurl.

+ -                return (Interop.Http.GetSslVersionDescription()?.StartsWith(Interop.Http.OpenSsl10Description, StringComparison.OrdinalIgnoreCase) ?? false);

+ +                return TestHelper.NativeHandlerSupportsSslConfiguration();

+              }

+          }

+  

+ diff --git a/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.SslProtocols.Unix.cs b/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.SslProtocols.Unix.cs

+ index 615f2cb4fa..e7631e3940 100644

+ --- a/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.SslProtocols.Unix.cs

+ +++ b/src/System.Net.Http/tests/FunctionalTests/HttpClientHandlerTest.SslProtocols.Unix.cs

+ @@ -17,7 +17,6 @@ namespace System.Net.Http.Functional.Tests

+      public abstract partial class HttpClientHandler_SslProtocols_Test

+      {

+          private bool BackendSupportsSslConfiguration =>

+ -            UseSocketsHttpHandler ||

+ -            (Interop.Http.GetSslVersionDescription()?.StartsWith(Interop.Http.OpenSsl10Description, StringComparison.OrdinalIgnoreCase) ?? false);

+ +            UseSocketsHttpHandler || TestHelper.NativeHandlerSupportsSslConfiguration();

+      }

+  }

+ diff --git a/src/System.Net.Http/tests/FunctionalTests/System.Net.Http.Functional.Tests.csproj b/src/System.Net.Http/tests/FunctionalTests/System.Net.Http.Functional.Tests.csproj

+ index 68c87c2b6e..b3b9d2437d 100644

+ --- a/src/System.Net.Http/tests/FunctionalTests/System.Net.Http.Functional.Tests.csproj

+ +++ b/src/System.Net.Http/tests/FunctionalTests/System.Net.Http.Functional.Tests.csproj

+ @@ -5,6 +5,7 @@

+      <ProjectGuid>{C85CF035-7804-41FF-9557-48B7C948B58D}</ProjectGuid>

+      <DefineConstants Condition="'$(TargetGroup)'=='netcoreapp'">$(DefineConstants);netcoreapp</DefineConstants>

+      <DefineConstants Condition="'$(TargetsWindows)'=='true'">$(DefineConstants);TargetsWindows</DefineConstants>

+ +    <DefineConstants>$(DefineConstants);SYSNETHTTP_NO_OPENSSL</DefineConstants>

+      <AllowUnsafeBlocks>true</AllowUnsafeBlocks>

+    </PropertyGroup>

+    <PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'netcoreapp-Unix-Debug|AnyCPU'" />

+ @@ -169,4 +170,4 @@

+      <Service Include="{82A7F48D-3B50-4B1E-B82E-3ADA8210C358}" />

+    </ItemGroup>

+    <Import Project="$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory), dir.targets))\dir.targets" />

+ -</Project>

+ \ No newline at end of file

+ +</Project>

+ diff --git a/src/System.Net.Http/tests/FunctionalTests/TestHelper.cs b/src/System.Net.Http/tests/FunctionalTests/TestHelper.cs

+ index 9bf6f216d1..2e29128a92 100644

+ --- a/src/System.Net.Http/tests/FunctionalTests/TestHelper.cs

+ +++ b/src/System.Net.Http/tests/FunctionalTests/TestHelper.cs

+ @@ -6,6 +6,8 @@ using System.Collections.Generic;

+  using System.Linq;

+  using System.Net.NetworkInformation;

+  using System.Net.Security;

+ +using System.Reflection;

+ +using System.Runtime.InteropServices;

+  using System.Security.Cryptography;

+  using System.Security.Cryptography.X509Certificates;

+  using System.Text;

+ @@ -107,5 +109,72 @@ namespace System.Net.Http.Functional.Tests

+                  .Select(a => a.Address)

+                  .Where(a => a.IsIPv6LinkLocal)

+                  .FirstOrDefault();

+ +

+ +        public static void EnsureHttp2Feature(HttpClientHandler handler)

+ +        {

+ +            // All .NET Core implementations of HttpClientHandler have HTTP/2 enabled by default except when using

+ +            // SocketsHttpHandler. Right now, the HTTP/2 feature is disabled on SocketsHttpHandler unless certain

+ +            // AppContext switches or environment variables are set. To help with testing, we can enable the HTTP/2

+ +            // feature for a specific handler instance by using reflection.

+ +            FieldInfo field_socketsHttpHandler = typeof(HttpClientHandler).GetField(

+ +                "_socketsHttpHandler",

+ +                BindingFlags.NonPublic | BindingFlags.Instance);

+ +            if (field_socketsHttpHandler == null)

+ +            {

+ +                // Not using .NET Core implementation, i.e. could be .NET Framework or UAP.

+ +                return;

+ +            }

+ +

+ +            object _socketsHttpHandler = field_socketsHttpHandler.GetValue(handler);

+ +            if (_socketsHttpHandler == null)

+ +            {

+ +                // Not using SocketsHttpHandler, i.e. using WinHttpHandler or CurlHandler.

+ +                return;

+ +            }

+ +

+ +            // Get HttpConnectionSettings object from SocketsHttpHandler.

+ +            Type type_SocketsHttpHandler = typeof(HttpClientHandler).Assembly.GetType("System.Net.Http.SocketsHttpHandler");

+ +            FieldInfo field_settings = type_SocketsHttpHandler.GetField(

+ +                "_settings",

+ +                BindingFlags.NonPublic | BindingFlags.Instance);

+ +            Assert.NotNull(field_settings);

+ +            object _settings = field_settings.GetValue(_socketsHttpHandler);

+ +            Assert.NotNull(_settings);

+ +

+ +            // Set _maxHttpVersion field to HTTP/2.0.

+ +            Type type_HttpConnectionSettings = typeof(HttpClientHandler).Assembly.GetType("System.Net.Http.HttpConnectionSettings");

+ +            FieldInfo field_maxHttpVersion = type_HttpConnectionSettings.GetField(

+ +                "_maxHttpVersion",

+ +                BindingFlags.NonPublic | BindingFlags.Instance);

+ +            field_maxHttpVersion.SetValue(_settings, new Version(2, 0));

+ +        }

+ +

+ +        public static bool NativeHandlerSupportsSslConfiguration()

+ +        {

+ +#if TargetsWindows

+ +            return true;

+ +#else

+ +            if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX))

+ +            {

+ +                return false;

+ +            }

+ +

+ +            // For other Unix-based systems it's true if (and only if) the currect openssl backend

+ +            // is used with libcurl.

+ +            bool hasAnyOpenSsl =

+ +                Interop.Http.GetSslVersionDescription()?.StartsWith(Interop.Http.OpenSslDescriptionPrefix, StringComparison.OrdinalIgnoreCase) ?? false;

+ +

+ +            if (!hasAnyOpenSsl)

+ +            {

+ +                return false;

+ +            }

+ +

+ +            // We're on an OpenSSL-based system, with an OpenSSL backend.

+ +            // Ask the product how it feels about this.

+ +            Type interopHttp = typeof(HttpClient).Assembly.GetType("Interop+Http");

+ +            PropertyInfo hasMatchingOpenSslVersion = interopHttp.GetProperty("HasMatchingOpenSslVersion", BindingFlags.Static | BindingFlags.NonPublic);

+ +            return (bool)hasMatchingOpenSslVersion.GetValue(null);

+ +#endif

+ +        }

+      }

+  }

+ -- 

+ 2.20.1

+ 

@@ -0,0 +1,28 @@ 

+ From 15bfd45926678221a3191f092243cf88d89298e9 Mon Sep 17 00:00:00 2001

+ From: Omair Majid <omajid@redhat.com>

+ Date: Tue, 15 Jan 2019 11:00:03 -0500

+ Subject: [PATCH 7/7] Relax the OpenSSL error checking code

+ 

+ OpenSSL 1.0 and 1.1 have different messages for the errors, but the same

+ error code. So only check the error code, not the exact error message.

+ 

+ This is a port of #30889.

+ ---

+  .../tests/CtorTests.cs                                           | 1 -

+  1 file changed, 1 deletion(-)

+ 

+ diff --git a/src/System.Security.Cryptography.X509Certificates/tests/CtorTests.cs b/src/System.Security.Cryptography.X509Certificates/tests/CtorTests.cs

+ index da6e2630c0..24c7361500 100644

+ --- a/src/System.Security.Cryptography.X509Certificates/tests/CtorTests.cs

+ +++ b/src/System.Security.Cryptography.X509Certificates/tests/CtorTests.cs

+ @@ -355,7 +355,6 @@ namespace System.Security.Cryptography.X509Certificates.Tests

+              else // Any Unix

+              {

+                  Assert.Equal(0x0D07803A, ex.HResult);

+ -                Assert.Equal("error:0D07803A:asn1 encoding routines:ASN1_ITEM_EX_D2I:nested asn1 error", ex.Message);

+              }

+          }

+  

+ -- 

+ 2.20.1

+ 

file modified
+1 -1
@@ -4,7 +4,7 @@ 

  

  set -x

  

- fedpkg srpm 2>&1 | tee fedpkg.output

+ fedpkg --release f29 srpm 2>&1 | tee fedpkg.output

  

  srpm_name=$(grep 'Wrote: ' fedpkg.output | cut -d' ' -f 2)

  

@@ -0,0 +1,48 @@ 

+ From e02ee86364b9db3edc298a6a081004aa07473d09 Mon Sep 17 00:00:00 2001

+ From: Omair Majid <omajid@redhat.com>

+ Date: Wed, 29 Aug 2018 17:03:25 -0400

+ Subject: [PATCH] Allow setting the commit id using /p:LatestCommit

+ 

+ This is similar to how CommitCount is already supported.

+ 

+ This lets consumers who are building outside a git repo, such as

+ source-build, set a commit id which is displayed by `dotnet --info`

+ and `strings dotnet | grep '@(#)'`.

+ 

+ See: https://github.com/dotnet/source-build/issues/651

+ See: https://github.com/dotnet/cli/pull/5945

+ ---

+  dir.targets | 9 +++++----

+  1 file changed, 5 insertions(+), 4 deletions(-)

+ 

+ diff --git a/dir.targets b/dir.targets

+ index 8d34872c6..59dc1ebde 100644

+ --- a/dir.targets

+ +++ b/dir.targets

+ @@ -17,7 +17,8 @@

+      <Exec Command="$(DotnetToolCommand) build $(MSBuildThisFileDirectory)tools-local/tasks/core-setup.tasks.csproj" />

+    </Target>

+  

+ -  <Target Name="GetLatestCommitHash">

+ +  <Target Name="GetLatestCommitHash"

+ +          Condition="'$(LatestCommit)' == ''">

+      <!-- Get the latest commit hash -->

+      <Exec Command="git rev-parse HEAD 2>&amp;1" StandardOutputImportance="Low" IgnoreExitCode="true" IgnoreStandardErrorWarningFormat="true" ConsoleToMSBuild="true">

+        <Output TaskParameter="ConsoleOutput" PropertyName="LatestCommit" />

+ @@ -29,13 +30,13 @@

+      </PropertyGroup>

+    </Target>

+  

+ -  <Target Name="GetCommitCount">

+ +  <Target Name="GetCommitCount"

+ +          Condition="'$(CommitCount)' == ''">

+      <Exec Command="git rev-list --count HEAD"

+            StandardOutputImportance="Low"

+            IgnoreExitCode="true"

+            IgnoreStandardErrorWarningFormat="true"

+ -          ConsoleToMSBuild="true"

+ -          Condition="'$(CommitCount)' == ''">

+ +          ConsoleToMSBuild="true">

+       <Output TaskParameter="ConsoleOutput" PropertyName="CommitCount" />

+       <Output TaskParameter="ExitCode" PropertyName="CommitCountExitCode" />

+      </Exec>

@@ -0,0 +1,22 @@ 

+ From 9b9697318e9990655ea878a28a00eda44fb615c2 Mon Sep 17 00:00:00 2001

+ From: Jeremy Barton <jbarton@microsoft.com>

+ Date: Mon, 22 Oct 2018 11:54:52 -0700

+ Subject: [PATCH] Fix ALPN detection logic (for non-portable shim builds)

+ 

+ ---

+  .../Unix/System.Security.Cryptography.Native/configure.cmake    | 2 +-

+  1 file changed, 1 insertion(+), 1 deletion(-)

+ 

+ diff --git a/src/Native/Unix/System.Security.Cryptography.Native/configure.cmake b/src/Native/Unix/System.Security.Cryptography.Native/configure.cmake

+ index cdc9f50f3c33..fac8c16343df 100644

+ --- a/src/Native/Unix/System.Security.Cryptography.Native/configure.cmake

+ +++ b/src/Native/Unix/System.Security.Cryptography.Native/configure.cmake

+ @@ -2,7 +2,7 @@ include(CheckLibraryExists)

+  include(CheckFunctionExists)

+  

+  set(CMAKE_REQUIRED_INCLUDES ${OPENSSL_INCLUDE_DIR})

+ -set(CMAKE_REQUIRED_LIBRARIES ${OPENSSL_CRYPTO_LIBRARY})

+ +set(CMAKE_REQUIRED_LIBRARIES ${OPENSSL_CRYPTO_LIBRARY} ${OPENSSL_SSL_LIBRARY})

+  

+  check_function_exists(

+      EC_GF2m_simple_method

file modified
+49 -16
@@ -14,13 +14,14 @@ 

  

  # Filter flags not supported by clang/dotnet:

  #  -fcf-protection is not supported by clang

+ #  -fstack-clask-protection is not supported by clang

  #  -specs= is not supported by clang

- %global dotnet_cflags %(echo %optflags | sed -e 's/-fcf-protection//' | sed -re 's/-specs=[^ ]*//g')

+ %global dotnet_cflags %(echo %optflags | sed -e 's/-fcf-protection//' | sed -e 's/-fstack-clash-protection//' | sed -re 's/-specs=[^ ]*//g')

  %global dotnet_ldflags %(echo %{__global_ldflags} | sed -re 's/-specs=[^ ]*//g')

  

- %global host_version 2.2.0

- %global sdk_version 2.2.100

- %global runtime_version 2.2.0

+ %global host_version 2.2.1

+ %global sdk_version 2.2.103

+ %global runtime_version 2.2.1

  

  Name:           dotnet

  Version:        %{sdk_version}
@@ -36,20 +37,31 @@ 

  # - ./build-source-tarball.sh dotnet-%%{sdk_version}

  # - tar cvzf dotnet-%%{runtime_version}.tar.gz dotnet-%%{runtime_version}

  

- Source0:        dotnet-v%{runtime_version}.tar.gz

+ Source0:        dotnet-v%{sdk_version}-SDK-ga.tar.gz

  Source1:        check-debug-symbols.py

  Source2:        dotnet.sh

  

- Patch1:         corefx-optflags-support.patch

+ # This is https://github.com/dotnet/corefx/pull/34443

+ Patch1:         0001-NetFX-compatibility-fixes-for-X500DistinguishedName.patch

+ Patch2:         0002-Drop-pal_asn1_print-in-favor-of-the-managed-code.patch

+ Patch3:         0003-Add-hybrid-support-for-OpenSSL-1.0-and-1.1.patch

+ Patch4:         0004-Use-HMAC_CTX_free-instead-of-free-on-a-HMAC_CTX-3422.patch

+ Patch5:         0005-Prefer-OpenSSL-1.0.x-for-portable-builds.patch

+ Patch6:         0006-Check-for-the-specific-in-use-version-of-OpenSSL-whe.patch

+ Patch7:         0007-Relax-the-OpenSSL-error-checking-code.patch

  

- Patch2:         cli-telemetry-optout.patch

+ Patch10:        corefx-optflags-support.patch

+ Patch11:        corefx-32956-alpn.patch

+ 

+ Patch300:       core-setup-4510-commit-id.patch

+ Patch400:       cli-telemetry-optout.patch

  

  ExclusiveArch:  x86_64

  

  BuildRequires:  clang

  BuildRequires:  cmake

- BuildRequires:  glibc-langpack-en

  BuildRequires:  git

+ BuildRequires:  glibc-langpack-en

  BuildRequires:  hostname

  BuildRequires:  krb5-devel

  BuildRequires:  libcurl-devel
@@ -59,13 +71,14 @@ 

  BuildRequires:  lldb-devel

  BuildRequires:  llvm

  BuildRequires:  lttng-ust-devel

+ BuildRequires:  openssl-devel

  BuildRequires:  python

  BuildRequires:  strace

  BuildRequires:  zlib-devel

- %if             0%{fedora} >= 26

- BuildRequires:  compat-openssl10-devel

- %else

- BuildRequires:  openssl-devel

+ # Bootstrap SDK needs OpenSSL 1.0 to run, but we can build and then

+ # run with either OpenSSL 1.0 or 1.1

+ %if 0%{fedora} >= 26

+ BuildRequires:  compat-openssl10

  %endif

  

  Requires:       %{name}-sdk-2.2%{?_isa} >= %{sdk_version}-%{release}
@@ -115,6 +128,7 @@ 

  It particularly focuses on creating console applications, web

  applications and micro-services.

  

+ 

  %package runtime-2.2

  

  Version:        %{runtime_version}
@@ -125,7 +139,6 @@ 

  # libicu is dlopen()ed

  Requires:       libicu

  

- 

  %description runtime-2.2

  The .NET Core runtime contains everything needed to run .NET Core applications.

  It includes a high performance Virtual Machine as well as the framework
@@ -137,6 +150,7 @@ 

  It particularly focuses on creating console applications, web

  applications and micro-services.

  

+ 

  %package sdk-2.2

  

  Version:        %{sdk_version}
@@ -154,6 +168,7 @@ 

  It particularly focuses on creating console applications, web

  applications and micro-services.

  

+ 

  %package sdk-2.2.1xx

  

  Version:        %{sdk_version}
@@ -171,18 +186,32 @@ 

  It particularly focuses on creating console applications, web

  applications and micro-services.

  

+ 

  %prep

- %setup -q -n %{name}-v%{runtime_version}

+ %setup -q -n %{name}-v%{sdk_version}-SDK-ga

  

  # Fix bad hardcoded path in build

  sed -i 's|/usr/share/dotnet|%{_libdir}/%{name}|' src/core-setup/src/corehost/common/pal.unix.cpp

  

  pushd src/corefx

  %patch1 -p1

+ %patch2 -p1

+ %patch3 -p1

+ %patch4 -p1

+ %patch5 -p1

+ %patch6 -p1

+ %patch7 -p1

+ 

+ %patch10 -p1

+ %patch11 -p1

+ popd

+ 

+ pushd src/core-setup

+ %patch300 -p1

  popd

  

  pushd src/cli

- %patch2 -p1

+ %patch400 -p1

  popd

  

  %build
@@ -192,7 +221,7 @@ 

  

  VERBOSE=1 ./build.sh \

    /v:diag \

- #  /p:MinimalConsoleLogOutput=false

+   /p:MinimalConsoleLogOutput=false

  

  %install

  install -d -m 0755 %{buildroot}%{_libdir}/%{name}/
@@ -266,6 +295,10 @@ 

  %{_libdir}/%{name}/sdk/%{sdk_version}

  

  %changelog

+ * Wed Jan 23 2019 Omair Majid <omajid@redhat.com> - 2.2.103-1

+ - Update to .NET Core Runtime 2.2.1 and SDK 2.2.103

+ - Sync with the 2.1 RPM

+ 

  * Fri Dec 07 2018 Omair Majid <omajid@redhat.com> - 2.2.100

  - Update to .NET Core 2.2.0