1 // Copyright 2009 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.
26 type clientHandshakeState struct {
29 serverHello *serverHelloMsg
32 finishedHash finishedHash
34 session *ClientSessionState
37 func (c *Conn) makeClientHello() (*clientHelloMsg, ecdheParameters, error) {
39 if len(config.ServerName) == 0 && !config.InsecureSkipVerify {
40 return nil, nil, errors.New("tls: either ServerName or InsecureSkipVerify must be specified in the tls.Config")
44 for _, proto := range config.NextProtos {
45 if l := len(proto); l == 0 || l > 255 {
46 return nil, nil, errors.New("tls: invalid NextProtos value")
48 nextProtosLength += 1 + l
51 if nextProtosLength > 0xffff {
52 return nil, nil, errors.New("tls: NextProtos values too large")
55 supportedVersions := config.supportedVersions(roleClient)
56 if len(supportedVersions) == 0 {
57 return nil, nil, errors.New("tls: no supported versions satisfy MinVersion and MaxVersion")
60 clientHelloVersion := config.maxSupportedVersion(roleClient)
61 // The version at the beginning of the ClientHello was capped at TLS 1.2
62 // for compatibility reasons. The supported_versions extension is used
63 // to negotiate versions now. See RFC 8446, Section 4.2.1.
64 if clientHelloVersion > VersionTLS12 {
65 clientHelloVersion = VersionTLS12
68 hello := &clientHelloMsg{
69 vers: clientHelloVersion,
70 compressionMethods: []uint8{compressionNone},
71 random: make([]byte, 32),
72 sessionId: make([]byte, 32),
75 serverName: hostnameInSNI(config.ServerName),
76 supportedCurves: config.curvePreferences(),
77 supportedPoints: []uint8{pointFormatUncompressed},
78 secureRenegotiationSupported: true,
79 alpnProtocols: config.NextProtos,
80 supportedVersions: supportedVersions,
84 hello.secureRenegotiation = c.clientFinished[:]
87 preferenceOrder := cipherSuitesPreferenceOrder
88 if !hasAESGCMHardwareSupport {
89 preferenceOrder = cipherSuitesPreferenceOrderNoAES
91 configCipherSuites := config.cipherSuites()
92 hello.cipherSuites = make([]uint16, 0, len(configCipherSuites))
94 for _, suiteId := range preferenceOrder {
95 suite := mutualCipherSuite(configCipherSuites, suiteId)
99 // Don't advertise TLS 1.2-only cipher suites unless
100 // we're attempting TLS 1.2.
101 if hello.vers < VersionTLS12 && suite.flags&suiteTLS12 != 0 {
104 hello.cipherSuites = append(hello.cipherSuites, suiteId)
107 _, err := io.ReadFull(config.rand(), hello.random)
109 return nil, nil, errors.New("tls: short read from Rand: " + err.Error())
112 // A random session ID is used to detect when the server accepted a ticket
113 // and is resuming a session (see RFC 5077). In TLS 1.3, it's always set as
114 // a compatibility measure (see RFC 8446, Section 4.1.2).
115 if _, err := io.ReadFull(config.rand(), hello.sessionId); err != nil {
116 return nil, nil, errors.New("tls: short read from Rand: " + err.Error())
119 if hello.vers >= VersionTLS12 {
120 hello.supportedSignatureAlgorithms = supportedSignatureAlgorithms()
122 if testingOnlyForceClientHelloSignatureAlgorithms != nil {
123 hello.supportedSignatureAlgorithms = testingOnlyForceClientHelloSignatureAlgorithms
126 var params ecdheParameters
127 if hello.supportedVersions[0] == VersionTLS13 {
128 if hasAESGCMHardwareSupport {
129 hello.cipherSuites = append(hello.cipherSuites, defaultCipherSuitesTLS13...)
131 hello.cipherSuites = append(hello.cipherSuites, defaultCipherSuitesTLS13NoAES...)
134 curveID := config.curvePreferences()[0]
135 if _, ok := curveForCurveID(curveID); curveID != X25519 && !ok {
136 return nil, nil, errors.New("tls: CurvePreferences includes unsupported curve")
138 params, err = generateECDHEParameters(config.rand(), curveID)
142 hello.keyShares = []keyShare{{group: curveID, data: params.PublicKey()}}
145 return hello, params, nil
148 func (c *Conn) clientHandshake(ctx context.Context) (err error) {
150 c.config = defaultConfig()
153 // This may be a renegotiation handshake, in which case some fields
157 hello, ecdheParams, err := c.makeClientHello()
161 c.serverName = hello.serverName
163 cacheKey, session, earlySecret, binderKey := c.loadSession(hello)
164 if cacheKey != "" && session != nil {
166 // If we got a handshake failure when resuming a session, throw away
167 // the session ticket. See RFC 5077, Section 3.2.
169 // RFC 8446 makes no mention of dropping tickets on failure, but it
170 // does require servers to abort on invalid binders, so we need to
171 // delete tickets to recover from a corrupted PSK.
173 c.config.ClientSessionCache.Put(cacheKey, nil)
178 if _, err := c.writeRecord(recordTypeHandshake, hello.marshal()); err != nil {
182 msg, err := c.readHandshake()
187 serverHello, ok := msg.(*serverHelloMsg)
189 c.sendAlert(alertUnexpectedMessage)
190 return unexpectedMessageError(serverHello, msg)
193 if err := c.pickTLSVersion(serverHello); err != nil {
197 // If we are negotiating a protocol version that's lower than what we
198 // support, check for the server downgrade canaries.
199 // See RFC 8446, Section 4.1.3.
200 maxVers := c.config.maxSupportedVersion(roleClient)
201 tls12Downgrade := string(serverHello.random[24:]) == downgradeCanaryTLS12
202 tls11Downgrade := string(serverHello.random[24:]) == downgradeCanaryTLS11
203 if maxVers == VersionTLS13 && c.vers <= VersionTLS12 && (tls12Downgrade || tls11Downgrade) ||
204 maxVers == VersionTLS12 && c.vers <= VersionTLS11 && tls11Downgrade {
205 c.sendAlert(alertIllegalParameter)
206 return errors.New("tls: downgrade attempt detected, possibly due to a MitM attack or a broken middlebox")
209 if c.vers == VersionTLS13 {
210 hs := &clientHandshakeStateTLS13{
213 serverHello: serverHello,
215 ecdheParams: ecdheParams,
217 earlySecret: earlySecret,
218 binderKey: binderKey,
221 // In TLS 1.3, session tickets are delivered after the handshake.
222 return hs.handshake()
225 hs := &clientHandshakeState{
228 serverHello: serverHello,
233 if err := hs.handshake(); err != nil {
237 // If we had a successful handshake and hs.session is different from
238 // the one already cached - cache a new one.
239 if cacheKey != "" && hs.session != nil && session != hs.session {
240 c.config.ClientSessionCache.Put(cacheKey, hs.session)
246 func (c *Conn) loadSession(hello *clientHelloMsg) (cacheKey string,
247 session *ClientSessionState, earlySecret, binderKey []byte) {
248 if c.config.SessionTicketsDisabled || c.config.ClientSessionCache == nil {
249 return "", nil, nil, nil
252 hello.ticketSupported = true
254 if hello.supportedVersions[0] == VersionTLS13 {
255 // Require DHE on resumption as it guarantees forward secrecy against
256 // compromise of the session ticket key. See RFC 8446, Section 4.2.9.
257 hello.pskModes = []uint8{pskModeDHE}
260 // Session resumption is not allowed if renegotiating because
261 // renegotiation is primarily used to allow a client to send a client
262 // certificate, which would be skipped if session resumption occurred.
263 if c.handshakes != 0 {
264 return "", nil, nil, nil
267 // Try to resume a previously negotiated TLS session, if available.
268 cacheKey = clientSessionCacheKey(c.conn.RemoteAddr(), c.config)
269 session, ok := c.config.ClientSessionCache.Get(cacheKey)
270 if !ok || session == nil {
271 return cacheKey, nil, nil, nil
274 // Check that version used for the previous session is still valid.
276 for _, v := range hello.supportedVersions {
277 if v == session.vers {
283 return cacheKey, nil, nil, nil
286 // Check that the cached server certificate is not expired, and that it's
287 // valid for the ServerName. This should be ensured by the cache key, but
288 // protect the application from a faulty ClientSessionCache implementation.
289 if !c.config.InsecureSkipVerify {
290 if len(session.verifiedChains) == 0 {
291 // The original connection had InsecureSkipVerify, while this doesn't.
292 return cacheKey, nil, nil, nil
294 serverCert := session.serverCertificates[0]
295 if c.config.time().After(serverCert.NotAfter) {
296 // Expired certificate, delete the entry.
297 c.config.ClientSessionCache.Put(cacheKey, nil)
298 return cacheKey, nil, nil, nil
300 if err := serverCert.VerifyHostname(c.config.ServerName); err != nil {
301 return cacheKey, nil, nil, nil
305 if session.vers != VersionTLS13 {
306 // In TLS 1.2 the cipher suite must match the resumed session. Ensure we
307 // are still offering it.
308 if mutualCipherSuite(hello.cipherSuites, session.cipherSuite) == nil {
309 return cacheKey, nil, nil, nil
312 hello.sessionTicket = session.sessionTicket
316 // Check that the session ticket is not expired.
317 if c.config.time().After(session.useBy) {
318 c.config.ClientSessionCache.Put(cacheKey, nil)
319 return cacheKey, nil, nil, nil
322 // In TLS 1.3 the KDF hash must match the resumed session. Ensure we
323 // offer at least one cipher suite with that hash.
324 cipherSuite := cipherSuiteTLS13ByID(session.cipherSuite)
325 if cipherSuite == nil {
326 return cacheKey, nil, nil, nil
328 cipherSuiteOk := false
329 for _, offeredID := range hello.cipherSuites {
330 offeredSuite := cipherSuiteTLS13ByID(offeredID)
331 if offeredSuite != nil && offeredSuite.hash == cipherSuite.hash {
337 return cacheKey, nil, nil, nil
340 // Set the pre_shared_key extension. See RFC 8446, Section 4.2.11.1.
341 ticketAge := uint32(c.config.time().Sub(session.receivedAt) / time.Millisecond)
342 identity := pskIdentity{
343 label: session.sessionTicket,
344 obfuscatedTicketAge: ticketAge + session.ageAdd,
346 hello.pskIdentities = []pskIdentity{identity}
347 hello.pskBinders = [][]byte{make([]byte, cipherSuite.hash.Size())}
349 // Compute the PSK binders. See RFC 8446, Section 4.2.11.2.
350 psk := cipherSuite.expandLabel(session.masterSecret, "resumption",
351 session.nonce, cipherSuite.hash.Size())
352 earlySecret = cipherSuite.extract(psk, nil)
353 binderKey = cipherSuite.deriveSecret(earlySecret, resumptionBinderLabel, nil)
354 transcript := cipherSuite.hash.New()
355 transcript.Write(hello.marshalWithoutBinders())
356 pskBinders := [][]byte{cipherSuite.finishedHash(binderKey, transcript)}
357 hello.updateBinders(pskBinders)
362 func (c *Conn) pickTLSVersion(serverHello *serverHelloMsg) error {
363 peerVersion := serverHello.vers
364 if serverHello.supportedVersion != 0 {
365 peerVersion = serverHello.supportedVersion
368 vers, ok := c.config.mutualVersion(roleClient, []uint16{peerVersion})
370 c.sendAlert(alertProtocolVersion)
371 return fmt.Errorf("tls: server selected unsupported protocol version %x", peerVersion)
382 // Does the handshake, either a full one or resumes old session. Requires hs.c,
383 // hs.hello, hs.serverHello, and, optionally, hs.session to be set.
384 func (hs *clientHandshakeState) handshake() error {
387 isResume, err := hs.processServerHello()
392 hs.finishedHash = newFinishedHash(c.vers, hs.suite)
394 // No signatures of the handshake are needed in a resumption.
395 // Otherwise, in a full handshake, if we don't have any certificates
396 // configured then we will never send a CertificateVerify message and
397 // thus no signatures are needed in that case either.
398 if isResume || (len(c.config.Certificates) == 0 && c.config.GetClientCertificate == nil) {
399 hs.finishedHash.discardHandshakeBuffer()
402 hs.finishedHash.Write(hs.hello.marshal())
403 hs.finishedHash.Write(hs.serverHello.marshal())
406 c.didResume = isResume
408 if err := hs.establishKeys(); err != nil {
411 if err := hs.readSessionTicket(); err != nil {
414 if err := hs.readFinished(c.serverFinished[:]); err != nil {
417 c.clientFinishedIsFirst = false
418 // Make sure the connection is still being verified whether or not this
419 // is a resumption. Resumptions currently don't reverify certificates so
420 // they don't call verifyServerCertificate. See Issue 31641.
421 if c.config.VerifyConnection != nil {
422 if err := c.config.VerifyConnection(c.connectionStateLocked()); err != nil {
423 c.sendAlert(alertBadCertificate)
427 if err := hs.sendFinished(c.clientFinished[:]); err != nil {
430 if _, err := c.flush(); err != nil {
434 if err := hs.doFullHandshake(); err != nil {
437 if err := hs.establishKeys(); err != nil {
440 if err := hs.sendFinished(c.clientFinished[:]); err != nil {
443 if _, err := c.flush(); err != nil {
446 c.clientFinishedIsFirst = true
447 if err := hs.readSessionTicket(); err != nil {
450 if err := hs.readFinished(c.serverFinished[:]); err != nil {
455 c.ekm = ekmFromMasterSecret(c.vers, hs.suite, hs.masterSecret, hs.hello.random, hs.serverHello.random)
456 atomic.StoreUint32(&c.handshakeStatus, 1)
461 func (hs *clientHandshakeState) pickCipherSuite() error {
462 if hs.suite = mutualCipherSuite(hs.hello.cipherSuites, hs.serverHello.cipherSuite); hs.suite == nil {
463 hs.c.sendAlert(alertHandshakeFailure)
464 return errors.New("tls: server chose an unconfigured cipher suite")
467 hs.c.cipherSuite = hs.suite.id
471 func (hs *clientHandshakeState) doFullHandshake() error {
474 msg, err := c.readHandshake()
478 certMsg, ok := msg.(*certificateMsg)
479 if !ok || len(certMsg.certificates) == 0 {
480 c.sendAlert(alertUnexpectedMessage)
481 return unexpectedMessageError(certMsg, msg)
483 hs.finishedHash.Write(certMsg.marshal())
485 msg, err = c.readHandshake()
490 cs, ok := msg.(*certificateStatusMsg)
492 // RFC4366 on Certificate Status Request:
493 // The server MAY return a "certificate_status" message.
495 if !hs.serverHello.ocspStapling {
496 // If a server returns a "CertificateStatus" message, then the
497 // server MUST have included an extension of type "status_request"
498 // with empty "extension_data" in the extended server hello.
500 c.sendAlert(alertUnexpectedMessage)
501 return errors.New("tls: received unexpected CertificateStatus message")
503 hs.finishedHash.Write(cs.marshal())
505 c.ocspResponse = cs.response
507 msg, err = c.readHandshake()
513 if c.handshakes == 0 {
514 // If this is the first handshake on a connection, process and
515 // (optionally) verify the server's certificates.
516 if err := c.verifyServerCertificate(certMsg.certificates); err != nil {
520 // This is a renegotiation handshake. We require that the
521 // server's identity (i.e. leaf certificate) is unchanged and
522 // thus any previous trust decision is still valid.
524 // See https://mitls.org/pages/attacks/3SHAKE for the
525 // motivation behind this requirement.
526 if !bytes.Equal(c.peerCertificates[0].Raw, certMsg.certificates[0]) {
527 c.sendAlert(alertBadCertificate)
528 return errors.New("tls: server's identity changed during renegotiation")
532 keyAgreement := hs.suite.ka(c.vers)
534 skx, ok := msg.(*serverKeyExchangeMsg)
536 hs.finishedHash.Write(skx.marshal())
537 err = keyAgreement.processServerKeyExchange(c.config, hs.hello, hs.serverHello, c.peerCertificates[0], skx)
539 c.sendAlert(alertUnexpectedMessage)
543 msg, err = c.readHandshake()
549 var chainToSend *Certificate
550 var certRequested bool
551 certReq, ok := msg.(*certificateRequestMsg)
554 hs.finishedHash.Write(certReq.marshal())
556 cri := certificateRequestInfoFromMsg(hs.ctx, c.vers, certReq)
557 if chainToSend, err = c.getClientCertificate(cri); err != nil {
558 c.sendAlert(alertInternalError)
562 msg, err = c.readHandshake()
568 shd, ok := msg.(*serverHelloDoneMsg)
570 c.sendAlert(alertUnexpectedMessage)
571 return unexpectedMessageError(shd, msg)
573 hs.finishedHash.Write(shd.marshal())
575 // If the server requested a certificate then we have to send a
576 // Certificate message, even if it's empty because we don't have a
577 // certificate to send.
579 certMsg = new(certificateMsg)
580 certMsg.certificates = chainToSend.Certificate
581 hs.finishedHash.Write(certMsg.marshal())
582 if _, err := c.writeRecord(recordTypeHandshake, certMsg.marshal()); err != nil {
587 preMasterSecret, ckx, err := keyAgreement.generateClientKeyExchange(c.config, hs.hello, c.peerCertificates[0])
589 c.sendAlert(alertInternalError)
593 hs.finishedHash.Write(ckx.marshal())
594 if _, err := c.writeRecord(recordTypeHandshake, ckx.marshal()); err != nil {
599 if chainToSend != nil && len(chainToSend.Certificate) > 0 {
600 certVerify := &certificateVerifyMsg{}
602 key, ok := chainToSend.PrivateKey.(crypto.Signer)
604 c.sendAlert(alertInternalError)
605 return fmt.Errorf("tls: client certificate private key of type %T does not implement crypto.Signer", chainToSend.PrivateKey)
609 var sigHash crypto.Hash
610 if c.vers >= VersionTLS12 {
611 signatureAlgorithm, err := selectSignatureScheme(c.vers, chainToSend, certReq.supportedSignatureAlgorithms)
613 c.sendAlert(alertIllegalParameter)
616 sigType, sigHash, err = typeAndHashFromSignatureScheme(signatureAlgorithm)
618 return c.sendAlert(alertInternalError)
620 certVerify.hasSignatureAlgorithm = true
621 certVerify.signatureAlgorithm = signatureAlgorithm
623 sigType, sigHash, err = legacyTypeAndHashFromPublicKey(key.Public())
625 c.sendAlert(alertIllegalParameter)
630 signed := hs.finishedHash.hashForClientCertificate(sigType, sigHash, hs.masterSecret)
631 signOpts := crypto.SignerOpts(sigHash)
632 if sigType == signatureRSAPSS {
633 signOpts = &rsa.PSSOptions{SaltLength: rsa.PSSSaltLengthEqualsHash, Hash: sigHash}
635 certVerify.signature, err = key.Sign(c.config.rand(), signed, signOpts)
637 c.sendAlert(alertInternalError)
641 hs.finishedHash.Write(certVerify.marshal())
642 if _, err := c.writeRecord(recordTypeHandshake, certVerify.marshal()); err != nil {
647 hs.masterSecret = masterFromPreMasterSecret(c.vers, hs.suite, preMasterSecret, hs.hello.random, hs.serverHello.random)
648 if err := c.config.writeKeyLog(keyLogLabelTLS12, hs.hello.random, hs.masterSecret); err != nil {
649 c.sendAlert(alertInternalError)
650 return errors.New("tls: failed to write to key log: " + err.Error())
653 hs.finishedHash.discardHandshakeBuffer()
658 func (hs *clientHandshakeState) establishKeys() error {
661 clientMAC, serverMAC, clientKey, serverKey, clientIV, serverIV :=
662 keysFromMasterSecret(c.vers, hs.suite, hs.masterSecret, hs.hello.random, hs.serverHello.random, hs.suite.macLen, hs.suite.keyLen, hs.suite.ivLen)
663 var clientCipher, serverCipher interface{}
664 var clientHash, serverHash hash.Hash
665 if hs.suite.cipher != nil {
666 clientCipher = hs.suite.cipher(clientKey, clientIV, false /* not for reading */)
667 clientHash = hs.suite.mac(clientMAC)
668 serverCipher = hs.suite.cipher(serverKey, serverIV, true /* for reading */)
669 serverHash = hs.suite.mac(serverMAC)
671 clientCipher = hs.suite.aead(clientKey, clientIV)
672 serverCipher = hs.suite.aead(serverKey, serverIV)
675 c.in.prepareCipherSpec(c.vers, serverCipher, serverHash)
676 c.out.prepareCipherSpec(c.vers, clientCipher, clientHash)
680 func (hs *clientHandshakeState) serverResumedSession() bool {
681 // If the server responded with the same sessionId then it means the
682 // sessionTicket is being used to resume a TLS session.
683 return hs.session != nil && hs.hello.sessionId != nil &&
684 bytes.Equal(hs.serverHello.sessionId, hs.hello.sessionId)
687 func (hs *clientHandshakeState) processServerHello() (bool, error) {
690 if err := hs.pickCipherSuite(); err != nil {
694 if hs.serverHello.compressionMethod != compressionNone {
695 c.sendAlert(alertUnexpectedMessage)
696 return false, errors.New("tls: server selected unsupported compression format")
699 if c.handshakes == 0 && hs.serverHello.secureRenegotiationSupported {
700 c.secureRenegotiation = true
701 if len(hs.serverHello.secureRenegotiation) != 0 {
702 c.sendAlert(alertHandshakeFailure)
703 return false, errors.New("tls: initial handshake had non-empty renegotiation extension")
707 if c.handshakes > 0 && c.secureRenegotiation {
708 var expectedSecureRenegotiation [24]byte
709 copy(expectedSecureRenegotiation[:], c.clientFinished[:])
710 copy(expectedSecureRenegotiation[12:], c.serverFinished[:])
711 if !bytes.Equal(hs.serverHello.secureRenegotiation, expectedSecureRenegotiation[:]) {
712 c.sendAlert(alertHandshakeFailure)
713 return false, errors.New("tls: incorrect renegotiation extension contents")
717 if err := checkALPN(hs.hello.alpnProtocols, hs.serverHello.alpnProtocol); err != nil {
718 c.sendAlert(alertUnsupportedExtension)
721 c.clientProtocol = hs.serverHello.alpnProtocol
723 c.scts = hs.serverHello.scts
725 if !hs.serverResumedSession() {
729 if hs.session.vers != c.vers {
730 c.sendAlert(alertHandshakeFailure)
731 return false, errors.New("tls: server resumed a session with a different version")
734 if hs.session.cipherSuite != hs.suite.id {
735 c.sendAlert(alertHandshakeFailure)
736 return false, errors.New("tls: server resumed a session with a different cipher suite")
739 // Restore masterSecret, peerCerts, and ocspResponse from previous state
740 hs.masterSecret = hs.session.masterSecret
741 c.peerCertificates = hs.session.serverCertificates
742 c.verifiedChains = hs.session.verifiedChains
743 c.ocspResponse = hs.session.ocspResponse
744 // Let the ServerHello SCTs override the session SCTs from the original
745 // connection, if any are provided
746 if len(c.scts) == 0 && len(hs.session.scts) != 0 {
747 c.scts = hs.session.scts
753 // checkALPN ensure that the server's choice of ALPN protocol is compatible with
754 // the protocols that we advertised in the Client Hello.
755 func checkALPN(clientProtos []string, serverProto string) error {
756 if serverProto == "" {
759 if len(clientProtos) == 0 {
760 return errors.New("tls: server advertised unrequested ALPN extension")
762 for _, proto := range clientProtos {
763 if proto == serverProto {
767 return errors.New("tls: server selected unadvertised ALPN protocol")
770 func (hs *clientHandshakeState) readFinished(out []byte) error {
773 if err := c.readChangeCipherSpec(); err != nil {
777 msg, err := c.readHandshake()
781 serverFinished, ok := msg.(*finishedMsg)
783 c.sendAlert(alertUnexpectedMessage)
784 return unexpectedMessageError(serverFinished, msg)
787 verify := hs.finishedHash.serverSum(hs.masterSecret)
788 if len(verify) != len(serverFinished.verifyData) ||
789 subtle.ConstantTimeCompare(verify, serverFinished.verifyData) != 1 {
790 c.sendAlert(alertHandshakeFailure)
791 return errors.New("tls: server's Finished message was incorrect")
793 hs.finishedHash.Write(serverFinished.marshal())
798 func (hs *clientHandshakeState) readSessionTicket() error {
799 if !hs.serverHello.ticketSupported {
804 msg, err := c.readHandshake()
808 sessionTicketMsg, ok := msg.(*newSessionTicketMsg)
810 c.sendAlert(alertUnexpectedMessage)
811 return unexpectedMessageError(sessionTicketMsg, msg)
813 hs.finishedHash.Write(sessionTicketMsg.marshal())
815 hs.session = &ClientSessionState{
816 sessionTicket: sessionTicketMsg.ticket,
818 cipherSuite: hs.suite.id,
819 masterSecret: hs.masterSecret,
820 serverCertificates: c.peerCertificates,
821 verifiedChains: c.verifiedChains,
822 receivedAt: c.config.time(),
823 ocspResponse: c.ocspResponse,
830 func (hs *clientHandshakeState) sendFinished(out []byte) error {
833 if _, err := c.writeRecord(recordTypeChangeCipherSpec, []byte{1}); err != nil {
837 finished := new(finishedMsg)
838 finished.verifyData = hs.finishedHash.clientSum(hs.masterSecret)
839 hs.finishedHash.Write(finished.marshal())
840 if _, err := c.writeRecord(recordTypeHandshake, finished.marshal()); err != nil {
843 copy(out, finished.verifyData)
847 // verifyServerCertificate parses and verifies the provided chain, setting
848 // c.verifiedChains and c.peerCertificates or sending the appropriate alert.
849 func (c *Conn) verifyServerCertificate(certificates [][]byte) error {
850 certs := make([]*x509.Certificate, len(certificates))
851 for i, asn1Data := range certificates {
852 cert, err := x509.ParseCertificate(asn1Data)
854 c.sendAlert(alertBadCertificate)
855 return errors.New("tls: failed to parse certificate from server: " + err.Error())
860 if !c.config.InsecureSkipVerify {
861 opts := x509.VerifyOptions{
862 IsBoring: isBoringCertificate,
864 Roots: c.config.RootCAs,
865 CurrentTime: c.config.time(),
866 DNSName: c.config.ServerName,
867 Intermediates: x509.NewCertPool(),
869 for _, cert := range certs[1:] {
870 opts.Intermediates.AddCert(cert)
873 c.verifiedChains, err = certs[0].Verify(opts)
875 c.sendAlert(alertBadCertificate)
880 switch certs[0].PublicKey.(type) {
881 case *rsa.PublicKey, *ecdsa.PublicKey, ed25519.PublicKey:
884 c.sendAlert(alertUnsupportedCertificate)
885 return fmt.Errorf("tls: server's certificate contains an unsupported type of public key: %T", certs[0].PublicKey)
888 c.peerCertificates = certs
890 if c.config.VerifyPeerCertificate != nil {
891 if err := c.config.VerifyPeerCertificate(certificates, c.verifiedChains); err != nil {
892 c.sendAlert(alertBadCertificate)
897 if c.config.VerifyConnection != nil {
898 if err := c.config.VerifyConnection(c.connectionStateLocked()); err != nil {
899 c.sendAlert(alertBadCertificate)
907 // certificateRequestInfoFromMsg generates a CertificateRequestInfo from a TLS
908 // <= 1.2 CertificateRequest, making an effort to fill in missing information.
909 func certificateRequestInfoFromMsg(ctx context.Context, vers uint16, certReq *certificateRequestMsg) *CertificateRequestInfo {
910 cri := &CertificateRequestInfo{
911 AcceptableCAs: certReq.certificateAuthorities,
916 var rsaAvail, ecAvail bool
917 for _, certType := range certReq.certificateTypes {
919 case certTypeRSASign:
921 case certTypeECDSASign:
926 if !certReq.hasSignatureAlgorithm {
927 // Prior to TLS 1.2, signature schemes did not exist. In this case we
928 // make up a list based on the acceptable certificate types, to help
929 // GetClientCertificate and SupportsCertificate select the right certificate.
930 // The hash part of the SignatureScheme is a lie here, because
931 // TLS 1.0 and 1.1 always use MD5+SHA1 for RSA and SHA1 for ECDSA.
933 case rsaAvail && ecAvail:
934 cri.SignatureSchemes = []SignatureScheme{
935 ECDSAWithP256AndSHA256, ECDSAWithP384AndSHA384, ECDSAWithP521AndSHA512,
936 PKCS1WithSHA256, PKCS1WithSHA384, PKCS1WithSHA512, PKCS1WithSHA1,
939 cri.SignatureSchemes = []SignatureScheme{
940 PKCS1WithSHA256, PKCS1WithSHA384, PKCS1WithSHA512, PKCS1WithSHA1,
943 cri.SignatureSchemes = []SignatureScheme{
944 ECDSAWithP256AndSHA256, ECDSAWithP384AndSHA384, ECDSAWithP521AndSHA512,
950 // Filter the signature schemes based on the certificate types.
951 // See RFC 5246, Section 7.4.4 (where it calls this "somewhat complicated").
952 cri.SignatureSchemes = make([]SignatureScheme, 0, len(certReq.supportedSignatureAlgorithms))
953 for _, sigScheme := range certReq.supportedSignatureAlgorithms {
954 sigType, _, err := typeAndHashFromSignatureScheme(sigScheme)
959 case signatureECDSA, signatureEd25519:
961 cri.SignatureSchemes = append(cri.SignatureSchemes, sigScheme)
963 case signatureRSAPSS, signaturePKCS1v15:
965 cri.SignatureSchemes = append(cri.SignatureSchemes, sigScheme)
973 func (c *Conn) getClientCertificate(cri *CertificateRequestInfo) (*Certificate, error) {
974 if c.config.GetClientCertificate != nil {
975 return c.config.GetClientCertificate(cri)
978 for _, chain := range c.config.Certificates {
979 if err := cri.SupportsCertificate(&chain); err != nil {
985 // No acceptable certificate found. Don't send a certificate.
986 return new(Certificate), nil
989 // clientSessionCacheKey returns a key used to cache sessionTickets that could
990 // be used to resume previously negotiated TLS sessions with a server.
991 func clientSessionCacheKey(serverAddr net.Addr, config *Config) string {
992 if len(config.ServerName) > 0 {
993 return config.ServerName
995 return serverAddr.String()
998 // hostnameInSNI converts name into an appropriate hostname for SNI.
999 // Literal IP addresses and absolute FQDNs are not permitted as SNI values.
1000 // See RFC 6066, Section 3.
1001 func hostnameInSNI(name string) string {
1003 if len(host) > 0 && host[0] == '[' && host[len(host)-1] == ']' {
1004 host = host[1 : len(host)-1]
1006 if i := strings.LastIndex(host, "%"); i > 0 {
1009 if net.ParseIP(host) != nil {
1012 for len(name) > 0 && name[len(name)-1] == '.' {
1013 name = name[:len(name)-1]