1
0
mirror of https://github.com/golang/go synced 2024-11-24 02:30:12 -07:00

runtime: use timer for GC control revise rather than timeout

Currently, we use a note sleep with a timeout in a loop in func gc to
periodically revise the GC control variables. Replace this with a
fully blocking note sleep and use a periodic timer to trigger the
revise instead. This is a step toward replacing the note sleep in func
gc.

Change-Id: I2d562f6b9b2e5f0c28e9a54227e2c0f8a2603f63
Reviewed-on: https://go-review.googlesource.com/9290
Reviewed-by: Rick Hudson <rlh@golang.org>
Reviewed-by: Russ Cox <rsc@golang.org>
This commit is contained in:
Austin Clements 2015-04-22 16:35:45 -04:00
parent e870f06c3f
commit 4e32718d3e

View File

@ -298,6 +298,10 @@ type gcControllerState struct {
// at the end of of each cycle. // at the end of of each cycle.
triggerRatio float64 triggerRatio float64
// reviseTimer is a timer that triggers periodic revision of
// control variables during the cycle.
reviseTimer timer
_ [_CacheLineSize]byte _ [_CacheLineSize]byte
// fractionalMarkWorkersNeeded is the number of fractional // fractionalMarkWorkersNeeded is the number of fractional
@ -344,10 +348,6 @@ func (c *gcControllerState) startCycle() {
c.fractionalMarkWorkersNeeded = 0 c.fractionalMarkWorkersNeeded = 0
} }
// Compute initial values for controls that are updated
// throughout the cycle.
c.revise()
// Clear per-P state // Clear per-P state
for _, p := range &allp { for _, p := range &allp {
if p == nil { if p == nil {
@ -356,7 +356,17 @@ func (c *gcControllerState) startCycle() {
p.gcAssistTime = 0 p.gcAssistTime = 0
} }
return // Compute initial values for controls that are updated
// throughout the cycle.
c.revise()
// Set up a timer to revise periodically
c.reviseTimer.f = func(interface{}, uintptr) {
gcController.revise()
}
c.reviseTimer.period = 10 * 1000 * 1000
c.reviseTimer.when = nanotime() + c.reviseTimer.period
addtimer(&c.reviseTimer)
} }
// revise updates the assist ratio during the GC cycle to account for // revise updates the assist ratio during the GC cycle to account for
@ -408,6 +418,9 @@ func (c *gcControllerState) endCycle() {
// EWMA weight given to this cycle's scan work ratio. // EWMA weight given to this cycle's scan work ratio.
const workRatioWeight = 0.75 const workRatioWeight = 0.75
// Stop the revise timer
deltimer(&c.reviseTimer)
// Compute next cycle trigger ratio. First, this computes the // Compute next cycle trigger ratio. First, this computes the
// "error" for this cycle; that is, how far off the trigger // "error" for this cycle; that is, how far off the trigger
// was from what it should have been, accounting for both heap // was from what it should have been, accounting for both heap
@ -768,9 +781,7 @@ func gc(mode int) {
if debug.gctrace > 0 { if debug.gctrace > 0 {
tMark = nanotime() tMark = nanotime()
} }
for !notetsleepg(&work.bgMarkNote, 10*1000*1000) { notetsleepg(&work.bgMarkNote, -1)
gcController.revise()
}
noteclear(&work.bgMarkNote) noteclear(&work.bgMarkNote)
// Begin mark termination. // Begin mark termination.