Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix compilation of the ports event multiplexer #9031

Merged
merged 2 commits into from Apr 17, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
65 changes: 59 additions & 6 deletions pdns/portsmplexer.cc
Expand Up @@ -23,11 +23,12 @@ class PortsFDMultiplexer : public FDMultiplexer
close(d_portfd);
}

virtual int run(struct timeval* tv, int timeout=500);
virtual int run(struct timeval* tv, int timeout=500) override;
virtual void getAvailableFDs(std::vector<int>& fds, int timeout) override;

virtual void addFD(callbackmap_t& cbmap, int fd, callbackfunc_t toDo, const boost::any& parameter, const struct timeval* ttd=nullptr);
virtual void removeFD(callbackmap_t& cbmap, int fd);
string getName()
virtual void addFD(callbackmap_t& cbmap, int fd, callbackfunc_t toDo, const boost::any& parameter, const struct timeval* ttd=nullptr) override;
virtual void removeFD(callbackmap_t& cbmap, int fd) override;
string getName() const override
{
return "solaris completion ports";
}
Expand Down Expand Up @@ -78,15 +79,67 @@ void PortsFDMultiplexer::removeFD(callbackmap_t& cbmap, int fd)
throw FDMultiplexerException("Removing fd from port set: "+stringerror());
}

void PortsFDMultiplexer::getAvailableFDs(std::vector<int>& fds, int timeout)
{
struct timespec timeoutspec;
timeoutspec.tv_sec = timeout / 1000;
timeoutspec.tv_nsec = (timeout % 1000) * 1000000;
unsigned int numevents = 1;
int ret = port_getn(d_portfd, d_pevents.get(), min(PORT_MAX_LIST, s_maxevents), &numevents, &timeoutspec);

/* port_getn has an unusual API - (ret == -1, errno == ETIME) can
mean partial success; you must check (*numevents) in this case
and process anything in there, otherwise you'll never see any
events from that object again. We don't care about pure timeouts
(ret == -1, errno == ETIME, *numevents == 0) so we don't bother
with that case. */
if (ret == -1 && errno != ETIME) {
if (errno != EINTR) {
throw FDMultiplexerException("completion port_getn returned error: " + stringerror());
}

// EINTR is not really an error
return;
}

if (numevents == 0) {
// nothing
return;
}

fds.reserve(numevents);

for (unsigned int n = 0; n < numevents; ++n) {
const auto fd = d_pevents[n].portev_object;

/* we need to re-associate the FD */
if (d_readCallbacks.count(fd)) {
if (port_associate(d_portfd, PORT_SOURCE_FD, fd, POLLIN, 0) < 0) {
throw FDMultiplexerException("Unable to add fd back to ports (read): " + stringerror());
}
}
else if (d_writeCallbacks.count(fd)) {
if (port_associate(d_portfd, PORT_SOURCE_FD, fd, POLLOUT, 0) < 0) {
throw FDMultiplexerException("Unable to add fd back to ports (write): " + stringerror());
}
} else {
/* not registered, this is unexpected */
continue;
}

fds.push_back(fd);
}
}

int PortsFDMultiplexer::run(struct timeval* now, int timeout)
{
if(d_inrun) {
throw FDMultiplexerException("FDMultiplexer::run() is not reentrant!\n");
}

struct timespec timeoutspec;
timeoutspec.tv_sec = time / 1000;
timeoutspec.tv_nsec = (time % 1000) * 1000000;
timeoutspec.tv_sec = timeout / 1000;
timeoutspec.tv_nsec = (timeout % 1000) * 1000000;
unsigned int numevents=1;
int ret= port_getn(d_portfd, d_pevents.get(), min(PORT_MAX_LIST, s_maxevents), &numevents, &timeoutspec);

Expand Down
2 changes: 1 addition & 1 deletion pdns/test-dns_random_hh.cc
Expand Up @@ -123,7 +123,7 @@ BOOST_AUTO_TEST_CASE(test_dns_random_getrandom_average) {
#endif

#if defined(HAVE_ARC4RANDOM)
BOOST_AUTO_TEST_CASE(test_dns_random_getrandom_average) {
BOOST_AUTO_TEST_CASE(test_dns_random_arc4random_average) {

::arg().set("rng")="arc4random";
::arg().set("entropy-source")="/dev/urandom";
Expand Down