146 lines
4.6 KiB
JavaScript
Executable File
146 lines
4.6 KiB
JavaScript
Executable File
#!/usr/bin/env node
|
|
|
|
/**
|
|
* Copyright (C) 2016, Canonical Ltd.
|
|
* All rights reserved.
|
|
*
|
|
* This source code is licensed under the BSD-style license found in the
|
|
* LICENSE file in the root directory of this source tree. An additional grant
|
|
* of patent rights can be found in the PATENTS file in the same directory.
|
|
*
|
|
*/
|
|
|
|
console.debug = console.log;
|
|
|
|
|
|
var net = require('net');
|
|
var repl = require('repl');
|
|
var vm = require('vm');
|
|
var util = require('util');
|
|
var Buffer = require('buffer').Buffer;
|
|
var realmConstructor = require("./node_modules/realm/lib/index.js");
|
|
console.log("Loaded realmConstructor: " + realmConstructor);
|
|
|
|
var DEBUG = 1;
|
|
|
|
function rnUbuntuServer(readable, writable) {
|
|
console.reportErrorsAsExceptions = false; // XXX:
|
|
var sandbox = { console: console, util: util, outerRealmConstructor: realmConstructor };
|
|
vm.createContext(sandbox);
|
|
|
|
var state = 'start';
|
|
var length = 0;
|
|
var buffer = new Buffer(0);
|
|
|
|
var internalEval = function(code) {
|
|
DEBUG > 3 && console.error("-- internalEval: executing script(length=" + code.length + "): " + code.slice(0, 80) + " ... " + code.slice(-80));
|
|
DEBUG > 3 && console.error("-- before sandbox=" + util.inspect(sandbox, { colors: true, depth: null }));
|
|
var result = vm.runInContext(code, sandbox);
|
|
DEBUG > 3 && console.error("-- internalEval: result = " + result);
|
|
DEBUG > 3 && console.error("-- after sandbox=" + util.inspect(sandbox, { colors: true, depth: null }));
|
|
return result;
|
|
};
|
|
|
|
var sendResponse = function(result) {
|
|
function sendResponsePacket(response) {
|
|
const sizeBuf = new Buffer(4);
|
|
const dataBuf = new Buffer(response);
|
|
sizeBuf.writeUInt32LE(dataBuf.length, 0);
|
|
writable.write(sizeBuf);
|
|
writable.write(dataBuf);
|
|
}
|
|
|
|
var stringifiedResult = JSON.stringify(result);
|
|
DEBUG > 3 && console.error("-- sending result=" + stringifiedResult);
|
|
if (stringifiedResult === undefined) {
|
|
sendResponsePacket('undefined');
|
|
return;
|
|
}
|
|
sendResponsePacket(stringifiedResult);
|
|
}
|
|
|
|
readable.on('error', function (exc) {
|
|
console.warn("ignoring exception: " + exc);
|
|
});
|
|
|
|
readable.on('data', function(chunk) {
|
|
DEBUG > 2 && console.error("-- Data received from RN Client: state = " + state)
|
|
DEBUG > 2 && console.error("-- chunk length: " + chunk.length)
|
|
DEBUG > 2 && console.error("-- buffer length(original): " + buffer.length)
|
|
|
|
if (chunk == null || state === 'eof')
|
|
return;
|
|
|
|
buffer = Buffer.concat([buffer, chunk]);
|
|
DEBUG > 2 && console.error("-- buffer length(concat): " + buffer.length)
|
|
|
|
while(true) {
|
|
if (state === 'start') {
|
|
if (buffer.length < 4)
|
|
return;
|
|
length = buffer.readUInt32LE(0);
|
|
DEBUG > 2 && console.error("-- New Packet: length=" + length);
|
|
|
|
if (buffer.length >= length + 4) {
|
|
var result = internalEval(buffer.toString('utf8', 4, length + 4));
|
|
var tmpBuffer = new Buffer(buffer.length - 4 - length);
|
|
buffer.copy(tmpBuffer, 0, length + 4, buffer.length);
|
|
buffer = tmpBuffer;
|
|
sendResponse(result);
|
|
} else {
|
|
state = 'script';
|
|
}
|
|
}
|
|
|
|
if (state === 'script') {
|
|
DEBUG > 2 && console.error("-- Packet length: " + length);
|
|
if (buffer.length >= length + 4) {
|
|
var result = internalEval(buffer.toString('utf8', 4, length + 4));
|
|
var tmpBuffer = new Buffer(buffer.length - 4 - length);
|
|
buffer.copy(tmpBuffer, 0, length + 4, buffer.length);
|
|
buffer = tmpBuffer;
|
|
state = 'start';
|
|
sendResponse(result);
|
|
} else {
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
});
|
|
|
|
readable.on('end', function() {
|
|
state = 'eof';
|
|
DEBUG && console.error("-- Session ended");
|
|
});
|
|
}
|
|
|
|
var closeDangerousConnection = function(sock) {
|
|
var remoteAddress = sock.remoteAddress;
|
|
if(remoteAddress.indexOf("127.0.0.1") == -1) {
|
|
console.log("WARN: connection not from localhost, will be closed: ", remoteAddress);
|
|
sock.destroy();
|
|
return true;
|
|
} else {
|
|
console.log("Connection from: ", remoteAddress);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
if (process.argv.indexOf('--pipe') != -1) {
|
|
console.log = console.error
|
|
rnUbuntuServer(process.stdin, process.stdout);
|
|
} else {
|
|
var port = process.env['REACT_SERVER_PORT'] || 5000;
|
|
process.argv.forEach((val, index) => {
|
|
if (val == '--port') {
|
|
port = process.argv[++index];
|
|
}
|
|
});
|
|
|
|
var server = net.createServer((sock) => {
|
|
DEBUG && console.error("-- Connection from RN client");
|
|
if(!closeDangerousConnection(sock))
|
|
rnUbuntuServer(sock, sock);
|
|
}).listen(port, function() { console.error("-- Server starting") });
|
|
}
|