[*] Atomic SOCK_CLOEXEC-awareness on some UNIX systems

This commit is contained in:
Reece Wilson 2023-08-19 15:05:14 +01:00
parent ef4dc9bc18
commit e6bf022bef
4 changed files with 85 additions and 10 deletions

View File

@ -66,16 +66,26 @@ namespace Aurora::IO::Net
{
sockaddr_nl nladdr {};
this->fd = socket(AF_NETLINK, SOCK_DGRAM, NETLINK_ROUTE);
this->fd = socket(AF_NETLINK, SOCK_DGRAM | SOCK_CLOEXEC, NETLINK_ROUTE);
bool bMakeCloseExec { !bool(SOCK_CLOEXEC) };
if (this->fd < 0)
{
this->fd = socket(AF_NETLINK, SOCK_DGRAM, NETLINK_ROUTE);
bMakeCloseExec = true;
}
if (this->fd < 0)
{
return false;
}
int flags = ::fcntl(this->fd, F_GETFL, 0);
if (flags != -1)
if (bMakeCloseExec)
{
::fcntl(this->fd, F_SETFL, flags | FD_CLOEXEC);
int flags = ::fcntl(this->fd, F_GETFL, 0);
if (flags != -1)
{
::fcntl(this->fd, F_SETFL, flags | FD_CLOEXEC);
}
}
nladdr.nl_family = AF_NETLINK;

View File

@ -12,6 +12,9 @@
#include "AuIPAddress.hpp"
#include "AuNetError.hpp"
#include <Source/IO/Loop/LSHandle.hpp>
#if !defined(SOCK_CLOEXEC)
#define SOCK_CLOEXEC 0
#endif
namespace Aurora::IO::Net
{
@ -83,18 +86,37 @@ namespace Aurora::IO::Net
this->CloseSocket();
this->osHandle_ = ::socket(
IPToDomain(this->remoteEndpoint_),
IPToDomain(this->remoteEndpoint_) | SOCK_CLOEXEC,
TransportToPlatformType(this->remoteEndpoint_),
0
);
bool bMakeCloseExec { !bool(SOCK_CLOEXEC) };
if (this->osHandle_ == -1)
{
this->osHandle_ = ::socket(
IPToDomain(this->remoteEndpoint_),
TransportToPlatformType(this->remoteEndpoint_),
0
);
bMakeCloseExec = true;
}
if (this->osHandle_ == -1)
{
this->SendErrorNoStream(GetLastNetError());
return;
}
if (bMakeCloseExec)
{
(void)this->MakeCloseonexec();
}
this->osHandleOwner_ = AuIO::IOHandleShared();
this->osHandleOwner_->InitFromPairMove((int)this->osHandle_, (int)this->osHandle_);
@ -115,17 +137,35 @@ namespace Aurora::IO::Net
}
this->osHandle_ = ::socket(
IPToDomain(this->remoteEndpoint_),
IPToDomain(this->remoteEndpoint_) | SOCK_CLOEXEC,
TransportToPlatformType(this->remoteEndpoint_),
0
);
bool bMakeCloseExec { !bool(SOCK_CLOEXEC) };
if (this->osHandle_ == -1)
{
this->osHandle_ = ::socket(
IPToDomain(this->remoteEndpoint_),
TransportToPlatformType(this->remoteEndpoint_),
0
);
bMakeCloseExec = true;
}
if (this->osHandle_ == -1)
{
this->SendErrorNoStream(GetLastNetError());
return;
}
if (bMakeCloseExec)
{
(void)this->MakeCloseonexec();
}
this->osHandleOwner_->InitFromPairMove((int)this->osHandle_, (int)this->osHandle_);
if (!this->PrepareConnectOperations())
@ -137,7 +177,6 @@ namespace Aurora::IO::Net
bool Socket::PrepareConnectOperations()
{
(void)this->MakeCloseonexec();
return this->MakeNonblocking();
}

View File

@ -10,6 +10,10 @@
#include "AuNetError.hpp"
#include "AuNetEndpoint.hpp"
#if !defined(SOCK_CLOEXEC)
#define SOCK_CLOEXEC 0
#endif
namespace Aurora::IO::Net
{
SocketServerImpl::SocketServerImpl(NetInterface *pInterface,
@ -55,12 +59,24 @@ namespace Aurora::IO::Net
return false;
}
bool bMakeCloseExec { !bool(SOCK_CLOEXEC) };
this->osHandle_ = ::socket(
IPToDomain(localAddress),
TransportToPlatformType(localAddress),
TransportToPlatformType(localAddress) | SOCK_CLOEXEC,
0
);
if (this->osHandle_ == -1)
{
this->osHandle_ = ::socket(
IPToDomain(localAddress),
TransportToPlatformType(localAddress),
0
);
bMakeCloseExec = true;
}
if (this->osHandle_ == -1)
{
NetError error;
@ -69,7 +85,12 @@ namespace Aurora::IO::Net
return false;
}
return this->MakeNonblocking() && this->MakeCloseonexec();
if (bMakeCloseExec)
{
this->MakeCloseonexec();
}
return this->MakeNonblocking();
}
bool SocketServerImpl::ImplBind()

View File

@ -408,7 +408,12 @@ namespace Aurora::IO::UNIX
#endif
}
int fd = ::socket(AF_UNIX, SOCK_STREAM, 0);
int fd = ::socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0);
if (fd <= -1)
{
fd = ::socket(AF_UNIX, SOCK_STREAM, 0);
}
if (fd <= -1)
{
SysPushErrorIO("No Resource?");