Merge pull request #2720 from mono/fix-39325
[mono.git] / mcs / class / System / Mono.Net.Security / SystemCertificateValidator.cs
index f0a0be39e0eb547f4e595696cd1c217aaea2b23e..8cd1ca0b6fac8de068150a1b0e18f3342ce8a7c0 100644 (file)
@@ -86,13 +86,13 @@ namespace Mono.Net.Security
                        return chain;
                }
 
-               public static bool BuildX509Chain (XX509CertificateCollection certs, X509Chain chain, ref SslPolicyErrors errors, ref int status11)
+               static bool BuildX509Chain (XX509CertificateCollection certs, X509Chain chain, ref SslPolicyErrors errors, ref int status11)
                {
 #if MOBILE
-                       return true;
+                       return false;
 #else
                        if (is_macosx)
-                               return true;
+                               return false;
 
                        var leaf = (X509Certificate2)certs [0];
 
@@ -121,7 +121,9 @@ namespace Mono.Net.Security
                static bool CheckUsage (XX509CertificateCollection certs, string host, ref SslPolicyErrors errors, ref int status11)
                {
 #if !MONOTOUCH
-                       var leaf = (X509Certificate2)certs[0];
+                       var leaf = certs[0] as X509Certificate2;
+                       if (leaf == null)
+                               leaf = new X509Certificate2 (certs[0]);
                        // for OSX and iOS we're using the native API to check for the SSL server policy and host names
                        if (!is_macosx) {
                                if (!CheckCertificateUsage (leaf)) {
@@ -130,7 +132,7 @@ namespace Mono.Net.Security
                                        return false;
                                }
 
-                               if (host != null && !CheckServerIdentity (leaf, host)) {
+                               if (!string.IsNullOrEmpty (host) && !CheckServerIdentity (leaf, host)) {
                                        errors |= SslPolicyErrors.RemoteCertificateNameMismatch;
                                        status11 = -2146762481; // CERT_E_CN_NO_MATCH 0x800B010F
                                        return false;
@@ -143,7 +145,7 @@ namespace Mono.Net.Security
                static bool EvaluateSystem (XX509CertificateCollection certs, XX509CertificateCollection anchors, string host, X509Chain chain, ref SslPolicyErrors errors, ref int status11)
                {
                        var leaf = certs [0];
-                       var result = false;
+                       bool result;
 
 #if MONODROID
                        result = AndroidPlatform.TrustEvaluateSsl (certs);
@@ -166,6 +168,8 @@ namespace Mono.Net.Security
                                        result = (trustResult == OSX509Certificates.SecTrustResult.Proceed ||
                                                trustResult == OSX509Certificates.SecTrustResult.Unspecified);
                                } catch {
+                                       result = false;
+                                       errors |= SslPolicyErrors.RemoteCertificateChainErrors;
                                        // Ignore
                                }
 
@@ -178,6 +182,8 @@ namespace Mono.Net.Security
                                        status11 = (int)trustResult;
                                        errors |= SslPolicyErrors.RemoteCertificateChainErrors;
                                }
+                       } else {
+                               result = BuildX509Chain (certs, chain, ref errors, ref status11);
                        }
 #endif
 
@@ -203,6 +209,8 @@ namespace Mono.Net.Security
 #if MOBILE
                        return false;
 #else
+                       if (!is_macosx)
+                               return true;
                        if (!CertificateValidationHelper.SupportsX509Chain)
                                return false;
                        if (settings != null)