summaryrefslogtreecommitdiffstats
path: root/common/rfb/VNCSConnectionST.cxx
diff options
context:
space:
mode:
authorPierre Ossman <ossman@cendio.se>2011-11-14 15:54:30 +0000
committerPierre Ossman <ossman@cendio.se>2011-11-14 15:54:30 +0000
commit2c7649422ecd811217bc85b4c493794b217014b7 (patch)
treea61845edec751a4055aa483981bf76d6292b41e0 /common/rfb/VNCSConnectionST.cxx
parentc754cceeca839b7caeca9c62bb2e08688725c458 (diff)
downloadtigervnc-2c7649422ecd811217bc85b4c493794b217014b7.tar.gz
tigervnc-2c7649422ecd811217bc85b4c493794b217014b7.zip
Implement proper support for fences in the server.
git-svn-id: svn://svn.code.sf.net/p/tigervnc/code/trunk@4799 3789f03b-4d11-0410-bbf8-ca57d06f2519
Diffstat (limited to 'common/rfb/VNCSConnectionST.cxx')
-rw-r--r--common/rfb/VNCSConnectionST.cxx57
1 files changed, 56 insertions, 1 deletions
diff --git a/common/rfb/VNCSConnectionST.cxx b/common/rfb/VNCSConnectionST.cxx
index 30d9b6ad..12dcf047 100644
--- a/common/rfb/VNCSConnectionST.cxx
+++ b/common/rfb/VNCSConnectionST.cxx
@@ -22,6 +22,7 @@
#include <rfb/LogWriter.h>
#include <rfb/Security.h>
#include <rfb/screenTypes.h>
+#include <rfb/fenceTypes.h>
#include <rfb/ServerCore.h>
#include <rfb/ComparingUpdateTracker.h>
#include <rfb/KeyRemapper.h>
@@ -35,7 +36,9 @@ static LogWriter vlog("VNCSConnST");
VNCSConnectionST::VNCSConnectionST(VNCServerST* server_, network::Socket *s,
bool reverse)
- : SConnection(reverse), sock(s), inProcessMessages(false), server(server_),
+ : SConnection(reverse), sock(s), inProcessMessages(false),
+ syncFence(false), fenceFlags(0), fenceDataLen(0), fenceData(NULL),
+ server(server_),
updates(false), image_getter(server->useEconomicTranslate),
drawRenderedCursor(false), removeRenderedCursor(false),
updateTimer(this), pointerEventTime(0),
@@ -70,6 +73,7 @@ VNCSConnectionST::~VNCSConnectionST()
// Remove this client from the server
server->clients.remove(this);
+ delete [] fenceData;
}
@@ -121,6 +125,10 @@ void VNCSConnectionST::processMessages()
while (getInStream()->checkNoWait(1)) {
processMsg();
+ if (syncFence) {
+ writer()->writeFence(fenceFlags, fenceDataLen, fenceData);
+ syncFence = false;
+ }
}
// Flush out everything in case we go idle after this.
@@ -566,6 +574,42 @@ void VNCSConnectionST::setInitialColourMap()
setColourMapEntries(0, 0);
}
+void VNCSConnectionST::fence(rdr::U32 flags, unsigned len, const char data[])
+{
+ if (flags & fenceFlagRequest) {
+ if (flags & fenceFlagSyncNext) {
+ if (syncFence)
+ vlog.error("Fence trying to synchronise another fence");
+
+ syncFence = true;
+
+ fenceFlags = flags & (fenceFlagBlockBefore | fenceFlagBlockAfter | fenceFlagSyncNext);
+ fenceDataLen = len;
+ delete [] fenceData;
+ if (len > 0) {
+ fenceData = new char[len];
+ memcpy(fenceData, data, len);
+ }
+
+ return;
+ }
+
+ // We handle everything synchronously so we trivially honor these modes
+ flags = flags & (fenceFlagBlockBefore | fenceFlagBlockAfter);
+
+ writer()->writeFence(flags, len, data);
+ return;
+ }
+
+ switch (len) {
+ case 0:
+ // Initial dummy fence;
+ break;
+ default:
+ vlog.error("Fence response of unexpected size received");
+ }
+}
+
// supportsLocalCursor() is called whenever the status of
// cp.supportsLocalCursor has changed. If the client does now support local
// cursor, we make sure that the old server-side rendered cursor is cleaned up
@@ -581,6 +625,11 @@ void VNCSConnectionST::supportsLocalCursor()
}
}
+void VNCSConnectionST::supportsFence()
+{
+ writer()->writeFence(fenceFlagRequest, 0, NULL);
+}
+
void VNCSConnectionST::writeSetCursorCallback()
{
if (cp.supportsLocalXCursor) {
@@ -642,6 +691,12 @@ void VNCSConnectionST::writeFramebufferUpdate()
{
updateTimer.stop();
+ // We're in the middle of processing a command that's supposed to be
+ // synchronised. Allowing an update to slip out right now might violate
+ // that synchronisation.
+ if (syncFence)
+ return;
+
// We try to aggregate responses, so don't send out anything whilst we
// still have incoming messages. processMessages() will give us another
// chance to run once things are idle.