func main() { flag.Parse() var ( cert tls.Certificate err error config *tls.Config ) if *doSSL { cert, err = tls.LoadX509KeyPair("ssl.crt", "ssl.key") check(err) config = &tls.Config{ Certificates: []tls.Certificate{cert}, ServerName: "eight22er.danga.com", } ln, err := webSSLPort.Listen() check(err) tln := tls.NewListener(ln, config) go runWebServer(tln) } log.Printf("server.") wln, err := webPort.Listen() check(err) if *dev { go runWebServer(wln) } else { go runSSLRedirector(wln) } // POP Listener pln, err := popPort.Listen() check(err) if *doSSL { pln = tls.NewListener(pln, config) } pop := NewPOPServer(pln) go pop.run() // SMTP Listener sln, err := smtpPort.Listen() check(err) if *doSSL { sln = tls.NewListener(sln, config) } ss := &smtpd.Server{ Hostname: "eight22er.danga.com", PlainAuth: true, OnNewMail: func(c smtpd.Connection, from smtpd.MailAddress) (smtpd.Envelope, error) { return nil, errors.New("TODO: we haven't finished sending direct messasges via SMTP yet") }, } go ss.Serve(sln) select {} }
// Listen starts listening on the given host:port addr. func (s *Server) Listen(addr string) error { if s.listener != nil { return nil } doLog := os.Getenv("TESTING_PORT_WRITE_FD") == "" // Don't make noise during unit tests if addr == "" { return fmt.Errorf("<host>:<port> needs to be provided to start listening") } var err error s.listener, err = listen.Listen(addr) if err != nil { return fmt.Errorf("Failed to listen on %s: %v", addr, err) } base := s.ListenURL() if doLog { s.printf("Starting to listen on %s\n", base) } doEnableTLS := func() error { config := &tls.Config{ Rand: rand.Reader, Time: time.Now, NextProtos: []string{http2.NextProtoTLS, "http/1.1"}, MinVersion: tls.VersionTLS12, } if s.tlsCertFile == "" && s.certManager != nil { config.GetCertificate = s.certManager s.listener = tls.NewListener(s.listener, config) return nil } config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = loadX509KeyPair(s.tlsCertFile, s.tlsKeyFile) if err != nil { return fmt.Errorf("Failed to load TLS cert: %v", err) } s.listener = tls.NewListener(s.listener, config) return nil } if s.enableTLS { if err := doEnableTLS(); err != nil { return err } } if doLog && strings.HasSuffix(base, ":0") { s.printf("Now listening on %s\n", s.ListenURL()) } return nil }
func (s *Server) listen(opt *ServerOption) net.Listener { ln, err := net.Listen("tcp", opt.ListenAddr) if err != nil { log.Panicln(err) } ln = &tcpKeepAliveListener{ TCPListener: ln.(*net.TCPListener), AlivePeriod: opt.KeepAlivePeriod, } if opt.TLSConfig != nil { return tls.NewListener(ln, opt.TLSConfig) } if opt.CertFile == "" { return ln } // from net/http/server.go.ListenAndServeTLS tc := &tls.Config{ NextProtos: []string{"http/1.1"}, Certificates: make([]tls.Certificate, 1), } tc.Certificates[0], err = tls.LoadX509KeyPair(opt.CertFile, opt.KeyFile) if err == nil { if opt.CAs != nil { tc.ClientCAs, err = tls2.CAPool(opt.CAs...) if err == nil { tc.ClientAuth = tls.RequireAndVerifyClientCert } } if err == nil { ln = tls.NewListener(ln, tc) } } if err != nil { if ln != nil { if e := ln.Close(); e != nil { log.Panicln(e) } } log.Panicln(err) } return ln }
// GetTLSListener creates an encrypted listener with the given TLS config and address. func GetTLSListener(addr string, conf *tls.Config) (net.Listener, error) { l, err := net.Listen("tcp", addr) if err != nil { return nil, err } return tls.NewListener(l, conf), nil }
// Like Serve, but enables TLS using the given config. func ServeTLS(config *tls.Config) { if !flag.Parsed() { flag.Parse() } ServeListener(tls.NewListener(bind.Default(), config)) }
// ListenAndServeTLS is equivalent to http.Server.ListenAndServeTLS with graceful shutdown enabled. func (srv *Server) ListenAndServeTLS(certFile, keyFile string) error { // Create the listener ourselves so we can control its lifetime addr := srv.Addr if addr == "" { addr = ":https" } config := &tls.Config{} if srv.TLSConfig != nil { *config = *srv.TLSConfig } if config.NextProtos == nil { config.NextProtos = []string{"http/1.1"} } var err error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return err } conn, err := net.Listen("tcp", addr) if err != nil { return err } tlsListener := tls.NewListener(conn, config) return srv.Serve(tlsListener) }
func startWebserver() (err error) { server := http.Server{Handler: gateKeeperMux} if cmdline.tls { // copied from net.http ListenAndServeTLS() // so we have a reference to the Listener to close it on /quit/ config := &tls.Config{} config.NextProtos = []string{"http/1.1"} config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(cmdline.cert, cmdline.key) if err != nil { return } wsListener, err = net.Listen("tcp", cmdline.laddr) if err != nil { return } wsListener = tls.NewListener(wsListener, config) } else { wsListener, err = net.Listen("tcp", cmdline.laddr) if err != nil { return } } startCookieServer() err = server.Serve(wsListener) stopCookieServer() fmt.Println("Shutting down in", cmdline.quittimeout, "second(s)...") time.Sleep(time.Duration(cmdline.quittimeout) * time.Second) return err }
func (s *server) listen() error { defer trace.End(trace.Begin("")) var err error s.uss = NewUserSessionStore() certificate, err := vchConfig.HostCertificate.Certificate() if err != nil { log.Errorf("Could not load certificate from config - running without TLS: %s", err) s.l, err = net.Listen("tcp", s.addr) return err } // FIXME: assignment copies lock value to tlsConfig: crypto/tls.Config contains sync.Once contains sync.Mutex tlsconfig := func(c *tls.Config) *tls.Config { // if there are CAs, then TLS is enabled if len(vchConfig.CertificateAuthorities) != 0 { if c.ClientCAs == nil { c.ClientCAs = x509.NewCertPool() } if !c.ClientCAs.AppendCertsFromPEM(vchConfig.CertificateAuthorities) { log.Errorf("Unable to load CAs from config; client auth via certificate will not function") } c.ClientAuth = tls.VerifyClientCertIfGiven } else { log.Warnf("No certificate authorities found for certificate-based authentication. This may be intentional, however, authentication is disabled") } return &tls.Config{ Certificates: c.Certificates, NameToCertificate: c.NameToCertificate, GetCertificate: c.GetCertificate, RootCAs: c.RootCAs, NextProtos: c.NextProtos, ServerName: c.ServerName, ClientAuth: c.ClientAuth, ClientCAs: c.ClientCAs, InsecureSkipVerify: c.InsecureSkipVerify, CipherSuites: c.CipherSuites, PreferServerCipherSuites: c.PreferServerCipherSuites, SessionTicketsDisabled: c.SessionTicketsDisabled, SessionTicketKey: c.SessionTicketKey, ClientSessionCache: c.ClientSessionCache, MinVersion: tls.VersionTLS12, MaxVersion: c.MaxVersion, CurvePreferences: c.CurvePreferences, } }(&tlsconfig.ServerDefault) tlsconfig.Certificates = []tls.Certificate{*certificate} innerListener, err := net.Listen("tcp", s.addr) if err != nil { log.Fatal(err) return err } s.l = tls.NewListener(innerListener, tlsconfig) return nil }
func (s *HTTPListener) listenAndServeTLS() error { certForHandshake := func(hello *tls.ClientHelloInfo) (*tls.Certificate, error) { r := s.findRoute(hello.ServerName, "/") if r == nil { return nil, errMissingTLS } return r.keypair, nil } tlsConfig := tlsconfig.SecureCiphers(&tls.Config{ GetCertificate: certForHandshake, Certificates: []tls.Certificate{s.keypair}, }) l, err := listenFunc("tcp4", s.TLSAddr) if err != nil { return listenErr{s.Addr, err} } s.tlsListener = tls.NewListener(l, tlsConfig) server := &http.Server{ Addr: s.tlsListener.Addr().String(), Handler: fwdProtoHandler{ Handler: s, Proto: "https", Port: mustPortFromAddr(s.tlsListener.Addr().String()), }, } // TODO: log error go server.Serve(s.tlsListener) return nil }
func NewTCPListener(ircd *Ircd, address string, port int, config *tls.Config) (*TCPListener, os.Error) { var listener net.Listener secure := Insecure // Go is slightly silly here. The IPv6 form, in Go, is "[::1]:6667" whereas // the IPv4 form is "127.0.0.1:6667". Let's try to satisfy both parties by // firstly trying with 'a:6667' and if that fails retry with '[a]:6667'. finalAddress, error := net.ResolveTCPAddr("TCP", address) if error != nil { finalAddress, error = net.ResolveTCPAddr("TCP", fmt.Sprintf("[%s]:%d", address, port)) if error != nil { return nil, error } } listener, error = net.ListenTCP(finalAddress.Network(), finalAddress) if error != nil { return nil, error } if config != nil { listener = tls.NewListener(listener, config) secure = Secure } bl := NewBasicListener(ircd) bl.listener = listener bl.secure = secure return &TCPListener{bl}, nil }
// ListenTLS is a convenience method that creates an https listener using the // provided cert and key files. Use this method if you need access to the // listener object directly. When ready, pass it to the Serve method. func (srv *Server) ListenTLS(certFile, keyFile string) (net.Listener, error) { // Create the listener ourselves so we can control its lifetime addr := srv.Addr if addr == "" { addr = ":https" } config := &tls.Config{} if srv.TLSConfig != nil { *config = *srv.TLSConfig } var err error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return nil, err } conn, err := srv.newTCPListener(addr) if err != nil { return nil, err } srv.TLSConfig = config tlsListener := tls.NewListener(conn, config) return tlsListener, nil }
func (lj *LJServer) Start() error { cert, err := tls.LoadX509KeyPair(lj.Config.SSLCrt, lj.Config.SSLKey) if err != nil { return fmt.Errorf("Error loading keys: %v", err) } conn, err := net.Listen("tcp", lj.Config.Host) if err != nil { return fmt.Errorf("Listener failed: %v", err) } config := tls.Config{Certificates: []tls.Certificate{cert}} ln := tls.NewListener(conn, &config) log.Printf("[%s] Started Lumberjack Instance", lj.name) for { select { case <-lj.term: log.Println("Lumberjack server received term signal") return nil default: conn, err := ln.Accept() if err != nil { log.Printf("Error accepting connection: %v", err) continue } go lumberConn(conn, lj.r) } } return nil }
func (this *HttpEndpoint) ListenTLS() error { // create tls configuration tlsCert, err := tls.LoadX509KeyPair(this.certFile, this.keyFile) if err != nil { return err } ln, err := net.Listen("tcp", this.httpsAddr) if err == nil { cfg := &tls.Config{ Certificates: []tls.Certificate{tlsCert}, ClientAuth: tls.NoClientCert, MinVersion: tls.VersionTLS10, CipherSuites: []uint16{tls.TLS_RSA_WITH_3DES_EDE_CBC_SHA, tls.TLS_RSA_WITH_AES_128_CBC_SHA, tls.TLS_RSA_WITH_AES_256_CBC_SHA, tls.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, tls.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA, tls.TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA, tls.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, tls.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, tls.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, tls.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256}, } tls_ln := tls.NewListener(ln, cfg) this.listenerTLS = tls_ln go http.Serve(tls_ln, this.mux) logging.Infop("HttpEndpoint: ListenTLS", logging.Pair{"Address", ln.Addr()}) } return err }
func setupTls(l net.Listener, config *tlsConfig) (net.Listener, error) { tlsCert, err := tls.LoadX509KeyPair(config.Certificate, config.Key) if err != nil { if os.IsNotExist(err) { return nil, fmt.Errorf("Could not load X509 key pair (%s, %s): %v", config.Certificate, config.Key, err) } return nil, fmt.Errorf("Error reading X509 key pair (%s, %s): %q. Make sure the key is encrypted.", config.Certificate, config.Key, err) } tlsConfig := &tls.Config{ NextProtos: []string{"http/1.1"}, Certificates: []tls.Certificate{tlsCert}, // Avoid fallback on insecure SSL protocols MinVersion: tls.VersionTLS10, } if config.CA != "" { certPool := x509.NewCertPool() file, err := ioutil.ReadFile(config.CA) if err != nil { return nil, fmt.Errorf("Could not read CA certificate: %v", err) } certPool.AppendCertsFromPEM(file) tlsConfig.ClientAuth = tls.RequireAndVerifyClientCert tlsConfig.ClientCAs = certPool } return tls.NewListener(l, tlsConfig), nil }
func (this *Server) ListenAndServeTLS(certFile, keyFile string) error { addr := this.httpServer.Addr if addr == "" { addr = ":https" } config := &tls.Config{} if this.httpServer.TLSConfig != nil { *config = *this.httpServer.TLSConfig } if config.NextProtos == nil { config.NextProtos = []string{"http/1.1"} } var err error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return err } ln, err := this.getNetListener(addr) if err != nil { return err } this.listener = tls.NewListener(newListener(ln.(*net.TCPListener)), config) return this.Serve() }
// NewServer serves the given state by accepting requests on the given // listener, using the given certificate and key (in PEM format) for // authentication. func NewServer(s *state.State, addr string, cert, key []byte, datadir, logDir string) (*Server, error) { lis, err := net.Listen("tcp", addr) if err != nil { return nil, err } logger.Infof("listening on %q", lis.Addr()) tlsCert, err := tls.X509KeyPair(cert, key) if err != nil { return nil, err } srv := &Server{ state: s, addr: lis.Addr(), dataDir: datadir, logDir: logDir, limiter: utils.NewLimiter(loginRateLimit), } // TODO(rog) check that *srvRoot is a valid type for using // as an RPC server. lis = tls.NewListener(lis, &tls.Config{ Certificates: []tls.Certificate{tlsCert}, }) go srv.run(lis) return srv, nil }
// ListenAndServeTLS starts a server that listens on the provided TCP mode (as supported // by net.Listen). func ListenAndServeTLS(srv *http.Server, network string, certFile, keyFile string) error { addr := srv.Addr if addr == "" { addr = ":https" } config := &tls.Config{} if srv.TLSConfig != nil { *config = *srv.TLSConfig } if config.NextProtos == nil { config.NextProtos = []string{"http/1.1"} } var err error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return err } ln, err := net.Listen(network, addr) if err != nil { return err } tlsListener := tls.NewListener(tcpKeepAliveListener{ln.(*net.TCPListener)}, config) return srv.Serve(tlsListener) }
// ListenAndServeTLS listens on the TCP network address srv.Addr and // then calls Serve to handle requests on incoming TLS connections. // // Filenames containing a certificate and matching private key for // the server must be provided. If the certificate is signed by a // certificate authority, the certFile should be the concatenation // of the server's certificate followed by the CA's certificate. // // If srv.Addr is blank, ":https" is used. func (s *Server) ListenAndServeTLS(certFile, keyFile string) os.Error { addr := s.Addr if addr == "" { addr = ":https" } config := &tls.Config{ Rand: rand.Reader, Time: time.Seconds, NextProtos: []string{"http/1.1"}, } var err os.Error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return err } conn, err := net.Listen("tcp", addr) if err != nil { return err } tlsListener := tls.NewListener(conn, config) return s.Serve(tlsListener) }
// ListenAndServeTLS provides a graceful equivalent of net/http.Serve.ListenAndServeTLS. func (s *GracefulServer) ListenAndServeTLS(certFile, keyFile string) error { // direct lift from net/http/server.go addr := s.Addr if addr == "" { addr = ":https" } config := &tls.Config{} if s.TLSConfig != nil { *config = *s.TLSConfig } if config.NextProtos == nil { config.NextProtos = []string{"http/1.1"} } var err error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return err } ln, err := net.Listen("tcp", addr) if err != nil { return err } return s.Serve(tls.NewListener(ln, config)) }
func listenTCPServer(addr string, vs *vpsServer) (net.Listener, error) { if len(addr) == 0 { log.Fatalf("Empty listen address.") return nil, nil } //var lp *net.TCPListener lp, err := net.Listen("tcp", addr) if nil != err { log.Printf("Can NOT listen on address:%s", addr) return nil, err } if len(remote.ServerConf.TLS.Cert) > 0 { tlscfg := &tls.Config{} tlscfg.Certificates = make([]tls.Certificate, 1) tlscfg.Certificates[0], err = tls.LoadX509KeyPair(remote.ServerConf.TLS.Cert, remote.ServerConf.TLS.Key) if nil != err { log.Fatalf("Invalid cert/key for reason:%v", err) return nil, nil } lp = tls.NewListener(lp, tlscfg) } tcpaddr := lp.Addr().(*net.TCPAddr) log.Printf("Listen on address %v", tcpaddr) if nil != vs { vs.port = uint32(tcpaddr.Port) vs.lp = lp vs.createTime = time.Now() } return lp, nil }
func setupTls(cert, key, ca string, l net.Listener) (net.Listener, error) { tlsCert, err := tls.LoadX509KeyPair(cert, key) if err != nil { return nil, fmt.Errorf("Couldn't load X509 key pair (%s, %s): %s. Key encrypted?", cert, key, err) } tlsConfig := &tls.Config{ NextProtos: []string{"http/1.1"}, Certificates: []tls.Certificate{tlsCert}, // Avoid fallback on insecure SSL protocols MinVersion: tls.VersionTLS10, } if ca != "" { certPool := x509.NewCertPool() file, err := ioutil.ReadFile(ca) if err != nil { return nil, fmt.Errorf("Couldn't read CA certificate: %s", err) } certPool.AppendCertsFromPEM(file) tlsConfig.ClientAuth = tls.RequireAndVerifyClientCert tlsConfig.ClientCAs = certPool } return tls.NewListener(l, tlsConfig), nil }
// ListenAndServeTLS listens on the TCP network address srv.Addr for // incoming TLS connections. func (srv *Server) ListenAndServeTLS(certFile, keyFile string) error { addr := srv.Addr if addr == "" { addr = ":564" } cfg := srv.TLSConfig if cfg == nil { cfg = new(tls.Config) } if len(cfg.Certificates) == 0 || certFile != "" || keyFile != "" { var err error cfg.Certificates = make([]tls.Certificate, 1) cfg.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return err } } ln, err := net.Listen("tcp", addr) if err != nil { return err } ln = tls.NewListener(ln, cfg) return srv.Serve(ln) }
func listenForCoordinator() { tlsCert, tlsKey := metadataValue("tls-cert"), metadataValue("tls-key") if (tlsCert == "") != (tlsKey == "") { log.Fatalf("tls-cert and tls-key must both be supplied, or neither.") } log.Printf("Listening on %s ...", *listenAddr) ln, err := net.Listen("tcp", *listenAddr) if err != nil { log.Fatalf("Failed to listen on %s: %v", *listenAddr, err) } ln = tcpKeepAliveListener{ln.(*net.TCPListener)} var srv http.Server if tlsCert != "" { cert, err := tls.X509KeyPair([]byte(tlsCert), []byte(tlsKey)) if err != nil { log.Fatalf("TLS cert error: %v", err) } tlsConf := &tls.Config{ Certificates: []tls.Certificate{cert}, } ln = tls.NewListener(ln, tlsConf) } log.Fatalf("Serve: %v", srv.Serve(ln)) }
func listenerWrapTLS( ln net.Listener, props map[string]string, config map[string]string) (net.Listener, map[string]string, error) { props["tls"] = "disabled" if v, ok := config["tls_disable"]; ok && v != "" { return ln, props, nil } certFile, ok := config["tls_cert_file"] if !ok { return nil, nil, fmt.Errorf("'tls_cert_file' must be set") } keyFile, ok := config["tls_key_file"] if !ok { return nil, nil, fmt.Errorf("'tls_key_file' must be set") } cert, err := tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return nil, nil, fmt.Errorf("error loading TLS cert: %s", err) } tlsConf := &tls.Config{} tlsConf.Certificates = []tls.Certificate{cert} tlsConf.NextProtos = []string{"http/1.1"} tlsConf.MinVersion = tls.VersionTLS12 // Minimum version is TLS 1.2 tlsConf.ClientAuth = tls.RequestClientCert ln = tls.NewListener(ln, tlsConf) props["tls"] = "enabled" return ln, props, nil }
// NewTLSServer creates and starts a TLS-enabled testing server. func NewTLSServer(bind string, containerChan chan<- *docker.Container, hook func(*http.Request), tlsConfig TLSConfig) (*DockerServer, error) { listener, err := net.Listen("tcp", bind) if err != nil { return nil, err } defaultCertificate, err := tls.LoadX509KeyPair(tlsConfig.CertPath, tlsConfig.CertKeyPath) if err != nil { return nil, err } tlsServerConfig := new(tls.Config) tlsServerConfig.Certificates = []tls.Certificate{defaultCertificate} if tlsConfig.RootCAPath != "" { rootCertPEM, err := ioutil.ReadFile(tlsConfig.RootCAPath) if err != nil { return nil, err } certsPool := x509.NewCertPool() certsPool.AppendCertsFromPEM(rootCertPEM) tlsServerConfig.RootCAs = certsPool } tlsListener := tls.NewListener(listener, tlsServerConfig) server := buildDockerServer(tlsListener, containerChan, hook) go http.Serve(tlsListener, server) return server, nil }
// Start implements `engine.Server#Start` function. func (s *Server) Start() error { if s.config.Listener == nil { ln, err := net.Listen("tcp", s.config.Address) if err != nil { return err } if s.config.TLSCertFile != "" && s.config.TLSKeyFile != "" { // TODO: https://github.com/golang/go/commit/d24f446a90ea94b87591bf16228d7d871fec3d92 config := &tls.Config{} if !s.config.DisableHTTP2 { config.NextProtos = append(config.NextProtos, "h2") } config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(s.config.TLSCertFile, s.config.TLSKeyFile) if err != nil { return err } s.config.Listener = tls.NewListener(tcpKeepAliveListener{ln.(*net.TCPListener)}, config) } else { s.config.Listener = tcpKeepAliveListener{ln.(*net.TCPListener)} } } return s.Serve(s.config.Listener) }
// Overridden version of net/http added so we can manage the listener. func (s *Server) listenAndServeTLS(certFile, keyFile string) error { addr := s.Server.Addr if addr == "" { addr = ":https" } config := &tls.Config{} if s.Server.TLSConfig != nil { *config = *s.Server.TLSConfig } if config.NextProtos == nil { config.NextProtos = []string{"http/1.1"} } var err error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return err } conn, err := net.Listen("tcp", addr) if err != nil { return err } tlsListener := tls.NewListener(conn, config) s.listener = tlsListener return s.Server.Serve(tlsListener) }
func listenTLS(network string, addr *net.TCPAddr, certFilename, keyFilename string) (net.Listener, error) { // This is cribbed from the source of net/http.Server.ListenAndServeTLS. // We have to separate the Listen and Serve parts because we need to // report the listening address before entering Serve (which is an // infinite loop). // https://groups.google.com/d/msg/Golang-nuts/3F1VRCCENp8/3hcayZiwYM8J config := &tls.Config{} config.NextProtos = []string{"http/1.1"} var err error config.Certificates = make([]tls.Certificate, 1) config.Certificates[0], err = tls.LoadX509KeyPair(certFilename, keyFilename) if err != nil { return nil, err } conn, err := net.ListenTCP(network, addr) if err != nil { return nil, err } // Additionally disable SSLv3 because of the POODLE attack. // http://googleonlinesecurity.blogspot.com/2014/10/this-poodle-bites-exploiting-ssl-30.html // https://code.google.com/p/go/source/detail?r=ad9e191a51946e43f1abac8b6a2fefbf2291eea7 config.MinVersion = tls.VersionTLS10 tlsListener := tls.NewListener(conn, config) return tlsListener, nil }
// StartTLS starts TLS on a server from NewUnstartedServer. func (s *Server) StartTLS() { if s.URL != "" { panic("Server already started") } cert, err := tls.X509KeyPair(localhostCert, localhostKey) if err != nil { panic(fmt.Sprintf("httptest: NewTLSServer: %v", err)) } existingConfig := s.TLS s.TLS = new(tls.Config) if existingConfig != nil { *s.TLS = *existingConfig } if s.TLS.NextProtos == nil { s.TLS.NextProtos = []string{"http/1.1"} } if len(s.TLS.Certificates) == 0 { s.TLS.Certificates = []tls.Certificate{cert} } tlsListener := tls.NewListener(s.Listener, s.TLS) s.Listener = &historyListener{Listener: tlsListener} s.URL = "https://" + s.Listener.Addr().String() s.wrapHandler() go s.Config.Serve(s.Listener) }
// NewServer serves the given state by accepting requests on the given // listener, using the given certificate and key (in PEM format) for // authentication. func NewServer(s *state.State, lis net.Listener, cfg ServerConfig) (*Server, error) { logger.Infof("listening on %q", lis.Addr()) tlsCert, err := tls.X509KeyPair(cfg.Cert, cfg.Key) if err != nil { return nil, err } _, listeningPort, err := net.SplitHostPort(lis.Addr().String()) if err != nil { return nil, err } srv := &Server{ state: s, addr: net.JoinHostPort("localhost", listeningPort), dataDir: cfg.DataDir, logDir: cfg.LogDir, limiter: utils.NewLimiter(loginRateLimit), validator: cfg.Validator, } // TODO(rog) check that *srvRoot is a valid type for using // as an RPC server. lis = tls.NewListener(lis, &tls.Config{ Certificates: []tls.Certificate{tlsCert}, }) go srv.run(lis) return srv, nil }