mirror of
https://github.com/Koenkk/zigbee-OTA.git
synced 2026-06-24 14:43:49 +00:00
58 lines
2.0 KiB
JavaScript
58 lines
2.0 KiB
JavaScript
const assert = require('assert');
|
|
const upgradeFileIdentifier = Buffer.from([0x1E, 0xF1, 0xEE, 0x0B]);
|
|
|
|
function parseSubElement(buffer, position) {
|
|
const tagID = buffer.readUInt16LE(position);
|
|
const length = buffer.readUInt32LE(position + 2);
|
|
const data = buffer.slice(position + 6, position + 6 + length);
|
|
return {tagID, length, data};
|
|
}
|
|
|
|
function parseImage(buffer) {
|
|
const header = {
|
|
otaUpgradeFileIdentifier: buffer.subarray(0, 4),
|
|
otaHeaderVersion: buffer.readUInt16LE(4),
|
|
otaHeaderLength: buffer.readUInt16LE(6),
|
|
otaHeaderFieldControl: buffer.readUInt16LE(8),
|
|
manufacturerCode: buffer.readUInt16LE(10),
|
|
imageType: buffer.readUInt16LE(12),
|
|
fileVersion: buffer.readUInt32LE(14),
|
|
zigbeeStackVersion: buffer.readUInt16LE(18),
|
|
otaHeaderString: buffer.toString('utf8', 20, 52),
|
|
totalImageSize: buffer.readUInt32LE(52),
|
|
};
|
|
let headerPos = 56;
|
|
if (header.otaHeaderFieldControl & 1) {
|
|
header.securityCredentialVersion = buffer.readUInt8(headerPos);
|
|
headerPos += 1;
|
|
}
|
|
if (header.otaHeaderFieldControl & 2) {
|
|
header.upgradeFileDestination = buffer.subarray(headerPos, headerPos + 8);
|
|
headerPos += 8;
|
|
}
|
|
if (header.otaHeaderFieldControl & 4) {
|
|
header.minimumHardwareVersion = buffer.readUInt16LE(headerPos);
|
|
headerPos += 2;
|
|
header.maximumHardwareVersion = buffer.readUInt16LE(headerPos);
|
|
headerPos += 2;
|
|
}
|
|
|
|
const raw = buffer.slice(0, header.totalImageSize);
|
|
|
|
assert(Buffer.compare(header.otaUpgradeFileIdentifier, upgradeFileIdentifier) === 0, 'Not an OTA file');
|
|
|
|
let position = header.otaHeaderLength;
|
|
const elements = [];
|
|
while (position < header.totalImageSize) {
|
|
const element = parseSubElement(buffer, position);
|
|
elements.push(element);
|
|
position += element.data.length + 6;
|
|
}
|
|
|
|
assert(position === header.totalImageSize, 'Size mismatch');
|
|
return {header, elements, raw};
|
|
}
|
|
|
|
module.exports = {
|
|
parseImage
|
|
}; |