/* * Copyright (c) 2025, ayeteadoe * * SPDX-License-Identifier: BSD-2-Clause */ #include #include #if !defined(AK_OS_WINDOWS) # include #endif namespace WebView { ProcessMonitor::ProcessMonitor(Function exit_handler) : m_on_process_exit(move(exit_handler)) { #if !defined(AK_OS_WINDOWS) m_signal_handle = Core::EventLoop::register_signal(SIGCHLD, [this](int) { auto result = Core::System::waitpid(-1, WNOHANG); while (!result.is_error() && result.value().pid > 0) { auto& [pid, status] = result.value(); if (m_monitored_processes.contains(pid)) { if (WIFEXITED(status) || WIFSIGNALED(status)) { m_monitored_processes.remove(pid); m_on_process_exit(pid); } } result = Core::System::waitpid(-1, WNOHANG); } }); #endif } ProcessMonitor::~ProcessMonitor() { #if defined(AK_OS_WINDOWS) for (pid_t pid : m_monitored_processes) { Core::EventLoop::unregister_process(pid); } #else Core::EventLoop::unregister_signal(m_signal_handle); #endif } void ProcessMonitor::add_process(pid_t pid) { if (m_monitored_processes.set(pid, AK::HashSetExistingEntryBehavior::Keep) != AK::HashSetResult::InsertedNewEntry) return; #if defined(AK_OS_WINDOWS) Core::EventLoop::register_process(pid, [this](pid_t pid) { m_monitored_processes.remove(pid); m_on_process_exit(pid); }); #endif } }