Fix bwlimit toggle in conjunction with schedules (Fixes #1607)

s3-about
cbruegg 2017-08-17 17:40:43 +02:00 committed by Nick Craig-Wood
parent e96c5b5f39
commit bb6300b032
2 changed files with 29 additions and 12 deletions

View File

@ -18,25 +18,26 @@ import (
// Globals
var (
Stats = NewStats()
tokenBucketMu sync.Mutex // protects the token bucket variables
tokenBucket *rate.Limiter
prevTokenBucket = tokenBucket
currLimitMu sync.Mutex // protects changes to the timeslot
currLimit BwTimeSlot
Stats = NewStats()
tokenBucketMu sync.Mutex // protects the token bucket variables
tokenBucket *rate.Limiter
prevTokenBucket = tokenBucket
bwLimitToggledOff = false
currLimitMu sync.Mutex // protects changes to the timeslot
currLimit BwTimeSlot
)
const maxBurstSize = 1 * 1024 * 1024 // must be bigger than the biggest request
// make a new empty token bucket with the bandwidth given
func newTokenBucket(bandwidth SizeSuffix) *rate.Limiter {
tokenBucket = rate.NewLimiter(rate.Limit(bandwidth), maxBurstSize)
newTokenBucket := rate.NewLimiter(rate.Limit(bandwidth), maxBurstSize)
// empty the bucket
err := tokenBucket.WaitN(context.Background(), maxBurstSize)
err := newTokenBucket.WaitN(context.Background(), maxBurstSize)
if err != nil {
Errorf(nil, "Failed to empty token bucket: %v", err)
}
return tokenBucket
return newTokenBucket
}
// Start the token bucket if necessary
@ -72,12 +73,27 @@ func startTokenTicker() {
if currLimit.bandwidth != limitNow.bandwidth {
tokenBucketMu.Lock()
// If bwlimit is toggled off, the change should only
// become active on the next toggle, which causes
// an exchange of tokenBucket <-> prevTokenBucket
var targetBucket **rate.Limiter
if bwLimitToggledOff {
targetBucket = &prevTokenBucket
} else {
targetBucket = &tokenBucket
}
// Set new bandwidth. If unlimited, set tokenbucket to nil.
if limitNow.bandwidth > 0 {
tokenBucket = newTokenBucket(limitNow.bandwidth)
Logf(nil, "Scheduled bandwidth change. Limit set to %vBytes/s", &limitNow.bandwidth)
*targetBucket = newTokenBucket(limitNow.bandwidth)
if bwLimitToggledOff {
Logf(nil, "Scheduled bandwidth change. " +
"Limit will be set to %vBytes/s when toggled on again.", &limitNow.bandwidth)
} else {
Logf(nil, "Scheduled bandwidth change. Limit set to %vBytes/s", &limitNow.bandwidth)
}
} else {
tokenBucket = nil
*targetBucket = nil
Logf(nil, "Scheduled bandwidth change. Bandwidth limits disabled")
}

View File

@ -21,6 +21,7 @@ func startSignalHandler() {
for {
<-signals
tokenBucketMu.Lock()
bwLimitToggledOff = !bwLimitToggledOff
tokenBucket, prevTokenBucket = prevTokenBucket, tokenBucket
s := "disabled"
if tokenBucket != nil {