Skip to content

Commit

Permalink
cool#9989: Only render invisible combined-tiles if IDLE
Browse files Browse the repository at this point in the history
As an attempt to increase responsiveness for client,
we only send invisible requested combined-tiles if IDLE.
IDLE is determined if socket poll timed out, i.e. nothing else to do for client.

Signed-off-by: Sven Göthel <sven.gothel@collabora.com>
Change-Id: Ic71b03747e57976ce4ac69a5f97a015d5d210648
  • Loading branch information
Sven Göthel committed Oct 17, 2024
1 parent 5d45ec5 commit 885977b
Show file tree
Hide file tree
Showing 4 changed files with 60 additions and 21 deletions.
70 changes: 51 additions & 19 deletions kit/Kit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2300,7 +2300,7 @@ void Document::drainCallbacks()
_websocketHandler->flush();
}

void Document::drainQueue()
void Document::drainQueue(bool isIDLE)
{
if (UnitKit::get().filterDrainQueue())
{
Expand Down Expand Up @@ -2369,11 +2369,34 @@ void Document::drainQueue()
{
std::vector<TileCombined> tileRequests = _queue->popWholeTileQueue();

// Put requests that include tiles in the visible area to the front to handle those first
std::partition(tileRequests.begin(), tileRequests.end(), [this](const TileCombined& req) {
return isTileRequestInsideVisibleArea(req); });
for (auto& tileCombined : tileRequests)
renderTiles(tileCombined);
if(isIDLE)
{
// Put requests that include tiles in the visible area to the front to handle those first
std::partition(tileRequests.begin(), tileRequests.end(), [this](const TileCombined& req) {
return isTileRequestInsideVisibleArea(req); });
for (auto& tileCombined : tileRequests)
renderTiles(tileCombined);

LOG_TRC("Kit TileCombined Items: " << tileRequests.size());
}
else
{
// Limited time left, push-back all invisible tile-requests
size_t invisibleCount = 0;
for(TileCombined& tileCombined : tileRequests)
{
if( isTileRequestInsideVisibleArea(tileCombined) )
{
renderTiles(tileCombined);
} else {
++invisibleCount;
_queue->pushTileQueue(tileCombined.getTiles());
}
}
LOG_TRC("Kit TileCombined Items: " << tileRequests.size()
<< ", invisible " << invisibleCount << " "
<< 100.0f * (float)invisibleCount / (float)tileRequests.size() << "%");
}
}
}
catch (const std::exception& exc)
Expand Down Expand Up @@ -2742,12 +2765,12 @@ std::shared_ptr<KitSocketPoll> KitSocketPoll::create() // static
}

// process pending message-queue events.
void KitSocketPoll::drainQueue()
void KitSocketPoll::drainQueue(bool isIDLE)
{
SigUtil::checkDumpGlobalState(dump_kit_state);

if (_document)
_document->drainQueue();
_document->drainQueue(isIDLE);
}

// called from inside poll, inside a wakeup
Expand Down Expand Up @@ -2798,10 +2821,10 @@ int KitSocketPoll::kitPoll(int timeoutMicroS)
int maxExtraEvents = 15;
int eventsSignalled = 0;

auto startTime = std::chrono::steady_clock::now();
std::chrono::steady_clock::time_point startTime = std::chrono::steady_clock::now();

// handle processtoidle waiting optimization
bool checkForIdle = ProcessToIdleDeadline >= startTime;
const bool checkForIdle = ProcessToIdleDeadline >= startTime;

if (timeoutMicroS < 0)
{
Expand All @@ -2822,15 +2845,24 @@ int KitSocketPoll::kitPoll(int timeoutMicroS)
if (_document && _document->needsQuickPoll())
realTimeout = 0;

if (poll(std::chrono::microseconds(realTimeout)) <= 0)
const int rc = poll(std::chrono::microseconds(realTimeout));
if(rc > 0)
{
// poll successful w/o timeout, i.e. !IDLE client activity
const auto now = std::chrono::steady_clock::now();
timeoutMicroS =
std::chrono::duration_cast<std::chrono::microseconds>(_pollEnd - now).count();
++eventsSignalled;
drainQueue(/*isIDLE=*/false);
}
else if(rc == 0)
{
// poll timed out, i.e. IDLE client in-activity
timeoutMicroS = 0;
drainQueue(/*isIDLE=*/realTimeout>0);
}
else // poll error
break;

const auto now = std::chrono::steady_clock::now();
drainQueue();

timeoutMicroS =
std::chrono::duration_cast<std::chrono::microseconds>(_pollEnd - now).count();
++eventsSignalled;
} while (timeoutMicroS > 0 && !SigUtil::getTerminationFlag() && maxExtraEvents-- > 0);
}

Expand All @@ -2849,7 +2881,7 @@ int KitSocketPoll::kitPoll(int timeoutMicroS)
LOG_TRC("Poll of would not close gap - continuing");
}

drainQueue();
drainQueue(/*isIDLE=*/false);

if (_document)
_document->trimAfterInactivity();
Expand Down
4 changes: 2 additions & 2 deletions kit/Kit.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ class KitSocketPoll final : public SocketPoll

public:
~KitSocketPoll();
void drainQueue();
void drainQueue(bool isIDLE);

static void dumpGlobalState(std::ostream& oss);
static std::shared_ptr<KitSocketPoll> create();
Expand Down Expand Up @@ -349,7 +349,7 @@ class Document final : public std::enable_shared_from_this<Document>

// poll is idle, are we ?
void checkIdle();
void drainQueue();
void drainQueue(bool isIDLE);
void drainCallbacks();

void dumpState(std::ostream& oss);
Expand Down
6 changes: 6 additions & 0 deletions kit/KitQueue.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -640,6 +640,12 @@ void KitQueue::pushTileQueue(const Payload &value)
_tileQueue.push_back(desc);
}

void KitQueue::pushTileQueue(const std::vector<TileDesc>& tiles)
{
for(const TileDesc desc : tiles)
_tileQueue.push_back(desc);
}

std::string KitQueue::combineRemoveText(const StringVector& tokens)
{
std::string id;
Expand Down
1 change: 1 addition & 0 deletions kit/KitQueue.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,7 @@ class KitQueue
/// Tiles are special manage a separate queue of them
void clearTileQueue() { _tileQueue.clear(); }
void pushTileQueue(const Payload &value);
void pushTileQueue(const std::vector<TileDesc>& tiles);
void pushTileCombineRequest(const Payload &value);
TileCombined popTileQueue();
std::vector<TileCombined> popWholeTileQueue();
Expand Down

0 comments on commit 885977b

Please sign in to comment.