浏览代码

Minimal server side implementation of the extended desktop size protocol.


git-svn-id: svn://svn.code.sf.net/p/tigervnc/code/trunk@3698 3789f03b-4d11-0410-bbf8-ca57d06f2519
tags/v0.0.90
Pierre Ossman 15 年前
父节点
当前提交
c5e25601d9

+ 7
- 2
common/rfb/ConnParams.cxx 查看文件

@@ -29,8 +29,10 @@ using namespace rfb;
ConnParams::ConnParams()
: majorVersion(0), minorVersion(0), tightExtensionsEnabled(false),
width(0), height(0), useCopyRect(false),
supportsLocalCursor(false), supportsLocalXCursor(false), supportsDesktopResize(true), supportsDesktopRename(false),
supportsLastRect(false), customCompressLevel(false), compressLevel(6),
supportsLocalCursor(false), supportsLocalXCursor(false),
supportsDesktopResize(false), supportsExtendedDesktopSize(false),
supportsDesktopRename(false), supportsLastRect(false),
customCompressLevel(false), compressLevel(6),
noJpeg(false), qualityLevel(-1),
name_(0), nEncodings_(0), encodings_(0),
currentEncoding_(encodingRaw), verStrPos(0)
@@ -92,6 +94,7 @@ void ConnParams::setEncodings(int nEncodings, const rdr::U32* encodings)
useCopyRect = false;
supportsLocalCursor = false;
supportsDesktopResize = false;
supportsExtendedDesktopSize = false;
supportsLocalXCursor = false;
supportsLastRect = false;
customCompressLevel = false;
@@ -111,6 +114,8 @@ void ConnParams::setEncodings(int nEncodings, const rdr::U32* encodings)
supportsLocalXCursor = true;
else if (encodings[i] == pseudoEncodingDesktopSize)
supportsDesktopResize = true;
else if (encodings[i] == pseudoEncodingExtendedDesktopSize)
supportsExtendedDesktopSize = true;
else if (encodings[i] == pseudoEncodingDesktopName)
supportsDesktopRename = true;
else if (encodings[i] == pseudoEncodingLastRect)

+ 1
- 0
common/rfb/ConnParams.h 查看文件

@@ -73,6 +73,7 @@ namespace rfb {
bool supportsLocalCursor;
bool supportsLocalXCursor;
bool supportsDesktopResize;
bool supportsExtendedDesktopSize;
bool supportsDesktopRename;
bool supportsLastRect;


+ 4
- 2
common/rfb/SMsgHandler.cxx 查看文件

@@ -43,11 +43,13 @@ void SMsgHandler::setEncodings(int nEncodings, rdr::U32* encodings)
supportsLocalCursor();
}

void SMsgHandler::framebufferUpdateRequest(const Rect& r, bool incremental)
void SMsgHandler::supportsLocalCursor()
{
}

void SMsgHandler::supportsLocalCursor()
void SMsgHandler::setDesktopSize(int fb_width, int fb_height)
{
cp.width = fb_width;
cp.height = fb_height;
}


+ 4
- 3
common/rfb/SMsgHandler.h 查看文件

@@ -38,14 +38,15 @@ namespace rfb {

// The following methods are called as corresponding messages are read. A
// derived class should override these methods as desired. Note that for
// the setPixelFormat() and setEncodings() methods, a derived class must
// call on to SMsgHandler's methods.
// the setPixelFormat(), setEncodings() and setDesktopSize() methods, a
// derived class must call on to SMsgHandler's methods.

virtual void clientInit(bool shared);

virtual void setPixelFormat(const PixelFormat& pf);
virtual void setEncodings(int nEncodings, rdr::U32* encodings);
virtual void framebufferUpdateRequest(const Rect& r, bool incremental);
virtual void framebufferUpdateRequest(const Rect& r, bool incremental) = 0;
virtual void setDesktopSize(int fb_width, int fb_height) = 0;

// InputHandler interface
// The InputHandler methods will be called for the corresponding messages.

+ 22
- 0
common/rfb/SMsgReaderV3.cxx 查看文件

@@ -1,4 +1,5 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
* Copyright 2009 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -51,9 +52,30 @@ void SMsgReaderV3::readMsg()
case msgTypeKeyEvent: readKeyEvent(); break;
case msgTypePointerEvent: readPointerEvent(); break;
case msgTypeClientCutText: readClientCutText(); break;
case msgTypeSetDesktopSize: readSetDesktopSize(); break;

default:
fprintf(stderr, "unknown message type %d\n", msgType);
throw Exception("unknown message type");
}
}

void SMsgReaderV3::readSetDesktopSize()
{
int width, height;
int screens, i;

is->skip(1);

width = is->readU16();
height = is->readU16();

screens = is->readU8();
is->skip(1);

// XXX: We don't support this command properly yet
is->skip(screens * 16);

handler->setDesktopSize(width, height);
}


+ 3
- 0
common/rfb/SMsgReaderV3.h 查看文件

@@ -1,4 +1,5 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
* Copyright 2009 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -27,6 +28,8 @@ namespace rfb {
virtual ~SMsgReaderV3();
virtual void readClientInit();
virtual void readMsg();
protected:
virtual void readSetDesktopSize();
};
}
#endif

+ 3
- 0
common/rfb/SMsgWriter.h 查看文件

@@ -24,6 +24,7 @@

#include <rdr/types.h>
#include <rfb/encodings.h>
#include <rfb/screenTypes.h>
#include <rfb/Encoder.h>
#include <rfb/PixelBuffer.h>

@@ -74,6 +75,8 @@ namespace rfb {
// writeSetDesktopSize() on a V3 writer won't actually write immediately,
// but will write the relevant pseudo-rectangle as part of the next update.
virtual bool writeSetDesktopSize()=0;
// Same thing for the extended version
virtual bool writeExtendedDesktopSize(rdr::U16 error = resultUnsolicited)=0;

virtual bool writeSetDesktopName()=0;


+ 57
- 0
common/rfb/SMsgWriterV3.cxx 查看文件

@@ -1,4 +1,5 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
* Copyright 2009 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -18,6 +19,7 @@
#include <rdr/OutStream.h>
#include <rdr/MemOutStream.h>
#include <rfb/msgTypes.h>
#include <rfb/screenTypes.h>
#include <rfb/Exception.h>
#include <rfb/ConnParams.h>
#include <rfb/SMsgWriterV3.h>
@@ -64,6 +66,15 @@ bool SMsgWriterV3::writeSetDesktopSize() {
return true;
}

bool SMsgWriterV3::writeExtendedDesktopSize(rdr::U16 error) {
if (!cp->supportsExtendedDesktopSize) return false;
if (error == resultUnsolicited)
needExtendedDesktopSize = true;
else
edsErrors.push_back(error);
return true;
}

bool SMsgWriterV3::writeSetDesktopName() {
if (!cp->supportsDesktopRename) return false;
needSetDesktopName = true;
@@ -124,6 +135,8 @@ void SMsgWriterV3::writeFramebufferUpdateStart(int nRects)
os->pad(1);
if (wsccb) nRects++;
if (needSetDesktopSize) nRects++;
if (needExtendedDesktopSize) nRects++;
if (!edsErrors.empty()) nRects += edsErrors.size();
if (needSetDesktopName) nRects++;
os->writeU16(nRects);
nRectsInUpdate = 0;
@@ -144,6 +157,50 @@ void SMsgWriterV3::writeFramebufferUpdateStart()

void SMsgWriterV3::writeFramebufferUpdateEnd()
{
/* Start with responses to SetDesktopSize messages */
if (!edsErrors.empty()) {
std::list<rdr::U16>::const_iterator iter;

if (!cp->supportsExtendedDesktopSize)
throw Exception("Client does not support extended desktop resize");
if ((nRectsInUpdate += edsErrors.size()) > nRectsInHeader && nRectsInHeader)
throw Exception("SMsgWriterV3 setExtendedDesktopSize: nRects out of sync");

for (iter = edsErrors.begin();iter != edsErrors.end();iter++) {
os->writeU16(1);
os->writeU16(*iter);
os->writeU16(0);
os->writeU16(0);
os->writeU32(pseudoEncodingExtendedDesktopSize);
os->writeU8(0); // # screens
os->pad(3);
}

edsErrors.clear();
}

/* Send this before SetDesktopSize to make life easier on the clients */
if (needExtendedDesktopSize) {
if (!cp->supportsExtendedDesktopSize)
throw Exception("Client does not support extended desktop resize");
if (++nRectsInUpdate > nRectsInHeader && nRectsInHeader)
throw Exception("SMsgWriterV3 setExtendedDesktopSize: nRects out of sync");
os->writeU16(0);
os->writeU16(0);
os->writeU16(cp->width);
os->writeU16(cp->height);
os->writeU32(pseudoEncodingExtendedDesktopSize);
os->writeU8(1); // # screens
os->pad(3);
os->writeU32(1); // id
os->writeU16(0); // x-pos
os->writeU16(0); // y-pos
os->writeU16(cp->width); // width
os->writeU16(cp->height); // height
os->writeU32(0); // flags
needExtendedDesktopSize = false;
}

if (needSetDesktopSize) {
if (!cp->supportsDesktopResize)
throw Exception("Client does not support desktop resize");

+ 6
- 0
common/rfb/SMsgWriterV3.h 查看文件

@@ -1,4 +1,5 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
* Copyright 2009 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -18,6 +19,8 @@
#ifndef __RFB_SMSGWRITERV3_H__
#define __RFB_SMSGWRITERV3_H__

#include <list>

#include <rfb/SMsgWriter.h>

namespace rdr { class MemOutStream; }
@@ -32,6 +35,7 @@ namespace rfb {
virtual void startMsg(int type);
virtual void endMsg();
virtual bool writeSetDesktopSize();
virtual bool writeExtendedDesktopSize(rdr::U16 error);
virtual bool writeSetDesktopName();
virtual void cursorChange(WriteSetCursorCallback* cb);
virtual void writeSetCursor(int width, int height, const Point& hotspot,
@@ -52,6 +56,8 @@ namespace rfb {
int nRectsInHeader;
WriteSetCursorCallback* wsccb;
bool needSetDesktopSize;
bool needExtendedDesktopSize;
std::list<rdr::U16> edsErrors;
bool needSetDesktopName;
bool needLastRect;
};

+ 13
- 1
common/rfb/VNCSConnectionST.cxx 查看文件

@@ -1,4 +1,5 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
* Copyright 2009 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -19,6 +20,7 @@
#include <rfb/VNCSConnectionST.h>
#include <rfb/LogWriter.h>
#include <rfb/secTypes.h>
#include <rfb/screenTypes.h>
#include <rfb/ServerCore.h>
#include <rfb/ComparingUpdateTracker.h>
#include <rfb/KeyRemapper.h>
@@ -168,7 +170,8 @@ void VNCSConnectionST::pixelBufferChange()
cp.width = server->pb->width();
cp.height = server->pb->height();
if (state() == RFBSTATE_NORMAL) {
if (!writer()->writeSetDesktopSize()) {
if (!writer()->writeSetDesktopSize() &&
!writer()->writeExtendedDesktopSize()) {
close("Client does not support desktop resize");
return;
}
@@ -490,9 +493,18 @@ void VNCSConnectionST::framebufferUpdateRequest(const Rect& r,bool incremental)
// Non-incremental update - treat as if area requested has changed
updates.add_changed(reqRgn);
server->comparer->add_changed(reqRgn);
// And update the clients view of screen layout
writer()->writeSetDesktopSize();
writer()->writeExtendedDesktopSize();
}
}

void VNCSConnectionST::setDesktopSize(int fb_width, int fb_height)
{
vlog.info("Rejecting client request to change desktop size");
writer()->writeExtendedDesktopSize(resultProhibited);
}

void VNCSConnectionST::setInitialColourMap()
{
setColourMapEntries(0, 0);

+ 2
- 0
common/rfb/VNCSConnectionST.h 查看文件

@@ -1,4 +1,5 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
* Copyright 2009 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -124,6 +125,7 @@ namespace rfb {
virtual void keyEvent(rdr::U32 key, bool down);
virtual void clientCutText(const char* str, int len);
virtual void framebufferUpdateRequest(const Rect& r, bool incremental);
virtual void setDesktopSize(int fb_width, int fb_height);
virtual void setInitialColourMap();
virtual void supportsLocalCursor();


+ 1
- 0
common/rfb/encodings.h 查看文件

@@ -33,6 +33,7 @@ namespace rfb {
const unsigned int pseudoEncodingXCursor = 0xffffff10;
const unsigned int pseudoEncodingCursor = 0xffffff11;
const unsigned int pseudoEncodingDesktopSize = 0xffffff21;
const unsigned int pseudoEncodingExtendedDesktopSize = 0xfffffecb; // FIXME: Unofficial
const unsigned int pseudoEncodingDesktopName = 0xfffffecdl;

// TightVNC-specific

+ 2
- 0
common/rfb/msgTypes.h 查看文件

@@ -39,5 +39,7 @@ namespace rfb {
const int msgTypeClientCutText = 6;

const int msgTypeEnableContinuousUpdates = 150;

const int msgTypeSetDesktopSize = 251; // FIXME: Unofficial
}
#endif

+ 37
- 0
common/rfb/screenTypes.h 查看文件

@@ -0,0 +1,37 @@
/* Copyright 2009 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
#ifndef __RFB_SCREENTYPES_H__
#define __RFB_SCREENTYPES_H__

namespace rfb {

// Reasons
const unsigned int reasonServer = 0;
const unsigned int reasonClient = 1;
const unsigned int reasonOtherClient = 2;

// Result codes
const unsigned int resultSuccess = 0;
const unsigned int resultProhibited = 1;
const unsigned int resultNoResources = 2;
const unsigned int resultInvalid = 3;

const int resultUnsolicited = 0xffff; // internal code used for server changes

}
#endif

正在加载...
取消
保存