diff --git a/source/eventcore/drivers/posix/events.d b/source/eventcore/drivers/posix/events.d index 92e9997..c96c060 100644 --- a/source/eventcore/drivers/posix/events.d +++ b/source/eventcore/drivers/posix/events.d @@ -64,6 +64,9 @@ final class PosixEventDriverEvents(Loop : PosixEventLoop, Sockets : EventDriverS } else { sock_t[2] fd; version (Posix) { + import core.sys.posix.fcntl : fcntl, F_SETFL; + import eventcore.drivers.posix.sockets : O_CLOEXEC; + // create a pair of sockets to communicate between threads import core.sys.posix.sys.socket : SOCK_DGRAM, AF_UNIX, socketpair; if (() @trusted { return socketpair(AF_UNIX, SOCK_DGRAM, 0, fd); } () != 0) @@ -72,7 +75,9 @@ final class PosixEventDriverEvents(Loop : PosixEventLoop, Sockets : EventDriverS assert(fd[0] != fd[1]); // use the first socket as the async receiver - auto s = m_sockets.adoptDatagramSocketInternal(fd[0]); + auto s = m_sockets.adoptDatagramSocketInternal(fd[0], true, true); + + () @trusted { fcntl(fd[1], F_SETFL, O_CLOEXEC); } (); } else { // fake missing socketpair support on Windows import std.socket : InternetAddress; diff --git a/source/eventcore/drivers/posix/signals.d b/source/eventcore/drivers/posix/signals.d index aec99ce..cc57398 100644 --- a/source/eventcore/drivers/posix/signals.d +++ b/source/eventcore/drivers/posix/signals.d @@ -33,7 +33,7 @@ final class SignalFDEventDriverSignals(Loop : PosixEventLoop) : EventDriverSigna if (sigprocmask(SIG_BLOCK, &sset, null) != 0) return SignalListenID.invalid; - return SignalListenID(signalfd(-1, &sset, SFD_NONBLOCK)); + return SignalListenID(signalfd(-1, &sset, SFD_NONBLOCK | SFD_CLOEXEC)); } (); @@ -52,7 +52,7 @@ final class SignalFDEventDriverSignals(Loop : PosixEventLoop) : EventDriverSigna assert(m_loop.m_fds[descriptor].common.refCount > 0, "Adding reference to unreferenced event FD."); m_loop.m_fds[descriptor].common.refCount++; } - + override bool releaseRef(SignalListenID descriptor) { FD fd = cast(FD)descriptor; @@ -71,7 +71,7 @@ final class SignalFDEventDriverSignals(Loop : PosixEventLoop) : EventDriverSigna SignalListenID lid = cast(SignalListenID)fd; signalfd_siginfo nfo; do { - auto ret = () @trusted { return read(cast(int)fd, &nfo, nfo.sizeof); } (); + auto ret = () @trusted { return read(cast(int)fd, &nfo, nfo.sizeof); } (); if (ret == -1 && errno.among!(EAGAIN, EINPROGRESS)) break; auto cb = m_loop.m_fds[fd].signal.callback; @@ -107,7 +107,7 @@ final class DummyEventDriverSignals(Loop : PosixEventLoop) : EventDriverSignals { assert(false); } - + override bool releaseRef(SignalListenID descriptor) { assert(false); diff --git a/source/eventcore/drivers/posix/sockets.d b/source/eventcore/drivers/posix/sockets.d index 6197537..489df3c 100644 --- a/source/eventcore/drivers/posix/sockets.d +++ b/source/eventcore/drivers/posix/sockets.d @@ -595,12 +595,12 @@ final class PosixEventDriverSockets(Loop : PosixEventLoop) : EventDriverSockets return adoptDatagramSocketInternal(socket, false); } - package DatagramSocketFD adoptDatagramSocketInternal(int socket, bool is_internal = true) + package DatagramSocketFD adoptDatagramSocketInternal(int socket, bool is_internal = true, bool close_on_exec = false) { auto fd = DatagramSocketFD(socket); if (m_loop.m_fds[fd].common.refCount) // FD already in use? return DatagramSocketFD.init; - setSocketNonBlocking(fd); + setSocketNonBlocking(fd, close_on_exec); m_loop.initFD(fd, is_internal ? FDFlags.internal : FDFlags.none); m_loop.registerFD(fd, EventMask.read|EventMask.write|EventMask.status); m_loop.m_fds[fd].specific = DgramSocketSlot.init; diff --git a/source/eventcore/drivers/posix/watchers.d b/source/eventcore/drivers/posix/watchers.d index d2ac005..ceae467 100644 --- a/source/eventcore/drivers/posix/watchers.d +++ b/source/eventcore/drivers/posix/watchers.d @@ -34,7 +34,7 @@ final class InotifyEventDriverWatchers(Events : EventDriverEvents) : EventDriver import std.range.primitives : walkLength; enum IN_NONBLOCK = 0x800; // value in core.sys.linux.sys.inotify is incorrect - auto handle = () @trusted { return inotify_init1(IN_NONBLOCK); } (); + auto handle = () @trusted { return inotify_init1(IN_NONBLOCK | IN_CLOEXEC); } (); if (handle == -1) return WatcherID.invalid; auto ret = WatcherID(handle);