Kernel: Fix leaking Timer instances

When a Timer is queued we add a reference, so whenever we remove
a timer or fire it we should drop that reference.

Fixes #4382
This commit is contained in:
Tom 2020-12-11 11:07:42 -07:00 committed by Andreas Kling
parent 66f9a2d9ec
commit 03fcd02dfd
2 changed files with 7 additions and 3 deletions

View file

@ -213,8 +213,6 @@ bool TimerQueue::cancel_timer(TimerId id)
ASSERT(found_timer);
ASSERT(timer_queue);
remove_timer_locked(*timer_queue, *found_timer);
lock.unlock();
found_timer->unref();
return true;
}
@ -241,6 +239,7 @@ bool TimerQueue::cancel_timer(Timer& timer)
return false;
}
ASSERT(timer.ref_count() > 1);
remove_timer_locked(timer_queue, timer);
return true;
}
@ -256,6 +255,10 @@ void TimerQueue::remove_timer_locked(Queue& queue, Timer& timer)
if (was_next_timer)
update_next_timer_due(queue);
// Whenever we remove a timer that was still queued (but hasn't been
// fired) we added a reference to it. So, when removing it from the
// queue we need to drop that reference.
timer.unref();
}
void TimerQueue::fire()
@ -279,6 +282,7 @@ void TimerQueue::fire()
m_timers_executing.remove(timer);
timer->set_queued(false);
// Drop the reference we added when queueing the timer
timer->unref();
timer = queue.list.head();

View file

@ -97,7 +97,7 @@ public:
bool cancel_timer(Timer&);
bool cancel_timer(NonnullRefPtr<Timer>&& timer)
{
return cancel_timer(timer.leak_ref());
return cancel_timer(*move(timer));
}
void fire();