blob: 45dc75d13c66aeaddc2028fd642c7e86af33b269 [file] [log] [blame]
Adam Langleyd9e397b2015-01-22 14:27:53 -08001// 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.
4
Kenny Roote99801b2015-11-06 15:31:15 -08005package runner
Adam Langleyd9e397b2015-01-22 14:27:53 -08006
7import (
8 "bytes"
David Benjaminc895d6b2016-08-11 13:26:41 -04009 "crypto"
Adam Langleyd9e397b2015-01-22 14:27:53 -080010 "crypto/ecdsa"
11 "crypto/elliptic"
12 "crypto/rsa"
13 "crypto/subtle"
14 "crypto/x509"
Adam Langleyd9e397b2015-01-22 14:27:53 -080015 "errors"
16 "fmt"
17 "io"
18 "math/big"
19 "net"
David Benjaminc895d6b2016-08-11 13:26:41 -040020 "time"
Robert Sloan572a4e22017-04-17 10:52:19 -070021
Robert Sloanf573be72018-09-17 15:29:11 -070022 "boringssl.googlesource.com/boringssl/ssl/test/runner/ed25519"
Adam Langleyd9e397b2015-01-22 14:27:53 -080023)
24
25type clientHandshakeState struct {
Adam Langleye9ada862015-05-11 17:20:37 -070026 c *Conn
27 serverHello *serverHelloMsg
28 hello *clientHelloMsg
29 suite *cipherSuite
30 finishedHash finishedHash
David Benjaminc895d6b2016-08-11 13:26:41 -040031 keyShares map[CurveID]ecdhCurve
Adam Langleye9ada862015-05-11 17:20:37 -070032 masterSecret []byte
33 session *ClientSessionState
34 finishedBytes []byte
Robert Sloan4c22c5f2019-03-01 15:53:37 -080035 peerPublicKey crypto.PublicKey
36 skxAlgo signatureAlgorithm
Adam Langleyd9e397b2015-01-22 14:27:53 -080037}
38
Robert Sloanf6200e72017-07-10 08:09:18 -070039func mapClientHelloVersion(vers uint16, isDTLS bool) uint16 {
40 if !isDTLS {
41 return vers
42 }
43
44 switch vers {
45 case VersionTLS12:
46 return VersionDTLS12
47 case VersionTLS10:
48 return VersionDTLS10
49 }
50
51 panic("Unknown ClientHello version.")
52}
53
Robert Sloanc9abfe42018-11-26 12:19:07 -080054func fixClientHellos(hello *clientHelloMsg, in []byte) ([]byte, error) {
55 ret := append([]byte{}, in...)
56 newHello := new(clientHelloMsg)
57 if !newHello.unmarshal(ret) {
58 return nil, errors.New("tls: invalid ClientHello")
59 }
60
61 hello.random = newHello.random
62 hello.sessionId = newHello.sessionId
63
64 // Replace |ret|'s key shares with those of |hello|. For simplicity, we
65 // require their lengths match, which is satisfied by matching the
66 // DefaultCurves setting to the selection in the replacement
67 // ClientHello.
68 bb := newByteBuilder()
69 hello.marshalKeyShares(bb)
70 keyShares := bb.finish()
71 if len(keyShares) != len(newHello.keySharesRaw) {
72 return nil, errors.New("tls: ClientHello key share length is inconsistent with DefaultCurves setting")
73 }
74 // |newHello.keySharesRaw| aliases |ret|.
75 copy(newHello.keySharesRaw, keyShares)
76
77 return ret, nil
78}
79
Adam Langleyd9e397b2015-01-22 14:27:53 -080080func (c *Conn) clientHandshake() error {
81 if c.config == nil {
82 c.config = defaultConfig()
83 }
84
85 if len(c.config.ServerName) == 0 && !c.config.InsecureSkipVerify {
86 return errors.New("tls: either ServerName or InsecureSkipVerify must be specified in the tls.Config")
87 }
88
89 c.sendHandshakeSeq = 0
90 c.recvHandshakeSeq = 0
91
92 nextProtosLength := 0
93 for _, proto := range c.config.NextProtos {
Kenny Rootb8494592015-09-25 02:29:14 +000094 if l := len(proto); l > 255 {
Adam Langleyd9e397b2015-01-22 14:27:53 -080095 return errors.New("tls: invalid NextProtos value")
96 } else {
97 nextProtosLength += 1 + l
98 }
99 }
100 if nextProtosLength > 0xffff {
101 return errors.New("tls: NextProtos values too large")
102 }
103
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400104 minVersion := c.config.minVersion(c.isDTLS)
105 maxVersion := c.config.maxVersion(c.isDTLS)
Adam Langleyd9e397b2015-01-22 14:27:53 -0800106 hello := &clientHelloMsg{
107 isDTLS: c.isDTLS,
Adam Langleyd9e397b2015-01-22 14:27:53 -0800108 compressionMethods: []uint8{compressionNone},
109 random: make([]byte, 32),
Steven Valdez909b19f2016-11-21 15:35:44 -0500110 ocspStapling: !c.config.Bugs.NoOCSPStapling,
111 sctListSupported: !c.config.Bugs.NoSignedCertificateTimestamps,
Adam Langleyd9e397b2015-01-22 14:27:53 -0800112 serverName: c.config.ServerName,
113 supportedCurves: c.config.curvePreferences(),
114 supportedPoints: []uint8{pointFormatUncompressed},
115 nextProtoNeg: len(c.config.NextProtos) > 0,
116 secureRenegotiation: []byte{},
117 alpnProtocols: c.config.NextProtos,
Robert Sloan8542c082018-02-05 09:07:34 -0800118 quicTransportParams: c.config.QUICTransportParams,
Adam Langleyd9e397b2015-01-22 14:27:53 -0800119 duplicateExtension: c.config.Bugs.DuplicateExtension,
120 channelIDSupported: c.config.ChannelID != nil,
Robert Sloan978112c2018-01-22 12:53:01 -0800121 tokenBindingParams: c.config.TokenBindingParams,
122 tokenBindingVersion: c.config.TokenBindingVersion,
Steven Valdez909b19f2016-11-21 15:35:44 -0500123 npnAfterAlpn: c.config.Bugs.SwapNPNAndALPN,
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400124 extendedMasterSecret: maxVersion >= VersionTLS10,
Adam Langleyd9e397b2015-01-22 14:27:53 -0800125 srtpProtectionProfiles: c.config.SRTPProtectionProfiles,
126 srtpMasterKeyIdentifier: c.config.Bugs.SRTPMasterKeyIdentifer,
Kenny Rootb8494592015-09-25 02:29:14 +0000127 customExtension: c.config.Bugs.CustomExtension,
Steven Valdez909b19f2016-11-21 15:35:44 -0500128 pskBinderFirst: c.config.Bugs.PSKBinderFirst,
Robert Sloana12bf462017-07-17 07:08:26 -0700129 omitExtensions: c.config.Bugs.OmitExtensions,
130 emptyExtensions: c.config.Bugs.EmptyExtensions,
Robert Sloan4c22c5f2019-03-01 15:53:37 -0800131 delegatedCredentials: !c.config.Bugs.DisableDelegatedCredentials,
Adam Langleyd9e397b2015-01-22 14:27:53 -0800132 }
133
Robert Sloanf6200e72017-07-10 08:09:18 -0700134 if maxVersion >= VersionTLS13 {
135 hello.vers = mapClientHelloVersion(VersionTLS12, c.isDTLS)
136 if !c.config.Bugs.OmitSupportedVersions {
137 hello.supportedVersions = c.config.supportedVersions(c.isDTLS)
138 }
Robert Sloana12bf462017-07-17 07:08:26 -0700139 hello.pskKEModes = []byte{pskDHEKEMode}
Robert Sloanf6200e72017-07-10 08:09:18 -0700140 } else {
141 hello.vers = mapClientHelloVersion(maxVersion, c.isDTLS)
142 }
143
144 if c.config.Bugs.SendClientVersion != 0 {
145 hello.vers = c.config.Bugs.SendClientVersion
146 }
147
148 if len(c.config.Bugs.SendSupportedVersions) > 0 {
149 hello.supportedVersions = c.config.Bugs.SendSupportedVersions
150 }
151
David Benjaminf0c4a6c2016-08-11 13:26:41 -0400152 disableEMS := c.config.Bugs.NoExtendedMasterSecret
153 if c.cipherSuite != nil {
154 disableEMS = c.config.Bugs.NoExtendedMasterSecretOnRenegotiation
Adam Langleyd9e397b2015-01-22 14:27:53 -0800155 }
156
David Benjaminf0c4a6c2016-08-11 13:26:41 -0400157 if disableEMS {
Adam Langleyd9e397b2015-01-22 14:27:53 -0800158 hello.extendedMasterSecret = false
159 }
160
Adam Langleye9ada862015-05-11 17:20:37 -0700161 if c.config.Bugs.NoSupportedCurves {
162 hello.supportedCurves = nil
163 }
164
Steven Valdez909b19f2016-11-21 15:35:44 -0500165 if len(c.config.Bugs.SendPSKKeyExchangeModes) != 0 {
166 hello.pskKEModes = c.config.Bugs.SendPSKKeyExchangeModes
167 }
168
David Benjaminf0c4a6c2016-08-11 13:26:41 -0400169 if c.config.Bugs.SendCompressionMethods != nil {
170 hello.compressionMethods = c.config.Bugs.SendCompressionMethods
171 }
172
Robert Sloan69939df2017-01-09 10:53:07 -0800173 if c.config.Bugs.SendSupportedPointFormats != nil {
174 hello.supportedPoints = c.config.Bugs.SendSupportedPointFormats
175 }
176
Adam Langleyd9e397b2015-01-22 14:27:53 -0800177 if len(c.clientVerify) > 0 && !c.config.Bugs.EmptyRenegotiationInfo {
178 if c.config.Bugs.BadRenegotiationInfo {
179 hello.secureRenegotiation = append(hello.secureRenegotiation, c.clientVerify...)
180 hello.secureRenegotiation[0] ^= 0x80
181 } else {
182 hello.secureRenegotiation = c.clientVerify
183 }
184 }
185
Adam Vartanianbfcf3a72018-08-10 14:55:24 +0100186 if c.config.Bugs.DuplicateCompressedCertAlgs {
187 hello.compressedCertAlgs = []uint16{1, 1}
188 } else if len(c.config.CertCompressionAlgs) > 0 {
189 hello.compressedCertAlgs = make([]uint16, 0, len(c.config.CertCompressionAlgs))
190 for id, _ := range c.config.CertCompressionAlgs {
191 hello.compressedCertAlgs = append(hello.compressedCertAlgs, uint16(id))
192 }
193 }
194
Adam Langley4139edb2016-01-13 15:00:54 -0800195 if c.noRenegotiationInfo() {
Adam Langleyd9e397b2015-01-22 14:27:53 -0800196 hello.secureRenegotiation = nil
197 }
198
David Benjaminc895d6b2016-08-11 13:26:41 -0400199 var keyShares map[CurveID]ecdhCurve
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400200 if maxVersion >= VersionTLS13 {
David Benjaminc895d6b2016-08-11 13:26:41 -0400201 keyShares = make(map[CurveID]ecdhCurve)
202 hello.hasKeyShares = true
David Benjamin7c0d06c2016-08-11 13:26:41 -0400203 hello.trailingKeyShareData = c.config.Bugs.TrailingKeyShareData
David Benjaminc895d6b2016-08-11 13:26:41 -0400204 curvesToSend := c.config.defaultCurves()
205 for _, curveID := range hello.supportedCurves {
206 if !curvesToSend[curveID] {
207 continue
208 }
Robert Sloanab8b8882018-03-26 11:39:51 -0700209 curve, ok := curveForCurveID(curveID, c.config)
David Benjaminc895d6b2016-08-11 13:26:41 -0400210 if !ok {
211 continue
212 }
213 publicKey, err := curve.offer(c.config.rand())
214 if err != nil {
215 return err
216 }
217
218 if c.config.Bugs.SendCurve != 0 {
219 curveID = c.config.Bugs.SendCurve
220 }
221 if c.config.Bugs.InvalidECDHPoint {
222 publicKey[0] ^= 0xff
223 }
224
225 hello.keyShares = append(hello.keyShares, keyShareEntry{
226 group: curveID,
227 keyExchange: publicKey,
228 })
229 keyShares[curveID] = curve
230
231 if c.config.Bugs.DuplicateKeyShares {
232 hello.keyShares = append(hello.keyShares, hello.keyShares[len(hello.keyShares)-1])
233 }
234 }
235
236 if c.config.Bugs.MissingKeyShare {
237 hello.hasKeyShares = false
238 }
239 }
240
Adam Langleyd9e397b2015-01-22 14:27:53 -0800241 possibleCipherSuites := c.config.cipherSuites()
242 hello.cipherSuites = make([]uint16, 0, len(possibleCipherSuites))
243
244NextCipherSuite:
245 for _, suiteId := range possibleCipherSuites {
246 for _, suite := range cipherSuites {
247 if suite.id != suiteId {
248 continue
249 }
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400250 // Don't advertise TLS 1.2-only cipher suites unless
251 // we're attempting TLS 1.2.
252 if maxVersion < VersionTLS12 && suite.flags&suiteTLS12 != 0 {
253 continue
254 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800255 hello.cipherSuites = append(hello.cipherSuites, suiteId)
256 continue NextCipherSuite
257 }
258 }
259
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400260 if c.config.Bugs.AdvertiseAllConfiguredCiphers {
261 hello.cipherSuites = possibleCipherSuites
262 }
263
Kenny Rootb8494592015-09-25 02:29:14 +0000264 if c.config.Bugs.SendRenegotiationSCSV {
265 hello.cipherSuites = append(hello.cipherSuites, renegotiationSCSV)
266 }
267
Adam Langleyd9e397b2015-01-22 14:27:53 -0800268 if c.config.Bugs.SendFallbackSCSV {
269 hello.cipherSuites = append(hello.cipherSuites, fallbackSCSV)
270 }
271
272 _, err := io.ReadFull(c.config.rand(), hello.random)
273 if err != nil {
274 c.sendAlert(alertInternalError)
275 return errors.New("tls: short read from Rand: " + err.Error())
276 }
277
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400278 if maxVersion >= VersionTLS12 && !c.config.Bugs.NoSignatureAlgorithms {
David Benjaminc895d6b2016-08-11 13:26:41 -0400279 hello.signatureAlgorithms = c.config.verifySignatureAlgorithms()
Adam Langleyd9e397b2015-01-22 14:27:53 -0800280 }
281
282 var session *ClientSessionState
283 var cacheKey string
284 sessionCache := c.config.ClientSessionCache
285
286 if sessionCache != nil {
287 hello.ticketSupported = !c.config.SessionTicketsDisabled
288
289 // Try to resume a previously negotiated TLS session, if
290 // available.
291 cacheKey = clientSessionCacheKey(c.conn.RemoteAddr(), c.config)
David Benjaminc895d6b2016-08-11 13:26:41 -0400292 // TODO(nharper): Support storing more than one session
293 // ticket for TLS 1.3.
Adam Langleyd9e397b2015-01-22 14:27:53 -0800294 candidateSession, ok := sessionCache.Get(cacheKey)
295 if ok {
296 ticketOk := !c.config.SessionTicketsDisabled || candidateSession.sessionTicket == nil
297
298 // Check that the ciphersuite/version used for the
299 // previous session are still valid.
300 cipherSuiteOk := false
Steven Valdez909b19f2016-11-21 15:35:44 -0500301 if candidateSession.vers <= VersionTLS12 {
302 for _, id := range hello.cipherSuites {
303 if id == candidateSession.cipherSuite {
304 cipherSuiteOk = true
305 break
306 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800307 }
Steven Valdez909b19f2016-11-21 15:35:44 -0500308 } else {
309 // TLS 1.3 allows the cipher to change on
310 // resumption.
311 cipherSuiteOk = true
Adam Langleyd9e397b2015-01-22 14:27:53 -0800312 }
313
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400314 versOk := candidateSession.vers >= minVersion &&
315 candidateSession.vers <= maxVersion
Adam Langleyd9e397b2015-01-22 14:27:53 -0800316 if ticketOk && versOk && cipherSuiteOk {
317 session = candidateSession
318 }
319 }
320 }
321
Steven Valdez909b19f2016-11-21 15:35:44 -0500322 var pskCipherSuite *cipherSuite
David Benjaminc895d6b2016-08-11 13:26:41 -0400323 if session != nil && c.config.time().Before(session.ticketExpiration) {
324 ticket := session.sessionTicket
Steven Valdez909b19f2016-11-21 15:35:44 -0500325 if c.config.Bugs.FilterTicket != nil && len(ticket) > 0 {
326 // Copy the ticket so FilterTicket may act in-place.
David Benjaminc895d6b2016-08-11 13:26:41 -0400327 ticket = make([]byte, len(session.sessionTicket))
328 copy(ticket, session.sessionTicket)
Steven Valdez909b19f2016-11-21 15:35:44 -0500329
330 ticket, err = c.config.Bugs.FilterTicket(ticket)
331 if err != nil {
332 return err
David Benjaminc895d6b2016-08-11 13:26:41 -0400333 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400334 }
335
David Benjaminf0c4a6c2016-08-11 13:26:41 -0400336 if session.vers >= VersionTLS13 || c.config.Bugs.SendBothTickets {
Steven Valdez909b19f2016-11-21 15:35:44 -0500337 pskCipherSuite = cipherSuiteFromID(session.cipherSuite)
338 if pskCipherSuite == nil {
339 return errors.New("tls: client session cache has invalid cipher suite")
340 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400341 // TODO(nharper): Support sending more
342 // than one PSK identity.
Steven Valdez909b19f2016-11-21 15:35:44 -0500343 ticketAge := uint32(c.config.time().Sub(session.ticketCreationTime) / time.Millisecond)
Robert Sloan1c9db532017-03-13 08:03:59 -0700344 if c.config.Bugs.SendTicketAge != 0 {
345 ticketAge = uint32(c.config.Bugs.SendTicketAge / time.Millisecond)
346 }
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400347 psk := pskIdentity{
Steven Valdez909b19f2016-11-21 15:35:44 -0500348 ticket: ticket,
349 obfuscatedTicketAge: session.ticketAgeAdd + ticketAge,
Adam Langleyd9e397b2015-01-22 14:27:53 -0800350 }
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400351 hello.pskIdentities = []pskIdentity{psk}
Steven Valdez909b19f2016-11-21 15:35:44 -0500352
353 if c.config.Bugs.ExtraPSKIdentity {
354 hello.pskIdentities = append(hello.pskIdentities, psk)
355 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800356 }
David Benjaminf0c4a6c2016-08-11 13:26:41 -0400357
358 if session.vers < VersionTLS13 || c.config.Bugs.SendBothTickets {
359 if ticket != nil {
360 hello.sessionTicket = ticket
361 // A random session ID is used to detect when the
362 // server accepted the ticket and is resuming a session
363 // (see RFC 5077).
364 sessionIdLen := 16
Robert Sloan5d625782017-02-13 09:55:39 -0800365 if c.config.Bugs.TicketSessionIDLength != 0 {
366 sessionIdLen = c.config.Bugs.TicketSessionIDLength
367 }
368 if c.config.Bugs.EmptyTicketSessionID {
369 sessionIdLen = 0
David Benjaminf0c4a6c2016-08-11 13:26:41 -0400370 }
371 hello.sessionId = make([]byte, sessionIdLen)
372 if _, err := io.ReadFull(c.config.rand(), hello.sessionId); err != nil {
373 c.sendAlert(alertInternalError)
374 return errors.New("tls: short read from Rand: " + err.Error())
375 }
376 } else {
377 hello.sessionId = session.sessionId
378 }
379 }
380 }
381
Robert Sloanab8b8882018-03-26 11:39:51 -0700382 // Request compatibility mode from the client by sending a fake session
383 // ID. Although BoringSSL always enables compatibility mode, other
384 // implementations make it conditional on the ClientHello. We test
385 // BoringSSL's expected behavior with SendClientHelloSessionID.
386 if len(hello.sessionId) == 0 && maxVersion >= VersionTLS13 {
387 hello.sessionId = make([]byte, 32)
388 if _, err := io.ReadFull(c.config.rand(), hello.sessionId); err != nil {
389 c.sendAlert(alertInternalError)
390 return errors.New("tls: short read from Rand: " + err.Error())
391 }
392 }
393
Steven Valdez909b19f2016-11-21 15:35:44 -0500394 if c.config.Bugs.SendCipherSuites != nil {
395 hello.cipherSuites = c.config.Bugs.SendCipherSuites
396 }
397
Robert Sloan47f43ed2017-02-06 14:55:15 -0800398 var sendEarlyData bool
Robert Sloan6d0d00e2017-03-27 07:13:07 -0700399 if len(hello.pskIdentities) > 0 && c.config.Bugs.SendEarlyData != nil {
David Benjamin1b249672016-12-06 18:25:50 -0500400 hello.hasEarlyData = true
Robert Sloan47f43ed2017-02-06 14:55:15 -0800401 sendEarlyData = true
402 }
403 if c.config.Bugs.SendFakeEarlyDataLength > 0 {
404 hello.hasEarlyData = true
405 }
406 if c.config.Bugs.OmitEarlyDataExtension {
407 hello.hasEarlyData = false
David Benjamin1b249672016-12-06 18:25:50 -0500408 }
Robert Sloanb6d070c2017-07-24 08:40:01 -0700409 if c.config.Bugs.SendClientHelloSessionID != nil {
410 hello.sessionId = c.config.Bugs.SendClientHelloSessionID
411 }
David Benjamin1b249672016-12-06 18:25:50 -0500412
Adam Langleyd9e397b2015-01-22 14:27:53 -0800413 var helloBytes []byte
414 if c.config.Bugs.SendV2ClientHello {
415 // Test that the peer left-pads random.
416 hello.random[0] = 0
417 v2Hello := &v2ClientHelloMsg{
418 vers: hello.vers,
419 cipherSuites: hello.cipherSuites,
420 // No session resumption for V2ClientHello.
421 sessionId: nil,
422 challenge: hello.random[1:],
423 }
424 helloBytes = v2Hello.marshal()
425 c.writeV2Record(helloBytes)
426 } else {
Steven Valdez909b19f2016-11-21 15:35:44 -0500427 if len(hello.pskIdentities) > 0 {
Robert Sloanb1b54b82017-11-06 13:50:02 -0800428 version := session.wireVersion
429 // We may have a pre-1.3 session if SendBothTickets is
Robert Sloan4c22c5f2019-03-01 15:53:37 -0800430 // set.
Robert Sloanb1b54b82017-11-06 13:50:02 -0800431 if session.vers < VersionTLS13 {
Robert Sloan4c22c5f2019-03-01 15:53:37 -0800432 version = VersionTLS13
Robert Sloanb1b54b82017-11-06 13:50:02 -0800433 }
434 generatePSKBinders(version, hello, pskCipherSuite, session.masterSecret, []byte{}, []byte{}, c.config)
Steven Valdez909b19f2016-11-21 15:35:44 -0500435 }
Robert Sloanc9abfe42018-11-26 12:19:07 -0800436 if c.config.Bugs.SendClientHelloWithFixes != nil {
437 helloBytes, err = fixClientHellos(hello, c.config.Bugs.SendClientHelloWithFixes)
438 if err != nil {
439 return err
440 }
441 } else {
442 helloBytes = hello.marshal()
443 }
Steven Valdez909b19f2016-11-21 15:35:44 -0500444
David Benjaminc895d6b2016-08-11 13:26:41 -0400445 if c.config.Bugs.PartialClientFinishedWithClientHello {
446 // Include one byte of Finished. We can compute it
447 // without completing the handshake. This assumes we
448 // negotiate TLS 1.3 with no HelloRetryRequest or
449 // CertificateRequest.
450 toWrite := make([]byte, 0, len(helloBytes)+1)
451 toWrite = append(toWrite, helloBytes...)
452 toWrite = append(toWrite, typeFinished)
453 c.writeRecord(recordTypeHandshake, toWrite)
454 } else {
455 c.writeRecord(recordTypeHandshake, helloBytes)
456 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800457 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400458 c.flushHandshake()
Adam Langleyd9e397b2015-01-22 14:27:53 -0800459
Adam Langleye9ada862015-05-11 17:20:37 -0700460 if err := c.simulatePacketLoss(nil); err != nil {
461 return err
462 }
David Benjamin1b249672016-12-06 18:25:50 -0500463 if c.config.Bugs.SendEarlyAlert {
464 c.sendAlert(alertHandshakeFailure)
465 }
Robert Sloan47f43ed2017-02-06 14:55:15 -0800466 if c.config.Bugs.SendFakeEarlyDataLength > 0 {
467 c.sendFakeEarlyData(c.config.Bugs.SendFakeEarlyDataLength)
David Benjamin1b249672016-12-06 18:25:50 -0500468 }
Robert Sloan47f43ed2017-02-06 14:55:15 -0800469
470 // Derive early write keys and set Conn state to allow early writes.
471 if sendEarlyData {
Robert Sloanb1b54b82017-11-06 13:50:02 -0800472 finishedHash := newFinishedHash(session.wireVersion, c.isDTLS, pskCipherSuite)
Robert Sloan47f43ed2017-02-06 14:55:15 -0800473 finishedHash.addEntropy(session.masterSecret)
474 finishedHash.Write(helloBytes)
Robert Sloanb1b54b82017-11-06 13:50:02 -0800475
Robert Sloan8542c082018-02-05 09:07:34 -0800476 if !c.config.Bugs.SkipChangeCipherSpec {
Robert Sloand5c22152017-11-13 09:22:12 -0800477 c.wireVersion = session.wireVersion
Robert Sloan0da43952018-01-03 15:13:14 -0800478 c.vers = VersionTLS13
Robert Sloand5c22152017-11-13 09:22:12 -0800479 c.writeRecord(recordTypeChangeCipherSpec, []byte{1})
480 c.wireVersion = 0
Robert Sloan0da43952018-01-03 15:13:14 -0800481 c.vers = 0
Robert Sloand5c22152017-11-13 09:22:12 -0800482 }
483
Robert Sloan8542c082018-02-05 09:07:34 -0800484 earlyTrafficSecret := finishedHash.deriveSecret(earlyTrafficLabel)
485 c.earlyExporterSecret = finishedHash.deriveSecret(earlyExporterLabel)
Robert Sloan55818102017-12-18 11:26:17 -0800486
Robert Sloan29c1d2c2017-10-30 14:10:28 -0700487 c.useOutTrafficSecret(session.wireVersion, pskCipherSuite, earlyTrafficSecret)
Robert Sloan47f43ed2017-02-06 14:55:15 -0800488 for _, earlyData := range c.config.Bugs.SendEarlyData {
489 if _, err := c.writeRecord(recordTypeApplicationData, earlyData); err != nil {
490 return err
491 }
492 }
493 }
494
Adam Langleyd9e397b2015-01-22 14:27:53 -0800495 msg, err := c.readHandshake()
496 if err != nil {
497 return err
498 }
499
500 if c.isDTLS {
501 helloVerifyRequest, ok := msg.(*helloVerifyRequestMsg)
502 if ok {
Robert Sloanf6200e72017-07-10 08:09:18 -0700503 if helloVerifyRequest.vers != VersionDTLS10 {
Adam Langleyd9e397b2015-01-22 14:27:53 -0800504 // Per RFC 6347, the version field in
505 // HelloVerifyRequest SHOULD be always DTLS
506 // 1.0. Enforce this for testing purposes.
507 return errors.New("dtls: bad HelloVerifyRequest version")
508 }
509
510 hello.raw = nil
511 hello.cookie = helloVerifyRequest.cookie
512 helloBytes = hello.marshal()
513 c.writeRecord(recordTypeHandshake, helloBytes)
David Benjaminc895d6b2016-08-11 13:26:41 -0400514 c.flushHandshake()
Adam Langleyd9e397b2015-01-22 14:27:53 -0800515
Adam Langleye9ada862015-05-11 17:20:37 -0700516 if err := c.simulatePacketLoss(nil); err != nil {
517 return err
518 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800519 msg, err = c.readHandshake()
520 if err != nil {
521 return err
522 }
523 }
524 }
525
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400526 var serverWireVersion uint16
David Benjaminc895d6b2016-08-11 13:26:41 -0400527 switch m := msg.(type) {
528 case *helloRetryRequestMsg:
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400529 serverWireVersion = m.vers
David Benjaminc895d6b2016-08-11 13:26:41 -0400530 case *serverHelloMsg:
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400531 serverWireVersion = m.vers
David Benjaminc895d6b2016-08-11 13:26:41 -0400532 default:
533 c.sendAlert(alertUnexpectedMessage)
534 return fmt.Errorf("tls: received unexpected message of type %T when waiting for HelloRetryRequest or ServerHello", msg)
535 }
536
Robert Sloanf6200e72017-07-10 08:09:18 -0700537 serverVersion, ok := c.config.isSupportedVersion(serverWireVersion, c.isDTLS)
David Benjaminc895d6b2016-08-11 13:26:41 -0400538 if !ok {
539 c.sendAlert(alertProtocolVersion)
540 return fmt.Errorf("tls: server selected unsupported protocol version %x", c.vers)
541 }
Robert Sloanf6200e72017-07-10 08:09:18 -0700542 c.wireVersion = serverWireVersion
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400543 c.vers = serverVersion
David Benjaminc895d6b2016-08-11 13:26:41 -0400544 c.haveVers = true
545
Robert Sloan8542c082018-02-05 09:07:34 -0800546 if c.vers >= VersionTLS13 {
Robert Sloan99319a12017-11-27 10:32:46 -0800547 // The first server message must be followed by a ChangeCipherSpec.
548 c.expectTLS13ChangeCipherSpec = true
549 }
550
David Benjaminc895d6b2016-08-11 13:26:41 -0400551 helloRetryRequest, haveHelloRetryRequest := msg.(*helloRetryRequestMsg)
552 var secondHelloBytes []byte
553 if haveHelloRetryRequest {
Robert Sloan11c28bd2018-12-17 12:09:20 -0800554 if c.config.Bugs.FailIfHelloRetryRequested {
555 return errors.New("tls: unexpected HelloRetryRequest")
556 }
Robert Sloan8542c082018-02-05 09:07:34 -0800557 // Explicitly read the ChangeCipherSpec now; it should
558 // be attached to the first flight, not the second flight.
559 if err := c.readTLS13ChangeCipherSpec(); err != nil {
560 return err
Robert Sloand5c22152017-11-13 09:22:12 -0800561 }
562
Robert Sloan47f43ed2017-02-06 14:55:15 -0800563 c.out.resetCipher()
David Benjamin95add822016-10-19 01:09:12 -0400564 if len(helloRetryRequest.cookie) > 0 {
565 hello.tls13Cookie = helloRetryRequest.cookie
566 }
567
David Benjaminc895d6b2016-08-11 13:26:41 -0400568 if c.config.Bugs.MisinterpretHelloRetryRequestCurve != 0 {
David Benjamin95add822016-10-19 01:09:12 -0400569 helloRetryRequest.hasSelectedGroup = true
David Benjaminc895d6b2016-08-11 13:26:41 -0400570 helloRetryRequest.selectedGroup = c.config.Bugs.MisinterpretHelloRetryRequestCurve
571 }
David Benjamin95add822016-10-19 01:09:12 -0400572 if helloRetryRequest.hasSelectedGroup {
573 var hrrCurveFound bool
574 group := helloRetryRequest.selectedGroup
575 for _, curveID := range hello.supportedCurves {
576 if group == curveID {
577 hrrCurveFound = true
578 break
579 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400580 }
David Benjamin95add822016-10-19 01:09:12 -0400581 if !hrrCurveFound || keyShares[group] != nil {
582 c.sendAlert(alertHandshakeFailure)
583 return errors.New("tls: received invalid HelloRetryRequest")
584 }
Robert Sloanab8b8882018-03-26 11:39:51 -0700585 curve, ok := curveForCurveID(group, c.config)
David Benjamin95add822016-10-19 01:09:12 -0400586 if !ok {
587 return errors.New("tls: Unable to get curve requested in HelloRetryRequest")
588 }
589 publicKey, err := curve.offer(c.config.rand())
590 if err != nil {
591 return err
592 }
593 keyShares[group] = curve
Steven Valdez909b19f2016-11-21 15:35:44 -0500594 hello.keyShares = []keyShareEntry{{
David Benjamin95add822016-10-19 01:09:12 -0400595 group: group,
596 keyExchange: publicKey,
Steven Valdez909b19f2016-11-21 15:35:44 -0500597 }}
David Benjaminc895d6b2016-08-11 13:26:41 -0400598 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400599
600 if c.config.Bugs.SecondClientHelloMissingKeyShare {
601 hello.hasKeyShares = false
602 }
603
David Benjamin1b249672016-12-06 18:25:50 -0500604 hello.hasEarlyData = c.config.Bugs.SendEarlyDataOnSecondClientHello
David Benjaminc895d6b2016-08-11 13:26:41 -0400605 hello.raw = nil
606
Steven Valdez909b19f2016-11-21 15:35:44 -0500607 if len(hello.pskIdentities) > 0 {
Robert Sloanb1b54b82017-11-06 13:50:02 -0800608 generatePSKBinders(c.wireVersion, hello, pskCipherSuite, session.masterSecret, helloBytes, helloRetryRequest.marshal(), c.config)
Steven Valdez909b19f2016-11-21 15:35:44 -0500609 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400610 secondHelloBytes = hello.marshal()
David Benjamin1b249672016-12-06 18:25:50 -0500611
612 if c.config.Bugs.InterleaveEarlyData {
613 c.sendFakeEarlyData(4)
614 c.writeRecord(recordTypeHandshake, secondHelloBytes[:16])
615 c.sendFakeEarlyData(4)
616 c.writeRecord(recordTypeHandshake, secondHelloBytes[16:])
617 } else {
618 c.writeRecord(recordTypeHandshake, secondHelloBytes)
619 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400620 c.flushHandshake()
621
David Benjamin1b249672016-12-06 18:25:50 -0500622 if c.config.Bugs.SendEarlyDataOnSecondClientHello {
623 c.sendFakeEarlyData(4)
624 }
625
David Benjaminc895d6b2016-08-11 13:26:41 -0400626 msg, err = c.readHandshake()
627 if err != nil {
628 return err
629 }
630 }
631
Adam Langleyd9e397b2015-01-22 14:27:53 -0800632 serverHello, ok := msg.(*serverHelloMsg)
633 if !ok {
634 c.sendAlert(alertUnexpectedMessage)
635 return unexpectedMessageError(serverHello, msg)
636 }
637
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400638 if serverWireVersion != serverHello.vers {
Adam Vartanianbfcf3a72018-08-10 14:55:24 +0100639 c.sendAlert(alertIllegalParameter)
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400640 return fmt.Errorf("tls: server sent non-matching version %x vs %x", serverWireVersion, serverHello.vers)
Adam Langleyd9e397b2015-01-22 14:27:53 -0800641 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800642
Robert Sloand9e572d2018-08-27 12:27:00 -0700643 _, supportsTLS13 := c.config.isSupportedVersion(VersionTLS13, false)
644 // Check for downgrade signals in the server random, per RFC 8446, section 4.1.3.
Robert Sloanc9abfe42018-11-26 12:19:07 -0800645 gotDowngrade := serverHello.random[len(serverHello.random)-8:]
Robert Sloand9e572d2018-08-27 12:27:00 -0700646 if (supportsTLS13 || c.config.Bugs.CheckTLS13DowngradeRandom) && !c.config.Bugs.IgnoreTLS13DowngradeRandom {
647 if c.vers <= VersionTLS12 && c.config.maxVersion(c.isDTLS) >= VersionTLS13 {
Robert Sloanc9abfe42018-11-26 12:19:07 -0800648 if bytes.Equal(gotDowngrade, downgradeTLS13) {
Robert Sloand9e572d2018-08-27 12:27:00 -0700649 c.sendAlert(alertProtocolVersion)
650 return errors.New("tls: downgrade from TLS 1.3 detected")
651 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400652 }
Robert Sloand9e572d2018-08-27 12:27:00 -0700653 if c.vers <= VersionTLS11 && c.config.maxVersion(c.isDTLS) >= VersionTLS12 {
Robert Sloanc9abfe42018-11-26 12:19:07 -0800654 if bytes.Equal(gotDowngrade, downgradeTLS12) {
Robert Sloand9e572d2018-08-27 12:27:00 -0700655 c.sendAlert(alertProtocolVersion)
656 return errors.New("tls: downgrade from TLS 1.2 detected")
657 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400658 }
659 }
660
Robert Sloanc9abfe42018-11-26 12:19:07 -0800661 if bytes.Equal(gotDowngrade, downgradeJDK11) != c.config.Bugs.ExpectJDK11DowngradeRandom {
662 c.sendAlert(alertProtocolVersion)
663 if c.config.Bugs.ExpectJDK11DowngradeRandom {
664 return errors.New("tls: server did not send a JDK 11 downgrade signal")
665 }
666 return errors.New("tls: server sent an unexpected JDK 11 downgrade signal")
667 }
668
David Benjaminc895d6b2016-08-11 13:26:41 -0400669 suite := mutualCipherSuite(hello.cipherSuites, serverHello.cipherSuite)
Adam Langleyd9e397b2015-01-22 14:27:53 -0800670 if suite == nil {
671 c.sendAlert(alertHandshakeFailure)
672 return fmt.Errorf("tls: server selected an unsupported cipher suite")
673 }
674
David Benjamin95add822016-10-19 01:09:12 -0400675 if haveHelloRetryRequest && helloRetryRequest.hasSelectedGroup && helloRetryRequest.selectedGroup != serverHello.keyShare.group {
David Benjaminc895d6b2016-08-11 13:26:41 -0400676 c.sendAlert(alertHandshakeFailure)
677 return errors.New("tls: ServerHello parameters did not match HelloRetryRequest")
Kenny Rootb8494592015-09-25 02:29:14 +0000678 }
679
Robert Sloana27a6a42017-09-05 08:39:28 -0700680 if c.config.Bugs.ExpectOmitExtensions && !serverHello.omitExtensions {
681 return errors.New("tls: ServerHello did not omit extensions")
682 }
683
Adam Langleyd9e397b2015-01-22 14:27:53 -0800684 hs := &clientHandshakeState{
685 c: c,
686 serverHello: serverHello,
687 hello: hello,
688 suite: suite,
Robert Sloanb1b54b82017-11-06 13:50:02 -0800689 finishedHash: newFinishedHash(c.wireVersion, c.isDTLS, suite),
David Benjaminc895d6b2016-08-11 13:26:41 -0400690 keyShares: keyShares,
Adam Langleyd9e397b2015-01-22 14:27:53 -0800691 session: session,
692 }
693
694 hs.writeHash(helloBytes, hs.c.sendHandshakeSeq-1)
David Benjaminc895d6b2016-08-11 13:26:41 -0400695 if haveHelloRetryRequest {
Robert Sloan8542c082018-02-05 09:07:34 -0800696 err = hs.finishedHash.UpdateForHelloRetryRequest()
697 if err != nil {
698 return err
Robert Sloanb1b54b82017-11-06 13:50:02 -0800699 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400700 hs.writeServerHash(helloRetryRequest.marshal())
701 hs.writeClientHash(secondHelloBytes)
702 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800703 hs.writeServerHash(hs.serverHello.marshal())
704
David Benjaminc895d6b2016-08-11 13:26:41 -0400705 if c.vers >= VersionTLS13 {
706 if err := hs.doTLS13Handshake(); err != nil {
Adam Langleyd9e397b2015-01-22 14:27:53 -0800707 return err
708 }
709 } else {
David Benjaminc895d6b2016-08-11 13:26:41 -0400710 if c.config.Bugs.EarlyChangeCipherSpec > 0 {
711 hs.establishKeys()
712 c.writeRecord(recordTypeChangeCipherSpec, []byte{1})
713 }
714
715 if hs.serverHello.compressionMethod != compressionNone {
716 c.sendAlert(alertUnexpectedMessage)
717 return errors.New("tls: server selected unsupported compression format")
718 }
719
720 err = hs.processServerExtensions(&serverHello.extensions)
721 if err != nil {
Adam Langleyd9e397b2015-01-22 14:27:53 -0800722 return err
723 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400724
725 isResume, err := hs.processServerHello()
726 if err != nil {
Adam Langleyd9e397b2015-01-22 14:27:53 -0800727 return err
728 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400729
730 if isResume {
731 if c.config.Bugs.EarlyChangeCipherSpec == 0 {
732 if err := hs.establishKeys(); err != nil {
733 return err
734 }
735 }
736 if err := hs.readSessionTicket(); err != nil {
737 return err
738 }
739 if err := hs.readFinished(c.firstFinished[:]); err != nil {
740 return err
741 }
742 if err := hs.sendFinished(nil, isResume); err != nil {
743 return err
744 }
745 } else {
746 if err := hs.doFullHandshake(); err != nil {
747 return err
748 }
749 if err := hs.establishKeys(); err != nil {
750 return err
751 }
752 if err := hs.sendFinished(c.firstFinished[:], isResume); err != nil {
753 return err
754 }
755 // Most retransmits are triggered by a timeout, but the final
756 // leg of the handshake is retransmited upon re-receiving a
757 // Finished.
758 if err := c.simulatePacketLoss(func() {
759 c.sendHandshakeSeq--
760 c.writeRecord(recordTypeHandshake, hs.finishedBytes)
761 c.flushHandshake()
762 }); err != nil {
763 return err
764 }
765 if err := hs.readSessionTicket(); err != nil {
766 return err
767 }
768 if err := hs.readFinished(nil); err != nil {
769 return err
770 }
Adam Langleyd9e397b2015-01-22 14:27:53 -0800771 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400772
773 if sessionCache != nil && hs.session != nil && session != hs.session {
774 if c.config.Bugs.RequireSessionTickets && len(hs.session.sessionTicket) == 0 {
775 return errors.New("tls: new session used session IDs instead of tickets")
776 }
Adam Vartanianbfcf3a72018-08-10 14:55:24 +0100777 if c.config.Bugs.RequireSessionIDs && len(hs.session.sessionId) == 0 {
778 return errors.New("tls: new session used session tickets instead of IDs")
779 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400780 sessionCache.Put(cacheKey, hs.session)
Adam Langleye9ada862015-05-11 17:20:37 -0700781 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400782
783 c.didResume = isResume
784 c.exporterSecret = hs.masterSecret
Adam Langleyd9e397b2015-01-22 14:27:53 -0800785 }
786
Adam Langleyd9e397b2015-01-22 14:27:53 -0800787 c.handshakeComplete = true
Adam Langleye9ada862015-05-11 17:20:37 -0700788 c.cipherSuite = suite
789 copy(c.clientRandom[:], hs.hello.random)
790 copy(c.serverRandom[:], hs.serverHello.random)
Kenny Rootb8494592015-09-25 02:29:14 +0000791
Adam Langleyd9e397b2015-01-22 14:27:53 -0800792 return nil
793}
794
David Benjaminc895d6b2016-08-11 13:26:41 -0400795func (hs *clientHandshakeState) doTLS13Handshake() error {
796 c := hs.c
797
Robert Sloan0da43952018-01-03 15:13:14 -0800798 if !bytes.Equal(hs.hello.sessionId, hs.serverHello.sessionId) {
Robert Sloanb6d070c2017-07-24 08:40:01 -0700799 return errors.New("tls: session IDs did not match.")
800 }
801
David Benjaminc895d6b2016-08-11 13:26:41 -0400802 // Once the PRF hash is known, TLS 1.3 does not require a handshake
803 // buffer.
804 hs.finishedHash.discardHandshakeBuffer()
805
806 zeroSecret := hs.finishedHash.zeroSecret()
807
808 // Resolve PSK and compute the early secret.
809 //
810 // TODO(davidben): This will need to be handled slightly earlier once
811 // 0-RTT is implemented.
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400812 if hs.serverHello.hasPSKIdentity {
David Benjaminc895d6b2016-08-11 13:26:41 -0400813 // We send at most one PSK identity.
814 if hs.session == nil || hs.serverHello.pskIdentity != 0 {
815 c.sendAlert(alertUnknownPSKIdentity)
816 return errors.New("tls: server sent unknown PSK identity")
817 }
Steven Valdez909b19f2016-11-21 15:35:44 -0500818 sessionCipher := cipherSuiteFromID(hs.session.cipherSuite)
819 if sessionCipher == nil || sessionCipher.hash() != hs.suite.hash() {
David Benjaminc895d6b2016-08-11 13:26:41 -0400820 c.sendAlert(alertHandshakeFailure)
Steven Valdez909b19f2016-11-21 15:35:44 -0500821 return errors.New("tls: server resumed an invalid session for the cipher suite")
David Benjaminc895d6b2016-08-11 13:26:41 -0400822 }
David Benjamin1b249672016-12-06 18:25:50 -0500823 hs.finishedHash.addEntropy(hs.session.masterSecret)
David Benjaminc895d6b2016-08-11 13:26:41 -0400824 c.didResume = true
825 } else {
David Benjamin1b249672016-12-06 18:25:50 -0500826 hs.finishedHash.addEntropy(zeroSecret)
David Benjaminc895d6b2016-08-11 13:26:41 -0400827 }
828
Steven Valdez909b19f2016-11-21 15:35:44 -0500829 if !hs.serverHello.hasKeyShare {
830 c.sendAlert(alertUnsupportedExtension)
831 return errors.New("tls: server omitted KeyShare on resumption.")
832 }
833
David Benjaminc895d6b2016-08-11 13:26:41 -0400834 // Resolve ECDHE and compute the handshake secret.
Steven Valdezbb1ceac2016-10-07 10:34:51 -0400835 if !c.config.Bugs.MissingKeyShare && !c.config.Bugs.SecondClientHelloMissingKeyShare {
David Benjaminc895d6b2016-08-11 13:26:41 -0400836 curve, ok := hs.keyShares[hs.serverHello.keyShare.group]
837 if !ok {
838 c.sendAlert(alertHandshakeFailure)
839 return errors.New("tls: server selected an unsupported group")
840 }
841 c.curveID = hs.serverHello.keyShare.group
842
David Benjamin1b249672016-12-06 18:25:50 -0500843 ecdheSecret, err := curve.finish(hs.serverHello.keyShare.keyExchange)
David Benjaminc895d6b2016-08-11 13:26:41 -0400844 if err != nil {
845 return err
846 }
Robert Sloanb1b54b82017-11-06 13:50:02 -0800847 hs.finishedHash.nextSecret()
David Benjamin1b249672016-12-06 18:25:50 -0500848 hs.finishedHash.addEntropy(ecdheSecret)
David Benjaminc895d6b2016-08-11 13:26:41 -0400849 } else {
Robert Sloanb1b54b82017-11-06 13:50:02 -0800850 hs.finishedHash.nextSecret()
David Benjamin1b249672016-12-06 18:25:50 -0500851 hs.finishedHash.addEntropy(zeroSecret)
David Benjaminc895d6b2016-08-11 13:26:41 -0400852 }
853
Robert Sloan47f43ed2017-02-06 14:55:15 -0800854 // Derive handshake traffic keys and switch read key to handshake
855 // traffic key.
Robert Sloan8542c082018-02-05 09:07:34 -0800856 clientHandshakeTrafficSecret := hs.finishedHash.deriveSecret(clientHandshakeTrafficLabel)
857 serverHandshakeTrafficSecret := hs.finishedHash.deriveSecret(serverHandshakeTrafficLabel)
Robert Sloan29c1d2c2017-10-30 14:10:28 -0700858 if err := c.useInTrafficSecret(c.wireVersion, hs.suite, serverHandshakeTrafficSecret); err != nil {
859 return err
860 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400861
862 msg, err := c.readHandshake()
863 if err != nil {
864 return err
865 }
866
867 encryptedExtensions, ok := msg.(*encryptedExtensionsMsg)
868 if !ok {
869 c.sendAlert(alertUnexpectedMessage)
870 return unexpectedMessageError(encryptedExtensions, msg)
871 }
872 hs.writeServerHash(encryptedExtensions.marshal())
873
874 err = hs.processServerExtensions(&encryptedExtensions.extensions)
875 if err != nil {
876 return err
877 }
878
879 var chainToSend *Certificate
880 var certReq *certificateRequestMsg
Steven Valdez909b19f2016-11-21 15:35:44 -0500881 if c.didResume {
David Benjaminc895d6b2016-08-11 13:26:41 -0400882 // Copy over authentication from the session.
883 c.peerCertificates = hs.session.serverCertificates
884 c.sctList = hs.session.sctList
885 c.ocspResponse = hs.session.ocspResponse
886 } else {
David Benjaminc895d6b2016-08-11 13:26:41 -0400887 msg, err := c.readHandshake()
888 if err != nil {
889 return err
890 }
891
892 var ok bool
893 certReq, ok = msg.(*certificateRequestMsg)
894 if ok {
David Benjaminf0c4a6c2016-08-11 13:26:41 -0400895 if len(certReq.requestContext) != 0 {
896 return errors.New("tls: non-empty certificate request context sent in handshake")
897 }
898
Robert Sloanb1b54b82017-11-06 13:50:02 -0800899 if c.config.Bugs.ExpectNoCertificateAuthoritiesExtension && certReq.hasCAExtension {
900 return errors.New("tls: expected no certificate_authorities extension")
901 }
902
Robert Sloan5cbb5c82018-04-24 11:35:46 -0700903 if err := checkRSAPSSSupport(c.config.Bugs.ExpectRSAPSSSupport, certReq.signatureAlgorithms, certReq.signatureAlgorithmsCert); err != nil {
904 return err
905 }
906
David Benjaminc895d6b2016-08-11 13:26:41 -0400907 if c.config.Bugs.IgnorePeerSignatureAlgorithmPreferences {
908 certReq.signatureAlgorithms = c.config.signSignatureAlgorithms()
909 }
910
911 hs.writeServerHash(certReq.marshal())
912
913 chainToSend, err = selectClientCertificate(c, certReq)
914 if err != nil {
915 return err
916 }
917
918 msg, err = c.readHandshake()
919 if err != nil {
920 return err
921 }
922 }
923
Adam Vartanianbfcf3a72018-08-10 14:55:24 +0100924 var certMsg *certificateMsg
925
926 if compressedCertMsg, ok := msg.(*compressedCertificateMsg); ok {
927 hs.writeServerHash(compressedCertMsg.marshal())
928
929 alg, ok := c.config.CertCompressionAlgs[compressedCertMsg.algID]
930 if !ok {
931 c.sendAlert(alertBadCertificate)
932 return fmt.Errorf("tls: received certificate compressed with unknown algorithm %x", compressedCertMsg.algID)
933 }
934
935 decompressed := make([]byte, 4+int(compressedCertMsg.uncompressedLength))
936 if !alg.Decompress(decompressed[4:], compressedCertMsg.compressed) {
937 c.sendAlert(alertBadCertificate)
938 return fmt.Errorf("tls: failed to decompress certificate with algorithm %x", compressedCertMsg.algID)
939 }
940
941 certMsg = &certificateMsg{
942 hasRequestContext: true,
943 }
944
945 if !certMsg.unmarshal(decompressed) {
946 c.sendAlert(alertBadCertificate)
947 return errors.New("tls: failed to parse decompressed certificate")
948 }
949
950 if expected := c.config.Bugs.ExpectedCompressedCert; expected != 0 && expected != compressedCertMsg.algID {
951 return fmt.Errorf("tls: expected certificate compressed with algorithm %x, but message used %x", expected, compressedCertMsg.algID)
952 }
953 } else {
954 if certMsg, ok = msg.(*certificateMsg); !ok {
955 c.sendAlert(alertUnexpectedMessage)
956 return unexpectedMessageError(certMsg, msg)
957 }
958 hs.writeServerHash(certMsg.marshal())
959
960 if c.config.Bugs.ExpectedCompressedCert != 0 {
961 return errors.New("tls: uncompressed certificate received")
962 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400963 }
David Benjaminc895d6b2016-08-11 13:26:41 -0400964
Steven Valdez909b19f2016-11-21 15:35:44 -0500965 // Check for unsolicited extensions.
966 for i, cert := range certMsg.certificates {
967 if c.config.Bugs.NoOCSPStapling && cert.ocspResponse != nil {
968 c.sendAlert(alertUnsupportedExtension)
969 return errors.New("tls: unexpected OCSP response in the server certificate")
970 }
971 if c.config.Bugs.NoSignedCertificateTimestamps && cert.sctList != nil {
972 c.sendAlert(alertUnsupportedExtension)
973 return errors.New("tls: unexpected SCT list in the server certificate")
974 }
975 if i > 0 && c.config.Bugs.ExpectNoExtensionsOnIntermediate && (cert.ocspResponse != nil || cert.sctList != nil) {
976 c.sendAlert(alertUnsupportedExtension)
977 return errors.New("tls: unexpected extensions in the server certificate")
978 }
979 }
980
David Benjaminc895d6b2016-08-11 13:26:41 -0400981 if err := hs.verifyCertificates(certMsg); err != nil {
982 return err
983 }
Steven Valdez909b19f2016-11-21 15:35:44 -0500984 c.ocspResponse = certMsg.certificates[0].ocspResponse
985 c.sctList = certMsg.certificates[0].sctList
David Benjaminc895d6b2016-08-11 13:26:41 -0400986
987 msg, err = c.readHandshake()
988 if err != nil {
989 return err
990 }
991 certVerifyMsg, ok := msg.(*certificateVerifyMsg)
992 if !ok {
993 c.sendAlert(alertUnexpectedMessage)
994 return unexpectedMessageError(certVerifyMsg, msg)
995 }
996
997 c.peerSignatureAlgorithm = certVerifyMsg.signatureAlgorithm
998 input := hs.finishedHash.certificateVerifyInput(serverCertificateVerifyContextTLS13)
Robert Sloan4c22c5f2019-03-01 15:53:37 -0800999 err = verifyMessage(c.vers, hs.peerPublicKey, c.config, certVerifyMsg.signatureAlgorithm, input, certVerifyMsg.signature)
David Benjaminc895d6b2016-08-11 13:26:41 -04001000 if err != nil {
1001 return err
1002 }
1003
1004 hs.writeServerHash(certVerifyMsg.marshal())
1005 }
1006
1007 msg, err = c.readHandshake()
1008 if err != nil {
1009 return err
1010 }
1011 serverFinished, ok := msg.(*finishedMsg)
1012 if !ok {
1013 c.sendAlert(alertUnexpectedMessage)
1014 return unexpectedMessageError(serverFinished, msg)
1015 }
1016
David Benjamin95add822016-10-19 01:09:12 -04001017 verify := hs.finishedHash.serverSum(serverHandshakeTrafficSecret)
David Benjaminc895d6b2016-08-11 13:26:41 -04001018 if len(verify) != len(serverFinished.verifyData) ||
1019 subtle.ConstantTimeCompare(verify, serverFinished.verifyData) != 1 {
1020 c.sendAlert(alertHandshakeFailure)
1021 return errors.New("tls: server's Finished message was incorrect")
1022 }
1023
1024 hs.writeServerHash(serverFinished.marshal())
1025
1026 // The various secrets do not incorporate the client's final leg, so
1027 // derive them now before updating the handshake context.
Robert Sloanb1b54b82017-11-06 13:50:02 -08001028 hs.finishedHash.nextSecret()
David Benjamin1b249672016-12-06 18:25:50 -05001029 hs.finishedHash.addEntropy(zeroSecret)
Robert Sloanb1b54b82017-11-06 13:50:02 -08001030
Robert Sloan8542c082018-02-05 09:07:34 -08001031 clientTrafficSecret := hs.finishedHash.deriveSecret(clientApplicationTrafficLabel)
1032 serverTrafficSecret := hs.finishedHash.deriveSecret(serverApplicationTrafficLabel)
1033 c.exporterSecret = hs.finishedHash.deriveSecret(exporterLabel)
Robert Sloan5d625782017-02-13 09:55:39 -08001034
1035 // Switch to application data keys on read. In particular, any alerts
1036 // from the client certificate are read over these keys.
Robert Sloan29c1d2c2017-10-30 14:10:28 -07001037 if err := c.useInTrafficSecret(c.wireVersion, hs.suite, serverTrafficSecret); err != nil {
1038 return err
1039 }
Robert Sloan4d1ac502017-02-06 08:36:14 -08001040
Robert Sloanb1b54b82017-11-06 13:50:02 -08001041 // If we're expecting 0.5-RTT messages from the server, read them now.
1042 var deferredTickets []*newSessionTicketMsg
Robert Sloan6d0d00e2017-03-27 07:13:07 -07001043 if encryptedExtensions.extensions.hasEarlyData {
1044 // BoringSSL will always send two tickets half-RTT when
1045 // negotiating 0-RTT.
1046 for i := 0; i < shimConfig.HalfRTTTickets; i++ {
1047 msg, err := c.readHandshake()
1048 if err != nil {
1049 return fmt.Errorf("tls: error reading half-RTT ticket: %s", err)
1050 }
1051 newSessionTicket, ok := msg.(*newSessionTicketMsg)
1052 if !ok {
1053 return errors.New("tls: expected half-RTT ticket")
1054 }
Robert Sloanb1b54b82017-11-06 13:50:02 -08001055 // Defer processing until the resumption secret is computed.
1056 deferredTickets = append(deferredTickets, newSessionTicket)
Robert Sloan4d1ac502017-02-06 08:36:14 -08001057 }
Robert Sloan6d0d00e2017-03-27 07:13:07 -07001058 for _, expectedMsg := range c.config.Bugs.ExpectHalfRTTData {
1059 if err := c.readRecord(recordTypeApplicationData); err != nil {
1060 return err
1061 }
1062 if !bytes.Equal(c.input.data[c.input.off:], expectedMsg) {
1063 return errors.New("ExpectHalfRTTData: did not get expected message")
1064 }
1065 c.in.freeBlock(c.input)
1066 c.input = nil
Robert Sloan4d1ac502017-02-06 08:36:14 -08001067 }
Robert Sloan4d1ac502017-02-06 08:36:14 -08001068 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001069
Robert Sloan47f43ed2017-02-06 14:55:15 -08001070 // Send EndOfEarlyData and then switch write key to handshake
1071 // traffic key.
Robert Sloanb1b54b82017-11-06 13:50:02 -08001072 if encryptedExtensions.extensions.hasEarlyData && c.out.cipher != nil && !c.config.Bugs.SkipEndOfEarlyData {
Robert Sloan6d0d00e2017-03-27 07:13:07 -07001073 if c.config.Bugs.SendStrayEarlyHandshake {
1074 helloRequest := new(helloRequestMsg)
1075 c.writeRecord(recordTypeHandshake, helloRequest.marshal())
1076 }
Robert Sloan8542c082018-02-05 09:07:34 -08001077 endOfEarlyData := new(endOfEarlyDataMsg)
1078 endOfEarlyData.nonEmpty = c.config.Bugs.NonEmptyEndOfEarlyData
1079 c.writeRecord(recordTypeHandshake, endOfEarlyData.marshal())
1080 hs.writeClientHash(endOfEarlyData.marshal())
Robert Sloan47f43ed2017-02-06 14:55:15 -08001081 }
Robert Sloana12bf462017-07-17 07:08:26 -07001082
Robert Sloan0da43952018-01-03 15:13:14 -08001083 if !c.config.Bugs.SkipChangeCipherSpec && !hs.hello.hasEarlyData {
Robert Sloand5c22152017-11-13 09:22:12 -08001084 c.writeRecord(recordTypeChangeCipherSpec, []byte{1})
1085 }
1086
1087 for i := 0; i < c.config.Bugs.SendExtraChangeCipherSpec; i++ {
Robert Sloana12bf462017-07-17 07:08:26 -07001088 c.writeRecord(recordTypeChangeCipherSpec, []byte{1})
1089 }
1090
Robert Sloan29c1d2c2017-10-30 14:10:28 -07001091 c.useOutTrafficSecret(c.wireVersion, hs.suite, clientHandshakeTrafficSecret)
Robert Sloan47f43ed2017-02-06 14:55:15 -08001092
David Benjaminc895d6b2016-08-11 13:26:41 -04001093 if certReq != nil && !c.config.Bugs.SkipClientCertificate {
1094 certMsg := &certificateMsg{
1095 hasRequestContext: true,
1096 requestContext: certReq.requestContext,
1097 }
1098 if chainToSend != nil {
Steven Valdez909b19f2016-11-21 15:35:44 -05001099 for _, certData := range chainToSend.Certificate {
1100 certMsg.certificates = append(certMsg.certificates, certificateEntry{
1101 data: certData,
1102 extraExtension: c.config.Bugs.SendExtensionOnCertificate,
1103 })
1104 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001105 }
1106 hs.writeClientHash(certMsg.marshal())
1107 c.writeRecord(recordTypeHandshake, certMsg.marshal())
1108
1109 if chainToSend != nil {
1110 certVerify := &certificateVerifyMsg{
1111 hasSignatureAlgorithm: true,
1112 }
1113
1114 // Determine the hash to sign.
1115 privKey := chainToSend.PrivateKey
1116
1117 var err error
1118 certVerify.signatureAlgorithm, err = selectSignatureAlgorithm(c.vers, privKey, c.config, certReq.signatureAlgorithms)
1119 if err != nil {
1120 c.sendAlert(alertInternalError)
1121 return err
1122 }
1123
1124 input := hs.finishedHash.certificateVerifyInput(clientCertificateVerifyContextTLS13)
1125 certVerify.signature, err = signMessage(c.vers, privKey, c.config, certVerify.signatureAlgorithm, input)
1126 if err != nil {
1127 c.sendAlert(alertInternalError)
1128 return err
1129 }
1130 if c.config.Bugs.SendSignatureAlgorithm != 0 {
1131 certVerify.signatureAlgorithm = c.config.Bugs.SendSignatureAlgorithm
1132 }
1133
Robert Sloan84377092017-08-14 09:33:19 -07001134 if !c.config.Bugs.SkipCertificateVerify {
1135 hs.writeClientHash(certVerify.marshal())
1136 c.writeRecord(recordTypeHandshake, certVerify.marshal())
1137 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001138 }
1139 }
1140
Steven Valdez909b19f2016-11-21 15:35:44 -05001141 if encryptedExtensions.extensions.channelIDRequested {
1142 channelIDHash := crypto.SHA256.New()
1143 channelIDHash.Write(hs.finishedHash.certificateVerifyInput(channelIDContextTLS13))
1144 channelIDMsgBytes, err := hs.writeChannelIDMessage(channelIDHash.Sum(nil))
1145 if err != nil {
1146 return err
1147 }
1148 hs.writeClientHash(channelIDMsgBytes)
1149 c.writeRecord(recordTypeHandshake, channelIDMsgBytes)
1150 }
1151
David Benjaminc895d6b2016-08-11 13:26:41 -04001152 // Send a client Finished message.
1153 finished := new(finishedMsg)
David Benjamin95add822016-10-19 01:09:12 -04001154 finished.verifyData = hs.finishedHash.clientSum(clientHandshakeTrafficSecret)
David Benjaminc895d6b2016-08-11 13:26:41 -04001155 if c.config.Bugs.BadFinished {
1156 finished.verifyData[0]++
1157 }
1158 hs.writeClientHash(finished.marshal())
1159 if c.config.Bugs.PartialClientFinishedWithClientHello {
1160 // The first byte has already been sent.
1161 c.writeRecord(recordTypeHandshake, finished.marshal()[1:])
David Benjamin1b249672016-12-06 18:25:50 -05001162 } else if c.config.Bugs.InterleaveEarlyData {
1163 finishedBytes := finished.marshal()
1164 c.sendFakeEarlyData(4)
1165 c.writeRecord(recordTypeHandshake, finishedBytes[:1])
1166 c.sendFakeEarlyData(4)
1167 c.writeRecord(recordTypeHandshake, finishedBytes[1:])
David Benjaminc895d6b2016-08-11 13:26:41 -04001168 } else {
1169 c.writeRecord(recordTypeHandshake, finished.marshal())
1170 }
1171 if c.config.Bugs.SendExtraFinished {
1172 c.writeRecord(recordTypeHandshake, finished.marshal())
1173 }
1174 c.flushHandshake()
1175
1176 // Switch to application data keys.
Robert Sloan29c1d2c2017-10-30 14:10:28 -07001177 c.useOutTrafficSecret(c.wireVersion, hs.suite, clientTrafficSecret)
Robert Sloan8542c082018-02-05 09:07:34 -08001178 c.resumptionSecret = hs.finishedHash.deriveSecret(resumptionLabel)
Robert Sloanb1b54b82017-11-06 13:50:02 -08001179 for _, ticket := range deferredTickets {
1180 if err := c.processTLS13NewSessionTicket(ticket, hs.suite); err != nil {
1181 return err
1182 }
1183 }
1184
David Benjaminc895d6b2016-08-11 13:26:41 -04001185 return nil
1186}
1187
Adam Langleyd9e397b2015-01-22 14:27:53 -08001188func (hs *clientHandshakeState) doFullHandshake() error {
1189 c := hs.c
1190
1191 var leaf *x509.Certificate
1192 if hs.suite.flags&suitePSK == 0 {
1193 msg, err := c.readHandshake()
1194 if err != nil {
1195 return err
1196 }
1197
1198 certMsg, ok := msg.(*certificateMsg)
David Benjaminc895d6b2016-08-11 13:26:41 -04001199 if !ok {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001200 c.sendAlert(alertUnexpectedMessage)
1201 return unexpectedMessageError(certMsg, msg)
1202 }
1203 hs.writeServerHash(certMsg.marshal())
1204
David Benjaminc895d6b2016-08-11 13:26:41 -04001205 if err := hs.verifyCertificates(certMsg); err != nil {
1206 return err
Adam Langleyd9e397b2015-01-22 14:27:53 -08001207 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001208 leaf = c.peerCertificates[0]
Adam Langleyd9e397b2015-01-22 14:27:53 -08001209 }
1210
David Benjaminc895d6b2016-08-11 13:26:41 -04001211 if hs.serverHello.extensions.ocspStapling {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001212 msg, err := c.readHandshake()
1213 if err != nil {
1214 return err
1215 }
1216 cs, ok := msg.(*certificateStatusMsg)
1217 if !ok {
1218 c.sendAlert(alertUnexpectedMessage)
1219 return unexpectedMessageError(cs, msg)
1220 }
1221 hs.writeServerHash(cs.marshal())
1222
1223 if cs.statusType == statusTypeOCSP {
1224 c.ocspResponse = cs.response
1225 }
1226 }
1227
1228 msg, err := c.readHandshake()
1229 if err != nil {
1230 return err
1231 }
1232
1233 keyAgreement := hs.suite.ka(c.vers)
1234
1235 skx, ok := msg.(*serverKeyExchangeMsg)
1236 if ok {
1237 hs.writeServerHash(skx.marshal())
Robert Sloan4c22c5f2019-03-01 15:53:37 -08001238 err = keyAgreement.processServerKeyExchange(c.config, hs.hello, hs.serverHello, hs.peerPublicKey, skx)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001239 if err != nil {
1240 c.sendAlert(alertUnexpectedMessage)
1241 return err
1242 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001243 if ecdhe, ok := keyAgreement.(*ecdheKeyAgreement); ok {
1244 c.curveID = ecdhe.curveID
1245 }
1246
1247 c.peerSignatureAlgorithm = keyAgreement.peerSignatureAlgorithm()
Adam Langleyd9e397b2015-01-22 14:27:53 -08001248
1249 msg, err = c.readHandshake()
1250 if err != nil {
1251 return err
1252 }
1253 }
1254
1255 var chainToSend *Certificate
1256 var certRequested bool
1257 certReq, ok := msg.(*certificateRequestMsg)
1258 if ok {
1259 certRequested = true
Robert Sloan5cbb5c82018-04-24 11:35:46 -07001260 if err := checkRSAPSSSupport(c.config.Bugs.ExpectRSAPSSSupport, certReq.signatureAlgorithms, certReq.signatureAlgorithmsCert); err != nil {
1261 return err
1262 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001263 if c.config.Bugs.IgnorePeerSignatureAlgorithmPreferences {
1264 certReq.signatureAlgorithms = c.config.signSignatureAlgorithms()
1265 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001266
1267 hs.writeServerHash(certReq.marshal())
1268
David Benjaminc895d6b2016-08-11 13:26:41 -04001269 chainToSend, err = selectClientCertificate(c, certReq)
1270 if err != nil {
1271 return err
Adam Langleyd9e397b2015-01-22 14:27:53 -08001272 }
1273
1274 msg, err = c.readHandshake()
1275 if err != nil {
1276 return err
1277 }
1278 }
1279
1280 shd, ok := msg.(*serverHelloDoneMsg)
1281 if !ok {
1282 c.sendAlert(alertUnexpectedMessage)
1283 return unexpectedMessageError(shd, msg)
1284 }
1285 hs.writeServerHash(shd.marshal())
1286
1287 // If the server requested a certificate then we have to send a
David Benjamin4969cc92016-04-22 15:02:23 -04001288 // Certificate message in TLS, even if it's empty because we don't have
1289 // a certificate to send. In SSL 3.0, skip the message and send a
1290 // no_certificate warning alert.
Adam Langleyd9e397b2015-01-22 14:27:53 -08001291 if certRequested {
David Benjamin4969cc92016-04-22 15:02:23 -04001292 if c.vers == VersionSSL30 && chainToSend == nil {
Robert Sloan69939df2017-01-09 10:53:07 -08001293 c.sendAlert(alertNoCertificate)
David Benjamin4969cc92016-04-22 15:02:23 -04001294 } else if !c.config.Bugs.SkipClientCertificate {
1295 certMsg := new(certificateMsg)
1296 if chainToSend != nil {
Steven Valdez909b19f2016-11-21 15:35:44 -05001297 for _, certData := range chainToSend.Certificate {
1298 certMsg.certificates = append(certMsg.certificates, certificateEntry{
1299 data: certData,
1300 })
1301 }
David Benjamin4969cc92016-04-22 15:02:23 -04001302 }
1303 hs.writeClientHash(certMsg.marshal())
1304 c.writeRecord(recordTypeHandshake, certMsg.marshal())
Adam Langleyd9e397b2015-01-22 14:27:53 -08001305 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001306 }
1307
1308 preMasterSecret, ckx, err := keyAgreement.generateClientKeyExchange(c.config, hs.hello, leaf)
1309 if err != nil {
1310 c.sendAlert(alertInternalError)
1311 return err
1312 }
1313 if ckx != nil {
1314 if c.config.Bugs.EarlyChangeCipherSpec < 2 {
1315 hs.writeClientHash(ckx.marshal())
1316 }
1317 c.writeRecord(recordTypeHandshake, ckx.marshal())
1318 }
1319
David Benjaminc895d6b2016-08-11 13:26:41 -04001320 if hs.serverHello.extensions.extendedMasterSecret && c.vers >= VersionTLS10 {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001321 hs.masterSecret = extendedMasterFromPreMasterSecret(c.vers, hs.suite, preMasterSecret, hs.finishedHash)
1322 c.extendedMasterSecret = true
1323 } else {
1324 if c.config.Bugs.RequireExtendedMasterSecret {
1325 return errors.New("tls: extended master secret required but not supported by peer")
1326 }
1327 hs.masterSecret = masterFromPreMasterSecret(c.vers, hs.suite, preMasterSecret, hs.hello.random, hs.serverHello.random)
1328 }
1329
1330 if chainToSend != nil {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001331 certVerify := &certificateVerifyMsg{
David Benjaminc895d6b2016-08-11 13:26:41 -04001332 hasSignatureAlgorithm: c.vers >= VersionTLS12,
Adam Langleyd9e397b2015-01-22 14:27:53 -08001333 }
1334
Adam Langleye9ada862015-05-11 17:20:37 -07001335 // Determine the hash to sign.
David Benjaminc895d6b2016-08-11 13:26:41 -04001336 privKey := c.config.Certificates[0].PrivateKey
1337
1338 if certVerify.hasSignatureAlgorithm {
1339 certVerify.signatureAlgorithm, err = selectSignatureAlgorithm(c.vers, privKey, c.config, certReq.signatureAlgorithms)
1340 if err != nil {
1341 c.sendAlert(alertInternalError)
1342 return err
1343 }
Kenny Rootb8494592015-09-25 02:29:14 +00001344 }
Adam Langleye9ada862015-05-11 17:20:37 -07001345
David Benjaminc895d6b2016-08-11 13:26:41 -04001346 if c.vers > VersionSSL30 {
1347 certVerify.signature, err = signMessage(c.vers, privKey, c.config, certVerify.signatureAlgorithm, hs.finishedHash.buffer)
1348 if err == nil && c.config.Bugs.SendSignatureAlgorithm != 0 {
1349 certVerify.signatureAlgorithm = c.config.Bugs.SendSignatureAlgorithm
Adam Langleyd9e397b2015-01-22 14:27:53 -08001350 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001351 } else {
1352 // SSL 3.0's client certificate construction is
1353 // incompatible with signatureAlgorithm.
1354 rsaKey, ok := privKey.(*rsa.PrivateKey)
1355 if !ok {
1356 err = errors.New("unsupported signature type for client certificate")
1357 } else {
1358 digest := hs.finishedHash.hashForClientCertificateSSL3(hs.masterSecret)
1359 if c.config.Bugs.InvalidSignature {
1360 digest[0] ^= 0x80
1361 }
1362 certVerify.signature, err = rsa.SignPKCS1v15(c.config.rand(), rsaKey, crypto.MD5SHA1, digest)
1363 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001364 }
1365 if err != nil {
1366 c.sendAlert(alertInternalError)
1367 return errors.New("tls: failed to sign handshake with client certificate: " + err.Error())
1368 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001369
Robert Sloan84377092017-08-14 09:33:19 -07001370 if !c.config.Bugs.SkipCertificateVerify {
1371 hs.writeClientHash(certVerify.marshal())
1372 c.writeRecord(recordTypeHandshake, certVerify.marshal())
1373 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001374 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001375 // flushHandshake will be called in sendFinished.
Adam Langleyd9e397b2015-01-22 14:27:53 -08001376
1377 hs.finishedHash.discardHandshakeBuffer()
1378
1379 return nil
1380}
1381
Robert Sloan4c22c5f2019-03-01 15:53:37 -08001382// delegatedCredentialSignedMessage returns the bytes that are signed in order
1383// to authenticate a delegated credential.
1384func delegatedCredentialSignedMessage(credBytes []byte, algorithm signatureAlgorithm, leafDER []byte) []byte {
1385 // https://tools.ietf.org/html/draft-ietf-tls-subcerts-03#section-3
1386 ret := make([]byte, 64, 128)
1387 for i := range ret {
1388 ret[i] = 0x20
1389 }
1390
1391 ret = append(ret, []byte("TLS, server delegated credentials\x00")...)
1392 ret = append(ret, leafDER...)
1393 ret = append(ret, byte(algorithm>>8), byte(algorithm))
1394 ret = append(ret, credBytes...)
1395
1396 return ret
1397}
1398
David Benjaminc895d6b2016-08-11 13:26:41 -04001399func (hs *clientHandshakeState) verifyCertificates(certMsg *certificateMsg) error {
1400 c := hs.c
1401
1402 if len(certMsg.certificates) == 0 {
1403 c.sendAlert(alertIllegalParameter)
1404 return errors.New("tls: no certificates sent")
1405 }
1406
Robert Sloan4c22c5f2019-03-01 15:53:37 -08001407 var dc *delegatedCredential
David Benjaminc895d6b2016-08-11 13:26:41 -04001408 certs := make([]*x509.Certificate, len(certMsg.certificates))
Steven Valdez909b19f2016-11-21 15:35:44 -05001409 for i, certEntry := range certMsg.certificates {
1410 cert, err := x509.ParseCertificate(certEntry.data)
David Benjaminc895d6b2016-08-11 13:26:41 -04001411 if err != nil {
1412 c.sendAlert(alertBadCertificate)
1413 return errors.New("tls: failed to parse certificate from server: " + err.Error())
1414 }
1415 certs[i] = cert
Robert Sloan4c22c5f2019-03-01 15:53:37 -08001416
1417 if certEntry.delegatedCredential != nil {
1418 if c.config.Bugs.FailIfDelegatedCredentials {
1419 c.sendAlert(alertIllegalParameter)
1420 return errors.New("tls: unexpected delegated credential")
1421 }
1422 if i != 0 {
1423 c.sendAlert(alertIllegalParameter)
1424 return errors.New("tls: non-leaf certificate has a delegated credential")
1425 }
1426 if c.config.Bugs.DisableDelegatedCredentials {
1427 c.sendAlert(alertIllegalParameter)
1428 return errors.New("tls: server sent delegated credential without it being requested")
1429 }
1430 dc = certEntry.delegatedCredential
1431 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001432 }
1433
1434 if !c.config.InsecureSkipVerify {
1435 opts := x509.VerifyOptions{
1436 Roots: c.config.RootCAs,
1437 CurrentTime: c.config.time(),
1438 DNSName: c.config.ServerName,
1439 Intermediates: x509.NewCertPool(),
1440 }
1441
1442 for i, cert := range certs {
1443 if i == 0 {
1444 continue
1445 }
1446 opts.Intermediates.AddCert(cert)
1447 }
1448 var err error
1449 c.verifiedChains, err = certs[0].Verify(opts)
1450 if err != nil {
1451 c.sendAlert(alertBadCertificate)
1452 return err
1453 }
1454 }
1455
Robert Sloan4c22c5f2019-03-01 15:53:37 -08001456 leafPublicKey := getCertificatePublicKey(certs[0])
1457 switch leafPublicKey.(type) {
Robert Sloan572a4e22017-04-17 10:52:19 -07001458 case *rsa.PublicKey, *ecdsa.PublicKey, ed25519.PublicKey:
David Benjaminc895d6b2016-08-11 13:26:41 -04001459 break
1460 default:
1461 c.sendAlert(alertUnsupportedCertificate)
Robert Sloan4c22c5f2019-03-01 15:53:37 -08001462 return fmt.Errorf("tls: server's certificate contains an unsupported type of public key: %T", leafPublicKey)
David Benjaminc895d6b2016-08-11 13:26:41 -04001463 }
1464
1465 c.peerCertificates = certs
Robert Sloan4c22c5f2019-03-01 15:53:37 -08001466
1467 if dc != nil {
1468 // Note that this doesn't check a) the delegated credential temporal
1469 // validity nor b) that the certificate has the special OID asserted.
1470 hs.skxAlgo = dc.expectedCertVerifyAlgo
1471
1472 var err error
1473 if hs.peerPublicKey, err = x509.ParsePKIXPublicKey(dc.pkixPublicKey); err != nil {
1474 c.sendAlert(alertBadCertificate)
1475 return errors.New("tls: failed to parse public key from delegated credential: " + err.Error())
1476 }
1477
1478 verifier, err := getSigner(c.vers, hs.peerPublicKey, c.config, dc.algorithm, true)
1479 if err != nil {
1480 c.sendAlert(alertBadCertificate)
1481 return errors.New("tls: failed to get verifier for delegated credential: " + err.Error())
1482 }
1483
1484 if err := verifier.verifyMessage(leafPublicKey, delegatedCredentialSignedMessage(dc.signedBytes, dc.algorithm, certs[0].Raw), dc.signature); err != nil {
1485 c.sendAlert(alertBadCertificate)
1486 return errors.New("tls: failed to verify delegated credential: " + err.Error())
1487 }
1488 } else if c.config.Bugs.ExpectDelegatedCredentials {
1489 c.sendAlert(alertInternalError)
1490 return errors.New("tls: delegated credentials missing")
1491 } else {
1492 hs.peerPublicKey = leafPublicKey
1493 }
1494
David Benjaminc895d6b2016-08-11 13:26:41 -04001495 return nil
1496}
1497
Adam Langleyd9e397b2015-01-22 14:27:53 -08001498func (hs *clientHandshakeState) establishKeys() error {
1499 c := hs.c
1500
1501 clientMAC, serverMAC, clientKey, serverKey, clientIV, serverIV :=
David Benjaminc895d6b2016-08-11 13:26:41 -04001502 keysFromMasterSecret(c.vers, hs.suite, hs.masterSecret, hs.hello.random, hs.serverHello.random, hs.suite.macLen, hs.suite.keyLen, hs.suite.ivLen(c.vers))
Adam Langleyd9e397b2015-01-22 14:27:53 -08001503 var clientCipher, serverCipher interface{}
1504 var clientHash, serverHash macFunction
1505 if hs.suite.cipher != nil {
1506 clientCipher = hs.suite.cipher(clientKey, clientIV, false /* not for reading */)
1507 clientHash = hs.suite.mac(c.vers, clientMAC)
1508 serverCipher = hs.suite.cipher(serverKey, serverIV, true /* for reading */)
1509 serverHash = hs.suite.mac(c.vers, serverMAC)
1510 } else {
David Benjaminc895d6b2016-08-11 13:26:41 -04001511 clientCipher = hs.suite.aead(c.vers, clientKey, clientIV)
1512 serverCipher = hs.suite.aead(c.vers, serverKey, serverIV)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001513 }
1514
Robert Sloandb4251a2017-09-18 09:38:15 -07001515 c.in.prepareCipherSpec(c.wireVersion, serverCipher, serverHash)
1516 c.out.prepareCipherSpec(c.wireVersion, clientCipher, clientHash)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001517 return nil
1518}
1519
David Benjaminc895d6b2016-08-11 13:26:41 -04001520func (hs *clientHandshakeState) processServerExtensions(serverExtensions *serverExtensions) error {
1521 c := hs.c
1522
1523 if c.vers < VersionTLS13 {
1524 if c.config.Bugs.RequireRenegotiationInfo && serverExtensions.secureRenegotiation == nil {
1525 return errors.New("tls: renegotiation extension missing")
1526 }
1527
1528 if len(c.clientVerify) > 0 && !c.noRenegotiationInfo() {
1529 var expectedRenegInfo []byte
1530 expectedRenegInfo = append(expectedRenegInfo, c.clientVerify...)
1531 expectedRenegInfo = append(expectedRenegInfo, c.serverVerify...)
1532 if !bytes.Equal(serverExtensions.secureRenegotiation, expectedRenegInfo) {
1533 c.sendAlert(alertHandshakeFailure)
1534 return fmt.Errorf("tls: renegotiation mismatch")
1535 }
1536 }
1537 } else if serverExtensions.secureRenegotiation != nil {
1538 return errors.New("tls: renegotiation info sent in TLS 1.3")
1539 }
1540
1541 if expected := c.config.Bugs.ExpectedCustomExtension; expected != nil {
1542 if serverExtensions.customExtension != *expected {
1543 return fmt.Errorf("tls: bad custom extension contents %q", serverExtensions.customExtension)
1544 }
1545 }
1546
1547 clientDidNPN := hs.hello.nextProtoNeg
1548 clientDidALPN := len(hs.hello.alpnProtocols) > 0
1549 serverHasNPN := serverExtensions.nextProtoNeg
1550 serverHasALPN := len(serverExtensions.alpnProtocol) > 0
1551
1552 if !clientDidNPN && serverHasNPN {
1553 c.sendAlert(alertHandshakeFailure)
1554 return errors.New("server advertised unrequested NPN extension")
1555 }
1556
1557 if !clientDidALPN && serverHasALPN {
1558 c.sendAlert(alertHandshakeFailure)
1559 return errors.New("server advertised unrequested ALPN extension")
1560 }
1561
1562 if serverHasNPN && serverHasALPN {
1563 c.sendAlert(alertHandshakeFailure)
1564 return errors.New("server advertised both NPN and ALPN extensions")
1565 }
1566
1567 if serverHasALPN {
1568 c.clientProtocol = serverExtensions.alpnProtocol
1569 c.clientProtocolFallback = false
1570 c.usedALPN = true
1571 }
1572
1573 if serverHasNPN && c.vers >= VersionTLS13 {
1574 c.sendAlert(alertHandshakeFailure)
1575 return errors.New("server advertised NPN over TLS 1.3")
1576 }
1577
1578 if !hs.hello.channelIDSupported && serverExtensions.channelIDRequested {
1579 c.sendAlert(alertHandshakeFailure)
1580 return errors.New("server advertised unrequested Channel ID extension")
1581 }
1582
Robert Sloan978112c2018-01-22 12:53:01 -08001583 if len(serverExtensions.tokenBindingParams) == 1 {
1584 found := false
1585 for _, p := range c.config.TokenBindingParams {
1586 if p == serverExtensions.tokenBindingParams[0] {
1587 c.tokenBindingParam = p
1588 found = true
1589 break
1590 }
1591 }
1592 if !found {
1593 return errors.New("tls: server advertised unsupported Token Binding key param")
1594 }
1595 if serverExtensions.tokenBindingVersion > c.config.TokenBindingVersion {
1596 return errors.New("tls: server's Token Binding version is too new")
1597 }
1598 if c.vers < VersionTLS13 {
1599 if !serverExtensions.extendedMasterSecret || serverExtensions.secureRenegotiation == nil {
1600 return errors.New("server sent Token Binding without EMS or RI")
1601 }
1602 }
1603 c.tokenBindingNegotiated = true
1604 }
1605
David Benjaminc895d6b2016-08-11 13:26:41 -04001606 if serverExtensions.extendedMasterSecret && c.vers >= VersionTLS13 {
1607 return errors.New("tls: server advertised extended master secret over TLS 1.3")
1608 }
1609
1610 if serverExtensions.ticketSupported && c.vers >= VersionTLS13 {
1611 return errors.New("tls: server advertised ticket extension over TLS 1.3")
1612 }
1613
Steven Valdez909b19f2016-11-21 15:35:44 -05001614 if serverExtensions.ocspStapling && c.vers >= VersionTLS13 {
1615 return errors.New("tls: server advertised OCSP in ServerHello over TLS 1.3")
1616 }
1617
1618 if serverExtensions.ocspStapling && c.config.Bugs.NoOCSPStapling {
1619 return errors.New("tls: server advertised unrequested OCSP extension")
1620 }
1621
1622 if len(serverExtensions.sctList) > 0 && c.vers >= VersionTLS13 {
1623 return errors.New("tls: server advertised SCTs in ServerHello over TLS 1.3")
1624 }
1625
1626 if len(serverExtensions.sctList) > 0 && c.config.Bugs.NoSignedCertificateTimestamps {
1627 return errors.New("tls: server advertised unrequested SCTs")
1628 }
1629
David Benjaminc895d6b2016-08-11 13:26:41 -04001630 if serverExtensions.srtpProtectionProfile != 0 {
1631 if serverExtensions.srtpMasterKeyIdentifier != "" {
1632 return errors.New("tls: server selected SRTP MKI value")
1633 }
1634
1635 found := false
1636 for _, p := range c.config.SRTPProtectionProfiles {
1637 if p == serverExtensions.srtpProtectionProfile {
1638 found = true
1639 break
1640 }
1641 }
1642 if !found {
1643 return errors.New("tls: server advertised unsupported SRTP profile")
1644 }
1645
1646 c.srtpProtectionProfile = serverExtensions.srtpProtectionProfile
1647 }
1648
Robert Sloan6d0d00e2017-03-27 07:13:07 -07001649 if c.vers >= VersionTLS13 && c.didResume {
1650 if c.config.Bugs.ExpectEarlyDataAccepted && !serverExtensions.hasEarlyData {
1651 c.sendAlert(alertHandshakeFailure)
1652 return errors.New("tls: server did not accept early data when expected")
1653 }
1654
1655 if !c.config.Bugs.ExpectEarlyDataAccepted && serverExtensions.hasEarlyData {
1656 c.sendAlert(alertHandshakeFailure)
1657 return errors.New("tls: server accepted early data when not expected")
1658 }
1659 }
1660
Robert Sloan8542c082018-02-05 09:07:34 -08001661 if len(serverExtensions.quicTransportParams) > 0 {
1662 if c.vers < VersionTLS13 {
1663 c.sendAlert(alertHandshakeFailure)
1664 return errors.New("tls: server sent QUIC transport params for TLS version less than 1.3")
1665 }
1666 c.quicTransportParams = serverExtensions.quicTransportParams
1667 }
Robert Sloanab8b8882018-03-26 11:39:51 -07001668
David Benjaminc895d6b2016-08-11 13:26:41 -04001669 return nil
1670}
1671
Adam Langleyd9e397b2015-01-22 14:27:53 -08001672func (hs *clientHandshakeState) serverResumedSession() bool {
1673 // If the server responded with the same sessionId then it means the
1674 // sessionTicket is being used to resume a TLS session.
Robert Sloan5d625782017-02-13 09:55:39 -08001675 //
1676 // Note that, if hs.hello.sessionId is a non-nil empty array, this will
1677 // accept an empty session ID from the server as resumption. See
1678 // EmptyTicketSessionID.
Adam Langleyd9e397b2015-01-22 14:27:53 -08001679 return hs.session != nil && hs.hello.sessionId != nil &&
1680 bytes.Equal(hs.serverHello.sessionId, hs.hello.sessionId)
1681}
1682
1683func (hs *clientHandshakeState) processServerHello() (bool, error) {
1684 c := hs.c
1685
Adam Langleyd9e397b2015-01-22 14:27:53 -08001686 if hs.serverResumedSession() {
Adam Langleyf4e42722015-06-04 17:45:09 -07001687 // For test purposes, assert that the server never accepts the
1688 // resumption offer on renegotiation.
1689 if c.cipherSuite != nil && c.config.Bugs.FailIfResumeOnRenego {
1690 return false, errors.New("tls: server resumed session on renegotiation")
1691 }
1692
David Benjaminc895d6b2016-08-11 13:26:41 -04001693 if hs.serverHello.extensions.sctList != nil {
Kenny Rootb8494592015-09-25 02:29:14 +00001694 return false, errors.New("tls: server sent SCT extension on session resumption")
1695 }
1696
David Benjaminc895d6b2016-08-11 13:26:41 -04001697 if hs.serverHello.extensions.ocspStapling {
Kenny Rootb8494592015-09-25 02:29:14 +00001698 return false, errors.New("tls: server sent OCSP extension on session resumption")
1699 }
1700
Adam Langleyd9e397b2015-01-22 14:27:53 -08001701 // Restore masterSecret and peerCerts from previous state
1702 hs.masterSecret = hs.session.masterSecret
1703 c.peerCertificates = hs.session.serverCertificates
1704 c.extendedMasterSecret = hs.session.extendedMasterSecret
Kenny Rootb8494592015-09-25 02:29:14 +00001705 c.sctList = hs.session.sctList
1706 c.ocspResponse = hs.session.ocspResponse
Adam Langleyd9e397b2015-01-22 14:27:53 -08001707 hs.finishedHash.discardHandshakeBuffer()
1708 return true, nil
1709 }
Kenny Rootb8494592015-09-25 02:29:14 +00001710
David Benjaminc895d6b2016-08-11 13:26:41 -04001711 if hs.serverHello.extensions.sctList != nil {
1712 c.sctList = hs.serverHello.extensions.sctList
Kenny Rootb8494592015-09-25 02:29:14 +00001713 }
1714
Adam Langleyd9e397b2015-01-22 14:27:53 -08001715 return false, nil
1716}
1717
Adam Langleyf4e42722015-06-04 17:45:09 -07001718func (hs *clientHandshakeState) readFinished(out []byte) error {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001719 c := hs.c
1720
1721 c.readRecord(recordTypeChangeCipherSpec)
1722 if err := c.in.error(); err != nil {
1723 return err
1724 }
1725
1726 msg, err := c.readHandshake()
1727 if err != nil {
1728 return err
1729 }
1730 serverFinished, ok := msg.(*finishedMsg)
1731 if !ok {
1732 c.sendAlert(alertUnexpectedMessage)
1733 return unexpectedMessageError(serverFinished, msg)
1734 }
1735
1736 if c.config.Bugs.EarlyChangeCipherSpec == 0 {
1737 verify := hs.finishedHash.serverSum(hs.masterSecret)
1738 if len(verify) != len(serverFinished.verifyData) ||
1739 subtle.ConstantTimeCompare(verify, serverFinished.verifyData) != 1 {
1740 c.sendAlert(alertHandshakeFailure)
1741 return errors.New("tls: server's Finished message was incorrect")
1742 }
1743 }
1744 c.serverVerify = append(c.serverVerify[:0], serverFinished.verifyData...)
Adam Langleyf4e42722015-06-04 17:45:09 -07001745 copy(out, serverFinished.verifyData)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001746 hs.writeServerHash(serverFinished.marshal())
1747 return nil
1748}
1749
1750func (hs *clientHandshakeState) readSessionTicket() error {
1751 c := hs.c
1752
1753 // Create a session with no server identifier. Either a
1754 // session ID or session ticket will be attached.
1755 session := &ClientSessionState{
1756 vers: c.vers,
Robert Sloanb1b54b82017-11-06 13:50:02 -08001757 wireVersion: c.wireVersion,
Adam Langleyd9e397b2015-01-22 14:27:53 -08001758 cipherSuite: hs.suite.id,
1759 masterSecret: hs.masterSecret,
Steven Valdez909b19f2016-11-21 15:35:44 -05001760 handshakeHash: hs.finishedHash.Sum(),
Adam Langleyd9e397b2015-01-22 14:27:53 -08001761 serverCertificates: c.peerCertificates,
Kenny Rootb8494592015-09-25 02:29:14 +00001762 sctList: c.sctList,
1763 ocspResponse: c.ocspResponse,
David Benjaminc895d6b2016-08-11 13:26:41 -04001764 ticketExpiration: c.config.time().Add(time.Duration(7 * 24 * time.Hour)),
Adam Langleyd9e397b2015-01-22 14:27:53 -08001765 }
1766
David Benjaminc895d6b2016-08-11 13:26:41 -04001767 if !hs.serverHello.extensions.ticketSupported {
Kenny Rootb8494592015-09-25 02:29:14 +00001768 if c.config.Bugs.ExpectNewTicket {
1769 return errors.New("tls: expected new ticket")
1770 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001771 if hs.session == nil && len(hs.serverHello.sessionId) > 0 {
1772 session.sessionId = hs.serverHello.sessionId
1773 hs.session = session
1774 }
1775 return nil
1776 }
1777
Kenny Roote99801b2015-11-06 15:31:15 -08001778 if c.vers == VersionSSL30 {
1779 return errors.New("tls: negotiated session tickets in SSL 3.0")
1780 }
Adam Vartanianbfcf3a72018-08-10 14:55:24 +01001781 if c.config.Bugs.ExpectNoNewSessionTicket {
1782 return errors.New("tls: received unexpected NewSessionTicket")
1783 }
Kenny Roote99801b2015-11-06 15:31:15 -08001784
Adam Langleyd9e397b2015-01-22 14:27:53 -08001785 msg, err := c.readHandshake()
1786 if err != nil {
1787 return err
1788 }
1789 sessionTicketMsg, ok := msg.(*newSessionTicketMsg)
1790 if !ok {
1791 c.sendAlert(alertUnexpectedMessage)
1792 return unexpectedMessageError(sessionTicketMsg, msg)
1793 }
1794
1795 session.sessionTicket = sessionTicketMsg.ticket
1796 hs.session = session
1797
1798 hs.writeServerHash(sessionTicketMsg.marshal())
1799
1800 return nil
1801}
1802
Adam Langleyf4e42722015-06-04 17:45:09 -07001803func (hs *clientHandshakeState) sendFinished(out []byte, isResume bool) error {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001804 c := hs.c
1805
David Benjaminc895d6b2016-08-11 13:26:41 -04001806 var postCCSMsgs [][]byte
Adam Langleyd9e397b2015-01-22 14:27:53 -08001807 seqno := hs.c.sendHandshakeSeq
David Benjaminc895d6b2016-08-11 13:26:41 -04001808 if hs.serverHello.extensions.nextProtoNeg {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001809 nextProto := new(nextProtoMsg)
David Benjaminc895d6b2016-08-11 13:26:41 -04001810 proto, fallback := mutualProtocol(c.config.NextProtos, hs.serverHello.extensions.nextProtos)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001811 nextProto.proto = proto
1812 c.clientProtocol = proto
1813 c.clientProtocolFallback = fallback
1814
1815 nextProtoBytes := nextProto.marshal()
1816 hs.writeHash(nextProtoBytes, seqno)
1817 seqno++
David Benjaminc895d6b2016-08-11 13:26:41 -04001818 postCCSMsgs = append(postCCSMsgs, nextProtoBytes)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001819 }
1820
David Benjaminc895d6b2016-08-11 13:26:41 -04001821 if hs.serverHello.extensions.channelIDRequested {
Adam Langleyd9e397b2015-01-22 14:27:53 -08001822 var resumeHash []byte
1823 if isResume {
1824 resumeHash = hs.session.handshakeHash
1825 }
Steven Valdez909b19f2016-11-21 15:35:44 -05001826 channelIDMsgBytes, err := hs.writeChannelIDMessage(hs.finishedHash.hashForChannelID(resumeHash))
Adam Langleyd9e397b2015-01-22 14:27:53 -08001827 if err != nil {
1828 return err
1829 }
David Benjaminc895d6b2016-08-11 13:26:41 -04001830 hs.writeHash(channelIDMsgBytes, seqno)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001831 seqno++
David Benjaminc895d6b2016-08-11 13:26:41 -04001832 postCCSMsgs = append(postCCSMsgs, channelIDMsgBytes)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001833 }
1834
1835 finished := new(finishedMsg)
1836 if c.config.Bugs.EarlyChangeCipherSpec == 2 {
1837 finished.verifyData = hs.finishedHash.clientSum(nil)
1838 } else {
1839 finished.verifyData = hs.finishedHash.clientSum(hs.masterSecret)
1840 }
Adam Langleyf4e42722015-06-04 17:45:09 -07001841 copy(out, finished.verifyData)
Adam Langleye9ada862015-05-11 17:20:37 -07001842 if c.config.Bugs.BadFinished {
1843 finished.verifyData[0]++
1844 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001845 c.clientVerify = append(c.clientVerify[:0], finished.verifyData...)
Adam Langleye9ada862015-05-11 17:20:37 -07001846 hs.finishedBytes = finished.marshal()
1847 hs.writeHash(hs.finishedBytes, seqno)
David Benjaminc895d6b2016-08-11 13:26:41 -04001848 postCCSMsgs = append(postCCSMsgs, hs.finishedBytes)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001849
1850 if c.config.Bugs.FragmentAcrossChangeCipherSpec {
David Benjaminc895d6b2016-08-11 13:26:41 -04001851 c.writeRecord(recordTypeHandshake, postCCSMsgs[0][:5])
1852 postCCSMsgs[0] = postCCSMsgs[0][5:]
1853 } else if c.config.Bugs.SendUnencryptedFinished {
1854 c.writeRecord(recordTypeHandshake, postCCSMsgs[0])
1855 postCCSMsgs = postCCSMsgs[1:]
Adam Langleyd9e397b2015-01-22 14:27:53 -08001856 }
1857
1858 if !c.config.Bugs.SkipChangeCipherSpec &&
1859 c.config.Bugs.EarlyChangeCipherSpec == 0 {
Adam Langley4139edb2016-01-13 15:00:54 -08001860 ccs := []byte{1}
1861 if c.config.Bugs.BadChangeCipherSpec != nil {
1862 ccs = c.config.Bugs.BadChangeCipherSpec
1863 }
1864 c.writeRecord(recordTypeChangeCipherSpec, ccs)
Adam Langleyd9e397b2015-01-22 14:27:53 -08001865 }
1866
1867 if c.config.Bugs.AppDataAfterChangeCipherSpec != nil {
1868 c.writeRecord(recordTypeApplicationData, c.config.Bugs.AppDataAfterChangeCipherSpec)
1869 }
Adam Langleye9ada862015-05-11 17:20:37 -07001870 if c.config.Bugs.AlertAfterChangeCipherSpec != 0 {
1871 c.sendAlert(c.config.Bugs.AlertAfterChangeCipherSpec)
1872 return errors.New("tls: simulating post-CCS alert")
1873 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001874
Adam Langleye9ada862015-05-11 17:20:37 -07001875 if !c.config.Bugs.SkipFinished {
David Benjaminc895d6b2016-08-11 13:26:41 -04001876 for _, msg := range postCCSMsgs {
1877 c.writeRecord(recordTypeHandshake, msg)
1878 }
1879
1880 if c.config.Bugs.SendExtraFinished {
1881 c.writeRecord(recordTypeHandshake, finished.marshal())
1882 }
Adam Langleye9ada862015-05-11 17:20:37 -07001883 }
Robert Sloanfe7cd212017-08-07 09:03:39 -07001884
Robert Sloan921ef2c2017-10-17 09:02:20 -07001885 if !isResume || !c.config.Bugs.PackAppDataWithHandshake {
1886 c.flushHandshake()
1887 }
Adam Langleyd9e397b2015-01-22 14:27:53 -08001888 return nil
1889}
1890
Steven Valdez909b19f2016-11-21 15:35:44 -05001891func (hs *clientHandshakeState) writeChannelIDMessage(channelIDHash []byte) ([]byte, error) {
1892 c := hs.c
1893 channelIDMsg := new(channelIDMsg)
1894 if c.config.ChannelID.Curve != elliptic.P256() {
1895 return nil, fmt.Errorf("tls: Channel ID is not on P-256.")
1896 }
1897 r, s, err := ecdsa.Sign(c.config.rand(), c.config.ChannelID, channelIDHash)
1898 if err != nil {
1899 return nil, err
1900 }
1901 channelID := make([]byte, 128)
1902 writeIntPadded(channelID[0:32], c.config.ChannelID.X)
1903 writeIntPadded(channelID[32:64], c.config.ChannelID.Y)
1904 writeIntPadded(channelID[64:96], r)
1905 writeIntPadded(channelID[96:128], s)
1906 if c.config.Bugs.InvalidChannelIDSignature {
1907 channelID[64] ^= 1
1908 }
1909 channelIDMsg.channelID = channelID
1910
1911 c.channelID = &c.config.ChannelID.PublicKey
1912
1913 return channelIDMsg.marshal(), nil
1914}
1915
Adam Langleyd9e397b2015-01-22 14:27:53 -08001916func (hs *clientHandshakeState) writeClientHash(msg []byte) {
1917 // writeClientHash is called before writeRecord.
1918 hs.writeHash(msg, hs.c.sendHandshakeSeq)
1919}
1920
1921func (hs *clientHandshakeState) writeServerHash(msg []byte) {
1922 // writeServerHash is called after readHandshake.
1923 hs.writeHash(msg, hs.c.recvHandshakeSeq-1)
1924}
1925
1926func (hs *clientHandshakeState) writeHash(msg []byte, seqno uint16) {
1927 if hs.c.isDTLS {
1928 // This is somewhat hacky. DTLS hashes a slightly different format.
1929 // First, the TLS header.
1930 hs.finishedHash.Write(msg[:4])
1931 // Then the sequence number and reassembled fragment offset (always 0).
1932 hs.finishedHash.Write([]byte{byte(seqno >> 8), byte(seqno), 0, 0, 0})
1933 // Then the reassembled fragment (always equal to the message length).
1934 hs.finishedHash.Write(msg[1:4])
1935 // And then the message body.
1936 hs.finishedHash.Write(msg[4:])
1937 } else {
1938 hs.finishedHash.Write(msg)
1939 }
1940}
1941
David Benjaminc895d6b2016-08-11 13:26:41 -04001942// selectClientCertificate selects a certificate for use with the given
1943// certificate, or none if none match. It may return a particular certificate or
1944// nil on success, or an error on internal error.
1945func selectClientCertificate(c *Conn, certReq *certificateRequestMsg) (*Certificate, error) {
Robert Sloana27a6a42017-09-05 08:39:28 -07001946 if len(c.config.Certificates) == 0 {
1947 return nil, nil
David Benjaminc895d6b2016-08-11 13:26:41 -04001948 }
1949
Robert Sloana27a6a42017-09-05 08:39:28 -07001950 // The test is assumed to have configured the certificate it meant to
1951 // send.
1952 if len(c.config.Certificates) > 1 {
1953 return nil, errors.New("tls: multiple certificates configured")
David Benjaminc895d6b2016-08-11 13:26:41 -04001954 }
1955
Robert Sloana27a6a42017-09-05 08:39:28 -07001956 return &c.config.Certificates[0], nil
David Benjaminc895d6b2016-08-11 13:26:41 -04001957}
1958
Adam Langleyd9e397b2015-01-22 14:27:53 -08001959// clientSessionCacheKey returns a key used to cache sessionTickets that could
1960// be used to resume previously negotiated TLS sessions with a server.
1961func clientSessionCacheKey(serverAddr net.Addr, config *Config) string {
1962 if len(config.ServerName) > 0 {
1963 return config.ServerName
1964 }
1965 return serverAddr.String()
1966}
1967
1968// mutualProtocol finds the mutual Next Protocol Negotiation or ALPN protocol
1969// given list of possible protocols and a list of the preference order. The
1970// first list must not be empty. It returns the resulting protocol and flag
1971// indicating if the fallback case was reached.
1972func mutualProtocol(protos, preferenceProtos []string) (string, bool) {
1973 for _, s := range preferenceProtos {
1974 for _, c := range protos {
1975 if s == c {
1976 return s, false
1977 }
1978 }
1979 }
1980
1981 return protos[0], true
1982}
1983
1984// writeIntPadded writes x into b, padded up with leading zeros as
1985// needed.
1986func writeIntPadded(b []byte, x *big.Int) {
1987 for i := range b {
1988 b[i] = 0
1989 }
1990 xb := x.Bytes()
1991 copy(b[len(b)-len(xb):], xb)
1992}
Steven Valdez909b19f2016-11-21 15:35:44 -05001993
Robert Sloanb1b54b82017-11-06 13:50:02 -08001994func generatePSKBinders(version uint16, hello *clientHelloMsg, pskCipherSuite *cipherSuite, psk, firstClientHello, helloRetryRequest []byte, config *Config) {
Steven Valdez909b19f2016-11-21 15:35:44 -05001995 if config.Bugs.SendNoPSKBinder {
1996 return
1997 }
1998
1999 binderLen := pskCipherSuite.hash().Size()
2000 if config.Bugs.SendShortPSKBinder {
2001 binderLen--
2002 }
2003
David Benjamin1b249672016-12-06 18:25:50 -05002004 numBinders := 1
2005 if config.Bugs.SendExtraPSKBinder {
2006 numBinders++
2007 }
2008
Steven Valdez909b19f2016-11-21 15:35:44 -05002009 // Fill hello.pskBinders with appropriate length arrays of zeros so the
2010 // length prefixes are correct when computing the binder over the truncated
2011 // ClientHello message.
David Benjamin1b249672016-12-06 18:25:50 -05002012 hello.pskBinders = make([][]byte, numBinders)
2013 for i := range hello.pskBinders {
Steven Valdez909b19f2016-11-21 15:35:44 -05002014 hello.pskBinders[i] = make([]byte, binderLen)
2015 }
2016
2017 helloBytes := hello.marshal()
2018 binderSize := len(hello.pskBinders)*(binderLen+1) + 2
2019 truncatedHello := helloBytes[:len(helloBytes)-binderSize]
Robert Sloan8542c082018-02-05 09:07:34 -08002020 binder := computePSKBinder(psk, version, resumptionPSKBinderLabel, pskCipherSuite, firstClientHello, helloRetryRequest, truncatedHello)
Steven Valdez909b19f2016-11-21 15:35:44 -05002021 if config.Bugs.SendShortPSKBinder {
2022 binder = binder[:binderLen]
2023 }
2024 if config.Bugs.SendInvalidPSKBinder {
2025 binder[0] ^= 1
2026 }
2027
2028 for i := range hello.pskBinders {
2029 hello.pskBinders[i] = binder
2030 }
2031
2032 hello.raw = nil
2033}