Source file src/crypto/tls/example_test.go

     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  	"crypto/tls"
     9  	"crypto/x509"
    10  	"log"
    11  	"net/http"
    12  	"net/http/httptest"
    13  	"os"
    14  	"time"
    15  )
    16  
    17  // zeroSource is an io.Reader that returns an unlimited number of zero bytes.
    18  type zeroSource struct{}
    19  
    20  func (zeroSource) Read(b []byte) (n int, err error) {
    21  	for i := range b {
    22  		b[i] = 0
    23  	}
    24  
    25  	return len(b), nil
    26  }
    27  
    28  func ExampleDial() {
    29  	// Connecting with a custom root-certificate set.
    30  
    31  	const rootPEM = `
    32  -- GlobalSign Root R2, valid until Dec 15, 2021
    33  -----BEGIN CERTIFICATE-----
    34  MIIDujCCAqKgAwIBAgILBAAAAAABD4Ym5g0wDQYJKoZIhvcNAQEFBQAwTDEgMB4G
    35  A1UECxMXR2xvYmFsU2lnbiBSb290IENBIC0gUjIxEzARBgNVBAoTCkdsb2JhbFNp
    36  Z24xEzARBgNVBAMTCkdsb2JhbFNpZ24wHhcNMDYxMjE1MDgwMDAwWhcNMjExMjE1
    37  MDgwMDAwWjBMMSAwHgYDVQQLExdHbG9iYWxTaWduIFJvb3QgQ0EgLSBSMjETMBEG
    38  A1UEChMKR2xvYmFsU2lnbjETMBEGA1UEAxMKR2xvYmFsU2lnbjCCASIwDQYJKoZI
    39  hvcNAQEBBQADggEPADCCAQoCggEBAKbPJA6+Lm8omUVCxKs+IVSbC9N/hHD6ErPL
    40  v4dfxn+G07IwXNb9rfF73OX4YJYJkhD10FPe+3t+c4isUoh7SqbKSaZeqKeMWhG8
    41  eoLrvozps6yWJQeXSpkqBy+0Hne/ig+1AnwblrjFuTosvNYSuetZfeLQBoZfXklq
    42  tTleiDTsvHgMCJiEbKjNS7SgfQx5TfC4LcshytVsW33hoCmEofnTlEnLJGKRILzd
    43  C9XZzPnqJworc5HGnRusyMvo4KD0L5CLTfuwNhv2GXqF4G3yYROIXJ/gkwpRl4pa
    44  zq+r1feqCapgvdzZX99yqWATXgAByUr6P6TqBwMhAo6CygPCm48CAwEAAaOBnDCB
    45  mTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUm+IH
    46  V2ccHsBqBt5ZtJot39wZhi4wNgYDVR0fBC8wLTAroCmgJ4YlaHR0cDovL2NybC5n
    47  bG9iYWxzaWduLm5ldC9yb290LXIyLmNybDAfBgNVHSMEGDAWgBSb4gdXZxwewGoG
    48  3lm0mi3f3BmGLjANBgkqhkiG9w0BAQUFAAOCAQEAmYFThxxol4aR7OBKuEQLq4Gs
    49  J0/WwbgcQ3izDJr86iw8bmEbTUsp9Z8FHSbBuOmDAGJFtqkIk7mpM0sYmsL4h4hO
    50  291xNBrBVNpGP+DTKqttVCL1OmLNIG+6KYnX3ZHu01yiPqFbQfXf5WRDLenVOavS
    51  ot+3i9DAgBkcRcAtjOj4LaR0VknFBbVPFd5uRHg5h6h+u/N5GJG79G+dwfCMNYxd
    52  AfvDbbnvRG15RjF+Cv6pgsH/76tuIMRQyV+dTZsXjAzlAcmgQWpzU/qlULRuJQ/7
    53  TBj0/VLZjmmx6BEP3ojY+x1J96relc8geMJgEtslQIxq/H5COEBkEveegeGTLg==
    54  -----END CERTIFICATE-----`
    55  
    56  	// First, create the set of root certificates. For this example we only
    57  	// have one. It's also possible to omit this in order to use the
    58  	// default root set of the current operating system.
    59  	roots := x509.NewCertPool()
    60  	ok := roots.AppendCertsFromPEM([]byte(rootPEM))
    61  	if !ok {
    62  		panic("failed to parse root certificate")
    63  	}
    64  
    65  	conn, err := tls.Dial("tcp", "mail.google.com:443", &tls.Config{
    66  		RootCAs: roots,
    67  	})
    68  	if err != nil {
    69  		panic("failed to connect: " + err.Error())
    70  	}
    71  	conn.Close()
    72  }
    73  
    74  func ExampleConfig_keyLogWriter() {
    75  	// Debugging TLS applications by decrypting a network traffic capture.
    76  
    77  	// WARNING: Use of KeyLogWriter compromises security and should only be
    78  	// used for debugging.
    79  
    80  	// Dummy test HTTP server for the example with insecure random so output is
    81  	// reproducible.
    82  	server := httptest.NewUnstartedServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {}))
    83  	server.TLS = &tls.Config{
    84  		Rand: zeroSource{}, // for example only; don't do this.
    85  	}
    86  	server.StartTLS()
    87  	defer server.Close()
    88  
    89  	// Typically the log would go to an open file:
    90  	// w, err := os.OpenFile("tls-secrets.txt", os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0600)
    91  	w := os.Stdout
    92  
    93  	client := &http.Client{
    94  		Transport: &http.Transport{
    95  			TLSClientConfig: &tls.Config{
    96  				KeyLogWriter: w,
    97  
    98  				Rand:               zeroSource{}, // for reproducible output; don't do this.
    99  				InsecureSkipVerify: true,         // test server certificate is not trusted.
   100  			},
   101  		},
   102  	}
   103  	resp, err := client.Get(server.URL)
   104  	if err != nil {
   105  		log.Fatalf("Failed to get URL: %v", err)
   106  	}
   107  	resp.Body.Close()
   108  
   109  	// The resulting file can be used with Wireshark to decrypt the TLS
   110  	// connection by setting (Pre)-Master-Secret log filename in SSL Protocol
   111  	// preferences.
   112  }
   113  
   114  func ExampleLoadX509KeyPair() {
   115  	cert, err := tls.LoadX509KeyPair("testdata/example-cert.pem", "testdata/example-key.pem")
   116  	if err != nil {
   117  		log.Fatal(err)
   118  	}
   119  	cfg := &tls.Config{Certificates: []tls.Certificate{cert}}
   120  	listener, err := tls.Listen("tcp", ":2000", cfg)
   121  	if err != nil {
   122  		log.Fatal(err)
   123  	}
   124  	_ = listener
   125  }
   126  
   127  func ExampleX509KeyPair() {
   128  	certPem := []byte(`-----BEGIN CERTIFICATE-----
   129  MIIBhTCCASugAwIBAgIQIRi6zePL6mKjOipn+dNuaTAKBggqhkjOPQQDAjASMRAw
   130  DgYDVQQKEwdBY21lIENvMB4XDTE3MTAyMDE5NDMwNloXDTE4MTAyMDE5NDMwNlow
   131  EjEQMA4GA1UEChMHQWNtZSBDbzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABD0d
   132  7VNhbWvZLWPuj/RtHFjvtJBEwOkhbN/BnnE8rnZR8+sbwnc/KhCk3FhnpHZnQz7B
   133  5aETbbIgmuvewdjvSBSjYzBhMA4GA1UdDwEB/wQEAwICpDATBgNVHSUEDDAKBggr
   134  BgEFBQcDATAPBgNVHRMBAf8EBTADAQH/MCkGA1UdEQQiMCCCDmxvY2FsaG9zdDo1
   135  NDUzgg4xMjcuMC4wLjE6NTQ1MzAKBggqhkjOPQQDAgNIADBFAiEA2zpJEPQyz6/l
   136  Wf86aX6PepsntZv2GYlA5UpabfT2EZICICpJ5h/iI+i341gBmLiAFQOyTDT+/wQc
   137  6MF9+Yw1Yy0t
   138  -----END CERTIFICATE-----`)
   139  	keyPem := []byte(`-----BEGIN EC PRIVATE KEY-----
   140  MHcCAQEEIIrYSSNQFaA2Hwf1duRSxKtLYX5CB04fSeQ6tF1aY/PuoAoGCCqGSM49
   141  AwEHoUQDQgAEPR3tU2Fta9ktY+6P9G0cWO+0kETA6SFs38GecTyudlHz6xvCdz8q
   142  EKTcWGekdmdDPsHloRNtsiCa697B2O9IFA==
   143  -----END EC PRIVATE KEY-----`)
   144  	cert, err := tls.X509KeyPair(certPem, keyPem)
   145  	if err != nil {
   146  		log.Fatal(err)
   147  	}
   148  	cfg := &tls.Config{Certificates: []tls.Certificate{cert}}
   149  	listener, err := tls.Listen("tcp", ":2000", cfg)
   150  	if err != nil {
   151  		log.Fatal(err)
   152  	}
   153  	_ = listener
   154  }
   155  
   156  func ExampleX509KeyPair_httpServer() {
   157  	certPem := []byte(`-----BEGIN CERTIFICATE-----
   158  MIIBhTCCASugAwIBAgIQIRi6zePL6mKjOipn+dNuaTAKBggqhkjOPQQDAjASMRAw
   159  DgYDVQQKEwdBY21lIENvMB4XDTE3MTAyMDE5NDMwNloXDTE4MTAyMDE5NDMwNlow
   160  EjEQMA4GA1UEChMHQWNtZSBDbzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABD0d
   161  7VNhbWvZLWPuj/RtHFjvtJBEwOkhbN/BnnE8rnZR8+sbwnc/KhCk3FhnpHZnQz7B
   162  5aETbbIgmuvewdjvSBSjYzBhMA4GA1UdDwEB/wQEAwICpDATBgNVHSUEDDAKBggr
   163  BgEFBQcDATAPBgNVHRMBAf8EBTADAQH/MCkGA1UdEQQiMCCCDmxvY2FsaG9zdDo1
   164  NDUzgg4xMjcuMC4wLjE6NTQ1MzAKBggqhkjOPQQDAgNIADBFAiEA2zpJEPQyz6/l
   165  Wf86aX6PepsntZv2GYlA5UpabfT2EZICICpJ5h/iI+i341gBmLiAFQOyTDT+/wQc
   166  6MF9+Yw1Yy0t
   167  -----END CERTIFICATE-----`)
   168  	keyPem := []byte(`-----BEGIN EC PRIVATE KEY-----
   169  MHcCAQEEIIrYSSNQFaA2Hwf1duRSxKtLYX5CB04fSeQ6tF1aY/PuoAoGCCqGSM49
   170  AwEHoUQDQgAEPR3tU2Fta9ktY+6P9G0cWO+0kETA6SFs38GecTyudlHz6xvCdz8q
   171  EKTcWGekdmdDPsHloRNtsiCa697B2O9IFA==
   172  -----END EC PRIVATE KEY-----`)
   173  	cert, err := tls.X509KeyPair(certPem, keyPem)
   174  	if err != nil {
   175  		log.Fatal(err)
   176  	}
   177  	cfg := &tls.Config{Certificates: []tls.Certificate{cert}}
   178  	srv := &http.Server{
   179  		TLSConfig:    cfg,
   180  		ReadTimeout:  time.Minute,
   181  		WriteTimeout: time.Minute,
   182  	}
   183  	log.Fatal(srv.ListenAndServeTLS("", ""))
   184  }
   185  
   186  func ExampleConfig_verifyConnection() {
   187  	// VerifyConnection can be used to replace and customize connection
   188  	// verification. This example shows a VerifyConnection implementation that
   189  	// will be approximately equivalent to what crypto/tls does normally to
   190  	// verify the peer's certificate.
   191  
   192  	// Client side configuration.
   193  	_ = &tls.Config{
   194  		// Set InsecureSkipVerify to skip the default validation we are
   195  		// replacing. This will not disable VerifyConnection.
   196  		InsecureSkipVerify: true,
   197  		VerifyConnection: func(cs tls.ConnectionState) error {
   198  			opts := x509.VerifyOptions{
   199  				DNSName:       cs.ServerName,
   200  				Intermediates: x509.NewCertPool(),
   201  			}
   202  			for _, cert := range cs.PeerCertificates[1:] {
   203  				opts.Intermediates.AddCert(cert)
   204  			}
   205  			_, err := cs.PeerCertificates[0].Verify(opts)
   206  			return err
   207  		},
   208  	}
   209  
   210  	// Server side configuration.
   211  	_ = &tls.Config{
   212  		// Require client certificates (or VerifyConnection will run anyway and
   213  		// panic accessing cs.PeerCertificates[0]) but don't verify them with the
   214  		// default verifier. This will not disable VerifyConnection.
   215  		ClientAuth: tls.RequireAnyClientCert,
   216  		VerifyConnection: func(cs tls.ConnectionState) error {
   217  			opts := x509.VerifyOptions{
   218  				DNSName:       cs.ServerName,
   219  				Intermediates: x509.NewCertPool(),
   220  				KeyUsages:     []x509.ExtKeyUsage{x509.ExtKeyUsageClientAuth},
   221  			}
   222  			for _, cert := range cs.PeerCertificates[1:] {
   223  				opts.Intermediates.AddCert(cert)
   224  			}
   225  			_, err := cs.PeerCertificates[0].Verify(opts)
   226  			return err
   227  		},
   228  	}
   229  
   230  	// Note that when certificates are not handled by the default verifier
   231  	// ConnectionState.VerifiedChains will be nil.
   232  }
   233  

View as plain text