github.com/ooni/psiphon/tunnel-core@v0.0.0-20230105123940-fe12a24c96ee/oovendor/qtls-go1-17/handshake_client_tls13.go (about) 1 // Copyright 2018 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 qtls 6 7 import ( 8 "bytes" 9 "context" 10 "crypto" 11 "crypto/hmac" 12 "crypto/rsa" 13 "encoding/binary" 14 "errors" 15 "fmt" 16 "hash" 17 "sync/atomic" 18 "time" 19 20 "golang.org/x/crypto/cryptobyte" 21 ) 22 23 type clientHandshakeStateTLS13 struct { 24 c *Conn 25 ctx context.Context 26 serverHello *serverHelloMsg 27 hello *clientHelloMsg 28 ecdheParams ecdheParameters 29 30 session *clientSessionState 31 earlySecret []byte 32 binderKey []byte 33 34 certReq *certificateRequestMsgTLS13 35 usingPSK bool 36 sentDummyCCS bool 37 suite *cipherSuiteTLS13 38 transcript hash.Hash 39 masterSecret []byte 40 trafficSecret []byte // client_application_traffic_secret_0 41 } 42 43 // handshake requires hs.c, hs.hello, hs.serverHello, hs.ecdheParams, and, 44 // optionally, hs.session, hs.earlySecret and hs.binderKey to be set. 45 func (hs *clientHandshakeStateTLS13) handshake() error { 46 c := hs.c 47 48 // The server must not select TLS 1.3 in a renegotiation. See RFC 8446, 49 // sections 4.1.2 and 4.1.3. 50 if c.handshakes > 0 { 51 c.sendAlert(alertProtocolVersion) 52 return errors.New("tls: server selected TLS 1.3 in a renegotiation") 53 } 54 55 // Consistency check on the presence of a keyShare and its parameters. 56 if hs.ecdheParams == nil || len(hs.hello.keyShares) != 1 { 57 return c.sendAlert(alertInternalError) 58 } 59 60 if err := hs.checkServerHelloOrHRR(); err != nil { 61 return err 62 } 63 64 hs.transcript = hs.suite.hash.New() 65 hs.transcript.Write(hs.hello.marshal()) 66 67 if bytes.Equal(hs.serverHello.random, helloRetryRequestRandom) { 68 if err := hs.sendDummyChangeCipherSpec(); err != nil { 69 return err 70 } 71 if err := hs.processHelloRetryRequest(); err != nil { 72 return err 73 } 74 } 75 76 hs.transcript.Write(hs.serverHello.marshal()) 77 78 c.buffering = true 79 if err := hs.processServerHello(); err != nil { 80 return err 81 } 82 if err := hs.sendDummyChangeCipherSpec(); err != nil { 83 return err 84 } 85 if err := hs.establishHandshakeKeys(); err != nil { 86 return err 87 } 88 if err := hs.readServerParameters(); err != nil { 89 return err 90 } 91 if err := hs.readServerCertificate(); err != nil { 92 return err 93 } 94 if err := hs.readServerFinished(); err != nil { 95 return err 96 } 97 if err := hs.sendClientCertificate(); err != nil { 98 return err 99 } 100 if err := hs.sendClientFinished(); err != nil { 101 return err 102 } 103 if _, err := c.flush(); err != nil { 104 return err 105 } 106 107 atomic.StoreUint32(&c.handshakeStatus, 1) 108 109 return nil 110 } 111 112 // checkServerHelloOrHRR does validity checks that apply to both ServerHello and 113 // HelloRetryRequest messages. It sets hs.suite. 114 func (hs *clientHandshakeStateTLS13) checkServerHelloOrHRR() error { 115 c := hs.c 116 117 if hs.serverHello.supportedVersion == 0 { 118 c.sendAlert(alertMissingExtension) 119 return errors.New("tls: server selected TLS 1.3 using the legacy version field") 120 } 121 122 if hs.serverHello.supportedVersion != VersionTLS13 { 123 c.sendAlert(alertIllegalParameter) 124 return errors.New("tls: server selected an invalid version after a HelloRetryRequest") 125 } 126 127 if hs.serverHello.vers != VersionTLS12 { 128 c.sendAlert(alertIllegalParameter) 129 return errors.New("tls: server sent an incorrect legacy version") 130 } 131 132 if hs.serverHello.ocspStapling || 133 hs.serverHello.ticketSupported || 134 hs.serverHello.secureRenegotiationSupported || 135 len(hs.serverHello.secureRenegotiation) != 0 || 136 len(hs.serverHello.alpnProtocol) != 0 || 137 len(hs.serverHello.scts) != 0 { 138 c.sendAlert(alertUnsupportedExtension) 139 return errors.New("tls: server sent a ServerHello extension forbidden in TLS 1.3") 140 } 141 142 if !bytes.Equal(hs.hello.sessionId, hs.serverHello.sessionId) { 143 c.sendAlert(alertIllegalParameter) 144 return errors.New("tls: server did not echo the legacy session ID") 145 } 146 147 if hs.serverHello.compressionMethod != compressionNone { 148 c.sendAlert(alertIllegalParameter) 149 return errors.New("tls: server selected unsupported compression format") 150 } 151 152 selectedSuite := mutualCipherSuiteTLS13(hs.hello.cipherSuites, hs.serverHello.cipherSuite) 153 if hs.suite != nil && selectedSuite != hs.suite { 154 c.sendAlert(alertIllegalParameter) 155 return errors.New("tls: server changed cipher suite after a HelloRetryRequest") 156 } 157 if selectedSuite == nil { 158 c.sendAlert(alertIllegalParameter) 159 return errors.New("tls: server chose an unconfigured cipher suite") 160 } 161 hs.suite = selectedSuite 162 c.cipherSuite = hs.suite.id 163 164 return nil 165 } 166 167 // sendDummyChangeCipherSpec sends a ChangeCipherSpec record for compatibility 168 // with middleboxes that didn't implement TLS correctly. See RFC 8446, Appendix D.4. 169 func (hs *clientHandshakeStateTLS13) sendDummyChangeCipherSpec() error { 170 if hs.sentDummyCCS { 171 return nil 172 } 173 hs.sentDummyCCS = true 174 175 _, err := hs.c.writeRecord(recordTypeChangeCipherSpec, []byte{1}) 176 return err 177 } 178 179 // processHelloRetryRequest handles the HRR in hs.serverHello, modifies and 180 // resends hs.hello, and reads the new ServerHello into hs.serverHello. 181 func (hs *clientHandshakeStateTLS13) processHelloRetryRequest() error { 182 c := hs.c 183 184 // The first ClientHello gets double-hashed into the transcript upon a 185 // HelloRetryRequest. (The idea is that the server might offload transcript 186 // storage to the client in the cookie.) See RFC 8446, Section 4.4.1. 187 chHash := hs.transcript.Sum(nil) 188 hs.transcript.Reset() 189 hs.transcript.Write([]byte{typeMessageHash, 0, 0, uint8(len(chHash))}) 190 hs.transcript.Write(chHash) 191 hs.transcript.Write(hs.serverHello.marshal()) 192 193 // The only HelloRetryRequest extensions we support are key_share and 194 // cookie, and clients must abort the handshake if the HRR would not result 195 // in any change in the ClientHello. 196 if hs.serverHello.selectedGroup == 0 && hs.serverHello.cookie == nil { 197 c.sendAlert(alertIllegalParameter) 198 return errors.New("tls: server sent an unnecessary HelloRetryRequest message") 199 } 200 201 if hs.serverHello.cookie != nil { 202 hs.hello.cookie = hs.serverHello.cookie 203 } 204 205 if hs.serverHello.serverShare.group != 0 { 206 c.sendAlert(alertDecodeError) 207 return errors.New("tls: received malformed key_share extension") 208 } 209 210 // If the server sent a key_share extension selecting a group, ensure it's 211 // a group we advertised but did not send a key share for, and send a key 212 // share for it this time. 213 if curveID := hs.serverHello.selectedGroup; curveID != 0 { 214 curveOK := false 215 for _, id := range hs.hello.supportedCurves { 216 if id == curveID { 217 curveOK = true 218 break 219 } 220 } 221 if !curveOK { 222 c.sendAlert(alertIllegalParameter) 223 return errors.New("tls: server selected unsupported group") 224 } 225 if hs.ecdheParams.CurveID() == curveID { 226 c.sendAlert(alertIllegalParameter) 227 return errors.New("tls: server sent an unnecessary HelloRetryRequest key_share") 228 } 229 if _, ok := curveForCurveID(curveID); curveID != X25519 && !ok { 230 c.sendAlert(alertInternalError) 231 return errors.New("tls: CurvePreferences includes unsupported curve") 232 } 233 params, err := generateECDHEParameters(c.config.rand(), curveID) 234 if err != nil { 235 c.sendAlert(alertInternalError) 236 return err 237 } 238 hs.ecdheParams = params 239 hs.hello.keyShares = []keyShare{{group: curveID, data: params.PublicKey()}} 240 } 241 242 hs.hello.raw = nil 243 if len(hs.hello.pskIdentities) > 0 { 244 pskSuite := cipherSuiteTLS13ByID(hs.session.cipherSuite) 245 if pskSuite == nil { 246 return c.sendAlert(alertInternalError) 247 } 248 if pskSuite.hash == hs.suite.hash { 249 // Update binders and obfuscated_ticket_age. 250 ticketAge := uint32(c.config.time().Sub(hs.session.receivedAt) / time.Millisecond) 251 hs.hello.pskIdentities[0].obfuscatedTicketAge = ticketAge + hs.session.ageAdd 252 253 transcript := hs.suite.hash.New() 254 transcript.Write([]byte{typeMessageHash, 0, 0, uint8(len(chHash))}) 255 transcript.Write(chHash) 256 transcript.Write(hs.serverHello.marshal()) 257 transcript.Write(hs.hello.marshalWithoutBinders()) 258 pskBinders := [][]byte{hs.suite.finishedHash(hs.binderKey, transcript)} 259 hs.hello.updateBinders(pskBinders) 260 } else { 261 // Server selected a cipher suite incompatible with the PSK. 262 hs.hello.pskIdentities = nil 263 hs.hello.pskBinders = nil 264 } 265 } 266 267 if hs.hello.earlyData && c.extraConfig != nil && c.extraConfig.Rejected0RTT != nil { 268 c.extraConfig.Rejected0RTT() 269 } 270 hs.hello.earlyData = false // disable 0-RTT 271 272 hs.transcript.Write(hs.hello.marshal()) 273 if _, err := c.writeRecord(recordTypeHandshake, hs.hello.marshal()); err != nil { 274 return err 275 } 276 277 msg, err := c.readHandshake() 278 if err != nil { 279 return err 280 } 281 282 serverHello, ok := msg.(*serverHelloMsg) 283 if !ok { 284 c.sendAlert(alertUnexpectedMessage) 285 return unexpectedMessageError(serverHello, msg) 286 } 287 hs.serverHello = serverHello 288 289 if err := hs.checkServerHelloOrHRR(); err != nil { 290 return err 291 } 292 293 return nil 294 } 295 296 func (hs *clientHandshakeStateTLS13) processServerHello() error { 297 c := hs.c 298 299 if bytes.Equal(hs.serverHello.random, helloRetryRequestRandom) { 300 c.sendAlert(alertUnexpectedMessage) 301 return errors.New("tls: server sent two HelloRetryRequest messages") 302 } 303 304 if len(hs.serverHello.cookie) != 0 { 305 c.sendAlert(alertUnsupportedExtension) 306 return errors.New("tls: server sent a cookie in a normal ServerHello") 307 } 308 309 if hs.serverHello.selectedGroup != 0 { 310 c.sendAlert(alertDecodeError) 311 return errors.New("tls: malformed key_share extension") 312 } 313 314 if hs.serverHello.serverShare.group == 0 { 315 c.sendAlert(alertIllegalParameter) 316 return errors.New("tls: server did not send a key share") 317 } 318 if hs.serverHello.serverShare.group != hs.ecdheParams.CurveID() { 319 c.sendAlert(alertIllegalParameter) 320 return errors.New("tls: server selected unsupported group") 321 } 322 323 if !hs.serverHello.selectedIdentityPresent { 324 return nil 325 } 326 327 if int(hs.serverHello.selectedIdentity) >= len(hs.hello.pskIdentities) { 328 c.sendAlert(alertIllegalParameter) 329 return errors.New("tls: server selected an invalid PSK") 330 } 331 332 if len(hs.hello.pskIdentities) != 1 || hs.session == nil { 333 return c.sendAlert(alertInternalError) 334 } 335 pskSuite := cipherSuiteTLS13ByID(hs.session.cipherSuite) 336 if pskSuite == nil { 337 return c.sendAlert(alertInternalError) 338 } 339 if pskSuite.hash != hs.suite.hash { 340 c.sendAlert(alertIllegalParameter) 341 return errors.New("tls: server selected an invalid PSK and cipher suite pair") 342 } 343 344 hs.usingPSK = true 345 c.didResume = true 346 c.peerCertificates = hs.session.serverCertificates 347 c.verifiedChains = hs.session.verifiedChains 348 c.ocspResponse = hs.session.ocspResponse 349 c.scts = hs.session.scts 350 return nil 351 } 352 353 func (hs *clientHandshakeStateTLS13) establishHandshakeKeys() error { 354 c := hs.c 355 356 sharedKey := hs.ecdheParams.SharedKey(hs.serverHello.serverShare.data) 357 if sharedKey == nil { 358 c.sendAlert(alertIllegalParameter) 359 return errors.New("tls: invalid server key share") 360 } 361 362 earlySecret := hs.earlySecret 363 if !hs.usingPSK { 364 earlySecret = hs.suite.extract(nil, nil) 365 } 366 handshakeSecret := hs.suite.extract(sharedKey, 367 hs.suite.deriveSecret(earlySecret, "derived", nil)) 368 369 clientSecret := hs.suite.deriveSecret(handshakeSecret, 370 clientHandshakeTrafficLabel, hs.transcript) 371 c.out.exportKey(EncryptionHandshake, hs.suite, clientSecret) 372 c.out.setTrafficSecret(hs.suite, clientSecret) 373 serverSecret := hs.suite.deriveSecret(handshakeSecret, 374 serverHandshakeTrafficLabel, hs.transcript) 375 c.in.exportKey(EncryptionHandshake, hs.suite, serverSecret) 376 c.in.setTrafficSecret(hs.suite, serverSecret) 377 378 err := c.config.writeKeyLog(keyLogLabelClientHandshake, hs.hello.random, clientSecret) 379 if err != nil { 380 c.sendAlert(alertInternalError) 381 return err 382 } 383 err = c.config.writeKeyLog(keyLogLabelServerHandshake, hs.hello.random, serverSecret) 384 if err != nil { 385 c.sendAlert(alertInternalError) 386 return err 387 } 388 389 hs.masterSecret = hs.suite.extract(nil, 390 hs.suite.deriveSecret(handshakeSecret, "derived", nil)) 391 392 return nil 393 } 394 395 func (hs *clientHandshakeStateTLS13) readServerParameters() error { 396 c := hs.c 397 398 msg, err := c.readHandshake() 399 if err != nil { 400 return err 401 } 402 403 encryptedExtensions, ok := msg.(*encryptedExtensionsMsg) 404 if !ok { 405 c.sendAlert(alertUnexpectedMessage) 406 return unexpectedMessageError(encryptedExtensions, msg) 407 } 408 // Notify the caller if 0-RTT was rejected. 409 if !encryptedExtensions.earlyData && hs.hello.earlyData && c.extraConfig != nil && c.extraConfig.Rejected0RTT != nil { 410 c.extraConfig.Rejected0RTT() 411 } 412 c.used0RTT = encryptedExtensions.earlyData 413 if hs.c.extraConfig != nil && hs.c.extraConfig.ReceivedExtensions != nil { 414 hs.c.extraConfig.ReceivedExtensions(typeEncryptedExtensions, encryptedExtensions.additionalExtensions) 415 } 416 hs.transcript.Write(encryptedExtensions.marshal()) 417 418 if c.extraConfig != nil && c.extraConfig.EnforceNextProtoSelection { 419 if len(encryptedExtensions.alpnProtocol) == 0 { 420 // the server didn't select an ALPN 421 c.sendAlert(alertNoApplicationProtocol) 422 return errors.New("ALPN negotiation failed. Server didn't offer any protocols") 423 } 424 if mutualProtocol([]string{encryptedExtensions.alpnProtocol}, hs.c.config.NextProtos) == "" { 425 // the protocol selected by the server was not offered 426 c.sendAlert(alertNoApplicationProtocol) 427 return fmt.Errorf("ALPN negotiation failed. Server offered: %q", encryptedExtensions.alpnProtocol) 428 } 429 } 430 if encryptedExtensions.alpnProtocol != "" { 431 if len(hs.hello.alpnProtocols) == 0 { 432 c.sendAlert(alertUnsupportedExtension) 433 return errors.New("tls: server advertised unrequested ALPN extension") 434 } 435 if mutualProtocol([]string{encryptedExtensions.alpnProtocol}, hs.hello.alpnProtocols) == "" { 436 c.sendAlert(alertUnsupportedExtension) 437 return errors.New("tls: server selected unadvertised ALPN protocol") 438 } 439 c.clientProtocol = encryptedExtensions.alpnProtocol 440 } 441 return nil 442 } 443 444 func (hs *clientHandshakeStateTLS13) readServerCertificate() error { 445 c := hs.c 446 447 // Either a PSK or a certificate is always used, but not both. 448 // See RFC 8446, Section 4.1.1. 449 if hs.usingPSK { 450 // Make sure the connection is still being verified whether or not this 451 // is a resumption. Resumptions currently don't reverify certificates so 452 // they don't call verifyServerCertificate. See Issue 31641. 453 if c.config.VerifyConnection != nil { 454 if err := c.config.VerifyConnection(c.connectionStateLocked()); err != nil { 455 c.sendAlert(alertBadCertificate) 456 return err 457 } 458 } 459 return nil 460 } 461 462 msg, err := c.readHandshake() 463 if err != nil { 464 return err 465 } 466 467 certReq, ok := msg.(*certificateRequestMsgTLS13) 468 if ok { 469 hs.transcript.Write(certReq.marshal()) 470 471 hs.certReq = certReq 472 473 msg, err = c.readHandshake() 474 if err != nil { 475 return err 476 } 477 } 478 479 certMsg, ok := msg.(*certificateMsgTLS13) 480 if !ok { 481 c.sendAlert(alertUnexpectedMessage) 482 return unexpectedMessageError(certMsg, msg) 483 } 484 if len(certMsg.certificate.Certificate) == 0 { 485 c.sendAlert(alertDecodeError) 486 return errors.New("tls: received empty certificates message") 487 } 488 hs.transcript.Write(certMsg.marshal()) 489 490 c.scts = certMsg.certificate.SignedCertificateTimestamps 491 c.ocspResponse = certMsg.certificate.OCSPStaple 492 493 if err := c.verifyServerCertificate(certMsg.certificate.Certificate); err != nil { 494 return err 495 } 496 497 msg, err = c.readHandshake() 498 if err != nil { 499 return err 500 } 501 502 certVerify, ok := msg.(*certificateVerifyMsg) 503 if !ok { 504 c.sendAlert(alertUnexpectedMessage) 505 return unexpectedMessageError(certVerify, msg) 506 } 507 508 // See RFC 8446, Section 4.4.3. 509 if !isSupportedSignatureAlgorithm(certVerify.signatureAlgorithm, supportedSignatureAlgorithms) { 510 c.sendAlert(alertIllegalParameter) 511 return errors.New("tls: certificate used with invalid signature algorithm") 512 } 513 sigType, sigHash, err := typeAndHashFromSignatureScheme(certVerify.signatureAlgorithm) 514 if err != nil { 515 return c.sendAlert(alertInternalError) 516 } 517 if sigType == signaturePKCS1v15 || sigHash == crypto.SHA1 { 518 c.sendAlert(alertIllegalParameter) 519 return errors.New("tls: certificate used with invalid signature algorithm") 520 } 521 signed := signedMessage(sigHash, serverSignatureContext, hs.transcript) 522 if err := verifyHandshakeSignature(sigType, c.peerCertificates[0].PublicKey, 523 sigHash, signed, certVerify.signature); err != nil { 524 c.sendAlert(alertDecryptError) 525 return errors.New("tls: invalid signature by the server certificate: " + err.Error()) 526 } 527 528 hs.transcript.Write(certVerify.marshal()) 529 530 return nil 531 } 532 533 func (hs *clientHandshakeStateTLS13) readServerFinished() error { 534 c := hs.c 535 536 msg, err := c.readHandshake() 537 if err != nil { 538 return err 539 } 540 541 finished, ok := msg.(*finishedMsg) 542 if !ok { 543 c.sendAlert(alertUnexpectedMessage) 544 return unexpectedMessageError(finished, msg) 545 } 546 547 expectedMAC := hs.suite.finishedHash(c.in.trafficSecret, hs.transcript) 548 if !hmac.Equal(expectedMAC, finished.verifyData) { 549 c.sendAlert(alertDecryptError) 550 return errors.New("tls: invalid server finished hash") 551 } 552 553 hs.transcript.Write(finished.marshal()) 554 555 // Derive secrets that take context through the server Finished. 556 557 hs.trafficSecret = hs.suite.deriveSecret(hs.masterSecret, 558 clientApplicationTrafficLabel, hs.transcript) 559 serverSecret := hs.suite.deriveSecret(hs.masterSecret, 560 serverApplicationTrafficLabel, hs.transcript) 561 c.in.exportKey(EncryptionApplication, hs.suite, serverSecret) 562 c.in.setTrafficSecret(hs.suite, serverSecret) 563 564 err = c.config.writeKeyLog(keyLogLabelClientTraffic, hs.hello.random, hs.trafficSecret) 565 if err != nil { 566 c.sendAlert(alertInternalError) 567 return err 568 } 569 err = c.config.writeKeyLog(keyLogLabelServerTraffic, hs.hello.random, serverSecret) 570 if err != nil { 571 c.sendAlert(alertInternalError) 572 return err 573 } 574 575 c.ekm = hs.suite.exportKeyingMaterial(hs.masterSecret, hs.transcript) 576 577 return nil 578 } 579 580 func (hs *clientHandshakeStateTLS13) sendClientCertificate() error { 581 c := hs.c 582 583 if hs.certReq == nil { 584 return nil 585 } 586 587 cert, err := c.getClientCertificate(toCertificateRequestInfo(&certificateRequestInfo{ 588 AcceptableCAs: hs.certReq.certificateAuthorities, 589 SignatureSchemes: hs.certReq.supportedSignatureAlgorithms, 590 Version: c.vers, 591 ctx: hs.ctx, 592 })) 593 if err != nil { 594 return err 595 } 596 597 certMsg := new(certificateMsgTLS13) 598 599 certMsg.certificate = *cert 600 certMsg.scts = hs.certReq.scts && len(cert.SignedCertificateTimestamps) > 0 601 certMsg.ocspStapling = hs.certReq.ocspStapling && len(cert.OCSPStaple) > 0 602 603 hs.transcript.Write(certMsg.marshal()) 604 if _, err := c.writeRecord(recordTypeHandshake, certMsg.marshal()); err != nil { 605 return err 606 } 607 608 // If we sent an empty certificate message, skip the CertificateVerify. 609 if len(cert.Certificate) == 0 { 610 return nil 611 } 612 613 certVerifyMsg := new(certificateVerifyMsg) 614 certVerifyMsg.hasSignatureAlgorithm = true 615 616 certVerifyMsg.signatureAlgorithm, err = selectSignatureScheme(c.vers, cert, hs.certReq.supportedSignatureAlgorithms) 617 if err != nil { 618 // getClientCertificate returned a certificate incompatible with the 619 // CertificateRequestInfo supported signature algorithms. 620 c.sendAlert(alertHandshakeFailure) 621 return err 622 } 623 624 sigType, sigHash, err := typeAndHashFromSignatureScheme(certVerifyMsg.signatureAlgorithm) 625 if err != nil { 626 return c.sendAlert(alertInternalError) 627 } 628 629 signed := signedMessage(sigHash, clientSignatureContext, hs.transcript) 630 signOpts := crypto.SignerOpts(sigHash) 631 if sigType == signatureRSAPSS { 632 signOpts = &rsa.PSSOptions{SaltLength: rsa.PSSSaltLengthEqualsHash, Hash: sigHash} 633 } 634 sig, err := cert.PrivateKey.(crypto.Signer).Sign(c.config.rand(), signed, signOpts) 635 if err != nil { 636 c.sendAlert(alertInternalError) 637 return errors.New("tls: failed to sign handshake: " + err.Error()) 638 } 639 certVerifyMsg.signature = sig 640 641 hs.transcript.Write(certVerifyMsg.marshal()) 642 if _, err := c.writeRecord(recordTypeHandshake, certVerifyMsg.marshal()); err != nil { 643 return err 644 } 645 646 return nil 647 } 648 649 func (hs *clientHandshakeStateTLS13) sendClientFinished() error { 650 c := hs.c 651 652 finished := &finishedMsg{ 653 verifyData: hs.suite.finishedHash(c.out.trafficSecret, hs.transcript), 654 } 655 656 hs.transcript.Write(finished.marshal()) 657 if _, err := c.writeRecord(recordTypeHandshake, finished.marshal()); err != nil { 658 return err 659 } 660 661 c.out.exportKey(EncryptionApplication, hs.suite, hs.trafficSecret) 662 c.out.setTrafficSecret(hs.suite, hs.trafficSecret) 663 664 if !c.config.SessionTicketsDisabled && c.config.ClientSessionCache != nil { 665 c.resumptionSecret = hs.suite.deriveSecret(hs.masterSecret, 666 resumptionLabel, hs.transcript) 667 } 668 669 return nil 670 } 671 672 func (c *Conn) handleNewSessionTicket(msg *newSessionTicketMsgTLS13) error { 673 if !c.isClient { 674 c.sendAlert(alertUnexpectedMessage) 675 return errors.New("tls: received new session ticket from a client") 676 } 677 678 if c.config.SessionTicketsDisabled || c.config.ClientSessionCache == nil { 679 return nil 680 } 681 682 // See RFC 8446, Section 4.6.1. 683 if msg.lifetime == 0 { 684 return nil 685 } 686 lifetime := time.Duration(msg.lifetime) * time.Second 687 if lifetime > maxSessionTicketLifetime { 688 c.sendAlert(alertIllegalParameter) 689 return errors.New("tls: received a session ticket with invalid lifetime") 690 } 691 692 cipherSuite := cipherSuiteTLS13ByID(c.cipherSuite) 693 if cipherSuite == nil || c.resumptionSecret == nil { 694 return c.sendAlert(alertInternalError) 695 } 696 697 // We need to save the max_early_data_size that the server sent us, in order 698 // to decide if we're going to try 0-RTT with this ticket. 699 // However, at the same time, the qtls.ClientSessionTicket needs to be equal to 700 // the tls.ClientSessionTicket, so we can't just add a new field to the struct. 701 // We therefore abuse the nonce field (which is a byte slice) 702 nonceWithEarlyData := make([]byte, len(msg.nonce)+4) 703 binary.BigEndian.PutUint32(nonceWithEarlyData, msg.maxEarlyData) 704 copy(nonceWithEarlyData[4:], msg.nonce) 705 706 var appData []byte 707 if c.extraConfig != nil && c.extraConfig.GetAppDataForSessionState != nil { 708 appData = c.extraConfig.GetAppDataForSessionState() 709 } 710 var b cryptobyte.Builder 711 b.AddUint16(clientSessionStateVersion) // revision 712 b.AddUint32(msg.maxEarlyData) 713 b.AddUint16LengthPrefixed(func(b *cryptobyte.Builder) { 714 b.AddBytes(appData) 715 }) 716 b.AddUint16LengthPrefixed(func(b *cryptobyte.Builder) { 717 b.AddBytes(msg.nonce) 718 }) 719 720 // Save the resumption_master_secret and nonce instead of deriving the PSK 721 // to do the least amount of work on NewSessionTicket messages before we 722 // know if the ticket will be used. Forward secrecy of resumed connections 723 // is guaranteed by the requirement for pskModeDHE. 724 session := &clientSessionState{ 725 sessionTicket: msg.label, 726 vers: c.vers, 727 cipherSuite: c.cipherSuite, 728 masterSecret: c.resumptionSecret, 729 serverCertificates: c.peerCertificates, 730 verifiedChains: c.verifiedChains, 731 receivedAt: c.config.time(), 732 nonce: b.BytesOrPanic(), 733 useBy: c.config.time().Add(lifetime), 734 ageAdd: msg.ageAdd, 735 ocspResponse: c.ocspResponse, 736 scts: c.scts, 737 } 738 739 cacheKey := clientSessionCacheKey(c.conn.RemoteAddr(), c.config) 740 c.config.ClientSessionCache.Put(cacheKey, toClientSessionState(session)) 741 742 return nil 743 }