Closed aaditmshah closed 5 years ago
Interesting. Which server are you using?
With rfb2 as only connection ( x11vnc / ubuntu virtualbox ) everything works as expected
2 connectins - still ok ( first connect "chicken of the vnc" in view mode, then start script )
I am using the Vine (OSXvnc) Server on Snow Leopard. The VNC viewer which I'm using is Flashlight VNC. From what I understand the server only sends framebuffer updates when a client requests for it. I suspect that the client doesn't receive the updates because it never requested for them.
Another possible problem could be that node-rfb2 doesn't send the keys immediately. I know that you flush the stream on every event:
RfbClient.prototype.pointerEvent = function(x, y, buttons)
{
var stream = this.pack_stream;
stream.pack('CCSS', [rfb.clientMsgTypes.pointerEvent, buttons, x, y]);
stream.flush();
}
RfbClient.prototype.keyEvent = function(keysym, isDown)
{
var stream = this.pack_stream;
stream.pack('CCxxL', [rfb.clientMsgTypes.keyEvent, isDown, keysym]);
stream.flush();
}
However on flush
you only seem to be generating new data
events:
UnpackStream.prototype.flush = function(stream)
{
// TODO: measure performance benefit of
// creating and writing one big concatenated buffer
// TODO: check write result
// pause/resume streaming
for (var i=0; i < this.write_queue.length; ++i)
{
//stream.write(this.write_queue[i])
this.emit('data', this.write_queue[i]);
}
this.write_queue = [];
this.write_length = 0;
}
I don't see where you're actually flushing the stream. Plus node.js net.Socket
objects don't even have a flush
method. The do however have a setNoDelay
method which can be used to disable Nagle's algorithm (which is enabled by default).
Nagle's algorithm buffers data before sending it off to ensure that small messages don't waste a lot of bandwidth because each TCP datagram is of at least 64 bytes. I don't see you calling setNoDelay
anywhere:
$ grep -r setNoDelay node_modules/rfb2/
$ # no results
yes, it's not real os flush, it's "combine all write requests into one buffer and do stream.write()". Can you try to add setNoDelay on your setup? Iou could be right about buffering, 'send key' is a very small packet. Also to verify - try to send more keys ( like, few 100 of them ). Requesting updates should not affect keys directly (you can receive zero rectangles but still able to send keys and mouse events) , but it might trigger buffer to be written
I added the following lines to your createConnection
function to disable Nagle's algorithm:
function createConnection(params)
{
// first matched to list of supported by server will be used
if (!params.security)
params.security = [rfb.security.VNC, rfb.security.None];
var stream;
if (!params.stream) {
if (params.in)
stream = createRfbStream(params.rfbfile);
else {
if (!params.host)
params.host = '127.0.0.1';
if (!params.port)
params.port = 5900;
stream = net.createConnection(params.port, params.host);
}
} else {
stream = params.stream;
}
+ if (typeof stream.setNoDelay === "function") {
+ console.log("Disabling Nagle's algorithm.");
+ stream.setNoDelay();
+ }
+
// todo: move outside rfbclient
On running the script again it disables Nagle's algorithm but the problem still persists. This rules out the buffering problem. I suspect that the server does indeed get the key events but it doesn't push the framebuffer updates to the other vnc clients. Is there any RFB extension to enable the server to automatically push updates to clients?
I also sent a really long string (1234567890
* 10) on the 10 second and the 20 second marks. Still no difference. I'm pretty sure the server is receiving the events. It's just not sending the updates to the other VNC clients.
Unfortunately Vine crashes on my system ( 10.8.5 ) and I don't have Snow Leopard mac. I guess it's a server issue.
You can't tell server to send updates every time screen content is damaged. However, when you request update server will wait (well, usually, protocol does not specify this) until content is changed. I usually request new screen update on every received one but you could have different strategy
I'm having the same issue with TightVNC server on Ubuntu host. I have to put requestUpdate in my rect event handler and even though the request for update is sent very rapidly, the refresh rate on the screen is still extremely sluggish.
hm, can't reproduce: I installed tightvnc in ubuntu14.10/virtualbox and successfully connected with https://github.com/sidorares/node-x11/tree/master/examples/vncviewer - it's quite responsive
I'm having trouble with this VM http://sourceforge.net/projects/metasploitable/files/Metasploitable2/ using the sample code here: https://github.com/mgechev/js-vnc-demo-project (the vnc server on that VM is running on port 5900 with the password "password". Please don't mind other stuffs going on on that machine)
So I have a VNC server which can handle multiple clients. I connect to the server using a VNC viewer in view-only mode to see the output. Then I run the following node.js script to print some text in a text editor opened on the server side:
When I run this program no output can be seen on the VNC viewer until the
rfb.end
is called, at which point the entire output is displayed at once.In between if I connect to the server with a second instance of the VNC viewer then the output till then is displayed at once. After that everything works as expected.
What could be causing this problem? How to workaround it?