Fix handling of multiple VNC commands per websockets frame

- When processing input, check if there is any extra data
  pending in the internal websocket frame and SSL buffers.
- Prevents input events lagging behind because they get
  stuck in one of the buffers.
  Data pending in our own buffers cannot be detected with
  select() so was not processed until more input arrives
  from the network.
- Closes # 55

Signed-off-by: Floris Bos <bos@je-eigen-domein.nl>
pull/1/head
Floris Bos 10 years ago
parent a48035a1ce
commit 6836ccb208

@ -550,7 +550,15 @@ clientInput(void *data)
rfbSendFileTransferChunk(cl); rfbSendFileTransferChunk(cl);
if (FD_ISSET(cl->sock, &rfds) || FD_ISSET(cl->sock, &efds)) if (FD_ISSET(cl->sock, &rfds) || FD_ISSET(cl->sock, &efds))
{
#ifdef LIBVNCSERVER_WITH_WEBSOCKETS
do {
rfbProcessClientMessage(cl);
} while (webSocketsHasDataInBuffer(cl));
#else
rfbProcessClientMessage(cl); rfbProcessClientMessage(cl);
#endif
}
} }
/* Get rid of the output thread. */ /* Get rid of the output thread. */

@ -391,7 +391,15 @@ rfbCheckFds(rfbScreenInfoPtr rfbScreen,long usec)
if (FD_ISSET(cl->sock, &(rfbScreen->allFds))) if (FD_ISSET(cl->sock, &(rfbScreen->allFds)))
{ {
if (FD_ISSET(cl->sock, &fds)) if (FD_ISSET(cl->sock, &fds))
{
#ifdef LIBVNCSERVER_WITH_WEBSOCKETS
do {
rfbProcessClientMessage(cl); rfbProcessClientMessage(cl);
} while (webSocketsHasDataInBuffer(cl));
#else
rfbProcessClientMessage(cl);
#endif
}
else else
rfbSendFileTransferChunk(cl); rfbSendFileTransferChunk(cl);
} }

@ -905,3 +905,16 @@ webSocketCheckDisconnect(rfbClientPtr cl)
return FALSE; return FALSE;
} }
/* returns TRUE if there is data waiting to be read in our internal buffer
* or if is there any pending data in the buffer of the SSL implementation
*/
rfbBool
webSocketsHasDataInBuffer(rfbClientPtr cl)
{
ws_ctx_t *wsctx = (ws_ctx_t *)cl->wsctx;
if (wsctx && wsctx->readbuflen)
return TRUE;
return (cl->sslctx && rfbssl_pending(cl) > 0);
}

@ -765,6 +765,7 @@ extern rfbBool webSocketsCheck(rfbClientPtr cl);
extern rfbBool webSocketCheckDisconnect(rfbClientPtr cl); extern rfbBool webSocketCheckDisconnect(rfbClientPtr cl);
extern int webSocketsEncode(rfbClientPtr cl, const char *src, int len, char **dst); extern int webSocketsEncode(rfbClientPtr cl, const char *src, int len, char **dst);
extern int webSocketsDecode(rfbClientPtr cl, char *dst, int len); extern int webSocketsDecode(rfbClientPtr cl, char *dst, int len);
extern rfbBool webSocketsHasDataInBuffer(rfbClientPtr cl);
#endif #endif
/* rfbserver.c */ /* rfbserver.c */

Loading…
Cancel
Save