diff --git a/ChangeLog b/ChangeLog index bae15d52..3173c2c6 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,7 @@ +2002-03-18 Tim Jansen + + * removed vertical splitting of tiles, simplifies code. + 2002-03-11 Tim Jansen * integrated KCModule diff --git a/ROADMAP b/ROADMAP index 8de022ce..bfac5fd2 100644 --- a/ROADMAP +++ b/ROADMAP @@ -12,10 +12,11 @@ Version 0.7: Better integration with KDE, improved GUI -> remove debug msgs, better error handling -> fetch new services while running - invitation support - -> check for xp dialogs + -> check xp dialogs as model + -> make sure request is completely ignored if password is available - kcontrol module -> on startup a dialog appears that allows the user to invite somebody - using email (and later other mechanisms). Dialog can be turned off forever, + using email (and later other mechanisms). Dialog can be turned off forever, of course -> remove STDOUT/STDERR logging -> add isConnected() dcop call diff --git a/TODO b/TODO index aa9e6289..1368f812 100644 --- a/TODO +++ b/TODO @@ -1,5 +1,6 @@ -Todo: +Todo (unscheduled features): - SLP support (or UPnP, or whatever KDE will use) +- NAT traversal support (MIDCOM stun/turn, UPnP) - look into adding extension to xfree to improve speed (get noticed of screen updates) diff --git a/kinetd/kinetd.cpp b/kinetd/kinetd.cpp index 983a7a5d..e0b0e123 100644 --- a/kinetd/kinetd.cpp +++ b/kinetd/kinetd.cpp @@ -32,8 +32,6 @@ PortListener::PortListener(KService::Ptr s) { loadConfig(s); - process.setExecutable(execPath); - port = portBase; socket = new KServerSocket(port, false); while (!socket->bindAndListen()) { @@ -109,10 +107,15 @@ void PortListener::accepted(KSocket *sock) { } process.clearArguments(); - process << argument << sock->socket(); + process << execPath << argument << QString::number(sock->socket()); if (!process.start(KProcess::DontCare)) { - kdDebug() << "kinetd: Calling process failed" << endl; + kdDebug() << "kinetd: Process \"" << execPath << " " << + argument << " "<< sock->socket() << + "\" call failed" << endl; } + else + kdDebug() << "kinetd: Calling process, ok" << endl; + delete sock; } diff --git a/krfb/main.cpp b/krfb/main.cpp index 18e161c6..ded2e688 100644 --- a/krfb/main.cpp +++ b/krfb/main.cpp @@ -47,7 +47,7 @@ static const char *description = I18N_NOOP("VNC-compatible server to share " #define ARG_DONT_CONFIRM_CONNECT "dont-confirm-connect" #define ARG_REMOTE_CONTROL "remote-control" #define ARG_STAND_ALONE "stand-alone" -#define ARG_KINETD "kinetd " +#define ARG_KINETD "kinetd" static KCmdLineOptions options[] = @@ -62,7 +62,7 @@ static KCmdLineOptions options[] = { ARG_REMOTE_CONTROL, I18N_NOOP("Allow remote side to control this computer."), 0}, { "s", 0, 0}, { ARG_STAND_ALONE, I18N_NOOP("Stand-alone mode, do not use daemon."), 0}, - { ARG_KINETD, I18N_NOOP("Used for calling from kinetd."), 0}, + { ARG_KINETD " ", I18N_NOOP("Used for calling from kinetd."), 0}, { 0, 0, 0 } }; @@ -170,15 +170,16 @@ int main(int argc, char *argv[]) allowDesktopControl, password); mode = KRFB_STAND_ALONE_CMDARG; } - else if (args->isSet(ARG_STAND_ALONE)) { - mode = KRFB_STAND_ALONE; - } - else if (args->isSet(ARG_KINETD)) { - fdString = args->getOption(ARG_KINETD); - mode = KRFB_KINETD_MODE; - } - else + else { + if (args->isSet(ARG_STAND_ALONE)) { + mode = KRFB_STAND_ALONE; + } + else if (args->isSet(ARG_KINETD)) { + fdString = args->getOption(ARG_KINETD); + mode = KRFB_KINETD_MODE; + } config = new Configuration(); + } args->clear(); if (mode == KRFB_UNKNOWN_MODE) @@ -186,6 +187,7 @@ int main(int argc, char *argv[]) if (mode == KRFB_INVITATION_MODE) { // TODO: display invitation + kdDebug() << "invitation mode" < */ @@ -39,19 +38,16 @@ #include "xupdatescanner.h" -int scanlines[32] = { 0, 16, 8, 24, - 4, 20, 12, 28, - 10, 26, 18, 2, - 22, 6, 30, 14, - 1, 17, 9, 25, - 7, 23, 15, 31, - 19, 3, 27, 11, - 29, 13, 5, 21 }; +unsigned int scanlines[32] = { 0, 16, 8, 24, + 4, 20, 12, 28, + 10, 26, 18, 2, + 22, 6, 30, 14, + 1, 17, 9, 25, + 7, 23, 15, 31, + 19, 3, 27, 11, + 29, 13, 5, 21 }; #define MAX_ADJ_TOLERANCE 8 -#define abs(x) (((x) >= 0) ? (x) : -(x)) - - XUpdateScanner::XUpdateScanner(Display *_dpy, Window _window, unsigned char *_fb, @@ -97,7 +93,8 @@ XUpdateScanner::XUpdateScanner(Display *_dpy, tileMap = new bool[tilesX * tilesY]; tileRegionMap = new struct TileChangeRegion[tilesX * tilesY]; - for (int i = 0; i < tilesX * tilesY; i++) + unsigned int i; + for (i = 0; i < tilesX * tilesY; i++) tileMap[i] = false; scanline = XShmCreateImage(dpy, @@ -134,92 +131,11 @@ XUpdateScanner::~XUpdateScanner() shmctl(shminfo_tile.shmid, IPC_RMID, 0); } -// check whether at the given line there is a right half in the tile -bool XUpdateScanner::checkRight(unsigned char *src, - unsigned char *dest, - int halfWidthBytes) -{ - return memcmp(dest + halfWidthBytes, - src + halfWidthBytes, - halfWidthBytes) != 0; -} - -// check whether the half exists in the tile -bool XUpdateScanner::checkSide(unsigned char *src, - unsigned char *dest, - int halfWidthBytes, - int n) -{ - for (int i = 0; i < n; i++) { - if (memcmp(dest + halfWidthBytes, - src + halfWidthBytes, - halfWidthBytes)) - return true; - src += tile->bytes_per_line; - dest += bytesPerLine; - } - return false; -} - -// finds the first changed line in the tile -int XUpdateScanner::findFirstLine(int maxHeight, - unsigned char *&ssrc, - unsigned char *&sdest, - int halfWidthBytes, - bool &left) { - int firstLine = maxHeight; - left = true; - for (int line = 0; line < maxHeight; line++) { - if (memcmp(sdest, ssrc, halfWidthBytes)) { - firstLine = line; - break; - } - if (memcmp(sdest + halfWidthBytes, - ssrc + halfWidthBytes, - halfWidthBytes)) { - firstLine = line; - left = false; - break; - } - ssrc += tile->bytes_per_line; - sdest += bytesPerLine; - } - return firstLine; -} - -// finds the last changed line in the tile -int XUpdateScanner::findLastLine(int maxHeight, - int firstLine, - unsigned char *msrc, - unsigned char *mdest, - int halfWidthBytes, - bool &left) { - int lastLine = firstLine; - left = true; - - for (int line = maxHeight-1; line > firstLine; line--) { - msrc -= tile->bytes_per_line; - mdest -= bytesPerLine; - if (memcmp(mdest, msrc, halfWidthBytes)) { - lastLine = line; - break; - } - if (memcmp(mdest + halfWidthBytes, - msrc + halfWidthBytes, - halfWidthBytes)) { - lastLine = line; - left = false; - break; - } - } - return lastLine; -} - bool XUpdateScanner::copyTile(int x, int y, int tx, int ty) { - int maxWidth = width - x; - int maxHeight = height - y; + unsigned int maxWidth = width - x; + unsigned int maxHeight = height - y; if (maxWidth > tileWidth) maxWidth = tileWidth; if (maxHeight > tileHeight) @@ -231,94 +147,59 @@ bool XUpdateScanner::copyTile(int x, int y, int tx, int ty) XGetSubImage(dpy, window, x, y, maxWidth, maxHeight, AllPlanes, ZPixmap, tile, 0, 0); } - + unsigned int line; int pixelsize = bitsPerPixel >> 3; - int halfWidthBytes = (maxWidth*pixelsize)>>1; - bool hitLeft = true; - bool leftConfirmed = false; - bool rightConfirmed = false; unsigned char *src = (unsigned char*) tile->data; unsigned char *dest = fb + y * bytesPerLine + x * pixelsize; unsigned char *ssrc = src; unsigned char *sdest = dest; - // search first changed line - int firstLine = findFirstLine(maxHeight, ssrc, sdest, - halfWidthBytes, hitLeft); + int firstLine = maxHeight; + + for (line = 0; line < maxHeight; line++) { + if (memcmp(sdest, ssrc, maxWidth * pixelsize)) { + firstLine = line; + break; + } + ssrc += tile->bytes_per_line; + sdest += bytesPerLine; + } - // if no changes, leave if (firstLine == maxHeight) { tileMap[tx + ty * tilesX] = false; return false; } - - // try to get more information whether left&right half both changed - if (hitLeft) { - leftConfirmed = true; - rightConfirmed = checkRight(ssrc, sdest, halfWidthBytes); - } - else - rightConfirmed = true; unsigned char *msrc = src + (tile->bytes_per_line * maxHeight); unsigned char *mdest = dest + (bytesPerLine * maxHeight); - // find the last line in the tile - int lastLine = findLastLine(maxHeight, firstLine, msrc, mdest, - halfWidthBytes, hitLeft); - // try to get more information whether left&right half both changed - if (hitLeft) { - leftConfirmed = true; - if (!rightConfirmed) - rightConfirmed = checkRight(ssrc, sdest, halfWidthBytes); - } - else - rightConfirmed = true; - - // now complete information about right&left half - if (!leftConfirmed) - leftConfirmed = checkSide(sdest, ssrc, halfWidthBytes, - lastLine-firstLine+1); - if (!rightConfirmed) - rightConfirmed = checkSide(sdest+halfWidthBytes, - ssrc+halfWidthBytes, - halfWidthBytes, - lastLine-firstLine+1); - - // identify what halfes to copy - int cw; - if (leftConfirmed && rightConfirmed) - cw = maxWidth * pixelsize; - else { - cw = halfWidthBytes; - if (rightConfirmed) { - sdest += halfWidthBytes; - ssrc += halfWidthBytes; + int lastLine = firstLine; + + for (line = maxHeight-1; line > firstLine; line--) { + msrc -= tile->bytes_per_line; + mdest -= bytesPerLine; + if (memcmp(mdest, msrc, maxWidth * pixelsize)) { + lastLine = line; + break; } - else - assert(leftConfirmed); - } + } - // copy the stuff into the framebuffer - for (int line = firstLine; line <= lastLine; line++) { - memcpy(sdest, ssrc, cw); + for (line = firstLine; line <= lastLine; line++) { + memcpy(sdest, ssrc, maxWidth * pixelsize ); ssrc += tile->bytes_per_line; sdest += bytesPerLine; } - // set the descriptor struct TileChangeRegion *r = &tileRegionMap[tx + (ty * tilesX)]; r->firstLine = firstLine; r->lastLine = lastLine; - r->leftSide = leftConfirmed; - r->rightSide = rightConfirmed; return lastLine == (maxHeight-1); } void XUpdateScanner::copyAllTiles() { - for (int y = 0; y < tilesY; y++) { - for (int x = 0; x < tilesX; x++) { + for (unsigned int y = 0; y < tilesY; y++) { + for (unsigned int x = 0; x < tilesX; x++) { if (tileMap[x + y * tilesX]) if (copyTile(x*tileWidth, y*tileHeight, x, y) && ((y+1) < tilesY)) @@ -328,20 +209,12 @@ void XUpdateScanner::copyAllTiles() } -void XUpdateScanner::createHintFromTile(int x, int y, int th, Hint &hint, - struct TileChangeRegion *r) +void XUpdateScanner::createHintFromTile(int x, int y, int th, Hint &hint) { - int tw = tileWidth; - if (r->leftSide ^ r->rightSide) { - tw = tileWidth>>1; - if (r->rightSide) - x += tw; - } - - int w = width - x; - int h = height - y; - if (w > tw) - w = tw; + unsigned int w = width - x; + unsigned int h = height - y; + if (w > tileWidth) + w = tileWidth; if (h > th) h = th; @@ -351,36 +224,16 @@ void XUpdateScanner::createHintFromTile(int x, int y, int th, Hint &hint, hint.h = h; } -// adds a tile to the right of the given existing tile -bool XUpdateScanner::addTileToHint(int x, int y, int wInTiles, - int th, Hint &hint, - struct TileChangeRegion *r) +void XUpdateScanner::addTileToHint(int x, int y, int th, Hint &hint) { - // tiles are always added to the right, so if this one has no left half.. - if (!r->leftSide) - return false; - // or the previous one no right half, leave - struct TileChangeRegion *prev = r-1; - if (!prev->rightSide) - return false; - - // half width for tiles without right half - int tw = tileWidth; - if (!r->rightSide) - tw = tileWidth>>1; - - int w = width - x; - int h = height - y; - if (w > tw) - w = tw; +// todo: refuse to add hint if this one is much smaller or bigger (use x0) + unsigned int w = width - x; + unsigned int h = height - y; + if (w > tileWidth) + w = tileWidth; if (h > th) h = th; - if ((wInTiles*abs(hint.y-y)) > MAX_ADJ_TOLERANCE) - return false; - if ((wInTiles*abs((hint.y+hint.h)-(y+h))) > MAX_ADJ_TOLERANCE) - return false; - if (hint.x > x) { hint.w += hint.x - x; hint.x = x; @@ -398,25 +251,16 @@ bool XUpdateScanner::addTileToHint(int x, int y, int wInTiles, if ((hint.y+hint.h) < (y+h)) { hint.h = (y+h) - hint.y; } - return true; } -// examines and possibly joins tiles under the hint with the hint void XUpdateScanner::extendHintY(int x, int y, int x0, Hint &hint) { int eh = 0; int lastLine = -1; int w = x - x0 + 1; - bool leftHalf = !tileRegionMap[x0 + y * tilesX].leftSide; - bool rightHalf = !tileRegionMap[x - 1 + y * tilesX].rightSide; - for (int i = y+1; i < tilesY; i++) { bool lk = true; int ll = 0; - if (leftHalf && tileRegionMap[x0 + i * tilesX].leftSide) - break; - if (rightHalf && tileRegionMap[x - 1 + i * tilesX].rightSide) - break; for (int j = x0; j < x; j++) { int idx = j + i * tilesX; if ((!tileMap[idx]) || @@ -464,10 +308,9 @@ static void printStatistics(Hint &hint) { ssum += p; snum++; float avg = ssum / snum; - kdDebug() << "avg size saved: "<< avg <<"%"< &hintList) { @@ -485,12 +328,10 @@ void XUpdateScanner::flushHint(int x, int y, int &x0, assert (hint.h > 0); //printStatistics(hint); -kdDebug() << "size: "<< hint.w << "/"< &hintList) { Hint hint; @@ -500,31 +341,25 @@ void XUpdateScanner::createHints(QPtrList &hintList) int x; for (x = 0; x < tilesX; x++) { int idx = x + y * tilesX; - if (!tileMap[idx]) { + if (tileMap[idx]) { + int ty = tileRegionMap[idx].firstLine; + int th = tileRegionMap[idx].lastLine - ty +1; + if (x0 < 0) { + createHintFromTile(x * tileWidth, + (y * tileHeight) + ty, + th, + hint); + x0 = x; + } + else { + addTileToHint(x * tileWidth, + (y * tileHeight) + ty, + th, + hint); + } + } + else flushHint(x, y, x0, hint, hintList); - continue; - } - struct TileChangeRegion *r = &tileRegionMap[idx]; - int ty = r->firstLine; - int th = r->lastLine - ty +1; - if (x0 < 0) { - createHintFromTile(x * tileWidth, - (y * tileHeight) + ty, - th, hint, r); - x0 = x; - continue; - } - if (!addTileToHint(x * tileWidth, - (y * tileHeight) + ty, - x0 - x + 1, - th, hint, r)) { - flushHint(x, y, x0, hint, hintList); - createHintFromTile(x * tileWidth, - (y * tileHeight) + ty, - th, hint, r); - x0 = x; - - } } flushHint(x, y, x0, hint, hintList); } @@ -535,8 +370,8 @@ void XUpdateScanner::searchUpdates(QPtrList &hintList) count++; count %= 32; - int i; - int x, y; + unsigned int i; + unsigned int x, y; for (i = 0; i < (tilesX * tilesY); i++) { tileMap[i] = false; diff --git a/krfb/xupdatescanner.h b/krfb/xupdatescanner.h index acf8697e..3d5f0007 100644 --- a/krfb/xupdatescanner.h +++ b/krfb/xupdatescanner.h @@ -59,7 +59,6 @@ class Hint { struct TileChangeRegion { short firstLine, lastLine; - bool leftSide, rightSide; }; @@ -84,30 +83,17 @@ class XUpdateScanner void flushHint(int x, int y, int &x0, Hint &hint, QPtrList &hintList); void createHints(QPtrList &hintList); - bool addTileToHint(int x, int y, int x0, int th, Hint &hint, - struct TileChangeRegion *r); - void createHintFromTile(int x, int y, int th, Hint &hint, - struct TileChangeRegion *r); - void extendHintY(int x, int y, int wInTiles, Hint &h); - int findFirstLine(int maxH, unsigned char *&ssrc, - unsigned char *&sdest, int halfWidthBytes, - bool &left); - int findLastLine(int maxH, int firstL, unsigned char *msrc, - unsigned char *mdest, int halfWidthBytes, - bool &left); - bool checkRight(unsigned char *src, - unsigned char *dest, - int halfWidthBytes); - bool checkSide(unsigned char *src, unsigned char *dest, - int halfWidthBytes, int n); + void addTileToHint(int x, int y, int th, Hint &hint); + void createHintFromTile(int x, int y, int th, Hint &hint); + void extendHintY(int x, int y, int x0, Hint &h); Display *dpy; Window window; unsigned char *fb; int width, height; int bitsPerPixel, bytesPerLine; - int tileWidth, tileHeight; - int count; + unsigned int tileWidth, tileHeight; + unsigned int count; XImage *scanline; XShmSegmentInfo shminfo_scanline; @@ -115,7 +101,7 @@ class XUpdateScanner XImage *tile; XShmSegmentInfo shminfo_tile; - int tilesX, tilesY; + unsigned int tilesX, tilesY; bool *tileMap; struct TileChangeRegion *tileRegionMap; }; diff --git a/libvncserver/CHANGES b/libvncserver/CHANGES index 14dda0d2..ccc89503 100644 --- a/libvncserver/CHANGES +++ b/libvncserver/CHANGES @@ -1,3 +1,9 @@ + 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 restarting with special options if compiling + with LOCAL_CONTROL defined 0.3 added x11vnc, a x0rfbserver clone regard deferUpdateTime in processEvents, if usec<0 diff --git a/libvncserver/main.c b/libvncserver/main.c index 81c3c656..6a7f43ff 100644 --- a/libvncserver/main.c +++ b/libvncserver/main.c @@ -299,14 +299,14 @@ listenerRun(void *data) rfbClientPtr cl; int len; - len = sizeof(peer); - if (rfbScreen->inetdSock != -1) { cl = rfbNewClient(rfbScreen, rfbScreen->inetdSock); - rfbStartOnHoldClient(cl); + if (cl && !cl->onHold ) + rfbStartOnHoldClient(cl); return; } - + + len = sizeof(peer); /* TODO: this thread wont die by restarting the server */ while ((client_fd = accept(rfbScreen->rfbListenSock, (struct sockaddr*)&peer, &len)) >= 0) { diff --git a/libvncserver/rfbserver.c b/libvncserver/rfbserver.c index 2190aef7..dbbf226e 100644 --- a/libvncserver/rfbserver.c +++ b/libvncserver/rfbserver.c @@ -42,6 +42,13 @@ #include #endif +#ifdef DEBUGPROTO +#undef DEBUGPROTO +#define DEBUGPROTO(x) x +#else +#define DEBUGPROTO(x) +#endif + rfbClientPtr pointerClient = NULL; /* Mutex for pointer events */ static void rfbProcessClientProtocolVersion(rfbClientPtr cl); diff --git a/libvncserver/sockets.c b/libvncserver/sockets.c index 1496f75f..812e4f8a 100644 --- a/libvncserver/sockets.c +++ b/libvncserver/sockets.c @@ -188,7 +188,7 @@ rfbCheckFds(rfbScreenInfoPtr rfbScreen,long usec) memcpy((char *)&fds, (char *)&(rfbScreen->allFds), sizeof(fd_set)); tv.tv_sec = 0; tv.tv_usec = usec; - nfds = select(rfbScreen->maxFd + 1, &fds, NULL, NULL, &tv); + nfds = select(rfbScreen->maxFd + 1, &fds, NULL, NULL /* &fds */, &tv); if (nfds == 0) { return; } @@ -451,7 +451,7 @@ WriteExact(cl, buf, len) FD_SET(sock, &fds); tv.tv_sec = 5; tv.tv_usec = 0; - n = select(sock+1, NULL, &fds, NULL, &tv); + n = select(sock+1, NULL, &fds, NULL /* &fds */, &tv); if (n < 0) { rfbLogPerror("WriteExact: select"); UNLOCK(cl->outputMutex);