github.com/nicocha30/gvisor-ligolo@v0.0.0-20230726075806-989fa2c0a413/pkg/sentry/kernel/time/time.go (about)

     1  // Copyright 2018 The gVisor Authors.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  // Package time defines the Timer type, which provides a periodic timer that
    16  // works by sampling a user-provided clock.
    17  package time
    18  
    19  import (
    20  	"fmt"
    21  	"math"
    22  	"time"
    23  
    24  	"github.com/nicocha30/gvisor-ligolo/pkg/abi/linux"
    25  	"github.com/nicocha30/gvisor-ligolo/pkg/errors/linuxerr"
    26  	"github.com/nicocha30/gvisor-ligolo/pkg/sync"
    27  	"github.com/nicocha30/gvisor-ligolo/pkg/waiter"
    28  )
    29  
    30  // Events that may be generated by a Clock.
    31  const (
    32  	// ClockEventSet occurs when a Clock undergoes a discontinuous change.
    33  	ClockEventSet waiter.EventMask = 1 << iota
    34  
    35  	// ClockEventRateIncrease occurs when the rate at which a Clock advances
    36  	// increases significantly, such that values returned by previous calls to
    37  	// Clock.WallTimeUntil may be too large.
    38  	ClockEventRateIncrease
    39  )
    40  
    41  // Time represents an instant in time with nanosecond precision.
    42  //
    43  // Time may represent time with respect to any clock and may not have any
    44  // meaning in the real world.
    45  //
    46  // +stateify savable
    47  type Time struct {
    48  	ns int64
    49  }
    50  
    51  var (
    52  	// MinTime is the zero time instant, the lowest possible time that can
    53  	// be represented by Time.
    54  	MinTime = Time{ns: math.MinInt64}
    55  
    56  	// MaxTime is the highest possible time that can be represented by
    57  	// Time.
    58  	MaxTime = Time{ns: math.MaxInt64}
    59  
    60  	// ZeroTime represents the zero time in an unspecified Clock's domain.
    61  	ZeroTime = Time{ns: 0}
    62  )
    63  
    64  const (
    65  	// MinDuration is the minimum duration representable by time.Duration.
    66  	MinDuration = time.Duration(math.MinInt64)
    67  
    68  	// MaxDuration is the maximum duration representable by time.Duration.
    69  	MaxDuration = time.Duration(math.MaxInt64)
    70  )
    71  
    72  // FromNanoseconds returns a Time representing the point ns nanoseconds after
    73  // an unspecified Clock's zero time.
    74  func FromNanoseconds(ns int64) Time {
    75  	return Time{ns}
    76  }
    77  
    78  // FromSeconds returns a Time representing the point s seconds after an
    79  // unspecified Clock's zero time.
    80  func FromSeconds(s int64) Time {
    81  	if s > math.MaxInt64/time.Second.Nanoseconds() {
    82  		return MaxTime
    83  	}
    84  	return Time{s * 1e9}
    85  }
    86  
    87  // FromUnix converts from Unix seconds and nanoseconds to Time, assuming a real
    88  // time Unix clock domain.
    89  func FromUnix(s int64, ns int64) Time {
    90  	if s > math.MaxInt64/time.Second.Nanoseconds() {
    91  		return MaxTime
    92  	}
    93  	t := s * 1e9
    94  	if t > math.MaxInt64-ns {
    95  		return MaxTime
    96  	}
    97  	return Time{t + ns}
    98  }
    99  
   100  // FromTimespec converts from Linux Timespec to Time.
   101  func FromTimespec(ts linux.Timespec) Time {
   102  	return Time{ts.ToNsecCapped()}
   103  }
   104  
   105  // FromTimeval converts a Linux Timeval to Time.
   106  func FromTimeval(tv linux.Timeval) Time {
   107  	return Time{tv.ToNsecCapped()}
   108  }
   109  
   110  // Nanoseconds returns nanoseconds elapsed since the zero time in t's Clock
   111  // domain. If t represents walltime, this is nanoseconds since the Unix epoch.
   112  func (t Time) Nanoseconds() int64 {
   113  	return t.ns
   114  }
   115  
   116  // Microseconds returns microseconds elapsed since the zero time in t's Clock
   117  // domain. If t represents walltime, this is microseconds since the Unix epoch.
   118  func (t Time) Microseconds() int64 {
   119  	return t.ns / 1000
   120  }
   121  
   122  // Seconds returns seconds elapsed since the zero time in t's Clock domain. If
   123  // t represents walltime, this is seconds since Unix epoch.
   124  func (t Time) Seconds() int64 {
   125  	return t.Nanoseconds() / time.Second.Nanoseconds()
   126  }
   127  
   128  // Timespec converts Time to a Linux timespec.
   129  func (t Time) Timespec() linux.Timespec {
   130  	return linux.NsecToTimespec(t.Nanoseconds())
   131  }
   132  
   133  // Unix returns the (seconds, nanoseconds) representation of t such that
   134  // seconds*1e9 + nanoseconds = t.
   135  func (t Time) Unix() (s int64, ns int64) {
   136  	s = t.ns / 1e9
   137  	ns = t.ns % 1e9
   138  	return
   139  }
   140  
   141  // TimeT converts Time to a Linux time_t.
   142  func (t Time) TimeT() linux.TimeT {
   143  	return linux.NsecToTimeT(t.Nanoseconds())
   144  }
   145  
   146  // Timeval converts Time to a Linux timeval.
   147  func (t Time) Timeval() linux.Timeval {
   148  	return linux.NsecToTimeval(t.Nanoseconds())
   149  }
   150  
   151  // StatxTimestamp converts Time to a Linux statx_timestamp.
   152  func (t Time) StatxTimestamp() linux.StatxTimestamp {
   153  	return linux.NsecToStatxTimestamp(t.Nanoseconds())
   154  }
   155  
   156  // Add adds the duration of d to t.
   157  func (t Time) Add(d time.Duration) Time {
   158  	if t.ns > 0 && d.Nanoseconds() > math.MaxInt64-int64(t.ns) {
   159  		return MaxTime
   160  	}
   161  	if t.ns < 0 && d.Nanoseconds() < math.MinInt64-int64(t.ns) {
   162  		return MinTime
   163  	}
   164  	return Time{int64(t.ns) + d.Nanoseconds()}
   165  }
   166  
   167  // AddTime adds the duration of u to t.
   168  func (t Time) AddTime(u Time) Time {
   169  	return t.Add(time.Duration(u.ns))
   170  }
   171  
   172  // Equal reports whether the two times represent the same instant in time.
   173  func (t Time) Equal(u Time) bool {
   174  	return t.ns == u.ns
   175  }
   176  
   177  // Before reports whether the instant t is before the instant u.
   178  func (t Time) Before(u Time) bool {
   179  	return t.ns < u.ns
   180  }
   181  
   182  // After reports whether the instant t is after the instant u.
   183  func (t Time) After(u Time) bool {
   184  	return t.ns > u.ns
   185  }
   186  
   187  // Sub returns the duration of t - u.
   188  //
   189  // N.B. This measure may not make sense for every Time returned by ktime.Clock.
   190  // Callers who need wall time duration can use ktime.Clock.WallTimeUntil to
   191  // estimate that wall time.
   192  func (t Time) Sub(u Time) time.Duration {
   193  	dur := time.Duration(int64(t.ns)-int64(u.ns)) * time.Nanosecond
   194  	switch {
   195  	case u.Add(dur).Equal(t):
   196  		return dur
   197  	case t.Before(u):
   198  		return MinDuration
   199  	default:
   200  		return MaxDuration
   201  	}
   202  }
   203  
   204  // IsMin returns whether t represents the lowest possible time instant.
   205  func (t Time) IsMin() bool {
   206  	return t == MinTime
   207  }
   208  
   209  // IsZero returns whether t represents the zero time instant in t's Clock domain.
   210  func (t Time) IsZero() bool {
   211  	return t == ZeroTime
   212  }
   213  
   214  // String returns the time represented in nanoseconds as a string.
   215  func (t Time) String() string {
   216  	return fmt.Sprintf("%dns", t.Nanoseconds())
   217  }
   218  
   219  // A Clock is an abstract time source.
   220  type Clock interface {
   221  	// Now returns the current time in nanoseconds according to the Clock.
   222  	Now() Time
   223  
   224  	// WallTimeUntil returns the estimated wall time until Now will return a
   225  	// value greater than or equal to t, given that a recent call to Now
   226  	// returned now. If t has already passed, WallTimeUntil may return 0 or a
   227  	// negative value.
   228  	//
   229  	// WallTimeUntil must be abstract to support Clocks that do not represent
   230  	// wall time (e.g. thread group execution timers). Clocks that represent
   231  	// wall times may embed the WallRateClock type to obtain an appropriate
   232  	// trivial implementation of WallTimeUntil.
   233  	//
   234  	// WallTimeUntil is used to determine when associated Timers should next
   235  	// check for expirations. Returning too small a value may result in
   236  	// spurious Timer goroutine wakeups, while returning too large a value may
   237  	// result in late expirations. Implementations should usually err on the
   238  	// side of underestimating.
   239  	WallTimeUntil(t, now Time) time.Duration
   240  
   241  	// Waitable methods may be used to subscribe to Clock events. Waiters will
   242  	// not be preserved by Save and must be re-established during restore.
   243  	//
   244  	// Since Clock events are transient, implementations of
   245  	// waiter.Waitable.Readiness should return 0.
   246  	waiter.Waitable
   247  }
   248  
   249  // WallRateClock implements Clock.WallTimeUntil for Clocks that elapse at the
   250  // same rate as wall time.
   251  type WallRateClock struct{}
   252  
   253  // WallTimeUntil implements Clock.WallTimeUntil.
   254  func (*WallRateClock) WallTimeUntil(t, now Time) time.Duration {
   255  	return t.Sub(now)
   256  }
   257  
   258  // NoClockEvents implements waiter.Waitable for Clocks that do not generate
   259  // events.
   260  type NoClockEvents struct{}
   261  
   262  // Readiness implements waiter.Waitable.Readiness.
   263  func (*NoClockEvents) Readiness(mask waiter.EventMask) waiter.EventMask {
   264  	return 0
   265  }
   266  
   267  // EventRegister implements waiter.Waitable.EventRegister.
   268  func (*NoClockEvents) EventRegister(e *waiter.Entry) error {
   269  	return nil
   270  }
   271  
   272  // EventUnregister implements waiter.Waitable.EventUnregister.
   273  func (*NoClockEvents) EventUnregister(e *waiter.Entry) {
   274  }
   275  
   276  // ClockEventsQueue implements waiter.Waitable by wrapping waiter.Queue and
   277  // defining waiter.Waitable.Readiness as required by Clock.
   278  type ClockEventsQueue struct {
   279  	waiter.Queue
   280  }
   281  
   282  // EventRegister implements waiter.Waitable.
   283  func (c *ClockEventsQueue) EventRegister(e *waiter.Entry) error {
   284  	c.Queue.EventRegister(e)
   285  	return nil
   286  }
   287  
   288  // Readiness implements waiter.Waitable.Readiness.
   289  func (*ClockEventsQueue) Readiness(mask waiter.EventMask) waiter.EventMask {
   290  	return 0
   291  }
   292  
   293  // Listener receives expirations from a Timer.
   294  type Listener interface {
   295  	// NotifyTimer is called when its associated Timer expires. exp is the number
   296  	// of expirations. setting is the next timer Setting.
   297  	//
   298  	// Notify is called with the associated Timer's mutex locked, so Notify
   299  	// must not take any locks that precede Timer.mu in lock order.
   300  	//
   301  	// If Notify returns true, the timer will use the returned setting
   302  	// rather than the passed one.
   303  	//
   304  	// Preconditions: exp > 0.
   305  	NotifyTimer(exp uint64, setting Setting) (newSetting Setting, update bool)
   306  }
   307  
   308  // Setting contains user-controlled mutable Timer properties.
   309  //
   310  // +stateify savable
   311  type Setting struct {
   312  	// Enabled is true if the timer is running.
   313  	Enabled bool
   314  
   315  	// Next is the time in nanoseconds of the next expiration.
   316  	Next Time
   317  
   318  	// Period is the time in nanoseconds between expirations. If Period is
   319  	// zero, the timer will not automatically restart after expiring.
   320  	//
   321  	// Invariant: Period >= 0.
   322  	Period time.Duration
   323  }
   324  
   325  // SettingFromSpec converts a (value, interval) pair to a Setting based on a
   326  // reading from c. value is interpreted as a time relative to c.Now().
   327  func SettingFromSpec(value time.Duration, interval time.Duration, c Clock) (Setting, error) {
   328  	return SettingFromSpecAt(value, interval, c.Now())
   329  }
   330  
   331  // SettingFromSpecAt converts a (value, interval) pair to a Setting. value is
   332  // interpreted as a time relative to now.
   333  func SettingFromSpecAt(value time.Duration, interval time.Duration, now Time) (Setting, error) {
   334  	if value < 0 {
   335  		return Setting{}, linuxerr.EINVAL
   336  	}
   337  	if value == 0 {
   338  		return Setting{Period: interval}, nil
   339  	}
   340  	return Setting{
   341  		Enabled: true,
   342  		Next:    now.Add(value),
   343  		Period:  interval,
   344  	}, nil
   345  }
   346  
   347  // SettingFromAbsSpec converts a (value, interval) pair to a Setting. value is
   348  // interpreted as an absolute time.
   349  func SettingFromAbsSpec(value Time, interval time.Duration) (Setting, error) {
   350  	if value.Before(ZeroTime) {
   351  		return Setting{}, linuxerr.EINVAL
   352  	}
   353  	if value.IsZero() {
   354  		return Setting{Period: interval}, nil
   355  	}
   356  	return Setting{
   357  		Enabled: true,
   358  		Next:    value,
   359  		Period:  interval,
   360  	}, nil
   361  }
   362  
   363  // SettingFromItimerspec converts a linux.Itimerspec to a Setting. If abs is
   364  // true, its.Value is interpreted as an absolute time. Otherwise, it is
   365  // interpreted as a time relative to c.Now().
   366  func SettingFromItimerspec(its linux.Itimerspec, abs bool, c Clock) (Setting, error) {
   367  	if abs {
   368  		return SettingFromAbsSpec(FromTimespec(its.Value), its.Interval.ToDuration())
   369  	}
   370  	return SettingFromSpec(its.Value.ToDuration(), its.Interval.ToDuration(), c)
   371  }
   372  
   373  // SpecFromSetting converts a timestamp and a Setting to a (relative value,
   374  // interval) pair, as used by most Linux syscalls that return a struct
   375  // itimerval or struct itimerspec.
   376  func SpecFromSetting(now Time, s Setting) (value, period time.Duration) {
   377  	if !s.Enabled {
   378  		return 0, s.Period
   379  	}
   380  	return s.Next.Sub(now), s.Period
   381  }
   382  
   383  // ItimerspecFromSetting converts a Setting to a linux.Itimerspec.
   384  func ItimerspecFromSetting(now Time, s Setting) linux.Itimerspec {
   385  	val, iv := SpecFromSetting(now, s)
   386  	return linux.Itimerspec{
   387  		Interval: linux.DurationToTimespec(iv),
   388  		Value:    linux.DurationToTimespec(val),
   389  	}
   390  }
   391  
   392  // At returns an updated Setting and a number of expirations after the
   393  // associated Clock indicates a time of now.
   394  //
   395  // Settings may be created by successive calls to At with decreasing
   396  // values of now (i.e. time may appear to go backward). Supporting this is
   397  // required to support non-monotonic clocks, as well as allowing
   398  // Timer.clock.Now() to be called without holding Timer.mu.
   399  func (s Setting) At(now Time) (Setting, uint64) {
   400  	if !s.Enabled {
   401  		return s, 0
   402  	}
   403  	if s.Next.After(now) {
   404  		return s, 0
   405  	}
   406  	if s.Period == 0 {
   407  		s.Enabled = false
   408  		return s, 1
   409  	}
   410  	exp := 1 + uint64(now.Sub(s.Next).Nanoseconds())/uint64(s.Period)
   411  	s.Next = s.Next.Add(time.Duration(uint64(s.Period) * exp))
   412  	return s, exp
   413  }
   414  
   415  // Timer is an optionally-periodic timer driven by sampling a user-specified
   416  // Clock. Timer's semantics support the requirements of Linux's interval timers
   417  // (setitimer(2), timer_create(2), timerfd_create(2)).
   418  //
   419  // Timers should be created using NewTimer and must be cleaned up by calling
   420  // Timer.Destroy when no longer used.
   421  //
   422  // +stateify savable
   423  type Timer struct {
   424  	// clock is the time source. clock is immutable.
   425  	clock Clock
   426  
   427  	// listener is notified of expirations. listener is immutable.
   428  	listener Listener
   429  
   430  	// mu protects the following mutable fields.
   431  	mu sync.Mutex `state:"nosave"`
   432  
   433  	// setting is the timer setting. setting is protected by mu.
   434  	setting Setting
   435  
   436  	// paused is true if the Timer is paused. paused is protected by mu.
   437  	paused bool
   438  
   439  	// kicker is used to wake the Timer goroutine. The kicker pointer is
   440  	// immutable, but its state is protected by mu.
   441  	kicker *time.Timer `state:"nosave"`
   442  
   443  	// entry is registered with clock.EventRegister. entry is immutable.
   444  	//
   445  	// Per comment in Clock, entry must be re-registered after restore; per
   446  	// comment in Timer.Load, this is done in Timer.Resume.
   447  	entry waiter.Entry `state:"nosave"`
   448  
   449  	// events is the channel that will be notified whenever entry receives an
   450  	// event. It is also closed by Timer.Destroy to instruct the Timer
   451  	// goroutine to exit.
   452  	events chan struct{} `state:"nosave"`
   453  }
   454  
   455  // timerTickEvents are Clock events that require the Timer goroutine to Tick
   456  // prematurely.
   457  const timerTickEvents = ClockEventSet | ClockEventRateIncrease
   458  
   459  // NewTimer returns a new Timer that will obtain time from clock and send
   460  // expirations to listener. The Timer is initially stopped and has no first
   461  // expiration or period configured.
   462  func NewTimer(clock Clock, listener Listener) *Timer {
   463  	t := &Timer{
   464  		clock:    clock,
   465  		listener: listener,
   466  	}
   467  	t.init()
   468  	return t
   469  }
   470  
   471  // init initializes Timer state that is not preserved across save/restore. If
   472  // init has already been called, calling it again is a no-op.
   473  //
   474  // Preconditions: t.mu must be locked, or the caller must have exclusive access
   475  // to t.
   476  func (t *Timer) init() {
   477  	if t.kicker != nil {
   478  		return
   479  	}
   480  	// If t.kicker is nil, the Timer goroutine can't be running, so we can't
   481  	// race with it.
   482  	t.kicker = time.NewTimer(0)
   483  	t.entry, t.events = waiter.NewChannelEntry(timerTickEvents)
   484  	if err := t.clock.EventRegister(&t.entry); err != nil {
   485  		panic(err)
   486  	}
   487  	go t.runGoroutine() // S/R-SAFE: synchronized by t.mu
   488  }
   489  
   490  // Destroy releases resources owned by the Timer. A Destroyed Timer must not be
   491  // used again; in particular, a Destroyed Timer should not be Saved.
   492  func (t *Timer) Destroy() {
   493  	// Stop the Timer, ensuring that the Timer goroutine will not call
   494  	// t.kicker.Reset, before calling t.kicker.Stop.
   495  	t.mu.Lock()
   496  	t.setting.Enabled = false
   497  	t.mu.Unlock()
   498  	t.kicker.Stop()
   499  	// Unregister t.entry, ensuring that the Clock will not send to t.events,
   500  	// before closing t.events to instruct the Timer goroutine to exit.
   501  	t.clock.EventUnregister(&t.entry)
   502  	close(t.events)
   503  }
   504  
   505  func (t *Timer) runGoroutine() {
   506  	for {
   507  		select {
   508  		case <-t.kicker.C:
   509  		case _, ok := <-t.events:
   510  			if !ok {
   511  				// Channel closed by Destroy.
   512  				return
   513  			}
   514  		}
   515  		t.Tick()
   516  	}
   517  }
   518  
   519  // Tick requests that the Timer immediately check for expirations and
   520  // re-evaluate when it should next check for expirations.
   521  func (t *Timer) Tick() {
   522  	now := t.clock.Now()
   523  	t.mu.Lock()
   524  	defer t.mu.Unlock()
   525  	if t.paused {
   526  		return
   527  	}
   528  	s, exp := t.setting.At(now)
   529  	t.setting = s
   530  	if exp > 0 {
   531  		if newS, ok := t.listener.NotifyTimer(exp, t.setting); ok {
   532  			t.setting = newS
   533  		}
   534  	}
   535  	t.resetKickerLocked(now)
   536  }
   537  
   538  // Pause pauses the Timer, ensuring that it does not generate any further
   539  // expirations until Resume is called. If the Timer is already paused, Pause
   540  // has no effect.
   541  func (t *Timer) Pause() {
   542  	t.mu.Lock()
   543  	defer t.mu.Unlock()
   544  	t.paused = true
   545  	// t.kicker may be nil if we were restored but never resumed.
   546  	if t.kicker != nil {
   547  		t.kicker.Stop()
   548  	}
   549  }
   550  
   551  // Resume ends the effect of Pause. If the Timer is not paused, Resume has no
   552  // effect.
   553  func (t *Timer) Resume() {
   554  	t.mu.Lock()
   555  	defer t.mu.Unlock()
   556  	if !t.paused {
   557  		return
   558  	}
   559  	t.paused = false
   560  
   561  	// Lazily initialize the Timer. We can't call Timer.init until Timer.Resume
   562  	// because save/restore will restore Timers before
   563  	// kernel.Timekeeper.SetClocks() has been called, so if t.clock is backed
   564  	// by a kernel.Timekeeper then the Timer goroutine will panic if it calls
   565  	// t.clock.Now().
   566  	t.init()
   567  
   568  	// Kick the Timer goroutine in case it was already initialized, but the
   569  	// Timer goroutine was sleeping.
   570  	t.kicker.Reset(0)
   571  }
   572  
   573  // Get returns a snapshot of the Timer's current Setting and the time
   574  // (according to the Timer's Clock) at which the snapshot was taken.
   575  //
   576  // Preconditions: The Timer must not be paused (since its Setting cannot
   577  // be advanced to the current time while it is paused.)
   578  func (t *Timer) Get() (Time, Setting) {
   579  	now := t.clock.Now()
   580  	t.mu.Lock()
   581  	defer t.mu.Unlock()
   582  	if t.paused {
   583  		panic(fmt.Sprintf("Timer.Get called on paused Timer %p", t))
   584  	}
   585  	s, exp := t.setting.At(now)
   586  	t.setting = s
   587  	if exp > 0 {
   588  		if newS, ok := t.listener.NotifyTimer(exp, t.setting); ok {
   589  			t.setting = newS
   590  		}
   591  	}
   592  	t.resetKickerLocked(now)
   593  	return now, s
   594  }
   595  
   596  // Swap atomically changes the Timer's Setting and returns the Timer's previous
   597  // Setting and the time (according to the Timer's Clock) at which the snapshot
   598  // was taken. Setting s.Enabled to true starts the Timer, while setting
   599  // s.Enabled to false stops it.
   600  //
   601  // Preconditions: The Timer must not be paused.
   602  func (t *Timer) Swap(s Setting) (Time, Setting) {
   603  	return t.SwapAnd(s, nil)
   604  }
   605  
   606  // SwapAnd atomically changes the Timer's Setting, calls f if it is not nil,
   607  // and returns the Timer's previous Setting and the time (according to the
   608  // Timer's Clock) at which the Setting was changed. Setting s.Enabled to true
   609  // starts the timer, while setting s.Enabled to false stops it.
   610  //
   611  // Preconditions:
   612  //   - The Timer must not be paused.
   613  //   - f cannot call any Timer methods since it is called with the Timer mutex
   614  //     locked.
   615  func (t *Timer) SwapAnd(s Setting, f func()) (Time, Setting) {
   616  	now := t.clock.Now()
   617  	t.mu.Lock()
   618  	defer t.mu.Unlock()
   619  	if t.paused {
   620  		panic(fmt.Sprintf("Timer.SwapAnd called on paused Timer %p", t))
   621  	}
   622  	oldS, oldExp := t.setting.At(now)
   623  	if oldExp > 0 {
   624  		t.listener.NotifyTimer(oldExp, oldS)
   625  		// N.B. The returned Setting doesn't matter because we're about
   626  		// to overwrite.
   627  	}
   628  	if f != nil {
   629  		f()
   630  	}
   631  	newS, newExp := s.At(now)
   632  	t.setting = newS
   633  	if newExp > 0 {
   634  		if newS, ok := t.listener.NotifyTimer(newExp, t.setting); ok {
   635  			t.setting = newS
   636  		}
   637  	}
   638  	t.resetKickerLocked(now)
   639  	return now, oldS
   640  }
   641  
   642  // Atomically invokes f atomically with respect to expirations of t; that is, t
   643  // cannot generate expirations while f is being called.
   644  //
   645  // Preconditions: f cannot call any Timer methods since it is called with the
   646  // Timer mutex locked.
   647  func (t *Timer) Atomically(f func()) {
   648  	t.mu.Lock()
   649  	defer t.mu.Unlock()
   650  	f()
   651  }
   652  
   653  // Preconditions: t.mu must be locked.
   654  func (t *Timer) resetKickerLocked(now Time) {
   655  	if t.setting.Enabled {
   656  		// Clock.WallTimeUntil may return a negative value. This is fine;
   657  		// time.when treats negative Durations as 0.
   658  		t.kicker.Reset(t.clock.WallTimeUntil(t.setting.Next, now))
   659  	}
   660  	// We don't call t.kicker.Stop if !t.setting.Enabled because in most cases
   661  	// resetKickerLocked will be called from the Timer goroutine itself, in
   662  	// which case t.kicker has already fired and t.kicker.Stop will be an
   663  	// expensive no-op (time.Timer.Stop => time.stopTimer => runtime.stopTimer
   664  	// => runtime.deltimer).
   665  }
   666  
   667  // Clock returns the Clock used by t.
   668  func (t *Timer) Clock() Clock {
   669  	return t.clock
   670  }
   671  
   672  // ChannelNotifier is a Listener that sends on a channel.
   673  //
   674  // ChannelNotifier cannot be saved or loaded.
   675  type ChannelNotifier chan struct{}
   676  
   677  // NewChannelNotifier creates a new channel notifier.
   678  //
   679  // If the notifier is used with a timer, Timer.Destroy will close the channel
   680  // returned here.
   681  func NewChannelNotifier() (Listener, <-chan struct{}) {
   682  	tchan := make(chan struct{}, 1)
   683  	return ChannelNotifier(tchan), tchan
   684  }
   685  
   686  // NotifyTimer implements Listener.NotifyTimer.
   687  func (c ChannelNotifier) NotifyTimer(uint64, Setting) (Setting, bool) {
   688  	select {
   689  	case c <- struct{}{}:
   690  	default:
   691  	}
   692  
   693  	return Setting{}, false
   694  }