1
0
mirror of https://github.com/golang/go synced 2024-11-26 23:11:24 -07:00

time: make time.Since a few nanoseconds faster

time.Since(base) is an idiom that can be used to read the system
monotonic time as efficiently as possible, when that matters.
The current code structure adds a few nanoseconds on top of
the 15-20ns the time read already takes. Remove those few.

After this CL, there is no reason at all for anyone to
//go:linkname runtime.nanotime1 instead.

Came up while investigating #61765.

Change-Id: Ic9e688af039babfc2a5a8e67dcbb02847a5eb686
Reviewed-on: https://go-review.googlesource.com/c/go/+/518336
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Damien Neil <dneil@google.com>
Run-TryBot: Russ Cox <rsc@golang.org>
Reviewed-by: Joseph Tsai <joetsai@digital-static.net>
This commit is contained in:
Russ Cox 2023-08-10 11:56:53 -04:00
parent 8870b8d281
commit 4467839602

View File

@ -891,16 +891,7 @@ func (t Time) Add(d Duration) Time {
// To compute t-d for a duration d, use t.Add(-d).
func (t Time) Sub(u Time) Duration {
if t.wall&u.wall&hasMonotonic != 0 {
te := t.ext
ue := u.ext
d := Duration(te - ue)
if d < 0 && te > ue {
return maxDuration // t - u is positive out of range
}
if d > 0 && te < ue {
return minDuration // t - u is negative out of range
}
return d
return subMono(t.ext, u.ext)
}
d := Duration(t.sec()-u.sec())*Second + Duration(t.nsec()-u.nsec())
// Check for overflow or underflow.
@ -914,17 +905,25 @@ func (t Time) Sub(u Time) Duration {
}
}
func subMono(t, u int64) Duration {
d := Duration(t - u)
if d < 0 && t > u {
return maxDuration // t - u is positive out of range
}
if d > 0 && t < u {
return minDuration // t - u is negative out of range
}
return d
}
// Since returns the time elapsed since t.
// It is shorthand for time.Now().Sub(t).
func Since(t Time) Duration {
var now Time
if t.wall&hasMonotonic != 0 {
// Common case optimization: if t has monotonic time, then Sub will use only it.
now = Time{hasMonotonic, runtimeNano() - startNano, nil}
} else {
now = Now()
return subMono(runtimeNano()-startNano, t.ext)
}
return now.Sub(t)
return Now().Sub(t)
}
// Until returns the duration until t.