system/EventPipe: use class Unique{Socket,File}Descriptor

This commit is contained in:
Max Kellermann 2021-01-11 17:37:30 +01:00
parent 17eae74c1c
commit 51f110a990
3 changed files with 35 additions and 45 deletions

View File

@ -38,10 +38,10 @@ class WakeFD {
public:
SocketDescriptor GetSocket() const noexcept {
#ifdef USE_EVENTFD
return SocketDescriptor::FromFileDescriptor(fd.Get());
#ifdef _WIN32
return fd.Get();
#else
return SocketDescriptor(fd.Get());
return SocketDescriptor::FromFileDescriptor(fd.Get());
#endif
}

View File

@ -34,59 +34,39 @@
#endif
#ifdef _WIN32
static void PoorSocketPair(int fd[2]);
static void PoorSocketPair(UniqueSocketDescriptor &socket0,
UniqueSocketDescriptor &socket01);
#endif
EventPipe::EventPipe()
{
#ifdef _WIN32
PoorSocketPair(fds);
PoorSocketPair(r, w);
#else
FileDescriptor r, w;
if (!FileDescriptor::CreatePipeNonBlock(r, w))
if (!UniqueFileDescriptor::CreatePipeNonBlock(r, w))
throw MakeErrno("pipe() has failed");
fds[0] = r.Steal();
fds[1] = w.Steal();
#endif
}
EventPipe::~EventPipe() noexcept
{
#ifdef _WIN32
closesocket(fds[0]);
closesocket(fds[1]);
#else
close(fds[0]);
close(fds[1]);
#endif
}
EventPipe::~EventPipe() noexcept = default;
bool
EventPipe::Read() noexcept
{
assert(fds[0] >= 0);
assert(fds[1] >= 0);
assert(r.IsDefined());
assert(w.IsDefined());
char buffer[256];
#ifdef _WIN32
return recv(fds[0], buffer, sizeof(buffer), 0) > 0;
#else
return read(fds[0], buffer, sizeof(buffer)) > 0;
#endif
return r.Read(buffer, sizeof(buffer)) > 0;
}
void
EventPipe::Write() noexcept
{
assert(fds[0] >= 0);
assert(fds[1] >= 0);
assert(r.IsDefined());
assert(w.IsDefined());
#ifdef _WIN32
send(fds[1], "", 1, 0);
#else
[[maybe_unused]] ssize_t nbytes = write(fds[1], "", 1);
#endif
w.Write("", 1);
}
#ifdef _WIN32
@ -97,10 +77,8 @@ EventPipe::Write() noexcept
* rather than wide-available API.
*/
static void
PoorSocketPair(int fd[2])
PoorSocketPair(UniqueSocketDescriptor &socket0, UniqueSocketDescriptor &socket1)
{
assert (fd != nullptr);
UniqueSocketDescriptor listen_socket;
if (!listen_socket.Create(AF_INET, SOCK_STREAM, IPPROTO_TCP))
throw MakeSocketError("Failed to create socket");
@ -111,7 +89,6 @@ PoorSocketPair(int fd[2])
if (!listen_socket.Listen(1))
throw MakeSocketError("Failed to listen on socket");
UniqueSocketDescriptor socket0;
if (!socket0.Create(AF_INET, SOCK_STREAM, IPPROTO_TCP))
throw MakeSocketError("Failed to create socket");
@ -120,12 +97,9 @@ PoorSocketPair(int fd[2])
socket0.SetNonBlocking();
auto socket1 = listen_socket.AcceptNonBlock();
socket1 = listen_socket.AcceptNonBlock();
if (!socket1.IsDefined())
throw MakeSocketError("Failed to accept connection");
fd[0] = socket0.Steal();
fd[1] = socket1.Steal();
}
#endif

View File

@ -20,13 +20,23 @@
#ifndef MPD_EVENT_PIPE_HXX
#define MPD_EVENT_PIPE_HXX
#ifdef _WIN32
#include "net/UniqueSocketDescriptor.hxx"
#else
#include "io/UniqueFileDescriptor.hxx"
#endif
/**
* A pipe that can be used to trigger an event to the read side.
*
* Errors in the constructor are fatal.
*/
class EventPipe {
int fds[2];
#ifdef _WIN32
UniqueSocketDescriptor r, w;
#else
UniqueFileDescriptor r, w;
#endif
public:
/**
@ -39,9 +49,15 @@ public:
EventPipe(const EventPipe &other) = delete;
EventPipe &operator=(const EventPipe &other) = delete;
int Get() const noexcept {
return fds[0];
#ifdef _WIN32
SocketDescriptor Get() const noexcept {
return r;
}
#else
FileDescriptor Get() const noexcept {
return r;
}
#endif
/**
* Checks if Write() was called at least once since the last