event/Loop: split InjectBreak() from Break()

This commit is contained in:
Max Kellermann 2022-11-22 22:26:16 +01:00
parent a57cf443ed
commit a3b32819b1
3 changed files with 33 additions and 17 deletions

View File

@ -87,17 +87,6 @@ EventLoop::GetUring() noexcept
#endif
void
EventLoop::Break() noexcept
{
if (quit.exchange(true))
return;
#ifdef HAVE_THREADED_EVENT_LOOP
wake_fd.Write();
#endif
}
bool
EventLoop::AddFD(int fd, unsigned events, SocketEvent &event) noexcept
{
@ -286,6 +275,7 @@ EventLoop::Run() noexcept
assert(IsInside());
assert(!quit);
assert(!quit_injected);
#ifdef HAVE_THREADED_EVENT_LOOP
assert(alive);
assert(busy);
@ -437,6 +427,11 @@ EventLoop::OnSocketReady([[maybe_unused]] unsigned flags) noexcept
wake_fd.Read();
if (quit_injected) {
Break();
return;
}
const std::scoped_lock<Mutex> lock(mutex);
HandleInject();
}

View File

@ -115,7 +115,7 @@ class EventLoop final
bool alive;
#endif
std::atomic_bool quit{false};
bool quit = false;
/**
* True when the object has been modified and another check is
@ -124,6 +124,8 @@ class EventLoop final
bool again;
#ifdef HAVE_THREADED_EVENT_LOOP
bool quit_injected = false;
/**
* True when handling callbacks, false when waiting for I/O or
* timeout.
@ -187,11 +189,30 @@ public:
#endif
/**
* Stop execution of this #EventLoop at the next chance. This
* method is thread-safe and non-blocking: after returning, it
* is not guaranteed that the EventLoop has really stopped.
* Stop execution of this #EventLoop at the next chance.
*
* This method is not thread-safe. For stopping the
* #EventLoop from within another thread, use InjectBreak().
*/
void Break() noexcept;
void Break() noexcept {
quit = true;
}
#ifdef HAVE_THREADED_EVENT_LOOP
/**
* Like Break(), but thread-safe. It is also non-blocking:
* after returning, it is not guaranteed that the EventLoop
* has really stopped.
*/
void InjectBreak() noexcept {
{
const std::scoped_lock lock{mutex};
quit_injected = true;
}
wake_fd.Write();
}
#endif // HAVE_THREADED_EVENT_LOOP
bool AddFD(int fd, unsigned events, SocketEvent &event) noexcept;
bool ModifyFD(int fd, unsigned events, SocketEvent &event) noexcept;

View File

@ -45,7 +45,7 @@ EventThread::Stop() noexcept
assert(event_loop.IsAlive());
event_loop.SetAlive(false);
event_loop.Break();
event_loop.InjectBreak();
thread.Join();
}
}