diff options
author | markmc <markmc> | 2003-09-11 16:08:19 +0000 |
---|---|---|
committer | markmc <markmc> | 2003-09-11 16:08:19 +0000 |
commit | 9edf7e56bbe5d396abbd47d4ed9fc1a14c64531c (patch) | |
tree | 04476b12c5715ad5698281a5bf710160369e7dad | |
parent | 937b906f0d8cd1b70521ea1ac8f20b457a22c3bb (diff) | |
download | libtdevnc-9edf7e56bbe5d396abbd47d4ed9fc1a14c64531c.tar.gz libtdevnc-9edf7e56bbe5d396abbd47d4ed9fc1a14c64531c.zip |
2003-09-11 Mark McLoughlin <[email protected]>
* rdr/Exception.h, rdr/FdInStream.cxx, rdr/FdInStream.h,
rdr/FdOutStream.cxx, rdr/FdOutStream.h, rdr/FixedMemOutStream.h,
rdr/InStream.cxx, rdr/InStream.h, rdr/MemInStream.h,
rdr/MemOutStream.h, rdr/NullOutStream.cxx, rdr/NullOutStream.h,
rdr/OutStream.h, rdr/ZlibInStream.cxx, rdr/ZlibInStream.h,
rdr/ZlibOutStream.cxx, rdr/ZlibOutStream.h, rdr/types.h,
zrle.cxx, zrleDecode.h, zrleEncode.h: remove original
C++ ZRLE implementation. Its been ported to C.
* NEWS: copy the existing ChangeLog to here and make
this a more detailed ChangeLog.
-rw-r--r-- | ChangeLog | 160 | ||||
-rw-r--r-- | NEWS | 178 | ||||
-rw-r--r-- | rdr/Exception.h | 71 | ||||
-rw-r--r-- | rdr/FdInStream.cxx | 251 | ||||
-rw-r--r-- | rdr/FdInStream.h | 72 | ||||
-rw-r--r-- | rdr/FdOutStream.cxx | 113 | ||||
-rw-r--r-- | rdr/FdOutStream.h | 53 | ||||
-rw-r--r-- | rdr/FixedMemOutStream.h | 52 | ||||
-rw-r--r-- | rdr/InStream.cxx | 35 | ||||
-rw-r--r-- | rdr/InStream.h | 143 | ||||
-rw-r--r-- | rdr/MemInStream.h | 47 | ||||
-rw-r--r-- | rdr/MemOutStream.h | 82 | ||||
-rw-r--r-- | rdr/NullOutStream.cxx | 60 | ||||
-rw-r--r-- | rdr/NullOutStream.h | 42 | ||||
-rw-r--r-- | rdr/OutStream.h | 152 | ||||
-rw-r--r-- | rdr/ZlibInStream.cxx | 121 | ||||
-rw-r--r-- | rdr/ZlibInStream.h | 59 | ||||
-rw-r--r-- | rdr/ZlibOutStream.cxx | 144 | ||||
-rw-r--r-- | rdr/ZlibOutStream.h | 57 | ||||
-rw-r--r-- | rdr/types.h | 33 | ||||
-rw-r--r-- | zrle.cxx | 179 | ||||
-rw-r--r-- | zrleDecode.h | 241 | ||||
-rw-r--r-- | zrleEncode.h | 310 |
23 files changed, 156 insertions, 2499 deletions
@@ -1,147 +1,13 @@ - Mark sent me patches to no longer need C++ for ZRLE encoding! - added --disable-cxx Option for configure - x11vnc changes from Karl Runge: - - Changed all those whimpy printf(...)'s into manly fprintf(stdxxx,...)'s. - - - Added -q switch (quiet) to suppress printing all the debug-looking output. - - - Added -bg switch to fork into background after everything is set up. - (checks for LIBVNCSERVER_HAVE_FORK and LIBVNCSERVER_HAVE_SETSID) - - - Print this string out to stdout: 'PORT=XXXX' (usually XXXX = 5900). - Combining with -bg, easy to write a ssh/rsh wrapper with something like: - port=`ssh $host "x11vnc -bg .."` then run vncviewer based on $port output. - (tunneling the vnc traffic thru ssh a bit more messy, but doable) - - - Quite a bit of code to be more careful when doing 8bpp indexed color, e.g. - not assuming NCOLORS is 256, handling 8bit TrueColor and Direct Color, etc - (I did all this probably in April, not quite clear in my mind now, but - I did test it out a fair amount on my old Sparcstation 20 wrt a user's - questions). - introduce rfbErr for Errors (Erik) - make rfbLog overridable (suggested by Erik) - don't reutrn on EINTR in WriteExact()/ReadExact() (suggested by Erik) - use AX_PREFIX_CONFIG_H to prefix constants in config.h to avoid - name clashes (also suggested by Erik) - transformed Bool, KeySym, Pixel to rfbBool, rfbKeySym, rfbPixel - (as suggested by Erik) - purged exit() calls (suggested by Erik) - fixed bug with maxRectsPerUpdate and Tight Encoding (these are incompatible) - checked sync with TightVNC 1.2.8: - viewonly/full passwords; if given a list, only the first is a full one - vncRandomBytes is a little more secure now - new weights for tight encoding - checked sync with RealVNC 3.3.7 - introduced maxRectsPerUpdate - added first alpha version of LibVNCClient - added simple and simple15 example (really simple examples) - finally got around to fix configure in CVS - long standing http bug (.jar was sent twice) fixed by a friend of Karl named Mike - http options in cargs - when closing a client and no longer listening for new ones, don't crash - fixed a bug with ClientConnectionGone - endianness is checked at configure time - fixed a bug that prevented the first client from being closed - fixed that annoying "libvncserver-config --link" bug - make rfbReverseByte public (for rdp2vnc) - fixed compilation on OS X, IRIX, Solaris - install target for headers is now ${prefix}/include/rfb ("#include <rfb/rfb.h>") - renamed "sraRegion.h" to "rfbregion.h" - CARD{8,16,32} are more standard uint{8,16,32}_t now - fixed LinuxVNC colour handling - fixed a bug with pthreads where the connection was not closed - moved vncterm to main package (LinuxVNC included) - portability fixes (IRIX, OSX, Solaris) - more portable way to determine endianness and types of a given size - through autoconf based methods -0.5 - rpm packaging through autoconf - autoconf'ed the whole package (including optional support for zlib, - pthreads and libjpeg as well as zrle/c++) - moved appropriate files to contrib/ and examples/ respectively - fixed long standing cargs bug (Justin "Zippy" Dearing) - Even better x11vnc from Karl J. Runge! (supports different kbd layouts of - client/server) - Better x11vnc from Karl J. Runge! - fixed severe bug (Const Kaplinsky) - got patch from Const Kaplisnky with CursorPosUpdate encoding and some Docs - sync'ed with newest RealVNC (ZRLE encoding) - a HTTP request for tunnelling was added (to fool strict web proxies) - sync'ed with TightVNC 1.2.5 -0.4 - support for NewFB from Const Kaplinsky - memory leaks squashed (localtime pseudo leak is still there :-) - small improvements for OSXvnc (still not working correctly) - synced with TightVNC 1.2.3 - solaris compile cleanups - many x11vnc improvements - added backchannel, an encoding which needs special clients to pass - arbitrary data to the client - changes from Tim Jansen regarding multi threading and client blocking - as well as C++ compliancy - x11vnc can be controlled by starting again with special options if compiling - with LOCAL_CONTROL defined -0.3 - added x11vnc, a x0rfbserver clone - regard deferUpdateTime in processEvents, if usec<0 - initialize deferUpdateTime (memory "leak"!) - changed command line handling (arguments are parsed and then removed) - added very simple example: zippy - added rfbDrawLine, rfbDrawPixel -0.2 - inserted a deferUpdate mechanism (X11 independent). - removed deletion of requestedRegion - added rfbLoadConsoleFont - fixed font colour handling. - added rfbSelectBox - added rfbDrawCharWithClip to allow for clipping and a background colour. - fixed font colours - added rfbFillRect - added IO function to check password. - rfbNewClient now sets the socket in the fd_set (for the select() call) - when compiling the library with HAVE_PTHREADS and an application - which includes "rfb.h" without, the structures got mixed up. - So, the pthreads section is now always at the end, and also - you get a linker error for rfbInitServer when using two different - pthread setups. - fixed two deadlocks: when setting a cursor and when using CopyRect - fixed CopyRect when copying modified regions (they lost the modified - property) - WIN32 target compiles and works for example :-) - fixed CopyRect (was using the wrong order of rectangles...) - should also work with pthreads, because copyrects are - always sent immediately (so that two consecutive copy rects - cannot conflict). - changed rfbUndrawCursor(rfbClientPtr) to (rfbScreenInfoPtr), because - this makes more sense! - flag backgroundLoop in rfbScreenInfo (if having pthreads) - CopyRect & CopyRegion were implemented. - if you use a rfbDoCopyR* function, it copies the data in the - framebuffer. If you prefer to do that yourself, use rfbScheduleCopyR* - instead; this doesn't modify the frameBuffer. - added flag to optionally not send XCursor updates, but only RichCursor, - or if that is not possible, fall back to server side cursor. - This is useful if your cursor has many nice colours. - fixed java viewer on server side: - SendCursorUpdate would send data even before the client pixel format - was set, but the java applet doesn't like the server's format. - fixed two pthread issues: - rfbSendFramebuffer was sent by a ProcessClientMessage function - (unprotected by updateMutex). - cursor coordinates were set without protection by cursorMutex - source is now equivalent to TridiaVNC 1.2.1 - pthreads now work (use iterators!) - cursors are supported (rfbSetCursor automatically undraws cursor) - support for 3 bytes/pixel (slow!) - server side colourmap support - fixed rfbCloseClient not to close the connection (pthreads!) - this is done lazily (and with proper signalling). - cleaned up mac.c (from original OSXvnc); now compiles (untested!) - compiles cleanly on Linux, IRIX, BSD, Apple (Darwin) - fixed prototypes -0.1 - rewrote API to use pseudo-methods instead of required functions. - lots of clean up. - Example can show symbols now. - All encodings - HTTP +2003-09-11 Mark McLoughlin <[email protected]> + + * rdr/Exception.h, rdr/FdInStream.cxx, rdr/FdInStream.h, + rdr/FdOutStream.cxx, rdr/FdOutStream.h, rdr/FixedMemOutStream.h, + rdr/InStream.cxx, rdr/InStream.h, rdr/MemInStream.h, + rdr/MemOutStream.h, rdr/NullOutStream.cxx, rdr/NullOutStream.h, + rdr/OutStream.h, rdr/ZlibInStream.cxx, rdr/ZlibInStream.h, + rdr/ZlibOutStream.cxx, rdr/ZlibOutStream.h, rdr/types.h, + zrle.cxx, zrleDecode.h, zrleEncode.h: remove original + C++ ZRLE implementation. Its been ported to C. + + * NEWS: copy the existing ChangeLog to here and make + this a more detailed ChangeLog. @@ -1,39 +1,147 @@ -Question: Why the *&!"/(� did you change so many things in the API? -Answer: It was necessary to make this library slightly less - painful to use with other libraries. + Mark sent me patches to no longer need C++ for ZRLE encoding! + added --disable-cxx Option for configure + x11vnc changes from Karl Runge: + - Changed all those whimpy printf(...)'s into manly fprintf(stdxxx,...)'s. - Anyway, most changes are just search-and-replace: + - Added -q switch (quiet) to suppress printing all the debug-looking output. - #include "rfb.h" -> #include <rfb/rfb.h> - CARD8 -> uint8_t - CARD16 -> uint16_t - CARD32 -> uint32_t - Pixel -> rfbPixel - KeySym -> rfbKeySym - Bool -> rfbBool + - Added -bg switch to fork into background after everything is set up. + (checks for LIBVNCSERVER_HAVE_FORK and LIBVNCSERVER_HAVE_SETSID) - also, rfbUsage doesn't exit any longer, but returns FALSE + - Print this string out to stdout: 'PORT=XXXX' (usually XXXX = 5900). + Combining with -bg, easy to write a ssh/rsh wrapper with something like: + port=`ssh $host "x11vnc -bg .."` then run vncviewer based on $port output. + (tunneling the vnc traffic thru ssh a bit more messy, but doable) - If you used some constants defined in rfbconfig.h, you now - have to prefix LIBVNCSERVER_ to the constants. - -Upcoming 0.6 release! - -lots of bugs fixed. - - -Version 5.0: - -The library just got autoconf && automake support as well as a real install -target! - -x11vnc was much improved thanks to Karl Runge! - -CursorPosUpdate encoding supported thanks to Const Kaplinsky! - -ZRLE encoding, if you have a c++ compiler! - -HTTP now optionally handles HTTP proxy functions to connect to the same -server only. - -Of course, a lot of bugs fixed since last release... + - Quite a bit of code to be more careful when doing 8bpp indexed color, e.g. + not assuming NCOLORS is 256, handling 8bit TrueColor and Direct Color, etc + (I did all this probably in April, not quite clear in my mind now, but + I did test it out a fair amount on my old Sparcstation 20 wrt a user's + questions). + introduce rfbErr for Errors (Erik) + make rfbLog overridable (suggested by Erik) + don't reutrn on EINTR in WriteExact()/ReadExact() (suggested by Erik) + use AX_PREFIX_CONFIG_H to prefix constants in config.h to avoid + name clashes (also suggested by Erik) + transformed Bool, KeySym, Pixel to rfbBool, rfbKeySym, rfbPixel + (as suggested by Erik) + purged exit() calls (suggested by Erik) + fixed bug with maxRectsPerUpdate and Tight Encoding (these are incompatible) + checked sync with TightVNC 1.2.8: + viewonly/full passwords; if given a list, only the first is a full one + vncRandomBytes is a little more secure now + new weights for tight encoding + checked sync with RealVNC 3.3.7 + introduced maxRectsPerUpdate + added first alpha version of LibVNCClient + added simple and simple15 example (really simple examples) + finally got around to fix configure in CVS + long standing http bug (.jar was sent twice) fixed by a friend of Karl named Mike + http options in cargs + when closing a client and no longer listening for new ones, don't crash + fixed a bug with ClientConnectionGone + endianness is checked at configure time + fixed a bug that prevented the first client from being closed + fixed that annoying "libvncserver-config --link" bug + make rfbReverseByte public (for rdp2vnc) + fixed compilation on OS X, IRIX, Solaris + install target for headers is now ${prefix}/include/rfb ("#include <rfb/rfb.h>") + renamed "sraRegion.h" to "rfbregion.h" + CARD{8,16,32} are more standard uint{8,16,32}_t now + fixed LinuxVNC colour handling + fixed a bug with pthreads where the connection was not closed + moved vncterm to main package (LinuxVNC included) + portability fixes (IRIX, OSX, Solaris) + more portable way to determine endianness and types of a given size + through autoconf based methods +0.5 + rpm packaging through autoconf + autoconf'ed the whole package (including optional support for zlib, + pthreads and libjpeg as well as zrle/c++) + moved appropriate files to contrib/ and examples/ respectively + fixed long standing cargs bug (Justin "Zippy" Dearing) + Even better x11vnc from Karl J. Runge! (supports different kbd layouts of + client/server) + Better x11vnc from Karl J. Runge! + fixed severe bug (Const Kaplinsky) + got patch from Const Kaplisnky with CursorPosUpdate encoding and some Docs + sync'ed with newest RealVNC (ZRLE encoding) + a HTTP request for tunnelling was added (to fool strict web proxies) + sync'ed with TightVNC 1.2.5 +0.4 + support for NewFB from Const Kaplinsky + memory leaks squashed (localtime pseudo leak is still there :-) + small improvements for OSXvnc (still not working correctly) + synced with TightVNC 1.2.3 + solaris compile cleanups + many x11vnc improvements + added backchannel, an encoding which needs special clients to pass + arbitrary data to the client + changes from Tim Jansen regarding multi threading and client blocking + as well as C++ compliancy + x11vnc can be controlled by starting again with special options if compiling + with LOCAL_CONTROL defined +0.3 + added x11vnc, a x0rfbserver clone + regard deferUpdateTime in processEvents, if usec<0 + initialize deferUpdateTime (memory "leak"!) + changed command line handling (arguments are parsed and then removed) + added very simple example: zippy + added rfbDrawLine, rfbDrawPixel +0.2 + inserted a deferUpdate mechanism (X11 independent). + removed deletion of requestedRegion + added rfbLoadConsoleFont + fixed font colour handling. + added rfbSelectBox + added rfbDrawCharWithClip to allow for clipping and a background colour. + fixed font colours + added rfbFillRect + added IO function to check password. + rfbNewClient now sets the socket in the fd_set (for the select() call) + when compiling the library with HAVE_PTHREADS and an application + which includes "rfb.h" without, the structures got mixed up. + So, the pthreads section is now always at the end, and also + you get a linker error for rfbInitServer when using two different + pthread setups. + fixed two deadlocks: when setting a cursor and when using CopyRect + fixed CopyRect when copying modified regions (they lost the modified + property) + WIN32 target compiles and works for example :-) + fixed CopyRect (was using the wrong order of rectangles...) + should also work with pthreads, because copyrects are + always sent immediately (so that two consecutive copy rects + cannot conflict). + changed rfbUndrawCursor(rfbClientPtr) to (rfbScreenInfoPtr), because + this makes more sense! + flag backgroundLoop in rfbScreenInfo (if having pthreads) + CopyRect & CopyRegion were implemented. + if you use a rfbDoCopyR* function, it copies the data in the + framebuffer. If you prefer to do that yourself, use rfbScheduleCopyR* + instead; this doesn't modify the frameBuffer. + added flag to optionally not send XCursor updates, but only RichCursor, + or if that is not possible, fall back to server side cursor. + This is useful if your cursor has many nice colours. + fixed java viewer on server side: + SendCursorUpdate would send data even before the client pixel format + was set, but the java applet doesn't like the server's format. + fixed two pthread issues: + rfbSendFramebuffer was sent by a ProcessClientMessage function + (unprotected by updateMutex). + cursor coordinates were set without protection by cursorMutex + source is now equivalent to TridiaVNC 1.2.1 + pthreads now work (use iterators!) + cursors are supported (rfbSetCursor automatically undraws cursor) + support for 3 bytes/pixel (slow!) + server side colourmap support + fixed rfbCloseClient not to close the connection (pthreads!) + this is done lazily (and with proper signalling). + cleaned up mac.c (from original OSXvnc); now compiles (untested!) + compiles cleanly on Linux, IRIX, BSD, Apple (Darwin) + fixed prototypes +0.1 + rewrote API to use pseudo-methods instead of required functions. + lots of clean up. + Example can show symbols now. + All encodings + HTTP diff --git a/rdr/Exception.h b/rdr/Exception.h deleted file mode 100644 index 49c59d9..0000000 --- a/rdr/Exception.h +++ /dev/null @@ -1,71 +0,0 @@ -// -// Copyright (C) 2002 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. - -#ifndef __RDR_EXCEPTION_H__ -#define __RDR_EXCEPTION_H__ - -#include <stdio.h> -#include <string.h> - -namespace rdr { - - struct Exception { - enum { len = 256 }; - char str_[len]; - Exception(const char* s=0, const char* e="rdr::Exception") { - str_[0] = 0; - strncat(str_, e, len-1); - if (s) { - strncat(str_, ": ", len-1-strlen(str_)); - strncat(str_, s, len-1-strlen(str_)); - } - } - virtual const char* str() const { return str_; } - }; - - struct SystemException : public Exception { - int err; - SystemException(const char* s, int err_) : err(err_) { - str_[0] = 0; - strncat(str_, "rdr::SystemException: ", len-1); - strncat(str_, s, len-1-strlen(str_)); - strncat(str_, ": ", len-1-strlen(str_)); - strncat(str_, strerror(err), len-1-strlen(str_)); - strncat(str_, " (", len-1-strlen(str_)); - char buf[20]; - sprintf(buf,"%d",err); - strncat(str_, buf, len-1-strlen(str_)); - strncat(str_, ")", len-1-strlen(str_)); - } - }; - - struct TimedOut : public Exception { - TimedOut(const char* s=0) : Exception(s,"rdr::TimedOut") {} - }; - - struct EndOfStream : public Exception { - EndOfStream(const char* s=0) : Exception(s,"rdr::EndOfStream") {} - }; - - struct FrameException : public Exception { - FrameException(const char* s=0) : Exception(s,"rdr::FrameException") {} - }; - -} - -#endif diff --git a/rdr/FdInStream.cxx b/rdr/FdInStream.cxx deleted file mode 100644 index b8248a0..0000000 --- a/rdr/FdInStream.cxx +++ /dev/null @@ -1,251 +0,0 @@ -// -// Copyright (C) 2002 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. - -#include <stdio.h> -#include <string.h> -#include <errno.h> -#include <sys/types.h> -#ifdef _WIN32 -#include <winsock.h> -#include <sys/timeb.h> -#define read(s,b,l) recv(s,(char*)b,l,0) -#undef errno -#define errno WSAGetLastError() -#else -#include <unistd.h> -#include <sys/time.h> -#endif - -// XXX should use autoconf HAVE_SYS_SELECT_H -#ifdef _AIX -#include <sys/select.h> -#endif - -#include <rdr/FdInStream.h> -#include <rdr/Exception.h> - -extern "C" { - extern void rfbLog(const char *format, ...); -} - -using namespace rdr; - -enum { DEFAULT_BUF_SIZE = 8192, - MIN_BULK_SIZE = 1024 }; - -FdInStream::FdInStream(int fd_, int timeout_, int bufSize_) - : fd(fd_), timeout(timeout_), blockCallback(0), blockCallbackArg(0), - timing(false), timeWaitedIn100us(5), timedKbits(0), - bufSize(bufSize_ ? bufSize_ : DEFAULT_BUF_SIZE), offset(0) -{ - ptr = end = start = new U8[bufSize]; -} - -FdInStream::FdInStream(int fd_, void (*blockCallback_)(void*), - void* blockCallbackArg_, int bufSize_) - : fd(fd_), timeout(0), blockCallback(blockCallback_), - blockCallbackArg(blockCallbackArg_), - timing(false), timeWaitedIn100us(5), timedKbits(0), - bufSize(bufSize_ ? bufSize_ : DEFAULT_BUF_SIZE), offset(0) -{ - ptr = end = start = new U8[bufSize]; -} - -FdInStream::~FdInStream() -{ - delete [] start; -} - - -int FdInStream::pos() -{ - return offset + ptr - start; -} - -void FdInStream::readBytes(void* data, int length) -{ - if (length < MIN_BULK_SIZE) { - InStream::readBytes(data, length); - return; - } - - U8* dataPtr = (U8*)data; - - int n = end - ptr; - if (n > length) n = length; - - memcpy(dataPtr, ptr, n); - dataPtr += n; - length -= n; - ptr += n; - - while (length > 0) { - n = readWithTimeoutOrCallback(dataPtr, length); - dataPtr += n; - length -= n; - offset += n; - } -} - - -int FdInStream::overrun(int itemSize, int nItems) -{ - if (itemSize > bufSize) - throw Exception("FdInStream overrun: max itemSize exceeded"); - - if (end - ptr != 0) - memmove(start, ptr, end - ptr); - - offset += ptr - start; - end -= ptr - start; - ptr = start; - - while (end < start + itemSize) { - int n = readWithTimeoutOrCallback((U8*)end, start + bufSize - end); - end += n; - } - - if (itemSize * nItems > end - ptr) - nItems = (end - ptr) / itemSize; - - return nItems; -} - -int FdInStream::checkReadable(int fd, int timeout) -{ - while (true) { - fd_set rfds; - struct timeval tv; - - tv.tv_sec = timeout / 1000; - tv.tv_usec = (timeout % 1000) * 1000; - - FD_ZERO(&rfds); - FD_SET(fd, &rfds); - int n = select(fd+1, &rfds, 0, 0, &tv); - if (n != -1 || errno != EINTR) - return n; - rfbLog("select returned EINTR\n"); - } -} - -#ifdef _WIN32 -static void gettimeofday(struct timeval* tv, void*) -{ - LARGE_INTEGER counts, countsPerSec; - static double usecPerCount = 0.0; - - if (QueryPerformanceCounter(&counts)) { - if (usecPerCount == 0.0) { - QueryPerformanceFrequency(&countsPerSec); - usecPerCount = 1000000.0 / countsPerSec.QuadPart; - } - - LONGLONG usecs = (LONGLONG)(counts.QuadPart * usecPerCount); - tv->tv_usec = (long)(usecs % 1000000); - tv->tv_sec = (long)(usecs / 1000000); - - } else { - struct timeb tb; - ftime(&tb); - tv->tv_sec = tb.time; - tv->tv_usec = tb.millitm * 1000; - } -} -#endif - -int FdInStream::readWithTimeoutOrCallback(void* buf, int len) -{ - struct timeval before, after; - if (timing) - gettimeofday(&before, 0); - - int n = checkReadable(fd, timeout); - - if (n < 0) throw SystemException("select",errno); - - if (n == 0) { - if (timeout) throw TimedOut(); - if (blockCallback) (*blockCallback)(blockCallbackArg); - } - - while (true) { - n = ::read(fd, buf, len); - if (n != -1 || errno != EINTR) - break; - rfbLog("read returned EINTR\n"); - } - - if (n < 0) throw SystemException("read",errno); - if (n == 0) throw EndOfStream(); - - if (timing) { - gettimeofday(&after, 0); -// rfbLog("%d.%06d\n",(after.tv_sec - before.tv_sec), -// (after.tv_usec - before.tv_usec)); - int newTimeWaited = ((after.tv_sec - before.tv_sec) * 10000 + - (after.tv_usec - before.tv_usec) / 100); - int newKbits = n * 8 / 1000; - -// if (newTimeWaited == 0) { -// rfbLog("new kbps infinite t %d k %d\n", -// newTimeWaited, newKbits); -// } else { -// rfbLog("new kbps %d t %d k %d\n", -// newKbits * 10000 / newTimeWaited, newTimeWaited, newKbits); -// } - - // limit rate to between 10kbit/s and 40Mbit/s - - if (newTimeWaited > newKbits*1000) newTimeWaited = newKbits*1000; - if (newTimeWaited < newKbits/4) newTimeWaited = newKbits/4; - - timeWaitedIn100us += newTimeWaited; - timedKbits += newKbits; - } - - return n; -} - -void FdInStream::startTiming() -{ - timing = true; - - // Carry over up to 1s worth of previous rate for smoothing. - - if (timeWaitedIn100us > 10000) { - timedKbits = timedKbits * 10000 / timeWaitedIn100us; - timeWaitedIn100us = 10000; - } -} - -void FdInStream::stopTiming() -{ - timing = false; - if (timeWaitedIn100us < timedKbits/2) - timeWaitedIn100us = timedKbits/2; // upper limit 20Mbit/s -} - -unsigned int FdInStream::kbitsPerSecond() -{ - // The following calculation will overflow 32-bit arithmetic if we have - // received more than about 50Mbytes (400Mbits) since we started timing, so - // it should be OK for a single RFB update. - - return timedKbits * 10000 / timeWaitedIn100us; -} diff --git a/rdr/FdInStream.h b/rdr/FdInStream.h deleted file mode 100644 index 5a1ed43..0000000 --- a/rdr/FdInStream.h +++ /dev/null @@ -1,72 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// FdInStream streams from a file descriptor. -// - -#ifndef __RDR_FDINSTREAM_H__ -#define __RDR_FDINSTREAM_H__ - -#include <rdr/InStream.h> - -namespace rdr { - - class FdInStream : public InStream { - - public: - - FdInStream(int fd, int timeout=0, int bufSize=0); - FdInStream(int fd, void (*blockCallback)(void*), void* blockCallbackArg=0, - int bufSize=0); - virtual ~FdInStream(); - - int getFd() { return fd; } - int pos(); - void readBytes(void* data, int length); - int bytesInBuf() { return end - ptr; } - - void startTiming(); - void stopTiming(); - unsigned int kbitsPerSecond(); - unsigned int timeWaited() { return timeWaitedIn100us; } - - protected: - int overrun(int itemSize, int nItems); - - private: - int checkReadable(int fd, int timeout); - int readWithTimeoutOrCallback(void* buf, int len); - - int fd; - int timeout; - void (*blockCallback)(void*); - void* blockCallbackArg; - - bool timing; - unsigned int timeWaitedIn100us; - unsigned int timedKbits; - - int bufSize; - int offset; - U8* start; - }; - -} // end of namespace rdr - -#endif diff --git a/rdr/FdOutStream.cxx b/rdr/FdOutStream.cxx deleted file mode 100644 index 40e7ac0..0000000 --- a/rdr/FdOutStream.cxx +++ /dev/null @@ -1,113 +0,0 @@ -// -// Copyright (C) 2002 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. - -#include <stdio.h> -#include <string.h> -#include <errno.h> -#include <sys/types.h> -#ifdef _WIN32 -#include <winsock.h> -#define write(s,b,l) send(s,(const char*)b,l,0) -#undef errno -#define errno WSAGetLastError() -#else -#include <unistd.h> -#include <sys/time.h> -#endif - -#include <rdr/FdOutStream.h> -#include <rdr/Exception.h> - - -using namespace rdr; - -enum { DEFAULT_BUF_SIZE = 16384, - MIN_BULK_SIZE = 1024 }; - -FdOutStream::FdOutStream(int fd_, int bufSize_) - : fd(fd_), bufSize(bufSize_ ? bufSize_ : DEFAULT_BUF_SIZE), offset(0) -{ - ptr = start = new U8[bufSize]; - end = start + bufSize; -} - -FdOutStream::~FdOutStream() -{ - try { - flush(); - } catch (Exception&) { - } - delete [] start; -} - - -void FdOutStream::writeBytes(const void* data, int length) -{ - if (length < MIN_BULK_SIZE) { - OutStream::writeBytes(data, length); - return; - } - - const U8* dataPtr = (const U8*)data; - - flush(); - - while (length > 0) { - int n = write(fd, dataPtr, length); - - if (n < 0) throw SystemException("write",errno); - - length -= n; - dataPtr += n; - offset += n; - } -} - -int FdOutStream::length() -{ - return offset + ptr - start; -} - -void FdOutStream::flush() -{ - U8* sentUpTo = start; - while (sentUpTo < ptr) { - int n = write(fd, (const void*) sentUpTo, ptr - sentUpTo); - - if (n < 0) throw SystemException("write",errno); - - sentUpTo += n; - offset += n; - } - - ptr = start; -} - - -int FdOutStream::overrun(int itemSize, int nItems) -{ - if (itemSize > bufSize) - throw Exception("FdOutStream overrun: max itemSize exceeded"); - - flush(); - - if (itemSize * nItems > end - ptr) - nItems = (end - ptr) / itemSize; - - return nItems; -} diff --git a/rdr/FdOutStream.h b/rdr/FdOutStream.h deleted file mode 100644 index e338852..0000000 --- a/rdr/FdOutStream.h +++ /dev/null @@ -1,53 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// FdOutStream streams to a file descriptor. -// - -#ifndef __RDR_FDOUTSTREAM_H__ -#define __RDR_FDOUTSTREAM_H__ - -#include <rdr/OutStream.h> - -namespace rdr { - - class FdOutStream : public OutStream { - - public: - - FdOutStream(int fd, int bufSize=0); - virtual ~FdOutStream(); - - int getFd() { return fd; } - - void flush(); - int length(); - void writeBytes(const void* data, int length); - - private: - int overrun(int itemSize, int nItems); - int fd; - int bufSize; - int offset; - U8* start; - }; - -} - -#endif diff --git a/rdr/FixedMemOutStream.h b/rdr/FixedMemOutStream.h deleted file mode 100644 index 5503505..0000000 --- a/rdr/FixedMemOutStream.h +++ /dev/null @@ -1,52 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// A FixedMemOutStream writes to a buffer of a fixed length. -// - -#ifndef __RDR_FIXEDMEMOUTSTREAM_H__ -#define __RDR_FIXEDMEMOUTSTREAM_H__ - -#include <rdr/OutStream.h> -#include <rdr/Exception.h> - -namespace rdr { - - class FixedMemOutStream : public OutStream { - - public: - - FixedMemOutStream(void* buf, int len) { - ptr = start = (U8*)buf; - end = start + len; - } - - int length() { return ptr - start; } - void reposition(int pos) { ptr = start + pos; } - const void* data() { return (const void*)start; } - - private: - - int overrun(int itemSize, int nItems) { throw EndOfStream(); } - U8* start; - }; - -} - -#endif diff --git a/rdr/InStream.cxx b/rdr/InStream.cxx deleted file mode 100644 index b5bf509..0000000 --- a/rdr/InStream.cxx +++ /dev/null @@ -1,35 +0,0 @@ -// -// Copyright (C) 2002 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. - -#include <rdr/InStream.h> -#include <rdr/Exception.h> - -using namespace rdr; - -U32 InStream::maxStringLength = 65535; - -char* InStream::readString() -{ - U32 len = readU32(); - if (len > maxStringLength) - throw Exception("InStream max string length exceeded"); - char* str = new char[len+1]; - readBytes(str, len); - str[len] = 0; - return str; -} diff --git a/rdr/InStream.h b/rdr/InStream.h deleted file mode 100644 index 2e2159e..0000000 --- a/rdr/InStream.h +++ /dev/null @@ -1,143 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// rdr::InStream marshalls data from a buffer stored in RDR (RFB Data -// Representation). -// - -#ifndef __RDR_INSTREAM_H__ -#define __RDR_INSTREAM_H__ - -#include <rdr/types.h> -#include <string.h> // for memcpy - -namespace rdr { - - class InStream { - - public: - - virtual ~InStream() {} - - // check() ensures there is buffer data for at least one item of size - // itemSize bytes. Returns the number of items in the buffer (up to a - // maximum of nItems). - - inline int check(int itemSize, int nItems=1) - { - if (ptr + itemSize * nItems > end) { - if (ptr + itemSize > end) - return overrun(itemSize, nItems); - - nItems = (end - ptr) / itemSize; - } - return nItems; - } - - // readU/SN() methods read unsigned and signed N-bit integers. - - inline U8 readU8() { check(1); return *ptr++; } - inline U16 readU16() { check(2); int b0 = *ptr++; int b1 = *ptr++; - return b0 << 8 | b1; } - inline U32 readU32() { check(4); int b0 = *ptr++; int b1 = *ptr++; - int b2 = *ptr++; int b3 = *ptr++; - return b0 << 24 | b1 << 16 | b2 << 8 | b3; } - - inline S8 readS8() { return (S8) readU8(); } - inline S16 readS16() { return (S16)readU16(); } - inline S32 readS32() { return (S32)readU32(); } - - // readString() reads a string - a U32 length followed by the data. - // Returns a null-terminated string - the caller should delete[] it - // afterwards. - - char* readString(); - - // maxStringLength protects against allocating a huge buffer. Set it - // higher if you need longer strings. - - static U32 maxStringLength; - - inline void skip(int bytes) { - while (bytes > 0) { - int n = check(1, bytes); - ptr += n; - bytes -= n; - } - } - - // readBytes() reads an exact number of bytes. - - virtual void readBytes(void* data, int length) { - U8* dataPtr = (U8*)data; - U8* dataEnd = dataPtr + length; - while (dataPtr < dataEnd) { - int n = check(1, dataEnd - dataPtr); - memcpy(dataPtr, ptr, n); - ptr += n; - dataPtr += n; - } - } - - // readOpaqueN() reads a quantity without byte-swapping. - - inline U8 readOpaque8() { return readU8(); } - inline U16 readOpaque16() { check(2); U16 r; ((U8*)&r)[0] = *ptr++; - ((U8*)&r)[1] = *ptr++; return r; } - inline U32 readOpaque32() { check(4); U32 r; ((U8*)&r)[0] = *ptr++; - ((U8*)&r)[1] = *ptr++; ((U8*)&r)[2] = *ptr++; - ((U8*)&r)[3] = *ptr++; return r; } - inline U32 readOpaque24A() { check(3); U32 r=0; ((U8*)&r)[0] = *ptr++; - ((U8*)&r)[1] = *ptr++; ((U8*)&r)[2] = *ptr++; - return r; } - inline U32 readOpaque24B() { check(3); U32 r=0; ((U8*)&r)[1] = *ptr++; - ((U8*)&r)[2] = *ptr++; ((U8*)&r)[3] = *ptr++; - return r; } - - // pos() returns the position in the stream. - - virtual int pos() = 0; - - // getptr(), getend() and setptr() are "dirty" methods which allow you to - // manipulate the buffer directly. This is useful for a stream which is a - // wrapper around an underlying stream. - - inline const U8* getptr() const { return ptr; } - inline const U8* getend() const { return end; } - inline void setptr(const U8* p) { ptr = p; } - - private: - - // overrun() is implemented by a derived class to cope with buffer overrun. - // It ensures there are at least itemSize bytes of buffer data. Returns - // the number of items in the buffer (up to a maximum of nItems). itemSize - // is supposed to be "small" (a few bytes). - - virtual int overrun(int itemSize, int nItems) = 0; - - protected: - - InStream() {} - const U8* ptr; - const U8* end; - }; - -} - -#endif diff --git a/rdr/MemInStream.h b/rdr/MemInStream.h deleted file mode 100644 index 0167949..0000000 --- a/rdr/MemInStream.h +++ /dev/null @@ -1,47 +0,0 @@ -// -// Copyright (C) 2002 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. - -#ifndef __RDR_MEMINSTREAM_H__ -#define __RDR_MEMINSTREAM_H__ - -#include <rdr/InStream.h> -#include <rdr/Exception.h> - -namespace rdr { - - class MemInStream : public InStream { - - public: - - MemInStream(const void* data, int len) { - ptr = start = (const U8*)data; - end = start + len; - } - - int pos() { return ptr - start; } - void reposition(int pos) { ptr = start + pos; } - - private: - - int overrun(int itemSize, int nItems) { throw EndOfStream(); } - const U8* start; - }; - -} - -#endif diff --git a/rdr/MemOutStream.h b/rdr/MemOutStream.h deleted file mode 100644 index 0031388..0000000 --- a/rdr/MemOutStream.h +++ /dev/null @@ -1,82 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// A MemOutStream grows as needed when data is written to it. -// - -#ifndef __RDR_MEMOUTSTREAM_H__ -#define __RDR_MEMOUTSTREAM_H__ - -#include <rdr/OutStream.h> - -namespace rdr { - - class MemOutStream : public OutStream { - - public: - - MemOutStream(int len=1024) { - start = ptr = new U8[len]; - end = start + len; - } - - virtual ~MemOutStream() { - delete [] start; - } - - void writeBytes(const void* data, int length) { - check(length); - memcpy(ptr, data, length); - ptr += length; - } - - int length() { return ptr - start; } - void clear() { ptr = start; }; - void reposition(int pos) { ptr = start + pos; } - - // data() returns a pointer to the buffer. - - const void* data() { return (const void*)start; } - - private: - - // overrun() either doubles the buffer or adds enough space for nItems of - // size itemSize bytes. - - int overrun(int itemSize, int nItems) { - int len = ptr - start + itemSize * nItems; - if (len < (end - start) * 2) - len = (end - start) * 2; - - U8* newStart = new U8[len]; - memcpy(newStart, start, ptr - start); - ptr = newStart + (ptr - start); - delete [] start; - start = newStart; - end = newStart + len; - - return nItems; - } - - U8* start; - }; - -} - -#endif diff --git a/rdr/NullOutStream.cxx b/rdr/NullOutStream.cxx deleted file mode 100644 index aae999d..0000000 --- a/rdr/NullOutStream.cxx +++ /dev/null @@ -1,60 +0,0 @@ -// -// Copyright (C) 2002 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. - -#include <rdr/NullOutStream.h> -#include <rdr/Exception.h> - -using namespace rdr; - -static const int bufferSize = 1024; - -NullOutStream::NullOutStream() - : offset(0) -{ - start = ptr = new U8[bufferSize]; - end = start + bufferSize; -} - -NullOutStream::~NullOutStream() -{ - delete [] start; -} - -int NullOutStream::length() -{ - return offset + ptr - start; -} - -void NullOutStream::writeBytes(const void* data, int length) -{ - offset += length; -} - -int NullOutStream::overrun(int itemSize, int nItems) -{ - if (itemSize > bufferSize) - throw Exception("NullOutStream overrun: max itemSize exceeded"); - - offset += ptr - start; - ptr = start; - - if (itemSize * nItems > end - ptr) - nItems = (end - ptr) / itemSize; - - return nItems; -} diff --git a/rdr/NullOutStream.h b/rdr/NullOutStream.h deleted file mode 100644 index 15c588b..0000000 --- a/rdr/NullOutStream.h +++ /dev/null @@ -1,42 +0,0 @@ -// -// Copyright (C) 2002 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. - -#ifndef __RDR_NULLOUTSTREAM_H__ -#define __RDR_NULLOUTSTREAM_H__ - -#include <rdr/OutStream.h> - -namespace rdr { - - class NullOutStream : public OutStream { - - public: - NullOutStream(); - virtual ~NullOutStream(); - int length(); - void writeBytes(const void* data, int length); - - private: - int overrun(int itemSize, int nItems); - int offset; - U8* start; - }; - -} - -#endif diff --git a/rdr/OutStream.h b/rdr/OutStream.h deleted file mode 100644 index 9aae80c..0000000 --- a/rdr/OutStream.h +++ /dev/null @@ -1,152 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// rdr::OutStream marshalls data into a buffer stored in RDR (RFB Data -// Representation). -// - -#ifndef __RDR_OUTSTREAM_H__ -#define __RDR_OUTSTREAM_H__ - -#include <rdr/types.h> -#include <string.h> // for memcpy - -namespace rdr { - - class OutStream { - - protected: - - OutStream() {} - - public: - - virtual ~OutStream() {} - - // check() ensures there is buffer space for at least one item of size - // itemSize bytes. Returns the number of items which fit (up to a maximum - // of nItems). - - inline int check(int itemSize, int nItems=1) - { - if (ptr + itemSize * nItems > end) { - if (ptr + itemSize > end) - return overrun(itemSize, nItems); - - nItems = (end - ptr) / itemSize; - } - return nItems; - } - - // writeU/SN() methods write unsigned and signed N-bit integers. - - inline void writeU8( U8 u) { check(1); *ptr++ = u; } - inline void writeU16(U16 u) { check(2); *ptr++ = u >> 8; *ptr++ = (U8)u; } - inline void writeU32(U32 u) { check(4); *ptr++ = u >> 24; *ptr++ = u >> 16; - *ptr++ = u >> 8; *ptr++ = u; } - - inline void writeS8( S8 s) { writeU8((U8)s); } - inline void writeS16(S16 s) { writeU16((U16)s); } - inline void writeS32(S32 s) { writeU32((U32)s); } - - // writeString() writes a string - a U32 length followed by the data. The - // given string should be null-terminated (but the terminating null is not - // written to the stream). - - inline void writeString(const char* str) { - U32 len = strlen(str); - writeU32(len); - writeBytes(str, len); - } - - inline void pad(int bytes) { - while (bytes-- > 0) writeU8(0); - } - - inline void skip(int bytes) { - while (bytes > 0) { - int n = check(1, bytes); - ptr += n; - bytes -= n; - } - } - - // writeBytes() writes an exact number of bytes. - - virtual void writeBytes(const void* data, int length) { - const U8* dataPtr = (const U8*)data; - const U8* dataEnd = dataPtr + length; - while (dataPtr < dataEnd) { - int n = check(1, dataEnd - dataPtr); - memcpy(ptr, dataPtr, n); - ptr += n; - dataPtr += n; - } - } - - // writeOpaqueN() writes a quantity without byte-swapping. - - inline void writeOpaque8( U8 u) { writeU8(u); } - inline void writeOpaque16(U16 u) { check(2); *ptr++ = ((U8*)&u)[0]; - *ptr++ = ((U8*)&u)[1]; } - inline void writeOpaque32(U32 u) { check(4); *ptr++ = ((U8*)&u)[0]; - *ptr++ = ((U8*)&u)[1]; - *ptr++ = ((U8*)&u)[2]; - *ptr++ = ((U8*)&u)[3]; } - inline void writeOpaque24A(U32 u) { check(3); *ptr++ = ((U8*)&u)[0]; - *ptr++ = ((U8*)&u)[1]; - *ptr++ = ((U8*)&u)[2]; } - inline void writeOpaque24B(U32 u) { check(3); *ptr++ = ((U8*)&u)[1]; - *ptr++ = ((U8*)&u)[2]; - *ptr++ = ((U8*)&u)[3]; } - - // length() returns the length of the stream. - - virtual int length() = 0; - - // flush() requests that the stream be flushed. - - virtual void flush() {} - - // getptr(), getend() and setptr() are "dirty" methods which allow you to - // manipulate the buffer directly. This is useful for a stream which is a - // wrapper around an underlying stream. - - inline U8* getptr() { return ptr; } - inline U8* getend() { return end; } - inline void setptr(U8* p) { ptr = p; } - - private: - - // overrun() is implemented by a derived class to cope with buffer overrun. - // It ensures there are at least itemSize bytes of buffer space. Returns - // the number of items which fit (up to a maximum of nItems). itemSize is - // supposed to be "small" (a few bytes). - - virtual int overrun(int itemSize, int nItems) = 0; - - protected: - - U8* ptr; - U8* end; - }; - -} - -#endif diff --git a/rdr/ZlibInStream.cxx b/rdr/ZlibInStream.cxx deleted file mode 100644 index d4d1f1f..0000000 --- a/rdr/ZlibInStream.cxx +++ /dev/null @@ -1,121 +0,0 @@ -// -// Copyright (C) 2002 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. - -#include <rdr/ZlibInStream.h> -#include <rdr/Exception.h> -#include <zlib.h> - -using namespace rdr; - -enum { DEFAULT_BUF_SIZE = 16384 }; - -ZlibInStream::ZlibInStream(int bufSize_) - : underlying(0), bufSize(bufSize_ ? bufSize_ : DEFAULT_BUF_SIZE), offset(0), - bytesIn(0) -{ - zs = new z_stream; - zs->zalloc = Z_NULL; - zs->zfree = Z_NULL; - zs->opaque = Z_NULL; - zs->next_in = Z_NULL; - zs->avail_in = 0; - if (inflateInit(zs) != Z_OK) { - delete zs; - throw Exception("ZlibInStream: inflateInit failed"); - } - ptr = end = start = new U8[bufSize]; -} - -ZlibInStream::~ZlibInStream() -{ - delete [] start; - inflateEnd(zs); - delete zs; -} - -void ZlibInStream::setUnderlying(InStream* is, int bytesIn_) -{ - underlying = is; - bytesIn = bytesIn_; - ptr = end = start; -} - -int ZlibInStream::pos() -{ - return offset + ptr - start; -} - -void ZlibInStream::reset() -{ - ptr = end = start; - if (!underlying) return; - - while (bytesIn > 0) { - decompress(); - end = start; // throw away any data - } - underlying = 0; -} - -int ZlibInStream::overrun(int itemSize, int nItems) -{ - if (itemSize > bufSize) - throw Exception("ZlibInStream overrun: max itemSize exceeded"); - if (!underlying) - throw Exception("ZlibInStream overrun: no underlying stream"); - - if (end - ptr != 0) - memmove(start, ptr, end - ptr); - - offset += ptr - start; - end -= ptr - start; - ptr = start; - - while (end - ptr < itemSize) { - decompress(); - } - - if (itemSize * nItems > end - ptr) - nItems = (end - ptr) / itemSize; - - return nItems; -} - -// decompress() calls the decompressor once. Note that this won't necessarily -// generate any output data - it may just consume some input data. - -void ZlibInStream::decompress() -{ - zs->next_out = (U8*)end; - zs->avail_out = start + bufSize - end; - - underlying->check(1); - zs->next_in = (U8*)underlying->getptr(); - zs->avail_in = underlying->getend() - underlying->getptr(); - if ((int)zs->avail_in > bytesIn) - zs->avail_in = bytesIn; - - int rc = inflate(zs, Z_SYNC_FLUSH); - if (rc != Z_OK) { - throw Exception("ZlibInStream: inflate failed"); - } - - bytesIn -= zs->next_in - underlying->getptr(); - end = zs->next_out; - underlying->setptr(zs->next_in); -} diff --git a/rdr/ZlibInStream.h b/rdr/ZlibInStream.h deleted file mode 100644 index 14ad6f0..0000000 --- a/rdr/ZlibInStream.h +++ /dev/null @@ -1,59 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// ZlibInStream streams from a compressed data stream ("underlying"), -// decompressing with zlib on the fly. -// - -#ifndef __RDR_ZLIBINSTREAM_H__ -#define __RDR_ZLIBINSTREAM_H__ - -#include <rdr/InStream.h> - -struct z_stream_s; - -namespace rdr { - - class ZlibInStream : public InStream { - - public: - - ZlibInStream(int bufSize=0); - virtual ~ZlibInStream(); - - void setUnderlying(InStream* is, int bytesIn); - void reset(); - int pos(); - - private: - - int overrun(int itemSize, int nItems); - void decompress(); - - InStream* underlying; - int bufSize; - int offset; - z_stream_s* zs; - int bytesIn; - U8* start; - }; - -} // end of namespace rdr - -#endif diff --git a/rdr/ZlibOutStream.cxx b/rdr/ZlibOutStream.cxx deleted file mode 100644 index e324998..0000000 --- a/rdr/ZlibOutStream.cxx +++ /dev/null @@ -1,144 +0,0 @@ -// -// Copyright (C) 2002 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. - -#include <rdr/ZlibOutStream.h> -#include <rdr/Exception.h> -#include <zlib.h> - -extern "C" { - extern void rfbLog(const char *format, ...); -} - -using namespace rdr; - -enum { DEFAULT_BUF_SIZE = 16384 }; - -ZlibOutStream::ZlibOutStream(OutStream* os, int bufSize_) - : underlying(os), bufSize(bufSize_ ? bufSize_ : DEFAULT_BUF_SIZE), offset(0) -{ - zs = new z_stream; - zs->zalloc = Z_NULL; - zs->zfree = Z_NULL; - zs->opaque = Z_NULL; - if (deflateInit(zs, Z_DEFAULT_COMPRESSION) != Z_OK) { - delete zs; - throw Exception("ZlibOutStream: deflateInit failed"); - } - ptr = start = new U8[bufSize]; - end = start + bufSize; -} - -ZlibOutStream::~ZlibOutStream() -{ - try { - flush(); - } catch (Exception&) { - } - delete [] start; - deflateEnd(zs); - delete zs; -} - -void ZlibOutStream::setUnderlying(OutStream* os) -{ - underlying = os; -} - -int ZlibOutStream::length() -{ - return offset + ptr - start; -} - -void ZlibOutStream::flush() -{ - zs->next_in = start; - zs->avail_in = ptr - start; - -// rfbLog("zos flush: avail_in %d\n",zs->avail_in); - - while (zs->avail_in != 0) { - - do { - underlying->check(1); - zs->next_out = underlying->getptr(); - zs->avail_out = underlying->getend() - underlying->getptr(); - -// rfbLog("zos flush: calling deflate, avail_in %d, avail_out %d\n", -// zs->avail_in,zs->avail_out); - int rc = deflate(zs, Z_SYNC_FLUSH); - if (rc != Z_OK) throw Exception("ZlibOutStream: deflate failed"); - -// rfbLog("zos flush: after deflate: %d bytes\n", -// zs->next_out-underlying->getptr()); - - underlying->setptr(zs->next_out); - } while (zs->avail_out == 0); - } - - offset += ptr - start; - ptr = start; -} - -int ZlibOutStream::overrun(int itemSize, int nItems) -{ -// rfbLog("ZlibOutStream overrun\n"); - - if (itemSize > bufSize) - throw Exception("ZlibOutStream overrun: max itemSize exceeded"); - - while (end - ptr < itemSize) { - zs->next_in = start; - zs->avail_in = ptr - start; - - do { - underlying->check(1); - zs->next_out = underlying->getptr(); - zs->avail_out = underlying->getend() - underlying->getptr(); - -// rfbLog("zos overrun: calling deflate, avail_in %d, avail_out %d\n", -// zs->avail_in,zs->avail_out); - - int rc = deflate(zs, 0); - if (rc != Z_OK) throw Exception("ZlibOutStream: deflate failed"); - -// rfbLog("zos overrun: after deflate: %d bytes\n", -// zs->next_out-underlying->getptr()); - - underlying->setptr(zs->next_out); - } while (zs->avail_out == 0); - - // output buffer not full - - if (zs->avail_in == 0) { - offset += ptr - start; - ptr = start; - } else { - // but didn't consume all the data? try shifting what's left to the - // start of the buffer. - rfbLog("z out buf not full, but in data not consumed\n"); - memmove(start, zs->next_in, ptr - zs->next_in); - offset += zs->next_in - start; - ptr -= zs->next_in - start; - } - } - - if (itemSize * nItems > end - ptr) - nItems = (end - ptr) / itemSize; - - return nItems; -} diff --git a/rdr/ZlibOutStream.h b/rdr/ZlibOutStream.h deleted file mode 100644 index 72f5239..0000000 --- a/rdr/ZlibOutStream.h +++ /dev/null @@ -1,57 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// ZlibOutStream streams to a compressed data stream (underlying), compressing -// with zlib on the fly. -// - -#ifndef __RDR_ZLIBOUTSTREAM_H__ -#define __RDR_ZLIBOUTSTREAM_H__ - -#include <rdr/OutStream.h> - -struct z_stream_s; - -namespace rdr { - - class ZlibOutStream : public OutStream { - - public: - - ZlibOutStream(OutStream* os=0, int bufSize=0); - virtual ~ZlibOutStream(); - - void setUnderlying(OutStream* os); - void flush(); - int length(); - - private: - - int overrun(int itemSize, int nItems); - - OutStream* underlying; - int bufSize; - int offset; - z_stream_s* zs; - U8* start; - }; - -} // end of namespace rdr - -#endif diff --git a/rdr/types.h b/rdr/types.h deleted file mode 100644 index 00b5c40..0000000 --- a/rdr/types.h +++ /dev/null @@ -1,33 +0,0 @@ -// -// Copyright (C) 2002 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. - -#ifndef __RDR_TYPES_H__ -#define __RDR_TYPES_H__ - -namespace rdr { - - typedef unsigned char U8; - typedef unsigned short U16; - typedef unsigned int U32; - typedef signed char S8; - typedef signed short S16; - typedef signed int S32; - -} // end of namespace rdr - -#endif diff --git a/zrle.cxx b/zrle.cxx deleted file mode 100644 index f64580c..0000000 --- a/zrle.cxx +++ /dev/null @@ -1,179 +0,0 @@ -// -// Copyright (C) 2002 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. -// - -// -// zrle.cc -// -// Routines to implement Zlib Run-length Encoding (ZRLE). -// - -extern "C" { -#include <rfb/rfb.h> -} -#include <rdr/MemOutStream.h> -#include <rdr/ZlibOutStream.h> - - -#define GET_IMAGE_INTO_BUF(tx,ty,tw,th,buf) \ - char *fbptr = (cl->screen->frameBuffer \ - + (cl->screen->paddedWidthInBytes * ty) \ - + (tx * (cl->screen->bitsPerPixel / 8))); \ - \ - (*cl->translateFn)(cl->translateLookupTable, &cl->screen->rfbServerFormat,\ - &cl->format, fbptr, (char*)buf, \ - cl->screen->paddedWidthInBytes, tw, th); - -#define EXTRA_ARGS , rfbClientPtr cl - -#define BPP 8 -#include <zrleEncode.h> -#undef BPP -#define BPP 16 -#include <zrleEncode.h> -#undef BPP -#define BPP 32 -#include <zrleEncode.h> -#define CPIXEL 24A -#include <zrleEncode.h> -#undef CPIXEL -#define CPIXEL 24B -#include <zrleEncode.h> -#undef CPIXEL -#undef BPP - - -/* - * zrleBeforeBuf contains pixel data in the client's format. It must be at - * least one pixel bigger than the largest tile of pixel data, since the - * ZRLE encoding algorithm writes to the position one past the end of the pixel - * data. - */ - -static char zrleBeforeBuf[rfbZRLETileWidth * rfbZRLETileHeight * 4 + 4]; - -static rdr::MemOutStream mos; - - -/* - * rfbSendRectEncodingZRLE - send a given rectangle using ZRLE encoding. - */ - - -rfbBool rfbSendRectEncodingZRLE(rfbClientPtr cl, int x, int y, int w, int h) -{ - if (!cl->zrleData) cl->zrleData = new rdr::ZlibOutStream; - rdr::ZlibOutStream* zos = (rdr::ZlibOutStream*)cl->zrleData; - mos.clear(); - - switch (cl->format.bitsPerPixel) { - - case 8: - zrleEncode8( x, y, w, h, &mos, zos, zrleBeforeBuf, cl); - break; - - case 16: - zrleEncode16(x, y, w, h, &mos, zos, zrleBeforeBuf, cl); - break; - - case 32: - bool fitsInLS3Bytes - = ((cl->format.redMax << cl->format.redShift) < (1<<24) && - (cl->format.greenMax << cl->format.greenShift) < (1<<24) && - (cl->format.blueMax << cl->format.blueShift) < (1<<24)); - - bool fitsInMS3Bytes = (cl->format.redShift > 7 && - cl->format.greenShift > 7 && - cl->format.blueShift > 7); - - if ((fitsInLS3Bytes && !cl->format.bigEndian) || - (fitsInMS3Bytes && cl->format.bigEndian)) - { - zrleEncode24A(x, y, w, h, &mos, zos, zrleBeforeBuf, cl); - } - else if ((fitsInLS3Bytes && cl->format.bigEndian) || - (fitsInMS3Bytes && !cl->format.bigEndian)) - { - zrleEncode24B(x, y, w, h, &mos, zos, zrleBeforeBuf, cl); - } - else - { - zrleEncode32(x, y, w, h, &mos, zos, zrleBeforeBuf, cl); - } - break; - } - - cl->rfbRectanglesSent[rfbEncodingZRLE]++; - cl->rfbBytesSent[rfbEncodingZRLE] += (sz_rfbFramebufferUpdateRectHeader - + sz_rfbZRLEHeader + mos.length()); - - if (cl->ublen + sz_rfbFramebufferUpdateRectHeader + sz_rfbZRLEHeader - > UPDATE_BUF_SIZE) - { - if (!rfbSendUpdateBuf(cl)) - return FALSE; - } - - rfbFramebufferUpdateRectHeader rect; - rect.r.x = Swap16IfLE(x); - rect.r.y = Swap16IfLE(y); - rect.r.w = Swap16IfLE(w); - rect.r.h = Swap16IfLE(h); - rect.encoding = Swap32IfLE(rfbEncodingZRLE); - - memcpy(cl->updateBuf+cl->ublen, (char *)&rect, - sz_rfbFramebufferUpdateRectHeader); - cl->ublen += sz_rfbFramebufferUpdateRectHeader; - - rfbZRLEHeader hdr; - - hdr.length = Swap32IfLE(mos.length()); - - memcpy(cl->updateBuf+cl->ublen, (char *)&hdr, sz_rfbZRLEHeader); - cl->ublen += sz_rfbZRLEHeader; - - // copy into updateBuf and send from there. Maybe should send directly? - - for (int i = 0; i < mos.length();) { - - int bytesToCopy = UPDATE_BUF_SIZE - cl->ublen; - - if (i + bytesToCopy > mos.length()) { - bytesToCopy = mos.length() - i; - } - - memcpy(cl->updateBuf+cl->ublen, (uint8_t*)mos.data() + i, bytesToCopy); - - cl->ublen += bytesToCopy; - i += bytesToCopy; - - if (cl->ublen == UPDATE_BUF_SIZE) { - if (!rfbSendUpdateBuf(cl)) - return FALSE; - } - } - - return TRUE; -} - - -void FreeZrleData(rfbClientPtr cl) -{ - delete (rdr::ZlibOutStream*)cl->zrleData; -} - diff --git a/zrleDecode.h b/zrleDecode.h deleted file mode 100644 index 8ddb5c8..0000000 --- a/zrleDecode.h +++ /dev/null @@ -1,241 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// zrleDecode.h - zrle decoding function. -// -// Before including this file, you must define a number of CPP macros. -// -// BPP should be 8, 16 or 32 depending on the bits per pixel. -// FILL_RECT -// IMAGE_RECT - -#include <rdr/ZlibInStream.h> -#include <rdr/InStream.h> -#include <assert.h> - -using namespace rdr; - -/* __RFB_CONCAT2 concatenates its two arguments. __RFB_CONCAT2E does the same - but also expands its arguments if they are macros */ - -#ifndef __RFB_CONCAT2E -#define __RFB_CONCAT2(a,b) a##b -#define __RFB_CONCAT2E(a,b) __RFB_CONCAT2(a,b) -#endif - -#ifdef CPIXEL -#define PIXEL_T __RFB_CONCAT2E(rdr::U,BPP) -#define READ_PIXEL __RFB_CONCAT2E(readOpaque,CPIXEL) -#define ZRLE_DECODE_BPP __RFB_CONCAT2E(zrleDecode,CPIXEL) -#else -#define PIXEL_T __RFB_CONCAT2E(rdr::U,BPP) -#define READ_PIXEL __RFB_CONCAT2E(readOpaque,BPP) -#define ZRLE_DECODE_BPP __RFB_CONCAT2E(zrleDecode,BPP) -#endif - -void ZRLE_DECODE_BPP (int x, int y, int w, int h, rdr::InStream* is, - rdr::ZlibInStream* zis, PIXEL_T* buf) -{ - int length = is->readU32(); - zis->setUnderlying(is, length); - - for (int ty = y; ty < y+h; ty += rfbZRLETileHeight) { - int th = rfbZRLETileHeight; - if (th > y+h-ty) th = y+h-ty; - for (int tx = x; tx < x+w; tx += rfbZRLETileWidth) { - int tw = rfbZRLETileWidth; - if (tw > x+w-tx) tw = x+w-tx; - - int mode = zis->readU8(); - bool rle = mode & 128; - int palSize = mode & 127; - PIXEL_T palette[128]; - - // fprintf(stderr,"rle %d palSize %d\n",rle,palSize); - - for (int i = 0; i < palSize; i++) { - palette[i] = zis->READ_PIXEL(); - } - - if (palSize == 1) { - PIXEL_T pix = palette[0]; - FILL_RECT(tx,ty,tw,th,pix); - continue; - } - - if (!rle) { - if (palSize == 0) { - - // raw - -#ifdef CPIXEL - for (PIXEL_T* ptr = buf; ptr < buf+tw*th; ptr++) { - *ptr = zis->READ_PIXEL(); - } -#else - zis->readBytes(buf, tw * th * (BPP / 8)); -#endif - - } else { - - // packed pixels - int bppp = ((palSize > 16) ? 8 : - ((palSize > 4) ? 4 : ((palSize > 2) ? 2 : 1))); - - PIXEL_T* ptr = buf; - - for (int i = 0; i < th; i++) { - PIXEL_T* eol = ptr + tw; - U8 byte = 0; - U8 nbits = 0; - - while (ptr < eol) { - if (nbits == 0) { - byte = zis->readU8(); - nbits = 8; - } - nbits -= bppp; - U8 index = (byte >> nbits) & ((1 << bppp) - 1) & 127; - *ptr++ = palette[index]; - } - } - } - -#ifdef FAVOUR_FILL_RECT - //fprintf(stderr,"copying data to screen %dx%d at %d,%d\n",tw,th,tx,ty); - IMAGE_RECT(tx,ty,tw,th,buf); -#endif - - } else { - - if (palSize == 0) { - - // plain RLE - - PIXEL_T* ptr = buf; - PIXEL_T* end = ptr + th * tw; - while (ptr < end) { - PIXEL_T pix = zis->READ_PIXEL(); - int len = 1; - int b; - do { - b = zis->readU8(); - len += b; - } while (b == 255); - - assert(len <= end - ptr); - -#ifdef FAVOUR_FILL_RECT - int i = ptr - buf; - ptr += len; - - int runX = i % tw; - int runY = i / tw; - - if (runX + len > tw) { - if (runX != 0) { - FILL_RECT(tx+runX, ty+runY, tw-runX, 1, pix); - len -= tw-runX; - runX = 0; - runY++; - } - - if (len > tw) { - FILL_RECT(tx, ty+runY, tw, len/tw, pix); - runY += len / tw; - len = len % tw; - } - } - - if (len != 0) { - FILL_RECT(tx+runX, ty+runY, len, 1, pix); - } -#else - while (len-- > 0) *ptr++ = pix; -#endif - - } - } else { - - // palette RLE - - PIXEL_T* ptr = buf; - PIXEL_T* end = ptr + th * tw; - while (ptr < end) { - int index = zis->readU8(); - int len = 1; - if (index & 128) { - int b; - do { - b = zis->readU8(); - len += b; - } while (b == 255); - - assert(len <= end - ptr); - } - - index &= 127; - - PIXEL_T pix = palette[index]; - -#ifdef FAVOUR_FILL_RECT - int i = ptr - buf; - ptr += len; - - int runX = i % tw; - int runY = i / tw; - - if (runX + len > tw) { - if (runX != 0) { - FILL_RECT(tx+runX, ty+runY, tw-runX, 1, pix); - len -= tw-runX; - runX = 0; - runY++; - } - - if (len > tw) { - FILL_RECT(tx, ty+runY, tw, len/tw, pix); - runY += len / tw; - len = len % tw; - } - } - - if (len != 0) { - FILL_RECT(tx+runX, ty+runY, len, 1, pix); - } -#else - while (len-- > 0) *ptr++ = pix; -#endif - } - } - } - -#ifndef FAVOUR_FILL_RECT - //fprintf(stderr,"copying data to screen %dx%d at %d,%d\n",tw,th,tx,ty); - IMAGE_RECT(tx,ty,tw,th,buf); -#endif - } - } - - zis->reset(); -} - -#undef ZRLE_DECODE_BPP -#undef READ_PIXEL -#undef PIXEL_T diff --git a/zrleEncode.h b/zrleEncode.h deleted file mode 100644 index 6d58a5a..0000000 --- a/zrleEncode.h +++ /dev/null @@ -1,310 +0,0 @@ -// -// Copyright (C) 2002 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. - -// -// zrleEncode.h - zrle encoding function. -// -// Before including this file, you must define a number of CPP macros. -// -// BPP should be 8, 16 or 32 depending on the bits per pixel. -// GET_IMAGE_INTO_BUF should be some code which gets a rectangle of pixel data -// into the given buffer. EXTRA_ARGS can be defined to pass any other -// arguments needed by GET_IMAGE_INTO_BUF. -// -// Note that the buf argument to ZRLE_ENCODE needs to be at least one pixel -// bigger than the largest tile of pixel data, since the ZRLE encoding -// algorithm writes to the position one past the end of the pixel data. -// - -#include <rdr/OutStream.h> -#include <assert.h> - -using namespace rdr; - -/* __RFB_CONCAT2 concatenates its two arguments. __RFB_CONCAT2E does the same - but also expands its arguments if they are macros */ - -#ifndef __RFB_CONCAT2E -#define __RFB_CONCAT2(a,b) a##b -#define __RFB_CONCAT2E(a,b) __RFB_CONCAT2(a,b) -#endif - -#ifdef CPIXEL -#define PIXEL_T __RFB_CONCAT2E(rdr::U,BPP) -#define WRITE_PIXEL __RFB_CONCAT2E(writeOpaque,CPIXEL) -#define ZRLE_ENCODE __RFB_CONCAT2E(zrleEncode,CPIXEL) -#define ZRLE_ENCODE_TILE __RFB_CONCAT2E(zrleEncodeTile,CPIXEL) -#define BPPOUT 24 -#else -#define PIXEL_T __RFB_CONCAT2E(rdr::U,BPP) -#define WRITE_PIXEL __RFB_CONCAT2E(writeOpaque,BPP) -#define ZRLE_ENCODE __RFB_CONCAT2E(zrleEncode,BPP) -#define ZRLE_ENCODE_TILE __RFB_CONCAT2E(zrleEncodeTile,BPP) -#define BPPOUT BPP -#endif - -#ifndef ZRLE_ONCE -#define ZRLE_ONCE -static const int bitsPerPackedPixel[] = { - 0, 1, 2, 2, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4 -}; - -// The PaletteHelper class helps us build up the palette from pixel data by -// storing a reverse index using a simple hash-table - -class PaletteHelper { -public: - enum { MAX_SIZE = 127 }; - - PaletteHelper() - { - memset(index, 255, sizeof(index)); - size = 0; - } - - inline int hash(rdr::U32 pix) - { - return (pix ^ (pix >> 17)) & 4095; - } - - inline void insert(rdr::U32 pix) - { - if (size < MAX_SIZE) { - int i = hash(pix); - while (index[i] != 255 && key[i] != pix) - i++; - if (index[i] != 255) return; - - index[i] = size; - key[i] = pix; - palette[size] = pix; - } - size++; - } - - inline int lookup(rdr::U32 pix) - { - assert(size <= MAX_SIZE); - int i = hash(pix); - while (index[i] != 255 && key[i] != pix) - i++; - if (index[i] != 255) return index[i]; - return -1; - } - - rdr::U32 palette[MAX_SIZE]; - rdr::U8 index[4096+MAX_SIZE]; - rdr::U32 key[4096+MAX_SIZE]; - int size; -}; -#endif - -void ZRLE_ENCODE_TILE (PIXEL_T* data, int w, int h, rdr::OutStream* os); - -void ZRLE_ENCODE (int x, int y, int w, int h, rdr::OutStream* os, - rdr::ZlibOutStream* zos, void* buf - EXTRA_ARGS - ) -{ - zos->setUnderlying(os); - - for (int ty = y; ty < y+h; ty += rfbZRLETileHeight) { - int th = rfbZRLETileHeight; - if (th > y+h-ty) th = y+h-ty; - for (int tx = x; tx < x+w; tx += rfbZRLETileWidth) { - int tw = rfbZRLETileWidth; - if (tw > x+w-tx) tw = x+w-tx; - - GET_IMAGE_INTO_BUF(tx,ty,tw,th,buf); - - ZRLE_ENCODE_TILE((PIXEL_T*)buf, tw, th, zos); - } - } - zos->flush(); -} - - -void ZRLE_ENCODE_TILE (PIXEL_T* data, int w, int h, rdr::OutStream* os) -{ - // First find the palette and the number of runs - - PaletteHelper ph; - - int runs = 0; - int singlePixels = 0; - - PIXEL_T* ptr = data; - PIXEL_T* end = ptr + h * w; - *end = ~*(end-1); // one past the end is different so the while loop ends - - while (ptr < end) { - PIXEL_T pix = *ptr; - if (*++ptr != pix) { - singlePixels++; - } else { - while (*++ptr == pix) ; - runs++; - } - ph.insert(pix); - } - - //fprintf(stderr,"runs %d, single pixels %d, paletteSize %d\n", - // runs, singlePixels, ph.size); - - // Solid tile is a special case - - if (ph.size == 1) { - os->writeU8(1); - os->WRITE_PIXEL(ph.palette[0]); - return; - } - - // Try to work out whether to use RLE and/or a palette. We do this by - // estimating the number of bytes which will be generated and picking the - // method which results in the fewest bytes. Of course this may not result - // in the fewest bytes after compression... - - bool useRle = false; - bool usePalette = false; - - int estimatedBytes = w * h * (BPPOUT/8); // start assuming raw - - int plainRleBytes = ((BPPOUT/8)+1) * (runs + singlePixels); - - if (plainRleBytes < estimatedBytes) { - useRle = true; - estimatedBytes = plainRleBytes; - } - - if (ph.size < 128) { - int paletteRleBytes = (BPPOUT/8) * ph.size + 2 * runs + singlePixels; - - if (paletteRleBytes < estimatedBytes) { - useRle = true; - usePalette = true; - estimatedBytes = paletteRleBytes; - } - - if (ph.size < 17) { - int packedBytes = ((BPPOUT/8) * ph.size + - w * h * bitsPerPackedPixel[ph.size-1] / 8); - - if (packedBytes < estimatedBytes) { - useRle = false; - usePalette = true; - estimatedBytes = packedBytes; - } - } - } - - if (!usePalette) ph.size = 0; - - os->writeU8((useRle ? 128 : 0) | ph.size); - - for (int i = 0; i < ph.size; i++) { - os->WRITE_PIXEL(ph.palette[i]); - } - - if (useRle) { - - PIXEL_T* ptr = data; - PIXEL_T* end = ptr + w * h; - PIXEL_T* runStart; - PIXEL_T pix; - while (ptr < end) { - runStart = ptr; - pix = *ptr++; - while (*ptr == pix && ptr < end) - ptr++; - int len = ptr - runStart; - if (len <= 2 && usePalette) { - int index = ph.lookup(pix); - if (len == 2) - os->writeU8(index); - os->writeU8(index); - continue; - } - if (usePalette) { - int index = ph.lookup(pix); - os->writeU8(index | 128); - } else { - os->WRITE_PIXEL(pix); - } - len -= 1; - while (len >= 255) { - os->writeU8(255); - len -= 255; - } - os->writeU8(len); - } - - } else { - - // no RLE - - if (usePalette) { - - // packed pixels - - assert (ph.size < 17); - - int bppp = bitsPerPackedPixel[ph.size-1]; - - PIXEL_T* ptr = data; - - for (int i = 0; i < h; i++) { - U8 nbits = 0; - U8 byte = 0; - - PIXEL_T* eol = ptr + w; - - while (ptr < eol) { - PIXEL_T pix = *ptr++; - U8 index = ph.lookup(pix); - byte = (byte << bppp) | index; - nbits += bppp; - if (nbits >= 8) { - os->writeU8(byte); - nbits = 0; - } - } - if (nbits > 0) { - byte <<= 8 - nbits; - os->writeU8(byte); - } - } - } else { - - // raw - -#ifdef CPIXEL - for (PIXEL_T* ptr = data; ptr < data+w*h; ptr++) { - os->WRITE_PIXEL(*ptr); - } -#else - os->writeBytes(data, w*h*(BPP/8)); -#endif - } - } -} - -#undef PIXEL_T -#undef WRITE_PIXEL -#undef ZRLE_ENCODE -#undef ZRLE_ENCODE_TILE -#undef BPPOUT |