Alternative TLS implementation in Go
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

handshake_server.go 25 KiB

пре 8 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
crypto/tls: decouple handshake signatures from the handshake hash. Prior to TLS 1.2, the handshake had a pleasing property that one could incrementally hash it and, from that, get the needed hashes for both the CertificateVerify and Finished messages. TLS 1.2 introduced negotiation for the signature and hash and it became possible for the handshake hash to be, say, SHA-384, but for the CertificateVerify to sign the handshake with SHA-1. The problem is that one doesn't know in advance which hashes will be needed and thus the handshake needs to be buffered. Go ignored this, always kept a single handshake hash, and any signatures over the handshake had to use that hash. However, there are a set of servers that inspect the client's offered signature hash functions and will abort the handshake if one of the server's certificates is signed with a hash function outside of that set. https://robertsspaceindustries.com/ is an example of such a server. Clearly not a lot of thought happened when that server code was written, but its out there and we have to deal with it. This change decouples the handshake hash from the CertificateVerify hash. This lays the groundwork for advertising support for SHA-384 but doesn't actually make that change in the interests of reviewability. Updating the advertised hash functions will cause changes in many of the testdata/ files and some errors might get lost in the noise. This change only needs to update four testdata/ files: one because a SHA-384-based handshake is now being signed with SHA-256 and the others because the TLS 1.2 CertificateRequest message now includes SHA-1. This change also has the effect of adding support for client-certificates in SSLv3 servers. However, SSLv3 is now disabled by default so this should be moot. It would be possible to avoid much of this change and just support SHA-384 for the ServerKeyExchange as the SKX only signs over the nonces and SKX params (a design mistake in TLS). However, that would leave Go in the odd situation where it advertised support for SHA-384, but would only use the handshake hash when signing client certificates. I fear that'll just cause problems in the future. Much of this code was written by davidben@ for the purposes of testing BoringSSL. Partly addresses #9757 Change-Id: I5137a472b6076812af387a5a69fc62c7373cd485 Reviewed-on: https://go-review.googlesource.com/9415 Run-TryBot: Adam Langley <agl@golang.org> Reviewed-by: Adam Langley <agl@golang.org>
пре 9 година
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896
  1. // Copyright 2009 The Go Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. package tls
  5. import (
  6. "crypto"
  7. "crypto/ecdsa"
  8. "crypto/rsa"
  9. "crypto/subtle"
  10. "crypto/x509"
  11. "errors"
  12. "fmt"
  13. "io"
  14. "sync/atomic"
  15. )
  16. type Committer interface {
  17. Commit() error
  18. }
  19. // serverHandshakeState contains details of a server handshake in progress.
  20. // It's discarded once the handshake has completed.
  21. type serverHandshakeState struct {
  22. c *Conn
  23. suite *cipherSuite
  24. masterSecret []byte
  25. cachedClientHelloInfo *ClientHelloInfo
  26. clientHello *clientHelloMsg
  27. hello *serverHelloMsg
  28. cert *Certificate
  29. // TLS 1.0-1.2 fields
  30. ellipticOk bool
  31. ecdsaOk bool
  32. rsaDecryptOk bool
  33. rsaSignOk bool
  34. sessionState *sessionState
  35. finishedHash finishedHash
  36. certsFromClient [][]byte
  37. // TLS 1.3 fields
  38. hello13Enc *encryptedExtensionsMsg
  39. keySchedule *keySchedule13
  40. clientFinishedKey []byte
  41. hsClientCipher interface{}
  42. appClientCipher interface{}
  43. }
  44. // serverHandshake performs a TLS handshake as a server.
  45. // c.out.Mutex <= L; c.handshakeMutex <= L.
  46. func (c *Conn) serverHandshake() error {
  47. // If this is the first server handshake, we generate a random key to
  48. // encrypt the tickets with.
  49. c.config.serverInitOnce.Do(func() { c.config.serverInit(nil) })
  50. hs := serverHandshakeState{
  51. c: c,
  52. }
  53. c.in.traceErr = hs.traceErr
  54. c.out.traceErr = hs.traceErr
  55. isResume, err := hs.readClientHello()
  56. if err != nil {
  57. return err
  58. }
  59. // For an overview of TLS handshaking, see https://tools.ietf.org/html/rfc5246#section-7.3
  60. // and https://tools.ietf.org/html/draft-ietf-tls-tls13-18#section-2
  61. c.buffering = true
  62. if c.vers >= VersionTLS13 {
  63. if err := hs.doTLS13Handshake(); err != nil {
  64. return err
  65. }
  66. if _, err := c.flush(); err != nil {
  67. return err
  68. }
  69. c.hs = &hs
  70. // If the client is sending early data while the server expects
  71. // it, delay the Finished check until HandshakeConfirmed() is
  72. // called or until all early data is Read(). Otherwise, complete
  73. // authenticating the client now (there is no support for
  74. // sending 0.5-RTT data to a potential unauthenticated client).
  75. if c.phase != readingEarlyData {
  76. if err := hs.readClientFinished13(false); err != nil {
  77. return err
  78. }
  79. }
  80. c.handshakeComplete = true
  81. return nil
  82. } else if isResume {
  83. // The client has included a session ticket and so we do an abbreviated handshake.
  84. if err := hs.doResumeHandshake(); err != nil {
  85. return err
  86. }
  87. if err := hs.establishKeys(); err != nil {
  88. return err
  89. }
  90. // ticketSupported is set in a resumption handshake if the
  91. // ticket from the client was encrypted with an old session
  92. // ticket key and thus a refreshed ticket should be sent.
  93. if hs.hello.ticketSupported {
  94. if err := hs.sendSessionTicket(); err != nil {
  95. return err
  96. }
  97. }
  98. if err := hs.sendFinished(c.serverFinished[:]); err != nil {
  99. return err
  100. }
  101. if _, err := c.flush(); err != nil {
  102. return err
  103. }
  104. c.clientFinishedIsFirst = false
  105. if err := hs.readFinished(nil); err != nil {
  106. return err
  107. }
  108. c.didResume = true
  109. } else {
  110. // The client didn't include a session ticket, or it wasn't
  111. // valid so we do a full handshake.
  112. if err := hs.doFullHandshake(); err != nil {
  113. return err
  114. }
  115. if err := hs.establishKeys(); err != nil {
  116. return err
  117. }
  118. if err := hs.readFinished(c.clientFinished[:]); err != nil {
  119. return err
  120. }
  121. c.clientFinishedIsFirst = true
  122. c.buffering = true
  123. if err := hs.sendSessionTicket(); err != nil {
  124. return err
  125. }
  126. if err := hs.sendFinished(nil); err != nil {
  127. return err
  128. }
  129. if _, err := c.flush(); err != nil {
  130. return err
  131. }
  132. }
  133. if c.hand.Len() > 0 {
  134. return c.sendAlert(alertUnexpectedMessage)
  135. }
  136. c.phase = handshakeConfirmed
  137. atomic.StoreInt32(&c.handshakeConfirmed, 1)
  138. c.handshakeComplete = true
  139. return nil
  140. }
  141. // readClientHello reads a ClientHello message from the client and decides
  142. // whether we will perform session resumption.
  143. func (hs *serverHandshakeState) readClientHello() (isResume bool, err error) {
  144. c := hs.c
  145. msg, err := c.readHandshake()
  146. if err != nil {
  147. return false, err
  148. }
  149. var ok bool
  150. hs.clientHello, ok = msg.(*clientHelloMsg)
  151. if !ok {
  152. c.sendAlert(alertUnexpectedMessage)
  153. return false, unexpectedMessageError(hs.clientHello, msg)
  154. }
  155. if c.config.GetConfigForClient != nil {
  156. if newConfig, err := c.config.GetConfigForClient(hs.clientHelloInfo()); err != nil {
  157. c.out.traceErr, c.in.traceErr = nil, nil // disable tracing
  158. c.sendAlert(alertInternalError)
  159. return false, err
  160. } else if newConfig != nil {
  161. newConfig.serverInitOnce.Do(func() { newConfig.serverInit(c.config) })
  162. c.config = newConfig
  163. }
  164. }
  165. var keyShares []CurveID
  166. for _, ks := range hs.clientHello.keyShares {
  167. keyShares = append(keyShares, ks.group)
  168. }
  169. if hs.clientHello.supportedVersions != nil {
  170. c.vers, ok = c.config.pickVersion(hs.clientHello.supportedVersions)
  171. if !ok {
  172. c.sendAlert(alertProtocolVersion)
  173. return false, fmt.Errorf("tls: none of the client versions (%x) are supported", hs.clientHello.supportedVersions)
  174. }
  175. } else {
  176. c.vers, ok = c.config.mutualVersion(hs.clientHello.vers)
  177. if !ok {
  178. c.sendAlert(alertProtocolVersion)
  179. return false, fmt.Errorf("tls: client offered an unsupported, maximum protocol version of %x", hs.clientHello.vers)
  180. }
  181. }
  182. c.haveVers = true
  183. preferredCurves := c.config.curvePreferences()
  184. Curves:
  185. for _, curve := range hs.clientHello.supportedCurves {
  186. for _, supported := range preferredCurves {
  187. if supported == curve {
  188. hs.ellipticOk = true
  189. break Curves
  190. }
  191. }
  192. }
  193. // If present, the supported points extension must include uncompressed.
  194. // Can be absent. This behavior mirrors BoringSSL.
  195. if hs.clientHello.supportedPoints != nil {
  196. supportedPointFormat := false
  197. for _, pointFormat := range hs.clientHello.supportedPoints {
  198. if pointFormat == pointFormatUncompressed {
  199. supportedPointFormat = true
  200. break
  201. }
  202. }
  203. if !supportedPointFormat {
  204. c.sendAlert(alertHandshakeFailure)
  205. return false, errors.New("tls: client does not support uncompressed points")
  206. }
  207. }
  208. foundCompression := false
  209. // We only support null compression, so check that the client offered it.
  210. for _, compression := range hs.clientHello.compressionMethods {
  211. if compression == compressionNone {
  212. foundCompression = true
  213. break
  214. }
  215. }
  216. if !foundCompression {
  217. c.sendAlert(alertIllegalParameter)
  218. return false, errors.New("tls: client does not support uncompressed connections")
  219. }
  220. if len(hs.clientHello.compressionMethods) != 1 && c.vers >= VersionTLS13 {
  221. c.sendAlert(alertIllegalParameter)
  222. return false, errors.New("tls: 1.3 client offered compression")
  223. }
  224. if len(hs.clientHello.secureRenegotiation) != 0 {
  225. c.sendAlert(alertHandshakeFailure)
  226. return false, errors.New("tls: initial handshake had non-empty renegotiation extension")
  227. }
  228. if c.vers < VersionTLS13 {
  229. hs.hello = new(serverHelloMsg)
  230. hs.hello.vers = c.vers
  231. hs.hello.random = make([]byte, 32)
  232. _, err = io.ReadFull(c.config.rand(), hs.hello.random)
  233. if err != nil {
  234. c.sendAlert(alertInternalError)
  235. return false, err
  236. }
  237. hs.hello.secureRenegotiationSupported = hs.clientHello.secureRenegotiationSupported
  238. hs.hello.compressionMethod = compressionNone
  239. } else {
  240. hs.hello = new(serverHelloMsg)
  241. hs.hello13Enc = new(encryptedExtensionsMsg)
  242. hs.hello.vers = c.vers
  243. hs.hello.random = make([]byte, 32)
  244. hs.hello.sessionId = hs.clientHello.sessionId
  245. _, err = io.ReadFull(c.config.rand(), hs.hello.random)
  246. if err != nil {
  247. c.sendAlert(alertInternalError)
  248. return false, err
  249. }
  250. }
  251. if len(hs.clientHello.serverName) > 0 {
  252. c.serverName = hs.clientHello.serverName
  253. }
  254. if len(hs.clientHello.alpnProtocols) > 0 {
  255. if selectedProto, fallback := mutualProtocol(hs.clientHello.alpnProtocols, c.config.NextProtos); !fallback {
  256. if hs.hello != nil {
  257. hs.hello.alpnProtocol = selectedProto
  258. } else {
  259. hs.hello13Enc.alpnProtocol = selectedProto
  260. }
  261. c.clientProtocol = selectedProto
  262. }
  263. } else {
  264. // Although sending an empty NPN extension is reasonable, Firefox has
  265. // had a bug around this. Best to send nothing at all if
  266. // c.config.NextProtos is empty. See
  267. // https://golang.org/issue/5445.
  268. if hs.clientHello.nextProtoNeg && len(c.config.NextProtos) > 0 && c.vers < VersionTLS13 {
  269. hs.hello.nextProtoNeg = true
  270. hs.hello.nextProtos = c.config.NextProtos
  271. }
  272. }
  273. hs.cert, err = c.config.getCertificate(hs.clientHelloInfo())
  274. if err != nil {
  275. c.sendAlert(alertInternalError)
  276. return false, err
  277. }
  278. if hs.clientHello.scts && hs.hello != nil {
  279. hs.hello.scts = hs.cert.SignedCertificateTimestamps
  280. }
  281. if priv, ok := hs.cert.PrivateKey.(crypto.Signer); ok {
  282. switch priv.Public().(type) {
  283. case *ecdsa.PublicKey:
  284. hs.ecdsaOk = true
  285. case *rsa.PublicKey:
  286. hs.rsaSignOk = true
  287. default:
  288. c.sendAlert(alertInternalError)
  289. return false, fmt.Errorf("tls: unsupported signing key type (%T)", priv.Public())
  290. }
  291. }
  292. if priv, ok := hs.cert.PrivateKey.(crypto.Decrypter); ok {
  293. switch priv.Public().(type) {
  294. case *rsa.PublicKey:
  295. hs.rsaDecryptOk = true
  296. default:
  297. c.sendAlert(alertInternalError)
  298. return false, fmt.Errorf("tls: unsupported decryption key type (%T)", priv.Public())
  299. }
  300. }
  301. if c.vers != VersionTLS13 && hs.checkForResumption() {
  302. return true, nil
  303. }
  304. var preferenceList, supportedList []uint16
  305. if c.config.PreferServerCipherSuites {
  306. preferenceList = c.config.cipherSuites()
  307. supportedList = hs.clientHello.cipherSuites
  308. } else {
  309. preferenceList = hs.clientHello.cipherSuites
  310. supportedList = c.config.cipherSuites()
  311. }
  312. for _, id := range preferenceList {
  313. if hs.setCipherSuite(id, supportedList, c.vers) {
  314. break
  315. }
  316. }
  317. if hs.suite == nil {
  318. c.sendAlert(alertHandshakeFailure)
  319. return false, errors.New("tls: no cipher suite supported by both client and server")
  320. }
  321. // See https://tools.ietf.org/html/rfc7507.
  322. for _, id := range hs.clientHello.cipherSuites {
  323. if id == TLS_FALLBACK_SCSV {
  324. // The client is doing a fallback connection.
  325. if c.vers < c.config.maxVersion() {
  326. c.sendAlert(alertInappropriateFallback)
  327. return false, errors.New("tls: client using inappropriate protocol fallback")
  328. }
  329. break
  330. }
  331. }
  332. return false, nil
  333. }
  334. // checkForResumption reports whether we should perform resumption on this connection.
  335. func (hs *serverHandshakeState) checkForResumption() bool {
  336. c := hs.c
  337. if c.config.SessionTicketsDisabled {
  338. return false
  339. }
  340. sessionTicket := append([]uint8{}, hs.clientHello.sessionTicket...)
  341. serializedState, usedOldKey := c.decryptTicket(sessionTicket)
  342. hs.sessionState = &sessionState{usedOldKey: usedOldKey}
  343. if hs.sessionState.unmarshal(serializedState) != alertSuccess {
  344. return false
  345. }
  346. // Never resume a session for a different TLS version.
  347. if c.vers != hs.sessionState.vers {
  348. return false
  349. }
  350. cipherSuiteOk := false
  351. // Check that the client is still offering the ciphersuite in the session.
  352. for _, id := range hs.clientHello.cipherSuites {
  353. if id == hs.sessionState.cipherSuite {
  354. cipherSuiteOk = true
  355. break
  356. }
  357. }
  358. if !cipherSuiteOk {
  359. return false
  360. }
  361. // Check that we also support the ciphersuite from the session.
  362. if !hs.setCipherSuite(hs.sessionState.cipherSuite, c.config.cipherSuites(), hs.sessionState.vers) {
  363. return false
  364. }
  365. sessionHasClientCerts := len(hs.sessionState.certificates) != 0
  366. needClientCerts := c.config.ClientAuth == RequireAnyClientCert || c.config.ClientAuth == RequireAndVerifyClientCert
  367. if needClientCerts && !sessionHasClientCerts {
  368. return false
  369. }
  370. if sessionHasClientCerts && c.config.ClientAuth == NoClientCert {
  371. return false
  372. }
  373. return true
  374. }
  375. func (hs *serverHandshakeState) doResumeHandshake() error {
  376. c := hs.c
  377. hs.hello.cipherSuite = hs.suite.id
  378. // We echo the client's session ID in the ServerHello to let it know
  379. // that we're doing a resumption.
  380. hs.hello.sessionId = hs.clientHello.sessionId
  381. hs.hello.ticketSupported = hs.sessionState.usedOldKey
  382. hs.finishedHash = newFinishedHash(c.vers, hs.suite)
  383. hs.finishedHash.discardHandshakeBuffer()
  384. hs.finishedHash.Write(hs.clientHello.marshal())
  385. hs.finishedHash.Write(hs.hello.marshal())
  386. if _, err := c.writeRecord(recordTypeHandshake, hs.hello.marshal()); err != nil {
  387. return err
  388. }
  389. if len(hs.sessionState.certificates) > 0 {
  390. if _, err := hs.processCertsFromClient(hs.sessionState.certificates); err != nil {
  391. return err
  392. }
  393. }
  394. hs.masterSecret = hs.sessionState.masterSecret
  395. return nil
  396. }
  397. func (hs *serverHandshakeState) doFullHandshake() error {
  398. c := hs.c
  399. if hs.clientHello.ocspStapling && len(hs.cert.OCSPStaple) > 0 {
  400. hs.hello.ocspStapling = true
  401. }
  402. hs.hello.ticketSupported = hs.clientHello.ticketSupported && !c.config.SessionTicketsDisabled
  403. hs.hello.cipherSuite = hs.suite.id
  404. hs.finishedHash = newFinishedHash(hs.c.vers, hs.suite)
  405. if c.config.ClientAuth == NoClientCert {
  406. // No need to keep a full record of the handshake if client
  407. // certificates won't be used.
  408. hs.finishedHash.discardHandshakeBuffer()
  409. }
  410. hs.finishedHash.Write(hs.clientHello.marshal())
  411. hs.finishedHash.Write(hs.hello.marshal())
  412. if _, err := c.writeRecord(recordTypeHandshake, hs.hello.marshal()); err != nil {
  413. return err
  414. }
  415. certMsg := new(certificateMsg)
  416. certMsg.certificates = hs.cert.Certificate
  417. hs.finishedHash.Write(certMsg.marshal())
  418. if _, err := c.writeRecord(recordTypeHandshake, certMsg.marshal()); err != nil {
  419. return err
  420. }
  421. if hs.hello.ocspStapling {
  422. certStatus := new(certificateStatusMsg)
  423. certStatus.statusType = statusTypeOCSP
  424. certStatus.response = hs.cert.OCSPStaple
  425. hs.finishedHash.Write(certStatus.marshal())
  426. if _, err := c.writeRecord(recordTypeHandshake, certStatus.marshal()); err != nil {
  427. return err
  428. }
  429. }
  430. keyAgreement := hs.suite.ka(c.vers)
  431. skx, err := keyAgreement.generateServerKeyExchange(c.config, hs.cert, hs.clientHello, hs.hello)
  432. if err != nil {
  433. c.sendAlert(alertHandshakeFailure)
  434. return err
  435. }
  436. if skx != nil {
  437. hs.finishedHash.Write(skx.marshal())
  438. if _, err := c.writeRecord(recordTypeHandshake, skx.marshal()); err != nil {
  439. return err
  440. }
  441. }
  442. if c.config.ClientAuth >= RequestClientCert {
  443. // Request a client certificate
  444. certReq := new(certificateRequestMsg)
  445. certReq.certificateTypes = []byte{
  446. byte(certTypeRSASign),
  447. byte(certTypeECDSASign),
  448. }
  449. if c.vers >= VersionTLS12 {
  450. certReq.hasSignatureAndHash = true
  451. certReq.supportedSignatureAlgorithms = supportedSignatureAlgorithms
  452. }
  453. // An empty list of certificateAuthorities signals to
  454. // the client that it may send any certificate in response
  455. // to our request. When we know the CAs we trust, then
  456. // we can send them down, so that the client can choose
  457. // an appropriate certificate to give to us.
  458. if c.config.ClientCAs != nil {
  459. certReq.certificateAuthorities = c.config.ClientCAs.Subjects()
  460. }
  461. hs.finishedHash.Write(certReq.marshal())
  462. if _, err := c.writeRecord(recordTypeHandshake, certReq.marshal()); err != nil {
  463. return err
  464. }
  465. }
  466. helloDone := new(serverHelloDoneMsg)
  467. hs.finishedHash.Write(helloDone.marshal())
  468. if _, err := c.writeRecord(recordTypeHandshake, helloDone.marshal()); err != nil {
  469. return err
  470. }
  471. if _, err := c.flush(); err != nil {
  472. return err
  473. }
  474. var pub crypto.PublicKey // public key for client auth, if any
  475. msg, err := c.readHandshake()
  476. if err != nil {
  477. return err
  478. }
  479. var ok bool
  480. // If we requested a client certificate, then the client must send a
  481. // certificate message, even if it's empty.
  482. if c.config.ClientAuth >= RequestClientCert {
  483. if certMsg, ok = msg.(*certificateMsg); !ok {
  484. c.sendAlert(alertUnexpectedMessage)
  485. return unexpectedMessageError(certMsg, msg)
  486. }
  487. hs.finishedHash.Write(certMsg.marshal())
  488. if len(certMsg.certificates) == 0 {
  489. // The client didn't actually send a certificate
  490. switch c.config.ClientAuth {
  491. case RequireAnyClientCert, RequireAndVerifyClientCert:
  492. c.sendAlert(alertBadCertificate)
  493. return errors.New("tls: client didn't provide a certificate")
  494. }
  495. }
  496. pub, err = hs.processCertsFromClient(certMsg.certificates)
  497. if err != nil {
  498. return err
  499. }
  500. msg, err = c.readHandshake()
  501. if err != nil {
  502. return err
  503. }
  504. }
  505. // Get client key exchange
  506. ckx, ok := msg.(*clientKeyExchangeMsg)
  507. if !ok {
  508. c.sendAlert(alertUnexpectedMessage)
  509. return unexpectedMessageError(ckx, msg)
  510. }
  511. hs.finishedHash.Write(ckx.marshal())
  512. preMasterSecret, err := keyAgreement.processClientKeyExchange(c.config, hs.cert, ckx, c.vers)
  513. if err != nil {
  514. if err == errClientKeyExchange {
  515. c.sendAlert(alertDecodeError)
  516. } else {
  517. c.sendAlert(alertInternalError)
  518. }
  519. return err
  520. }
  521. hs.masterSecret = masterFromPreMasterSecret(c.vers, hs.suite, preMasterSecret, hs.clientHello.random, hs.hello.random)
  522. if err := c.config.writeKeyLog("CLIENT_RANDOM", hs.clientHello.random, hs.masterSecret); err != nil {
  523. c.sendAlert(alertInternalError)
  524. return err
  525. }
  526. // If we received a client cert in response to our certificate request message,
  527. // the client will send us a certificateVerifyMsg immediately after the
  528. // clientKeyExchangeMsg. This message is a digest of all preceding
  529. // handshake-layer messages that is signed using the private key corresponding
  530. // to the client's certificate. This allows us to verify that the client is in
  531. // possession of the private key of the certificate.
  532. if len(c.peerCertificates) > 0 {
  533. msg, err = c.readHandshake()
  534. if err != nil {
  535. return err
  536. }
  537. certVerify, ok := msg.(*certificateVerifyMsg)
  538. if !ok {
  539. c.sendAlert(alertUnexpectedMessage)
  540. return unexpectedMessageError(certVerify, msg)
  541. }
  542. // Determine the signature type.
  543. _, sigType, hashFunc, err := pickSignatureAlgorithm(pub, []SignatureScheme{certVerify.signatureAlgorithm}, supportedSignatureAlgorithms, c.vers)
  544. if err != nil {
  545. c.sendAlert(alertIllegalParameter)
  546. return err
  547. }
  548. var digest []byte
  549. if digest, err = hs.finishedHash.hashForClientCertificate(sigType, hashFunc, hs.masterSecret); err == nil {
  550. err = verifyHandshakeSignature(sigType, pub, hashFunc, digest, certVerify.signature)
  551. }
  552. if err != nil {
  553. c.sendAlert(alertBadCertificate)
  554. return errors.New("tls: could not validate signature of connection nonces: " + err.Error())
  555. }
  556. hs.finishedHash.Write(certVerify.marshal())
  557. }
  558. hs.finishedHash.discardHandshakeBuffer()
  559. return nil
  560. }
  561. func (hs *serverHandshakeState) establishKeys() error {
  562. c := hs.c
  563. clientMAC, serverMAC, clientKey, serverKey, clientIV, serverIV :=
  564. keysFromMasterSecret(c.vers, hs.suite, hs.masterSecret, hs.clientHello.random, hs.hello.random, hs.suite.macLen, hs.suite.keyLen, hs.suite.ivLen)
  565. var clientCipher, serverCipher interface{}
  566. var clientHash, serverHash macFunction
  567. if hs.suite.aead == nil {
  568. clientCipher = hs.suite.cipher(clientKey, clientIV, true /* for reading */)
  569. clientHash = hs.suite.mac(c.vers, clientMAC)
  570. serverCipher = hs.suite.cipher(serverKey, serverIV, false /* not for reading */)
  571. serverHash = hs.suite.mac(c.vers, serverMAC)
  572. } else {
  573. clientCipher = hs.suite.aead(clientKey, clientIV)
  574. serverCipher = hs.suite.aead(serverKey, serverIV)
  575. }
  576. c.in.prepareCipherSpec(c.vers, clientCipher, clientHash)
  577. c.out.prepareCipherSpec(c.vers, serverCipher, serverHash)
  578. return nil
  579. }
  580. func (hs *serverHandshakeState) readFinished(out []byte) error {
  581. c := hs.c
  582. c.readRecord(recordTypeChangeCipherSpec)
  583. if c.in.err != nil {
  584. return c.in.err
  585. }
  586. if hs.hello.nextProtoNeg {
  587. msg, err := c.readHandshake()
  588. if err != nil {
  589. return err
  590. }
  591. nextProto, ok := msg.(*nextProtoMsg)
  592. if !ok {
  593. c.sendAlert(alertUnexpectedMessage)
  594. return unexpectedMessageError(nextProto, msg)
  595. }
  596. hs.finishedHash.Write(nextProto.marshal())
  597. c.clientProtocol = nextProto.proto
  598. }
  599. msg, err := c.readHandshake()
  600. if err != nil {
  601. return err
  602. }
  603. clientFinished, ok := msg.(*finishedMsg)
  604. if !ok {
  605. c.sendAlert(alertUnexpectedMessage)
  606. return unexpectedMessageError(clientFinished, msg)
  607. }
  608. verify := hs.finishedHash.clientSum(hs.masterSecret)
  609. if len(verify) != len(clientFinished.verifyData) ||
  610. subtle.ConstantTimeCompare(verify, clientFinished.verifyData) != 1 {
  611. c.sendAlert(alertDecryptError)
  612. return errors.New("tls: client's Finished message is incorrect")
  613. }
  614. hs.finishedHash.Write(clientFinished.marshal())
  615. copy(out, verify)
  616. return nil
  617. }
  618. func (hs *serverHandshakeState) sendSessionTicket() error {
  619. if !hs.hello.ticketSupported {
  620. return nil
  621. }
  622. c := hs.c
  623. m := new(newSessionTicketMsg)
  624. var err error
  625. state := sessionState{
  626. vers: c.vers,
  627. cipherSuite: hs.suite.id,
  628. masterSecret: hs.masterSecret,
  629. certificates: hs.certsFromClient,
  630. }
  631. m.ticket, err = c.encryptTicket(state.marshal())
  632. if err != nil {
  633. return err
  634. }
  635. hs.finishedHash.Write(m.marshal())
  636. if _, err := c.writeRecord(recordTypeHandshake, m.marshal()); err != nil {
  637. return err
  638. }
  639. return nil
  640. }
  641. func (hs *serverHandshakeState) sendFinished(out []byte) error {
  642. c := hs.c
  643. if _, err := c.writeRecord(recordTypeChangeCipherSpec, []byte{1}); err != nil {
  644. return err
  645. }
  646. finished := new(finishedMsg)
  647. finished.verifyData = hs.finishedHash.serverSum(hs.masterSecret)
  648. hs.finishedHash.Write(finished.marshal())
  649. if _, err := c.writeRecord(recordTypeHandshake, finished.marshal()); err != nil {
  650. return err
  651. }
  652. c.cipherSuite = hs.suite.id
  653. copy(out, finished.verifyData)
  654. return nil
  655. }
  656. // processCertsFromClient takes a chain of client certificates either from a
  657. // Certificates message or from a sessionState and verifies them. It returns
  658. // the public key of the leaf certificate.
  659. func (hs *serverHandshakeState) processCertsFromClient(certificates [][]byte) (crypto.PublicKey, error) {
  660. c := hs.c
  661. hs.certsFromClient = certificates
  662. certs := make([]*x509.Certificate, len(certificates))
  663. var err error
  664. for i, asn1Data := range certificates {
  665. if certs[i], err = x509.ParseCertificate(asn1Data); err != nil {
  666. c.sendAlert(alertBadCertificate)
  667. return nil, errors.New("tls: failed to parse client certificate: " + err.Error())
  668. }
  669. }
  670. if c.config.ClientAuth >= VerifyClientCertIfGiven && len(certs) > 0 {
  671. opts := x509.VerifyOptions{
  672. Roots: c.config.ClientCAs,
  673. CurrentTime: c.config.time(),
  674. Intermediates: x509.NewCertPool(),
  675. KeyUsages: []x509.ExtKeyUsage{x509.ExtKeyUsageClientAuth},
  676. }
  677. for _, cert := range certs[1:] {
  678. opts.Intermediates.AddCert(cert)
  679. }
  680. chains, err := certs[0].Verify(opts)
  681. if err != nil {
  682. c.sendAlert(alertBadCertificate)
  683. return nil, errors.New("tls: failed to verify client's certificate: " + err.Error())
  684. }
  685. c.verifiedChains = chains
  686. }
  687. if c.config.VerifyPeerCertificate != nil {
  688. if err := c.config.VerifyPeerCertificate(certificates, c.verifiedChains); err != nil {
  689. c.sendAlert(alertBadCertificate)
  690. return nil, err
  691. }
  692. }
  693. if len(certs) == 0 {
  694. return nil, nil
  695. }
  696. var pub crypto.PublicKey
  697. switch key := certs[0].PublicKey.(type) {
  698. case *ecdsa.PublicKey, *rsa.PublicKey:
  699. pub = key
  700. default:
  701. c.sendAlert(alertUnsupportedCertificate)
  702. return nil, fmt.Errorf("tls: client's certificate contains an unsupported public key of type %T", certs[0].PublicKey)
  703. }
  704. c.peerCertificates = certs
  705. return pub, nil
  706. }
  707. // setCipherSuite sets a cipherSuite with the given id as the serverHandshakeState
  708. // suite if that cipher suite is acceptable to use.
  709. // It returns a bool indicating if the suite was set.
  710. func (hs *serverHandshakeState) setCipherSuite(id uint16, supportedCipherSuites []uint16, version uint16) bool {
  711. for _, supported := range supportedCipherSuites {
  712. if id == supported {
  713. var candidate *cipherSuite
  714. for _, s := range cipherSuites {
  715. if s.id == id {
  716. candidate = s
  717. break
  718. }
  719. }
  720. if candidate == nil {
  721. continue
  722. }
  723. if version >= VersionTLS13 && candidate.flags&suiteTLS13 != 0 {
  724. hs.suite = candidate
  725. return true
  726. }
  727. if version < VersionTLS13 && candidate.flags&suiteTLS13 != 0 {
  728. continue
  729. }
  730. // Don't select a ciphersuite which we can't
  731. // support for this client.
  732. if candidate.flags&suiteECDHE != 0 {
  733. if !hs.ellipticOk {
  734. continue
  735. }
  736. if candidate.flags&suiteECDSA != 0 {
  737. if !hs.ecdsaOk {
  738. continue
  739. }
  740. } else if !hs.rsaSignOk {
  741. continue
  742. }
  743. } else if !hs.rsaDecryptOk {
  744. continue
  745. }
  746. if version < VersionTLS12 && candidate.flags&suiteTLS12 != 0 {
  747. continue
  748. }
  749. hs.suite = candidate
  750. return true
  751. }
  752. }
  753. return false
  754. }
  755. // suppVersArray is the backing array of ClientHelloInfo.SupportedVersions
  756. var suppVersArray = [...]uint16{VersionTLS12, VersionTLS11, VersionTLS10, VersionSSL30}
  757. func (hs *serverHandshakeState) clientHelloInfo() *ClientHelloInfo {
  758. if hs.cachedClientHelloInfo != nil {
  759. return hs.cachedClientHelloInfo
  760. }
  761. var supportedVersions []uint16
  762. if hs.clientHello.supportedVersions != nil {
  763. supportedVersions = hs.clientHello.supportedVersions
  764. } else if hs.clientHello.vers > VersionTLS12 {
  765. supportedVersions = suppVersArray[:]
  766. } else if hs.clientHello.vers >= VersionSSL30 {
  767. supportedVersions = suppVersArray[VersionTLS12-hs.clientHello.vers:]
  768. }
  769. var pskBinder []byte
  770. if len(hs.clientHello.psks) > 0 {
  771. pskBinder = hs.clientHello.psks[0].binder
  772. }
  773. hs.cachedClientHelloInfo = &ClientHelloInfo{
  774. CipherSuites: hs.clientHello.cipherSuites,
  775. ServerName: hs.clientHello.serverName,
  776. SupportedCurves: hs.clientHello.supportedCurves,
  777. SupportedPoints: hs.clientHello.supportedPoints,
  778. SignatureSchemes: hs.clientHello.supportedSignatureAlgorithms,
  779. SupportedProtos: hs.clientHello.alpnProtocols,
  780. SupportedVersions: supportedVersions,
  781. Conn: hs.c.conn,
  782. Offered0RTTData: hs.clientHello.earlyData,
  783. Fingerprint: pskBinder,
  784. }
  785. return hs.cachedClientHelloInfo
  786. }