Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix bug in meter traversal logic #11

Merged
merged 1 commit into from
Nov 8, 2019
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 9 additions & 6 deletions sweeper.go
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,6 @@ func (sw *sweeper) update() {
timeMultiplier := float64(time.Second) / float64(tdiff)

// Calculate the bandwidth for all active meters.
newLen := len(sw.meters)
for i, m := range sw.meters[:sw.activeMeters] {
total := atomic.LoadUint64(&m.accumulator)
diff := total - m.snapshot.Total
Expand Down Expand Up @@ -147,8 +146,7 @@ func (sw *sweeper) update() {
// Reset the rate, keep the total.
m.registered = false
m.snapshot.Rate = 0
newLen--
sw.meters[i] = sw.meters[newLen]
sw.meters[i] = nil
}

// Re-add the total to all the newly active accumulators and set the snapshot to the total.
Expand All @@ -162,10 +160,15 @@ func (sw *sweeper) update() {
m.snapshot.Total = total
}

// trim the meter list
for i := newLen; i < len(sw.meters); i++ {
sw.meters[i] = nil
// compress and trim the meter list
var newLen int
for _, m := range sw.meters {
if m != nil {
sw.meters[newLen] = m
newLen++
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's actually a trick to this:

newMeters := sw.meters[:0]
for _, m := range sw.meters {
    if m != nil {
        newMeters = append(newMeters, m)
    }
}
sw.meters = newMeters

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

neat, but it probably generates the same code underneath :)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

do you want me to apply it? I am neutral either way and I usually prefer explicitness.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

actually, the trick might generate slower code because it has to do bounds checking.
Maybe the compiler is smart enough to elide it though, I wouldn't bet against it.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The trick will do less bounds checking, IIRC. But I'm fine with this as it is.

}

sw.meters = sw.meters[:newLen]

// Finally, mark all meters still in the list as "active".
Expand Down