Implement message order correction on the server side.

rlgwebd can now correct for the client's messages arriving in the wrong
order, in theory.  I haven't found a good way of testing it yet.
This commit is contained in:
John "Elwin" Edwards 2012-05-24 11:36:57 -07:00
parent c1856a6184
commit 53d5e7dd0d

View file

@ -61,6 +61,7 @@ function TermSession(game, user, files, dims) {
this.nsend = 0; this.nsend = 0;
this.nrecv = 0; this.nrecv = 0;
this.msgQ = [] this.msgQ = []
this.Qtimeout = null;
/* Set up the sizes. */ /* Set up the sizes. */
this.w = Math.floor(Number(dims[1])); this.w = Math.floor(Number(dims[1]));
if (!(this.w > 0 && this.w < 256)) if (!(this.w > 0 && this.w < 256))
@ -106,10 +107,63 @@ function TermSession(game, user, files, dims) {
/* Wait for all the data to get collected */ /* Wait for all the data to get collected */
setTimeout(ss.cleanup, 1000); setTimeout(ss.cleanup, 1000);
}); });
this.write = function (data) { this.write = function (data, n) {
if (this.alive) if (!this.alive || typeof (n) != "number") {
return;
}
//console.log("Got message " + n);
var oindex = n - this.nrecv;
if (oindex === 0) {
//console.log("Writing message " + n);
this.child.stdin.write(data); this.child.stdin.write(data);
/* Otherwise, throw some kind of exception? */ this.nrecv++;
var next;
while ((next = this.msgQ.shift()) !== undefined) {
//console.log("Writing message " + this.nrecv);
this.child.stdin.write(next);
this.nrecv++;
}
if (this.msgQ.length == 0 && this.Qtimeout) {
clearTimeout(this.Qtimeout);
this.Qtimeout = null;
}
}
else if (oindex > 0 && oindex <= 1024) {
console.log("Stashing message " + n + " at " + (oindex - 1));
this.msgQ[oindex - 1] = data;
if (!this.Qtimeout) {
var nextn = this.nrecv + this.msgQ.length + 1;
this.Qtimeout = setTimeout(this.flushQ, 30000, this, nextn);
}
}
/* Otherwise, discard it */
return;
};
this.flushQ = function (session, n) {
/* Callback for when an unreceived message times out.
* n is the first empty space that will not be given up on. */
if (!session.alive)
return;
session.nrecv++;
var next;
/* Clear the queue up to n */
while (session.nrecv < n) {
next = session.msgQ.shift();
if (next !== undefined)
session.child.stdin.write(next);
session.nrecv++;
}
/* Clear out anything that's ready. */
while ((next = session.msgQ.shift()) !== undefined) {
session.child.stdin.write(next);
session.nrecv++;
}
/* Now set another timeout if necessary. */
if (session.msgQ.length != 0) {
var nextn = session.nrecv + session.msgQ.length + 1;
session.Qtimeout = setTimeout(session.flushQ, 30000, session, nextn);
}
console.log("Flushing queue for session " + session.sessid);
}; };
this.read = function () { this.read = function () {
if (this.data.length == 0) if (this.data.length == 0)
@ -534,7 +588,7 @@ function handler(req, res) {
} }
keybuf = new Buffer(hexstr, "hex"); keybuf = new Buffer(hexstr, "hex");
/* TODO OoO correction */ /* TODO OoO correction */
cterm.write(keybuf); cterm.write(keybuf, formdata.n);
} }
readFeed(res, cterm); readFeed(res, cterm);
} }