[Libreoffice-commits] online.git: Branch 'private/tml/cancellation' - 3 commits - loolwsd/LoadTest.cpp loolwsd/LOOLSession.cpp loolwsd/LOOLSession.hpp loolwsd/LOOLWSD.cpp loolwsd/protocol.txt

Tor Lillqvist tml at collabora.com
Tue Jun 9 08:05:27 PDT 2015


 loolwsd/LOOLSession.cpp |    8 ++++++-
 loolwsd/LOOLSession.hpp |    4 +--
 loolwsd/LOOLWSD.cpp     |   54 +++++++++++++++++++++++++++++++++++++-----------
 loolwsd/LoadTest.cpp    |   15 +++++++++----
 loolwsd/protocol.txt    |    2 -
 5 files changed, 63 insertions(+), 20 deletions(-)

New commits:
commit e6ac9891fb2ef392715c8dab95017561ad846c17
Author: Tor Lillqvist <tml at collabora.com>
Date:   Tue Jun 9 18:04:46 2015 +0300

    Use a queue also in the child processes

diff --git a/loolwsd/LOOLSession.cpp b/loolwsd/LOOLSession.cpp
index 159955b..9da6244 100644
--- a/loolwsd/LOOLSession.cpp
+++ b/loolwsd/LOOLSession.cpp
@@ -239,7 +239,8 @@ bool MasterProcessSession::handleInput(const char *buffer, int length)
         }
         return loadDocument(buffer, length, tokens);
     }
-    else if (tokens[0] != "invalidatetiles" &&
+    else if (tokens[0] != "canceltiles" &&
+             tokens[0] != "invalidatetiles" &&
              tokens[0] != "key" &&
              tokens[0] != "mouse" &&
              tokens[0] != "resetselection" &&
@@ -258,6 +259,11 @@ bool MasterProcessSession::handleInput(const char *buffer, int length)
         sendTextFrame("error: cmd=" + tokens[0] + " kind=nodocloaded");
         return false;
     }
+    else if (tokens[0] == "canceltiles")
+    {
+        if (!_peer.expired())
+            forwardToPeer(buffer, length);
+    }
     else if (tokens[0] == "invalidatetiles")
     {
         return invalidateTiles(buffer, length, tokens);
diff --git a/loolwsd/LOOLSession.hpp b/loolwsd/LOOLSession.hpp
index 2fd7d0b..a62012f 100644
--- a/loolwsd/LOOLSession.hpp
+++ b/loolwsd/LOOLSession.hpp
@@ -45,6 +45,8 @@ public:
 
     virtual bool getStatus(const char *buffer, int length) = 0;
 
+    virtual bool handleInput(const char *buffer, int length) = 0;
+
 protected:
     LOOLSession(std::shared_ptr<Poco::Net::WebSocket> ws, Kind kind);
     virtual ~LOOLSession();
@@ -53,8 +55,6 @@ protected:
 
     const Kind _kind;
 
-    virtual bool handleInput(const char *buffer, int length) = 0;
-
     void sendBinaryFrame(const char *buffer, int length);
 
     virtual bool loadDocument(const char *buffer, int length, Poco::StringTokenizer& tokens) = 0;
diff --git a/loolwsd/LOOLWSD.cpp b/loolwsd/LOOLWSD.cpp
index cdced5f..7bbe69c 100644
--- a/loolwsd/LOOLWSD.cpp
+++ b/loolwsd/LOOLWSD.cpp
@@ -121,15 +121,15 @@ using Poco::Util::Option;
 using Poco::Util::OptionSet;
 using Poco::Util::ServerApplication;
 
-class FromClientQueueHandler: public Runnable
+class QueueHandler: public Runnable
 {
 public:
-    FromClientQueueHandler(tsqueue<std::string>& queue):
+    QueueHandler(tsqueue<std::string>& queue):
         _queue(queue)
     {
     }
 
-    void setSession(std::shared_ptr<MasterProcessSession> session)
+    void setSession(std::shared_ptr<LOOLSession> session)
     {
         _session = session;
     }
@@ -147,7 +147,7 @@ public:
     }
 
 private:
-    std::shared_ptr<MasterProcessSession> _session;
+    std::shared_ptr<LOOLSession> _session;
     tsqueue<std::string>& _queue;
 };
 
@@ -173,7 +173,7 @@ public:
 
         tsqueue<std::string> queue;
         Thread queueHandlerThread;
-        FromClientQueueHandler handler(queue);
+        QueueHandler handler(queue);
 
         try
         {
@@ -209,11 +209,11 @@ public:
                     char buffer[100000];
                     n = ws->receiveFrame(buffer, sizeof(buffer), flags);
 
-                    std::string firstLine = getFirstLine(buffer, n);
-                    StringTokenizer tokens(firstLine, " ", StringTokenizer::TOK_IGNORE_EMPTY | StringTokenizer::TOK_TRIM);
-
                     if (n > 0 && (flags & WebSocket::FRAME_OP_BITMASK) != WebSocket::FRAME_OP_CLOSE)
                     {
+                        std::string firstLine = getFirstLine(buffer, n);
+                        StringTokenizer tokens(firstLine, " ", StringTokenizer::TOK_IGNORE_EMPTY | StringTokenizer::TOK_TRIM);
+
                         if (kind == LOOLSession::Kind::ToClient && firstLine.size() == static_cast<std::string::size_type>(n))
                         {
                             // Check if it is a "canceltiles" and in that case remove outstanding
@@ -221,6 +221,9 @@ public:
                             if (tokens.count() == 1 && tokens[0] == "canceltiles")
                             {
                                 queue.remove_if([](std::string& x){ return x.find("tile ") == 0;});
+
+                                // Also forward the "canceltiles" to the child process, if any
+                                session->handleInput(buffer, n);
                             }
                             else
                             {
@@ -747,12 +750,19 @@ int LOOLWSD::childMain()
         HTTPResponse response;
         std::shared_ptr<WebSocket> ws(new WebSocket(cs, request, response));
 
-        ChildProcessSession session(ws, loKit);
+        std::shared_ptr<ChildProcessSession> session(new ChildProcessSession(ws, loKit));
 
         ws->setReceiveTimeout(0);
 
         std::string hello("child " + std::to_string(_childId));
-        session.sendTextFrame(hello);
+        session->sendTextFrame(hello);
+
+        tsqueue<std::string> queue;
+        Thread queueHandlerThread;
+        QueueHandler handler(queue);
+
+        handler.setSession(session);
+        queueHandlerThread.start(handler);
 
         int flags;
         int n;
@@ -762,10 +772,30 @@ int LOOLWSD::childMain()
             n = ws->receiveFrame(buffer, sizeof(buffer), flags);
 
             if (n > 0 && (flags & WebSocket::FRAME_OP_BITMASK) != WebSocket::FRAME_OP_CLOSE)
-                if (!session.handleInput(buffer, n))
-                    n = 0;
+            {
+                std::string firstLine = getFirstLine(buffer, n);
+                StringTokenizer tokens(firstLine, " ", StringTokenizer::TOK_IGNORE_EMPTY | StringTokenizer::TOK_TRIM);
+
+                // The only kind of messages a child process receives are the single-line ones (?)
+                assert(firstLine.size() == static_cast<std::string::size_type>(n));
+
+                // Check if it is a "canceltiles" and in that case remove outstanding
+                // "tile" messages from the queue.
+                if (tokens.count() == 1 && tokens[0] == "canceltiles")
+                {
+                    queue.remove_if([](std::string& x){ return x.find("tile ") == 0;});
+                }
+                else
+                {
+                    queue.put(firstLine);
+                }
+            }
         }
         while (n > 0 && (flags & WebSocket::FRAME_OP_BITMASK) != WebSocket::FRAME_OP_CLOSE);
+
+        queue.clear();
+        queue.put("eof");
+        queueHandlerThread.join();
     }
     catch (Exception& exc)
     {
commit 94b80340d9854737c1bfbf7c3f08c87440887de4
Author: Tor Lillqvist <tml at collabora.com>
Date:   Tue Jun 9 17:13:13 2015 +0300

    Log the number of tiles requests and replies

diff --git a/loolwsd/LoadTest.cpp b/loolwsd/LoadTest.cpp
index c0c2eed..c03d581 100644
--- a/loolwsd/LoadTest.cpp
+++ b/loolwsd/LoadTest.cpp
@@ -85,6 +85,7 @@ public:
     {
         int flags;
         int n;
+        int tileCount = 0;
         Application& app = Application::instance();
         try
         {
@@ -117,15 +118,17 @@ public:
                             "Client got " << n << " bytes: " << getAbbreviatedMessage(largeBuffer, n) <<
                             std::endl;
 #endif
-                        // We don't actually need to do anything with the buffer in this program. We
-                        // only parse status: messages and they are not preceded by nextmessage:
-                        // messages.
+                        response = getFirstLine(buffer, n);
                     }
                     if (response.find("status:") == 0)
                     {
                         parseStatus(response, _type, _numParts, _currentPart, _width, _height);
                         _cond.signal();
                     }
+                    else if (response.find("tile:") == 0)
+                    {
+                        tileCount++;
+                    }
                 }
             }
             while (n > 0 && (flags & WebSocket::FRAME_OP_BITMASK) != WebSocket::FRAME_OP_CLOSE);
@@ -135,6 +138,7 @@ public:
             app.logger().error("WebSocketException: " + exc.message());
             _ws.close();
         }
+        std::cout << Util::logPrefix() << "Got " << tileCount << " tiles" << std::endl;
     }
 
     WebSocket& _ws;
@@ -224,6 +228,8 @@ private:
         std::uniform_int_distribution<> dis(0, 20);
         int extra = dis(_g);
 
+        int requestCount = 0;
+
         // Exercise the server with this document for some minutes
         while (!documentStartTimestamp.isElapsed((20 + extra) * Timespan::SECONDS) && !clientDurationExceeded())
         {
@@ -236,6 +242,7 @@ private:
                               "tileposy=" + std::to_string(y * DOCTILESIZE) + " "
                               "tilewidth=" + std::to_string(DOCTILESIZE) + " "
                               "tileheight=" + std::to_string(DOCTILESIZE));
+                requestCount++;
                 x = ((x + 1) % ((output._width-1)/DOCTILESIZE + 1));
                 if (x == 0)
                     break;
@@ -247,7 +254,7 @@ private:
 
         Thread::sleep(10000);
 
-        std::cout << Util::logPrefix() << "Shutting down client for '" << document << "'" << std::endl;
+        std::cout << Util::logPrefix() << "Sent " << requestCount << " tile requests, shutting down client for '" << document << "'" << std::endl;
 
         ws.shutdown();
         thread.join();
commit e05db7057bd74980a114cbe6ef3cc82afab75655
Author: Tor Lillqvist <tml at collabora.com>
Date:   Tue Jun 9 16:09:23 2015 +0300

    Typo

diff --git a/loolwsd/protocol.txt b/loolwsd/protocol.txt
index 655dcba..74af6c3 100644
--- a/loolwsd/protocol.txt
+++ b/loolwsd/protocol.txt
@@ -14,7 +14,7 @@ client -> server
 canceltiles
 
     All outstanding tile messages from the client to the server are
-    dropped and will not be handled. There is no guarantee of exacely
+    dropped and will not be handled. There is no guarantee of exactly
     which tile: messages might still be sent back to the client.
 
 invalidatetiles part=<partNumber> tileposx=<xpos> tileposy=<ypos> tilewidth=<tileWidth> tileheight=<tileHeight>


More information about the Libreoffice-commits mailing list