github.com/x04/go/src@v0.0.0-20200202162449-3d481ceb3525/crypto/tls/example_test.go (about) 1 // Copyright 2014 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package tls_test 6 7 import ( 8 "github.com/x04/go/src/crypto/tls" 9 "github.com/x04/go/src/crypto/x509" 10 "github.com/x04/go/src/errors" 11 "github.com/x04/go/src/log" 12 "github.com/x04/go/src/net/http" 13 "github.com/x04/go/src/net/http/httptest" 14 "github.com/x04/go/src/os" 15 "github.com/x04/go/src/time" 16 ) 17 18 // zeroSource is an io.Reader that returns an unlimited number of zero bytes. 19 type zeroSource struct{} 20 21 func (zeroSource) Read(b []byte) (n int, err error) { 22 for i := range b { 23 b[i] = 0 24 } 25 26 return len(b), nil 27 } 28 29 func ExampleDial() { 30 // Connecting with a custom root-certificate set. 31 32 const rootPEM = ` 33 -----BEGIN CERTIFICATE----- 34 MIIEBDCCAuygAwIBAgIDAjppMA0GCSqGSIb3DQEBBQUAMEIxCzAJBgNVBAYTAlVT 35 MRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMRswGQYDVQQDExJHZW9UcnVzdCBHbG9i 36 YWwgQ0EwHhcNMTMwNDA1MTUxNTU1WhcNMTUwNDA0MTUxNTU1WjBJMQswCQYDVQQG 37 EwJVUzETMBEGA1UEChMKR29vZ2xlIEluYzElMCMGA1UEAxMcR29vZ2xlIEludGVy 38 bmV0IEF1dGhvcml0eSBHMjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB 39 AJwqBHdc2FCROgajguDYUEi8iT/xGXAaiEZ+4I/F8YnOIe5a/mENtzJEiaB0C1NP 40 VaTOgmKV7utZX8bhBYASxF6UP7xbSDj0U/ck5vuR6RXEz/RTDfRK/J9U3n2+oGtv 41 h8DQUB8oMANA2ghzUWx//zo8pzcGjr1LEQTrfSTe5vn8MXH7lNVg8y5Kr0LSy+rE 42 ahqyzFPdFUuLH8gZYR/Nnag+YyuENWllhMgZxUYi+FOVvuOAShDGKuy6lyARxzmZ 43 EASg8GF6lSWMTlJ14rbtCMoU/M4iarNOz0YDl5cDfsCx3nuvRTPPuj5xt970JSXC 44 DTWJnZ37DhF5iR43xa+OcmkCAwEAAaOB+zCB+DAfBgNVHSMEGDAWgBTAephojYn7 45 qwVkDBF9qn1luMrMTjAdBgNVHQ4EFgQUSt0GFhu89mi1dvWBtrtiGrpagS8wEgYD 46 VR0TAQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8EBAMCAQYwOgYDVR0fBDMwMTAvoC2g 47 K4YpaHR0cDovL2NybC5nZW90cnVzdC5jb20vY3Jscy9ndGdsb2JhbC5jcmwwPQYI 48 KwYBBQUHAQEEMTAvMC0GCCsGAQUFBzABhiFodHRwOi8vZ3RnbG9iYWwtb2NzcC5n 49 ZW90cnVzdC5jb20wFwYDVR0gBBAwDjAMBgorBgEEAdZ5AgUBMA0GCSqGSIb3DQEB 50 BQUAA4IBAQA21waAESetKhSbOHezI6B1WLuxfoNCunLaHtiONgaX4PCVOzf9G0JY 51 /iLIa704XtE7JW4S615ndkZAkNoUyHgN7ZVm2o6Gb4ChulYylYbc3GrKBIxbf/a/ 52 zG+FA1jDaFETzf3I93k9mTXwVqO94FntT0QJo544evZG0R0SnU++0ED8Vf4GXjza 53 HFa9llF7b1cq26KqltyMdMKVvvBulRP/F/A8rLIQjcxz++iPAsbw+zOzlTvjwsto 54 WHPbqCRiOwY1nQ2pM714A5AuTHhdUDqB1O6gyHA43LL5Z/qHQF1hwFGPa4NrzQU6 55 yuGnBXj8ytqU0CwIPX4WecigUCAkVDNx 56 -----END CERTIFICATE-----` 57 58 // First, create the set of root certificates. For this example we only 59 // have one. It's also possible to omit this in order to use the 60 // default root set of the current operating system. 61 roots := x509.NewCertPool() 62 ok := roots.AppendCertsFromPEM([]byte(rootPEM)) 63 if !ok { 64 panic("failed to parse root certificate") 65 } 66 67 conn, err := tls.Dial("tcp", "mail.google.com:443", &tls.Config{ 68 RootCAs: roots, 69 }) 70 if err != nil { 71 panic("failed to connect: " + err.Error()) 72 } 73 conn.Close() 74 } 75 76 func ExampleConfig_keyLogWriter() { 77 // Debugging TLS applications by decrypting a network traffic capture. 78 79 // WARNING: Use of KeyLogWriter compromises security and should only be 80 // used for debugging. 81 82 // Dummy test HTTP server for the example with insecure random so output is 83 // reproducible. 84 server := httptest.NewUnstartedServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {})) 85 server.TLS = &tls.Config{ 86 Rand: zeroSource{}, // for example only; don't do this. 87 } 88 server.StartTLS() 89 defer server.Close() 90 91 // Typically the log would go to an open file: 92 // w, err := os.OpenFile("tls-secrets.txt", os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0600) 93 w := os.Stdout 94 95 client := &http.Client{ 96 Transport: &http.Transport{ 97 TLSClientConfig: &tls.Config{ 98 KeyLogWriter: w, 99 100 Rand: zeroSource{}, // for reproducible output; don't do this. 101 InsecureSkipVerify: true, // test server certificate is not trusted. 102 }, 103 }, 104 } 105 resp, err := client.Get(server.URL) 106 if err != nil { 107 log.Fatalf("Failed to get URL: %v", err) 108 } 109 resp.Body.Close() 110 111 // The resulting file can be used with Wireshark to decrypt the TLS 112 // connection by setting (Pre)-Master-Secret log filename in SSL Protocol 113 // preferences. 114 } 115 116 func ExampleLoadX509KeyPair() { 117 cert, err := tls.LoadX509KeyPair("testdata/example-cert.pem", "testdata/example-key.pem") 118 if err != nil { 119 log.Fatal(err) 120 } 121 cfg := &tls.Config{Certificates: []tls.Certificate{cert}} 122 listener, err := tls.Listen("tcp", ":2000", cfg) 123 if err != nil { 124 log.Fatal(err) 125 } 126 _ = listener 127 } 128 129 func ExampleX509KeyPair() { 130 certPem := []byte(`-----BEGIN CERTIFICATE----- 131 MIIBhTCCASugAwIBAgIQIRi6zePL6mKjOipn+dNuaTAKBggqhkjOPQQDAjASMRAw 132 DgYDVQQKEwdBY21lIENvMB4XDTE3MTAyMDE5NDMwNloXDTE4MTAyMDE5NDMwNlow 133 EjEQMA4GA1UEChMHQWNtZSBDbzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABD0d 134 7VNhbWvZLWPuj/RtHFjvtJBEwOkhbN/BnnE8rnZR8+sbwnc/KhCk3FhnpHZnQz7B 135 5aETbbIgmuvewdjvSBSjYzBhMA4GA1UdDwEB/wQEAwICpDATBgNVHSUEDDAKBggr 136 BgEFBQcDATAPBgNVHRMBAf8EBTADAQH/MCkGA1UdEQQiMCCCDmxvY2FsaG9zdDo1 137 NDUzgg4xMjcuMC4wLjE6NTQ1MzAKBggqhkjOPQQDAgNIADBFAiEA2zpJEPQyz6/l 138 Wf86aX6PepsntZv2GYlA5UpabfT2EZICICpJ5h/iI+i341gBmLiAFQOyTDT+/wQc 139 6MF9+Yw1Yy0t 140 -----END CERTIFICATE-----`) 141 keyPem := []byte(`-----BEGIN EC PRIVATE KEY----- 142 MHcCAQEEIIrYSSNQFaA2Hwf1duRSxKtLYX5CB04fSeQ6tF1aY/PuoAoGCCqGSM49 143 AwEHoUQDQgAEPR3tU2Fta9ktY+6P9G0cWO+0kETA6SFs38GecTyudlHz6xvCdz8q 144 EKTcWGekdmdDPsHloRNtsiCa697B2O9IFA== 145 -----END EC PRIVATE KEY-----`) 146 cert, err := tls.X509KeyPair(certPem, keyPem) 147 if err != nil { 148 log.Fatal(err) 149 } 150 cfg := &tls.Config{Certificates: []tls.Certificate{cert}} 151 listener, err := tls.Listen("tcp", ":2000", cfg) 152 if err != nil { 153 log.Fatal(err) 154 } 155 _ = listener 156 } 157 158 func ExampleX509KeyPair_httpServer() { 159 certPem := []byte(`-----BEGIN CERTIFICATE----- 160 MIIBhTCCASugAwIBAgIQIRi6zePL6mKjOipn+dNuaTAKBggqhkjOPQQDAjASMRAw 161 DgYDVQQKEwdBY21lIENvMB4XDTE3MTAyMDE5NDMwNloXDTE4MTAyMDE5NDMwNlow 162 EjEQMA4GA1UEChMHQWNtZSBDbzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABD0d 163 7VNhbWvZLWPuj/RtHFjvtJBEwOkhbN/BnnE8rnZR8+sbwnc/KhCk3FhnpHZnQz7B 164 5aETbbIgmuvewdjvSBSjYzBhMA4GA1UdDwEB/wQEAwICpDATBgNVHSUEDDAKBggr 165 BgEFBQcDATAPBgNVHRMBAf8EBTADAQH/MCkGA1UdEQQiMCCCDmxvY2FsaG9zdDo1 166 NDUzgg4xMjcuMC4wLjE6NTQ1MzAKBggqhkjOPQQDAgNIADBFAiEA2zpJEPQyz6/l 167 Wf86aX6PepsntZv2GYlA5UpabfT2EZICICpJ5h/iI+i341gBmLiAFQOyTDT+/wQc 168 6MF9+Yw1Yy0t 169 -----END CERTIFICATE-----`) 170 keyPem := []byte(`-----BEGIN EC PRIVATE KEY----- 171 MHcCAQEEIIrYSSNQFaA2Hwf1duRSxKtLYX5CB04fSeQ6tF1aY/PuoAoGCCqGSM49 172 AwEHoUQDQgAEPR3tU2Fta9ktY+6P9G0cWO+0kETA6SFs38GecTyudlHz6xvCdz8q 173 EKTcWGekdmdDPsHloRNtsiCa697B2O9IFA== 174 -----END EC PRIVATE KEY-----`) 175 cert, err := tls.X509KeyPair(certPem, keyPem) 176 if err != nil { 177 log.Fatal(err) 178 } 179 cfg := &tls.Config{Certificates: []tls.Certificate{cert}} 180 srv := &http.Server{ 181 TLSConfig: cfg, 182 ReadTimeout: time.Minute, 183 WriteTimeout: time.Minute, 184 } 185 log.Fatal(srv.ListenAndServeTLS("", "")) 186 } 187 188 func ExampleConfig_verifyPeerCertificate() { 189 // VerifyPeerCertificate can be used to replace and customize certificate 190 // verification. This example shows a VerifyPeerCertificate implementation 191 // that will be approximately equivalent to what crypto/tls does normally. 192 193 config := &tls.Config{ 194 // Set InsecureSkipVerify to skip the default validation we are 195 // replacing. This will not disable VerifyPeerCertificate. 196 InsecureSkipVerify: true, 197 198 // While packages like net/http will implicitly set ServerName, the 199 // VerifyPeerCertificate callback can't access that value, so it has to be set 200 // explicitly here or in VerifyPeerCertificate on the client side. If in 201 // an http.Transport DialTLS callback, this can be obtained by passing 202 // the addr argument to net.SplitHostPort. 203 ServerName: "example.com", 204 205 // On the server side, set ClientAuth to require client certificates (or 206 // VerifyPeerCertificate will run anyway and panic accessing certs[0]) 207 // but not verify them with the default verifier. 208 // ClientAuth: tls.RequireAnyClientCert, 209 } 210 211 config.VerifyPeerCertificate = func(certificates [][]byte, _ [][]*x509.Certificate) error { 212 certs := make([]*x509.Certificate, len(certificates)) 213 for i, asn1Data := range certificates { 214 cert, err := x509.ParseCertificate(asn1Data) 215 if err != nil { 216 return errors.New("tls: failed to parse certificate from server: " + err.Error()) 217 } 218 certs[i] = cert 219 } 220 221 opts := x509.VerifyOptions{ 222 Roots: config.RootCAs, // On the server side, use config.ClientCAs. 223 DNSName: config.ServerName, 224 Intermediates: x509.NewCertPool(), 225 // On the server side, set KeyUsages to ExtKeyUsageClientAuth. The 226 // default value is appropriate for clients side verification. 227 // KeyUsages: []x509.ExtKeyUsage{x509.ExtKeyUsageClientAuth}, 228 } 229 for _, cert := range certs[1:] { 230 opts.Intermediates.AddCert(cert) 231 } 232 _, err := certs[0].Verify(opts) 233 return err 234 } 235 236 // Note that when InsecureSkipVerify and VerifyPeerCertificate are in use, 237 // ConnectionState.VerifiedChains will be nil. 238 }