Mercurial > hg > rlgwebd
comparison rlgwebd.js @ 180:85fde763c7ed
Improve the clear-command recognition.
xterm and screen use different control sequences to clear the screen.
Both are now recognized.
| author | John "Elwin" Edwards |
|---|---|
| date | Fri, 16 Jan 2015 08:25:25 -0500 |
| parents | bf518a00190b |
| children | 926b0780bc44 |
comparison
equal
deleted
inserted
replaced
| 179:b745c37fd2ec | 180:85fde763c7ed |
|---|---|
| 18 var httpPort = 8080; | 18 var httpPort = 8080; |
| 19 var chrootDir = "/var/dgl/"; | 19 var chrootDir = "/var/dgl/"; |
| 20 var dropToUser = "rodney"; | 20 var dropToUser = "rodney"; |
| 21 var serveStaticRoot = "/var/www/"; // inside the chroot | 21 var serveStaticRoot = "/var/www/"; // inside the chroot |
| 22 | 22 |
| 23 var clearbufs = [ | |
| 24 new Buffer([27, 91, 72, 27, 91, 50, 74]), // xterm: CSI H CSI 2J | |
| 25 new Buffer([27, 91, 72, 27, 91, 74]) // screen: CSI H CSI J | |
| 26 ]; | |
| 27 | |
| 23 /* Data on the games available. */ | 28 /* Data on the games available. */ |
| 24 var games = { | 29 var games = { |
| 25 "rogue3": { | 30 "rogue3": { |
| 26 "name": "Rogue V3", | 31 "name": "Rogue V3", |
| 27 "uname": "rogue3", | 32 "uname": "rogue3", |
| 28 "suffix": ".r3sav", | 33 "suffix": ".r3sav", |
| 29 "path": "/usr/bin/rogue3", | 34 "path": "/usr/bin/rogue3" |
| 30 "clear": new Buffer([27, 91, 72, 27, 91, 50, 74]) // CSI H CSI 2J | |
| 31 }, | 35 }, |
| 32 "rogue4": { | 36 "rogue4": { |
| 33 "name": "Rogue V4", | 37 "name": "Rogue V4", |
| 34 "uname": "rogue4", | 38 "uname": "rogue4", |
| 35 "suffix": ".r4sav", | 39 "suffix": ".r4sav", |
| 36 "path": "/usr/bin/rogue4", | 40 "path": "/usr/bin/rogue4" |
| 37 "clear": new Buffer([27, 91, 72, 27, 91, 50, 74]) // CSI H CSI 2J | |
| 38 }, | 41 }, |
| 39 "rogue5": { | 42 "rogue5": { |
| 40 "name": "Rogue V5", | 43 "name": "Rogue V5", |
| 41 "uname": "rogue5", | 44 "uname": "rogue5", |
| 42 "suffix": ".r5sav", | 45 "suffix": ".r5sav", |
| 43 "path": "/usr/bin/rogue5", | 46 "path": "/usr/bin/rogue5" |
| 44 "clear": new Buffer([27, 91, 72, 27, 91, 50, 74]) // CSI H CSI 2J | |
| 45 }, | 47 }, |
| 46 "srogue": { | 48 "srogue": { |
| 47 "name": "Super-Rogue", | 49 "name": "Super-Rogue", |
| 48 "uname": "srogue", | 50 "uname": "srogue", |
| 49 "suffix": ".srsav", | 51 "suffix": ".srsav", |
| 50 "path": "/usr/bin/srogue", | 52 "path": "/usr/bin/srogue" |
| 51 "clear": new Buffer([27, 91, 72, 27, 91, 50, 74]) // CSI H CSI 2J | |
| 52 }, | 53 }, |
| 53 "arogue5": { | 54 "arogue5": { |
| 54 "name": "Advanced Rogue 5", | 55 "name": "Advanced Rogue 5", |
| 55 "uname": "arogue5", | 56 "uname": "arogue5", |
| 56 "suffix": ".ar5sav", | 57 "suffix": ".ar5sav", |
| 57 "path": "/usr/bin/arogue5", | 58 "path": "/usr/bin/arogue5" |
| 58 "clear": new Buffer([27, 91, 72, 27, 91, 50, 74]) // CSI H CSI 2J | |
| 59 } | 59 } |
| 60 }; | 60 }; |
| 61 | 61 |
| 62 /* Global state */ | 62 /* Global state */ |
| 63 var logins = {}; | 63 var logins = {}; |
| 150 ss.emit('data', buf); | 150 ss.emit('data', buf); |
| 151 } | 151 } |
| 152 this.term.on("data", ttyrec_chunk); | 152 this.term.on("data", ttyrec_chunk); |
| 153 this.framepush = function(chunk) { | 153 this.framepush = function(chunk) { |
| 154 /* If this chunk resets the screen, discard what preceded it. */ | 154 /* If this chunk resets the screen, discard what preceded it. */ |
| 155 if (bufncmp(chunk, this.game.clear, this.game.clear.length)) { | 155 if (isclear(chunk)) { |
| 156 this.framebuf = new Buffer(1024); | 156 this.framebuf = new Buffer(1024); |
| 157 this.frameoff = 0; | 157 this.frameoff = 0; |
| 158 } | 158 } |
| 159 /* Make sure there's space. */ | 159 /* Make sure there's space. */ |
| 160 while (this.framebuf.length < chunk.length + this.frameoff) { | 160 while (this.framebuf.length < chunk.length + this.frameoff) { |
| 261 this.rpos = 0; | 261 this.rpos = 0; |
| 262 this.framebuf = new Buffer(1024); | 262 this.framebuf = new Buffer(1024); |
| 263 this.frameoff = 0; | 263 this.frameoff = 0; |
| 264 this.framepush = function(chunk) { | 264 this.framepush = function(chunk) { |
| 265 /* If this chunk resets the screen, discard what preceded it. */ | 265 /* If this chunk resets the screen, discard what preceded it. */ |
| 266 var cgame = games[this.gname]; | 266 if (isclear(chunk)) { |
| 267 if (bufncmp(chunk, cgame.clear, cgame.clear.length)) { | |
| 268 tslog("DGL %s: clearing frame", ss.tag()); | |
| 269 this.framebuf = new Buffer(1024); | 267 this.framebuf = new Buffer(1024); |
| 270 this.frameoff = 0; | 268 this.frameoff = 0; |
| 271 } | 269 } |
| 272 /* Make sure there's space. */ | 270 /* Make sure there's space. */ |
| 273 while (this.framebuf.length < chunk.length + this.frameoff) { | 271 while (this.framebuf.length < chunk.length + this.frameoff) { |
| 298 } | 296 } |
| 299 ss.rpos += 12; | 297 ss.rpos += 12; |
| 300 /* Update timestamp, to within 1 second. */ | 298 /* Update timestamp, to within 1 second. */ |
| 301 ss.lasttime = new Date(1000 * buf.readUInt32LE(0)); | 299 ss.lasttime = new Date(1000 * buf.readUInt32LE(0)); |
| 302 var datalen = buf.readUInt32LE(8); | 300 var datalen = buf.readUInt32LE(8); |
| 303 //tslog("Allocating %d bytes", datalen); | |
| 304 if (datalen > 16384) { | 301 if (datalen > 16384) { |
| 302 // Something is probably wrong... | |
| 305 tslog("DGL %s: looking for %d bytes", ss.tag(), datalen); | 303 tslog("DGL %s: looking for %d bytes", ss.tag(), datalen); |
| 306 } | 304 } |
| 307 var databuf = new Buffer(datalen); | 305 var databuf = new Buffer(datalen); |
| 308 fs.read(ss.fd, databuf, 0, datalen, ss.rpos, function (err, n, buf) { | 306 fs.read(ss.fd, databuf, 0, datalen, ss.rpos, function (err, n, buf) { |
| 309 if (err || n < datalen) { | 307 if (err || n < datalen) { |
| 532 return false; | 530 return false; |
| 533 if (buf1[i] != buf2[i]) | 531 if (buf1[i] != buf2[i]) |
| 534 return false; | 532 return false; |
| 535 } | 533 } |
| 536 return true; | 534 return true; |
| 535 } | |
| 536 | |
| 537 function isclear(buf) { | |
| 538 for (var i = 0; i < clearbufs.length; i++) { | |
| 539 if (bufncmp(buf, clearbufs[i], clearbufs[i].length)) | |
| 540 return true; | |
| 541 } | |
| 542 return false; | |
| 537 } | 543 } |
| 538 | 544 |
| 539 function tslog() { | 545 function tslog() { |
| 540 arguments[0] = new Date().toISOString() + ": " + String(arguments[0]); | 546 arguments[0] = new Date().toISOString() + ": " + String(arguments[0]); |
| 541 console.log.apply(console, arguments); | 547 console.log.apply(console, arguments); |
