From a8b0ea58e60bb0326b7f7c8f3c736d89ce9ef1df Mon Sep 17 00:00:00 2001 From: Lexi Winter Date: Sun, 29 Jun 2025 19:19:23 +0100 Subject: wip macOS port --- nihil.posix/process.ccm | 91 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 91 insertions(+) create mode 100644 nihil.posix/process.ccm (limited to 'nihil.posix/process.ccm') diff --git a/nihil.posix/process.ccm b/nihil.posix/process.ccm new file mode 100644 index 0000000..425deac --- /dev/null +++ b/nihil.posix/process.ccm @@ -0,0 +1,91 @@ +/* + * This source code is released into the public domain. + */ + +module; + +#include +#include +#include +#include + +#include + +export module nihil.posix:process; + +import nihil.error; + +namespace nihil { + +/* + * wait_result: the exit status of a process. + */ +export struct wait_result final { + // Return true if the process exited normally with an exit code of + // zero, otherwise false. + [[nodiscard]] auto okay(this wait_result const &self) -> bool; + [[nodiscard]] explicit operator bool(this wait_result const &self); + + // Return the exit status, if any. + [[nodiscard]] auto status(this wait_result const &self) + -> std::optional; + + // Return the exit signal, if any. + [[nodiscard]] auto signal(this wait_result const &self) + -> std::optional; + +private: + friend struct process; + + int _status; + + // Construct a new wait_result from the output of waitpid(). + wait_result(int status); +}; + +/* + * process: represents a process we created, which can be waited for. + */ +export struct process final { + process() = delete; + + /* + * Create a new process from a pid, which must be a child of the + * current process. + */ + process(::pid_t pid); + + // When destroyed, we automatically wait for the process to + // avoid creating zombie processes. + ~process(); + + // Movable. + process(process &&) noexcept; + auto operator=(this process &, process &&) noexcept -> process &; + + // Not copyable. + process(process const &) = delete; + auto operator=(this process &, process const &) -> process & = delete; + + // Get the child's process id. + [[nodiscard]] auto pid(this process const &self) noexcept -> ::pid_t; + + /* + * Wait for this process to exit (by calling waitpid()) and return + * its exit status. This destroys the process state, leaving this + * object in a moved-from state. + */ + [[nodiscard]] auto wait(this process &&self) + -> std::expected; + + /* + * Release this process so we won't try to wait for it when + * destroying this object. + */ + [[nodiscard]] auto release(this process &&self) -> ::pid_t; + +private: + ::pid_t m_pid; +}; + +} // namespace nihil -- cgit v1.2.3