aboutsummaryrefslogtreecommitdiffstats
path: root/common/rfb
diff options
context:
space:
mode:
Diffstat (limited to 'common/rfb')
-rw-r--r--common/rfb/CConnection.cxx2
-rw-r--r--common/rfb/CSecurityTLS.cxx19
-rw-r--r--common/rfb/CSecurityTLS.h2
-rw-r--r--common/rfb/ComparingUpdateTracker.cxx29
-rw-r--r--common/rfb/ComparingUpdateTracker.h5
-rw-r--r--common/rfb/Configuration.cxx19
-rw-r--r--common/rfb/Configuration.h4
-rw-r--r--common/rfb/HTTPServer.h12
-rw-r--r--common/rfb/Hostname.h73
-rw-r--r--common/rfb/KeyRemapper.cxx27
-rw-r--r--common/rfb/KeyRemapper.h6
-rw-r--r--common/rfb/Logger_file.cxx18
-rw-r--r--common/rfb/Logger_file.h3
-rw-r--r--common/rfb/Logger_syslog.cxx1
-rw-r--r--common/rfb/SSecurityTLS.cxx20
-rw-r--r--common/rfb/SSecurityTLS.h2
-rw-r--r--common/rfb/Threading.h31
-rw-r--r--common/rfb/VNCServerST.cxx9
-rw-r--r--common/rfb/VNCServerST.h11
-rw-r--r--common/rfb/ZRLEDecoder.cxx11
-rw-r--r--common/rfb/hextileDecode.h6
-rw-r--r--common/rfb/zrleDecode.h3
22 files changed, 173 insertions, 140 deletions
diff --git a/common/rfb/CConnection.cxx b/common/rfb/CConnection.cxx
index 7e9fd310..35be9468 100644
--- a/common/rfb/CConnection.cxx
+++ b/common/rfb/CConnection.cxx
@@ -86,7 +86,7 @@ void CConnection::setFramebuffer(ModifiablePixelBuffer* fb)
if (fb->width() > framebuffer->width()) {
rect.setXYWH(framebuffer->width(), 0,
- fb->width() - fb->width(),
+ fb->width() - framebuffer->width(),
fb->height());
fb->fillRect(rect, black);
}
diff --git a/common/rfb/CSecurityTLS.cxx b/common/rfb/CSecurityTLS.cxx
index 3dcededb..8a053e3d 100644
--- a/common/rfb/CSecurityTLS.cxx
+++ b/common/rfb/CSecurityTLS.cxx
@@ -67,21 +67,14 @@ StringParameter CSecurityTLS::X509CRL("X509CRL", "X509 CRL file", "", ConfViewer
static LogWriter vlog("TLS");
-void CSecurityTLS::initGlobal()
-{
- static bool globalInitDone = false;
-
- if (!globalInitDone) {
- gnutls_global_init();
- globalInitDone = true;
- }
-}
-
CSecurityTLS::CSecurityTLS(bool _anon) : session(0), anon_cred(0),
anon(_anon), fis(0), fos(0)
{
cafile = X509CA.getData();
crlfile = X509CRL.getData();
+
+ if (gnutls_global_init() != GNUTLS_E_SUCCESS)
+ throw AuthFailureException("gnutls_global_init failed");
}
void CSecurityTLS::setDefaults()
@@ -125,8 +118,6 @@ void CSecurityTLS::shutdown(bool needbye)
if (session) {
gnutls_deinit(session);
session = 0;
-
- gnutls_global_deinit();
}
}
@@ -142,6 +133,8 @@ CSecurityTLS::~CSecurityTLS()
delete[] cafile;
delete[] crlfile;
+
+ gnutls_global_deinit();
}
bool CSecurityTLS::processMsg(CConnection* cc)
@@ -150,8 +143,6 @@ bool CSecurityTLS::processMsg(CConnection* cc)
rdr::OutStream* os = cc->getOutStream();
client = cc;
- initGlobal();
-
if (!session) {
if (!is->checkNoWait(1))
return false;
diff --git a/common/rfb/CSecurityTLS.h b/common/rfb/CSecurityTLS.h
index b147d802..57d964d7 100644
--- a/common/rfb/CSecurityTLS.h
+++ b/common/rfb/CSecurityTLS.h
@@ -62,8 +62,6 @@ namespace rfb {
CConnection *client;
private:
- static void initGlobal();
-
gnutls_session_t session;
gnutls_anon_client_credentials_t anon_cred;
gnutls_certificate_credentials_t cert_cred;
diff --git a/common/rfb/ComparingUpdateTracker.cxx b/common/rfb/ComparingUpdateTracker.cxx
index 1d27f3c4..237adc41 100644
--- a/common/rfb/ComparingUpdateTracker.cxx
+++ b/common/rfb/ComparingUpdateTracker.cxx
@@ -20,12 +20,16 @@
#include <vector>
#include <rdr/types.h>
#include <rfb/Exception.h>
+#include <rfb/LogWriter.h>
#include <rfb/ComparingUpdateTracker.h>
using namespace rfb;
+static LogWriter vlog("ComparingUpdateTracker");
+
ComparingUpdateTracker::ComparingUpdateTracker(PixelBuffer* buffer)
- : fb(buffer), oldFb(fb->getPF(), 0, 0), firstCompare(true), enabled(true)
+ : fb(buffer), oldFb(fb->getPF(), 0, 0), firstCompare(true),
+ enabled(true), totalPixels(0), missedPixels(0)
{
changed.assign_union(fb->getRect());
}
@@ -72,6 +76,13 @@ bool ComparingUpdateTracker::compare()
for (i = rects.begin(); i != rects.end(); i++)
compareRect(*i, &newChanged);
+ changed.get_rects(&rects);
+ for (i = rects.begin(); i != rects.end(); i++)
+ totalPixels += i->area();
+ newChanged.get_rects(&rects);
+ for (i = rects.begin(); i != rects.end(); i++)
+ missedPixels += i->area();
+
if (changed.equals(newChanged))
return false;
@@ -165,3 +176,19 @@ void ComparingUpdateTracker::compareRect(const Rect& r, Region* newChanged)
newChanged->assign_union(temp);
}
}
+
+void ComparingUpdateTracker::logStats()
+{
+ double ratio;
+ char a[1024], b[1024];
+
+ siPrefix(totalPixels, "pixels", a, sizeof(a));
+ siPrefix(missedPixels, "pixels", b, sizeof(b));
+
+ ratio = (double)totalPixels / missedPixels;
+
+ vlog.info("%s in / %s out", a, b);
+ vlog.info("(1:%g ratio)", ratio);
+
+ totalPixels = missedPixels = 0;
+}
diff --git a/common/rfb/ComparingUpdateTracker.h b/common/rfb/ComparingUpdateTracker.h
index fccc2222..e62f2b23 100644
--- a/common/rfb/ComparingUpdateTracker.h
+++ b/common/rfb/ComparingUpdateTracker.h
@@ -40,12 +40,17 @@ namespace rfb {
virtual void enable();
virtual void disable();
+
+ void logStats();
+
private:
void compareRect(const Rect& r, Region* newchanged);
PixelBuffer* fb;
ManagedPixelBuffer oldFb;
bool firstCompare;
bool enabled;
+
+ rdr::U32 totalPixels, missedPixels;
};
}
diff --git a/common/rfb/Configuration.cxx b/common/rfb/Configuration.cxx
index 8e1ea6e9..a5c23028 100644
--- a/common/rfb/Configuration.cxx
+++ b/common/rfb/Configuration.cxx
@@ -23,24 +23,14 @@
#include <ctype.h>
#include <string.h>
+#include <os/Mutex.h>
+
#include <rfb/util.h>
#include <rfb/Configuration.h>
#include <rfb/LogWriter.h>
#include <rfb/Exception.h>
-#include <rfb/Threading.h>
-#ifdef __RFB_THREADING_IMPL
-// On platforms that support Threading, we use Locks to make getData safe
-#define LOCK_CONFIG Lock l(*configLock())
-rfb::Mutex* configLock_ = 0;
-static rfb::Mutex* configLock() {
- if (!configLock_)
- configLock_ = new rfb::Mutex;
- return configLock_;
-}
-#else
-#define LOCK_CONFIG
-#endif
+#define LOCK_CONFIG os::AutoMutex a(mutex)
#include <rdr/HexOutStream.h>
#include <rdr/HexInStream.h>
@@ -195,9 +185,12 @@ VoidParameter::VoidParameter(const char* name_, const char* desc_,
_next = conf->head;
conf->head = this;
+
+ mutex = new os::Mutex();
}
VoidParameter::~VoidParameter() {
+ delete mutex;
}
const char*
diff --git a/common/rfb/Configuration.h b/common/rfb/Configuration.h
index da93fddf..fbf161db 100644
--- a/common/rfb/Configuration.h
+++ b/common/rfb/Configuration.h
@@ -45,6 +45,8 @@
#include <rfb/util.h>
+namespace os { class Mutex; }
+
namespace rfb {
class VoidParameter;
struct ParameterIterator;
@@ -174,6 +176,8 @@ namespace rfb {
bool immutable;
const char* name;
const char* description;
+
+ os::Mutex* mutex;
};
class AliasParameter : public VoidParameter {
diff --git a/common/rfb/HTTPServer.h b/common/rfb/HTTPServer.h
index d7ca69ad..04ef4993 100644
--- a/common/rfb/HTTPServer.h
+++ b/common/rfb/HTTPServer.h
@@ -26,8 +26,6 @@
#ifndef __RFB_HTTP_SERVER_H__
#define __RFB_HTTP_SERVER_H__
-#include <list>
-
#include <rdr/MemInStream.h>
#include <rfb/UpdateTracker.h>
#include <rfb/Configuration.h>
@@ -58,6 +56,10 @@ namespace rfb {
// Could clean up socket-specific resources here.
virtual void removeSocket(network::Socket* sock);
+ // getSockets() gets a list of sockets. This can be used to generate an
+ // fd_set for calling select().
+ virtual void getSockets(std::list<network::Socket*>* sockets);
+
// processSocketReadEvent()
// The platform-specific side of the server implementation calls
// this method whenever data arrives on one of the active
@@ -73,12 +75,6 @@ namespace rfb {
virtual int checkTimeouts();
- // getSockets() gets a list of sockets. This can be used to generate an
- // fd_set for calling select().
-
- virtual void getSockets(std::list<network::Socket*>* sockets);
-
-
// -=- File interface
// - getFile is passed the path portion of a URL and returns an
diff --git a/common/rfb/Hostname.h b/common/rfb/Hostname.h
index f70347f9..bd68dc02 100644
--- a/common/rfb/Hostname.h
+++ b/common/rfb/Hostname.h
@@ -19,6 +19,7 @@
#ifndef __RFB_HOSTNAME_H__
#define __RFB_HOSTNAME_H__
+#include <assert.h>
#include <stdlib.h>
#include <rdr/Exception.h>
#include <rfb/util.h>
@@ -26,30 +27,72 @@
namespace rfb {
static void getHostAndPort(const char* hi, char** host, int* port, int basePort=5900) {
- CharArray portBuf;
- CharArray hostBuf;
+ const char* hostStart;
+ const char* hostEnd;
+ const char* portStart;
+
if (hi == NULL)
throw rdr::Exception("NULL host specified");
+
+ assert(host);
+ assert(port);
+
if (hi[0] == '[') {
- if (!strSplit(&hi[1], ']', &hostBuf.buf, &portBuf.buf))
+ hostStart = &hi[1];
+ hostEnd = strchr(hostStart, ']');
+ if (hostEnd == NULL)
throw rdr::Exception("unmatched [ in host");
+
+ portStart = hostEnd + 1;
+ if (*portStart == '\0')
+ portStart = NULL;
} else {
- portBuf.buf = strDup(hi);
- }
- if (strSplit(portBuf.buf, ':', hostBuf.buf ? 0 : &hostBuf.buf, &portBuf.buf)) {
- if (portBuf.buf[0] == ':') {
- *port = atoi(&portBuf.buf[1]);
+ hostStart = &hi[0];
+ hostEnd = strrchr(hostStart, ':');
+
+ if (hostEnd == NULL) {
+ hostEnd = hostStart + strlen(hostStart);
+ portStart = NULL;
} else {
- *port = atoi(portBuf.buf);
- if (*port < 100) *port += basePort;
+ if ((hostEnd > hostStart) && (hostEnd[-1] == ':'))
+ hostEnd--;
+ portStart = strchr(hostStart, ':');
+ if (portStart != hostEnd) {
+ // We found more : in the host. This is probably an IPv6 address
+ hostEnd = hostStart + strlen(hostStart);
+ portStart = NULL;
+ }
}
- } else {
- *port = basePort;
}
- if (strlen(hostBuf.buf) == 0)
+
+ if (hostStart == hostEnd)
*host = strDup("localhost");
- else
- *host = hostBuf.takeBuf();
+ else {
+ size_t len;
+ len = hostEnd - hostStart + 1;
+ *host = new char[len];
+ strncpy(*host, hostStart, len-1);
+ (*host)[len-1] = '\0';
+ }
+
+ if (portStart == NULL)
+ *port = basePort;
+ else {
+ char* end;
+
+ if (portStart[0] != ':')
+ throw rdr::Exception("invalid port specified");
+
+ if (portStart[1] != ':')
+ *port = strtol(portStart + 1, &end, 10);
+ else
+ *port = strtol(portStart + 2, &end, 10);
+ if (*end != '\0')
+ throw rdr::Exception("invalid port specified");
+
+ if ((portStart[1] != ':') && (*port < 100))
+ *port += basePort;
+ }
}
};
diff --git a/common/rfb/KeyRemapper.cxx b/common/rfb/KeyRemapper.cxx
index d33f0a45..b4c2793c 100644
--- a/common/rfb/KeyRemapper.cxx
+++ b/common/rfb/KeyRemapper.cxx
@@ -17,6 +17,9 @@
*/
#include <stdio.h>
+
+#include <os/Mutex.h>
+
#include <rfb/KeyRemapper.h>
#include <rfb/Configuration.h>
#include <rfb/LogWriter.h>
@@ -27,14 +30,21 @@ static LogWriter vlog("KeyRemapper");
KeyRemapper KeyRemapper::defInstance;
-#ifdef __RFB_THREADING_IMPL
-static Mutex mappingLock;
-#endif
+KeyRemapper::KeyRemapper(const char* m)
+{
+ mutex = new os::Mutex;
+
+ setMapping(m);
+}
+
+KeyRemapper::~KeyRemapper()
+{
+ delete mutex;
+}
void KeyRemapper::setMapping(const char* m) {
-#ifdef __RFB_THREADING_IMPL
- Lock l(mappingLock);
-#endif
+ os::AutoMutex a(mutex);
+
mapping.clear();
while (m[0]) {
int from, to;
@@ -59,9 +69,8 @@ void KeyRemapper::setMapping(const char* m) {
}
rdr::U32 KeyRemapper::remapKey(rdr::U32 key) const {
-#ifdef __RFB_THREADING_IMPL
- Lock l(mappingLock);
-#endif
+ os::AutoMutex a(mutex);
+
std::map<rdr::U32,rdr::U32>::const_iterator i = mapping.find(key);
if (i != mapping.end())
return i->second;
diff --git a/common/rfb/KeyRemapper.h b/common/rfb/KeyRemapper.h
index a4b7aa01..1406bad2 100644
--- a/common/rfb/KeyRemapper.h
+++ b/common/rfb/KeyRemapper.h
@@ -22,16 +22,20 @@
#include <map>
#include <rdr/types.h>
+namespace os { class Mutex; }
+
namespace rfb {
class KeyRemapper {
public:
- KeyRemapper(const char* m="") { setMapping(m); }
+ KeyRemapper(const char* m="");
+ ~KeyRemapper();
void setMapping(const char* m);
rdr::U32 remapKey(rdr::U32 key) const;
static KeyRemapper defInstance;
private:
std::map<rdr::U32,rdr::U32> mapping;
+ os::Mutex* mutex;
};
};
diff --git a/common/rfb/Logger_file.cxx b/common/rfb/Logger_file.cxx
index ebe15d52..149ad404 100644
--- a/common/rfb/Logger_file.cxx
+++ b/common/rfb/Logger_file.cxx
@@ -21,36 +21,30 @@
#include <stdlib.h>
#include <string.h>
+#include <os/Mutex.h>
+
#include <rfb/util.h>
#include <rfb/Logger_file.h>
-#include <rfb/Threading.h>
using namespace rfb;
-
-// If threading is available then protect the write() operation
-// from concurrent accesses
-#ifdef __RFB_THREADING_IMPL
-static Mutex logLock;
-#endif
-
-
Logger_File::Logger_File(const char* loggerName)
: Logger(loggerName), indent(13), width(79), m_filename(0), m_file(0),
m_lastLogTime(0)
{
+ mutex = new os::Mutex();
}
Logger_File::~Logger_File()
{
closeFile();
+ delete mutex;
}
void Logger_File::write(int level, const char *logname, const char *message)
{
-#ifdef __RFB_THREADING_IMPL
- Lock l(logLock);
-#endif
+ os::AutoMutex a(mutex);
+
if (!m_file) {
if (!m_filename) return;
CharArray bakFilename(strlen(m_filename) + 1 + 4);
diff --git a/common/rfb/Logger_file.h b/common/rfb/Logger_file.h
index 5e0c917b..5b5c34e1 100644
--- a/common/rfb/Logger_file.h
+++ b/common/rfb/Logger_file.h
@@ -24,6 +24,8 @@
#include <time.h>
#include <rfb/Logger.h>
+namespace os { class Mutex; }
+
namespace rfb {
class Logger_File : public Logger {
@@ -43,6 +45,7 @@ namespace rfb {
char* m_filename;
FILE* m_file;
time_t m_lastLogTime;
+ os::Mutex* mutex;
};
bool initFileLogger(const char* filename);
diff --git a/common/rfb/Logger_syslog.cxx b/common/rfb/Logger_syslog.cxx
index 291d36cd..dc1d0c1a 100644
--- a/common/rfb/Logger_syslog.cxx
+++ b/common/rfb/Logger_syslog.cxx
@@ -25,7 +25,6 @@
#include <rfb/util.h>
#include <rfb/Logger_syslog.h>
#include <rfb/LogWriter.h>
-#include <rfb/Threading.h>
using namespace rfb;
diff --git a/common/rfb/SSecurityTLS.cxx b/common/rfb/SSecurityTLS.cxx
index 0f52d34b..b9460223 100644
--- a/common/rfb/SSecurityTLS.cxx
+++ b/common/rfb/SSecurityTLS.cxx
@@ -48,23 +48,15 @@ StringParameter SSecurityTLS::X509_KeyFile
static LogWriter vlog("TLS");
-void SSecurityTLS::initGlobal()
-{
- static bool globalInitDone = false;
-
- if (!globalInitDone) {
- if (gnutls_global_init() != GNUTLS_E_SUCCESS)
- throw AuthFailureException("gnutls_global_init failed");
- globalInitDone = true;
- }
-}
-
SSecurityTLS::SSecurityTLS(bool _anon) : session(0), dh_params(0),
anon_cred(0), cert_cred(0),
anon(_anon), fis(0), fos(0)
{
certfile = X509_CertFile.getData();
keyfile = X509_KeyFile.getData();
+
+ if (gnutls_global_init() != GNUTLS_E_SUCCESS)
+ throw AuthFailureException("gnutls_global_init failed");
}
void SSecurityTLS::shutdown()
@@ -94,8 +86,6 @@ void SSecurityTLS::shutdown()
if (session) {
gnutls_deinit(session);
session = 0;
-
- gnutls_global_deinit();
}
}
@@ -111,6 +101,8 @@ SSecurityTLS::~SSecurityTLS()
delete[] keyfile;
delete[] certfile;
+
+ gnutls_global_deinit();
}
bool SSecurityTLS::processMsg(SConnection *sc)
@@ -121,8 +113,6 @@ bool SSecurityTLS::processMsg(SConnection *sc)
vlog.debug("Process security message (session %p)", session);
if (!session) {
- initGlobal();
-
if (gnutls_init(&session, GNUTLS_SERVER) != GNUTLS_E_SUCCESS)
throw AuthFailureException("gnutls_init failed");
diff --git a/common/rfb/SSecurityTLS.h b/common/rfb/SSecurityTLS.h
index a7932054..30242a24 100644
--- a/common/rfb/SSecurityTLS.h
+++ b/common/rfb/SSecurityTLS.h
@@ -54,8 +54,6 @@ namespace rfb {
void setParams(gnutls_session_t session);
private:
- static void initGlobal();
-
gnutls_session_t session;
gnutls_dh_params_t dh_params;
gnutls_anon_server_credentials_t anon_cred;
diff --git a/common/rfb/Threading.h b/common/rfb/Threading.h
deleted file mode 100644
index 66b3aa0f..00000000
--- a/common/rfb/Threading.h
+++ /dev/null
@@ -1,31 +0,0 @@
-/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
- *
- * 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.
- */
-
-// -=- Threading.h
-// General purpose threading interface.
-// If the current platform supports threading then __RFB_THREADING_IMPL
-// will be defined after this header has been included.
-
-#ifndef __RFB_THREADING_H__
-#define __RFB_THREADING_H__
-
-#ifdef WIN32
-#include <rfb_win32/Threading.h>
-#endif
-
-#endif // __RFB_THREADING_H__
diff --git a/common/rfb/VNCServerST.cxx b/common/rfb/VNCServerST.cxx
index d5010854..e15cd701 100644
--- a/common/rfb/VNCServerST.cxx
+++ b/common/rfb/VNCServerST.cxx
@@ -110,6 +110,8 @@ VNCServerST::~VNCServerST()
desktop->stop();
}
+ if (comparer)
+ comparer->logStats();
delete comparer;
}
@@ -155,6 +157,10 @@ void VNCServerST::removeSocket(network::Socket* sock) {
desktopStarted = false;
desktop->stop();
}
+
+ if (comparer)
+ comparer->logStats();
+
return;
}
}
@@ -292,6 +298,9 @@ void VNCServerST::unblockUpdates()
void VNCServerST::setPixelBuffer(PixelBuffer* pb_, const ScreenSet& layout)
{
+ if (comparer)
+ comparer->logStats();
+
pb = pb_;
delete comparer;
comparer = 0;
diff --git a/common/rfb/VNCServerST.h b/common/rfb/VNCServerST.h
index bd84c452..0ced12a4 100644
--- a/common/rfb/VNCServerST.h
+++ b/common/rfb/VNCServerST.h
@@ -25,8 +25,6 @@
#include <sys/time.h>
-#include <list>
-
#include <rfb/SDesktop.h>
#include <rfb/VNCServer.h>
#include <rfb/Configuration.h>
@@ -67,6 +65,10 @@ namespace rfb {
// Clean up any resources associated with the Socket
virtual void removeSocket(network::Socket* sock);
+ // getSockets() gets a list of sockets. This can be used to generate an
+ // fd_set for calling select().
+ virtual void getSockets(std::list<network::Socket*>* sockets);
+
// processSocketReadEvent
// Read more RFB data from the Socket. If an error occurs during
// processing then shutdown() is called on the Socket, causing
@@ -111,11 +113,6 @@ namespace rfb {
// any), and logs the specified reason for closure.
void closeClients(const char* reason, network::Socket* sock);
- // getSockets() gets a list of sockets. This can be used to generate an
- // fd_set for calling select().
-
- void getSockets(std::list<network::Socket*>* sockets);
-
// getSConnection() gets the SConnection for a particular Socket. If
// the Socket is not recognised then null is returned.
diff --git a/common/rfb/ZRLEDecoder.cxx b/common/rfb/ZRLEDecoder.cxx
index c13f2861..b891ba52 100644
--- a/common/rfb/ZRLEDecoder.cxx
+++ b/common/rfb/ZRLEDecoder.cxx
@@ -86,10 +86,9 @@ void ZRLEDecoder::decodeRect(const Rect& r, const void* buffer,
{
rdr::MemInStream is(buffer, buflen);
const rfb::PixelFormat& pf = cp.pf();
- rdr::U8* buf[64 * 64 * 4 * pf.bpp/8];
switch (pf.bpp) {
- case 8: zrleDecode8 (r, &is, &zis, (rdr::U8*) buf, pf, pb); break;
- case 16: zrleDecode16(r, &is, &zis, (rdr::U16*)buf, pf, pb); break;
+ case 8: zrleDecode8 (r, &is, &zis, pf, pb); break;
+ case 16: zrleDecode16(r, &is, &zis, pf, pb); break;
case 32:
{
Pixel maxPixel = pf.pixelFromRGB((rdr::U16)-1, (rdr::U16)-1, (rdr::U16)-1);
@@ -99,16 +98,16 @@ void ZRLEDecoder::decodeRect(const Rect& r, const void* buffer,
if ((fitsInLS3Bytes && pf.isLittleEndian()) ||
(fitsInMS3Bytes && pf.isBigEndian()))
{
- zrleDecode24A(r, &is, &zis, (rdr::U32*)buf, pf, pb);
+ zrleDecode24A(r, &is, &zis, pf, pb);
}
else if ((fitsInLS3Bytes && pf.isBigEndian()) ||
(fitsInMS3Bytes && pf.isLittleEndian()))
{
- zrleDecode24B(r, &is, &zis, (rdr::U32*)buf, pf, pb);
+ zrleDecode24B(r, &is, &zis, pf, pb);
}
else
{
- zrleDecode32(r, &is, &zis, (rdr::U32*)buf, pf, pb);
+ zrleDecode32(r, &is, &zis, pf, pb);
}
break;
}
diff --git a/common/rfb/hextileDecode.h b/common/rfb/hextileDecode.h
index 7affa157..402cd031 100644
--- a/common/rfb/hextileDecode.h
+++ b/common/rfb/hextileDecode.h
@@ -22,6 +22,7 @@
// BPP - 8, 16 or 32
#include <rdr/InStream.h>
+#include <rfb/Exception.h>
#include <rfb/hextileConstants.h>
namespace rfb {
@@ -44,7 +45,7 @@ static void HEXTILE_DECODE (const Rect& r, rdr::InStream* is,
Rect t;
PIXEL_T bg = 0;
PIXEL_T fg = 0;
- PIXEL_T buf[16 * 16 * 4];
+ PIXEL_T buf[16 * 16];
for (t.tl.y = r.tl.y; t.tl.y < r.br.y; t.tl.y += 16) {
@@ -87,6 +88,9 @@ static void HEXTILE_DECODE (const Rect& r, rdr::InStream* is,
int y = (xy & 15);
int w = ((wh >> 4) & 15) + 1;
int h = (wh & 15) + 1;
+ if (x + w > 16 || y + h > 16) {
+ throw rfb::Exception("HEXTILE_DECODE: Hextile out of bounds");
+ }
PIXEL_T* ptr = buf + y * t.width() + x;
int rowAdd = t.width() - w;
while (h-- > 0) {
diff --git a/common/rfb/zrleDecode.h b/common/rfb/zrleDecode.h
index 07d6795a..0bfbbe15 100644
--- a/common/rfb/zrleDecode.h
+++ b/common/rfb/zrleDecode.h
@@ -47,12 +47,13 @@ namespace rfb {
#endif
void ZRLE_DECODE (const Rect& r, rdr::InStream* is,
- rdr::ZlibInStream* zis, PIXEL_T* buf,
+ rdr::ZlibInStream* zis,
const PixelFormat& pf, ModifiablePixelBuffer* pb)
{
int length = is->readU32();
zis->setUnderlying(is, length);
Rect t;
+ PIXEL_T buf[64 * 64];
for (t.tl.y = r.tl.y; t.tl.y < r.br.y; t.tl.y += 64) {