diff --git a/src/shared/Core/Constants.cs b/src/shared/Core/Constants.cs index 617aed645..f861347ba 100644 --- a/src/shared/Core/Constants.cs +++ b/src/shared/Core/Constants.cs @@ -158,6 +158,7 @@ public static class Http public const string SslBackend = "sslBackend"; public const string SslVerify = "sslVerify"; public const string SslCaInfo = "sslCAInfo"; + public const string SslAutoClientCert = "sslAutoClientCert"; } public static class Remote diff --git a/src/shared/Core/HttpClientFactory.cs b/src/shared/Core/HttpClientFactory.cs index 367704832..a3ea8ab6f 100644 --- a/src/shared/Core/HttpClientFactory.cs +++ b/src/shared/Core/HttpClientFactory.cs @@ -76,6 +76,20 @@ public HttpClient CreateClient() handler = new HttpClientHandler(); } + // Trace Git's chosen SSL/TLS backend + _trace.WriteLine($"Git's SSL/TLS backend is: {_settings.TlsBackend}"); + + // Mirror Git for Windows and only send client TLS certificates automatically if we're using + // the schannel backend _and_ the user has opted in to sending them. + if (_settings.TlsBackend == TlsBackend.Schannel && + _settings.AutomaticallyUseClientCertificates) + { + _trace.WriteLine("Configured to automatically send TLS client certificates."); + handler.ClientCertificateOptions = ClientCertificateOption.Automatic; + } + + // Configure server certificate verification and warn if we're bypassing validation + // IsCertificateVerificationEnabled takes precedence over custom TLS cert verification if (!_settings.IsCertificateVerificationEnabled) { diff --git a/src/shared/Core/Settings.cs b/src/shared/Core/Settings.cs index 3eafa0baa..158b38b90 100644 --- a/src/shared/Core/Settings.cs +++ b/src/shared/Core/Settings.cs @@ -119,6 +119,11 @@ public interface ISettings : IDisposable /// bool IsCertificateVerificationEnabled { get; } + /// + /// Automatically send client TLS certificates. + /// + bool AutomaticallyUseClientCertificates { get; } + /// /// Get the proxy setting if configured, or null otherwise. /// @@ -563,6 +568,9 @@ public bool IsCertificateVerificationEnabled } } + public bool AutomaticallyUseClientCertificates => + TryGetSetting(null, KnownGitCfg.Credential.SectionName, KnownGitCfg.Http.SslAutoClientCert, out string value) && value.ToBooleanyOrDefault(false); + public string CustomCertificateBundlePath => TryGetPathSetting(KnownEnvars.GitSslCaInfo, KnownGitCfg.Http.SectionName, KnownGitCfg.Http.SslCaInfo, out string value) ? value : null; diff --git a/src/shared/TestInfrastructure/Objects/TestSettings.cs b/src/shared/TestInfrastructure/Objects/TestSettings.cs index e0d03d8fb..6f72766f4 100644 --- a/src/shared/TestInfrastructure/Objects/TestSettings.cs +++ b/src/shared/TestInfrastructure/Objects/TestSettings.cs @@ -31,6 +31,8 @@ public class TestSettings : ISettings public bool IsCertificateVerificationEnabled { get; set; } = true; + public bool AutomaticallyUseClientCertificates { get; set; } + public ProxyConfiguration ProxyConfiguration { get; set; } public string ParentWindowId { get; set; }