This change causes TLS handshake messages to be buffered and written in
a single Write to the underlying net.Conn.
There are two reasons to want to do this:
Firstly, it's slightly preferable to do this in order to save sending
several, small packets over the network where a single one will do.
Secondly, since 37c28759ca46cf381a466e32168a793165d9c9e9 errors from
Write have been returned from a handshake. This means that, if a peer
closes the connection during a handshake, a “broken pipe” error may
result from tls.Conn.Handshake(). This can mask any, more detailed,
fatal alerts that the peer may have sent because a read will never
happen.
Buffering handshake messages means that the peer will not receive, and
possibly reject, any of a flow while it's still being written.
Fixes#15709
Change-Id: I38dcff1abecc06e52b2de647ea98713ce0fb9a21
Reviewed-on: https://go-review.googlesource.com/23609
Reviewed-by: Andrew Gerrand <adg@golang.org>
Run-TryBot: Andrew Gerrand <adg@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
This fixes `go test go/types`.
https://golang.org/cl/23487/ introduced this code which contains
two unused variables (declared and assigned to, but never read).
cmd/compile doesn't report the error due open issue #8560 (the
variables are assigned to in a closure), but go/types does. The
build bot only runs go/types tests in -short mode (which doesn't
typecheck the std lib), hence this doesn't show up on the dashboard
either.
We cannot call b.Fatal and friends in the goroutine. Communicating
the error to the invoking function requires a channel or a mutex.
Unless the channel/sycnhronized variable is tested in each iteration
that follows, the iteration blocks if there's a failure. Testing in
each iteration may affect benchmark times.
One could use a time-out but that time depends on the underlying system.
Panicking seems good enough in this unlikely case; better than hanging
or affecting benchmark times.
Change-Id: Idce1172da8058e580fa3b3e398825b0eb4316325
Reviewed-on: https://go-review.googlesource.com/23528
Reviewed-by: Ian Lance Taylor <iant@golang.org>
Run-TryBot: Ian Lance Taylor <iant@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
The Windows builders run the throughput benchmarks really slowly with a
64kb buffer. Lowering it to 16kb brings the performance back into line
with the other builders.
This is a work-around to get the build green until we can figure out why
the Windows builders are slow with the larger buffer size.
Update #15899
Change-Id: I215ebf115e8295295c87f3b3e22a4ef1f9e77f81
Reviewed-on: https://go-review.googlesource.com/23574
Reviewed-by: Ian Lance Taylor <iant@golang.org>
The current code, introduced after Go 1.6 to improve latency on
low-bandwidth connections, sends 1 kB packets until 1 MB has been sent,
and then sends 16 kB packets (the maximum record size).
Unfortunately this decreases throughput for 1-16 MB responses by 20% or so.
Following discussion on #15713, change cutoff to 128 kB sent
and also grow the size allowed for successive packets:
1 kB, 2 kB, 3 kB, ..., 15 kB, 16 kB.
This fixes the throughput problems: the overhead is now closer to 2%.
I hope this still helps with latency but I don't have a great way to test it.
At the least, it's not worse than Go 1.6.
Comparing MaxPacket vs DynamicPacket benchmarks:
name maxpkt time/op dyn. time/op delta
Throughput/1MB-8 5.07ms ± 7% 5.21ms ± 7% +2.73% (p=0.023 n=16+16)
Throughput/2MB-8 15.7ms ±201% 8.4ms ± 5% ~ (p=0.604 n=20+16)
Throughput/4MB-8 14.3ms ± 1% 14.5ms ± 1% +1.53% (p=0.000 n=16+16)
Throughput/8MB-8 26.6ms ± 1% 26.8ms ± 1% +0.47% (p=0.003 n=19+18)
Throughput/16MB-8 51.0ms ± 1% 51.3ms ± 1% +0.47% (p=0.000 n=20+20)
Throughput/32MB-8 100ms ± 1% 100ms ± 1% +0.24% (p=0.033 n=20+20)
Throughput/64MB-8 197ms ± 0% 198ms ± 0% +0.56% (p=0.000 n=18+7)
The small MB runs are bimodal in both cases, probably GC pauses.
But there's clearly no general slowdown anymore.
Fixes#15713.
Change-Id: I5fc44680ba71812d24baac142bceee0e23f2e382
Reviewed-on: https://go-review.googlesource.com/23487
Reviewed-by: Ian Lance Taylor <iant@golang.org>
Instead, decline the session and do a full handshake. The semantics of
cross-version resume are unclear, and all major client implementations
treat this as a fatal error. (This doesn't come up very much, mostly if
the client does the browser version fallback without sharding the
session cache.)
See BoringSSL's bdf5e72f50e25f0e45e825c156168766d8442dde and OpenSSL's
9e189b9dc10786c755919e6792e923c584c918a1.
Change-Id: I51ca95ac1691870dd0c148fd967739e2d4f58824
Reviewed-on: https://go-review.googlesource.com/21152
Reviewed-by: Adam Langley <agl@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
This change adds Config.Renegotiation which controls whether a TLS
client will accept renegotiation requests from a server. This is used,
for example, by some web servers that wish to “add” a client certificate
to an HTTPS connection.
This is disabled by default because it significantly complicates the
state machine.
Originally, handshakeMutex was taken before locking either Conn.in or
Conn.out. However, if renegotiation is permitted then a handshake may
be triggered during a Read() call. If Conn.in were unlocked before
taking handshakeMutex then a concurrent Read() call could see an
intermediate state and trigger an error. Thus handshakeMutex is now
locked after Conn.in and the handshake functions assume that Conn.in is
locked for the duration of the handshake.
Additionally, handshakeMutex used to protect Conn.out also. With the
possibility of renegotiation that's no longer viable and so
writeRecordLocked has been split off.
Fixes#5742.
Change-Id: I935914db1f185d507ff39bba8274c148d756a1c8
Reviewed-on: https://go-review.googlesource.com/22475
Run-TryBot: Adam Langley <agl@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Russ Cox <rsc@golang.org>
cmd and runtime were handled separately, and I'm intentionally skipped
syscall. This is the rest of the standard library.
CL generated mechanically with github.com/mdempsky/unconvert.
Change-Id: I9e0eff886974dedc37adb93f602064b83e469122
Reviewed-on: https://go-review.googlesource.com/22104
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Error strings in this package were all over the place: some were
prefixed with “tls:”, some with “crypto/tls:” and some didn't have a
prefix.
This change makes everything use the prefix “tls:”.
Change-Id: Ie8b073c897764b691140412ecd6613da8c4e33a2
Reviewed-on: https://go-review.googlesource.com/21893
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
Standardize on space between "RFC" and number. Additionally change
the couple "a RFC" instances to "an RFC."
Fixes#15258
Change-Id: I2b17ecd06be07dfbb4207c690f52a59ea9b04808
Reviewed-on: https://go-review.googlesource.com/21902
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Per RFC 5246, 7.4.1.3:
cipher_suite
The single cipher suite selected by the server from the list in
ClientHello.cipher_suites. For resumed sessions, this field is
the value from the state of the session being resumed.
The specifications are not very clearly written about resuming sessions
at the wrong version (i.e. is the TLS 1.0 notion of "session" the same
type as the TLS 1.1 notion of "session"?). But every other
implementation enforces this check and not doing so has some odd
semantics.
Change-Id: I6234708bd02b636c25139d83b0d35381167e5cad
Reviewed-on: https://go-review.googlesource.com/21153
Reviewed-by: Adam Langley <agl@golang.org>
This change removes a lot of dead code. Some of the code has never been
used, not even when it was first commited. The rest shouldn't have
survived refactors.
This change doesn't remove unused routines helpful for debugging, nor
does it remove code that's used in commented out blocks of code that are
only unused temporarily. Furthermore, unused constants weren't removed
when they were part of a set of constants from specifications.
One noteworthy omission from this CL are about 1000 lines of unused code
in cmd/fix, 700 lines of which are the typechecker, which hasn't been
used ever since the pre-Go 1 fixes have been removed. I wasn't sure if
this code should stick around for future uses of cmd/fix or be culled as
well.
Change-Id: Ib714bc7e487edc11ad23ba1c3222d1fd02e4a549
Reviewed-on: https://go-review.googlesource.com/20926
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Currently, if a client of crypto/tls (e.g., net/http, http2) calls
tls.Conn.Write with a 33KB buffer, that ends up writing three TLS
records: 16KB, 16KB, and 1KB. Slow clients (such as 2G phones) must
download the first 16KB record before they can decrypt the first byte.
To improve latency, it's better to send smaller TLS records. However,
sending smaller records adds overhead (more overhead bytes and more
crypto calls), which slightly hurts throughput.
A simple heuristic, implemented in this change, is to send small
records for new connections, then boost to large records after the
first 1MB has been written on the connection.
Fixes#14376
Change-Id: Ice0f6279325be6775aa55351809f88e07dd700cd
Reviewed-on: https://go-review.googlesource.com/19591
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Tom Bergan <tombergan@google.com>
Reviewed-by: Adam Langley <agl@golang.org>
This change improves the error message when encountering a TLS handshake
message that is larger than our limit (64KB). Previously the error was
just “local error: internal error”.
Updates #13401.
Change-Id: I86127112045ae33e51079e3bc047dd7386ddc71a
Reviewed-on: https://go-review.googlesource.com/20547
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Adam Langley <agl@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Don't do a substring search to test for a timeout error.
Fixes#14722 (maybe)
Change-Id: I4e18c749d6fd92c084a1b0b83a805119e1ae5ff2
Reviewed-on: https://go-review.googlesource.com/20403
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
Reviewed-by: Keith Randall <khr@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
This promotes a connection hang during TLS handshake to a proper error.
This doesn't fully address #14539 because the error reported in that
case is a write-on-socket-not-connected error, which implies that an
earlier error during connection setup is not being checked, but it is
an improvement over the current behaviour.
Updates #14539.
Change-Id: I0571a752d32d5303db48149ab448226868b19495
Reviewed-on: https://go-review.googlesource.com/19990
Reviewed-by: Adam Langley <agl@golang.org>
The tree's pretty inconsistent about single space vs double space
after a period in documentation. Make it consistently a single space,
per earlier decisions. This means contributors won't be confused by
misleading precedence.
This CL doesn't use go/doc to parse. It only addresses // comments.
It was generated with:
$ perl -i -npe 's,^(\s*// .+[a-z]\.) +([A-Z]),$1 $2,' $(git grep -l -E '^\s*//(.+\.) +([A-Z])')
$ go test go/doc -update
Change-Id: Iccdb99c37c797ef1f804a94b22ba5ee4b500c4f7
Reviewed-on: https://go-review.googlesource.com/20022
Reviewed-by: Rob Pike <r@golang.org>
Reviewed-by: Dave Day <djd@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Named returned values should only be used on public funcs and methods
when it contributes to the documentation.
Named return values should not be used if they're only saving the
programmer a few lines of code inside the body of the function,
especially if that means there's stutter in the documentation or it
was only there so the programmer could use a naked return
statement. (Naked returns should not be used except in very small
functions)
This change is a manual audit & cleanup of public func signatures.
Signatures were not changed if:
* the func was private (wouldn't be in public godoc)
* the documentation referenced it
* the named return value was an interesting name. (i.e. it wasn't
simply stutter, repeating the name of the type)
There should be no changes in behavior. (At least: none intended)
Change-Id: I3472ef49619678fe786e5e0994bdf2d9de76d109
Reviewed-on: https://go-review.googlesource.com/20024
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Andrew Gerrand <adg@golang.org>
This is minor cleanup that reduces test output noise.
Change-Id: Ib6db4daf8cb67b7784b2d5b222fa37c7f78a6a04
Reviewed-on: https://go-review.googlesource.com/19997
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
This is minor cleanup that makes the tests more readable.
Change-Id: I9f1f98f0f035096c284bdf3501e7520517a3e4d9
Reviewed-on: https://go-review.googlesource.com/19993
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
This is a followup change to #13111 for filtering out IPv6 literals and
absolute FQDNs from being as the SNI values.
Updates #13111.
Fixes#14404.
Change-Id: I09ab8d2a9153d9a92147e57ca141f2e97ddcef6e
Reviewed-on: https://go-review.googlesource.com/19704
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
A comment existed referencing RC4 coming before AES because of it's
vulnerability to the Lucky 13 attack. This clarifies that the Lucky 13 attack
only effects AES-CBC, and not AES-GCM.
Fixes#14474
Change-Id: Idcb07b5e0cdb0f9257cf75abea60129ba495b5f5
Reviewed-on: https://go-review.googlesource.com/19845
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Conn.Close sends an encrypted "close notify" to signal secure EOF.
But writing that involves acquiring mutexes (handshake mutex + the
c.out mutex) and writing to the network. But if the reason we're
calling Conn.Close is because the network is already being
problematic, then Close might block, waiting for one of those mutexes.
Instead of blocking, and instead of introducing new API (at least for
now), distinguish between a normal Close (one that sends a secure EOF)
and a resource-releasing destructor-style Close based on whether there
are existing Write calls in-flight.
Because io.Writer and io.Closer aren't defined with respect to
concurrent usage, a Close with active Writes is already undefined, and
should only be used during teardown after failures (e.g. deadlines or
cancelations by HTTP users). A normal user will do a Write then
serially do a Close, and things are unchanged for that case.
This should fix the leaked goroutines and hung net/http.Transport
requests when there are network errors while making TLS requests.
Change-Id: If3f8c69d6fdcebf8c70227f41ad042ccc3f20ac9
Reviewed-on: https://go-review.googlesource.com/18572
Reviewed-by: Adam Langley <agl@golang.org>
Reviewed-by: Russ Cox <rsc@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
During the TLS handshake, check the cipher suite the server selects is
one of those offered in the ClientHello. The code was checking it was
in the larger list that was sometimes whittled down for the ClientHello.
Fixes#13174
Change-Id: Iad8eebbcfa5027f30403b9700c43cfa949e135bb
Reviewed-on: https://go-review.googlesource.com/16698
Reviewed-by: Adam Langley <agl@golang.org>
Run-TryBot: Adam Langley <agl@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Russ Cox <rsc@golang.org>
The user can inspect the record data to detect that the other side is
not using the TLS protocol.
This will be used by the net/http client (in a follow-on CL) to detect
when an HTTPS client is speaking to an HTTP server.
Updates #11111.
Change-Id: I872f78717aa8e8e98cebd8075436209a52039a73
Reviewed-on: https://go-review.googlesource.com/16078
Reviewed-by: Adam Langley <agl@golang.org>
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
In keysFromMasterSecret(), don't copy from serverRandom into
seed[:len(clientRandom)]. Actually, switch from an array to a slice in
keysFromMasterSecret() and masterFromPreMasterSecret() so the length
need not be given; that's how it's done elsewhere in the file.
Fixes#13181
Change-Id: I92abaa892d1bba80c2d4f12776341cda7d538837
Reviewed-on: https://go-review.googlesource.com/16697
Run-TryBot: Adam Langley <agl@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Adam Langley <agl@golang.org>
(This relands commit a4dcc692011bf1ceca9b1a363fd83f3e59e399ee.)
https://tools.ietf.org/html/rfc6066#section-3 states:
“Literal IPv4 and IPv6 addresses are not permitted in "HostName".”
However, if an IP literal was set as Config.ServerName (which could
happen as easily as calling Dial with an IP address) then the code would
send the IP literal as the SNI value.
This change filters out IP literals, as recognised by net.ParseIP, from
being sent as the SNI value.
Fixes#13111.
Change-Id: I6e544a78a01388f8fe98150589d073b917087f75
Reviewed-on: https://go-review.googlesource.com/16776
Run-TryBot: Adam Langley <agl@golang.org>
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Reviewed-by: Russ Cox <rsc@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
https://tools.ietf.org/html/rfc6066#section-3 states:
“Literal IPv4 and IPv6 addresses are not permitted in "HostName".”
However, if an IP literal was set as Config.ServerName (which could
happen as easily as calling Dial with an IP address) then the code would
send the IP literal as the SNI value.
This change filters out IP literals, as recognised by net.ParseIP, from
being sent as the SNI value.
Fixes#13111.
Change-Id: Ie9ec7acc767ae172b48c9c6dd8d84fa27b1cf0de
Reviewed-on: https://go-review.googlesource.com/16742
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Adam Langley <agl@golang.org>
This change causes the types of skipped PEM blocks to be recorded when
no certificate or private-key data is found in a PEM input. This allows
for better error messages to be return in the case of common errors like
switching the certifiate and key inputs to X509KeyPair.
Fixes#11092
Change-Id: Ifc155a811cdcddd93b5787fe16a84c972011f2f7
Reviewed-on: https://go-review.googlesource.com/14054
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
https://tools.ietf.org/html/rfc7301#section-3.1 specifies that a
ProtocolName may not be empty. This change enforces this for ServerHello
messages—it's already enforced for ClientHello messages.
Change-Id: Ic5a5be6bebf07fba90a3cabd10b07ab7b4337f53
Reviewed-on: https://go-review.googlesource.com/12003
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
In Go 1.5, Config.Certificates is no longer required if
Config.GetCertificate has been set. This change updated four comments to
reflect that.
Change-Id: Id72cc22fc79e931b2d645a7c3960c3241042762c
Reviewed-on: https://go-review.googlesource.com/13800
Reviewed-by: Adam Langley <agl@golang.org>
Go 1.5 allowed TLS connections where Config.Certificates was nil as long
as the GetCertificate callback was given. However, tls.Listen wasn't
updated accordingly until this change.
Change-Id: I5f67f323f63c988ff79642f3daf8a6b2a153e6b2
Reviewed-on: https://go-review.googlesource.com/13801
Reviewed-by: Adam Langley <agl@golang.org>
Could go in 1.5, although not critical.
See also #12107
Change-Id: I7f1608b58581d21df4db58f0db654fef79e33a90
Reviewed-on: https://go-review.googlesource.com/13481
Reviewed-by: Dave Cheney <dave@cheney.net>
Strengthening VerifyHostname exposed the fact that for resumed
connections, ConnectionState().VerifiedChains was not being saved
and restored during the ClientSessionCache operations.
Do that.
This change just saves the verified chains in the client's session
cache. It does not re-verify the certificates when resuming a
connection.
There are arguments both ways about this: we want fast, light-weight
resumption connections (thus suggesting that we shouldn't verify) but
it could also be a little surprising that, if the verification config
is changed, that would be ignored if the same session cache is used.
On the server side we do re-verify client-auth certificates, but the
situation is a little different there. The client session cache is an
object in memory that's reset each time the process restarts. But the
server's session cache is a conceptual object, held by the clients, so
can persist across server restarts. Thus the chance of a change in
verification config being surprisingly ignored is much higher in the
server case.
Fixes#12024.
Change-Id: I3081029623322ce3d9f4f3819659fdd9a381db16
Reviewed-on: https://go-review.googlesource.com/13164
Reviewed-by: Russ Cox <rsc@golang.org>
Run-TryBot: Russ Cox <rsc@golang.org>
Reviewed-by: Adam Langley <agl@golang.org>
This change alters the certificate used in many tests so that it's no
longer self-signed. This allows some tests to exercise the standard
certificate verification paths in the future.
Change-Id: I9c3fcd6847eed8269ff3b86d9b6966406bf0642d
Reviewed-on: https://go-review.googlesource.com/13244
Reviewed-by: Russ Cox <rsc@golang.org>
Run-TryBot: Adam Langley <agl@golang.org>
Reviewed-by: Adam Langley <agl@golang.org>
The one in misc/makerelease/makerelease.go is particularly bad and
probably warrants rotating our keys.
I didn't update old weekly notes, and reverted some changes involving
test code for now, since we're late in the Go 1.5 freeze. Otherwise,
the rest are all auto-generated changes, and all manually reviewed.
Change-Id: Ia2753576ab5d64826a167d259f48a2f50508792d
Reviewed-on: https://go-review.googlesource.com/12048
Reviewed-by: Rob Pike <r@golang.org>
The previous code had a brain fart: it took one of the length prefixes
as an element count, not a length. This didn't actually affect anything
because the loop stops as soon as it finds a hostname element, and the
hostname element is always the first and only element. (No other element
types have ever been defined.)
This change fixes the parsing in case SNI is ever changed in the future.
Fixes#10793.
Change-Id: Iafdf3381942bc22b1f33595315c53dc6cc2e9f0f
Reviewed-on: https://go-review.googlesource.com/11059
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
These were found by grepping the comments from the go code and feeding
the output to aspell.
Change-Id: Id734d6c8d1938ec3c36bd94a4dbbad577e3ad395
Reviewed-on: https://go-review.googlesource.com/10941
Reviewed-by: Aamir Khan <syst3m.w0rm@gmail.com>
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>