mirror of
https://github.com/tailscale/tailscale.git
synced 2024-11-29 04:55:31 +00:00
wgengine: use a singleflight.Group to reduce status contention (#5450)
Updates tailscale/coral#72 Signed-off-by: Andrew Dunham <andrew@tailscale.com> Signed-off-by: Andrew Dunham <andrew@tailscale.com>
This commit is contained in:
parent
70f9fc8c7a
commit
e8f09d24c7
@ -157,12 +157,21 @@ func (e *userspaceEngine) onOpenTimeout(flow flowtrack.Tuple) {
|
||||
return
|
||||
}
|
||||
|
||||
// We don't care if this information is perfectly up-to-date, since
|
||||
// we're just using it to print debug information.
|
||||
//
|
||||
// In tailscale/coral#72, we see a goroutine profile with thousands of
|
||||
// goroutines blocked on the mutex in getStatus here, so we wrap it in
|
||||
// a singleflight and accept stale information to reduce contention.
|
||||
st, err, _ := e.getStatusSf.Do(struct{}{}, e.getStatus)
|
||||
|
||||
var ps *ipnstate.PeerStatusLite
|
||||
if st, err := e.getStatus(); err == nil {
|
||||
if err == nil {
|
||||
for _, v := range st.Peers {
|
||||
if v.NodeKey == n.Key {
|
||||
v := v // copy
|
||||
ps = &v
|
||||
break
|
||||
}
|
||||
}
|
||||
} else {
|
||||
|
@ -46,6 +46,7 @@
|
||||
"tailscale.com/util/clientmetric"
|
||||
"tailscale.com/util/deephash"
|
||||
"tailscale.com/util/mak"
|
||||
"tailscale.com/util/singleflight"
|
||||
"tailscale.com/version"
|
||||
"tailscale.com/wgengine/filter"
|
||||
"tailscale.com/wgengine/magicsock"
|
||||
@ -146,6 +147,10 @@ type userspaceEngine struct {
|
||||
// value of the ICMP identifer and sequence number concatenated.
|
||||
icmpEchoResponseCallback map[uint32]func()
|
||||
|
||||
// this singleflight is used to deduplicate calls to getStatus when we
|
||||
// don't care if the data is perfectly fresh
|
||||
getStatusSf singleflight.Group[struct{}, *Status]
|
||||
|
||||
// Lock ordering: magicsock.Conn.mu, wgLock, then mu.
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user