Makefile.am | 20 ++++++++++---- common/Util.hpp | 2 - common/security.h | 2 + kit/ForKit.cpp | 68 ++++++++++++++++++++++++++++++++++++------------- kit/Kit.cpp | 14 ++++++---- kit/Kit.hpp | 8 +++++ kit/KitHelper.hpp | 1 tools/KitClient.cpp | 1 wsd/DocumentBroker.cpp | 2 + wsd/LOOLWSD.cpp | 28 +++++++++++++++++++- wsd/Storage.cpp | 4 ++ 11 files changed, 118 insertions(+), 32 deletions(-)
New commits: commit 04d7ed9d091c56eac056036a2b7f0a451619a043 Author: Jan Holesovsky <ke...@collabora.com> Date: Mon Feb 6 23:26:38 2017 +0100 fuzzer: Make the shared loolwsd and loolforkit binary actually work. Change-Id: If6ee9f22d93aa040f94df86b30fdc8a0a1ad68e2 diff --git a/common/security.h b/common/security.h index cd4dd0f..eb79f46 100644 --- a/common/security.h +++ b/common/security.h @@ -20,6 +20,7 @@ #define LOOL_USER_ID "lool" +#ifndef KIT_IN_PROCESS static int hasCorrectUID(const char *appName) { #if ENABLE_DEBUG @@ -36,5 +37,6 @@ static int hasCorrectUID(const char *appName) } #endif } +#endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/kit/ForKit.cpp b/kit/ForKit.cpp index 0a27fde..837812c 100644 --- a/kit/ForKit.cpp +++ b/kit/ForKit.cpp @@ -46,7 +46,9 @@ using Poco::StringTokenizer; using Poco::Thread; using Poco::Util::Application; +#ifndef KIT_IN_PROCESS static bool NoCapsForKit = false; +#endif static bool DisplayVersion = false; static std::string UnitTestLibrary; static std::atomic<unsigned> ForkCounter( 0 ); @@ -112,6 +114,7 @@ public: } }; +#ifndef KIT_IN_PROCESS static bool haveCapability(cap_value_t capability) { cap_t caps = cap_get_proc(); @@ -180,6 +183,7 @@ static bool haveCorrectCapabilities() return result; } +#endif /// Check if some previously forked kids have died. static void cleanupChildren() @@ -225,7 +229,9 @@ static int createLibreOfficeKit(const std::string& childRoot, // Close the pipe from loolwsd close(0); +#ifndef KIT_IN_PROCESS UnitKit::get().postFork(); +#endif if (std::getenv("SLEEPKITFORDEBUGGER")) { @@ -239,7 +245,11 @@ static int createLibreOfficeKit(const std::string& childRoot, } } +#ifndef KIT_IN_PROCESS lokit_main(childRoot, sysTemplate, loTemplate, loSubPath, NoCapsForKit, queryVersion, DisplayVersion); +#else + lokit_main(childRoot, sysTemplate, loTemplate, loSubPath, true, queryVersion, DisplayVersion); +#endif } else { @@ -254,12 +264,48 @@ static int createLibreOfficeKit(const std::string& childRoot, childJails[pid] = childRoot + std::to_string(pid); } +#ifndef KIT_IN_PROCESS UnitKit::get().launchedKit(pid); +#endif } return pid; } +void forkLibreOfficeKit(const std::string& childRoot, + const std::string& sysTemplate, + const std::string& loTemplate, + const std::string& loSubPath, + int limit) +{ + // Cleanup first, to reduce disk load. + cleanupChildren(); + +#ifndef KIT_IN_PROCESS + (void) limit; +#else + if (limit > 0) + ForkCounter = limit; +#endif + + if (ForkCounter > 0) + { + // Create as many as requested. + const size_t count = ForkCounter; + LOG_INF("Spawning " << count << " new child" << (count == 1 ? "." : "ren.")); + const size_t retry = count * 2; + for (size_t i = 0; ForkCounter > 0 && i < retry; ++i) + { + if (ForkCounter-- <= 0 || createLibreOfficeKit(childRoot, sysTemplate, loTemplate, loSubPath) < 0) + { + LOG_ERR("Failed to create a kit process."); + ++ForkCounter; + } + } + } +} + +#ifndef KIT_IN_PROCESS static void printArgumentHelp() { std::cout << "Usage: loolforkit [OPTION]..." << std::endl; @@ -269,11 +315,7 @@ static void printArgumentHelp() std::cout << "" << std::endl; } -#ifndef KIT_IN_PROCESS int main(int argc, char** argv) -#else -int loolforkit_main(int argc, char** argv) -#endif { if (!hasCorrectUID("loolforkit")) { @@ -313,7 +355,7 @@ int loolforkit_main(int argc, char** argv) std::string sysTemplate; std::string loTemplate; -#if ENABLE_DEBUG && !defined(KIT_IN_PROCESS) +#if ENABLE_DEBUG static const char* clientPort = std::getenv("LOOL_TEST_CLIENT_PORT"); if (clientPort) ClientPortNumber = std::stoi(clientPort); @@ -346,7 +388,6 @@ int loolforkit_main(int argc, char** argv) eq = std::strchr(cmd, '='); childRoot = std::string(eq+1); } -#ifndef KIT_IN_PROCESS else if (std::strstr(cmd, "--clientport=") == cmd) { eq = std::strchr(cmd, '='); @@ -357,7 +398,6 @@ int loolforkit_main(int argc, char** argv) eq = std::strchr(cmd, '='); MasterPortNumber = std::stoll(std::string(eq+1)); } -#endif else if (std::strstr(cmd, "--version") == cmd) { std::string version, hash; @@ -428,24 +468,7 @@ int loolforkit_main(int argc, char** argv) break; } - // Cleanup first, to reduce disk load. - cleanupChildren(); - - if (ForkCounter > 0) - { - // Create as many as requested. - const size_t count = ForkCounter; - LOG_INF("Spawning " << count << " new child" << (count == 1 ? "." : "ren.")); - const size_t retry = count * 2; - for (size_t i = 0; ForkCounter > 0 && i < retry; ++i) - { - if (ForkCounter-- <= 0 || createLibreOfficeKit(childRoot, sysTemplate, loTemplate, loSubPath) < 0) - { - LOG_ERR("Failed to create a kit process."); - ++ForkCounter; - } - } - } + forkLibreOfficeKit(childRoot, sysTemplate, loTemplate, loSubPath); } int returnValue = Application::EXIT_OK; @@ -459,5 +482,6 @@ int loolforkit_main(int argc, char** argv) LOG_INF("ForKit process finished."); std::_Exit(returnValue); } +#endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/kit/Kit.cpp b/kit/Kit.cpp index 6ca6769..29fc24f 100644 --- a/kit/Kit.cpp +++ b/kit/Kit.cpp @@ -1712,7 +1712,11 @@ void lokit_main(const std::string& childRoot, { const char *instdir = instdir_path.c_str(); const char *userdir = userdir_url.c_str(); - auto kit = UnitKit::get().lok_init(instdir, userdir); +#ifndef KIT_IN_PROCESS + LibreOfficeKit* kit = UnitKit::get().lok_init(instdir, userdir); +#else + LibreOfficeKit* kit = nullptr; +#endif if (!kit) { kit = (initFunction ? initFunction(instdir, userdir) : lok_init_2(instdir, userdir)); @@ -1758,10 +1762,12 @@ void lokit_main(const std::string& childRoot, { std::string message(data.data(), data.size()); +#ifndef KIT_IN_PROCESS if (UnitKit::get().filterKitMessage(ws, message)) { return true; } +#endif LOG_DBG(socketName << ": recv [" << LOOLProtocol::getAbbreviatedMessage(message) << "]."); StringTokenizer tokens(message, " ", StringTokenizer::TOK_IGNORE_EMPTY | StringTokenizer::TOK_TRIM); diff --git a/kit/Kit.hpp b/kit/Kit.hpp index 8431d76..a1b97c6 100644 --- a/kit/Kit.hpp +++ b/kit/Kit.hpp @@ -40,6 +40,14 @@ struct UserInfo std::string username; }; +/// Check the ForkCounter, and if non-zero, fork more of them accordingly. +/// @param limit If non-zero, set the ForkCounter to this limit. +void forkLibreOfficeKit(const std::string& childRoot, + const std::string& sysTemplate, + const std::string& loTemplate, + const std::string& loSubPath, + int limit = 0); + #endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/wsd/DocumentBroker.cpp b/wsd/DocumentBroker.cpp index 59453a8..f37152c 100644 --- a/wsd/DocumentBroker.cpp +++ b/wsd/DocumentBroker.cpp @@ -223,10 +223,12 @@ bool DocumentBroker::load(std::shared_ptr<ClientSession>& session, const std::st // user/doc/jailId const auto jailPath = Poco::Path(JAILED_DOCUMENT_ROOT, jailId); std::string jailRoot = getJailRoot(); +#ifndef KIT_IN_PROCESS if (LOOLWSD::NoCapsForKit) { jailRoot = jailPath.toString() + "/" + getJailRoot(); } +#endif LOG_INF("jailPath: " << jailPath.toString() << ", jailRoot: " << jailRoot); diff --git a/wsd/LOOLWSD.cpp b/wsd/LOOLWSD.cpp index 78bb6ef..65335c7 100644 --- a/wsd/LOOLWSD.cpp +++ b/wsd/LOOLWSD.cpp @@ -117,6 +117,10 @@ #include "common/FileUtil.hpp" #include <LOOLWebSocket.hpp> +#ifdef KIT_IN_PROCESS +#include <Kit.hpp> +#endif + #include "common/SigUtil.hpp" using namespace LOOLProtocol; @@ -323,9 +327,13 @@ static bool forkChildren(const int number) alertAllUsersInternal("error: cmd=internal kind=diskfull"); } +#ifdef KIT_IN_PROCESS + forkLibreOfficeKit(LOOLWSD::ChildRoot, LOOLWSD::SysTemplate, LOOLWSD::LoTemplate, LO_JAIL_SUBPATH, number); +#else const std::string aMessage = "spawn " + std::to_string(number) + "\n"; LOG_DBG("MasterToForKit: " << aMessage.substr(0, aMessage.length() - 1)); if (IoUtil::writeToPipe(LOOLWSD::ForKitWritePipe, aMessage) > 0) +#endif { OutstandingForks += number; LastForkRequestTime = std::chrono::steady_clock::now(); @@ -1682,9 +1690,11 @@ inline std::string getAdminURI(const Poco::Util::LayeredConfiguration &config) } // anonymous namespace std::atomic<unsigned> LOOLWSD::NextSessionId; +#ifndef KIT_IN_PROCESS std::atomic<int> LOOLWSD::ForKitWritePipe(-1); std::atomic<int> LOOLWSD::ForKitProcId(-1); bool LOOLWSD::NoCapsForKit = false; +#endif std::string LOOLWSD::Cache = LOOLWSD_CACHEDIR; std::string LOOLWSD::SysTemplate; std::string LOOLWSD::LoTemplate; @@ -2098,8 +2108,10 @@ void LOOLWSD::handleOption(const std::string& optionName, #if ENABLE_DEBUG else if (optionName == "unitlib") UnitTestLibrary = value; +#ifndef KIT_IN_PROCESS else if (optionName == "nocaps") NoCapsForKit = true; +#endif else if (optionName == "careerspan") careerSpanSeconds = std::stoi(value); @@ -2124,6 +2136,9 @@ void LOOLWSD::displayHelp() bool LOOLWSD::checkAndRestoreForKit() { +#ifdef KIT_IN_PROCESS + return false; +#else int status; const pid_t pid = waitpid(ForKitProcId, &status, WUNTRACED | WNOHANG); if (pid > 0) @@ -2190,10 +2205,14 @@ bool LOOLWSD::checkAndRestoreForKit() } return false; +#endif } bool LOOLWSD::createForKit() { +#ifdef KIT_IN_PROCESS + return true; +#else LOG_INF("Creating new forkit process."); Process::Args args; @@ -2258,6 +2277,7 @@ bool LOOLWSD::createForKit() preForkChildren(newChildrenLock); return (ForKitProcId != -1); +#endif } int LOOLWSD::main(const std::vector<std::string>& /*args*/) @@ -2396,7 +2416,6 @@ int LOOLWSD::main(const std::vector<std::string>& /*args*/) #endif auto last30SecCheckTime = std::chrono::steady_clock::now(); - int status = 0; while (!TerminationFlag && !SigUtil::isShuttingDown()) { UnitWSD::get().invokeTest(); @@ -2464,9 +2483,11 @@ int LOOLWSD::main(const std::vector<std::string>& /*args*/) LOG_INF("Cleaning up lingering documents."); DocBrokers.clear(); +#ifndef KIT_IN_PROCESS // Terminate child processes LOG_INF("Requesting forkit process " << ForKitProcId << " to terminate."); SigUtil::killChild(ForKitProcId); +#endif // Terminate child processes LOG_INF("Requesting child processes to terminate."); @@ -2475,9 +2496,12 @@ int LOOLWSD::main(const std::vector<std::string>& /*args*/) child->close(true); } +#ifndef KIT_IN_PROCESS // Wait for forkit process finish. + int status = 0; waitpid(ForKitProcId, &status, WUNTRACED); close(ForKitWritePipe); +#endif // In case forkit didn't cleanup properly, don't leave jails behind. LOG_INF("Cleaning up childroot directory [" << ChildRoot << "]."); diff --git a/wsd/Storage.cpp b/wsd/Storage.cpp index d7a7119..d4e5709 100644 --- a/wsd/Storage.cpp +++ b/wsd/Storage.cpp @@ -248,7 +248,11 @@ std::string LocalStorage::loadStorageFileToLocal() _isLoaded = true; // Now return the jailed path. +#ifndef KIT_IN_PROCESS return Poco::Path(_jailPath, filename).toString(); +#else + return _jailedFilePath; +#endif } StorageBase::SaveResult LocalStorage::saveLocalFileToStorage(const Poco::URI& uriPublic) commit 0dac1c4321b7c0b82ee377b9b9d3ff01c33ff1cd Author: Jan Holesovsky <ke...@collabora.com> Date: Mon Feb 6 15:59:14 2017 +0100 fuzzer: Compile a separate binary that contains both loolwsd and loolforkit. Change-Id: I158e4b19d0929de03f09645c106aebfdbc44ea74 diff --git a/Makefile.am b/Makefile.am index 8a08027..e4a2af1 100644 --- a/Makefile.am +++ b/Makefile.am @@ -2,7 +2,7 @@ SUBDIRS = . test loleaflet export ENABLE_DEBUG -bin_PROGRAMS = loolwsd loolforkit loolmap loolmount looltool loolstress +bin_PROGRAMS = loolwsd loolforkit loolwsd_fuzzer loolmap loolmount looltool loolstress dist_bin_SCRIPTS = loolwsd-systemplate-setup @@ -32,6 +32,8 @@ AM_LDFLAGS = -pthread -Wl,-E loolforkit_LDFLAGS = -pthread -Wl,-E,-rpath,/snap/loolwsd/current/usr/lib loolmount_LDFLAGS = -pthread -Wl,-E,-rpath,/snap/loolwsd/current/usr/lib +loolwsd_fuzzer_CPPFLAGS = -DKIT_IN_PROCESS=1 $(AM_CPPFLAGS) + AM_ETAGSFLAGS = --c++-kinds=+p --fields=+iaS --extra=+q -R --totals=yes * AM_CTAGSFLAGS = $(AM_ETAGSFLAGS) @@ -47,7 +49,7 @@ shared_sources = common/FileUtil.cpp \ common/UnitHTTP.cpp \ common/Util.cpp -loolwsd_SOURCES = wsd/Admin.cpp \ +loolwsd_sources = wsd/Admin.cpp \ wsd/AdminModel.cpp \ wsd/Auth.cpp \ wsd/DocumentBroker.cpp \ @@ -55,7 +57,9 @@ loolwsd_SOURCES = wsd/Admin.cpp \ wsd/ClientSession.cpp \ wsd/FileServer.cpp \ wsd/Storage.cpp \ - wsd/TileCache.cpp \ + wsd/TileCache.cpp + +loolwsd_SOURCES = $(loolwsd_sources) \ $(shared_sources) noinst_PROGRAMS = connect \ @@ -73,11 +77,17 @@ lokitclient_SOURCES = common/IoUtil.cpp \ common/Protocol.cpp \ common/Util.cpp -loolforkit_SOURCES = kit/ChildSession.cpp \ +loolforkit_sources = kit/ChildSession.cpp \ kit/ForKit.cpp \ - kit/Kit.cpp \ + kit/Kit.cpp + +loolforkit_SOURCES = $(loolforkit_sources) \ $(shared_sources) +loolwsd_fuzzer_SOURCES = $(loolwsd_sources) \ + $(loolforkit_sources) \ + $(shared_sources) + # build a binary with no caps to help debugging loolforkit_nocaps_SOURCES = $(loolforkit_SOURCES) diff --git a/common/Util.hpp b/common/Util.hpp index ad0fea8..9fae42b 100644 --- a/common/Util.hpp +++ b/common/Util.hpp @@ -46,7 +46,7 @@ namespace Util bool windowingAvailable(); -#ifndef BUILDING_TESTS +#if !defined(BUILDING_TESTS) && !defined(KIT_IN_PROCESS) /// Send a message to all clients. void alertAllUsers(const std::string& msg); diff --git a/kit/ForKit.cpp b/kit/ForKit.cpp index b6383a8..0a27fde 100644 --- a/kit/ForKit.cpp +++ b/kit/ForKit.cpp @@ -53,8 +53,10 @@ static std::atomic<unsigned> ForkCounter( 0 ); static std::map<Process::PID, std::string> childJails; +#ifndef KIT_IN_PROCESS int ClientPortNumber = DEFAULT_CLIENT_PORT_NUMBER; int MasterPortNumber = DEFAULT_MASTER_PORT_NUMBER; +#endif /// Dispatcher class to demultiplex requests from /// WSD and handles them. @@ -267,7 +269,11 @@ static void printArgumentHelp() std::cout << "" << std::endl; } +#ifndef KIT_IN_PROCESS int main(int argc, char** argv) +#else +int loolforkit_main(int argc, char** argv) +#endif { if (!hasCorrectUID("loolforkit")) { @@ -307,7 +313,7 @@ int main(int argc, char** argv) std::string sysTemplate; std::string loTemplate; -#if ENABLE_DEBUG +#if ENABLE_DEBUG && !defined(KIT_IN_PROCESS) static const char* clientPort = std::getenv("LOOL_TEST_CLIENT_PORT"); if (clientPort) ClientPortNumber = std::stoi(clientPort); @@ -340,6 +346,7 @@ int main(int argc, char** argv) eq = std::strchr(cmd, '='); childRoot = std::string(eq+1); } +#ifndef KIT_IN_PROCESS else if (std::strstr(cmd, "--clientport=") == cmd) { eq = std::strchr(cmd, '='); @@ -350,6 +357,7 @@ int main(int argc, char** argv) eq = std::strchr(cmd, '='); MasterPortNumber = std::stoll(std::string(eq+1)); } +#endif else if (std::strstr(cmd, "--version") == cmd) { std::string version, hash; diff --git a/kit/Kit.cpp b/kit/Kit.cpp index b527fda..6ca6769 100644 --- a/kit/Kit.cpp +++ b/kit/Kit.cpp @@ -1930,11 +1930,10 @@ bool globalPreinit(const std::string &loTemplate) return true; } +#if !defined(BUILDING_TESTS) && !defined(KIT_IN_PROCESS) namespace Util { -#ifndef BUILDING_TESTS - void alertAllUsers(const std::string& msg) { document->sendTextFrame(msg); @@ -1945,8 +1944,7 @@ void alertAllUsers(const std::string& cmd, const std::string& kind) alertAllUsers("errortoall: cmd=" + cmd + " kind=" + kind); } -#endif - } +#endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/wsd/LOOLWSD.cpp b/wsd/LOOLWSD.cpp index 9e30ee1..78bb6ef 100644 --- a/wsd/LOOLWSD.cpp +++ b/wsd/LOOLWSD.cpp @@ -2541,6 +2541,7 @@ void UnitWSD::testHandleRequest(TestRequest type, UnitHTTPServerRequest& request } } +#if !defined(BUILDING_TESTS) && !defined(KIT_IN_PROCESS) namespace Util { @@ -2557,6 +2558,7 @@ void alertAllUsers(const std::string& msg) } } +#endif POCO_SERVER_MAIN(LOOLWSD) commit 02e118387a084918b8b68a5feb03e7baa76c7a14 Author: Jan Holesovsky <ke...@collabora.com> Date: Mon Feb 6 14:30:40 2017 +0100 Avoid including LibreOfficeKit.h. Change-Id: I112b79790839352ffd0d82394ffc7e2d8e8dcf44 diff --git a/kit/KitHelper.hpp b/kit/KitHelper.hpp index 038a386..19c36f3 100644 --- a/kit/KitHelper.hpp +++ b/kit/KitHelper.hpp @@ -14,7 +14,6 @@ #include <string> #define LOK_USE_UNSTABLE_API -#include <LibreOfficeKit/LibreOfficeKit.h> #include <LibreOfficeKit/LibreOfficeKitEnums.h> namespace LOKitHelper diff --git a/tools/KitClient.cpp b/tools/KitClient.cpp index 33eec54..5066386 100644 --- a/tools/KitClient.cpp +++ b/tools/KitClient.cpp @@ -15,7 +15,6 @@ #include <memory> #define LOK_USE_UNSTABLE_API -#include <LibreOfficeKit/LibreOfficeKit.h> #include <LibreOfficeKit/LibreOfficeKitInit.h> #include <Poco/Buffer.h> _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits