-
Notifications
You must be signed in to change notification settings - Fork 82
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
Memory leaks in govpp core #184
Conversation
Signed-off-by: Vladimir Lavor <[email protected]>
replyTimeoutTimer := time.NewTimer(ch.receiveReplyTimeout) | ||
defer replyTimeoutTimer.Stop() | ||
select { | ||
case ch.replyChan <- reply: | ||
return // reply sent ok | ||
case <-time.After(ch.receiveReplyTimeout): | ||
// receiver still not ready | ||
case <-replyTimeoutTimer.C: | ||
// receiver still isn't ready |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I understand the idea but I don't understand the issue.
time.After creates a temporary leak until the timer expires. After the expiration, it is supposed to be garbage collected. By default the timeout is 100ms. So I am not sure how you can fire enough API calls in such a little time window to create a significant memory impact.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@hardeker hello Arthur, two reasons:
- the reply timeout is indeed 100ms by default, but is configurable via
ReplyChannelTimeout
so the garbage collection can be easily and unknowingly by a user "postponed". - It depends on what we consider a "significant memory impact". I understand the impact is temporary, but memory spikes are noticeable as the timer is responsible for >30% of total GoVPP memory consumption. Or even much more, see this example:
With the fix, the time.After()
drops to ~10kB in the same scenario.
Fixed memory leaks in GoVPP core stream and request handler.
Edit: the second issue was already addressed in #182
The temporary leak is occurring in the request handler.
<-time.After()
is not garbage-collected before expiration and shouldn't be used in such a frequently called method.The second memory leak is permanent, caused by the timer not being closed, causing a slow increase in memory consumption over time.
Performance profile (done on ~1000 API calls using the Stream API):
With the fix: