mirror of
https://github.com/XTLS/REALITY.git
synced 2025-08-22 14:38:35 +00:00
Uses the new weak package to replace the existing custom intern cache with a map of weak.Pointers instead. This simplifies the cache, and means we don't need to store a slice of handles on the Conn anymore. Change-Id: I5c2bf6ef35fac4255e140e184f4e48574b34174c Reviewed-on: https://go-review.googlesource.com/c/go/+/644176 TryBot-Bypass: Roland Shoemaker <roland@golang.org> Reviewed-by: Michael Knyszek <mknyszek@google.com> Auto-Submit: Roland Shoemaker <roland@golang.org>
44 lines
1.3 KiB
Go
44 lines
1.3 KiB
Go
// Copyright 2022 The Go Authors. All rights reserved.
|
|
// Use of this source code is governed by a BSD-style
|
|
// license that can be found in the LICENSE-Go file.
|
|
|
|
package reality
|
|
|
|
import (
|
|
"crypto/x509"
|
|
"runtime"
|
|
"sync"
|
|
"weak"
|
|
)
|
|
|
|
// weakCertCache provides a cache of *x509.Certificates, allowing multiple
|
|
// connections to reuse parsed certificates, instead of re-parsing the
|
|
// certificate for every connection, which is an expensive operation.
|
|
type weakCertCache struct{ sync.Map }
|
|
|
|
func (wcc *weakCertCache) newCert(der []byte) (*x509.Certificate, error) {
|
|
if entry, ok := wcc.Load(string(der)); ok {
|
|
if v := entry.(weak.Pointer[x509.Certificate]).Value(); v != nil {
|
|
return v, nil
|
|
}
|
|
}
|
|
|
|
cert, err := x509.ParseCertificate(der)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
wp := weak.Make(cert)
|
|
if entry, loaded := wcc.LoadOrStore(string(der), wp); !loaded {
|
|
runtime.AddCleanup(cert, func(_ any) { wcc.CompareAndDelete(string(der), entry) }, any(string(der)))
|
|
} else if v := entry.(weak.Pointer[x509.Certificate]).Value(); v != nil {
|
|
return v, nil
|
|
} else {
|
|
if wcc.CompareAndSwap(string(der), entry, wp) {
|
|
runtime.AddCleanup(cert, func(_ any) { wcc.CompareAndDelete(string(der), wp) }, any(string(der)))
|
|
}
|
|
}
|
|
return cert, nil
|
|
}
|
|
|
|
var globalCertCache = new(weakCertCache) |