diff options
Diffstat (limited to 'src/mongo/gotools/common/db/tlsgo')
13 files changed, 902 insertions, 0 deletions
diff --git a/src/mongo/gotools/common/db/tlsgo/config.go b/src/mongo/gotools/common/db/tlsgo/config.go new file mode 100644 index 00000000000..8d3971b537b --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/config.go @@ -0,0 +1,246 @@ +// Copyright (C) MongoDB, Inc. 2018-present. +// +// Licensed under the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. You may obtain +// a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 + +// This file contains code adapted from the MongoDB Go Driver. + +// Package tlsgo provides a mgo connection using Go's native TLS library. +package tlsgo + +import ( + "crypto/tls" + "crypto/x509" + "encoding/asn1" + "encoding/hex" + "encoding/pem" + "fmt" + "io/ioutil" + "strings" +) + +// TLSConfig contains options for configuring an SSL connection to the server. +type TLSConfig struct { + caCert *x509.Certificate + clientCert *tls.Certificate + insecure bool +} + +// NewTLSConfig creates a new TLSConfig. +func NewTLSConfig() *TLSConfig { + cfg := &TLSConfig{} + + return cfg +} + +// SetInsecure sets whether the client should verify the server's certificate chain and hostnames. +func (c *TLSConfig) SetInsecure(allow bool) { + c.insecure = allow +} + +// AddClientCertFromFile adds a client certificate to the configuration given a path to the +// containing file and returns the certificate's subject name. +func (c *TLSConfig) AddClientCertFromFile(clientFile, password string) (string, error) { + data, err := ioutil.ReadFile(clientFile) + if err != nil { + return "", err + } + + certPEM, err := loadPEMBlock(data, "CERTIFICATE") + if err != nil { + return "", err + } + + keyPEM, err := loadPEMBlock(data, "PRIVATE KEY") + if err != nil { + return "", err + } + // This check only covers encrypted PEM data with a DEK-Info header. It + // does not detect unencrypted PEM containing PKCS#8 format data with an + // encrypted private key. + if x509.IsEncryptedPEMBlock(keyPEM) { + if password == "" { + return "", fmt.Errorf("No password provided to decrypt private key") + } + decrypted, err := x509.DecryptPEMBlock(keyPEM, []byte(password)) + if err != nil { + return "", err + } + keyPEM = &pem.Block{Bytes: decrypted, Type: keyPEM.Type} + } + + if strings.Contains(keyPEM.Type, "ENCRYPTED") { + return "", fmt.Errorf("PKCS#8 encrypted private keys are not supported") + } + + cert, err := tls.X509KeyPair(pem.EncodeToMemory(certPEM), pem.EncodeToMemory(keyPEM)) + if err != nil { + return "", err + } + + c.clientCert = &cert + + // The documentation for the tls.X509KeyPair indicates that the Leaf + // certificate is not retained. Because there isn't any way of creating a + // tls.Certificate from an x509.Certificate short of calling X509KeyPair + // on the raw bytes, we're forced to parse the certificate over again to + // get the subject name. + crt, err := x509.ParseCertificate(certPEM.Bytes) + if err != nil { + return "", err + } + + return x509CertSubject(crt), nil +} + +// AddCaCertFromFile adds a root CA certificate to the configuration given a path to the containing file. +func (c *TLSConfig) AddCaCertFromFile(caFile string) error { + data, err := ioutil.ReadFile(caFile) + if err != nil { + return err + } + + certBytes, err := loadCertBytes(data) + if err != nil { + return err + } + + cert, err := x509.ParseCertificate(certBytes) + if err != nil { + return err + } + + c.caCert = cert + + return nil +} + +// MakeConfig constructs a new tls.Config from the configuration specified. +func (c *TLSConfig) MakeConfig() (*tls.Config, error) { + cfg := &tls.Config{} + + if c.clientCert != nil { + cfg.Certificates = []tls.Certificate{*c.clientCert} + } + + if c.caCert == nil { + roots, err := loadSystemCAs() + if err != nil { + return nil, err + } + cfg.RootCAs = roots + } else { + cfg.RootCAs = x509.NewCertPool() + cfg.RootCAs.AddCert(c.caCert) + } + + cfg.InsecureSkipVerify = c.insecure + + return cfg, nil +} + +func loadCertBytes(data []byte) ([]byte, error) { + b, err := loadPEMBlock(data, "CERTIFICATE") + if err != nil { + return nil, err + } + return b.Bytes, nil +} + +func loadPEMBlock(data []byte, blocktype string) (*pem.Block, error) { + var b *pem.Block + + for b == nil { + if data == nil || len(data) == 0 { + return nil, fmt.Errorf("no block of type %s found in .pem file", blocktype) + } + + block, rest := pem.Decode(data) + if block == nil { + return nil, fmt.Errorf("invalid .pem file") + } + + if strings.Contains(block.Type, blocktype) { + if b != nil { + return nil, fmt.Errorf("multiple %s sections in .pem file", blocktype) + } + b = block + } + + data = rest + } + + return b, nil +} + +// Because the functionality to convert a pkix.Name to a string wasn't added until Go 1.10, we +// need to copy the implementation (along with the attributeTypeNames map below). +func x509CertSubject(cert *x509.Certificate) string { + r := cert.Subject.ToRDNSequence() + + s := "" + for i := 0; i < len(r); i++ { + rdn := r[len(r)-1-i] + if i > 0 { + s += "," + } + for j, tv := range rdn { + if j > 0 { + s += "+" + } + + oidString := tv.Type.String() + typeName, ok := attributeTypeNames[oidString] + if !ok { + derBytes, err := asn1.Marshal(tv.Value) + if err == nil { + s += oidString + "=#" + hex.EncodeToString(derBytes) + continue // No value escaping necessary. + } + + typeName = oidString + } + + valueString := fmt.Sprint(tv.Value) + escaped := make([]rune, 0, len(valueString)) + + for k, c := range valueString { + escape := false + + switch c { + case ',', '+', '"', '\\', '<', '>', ';': + escape = true + + case ' ': + escape = k == 0 || k == len(valueString)-1 + + case '#': + escape = k == 0 + } + + if escape { + escaped = append(escaped, '\\', c) + } else { + escaped = append(escaped, c) + } + } + + s += typeName + "=" + string(escaped) + } + } + + return s +} + +var attributeTypeNames = map[string]string{ + "2.5.4.6": "C", + "2.5.4.10": "O", + "2.5.4.11": "OU", + "2.5.4.3": "CN", + "2.5.4.5": "SERIALNUMBER", + "2.5.4.7": "L", + "2.5.4.8": "ST", + "2.5.4.9": "STREET", + "2.5.4.17": "POSTALCODE", +} diff --git a/src/mongo/gotools/common/db/tlsgo/config_test.go b/src/mongo/gotools/common/db/tlsgo/config_test.go new file mode 100644 index 00000000000..7eb09b8643c --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/config_test.go @@ -0,0 +1,41 @@ +package tlsgo + +import ( + "strings" + "testing" +) + +func TestAddClientCert(t *testing.T) { + cases := []struct { + Path string + Pass string + Valid bool + }{ + {Path: "testdata/pkcs1.pem", Valid: true}, + {Path: "testdata/pkcs1-rev.pem", Valid: true}, + {Path: "testdata/pkcs1-encrypted.pem", Pass: "qwerty", Valid: true}, + {Path: "testdata/pkcs1-encrypted-rev.pem", Pass: "qwerty", Valid: true}, + + {Path: "testdata/pkcs8.pem", Valid: true}, + {Path: "testdata/pkcs8-rev.pem", Valid: true}, + {Path: "testdata/pkcs8-encrypted.pem", Valid: false}, + {Path: "testdata/pkcs8-encrypted-rev.pem", Valid: false}, + } + + for _, v := range cases { + tlsc := NewTLSConfig() + _, err := tlsc.AddClientCertFromFile(v.Path, v.Pass) + switch v.Valid { + case true: + if err != nil { + t.Errorf("Error parsing %s: %s", v.Path, err.Error()) + } + case false: + if err == nil { + t.Errorf("Expected error parsing %s but parsed OK", v.Path) + } else if !strings.Contains(err.Error(), "encrypted private keys are not supported") { + t.Errorf("Incorrect error for %s: %s", v.Path, err.Error()) + } + } + } +} diff --git a/src/mongo/gotools/common/db/tlsgo/rootcerts.go b/src/mongo/gotools/common/db/tlsgo/rootcerts.go new file mode 100644 index 00000000000..ee3ec3769f1 --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/rootcerts.go @@ -0,0 +1,22 @@ +// Copyright (C) MongoDB, Inc. 2018-present. +// +// Licensed under the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. You may obtain +// a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 +// +// Based on https://github.com/hashicorp/go-rootcerts by HashiCorp +// See THIRD-PARTY-NOTICES for original license terms. + +// +build !darwin + +package tlsgo + +import ( + "crypto/x509" +) + +// Stubbed for non-darwin systems. By returning nil, the Go library +// will use its own code for finding system certs. +func loadSystemCAs() (*x509.CertPool, error) { + return nil, nil +} diff --git a/src/mongo/gotools/common/db/tlsgo/rootcerts_darwin.go b/src/mongo/gotools/common/db/tlsgo/rootcerts_darwin.go new file mode 100644 index 00000000000..72c7a9116ad --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/rootcerts_darwin.go @@ -0,0 +1,58 @@ +// Copyright (C) MongoDB, Inc. 2018-present. +// +// Licensed under the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. You may obtain +// a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 +// +// Based on https://github.com/hashicorp/go-rootcerts by HashiCorp +// See THIRD-PARTY-NOTICES for original license terms. + +package tlsgo + +import ( + "crypto/x509" + "os/exec" + "os/user" + "path" +) + +// loadSystemCAs has special behavior on Darwin systems to work around +// bugs loading certs from keychains. See this GitHub issues query: +// https://github.com/golang/go/issues?utf8=%E2%9C%93&q=is%3Aissue+darwin+keychain +func loadSystemCAs() (*x509.CertPool, error) { + pool := x509.NewCertPool() + + for _, keychain := range certKeychains() { + err := addCertsFromKeychain(pool, keychain) + if err != nil { + return nil, err + } + } + + return pool, nil +} + +func addCertsFromKeychain(pool *x509.CertPool, keychain string) error { + cmd := exec.Command("/usr/bin/security", "find-certificate", "-a", "-p", keychain) + data, err := cmd.Output() + if err != nil { + return err + } + + pool.AppendCertsFromPEM(data) + + return nil +} + +func certKeychains() []string { + keychains := []string{ + "/System/Library/Keychains/SystemRootCertificates.keychain", + "/Library/Keychains/System.keychain", + } + user, err := user.Current() + if err == nil { + loginKeychain := path.Join(user.HomeDir, "Library", "Keychains", "login.keychain") + keychains = append(keychains, loginKeychain) + } + return keychains +} diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-encrypted-rev.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-encrypted-rev.pem new file mode 100644 index 00000000000..308e2263d4a --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-encrypted-rev.pem @@ -0,0 +1,51 @@ +-----BEGIN CERTIFICATE----- +MIIDfjCCAmagAwIBAgIDBUEVMA0GCSqGSIb3DQEBBQUAMHQxFzAVBgNVBAMTDktl +cm5lbCBUZXN0IENBMQ8wDQYDVQQLEwZLZXJuZWwxEDAOBgNVBAoTB01vbmdvREIx +FjAUBgNVBAcTDU5ldyBZb3JrIENpdHkxETAPBgNVBAgTCE5ldyBZb3JrMQswCQYD +VQQGEwJVUzAeFw0xNjA5MjIxODE1MTJaFw0zNjA5MjIxODE1MTJaMG8xEjAQBgNV +BAMTCWxvY2FsaG9zdDEPMA0GA1UECxMGS2VybmVsMRAwDgYDVQQKEwdNb25nb0RC +MRYwFAYDVQQHEw1OZXcgWW9yayBDaXR5MREwDwYDVQQIEwhOZXcgWW9yazELMAkG +A1UEBhMCVVMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCTHMXV0LEZ +OCuDZ292e26NbbrMaib6IL3obp/5tOvNVCNnvfgYyJwCCTIZq/mwCjAV5N8Y7tJM +v0JrrGIWgJ3qtPMQ/1VxfzLLW598nnBuqZG2HiR3CTfhd0JBmnjKDMscz90+xB2x +DUDVe6PkbZWnN2otsBzVbW+AAJRVTgUb3cjSbGcC0eTMg3SGaWiB+DtiJIAe3bl8 +6TTmrUKVvbzbJrdrFWpz+NVxf5ejZje+Wlz6OXgkWki5U41PtA7aDFIX3mo1J3c0 +jW957fC/q76jrBoTCbufYPaLQIb5QSex+aJZ40rHpSSV75tsXNUkn22u83Bes+Ih +X0As7g5kW2TDAgMBAAGjHjAcMBoGA1UdEQQTMBGCCWxvY2FsaG9zdIcEfwAAATAN +BgkqhkiG9w0BAQUFAAOCAQEAEDzWG64/IlXSEFQZom1z0uBLSLVaxrNg4se6geLH +Bt63EW78H+JMf97AA32DsDiT3ih5uo8yUcOVoEUwontUOSjekHrYfagF/KxMvyMy +sWX+8m5SLrU6s4FysUCtlXa92g1Nh/rET074U2sNShhALgNB2XSw9P5n9GnKt5VT +Rkh0AeBJd09WcOGnSHs30+kKGNV8A5a2GTJbDma0dLa7zlhV6VU91Z9LA0aamyrX +eWwnymJvRcIYvxGqgNDxN/8MsaU1EcW0MNEDkc+kDE1LbOwlAQbCeLQDq/w6AlmC +smoCi0pp6Bf8tZM2RhcUN/xXxgEKcZzhlDOI4v8RNHOyMg== +-----END CERTIFICATE----- +-----BEGIN RSA PRIVATE KEY----- +Proc-Type: 4,ENCRYPTED +DEK-Info: AES-128-CBC,B57A03692CDD397E50317A829B4A4698 + +V/V8LyrTJtyxBZYcodeO7xyS/+pmjmbEEYWC6ugP+MgeStTINrjfiYbc3QPkfUEg +SpWFgeq6rFbnszeWrcuk9U0NCv+vg3SjMuprrisCJerpv9bCldF9lbbqElL6o3ov +Q3EIS5JJWxXOJN/FAvTF4nNhh+0aasMmnZyHZMsT2aqBrswDQ7h51wCV4IRHk5Xr +StqjV314kQHMRQfybYkPKZkABtpghSLGGLguwch1cbKPCKHTinFuIuZGHJlQmnOz +tfXtnjlrAG7LtyfddrTlWkm/fGF6lhewC15HLLgpNVkLmFtHCyOtDVTkInT6CM+x +DaDnXebj4gghvJ0kmm7uX3rLX/pvnne+iNpNLaZcjVx20+iGhYaJdy4yUq+nH/UU ++dHlyublzcsDHmZG8CX297DT5kRgkH6Nh3VQdhygQNRNCEHQbR8Gsff/3bJ+KDO8 +6vw/xtcjnbIsOVM8Wxp+lkvKmwk+tTVEhL4bG/+6sq1Cd9jDnf0fzWx7t+IA4t/Y +OJ2K65T6I7QVgu0y3jSyLN1MH3oLPF3VGlF6NZlRZUObDL/HzWCFWCpBMtdAxfjI +Wxh5QyQix5lo9IuvYMYmCGk6d+N/fhpLmp3mcURkZrSZCIvfLFF7jrlO4z68j0Os +XODkuYgBXhHKf+tYc0Scokd5cbHlLZ986ngPsSClTtdovouHMxRfWoLQBdlXvxi0 +CjC7SRPuvLSSRLXzF72Htgb7U/W+JflSwvpZrO8VJ7ngR4sU2s1fO1K7x+fLIHEx +M1V6OTQfmJoumg6DIYqAqO8QD6JVIn+JfZ8Ympt7zFaPCJtpxxmKjmpQ1BWatDP6 +dLrdxW9uV6VKYBQuVv+k+jFcjNMrRfJHfeUxrOjCIo3dUDfju+DOdJUAMxWPzdZZ +OmcTG/4AIzw0BJirIAuAsz1RE3V8UXjefnO3YOBZMJPx22iBOacRtcYZXX5Vi/hs +UMmBWrjrsgmtb8KxIvDED3fnfWI6JdK92x+yIJAOB920z//XP1XmiLV6QjwXgXIw +g85ZceCh7Z6E62GYRQ3xboelbKlOzeRXqwM9Tz75677pqnloeEZfN/0GCABX4SAi +jDmb1dt9DiwHsVnt2zvY85V14qNq5QkCTkD+34l+ASLrwgYj8iJ8f3NQMXvBatY0 +eKUonwjSD0odxgvgdwvGlsx1++ec6TWB7jUD/dLxPqPy+m+SpsrxmJG9/WxFXIA/ +UHcW8n5xy1D1mKgeGxTPgWLwYlbcLD3HBaIFj6s9vDfP7+ztcg6Xdsslf8irHByp +JZgnG3ptQFAVEftM7oWvM2eXdBp1mgxuSGgZohURNOAdW0m5VEsmMp95k/iN4vXI ++aTYuVmeWJhQY9pvRW38RDhwxBXIiN2dCkijUPHCi7fc1k9ox06rGsX3doW6UBu+ +H45w0BTVpJR8kv7y+Ep5yd0VTKnGy16PVL/K9GqNahzwb72JxLP+hI4Amlp7rSAG +Mfq0O3SvSrDks5PsPgBHEKnBfMMgKgTQOWICLtFG7Xoh1aJA9ykge2TniaUZeRuN +Wm4FEDBqhCEZpOOFdtq/P9v8KV/IDuyMhFEMb6tSn9P6EDTIS7feJnhXn7JFMdJT +-----END RSA PRIVATE KEY----- diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-encrypted.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-encrypted.pem new file mode 100644 index 00000000000..fa92cebe1d7 --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-encrypted.pem @@ -0,0 +1,51 @@ +-----BEGIN RSA PRIVATE KEY----- +Proc-Type: 4,ENCRYPTED +DEK-Info: AES-128-CBC,B57A03692CDD397E50317A829B4A4698 + +V/V8LyrTJtyxBZYcodeO7xyS/+pmjmbEEYWC6ugP+MgeStTINrjfiYbc3QPkfUEg +SpWFgeq6rFbnszeWrcuk9U0NCv+vg3SjMuprrisCJerpv9bCldF9lbbqElL6o3ov +Q3EIS5JJWxXOJN/FAvTF4nNhh+0aasMmnZyHZMsT2aqBrswDQ7h51wCV4IRHk5Xr +StqjV314kQHMRQfybYkPKZkABtpghSLGGLguwch1cbKPCKHTinFuIuZGHJlQmnOz +tfXtnjlrAG7LtyfddrTlWkm/fGF6lhewC15HLLgpNVkLmFtHCyOtDVTkInT6CM+x +DaDnXebj4gghvJ0kmm7uX3rLX/pvnne+iNpNLaZcjVx20+iGhYaJdy4yUq+nH/UU ++dHlyublzcsDHmZG8CX297DT5kRgkH6Nh3VQdhygQNRNCEHQbR8Gsff/3bJ+KDO8 +6vw/xtcjnbIsOVM8Wxp+lkvKmwk+tTVEhL4bG/+6sq1Cd9jDnf0fzWx7t+IA4t/Y +OJ2K65T6I7QVgu0y3jSyLN1MH3oLPF3VGlF6NZlRZUObDL/HzWCFWCpBMtdAxfjI +Wxh5QyQix5lo9IuvYMYmCGk6d+N/fhpLmp3mcURkZrSZCIvfLFF7jrlO4z68j0Os +XODkuYgBXhHKf+tYc0Scokd5cbHlLZ986ngPsSClTtdovouHMxRfWoLQBdlXvxi0 +CjC7SRPuvLSSRLXzF72Htgb7U/W+JflSwvpZrO8VJ7ngR4sU2s1fO1K7x+fLIHEx +M1V6OTQfmJoumg6DIYqAqO8QD6JVIn+JfZ8Ympt7zFaPCJtpxxmKjmpQ1BWatDP6 +dLrdxW9uV6VKYBQuVv+k+jFcjNMrRfJHfeUxrOjCIo3dUDfju+DOdJUAMxWPzdZZ +OmcTG/4AIzw0BJirIAuAsz1RE3V8UXjefnO3YOBZMJPx22iBOacRtcYZXX5Vi/hs +UMmBWrjrsgmtb8KxIvDED3fnfWI6JdK92x+yIJAOB920z//XP1XmiLV6QjwXgXIw +g85ZceCh7Z6E62GYRQ3xboelbKlOzeRXqwM9Tz75677pqnloeEZfN/0GCABX4SAi +jDmb1dt9DiwHsVnt2zvY85V14qNq5QkCTkD+34l+ASLrwgYj8iJ8f3NQMXvBatY0 +eKUonwjSD0odxgvgdwvGlsx1++ec6TWB7jUD/dLxPqPy+m+SpsrxmJG9/WxFXIA/ +UHcW8n5xy1D1mKgeGxTPgWLwYlbcLD3HBaIFj6s9vDfP7+ztcg6Xdsslf8irHByp +JZgnG3ptQFAVEftM7oWvM2eXdBp1mgxuSGgZohURNOAdW0m5VEsmMp95k/iN4vXI ++aTYuVmeWJhQY9pvRW38RDhwxBXIiN2dCkijUPHCi7fc1k9ox06rGsX3doW6UBu+ +H45w0BTVpJR8kv7y+Ep5yd0VTKnGy16PVL/K9GqNahzwb72JxLP+hI4Amlp7rSAG +Mfq0O3SvSrDks5PsPgBHEKnBfMMgKgTQOWICLtFG7Xoh1aJA9ykge2TniaUZeRuN +Wm4FEDBqhCEZpOOFdtq/P9v8KV/IDuyMhFEMb6tSn9P6EDTIS7feJnhXn7JFMdJT +-----END RSA PRIVATE KEY----- +-----BEGIN CERTIFICATE----- +MIIDfjCCAmagAwIBAgIDBUEVMA0GCSqGSIb3DQEBBQUAMHQxFzAVBgNVBAMTDktl +cm5lbCBUZXN0IENBMQ8wDQYDVQQLEwZLZXJuZWwxEDAOBgNVBAoTB01vbmdvREIx +FjAUBgNVBAcTDU5ldyBZb3JrIENpdHkxETAPBgNVBAgTCE5ldyBZb3JrMQswCQYD +VQQGEwJVUzAeFw0xNjA5MjIxODE1MTJaFw0zNjA5MjIxODE1MTJaMG8xEjAQBgNV +BAMTCWxvY2FsaG9zdDEPMA0GA1UECxMGS2VybmVsMRAwDgYDVQQKEwdNb25nb0RC +MRYwFAYDVQQHEw1OZXcgWW9yayBDaXR5MREwDwYDVQQIEwhOZXcgWW9yazELMAkG +A1UEBhMCVVMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCTHMXV0LEZ +OCuDZ292e26NbbrMaib6IL3obp/5tOvNVCNnvfgYyJwCCTIZq/mwCjAV5N8Y7tJM +v0JrrGIWgJ3qtPMQ/1VxfzLLW598nnBuqZG2HiR3CTfhd0JBmnjKDMscz90+xB2x +DUDVe6PkbZWnN2otsBzVbW+AAJRVTgUb3cjSbGcC0eTMg3SGaWiB+DtiJIAe3bl8 +6TTmrUKVvbzbJrdrFWpz+NVxf5ejZje+Wlz6OXgkWki5U41PtA7aDFIX3mo1J3c0 +jW957fC/q76jrBoTCbufYPaLQIb5QSex+aJZ40rHpSSV75tsXNUkn22u83Bes+Ih +X0As7g5kW2TDAgMBAAGjHjAcMBoGA1UdEQQTMBGCCWxvY2FsaG9zdIcEfwAAATAN +BgkqhkiG9w0BAQUFAAOCAQEAEDzWG64/IlXSEFQZom1z0uBLSLVaxrNg4se6geLH +Bt63EW78H+JMf97AA32DsDiT3ih5uo8yUcOVoEUwontUOSjekHrYfagF/KxMvyMy +sWX+8m5SLrU6s4FysUCtlXa92g1Nh/rET074U2sNShhALgNB2XSw9P5n9GnKt5VT +Rkh0AeBJd09WcOGnSHs30+kKGNV8A5a2GTJbDma0dLa7zlhV6VU91Z9LA0aamyrX +eWwnymJvRcIYvxGqgNDxN/8MsaU1EcW0MNEDkc+kDE1LbOwlAQbCeLQDq/w6AlmC +smoCi0pp6Bf8tZM2RhcUN/xXxgEKcZzhlDOI4v8RNHOyMg== +-----END CERTIFICATE----- diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-rev.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-rev.pem new file mode 100644 index 00000000000..0bb7b967c9d --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1-rev.pem @@ -0,0 +1,48 @@ +-----BEGIN CERTIFICATE----- +MIIDfjCCAmagAwIBAgIDBUEVMA0GCSqGSIb3DQEBBQUAMHQxFzAVBgNVBAMTDktl +cm5lbCBUZXN0IENBMQ8wDQYDVQQLEwZLZXJuZWwxEDAOBgNVBAoTB01vbmdvREIx +FjAUBgNVBAcTDU5ldyBZb3JrIENpdHkxETAPBgNVBAgTCE5ldyBZb3JrMQswCQYD +VQQGEwJVUzAeFw0xNjA5MjIxODE1MTJaFw0zNjA5MjIxODE1MTJaMG8xEjAQBgNV +BAMTCWxvY2FsaG9zdDEPMA0GA1UECxMGS2VybmVsMRAwDgYDVQQKEwdNb25nb0RC +MRYwFAYDVQQHEw1OZXcgWW9yayBDaXR5MREwDwYDVQQIEwhOZXcgWW9yazELMAkG +A1UEBhMCVVMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCTHMXV0LEZ +OCuDZ292e26NbbrMaib6IL3obp/5tOvNVCNnvfgYyJwCCTIZq/mwCjAV5N8Y7tJM +v0JrrGIWgJ3qtPMQ/1VxfzLLW598nnBuqZG2HiR3CTfhd0JBmnjKDMscz90+xB2x +DUDVe6PkbZWnN2otsBzVbW+AAJRVTgUb3cjSbGcC0eTMg3SGaWiB+DtiJIAe3bl8 +6TTmrUKVvbzbJrdrFWpz+NVxf5ejZje+Wlz6OXgkWki5U41PtA7aDFIX3mo1J3c0 +jW957fC/q76jrBoTCbufYPaLQIb5QSex+aJZ40rHpSSV75tsXNUkn22u83Bes+Ih +X0As7g5kW2TDAgMBAAGjHjAcMBoGA1UdEQQTMBGCCWxvY2FsaG9zdIcEfwAAATAN +BgkqhkiG9w0BAQUFAAOCAQEAEDzWG64/IlXSEFQZom1z0uBLSLVaxrNg4se6geLH +Bt63EW78H+JMf97AA32DsDiT3ih5uo8yUcOVoEUwontUOSjekHrYfagF/KxMvyMy +sWX+8m5SLrU6s4FysUCtlXa92g1Nh/rET074U2sNShhALgNB2XSw9P5n9GnKt5VT +Rkh0AeBJd09WcOGnSHs30+kKGNV8A5a2GTJbDma0dLa7zlhV6VU91Z9LA0aamyrX +eWwnymJvRcIYvxGqgNDxN/8MsaU1EcW0MNEDkc+kDE1LbOwlAQbCeLQDq/w6AlmC +smoCi0pp6Bf8tZM2RhcUN/xXxgEKcZzhlDOI4v8RNHOyMg== +-----END CERTIFICATE----- +-----BEGIN RSA PRIVATE KEY----- +MIIEowIBAAKCAQEAkxzF1dCxGTgrg2dvdntujW26zGom+iC96G6f+bTrzVQjZ734 +GMicAgkyGav5sAowFeTfGO7STL9Ca6xiFoCd6rTzEP9VcX8yy1uffJ5wbqmRth4k +dwk34XdCQZp4ygzLHM/dPsQdsQ1A1Xuj5G2VpzdqLbAc1W1vgACUVU4FG93I0mxn +AtHkzIN0hmlogfg7YiSAHt25fOk05q1Clb282ya3axVqc/jVcX+Xo2Y3vlpc+jl4 +JFpIuVONT7QO2gxSF95qNSd3NI1vee3wv6u+o6waEwm7n2D2i0CG+UEnsfmiWeNK +x6Ukle+bbFzVJJ9trvNwXrPiIV9ALO4OZFtkwwIDAQABAoIBAAuueTclPyrVfv8M +M5mg64JneDHLLBUojGvsfN+DMkY3rCgMuaqeI2U1/bh0I3uLE45pgh2kuSZG+as7 +IP7Qb7m3bKWo4MwGYa4sNFnc6uiepmdjtVmObdWFdslmzrick3RSPStCv2jTuJY7 +HySAXyXMDK5cEa4Q5o2vfhfX/ifcMZrS2Pz1o4k2Wh8EtzmRxJR+QR8d+XLtVsKf +WIvtlhwGqWkmocFOsWW/6Mtf7IPWC3QAPjVYNcxe/8LSE/FhnRr7L6Uv1K7vGImE +/+QVScl5sP2bpvo+9LxzOMANMdTWWX5ZZJhIdvwpsyctcZovuJq/Lrh9A0j40nRJ +LuR6wUECgYEA2AgCKimqgpf7WCZMv72Kbur2banm1nwRsnPENGK4e6ZuYwHXu5n6 +HLgk/zp2lJdE4yGr8EBE5hvoFCosxEuvF2ldlqnKDqRUC9IKNtXJEisadWCEPmOp +v04zPaV5hWOXaK3ZoCQ7D8xvzThcZderMMdGoeacv050nJnSkPEhissCgYEArlSG +x2KRa1AvAYwMnEIeABrzjSzLLPHyYmCByouo3ljjWiBu7gSsJCO+O8QBjIklpW24 +g+Cek8d9X3oMw2aKKukgecxTR/XE7StB6RXngEIWvIqLj3CNWn1l+K/F95rrQrBr +6Fea6qWnMYeZrnuGGvBX7PwjJncE1nvn+ey/9ukCgYB/1N1TDayz8jLsil1H6GSO +FcMUSUErEed27UHgrbn0kRsowuJhRE/Xxq89x957NrewnzAaziz27PR7Wil7Tj2h +YNvcV0QVPe/tvrAEmqSMd60EX8RhFqBPb3qqs8wgvjnN23G3bTj1tEdD7GHgcan/ +BywoiUmfelFOiUcsNUNf2QKBgBUuig3R6S9r17pNZP7bfb+vhqZBqhI096mCZmLQ +41zY2g8KX9Al2zCs8yFZ6IJF68AU+9VyRnJYS+B8+O4JGIKsPtjtvbTBpQLYPbLv +iWhpH1AbWWe9Wj+Dew9jdB9owGsi+omJk3YtWIpJGqA7vAir6VMPM8oprfnNplsU +rCJ5AoGBANRKxMsriiA/sDLPxDCQOZg4JGRy1ycRVu75wETwoWnDMUP6J6BxE/pK +keA1nmrVXLheVs3kB7Bg7Jm+53E6RPATRGbvJ+5nqtDDxjL3HL8Jg6uKFjPmnpJ4 +crTsbc7nrAxo0cRmUlgbzQqhgAfnb8B7Fai2T1qoFixPtIFicehx +-----END RSA PRIVATE KEY----- diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1.pem new file mode 100644 index 00000000000..9f6124b5fa2 --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs1.pem @@ -0,0 +1,48 @@ +-----BEGIN RSA PRIVATE KEY----- +MIIEowIBAAKCAQEAkxzF1dCxGTgrg2dvdntujW26zGom+iC96G6f+bTrzVQjZ734 +GMicAgkyGav5sAowFeTfGO7STL9Ca6xiFoCd6rTzEP9VcX8yy1uffJ5wbqmRth4k +dwk34XdCQZp4ygzLHM/dPsQdsQ1A1Xuj5G2VpzdqLbAc1W1vgACUVU4FG93I0mxn +AtHkzIN0hmlogfg7YiSAHt25fOk05q1Clb282ya3axVqc/jVcX+Xo2Y3vlpc+jl4 +JFpIuVONT7QO2gxSF95qNSd3NI1vee3wv6u+o6waEwm7n2D2i0CG+UEnsfmiWeNK +x6Ukle+bbFzVJJ9trvNwXrPiIV9ALO4OZFtkwwIDAQABAoIBAAuueTclPyrVfv8M +M5mg64JneDHLLBUojGvsfN+DMkY3rCgMuaqeI2U1/bh0I3uLE45pgh2kuSZG+as7 +IP7Qb7m3bKWo4MwGYa4sNFnc6uiepmdjtVmObdWFdslmzrick3RSPStCv2jTuJY7 +HySAXyXMDK5cEa4Q5o2vfhfX/ifcMZrS2Pz1o4k2Wh8EtzmRxJR+QR8d+XLtVsKf +WIvtlhwGqWkmocFOsWW/6Mtf7IPWC3QAPjVYNcxe/8LSE/FhnRr7L6Uv1K7vGImE +/+QVScl5sP2bpvo+9LxzOMANMdTWWX5ZZJhIdvwpsyctcZovuJq/Lrh9A0j40nRJ +LuR6wUECgYEA2AgCKimqgpf7WCZMv72Kbur2banm1nwRsnPENGK4e6ZuYwHXu5n6 +HLgk/zp2lJdE4yGr8EBE5hvoFCosxEuvF2ldlqnKDqRUC9IKNtXJEisadWCEPmOp +v04zPaV5hWOXaK3ZoCQ7D8xvzThcZderMMdGoeacv050nJnSkPEhissCgYEArlSG +x2KRa1AvAYwMnEIeABrzjSzLLPHyYmCByouo3ljjWiBu7gSsJCO+O8QBjIklpW24 +g+Cek8d9X3oMw2aKKukgecxTR/XE7StB6RXngEIWvIqLj3CNWn1l+K/F95rrQrBr +6Fea6qWnMYeZrnuGGvBX7PwjJncE1nvn+ey/9ukCgYB/1N1TDayz8jLsil1H6GSO +FcMUSUErEed27UHgrbn0kRsowuJhRE/Xxq89x957NrewnzAaziz27PR7Wil7Tj2h +YNvcV0QVPe/tvrAEmqSMd60EX8RhFqBPb3qqs8wgvjnN23G3bTj1tEdD7GHgcan/ +BywoiUmfelFOiUcsNUNf2QKBgBUuig3R6S9r17pNZP7bfb+vhqZBqhI096mCZmLQ +41zY2g8KX9Al2zCs8yFZ6IJF68AU+9VyRnJYS+B8+O4JGIKsPtjtvbTBpQLYPbLv +iWhpH1AbWWe9Wj+Dew9jdB9owGsi+omJk3YtWIpJGqA7vAir6VMPM8oprfnNplsU +rCJ5AoGBANRKxMsriiA/sDLPxDCQOZg4JGRy1ycRVu75wETwoWnDMUP6J6BxE/pK +keA1nmrVXLheVs3kB7Bg7Jm+53E6RPATRGbvJ+5nqtDDxjL3HL8Jg6uKFjPmnpJ4 +crTsbc7nrAxo0cRmUlgbzQqhgAfnb8B7Fai2T1qoFixPtIFicehx +-----END RSA PRIVATE KEY----- +-----BEGIN CERTIFICATE----- +MIIDfjCCAmagAwIBAgIDBUEVMA0GCSqGSIb3DQEBBQUAMHQxFzAVBgNVBAMTDktl +cm5lbCBUZXN0IENBMQ8wDQYDVQQLEwZLZXJuZWwxEDAOBgNVBAoTB01vbmdvREIx +FjAUBgNVBAcTDU5ldyBZb3JrIENpdHkxETAPBgNVBAgTCE5ldyBZb3JrMQswCQYD +VQQGEwJVUzAeFw0xNjA5MjIxODE1MTJaFw0zNjA5MjIxODE1MTJaMG8xEjAQBgNV +BAMTCWxvY2FsaG9zdDEPMA0GA1UECxMGS2VybmVsMRAwDgYDVQQKEwdNb25nb0RC +MRYwFAYDVQQHEw1OZXcgWW9yayBDaXR5MREwDwYDVQQIEwhOZXcgWW9yazELMAkG +A1UEBhMCVVMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCTHMXV0LEZ +OCuDZ292e26NbbrMaib6IL3obp/5tOvNVCNnvfgYyJwCCTIZq/mwCjAV5N8Y7tJM +v0JrrGIWgJ3qtPMQ/1VxfzLLW598nnBuqZG2HiR3CTfhd0JBmnjKDMscz90+xB2x +DUDVe6PkbZWnN2otsBzVbW+AAJRVTgUb3cjSbGcC0eTMg3SGaWiB+DtiJIAe3bl8 +6TTmrUKVvbzbJrdrFWpz+NVxf5ejZje+Wlz6OXgkWki5U41PtA7aDFIX3mo1J3c0 +jW957fC/q76jrBoTCbufYPaLQIb5QSex+aJZ40rHpSSV75tsXNUkn22u83Bes+Ih +X0As7g5kW2TDAgMBAAGjHjAcMBoGA1UdEQQTMBGCCWxvY2FsaG9zdIcEfwAAATAN +BgkqhkiG9w0BAQUFAAOCAQEAEDzWG64/IlXSEFQZom1z0uBLSLVaxrNg4se6geLH +Bt63EW78H+JMf97AA32DsDiT3ih5uo8yUcOVoEUwontUOSjekHrYfagF/KxMvyMy +sWX+8m5SLrU6s4FysUCtlXa92g1Nh/rET074U2sNShhALgNB2XSw9P5n9GnKt5VT +Rkh0AeBJd09WcOGnSHs30+kKGNV8A5a2GTJbDma0dLa7zlhV6VU91Z9LA0aamyrX +eWwnymJvRcIYvxGqgNDxN/8MsaU1EcW0MNEDkc+kDE1LbOwlAQbCeLQDq/w6AlmC +smoCi0pp6Bf8tZM2RhcUN/xXxgEKcZzhlDOI4v8RNHOyMg== +-----END CERTIFICATE----- diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-encrypted-rev.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-encrypted-rev.pem new file mode 100644 index 00000000000..2a9b8ea4aa4 --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-encrypted-rev.pem @@ -0,0 +1,51 @@ +-----BEGIN CERTIFICATE----- +MIIDfjCCAmagAwIBAgIDBUEVMA0GCSqGSIb3DQEBBQUAMHQxFzAVBgNVBAMTDktl +cm5lbCBUZXN0IENBMQ8wDQYDVQQLEwZLZXJuZWwxEDAOBgNVBAoTB01vbmdvREIx +FjAUBgNVBAcTDU5ldyBZb3JrIENpdHkxETAPBgNVBAgTCE5ldyBZb3JrMQswCQYD +VQQGEwJVUzAeFw0xNjA5MjIxODE1MTJaFw0zNjA5MjIxODE1MTJaMG8xEjAQBgNV +BAMTCWxvY2FsaG9zdDEPMA0GA1UECxMGS2VybmVsMRAwDgYDVQQKEwdNb25nb0RC +MRYwFAYDVQQHEw1OZXcgWW9yayBDaXR5MREwDwYDVQQIEwhOZXcgWW9yazELMAkG +A1UEBhMCVVMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCTHMXV0LEZ +OCuDZ292e26NbbrMaib6IL3obp/5tOvNVCNnvfgYyJwCCTIZq/mwCjAV5N8Y7tJM +v0JrrGIWgJ3qtPMQ/1VxfzLLW598nnBuqZG2HiR3CTfhd0JBmnjKDMscz90+xB2x +DUDVe6PkbZWnN2otsBzVbW+AAJRVTgUb3cjSbGcC0eTMg3SGaWiB+DtiJIAe3bl8 +6TTmrUKVvbzbJrdrFWpz+NVxf5ejZje+Wlz6OXgkWki5U41PtA7aDFIX3mo1J3c0 +jW957fC/q76jrBoTCbufYPaLQIb5QSex+aJZ40rHpSSV75tsXNUkn22u83Bes+Ih +X0As7g5kW2TDAgMBAAGjHjAcMBoGA1UdEQQTMBGCCWxvY2FsaG9zdIcEfwAAATAN +BgkqhkiG9w0BAQUFAAOCAQEAEDzWG64/IlXSEFQZom1z0uBLSLVaxrNg4se6geLH +Bt63EW78H+JMf97AA32DsDiT3ih5uo8yUcOVoEUwontUOSjekHrYfagF/KxMvyMy +sWX+8m5SLrU6s4FysUCtlXa92g1Nh/rET074U2sNShhALgNB2XSw9P5n9GnKt5VT +Rkh0AeBJd09WcOGnSHs30+kKGNV8A5a2GTJbDma0dLa7zlhV6VU91Z9LA0aamyrX +eWwnymJvRcIYvxGqgNDxN/8MsaU1EcW0MNEDkc+kDE1LbOwlAQbCeLQDq/w6AlmC +smoCi0pp6Bf8tZM2RhcUN/xXxgEKcZzhlDOI4v8RNHOyMg== +-----END CERTIFICATE----- +-----BEGIN ENCRYPTED PRIVATE KEY----- +MIIFHzBJBgkqhkiG9w0BBQ0wPDAbBgkqhkiG9w0BBQwwDgQIP80PLbXYYHUCAggA +MB0GCWCGSAFlAwQBAgQQu1qZnln9ymhZVDJmGJpIJQSCBNDufC1nGCgwBWtkzqP+ +MN3/UJD4cX6TQDjGotN484gLvCm138yB8EPSuFz2RUcOFQImKm3fuqBKgx08jen6 +DQRNekzW1ngIV3BZwn5kMwr0lJK4ibpfEmdTYu/2INq55ljsFx7pq+69PLOqskPa +l+1CzPub0xPC8spG6H0xxOV3HYZlzNX6SKgpK/GPCyGzspgijdacn+x+KFpvMRG3 +fDvdGTP5F/lk6++EHFM/LBfitNV0qkd9GoOIbcDkinu6EytSfJY/mY337AhitWQZ +zdhgC3nA+QYy9s/hs2hXBepkIsFzLMRF162Cqc7KPNObpVGBPxFS+an3c7FyYXVw +ekTf1XrUpdsqNIgvSQkUhzkPc01jHWd4paHgSCLayLx6c9jPXiCxgASZ7BcjAZOC +VLqoi9RHYrEdpoZBwMnSheHa6OVdqPbitlx4vA41s1ERuRktz9hXuhl/Rje+IF5i +2N2l4q3ix4K2yvtZ4wmoc92/WPy2XVudeBinupIxLbrq82HIs1KvLZZ78s+s2Gfh +PDH/1gMiraOWyBY1/4DtAnptl2qKW3YsTwMGCfrX8euRC7WCk/QBw6SBy1XlV2pc +uc1ZOAgWQHwDSRK6XJHgElrQkgVRlszg5vofJ1RdRxJo6XossIc3vx/IUqv2+7xx +mGBE+71FYDg4vmN5nAgN2MjEGdyMEGL4WiKT6Y/WSOTrtRVKRFTilzxuOmx6Hq37 +rldBokhttrx0JikU0fqDWSaDbERSslmv5TinygKyq/PnGOHtcBzHC0c+AIlp2Rj8 +Z5TbgMVcxjV0GZ0SojjO6DO9weJ5c5iBom+VJrniYNDc4jqn0OqIQEembgGuTdHk +37Dqp7oxonLZS1Qi+YNljxQvGUeaoy0hSJS/9C2ANWoo+POB/BkhdS3NT2CQAxNZ +ca4ThdtyLvhSjLIEEMJH7J+LFVuE32hbivWtjKcha8vJ/sYz5gZE193Jfz5H92Zq +3Ee7ipvaKQrxATCp7xJdX5ftHp2+dMsiRKxff8TOO9TVwoJkWOw9zSOMidI+znuL +IF2kTMMPu/o1EbOzEvgck/dcvPlTzWQEGy6eCSixndB4c9yjcVnZpzYnWJEhV7to +W9OfcBkQ/3V5jn96yQPCXm1br2j9FS5QDmWP+GOlLUEPwb27jUajTs3emeqvC0qJ +OALtJsKkwT9L7Cq/cZNByBrbmimEI1NkaVRPjauHhQSzPYIJWBkaJPoZIkbCJ5eO +vRi/2Bd74fda8pVFxm9kUNP8wwpz9JSXmzVRzGXOJ3lS1TKAXl++gb5HX+bieSNy +QHcjw6rBwOkdac40vs5mxGb0XHtP8Qqvn0+fzmKan4MBGKGrB2nlfBrhI2Uopni5 +WRSWbZjDe3ofsjlaj39rxQksvSnZEN/us4JHl2QWfYhpg9tYiCmO0zPREqdWKoi2 +IgydR30JXmNx+W2UBoh1iIPgxeqkDXsxWusGbAgyZs4s7/dcrlcVQz5vzHm0zXsK +hix58eAuxTJORkGKaxva5fmdwvHJJPt5/nPPsGdm81WVqm79yKRRE4mjl+PTBryE +4IuFZjGksVDHpi1LMpW4FMmaYjf/oNm9/ZAqOtxJYC8CFIyyVbqSMOwrqSDxmE8O +gHyWskGclbX/lOH8H83lXnh2xw== +-----END ENCRYPTED PRIVATE KEY----- diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-encrypted.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-encrypted.pem new file mode 100644 index 00000000000..88773490b0f --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-encrypted.pem @@ -0,0 +1,51 @@ +-----BEGIN ENCRYPTED PRIVATE KEY----- +MIIFHzBJBgkqhkiG9w0BBQ0wPDAbBgkqhkiG9w0BBQwwDgQIP80PLbXYYHUCAggA +MB0GCWCGSAFlAwQBAgQQu1qZnln9ymhZVDJmGJpIJQSCBNDufC1nGCgwBWtkzqP+ +MN3/UJD4cX6TQDjGotN484gLvCm138yB8EPSuFz2RUcOFQImKm3fuqBKgx08jen6 +DQRNekzW1ngIV3BZwn5kMwr0lJK4ibpfEmdTYu/2INq55ljsFx7pq+69PLOqskPa +l+1CzPub0xPC8spG6H0xxOV3HYZlzNX6SKgpK/GPCyGzspgijdacn+x+KFpvMRG3 +fDvdGTP5F/lk6++EHFM/LBfitNV0qkd9GoOIbcDkinu6EytSfJY/mY337AhitWQZ +zdhgC3nA+QYy9s/hs2hXBepkIsFzLMRF162Cqc7KPNObpVGBPxFS+an3c7FyYXVw +ekTf1XrUpdsqNIgvSQkUhzkPc01jHWd4paHgSCLayLx6c9jPXiCxgASZ7BcjAZOC +VLqoi9RHYrEdpoZBwMnSheHa6OVdqPbitlx4vA41s1ERuRktz9hXuhl/Rje+IF5i +2N2l4q3ix4K2yvtZ4wmoc92/WPy2XVudeBinupIxLbrq82HIs1KvLZZ78s+s2Gfh +PDH/1gMiraOWyBY1/4DtAnptl2qKW3YsTwMGCfrX8euRC7WCk/QBw6SBy1XlV2pc +uc1ZOAgWQHwDSRK6XJHgElrQkgVRlszg5vofJ1RdRxJo6XossIc3vx/IUqv2+7xx +mGBE+71FYDg4vmN5nAgN2MjEGdyMEGL4WiKT6Y/WSOTrtRVKRFTilzxuOmx6Hq37 +rldBokhttrx0JikU0fqDWSaDbERSslmv5TinygKyq/PnGOHtcBzHC0c+AIlp2Rj8 +Z5TbgMVcxjV0GZ0SojjO6DO9weJ5c5iBom+VJrniYNDc4jqn0OqIQEembgGuTdHk +37Dqp7oxonLZS1Qi+YNljxQvGUeaoy0hSJS/9C2ANWoo+POB/BkhdS3NT2CQAxNZ +ca4ThdtyLvhSjLIEEMJH7J+LFVuE32hbivWtjKcha8vJ/sYz5gZE193Jfz5H92Zq +3Ee7ipvaKQrxATCp7xJdX5ftHp2+dMsiRKxff8TOO9TVwoJkWOw9zSOMidI+znuL +IF2kTMMPu/o1EbOzEvgck/dcvPlTzWQEGy6eCSixndB4c9yjcVnZpzYnWJEhV7to +W9OfcBkQ/3V5jn96yQPCXm1br2j9FS5QDmWP+GOlLUEPwb27jUajTs3emeqvC0qJ +OALtJsKkwT9L7Cq/cZNByBrbmimEI1NkaVRPjauHhQSzPYIJWBkaJPoZIkbCJ5eO +vRi/2Bd74fda8pVFxm9kUNP8wwpz9JSXmzVRzGXOJ3lS1TKAXl++gb5HX+bieSNy +QHcjw6rBwOkdac40vs5mxGb0XHtP8Qqvn0+fzmKan4MBGKGrB2nlfBrhI2Uopni5 +WRSWbZjDe3ofsjlaj39rxQksvSnZEN/us4JHl2QWfYhpg9tYiCmO0zPREqdWKoi2 +IgydR30JXmNx+W2UBoh1iIPgxeqkDXsxWusGbAgyZs4s7/dcrlcVQz5vzHm0zXsK +hix58eAuxTJORkGKaxva5fmdwvHJJPt5/nPPsGdm81WVqm79yKRRE4mjl+PTBryE +4IuFZjGksVDHpi1LMpW4FMmaYjf/oNm9/ZAqOtxJYC8CFIyyVbqSMOwrqSDxmE8O +gHyWskGclbX/lOH8H83lXnh2xw== +-----END ENCRYPTED PRIVATE KEY----- +-----BEGIN CERTIFICATE----- +MIIDfjCCAmagAwIBAgIDBUEVMA0GCSqGSIb3DQEBBQUAMHQxFzAVBgNVBAMTDktl +cm5lbCBUZXN0IENBMQ8wDQYDVQQLEwZLZXJuZWwxEDAOBgNVBAoTB01vbmdvREIx +FjAUBgNVBAcTDU5ldyBZb3JrIENpdHkxETAPBgNVBAgTCE5ldyBZb3JrMQswCQYD +VQQGEwJVUzAeFw0xNjA5MjIxODE1MTJaFw0zNjA5MjIxODE1MTJaMG8xEjAQBgNV +BAMTCWxvY2FsaG9zdDEPMA0GA1UECxMGS2VybmVsMRAwDgYDVQQKEwdNb25nb0RC +MRYwFAYDVQQHEw1OZXcgWW9yayBDaXR5MREwDwYDVQQIEwhOZXcgWW9yazELMAkG +A1UEBhMCVVMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCTHMXV0LEZ +OCuDZ292e26NbbrMaib6IL3obp/5tOvNVCNnvfgYyJwCCTIZq/mwCjAV5N8Y7tJM +v0JrrGIWgJ3qtPMQ/1VxfzLLW598nnBuqZG2HiR3CTfhd0JBmnjKDMscz90+xB2x +DUDVe6PkbZWnN2otsBzVbW+AAJRVTgUb3cjSbGcC0eTMg3SGaWiB+DtiJIAe3bl8 +6TTmrUKVvbzbJrdrFWpz+NVxf5ejZje+Wlz6OXgkWki5U41PtA7aDFIX3mo1J3c0 +jW957fC/q76jrBoTCbufYPaLQIb5QSex+aJZ40rHpSSV75tsXNUkn22u83Bes+Ih +X0As7g5kW2TDAgMBAAGjHjAcMBoGA1UdEQQTMBGCCWxvY2FsaG9zdIcEfwAAATAN +BgkqhkiG9w0BAQUFAAOCAQEAEDzWG64/IlXSEFQZom1z0uBLSLVaxrNg4se6geLH +Bt63EW78H+JMf97AA32DsDiT3ih5uo8yUcOVoEUwontUOSjekHrYfagF/KxMvyMy +sWX+8m5SLrU6s4FysUCtlXa92g1Nh/rET074U2sNShhALgNB2XSw9P5n9GnKt5VT +Rkh0AeBJd09WcOGnSHs30+kKGNV8A5a2GTJbDma0dLa7zlhV6VU91Z9LA0aamyrX +eWwnymJvRcIYvxGqgNDxN/8MsaU1EcW0MNEDkc+kDE1LbOwlAQbCeLQDq/w6AlmC +smoCi0pp6Bf8tZM2RhcUN/xXxgEKcZzhlDOI4v8RNHOyMg== +-----END CERTIFICATE----- diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-rev.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-rev.pem new file mode 100644 index 00000000000..7d902b28e11 --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8-rev.pem @@ -0,0 +1,50 @@ +-----BEGIN CERTIFICATE----- +MIIDuDCCAqCgAwIBAgIJAIJdodI/q6hqMA0GCSqGSIb3DQEBCwUAMFIxCzAJBgNV +BAYTAlVTMREwDwYDVQQIDAhOZXcgWW9yazEQMA4GA1UECgwHTW9uZ29EQjERMA8G +A1UECwwIU2VjdXJpdHkxCzAJBgNVBAMMAmNhMB4XDTE3MDMxNzEwMTQ0MVoXDTI3 +MDMxNTEwMTQ0MVowaDELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMREw +DwYDVQQHDAhOZXcgWW9yazEQMA4GA1UECgwHTW9uZ29EQjEQMA4GA1UECwwHRHJp +dmVyczEPMA0GA1UEAwwGY2xpZW50MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIB +CgKCAQEA0nYSydRYw7eM1KtyM6s49A7SIPGUua+wStu9KkTzFcaJ8y/hcrek5J/4 +PcpY5gf8tkf3GrXxumtPnWCJJP+wbNh4U9HJgtFrzkIHnYmOxjLERGgu/w+4W3J+ +/RUSOOHK2DeOzIYZd79d48716kNWYFV80nhQRJexJSD1fGgQLll947HBh50f4Jne +JMtq3Bw/YoJfKDa8AcsWj80U5yGF6BUhVddteIwXlHbTUJxFu5cZ3iVOEr7sTd8O +gpJ1XZgUGOW9fVBxwRRiLe1MXHrljvaNOT532W+kQDw9U94teD6pDTIRPrOxJ8l4 +GWiP3hyKVqcbx2fPumj5zqRz8nlZSQIDAQABo3sweTAJBgNVHRMEAjAAMCwGCWCG +SAGG+EIBDQQfFh1PcGVuU1NMIEdlbmVyYXRlZCBDZXJ0aWZpY2F0ZTAdBgNVHQ4E +FgQUd7IrLVymryD9EI7JqSDy61B0hiYwHwYDVR0jBBgwFoAU6V78cAw4dTLrQwZE +x8Vf5k+rHDkwDQYJKoZIhvcNAQELBQADggEBAGxTZl9WrjlXd9UFIFKiTx3io/YR +NuAfStSuLwoNAi3P+XYLwvfUScyHOambqBmBFsMSNiQe6h4tepcVIFLeGcsTsoyf +JkTMwiJH1iIdAchNJmsdkWrPlzUc8s7modmzBx6TBokiGL79vVuh20SW8IyWJZaf +79A1vFR7PRRPsJWfbXkEOP+CoyQfJtPLz+fFcX2CFkvtn5T8IM97OBBckyE3pjRQ +nZ7bDc+mM/2T23KMnSWNvqP68Yt+7YMyQ+uj1+HJOHfHQSD0nU/Mn0+EqLhZbzvL +EKJ5z1meByoriHlMGvZjGMIIcH1Gt/QAi8sVzZBJr+Cq0c9P7F+uNFcODaM= +-----END CERTIFICATE----- +-----BEGIN PRIVATE KEY----- +MIIEwAIBADANBgkqhkiG9w0BAQEFAASCBKowggSmAgEAAoIBAQDSdhLJ1FjDt4zU +q3Izqzj0DtIg8ZS5r7BK270qRPMVxonzL+Fyt6Tkn/g9yljmB/y2R/catfG6a0+d +YIkk/7Bs2HhT0cmC0WvOQgediY7GMsREaC7/D7hbcn79FRI44crYN47Mhhl3v13j +zvXqQ1ZgVXzSeFBEl7ElIPV8aBAuWX3jscGHnR/gmd4ky2rcHD9igl8oNrwByxaP +zRTnIYXoFSFV1214jBeUdtNQnEW7lxneJU4SvuxN3w6CknVdmBQY5b19UHHBFGIt +7UxceuWO9o05PnfZb6RAPD1T3i14PqkNMhE+s7EnyXgZaI/eHIpWpxvHZ8+6aPnO +pHPyeVlJAgMBAAECggEBALR2AAhF51Ly2XQmCkeZor1K1AzhePh7WDvoDVzoQFPE +qNb4kGTwaRiMvqwlDHM6GAwoyw6BQmPpzhuRAifSgvHh79NXiGV+suTqI2OG5wC1 +2Ssa9mlIjnkDRTY3UieqHGenw+9FcSMH2TcUaDLWSINT6jMCbTlTpNbEWxqwlGdY +URP4I0lN/NiKyfGemctXTuKj3YOB+6feQZaL1RWYJ9pneSad6rbsLYLOc0JAK8zG +wu3mPhPTrMqaj7DXAbhz4NWmIjosIp4/5bnV2HSvpd4UiB7/yK/gknZ4XesHOz4z +aIKbYxbaUkrKIGO/mwuZOjCDSw/rSDmuxuDWFRU3NE0CgYEA6LW2dFPfxIxEmeXl +EzFxJhsCeCOcPo4ueWxbMboILl2KjMhTUGxKZEjJtWpK+FwVqashU2CrDfW/zfzp +ekb1EVAeq+bDsHKRXMJfHQ3qky733nqsKbpQonJwyQ64AVhQVLgr8Xi+gNiYaOWo +g5ZftrlNlJu59GJv+St2eipAlwsCgYEA54ZTpYAodRkMcZOGqiG8mHwNwxPSRIRO +7iRRT+8NFLVfC3Y1oPD7o2tmwFDpSzybgIOpdKuqHOG6/ed82AyqnODhmdNPcCpv +FgyWZaurgJepe8Y61vjoaV6y7geLJAOL/WAbqzRRq6tDI708t21lsFCTvtoyW/0I +0kggr/+ytXsCgYEAkaW5jlE4ilGoVhI3L64QPWNGRl8zWUuv9rtE0Hi4yhwtrTNs +QbelT+LmrC7cwVkRDeJXt1GXfeNDqu8SSj/C/pUAvWJvNC5goIfe89ZT7M7GwG5S +9sLv2Nx7jrsxm1Xk4UFr73Q893OY4H5s2/7v5PNRhSN6XWSG5JK5UnjDeEUCgYEA +iMQnAWsVeybS3Pzi3fmT6RfPIV/CJEtsPO0jQ27ZcVQ60xB/WZVBcSXuysiBJ7qj +uWUNYyhNE0adKYPnkdDZsFZ/rljPYlkOyh2hcmnYo9vzeHR/KaJb2HLijA3Uue+G +cKSnc5kybZB71s7g4RI0sdTHkkRe30w4O8/zz0PjE6UCgYEAzARJZItdMu9wGu3U +X7tSSXJL2avVKv/lBDUfZAChBhpXOQf7MvgmKUCiZC/BMZ/plw/AxBL8swrfKgsw +TdrZwrhK3wOgqYWIHCAfzR+Qa0rRTqVmRQERFylqXzNmUWMG5iq7D9rp3Ht9/Ozn +6NGsAa53FvCDeBkFzi/dsbhxvjk= +-----END PRIVATE KEY----- diff --git a/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8.pem b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8.pem new file mode 100644 index 00000000000..305c67658c9 --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/testdata/pkcs8.pem @@ -0,0 +1,50 @@ +-----BEGIN PRIVATE KEY----- +MIIEwAIBADANBgkqhkiG9w0BAQEFAASCBKowggSmAgEAAoIBAQDSdhLJ1FjDt4zU +q3Izqzj0DtIg8ZS5r7BK270qRPMVxonzL+Fyt6Tkn/g9yljmB/y2R/catfG6a0+d +YIkk/7Bs2HhT0cmC0WvOQgediY7GMsREaC7/D7hbcn79FRI44crYN47Mhhl3v13j +zvXqQ1ZgVXzSeFBEl7ElIPV8aBAuWX3jscGHnR/gmd4ky2rcHD9igl8oNrwByxaP +zRTnIYXoFSFV1214jBeUdtNQnEW7lxneJU4SvuxN3w6CknVdmBQY5b19UHHBFGIt +7UxceuWO9o05PnfZb6RAPD1T3i14PqkNMhE+s7EnyXgZaI/eHIpWpxvHZ8+6aPnO +pHPyeVlJAgMBAAECggEBALR2AAhF51Ly2XQmCkeZor1K1AzhePh7WDvoDVzoQFPE +qNb4kGTwaRiMvqwlDHM6GAwoyw6BQmPpzhuRAifSgvHh79NXiGV+suTqI2OG5wC1 +2Ssa9mlIjnkDRTY3UieqHGenw+9FcSMH2TcUaDLWSINT6jMCbTlTpNbEWxqwlGdY +URP4I0lN/NiKyfGemctXTuKj3YOB+6feQZaL1RWYJ9pneSad6rbsLYLOc0JAK8zG +wu3mPhPTrMqaj7DXAbhz4NWmIjosIp4/5bnV2HSvpd4UiB7/yK/gknZ4XesHOz4z +aIKbYxbaUkrKIGO/mwuZOjCDSw/rSDmuxuDWFRU3NE0CgYEA6LW2dFPfxIxEmeXl +EzFxJhsCeCOcPo4ueWxbMboILl2KjMhTUGxKZEjJtWpK+FwVqashU2CrDfW/zfzp +ekb1EVAeq+bDsHKRXMJfHQ3qky733nqsKbpQonJwyQ64AVhQVLgr8Xi+gNiYaOWo +g5ZftrlNlJu59GJv+St2eipAlwsCgYEA54ZTpYAodRkMcZOGqiG8mHwNwxPSRIRO +7iRRT+8NFLVfC3Y1oPD7o2tmwFDpSzybgIOpdKuqHOG6/ed82AyqnODhmdNPcCpv +FgyWZaurgJepe8Y61vjoaV6y7geLJAOL/WAbqzRRq6tDI708t21lsFCTvtoyW/0I +0kggr/+ytXsCgYEAkaW5jlE4ilGoVhI3L64QPWNGRl8zWUuv9rtE0Hi4yhwtrTNs +QbelT+LmrC7cwVkRDeJXt1GXfeNDqu8SSj/C/pUAvWJvNC5goIfe89ZT7M7GwG5S +9sLv2Nx7jrsxm1Xk4UFr73Q893OY4H5s2/7v5PNRhSN6XWSG5JK5UnjDeEUCgYEA +iMQnAWsVeybS3Pzi3fmT6RfPIV/CJEtsPO0jQ27ZcVQ60xB/WZVBcSXuysiBJ7qj +uWUNYyhNE0adKYPnkdDZsFZ/rljPYlkOyh2hcmnYo9vzeHR/KaJb2HLijA3Uue+G +cKSnc5kybZB71s7g4RI0sdTHkkRe30w4O8/zz0PjE6UCgYEAzARJZItdMu9wGu3U +X7tSSXJL2avVKv/lBDUfZAChBhpXOQf7MvgmKUCiZC/BMZ/plw/AxBL8swrfKgsw +TdrZwrhK3wOgqYWIHCAfzR+Qa0rRTqVmRQERFylqXzNmUWMG5iq7D9rp3Ht9/Ozn +6NGsAa53FvCDeBkFzi/dsbhxvjk= +-----END PRIVATE KEY----- +-----BEGIN CERTIFICATE----- +MIIDuDCCAqCgAwIBAgIJAIJdodI/q6hqMA0GCSqGSIb3DQEBCwUAMFIxCzAJBgNV +BAYTAlVTMREwDwYDVQQIDAhOZXcgWW9yazEQMA4GA1UECgwHTW9uZ29EQjERMA8G +A1UECwwIU2VjdXJpdHkxCzAJBgNVBAMMAmNhMB4XDTE3MDMxNzEwMTQ0MVoXDTI3 +MDMxNTEwMTQ0MVowaDELMAkGA1UEBhMCVVMxETAPBgNVBAgMCE5ldyBZb3JrMREw +DwYDVQQHDAhOZXcgWW9yazEQMA4GA1UECgwHTW9uZ29EQjEQMA4GA1UECwwHRHJp +dmVyczEPMA0GA1UEAwwGY2xpZW50MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIB +CgKCAQEA0nYSydRYw7eM1KtyM6s49A7SIPGUua+wStu9KkTzFcaJ8y/hcrek5J/4 +PcpY5gf8tkf3GrXxumtPnWCJJP+wbNh4U9HJgtFrzkIHnYmOxjLERGgu/w+4W3J+ +/RUSOOHK2DeOzIYZd79d48716kNWYFV80nhQRJexJSD1fGgQLll947HBh50f4Jne +JMtq3Bw/YoJfKDa8AcsWj80U5yGF6BUhVddteIwXlHbTUJxFu5cZ3iVOEr7sTd8O +gpJ1XZgUGOW9fVBxwRRiLe1MXHrljvaNOT532W+kQDw9U94teD6pDTIRPrOxJ8l4 +GWiP3hyKVqcbx2fPumj5zqRz8nlZSQIDAQABo3sweTAJBgNVHRMEAjAAMCwGCWCG +SAGG+EIBDQQfFh1PcGVuU1NMIEdlbmVyYXRlZCBDZXJ0aWZpY2F0ZTAdBgNVHQ4E +FgQUd7IrLVymryD9EI7JqSDy61B0hiYwHwYDVR0jBBgwFoAU6V78cAw4dTLrQwZE +x8Vf5k+rHDkwDQYJKoZIhvcNAQELBQADggEBAGxTZl9WrjlXd9UFIFKiTx3io/YR +NuAfStSuLwoNAi3P+XYLwvfUScyHOambqBmBFsMSNiQe6h4tepcVIFLeGcsTsoyf +JkTMwiJH1iIdAchNJmsdkWrPlzUc8s7modmzBx6TBokiGL79vVuh20SW8IyWJZaf +79A1vFR7PRRPsJWfbXkEOP+CoyQfJtPLz+fFcX2CFkvtn5T8IM97OBBckyE3pjRQ +nZ7bDc+mM/2T23KMnSWNvqP68Yt+7YMyQ+uj1+HJOHfHQSD0nU/Mn0+EqLhZbzvL +EKJ5z1meByoriHlMGvZjGMIIcH1Gt/QAi8sVzZBJr+Cq0c9P7F+uNFcODaM= +-----END CERTIFICATE----- diff --git a/src/mongo/gotools/common/db/tlsgo/tlsgo.go b/src/mongo/gotools/common/db/tlsgo/tlsgo.go new file mode 100644 index 00000000000..c26b7e2dc4f --- /dev/null +++ b/src/mongo/gotools/common/db/tlsgo/tlsgo.go @@ -0,0 +1,135 @@ +// Copyright (C) MongoDB, Inc. 2014-present. +// +// Licensed under the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. You may obtain +// a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 + +// Package tlsgo implements connection to MongoDB with Go native TLS. +package tlsgo + +import ( + "crypto/tls" + "fmt" + "net" + "strings" + "time" + + "github.com/mongodb/mongo-tools/common/db/kerberos" + "github.com/mongodb/mongo-tools/common/log" + "github.com/mongodb/mongo-tools/common/options" + "github.com/mongodb/mongo-tools/common/util" + "gopkg.in/mgo.v2" +) + +// TLSDBConnector makes a connection to the database with Go native TLS. +type TLSDBConnector struct { + dialInfo *mgo.DialInfo + config *TLSConfig +} + +// Configure the connector to connect to the server over ssl. Sets up the +// correct function to dial the server based on the ssl options passed in. +func (c *TLSDBConnector) Configure(opts options.ToolOptions) error { + if opts.SSLFipsMode { + return fmt.Errorf("FIPS mode not supported") + } + + if opts.SSLCRLFile != "" { + return fmt.Errorf("CRL files are not supported on this platform") + } + + c.config = NewTLSConfig() + + if opts.SSLAllowInvalidCert || opts.SSLAllowInvalidHost { + c.config.SetInsecure(true) + } + + if opts.SSLPEMKeyFile != "" { + subject, err := c.config.AddClientCertFromFile(opts.SSLPEMKeyFile, opts.SSLPEMKeyPassword) + if err != nil { + return err + } + if opts.Auth.Mechanism == "MONGODB-X509" && opts.Auth.Username == "" { + opts.Auth.Username = subject + } + } + + if opts.SSLCAFile != "" { + c.config.AddCaCertFromFile(opts.SSLCAFile) + } + + // set up the dial info + c.dialInfo = &mgo.DialInfo{ + Timeout: time.Duration(opts.Timeout) * time.Second, + Direct: opts.Direct, + ReplicaSetName: opts.ReplicaSetName, + DialServer: c.makeDialer(opts), + Username: opts.Auth.Username, + Password: opts.Auth.Password, + Source: opts.GetAuthenticationDatabase(), + Mechanism: opts.Auth.Mechanism, + } + + // create or fetch the addresses to be used to connect + if opts.URI != nil && opts.URI.ConnectionString != "" { + c.dialInfo.Addrs = opts.URI.GetConnectionAddrs() + } else { + c.dialInfo.Addrs = util.CreateConnectionAddrs(opts.Host, opts.Port) + } + kerberos.AddKerberosOpts(opts, c.dialInfo) + return nil +} + +// GetNewSession dials the server. +func (c *TLSDBConnector) GetNewSession() (*mgo.Session, error) { + return mgo.DialWithInfo(c.dialInfo) +} + +// To be handed to mgo.DialInfo for connecting to the server. +type dialerFunc func(addr *mgo.ServerAddr) (net.Conn, error) + +func (c *TLSDBConnector) makeDialer(opts options.ToolOptions) dialerFunc { + return func(addr *mgo.ServerAddr) (net.Conn, error) { + address := addr.String() + conn, err := net.Dial("tcp", address) + if err != nil { + // mgo discards dialer errors so log it now + log.Logvf(log.Always, "error dialing %v: %v", address, err) + return nil, err + } + // enable TCP keepalive + err = util.EnableTCPKeepAlive(conn, time.Duration(opts.TCPKeepAliveSeconds)*time.Second) + if err != nil { + // mgo discards dialer errors so log it now + log.Logvf(log.Always, "error enabling TCP keepalive on connection to %v: %v", address, err) + conn.Close() + return nil, err + } + + tlsConfig, err := c.config.MakeConfig() + if err != nil { + return nil, err + } + + if !tlsConfig.InsecureSkipVerify { + colonPos := strings.LastIndex(address, ":") + if colonPos == -1 { + colonPos = len(address) + } + + hostname := address[:colonPos] + tlsConfig.ServerName = hostname + } + + client := tls.Client(conn, tlsConfig) + err = client.Handshake() + if err != nil { + // mgo discards dialer errors so log it now + log.Logvf(log.Always, "error doing TLS handshake with %v: %v", address, err) + client.Close() + return nil, err + } + + return client, nil + } +} |