Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

Send the correct SNI from tsh to auth server #3872

Merged
merged 1 commit into from
Jun 29, 2020
Merged

Conversation

awly
Copy link
Contributor

@awly awly commented Jun 23, 2020

SNI is used to indicate which cluster's CA to use for client cert
validation. If SNI is not sent, or set as "teleport.cluster.local"
(which is default in the client config), auth server will attempt to
validate against all known CAs.

The list of CA subjects is sent to the client during handshake, before
client sends its own client cert. If this list is too long, handshake
will fail. The limit is 65535 bytes, because TLS wire encoding uses 2
bytes for a length prefix. In teleport, this fits ~520-540 trusted
cluster CAs.

To avoid handshake failures on such large setups, all clients must send
the correct SNI. In some future version, we should enforce this to catch
such issues early. For now, added a debug log to report clients using
the default ServerName. Also added a check for large number of CAs, to
print a helpful error.

Updates #3870

Comment on lines +173 to +187
// Per https://tools.ietf.org/html/rfc5246#section-7.4.4 the total size of
// the known CA subjects sent to the client can't exceed 2^16-1 (due to
// 2-byte length encoding). The crypto/tls stack will panic if this
// happens. To make the error less cryptic, catch this condition and return
// a better error.
//
// This may happen with a very large (>500) number of trusted clusters, if
// the client doesn't send the correct ServerName in its ClientHelloInfo
// (see the switch at the top of this func).
var totalSubjectsLen int64
for _, s := range pool.Subjects() {
// Each subject in the list gets a separate 2-byte length prefix.
totalSubjectsLen += 2
totalSubjectsLen += int64(len(s))
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is great! 👍

lib/auth/middleware.go Outdated Show resolved Hide resolved
SNI is used to indicate which cluster's CA to use for client cert
validation. If SNI is not sent, or set as "teleport.cluster.local"
(which is default in the client config), auth server will attempt to
validate against all known CAs.

The list of CA subjects is sent to the client during handshake, before
client sends its own client cert. If this list is too long, handshake
will fail. The limit is 65535 bytes, because TLS wire encoding uses 2
bytes for a length prefix. In teleport, this fits ~520-540 trusted
cluster CAs.

To avoid handshake failures on such large setups, all clients must send
the correct SNI. In some future version, we should enforce this to catch
such issues early. For now, added a debug log to report clients using
the default ServerName. Also added a check for large number of CAs, to
print a helpful error.

Updates #3870
@awly awly force-pushed the andrew/tsh-auth-server-sni branch from c950d8e to fb94a64 Compare June 26, 2020 18:14
@awly
Copy link
Contributor Author

awly commented Jun 27, 2020

retest this please

@awly awly merged commit d2c03e9 into master Jun 29, 2020
@awly awly deleted the andrew/tsh-auth-server-sni branch June 29, 2020 16:39
# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants