crypto/tls: use hash.Cloner

A hash object needs to be cloned when doing certain steps in a
TLS 1.3 server handshake. It is more efficient to use the
hash.Cloner interface to clone a hash than to encode and decode
the hash object using the binary encoding interfaces.

We still need to support the binary encoding path in case the
hash objects come from the fips140 v1.0.0 module, given that
this module doesn't support the hash.Cloner interface.

Change-Id: I8425e14e481dcefafc9aa1e5bfd63b61c22675ad
Reviewed-on: https://go-review.googlesource.com/c/go/+/682597
Reviewed-by: Damien Neil <dneil@google.com>
Reviewed-by: Roland Shoemaker <roland@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
This commit is contained in:
qmuntal 2025-06-20 14:28:56 +02:00 committed by Quim Muntal
parent 13bb48e6fb
commit 53515fb0a9

View file

@ -468,10 +468,17 @@ func (hs *serverHandshakeStateTLS13) checkForResumption() error {
return nil
}
// cloneHash uses the encoding.BinaryMarshaler and encoding.BinaryUnmarshaler
// cloneHash uses [hash.Cloner] to clone in. If [hash.Cloner]
// is not implemented or not supported, then it falls back to the
// [encoding.BinaryMarshaler] and [encoding.BinaryUnmarshaler]
// interfaces implemented by standard library hashes to clone the state of in
// to a new instance of h. It returns nil if the operation fails.
func cloneHash(in hash.Hash, h crypto.Hash) hash.Hash {
if cloner, ok := in.(hash.Cloner); ok {
if out, err := cloner.Clone(); err == nil {
return out
}
}
// Recreate the interface to avoid importing encoding.
type binaryMarshaler interface {
MarshalBinary() (data []byte, err error)