aboutsummaryrefslogtreecommitdiff
path: root/src/runtime/netpoll.go
diff options
context:
space:
mode:
authorDmitry Vyukov <dvyukov@google.com>2018-10-31 17:03:35 +0100
committerDmitry Vyukov <dvyukov@google.com>2018-11-02 12:49:16 +0000
commita86f549703c107c8b4d83d8e7527521c9e215d9a (patch)
tree07dc006883bd7b4cf9d2b0581e11109ee28b6403 /src/runtime/netpoll.go
parent86d375498fa377c7d81c5b93750e8dce2389500e (diff)
downloadgo-a86f549703c107c8b4d83d8e7527521c9e215d9a.tar.gz
go-a86f549703c107c8b4d83d8e7527521c9e215d9a.zip
runtime: add and use modtimer in netpoll
Currently when netpoll deadline is incrementally prolonged, we delete and re-add timer each time. Add modtimer function that does both and use it when we need to modify an existing netpoll timer to avoid unnecessary lock/unlock. TCP4OneShotTimeout-6 17.2µs ± 0% 17.0µs ± 0% -0.82% (p=0.008 n=5+5) SetReadDeadline-6 274ns ± 2% 261ns ± 0% -4.89% (p=0.008 n=5+5) Update #25729 Change-Id: I08b89dbbc1785dd180e967a37b0aa23b0c4613a8 Reviewed-on: https://go-review.googlesource.com/c/146339 Reviewed-by: Ian Lance Taylor <iant@golang.org>
Diffstat (limited to 'src/runtime/netpoll.go')
-rw-r--r--src/runtime/netpoll.go46
1 files changed, 24 insertions, 22 deletions
diff --git a/src/runtime/netpoll.go b/src/runtime/netpoll.go
index 00701665f1..34e7c902eb 100644
--- a/src/runtime/netpoll.go
+++ b/src/runtime/netpoll.go
@@ -211,21 +211,13 @@ func poll_runtime_pollSetDeadline(pd *pollDesc, d int64, mode int) {
pd.wd = d
}
combo := pd.rd > 0 && pd.rd == pd.wd
- // Reset current timers if necessary.
- if pd.rt.f != nil && (pd.rd != rd0 || combo != combo0) {
- pd.rseq++ // invalidate current timers
- deltimer(&pd.rt)
- pd.rt.f = nil
- }
- if pd.wt.f != nil && (pd.wd != wd0 || combo != combo0) {
- pd.wseq++ // invalidate current timers
- deltimer(&pd.wt)
- pd.wt.f = nil
- }
- // Setup new timers.
+ rtf := netpollReadDeadline
if combo {
- if pd.rt.f == nil {
- pd.rt.f = netpollDeadline
+ rtf = netpollDeadline
+ }
+ if pd.rt.f == nil {
+ if pd.rd > 0 {
+ pd.rt.f = rtf
pd.rt.when = pd.rd
// Copy current seq into the timer arg.
// Timer func will check the seq against current descriptor seq,
@@ -234,21 +226,31 @@ func poll_runtime_pollSetDeadline(pd *pollDesc, d int64, mode int) {
pd.rt.seq = pd.rseq
addtimer(&pd.rt)
}
- } else {
- if pd.rd > 0 && pd.rt.f == nil {
- pd.rt.f = netpollReadDeadline
- pd.rt.when = pd.rd
- pd.rt.arg = pd
- pd.rt.seq = pd.rseq
- addtimer(&pd.rt)
+ } else if pd.rd != rd0 || combo != combo0 {
+ pd.rseq++ // invalidate current timers
+ if pd.rd > 0 {
+ modtimer(&pd.rt, pd.rd, 0, rtf, pd, pd.rseq)
+ } else {
+ deltimer(&pd.rt)
+ pd.rt.f = nil
}
- if pd.wd > 0 && pd.wt.f == nil {
+ }
+ if pd.wt.f == nil {
+ if pd.wd > 0 && !combo {
pd.wt.f = netpollWriteDeadline
pd.wt.when = pd.wd
pd.wt.arg = pd
pd.wt.seq = pd.wseq
addtimer(&pd.wt)
}
+ } else if pd.wd != wd0 || combo != combo0 {
+ pd.wseq++ // invalidate current timers
+ if pd.wd > 0 && !combo {
+ modtimer(&pd.wt, pd.wd, 0, netpollWriteDeadline, pd, pd.wseq)
+ } else {
+ deltimer(&pd.wt)
+ pd.wt.f = nil
+ }
}
// If we set the new deadline in the past, unblock currently pending IO if any.
var rg, wg *g