Commit 07287cfd authored by Joel Martin's avatar Joel Martin

Send seq nums and b64 encode based on query string.

Query string variable 'b64encode' determine if wsproxy b64 encodes the
results. Variable 'seq_num' determines if sequence numbers are
prepended. This way, sequence numbers are only used with the flash
WebSocket proxy.
parent 8759ea6f
......@@ -65,7 +65,7 @@
RFB.updateState('failed', "'file://' URL is incompatible with Adobe Flash");
} else {
WebSocket.__swfLocation = "include/web-socket-js/WebSocketMain.swf";
RFB.force_copy = true;
RFB.use_seq = true;
RFB.updateState('disconnected', 'Disconnected');
}
}
......
......@@ -83,7 +83,7 @@ RFB = {
ws : null, // Web Socket object
sendID : null,
force_copy : false,
use_seq : false,
version : "RFB 003.003\n",
state : 'disconnected',
......@@ -647,6 +647,84 @@ clientCutText: function (text) {
* Utility routines
*/
recv_message: function(e) {
//console.log(">> recv_message");
RQ = RQ.concat(Base64.decode(e.data, 0));
RFB.handle_message();
//console.log("<< recv_message");
},
recv_message_reorder: function(e) {
//console.log(">> recv_message_reorder");
var offset = e.data.indexOf(":") + 1;
var seq_num = parseInt(e.data.substr(0, offset-1));
if (RQ_seq_num == seq_num) {
RQ = RQ.concat(Base64.decode(e.data, offset));
RQ_seq_num++;
} else {
console.warn("sequence number mismatch RQ_seq_num:" + RQ_seq_num + ", seq_num:" + seq_num);
if (RQ_reorder.length > 20) {
RFB.updateState('failed', "Re-order queue too long");
} else {
RQ_reorder = RQ_reorder.concat(e.data.substr(0));
var i = 0;
while (i < RQ_reorder.length) {
var offset = RQ_reorder[i].indexOf(":") + 1;
var seq_num = parseInt(RQ_reorder[i].substr(0, offset-1));
console.log("Searching reorder list item " + i + ", seq_num " + seq_num);
if (seq_num == RQ_seq_num) {
/* Remove it from reorder queue, decode it and
* add it to the receive queue */
console.log("Found re-ordered packet seq_num " + seq_num);
RQ = RQ.concat(Base64.decode(RQ_reorder.splice(i, 1)[0], offset));
RQ_seq_num++;
i = 0; // Start search again for next one
} else {
i++;
}
}
}
}
RFB.handle_message();
//console.log("<< recv_message_reorder");
},
handle_message: function () {
switch (RFB.state) {
case 'disconnected':
console.error("Got data while disconnected");
break;
case 'reset':
/* close and reset connection */
RFB.disconnect();
RFB.init_ws();
break;
case 'failed':
console.log("Giving up!");
RFB.disconnect();
break;
case 'normal':
RFB.normal_msg();
/*
while (RQ.length > 0) {
if (RFB.normal_msg() && RFB.state == 'normal') {
console.log("More to process");
} else {
break;
}
}
*/
break;
default:
RFB.init_msg();
break;
}
},
send_string: function (str) {
//console.log(">> send_string: " + str);
RFB.send_array(str.split('').map(
......@@ -828,74 +906,18 @@ updateState: function(state, statusMsg) {
init_ws: function () {
console.log(">> init_ws");
var uri = "ws://" + RFB.host + ":" + RFB.port;
var uri = "ws://" + RFB.host + ":" + RFB.port + "/?b64encode";
if (RFB.use_seq) {
uri += "&seq_num";
}
console.log("connecting to " + uri);
RFB.ws = new WebSocket(uri);
RFB.ws.onmessage = function(e) {
//console.log(">> WebSocket.onmessage");
var offset = e.data.indexOf(":") + 1;
var seq_num = parseInt(e.data.substr(0, offset-1));
if (RQ_seq_num == seq_num) {
RQ = RQ.concat(Base64.decode(e.data, offset));
RQ_seq_num++;
} else {
console.warn("sequence number mismatch RQ_seq_num:" + RQ_seq_num + ", seq_num:" + seq_num);
if (RQ_reorder.length > 20) {
RFB.updateState('failed', "Re-order queue too long");
} else {
RQ_reorder = RQ_reorder.concat(e.data.substr(0));
var i = 0;
while (i < RQ_reorder.length) {
var offset = RQ_reorder[i].indexOf(":") + 1;
var seq_num = parseInt(RQ_reorder[i].substr(0, offset-1));
console.log("Searching reorder list item " + i + ", seq_num " + seq_num);
if (seq_num == RQ_seq_num) {
/* Remove it from reorder queue, decode it and
* add it to the receive queue */
console.log("Found re-ordered packet seq_num " + seq_num);
RQ = RQ.concat(Base64.decode(RQ_reorder.splice(i, 1)[0], offset));
RQ_seq_num++;
i = 0; // Start search again for next one
} else {
i++;
}
}
}
}
switch (RFB.state) {
case 'disconnected':
console.error("WebSocket.onmessage while disconnected");
break;
case 'reset':
/* close and reset connection */
RFB.disconnect();
RFB.init_ws();
break;
case 'failed':
console.log("Giving up!");
RFB.disconnect();
break;
case 'normal':
RFB.normal_msg();
/*
while (RQ.length > 0) {
if (RFB.normal_msg() && RFB.state == 'normal') {
console.log("More to process");
} else {
break;
}
}
*/
break;
default:
RFB.init_msg();
break;
}
//console.log("<< WebSocket.onmessage");
};
if (RFB.use_seq) {
RFB.ws.onmessage = RFB.recv_message_reorder;
} else {
RFB.ws.onmessage = RFB.recv_message;
}
RFB.ws.onopen = function(e) {
console.log(">> WebSocket.onopen");
RFB.updateState('ProtocolVersion', "Starting VNC handshake");
......
#!/usr/bin/python
import sys, os, socket, time, traceback
import sys, os, socket, time, traceback, re
from base64 import b64encode, b64decode
from select import select
buffer_size = 65536
send_seq = 0
client_settings = {}
server_handshake = """HTTP/1.1 101 Web Socket Protocol Handshake\r
Upgrade: WebSocket\r
......@@ -32,21 +33,27 @@ Traffic Legend:
def do_handshake(client):
global client_settings
handshake = client.recv(1024)
print "Handshake [%s]" % handshake
#print "Handshake [%s]" % handshake
if handshake.startswith("<policy-file-request/>"):
print "Sending:", policy_response
print "Sending flash policy response"
client.send(policy_response)
client.close()
return False
#handshake = client.recv(1024)
#if len(handshake) == 0:
# raise Exception("Policy exchange failed")
#print "Handshake [%s]" % handshake
req_lines = handshake.split("\r\n")
_, path, _ = req_lines[0].split(" ")
_, origin = req_lines[4].split(" ")
_, host = req_lines[3].split(" ")
# Parse settings from the path
cvars = path.partition('?')[2].partition('#')[0].split('&')
for cvar in [c for c in cvars if c]:
name, _, value = cvar.partition('=')
client_settings[name] = value and value or True
print "client_settings:", client_settings
client.send(server_handshake % (origin, host, path))
return True
......@@ -76,7 +83,7 @@ def proxy(client, target):
if tqueue and target in outs:
#print "Target send: %s" % repr(tqueue[0])
log.write("Target send: %s\n" % map(ord, tqueue[0]))
##log.write("Target send: %s\n" % map(ord, tqueue[0]))
dat = tqueue.pop(0)
sent = target.send(dat)
if sent == len(dat):
......@@ -90,25 +97,28 @@ def proxy(client, target):
sent = client.send(dat)
if sent == len(dat):
traffic("<")
log.write("Client send: %s\n" % repr(dat))
##log.write("Client send: %s\n" % repr(dat))
else:
cqueue.insert(0, dat[sent:])
traffic("<.")
log.write("Client send partial: %s\n" % repr(dat[0:send]))
##log.write("Client send partial: %s\n" % repr(dat[0:send]))
if target in ins:
buf = target.recv(buffer_size)
if len(buf) == 0: raise Exception("Target closed")
#enc = b64encode(buf)
#chksum = sum([ord(c) for c in enc])
#cqueue.append("\x00^" + str(chksum) + "@" + enc + "$\xff")
##log.write("Target recv (%d): %s\n" % (len(buf), map(ord, buf)))
cqueue.append("\x00%d:%s\xff" % (send_seq, b64encode(buf)))
send_seq += 1
if client_settings.get("b64encode"):
buf = b64encode(buf)
if client_settings.get("seq_num"):
cqueue.append("\x00%d:%s\xff" % (send_seq, buf))
send_seq += 1
else:
cqueue.append("\x00%s\xff" % buf)
log.write("Target recv (%d): %s\n" % (len(buf), map(ord, buf)))
traffic("{")
if client in ins:
......@@ -117,7 +127,7 @@ def proxy(client, target):
if buf[-1] == "\xff":
traffic("}")
log.write("Client recv (%d): %s\n" % (len(buf), repr(buf)))
##log.write("Client recv (%d): %s\n" % (len(buf), repr(buf)))
if cpartial:
tqueue.extend(decode(cpartial + buf))
cpartial = ""
......@@ -125,7 +135,7 @@ def proxy(client, target):
tqueue.extend(decode(buf))
else:
traffic("}.")
log.write("Client recv partial (%d): %s\n" % (len(buf), repr(buf)))
##log.write("Client recv partial (%d): %s\n" % (len(buf), repr(buf)))
cpartial = cpartial + buf
......@@ -157,7 +167,7 @@ def start_server(listen_port, target_host, target_port):
if tsock: tsock.close()
if __name__ == '__main__':
log = open("ws.log", 'w')
##log = open("ws.log", 'w')
try:
if len(sys.argv) != 4: raise
listen_port = int(sys.argv[1])
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment