flashmagic.js
Version:
NXP LPC Microprocessor Programmer
241 lines (240 loc) • 8.59 kB
JavaScript
"use strict";
var Symbol = require('es6-symbol');
var SerialPort = require('serialport');
var ReturnCode = require('./ReturnCode');
var UNLOCK_CODE = 0x5A5A;
var LineQueue = (function () {
function LineQueue() {
this.queue = [];
}
LineQueue.prototype.drain = function () { this.queue.length = 0; };
LineQueue.prototype.pop = function () { return this.queue.shift(); };
LineQueue.prototype.push = function (data) { this.queue.push(data); };
return LineQueue;
}());
var VerboseLogger = (function () {
function VerboseLogger() {
}
VerboseLogger.prototype.log = function (msg) { console.log(msg); };
return VerboseLogger;
}());
var QuiteLogger = (function () {
function QuiteLogger() {
}
QuiteLogger.prototype.log = function (msg) { };
return QuiteLogger;
}());
var LINE_QUEUE = new LineQueue;
var _baudRateSym = Symbol();
var _bootVerSym = Symbol();
var _partIdSym = Symbol();
var InSystemProgramming = (function () {
function InSystemProgramming(path, baud, cclk) {
this.path = path;
this.cclk = cclk;
this.queue = LINE_QUEUE;
this.logger = new QuiteLogger();
this.echo = true;
this.reinitialize(baud, 1);
}
Object.defineProperty(InSystemProgramming, "VLAB_MODE", {
get: function () { return process.env['ISP'] === 'vlab'; },
enumerable: true,
configurable: true
});
;
Object.defineProperty(InSystemProgramming.prototype, "verbose", {
set: function (b) { this.logger = b ? new VerboseLogger() : new QuiteLogger(); },
enumerable: true,
configurable: true
});
InSystemProgramming.prototype.reinitialize = function (baud, stop) {
var _this = this;
this[_baudRateSym] = baud;
this.serialport = new SerialPort(this.path, {
baudRate: baud,
stopBits: stop,
parity: 'none',
parser: SerialPort.parsers.readline('\r\n'),
autoOpen: false
});
this.serialport.on('data', function (data) {
var s = data.toString();
_this.logger.log("---> " + s);
try {
_this.queue.push(s);
}
finally {
_this.queue = LINE_QUEUE;
}
});
};
InSystemProgramming.prototype.open = function () {
var _this = this;
return new Promise(function (resolve, reject) {
_this.serialport.open(function (error) {
return error ? reject(error) : resolve(_this);
});
});
};
InSystemProgramming.prototype.read = function (timeout) {
var _this = this;
if (timeout === void 0) { timeout = 1000; }
return new Promise(function (resolve, reject) {
var s = _this.queue.pop();
if (s) {
return resolve(s);
}
(function (to) {
_this.queue = {
push: function (data) {
clearTimeout(to);
resolve(data);
},
pop: function () { throw new Error('Not implemented'); },
drain: function () { throw new Error('Not implemented'); }
};
})(setTimeout(function () {
try {
reject(new Error("Timed out: > " + timeout + "ms"));
}
finally {
_this.queue = LINE_QUEUE;
}
}, timeout));
});
};
InSystemProgramming.prototype.write = function (data) {
var _this = this;
this.logger.log("<--- " + data.trim());
this.queue.drain();
return new Promise(function (resolve, reject) {
_this.serialport.write(data, function (error) {
if (error) {
return reject(error);
}
_this.serialport.drain(function (error) {
return error ? reject(error) : resolve(_this);
});
});
});
};
InSystemProgramming.prototype.writeln = function (data) {
return this.write(data + '\r\n');
};
InSystemProgramming.prototype.close = function () {
var _this = this;
return new Promise(function (resolve, reject) {
_this.serialport.close(function (error) {
_this.serialport = null;
return error ? reject(error) : resolve(_this);
});
});
};
InSystemProgramming.prototype.sendLine = function (data) {
var _this = this;
var p = this.writeln(data);
if (this.echo) {
p = p.then(function () {
return _this.read();
}).then(function (ack) {
if (ack !== data) {
throw new Error("Not acknowledged: " + JSON.stringify(ack));
}
return _this;
});
}
return p;
};
InSystemProgramming.prototype.sendCommand = function (data) {
var _this = this;
return this.sendLine(data).then(function () { return _this.assertSuccess(); });
};
InSystemProgramming.prototype.assertSuccess = function () {
var _this = this;
return this.read().then(function (data) {
if (!(/^\d+$/.test(data))) {
throw new TypeError("Not a number: " + JSON.stringify(data));
}
ReturnCode.rethrow(~~data);
return _this;
});
};
InSystemProgramming.prototype.assertOK = function () {
var _this = this;
return this.read().then(function (data) {
if (data !== 'OK') {
throw new Error("Not \"OK\": " + JSON.stringify(data));
}
return _this;
});
};
InSystemProgramming.prototype.assert = function (ack, timeout) {
var _this = this;
return this.read(timeout).then(function (data) {
if (data.match(ack) === null) {
throw new Error("Not /" + ack.source + "/: " + JSON.stringify(data));
}
return _this;
});
};
InSystemProgramming.prototype.reset = function () {
this.echo = true;
return this;
};
InSystemProgramming.prototype.unlock = function () {
return this.sendCommand("U " + UNLOCK_CODE);
};
InSystemProgramming.prototype.setEcho = function (echo) {
var _this = this;
return this.sendCommand("A " + (echo ? 1 : 0))
.then(function () {
_this.echo = echo;
return _this;
});
};
Object.defineProperty(InSystemProgramming.prototype, "baudRate", {
get: function () { return this[_baudRateSym]; },
enumerable: true,
configurable: true
});
InSystemProgramming.prototype.setBaudRate = function (baud, stop) {
var _this = this;
if (stop === void 0) { stop = 1; }
baud = ~~baud;
if (this.baudRate === baud) {
return Promise.resolve(this);
}
this[_baudRateSym] = baud;
return this.sendCommand("B " + baud + " " + stop)
.then(function () { return _this.close(); })
.then(function () { return _this.reinitialize(baud, stop); })
.then(function () { return _this.open(); });
};
Object.defineProperty(InSystemProgramming.prototype, "partIdentification", {
get: function () { return this[_partIdSym]; },
enumerable: true,
configurable: true
});
InSystemProgramming.prototype.readPartIdentification = function () {
var _this = this;
return this.sendCommand('J')
.then(function () { return _this.read(); })
.then(function (partId) { return _this[_partIdSym] = partId; });
};
Object.defineProperty(InSystemProgramming.prototype, "bootcodeVersion", {
get: function () { return this[_bootVerSym]; },
enumerable: true,
configurable: true
});
InSystemProgramming.prototype.readBootcodeVersion = function () {
var _this = this;
var major_ = '';
return this.sendCommand('K')
.then(function () { return _this.read(); })
.then(function (major) { return Promise.all([major, _this.read()]); })
.then(function (ver) { return _this[_bootVerSym] = ver[0] + "." + ver[1]; });
};
return InSystemProgramming;
}());
exports.InSystemProgramming = InSystemProgramming;