[Libreoffice-commits] online.git: Branch 'private/Ashod/nonblocking' - common/SigUtil.cpp common/SigUtil.hpp Makefile.am net/Socket.cpp net/Socket.hpp test/Makefile.am
Michael Meeks
michael.meeks at collabora.com
Thu Mar 2 19:38:59 UTC 2017
Makefile.am | 4 +++-
common/SigUtil.cpp | 3 +++
common/SigUtil.hpp | 2 ++
net/Socket.cpp | 39 +++++++++++++++++++++++++++++++++++++++
net/Socket.hpp | 39 ++++++++++++++++++++++-----------------
test/Makefile.am | 3 ++-
6 files changed, 71 insertions(+), 19 deletions(-)
New commits:
commit 9c82365766d5d5ae15b6d3a88647f3945e445eb9
Author: Michael Meeks <michael.meeks at collabora.com>
Date: Thu Mar 2 18:12:52 2017 +0000
signal handling: keep track of all socket poll wakeups & wakeup.
Instead of waiting for polls to timeout; wake them up.
diff --git a/Makefile.am b/Makefile.am
index 2d8eb16..dd249b7 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -59,7 +59,8 @@ shared_sources = common/FileUtil.cpp \
common/SpookyV2.cpp \
common/Unit.cpp \
common/UnitHTTP.cpp \
- common/Util.cpp
+ common/Util.cpp \
+ net/Socket.cpp
if ENABLE_SSL
shared_sources += net/Ssl.cpp
endif
@@ -105,6 +106,7 @@ loolwsd_fuzzer_SOURCES = $(loolwsd_sources) \
kit/DummyLibreOfficeKit.cpp
loolnb_SOURCES = net/loolnb.cpp \
+ net/Socket.cpp \
common/Log.cpp \
common/Util.cpp
if ENABLE_SSL
diff --git a/common/SigUtil.cpp b/common/SigUtil.cpp
index 63d643b..d88afa4 100644
--- a/common/SigUtil.cpp
+++ b/common/SigUtil.cpp
@@ -33,6 +33,7 @@
#include <string>
#include <thread>
+#include "Socket.hpp"
#include "Common.hpp"
#include "Log.hpp"
#include "Util.hpp"
@@ -119,6 +120,7 @@ namespace SigUtil
Log::signalLog(signalName(signal));
Log::signalLog("\n");
SigUtil::requestShutdown();
+ SocketPoll::wakeupWorld();
}
else if (!TerminationFlag)
{
@@ -127,6 +129,7 @@ namespace SigUtil
Log::signalLog(signalName(signal));
Log::signalLog("\n");
TerminationFlag = true;
+ SocketPoll::wakeupWorld();
}
else
{
diff --git a/common/SigUtil.hpp b/common/SigUtil.hpp
index a478161..21088d6 100644
--- a/common/SigUtil.hpp
+++ b/common/SigUtil.hpp
@@ -25,6 +25,8 @@ namespace SigUtil
/// Returns the name of the signal.
const char* signalName(int signo);
+ /// Register a wakeup function when changing
+
/// Trap signals to cleanup and exit the process gracefully.
void setTerminationSignals();
diff --git a/net/Socket.cpp b/net/Socket.cpp
new file mode 100644
index 0000000..48549db
--- /dev/null
+++ b/net/Socket.cpp
@@ -0,0 +1,39 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include "Socket.hpp"
+
+std::mutex SocketPoll::_pollWakeupsMutex;
+std::vector<int> SocketPoll::_pollWakeups;
+
+SocketPoll::SocketPoll()
+{
+ // Create the wakeup fd.
+ if (::pipe2(_wakeup, O_CLOEXEC | O_NONBLOCK) == -1)
+ {
+ throw std::runtime_error("Failed to allocate pipe for SocketPoll waking.");
+ }
+ std::lock_guard<std::mutex> lock(_pollWakeupsMutex);
+ _pollWakeups.push_back(_wakeup[1]);
+}
+
+SocketPoll::~SocketPoll()
+{
+ ::close(_wakeup[0]);
+ ::close(_wakeup[1]);
+
+ std::lock_guard<std::mutex> lock(_pollWakeupsMutex);
+ auto it = std::find(_pollWakeups.begin(),
+ _pollWakeups.end(),
+ _wakeup[1]);
+ if (it != _pollWakeups.end())
+ _pollWakeups.erase(it);
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/net/Socket.hpp b/net/Socket.hpp
index 026a414..be19f3e 100644
--- a/net/Socket.hpp
+++ b/net/Socket.hpp
@@ -175,21 +175,13 @@ private:
/// overhead to adding/removing sockets is not helpful.
class SocketPoll
{
-public:
- SocketPoll()
- {
- // Create the wakeup fd.
- if (::pipe2(_wakeup, O_CLOEXEC | O_NONBLOCK) == -1)
- {
- throw std::runtime_error("Failed to allocate pipe for SocketPoll waking.");
- }
- }
+ static std::mutex _pollWakeupsMutex;
+ static std::vector<int> _pollWakeups;
- ~SocketPoll()
- {
- ::close(_wakeup[0]);
- ::close(_wakeup[1]);
- }
+public:
+ /// Create a socket poll, called rather infrequently.
+ SocketPoll();
+ ~SocketPoll();
/// Poll the sockets for available data to read or buffer to write.
void poll(const int timeoutMaxMs)
@@ -260,18 +252,31 @@ public:
}
}
- /// Wakeup the main polling loop in another thread
- void wakeup()
+ /// Write to a wakeup descriptor
+ static void wakeup (int fd)
{
// wakeup the main-loop.
int rc;
do {
- rc = ::write(_wakeup[1], "w", 1);
+ rc = ::write(fd, "w", 1);
} while (rc == -1 && errno == EINTR);
assert (rc != -1 || errno == EAGAIN || errno == EWOULDBLOCK);
}
+ /// Wakeup the main polling loop in another thread
+ void wakeup()
+ {
+ wakeup(_wakeup[1]);
+ }
+
+ /// Global wakeup - signal safe: wakeup all socket polls.
+ static void wakeupWorld()
+ {
+ for (const auto& fd : _pollWakeups)
+ wakeup(fd);
+ }
+
/// Insert a new socket to be polled.
/// Sockets are removed only when the handler return false.
void insertNewSocket(const std::shared_ptr<Socket>& newSocket)
diff --git a/test/Makefile.am b/test/Makefile.am
index d849f13..1785d62 100644
--- a/test/Makefile.am
+++ b/test/Makefile.am
@@ -39,7 +39,8 @@ wsd_sources = \
../kit/Kit.cpp \
../wsd/TileCache.cpp \
../common/Unit.cpp \
- ../common/Util.cpp
+ ../common/Util.cpp \
+ ../net/Socket.cpp
unittest_CPPFLAGS = -I$(top_srcdir) -DBUILDING_TESTS
unittest_SOURCES = TileQueueTests.cpp WhiteBoxTests.cpp test.cpp $(wsd_sources)
More information about the Libreoffice-commits
mailing list